/* SPDX-License-Identifier: GPL-2.0-or-later */
/*
 * QEMU loongson 3a5000 develop board emulation
 *
 * Copyright (c) 2021 Loongson Technology Corporation Limited
 */
#include "qemu/osdep.h"
#include "qemu/units.h"
#include "qemu/datadir.h"
#include "qapi/error.h"
#include "exec/target_page.h"
#include "hw/boards.h"
#include "hw/char/serial-mm.h"
#include "system/kvm.h"
#include "system/tcg.h"
#include "system/system.h"
#include "system/qtest.h"
#include "system/runstate.h"
#include "system/reset.h"
#include "system/rtc.h"
#include "hw/loongarch/virt.h"
#include "system/address-spaces.h"
#include "hw/irq.h"
#include "net/net.h"
#include "hw/loader.h"
#include "elf.h"
#include "hw/intc/loongarch_ipi.h"
#include "hw/intc/loongarch_extioi.h"
#include "hw/intc/loongarch_pch_pic.h"
#include "hw/intc/loongarch_pch_msi.h"
#include "hw/pci-host/ls7a.h"
#include "hw/pci-host/gpex.h"
#include "hw/misc/unimp.h"
#include "hw/loongarch/fw_cfg.h"
#include "target/loongarch/cpu.h"
#include "hw/firmware/smbios.h"
#include "qapi/qapi-visit-common.h"
#include "hw/acpi/generic_event_device.h"
#include "hw/mem/nvdimm.h"
#include "hw/platform-bus.h"
#include "hw/display/ramfb.h"
#include "hw/uefi/var-service-api.h"
#include "hw/mem/pc-dimm.h"
#include "system/tpm.h"
#include "system/block-backend.h"
#include "hw/block/flash.h"
#include "hw/virtio/virtio-iommu.h"
#include "qemu/error-report.h"

static void virt_get_veiointc(Object *obj, Visitor *v, const char *name,
                              void *opaque, Error **errp)
{
    LoongArchVirtMachineState *lvms = LOONGARCH_VIRT_MACHINE(obj);
    OnOffAuto veiointc = lvms->veiointc;

    visit_type_OnOffAuto(v, name, &veiointc, errp);
}

static void virt_set_veiointc(Object *obj, Visitor *v, const char *name,
                              void *opaque, Error **errp)
{
    LoongArchVirtMachineState *lvms = LOONGARCH_VIRT_MACHINE(obj);

    visit_type_OnOffAuto(v, name, &lvms->veiointc, errp);
}

static PFlashCFI01 *virt_flash_create1(LoongArchVirtMachineState *lvms,
                                       const char *name,
                                       const char *alias_prop_name)
{
    DeviceState *dev = qdev_new(TYPE_PFLASH_CFI01);

    qdev_prop_set_uint64(dev, "sector-length", VIRT_FLASH_SECTOR_SIZE);
    qdev_prop_set_uint8(dev, "width", 4);
    qdev_prop_set_uint8(dev, "device-width", 2);
    qdev_prop_set_bit(dev, "big-endian", false);
    qdev_prop_set_uint16(dev, "id0", 0x89);
    qdev_prop_set_uint16(dev, "id1", 0x18);
    qdev_prop_set_uint16(dev, "id2", 0x00);
    qdev_prop_set_uint16(dev, "id3", 0x00);
    qdev_prop_set_string(dev, "name", name);
    object_property_add_child(OBJECT(lvms), name, OBJECT(dev));
    object_property_add_alias(OBJECT(lvms), alias_prop_name,
                              OBJECT(dev), "drive");
    return PFLASH_CFI01(dev);
}

static void virt_flash_create(LoongArchVirtMachineState *lvms)
{
    lvms->flash[0] = virt_flash_create1(lvms, "virt.flash0", "pflash0");
    lvms->flash[1] = virt_flash_create1(lvms, "virt.flash1", "pflash1");
}

static void virt_flash_map1(PFlashCFI01 *flash,
                            hwaddr base, hwaddr size,
                            MemoryRegion *sysmem)
{
    DeviceState *dev = DEVICE(flash);
    BlockBackend *blk;
    hwaddr real_size = size;

    blk = pflash_cfi01_get_blk(flash);
    if (blk) {
        real_size = blk_getlength(blk);
        assert(real_size && real_size <= size);
    }

    assert(QEMU_IS_ALIGNED(real_size, VIRT_FLASH_SECTOR_SIZE));
    assert(real_size / VIRT_FLASH_SECTOR_SIZE <= UINT32_MAX);

    qdev_prop_set_uint32(dev, "num-blocks", real_size / VIRT_FLASH_SECTOR_SIZE);
    sysbus_realize_and_unref(SYS_BUS_DEVICE(dev), &error_fatal);
    memory_region_add_subregion(sysmem, base,
                                sysbus_mmio_get_region(SYS_BUS_DEVICE(dev), 0));
}

static void virt_flash_map(LoongArchVirtMachineState *lvms,
                           MemoryRegion *sysmem)
{
    PFlashCFI01 *flash0 = lvms->flash[0];
    PFlashCFI01 *flash1 = lvms->flash[1];

    virt_flash_map1(flash0, VIRT_FLASH0_BASE, VIRT_FLASH0_SIZE, sysmem);
    virt_flash_map1(flash1, VIRT_FLASH1_BASE, VIRT_FLASH1_SIZE, sysmem);
}

static void virt_build_smbios(LoongArchVirtMachineState *lvms)
{
    MachineState *ms = MACHINE(lvms);
    MachineClass *mc = MACHINE_GET_CLASS(lvms);
    uint8_t *smbios_tables, *smbios_anchor;
    size_t smbios_tables_len, smbios_anchor_len;
    const char *product = "QEMU Virtual Machine";

    if (!lvms->fw_cfg) {
        return;
    }

    if (kvm_enabled()) {
        product = "KVM Virtual Machine";
    }

    smbios_set_defaults("QEMU", product, mc->name);

    smbios_get_tables(ms, SMBIOS_ENTRY_POINT_TYPE_64,
                      NULL, 0,
                      &smbios_tables, &smbios_tables_len,
                      &smbios_anchor, &smbios_anchor_len, &error_fatal);

    if (smbios_anchor) {
        fw_cfg_add_file(lvms->fw_cfg, "etc/smbios/smbios-tables",
                        smbios_tables, smbios_tables_len);
        fw_cfg_add_file(lvms->fw_cfg, "etc/smbios/smbios-anchor",
                        smbios_anchor, smbios_anchor_len);
    }
}

