]> www.infradead.org Git - users/hch/misc.git/commitdiff
md: add a new mddev field 'bitmap_id'
authorYu Kuai <yukuai3@huawei.com>
Fri, 29 Aug 2025 08:04:19 +0000 (16:04 +0800)
committerYu Kuai <yukuai3@huawei.com>
Sat, 6 Sep 2025 09:18:48 +0000 (17:18 +0800)
Prepare to store the bitmap id selected by user, also refactor
mddev_set_bitmap_ops a bit in case the value is invalid.

Link: https://lore.kernel.org/linux-raid/20250829080426.1441678-5-yukuai1@huaweicloud.com
Signed-off-by: Yu Kuai <yukuai3@huawei.com>
Reviewed-by: Hannes Reinecke <hare@suse.de>
Reviewed-by: Li Nan <linan122@huawei.com>
Reviewed-by: Xiao Ni <xni@redhat.com>
drivers/md/md.c
drivers/md/md.h

index 8a89dca8209c660a7f94db1908f09e18a278a4bc..806fa7fb25a552070156b4b85333fa32f76792b5 100644 (file)
@@ -676,13 +676,33 @@ static void active_io_release(struct percpu_ref *ref)
 
 static void no_op(struct percpu_ref *r) {}
 
-static void mddev_set_bitmap_ops(struct mddev *mddev, enum md_submodule_id id)
+static bool mddev_set_bitmap_ops(struct mddev *mddev)
 {
+       struct md_submodule_head *head;
+
+       if (mddev->bitmap_id == ID_BITMAP_NONE)
+               return true;
+
        xa_lock(&md_submodule);
-       mddev->bitmap_ops = xa_load(&md_submodule, id);
+       head = xa_load(&md_submodule, mddev->bitmap_id);
+
+       if (!head) {
+               pr_warn("md: can't find bitmap id %d\n", mddev->bitmap_id);
+               goto err;
+       }
+
+       if (head->type != MD_BITMAP) {
+               pr_warn("md: invalid bitmap id %d\n", mddev->bitmap_id);
+               goto err;
+       }
+
+       mddev->bitmap_ops = (void *)head;
        xa_unlock(&md_submodule);
-       if (!mddev->bitmap_ops)
-               pr_warn_once("md: can't find bitmap id %d\n", id);
+       return true;
+
+err:
+       xa_unlock(&md_submodule);
+       return false;
 }
 
 static void mddev_clear_bitmap_ops(struct mddev *mddev)
@@ -692,8 +712,13 @@ static void mddev_clear_bitmap_ops(struct mddev *mddev)
 
 int mddev_init(struct mddev *mddev)
 {
-       /* TODO: support more versions */
-       mddev_set_bitmap_ops(mddev, ID_BITMAP);
+       if (!IS_ENABLED(CONFIG_MD_BITMAP)) {
+               mddev->bitmap_id = ID_BITMAP_NONE;
+       } else {
+               mddev->bitmap_id = ID_BITMAP;
+               if (!mddev_set_bitmap_ops(mddev))
+                       return -EINVAL;
+       }
 
        if (percpu_ref_init(&mddev->active_io, active_io_release,
                            PERCPU_REF_ALLOW_REINIT, GFP_KERNEL)) {
index 1b767b5320cfb095f70755a82e1c84eff8d79d44..4fa5a3e68a0c22f832a33a3d67138a70690cbb28 100644 (file)
@@ -40,6 +40,7 @@ enum md_submodule_id {
        ID_CLUSTER,
        ID_BITMAP,
        ID_LLBITMAP,    /* TODO */
+       ID_BITMAP_NONE,
 };
 
 struct md_submodule_head {
@@ -565,6 +566,7 @@ struct mddev {
        struct percpu_ref               writes_pending;
        int                             sync_checkers;  /* # of threads checking writes_pending */
 
+       enum md_submodule_id            bitmap_id;
        void                            *bitmap; /* the bitmap for the device */
        struct bitmap_operations        *bitmap_ops;
        struct {