[libvirt] [PATCHv5 26/28] qemu: Refactor qemuDomainPrepareDiskChainElement

Peter Krempa pkrempa at redhat.com
Fri Jul 4 11:29:41 UTC 2014


Now that security, cgroup and locking APIs support working on individual
images and we track the backing chain security info on a per-image basis
we can finally kill swapping the disk source in virDomainDiskDef and use
the virStorageSource directly.
---
 src/qemu/qemu_driver.c | 85 ++++++++++++++++++++++----------------------------
 1 file changed, 38 insertions(+), 47 deletions(-)

diff --git a/src/qemu/qemu_driver.c b/src/qemu/qemu_driver.c
index e648108..6721fc9 100644
--- a/src/qemu/qemu_driver.c
+++ b/src/qemu/qemu_driver.c
@@ -12040,61 +12040,52 @@ typedef enum {
     VIR_DISK_CHAIN_READ_WRITE,
 } qemuDomainDiskChainMode;

-/* Several operations end up adding or removing a single element of a
- * disk backing file chain; this helper function ensures that the lock
- * manager, cgroup device controller, and security manager labelling
- * are all aware of each new file before it is added to a chain, and
- * can revoke access to a file no longer needed in a chain.  */
+/* Several operations end up adding or removing a single element of a disk
+ * backing file chain; this helper function ensures that the lock manager,
+ * cgroup device controller, and security manager labelling are all aware of
+ * each new file before it is added to a chain, and can revoke access to a file
+ * no longer needed in a chain.  */
 static int
 qemuDomainPrepareDiskChainElement(virQEMUDriverPtr driver,
                                   virDomainObjPtr vm,
-                                  virDomainDiskDefPtr disk,
                                   virStorageSourcePtr elem,
                                   qemuDomainDiskChainMode mode)
 {
-    /* The easiest way to label a single file with the same
-     * permissions it would have as if part of the disk chain is to
-     * temporarily modify the disk in place.  */
-    virStorageSource origdisk;
-    bool origreadonly = disk->src->readonly;
+    bool readonly = elem->readonly;
     virQEMUDriverConfigPtr cfg = NULL;
     int ret = -1;

-    /* XXX Labelling of non-local files isn't currently supported */
-    if (virStorageSourceGetActualType(disk->src) == VIR_STORAGE_TYPE_NETWORK)
-        return 0;
-
     cfg = virQEMUDriverGetConfig(driver);

-    /* XXX Need to refactor the security manager and lock daemon to
-     * operate directly on a virStorageSourcePtr plus tidbits rather
-     * than a full virDomainDiskDef.  */
-    memcpy(&origdisk, disk->src, sizeof(origdisk));
-    memcpy(disk->src, elem, sizeof(*elem));
-    disk->src->readonly = mode == VIR_DISK_CHAIN_READ_ONLY;
+    elem->readonly = mode == VIR_DISK_CHAIN_READ_ONLY;

     if (mode == VIR_DISK_CHAIN_NO_ACCESS) {
-        if (virSecurityManagerRestoreDiskLabel(driver->securityManager,
-                                               vm->def, disk) < 0)
-            VIR_WARN("Unable to restore security label on %s", disk->src->path);
-        if (qemuTeardownDiskCgroup(vm, disk) < 0)
-            VIR_WARN("Failed to teardown cgroup for disk path %s",
-                     disk->src->path);
-        if (virDomainLockDiskDetach(driver->lockManager, vm, disk) < 0)
-            VIR_WARN("Unable to release lock on %s", disk->src->path);
-    } else if (virDomainLockDiskAttach(driver->lockManager, cfg->uri,
-                                       vm, disk) < 0 ||
-               qemuSetupDiskCgroup(vm, disk) < 0 ||
-               virSecurityManagerSetDiskLabel(driver->securityManager,
-                                              vm->def, disk) < 0) {
-        goto cleanup;
+        if (virSecurityManagerRestoreImageLabel(driver->securityManager,
+                                                vm->def, elem) < 0)
+            VIR_WARN("Unable to restore security label on %s", elem->path);
+
+        if (qemuSetImageCgroup(vm, elem, true) < 0)
+            VIR_WARN("Failed to teardown cgroup for disk path %s", elem->path);
+
+        if (virDomainLockImageDetach(driver->lockManager, vm, elem) < 0)
+            VIR_WARN("Unable to release lock on %s", elem->path);
+    } else {
+        if (virDomainLockImageAttach(driver->lockManager, cfg->uri,
+                                     vm, elem) < 0)
+            goto cleanup;
+
+        if (qemuSetImageCgroup(vm, elem, false) < 0)
+            goto cleanup;
+
+        if (virSecurityManagerSetImageLabel(driver->securityManager,
+                                            vm->def, elem) < 0)
+            goto cleanup;
     }

     ret = 0;

  cleanup:
-    memcpy(disk->src, &origdisk, sizeof(origdisk));
-    disk->src->readonly = origreadonly;
+    elem->readonly = readonly;
     virObjectUnref(cfg);
     return ret;
 }
