[libvirt] [PATCH 5/6] snapshot: support new undefine flags in qemu

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


A nice benefit of deleting all snapshots at undefine time is that
you don't have to do any reparenting or subtree identification - since
everything goes, this is an O(n) process whereas using multiple
virDomainSnapshotDelete calls would be O(n^2) or worse.

* src/qemu/qemu_driver.c (qemuDomainDestroyFlags)
(qemuDomainUndefineFlags): Honor new flags.
---
 src/qemu/qemu_driver.c |   51 ++++++++++++++++++++++++++++++++++++++---------
 1 files changed, 41 insertions(+), 10 deletions(-)

diff --git a/src/qemu/qemu_driver.c b/src/qemu/qemu_driver.c
index 08d5a27..bf82df4 100644
--- a/src/qemu/qemu_driver.c
+++ b/src/qemu/qemu_driver.c
@@ -1713,7 +1713,8 @@ qemuDomainDestroyFlags(virDomainPtr dom,
     qemuDomainObjPrivatePtr priv;
     int nsnapshots;

-    virCheckFlags(0, -1);
+    virCheckFlags(VIR_DOMAIN_DESTROY_SNAPSHOTS_METADATA |
+                  VIR_DOMAIN_DESTROY_SNAPSHOTS_FULL, -1);

     qemuDriverLock(driver);
     vm  = virDomainFindByUUID(&driver->domains, dom->uuid);
@@ -1727,10 +1728,24 @@ qemuDomainDestroyFlags(virDomainPtr dom,

     if (!vm->persistent &&
         (nsnapshots = virDomainSnapshotObjListNum(&vm->snapshots))) {
-        qemuReportError(VIR_ERR_OPERATION_INVALID,
-                        _("cannot delete transient domain with %d snapshots"),
-                        nsnapshots);
-        goto cleanup;
+        struct snap_remove rem;
+
+        if ((flags & (VIR_DOMAIN_DESTROY_SNAPSHOTS_METADATA |
+                      VIR_DOMAIN_DESTROY_SNAPSHOTS_FULL)) == 0) {
+            qemuReportError(VIR_ERR_OPERATION_INVALID,
+                            _("cannot delete transient domain with %d "
+                              "snapshots"),
+                            nsnapshots);
+            goto cleanup;
+        }
+
+        rem.driver = driver;
+        rem.vm = vm;
+        rem.metadata_only = !(flags & VIR_DOMAIN_DESTROY_SNAPSHOTS_FULL);
+        rem.err = 0;
+        virHashForEach(vm->snapshots.objs, qemuDomainSnapshotDiscardAll, &rem);
+        if (rem.err < 0)
+            goto cleanup;
     }

     priv = vm->privateData;
@@ -4854,7 +4869,9 @@ qemuDomainUndefineFlags(virDomainPtr dom,
     int ret = -1;
     int nsnapshots;

-    virCheckFlags(VIR_DOMAIN_UNDEFINE_MANAGED_SAVE, -1);
+    virCheckFlags(VIR_DOMAIN_UNDEFINE_MANAGED_SAVE |
+                  VIR_DOMAIN_UNDEFINE_SNAPSHOTS_METADATA |
+                  VIR_DOMAIN_UNDEFINE_SNAPSHOTS_FULL, -1);

     qemuDriverLock(driver);
     vm = virDomainFindByUUID(&driver->domains, dom->uuid);
@@ -4874,10 +4891,24 @@ qemuDomainUndefineFlags(virDomainPtr dom,
                         "%s", _("cannot delete active domain"));
         goto cleanup;
     } else if ((nsnapshots = virDomainSnapshotObjListNum(&vm->snapshots))) {
-        qemuReportError(VIR_ERR_OPERATION_INVALID,
-                        _("cannot delete inactive domain with %d snapshots"),
-                        nsnapshots);
-        goto cleanup;
+        struct snap_remove rem;
+
+        if ((flags & (VIR_DOMAIN_UNDEFINE_SNAPSHOTS_METADATA |
+                      VIR_DOMAIN_UNDEFINE_SNAPSHOTS_FULL)) == 0) {
+            qemuReportError(VIR_ERR_OPERATION_INVALID,
+                            _("cannot delete inactive domain with %d "
+                              "snapshots"),
+                            nsnapshots);
+            goto cleanup;
+        }
+
+        rem.driver = driver;
+        rem.vm = vm;
+        rem.metadata_only = !(flags & VIR_DOMAIN_UNDEFINE_SNAPSHOTS_FULL);
+        rem.err = 0;
+        virHashForEach(vm->snapshots.objs, qemuDomainSnapshotDiscardAll, &rem);
+        if (rem.err < 0)
+            goto cleanup;
     }

     if (!vm->persistent) {
-- 
1.7.4.4




More information about the libvir-list mailing list