drivers/md/raid5.c | 70 ++++++++++++++++++++++++++++++++++------------ 1 file changed, 52 insertions(+), 18 deletions(-)
Teach RAID5 to export exact old and new llbitmap mappings and the
corresponding sync and array sizes for reshape-aware bitmap users.
Signed-off-by: Yu Kuai <yukuai@fnnas.com>
---
drivers/md/raid5.c | 70 ++++++++++++++++++++++++++++++++++------------
1 file changed, 52 insertions(+), 18 deletions(-)
diff --git a/drivers/md/raid5.c b/drivers/md/raid5.c
index 1f8360d4cdb7..0c58c175bad9 100644
--- a/drivers/md/raid5.c
+++ b/drivers/md/raid5.c
@@ -5898,25 +5898,43 @@ static enum reshape_loc get_reshape_loc(struct mddev *mddev,
return LOC_BEHIND_RESHAPE;
}
-static void raid5_bitmap_sector(struct mddev *mddev, sector_t *offset,
- unsigned long *sectors)
+static void raid5_bitmap_sector_map(struct mddev *mddev, sector_t *offset,
+ unsigned long *sectors,
+ bool previous)
{
struct r5conf *conf = mddev->private;
sector_t start = *offset;
sector_t end = start + *sectors;
- sector_t prev_start = start;
- sector_t prev_end = end;
int sectors_per_chunk;
- enum reshape_loc loc;
int dd_idx;
- sectors_per_chunk = conf->chunk_sectors *
- (conf->raid_disks - conf->max_degraded);
+ if (previous)
+ sectors_per_chunk = conf->prev_chunk_sectors *
+ (conf->previous_raid_disks - conf->max_degraded);
+ else
+ sectors_per_chunk = conf->chunk_sectors *
+ (conf->raid_disks - conf->max_degraded);
start = round_down(start, sectors_per_chunk);
end = round_up(end, sectors_per_chunk);
- start = raid5_compute_sector(conf, start, 0, &dd_idx, NULL);
- end = raid5_compute_sector(conf, end, 0, &dd_idx, NULL);
+ start = raid5_compute_sector(conf, start, previous, &dd_idx, NULL);
+ end = raid5_compute_sector(conf, end, previous, &dd_idx, NULL);
+ *offset = start;
+ *sectors = end - start;
+}
+
+static void raid5_bitmap_sector(struct mddev *mddev, sector_t *offset,
+ unsigned long *sectors)
+{
+ struct r5conf *conf = mddev->private;
+ sector_t start = *offset;
+ sector_t end = start + *sectors;
+ sector_t prev_start = start;
+ unsigned long prev_sectors = end - start;
+ enum reshape_loc loc;
+
+ raid5_bitmap_sector_map(mddev, &start, sectors, false);
+ end = start + *sectors;
/*
* For LOC_INSIDE_RESHAPE, this IO will wait for reshape to make
@@ -5925,17 +5943,10 @@ static void raid5_bitmap_sector(struct mddev *mddev, sector_t *offset,
loc = get_reshape_loc(mddev, conf, prev_start);
if (likely(loc != LOC_AHEAD_OF_RESHAPE)) {
*offset = start;
- *sectors = end - start;
return;
}
- sectors_per_chunk = conf->prev_chunk_sectors *
- (conf->previous_raid_disks - conf->max_degraded);
- prev_start = round_down(prev_start, sectors_per_chunk);
- prev_end = round_down(prev_end, sectors_per_chunk);
-
- prev_start = raid5_compute_sector(conf, prev_start, 1, &dd_idx, NULL);
- prev_end = raid5_compute_sector(conf, prev_end, 1, &dd_idx, NULL);
+ raid5_bitmap_sector_map(mddev, &prev_start, &prev_sectors, true);
/*
* for LOC_AHEAD_OF_RESHAPE, reshape can make progress before this IO
@@ -5943,7 +5954,7 @@ static void raid5_bitmap_sector(struct mddev *mddev, sector_t *offset,
* we set bits for both.
*/
*offset = min(start, prev_start);
- *sectors = max(end, prev_end) - *offset;
+ *sectors = max(end, prev_start + prev_sectors) - *offset;
}
static enum stripe_result make_stripe_request(struct mddev *mddev,
@@ -9002,6 +9013,20 @@ static void raid5_prepare_suspend(struct mddev *mddev)
wake_up(&conf->wait_for_reshape);
}
+static sector_t raid5_bitmap_sync_size(struct mddev *mddev, bool previous)
+{
+ return mddev->dev_sectors;
+}
+
+static sector_t raid5_bitmap_array_sectors(struct mddev *mddev, bool previous)
+{
+ struct r5conf *conf = mddev->private;
+
+ if (previous)
+ return raid5_size(mddev, 0, 0);
+ return raid5_size(mddev, mddev->dev_sectors, conf->raid_disks);
+}
+
static struct md_personality raid6_personality =
{
.head = {
@@ -9031,6 +9056,9 @@ static struct md_personality raid6_personality =
.change_consistency_policy = raid5_change_consistency_policy,
.prepare_suspend = raid5_prepare_suspend,
.bitmap_sector = raid5_bitmap_sector,
+ .bitmap_sector_map = raid5_bitmap_sector_map,
+ .bitmap_sync_size = raid5_bitmap_sync_size,
+ .bitmap_array_sectors = raid5_bitmap_array_sectors,
};
static struct md_personality raid5_personality =
{
@@ -9061,6 +9089,9 @@ static struct md_personality raid5_personality =
.change_consistency_policy = raid5_change_consistency_policy,
.prepare_suspend = raid5_prepare_suspend,
.bitmap_sector = raid5_bitmap_sector,
+ .bitmap_sector_map = raid5_bitmap_sector_map,
+ .bitmap_sync_size = raid5_bitmap_sync_size,
+ .bitmap_array_sectors = raid5_bitmap_array_sectors,
};
static struct md_personality raid4_personality =
@@ -9092,6 +9123,9 @@ static struct md_personality raid4_personality =
.change_consistency_policy = raid5_change_consistency_policy,
.prepare_suspend = raid5_prepare_suspend,
.bitmap_sector = raid5_bitmap_sector,
+ .bitmap_sector_map = raid5_bitmap_sector_map,
+ .bitmap_sync_size = raid5_bitmap_sync_size,
+ .bitmap_array_sectors = raid5_bitmap_array_sectors,
};
static int __init raid5_init(void)
--
2.51.0
Hi Yu,
kernel test robot noticed the following build errors:
[auto build test ERROR on linus/master]
[also build test ERROR on v7.1-rc1 next-20260430]
[If your patch is applied to the wrong git tree, kindly drop us a note.
And when submitting patch, we suggest to use '--base' as documented in
https://git-scm.com/docs/git-format-patch#_base_tree_information]
url: https://github.com/intel-lab-lkp/linux/commits/Yu-Kuai/md-raid5-add-exact-old-and-new-llbitmap-mapping-helpers/20260421-233709
base: linus/master
patch link: https://lore.kernel.org/r/20260419030942.824195-17-yukuai%40fnnas.com
patch subject: [PATCH] md/raid5: add exact old and new llbitmap mapping helpers
config: hexagon-allmodconfig (https://download.01.org/0day-ci/archive/20260502/202605020242.1lRKHrkP-lkp@intel.com/config)
compiler: clang version 17.0.6 (https://github.com/llvm/llvm-project 6009708b4367171ccdbf4b5905cb6a803753fe18)
reproduce (this is a W=1 build): (https://download.01.org/0day-ci/archive/20260502/202605020242.1lRKHrkP-lkp@intel.com/reproduce)
If you fix the issue in a separate patch/commit (i.e. not just a new version of
the same patch/commit), kindly add following tags
| Reported-by: kernel test robot <lkp@intel.com>
| Closes: https://lore.kernel.org/oe-kbuild-all/202605020242.1lRKHrkP-lkp@intel.com/
All errors (new ones prefixed by >>):
>> drivers/md/raid5.c:9065:3: error: field designator 'bitmap_sector_map' does not refer to any field in type 'struct md_personality'; did you mean 'bitmap_sector'?
9065 | .bitmap_sector_map = raid5_bitmap_sector_map,
| ^~~~~~~~~~~~~~~~~
| bitmap_sector
drivers/md/md.h:797:9: note: 'bitmap_sector' declared here
797 | void (*bitmap_sector)(struct mddev *mddev, sector_t *offset,
| ^
>> drivers/md/raid5.c:9065:23: error: incompatible function pointer types initializing 'void (*)(struct mddev *, sector_t *, unsigned long *)' (aka 'void (*)(struct mddev *, unsigned long long *, unsigned long *)') with an expression of type 'void (struct mddev *, sector_t *, unsigned long *, bool)' (aka 'void (struct mddev *, unsigned long long *, unsigned long *, _Bool)') [-Wincompatible-function-pointer-types]
9065 | .bitmap_sector_map = raid5_bitmap_sector_map,
| ^~~~~~~~~~~~~~~~~~~~~~~
drivers/md/raid5.c:9065:23: warning: initializer overrides prior initialization of this subobject [-Winitializer-overrides]
9065 | .bitmap_sector_map = raid5_bitmap_sector_map,
| ^~~~~~~~~~~~~~~~~~~~~~~
drivers/md/raid5.c:9064:19: note: previous initialization is here
9064 | .bitmap_sector = raid5_bitmap_sector,
| ^~~~~~~~~~~~~~~~~~~
>> drivers/md/raid5.c:9066:3: error: field designator 'bitmap_sync_size' does not refer to any field in type 'struct md_personality'
9066 | .bitmap_sync_size = raid5_bitmap_sync_size,
| ~^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
>> drivers/md/raid5.c:9067:3: error: field designator 'bitmap_array_sectors' does not refer to any field in type 'struct md_personality'
9067 | .bitmap_array_sectors = raid5_bitmap_array_sectors,
| ~^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
drivers/md/raid5.c:9098:3: error: field designator 'bitmap_sector_map' does not refer to any field in type 'struct md_personality'; did you mean 'bitmap_sector'?
9098 | .bitmap_sector_map = raid5_bitmap_sector_map,
| ^~~~~~~~~~~~~~~~~
| bitmap_sector
drivers/md/md.h:797:9: note: 'bitmap_sector' declared here
797 | void (*bitmap_sector)(struct mddev *mddev, sector_t *offset,
| ^
drivers/md/raid5.c:9098:23: error: incompatible function pointer types initializing 'void (*)(struct mddev *, sector_t *, unsigned long *)' (aka 'void (*)(struct mddev *, unsigned long long *, unsigned long *)') with an expression of type 'void (struct mddev *, sector_t *, unsigned long *, bool)' (aka 'void (struct mddev *, unsigned long long *, unsigned long *, _Bool)') [-Wincompatible-function-pointer-types]
9098 | .bitmap_sector_map = raid5_bitmap_sector_map,
| ^~~~~~~~~~~~~~~~~~~~~~~
drivers/md/raid5.c:9098:23: warning: initializer overrides prior initialization of this subobject [-Winitializer-overrides]
9098 | .bitmap_sector_map = raid5_bitmap_sector_map,
| ^~~~~~~~~~~~~~~~~~~~~~~
drivers/md/raid5.c:9097:19: note: previous initialization is here
9097 | .bitmap_sector = raid5_bitmap_sector,
| ^~~~~~~~~~~~~~~~~~~
drivers/md/raid5.c:9099:3: error: field designator 'bitmap_sync_size' does not refer to any field in type 'struct md_personality'
9099 | .bitmap_sync_size = raid5_bitmap_sync_size,
| ~^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
drivers/md/raid5.c:9100:3: error: field designator 'bitmap_array_sectors' does not refer to any field in type 'struct md_personality'
9100 | .bitmap_array_sectors = raid5_bitmap_array_sectors,
| ~^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
drivers/md/raid5.c:9132:3: error: field designator 'bitmap_sector_map' does not refer to any field in type 'struct md_personality'; did you mean 'bitmap_sector'?
9132 | .bitmap_sector_map = raid5_bitmap_sector_map,
| ^~~~~~~~~~~~~~~~~
| bitmap_sector
drivers/md/md.h:797:9: note: 'bitmap_sector' declared here
797 | void (*bitmap_sector)(struct mddev *mddev, sector_t *offset,
| ^
drivers/md/raid5.c:9132:23: error: incompatible function pointer types initializing 'void (*)(struct mddev *, sector_t *, unsigned long *)' (aka 'void (*)(struct mddev *, unsigned long long *, unsigned long *)') with an expression of type 'void (struct mddev *, sector_t *, unsigned long *, bool)' (aka 'void (struct mddev *, unsigned long long *, unsigned long *, _Bool)') [-Wincompatible-function-pointer-types]
9132 | .bitmap_sector_map = raid5_bitmap_sector_map,
| ^~~~~~~~~~~~~~~~~~~~~~~
drivers/md/raid5.c:9132:23: warning: initializer overrides prior initialization of this subobject [-Winitializer-overrides]
9132 | .bitmap_sector_map = raid5_bitmap_sector_map,
| ^~~~~~~~~~~~~~~~~~~~~~~
drivers/md/raid5.c:9131:19: note: previous initialization is here
9131 | .bitmap_sector = raid5_bitmap_sector,
| ^~~~~~~~~~~~~~~~~~~
drivers/md/raid5.c:9133:3: error: field designator 'bitmap_sync_size' does not refer to any field in type 'struct md_personality'
9133 | .bitmap_sync_size = raid5_bitmap_sync_size,
| ~^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
drivers/md/raid5.c:9134:3: error: field designator 'bitmap_array_sectors' does not refer to any field in type 'struct md_personality'
9134 | .bitmap_array_sectors = raid5_bitmap_array_sectors,
| ~^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
3 warnings and 12 errors generated.
vim +9065 drivers/md/raid5.c
9035
9036 static struct md_personality raid6_personality =
9037 {
9038 .head = {
9039 .type = MD_PERSONALITY,
9040 .id = ID_RAID6,
9041 .name = "raid6",
9042 .owner = THIS_MODULE,
9043 },
9044
9045 .make_request = raid5_make_request,
9046 .run = raid5_run,
9047 .start = raid5_start,
9048 .free = raid5_free,
9049 .status = raid5_status,
9050 .error_handler = raid5_error,
9051 .hot_add_disk = raid5_add_disk,
9052 .hot_remove_disk= raid5_remove_disk,
9053 .spare_active = raid5_spare_active,
9054 .sync_request = raid5_sync_request,
9055 .resize = raid5_resize,
9056 .size = raid5_size,
9057 .check_reshape = raid6_check_reshape,
9058 .start_reshape = raid5_start_reshape,
9059 .finish_reshape = raid5_finish_reshape,
9060 .quiesce = raid5_quiesce,
9061 .takeover = raid6_takeover,
9062 .change_consistency_policy = raid5_change_consistency_policy,
9063 .prepare_suspend = raid5_prepare_suspend,
9064 .bitmap_sector = raid5_bitmap_sector,
> 9065 .bitmap_sector_map = raid5_bitmap_sector_map,
> 9066 .bitmap_sync_size = raid5_bitmap_sync_size,
> 9067 .bitmap_array_sectors = raid5_bitmap_array_sectors,
9068 };
9069 static struct md_personality raid5_personality =
9070 {
9071 .head = {
9072 .type = MD_PERSONALITY,
9073 .id = ID_RAID5,
9074 .name = "raid5",
9075 .owner = THIS_MODULE,
9076 },
9077
9078 .make_request = raid5_make_request,
9079 .run = raid5_run,
9080 .start = raid5_start,
9081 .free = raid5_free,
9082 .status = raid5_status,
9083 .error_handler = raid5_error,
9084 .hot_add_disk = raid5_add_disk,
9085 .hot_remove_disk= raid5_remove_disk,
9086 .spare_active = raid5_spare_active,
9087 .sync_request = raid5_sync_request,
9088 .resize = raid5_resize,
9089 .size = raid5_size,
9090 .check_reshape = raid5_check_reshape,
9091 .start_reshape = raid5_start_reshape,
9092 .finish_reshape = raid5_finish_reshape,
9093 .quiesce = raid5_quiesce,
9094 .takeover = raid5_takeover,
9095 .change_consistency_policy = raid5_change_consistency_policy,
9096 .prepare_suspend = raid5_prepare_suspend,
9097 .bitmap_sector = raid5_bitmap_sector,
9098 .bitmap_sector_map = raid5_bitmap_sector_map,
9099 .bitmap_sync_size = raid5_bitmap_sync_size,
9100 .bitmap_array_sectors = raid5_bitmap_array_sectors,
9101 };
9102
--
0-DAY CI Kernel Test Service
https://github.com/intel/lkp-tests/wiki
© 2016 - 2026 Red Hat, Inc.