[libvirt] [PATCH 1/2] qemu: Copy complete domain def in qemuDomainDefFormatBuf

Jiri Denemark jdenemar at redhat.com
Fri Jul 8 15:40:29 UTC 2016


Playing directly with our live definition, updating it, and reverting it
back once we are done is very nice and it's quite dangerous too. Let's
just make a copy of the domain definition if needed and do all tricks on
the copy.

https://bugzilla.redhat.com/show_bug.cgi?id=1320470

Signed-off-by: Jiri Denemark <jdenemar at redhat.com>
---
 src/conf/domain_conf.c | 10 ++++++----
 src/qemu/qemu_domain.c | 44 ++++++++++++++++++++++++--------------------
 2 files changed, 30 insertions(+), 24 deletions(-)

diff --git a/src/conf/domain_conf.c b/src/conf/domain_conf.c
index cf5eb1d..72ff5c1 100644
--- a/src/conf/domain_conf.c
+++ b/src/conf/domain_conf.c
@@ -21039,10 +21039,12 @@ virDomainChrSourceDefFormat(virBufferPtr buf,
         break;
 
     case VIR_DOMAIN_CHR_TYPE_UNIX:
-        virBufferAsprintf(buf, "<source mode='%s'",
-                          def->data.nix.listen ? "bind" : "connect");
-        virBufferEscapeString(buf, " path='%s'", def->data.nix.path);
-        virDomainSourceDefFormatSeclabel(buf, nseclabels, seclabels, flags);
+        if (def->data.nix.path) {
+            virBufferAsprintf(buf, "<source mode='%s'",
+                              def->data.nix.listen ? "bind" : "connect");
+            virBufferEscapeString(buf, " path='%s'", def->data.nix.path);
+            virDomainSourceDefFormatSeclabel(buf, nseclabels, seclabels, flags);
+        }
         break;
 
     case VIR_DOMAIN_CHR_TYPE_SPICEPORT:
diff --git a/src/qemu/qemu_domain.c b/src/qemu/qemu_domain.c
index 930e0b7..1b0279b 100644
--- a/src/qemu/qemu_domain.c
+++ b/src/qemu/qemu_domain.c
@@ -3071,19 +3071,25 @@ qemuDomainDefFormatBuf(virQEMUDriverPtr driver,
                        virBuffer *buf)
 {
     int ret = -1;
-    virCPUDefPtr cpu = NULL;
-    virCPUDefPtr def_cpu = def->cpu;
-    virDomainControllerDefPtr *controllers = NULL;
-    int ncontrollers = 0;
+    virDomainDefPtr copy = NULL;
     virCapsPtr caps = NULL;
 
     if (!(caps = virQEMUDriverGetCapabilities(driver, false)))
         goto cleanup;
 
+    if (!(flags & (VIR_DOMAIN_XML_UPDATE_CPU | VIR_DOMAIN_XML_MIGRATABLE)))
+        goto format;
+
+    if (!(copy = virDomainDefCopy(def, caps, driver->xmlopt,
+                                  flags & VIR_DOMAIN_XML_MIGRATABLE)))
+        goto cleanup;
+
+    def = copy;
+
     /* Update guest CPU requirements according to host CPU */
     if ((flags & VIR_DOMAIN_XML_UPDATE_CPU) &&
-        def_cpu &&
-        (def_cpu->mode != VIR_CPU_MODE_CUSTOM || def_cpu->model)) {
+        def->cpu &&
+        (def->cpu->mode != VIR_CPU_MODE_CUSTOM || def->cpu->model)) {
         if (!caps->host.cpu ||
             !caps->host.cpu->model) {
             virReportError(VIR_ERR_OPERATION_FAILED,
@@ -3091,10 +3097,8 @@ qemuDomainDefFormatBuf(virQEMUDriverPtr driver,
             goto cleanup;
         }
 
-        if (!(cpu = virCPUDefCopy(def_cpu)) ||
-            cpuUpdate(cpu, caps->host.cpu) < 0)
+        if (cpuUpdate(def->cpu, caps->host.cpu) < 0)
             goto cleanup;
-        def->cpu = cpu;
     }
 
     if ((flags & VIR_DOMAIN_XML_MIGRATABLE)) {
@@ -3151,10 +3155,11 @@ qemuDomainDefFormatBuf(virQEMUDriverPtr driver,
         }
 
         if (toremove) {
-            controllers = def->controllers;
-            ncontrollers = def->ncontrollers;
+            virDomainControllerDefPtr *controllers = def->controllers;
+            int ncontrollers = def->ncontrollers;
+
             if (VIR_ALLOC_N(def->controllers, ncontrollers - toremove) < 0) {
-                controllers = NULL;
+                def->controllers = controllers;
                 goto cleanup;
             }
 
@@ -3163,23 +3168,22 @@ qemuDomainDefFormatBuf(virQEMUDriverPtr driver,
                 if (controllers[i] != usb && controllers[i] != pci)
                     def->controllers[def->ncontrollers++] = controllers[i];
             }
+
+            VIR_FREE(controllers);
+            virDomainControllerDefFree(pci);
+            virDomainControllerDefFree(usb);
         }
 
 
     }
 
-    ret = virDomainDefFormatInternal(def, driver->caps,
+ format:
+    ret = virDomainDefFormatInternal(def, caps,
                                      virDomainDefFormatConvertXMLFlags(flags),
                                      buf);
 
  cleanup:
-    def->cpu = def_cpu;
-    virCPUDefFree(cpu);
-    if (controllers) {
-        VIR_FREE(def->controllers);
-        def->controllers = controllers;
-        def->ncontrollers = ncontrollers;
-    }
+    virDomainDefFree(copy);
     virObjectUnref(caps);
     return ret;
 }
-- 
2.9.0




More information about the libvir-list mailing list