21ab4e
From 5dadc2d8f1193cbffa1aa1f83776725747ec177b Mon Sep 17 00:00:00 2001
21ab4e
From: Raghavendra Bhat <raghavendra@redhat.com>
21ab4e
Date: Thu, 12 May 2016 16:40:04 -0400
21ab4e
Subject: [PATCH 386/393] features/bit-rot-stub: bring in optional versioning
21ab4e
21ab4e
  As of now bit-rot-stub does versioning always. This leads
21ab4e
  lots of getxattr calls being made in lookups. So make
21ab4e
  object versioning optional.
21ab4e
21ab4e
> BUG: 1359599
21ab4e
> Signed-off-by: Raghavendra Bhat <raghavendra@redhat.com>
21ab4e
> Signed-off-by: Kotresh HR <khiremat@redhat.com>
21ab4e
> Reviewed-on: https://review.gluster.org/14442
21ab4e
> Smoke: Gluster Build System <jenkins@build.gluster.org>
21ab4e
> NetBSD-regression: NetBSD Build System <jenkins@build.gluster.org>
21ab4e
> CentOS-regression: Gluster Build System <jenkins@build.gluster.org>
21ab4e
> Reviewed-by: Vijay Bellur <vbellur@redhat.com>
21ab4e
21ab4e
Change-Id: I83713e45ae59fb28004bb3cfa008f2d69edebbfa
21ab4e
BUG: 1298258
21ab4e
Signed-off-by: Kotresh HR <khiremat@redhat.com>
21ab4e
Reviewed-on: https://code.engineering.redhat.com/gerrit/103743
21ab4e
Reviewed-by: Atin Mukherjee <amukherj@redhat.com>
21ab4e
---
21ab4e
 tests/bitrot/br-stub.t                             |   3 +
21ab4e
 tests/bitrot/bug-1221914.t                         |   3 +
21ab4e
 tests/bitrot/bug-1244613.t                         |   3 +
21ab4e
 .../bit-rot/src/stub/bit-rot-stub-helpers.c        |   3 +
21ab4e
 xlators/features/bit-rot/src/stub/bit-rot-stub.c   | 318 +++++++++++++++++----
21ab4e
 xlators/features/bit-rot/src/stub/bit-rot-stub.h   |  26 +-
21ab4e
 xlators/mgmt/glusterd/src/glusterd-volgen.c        |  17 +-
21ab4e
 7 files changed, 314 insertions(+), 59 deletions(-)
21ab4e
21ab4e
diff --git a/tests/bitrot/br-stub.t b/tests/bitrot/br-stub.t
21ab4e
index 8ce170d..5013398 100644
21ab4e
--- a/tests/bitrot/br-stub.t
21ab4e
+++ b/tests/bitrot/br-stub.t
21ab4e
@@ -27,6 +27,9 @@ TEST $CLI volume set $V0 performance.write-behind off
21ab4e
 TEST $CLI volume start $V0;
21ab4e
 EXPECT 'Started' volinfo_field $V0 'Status';
21ab4e
 
21ab4e
+## enable bitrot
21ab4e
+TEST $CLI volume bitrot $V0 enable;
21ab4e
+
21ab4e
 ## Wait for gluster nfs to come up
21ab4e
 EXPECT_WITHIN $NFS_EXPORT_TIMEOUT "1" is_nfs_export_available
21ab4e
 
21ab4e
diff --git a/tests/bitrot/bug-1221914.t b/tests/bitrot/bug-1221914.t
21ab4e
index 85715e5..7f6c10c 100644
21ab4e
--- a/tests/bitrot/bug-1221914.t
21ab4e
+++ b/tests/bitrot/bug-1221914.t
21ab4e
@@ -25,6 +25,9 @@ TEST $CLI volume set $V0 performance.write-behind off
21ab4e
 TEST $CLI volume start $V0;
21ab4e
 EXPECT 'Started' volinfo_field $V0 'Status';
21ab4e
 
21ab4e
+## Enable bitrot
21ab4e
+TEST $CLI volume bitrot $V0 enable;
21ab4e
+
21ab4e
 ## Mount the volume
21ab4e
 TEST $GFS --volfile-server=$H0 --volfile-id=$V0 $M0;
21ab4e
 
21ab4e
diff --git a/tests/bitrot/bug-1244613.t b/tests/bitrot/bug-1244613.t
21ab4e
index 7cb57f0..5674e6f 100644
21ab4e
--- a/tests/bitrot/bug-1244613.t
21ab4e
+++ b/tests/bitrot/bug-1244613.t
21ab4e
@@ -40,6 +40,9 @@ TEST $CLI volume set $V0 performance.nfs.write-behind off
21ab4e
 TEST $CLI volume start $V0;
21ab4e
 EXPECT 'Started' volinfo_field $V0 'Status';
21ab4e
 
21ab4e
+## Enable bitrot
21ab4e
+TEST $CLI volume bitrot $V0 enable;
21ab4e
+
21ab4e
 ## Wait for gluster nfs to come up
21ab4e
 EXPECT_WITHIN $NFS_EXPORT_TIMEOUT "1" is_nfs_export_available
21ab4e
 
21ab4e
diff --git a/xlators/features/bit-rot/src/stub/bit-rot-stub-helpers.c b/xlators/features/bit-rot/src/stub/bit-rot-stub-helpers.c
21ab4e
index 7bd270d..7a308f9 100644
21ab4e
--- a/xlators/features/bit-rot/src/stub/bit-rot-stub-helpers.c
21ab4e
+++ b/xlators/features/bit-rot/src/stub/bit-rot-stub-helpers.c
21ab4e
@@ -393,8 +393,11 @@ br_stub_lookup_wrapper (call_frame_t *frame, xlator_t *this,
21ab4e
         struct iatt        stbuf       = {0, };
21ab4e
         struct iatt        postparent  = {0,};
21ab4e
         dict_t            *xattr       = NULL;
21ab4e
+        gf_boolean_t       ver_enabled = _gf_false;
21ab4e
 
21ab4e
+        BR_STUB_VER_ENABLED_IN_CALLPATH(frame, ver_enabled);
21ab4e
         priv = this->private;
21ab4e
+        BR_STUB_VER_COND_GOTO (priv, (!ver_enabled), done);
21ab4e
 
21ab4e
         VALIDATE_OR_GOTO (loc, done);
21ab4e
         if (gf_uuid_compare (loc->gfid, priv->bad_object_dir_gfid))
21ab4e
diff --git a/xlators/features/bit-rot/src/stub/bit-rot-stub.c b/xlators/features/bit-rot/src/stub/bit-rot-stub.c
21ab4e
index 4e01f5c..115b10d 100644
21ab4e
--- a/xlators/features/bit-rot/src/stub/bit-rot-stub.c
21ab4e
+++ b/xlators/features/bit-rot/src/stub/bit-rot-stub.c
21ab4e
@@ -136,7 +136,7 @@ init (xlator_t *this)
21ab4e
         if (!priv->local_pool)
21ab4e
                 goto free_priv;
21ab4e
 
21ab4e
-        GF_OPTION_INIT ("bitrot", priv->go, bool, free_mempool);
21ab4e
+        GF_OPTION_INIT ("bitrot", priv->do_versioning, bool, free_mempool);
21ab4e
 
21ab4e
         GF_OPTION_INIT ("export", tmp, str, free_mempool);
21ab4e
         memcpy (priv->export, tmp, strlen (tmp) + 1);
21ab4e
@@ -186,6 +186,34 @@ init (xlator_t *this)
21ab4e
         return -1;
21ab4e
 }
