"Fossies" - the Fresh Open Source Software Archive

Member "glusterfs-8.2/xlators/cluster/dht/src/dht-linkfile.c" (16 Sep 2020, 8998 Bytes) of package /linux/misc/glusterfs-8.2.tar.gz:


As a special service "Fossies" has tried to format the requested source page into HTML format using (guessed) C and C++ source code syntax highlighting (style: standard) with prefixed line numbers and code folding option. Alternatively you can here view or download the uninterpreted source code file. For more information about "dht-linkfile.c" see the Fossies "Dox" file reference documentation.

    1 /*
    2   Copyright (c) 2008-2012 Red Hat, Inc. <http://www.redhat.com>
    3   This file is part of GlusterFS.
    4 
    5   This file is licensed to you under your choice of the GNU Lesser
    6   General Public License, version 3 or any later version (LGPLv3 or
    7   later), or the GNU General Public License, version 2 (GPLv2), in all
    8   cases as published by the Free Software Foundation.
    9 */
   10 
   11 #include <glusterfs/compat.h>
   12 #include "dht-common.h"
   13 
   14 static int
   15 dht_linkfile_lookup_cbk(call_frame_t *frame, void *cookie, xlator_t *this,
   16                         int op_ret, int op_errno, inode_t *inode,
   17                         struct iatt *stbuf, dict_t *xattr,
   18                         struct iatt *postparent)
   19 {
   20     char is_linkfile = 0;
   21     dht_conf_t *conf = NULL;
   22     dht_local_t *local = NULL;
   23     xlator_t *prev = NULL;
   24     char gfid[GF_UUID_BUF_SIZE] = {0};
   25 
   26     local = frame->local;
   27     prev = cookie;
   28     conf = this->private;
   29 
   30     if (op_ret)
   31         goto out;
   32 
   33     gf_uuid_unparse(local->loc.gfid, gfid);
   34 
   35     is_linkfile = check_is_linkfile(inode, stbuf, xattr, conf->link_xattr_name);
   36     if (!is_linkfile)
   37         gf_smsg(this->name, GF_LOG_WARNING, 0, DHT_MSG_NOT_LINK_FILE_ERROR,
   38                 "name=%s", prev->name, "path=%s", local->loc.path, "gfid=%s",
   39                 gfid, NULL);
   40 out:
   41     local->linkfile.linkfile_cbk(frame, cookie, this, op_ret, op_errno, inode,
   42                                  stbuf, postparent, postparent, xattr);
   43     return 0;
   44 }
   45 
   46 static int
   47 dht_linkfile_create_cbk(call_frame_t *frame, void *cookie, xlator_t *this,
   48                         int op_ret, int op_errno, inode_t *inode,
   49                         struct iatt *stbuf, struct iatt *preparent,
   50                         struct iatt *postparent, dict_t *xdata)
   51 {
   52     dht_local_t *local = NULL;
   53     xlator_t *subvol = NULL;
   54     dict_t *xattrs = NULL;
   55     dht_conf_t *conf = NULL;
   56     int ret = -1;
   57 
   58     local = frame->local;
   59 
   60     if (!op_ret)
   61         local->linked = _gf_true;
   62 
   63     FRAME_SU_UNDO(frame, dht_local_t);
   64 
   65     if (op_ret && (op_errno == EEXIST)) {
   66         conf = this->private;
   67         subvol = cookie;
   68         if (!subvol)
   69             goto out;
   70         xattrs = dict_new();
   71         if (!xattrs)
   72             goto out;
   73         ret = dict_set_uint32(xattrs, conf->link_xattr_name, 256);
   74         if (ret) {
   75             gf_smsg(this->name, GF_LOG_ERROR, 0, DHT_MSG_DICT_SET_FAILED,
   76                     "mame=%s", conf->link_xattr_name, NULL);
   77             goto out;
   78         }
   79 
   80         STACK_WIND_COOKIE(frame, dht_linkfile_lookup_cbk, subvol, subvol,
   81                           subvol->fops->lookup, &local->linkfile.loc, xattrs);
   82         if (xattrs)
   83             dict_unref(xattrs);
   84         return 0;
   85     }
   86 out:
   87     local->linkfile.linkfile_cbk(frame, cookie, this, op_ret, op_errno, inode,
   88                                  stbuf, preparent, postparent, xdata);
   89     if (xattrs)
   90         dict_unref(xattrs);
   91     return 0;
   92 }
   93 
   94 int
   95 dht_linkfile_create(call_frame_t *frame, fop_mknod_cbk_t linkfile_cbk,
   96                     xlator_t *this, xlator_t *tovol, xlator_t *fromvol,
   97                     loc_t *loc)
   98 {
   99     dht_local_t *local = NULL;
  100     dict_t *dict = NULL;
  101     int need_unref = 0;
  102     int ret = 0;
  103     dht_conf_t *conf = this->private;
  104     char gfid[GF_UUID_BUF_SIZE] = {0};
  105 
  106     local = frame->local;
  107     local->linkfile.linkfile_cbk = linkfile_cbk;
  108     local->linkfile.srcvol = tovol;
  109     loc_copy(&local->linkfile.loc, loc);
  110 
  111     local->linked = _gf_false;
  112 
  113     dict = local->params;
  114     if (!dict) {
  115         dict = dict_new();
  116         if (!dict)
  117             goto out;
  118         need_unref = 1;
  119     }
  120 
  121     if (!gf_uuid_is_null(local->gfid)) {
  122         gf_uuid_unparse(local->gfid, gfid);
  123 
  124         ret = dict_set_gfuuid(dict, "gfid-req", local->gfid, true);
  125         if (ret)
  126             gf_smsg("dht-linkfile", GF_LOG_INFO, 0, DHT_MSG_DICT_SET_FAILED,
  127                     "path=%s", loc->path, "gfid=%s", gfid, NULL);
  128     } else {
  129         gf_uuid_unparse(loc->gfid, gfid);
  130     }
  131 
  132     ret = dict_set_str(dict, GLUSTERFS_INTERNAL_FOP_KEY, "yes");
  133     if (ret)
  134         gf_smsg("dht-linkfile", GF_LOG_INFO, 0, DHT_MSG_DICT_SET_FAILED,
  135                 "path=%s", loc->path, "key=%s", GLUSTERFS_INTERNAL_FOP_KEY,
  136                 "gfid=%s", gfid, NULL);
  137 
  138     ret = dict_set_str(dict, conf->link_xattr_name, tovol->name);
  139 
  140     if (ret < 0) {
  141         gf_smsg(frame->this->name, GF_LOG_INFO, 0, DHT_MSG_CREATE_LINK_FAILED,
  142                 "path=%s", loc->path, "gfid=%s", gfid, NULL);
  143         goto out;
  144     }
  145 
  146     local->link_subvol = fromvol;
  147     /* Always create as root:root. dht_linkfile_attr_heal fixes the
  148      * ownsership */
  149     FRAME_SU_DO(frame, dht_local_t);
  150     STACK_WIND_COOKIE(frame, dht_linkfile_create_cbk, fromvol, fromvol,
  151                       fromvol->fops->mknod, loc, S_IFREG | DHT_LINKFILE_MODE, 0,
  152                       0, dict);
  153 
  154     if (need_unref && dict)
  155         dict_unref(dict);
  156 
  157     return 0;
  158 out:
  159     local->linkfile.linkfile_cbk(frame, frame->this, frame->this, -1, ENOMEM,
  160                                  loc->inode, NULL, NULL, NULL, NULL);
  161 
  162     if (need_unref && dict)
  163         dict_unref(dict);
  164 
  165     return 0;
  166 }
  167 
  168 int
  169 dht_linkfile_unlink_cbk(call_frame_t *frame, void *cookie, xlator_t *this,
  170                         int32_t op_ret, int32_t op_errno,
  171                         struct iatt *preparent, struct iatt *postparent,
  172                         dict_t *xdata)
  173 {
  174     dht_local_t *local = NULL;
  175     xlator_t *subvol = NULL;
  176     char gfid[GF_UUID_BUF_SIZE] = {0};
  177 
  178     local = frame->local;
  179     subvol = cookie;
  180 
  181     if (op_ret == -1) {
  182         gf_uuid_unparse(local->loc.gfid, gfid);
  183         gf_smsg(this->name, GF_LOG_INFO, op_errno, DHT_MSG_UNLINK_FAILED,
  184                 "path=%s", local->loc.path, "gfid=%s", gfid, "subvolume=%s",
  185                 subvol->name, NULL);
  186     }
  187 
  188     DHT_STACK_DESTROY(frame);
  189 
  190     return 0;
  191 }
  192 
  193 int
  194 dht_linkfile_unlink(call_frame_t *frame, xlator_t *this, xlator_t *subvol,
  195                     loc_t *loc)
  196 {
  197     call_frame_t *unlink_frame = NULL;
  198     dht_local_t *unlink_local = NULL;
  199 
  200     unlink_frame = copy_frame(frame);
  201     if (!unlink_frame) {
  202         goto err;
  203     }
  204 
  205     /* Using non-fop value here, as anyways, 'local->fop' is not used in
  206        this particular case */
  207     unlink_local = dht_local_init(unlink_frame, loc, NULL, GF_FOP_MAXVALUE);
  208     if (!unlink_local) {
  209         goto err;
  210     }
  211 
  212     STACK_WIND_COOKIE(unlink_frame, dht_linkfile_unlink_cbk, subvol, subvol,
  213                       subvol->fops->unlink, &unlink_local->loc, 0, NULL);
  214 
  215     return 0;
  216 err:
  217     if (unlink_frame)
  218         DHT_STACK_DESTROY(unlink_frame);
  219 
  220     return -1;
  221 }
  222 
  223 xlator_t *
  224 dht_linkfile_subvol(xlator_t *this, inode_t *inode, struct iatt *stbuf,
  225                     dict_t *xattr)
  226 {
  227     dht_conf_t *conf = NULL;
  228     xlator_t *subvol = NULL;
  229     void *volname = NULL;
  230     int i = 0, ret = 0;
  231 
  232     conf = this->private;
  233 
  234     if (!xattr)
  235         goto out;
  236 
  237     ret = dict_get_ptr(xattr, conf->link_xattr_name, &volname);
  238 
  239     if ((-1 == ret) || !volname)
  240         goto out;
  241 
  242     for (i = 0; i < conf->subvolume_cnt; i++) {
  243         if (strcmp(conf->subvolumes[i]->name, (char *)volname) == 0) {
  244             subvol = conf->subvolumes[i];
  245             break;
  246         }
  247     }
  248 
  249 out:
  250     return subvol;
  251 }
  252 
  253 static int
  254 dht_linkfile_setattr_cbk(call_frame_t *frame, void *cookie, xlator_t *this,
  255                          int op_ret, int op_errno, struct iatt *statpre,
  256                          struct iatt *statpost, dict_t *xdata)
  257 {
  258     dht_local_t *local = NULL;
  259     loc_t *loc = NULL;
  260 
  261     local = frame->local;
  262     loc = &local->loc;
  263 
  264     if (op_ret)
  265         gf_smsg(this->name, GF_LOG_ERROR, op_errno, DHT_MSG_SETATTR_FAILED,
  266                 "path=%s", (loc->path ? loc->path : "NULL"), "gfid=%s",
  267                 uuid_utoa(local->gfid), NULL);
  268 
  269     DHT_STACK_DESTROY(frame);
  270 
  271     return 0;
  272 }
  273 
  274 int
  275 dht_linkfile_attr_heal(call_frame_t *frame, xlator_t *this)
  276 {
  277     int ret = -1;
  278     call_frame_t *copy = NULL;
  279     dht_local_t *local = NULL;
  280     dht_local_t *copy_local = NULL;
  281     xlator_t *subvol = NULL;
  282     struct iatt stbuf = {
  283         0,
  284     };
  285     dict_t *xattr = NULL;
  286 
  287     local = frame->local;
  288 
  289     GF_VALIDATE_OR_GOTO("dht", local, out);
  290     GF_VALIDATE_OR_GOTO("dht", local->link_subvol, out);
  291 
  292     if (local->stbuf.ia_type == IA_INVAL)
  293         return 0;
  294 
  295     DHT_MARK_FOP_INTERNAL(xattr);
  296 
  297     gf_uuid_copy(local->loc.gfid, local->stbuf.ia_gfid);
  298 
  299     copy = copy_frame(frame);
  300 
  301     if (!copy)
  302         goto out;
  303 
  304     copy_local = dht_local_init(copy, &local->loc, NULL, 0);
  305 
  306     if (!copy_local)
  307         goto out;
  308 
  309     stbuf = local->stbuf;
  310     subvol = local->link_subvol;
  311 
  312     copy->local = copy_local;
  313 
  314     FRAME_SU_DO(copy, dht_local_t);
  315 
  316     STACK_WIND(copy, dht_linkfile_setattr_cbk, subvol, subvol->fops->setattr,
  317                &copy_local->loc, &stbuf, (GF_SET_ATTR_UID | GF_SET_ATTR_GID),
  318                xattr);
  319     ret = 0;
  320 out:
  321     if ((ret < 0) && (copy))
  322         DHT_STACK_DESTROY(copy);
  323 
  324     if (xattr)
  325         dict_unref(xattr);
  326 
  327     return ret;
  328 }