zfs: merge OpenZFS master-bf156c966
Notable upstream changes: bf156c966 Remove unused abd_alloc_scatter_offset_chunkcnt 658fb8020 Add "compatibility" property for zpool feature sets This update introduces a new pool property called "compatibility" that can be used to enable a limited set of pool features on pool creation and "stick" to it, so the "zpool upgrade" does not accidentally enable features that are not desired. The value of this property may then be changed later. See zpool-features(5) for more information about the "compatibility" pool property. Obtained from: OpenZFS MFC after: 2 weeks
This commit is contained in:
commit
ee36e25a86
@ -39,7 +39,7 @@ include $(top_srcdir)/config/CppCheck.am
|
||||
zpoolconfdir = $(sysconfdir)/zfs/zpool.d
|
||||
zpoolexecdir = $(zfsexecdir)/zpool.d
|
||||
|
||||
EXTRA_DIST = zpool.d/README
|
||||
EXTRA_DIST = zpool.d/README compatibility.d
|
||||
|
||||
dist_zpoolexec_SCRIPTS = \
|
||||
zpool.d/dm-deps \
|
||||
@ -129,6 +129,48 @@ zpoolconfdefaults = \
|
||||
test_progress \
|
||||
test_ended
|
||||
|
||||
zpoolcompatdir = $(pkgdatadir)/compatibility.d
|
||||
|
||||
dist_zpoolcompat_DATA = \
|
||||
compatibility.d/compat-2018 \
|
||||
compatibility.d/compat-2019 \
|
||||
compatibility.d/compat-2020 \
|
||||
compatibility.d/compat-2021 \
|
||||
compatibility.d/freebsd-11.0 \
|
||||
compatibility.d/freebsd-11.2 \
|
||||
compatibility.d/freebsd-11.3 \
|
||||
compatibility.d/freenas-9.10.2 \
|
||||
compatibility.d/grub2 \
|
||||
compatibility.d/openzfsonosx-1.7.0 \
|
||||
compatibility.d/openzfsonosx-1.8.1 \
|
||||
compatibility.d/openzfsonosx-1.9.3 \
|
||||
compatibility.d/openzfs-2.0-freebsd \
|
||||
compatibility.d/openzfs-2.0-linux \
|
||||
compatibility.d/zol-0.6.5 \
|
||||
compatibility.d/zol-0.7 \
|
||||
compatibility.d/zol-0.8
|
||||
|
||||
# canonical <- alias symbolic link pairs
|
||||
# eg: "2018" is a link to "compat-2018"
|
||||
zpoolcompatlinks = \
|
||||
"compat-2018 2018" \
|
||||
"compat-2019 2019" \
|
||||
"compat-2020 2020" \
|
||||
"compat-2021 2021" \
|
||||
"freebsd-11.0 freebsd-11.1" \
|
||||
"freebsd-11.0 freenas-11.0" \
|
||||
"freebsd-11.2 freenas-11.2" \
|
||||
"freebsd-11.3 freebsd-11.4" \
|
||||
"freebsd-11.3 freebsd-12.0" \
|
||||
"freebsd-11.3 freebsd-12.1" \
|
||||
"freebsd-11.3 freebsd-12.2" \
|
||||
"freebsd-11.3 freenas-11.3" \
|
||||
"freenas-11.0 freenas-11.1" \
|
||||
"openzfsonosx-1.9.3 openzfsonosx-1.9.4" \
|
||||
"openzfs-2.0-freebsd truenas-12.0" \
|
||||
"zol-0.7 ubuntu-18.04" \
|
||||
"zol-0.8 ubuntu-20.04"
|
||||
|
||||
install-data-hook:
|
||||
$(MKDIR_P) "$(DESTDIR)$(zpoolconfdir)"
|
||||
for f in $(zpoolconfdefaults); do \
|
||||
@ -136,3 +178,6 @@ install-data-hook:
|
||||
-L "$(DESTDIR)$(zpoolconfdir)/$${f}" || \
|
||||
ln -s "$(zpoolexecdir)/$${f}" "$(DESTDIR)$(zpoolconfdir)"; \
|
||||
done
|
||||
for l in $(zpoolcompatlinks); do \
|
||||
(cd "$(DESTDIR)$(zpoolcompatdir)"; ln -s $${l} ); \
|
||||
done
|
||||
|
12
sys/contrib/openzfs/cmd/zpool/compatibility.d/compat-2018
Normal file
12
sys/contrib/openzfs/cmd/zpool/compatibility.d/compat-2018
Normal file
@ -0,0 +1,12 @@
|
||||
# Features supported by all Tier 1 platforms as of 2018
|
||||
async_destroy
|
||||
bookmarks
|
||||
embedded_data
|
||||
empty_bpobj
|
||||
enabled_txg
|
||||
extensible_dataset
|
||||
filesystem_limits
|
||||
hole_birth
|
||||
large_blocks
|
||||
lz4_compress
|
||||
spacemap_histogram
|
15
sys/contrib/openzfs/cmd/zpool/compatibility.d/compat-2019
Normal file
15
sys/contrib/openzfs/cmd/zpool/compatibility.d/compat-2019
Normal file
@ -0,0 +1,15 @@
|
||||
# Features supported by all Tier 1 platforms as of 2019
|
||||
async_destroy
|
||||
bookmarks
|
||||
embedded_data
|
||||
empty_bpobj
|
||||
enabled_txg
|
||||
extensible_dataset
|
||||
filesystem_limits
|
||||
hole_birth
|
||||
large_blocks
|
||||
lz4_compress
|
||||
multi_vdev_crash_dump
|
||||
sha512
|
||||
skein
|
||||
spacemap_histogram
|
15
sys/contrib/openzfs/cmd/zpool/compatibility.d/compat-2020
Normal file
15
sys/contrib/openzfs/cmd/zpool/compatibility.d/compat-2020
Normal file
@ -0,0 +1,15 @@
|
||||
# Features supported by all Tier 1 platforms as of 2020
|
||||
async_destroy
|
||||
bookmarks
|
||||
embedded_data
|
||||
empty_bpobj
|
||||
enabled_txg
|
||||
extensible_dataset
|
||||
filesystem_limits
|
||||
hole_birth
|
||||
large_blocks
|
||||
lz4_compress
|
||||
multi_vdev_crash_dump
|
||||
sha512
|
||||
skein
|
||||
spacemap_histogram
|
19
sys/contrib/openzfs/cmd/zpool/compatibility.d/compat-2021
Normal file
19
sys/contrib/openzfs/cmd/zpool/compatibility.d/compat-2021
Normal file
@ -0,0 +1,19 @@
|
||||
# Features supported by all Tier 1 platforms as of 2021
|
||||
async_destroy
|
||||
bookmarks
|
||||
device_removal
|
||||
embedded_data
|
||||
empty_bpobj
|
||||
enabled_txg
|
||||
extensible_dataset
|
||||
filesystem_limits
|
||||
hole_birth
|
||||
large_blocks
|
||||
lz4_compress
|
||||
multi_vdev_crash_dump
|
||||
obsolete_counts
|
||||
sha512
|
||||
skein
|
||||
spacemap_histogram
|
||||
spacemap_v2
|
||||
zpool_checkpoint
|
15
sys/contrib/openzfs/cmd/zpool/compatibility.d/freebsd-11.0
Normal file
15
sys/contrib/openzfs/cmd/zpool/compatibility.d/freebsd-11.0
Normal file
@ -0,0 +1,15 @@
|
||||
# Features supported by FreeBSD 11.0
|
||||
async_destroy
|
||||
bookmarks
|
||||
embedded_data
|
||||
empty_bpobj
|
||||
enabled_txg
|
||||
extensible_dataset
|
||||
filesystem_limits
|
||||
hole_birth
|
||||
large_blocks
|
||||
lz4_compress
|
||||
multi_vdev_crash_dump
|
||||
sha512
|
||||
skein
|
||||
spacemap_histogram
|
18
sys/contrib/openzfs/cmd/zpool/compatibility.d/freebsd-11.2
Normal file
18
sys/contrib/openzfs/cmd/zpool/compatibility.d/freebsd-11.2
Normal file
@ -0,0 +1,18 @@
|
||||
# Features supported by FreeBSD 11.2
|
||||
async_destroy
|
||||
bookmarks
|
||||
device_removal
|
||||
embedded_data
|
||||
empty_bpobj
|
||||
enabled_txg
|
||||
extensible_dataset
|
||||
filesystem_limits
|
||||
hole_birth
|
||||
large_blocks
|
||||
lz4_compress
|
||||
multi_vdev_crash_dump
|
||||
obsolete_counts
|
||||
sha512
|
||||
skein
|
||||
spacemap_histogram
|
||||
zpool_checkpoint
|
19
sys/contrib/openzfs/cmd/zpool/compatibility.d/freebsd-11.3
Normal file
19
sys/contrib/openzfs/cmd/zpool/compatibility.d/freebsd-11.3
Normal file
@ -0,0 +1,19 @@
|
||||
# Features supported by FreeBSD 11.3
|
||||
async_destroy
|
||||
bookmarks
|
||||
device_removal
|
||||
embedded_data
|
||||
empty_bpobj
|
||||
enabled_txg
|
||||
extensible_dataset
|
||||
filesystem_limits
|
||||
hole_birth
|
||||
large_blocks
|
||||
lz4_compress
|
||||
multi_vdev_crash_dump
|
||||
obsolete_counts
|
||||
sha512
|
||||
skein
|
||||
spacemap_histogram
|
||||
spacemap_v2
|
||||
zpool_checkpoint
|
13
sys/contrib/openzfs/cmd/zpool/compatibility.d/freenas-9.10.2
Normal file
13
sys/contrib/openzfs/cmd/zpool/compatibility.d/freenas-9.10.2
Normal file
@ -0,0 +1,13 @@
|
||||
# Features supported by FreeNAS 9.10.2
|
||||
async_destroy
|
||||
bookmarks
|
||||
embedded_data
|
||||
empty_bpobj
|
||||
enabled_txg
|
||||
extensible_dataset
|
||||
filesystem_limits
|
||||
hole_birth
|
||||
large_blocks
|
||||
lz4_compress
|
||||
multi_vdev_crash_dump
|
||||
spacemap_histogram
|
12
sys/contrib/openzfs/cmd/zpool/compatibility.d/grub2
Normal file
12
sys/contrib/openzfs/cmd/zpool/compatibility.d/grub2
Normal file
@ -0,0 +1,12 @@
|
||||
# Features which are supported by GRUB2
|
||||
async_destroy
|
||||
bookmarks
|
||||
embedded_data
|
||||
empty_bpobj
|
||||
enabled_txg
|
||||
extensible_dataset
|
||||
filesystem_limits
|
||||
hole_birth
|
||||
large_blocks
|
||||
lz4_compress
|
||||
spacemap_histogram
|
@ -0,0 +1,33 @@
|
||||
# Features supported by OpenZFS 2.0 on FreeBSD
|
||||
allocation_classes
|
||||
async_destroy
|
||||
bookmark_v2
|
||||
bookmark_written
|
||||
bookmarks
|
||||
device_rebuild
|
||||
device_removal
|
||||
embedded_data
|
||||
empty_bpobj
|
||||
enabled_txg
|
||||
encryption
|
||||
extensible_dataset
|
||||
filesystem_limits
|
||||
hole_birth
|
||||
large_blocks
|
||||
large_dnode
|
||||
livelist
|
||||
log_spacemap
|
||||
lz4_compress
|
||||
multi_vdev_crash_dump
|
||||
obsolete_counts
|
||||
project_quota
|
||||
redacted_datasets
|
||||
redaction_bookmarks
|
||||
resilver_defer
|
||||
sha512
|
||||
skein
|
||||
spacemap_histogram
|
||||
spacemap_v2
|
||||
userobj_accounting
|
||||
zpool_checkpoint
|
||||
zstd_compress
|
@ -0,0 +1,34 @@
|
||||
# Features supported by OpenZFS 2.0 on Linux
|
||||
allocation_classes
|
||||
async_destroy
|
||||
bookmark_v2
|
||||
bookmark_written
|
||||
bookmarks
|
||||
device_rebuild
|
||||
device_removal
|
||||
edonr
|
||||
embedded_data
|
||||
empty_bpobj
|
||||
enabled_txg
|
||||
encryption
|
||||
extensible_dataset
|
||||
filesystem_limits
|
||||
hole_birth
|
||||
large_blocks
|
||||
large_dnode
|
||||
livelist
|
||||
log_spacemap
|
||||
lz4_compress
|
||||
multi_vdev_crash_dump
|
||||
obsolete_counts
|
||||
project_quota
|
||||
redacted_datasets
|
||||
redaction_bookmarks
|
||||
resilver_defer
|
||||
sha512
|
||||
skein
|
||||
spacemap_histogram
|
||||
spacemap_v2
|
||||
userobj_accounting
|
||||
zpool_checkpoint
|
||||
zstd_compress
|
@ -0,0 +1,16 @@
|
||||
# Features supported by OpenZFSonOSX 1.7.0
|
||||
async_destroy
|
||||
bookmarks
|
||||
edonr
|
||||
embedded_data
|
||||
empty_bpobj
|
||||
enabled_txg
|
||||
extensible_dataset
|
||||
filesystem_limits
|
||||
hole_birth
|
||||
large_blocks
|
||||
lz4_compress
|
||||
multi_vdev_crash_dump
|
||||
sha512
|
||||
skein
|
||||
spacemap_histogram
|
@ -0,0 +1,21 @@
|
||||
# Features supported by OpenZFSonOSX 1.8.1
|
||||
async_destroy
|
||||
bookmarks
|
||||
device_removal
|
||||
edonr
|
||||
embedded_data
|
||||
empty_bpobj
|
||||
enabled_txg
|
||||
encryption
|
||||
extensible_dataset
|
||||
filesystem_limits
|
||||
hole_birth
|
||||
large_blocks
|
||||
lz4_compress
|
||||
multi_vdev_crash_dump
|
||||
obsolete_counts
|
||||
sha512
|
||||
skein
|
||||
spacemap_histogram
|
||||
spacemap_v2
|
||||
zpool_checkpoint
|
@ -0,0 +1,27 @@
|
||||
# Features supported by OpenZFSonOSX 1.9.3
|
||||
allocation_classes
|
||||
async_destroy
|
||||
bookmark_v2
|
||||
bookmarks
|
||||
device_removal
|
||||
edonr
|
||||
embedded_data
|
||||
empty_bpobj
|
||||
enabled_txg
|
||||
encryption
|
||||
extensible_dataset
|
||||
filesystem_limits
|
||||
hole_birth
|
||||
large_blocks
|
||||
large_dnode
|
||||
lz4_compress
|
||||
multi_vdev_crash_dump
|
||||
obsolete_counts
|
||||
project_quota
|
||||
resilver_defer
|
||||
sha512
|
||||
skein
|
||||
spacemap_histogram
|
||||
spacemap_v2
|
||||
userobj_accounting
|
||||
zpool_checkpoint
|
12
sys/contrib/openzfs/cmd/zpool/compatibility.d/zol-0.6.5
Normal file
12
sys/contrib/openzfs/cmd/zpool/compatibility.d/zol-0.6.5
Normal file
@ -0,0 +1,12 @@
|
||||
# Features supported by ZFSonLinux v0.6.5
|
||||
async_destroy
|
||||
bookmarks
|
||||
embedded_data
|
||||
empty_bpobj
|
||||
enabled_txg
|
||||
extensible_dataset
|
||||
filesystem_limits
|
||||
hole_birth
|
||||
large_blocks
|
||||
lz4_compress
|
||||
spacemap_histogram
|
18
sys/contrib/openzfs/cmd/zpool/compatibility.d/zol-0.7
Normal file
18
sys/contrib/openzfs/cmd/zpool/compatibility.d/zol-0.7
Normal file
@ -0,0 +1,18 @@
|
||||
# Features supported by ZFSonLinux v0.7
|
||||
async_destroy
|
||||
bookmarks
|
||||
edonr
|
||||
embedded_data
|
||||
empty_bpobj
|
||||
enabled_txg
|
||||
extensible_dataset
|
||||
filesystem_limits
|
||||
hole_birth
|
||||
large_blocks
|
||||
large_dnode
|
||||
lz4_compress
|
||||
multi_vdev_crash_dump
|
||||
sha512
|
||||
skein
|
||||
spacemap_histogram
|
||||
userobj_accounting
|
27
sys/contrib/openzfs/cmd/zpool/compatibility.d/zol-0.8
Normal file
27
sys/contrib/openzfs/cmd/zpool/compatibility.d/zol-0.8
Normal file
@ -0,0 +1,27 @@
|
||||
# Features supported by ZFSonLinux v0.8
|
||||
allocation_classes
|
||||
async_destroy
|
||||
bookmark_v2
|
||||
bookmarks
|
||||
device_removal
|
||||
edonr
|
||||
embedded_data
|
||||
empty_bpobj
|
||||
enabled_txg
|
||||
encryption
|
||||
extensible_dataset
|
||||
filesystem_limits
|
||||
hole_birth
|
||||
large_blocks
|
||||
large_dnode
|
||||
lz4_compress
|
||||
multi_vdev_crash_dump
|
||||
obsolete_counts
|
||||
project_quota
|
||||
resilver_defer
|
||||
sha512
|
||||
skein
|
||||
spacemap_histogram
|
||||
spacemap_v2
|
||||
userobj_accounting
|
||||
zpool_checkpoint
|
@ -31,6 +31,7 @@
|
||||
* Copyright (c) 2017 Open-E, Inc. All Rights Reserved.
|
||||
* Copyright (c) 2017, Intel Corporation.
|
||||
* Copyright (c) 2019, loli10K <ezomori.nozomu@gmail.com>
|
||||
* Copyright (c) 2021, Colm Buckley <colm@tuatha.org>
|
||||
*/
|
||||
|
||||
#include <assert.h>
|
||||
@ -124,6 +125,9 @@ static int zpool_do_version(int, char **);
|
||||
|
||||
static int zpool_do_wait(int, char **);
|
||||
|
||||
static zpool_compat_status_t zpool_do_load_compat(
|
||||
const char *, boolean_t *);
|
||||
|
||||
/*
|
||||
* These libumem hooks provide a reasonable set of defaults for the allocator's
|
||||
* debugging facilities.
|
||||
@ -782,6 +786,8 @@ add_prop_list(const char *propname, char *propval, nvlist_t **props,
|
||||
|
||||
if (poolprop) {
|
||||
const char *vname = zpool_prop_to_name(ZPOOL_PROP_VERSION);
|
||||
const char *fname =
|
||||
zpool_prop_to_name(ZPOOL_PROP_COMPATIBILITY);
|
||||
|
||||
if ((prop = zpool_name_to_prop(propname)) == ZPOOL_PROP_INVAL &&
|
||||
!zpool_prop_feature(propname)) {
|
||||
@ -804,6 +810,19 @@ add_prop_list(const char *propname, char *propval, nvlist_t **props,
|
||||
return (2);
|
||||
}
|
||||
|
||||
/*
|
||||
* compatibility property and version should not be specified
|
||||
* at the same time.
|
||||
*/
|
||||
if ((prop == ZPOOL_PROP_COMPATIBILITY &&
|
||||
nvlist_exists(proplist, vname)) ||
|
||||
(prop == ZPOOL_PROP_VERSION &&
|
||||
nvlist_exists(proplist, fname))) {
|
||||
(void) fprintf(stderr, gettext("'compatibility' and "
|
||||
"'version' properties cannot be specified "
|
||||
"together\n"));
|
||||
return (2);
|
||||
}
|
||||
|
||||
if (zpool_prop_feature(propname))
|
||||
normnm = propname;
|
||||
@ -1374,13 +1393,15 @@ zpool_do_create(int argc, char **argv)
|
||||
{
|
||||
boolean_t force = B_FALSE;
|
||||
boolean_t dryrun = B_FALSE;
|
||||
boolean_t enable_all_pool_feat = B_TRUE;
|
||||
boolean_t enable_pool_features = B_TRUE;
|
||||
|
||||
int c;
|
||||
nvlist_t *nvroot = NULL;
|
||||
char *poolname;
|
||||
char *tname = NULL;
|
||||
int ret = 1;
|
||||
char *altroot = NULL;
|
||||
char *compat = NULL;
|
||||
char *mountpoint = NULL;
|
||||
nvlist_t *fsprops = NULL;
|
||||
nvlist_t *props = NULL;
|
||||
@ -1396,7 +1417,7 @@ zpool_do_create(int argc, char **argv)
|
||||
dryrun = B_TRUE;
|
||||
break;
|
||||
case 'd':
|
||||
enable_all_pool_feat = B_FALSE;
|
||||
enable_pool_features = B_FALSE;
|
||||
break;
|
||||
case 'R':
|
||||
altroot = optarg;
|
||||
@ -1434,11 +1455,14 @@ zpool_do_create(int argc, char **argv)
|
||||
ver = strtoull(propval, &end, 10);
|
||||
if (*end == '\0' &&
|
||||
ver < SPA_VERSION_FEATURES) {
|
||||
enable_all_pool_feat = B_FALSE;
|
||||
enable_pool_features = B_FALSE;
|
||||
}
|
||||
}
|
||||
if (zpool_name_to_prop(optarg) == ZPOOL_PROP_ALTROOT)
|
||||
altroot = propval;
|
||||
if (zpool_name_to_prop(optarg) ==
|
||||
ZPOOL_PROP_COMPATIBILITY)
|
||||
compat = propval;
|
||||
break;
|
||||
case 'O':
|
||||
if ((propval = strchr(optarg, '=')) == NULL) {
|
||||
@ -1632,10 +1656,26 @@ zpool_do_create(int argc, char **argv)
|
||||
ret = 0;
|
||||
} else {
|
||||
/*
|
||||
* Hand off to libzfs.
|
||||
* Load in feature set.
|
||||
* Note: if compatibility property not given, we'll have
|
||||
* NULL, which means 'all features'.
|
||||
*/
|
||||
spa_feature_t i;
|
||||
for (i = 0; i < SPA_FEATURES; i++) {
|
||||
boolean_t requested_features[SPA_FEATURES];
|
||||
if (zpool_do_load_compat(compat, requested_features) !=
|
||||
ZPOOL_COMPATIBILITY_OK)
|
||||
goto errout;
|
||||
|
||||
/*
|
||||
* props contains list of features to enable.
|
||||
* For each feature:
|
||||
* - remove it if feature@name=disabled
|
||||
* - leave it there if feature@name=enabled
|
||||
* - add it if:
|
||||
* - enable_pool_features (ie: no '-d' or '-o version')
|
||||
* - it's supported by the kernel module
|
||||
* - it's in the requested feature set
|
||||
*/
|
||||
for (spa_feature_t i = 0; i < SPA_FEATURES; i++) {
|
||||
char propname[MAXPATHLEN];
|
||||
char *propval;
|
||||
zfeature_info_t *feat = &spa_feature_table[i];
|
||||
@ -1643,18 +1683,14 @@ zpool_do_create(int argc, char **argv)
|
||||
(void) snprintf(propname, sizeof (propname),
|
||||
"feature@%s", feat->fi_uname);
|
||||
|
||||
/*
|
||||
* Only features contained in props will be enabled:
|
||||
* remove from the nvlist every ZFS_FEATURE_DISABLED
|
||||
* value and add every missing ZFS_FEATURE_ENABLED if
|
||||
* enable_all_pool_feat is set.
|
||||
*/
|
||||
if (!nvlist_lookup_string(props, propname, &propval)) {
|
||||
if (strcmp(propval, ZFS_FEATURE_DISABLED) == 0)
|
||||
(void) nvlist_remove_all(props,
|
||||
propname);
|
||||
} else if (enable_all_pool_feat &&
|
||||
feat->fi_zfs_mod_supported) {
|
||||
} else if (
|
||||
enable_pool_features &&
|
||||
feat->fi_zfs_mod_supported &&
|
||||
requested_features[i]) {
|
||||
ret = add_prop_list(propname,
|
||||
ZFS_FEATURE_ENABLED, &props, B_TRUE);
|
||||
if (ret != 0)
|
||||
@ -2674,8 +2710,15 @@ show_import(nvlist_t *config)
|
||||
|
||||
case ZPOOL_STATUS_FEAT_DISABLED:
|
||||
printf_color(ANSI_BOLD, gettext("status: "));
|
||||
printf_color(ANSI_YELLOW, gettext("Some supported features are "
|
||||
"not enabled on the pool.\n"));
|
||||
printf_color(ANSI_YELLOW, gettext("Some supported and "
|
||||
"requested features are not enabled on the pool.\n"));
|
||||
break;
|
||||
|
||||
case ZPOOL_STATUS_COMPATIBILITY_ERR:
|
||||
printf_color(ANSI_BOLD, gettext("status: "));
|
||||
printf_color(ANSI_YELLOW, gettext("Error reading or parsing "
|
||||
"the file(s) indicated by the 'compatibility'\n"
|
||||
"property.\n"));
|
||||
break;
|
||||
|
||||
case ZPOOL_STATUS_UNSUP_FEAT_READ:
|
||||
@ -2767,6 +2810,12 @@ show_import(nvlist_t *config)
|
||||
"imported using its name or numeric identifier, "
|
||||
"though\n\tsome features will not be available "
|
||||
"without an explicit 'zpool upgrade'.\n"));
|
||||
} else if (reason == ZPOOL_STATUS_COMPATIBILITY_ERR) {
|
||||
(void) printf(gettext(" action: The pool can be "
|
||||
"imported using its name or numeric\n\tidentifier, "
|
||||
"though the file(s) indicated by its "
|
||||
"'compatibility'\n\tproperty cannot be parsed at "
|
||||
"this time.\n"));
|
||||
} else if (reason == ZPOOL_STATUS_HOSTID_MISMATCH) {
|
||||
(void) printf(gettext(" action: The pool can be "
|
||||
"imported using its name or numeric "
|
||||
@ -7942,7 +7991,8 @@ status_callback(zpool_handle_t *zhp, void *data)
|
||||
if (cbp->cb_explain &&
|
||||
(reason == ZPOOL_STATUS_OK ||
|
||||
reason == ZPOOL_STATUS_VERSION_OLDER ||
|
||||
reason == ZPOOL_STATUS_FEAT_DISABLED)) {
|
||||
reason == ZPOOL_STATUS_FEAT_DISABLED ||
|
||||
reason == ZPOOL_STATUS_COMPATIBILITY_ERR)) {
|
||||
if (!cbp->cb_allpools) {
|
||||
(void) printf(gettext("pool '%s' is healthy\n"),
|
||||
zpool_get_name(zhp));
|
||||
@ -8117,9 +8167,10 @@ status_callback(zpool_handle_t *zhp, void *data)
|
||||
|
||||
case ZPOOL_STATUS_FEAT_DISABLED:
|
||||
printf_color(ANSI_BOLD, gettext("status: "));
|
||||
printf_color(ANSI_YELLOW, gettext("Some supported features are "
|
||||
"not enabled on the pool. The pool can\n\tstill be used, "
|
||||
"but some features are unavailable.\n"));
|
||||
printf_color(ANSI_YELLOW, gettext("Some supported and "
|
||||
"requested features are not enabled on the pool.\n\t"
|
||||
"The pool can still be used, but some features are "
|
||||
"unavailable.\n"));
|
||||
printf_color(ANSI_BOLD, gettext("action: "));
|
||||
printf_color(ANSI_YELLOW, gettext("Enable all features using "
|
||||
"'zpool upgrade'. Once this is done,\n\tthe pool may no "
|
||||
@ -8127,6 +8178,19 @@ status_callback(zpool_handle_t *zhp, void *data)
|
||||
"the features. See zpool-features(5) for details.\n"));
|
||||
break;
|
||||
|
||||
case ZPOOL_STATUS_COMPATIBILITY_ERR:
|
||||
printf_color(ANSI_BOLD, gettext("status: "));
|
||||
printf_color(ANSI_YELLOW, gettext("This pool has a "
|
||||
"compatibility list specified, but it could not be\n\t"
|
||||
"read/parsed at this time. The pool can still be used, "
|
||||
"but this\n\tshould be investigated.\n"));
|
||||
printf_color(ANSI_BOLD, gettext("action: "));
|
||||
printf_color(ANSI_YELLOW, gettext("Check the value of the "
|
||||
"'compatibility' property against the\n\t"
|
||||
"appropriate file in " ZPOOL_SYSCONF_COMPAT_D " or "
|
||||
ZPOOL_DATA_COMPAT_D ".\n"));
|
||||
break;
|
||||
|
||||
case ZPOOL_STATUS_UNSUP_FEAT_READ:
|
||||
printf_color(ANSI_BOLD, gettext("status: "));
|
||||
printf_color(ANSI_YELLOW, gettext("The pool cannot be accessed "
|
||||
@ -8625,11 +8689,25 @@ upgrade_enable_all(zpool_handle_t *zhp, int *countp)
|
||||
boolean_t firstff = B_TRUE;
|
||||
nvlist_t *enabled = zpool_get_features(zhp);
|
||||
|
||||
char compat[ZFS_MAXPROPLEN];
|
||||
if (zpool_get_prop(zhp, ZPOOL_PROP_COMPATIBILITY, compat,
|
||||
ZFS_MAXPROPLEN, NULL, B_FALSE) != 0)
|
||||
compat[0] = '\0';
|
||||
|
||||
boolean_t requested_features[SPA_FEATURES];
|
||||
if (zpool_do_load_compat(compat, requested_features) !=
|
||||
ZPOOL_COMPATIBILITY_OK)
|
||||
return (-1);
|
||||
|
||||
count = 0;
|
||||
for (i = 0; i < SPA_FEATURES; i++) {
|
||||
const char *fname = spa_feature_table[i].fi_uname;
|
||||
const char *fguid = spa_feature_table[i].fi_guid;
|
||||
if (!nvlist_exists(enabled, fguid)) {
|
||||
|
||||
if (!spa_feature_table[i].fi_zfs_mod_supported)
|
||||
continue;
|
||||
|
||||
if (!nvlist_exists(enabled, fguid) && requested_features[i]) {
|
||||
char *propname;
|
||||
verify(-1 != asprintf(&propname, "feature@%s", fname));
|
||||
ret = zpool_set_prop(zhp, propname,
|
||||
@ -8759,6 +8837,10 @@ upgrade_list_disabled_cb(zpool_handle_t *zhp, void *arg)
|
||||
for (i = 0; i < SPA_FEATURES; i++) {
|
||||
const char *fguid = spa_feature_table[i].fi_guid;
|
||||
const char *fname = spa_feature_table[i].fi_uname;
|
||||
|
||||
if (!spa_feature_table[i].fi_zfs_mod_supported)
|
||||
continue;
|
||||
|
||||
if (!nvlist_exists(enabled, fguid)) {
|
||||
if (cbp->cb_first) {
|
||||
(void) printf(gettext("\nSome "
|
||||
@ -8847,7 +8929,7 @@ upgrade_one(zpool_handle_t *zhp, void *data)
|
||||
printnl = B_TRUE;
|
||||
} else if (cur_version == SPA_VERSION) {
|
||||
(void) printf(gettext("Pool '%s' already has all "
|
||||
"supported features enabled.\n"),
|
||||
"supported and requested features enabled.\n"),
|
||||
zpool_get_name(zhp));
|
||||
}
|
||||
}
|
||||
@ -9008,8 +9090,8 @@ zpool_do_upgrade(int argc, char **argv)
|
||||
(void) printf(gettext("All pools are already "
|
||||
"formatted using feature flags.\n\n"));
|
||||
(void) printf(gettext("Every feature flags "
|
||||
"pool already has all supported features "
|
||||
"enabled.\n"));
|
||||
"pool already has all supported and "
|
||||
"requested features enabled.\n"));
|
||||
} else {
|
||||
(void) printf(gettext("All pools are already "
|
||||
"formatted with version %llu or higher.\n"),
|
||||
@ -9035,7 +9117,7 @@ zpool_do_upgrade(int argc, char **argv)
|
||||
|
||||
if (cb.cb_first) {
|
||||
(void) printf(gettext("Every feature flags pool has "
|
||||
"all supported features enabled.\n"));
|
||||
"all supported and requested features enabled.\n"));
|
||||
} else {
|
||||
(void) printf(gettext("\n"));
|
||||
}
|
||||
@ -10339,6 +10421,39 @@ zpool_do_version(int argc, char **argv)
|
||||
return (0);
|
||||
}
|
||||
|
||||
/*
|
||||
* Do zpool_load_compat() and print error message on failure
|
||||
*/
|
||||
static zpool_compat_status_t
|
||||
zpool_do_load_compat(const char *compat, boolean_t *list)
|
||||
{
|
||||
char badword[ZFS_MAXPROPLEN];
|
||||
char badfile[MAXPATHLEN];
|
||||
zpool_compat_status_t ret;
|
||||
|
||||
switch (ret = zpool_load_compat(compat, list, badword, badfile)) {
|
||||
case ZPOOL_COMPATIBILITY_OK:
|
||||
break;
|
||||
case ZPOOL_COMPATIBILITY_READERR:
|
||||
(void) fprintf(stderr, gettext("error reading compatibility "
|
||||
"file '%s'\n"), badfile);
|
||||
break;
|
||||
case ZPOOL_COMPATIBILITY_BADFILE:
|
||||
(void) fprintf(stderr, gettext("compatibility file '%s' "
|
||||
"too large or not newline-terminated\n"), badfile);
|
||||
break;
|
||||
case ZPOOL_COMPATIBILITY_BADWORD:
|
||||
(void) fprintf(stderr, gettext("unknown feature '%s' in "
|
||||
"compatibility file '%s'\n"), badword, badfile);
|
||||
break;
|
||||
case ZPOOL_COMPATIBILITY_NOFILES:
|
||||
(void) fprintf(stderr, gettext("no compatibility files "
|
||||
"specified\n"));
|
||||
break;
|
||||
}
|
||||
return (ret);
|
||||
}
|
||||
|
||||
int
|
||||
main(int argc, char **argv)
|
||||
{
|
||||
|
@ -133,7 +133,7 @@
|
||||
#include <libnvpair.h>
|
||||
#include <libzutil.h>
|
||||
#include <sys/crypto/icp.h>
|
||||
#ifdef __GLIBC__
|
||||
#if (__GLIBC__ && !__UCLIBC__)
|
||||
#include <execinfo.h> /* for backtrace() */
|
||||
#endif
|
||||
|
||||
@ -563,7 +563,7 @@ dump_debug_buffer(void)
|
||||
static void sig_handler(int signo)
|
||||
{
|
||||
struct sigaction action;
|
||||
#ifdef __GLIBC__ /* backtrace() is a GNU extension */
|
||||
#if (__GLIBC__ && !__UCLIBC__) /* backtrace() is a GNU extension */
|
||||
int nptrs;
|
||||
void *buffer[BACKTRACE_SZ];
|
||||
|
||||
|
@ -44,6 +44,7 @@ AM_CPPFLAGS += -DLIBEXECDIR=\"$(libexecdir)\"
|
||||
AM_CPPFLAGS += -DRUNSTATEDIR=\"$(runstatedir)\"
|
||||
AM_CPPFLAGS += -DSBINDIR=\"$(sbindir)\"
|
||||
AM_CPPFLAGS += -DSYSCONFDIR=\"$(sysconfdir)\"
|
||||
AM_CPPFLAGS += -DPKGDATADIR=\"$(pkgdatadir)\"
|
||||
AM_CPPFLAGS += $(DEBUG_CPPFLAGS)
|
||||
AM_CPPFLAGS += $(CODE_COVERAGE_CPPFLAGS)
|
||||
if BUILD_LINUX
|
||||
|
@ -28,6 +28,7 @@
|
||||
* Copyright 2016 Nexenta Systems, Inc.
|
||||
* Copyright (c) 2017 Open-E, Inc. All Rights Reserved.
|
||||
* Copyright (c) 2019 Datto Inc.
|
||||
* Copyright (c) 2021, Colm Buckley <colm@tuatha.org>
|
||||
*/
|
||||
|
||||
#ifndef _LIBZFS_H
|
||||
@ -391,6 +392,7 @@ typedef enum {
|
||||
ZPOOL_STATUS_REBUILDING, /* device being rebuilt */
|
||||
ZPOOL_STATUS_REBUILD_SCRUB, /* recommend scrubbing the pool */
|
||||
ZPOOL_STATUS_NON_NATIVE_ASHIFT, /* (e.g. 512e dev with ashift of 9) */
|
||||
ZPOOL_STATUS_COMPATIBILITY_ERR, /* bad 'compatibility' property */
|
||||
|
||||
/*
|
||||
* Finally, the following indicates a healthy pool.
|
||||
@ -912,6 +914,20 @@ int zfs_smb_acl_rename(libzfs_handle_t *, char *, char *, char *, char *);
|
||||
extern int zpool_enable_datasets(zpool_handle_t *, const char *, int);
|
||||
extern int zpool_disable_datasets(zpool_handle_t *, boolean_t);
|
||||
|
||||
/*
|
||||
* Parse a features file for -o compatibility
|
||||
*/
|
||||
typedef enum {
|
||||
ZPOOL_COMPATIBILITY_OK,
|
||||
ZPOOL_COMPATIBILITY_READERR,
|
||||
ZPOOL_COMPATIBILITY_BADFILE,
|
||||
ZPOOL_COMPATIBILITY_BADWORD,
|
||||
ZPOOL_COMPATIBILITY_NOFILES
|
||||
} zpool_compat_status_t;
|
||||
|
||||
extern zpool_compat_status_t zpool_load_compat(const char *,
|
||||
boolean_t *, char *, char *);
|
||||
|
||||
#ifdef __FreeBSD__
|
||||
|
||||
/*
|
||||
|
@ -27,10 +27,10 @@
|
||||
* Copyright (c) 2014 Integros [integros.com]
|
||||
* Copyright (c) 2017, Intel Corporation.
|
||||
* Copyright (c) 2019 Datto Inc.
|
||||
* Portions Copyright 2010 Robert Milkowski
|
||||
* Copyright (c) 2021, Colm Buckley <colm@tuatha.org>
|
||||
*/
|
||||
|
||||
/* Portions Copyright 2010 Robert Milkowski */
|
||||
|
||||
#ifndef _SYS_FS_ZFS_H
|
||||
#define _SYS_FS_ZFS_H
|
||||
|
||||
@ -246,6 +246,7 @@ typedef enum {
|
||||
ZPOOL_PROP_CHECKPOINT,
|
||||
ZPOOL_PROP_LOAD_GUID,
|
||||
ZPOOL_PROP_AUTOTRIM,
|
||||
ZPOOL_PROP_COMPATIBILITY,
|
||||
ZPOOL_NUM_PROPS
|
||||
} zpool_prop_t;
|
||||
|
||||
@ -733,6 +734,7 @@ typedef struct zpool_load_policy {
|
||||
#define ZPOOL_CONFIG_ALLOCATION_BIAS "alloc_bias" /* not stored on disk */
|
||||
#define ZPOOL_CONFIG_EXPANSION_TIME "expansion_time" /* not stored */
|
||||
#define ZPOOL_CONFIG_REBUILD_STATS "org.openzfs:rebuild_stats"
|
||||
#define ZPOOL_CONFIG_COMPATIBILITY "compatibility"
|
||||
|
||||
/*
|
||||
* The persistent vdev state is stored as separate values rather than a single
|
||||
@ -845,6 +847,19 @@ typedef struct zpool_load_policy {
|
||||
*/
|
||||
#define ZPOOL_CACHE_BOOT "/boot/zfs/zpool.cache"
|
||||
#define ZPOOL_CACHE "/etc/zfs/zpool.cache"
|
||||
/*
|
||||
* Settings for zpool compatibility features files
|
||||
*/
|
||||
#define ZPOOL_SYSCONF_COMPAT_D SYSCONFDIR "/zfs/compatibility.d"
|
||||
#define ZPOOL_DATA_COMPAT_D PKGDATADIR "/compatibility.d"
|
||||
#define ZPOOL_COMPAT_MAXSIZE 16384
|
||||
|
||||
/*
|
||||
* Hard-wired compatibility settings
|
||||
*/
|
||||
#define ZPOOL_COMPAT_LEGACY "legacy"
|
||||
#define ZPOOL_COMPAT_OFF "off"
|
||||
|
||||
/*
|
||||
* vdev states are ordered from least to most healthy.
|
||||
* A vdev that's CANT_OPEN or below is considered unusable.
|
||||
|
@ -424,6 +424,8 @@ struct spa {
|
||||
int spa_waiters; /* number of waiting threads */
|
||||
boolean_t spa_waiters_cancel; /* waiters should return */
|
||||
|
||||
char *spa_compatibility; /* compatibility file(s) */
|
||||
|
||||
/*
|
||||
* spa_refcount & spa_config_lock must be the last elements
|
||||
* because zfs_refcount_t changes size based on compilation options.
|
||||
|
@ -56,9 +56,7 @@ typedef enum spa_feature {
|
||||
SPA_FEATURE_LARGE_DNODE,
|
||||
SPA_FEATURE_SHA512,
|
||||
SPA_FEATURE_SKEIN,
|
||||
#if !defined(__FreeBSD__)
|
||||
SPA_FEATURE_EDONR,
|
||||
#endif
|
||||
SPA_FEATURE_USEROBJ_ACCOUNTING,
|
||||
SPA_FEATURE_ENCRYPTION,
|
||||
SPA_FEATURE_PROJECT_QUOTA,
|
||||
|
File diff suppressed because it is too large
Load Diff
@ -28,6 +28,7 @@
|
||||
* Copyright (c) 2017 Open-E, Inc. All Rights Reserved.
|
||||
* Copyright (c) 2017, Intel Corporation.
|
||||
* Copyright (c) 2018, loli10K <ezomori.nozomu@gmail.com>
|
||||
* Copyright (c) 2021, Colm Buckley <colm@tuatha.org>
|
||||
*/
|
||||
|
||||
#include <errno.h>
|
||||
@ -44,8 +45,12 @@
|
||||
#include <sys/zfs_ioctl.h>
|
||||
#include <sys/zfs_sysfs.h>
|
||||
#include <sys/vdev_disk.h>
|
||||
#include <sys/types.h>
|
||||
#include <dlfcn.h>
|
||||
#include <libzutil.h>
|
||||
#include <fcntl.h>
|
||||
#include <unistd.h>
|
||||
|
||||
#include "zfs_namecheck.h"
|
||||
#include "zfs_prop.h"
|
||||
#include "libzfs_impl.h"
|
||||
@ -302,6 +307,7 @@ zpool_get_prop(zpool_handle_t *zhp, zpool_prop_t prop, char *buf,
|
||||
case ZPOOL_PROP_ALTROOT:
|
||||
case ZPOOL_PROP_CACHEFILE:
|
||||
case ZPOOL_PROP_COMMENT:
|
||||
case ZPOOL_PROP_COMPATIBILITY:
|
||||
if (zhp->zpool_props != NULL ||
|
||||
zpool_get_all_props(zhp) == 0) {
|
||||
(void) strlcpy(buf,
|
||||
@ -462,6 +468,8 @@ zpool_valid_proplist(libzfs_handle_t *hdl, const char *poolname,
|
||||
char *slash, *check;
|
||||
struct stat64 statbuf;
|
||||
zpool_handle_t *zhp;
|
||||
char badword[ZFS_MAXPROPLEN];
|
||||
char badfile[MAXPATHLEN];
|
||||
|
||||
if (nvlist_alloc(&retprops, NV_UNIQUE_NAME, 0) != 0) {
|
||||
(void) no_memory(hdl);
|
||||
@ -671,6 +679,39 @@ zpool_valid_proplist(libzfs_handle_t *hdl, const char *poolname,
|
||||
*slash = '/';
|
||||
break;
|
||||
|
||||
case ZPOOL_PROP_COMPATIBILITY:
|
||||
switch (zpool_load_compat(strval, NULL,
|
||||
badword, badfile)) {
|
||||
case ZPOOL_COMPATIBILITY_OK:
|
||||
break;
|
||||
case ZPOOL_COMPATIBILITY_READERR:
|
||||
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
|
||||
"error reading feature file '%s'"),
|
||||
badfile);
|
||||
(void) zfs_error(hdl, EZFS_BADPROP, errbuf);
|
||||
goto error;
|
||||
case ZPOOL_COMPATIBILITY_BADFILE:
|
||||
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
|
||||
"feature file '%s' too large or not "
|
||||
"newline-terminated"),
|
||||
badfile);
|
||||
(void) zfs_error(hdl, EZFS_BADPROP, errbuf);
|
||||
goto error;
|
||||
case ZPOOL_COMPATIBILITY_BADWORD:
|
||||
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
|
||||
"unknown feature '%s' in feature "
|
||||
"file '%s'"),
|
||||
badword, badfile);
|
||||
(void) zfs_error(hdl, EZFS_BADPROP, errbuf);
|
||||
goto error;
|
||||
case ZPOOL_COMPATIBILITY_NOFILES:
|
||||
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
|
||||
"no feature files specified"));
|
||||
(void) zfs_error(hdl, EZFS_BADPROP, errbuf);
|
||||
goto error;
|
||||
}
|
||||
break;
|
||||
|
||||
case ZPOOL_PROP_COMMENT:
|
||||
for (check = strval; *check != '\0'; check++) {
|
||||
if (!isprint(*check)) {
|
||||
@ -4663,3 +4704,190 @@ zpool_get_bootenv(zpool_handle_t *zhp, nvlist_t **nvlp)
|
||||
|
||||
return (error);
|
||||
}
|
||||
|
||||
/*
|
||||
* Attempt to read and parse feature file(s) (from "compatibility" property).
|
||||
* Files contain zpool feature names, comma or whitespace-separated.
|
||||
* Comments (# character to next newline) are discarded.
|
||||
*
|
||||
* Arguments:
|
||||
* compatibility : string containing feature filenames
|
||||
* features : either NULL or pointer to array of boolean
|
||||
* badtoken : either NULL or pointer to char[ZFS_MAXPROPLEN]
|
||||
* badfile : either NULL or pointer to char[MAXPATHLEN]
|
||||
*
|
||||
* compatibility is NULL (unset), "", "off", "legacy", or list of
|
||||
* comma-separated filenames. filenames should either be absolute,
|
||||
* or relative to:
|
||||
* 1) ZPOOL_SYSCONF_COMPAT_D (eg: /etc/zfs/compatibility.d) or
|
||||
* 2) ZPOOL_DATA_COMPAT_D (eg: /usr/share/zfs/compatibility.d).
|
||||
* (Unset), "" or "off" => enable all features
|
||||
* "legacy" => disable all features
|
||||
* Any feature names read from files which match unames in spa_feature_table
|
||||
* will have the corresponding boolean set in the features array (if non-NULL).
|
||||
* If more than one feature set specified, only features present in *all* of
|
||||
* them will be set.
|
||||
*
|
||||
* An unreadable filename will be strlcpy'd to badfile (if non-NULL).
|
||||
* An unrecognized feature will be strlcpy'd to badtoken (if non-NULL).
|
||||
*
|
||||
* Return values:
|
||||
* ZPOOL_COMPATIBILITY_OK : files read and parsed ok
|
||||
* ZPOOL_COMPATIBILITY_READERR : file could not be opened / mmap'd
|
||||
* ZPOOL_COMPATIBILITY_BADFILE : file too big or not a text file
|
||||
* ZPOOL_COMPATIBILITY_BADWORD : file contains invalid feature name
|
||||
* ZPOOL_COMPATIBILITY_NOFILES : no file names found
|
||||
*/
|
||||
zpool_compat_status_t
|
||||
zpool_load_compat(const char *compatibility,
|
||||
boolean_t *features, char *badtoken, char *badfile)
|
||||
{
|
||||
int sdirfd, ddirfd, featfd;
|
||||
int i;
|
||||
struct stat fs;
|
||||
char *fc; /* mmap of file */
|
||||
char *ps, *ls, *ws; /* strtok state */
|
||||
char *file, *line, *word;
|
||||
char filenames[ZFS_MAXPROPLEN];
|
||||
int filecount = 0;
|
||||
|
||||
/* special cases (unset), "" and "off" => enable all features */
|
||||
if (compatibility == NULL || compatibility[0] == '\0' ||
|
||||
strcmp(compatibility, ZPOOL_COMPAT_OFF) == 0) {
|
||||
if (features != NULL)
|
||||
for (i = 0; i < SPA_FEATURES; i++)
|
||||
features[i] = B_TRUE;
|
||||
return (ZPOOL_COMPATIBILITY_OK);
|
||||
}
|
||||
|
||||
/* Final special case "legacy" => disable all features */
|
||||
if (strcmp(compatibility, ZPOOL_COMPAT_LEGACY) == 0) {
|
||||
if (features != NULL)
|
||||
for (i = 0; i < SPA_FEATURES; i++)
|
||||
features[i] = B_FALSE;
|
||||
return (ZPOOL_COMPATIBILITY_OK);
|
||||
}
|
||||
|
||||
/*
|
||||
* Start with all true; will be ANDed with results from each file
|
||||
*/
|
||||
if (features != NULL)
|
||||
for (i = 0; i < SPA_FEATURES; i++)
|
||||
features[i] = B_TRUE;
|
||||
|
||||
/*
|
||||
* We ignore errors from the directory open()
|
||||
* as they're only needed if the filename is relative
|
||||
* which will be checked during the openat().
|
||||
*/
|
||||
#ifdef O_PATH
|
||||
sdirfd = open(ZPOOL_SYSCONF_COMPAT_D, O_DIRECTORY | O_PATH);
|
||||
ddirfd = open(ZPOOL_DATA_COMPAT_D, O_DIRECTORY | O_PATH);
|
||||
#else
|
||||
sdirfd = open(ZPOOL_SYSCONF_COMPAT_D, O_DIRECTORY | O_RDONLY);
|
||||
ddirfd = open(ZPOOL_DATA_COMPAT_D, O_DIRECTORY | O_RDONLY);
|
||||
#endif
|
||||
|
||||
(void) strlcpy(filenames, compatibility, ZFS_MAXPROPLEN);
|
||||
file = strtok_r(filenames, ",", &ps);
|
||||
while (file != NULL) {
|
||||
boolean_t features_local[SPA_FEATURES];
|
||||
|
||||
/* try sysconfdir first, then datadir */
|
||||
if ((featfd = openat(sdirfd, file, 0, O_RDONLY)) < 0)
|
||||
featfd = openat(ddirfd, file, 0, O_RDONLY);
|
||||
|
||||
if (featfd < 0 || fstat(featfd, &fs) < 0) {
|
||||
(void) close(featfd);
|
||||
(void) close(sdirfd);
|
||||
(void) close(ddirfd);
|
||||
if (badfile != NULL)
|
||||
(void) strlcpy(badfile, file, MAXPATHLEN);
|
||||
return (ZPOOL_COMPATIBILITY_READERR);
|
||||
}
|
||||
|
||||
/* Too big or too small */
|
||||
if (fs.st_size < 1 || fs.st_size > ZPOOL_COMPAT_MAXSIZE) {
|
||||
(void) close(featfd);
|
||||
(void) close(sdirfd);
|
||||
(void) close(ddirfd);
|
||||
if (badfile != NULL)
|
||||
(void) strlcpy(badfile, file, MAXPATHLEN);
|
||||
return (ZPOOL_COMPATIBILITY_BADFILE);
|
||||
}
|
||||
|
||||
/* private mmap() so we can strtok safely */
|
||||
fc = (char *)mmap(NULL, fs.st_size,
|
||||
PROT_READ|PROT_WRITE, MAP_PRIVATE, featfd, 0);
|
||||
(void) close(featfd);
|
||||
|
||||
if (fc < 0) {
|
||||
(void) close(sdirfd);
|
||||
(void) close(ddirfd);
|
||||
if (badfile != NULL)
|
||||
(void) strlcpy(badfile, file, MAXPATHLEN);
|
||||
return (ZPOOL_COMPATIBILITY_READERR);
|
||||
}
|
||||
|
||||
/* Text file sanity check - last char should be newline */
|
||||
if (fc[fs.st_size - 1] != '\n') {
|
||||
(void) munmap((void *) fc, fs.st_size);
|
||||
(void) close(sdirfd);
|
||||
(void) close(ddirfd);
|
||||
if (badfile != NULL)
|
||||
(void) strlcpy(badfile, file, MAXPATHLEN);
|
||||
return (ZPOOL_COMPATIBILITY_BADFILE);
|
||||
}
|
||||
|
||||
/* replace with NUL to ensure we have a delimiter */
|
||||
fc[fs.st_size - 1] = '\0';
|
||||
|
||||
for (i = 0; i < SPA_FEATURES; i++)
|
||||
features_local[i] = B_FALSE;
|
||||
|
||||
line = strtok_r(fc, "\n", &ls);
|
||||
while (line != NULL) {
|
||||
/* discard comments */
|
||||
*(strchrnul(line, '#')) = '\0';
|
||||
|
||||
word = strtok_r(line, ", \t", &ws);
|
||||
while (word != NULL) {
|
||||
/* Find matching feature name */
|
||||
for (i = 0; i < SPA_FEATURES; i++) {
|
||||
zfeature_info_t *fi =
|
||||
&spa_feature_table[i];
|
||||
if (strcmp(word, fi->fi_uname) == 0) {
|
||||
features_local[i] = B_TRUE;
|
||||
break;
|
||||
}
|
||||
}
|
||||
if (i == SPA_FEATURES) {
|
||||
if (badtoken != NULL)
|
||||
(void) strlcpy(badtoken, word,
|
||||
ZFS_MAXPROPLEN);
|
||||
if (badfile != NULL)
|
||||
(void) strlcpy(badfile, file,
|
||||
MAXPATHLEN);
|
||||
(void) munmap((void *) fc, fs.st_size);
|
||||
(void) close(sdirfd);
|
||||
(void) close(ddirfd);
|
||||
return (ZPOOL_COMPATIBILITY_BADWORD);
|
||||
}
|
||||
word = strtok_r(NULL, ", \t", &ws);
|
||||
}
|
||||
line = strtok_r(NULL, "\n", &ls);
|
||||
}
|
||||
(void) munmap((void *) fc, fs.st_size);
|
||||
if (features != NULL) {
|
||||
for (i = 0; i < SPA_FEATURES; i++)
|
||||
features[i] &= features_local[i];
|
||||
}
|
||||
filecount++;
|
||||
file = strtok_r(NULL, ",", &ps);
|
||||
}
|
||||
(void) close(sdirfd);
|
||||
(void) close(ddirfd);
|
||||
if (filecount == 0)
|
||||
return (ZPOOL_COMPATIBILITY_NOFILES);
|
||||
return (ZPOOL_COMPATIBILITY_OK);
|
||||
}
|
||||
|
@ -23,6 +23,7 @@
|
||||
* Copyright (c) 2005, 2010, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2012 by Delphix. All rights reserved.
|
||||
* Copyright (c) 2013 Steven Hartland. All rights reserved.
|
||||
* Copyright (c) 2021, Colm Buckley <colm@tuatha.org>
|
||||
*/
|
||||
|
||||
/*
|
||||
@ -87,6 +88,7 @@ static char *zfs_msgid_table[] = {
|
||||
* ZPOOL_STATUS_REMOVED_DEV
|
||||
* ZPOOL_STATUS_REBUILDING
|
||||
* ZPOOL_STATUS_REBUILD_SCRUB
|
||||
* ZPOOL_STATUS_COMPATIBILITY_ERR
|
||||
* ZPOOL_STATUS_OK
|
||||
*/
|
||||
};
|
||||
@ -218,7 +220,8 @@ find_vdev_problem(nvlist_t *vdev, int (*func)(vdev_stat_t *, uint_t),
|
||||
* only picks the most damaging of all the current errors to report.
|
||||
*/
|
||||
static zpool_status_t
|
||||
check_status(nvlist_t *config, boolean_t isimport, zpool_errata_t *erratap)
|
||||
check_status(nvlist_t *config, boolean_t isimport,
|
||||
zpool_errata_t *erratap, const char *compat)
|
||||
{
|
||||
nvlist_t *nvroot;
|
||||
vdev_stat_t *vs;
|
||||
@ -471,9 +474,16 @@ check_status(nvlist_t *config, boolean_t isimport, zpool_errata_t *erratap)
|
||||
ZPOOL_CONFIG_FEATURE_STATS);
|
||||
}
|
||||
|
||||
/* check against all features, or limited set? */
|
||||
boolean_t pool_features[SPA_FEATURES];
|
||||
|
||||
if (zpool_load_compat(compat, pool_features, NULL, NULL) !=
|
||||
ZPOOL_COMPATIBILITY_OK)
|
||||
return (ZPOOL_STATUS_COMPATIBILITY_ERR);
|
||||
for (i = 0; i < SPA_FEATURES; i++) {
|
||||
zfeature_info_t *fi = &spa_feature_table[i];
|
||||
if (!nvlist_exists(feat, fi->fi_guid))
|
||||
if (pool_features[i] &&
|
||||
!nvlist_exists(feat, fi->fi_guid))
|
||||
return (ZPOOL_STATUS_FEAT_DISABLED);
|
||||
}
|
||||
}
|
||||
@ -484,7 +494,18 @@ check_status(nvlist_t *config, boolean_t isimport, zpool_errata_t *erratap)
|
||||
zpool_status_t
|
||||
zpool_get_status(zpool_handle_t *zhp, char **msgid, zpool_errata_t *errata)
|
||||
{
|
||||
zpool_status_t ret = check_status(zhp->zpool_config, B_FALSE, errata);
|
||||
/*
|
||||
* pass in the desired feature set, as
|
||||
* it affects check for disabled features
|
||||
*/
|
||||
char compatibility[ZFS_MAXPROPLEN];
|
||||
if (zpool_get_prop(zhp, ZPOOL_PROP_COMPATIBILITY, compatibility,
|
||||
ZFS_MAXPROPLEN, NULL, B_FALSE) != 0)
|
||||
compatibility[0] = '\0';
|
||||
|
||||
zpool_status_t ret = check_status(zhp->zpool_config, B_FALSE, errata,
|
||||
compatibility);
|
||||
|
||||
if (msgid != NULL) {
|
||||
if (ret >= NMSGID)
|
||||
*msgid = NULL;
|
||||
@ -497,7 +518,7 @@ zpool_get_status(zpool_handle_t *zhp, char **msgid, zpool_errata_t *errata)
|
||||
zpool_status_t
|
||||
zpool_import_status(nvlist_t *config, char **msgid, zpool_errata_t *errata)
|
||||
{
|
||||
zpool_status_t ret = check_status(config, B_TRUE, errata);
|
||||
zpool_status_t ret = check_status(config, B_TRUE, errata, NULL);
|
||||
|
||||
if (ret >= NMSGID)
|
||||
*msgid = NULL;
|
||||
|
@ -24,6 +24,7 @@
|
||||
* Copyright (c) 2012, 2018 by Delphix. All rights reserved.
|
||||
* Copyright 2015 RackTop Systems.
|
||||
* Copyright (c) 2016, Intel Corporation.
|
||||
* Copyright (c) 2021, Colm Buckley <colm@tuatha.org>
|
||||
*/
|
||||
|
||||
/*
|
||||
@ -552,12 +553,14 @@ get_configs(libpc_handle_t *hdl, pool_list_t *pl, boolean_t active_ok,
|
||||
* pool guid
|
||||
* name
|
||||
* comment (if available)
|
||||
* compatibility features (if available)
|
||||
* pool state
|
||||
* hostid (if available)
|
||||
* hostname (if available)
|
||||
*/
|
||||
uint64_t state, version;
|
||||
char *comment = NULL;
|
||||
char *compatibility = NULL;
|
||||
|
||||
version = fnvlist_lookup_uint64(tmp,
|
||||
ZPOOL_CONFIG_VERSION);
|
||||
@ -577,6 +580,13 @@ get_configs(libpc_handle_t *hdl, pool_list_t *pl, boolean_t active_ok,
|
||||
fnvlist_add_string(config,
|
||||
ZPOOL_CONFIG_COMMENT, comment);
|
||||
|
||||
if (nvlist_lookup_string(tmp,
|
||||
ZPOOL_CONFIG_COMPATIBILITY,
|
||||
&compatibility) == 0)
|
||||
fnvlist_add_string(config,
|
||||
ZPOOL_CONFIG_COMPATIBILITY,
|
||||
compatibility);
|
||||
|
||||
state = fnvlist_lookup_uint64(tmp,
|
||||
ZPOOL_CONFIG_POOL_STATE);
|
||||
fnvlist_add_uint64(config,
|
||||
|
@ -16,6 +16,7 @@
|
||||
.\" Portions Copyright [yyyy] [name of copyright owner]
|
||||
.\" Copyright (c) 2019, Klara Inc.
|
||||
.\" Copyright (c) 2019, Allan Jude
|
||||
.\" Copyright (c) 2021, Colm Buckley <colm@tuatha.org>
|
||||
.TH ZPOOL-FEATURES 5 "Aug 24, 2020" OpenZFS
|
||||
.SH NAME
|
||||
zpool\-features \- ZFS pool feature descriptions
|
||||
@ -26,7 +27,8 @@ ZFS pool on\-disk format versions are specified via "features" which replace
|
||||
the old on\-disk format numbers (the last supported on\-disk format number is
|
||||
28). To enable a feature on a pool use the \fBupgrade\fR subcommand of the
|
||||
zpool(8) command, or set the \fBfeature@\fR\fIfeature_name\fR property
|
||||
to \fBenabled\fR.
|
||||
to \fBenabled\fR. Please also see the \fB"Compatibility feature sets"\fR
|
||||
section for information on how sets of features may be enabled together.
|
||||
.sp
|
||||
.LP
|
||||
The pool format does not affect file system version compatibility or the ability
|
||||
@ -140,6 +142,61 @@ read\-only mode.
|
||||
Some features depend on other features being enabled in order to function
|
||||
properly. Enabling a feature will automatically enable any features it
|
||||
depends on.
|
||||
|
||||
.SS "Compatibility feature sets"
|
||||
.sp
|
||||
.LP
|
||||
It is sometimes necessary for a pool to maintain compatibility with a
|
||||
specific on\-disk format, by enabling and disabling particular features. The
|
||||
\fBcompatibility\fR feature facilitates this by allowing feature sets to
|
||||
be read from text files. When set to \fBoff\fR (the default); compatibility
|
||||
feature sets are disabled (ie: all features are enabled); when set to
|
||||
\fBlegacy\fR; no features are enabled. When set to a comma\-separated list
|
||||
of filenames (each filename may either be an absolute path, or relative to
|
||||
\fB/etc/zfs/compatibility.d\fR or \fB/usr/share/zfs/compatibility.d\fR)
|
||||
the lists of requested features are read from those files, separated by
|
||||
whitespace and/or commas. Only features present in all files are enabled.
|
||||
.LP
|
||||
Simple sanity checks are applied to the files; they must be between 1 and
|
||||
16,384 bytes in size, and must end with a newline character.
|
||||
.LP
|
||||
The requested features are applied when a pool is created using
|
||||
\fBzpool create \-o compatibility=...\fR and controls which features are
|
||||
enabled when using \fBzpool upgrade\fR. \fBzpool status\fR
|
||||
will not show a warning about disabled features which are not part
|
||||
of the requested feature set.
|
||||
.LP
|
||||
By convention, compatibility files in \fB/usr/share/zfs/compatibility.d\fR
|
||||
are provided by the distribution package, and include feature sets
|
||||
supported by important versions of popular distribtions, and feature
|
||||
sets commonly supported at the start of each year. Compatibility files
|
||||
in \fB/etc/zfs/compatibility.d\fR, if present, will take precedence over
|
||||
files with the same name in \fB/usr/share/zfs/compatibility.d\fR.
|
||||
.LP
|
||||
Compatibility files may include comments; any text from \fB#\fR to the end
|
||||
of the line is ignored.
|
||||
.LP
|
||||
\fBExample:\fR
|
||||
.EX
|
||||
# \fBcat /usr/share/zfs/compatibility.d/grub2\fR
|
||||
# Features which are supported by GRUB2
|
||||
async_destroy
|
||||
bookmarks
|
||||
embedded_data
|
||||
empty_bpobj
|
||||
enabled_txg
|
||||
extensible_dataset
|
||||
filesystem_limits
|
||||
hole_birth
|
||||
large_blocks
|
||||
lz4_compress
|
||||
spacemap_histogram
|
||||
|
||||
# \fBzpool create \-o compatibility=grub2 bootpool vdev\fR
|
||||
.EE
|
||||
.LP
|
||||
See \fBzpool\-create(8)\fR and \fBzpool\-upgrade(8)\fR for more information
|
||||
on how these commands are affected by feature sets.
|
||||
.SH FEATURES
|
||||
.sp
|
||||
.LP
|
||||
|
@ -26,6 +26,7 @@
|
||||
.\" Copyright (c) 2018 George Melikov. All Rights Reserved.
|
||||
.\" Copyright 2017 Nexenta Systems, Inc.
|
||||
.\" Copyright (c) 2017 Open-E, Inc. All Rights Reserved.
|
||||
.\" Copyright (c) 2021, Colm Buckley <colm@tuatha.org>
|
||||
.\"
|
||||
.Dd August 9, 2019
|
||||
.Dt ZPOOL-CREATE 8
|
||||
@ -40,6 +41,7 @@
|
||||
.Op Fl m Ar mountpoint
|
||||
.Oo Fl o Ar property Ns = Ns Ar value Oc Ns ...
|
||||
.Oo Fl o Ar feature@feature Ns = Ns Ar value Oc
|
||||
.Op Fl o Ar compatibility Ns = Ns Ar off | legacy | file Bq , Ns Ar file Ns ...
|
||||
.Oo Fl O Ar file-system-property Ns = Ns Ar value Oc Ns ...
|
||||
.Op Fl R Ar root
|
||||
.Ar pool vdev Ns ...
|
||||
@ -52,6 +54,7 @@
|
||||
.Op Fl m Ar mountpoint
|
||||
.Oo Fl o Ar property Ns = Ns Ar value Oc Ns ...
|
||||
.Oo Fl o Ar feature@feature Ns = Ns Ar value Oc Ns ...
|
||||
.Op Fl o Ar compatibility Ns = Ns Ar off | legacy | file Bq , Ns Ar file Ns ...
|
||||
.Oo Fl O Ar file-system-property Ns = Ns Ar value Oc Ns ...
|
||||
.Op Fl R Ar root
|
||||
.Op Fl t Ar tname
|
||||
@ -135,9 +138,14 @@ This can be overridden with the
|
||||
.Fl m
|
||||
option.
|
||||
.Pp
|
||||
By default all supported features are enabled on the new pool unless the
|
||||
By default all supported features are enabled on the new pool. The
|
||||
.Fl d
|
||||
option is specified.
|
||||
option or the
|
||||
.Fl o Ar compatibility
|
||||
property (eg:
|
||||
.Fl o Ar compatibility=2020
|
||||
) can be used to restrict the features that are enabled, so that the
|
||||
pool can be imported on other releases of the ZFS software.
|
||||
.Bl -tag -width Ds
|
||||
.It Fl d
|
||||
Do not enable any features on the new pool.
|
||||
@ -179,6 +187,10 @@ Sets the given pool properties.
|
||||
See the
|
||||
.Xr zpoolprops
|
||||
manual page for a list of valid properties that can be set.
|
||||
.It Fl o Ar compatibility Ns = Ns Ar off | legacy | file Bq , Ns Ar file Ns ...
|
||||
Specifies compatibility feature sets. See
|
||||
.Xr zpool-features 5
|
||||
for more information about compatibility feature sets.
|
||||
.It Fl o Ar feature@feature Ns = Ns Ar value
|
||||
Sets the given pool feature. See the
|
||||
.Xr zpool-features 5
|
||||
|
@ -26,6 +26,7 @@
|
||||
.\" Copyright (c) 2018 George Melikov. All Rights Reserved.
|
||||
.\" Copyright 2017 Nexenta Systems, Inc.
|
||||
.\" Copyright (c) 2017 Open-E, Inc. All Rights Reserved.
|
||||
.\" Copyright (c) 2021, Colm Buckley <colm@tuatha.org>
|
||||
.\"
|
||||
.Dd August 9, 2019
|
||||
.Dt ZPOOL-UPGRADE 8
|
||||
@ -54,7 +55,11 @@ formatted using a legacy ZFS version number.
|
||||
These pools can continue to be used, but some features may not be available.
|
||||
Use
|
||||
.Nm zpool Cm upgrade Fl a
|
||||
to enable all features on all pools.
|
||||
to enable all features on all pools. (If a pool has specified compatibility
|
||||
feature sets using the
|
||||
.Fl o Ar compatibility
|
||||
property, only the features present in all requested compatibility sets will
|
||||
be enabled on that pool.)
|
||||
.It Xo
|
||||
.Nm zpool
|
||||
.Cm upgrade
|
||||
@ -70,7 +75,11 @@ for a description of feature flags features supported by the current software.
|
||||
.Op Fl V Ar version
|
||||
.Fl a Ns | Ns Ar pool Ns ...
|
||||
.Xc
|
||||
Enables all supported features on the given pool.
|
||||
Enables all supported features on the given pool. (If the pool has specified
|
||||
compatibility feature sets using the
|
||||
.Fl o Ar compatibility
|
||||
property, only the features present in all requested compatibility sets will be
|
||||
enabled.)
|
||||
Once this is done, the pool will no longer be accessible on systems that do not
|
||||
support feature flags.
|
||||
See
|
||||
@ -79,7 +88,8 @@ for details on compatibility with systems that support feature flags, but do not
|
||||
support all features enabled on the pool.
|
||||
.Bl -tag -width Ds
|
||||
.It Fl a
|
||||
Enables all supported features on all pools.
|
||||
Enables all supported features (from specified compatibility sets, if any) on all
|
||||
pools.
|
||||
.It Fl V Ar version
|
||||
Upgrade to the specified legacy version.
|
||||
If the
|
||||
|
@ -26,6 +26,7 @@
|
||||
.\" Copyright (c) 2018 George Melikov. All Rights Reserved.
|
||||
.\" Copyright 2017 Nexenta Systems, Inc.
|
||||
.\" Copyright (c) 2017 Open-E, Inc. All Rights Reserved.
|
||||
.\" Copyright (c) 2021, Colm Buckley <colm@tuatha.org>
|
||||
.\"
|
||||
.Dd August 9, 2019
|
||||
.Dt ZPOOLPROPS 8
|
||||
@ -285,6 +286,24 @@ A text string consisting of printable ASCII characters that will be stored
|
||||
such that it is available even if the pool becomes faulted.
|
||||
An administrator can provide additional information about a pool using this
|
||||
property.
|
||||
.It Sy compatibility Ns = Ns Ar off | legacy | file Bq , Ns Ar file Ns ...
|
||||
Specifies that the pool maintain compatibility with specific feature sets.
|
||||
When set to
|
||||
.Sy off
|
||||
(or unset); compatibility is disabled (all features are enabled); when set to
|
||||
.Sy legacy Ns ;
|
||||
no features are enabled. When set to a comma-separated list of
|
||||
filenames (each filename may either be an absolute path, or relative to
|
||||
.Pa /etc/zfs/compatibility.d or Pa /usr/share/zfs/compatibility.d Ns )
|
||||
the lists of requested features are read from those files, separated by
|
||||
whitespace and/or commas. Only features present in all files are enabled.
|
||||
|
||||
See
|
||||
.Xr zpool-features 5 Ns ,
|
||||
.Xr zpool-create 8
|
||||
and
|
||||
.Xr zpool-upgrade 8
|
||||
for more information on the operation of compatibility feature sets.
|
||||
.It Sy dedupditto Ns = Ns Ar number
|
||||
This property is deprecated and no longer has any effect.
|
||||
.It Sy delegation Ns = Ns Sy on Ns | Ns Sy off
|
||||
|
@ -328,25 +328,6 @@ abd_alloc_for_io(size_t size, boolean_t is_metadata)
|
||||
return (abd_alloc_linear(size, is_metadata));
|
||||
}
|
||||
|
||||
/*
|
||||
* This is just a helper function to abd_get_offset_scatter() to alloc a
|
||||
* scatter ABD using the calculated chunkcnt based on the offset within the
|
||||
* parent ABD.
|
||||
*/
|
||||
static abd_t *
|
||||
abd_alloc_scatter_offset_chunkcnt(size_t chunkcnt)
|
||||
{
|
||||
size_t abd_size = offsetof(abd_t,
|
||||
abd_u.abd_scatter.abd_chunks[chunkcnt]);
|
||||
abd_t *abd = kmem_alloc(abd_size, KM_PUSHPAGE);
|
||||
ASSERT3P(abd, !=, NULL);
|
||||
list_link_init(&abd->abd_gang_link);
|
||||
mutex_init(&abd->abd_mtx, NULL, MUTEX_DEFAULT, NULL);
|
||||
ABDSTAT_INCR(abdstat_struct_size, abd_size);
|
||||
|
||||
return (abd);
|
||||
}
|
||||
|
||||
abd_t *
|
||||
abd_get_offset_scatter(abd_t *abd, abd_t *sabd, size_t off)
|
||||
{
|
||||
|
@ -222,9 +222,15 @@ zfs_mod_supported_feature(const char *name)
|
||||
* features are supported.
|
||||
*
|
||||
* The equivalent _can_ be done on FreeBSD by way of the sysctl
|
||||
* tree, but this has not been done yet.
|
||||
* tree, but this has not been done yet. Therefore, we return
|
||||
* that all features except edonr are supported.
|
||||
*/
|
||||
#if defined(_KERNEL) || defined(LIB_ZPOOL_BUILD) || defined(__FreeBSD__)
|
||||
#if defined(__FreeBSD__)
|
||||
if (strcmp(name, "org.illumos:edonr") == 0)
|
||||
return (B_FALSE);
|
||||
else
|
||||
return (B_TRUE);
|
||||
#elif defined(_KERNEL) || defined(LIB_ZPOOL_BUILD)
|
||||
return (B_TRUE);
|
||||
#else
|
||||
return (zfs_mod_supported(ZFS_SYSFS_POOL_FEATURES, name));
|
||||
@ -440,8 +446,6 @@ zpool_feature_init(void)
|
||||
skein_deps);
|
||||
}
|
||||
|
||||
#if !defined(__FreeBSD__)
|
||||
|
||||
{
|
||||
static const spa_feature_t edonr_deps[] = {
|
||||
SPA_FEATURE_EXTENSIBLE_DATASET,
|
||||
@ -453,7 +457,6 @@ zpool_feature_init(void)
|
||||
ZFEATURE_FLAG_PER_DATASET, ZFEATURE_TYPE_BOOLEAN,
|
||||
edonr_deps);
|
||||
}
|
||||
#endif
|
||||
|
||||
{
|
||||
static const spa_feature_t redact_books_deps[] = {
|
||||
|
@ -22,6 +22,7 @@
|
||||
* Copyright (c) 2007, 2010, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright 2011 Nexenta Systems, Inc. All rights reserved.
|
||||
* Copyright (c) 2012, 2018 by Delphix. All rights reserved.
|
||||
* Copyright (c) 2021, Colm Buckley <colm@tuatha.org>
|
||||
*/
|
||||
|
||||
#include <sys/zio.h>
|
||||
@ -71,6 +72,9 @@ zpool_prop_init(void)
|
||||
PROP_DEFAULT, ZFS_TYPE_POOL, "<file> | none", "CACHEFILE");
|
||||
zprop_register_string(ZPOOL_PROP_COMMENT, "comment", NULL,
|
||||
PROP_DEFAULT, ZFS_TYPE_POOL, "<comment-string>", "COMMENT");
|
||||
zprop_register_string(ZPOOL_PROP_COMPATIBILITY, "compatibility",
|
||||
"off", PROP_DEFAULT, ZFS_TYPE_POOL,
|
||||
"<file[,file...]> | off | legacy", "COMPATIBILITY");
|
||||
|
||||
/* readonly number properties */
|
||||
zprop_register_number(ZPOOL_PROP_SIZE, "size", 0, PROP_READONLY,
|
||||
|
@ -32,6 +32,7 @@
|
||||
* Copyright (c) 2017, 2019, Datto Inc. All rights reserved.
|
||||
* Copyright 2017 Joyent, Inc.
|
||||
* Copyright (c) 2017, Intel Corporation.
|
||||
* Copyright (c) 2021, Colm Buckley <colm@tuatha.org>
|
||||
*/
|
||||
|
||||
/*
|
||||
@ -377,6 +378,11 @@ spa_prop_get_config(spa_t *spa, nvlist_t **nvp)
|
||||
0, ZPROP_SRC_LOCAL);
|
||||
}
|
||||
|
||||
if (spa->spa_compatibility != NULL) {
|
||||
spa_prop_add_list(*nvp, ZPOOL_PROP_COMPATIBILITY,
|
||||
spa->spa_compatibility, 0, ZPROP_SRC_LOCAL);
|
||||
}
|
||||
|
||||
if (spa->spa_root != NULL)
|
||||
spa_prop_add_list(*nvp, ZPOOL_PROP_ALTROOT, spa->spa_root,
|
||||
0, ZPROP_SRC_LOCAL);
|
||||
@ -1669,6 +1675,10 @@ spa_unload(spa_t *spa)
|
||||
spa_strfree(spa->spa_comment);
|
||||
spa->spa_comment = NULL;
|
||||
}
|
||||
if (spa->spa_compatibility != NULL) {
|
||||
spa_strfree(spa->spa_compatibility);
|
||||
spa->spa_compatibility = NULL;
|
||||
}
|
||||
|
||||
spa_config_exit(spa, SCL_ALL, spa);
|
||||
}
|
||||
@ -3249,6 +3259,7 @@ spa_ld_parse_config(spa_t *spa, spa_import_type_t type)
|
||||
vdev_t *rvd;
|
||||
uint64_t pool_guid;
|
||||
char *comment;
|
||||
char *compatibility;
|
||||
|
||||
/*
|
||||
* Versioning wasn't explicitly added to the label until later, so if
|
||||
@ -3297,6 +3308,11 @@ spa_ld_parse_config(spa_t *spa, spa_import_type_t type)
|
||||
if (nvlist_lookup_string(config, ZPOOL_CONFIG_COMMENT, &comment) == 0)
|
||||
spa->spa_comment = spa_strdup(comment);
|
||||
|
||||
ASSERT(spa->spa_compatibility == NULL);
|
||||
if (nvlist_lookup_string(config, ZPOOL_CONFIG_COMPATIBILITY,
|
||||
&compatibility) == 0)
|
||||
spa->spa_compatibility = spa_strdup(compatibility);
|
||||
|
||||
(void) nvlist_lookup_uint64(config, ZPOOL_CONFIG_POOL_TXG,
|
||||
&spa->spa_config_txg);
|
||||
|
||||
@ -8668,6 +8684,20 @@ spa_sync_props(void *arg, dmu_tx_t *tx)
|
||||
spa_history_log_internal(spa, "set", tx,
|
||||
"%s=%s", nvpair_name(elem), strval);
|
||||
break;
|
||||
case ZPOOL_PROP_COMPATIBILITY:
|
||||
strval = fnvpair_value_string(elem);
|
||||
if (spa->spa_compatibility != NULL)
|
||||
spa_strfree(spa->spa_compatibility);
|
||||
spa->spa_compatibility = spa_strdup(strval);
|
||||
/*
|
||||
* Dirty the configuration on vdevs as above.
|
||||
*/
|
||||
if (tx->tx_txg != TXG_INITIAL)
|
||||
vdev_config_dirty(spa->spa_root_vdev);
|
||||
spa_history_log_internal(spa, "set", tx,
|
||||
"%s=%s", nvpair_name(elem), strval);
|
||||
break;
|
||||
|
||||
default:
|
||||
/*
|
||||
* Set pool property values in the poolprops mos object.
|
||||
|
@ -24,6 +24,7 @@
|
||||
* Copyright 2011 Nexenta Systems, Inc. All rights reserved.
|
||||
* Copyright (c) 2011, 2020 by Delphix. All rights reserved.
|
||||
* Copyright 2017 Joyent, Inc.
|
||||
* Copyright (c) 2021, Colm Buckley <colm@tuatha.org>
|
||||
*/
|
||||
|
||||
#include <sys/spa.h>
|
||||
@ -446,6 +447,9 @@ spa_config_generate(spa_t *spa, vdev_t *vd, uint64_t txg, int getstats)
|
||||
if (spa->spa_comment != NULL)
|
||||
fnvlist_add_string(config, ZPOOL_CONFIG_COMMENT,
|
||||
spa->spa_comment);
|
||||
if (spa->spa_compatibility != NULL)
|
||||
fnvlist_add_string(config, ZPOOL_CONFIG_COMPATIBILITY,
|
||||
spa->spa_compatibility);
|
||||
|
||||
hostid = spa_get_hostid(spa);
|
||||
if (hostid != 0)
|
||||
|
@ -457,6 +457,7 @@ systemctl --system daemon-reload >/dev/null || true
|
||||
%{_udevdir}/vdev_id
|
||||
%{_udevdir}/zvol_id
|
||||
%{_udevdir}/rules.d/*
|
||||
%{_datadir}/%{name}/compatibility.d
|
||||
%if ! 0%{?_systemd} || 0%{?_initramfs}
|
||||
# Files needed for sysvinit and initramfs-tools
|
||||
%{_sysconfdir}/%{name}/zfs-functions
|
||||
@ -503,7 +504,10 @@ systemctl --system daemon-reload >/dev/null || true
|
||||
%doc AUTHORS COPYRIGHT LICENSE NOTICE README.md
|
||||
|
||||
%files test
|
||||
%{_datadir}/%{name}
|
||||
%{_datadir}/%{name}/zfs-tests
|
||||
%{_datadir}/%{name}/test-runner
|
||||
%{_datadir}/%{name}/runfiles
|
||||
%{_datadir}/%{name}/*.sh
|
||||
|
||||
%files dracut
|
||||
%doc contrib/dracut/README.dracut.markdown
|
||||
|
@ -34,6 +34,7 @@ export ZEDLET_ETC_DIR=$$CMD_DIR/zed/zed.d
|
||||
export ZEDLET_LIBEXEC_DIR=$$CMD_DIR/zed/zed.d
|
||||
export ZPOOL_SCRIPT_DIR=$$CMD_DIR/zpool/zpool.d
|
||||
export ZPOOL_SCRIPTS_PATH=$$CMD_DIR/zpool/zpool.d
|
||||
export ZPOOL_COMPAT_DIR=$$CMD_DIR/zpool/compatibility.d
|
||||
export CONTRIB_DIR=@abs_top_builddir@/contrib
|
||||
export LIB_DIR=@abs_top_builddir@/lib
|
||||
export SYSCONF_DIR=@abs_top_builddir@/etc
|
||||
|
@ -344,7 +344,8 @@ tests = ['zpool_create_001_pos', 'zpool_create_002_pos',
|
||||
'zpool_create_draid_003_pos', 'zpool_create_draid_004_pos',
|
||||
'zpool_create_features_001_pos', 'zpool_create_features_002_pos',
|
||||
'zpool_create_features_003_pos', 'zpool_create_features_004_neg',
|
||||
'zpool_create_features_005_pos',
|
||||
'zpool_create_features_005_pos', 'zpool_create_features_006_pos',
|
||||
'zpool_create_features_007_pos', 'zpool_create_features_008_pos',
|
||||
'create-o_ashift', 'zpool_create_tempname', 'zpool_create_dryrun_output']
|
||||
tags = ['functional', 'cli_root', 'zpool_create']
|
||||
|
||||
@ -468,7 +469,8 @@ tests = ['zpool_split_cliargs', 'zpool_split_devices',
|
||||
tags = ['functional', 'cli_root', 'zpool_split']
|
||||
|
||||
[tests/functional/cli_root/zpool_status]
|
||||
tests = ['zpool_status_001_pos', 'zpool_status_002_pos']
|
||||
tests = ['zpool_status_001_pos', 'zpool_status_002_pos',
|
||||
'zpool_status_features_001_pos']
|
||||
tags = ['functional', 'cli_root', 'zpool_status']
|
||||
|
||||
[tests/functional/cli_root/zpool_sync]
|
||||
@ -491,7 +493,7 @@ tests = ['zpool_upgrade_001_pos', 'zpool_upgrade_002_pos',
|
||||
'zpool_upgrade_003_pos', 'zpool_upgrade_004_pos',
|
||||
'zpool_upgrade_005_neg', 'zpool_upgrade_006_neg',
|
||||
'zpool_upgrade_007_pos', 'zpool_upgrade_008_pos',
|
||||
'zpool_upgrade_009_neg']
|
||||
'zpool_upgrade_009_neg', 'zpool_upgrade_features_001_pos']
|
||||
tags = ['functional', 'cli_root', 'zpool_upgrade']
|
||||
|
||||
[tests/functional/cli_root/zpool_wait]
|
||||
|
@ -44,11 +44,9 @@
|
||||
#include <sys/time.h>
|
||||
#include <linux/limits.h>
|
||||
|
||||
extern char *program_invocation_short_name;
|
||||
|
||||
#define ERROR(fmt, ...) \
|
||||
fprintf(stderr, "%s: %s:%d: %s: " fmt "\n", \
|
||||
program_invocation_short_name, __FILE__, __LINE__, \
|
||||
fprintf(stderr, "xattrtest: %s:%d: %s: " fmt "\n", \
|
||||
__FILE__, __LINE__, \
|
||||
__func__, ## __VA_ARGS__);
|
||||
|
||||
static const char shortopts[] = "hvycdn:f:x:s:p:t:e:rRko:";
|
||||
|
@ -37,6 +37,7 @@
|
||||
export ZEDLET_ETC_DIR=${ZEDLET_ETC_DIR:-@sysconfdir@/zfs/zed.d}
|
||||
export ZEDLET_LIBEXEC_DIR=${ZEDLET_LIBEXEC_DIR:-@zfsexecdir@/zed.d}
|
||||
export ZPOOL_SCRIPT_DIR=${ZPOOL_SCRIPT_DIR:-@sysconfdir@/zfs/zpool.d}
|
||||
export ZPOOL_COMPAT_DIR=${ZPOOL_COMPAT_DIR:-@datadir@/zfs/compatibility.d}
|
||||
|
||||
# Define run length constants
|
||||
export RT_LONG="3"
|
||||
|
@ -36,6 +36,9 @@ dist_pkgdata_SCRIPTS = \
|
||||
zpool_create_features_003_pos.ksh \
|
||||
zpool_create_features_004_neg.ksh \
|
||||
zpool_create_features_005_pos.ksh \
|
||||
zpool_create_features_006_pos.ksh \
|
||||
zpool_create_features_007_pos.ksh \
|
||||
zpool_create_features_008_pos.ksh \
|
||||
create-o_ashift.ksh \
|
||||
zpool_create_tempname.ksh \
|
||||
zpool_create_dryrun_output.ksh
|
||||
|
@ -107,3 +107,84 @@ function save_dump_dev
|
||||
fi
|
||||
echo $dumpdev
|
||||
}
|
||||
|
||||
#
|
||||
# Verify a pools enabled features match the provided feature set.
|
||||
# $1, pool name
|
||||
# $2, feature set(s)
|
||||
#
|
||||
# check_feature_set $TESTPOOL set1 set2 set3 ...
|
||||
#
|
||||
function check_feature_set
|
||||
{
|
||||
typeset pool=$1
|
||||
typeset feature_set=$2
|
||||
shift
|
||||
|
||||
for set in "$@"; do
|
||||
if test -e "$ZPOOL_COMPAT_DIR/$set"; then
|
||||
file="$ZPOOL_COMPAT_DIR/$set"
|
||||
else
|
||||
log_fail "Missing feature file: $ZPOOL_COMPAT_DIR/$set"
|
||||
fi
|
||||
done
|
||||
|
||||
#
|
||||
# Create a temporary file which contains all features which are
|
||||
# common to the listed feature sets. This is used for comparison
|
||||
# below to determine which features should be enabled.
|
||||
#
|
||||
typeset tmpfile=$(mktemp)
|
||||
|
||||
while read line; do
|
||||
typeset flag=1
|
||||
|
||||
if [[ "$line" == "#*" ]]; then
|
||||
continue
|
||||
fi
|
||||
|
||||
for set in "$@"; do
|
||||
if ! grep -q "$line" $ZPOOL_COMPAT_DIR/$set; then
|
||||
flag=0
|
||||
break;
|
||||
fi
|
||||
done
|
||||
|
||||
if [[ $flag -eq 1 ]]; then
|
||||
echo "$line" >>$tmpfile
|
||||
fi
|
||||
done <"$file"
|
||||
|
||||
#
|
||||
# Verify every enabled feature appears in the merged feature set.
|
||||
# Verify every disabled feature does not.
|
||||
#
|
||||
for feature in $(zpool get all $pool | \
|
||||
awk '$2 ~ /feature@/ { print $2 }'); do
|
||||
state=$(get_pool_prop $feature $pool)
|
||||
name=$(cut -d'@' -f2 <<<"$feature")
|
||||
|
||||
if [[ "$state" = "enabled" || "$state" = "active" ]]; then
|
||||
if ! grep -q $name $tmpfile; then
|
||||
cat $tmpfile
|
||||
rm -f $tmpfile
|
||||
log_fail "Enabled feature $name not " \
|
||||
"in feature set file"
|
||||
fi
|
||||
elif [[ "$state" = "disabled" ]]; then
|
||||
if grep -q $name $tmpfile; then
|
||||
cat $tmpfile
|
||||
rm -f $tmpfile
|
||||
log_fail "Disabled feature $name is " \
|
||||
"in feature set file"
|
||||
fi
|
||||
else
|
||||
rm -f $tmpfile
|
||||
log_fail "Feature $name in unknown state $state"
|
||||
fi
|
||||
done
|
||||
|
||||
log_note "Checked all features"
|
||||
|
||||
rm -f $tmpfile
|
||||
}
|
||||
|
@ -0,0 +1,58 @@
|
||||
#!/bin/ksh -p
|
||||
#
|
||||
# CDDL HEADER START
|
||||
#
|
||||
# The contents of this file are subject to the terms of the
|
||||
# Common Development and Distribution License (the "License").
|
||||
# You may not use this file except in compliance with the License.
|
||||
#
|
||||
# You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
|
||||
# or http://www.opensolaris.org/os/licensing.
|
||||
# See the License for the specific language governing permissions
|
||||
# and limitations under the License.
|
||||
#
|
||||
# When distributing Covered Code, include this CDDL HEADER in each
|
||||
# file and include the License file at usr/src/OPENSOLARIS.LICENSE.
|
||||
# If applicable, add the following below this CDDL HEADER, with the
|
||||
# fields enclosed by brackets "[]" replaced with your own identifying
|
||||
# information: Portions Copyright [yyyy] [name of copyright owner]
|
||||
#
|
||||
# CDDL HEADER END
|
||||
#
|
||||
|
||||
#
|
||||
# Copyright (c) 2021 Lawrence Livermore National Security, LLC.
|
||||
#
|
||||
|
||||
. $STF_SUITE/include/libtest.shlib
|
||||
|
||||
#
|
||||
# DESCRIPTION:
|
||||
# Verify '-o compatibility' reserved values 'off, legacy'
|
||||
#
|
||||
# STRATEGY:
|
||||
# 1. Create a pool with '-o compatibility=off'
|
||||
# 2. Create a pool with '-o compatibility=legacy'
|
||||
# 3. Cannot create a pool with '-o compatibility=unknown'
|
||||
#
|
||||
|
||||
verify_runnable "global"
|
||||
|
||||
function cleanup
|
||||
{
|
||||
datasetexists $TESTPOOL && log_must zpool destroy $TESTPOOL
|
||||
}
|
||||
|
||||
log_onexit cleanup
|
||||
|
||||
log_assert "verify '-o compatibility' reserved values 'off, legacy'"
|
||||
|
||||
log_must zpool create -f -o compatibility=off $TESTPOOL $DISKS
|
||||
log_must zpool destroy -f $TESTPOOL
|
||||
|
||||
log_must zpool create -f -o compatibility=legacy $TESTPOOL $DISKS
|
||||
log_must zpool destroy -f $TESTPOOL
|
||||
|
||||
log_mustnot zpool create -f -o compatibility=unknown $TESTPOOL $DISKS
|
||||
|
||||
log_pass "verify '-o compatibility' reserved values 'off, legacy'"
|
@ -0,0 +1,54 @@
|
||||
#!/bin/ksh -p
|
||||
#
|
||||
# CDDL HEADER START
|
||||
#
|
||||
# The contents of this file are subject to the terms of the
|
||||
# Common Development and Distribution License (the "License").
|
||||
# You may not use this file except in compliance with the License.
|
||||
#
|
||||
# You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
|
||||
# or http://www.opensolaris.org/os/licensing.
|
||||
# See the License for the specific language governing permissions
|
||||
# and limitations under the License.
|
||||
#
|
||||
# When distributing Covered Code, include this CDDL HEADER in each
|
||||
# file and include the License file at usr/src/OPENSOLARIS.LICENSE.
|
||||
# If applicable, add the following below this CDDL HEADER, with the
|
||||
# fields enclosed by brackets "[]" replaced with your own identifying
|
||||
# information: Portions Copyright [yyyy] [name of copyright owner]
|
||||
#
|
||||
# CDDL HEADER END
|
||||
#
|
||||
|
||||
#
|
||||
# Copyright (c) 2021 Lawrence Livermore National Security, LLC.
|
||||
#
|
||||
|
||||
. $STF_SUITE/include/libtest.shlib
|
||||
. $STF_SUITE/tests/functional/cli_root/zpool_create/zpool_create.shlib
|
||||
|
||||
#
|
||||
# DESCRIPTION:
|
||||
# Verify pools can be created with the expected feature set enabled.
|
||||
#
|
||||
# STRATEGY:
|
||||
# 1. Create a pool with a known feature set.
|
||||
# 2. Verify only those features are active/enabled.
|
||||
#
|
||||
|
||||
verify_runnable "global"
|
||||
|
||||
function cleanup
|
||||
{
|
||||
datasetexists $TESTPOOL && log_must zpool destroy $TESTPOOL
|
||||
}
|
||||
|
||||
log_onexit cleanup
|
||||
|
||||
log_assert "creates a pool with a specified feature set enabled"
|
||||
|
||||
log_must zpool create -f -o compatibility=compat-2020 $TESTPOOL $DISKS
|
||||
check_feature_set $TESTPOOL compat-2020
|
||||
log_must zpool destroy -f $TESTPOOL
|
||||
|
||||
log_pass "creates a pool with a specified feature set enabled"
|
@ -0,0 +1,54 @@
|
||||
#!/bin/ksh -p
|
||||
#
|
||||
# CDDL HEADER START
|
||||
#
|
||||
# The contents of this file are subject to the terms of the
|
||||
# Common Development and Distribution License (the "License").
|
||||
# You may not use this file except in compliance with the License.
|
||||
#
|
||||
# You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
|
||||
# or http://www.opensolaris.org/os/licensing.
|
||||
# See the License for the specific language governing permissions
|
||||
# and limitations under the License.
|
||||
#
|
||||
# When distributing Covered Code, include this CDDL HEADER in each
|
||||
# file and include the License file at usr/src/OPENSOLARIS.LICENSE.
|
||||
# If applicable, add the following below this CDDL HEADER, with the
|
||||
# fields enclosed by brackets "[]" replaced with your own identifying
|
||||
# information: Portions Copyright [yyyy] [name of copyright owner]
|
||||
#
|
||||
# CDDL HEADER END
|
||||
#
|
||||
|
||||
#
|
||||
# Copyright (c) 2021 Lawrence Livermore National Security, LLC.
|
||||
#
|
||||
|
||||
. $STF_SUITE/include/libtest.shlib
|
||||
. $STF_SUITE/tests/functional/cli_root/zpool_create/zpool_create.shlib
|
||||
|
||||
#
|
||||
# DESCRIPTION:
|
||||
# Verify pools can be created with multiple feature sets.
|
||||
#
|
||||
# STRATEGY:
|
||||
# 1. Create a pool with multiple feature sets.
|
||||
# 2. Verify only the features common to both sets are enabled.
|
||||
#
|
||||
|
||||
verify_runnable "global"
|
||||
|
||||
function cleanup
|
||||
{
|
||||
datasetexists $TESTPOOL && log_must zpool destroy $TESTPOOL
|
||||
}
|
||||
|
||||
log_onexit cleanup
|
||||
|
||||
log_assert "creates a pool with multiple feature sets enabled"
|
||||
|
||||
log_must zpool create -f -o compatibility=freebsd-11.0,zol-0.8 $TESTPOOL $DISKS
|
||||
check_feature_set $TESTPOOL freebsd-11.0 zol-0.8
|
||||
log_must zpool destroy -f $TESTPOOL
|
||||
|
||||
log_pass "creates a pool with multiple feature sets enabled"
|
@ -57,6 +57,7 @@ typeset -a properties=(
|
||||
"leaked"
|
||||
"multihost"
|
||||
"autotrim"
|
||||
"compatibility"
|
||||
"feature@async_destroy"
|
||||
"feature@empty_bpobj"
|
||||
"feature@lz4_compress"
|
||||
|
@ -3,4 +3,5 @@ dist_pkgdata_SCRIPTS = \
|
||||
setup.ksh \
|
||||
cleanup.ksh \
|
||||
zpool_status_001_pos.ksh \
|
||||
zpool_status_002_pos.ksh
|
||||
zpool_status_002_pos.ksh \
|
||||
zpool_status_features_001_pos.ksh
|
||||
|
@ -0,0 +1,63 @@
|
||||
#!/bin/ksh -p
|
||||
#
|
||||
# CDDL HEADER START
|
||||
#
|
||||
# The contents of this file are subject to the terms of the
|
||||
# Common Development and Distribution License (the "License").
|
||||
# You may not use this file except in compliance with the License.
|
||||
#
|
||||
# You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
|
||||
# or http://www.opensolaris.org/os/licensing.
|
||||
# See the License for the specific language governing permissions
|
||||
# and limitations under the License.
|
||||
#
|
||||
# When distributing Covered Code, include this CDDL HEADER in each
|
||||
# file and include the License file at usr/src/OPENSOLARIS.LICENSE.
|
||||
# If applicable, add the following below this CDDL HEADER, with the
|
||||
# fields enclosed by brackets "[]" replaced with your own identifying
|
||||
# information: Portions Copyright [yyyy] [name of copyright owner]
|
||||
#
|
||||
# CDDL HEADER END
|
||||
#
|
||||
|
||||
#
|
||||
# Copyright (c) 2021 Lawrence Livermore National Security, LLC.
|
||||
#
|
||||
|
||||
. $STF_SUITE/include/libtest.shlib
|
||||
. $STF_SUITE/tests/functional/cli_root/zpool_create/zpool_create.shlib
|
||||
|
||||
#
|
||||
# DESCRIPTION:
|
||||
# Verify zpool status only recommends upgrading the pool when
|
||||
# the enabled features don't match those in the feature set.
|
||||
#
|
||||
# STRATEGY:
|
||||
# 1. Create a pool with a known feature set.
|
||||
# 2. Verify there is no `zpool status` notice to upgrade the pool.
|
||||
# 3. Set the pool compatibility to a newer feature set.
|
||||
# 4. Verify there is a `zpool status` notice to upgrade the pool.
|
||||
#
|
||||
|
||||
verify_runnable "global"
|
||||
|
||||
function cleanup
|
||||
{
|
||||
datasetexists $TESTPOOL1 && log_must zpool destroy $TESTPOOL1
|
||||
rm -f $FILEDEV
|
||||
}
|
||||
|
||||
FILEDEV="$TEST_BASE_DIR/filedev.$$"
|
||||
|
||||
log_onexit cleanup
|
||||
|
||||
log_assert "check 'zpool status' upgrade notice"
|
||||
|
||||
log_must truncate -s $MINVDEVSIZE $FILEDEV
|
||||
log_must zpool create -f -o compatibility=compat-2018 $TESTPOOL1 $FILEDEV
|
||||
log_mustnot check_pool_status $TESTPOOL1 "status" "features are not enabled"
|
||||
|
||||
log_must zpool set compatibility=compat-2020 $TESTPOOL1
|
||||
log_must check_pool_status $TESTPOOL1 "status" "features are not enabled"
|
||||
|
||||
log_pass "check 'zpool status' upgrade notice"
|
@ -12,7 +12,8 @@ dist_pkgdata_SCRIPTS = \
|
||||
zpool_upgrade_006_neg.ksh \
|
||||
zpool_upgrade_007_pos.ksh \
|
||||
zpool_upgrade_008_pos.ksh \
|
||||
zpool_upgrade_009_neg.ksh
|
||||
zpool_upgrade_009_neg.ksh \
|
||||
zpool_upgrade_features_001_pos.ksh
|
||||
|
||||
dist_pkgdata_DATA = \
|
||||
zpool_upgrade.cfg \
|
||||
|
@ -0,0 +1,67 @@
|
||||
#!/bin/ksh -p
|
||||
#
|
||||
# CDDL HEADER START
|
||||
#
|
||||
# The contents of this file are subject to the terms of the
|
||||
# Common Development and Distribution License (the "License").
|
||||
# You may not use this file except in compliance with the License.
|
||||
#
|
||||
# You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
|
||||
# or http://www.opensolaris.org/os/licensing.
|
||||
# See the License for the specific language governing permissions
|
||||
# and limitations under the License.
|
||||
#
|
||||
# When distributing Covered Code, include this CDDL HEADER in each
|
||||
# file and include the License file at usr/src/OPENSOLARIS.LICENSE.
|
||||
# If applicable, add the following below this CDDL HEADER, with the
|
||||
# fields enclosed by brackets "[]" replaced with your own identifying
|
||||
# information: Portions Copyright [yyyy] [name of copyright owner]
|
||||
#
|
||||
# CDDL HEADER END
|
||||
#
|
||||
|
||||
#
|
||||
# Copyright (c) 2021 Lawrence Livermore National Security, LLC.
|
||||
#
|
||||
|
||||
. $STF_SUITE/include/libtest.shlib
|
||||
. $STF_SUITE/tests/functional/cli_root/zpool_create/zpool_create.shlib
|
||||
|
||||
#
|
||||
# DESCRIPTION:
|
||||
# Verify pools can be upgraded to known feature sets.
|
||||
#
|
||||
# STRATEGY:
|
||||
# 1. Create a pool with a known feature set.
|
||||
# 2. Verify only those features are active/enabled.
|
||||
# 3. Upgrade the pool to a newer feature set.
|
||||
# 4. Verify only those features are active/enabled.
|
||||
#
|
||||
|
||||
verify_runnable "global"
|
||||
|
||||
function cleanup
|
||||
{
|
||||
datasetexists $TESTPOOL1 && log_must zpool destroy $TESTPOOL1
|
||||
rm -f $FILEDEV
|
||||
}
|
||||
|
||||
FILEDEV="$TEST_BASE_DIR/filedev.$$"
|
||||
|
||||
log_onexit cleanup
|
||||
|
||||
log_assert "verify pools can be upgraded to known feature sets."
|
||||
|
||||
log_must truncate -s $MINVDEVSIZE $FILEDEV
|
||||
log_must zpool create -f -o compatibility=compat-2018 $TESTPOOL1 $FILEDEV
|
||||
check_feature_set $TESTPOOL1 compat-2018
|
||||
log_mustnot check_pool_status $TESTPOOL1 "status" "features are not enabled"
|
||||
|
||||
log_must zpool set compatibility=compat-2020 $TESTPOOL1
|
||||
log_must check_pool_status $TESTPOOL1 "status" "features are not enabled"
|
||||
|
||||
log_must zpool upgrade $TESTPOOL1
|
||||
check_feature_set $TESTPOOL1 compat-2020
|
||||
log_mustnot check_pool_status $TESTPOOL1 "status" "features are not enabled"
|
||||
|
||||
log_pass "verify pools can be upgraded to known feature sets."
|
Loading…
Reference in New Issue
Block a user