static void virt_done(Notifier *notifier, void *data)
{
    LoongArchVirtMachineState *lvms = container_of(notifier,
                                      LoongArchVirtMachineState, machine_done);
    virt_build_smbios(lvms);
    virt_acpi_setup(lvms);
    virt_fdt_setup(lvms);
}

static void virt_powerdown_req(Notifier *notifier, void *opaque)
{
    LoongArchVirtMachineState *s;

    s = container_of(notifier, LoongArchVirtMachineState, powerdown_notifier);
    acpi_send_event(s->acpi_ged, ACPI_POWER_DOWN_STATUS);
}

static void memmap_add_entry(MachineState *ms, uint64_t address,
                             uint64_t length, uint32_t type)
{
    LoongArchVirtMachineState *lvms = LOONGARCH_VIRT_MACHINE(ms);
    struct memmap_entry *memmap_table;
    unsigned int memmap_entries;

    memmap_table = lvms->memmap_table;
    memmap_entries = lvms->memmap_entries;
    /* Ensure there are no duplicate entries. */
    for (unsigned i = 0; i < memmap_entries; i++) {
        assert(memmap_table[i].address != address);
    }

    memmap_table = g_renew(struct memmap_entry, memmap_table,
                           memmap_entries + 1);
    memmap_table[memmap_entries].address = cpu_to_le64(address);
    memmap_table[memmap_entries].length = cpu_to_le64(length);
    memmap_table[memmap_entries].type = cpu_to_le32(type);
    memmap_table[memmap_entries].reserved = 0;
    memmap_entries++;
    lvms->memmap_table = memmap_table;
    lvms->memmap_entries = memmap_entries;
}

static DeviceState *create_acpi_ged(DeviceState *pch_pic,
                                    LoongArchVirtMachineState *lvms)
{
    DeviceState *dev;
    MachineState *ms = MACHINE(lvms);
    MachineClass *mc = MACHINE_GET_CLASS(lvms);
    uint32_t event = ACPI_GED_PWR_DOWN_EVT;

    if (ms->ram_slots) {
        event |= ACPI_GED_MEM_HOTPLUG_EVT;
    }

    if (mc->has_hotpluggable_cpus) {
        event |= ACPI_GED_CPU_HOTPLUG_EVT;
    }

    dev = qdev_new(TYPE_ACPI_GED);
    qdev_prop_set_uint32(dev, "ged-event", event);
    sysbus_realize_and_unref(SYS_BUS_DEVICE(dev), &error_fatal);

    /* ged event */
    sysbus_mmio_map(SYS_BUS_DEVICE(dev), 0, VIRT_GED_EVT_ADDR);
    /* memory hotplug */
    sysbus_mmio_map(SYS_BUS_DEVICE(dev), 1, VIRT_GED_MEM_ADDR);
    /* ged regs used for reset and power down */
    sysbus_mmio_map(SYS_BUS_DEVICE(dev), 2, VIRT_GED_REG_ADDR);

    if (mc->has_hotpluggable_cpus) {
        sysbus_mmio_map(SYS_BUS_DEVICE(dev), 3, VIRT_GED_CPUHP_ADDR);
    }

    sysbus_connect_irq(SYS_BUS_DEVICE(dev), 0,
                       qdev_get_gpio_in(pch_pic, VIRT_SCI_IRQ - VIRT_GSI_BASE));
    return dev;
}

static DeviceState *create_platform_bus(DeviceState *pch_pic)
{
    DeviceState *dev;
    SysBusDevice *sysbus;
    int i, irq;
    MemoryRegion *sysmem = get_system_memory();

    dev = qdev_new(TYPE_PLATFORM_BUS_DEVICE);
    dev->id = g_strdup(TYPE_PLATFORM_BUS_DEVICE);
    qdev_prop_set_uint32(dev, "num_irqs", VIRT_PLATFORM_BUS_NUM_IRQS);
    qdev_prop_set_uint32(dev, "mmio_size", VIRT_PLATFORM_BUS_SIZE);
    sysbus_realize_and_unref(SYS_BUS_DEVICE(dev), &error_fatal);

    sysbus = SYS_BUS_DEVICE(dev);
    for (i = 0; i < VIRT_PLATFORM_BUS_NUM_IRQS; i++) {
        irq = VIRT_PLATFORM_BUS_IRQ - VIRT_GSI_BASE + i;
        sysbus_connect_irq(sysbus, i, qdev_get_gpio_in(pch_pic, irq));
    }

    memory_region_add_subregion(sysmem,
                                VIRT_PLATFORM_BUS_BASEADDRESS,
                                sysbus_mmio_get_region(sysbus, 0));
    return dev;
}

static void virt_devices_init(DeviceState *pch_pic,
                                   LoongArchVirtMachineState *lvms)
{
    MachineClass *mc = MACHINE_GET_CLASS(lvms);
    DeviceState *gpex_dev;
    SysBusDevice *d;
    PCIBus *pci_bus;
    MemoryRegion *ecam_alias, *ecam_reg, *pio_alias, *pio_reg;
    MemoryRegion *mmio_alias, *mmio_reg;
    int i;

    gpex_dev = qdev_new(TYPE_GPEX_HOST);
    d = SYS_BUS_DEVICE(gpex_dev);
    sysbus_realize_and_unref(d, &error_fatal);
    pci_bus = PCI_HOST_BRIDGE(gpex_dev)->bus;
    lvms->pci_bus = pci_bus;

    /* Map only part size_ecam bytes of ECAM space */
    ecam_alias = g_new0(MemoryRegion, 1);
    ecam_reg = sysbus_mmio_get_region(d, 0);
    memory_region_init_alias(ecam_alias, OBJECT(gpex_dev), "pcie-ecam",
                             ecam_reg, 0, VIRT_PCI_CFG_SIZE);
    memory_region_add_subregion(get_system_memory(), VIRT_PCI_CFG_BASE,
                                ecam_alias);

    /* Map PCI mem space */
    mmio_alias = g_new0(MemoryRegion, 1);
    mmio_reg = sysbus_mmio_get_region(d, 1);
    memory_region_init_alias(mmio_alias, OBJECT(gpex_dev), "pcie-mmio",
                             mmio_reg, VIRT_PCI_MEM_BASE, VIRT_PCI_MEM_SIZE);
    memory_region_add_subregion(get_system_memory(), VIRT_PCI_MEM_BASE,
                                mmio_alias);

    /* Map PCI IO port space. */
    pio_alias = g_new0(MemoryRegion, 1);
    pio_reg = sysbus_mmio_get_region(d, 2);
    memory_region_init_alias(pio_alias, OBJECT(gpex_dev), "pcie-io", pio_reg,
                             VIRT_PCI_IO_OFFSET, VIRT_PCI_IO_SIZE);
    memory_region_add_subregion(get_system_memory(), VIRT_PCI_IO_BASE,
                                pio_alias);

    for (i = 0; i < PCI_NUM_PINS; i++) {
        sysbus_connect_irq(d, i,
                           qdev_get_gpio_in(pch_pic, 16 + i));
        gpex_set_irq_num(GPEX_HOST(gpex_dev), i, 16 + i);
    }

    /*
     * Create uart fdt node in reverse order so that they appear
     * in the finished device tree lowest address first
     */
    for (i = VIRT_UART_COUNT; i-- > 0;) {
        hwaddr base = VIRT_UART_BASE + i * VIRT_UART_SIZE;
        int irq = VIRT_UART_IRQ + i - VIRT_GSI_BASE;
        serial_mm_init(get_system_memory(), base, 0,
                       qdev_get_gpio_in(pch_pic, irq),
                       115200, serial_hd(i), DEVICE_LITTLE_ENDIAN);
    }

    /* Network init */
    pci_init_nic_devices(pci_bus, mc->default_nic);

    /*
     * There are some invalid guest memory access.
     * Create some unimplemented devices to emulate this.
     */
    create_unimplemented_device("pci-dma-cfg", 0x1001041c, 0x4);
    sysbus_create_simple("ls7a_rtc", VIRT_RTC_REG_BASE,
                         qdev_get_gpio_in(pch_pic,
                         VIRT_RTC_IRQ - VIRT_GSI_BASE));

    /* acpi ged */
    lvms->acpi_ged = create_acpi_ged(pch_pic, lvms);
    /* platform bus */
    lvms->platform_bus_dev = create_platform_bus(pch_pic);
}

