diff options
author | Pranith Kumar K <pkarampu@redhat.com> | 2014-04-25 20:36:11 +0530 |
---|---|---|
committer | Anand Avati <avati@redhat.com> | 2014-04-28 18:18:59 -0700 |
commit | 49e2d5162013ccf5f3f99c68c2521ca1cc6c3f20 (patch) | |
tree | a1812d0e30d0f44717b4b62736e8afba9aac29e1 /xlators/cluster/afr/src/afr-self-heald.c | |
parent | 3ea85192f1521c32915ed38bb4db61be11d59922 (diff) |
cluster/afr: Fix inode_forget assert failure
Problem:
If two self-heals are triggered on same inode in
parallel then one inode will be linked and the other
inode will not be linked as an inode with that gfid
is already linked in inode table. Calling inode-forget
on that inode leads to assert failure.
Fix:
Always use linked inode for performing self-heal.
Added inode-forgets in other places as well even though
its not really a memory leak.
Change-Id: Ib84bf080c8cb6a4243f66541ece587db28f9a052
BUG: 1091597
Signed-off-by: Pranith Kumar K <pkarampu@redhat.com>
Reviewed-on: http://review.gluster.org/7567
Tested-by: Gluster Build System <jenkins@build.gluster.com>
Reviewed-by: Anand Avati <avati@redhat.com>
Diffstat (limited to 'xlators/cluster/afr/src/afr-self-heald.c')
-rw-r--r-- | xlators/cluster/afr/src/afr-self-heald.c | 19 |
1 files changed, 16 insertions, 3 deletions
diff --git a/xlators/cluster/afr/src/afr-self-heald.c b/xlators/cluster/afr/src/afr-self-heald.c index 4bfe909bcb9..787cb4ff557 100644 --- a/xlators/cluster/afr/src/afr-self-heald.c +++ b/xlators/cluster/afr/src/afr-self-heald.c @@ -186,8 +186,10 @@ afr_shd_inode_find (xlator_t *this, xlator_t *subvol, uuid_t gfid) struct iatt iatt = {0, }; inode = inode_find (this->itable, gfid); - if (inode) + if (inode) { + inode_lookup (inode); goto out; + } loc.inode = inode_new (this->itable); if (!loc.inode) @@ -245,6 +247,9 @@ afr_shd_index_opendir (xlator_t *this, int child) fd = fd_anonymous (inode); out: loc_wipe (&rootloc); + if (inode) + inode_unref (inode); + if (xattr) dict_unref (xattr); return fd; @@ -440,8 +445,12 @@ afr_shd_index_sweep (struct subvol_healer *healer) break; } - if (fd) + if (fd) { + if (fd->inode) + inode_forget (fd->inode, 1); fd_unref (fd); + } + if (!ret) ret = count; return ret; @@ -942,8 +951,12 @@ afr_shd_gather_index_entries (xlator_t *this, int child, dict_t *output) break; } - if (fd) + if (fd) { + if (fd->inode) + inode_forget (fd->inode, 1); fd_unref (fd); + } + if (!ret) ret = count; return ret; |