summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorXavier Hernandez <xhernandez@datalab.es>2015-01-13 10:50:06 +0100
committerRaghavendra Bhat <raghavendra@redhat.com>2015-02-11 01:40:11 -0800
commit258f38c76f5ad816450c826becfddbe3cc91f874 (patch)
tree941790a8594decba46f965485cbcb1a2b0c52f50
parent22035d5e37db748cbdee2596d99006cea6b5282e (diff)
ec: Don't use inodelk on getxattr when clearing locks
When command 'clear-locks' from cli is executed, a getxattr request is received by ec. This request was handled as usual, first locking the inode. Once this request was processed by the bricks, all locks were removed, including the lock used by ec. When ec tried to unlock the previously acquired lock (which was already released), caused a crash in glusterfsd. This fix executes the getxattr request without any lock acquired for the clear-locks command. This is a backport of http://review.gluster.org/9440/ Change-Id: I77e550d13c4673d2468a1e13fe6e2fed20e233c6 BUG: 1181977 Signed-off-by: Xavier Hernandez <xhernandez@datalab.es> Reviewed-on: http://review.gluster.org/9444 Reviewed-by: Dan Lambright <dlambrig@redhat.com> Tested-by: Gluster Build System <jenkins@build.gluster.com> Reviewed-by: Raghavendra Bhat <raghavendra@redhat.com>
-rw-r--r--tests/bugs/bug-1179050.t23
-rw-r--r--xlators/cluster/ec/src/ec-combine.c2
-rw-r--r--xlators/cluster/ec/src/ec-inode-read.c19
3 files changed, 35 insertions, 9 deletions
diff --git a/tests/bugs/bug-1179050.t b/tests/bugs/bug-1179050.t
new file mode 100644
index 00000000000..be261cbc144
--- /dev/null
+++ b/tests/bugs/bug-1179050.t
@@ -0,0 +1,23 @@
+#!/bin/bash
+
+. $(dirname $0)/../include.rc
+. $(dirname $0)/../volume.rc
+
+cleanup
+
+TEST glusterd
+TEST pidof glusterd
+TEST $CLI volume create $V0 redundancy 1 $H0:$B0/${V0}{0..2}
+EXPECT "Created" volinfo_field $V0 'Status'
+TEST $CLI volume start $V0
+EXPECT_WITHIN $PROCESS_UP_TIMEOUT "Started" volinfo_field $V0 'Status'
+TEST glusterfs --entry-timeout=0 --attribute-timeout=0 --volfile-id=/$V0 --volfile-server=$H0 $M0
+EXPECT_WITHIN $CHILD_UP_TIMEOUT "3" ec_child_up_count $V0 0
+
+TEST $CLI volume clear-locks $V0 / kind all inode
+
+sleep 1
+
+EXPECT "3" ec_child_up_count $V0 0
+
+cleanup
diff --git a/xlators/cluster/ec/src/ec-combine.c b/xlators/cluster/ec/src/ec-combine.c
index e605f7ba567..0f883d03fac 100644
--- a/xlators/cluster/ec/src/ec-combine.c
+++ b/xlators/cluster/ec/src/ec-combine.c
@@ -131,8 +131,8 @@ int32_t ec_dict_data_compare(dict_t * dict, char * key, data_t * value,
(strcmp(key, GF_XATTR_PATHINFO_KEY) == 0) ||
(strcmp(key, GF_XATTR_USER_PATHINFO_KEY) == 0) ||
(strcmp(key, GF_XATTR_LOCKINFO_KEY) == 0) ||
- (strcmp(key, GF_XATTR_CLRLK_CMD) == 0) ||
(strcmp(key, GLUSTERFS_OPEN_FD_COUNT) == 0) ||
+ (strncmp(key, GF_XATTR_CLRLK_CMD, strlen(GF_XATTR_CLRLK_CMD)) == 0) ||
(strncmp(key, EC_QUOTA_PREFIX, strlen(EC_QUOTA_PREFIX)) == 0) ||
(fnmatch(GF_XATTR_STIME_PATTERN, key, 0) == 0) ||
(fnmatch(MARKER_XATTR_PREFIX ".*." XTIME, key, 0) == 0) ||
diff --git a/xlators/cluster/ec/src/ec-inode-read.c b/xlators/cluster/ec/src/ec-inode-read.c
index c87f6ea1d01..3483dfb3354 100644
--- a/xlators/cluster/ec/src/ec-inode-read.c
+++ b/xlators/cluster/ec/src/ec-inode-read.c
@@ -242,15 +242,18 @@ int32_t ec_manager_getxattr(ec_fop_data_t * fop, int32_t state)
{
case EC_STATE_INIT:
case EC_STATE_LOCK:
- if (fop->fd == NULL)
- {
- ec_lock_prepare_inode(fop, &fop->loc[0], 0);
- }
- else
- {
- ec_lock_prepare_fd(fop, fop->fd, 0);
+ /* clear-locks commands must be done without any locks acquired
+ to avoid interferences. */
+ if ((fop->str[0] == NULL) ||
+ (strncmp(fop->str[0], GF_XATTR_CLRLK_CMD,
+ strlen(GF_XATTR_CLRLK_CMD)) != 0)) {
+ if (fop->fd == NULL) {
+ ec_lock_prepare_inode(fop, &fop->loc[0], 0);
+ } else {
+ ec_lock_prepare_fd(fop, fop->fd, 0);
+ }
+ ec_lock(fop);
}
- ec_lock(fop);
return EC_STATE_DISPATCH;