From patchwork Fri Jul 21 14:29:10 2023 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Jeff Layton X-Patchwork-Id: 123907 Return-Path: Delivered-To: ouuuleilei@gmail.com Received: by 2002:a59:9010:0:b0:3e4:2afc:c1 with SMTP id l16csp254934vqg; Fri, 21 Jul 2023 07:45:01 -0700 (PDT) X-Google-Smtp-Source: APBJJlG418Ec9hh0DhHE8ExKhTHCBe72qa8YISWiPjvHlUXh4b7lCYL5OiuXKQErOnmBjr2rHSJz X-Received: by 2002:a17:906:5393:b0:99b:4956:e4df with SMTP id g19-20020a170906539300b0099b4956e4dfmr1807668ejo.11.1689950701479; Fri, 21 Jul 2023 07:45:01 -0700 (PDT) ARC-Seal: i=1; a=rsa-sha256; t=1689950701; cv=none; d=google.com; s=arc-20160816; b=gcnb0h0lMRfiPL4EUE+A1tEj7tYjcFiVlg9WiUAaYd2uJMmnERlV4fMfKtG8OrAvjk jYiOSAMOh/R0RZQkRnG/L1cVd4/b+HMh8d7SvjEowenyezOKQE3ooQPEpFSlawa5I5AD qs4Ge/zug5IUCpiUx9p5NvAXm4IrT+w21uJ7KeX5mCRGz/txylLCk1/Zz6scK4KgVFoy bOOpvHcomER53i1Gv6XXyhQN+x9kb5AKMOZOtQ/ukplMPi/5nS67aDA7qcIMwVDhbomo PlhxpLKneXlKSfdR9z/UFLYp7pa/l4uU3orR5SewQ24oDOQMmiLbA9GtlPQL9AkY9LEW GKnw== ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=google.com; s=arc-20160816; h=list-id:precedence:cc:to:in-reply-to:references:message-id :content-transfer-encoding:mime-version:subject:date:from :dkim-signature; bh=Kxd5lJqpwOhO+RiZO82oiyuNYIYChGnzxqv/dfX++H4=; fh=7kqWyKiIQpgkLC2sS92h74MY/UjqV8MeZaswkbSb4vE=; b=WyY2JpMOtRETkb2aWVuhkRpGpDvWwLKlaWJ6MvFN16YMhGOX/LlJQqCEE9rEbt1HDf +xO5wlrJJNDnvfymN1TLcmTXtVM4KKT16Xkce4e5XU9XMXBT5TmJTdWZoOY1kv377g1c J4VrS4g2bCc9EyGmFxYYu3PdliG59SbApqisOEY5yPPGI74MgfKRHDR0rKXqFUh6ay5b O/Mj8l9/wiEFiVe8ndQbq9Ysjr7xbERWH1uYEGKa/xylEJTusRtaKPOXW1uw2EJc6JcR 4BRQ5Ty44yPhB3hJptSqgM2+KL7GvcpbQp8+ThN+bUa5cWAV/WMbbPfXaXubEvH5YSaH q+xg== ARC-Authentication-Results: i=1; mx.google.com; dkim=pass header.i=@kernel.org header.s=k20201202 header.b=bHbybRe6; spf=pass (google.com: domain of linux-kernel-owner@vger.kernel.org designates 2620:137:e000::1:20 as permitted sender) smtp.mailfrom=linux-kernel-owner@vger.kernel.org; dmarc=pass (p=NONE sp=NONE dis=NONE) header.from=kernel.org Received: from out1.vger.email (out1.vger.email. [2620:137:e000::1:20]) by mx.google.com with ESMTP id m22-20020a17090607d600b009930f844671si2177359ejc.963.2023.07.21.07.44.35; Fri, 21 Jul 2023 07:45:01 -0700 (PDT) Received-SPF: pass (google.com: domain of linux-kernel-owner@vger.kernel.org designates 2620:137:e000::1:20 as permitted sender) client-ip=2620:137:e000::1:20; Authentication-Results: mx.google.com; dkim=pass header.i=@kernel.org header.s=k20201202 header.b=bHbybRe6; spf=pass (google.com: domain of linux-kernel-owner@vger.kernel.org designates 2620:137:e000::1:20 as permitted sender) smtp.mailfrom=linux-kernel-owner@vger.kernel.org; dmarc=pass (p=NONE sp=NONE dis=NONE) header.from=kernel.org Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S231205AbjGUO3X (ORCPT + 99 others); Fri, 21 Jul 2023 10:29:23 -0400 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:48844 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S229983AbjGUO3U (ORCPT ); Fri, 21 Jul 2023 10:29:20 -0400 Received: from dfw.source.kernel.org (dfw.source.kernel.org [IPv6:2604:1380:4641:c500::1]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id 8605D1710; Fri, 21 Jul 2023 07:29:18 -0700 (PDT) Received: from smtp.kernel.org (relay.kernel.org [52.25.139.140]) (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits) key-exchange X25519 server-signature RSA-PSS (2048 bits)) (No client certificate requested) by dfw.source.kernel.org (Postfix) with ESMTPS id 0E39061CD7; Fri, 21 Jul 2023 14:29:18 +0000 (UTC) Received: by smtp.kernel.org (Postfix) with ESMTPSA id C72D8C433CC; Fri, 21 Jul 2023 14:29:16 +0000 (UTC) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=kernel.org; s=k20201202; t=1689949757; bh=5SbzInu0+29GFH19NM+oP1Yogx/hKJ4534iz9eAGDYA=; h=From:Date:Subject:References:In-Reply-To:To:Cc:From; b=bHbybRe61212Gj5/TlQJCNabAiP2uR6LIJiPCMNpk1PCk3afur9G5t41bNmh/ncpm slvDrzAimmVtIU/9sFuARZIZW1WvenCzCmPAZeK7rCLqT9ATzQkaCQCRcRqciejErg KrBjOiHDqBXSYARB6CLxRM1/pj6M7gm/TxKJ5kbdjjHfyXXeb9Sty/ARfeObdmee4N iLNkXouYK/EpnoyB2keEHvn2GuQAHsdMPwNNWluTlkmaWhdy755xBfQZHzXleWfTe5 T88JdsOKo+Kej4C49jH+dH5INcTIPg4vFOhouk2D3urpaqjf73xNinD9EGkujeYY49 3yiO1PZmGIwAQ== From: Jeff Layton Date: Fri, 21 Jul 2023 10:29:10 -0400 Subject: [PATCH v3 1/2] nfsd: handle failure to collect pre/post-op attrs more sanely MIME-Version: 1.0 Message-Id: <20230721-bz2223560-v3-1-bb57e302bab7@kernel.org> References: <20230721-bz2223560-v3-0-bb57e302bab7@kernel.org> In-Reply-To: <20230721-bz2223560-v3-0-bb57e302bab7@kernel.org> To: Chuck Lever , Neil Brown , Olga Kornievskaia , Dai Ngo , Tom Talpey Cc: linux-nfs@vger.kernel.org, linux-kernel@vger.kernel.org, Jeff Layton X-Mailer: b4 0.12.3 X-Developer-Signature: v=1; a=openpgp-sha256; l=9361; i=jlayton@kernel.org; h=from:subject:message-id; bh=5SbzInu0+29GFH19NM+oP1Yogx/hKJ4534iz9eAGDYA=; b=owEBbQKS/ZANAwAIAQAOaEEZVoIVAcsmYgBkupY7tVRBUGGiYjkpRHQTU2Lvs9imE54TdVjet 8qil8YGZgKJAjMEAAEIAB0WIQRLwNeyRHGyoYTq9dMADmhBGVaCFQUCZLqWOwAKCRAADmhBGVaC FUV5D/oCmFXjHpuHUJy7AoNc0FcmyQ+tvwh+HKWfP7a2lNypx3CNGadPTgxkc1th/Kims+x+nuX F1vhgFauq7xKFpE+qgKkreyNd2b2z3ZSO7mFHgWoytswqkpzyMWkjA7+XqtLhp5ItKr3SYW6iC6 X6JP6CU8FmISSg0NYMe5azT8n4woRcMXQkBl6Qc3g4MzJP+Gdfzq58WST/Z/glLcCOMvdAYabkG 50HzG9rMNmOgJL3QFxPFsXJz9pIlf2Ses+/gb4mzNx/lTNyojJ4K3Wuton5x8unFgFo6x+/rlj2 aow+iNc6LDo/vvt/d4Nf3lhrWhExT5z7jnFEQEZbW0v3dMCsigxXyJnz3YbViY7+cd4yj+fGf3p BhJqnvN9oDn0inH7VDQCRcKql3YtPczrFBCsiEKwzq6DJ+22wWRnwYm8ABnDVQtdniJBfZ/2z0y K4boztYBZzJrPKT7tHBsQDVZbu7TXW6oj5ULnC8e1ZHyq7ZbXuXywAYabCAxlX/GO8S4nJNuH7O PGkIGAcB7E3JBJHYlhDio5nttSHo1eCsto6ncxJFMMpQOqNKD8DlP0R/PHX7hk1g7Xt7ONtOvLf y9QTeDw1k9y7Uy+UADx9nPYkhQ+CN2uIpo8/LchbFUpBHcIyPYGpvIDdoT8LONPROWCHNQfN6xu rNlwUNG80S744zg== X-Developer-Key: i=jlayton@kernel.org; a=openpgp; fpr=4BC0D7B24471B2A184EAF5D3000E684119568215 X-Spam-Status: No, score=-2.1 required=5.0 tests=BAYES_00,DKIMWL_WL_HIGH, DKIM_SIGNED,DKIM_VALID,DKIM_VALID_AU,DKIM_VALID_EF, RCVD_IN_DNSWL_BLOCKED,SPF_HELO_NONE,SPF_PASS,T_SCC_BODY_TEXT_LINE autolearn=ham autolearn_force=no version=3.4.6 X-Spam-Checker-Version: SpamAssassin 3.4.6 (2021-04-09) on lindbergh.monkeyblade.net Precedence: bulk List-ID: X-Mailing-List: linux-kernel@vger.kernel.org X-getmail-retrieved-from-mailbox: INBOX X-GMAIL-THRID: 1772041746751785453 X-GMAIL-MSGID: 1772041746751785453 Collecting pre_op_attrs can fail, in which case it's probably best to fail the whole operation. Change fh_fill_pre_attrs and fh_fill_both_attrs to return __be32, and have the callers check the return code and abort the operation if it's not nfs_ok. Signed-off-by: Jeff Layton --- fs/nfsd/nfs3proc.c | 4 +++- fs/nfsd/nfs4proc.c | 14 ++++++++------ fs/nfsd/nfsfh.c | 26 ++++++++++++++++---------- fs/nfsd/nfsfh.h | 6 +++--- fs/nfsd/vfs.c | 52 +++++++++++++++++++++++++++++++++++----------------- 5 files changed, 65 insertions(+), 37 deletions(-) diff --git a/fs/nfsd/nfs3proc.c b/fs/nfsd/nfs3proc.c index fc8d5b7db9f8..268ef57751c4 100644 --- a/fs/nfsd/nfs3proc.c +++ b/fs/nfsd/nfs3proc.c @@ -307,7 +307,9 @@ nfsd3_create_file(struct svc_rqst *rqstp, struct svc_fh *fhp, if (!IS_POSIXACL(inode)) iap->ia_mode &= ~current_umask(); - fh_fill_pre_attrs(fhp); + status = fh_fill_pre_attrs(fhp); + if (status != nfs_ok) + goto out; host_err = vfs_create(&nop_mnt_idmap, inode, child, iap->ia_mode, true); if (host_err < 0) { status = nfserrno(host_err); diff --git a/fs/nfsd/nfs4proc.c b/fs/nfsd/nfs4proc.c index d8e7a533f9d2..9285e1eab4d5 100644 --- a/fs/nfsd/nfs4proc.c +++ b/fs/nfsd/nfs4proc.c @@ -297,12 +297,12 @@ nfsd4_create_file(struct svc_rqst *rqstp, struct svc_fh *fhp, } if (d_really_is_positive(child)) { - status = nfs_ok; - /* NFSv4 protocol requires change attributes even though * no change happened. */ - fh_fill_both_attrs(fhp); + status = fh_fill_both_attrs(fhp); + if (status != nfs_ok) + goto out; switch (open->op_createmode) { case NFS4_CREATE_UNCHECKED: @@ -345,7 +345,9 @@ nfsd4_create_file(struct svc_rqst *rqstp, struct svc_fh *fhp, if (!IS_POSIXACL(inode)) iap->ia_mode &= ~current_umask(); - fh_fill_pre_attrs(fhp); + status = fh_fill_pre_attrs(fhp); + if (status != nfs_ok) + goto out; status = nfsd4_vfs_create(fhp, child, open); if (status != nfs_ok) goto out; @@ -424,11 +426,11 @@ do_open_lookup(struct svc_rqst *rqstp, struct nfsd4_compound_state *cstate, stru } else { status = nfsd_lookup(rqstp, current_fh, open->op_fname, open->op_fnamelen, *resfh); - if (!status) + if (status == nfs_ok) /* NFSv4 protocol requires change attributes even though * no change happened. */ - fh_fill_both_attrs(current_fh); + status = fh_fill_both_attrs(current_fh); } if (status) goto out; diff --git a/fs/nfsd/nfsfh.c b/fs/nfsd/nfsfh.c index c291389a1d71..355bf0db3235 100644 --- a/fs/nfsd/nfsfh.c +++ b/fs/nfsd/nfsfh.c @@ -614,7 +614,7 @@ fh_update(struct svc_fh *fhp) * @fhp: file handle to be updated * */ -void fh_fill_pre_attrs(struct svc_fh *fhp) +__be32 __must_check fh_fill_pre_attrs(struct svc_fh *fhp) { bool v4 = (fhp->fh_maxsize == NFS4_FHSIZE); struct inode *inode; @@ -622,12 +622,12 @@ void fh_fill_pre_attrs(struct svc_fh *fhp) __be32 err; if (fhp->fh_no_wcc || fhp->fh_pre_saved) - return; + return nfs_ok; inode = d_inode(fhp->fh_dentry); err = fh_getattr(fhp, &stat); if (err) - return; + return err; if (v4) fhp->fh_pre_change = nfsd4_change_attribute(&stat, inode); @@ -636,6 +636,7 @@ void fh_fill_pre_attrs(struct svc_fh *fhp) fhp->fh_pre_ctime = stat.ctime; fhp->fh_pre_size = stat.size; fhp->fh_pre_saved = true; + return nfs_ok; } /** @@ -643,26 +644,27 @@ void fh_fill_pre_attrs(struct svc_fh *fhp) * @fhp: file handle to be updated * */ -void fh_fill_post_attrs(struct svc_fh *fhp) +__be32 fh_fill_post_attrs(struct svc_fh *fhp) { bool v4 = (fhp->fh_maxsize == NFS4_FHSIZE); struct inode *inode = d_inode(fhp->fh_dentry); __be32 err; if (fhp->fh_no_wcc) - return; + return nfs_ok; if (fhp->fh_post_saved) printk("nfsd: inode locked twice during operation.\n"); err = fh_getattr(fhp, &fhp->fh_post_attr); if (err) - return; + return err; fhp->fh_post_saved = true; if (v4) fhp->fh_post_change = nfsd4_change_attribute(&fhp->fh_post_attr, inode); + return nfs_ok; } /** @@ -672,16 +674,20 @@ void fh_fill_post_attrs(struct svc_fh *fhp) * This is used when the directory wasn't changed, but wcc attributes * are needed anyway. */ -void fh_fill_both_attrs(struct svc_fh *fhp) +__be32 __must_check fh_fill_both_attrs(struct svc_fh *fhp) { - fh_fill_post_attrs(fhp); - if (!fhp->fh_post_saved) - return; + __be32 err; + + err = fh_fill_post_attrs(fhp); + if (err) + return err; + fhp->fh_pre_change = fhp->fh_post_change; fhp->fh_pre_mtime = fhp->fh_post_attr.mtime; fhp->fh_pre_ctime = fhp->fh_post_attr.ctime; fhp->fh_pre_size = fhp->fh_post_attr.size; fhp->fh_pre_saved = true; + return nfs_ok; } /* diff --git a/fs/nfsd/nfsfh.h b/fs/nfsd/nfsfh.h index 4e0ecf0ae2cf..40426f899e76 100644 --- a/fs/nfsd/nfsfh.h +++ b/fs/nfsd/nfsfh.h @@ -294,7 +294,7 @@ static inline void fh_clear_pre_post_attrs(struct svc_fh *fhp) } u64 nfsd4_change_attribute(struct kstat *stat, struct inode *inode); -extern void fh_fill_pre_attrs(struct svc_fh *fhp); -extern void fh_fill_post_attrs(struct svc_fh *fhp); -extern void fh_fill_both_attrs(struct svc_fh *fhp); +__be32 __must_check fh_fill_pre_attrs(struct svc_fh *fhp); +__be32 fh_fill_post_attrs(struct svc_fh *fhp); +__be32 __must_check fh_fill_both_attrs(struct svc_fh *fhp); #endif /* _LINUX_NFSD_NFSFH_H */ diff --git a/fs/nfsd/vfs.c b/fs/nfsd/vfs.c index 8a2321d19194..0389c91c52fa 100644 --- a/fs/nfsd/vfs.c +++ b/fs/nfsd/vfs.c @@ -1537,7 +1537,9 @@ nfsd_create(struct svc_rqst *rqstp, struct svc_fh *fhp, dput(dchild); if (err) goto out_unlock; - fh_fill_pre_attrs(fhp); + err = fh_fill_pre_attrs(fhp); + if (err != nfs_ok) + goto out_unlock; err = nfsd_create_locked(rqstp, fhp, attrs, type, rdev, resfhp); fh_fill_post_attrs(fhp); out_unlock: @@ -1632,13 +1634,16 @@ nfsd_symlink(struct svc_rqst *rqstp, struct svc_fh *fhp, inode_unlock(dentry->d_inode); goto out_drop_write; } - fh_fill_pre_attrs(fhp); + err = fh_fill_pre_attrs(fhp); + if (err != nfs_ok) + goto out_unlock; host_err = vfs_symlink(&nop_mnt_idmap, d_inode(dentry), dnew, path); err = nfserrno(host_err); cerr = fh_compose(resfhp, fhp->fh_export, dnew, fhp); if (!err) nfsd_create_setattr(rqstp, fhp, resfhp, attrs); fh_fill_post_attrs(fhp); +out_unlock: inode_unlock(dentry->d_inode); if (!err) err = nfserrno(commit_metadata(fhp)); @@ -1700,7 +1705,9 @@ nfsd_link(struct svc_rqst *rqstp, struct svc_fh *ffhp, err = nfserr_noent; if (d_really_is_negative(dold)) goto out_dput; - fh_fill_pre_attrs(ffhp); + err = fh_fill_pre_attrs(ffhp); + if (err != nfs_ok) + goto out_dput; host_err = vfs_link(dold, &nop_mnt_idmap, dirp, dnew, NULL); fh_fill_post_attrs(ffhp); inode_unlock(dirp); @@ -1786,8 +1793,12 @@ nfsd_rename(struct svc_rqst *rqstp, struct svc_fh *ffhp, char *fname, int flen, } trap = lock_rename(tdentry, fdentry); - fh_fill_pre_attrs(ffhp); - fh_fill_pre_attrs(tfhp); + err = fh_fill_pre_attrs(ffhp); + if (err != nfs_ok) + goto out_unlock; + err = fh_fill_pre_attrs(tfhp); + if (err != nfs_ok) + goto out_unlock; odentry = lookup_one_len(fname, fdentry, flen); host_err = PTR_ERR(odentry); @@ -1854,6 +1865,7 @@ nfsd_rename(struct svc_rqst *rqstp, struct svc_fh *ffhp, char *fname, int flen, fh_fill_post_attrs(ffhp); fh_fill_post_attrs(tfhp); } +out_unlock: unlock_rename(tdentry, fdentry); fh_drop_write(ffhp); @@ -1913,12 +1925,14 @@ nfsd_unlink(struct svc_rqst *rqstp, struct svc_fh *fhp, int type, goto out_unlock; } rinode = d_inode(rdentry); - ihold(rinode); + err = fh_fill_pre_attrs(fhp); + if (err != nfs_ok) + goto out_unlock; + ihold(rinode); if (!type) type = d_inode(rdentry)->i_mode & S_IFMT; - fh_fill_pre_attrs(fhp); if (type != S_IFDIR) { int retries; @@ -2338,16 +2352,18 @@ nfsd_removexattr(struct svc_rqst *rqstp, struct svc_fh *fhp, char *name) return nfserrno(ret); inode_lock(fhp->fh_dentry->d_inode); - fh_fill_pre_attrs(fhp); - + err = fh_fill_pre_attrs(fhp); + if (err != nfs_ok) + goto out_unlock; ret = __vfs_removexattr_locked(&nop_mnt_idmap, fhp->fh_dentry, name, NULL); - + err = nfsd_xattr_errno(ret); fh_fill_post_attrs(fhp); +out_unlock: inode_unlock(fhp->fh_dentry->d_inode); fh_drop_write(fhp); - return nfsd_xattr_errno(ret); + return err; } __be32 @@ -2365,15 +2381,17 @@ nfsd_setxattr(struct svc_rqst *rqstp, struct svc_fh *fhp, char *name, if (ret) return nfserrno(ret); inode_lock(fhp->fh_dentry->d_inode); - fh_fill_pre_attrs(fhp); - - ret = __vfs_setxattr_locked(&nop_mnt_idmap, fhp->fh_dentry, name, buf, - len, flags, NULL); + err = fh_fill_pre_attrs(fhp); + if (err != nfs_ok) + goto out_unlock; + ret = __vfs_setxattr_locked(&nop_mnt_idmap, fhp->fh_dentry, + name, buf, len, flags, NULL); fh_fill_post_attrs(fhp); + err = nfsd_xattr_errno(ret); +out_unlock: inode_unlock(fhp->fh_dentry->d_inode); fh_drop_write(fhp); - - return nfsd_xattr_errno(ret); + return err; } #endif From patchwork Fri Jul 21 14:29:11 2023 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Jeff Layton X-Patchwork-Id: 123906 Return-Path: Delivered-To: ouuuleilei@gmail.com Received: by 2002:a59:9010:0:b0:3e4:2afc:c1 with SMTP id l16csp254308vqg; Fri, 21 Jul 2023 07:43:57 -0700 (PDT) X-Google-Smtp-Source: APBJJlGwuZ3QXi2jRLf8QT0675Qr55wH2kUuOMRo9QVnFHQYXZzAQb1TQR0PrXE6xS6atHzAoHh6 X-Received: by 2002:a17:903:1205:b0:1bb:3a7:6af7 with SMTP id l5-20020a170903120500b001bb03a76af7mr2103945plh.23.1689950637539; Fri, 21 Jul 2023 07:43:57 -0700 (PDT) ARC-Seal: i=1; a=rsa-sha256; t=1689950637; cv=none; d=google.com; s=arc-20160816; b=D9VR4mzbDL8NZqskaYvqwFSlT44riQXNks14wgE6zWvoi/98fe8lq+bG1cDl29wJnB 9dRwWnQThXR8tUOxTc97lOUyxed+VKCD/brkvyJIQVb7uAa5tJ4CcRjuF8m6+24EIRq/ 61krGTTD7wI2cuwWFHB78bHOUZFxsLO3No072DDV/3LuNDVhHMZlp/KatqmwvKQg2To3 3LpBZLYmbf1ptAmmGk7VJoKMHdnEj5b02q7ygfIHGgkIIZ/VLMUPBzfUxgRYBOZIOprd eFFjwhhhNu0UcRb/Y06strmmjEloCJDx4wqxC5rkiIIDdaKF0dx/gkYS9uzwF1IyDz2G u5fg== ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=google.com; s=arc-20160816; h=list-id:precedence:cc:to:in-reply-to:references:message-id :content-transfer-encoding:mime-version:subject:date:from :dkim-signature; bh=aVBkP7hIWFlk2UFsm19L/CM299CztzNEryHukW6yEKQ=; fh=+d9EA0ASG1ukkd7H8IyPKHx6rAxJS58s7dr6FWKuwS8=; b=BpwdGGoDGd/BQztbAJ6F+ycExe9Do+HTfJbKtz2MbVO55VbCE5bjSyE0xRi4XMh6PM WFdiNnQwxnpFe2YfFKltKQu9huhTbAYFAxcrKUi2OCXByf36xgQeHzbks/UO9RkgMNYi b/mep4NH5rj3q0Ka1K5PfahDU5pqNIVTxD2bKlXOKUsXXFuqwzFqbGtQHVKhENAwsZjm G/OMo6IqZKMnDnT4Q0q2DWH6TCGBgLXm2O2vBroyMLE5rVG1cc9rJ3r2J1JJZypyGwLM jhP6Ki5s1AeMc5GmIazCgXGIQmTDNfn2O09vNpk61xrmeDAGbE11ub8FhZqWaWskOo0D HUqQ== ARC-Authentication-Results: i=1; mx.google.com; dkim=pass header.i=@kernel.org header.s=k20201202 header.b=eM1PESOg; spf=pass (google.com: domain of linux-kernel-owner@vger.kernel.org designates 2620:137:e000::1:20 as permitted sender) smtp.mailfrom=linux-kernel-owner@vger.kernel.org; dmarc=pass (p=NONE sp=NONE dis=NONE) header.from=kernel.org Received: from out1.vger.email (out1.vger.email. [2620:137:e000::1:20]) by mx.google.com with ESMTP id le13-20020a170902fb0d00b001b7eb771d5esi2941877plb.527.2023.07.21.07.43.43; Fri, 21 Jul 2023 07:43:57 -0700 (PDT) Received-SPF: pass (google.com: domain of linux-kernel-owner@vger.kernel.org designates 2620:137:e000::1:20 as permitted sender) client-ip=2620:137:e000::1:20; Authentication-Results: mx.google.com; dkim=pass header.i=@kernel.org header.s=k20201202 header.b=eM1PESOg; spf=pass (google.com: domain of linux-kernel-owner@vger.kernel.org designates 2620:137:e000::1:20 as permitted sender) smtp.mailfrom=linux-kernel-owner@vger.kernel.org; dmarc=pass (p=NONE sp=NONE dis=NONE) header.from=kernel.org Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S229805AbjGUO31 (ORCPT + 99 others); Fri, 21 Jul 2023 10:29:27 -0400 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:48846 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S230201AbjGUO3U (ORCPT ); Fri, 21 Jul 2023 10:29:20 -0400 Received: from dfw.source.kernel.org (dfw.source.kernel.org [IPv6:2604:1380:4641:c500::1]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id 7CC61E68; Fri, 21 Jul 2023 07:29:19 -0700 (PDT) Received: from smtp.kernel.org (relay.kernel.org [52.25.139.140]) (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits) key-exchange X25519 server-signature RSA-PSS (2048 bits)) (No client certificate requested) by dfw.source.kernel.org (Postfix) with ESMTPS id 103B161CDE; Fri, 21 Jul 2023 14:29:19 +0000 (UTC) Received: by smtp.kernel.org (Postfix) with ESMTPSA id B311BC433C7; Fri, 21 Jul 2023 14:29:17 +0000 (UTC) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=kernel.org; s=k20201202; t=1689949758; bh=n5CM7X3lN74+RyydF842JksyHcy3Wi22/2HsBm0XHug=; h=From:Date:Subject:References:In-Reply-To:To:Cc:From; b=eM1PESOg5xMGMQaVB7l97rvozA/NGL2jli8sDbORbMwaqJIc6jMzUKBHHQx1EtFo6 hQYvt5GWeXmG30IRgrSon1Sm6paEtGn+f6yXdEFm94zvOATHfyXgCjhLbWQQxBE9jX 37O+FAD8F7ki2cs7Rr8q7O+YIFkp70M+hTt20XPf8frZWCl7C9a9Ykey18y3adYpH8 jiD9Dy1UtpZgCgOUTqKI5HfoKtXdA40K8vlfzE6pGqMiaOb/7/U+5GvaaNfaqyfBzA cUVAv2zhkS2B/6AYbgwaa4nrAPJlw0cN4/pye1F54VZyglzxOP/PPhtlG8AKWrPZk0 br8pnq5BTD5uw== From: Jeff Layton Date: Fri, 21 Jul 2023 10:29:11 -0400 Subject: [PATCH v3 2/2] nfsd: remove unsafe BUG_ON from set_change_info MIME-Version: 1.0 Message-Id: <20230721-bz2223560-v3-2-bb57e302bab7@kernel.org> References: <20230721-bz2223560-v3-0-bb57e302bab7@kernel.org> In-Reply-To: <20230721-bz2223560-v3-0-bb57e302bab7@kernel.org> To: Chuck Lever , Neil Brown , Olga Kornievskaia , Dai Ngo , Tom Talpey Cc: linux-nfs@vger.kernel.org, linux-kernel@vger.kernel.org, Jeff Layton , Boyang Xue X-Mailer: b4 0.12.3 X-Developer-Signature: v=1; a=openpgp-sha256; l=3480; i=jlayton@kernel.org; h=from:subject:message-id; bh=n5CM7X3lN74+RyydF842JksyHcy3Wi22/2HsBm0XHug=; b=owEBbQKS/ZANAwAIAQAOaEEZVoIVAcsmYgBkupY7P/EQhQx0cLkz0dwczVoxvUEnc6+CSgZzW j0jrAvv4kqJAjMEAAEIAB0WIQRLwNeyRHGyoYTq9dMADmhBGVaCFQUCZLqWOwAKCRAADmhBGVaC FUOGD/9WfQyqmzYlBzNM3CcAxjJYoeQATI72bqz1Ro3NcJ5P+eoaNx+m6LMcI6NTk6xekuBTxKX TdOQ5smFiBBfDYSDYom7MJyH8qGTzDmR6EeuiW0xTBTHvfLd4CjHDpjgWtDHHjCwPs8OrJ7bJzu 27Yo7rfyEleWB8/utCZWiYoXMpqH04ndieR5A5WUWOCxUuQ1SXOTSdYCXpUuUGGX/JKB+fEAgYs 26g3mgxSP3T8UbDy9ykAarejEZGjqTjUshvUCY4cpvYqkN6Bsn2TQE9UM8mDsS3KibXtQ8pJHPF loL64gwt+CkbUJoUVbkuh2YpKCHbxvFBoeTOre3K66x6SkfpcYFDUlxzLrScoeMnvaF+PhZiP5q s8eyGupKvZNHOlqwlAEs/sVZchc7vAkwAPRdjofl78+s+S45LupZLUO5+t//fMjJqG28ldAtkd6 KSIVkIzmzqjyq/t8yPLJfW2WXOBcsd05gklfTsyufDYua4vrpBFaVNiBjThjvGj+2sVMMCqE6L8 ufnyA1PgCaeckHttJyTUMaMWSc7ami+h31JRyFfDpjgADX9K3FM4in5hTxk116MJVFO8v0fOwJd 5MVQJhpcZV1+Fsi9LemvWr7K8D4KuhhEKPxgMv9fgdsN+IO5DY7S2QF6uxB0pZhIKypCCQjdL9E eqTHmjMjfVY8YRA== X-Developer-Key: i=jlayton@kernel.org; a=openpgp; fpr=4BC0D7B24471B2A184EAF5D3000E684119568215 X-Spam-Status: No, score=-2.1 required=5.0 tests=BAYES_00,DKIMWL_WL_HIGH, DKIM_SIGNED,DKIM_VALID,DKIM_VALID_AU,DKIM_VALID_EF, RCVD_IN_DNSWL_BLOCKED,SPF_HELO_NONE,SPF_PASS,T_SCC_BODY_TEXT_LINE autolearn=ham autolearn_force=no version=3.4.6 X-Spam-Checker-Version: SpamAssassin 3.4.6 (2021-04-09) on lindbergh.monkeyblade.net Precedence: bulk List-ID: X-Mailing-List: linux-kernel@vger.kernel.org X-getmail-retrieved-from-mailbox: INBOX X-GMAIL-THRID: 1772041679281893634 X-GMAIL-MSGID: 1772041679281893634 At one time, nfsd would scrape inode information directly out of struct inode in order to populate the change_info4. At that time, the BUG_ON in set_change_info made some sense, since having it unset meant a coding error. More recently, it calls vfs_getattr to get this information, which can fail. If that fails, fh_pre_saved can end up not being set. While this situation is unfortunate, we don't need to crash the box. Move set_change_info to nfs4proc.c since all of the callers are there. Revise the condition for setting "atomic" to also check for fh_pre_saved. Drop the BUG_ON and and just have it zero out both change_attr4s when this occurs. Reported-by: Boyang Xue Closes: https://bugzilla.redhat.com/show_bug.cgi?id=2223560 Signed-off-by: Jeff Layton --- fs/nfsd/nfs4proc.c | 32 ++++++++++++++++++++++++++++++++ fs/nfsd/xdr4.h | 11 ----------- 2 files changed, 32 insertions(+), 11 deletions(-) diff --git a/fs/nfsd/nfs4proc.c b/fs/nfsd/nfs4proc.c index 9285e1eab4d5..3f6710c9c5c9 100644 --- a/fs/nfsd/nfs4proc.c +++ b/fs/nfsd/nfs4proc.c @@ -382,6 +382,38 @@ nfsd4_create_file(struct svc_rqst *rqstp, struct svc_fh *fhp, return status; } +/** + * set_change_info - set up the change_info4 for a reply + * @cinfo: pointer to nfsd4_change_info to be populated + * @fhp: pointer to svc_fh to use as source + * + * Many operations in NFSv4 require change_info4 in the reply. This function + * populates that from the info that we (should!) have already collected. In + * the event that we didn't get any pre-attrs, just zero out both. + */ +static void +set_change_info(struct nfsd4_change_info *cinfo, struct svc_fh *fhp) +{ + cinfo->atomic = (u32)(fhp->fh_pre_saved && fhp->fh_post_saved && !fhp->fh_no_atomic_attr); + cinfo->before_change = fhp->fh_pre_change; + cinfo->after_change = fhp->fh_post_change; + + /* + * If fetching the pre-change attributes failed, then we should + * have already failed the whole operation. We could have still + * failed to fetch post-change attributes however. + * + * If we didn't get post-op attrs, just zero-out the after + * field since we don't know what it should be. If the pre_saved + * field isn't set for some reason, throw warning and just copy + * whatever is in the after field. + */ + if (WARN_ON_ONCE(!fhp->fh_pre_saved)) + cinfo->before_change = 0; + if (!fhp->fh_post_saved) + cinfo->after_change = 0; +} + static __be32 do_open_lookup(struct svc_rqst *rqstp, struct nfsd4_compound_state *cstate, struct nfsd4_open *open, struct svc_fh **resfh) { diff --git a/fs/nfsd/xdr4.h b/fs/nfsd/xdr4.h index b2931fdf53be..9e67f63c5f4d 100644 --- a/fs/nfsd/xdr4.h +++ b/fs/nfsd/xdr4.h @@ -775,17 +775,6 @@ void warn_on_nonidempotent_op(struct nfsd4_op *op); #define NFS4_SVC_XDRSIZE sizeof(struct nfsd4_compoundargs) -static inline void -set_change_info(struct nfsd4_change_info *cinfo, struct svc_fh *fhp) -{ - BUG_ON(!fhp->fh_pre_saved); - cinfo->atomic = (u32)(fhp->fh_post_saved && !fhp->fh_no_atomic_attr); - - cinfo->before_change = fhp->fh_pre_change; - cinfo->after_change = fhp->fh_post_change; -} - - bool nfsd4_mach_creds_match(struct nfs4_client *cl, struct svc_rqst *rqstp); bool nfs4svc_decode_compoundargs(struct svc_rqst *rqstp, struct xdr_stream *xdr); bool nfs4svc_encode_compoundres(struct svc_rqst *rqstp, struct xdr_stream *xdr);