static void virt_cpu_irq_init(LoongArchVirtMachineState *lvms)
{
    int num;
    MachineState *ms = MACHINE(lvms);
    MachineClass *mc = MACHINE_GET_CLASS(ms);
    const CPUArchIdList *possible_cpus;
    CPUState *cs;

    /* cpu nodes */
    possible_cpus = mc->possible_cpu_arch_ids(ms);
    for (num = 0; num < possible_cpus->len; num++) {
        cs = possible_cpus->cpus[num].cpu;
        if (cs == NULL) {
            continue;
        }

        hotplug_handler_plug(HOTPLUG_HANDLER(lvms->ipi), DEVICE(cs),
                             &error_abort);
        hotplug_handler_plug(HOTPLUG_HANDLER(lvms->extioi), DEVICE(cs),
                             &error_abort);
    }
}

static void virt_irq_init(LoongArchVirtMachineState *lvms)
{
    DeviceState *pch_pic, *pch_msi;
    DeviceState *ipi, *extioi;
    SysBusDevice *d;
    int i, start, num;

    /*
     * Extended IRQ model.
     *                                 |
     * +-----------+     +-------------|--------+     +-----------+
     * | IPI/Timer | --> | CPUINTC(0-3)|(4-255) | <-- | IPI/Timer |
     * +-----------+     +-------------|--------+     +-----------+
     *                         ^       |
     *                         |
     *                    +---------+
     *                    | EIOINTC |
     *                    +---------+
     *                     ^       ^
     *                     |       |
     *              +---------+ +---------+
     *              | PCH-PIC | | PCH-MSI |
     *              +---------+ +---------+
     *                ^      ^          ^
     *                |      |          |
     *         +--------+ +---------+ +---------+
     *         | UARTs  | | Devices | | Devices |
     *         +--------+ +---------+ +---------+
     *
     * Virt extended IRQ model.
     *
     *   +-----+    +---------------+     +-------+
     *   | IPI |--> | CPUINTC(0-255)| <-- | Timer |
     *   +-----+    +---------------+     +-------+
     *                     ^
     *                     |
     *               +-----------+
     *               | V-EIOINTC |
     *               +-----------+
     *                ^         ^
     *                |         |
     *         +---------+ +---------+
     *         | PCH-PIC | | PCH-MSI |
     *         +---------+ +---------+
     *           ^      ^          ^
     *           |      |          |
     *    +--------+ +---------+ +---------+
     *    | UARTs  | | Devices | | Devices |
     *    +--------+ +---------+ +---------+
     */

    /* Create IPI device */
    ipi = qdev_new(TYPE_LOONGARCH_IPI);
    lvms->ipi = ipi;
    sysbus_realize_and_unref(SYS_BUS_DEVICE(ipi), &error_fatal);

    /* Create EXTIOI device */
    extioi = qdev_new(TYPE_LOONGARCH_EXTIOI);
    lvms->extioi = extioi;
    if (virt_is_veiointc_enabled(lvms)) {
        qdev_prop_set_bit(extioi, "has-virtualization-extension", true);
    }
    sysbus_realize_and_unref(SYS_BUS_DEVICE(extioi), &error_fatal);

    virt_cpu_irq_init(lvms);
    pch_pic = qdev_new(TYPE_LOONGARCH_PIC);
    num = VIRT_PCH_PIC_IRQ_NUM;
    qdev_prop_set_uint32(pch_pic, "pch_pic_irq_num", num);
    d = SYS_BUS_DEVICE(pch_pic);
    sysbus_realize_and_unref(d, &error_fatal);

    pch_msi = qdev_new(TYPE_LOONGARCH_PCH_MSI);
    start   =  num;
    num = EXTIOI_IRQS - start;
    qdev_prop_set_uint32(pch_msi, "msi_irq_base", start);
    qdev_prop_set_uint32(pch_msi, "msi_irq_num", num);
    d = SYS_BUS_DEVICE(pch_msi);
    sysbus_realize_and_unref(d, &error_fatal);
    sysbus_mmio_map(d, 0, VIRT_PCH_MSI_ADDR_LOW);

    if (kvm_irqchip_in_kernel()) {
        kvm_loongarch_init_irq_routing();
    } else {
        /* IPI iocsr memory region */
        memory_region_add_subregion(&lvms->system_iocsr, SMP_IPI_MAILBOX,
                       sysbus_mmio_get_region(SYS_BUS_DEVICE(ipi), 0));
        memory_region_add_subregion(&lvms->system_iocsr, MAIL_SEND_ADDR,
                       sysbus_mmio_get_region(SYS_BUS_DEVICE(ipi), 1));

        /* EXTIOI iocsr memory region */
        memory_region_add_subregion(&lvms->system_iocsr, APIC_BASE,
                    sysbus_mmio_get_region(SYS_BUS_DEVICE(extioi), 0));
        if (virt_is_veiointc_enabled(lvms)) {
            memory_region_add_subregion(&lvms->system_iocsr, EXTIOI_VIRT_BASE,
                    sysbus_mmio_get_region(SYS_BUS_DEVICE(extioi), 1));
        }

        /* PCH_PIC memory region */
        memory_region_add_subregion(get_system_memory(), VIRT_IOAPIC_REG_BASE,
                    sysbus_mmio_get_region(SYS_BUS_DEVICE(pch_pic), 0));

        /* Connect pch_pic irqs to extioi */
        for (i = 0; i < VIRT_PCH_PIC_IRQ_NUM; i++) {
            qdev_connect_gpio_out(DEVICE(pch_pic), i,
                                  qdev_get_gpio_in(extioi, i));
        }

        for (i = VIRT_PCH_PIC_IRQ_NUM; i < EXTIOI_IRQS; i++) {
            /* Connect pch_msi irqs to extioi */
            qdev_connect_gpio_out(DEVICE(pch_msi), i - VIRT_PCH_PIC_IRQ_NUM,
                                  qdev_get_gpio_in(extioi, i));
        }
    }
    virt_devices_init(pch_pic, lvms);
}

