[PATCH v3 4/5] qemu: command: add support for qemu options that enables/disables acpi hotplug

Ani Sinha ani at anisinha.ca
Sun Sep 12 03:26:30 UTC 2021


This change adds backend qemu commandline support for two new libvirt global
conf options:

<pm>
  <acpi-hotplug-bridge enabled='no'/>
  <acpi-root-hotplug enabled='yes'/>
</pm>

Additionally it adds validations to make sure that qemu has the capabilities
to support the above two options.
The details of the above two options are provided in the commit log for the
following commit:

69e01d2d3a50f ("conf: introduce acpi-hotplug-bridge and acpi-root-hotplug pm options")

'acpi-hotplug-bridge' turns on the following commandline option to qemu for
x86 guests:

(pc machines): -global PIIX4_PM.acpi-pci-hotplug-with-bridge-support=<off/on>
(q35 machines): -global ICH9-LPC.acpi-pci-hotplug-with-bridge-support=<off/on>

'acpi-root-hotplug' is only valid for pc machines and turns on the following
commandline option to qemu for x86 guests:

-global PIIX4_PM.acpi-root-pci-hotplug=<off/on>

This change also adds the required qemuxml2argv unit tests in order to test
correct qemu arguments. Also unit tests have been added to test qemu capability
validation checks.

Signed-off-by: Ani Sinha <ani at anisinha.ca>
---
 src/qemu/qemu_command.c                       | 28 +++++++++++++++++
 src/qemu/qemu_validate.c                      | 21 +++++++++++++
 ...pc-i440fx-acpi-hotplug-bridge-disable.args | 29 +++++++++++++++++
 .../pc-i440fx-acpi-hotplug-bridge-enable.err  |  1 +
 .../pc-i440fx-acpi-root-hotplug-disable.args  | 29 +++++++++++++++++
 .../pc-i440fx-acpi-root-hotplug-enable.err    |  1 +
 .../q35-acpi-hotplug-bridge-disable.args      | 31 +++++++++++++++++++
 .../q35-acpi-hotplug-bridge-enable.err        |  1 +
 tests/qemuxml2argvtest.c                      | 18 +++++++++++
 9 files changed, 159 insertions(+)
 create mode 100644 tests/qemuxml2argvdata/pc-i440fx-acpi-hotplug-bridge-disable.args
 create mode 100644 tests/qemuxml2argvdata/pc-i440fx-acpi-hotplug-bridge-enable.err
 create mode 100644 tests/qemuxml2argvdata/pc-i440fx-acpi-root-hotplug-disable.args
 create mode 100644 tests/qemuxml2argvdata/pc-i440fx-acpi-root-hotplug-enable.err
 create mode 100644 tests/qemuxml2argvdata/q35-acpi-hotplug-bridge-disable.args
 create mode 100644 tests/qemuxml2argvdata/q35-acpi-hotplug-bridge-enable.err

diff --git a/src/qemu/qemu_command.c b/src/qemu/qemu_command.c
index 4d29313f45..f23b9a7b1d 100644
--- a/src/qemu/qemu_command.c
+++ b/src/qemu/qemu_command.c
@@ -6197,6 +6197,34 @@ qemuBuildPMCommandLine(virCommand *cmd,
                                pm_object, def->pm.s4 == VIR_TRISTATE_BOOL_NO);
     }
 
+    if (def->pm.acpi_hp_bridge) {
+        const char *pm_object = "PIIX4_PM";
+        const char *switch_str = "on";
+
+        if (def->pm.acpi_hp_bridge == VIR_TRISTATE_BOOL_NO)
+            switch_str = "off";
+
+        if (qemuDomainIsQ35(def) &&
+            virQEMUCapsGet(qemuCaps, QEMU_CAPS_ICH9_ACPI_HOTPLUG_BRIDGE))
+            pm_object = "ICH9-LPC";
+
+        virCommandAddArg(cmd, "-global");
+        virCommandAddArgFormat(cmd, "%s.acpi-pci-hotplug-with-bridge-support=%s",
+                               pm_object, switch_str);
+    }
+
+    if (def->pm.acpi_root_hp) {
+        const char *pm_object = "PIIX4_PM";
+        const char *switch_str = "on";
+
+        if (def->pm.acpi_root_hp == VIR_TRISTATE_BOOL_NO)
+            switch_str = "off";
+
+        virCommandAddArg(cmd, "-global");
+        virCommandAddArgFormat(cmd, "%s.acpi-root-pci-hotplug=%s",
+                               pm_object, switch_str);
+    }
+
     return 0;
 }
 
