Build the virt machine with the hex-board helpers instead of its own
copies, and drop the machine state that nothing used.  The machine, its
device tree and its devices are unchanged; virt writes interrupts as the
bare line number.

Reviewed-by: Pierrick Bouvier <[email protected]>
Signed-off-by: Brian Cain <[email protected]>
---
 include/hw/hexagon/virt.h |   6 -
 hw/hexagon/virt.c         | 309 ++++----------------------------------
 2 files changed, 26 insertions(+), 289 deletions(-)

diff --git a/include/hw/hexagon/virt.h b/include/hw/hexagon/virt.h
index 4ca2f1ef859..dc9f22a83c4 100644
--- a/include/hw/hexagon/virt.h
+++ b/include/hw/hexagon/virt.h
@@ -17,15 +17,9 @@ struct HexagonVirtMachineState {
     HexagonCommonMachineState parent_obj;
 
     int fdt_size;
-    MemoryRegion *sys;
     MemoryRegion tcm;
-    MemoryRegion bios;
-    Clock *apb_clk;
-    DeviceState *virtio_mmio[VIRTIO_DEV_COUNT];
 };
 
-void hexagon_load_fdt(const struct HexagonVirtMachineState *vms);
-
 #define TYPE_HEXAGON_VIRT_MACHINE MACHINE_TYPE_NAME("virt")
 OBJECT_DECLARE_SIMPLE_TYPE(HexagonVirtMachineState, HEXAGON_VIRT_MACHINE)
 
diff --git a/hw/hexagon/virt.c b/hw/hexagon/virt.c
index b601cd77a92..d8e91770595 100644
--- a/hw/hexagon/virt.c
+++ b/hw/hexagon/virt.c
@@ -8,26 +8,15 @@
 #include "qemu/osdep.h"
 #include "qapi/error.h"
 #include "hw/hexagon/virt.h"
-#include "elf.h"
-#include "hw/char/pl011.h"
-#include "hw/core/clock.h"
-#include "hw/core/sysbus-fdt.h"
 #include "hw/hexagon/hexagon.h"
+#include "hw/hexagon/hex-board.h"
 #include "hw/hexagon/hex-subsys.h"
 #include "hw/core/loader.h"
-#include "hw/core/qdev-properties.h"
-#include "hw/core/qdev-clock.h"
-#include "hw/core/register.h"
 #include "qemu/error-report.h"
-#include "qemu/guest-random.h"
 #include "qemu/target-info.h"
 #include "qemu/units.h"
 #include "machine_cfg_v68n_1024.h.inc"
-#include "system/address-spaces.h"
 #include "system/device_tree.h"