@@ -12863,9 +12854,9 @@ qemuDomainSnapshotCreateSingleDiskActive(virQEMUDriverPtr driver,
             VIR_FORCE_CLOSE(fd);
         }

-        if (qemuDomainPrepareDiskChainElement(driver, vm, disk, snap->src,
+        if (qemuDomainPrepareDiskChainElement(driver, vm, snap->src,
                                               VIR_DISK_CHAIN_READ_WRITE) < 0) {
-            qemuDomainPrepareDiskChainElement(driver, vm, disk, snap->src,
+            qemuDomainPrepareDiskChainElement(driver, vm, snap->src,
                                               VIR_DISK_CHAIN_NO_ACCESS);
             goto cleanup;
         }
@@ -12960,7 +12951,7 @@ qemuDomainSnapshotUndoSingleDiskActive(virQEMUDriverPtr driver,

     ignore_value(virStorageFileInit(disk->src));

-    qemuDomainPrepareDiskChainElement(driver, vm, disk, disk->src,
+    qemuDomainPrepareDiskChainElement(driver, vm, disk->src,
                                       VIR_DISK_CHAIN_NO_ACCESS);
     if (need_unlink &&
         virStorageFileStat(disk->src, &st) == 0 && S_ISREG(st.st_mode) &&
@@ -15283,9 +15274,9 @@ qemuDomainBlockCopy(virDomainObjPtr vm,
     if (virStorageSourceInitChainElement(disk->mirror, disk->src, false) < 0)
         goto endjob;

-    if (qemuDomainPrepareDiskChainElement(driver, vm, disk, mirror,
+    if (qemuDomainPrepareDiskChainElement(driver, vm, mirror,
                                           VIR_DISK_CHAIN_READ_WRITE) < 0) {
-        qemuDomainPrepareDiskChainElement(driver, vm, disk, mirror,
+        qemuDomainPrepareDiskChainElement(driver, vm, mirror,
                                           VIR_DISK_CHAIN_NO_ACCESS);
         goto endjob;
     }
@@ -15297,7 +15288,7 @@ qemuDomainBlockCopy(virDomainObjPtr vm,
     virDomainAuditDisk(vm, NULL, mirror, "mirror", ret >= 0);
     qemuDomainObjExitMonitor(driver, vm);
     if (ret < 0) {
-        qemuDomainPrepareDiskChainElement(driver, vm, disk, mirror,
+        qemuDomainPrepareDiskChainElement(driver, vm, mirror,
                                           VIR_DISK_CHAIN_NO_ACCESS);
         goto endjob;
     }
@@ -15499,10 +15490,10 @@ qemuDomainBlockCommit(virDomainPtr dom,
      * operation succeeds, but doing that requires tracking the
      * operation in XML across libvirtd restarts.  */
     clean_access = true;
-    if (qemuDomainPrepareDiskChainElement(driver, vm, disk, baseSource,
+    if (qemuDomainPrepareDiskChainElement(driver, vm, baseSource,
                                           VIR_DISK_CHAIN_READ_WRITE) < 0 ||
         (top_parent != disk->src &&
-         qemuDomainPrepareDiskChainElement(driver, vm, disk, top_parent,
+         qemuDomainPrepareDiskChainElement(driver, vm, top_parent,
                                            VIR_DISK_CHAIN_READ_WRITE) < 0))
         goto endjob;

@@ -15522,10 +15513,10 @@ qemuDomainBlockCommit(virDomainPtr dom,
  endjob:
     if (ret < 0 && clean_access) {
         /* Revert access to read-only, if possible.  */
-        qemuDomainPrepareDiskChainElement(driver, vm, disk, baseSource,
+        qemuDomainPrepareDiskChainElement(driver, vm, baseSource,
                                           VIR_DISK_CHAIN_READ_ONLY);
         if (top_parent != disk->src)
-            qemuDomainPrepareDiskChainElement(driver, vm, disk, top_parent,
+            qemuDomainPrepareDiskChainElement(driver, vm, top_parent,
                                               VIR_DISK_CHAIN_READ_ONLY);
     }
     if (!qemuDomainObjEndJob(driver, vm))
-- 
1.9.3




More information about the libvir-list mailing list