diff options
author | Ameer Hamza <[email protected]> | 2022-09-28 21:48:46 +0500 |
---|---|---|
committer | GitHub <[email protected]> | 2022-09-28 09:48:46 -0700 |
commit | 55c12724d377e6c7ace5b4bd42cd728d4a60af3e (patch) | |
tree | e5d28efce371d1097882dc064c16f362560e933e /lib/libzfs | |
parent | eb9bec0a5d19abf9404f52081424fbb814e6188a (diff) |
zed: mark disks as REMOVED when they are removed
ZED does not take any action for disk removal events if there is no
spare VDEV available. Added zpool_vdev_remove_wanted() in libzfs
and vdev_remove_wanted() in vdev.c to remove the VDEV through ZED
on removal event. This means that if you are running zed and
remove a disk, it will be properly marked as REMOVED.
Reviewed-by: Alexander Motin <[email protected]>
Reviewed-by: Ryan Moeller <[email protected]>
Reviewed-by: Tony Hutter <[email protected]>
Signed-off-by: Ameer Hamza <[email protected]>
Closes #13797
Diffstat (limited to 'lib/libzfs')
-rw-r--r-- | lib/libzfs/libzfs.abi | 6 | ||||
-rw-r--r-- | lib/libzfs/libzfs_pool.c | 37 |
2 files changed, 43 insertions, 0 deletions
diff --git a/lib/libzfs/libzfs.abi b/lib/libzfs/libzfs.abi index 7dd12df81..3471bcac9 100644 --- a/lib/libzfs/libzfs.abi +++ b/lib/libzfs/libzfs.abi @@ -550,6 +550,7 @@ <elf-symbol name='zpool_vdev_path_to_guid' type='func-type' binding='global-binding' visibility='default-visibility' is-defined='yes'/> <elf-symbol name='zpool_vdev_remove' type='func-type' binding='global-binding' visibility='default-visibility' is-defined='yes'/> <elf-symbol name='zpool_vdev_remove_cancel' type='func-type' binding='global-binding' visibility='default-visibility' is-defined='yes'/> + <elf-symbol name='zpool_vdev_remove_wanted' type='func-type' binding='global-binding' visibility='default-visibility' is-defined='yes'/> <elf-symbol name='zpool_vdev_split' type='func-type' binding='global-binding' visibility='default-visibility' is-defined='yes'/> <elf-symbol name='zpool_wait' type='func-type' binding='global-binding' visibility='default-visibility' is-defined='yes'/> <elf-symbol name='zpool_wait_status' type='func-type' binding='global-binding' visibility='default-visibility' is-defined='yes'/> @@ -3505,6 +3506,11 @@ <parameter type-id='c19b74c3' name='istmp'/> <return type-id='95e97e5e'/> </function-decl> + <function-decl name='zpool_vdev_remove_wanted' mangled-name='zpool_vdev_remove_wanted' visibility='default' binding='global' size-in-bits='64' elf-symbol-id='zpool_vdev_remove_wanted'> + <parameter type-id='4c81de99' name='zhp'/> + <parameter type-id='80f4b756' name='path'/> + <return type-id='95e97e5e'/> + </function-decl> <function-decl name='zpool_vdev_fault' mangled-name='zpool_vdev_fault' visibility='default' binding='global' size-in-bits='64' elf-symbol-id='zpool_vdev_fault'> <parameter type-id='4c81de99' name='zhp'/> <parameter type-id='9c313c2d' name='guid'/> diff --git a/lib/libzfs/libzfs_pool.c b/lib/libzfs/libzfs_pool.c index eea388cf3..b9806dc30 100644 --- a/lib/libzfs/libzfs_pool.c +++ b/lib/libzfs/libzfs_pool.c @@ -3074,6 +3074,43 @@ zpool_vdev_offline(zpool_handle_t *zhp, const char *path, boolean_t istmp) } /* + * Remove the specified vdev asynchronously from the configuration, so + * that it may come ONLINE if reinserted. This is called from zed on + * Udev remove event. + * Note: We also have a similar function zpool_vdev_remove() that + * removes the vdev from the pool. + */ +int +zpool_vdev_remove_wanted(zpool_handle_t *zhp, const char *path) +{ + zfs_cmd_t zc = {"\0"}; + char errbuf[ERRBUFLEN]; + nvlist_t *tgt; + boolean_t avail_spare, l2cache; + libzfs_handle_t *hdl = zhp->zpool_hdl; + + (void) snprintf(errbuf, sizeof (errbuf), + dgettext(TEXT_DOMAIN, "cannot remove %s"), path); + + (void) strlcpy(zc.zc_name, zhp->zpool_name, sizeof (zc.zc_name)); + if ((tgt = zpool_find_vdev(zhp, path, &avail_spare, &l2cache, + NULL)) == NULL) + return (zfs_error(hdl, EZFS_NODEVICE, errbuf)); + + zc.zc_guid = fnvlist_lookup_uint64(tgt, ZPOOL_CONFIG_GUID); + + if (avail_spare) + return (zfs_error(hdl, EZFS_ISSPARE, errbuf)); + + zc.zc_cookie = VDEV_STATE_REMOVED; + + if (zfs_ioctl(hdl, ZFS_IOC_VDEV_SET_STATE, &zc) == 0) + return (0); + + return (zpool_standard_error(hdl, errno, errbuf)); +} + +/* * Mark the given vdev faulted. */ int |