Skip site navigation (1)Skip section navigation (2)
Date:      Fri, 19 Mar 2021 22:10:49 GMT
From:      Rick Macklem <rmacklem@FreeBSD.org>
To:        src-committers@FreeBSD.org, dev-commits-src-all@FreeBSD.org, dev-commits-src-main@FreeBSD.org
Subject:   git: 5f742d3879de - main - nfsv4 client: fix forced dismount when sleeping on nfsv4lck
Message-ID:  <202103192210.12JMAnZL035117@gitrepo.freebsd.org>

next in thread | raw e-mail | index | archive | help
The branch main has been updated by rmacklem:

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

commit 5f742d3879deb1f46f2d151d5ef84f49e8d6afe6
Author:     Rick Macklem <rmacklem@FreeBSD.org>
AuthorDate: 2021-03-19 21:09:33 +0000
Commit:     Rick Macklem <rmacklem@FreeBSD.org>
CommitDate: 2021-03-19 21:09:33 +0000

    nfsv4 client: fix forced dismount when sleeping on nfsv4lck
    
    During a recent NFSv4 testing event a test server caused a hang
    where "umount -N" failed.  The renew thread was sleeping on "nfsv4lck"
    and the "umount" was sleeping, waiting for the renew thread to
    terminate.
    
    This is the first of two patches that is hoped to fix the renew thread
    so that it will terminate when "umount -N" is done on the mount.
    
    nfsv4_lock() checks for forced dismount, but only after it wakes up
    from msleep().  Without this patch, a wakeup() call was required.
    This patch adds a 1second timeout on the msleep(), so that it will
    wake up and see the forced dismount flag.  Normally a wakeup()
    will occur in less than 1second, but if a premature return from
    msleep() does occur, it will simply loop around and msleep() again.
    
    While here, replace the nfsmsleep() wrapper that was used for portability
    with the actual msleep() call and make the same change for nfsv4_getref().
    
    MFC after:      2 weeks
---
 sys/fs/nfs/nfs_commonsubs.c | 10 ++++------
 sys/fs/nfs/nfs_var.h        |  4 ++--
 2 files changed, 6 insertions(+), 8 deletions(-)

diff --git a/sys/fs/nfs/nfs_commonsubs.c b/sys/fs/nfs/nfs_commonsubs.c
index d44ff122a95c..e9b2af17d8b4 100644
--- a/sys/fs/nfs/nfs_commonsubs.c
+++ b/sys/fs/nfs/nfs_commonsubs.c
@@ -2252,7 +2252,7 @@ nfsmout:
  */
 int
 nfsv4_lock(struct nfsv4lock *lp, int iwantlock, int *isleptp,
-    void *mutex, struct mount *mp)
+    struct mtx *mutex, struct mount *mp)
 {
 
 	if (isleptp)
@@ -2280,8 +2280,7 @@ nfsv4_lock(struct nfsv4lock *lp, int iwantlock, int *isleptp,
 		lp->nfslock_lock |= NFSV4LOCK_WANTED;
 		if (isleptp)
 			*isleptp = 1;
-		(void) nfsmsleep(&lp->nfslock_lock, mutex,
-		    PZERO - 1, "nfsv4lck", NULL);
+		msleep(&lp->nfslock_lock, mutex, PVFS, "nfsv4lck", hz);
 		if (iwantlock && !(lp->nfslock_lock & NFSV4LOCK_LOCK) &&
 		    lp->nfslock_usecnt == 0) {
 			lp->nfslock_lock &= ~NFSV4LOCK_LOCKWANTED;
@@ -2331,7 +2330,7 @@ nfsv4_relref(struct nfsv4lock *lp)
  * return without getting a refcnt for that case.
  */
 void
-nfsv4_getref(struct nfsv4lock *lp, int *isleptp, void *mutex,
+nfsv4_getref(struct nfsv4lock *lp, int *isleptp, struct mtx *mutex,
     struct mount *mp)
 {
 
@@ -2347,8 +2346,7 @@ nfsv4_getref(struct nfsv4lock *lp, int *isleptp, void *mutex,
 		lp->nfslock_lock |= NFSV4LOCK_WANTED;
 		if (isleptp)
 			*isleptp = 1;
-		(void) nfsmsleep(&lp->nfslock_lock, mutex,
-		    PZERO - 1, "nfsv4gr", NULL);
+		msleep(&lp->nfslock_lock, mutex, PVFS, "nfsv4gr", hz);
 	}
 	if (mp != NULL && NFSCL_FORCEDISM(mp))
 		return;
diff --git a/sys/fs/nfs/nfs_var.h b/sys/fs/nfs/nfs_var.h
index 0a1fe3ce053d..aba5c5124e72 100644
--- a/sys/fs/nfs/nfs_var.h
+++ b/sys/fs/nfs/nfs_var.h
@@ -335,10 +335,10 @@ int nfsv4_loadattr(struct nfsrv_descript *, vnode_t,
     struct nfsv3_pathconf *, struct statfs *, struct nfsstatfs *,
     struct nfsfsinfo *, NFSACL_T *,
     int, int *, u_int32_t *, u_int32_t *, NFSPROC_T *, struct ucred *);
-int nfsv4_lock(struct nfsv4lock *, int, int *, void *, struct mount *);
+int nfsv4_lock(struct nfsv4lock *, int, int *, struct mtx *, struct mount *);
 void nfsv4_unlock(struct nfsv4lock *, int);
 void nfsv4_relref(struct nfsv4lock *);
-void nfsv4_getref(struct nfsv4lock *, int *, void *, struct mount *);
+void nfsv4_getref(struct nfsv4lock *, int *, struct mtx *, struct mount *);
 int nfsv4_getref_nonblock(struct nfsv4lock *);
 int nfsv4_testlock(struct nfsv4lock *);
 int nfsrv_mtostr(struct nfsrv_descript *, char *, int);



Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?202103192210.12JMAnZL035117>