887953
From 9be984ac2b71423b72ab3b1fa45b4d77a263ce1e Mon Sep 17 00:00:00 2001
887953
From: Krutika Dhananjay <kdhananj@redhat.com>
887953
Date: Wed, 28 Mar 2018 12:09:27 +0530
887953
Subject: [PATCH 426/444] features/shard: Make operations on internal
887953
 directories generic
887953
887953
> Upstream: https://review.gluster.org/19892
887953
> BUG: 1568521
887953
> Change-Id: Iea7ad2102220c6d415909f8caef84167ce2d6818
887953
887953
Change-Id: Iea7ad2102220c6d415909f8caef84167ce2d6818
887953
BUG: 1520882
887953
Signed-off-by: Krutika Dhananjay <kdhananj@redhat.com>
887953
Reviewed-on: https://code.engineering.redhat.com/gerrit/154860
887953
Tested-by: RHGS Build Bot <nigelb@redhat.com>
887953
Reviewed-by: Xavi Hernandez <xhernandez@redhat.com>
887953
---
887953
 xlators/features/shard/src/shard.c | 295 +++++++++++++++++++++++++------------
887953
 xlators/features/shard/src/shard.h |   4 +
887953
 2 files changed, 206 insertions(+), 93 deletions(-)
887953
887953
diff --git a/xlators/features/shard/src/shard.c b/xlators/features/shard/src/shard.c
887953
index f5fb181..5ff04df 100644
887953
--- a/xlators/features/shard/src/shard.c
887953
+++ b/xlators/features/shard/src/shard.c
887953
@@ -546,30 +546,55 @@ shard_call_count_return (call_frame_t *frame)
887953
         return call_count;
887953
 }
887953
 
887953
+static char *
887953
+shard_internal_dir_string (shard_internal_dir_type_t type)
887953
+{
887953
+        char *str = NULL;
887953
+
887953
+        switch (type) {
887953
+        case SHARD_INTERNAL_DIR_DOT_SHARD:
887953
+                str = ".shard";
887953
+                break;
887953
+        default:
887953
+                break;
887953
+        }
887953
+        return str;
887953
+}
887953
+
887953
 static int
887953
-shard_init_dot_shard_loc (xlator_t *this, shard_local_t *local)
887953
+shard_init_internal_dir_loc (xlator_t *this, shard_local_t *local,
887953
+                             shard_internal_dir_type_t type)
887953
 {
887953
-        int    ret           = -1;
887953
-        loc_t *dot_shard_loc = NULL;
887953
+        int    ret              = -1;
887953
+        char  *bname            = NULL;
887953
+        loc_t *internal_dir_loc = NULL;
887953
 
887953
         if (!local)
887953
                 return -1;
887953
 
887953
-        dot_shard_loc = &local->dot_shard_loc;
887953
-        dot_shard_loc->inode = inode_new (this->itable);
887953
-        dot_shard_loc->parent = inode_ref (this->itable->root);
887953
-        ret = inode_path (dot_shard_loc->parent, GF_SHARD_DIR,
887953
-                          (char **)&dot_shard_loc->path);
887953
-        if (ret < 0 || !(dot_shard_loc->inode)) {
887953
+        switch (type) {
887953
+        case SHARD_INTERNAL_DIR_DOT_SHARD:
887953
+                internal_dir_loc = &local->dot_shard_loc;
887953
+                bname = GF_SHARD_DIR;
887953
+                break;
887953
+        default:
887953
+                break;
887953
+        }
887953
+
887953
+        internal_dir_loc->inode = inode_new (this->itable);
887953
+        internal_dir_loc->parent = inode_ref (this->itable->root);
887953
+        ret = inode_path (internal_dir_loc->parent, bname,
887953
+                          (char **)&internal_dir_loc->path);
887953
+        if (ret < 0 || !(internal_dir_loc->inode)) {
887953
                 gf_msg (this->name, GF_LOG_ERROR, 0,
887953
                         SHARD_MSG_INODE_PATH_FAILED,
887953
-                        "Inode path failed on %s", GF_SHARD_DIR);
887953
+                        "Inode path failed on %s", bname);
887953
                 goto out;
887953
         }
887953
 
887953
-        dot_shard_loc->name = strrchr (dot_shard_loc->path, '/');
887953
-        if (dot_shard_loc->name)
887953
-                dot_shard_loc->name++;
887953
+        internal_dir_loc->name = strrchr (internal_dir_loc->path, '/');
887953
+        if (internal_dir_loc->name)
887953
+                internal_dir_loc->name++;
887953
 
887953
         ret = 0;
887953
 out:
887953
@@ -1029,28 +1054,42 @@ out:
887953
 }
