summaryrefslogtreecommitdiffstats
path: root/module/zfs/vdev_disk.c
diff options
context:
space:
mode:
authorOlaf Faaland <[email protected]>2018-05-11 12:46:07 -0700
committerBrian Behlendorf <[email protected]>2018-05-11 12:46:07 -0700
commitbc5f51c5de21fd8b7cf3110801a6b1db1e4c3d0a (patch)
tree9781fdf091e1a1e364f4ae8a6f1d7ff133da2206 /module/zfs/vdev_disk.c
parent68fded814692c6a7fa7ca1f584a34a92aaa279af (diff)
module param callbacks check for initialized spa
Callbacks provided for module parameters are executed both after the module is loaded, when a user alters it via sysfs, e.g echo bar > /sys/modules/zfs/parameters/foo as well as when the module is loaded with an argument, e.g. modprobe zfs foo=bar In the latter case, the init functions likely have not run yet, including spa_init() which initializes the namespace lock so it is safe to use. Instead of immediately taking the namespace lock and attemping to iterate over initialized spa structures, check whether spa_mode_global is nonzero. This is set by spa_init() after it has initialized the namespace lock. Reviewed-by: Brian Behlendorf <[email protected]> Reviewed-by: Tim Chase <[email protected]> Signed-off-by: Olaf Faaland <[email protected]> Closes #7496 Closes #7521
Diffstat (limited to 'module/zfs/vdev_disk.c')
-rw-r--r--module/zfs/vdev_disk.c24
1 files changed, 13 insertions, 11 deletions
diff --git a/module/zfs/vdev_disk.c b/module/zfs/vdev_disk.c
index f537c0d27..9c3a1ba80 100644
--- a/module/zfs/vdev_disk.c
+++ b/module/zfs/vdev_disk.c
@@ -818,19 +818,21 @@ param_set_vdev_scheduler(const char *val, zfs_kernel_param_t *kp)
if ((p = strchr(val, '\n')) != NULL)
*p = '\0';
- mutex_enter(&spa_namespace_lock);
- while ((spa = spa_next(spa)) != NULL) {
- if (spa_state(spa) != POOL_STATE_ACTIVE ||
- !spa_writeable(spa) || spa_suspended(spa))
- continue;
-
- spa_open_ref(spa, FTAG);
- mutex_exit(&spa_namespace_lock);
- vdev_elevator_switch(spa->spa_root_vdev, (char *)val);
+ if (spa_mode_global != 0) {
mutex_enter(&spa_namespace_lock);
- spa_close(spa, FTAG);
+ while ((spa = spa_next(spa)) != NULL) {
+ if (spa_state(spa) != POOL_STATE_ACTIVE ||
+ !spa_writeable(spa) || spa_suspended(spa))
+ continue;
+
+ spa_open_ref(spa, FTAG);
+ mutex_exit(&spa_namespace_lock);
+ vdev_elevator_switch(spa->spa_root_vdev, (char *)val);
+ mutex_enter(&spa_namespace_lock);
+ spa_close(spa, FTAG);
+ }
+ mutex_exit(&spa_namespace_lock);
}
- mutex_exit(&spa_namespace_lock);
return (param_set_charp(val, kp));
}