From f2cf53322feb15cf8976e73923145d9272b2076c Mon Sep 17 00:00:00 2001 From: Daniel Rosenberg Date: Mon, 25 Jul 2022 14:28:33 -0700 Subject: [PATCH] ANDROID: fuse-bpf: Fix RCU/reference issue 094905c87771 ("ANDROID: fuse-bpf: Always call revalidate for backing") called dget_parent/dput improperly within an RCU context. Additionally, it failed to free/put some references. Fixes: 094905c87771 ("ANDROID: fuse-bpf: Always call revalidate for backing") Signed-off-by: Daniel Rosenberg Change-Id: Iedeee7550ff88366bc5310eedece285019336814 --- fs/fuse/dir.c | 25 ++++++++++--------------- 1 file changed, 10 insertions(+), 15 deletions(-) diff --git a/fs/fuse/dir.c b/fs/fuse/dir.c index 0eacbe8cf9c8..7d464480d74f 100644 --- a/fs/fuse/dir.c +++ b/fs/fuse/dir.c @@ -243,14 +243,6 @@ static int fuse_dentry_revalidate(struct dentry *entry, unsigned int flags) goto out; } } - /* TODO: Respect timeouts for lookups with backing inodes */ - parent = dget_parent(entry); - if (get_fuse_inode(d_inode_rcu(parent))->backing_inode) { - dput(parent); - ret = 1; - goto out; - } - dput(parent); #endif if (time_before64(fuse_dentry_time(entry), get_jiffies_64()) || (flags & LOOKUP_REVAL)) { @@ -269,23 +261,26 @@ static int fuse_dentry_revalidate(struct dentry *entry, unsigned int flags) goto out; fm = get_fuse_mount(inode); - forget = fuse_alloc_forget(); - ret = -ENOMEM; - if (!forget) - goto out; - - attr_version = fuse_get_attr_version(fm->fc); - parent = dget_parent(entry); /* TODO: Once we're handling timeouts for backing inodes, do a * bpf based lookup_revalidate here. */ if (get_fuse_inode(parent->d_inode)->backing_inode) { + dput(parent); ret = 1; goto out; } + forget = fuse_alloc_forget(); + ret = -ENOMEM; + if (!forget) { + dput(parent); + goto out; + } + + attr_version = fuse_get_attr_version(fm->fc); + fuse_lookup_init(fm->fc, &args, get_node_id(d_inode(parent)), &entry->d_name, &outarg, &bpf_arg.out); ret = fuse_simple_request(fm, &args);