Add support for filesystem labels via mkfs.btrfs -L
authorChris Mason <chris.mason@oracle.com>
Fri, 18 Apr 2008 14:31:42 +0000 (10:31 -0400)
committerDavid Woodhouse <dwmw2@hera.kernel.org>
Fri, 18 Apr 2008 14:31:42 +0000 (10:31 -0400)
ctree.h
mkfs.c
utils.c
utils.h
volumes.c

diff --git a/ctree.h b/ctree.h
index 4e62fe6..1c22de7 100644 (file)
--- a/ctree.h
+++ b/ctree.h
@@ -235,6 +235,7 @@ struct btrfs_header {
  * room to translate 14 chunks with 3 stripes each.
  */
 #define BTRFS_SYSTEM_CHUNK_ARRAY_SIZE 2048
+#define BTRFS_LABEL_SIZE 256
 
 /*
  * the super block basically lists the main trees of the FS
@@ -264,6 +265,7 @@ struct btrfs_super_block {
        u8 root_level;
        u8 chunk_root_level;
        struct btrfs_dev_item dev_item;
+       char label[BTRFS_LABEL_SIZE];
        u8 sys_chunk_array[BTRFS_SYSTEM_CHUNK_ARRAY_SIZE];
 } __attribute__ ((__packed__));
 
diff --git a/mkfs.c b/mkfs.c
index 2b74309..4fae944 100644 (file)
--- a/mkfs.c
+++ b/mkfs.c
@@ -260,12 +260,32 @@ static u64 parse_profile(char *s)
        return 0;
 }
 
+static char *parse_label(char *input)
+{
+       int i;
+       int len = strlen(input);
+
+       if (len > BTRFS_LABEL_SIZE) {
+               fprintf(stderr, "Label %s is too long (max %d)\n", input,
+                       BTRFS_LABEL_SIZE);
+               exit(1);
+       }
+       for (i = 0; i < len; i++) {
+               if (input[i] == '/' || input[i] == '\\') {
+                       fprintf(stderr, "invalid label %s\n", input);
+                       exit(1);
+               }
+       }
+       return strdup(input);
+}
+
 static struct option long_options[] = {
        { "byte-count", 1, NULL, 'b' },
        { "leafsize", 1, NULL, 'l' },
+       { "label", 1, NULL, 'L'},
+       { "metadata", 1, NULL, 'm' },
        { "nodesize", 1, NULL, 'n' },
        { "sectorsize", 1, NULL, 's' },
-       { "metadata", 1, NULL, 'm' },
        { "data", 1, NULL, 'd' },
        { 0, 0, 0, 0}
 };
@@ -273,27 +293,28 @@ static struct option long_options[] = {
 int main(int ac, char **av)
 {
        char *file;
+       struct btrfs_root *root;
+       struct btrfs_trans_handle *trans;
+       char *label = NULL;
        u64 block_count = 0;
        u64 dev_block_count = 0;
-       int fd;
-       int first_fd;
-       int ret;
-       int i;
+       u64 blocks[6];
+       u64 metadata_profile = BTRFS_BLOCK_GROUP_RAID1 | BTRFS_BLOCK_GROUP_DUP;
+       u64 data_profile = BTRFS_BLOCK_GROUP_RAID0;
        u32 leafsize = getpagesize();
        u32 sectorsize = 4096;
        u32 nodesize = leafsize;
        u32 stripesize = 4096;
-       u64 blocks[6];
        int zero_end = 1;
        int option_index = 0;
-       struct btrfs_root *root;
-       struct btrfs_trans_handle *trans;
-       u64 metadata_profile = BTRFS_BLOCK_GROUP_RAID1 | BTRFS_BLOCK_GROUP_DUP;
-       u64 data_profile = BTRFS_BLOCK_GROUP_RAID0;
+       int fd;
+       int first_fd;
+       int ret;
+       int i;
 
        while(1) {
                int c;
-               c = getopt_long(ac, av, "b:l:n:s:m:d:", long_options,
+               c = getopt_long(ac, av, "b:l:n:s:m:d:L:", long_options,
                                &option_index);
                if (c < 0)
                        break;
@@ -301,12 +322,15 @@ int main(int ac, char **av)
                        case 'd':
                                data_profile = parse_profile(optarg);
                                break;
-                       case 'm':
-                               metadata_profile = parse_profile(optarg);
                                break;
                        case 'l':
                                leafsize = parse_size(optarg);
                                break;
+                       case 'L':
+                               label = parse_label(optarg);
+                               break;
+                       case 'm':
+                               metadata_profile = parse_profile(optarg);
                        case 'n':
                                nodesize = parse_size(optarg);
                                break;
@@ -358,7 +382,8 @@ int main(int ac, char **av)
        for (i = 0; i < 6; i++)
                blocks[i] = BTRFS_SUPER_INFO_OFFSET + leafsize * i;
 
-       ret = make_btrfs(fd, file, blocks, block_count, nodesize, leafsize,
+       ret = make_btrfs(fd, file, label, blocks, block_count,
+                        nodesize, leafsize,
                         sectorsize, stripesize);
        if (ret) {
                fprintf(stderr, "error during mkfs %d\n", ret);
@@ -369,10 +394,12 @@ int main(int ac, char **av)
                fprintf(stderr, "failed to setup the root directory\n");
                exit(1);
        }
-       printf("fs created on %s nodesize %u leafsize %u sectorsize %u bytes %llu\n",
-              file, nodesize, leafsize, sectorsize,
+       printf("fs created label %s on %s\n\tnodesize %u leafsize %u "
+              "sectorsize %u bytes %llu\n",
+              label, file, nodesize, leafsize, sectorsize,
               (unsigned long long)block_count);
 
+       free(label);
        root = open_ctree(file, 0);
        trans = btrfs_start_transaction(root, 1);
 
@@ -403,13 +430,12 @@ int main(int ac, char **av)
                        fprintf(stderr, "unable to open %s\n", file);
                        exit(1);
                }
-               fprintf(stderr, "adding device %s\n", file);
                ret = btrfs_prepare_device(fd, file, zero_end,
                                           &dev_block_count);
 
                BUG_ON(ret);
 
-               ret = btrfs_add_to_fsid(trans, root, fd, dev_block_count,
+               ret = btrfs_add_to_fsid(trans, root, fd, file, dev_block_count,
                                        sectorsize, sectorsize, sectorsize);
                BUG_ON(ret);
                btrfs_register_one_device(file);
diff --git a/utils.c b/utils.c
index 0caa708..ba9c7fb 100644 (file)
--- a/utils.c
+++ b/utils.c
@@ -54,7 +54,7 @@ static u64 reference_root_table[6] = {
        [5] =   BTRFS_FS_TREE_OBJECTID,
 };
 
-int make_btrfs(int fd, char *device_name,
+int make_btrfs(int fd, char *device_name, char *label,
               u64 blocks[6], u64 num_bytes, u32 nodesize,
               u32 leafsize, u32 sectorsize, u32 stripesize)
 {
@@ -84,10 +84,11 @@ int make_btrfs(int fd, char *device_name,
        first_free = BTRFS_SUPER_INFO_OFFSET + sectorsize * 2 - 1;
        first_free &= ~((u64)sectorsize - 1);
 
+       memset(&super, 0, sizeof(super));
+
        num_bytes = (num_bytes / sectorsize) * sectorsize;
        uuid_generate(super.fsid);
        uuid_generate(super.dev_item.uuid);
-
        uuid_generate(chunk_tree_uuid);
 
        btrfs_set_super_bytenr(&super, blocks[0]);
@@ -98,14 +99,12 @@ int make_btrfs(int fd, char *device_name,
        btrfs_set_super_chunk_root(&super, blocks[3]);
        btrfs_set_super_total_bytes(&super, num_bytes);
        btrfs_set_super_bytes_used(&super, first_free + 5 * leafsize);
-       btrfs_set_super_root_dir(&super, 0);
        btrfs_set_super_sectorsize(&super, sectorsize);
        btrfs_set_super_leafsize(&super, leafsize);
        btrfs_set_super_nodesize(&super, nodesize);
        btrfs_set_super_stripesize(&super, stripesize);
-       btrfs_set_super_root_level(&super, 0);
-       btrfs_set_super_chunk_root_level(&super, 0);
-       btrfs_set_super_sys_array_size(&super, 0);
+       if (label)
+               strcpy(super.label, label);
 
        buf = malloc(sizeof(*buf) + max(sectorsize, leafsize));
 
@@ -429,8 +428,9 @@ static int zero_dev_end(int fd, u64 dev_size)
 }
 
 int btrfs_add_to_fsid(struct btrfs_trans_handle *trans,
-                     struct btrfs_root *root, int fd, u64 block_count,
-                     u32 io_width, u32 io_align, u32 sectorsize)
+                     struct btrfs_root *root, int fd, char *path,
+                     u64 block_count, u32 io_width, u32 io_align,
+                     u32 sectorsize)
 {
        struct btrfs_super_block *disk_super;
        struct btrfs_super_block *super = &root->fs_info->super_copy;
@@ -478,7 +478,9 @@ int btrfs_add_to_fsid(struct btrfs_trans_handle *trans,
 
        memcpy(disk_super, super, sizeof(*disk_super));
 
-       printf("adding device id %llu\n", (unsigned long long)device->devid);
+       printf("adding device %s id %llu\n", path,
+              (unsigned long long)device->devid);
+
        btrfs_set_stack_device_id(dev_item, device->devid);
        btrfs_set_stack_device_type(dev_item, device->type);
        btrfs_set_stack_device_io_align(dev_item, device->io_align);
diff --git a/utils.h b/utils.h
index 997d134..d03cd07 100644 (file)
--- a/utils.h
+++ b/utils.h
@@ -21,7 +21,7 @@
 
 #define BTRFS_MKFS_SYSTEM_GROUP_SIZE (4 * 1024 * 1024)
 
-int make_btrfs(int fd, char *device_name,
+int make_btrfs(int fd, char *device_name, char *label,
               u64 blocks[6], u64 num_bytes, u32 nodesize,
               u32 leafsize, u32 sectorsize, u32 stripesize);
 int btrfs_make_root_dir(struct btrfs_trans_handle *trans,
@@ -29,8 +29,9 @@ int btrfs_make_root_dir(struct btrfs_trans_handle *trans,
 int btrfs_prepare_device(int fd, char *file, int zero_end,
                         u64 *block_count_ret);
 int btrfs_add_to_fsid(struct btrfs_trans_handle *trans,
-                     struct btrfs_root *root, int fd, u64 block_count,
-                     u32 io_width, u32 io_align, u32 sectorsize);
+                     struct btrfs_root *root, int fd, char *path,
+                     u64 block_count, u32 io_width, u32 io_align,
+                     u32 sectorsize);
 int btrfs_scan_for_fsid(struct btrfs_fs_devices *fs_devices, u64 total_devs,
                        int run_ioctls);
 int btrfs_register_one_device(char *fname);
index a923388..cfe0f34 100644 (file)
--- a/volumes.c
+++ b/volumes.c
@@ -128,7 +128,6 @@ static int device_list_add(const char *path,
        }
        if (fs_devices->lowest_devid > devid) {
                fs_devices->lowest_devid = devid;
-               printk("lowest devid now %llu\n", (unsigned long long)devid);
        }
        *fs_devices_ret = fs_devices;
        return 0;
@@ -184,6 +183,7 @@ int btrfs_scan_one_device(int fd, const char *path,
        char *buf;
        int ret;
        u64 devid;
+       char uuidbuf[37];
 
        buf = malloc(4096);
        if (!buf) {
@@ -203,7 +203,14 @@ int btrfs_scan_one_device(int fd, const char *path,
        }
        devid = le64_to_cpu(disk_super->dev_item.devid);
        *total_devs = btrfs_super_num_devices(disk_super);
-       printk("found device %llu on %s\n", (unsigned long long)devid, path);
+       uuid_unparse(disk_super->fsid, uuidbuf);
+
+       printf("device ");
+       if (disk_super->label[0])
+               printf("label %s ", disk_super->label);
+       else
+               printf("fsuuid %s ", uuidbuf);
+       printf("devid %llu %s\n", (unsigned long long)devid, path);
        ret = device_list_add(path, disk_super, devid, fs_devices_ret);
 
 error_brelse: