Blob Blame History Raw
From 4fc22ae3f2a6894e26e996918d48e8cb8b4ca591 Mon Sep 17 00:00:00 2001
Message-Id: <4fc22ae3f2a6894e26e996918d48e8cb8b4ca591@dist-git>
From: Jiri Denemark <jdenemar@redhat.com>
Date: Fri, 8 Jul 2016 17:25:03 +0200
Subject: [PATCH] qemu: Drop default channel path during migration

Migration to an older libvirt (pre v1.3.0-175-g7140807) is broken
because older versions of libvirt generated different channel paths and
they didn't drop the default paths when parsing domain XMLs. We'd get
such a nice error message:

    internal error: process exited while connecting to monitor:
    2016-07-08T15:28:02.665706Z qemu-kvm: -chardev socket,
    id=charchannel0,path=/var/lib/libvirt/qemu/channel/target/
    domain-3-nest/org.qemu.guest_agent.0,server,nowait: Failed to bind
    socket to /var/lib/libvirt/qemu/channel/target/domain-3-nest/
    org.qemu.guest_agent.0: No such file or directory

That said, we should not even format the default paths when generating a
migratable XML.

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

Signed-off-by: Jiri Denemark <jdenemar@redhat.com>
(cherry picked from commit 08d566a0cf7ed052b6ab3c9bd93f04156999d80b)
Signed-off-by: Jiri Denemark <jdenemar@redhat.com>
---
 src/qemu/qemu_domain.c | 43 +++++++++++++++++++++++++++----------------
 1 file changed, 27 insertions(+), 16 deletions(-)

diff --git a/src/qemu/qemu_domain.c b/src/qemu/qemu_domain.c
index e81e63f..5b4d7a3 100644
--- a/src/qemu/qemu_domain.c
+++ b/src/qemu/qemu_domain.c
@@ -2254,6 +2254,29 @@ qemuDomainDefaultNetModel(const virDomainDef *def,
     return "rtl8139";
 }
 
+
+/*
+ * Clear auto generated unix socket path, i.e., the one which starts with our
+ * channel directory.
+ */
+static void
+qemuDomainChrDefDropDefaultPath(virDomainChrDefPtr chr,
+                                virQEMUDriverPtr driver)
+{
+    virQEMUDriverConfigPtr cfg = virQEMUDriverGetConfig(driver);
+
+    if (chr->deviceType == VIR_DOMAIN_CHR_DEVICE_TYPE_CHANNEL &&
+        chr->targetType == VIR_DOMAIN_CHR_CHANNEL_TARGET_TYPE_VIRTIO &&
+        chr->source.type == VIR_DOMAIN_CHR_TYPE_UNIX &&
+        chr->source.data.nix.path &&
+        STRPREFIX(chr->source.data.nix.path, cfg->channelTargetDir)) {
+        VIR_FREE(chr->source.data.nix.path);
+    }
+
+    virObjectUnref(cfg);
+}
+
+
 static int
 qemuDomainDeviceDefPostParse(virDomainDeviceDefPtr dev,
                              const virDomainDef *def,
@@ -2335,21 +2358,8 @@ qemuDomainDeviceDefPostParse(virDomainDeviceDefPtr dev,
 
     /* clear auto generated unix socket path for inactive definitions */
     if ((parseFlags & VIR_DOMAIN_DEF_PARSE_INACTIVE) &&
-        dev->type == VIR_DOMAIN_DEVICE_CHR &&
-        dev->data.chr->deviceType == VIR_DOMAIN_CHR_DEVICE_TYPE_CHANNEL &&
-        dev->data.chr->targetType == VIR_DOMAIN_CHR_CHANNEL_TARGET_TYPE_VIRTIO &&
-        dev->data.chr->source.type == VIR_DOMAIN_CHR_TYPE_UNIX &&
-        dev->data.chr->source.data.nix.path &&
-        STRPREFIX(dev->data.chr->source.data.nix.path, cfg->channelTargetDir)) {
-        /*
-         * If the address is generated by us (starts with our
-         * channel dir), we should not keep it in the persistent
-         * XML.  If libvirt is the one who generated it, users
-         * shouldn't care about that.  If they do, they are
-         * supposed to set it themselves.
-         */
-        VIR_FREE(dev->data.chr->source.data.nix.path);
-    }
+        dev->type == VIR_DOMAIN_DEVICE_CHR)
+        qemuDomainChrDefDropDefaultPath(dev->data.chr, driver);
 
     /* forbid capabilities mode hostdev in this kind of hypervisor */
     if (dev->type == VIR_DOMAIN_DEVICE_HOSTDEV &&
@@ -3164,7 +3174,8 @@ qemuDomainDefFormatBuf(virQEMUDriverPtr driver,
             virDomainControllerDefFree(usb);
         }
 
-
+        for (i = 0; i < def->nchannels; i++)
+            qemuDomainChrDefDropDefaultPath(def->channels[i], driver);
     }
 
  format:
-- 
2.9.2