bcachefs: More BCH_SB_MEMBER_INVALID support
authorKent Overstreet <kent.overstreet@linux.dev>
Wed, 4 Sep 2024 21:50:20 +0000 (17:50 -0400)
committerKent Overstreet <kent.overstreet@linux.dev>
Mon, 9 Sep 2024 13:41:46 +0000 (09:41 -0400)
Signed-off-by: Kent Overstreet <kent.overstreet@linux.dev>
fs/bcachefs/buckets.c
fs/bcachefs/ec.h
fs/bcachefs/extents.c
fs/bcachefs/replicas.c

index 20219c1e6ddf9a17e739358f382daf2cef55a437..721bbe1dffc11af3f5583741ba25abce3cba31b5 100644 (file)
@@ -100,12 +100,13 @@ static int bch2_check_fix_ptr(struct btree_trans *trans,
 
        struct bch_dev *ca = bch2_dev_tryget(c, p.ptr.dev);
        if (!ca) {
-               if (fsck_err(trans, ptr_to_invalid_device,
-                            "pointer to missing device %u\n"
-                            "while marking %s",
-                            p.ptr.dev,
-                            (printbuf_reset(&buf),
-                             bch2_bkey_val_to_text(&buf, c, k), buf.buf)))
+               if (fsck_err_on(p.ptr.dev != BCH_SB_MEMBER_INVALID,
+                               trans, ptr_to_invalid_device,
+                               "pointer to missing device %u\n"
+                               "while marking %s",
+                               p.ptr.dev,
+                               (printbuf_reset(&buf),
+                                bch2_bkey_val_to_text(&buf, c, k), buf.buf)))
                        *do_update = true;
                return 0;
        }
@@ -562,7 +563,7 @@ static int bch2_trigger_pointer(struct btree_trans *trans,
        struct bch_fs *c = trans->c;
        struct bch_dev *ca = bch2_dev_tryget(c, p.ptr.dev);
        if (unlikely(!ca)) {
-               if (insert)
+               if (insert && p.ptr.dev != BCH_SB_MEMBER_INVALID)
                        ret = -EIO;
                goto err;
        }
index 90962b3c0130572a75e0d333d3ee70c0fb4e29e8..9baf3411a8f94d046a8b47127e79556c64ca4f33 100644 (file)
@@ -97,7 +97,9 @@ static inline bool __bch2_ptr_matches_stripe(const struct bch_extent_ptr *stripe
                                             const struct bch_extent_ptr *data_ptr,
                                             unsigned sectors)
 {
-       return  data_ptr->dev    == stripe_ptr->dev &&
+       return  (data_ptr->dev    == stripe_ptr->dev ||
+                data_ptr->dev    == BCH_SB_MEMBER_INVALID ||
+                stripe_ptr->dev  == BCH_SB_MEMBER_INVALID) &&
                data_ptr->gen    == stripe_ptr->gen &&
                data_ptr->offset >= stripe_ptr->offset &&
                data_ptr->offset  < stripe_ptr->offset + sectors;
index 1a0c714c13e2f3e8b56d910ebb5bcbf3210ad0e0..324303bf4353000753bf70e67519c37a98a7e092 100644 (file)
@@ -787,6 +787,11 @@ void bch2_bkey_drop_ptr_noerror(struct bkey_s k, struct bch_extent_ptr *ptr)
        union bch_extent_entry *entry = to_entry(ptr), *next;
        bool drop_crc = true;
 
+       if (k.k->type == KEY_TYPE_stripe) {
+               ptr->dev = BCH_SB_MEMBER_INVALID;
+               return;
+       }
+
        EBUG_ON(ptr < &ptrs.start->ptr ||
                ptr >= &ptrs.end->ptr);
        EBUG_ON(ptr->type != 1 << BCH_EXTENT_ENTRY_ptr);
index 12d4de65ae17c6516f7e7a2f2bb5143d40b40de6..1f34c92a6d11417f61081522630655f975d69571 100644 (file)
@@ -796,7 +796,7 @@ bool bch2_have_enough_devs(struct bch_fs *c, struct bch_devs_mask devs,
                        nr_online += test_bit(e->devs[i], devs.d);
 
                        struct bch_dev *ca = bch2_dev_rcu(c, e->devs[i]);
-                       nr_failed += ca && ca->mi.state == BCH_MEMBER_STATE_failed;
+                       nr_failed += !ca || ca->mi.state == BCH_MEMBER_STATE_failed;
                }
                rcu_read_unlock();