On 2025/07/17 11:32, Shin'ichiro Kawasaki wrote: > Since commit f70291411ba2 ("block: Introduce > bio_needs_zone_write_plugging()"), blk_mq_submit_bio() no longer splits > write BIOs to comply with the requirements of zoned block devices. This > change applies to write BIOs issued by zoned DM targets. Following this > modification, it is expected that DM targets themselves split write BIOs > for zoned block devices.
This description is confusing: if the underlying device of a DM target is a blk-mq block device, then blk_mq_submit_bio() will be called and will split BIOs as needed, regardless of what the DM target did. For BIOs that are issued by the user/FS to the DM device, then that is when bio_needs_zone_write_plugging() is used by DM core to determine if a BIO must be split. Anyway, I do not think you need to reference this commit. So I would drop this entire paragraph from the commit message, and start the explanation with the below paragraph. That is very clear I think. > Commit 2df7168717b7 ("dm: Always split write BIOs to zoned device > limits") updates the device-mapper driver to perform splits for the > write BIOs. However, it did not address the cases where DM targets do > not emulate zone append, such as in the cases of dm-linear or dm-flakey. > For these targets, when the write BIOs span across zone boundaries, they > trigger WARN_ON_ONCE(bio_straddles_zones(bio)) in > blk_zone_wplug_handle_write(). This results in I/O errors. The errors > are reproduced by running blktests test case zbd/004 using zoned > dm-linear or dm-flakey devices. > > To avoid the I/O errors, handle the write BIOs regardless whether DM > targets emulate zone append or not, so that all write BIOs are split at > zone boundaries. For that purpose, drop the check for zone append > emulation in dm_zone_bio_needs_split(). Its argument 'md' is no longer > used then drop it also. > > Fixes: 2df7168717b7 ("dm: Always split write BIOs to zoned device limits") > Cc: sta...@vger.kernel.org The above patch is queued in block-next, so there is no need for this CC-stable. Remove it please. > Signed-off-by: Shin'ichiro Kawasaki <shinichiro.kawas...@wdc.com> One more nit below. With these fixed, feel free to add: Reviewed-by: Damien Le Moal <dlem...@kernel.org> > --- > drivers/md/dm.c | 17 ++++++----------- > 1 file changed, 6 insertions(+), 11 deletions(-) > > diff --git a/drivers/md/dm.c b/drivers/md/dm.c > index ca889328fdfe..a64809f04241 100644 > --- a/drivers/md/dm.c > +++ b/drivers/md/dm.c > @@ -1785,8 +1785,7 @@ static void init_clone_info(struct clone_info *ci, > struct dm_io *io, > } > > #ifdef CONFIG_BLK_DEV_ZONED > -static inline bool dm_zone_bio_needs_split(struct mapped_device *md, > - struct bio *bio) > +static inline bool dm_zone_bio_needs_split(struct bio *bio) > { > /* > * Special case the zone operations that cannot or should not be split. > @@ -1802,13 +1801,10 @@ static inline bool dm_zone_bio_needs_split(struct > mapped_device *md, > } > > /* > - * Mapped devices that require zone append emulation will use the block > - * layer zone write plugging. In such case, we must split any large BIO > - * to the mapped device limits to avoid potential deadlocks with queue > - * freeze operations. > + * When mapped devices use the block layer zone write plugging, we must > + * split any large BIO to the mapped device limits to avoid potential > + * deadlocks with queue freeze operations. Nit: * split any large BIO to the mapped device limits to not submit BIOs * that span zone boundaries and to avoid potential deadlocks with * queue freeze operations. > */ > - if (!dm_emulate_zone_append(md)) > - return false; > return bio_needs_zone_write_plugging(bio) || bio_straddles_zones(bio); > } > > @@ -1932,8 +1928,7 @@ static blk_status_t __send_zone_reset_all(struct > clone_info *ci) > } > > #else > -static inline bool dm_zone_bio_needs_split(struct mapped_device *md, > - struct bio *bio) > +static inline bool dm_zone_bio_needs_split(struct bio *bio) > { > return false; > } > @@ -1960,7 +1955,7 @@ static void dm_split_and_process_bio(struct > mapped_device *md, > > is_abnormal = is_abnormal_io(bio); > if (static_branch_unlikely(&zoned_enabled)) { > - need_split = is_abnormal || dm_zone_bio_needs_split(md, bio); > + need_split = is_abnormal || dm_zone_bio_needs_split(bio); > } else { > need_split = is_abnormal; > } -- Damien Le Moal Western Digital Research