diff --git a/src/qemu/qemu_validate.c b/src/qemu/qemu_validate.c
index 9d93f373ab..9bde0e1f0a 100644
--- a/src/qemu/qemu_validate.c
+++ b/src/qemu/qemu_validate.c
@@ -561,6 +561,27 @@ qemuValidateDomainDefPM(const virDomainDef *def,
         }
     }
 
+    if (def->pm.acpi_hp_bridge) {
+        bool q35ICH9_pcihpbr = q35Dom &&
+                                virQEMUCapsGet(qemuCaps,
+                                              QEMU_CAPS_ICH9_ACPI_HOTPLUG_BRIDGE);
+
+        if (!q35ICH9_pcihpbr && !virQEMUCapsGet(qemuCaps,
+                                                QEMU_CAPS_PIIX_ACPI_HOTPLUG_BRIDGE)) {
+            virReportError(VIR_ERR_CONFIG_UNSUPPORTED,
+                           "%s", _("setting ACPI hotplug bridge not supported"));
+            return -1;
+        }
+    }
+
+    if (def->pm.acpi_root_hp) {
+        if (!q35Dom && !virQEMUCapsGet(qemuCaps, QEMU_CAPS_PIIX_ACPI_ROOT_PCI_HOTPLUG)) {
+            virReportError(VIR_ERR_CONFIG_UNSUPPORTED,
+                           "%s", _("setting ACPI root pci hotplug not supported"));
+            return -1;
+        }
+    }
+
     return 0;
 }
 