static void virt_firmware_init(LoongArchVirtMachineState *lvms)
{
    char *filename = MACHINE(lvms)->firmware;
    char *bios_name = NULL;
    int bios_size, i;
    BlockBackend *pflash_blk0;
    MemoryRegion *mr;

    lvms->bios_loaded = false;

    /* Map legacy -drive if=pflash to machine properties */
    for (i = 0; i < ARRAY_SIZE(lvms->flash); i++) {
        pflash_cfi01_legacy_drive(lvms->flash[i],
                                  drive_get(IF_PFLASH, 0, i));
    }

    virt_flash_map(lvms, get_system_memory());

    pflash_blk0 = pflash_cfi01_get_blk(lvms->flash[0]);

    if (pflash_blk0) {
        if (filename) {
            error_report("cannot use both '-bios' and '-drive if=pflash'"
                         "options at once");
            exit(1);
        }
        lvms->bios_loaded = true;
        return;
    }

    if (filename) {
        bios_name = qemu_find_file(QEMU_FILE_TYPE_BIOS, filename);
        if (!bios_name) {
            error_report("Could not find ROM image '%s'", filename);
            exit(1);
        }

        mr = sysbus_mmio_get_region(SYS_BUS_DEVICE(lvms->flash[0]), 0);
        bios_size = load_image_mr(bios_name, mr);
        if (bios_size < 0) {
            error_report("Could not load ROM image '%s'", bios_name);
            exit(1);
        }
        g_free(bios_name);
        lvms->bios_loaded = true;
    }
}

static MemTxResult virt_iocsr_misc_write(void *opaque, hwaddr addr,
                                         uint64_t val, unsigned size,
                                         MemTxAttrs attrs)
{
    LoongArchVirtMachineState *lvms = LOONGARCH_VIRT_MACHINE(opaque);
    uint64_t features;

    switch (addr) {
    case MISC_FUNC_REG:
        if (kvm_irqchip_in_kernel()) {
            return MEMTX_OK;
        }

        if (!virt_is_veiointc_enabled(lvms)) {
            return MEMTX_OK;
        }

        features = address_space_ldl(&lvms->as_iocsr,
                                     EXTIOI_VIRT_BASE + EXTIOI_VIRT_CONFIG,
                                     attrs, NULL);
        if (val & BIT_ULL(IOCSRM_EXTIOI_EN)) {
            features |= BIT(EXTIOI_ENABLE);
        }
        if (val & BIT_ULL(IOCSRM_EXTIOI_INT_ENCODE)) {
            features |= BIT(EXTIOI_ENABLE_INT_ENCODE);
        }

        address_space_stl(&lvms->as_iocsr,
                          EXTIOI_VIRT_BASE + EXTIOI_VIRT_CONFIG,
                          features, attrs, NULL);
        break;
    default:
        g_assert_not_reached();
    }

    return MEMTX_OK;
}

static MemTxResult virt_iocsr_misc_read(void *opaque, hwaddr addr,
                                        uint64_t *data,
                                        unsigned size, MemTxAttrs attrs)
{
    LoongArchVirtMachineState *lvms = LOONGARCH_VIRT_MACHINE(opaque);
    uint64_t ret = 0;
    int features;

    switch (addr) {
    case VERSION_REG:
        ret = 0x11ULL;
        break;
    case FEATURE_REG:
        ret = BIT(IOCSRF_MSI) | BIT(IOCSRF_EXTIOI) | BIT(IOCSRF_CSRIPI);
        if (kvm_enabled()) {
            ret |= BIT(IOCSRF_VM);
        }
        break;
    case VENDOR_REG:
        ret = 0x6e6f73676e6f6f4cULL; /* "Loongson" */
        break;
    case CPUNAME_REG:
        ret = 0x303030354133ULL;     /* "3A5000" */
        break;
    case MISC_FUNC_REG:
        if (kvm_irqchip_in_kernel()) {
            return MEMTX_OK;
        }

        if (!virt_is_veiointc_enabled(lvms)) {
            ret |= BIT_ULL(IOCSRM_EXTIOI_EN);
            break;
        }

        features = address_space_ldl(&lvms->as_iocsr,
                                     EXTIOI_VIRT_BASE + EXTIOI_VIRT_CONFIG,
                                     attrs, NULL);
        if (features & BIT(EXTIOI_ENABLE)) {
            ret |= BIT_ULL(IOCSRM_EXTIOI_EN);
        }
        if (features & BIT(EXTIOI_ENABLE_INT_ENCODE)) {
            ret |= BIT_ULL(IOCSRM_EXTIOI_INT_ENCODE);
        }
        break;
    default:
        g_assert_not_reached();
    }

    *data = ret;
    return MEMTX_OK;
}

static const MemoryRegionOps virt_iocsr_misc_ops = {
    .read_with_attrs  = virt_iocsr_misc_read,
    .write_with_attrs = virt_iocsr_misc_write,
    .endianness = DEVICE_LITTLE_ENDIAN,
    .valid = {
        .min_access_size = 4,
        .max_access_size = 8,
    },
    .impl = {
        .min_access_size = 8,
        .max_access_size = 8,
    },
};

