mirror of
https://github.com/izzy2lost/xemu.git
synced 2026-07-06 00:20:22 -07:00
Merge tag 'for-upstream' of https://repo.or.cz/qemu/kevin into staging
Block layer patches - Graph locking, part 3 (more block drivers) - Compile out assert_bdrv_graph_readable() by default - Add configure options for vmdk, vhdx and vpc - Fix use after free in blockdev_mark_auto_del() - migration: Attempt disk reactivation in more failure scenarios - Coroutine correctness fixes # -----BEGIN PGP SIGNATURE----- # # iQJFBAABCAAvFiEE3D3rFZqa+V09dFb+fwmycsiPL9YFAmRbi6ERHGt3b2xmQHJl # ZGhhdC5jb20ACgkQfwmycsiPL9Y66A//ZRk/0M6EZUJPAKG6m/XLTDNrOCNBZ1Tu # kBGvxXsVQZMt4gGpBad4l2INN6IQKTIdIf+lK71EpxMPmFG6xK32btn38yywCAfQ # lr1p5nR0Y/zSlT+XzP4yKy/CtQl6U0rkysmjCIk35bZc7uLy6eo4oFR4vmhRRt2M # UGltB50/Nicx12YFufVjodbhv+apxTGwS2XHatmwqtjKeYReSz8mJHslEy6DvC8m # ziNThD6YBy7hMktAhNaqUqtZD0OSWz66VMObco/4i2++sOAMZIspXQkjv3AjH74e # lmgMhNc/xgJKPwFBPsj6F7dOKxwhdKD9jzZlx3yaBtAU18hpWX54QWuA3/CFlySc # 5QbbqIstFTC8lqoRWThQrcHHRKbDBJCP4ImRXUIKhuPaxEzXA9zb3+f3QPTIjLSA # KO7nxuSmO+tC7hQ1K9kAjRZHWlxxAk4clk+7UrK4UrWgGxfCUKgFg4Tyx7RrpwA6 # j4L5vwAY60LW74tikWe9xJx2QbdRoWBTTZhUyirbO7rLX1e8mS1nUWmtIsFSQxAq # Z7nX7ygN0WEF+8qIsk3jTGaEeJoCM7+7B+X2RpSy0sftFjFYmybIiUgLMO7e+ozK # rvUPnwlHAbGCVIJOKrUDj3cGt6k3/xnrTajUc7pCB3KKqG4pe+IlZuHyKIUMActb # dBLaBnj0M2o= # =hw9E # -----END PGP SIGNATURE----- # gpg: Signature made Wed 10 May 2023 01:18:41 PM BST # gpg: using RSA key DC3DEB159A9AF95D3D7456FE7F09B272C88F2FD6 # gpg: issuer "kwolf@redhat.com" # gpg: Good signature from "Kevin Wolf <kwolf@redhat.com>" [full] * tag 'for-upstream' of https://repo.or.cz/qemu/kevin: (28 commits) block: compile out assert_bdrv_graph_readable() by default block: Mark bdrv_refresh_limits() and callers GRAPH_RDLOCK block: Mark bdrv_recurse_can_replace() and callers GRAPH_RDLOCK block: Mark bdrv_query_block_graph_info() and callers GRAPH_RDLOCK block: Mark bdrv_query_bds_stats() and callers GRAPH_RDLOCK block: Mark BlockDriver callbacks for amend job GRAPH_RDLOCK block: Mark bdrv_co_debug_event() GRAPH_RDLOCK block: Mark bdrv_co_get_info() and callers GRAPH_RDLOCK block: Mark bdrv_co_get_allocated_file_size() and callers GRAPH_RDLOCK mirror: Require GRAPH_RDLOCK for accessing a node's parent list vhdx: Require GRAPH_RDLOCK for accessing a node's parent list nbd: Mark nbd_co_do_establish_connection() and callers GRAPH_RDLOCK nbd: Remove nbd_co_flush() wrapper function block: .bdrv_open is non-coroutine and unlocked graph-lock: Fix GRAPH_RDLOCK_GUARD*() to be reader lock graph-lock: Add GRAPH_UNLOCKED(_PTR) test-bdrv-drain: Don't modify the graph in coroutines iotests: Test resizing image attached to an iothread block: Don't call no_coroutine_fns in qmp_block_resize() block: bdrv/blk_co_unref() for calls in coroutine context ... Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
This commit is contained in:
@@ -680,7 +680,7 @@ int coroutine_fn bdrv_co_create_opts_simple(BlockDriver *drv,
|
||||
|
||||
ret = 0;
|
||||
out:
|
||||
blk_unref(blk);
|
||||
blk_co_unref(blk);
|
||||
return ret;
|
||||
}
|
||||
|
||||
@@ -1610,9 +1610,9 @@ out:
|
||||
* bdrv_refresh_total_sectors() which polls when called from non-coroutine
|
||||
* context.
|
||||
*/
|
||||
static int bdrv_open_driver(BlockDriverState *bs, BlockDriver *drv,
|
||||
const char *node_name, QDict *options,
|
||||
int open_flags, Error **errp)
|
||||
static int no_coroutine_fn GRAPH_UNLOCKED
|
||||
bdrv_open_driver(BlockDriverState *bs, BlockDriver *drv, const char *node_name,
|
||||
QDict *options, int open_flags, Error **errp)
|
||||
{
|
||||
Error *local_err = NULL;
|
||||
int i, ret;
|
||||
@@ -1667,7 +1667,10 @@ static int bdrv_open_driver(BlockDriverState *bs, BlockDriver *drv,
|
||||
return ret;
|
||||
}
|
||||
|
||||
bdrv_graph_rdlock_main_loop();
|
||||
bdrv_refresh_limits(bs, NULL, &local_err);
|
||||
bdrv_graph_rdunlock_main_loop();
|
||||
|
||||
if (local_err) {
|
||||
error_propagate(errp, local_err);
|
||||
return -EINVAL;
|
||||
@@ -3419,7 +3422,9 @@ static int bdrv_set_file_or_backing_noperm(BlockDriverState *parent_bs,
|
||||
}
|
||||
|
||||
out:
|
||||
bdrv_graph_rdlock_main_loop();
|
||||
bdrv_refresh_limits(parent_bs, tran, NULL);
|
||||
bdrv_graph_rdunlock_main_loop();
|
||||
|
||||
return 0;
|
||||
}
|
||||
@@ -4917,7 +4922,9 @@ static void bdrv_reopen_commit(BDRVReopenState *reopen_state)
|
||||
qdict_del(bs->explicit_options, "backing");
|
||||
qdict_del(bs->options, "backing");
|
||||
|
||||
bdrv_graph_rdlock_main_loop();
|
||||
bdrv_refresh_limits(bs, NULL, NULL);
|
||||
bdrv_graph_rdunlock_main_loop();
|
||||
bdrv_refresh_total_sectors(bs, bs->total_sectors);
|
||||
}
|
||||
|
||||
@@ -5316,7 +5323,9 @@ int bdrv_append(BlockDriverState *bs_new, BlockDriverState *bs_top,
|
||||
out:
|
||||
tran_finalize(tran, ret);
|
||||
|
||||
bdrv_graph_rdlock_main_loop();
|
||||
bdrv_refresh_limits(bs_top, NULL, NULL);
|
||||
bdrv_graph_rdunlock_main_loop();
|
||||
|
||||
if (new_context && old_context != new_context) {
|
||||
aio_context_release(new_context);
|
||||
@@ -5750,7 +5759,8 @@ exit:
|
||||
* sums the size of all data-bearing children. (This excludes backing
|
||||
* children.)
|
||||
*/
|
||||
static int64_t coroutine_fn bdrv_sum_allocated_file_size(BlockDriverState *bs)
|
||||
static int64_t coroutine_fn GRAPH_RDLOCK
|
||||
bdrv_sum_allocated_file_size(BlockDriverState *bs)
|
||||
{
|
||||
BdrvChild *child;
|
||||
int64_t child_size, sum = 0;
|
||||
@@ -5778,6 +5788,7 @@ int64_t coroutine_fn bdrv_co_get_allocated_file_size(BlockDriverState *bs)
|
||||
{
|
||||
BlockDriver *drv = bs->drv;
|
||||
IO_CODE();
|
||||
assert_bdrv_graph_readable();
|
||||
|
||||
if (!drv) {
|
||||
return -ENOMEDIUM;
|
||||
@@ -6347,6 +6358,8 @@ int coroutine_fn bdrv_co_get_info(BlockDriverState *bs, BlockDriverInfo *bdi)
|
||||
int ret;
|
||||
BlockDriver *drv = bs->drv;
|
||||
IO_CODE();
|
||||
assert_bdrv_graph_readable();
|
||||
|
||||
/* if bs->drv == NULL, bs is closed, so there's nothing to do here */
|
||||
if (!drv) {
|
||||
return -ENOMEDIUM;
|
||||
@@ -6395,6 +6408,8 @@ BlockStatsSpecific *bdrv_get_specific_stats(BlockDriverState *bs)
|
||||
void coroutine_fn bdrv_co_debug_event(BlockDriverState *bs, BlkdebugEvent event)
|
||||
{
|
||||
IO_CODE();
|
||||
assert_bdrv_graph_readable();
|
||||
|
||||
if (!bs || !bs->drv || !bs->drv->bdrv_co_debug_event) {
|
||||
return;
|
||||
}
|
||||
|
||||
+7
-1
@@ -46,6 +46,7 @@ static int coroutine_fn blockdev_amend_run(Job *job, Error **errp)
|
||||
{
|
||||
BlockdevAmendJob *s = container_of(job, BlockdevAmendJob, common);
|
||||
int ret;
|
||||
GRAPH_RDLOCK_GUARD();
|
||||
|
||||
job_progress_set_remaining(&s->common, 1);
|
||||
ret = s->bs->drv->bdrv_co_amend(s->bs, s->opts, s->force, errp);
|
||||
@@ -54,7 +55,8 @@ static int coroutine_fn blockdev_amend_run(Job *job, Error **errp)
|
||||
return ret;
|
||||
}
|
||||
|
||||
static int blockdev_amend_pre_run(BlockdevAmendJob *s, Error **errp)
|
||||
static int GRAPH_RDLOCK
|
||||
blockdev_amend_pre_run(BlockdevAmendJob *s, Error **errp)
|
||||
{
|
||||
if (s->bs->drv->bdrv_amend_pre_run) {
|
||||
return s->bs->drv->bdrv_amend_pre_run(s->bs, errp);
|
||||
@@ -67,9 +69,11 @@ static void blockdev_amend_free(Job *job)
|
||||
{
|
||||
BlockdevAmendJob *s = container_of(job, BlockdevAmendJob, common);
|
||||
|
||||
bdrv_graph_rdlock_main_loop();
|
||||
if (s->bs->drv->bdrv_amend_clean) {
|
||||
s->bs->drv->bdrv_amend_clean(s->bs);
|
||||
}
|
||||
bdrv_graph_rdunlock_main_loop();
|
||||
|
||||
bdrv_unref(s->bs);
|
||||
}
|
||||
@@ -93,6 +97,8 @@ void qmp_x_blockdev_amend(const char *job_id,
|
||||
BlockDriver *drv = bdrv_find_format(fmt);
|
||||
BlockDriverState *bs;
|
||||
|
||||
GRAPH_RDLOCK_GUARD_MAINLOOP();
|
||||
|
||||
bs = bdrv_lookup_bs(NULL, node_name, errp);
|
||||
if (!bs) {
|
||||
return;
|
||||
|
||||
+3
-2
@@ -265,8 +265,9 @@ static int coroutine_fn GRAPH_RDLOCK blkverify_co_flush(BlockDriverState *bs)
|
||||
return bdrv_co_flush(s->test_file->bs);
|
||||
}
|
||||
|
||||
static bool blkverify_recurse_can_replace(BlockDriverState *bs,
|
||||
BlockDriverState *to_replace)
|
||||
static bool GRAPH_RDLOCK
|
||||
blkverify_recurse_can_replace(BlockDriverState *bs,
|
||||
BlockDriverState *to_replace)
|
||||
{
|
||||
BDRVBlkverifyState *s = bs->opaque;
|
||||
|
||||
|
||||
@@ -2024,7 +2024,15 @@ void blk_activate(BlockBackend *blk, Error **errp)
|
||||
return;
|
||||
}
|
||||
|
||||
bdrv_activate(bs, errp);
|
||||
/*
|
||||
* Migration code can call this function in coroutine context, so leave
|
||||
* coroutine context if necessary.
|
||||
*/
|
||||
if (qemu_in_coroutine()) {
|
||||
bdrv_co_activate(bs, errp);
|
||||
} else {
|
||||
bdrv_activate(bs, errp);
|
||||
}
|
||||
}
|
||||
|
||||
bool coroutine_fn blk_co_is_inserted(BlockBackend *blk)
|
||||
|
||||
+3
-2
@@ -61,7 +61,7 @@ bdrv_co_readv_vmstate(BlockDriverState *bs, QEMUIOVector *qiov, int64_t pos);
|
||||
int coroutine_fn GRAPH_RDLOCK
|
||||
bdrv_co_writev_vmstate(BlockDriverState *bs, QEMUIOVector *qiov, int64_t pos);
|
||||
|
||||
int coroutine_fn
|
||||
int coroutine_fn GRAPH_RDLOCK
|
||||
nbd_co_do_establish_connection(BlockDriverState *bs, bool blocking,
|
||||
Error **errp);
|
||||
|
||||
@@ -85,7 +85,8 @@ bdrv_common_block_status_above(BlockDriverState *bs,
|
||||
int64_t *map,
|
||||
BlockDriverState **file,
|
||||
int *depth);
|
||||
int co_wrapper_mixed
|
||||
|
||||
int co_wrapper_mixed_bdrv_rdlock
|
||||
nbd_do_establish_connection(BlockDriverState *bs, bool blocking, Error **errp);
|
||||
|
||||
#endif /* BLOCK_COROUTINES_H */
|
||||
|
||||
+4
-4
@@ -355,7 +355,7 @@ block_crypto_co_create_generic(BlockDriverState *bs, int64_t size,
|
||||
ret = 0;
|
||||
cleanup:
|
||||
qcrypto_block_free(crypto);
|
||||
blk_unref(blk);
|
||||
blk_co_unref(blk);
|
||||
return ret;
|
||||
}
|
||||
|
||||
@@ -661,7 +661,7 @@ block_crypto_co_create_luks(BlockdevCreateOptions *create_options, Error **errp)
|
||||
|
||||
ret = 0;
|
||||
fail:
|
||||
bdrv_unref(bs);
|
||||
bdrv_co_unref(bs);
|
||||
return ret;
|
||||
}
|
||||
|
||||
@@ -730,13 +730,13 @@ fail:
|
||||
bdrv_co_delete_file_noerr(bs);
|
||||
}
|
||||
|
||||
bdrv_unref(bs);
|
||||
bdrv_co_unref(bs);
|
||||
qapi_free_QCryptoBlockCreateOptions(create_opts);
|
||||
qobject_unref(cryptoopts);
|
||||
return ret;
|
||||
}
|
||||
|
||||
static int coroutine_fn
|
||||
static int coroutine_fn GRAPH_RDLOCK
|
||||
block_crypto_co_get_info_luks(BlockDriverState *bs, BlockDriverInfo *bdi)
|
||||
{
|
||||
BlockDriverInfo subbdi;
|
||||
|
||||
@@ -265,7 +265,10 @@ void bdrv_graph_rdunlock_main_loop(void)
|
||||
|
||||
void assert_bdrv_graph_readable(void)
|
||||
{
|
||||
/* reader_count() is slow due to aio_context_list_lock lock contention */
|
||||
#ifdef CONFIG_DEBUG_GRAPH_LOCK
|
||||
assert(qemu_in_main_thread() || reader_count());
|
||||
#endif
|
||||
}
|
||||
|
||||
void assert_bdrv_graph_writable(void)
|
||||
|
||||
+5
-7
@@ -160,7 +160,6 @@ void bdrv_refresh_limits(BlockDriverState *bs, Transaction *tran, Error **errp)
|
||||
bool have_limits;
|
||||
|
||||
GLOBAL_STATE_CODE();
|
||||
assume_graph_lock(); /* FIXME */
|
||||
|
||||
if (tran) {
|
||||
BdrvRefreshLimitsState *s = g_new(BdrvRefreshLimitsState, 1);
|
||||
@@ -727,10 +726,9 @@ BdrvTrackedRequest *coroutine_fn bdrv_co_get_self_request(BlockDriverState *bs)
|
||||
/**
|
||||
* Round a region to cluster boundaries
|
||||
*/
|
||||
void coroutine_fn bdrv_round_to_clusters(BlockDriverState *bs,
|
||||
int64_t offset, int64_t bytes,
|
||||
int64_t *cluster_offset,
|
||||
int64_t *cluster_bytes)
|
||||
void coroutine_fn GRAPH_RDLOCK
|
||||
bdrv_round_to_clusters(BlockDriverState *bs, int64_t offset, int64_t bytes,
|
||||
int64_t *cluster_offset, int64_t *cluster_bytes)
|
||||
{
|
||||
BlockDriverInfo bdi;
|
||||
IO_CODE();
|
||||
@@ -744,7 +742,7 @@ void coroutine_fn bdrv_round_to_clusters(BlockDriverState *bs,
|
||||
}
|
||||
}
|
||||
|
||||
static coroutine_fn int bdrv_get_cluster_size(BlockDriverState *bs)
|
||||
static int coroutine_fn GRAPH_RDLOCK bdrv_get_cluster_size(BlockDriverState *bs)
|
||||
{
|
||||
BlockDriverInfo bdi;
|
||||
int ret;
|
||||
@@ -1800,7 +1798,7 @@ fail:
|
||||
return ret;
|
||||
}
|
||||
|
||||
static inline int coroutine_fn
|
||||
static inline int coroutine_fn GRAPH_RDLOCK
|
||||
bdrv_co_write_req_prepare(BdrvChild *child, int64_t offset, int64_t bytes,
|
||||
BdrvTrackedRequest *req, int flags)
|
||||
{
|
||||
|
||||
+13
-5
@@ -38,11 +38,6 @@ block_ss.add(files(
|
||||
'snapshot-access.c',
|
||||
'throttle-groups.c',
|
||||
'throttle.c',
|
||||
'vhdx-endian.c',
|
||||
'vhdx-log.c',
|
||||
'vhdx.c',
|
||||
'vmdk.c',
|
||||
'vpc.c',
|
||||
'write-threshold.c',
|
||||
), zstd, zlib, gnutls)
|
||||
|
||||
@@ -55,6 +50,19 @@ endif
|
||||
if get_option('vdi').allowed()
|
||||
block_ss.add(files('vdi.c'))
|
||||
endif
|
||||
if get_option('vhdx').allowed()
|
||||
block_ss.add(files(
|
||||
'vhdx-endian.c',
|
||||
'vhdx-log.c',
|
||||
'vhdx.c'
|
||||
))
|
||||
endif
|
||||
if get_option('vmdk').allowed()
|
||||
block_ss.add(files('vmdk.c'))
|
||||
endif
|
||||
if get_option('vpc').allowed()
|
||||
block_ss.add(files('vpc.c'))
|
||||
endif
|
||||
if get_option('cloop').allowed()
|
||||
block_ss.add(files('cloop.c'))
|
||||
endif
|
||||
|
||||
+13
-5
@@ -270,8 +270,8 @@ static inline int64_t mirror_clip_bytes(MirrorBlockJob *s,
|
||||
|
||||
/* Round offset and/or bytes to target cluster if COW is needed, and
|
||||
* return the offset of the adjusted tail against original. */
|
||||
static int mirror_cow_align(MirrorBlockJob *s, int64_t *offset,
|
||||
uint64_t *bytes)
|
||||
static int coroutine_fn mirror_cow_align(MirrorBlockJob *s, int64_t *offset,
|
||||
uint64_t *bytes)
|
||||
{
|
||||
bool need_cow;
|
||||
int ret = 0;
|
||||
@@ -576,8 +576,10 @@ static uint64_t coroutine_fn mirror_iteration(MirrorBlockJob *s)
|
||||
} else if (ret >= 0 && !(ret & BDRV_BLOCK_DATA)) {
|
||||
int64_t target_offset;
|
||||
int64_t target_bytes;
|
||||
bdrv_round_to_clusters(blk_bs(s->target), offset, io_bytes,
|
||||
&target_offset, &target_bytes);
|
||||
WITH_GRAPH_RDLOCK_GUARD() {
|
||||
bdrv_round_to_clusters(blk_bs(s->target), offset, io_bytes,
|
||||
&target_offset, &target_bytes);
|
||||
}
|
||||
if (target_offset == offset &&
|
||||
target_bytes == io_bytes) {
|
||||
mirror_method = ret & BDRV_BLOCK_ZERO ?
|
||||
@@ -745,7 +747,10 @@ static int mirror_exit_common(Job *job)
|
||||
* Cannot use check_to_replace_node() here, because that would
|
||||
* check for an op blocker on @to_replace, and we have our own
|
||||
* there.
|
||||
*
|
||||
* TODO Pull out the writer lock from bdrv_replace_node() to here
|
||||
*/
|
||||
bdrv_graph_rdlock_main_loop();
|
||||
if (bdrv_recurse_can_replace(src, to_replace)) {
|
||||
bdrv_replace_node(to_replace, target_bs, &local_err);
|
||||
} else {
|
||||
@@ -754,6 +759,7 @@ static int mirror_exit_common(Job *job)
|
||||
"would not lead to an abrupt change of visible data",
|
||||
to_replace->node_name, target_bs->node_name);
|
||||
}
|
||||
bdrv_graph_rdunlock_main_loop();
|
||||
bdrv_drained_end(target_bs);
|
||||
if (local_err) {
|
||||
error_report_err(local_err);
|
||||
@@ -966,11 +972,13 @@ static int coroutine_fn mirror_run(Job *job, Error **errp)
|
||||
*/
|
||||
bdrv_get_backing_filename(target_bs, backing_filename,
|
||||
sizeof(backing_filename));
|
||||
bdrv_graph_co_rdlock();
|
||||
if (!bdrv_co_get_info(target_bs, &bdi) && bdi.cluster_size) {
|
||||
s->target_cluster_size = bdi.cluster_size;
|
||||
} else {
|
||||
s->target_cluster_size = BDRV_SECTOR_SIZE;
|
||||
}
|
||||
bdrv_graph_co_rdunlock();
|
||||
if (backing_filename[0] && !bdrv_backing_chain_next(target_bs) &&
|
||||
s->granularity < s->target_cluster_size) {
|
||||
s->buf_size = MAX(s->buf_size, s->target_cluster_size);
|
||||
@@ -1416,7 +1424,7 @@ static MirrorOp *coroutine_fn active_write_prepare(MirrorBlockJob *s,
|
||||
return op;
|
||||
}
|
||||
|
||||
static void coroutine_fn active_write_settle(MirrorOp *op)
|
||||
static void coroutine_fn GRAPH_RDLOCK active_write_settle(MirrorOp *op)
|
||||
{
|
||||
uint64_t start_chunk = op->offset / op->s->granularity;
|
||||
uint64_t end_chunk = DIV_ROUND_UP(op->offset + op->bytes,
|
||||
|
||||
+24
-26
@@ -322,6 +322,7 @@ int coroutine_fn nbd_co_do_establish_connection(BlockDriverState *bs,
|
||||
int ret;
|
||||
IO_CODE();
|
||||
|
||||
assert_bdrv_graph_readable();
|
||||
assert(!s->ioc);
|
||||
|
||||
s->ioc = nbd_co_establish_connection(s->conn, &s->info, blocking, errp);
|
||||
@@ -369,7 +370,7 @@ static bool nbd_client_connecting(BDRVNBDState *s)
|
||||
}
|
||||
|
||||
/* Called with s->requests_lock taken. */
|
||||
static coroutine_fn void nbd_reconnect_attempt(BDRVNBDState *s)
|
||||
static void coroutine_fn GRAPH_RDLOCK nbd_reconnect_attempt(BDRVNBDState *s)
|
||||
{
|
||||
int ret;
|
||||
bool blocking = s->state == NBD_CLIENT_CONNECTING_WAIT;
|
||||
@@ -480,9 +481,9 @@ static coroutine_fn int nbd_receive_replies(BDRVNBDState *s, uint64_t handle)
|
||||
}
|
||||
}
|
||||
|
||||
static int coroutine_fn nbd_co_send_request(BlockDriverState *bs,
|
||||
NBDRequest *request,
|
||||
QEMUIOVector *qiov)
|
||||
static int coroutine_fn GRAPH_RDLOCK
|
||||
nbd_co_send_request(BlockDriverState *bs, NBDRequest *request,
|
||||
QEMUIOVector *qiov)
|
||||
{
|
||||
BDRVNBDState *s = (BDRVNBDState *)bs->opaque;
|
||||
int rc, i = -1;
|
||||
@@ -1171,8 +1172,9 @@ static int coroutine_fn nbd_co_receive_blockstatus_reply(BDRVNBDState *s,
|
||||
return iter.ret;
|
||||
}
|
||||
|
||||
static int coroutine_fn nbd_co_request(BlockDriverState *bs, NBDRequest *request,
|
||||
QEMUIOVector *write_qiov)
|
||||
static int coroutine_fn GRAPH_RDLOCK
|
||||
nbd_co_request(BlockDriverState *bs, NBDRequest *request,
|
||||
QEMUIOVector *write_qiov)
|
||||
{
|
||||
int ret, request_ret;
|
||||
Error *local_err = NULL;
|
||||
@@ -1208,9 +1210,9 @@ static int coroutine_fn nbd_co_request(BlockDriverState *bs, NBDRequest *request
|
||||
return ret ? ret : request_ret;
|
||||
}
|
||||
|
||||
static int coroutine_fn nbd_client_co_preadv(BlockDriverState *bs, int64_t offset,
|
||||
int64_t bytes, QEMUIOVector *qiov,
|
||||
BdrvRequestFlags flags)
|
||||
static int coroutine_fn GRAPH_RDLOCK
|
||||
nbd_client_co_preadv(BlockDriverState *bs, int64_t offset, int64_t bytes,
|
||||
QEMUIOVector *qiov, BdrvRequestFlags flags)
|
||||
{
|
||||
int ret, request_ret;
|
||||
Error *local_err = NULL;
|
||||
@@ -1266,9 +1268,9 @@ static int coroutine_fn nbd_client_co_preadv(BlockDriverState *bs, int64_t offse
|
||||
return ret ? ret : request_ret;
|
||||
}
|
||||
|
||||
static int coroutine_fn nbd_client_co_pwritev(BlockDriverState *bs, int64_t offset,
|
||||
int64_t bytes, QEMUIOVector *qiov,
|
||||
BdrvRequestFlags flags)
|
||||
static int coroutine_fn GRAPH_RDLOCK
|
||||
nbd_client_co_pwritev(BlockDriverState *bs, int64_t offset, int64_t bytes,
|
||||
QEMUIOVector *qiov, BdrvRequestFlags flags)
|
||||
{
|
||||
BDRVNBDState *s = (BDRVNBDState *)bs->opaque;
|
||||
NBDRequest request = {
|
||||
@@ -1291,8 +1293,9 @@ static int coroutine_fn nbd_client_co_pwritev(BlockDriverState *bs, int64_t offs
|
||||
return nbd_co_request(bs, &request, qiov);
|
||||
}
|
||||
|
||||
static int coroutine_fn nbd_client_co_pwrite_zeroes(BlockDriverState *bs, int64_t offset,
|
||||
int64_t bytes, BdrvRequestFlags flags)
|
||||
static int coroutine_fn GRAPH_RDLOCK
|
||||
nbd_client_co_pwrite_zeroes(BlockDriverState *bs, int64_t offset, int64_t bytes,
|
||||
BdrvRequestFlags flags)
|
||||
{
|
||||
BDRVNBDState *s = (BDRVNBDState *)bs->opaque;
|
||||
NBDRequest request = {
|
||||
@@ -1326,7 +1329,7 @@ static int coroutine_fn nbd_client_co_pwrite_zeroes(BlockDriverState *bs, int64_
|
||||
return nbd_co_request(bs, &request, NULL);
|
||||
}
|
||||
|
||||
static int coroutine_fn nbd_client_co_flush(BlockDriverState *bs)
|
||||
static int coroutine_fn GRAPH_RDLOCK nbd_client_co_flush(BlockDriverState *bs)
|
||||
{
|
||||
BDRVNBDState *s = (BDRVNBDState *)bs->opaque;
|
||||
NBDRequest request = { .type = NBD_CMD_FLUSH };
|
||||
@@ -1341,8 +1344,8 @@ static int coroutine_fn nbd_client_co_flush(BlockDriverState *bs)
|
||||
return nbd_co_request(bs, &request, NULL);
|
||||
}
|
||||
|
||||
static int coroutine_fn nbd_client_co_pdiscard(BlockDriverState *bs, int64_t offset,
|
||||
int64_t bytes)
|
||||
static int coroutine_fn GRAPH_RDLOCK
|
||||
nbd_client_co_pdiscard(BlockDriverState *bs, int64_t offset, int64_t bytes)
|
||||
{
|
||||
BDRVNBDState *s = (BDRVNBDState *)bs->opaque;
|
||||
NBDRequest request = {
|
||||
@@ -1361,7 +1364,7 @@ static int coroutine_fn nbd_client_co_pdiscard(BlockDriverState *bs, int64_t off
|
||||
return nbd_co_request(bs, &request, NULL);
|
||||
}
|
||||
|
||||
static int coroutine_fn nbd_client_co_block_status(
|
||||
static int coroutine_fn GRAPH_RDLOCK nbd_client_co_block_status(
|
||||
BlockDriverState *bs, bool want_zero, int64_t offset, int64_t bytes,
|
||||
int64_t *pnum, int64_t *map, BlockDriverState **file)
|
||||
{
|
||||
@@ -1920,11 +1923,6 @@ fail:
|
||||
return ret;
|
||||
}
|
||||
|
||||
static int coroutine_fn nbd_co_flush(BlockDriverState *bs)
|
||||
{
|
||||
return nbd_client_co_flush(bs);
|
||||
}
|
||||
|
||||
static void nbd_refresh_limits(BlockDriverState *bs, Error **errp)
|
||||
{
|
||||
BDRVNBDState *s = (BDRVNBDState *)bs->opaque;
|
||||
@@ -2120,7 +2118,7 @@ static BlockDriver bdrv_nbd = {
|
||||
.bdrv_co_pwritev = nbd_client_co_pwritev,
|
||||
.bdrv_co_pwrite_zeroes = nbd_client_co_pwrite_zeroes,
|
||||
.bdrv_close = nbd_close,
|
||||
.bdrv_co_flush_to_os = nbd_co_flush,
|
||||
.bdrv_co_flush_to_os = nbd_client_co_flush,
|
||||
.bdrv_co_pdiscard = nbd_client_co_pdiscard,
|
||||
.bdrv_refresh_limits = nbd_refresh_limits,
|
||||
.bdrv_co_truncate = nbd_co_truncate,
|
||||
@@ -2148,7 +2146,7 @@ static BlockDriver bdrv_nbd_tcp = {
|
||||
.bdrv_co_pwritev = nbd_client_co_pwritev,
|
||||
.bdrv_co_pwrite_zeroes = nbd_client_co_pwrite_zeroes,
|
||||
.bdrv_close = nbd_close,
|
||||
.bdrv_co_flush_to_os = nbd_co_flush,
|
||||
.bdrv_co_flush_to_os = nbd_client_co_flush,
|
||||
.bdrv_co_pdiscard = nbd_client_co_pdiscard,
|
||||
.bdrv_refresh_limits = nbd_refresh_limits,
|
||||
.bdrv_co_truncate = nbd_co_truncate,
|
||||
@@ -2176,7 +2174,7 @@ static BlockDriver bdrv_nbd_unix = {
|
||||
.bdrv_co_pwritev = nbd_client_co_pwritev,
|
||||
.bdrv_co_pwrite_zeroes = nbd_client_co_pwrite_zeroes,
|
||||
.bdrv_close = nbd_close,
|
||||
.bdrv_co_flush_to_os = nbd_co_flush,
|
||||
.bdrv_co_flush_to_os = nbd_client_co_flush,
|
||||
.bdrv_co_pdiscard = nbd_client_co_pdiscard,
|
||||
.bdrv_refresh_limits = nbd_refresh_limits,
|
||||
.bdrv_co_truncate = nbd_co_truncate,
|
||||
|
||||
+3
-3
@@ -613,8 +613,8 @@ static int coroutine_fn parallels_co_create(BlockdevCreateOptions* opts,
|
||||
|
||||
ret = 0;
|
||||
out:
|
||||
blk_unref(blk);
|
||||
bdrv_unref(bs);
|
||||
blk_co_unref(blk);
|
||||
bdrv_co_unref(bs);
|
||||
return ret;
|
||||
|
||||
exit:
|
||||
@@ -691,7 +691,7 @@ parallels_co_create_opts(BlockDriver *drv, const char *filename,
|
||||
|
||||
done:
|
||||
qobject_unref(qdict);
|
||||
bdrv_unref(bs);
|
||||
bdrv_co_unref(bs);
|
||||
qapi_free_BlockdevCreateOptions(create_options);
|
||||
return ret;
|
||||
}
|
||||
|
||||
+4
-2
@@ -604,8 +604,8 @@ static void bdrv_query_blk_stats(BlockDeviceStats *ds, BlockBackend *blk)
|
||||
= bdrv_latency_histogram_stats(&hgram[BLOCK_ACCT_FLUSH]);
|
||||
}
|
||||
|
||||
static BlockStats *bdrv_query_bds_stats(BlockDriverState *bs,
|
||||
bool blk_level)
|
||||
static BlockStats * GRAPH_RDLOCK
|
||||
bdrv_query_bds_stats(BlockDriverState *bs, bool blk_level)
|
||||
{
|
||||
BdrvChild *parent_child;
|
||||
BlockDriverState *filter_or_cow_bs;
|
||||
@@ -713,6 +713,8 @@ BlockStatsList *qmp_query_blockstats(bool has_query_nodes,
|
||||
BlockBackend *blk;
|
||||
BlockDriverState *bs;
|
||||
|
||||
GRAPH_RDLOCK_GUARD_MAINLOOP();
|
||||
|
||||
/* Just to be safe if query_nodes is not always initialized */
|
||||
if (has_query_nodes && query_nodes) {
|
||||
for (bs = bdrv_next_node(NULL); bs; bs = bdrv_next_node(bs)) {
|
||||
|
||||
+3
-3
@@ -915,8 +915,8 @@ static int coroutine_fn qcow_co_create(BlockdevCreateOptions *opts,
|
||||
g_free(tmp);
|
||||
ret = 0;
|
||||
exit:
|
||||
blk_unref(qcow_blk);
|
||||
bdrv_unref(bs);
|
||||
blk_co_unref(qcow_blk);
|
||||
bdrv_co_unref(bs);
|
||||
qcrypto_block_free(crypto);
|
||||
return ret;
|
||||
}
|
||||
@@ -1015,7 +1015,7 @@ qcow_co_create_opts(BlockDriver *drv, const char *filename,
|
||||
fail:
|
||||
g_free(backing_fmt);
|
||||
qobject_unref(qdict);
|
||||
bdrv_unref(bs);
|
||||
bdrv_co_unref(bs);
|
||||
qapi_free_BlockdevCreateOptions(create_options);
|
||||
return ret;
|
||||
}
|
||||
|
||||
@@ -3715,7 +3715,7 @@ int coroutine_fn qcow2_detect_metadata_preallocation(BlockDriverState *bs)
|
||||
|
||||
qemu_co_mutex_assert_locked(&s->lock);
|
||||
|
||||
file_length = bdrv_getlength(bs->file->bs);
|
||||
file_length = bdrv_co_getlength(bs->file->bs);
|
||||
if (file_length < 0) {
|
||||
return file_length;
|
||||
}
|
||||
|
||||
+22
-26
@@ -1891,7 +1891,7 @@ static void coroutine_fn qcow2_open_entry(void *opaque)
|
||||
QCow2OpenCo *qoc = opaque;
|
||||
BDRVQcow2State *s = qoc->bs->opaque;
|
||||
|
||||
assume_graph_lock(); /* FIXME */
|
||||
GRAPH_RDLOCK_GUARD();
|
||||
|
||||
qemu_co_mutex_lock(&s->lock);
|
||||
qoc->ret = qcow2_do_open(qoc->bs, qoc->options, qoc->flags, true,
|
||||
@@ -1920,14 +1920,11 @@ static int qcow2_open(BlockDriverState *bs, QDict *options, int flags,
|
||||
/* Initialise locks */
|
||||
qemu_co_mutex_init(&s->lock);
|
||||
|
||||
if (qemu_in_coroutine()) {
|
||||
/* From bdrv_co_create. */
|
||||
qcow2_open_entry(&qoc);
|
||||
} else {
|
||||
assert(qemu_get_current_aio_context() == qemu_get_aio_context());
|
||||
qemu_coroutine_enter(qemu_coroutine_create(qcow2_open_entry, &qoc));
|
||||
BDRV_POLL_WHILE(bs, qoc.ret == -EINPROGRESS);
|
||||
}
|
||||
assert(!qemu_in_coroutine());
|
||||
assert(qemu_get_current_aio_context() == qemu_get_aio_context());
|
||||
qemu_coroutine_enter(qemu_coroutine_create(qcow2_open_entry, &qoc));
|
||||
BDRV_POLL_WHILE(bs, qoc.ret == -EINPROGRESS);
|
||||
|
||||
return qoc.ret;
|
||||
}
|
||||
|
||||
@@ -2089,11 +2086,10 @@ static void qcow2_join_options(QDict *options, QDict *old_options)
|
||||
}
|
||||
}
|
||||
|
||||
static int coroutine_fn qcow2_co_block_status(BlockDriverState *bs,
|
||||
bool want_zero,
|
||||
int64_t offset, int64_t count,
|
||||
int64_t *pnum, int64_t *map,
|
||||
BlockDriverState **file)
|
||||
static int coroutine_fn GRAPH_RDLOCK
|
||||
qcow2_co_block_status(BlockDriverState *bs, bool want_zero, int64_t offset,
|
||||
int64_t count, int64_t *pnum, int64_t *map,
|
||||
BlockDriverState **file)
|
||||
{
|
||||
BDRVQcow2State *s = bs->opaque;
|
||||
uint64_t host_offset;
|
||||
@@ -3235,7 +3231,7 @@ preallocate_co(BlockDriverState *bs, uint64_t offset, uint64_t new_length,
|
||||
* all of the allocated clusters (otherwise we get failing reads after
|
||||
* EOF). Extend the image to the last allocated sector.
|
||||
*/
|
||||
file_length = bdrv_getlength(s->data_file->bs);
|
||||
file_length = bdrv_co_getlength(s->data_file->bs);
|
||||
if (file_length < 0) {
|
||||
error_setg_errno(errp, -file_length, "Could not get file size");
|
||||
ret = file_length;
|
||||
@@ -3706,7 +3702,7 @@ qcow2_co_create(BlockdevCreateOptions *create_options, Error **errp)
|
||||
goto out;
|
||||
}
|
||||
|
||||
blk_unref(blk);
|
||||
blk_co_unref(blk);
|
||||
blk = NULL;
|
||||
|
||||
/*
|
||||
@@ -3786,7 +3782,7 @@ qcow2_co_create(BlockdevCreateOptions *create_options, Error **errp)
|
||||
}
|
||||
}
|
||||
|
||||
blk_unref(blk);
|
||||
blk_co_unref(blk);
|
||||
blk = NULL;
|
||||
|
||||
/* Reopen the image without BDRV_O_NO_FLUSH to flush it before returning.
|
||||
@@ -3811,9 +3807,9 @@ qcow2_co_create(BlockdevCreateOptions *create_options, Error **errp)
|
||||
|
||||
ret = 0;
|
||||
out:
|
||||
blk_unref(blk);
|
||||
bdrv_unref(bs);
|
||||
bdrv_unref(data_bs);
|
||||
blk_co_unref(blk);
|
||||
bdrv_co_unref(bs);
|
||||
bdrv_co_unref(data_bs);
|
||||
return ret;
|
||||
}
|
||||
|
||||
@@ -3944,8 +3940,8 @@ finish:
|
||||
}
|
||||
|
||||
qobject_unref(qdict);
|
||||
bdrv_unref(bs);
|
||||
bdrv_unref(data_bs);
|
||||
bdrv_co_unref(bs);
|
||||
bdrv_co_unref(data_bs);
|
||||
qapi_free_BlockdevCreateOptions(create_options);
|
||||
return ret;
|
||||
}
|
||||
@@ -4098,7 +4094,7 @@ qcow2_co_copy_range_from(BlockDriverState *bs,
|
||||
case QCOW2_SUBCLUSTER_UNALLOCATED_PLAIN:
|
||||
case QCOW2_SUBCLUSTER_UNALLOCATED_ALLOC:
|
||||
if (bs->backing && bs->backing->bs) {
|
||||
int64_t backing_length = bdrv_getlength(bs->backing->bs);
|
||||
int64_t backing_length = bdrv_co_getlength(bs->backing->bs);
|
||||
if (src_offset >= backing_length) {
|
||||
cur_write_flags |= BDRV_REQ_ZERO_WRITE;
|
||||
} else {
|
||||
@@ -4293,7 +4289,7 @@ qcow2_co_truncate(BlockDriverState *bs, int64_t offset, bool exact,
|
||||
goto fail;
|
||||
}
|
||||
|
||||
old_file_size = bdrv_getlength(bs->file->bs);
|
||||
old_file_size = bdrv_co_getlength(bs->file->bs);
|
||||
if (old_file_size < 0) {
|
||||
error_setg_errno(errp, -old_file_size,
|
||||
"Failed to inquire current file length");
|
||||
@@ -4386,7 +4382,7 @@ qcow2_co_truncate(BlockDriverState *bs, int64_t offset, bool exact,
|
||||
break;
|
||||
}
|
||||
|
||||
old_file_size = bdrv_getlength(bs->file->bs);
|
||||
old_file_size = bdrv_co_getlength(bs->file->bs);
|
||||
if (old_file_size < 0) {
|
||||
error_setg_errno(errp, -old_file_size,
|
||||
"Failed to inquire current file length");
|
||||
@@ -4694,7 +4690,7 @@ qcow2_co_pwritev_compressed_part(BlockDriverState *bs,
|
||||
* align end of file to a sector boundary to ease reading with
|
||||
* sector based I/Os
|
||||
*/
|
||||
int64_t len = bdrv_getlength(bs->file->bs);
|
||||
int64_t len = bdrv_co_getlength(bs->file->bs);
|
||||
if (len < 0) {
|
||||
return len;
|
||||
}
|
||||
|
||||
+3
-1
@@ -895,7 +895,9 @@ int qcow2_change_refcount_order(BlockDriverState *bs, int refcount_order,
|
||||
void *cb_opaque, Error **errp);
|
||||
int coroutine_fn GRAPH_RDLOCK qcow2_shrink_reftable(BlockDriverState *bs);
|
||||
int64_t coroutine_fn qcow2_get_last_cluster(BlockDriverState *bs, int64_t size);
|
||||
int coroutine_fn qcow2_detect_metadata_preallocation(BlockDriverState *bs);
|
||||
|
||||
int coroutine_fn GRAPH_RDLOCK
|
||||
qcow2_detect_metadata_preallocation(BlockDriverState *bs);
|
||||
|
||||
/* qcow2-cluster.c functions */
|
||||
int qcow2_grow_l1_table(BlockDriverState *bs, uint64_t min_size,
|
||||
|
||||
+11
-13
@@ -557,11 +557,13 @@ typedef struct QEDOpenCo {
|
||||
int ret;
|
||||
} QEDOpenCo;
|
||||
|
||||
static void coroutine_fn GRAPH_RDLOCK bdrv_qed_open_entry(void *opaque)
|
||||
static void coroutine_fn bdrv_qed_open_entry(void *opaque)
|
||||
{
|
||||
QEDOpenCo *qoc = opaque;
|
||||
BDRVQEDState *s = qoc->bs->opaque;
|
||||
|
||||
GRAPH_RDLOCK_GUARD();
|
||||
|
||||
qemu_co_mutex_lock(&s->table_lock);
|
||||
qoc->ret = bdrv_qed_do_open(qoc->bs, qoc->options, qoc->flags, qoc->errp);
|
||||
qemu_co_mutex_unlock(&s->table_lock);
|
||||
@@ -579,21 +581,17 @@ static int bdrv_qed_open(BlockDriverState *bs, QDict *options, int flags,
|
||||
};
|
||||
int ret;
|
||||
|
||||
assume_graph_lock(); /* FIXME */
|
||||
|
||||
ret = bdrv_open_file_child(NULL, options, "file", bs, errp);
|
||||
if (ret < 0) {
|
||||
return ret;
|
||||
}
|
||||
|
||||
bdrv_qed_init_state(bs);
|
||||
if (qemu_in_coroutine()) {
|
||||
bdrv_qed_open_entry(&qoc);
|
||||
} else {
|
||||
assert(qemu_get_current_aio_context() == qemu_get_aio_context());
|
||||
qemu_coroutine_enter(qemu_coroutine_create(bdrv_qed_open_entry, &qoc));
|
||||
BDRV_POLL_WHILE(bs, qoc.ret == -EINPROGRESS);
|
||||
}
|
||||
assert(!qemu_in_coroutine());
|
||||
assert(qemu_get_current_aio_context() == qemu_get_aio_context());
|
||||
qemu_coroutine_enter(qemu_coroutine_create(bdrv_qed_open_entry, &qoc));
|
||||
BDRV_POLL_WHILE(bs, qoc.ret == -EINPROGRESS);
|
||||
|
||||
return qoc.ret;
|
||||
}
|
||||
|
||||
@@ -748,8 +746,8 @@ static int coroutine_fn bdrv_qed_co_create(BlockdevCreateOptions *opts,
|
||||
ret = 0; /* success */
|
||||
out:
|
||||
g_free(l1_table);
|
||||
blk_unref(blk);
|
||||
bdrv_unref(bs);
|
||||
blk_co_unref(blk);
|
||||
bdrv_co_unref(bs);
|
||||
return ret;
|
||||
}
|
||||
|
||||
@@ -819,7 +817,7 @@ bdrv_qed_co_create_opts(BlockDriver *drv, const char *filename,
|
||||
|
||||
fail:
|
||||
qobject_unref(qdict);
|
||||
bdrv_unref(bs);
|
||||
bdrv_co_unref(bs);
|
||||
qapi_free_BlockdevCreateOptions(create_options);
|
||||
return ret;
|
||||
}
|
||||
|
||||
+2
-2
@@ -825,8 +825,8 @@ static coroutine_fn GRAPH_RDLOCK int quorum_co_flush(BlockDriverState *bs)
|
||||
return result;
|
||||
}
|
||||
|
||||
static bool quorum_recurse_can_replace(BlockDriverState *bs,
|
||||
BlockDriverState *to_replace)
|
||||
static bool GRAPH_RDLOCK
|
||||
quorum_recurse_can_replace(BlockDriverState *bs, BlockDriverState *to_replace)
|
||||
{
|
||||
BDRVQuorumState *s = bs->opaque;
|
||||
int i;
|
||||
|
||||
+1
-1
@@ -369,7 +369,7 @@ static BlockMeasureInfo *raw_measure(QemuOpts *opts, BlockDriverState *in_bs,
|
||||
return info;
|
||||
}
|
||||
|
||||
static int coroutine_fn
|
||||
static int coroutine_fn GRAPH_RDLOCK
|
||||
raw_co_get_info(BlockDriverState *bs, BlockDriverInfo *bdi)
|
||||
{
|
||||
return bdrv_co_get_info(bs->file->bs, bdi);
|
||||
|
||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user