[PATCH 3/3] qemu: enable qcow2 data-file attach to VM on start

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

 



- parse data-file metadata and init src->dataFileStore struct
- chown data-file to allow qemu to open it
- add data-file path to VM's cgroup and namespace
- add data-file option to QEMU process command line

Signed-off-by: Nikolai Barybin <nikolai.barybin@xxxxxxxxxxxxx>
---
 src/qemu/qemu_block.c             | 45 +++++++++++++++++++++++++++++++
 src/qemu/qemu_cgroup.c            |  3 +++
 src/qemu/qemu_namespace.c         |  6 +++++
 src/storage_file/storage_source.c | 38 ++++++++++++++++++++++++--
 4 files changed, 90 insertions(+), 2 deletions(-)

diff --git a/src/qemu/qemu_block.c b/src/qemu/qemu_block.c
index d6cdf521c4..38f4717d56 100644
--- a/src/qemu/qemu_block.c
+++ b/src/qemu/qemu_block.c
@@ -1271,6 +1271,48 @@ qemuBlockStorageSourceGetFormatQcowGenericProps(virStorageSource *src,
 }
 
 
+static int
+qemuBlockStorageGetQcow2DataFileProps(virStorageSource *src,
+                                      virJSONValue *props)
+{
+    g_autoptr(virJSONValue) dataFileDef = NULL;
+    virStorageType actualType;
+    g_autofree char *driverName = NULL;
+
+    if (!src->dataFileRaw)
+        return 0;
+
+    actualType = virStorageSourceGetActualType(src->dataFileStore);
+    if (actualType != VIR_STORAGE_TYPE_BLOCK &&
+        actualType != VIR_STORAGE_TYPE_FILE) {
+        virReportError(VIR_ERR_INTERNAL_ERROR,
+                       _("%1$s storage type is not supported for qcow2 data-file"),
+                       NULLSTR(virStorageTypeToString(actualType)));
+        return -1;
+    }
+
+    if (virStorageSourceIsBlockLocal(src->dataFileStore))
+        driverName = g_strdup("host_device");
+    else
+        driverName = g_strdup("file");
+
+    if (virJSONValueObjectAdd(&dataFileDef,
+                              "s:driver", driverName,
+                              "b:read-only", src->readonly,
+                              "s:filename", src->dataFileRaw,
+                              NULL) < 0)
+        return -1;
+
+    if (virJSONValueObjectAdd(&props,
+                              "A:data-file", &dataFileDef,
+                              NULL) < 0)
+        return -1;
+
+    return 0;
+}
+
+
+
 static int
 qemuBlockStorageSourceGetFormatQcow2Props(virStorageSource *src,
                                           virJSONValue *props)
@@ -1301,6 +1343,9 @@ qemuBlockStorageSourceGetFormatQcow2Props(virStorageSource *src,
                               NULL) < 0)
         return -1;
 
+    if (qemuBlockStorageGetQcow2DataFileProps(src, props) < 0)
+        return -1;
+
     return 0;
 }
 
diff --git a/src/qemu/qemu_cgroup.c b/src/qemu/qemu_cgroup.c
index 23b7e6b4e8..84c749b567 100644
--- a/src/qemu/qemu_cgroup.c
+++ b/src/qemu/qemu_cgroup.c
@@ -223,6 +223,9 @@ qemuSetupImageCgroupInternal(virDomainObj *vm,
         qemuSetupImagePathCgroup(vm, QEMU_DEVICE_MAPPER_CONTROL_PATH, false) < 0)
         return -1;
 
+    if (src->dataFileRaw && qemuSetupImagePathCgroup(vm, src->dataFileRaw, readonly) < 0)
+        return -1;
+
     return qemuSetupImagePathCgroup(vm, path, readonly);
 }
 
diff --git a/src/qemu/qemu_namespace.c b/src/qemu/qemu_namespace.c
index bbe3d5a1f7..32653443ec 100644
--- a/src/qemu/qemu_namespace.c
+++ b/src/qemu/qemu_namespace.c
@@ -290,6 +290,12 @@ qemuDomainSetupDisk(virStorageSource *src,
 
             if (targetPaths)
                 *paths = g_slist_concat(g_slist_reverse(targetPaths), *paths);
+
+            if (next->dataFileRaw) {
+                g_autofree char *datafile = NULL;
+                datafile = g_strdup(next->dataFileRaw);
+                *paths = g_slist_prepend(*paths, g_steal_pointer(&datafile));
+            }
         }
 
         *paths = g_slist_prepend(*paths, g_steal_pointer(&tmpPath));
diff --git a/src/storage_file/storage_source.c b/src/storage_file/storage_source.c
index 2cfe3bc325..0ea11228d4 100644
--- a/src/storage_file/storage_source.c
+++ b/src/storage_file/storage_source.c
@@ -1378,8 +1378,16 @@ virStorageSourceGetMetadataRecurse(virStorageSource *src,
                                                      &buf, &headerLen) < 0)
         return -1;
 
-    if (virStorageFileProbeGetMetadata(src, buf, headerLen) < 0)
-        return -1;
+    if (!parent->dataFileRaw) {
+        if (virStorageFileProbeGetMetadata(src, buf, headerLen) < 0)
+            return -1;
+    } else {
+        if (virStorageSourceInitAs(src, uid, gid) < 0)
+            return -1;
+        if (virStorageSourceChown(src, uid, gid) < 0)
+            return -1;
+        virStorageSourceDeinit(src);
+    }
 
     /* If we probed the format we MUST ensure that nothing else than the current
      * image is considered for security labelling and/or recursion. */
@@ -1417,6 +1425,32 @@ virStorageSourceGetMetadataRecurse(virStorageSource *src,
 
         backingStore->id = depth;
         src->backingStore = g_steal_pointer(&backingStore);
+
+    } else if (src->dataFileRaw) {
+        if ((rv = virStorageSourceNewFromChild(src, src->dataFileRaw, &backingStore)) < 0)
+            return -1;
+
+        if (rv == 1)
+            return 0;
+
+        if ((rv = virStorageSourceGetMetadataRecurse(backingStore, parent,
+                                                     uid, gid,
+                                                     report_broken,
+                                                     max_depth, depth + 1)) < 0) {
+            if (!report_broken)
+                return 0;
+
+            if (rv == -2) {
+                virReportError(VIR_ERR_OPERATION_INVALID,
+                               _("format of data file image '%1$s' of image '%2$s' was not specified in the image metadata (See https://libvirt.org/kbase/backing_chains.html for troubleshooting)"),
+                               src->dataFileRaw, NULLSTR(src->path));
+            }
+
+            return -1;
+        }
+
+        backingStore->id = depth;
+        src->dataFileStore = g_steal_pointer(&backingStore);
     } else {
         /* add terminator */
         src->backingStore = virStorageSourceNew();
-- 
2.43.5



[Index of Archives]     [Virt Tools]     [Libvirt Users]     [Lib OS Info]     [Fedora Users]     [Fedora Desktop]     [Fedora SELinux]     [Big List of Linux Books]     [Yosemite News]     [KDE Users]     [Fedora Tools]

  Powered by Linux