Messages in this thread Patch in this message | | | From | Greg Kroah-Hartman <> | Subject | [PATCH 5.10 01/79] NFSD: Fix verifier returned in stable WRITEs | Date | Tue, 13 Sep 2022 16:04:06 +0200 |
| |
From: Chuck Lever <chuck.lever@oracle.com>
commit f11ad7aa653130b71e2e89bed207f387718216d5 upstream.
RFC 8881 explains the purpose of the write verifier this way:
> The final portion of the result is the field writeverf. This field > is the write verifier and is a cookie that the client can use to > determine whether a server has changed instance state (e.g., server > restart) between a call to WRITE and a subsequent call to either > WRITE or COMMIT.
But then it says:
> This cookie MUST be unchanged during a single instance of the > NFSv4.1 server and MUST be unique between instances of the NFSv4.1 > server. If the cookie changes, then the client MUST assume that > any data written with an UNSTABLE4 value for committed and an old > writeverf in the reply has been lost and will need to be > recovered.
RFC 1813 has similar language for NFSv3. NFSv2 does not have a write verifier since it doesn't implement the COMMIT procedure.
Since commit 19e0663ff9bc ("nfsd: Ensure sampling of the write verifier is atomic with the write"), the Linux NFS server has returned a boot-time-based verifier for UNSTABLE WRITEs, but a zero verifier for FILE_SYNC and DATA_SYNC WRITEs. FILE_SYNC and DATA_SYNC WRITEs are not followed up with a COMMIT, so there's no need for clients to compare verifiers for stable writes.
However, by returning a different verifier for stable and unstable writes, the above commit puts the Linux NFS server a step farther out of compliance with the first MUST above. At least one NFS client (FreeBSD) noticed the difference, making this a potential regression.
[Removed down_write to fix the conflict in the cherry-pick. The down_write functionality was no longer needed there. Upstream commit 555dbf1a9aac6d3150c8b52fa35f768a692f4eeb titled nfsd: Replace use of rwsem with errseq_t removed those and replace it with new functionality that was more scalable. This commit is already backported onto 5.10 and so removing down_write ensures consistency with that change. Tested by compiling and booting successfully. - kochera]
Reported-by: Rick Macklem <rmacklem@uoguelph.ca> Link: https://lore.kernel.org/linux-nfs/YQXPR0101MB096857EEACF04A6DF1FC6D9BDD749@YQXPR0101MB0968.CANPRD01.PROD.OUTLOOK.COM/T/ Fixes: 19e0663ff9bc ("nfsd: Ensure sampling of the write verifier is atomic with the write") Signed-off-by: Chuck Lever <chuck.lever@oracle.com> Signed-off-by: Michael Kochera <kochera@google.com> Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org> --- fs/nfsd/vfs.c | 4 ++++ 1 file changed, 4 insertions(+)
--- a/fs/nfsd/vfs.c +++ b/fs/nfsd/vfs.c @@ -1014,6 +1014,10 @@ nfsd_vfs_write(struct svc_rqst *rqstp, s iov_iter_kvec(&iter, WRITE, vec, vlen, *cnt); since = READ_ONCE(file->f_wb_err); if (flags & RWF_SYNC) { + if (verf) + nfsd_copy_boot_verifier(verf, + net_generic(SVC_NET(rqstp), + nfsd_net_id)); host_err = vfs_iter_write(file, &iter, &pos, flags); if (host_err < 0) nfsd_reset_boot_verifier(net_generic(SVC_NET(rqstp),
| |