From b8435c569398fbc8a4a209dcd55cb660b6577d3d Mon Sep 17 00:00:00 2001 From: Kent Overstreet <kent.overstreet@linux.dev> Date: Sun, 23 Mar 2025 11:03:42 -0400 Subject: [PATCH] bch2_format() now takes a darray of dev_opts Signed-off-by: Kent Overstreet <kent.overstreet@linux.dev> --- c_src/cmd_device.c | 9 +++---- c_src/cmd_format.c | 10 +++----- c_src/cmd_migrate.c | 7 ++++-- c_src/libbcachefs.c | 58 +++++++++++++++++++-------------------------- c_src/libbcachefs.h | 5 +++- 5 files changed, 42 insertions(+), 47 deletions(-) diff --git a/c_src/cmd_device.c b/c_src/cmd_device.c index a1e78e25..d953055c 100644 --- a/c_src/cmd_device.c +++ b/c_src/cmd_device.c @@ -137,10 +137,11 @@ int cmd_device_add(int argc, char *argv[]) opt_set(fs_opts, btree_node_size, read_file_u64(fs.sysfs_fd, "options/btree_node_size")); - struct bch_sb *sb = bch2_format(fs_opt_strs, - fs_opts, - format_opts, - &dev_opts, 1); + dev_opts_list devs = {}; + darray_push(&devs, dev_opts); + + struct bch_sb *sb = bch2_format(fs_opt_strs, fs_opts, format_opts, devs); + darray_exit(&devs); free(sb); bchu_disk_add(fs, dev_opts.path); return 0; diff --git a/c_src/cmd_format.c b/c_src/cmd_format.c index 4fbf3a4b..7c0d1920 100644 --- a/c_src/cmd_format.c +++ b/c_src/cmd_format.c @@ -126,8 +126,8 @@ void build_fs(struct bch_fs *c, const char *src_path) int cmd_format(int argc, char *argv[]) { - DARRAY(struct dev_opts) devices = { 0 }; - DARRAY(char *) device_paths = { 0 }; + dev_opts_list devices = {}; + darray_str device_paths = {}; struct format_opts opts = format_opts_default(); struct dev_opts dev_opts = dev_opts_default(); bool force = false, no_passphrase = false, quiet = false, initialize = true, verbose = false; @@ -277,11 +277,7 @@ int cmd_format(int argc, char *argv[]) die("Error opening %s: %s", dev_opts.path, strerror(-ret)); } - struct bch_sb *sb = - bch2_format(fs_opt_strs, - fs_opts, - opts, - devices.data, devices.nr); + struct bch_sb *sb = bch2_format(fs_opt_strs, fs_opts, opts, devices); bch2_opt_strs_free(&fs_opt_strs); if (!quiet) { diff --git a/c_src/cmd_migrate.c b/c_src/cmd_migrate.c index 698cfd55..109416a8 100644 --- a/c_src/cmd_migrate.c +++ b/c_src/cmd_migrate.c @@ -239,8 +239,11 @@ static int migrate_fs(const char *fs_path, find_superblock_space(extents, format_opts, &dev); - struct bch_sb *sb = bch2_format(fs_opt_strs, - fs_opts, format_opts, &dev, 1); + dev_opts_list devs = {}; + darray_push(&devs, dev); + struct bch_sb *sb = bch2_format(fs_opt_strs, fs_opts, format_opts, devs); + darray_exit(&devs); + u64 sb_offset = le64_to_cpu(sb->layout.sb_offset[0]); if (format_opts.passphrase) diff --git a/c_src/libbcachefs.c b/c_src/libbcachefs.c index d212b6ef..50ac96a8 100644 --- a/c_src/libbcachefs.c +++ b/c_src/libbcachefs.c @@ -116,20 +116,17 @@ void bch2_check_bucket_size(struct bch_opts opts, struct dev_opts *dev) } static unsigned parse_target(struct bch_sb_handle *sb, - struct dev_opts *devs, size_t nr_devs, + dev_opts_list devs, const char *s) { - struct dev_opts *i; - int idx; - if (!s) return 0; - for (i = devs; i < devs + nr_devs; i++) + darray_for_each(devs, i) if (!strcmp(s, i->path)) - return dev_to_target(i - devs); + return dev_to_target(i - devs.data); - idx = bch2_disk_path_find(sb, s); + int idx = bch2_disk_path_find(sb, s); if (idx >= 0) return group_to_target(idx); @@ -151,15 +148,13 @@ static void bch2_opt_set_sb_all(struct bch_sb *sb, int dev_idx, struct bch_opts struct bch_sb *bch2_format(struct bch_opt_strs fs_opt_strs, struct bch_opts fs_opts, struct format_opts opts, - struct dev_opts *devs, - size_t nr_devs) + dev_opts_list devs) { struct bch_sb_handle sb = { NULL }; - struct dev_opts *i; unsigned max_dev_block_size = 0; u64 min_bucket_size = U64_MAX; - for (i = devs; i < devs + nr_devs; i++) + darray_for_each(devs, i) max_dev_block_size = max(max_dev_block_size, get_blocksize(i->bdev->bd_fd)); /* calculate block size: */ @@ -171,20 +166,20 @@ struct bch_sb *bch2_format(struct bch_opt_strs fs_opt_strs, fs_opts.block_size, max_dev_block_size); /* get device size, if it wasn't specified: */ - for (i = devs; i < devs + nr_devs; i++) + darray_for_each(devs, i) if (!opt_defined(i->opts, fs_size)) opt_set(i->opts, fs_size, get_size(i->bdev->bd_fd)); /* calculate bucket sizes: */ - for (i = devs; i < devs + nr_devs; i++) + darray_for_each(devs, i) min_bucket_size = min(min_bucket_size, i->opts.bucket_size ?: bch2_pick_bucket_size(fs_opts, i)); - for (i = devs; i < devs + nr_devs; i++) + darray_for_each(devs, i) if (!opt_defined(i->opts, bucket_size)) opt_set(i->opts, bucket_size, min_bucket_size); - for (i = devs; i < devs + nr_devs; i++) { + darray_for_each(devs, i) { i->nbuckets = i->opts.fs_size / i->opts.bucket_size; bch2_check_bucket_size(fs_opts, i); } @@ -193,7 +188,7 @@ struct bch_sb *bch2_format(struct bch_opt_strs fs_opt_strs, if (!opt_defined(fs_opts, btree_node_size)) { unsigned s = bch2_opts_default.btree_node_size; - for (i = devs; i < devs + nr_devs; i++) + darray_for_each(devs, i) s = min(s, i->opts.bucket_size); opt_set(fs_opts, btree_node_size, s); } @@ -208,7 +203,7 @@ struct bch_sb *bch2_format(struct bch_opt_strs fs_opt_strs, sb.sb->version_min = le16_to_cpu(opts.version); sb.sb->magic = BCHFS_MAGIC; sb.sb->user_uuid = opts.uuid; - sb.sb->nr_devices = nr_devs; + sb.sb->nr_devices = devs.nr; SET_BCH_SB_VERSION_INCOMPAT_ALLOWED(sb.sb, opts.version); if (opts.version == bcachefs_metadata_version_current) @@ -233,11 +228,11 @@ struct bch_sb *bch2_format(struct bch_opt_strs fs_opt_strs, /* Member info: */ struct bch_sb_field_members_v2 *mi = bch2_sb_field_resize(&sb, members_v2, - (sizeof(*mi) + sizeof(struct bch_member) * - nr_devs) / sizeof(u64)); + (sizeof(*mi) + sizeof(struct bch_member) * devs.nr) / sizeof(u64)); + mi->member_bytes = cpu_to_le16(sizeof(struct bch_member)); - for (i = devs; i < devs + nr_devs; i++) { - unsigned idx = i - devs; + darray_for_each(devs, i) { + unsigned idx = i - devs.data; struct bch_member *m = bch2_members_v2_get_mut(sb.sb, idx); uuid_generate(m->uuid.b); @@ -247,14 +242,11 @@ struct bch_sb *bch2_format(struct bch_opt_strs fs_opt_strs, } /* Disk labels*/ - for (i = devs; i < devs + nr_devs; i++) { - struct bch_member *m; - int idx; - + darray_for_each(devs, i) { if (!i->label) continue; - idx = bch2_disk_path_find_or_create(&sb, i->label); + int idx = bch2_disk_path_find_or_create(&sb, i->label); if (idx < 0) die("error creating disk path: %s", strerror(-idx)); @@ -262,18 +254,18 @@ struct bch_sb *bch2_format(struct bch_opt_strs fs_opt_strs, * Recompute mi and m after each sb modification: its location * in memory may have changed due to reallocation. */ - m = bch2_members_v2_get_mut(sb.sb, (i - devs)); + struct bch_member *m = bch2_members_v2_get_mut(sb.sb, (i - devs.data)); SET_BCH_MEMBER_GROUP(m, idx + 1); } SET_BCH_SB_FOREGROUND_TARGET(sb.sb, - parse_target(&sb, devs, nr_devs, fs_opt_strs.foreground_target)); + parse_target(&sb, devs, fs_opt_strs.foreground_target)); SET_BCH_SB_BACKGROUND_TARGET(sb.sb, - parse_target(&sb, devs, nr_devs, fs_opt_strs.background_target)); + parse_target(&sb, devs, fs_opt_strs.background_target)); SET_BCH_SB_PROMOTE_TARGET(sb.sb, - parse_target(&sb, devs, nr_devs, fs_opt_strs.promote_target)); + parse_target(&sb, devs, fs_opt_strs.promote_target)); SET_BCH_SB_METADATA_TARGET(sb.sb, - parse_target(&sb, devs, nr_devs, fs_opt_strs.metadata_target)); + parse_target(&sb, devs, fs_opt_strs.metadata_target)); /* Crypt: */ if (opts.encrypted) { @@ -286,10 +278,10 @@ struct bch_sb *bch2_format(struct bch_opt_strs fs_opt_strs, bch2_sb_members_cpy_v2_v1(&sb); - for (i = devs; i < devs + nr_devs; i++) { + darray_for_each(devs, i) { u64 size_sectors = i->opts.fs_size >> 9; - sb.sb->dev_idx = i - devs; + sb.sb->dev_idx = i - devs.data; if (!i->sb_offset) { i->sb_offset = BCH_SB_SECTOR; diff --git a/c_src/libbcachefs.h b/c_src/libbcachefs.h index 05ba1069..4185cebb 100644 --- a/c_src/libbcachefs.h +++ b/c_src/libbcachefs.h @@ -83,9 +83,12 @@ void bch2_sb_layout_init(struct bch_sb_layout *, u64 bch2_pick_bucket_size(struct bch_opts, struct dev_opts *); void bch2_check_bucket_size(struct bch_opts, struct dev_opts *); +typedef DARRAY(struct dev_opts) dev_opts_list; + struct bch_sb *bch2_format(struct bch_opt_strs, struct bch_opts, - struct format_opts, struct dev_opts *, size_t); + struct format_opts, + dev_opts_list devs); void bch2_super_write(int, struct bch_sb *); struct bch_sb *__bch2_super_read(int, u64);