887953
 
887953
 static inode_t *
887953
-shard_link_dot_shard_inode (shard_local_t *local, inode_t *inode,
887953
-                            struct iatt *buf)
887953
+shard_link_internal_dir_inode (shard_local_t *local, inode_t *inode,
887953
+                               struct iatt *buf, shard_internal_dir_type_t type)
887953
 {
887953
         inode_t       *linked_inode = NULL;
887953
         shard_priv_t  *priv         = NULL;
887953
+        char          *bname        = NULL;
887953
+        inode_t       **priv_inode  = NULL;
887953
 
887953
         priv = THIS->private;
887953
 
887953
-        linked_inode = inode_link (inode, inode->table->root, ".shard", buf);
887953
+        switch (type) {
887953
+        case SHARD_INTERNAL_DIR_DOT_SHARD:
887953
+                bname = ".shard";
887953
+                priv_inode = &priv->dot_shard_inode;
887953
+                break;
887953
+        default:
887953
+                break;
887953
+        }
887953
+
887953
+        linked_inode = inode_link (inode, inode->table->root, bname, buf);
887953
         inode_lookup (linked_inode);
887953
-        priv->dot_shard_inode = linked_inode;
887953
+        *priv_inode = linked_inode;
887953
         return linked_inode;
887953
 }
887953
 
887953
 
887953
 int
887953
-shard_refresh_dot_shard_cbk (call_frame_t *frame, void *cookie, xlator_t *this,
887953
-                             int32_t op_ret, int32_t op_errno, inode_t *inode,
887953
-                             struct iatt *buf, dict_t *xdata,
887953
-                             struct iatt *postparent)
887953
+shard_refresh_internal_dir_cbk (call_frame_t *frame, void *cookie,
887953
+                                xlator_t *this, int32_t op_ret,
887953
+                                int32_t op_errno, inode_t *inode,
887953
+                                struct iatt *buf, dict_t *xdata,
887953
+                                struct iatt *postparent)
887953
 {
887953
-        shard_local_t *local = NULL;
887953
+        shard_local_t             *local           = NULL;
887953
+        inode_t                   *linked_inode    = NULL;
887953
+        shard_internal_dir_type_t  type            = (shard_internal_dir_type_t) cookie;
887953
 
887953
         local = frame->local;
887953
 
887953
@@ -1061,27 +1100,37 @@ shard_refresh_dot_shard_cbk (call_frame_t *frame, void *cookie, xlator_t *this,
887953
         }
887953
 
887953
         /* To-Do: Fix refcount increment per call to
887953
-         * shard_link_dot_shard_inode().
887953
+         * shard_link_internal_dir_inode().
887953
          */
887953
-        shard_link_dot_shard_inode (local, inode, buf);
887953
-        shard_inode_ctx_set_refreshed_flag (inode, this);
887953
+        linked_inode = shard_link_internal_dir_inode (local, inode, buf, type);
887953
+        shard_inode_ctx_set_refreshed_flag (linked_inode, this);
887953
 out:
887953
         shard_common_resolve_shards (frame, this, local->post_res_handler);
887953
         return 0;
887953
 }
887953
 
887953
 int
