Commit 50f1cff3 authored by Christoph Hellwig's avatar Christoph Hellwig Committed by David Sterba

btrfs: fix and document the zoned device choice in alloc_new_bio

Zone Append bios only need a valid block device in struct bio, but
not the device in the btrfs_bio.  Use the information from
btrfs_zoned_get_device to set up bi_bdev and fix zoned writes on
multi-device file system with non-homogeneous capabilities and remove
the pointless btrfs_bio.device assignment.

Add big fat comments explaining what is going on here.
Reviewed-by: default avatarJohannes Thumshirn <johannes.thumshirn@wdc.com>
Reviewed-by: default avatarNaohiro Aota <naohiro.aota@wdc.com>
Signed-off-by: default avatarChristoph Hellwig <hch@lst.de>
Signed-off-by: default avatarDavid Sterba <dsterba@suse.com>
parent 50ff5788
...@@ -3334,24 +3334,37 @@ static int alloc_new_bio(struct btrfs_inode *inode, ...@@ -3334,24 +3334,37 @@ static int alloc_new_bio(struct btrfs_inode *inode,
ret = calc_bio_boundaries(bio_ctrl, inode, file_offset); ret = calc_bio_boundaries(bio_ctrl, inode, file_offset);
if (ret < 0) if (ret < 0)
goto error; goto error;
if (wbc) {
struct block_device *bdev;
bdev = fs_info->fs_devices->latest_dev->bdev; if (wbc) {
bio_set_dev(bio, bdev); /*
wbc_init_bio(wbc, bio); * For Zone append we need the correct block_device that we are
} * going to write to set in the bio to be able to respect the
if (bio_op(bio) == REQ_OP_ZONE_APPEND) { * hardware limitation. Look it up here:
struct btrfs_device *device; */
if (bio_op(bio) == REQ_OP_ZONE_APPEND) {
struct btrfs_device *dev;
dev = btrfs_zoned_get_device(fs_info, disk_bytenr,
fs_info->sectorsize);
if (IS_ERR(dev)) {
ret = PTR_ERR(dev);
goto error;
}
device = btrfs_zoned_get_device(fs_info, disk_bytenr, bio_set_dev(bio, dev->bdev);
fs_info->sectorsize); } else {
if (IS_ERR(device)) { /*
ret = PTR_ERR(device); * Otherwise pick the last added device to support
goto error; * cgroup writeback. For multi-device file systems this
* means blk-cgroup policies have to always be set on the
* last added/replaced device. This is a bit odd but has
* been like that for a long time.
*/
bio_set_dev(bio, fs_info->fs_devices->latest_dev->bdev);
} }
wbc_init_bio(wbc, bio);
btrfs_bio(bio)->device = device; } else {
ASSERT(bio_op(bio) != REQ_OP_ZONE_APPEND);
} }
return 0; return 0;
error: error:
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment