Skip to content

Commit

Permalink
Add feature check for 'zpool resilver' command
Browse files Browse the repository at this point in the history
The 'zpool resilver' command requires that the resilver_defer
feature is active on the pool. Unfortunately, the check for
this was left out of the original patch. This commit simply
corrects this so that the command properly returns an error
in this case.

Reviewed by: Brian Behlendorf <behlendorf1@llnl.gov>
Reviewed-by: Igor Kozhukhov <igor@dilos.org>
Signed-off-by: Tom Caputi <tcaputi@datto.com>
Closes openzfs#8700
  • Loading branch information
Tom Caputi authored and allanjude committed Jun 15, 2019
1 parent 4159602 commit 7db1a4c
Show file tree
Hide file tree
Showing 6 changed files with 30 additions and 1 deletion.
1 change: 1 addition & 0 deletions include/libzfs.h
Original file line number Diff line number Diff line change
Expand Up @@ -146,6 +146,7 @@ typedef enum zfs_error {
EZFS_TRIMMING, /* currently trimming */
EZFS_NO_TRIM, /* no active trim */
EZFS_TRIM_NOTSUP, /* device does not support trim */
EZFS_NO_RESILVER_DEFER, /* pool doesn't support resilver_defer */
EZFS_UNKNOWN
} zfs_error_t;

Expand Down
6 changes: 6 additions & 0 deletions lib/libzfs/libzfs_pool.c
Original file line number Diff line number Diff line change
Expand Up @@ -2353,6 +2353,10 @@ zpool_scan(zpool_handle_t *zhp, pool_scan_func_t func, pool_scrub_cmd_t cmd)
(void) snprintf(msg, sizeof (msg), dgettext(TEXT_DOMAIN,
"cannot scrub %s"), zc.zc_name);
}
} else if (func == POOL_SCAN_RESILVER) {
assert(cmd == POOL_SCRUB_NORMAL);
(void) snprintf(msg, sizeof (msg), dgettext(TEXT_DOMAIN,
"cannot restart resilver on %s"), zc.zc_name);
} else if (func == POOL_SCAN_NONE) {
(void) snprintf(msg, sizeof (msg),
dgettext(TEXT_DOMAIN, "cannot cancel scrubbing %s"),
Expand Down Expand Up @@ -2380,6 +2384,8 @@ zpool_scan(zpool_handle_t *zhp, pool_scan_func_t func, pool_scrub_cmd_t cmd)
}
} else if (err == ENOENT) {
return (zfs_error(hdl, EZFS_NO_SCRUB, msg));
} else if (err == ENOTSUP && func == POOL_SCAN_RESILVER) {
return (zfs_error(hdl, EZFS_NO_RESILVER_DEFER, msg));
} else {
return (zpool_standard_error(hdl, err, msg));
}
Expand Down
3 changes: 3 additions & 0 deletions lib/libzfs/libzfs_util.c
Original file line number Diff line number Diff line change
Expand Up @@ -312,6 +312,9 @@ libzfs_error_description(libzfs_handle_t *hdl)
case EZFS_TRIM_NOTSUP:
return (dgettext(TEXT_DOMAIN, "trim operations are not "
"supported by this device"));
case EZFS_NO_RESILVER_DEFER:
return (dgettext(TEXT_DOMAIN, "this action requires the "
"resilver_defer feature"));
case EZFS_UNKNOWN:
return (dgettext(TEXT_DOMAIN, "unknown error"));
default:
Expand Down
4 changes: 3 additions & 1 deletion man/man8/zpool.8
Original file line number Diff line number Diff line change
Expand Up @@ -2216,7 +2216,9 @@ again.
.Xc
Starts a resilver. If an existing resilver is already running it will be
restarted from the beginning. Any drives that were scheduled for a deferred
resilver will be added to the new one.
resilver will be added to the new one. This requires the
.Sy resilver_defer
feature.
.It Xo
.Nm
.Cm trim
Expand Down
4 changes: 4 additions & 0 deletions module/zfs/spa.c
Original file line number Diff line number Diff line change
Expand Up @@ -7264,6 +7264,10 @@ spa_scan(spa_t *spa, pool_scan_func_t func)
if (func >= POOL_SCAN_FUNCS || func == POOL_SCAN_NONE)
return (SET_ERROR(ENOTSUP));

if (func == POOL_SCAN_RESILVER &&
!spa_feature_is_enabled(spa, SPA_FEATURE_RESILVER_DEFER))
return (SET_ERROR(ENOTSUP));

/*
* If a resilver was requested, but there is no DTL on a
* writeable leaf device, we have nothing to do.
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -35,6 +35,8 @@
# 1. Create an array containing bad 'zpool reilver' parameters.
# 2. For each element, execute the sub-command.
# 3. Verify it returns an error.
# 4. Confirm the sub-command returns an error if the resilver_defer
# feature isn't active.
#

verify_runnable "global"
Expand All @@ -45,6 +47,13 @@ set -A args "" "-?" "blah blah" "-%" "--?" "-*" "-=" \
"-A" "-B" "-C" "-D" "-E" "-F" "-G" "-H" "-I" "-J" "-K" "-L" \
"-M" "-N" "-O" "-P" "-Q" "-R" "-S" "-T" "-U" "-V" "-W" "-X" "-W" "-Z"

function cleanup
{
log_must destroy_pool $TESTPOOL2
log_must rm -f $TEST_BASE_DIR/zpool_resilver.dat
}

log_onexit cleanup

log_assert "Execute 'zpool resilver' using invalid parameters."

Expand All @@ -55,4 +64,8 @@ while [[ $i -lt ${#args[*]} ]]; do
((i = i + 1))
done

log_must mkfile $MINVDEVSIZE $TEST_BASE_DIR/zpool_resilver.dat
log_must zpool create -d $TESTPOOL2 $TEST_BASE_DIR/zpool_resilver.dat
log_mustnot zpool resilver $TESTPOOL2

log_pass "Badly formed 'zpool resilver' parameters fail as expected."

0 comments on commit 7db1a4c

Please sign in to comment.