[libvirt] [PATCH 3/6] snapshot: refactor some qemu code

Eric Blake eblake at redhat.com
Fri Aug 12 18:49:02 UTC 2011


Prepare for code sharing.  No semantic change.

* src/qemu/qemu_driver.c (qemuFindQemuImgBinary)
(qemuDomainSnapshotDiscard): Float up.
(qemuDomainSnapshotDiscardDescendant): Likewise, and rename...
(qemuDomainSnapshotDiscardAll): ...for generic use.
(qemuDomainSnapshotDelete): Update caller.
---
 src/qemu/qemu_driver.c |  253 ++++++++++++++++++++++++-----------------------
 1 files changed, 129 insertions(+), 124 deletions(-)

diff --git a/src/qemu/qemu_driver.c b/src/qemu/qemu_driver.c
index 678ac1b..d9e88fe 100644
--- a/src/qemu/qemu_driver.c
+++ b/src/qemu/qemu_driver.c
@@ -1574,6 +1574,134 @@ cleanup:
 }


+struct snap_remove {
+    struct qemud_driver *driver;
+    virDomainObjPtr vm;
+    bool metadata_only;
+    int err;
+};
+
+/* Locate an appropriate 'qemu-img' binary.  */
+static char *
+qemuFindQemuImgBinary(void)
+{
+    char *ret;
+
+    ret = virFindFileInPath("kvm-img");
+    if (ret == NULL)
+        ret = virFindFileInPath("qemu-img");
+    if (ret == NULL)
+        qemuReportError(VIR_ERR_INTERNAL_ERROR,
+                        "%s", _("unable to find kvm-img or qemu-img"));
+
+    return ret;
+}
+
+/* Discard one snapshot (or its metadata), without reparenting any children.  */
+static int
+qemuDomainSnapshotDiscard(struct qemud_driver *driver,
+                          virDomainObjPtr vm,
+                          virDomainSnapshotObjPtr snap,
+                          bool metadata_only)
+{
+    const char *qemuimgarg[] = { NULL, "snapshot", "-d", NULL, NULL, NULL };
+    char *snapFile = NULL;
+    int ret = -1;
+    int i;
+    qemuDomainObjPrivatePtr priv;
+    virDomainSnapshotObjPtr parentsnap;
+
+    if (!metadata_only) {
+        if (!virDomainObjIsActive(vm)) {
+            qemuimgarg[0] = qemuFindQemuImgBinary();
+            if (qemuimgarg[0] == NULL)
+                /* qemuFindQemuImgBinary set the error */
+                goto cleanup;
+
+            qemuimgarg[3] = snap->def->name;
+
+            for (i = 0; i < vm->def->ndisks; i++) {
+                /* FIXME: we also need to handle LVM here */
+                if (vm->def->disks[i]->device == VIR_DOMAIN_DISK_DEVICE_DISK) {
+                    if (!vm->def->disks[i]->driverType ||
+                        STRNEQ(vm->def->disks[i]->driverType, "qcow2")) {
+                        /* we continue on even in the face of error, since other
+                         * disks in this VM may have this snapshot in place
+                         */
+                        continue;
+                    }
+
+                    qemuimgarg[4] = vm->def->disks[i]->src;
+
+                    if (virRun(qemuimgarg, NULL) < 0) {
+                        /* we continue on even in the face of error, since other
+                         * disks in this VM may have this snapshot in place
+                         */
+                        continue;
+                    }
+                }
+            }
+        } else {
+            priv = vm->privateData;
+            qemuDomainObjEnterMonitorWithDriver(driver, vm);
+            /* we continue on even in the face of error */
+            qemuMonitorDeleteSnapshot(priv->mon, snap->def->name);
+            qemuDomainObjExitMonitorWithDriver(driver, vm);
+        }
+    }
+
+    if (snap == vm->current_snapshot) {
+        if (snap->def->parent) {
+            parentsnap = virDomainSnapshotFindByName(&vm->snapshots,
+                                                     snap->def->parent);
+            if (!parentsnap) {
+                qemuReportError(VIR_ERR_NO_DOMAIN_SNAPSHOT,
+                                _("no domain snapshot parent with matching name '%s'"),
+                                snap->def->parent);
+                goto cleanup;
+            }
+
+            /* Now we set the new current_snapshot for the domain */
+            vm->current_snapshot = parentsnap;
+        } else {
+            vm->current_snapshot = NULL;
+        }
+    }
+
+    if (virAsprintf(&snapFile, "%s/%s/%s.xml", driver->snapshotDir,
+                    vm->def->name, snap->def->name) < 0) {
+        virReportOOMError();
+        goto cleanup;
+    }
+    unlink(snapFile);
+
+    virDomainSnapshotObjListRemove(&vm->snapshots, snap);
+
+    ret = 0;
+
+cleanup:
+    VIR_FREE(snapFile);
+    VIR_FREE(qemuimgarg[0]);
+
+    return ret;
+}
+
+/* Hash iterator callback to discard multiple snapshots.  */
+static void
+qemuDomainSnapshotDiscardAll(void *payload,
+                             const void *name ATTRIBUTE_UNUSED,
+                             void *data)
+{
+    virDomainSnapshotObjPtr snap = payload;
+    struct snap_remove *curr = data;
+    int err;
+
+    err = qemuDomainSnapshotDiscard(curr->driver, curr->vm, snap,
+                                    curr->metadata_only);
+    if (err && !curr->err)
+        curr->err = err;
+}
+
 static int
 qemuDomainDestroyFlags(virDomainPtr dom,
                        unsigned int flags)