887953
-shard_refresh_dot_shard (call_frame_t *frame, xlator_t *this)
887953
+shard_refresh_internal_dir (call_frame_t *frame, xlator_t *this,
887953
+                            shard_internal_dir_type_t type)
887953
 {
887953
         loc_t          loc       = {0,};
887953
         inode_t       *inode     = NULL;
887953
         shard_priv_t  *priv      = NULL;
887953
         shard_local_t *local     = NULL;
887953
+        uuid_t         gfid      = {0,};
887953
 
887953
         local = frame->local;
887953
         priv = this->private;
887953
 
887953
-        inode = inode_find (this->itable, priv->dot_shard_gfid);
887953
+        switch (type) {
887953
+        case SHARD_INTERNAL_DIR_DOT_SHARD:
887953
+                gf_uuid_copy (gfid, priv->dot_shard_gfid);
887953
+                break;
887953
+        default:
887953
+                break;
887953
+        }
887953
+
887953
+        inode = inode_find (this->itable, gfid);
887953
 
887953
         if (!shard_inode_ctx_needs_lookup (inode, this)) {
887953
                 local->op_ret = 0;
887953
@@ -1092,10 +1141,11 @@ shard_refresh_dot_shard (call_frame_t *frame, xlator_t *this)
887953
          * call to inode_find()
887953
          */
887953
         loc.inode = inode;
887953
-        gf_uuid_copy (loc.gfid, priv->dot_shard_gfid);
887953
+        gf_uuid_copy (loc.gfid, gfid);
887953
 
887953
-        STACK_WIND (frame, shard_refresh_dot_shard_cbk, FIRST_CHILD(this),
887953
-                    FIRST_CHILD(this)->fops->lookup, &loc, NULL);
887953
+        STACK_WIND_COOKIE (frame, shard_refresh_internal_dir_cbk,
887953
+                           (void *)(long) type, FIRST_CHILD(this),
887953
+                           FIRST_CHILD(this)->fops->lookup, &loc, NULL);
887953
         loc_wipe (&loc;;
887953
 
887953
         return 0;
887953
@@ -1106,13 +1156,14 @@ out:
887953
 }
887953
 
887953
 int
887953
-shard_lookup_dot_shard_cbk (call_frame_t *frame, void *cookie, xlator_t *this,
887953
-                            int32_t op_ret, int32_t op_errno, inode_t *inode,
887953
-                            struct iatt *buf, dict_t *xdata,
887953
-                            struct iatt *postparent)
887953
+shard_lookup_internal_dir_cbk (call_frame_t *frame, void *cookie, xlator_t *this,
887953
+                               int32_t op_ret, int32_t op_errno, inode_t *inode,
887953
+                               struct iatt *buf, dict_t *xdata,
887953
+                               struct iatt *postparent)
887953
 {
887953
-        inode_t       *link_inode = NULL;
887953
-        shard_local_t *local      = NULL;
887953
+        inode_t                   *link_inode = NULL;
887953
+        shard_local_t             *local      = NULL;
887953
+        shard_internal_dir_type_t  type       = (shard_internal_dir_type_t) cookie;
887953
 
887953
         local = frame->local;
887953
 
887953
@@ -1124,17 +1175,17 @@ shard_lookup_dot_shard_cbk (call_frame_t *frame, void *cookie, xlator_t *this,
887953
 
887953
         if (!IA_ISDIR (buf->ia_type)) {
887953
                 gf_msg (this->name, GF_LOG_CRITICAL, 0,
887953
-                        SHARD_MSG_DOT_SHARD_NODIR, "/.shard already exists and "
887953
-                        "is not a directory. Please remove /.shard from all "
887953
-                        "bricks and try again");
887953
+                        SHARD_MSG_DOT_SHARD_NODIR, "%s already exists and "
887953
+                        "is not a directory. Please remove it from all bricks "
887953
+                        "and try again", shard_internal_dir_string (type));
887953
                 local->op_ret = -1;
887953
                 local->op_errno = EIO;
887953
                 goto unwind;
887953
         }
887953
 
887953
-        link_inode = shard_link_dot_shard_inode (local, inode, buf);
887953
+        link_inode = shard_link_internal_dir_inode (local, inode, buf, type);
887953
         if (link_inode != inode) {
887953
-                shard_refresh_dot_shard (frame, this);
887953
+                shard_refresh_internal_dir (frame, this, type);
887953
         } else {
887953
                 shard_inode_ctx_set_refreshed_flag (link_inode, this);
887953
                 shard_common_resolve_shards (frame, this,
887953
@@ -1148,18 +1199,26 @@ unwind:
887953
 }
887953
 
887953
 int
887953
-shard_lookup_dot_shard (call_frame_t *frame, xlator_t *this,
887953
-                        shard_post_resolve_fop_handler_t post_res_handler)
887953
+shard_lookup_internal_dir (call_frame_t *frame, xlator_t *this,
887953
+                           shard_post_resolve_fop_handler_t post_res_handler,
887953
+                           shard_internal_dir_type_t type)
887953
 {
887953
         int                 ret       = -1;
887953
         dict_t             *xattr_req = NULL;
887953
         shard_priv_t       *priv      = NULL;
887953
         shard_local_t      *local     = NULL;
887953
+        uuid_t             *gfid      = NULL;
887953
+        loc_t              *loc       = NULL;
887953
+        gf_boolean_t        free_gfid  = _gf_true;
887953
 
887953
         local = frame->local;
887953
         priv = this->private;
887953
         local->post_res_handler = post_res_handler;
887953
 
887953
+        gfid = GF_CALLOC (1, sizeof(uuid_t), gf_common_mt_uuid_t);
887953
+        if (!gfid)
887953
+                goto err;
887953
+
887953
         xattr_req = dict_new ();
887953
         if (!xattr_req) {
887953
                 local->op_ret = -1;
887953
@@ -1167,26 +1226,38 @@ shard_lookup_dot_shard (call_frame_t *frame, xlator_t *this,
887953
                 goto err;
887953
         }
887953
 
887953
-        ret = dict_set_static_bin (xattr_req, "gfid-req", priv->dot_shard_gfid,
887953
-                                   16);
887953
+        switch (type) {
887953
+        case SHARD_INTERNAL_DIR_DOT_SHARD:
887953
+                gf_uuid_copy (*gfid, priv->dot_shard_gfid);
887953
+                loc = &local->dot_shard_loc;
887953
+                break;
887953
+        default:
887953
+                break;
887953
+        }
887953
+
887953
+        ret = dict_set_bin (xattr_req, "gfid-req", *gfid, 16);
887953
         if (ret) {
887953
                 gf_msg (this->name, GF_LOG_ERROR, 0, SHARD_MSG_DICT_SET_FAILED,
887953
-                        "Failed to set gfid of /.shard into dict");
887953
+                        "Failed to set gfid of %s into dict",
887953
+                        shard_internal_dir_string (type));
887953
                 local->op_ret = -1;
887953
                 local->op_errno = ENOMEM;
887953
                 goto err;
887953
+        } else {
887953
+                free_gfid = _gf_false;
887953
         }
887953
 
887953
-        STACK_WIND (frame, shard_lookup_dot_shard_cbk, FIRST_CHILD(this),
887953
-                    FIRST_CHILD(this)->fops->lookup, &local->dot_shard_loc,
887953
-                    xattr_req);
887953
-
887953
+        STACK_WIND_COOKIE (frame, shard_lookup_internal_dir_cbk,
887953
+                           (void *) (long) type, FIRST_CHILD(this),
887953
+                           FIRST_CHILD(this)->fops->lookup, loc, xattr_req);
887953
         dict_unref (xattr_req);
887953
         return 0;
887953
 
887953
 err:
887953
         if (xattr_req)
887953
                 dict_unref (xattr_req);
887953
+        if (free_gfid)
887953
+                GF_FREE (gfid);
887953
         post_res_handler (frame, this);
887953
         return 0;
887953
 }
887953
@@ -2203,14 +2274,17 @@ shard_truncate_begin (call_frame_t *frame, xlator_t *this)
887953
         local->dot_shard_loc.inode = inode_find (this->itable,
887953
                                                  priv->dot_shard_gfid);
887953
         if (!local->dot_shard_loc.inode) {
887953
-                ret = shard_init_dot_shard_loc (this, local);
887953
+                ret = shard_init_internal_dir_loc (this, local,
887953
+                                                   SHARD_INTERNAL_DIR_DOT_SHARD);
887953
                 if (ret)
887953
                         goto err;
887953
-                shard_lookup_dot_shard (frame, this,
887953
-                                        shard_post_resolve_truncate_handler);
887953
+                shard_lookup_internal_dir (frame, this,
887953
+                                           shard_post_resolve_truncate_handler,
887953
+                                           SHARD_INTERNAL_DIR_DOT_SHARD);
887953
         } else {
887953
                 local->post_res_handler = shard_post_resolve_truncate_handler;
887953
-                shard_refresh_dot_shard (frame, this);
887953
+                shard_refresh_internal_dir (frame, this,
887953
+                                            SHARD_INTERNAL_DIR_DOT_SHARD);
887953
         }
887953
         return 0;
887953
 
887953
@@ -2682,14 +2756,17 @@ shard_unlink_base_file_cbk (call_frame_t *frame, void *cookie, xlator_t *this,
887953
         local->dot_shard_loc.inode = inode_find (this->itable,
887953
                                                  priv->dot_shard_gfid);
887953
         if (!local->dot_shard_loc.inode) {
887953
-                ret = shard_init_dot_shard_loc (this, local);
887953
+                ret = shard_init_internal_dir_loc (this, local,
887953
+                                                   SHARD_INTERNAL_DIR_DOT_SHARD);
887953
                 if (ret)
887953
                         goto unwind;
887953
-                shard_lookup_dot_shard (frame, this,
887953
-                                        shard_post_resolve_unlink_handler);
887953
+                shard_lookup_internal_dir (frame, this,
887953
+                                           shard_post_resolve_unlink_handler,
887953
+                                           SHARD_INTERNAL_DIR_DOT_SHARD);
887953
         } else {
887953
                 local->post_res_handler = shard_post_resolve_unlink_handler;
887953
-                shard_refresh_dot_shard (frame, this);
887953
+                shard_refresh_internal_dir (frame, this,
887953
+                                            SHARD_INTERNAL_DIR_DOT_SHARD);
887953
         }
887953
 
887953
         return 0;
887953
@@ -3048,14 +3125,17 @@ shard_rename_unlink_dst_shards_do (call_frame_t *frame, xlator_t *this)
887953
         local->dot_shard_loc.inode = inode_find (this->itable,
887953
                                                  priv->dot_shard_gfid);
887953
         if (!local->dot_shard_loc.inode) {
887953
-                ret = shard_init_dot_shard_loc (this, local);
887953
+                ret = shard_init_internal_dir_loc (this, local,
887953
+                                                   SHARD_INTERNAL_DIR_DOT_SHARD);
887953
                 if (ret)
887953
                         goto out;
887953
-                shard_lookup_dot_shard (frame, this,
887953
-                                        shard_post_resolve_unlink_handler);
887953
+                shard_lookup_internal_dir (frame, this,
887953
+                                           shard_post_resolve_unlink_handler,
887953
+                                           SHARD_INTERNAL_DIR_DOT_SHARD);
887953
         } else {
887953
                 local->post_res_handler = shard_post_resolve_unlink_handler;
887953
-                shard_refresh_dot_shard (frame, this);
887953
+                shard_refresh_internal_dir (frame, this,
887953
+                                            SHARD_INTERNAL_DIR_DOT_SHARD);
887953
         }
887953
 
887953
         return 0;
887953
@@ -3811,14 +3891,17 @@ shard_post_lookup_readv_handler (call_frame_t *frame, xlator_t *this)
887953
         local->dot_shard_loc.inode = inode_find (this->itable,
887953
                                                  priv->dot_shard_gfid);
887953
         if (!local->dot_shard_loc.inode) {
887953
-                ret = shard_init_dot_shard_loc (this, local);
887953
+                ret = shard_init_internal_dir_loc (this, local,
887953
+                                                   SHARD_INTERNAL_DIR_DOT_SHARD);
887953
                 if (ret)
887953
                         goto err;
887953
-                shard_lookup_dot_shard (frame, this,
887953
-                                        shard_post_resolve_readv_handler);
887953
+                shard_lookup_internal_dir (frame, this,
887953
+                                           shard_post_resolve_readv_handler,
887953
+                                           SHARD_INTERNAL_DIR_DOT_SHARD);
887953
         } else {
887953
                 local->post_res_handler = shard_post_resolve_readv_handler;
887953
-                shard_refresh_dot_shard (frame, this);
887953
+                shard_refresh_internal_dir (frame, this,
887953
+                                            SHARD_INTERNAL_DIR_DOT_SHARD);
887953
         }
887953
         return 0;
887953
 
887953
@@ -4249,8 +4332,9 @@ shard_common_inode_write_post_mknod_handler (call_frame_t *frame,
887953
 }
887953
 
887953
 int
887953
-shard_mkdir_dot_shard (call_frame_t *frame, xlator_t *this,
887953
-                       shard_post_resolve_fop_handler_t handler);
887953
+shard_mkdir_internal_dir (call_frame_t *frame, xlator_t *this,
887953
+                          shard_post_resolve_fop_handler_t handler,
887953
+                          shard_internal_dir_type_t type);
887953
 int
887953
 shard_common_inode_write_post_resolve_handler (call_frame_t *frame,
887953
                                                xlator_t *this)
887953
@@ -4323,26 +4407,28 @@ shard_common_inode_write_post_lookup_handler (call_frame_t *frame,
887953
 
887953
         if (!local->dot_shard_loc.inode) {
887953
                 /*change handler*/
887953
-                shard_mkdir_dot_shard (frame, this,
887953
-                                 shard_common_inode_write_post_resolve_handler);
887953
+                shard_mkdir_internal_dir (frame, this,
887953
+                                 shard_common_inode_write_post_resolve_handler,
887953
+                                          SHARD_INTERNAL_DIR_DOT_SHARD);
887953
         } else {
887953
                 /*change handler*/
887953
                 local->post_res_handler =
887953
                                 shard_common_inode_write_post_resolve_handler;
887953
-                shard_refresh_dot_shard (frame, this);
887953
+                shard_refresh_internal_dir (frame, this,
887953
+                                            SHARD_INTERNAL_DIR_DOT_SHARD);
887953
         }
887953
         return 0;
887953
 }
887953
 
887953
 int
887953
-shard_mkdir_dot_shard_cbk (call_frame_t *frame, void *cookie,
887953
-                                       xlator_t *this, int32_t op_ret,
887953
-                                       int32_t op_errno, inode_t *inode,
887953
-                                       struct iatt *buf, struct iatt *preparent,
887953
-                                       struct iatt *postparent, dict_t *xdata)
887953
+shard_mkdir_internal_dir_cbk (call_frame_t *frame, void *cookie, xlator_t *this,
887953
+                              int32_t op_ret, int32_t op_errno, inode_t *inode,
887953
+                              struct iatt *buf, struct iatt *preparent,
887953
+                              struct iatt *postparent, dict_t *xdata)
887953
 {
887953
-        inode_t       *link_inode = NULL;
887953
-        shard_local_t *local      = NULL;
887953
+        inode_t                   *link_inode = NULL;
887953
+        shard_local_t             *local      = NULL;
887953
+        shard_internal_dir_type_t  type       = (shard_internal_dir_type_t) cookie;
887953
 
887953
         local = frame->local;
887953
 
887953
@@ -4354,17 +4440,19 @@ shard_mkdir_dot_shard_cbk (call_frame_t *frame, void *cookie,
887953
                         local->op_errno = op_errno;
887953
                         goto unwind;
887953
                 } else {
887953
-                        gf_msg_debug (this->name, 0, "mkdir on /.shard failed "
887953
-                                      "with EEXIST. Attempting lookup now");
887953
-                        shard_lookup_dot_shard (frame, this,
887953
-                                                local->post_res_handler);
887953
+                        gf_msg_debug (this->name, 0, "mkdir on %s failed "
887953
+                                      "with EEXIST. Attempting lookup now",
887953
+                                      shard_internal_dir_string (type));
887953
+                        shard_lookup_internal_dir (frame, this,
887953
+                                                   local->post_res_handler,
887953
+                                                   type);
887953
                         return 0;
887953
                 }
887953
         }
887953
 
887953
-        link_inode = shard_link_dot_shard_inode (local, inode, buf);
887953
+        link_inode = shard_link_internal_dir_inode (local, inode, buf, type);
887953
         if (link_inode != inode) {
887953
-                shard_refresh_dot_shard (frame, this);
887953
+                shard_refresh_internal_dir (frame, this, type);
887953
         } else {
887953
                 shard_inode_ctx_set_refreshed_flag (link_inode, this);
887953
                 shard_common_resolve_shards (frame, this,
887953
@@ -4377,40 +4465,59 @@ unwind:
887953
 }
887953
 
887953
 int
887953
-shard_mkdir_dot_shard (call_frame_t *frame, xlator_t *this,
887953
-                       shard_post_resolve_fop_handler_t handler)
887953
+shard_mkdir_internal_dir (call_frame_t *frame, xlator_t *this,
887953
+                          shard_post_resolve_fop_handler_t handler,
887953
+                          shard_internal_dir_type_t type)
887953
 {
887953
         int             ret           = -1;
887953
         shard_local_t  *local         = NULL;
887953
         shard_priv_t   *priv          = NULL;
887953
         dict_t         *xattr_req     = NULL;
887953
+        uuid_t          *gfid         = NULL;
887953
+        loc_t          *loc           = NULL;
887953
+        gf_boolean_t    free_gfid     = _gf_true;
887953
 
887953
         local = frame->local;
887953
         priv = this->private;
887953
 
887953
         local->post_res_handler = handler;
887953
+        gfid = GF_CALLOC (1, sizeof(uuid_t), gf_common_mt_uuid_t);
887953
+        if (!gfid)
887953
+                goto err;
887953
+
887953
+        switch (type) {
887953
+        case SHARD_INTERNAL_DIR_DOT_SHARD:
887953
+                gf_uuid_copy (*gfid, priv->dot_shard_gfid);
887953
+                loc = &local->dot_shard_loc;
887953
+                break;
887953
+        default:
887953
+                break;
887953
+        }
887953
 
887953
         xattr_req = dict_new ();
887953
         if (!xattr_req)
887953
                 goto err;
887953
 
887953
-        ret = shard_init_dot_shard_loc (this, local);
887953
+        ret = shard_init_internal_dir_loc (this, local, type);
887953
         if (ret)
887953
                 goto err;
887953
 
887953
-        ret = dict_set_static_bin (xattr_req, "gfid-req", priv->dot_shard_gfid,
887953
-                                   16);
887953
+        ret = dict_set_bin (xattr_req, "gfid-req", *gfid, 16);
887953
         if (ret) {
887953
                 gf_msg (this->name, GF_LOG_ERROR, 0, SHARD_MSG_DICT_SET_FAILED,
887953
-                        "Failed to set gfid-req for /.shard");
887953
+                        "Failed to set gfid-req for %s",
887953
+                        shard_internal_dir_string (type));
887953
                 goto err;
887953
+        } else {
887953
+                free_gfid = _gf_false;
887953
         }
887953
 
887953
         SHARD_SET_ROOT_FS_ID (frame, local);
887953
 
887953
-        STACK_WIND (frame, shard_mkdir_dot_shard_cbk,
887953
-                    FIRST_CHILD(this), FIRST_CHILD(this)->fops->mkdir,
887953
-                    &local->dot_shard_loc, 0755, 0, xattr_req);
887953
+        STACK_WIND_COOKIE (frame, shard_mkdir_internal_dir_cbk,
887953
+                           (void *)(long) type, FIRST_CHILD(this),
887953
+                           FIRST_CHILD(this)->fops->mkdir, loc, 0755, 0,
887953
+                           xattr_req);
887953
         dict_unref (xattr_req);
887953
         return 0;
887953
 
887953
@@ -4419,6 +4526,8 @@ err:
887953
                 dict_unref (xattr_req);
887953
         local->op_ret = -1;
887953
         local->op_errno = ENOMEM;
887953
+        if (free_gfid)
887953
+                GF_FREE (gfid);
887953
         handler (frame, this);
887953
         return 0;
887953
 }
887953
diff --git a/xlators/features/shard/src/shard.h b/xlators/features/shard/src/shard.h
887953
index 75d39a1..a1adb6a 100644
887953
--- a/xlators/features/shard/src/shard.h
887953
+++ b/xlators/features/shard/src/shard.h
887953
@@ -278,4 +278,8 @@ typedef struct shard_inode_ctx {
887953
         inode_t *base_inode;
887953
 } shard_inode_ctx_t;
887953
 
887953
+typedef enum {
887953
+        SHARD_INTERNAL_DIR_DOT_SHARD = 1,
887953
+} shard_internal_dir_type_t;
887953
+
887953
 #endif /* __SHARD_H__ */
887953
-- 
887953
1.8.3.1
887953