diff --git a/src/qemu/qemu_domain.c b/src/qemu/qemu_domain.c index 39f3e38351..562fa76a78 100644 --- a/src/qemu/qemu_domain.c +++ b/src/qemu/qemu_domain.c @@ -4262,6 +4262,7 @@ qemuDomainDefAddDefaultDevices(virQEMUDriver *driver, bool addDefaultUSBMouse = false; bool addPanicDevice = false; bool addITCOWatchdog = false; + bool addIOMMU = false; /* add implicit input devices */ if (qemuDomainDefAddImplicitInputDevice(def, qemuCaps) < 0) @@ -4284,6 +4285,10 @@ qemuDomainDefAddDefaultDevices(virQEMUDriver *driver, addImplicitSATA = true; addITCOWatchdog = true; + if (virDomainDefGetVcpusMax(def) > QEMU_MAX_VCPUS_WITHOUT_EIM) { + addIOMMU = true; + } + /* Prefer adding a USB3 controller if supported, fall back * to USB2 if there is no USB3 available, and if that's * unavailable don't add anything. @@ -4530,6 +4535,21 @@ qemuDomainDefAddDefaultDevices(virQEMUDriver *driver, } } + if (addIOMMU && !def->iommu && + virQEMUCapsGet(qemuCaps, QEMU_CAPS_DEVICE_INTEL_IOMMU) && + virQEMUCapsGet(qemuCaps, QEMU_CAPS_INTEL_IOMMU_INTREMAP) && + virQEMUCapsGet(qemuCaps, QEMU_CAPS_INTEL_IOMMU_EIM)) { + g_autoptr(virDomainIOMMUDef) iommu = NULL; + + iommu = virDomainIOMMUDefNew(); + iommu->model = VIR_DOMAIN_IOMMU_MODEL_INTEL; + /* eim requires intremap. */ + iommu->intremap = VIR_TRISTATE_SWITCH_ON; + iommu->eim = VIR_TRISTATE_SWITCH_ON; + + def->iommu = g_steal_pointer(&iommu); + } + if (qemuDomainDefAddDefaultAudioBackend(driver, def) < 0) return -1; diff --git a/tests/qemuxmlconfdata/intel-iommu-eim-autoadd.xml b/tests/qemuxmlconfdata/intel-iommu-eim-autoadd.xml index 7c294fe2f9..fa3aaf0d44 100644 --- a/tests/qemuxmlconfdata/intel-iommu-eim-autoadd.xml +++ b/tests/qemuxmlconfdata/intel-iommu-eim-autoadd.xml @@ -30,6 +30,5 @@