aboutsummaryrefslogtreecommitdiffstats
path: root/module
diff options
context:
space:
mode:
authorMark Johnston <[email protected]>2024-07-10 16:27:44 -0500
committerGitHub <[email protected]>2024-07-10 14:27:44 -0700
commit4367312760612cb755acfc218ffeda8eb35ce509 (patch)
tree08bdfe3bf5622562b94571ee55d2f5d7ddfa7313 /module
parent326040b285251598e84c7269ba26898832744b29 (diff)
zvol: Fix suspend lock leaks (#16270)
In several functions, we use a flag variable to track whether zv_suspend_lock is held. This flag was not getting reset in a particular case where we need to retry the underlying operation, resulting in a lock leak. Make sure to update the flag where necessary. Signed-off-by: Mark Johnston <[email protected]> Reviewed-by: Allan Jude <[email protected]> Reviewed-by: Alexander Motin <[email protected]> Reviewed-by: Tino Reichardt <[email protected]> Reviewed-by: Tony Hutter <[email protected]>
Diffstat (limited to 'module')
-rw-r--r--module/os/freebsd/zfs/zvol_os.c2
-rw-r--r--module/os/linux/zfs/zvol_os.c1
2 files changed, 3 insertions, 0 deletions
diff --git a/module/os/freebsd/zfs/zvol_os.c b/module/os/freebsd/zfs/zvol_os.c
index 712ff1b83..38e9debbe 100644
--- a/module/os/freebsd/zfs/zvol_os.c
+++ b/module/os/freebsd/zfs/zvol_os.c
@@ -292,6 +292,7 @@ retry:
if (!mutex_tryenter(&spa_namespace_lock)) {
mutex_exit(&zv->zv_state_lock);
rw_exit(&zv->zv_suspend_lock);
+ drop_suspend = B_FALSE;
kern_yield(PRI_USER);
goto retry;
} else {
@@ -983,6 +984,7 @@ retry:
if (!mutex_tryenter(&spa_namespace_lock)) {
mutex_exit(&zv->zv_state_lock);
rw_exit(&zv->zv_suspend_lock);
+ drop_suspend = B_FALSE;
kern_yield(PRI_USER);
goto retry;
} else {
diff --git a/module/os/linux/zfs/zvol_os.c b/module/os/linux/zfs/zvol_os.c
index acb42c3b4..1d5d54b80 100644
--- a/module/os/linux/zfs/zvol_os.c
+++ b/module/os/linux/zfs/zvol_os.c
@@ -791,6 +791,7 @@ retry:
if (!mutex_tryenter(&spa_namespace_lock)) {
mutex_exit(&zv->zv_state_lock);
rw_exit(&zv->zv_suspend_lock);
+ drop_suspend = B_FALSE;
#ifdef HAVE_BLKDEV_GET_ERESTARTSYS
schedule();