From e3d66229a1026cd33319714c0ededf650cd261c2 Mon Sep 17 00:00:00 2001 From: John Ferlan Date: Tue, 8 Apr 2014 10:59:09 -0400 Subject: [PATCH] qemu: Adjust size for qcow2/qed if not on sector boundary https://bugzilla.redhat.com/show_bug.cgi?id=1002813 If qemuDomainBlockResize() is passed a size not on a KiB boundary - that is passed a size based in bytes (VIR_DOMAIN_BLOCK_RESIZE_BYTES), then depending on the source format (qcow2 or qed), the value passed must be on a sector (or 512 byte) boundary. Since other libvirt code quietly adjusts the capacity values, then do so here as well - of course ensuring that adjustment still fits. Signed-off-by: John Ferlan --- src/qemu/qemu_driver.c | 22 ++++++++++++++++++++++ 1 file changed, 22 insertions(+) diff --git a/src/qemu/qemu_driver.c b/src/qemu/qemu_driver.c index f0e82e9fbf..4ff8a2d0d7 100644 --- a/src/qemu/qemu_driver.c +++ b/src/qemu/qemu_driver.c @@ -9413,6 +9413,7 @@ qemuDomainBlockResize(virDomainPtr dom, virDomainObjPtr vm; qemuDomainObjPrivatePtr priv; int ret = -1, idx; + unsigned long long size_up; char *device = NULL; virDomainDiskDefPtr disk = NULL; @@ -9433,6 +9434,12 @@ qemuDomainBlockResize(virDomainPtr dom, return -1; } size *= 1024; + size_up = size; + } else { + /* For 'qcow2' and 'qed', qemu resize blocks expects values + * on sector boundary, so round our value up to prepare + */ + size_up = VIR_ROUND_UP(size, 512); } if (!(vm = qemuDomObjFromDomain(dom))) @@ -9459,6 +9466,21 @@ qemuDomainBlockResize(virDomainPtr dom, } disk = vm->def->disks[idx]; + /* qcow2 and qed must be sized appropriately, so be sure our value + * is sized appropriately and will fit + */ + if (size != size_up && + (disk->src.format == VIR_STORAGE_FILE_QCOW2 || + disk->src.format == VIR_STORAGE_FILE_QED)) { + if (size_up > ULLONG_MAX) { + virReportError(VIR_ERR_OVERFLOW, + _("size must be less than %llu KiB"), + ULLONG_MAX / 1024); + goto endjob; + } + size = size_up; + } + if (virAsprintf(&device, "%s%s", QEMU_DRIVE_HOST_PREFIX, disk->info.alias) < 0) goto endjob; -- 2.47.2