[PATCH 065/103] qemuBuildHostdevMediatedDevProps: Format USB host devices via JSON

Peter Krempa pkrempa at redhat.com
Thu Oct 7 15:17:53 UTC 2021


The 'usb-host' device has the following types according to QEMU for
properties we control:

  hostdevice=<str>
  hostbus=<uint32>       -  (default: 0)
  hostaddr=<uint32>      -  (default: 0)
  bootindex=<int32>

Signed-off-by: Peter Krempa <pkrempa at redhat.com>
---
 src/qemu/qemu_command.c | 46 ++++++++++++++++++++++++-----------------
 src/qemu/qemu_command.h |  7 ++++---
 src/qemu/qemu_hotplug.c |  6 +++---
 3 files changed, 34 insertions(+), 25 deletions(-)

diff --git a/src/qemu/qemu_command.c b/src/qemu/qemu_command.c
index 99287c013a..810a4cc760 100644
--- a/src/qemu/qemu_command.c
+++ b/src/qemu/qemu_command.c
@@ -4779,15 +4779,17 @@ qemuBuildPCIHostdevDevStr(const virDomainDef *def,
 }


-char *
-qemuBuildUSBHostdevDevStr(const virDomainDef *def,
-                          virDomainHostdevDef *dev,
-                          virQEMUCaps *qemuCaps)
+virJSONValue *
+qemuBuildUSBHostdevDevProps(const virDomainDef *def,
+                            virDomainHostdevDef *dev,
+                            virQEMUCaps *qemuCaps)
 {
-    g_auto(virBuffer) buf = VIR_BUFFER_INITIALIZER;
+    g_autoptr(virJSONValue) props = NULL;
     virDomainHostdevSubsysUSB *usbsrc = &dev->source.subsys.u.usb;
+    unsigned int hostbus = 0;
+    unsigned int hostaddr = 0;
+    g_autofree char *hostdevice = NULL;

-    virBufferAddLit(&buf, "usb-host");
     if (!dev->missing) {
         if (usbsrc->bus == 0 && usbsrc->device == 0) {
             virReportError(VIR_ERR_INTERNAL_ERROR, "%s",
@@ -4796,21 +4798,28 @@ qemuBuildUSBHostdevDevStr(const virDomainDef *def,
         }

         if (virQEMUCapsGet(qemuCaps, QEMU_CAPS_USB_HOST_HOSTDEVICE)) {
-            virBufferAsprintf(&buf, ",hostdevice=/dev/bus/usb/%03d/%03d",
-                              usbsrc->bus, usbsrc->device);
+            hostdevice = g_strdup_printf("/dev/bus/usb/%03d/%03d",
+                                         usbsrc->bus, usbsrc->device);
         } else {
-            virBufferAsprintf(&buf, ",hostbus=%d,hostaddr=%d",
-                              usbsrc->bus, usbsrc->device);
+            hostbus = usbsrc->bus;
+            hostaddr = usbsrc->device;
         }
     }
-    virBufferAsprintf(&buf, ",id=%s", dev->info->alias);
-    if (dev->info->bootIndex)
-        virBufferAsprintf(&buf, ",bootindex=%u", dev->info->bootIndex);

-    if (qemuBuildDeviceAddressStr(&buf, def, dev->info) < 0)
+    if (virJSONValueObjectCreate(&props,
+                                 "s:driver", "usb-host",
+                                 "S:hostdevice", hostdevice,
+                                 "p:hostbus", hostbus,
+                                 "p:hostaddr", hostaddr,
+                                 "s:id", dev->info->alias,
+                                 "p:bootindex",  dev->info->bootIndex,
+                                 NULL) < 0)
         return NULL;

-    return virBufferContentAndReset(&buf);
+    if (qemuBuildDeviceAddressProps(props, def, dev->info) < 0)
+        return NULL;
+
+    return g_steal_pointer(&props);
 }


@@ -5502,12 +5511,11 @@ qemuBuildHostdevCommandLine(virCommand *cmd,
         switch ((virDomainHostdevSubsysType) subsys->type) {
         /* USB */
         case VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_USB:
-            virCommandAddArg(cmd, "-device");
-            if (!(devstr =
-                  qemuBuildUSBHostdevDevStr(def, hostdev, qemuCaps)))
+            if (!(devprops = qemuBuildUSBHostdevDevProps(def, hostdev, qemuCaps)))
                 return -1;
-            virCommandAddArg(cmd, devstr);

+            if (qemuBuildDeviceCommandlineFromJSON(cmd, devprops, qemuCaps) < 0)
+                return -1;
             break;

         /* PCI */
diff --git a/src/qemu/qemu_command.h b/src/qemu/qemu_command.h
index 45a9cb0ac1..6995780f83 100644
--- a/src/qemu/qemu_command.h
+++ b/src/qemu/qemu_command.h
@@ -177,9 +177,10 @@ int qemuBuildRNGBackendProps(virDomainRNGDef *rng,
                              virJSONValue **props);

 /* Current, best practice */
-char *qemuBuildUSBHostdevDevStr(const virDomainDef *def,
-                                virDomainHostdevDef *dev,
-                                virQEMUCaps *qemuCaps);
+virJSONValue *
+qemuBuildUSBHostdevDevProps(const virDomainDef *def,
+                            virDomainHostdevDef *dev,
+                            virQEMUCaps *qemuCaps);

 char *qemuBuildSCSIHostdevDevStr(const virDomainDef *def,
                                  virDomainHostdevDef *dev,
diff --git a/src/qemu/qemu_hotplug.c b/src/qemu/qemu_hotplug.c
index 8250ca76a2..e1db3d55f3 100644
--- a/src/qemu/qemu_hotplug.c
+++ b/src/qemu/qemu_hotplug.c
@@ -2573,7 +2573,7 @@ qemuDomainAttachHostUSBDevice(virQEMUDriver *driver,
                               virDomainHostdevDef *hostdev)
 {
     qemuDomainObjPrivate *priv = vm->privateData;
-    g_autofree char *devstr = NULL;
+    g_autoptr(virJSONValue) devprops = NULL;
     bool added = false;
     bool teardowncgroup = false;
     bool teardownlabel = false;
@@ -2601,13 +2601,13 @@ qemuDomainAttachHostUSBDevice(virQEMUDriver *driver,

     if (qemuAssignDeviceHostdevAlias(vm->def, &hostdev->info->alias, -1) < 0)
         goto cleanup;
-    if (!(devstr = qemuBuildUSBHostdevDevStr(vm->def, hostdev, priv->qemuCaps)))
+    if (!(devprops = qemuBuildUSBHostdevDevProps(vm->def, hostdev, priv->qemuCaps)))
         goto cleanup;

     VIR_REALLOC_N(vm->def->hostdevs, vm->def->nhostdevs+1);

     qemuDomainObjEnterMonitor(driver, vm);
-    ret = qemuMonitorAddDevice(priv->mon, devstr);
+    ret = qemuMonitorAddDeviceProps(priv->mon, &devprops);
     if (qemuDomainObjExitMonitor(driver, vm) < 0) {
         ret = -1;
         goto cleanup;
-- 
2.31.1




More information about the libvir-list mailing list