summaryrefslogtreecommitdiff
path: root/block/mirror.c
diff options
context:
space:
mode:
authorKevin Wolf <kwolf@redhat.com>2017-01-13 19:02:32 +0100
committerKevin Wolf <kwolf@redhat.com>2017-02-28 20:40:36 +0100
commitd7086422b1c1e75e320519cfe26176db6ec97a37 (patch)
tree5b8cc8a489ee05f6432288590f1b621bccfa39c4 /block/mirror.c
parent6d0eb64d5c6d57017c52a4f36ccae1db79215ee1 (diff)
downloadqemu-d7086422b1c1e75e320519cfe26176db6ec97a37.tar.gz
block: Add error parameter to blk_insert_bs()
Now that blk_insert_bs() requests the BlockBackend permissions for the node it attaches to, it can fail. Instead of aborting, pass the errors to the callers. Signed-off-by: Kevin Wolf <kwolf@redhat.com> Reviewed-by: Max Reitz <mreitz@redhat.com> Acked-by: Fam Zheng <famz@redhat.com>
Diffstat (limited to 'block/mirror.c')
-rw-r--r--block/mirror.c15
1 files changed, 12 insertions, 3 deletions
diff --git a/block/mirror.c b/block/mirror.c
index 30398fb857..063925a1f0 100644
--- a/block/mirror.c
+++ b/block/mirror.c
@@ -525,9 +525,12 @@ static void mirror_exit(BlockJob *job, void *opaque)
bdrv_replace_in_backing_chain(to_replace, target_bs);
bdrv_drained_end(target_bs);
- /* We just changed the BDS the job BB refers to */
+ /* We just changed the BDS the job BB refers to, so switch the BB back
+ * so the cleanup does the right thing. We don't need any permissions
+ * any more now. */
blk_remove_bs(job->blk);
- blk_insert_bs(job->blk, src);
+ blk_set_perm(job->blk, 0, BLK_PERM_ALL, &error_abort);
+ blk_insert_bs(job->blk, src, &error_abort);
}
if (s->to_replace) {
bdrv_op_unblock_all(s->to_replace, s->replace_blocker);
@@ -995,6 +998,7 @@ static void mirror_start_job(const char *job_id, BlockDriverState *bs,
bool auto_complete)
{
MirrorBlockJob *s;
+ int ret;
if (granularity == 0) {
granularity = bdrv_get_default_bitmap_granularity(target);
@@ -1019,7 +1023,12 @@ static void mirror_start_job(const char *job_id, BlockDriverState *bs,
/* FIXME Use real permissions */
s->target = blk_new(0, BLK_PERM_ALL);
- blk_insert_bs(s->target, target);
+ ret = blk_insert_bs(s->target, target, errp);
+ if (ret < 0) {
+ blk_unref(s->target);
+ block_job_unref(&s->common);
+ return;
+ }
s->replaces = g_strdup(replaces);
s->on_source_error = on_source_error;