/*
 * Arm Musca-B1 test chip board emulation
 *
 * Copyright (c) 2019 Linaro Limited
 * Written by Peter Maydell
 *
 *  This program is free software; you can redistribute it and/or modify
 *  it under the terms of the GNU General Public License version 2 or
 *  (at your option) any later version.
 */

/*
 * The Musca boards are a reference implementation of a system using
 * the SSE-200 subsystem for embedded:
 * https://developer.arm.com/products/system-design/development-boards/iot-test-chips-and-boards/musca-a-test-chip-board
 * https://developer.arm.com/products/system-design/development-boards/iot-test-chips-and-boards/musca-b-test-chip-board
 * We model the A and B1 variants of this board, as described in the TRMs:
 * http://infocenter.arm.com/help/topic/com.arm.doc.101107_0000_00_en/index.html
 * http://infocenter.arm.com/help/topic/com.arm.doc.101312_0000_00_en/index.html
 */

#include "qemu/osdep.h"
#include "qemu/error-report.h"
#include "qapi/error.h"
#include "exec/address-spaces.h"
#include "sysemu/sysemu.h"
#include "hw/arm/arm.h"
#include "hw/arm/armsse.h"
#include "hw/boards.h"
#include "hw/char/pl011.h"
#include "hw/core/split-irq.h"
#include "hw/misc/tz-mpc.h"
#include "hw/misc/tz-ppc.h"
#include "hw/misc/unimp.h"
#include "hw/timer/pl031.h"

#define MUSCA_NUMIRQ_MAX 96
#define MUSCA_PPC_MAX 3
#define MUSCA_MPC_MAX 5

typedef struct MPCInfo MPCInfo;

typedef enum MuscaType {
    MUSCA_A,
    MUSCA_B1,
} MuscaType;

typedef struct {
    MachineClass parent;
    MuscaType type;
    uint32_t init_svtor;
    int sram_addr_width;
    int num_irqs;
    const MPCInfo *mpc_info;
    int num_mpcs;
} MuscaMachineClass;

typedef struct {
    MachineState parent;

    ARMSSE sse;
    /* RAM and flash */
    MemoryRegion ram[MUSCA_MPC_MAX];
    SplitIRQ cpu_irq_splitter[MUSCA_NUMIRQ_MAX];
    SplitIRQ sec_resp_splitter;
    TZPPC ppc[MUSCA_PPC_MAX];
    MemoryRegion container;
    UnimplementedDeviceState eflash[2];
    UnimplementedDeviceState qspi;
    TZMPC mpc[MUSCA_MPC_MAX];
    UnimplementedDeviceState mhu[2];
    UnimplementedDeviceState pwm[3];
    UnimplementedDeviceState i2s;
    PL011State uart[2];
    UnimplementedDeviceState i2c[2];
    UnimplementedDeviceState spi;
    UnimplementedDeviceState scc;
    UnimplementedDeviceState timer;
    PL031State rtc;
    UnimplementedDeviceState pvt;
    UnimplementedDeviceState sdio;
    UnimplementedDeviceState gpio;
    UnimplementedDeviceState cryptoisland;
} MuscaMachineState;

#define TYPE_MUSCA_MACHINE "musca"
#define TYPE_MUSCA_A_MACHINE MACHINE_TYPE_NAME("musca-a")
#define TYPE_MUSCA_B1_MACHINE MACHINE_TYPE_NAME("musca-b1")

#define MUSCA_MACHINE(obj) \
    OBJECT_CHECK(MuscaMachineState, obj, TYPE_MUSCA_MACHINE)
#define MUSCA_MACHINE_GET_CLASS(obj) \
    OBJECT_GET_CLASS(MuscaMachineClass, obj, TYPE_MUSCA_MACHINE)
#define MUSCA_MACHINE_CLASS(klass) \
    OBJECT_CLASS_CHECK(MuscaMachineClass, klass, TYPE_MUSCA_MACHINE)

/*
 * Main SYSCLK frequency in Hz
 * TODO this should really be different for the two cores, but we
 * don't model that in our SSE-200 model yet.
 */
#define SYSCLK_FRQ 40000000

