On Wed, Feb 23, 2022 at 14:17:40 +0100, Kashyap Chamarthy wrote: > On Tue, Feb 22, 2022 at 05:55:38PM +0100, Peter Krempa wrote: > > In case when a user starts a block copy operation with > > VIR_DOMAIN_BLOCK_COPY_SHALLOW and VIR_DOMAIN_BLOCK_COPY_REUSE_EXT and > > both the reused image and the original disk have a backing image libvirt > > specifically does not insert the backing image until after the job is > > asked to be completed via virBlockJobAbort with > > VIR_DOMAIN_BLOCK_JOB_ABORT_PIVOT. > > Thanks for the quick patch! > > First, to refresh my memory (and for others reading the thread), these > are the two main uses of combining '--reuse-external' and '--shallow' > flags with "blockcopy": > > (a) You can control what the backing file is, as long as the top of that > backing file chain has identical guest-visible contents to what the > original chain had in its backing file. > > (b) The new backing file can have a _different_ backing chain depth or > even different format. > > * * * > > Now to construct a reproducer with `virsh`. Peter, tell me what I got > wrong :-) > > (1) Let's start with this image chain (overlays are always of qcow2 > format): > > base.raw <-- overlay1 <-- overlay2 (live QEMU). > > With the goal of copying the above into the below chain (note, here > we're flattening both base.raw and overlay1 into a single file, > "flat-o-b1") > > flat-o-b1.raw <-- copy (live QEMU) > > (2) Make a *raw* variant of "base <-- overlay1", call it "flat-b-o1.raw" > (i.e. flattened version of combined base and overlay1): > > $ qemu-img convert -f qcow2 -O raw overlay1.qcow2 \ > flat-b-o1.raw > > (3) Then, create an empty QCOW2 file to create "flat-b-o1 <-- copy (empty)": > > $ qemu-img create -f qcow2 \ > -o backing_file=flat-b-o1.raw,backing_fmt=raw copy.qcow2 > > (4) *Then* perform the `blockcopy --reuse-external --shallow`: > > $ virsh blockcopy \ > --domain vm1 vda ./copy.qcow2 \ > --wait --verbose --reuse-external --shallow \ > --finish If you are working on a persistent domain/vm use --transient-job to avoid the need to undefine it. Also note that '--finish' is equivalent to aborting the job after it reaches synchronized phase ... > > (5) And then pivot the job, so that live QEMU now points to copy > > $ virsh blockjob --pivot ... so this will actually say that there is no blockjob, because the previous step actually cancelled it. > > And the final result, we get the "goal" chain in step (1). > > src: base <-- overlay1 <-- overlay2 > == == > dst: flat-o-b1 <-- copy (live QEMU) > > > Am I missing anything else? Now the bug is that when you _cancel_ the job we attempt to blockdev-del some images which were not blockdev-added, and thus create some spurious log entries, but the rest of the code behaves correctly. So you'll only see the failure this is fixing in the logs.