diff --git a/tests/qemuxml2argvdata/pc-i440fx-acpi-hotplug-bridge-disable.args b/tests/qemuxml2argvdata/pc-i440fx-acpi-hotplug-bridge-disable.args
new file mode 100644
index 0000000000..1eed691975
--- /dev/null
+++ b/tests/qemuxml2argvdata/pc-i440fx-acpi-hotplug-bridge-disable.args
@@ -0,0 +1,29 @@
+LC_ALL=C \
+PATH=/bin \
+HOME=/tmp/lib/domain--1-i440fx \
+USER=test \
+LOGNAME=test \
+XDG_DATA_HOME=/tmp/lib/domain--1-i440fx/.local/share \
+XDG_CACHE_HOME=/tmp/lib/domain--1-i440fx/.cache \
+XDG_CONFIG_HOME=/tmp/lib/domain--1-i440fx/.config \
+QEMU_AUDIO_DRV=none \
+/usr/bin/qemu-system-x86_64 \
+-name guest=i440fx,debug-threads=on \
+-S \
+-machine pc-i440fx-2.5,accel=tcg,usb=off,dump-guest-core=off \
+-m 1024 \
+-realtime mlock=off \
+-smp 1,sockets=1,cores=1,threads=1 \
+-uuid 56f5055c-1b8d-490c-844a-ad646a1caaaa \
+-display none \
+-no-user-config \
+-nodefaults \
+-chardev socket,id=charmonitor,path=/tmp/lib/domain--1-i440fx/monitor.sock,server=on,wait=off \
+-mon chardev=charmonitor,id=monitor,mode=control \
+-rtc base=utc \
+-no-shutdown \
+-no-acpi \
+-global PIIX4_PM.acpi-pci-hotplug-with-bridge-support=off \
+-usb \
+-device virtio-balloon-pci,id=balloon0,bus=pci.0,addr=0x2 \
+-msg timestamp=on
diff --git a/tests/qemuxml2argvdata/pc-i440fx-acpi-hotplug-bridge-enable.err b/tests/qemuxml2argvdata/pc-i440fx-acpi-hotplug-bridge-enable.err
new file mode 100644
index 0000000000..98211b726f
--- /dev/null
+++ b/tests/qemuxml2argvdata/pc-i440fx-acpi-hotplug-bridge-enable.err
@@ -0,0 +1 @@
+unsupported configuration: setting ACPI hotplug bridge not supported
diff --git a/tests/qemuxml2argvdata/pc-i440fx-acpi-root-hotplug-disable.args b/tests/qemuxml2argvdata/pc-i440fx-acpi-root-hotplug-disable.args
new file mode 100644
index 0000000000..6f1e2814bf
--- /dev/null
+++ b/tests/qemuxml2argvdata/pc-i440fx-acpi-root-hotplug-disable.args
@@ -0,0 +1,29 @@
+LC_ALL=C \
+PATH=/bin \
+HOME=/tmp/lib/domain--1-i440fx \
+USER=test \
+LOGNAME=test \
+XDG_DATA_HOME=/tmp/lib/domain--1-i440fx/.local/share \
+XDG_CACHE_HOME=/tmp/lib/domain--1-i440fx/.cache \
+XDG_CONFIG_HOME=/tmp/lib/domain--1-i440fx/.config \
+QEMU_AUDIO_DRV=none \
+/usr/bin/qemu-system-x86_64 \
+-name guest=i440fx,debug-threads=on \
+-S \
+-machine pc-i440fx-2.5,accel=tcg,usb=off,dump-guest-core=off \
+-m 1024 \
+-realtime mlock=off \
+-smp 1,sockets=1,cores=1,threads=1 \
+-uuid 56f5055c-1b8d-490c-844a-ad646a1caaaa \
+-display none \
+-no-user-config \
+-nodefaults \
+-chardev socket,id=charmonitor,path=/tmp/lib/domain--1-i440fx/monitor.sock,server=on,wait=off \
+-mon chardev=charmonitor,id=monitor,mode=control \
+-rtc base=utc \
+-no-shutdown \
+-no-acpi \
+-global PIIX4_PM.acpi-root-pci-hotplug=off \
+-usb \
+-device virtio-balloon-pci,id=balloon0,bus=pci.0,addr=0x2 \
+-msg timestamp=on
diff --git a/tests/qemuxml2argvdata/pc-i440fx-acpi-root-hotplug-enable.err b/tests/qemuxml2argvdata/pc-i440fx-acpi-root-hotplug-enable.err
new file mode 100644
index 0000000000..c5c9de8389
--- /dev/null
+++ b/tests/qemuxml2argvdata/pc-i440fx-acpi-root-hotplug-enable.err
@@ -0,0 +1 @@
+unsupported configuration: setting ACPI root pci hotplug not supported
diff --git a/tests/qemuxml2argvdata/q35-acpi-hotplug-bridge-disable.args b/tests/qemuxml2argvdata/q35-acpi-hotplug-bridge-disable.args
new file mode 100644
index 0000000000..b88dd251b0
--- /dev/null
+++ b/tests/qemuxml2argvdata/q35-acpi-hotplug-bridge-disable.args
@@ -0,0 +1,31 @@
+LC_ALL=C \
+PATH=/bin \
+HOME=/tmp/lib/domain--1-q35 \
+USER=test \
+LOGNAME=test \
+XDG_DATA_HOME=/tmp/lib/domain--1-q35/.local/share \
+XDG_CACHE_HOME=/tmp/lib/domain--1-q35/.cache \
+XDG_CONFIG_HOME=/tmp/lib/domain--1-q35/.config \
+QEMU_AUDIO_DRV=none \
+/usr/bin/qemu-system-x86_64 \
+-name guest=q35,debug-threads=on \
+-S \
+-machine pc-q35-2.5,accel=tcg,usb=off,dump-guest-core=off \
+-m 1024 \
+-realtime mlock=off \
+-smp 1,sockets=1,cores=1,threads=1 \
+-uuid 56f5055c-1b8d-490c-844a-ad646a1caaaa \
+-display none \
+-no-user-config \
+-nodefaults \
+-chardev socket,id=charmonitor,path=/tmp/lib/domain--1-q35/monitor.sock,server=on,wait=off \
+-mon chardev=charmonitor,id=monitor,mode=control \
+-rtc base=utc \
+-no-shutdown \
+-no-acpi \
+-global ICH9-LPC.acpi-pci-hotplug-with-bridge-support=off \
+-device i82801b11-bridge,id=pci.1,bus=pcie.0,addr=0x1e \
+-device pci-bridge,chassis_nr=2,id=pci.2,bus=pci.1,addr=0x0 \
+-device ioh3420,port=0x8,chassis=3,id=pci.3,bus=pcie.0,addr=0x1 \
+-device virtio-balloon-pci,id=balloon0,bus=pci.2,addr=0x1 \
+-msg timestamp=on
diff --git a/tests/qemuxml2argvdata/q35-acpi-hotplug-bridge-enable.err b/tests/qemuxml2argvdata/q35-acpi-hotplug-bridge-enable.err
new file mode 100644
index 0000000000..98211b726f
--- /dev/null
+++ b/tests/qemuxml2argvdata/q35-acpi-hotplug-bridge-enable.err
@@ -0,0 +1 @@
+unsupported configuration: setting ACPI hotplug bridge not supported
diff --git a/tests/qemuxml2argvtest.c b/tests/qemuxml2argvtest.c
index 74af93b08f..6e80b9cedf 100644
--- a/tests/qemuxml2argvtest.c
+++ b/tests/qemuxml2argvtest.c
@@ -2629,6 +2629,24 @@ mymain(void)
             QEMU_CAPS_DEVICE_IOH3420,
             QEMU_CAPS_DEVICE_DMI_TO_PCI_BRIDGE, QEMU_CAPS_ICH9_AHCI,
             QEMU_CAPS_PIIX_DISABLE_S3, QEMU_CAPS_PIIX_DISABLE_S4);