static qemu_irq get_sse_irq_in(MuscaMachineState *mms, int irqno)
{
    /* Return a qemu_irq which will signal IRQ n to all CPUs in the SSE. */
    assert(irqno < MUSCA_NUMIRQ_MAX);

    return qdev_get_gpio_in(DEVICE(&mms->cpu_irq_splitter[irqno]), 0);
}

/*
 * Most of the devices in the Musca board sit behind Peripheral Protection
 * Controllers. These data structures define the layout of which devices
 * sit behind which PPCs.
 * The devfn for each port is a function which creates, configures
 * and initializes the device, returning the MemoryRegion which
 * needs to be plugged into the downstream end of the PPC port.
 */
typedef MemoryRegion *MakeDevFn(MuscaMachineState *mms, void *opaque,
                                const char *name, hwaddr size);

typedef struct PPCPortInfo {
    const char *name;
    MakeDevFn *devfn;
    void *opaque;
    hwaddr addr;
    hwaddr size;
} PPCPortInfo;

typedef struct PPCInfo {
    const char *name;
    PPCPortInfo ports[TZ_NUM_PORTS];
} PPCInfo;

static MemoryRegion *make_unimp_dev(MuscaMachineState *mms,
                                    void *opaque, const char *name, hwaddr size)
{
    /*
     * Initialize, configure and realize a TYPE_UNIMPLEMENTED_DEVICE,
     * and return a pointer to its MemoryRegion.
     */
    UnimplementedDeviceState *uds = opaque;

    sysbus_init_child_obj(OBJECT(mms), name, uds,
                          sizeof(UnimplementedDeviceState),
                          TYPE_UNIMPLEMENTED_DEVICE);
    qdev_prop_set_string(DEVICE(uds), "name", name);
    qdev_prop_set_uint64(DEVICE(uds), "size", size);
    object_property_set_bool(OBJECT(uds), true, "realized", &error_fatal);
    return sysbus_mmio_get_region(SYS_BUS_DEVICE(uds), 0);
}

typedef enum MPCInfoType {
    MPC_RAM,
    MPC_ROM,
    MPC_CRYPTOISLAND,
} MPCInfoType;

struct MPCInfo {
    const char *name;
    hwaddr addr;
    hwaddr size;
    MPCInfoType type;
};

/* Order of the MPCs here must match the order of the bits in SECMPCINTSTATUS */
static const MPCInfo a_mpc_info[] = { {
        .name = "qspi",
        .type = MPC_ROM,
        .addr = 0x00200000,
        .size = 0x00800000,
    }, {
        .name = "sram",
        .type = MPC_RAM,
        .addr = 0x00000000,
        .size = 0x00200000,
    }
};

static const MPCInfo b1_mpc_info[] = { {
        .name = "qspi",
        .type = MPC_ROM,
        .addr = 0x00000000,
        .size = 0x02000000,
    }, {
        .name = "sram",
        .type = MPC_RAM,
        .addr = 0x0a400000,
        .size = 0x00080000,
    }, {
        .name = "eflash0",
        .type = MPC_ROM,
        .addr = 0x0a000000,
        .size = 0x00200000,
    }, {
        .name = "eflash1",
        .type = MPC_ROM,
        .addr = 0x0a200000,
        .size = 0x00200000,
    }, {
        .name = "cryptoisland",
        .type = MPC_CRYPTOISLAND,
        .addr = 0x0a000000,
        .size = 0x00200000,
    }
};

