summaryrefslogtreecommitdiffstats
path: root/libglusterfs/src/inode.c
diff options
context:
space:
mode:
authorPoornima G <pgurusid@redhat.com>2017-02-15 11:18:31 +0530
committerShyamsundar Ranganathan <srangana@redhat.com>2017-02-20 07:25:29 -0500
commitd10c5375b33520f36fd6acbd47b617d43f529ca2 (patch)
tree40d8b2f2385e74431fa03bcd4cf5913b8c40e00d /libglusterfs/src/inode.c
parenta0f6d7c775fb0de4beff0e326f2865353207b8db (diff)
libglusterfs: Fix a crash due to race between inode_ctx_set and inode_ref
Issue: Currently inode ref count is guarded by inode_table->lock, and inode_ctx is guarded by inode->lock. With the new patch [1] inode_ref was modified to change the inode_ctx to track the ref count per xlator. Thus inode_ref performed under inode_table->lock is modifying inode_ctx which has to be modified only under inode->lock Solution: When a inode is created, inode_ctx holder is allocated for all the xlators. Hence in case of inode_ctx_set instead of using the first free index in inode ctx holder, we can have predecided index for every xlator in the graph. Credits Pranith K <pkarampu@redhat.com> [1] http://review.gluster.org/13736 > Reviewed-on: https://review.gluster.org/16622 > Smoke: Gluster Build System <jenkins@build.gluster.org> > NetBSD-regression: NetBSD Build System <jenkins@build.gluster.org> > Reviewed-by: Niels de Vos <ndevos@redhat.com> > CentOS-regression: Gluster Build System <jenkins@build.gluster.org> > Reviewed-by: Pranith Kumar Karampuri <pkarampu@redhat.com> Change-Id: I1bfe111c211fcc4fcd761bba01dc87c4c69b5170 BUG: 1423385 Signed-off-by: Poornima G <pgurusid@redhat.com> Reviewed-on: https://review.gluster.org/16655 NetBSD-regression: NetBSD Build System <jenkins@build.gluster.org> Smoke: Gluster Build System <jenkins@build.gluster.org> CentOS-regression: Gluster Build System <jenkins@build.gluster.org> Reviewed-by: Shyamsundar Ranganathan <srangana@redhat.com>
Diffstat (limited to 'libglusterfs/src/inode.c')
-rw-r--r--libglusterfs/src/inode.c48
1 files changed, 14 insertions, 34 deletions
diff --git a/libglusterfs/src/inode.c b/libglusterfs/src/inode.c
index d39a2194921..573ec03819a 100644
--- a/libglusterfs/src/inode.c
+++ b/libglusterfs/src/inode.c
@@ -451,21 +451,15 @@ static int
__inode_get_xl_index (inode_t *inode, xlator_t *xlator)
{
int set_idx = -1;
- int index = 0;
-
- for (index = 0; index < inode->table->ctxcount; index++) {
- if (!inode->_ctx[index].xl_key) {
- if (set_idx == -1)
- set_idx = index;
- /* dont break, to check if key already exists
- further on */
- }
- if (inode->_ctx[index].xl_key == xlator) {
- set_idx = index;
- break;
- }
- }
+ if ((inode->_ctx[xlator->xl_id].xl_key != NULL) &&
+ (inode->_ctx[xlator->xl_id].xl_key != xlator))
+ goto out;
+
+ set_idx = xlator->xl_id;
+ inode->_ctx[set_idx].xl_key = xlator;
+
+out:
return set_idx;
}
@@ -2075,12 +2069,8 @@ __inode_ctx_get2 (inode_t *inode, xlator_t *xlator, uint64_t *value1,
if (!inode || !xlator || !inode->_ctx)
goto out;
- for (index = 0; index < inode->table->ctxcount; index++) {
- if (inode->_ctx[index].xl_key == xlator)
- break;
- }
-
- if (index == inode->table->ctxcount)
+ index = xlator->xl_id;
+ if (inode->_ctx[index].xl_key != xlator)
goto out;
if (inode->_ctx[index].value1) {
@@ -2196,13 +2186,8 @@ inode_ctx_del2 (inode_t *inode, xlator_t *xlator, uint64_t *value1,
if (!inode->_ctx)
goto unlock;
- for (index = 0; index < inode->table->ctxcount;
- index++) {
- if (inode->_ctx[index].xl_key == xlator)
- break;
- }
-
- if (index == inode->table->ctxcount) {
+ index = xlator->xl_id;
+ if (inode->_ctx[index].xl_key != xlator) {
ret = -1;
goto unlock;
}
@@ -2242,13 +2227,8 @@ __inode_ctx_reset2 (inode_t *inode, xlator_t *xlator, uint64_t *value1,
LOCK (&inode->lock);
{
- for (index = 0; index < inode->table->ctxcount;
- index++) {
- if (inode->_ctx[index].xl_key == xlator)
- break;
- }
-
- if (index == inode->table->ctxcount) {
+ index = xlator->xl_id;
+ if (inode->_ctx[index].xl_key != xlator) {
ret = -1;
goto unlock;
}