aboutsummaryrefslogtreecommitdiffstats
path: root/fs/dcache.c
diff options
context:
space:
mode:
authorAl Viro <viro@zeniv.linux.org.uk>2018-08-09 10:15:54 -0400
committerAl Viro <viro@zeniv.linux.org.uk>2018-08-09 18:07:15 -0400
commit4c0d7cd5c8416b1ef41534d19163cb07ffaa03ab (patch)
tree1271fc0ec0ee812900750b246c90afd807efabac /fs/dcache.c
parent119e1ef80ecfe0d1deb6378d4ab41f5b71519de1 (diff)
make sure that __dentry_kill() always invalidates d_seq, unhashed or not
RCU pathwalk relies upon the assumption that anything that changes ->d_inode of a dentry will invalidate its ->d_seq. That's almost true - the one exception is that the final dput() of already unhashed dentry does *not* touch ->d_seq at all. Unhashing does, though, so for anything we'd found by RCU dcache lookup we are fine. Unfortunately, we can *start* with an unhashed dentry or jump into it. We could try and be careful in the (few) places where that could happen. Or we could just make the final dput() invalidate the damn thing, unhashed or not. The latter is much simpler and easier to backport, so let's do it that way. Reported-by: "Dae R. Jeong" <threeearcat@gmail.com> Cc: stable@vger.kernel.org Signed-off-by: Al Viro <viro@zeniv.linux.org.uk>
Diffstat (limited to 'fs/dcache.c')
-rw-r--r--fs/dcache.c7
1 files changed, 2 insertions, 5 deletions
diff --git a/fs/dcache.c b/fs/dcache.c
index d677290b0aca..ceb7b491d1b9 100644
--- a/fs/dcache.c
+++ b/fs/dcache.c
@@ -358,14 +358,11 @@ static void dentry_unlink_inode(struct dentry * dentry)
358 __releases(dentry->d_inode->i_lock) 358 __releases(dentry->d_inode->i_lock)
359{ 359{
360 struct inode *inode = dentry->d_inode; 360 struct inode *inode = dentry->d_inode;
361 bool hashed = !d_unhashed(dentry);
362 361
363 if (hashed) 362 raw_write_seqcount_begin(&dentry->d_seq);
364 raw_write_seqcount_begin(&dentry->d_seq);
365 __d_clear_type_and_inode(dentry); 363 __d_clear_type_and_inode(dentry);
366 hlist_del_init(&dentry->d_u.d_alias); 364 hlist_del_init(&dentry->d_u.d_alias);
367 if (hashed) 365 raw_write_seqcount_end(&dentry->d_seq);
368 raw_write_seqcount_end(&dentry->d_seq);
369 spin_unlock(&dentry->d_lock); 366 spin_unlock(&dentry->d_lock);
370 spin_unlock(&inode->i_lock); 367 spin_unlock(&inode->i_lock);
371 if (!inode->i_nlink) 368 if (!inode->i_nlink)