Print this page
4171 clean up spa_feature_*() interfaces
4172 implement extensible_dataset feature for use by other zpool features
Reviewed by: Max Grossman <max.grossman@delphix.com>
Reviewed by: Christopher Siden <christopher.siden@delphix.com>
Reviewed by: George Wilson <george.wilson@delphix.com>


 457         kmem_free(sm, sizeof (*sm));
 458 }
 459 
 460 static void
 461 space_map_reallocate(space_map_t *sm, dmu_tx_t *tx)
 462 {
 463         ASSERT(dmu_tx_is_syncing(tx));
 464 
 465         space_map_free(sm, tx);
 466         dmu_buf_rele(sm->sm_dbuf, sm);
 467 
 468         sm->sm_object = space_map_alloc(sm->sm_os, tx);
 469         VERIFY0(space_map_open_impl(sm));
 470 }
 471 
 472 void
 473 space_map_truncate(space_map_t *sm, dmu_tx_t *tx)
 474 {
 475         objset_t *os = sm->sm_os;
 476         spa_t *spa = dmu_objset_spa(os);
 477         zfeature_info_t *space_map_histogram =
 478             &spa_feature_table[SPA_FEATURE_SPACEMAP_HISTOGRAM];
 479         dmu_object_info_t doi;
 480         int bonuslen;
 481 
 482         ASSERT(dsl_pool_sync_context(dmu_objset_pool(os)));
 483         ASSERT(dmu_tx_is_syncing(tx));
 484 
 485         VERIFY0(dmu_free_range(os, space_map_object(sm), 0, -1ULL, tx));
 486         dmu_object_info_from_db(sm->sm_dbuf, &doi);
 487 
 488         if (spa_feature_is_enabled(spa, space_map_histogram)) {
 489                 bonuslen = sizeof (space_map_phys_t);
 490                 ASSERT3U(bonuslen, <=, dmu_bonus_max());
 491         } else {
 492                 bonuslen = SPACE_MAP_SIZE_V0;
 493         }
 494 
 495         if (bonuslen != doi.doi_bonus_size ||
 496             doi.doi_data_block_size != SPACE_MAP_INITIAL_BLOCKSIZE) {
 497                 zfs_dbgmsg("txg %llu, spa %s, reallocating: "
 498                     "old bonus %u, old blocksz %u", dmu_tx_get_txg(tx),
 499                     spa_name(spa), doi.doi_bonus_size, doi.doi_data_block_size);
 500                 space_map_reallocate(sm, tx);
 501                 VERIFY3U(sm->sm_blksz, ==, SPACE_MAP_INITIAL_BLOCKSIZE);
 502         }
 503 
 504         dmu_buf_will_dirty(sm->sm_dbuf, tx);
 505         sm->sm_phys->smp_objsize = 0;
 506         sm->sm_phys->smp_alloc = 0;
 507 }
 508 
 509 /*
 510  * Update the in-core space_map allocation and length values.
 511  */
 512 void
 513 space_map_update(space_map_t *sm)
 514 {
 515         if (sm == NULL)
 516                 return;
 517 
 518         ASSERT(MUTEX_HELD(sm->sm_lock));
 519 
 520         sm->sm_alloc = sm->sm_phys->smp_alloc;
 521         sm->sm_length = sm->sm_phys->smp_objsize;
 522 }
 523 
 524 uint64_t
 525 space_map_alloc(objset_t *os, dmu_tx_t *tx)
 526 {
 527         spa_t *spa = dmu_objset_spa(os);
 528         zfeature_info_t *space_map_histogram =
 529             &spa_feature_table[SPA_FEATURE_SPACEMAP_HISTOGRAM];
 530         uint64_t object;
 531         int bonuslen;
 532 
 533         if (spa_feature_is_enabled(spa, space_map_histogram)) {
 534                 spa_feature_incr(spa, space_map_histogram, tx);
 535                 bonuslen = sizeof (space_map_phys_t);
 536                 ASSERT3U(bonuslen, <=, dmu_bonus_max());
 537         } else {
 538                 bonuslen = SPACE_MAP_SIZE_V0;
 539         }
 540 
 541         object = dmu_object_alloc(os,
 542             DMU_OT_SPACE_MAP, SPACE_MAP_INITIAL_BLOCKSIZE,
 543             DMU_OT_SPACE_MAP_HEADER, bonuslen, tx);
 544 
 545         return (object);
 546 }
 547 
 548 void
 549 space_map_free(space_map_t *sm, dmu_tx_t *tx)
 550 {
 551         spa_t *spa;
 552         zfeature_info_t *space_map_histogram =
 553             &spa_feature_table[SPA_FEATURE_SPACEMAP_HISTOGRAM];
 554 
 555         if (sm == NULL)
 556                 return;
 557 
 558         spa = dmu_objset_spa(sm->sm_os);
 559         if (spa_feature_is_enabled(spa, space_map_histogram)) {
 560                 dmu_object_info_t doi;
 561 
 562                 dmu_object_info_from_db(sm->sm_dbuf, &doi);
 563                 if (doi.doi_bonus_size != SPACE_MAP_SIZE_V0) {
 564                         VERIFY(spa_feature_is_active(spa, space_map_histogram));
 565                         spa_feature_decr(spa, space_map_histogram, tx);


 566                 }
 567         }
 568 
 569         VERIFY3U(dmu_object_free(sm->sm_os, space_map_object(sm), tx), ==, 0);
 570         sm->sm_object = 0;
 571 }
 572 
 573 uint64_t
 574 space_map_object(space_map_t *sm)
 575 {
 576         return (sm != NULL ? sm->sm_object : 0);
 577 }
 578 
 579 /*
 580  * Returns the already synced, on-disk allocated space.
 581  */
 582 uint64_t
 583 space_map_allocated(space_map_t *sm)
 584 {
 585         return (sm != NULL ? sm->sm_alloc : 0);




 457         kmem_free(sm, sizeof (*sm));
 458 }
 459 
 460 static void
 461 space_map_reallocate(space_map_t *sm, dmu_tx_t *tx)
 462 {
 463         ASSERT(dmu_tx_is_syncing(tx));
 464 
 465         space_map_free(sm, tx);
 466         dmu_buf_rele(sm->sm_dbuf, sm);
 467 
 468         sm->sm_object = space_map_alloc(sm->sm_os, tx);
 469         VERIFY0(space_map_open_impl(sm));
 470 }
 471 
 472 void
 473 space_map_truncate(space_map_t *sm, dmu_tx_t *tx)
 474 {
 475         objset_t *os = sm->sm_os;
 476         spa_t *spa = dmu_objset_spa(os);


 477         dmu_object_info_t doi;
 478         int bonuslen;
 479 
 480         ASSERT(dsl_pool_sync_context(dmu_objset_pool(os)));
 481         ASSERT(dmu_tx_is_syncing(tx));
 482 
 483         VERIFY0(dmu_free_range(os, space_map_object(sm), 0, -1ULL, tx));
 484         dmu_object_info_from_db(sm->sm_dbuf, &doi);
 485 
 486         if (spa_feature_is_enabled(spa, SPA_FEATURE_SPACEMAP_HISTOGRAM)) {
 487                 bonuslen = sizeof (space_map_phys_t);
 488                 ASSERT3U(bonuslen, <=, dmu_bonus_max());
 489         } else {
 490                 bonuslen = SPACE_MAP_SIZE_V0;
 491         }
 492 
 493         if (bonuslen != doi.doi_bonus_size ||
 494             doi.doi_data_block_size != SPACE_MAP_INITIAL_BLOCKSIZE) {
 495                 zfs_dbgmsg("txg %llu, spa %s, reallocating: "
 496                     "old bonus %u, old blocksz %u", dmu_tx_get_txg(tx),
 497                     spa_name(spa), doi.doi_bonus_size, doi.doi_data_block_size);
 498                 space_map_reallocate(sm, tx);
 499                 VERIFY3U(sm->sm_blksz, ==, SPACE_MAP_INITIAL_BLOCKSIZE);
 500         }
 501 
 502         dmu_buf_will_dirty(sm->sm_dbuf, tx);
 503         sm->sm_phys->smp_objsize = 0;
 504         sm->sm_phys->smp_alloc = 0;
 505 }
 506 
 507 /*
 508  * Update the in-core space_map allocation and length values.
 509  */
 510 void
 511 space_map_update(space_map_t *sm)
 512 {
 513         if (sm == NULL)
 514                 return;
 515 
 516         ASSERT(MUTEX_HELD(sm->sm_lock));
 517 
 518         sm->sm_alloc = sm->sm_phys->smp_alloc;
 519         sm->sm_length = sm->sm_phys->smp_objsize;
 520 }
 521 
 522 uint64_t
 523 space_map_alloc(objset_t *os, dmu_tx_t *tx)
 524 {
 525         spa_t *spa = dmu_objset_spa(os);


 526         uint64_t object;
 527         int bonuslen;
 528 
 529         if (spa_feature_is_enabled(spa, SPA_FEATURE_SPACEMAP_HISTOGRAM)) {
 530                 spa_feature_incr(spa, SPA_FEATURE_SPACEMAP_HISTOGRAM, tx);
 531                 bonuslen = sizeof (space_map_phys_t);
 532                 ASSERT3U(bonuslen, <=, dmu_bonus_max());
 533         } else {
 534                 bonuslen = SPACE_MAP_SIZE_V0;
 535         }
 536 
 537         object = dmu_object_alloc(os,
 538             DMU_OT_SPACE_MAP, SPACE_MAP_INITIAL_BLOCKSIZE,
 539             DMU_OT_SPACE_MAP_HEADER, bonuslen, tx);
 540 
 541         return (object);
 542 }
 543 
 544 void
 545 space_map_free(space_map_t *sm, dmu_tx_t *tx)
 546 {
 547         spa_t *spa;


 548 
 549         if (sm == NULL)
 550                 return;
 551 
 552         spa = dmu_objset_spa(sm->sm_os);
 553         if (spa_feature_is_enabled(spa, SPA_FEATURE_SPACEMAP_HISTOGRAM)) {
 554                 dmu_object_info_t doi;
 555 
 556                 dmu_object_info_from_db(sm->sm_dbuf, &doi);
 557                 if (doi.doi_bonus_size != SPACE_MAP_SIZE_V0) {
 558                         VERIFY(spa_feature_is_active(spa,
 559                             SPA_FEATURE_SPACEMAP_HISTOGRAM));
 560                         spa_feature_decr(spa,
 561                             SPA_FEATURE_SPACEMAP_HISTOGRAM, tx);
 562                 }
 563         }
 564 
 565         VERIFY3U(dmu_object_free(sm->sm_os, space_map_object(sm), tx), ==, 0);
 566         sm->sm_object = 0;
 567 }
 568 
 569 uint64_t
 570 space_map_object(space_map_t *sm)
 571 {
 572         return (sm != NULL ? sm->sm_object : 0);
 573 }
 574 
 575 /*
 576  * Returns the already synced, on-disk allocated space.
 577  */
 578 uint64_t
 579 space_map_allocated(space_map_t *sm)
 580 {
 581         return (sm != NULL ? sm->sm_alloc : 0);