-#include "system/reset.h"
-#include "system/system.h"
-#include <libfdt.h>
 
 enum {
     VIRT_UART0,
@@ -49,222 +38,9 @@ static const MemMapEntry base_memmap[] = {
 };
 
 
-static void create_fdt(HexagonVirtMachineState *vms)
-{
-    MachineState *ms = MACHINE(vms);
-    void *fdt = create_device_tree(&vms->fdt_size);
-    uint8_t rng_seed[32];
-
-    if (!fdt) {
-        error_report("create_device_tree() failed");
-        exit(1);
-    }
-
-    ms->fdt = fdt;
-
-    qemu_fdt_setprop_cell(fdt, "/", "#address-cells", 0x2);
-    qemu_fdt_setprop_cell(fdt, "/", "#size-cells", 0x1);
-    qemu_fdt_setprop_string(fdt, "/", "model", "hexagon-virt,qemu");
-    qemu_fdt_setprop_string(fdt, "/", "compatible", "qcom,sm8150");
-
-    qemu_fdt_add_subnode(fdt, "/soc");
-    qemu_fdt_setprop_cell(fdt, "/soc", "#address-cells", 0x2);
-    qemu_fdt_setprop_cell(fdt, "/soc", "#size-cells", 0x1);
-    qemu_fdt_setprop(fdt, "/soc", "ranges", NULL, 0);
-
-    qemu_fdt_add_subnode(fdt, "/chosen");
-    qemu_guest_getrandom_nofail(rng_seed, sizeof(rng_seed));
-    qemu_fdt_setprop(fdt, "/chosen", "rng-seed", rng_seed, sizeof(rng_seed));
-}
-
-static int32_t fdt_add_l2vic(HexagonVirtMachineState *vms,
-                             const struct hexagon_machine_config *m_cfg)
-{
-    MachineState *ms = MACHINE(vms);
-    int32_t l2vic_phandle = qemu_fdt_alloc_phandle(ms->fdt);
-    char *nodename = g_strdup_printf("/soc/interrupt-controller@%x",
-                                     m_cfg->l2vic_base);
-    const char compat[] = "qcom,h2-pic\0hvm-pic";
-
-    qemu_fdt_setprop_cell(ms->fdt, "/soc", "interrupt-parent", l2vic_phandle);
-
-    qemu_fdt_add_subnode(ms->fdt, nodename);
-    qemu_fdt_setprop_cell(ms->fdt, nodename, "#address-cells", 0x0);
-    qemu_fdt_setprop_cell(ms->fdt, nodename, "#interrupt-cells", 0x1);
-    qemu_fdt_setprop(ms->fdt, nodename, "compatible", compat, sizeof(compat));
-    qemu_fdt_setprop_cells(ms->fdt, nodename, "reg", 0,
-                           m_cfg->l2vic_base, m_cfg->l2vic_size);
-    qemu_fdt_setprop(ms->fdt, nodename, "interrupt-controller", NULL, 0);
-    qemu_fdt_setprop_cell(ms->fdt, nodename, "phandle", l2vic_phandle);
-
-    g_free(nodename);
-    return l2vic_phandle;
-}
-
-static void fdt_add_hvx(HexagonVirtMachineState *vms,
-                        const struct hexagon_machine_config *m_cfg)
-{
-    const MachineState *ms = MACHINE(vms);
-    uint32_t vtcm_size_bytes = m_cfg->cfgtable.vtcm_size_kb * 1024;
-    if (vtcm_size_bytes > 0) {
-        qemu_fdt_add_subnode(ms->fdt, "/soc/vtcm");
-        qemu_fdt_setprop_string(ms->fdt, "/soc/vtcm", "compatible",
-                                "qcom,hexagon_vtcm");
-
-        assert(sizeof(m_cfg->cfgtable.vtcm_base) == sizeof(uint32_t));
-        qemu_fdt_setprop_cells(ms->fdt, "/soc/vtcm", "reg", 0,
-                               m_cfg->cfgtable.vtcm_base << 16,
-                               vtcm_size_bytes);
-    }
-
-    if (m_cfg->cfgtable.ext_contexts > 0) {
-        qemu_fdt_add_subnode(ms->fdt, "/soc/hvx");
-        qemu_fdt_setprop_string(ms->fdt, "/soc/hvx", "compatible",
-                                "qcom,hexagon-hvx");
-        qemu_fdt_setprop_cells(ms->fdt, "/soc/hvx", "qcom,hvx-max-ctxts",
-                               m_cfg->cfgtable.ext_contexts);
-        qemu_fdt_setprop_cells(ms->fdt, "/soc/hvx", "qcom,hvx-vlength",
-                               m_cfg->cfgtable.hvx_vec_log_length);
-    }
-}
-
-static int32_t fdt_add_clocks(const HexagonVirtMachineState *vms)
-{
-    MachineState *ms = MACHINE(vms);
-    int32_t clk_phandle = qemu_fdt_alloc_phandle(ms->fdt);
-
-    qemu_fdt_add_subnode(ms->fdt, "/apb-pclk");
-    qemu_fdt_setprop_string(ms->fdt, "/apb-pclk", "compatible", "fixed-clock");
-    qemu_fdt_setprop_cell(ms->fdt, "/apb-pclk", "#clock-cells", 0x0);
-    qemu_fdt_setprop_cell(ms->fdt, "/apb-pclk", "clock-frequency", 24000000);
-    qemu_fdt_setprop_string(ms->fdt, "/apb-pclk", "clock-output-names",
-                            "clk24mhz");
-    qemu_fdt_setprop_cell(ms->fdt, "/apb-pclk", "phandle", clk_phandle);
-
-    return clk_phandle;
-}
-
-static void fdt_add_uart(const HexagonVirtMachineState *vms, int uart,
-                         int32_t clk_phandle, int32_t l2vic_phandle)
-{
-    char *nodename;
-    hwaddr base = base_memmap[uart].base;
-    hwaddr size = base_memmap[uart].size;
-    assert(uart == 0);
-    const char compat[] = "arm,pl011\0arm,primecell";
-    const char clocknames[] = "uartclk\0apb_pclk";
-    MachineState *ms = MACHINE(vms);
-    DeviceState *dev;
-    SysBusDevice *s;
-
-    dev = qdev_new(TYPE_PL011);
-    s = SYS_BUS_DEVICE(dev);
-    qdev_prop_set_chr(dev, "chardev", serial_hd(0));
-    qdev_connect_clock_in(dev, "clk", vms->apb_clk);
-    sysbus_realize_and_unref(s, &error_fatal);
-    sysbus_mmio_map(s, 0, base);
-    sysbus_connect_irq(s, 0,
-                       qdev_get_gpio_in(vms->parent_obj.l2vic, 
VIRT_UART0_IRQ));
-
-    nodename = g_strdup_printf("/pl011@%" PRIx64, base);
-    qemu_fdt_add_subnode(ms->fdt, nodename);
-
-    /* Note that we can't use setprop_string because of the embedded NUL */
-    qemu_fdt_setprop(ms->fdt, nodename, "compatible", compat, sizeof(compat));
-    qemu_fdt_setprop_cells(ms->fdt, nodename, "reg", 0, base, size);
-    qemu_fdt_setprop_cell(ms->fdt, nodename, "interrupts", VIRT_UART0_IRQ);
-    qemu_fdt_setprop_cell(ms->fdt, nodename, "interrupt-parent",
-                          l2vic_phandle);
-    qemu_fdt_setprop_cells(ms->fdt, nodename, "clocks", clk_phandle,
-                           clk_phandle);
-    qemu_fdt_setprop(ms->fdt, nodename, "clock-names", clocknames,
-                     sizeof(clocknames));
-
-    qemu_fdt_setprop_string(ms->fdt, "/chosen", "stdout-path", nodename);
-    qemu_fdt_add_subnode(ms->fdt, "/aliases");
-    qemu_fdt_setprop_string(ms->fdt, "/aliases", "serial0", nodename);
-
-    g_free(nodename);
-}
-
-static void fdt_add_cpu_nodes(const HexagonVirtMachineState *vms)
-{
-    MachineState *ms = MACHINE(vms);
-    qemu_fdt_add_subnode(ms->fdt, "/cpus");
-    qemu_fdt_setprop_cell(ms->fdt, "/cpus", "#address-cells", 0x1);
-    qemu_fdt_setprop_cell(ms->fdt, "/cpus", "#size-cells", 0x0);
-
-    /* cpu nodes */
-    for (int num = ms->smp.cpus - 1; num >= 0; num--) {
-        char *nodename = g_strdup_printf("/cpus/cpu@%d", num);
-        qemu_fdt_add_subnode(ms->fdt, nodename);
-        qemu_fdt_setprop_string(ms->fdt, nodename, "device_type", "cpu");
-        qemu_fdt_setprop_cell(ms->fdt, nodename, "reg", num);
-        qemu_fdt_setprop_cell(ms->fdt, nodename, "phandle",
-                              qemu_fdt_alloc_phandle(ms->fdt));
-        g_free(nodename);
-    }
-}
-
-static void create_virtio_devices(HexagonVirtMachineState *vms,
-                                  int32_t l2vic_phandle)
-{
-    MachineState *ms = MACHINE(vms);
-    hwaddr size = base_memmap[VIRT_MMIO].size;
-
-    for (int i = 0; i < VIRTIO_DEV_COUNT; i++) {
-        int irq = VIRTIO_IRQ_BASE + i;
-        hwaddr base = base_memmap[VIRT_MMIO].base + i * size;
-        char *nodename = g_strdup_printf("/soc/virtio_mmio@%" PRIx64, base);
-        DeviceState *dev = qdev_new("virtio-mmio");
-        SysBusDevice *s = SYS_BUS_DEVICE(dev);
-
-        object_property_add_child(OBJECT(MACHINE(vms)), "virtio-mmio[*]",
-                                  OBJECT(dev));
-        sysbus_realize_and_unref(s, &error_fatal);
-        sysbus_mmio_map(s, 0, base);
-        sysbus_connect_irq(s, 0,
-                           qdev_get_gpio_in(vms->parent_obj.l2vic, irq));
-        vms->virtio_mmio[i] = dev;
-
-        qemu_fdt_add_subnode(ms->fdt, nodename);
-        qemu_fdt_setprop_string(ms->fdt, nodename, "compatible",
-                                "virtio,mmio");
-        qemu_fdt_setprop_cells(ms->fdt, nodename, "reg", 0, base, size);
-        qemu_fdt_setprop_cell(ms->fdt, nodename, "interrupts", irq);
-        qemu_fdt_setprop_cell(ms->fdt, nodename, "interrupt-parent",
-                              l2vic_phandle);
-
-        g_free(nodename);
-    }
-}
-
-void hexagon_load_fdt(const HexagonVirtMachineState *vms)
-{
-    MachineState *ms = MACHINE(vms);
-    hwaddr fdt_addr = base_memmap[VIRT_FDT].base;
-    uint32_t fdtsize = vms->fdt_size;
-
-    g_assert(fdtsize <= base_memmap[VIRT_FDT].size);
-    /* copy in the device tree */
-    rom_add_blob_fixed_as("fdt", ms->fdt, fdtsize, fdt_addr,
-                          &address_space_memory);
-    qemu_register_reset_nosnapshotload(
-        qemu_fdt_randomize_seeds,
-        rom_ptr_for_as(&address_space_memory, fdt_addr, fdtsize));
-}
-
 static uint64_t load_kernel(const HexagonVirtMachineState *vms)
 {
-    MachineState *ms = MACHINE(vms);
-    uint64_t entry = 0;
-    if (load_elf_ram_sym(ms->kernel_filename, NULL, NULL, NULL, &entry, NULL,
-                         NULL, NULL, 0, EM_HEXAGON, 0, 0, 
&address_space_memory,
-                         false, NULL) > 0) {
-        return entry;
-    }
-    error_report("error loading '%s'", ms->kernel_filename);
-    exit(1);
+    return hex_board_load_elf(MACHINE(vms)->kernel_filename, NULL, NULL, NULL);
 }
 
 static uint64_t load_bios(HexagonVirtMachineState *vms)
@@ -283,75 +59,42 @@ static uint64_t load_bios(HexagonVirtMachineState *vms)
     return bios_addr;  /* Return entry point at address 0x0 */
 }
 