static MemoryRegion *make_mpc(MuscaMachineState *mms, void *opaque,
                              const char *name, hwaddr size)
{
    /*
     * Create an MPC and the RAM or flash behind it.
     * MPC 0: eFlash 0
     * MPC 1: eFlash 1
     * MPC 2: SRAM
     * MPC 3: QSPI flash
     * MPC 4: CryptoIsland
     * For now we implement the flash regions as ROM (ie not programmable)
     * (with their control interface memory regions being unimplemented
     * stubs behind the PPCs).
     * The whole CryptoIsland region behind its MPC is an unimplemented stub.
     */
    MuscaMachineClass *mmc = MUSCA_MACHINE_GET_CLASS(mms);
    TZMPC *mpc = opaque;
    int i = mpc - &mms->mpc[0];
    MemoryRegion *downstream;
    MemoryRegion *upstream;
    UnimplementedDeviceState *uds;
    char *mpcname;
    const MPCInfo *mpcinfo = mmc->mpc_info;

    mpcname = g_strdup_printf("%s-mpc", mpcinfo[i].name);

    switch (mpcinfo[i].type) {
    case MPC_ROM:
        downstream = &mms->ram[i];
        memory_region_init_rom(downstream, NULL, mpcinfo[i].name,
                               mpcinfo[i].size, &error_fatal);
        break;
    case MPC_RAM:
        downstream = &mms->ram[i];
        memory_region_init_ram(downstream, NULL, mpcinfo[i].name,
                               mpcinfo[i].size, &error_fatal);
        break;
    case MPC_CRYPTOISLAND:
        /* We don't implement the CryptoIsland yet */
        uds = &mms->cryptoisland;
        sysbus_init_child_obj(OBJECT(mms), name, uds,
                              sizeof(UnimplementedDeviceState),
                              TYPE_UNIMPLEMENTED_DEVICE);
        qdev_prop_set_string(DEVICE(uds), "name", mpcinfo[i].name);
        qdev_prop_set_uint64(DEVICE(uds), "size", mpcinfo[i].size);
        object_property_set_bool(OBJECT(uds), true, "realized", &error_fatal);
        downstream = sysbus_mmio_get_region(SYS_BUS_DEVICE(uds), 0);
        break;
    default:
        g_assert_not_reached();
    }

    sysbus_init_child_obj(OBJECT(mms), mpcname, mpc, sizeof(mms->mpc[0]),
                          TYPE_TZ_MPC);
    object_property_set_link(OBJECT(mpc), OBJECT(downstream),
                             "downstream", &error_fatal);
    object_property_set_bool(OBJECT(mpc), true, "realized", &error_fatal);
    /* Map the upstream end of the MPC into system memory */
    upstream = sysbus_mmio_get_region(SYS_BUS_DEVICE(mpc), 1);
    memory_region_add_subregion(get_system_memory(), mpcinfo[i].addr, upstream);
    /* and connect its interrupt to the SSE-200 */
    qdev_connect_gpio_out_named(DEVICE(mpc), "irq", 0,
                                qdev_get_gpio_in_named(DEVICE(&mms->sse),
                                                       "mpcexp_status", i));

    g_free(mpcname);
    /* Return the register interface MR for our caller to map behind the PPC */
    return sysbus_mmio_get_region(SYS_BUS_DEVICE(mpc), 0);
}

static MemoryRegion *make_rtc(MuscaMachineState *mms, void *opaque,
                              const char *name, hwaddr size)
{
    PL031State *rtc = opaque;

    sysbus_init_child_obj(OBJECT(mms), name, rtc, sizeof(mms->rtc), TYPE_PL031);
    object_property_set_bool(OBJECT(rtc), true, "realized", &error_fatal);
    sysbus_connect_irq(SYS_BUS_DEVICE(rtc), 0, get_sse_irq_in(mms, 39));
    return sysbus_mmio_get_region(SYS_BUS_DEVICE(rtc), 0);
}

static MemoryRegion *make_uart(MuscaMachineState *mms, void *opaque,
                               const char *name, hwaddr size)
{
    PL011State *uart = opaque;
    int i = uart - &mms->uart[0];
    int irqbase = 7 + i * 6;
    SysBusDevice *s;

    sysbus_init_child_obj(OBJECT(mms), name, uart, sizeof(mms->uart[0]),
                          TYPE_PL011);
    qdev_prop_set_chr(DEVICE(uart), "chardev", serial_hd(i));
    object_property_set_bool(OBJECT(uart), true, "realized", &error_fatal);
    s = SYS_BUS_DEVICE(uart);
    sysbus_connect_irq(s, 0, get_sse_irq_in(mms, irqbase + 5)); /* combined */
    sysbus_connect_irq(s, 1, get_sse_irq_in(mms, irqbase + 0)); /* RX */
    sysbus_connect_irq(s, 2, get_sse_irq_in(mms, irqbase + 1)); /* TX */
    sysbus_connect_irq(s, 3, get_sse_irq_in(mms, irqbase + 2)); /* RT */
    sysbus_connect_irq(s, 4, get_sse_irq_in(mms, irqbase + 3)); /* MS */
    sysbus_connect_irq(s, 5, get_sse_irq_in(mms, irqbase + 4)); /* E */
    return sysbus_mmio_get_region(SYS_BUS_DEVICE(uart), 0);
}

