summaryrefslogtreecommitdiffstats
path: root/fs/gfs2/dir.c
diff options
context:
space:
mode:
authorBob Peterson <rpeterso@redhat.com>2015-10-29 10:03:41 -0500
committerBob Peterson <rpeterso@redhat.com>2015-11-04 12:05:42 -0600
commitc36b97e9430defab4b52ee370c18745343d92f6d (patch)
treedfa18e7c6ddb1a1c2042cf583d755385141cb6ff /fs/gfs2/dir.c
parentf3dd1649122b9e73f869e5304d5fa8554e128b7a (diff)
downloadlinux-c36b97e9430defab4b52ee370c18745343d92f6d.tar.bz2
GFS2: Protect freeing directory hash table with i_lock spin_lock
This patch changes function gfs2_dir_hash_inval so it uses the i_lock spin_lock to protect the in-core hash table, i_hash_cache. This will prevent double-frees due to a race between gfs2_evict_inode and inode invalidation. Signed-off-by: Bob Peterson <rpeterso@redhat.com>
Diffstat (limited to 'fs/gfs2/dir.c')
-rw-r--r--fs/gfs2/dir.c7
1 files changed, 6 insertions, 1 deletions
diff --git a/fs/gfs2/dir.c b/fs/gfs2/dir.c
index 487527b42d94..ad8a5b757cc7 100644
--- a/fs/gfs2/dir.c
+++ b/fs/gfs2/dir.c
@@ -388,8 +388,13 @@ static __be64 *gfs2_dir_get_hash_table(struct gfs2_inode *ip)
*/
void gfs2_dir_hash_inval(struct gfs2_inode *ip)
{
- __be64 *hc = ip->i_hash_cache;
+ __be64 *hc;
+
+ spin_lock(&ip->i_inode.i_lock);
+ hc = ip->i_hash_cache;
ip->i_hash_cache = NULL;
+ spin_unlock(&ip->i_inode.i_lock);
+
kvfree(hc);
}