[libvirt] [PATCH 06/13] qemu: Generate and use zPCI device in QEMU command line

Xiao Feng Ren renxiaof at linux.vnet.ibm.com
Thu May 24 12:24:31 UTC 2018


From: Yi Min Zhao <zyimin at linux.ibm.com>

Add new functions to generate zPCI command string and append it to
QEMU command line.

Signed-off-by: Yi Min Zhao <zyimin at linux.ibm.com>
Reviewed-by: Boris Fiuczynski <fiuczy at linux.vnet.ibm.com>
Reviewed-by: Stefan Zimmermann <stzi at linux.ibm.com>
Reviewed-by: Bjoern Walk <bwalk at linux.vnet.ibm.com>
---
 src/qemu/qemu_command.c | 104 ++++++++++++++++++++++++++++++++++++++++++++++++
 src/qemu/qemu_command.h |   4 ++
 2 files changed, 108 insertions(+)

diff --git a/src/qemu/qemu_command.c b/src/qemu/qemu_command.c
index cb397c7558..ad10846d73 100644
--- a/src/qemu/qemu_command.c
+++ b/src/qemu/qemu_command.c
@@ -2167,6 +2167,68 @@ qemuBuildDriveDevStr(const virDomainDef *def,
     return NULL;
 }
 
+char *
+qemuBuildZPCIDevStr(virDomainDeviceInfoPtr dev)
+{
+    virBuffer buf = VIR_BUFFER_INITIALIZER;
+
+    virBufferAddLit(&buf, "zpci");
+    virBufferAsprintf(&buf, ",uid=%u", dev->addr.pci.zpci->zpciuid);
+    virBufferAsprintf(&buf, ",fid=%u", dev->addr.pci.zpci->zpcifid);
+    virBufferAsprintf(&buf, ",target=%s", dev->alias);
+    virBufferAsprintf(&buf, ",id=zpci%u", dev->addr.pci.zpci->zpciuid);
+
+    if (virBufferCheckError(&buf) < 0) {
+        virBufferFreeAndReset(&buf);
+        return NULL;
+    }
+
+    return virBufferContentAndReset(&buf);
+}
+
+bool
+qemuCheckDeviceIsZPCI(virDomainDeviceInfoPtr info)
+{
+    if (info->type == VIR_DOMAIN_DEVICE_ADDRESS_TYPE_PCI &&
+        ((info->pciAddressExtFlags & VIR_PCI_ADDRESS_EXTENSION_ZPCI) ||
+         info->addr.pci.zpci))
+        return true;
+
+    return false;
+}
+
+static int
+qemuAppendZPCIDevStr(virCommandPtr cmd,
+                     virDomainDeviceInfoPtr dev)
+{
+    char *devstr = NULL;
+
+    virCommandAddArg(cmd, "-device");
+    if (!(devstr = qemuBuildZPCIDevStr(dev)))
+        return -1;
+
+    virCommandAddArg(cmd, devstr);
+
+    VIR_FREE(devstr);
+    return 0;
+}
+
+static int
+qemuBuildExtensionCommandLine(virCommandPtr cmd,
+                              virQEMUCapsPtr qemuCaps,
+                              virDomainDeviceInfoPtr dev)
+{
+    if (qemuCheckDeviceIsZPCI(dev)) {
+        if (!virQEMUCapsGet(qemuCaps, QEMU_CAPS_DEVICE_ZPCI)) {
+            virReportError(VIR_ERR_CONFIG_UNSUPPORTED, "%s",
+                           _("This QEMU doesn't support zpci devices"));
+            return -1;
+        }
+        return qemuAppendZPCIDevStr(cmd, dev);
+    }
+
+    return 0;
+}
 
 static int
 qemuBulildFloppyCommandLineOptions(virCommandPtr cmd,
@@ -2311,6 +2373,9 @@ qemuBuildDiskDriveCommandLine(virCommandPtr cmd,
                                                        bootindex) < 0)
                     return -1;
             } else {
+                if (qemuBuildExtensionCommandLine(cmd, qemuCaps, &disk->info) < 0)
+                    return -1;
+
                 virCommandAddArg(cmd, "-device");
 
                 if (!(optstr = qemuBuildDriveDevStr(def, disk, bootindex,
@@ -2443,6 +2508,9 @@ qemuBuildFSDevCommandLine(virCommandPtr cmd,
         virCommandAddArg(cmd, optstr);
         VIR_FREE(optstr);
 
+        if (qemuBuildExtensionCommandLine(cmd, qemuCaps, &fs->info) < 0)
+            return -1;
+
         virCommandAddArg(cmd, "-device");
         if (!(optstr = qemuBuildFSDevStr(def, fs, qemuCaps)))
             return -1;
@@ -3745,6 +3813,9 @@ qemuBuildWatchdogCommandLine(virCommandPtr cmd,
     if (!def->watchdog)
         return 0;
 
+    if (qemuBuildExtensionCommandLine(cmd, qemuCaps, &def->watchdog->info) < 0)
+        return -1;
+
     virCommandAddArg(cmd, "-device");
 
     optstr = qemuBuildWatchdogDevStr(def, watchdog, qemuCaps);
@@ -3829,6 +3900,9 @@ qemuBuildMemballoonCommandLine(virCommandPtr cmd,
     if (qemuBuildVirtioOptionsStr(&buf, def->memballoon->virtio, qemuCaps) < 0)
         goto error;
 
+    if (qemuBuildExtensionCommandLine(cmd, qemuCaps, &def->memballoon->info) < 0)
+        goto error;
+
     virCommandAddArg(cmd, "-device");
     virCommandAddArgBuffer(cmd, &buf);
     return 0;
@@ -4051,6 +4125,9 @@ qemuBuildInputCommandLine(virCommandPtr cmd,
         virDomainInputDefPtr input = def->inputs[i];
         char *devstr = NULL;
 
+        if (qemuBuildExtensionCommandLine(cmd, qemuCaps, &input->info) < 0)
+            return -1;
+
         if (qemuBuildInputDevStr(&devstr, def, input, qemuCaps) < 0)
             return -1;
 
@@ -4192,6 +4269,9 @@ qemuBuildSoundCommandLine(virCommandPtr cmd,
         if (sound->model == VIR_DOMAIN_SOUND_MODEL_PCSPK) {
             virCommandAddArgList(cmd, "-soundhw", "pcspk", NULL);
         } else {
+            if (qemuBuildExtensionCommandLine(cmd, qemuCaps, &sound->info) < 0)
+                return -1;
+
             virCommandAddArg(cmd, "-device");
             if (!(str = qemuBuildSoundDevStr(def, sound, qemuCaps)))
                 return -1;
@@ -4428,6 +4508,8 @@ qemuBuildVideoCommandLine(virCommandPtr cmd,
         if (video->primary) {
             if (virQEMUCapsGet(qemuCaps, QEMU_CAPS_DEVICE_VIDEO_PRIMARY)) {
 
+                if (qemuBuildExtensionCommandLine(cmd, qemuCaps, &def->videos[i]->info) < 0)
+                    return -1;
                 virCommandAddArg(cmd, "-device");
 
                 if (!(str = qemuBuildDeviceVideoStr(def, video, qemuCaps)))
@@ -4440,6 +4522,9 @@ qemuBuildVideoCommandLine(virCommandPtr cmd,
                     return -1;
             }
         } else {
+            if (qemuBuildExtensionCommandLine(cmd, qemuCaps, &def->videos[i]->info) < 0)
+                return -1;
+
             virCommandAddArg(cmd, "-device");
 
             if (!(str = qemuBuildDeviceVideoStr(def, video, qemuCaps)))
@@ -5209,6 +5294,10 @@ qemuBuildHostdevCommandLine(virCommandPtr cmd,
                                      VIR_COMMAND_PASS_FD_CLOSE_PARENT);
                 }
             }
+
+            if (qemuBuildExtensionCommandLine(cmd, qemuCaps, hostdev->info) < 0)
+                return -1;
+
             virCommandAddArg(cmd, "-device");
             devstr = qemuBuildPCIHostdevDevStr(def, hostdev, bootIndex,
                                                configfd_name, qemuCaps);
@@ -5673,6 +5762,9 @@ qemuBuildRNGCommandLine(virLogManagerPtr logManager,
         VIR_FREE(tmp);
 
         /* add the device */
+        if (qemuBuildExtensionCommandLine(cmd, qemuCaps, &rng->info) < 0)
+            return -1;
+
         if (!(tmp = qemuBuildRNGDevStr(def, rng, qemuCaps)))
             return -1;
         virCommandAddArgList(cmd, "-device", tmp, NULL);
@@ -8109,6 +8201,9 @@ qemuBuildVhostuserCommandLine(virQEMUDriverPtr driver,
     virCommandAddArg(cmd, netdev);
     VIR_FREE(netdev);
 
+    if (qemuBuildExtensionCommandLine(cmd, qemuCaps, &net->info) < 0)
+        goto error;
+
     if (!(nic = qemuBuildNicDevStr(def, net, -1, bootindex,
                                    queues, qemuCaps))) {
         virReportError(VIR_ERR_INTERNAL_ERROR,
@@ -8400,6 +8495,9 @@ qemuBuildInterfaceCommandLine(virQEMUDriverPtr driver,
             goto cleanup;
         virCommandAddArgList(cmd, "-netdev", host, NULL);
 
+        if (qemuBuildExtensionCommandLine(cmd, qemuCaps, &net->info) < 0)
+            goto cleanup;
+
         if (!(nic = qemuBuildNicDevStr(def, net, vlan, bootindex,
                                        vhostfdSize, qemuCaps)))
             goto cleanup;
@@ -8857,6 +8955,9 @@ qemuBuildShmemCommandLine(virLogManagerPtr logManager,
 
     switch ((virDomainShmemModel)shmem->model) {
     case VIR_DOMAIN_SHMEM_MODEL_IVSHMEM:
+        if (qemuBuildExtensionCommandLine(cmd, qemuCaps, &shmem->info) < 0)
+            return -1;
+
         devstr = qemuBuildShmemDevLegacyStr(def, shmem, qemuCaps);
         break;
 
@@ -8869,6 +8970,9 @@ qemuBuildShmemCommandLine(virLogManagerPtr logManager,
 
         ATTRIBUTE_FALLTHROUGH;
     case VIR_DOMAIN_SHMEM_MODEL_IVSHMEM_DOORBELL:
+        if (qemuBuildExtensionCommandLine(cmd, qemuCaps, &shmem->info) < 0)
+            return -1;
+
         devstr = qemuBuildShmemDevStr(def, shmem, qemuCaps);
         break;
 
diff --git a/src/qemu/qemu_command.h b/src/qemu/qemu_command.h
index bbbf152660..7100af477f 100644
--- a/src/qemu/qemu_command.h
+++ b/src/qemu/qemu_command.h
@@ -172,6 +172,10 @@ char *qemuBuildRedirdevDevStr(const virDomainDef *def,
                               virDomainRedirdevDefPtr dev,
                               virQEMUCapsPtr qemuCaps);
 
+char *qemuBuildZPCIDevStr(virDomainDeviceInfoPtr dev);
+
+bool qemuCheckDeviceIsZPCI(virDomainDeviceInfoPtr info);
+
 int qemuNetworkPrepareDevices(virDomainDefPtr def);
 
 int qemuGetDriveSourceString(virStorageSourcePtr src,
-- 
2.16.3




More information about the libvir-list mailing list