zdb.c (177698) | zdb.c (185029) |
---|---|
1/* 2 * CDDL HEADER START 3 * 4 * The contents of this file are subject to the terms of the 5 * Common Development and Distribution License (the "License"). 6 * You may not use this file except in compliance with the License. 7 * 8 * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE --- 5 unchanged lines hidden (view full) --- 14 * file and include the License file at usr/src/OPENSOLARIS.LICENSE. 15 * If applicable, add the following below this CDDL HEADER, with the 16 * fields enclosed by brackets "[]" replaced with your own identifying 17 * information: Portions Copyright [yyyy] [name of copyright owner] 18 * 19 * CDDL HEADER END 20 */ 21/* | 1/* 2 * CDDL HEADER START 3 * 4 * The contents of this file are subject to the terms of the 5 * Common Development and Distribution License (the "License"). 6 * You may not use this file except in compliance with the License. 7 * 8 * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE --- 5 unchanged lines hidden (view full) --- 14 * file and include the License file at usr/src/OPENSOLARIS.LICENSE. 15 * If applicable, add the following below this CDDL HEADER, with the 16 * fields enclosed by brackets "[]" replaced with your own identifying 17 * information: Portions Copyright [yyyy] [name of copyright owner] 18 * 19 * CDDL HEADER END 20 */ 21/* |
22 * Copyright 2007 Sun Microsystems, Inc. All rights reserved. | 22 * Copyright 2008 Sun Microsystems, Inc. All rights reserved. |
23 * Use is subject to license terms. 24 */ 25 | 23 * Use is subject to license terms. 24 */ 25 |
26#pragma ident "%Z%%M% %I% %E% SMI" 27 | |
28#include <stdio.h> 29#include <stdio_ext.h> 30#include <stdlib.h> 31#include <ctype.h> 32#include <sys/zfs_context.h> 33#include <sys/spa.h> 34#include <sys/spa_impl.h> 35#include <sys/dmu.h> --- 10 unchanged lines hidden (view full) --- 46#include <sys/dbuf.h> 47#include <sys/zil.h> 48#include <sys/zil_impl.h> 49#include <sys/stat.h> 50#include <sys/resource.h> 51#include <sys/dmu_traverse.h> 52#include <sys/zio_checksum.h> 53#include <sys/zio_compress.h> | 26#include <stdio.h> 27#include <stdio_ext.h> 28#include <stdlib.h> 29#include <ctype.h> 30#include <sys/zfs_context.h> 31#include <sys/spa.h> 32#include <sys/spa_impl.h> 33#include <sys/dmu.h> --- 10 unchanged lines hidden (view full) --- 44#include <sys/dbuf.h> 45#include <sys/zil.h> 46#include <sys/zil_impl.h> 47#include <sys/stat.h> 48#include <sys/resource.h> 49#include <sys/dmu_traverse.h> 50#include <sys/zio_checksum.h> 51#include <sys/zio_compress.h> |
52#include <sys/zfs_fuid.h> 53#undef ZFS_MAXNAMELEN 54#undef verify 55#include <libzfs.h> |
|
54 55const char cmdname[] = "zdb"; 56uint8_t dump_opt[256]; 57 58typedef void object_viewer_t(objset_t *, uint64_t, void *data, size_t size); 59 60extern void dump_intent_log(zilog_t *); 61uint64_t *zopt_object = NULL; 62int zopt_objects = 0; 63int zdb_advance = ADVANCE_PRE; 64zbookmark_t zdb_noread = { 0, 0, ZB_NO_LEVEL, 0 }; | 56 57const char cmdname[] = "zdb"; 58uint8_t dump_opt[256]; 59 60typedef void object_viewer_t(objset_t *, uint64_t, void *data, size_t size); 61 62extern void dump_intent_log(zilog_t *); 63uint64_t *zopt_object = NULL; 64int zopt_objects = 0; 65int zdb_advance = ADVANCE_PRE; 66zbookmark_t zdb_noread = { 0, 0, ZB_NO_LEVEL, 0 }; |
67libzfs_handle_t *g_zfs; 68boolean_t zdb_sig_user_data = B_TRUE; 69int zdb_sig_cksumalg = ZIO_CHECKSUM_SHA256; |
|
65 66/* 67 * These libumem hooks provide a reasonable set of defaults for the allocator's 68 * debugging facilities. 69 */ 70const char * 71_umem_debug_init() 72{ --- 5 unchanged lines hidden (view full) --- 78{ 79 return ("fail,contents"); /* $UMEM_LOGGING setting */ 80} 81 82static void 83usage(void) 84{ 85 (void) fprintf(stderr, | 70 71/* 72 * These libumem hooks provide a reasonable set of defaults for the allocator's 73 * debugging facilities. 74 */ 75const char * 76_umem_debug_init() 77{ --- 5 unchanged lines hidden (view full) --- 83{ 84 return ("fail,contents"); /* $UMEM_LOGGING setting */ 85} 86 87static void 88usage(void) 89{ 90 (void) fprintf(stderr, |
86 "Usage: %s [-udibcsvLU] [-O order] [-B os:obj:level:blkid] " | 91 "Usage: %s [-udibcsvL] [-U cachefile_path] [-O order] " 92 "[-B os:obj:level:blkid] [-S user:cksumalg] " |
87 "dataset [object...]\n" 88 " %s -C [pool]\n" 89 " %s -l dev\n" | 93 "dataset [object...]\n" 94 " %s -C [pool]\n" 95 " %s -l dev\n" |
90 " %s -R vdev:offset:size:flags\n", 91 cmdname, cmdname, cmdname, cmdname); | 96 " %s -R pool:vdev:offset:size:flags\n" 97 " %s [-p path_to_vdev_dir]\n" 98 " %s -e pool | GUID | devid ...\n", 99 cmdname, cmdname, cmdname, cmdname, cmdname, cmdname); |
92 93 (void) fprintf(stderr, " -u uberblock\n"); 94 (void) fprintf(stderr, " -d datasets\n"); 95 (void) fprintf(stderr, " -C cached pool configuration\n"); 96 (void) fprintf(stderr, " -i intent logs\n"); 97 (void) fprintf(stderr, " -b block statistics\n"); 98 (void) fprintf(stderr, " -c checksum all data blocks\n"); 99 (void) fprintf(stderr, " -s report stats on zdb's I/O\n"); | 100 101 (void) fprintf(stderr, " -u uberblock\n"); 102 (void) fprintf(stderr, " -d datasets\n"); 103 (void) fprintf(stderr, " -C cached pool configuration\n"); 104 (void) fprintf(stderr, " -i intent logs\n"); 105 (void) fprintf(stderr, " -b block statistics\n"); 106 (void) fprintf(stderr, " -c checksum all data blocks\n"); 107 (void) fprintf(stderr, " -s report stats on zdb's I/O\n"); |
108 (void) fprintf(stderr, " -S <user|all>:<cksum_alg|all> -- " 109 "dump blkptr signatures\n"); |
|
100 (void) fprintf(stderr, " -v verbose (applies to all others)\n"); 101 (void) fprintf(stderr, " -l dump label contents\n"); 102 (void) fprintf(stderr, " -L live pool (allows some errors)\n"); 103 (void) fprintf(stderr, " -O [!]<pre|post|prune|data|holes> " 104 "visitation order\n"); | 110 (void) fprintf(stderr, " -v verbose (applies to all others)\n"); 111 (void) fprintf(stderr, " -l dump label contents\n"); 112 (void) fprintf(stderr, " -L live pool (allows some errors)\n"); 113 (void) fprintf(stderr, " -O [!]<pre|post|prune|data|holes> " 114 "visitation order\n"); |
105 (void) fprintf(stderr, " -U use zpool.cache in /tmp\n"); | 115 (void) fprintf(stderr, " -U cachefile_path -- use alternate " 116 "cachefile\n"); |
106 (void) fprintf(stderr, " -B objset:object:level:blkid -- " 107 "simulate bad block\n"); | 117 (void) fprintf(stderr, " -B objset:object:level:blkid -- " 118 "simulate bad block\n"); |
108 (void) fprintf(stderr, " -R read and display block from a" | 119 (void) fprintf(stderr, " -R read and display block from a " |
109 "device\n"); | 120 "device\n"); |
121 (void) fprintf(stderr, " -e Pool is exported/destroyed/" 122 "has altroot\n"); 123 (void) fprintf(stderr, " -p <Path to vdev dir> (use with -e)\n"); |
|
110 (void) fprintf(stderr, "Specify an option more than once (e.g. -bb) " 111 "to make only that option verbose\n"); 112 (void) fprintf(stderr, "Default is to dump everything non-verbosely\n"); 113 exit(1); 114} 115 116static void 117fatal(const char *fmt, ...) --- 244 unchanged lines hidden (view full) --- 362 } 363 } 364 (void) printf("\n"); 365 umem_free(prop, attr.za_num_integers * attr.za_integer_length); 366 } 367 zap_cursor_fini(&zc); 368} 369 | 124 (void) fprintf(stderr, "Specify an option more than once (e.g. -bb) " 125 "to make only that option verbose\n"); 126 (void) fprintf(stderr, "Default is to dump everything non-verbosely\n"); 127 exit(1); 128} 129 130static void 131fatal(const char *fmt, ...) --- 244 unchanged lines hidden (view full) --- 376 } 377 } 378 (void) printf("\n"); 379 umem_free(prop, attr.za_num_integers * attr.za_integer_length); 380 } 381 zap_cursor_fini(&zc); 382} 383 |
384/*ARGSUSED*/ |
|
370static void | 385static void |
386dump_zpldir(objset_t *os, uint64_t object, void *data, size_t size) 387{ 388 zap_cursor_t zc; 389 zap_attribute_t attr; 390 const char *typenames[] = { 391 /* 0 */ "not specified", 392 /* 1 */ "FIFO", 393 /* 2 */ "Character Device", 394 /* 3 */ "3 (invalid)", 395 /* 4 */ "Directory", 396 /* 5 */ "5 (invalid)", 397 /* 6 */ "Block Device", 398 /* 7 */ "7 (invalid)", 399 /* 8 */ "Regular File", 400 /* 9 */ "9 (invalid)", 401 /* 10 */ "Symbolic Link", 402 /* 11 */ "11 (invalid)", 403 /* 12 */ "Socket", 404 /* 13 */ "Door", 405 /* 14 */ "Event Port", 406 /* 15 */ "15 (invalid)", 407 }; 408 409 dump_zap_stats(os, object); 410 (void) printf("\n"); 411 412 for (zap_cursor_init(&zc, os, object); 413 zap_cursor_retrieve(&zc, &attr) == 0; 414 zap_cursor_advance(&zc)) { 415 (void) printf("\t\t%s = %lld (type: %s)\n", 416 attr.za_name, ZFS_DIRENT_OBJ(attr.za_first_integer), 417 typenames[ZFS_DIRENT_TYPE(attr.za_first_integer)]); 418 } 419 zap_cursor_fini(&zc); 420} 421 422static void |
|
371dump_spacemap(objset_t *os, space_map_obj_t *smo, space_map_t *sm) 372{ 373 uint64_t alloc, offset, entry; 374 uint8_t mapshift = sm->sm_shift; 375 uint64_t mapstart = sm->sm_start; 376 char *ddata[] = { "ALLOC", "FREE", "CONDENSE", "INVALID", 377 "INVALID", "INVALID", "INVALID", "INVALID" }; 378 --- 72 unchanged lines hidden (view full) --- 451 vdev_t *vd; 452 int c, m; 453 454 (void) printf("\nMetaslabs:\n"); 455 456 for (c = 0; c < rvd->vdev_children; c++) { 457 vd = rvd->vdev_child[c]; 458 | 423dump_spacemap(objset_t *os, space_map_obj_t *smo, space_map_t *sm) 424{ 425 uint64_t alloc, offset, entry; 426 uint8_t mapshift = sm->sm_shift; 427 uint64_t mapstart = sm->sm_start; 428 char *ddata[] = { "ALLOC", "FREE", "CONDENSE", "INVALID", 429 "INVALID", "INVALID", "INVALID", "INVALID" }; 430 --- 72 unchanged lines hidden (view full) --- 503 vdev_t *vd; 504 int c, m; 505 506 (void) printf("\nMetaslabs:\n"); 507 508 for (c = 0; c < rvd->vdev_children; c++) { 509 vd = rvd->vdev_child[c]; 510 |
459 spa_config_enter(spa, RW_READER, FTAG); 460 (void) printf("\n vdev %llu = %s\n\n", 461 (u_longlong_t)vd->vdev_id, vdev_description(vd)); 462 spa_config_exit(spa, FTAG); | 511 (void) printf("\n vdev %llu\n\n", (u_longlong_t)vd->vdev_id); |
463 464 if (dump_opt['d'] <= 5) { 465 (void) printf("\t%10s %10s %5s\n", 466 "offset", "spacemap", "free"); 467 (void) printf("\t%10s %10s %5s\n", 468 "------", "--------", "----"); 469 } 470 for (m = 0; m < vd->vdev_ms_count; m++) 471 dump_metaslab(vd->vdev_ms[m]); 472 (void) printf("\n"); 473 } 474} 475 476static void 477dump_dtl(vdev_t *vd, int indent) 478{ 479 avl_tree_t *t = &vd->vdev_dtl_map.sm_root; | 512 513 if (dump_opt['d'] <= 5) { 514 (void) printf("\t%10s %10s %5s\n", 515 "offset", "spacemap", "free"); 516 (void) printf("\t%10s %10s %5s\n", 517 "------", "--------", "----"); 518 } 519 for (m = 0; m < vd->vdev_ms_count; m++) 520 dump_metaslab(vd->vdev_ms[m]); 521 (void) printf("\n"); 522 } 523} 524 525static void 526dump_dtl(vdev_t *vd, int indent) 527{ 528 avl_tree_t *t = &vd->vdev_dtl_map.sm_root; |
480 spa_t *spa = vd->vdev_spa; | |
481 space_seg_t *ss; 482 vdev_t *pvd; 483 int c; 484 485 if (indent == 0) 486 (void) printf("\nDirty time logs:\n\n"); 487 | 529 space_seg_t *ss; 530 vdev_t *pvd; 531 int c; 532 533 if (indent == 0) 534 (void) printf("\nDirty time logs:\n\n"); 535 |
488 spa_config_enter(spa, RW_READER, FTAG); 489 (void) printf("\t%*s%s\n", indent, "", vdev_description(vd)); 490 spa_config_exit(spa, FTAG); | 536 (void) printf("\t%*s%s\n", indent, "", 537 vd->vdev_path ? vd->vdev_path : 538 vd->vdev_parent ? vd->vdev_ops->vdev_op_type : 539 spa_name(vd->vdev_spa)); |
491 492 for (ss = avl_first(t); ss; ss = AVL_NEXT(t, ss)) { 493 /* 494 * Everything in this DTL must appear in all parent DTL unions. 495 */ 496 for (pvd = vd; pvd; pvd = pvd->vdev_parent) 497 ASSERT(vdev_dtl_contains(&pvd->vdev_dtl_map, 498 ss->ss_start, ss->ss_end - ss->ss_start)); --- 166 unchanged lines hidden (view full) --- 665} 666 667/*ARGSUSED*/ 668static void 669dump_dsl_dir(objset_t *os, uint64_t object, void *data, size_t size) 670{ 671 dsl_dir_phys_t *dd = data; 672 time_t crtime; | 540 541 for (ss = avl_first(t); ss; ss = AVL_NEXT(t, ss)) { 542 /* 543 * Everything in this DTL must appear in all parent DTL unions. 544 */ 545 for (pvd = vd; pvd; pvd = pvd->vdev_parent) 546 ASSERT(vdev_dtl_contains(&pvd->vdev_dtl_map, 547 ss->ss_start, ss->ss_end - ss->ss_start)); --- 166 unchanged lines hidden (view full) --- 714} 715 716/*ARGSUSED*/ 717static void 718dump_dsl_dir(objset_t *os, uint64_t object, void *data, size_t size) 719{ 720 dsl_dir_phys_t *dd = data; 721 time_t crtime; |
673 char used[6], compressed[6], uncompressed[6], quota[6], resv[6]; | 722 char nice[6]; |
674 675 if (dd == NULL) 676 return; 677 | 723 724 if (dd == NULL) 725 return; 726 |
678 ASSERT(size == sizeof (*dd)); | 727 ASSERT3U(size, >=, sizeof (dsl_dir_phys_t)); |
679 680 crtime = dd->dd_creation_time; | 728 729 crtime = dd->dd_creation_time; |
681 nicenum(dd->dd_used_bytes, used); 682 nicenum(dd->dd_compressed_bytes, compressed); 683 nicenum(dd->dd_uncompressed_bytes, uncompressed); 684 nicenum(dd->dd_quota, quota); 685 nicenum(dd->dd_reserved, resv); 686 | |
687 (void) printf("\t\tcreation_time = %s", ctime(&crtime)); 688 (void) printf("\t\thead_dataset_obj = %llu\n", 689 (u_longlong_t)dd->dd_head_dataset_obj); 690 (void) printf("\t\tparent_dir_obj = %llu\n", 691 (u_longlong_t)dd->dd_parent_obj); | 730 (void) printf("\t\tcreation_time = %s", ctime(&crtime)); 731 (void) printf("\t\thead_dataset_obj = %llu\n", 732 (u_longlong_t)dd->dd_head_dataset_obj); 733 (void) printf("\t\tparent_dir_obj = %llu\n", 734 (u_longlong_t)dd->dd_parent_obj); |
692 (void) printf("\t\tclone_parent_obj = %llu\n", 693 (u_longlong_t)dd->dd_clone_parent_obj); | 735 (void) printf("\t\torigin_obj = %llu\n", 736 (u_longlong_t)dd->dd_origin_obj); |
694 (void) printf("\t\tchild_dir_zapobj = %llu\n", 695 (u_longlong_t)dd->dd_child_dir_zapobj); | 737 (void) printf("\t\tchild_dir_zapobj = %llu\n", 738 (u_longlong_t)dd->dd_child_dir_zapobj); |
696 (void) printf("\t\tused_bytes = %s\n", used); 697 (void) printf("\t\tcompressed_bytes = %s\n", compressed); 698 (void) printf("\t\tuncompressed_bytes = %s\n", uncompressed); 699 (void) printf("\t\tquota = %s\n", quota); 700 (void) printf("\t\treserved = %s\n", resv); | 739 nicenum(dd->dd_used_bytes, nice); 740 (void) printf("\t\tused_bytes = %s\n", nice); 741 nicenum(dd->dd_compressed_bytes, nice); 742 (void) printf("\t\tcompressed_bytes = %s\n", nice); 743 nicenum(dd->dd_uncompressed_bytes, nice); 744 (void) printf("\t\tuncompressed_bytes = %s\n", nice); 745 nicenum(dd->dd_quota, nice); 746 (void) printf("\t\tquota = %s\n", nice); 747 nicenum(dd->dd_reserved, nice); 748 (void) printf("\t\treserved = %s\n", nice); |
701 (void) printf("\t\tprops_zapobj = %llu\n", 702 (u_longlong_t)dd->dd_props_zapobj); | 749 (void) printf("\t\tprops_zapobj = %llu\n", 750 (u_longlong_t)dd->dd_props_zapobj); |
751 (void) printf("\t\tdeleg_zapobj = %llu\n", 752 (u_longlong_t)dd->dd_deleg_zapobj); 753 (void) printf("\t\tflags = %llx\n", 754 (u_longlong_t)dd->dd_flags); 755 756#define DO(which) \ 757 nicenum(dd->dd_used_breakdown[DD_USED_ ## which], nice); \ 758 (void) printf("\t\tused_breakdown[" #which "] = %s\n", nice) 759 DO(HEAD); 760 DO(SNAP); 761 DO(CHILD); 762 DO(CHILD_RSRV); 763 DO(REFRSRV); 764#undef DO |
|
703} 704 705/*ARGSUSED*/ 706static void 707dump_dsl_dataset(objset_t *os, uint64_t object, void *data, size_t size) 708{ 709 dsl_dataset_phys_t *ds = data; 710 time_t crtime; --- 6 unchanged lines hidden (view full) --- 717 ASSERT(size == sizeof (*ds)); 718 crtime = ds->ds_creation_time; 719 nicenum(ds->ds_used_bytes, used); 720 nicenum(ds->ds_compressed_bytes, compressed); 721 nicenum(ds->ds_uncompressed_bytes, uncompressed); 722 nicenum(ds->ds_unique_bytes, unique); 723 sprintf_blkptr(blkbuf, BP_SPRINTF_LEN, &ds->ds_bp); 724 | 765} 766 767/*ARGSUSED*/ 768static void 769dump_dsl_dataset(objset_t *os, uint64_t object, void *data, size_t size) 770{ 771 dsl_dataset_phys_t *ds = data; 772 time_t crtime; --- 6 unchanged lines hidden (view full) --- 779 ASSERT(size == sizeof (*ds)); 780 crtime = ds->ds_creation_time; 781 nicenum(ds->ds_used_bytes, used); 782 nicenum(ds->ds_compressed_bytes, compressed); 783 nicenum(ds->ds_uncompressed_bytes, uncompressed); 784 nicenum(ds->ds_unique_bytes, unique); 785 sprintf_blkptr(blkbuf, BP_SPRINTF_LEN, &ds->ds_bp); 786 |
725 (void) printf("\t\tdataset_obj = %llu\n", | 787 (void) printf("\t\tdir_obj = %llu\n", |
726 (u_longlong_t)ds->ds_dir_obj); 727 (void) printf("\t\tprev_snap_obj = %llu\n", 728 (u_longlong_t)ds->ds_prev_snap_obj); 729 (void) printf("\t\tprev_snap_txg = %llu\n", 730 (u_longlong_t)ds->ds_prev_snap_txg); 731 (void) printf("\t\tnext_snap_obj = %llu\n", 732 (u_longlong_t)ds->ds_next_snap_obj); 733 (void) printf("\t\tsnapnames_zapobj = %llu\n", --- 10 unchanged lines hidden (view full) --- 744 (void) printf("\t\tuncompressed_bytes = %s\n", uncompressed); 745 (void) printf("\t\tunique = %s\n", unique); 746 (void) printf("\t\tfsid_guid = %llu\n", 747 (u_longlong_t)ds->ds_fsid_guid); 748 (void) printf("\t\tguid = %llu\n", 749 (u_longlong_t)ds->ds_guid); 750 (void) printf("\t\tflags = %llx\n", 751 (u_longlong_t)ds->ds_flags); | 788 (u_longlong_t)ds->ds_dir_obj); 789 (void) printf("\t\tprev_snap_obj = %llu\n", 790 (u_longlong_t)ds->ds_prev_snap_obj); 791 (void) printf("\t\tprev_snap_txg = %llu\n", 792 (u_longlong_t)ds->ds_prev_snap_txg); 793 (void) printf("\t\tnext_snap_obj = %llu\n", 794 (u_longlong_t)ds->ds_next_snap_obj); 795 (void) printf("\t\tsnapnames_zapobj = %llu\n", --- 10 unchanged lines hidden (view full) --- 806 (void) printf("\t\tuncompressed_bytes = %s\n", uncompressed); 807 (void) printf("\t\tunique = %s\n", unique); 808 (void) printf("\t\tfsid_guid = %llu\n", 809 (u_longlong_t)ds->ds_fsid_guid); 810 (void) printf("\t\tguid = %llu\n", 811 (u_longlong_t)ds->ds_guid); 812 (void) printf("\t\tflags = %llx\n", 813 (u_longlong_t)ds->ds_flags); |
814 (void) printf("\t\tnext_clones_obj = %llu\n", 815 (u_longlong_t)ds->ds_next_clones_obj); 816 (void) printf("\t\tprops_obj = %llu\n", 817 (u_longlong_t)ds->ds_props_obj); |
|
752 (void) printf("\t\tbp = %s\n", blkbuf); 753} 754 755static void 756dump_bplist(objset_t *mos, uint64_t object, char *name) 757{ 758 bplist_t bpl = { 0 }; 759 blkptr_t blk, *bp = &blk; 760 uint64_t itor = 0; 761 char bytes[6]; 762 char comp[6]; 763 char uncomp[6]; 764 765 if (dump_opt['d'] < 3) 766 return; 767 | 818 (void) printf("\t\tbp = %s\n", blkbuf); 819} 820 821static void 822dump_bplist(objset_t *mos, uint64_t object, char *name) 823{ 824 bplist_t bpl = { 0 }; 825 blkptr_t blk, *bp = &blk; 826 uint64_t itor = 0; 827 char bytes[6]; 828 char comp[6]; 829 char uncomp[6]; 830 831 if (dump_opt['d'] < 3) 832 return; 833 |
834 mutex_init(&bpl.bpl_lock, NULL, MUTEX_DEFAULT, NULL); |
|
768 VERIFY(0 == bplist_open(&bpl, mos, object)); 769 if (bplist_empty(&bpl)) { 770 bplist_close(&bpl); | 835 VERIFY(0 == bplist_open(&bpl, mos, object)); 836 if (bplist_empty(&bpl)) { 837 bplist_close(&bpl); |
838 mutex_destroy(&bpl.bpl_lock); |
|
771 return; 772 } 773 774 nicenum(bpl.bpl_phys->bpl_bytes, bytes); 775 if (bpl.bpl_dbuf->db_size == sizeof (bplist_phys_t)) { 776 nicenum(bpl.bpl_phys->bpl_comp, comp); 777 nicenum(bpl.bpl_phys->bpl_uncomp, uncomp); 778 (void) printf("\n %s: %llu entries, %s (%s/%s comp)\n", 779 name, (u_longlong_t)bpl.bpl_phys->bpl_entries, 780 bytes, comp, uncomp); 781 } else { 782 (void) printf("\n %s: %llu entries, %s\n", 783 name, (u_longlong_t)bpl.bpl_phys->bpl_entries, bytes); 784 } 785 786 if (dump_opt['d'] < 5) { 787 bplist_close(&bpl); | 839 return; 840 } 841 842 nicenum(bpl.bpl_phys->bpl_bytes, bytes); 843 if (bpl.bpl_dbuf->db_size == sizeof (bplist_phys_t)) { 844 nicenum(bpl.bpl_phys->bpl_comp, comp); 845 nicenum(bpl.bpl_phys->bpl_uncomp, uncomp); 846 (void) printf("\n %s: %llu entries, %s (%s/%s comp)\n", 847 name, (u_longlong_t)bpl.bpl_phys->bpl_entries, 848 bytes, comp, uncomp); 849 } else { 850 (void) printf("\n %s: %llu entries, %s\n", 851 name, (u_longlong_t)bpl.bpl_phys->bpl_entries, bytes); 852 } 853 854 if (dump_opt['d'] < 5) { 855 bplist_close(&bpl); |
856 mutex_destroy(&bpl.bpl_lock); |
|
788 return; 789 } 790 791 (void) printf("\n"); 792 793 while (bplist_iterate(&bpl, &itor, bp) == 0) { 794 char blkbuf[BP_SPRINTF_LEN]; 795 796 ASSERT(bp->blk_birth != 0); 797 sprintf_blkptr_compact(blkbuf, bp, dump_opt['d'] > 5 ? 1 : 0); 798 (void) printf("\tItem %3llu: %s\n", 799 (u_longlong_t)itor - 1, blkbuf); 800 } 801 802 bplist_close(&bpl); | 857 return; 858 } 859 860 (void) printf("\n"); 861 862 while (bplist_iterate(&bpl, &itor, bp) == 0) { 863 char blkbuf[BP_SPRINTF_LEN]; 864 865 ASSERT(bp->blk_birth != 0); 866 sprintf_blkptr_compact(blkbuf, bp, dump_opt['d'] > 5 ? 1 : 0); 867 (void) printf("\tItem %3llu: %s\n", 868 (u_longlong_t)itor - 1, blkbuf); 869 } 870 871 bplist_close(&bpl); |
872 mutex_destroy(&bpl.bpl_lock); |
|
803} 804 | 873} 874 |
875static avl_tree_t idx_tree; 876static avl_tree_t domain_tree; 877static boolean_t fuid_table_loaded; 878 879static void 880fuid_table_destroy() 881{ 882 if (fuid_table_loaded) { 883 zfs_fuid_table_destroy(&idx_tree, &domain_tree); 884 fuid_table_loaded = B_FALSE; 885 } 886} 887 888/* 889 * print uid or gid information. 890 * For normal POSIX id just the id is printed in decimal format. 891 * For CIFS files with FUID the fuid is printed in hex followed by 892 * the doman-rid string. 893 */ 894static void 895print_idstr(uint64_t id, const char *id_type) 896{ 897 if (FUID_INDEX(id)) { 898 char *domain; 899 900 domain = zfs_fuid_idx_domain(&idx_tree, FUID_INDEX(id)); 901 (void) printf("\t%s %llx [%s-%d]\n", id_type, 902 (u_longlong_t)id, domain, (int)FUID_RID(id)); 903 } else { 904 (void) printf("\t%s %llu\n", id_type, (u_longlong_t)id); 905 } 906 907} 908 909static void 910dump_uidgid(objset_t *os, znode_phys_t *zp) 911{ 912 uint32_t uid_idx, gid_idx; 913 914 uid_idx = FUID_INDEX(zp->zp_uid); 915 gid_idx = FUID_INDEX(zp->zp_gid); 916 917 /* Load domain table, if not already loaded */ 918 if (!fuid_table_loaded && (uid_idx || gid_idx)) { 919 uint64_t fuid_obj; 920 921 /* first find the fuid object. It lives in the master node */ 922 VERIFY(zap_lookup(os, MASTER_NODE_OBJ, ZFS_FUID_TABLES, 923 8, 1, &fuid_obj) == 0); 924 (void) zfs_fuid_table_load(os, fuid_obj, 925 &idx_tree, &domain_tree); 926 fuid_table_loaded = B_TRUE; 927 } 928 929 print_idstr(zp->zp_uid, "uid"); 930 print_idstr(zp->zp_gid, "gid"); 931} 932 |
|
805/*ARGSUSED*/ 806static void 807dump_znode(objset_t *os, uint64_t object, void *data, size_t size) 808{ 809 znode_phys_t *zp = data; 810 time_t z_crtime, z_atime, z_mtime, z_ctime; 811 char path[MAXPATHLEN * 2]; /* allow for xattr and failure prefix */ 812 int error; --- 12 unchanged lines hidden (view full) --- 825 } 826 827 z_crtime = (time_t)zp->zp_crtime[0]; 828 z_atime = (time_t)zp->zp_atime[0]; 829 z_mtime = (time_t)zp->zp_mtime[0]; 830 z_ctime = (time_t)zp->zp_ctime[0]; 831 832 (void) printf("\tpath %s\n", path); | 933/*ARGSUSED*/ 934static void 935dump_znode(objset_t *os, uint64_t object, void *data, size_t size) 936{ 937 znode_phys_t *zp = data; 938 time_t z_crtime, z_atime, z_mtime, z_ctime; 939 char path[MAXPATHLEN * 2]; /* allow for xattr and failure prefix */ 940 int error; --- 12 unchanged lines hidden (view full) --- 953 } 954 955 z_crtime = (time_t)zp->zp_crtime[0]; 956 z_atime = (time_t)zp->zp_atime[0]; 957 z_mtime = (time_t)zp->zp_mtime[0]; 958 z_ctime = (time_t)zp->zp_ctime[0]; 959 960 (void) printf("\tpath %s\n", path); |
961 dump_uidgid(os, zp); |
|
833 (void) printf("\tatime %s", ctime(&z_atime)); 834 (void) printf("\tmtime %s", ctime(&z_mtime)); 835 (void) printf("\tctime %s", ctime(&z_ctime)); 836 (void) printf("\tcrtime %s", ctime(&z_crtime)); 837 (void) printf("\tgen %llu\n", (u_longlong_t)zp->zp_gen); 838 (void) printf("\tmode %llo\n", (u_longlong_t)zp->zp_mode); 839 (void) printf("\tsize %llu\n", (u_longlong_t)zp->zp_size); 840 (void) printf("\tparent %llu\n", (u_longlong_t)zp->zp_parent); --- 28 unchanged lines hidden (view full) --- 869 dump_dnode, /* DMU dnode */ 870 dump_dmu_objset, /* DMU objset */ 871 dump_dsl_dir, /* DSL directory */ 872 dump_zap, /* DSL directory child map */ 873 dump_zap, /* DSL dataset snap map */ 874 dump_zap, /* DSL props */ 875 dump_dsl_dataset, /* DSL dataset */ 876 dump_znode, /* ZFS znode */ | 962 (void) printf("\tatime %s", ctime(&z_atime)); 963 (void) printf("\tmtime %s", ctime(&z_mtime)); 964 (void) printf("\tctime %s", ctime(&z_ctime)); 965 (void) printf("\tcrtime %s", ctime(&z_crtime)); 966 (void) printf("\tgen %llu\n", (u_longlong_t)zp->zp_gen); 967 (void) printf("\tmode %llo\n", (u_longlong_t)zp->zp_mode); 968 (void) printf("\tsize %llu\n", (u_longlong_t)zp->zp_size); 969 (void) printf("\tparent %llu\n", (u_longlong_t)zp->zp_parent); --- 28 unchanged lines hidden (view full) --- 998 dump_dnode, /* DMU dnode */ 999 dump_dmu_objset, /* DMU objset */ 1000 dump_dsl_dir, /* DSL directory */ 1001 dump_zap, /* DSL directory child map */ 1002 dump_zap, /* DSL dataset snap map */ 1003 dump_zap, /* DSL props */ 1004 dump_dsl_dataset, /* DSL dataset */ 1005 dump_znode, /* ZFS znode */ |
877 dump_acl, /* ZFS ACL */ | 1006 dump_acl, /* ZFS V0 ACL */ |
878 dump_uint8, /* ZFS plain file */ | 1007 dump_uint8, /* ZFS plain file */ |
879 dump_zap, /* ZFS directory */ | 1008 dump_zpldir, /* ZFS directory */ |
880 dump_zap, /* ZFS master node */ 881 dump_zap, /* ZFS delete queue */ 882 dump_uint8, /* zvol object */ 883 dump_zap, /* zvol prop */ 884 dump_uint8, /* other uint8[] */ 885 dump_uint64, /* other uint64[] */ 886 dump_zap, /* other ZAP */ 887 dump_zap, /* persistent error log */ 888 dump_uint8, /* SPA history */ 889 dump_uint64, /* SPA history offsets */ 890 dump_zap, /* Pool properties */ | 1009 dump_zap, /* ZFS master node */ 1010 dump_zap, /* ZFS delete queue */ 1011 dump_uint8, /* zvol object */ 1012 dump_zap, /* zvol prop */ 1013 dump_uint8, /* other uint8[] */ 1014 dump_uint64, /* other uint64[] */ 1015 dump_zap, /* other ZAP */ 1016 dump_zap, /* persistent error log */ 1017 dump_uint8, /* SPA history */ 1018 dump_uint64, /* SPA history offsets */ 1019 dump_zap, /* Pool properties */ |
1020 dump_zap, /* DSL permissions */ 1021 dump_acl, /* ZFS ACL */ 1022 dump_uint8, /* ZFS SYSACL */ 1023 dump_none, /* FUID nvlist */ 1024 dump_packed_nvlist, /* FUID nvlist size */ 1025 dump_zap, /* DSL dataset next clones */ 1026 dump_zap, /* DSL scrub queue */ |
|
891}; 892 893static void 894dump_object(objset_t *os, uint64_t object, int verbosity, int *print_header) 895{ 896 dmu_buf_t *db = NULL; 897 dmu_object_info_t doi; 898 dnode_t *dn; --- 26 unchanged lines hidden (view full) --- 925 nicenum(doi.doi_data_block_size, dblk); 926 nicenum(doi.doi_data_block_size * (doi.doi_max_block_offset + 1), 927 lsize); 928 nicenum(doi.doi_physical_blks << 9, asize); 929 nicenum(doi.doi_bonus_size, bonus_size); 930 931 aux[0] = '\0'; 932 | 1027}; 1028 1029static void 1030dump_object(objset_t *os, uint64_t object, int verbosity, int *print_header) 1031{ 1032 dmu_buf_t *db = NULL; 1033 dmu_object_info_t doi; 1034 dnode_t *dn; --- 26 unchanged lines hidden (view full) --- 1061 nicenum(doi.doi_data_block_size, dblk); 1062 nicenum(doi.doi_data_block_size * (doi.doi_max_block_offset + 1), 1063 lsize); 1064 nicenum(doi.doi_physical_blks << 9, asize); 1065 nicenum(doi.doi_bonus_size, bonus_size); 1066 1067 aux[0] = '\0'; 1068 |
933 if (doi.doi_checksum != ZIO_CHECKSUM_INHERIT || verbosity >= 6) | 1069 if (doi.doi_checksum != ZIO_CHECKSUM_INHERIT || verbosity >= 6) { |
934 (void) snprintf(aux + strlen(aux), sizeof (aux), " (K=%s)", | 1070 (void) snprintf(aux + strlen(aux), sizeof (aux), " (K=%s)", |
935 zio_checksum_table[doi.doi_checksum].ci_name); | 1071 zio_checksum_table[doi.doi_checksum].ci_name); 1072 } |
936 | 1073 |
937 if (doi.doi_compress != ZIO_COMPRESS_INHERIT || verbosity >= 6) | 1074 if (doi.doi_compress != ZIO_COMPRESS_INHERIT || verbosity >= 6) { |
938 (void) snprintf(aux + strlen(aux), sizeof (aux), " (Z=%s)", | 1075 (void) snprintf(aux + strlen(aux), sizeof (aux), " (Z=%s)", |
939 zio_compress_table[doi.doi_compress].ci_name); | 1076 zio_compress_table[doi.doi_compress].ci_name); 1077 } |
940 941 (void) printf("%10lld %3u %5s %5s %5s %5s %s%s\n", 942 (u_longlong_t)object, doi.doi_indirection, iblk, dblk, lsize, 943 asize, dmu_ot[doi.doi_type].ot_name, aux); 944 945 if (doi.doi_bonus_type != DMU_OT_NONE && verbosity > 3) { 946 (void) printf("%10s %3s %5s %5s %5s %5s %s\n", 947 "", "", "", "", bonus_size, "bonus", --- 19 unchanged lines hidden (view full) --- 967 int minlvl = 1; 968 969 if (dn->dn_type == DMU_OT_DNODE) { 970 minlvl = 0; 971 blkfill = DNODES_PER_BLOCK; 972 } 973 974 for (;;) { | 1078 1079 (void) printf("%10lld %3u %5s %5s %5s %5s %s%s\n", 1080 (u_longlong_t)object, doi.doi_indirection, iblk, dblk, lsize, 1081 asize, dmu_ot[doi.doi_type].ot_name, aux); 1082 1083 if (doi.doi_bonus_type != DMU_OT_NONE && verbosity > 3) { 1084 (void) printf("%10s %3s %5s %5s %5s %5s %s\n", 1085 "", "", "", "", bonus_size, "bonus", --- 19 unchanged lines hidden (view full) --- 1105 int minlvl = 1; 1106 1107 if (dn->dn_type == DMU_OT_DNODE) { 1108 minlvl = 0; 1109 blkfill = DNODES_PER_BLOCK; 1110 } 1111 1112 for (;;) { |
975 error = dnode_next_offset(dn, B_FALSE, &start, minlvl, 976 blkfill, 0); | 1113 error = dnode_next_offset(dn, 1114 0, &start, minlvl, blkfill, 0); |
977 if (error) 978 break; 979 end = start; | 1115 if (error) 1116 break; 1117 end = start; |
980 error = dnode_next_offset(dn, B_TRUE, &end, minlvl, 981 blkfill, 0); | 1118 error = dnode_next_offset(dn, 1119 DNODE_FIND_HOLE, &end, minlvl, blkfill, 0); |
982 nicenum(end - start, segsize); 983 (void) printf("\t\tsegment [%016llx, %016llx)" 984 " size %5s\n", (u_longlong_t)start, 985 (u_longlong_t)end, segsize); 986 if (error) 987 break; 988 start = end; 989 } 990 } 991 992 if (db != NULL) 993 dmu_buf_rele(db, FTAG); 994} 995 996static char *objset_types[DMU_OST_NUMTYPES] = { 997 "NONE", "META", "ZPL", "ZVOL", "OTHER", "ANY" }; 998 | 1120 nicenum(end - start, segsize); 1121 (void) printf("\t\tsegment [%016llx, %016llx)" 1122 " size %5s\n", (u_longlong_t)start, 1123 (u_longlong_t)end, segsize); 1124 if (error) 1125 break; 1126 start = end; 1127 } 1128 } 1129 1130 if (db != NULL) 1131 dmu_buf_rele(db, FTAG); 1132} 1133 1134static char *objset_types[DMU_OST_NUMTYPES] = { 1135 "NONE", "META", "ZPL", "ZVOL", "OTHER", "ANY" }; 1136 |
999/*ARGSUSED*/ | |
1000static void 1001dump_dir(objset_t *os) 1002{ 1003 dmu_objset_stats_t dds; 1004 uint64_t object, object_count; 1005 uint64_t refdbytes, usedobjs, scratch; 1006 char numbuf[8]; 1007 char blkbuf[BP_SPRINTF_LEN]; --- 6 unchanged lines hidden (view full) --- 1014 dmu_objset_fast_stat(os, &dds); 1015 1016 if (dds.dds_type < DMU_OST_NUMTYPES) 1017 type = objset_types[dds.dds_type]; 1018 1019 if (dds.dds_type == DMU_OST_META) { 1020 dds.dds_creation_txg = TXG_INITIAL; 1021 usedobjs = os->os->os_rootbp->blk_fill; | 1137static void 1138dump_dir(objset_t *os) 1139{ 1140 dmu_objset_stats_t dds; 1141 uint64_t object, object_count; 1142 uint64_t refdbytes, usedobjs, scratch; 1143 char numbuf[8]; 1144 char blkbuf[BP_SPRINTF_LEN]; --- 6 unchanged lines hidden (view full) --- 1151 dmu_objset_fast_stat(os, &dds); 1152 1153 if (dds.dds_type < DMU_OST_NUMTYPES) 1154 type = objset_types[dds.dds_type]; 1155 1156 if (dds.dds_type == DMU_OST_META) { 1157 dds.dds_creation_txg = TXG_INITIAL; 1158 usedobjs = os->os->os_rootbp->blk_fill; |
1022 refdbytes = 1023 os->os->os_spa->spa_dsl_pool->dp_mos_dir->dd_used_bytes; | 1159 refdbytes = os->os->os_spa->spa_dsl_pool-> 1160 dp_mos_dir->dd_phys->dd_used_bytes; |
1024 } else { 1025 dmu_objset_space(os, &refdbytes, &scratch, &usedobjs, &scratch); 1026 } 1027 1028 ASSERT3U(usedobjs, ==, os->os->os_rootbp->blk_fill); 1029 1030 nicenum(refdbytes, numbuf); 1031 --- 17 unchanged lines hidden (view full) --- 1049 1050 if (dmu_objset_ds(os) != NULL) 1051 dump_bplist(dmu_objset_pool(os)->dp_meta_objset, 1052 dmu_objset_ds(os)->ds_phys->ds_deadlist_obj, "Deadlist"); 1053 1054 if (verbosity < 2) 1055 return; 1056 | 1161 } else { 1162 dmu_objset_space(os, &refdbytes, &scratch, &usedobjs, &scratch); 1163 } 1164 1165 ASSERT3U(usedobjs, ==, os->os->os_rootbp->blk_fill); 1166 1167 nicenum(refdbytes, numbuf); 1168 --- 17 unchanged lines hidden (view full) --- 1186 1187 if (dmu_objset_ds(os) != NULL) 1188 dump_bplist(dmu_objset_pool(os)->dp_meta_objset, 1189 dmu_objset_ds(os)->ds_phys->ds_deadlist_obj, "Deadlist"); 1190 1191 if (verbosity < 2) 1192 return; 1193 |
1194 if (os->os->os_rootbp->blk_birth == 0) 1195 return; 1196 |
|
1057 if (zopt_objects != 0) { 1058 for (i = 0; i < zopt_objects; i++) 1059 dump_object(os, zopt_object[i], verbosity, 1060 &print_header); 1061 (void) printf("\n"); 1062 return; 1063 } 1064 --- 45 unchanged lines hidden (view full) --- 1110 (void) printf("%s\n", spa_name(spa)); 1111 if (pool == NULL || strcmp(pool, spa_name(spa)) == 0) 1112 dump_nvlist(spa->spa_config, 4); 1113 } 1114 mutex_exit(&spa_namespace_lock); 1115} 1116 1117static void | 1197 if (zopt_objects != 0) { 1198 for (i = 0; i < zopt_objects; i++) 1199 dump_object(os, zopt_object[i], verbosity, 1200 &print_header); 1201 (void) printf("\n"); 1202 return; 1203 } 1204 --- 45 unchanged lines hidden (view full) --- 1250 (void) printf("%s\n", spa_name(spa)); 1251 if (pool == NULL || strcmp(pool, spa_name(spa)) == 0) 1252 dump_nvlist(spa->spa_config, 4); 1253 } 1254 mutex_exit(&spa_namespace_lock); 1255} 1256 1257static void |
1258dump_cachefile(const char *cachefile) 1259{ 1260 int fd; 1261 struct stat64 statbuf; 1262 char *buf; 1263 nvlist_t *config; 1264 1265 if ((fd = open64(cachefile, O_RDONLY)) < 0) { 1266 (void) printf("cannot open '%s': %s\n", cachefile, 1267 strerror(errno)); 1268 exit(1); 1269 } 1270 1271 if (fstat64(fd, &statbuf) != 0) { 1272 (void) printf("failed to stat '%s': %s\n", cachefile, 1273 strerror(errno)); 1274 exit(1); 1275 } 1276 1277 if ((buf = malloc(statbuf.st_size)) == NULL) { 1278 (void) fprintf(stderr, "failed to allocate %llu bytes\n", 1279 (u_longlong_t)statbuf.st_size); 1280 exit(1); 1281 } 1282 1283 if (read(fd, buf, statbuf.st_size) != statbuf.st_size) { 1284 (void) fprintf(stderr, "failed to read %llu bytes\n", 1285 (u_longlong_t)statbuf.st_size); 1286 exit(1); 1287 } 1288 1289 (void) close(fd); 1290 1291 if (nvlist_unpack(buf, statbuf.st_size, &config, 0) != 0) { 1292 (void) fprintf(stderr, "failed to unpack nvlist\n"); 1293 exit(1); 1294 } 1295 1296 free(buf); 1297 1298 dump_nvlist(config, 0); 1299 1300 nvlist_free(config); 1301} 1302 1303static void |
|
1118dump_label(const char *dev) 1119{ 1120 int fd; 1121 vdev_label_t label; 1122 char *buf = label.vl_vdev_phys.vp_nvlist; 1123 size_t buflen = sizeof (label.vl_vdev_phys.vp_nvlist); 1124 struct stat64 statbuf; 1125 uint64_t psize; --- 5 unchanged lines hidden (view full) --- 1131 } 1132 1133 if (fstat64(fd, &statbuf) != 0) { 1134 (void) printf("failed to stat '%s': %s\n", dev, 1135 strerror(errno)); 1136 exit(1); 1137 } 1138 | 1304dump_label(const char *dev) 1305{ 1306 int fd; 1307 vdev_label_t label; 1308 char *buf = label.vl_vdev_phys.vp_nvlist; 1309 size_t buflen = sizeof (label.vl_vdev_phys.vp_nvlist); 1310 struct stat64 statbuf; 1311 uint64_t psize; --- 5 unchanged lines hidden (view full) --- 1317 } 1318 1319 if (fstat64(fd, &statbuf) != 0) { 1320 (void) printf("failed to stat '%s': %s\n", dev, 1321 strerror(errno)); 1322 exit(1); 1323 } 1324 |
1139 if (S_ISCHR(statbuf.st_mode)) { 1140 if (ioctl(fd, DIOCGMEDIASIZE, &psize) != 0) { 1141 (void) printf("failed to get size '%s': %s\n", dev, 1142 strerror(errno)); 1143 exit(1); 1144 } 1145 } else 1146 psize = statbuf.st_size; 1147 | 1325 psize = statbuf.st_size; |
1148 psize = P2ALIGN(psize, (uint64_t)sizeof (vdev_label_t)); 1149 1150 for (l = 0; l < VDEV_LABELS; l++) { 1151 1152 nvlist_t *config = NULL; 1153 1154 (void) printf("--------------------------------------------\n"); 1155 (void) printf("LABEL %d\n", l); --- 17 unchanged lines hidden (view full) --- 1173/*ARGSUSED*/ 1174static int 1175dump_one_dir(char *dsname, void *arg) 1176{ 1177 int error; 1178 objset_t *os; 1179 1180 error = dmu_objset_open(dsname, DMU_OST_ANY, | 1326 psize = P2ALIGN(psize, (uint64_t)sizeof (vdev_label_t)); 1327 1328 for (l = 0; l < VDEV_LABELS; l++) { 1329 1330 nvlist_t *config = NULL; 1331 1332 (void) printf("--------------------------------------------\n"); 1333 (void) printf("LABEL %d\n", l); --- 17 unchanged lines hidden (view full) --- 1351/*ARGSUSED*/ 1352static int 1353dump_one_dir(char *dsname, void *arg) 1354{ 1355 int error; 1356 objset_t *os; 1357 1358 error = dmu_objset_open(dsname, DMU_OST_ANY, |
1181 DS_MODE_STANDARD | DS_MODE_READONLY, &os); | 1359 DS_MODE_USER | DS_MODE_READONLY, &os); |
1182 if (error) { 1183 (void) printf("Could not open %s\n", dsname); 1184 return (0); 1185 } 1186 dump_dir(os); 1187 dmu_objset_close(os); | 1360 if (error) { 1361 (void) printf("Could not open %s\n", dsname); 1362 return (0); 1363 } 1364 dump_dir(os); 1365 dmu_objset_close(os); |
1366 fuid_table_destroy(); |
|
1188 return (0); 1189} 1190 1191static void | 1367 return (0); 1368} 1369 1370static void |
1192zdb_space_map_load(spa_t *spa) | 1371zdb_leak(space_map_t *sm, uint64_t start, uint64_t size) |
1193{ | 1372{ |
1194 vdev_t *rvd = spa->spa_root_vdev; 1195 vdev_t *vd; 1196 int c, m, error; | 1373 vdev_t *vd = sm->sm_ppd; |
1197 | 1374 |
1198 for (c = 0; c < rvd->vdev_children; c++) { 1199 vd = rvd->vdev_child[c]; 1200 for (m = 0; m < vd->vdev_ms_count; m++) { 1201 metaslab_t *msp = vd->vdev_ms[m]; 1202 mutex_enter(&msp->ms_lock); 1203 error = space_map_load(&msp->ms_allocmap[0], NULL, 1204 SM_ALLOC, &msp->ms_smo, spa->spa_meta_objset); 1205 mutex_exit(&msp->ms_lock); 1206 if (error) 1207 fatal("%s bad space map #%d, error %d", 1208 spa->spa_name, c, error); 1209 } 1210 } | 1375 (void) printf("leaked space: vdev %llu, offset 0x%llx, size %llu\n", 1376 (u_longlong_t)vd->vdev_id, (u_longlong_t)start, (u_longlong_t)size); |
1211} 1212 | 1377} 1378 |
1213static int 1214zdb_space_map_claim(spa_t *spa, blkptr_t *bp, zbookmark_t *zb) | 1379/* ARGSUSED */ 1380static void 1381zdb_space_map_load(space_map_t *sm) |
1215{ | 1382{ |
1216 dva_t *dva = bp->blk_dva; 1217 vdev_t *vd; 1218 metaslab_t *msp; 1219 space_map_t *allocmap, *freemap; 1220 int error; 1221 int d; 1222 blkptr_t blk = *bp; 1223 1224 for (d = 0; d < BP_GET_NDVAS(bp); d++) { 1225 uint64_t vdev = DVA_GET_VDEV(&dva[d]); 1226 uint64_t offset = DVA_GET_OFFSET(&dva[d]); 1227 uint64_t size = DVA_GET_ASIZE(&dva[d]); 1228 1229 if ((vd = vdev_lookup_top(spa, vdev)) == NULL) 1230 return (ENXIO); 1231 1232 if ((offset >> vd->vdev_ms_shift) >= vd->vdev_ms_count) 1233 return (ENXIO); 1234 1235 msp = vd->vdev_ms[offset >> vd->vdev_ms_shift]; 1236 allocmap = &msp->ms_allocmap[0]; 1237 freemap = &msp->ms_freemap[0]; 1238 1239 /* Prepare our copy of the bp in case we need to read GBHs */ 1240 if (DVA_GET_GANG(&dva[d])) { 1241 size = vdev_psize_to_asize(vd, SPA_GANGBLOCKSIZE); 1242 DVA_SET_ASIZE(&blk.blk_dva[d], size); 1243 DVA_SET_GANG(&blk.blk_dva[d], 0); 1244 } 1245 1246 mutex_enter(&msp->ms_lock); 1247 if (space_map_contains(freemap, offset, size)) { 1248 mutex_exit(&msp->ms_lock); 1249 return (EAGAIN); /* allocated more than once */ 1250 } 1251 1252 if (!space_map_contains(allocmap, offset, size)) { 1253 mutex_exit(&msp->ms_lock); 1254 return (ESTALE); /* not allocated at all */ 1255 } 1256 1257 space_map_remove(allocmap, offset, size); 1258 space_map_add(freemap, offset, size); 1259 1260 mutex_exit(&msp->ms_lock); 1261 } 1262 1263 if (BP_IS_GANG(bp)) { 1264 zio_gbh_phys_t gbh; 1265 int g; 1266 1267 /* LINTED - compile time assert */ 1268 ASSERT(sizeof (zio_gbh_phys_t) == SPA_GANGBLOCKSIZE); 1269 1270 BP_SET_CHECKSUM(&blk, ZIO_CHECKSUM_GANG_HEADER); 1271 BP_SET_PSIZE(&blk, SPA_GANGBLOCKSIZE); 1272 BP_SET_LSIZE(&blk, SPA_GANGBLOCKSIZE); 1273 BP_SET_COMPRESS(&blk, ZIO_COMPRESS_OFF); 1274 error = zio_wait(zio_read(NULL, spa, &blk, &gbh, 1275 SPA_GANGBLOCKSIZE, NULL, NULL, ZIO_PRIORITY_SYNC_READ, 1276 ZIO_FLAG_CANFAIL | ZIO_FLAG_CONFIG_HELD, zb)); 1277 if (error) 1278 return (error); 1279 if (BP_SHOULD_BYTESWAP(&blk)) 1280 byteswap_uint64_array(&gbh, SPA_GANGBLOCKSIZE); 1281 for (g = 0; g < SPA_GBH_NBLKPTRS; g++) { 1282 if (BP_IS_HOLE(&gbh.zg_blkptr[g])) 1283 break; 1284 error = zdb_space_map_claim(spa, &gbh.zg_blkptr[g], zb); 1285 if (error) 1286 return (error); 1287 } 1288 } 1289 1290 return (0); | |
1291} 1292 1293static void | 1383} 1384 1385static void |
1294zdb_leak(space_map_t *sm, uint64_t start, uint64_t size) | 1386zdb_space_map_unload(space_map_t *sm) |
1295{ | 1387{ |
1296 metaslab_t *msp; | 1388 space_map_vacate(sm, zdb_leak, sm); 1389} |
1297 | 1390 |
1298 /* LINTED */ 1299 msp = (metaslab_t *)((char *)sm - offsetof(metaslab_t, ms_allocmap[0])); 1300 1301 (void) printf("leaked space: vdev %llu, offset 0x%llx, size %llu\n", 1302 (u_longlong_t)msp->ms_group->mg_vd->vdev_id, 1303 (u_longlong_t)start, 1304 (u_longlong_t)size); | 1391/* ARGSUSED */ 1392static void 1393zdb_space_map_claim(space_map_t *sm, uint64_t start, uint64_t size) 1394{ |
1305} 1306 | 1395} 1396 |
1397static space_map_ops_t zdb_space_map_ops = { 1398 zdb_space_map_load, 1399 zdb_space_map_unload, 1400 NULL, /* alloc */ 1401 zdb_space_map_claim, 1402 NULL /* free */ 1403}; 1404 |
|
1307static void | 1405static void |
1308zdb_space_map_unload(spa_t *spa) | 1406zdb_leak_init(spa_t *spa) |
1309{ 1310 vdev_t *rvd = spa->spa_root_vdev; | 1407{ 1408 vdev_t *rvd = spa->spa_root_vdev; |
1311 vdev_t *vd; 1312 int c, m; | |
1313 | 1409 |
1314 for (c = 0; c < rvd->vdev_children; c++) { 1315 vd = rvd->vdev_child[c]; 1316 for (m = 0; m < vd->vdev_ms_count; m++) { | 1410 for (int c = 0; c < rvd->vdev_children; c++) { 1411 vdev_t *vd = rvd->vdev_child[c]; 1412 for (int m = 0; m < vd->vdev_ms_count; m++) { |
1317 metaslab_t *msp = vd->vdev_ms[m]; 1318 mutex_enter(&msp->ms_lock); | 1413 metaslab_t *msp = vd->vdev_ms[m]; 1414 mutex_enter(&msp->ms_lock); |
1319 space_map_vacate(&msp->ms_allocmap[0], zdb_leak, 1320 &msp->ms_allocmap[0]); 1321 space_map_unload(&msp->ms_allocmap[0]); 1322 space_map_vacate(&msp->ms_freemap[0], NULL, NULL); | 1415 VERIFY(space_map_load(&msp->ms_map, &zdb_space_map_ops, 1416 SM_ALLOC, &msp->ms_smo, spa->spa_meta_objset) == 0); 1417 msp->ms_map.sm_ppd = vd; |
1323 mutex_exit(&msp->ms_lock); 1324 } 1325 } 1326} 1327 1328static void | 1418 mutex_exit(&msp->ms_lock); 1419 } 1420 } 1421} 1422 1423static void |
1329zdb_refresh_ubsync(spa_t *spa) | 1424zdb_leak_fini(spa_t *spa) |
1330{ | 1425{ |
1331 uberblock_t ub = { 0 }; | |
1332 vdev_t *rvd = spa->spa_root_vdev; | 1426 vdev_t *rvd = spa->spa_root_vdev; |
1333 zio_t *zio; | |
1334 | 1427 |
1335 /* 1336 * Reload the uberblock. 1337 */ 1338 zio = zio_root(spa, NULL, NULL, 1339 ZIO_FLAG_CANFAIL | ZIO_FLAG_SPECULATIVE); 1340 vdev_uberblock_load(zio, rvd, &ub); 1341 (void) zio_wait(zio); 1342 1343 if (ub.ub_txg != 0) 1344 spa->spa_ubsync = ub; | 1428 for (int c = 0; c < rvd->vdev_children; c++) { 1429 vdev_t *vd = rvd->vdev_child[c]; 1430 for (int m = 0; m < vd->vdev_ms_count; m++) { 1431 metaslab_t *msp = vd->vdev_ms[m]; 1432 mutex_enter(&msp->ms_lock); 1433 space_map_unload(&msp->ms_map); 1434 mutex_exit(&msp->ms_lock); 1435 } 1436 } |
1345} 1346 1347/* 1348 * Verify that the sum of the sizes of all blocks in the pool adds up 1349 * to the SPA's sa_alloc total. 1350 */ 1351typedef struct zdb_blkstats { 1352 uint64_t zb_asize; --- 13 unchanged lines hidden (view full) --- 1366 traverse_blk_cache_t *zcb_cache; 1367 int zcb_readfails; 1368 int zcb_haderrors; 1369} zdb_cb_t; 1370 1371static void 1372zdb_count_block(spa_t *spa, zdb_cb_t *zcb, blkptr_t *bp, int type) 1373{ | 1437} 1438 1439/* 1440 * Verify that the sum of the sizes of all blocks in the pool adds up 1441 * to the SPA's sa_alloc total. 1442 */ 1443typedef struct zdb_blkstats { 1444 uint64_t zb_asize; --- 13 unchanged lines hidden (view full) --- 1458 traverse_blk_cache_t *zcb_cache; 1459 int zcb_readfails; 1460 int zcb_haderrors; 1461} zdb_cb_t; 1462 1463static void 1464zdb_count_block(spa_t *spa, zdb_cb_t *zcb, blkptr_t *bp, int type) 1465{ |
1374 int i, error; 1375 1376 for (i = 0; i < 4; i++) { | 1466 for (int i = 0; i < 4; i++) { |
1377 int l = (i < 2) ? BP_GET_LEVEL(bp) : ZB_TOTAL; 1378 int t = (i & 1) ? type : DMU_OT_TOTAL; 1379 zdb_blkstats_t *zb = &zcb->zcb_type[l][t]; 1380 1381 zb->zb_asize += BP_GET_ASIZE(bp); 1382 zb->zb_lsize += BP_GET_LSIZE(bp); 1383 zb->zb_psize += BP_GET_PSIZE(bp); 1384 zb->zb_count++; 1385 } 1386 | 1467 int l = (i < 2) ? BP_GET_LEVEL(bp) : ZB_TOTAL; 1468 int t = (i & 1) ? type : DMU_OT_TOTAL; 1469 zdb_blkstats_t *zb = &zcb->zcb_type[l][t]; 1470 1471 zb->zb_asize += BP_GET_ASIZE(bp); 1472 zb->zb_lsize += BP_GET_LSIZE(bp); 1473 zb->zb_psize += BP_GET_PSIZE(bp); 1474 zb->zb_count++; 1475 } 1476 |
1387 if (dump_opt['L']) 1388 return; | 1477 if (dump_opt['S']) { 1478 boolean_t print_sig; |
1389 | 1479 |
1390 error = zdb_space_map_claim(spa, bp, &zcb->zcb_cache->bc_bookmark); | 1480 print_sig = !zdb_sig_user_data || (BP_GET_LEVEL(bp) == 0 && 1481 BP_GET_TYPE(bp) == DMU_OT_PLAIN_FILE_CONTENTS); |
1391 | 1482 |
1392 if (error == 0) 1393 return; | 1483 if (BP_GET_CHECKSUM(bp) < zdb_sig_cksumalg) 1484 print_sig = B_FALSE; |
1394 | 1485 |
1395 if (error == EAGAIN) 1396 (void) fatal("double-allocation, bp=%p", bp); | 1486 if (print_sig) { 1487 (void) printf("%llu\t%lld\t%lld\t%s\t%s\t%s\t" 1488 "%llx:%llx:%llx:%llx\n", 1489 (u_longlong_t)BP_GET_LEVEL(bp), 1490 (longlong_t)BP_GET_PSIZE(bp), 1491 (longlong_t)BP_GET_NDVAS(bp), 1492 dmu_ot[BP_GET_TYPE(bp)].ot_name, 1493 zio_checksum_table[BP_GET_CHECKSUM(bp)].ci_name, 1494 zio_compress_table[BP_GET_COMPRESS(bp)].ci_name, 1495 (u_longlong_t)bp->blk_cksum.zc_word[0], 1496 (u_longlong_t)bp->blk_cksum.zc_word[1], 1497 (u_longlong_t)bp->blk_cksum.zc_word[2], 1498 (u_longlong_t)bp->blk_cksum.zc_word[3]); 1499 } 1500 } |
1397 | 1501 |
1398 if (error == ESTALE) 1399 (void) fatal("reference to freed block, bp=%p", bp); 1400 1401 (void) fatal("fatal error %d in bp %p", error, bp); | 1502 if (!dump_opt['L']) 1503 VERIFY(zio_wait(zio_claim(NULL, spa, spa_first_txg(spa), bp, 1504 NULL, NULL, ZIO_FLAG_MUSTSUCCEED)) == 0); |
1402} 1403 1404static int 1405zdb_blkptr_cb(traverse_blk_cache_t *bc, spa_t *spa, void *arg) 1406{ 1407 zbookmark_t *zb = &bc->bc_bookmark; 1408 zdb_cb_t *zcb = arg; 1409 blkptr_t *bp = &bc->bc_blkptr; 1410 dmu_object_type_t type = BP_GET_TYPE(bp); 1411 char blkbuf[BP_SPRINTF_LEN]; 1412 int error = 0; 1413 | 1505} 1506 1507static int 1508zdb_blkptr_cb(traverse_blk_cache_t *bc, spa_t *spa, void *arg) 1509{ 1510 zbookmark_t *zb = &bc->bc_bookmark; 1511 zdb_cb_t *zcb = arg; 1512 blkptr_t *bp = &bc->bc_blkptr; 1513 dmu_object_type_t type = BP_GET_TYPE(bp); 1514 char blkbuf[BP_SPRINTF_LEN]; 1515 int error = 0; 1516 |
1517 ASSERT(!BP_IS_HOLE(bp)); 1518 1519 zdb_count_block(spa, zcb, bp, type); 1520 |
|
1414 if (bc->bc_errno) { 1415 if (zcb->zcb_readfails++ < 10 && dump_opt['L']) { | 1521 if (bc->bc_errno) { 1522 if (zcb->zcb_readfails++ < 10 && dump_opt['L']) { |
1416 zdb_refresh_ubsync(spa); | 1523 uberblock_t ub; 1524 vdev_uberblock_load(NULL, spa->spa_root_vdev, &ub); 1525 if (ub.ub_txg != 0) 1526 spa->spa_ubsync = ub; |
1417 error = EAGAIN; 1418 } else { 1419 zcb->zcb_haderrors = 1; 1420 zcb->zcb_errors[bc->bc_errno]++; 1421 error = ERESTART; 1422 } 1423 1424 if (dump_opt['b'] >= 3 || (dump_opt['b'] >= 2 && bc->bc_errno)) 1425 sprintf_blkptr(blkbuf, BP_SPRINTF_LEN, bp); 1426 else 1427 blkbuf[0] = '\0'; 1428 | 1527 error = EAGAIN; 1528 } else { 1529 zcb->zcb_haderrors = 1; 1530 zcb->zcb_errors[bc->bc_errno]++; 1531 error = ERESTART; 1532 } 1533 1534 if (dump_opt['b'] >= 3 || (dump_opt['b'] >= 2 && bc->bc_errno)) 1535 sprintf_blkptr(blkbuf, BP_SPRINTF_LEN, bp); 1536 else 1537 blkbuf[0] = '\0'; 1538 |
1429 (void) printf("zdb_blkptr_cb: Got error %d reading " 1430 "<%llu, %llu, %lld, %llx> %s -- %s\n", 1431 bc->bc_errno, 1432 (u_longlong_t)zb->zb_objset, 1433 (u_longlong_t)zb->zb_object, 1434 (u_longlong_t)zb->zb_level, 1435 (u_longlong_t)zb->zb_blkid, 1436 blkbuf, 1437 error == EAGAIN ? "retrying" : "skipping"); | 1539 if (!dump_opt['S']) { 1540 (void) printf("zdb_blkptr_cb: Got error %d reading " 1541 "<%llu, %llu, %lld, %llx> %s -- %s\n", 1542 bc->bc_errno, 1543 (u_longlong_t)zb->zb_objset, 1544 (u_longlong_t)zb->zb_object, 1545 (u_longlong_t)zb->zb_level, 1546 (u_longlong_t)zb->zb_blkid, 1547 blkbuf, 1548 error == EAGAIN ? "retrying" : "skipping"); 1549 } |
1438 1439 return (error); 1440 } 1441 1442 zcb->zcb_readfails = 0; 1443 | 1550 1551 return (error); 1552 } 1553 1554 zcb->zcb_readfails = 0; 1555 |
1444 ASSERT(!BP_IS_HOLE(bp)); 1445 | |
1446 if (dump_opt['b'] >= 4) { 1447 sprintf_blkptr(blkbuf, BP_SPRINTF_LEN, bp); 1448 (void) printf("objset %llu object %llu offset 0x%llx %s\n", 1449 (u_longlong_t)zb->zb_objset, 1450 (u_longlong_t)zb->zb_object, 1451 (u_longlong_t)blkid2offset(bc->bc_dnode, | 1556 if (dump_opt['b'] >= 4) { 1557 sprintf_blkptr(blkbuf, BP_SPRINTF_LEN, bp); 1558 (void) printf("objset %llu object %llu offset 0x%llx %s\n", 1559 (u_longlong_t)zb->zb_objset, 1560 (u_longlong_t)zb->zb_object, 1561 (u_longlong_t)blkid2offset(bc->bc_dnode, |
1452 zb->zb_level, zb->zb_blkid), 1453 blkbuf); | 1562 zb->zb_level, zb->zb_blkid), blkbuf); |
1454 } 1455 | 1563 } 1564 |
1456 zdb_count_block(spa, zcb, bp, type); 1457 | |
1458 return (0); 1459} 1460 1461static int 1462dump_block_stats(spa_t *spa) 1463{ 1464 traverse_handle_t *th; 1465 zdb_cb_t zcb = { 0 }; 1466 traverse_blk_cache_t dummy_cache = { 0 }; 1467 zdb_blkstats_t *zb, *tzb; | 1565 return (0); 1566} 1567 1568static int 1569dump_block_stats(spa_t *spa) 1570{ 1571 traverse_handle_t *th; 1572 zdb_cb_t zcb = { 0 }; 1573 traverse_blk_cache_t dummy_cache = { 0 }; 1574 zdb_blkstats_t *zb, *tzb; |
1468 uint64_t alloc, space; | 1575 uint64_t alloc, space, logalloc; 1576 vdev_t *rvd = spa->spa_root_vdev; |
1469 int leaks = 0; 1470 int advance = zdb_advance; | 1577 int leaks = 0; 1578 int advance = zdb_advance; |
1471 int flags; 1472 int e; | 1579 int c, e, flags; |
1473 1474 zcb.zcb_cache = &dummy_cache; 1475 | 1580 1581 zcb.zcb_cache = &dummy_cache; 1582 |
1476 if (dump_opt['c']) | 1583 if (dump_opt['c'] || dump_opt['S']) |
1477 advance |= ADVANCE_DATA; 1478 1479 advance |= ADVANCE_PRUNE | ADVANCE_ZIL; 1480 | 1584 advance |= ADVANCE_DATA; 1585 1586 advance |= ADVANCE_PRUNE | ADVANCE_ZIL; 1587 |
1481 (void) printf("\nTraversing all blocks to %sverify" 1482 " nothing leaked ...\n", 1483 dump_opt['c'] ? "verify checksums and " : ""); | 1588 if (!dump_opt['S']) { 1589 (void) printf("\nTraversing all blocks to %sverify" 1590 " nothing leaked ...\n", 1591 dump_opt['c'] ? "verify checksums and " : ""); 1592 } |
1484 1485 /* | 1593 1594 /* |
1486 * Load all space maps. As we traverse the pool, if we find a block 1487 * that's not in its space map, that indicates a double-allocation, 1488 * reference to a freed block, or an unclaimed block. Otherwise we 1489 * remove the block from the space map. If the space maps are not 1490 * empty when we're done, that indicates leaked blocks. | 1595 * Load all space maps as SM_ALLOC maps, then traverse the pool 1596 * claiming each block we discover. If the pool is perfectly 1597 * consistent, the space maps will be empty when we're done. 1598 * Anything left over is a leak; any block we can't claim (because 1599 * it's not part of any space map) is a double allocation, 1600 * reference to a freed block, or an unclaimed log block. |
1491 */ 1492 if (!dump_opt['L']) | 1601 */ 1602 if (!dump_opt['L']) |
1493 zdb_space_map_load(spa); | 1603 zdb_leak_init(spa); |
1494 1495 /* 1496 * If there's a deferred-free bplist, process that first. 1497 */ 1498 if (spa->spa_sync_bplist_obj != 0) { 1499 bplist_t *bpl = &spa->spa_sync_bplist; 1500 blkptr_t blk; 1501 uint64_t itor = 0; --- 26 unchanged lines hidden (view full) --- 1528 1529 traverse_add_pool(th, 0, spa_first_txg(spa) + TXG_CONCURRENT_STATES); 1530 1531 while (traverse_more(th) == EAGAIN) 1532 continue; 1533 1534 traverse_fini(th); 1535 | 1604 1605 /* 1606 * If there's a deferred-free bplist, process that first. 1607 */ 1608 if (spa->spa_sync_bplist_obj != 0) { 1609 bplist_t *bpl = &spa->spa_sync_bplist; 1610 blkptr_t blk; 1611 uint64_t itor = 0; --- 26 unchanged lines hidden (view full) --- 1638 1639 traverse_add_pool(th, 0, spa_first_txg(spa) + TXG_CONCURRENT_STATES); 1640 1641 while (traverse_more(th) == EAGAIN) 1642 continue; 1643 1644 traverse_fini(th); 1645 |
1536 if (zcb.zcb_haderrors) { | 1646 if (zcb.zcb_haderrors && !dump_opt['S']) { |
1537 (void) printf("\nError counts:\n\n"); 1538 (void) printf("\t%5s %s\n", "errno", "count"); 1539 for (e = 0; e < 256; e++) { 1540 if (zcb.zcb_errors[e] != 0) { 1541 (void) printf("\t%5d %llu\n", 1542 e, (u_longlong_t)zcb.zcb_errors[e]); 1543 } 1544 } 1545 } 1546 1547 /* 1548 * Report any leaked segments. 1549 */ 1550 if (!dump_opt['L']) | 1647 (void) printf("\nError counts:\n\n"); 1648 (void) printf("\t%5s %s\n", "errno", "count"); 1649 for (e = 0; e < 256; e++) { 1650 if (zcb.zcb_errors[e] != 0) { 1651 (void) printf("\t%5d %llu\n", 1652 e, (u_longlong_t)zcb.zcb_errors[e]); 1653 } 1654 } 1655 } 1656 1657 /* 1658 * Report any leaked segments. 1659 */ 1660 if (!dump_opt['L']) |
1551 zdb_space_map_unload(spa); | 1661 zdb_leak_fini(spa); |
1552 | 1662 |
1663 /* 1664 * If we're interested in printing out the blkptr signatures, 1665 * return now as we don't print out anything else (including 1666 * errors and leaks). 1667 */ 1668 if (dump_opt['S']) 1669 return (zcb.zcb_haderrors ? 3 : 0); 1670 |
|
1553 if (dump_opt['L']) 1554 (void) printf("\n\n *** Live pool traversal; " 1555 "block counts are only approximate ***\n\n"); 1556 1557 alloc = spa_get_alloc(spa); 1558 space = spa_get_space(spa); 1559 | 1671 if (dump_opt['L']) 1672 (void) printf("\n\n *** Live pool traversal; " 1673 "block counts are only approximate ***\n\n"); 1674 1675 alloc = spa_get_alloc(spa); 1676 space = spa_get_space(spa); 1677 |
1678 /* 1679 * Log blocks allocated from a separate log device don't count 1680 * as part of the normal pool space; factor them in here. 1681 */ 1682 logalloc = 0; 1683 1684 for (c = 0; c < rvd->vdev_children; c++) 1685 if (rvd->vdev_child[c]->vdev_islog) 1686 logalloc += rvd->vdev_child[c]->vdev_stat.vs_alloc; 1687 |
|
1560 tzb = &zcb.zcb_type[ZB_TOTAL][DMU_OT_TOTAL]; 1561 | 1688 tzb = &zcb.zcb_type[ZB_TOTAL][DMU_OT_TOTAL]; 1689 |
1562 if (tzb->zb_asize == alloc) { | 1690 if (tzb->zb_asize == alloc + logalloc) { |
1563 (void) printf("\n\tNo leaks (block sum matches space" 1564 " maps exactly)\n"); 1565 } else { 1566 (void) printf("block traversal size %llu != alloc %llu " 1567 "(leaked %lld)\n", 1568 (u_longlong_t)tzb->zb_asize, | 1691 (void) printf("\n\tNo leaks (block sum matches space" 1692 " maps exactly)\n"); 1693 } else { 1694 (void) printf("block traversal size %llu != alloc %llu " 1695 "(leaked %lld)\n", 1696 (u_longlong_t)tzb->zb_asize, |
1569 (u_longlong_t)alloc, 1570 (u_longlong_t)(alloc - tzb->zb_asize)); | 1697 (u_longlong_t)alloc + logalloc, 1698 (u_longlong_t)(alloc + logalloc - tzb->zb_asize)); |
1571 leaks = 1; 1572 } 1573 1574 if (tzb->zb_count == 0) 1575 return (2); 1576 1577 (void) printf("\n"); 1578 (void) printf("\tbp count: %10llu\n", --- 98 unchanged lines hidden (view full) --- 1677 if (dump_opt['d'] || dump_opt['i']) { 1678 dump_dir(dp->dp_meta_objset); 1679 if (dump_opt['d'] >= 3) { 1680 dump_bplist(dp->dp_meta_objset, 1681 spa->spa_sync_bplist_obj, "Deferred frees"); 1682 dump_dtl(spa->spa_root_vdev, 0); 1683 dump_metaslabs(spa); 1684 } | 1699 leaks = 1; 1700 } 1701 1702 if (tzb->zb_count == 0) 1703 return (2); 1704 1705 (void) printf("\n"); 1706 (void) printf("\tbp count: %10llu\n", --- 98 unchanged lines hidden (view full) --- 1805 if (dump_opt['d'] || dump_opt['i']) { 1806 dump_dir(dp->dp_meta_objset); 1807 if (dump_opt['d'] >= 3) { 1808 dump_bplist(dp->dp_meta_objset, 1809 spa->spa_sync_bplist_obj, "Deferred frees"); 1810 dump_dtl(spa->spa_root_vdev, 0); 1811 dump_metaslabs(spa); 1812 } |
1685 (void) dmu_objset_find(spa->spa_name, dump_one_dir, NULL, | 1813 (void) dmu_objset_find(spa_name(spa), dump_one_dir, NULL, |
1686 DS_FIND_SNAPSHOTS | DS_FIND_CHILDREN); 1687 } 1688 | 1814 DS_FIND_SNAPSHOTS | DS_FIND_CHILDREN); 1815 } 1816 |
1689 if (dump_opt['b'] || dump_opt['c']) | 1817 if (dump_opt['b'] || dump_opt['c'] || dump_opt['S']) |
1690 rc = dump_block_stats(spa); 1691 1692 if (dump_opt['s']) 1693 show_pool_stats(spa); 1694 1695 if (rc != 0) 1696 exit(rc); 1697} --- 195 unchanged lines hidden (view full) --- 1893zdb_read_block(char *thing, spa_t **spap) 1894{ 1895 spa_t *spa = *spap; 1896 int flags = 0; 1897 uint64_t offset = 0, size = 0, blkptr_offset = 0; 1898 zio_t *zio; 1899 vdev_t *vd; 1900 void *buf; | 1818 rc = dump_block_stats(spa); 1819 1820 if (dump_opt['s']) 1821 show_pool_stats(spa); 1822 1823 if (rc != 0) 1824 exit(rc); 1825} --- 195 unchanged lines hidden (view full) --- 2021zdb_read_block(char *thing, spa_t **spap) 2022{ 2023 spa_t *spa = *spap; 2024 int flags = 0; 2025 uint64_t offset = 0, size = 0, blkptr_offset = 0; 2026 zio_t *zio; 2027 vdev_t *vd; 2028 void *buf; |
1901 char *s, *p, *dup, *spa_name, *vdev, *flagstr; | 2029 char *s, *p, *dup, *pool, *vdev, *flagstr; |
1902 int i, error, zio_flags; 1903 1904 dup = strdup(thing); 1905 s = strtok(dup, ":"); | 2030 int i, error, zio_flags; 2031 2032 dup = strdup(thing); 2033 s = strtok(dup, ":"); |
1906 spa_name = s ? s : ""; | 2034 pool = s ? s : ""; |
1907 s = strtok(NULL, ":"); 1908 vdev = s ? s : ""; 1909 s = strtok(NULL, ":"); 1910 offset = strtoull(s ? s : "", NULL, 16); 1911 s = strtok(NULL, ":"); 1912 size = strtoull(s ? s : "", NULL, 16); 1913 s = strtok(NULL, ":"); 1914 flagstr = s ? s : ""; --- 33 unchanged lines hidden (view full) --- 1948 if (*p != ':' && *p != '\0') { 1949 (void) printf("***Invalid flag arg: '%s'\n", s); 1950 free(dup); 1951 return; 1952 } 1953 } 1954 } 1955 | 2035 s = strtok(NULL, ":"); 2036 vdev = s ? s : ""; 2037 s = strtok(NULL, ":"); 2038 offset = strtoull(s ? s : "", NULL, 16); 2039 s = strtok(NULL, ":"); 2040 size = strtoull(s ? s : "", NULL, 16); 2041 s = strtok(NULL, ":"); 2042 flagstr = s ? s : ""; --- 33 unchanged lines hidden (view full) --- 2076 if (*p != ':' && *p != '\0') { 2077 (void) printf("***Invalid flag arg: '%s'\n", s); 2078 free(dup); 2079 return; 2080 } 2081 } 2082 } 2083 |
1956 if (spa == NULL || spa->spa_name == NULL || 1957 strcmp(spa->spa_name, spa_name)) { 1958 if (spa && spa->spa_name) | 2084 if (spa == NULL || strcmp(spa_name(spa), pool) != 0) { 2085 if (spa) |
1959 spa_close(spa, (void *)zdb_read_block); | 2086 spa_close(spa, (void *)zdb_read_block); |
1960 error = spa_open(spa_name, spap, (void *)zdb_read_block); | 2087 error = spa_open(pool, spap, (void *)zdb_read_block); |
1961 if (error) 1962 fatal("Failed to open pool '%s': %s", | 2088 if (error) 2089 fatal("Failed to open pool '%s': %s", |
1963 spa_name, strerror(error)); | 2090 pool, strerror(error)); |
1964 spa = *spap; 1965 } 1966 1967 vd = zdb_vdev_lookup(spa->spa_root_vdev, vdev); 1968 if (vd == NULL) { 1969 (void) printf("***Invalid vdev: %s\n", vdev); 1970 free(dup); 1971 return; 1972 } else { 1973 if (vd->vdev_path) 1974 (void) printf("Found vdev: %s\n", vd->vdev_path); 1975 else 1976 (void) printf("Found vdev type: %s\n", 1977 vd->vdev_ops->vdev_op_type); 1978 } 1979 1980 buf = umem_alloc(size, UMEM_NOFAIL); 1981 1982 zio_flags = ZIO_FLAG_DONT_CACHE | ZIO_FLAG_DONT_QUEUE | | 2091 spa = *spap; 2092 } 2093 2094 vd = zdb_vdev_lookup(spa->spa_root_vdev, vdev); 2095 if (vd == NULL) { 2096 (void) printf("***Invalid vdev: %s\n", vdev); 2097 free(dup); 2098 return; 2099 } else { 2100 if (vd->vdev_path) 2101 (void) printf("Found vdev: %s\n", vd->vdev_path); 2102 else 2103 (void) printf("Found vdev type: %s\n", 2104 vd->vdev_ops->vdev_op_type); 2105 } 2106 2107 buf = umem_alloc(size, UMEM_NOFAIL); 2108 2109 zio_flags = ZIO_FLAG_DONT_CACHE | ZIO_FLAG_DONT_QUEUE | |
1983 ZIO_FLAG_DONT_PROPAGATE | ZIO_FLAG_DONT_RETRY | ZIO_FLAG_NOBOOKMARK; | 2110 ZIO_FLAG_DONT_PROPAGATE | ZIO_FLAG_DONT_RETRY; |
1984 | 2111 |
1985 if (flags & ZDB_FLAG_PHYS) 1986 zio_flags |= ZIO_FLAG_PHYSICAL; 1987 | 2112 spa_config_enter(spa, SCL_STATE, FTAG, RW_READER); |
1988 zio = zio_root(spa, NULL, NULL, 0); 1989 /* XXX todo - cons up a BP so RAID-Z will be happy */ 1990 zio_nowait(zio_vdev_child_io(zio, NULL, vd, offset, buf, size, 1991 ZIO_TYPE_READ, ZIO_PRIORITY_SYNC_READ, zio_flags, NULL, NULL)); 1992 error = zio_wait(zio); | 2113 zio = zio_root(spa, NULL, NULL, 0); 2114 /* XXX todo - cons up a BP so RAID-Z will be happy */ 2115 zio_nowait(zio_vdev_child_io(zio, NULL, vd, offset, buf, size, 2116 ZIO_TYPE_READ, ZIO_PRIORITY_SYNC_READ, zio_flags, NULL, NULL)); 2117 error = zio_wait(zio); |
2118 spa_config_exit(spa, SCL_STATE, FTAG); |
|
1993 1994 if (error) { 1995 (void) printf("Read of %s failed, error: %d\n", thing, error); 1996 goto out; 1997 } 1998 1999 if (flags & ZDB_FLAG_PRINT_BLKPTR) 2000 zdb_print_blkptr((blkptr_t *)(void *) --- 8 unchanged lines hidden (view full) --- 2009 else 2010 zdb_dump_block(thing, buf, size, flags); 2011 2012out: 2013 umem_free(buf, size); 2014 free(dup); 2015} 2016 | 2119 2120 if (error) { 2121 (void) printf("Read of %s failed, error: %d\n", thing, error); 2122 goto out; 2123 } 2124 2125 if (flags & ZDB_FLAG_PRINT_BLKPTR) 2126 zdb_print_blkptr((blkptr_t *)(void *) --- 8 unchanged lines hidden (view full) --- 2135 else 2136 zdb_dump_block(thing, buf, size, flags); 2137 2138out: 2139 umem_free(buf, size); 2140 free(dup); 2141} 2142 |
2143static boolean_t 2144nvlist_string_match(nvlist_t *config, char *name, char *tgt) 2145{ 2146 char *s; 2147 2148 if (nvlist_lookup_string(config, name, &s) != 0) 2149 return (B_FALSE); 2150 2151 return (strcmp(s, tgt) == 0); 2152} 2153 2154static boolean_t 2155nvlist_uint64_match(nvlist_t *config, char *name, uint64_t tgt) 2156{ 2157 uint64_t val; 2158 2159 if (nvlist_lookup_uint64(config, name, &val) != 0) 2160 return (B_FALSE); 2161 2162 return (val == tgt); 2163} 2164 2165static boolean_t 2166vdev_child_guid_match(nvlist_t *vdev, uint64_t guid) 2167{ 2168 nvlist_t **child; 2169 uint_t c, children; 2170 2171 verify(nvlist_lookup_nvlist_array(vdev, ZPOOL_CONFIG_CHILDREN, 2172 &child, &children) == 0); 2173 for (c = 0; c < children; ++c) 2174 if (nvlist_uint64_match(child[c], ZPOOL_CONFIG_GUID, guid)) 2175 return (B_TRUE); 2176 return (B_FALSE); 2177} 2178 2179static boolean_t 2180vdev_child_string_match(nvlist_t *vdev, char *tgt) 2181{ 2182 nvlist_t **child; 2183 uint_t c, children; 2184 2185 verify(nvlist_lookup_nvlist_array(vdev, ZPOOL_CONFIG_CHILDREN, 2186 &child, &children) == 0); 2187 for (c = 0; c < children; ++c) { 2188 if (nvlist_string_match(child[c], ZPOOL_CONFIG_PATH, tgt) || 2189 nvlist_string_match(child[c], ZPOOL_CONFIG_DEVID, tgt)) 2190 return (B_TRUE); 2191 } 2192 return (B_FALSE); 2193} 2194 2195static boolean_t 2196vdev_guid_match(nvlist_t *config, uint64_t guid) 2197{ 2198 nvlist_t *nvroot; 2199 2200 verify(nvlist_lookup_nvlist(config, ZPOOL_CONFIG_VDEV_TREE, 2201 &nvroot) == 0); 2202 2203 return (nvlist_uint64_match(nvroot, ZPOOL_CONFIG_GUID, guid) || 2204 vdev_child_guid_match(nvroot, guid)); 2205} 2206 2207static boolean_t 2208vdev_string_match(nvlist_t *config, char *tgt) 2209{ 2210 nvlist_t *nvroot; 2211 2212 verify(nvlist_lookup_nvlist(config, ZPOOL_CONFIG_VDEV_TREE, 2213 &nvroot) == 0); 2214 2215 return (vdev_child_string_match(nvroot, tgt)); 2216} 2217 2218static boolean_t 2219pool_match(nvlist_t *config, char *tgt) 2220{ 2221 uint64_t guid = strtoull(tgt, NULL, 0); 2222 2223 if (guid != 0) { 2224 return ( 2225 nvlist_uint64_match(config, ZPOOL_CONFIG_POOL_GUID, guid) || 2226 vdev_guid_match(config, guid)); 2227 } else { 2228 return ( 2229 nvlist_string_match(config, ZPOOL_CONFIG_POOL_NAME, tgt) || 2230 vdev_string_match(config, tgt)); 2231 } 2232} 2233 2234static int 2235find_exported_zpool(char *pool_id, nvlist_t **configp, char *vdev_dir) 2236{ 2237 nvlist_t *pools; 2238 int error = ENOENT; 2239 nvlist_t *match = NULL; 2240 2241 if (vdev_dir != NULL) 2242 pools = zpool_find_import_activeok(g_zfs, 1, &vdev_dir); 2243 else 2244 pools = zpool_find_import_activeok(g_zfs, 0, NULL); 2245 2246 if (pools != NULL) { 2247 nvpair_t *elem = NULL; 2248 2249 while ((elem = nvlist_next_nvpair(pools, elem)) != NULL) { 2250 verify(nvpair_value_nvlist(elem, configp) == 0); 2251 if (pool_match(*configp, pool_id)) { 2252 if (match != NULL) { 2253 (void) fatal( 2254 "More than one matching pool - " 2255 "specify guid/devid/device path."); 2256 } else { 2257 match = *configp; 2258 error = 0; 2259 } 2260 } 2261 } 2262 } 2263 2264 *configp = error ? NULL : match; 2265 2266 return (error); 2267} 2268 |
|
2017int 2018main(int argc, char **argv) 2019{ 2020 int i, c; 2021 struct rlimit rl = { 1024, 1024 }; 2022 spa_t *spa; 2023 objset_t *os = NULL; 2024 char *endstr; 2025 int dump_all = 1; 2026 int verbose = 0; 2027 int error; 2028 int flag, set; | 2269int 2270main(int argc, char **argv) 2271{ 2272 int i, c; 2273 struct rlimit rl = { 1024, 1024 }; 2274 spa_t *spa; 2275 objset_t *os = NULL; 2276 char *endstr; 2277 int dump_all = 1; 2278 int verbose = 0; 2279 int error; 2280 int flag, set; |
2281 int exported = 0; 2282 char *vdev_dir = NULL; |
|
2029 2030 (void) setrlimit(RLIMIT_NOFILE, &rl); 2031 (void) enable_extended_FILE_stdio(-1, -1); 2032 2033 dprintf_setup(&argc, argv); 2034 | 2283 2284 (void) setrlimit(RLIMIT_NOFILE, &rl); 2285 (void) enable_extended_FILE_stdio(-1, -1); 2286 2287 dprintf_setup(&argc, argv); 2288 |
2035 while ((c = getopt(argc, argv, "udibcsvCLO:B:UlR")) != -1) { | 2289 while ((c = getopt(argc, argv, "udibcsvCLO:B:S:U:lRep:")) != -1) { |
2036 switch (c) { 2037 case 'u': 2038 case 'd': 2039 case 'i': 2040 case 'b': 2041 case 'c': 2042 case 's': 2043 case 'C': --- 44 unchanged lines hidden (view full) --- 2088 (u_longlong_t)zdb_noread.zb_object, 2089 (u_longlong_t)zdb_noread.zb_level, 2090 (u_longlong_t)zdb_noread.zb_blkid); 2091 break; 2092 case 'v': 2093 verbose++; 2094 break; 2095 case 'U': | 2290 switch (c) { 2291 case 'u': 2292 case 'd': 2293 case 'i': 2294 case 'b': 2295 case 'c': 2296 case 's': 2297 case 'C': --- 44 unchanged lines hidden (view full) --- 2342 (u_longlong_t)zdb_noread.zb_object, 2343 (u_longlong_t)zdb_noread.zb_level, 2344 (u_longlong_t)zdb_noread.zb_blkid); 2345 break; 2346 case 'v': 2347 verbose++; 2348 break; 2349 case 'U': |
2096 spa_config_dir = "/tmp"; | 2350 spa_config_path = optarg; |
2097 break; | 2351 break; |
2352 case 'e': 2353 exported = 1; 2354 break; 2355 case 'p': 2356 vdev_dir = optarg; 2357 break; 2358 case 'S': 2359 dump_opt[c]++; 2360 dump_all = 0; 2361 zdb_sig_user_data = (strncmp(optarg, "user:", 5) == 0); 2362 if (!zdb_sig_user_data && strncmp(optarg, "all:", 4)) 2363 usage(); 2364 endstr = strchr(optarg, ':') + 1; 2365 if (strcmp(endstr, "fletcher2") == 0) 2366 zdb_sig_cksumalg = ZIO_CHECKSUM_FLETCHER_2; 2367 else if (strcmp(endstr, "fletcher4") == 0) 2368 zdb_sig_cksumalg = ZIO_CHECKSUM_FLETCHER_4; 2369 else if (strcmp(endstr, "sha256") == 0) 2370 zdb_sig_cksumalg = ZIO_CHECKSUM_SHA256; 2371 else if (strcmp(endstr, "all") == 0) 2372 zdb_sig_cksumalg = ZIO_CHECKSUM_FLETCHER_2; 2373 else 2374 usage(); 2375 break; |
|
2098 default: 2099 usage(); 2100 break; 2101 } 2102 } 2103 | 2376 default: 2377 usage(); 2378 break; 2379 } 2380 } 2381 |
2382 if (vdev_dir != NULL && exported == 0) 2383 (void) fatal("-p option requires use of -e\n"); 2384 |
|
2104 kernel_init(FREAD); | 2385 kernel_init(FREAD); |
2386 g_zfs = libzfs_init(); 2387 ASSERT(g_zfs != NULL); |
|
2105 2106 /* 2107 * Disable vdev caching. If we don't do this, live pool traversal 2108 * won't make progress because it will never see disk updates. 2109 */ 2110 zfs_vdev_cache_size = 0; 2111 2112 for (c = 0; c < 256; c++) { 2113 if (dump_all && c != 'L' && c != 'l' && c != 'R') 2114 dump_opt[c] = 1; 2115 if (dump_opt[c]) 2116 dump_opt[c] += verbose; 2117 } 2118 2119 argc -= optind; 2120 argv += optind; 2121 2122 if (argc < 1) { 2123 if (dump_opt['C']) { | 2388 2389 /* 2390 * Disable vdev caching. If we don't do this, live pool traversal 2391 * won't make progress because it will never see disk updates. 2392 */ 2393 zfs_vdev_cache_size = 0; 2394 2395 for (c = 0; c < 256; c++) { 2396 if (dump_all && c != 'L' && c != 'l' && c != 'R') 2397 dump_opt[c] = 1; 2398 if (dump_opt[c]) 2399 dump_opt[c] += verbose; 2400 } 2401 2402 argc -= optind; 2403 argv += optind; 2404 2405 if (argc < 1) { 2406 if (dump_opt['C']) { |
2124 dump_config(NULL); | 2407 dump_cachefile(spa_config_path); |
2125 return (0); 2126 } 2127 usage(); 2128 } 2129 2130 if (dump_opt['l']) { 2131 dump_label(argv[0]); 2132 return (0); --- 18 unchanged lines hidden (view full) --- 2151 if (spa) 2152 spa_close(spa, (void *)zdb_read_block); 2153 return (0); 2154 } 2155 2156 if (dump_opt['C']) 2157 dump_config(argv[0]); 2158 | 2408 return (0); 2409 } 2410 usage(); 2411 } 2412 2413 if (dump_opt['l']) { 2414 dump_label(argv[0]); 2415 return (0); --- 18 unchanged lines hidden (view full) --- 2434 if (spa) 2435 spa_close(spa, (void *)zdb_read_block); 2436 return (0); 2437 } 2438 2439 if (dump_opt['C']) 2440 dump_config(argv[0]); 2441 |
2159 if (strchr(argv[0], '/') != NULL) { 2160 error = dmu_objset_open(argv[0], DMU_OST_ANY, 2161 DS_MODE_STANDARD | DS_MODE_READONLY, &os); 2162 } else { 2163 error = spa_open(argv[0], &spa, FTAG); | 2442 error = 0; 2443 if (exported) { 2444 /* 2445 * Check to see if the name refers to an exported zpool 2446 */ 2447 char *slash; 2448 nvlist_t *exported_conf = NULL; 2449 2450 if ((slash = strchr(argv[0], '/')) != NULL) 2451 *slash = '\0'; 2452 2453 error = find_exported_zpool(argv[0], &exported_conf, vdev_dir); 2454 if (error == 0) { 2455 nvlist_t *nvl = NULL; 2456 2457 if (vdev_dir != NULL) { 2458 if (nvlist_alloc(&nvl, NV_UNIQUE_NAME, 0) != 0) 2459 error = ENOMEM; 2460 else if (nvlist_add_string(nvl, 2461 zpool_prop_to_name(ZPOOL_PROP_ALTROOT), 2462 vdev_dir) != 0) 2463 error = ENOMEM; 2464 } 2465 2466 if (error == 0) 2467 error = spa_import_faulted(argv[0], 2468 exported_conf, nvl); 2469 2470 nvlist_free(nvl); 2471 } 2472 2473 if (slash != NULL) 2474 *slash = '/'; |
2164 } 2165 | 2475 } 2476 |
2477 if (error == 0) { 2478 if (strchr(argv[0], '/') != NULL) { 2479 error = dmu_objset_open(argv[0], DMU_OST_ANY, 2480 DS_MODE_USER | DS_MODE_READONLY, &os); 2481 } else { 2482 error = spa_open(argv[0], &spa, FTAG); 2483 } 2484 } 2485 |
|
2166 if (error) 2167 fatal("can't open %s: %s", argv[0], strerror(error)); 2168 2169 argv++; 2170 if (--argc > 0) { 2171 zopt_objects = argc; 2172 zopt_object = calloc(zopt_objects, sizeof (uint64_t)); 2173 for (i = 0; i < zopt_objects; i++) { --- 8 unchanged lines hidden (view full) --- 2182 if (os != NULL) { 2183 dump_dir(os); 2184 dmu_objset_close(os); 2185 } else { 2186 dump_zpool(spa); 2187 spa_close(spa, FTAG); 2188 } 2189 | 2486 if (error) 2487 fatal("can't open %s: %s", argv[0], strerror(error)); 2488 2489 argv++; 2490 if (--argc > 0) { 2491 zopt_objects = argc; 2492 zopt_object = calloc(zopt_objects, sizeof (uint64_t)); 2493 for (i = 0; i < zopt_objects; i++) { --- 8 unchanged lines hidden (view full) --- 2502 if (os != NULL) { 2503 dump_dir(os); 2504 dmu_objset_close(os); 2505 } else { 2506 dump_zpool(spa); 2507 spa_close(spa, FTAG); 2508 } 2509 |
2510 fuid_table_destroy(); 2511 2512 libzfs_fini(g_zfs); |
|
2190 kernel_fini(); 2191 2192 return (0); 2193} | 2513 kernel_fini(); 2514 2515 return (0); 2516} |