static MemoryRegion *make_musca_a_devs(MuscaMachineState *mms, void *opaque,
                                       const char *name, hwaddr size)
{
    /*
     * Create the container MemoryRegion for all the devices that live
     * behind the Musca-A PPC's single port. These devices don't have a PPC
     * port each, but we use the PPCPortInfo struct as a convenient way
     * to describe them. Note that addresses here are relative to the base
     * address of the PPC port region: 0x40100000, and devices appear both
     * at the 0x4... NS region and the 0x5... S region.
     */
    int i;
    MemoryRegion *container = &mms->container;

    const PPCPortInfo devices[] = {
        { "uart0", make_uart, &mms->uart[0], 0x1000, 0x1000 },
        { "uart1", make_uart, &mms->uart[1], 0x2000, 0x1000 },
        { "spi", make_unimp_dev, &mms->spi, 0x3000, 0x1000 },
        { "i2c0", make_unimp_dev, &mms->i2c[0], 0x4000, 0x1000 },
        { "i2c1", make_unimp_dev, &mms->i2c[1], 0x5000, 0x1000 },
        { "i2s", make_unimp_dev, &mms->i2s, 0x6000, 0x1000 },
        { "pwm0", make_unimp_dev, &mms->pwm[0], 0x7000, 0x1000 },
        { "rtc", make_rtc, &mms->rtc, 0x8000, 0x1000 },
        { "qspi", make_unimp_dev, &mms->qspi, 0xa000, 0x1000 },
        { "timer", make_unimp_dev, &mms->timer, 0xb000, 0x1000 },
        { "scc", make_unimp_dev, &mms->scc, 0xc000, 0x1000 },
        { "pwm1", make_unimp_dev, &mms->pwm[1], 0xe000, 0x1000 },
        { "pwm2", make_unimp_dev, &mms->pwm[2], 0xf000, 0x1000 },
        { "gpio", make_unimp_dev, &mms->gpio, 0x10000, 0x1000 },
        { "mpc0", make_mpc, &mms->mpc[0], 0x12000, 0x1000 },
        { "mpc1", make_mpc, &mms->mpc[1], 0x13000, 0x1000 },
    };

    memory_region_init(container, OBJECT(mms), "musca-device-container", size);

    for (i = 0; i < ARRAY_SIZE(devices); i++) {
        const PPCPortInfo *pinfo = &devices[i];
        MemoryRegion *mr;

        mr = pinfo->devfn(mms, pinfo->opaque, pinfo->name, pinfo->size);
        memory_region_add_subregion(container, pinfo->addr, mr);
    }

    return &mms->container;
}

