sysbus_mmio_map(SYS_BUS_DEVICE(dev), 0, vms->memmap[VIRT_GIC_ITS].base);
fdt_add_its_gic_node(vms);
+ vms->msi_controller = VIRT_MSI_CTRL_ITS;
}
static void create_v2m(VirtMachineState *vms)
}
fdt_add_v2m_gic_node(vms);
+ vms->msi_controller = VIRT_MSI_CTRL_GICV2M;
}
static void create_gic(VirtMachineState *vms)
static void virt_machine_device_pre_plug_cb(HotplugHandler *hotplug_dev,
DeviceState *dev, Error **errp)
{
+ VirtMachineState *vms = VIRT_MACHINE(hotplug_dev);
+
if (object_dynamic_cast(OBJECT(dev), TYPE_PC_DIMM)) {
virt_memory_pre_plug(hotplug_dev, dev, errp);
+ } else if (object_dynamic_cast(OBJECT(dev), TYPE_VIRTIO_IOMMU_PCI)) {
+ hwaddr db_start = 0, db_end = 0;
+ char *resv_prop_str;
+
+ switch (vms->msi_controller) {
+ case VIRT_MSI_CTRL_NONE:
+ return;
+ case VIRT_MSI_CTRL_ITS:
+ /* GITS_TRANSLATER page */
+ db_start = base_memmap[VIRT_GIC_ITS].base + 0x10000;
+ db_end = base_memmap[VIRT_GIC_ITS].base +
+ base_memmap[VIRT_GIC_ITS].size - 1;
+ break;
+ case VIRT_MSI_CTRL_GICV2M:
+ /* MSI_SETSPI_NS page */
+ db_start = base_memmap[VIRT_GIC_V2M].base;
+ db_end = db_start + base_memmap[VIRT_GIC_V2M].size - 1;
+ break;
+ }
+ resv_prop_str = g_strdup_printf("0x%"PRIx64":0x%"PRIx64":%u",
+ db_start, db_end,
+ VIRTIO_IOMMU_RESV_MEM_T_MSI);
+
+ qdev_prop_set_uint32(dev, "len-reserved-regions", 1);
+ qdev_prop_set_string(dev, "reserved-regions[0]", resv_prop_str);
+ g_free(resv_prop_str);
}
}