git: 5a0050e68a54 - main - nfsserver: Fix handling of SP4_NONE

From: Rick Macklem <rmacklem_at_FreeBSD.org>
Date: Sun, 15 Jan 2023 22:08:38 UTC
The branch main has been updated by rmacklem:

URL: https://cgit.FreeBSD.org/src/commit/?id=5a0050e68a54353af53ac28df90854797ebbef16

commit 5a0050e68a54353af53ac28df90854797ebbef16
Author:     Rick Macklem <rmacklem@FreeBSD.org>
AuthorDate: 2023-01-15 22:07:40 +0000
Commit:     Rick Macklem <rmacklem@FreeBSD.org>
CommitDate: 2023-01-15 22:07:40 +0000

    nfsserver: Fix handling of SP4_NONE
    
    For NFSv4.1/4.2, when the client specifies SP4_NONE for
    state protection in the ExchangeID operation arguments,
    the server MUST allow the state management operations for
    any user credentials.  (I misread the RFC and thought that
    SP4_NONE meant "at the server's discression" and not MUST
    be allowed.)
    
    This means that the "sec=XXX" field of the "V4:" exports(5)
    line only applies to NFSv4.0.
    
    This patch fixes the server to always allow state management
    operations for SP4_NONE, which is the only state management
    option currently supported. (I have patches that add support
    for SP4_MACH_CRED to the server. These will be in a future commit.)
    
    In practice, this bug does not seem to have caused
    interoperability problems.
    
    MFC after:      2 weeks
---
 sys/fs/nfsserver/nfs_nfsdstate.c | 7 ++++++-
 sys/fs/nfsserver/nfs_nfsdsubs.c  | 8 ++++++++
 2 files changed, 14 insertions(+), 1 deletion(-)

diff --git a/sys/fs/nfsserver/nfs_nfsdstate.c b/sys/fs/nfsserver/nfs_nfsdstate.c
index 84da1d9561cd..7430f1f200b3 100644
--- a/sys/fs/nfsserver/nfs_nfsdstate.c
+++ b/sys/fs/nfsserver/nfs_nfsdstate.c
@@ -5867,12 +5867,17 @@ nfsrv_throwawayopens(NFSPROC_T *p)
 
 /*
  * This function checks to see if the credentials are the same.
- * Returns 1 for not same, 0 otherwise.
+ * The check for same credentials is needed for state management operations
+ * for NFSv4.0 where 1 is returned if not same, 0 is returned otherwise.
  */
 static int
 nfsrv_notsamecredname(struct nfsrv_descript *nd, struct nfsclient *clp)
 {
 
+	/* For NFSv4.1/4.2, SP4_NONE always allows this. */
+	if ((nd->nd_flag & ND_NFSV41) != 0)
+		return (0);
+
 	if (nd->nd_flag & ND_GSS) {
 		if (!(clp->lc_flags & LCL_GSS))
 			return (1);
diff --git a/sys/fs/nfsserver/nfs_nfsdsubs.c b/sys/fs/nfsserver/nfs_nfsdsubs.c
index ca691941ed0d..20f62211f53e 100644
--- a/sys/fs/nfsserver/nfs_nfsdsubs.c
+++ b/sys/fs/nfsserver/nfs_nfsdsubs.c
@@ -2121,6 +2121,14 @@ nfsd_checkrootexp(struct nfsrv_descript *nd)
 
 	if (nfs_rootfhset == 0)
 		return (NFSERR_AUTHERR | AUTH_FAILED);
+	/*
+	 * For NFSv4.1/4.2, if the client specifies SP4_NONE, then these
+	 * operations are allowed regardless of the value of the "sec=XXX"
+	 * field in the V4: exports line.
+	 * As such, these Kerberos checks only apply to NFSv4.0 mounts.
+	 */
+	if ((nd->nd_flag & ND_NFSV41) != 0)
+		goto checktls;
 	if ((nd->nd_flag & (ND_GSS | ND_EXAUTHSYS)) == ND_EXAUTHSYS)
 		goto checktls;
 	if ((nd->nd_flag & (ND_GSSINTEGRITY | ND_EXGSSINTEGRITY)) ==