static void musca_init(MachineState *machine)
{
    MuscaMachineState *mms = MUSCA_MACHINE(machine);
    MuscaMachineClass *mmc = MUSCA_MACHINE_GET_CLASS(mms);
    MachineClass *mc = MACHINE_GET_CLASS(machine);
    MemoryRegion *system_memory = get_system_memory();
    DeviceState *ssedev;
    DeviceState *dev_splitter;
    const PPCInfo *ppcs;
    int num_ppcs;
    int i;

    assert(mmc->num_irqs <= MUSCA_NUMIRQ_MAX);
    assert(mmc->num_mpcs <= MUSCA_MPC_MAX);

    if (strcmp(machine->cpu_type, mc->default_cpu_type) != 0) {
        error_report("This board can only be used with CPU %s",
                     mc->default_cpu_type);
        exit(1);
    }

    sysbus_init_child_obj(OBJECT(machine), "sse-200", &mms->sse,
                          sizeof(mms->sse), TYPE_SSE200);
    ssedev = DEVICE(&mms->sse);
    object_property_set_link(OBJECT(&mms->sse), OBJECT(system_memory),
                             "memory", &error_fatal);
    qdev_prop_set_uint32(ssedev, "EXP_NUMIRQ", mmc->num_irqs);
    qdev_prop_set_uint32(ssedev, "init-svtor", mmc->init_svtor);
    qdev_prop_set_uint32(ssedev, "SRAM_ADDR_WIDTH", mmc->sram_addr_width);
    qdev_prop_set_uint32(ssedev, "MAINCLK", SYSCLK_FRQ);
    object_property_set_bool(OBJECT(&mms->sse), true, "realized",
                             &error_fatal);

    /*
     * We need to create splitters to feed the IRQ inputs
     * for each CPU in the SSE-200 from each device in the board.
     */
    for (i = 0; i < mmc->num_irqs; i++) {
        char *name = g_strdup_printf("musca-irq-splitter%d", i);
        SplitIRQ *splitter = &mms->cpu_irq_splitter[i];

        object_initialize_child(OBJECT(machine), name,
                                splitter, sizeof(*splitter),
                                TYPE_SPLIT_IRQ, &error_fatal, NULL);
        g_free(name);

        object_property_set_int(OBJECT(splitter), 2, "num-lines",
                                &error_fatal);
        object_property_set_bool(OBJECT(splitter), true, "realized",
                                 &error_fatal);
        qdev_connect_gpio_out(DEVICE(splitter), 0,
                              qdev_get_gpio_in_named(ssedev, "EXP_IRQ", i));
        qdev_connect_gpio_out(DEVICE(splitter), 1,
                              qdev_get_gpio_in_named(ssedev,
                                                     "EXP_CPU1_IRQ", i));
    }

    /*
     * The sec_resp_cfg output from the SSE-200 must be split into multiple
     * lines, one for each of the PPCs we create here.
     */
    object_initialize(&mms->sec_resp_splitter, sizeof(mms->sec_resp_splitter),
                      TYPE_SPLIT_IRQ);
    object_property_add_child(OBJECT(machine), "sec-resp-splitter",
                              OBJECT(&mms->sec_resp_splitter), &error_fatal);
    object_property_set_int(OBJECT(&mms->sec_resp_splitter),
                            ARRAY_SIZE(mms->ppc), "num-lines", &error_fatal);
    object_property_set_bool(OBJECT(&mms->sec_resp_splitter), true,
                             "realized", &error_fatal);
    dev_splitter = DEVICE(&mms->sec_resp_splitter);
    qdev_connect_gpio_out_named(ssedev, "sec_resp_cfg", 0,
                                qdev_get_gpio_in(dev_splitter, 0));

    /*
     * Most of the devices in the board are behind Peripheral Protection
     * Controllers. The required order for initializing things is:
     *  + initialize the PPC
     *  + initialize, configure and realize downstream devices
     *  + connect downstream device MemoryRegions to the PPC
     *  + realize the PPC
     *  + map the PPC's MemoryRegions to the places in the address map
     *    where the downstream devices should appear
     *  + wire up the PPC's control lines to the SSE object
     *
     * The PPC mapping differs for the -A and -B1 variants; the -A version
     * is much simpler, using only a single port of a single PPC and putting
     * all the devices behind that.
     */
    const PPCInfo a_ppcs[] = { {
            .name = "ahb_ppcexp0",
            .ports = {
                { "musca-devices", make_musca_a_devs, 0, 0x40100000, 0x100000 },
            },
        },
    };

    /*
     * Devices listed with an 0x4.. address appear in both the NS 0x4.. region
     * and the 0x5.. S region. Devices listed with an 0x5.. address appear
     * only in the S region.
     */
    const PPCInfo b1_ppcs[] = { {
            .name = "apb_ppcexp0",
            .ports = {
                { "eflash0", make_unimp_dev, &mms->eflash[0],
                  0x52400000, 0x1000 },
                { "eflash1", make_unimp_dev, &mms->eflash[1],
                  0x52500000, 0x1000 },
                { "qspi", make_unimp_dev, &mms->qspi, 0x42800000, 0x100000 },
                { "mpc0", make_mpc, &mms->mpc[0], 0x52000000, 0x1000 },
                { "mpc1", make_mpc, &mms->mpc[1], 0x52100000, 0x1000 },
                { "mpc2", make_mpc, &mms->mpc[2], 0x52200000, 0x1000 },
                { "mpc3", make_mpc, &mms->mpc[3], 0x52300000, 0x1000 },
                { "mhu0", make_unimp_dev, &mms->mhu[0], 0x42600000, 0x100000 },
                { "mhu1", make_unimp_dev, &mms->mhu[1], 0x42700000, 0x100000 },
                { }, /* port 9: unused */
                { }, /* port 10: unused */
                { }, /* port 11: unused */
                { }, /* port 12: unused */
                { }, /* port 13: unused */
                { "mpc4", make_mpc, &mms->mpc[4], 0x52e00000, 0x1000 },
            },
        }, {
            .name = "apb_ppcexp1",
            .ports = {
                { "pwm0", make_unimp_dev, &mms->pwm[0], 0x40101000, 0x1000 },
                { "pwm1", make_unimp_dev, &mms->pwm[1], 0x40102000, 0x1000 },
                { "pwm2", make_unimp_dev, &mms->pwm[2], 0x40103000, 0x1000 },
                { "i2s", make_unimp_dev, &mms->i2s, 0x40104000, 0x1000 },
                { "uart0", make_uart, &mms->uart[0], 0x40105000, 0x1000 },
                { "uart1", make_uart, &mms->uart[1], 0x40106000, 0x1000 },
                { "i2c0", make_unimp_dev, &mms->i2c[0], 0x40108000, 0x1000 },
                { "i2c1", make_unimp_dev, &mms->i2c[1], 0x40109000, 0x1000 },
                { "spi", make_unimp_dev, &mms->spi, 0x4010a000, 0x1000 },
                { "scc", make_unimp_dev, &mms->scc, 0x5010b000, 0x1000 },
                { "timer", make_unimp_dev, &mms->timer, 0x4010c000, 0x1000 },
                { "rtc", make_rtc, &mms->rtc, 0x4010d000, 0x1000 },
                { "pvt", make_unimp_dev, &mms->pvt, 0x4010e000, 0x1000 },
                { "sdio", make_unimp_dev, &mms->sdio, 0x4010f000, 0x1000 },
            },
        }, {
            .name = "ahb_ppcexp0",
            .ports = {
                { }, /* port 0: unused */
                { "gpio", make_unimp_dev, &mms->gpio, 0x41000000, 0x1000 },
            },
        },
    };

    switch (mmc->type) {
    case MUSCA_A:
        ppcs = a_ppcs;
        num_ppcs = ARRAY_SIZE(a_ppcs);
        break;
    case MUSCA_B1:
        ppcs = b1_ppcs;
        num_ppcs = ARRAY_SIZE(b1_ppcs);
        break;
    default:
        g_assert_not_reached();
    }
    assert(num_ppcs <= MUSCA_PPC_MAX);

    for (i = 0; i < num_ppcs; i++) {
        const PPCInfo *ppcinfo = &ppcs[i];
        TZPPC *ppc = &mms->ppc[i];
        DeviceState *ppcdev;
        int port;
        char *gpioname;

        sysbus_init_child_obj(OBJECT(machine), ppcinfo->name, ppc,
                              sizeof(TZPPC), TYPE_TZ_PPC);
        ppcdev = DEVICE(ppc);

        for (port = 0; port < TZ_NUM_PORTS; port++) {
            const PPCPortInfo *pinfo = &ppcinfo->ports[port];
            MemoryRegion *mr;
            char *portname;

            if (!pinfo->devfn) {
                continue;
            }

            mr = pinfo->devfn(mms, pinfo->opaque, pinfo->name, pinfo->size);
            portname = g_strdup_printf("port[%d]", port);
            object_property_set_link(OBJECT(ppc), OBJECT(mr),
                                     portname, &error_fatal);
            g_free(portname);
        }

        object_property_set_bool(OBJECT(ppc), true, "realized", &error_fatal);

        for (port = 0; port < TZ_NUM_PORTS; port++) {
            const PPCPortInfo *pinfo = &ppcinfo->ports[port];

            if (!pinfo->devfn) {
                continue;
            }
            sysbus_mmio_map(SYS_BUS_DEVICE(ppc), port, pinfo->addr);

            gpioname = g_strdup_printf("%s_nonsec", ppcinfo->name);
            qdev_connect_gpio_out_named(ssedev, gpioname, port,
                                        qdev_get_gpio_in_named(ppcdev,
                                                               "cfg_nonsec",
                                                               port));
            g_free(gpioname);
            gpioname = g_strdup_printf("%s_ap", ppcinfo->name);
            qdev_connect_gpio_out_named(ssedev, gpioname, port,
                                        qdev_get_gpio_in_named(ppcdev,
                                                               "cfg_ap", port));
            g_free(gpioname);
        }

        gpioname = g_strdup_printf("%s_irq_enable", ppcinfo->name);
        qdev_connect_gpio_out_named(ssedev, gpioname, 0,
                                    qdev_get_gpio_in_named(ppcdev,
                                                           "irq_enable", 0));
        g_free(gpioname);
        gpioname = g_strdup_printf("%s_irq_clear", ppcinfo->name);
        qdev_connect_gpio_out_named(ssedev, gpioname, 0,
                                    qdev_get_gpio_in_named(ppcdev,
                                                           "irq_clear", 0));
        g_free(gpioname);
        gpioname = g_strdup_printf("%s_irq_status", ppcinfo->name);
        qdev_connect_gpio_out_named(ppcdev, "irq", 0,
                                    qdev_get_gpio_in_named(ssedev,
                                                           gpioname, 0));
        g_free(gpioname);

        qdev_connect_gpio_out(dev_splitter, i,
                              qdev_get_gpio_in_named(ppcdev,
                                                     "cfg_sec_resp", 0));
    }

    armv7m_load_kernel(ARM_CPU(first_cpu), machine->kernel_filename, 0x2000000);
}

