From 69874af7b81519e40db9d92efa6beebee4220c63 Mon Sep 17 00:00:00 2001 From: David Sterba Date: Thu, 10 Mar 2016 15:57:46 +0100 Subject: [PATCH] btrfs-progs: dump-tree: let --tree understand name of the tree For practical purposes teach -t about the human readable names of the trees in addition to the numerical id. The name syntax is flexible. Signed-off-by: David Sterba --- Documentation/btrfs-inspect-internal.asciidoc | 11 ++- cmds-inspect-dump-tree.c | 87 ++++++++++++++++++- 2 files changed, 95 insertions(+), 3 deletions(-) diff --git a/Documentation/btrfs-inspect-internal.asciidoc b/Documentation/btrfs-inspect-internal.asciidoc index f19522f4..d71b10a8 100644 --- a/Documentation/btrfs-inspect-internal.asciidoc +++ b/Documentation/btrfs-inspect-internal.asciidoc @@ -46,7 +46,16 @@ print only the uuid tree information, empty output if the tree does not exist -b :::: print info of the specified block only -t :::: -print only the tree with the specified numerical ID +print only the tree with the specified ID, where the ID can be numerical or +common name in a flexible human readable form ++ +The tree id name recognition rules: +[options="compact"] +* case does not matter +* the C source definition, eg. BTRFS_ROOT_TREE_OBJECTID +* short forms without BTRFS_ prefix, without _TREE and _OBJECTID suffix, eg. ROOT_TREE, ROOT +* convenience aliases, eg. DEVICE for the DEV tree, CHECKSUM for CSUM +* unrecognized ID is an error *inode-resolve* [-v] :: (needs root privileges) diff --git a/cmds-inspect-dump-tree.c b/cmds-inspect-dump-tree.c index f548efa4..43c8b67c 100644 --- a/cmds-inspect-dump-tree.c +++ b/cmds-inspect-dump-tree.c @@ -106,6 +106,72 @@ static void print_old_roots(struct btrfs_super_block *super) } } +/* + * Convert a tree name from various forms to the numerical id if possible + * Accepted forms: + * - case does not matter + * - same as the key name, BTRFS_ROOT_TREE_OBJECTID + * - dtto shortened, BTRFS_ROOT_TREE + * - dtto without prefix, ROOT_TREE + * - common name, ROOT, CHUNK, EXTENT, ... + * - dtto alias, DEVICE for DEV, CHECKSUM for CSUM + * + * Returns 0 if the tree id was not recognized. + */ +static u64 treeid_from_string(const char *str, const char **end) +{ + int match = 0; + int i; + u64 id; + static struct treename { + const char *name; + u64 id; + } tn[] = { + { "ROOT", BTRFS_ROOT_TREE_OBJECTID }, + { "EXTENT", BTRFS_EXTENT_TREE_OBJECTID }, + { "CHUNK", BTRFS_CHUNK_TREE_OBJECTID }, + { "DEVICE", BTRFS_DEV_TREE_OBJECTID }, + { "DEV", BTRFS_DEV_TREE_OBJECTID }, + { "FS_TREE", BTRFS_FS_TREE_OBJECTID }, + { "CSUM", BTRFS_CSUM_TREE_OBJECTID }, + { "CHECKSUM", BTRFS_CSUM_TREE_OBJECTID }, + { "QUOTA", BTRFS_QUOTA_TREE_OBJECTID }, + { "UUID", BTRFS_UUID_TREE_OBJECTID }, + { "FREE_SPACE", BTRFS_FREE_SPACE_TREE_OBJECTID }, + { "TREE_LOG_FIXUP", BTRFS_TREE_LOG_FIXUP_OBJECTID }, + { "TREE_LOG", BTRFS_TREE_LOG_OBJECTID }, + { "TREE_RELOC", BTRFS_TREE_RELOC_OBJECTID }, + { "DATA_RELOC", BTRFS_DATA_RELOC_TREE_OBJECTID } + }; + + if (strncasecmp("BTRFS_", str, strlen("BTRFS_")) == 0) + str += strlen("BTRFS_"); + + for (i = 0; i < ARRAY_SIZE(tn); i++) { + int len = strlen(tn[i].name); + + if (strncasecmp(tn[i].name, str, len) == 0) { + id = tn[i].id; + match = 1; + str += len; + break; + } + } + + if (!match) + return 0; + + if (strncasecmp("_TREE", str, strlen("_TREE")) == 0) + str += strlen("_TREE"); + + if (strncasecmp("_OBJECTID", str, strlen("_OBJECTID")) == 0) + str += strlen("_OBJECTID"); + + *end = str; + + return id; +} + const char * const cmd_inspect_dump_tree_usage[] = { "btrfs inspect-internal dump-tree [options] device", "Dump tree structures from a given device", @@ -120,7 +186,7 @@ const char * const cmd_inspect_dump_tree_usage[] = { "-R|--backups same as --roots plus print backup root info", "-u|--uuid print only the uuid tree", "-b|--block print info from the specified block only", - "-t|--tree print only the tree with the given tree_id", + "-t|--tree print only tree with the given id (string or number)", NULL }; @@ -183,7 +249,24 @@ int cmd_inspect_dump_tree(int argc, char **argv) block_only = arg_strtou64(optarg); break; case 't': - tree_id = arg_strtou64(optarg); + if (string_is_numerical(optarg)) { + tree_id = arg_strtou64(optarg); + } else { + const char *end = NULL; + + tree_id = treeid_from_string(optarg, &end); + + if (*end) { + error("unexpected tree id suffix of '%s': %s\n", + optarg, end); + exit(1); + } + } + if (!tree_id) { + error("unrecognized tree id: %s\n", + optarg); + exit(1); + } break; default: usage(cmd_inspect_dump_tree_usage);