+    DO_TEST("q35-acpi-hotplug-bridge-disable",
+            QEMU_CAPS_DEVICE_PCI_BRIDGE,
+            QEMU_CAPS_DEVICE_IOH3420,
+            QEMU_CAPS_DEVICE_DMI_TO_PCI_BRIDGE, QEMU_CAPS_ICH9_AHCI,
+            QEMU_CAPS_ICH9_ACPI_HOTPLUG_BRIDGE);
+    DO_TEST("pc-i440fx-acpi-hotplug-bridge-disable",
+            QEMU_CAPS_DEVICE_PCI_BRIDGE,
+            QEMU_CAPS_DEVICE_IOH3420,
+            QEMU_CAPS_DEVICE_DMI_TO_PCI_BRIDGE,
+            QEMU_CAPS_PIIX_ACPI_HOTPLUG_BRIDGE);
+    DO_TEST("pc-i440fx-acpi-root-hotplug-disable",
+            QEMU_CAPS_DEVICE_PCI_BRIDGE,
+            QEMU_CAPS_DEVICE_IOH3420,
+            QEMU_CAPS_DEVICE_DMI_TO_PCI_BRIDGE,
+            QEMU_CAPS_PIIX_ACPI_ROOT_PCI_HOTPLUG);
+    DO_TEST_PARSE_ERROR_NOCAPS("q35-acpi-hotplug-bridge-enable");
+    DO_TEST_PARSE_ERROR_NOCAPS("pc-i440fx-acpi-hotplug-bridge-enable");
+    DO_TEST_PARSE_ERROR_NOCAPS("pc-i440fx-acpi-root-hotplug-enable");
     DO_TEST("q35-usb2",
             QEMU_CAPS_DEVICE_PCI_BRIDGE,
             QEMU_CAPS_DEVICE_DMI_TO_PCI_BRIDGE,
-- 
2.25.1




More information about the libvir-list mailing list