-static void do_cpu_reset(void *opaque)
-{
-    HexagonCPU *cpu = opaque;
-    CPUState *cs = CPU(cpu);
-    cpu_reset(cs);
-}
-
 static void virt_init(MachineState *ms)
 {
     HexagonVirtMachineState *vms = HEXAGON_VIRT_MACHINE(ms);
     const struct hexagon_machine_config *m_cfg = &v68n_1024;
-    int32_t clk_phandle;
     int32_t l2vic_phandle;
+    uint64_t start = 0;
+    bool have_start = false;
 
-    create_fdt(vms);
+    hex_board_create_fdt(ms, "hexagon-virt,qemu", "qcom,sm8150",
+                         &vms->fdt_size);
     qemu_fdt_setprop_string(ms->fdt, "/chosen", "bootargs", 
ms->kernel_cmdline);
 
-    vms->sys = get_system_memory();
-
-    /* Create APB clock for peripherals */
-    vms->apb_clk = clock_new(OBJECT(ms), "apb-pclk");
-    clock_set_hz(vms->apb_clk, 24000000);
-
     hex_subsys_create(&vms->parent_obj, m_cfg, v68_rev);
-
-    if (m_cfg->l2tcm_size) {
-        memory_region_init_ram(&vms->tcm, NULL, "tcm.ram", m_cfg->l2tcm_size,
-                               &error_fatal);
-        memory_region_add_subregion(vms->sys, m_cfg->cfgtable.l2tcm_base << 16,
-                                    &vms->tcm);
-    }
-
-    fdt_add_hvx(vms, m_cfg);
-
-    l2vic_phandle = fdt_add_l2vic(vms, m_cfg);
-    create_virtio_devices(vms, l2vic_phandle);
-
-    g_autofree HexagonCPU **cpus = g_new(HexagonCPU *, ms->smp.cpus);
-
-    for (int i = 0; i < ms->smp.cpus; i++) {
-        HexagonCPU *cpu = HEXAGON_CPU(object_new(ms->cpu_type));
-        qemu_register_reset(do_cpu_reset, cpu);
-
-        if (i == 0) {
-            if (ms->kernel_filename) {
-                uint64_t entry = load_kernel(vms);
-                qdev_prop_set_uint32(DEVICE(cpu), "exec-start-addr", entry);
-            } else if (ms->firmware) {
-                uint64_t entry = load_bios(vms);
-                qdev_prop_set_uint32(DEVICE(cpu), "exec-start-addr", entry);
-            }
-        }
-        qdev_prop_set_uint32(DEVICE(cpu), "htid", i);
-        qdev_prop_set_bit(DEVICE(cpu), "start-powered-off", (i != 0));
-        hex_subsys_add_cpu(&vms->parent_obj, DEVICE(cpu));
-        cpus[i] = cpu;
-    }
-
-    hex_subsys_realize_cluster(&vms->parent_obj);
-
-    for (int i = 0; i < ms->smp.cpus; i++) {
-        hex_subsys_realize_cpu(&vms->parent_obj, DEVICE(cpus[i]), (i == 0));
+    hex_board_create_tcm(m_cfg, &vms->tcm);
+    hex_board_fdt_add_hvx(ms, m_cfg);
+
+    l2vic_phandle = hex_board_fdt_add_l2vic(ms, m_cfg);
+    hex_board_create_virtio(ms, base_memmap[VIRT_MMIO].base,
+                            base_memmap[VIRT_MMIO].size, VIRTIO_IRQ_BASE,
+                            VIRTIO_DEV_COUNT, l2vic_phandle);
+
+    if (ms->kernel_filename) {
+        start = load_kernel(vms);
+        have_start = true;
+    } else if (ms->firmware) {
+        start = load_bios(vms);
+        have_start = true;
     }
+    hex_board_create_cpus(ms, have_start, start);
 
-    fdt_add_cpu_nodes(vms);
-    clk_phandle = fdt_add_clocks(vms);
-    fdt_add_uart(vms, VIRT_UART0, clk_phandle, l2vic_phandle);
+    hex_board_fdt_add_cpus(ms);
+    hex_board_create_uart(ms, base_memmap[VIRT_UART0].base,
+                          base_memmap[VIRT_UART0].size, VIRT_UART0_IRQ,
+                          l2vic_phandle);
 
-    hexagon_load_fdt(vms);
+    hex_board_load_fdt(ms, vms->fdt_size, base_memmap[VIRT_FDT].base);
 }
 
 
-- 
2.34.1

Reply via email to