@@ -8272,20 +8400,6 @@ cleanup:
     return ret;
 }

-static char *qemuFindQemuImgBinary(void)
-{
-    char *ret;
-
-    ret = virFindFileInPath("kvm-img");
-    if (ret == NULL)
-        ret = virFindFileInPath("qemu-img");
-    if (ret == NULL)
-        qemuReportError(VIR_ERR_INTERNAL_ERROR,
-                        "%s", _("unable to find kvm-img or qemu-img"));
-
-    return ret;
-}
-
 static int qemuDomainSnapshotWriteMetadata(virDomainObjPtr vm,
                                            virDomainSnapshotObjPtr snapshot,
                                            char *snapshotDir)
@@ -8951,115 +9065,6 @@ cleanup:
     return ret;
 }

-static int qemuDomainSnapshotDiscard(struct qemud_driver *driver,
-                                     virDomainObjPtr vm,
-                                     virDomainSnapshotObjPtr snap,
-                                     bool metadata_only)
-{
-    const char *qemuimgarg[] = { NULL, "snapshot", "-d", NULL, NULL, NULL };
-    char *snapFile = NULL;
-    int ret = -1;
-    int i;
-    qemuDomainObjPrivatePtr priv;
-    virDomainSnapshotObjPtr parentsnap;
-
-    if (!metadata_only) {
-        if (!virDomainObjIsActive(vm)) {
-            qemuimgarg[0] = qemuFindQemuImgBinary();
-            if (qemuimgarg[0] == NULL)
-                /* qemuFindQemuImgBinary set the error */
-                goto cleanup;
-
-            qemuimgarg[3] = snap->def->name;
-
-            for (i = 0; i < vm->def->ndisks; i++) {
-                /* FIXME: we also need to handle LVM here */
-                if (vm->def->disks[i]->device == VIR_DOMAIN_DISK_DEVICE_DISK) {
-                    if (!vm->def->disks[i]->driverType ||
-                        STRNEQ(vm->def->disks[i]->driverType, "qcow2")) {
-                        /* we continue on even in the face of error, since other
-                         * disks in this VM may have this snapshot in place
-                         */
-                        continue;
-                    }
-
-                    qemuimgarg[4] = vm->def->disks[i]->src;
-
-                    if (virRun(qemuimgarg, NULL) < 0) {
-                        /* we continue on even in the face of error, since other
-                         * disks in this VM may have this snapshot in place
-                         */
-                        continue;
-                    }
-                }
-            }
-        } else {
-            priv = vm->privateData;
-            qemuDomainObjEnterMonitorWithDriver(driver, vm);
-            /* we continue on even in the face of error */
-            qemuMonitorDeleteSnapshot(priv->mon, snap->def->name);
-            qemuDomainObjExitMonitorWithDriver(driver, vm);
-        }
-    }
-
-    if (snap == vm->current_snapshot) {
-        if (snap->def->parent) {
-            parentsnap = virDomainSnapshotFindByName(&vm->snapshots,
-                                                     snap->def->parent);
-            if (!parentsnap) {
-                qemuReportError(VIR_ERR_NO_DOMAIN_SNAPSHOT,
-                                _("no domain snapshot parent with matching name '%s'"),
-                                snap->def->parent);
-                goto cleanup;
-            }
-
-            /* Now we set the new current_snapshot for the domain */
-            vm->current_snapshot = parentsnap;
-        } else {
-            vm->current_snapshot = NULL;
-        }
-    }
-
-    if (virAsprintf(&snapFile, "%s/%s/%s.xml", driver->snapshotDir,
-                    vm->def->name, snap->def->name) < 0) {
-        virReportOOMError();
-        goto cleanup;
-    }
-    unlink(snapFile);
-
-    virDomainSnapshotObjListRemove(&vm->snapshots, snap);
-
-    ret = 0;
-
-cleanup:
-    VIR_FREE(snapFile);
-    VIR_FREE(qemuimgarg[0]);
-
-    return ret;
-}
-
-struct snap_remove {
-    struct qemud_driver *driver;
-    virDomainObjPtr vm;
-    bool metadata_only;
-    int err;
-};
-
-static void
-qemuDomainSnapshotDiscardDescendant(void *payload,
-                                    const void *name ATTRIBUTE_UNUSED,
-                                    void *data)
-{
-    virDomainSnapshotObjPtr snap = payload;
-    struct snap_remove *curr = data;
-    int err;
-
-    err = qemuDomainSnapshotDiscard(curr->driver, curr->vm, snap,
-                                    curr->metadata_only);
-    if (err && !curr->err)
-        curr->err = err;
-}
-
 struct snap_reparent {
     struct qemud_driver *driver;
     virDomainSnapshotObjPtr snap;
@@ -9139,7 +9144,7 @@ static int qemuDomainSnapshotDelete(virDomainSnapshotPtr snapshot,
         rem.err = 0;
         virDomainSnapshotForEachDescendant(&vm->snapshots,
                                            snap,
-                                           qemuDomainSnapshotDiscardDescendant,
+                                           qemuDomainSnapshotDiscardAll,
                                            &rem);
         if (rem.err < 0)
             goto endjob;
-- 
1.7.4.4




More information about the libvir-list mailing list