static void musca_class_init(ObjectClass *oc, void *data)
{
    MachineClass *mc = MACHINE_CLASS(oc);

    mc->default_cpus = 2;
    mc->min_cpus = mc->default_cpus;
    mc->max_cpus = mc->default_cpus;
    mc->default_cpu_type = ARM_CPU_TYPE_NAME("cortex-m33");
    mc->init = musca_init;
}

static void musca_a_class_init(ObjectClass *oc, void *data)
{
    MachineClass *mc = MACHINE_CLASS(oc);
    MuscaMachineClass *mmc = MUSCA_MACHINE_CLASS(oc);

    mc->desc = "ARM Musca-A board (dual Cortex-M33)";
    mmc->type = MUSCA_A;
    mmc->init_svtor = 0x10200000;
    mmc->sram_addr_width = 15;
    mmc->num_irqs = 64;
    mmc->mpc_info = a_mpc_info;
    mmc->num_mpcs = ARRAY_SIZE(a_mpc_info);
}

static void musca_b1_class_init(ObjectClass *oc, void *data)
{
    MachineClass *mc = MACHINE_CLASS(oc);
    MuscaMachineClass *mmc = MUSCA_MACHINE_CLASS(oc);

    mc->desc = "ARM Musca-B1 board (dual Cortex-M33)";
    mmc->type = MUSCA_B1;
    /*
     * This matches the DAPlink firmware which boots from QSPI. There
     * is also a firmware blob which boots from the eFlash, which
     * uses init_svtor = 0x1A000000. QEMU doesn't currently support that,
     * though we could in theory expose a machine property on the command
     * line to allow the user to request eFlash boot.
     */
    mmc->init_svtor = 0x10000000;
    mmc->sram_addr_width = 17;
    mmc->num_irqs = 96;
    mmc->mpc_info = b1_mpc_info;
    mmc->num_mpcs = ARRAY_SIZE(b1_mpc_info);
}

static const TypeInfo musca_info = {
    .name = TYPE_MUSCA_MACHINE,
    .parent = TYPE_MACHINE,
    .abstract = true,
    .instance_size = sizeof(MuscaMachineState),
    .class_size = sizeof(MuscaMachineClass),
    .class_init = musca_class_init,
};

static const TypeInfo musca_a_info = {
    .name = TYPE_MUSCA_A_MACHINE,
    .parent = TYPE_MUSCA_MACHINE,
    .class_init = musca_a_class_init,
};

static const TypeInfo musca_b1_info = {
    .name = TYPE_MUSCA_B1_MACHINE,
    .parent = TYPE_MUSCA_MACHINE,
    .class_init = musca_b1_class_init,
};

static void musca_machine_init(void)
{
    type_register_static(&musca_info);
    type_register_static(&musca_a_info);
    type_register_static(&musca_b1_info);
}

type_init(musca_machine_init);
