From nobody Mon Jan 5 11:07:21 2026 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by smtp.lore.kernel.org (Postfix) with ESMTP id 9F2C0E784BC for ; Mon, 2 Oct 2023 15:24:55 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S238091AbjJBPY4 (ORCPT ); Mon, 2 Oct 2023 11:24:56 -0400 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:47356 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S238087AbjJBPYu (ORCPT ); Mon, 2 Oct 2023 11:24:50 -0400 Received: from bee.birch.relay.mailchannels.net (bee.birch.relay.mailchannels.net [23.83.209.14]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id D55EDB8 for ; Mon, 2 Oct 2023 08:24:46 -0700 (PDT) X-Sender-Id: dreamhost|x-authsender|kjlx@templeofstupid.com Received: from relay.mailchannels.net (localhost [127.0.0.1]) by relay.mailchannels.net (Postfix) with ESMTP id 9F9CB800BC2 for ; Mon, 2 Oct 2023 15:24:43 +0000 (UTC) Received: from pdx1-sub0-mail-a234.dreamhost.com (unknown [127.0.0.6]) (Authenticated sender: dreamhost) by relay.mailchannels.net (Postfix) with ESMTPA id 2ACC3801C06 for ; Mon, 2 Oct 2023 15:24:43 +0000 (UTC) ARC-Seal: i=1; s=arc-2022; d=mailchannels.net; t=1696260283; a=rsa-sha256; cv=none; b=ZPypHAlP6Jjjo6MElegIyivurm/bZW6rWOWxDEmrMKQYcfq9aM4bxSv6Nmz85EM9EGUIqw rVr69k6Z99oRSDJatKnMYsGn/F4tC8fIbbVW2di9m5bcjsGsF5LDcXDjW773sxeNwltJxS 9/k0KO/QZ9VPqYscdXW3kord5122BQwNoUDOM76GyFB7N61J/sz63227nVviAalriAcoTs e0IzxnEB1xX4a9VMb/07iuqjKcakaR+gbufDbgiDJuaL0RV+7AbTyc5Gi2SAY6aTsbbaZ7 Q7PQng6GVsyhvBdjfHuuZ07jaJe00u/0g/zhh1Ns/x+ZrwiexT/6dtmW/rCuYA== ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=mailchannels.net; s=arc-2022; t=1696260283; h=from:from:reply-to:subject:subject:date:date:message-id:message-id: to:to:cc:cc:mime-version:mime-version:content-type:content-type: in-reply-to:in-reply-to:references:references:dkim-signature; bh=TVjVZZCVY56Vmj7QpyQH3UJ5VWeUuqsU7/tY0Ipy4co=; b=W4+CZEqQpB/vVFuICfVqf4VkMkrHelrSs/wH1rm0j+vX51BNV6babfKHFIzq9McDH+XokH cAMjRZzYU9EhYvroawnC2SC4qoFc2SFFWaJ1/EasR0tteG9fqOqdt+GroF8kl7d1imT+NC RLjux/m3ytyPPpJkXMju0FYHHmA/lZTKwAayC97Wa65KwPSeLrmzShjH/21gqNkXNl9+sT uTb5XZ51sEJB8mfWt7reDjEOnOeQKdpP0TTYKjBuaVWBecnJiqmth3ryHf5jGDSXZzCvFv J5LoVSBM1/f6SxbeqS9LdC6NxDG3PqF+mfBUF8Th24mN1HEgz5J9RUGHjXZXsA== ARC-Authentication-Results: i=1; rspamd-7c449d4847-p25dv; auth=pass smtp.auth=dreamhost smtp.mailfrom=kjlx@templeofstupid.com X-Sender-Id: dreamhost|x-authsender|kjlx@templeofstupid.com X-MC-Relay: Neutral X-MailChannels-SenderId: dreamhost|x-authsender|kjlx@templeofstupid.com X-MailChannels-Auth-Id: dreamhost X-Eight-Abortive: 3bab207e103c039a_1696260283434_2964901075 X-MC-Loop-Signature: 1696260283434:4163934859 X-MC-Ingress-Time: 1696260283434 Received: from pdx1-sub0-mail-a234.dreamhost.com (pop.dreamhost.com [64.90.62.162]) (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384) by 100.97.162.150 (trex/6.9.1); Mon, 02 Oct 2023 15:24:43 +0000 Received: from kmjvbox (c-73-231-176-24.hsd1.ca.comcast.net [73.231.176.24]) (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits) key-exchange X25519 server-signature RSA-PSS (2048 bits) server-digest SHA256) (No client certificate requested) (Authenticated sender: kjlx@templeofstupid.com) by pdx1-sub0-mail-a234.dreamhost.com (Postfix) with ESMTPSA id 4RzlB23fmQz1TG for ; Mon, 2 Oct 2023 08:24:42 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=templeofstupid.com; s=dreamhost; t=1696260282; bh=TVjVZZCVY56Vmj7QpyQH3UJ5VWeUuqsU7/tY0Ipy4co=; h=Date:From:To:Cc:Subject:Content-Type; b=RVADlwDi63AV3zzotDLLj5vXk6zEWrjFRHZnmfcpOnLAmCw2Yd0wGuSV+tOAHRpBk ma45QvOv3sGdnHg0u0QRltGTzLRmFkYvLRgYkZ0opMsAovJXSQwI8Xw+/plBVB2DTk LkYWqhUfw+JSykiLkBaGgLfwlgbvgsBUMGbsPsX0dCsukVSl09YfR1dFRYHfaWUB4m 3yygStcInkJM13JZvfZprEBMQUE+40fjycZxBRutU85+uYartlauJDdX+CZKdqCzSZ Pz1AxCpxLP1w2yybrKHxlEryq8tPQsUT4QOFKc5+UcLwHFYG/J9DynTiH06jnyNbmN QefBFIHkll+rg== Received: from johansen (uid 1000) (envelope-from kjlx@templeofstupid.com) id e0110 by kmjvbox (DragonFly Mail Agent v0.12); Mon, 02 Oct 2023 08:24:38 -0700 Date: Mon, 2 Oct 2023 08:24:38 -0700 From: Krister Johansen To: Miklos Szeredi , linux-fsdevel@vger.kernel.org Cc: Miklos Szeredi , linux-kernel@vger.kernel.org, German Maglione , Greg Kurz , Max Reitz , Bernd Schubert Subject: [resend PATCH v2 1/2] fuse: revalidate: move lookup into a separate function Message-ID: <82abdcba1e56dd3bc524bc3f2f44ae9c71f40fb7.1696043833.git.kjlx@templeofstupid.com> References: MIME-Version: 1.0 Content-Disposition: inline In-Reply-To: Precedence: bulk List-ID: X-Mailing-List: linux-kernel@vger.kernel.org Content-Transfer-Encoding: quoted-printable Content-Type: text/plain; charset="utf-8" Move the lookup parts of fuse_dentry_revalidate into a common function. This function will be used elsewhere in a separate commit. In the meantime, the new function fuse_dentry_revalidate_lookup is responsible for just the lookup and validation portions of the revalidate dance. The fuse_dentry_revalidate function retains the responsibility for invalidating and mutating any state associated with the origial fuse_inode and dentry. The rationale for this refactoring is to allow a lookup to be triggered as part of creating a submount. The submount code lives in another module. A subsequent commit will utilize the common function that is created by this commit. Signed-off-by: Krister Johansen --- fs/fuse/dir.c | 85 +++++++++++++++++++++++++++++++++++---------------- 1 file changed, 58 insertions(+), 27 deletions(-) diff --git a/fs/fuse/dir.c b/fs/fuse/dir.c index d707e6987da9..5e01946d7531 100644 --- a/fs/fuse/dir.c +++ b/fs/fuse/dir.c @@ -183,6 +183,57 @@ static void fuse_lookup_init(struct fuse_conn *fc, str= uct fuse_args *args, args->out_args[0].value =3D outarg; } =20 +static int fuse_dentry_revalidate_lookup(struct fuse_mount *fm, + struct dentry *entry, + struct inode *inode, + struct fuse_entry_out *outarg, + bool *lookedup) +{ + struct dentry *parent; + struct fuse_forget_link *forget; + FUSE_ARGS(args); + int ret; + + forget =3D fuse_alloc_forget(); + ret =3D -ENOMEM; + if (!forget) + goto out; + + parent =3D dget_parent(entry); + fuse_lookup_init(fm->fc, &args, get_node_id(d_inode(parent)), + &entry->d_name, outarg); + ret =3D fuse_simple_request(fm, &args); + dput(parent); + + /* Zero nodeid is same as -ENOENT */ + if (!ret && !outarg->nodeid) + ret =3D -ENOENT; + if (!ret) { + if (outarg->nodeid !=3D get_node_id(inode) || + (bool) IS_AUTOMOUNT(inode) !=3D (bool) (outarg->attr.flags & FUSE_AT= TR_SUBMOUNT)) { + fuse_queue_forget(fm->fc, forget, + outarg->nodeid, 1); + goto invalid; + } + *lookedup =3D true; + } + kfree(forget); + if (ret =3D=3D -ENOMEM || ret =3D=3D -EINTR) + goto out; + if (ret || fuse_invalid_attr(&outarg->attr) || + fuse_stale_inode(inode, outarg->generation, &outarg->attr)) { + goto invalid; + } + + ret =3D 1; +out: + return ret; + +invalid: + ret =3D 0; + goto out; +} + /* * Check whether the dentry is still valid * @@ -206,9 +257,8 @@ static int fuse_dentry_revalidate(struct dentry *entry,= unsigned int flags) else if (time_before64(fuse_dentry_time(entry), get_jiffies_64()) || (flags & (LOOKUP_EXCL | LOOKUP_REVAL | LOOKUP_RENAME_TARGET))) { struct fuse_entry_out outarg; - FUSE_ARGS(args); - struct fuse_forget_link *forget; u64 attr_version; + bool lookedup =3D false; =20 /* For negative dentries, always do a fresh lookup */ if (!inode) @@ -220,38 +270,19 @@ static int fuse_dentry_revalidate(struct dentry *entr= y, unsigned int flags) =20 fm =3D get_fuse_mount(inode); =20 - forget =3D fuse_alloc_forget(); - ret =3D -ENOMEM; - if (!forget) - goto out; - attr_version =3D fuse_get_attr_version(fm->fc); =20 - parent =3D dget_parent(entry); - fuse_lookup_init(fm->fc, &args, get_node_id(d_inode(parent)), - &entry->d_name, &outarg); - ret =3D fuse_simple_request(fm, &args); - dput(parent); - /* Zero nodeid is same as -ENOENT */ - if (!ret && !outarg.nodeid) - ret =3D -ENOENT; - if (!ret) { + ret =3D fuse_dentry_revalidate_lookup(fm, entry, inode, &outarg, + &lookedup); + if (ret =3D=3D -ENOMEM || ret =3D=3D -EINTR) + goto out; + if (lookedup) { fi =3D get_fuse_inode(inode); - if (outarg.nodeid !=3D get_node_id(inode) || - (bool) IS_AUTOMOUNT(inode) !=3D (bool) (outarg.attr.flags & FUSE_AT= TR_SUBMOUNT)) { - fuse_queue_forget(fm->fc, forget, - outarg.nodeid, 1); - goto invalid; - } spin_lock(&fi->lock); fi->nlookup++; spin_unlock(&fi->lock); } - kfree(forget); - if (ret =3D=3D -ENOMEM || ret =3D=3D -EINTR) - goto out; - if (ret || fuse_invalid_attr(&outarg.attr) || - fuse_stale_inode(inode, outarg.generation, &outarg.attr)) + if (ret <=3D 0) goto invalid; =20 forget_all_cached_acls(inode); --=20 2.25.1 From nobody Mon Jan 5 11:07:21 2026 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by smtp.lore.kernel.org (Postfix) with ESMTP id 0B0F2E784BE for ; Mon, 2 Oct 2023 15:25:03 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S238106AbjJBPZD (ORCPT ); Mon, 2 Oct 2023 11:25:03 -0400 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:43046 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S238088AbjJBPY6 (ORCPT ); Mon, 2 Oct 2023 11:24:58 -0400 Received: from bird.elm.relay.mailchannels.net (bird.elm.relay.mailchannels.net [23.83.212.17]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id CCB5999 for ; Mon, 2 Oct 2023 08:24:54 -0700 (PDT) X-Sender-Id: dreamhost|x-authsender|kjlx@templeofstupid.com Received: from relay.mailchannels.net (localhost [127.0.0.1]) by relay.mailchannels.net (Postfix) with ESMTP id 732036C2346 for ; Mon, 2 Oct 2023 15:24:53 +0000 (UTC) Received: from pdx1-sub0-mail-a234.dreamhost.com (unknown [127.0.0.6]) (Authenticated sender: dreamhost) by relay.mailchannels.net (Postfix) with ESMTPA id 144BA6C25DC for ; Mon, 2 Oct 2023 15:24:53 +0000 (UTC) ARC-Seal: i=1; s=arc-2022; d=mailchannels.net; t=1696260293; a=rsa-sha256; cv=none; b=ZSq5TA12Aoo7Y/2xeI25EFcJ5tecBJ4mjk/2ecRWG6WXRQTdQO6rqcwPw2QptkU2EUehpM 0yft6F7WPSj7IYQlaSFP+wdkj2QnrRiWMdSu7HwezgISfZKJqPgRLOkCHehIsLW2bTeAFx 5Q2JlF15jC8zPX8oRenUU/Xrtth953/CcFPpXixFjM4DrR8HHxSb3JJq20otpEm6mU+OJ1 DPDGa3ZH9d6S5LIMA8A7/3wBBgsWAidtOr6JyzYfkwBSK+9Vo5e58o92RSiko72HymLEhe R3BIKVedEOFvg30JoTGG1U97Rd9r+4cT5ReeoHekz6xaavlCN+d0y++ftKx36A== ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=mailchannels.net; s=arc-2022; t=1696260293; h=from:from:reply-to:subject:subject:date:date:message-id:message-id: to:to:cc:cc:mime-version:mime-version:content-type:content-type: in-reply-to:in-reply-to:references:references:dkim-signature; bh=BpDz/GSeF06rc+c8xq1C9eT93VnU3phb3ZkiVcYrwwo=; b=7E3Qdt/v8aeHQvR00A58F7SI/cWHNloeX0BkUInnNVUQIcDbKT8DKtWEmWAg541O6APgBa j+piL0m2syRnO/PJm01faggtBmKahcwm0uP7lbNpIy+zDTHGrafDS5oLAXthzFIQq0PKRO /43148woUwxRzRXZ0lRjIZbNtgIPrX2nTSi4DZu80iNn0prq3g55zOpTkeDg5ARkMf1oJO +1m/14g6CP/5vrscJKTsALUBEnjj7xRaUOiZ3gPuCWPjYjIsIMZ09l99zSKYEELuVxq8dl qTAu4xtPimvFm0z4l4cw2ItC+ARW4BEMHXLirRcYF4dBnxleHmI31YDYYTRP+Q== ARC-Authentication-Results: i=1; rspamd-7d5dc8fd68-7jvhx; auth=pass smtp.auth=dreamhost smtp.mailfrom=kjlx@templeofstupid.com X-Sender-Id: dreamhost|x-authsender|kjlx@templeofstupid.com X-MC-Relay: Neutral X-MailChannels-SenderId: dreamhost|x-authsender|kjlx@templeofstupid.com X-MailChannels-Auth-Id: dreamhost X-Shelf-Whispering: 272698364e44d9dc_1696260293310_3036199405 X-MC-Loop-Signature: 1696260293310:705572807 X-MC-Ingress-Time: 1696260293310 Received: from pdx1-sub0-mail-a234.dreamhost.com (pop.dreamhost.com [64.90.62.162]) (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384) by 100.124.45.11 (trex/6.9.1); Mon, 02 Oct 2023 15:24:53 +0000 Received: from kmjvbox (c-73-231-176-24.hsd1.ca.comcast.net [73.231.176.24]) (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits) key-exchange X25519 server-signature RSA-PSS (2048 bits) server-digest SHA256) (No client certificate requested) (Authenticated sender: kjlx@templeofstupid.com) by pdx1-sub0-mail-a234.dreamhost.com (Postfix) with ESMTPSA id 4RzlBD5nx3z11T for ; Mon, 2 Oct 2023 08:24:52 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=templeofstupid.com; s=dreamhost; t=1696260292; bh=BpDz/GSeF06rc+c8xq1C9eT93VnU3phb3ZkiVcYrwwo=; h=Date:From:To:Cc:Subject:Content-Type; b=VmXXspI4qsfiYqhz5/mCWzzyo+dIKOMdlF3OebWW0mcd3gmSmEZvmYuMQ36gkw7NF MFCLv0xA1YtqyVzi2Q51ZVN2l9L5k5XQ1NmFghkA3l4rcKwfDKYpYn5lwy8xRx7DQZ iXln9qeqUX8y+SH3bSg5vWNRkHJRaZTDwkCic1/b8pu9VFbUJxah7LEGQwOfE/4kMK DSSuZf9s0lUI/Ue9kaXTI/HFkYmN4e7iBRNNFR+14UR6g7PF75HIImlWpDIuow3jsQ ACD1obGTy4TFa4wCDQNo6p04c+bjGObhDK5nLaDIRKVpEdkwOfIMSRw/6gJT5SRBG9 mnFDWgCFSozkw== Received: from johansen (uid 1000) (envelope-from kjlx@templeofstupid.com) id e0110 by kmjvbox (DragonFly Mail Agent v0.12); Mon, 02 Oct 2023 08:24:49 -0700 Date: Mon, 2 Oct 2023 08:24:49 -0700 From: Krister Johansen To: Miklos Szeredi , linux-fsdevel@vger.kernel.org Cc: Miklos Szeredi , linux-kernel@vger.kernel.org, German Maglione , Greg Kurz , Max Reitz , Bernd Schubert Subject: [resend PATCH v2 2/2] fuse: ensure that submounts lookup their parent Message-ID: <45778432fba32dce1fb1f5fd13272c89c95c3f52.1696043833.git.kjlx@templeofstupid.com> References: MIME-Version: 1.0 Content-Disposition: inline In-Reply-To: Precedence: bulk List-ID: X-Mailing-List: linux-kernel@vger.kernel.org Content-Transfer-Encoding: quoted-printable Content-Type: text/plain; charset="utf-8" The submount code uses the parent nodeid passed into the function in order to create the root dentry for the new submount. This nodeid does not get its remote reference count incremented by a lookup option. If the parent inode is evicted from its superblock, due to memory pressure for example, it can result in a forget opertation being sent to the server. Should this nodeid be forgotten while it is still in use in a submount, users of the submount get an error from the server on any subsequent access. In the author's case, this was an EBADF on all subsequent operations that needed to reference the root. Debugging the problem revealed that the dentry shrinker triggered a forget after killing the dentry with the last reference, despite the root dentry in another superblock still using the nodeid. As a result, a container that was also using this submount failed to access its filesystem because it had borrowed the reference instead of taking its own when setting up its superblock for the submount. This commit fixes the problem by having the new submount trigger a lookup for the parent as part of creating a new root dentry for the virtiofsd submount superblock. This allows each superblock to have its inodes removed by the shrinker when unreferenced, while keeping the nodeid reference count accurate and active with the server. Signed-off-by: Krister Johansen --- fs/fuse/dir.c | 10 +++++----- fs/fuse/fuse_i.h | 6 ++++++ fs/fuse/inode.c | 43 +++++++++++++++++++++++++++++++++++++------ 3 files changed, 48 insertions(+), 11 deletions(-) diff --git a/fs/fuse/dir.c b/fs/fuse/dir.c index 5e01946d7531..333730c74619 100644 --- a/fs/fuse/dir.c +++ b/fs/fuse/dir.c @@ -183,11 +183,11 @@ static void fuse_lookup_init(struct fuse_conn *fc, st= ruct fuse_args *args, args->out_args[0].value =3D outarg; } =20 -static int fuse_dentry_revalidate_lookup(struct fuse_mount *fm, - struct dentry *entry, - struct inode *inode, - struct fuse_entry_out *outarg, - bool *lookedup) +int fuse_dentry_revalidate_lookup(struct fuse_mount *fm, + struct dentry *entry, + struct inode *inode, + struct fuse_entry_out *outarg, + bool *lookedup) { struct dentry *parent; struct fuse_forget_link *forget; diff --git a/fs/fuse/fuse_i.h b/fs/fuse/fuse_i.h index 405252bb51f2..a66fcf50a4cc 100644 --- a/fs/fuse/fuse_i.h +++ b/fs/fuse/fuse_i.h @@ -1325,6 +1325,12 @@ void fuse_dax_dontcache(struct inode *inode, unsigne= d int flags); bool fuse_dax_check_alignment(struct fuse_conn *fc, unsigned int map_align= ment); void fuse_dax_cancel_work(struct fuse_conn *fc); =20 +/* dir.c */ +int fuse_dentry_revalidate_lookup(struct fuse_mount *fm, struct dentry *en= try, + struct inode *inode, + struct fuse_entry_out *outarg, + bool *lookedup); + /* ioctl.c */ long fuse_file_ioctl(struct file *file, unsigned int cmd, unsigned long ar= g); long fuse_file_compat_ioctl(struct file *file, unsigned int cmd, diff --git a/fs/fuse/inode.c b/fs/fuse/inode.c index 444418e240c8..79a31cb55512 100644 --- a/fs/fuse/inode.c +++ b/fs/fuse/inode.c @@ -1464,7 +1464,13 @@ static int fuse_fill_super_submount(struct super_blo= ck *sb, struct fuse_mount *fm =3D get_fuse_mount_super(sb); struct super_block *parent_sb =3D parent_fi->inode.i_sb; struct fuse_attr root_attr; + struct fuse_inode *fi; struct inode *root; + struct inode *parent; + struct dentry *pdent; + struct fuse_entry_out outarg; + bool lookedup =3D false; + int ret; =20 fuse_sb_defaults(sb); fm->sb =3D sb; @@ -1480,14 +1486,39 @@ static int fuse_fill_super_submount(struct super_bl= ock *sb, if (parent_sb->s_subtype && !sb->s_subtype) return -ENOMEM; =20 - fuse_fill_attr_from_inode(&root_attr, parent_fi); - root =3D fuse_iget(sb, parent_fi->nodeid, 0, &root_attr, 0, 0); /* - * This inode is just a duplicate, so it is not looked up and - * its nlookup should not be incremented. fuse_iget() does - * that, though, so undo it here. + * It is necessary to lookup the parent_if->nodeid in case the dentry + * that triggered the automount of the submount is later evicted. + * If this dentry is evicted without the lookup count getting increased + * on the submount root, then the server can subsequently forget this + * nodeid which leads to errors when trying to access the root of the + * submount. */ - get_fuse_inode(root)->nlookup--; + parent =3D &parent_fi->inode; + pdent =3D d_find_alias(parent); + if (!pdent) + return -EINVAL; + + ret =3D fuse_dentry_revalidate_lookup(fm, pdent, parent, &outarg, + &lookedup); + dput(pdent); + /* + * The new root owns this nlookup on success, and it is incremented by + * fuse_iget(). In the case the lookup succeeded but revalidate fails, + * ensure that the lookup count is tracked by the parent. + */ + if (ret <=3D 0) { + if (lookedup) { + fi =3D get_fuse_inode(parent); + spin_lock(&fi->lock); + fi->nlookup++; + spin_unlock(&fi->lock); + } + return ret ? ret : -EINVAL; + } + + fuse_fill_attr_from_inode(&root_attr, parent_fi); + root =3D fuse_iget(sb, parent_fi->nodeid, 0, &root_attr, 0, 0); sb->s_d_op =3D &fuse_dentry_operations; sb->s_root =3D d_make_root(root); if (!sb->s_root) --=20 2.25.1