diff options
author | Matthew Ahrens <mahrens@delphix.com> | 2019-06-24 16:44:01 -0700 |
---|---|---|
committer | Brian Behlendorf <behlendorf1@llnl.gov> | 2019-06-24 16:44:01 -0700 |
commit | 59ec30a3290d865b98e3805df6c82b6b4f88aab0 (patch) | |
tree | 4c29fb392d0bb53531756f0b3a931ba38c1493e9 | |
parent | 53864800f60b843b8212514428530adfa155211b (diff) |
Remove code for zfs remap
The "zfs remap" command was disabled by
6e91a72fe3ff8bb282490773bd687632f3e8c79d, because it has little utility
and introduced some tricky bugs. This commit removes the code for it,
the associated ZFS_IOC_REMAP ioctl, and tests.
Note that the ioctl and property will remain, but have no functionality.
This allows older software to fail gracefully if it attempts to use
these, and avoids a backwards incompatibility that would be introduced if
we renumbered the later ioctls/props.
Reviewed-by: Tom Caputi <tcaputi@datto.com>
Reviewed-by: Brian Behlendorf <behlendorf1@llnl.gov>
Signed-off-by: Matthew Ahrens <mahrens@delphix.com>
Closes #8944
40 files changed, 29 insertions, 947 deletions
diff --git a/cmd/zfs/zfs_main.c b/cmd/zfs/zfs_main.c index 634303f80..30942e1f0 100644 --- a/cmd/zfs/zfs_main.c +++ b/cmd/zfs/zfs_main.c @@ -114,7 +114,6 @@ static int zfs_do_release(int argc, char **argv); static int zfs_do_diff(int argc, char **argv); static int zfs_do_bookmark(int argc, char **argv); static int zfs_do_channel_program(int argc, char **argv); -static int zfs_do_remap(int argc, char **argv); static int zfs_do_load_key(int argc, char **argv); static int zfs_do_unload_key(int argc, char **argv); static int zfs_do_change_key(int argc, char **argv); @@ -169,7 +168,6 @@ typedef enum { HELP_HOLDS, HELP_RELEASE, HELP_DIFF, - HELP_REMAP, HELP_BOOKMARK, HELP_CHANNEL_PROGRAM, HELP_LOAD_KEY, @@ -237,7 +235,6 @@ static zfs_command_t command_table[] = { { "holds", zfs_do_holds, HELP_HOLDS }, { "release", zfs_do_release, HELP_RELEASE }, { "diff", zfs_do_diff, HELP_DIFF }, - { "remap", zfs_do_remap, HELP_REMAP }, { "load-key", zfs_do_load_key, HELP_LOAD_KEY }, { "unload-key", zfs_do_unload_key, HELP_UNLOAD_KEY }, { "change-key", zfs_do_change_key, HELP_CHANGE_KEY }, @@ -371,8 +368,6 @@ get_usage(zfs_help_t idx) case HELP_DIFF: return (gettext("\tdiff [-FHt] <snapshot> " "[snapshot|filesystem]\n")); - case HELP_REMAP: - return (gettext("\tremap <filesystem | volume>\n")); case HELP_BOOKMARK: return (gettext("\tbookmark <snapshot> <bookmark>\n")); case HELP_CHANNEL_PROGRAM: @@ -4587,7 +4582,6 @@ zfs_do_receive(int argc, char **argv) #define ZFS_DELEG_PERM_RELEASE "release" #define ZFS_DELEG_PERM_DIFF "diff" #define ZFS_DELEG_PERM_BOOKMARK "bookmark" -#define ZFS_DELEG_PERM_REMAP "remap" #define ZFS_DELEG_PERM_LOAD_KEY "load-key" #define ZFS_DELEG_PERM_CHANGE_KEY "change-key" @@ -4615,7 +4609,6 @@ static zfs_deleg_perm_tab_t zfs_deleg_perm_tbl[] = { { ZFS_DELEG_PERM_SHARE, ZFS_DELEG_NOTE_SHARE }, { ZFS_DELEG_PERM_SNAPSHOT, ZFS_DELEG_NOTE_SNAPSHOT }, { ZFS_DELEG_PERM_BOOKMARK, ZFS_DELEG_NOTE_BOOKMARK }, - { ZFS_DELEG_PERM_REMAP, ZFS_DELEG_NOTE_REMAP }, { ZFS_DELEG_PERM_LOAD_KEY, ZFS_DELEG_NOTE_LOAD_KEY }, { ZFS_DELEG_PERM_CHANGE_KEY, ZFS_DELEG_NOTE_CHANGE_KEY }, @@ -7312,21 +7305,6 @@ zfs_do_unshare(int argc, char **argv) } static int -disable_command_idx(char *command) -{ - for (int i = 0; i < NCOMMAND; i++) { - if (command_table[i].name == NULL) - continue; - - if (strcmp(command, command_table[i].name) == 0) { - command_table[i].name = NULL; - return (0); - } - } - return (1); -} - -static int find_command_idx(char *command, int *idx) { int i; @@ -7429,55 +7407,6 @@ out: return (err != 0); } - -/* - * zfs remap <filesystem | volume> - * - * N.B. The remap command has been disabled and may be removed in the future. - * - * Remap the indirect blocks in the given filesystem or volume so that they no - * longer reference blocks on previously removed vdevs and we can eventually - * shrink the size of the indirect mapping objects for the previously removed - * vdevs. Note that remapping all blocks might not be possible and that - * references from snapshots will still exist and cannot be remapped. - * - * This functionality is no longer particularly useful now that the removal - * code can map large chunks. Furthermore, explaining what this command - * does and why it may be useful requires a detailed understanding of the - * internals of device removal. These are details users should not be - * bothered with. If required, the remap command can be re-enabled by - * setting the ZFS_REMAP_ENABLED environment variable. - * - * > ZFS_REMAP_ENABLED=yes zfs remap <filesystem | volume> - */ -static int -zfs_do_remap(int argc, char **argv) -{ - const char *fsname; - int err = 0; - int c; - - /* check options */ - while ((c = getopt(argc, argv, "")) != -1) { - switch (c) { - case '?': - (void) fprintf(stderr, - gettext("invalid option '%c'\n"), optopt); - usage(B_FALSE); - } - } - - if (argc != 2) { - (void) fprintf(stderr, gettext("wrong number of arguments\n")); - usage(B_FALSE); - } - - fsname = argv[1]; - err = zfs_remap_indirects(g_zfs, fsname); - - return (err); -} - /* * zfs bookmark <fs@snap> <fs#bmark> * @@ -8287,13 +8216,6 @@ main(int argc, char **argv) cmdname = "snapshot"; /* - * The 'remap' command has been disabled and may be removed in the - * future. See the comment above zfs_do_remap() for details. - */ - if (!libzfs_envvar_is_set("ZFS_REMAP_ENABLED")) - disable_command_idx("remap"); - - /* * Special case '-?' */ if ((strcmp(cmdname, "-?") == 0) || diff --git a/configure.ac b/configure.ac index f2d30517b..49396efb8 100644 --- a/configure.ac +++ b/configure.ac @@ -226,7 +226,6 @@ AC_CONFIG_FILES([ tests/zfs-tests/tests/functional/cli_root/zfs_promote/Makefile tests/zfs-tests/tests/functional/cli_root/zfs_property/Makefile tests/zfs-tests/tests/functional/cli_root/zfs_receive/Makefile - tests/zfs-tests/tests/functional/cli_root/zfs_remap/Makefile tests/zfs-tests/tests/functional/cli_root/zfs_rename/Makefile tests/zfs-tests/tests/functional/cli_root/zfs_reservation/Makefile tests/zfs-tests/tests/functional/cli_root/zfs_rollback/Makefile diff --git a/contrib/pyzfs/libzfs_core/__init__.py b/contrib/pyzfs/libzfs_core/__init__.py index a195b05f5..78e96738e 100644 --- a/contrib/pyzfs/libzfs_core/__init__.py +++ b/contrib/pyzfs/libzfs_core/__init__.py @@ -73,7 +73,6 @@ from ._libzfs_core import ( lzc_receive_with_cmdprops, lzc_receive_with_header, lzc_release, - lzc_remap, lzc_reopen, lzc_rollback, lzc_rollback_to, @@ -129,7 +128,6 @@ __all__ = [ 'lzc_receive_with_cmdprops', 'lzc_receive_with_header', 'lzc_release', - 'lzc_remap', 'lzc_reopen', 'lzc_rollback', 'lzc_rollback_to', diff --git a/contrib/pyzfs/libzfs_core/_error_translation.py b/contrib/pyzfs/libzfs_core/_error_translation.py index b888fd725..cf52ac918 100644 --- a/contrib/pyzfs/libzfs_core/_error_translation.py +++ b/contrib/pyzfs/libzfs_core/_error_translation.py @@ -550,18 +550,6 @@ def lzc_channel_program_translate_error(ret, name, error): raise _generic_exception(ret, name, "Failed to execute channel program") -def lzc_remap_translate_error(ret, name): - if ret == 0: - return - if ret == errno.ENOENT: - raise lzc_exc.DatasetNotFound(name) - if ret == errno.EINVAL: - _validate_fs_name(name) - if ret == errno.ENOTSUP: - return lzc_exc.FeatureNotSupported(name) - raise _generic_exception(ret, name, "Failed to remap dataset") - - def lzc_pool_checkpoint_translate_error(ret, name, discard=False): if ret == 0: return diff --git a/contrib/pyzfs/libzfs_core/_libzfs_core.py b/contrib/pyzfs/libzfs_core/_libzfs_core.py index 5c8a1f5e6..5a4843943 100644 --- a/contrib/pyzfs/libzfs_core/_libzfs_core.py +++ b/contrib/pyzfs/libzfs_core/_libzfs_core.py @@ -1563,22 +1563,6 @@ def lzc_promote(name): @_uncommitted() -def lzc_remap(name): - ''' - Remaps the ZFS dataset. - - :param bytes name: the name of the dataset to remap. - :raises NameInvalid: if the dataset name is invalid. - :raises NameTooLong: if the dataset name is too long. - :raises DatasetNotFound: if the dataset does not exist. - :raises FeatureNotSupported: if the pool containing the dataset does not - have the *obsolete_counts* feature enabled. - ''' - ret = _lib.lzc_remap(name) - errors.lzc_remap_translate_error(ret, name) - - -@_uncommitted() def lzc_pool_checkpoint(name): ''' Creates a checkpoint for the specified pool. diff --git a/contrib/pyzfs/libzfs_core/bindings/libzfs_core.py b/contrib/pyzfs/libzfs_core/bindings/libzfs_core.py index ce2d9d62c..1b46a0891 100644 --- a/contrib/pyzfs/libzfs_core/bindings/libzfs_core.py +++ b/contrib/pyzfs/libzfs_core/bindings/libzfs_core.py @@ -127,7 +127,6 @@ CDEF = """ int lzc_snapshot(nvlist_t *, nvlist_t *, nvlist_t **); int lzc_sync(const char *, nvlist_t *, nvlist_t **); int lzc_unload_key(const char *); - int lzc_remap(const char *); int lzc_pool_checkpoint(const char *); int lzc_pool_checkpoint_discard(const char *); int lzc_rename(const char *, const char *); diff --git a/contrib/pyzfs/libzfs_core/test/test_libzfs_core.py b/contrib/pyzfs/libzfs_core/test/test_libzfs_core.py index 25f20a4ae..18306f88e 100644 --- a/contrib/pyzfs/libzfs_core/test/test_libzfs_core.py +++ b/contrib/pyzfs/libzfs_core/test/test_libzfs_core.py @@ -3632,31 +3632,6 @@ zfs.sync.snapshot('""" + pool + b"""@zcp') with self.assertRaises(lzc_exc.EncryptionKeyNotLoaded): lzc.lzc_unload_key(fs) - def test_remap_missing_fs(self): - name = b"nonexistent" - - with self.assertRaises(lzc_exc.DatasetNotFound): - lzc.lzc_remap(name) - - def test_remap_invalid_fs(self): - ds = ZFSTest.pool.makeName(b"fs1") - snap = ds + b"@snap1" - - lzc.lzc_snapshot([snap]) - with self.assertRaises(lzc_exc.NameInvalid): - lzc.lzc_remap(snap) - - def test_remap_too_long_fs_name(self): - name = ZFSTest.pool.makeTooLongName() - - with self.assertRaises(lzc_exc.NameTooLong): - lzc.lzc_remap(name) - - def test_remap(self): - name = ZFSTest.pool.makeName(b"fs1") - - lzc.lzc_remap(name) - def test_checkpoint(self): pool = ZFSTest.pool.getRoot().getName() diff --git a/include/libzfs.h b/include/libzfs.h index 1b9eea15b..8b348746a 100644 --- a/include/libzfs.h +++ b/include/libzfs.h @@ -852,8 +852,6 @@ 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); -extern int zfs_remap_indirects(libzfs_handle_t *hdl, const char *); - #ifdef __cplusplus } #endif diff --git a/include/libzfs_core.h b/include/libzfs_core.h index 2588ed015..04cc47781 100644 --- a/include/libzfs_core.h +++ b/include/libzfs_core.h @@ -49,7 +49,6 @@ enum lzc_dataset_type { LZC_DATSET_TYPE_ZVOL }; -int lzc_remap(const char *fsname); int lzc_snapshot(nvlist_t *, nvlist_t *, nvlist_t **); int lzc_create(const char *, enum lzc_dataset_type, nvlist_t *, uint8_t *, uint_t); diff --git a/include/sys/dbuf.h b/include/sys/dbuf.h index 487cfb513..a2f606265 100644 --- a/include/sys/dbuf.h +++ b/include/sys/dbuf.h @@ -336,8 +336,6 @@ void dbuf_unoverride(dbuf_dirty_record_t *dr); void dbuf_sync_list(list_t *list, int level, dmu_tx_t *tx); void dbuf_release_bp(dmu_buf_impl_t *db); -boolean_t dbuf_can_remap(const dmu_buf_impl_t *buf); - void dbuf_free_range(struct dnode *dn, uint64_t start, uint64_t end, struct dmu_tx *); diff --git a/include/sys/dmu.h b/include/sys/dmu.h index 04b2d9846..3f7350554 100644 --- a/include/sys/dmu.h +++ b/include/sys/dmu.h @@ -342,7 +342,6 @@ int dmu_objset_find(char *name, int func(const char *, void *), void *arg, void dmu_objset_byteswap(void *buf, size_t size); int dsl_dataset_rename_snapshot(const char *fsname, const char *oldsnapname, const char *newsnapname, boolean_t recursive); -int dmu_objset_remap_indirects(const char *fsname); typedef struct dmu_buf { uint64_t db_object; /* object that this buffer is part of */ @@ -498,9 +497,6 @@ void dmu_object_set_checksum(objset_t *os, uint64_t object, uint8_t checksum, void dmu_object_set_compress(objset_t *os, uint64_t object, uint8_t compress, dmu_tx_t *tx); - -int dmu_object_remap_indirects(objset_t *os, uint64_t object, uint64_t txg); - void dmu_write_embedded(objset_t *os, uint64_t object, uint64_t offset, void *data, uint8_t etype, uint8_t comp, int uncompressed_size, int compressed_size, int byteorder, dmu_tx_t *tx); @@ -777,7 +773,6 @@ void dmu_tx_hold_free(dmu_tx_t *tx, uint64_t object, uint64_t off, uint64_t len); void dmu_tx_hold_free_by_dnode(dmu_tx_t *tx, dnode_t *dn, uint64_t off, uint64_t len); -void dmu_tx_hold_remap_l1indirect(dmu_tx_t *tx, uint64_t object); void dmu_tx_hold_zap(dmu_tx_t *tx, uint64_t object, int add, const char *name); void dmu_tx_hold_zap_by_dnode(dmu_tx_t *tx, dnode_t *dn, int add, const char *name); diff --git a/include/sys/dnode.h b/include/sys/dnode.h index c60258bbc..f18b5dd5c 100644 --- a/include/sys/dnode.h +++ b/include/sys/dnode.h @@ -440,7 +440,6 @@ int dnode_next_offset(dnode_t *dn, int flags, uint64_t *off, void dnode_evict_dbufs(dnode_t *dn); void dnode_evict_bonus(dnode_t *dn); void dnode_free_interior_slots(dnode_t *dn); -boolean_t dnode_needs_remap(const dnode_t *dn); #define DNODE_IS_DIRTY(_dn) \ ((_dn)->dn_dirty_txg >= spa_syncing_txg((_dn)->dn_objset->os_spa)) diff --git a/include/sys/dsl_deleg.h b/include/sys/dsl_deleg.h index bb28014ac..7f46233a8 100644 --- a/include/sys/dsl_deleg.h +++ b/include/sys/dsl_deleg.h @@ -61,7 +61,6 @@ extern "C" { #define ZFS_DELEG_PERM_RELEASE "release" #define ZFS_DELEG_PERM_DIFF "diff" #define ZFS_DELEG_PERM_BOOKMARK "bookmark" -#define ZFS_DELEG_PERM_REMAP "remap" #define ZFS_DELEG_PERM_LOAD_KEY "load-key" #define ZFS_DELEG_PERM_CHANGE_KEY "change-key" #define ZFS_DELEG_PERM_PROJECTUSED "projectused" diff --git a/include/sys/dsl_dir.h b/include/sys/dsl_dir.h index 067bcfb6a..08d1fcb37 100644 --- a/include/sys/dsl_dir.h +++ b/include/sys/dsl_dir.h @@ -49,7 +49,6 @@ struct dsl_dataset; #define DD_FIELD_FILESYSTEM_COUNT "com.joyent:filesystem_count" #define DD_FIELD_SNAPSHOT_COUNT "com.joyent:snapshot_count" #define DD_FIELD_CRYPTO_KEY_OBJ "com.datto:crypto_key_obj" -#define DD_FIELD_LAST_REMAP_TXG "com.delphix:last_remap_txg" typedef enum dd_used { DD_USED_HEAD, @@ -154,7 +153,6 @@ void dsl_dir_stats(dsl_dir_t *dd, nvlist_t *nv); uint64_t dsl_dir_space_available(dsl_dir_t *dd, dsl_dir_t *ancestor, int64_t delta, int ondiskonly); void dsl_dir_dirty(dsl_dir_t *dd, dmu_tx_t *tx); -int dsl_dir_get_remaptxg(dsl_dir_t *dd, uint64_t *count); void dsl_dir_sync(dsl_dir_t *dd, dmu_tx_t *tx); int dsl_dir_tempreserve_space(dsl_dir_t *dd, uint64_t mem, uint64_t asize, boolean_t netfree, void **tr_cookiep, dmu_tx_t *tx); @@ -172,7 +170,6 @@ int dsl_dir_activate_fs_ss_limit(const char *); int dsl_fs_ss_limit_check(dsl_dir_t *, uint64_t, zfs_prop_t, dsl_dir_t *, cred_t *); void dsl_fs_ss_count_adjust(dsl_dir_t *, int64_t, const char *, dmu_tx_t *); -int dsl_dir_update_last_remap_txg(dsl_dir_t *, uint64_t); int dsl_dir_rename(const char *oldname, const char *newname); int dsl_dir_transfer_possible(dsl_dir_t *sdd, dsl_dir_t *tdd, uint64_t fs_cnt, uint64_t ss_cnt, uint64_t space, cred_t *); diff --git a/include/sys/fs/zfs.h b/include/sys/fs/zfs.h index fa84d3fa2..93a3533c3 100644 --- a/include/sys/fs/zfs.h +++ b/include/sys/fs/zfs.h @@ -181,7 +181,7 @@ typedef enum { ZFS_PROP_ENCRYPTION_ROOT, ZFS_PROP_KEY_GUID, ZFS_PROP_KEYSTATUS, - ZFS_PROP_REMAPTXG, /* not exposed to the user */ + ZFS_PROP_REMAPTXG, /* obsolete - no longer used */ ZFS_PROP_SPECIAL_SMALL_BLOCKS, ZFS_PROP_IVSET_GUID, /* not exposed to the user */ ZFS_PROP_REDACTED, diff --git a/include/zfs_deleg.h b/include/zfs_deleg.h index 32d66980e..5738b2a73 100644 --- a/include/zfs_deleg.h +++ b/include/zfs_deleg.h @@ -77,7 +77,6 @@ typedef enum { ZFS_DELEG_NOTE_PROJECTQUOTA, ZFS_DELEG_NOTE_PROJECTOBJUSED, ZFS_DELEG_NOTE_PROJECTOBJQUOTA, - ZFS_DELEG_NOTE_REMAP, ZFS_DELEG_NOTE_NONE } zfs_deleg_note_t; diff --git a/lib/libzfs/libzfs_dataset.c b/lib/libzfs/libzfs_dataset.c index 1128275c0..c1aff4725 100644 --- a/lib/libzfs/libzfs_dataset.c +++ b/lib/libzfs/libzfs_dataset.c @@ -4210,36 +4210,6 @@ zfs_snapshot_cb(zfs_handle_t *zhp, void *arg) return (rv); } -int -zfs_remap_indirects(libzfs_handle_t *hdl, const char *fs) -{ - int err; - char errbuf[1024]; - - (void) snprintf(errbuf, sizeof (errbuf), dgettext(TEXT_DOMAIN, - "cannot remap dataset '%s'"), fs); - - err = lzc_remap(fs); - - if (err != 0) { - switch (err) { - case ENOTSUP: - zfs_error_aux(hdl, dgettext(TEXT_DOMAIN, - "pool must be upgraded")); - (void) zfs_error(hdl, EZFS_BADVERSION, errbuf); - break; - case EINVAL: - (void) zfs_error(hdl, EZFS_BADTYPE, errbuf); - break; - default: - (void) zfs_standard_error(hdl, err, errbuf); - break; - } - } - - return (err); -} - /* * Creates snapshots. The keys in the snaps nvlist are the snapshots to be * created. diff --git a/lib/libzfs_core/libzfs_core.c b/lib/libzfs_core/libzfs_core.c index 8ee1dd5e5..d441f3655 100644 --- a/lib/libzfs_core/libzfs_core.c +++ b/lib/libzfs_core/libzfs_core.c @@ -307,16 +307,6 @@ lzc_promote(const char *fsname, char *snapnamebuf, int snapnamelen) } int -lzc_remap(const char *fsname) -{ - int error; - nvlist_t *args = fnvlist_alloc(); - error = lzc_ioctl(ZFS_IOC_REMAP, fsname, args, NULL); - nvlist_free(args); - return (error); -} - -int lzc_rename(const char *source, const char *target) { zfs_cmd_t zc = { "\0" }; diff --git a/module/zcommon/zfs_deleg.c b/module/zcommon/zfs_deleg.c index 8d98f720a..e1f5a353b 100644 --- a/module/zcommon/zfs_deleg.c +++ b/module/zcommon/zfs_deleg.c @@ -52,7 +52,6 @@ zfs_deleg_perm_tab_t zfs_deleg_perm_tab[] = { {ZFS_DELEG_PERM_MOUNT}, {ZFS_DELEG_PERM_PROMOTE}, {ZFS_DELEG_PERM_RECEIVE}, - {ZFS_DELEG_PERM_REMAP}, {ZFS_DELEG_PERM_RENAME}, {ZFS_DELEG_PERM_ROLLBACK}, {ZFS_DELEG_PERM_SNAPSHOT}, diff --git a/module/zcommon/zfs_prop.c b/module/zcommon/zfs_prop.c index 296c883f6..c42f046da 100644 --- a/module/zcommon/zfs_prop.c +++ b/module/zcommon/zfs_prop.c @@ -512,8 +512,6 @@ zfs_prop_init(void) ZFS_TYPE_DATASET | ZFS_TYPE_BOOKMARK, "<uint64>", "GUID"); zprop_register_number(ZFS_PROP_CREATETXG, "createtxg", 0, PROP_READONLY, ZFS_TYPE_DATASET | ZFS_TYPE_BOOKMARK, "<uint64>", "CREATETXG"); - zprop_register_hidden(ZFS_PROP_REMAPTXG, "remaptxg", PROP_TYPE_NUMBER, - PROP_READONLY, ZFS_TYPE_DATASET, "REMAPTXG"); zprop_register_number(ZFS_PROP_PBKDF2_ITERS, "pbkdf2iters", 0, PROP_ONETIME_DEFAULT, ZFS_TYPE_FILESYSTEM | ZFS_TYPE_VOLUME, "<iters>", "PBKDF2ITERS"); @@ -579,11 +577,15 @@ zfs_prop_init(void) PROP_READONLY, ZFS_TYPE_DATASET, "REDACTED"); /* - * Property to be removed once libbe is integrated + * Properties that are obsolete and not used. These are retained so + * that we don't have to change the values of the zfs_prop_t enum, or + * have NULL pointers in the zfs_prop_table[]. */ zprop_register_hidden(ZFS_PROP_PRIVATE, "priv_prop", PROP_TYPE_NUMBER, PROP_READONLY, ZFS_TYPE_FILESYSTEM, "PRIV_PROP"); + zprop_register_hidden(ZFS_PROP_REMAPTXG, "remaptxg", PROP_TYPE_NUMBER, + PROP_READONLY, ZFS_TYPE_DATASET, "REMAPTXG"); /* oddball properties */ zprop_register_impl(ZFS_PROP_CREATION, "creation", PROP_TYPE_NUMBER, 0, diff --git a/module/zfs/dbuf.c b/module/zfs/dbuf.c index 8afc3df37..abfae29ad 100644 --- a/module/zfs/dbuf.c +++ b/module/zfs/dbuf.c @@ -4445,60 +4445,6 @@ dbuf_remap_impl(dnode_t *dn, blkptr_t *bp, dmu_tx_t *tx) } /* - * Returns true if a dbuf_remap would modify the dbuf. We do this by attempting - * to remap a copy of every bp in the dbuf. - */ -boolean_t -dbuf_can_remap(const dmu_buf_impl_t *db) -{ - spa_t *spa = dmu_objset_spa(db->db_objset); - blkptr_t *bp = db->db.db_data; - boolean_t ret = B_FALSE; - - ASSERT3U(db->db_level, >, 0); - ASSERT3S(db->db_state, ==, DB_CACHED); - - ASSERT(spa_feature_is_active(spa, SPA_FEATURE_DEVICE_REMOVAL)); - - spa_config_enter(spa, SCL_VDEV, FTAG, RW_READER); - for (int i = 0; i < db->db.db_size >> SPA_BLKPTRSHIFT; i++) { - blkptr_t bp_copy = bp[i]; - if (spa_remap_blkptr(spa, &bp_copy, NULL, NULL)) { - ret = B_TRUE; - break; - } - } - spa_config_exit(spa, SCL_VDEV, FTAG); - - return (ret); -} - -boolean_t -dnode_needs_remap(const dnode_t *dn) -{ - spa_t *spa = dmu_objset_spa(dn->dn_objset); - boolean_t ret = B_FALSE; - - if (dn->dn_phys->dn_nlevels == 0) { - return (B_FALSE); - } - - ASSERT(spa_feature_is_active(spa, SPA_FEATURE_DEVICE_REMOVAL)); - - spa_config_enter(spa, SCL_VDEV, FTAG, RW_READER); - for (int j = 0; j < dn->dn_phys->dn_nblkptr; j++) { - blkptr_t bp_copy = dn->dn_phys->dn_blkptr[j]; - if (spa_remap_blkptr(spa, &bp_copy, NULL, NULL)) { - ret = B_TRUE; - break; - } - } - spa_config_exit(spa, SCL_VDEV, FTAG); - - return (ret); -} - -/* * Remap any existing BP's to concrete vdevs, if possible. */ static void diff --git a/module/zfs/dmu.c b/module/zfs/dmu.c index 4af2a13e7..0722f5c5e 100644 --- a/module/zfs/dmu.c +++ b/module/zfs/dmu.c @@ -75,13 +75,6 @@ unsigned long zfs_per_txg_dirty_frees_percent = 5; int zfs_dmu_offset_next_sync = 0; /* - * This can be used for testing, to ensure that certain actions happen - * while in the middle of a remap (which might otherwise complete too - * quickly). Used by ztest(8). - */ -int zfs_object_remap_one_indirect_delay_ms = 0; - -/* * Limit the amount we can prefetch with one call to this amount. This * helps to limit the amount of memory that can be used by prefetching. * Larger objects should be prefetched a bit at a time. @@ -1114,137 +1107,6 @@ dmu_write_by_dnode(dnode_t *dn, uint64_t offset, uint64_t size, dmu_buf_rele_array(dbp, numbufs, FTAG); } -static int -dmu_object_remap_one_indirect(objset_t *os, dnode_t *dn, - uint64_t last_removal_txg, uint64_t offset) -{ - uint64_t l1blkid = dbuf_whichblock(dn, 1, offset); - dnode_t *dn_tx; - int err = 0; - - rw_enter(&dn->dn_struct_rwlock, RW_READER); - dmu_buf_impl_t *dbuf = dbuf_hold_level(dn, 1, l1blkid, FTAG); - ASSERT3P(dbuf, !=, NULL); - - /* - * If the block hasn't been written yet, this default will ensure - * we don't try to remap it. - */ - uint64_t birth = UINT64_MAX; - ASSERT3U(last_removal_txg, !=, UINT64_MAX); - if (dbuf->db_blkptr != NULL) - birth = dbuf->db_blkptr->blk_birth; - rw_exit(&dn->dn_struct_rwlock); - - /* - * If this L1 was already written after the last removal, then we've - * already tried to remap it. An additional hold is taken after the - * dmu_tx_assign() to handle the case where the dnode is freed while - * waiting for the next open txg. - */ - if (birth <= last_removal_txg && - dbuf_read(dbuf, NULL, DB_RF_MUST_SUCCEED) == 0 && - dbuf_can_remap(dbuf)) { - dmu_tx_t *tx = dmu_tx_create(os); - dmu_tx_hold_remap_l1indirect(tx, dn->dn_object); - err = dmu_tx_assign(tx, TXG_WAIT); - if (err == 0) { - err = dnode_hold(os, dn->dn_object, FTAG, &dn_tx); - if (err == 0) { - (void) dbuf_dirty(dbuf, tx); - dnode_rele(dn_tx, FTAG); - } - dmu_tx_commit(tx); - } else { - dmu_tx_abort(tx); - } - } - - dbuf_rele(dbuf, FTAG); - - delay(MSEC_TO_TICK(zfs_object_remap_one_indirect_delay_ms)); - - return (err); -} - -/* - * Remap all blockpointers in the object, if possible, so that they reference - * only concrete vdevs. - * - * To do this, iterate over the L0 blockpointers and remap any that reference - * an indirect vdev. Note that we only examine L0 blockpointers; since we - * cannot guarantee that we can remap all blockpointer anyways (due to split - * blocks), we do not want to make the code unnecessarily complicated to - * catch the unlikely case that there is an L1 block on an indirect vdev that - * contains no indirect blockpointers. - */ -int -dmu_object_remap_indirects(objset_t *os, uint64_t object, - uint64_t last_removal_txg) -{ - uint64_t offset, l1span; - int err; - dnode_t *dn, *dn_tx; - - err = dnode_hold(os, object, FTAG, &dn); - if (err != 0) { - return (err); - } - - if (dn->dn_nlevels <= 1) { - if (issig(JUSTLOOKING) && issig(FORREAL)) { - err = SET_ERROR(EINTR); - } - - /* - * If the dnode has no indirect blocks, we cannot dirty them. - * We still want to remap the blkptr(s) in the dnode if - * appropriate, so mark it as dirty. An additional hold is - * taken after the dmu_tx_assign() to handle the case where - * the dnode is freed while waiting for the next open txg. - */ - if (err == 0 && dnode_needs_remap(dn)) { - dmu_tx_t *tx = dmu_tx_create(os); - dmu_tx_hold_bonus(tx, object); - err = dmu_tx_assign(tx, TXG_WAIT); - if (err == 0) { - err = dnode_hold(os, object, FTAG, &dn_tx); - if (err == 0) { - dnode_setdirty(dn_tx, tx); - dnode_rele(dn_tx, FTAG); - } - dmu_tx_commit(tx); - } else { - dmu_tx_abort(tx); - } - } - - dnode_rele(dn, FTAG); - return (err); - } - - offset = 0; - l1span = 1ULL << (dn->dn_indblkshift - SPA_BLKPTRSHIFT + - dn->dn_datablkshift); - /* - * Find the next L1 indirect that is not a hole. - */ - while (dnode_next_offset(dn, 0, &offset, 2, 1, 0) == 0) { - if (issig(JUSTLOOKING) && issig(FORREAL)) { - err = SET_ERROR(EINTR); - break; - } - if ((err = dmu_object_remap_one_indirect(os, dn, - last_removal_txg, offset)) != 0) { - break; - } - offset += l1span; - } - - dnode_rele(dn, FTAG); - return (err); -} - void dmu_prealloc(objset_t *os, uint64_t object, uint64_t offset, uint64_t size, dmu_tx_t *tx) diff --git a/module/zfs/dmu_objset.c b/module/zfs/dmu_objset.c index 6b8c380e5..4091ac355 100644 --- a/module/zfs/dmu_objset.c +++ b/module/zfs/dmu_objset.c @@ -1396,101 +1396,6 @@ dmu_objset_clone(const char *clone, const char *origin) 6, ZFS_SPACE_CHECK_NORMAL)); } -static int -dmu_objset_remap_indirects_impl(objset_t *os, uint64_t last_removed_txg) -{ - int error = 0; - uint64_t object = 0; - while ((error = dmu_object_next(os, &object, B_FALSE, 0)) == 0) { - error = dmu_object_remap_indirects(os, object, - last_removed_txg); - /* - * If the ZPL removed the object before we managed to dnode_hold - * it, we would get an ENOENT. If the ZPL declares its intent - * to remove the object (dnode_free) before we manage to - * dnode_hold it, we would get an EEXIST. In either case, we - * want to continue remapping the other objects in the objset; - * in all other cases, we want to break early. - */ - if (error != 0 && error != ENOENT && error != EEXIST) { - break; - } - } - if (error == ESRCH) { - error = 0; - } - return (error); -} - -int -dmu_objset_remap_indirects(const char *fsname) -{ - int error = 0; - objset_t *os = NULL; - uint64_t last_removed_txg; - uint64_t remap_start_txg; - dsl_dir_t *dd; - - error = dmu_objset_hold(fsname, FTAG, &os); - if (error != 0) { - return (error); - } - dd = dmu_objset_ds(os)->ds_dir; - - if (!spa_feature_is_enabled(dmu_objset_spa(os), - SPA_FEATURE_OBSOLETE_COUNTS)) { - dmu_objset_rele(os, FTAG); - return (SET_ERROR(ENOTSUP)); - } - - if (dsl_dataset_is_snapshot(dmu_objset_ds(os))) { - dmu_objset_rele(os, FTAG); - return (SET_ERROR(EINVAL)); - } - - /* - * If there has not been a removal, we're done. - */ - last_removed_txg = spa_get_last_removal_txg(dmu_objset_spa(os)); - if (last_removed_txg == -1ULL) { - dmu_objset_rele(os, FTAG); - return (0); - } - - /* - * If we have remapped since the last removal, we're done. - */ - if (dsl_dir_is_zapified(dd)) { - uint64_t last_remap_txg; - if (zap_lookup(spa_meta_objset(dmu_objset_spa(os)), - dd->dd_object, DD_FIELD_LAST_REMAP_TXG, - sizeof (last_remap_txg), 1, &last_remap_txg) == 0 && - last_remap_txg > last_removed_txg) { - dmu_objset_rele(os, FTAG); - return (0); - } - } - - dsl_dataset_long_hold(dmu_objset_ds(os), FTAG); - dsl_pool_rele(dmu_objset_pool(os), FTAG); - - remap_start_txg = spa_last_synced_txg(dmu_objset_spa(os)); - error = dmu_objset_remap_indirects_impl(os, last_removed_txg); - if (error == 0) { - /* - * We update the last_remap_txg to be the start txg so that - * we can guarantee that every block older than last_remap_txg - * that can be remapped has been remapped. - */ - error = dsl_dir_update_last_remap_txg(dd, remap_start_txg); - } - - dsl_dataset_long_rele(dmu_objset_ds(os), FTAG); - dsl_dataset_rele(dmu_objset_ds(os), FTAG); - - return (error); -} - int dmu_objset_snapshot_one(const char *fsname, const char *snapname) { diff --git a/module/zfs/dmu_tx.c b/module/zfs/dmu_tx.c index 7d65e842f..4f489de5f 100644 --- a/module/zfs/dmu_tx.c +++ b/module/zfs/dmu_tx.c @@ -317,23 +317,6 @@ dmu_tx_hold_write(dmu_tx_t *tx, uint64_t object, uint64_t off, int len) } void -dmu_tx_hold_remap_l1indirect(dmu_tx_t *tx, uint64_t object) -{ - dmu_tx_hold_t *txh; - - ASSERT(tx->tx_txg == 0); - txh = dmu_tx_hold_object_impl(tx, tx->tx_objset, - object, THT_WRITE, 0, 0); - if (txh == NULL) - return; - - dnode_t *dn = txh->txh_dnode; - (void) zfs_refcount_add_many(&txh->txh_space_towrite, - 1ULL << dn->dn_indblkshift, FTAG); - dmu_tx_count_dnode(txh); -} - -void dmu_tx_hold_write_by_dnode(dmu_tx_t *tx, dnode_t *dn, uint64_t off, int len) { dmu_tx_hold_t *txh; diff --git a/module/zfs/dsl_dir.c b/module/zfs/dsl_dir.c index 6fb711f59..741ca232e 100644 --- a/module/zfs/dsl_dir.c +++ b/module/zfs/dsl_dir.c @@ -757,35 +757,6 @@ dsl_enforce_ds_ss_limits(dsl_dir_t *dd, zfs_prop_t prop, cred_t *cr) return (enforce); } -static void -dsl_dir_update_last_remap_txg_sync(void *varg, dmu_tx_t *tx) -{ - ddulrt_arg_t *arg = varg; - uint64_t last_remap_txg; - dsl_dir_t *dd = arg->ddulrta_dd; - objset_t *mos = dd->dd_pool->dp_meta_objset; - - dsl_dir_zapify(dd, tx); - if (zap_lookup(mos, dd->dd_object, DD_FIELD_LAST_REMAP_TXG, - sizeof (last_remap_txg), 1, &last_remap_txg) != 0 || - last_remap_txg < arg->ddlrta_txg) { - VERIFY0(zap_update(mos, dd->dd_object, DD_FIELD_LAST_REMAP_TXG, - sizeof (arg->ddlrta_txg), 1, &arg->ddlrta_txg, tx)); - } -} - -int -dsl_dir_update_last_remap_txg(dsl_dir_t *dd, uint64_t txg) -{ - ddulrt_arg_t arg; - arg.ddulrta_dd = dd; - arg.ddlrta_txg = txg; - - return (dsl_sync_task(spa_name(dd->dd_pool->dp_spa), - NULL, dsl_dir_update_last_remap_txg_sync, &arg, - 1, ZFS_SPACE_CHECK_RESERVED)); -} - /* * Check if adding additional child filesystem(s) would exceed any filesystem * limits or adding additional snapshot(s) would exceed any snapshot limits. @@ -1083,19 +1054,6 @@ dsl_dir_get_snapshot_count(dsl_dir_t *dd, uint64_t *count) } } -int -dsl_dir_get_remaptxg(dsl_dir_t *dd, uint64_t *count) -{ - if (dsl_dir_is_zapified(dd)) { - objset_t *os = dd->dd_pool->dp_meta_objset; - return (zap_lookup(os, dd->dd_object, DD_FIELD_LAST_REMAP_TXG, - sizeof (*count), 1, count)); - } else { - return (ENOENT); - } - -} - void dsl_dir_stats(dsl_dir_t *dd, nvlist_t *nv) { @@ -1127,10 +1085,6 @@ dsl_dir_stats(dsl_dir_t *dd, nvlist_t *nv) dsl_prop_nvlist_add_uint64(nv, ZFS_PROP_SNAPSHOT_COUNT, count); } - if (dsl_dir_get_remaptxg(dd, &count) == 0) { - dsl_prop_nvlist_add_uint64(nv, ZFS_PROP_REMAPTXG, - count); - } if (dsl_dir_is_clone(dd)) { char buf[ZFS_MAX_DATASET_NAME_LEN]; diff --git a/module/zfs/zfs_ioctl.c b/module/zfs/zfs_ioctl.c index 2b67761fd..c2b75cc98 100644 --- a/module/zfs/zfs_ioctl.c +++ b/module/zfs/zfs_ioctl.c @@ -1047,14 +1047,6 @@ zfs_secpolicy_bookmark(zfs_cmd_t *zc, nvlist_t *innvl, cred_t *cr) /* ARGSUSED */ static int -zfs_secpolicy_remap(zfs_cmd_t *zc, nvlist_t *innvl, cred_t *cr) -{ - return (zfs_secpolicy_write_perms(zc->zc_name, - ZFS_DELEG_PERM_REMAP, cr)); -} - -/* ARGSUSED */ -static int zfs_secpolicy_destroy_bookmarks(zfs_cmd_t *zc, nvlist_t *innvl, cred_t *cr) { nvpair_t *pair, *nextpair; @@ -3447,11 +3439,8 @@ static const zfs_ioc_key_t zfs_keys_remap[] = { static int zfs_ioc_remap(const char *fsname, nvlist_t *innvl, nvlist_t *outnvl) { - if (strchr(fsname, '@') || - strchr(fsname, '%')) - return (SET_ERROR(EINVAL)); - - return (dmu_objset_remap_indirects(fsname)); + /* This IOCTL is no longer supported. */ + return (0); } /* @@ -6790,7 +6779,7 @@ zfs_ioctl_init(void) zfs_keys_clone, ARRAY_SIZE(zfs_keys_clone)); zfs_ioctl_register("remap", ZFS_IOC_REMAP, - zfs_ioc_remap, zfs_secpolicy_remap, DATASET_NAME, + zfs_ioc_remap, zfs_secpolicy_none, DATASET_NAME, POOL_CHECK_SUSPENDED | POOL_CHECK_READONLY, B_FALSE, B_TRUE, zfs_keys_remap, ARRAY_SIZE(zfs_keys_remap)); diff --git a/tests/runfiles/linux.run b/tests/runfiles/linux.run index b73528e43..4a9c06065 100644 --- a/tests/runfiles/linux.run +++ b/tests/runfiles/linux.run @@ -210,10 +210,6 @@ tests = ['zfs_receive_001_pos', 'zfs_receive_002_pos', 'zfs_receive_003_pos', 'zfs_receive_raw_incremental', 'zfs_receive_-e'] tags = ['functional', 'cli_root', 'zfs_receive'] -[tests/functional/cli_root/zfs_remap] -tests = ['zfs_remap_cliargs', 'zfs_remap_obsolete_counts'] -tags = ['functional', 'cli_root', 'zfs_remap'] - [tests/functional/cli_root/zfs_rename] tests = ['zfs_rename_001_pos', 'zfs_rename_002_pos', 'zfs_rename_003_pos', 'zfs_rename_004_neg', 'zfs_rename_005_neg', 'zfs_rename_006_pos', @@ -767,11 +763,11 @@ tags = ['functional', 'refreserv'] pre = tests = ['removal_all_vdev', 'removal_check_space', 'removal_condense_export', 'removal_multiple_indirection', - 'removal_remap', 'removal_remap_deadlists', + 'removal_remap_deadlists', 'removal_resume_export', 'removal_sanity', 'removal_with_add', 'removal_with_create_fs', 'removal_with_dedup', 'removal_with_errors', 'removal_with_export', - 'removal_with_ganging', 'removal_with_faulted', 'removal_with_remap', + 'removal_with_ganging', 'removal_with_faulted', 'removal_with_remove', 'removal_with_scrub', 'removal_with_send', 'removal_with_send_recv', 'removal_with_snapshot', 'removal_with_write', 'removal_with_zdb', 'remove_expanded', diff --git a/tests/test-runner/bin/zts-report.py b/tests/test-runner/bin/zts-report.py index d046c13a5..b6f3cf22c 100755 --- a/tests/test-runner/bin/zts-report.py +++ b/tests/test-runner/bin/zts-report.py @@ -186,7 +186,6 @@ known = { 'inuse/inuse_007_pos': ['SKIP', na_reason], 'privilege/setup': ['SKIP', na_reason], 'refreserv/refreserv_004_pos': ['FAIL', known_reason], - 'removal/removal_condense_export': ['SKIP', known_reason], 'removal/removal_with_zdb': ['SKIP', known_reason], 'rootpool/setup': ['SKIP', na_reason], 'rsend/rsend_008_pos': ['SKIP', '6066'], diff --git a/tests/zfs-tests/tests/functional/alloc_class/alloc_class_012_pos.ksh b/tests/zfs-tests/tests/functional/alloc_class/alloc_class_012_pos.ksh index bd6c6631f..7ab6a0543 100755 --- a/tests/zfs-tests/tests/functional/alloc_class/alloc_class_012_pos.ksh +++ b/tests/zfs-tests/tests/functional/alloc_class/alloc_class_012_pos.ksh @@ -93,14 +93,7 @@ for i in 1 2 3 4; do log_must file_in_special_vdev $dataset $inum done -# -# remove a special allocation vdev and force a remapping -# N.B. The 'zfs remap' command has been disabled and may be removed. -# -export ZFS_REMAP_ENABLED=YES - log_must zpool remove $TESTPOOL $CLASS_DISK0 -log_must zfs remap $TESTPOOL/$TESTFS sleep 5 log_must sync_pool $TESTPOOL diff --git a/tests/zfs-tests/tests/functional/cli_root/Makefile.am b/tests/zfs-tests/tests/functional/cli_root/Makefile.am index 99f125783..58f789514 100644 --- a/tests/zfs-tests/tests/functional/cli_root/Makefile.am +++ b/tests/zfs-tests/tests/functional/cli_root/Makefile.am @@ -20,7 +20,6 @@ SUBDIRS = \ zfs_promote \ zfs_property \ zfs_receive \ - zfs_remap \ zfs_rename \ zfs_reservation \ zfs_rollback \ diff --git a/tests/zfs-tests/tests/functional/cli_root/zfs_remap/Makefile.am b/tests/zfs-tests/tests/functional/cli_root/zfs_remap/Makefile.am deleted file mode 100644 index 91abff68c..000000000 --- a/tests/zfs-tests/tests/functional/cli_root/zfs_remap/Makefile.am +++ /dev/null @@ -1,7 +0,0 @@ -pkgdatadir = $(datadir)/@PACKAGE@/zfs-tests/tests/functional/cli_root/zfs_remap - -dist_pkgdata_SCRIPTS = \ - setup.ksh \ - cleanup.ksh \ - zfs_remap_cliargs.ksh \ - zfs_remap_obsolete_counts.ksh diff --git a/tests/zfs-tests/tests/functional/cli_root/zfs_remap/cleanup.ksh b/tests/zfs-tests/tests/functional/cli_root/zfs_remap/cleanup.ksh deleted file mode 100755 index e78deacd5..000000000 --- a/tests/zfs-tests/tests/functional/cli_root/zfs_remap/cleanup.ksh +++ /dev/null @@ -1,19 +0,0 @@ -#!/bin/ksh -p -# -# This file and its contents are supplied under the terms of the -# Common Development and Distribution License ("CDDL"), version 1.0. -# You may only use this file in accordance with the terms of version -# 1.0 of the CDDL. -# -# A full copy of the text of the CDDL should have accompanied this -# source. A copy of the CDDL is also available via the Internet at -# http://www.illumos.org/license/CDDL. -# - -# -# Copyright 2018, loli10K <ezomori.nozomu@gmail.com>. All rights reserved. -# - -. $STF_SUITE/include/libtest.shlib - -default_cleanup diff --git a/tests/zfs-tests/tests/functional/cli_root/zfs_remap/setup.ksh b/tests/zfs-tests/tests/functional/cli_root/zfs_remap/setup.ksh deleted file mode 100755 index 4497dbd74..000000000 --- a/tests/zfs-tests/tests/functional/cli_root/zfs_remap/setup.ksh +++ /dev/null @@ -1,17 +0,0 @@ -#!/bin/ksh -p -# -# This file and its contents are supplied under the terms of the -# Common Development and Distribution License ("CDDL"), version 1.0. -# You may only use this file in accordance with the terms of version -# 1.0 of the CDDL. -# -# A full copy of the text of the CDDL should have accompanied this -# source. A copy of the CDDL is also available via the Internet at -# http://www.illumos.org/license/CDDL. -# - -# -# Copyright 2018, loli10K <ezomori.nozomu@gmail.com>. All rights reserved. -# - -. $STF_SUITE/include/libtest.shlib diff --git a/tests/zfs-tests/tests/functional/cli_root/zfs_remap/zfs_remap_cliargs.ksh b/tests/zfs-tests/tests/functional/cli_root/zfs_remap/zfs_remap_cliargs.ksh deleted file mode 100755 index 80a5e6e0d..000000000 --- a/tests/zfs-tests/tests/functional/cli_root/zfs_remap/zfs_remap_cliargs.ksh +++ /dev/null @@ -1,81 +0,0 @@ -#!/bin/ksh -p -# -# This file and its contents are supplied under the terms of the -# Common Development and Distribution License ("CDDL"), version 1.0. -# You may only use this file in accordance with the terms of version -# 1.0 of the CDDL. -# -# A full copy of the text of the CDDL should have accompanied this -# source. A copy of the CDDL is also available via the Internet at -# http://www.illumos.org/license/CDDL. -# - -# -# Copyright 2018, loli10K <ezomori.nozomu@gmail.com>. All rights reserved. -# - -. $STF_SUITE/include/libtest.shlib -. $STF_SUITE/tests/functional/removal/removal.kshlib - -# -# DESCRIPTION: -# 'zfs remap' should only work with supported parameters. -# -# STRATEGY: -# 1. Prepare a pool where a top-level VDEV has been removed -# 2. Verify every supported parameter to 'zfs remap' is accepted -# 3. Verify other unsupported parameters raise an error -# - -# The 'zfs remap' command has been disabled and may be removed. -export ZFS_REMAP_ENABLED=YES - -verify_runnable "both" - -function cleanup -{ - destroy_pool $TESTPOOL - rm -f $DISK1 $DISK2 -} - -log_assert "'zfs remap' should only work with supported parameters" -log_onexit cleanup - -f="$TESTPOOL/fs" -v="$TESTPOOL/vol" -s="$TESTPOOL/fs@snap" -b="$TESTPOOL/fs#bmark" -c="$TESTPOOL/clone" - -typeset goodparams=("$f" "$v" "$c") -typeset badparams=("-H" "-p" "-?" "$s" "$b" "$f $f" "$f $v" "$f $s") - -DISK1="$TEST_BASE_DIR/zfs_remap-1" -DISK2="$TEST_BASE_DIR/zfs_remap-2" - -# 1. Prepare a pool where a top-level VDEV has been removed -log_must truncate -s $(($MINVDEVSIZE * 2)) $DISK1 -log_must zpool create $TESTPOOL $DISK1 -log_must zfs create $f -log_must zfs create -V 1M -s $v -log_must zfs snap $s -log_must zfs bookmark $s $b -log_must zfs clone $s $c -log_must truncate -s $(($MINVDEVSIZE * 2)) $DISK2 -log_must zpool add $TESTPOOL $DISK2 -log_must zpool remove $TESTPOOL $DISK1 -log_must wait_for_removal $TESTPOOL - -# 2. Verify every supported parameter to 'zfs remap' is accepted -for param in "${goodparams[@]}" -do - log_must zfs remap $param -done - -# 3. Verify other unsupported parameters raise an error -for param in "${badparams[@]}" -do - log_mustnot zfs remap $param -done - -log_pass "'zfs remap' only works with supported parameters" diff --git a/tests/zfs-tests/tests/functional/cli_root/zfs_remap/zfs_remap_obsolete_counts.ksh b/tests/zfs-tests/tests/functional/cli_root/zfs_remap/zfs_remap_obsolete_counts.ksh deleted file mode 100755 index 1f0e0e85d..000000000 --- a/tests/zfs-tests/tests/functional/cli_root/zfs_remap/zfs_remap_obsolete_counts.ksh +++ /dev/null @@ -1,79 +0,0 @@ -#!/bin/ksh -p -# -# This file and its contents are supplied under the terms of the -# Common Development and Distribution License ("CDDL"), version 1.0. -# You may only use this file in accordance with the terms of version -# 1.0 of the CDDL. -# -# A full copy of the text of the CDDL should have accompanied this -# source. A copy of the CDDL is also available via the Internet at -# http://www.illumos.org/license/CDDL. -# - -# -# Copyright 2018, loli10K <ezomori.nozomu@gmail.com>. All rights reserved. -# - -. $STF_SUITE/include/libtest.shlib -. $STF_SUITE/tests/functional/removal/removal.kshlib - -# -# DESCRIPTION: -# 'zfs remap' depends on 'feature@obsolete_counts' being active -# -# STRATEGY: -# 1. Prepare a pool where a top-level VDEV has been removed and with -# feature@obsolete_counts disabled -# 2. Verify any 'zfs remap' command cannot be executed -# 3. Verify the same commands complete successfully when -# feature@obsolete_counts is enabled -# - -# N.B. The 'zfs remap' command has been disabled and may be removed. -export ZFS_REMAP_ENABLED=YES - -verify_runnable "both" - -function cleanup -{ - destroy_pool $TESTPOOL - rm -f $DISK1 $DISK2 -} - -log_assert "'zfs remap' depends on feature@obsolete_counts being active" -log_onexit cleanup - -f="$TESTPOOL/fs" -v="$TESTPOOL/vol" -s="$TESTPOOL/fs@snap" -c="$TESTPOOL/clone" - -DISK1="$TEST_BASE_DIR/zfs_remap-1" -DISK2="$TEST_BASE_DIR/zfs_remap-2" - -# 1. Prepare a pool where a top-level VDEV has been removed with -# feature@obsolete_counts disabled -log_must truncate -s $(($MINVDEVSIZE * 2)) $DISK1 -log_must zpool create -o feature@obsolete_counts=disabled $TESTPOOL $DISK1 -log_must zfs create $f -log_must zfs create -V 1M -s $v -log_must zfs snap $s -log_must zfs clone $s $c -log_must truncate -s $(($MINVDEVSIZE * 2)) $DISK2 -log_must zpool add $TESTPOOL $DISK2 -log_must zpool remove $TESTPOOL $DISK1 -log_must wait_for_removal $TESTPOOL - -# 2. Verify any 'zfs remap' command cannot be executed -log_mustnot zfs remap $f -log_mustnot zfs remap $v -log_mustnot zfs remap $c - -# 3. Verify the same commands complete successfully when -# feature@obsolete_counts is enabled -log_must zpool set feature@obsolete_counts=enabled $TESTPOOL -log_must zfs remap $f -log_must zfs remap $v -log_must zfs remap $c - -log_pass "'zfs remap' correctly depends on feature@obsolete_counts being active" diff --git a/tests/zfs-tests/tests/functional/removal/Makefile.am b/tests/zfs-tests/tests/functional/removal/Makefile.am index ba42b899a..dc52bf1f2 100644 --- a/tests/zfs-tests/tests/functional/removal/Makefile.am +++ b/tests/zfs-tests/tests/functional/removal/Makefile.am @@ -18,12 +18,12 @@ pkgdatadir = $(datadir)/@PACKAGE@/zfs-tests/tests/functional/removal dist_pkgdata_SCRIPTS = \ cleanup.ksh removal_all_vdev.ksh removal_check_space.ksh \ removal_condense_export.ksh removal_multiple_indirection.ksh \ - removal_remap_deadlists.ksh removal_remap.ksh \ + removal_remap_deadlists.ksh \ removal_reservation.ksh removal_resume_export.ksh \ removal_sanity.ksh removal_with_add.ksh removal_with_create_fs.ksh \ removal_with_dedup.ksh removal_with_errors.ksh \ removal_with_export.ksh removal_with_faulted.ksh \ - removal_with_ganging.ksh removal_with_remap.ksh \ + removal_with_ganging.ksh \ removal_with_remove.ksh removal_with_scrub.ksh \ removal_with_send.ksh removal_with_send_recv.ksh \ removal_with_snapshot.ksh removal_with_write.ksh \ diff --git a/tests/zfs-tests/tests/functional/removal/removal_condense_export.ksh b/tests/zfs-tests/tests/functional/removal/removal_condense_export.ksh index ad33caec8..655352f05 100755 --- a/tests/zfs-tests/tests/functional/removal/removal_condense_export.ksh +++ b/tests/zfs-tests/tests/functional/removal/removal_condense_export.ksh @@ -21,10 +21,6 @@ . $STF_SUITE/include/libtest.shlib . $STF_SUITE/tests/functional/removal/removal.kshlib -if is_linux; then - log_unsupported "ZDB fails during concurrent pool activity." -fi - function reset { log_must set_tunable64 zfs_condense_indirect_commit_entry_delay_ms 0 @@ -77,7 +73,14 @@ log_must zpool remove $TESTPOOL $REMOVEDISK log_must wait_for_removal $TESTPOOL log_mustnot vdevs_in_pool $TESTPOOL $REMOVEDISK -log_must zfs remap $TESTPOOL/$TESTFS +# +# Touch one block under each L1 indirect block, so that the other data blocks +# will be remapped to their concrete locations. These parameters assume +# recordsize=512, indirect block size of 128K (1024 block pointers per +# indirect block), and file size of less than 20*1024 blocks (10MB). +# +log_must stride_dd -i /dev/urandom -o $TESTDIR/file -b 512 -c 20 -s 1024 + sync_pool $TESTPOOL sleep 5 sync_pool $TESTPOOL diff --git a/tests/zfs-tests/tests/functional/removal/removal_remap.ksh b/tests/zfs-tests/tests/functional/removal/removal_remap.ksh deleted file mode 100755 index 5239ef3a5..000000000 --- a/tests/zfs-tests/tests/functional/removal/removal_remap.ksh +++ /dev/null @@ -1,126 +0,0 @@ -#! /bin/ksh -p -# -# CDDL HEADER START -# -# This file and its contents are supplied under the terms of the -# Common Development and Distribution License ("CDDL"), version 1.0. -# You may only use this file in accordance with the terms of version -# 1.0 of the CDDL. -# -# A full copy of the text of the CDDL should have accompanied this -# source. A copy of the CDDL is also available via the Internet at -# http://www.illumos.org/license/CDDL. -# -# CDDL HEADER END -# - -# -# Copyright (c) 2015, 2016 by Delphix. All rights reserved. -# - -. $STF_SUITE/include/libtest.shlib -. $STF_SUITE/tests/functional/removal/removal.kshlib - -# N.B. The 'zfs remap' command has been disabled and may be removed. -export ZFS_REMAP_ENABLED=YES - -default_setup_noexit "$DISKS" - - -function cleanup -{ - set_tunable64 zfs_condense_min_mapping_bytes 131072 - default_cleanup_noexit -} - -log_onexit cleanup - -log_must set_tunable64 zfs_condense_min_mapping_bytes 1 - -log_must zfs set recordsize=512 $TESTPOOL/$TESTFS - -# -# Create a large file so that we know some of the blocks will be on the -# removed device, and hence eligible for remapping. -# -log_must dd if=/dev/urandom of=$TESTDIR/file bs=$((2**12)) count=$((2**9)) - -# -# Randomly rewrite some of blocks in the file so that there will be holes and -# we will not be able to remap the entire file in a few huge chunks. -# -for i in $(seq $((2**12))); do - # - # We have to sync periodically so that all the writes don't end up in - # the same txg. If they were all in the same txg, only the last write - # would go through and we would not have as many allocations to - # fragment the file. - # - ((i % 100 > 0 )) || sync_pool || log_fail "Could not sync." - random_write $TESTDIR/file $((2**9)) || \ - log_fail "Could not random write." -done - -# -# Remap should quietly succeed as a noop before a removal. -# -log_must zfs remap $TESTPOOL/$TESTFS -remaptxg_before=$(zfs get -H -o value remaptxg $TESTPOOL/$TESTFS) -(( $? == 0 )) || log_fail "Could not get remaptxg." -[[ $remaptxg_before == "-" ]] || \ - log_fail "remaptxg ($remaptxg_before) had value before a removal" - -log_must zpool remove $TESTPOOL $REMOVEDISK -log_must wait_for_removal $TESTPOOL -log_mustnot vdevs_in_pool $TESTPOOL $REMOVEDISK - -# -# remaptxg should not be set if we haven't done a remap. -# -remaptxg_before=$(zfs get -H -o value remaptxg $TESTPOOL/$TESTFS) -(( $? == 0 )) || log_fail "Could not get remaptxg." -[[ $remaptxg_before == "-" ]] || \ - log_fail "remaptxg ($remaptxg_before) had value before a removal" - -mapping_size_before=$(indirect_vdev_mapping_size $TESTPOOL) -log_must zfs remap $TESTPOOL/$TESTFS - -# Try to wait for a condense to finish. -for i in {1..5}; do - sleep 5 - sync_pool -done -mapping_size_after=$(indirect_vdev_mapping_size $TESTPOOL) - -# -# After the remap, there should not be very many blocks referenced. The reason -# why our threshold is as high as 512 is because our ratio of metadata to -# user data is relatively high, with only 64M of user data on the file system. -# -(( mapping_size_after < mapping_size_before )) || \ - log_fail "Mapping size did not decrease after remap: " \ - "$mapping_size_before before to $mapping_size_after after." -(( mapping_size_after < 512 )) || \ - log_fail "Mapping size not small enough after remap: " \ - "$mapping_size_before before to $mapping_size_after after." - -# -# After a remap, the remaptxg should be set to a non-zero value. -# -remaptxg_after=$(zfs get -H -o value remaptxg $TESTPOOL/$TESTFS) -(( $? == 0 )) || log_fail "Could not get remaptxg." -log_note "remap txg after remap is $remaptxg_after" -(( remaptxg_after > 0 )) || log_fail "remaptxg not increased" - -# -# Remap should quietly succeed as a noop if there have been no removals since -# the last remap. -# -log_must zfs remap $TESTPOOL/$TESTFS -remaptxg_again=$(zfs get -H -o value remaptxg $TESTPOOL/$TESTFS) -(( $? == 0 )) || log_fail "Could not get remaptxg." -log_note "remap txg after second remap is $remaptxg_again" -(( remaptxg_again == remaptxg_after )) || \ - log_fail "remap not noop if there has been no removal" - -log_pass "Remapping a fs caused mapping size to decrease." diff --git a/tests/zfs-tests/tests/functional/removal/removal_remap_deadlists.ksh b/tests/zfs-tests/tests/functional/removal/removal_remap_deadlists.ksh index a2f6580b4..6db3587c5 100755 --- a/tests/zfs-tests/tests/functional/removal/removal_remap_deadlists.ksh +++ b/tests/zfs-tests/tests/functional/removal/removal_remap_deadlists.ksh @@ -21,9 +21,6 @@ . $STF_SUITE/include/libtest.shlib . $STF_SUITE/tests/functional/removal/removal.kshlib -# N.B. The 'zfs remap' command has been disabled and may be removed. -export ZFS_REMAP_ENABLED=YES - default_setup_noexit "$DISKS" log_onexit default_cleanup_noexit @@ -45,7 +42,14 @@ fi log_mustnot vdevs_in_pool $TESTPOOL $REMOVEDISK log_must zdb -cd $TESTPOOL -log_must zfs remap $TESTPOOL/$TESTFS +# +# Touch one block under each L1 indirect block, so that the other data blocks +# will be remapped to their concrete locations. These parameters assume +# recordsize=128K, indirect block size of 128K (1024 block pointers per +# indirect block), and file size of less than 3*1024 blocks (384MB). +# +log_must stride_dd -i /dev/urandom -o $TESTDIR/file -b 131072 -c 3 -s 1024 + log_must zdb -cd $TESTPOOL log_must zfs snapshot $TESTPOOL/$TESTFS@snap-post3 diff --git a/tests/zfs-tests/tests/functional/removal/removal_with_remap.ksh b/tests/zfs-tests/tests/functional/removal/removal_with_remap.ksh deleted file mode 100755 index 6f56740b8..000000000 --- a/tests/zfs-tests/tests/functional/removal/removal_with_remap.ksh +++ /dev/null @@ -1,32 +0,0 @@ -#! /bin/ksh -p -# -# CDDL HEADER START -# -# This file and its contents are supplied under the terms of the -# Common Development and Distribution License ("CDDL"), version 1.0. -# You may only use this file in accordance with the terms of version -# 1.0 of the CDDL. -# -# A full copy of the text of the CDDL should have accompanied this -# source. A copy of the CDDL is also available via the Internet at -# http://www.illumos.org/license/CDDL. -# -# CDDL HEADER END -# - -# -# Copyright (c) 2015, 2017 by Delphix. All rights reserved. -# - -. $STF_SUITE/include/libtest.shlib -. $STF_SUITE/tests/functional/removal/removal.kshlib - -# N.B. The 'zfs remap' command has been disabled and may be removed. -export ZFS_REMAP_ENABLED=YES - -default_setup_noexit "$DISKS" -log_onexit default_cleanup_noexit - -test_removal_with_operation zfs remap $TESTPOOL/$TESTFS - -log_pass "Can remap a filesystem during removal" |