@@ -4649,6 +4649,20 @@ void bdrv_get_geometry(BlockDriverState *bs, uint64_t *nb_sectors_ptr)
*nb_sectors_ptr = nb_sectors < 0 ? 0 : nb_sectors;
}
+uint8_t bdrv_get_zoned_model(BlockDriverState *bs)
+{
+ if (bs->drv->bdrv_get_zoned_info) {
+ bs->drv->bdrv_get_zoned_info(bs);
+ }
+
+ return bs->bl.zoned_model;
+}
+
+uint8_t bdrv_is_zoned(BlockDriverState *bs)
+{
+ return bdrv_get_zoned_model(bs) != BLK_ZONED_NONE;
+}
+
bool bdrv_is_sg(BlockDriverState *bs)
{
return bs->sg;
@@ -1438,6 +1438,15 @@ int64_t blk_nb_sectors(BlockBackend *blk)
return bdrv_nb_sectors(blk_bs(blk));
}
+uint8_t blk_get_zoned_model(BlockBackend *blk)
+{
+ if (!blk_is_available(blk)) {
+ return BLK_ZONED_NONE;
+ }
+
+ return bdrv_get_zoned_model(blk_bs(blk));
+}
+
BlockAIOCB *blk_aio_preadv(BlockBackend *blk, int64_t offset,
QEMUIOVector *qiov, BdrvRequestFlags flags,
BlockCompletionFunc *cb, void *opaque)
@@ -1705,6 +1714,17 @@ bool blk_is_sg(BlockBackend *blk)
return bdrv_is_sg(bs);
}
+bool blk_is_zoned(BlockBackend *blk)
+{
+ BlockDriverState *bs = blk_bs(blk);
+
+ if (!bs) {
+ return false;
+ }
+
+ return bdrv_is_zoned(bs);
+}
+
bool blk_enable_write_cache(BlockBackend *blk)
{
return blk->enable_write_cache;
@@ -278,6 +278,13 @@ enum {
char *bdrv_perm_names(uint64_t perm);
+/* Known zoned device models */
+enum blk_zoned_model {
+ BLK_ZONED_NONE, /* Regular block device */
+ BLK_ZONED_HA, /* Host-aware zoned block device */
+ BLK_ZONED_HM, /* Host-managed zoned block device */
+};
+
/* disk I/O throttling */
void bdrv_init(void);
void bdrv_init_with_whitelist(void);
@@ -354,6 +361,8 @@ int64_t bdrv_get_allocated_file_size(BlockDriverState *bs);
BlockMeasureInfo *bdrv_measure(BlockDriver *drv, QemuOpts *opts,
BlockDriverState *in_bs, Error **errp);
void bdrv_get_geometry(BlockDriverState *bs, uint64_t *nb_sectors_ptr);
+uint8_t bdrv_get_zoned_model(BlockDriverState *bs);
+uint8_t bdrv_is_zoned(BlockDriverState *bs);
void bdrv_refresh_limits(BlockDriverState *bs, Error **errp);
int bdrv_commit(BlockDriverState *bs);
int bdrv_change_backing_file(BlockDriverState *bs,
@@ -416,6 +416,7 @@ struct BlockDriver {
bool (*bdrv_debug_is_suspended)(BlockDriverState *bs, const char *tag);
void (*bdrv_refresh_limits)(BlockDriverState *bs, Error **errp);
+ void (*bdrv_get_zoned_info)(BlockDriverState *bs);
/*
* Returns 1 if newly created images are guaranteed to contain only
@@ -614,6 +615,9 @@ typedef struct BlockLimits {
/* maximum number of iovec elements */
int max_iov;
+
+ /* Zoned device model. Zero value indicates a regular block device */
+ uint8_t zoned_model;
} BlockLimits;
typedef struct BdrvOpBlocker BdrvOpBlocker;
@@ -156,6 +156,7 @@ int blk_pwrite(BlockBackend *blk, int64_t offset, const void *buf, int bytes,
int64_t blk_getlength(BlockBackend *blk);
void blk_get_geometry(BlockBackend *blk, uint64_t *nb_sectors_ptr);
int64_t blk_nb_sectors(BlockBackend *blk);
+uint8_t blk_get_zoned_model(BlockBackend *blk);
BlockAIOCB *blk_aio_preadv(BlockBackend *blk, int64_t offset,
QEMUIOVector *qiov, BdrvRequestFlags flags,
BlockCompletionFunc *cb, void *opaque);
@@ -189,6 +190,7 @@ void blk_error_action(BlockBackend *blk, BlockErrorAction action,
bool is_read, int error);
bool blk_is_read_only(BlockBackend *blk);
bool blk_is_sg(BlockBackend *blk);
+bool blk_is_zoned(BlockBackend *blk);
bool blk_enable_write_cache(BlockBackend *blk);
void blk_set_enable_write_cache(BlockBackend *blk, bool wce);
void blk_invalidate_cache(BlockBackend *blk, Error **errp);
This commit adds Zoned Device Model as defined in T10 ZBC and T13 ZAC standards, along with some useful accessor functions. Since the default value of zero in the zoned model field corresponds to a regular (non-zoned) block device, there is no functionality change with this commit. Signed-off-by: Dmitry Fomichev <dmitry.fomichev@wdc.com> --- block.c | 14 ++++++++++++++ block/block-backend.c | 20 ++++++++++++++++++++ include/block/block.h | 9 +++++++++ include/block/block_int.h | 4 ++++ include/sysemu/block-backend.h | 2 ++ 5 files changed, 49 insertions(+)