static void fw_cfg_add_memory(MachineState *ms)
{
    hwaddr base, size, ram_size, gap;
    int nb_numa_nodes, nodes;
    NodeInfo *numa_info;

    ram_size = ms->ram_size;
    base = VIRT_LOWMEM_BASE;
    gap = VIRT_LOWMEM_SIZE;
    nodes = nb_numa_nodes = ms->numa_state->num_nodes;
    numa_info = ms->numa_state->nodes;
    if (!nodes) {
        nodes = 1;
    }

    /* add fw_cfg memory map of node0 */
    if (nb_numa_nodes) {
        size = numa_info[0].node_mem;
    } else {
        size = ram_size;
    }

    if (size >= gap) {
        memmap_add_entry(ms, base, gap, 1);
        size -= gap;
        base = VIRT_HIGHMEM_BASE;
    }

    if (size) {
        memmap_add_entry(ms, base, size, 1);
        base += size;
    }

    if (nodes < 2) {
        return;
    }

    /* add fw_cfg memory map of other nodes */
    if (numa_info[0].node_mem < gap && ram_size > gap) {
        /*
         * memory map for the maining nodes splited into two part
         * lowram:  [base, +(gap - numa_info[0].node_mem))
         * highram: [VIRT_HIGHMEM_BASE, +(ram_size - gap))
         */
        memmap_add_entry(ms, base, gap - numa_info[0].node_mem, 1);
        size = ram_size - gap;
        base = VIRT_HIGHMEM_BASE;
    } else {
        size = ram_size - numa_info[0].node_mem;
    }

    if (size) {
        memmap_add_entry(ms, base, size, 1);
    }
}

static void virt_init(MachineState *machine)
{
    const char *cpu_model = machine->cpu_type;
    MemoryRegion *address_space_mem = get_system_memory();
    LoongArchVirtMachineState *lvms = LOONGARCH_VIRT_MACHINE(machine);
    int i;
    hwaddr base, size, ram_size = machine->ram_size;
    MachineClass *mc = MACHINE_GET_CLASS(machine);
    Object *cpuobj;

    if (!cpu_model) {
        cpu_model = LOONGARCH_CPU_TYPE_NAME("la464");
    }

    /* Create IOCSR space */
    memory_region_init_io(&lvms->system_iocsr, OBJECT(machine), NULL,
                          machine, "iocsr", UINT64_MAX);
    address_space_init(&lvms->as_iocsr, &lvms->system_iocsr, "IOCSR");
    memory_region_init_io(&lvms->iocsr_mem, OBJECT(machine),
                          &virt_iocsr_misc_ops,
                          machine, "iocsr_misc", 0x428);
    memory_region_add_subregion(&lvms->system_iocsr, 0, &lvms->iocsr_mem);

    /* Init CPUs */
    mc->possible_cpu_arch_ids(machine);
    for (i = 0; i < machine->smp.cpus; i++) {
        cpuobj = object_new(machine->cpu_type);
        if (cpuobj == NULL) {
            error_report("Fail to create object with type %s ",
                         machine->cpu_type);
            exit(EXIT_FAILURE);
        }
        qdev_realize_and_unref(DEVICE(cpuobj), NULL, &error_fatal);
    }
    fw_cfg_add_memory(machine);

    /* Node0 memory */
    size = ram_size;
    base = VIRT_LOWMEM_BASE;
    if (size > VIRT_LOWMEM_SIZE) {
        size = VIRT_LOWMEM_SIZE;
    }

    memory_region_init_alias(&lvms->lowmem, NULL, "loongarch.lowram",
                              machine->ram, base, size);
    memory_region_add_subregion(address_space_mem, base, &lvms->lowmem);
    base += size;
    if (ram_size - size) {
        base = VIRT_HIGHMEM_BASE;
        memory_region_init_alias(&lvms->highmem, NULL, "loongarch.highram",
                machine->ram, VIRT_LOWMEM_BASE + size, ram_size - size);
        memory_region_add_subregion(address_space_mem, base, &lvms->highmem);
        base += ram_size - size;
    }

    /* initialize device memory address space */
    if (machine->ram_size < machine->maxram_size) {
        ram_addr_t device_mem_size = machine->maxram_size - machine->ram_size;

        if (machine->ram_slots > ACPI_MAX_RAM_SLOTS) {
            error_report("unsupported amount of memory slots: %"PRIu64,
                         machine->ram_slots);
            exit(EXIT_FAILURE);
        }

        if (QEMU_ALIGN_UP(machine->maxram_size,
                          TARGET_PAGE_SIZE) != machine->maxram_size) {
            error_report("maximum memory size must by aligned to multiple of "
                         "%d bytes", TARGET_PAGE_SIZE);
            exit(EXIT_FAILURE);
        }
        machine_memory_devices_init(machine, base, device_mem_size);
    }

    /* load the BIOS image. */
    virt_firmware_init(lvms);

    /* fw_cfg init */
    lvms->fw_cfg = virt_fw_cfg_init(ram_size, machine);
    rom_set_fw(lvms->fw_cfg);
    if (lvms->fw_cfg != NULL) {
        fw_cfg_add_file(lvms->fw_cfg, "etc/memmap",
                        lvms->memmap_table,
                        sizeof(struct memmap_entry) * lvms->memmap_entries);
    }

    /* Initialize the IO interrupt subsystem */
    virt_irq_init(lvms);
    lvms->machine_done.notify = virt_done;
    qemu_add_machine_init_done_notifier(&lvms->machine_done);
     /* connect powerdown request */
    lvms->powerdown_notifier.notify = virt_powerdown_req;
    qemu_register_powerdown_notifier(&lvms->powerdown_notifier);

    lvms->bootinfo.ram_size = ram_size;
    loongarch_load_kernel(machine, &lvms->bootinfo);
}

static void virt_get_acpi(Object *obj, Visitor *v, const char *name,
                          void *opaque, Error **errp)
{
    LoongArchVirtMachineState *lvms = LOONGARCH_VIRT_MACHINE(obj);
    OnOffAuto acpi = lvms->acpi;

    visit_type_OnOffAuto(v, name, &acpi, errp);
}

static void virt_set_acpi(Object *obj, Visitor *v, const char *name,
                               void *opaque, Error **errp)
{
    LoongArchVirtMachineState *lvms = LOONGARCH_VIRT_MACHINE(obj);

    visit_type_OnOffAuto(v, name, &lvms->acpi, errp);
}

static char *virt_get_oem_id(Object *obj, Error **errp)
{
    LoongArchVirtMachineState *lvms = LOONGARCH_VIRT_MACHINE(obj);

    return g_strdup(lvms->oem_id);
}

static void virt_set_oem_id(Object *obj, const char *value, Error **errp)
{
    LoongArchVirtMachineState *lvms = LOONGARCH_VIRT_MACHINE(obj);
    size_t len = strlen(value);

    if (len > 6) {
        error_setg(errp,
                   "User specified oem-id value is bigger than 6 bytes in size");
        return;
    }

    strncpy(lvms->oem_id, value, 6);
}

