Skip to content

Commit c986dd7

Browse files
author
Kent Overstreet
committed
bcachefs: Improve check_snapshot_exists()
Check if we have snapshot_trees or subvolumes that refer to the snapshot node being reconstructed, and use them. With this, the kill_btree_root test that blows away the snapshots btree now passes, and we're able to successfully reconstruct. Signed-off-by: Kent Overstreet <[email protected]>
1 parent 9183c2b commit c986dd7

File tree

1 file changed

+30
-2
lines changed

1 file changed

+30
-2
lines changed

fs/bcachefs/snapshot.c

Lines changed: 30 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -905,12 +905,30 @@ static int check_snapshot_exists(struct btree_trans *trans, u32 id)
905905
if (bch2_snapshot_equiv(c, id))
906906
return 0;
907907

908-
/* 0 is an invalid tree ID */
908+
/* Do we need to reconstruct the snapshot_tree entry as well? */
909+
struct btree_iter iter;
910+
struct bkey_s_c k;
911+
int ret = 0;
909912
u32 tree_id = 0;
910-
int ret = bch2_snapshot_tree_create(trans, id, 0, &tree_id);
913+
914+
for_each_btree_key_norestart(trans, iter, BTREE_ID_snapshot_trees, POS_MIN,
915+
0, k, ret) {
916+
if (le32_to_cpu(bkey_s_c_to_snapshot_tree(k).v->root_snapshot) == id) {
917+
tree_id = k.k->p.offset;
918+
break;
919+
}
920+
}
921+
bch2_trans_iter_exit(trans, &iter);
922+
911923
if (ret)
912924
return ret;
913925

926+
if (!tree_id) {
927+
ret = bch2_snapshot_tree_create(trans, id, 0, &tree_id);
928+
if (ret)
929+
return ret;
930+
}
931+
914932
struct bkey_i_snapshot *snapshot = bch2_trans_kmalloc(trans, sizeof(*snapshot));
915933
ret = PTR_ERR_OR_ZERO(snapshot);
916934
if (ret)
@@ -921,6 +939,16 @@ static int check_snapshot_exists(struct btree_trans *trans, u32 id)
921939
snapshot->v.tree = cpu_to_le32(tree_id);
922940
snapshot->v.btime.lo = cpu_to_le64(bch2_current_time(c));
923941

942+
for_each_btree_key_norestart(trans, iter, BTREE_ID_subvolumes, POS_MIN,
943+
0, k, ret) {
944+
if (le32_to_cpu(bkey_s_c_to_subvolume(k).v->snapshot) == id) {
945+
snapshot->v.subvol = cpu_to_le32(k.k->p.offset);
946+
SET_BCH_SNAPSHOT_SUBVOL(&snapshot->v, true);
947+
break;
948+
}
949+
}
950+
bch2_trans_iter_exit(trans, &iter);
951+
924952
return bch2_btree_insert_trans(trans, BTREE_ID_snapshots, &snapshot->k_i, 0) ?:
925953
bch2_mark_snapshot(trans, BTREE_ID_snapshots, 0,
926954
bkey_s_c_null, bkey_i_to_s(&snapshot->k_i), 0) ?:

0 commit comments

Comments
 (0)