21ab4e
 
21ab4e
+/* TODO:
21ab4e
+ * As of now enabling bitrot option does 2 things.
21ab4e
+ * 1) Start the Bitrot Daemon which signs the objects (currently files only)
21ab4e
+ *    upon getting notified by the stub.
21ab4e
+ * 2) Enable versioning of the objects. Object versions (again files only) are
21ab4e
+ *    incremented upon modification.
21ab4e
+ * So object versioning is tied to bitrot daemon's signing. In future, object
21ab4e
+ * versioning might be necessary for other things as well apart from bit-rot
21ab4e
+ * detection (well thats the objective of bringing in object-versioning :)).
21ab4e
+ * In that case, better to make versioning a new option and letting it to be
21ab4e
+ * enabled despite bit-rot detection is not needed.
21ab4e
+ * Ex: ICAP.
21ab4e
+ */
21ab4e
+int32_t
21ab4e
+reconfigure (xlator_t *this, dict_t *options)
21ab4e
+{
21ab4e
+        int32_t            ret  = -1;
21ab4e
+        br_stub_private_t *priv = NULL;
21ab4e
+
21ab4e
+        priv = this->private;
21ab4e
+
21ab4e
+        GF_OPTION_RECONF ("bitrot", priv->do_versioning, options, bool, out);
21ab4e
+
21ab4e
+        ret = 0;
21ab4e
+out:
21ab4e
+        return ret;
21ab4e
+}
21ab4e
+
21ab4e
 void
21ab4e
 fini (xlator_t *this)