static char *virt_get_oem_table_id(Object *obj, Error **errp)
{
    LoongArchVirtMachineState *lvms = LOONGARCH_VIRT_MACHINE(obj);

    return g_strdup(lvms->oem_table_id);
}

static void virt_set_oem_table_id(Object *obj, const char *value,
                                  Error **errp)
{
    LoongArchVirtMachineState *lvms = LOONGARCH_VIRT_MACHINE(obj);
    size_t len = strlen(value);

    if (len > 8) {
        error_setg(errp,
                   "User specified oem-table-id value is bigger than 8 bytes in size");
        return;
    }
    strncpy(lvms->oem_table_id, value, 8);
}

static void virt_initfn(Object *obj)
{
    LoongArchVirtMachineState *lvms = LOONGARCH_VIRT_MACHINE(obj);

    if (tcg_enabled()) {
        lvms->veiointc = ON_OFF_AUTO_OFF;
    }
    lvms->acpi = ON_OFF_AUTO_AUTO;
    lvms->oem_id = g_strndup(ACPI_BUILD_APPNAME6, 6);
    lvms->oem_table_id = g_strndup(ACPI_BUILD_APPNAME8, 8);
    virt_flash_create(lvms);
}

static void virt_get_topo_from_index(MachineState *ms,
                                     LoongArchCPUTopo *topo, int index)
{
    topo->socket_id = index / (ms->smp.cores * ms->smp.threads);
    topo->core_id = index / ms->smp.threads % ms->smp.cores;
    topo->thread_id = index % ms->smp.threads;
}

static unsigned int topo_align_up(unsigned int count)
{
    g_assert(count >= 1);
    count -= 1;
    return BIT(count ? 32 - clz32(count) : 0);
}

/*
 * LoongArch Reference Manual Vol1, Chapter 7.4.12 CPU Identity
 *  For CPU architecture, bit0 .. bit8 is valid for CPU id, max cpuid is 512
 *  However for IPI/Eiointc interrupt controller, max supported cpu id for
 *  irq routingis 256
 *
 *  Here max cpu id is 256 for virt machine
 */
static int virt_get_arch_id_from_topo(MachineState *ms, LoongArchCPUTopo *topo)
{
    int arch_id, threads, cores, sockets;

    threads = topo_align_up(ms->smp.threads);
    cores = topo_align_up(ms->smp.cores);
    sockets = topo_align_up(ms->smp.sockets);
    if ((threads * cores * sockets) > 256) {
        error_report("Exceeding max cpuid 256 with sockets[%d] cores[%d]"
                     " threads[%d]", ms->smp.sockets, ms->smp.cores,
                     ms->smp.threads);
        exit(1);
    }

    arch_id = topo->thread_id + topo->core_id * threads;
    arch_id += topo->socket_id * threads * cores;
    return arch_id;
}

/* Find cpu slot in machine->possible_cpus by arch_id */
static CPUArchId *virt_find_cpu_slot(MachineState *ms, int arch_id)
{
    int n;
    for (n = 0; n < ms->possible_cpus->len; n++) {
        if (ms->possible_cpus->cpus[n].arch_id == arch_id) {
            return &ms->possible_cpus->cpus[n];
        }
    }

    return NULL;
}

/* Find cpu slot for cold-plut CPU object where cpu is NULL */
static CPUArchId *virt_find_empty_cpu_slot(MachineState *ms)
{
    int n;
    for (n = 0; n < ms->possible_cpus->len; n++) {
        if (ms->possible_cpus->cpus[n].cpu == NULL) {
            return &ms->possible_cpus->cpus[n];
        }
    }

    return NULL;
}

static void virt_cpu_pre_plug(HotplugHandler *hotplug_dev,
                              DeviceState *dev, Error **errp)
{
    LoongArchVirtMachineState *lvms = LOONGARCH_VIRT_MACHINE(hotplug_dev);
    MachineState *ms = MACHINE(OBJECT(hotplug_dev));
    LoongArchCPU *cpu = LOONGARCH_CPU(dev);
    CPUState *cs = CPU(dev);
    CPUArchId *cpu_slot;
    LoongArchCPUTopo topo;
    int arch_id;

    if (lvms->acpi_ged) {
        if ((cpu->thread_id < 0) || (cpu->thread_id >= ms->smp.threads)) {
            error_setg(errp,
                       "Invalid thread-id %u specified, must be in range 1:%u",
                       cpu->thread_id, ms->smp.threads - 1);
            return;
        }

        if ((cpu->core_id < 0) || (cpu->core_id >= ms->smp.cores)) {
            error_setg(errp,
                       "Invalid core-id %u specified, must be in range 1:%u",
                       cpu->core_id, ms->smp.cores - 1);
            return;
        }

        if ((cpu->socket_id < 0) || (cpu->socket_id >= ms->smp.sockets)) {
            error_setg(errp,
                       "Invalid socket-id %u specified, must be in range 1:%u",
                       cpu->socket_id, ms->smp.sockets - 1);
            return;
        }

        topo.socket_id = cpu->socket_id;
        topo.core_id = cpu->core_id;
        topo.thread_id = cpu->thread_id;
        arch_id =  virt_get_arch_id_from_topo(ms, &topo);
        cpu_slot = virt_find_cpu_slot(ms, arch_id);
        if (CPU(cpu_slot->cpu)) {
            error_setg(errp,
                       "cpu(id%d=%d:%d:%d) with arch-id %" PRIu64 " exists",
                       cs->cpu_index, cpu->socket_id, cpu->core_id,
                       cpu->thread_id, cpu_slot->arch_id);
            return;
        }
    } else {
        /* For cold-add cpu, find empty cpu slot */
        cpu_slot = virt_find_empty_cpu_slot(ms);
        topo.socket_id = cpu_slot->props.socket_id;
        topo.core_id = cpu_slot->props.core_id;
        topo.thread_id = cpu_slot->props.thread_id;
        object_property_set_int(OBJECT(dev), "socket-id", topo.socket_id, NULL);
        object_property_set_int(OBJECT(dev), "core-id", topo.core_id, NULL);
        object_property_set_int(OBJECT(dev), "thread-id", topo.thread_id, NULL);
    }

    cpu->env.address_space_iocsr = &lvms->as_iocsr;
    cpu->phy_id = cpu_slot->arch_id;
    cs->cpu_index = cpu_slot - ms->possible_cpus->cpus;
    numa_cpu_pre_plug(cpu_slot, dev, errp);
}

