[Top][All Lists]

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

[Qemu-devel] [PATCH 1/2] block/mirror: Fix target backing BDS

From: Max Reitz
Subject: [Qemu-devel] [PATCH 1/2] block/mirror: Fix target backing BDS
Date: Thu, 26 May 2016 15:40:02 +0200

Currently, we are trying to move the backing BDS from the source to the
target in bdrv_replace_in_backing_chain(). However, the conditions used
to decide when to move the backing BDS from source to target are not
really correct.

Basically, we do not have to set the target's backing BDS when doing a
commit operation (an active commit, to be specific) but we do have to
set it for every mirror operation (unless the target's backing BDS is
already the one it should have).

The decision when to adjust the target's backing BDS and what it should
be set to is something that the mirror code can do best, so let's do it

Also, we do not need to drop the source's backing BDS. In most cases,
the source will be deleted after the mirroring operation anyway, and if
it is not, we probably want it to keep its own backing chain so it stays

Signed-off-by: Max Reitz <address@hidden>
 block.c        |  8 --------
 block/mirror.c | 13 +++++++++++++
 2 files changed, 13 insertions(+), 8 deletions(-)

diff --git a/block.c b/block.c
index 736432f..7ae2766 100644
--- a/block.c
+++ b/block.c
@@ -2275,14 +2275,6 @@ void bdrv_replace_in_backing_chain(BlockDriverState 
*old, BlockDriverState *new)
     change_parent_backing_link(old, new);
-    /* Change backing files if a previously independent node is added to the
-     * chain. For active commit, we replace top by its own (indirect) backing
-     * file and don't do anything here so we don't build a loop. */
-    if (new->backing == NULL && !bdrv_chain_contains(backing_bs(old), new)) {
-        bdrv_set_backing_hd(new, backing_bs(old));
-        bdrv_set_backing_hd(old, NULL);
-    }
diff --git a/block/mirror.c b/block/mirror.c
index 80fd3c7..bc65e54 100644
--- a/block/mirror.c
+++ b/block/mirror.c
@@ -482,6 +482,19 @@ static void mirror_exit(BlockJob *job, void *opaque)
         /* We just changed the BDS the job BB refers to */
         blk_insert_bs(job->blk, src);
+        /* Now we need to adjust the target's backing BDS. This is not 
+         * when having performed a commit operation.
+         * Note that we cannot do this adjustment before the call to
+         * bdrv_replace_in_backing_chain(), because we may end up using
+         * to_replace as the target's BDS, which makes it impossible to replace
+         * to_replace by the target afterwards */
+        if (!bdrv_chain_contains(backing_bs(to_replace), target_bs)) {
+            BlockDriverState *backing = s->is_none_mode ? to_replace : s->base;
+            if (backing_bs(target_bs) != backing) {
+                bdrv_set_backing_hd(target_bs, backing);
+            }
+        }
     if (s->to_replace) {
         bdrv_op_unblock_all(s->to_replace, s->replace_blocker);

reply via email to

[Prev in Thread] Current Thread [Next in Thread]