[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
[PATCH v3 6/6] hw/arm/virt: Allow user-creatable SMMUv3 dev instantiatio
From: |
Shameer Kolothum |
Subject: |
[PATCH v3 6/6] hw/arm/virt: Allow user-creatable SMMUv3 dev instantiation |
Date: |
Mon, 2 Jun 2025 16:41:10 +0100 |
Allow cold-plug of smmuv3 device to virt if there is no machine
wide legacy smmuv3 or a virtio-iommu is specified.
Device tree support for new smmuv3 dev is limited to the case where
it is associated with the default pcie.0 RC.
Signed-off-by: Shameer Kolothum <shameerali.kolothum.thodi@huawei.com>
---
hw/arm/smmuv3.c | 2 ++
hw/arm/virt.c | 50 ++++++++++++++++++++++++++++++++++++++++++++
hw/core/sysbus-fdt.c | 3 +++
3 files changed, 55 insertions(+)
diff --git a/hw/arm/smmuv3.c b/hw/arm/smmuv3.c
index 7e934336c2..d1f66dcd8f 100644
--- a/hw/arm/smmuv3.c
+++ b/hw/arm/smmuv3.c
@@ -2004,6 +2004,8 @@ static void smmuv3_class_init(ObjectClass *klass, const
void *data)
device_class_set_parent_realize(dc, smmu_realize,
&c->parent_realize);
device_class_set_props(dc, smmuv3_properties);
+ dc->hotpluggable = false;
+ dc->user_creatable = true;
}
static int smmuv3_notify_flag_changed(IOMMUMemoryRegion *iommu,
diff --git a/hw/arm/virt.c b/hw/arm/virt.c
index eeace4754d..04bc940fc3 100644
--- a/hw/arm/virt.c
+++ b/hw/arm/virt.c
@@ -56,6 +56,7 @@
#include "qemu/cutils.h"
#include "qemu/error-report.h"
#include "qemu/module.h"
+#include "hw/pci/pci_bus.h"
#include "hw/pci-host/gpex.h"
#include "hw/virtio/virtio-pci.h"
#include "hw/core/sysbus-fdt.h"
@@ -1443,6 +1444,28 @@ static void create_smmuv3_dt_bindings(const
VirtMachineState *vms, hwaddr base,
g_free(node);
}
+static void create_smmuv3_dev_dtb(VirtMachineState *vms,
+ DeviceState *dev, PCIBus *bus)
+{
+ PlatformBusDevice *pbus = PLATFORM_BUS_DEVICE(vms->platform_bus_dev);
+ SysBusDevice *sbdev = SYS_BUS_DEVICE(dev);
+ int irq = platform_bus_get_irqn(pbus, sbdev, 0);
+ hwaddr base = platform_bus_get_mmio_addr(pbus, sbdev, 0);
+ MachineState *ms = MACHINE(vms);
+
+ if (strcmp("pcie.0", bus->qbus.name)) {
+ warn_report("SMMUv3 device only supported with pcie.0 for DT");
+ return;
+ }
+ base += vms->memmap[VIRT_PLATFORM_BUS].base;
+ irq += vms->irqmap[VIRT_PLATFORM_BUS];
+
+ vms->iommu_phandle = qemu_fdt_alloc_phandle(ms->fdt);
+ create_smmuv3_dt_bindings(vms, base, SMMU_IO_LEN, irq);
+ qemu_fdt_setprop_cells(ms->fdt, vms->pciehb_nodename, "iommu-map",
+ 0x0, vms->iommu_phandle, 0x0, 0x10000);
+}
+
static void create_smmu(const VirtMachineState *vms,
PCIBus *bus)
{
@@ -2931,6 +2954,13 @@ static void
virt_machine_device_pre_plug_cb(HotplugHandler *hotplug_dev,
qlist_append_str(reserved_regions, resv_prop_str);
qdev_prop_set_array(dev, "reserved-regions", reserved_regions);
g_free(resv_prop_str);
+ } else if (object_dynamic_cast(OBJECT(dev), TYPE_ARM_SMMUV3)) {
+ if (vms->legacy_smmuv3_present || vms->iommu == VIRT_IOMMU_VIRTIO) {
+ error_setg(errp, "virt machine already has %s set. "
+ "Doesn't support incompatible iommus",
+ (vms->legacy_smmuv3_present) ?
+ "iommu=smmuv3" : "virtio-iommu");
+ }
}
}
@@ -2954,6 +2984,25 @@ static void virt_machine_device_plug_cb(HotplugHandler
*hotplug_dev,
virtio_md_pci_plug(VIRTIO_MD_PCI(dev), MACHINE(hotplug_dev), errp);
}
+ if (object_dynamic_cast(OBJECT(dev), TYPE_ARM_SMMUV3)) {
+ if (!vms->legacy_smmuv3_present && vms->platform_bus_dev) {
+ PCIBus *bus;
+
+ bus = PCI_BUS(object_property_get_link(OBJECT(dev), "primary-bus",
+ &error_abort));
+ if (pci_bus_bypass_iommu(bus)) {
+ error_setg(errp, "Bypass option cannot be set for SMMUv3 "
+ "associated PCIe RC");
+ return;
+ }
+
+ create_smmuv3_dev_dtb(vms, dev, bus);
+ if (vms->iommu != VIRT_IOMMU_SMMUV3) {
+ vms->iommu = VIRT_IOMMU_SMMUV3;
+ }
+ }
+ }
+
if (object_dynamic_cast(OBJECT(dev), TYPE_VIRTIO_IOMMU_PCI)) {
PCIDevice *pdev = PCI_DEVICE(dev);
@@ -3156,6 +3205,7 @@ static void virt_machine_class_init(ObjectClass *oc,
const void *data)
machine_class_allow_dynamic_sysbus_dev(mc, TYPE_RAMFB_DEVICE);
machine_class_allow_dynamic_sysbus_dev(mc, TYPE_VFIO_PLATFORM);
machine_class_allow_dynamic_sysbus_dev(mc, TYPE_UEFI_VARS_SYSBUS);
+ machine_class_allow_dynamic_sysbus_dev(mc, TYPE_ARM_SMMUV3);
#ifdef CONFIG_TPM
machine_class_allow_dynamic_sysbus_dev(mc, TYPE_TPM_TIS_SYSBUS);
#endif
diff --git a/hw/core/sysbus-fdt.c b/hw/core/sysbus-fdt.c
index c339a27875..e80776080b 100644
--- a/hw/core/sysbus-fdt.c
+++ b/hw/core/sysbus-fdt.c
@@ -31,6 +31,7 @@
#include "qemu/error-report.h"
#include "system/device_tree.h"
#include "system/tpm.h"
+#include "hw/arm/smmuv3.h"
#include "hw/platform-bus.h"
#include "hw/vfio/vfio-platform.h"
#include "hw/vfio/vfio-calxeda-xgmac.h"
@@ -518,6 +519,8 @@ static const BindingEntry bindings[] = {
#ifdef CONFIG_TPM
TYPE_BINDING(TYPE_TPM_TIS_SYSBUS, add_tpm_tis_fdt_node),
#endif
+ /* No generic DT support for smmuv3 dev. Support added for arm virt only */
+ TYPE_BINDING(TYPE_ARM_SMMUV3, no_fdt_node),
TYPE_BINDING(TYPE_RAMFB_DEVICE, no_fdt_node),
TYPE_BINDING(TYPE_UEFI_VARS_SYSBUS, add_uefi_vars_node),
TYPE_BINDING("", NULL), /* last element */
--
2.34.1
- RE: [PATCH v3 1/6] hw/arm/smmuv3: Check SMMUv3 has PCIe Root Complex association, (continued)
[PATCH v3 2/6] hw/arm/virt-acpi-build: Re-arrange SMMUv3 IORT build, Shameer Kolothum, 2025/06/02
[PATCH v3 3/6] hw/arm/virt-acpi-build: Update IORT for multiple smmuv3 devices, Shameer Kolothum, 2025/06/02
[PATCH v3 4/6] hw/arm/virt: Factor out common SMMUV3 dt bindings code, Shameer Kolothum, 2025/06/02
[PATCH v3 5/6] hw/arm/virt: Add an SMMU_IO_LEN macro, Shameer Kolothum, 2025/06/02
[PATCH v3 6/6] hw/arm/virt: Allow user-creatable SMMUv3 dev instantiation,
Shameer Kolothum <=
Re: [PATCH v3 0/6] hw/arm/virt: Add support for user creatable SMMUv3 device, Nathan Chen, 2025/06/04