Date: Thu, 26 Jan 2012 03:40:33 +0000 (UTC) From: Rick Macklem <rmacklem@FreeBSD.org> To: src-committers@freebsd.org, svn-src-projects@freebsd.org Subject: svn commit: r230561 - in projects/nfsv4.1-client/sys/fs: nfs nfsclient Message-ID: <201201260340.q0Q3eXvh059674@svn.freebsd.org>
next in thread | raw e-mail | index | archive | help
Author: rmacklem Date: Thu Jan 26 03:40:32 2012 New Revision: 230561 URL: http://svn.freebsd.org/changeset/base/230561 Log: To avoid crashes during forced dismounts, the NFSv4.1 session structure needed to be moved from the clientid (nfsclclient) structure to the nfsmount structure. The crashes happened because the clientid structure was being free'd too early in the forced umount. Modified: projects/nfsv4.1-client/sys/fs/nfs/nfs_commonkrpc.c projects/nfsv4.1-client/sys/fs/nfs/nfsclstate.h projects/nfsv4.1-client/sys/fs/nfsclient/nfs_clcomsubs.c projects/nfsv4.1-client/sys/fs/nfsclient/nfs_clrpcops.c projects/nfsv4.1-client/sys/fs/nfsclient/nfs_clstate.c projects/nfsv4.1-client/sys/fs/nfsclient/nfs_clvfsops.c projects/nfsv4.1-client/sys/fs/nfsclient/nfsmount.h Modified: projects/nfsv4.1-client/sys/fs/nfs/nfs_commonkrpc.c ============================================================================== --- projects/nfsv4.1-client/sys/fs/nfs/nfs_commonkrpc.c Thu Jan 26 00:49:05 2012 (r230560) +++ projects/nfsv4.1-client/sys/fs/nfs/nfs_commonkrpc.c Thu Jan 26 03:40:32 2012 (r230561) @@ -797,9 +797,9 @@ tryagain: nd->nd_dpos = NFSMTOD(nd->nd_md, caddr_t); nd->nd_repstat = 0; if (nd->nd_procnum != NFSPROC_NULL) { - /* If sep == NULL, set it to the default in nfsclclient. */ - if (sep == NULL && nmp != NULL && nmp->nm_clp != NULL) - sep = &nmp->nm_clp->nfsc_sess; + /* If sep == NULL, set it to the default in nmp. */ + if (sep == NULL && nmp != NULL) + sep = &nmp->nm_sess; /* * and now the actual NFS xdr. */ Modified: projects/nfsv4.1-client/sys/fs/nfs/nfsclstate.h ============================================================================== --- projects/nfsv4.1-client/sys/fs/nfs/nfsclstate.h Thu Jan 26 00:49:05 2012 (r230560) +++ projects/nfsv4.1-client/sys/fs/nfs/nfsclstate.h Thu Jan 26 03:40:32 2012 (r230561) @@ -87,7 +87,6 @@ struct nfsclclient { struct nfscldevinfohead nfsc_devinfo; struct nfscldevinfohash nfsc_devinfohash[NFSCLDEVINFOHASHSIZE]; struct nfsv4lock nfsc_lock; - struct nfsclsession nfsc_sess; struct proc *nfsc_renewthread; struct nfsmount *nfsc_nmp; time_t nfsc_expire; @@ -100,16 +99,6 @@ struct nfsclclient { u_int8_t nfsc_id[1]; /* Malloc'd to correct length */ }; -#define nfsc_mtx nfsc_sess.nfsess_mtx -#define nfsc_cbslots nfsc_sess.nfsess_cbslots -#define nfsc_clientid nfsc_sess.nfsess_clientid -#define nfsc_slotseq nfsc_sess.nfsess_slotseq -#define nfsc_slots nfsc_sess.nfsess_slots -#define nfsc_sequenceid nfsc_sess.nfsess_sequenceid -#define nfsc_foreslots nfsc_sess.nfsess_foreslots -#define nfsc_backslots nfsc_sess.nfsess_backslots -#define nfsc_sessionid nfsc_sess.nfsess_sessionid - /* * Bits for nfsc_flags. */ Modified: projects/nfsv4.1-client/sys/fs/nfsclient/nfs_clcomsubs.c ============================================================================== --- projects/nfsv4.1-client/sys/fs/nfsclient/nfs_clcomsubs.c Thu Jan 26 00:49:05 2012 (r230560) +++ projects/nfsv4.1-client/sys/fs/nfsclient/nfs_clcomsubs.c Thu Jan 26 03:40:32 2012 (r230561) @@ -192,7 +192,7 @@ nfscl_reqstart(struct nfsrv_descript *nd NFSM_BUILD(tl, u_int32_t *, NFSX_UNSIGNED); *tl = txdr_unsigned(NFSV4OP_SEQUENCE); if (sep == NULL) - nfsv4_setsequence(nd, &nmp->nm_clp->nfsc_sess, + nfsv4_setsequence(nd, &nmp->nm_sess, nfs_bigreply[procnum]); else nfsv4_setsequence(nd, sep, Modified: projects/nfsv4.1-client/sys/fs/nfsclient/nfs_clrpcops.c ============================================================================== --- projects/nfsv4.1-client/sys/fs/nfsclient/nfs_clrpcops.c Thu Jan 26 00:49:05 2012 (r230560) +++ projects/nfsv4.1-client/sys/fs/nfsclient/nfs_clrpcops.c Thu Jan 26 03:40:32 2012 (r230561) @@ -367,8 +367,8 @@ nfsrpc_openrpc(struct nfsmount *nmp, vno *tl++ = txdr_unsigned(op->nfso_own->nfsow_seqid); *tl++ = txdr_unsigned(mode & NFSV4OPEN_ACCESSBOTH); *tl++ = txdr_unsigned((mode >> NFSLCK_SHIFT) & NFSV4OPEN_DENYBOTH); - *tl++ = op->nfso_own->nfsow_clp->nfsc_clientid.lval[0]; - *tl = op->nfso_own->nfsow_clp->nfsc_clientid.lval[1]; + *tl++ = nmp->nm_sess.nfsess_clientid.lval[0]; + *tl = nmp->nm_sess.nfsess_clientid.lval[1]; (void) nfsm_strtom(nd, op->nfso_own->nfsow_owner, NFSV4CL_LOCKNAMELEN); NFSM_BUILD(tl, u_int32_t *, 2 * NFSX_UNSIGNED); *tl++ = txdr_unsigned(NFSV4OPEN_NOCREATE); @@ -796,11 +796,11 @@ nfsrpc_setclient(struct nfsmount *nmp, s NFSSETBOOTTIME(nfsboottime); clp->nfsc_rev = rev++; if (NFSHASNFSV4N(nmp)) { - error = nfsrpc_exchangeid(nmp, clp, &clp->nfsc_sess, + error = nfsrpc_exchangeid(nmp, clp, &nmp->nm_sess, NFSV4EXCH_USEPNFSMDS | NFSV4EXCH_USENONPNFS, cred, p); if (error) printf("exch=%d\n",error); if (error == 0) - error = nfsrpc_createsession(nmp, &clp->nfsc_sess, cred, + error = nfsrpc_createsession(nmp, &nmp->nm_sess, cred, p); if (error) printf("aft crs=%d\n",error); return (error); @@ -864,8 +864,8 @@ if (error) printf("aft crs=%d\n",error); return (error); if (nd->nd_repstat == 0) { NFSM_DISSECT(tl, u_int32_t *, 4 * NFSX_UNSIGNED); - clp->nfsc_clientid.lval[0] = *tl++; - clp->nfsc_clientid.lval[1] = *tl++; + nmp->nm_sess.nfsess_clientid.lval[0] = *tl++; + nmp->nm_sess.nfsess_clientid.lval[1] = *tl++; confirm.lval[0] = *tl++; confirm.lval[1] = *tl; mbuf_freem(nd->nd_mrep); @@ -877,8 +877,8 @@ if (error) printf("aft crs=%d\n",error); nfscl_reqstart(nd, NFSPROC_SETCLIENTIDCFRM, nmp, NULL, 0, NULL, NULL); NFSM_BUILD(tl, u_int32_t *, 4 * NFSX_UNSIGNED); - *tl++ = clp->nfsc_clientid.lval[0]; - *tl++ = clp->nfsc_clientid.lval[1]; + *tl++ = nmp->nm_sess.nfsess_clientid.lval[0]; + *tl++ = nmp->nm_sess.nfsess_clientid.lval[1]; *tl++ = confirm.lval[0]; *tl = confirm.lval[1]; nd->nd_flag |= ND_USEGSSNAME; @@ -1876,7 +1876,9 @@ nfsrpc_createv4(vnode_t dvp, char *name, nfsattrbit_t attrbits; nfsv4stateid_t stateid; u_int32_t rflags; + struct nfsmount *nmp; + nmp = VFSTONFS(dvp->v_mount); *unlockedp = 0; *nfhpp = NULL; *dpp = NULL; @@ -1893,8 +1895,8 @@ nfsrpc_createv4(vnode_t dvp, char *name, *tl++ = txdr_unsigned(NFSV4OPEN_ACCESSWRITE | NFSV4OPEN_ACCESSREAD); *tl++ = txdr_unsigned(NFSV4OPEN_DENYNONE); - *tl++ = owp->nfsow_clp->nfsc_clientid.lval[0]; - *tl = owp->nfsow_clp->nfsc_clientid.lval[1]; + *tl++ = nmp->nm_sess.nfsess_clientid.lval[0]; + *tl = nmp->nm_sess.nfsess_clientid.lval[1]; (void) nfsm_strtom(nd, owp->nfsow_owner, NFSV4CL_LOCKNAMELEN); NFSM_BUILD(tl, u_int32_t *, 2 * NFSX_UNSIGNED); *tl++ = txdr_unsigned(NFSV4OPEN_CREATE); @@ -3670,7 +3672,9 @@ nfsrpc_lockt(struct nfsrv_descript *nd, int error, type, size; uint8_t own[NFSV4CL_LOCKNAMELEN + NFSX_V4FHMAX]; struct nfsnode *np; + struct nfsmount *nmp; + nmp = VFSTONFS(vp->v_mount); NFSCL_REQSTART(nd, NFSPROC_LOCKT, vp); NFSM_BUILD(tl, u_int32_t *, 7 * NFSX_UNSIGNED); if (fl->l_type == F_RDLCK) @@ -3681,8 +3685,8 @@ nfsrpc_lockt(struct nfsrv_descript *nd, tl += 2; txdr_hyper(len, tl); tl += 2; - *tl++ = clp->nfsc_clientid.lval[0]; - *tl = clp->nfsc_clientid.lval[1]; + *tl++ = nmp->nm_sess.nfsess_clientid.lval[0]; + *tl = nmp->nm_sess.nfsess_clientid.lval[1]; nfscl_filllockowner(id, own, flags); np = VTONFS(vp); NFSBCOPY(np->n_fhp->nfh_fh, &own[NFSV4CL_LOCKNAMELEN], @@ -3810,8 +3814,8 @@ nfsrpc_lock(struct nfsrv_descript *nd, s *tl++ = lp->nfsl_open->nfso_stateid.other[1]; *tl++ = lp->nfsl_open->nfso_stateid.other[2]; *tl++ = txdr_unsigned(lp->nfsl_seqid); - *tl++ = lp->nfsl_open->nfso_own->nfsow_clp->nfsc_clientid.lval[0]; - *tl = lp->nfsl_open->nfso_own->nfsow_clp->nfsc_clientid.lval[1]; + *tl++ = nmp->nm_sess.nfsess_clientid.lval[0]; + *tl = nmp->nm_sess.nfsess_clientid.lval[1]; NFSBCOPY(lp->nfsl_owner, own, NFSV4CL_LOCKNAMELEN); NFSBCOPY(nfhp, &own[NFSV4CL_LOCKNAMELEN], fhlen); (void)nfsm_strtom(nd, own, NFSV4CL_LOCKNAMELEN + fhlen); @@ -4055,8 +4059,8 @@ nfsrpc_renew(struct nfsclclient *clp, st if (!NFSHASNFSV4N(nmp)) { /* NFSv4.1 just uses a Sequence Op and not a Renew. */ NFSM_BUILD(tl, u_int32_t *, 2 * NFSX_UNSIGNED); - *tl++ = clp->nfsc_clientid.lval[0]; - *tl = clp->nfsc_clientid.lval[1]; + *tl++ = nmp->nm_sess.nfsess_clientid.lval[0]; + *tl = nmp->nm_sess.nfsess_clientid.lval[1]; } nd->nd_flag |= ND_USEGSSNAME; error = newnfs_request(nd, nmp, NULL, &nmp->nm_sockreq, NULL, p, cred, @@ -4089,8 +4093,8 @@ nfsrpc_rellockown(struct nfsmount *nmp, nfscl_reqstart(nd, NFSPROC_RELEASELCKOWN, nmp, NULL, 0, NULL, NULL); NFSM_BUILD(tl, u_int32_t *, 2 * NFSX_UNSIGNED); - *tl++ = nmp->nm_clp->nfsc_clientid.lval[0]; - *tl = nmp->nm_clp->nfsc_clientid.lval[1]; + *tl++ = nmp->nm_sess.nfsess_clientid.lval[0]; + *tl = nmp->nm_sess.nfsess_clientid.lval[1]; NFSBCOPY(lp->nfsl_owner, own, NFSV4CL_LOCKNAMELEN); NFSBCOPY(fh, &own[NFSV4CL_LOCKNAMELEN], fhlen); (void)nfsm_strtom(nd, own, NFSV4CL_LOCKNAMELEN + fhlen); @@ -4443,7 +4447,7 @@ nfsrpc_destroysession(struct nfsmount *n nfscl_reqstart(nd, NFSPROC_DESTROYSESSION, nmp, NULL, 0, NULL, NULL); NFSM_BUILD(tl, uint32_t *, NFSX_V4SESSIONID); - bcopy(clp->nfsc_sessionid, tl, NFSX_V4SESSIONID); + bcopy(nmp->nm_sess.nfsess_sessionid, tl, NFSX_V4SESSIONID); nd->nd_flag |= ND_USEGSSNAME; error = newnfs_request(nd, nmp, NULL, &nmp->nm_sockreq, NULL, p, cred, NFS_PROG, NFS_VER4, NULL, 1, NULL, NULL); @@ -4468,8 +4472,8 @@ nfsrpc_destroyclient(struct nfsmount *nm nfscl_reqstart(nd, NFSPROC_DESTROYCLIENT, nmp, NULL, 0, NULL, NULL); NFSM_BUILD(tl, uint32_t *, 2 * NFSX_UNSIGNED); - *tl++ = clp->nfsc_clientid.lval[0]; - *tl = clp->nfsc_clientid.lval[1]; + *tl++ = nmp->nm_sess.nfsess_clientid.lval[0]; + *tl = nmp->nm_sess.nfsess_clientid.lval[1]; nd->nd_flag |= ND_USEGSSNAME; error = newnfs_request(nd, nmp, NULL, &nmp->nm_sockreq, NULL, p, cred, NFS_PROG, NFS_VER4, NULL, 1, NULL, NULL); Modified: projects/nfsv4.1-client/sys/fs/nfsclient/nfs_clstate.c ============================================================================== --- projects/nfsv4.1-client/sys/fs/nfsclient/nfs_clstate.c Thu Jan 26 00:49:05 2012 (r230560) +++ projects/nfsv4.1-client/sys/fs/nfsclient/nfs_clstate.c Thu Jan 26 03:40:32 2012 (r230561) @@ -729,8 +729,6 @@ nfscl_getcl(struct mount *mp, struct ucr MALLOC(newclp, struct nfsclclient *, sizeof (struct nfsclclient) + idlen - 1, M_NFSCLCLIENT, M_WAITOK | M_ZERO); - mtx_init(&newclp->nfsc_mtx, "ClientID lock", NULL, - MTX_DEF | MTX_DUPOK); } NFSLOCKCLSTATE(); /* @@ -740,10 +738,8 @@ nfscl_getcl(struct mount *mp, struct ucr */ if ((mp->mnt_kern_flag & MNTK_UNMOUNTF) != 0) { NFSUNLOCKCLSTATE(); - if (newclp != NULL) { - mtx_destroy(&newclp->nfsc_mtx); + if (newclp != NULL) free(newclp, M_NFSCLCLIENT); - } return (EBADF); } clp = nmp->nm_clp; @@ -777,10 +773,8 @@ nfscl_getcl(struct mount *mp, struct ucr nfscl_start_renewthread(clp); } else { NFSUNLOCKCLSTATE(); - if (newclp != NULL) { - mtx_destroy(&newclp->nfsc_mtx); + if (newclp != NULL) free(newclp, M_NFSCLCLIENT); - } } NFSLOCKCLSTATE(); while ((clp->nfsc_flags & NFSCLFLAGS_HASCLIENTID) == 0 && !igotlock && @@ -1781,7 +1775,7 @@ nfscl_umount(struct nfsmount *nmp, NFSPR { struct nfsclclient *clp; struct ucred *cred; - int i, igotlock; + int igotlock; /* * For the case that matters, this is the thread that set @@ -1850,10 +1844,7 @@ nfscl_umount(struct nfsmount *nmp, NFSPR nfscl_cleanclient(clp); nmp->nm_clp = NULL; NFSFREECRED(cred); - for (i = 0; i < NFSV4_CBSLOTS; i++) - if (clp->nfsc_cbslots[i].nfssl_reply != NULL) - m_freem(clp->nfsc_cbslots[i].nfssl_reply); - FREE((caddr_t)clp, M_NFSCLCLIENT); + free(clp, M_NFSCLCLIENT); } else NFSUNLOCKCLSTATE(); } @@ -3205,8 +3196,9 @@ printf("cbrecall\n"); error = NFSERR_SEQUENCEPOS; if (error == 0) error = nfsv4_seqsession(seqid, slotid, - highslot, clp->nfsc_cbslots, &rep, - clp->nfsc_backslots); + highslot, + clp->nfsc_nmp->nm_sess.nfsess_cbslots, &rep, + clp->nfsc_nmp->nm_sess.nfsess_backslots); NFSUNLOCKCLSTATE(); if (error == 0) { gotseq_ok = 1; @@ -3273,7 +3265,8 @@ out: NFSLOCKCLSTATE(); clp = nfscl_getclntsess(sessionid); if (clp != NULL) { - nfsv4_seqsess_cacherep(slotid, clp->nfsc_cbslots, rep); + nfsv4_seqsess_cacherep(slotid, + clp->nfsc_nmp->nm_sess.nfsess_cbslots, rep); NFSUNLOCKCLSTATE(); } else { NFSUNLOCKCLSTATE(); @@ -3335,8 +3328,8 @@ nfscl_getmnt(int minorvers, uint8_t *ses if (minorvers == NFSV4_MINORVERSION) { if (clp->nfsc_cbident == cbident) break; - } else if (!NFSBCMP(clp->nfsc_sessionid, sessionid, - NFSX_V4SESSIONID)) + } else if (!NFSBCMP(clp->nfsc_nmp->nm_sess.nfsess_sessionid, + sessionid, NFSX_V4SESSIONID)) break; } if (clp == NULL) { @@ -3377,7 +3370,8 @@ nfscl_getclntsess(uint8_t *sessionid) struct nfsclclient *clp; LIST_FOREACH(clp, &nfsclhead, nfsc_list) - if (!NFSBCMP(clp->nfsc_sessionid, sessionid, NFSX_V4SESSIONID)) + if (!NFSBCMP(clp->nfsc_nmp->nm_sess.nfsess_sessionid, sessionid, + NFSX_V4SESSIONID)) break; return (clp); } Modified: projects/nfsv4.1-client/sys/fs/nfsclient/nfs_clvfsops.c ============================================================================== --- projects/nfsv4.1-client/sys/fs/nfsclient/nfs_clvfsops.c Thu Jan 26 00:49:05 2012 (r230560) +++ projects/nfsv4.1-client/sys/fs/nfsclient/nfs_clvfsops.c Thu Jan 26 03:40:32 2012 (r230561) @@ -1169,7 +1169,7 @@ mountnfs(struct nfs_args *argp, struct m { struct nfsmount *nmp; struct nfsnode *np; - int error, trycnt, ret; + int error, i, trycnt, ret; struct nfsvattr nfsva; struct nfsclclient *clp; uint32_t lease; @@ -1230,6 +1230,7 @@ printf("in mnt\n"); } nmp->nm_sockreq.nr_cred = crhold(cred); mtx_init(&nmp->nm_sockreq.nr_mtx, "nfssock", NULL, MTX_DEF); + mtx_init(&nmp->nm_sess.nfsess_mtx, "nfssession", NULL, MTX_DEF); mp->mnt_data = nmp; nmp->nm_getinfo = nfs_getnlminfo; nmp->nm_vinvalbuf = ncl_vinvalbuf; @@ -1419,12 +1420,17 @@ bad: newnfs_disconnect(&nmp->nm_sockreq); crfree(nmp->nm_sockreq.nr_cred); mtx_destroy(&nmp->nm_sockreq.nr_mtx); + mtx_destroy(&nmp->nm_sess.nfsess_mtx); mtx_destroy(&nmp->nm_mtx); if (nmp->nm_clp != NULL) { NFSLOCKCLSTATE(); LIST_REMOVE(nmp->nm_clp, nfsc_list); NFSUNLOCKCLSTATE(); free(nmp->nm_clp, M_NFSCLCLIENT); + for (i = 0; i < NFSV4_CBSLOTS; i++) + if (nmp->nm_sess.nfsess_cbslots[i].nfssl_reply != NULL) + m_freem( + nmp->nm_sess.nfsess_cbslots[i].nfssl_reply); } FREE(nmp, M_NEWNFSMNT); FREE(nam, M_SONAME); @@ -1439,7 +1445,7 @@ nfs_unmount(struct mount *mp, int mntfla { struct thread *td; struct nfsmount *nmp; - int error, flags = 0, trycnt = 0; + int error, flags = 0, i, trycnt = 0; td = curthread; @@ -1480,6 +1486,10 @@ nfs_unmount(struct mount *mp, int mntfla mtx_destroy(&nmp->nm_sockreq.nr_mtx); mtx_destroy(&nmp->nm_mtx); + mtx_destroy(&nmp->nm_sess.nfsess_mtx); + for (i = 0; i < NFSV4_CBSLOTS; i++) + if (nmp->nm_sess.nfsess_cbslots[i].nfssl_reply != NULL) + m_freem(nmp->nm_sess.nfsess_cbslots[i].nfssl_reply); FREE(nmp, M_NEWNFSMNT); out: return (error); Modified: projects/nfsv4.1-client/sys/fs/nfsclient/nfsmount.h ============================================================================== --- projects/nfsv4.1-client/sys/fs/nfsclient/nfsmount.h Thu Jan 26 00:49:05 2012 (r230560) +++ projects/nfsv4.1-client/sys/fs/nfsclient/nfsmount.h Thu Jan 26 03:40:32 2012 (r230561) @@ -69,6 +69,7 @@ struct nfsmount { int nm_negnametimeo; /* timeout for -ve entries (sec) */ /* Newnfs additions */ + struct nfsclsession nm_sess; /* Session for NFSv4.1 mount. */ struct nfsclclient *nm_clp; uid_t nm_uid; /* Uid for SetClientID etc. */ u_int64_t nm_clval; /* identifies which clientid */
Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?201201260340.q0Q3eXvh059674>