From f2cd875d54e95f87a4c994cfef082f09b4953aa9 Mon Sep 17 00:00:00 2001 From: Kevin Wolf Date: Mon, 21 Mar 2016 11:27:04 +0100 Subject: block: Introduce BlockBackendPublic Some features, like I/O throttling, are implemented outside block-backend.c, but still want to keep information in BlockBackend, e.g. list entries that allow keeping a list of BlockBackends. In order to avoid exposing the whole struct layout in the public header file, this patch introduces an embedded public struct where such information can be added and a pair of functions to convert between BlockBackend and BlockBackendPublic. Signed-off-by: Kevin Wolf Reviewed-by: Alberto Garcia Reviewed-by: Eric Blake Acked-by: Stefan Hajnoczi --- include/sysemu/block-backend.h | 10 ++++++++++ 1 file changed, 10 insertions(+) (limited to 'include') diff --git a/include/sysemu/block-backend.h b/include/sysemu/block-backend.h index 26736ed..a771603 100644 --- a/include/sysemu/block-backend.h +++ b/include/sysemu/block-backend.h @@ -59,6 +59,13 @@ typedef struct BlockDevOps { void (*resize_cb)(void *opaque); } BlockDevOps; +/* This struct is embedded in (the private) BlockBackend struct and contains + * fields that must be public. This is in particular for QLIST_ENTRY() and + * friends so that BlockBackends can be kept in lists outside block-backend.c */ +typedef struct BlockBackendPublic { + int dummy; /* empty structs are illegal */ +} BlockBackendPublic; + BlockBackend *blk_new(Error **errp); BlockBackend *blk_new_with_bs(Error **errp); BlockBackend *blk_new_open(const char *filename, const char *reference, @@ -74,6 +81,9 @@ BlockDriverState *blk_next_root_bs(BlockDriverState *bs); bool monitor_add_blk(BlockBackend *blk, const char *name, Error **errp); void monitor_remove_blk(BlockBackend *blk); +BlockBackendPublic *blk_get_public(BlockBackend *blk); +BlockBackend *blk_by_public(BlockBackendPublic *public); + BlockDriverState *blk_bs(BlockBackend *blk); void blk_remove_bs(BlockBackend *blk); void blk_insert_bs(BlockBackend *blk, BlockDriverState *bs); -- cgit v1.1 From 31dce3ccca98bc9f9eb57f8b08b008edd07661ba Mon Sep 17 00:00:00 2001 From: Kevin Wolf Date: Mon, 21 Mar 2016 11:30:57 +0100 Subject: block: throttle-groups: Use BlockBackend pointers internally As a first step towards moving I/O throttling to the BlockBackend level, this patch changes all pointers in struct ThrottleGroup from referencing a BlockDriverState to referencing a BlockBackend. This change is valid because we made sure that throttling can only be enabled on BDSes which have a BB attached. Signed-off-by: Kevin Wolf Reviewed-by: Alberto Garcia Acked-by: Stefan Hajnoczi --- include/block/block_int.h | 1 - include/block/throttle-groups.h | 4 ++-- include/sysemu/block-backend.h | 5 ++++- 3 files changed, 6 insertions(+), 4 deletions(-) (limited to 'include') diff --git a/include/block/block_int.h b/include/block/block_int.h index a029c20..3f5d2b1 100644 --- a/include/block/block_int.h +++ b/include/block/block_int.h @@ -435,7 +435,6 @@ struct BlockDriverState { ThrottleState *throttle_state; ThrottleTimers throttle_timers; unsigned pending_reqs[2]; - QLIST_ENTRY(BlockDriverState) round_robin; /* Offset after the highest byte written to */ uint64_t wr_highest_offset; diff --git a/include/block/throttle-groups.h b/include/block/throttle-groups.h index 395f72d..b9114ee 100644 --- a/include/block/throttle-groups.h +++ b/include/block/throttle-groups.h @@ -36,8 +36,8 @@ void throttle_group_unref(ThrottleState *ts); void throttle_group_config(BlockDriverState *bs, ThrottleConfig *cfg); void throttle_group_get_config(BlockDriverState *bs, ThrottleConfig *cfg); -void throttle_group_register_bs(BlockDriverState *bs, const char *groupname); -void throttle_group_unregister_bs(BlockDriverState *bs); +void throttle_group_register_blk(BlockBackend *blk, const char *groupname); +void throttle_group_unregister_blk(BlockBackend *blk); void throttle_group_restart_bs(BlockDriverState *bs); void coroutine_fn throttle_group_co_io_limits_intercept(BlockDriverState *bs, diff --git a/include/sysemu/block-backend.h b/include/sysemu/block-backend.h index a771603..1dcd70e 100644 --- a/include/sysemu/block-backend.h +++ b/include/sysemu/block-backend.h @@ -63,7 +63,10 @@ typedef struct BlockDevOps { * fields that must be public. This is in particular for QLIST_ENTRY() and * friends so that BlockBackends can be kept in lists outside block-backend.c */ typedef struct BlockBackendPublic { - int dummy; /* empty structs are illegal */ + /* I/O throttling */ + /* The following fields are protected by the ThrottleGroup lock. + * See the ThrottleGroup documentation for details. */ + QLIST_ENTRY(BlockBackendPublic) round_robin; } BlockBackendPublic; BlockBackend *blk_new(Error **errp); -- cgit v1.1 From 49d2165d7d6b589d1ea28b15a8874c417bdc55ed Mon Sep 17 00:00:00 2001 From: Kevin Wolf Date: Mon, 21 Mar 2016 11:58:21 +0100 Subject: block: Convert throttle_group_get_name() to BlockBackend Signed-off-by: Kevin Wolf Reviewed-by: Alberto Garcia Acked-by: Stefan Hajnoczi --- include/block/throttle-groups.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'include') diff --git a/include/block/throttle-groups.h b/include/block/throttle-groups.h index b9114ee..bd55a34 100644 --- a/include/block/throttle-groups.h +++ b/include/block/throttle-groups.h @@ -28,7 +28,7 @@ #include "qemu/throttle.h" #include "block/block_int.h" -const char *throttle_group_get_name(BlockDriverState *bs); +const char *throttle_group_get_name(BlockBackend *blk); ThrottleState *throttle_group_incref(const char *name); void throttle_group_unref(ThrottleState *ts); -- cgit v1.1 From 27ccdd52598290f0f8b58be56e235aff7aebfaf3 Mon Sep 17 00:00:00 2001 From: Kevin Wolf Date: Mon, 21 Mar 2016 12:56:44 +0100 Subject: block: Move throttling fields from BDS to BB This patch changes where the throttling state is stored (used to be the BlockDriverState, now it is the BlockBackend), but it doesn't actually make it a BB level feature yet. For example, throttling is still disabled when the BDS is detached from the BB. Signed-off-by: Kevin Wolf Acked-by: Stefan Hajnoczi --- include/block/block_int.h | 13 ------------- include/block/throttle-groups.h | 2 +- include/sysemu/block-backend.h | 11 ++++++++++- 3 files changed, 11 insertions(+), 15 deletions(-) (limited to 'include') diff --git a/include/block/block_int.h b/include/block/block_int.h index 3f5d2b1..2bbc2c0 100644 --- a/include/block/block_int.h +++ b/include/block/block_int.h @@ -26,7 +26,6 @@ #include "block/accounting.h" #include "block/block.h" -#include "block/throttle-groups.h" #include "qemu/option.h" #include "qemu/queue.h" #include "qemu/coroutine.h" @@ -424,18 +423,6 @@ struct BlockDriverState { /* number of in-flight serialising requests */ unsigned int serialising_in_flight; - /* I/O throttling. - * throttle_state tells us if this BDS has I/O limits configured. - * io_limits_disabled tells us if they are currently being enforced */ - CoQueue throttled_reqs[2]; - unsigned int io_limits_disabled; - - /* The following fields are protected by the ThrottleGroup lock. - * See the ThrottleGroup documentation for details. */ - ThrottleState *throttle_state; - ThrottleTimers throttle_timers; - unsigned pending_reqs[2]; - /* Offset after the highest byte written to */ uint64_t wr_highest_offset; diff --git a/include/block/throttle-groups.h b/include/block/throttle-groups.h index bd55a34..840ba44 100644 --- a/include/block/throttle-groups.h +++ b/include/block/throttle-groups.h @@ -38,7 +38,7 @@ void throttle_group_get_config(BlockDriverState *bs, ThrottleConfig *cfg); void throttle_group_register_blk(BlockBackend *blk, const char *groupname); void throttle_group_unregister_blk(BlockBackend *blk); -void throttle_group_restart_bs(BlockDriverState *bs); +void throttle_group_restart_blk(BlockBackend *blk); void coroutine_fn throttle_group_co_io_limits_intercept(BlockDriverState *bs, unsigned int bytes, diff --git a/include/sysemu/block-backend.h b/include/sysemu/block-backend.h index 1dcd70e..08d27a8 100644 --- a/include/sysemu/block-backend.h +++ b/include/sysemu/block-backend.h @@ -14,6 +14,7 @@ #define BLOCK_BACKEND_H #include "qemu/iov.h" +#include "block/throttle-groups.h" /* * TODO Have to include block/block.h for a bunch of block layer @@ -63,9 +64,17 @@ typedef struct BlockDevOps { * fields that must be public. This is in particular for QLIST_ENTRY() and * friends so that BlockBackends can be kept in lists outside block-backend.c */ typedef struct BlockBackendPublic { - /* I/O throttling */ + /* I/O throttling. + * throttle_state tells us if this BlockBackend has I/O limits configured. + * io_limits_disabled tells us if they are currently being enforced */ + CoQueue throttled_reqs[2]; + unsigned int io_limits_disabled; + /* The following fields are protected by the ThrottleGroup lock. * See the ThrottleGroup documentation for details. */ + ThrottleState *throttle_state; + ThrottleTimers throttle_timers; + unsigned pending_reqs[2]; QLIST_ENTRY(BlockBackendPublic) round_robin; } BlockBackendPublic; -- cgit v1.1 From 441565b2792d4ee9ee1928a8d14538be39211292 Mon Sep 17 00:00:00 2001 From: Kevin Wolf Date: Mon, 21 Mar 2016 13:30:30 +0100 Subject: block: Move actual I/O throttling to BlockBackend Signed-off-by: Kevin Wolf Reviewed-by: Alberto Garcia Acked-by: Stefan Hajnoczi --- include/block/throttle-groups.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'include') diff --git a/include/block/throttle-groups.h b/include/block/throttle-groups.h index 840ba44..ac42248 100644 --- a/include/block/throttle-groups.h +++ b/include/block/throttle-groups.h @@ -40,7 +40,7 @@ void throttle_group_register_blk(BlockBackend *blk, const char *groupname); void throttle_group_unregister_blk(BlockBackend *blk); void throttle_group_restart_blk(BlockBackend *blk); -void coroutine_fn throttle_group_co_io_limits_intercept(BlockDriverState *bs, +void coroutine_fn throttle_group_co_io_limits_intercept(BlockBackend *blk, unsigned int bytes, bool is_write); -- cgit v1.1 From 97148076e8beebbcab11e5cb581d8508722143fc Mon Sep 17 00:00:00 2001 From: Kevin Wolf Date: Mon, 21 Mar 2016 13:53:52 +0100 Subject: block: Move I/O throttling configuration functions to BlockBackend Signed-off-by: Kevin Wolf Reviewed-by: Alberto Garcia Acked-by: Stefan Hajnoczi --- include/block/block.h | 4 ---- include/block/block_int.h | 3 +-- include/block/throttle-groups.h | 4 ++-- include/sysemu/block-backend.h | 5 +++++ 4 files changed, 8 insertions(+), 8 deletions(-) (limited to 'include') diff --git a/include/block/block.h b/include/block/block.h index b210832..2c5c280 100644 --- a/include/block/block.h +++ b/include/block/block.h @@ -187,10 +187,6 @@ void bdrv_stats_print(Monitor *mon, const QObject *data); void bdrv_info_stats(Monitor *mon, QObject **ret_data); /* disk I/O throttling */ -void bdrv_io_limits_enable(BlockDriverState *bs, const char *group); -void bdrv_io_limits_disable(BlockDriverState *bs); -void bdrv_io_limits_update_group(BlockDriverState *bs, const char *group); - void bdrv_init(void); void bdrv_init_with_whitelist(void); bool bdrv_uses_whitelist(void); diff --git a/include/block/block_int.h b/include/block/block_int.h index 2bbc2c0..1218857 100644 --- a/include/block/block_int.h +++ b/include/block/block_int.h @@ -525,8 +525,7 @@ int get_tmp_filename(char *filename, int size); BlockDriver *bdrv_probe_all(const uint8_t *buf, int buf_size, const char *filename); -void bdrv_set_io_limits(BlockDriverState *bs, - ThrottleConfig *cfg); +bool bdrv_start_throttled_reqs(BlockDriverState *bs); /** diff --git a/include/block/throttle-groups.h b/include/block/throttle-groups.h index ac42248..d983d34 100644 --- a/include/block/throttle-groups.h +++ b/include/block/throttle-groups.h @@ -33,8 +33,8 @@ const char *throttle_group_get_name(BlockBackend *blk); ThrottleState *throttle_group_incref(const char *name); void throttle_group_unref(ThrottleState *ts); -void throttle_group_config(BlockDriverState *bs, ThrottleConfig *cfg); -void throttle_group_get_config(BlockDriverState *bs, ThrottleConfig *cfg); +void throttle_group_config(BlockBackend *blk, ThrottleConfig *cfg); +void throttle_group_get_config(BlockBackend *blk, ThrottleConfig *cfg); void throttle_group_register_blk(BlockBackend *blk, const char *groupname); void throttle_group_unregister_blk(BlockBackend *blk); diff --git a/include/sysemu/block-backend.h b/include/sysemu/block-backend.h index 08d27a8..dd9c8ca 100644 --- a/include/sysemu/block-backend.h +++ b/include/sysemu/block-backend.h @@ -212,4 +212,9 @@ BlockAIOCB *blk_abort_aio_request(BlockBackend *blk, BlockCompletionFunc *cb, void *opaque, int ret); +void blk_set_io_limits(BlockBackend *blk, ThrottleConfig *cfg); +void blk_io_limits_disable(BlockBackend *blk); +void blk_io_limits_enable(BlockBackend *blk, const char *group); +void blk_io_limits_update_group(BlockBackend *blk, const char *group); + #endif -- cgit v1.1 From 22aa8b246ada8d45add8eef64d4640a20b4f7ef3 Mon Sep 17 00:00:00 2001 From: Kevin Wolf Date: Wed, 24 Feb 2016 15:13:35 +0100 Subject: block: Introduce BdrvChild.opaque BlockBackends use it to get a back pointer from BdrvChild to BlockBackend in any BdrvChildRole callbacks. Signed-off-by: Kevin Wolf Reviewed-by: Alberto Garcia Acked-by: Stefan Hajnoczi --- include/block/block_int.h | 1 + 1 file changed, 1 insertion(+) (limited to 'include') diff --git a/include/block/block_int.h b/include/block/block_int.h index 1218857..47dfafa 100644 --- a/include/block/block_int.h +++ b/include/block/block_int.h @@ -373,6 +373,7 @@ struct BdrvChild { BlockDriverState *bs; char *name; const BdrvChildRole *role; + void *opaque; QLIST_ENTRY(BdrvChild) next; QLIST_ENTRY(BdrvChild) next_parent; }; -- cgit v1.1 From c2066af0514d80a805dac82accaec1121babfa15 Mon Sep 17 00:00:00 2001 From: Kevin Wolf Date: Tue, 22 Mar 2016 12:05:35 +0100 Subject: block: Drain throttling queue with BdrvChild callback This removes the last part of I/O throttling from block/io.c and moves it to the BlockBackend. Instead of having knowledge about throttling inside io.c, we can call a BdrvChild callback .drained_begin/end, which happens to drain the throttled requests for BlockBackend parents. Signed-off-by: Kevin Wolf Reviewed-by: Alberto Garcia Acked-by: Stefan Hajnoczi --- include/block/block_int.h | 16 +++++++++++----- 1 file changed, 11 insertions(+), 5 deletions(-) (limited to 'include') diff --git a/include/block/block_int.h b/include/block/block_int.h index 47dfafa..a1f8488 100644 --- a/include/block/block_int.h +++ b/include/block/block_int.h @@ -364,6 +364,17 @@ typedef struct BdrvAioNotifier { struct BdrvChildRole { void (*inherit_options)(int *child_flags, QDict *child_options, int parent_flags, QDict *parent_options); + + /* + * If this pair of functions is implemented, the parent doesn't issue new + * requests after returning from .drained_begin() until .drained_end() is + * called. + * + * Note that this can be nested. If drained_begin() was called twice, new + * I/O is allowed only after drained_end() was called twice, too. + */ + void (*drained_begin)(BdrvChild *child); + void (*drained_end)(BdrvChild *child); }; extern const BdrvChildRole child_file; @@ -526,8 +537,6 @@ int get_tmp_filename(char *filename, int size); BlockDriver *bdrv_probe_all(const uint8_t *buf, int buf_size, const char *filename); -bool bdrv_start_throttled_reqs(BlockDriverState *bs); - /** * bdrv_add_before_write_notifier: @@ -710,9 +719,6 @@ BdrvChild *bdrv_root_attach_child(BlockDriverState *child_bs, const BdrvChildRole *child_role); void bdrv_root_unref_child(BdrvChild *child); -void bdrv_no_throttling_begin(BlockDriverState *bs); -void bdrv_no_throttling_end(BlockDriverState *bs); - void blk_dev_change_media_cb(BlockBackend *blk, bool load); bool blk_dev_has_removable_media(BlockBackend *blk); bool blk_dev_has_tray(BlockBackend *blk); -- cgit v1.1 From 7ca7f0f6db1fedd28d490795d778cf23979a2aa7 Mon Sep 17 00:00:00 2001 From: Kevin Wolf Date: Tue, 22 Mar 2016 13:00:08 +0100 Subject: block: Decouple throttling from BlockDriverState This moves the throttling related part of the BDS life cycle management to BlockBackend. The throttling group reference is now kept even when no medium is inserted. With this commit, throttling isn't disabled and then re-enabled any more during graph reconfiguration. This fixes the temporary breakage of I/O throttling when used with live snapshots or block jobs that manipulate the graph. Signed-off-by: Kevin Wolf Reviewed-by: Alberto Garcia Acked-by: Stefan Hajnoczi --- include/block/block_int.h | 3 --- 1 file changed, 3 deletions(-) (limited to 'include') diff --git a/include/block/block_int.h b/include/block/block_int.h index a1f8488..db2b4bc 100644 --- a/include/block/block_int.h +++ b/include/block/block_int.h @@ -500,9 +500,6 @@ struct BlockBackendRootState { int open_flags; bool read_only; BlockdevDetectZeroesOptions detect_zeroes; - - char *throttle_group; - ThrottleState *throttle_state; }; static inline BlockDriverState *backing_bs(BlockDriverState *bs) -- cgit v1.1 From 5c8cab48087d3544cb788309ac729bca08244020 Mon Sep 17 00:00:00 2001 From: Kevin Wolf Date: Wed, 24 Feb 2016 15:13:35 +0100 Subject: block: Use BdrvChild callbacks for change_media/resize We want to get rid of BlockDriverState.blk in order to allow multiple BlockBackends per BDS. Converting the device callbacks in block.c (which assume a single BlockBackend) to per-child callbacks gets us rid of the first few instances. Signed-off-by: Kevin Wolf Reviewed-by: Max Reitz --- include/block/block_int.h | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) (limited to 'include') diff --git a/include/block/block_int.h b/include/block/block_int.h index db2b4bc..9555429 100644 --- a/include/block/block_int.h +++ b/include/block/block_int.h @@ -365,6 +365,9 @@ struct BdrvChildRole { void (*inherit_options)(int *child_flags, QDict *child_options, int parent_flags, QDict *parent_options); + void (*change_media)(BdrvChild *child, bool load); + void (*resize)(BdrvChild *child); + /* * If this pair of functions is implemented, the parent doesn't issue new * requests after returning from .drained_begin() until .drained_end() is @@ -722,7 +725,6 @@ bool blk_dev_has_tray(BlockBackend *blk); void blk_dev_eject_request(BlockBackend *blk, bool force); bool blk_dev_is_tray_open(BlockBackend *blk); bool blk_dev_is_medium_locked(BlockBackend *blk); -void blk_dev_resize_cb(BlockBackend *blk); void bdrv_set_dirty(BlockDriverState *bs, int64_t cur_sector, int nr_sectors); bool bdrv_requests_pending(BlockDriverState *bs); -- cgit v1.1 From 4c265bf9f434d4b47f42e3c079adc205b7625ad6 Mon Sep 17 00:00:00 2001 From: Kevin Wolf Date: Fri, 26 Feb 2016 10:22:16 +0100 Subject: block: User BdrvChild callback for device name In order to get rid of bs->blk for bdrv_get_device_name() and bdrv_get_device_or_node_name(), ask all parents for their name and simply pick the first one. Signed-off-by: Kevin Wolf Reviewed-by: Max Reitz --- include/block/block_int.h | 5 +++++ 1 file changed, 5 insertions(+) (limited to 'include') diff --git a/include/block/block_int.h b/include/block/block_int.h index 9555429..80e2da5 100644 --- a/include/block/block_int.h +++ b/include/block/block_int.h @@ -368,6 +368,11 @@ struct BdrvChildRole { void (*change_media)(BdrvChild *child, bool load); void (*resize)(BdrvChild *child); + /* Returns a name that is supposedly more useful for human users than the + * node name for identifying the node in question (in particular, a BB + * name), or NULL if the parent can't provide a better name. */ + const char* (*get_name)(BdrvChild *child); + /* * If this pair of functions is implemented, the parent doesn't issue new * requests after returning from .drained_begin() until .drained_end() is -- cgit v1.1 From 81e254dc8349795d17c585a997f9076b77a863fc Mon Sep 17 00:00:00 2001 From: Kevin Wolf Date: Mon, 18 Apr 2016 11:36:38 +0200 Subject: blockjob: Don't set iostatus of target When block job errors were introduced, we assigned the iostatus of the target BDS "just in case". The field has never been accessible for the user because the target isn't listed in query-block. Before we can allow the user to have a second BlockBackend on the target, we need to clean this up. If anything, we would want to set the iostatus for the internal BB of the job (which we can always do later), but certainly not for a separate BB which the job doesn't even use. As a nice side effect, this gets us rid of another bs->blk use. Signed-off-by: Kevin Wolf Reviewed-by: Max Reitz --- include/block/blockjob.h | 4 +--- 1 file changed, 1 insertion(+), 3 deletions(-) (limited to 'include') diff --git a/include/block/blockjob.h b/include/block/blockjob.h index 8bedc49..073a433 100644 --- a/include/block/blockjob.h +++ b/include/block/blockjob.h @@ -383,7 +383,6 @@ void block_job_iostatus_reset(BlockJob *job); /** * block_job_error_action: * @job: The job to signal an error for. - * @bs: The block device on which to set an I/O error. * @on_err: The error action setting. * @is_read: Whether the operation was a read. * @error: The error that was reported. @@ -391,8 +390,7 @@ void block_job_iostatus_reset(BlockJob *job); * Report an I/O error for a block job and possibly stop the VM. Return the * action that was selected based on @on_err and @error. */ -BlockErrorAction block_job_error_action(BlockJob *job, BlockDriverState *bs, - BlockdevOnError on_err, +BlockErrorAction block_job_error_action(BlockJob *job, BlockdevOnError on_err, int is_read, int error); typedef void BlockJobDeferToMainLoopFn(BlockJob *job, void *opaque); -- cgit v1.1 From 91c6e4b7bba906cfb8d84481da6340957f876c90 Mon Sep 17 00:00:00 2001 From: Kevin Wolf Date: Fri, 26 Feb 2016 13:50:43 +0100 Subject: block: Remove bdrv_aio_multiwrite() Since virtio-blk implements request merging itself these days, the only remaining users are test cases for the function. That doesn't make the function exactly useful any more. Signed-off-by: Kevin Wolf Reviewed-by: Max Reitz Reviewed-by: Eric Blake --- include/block/block.h | 7 ++----- include/sysemu/block-backend.h | 1 - 2 files changed, 2 insertions(+), 6 deletions(-) (limited to 'include') diff --git a/include/block/block.h b/include/block/block.h index 2c5c280..d1f9380 100644 --- a/include/block/block.h +++ b/include/block/block.h @@ -329,7 +329,7 @@ void bdrv_aio_cancel(BlockAIOCB *acb); void bdrv_aio_cancel_async(BlockAIOCB *acb); typedef struct BlockRequest { - /* Fields to be filled by multiwrite caller */ + /* Fields to be filled by caller */ union { struct { int64_t sector; @@ -345,13 +345,10 @@ typedef struct BlockRequest { BlockCompletionFunc *cb; void *opaque; - /* Filled by multiwrite implementation */ + /* Filled by block layer */ int error; } BlockRequest; -int bdrv_aio_multiwrite(BlockDriverState *bs, BlockRequest *reqs, - int num_reqs); - /* sg packet commands */ int bdrv_ioctl(BlockDriverState *bs, unsigned long int req, void *buf); BlockAIOCB *bdrv_aio_ioctl(BlockDriverState *bs, diff --git a/include/sysemu/block-backend.h b/include/sysemu/block-backend.h index dd9c8ca..79f39b8 100644 --- a/include/sysemu/block-backend.h +++ b/include/sysemu/block-backend.h @@ -138,7 +138,6 @@ BlockAIOCB *blk_aio_discard(BlockBackend *blk, BlockCompletionFunc *cb, void *opaque); void blk_aio_cancel(BlockAIOCB *acb); void blk_aio_cancel_async(BlockAIOCB *acb); -int blk_aio_multiwrite(BlockBackend *blk, BlockRequest *reqs, int num_reqs); int blk_ioctl(BlockBackend *blk, unsigned long int req, void *buf); BlockAIOCB *blk_aio_ioctl(BlockBackend *blk, unsigned long int req, void *buf, BlockCompletionFunc *cb, void *opaque); -- cgit v1.1 From dde33812a83b9c55b180a85411bfc4d6c39e8b11 Mon Sep 17 00:00:00 2001 From: Kevin Wolf Date: Mon, 29 Feb 2016 10:50:38 +0100 Subject: block: Add bdrv_has_blk() In many cases we just want to know whether a BDS has at least one BB attached, without needing to know the exact BB that is attached. In contrast to bs->blk, this is still a valid question when more than one BB can be attached, so just answer it by checking the parents list. Signed-off-by: Kevin Wolf Reviewed-by: Max Reitz --- include/sysemu/block-backend.h | 1 + 1 file changed, 1 insertion(+) (limited to 'include') diff --git a/include/sysemu/block-backend.h b/include/sysemu/block-backend.h index 79f39b8..44a222d8 100644 --- a/include/sysemu/block-backend.h +++ b/include/sysemu/block-backend.h @@ -99,6 +99,7 @@ BlockBackend *blk_by_public(BlockBackendPublic *public); BlockDriverState *blk_bs(BlockBackend *blk); void blk_remove_bs(BlockBackend *blk); void blk_insert_bs(BlockBackend *blk, BlockDriverState *bs); +bool bdrv_has_blk(BlockDriverState *bs); void blk_set_allow_write_beyond_eof(BlockBackend *blk, bool allow); void blk_iostatus_enable(BlockBackend *blk); -- cgit v1.1 From 7c8eece45b10fc9b716850345118ed6fa8d17887 Mon Sep 17 00:00:00 2001 From: Kevin Wolf Date: Tue, 22 Mar 2016 18:58:50 +0100 Subject: block: Avoid bs->blk in bdrv_next() We need to introduce a separate BdrvNextIterator struct that can keep more state than just the current BDS in order to avoid using the bs->blk pointer. Signed-off-by: Kevin Wolf Reviewed-by: Max Reitz --- include/block/block.h | 3 ++- include/sysemu/block-backend.h | 1 - 2 files changed, 2 insertions(+), 2 deletions(-) (limited to 'include') diff --git a/include/block/block.h b/include/block/block.h index d1f9380..a8c15e3 100644 --- a/include/block/block.h +++ b/include/block/block.h @@ -17,6 +17,7 @@ typedef struct BlockJob BlockJob; typedef struct BdrvChild BdrvChild; typedef struct BdrvChildRole BdrvChildRole; typedef struct BlockJobTxn BlockJobTxn; +typedef struct BdrvNextIterator BdrvNextIterator; typedef struct BlockDriverInfo { /* in bytes, 0 if irrelevant */ @@ -401,7 +402,7 @@ BlockDriverState *bdrv_lookup_bs(const char *device, Error **errp); bool bdrv_chain_contains(BlockDriverState *top, BlockDriverState *base); BlockDriverState *bdrv_next_node(BlockDriverState *bs); -BlockDriverState *bdrv_next(BlockDriverState *bs); +BdrvNextIterator *bdrv_next(BdrvNextIterator *it, BlockDriverState **bs); BlockDriverState *bdrv_next_monitor_owned(BlockDriverState *bs); int bdrv_is_encrypted(BlockDriverState *bs); int bdrv_key_required(BlockDriverState *bs); diff --git a/include/sysemu/block-backend.h b/include/sysemu/block-backend.h index 44a222d8..68d92b5 100644 --- a/include/sysemu/block-backend.h +++ b/include/sysemu/block-backend.h @@ -89,7 +89,6 @@ void blk_remove_all_bs(void); const char *blk_name(BlockBackend *blk); BlockBackend *blk_by_name(const char *name); BlockBackend *blk_next(BlockBackend *blk); -BlockDriverState *blk_next_root_bs(BlockDriverState *bs); bool monitor_add_blk(BlockBackend *blk, const char *name, Error **errp); void monitor_remove_blk(BlockBackend *blk); -- cgit v1.1 From 1f0c461b82d5ec2664ca0cfc9548f80da87a8f8a Mon Sep 17 00:00:00 2001 From: Kevin Wolf Date: Tue, 22 Mar 2016 18:38:44 +0100 Subject: block: Remove BlockDriverState.blk This patch removes the remaining users of bs->blk, which will allow us to have multiple BBs on top of a single BDS. In the meantime, all checks that are currently in place to prevent the user from creating such setups can be switched to bdrv_has_blk() instead of accessing BDS.blk. Future patches can allow them and e.g. enable users to mirror to a block device that already has a BlockBackend on it. Signed-off-by: Kevin Wolf Reviewed-by: Max Reitz --- include/block/block_int.h | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) (limited to 'include') diff --git a/include/block/block_int.h b/include/block/block_int.h index 80e2da5..b6f4755 100644 --- a/include/block/block_int.h +++ b/include/block/block_int.h @@ -418,8 +418,6 @@ struct BlockDriverState { BlockDriver *drv; /* NULL means no media */ void *opaque; - BlockBackend *blk; /* owning backend, if any */ - AioContext *aio_context; /* event loop used for fd handlers, timers, etc */ /* long-running tasks intended to always use the same AioContext as this * BDS may register themselves in this list to be notified of changes @@ -724,6 +722,7 @@ BdrvChild *bdrv_root_attach_child(BlockDriverState *child_bs, const BdrvChildRole *child_role); void bdrv_root_unref_child(BdrvChild *child); +const char *bdrv_get_parent_name(const BlockDriverState *bs); void blk_dev_change_media_cb(BlockBackend *blk, bool load); bool blk_dev_has_removable_media(BlockBackend *blk); bool blk_dev_has_tray(BlockBackend *blk); -- cgit v1.1