[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
[Qemu-devel] [PATCH 09/17] e500: move mpic under CCSR
From: |
Michael Davidsaver |
Subject: |
[Qemu-devel] [PATCH 09/17] e500: move mpic under CCSR |
Date: |
Sun, 26 Nov 2017 15:59:07 -0600 |
Start moving code out of ppce500_init()
Existing ppce500_init_mpic() suggests that MPIC may not be created w/ KVM.
However, ppce500_init() used mpicdev unconditionally, and would
fail if the MPIC isn't created. So require creation.
Not tested with KVM for lack of hardware.
Signed-off-by: Michael Davidsaver <address@hidden>
---
hw/ppc/e500.c | 102 +++--------------------------------------------------
hw/ppc/e500_ccsr.c | 85 +++++++++++++++++++++++++++++++++++++++++---
2 files changed, 84 insertions(+), 103 deletions(-)
diff --git a/hw/ppc/e500.c b/hw/ppc/e500.c
index e22919f4f1..1872bb8eaa 100644
--- a/hw/ppc/e500.c
+++ b/hw/ppc/e500.c
@@ -29,7 +29,6 @@
#include "sysemu/kvm.h"
#include "kvm_ppc.h"
#include "sysemu/device_tree.h"
-#include "hw/ppc/openpic.h"
#include "hw/ppc/ppc.h"
#include "hw/loader.h"
#include "elf.h"
@@ -679,92 +678,6 @@ static void ppce500_cpu_reset(void *opaque)
mmubooke_create_initial_mapping(env);
}
-static DeviceState *ppce500_init_mpic_qemu(PPCE500Params *params,
- qemu_irq **irqs)
-{
- DeviceState *dev;
- SysBusDevice *s;
- int i, j, k;
-
- dev = qdev_create(NULL, TYPE_OPENPIC);
- object_property_add_child(qdev_get_machine(), "pic", OBJECT(dev),
- &error_fatal);
- qdev_prop_set_uint32(dev, "model", params->mpic_version);
- qdev_prop_set_uint32(dev, "nb_cpus", smp_cpus);
-
- qdev_init_nofail(dev);
- s = SYS_BUS_DEVICE(dev);
-
- k = 0;
- for (i = 0; i < smp_cpus; i++) {
- for (j = 0; j < OPENPIC_OUTPUT_NB; j++) {
- sysbus_connect_irq(s, k++, irqs[i][j]);
- }
- }
-
- return dev;
-}
-
-static DeviceState *ppce500_init_mpic_kvm(PPCE500Params *params,
- qemu_irq **irqs, Error **errp)
-{
- Error *err = NULL;
- DeviceState *dev;
- CPUState *cs;
-
- dev = qdev_create(NULL, TYPE_KVM_OPENPIC);
- qdev_prop_set_uint32(dev, "model", params->mpic_version);
-
- object_property_set_bool(OBJECT(dev), true, "realized", &err);
- if (err) {
- error_propagate(errp, err);
- object_unparent(OBJECT(dev));
- return NULL;
- }
-
- CPU_FOREACH(cs) {
- if (kvm_openpic_connect_vcpu(dev, cs)) {
- fprintf(stderr, "%s: failed to connect vcpu to irqchip\n",
- __func__);
- abort();
- }
- }
-
- return dev;
-}
-
-static DeviceState *ppce500_init_mpic(MachineState *machine,
- PPCE500Params *params,
- MemoryRegion *ccsr,
- qemu_irq **irqs)
-{
- DeviceState *dev = NULL;
- SysBusDevice *s;
-
- if (kvm_enabled()) {
- Error *err = NULL;
-
- if (machine_kernel_irqchip_allowed(machine)) {
- dev = ppce500_init_mpic_kvm(params, irqs, &err);
- }
- if (machine_kernel_irqchip_required(machine) && !dev) {
- error_reportf_err(err,
- "kernel_irqchip requested but unavailable: ");
- exit(1);
- }
- }
-
- if (!dev) {
- dev = ppce500_init_mpic_qemu(params, irqs);
- }
-
- s = SYS_BUS_DEVICE(dev);
- memory_region_add_subregion(ccsr, MPC8544_MPIC_REGS_OFFSET,
- s->mmio[0].memory);
-
- return dev;
-}
-
static void ppce500_power_off(void *opaque, int line, int on)
{
if (on) {
@@ -794,18 +707,14 @@ void ppce500_init(MachineState *machine, PPCE500Params
*params)
/* irq num for pin INTA, INTB, INTC and INTD is 1, 2, 3 and
* 4 respectively */
unsigned int pci_irq_nrs[PCI_NUM_PINS] = {1, 2, 3, 4};
- qemu_irq **irqs;
DeviceState *dev, *mpicdev;
CPUPPCState *firstenv = NULL;
MemoryRegion *ccsr_addr_space;
SysBusDevice *s;
- irqs = g_malloc0(smp_cpus * sizeof(qemu_irq *));
- irqs[0] = g_malloc0(smp_cpus * sizeof(qemu_irq) * OPENPIC_OUTPUT_NB);
for (i = 0; i < smp_cpus; i++) {
PowerPCCPU *cpu;
CPUState *cs;
- qemu_irq *input;
cpu = POWERPC_CPU(cpu_create(machine->cpu_type));
env = &cpu->env;
@@ -821,13 +730,7 @@ void ppce500_init(MachineState *machine, PPCE500Params
*params)
firstenv = env;
}
- irqs[i] = irqs[0] + (i * OPENPIC_OUTPUT_NB);
- input = (qemu_irq *)env->irq_inputs;
- irqs[i][OPENPIC_OUTPUT_INT] = input[PPCE500_INPUT_INT];
- irqs[i][OPENPIC_OUTPUT_CINT] = input[PPCE500_INPUT_CINT];
env->spr_cb[SPR_BOOKE_PIR].default_value = cs->cpu_index = i;
- env->mpic_iack = params->ccsrbar_base +
- MPC8544_MPIC_REGS_OFFSET + 0xa0;
ppc_booke_timers_init(cpu, 400000000, PPC_TIMER_E500);
@@ -857,12 +760,15 @@ void ppce500_init(MachineState *machine, PPCE500Params
*params)
dev = qdev_create(NULL, "e500-ccsr");
object_property_add_child(qdev_get_machine(), "e500-ccsr",
OBJECT(dev), NULL);
+ qdev_prop_set_uint32(dev, "mpic-model", params->mpic_version);
qdev_prop_set_uint32(dev, "base", params->ccsrbar_base);
qdev_prop_set_uint32(dev, "ram-size", ram_size);
qdev_init_nofail(dev);
ccsr_addr_space = sysbus_mmio_get_region(SYS_BUS_DEVICE(dev), 0);
- mpicdev = ppce500_init_mpic(machine, params, ccsr_addr_space, irqs);
+ /* created under "e500-ccsr" */
+ mpicdev = DEVICE(object_resolve_path("/machine/pic", 0));
+ assert(mpicdev);
/* Serial */
if (serial_hds[0]) {
diff --git a/hw/ppc/e500_ccsr.c b/hw/ppc/e500_ccsr.c
index 9400d7cf13..68d952794e 100644
--- a/hw/ppc/e500_ccsr.c
+++ b/hw/ppc/e500_ccsr.c
@@ -24,10 +24,14 @@
#include "qemu-common.h"
#include "qemu/log.h"
#include "qemu/error-report.h"
+#include "qapi/error.h"
#include "cpu.h"
#include "hw/hw.h"
+#include "hw/boards.h"
#include "sysemu/sysemu.h"
+#include "sysemu/kvm.h"
#include "hw/sysbus.h"
+#include "hw/ppc/openpic.h"
/* E500_ denotes registers common to all */
/* Some CCSR offsets duplicated in e500.c */
@@ -185,20 +189,90 @@ static void e500_ccsr_reset(DeviceState *dev)
e500_ccsr_post_move(ccsr);
}
-static void e500_ccsr_initfn(Object *obj)
+static void e500_ccsr_init(Object *obj)
{
- CCSRState *ccsr = E500_CCSR(obj);
+ DeviceState *dev = DEVICE(obj);
+ CCSRState *ccsr = E500_CCSR(dev);
+
+ assert(current_machine);
+ if (kvm_enabled()) {
+
+ if (!machine_kernel_irqchip_allowed(current_machine)) {
+ error_report("Machine does not allow PIC,"
+ " but this is not supported");
+ exit(1);
+ }
- memory_region_init_io(&ccsr->iomem, obj, &e500_ccsr_ops,
+ ccsr->pic = qdev_create(NULL, TYPE_KVM_OPENPIC);
+ } else {
+ ccsr->pic = qdev_create(NULL, TYPE_OPENPIC);
+ }
+
+ if (!ccsr->pic) {
+ error_report("Failed to create PIC");
+ exit(1);
+ }
+
+ object_property_add_child(qdev_get_machine(), "pic", OBJECT(ccsr->pic),
+ &error_fatal);
+
+ qdev_prop_set_uint32(ccsr->pic, "nb_cpus", smp_cpus);
+
+ object_property_add_alias(obj, "mpic-model",
+ OBJECT(ccsr->pic), "model",
+ &error_fatal);
+}
+
+static void e500_ccsr_realize(DeviceState *dev, Error **errp)
+{
+ CCSRState *ccsr = E500_CCSR(dev);
+ SysBusDevice *pic;
+
+ /* Base 1MB CCSR Region */
+ memory_region_init_io(&ccsr->iomem, OBJECT(dev), &e500_ccsr_ops,
ccsr, "e500-ccsr", 1024 * 1024);
- sysbus_init_mmio(SYS_BUS_DEVICE(obj), &ccsr->iomem);
+ sysbus_init_mmio(SYS_BUS_DEVICE(dev), &ccsr->iomem);
+
+ qdev_init_nofail(ccsr->pic);
+ pic = SYS_BUS_DEVICE(ccsr->pic);
+
+ /* connect MPIC to CPU(s) */
+ if (kvm_enabled()) {
+ CPUState *cs;
+
+ CPU_FOREACH(cs) {
+ if (kvm_openpic_connect_vcpu(ccsr->pic, cs)) {
+ error_setg(errp, "%s: failed to connect vcpu to irqchip",
+ __func__);
+ return;
+ }
+ }
+
+ } else {
+ CPUState *cs;
+
+ CPU_FOREACH(cs) {
+ PowerPCCPU *cpu = POWERPC_CPU(cs);
+ CPUPPCState *env = &cpu->env;
+ qemu_irq *inputs = (qemu_irq *)env->irq_inputs;
+ int base = cs->cpu_index * PPCE500_INPUT_NB;
+
+ sysbus_connect_irq(pic, base + OPENPIC_OUTPUT_INT,
+ inputs[PPCE500_INPUT_INT]);
+ sysbus_connect_irq(pic, base + OPENPIC_OUTPUT_CINT,
+ inputs[PPCE500_INPUT_CINT]);
+ }
+ }
+ memory_region_add_subregion(&ccsr->iomem, E500_MPIC_OFFSET,
+ sysbus_mmio_get_region(pic, 0));
}
static Property e500_ccsr_props[] = {
DEFINE_PROP_UINT32("base", CCSRState, defbase, 0xff700000),
DEFINE_PROP_UINT32("ram-size", CCSRState, ram_size, 0),
DEFINE_PROP_UINT32("porpllsr", CCSRState, porpllsr, 0),
+ /* "mpic-model" aliased from MPIC */
DEFINE_PROP_END_OF_LIST()
};
@@ -221,6 +295,7 @@ void e500_ccsr_class_initfn(ObjectClass *klass, void *data)
dc->props = e500_ccsr_props;
dc->vmsd = &vmstate_e500_ccsr;
+ dc->realize = e500_ccsr_realize;
dc->reset = e500_ccsr_reset;
}
@@ -228,7 +303,7 @@ static const TypeInfo e500_ccsr_info = {
.name = TYPE_E500_CCSR,
.parent = TYPE_SYS_BUS_DEVICE,
.instance_size = sizeof(CCSRState),
- .instance_init = e500_ccsr_initfn,
+ .instance_init = e500_ccsr_init,
.class_size = sizeof(SysBusDeviceClass),
.class_init = e500_ccsr_class_initfn
};
--
2.11.0
- [Qemu-devel] [PATCH 04/17] qtest: add e500_i2c_create(), (continued)
- [Qemu-devel] [PATCH 04/17] qtest: add e500_i2c_create(), Michael Davidsaver, 2017/11/26
- [Qemu-devel] [PATCH 03/17] i2c: add mpc8540 i2c controller, Michael Davidsaver, 2017/11/26
- [Qemu-devel] [PATCH 01/17] openpic: debug w/ info_report(), Michael Davidsaver, 2017/11/26
- [Qemu-devel] [PATCH 07/17] e500: fix pci host bridge class/type, Michael Davidsaver, 2017/11/26
- [Qemu-devel] [PATCH 05/17] timer: generalize Dallas/Maxim RTC i2c devices, Michael Davidsaver, 2017/11/26
- [Qemu-devel] [PATCH 11/17] e500: derive baud from CCB clock, Michael Davidsaver, 2017/11/26
- [Qemu-devel] [PATCH 06/17] tests: rewrite testing for DS RTC devices, Michael Davidsaver, 2017/11/26
- [Qemu-devel] [PATCH 09/17] e500: move mpic under CCSR,
Michael Davidsaver <=
- [Qemu-devel] [PATCH 10/17] e500: move uarts CCSR, Michael Davidsaver, 2017/11/26
- [Qemu-devel] [PATCH 14/17] e500: split mpc8544ds specific initialization, Michael Davidsaver, 2017/11/26
- [Qemu-devel] [PATCH 08/17] e500: additional CCSR registers, Michael Davidsaver, 2017/11/26
- [Qemu-devel] [PATCH 12/17] e500: add i2c controller to CCSR, Michael Davidsaver, 2017/11/26
- [Qemu-devel] [PATCH 13/17] e500: move PCI host bridge into CCSR, Michael Davidsaver, 2017/11/26
- [Qemu-devel] [PATCH 17/17] tests: add mvme3100-test, Michael Davidsaver, 2017/11/26
- [Qemu-devel] [PATCH 16/17] tests: run ds-rtc-i2c-test w/ ppc/mvme3100, Michael Davidsaver, 2017/11/26
- [Qemu-devel] [PATCH 15/17] ppc: add mvme3100 machine, Michael Davidsaver, 2017/11/26