21ab4e
 {
21ab4e
@@ -289,6 +317,9 @@ br_stub_alloc_local (xlator_t *this)
21ab4e
 static void
21ab4e
 br_stub_dealloc_local (br_stub_local_t *ptr)
21ab4e
 {
21ab4e
+        if (!ptr)
21ab4e
+                return;
21ab4e
+
21ab4e
         mem_put (ptr);
21ab4e
 }
21ab4e
 
21ab4e
@@ -408,6 +439,9 @@ br_stub_fill_local (br_stub_local_t *local,
21ab4e
 static void
21ab4e
 br_stub_cleanup_local (br_stub_local_t *local)
21ab4e
 {
21ab4e
+        if (!local)
21ab4e
+                return;
21ab4e
+
21ab4e
         local->fopstub = NULL;
21ab4e
         local->versioningtype = 0;
21ab4e
         local->u.context.version = 0;
21ab4e
@@ -430,17 +464,33 @@ br_stub_need_versioning (xlator_t *this,
21ab4e
         int32_t ret      = -1;
21ab4e
         uint64_t ctx_addr = 0;
21ab4e
         br_stub_inode_ctx_t *c = NULL;
21ab4e
+        unsigned long        version  = BITROT_DEFAULT_CURRENT_VERSION;
21ab4e
 
21ab4e
         *versioning = _gf_false;
21ab4e
         *modified = _gf_false;
21ab4e
 
21ab4e
+        /* Bitrot stub inode context was initialized only in lookup, create
21ab4e
+         * and mknod cbk path. Object versioning was enabled by default
21ab4e
+         * irrespective of bitrot enbaled or not. But it's made optional now.
21ab4e
+         * As a consequence there could be cases where getting inode ctx would
21ab4e
+         * fail because it's not set yet.
21ab4e
+         * e.g., If versioning (with bitrot enable) is enabled while I/O is
21ab4e
+         * happening, it could directly get other fops like writev without
21ab4e
+         * lookup, where getting inode ctx would fail. Hence initialize the
21ab4e
+         * inode ctx on failure to get ctx. This is done in all places where
21ab4e
+         * applicable.
21ab4e
+         */
21ab4e
         ret = br_stub_get_inode_ctx (this, fd->inode, &ctx_addr);
21ab4e
         if (ret < 0) {
21ab4e
-                gf_msg (this->name, GF_LOG_ERROR, 0,
21ab4e
-                        BRS_MSG_GET_INODE_CONTEXT_FAILED, "failed to get the "
21ab4e
-                        "inode context for the inode %s",
21ab4e
-                        uuid_utoa (fd->inode->gfid));
21ab4e
-                goto error_return;
21ab4e
+                ret = br_stub_init_inode_versions (this, fd, fd->inode, version,
21ab4e
+                                                   _gf_true, _gf_false);
21ab4e
+                if (ret) {
21ab4e
+                        gf_msg (this->name, GF_LOG_ERROR, 0,
21ab4e
+                                BRS_MSG_GET_INODE_CONTEXT_FAILED, "failed to "
21ab4e
+                                " init the inode context for the inode %s",
21ab4e
+                                uuid_utoa (fd->inode->gfid));
21ab4e
+                        goto error_return;
21ab4e
+                }
21ab4e
         }
21ab4e
 
21ab4e
         c = (br_stub_inode_ctx_t *) (long) ctx_addr;
21ab4e
@@ -524,12 +574,17 @@ br_stub_mark_inode_modified (xlator_t *this, br_stub_local_t *local)
21ab4e
         int32_t              ret      = 0;
21ab4e
         uint64_t             ctx_addr = 0;
21ab4e
         br_stub_inode_ctx_t *ctx      = NULL;
21ab4e
+        unsigned long        version  = BITROT_DEFAULT_CURRENT_VERSION;
21ab4e
 
21ab4e
         fd = local->u.context.fd;
21ab4e
 
21ab4e
         ret = br_stub_get_inode_ctx (this, fd->inode, &ctx_addr);
21ab4e
-        if (ret < 0)
21ab4e
-                goto error_return;
21ab4e
+        if (ret < 0) {
21ab4e
+                ret = br_stub_init_inode_versions (this, fd, fd->inode, version,
21ab4e
+                                                   _gf_true, _gf_false);
21ab4e
+                if (ret)
21ab4e
+                        goto error_return;
21ab4e
+        }
21ab4e
 
21ab4e
         ctx = (br_stub_inode_ctx_t *) (long) ctx_addr;
21ab4e
 
21ab4e
@@ -558,6 +613,7 @@ br_stub_check_bad_object (xlator_t *this, inode_t *inode, int32_t *op_ret,
21ab4e
                            int32_t *op_errno)
21ab4e
 {
21ab4e
         int ret = -1;
21ab4e
+        unsigned long        version  = BITROT_DEFAULT_CURRENT_VERSION;
21ab4e
 
21ab4e
         ret = br_stub_is_bad_object (this, inode);
21ab4e
         if (ret == -2) {
21ab4e
@@ -569,11 +625,16 @@ br_stub_check_bad_object (xlator_t *this, inode_t *inode, int32_t *op_ret,
21ab4e
         }
21ab4e
 
21ab4e
         if (ret == -1) {
21ab4e
-                gf_msg (this->name, GF_LOG_ERROR, 0,
21ab4e
-                        BRS_MSG_GET_INODE_CONTEXT_FAILED, "could not get inode"
21ab4e
-                        " context for %s", uuid_utoa (inode->gfid));
21ab4e
-                *op_ret = -1;
21ab4e
-                *op_errno = EINVAL;
21ab4e
+                ret = br_stub_init_inode_versions (this, NULL, inode, version,
21ab4e
+                                                   _gf_true, _gf_false);
21ab4e
+                if (ret) {
21ab4e
+                        gf_msg (this->name, GF_LOG_ERROR, 0,
21ab4e
+                                BRS_MSG_GET_INODE_CONTEXT_FAILED,
21ab4e
+                                "failed to init inode context for %s",
21ab4e
+                                uuid_utoa (inode->gfid));
21ab4e
+                        *op_ret = -1;
21ab4e
+                        *op_errno = EINVAL;
21ab4e
+                }
21ab4e
         }
21ab4e
 
21ab4e
         return ret;
21ab4e
@@ -787,6 +848,20 @@ br_stub_signth (void *arg)
21ab4e
         return NULL;
21ab4e
 }
21ab4e
 
21ab4e
+static gf_boolean_t
21ab4e
+br_stub_internal_xattr (dict_t *dict) {
21ab4e
+
21ab4e
+        if (dict_get (dict, GLUSTERFS_SET_OBJECT_SIGNATURE) ||
21ab4e
+            dict_get (dict, GLUSTERFS_GET_OBJECT_SIGNATURE) ||
21ab4e
+            dict_get (dict, BR_REOPEN_SIGN_HINT_KEY) ||
21ab4e
+            dict_get (dict, BITROT_OBJECT_BAD_KEY) ||
21ab4e
+            dict_get (dict, BITROT_SIGNING_VERSION_KEY) ||
21ab4e
+            dict_get (dict, BITROT_CURRENT_VERSION_KEY))
21ab4e
+                return _gf_true;
21ab4e
+
21ab4e
+        return _gf_false;
21ab4e
+}
21ab4e
+
21ab4e
 int
21ab4e
 orderq (struct list_head *elem1, struct list_head *elem2)
21ab4e
 {
21ab4e
@@ -1200,6 +1275,26 @@ br_stub_fsetxattr (call_frame_t *frame, xlator_t *this,
21ab4e
         int32_t              ret      = 0;
21ab4e
         uint32_t             val      = 0;
21ab4e
         br_isignature_t     *sign     = NULL;
21ab4e
+        br_stub_private_t   *priv     = NULL;
21ab4e
+        int32_t              op_ret   = -1;
21ab4e
+        int32_t              op_errno = EINVAL;
21ab4e
+        char                *format   = "(%s:%s)";
21ab4e
+        char                 dump[64*1024]  = {0,};
21ab4e
+
21ab4e
+        priv = this->private;
21ab4e
+
21ab4e
+        if ((frame->root->pid != GF_CLIENT_PID_BITD &&
21ab4e
+            frame->root->pid != GF_CLIENT_PID_SCRUB) &&
21ab4e
+            br_stub_internal_xattr (dict)) {
21ab4e
+                dict_dump_to_str (dict, dump, sizeof(dump), format);
21ab4e
+                gf_msg (this->name, GF_LOG_ERROR, 0,
21ab4e
+                        BRS_MSG_SET_INTERNAL_XATTR, "fsetxattr called on "
21ab4e
+                        "internal xattr %s", dump);
21ab4e
+                goto unwind;
21ab4e
+        }
21ab4e
+
21ab4e
+        if (!priv->do_versioning)
21ab4e
+                goto wind;
21ab4e
 
21ab4e
         if (!IA_ISREG (fd->inode->ia_type))
21ab4e
                 goto wind;
21ab4e
@@ -1251,6 +1346,11 @@ wind:
21ab4e
         STACK_WIND (frame, default_fsetxattr_cbk, FIRST_CHILD (this),
21ab4e
                     FIRST_CHILD (this)->fops->fsetxattr, fd, dict, flags,
21ab4e
                     xdata);
21ab4e
+        return 0;
21ab4e
+
21ab4e
+unwind:
21ab4e
+        STACK_UNWIND_STRICT (fsetxattr, frame, op_ret, op_errno, NULL);
21ab4e
+
21ab4e
 done:
21ab4e
         return 0;
21ab4e
 }
21ab4e
@@ -1272,12 +1372,7 @@ br_stub_setxattr (call_frame_t *frame, xlator_t *this,
21ab4e
         char     dump[64*1024]             = {0,};
21ab4e
         char    *format                    = "(%s:%s)";
21ab4e
 
21ab4e
-        if (dict_get (dict, GLUSTERFS_SET_OBJECT_SIGNATURE) ||
21ab4e
-            dict_get (dict, GLUSTERFS_GET_OBJECT_SIGNATURE) ||
21ab4e
-            dict_get (dict, BR_REOPEN_SIGN_HINT_KEY) ||
21ab4e
-            dict_get (dict, BITROT_OBJECT_BAD_KEY) ||
21ab4e
-            dict_get (dict, BITROT_SIGNING_VERSION_KEY) ||
21ab4e
-            dict_get (dict, BITROT_CURRENT_VERSION_KEY)) {
21ab4e
+        if (br_stub_internal_xattr (dict)) {
21ab4e
                 dict_dump_to_str (dict, dump, sizeof(dump), format);
21ab4e
                 gf_msg (this->name, GF_LOG_ERROR, 0,
21ab4e
                         BRS_MSG_SET_INTERNAL_XATTR, "setxattr called on "
21ab4e
@@ -1285,7 +1380,6 @@ br_stub_setxattr (call_frame_t *frame, xlator_t *this,
21ab4e
                 goto unwind;
21ab4e
         }
21ab4e
 
21ab4e
-
21ab4e
         STACK_WIND_TAIL (frame, FIRST_CHILD (this),
21ab4e
                          FIRST_CHILD (this)->fops->setxattr, loc, dict, flags,
21ab4e
                          xdata);
21ab4e
@@ -1318,7 +1412,6 @@ br_stub_removexattr (call_frame_t *frame, xlator_t *this,
21ab4e
                 goto unwind;
21ab4e
         }
21ab4e
 
21ab4e
-
21ab4e
         STACK_WIND_TAIL (frame, FIRST_CHILD(this),
21ab4e
                          FIRST_CHILD(this)->fops->removexattr,
21ab4e
                          loc, name, xdata);
21ab4e
@@ -1345,7 +1438,6 @@ br_stub_fremovexattr (call_frame_t *frame, xlator_t *this,
21ab4e
                 goto unwind;
21ab4e
         }
21ab4e
 
21ab4e
-
21ab4e
         STACK_WIND_TAIL (frame, FIRST_CHILD(this),
21ab4e
                          FIRST_CHILD(this)->fops->fremovexattr,
21ab4e
                          fd, name, xdata);
21ab4e
@@ -1593,9 +1685,12 @@ br_stub_getxattr (call_frame_t *frame, xlator_t *this,
21ab4e
         int32_t             op_ret   = -1;
21ab4e
         int32_t             op_errno = EINVAL;
21ab4e
         br_stub_local_t    *local    = NULL;
21ab4e
+        br_stub_private_t  *priv     = NULL;
21ab4e
+
21ab4e
 
21ab4e
         GF_VALIDATE_OR_GOTO ("bit-rot-stub", this, unwind);
21ab4e
         GF_VALIDATE_OR_GOTO (this->name, loc, unwind);
21ab4e
+        GF_VALIDATE_OR_GOTO (this->name, this->private, unwind);
21ab4e
         GF_VALIDATE_OR_GOTO (this->name, loc->inode, unwind);
21ab4e
 
21ab4e
         rootgfid[15] = 1;
21ab4e
@@ -1605,6 +1700,13 @@ br_stub_getxattr (call_frame_t *frame, xlator_t *this,
21ab4e
                 goto wind;
21ab4e
         }
21ab4e
 
21ab4e
+        if (br_stub_is_internal_xattr (name))
21ab4e
+                goto unwind;
21ab4e
+
21ab4e
+        priv = this->private;
21ab4e
+        if (!priv->do_versioning)
21ab4e
+                goto wind;
21ab4e
+
21ab4e
         /**
21ab4e
          * If xattr is node-uuid and the inode is marked bad, return EIO.
21ab4e
          * Returning EIO would result in AFR to choose correct node-uuid
21ab4e
@@ -1616,9 +1718,6 @@ br_stub_getxattr (call_frame_t *frame, xlator_t *this,
21ab4e
                 goto unwind;
21ab4e
         }
21ab4e
 
21ab4e
-        if (br_stub_is_internal_xattr (name))
21ab4e
-                goto unwind;
21ab4e
-
21ab4e
         /**
21ab4e
          * this special extended attribute is allowed only on root
21ab4e
          */
21ab4e
@@ -1671,6 +1770,7 @@ br_stub_fgetxattr (call_frame_t *frame, xlator_t *this,
21ab4e
         int32_t op_ret = -1;
21ab4e
         int32_t op_errno = EINVAL;
21ab4e
         br_stub_local_t *local = NULL;
21ab4e
+        br_stub_private_t  *priv = NULL;
21ab4e
 
21ab4e
         rootgfid[15] = 1;
21ab4e
 
21ab4e
@@ -1679,6 +1779,13 @@ br_stub_fgetxattr (call_frame_t *frame, xlator_t *this,
21ab4e
                 goto wind;
21ab4e
         }
21ab4e
 
21ab4e
+        if (br_stub_is_internal_xattr (name))
21ab4e
+                goto unwind;
21ab4e
+
21ab4e
+        priv = this->private;
21ab4e
+        if (!priv->do_versioning)
21ab4e
+                goto wind;
21ab4e
+
21ab4e
         /**
21ab4e
          * If xattr is node-uuid and the inode is marked bad, return EIO.
21ab4e
          * Returning EIO would result in AFR to choose correct node-uuid
21ab4e
@@ -1690,9 +1797,6 @@ br_stub_fgetxattr (call_frame_t *frame, xlator_t *this,
21ab4e
                 goto unwind;
21ab4e
         }
21ab4e
 
21ab4e
-        if (br_stub_is_internal_xattr (name))
21ab4e
-                goto unwind;
21ab4e
-
21ab4e
         /**
21ab4e
          * this special extended attribute is allowed only on root
21ab4e
          */
21ab4e
@@ -1741,16 +1845,23 @@ br_stub_readv (call_frame_t *frame, xlator_t *this,
21ab4e
         int32_t              op_ret   = -1;
21ab4e
         int32_t              op_errno = EINVAL;
21ab4e
         int32_t              ret      = -1;
21ab4e
+        br_stub_private_t   *priv     = NULL;
21ab4e
 
21ab4e
         GF_VALIDATE_OR_GOTO ("bit-rot-stub", this, unwind);
21ab4e
         GF_VALIDATE_OR_GOTO (this->name, frame, unwind);
21ab4e
+        GF_VALIDATE_OR_GOTO (this->name, this->private, unwind);
21ab4e
         GF_VALIDATE_OR_GOTO (this->name, fd, unwind);
21ab4e
         GF_VALIDATE_OR_GOTO (this->name, fd->inode, unwind);
21ab4e
 
21ab4e
+        priv = this->private;
21ab4e
+        if (!priv->do_versioning)
21ab4e
+                goto wind;
21ab4e
+
21ab4e
         ret = br_stub_check_bad_object (this, fd->inode, &op_ret, &op_errno);
21ab4e
         if (ret)
21ab4e
                 goto unwind;
21ab4e
 
21ab4e
+wind:
21ab4e
         STACK_WIND_TAIL (frame, FIRST_CHILD(this),
21ab4e
                          FIRST_CHILD(this)->fops->readv, fd, size, offset,
21ab4e
                          flags, xdata);
21ab4e
@@ -1774,8 +1885,8 @@ br_stub_writev_cbk (call_frame_t *frame, void *cookie, xlator_t *this,
21ab4e
                     int32_t op_ret, int32_t op_errno, struct iatt *prebuf,
21ab4e
                     struct iatt *postbuf, dict_t *xdata)
21ab4e
 {
21ab4e
-        int32_t          ret   = 0;
21ab4e
-        br_stub_local_t *local = NULL;
21ab4e
+        int32_t            ret   = 0;
21ab4e
+        br_stub_local_t   *local = NULL;
21ab4e
 
21ab4e
         local = frame->local;
21ab4e
         frame->local = NULL;
21ab4e
@@ -1834,11 +1945,17 @@ br_stub_writev (call_frame_t *frame, xlator_t *this, fd_t *fd,
21ab4e
         int32_t              ret         = -1;
21ab4e
         fop_writev_cbk_t     cbk         = default_writev_cbk;
21ab4e
         br_stub_local_t     *local       = NULL;
21ab4e
+        br_stub_private_t   *priv        = NULL;
21ab4e
 
21ab4e
         GF_VALIDATE_OR_GOTO ("bit-rot-stub", this, unwind);
21ab4e
+        GF_VALIDATE_OR_GOTO (this->name, this->private, unwind);
21ab4e
         GF_VALIDATE_OR_GOTO (this->name, frame, unwind);
21ab4e
         GF_VALIDATE_OR_GOTO (this->name, fd, unwind);
21ab4e
 
21ab4e
+        priv = this->private;
21ab4e
+        if (!priv->do_versioning)
21ab4e
+                goto wind;
21ab4e
+
21ab4e
         ret = br_stub_need_versioning (this, fd, &inc_version, &modified, &ctx;;
21ab4e
         if (ret)
21ab4e
                 goto unwind;
21ab4e
@@ -1909,8 +2026,8 @@ br_stub_ftruncate_cbk (call_frame_t *frame, void *cookie, xlator_t *this,
21ab4e
                        int32_t op_ret, int32_t op_errno, struct iatt *prebuf,
21ab4e
                        struct iatt *postbuf, dict_t *xdata)
21ab4e
 {
21ab4e
-        int32_t          ret   = -1;
21ab4e
-        br_stub_local_t *local = NULL;
21ab4e
+        int32_t            ret   = -1;
21ab4e
+        br_stub_local_t   *local = NULL;
21ab4e
 
21ab4e
         local = frame->local;
21ab4e
         frame->local = NULL;
21ab4e
@@ -1957,11 +2074,17 @@ br_stub_ftruncate (call_frame_t *frame, xlator_t *this, fd_t *fd,
21ab4e
         br_stub_inode_ctx_t *ctx         = NULL;
21ab4e
         int32_t              ret         = -1;
21ab4e
         fop_ftruncate_cbk_t  cbk         = default_ftruncate_cbk;
21ab4e
+        br_stub_private_t   *priv        = NULL;
21ab4e
 
21ab4e
         GF_VALIDATE_OR_GOTO ("bit-rot-stub", this, unwind);
21ab4e
+        GF_VALIDATE_OR_GOTO (this->name, this->private, unwind);
21ab4e
         GF_VALIDATE_OR_GOTO (this->name, frame, unwind);
21ab4e
         GF_VALIDATE_OR_GOTO (this->name, fd, unwind);
21ab4e
 
21ab4e
+        priv = this->private;
21ab4e
+        if (!priv->do_versioning)
21ab4e
+                goto wind;
21ab4e
+
21ab4e
         ret = br_stub_need_versioning (this, fd, &inc_version, &modified, &ctx;;
21ab4e
         if (ret)
21ab4e
                 goto unwind;
21ab4e
@@ -2081,12 +2204,18 @@ br_stub_truncate (call_frame_t *frame, xlator_t *this, loc_t *loc,
21ab4e
         int32_t              ret         = -1;
21ab4e
         fd_t                *fd          = NULL;
21ab4e
         fop_truncate_cbk_t   cbk         = default_truncate_cbk;
21ab4e
+        br_stub_private_t   *priv        = NULL;
21ab4e
 
21ab4e
         GF_VALIDATE_OR_GOTO ("bit-rot-stub", this, unwind);
21ab4e
+        GF_VALIDATE_OR_GOTO (this->name, this->private, unwind);
21ab4e
         GF_VALIDATE_OR_GOTO (this->name, frame, unwind);
21ab4e
         GF_VALIDATE_OR_GOTO (this->name, loc, unwind);
21ab4e
         GF_VALIDATE_OR_GOTO (this->name, loc->inode, unwind);
21ab4e
 
21ab4e
+        priv = this->private;
21ab4e
+        if (!priv->do_versioning)
21ab4e
+                goto wind;
21ab4e
+
21ab4e
         fd = fd_anonymous (loc->inode);
21ab4e
         if (!fd) {
21ab4e
                 gf_msg (this->name, GF_LOG_ERROR, 0,
21ab4e
@@ -2133,7 +2262,8 @@ br_stub_truncate (call_frame_t *frame, xlator_t *this, loc_t *loc,
21ab4e
  wind:
21ab4e
         STACK_WIND (frame, cbk, FIRST_CHILD(this),
21ab4e
                     FIRST_CHILD(this)->fops->truncate, loc, offset, xdata);
21ab4e
-        fd_unref (fd);
21ab4e
+        if (fd)
21ab4e
+                fd_unref (fd);
21ab4e
         return 0;
21ab4e
 
21ab4e
  cleanup_local:
21ab4e
@@ -2179,19 +2309,32 @@ br_stub_open (call_frame_t *frame, xlator_t *this,
21ab4e
         uint64_t             ctx_addr = 0;
21ab4e
         int32_t              op_ret   = -1;
21ab4e
         int32_t              op_errno = EINVAL;
21ab4e
+        br_stub_private_t   *priv     = NULL;
21ab4e
+        unsigned long        version  = BITROT_DEFAULT_CURRENT_VERSION;
21ab4e
 
21ab4e
         GF_VALIDATE_OR_GOTO ("bit-rot-stub", this, unwind);
21ab4e
+        GF_VALIDATE_OR_GOTO (this->name, this->private, unwind);
21ab4e
         GF_VALIDATE_OR_GOTO (this->name, loc, unwind);
21ab4e
         GF_VALIDATE_OR_GOTO (this->name, fd, unwind);
21ab4e
         GF_VALIDATE_OR_GOTO (this->name, fd->inode, unwind);
21ab4e
 
21ab4e
+        priv = this->private;
21ab4e
+
21ab4e
+        if (!priv->do_versioning)
21ab4e
+                goto wind;
21ab4e
+
21ab4e
         ret = br_stub_get_inode_ctx (this, fd->inode, &ctx_addr);
21ab4e
         if (ret) {
21ab4e
-                gf_msg (this->name, GF_LOG_ERROR, 0,
21ab4e
-                        BRS_MSG_GET_INODE_CONTEXT_FAILED, "failed to get the "
21ab4e
-                        "inode context for the file %s (gfid: %s)", loc->path,
21ab4e
-                        uuid_utoa (fd->inode->gfid));
21ab4e
-                goto unwind;
21ab4e
+                ret = br_stub_init_inode_versions (this, fd, fd->inode, version,
21ab4e
+                                                   _gf_true, _gf_false);
21ab4e
+                if (ret) {
21ab4e
+                        gf_msg (this->name, GF_LOG_ERROR, 0,
21ab4e
+                                BRS_MSG_GET_INODE_CONTEXT_FAILED,
21ab4e
+                                "failed to init the inode context for "
21ab4e
+                                "the file %s (gfid: %s)", loc->path,
21ab4e
+                                uuid_utoa (fd->inode->gfid));
21ab4e
+                        goto unwind;
21ab4e
+                }
21ab4e
         }
21ab4e
 
21ab4e
         ctx = (br_stub_inode_ctx_t *)(long)ctx_addr;
21ab4e
@@ -2272,10 +2415,16 @@ br_stub_create_cbk (call_frame_t *frame, void *cookie, xlator_t *this,
21ab4e
         uint64_t             ctx_addr = 0;
21ab4e
         br_stub_inode_ctx_t *ctx      = NULL;
21ab4e
         unsigned long        version  = BITROT_DEFAULT_CURRENT_VERSION;
21ab4e
+        br_stub_private_t   *priv     = NULL;
21ab4e
+
21ab4e
+        priv = this->private;
21ab4e
 
21ab4e
         if (op_ret < 0)
21ab4e
                 goto unwind;
21ab4e
 
21ab4e
+        if (!priv->do_versioning)
21ab4e
+                goto unwind;
21ab4e
+
21ab4e
         ret = br_stub_get_inode_ctx (this, fd->inode, &ctx_addr);
21ab4e
         if (ret < 0) {
21ab4e
                 ret = br_stub_init_inode_versions (this, fd, inode, version,
21ab4e
@@ -2324,10 +2473,16 @@ br_stub_mknod_cbk (call_frame_t *frame, void *cookie, xlator_t *this,
21ab4e
 {
21ab4e
         int32_t              ret      = -1;
21ab4e
         unsigned long        version  = BITROT_DEFAULT_CURRENT_VERSION;
21ab4e
+        br_stub_private_t   *priv     = NULL;
21ab4e
+
21ab4e
+        priv = this->private;
21ab4e
 
21ab4e
         if (op_ret < 0)
21ab4e
                 goto unwind;
21ab4e
 
21ab4e
+        if (!priv->do_versioning)
21ab4e
+                goto unwind;
21ab4e
+
21ab4e
         ret = br_stub_init_inode_versions (this, NULL, inode, version,
21ab4e
                                            _gf_true, _gf_false);
21ab4e
         /**
21ab4e
@@ -2478,6 +2633,9 @@ br_stub_readdir (call_frame_t *frame, xlator_t *this,
21ab4e
         br_stub_private_t    *priv = NULL;
21ab4e
 
21ab4e
         priv = this->private;
21ab4e
+        if (!priv->do_versioning)
21ab4e
+                goto out;
21ab4e
+
21ab4e
         if (gf_uuid_compare (fd->inode->gfid, priv->bad_object_dir_gfid))
21ab4e
                 goto out;
21ab4e
         stub = fop_readdir_stub (frame, br_stub_readdir_wrapper, fd, size, off,
21ab4e
@@ -2499,9 +2657,15 @@ br_stub_readdirp_cbk (call_frame_t *frame, void *cookie, xlator_t *this,
21ab4e
                       int op_ret, int op_errno, gf_dirent_t *entries,
21ab4e
                       dict_t *dict)
21ab4e
 {
21ab4e
-        int32_t      ret     = 0;
21ab4e
-        uint64_t     ctxaddr = 0;
21ab4e
-        gf_dirent_t *entry   = NULL;
21ab4e
+        int32_t            ret     = 0;
21ab4e
+        uint64_t           ctxaddr = 0;
21ab4e
+        gf_dirent_t       *entry   = NULL;
21ab4e
+        br_stub_private_t *priv    = NULL;
21ab4e
+        gf_boolean_t       ver_enabled = _gf_false;
21ab4e
+
21ab4e
+        BR_STUB_VER_ENABLED_IN_CALLPATH (frame, ver_enabled);
21ab4e
+        priv = this->private;
21ab4e
+        BR_STUB_VER_COND_GOTO (priv, (!ver_enabled), unwind);
21ab4e
 
21ab4e
         if (op_ret < 0)
21ab4e
                 goto unwind;
21ab4e
@@ -2549,9 +2713,13 @@ int
21ab4e
 br_stub_readdirp (call_frame_t *frame, xlator_t *this,
21ab4e
                   fd_t *fd, size_t size, off_t offset, dict_t *dict)
21ab4e
 {
21ab4e
-        int32_t ret = -1;
21ab4e
-        int op_errno = 0;
21ab4e
-        gf_boolean_t xref = _gf_false;
21ab4e
+        int32_t            ret      = -1;
21ab4e
+        int                op_errno = 0;
21ab4e
+        gf_boolean_t       xref     = _gf_false;
21ab4e
+        br_stub_private_t *priv     = NULL;
21ab4e
+
21ab4e
+        priv = this->private;
21ab4e
+        BR_STUB_VER_NOT_ACTIVE_THEN_GOTO (frame, priv, wind);
21ab4e
 
21ab4e
         op_errno = ENOMEM;
21ab4e
         if (!dict) {
21ab4e
@@ -2575,16 +2743,19 @@ br_stub_readdirp (call_frame_t *frame, xlator_t *this,
21ab4e
         if (ret)
21ab4e
                 goto unwind;
21ab4e
 
21ab4e
+wind:
21ab4e
         STACK_WIND (frame, br_stub_readdirp_cbk, FIRST_CHILD (this),
21ab4e
                     FIRST_CHILD(this)->fops->readdirp, fd, size,
21ab4e
                     offset, dict);
21ab4e
         goto unref_dict;
21ab4e
 
21ab4e
- unwind:
21ab4e
+unwind:
21ab4e
+        if (frame->local == (void *)0x1)
21ab4e
+                frame->local = NULL;
21ab4e
         STACK_UNWIND_STRICT (readdirp, frame, -1, op_errno, NULL, NULL);
21ab4e
         return 0;
21ab4e
 
21ab4e
- unref_dict:
21ab4e
+unref_dict:
21ab4e
         if (xref)
21ab4e
                 dict_unref (dict);
21ab4e
         return 0;
21ab4e
@@ -2653,6 +2824,12 @@ br_stub_lookup_cbk (call_frame_t *frame, void *cookie,
21ab4e
                     struct iatt *stbuf, dict_t *xattr, struct iatt *postparent)
21ab4e
 {
21ab4e
         int32_t ret = 0;
21ab4e
+        br_stub_private_t *priv = NULL;
21ab4e
+        gf_boolean_t  ver_enabled = _gf_false;
21ab4e
+
21ab4e
+        BR_STUB_VER_ENABLED_IN_CALLPATH(frame, ver_enabled);
21ab4e
+        priv = this->private;
21ab4e
+        BR_STUB_VER_COND_GOTO (priv, (!ver_enabled), unwind);
21ab4e
 
21ab4e
         if (op_ret < 0) {
21ab4e
                 (void) br_stub_handle_lookup_error (this, inode, op_errno);
21ab4e
@@ -2730,6 +2907,8 @@ br_stub_lookup (call_frame_t *frame,
21ab4e
 
21ab4e
         priv = this->private;
21ab4e
 
21ab4e
+        BR_STUB_VER_NOT_ACTIVE_THEN_GOTO (frame, priv, wind);
21ab4e
+
21ab4e
         if (!gf_uuid_compare (loc->gfid, priv->bad_object_dir_gfid) ||
21ab4e
             !gf_uuid_compare (loc->pargfid, priv->bad_object_dir_gfid)) {
21ab4e
 
21ab4e
@@ -2787,6 +2966,8 @@ br_stub_lookup (call_frame_t *frame,
21ab4e
         goto dealloc_dict;
21ab4e
 
21ab4e
  unwind:
21ab4e
+        if (frame->local == (void *) 0x1)
21ab4e
+                frame->local = NULL;
21ab4e
         STACK_UNWIND_STRICT (lookup, frame,
21ab4e
                              -1, op_errno, NULL, NULL, NULL, NULL);
21ab4e
  dealloc_dict:
21ab4e
@@ -2803,9 +2984,15 @@ br_stub_lookup (call_frame_t *frame,
21ab4e
 int
21ab4e
 br_stub_stat (call_frame_t *frame, xlator_t *this, loc_t *loc, dict_t *xdata)
21ab4e
 {
21ab4e
-        int32_t ret      = 0;
21ab4e
-        int32_t op_ret   = -1;
21ab4e
-        int32_t op_errno = EINVAL;
21ab4e
+        int32_t            ret      = 0;
21ab4e
+        int32_t            op_ret   = -1;
21ab4e
+        int32_t            op_errno = EINVAL;
21ab4e
+        br_stub_private_t *priv     = NULL;
21ab4e
+
21ab4e
+        priv = this->private;
21ab4e
+
21ab4e
+        if (!priv->do_versioning)
21ab4e
+                goto wind;
21ab4e
 
21ab4e
         if (!IA_ISREG (loc->inode->ia_type))
21ab4e
                 goto wind;
21ab4e
@@ -2828,9 +3015,15 @@ unwind:
21ab4e
 int
21ab4e
 br_stub_fstat (call_frame_t *frame, xlator_t *this, fd_t *fd, dict_t *xdata)
21ab4e
 {
21ab4e
-        int32_t ret      = 0;
21ab4e
-        int32_t op_ret   = -1;
21ab4e
-        int32_t op_errno = EINVAL;
21ab4e
+        int32_t            ret      = 0;
21ab4e
+        int32_t            op_ret   = -1;
21ab4e
+        int32_t            op_errno = EINVAL;
21ab4e
+        br_stub_private_t *priv     = NULL;
21ab4e
+
21ab4e
+        priv = this->private;
21ab4e
+
21ab4e
+        if (!priv->do_versioning)
21ab4e
+                goto wind;
21ab4e
 
21ab4e
         if (!IA_ISREG (fd->inode->ia_type))
21ab4e
                 goto wind;
21ab4e
@@ -2865,6 +3058,12 @@ br_stub_unlink_cbk (call_frame_t *frame, void *cookie, xlator_t *this,
21ab4e
         uint64_t             ctx_addr = 0;
21ab4e
         br_stub_inode_ctx_t *ctx      = NULL;
21ab4e
         int32_t              ret      = -1;
21ab4e
+        br_stub_private_t   *priv     = NULL;
21ab4e
+        gf_boolean_t         ver_enabled = _gf_false;
21ab4e
+
21ab4e
+        BR_STUB_VER_ENABLED_IN_CALLPATH (frame, ver_enabled);
21ab4e
+        priv = this->private;
21ab4e
+        BR_STUB_VER_COND_GOTO (priv, (!ver_enabled), unwind);
21ab4e
 
21ab4e
         local = frame->local;
21ab4e
         frame->local = NULL;
21ab4e
@@ -2921,9 +3120,13 @@ int
21ab4e
 br_stub_unlink (call_frame_t *frame, xlator_t *this, loc_t *loc, int flag,
21ab4e
                 dict_t *xdata)
21ab4e
 {
21ab4e
-        br_stub_local_t *local = NULL;
21ab4e
-        int32_t          op_ret = -1;
21ab4e
-        int32_t          op_errno = 0;
21ab4e
+        br_stub_local_t   *local    = NULL;
21ab4e
+        int32_t            op_ret   = -1;
21ab4e
+        int32_t            op_errno = 0;
21ab4e
+        br_stub_private_t *priv     = NULL;
21ab4e
+
21ab4e
+        priv = this->private;
21ab4e
+        BR_STUB_VER_NOT_ACTIVE_THEN_GOTO (frame, priv, wind);
21ab4e
 
21ab4e
         local = br_stub_alloc_local (this);
21ab4e
         if (!local) {
21ab4e
@@ -2941,11 +3144,14 @@ br_stub_unlink (call_frame_t *frame, xlator_t *this, loc_t *loc, int flag,
21ab4e
 
21ab4e
         frame->local = local;
21ab4e
 
21ab4e
+wind:
21ab4e
         STACK_WIND (frame, br_stub_unlink_cbk, FIRST_CHILD (this),
21ab4e
                     FIRST_CHILD (this)->fops->unlink, loc, flag, xdata);
21ab4e
         return 0;
21ab4e
 
21ab4e
 unwind:
21ab4e
+        if (frame->local == (void *)0x1)
21ab4e
+                frame->local = NULL;
21ab4e
         STACK_UNWIND_STRICT (unlink, frame, op_ret, op_errno, NULL, NULL, NULL);
21ab4e
         return 0;
21ab4e
 }
21ab4e
@@ -3246,7 +3452,7 @@ struct xlator_cbks cbks = {
21ab4e
 struct volume_options options[] = {
21ab4e
         { .key = {"bitrot"},
21ab4e
           .type = GF_OPTION_TYPE_BOOL,
21ab4e
-          .default_value = "on",
21ab4e
+          .default_value = "off",
21ab4e
           .description = "enable/disable bitrot stub"
21ab4e
         },
21ab4e
         { .key = {"export"},
21ab4e
diff --git a/xlators/features/bit-rot/src/stub/bit-rot-stub.h b/xlators/features/bit-rot/src/stub/bit-rot-stub.h
21ab4e
index 2d51541..e4f1cef 100644
21ab4e
--- a/xlators/features/bit-rot/src/stub/bit-rot-stub.h
21ab4e
+++ b/xlators/features/bit-rot/src/stub/bit-rot-stub.h
21ab4e
@@ -18,12 +18,36 @@
21ab4e
 #include "call-stub.h"
21ab4e
 #include "bit-rot-stub-mem-types.h"
21ab4e
 #include "syscall.h"
21ab4e
+#include "common-utils.h"
21ab4e
 #include "bit-rot-common.h"
21ab4e
 #include "bit-rot-stub-messages.h"
21ab4e
 #include "glusterfs3-xdr.h"
21ab4e
 
21ab4e
 #define BAD_OBJECT_THREAD_STACK_SIZE   ((size_t)(1024*1024))
21ab4e
 
21ab4e
+/* do not reference frame->local in cbk unless initialized.
21ab4e
+ * Assigned 0x1 marks verisoning flag between call path and
21ab4e
+ * cbk path.
21ab4e
+ */
21ab4e
+#define BR_STUB_VER_NOT_ACTIVE_THEN_GOTO(frame, priv, label) do {      \
21ab4e
+                if (priv->do_versioning)                               \
21ab4e
+                        frame->local = (void *)0x1;                    \
21ab4e
+                else                                                   \
21ab4e
+                        goto label;                                    \
21ab4e
+        } while (0)
21ab4e
+
21ab4e
+#define BR_STUB_VER_COND_GOTO(priv, cond, label) do {       \
21ab4e
+                if (!priv->do_versioning || cond)           \
21ab4e
+                        goto label;                         \
21ab4e
+        } while (0)
21ab4e
+
21ab4e
+#define BR_STUB_VER_ENABLED_IN_CALLPATH(frame, flag) do {   \
21ab4e
+                if (frame->local)                           \
21ab4e
+                        flag = _gf_true;                    \
21ab4e
+                if (frame->local == (void *) 0x1)           \
21ab4e
+                        frame->local = NULL;                \
21ab4e
+        } while (0)
21ab4e
+
21ab4e
 typedef int (br_stub_version_cbk) (call_frame_t *, void *,
21ab4e
                                    xlator_t *, int32_t, int32_t, dict_t *);
21ab4e
 
21ab4e
@@ -74,7 +98,7 @@ typedef struct br_stub_local {
21ab4e
 #define BR_STUB_INCREMENTAL_VERSIONING (1 << 1)
21ab4e
 
21ab4e
 typedef struct br_stub_private {
21ab4e
-        gf_boolean_t go;
21ab4e
+        gf_boolean_t do_versioning;
21ab4e
 
21ab4e
         uint32_t boot[2];
21ab4e
         char export[PATH_MAX];
21ab4e
diff --git a/xlators/mgmt/glusterd/src/glusterd-volgen.c b/xlators/mgmt/glusterd/src/glusterd-volgen.c
21ab4e
index faa6c72..c112dc8 100644
21ab4e
--- a/xlators/mgmt/glusterd/src/glusterd-volgen.c
21ab4e
+++ b/xlators/mgmt/glusterd/src/glusterd-volgen.c
21ab4e
@@ -1615,8 +1615,10 @@ static int
21ab4e
 brick_graph_add_bitrot_stub (volgen_graph_t *graph, glusterd_volinfo_t *volinfo,
21ab4e
                             dict_t *set_dict, glusterd_brickinfo_t *brickinfo)
21ab4e
 {
21ab4e
-        xlator_t        *xl  = NULL;
21ab4e
-        int              ret = -1;
21ab4e
+        xlator_t *xl    = NULL;
21ab4e
+        int       ret   = -1;
21ab4e
+        char     *value = NULL;
21ab4e
+        xlator_t *this  = THIS;
21ab4e
 
21ab4e
         if (!graph || !volinfo || !set_dict || !brickinfo)
21ab4e
                 goto out;
21ab4e
@@ -1626,6 +1628,17 @@ brick_graph_add_bitrot_stub (volgen_graph_t *graph, glusterd_volinfo_t *volinfo,
21ab4e
                 goto out;
21ab4e
 
21ab4e
         ret = xlator_set_option (xl, "export", brickinfo->path);
21ab4e
+        if (ret) {
21ab4e
+                gf_log (this->name, GF_LOG_WARNING, "failed to set the export "
21ab4e
+                        "option in bit-rot-stub");
21ab4e
+                goto out;
21ab4e
+        }
21ab4e
+
21ab4e
+        ret = glusterd_volinfo_get (volinfo, VKEY_FEATURES_BITROT, &value);
21ab4e
+        ret = xlator_set_option (xl, "bitrot", value);
21ab4e
+        if (ret)
21ab4e
+                gf_log (this->name, GF_LOG_WARNING, "failed to set bitrot "
21ab4e
+                        "enable option in bit-rot-stub");
21ab4e
 
21ab4e
 out:
21ab4e
         return ret;
21ab4e
-- 
21ab4e
1.8.3.1
21ab4e