Btrfs: Move device information into the super block so it can be scanned

Signed-off-by: Chris Mason <chris.mason@oracle.com>
diff --git a/fs/btrfs/ctree.h b/fs/btrfs/ctree.h
index 285fb7e..96a4932 100644
--- a/fs/btrfs/ctree.h
+++ b/fs/btrfs/ctree.h
@@ -150,21 +150,11 @@
 	/* minimal io size for this device */
 	__le32 sector_size;
 
-	/* the kernel device number */
-	__le64 rdev;
-
 	/* type and info about this device */
 	__le64 type;
 
-	/* partition number, 0 for whole dev */
-	__le32 partition;
-
-	/* length of the name data at the end of the item */
-	__le16 name_len;
-
-	/* physical drive uuid (or lvm uuid) */
+	/* btrfs generated uuid for this device */
 	u8 uuid[BTRFS_DEV_UUID_SIZE];
-	/* name goes here */
 } __attribute__ ((__packed__));
 
 struct btrfs_stripe {
@@ -255,6 +245,7 @@
 	__le32 sys_chunk_array_size;
 	u8 root_level;
 	u8 chunk_root_level;
+	struct btrfs_dev_item dev_item;
 	u8 sys_chunk_array[BTRFS_SYSTEM_CHUNK_ARRAY_SIZE];
 } __attribute__ ((__packed__));
 
@@ -685,20 +676,12 @@
 BTRFS_SETGET_FUNCS(device_io_width, struct btrfs_dev_item, io_width, 32);
 BTRFS_SETGET_FUNCS(device_sector_size, struct btrfs_dev_item, sector_size, 32);
 BTRFS_SETGET_FUNCS(device_id, struct btrfs_dev_item, devid, 64);
-BTRFS_SETGET_FUNCS(device_rdev, struct btrfs_dev_item, rdev, 64);
-BTRFS_SETGET_FUNCS(device_partition, struct btrfs_dev_item, partition, 32);
-BTRFS_SETGET_FUNCS(device_name_len, struct btrfs_dev_item, name_len, 16);
 
 static inline char *btrfs_device_uuid(struct btrfs_dev_item *d)
 {
 	return (char *)d + offsetof(struct btrfs_dev_item, uuid);
 }
 
-static inline char *btrfs_device_name(struct btrfs_dev_item *d)
-{
-	return (char *)(d + 1);
-}
-
 BTRFS_SETGET_FUNCS(chunk_owner, struct btrfs_chunk, owner, 64);
 BTRFS_SETGET_FUNCS(chunk_stripe_len, struct btrfs_chunk, stripe_len, 64);
 BTRFS_SETGET_FUNCS(chunk_io_align, struct btrfs_chunk, io_align, 32);
diff --git a/fs/btrfs/disk-io.c b/fs/btrfs/disk-io.c
index 2a239ae..26185d4 100644
--- a/fs/btrfs/disk-io.c
+++ b/fs/btrfs/disk-io.c
@@ -370,7 +370,6 @@
 		next = list->next;
 		list_del(next);
 		device = list_entry(next, struct btrfs_device, dev_list);
-		kfree(device->name);
 		kfree(device);
 	}
 	return 0;
@@ -800,6 +799,9 @@
 	}
 
 	mutex_lock(&fs_info->fs_mutex);
+	ret = btrfs_read_super_device(tree_root, fs_info->sb_buffer);
+	BUG_ON(ret);
+
 	ret = btrfs_read_sys_array(tree_root);
 	BUG_ON(ret);
 