static void virt_cpu_unplug_request(HotplugHandler *hotplug_dev,
                                    DeviceState *dev, Error **errp)
{
    LoongArchVirtMachineState *lvms = LOONGARCH_VIRT_MACHINE(hotplug_dev);
    LoongArchCPU *cpu = LOONGARCH_CPU(dev);
    CPUState *cs = CPU(dev);

    if (cs->cpu_index == 0) {
        error_setg(errp, "hot-unplug of boot cpu(id%d=%d:%d:%d) not supported",
                   cs->cpu_index, cpu->socket_id,
                   cpu->core_id, cpu->thread_id);
        return;
    }

    hotplug_handler_unplug_request(HOTPLUG_HANDLER(lvms->acpi_ged), dev, errp);
}

static void virt_cpu_unplug(HotplugHandler *hotplug_dev,
                            DeviceState *dev, Error **errp)
{
    CPUArchId *cpu_slot;
    LoongArchCPU *cpu = LOONGARCH_CPU(dev);
    LoongArchVirtMachineState *lvms = LOONGARCH_VIRT_MACHINE(hotplug_dev);

    /* Notify ipi and extioi irqchip to remove interrupt routing to CPU */
    hotplug_handler_unplug(HOTPLUG_HANDLER(lvms->ipi), dev, &error_abort);
    hotplug_handler_unplug(HOTPLUG_HANDLER(lvms->extioi), dev, &error_abort);

    /* Notify acpi ged CPU removed */
    hotplug_handler_unplug(HOTPLUG_HANDLER(lvms->acpi_ged), dev, &error_abort);

    cpu_slot = virt_find_cpu_slot(MACHINE(lvms), cpu->phy_id);
    cpu_slot->cpu = NULL;
}

static void virt_cpu_plug(HotplugHandler *hotplug_dev,
                          DeviceState *dev, Error **errp)
{
    CPUArchId *cpu_slot;
    LoongArchCPU *cpu = LOONGARCH_CPU(dev);
    LoongArchVirtMachineState *lvms = LOONGARCH_VIRT_MACHINE(hotplug_dev);

    if (lvms->ipi) {
        hotplug_handler_plug(HOTPLUG_HANDLER(lvms->ipi), dev, &error_abort);
    }

    if (lvms->extioi) {
        hotplug_handler_plug(HOTPLUG_HANDLER(lvms->extioi), dev, &error_abort);
    }

    if (lvms->acpi_ged) {
        hotplug_handler_plug(HOTPLUG_HANDLER(lvms->acpi_ged), dev,
                             &error_abort);
    }

    cpu_slot = virt_find_cpu_slot(MACHINE(lvms), cpu->phy_id);
    cpu_slot->cpu = CPU(dev);
}

static bool memhp_type_supported(DeviceState *dev)
{
    /* we only support pc dimm now */
    return object_dynamic_cast(OBJECT(dev), TYPE_PC_DIMM) &&
           !object_dynamic_cast(OBJECT(dev), TYPE_NVDIMM);
}

static void virt_mem_pre_plug(HotplugHandler *hotplug_dev, DeviceState *dev,
                                 Error **errp)
{
    pc_dimm_pre_plug(PC_DIMM(dev), MACHINE(hotplug_dev), errp);
}

static void virt_device_pre_plug(HotplugHandler *hotplug_dev,
                                            DeviceState *dev, Error **errp)
{
    if (memhp_type_supported(dev)) {
        virt_mem_pre_plug(hotplug_dev, dev, errp);
    } else if (object_dynamic_cast(OBJECT(dev), TYPE_LOONGARCH_CPU)) {
        virt_cpu_pre_plug(hotplug_dev, dev, errp);
    }
}

static void virt_mem_unplug_request(HotplugHandler *hotplug_dev,
                                     DeviceState *dev, Error **errp)
{
    LoongArchVirtMachineState *lvms = LOONGARCH_VIRT_MACHINE(hotplug_dev);

    /* the acpi ged is always exist */
    hotplug_handler_unplug_request(HOTPLUG_HANDLER(lvms->acpi_ged), dev,
                                   errp);
}

static void virt_device_unplug_request(HotplugHandler *hotplug_dev,
                                          DeviceState *dev, Error **errp)
{
    if (memhp_type_supported(dev)) {
        virt_mem_unplug_request(hotplug_dev, dev, errp);
    } else if (object_dynamic_cast(OBJECT(dev), TYPE_LOONGARCH_CPU)) {
        virt_cpu_unplug_request(hotplug_dev, dev, errp);
    }
}

static void virt_mem_unplug(HotplugHandler *hotplug_dev,
                             DeviceState *dev, Error **errp)
{
    LoongArchVirtMachineState *lvms = LOONGARCH_VIRT_MACHINE(hotplug_dev);

    hotplug_handler_unplug(HOTPLUG_HANDLER(lvms->acpi_ged), dev, errp);
    pc_dimm_unplug(PC_DIMM(dev), MACHINE(lvms));
    qdev_unrealize(dev);
}

static void virt_device_unplug(HotplugHandler *hotplug_dev,
                                          DeviceState *dev, Error **errp)
{
    if (memhp_type_supported(dev)) {
        virt_mem_unplug(hotplug_dev, dev, errp);
    } else if (object_dynamic_cast(OBJECT(dev), TYPE_LOONGARCH_CPU)) {
        virt_cpu_unplug(hotplug_dev, dev, errp);
    }
}

static void virt_mem_plug(HotplugHandler *hotplug_dev,
                             DeviceState *dev, Error **errp)
{
    LoongArchVirtMachineState *lvms = LOONGARCH_VIRT_MACHINE(hotplug_dev);

    pc_dimm_plug(PC_DIMM(dev), MACHINE(lvms));
    hotplug_handler_plug(HOTPLUG_HANDLER(lvms->acpi_ged),
                         dev, &error_abort);
}

static void virt_device_plug_cb(HotplugHandler *hotplug_dev,
                                        DeviceState *dev, Error **errp)
{
    LoongArchVirtMachineState *lvms = LOONGARCH_VIRT_MACHINE(hotplug_dev);
    MachineClass *mc = MACHINE_GET_CLASS(lvms);
    PlatformBusDevice *pbus;

    if (device_is_dynamic_sysbus(mc, dev)) {
        if (lvms->platform_bus_dev) {
            pbus = PLATFORM_BUS_DEVICE(lvms->platform_bus_dev);
            platform_bus_link_device(pbus, SYS_BUS_DEVICE(dev));
        }
    } else if (memhp_type_supported(dev)) {
        virt_mem_plug(hotplug_dev, dev, errp);
    } else if (object_dynamic_cast(OBJECT(dev), TYPE_LOONGARCH_CPU)) {
        virt_cpu_plug(hotplug_dev, dev, errp);
    }
}

