svn commit: r206688 - in head/sys/fs: nfs nfsclient
Rick Macklem
rmacklem at FreeBSD.org
Thu Apr 15 22:57:31 UTC 2010
Author: rmacklem
Date: Thu Apr 15 22:57:30 2010
New Revision: 206688
URL: http://svn.freebsd.org/changeset/base/206688
Log:
The experimental NFS client was not filling in recovery credentials
for opens done locally in the client when a delegation for the file
was held. This could cause the client to crash in crsetgroups() when
recovering from a server crash/reboot. This patch fills in the
recovery credentials for this case, in order to avoid the client crash.
Also, add KASSERT()s to the credential copy functions, to catch any
other cases where the credentials aren't filled in correctly.
MFC after: 1 week
Modified:
head/sys/fs/nfs/nfs_commonport.c
head/sys/fs/nfs/nfsclstate.h
head/sys/fs/nfsclient/nfs_clport.c
head/sys/fs/nfsclient/nfs_clrpcops.c
head/sys/fs/nfsclient/nfs_clstate.c
Modified: head/sys/fs/nfs/nfs_commonport.c
==============================================================================
--- head/sys/fs/nfs/nfs_commonport.c Thu Apr 15 21:41:07 2010 (r206687)
+++ head/sys/fs/nfs/nfs_commonport.c Thu Apr 15 22:57:30 2010 (r206688)
@@ -225,6 +225,8 @@ void
newnfs_copycred(struct nfscred *nfscr, struct ucred *cr)
{
+ KASSERT(nfscr->nfsc_ngroups >= 0,
+ ("newnfs_copycred: negative nfsc_ngroups"));
cr->cr_uid = nfscr->nfsc_uid;
crsetgroups(cr, nfscr->nfsc_ngroups, nfscr->nfsc_groups);
}
Modified: head/sys/fs/nfs/nfsclstate.h
==============================================================================
--- head/sys/fs/nfs/nfsclstate.h Thu Apr 15 21:41:07 2010 (r206687)
+++ head/sys/fs/nfs/nfsclstate.h Thu Apr 15 22:57:30 2010 (r206688)
@@ -140,6 +140,7 @@ struct nfsclopen {
#define NFSCLOPEN_OK 0
#define NFSCLOPEN_DOOPEN 1
#define NFSCLOPEN_DOOPENDOWNGRADE 2
+#define NFSCLOPEN_SETCRED 3
struct nfscllockowner {
LIST_ENTRY(nfscllockowner) nfsl_list;
Modified: head/sys/fs/nfsclient/nfs_clport.c
==============================================================================
--- head/sys/fs/nfsclient/nfs_clport.c Thu Apr 15 21:41:07 2010 (r206687)
+++ head/sys/fs/nfsclient/nfs_clport.c Thu Apr 15 22:57:30 2010 (r206688)
@@ -978,6 +978,8 @@ newnfs_copyincred(struct ucred *cr, stru
{
int i;
+ KASSERT(cr->cr_ngroups >= 0,
+ ("newnfs_copyincred: negative cr_ngroups"));
nfscr->nfsc_uid = cr->cr_uid;
nfscr->nfsc_ngroups = MIN(cr->cr_ngroups, NFS_MAXGRPS + 1);
for (i = 0; i < nfscr->nfsc_ngroups; i++)
Modified: head/sys/fs/nfsclient/nfs_clrpcops.c
==============================================================================
--- head/sys/fs/nfsclient/nfs_clrpcops.c Thu Apr 15 21:41:07 2010 (r206687)
+++ head/sys/fs/nfsclient/nfs_clrpcops.c Thu Apr 15 22:57:30 2010 (r206688)
@@ -278,7 +278,13 @@ else printf(" fhl=0\n");
error = EIO;
}
newnfs_copyincred(cred, &op->nfso_cred);
- }
+ } else if (ret == NFSCLOPEN_SETCRED)
+ /*
+ * This is a new local open on a delegation. It needs
+ * to have credentials so that an open can be done
+ * against the server during recovery.
+ */
+ newnfs_copyincred(cred, &op->nfso_cred);
/*
* nfso_opencnt is the count of how many VOP_OPEN()s have
Modified: head/sys/fs/nfsclient/nfs_clstate.c
==============================================================================
--- head/sys/fs/nfsclient/nfs_clstate.c Thu Apr 15 21:41:07 2010 (r206687)
+++ head/sys/fs/nfsclient/nfs_clstate.c Thu Apr 15 22:57:30 2010 (r206688)
@@ -274,8 +274,13 @@ nfscl_open(vnode_t vp, u_int8_t *nfhp, i
*owpp = owp;
if (opp != NULL)
*opp = op;
- if (retp != NULL)
- *retp = NFSCLOPEN_OK;
+ if (retp != NULL) {
+ if (nfhp != NULL && dp != NULL && nop == NULL)
+ /* new local open on delegation */
+ *retp = NFSCLOPEN_SETCRED;
+ else
+ *retp = NFSCLOPEN_OK;
+ }
/*
* Now, check the mode on the open and return the appropriate
More information about the svn-src-all
mailing list