X-Git-Url: https://git.sesse.net/?a=blobdiff_plain;f=cmd_migrate.c;h=08ec7de28004df6eca81c97b7fd933c9b502a434;hb=e240b4ae86adb022e3266220ce9807dad8b51beb;hp=0beebc9cf81dcc4a62079c4e9c984c99912e1e6b;hpb=9e5d774875df1605c23f38f1da6c9dbb49826471;p=bcachefs-tools-debian diff --git a/cmd_migrate.c b/cmd_migrate.c index 0beebc9..08ec7de 100644 --- a/cmd_migrate.c +++ b/cmd_migrate.c @@ -123,6 +123,7 @@ static void update_inode(struct bch_fs *c, int ret; bch2_inode_pack(c, &packed, inode); + packed.inode.k.p.snapshot = U32_MAX; ret = bch2_btree_insert(c, BTREE_ID_inodes, &packed.inode.k_i, NULL, NULL, 0); if (ret) @@ -138,8 +139,9 @@ static void create_link(struct bch_fs *c, struct bch_inode_unpacked inode; int ret = bch2_trans_do(c, NULL, NULL, 0, - bch2_link_trans(&trans, parent->bi_inum, inum, - &parent_u, &inode, &qstr)); + bch2_link_trans(&trans, + (subvol_inum) { 1, parent->bi_inum }, &parent_u, + (subvol_inum) { 1, inum }, &inode, &qstr)); if (ret) die("error creating hardlink: %s", strerror(-ret)); } @@ -153,13 +155,16 @@ static struct bch_inode_unpacked create_file(struct bch_fs *c, struct qstr qstr = QSTR(name); struct bch_inode_unpacked new_inode; + bch2_inode_init_early(c, &new_inode); + int ret = bch2_trans_do(c, NULL, NULL, 0, bch2_create_trans(&trans, - parent->bi_inum, parent, + (subvol_inum) { 1, parent->bi_inum }, parent, &new_inode, &qstr, - uid, gid, mode, rdev, NULL, NULL)); + uid, gid, mode, rdev, NULL, NULL, + (subvol_inum) {}, 0)); if (ret) - die("error creating file: %s", strerror(-ret)); + die("error creating %s: %s", name, strerror(-ret)); return new_inode; } @@ -225,44 +230,48 @@ static void copy_xattrs(struct bch_fs *c, struct bch_inode_unpacked *dst, const struct xattr_handler *h = xattr_resolve_name(&attr); int ret = bch2_trans_do(c, NULL, NULL, 0, - bch2_xattr_set(&trans, dst->bi_inum, &hash_info, attr, + bch2_xattr_set(&trans, + (subvol_inum) { 1, dst->bi_inum }, + &hash_info, attr, val, val_size, h->flags, 0)); if (ret < 0) die("error creating xattr: %s", strerror(-ret)); } } -static char buf[1 << 20] __aligned(PAGE_SIZE); +#define WRITE_DATA_BUF (1 << 20) + +static char buf[WRITE_DATA_BUF] __aligned(PAGE_SIZE); static void write_data(struct bch_fs *c, struct bch_inode_unpacked *dst_inode, u64 dst_offset, void *buf, size_t len) { - struct { - struct bch_write_op op; - struct bio_vec bv[sizeof(buf) / PAGE_SIZE]; - } o; + struct bch_write_op op; + struct bio_vec bv[WRITE_DATA_BUF / PAGE_SIZE]; struct closure cl; BUG_ON(dst_offset & (block_bytes(c) - 1)); BUG_ON(len & (block_bytes(c) - 1)); + BUG_ON(len > WRITE_DATA_BUF); closure_init_stack(&cl); - bio_init(&o.op.wbio.bio, o.bv, ARRAY_SIZE(o.bv)); - bch2_bio_map(&o.op.wbio.bio, buf, len); + bio_init(&op.wbio.bio, bv, ARRAY_SIZE(bv)); + bch2_bio_map(&op.wbio.bio, buf, len); - bch2_write_op_init(&o.op, c, bch2_opts_to_inode_opts(c->opts)); - o.op.write_point = writepoint_hashed(0); - o.op.nr_replicas = 1; - o.op.pos = POS(dst_inode->bi_inum, dst_offset >> 9); + bch2_write_op_init(&op, c, bch2_opts_to_inode_opts(c->opts)); + op.write_point = writepoint_hashed(0); + op.nr_replicas = 1; + op.subvol = 1; + op.pos = SPOS(dst_inode->bi_inum, dst_offset >> 9, U32_MAX); - int ret = bch2_disk_reservation_get(c, &o.op.res, len >> 9, + int ret = bch2_disk_reservation_get(c, &op.res, len >> 9, c->opts.data_replicas, 0); if (ret) die("error reserving space in new filesystem: %s", strerror(-ret)); - closure_call(&o.op.cl, bch2_write, NULL, &cl); + closure_call(&op.cl, bch2_write, NULL, &cl); closure_sync(&cl); dst_inode->bi_sectors += len >> 9; @@ -314,11 +323,12 @@ static void link_data(struct bch_fs *c, struct bch_inode_unpacked *dst, e = bkey_extent_init(&k.k); e->k.p.inode = dst->bi_inum; e->k.p.offset = logical + sectors; + e->k.p.snapshot = U32_MAX; e->k.size = sectors; bch2_bkey_append_ptr(&e->k_i, (struct bch_extent_ptr) { .offset = physical, .dev = 0, - .gen = bucket(ca, b)->mark.gen, + .gen = *bucket_gen(ca, b), }); ret = bch2_disk_reservation_get(c, &res, sectors, 1, @@ -327,8 +337,6 @@ static void link_data(struct bch_fs *c, struct bch_inode_unpacked *dst, die("error reserving space in new filesystem: %s", strerror(-ret)); - bch2_mark_bkey_replicas(c, extent_i_to_s_c(e).s_c); - ret = bch2_btree_insert(c, BTREE_ID_extents, &e->k_i, &res, NULL, 0); if (ret) @@ -428,6 +436,7 @@ static void copy_dir(struct copy_fs_state *s, if (!strcmp(d->d_name, ".") || !strcmp(d->d_name, "..") || + !strcmp(d->d_name, "lost+found") || stat.st_ino == s->bcachefs_inum) continue; @@ -521,7 +530,7 @@ static ranges reserve_new_fs_space(const char *file_path, unsigned block_size, struct fiemap_iter iter; struct fiemap_extent e; - ranges extents = { NULL }; + ranges extents = { 0 }; fiemap_for_each(fd, iter, e) { if (e.fe_flags & (FIEMAP_EXTENT_UNKNOWN| @@ -569,7 +578,8 @@ static void copy_fs(struct bch_fs *c, int src_fd, const char *src_path, syncfs(src_fd); struct bch_inode_unpacked root_inode; - int ret = bch2_inode_find_by_inum(c, BCACHEFS_ROOT_INO, &root_inode); + int ret = bch2_inode_find_by_inum(c, (subvol_inum) { 1, BCACHEFS_ROOT_INO }, + &root_inode); if (ret) die("error looking up root directory: %s", strerror(-ret)); @@ -593,25 +603,26 @@ static void copy_fs(struct bch_fs *c, int src_fd, const char *src_path, update_inode(c, &root_inode); - darray_free(s.extents); + darray_exit(s.extents); genradix_free(&s.hardlinks); - - bch2_alloc_write(c, false); } -static void find_superblock_space(ranges extents, struct dev_opts *dev) +static void find_superblock_space(ranges extents, + struct format_opts opts, + struct dev_opts *dev) { struct range *i; - darray_foreach(i, extents) { + darray_for_each(extents, i) { u64 start = round_up(max(256ULL << 10, i->start), dev->bucket_size << 9); u64 end = round_down(i->end, dev->bucket_size << 9); - if (start + (128 << 10) <= end) { + /* Need space for two superblocks: */ + if (start + (opts.superblock_size << 9) * 2 <= end) { dev->sb_offset = start >> 9; - dev->sb_end = dev->sb_offset + 256; + dev->sb_end = dev->sb_offset + opts.superblock_size * 2; return; } } @@ -669,11 +680,11 @@ static int migrate_fs(const char *fs_path, u64 bcachefs_inum; ranges extents = reserve_new_fs_space(file_path, - fs_opts.block_size << 9, + fs_opts.block_size >> 9, get_size(dev.path, dev.fd) / 5, &bcachefs_inum, stat.st_dev, force); - find_superblock_space(extents, &dev); + find_superblock_space(extents, format_opts, &dev); struct bch_sb *sb = bch2_format(fs_opt_strs, fs_opts,format_opts, &dev, 1); @@ -691,6 +702,7 @@ static int migrate_fs(const char *fs_path, opt_set(opts, sb, sb_offset); opt_set(opts, nostart, true); opt_set(opts, noexcl, true); + opt_set(opts, buckets_nouse, true); c = bch2_fs_open(path, 1, opts); if (IS_ERR(c)) @@ -770,10 +782,12 @@ int cmd_migrate(int argc, char *argv[]) if (format_opts.encrypted && !no_passphrase) format_opts.passphrase = read_passphrase_twice("Enter passphrase: "); - return migrate_fs(fs_path, - fs_opt_strs, - fs_opts, - format_opts, force); + int ret = migrate_fs(fs_path, + fs_opt_strs, + fs_opts, + format_opts, force); + bch2_opt_strs_free(&fs_opt_strs); + return ret; } static void migrate_superblock_usage(void)