From acf8cfdf698aa3ebe42ed55bba8be4f85b751c29 Mon Sep 17 00:00:00 2001 From: shishir gowda Date: Thu, 20 Jun 2013 14:06:04 +0530 Subject: Revert "storage/posix: Remove the interim fix that handles the gfid race" This reverts commit 97807e75956a2d240282bc64fab1b71762de0546. In a distribute or distribute-replica volume, this fix is required to prevent gfid mis-match due to race issues. test script bug-767585-gfid.t needs a sleep of 2, cause after setting backend gfid directly, we try to heal, and with this fix, we do not allow setxattr of gfid within creation of 1 second if not created by itself Change-Id: Ie3f4b385416889fd5de444638a64a7eaaf24cd60 BUG: 951195 Signed-off-by: shishir gowda Reviewed-on: http://review.gluster.org/5240 Tested-by: Gluster Build System Reviewed-by: Amar Tumballi --- tests/bugs/bug-767585-gfid.t | 3 +- xlators/storage/posix/src/posix-helpers.c | 68 +++++++++++++++++++++++++++++++ xlators/storage/posix/src/posix.c | 2 +- xlators/storage/posix/src/posix.h | 2 +- 4 files changed, 72 insertions(+), 3 deletions(-) mode change 100644 => 100755 tests/bugs/bug-767585-gfid.t diff --git a/tests/bugs/bug-767585-gfid.t b/tests/bugs/bug-767585-gfid.t old mode 100644 new mode 100755 index 0cb6e3cb..49cf7423 --- a/tests/bugs/bug-767585-gfid.t +++ b/tests/bugs/bug-767585-gfid.t @@ -12,7 +12,6 @@ gfid1="0x8428b7193a764bf8be8046fb860b8993" gfid2="0x85ad91afa2f74694bf52c3326d048209" cleanup; - TEST glusterd TEST pidof glusterd TEST $CLI volume create $V0 replica 2 $H0:$B0/${V0}0 $H0:$B0/${V0}1 @@ -25,6 +24,8 @@ touch $B0/${V0}0/c $B0/${V0}1/c TEST setfattr -n trusted.gfid -v $gfid1 $B0/${V0}0/b TEST setfattr -n trusted.gfid -v $gfid2 $B0/${V0}1/c +sleep 2 + cd $M0 TEST ls -l a TEST ls -l b diff --git a/xlators/storage/posix/src/posix-helpers.c b/xlators/storage/posix/src/posix-helpers.c index 616664a3..2fa55eda 100644 --- a/xlators/storage/posix/src/posix-helpers.c +++ b/xlators/storage/posix/src/posix-helpers.c @@ -901,6 +901,74 @@ unlock: UNLOCK (&priv->lock); } +static int +is_fresh_file (struct stat *stat) +{ + struct timeval tv; + + gettimeofday (&tv, NULL); + + if ((stat->st_ctime >= (tv.tv_sec - 1)) + && (stat->st_ctime <= tv.tv_sec)) + return 1; + + return 0; +} + + +int +posix_gfid_heal (xlator_t *this, const char *path, loc_t *loc, dict_t *xattr_req) +{ + /* The purpose of this function is to prevent a race + where an inode creation FOP (like mkdir/mknod/create etc) + races with lookup in the following way: + + {create thread} | {lookup thread} + | + t0 + mkdir ("name") | + t1 + | posix_gfid_set ("name", 2); + t2 + posix_gfid_set ("name", 1); | + t3 + lstat ("name"); | lstat ("name"); + + In the above case mkdir FOP would have resulted with GFID 2 while + it should have been GFID 1. It matters in the case where GFID would + have gotten set to 1 on other subvolumes of replciate/distribute + + The "solution" here is that, if we detect lookup is attempting to + set a GFID on a file which is created very recently, but does not + yet have a GFID (i.e, between t1 and t2), then "fake" it as though + posix_gfid_heal was called at t0 instead. + */ + + uuid_t uuid_curr; + int ret = 0; + struct stat stat = {0, }; + + if (!xattr_req) + goto out; + + if (sys_lstat (path, &stat) != 0) + goto out; + + ret = sys_lgetxattr (path, GFID_XATTR_KEY, uuid_curr, 16); + if (ret != 16) { + if (is_fresh_file (&stat)) { + ret = -1; + errno = ENOENT; + goto out; + } + } + + ret = posix_gfid_set (this, path, loc, xattr_req); +out: + return ret; +} + + int posix_acl_xattr_set (xlator_t *this, const char *path, dict_t *xattr_req) { diff --git a/xlators/storage/posix/src/posix.c b/xlators/storage/posix/src/posix.c index e917766b..0a703021 100644 --- a/xlators/storage/posix/src/posix.c +++ b/xlators/storage/posix/src/posix.c @@ -129,7 +129,7 @@ posix_lookup (call_frame_t *frame, xlator_t *this, MAKE_ENTRY_HANDLE (real_path, par_path, this, loc, &buf); if (uuid_is_null (loc->inode->gfid)) { - posix_gfid_set (this, real_path, loc, xdata); + posix_gfid_heal (this, real_path, loc, xdata); MAKE_ENTRY_HANDLE (real_path, par_path, this, loc, &buf); } diff --git a/xlators/storage/posix/src/posix.h b/xlators/storage/posix/src/posix.h index c834b29d..a957e187 100644 --- a/xlators/storage/posix/src/posix.h +++ b/xlators/storage/posix/src/posix.h @@ -188,7 +188,7 @@ int posix_get_file_contents (xlator_t *this, uuid_t pargfid, int posix_set_file_contents (xlator_t *this, const char *path, char *key, data_t *value, int flags); int posix_acl_xattr_set (xlator_t *this, const char *path, dict_t *xattr_req); -int posix_gfid_heal (xlator_t *this, const char *path, dict_t *xattr_req); +int posix_gfid_heal (xlator_t *this, const char *path, loc_t *loc, dict_t *xattr_req); int posix_entry_create_xattr_set (xlator_t *this, const char *path, dict_t *dict); -- cgit