Add a new BLOCK_URING_CMD_ZONE_RESET_ALL uring cmd to reset all zones for a given block device. This can be used by storage systems or file system mkfs tools to initialize multiple devices in parallel.
Unified · Split
| @@ -14,6 +14,7 @@ · 13 unmodified lines | ||
| 14 | 14 | #include <linux/pagemap.h> |
| 15 | 15 | #include <linux/io_uring/cmd.h> |
| 16 | 16 | #include <linux/blk-integrity.h> |
| 17 | +#include <trace/events/block.h> | |
| 17 | 18 | #include <uapi/linux/blkdev.h> |
| 18 | 19 | #include "blk.h" |
| 19 | 20 | #include "blk-crypto-internal.h" |
| @@ -943,6 +944,40 @@ static int blkdev_cmd_discard(struct io_uring_cmd *cmd) · 923 unmodified lines | ||
| 943 | 944 | return -EIOCBQUEUED; |
| 944 | 945 | } |
| 945 | 946 | |
| 947 | +static int blkdev_cmd_zone_reset_all(struct io_uring_cmd *cmd) | |
| 948 | +{ | |
| 949 | + struct blk_iou_cmd *bic = io_uring_cmd_to_pdu(cmd, struct blk_iou_cmd); | |
| 950 | + struct block_device *bdev = I_BDEV(cmd->file->f_mapping->host); | |
| 951 | + struct bio *bio; | |
| 952 | + int err; | |
| 953 | + | |
| 954 | + if (!(file_to_blk_mode(cmd->file) & BLK_OPEN_WRITE)) | |
| 955 | + return -EBADF; | |
| 956 | + if (bdev_read_only(bdev)) | |
| 957 | + return -EPERM; | |
| 958 | + if (!bdev_is_zoned(bdev)) | |
| 959 | + return -EOPNOTSUPP; | |
| 960 | + if (bic->start || bic->len) | |
| 961 | + return -EINVAL; | |
| 962 | + | |
| 963 | + err = filemap_invalidate_pages(bdev->bd_mapping, 0, | |
| 964 | + bdev_nr_bytes(bdev) - 1, bic->nowait); | |
| 965 | + if (err) | |
| 966 | + return err; | |
| 967 | + | |
| 968 | + bio = bio_alloc(bdev, 0, REQ_OP_ZONE_RESET_ALL, | |
| 969 | + bic->nowait ? GFP_NOWAIT : GFP_KERNEL); | |
| 970 | + if (!bio) | |
| 971 | + return -EAGAIN; | |
| 972 | + if (bic->nowait) | |
| 973 | + bio->bi_opf |= REQ_NOWAIT; | |
| 974 | + trace_blkdev_zone_mgmt(bio, 0); | |
| 975 | + bio->bi_private = cmd; | |
| 976 | + bio->bi_end_io = bio_cmd_bio_end_io; | |
| 977 | + submit_bio(bio); | |
| 978 | + return -EIOCBQUEUED; | |
| 979 | +} | |
| 980 | + | |
| 946 | 981 | int blkdev_uring_cmd(struct io_uring_cmd *cmd, unsigned int issue_flags) |
| 947 | 982 | { |
| 948 | 983 | struct blk_iou_cmd *bic = io_uring_cmd_to_pdu(cmd, struct blk_iou_cmd); |
| @@ -966,6 +1001,8 @@ int blkdev_uring_cmd(struct io_uring_cmd *cmd, unsigned int issue_flags) · 17 unmodified lines | ||
| 966 | 1001 | switch (cmd_op) { |
| 967 | 1002 | case BLOCK_URING_CMD_DISCARD: |
| 968 | 1003 | return blkdev_cmd_discard(cmd); |
| 1004 | + case BLOCK_URING_CMD_ZONE_RESET_ALL: | |
| 1005 | + return blkdev_cmd_zone_reset_all(cmd); | |
| 969 | 1006 | } |
| 970 | 1007 | return -EINVAL; |
| 971 | 1008 | } |
| @@ -10,5 +10,6 @@ · 9 unmodified lines | ||
| 10 | 10 | * It's a different number space from ioctl(), reuse the block's code 0x12. |
| 11 | 11 | */ |
| 12 | 12 | #define BLOCK_URING_CMD_DISCARD _IO(0x12, 0) |
| 13 | +#define BLOCK_URING_CMD_ZONE_RESET_ALL _IO(0x12, 1) | |
| 13 | 14 | |
| 14 | 15 | #endif |