diff --git a/fs/btrfs/print-tree.c b/fs/btrfs/print-tree.c
index 9c1335d..ee0de11 100644
--- a/fs/btrfs/print-tree.c
+++ b/fs/btrfs/print-tree.c
@@ -37,22 +37,11 @@
 static void print_dev_item(struct extent_buffer *eb,
 			   struct btrfs_dev_item *dev_item)
 {
-	char *name;
-	int name_len;
-
-	name_len = btrfs_device_name_len(eb, dev_item);
-	name = kmalloc(name_len, GFP_NOFS);
-	if (name) {
-		read_extent_buffer(eb, name,
-				   (unsigned long)btrfs_device_name(dev_item),
-				   name_len);
-	}
-	printk("\t\tdev item name %.*s devid %llu "
-	       "total_bytes %llu bytes used %Lu\n", name_len, name,
+	printk("\t\tdev item devid %llu "
+	       "total_bytes %llu bytes used %Lu\n",
 	       (unsigned long long)btrfs_device_id(eb, dev_item),
 	       (unsigned long long)btrfs_device_total_bytes(eb, dev_item),
 	       (unsigned long long)btrfs_device_bytes_used(eb, dev_item));
-	kfree(name);
 }
 void btrfs_print_leaf(struct btrfs_root *root, struct extent_buffer *l)
 {
diff --git a/fs/btrfs/volumes.c b/fs/btrfs/volumes.c
index a52a13f..ae22d01 100644
--- a/fs/btrfs/volumes.c
+++ b/fs/btrfs/volumes.c
@@ -278,7 +278,7 @@
 	key.offset = free_devid;
 
 	ret = btrfs_insert_empty_item(trans, root, path, &key,
-				      sizeof(*dev_item) + device->name_len);
+				      sizeof(*dev_item));
 	if (ret)
 		goto out;
 
@@ -290,15 +290,9 @@
 	btrfs_set_device_io_align(leaf, dev_item, device->io_align);
 	btrfs_set_device_io_width(leaf, dev_item, device->io_width);
 	btrfs_set_device_sector_size(leaf, dev_item, device->sector_size);
-	btrfs_set_device_rdev(leaf, dev_item, device->rdev);
-	btrfs_set_device_partition(leaf, dev_item, device->partition);
-	btrfs_set_device_name_len(leaf, dev_item, device->name_len);
 	btrfs_set_device_total_bytes(leaf, dev_item, device->total_bytes);
 	btrfs_set_device_bytes_used(leaf, dev_item, device->bytes_used);
 
-	ptr = (unsigned long)btrfs_device_name(dev_item);
-	write_extent_buffer(leaf, device->name, ptr, device->name_len);
-
 	ptr = (unsigned long)btrfs_device_uuid(dev_item);
 	write_extent_buffer(leaf, device->uuid, ptr, BTRFS_DEV_UUID_SIZE);
 	btrfs_mark_buffer_dirty(leaf);
@@ -345,8 +339,6 @@
 	btrfs_set_device_io_align(leaf, dev_item, device->io_align);
 	btrfs_set_device_io_width(leaf, dev_item, device->io_width);
 	btrfs_set_device_sector_size(leaf, dev_item, device->sector_size);
-	btrfs_set_device_rdev(leaf, dev_item, device->rdev);
-	btrfs_set_device_partition(leaf, dev_item, device->partition);
 	btrfs_set_device_total_bytes(leaf, dev_item, device->total_bytes);
 	btrfs_set_device_bytes_used(leaf, dev_item, device->bytes_used);
 	btrfs_mark_buffer_dirty(leaf);
@@ -676,7 +668,6 @@
 				 struct btrfs_device *device)
 {
 	unsigned long ptr;
-	char *name;
 
 	device->devid = btrfs_device_id(leaf, dev_item);
 	device->total_bytes = btrfs_device_total_bytes(leaf, dev_item);
@@ -685,24 +676,14 @@
 	device->io_align = btrfs_device_io_align(leaf, dev_item);
 	device->io_width = btrfs_device_io_width(leaf, dev_item);
 	device->sector_size = btrfs_device_sector_size(leaf, dev_item);
-	device->rdev = btrfs_device_rdev(leaf, dev_item);
-	device->partition = btrfs_device_partition(leaf, dev_item);
-	device->name_len = btrfs_device_name_len(leaf, dev_item);
 
 	ptr = (unsigned long)btrfs_device_uuid(dev_item);
 	read_extent_buffer(leaf, device->uuid, ptr, BTRFS_DEV_UUID_SIZE);
 
-	name = kmalloc(device->name_len + 1, GFP_NOFS);
-	if (!name)
-		return -ENOMEM;
-	device->name = name;
-	ptr = (unsigned long)btrfs_device_name(dev_item);
-	read_extent_buffer(leaf, name, ptr, device->name_len);
-	name[device->name_len] = '\0';
 	return 0;
 }
 
-static int read_one_dev(struct btrfs_root *root, struct btrfs_key *key,
+static int read_one_dev(struct btrfs_root *root,
 			struct extent_buffer *leaf,
 			struct btrfs_dev_item *dev_item)
 {
@@ -722,7 +703,6 @@
 	fill_device_from_item(leaf, dev_item, device);
 	device->dev_root = root->fs_info->dev_root;
 	device->bdev = root->fs_info->sb->s_bdev;
-	memcpy(&device->dev_key, key, sizeof(*key));
 	ret = 0;
 #if 0
 	ret = btrfs_open_device(device);
@@ -733,12 +713,20 @@
 	return ret;
 }
 
+int btrfs_read_super_device(struct btrfs_root *root, struct extent_buffer *buf)
+{
+	struct btrfs_dev_item *dev_item;
+
+	dev_item = (struct btrfs_dev_item *)offsetof(struct btrfs_super_block,
+						     dev_item);
+	return read_one_dev(root, buf, dev_item);
+}
+
 int btrfs_read_sys_array(struct btrfs_root *root)
 {
 	struct btrfs_super_block *super_copy = &root->fs_info->super_copy;
 	struct extent_buffer *sb = root->fs_info->sb_buffer;
 	struct btrfs_disk_key *disk_key;
-	struct btrfs_dev_item *dev_item;
 	struct btrfs_chunk *chunk;
 	struct btrfs_key key;
 	u32 num_stripes;
@@ -748,7 +736,6 @@
 	unsigned long sb_ptr;
 	u32 cur;
 	int ret;
-	int dev_only = 1;
 
 	array_size = btrfs_super_sys_array_size(super_copy);
 
@@ -757,7 +744,6 @@
 	 * once for all of the chunks.  This way there are device
 	 * structs filled in for every chunk
 	 */
-again:
 	ptr = super_copy->sys_chunk_array;
 	sb_ptr = offsetof(struct btrfs_super_block, sys_chunk_array);
 	cur = 0;
@@ -771,22 +757,10 @@
 		sb_ptr += len;
 		cur += len;
 
-		if (key.objectid == BTRFS_DEV_ITEMS_OBJECTID &&
-		    key.type == BTRFS_DEV_ITEM_KEY) {
-			dev_item = (struct btrfs_dev_item *)sb_ptr;
-			if (dev_only) {
-				ret = read_one_dev(root, &key, sb, dev_item);
-				BUG_ON(ret);
-			}
-			len = sizeof(*dev_item);
-			len += btrfs_device_name_len(sb, dev_item);
-		} else if (key.type == BTRFS_CHUNK_ITEM_KEY) {
-
+		if (key.type == BTRFS_CHUNK_ITEM_KEY) {
 			chunk = (struct btrfs_chunk *)sb_ptr;
-			if (!dev_only) {
-				ret = read_one_chunk(root, &key, sb, chunk);
-				BUG_ON(ret);
-			}
+			ret = read_one_chunk(root, &key, sb, chunk);
+			BUG_ON(ret);
 			num_stripes = btrfs_chunk_num_stripes(sb, chunk);
 			len = btrfs_chunk_item_size(num_stripes);
 		} else {
@@ -796,10 +770,6 @@
 		sb_ptr += len;
 		cur += len;
 	}
-	if (dev_only == 1) {
-		dev_only = 0;
-		goto again;
-	}
 	return 0;
 }
 
@@ -846,8 +816,7 @@
 				struct btrfs_dev_item *dev_item;
 				dev_item = btrfs_item_ptr(leaf, slot,
 						  struct btrfs_dev_item);
-				ret = read_one_dev(root, &found_key, leaf,
-						   dev_item);
+				ret = read_one_dev(root, leaf, dev_item);
 				BUG_ON(ret);
 			}
 		} else if (found_key.type == BTRFS_CHUNK_ITEM_KEY) {
diff --git a/fs/btrfs/volumes.h b/fs/btrfs/volumes.h
index 4ab9891..77fa6ef 100644
--- a/fs/btrfs/volumes.h
+++ b/fs/btrfs/volumes.h
@@ -21,7 +21,6 @@
 struct btrfs_device {
 	struct list_head dev_list;
 	struct btrfs_root *dev_root;
-	struct btrfs_key dev_key;
 
 	struct block_device *bdev;
 
@@ -43,22 +42,11 @@
 	/* minimal io size for this device */
 	u32 sector_size;
 
-	/* the kernel device number */
-	u64 rdev;
-
 	/* type and info about this device */
 	u64 type;
 
-	/* partition number, 0 for whole dev */
-	int partition;
-
-	/* length of the name data at the end of the item */
-	int name_len;
-
 	/* physical drive uuid (or lvm uuid) */
 	u8 uuid[BTRFS_DEV_UUID_SIZE];
-
-	char *name;
 };
 
 int btrfs_alloc_dev_extent(struct btrfs_trans_handle *trans,
@@ -75,4 +63,5 @@
 void btrfs_mapping_init(struct btrfs_mapping_tree *tree);
 void btrfs_mapping_tree_free(struct btrfs_mapping_tree *tree);
 int btrfs_map_bio(struct btrfs_root *root, int rw, struct bio *bio);
+int btrfs_read_super_device(struct btrfs_root *root, struct extent_buffer *buf);
 #endif