qemu: block: Add support for 'data-file' feature of qcow2

Add the block infrastructure for detecting and landling the data file
for images and starting qemu with the configuration.

Signed-off-by: Nikolai Barybin <nikolai.barybin@virtuozzo.com>
Signed-off-by: Peter Krempa <pkrempa@redhat.com>
Reviewed-by: Peter Krempa <pkrempa@redhat.com>
This commit is contained in:
Nikolai Barybin 2024-11-20 18:48:48 +03:00 committed by Peter Krempa
parent cb5371a8bd
commit 59b1408860
3 changed files with 44 additions and 1 deletions

View File

@ -1302,6 +1302,13 @@ qemuBlockStorageSourceGetFormatQcow2Props(virStorageSource *src,
NULL) < 0)
return -1;
if (src->dataFileStore) {
if (virJSONValueObjectAdd(&props,
"s:data-file", qemuBlockStorageSourceGetEffectiveNodename(src->dataFileStore),
NULL) < 0)
return -1;
}
return 0;
}
@ -1859,6 +1866,13 @@ qemuBlockStorageSourceChainDetachPrepareBlockdev(virStorageSource *src)
return NULL;
VIR_APPEND_ELEMENT(data->srcdata, data->nsrcdata, backend);
if (n->dataFileStore) {
if (!(backend = qemuBlockStorageSourceDetachPrepare(n->dataFileStore)))
return NULL;
VIR_APPEND_ELEMENT(data->srcdata, data->nsrcdata, backend);
}
}
return g_steal_pointer(&data);
@ -2589,6 +2603,12 @@ qemuBlockStorageSourceCreateFormat(virDomainObj *vm,
if (qemuBlockStorageSourceIsRaw(src))
return 0;
if (src->dataFileStore) {
virReportError(VIR_ERR_OPERATION_UNSUPPORTED, "%s",
_("creation of storage images with <dataStore> feature is not supported"));
return -1;
}
if (qemuBlockStorageSourceCreateGetFormatProps(src, backingStore,
&createformatprops) < 0)
return -1;

View File

@ -11018,6 +11018,11 @@ qemuBuildStorageSourceChainAttachPrepareBlockdev(virStorageSource *top)
if (qemuBuildStorageSourceChainAttachPrepareBlockdevOne(data, n,
n->backingStore) < 0)
return NULL;
/* the dataStore must not have a backing image so we pass NULL */
if (n->dataFileStore &&
qemuBuildStorageSourceChainAttachPrepareBlockdevOne(data, n->dataFileStore, NULL) < 0)
return NULL;
}
return g_steal_pointer(&data);

View File

@ -6158,6 +6158,7 @@ qemuDomainDetermineDiskChain(virQEMUDriver *driver,
virStorageSource *disksrc)
{
g_autoptr(virQEMUDriverConfig) cfg = virQEMUDriverGetConfig(driver);
bool hadDataStore = false;
virStorageSource *src; /* iterator for the backing chain declared in XML */
virStorageSource *n; /* iterator for the backing chain detected from disk */
uid_t uid;
@ -6237,14 +6238,27 @@ qemuDomainDetermineDiskChain(virQEMUDriver *driver,
qemuDomainGetImageIds(cfg, vm->def, src, disksrc, &uid, &gid);
hadDataStore = !!src->dataFileStore;
if (virStorageSourceGetMetadata(src, uid, gid,
QEMU_DOMAIN_STORAGE_SOURCE_CHAIN_MAX_DEPTH,
true) < 0)
return -1;
/* As we perform image properties detection on the last member of the
* backing chain we need to also consider the data store part of the current
* image */
if (src->dataFileStore && !hadDataStore &&
qemuDomainPrepareStorageSource(src->dataFileStore, vm, disk, cfg) < 0)
return -1;
for (n = src->backingStore; virStorageSourceIsBacking(n); n = n->backingStore) {
if (qemuDomainPrepareStorageSource(n, vm, disk, cfg) < 0)
return -1;
if (n->dataFileStore &&
qemuDomainPrepareStorageSource(n->dataFileStore, vm, disk, cfg) < 0)
return -1;
}
if (qemuDomainStorageSourceValidateDepth(disksrc, 0, disk->dst) < 0)
@ -9484,7 +9498,7 @@ qemuDomainPrepareDiskSourceData(virDomainDiskDef *disk,
return;
/* transfer properties valid only for the top level image */
if (src == disk->src)
if (src == disk->src || src == disk->src->dataFileStore)
src->detect_zeroes = disk->detect_zeroes;
/* transfer properties valid for the full chain */
@ -9713,6 +9727,10 @@ qemuDomainPrepareDiskSourceBlockdev(virDomainDiskDef *disk,
for (n = disk->src; virStorageSourceIsBacking(n); n = n->backingStore) {
if (qemuDomainPrepareStorageSourceBlockdev(disk, n, priv, cfg) < 0)
return -1;
if (n->dataFileStore &&
qemuDomainPrepareStorageSourceBlockdev(disk, n->dataFileStore, priv, cfg) < 0)
return -1;
}
return 0;