static HotplugHandler *virt_get_hotplug_handler(MachineState *machine,
                                                DeviceState *dev)
{
    MachineClass *mc = MACHINE_GET_CLASS(machine);

    if (device_is_dynamic_sysbus(mc, dev) ||
        object_dynamic_cast(OBJECT(dev), TYPE_LOONGARCH_CPU) ||
        object_dynamic_cast(OBJECT(dev), TYPE_VIRTIO_IOMMU_PCI) ||
        memhp_type_supported(dev)) {
        return HOTPLUG_HANDLER(machine);
    }
    return NULL;
}

static const CPUArchIdList *virt_possible_cpu_arch_ids(MachineState *ms)
{
    int n, arch_id;
    unsigned int max_cpus = ms->smp.max_cpus;
    LoongArchCPUTopo topo;

    if (ms->possible_cpus) {
        assert(ms->possible_cpus->len == max_cpus);
        return ms->possible_cpus;
    }

    ms->possible_cpus = g_malloc0(sizeof(CPUArchIdList) +
                                  sizeof(CPUArchId) * max_cpus);
    ms->possible_cpus->len = max_cpus;
    for (n = 0; n < ms->possible_cpus->len; n++) {
        virt_get_topo_from_index(ms, &topo, n);
        arch_id = virt_get_arch_id_from_topo(ms, &topo);
        ms->possible_cpus->cpus[n].type = ms->cpu_type;
        ms->possible_cpus->cpus[n].arch_id = arch_id;
        ms->possible_cpus->cpus[n].vcpus_count = 1;
        ms->possible_cpus->cpus[n].props.has_socket_id = true;
        ms->possible_cpus->cpus[n].props.socket_id = topo.socket_id;
        ms->possible_cpus->cpus[n].props.has_core_id = true;
        ms->possible_cpus->cpus[n].props.core_id = topo.core_id;
        ms->possible_cpus->cpus[n].props.has_thread_id = true;
        ms->possible_cpus->cpus[n].props.thread_id = topo.thread_id;
    }
    return ms->possible_cpus;
}

static CpuInstanceProperties virt_cpu_index_to_props(MachineState *ms,
                                                     unsigned cpu_index)
{
    MachineClass *mc = MACHINE_GET_CLASS(ms);
    const CPUArchIdList *possible_cpus = mc->possible_cpu_arch_ids(ms);

    assert(cpu_index < possible_cpus->len);
    return possible_cpus->cpus[cpu_index].props;
}

static int64_t virt_get_default_cpu_node_id(const MachineState *ms, int idx)
{
    int64_t socket_id;

    if (ms->numa_state->num_nodes) {
        socket_id = ms->possible_cpus->cpus[idx].props.socket_id;
        return socket_id % ms->numa_state->num_nodes;
    } else {
        return 0;
    }
}

static void virt_class_init(ObjectClass *oc, const void *data)
{
    MachineClass *mc = MACHINE_CLASS(oc);
    HotplugHandlerClass *hc = HOTPLUG_HANDLER_CLASS(oc);

    mc->init = virt_init;
    mc->default_cpu_type = LOONGARCH_CPU_TYPE_NAME("la464");
    mc->default_ram_id = "loongarch.ram";
    mc->desc = "QEMU LoongArch Virtual Machine";
    mc->max_cpus = LOONGARCH_MAX_CPUS;
    mc->is_default = 1;
    mc->default_kernel_irqchip_split = false;
    mc->block_default_type = IF_VIRTIO;
    mc->default_boot_order = "c";
    mc->no_cdrom = 1;
    mc->possible_cpu_arch_ids = virt_possible_cpu_arch_ids;
    mc->cpu_index_to_instance_props = virt_cpu_index_to_props;
    mc->get_default_cpu_node_id = virt_get_default_cpu_node_id;
    mc->numa_mem_supported = true;
    mc->auto_enable_numa_with_memhp = true;
    mc->auto_enable_numa_with_memdev = true;
    mc->has_hotpluggable_cpus = true;
    mc->get_hotplug_handler = virt_get_hotplug_handler;
    mc->default_nic = "virtio-net-pci";
    hc->plug = virt_device_plug_cb;
    hc->pre_plug = virt_device_pre_plug;
    hc->unplug_request = virt_device_unplug_request;
    hc->unplug = virt_device_unplug;

    object_class_property_add(oc, "acpi", "OnOffAuto",
        virt_get_acpi, virt_set_acpi,
        NULL, NULL);
    object_class_property_set_description(oc, "acpi",
        "Enable ACPI");
    object_class_property_add(oc, "v-eiointc", "OnOffAuto",
        virt_get_veiointc, virt_set_veiointc,
        NULL, NULL);
    object_class_property_set_description(oc, "v-eiointc",
                            "Enable Virt Extend I/O Interrupt Controller.");
    machine_class_allow_dynamic_sysbus_dev(mc, TYPE_RAMFB_DEVICE);
    machine_class_allow_dynamic_sysbus_dev(mc, TYPE_UEFI_VARS_SYSBUS);
#ifdef CONFIG_TPM
    machine_class_allow_dynamic_sysbus_dev(mc, TYPE_TPM_TIS_SYSBUS);
#endif
    object_class_property_add_str(oc, "x-oem-id",
                                  virt_get_oem_id,
                                  virt_set_oem_id);
    object_class_property_set_description(oc, "x-oem-id",
                                          "Override the default value of field OEMID "
                                          "in ACPI table header."
                                          "The string may be up to 6 bytes in size");


    object_class_property_add_str(oc, "x-oem-table-id",
                                  virt_get_oem_table_id,
                                  virt_set_oem_table_id);
    object_class_property_set_description(oc, "x-oem-table-id",
                                          "Override the default value of field OEM Table ID "
                                          "in ACPI table header."
                                          "The string may be up to 8 bytes in size");
}

static const TypeInfo virt_machine_types[] = {
    {
        .name           = TYPE_LOONGARCH_VIRT_MACHINE,
        .parent         = TYPE_MACHINE,
        .instance_size  = sizeof(LoongArchVirtMachineState),
        .class_init     = virt_class_init,
        .instance_init  = virt_initfn,
        .interfaces = (const InterfaceInfo[]) {
         { TYPE_HOTPLUG_HANDLER },
         { }
        },
    }
};

DEFINE_TYPES(virt_machine_types)
