Print this page
2619 asynchronous destruction of ZFS file systems
2747 SPA versioning with zfs feature flags
Reviewed by: Matt Ahrens <mahrens@delphix.com>
Reviewed by: George Wilson <gwilson@delphix.com>
Reviewed by: Richard Lowe <richlowe@richlowe.net>
Reviewed by: Dan Kruchinin <dan.kruchinin@gmail.com>
Approved by: Dan McDonald <danmcd@nexenta.com>

*** 18,28 **** * * CDDL HEADER END */ /* * Copyright (c) 2005, 2010, Oracle and/or its affiliates. All rights reserved. ! * Copyright (c) 2011 by Delphix. All rights reserved. */ #include <sys/dsl_pool.h> #include <sys/dsl_dataset.h> #include <sys/dsl_prop.h> --- 18,28 ---- * * CDDL HEADER END */ /* * Copyright (c) 2005, 2010, Oracle and/or its affiliates. All rights reserved. ! * Copyright (c) 2012 by Delphix. All rights reserved. */ #include <sys/dsl_pool.h> #include <sys/dsl_dataset.h> #include <sys/dsl_prop.h>
*** 38,47 **** --- 38,49 ---- #include <sys/zfs_context.h> #include <sys/fs/zfs.h> #include <sys/zfs_znode.h> #include <sys/spa_impl.h> #include <sys/dsl_deadlist.h> + #include <sys/bptree.h> + #include <sys/zfeature.h> int zfs_no_write_throttle = 0; int zfs_write_limit_shift = 3; /* 1/8th of physical memory */ int zfs_txg_synctime_ms = 1000; /* target millisecs to sync a txg */
*** 98,121 **** return (dp); } int ! dsl_pool_open(spa_t *spa, uint64_t txg, dsl_pool_t **dpp) { int err; dsl_pool_t *dp = dsl_pool_open_impl(spa, txg); dsl_dir_t *dd; dsl_dataset_t *ds; uint64_t obj; ! rw_enter(&dp->dp_config_rwlock, RW_WRITER); ! err = dmu_objset_open_impl(spa, NULL, &dp->dp_meta_rootbp, ! &dp->dp_meta_objset); ! if (err) ! goto out; err = zap_lookup(dp->dp_meta_objset, DMU_POOL_DIRECTORY_OBJECT, DMU_POOL_ROOT_DATASET, sizeof (uint64_t), 1, &dp->dp_root_dir_obj); if (err) goto out; --- 100,135 ---- return (dp); } int ! dsl_pool_init(spa_t *spa, uint64_t txg, dsl_pool_t **dpp) { int err; dsl_pool_t *dp = dsl_pool_open_impl(spa, txg); + + err = dmu_objset_open_impl(spa, NULL, &dp->dp_meta_rootbp, + &dp->dp_meta_objset); + if (err != 0) + dsl_pool_close(dp); + else + *dpp = dp; + + return (err); + } + + int + dsl_pool_open(dsl_pool_t *dp) + { + int err; dsl_dir_t *dd; dsl_dataset_t *ds; uint64_t obj; ! ASSERT(!dmu_objset_is_dirty_anywhere(dp->dp_meta_objset)); + rw_enter(&dp->dp_config_rwlock, RW_WRITER); err = zap_lookup(dp->dp_meta_objset, DMU_POOL_DIRECTORY_OBJECT, DMU_POOL_ROOT_DATASET, sizeof (uint64_t), 1, &dp->dp_root_dir_obj); if (err) goto out;
*** 127,137 **** err = dsl_pool_open_special_dir(dp, MOS_DIR_NAME, &dp->dp_mos_dir); if (err) goto out; ! if (spa_version(spa) >= SPA_VERSION_ORIGIN) { err = dsl_pool_open_special_dir(dp, ORIGIN_DIR_NAME, &dd); if (err) goto out; err = dsl_dataset_hold_obj(dp, dd->dd_phys->dd_head_dataset_obj, FTAG, &ds); --- 141,151 ---- err = dsl_pool_open_special_dir(dp, MOS_DIR_NAME, &dp->dp_mos_dir); if (err) goto out; ! if (spa_version(dp->dp_spa) >= SPA_VERSION_ORIGIN) { err = dsl_pool_open_special_dir(dp, ORIGIN_DIR_NAME, &dd); if (err) goto out; err = dsl_dataset_hold_obj(dp, dd->dd_phys->dd_head_dataset_obj, FTAG, &ds);
*** 144,154 **** dsl_dir_close(dd, dp); if (err) goto out; } ! if (spa_version(spa) >= SPA_VERSION_DEADLISTS) { err = dsl_pool_open_special_dir(dp, FREE_DIR_NAME, &dp->dp_free_dir); if (err) goto out; --- 158,168 ---- dsl_dir_close(dd, dp); if (err) goto out; } ! if (spa_version(dp->dp_spa) >= SPA_VERSION_DEADLISTS) { err = dsl_pool_open_special_dir(dp, FREE_DIR_NAME, &dp->dp_free_dir); if (err) goto out;
*** 158,184 **** goto out; VERIFY3U(0, ==, bpobj_open(&dp->dp_free_bpobj, dp->dp_meta_objset, obj)); } err = zap_lookup(dp->dp_meta_objset, DMU_POOL_DIRECTORY_OBJECT, DMU_POOL_TMP_USERREFS, sizeof (uint64_t), 1, &dp->dp_tmp_userrefs_obj); if (err == ENOENT) err = 0; if (err) goto out; ! err = dsl_scan_init(dp, txg); out: rw_exit(&dp->dp_config_rwlock); - if (err) - dsl_pool_close(dp); - else - *dpp = dp; - return (err); } void dsl_pool_close(dsl_pool_t *dp) --- 172,202 ---- goto out; VERIFY3U(0, ==, bpobj_open(&dp->dp_free_bpobj, dp->dp_meta_objset, obj)); } + if (spa_feature_is_active(dp->dp_spa, + &spa_feature_table[SPA_FEATURE_ASYNC_DESTROY])) { err = zap_lookup(dp->dp_meta_objset, DMU_POOL_DIRECTORY_OBJECT, + DMU_POOL_BPTREE_OBJ, sizeof (uint64_t), 1, + &dp->dp_bptree_obj); + if (err != 0) + goto out; + } + + err = zap_lookup(dp->dp_meta_objset, DMU_POOL_DIRECTORY_OBJECT, DMU_POOL_TMP_USERREFS, sizeof (uint64_t), 1, &dp->dp_tmp_userrefs_obj); if (err == ENOENT) err = 0; if (err) goto out; ! err = dsl_scan_init(dp, dp->dp_tx.tx_open_txg); out: rw_exit(&dp->dp_config_rwlock); return (err); } void dsl_pool_close(dsl_pool_t *dp)
*** 468,478 **** */ int dsl_pool_sync_context(dsl_pool_t *dp) { return (curthread == dp->dp_tx.tx_sync_thread || ! spa_get_dsl(dp->dp_spa) == NULL); } uint64_t dsl_pool_adjustedsize(dsl_pool_t *dp, boolean_t netfree) { --- 486,496 ---- */ int dsl_pool_sync_context(dsl_pool_t *dp) { return (curthread == dp->dp_tx.tx_sync_thread || ! spa_is_initializing(dp->dp_spa)); } uint64_t dsl_pool_adjustedsize(dsl_pool_t *dp, boolean_t netfree) {
*** 786,800 **** objset_t *mos = dp->dp_meta_objset; ASSERT(dp->dp_tmp_userrefs_obj == 0); ASSERT(dmu_tx_is_syncing(tx)); ! dp->dp_tmp_userrefs_obj = zap_create(mos, DMU_OT_USERREFS, ! DMU_OT_NONE, 0, tx); ! ! VERIFY(zap_add(mos, DMU_POOL_DIRECTORY_OBJECT, DMU_POOL_TMP_USERREFS, ! sizeof (uint64_t), 1, &dp->dp_tmp_userrefs_obj, tx) == 0); } static int dsl_pool_user_hold_rele_impl(dsl_pool_t *dp, uint64_t dsobj, const char *tag, uint64_t *now, dmu_tx_t *tx, boolean_t holding) --- 804,815 ---- objset_t *mos = dp->dp_meta_objset; ASSERT(dp->dp_tmp_userrefs_obj == 0); ASSERT(dmu_tx_is_syncing(tx)); ! dp->dp_tmp_userrefs_obj = zap_create_link(mos, DMU_OT_USERREFS, ! DMU_POOL_DIRECTORY_OBJECT, DMU_POOL_TMP_USERREFS, tx); } static int dsl_pool_user_hold_rele_impl(dsl_pool_t *dp, uint64_t dsobj, const char *tag, uint64_t *now, dmu_tx_t *tx, boolean_t holding)