[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
[Qemu-ppc] [PATCH v3 22/35] spapr: add classes for the XIVE models
From: |
Cédric Le Goater |
Subject: |
[Qemu-ppc] [PATCH v3 22/35] spapr: add classes for the XIVE models |
Date: |
Thu, 19 Apr 2018 14:43:18 +0200 |
The XIVE models for the emulated and the KVM mode will have a lot in
common. Introduce some classes to handle the differences, mostly to
synchronize the state with KVM for the monitor and migration. This is
very much like XICS is doing.
Signed-off-by: Cédric Le Goater <address@hidden>
---
hw/intc/spapr_xive.c | 32 ++++++++++++++++++
hw/intc/xive.c | 79 +++++++++++++++++++++++++++++++++++++++++++++
include/hw/ppc/spapr_xive.h | 13 ++++++++
include/hw/ppc/xive.h | 30 +++++++++++++++++
4 files changed, 154 insertions(+)
diff --git a/hw/intc/spapr_xive.c b/hw/intc/spapr_xive.c
index 98e067bfc90c..f0c2fe52b3c6 100644
--- a/hw/intc/spapr_xive.c
+++ b/hw/intc/spapr_xive.c
@@ -20,8 +20,13 @@
void spapr_xive_pic_print_info(sPAPRXive *xive, Monitor *mon)
{
+ sPAPRXiveClass *sxc = SPAPR_XIVE_GET_CLASS(xive);
int i;
+ if (sxc->synchronize_state) {
+ sxc->synchronize_state(xive);
+ }
+
xive_source_pic_print_info(&xive->source, mon);
monitor_printf(mon, "IVE Table\n");
@@ -150,6 +155,30 @@ static XiveEQ *spapr_xive_get_eq(XiveFabric *xf, uint32_t
eq_idx)
return xive_nvt_eq_get(nvt, SPAPR_XIVE_EQ_PRIO(eq_idx));
}
+static int vmstate_spapr_xive_pre_save(void *opaque)
+{
+ sPAPRXive *xive = opaque;
+ sPAPRXiveClass *sxc = SPAPR_XIVE_GET_CLASS(xive);
+
+ if (sxc->pre_save) {
+ sxc->pre_save(xive);
+ }
+
+ return 0;
+}
+
+static int vmstate_spapr_xive_post_load(void *opaque, int version_id)
+{
+ sPAPRXive *xive = opaque;
+ sPAPRXiveClass *sxc = SPAPR_XIVE_GET_CLASS(xive);
+
+ if (sxc->post_load) {
+ sxc->post_load(xive, version_id);
+ }
+
+ return 0;
+}
+
static const VMStateDescription vmstate_spapr_xive_ive = {
.name = TYPE_SPAPR_XIVE "/ive",
.version_id = 1,
@@ -164,6 +193,8 @@ static const VMStateDescription vmstate_spapr_xive = {
.name = TYPE_SPAPR_XIVE,
.version_id = 1,
.minimum_version_id = 1,
+ .pre_save = vmstate_spapr_xive_pre_save,
+ .post_load = vmstate_spapr_xive_post_load,
.fields = (VMStateField[]) {
VMSTATE_UINT32_EQUAL(nr_irqs, sPAPRXive, NULL),
VMSTATE_STRUCT_VARRAY_POINTER_UINT32(ivt, sPAPRXive, nr_irqs,
@@ -199,6 +230,7 @@ static const TypeInfo spapr_xive_info = {
.instance_init = spapr_xive_init,
.instance_size = sizeof(sPAPRXive),
.class_init = spapr_xive_class_init,
+ .class_size = sizeof(sPAPRXiveClass),
.interfaces = (InterfaceInfo[]) {
{ TYPE_XIVE_FABRIC },
{ },
diff --git a/hw/intc/xive.c b/hw/intc/xive.c
index 2daa36f77a6b..11af3bf1184a 100644
--- a/hw/intc/xive.c
+++ b/hw/intc/xive.c
@@ -349,9 +349,14 @@ static char *xive_nvt_ring_print(uint8_t *ring)
void xive_nvt_pic_print_info(XiveNVT *nvt, Monitor *mon)
{
+ XiveNVTClass *xnc = XIVE_NVT_GET_CLASS(nvt);
int cpu_index = nvt->cs ? nvt->cs->cpu_index : -1;
char *s;
+ if (xnc->synchronize_state) {
+ xnc->synchronize_state(nvt);
+ }
+
monitor_printf(mon, "CPU[%04x]: QW NSR CPPR IPB LSMFB ACK# INC AGE PIPR"
" W2\n", cpu_index);
@@ -366,6 +371,7 @@ void xive_nvt_pic_print_info(XiveNVT *nvt, Monitor *mon)
static void xive_nvt_reset(void *dev)
{
XiveNVT *nvt = XIVE_NVT(dev);
+ XiveNVTClass *xnc = XIVE_NVT_GET_CLASS(nvt);
int i;
memset(nvt->regs, 0, sizeof(nvt->regs));
@@ -378,11 +384,16 @@ static void xive_nvt_reset(void *dev)
for (i = 0; i < ARRAY_SIZE(nvt->eqt); i++) {
xive_eq_reset(&nvt->eqt[i]);
}
+
+ if (xnc->reset) {
+ xnc->reset(nvt);
+ }
}
static void xive_nvt_realize(DeviceState *dev, Error **errp)
{
XiveNVT *nvt = XIVE_NVT(dev);
+ XiveNVTClass *xnc = XIVE_NVT_GET_CLASS(nvt);
PowerPCCPU *cpu;
CPUPPCState *env;
Object *obj;
@@ -410,6 +421,10 @@ static void xive_nvt_realize(DeviceState *dev, Error
**errp)
return;
}
+ if (xnc->realize) {
+ xnc->realize(nvt, errp);
+ }
+
qemu_register_reset(xive_nvt_reset, dev);
}
@@ -442,10 +457,36 @@ static const VMStateDescription vmstate_xive_nvt_eq = {
},
};
+static int vmstate_xive_nvt_pre_save(void *opaque)
+{
+ XiveNVT *nvt = opaque;
+ XiveNVTClass *xnc = XIVE_NVT_GET_CLASS(nvt);
+
+ if (xnc->pre_save) {
+ xnc->pre_save(nvt);
+ }
+
+ return 0;
+}
+
+static int vmstate_xive_nvt_post_load(void *opaque, int version_id)
+{
+ XiveNVT *nvt = opaque;
+ XiveNVTClass *xnc = XIVE_NVT_GET_CLASS(nvt);
+
+ if (xnc->post_load) {
+ xnc->post_load(nvt, version_id);
+ }
+
+ return 0;
+}
+
static const VMStateDescription vmstate_xive_nvt = {
.name = TYPE_XIVE_NVT,
.version_id = 1,
.minimum_version_id = 1,
+ .pre_save = vmstate_xive_nvt_pre_save,
+ .post_load = vmstate_xive_nvt_post_load,
.fields = (VMStateField[]) {
VMSTATE_BUFFER(regs, XiveNVT),
VMSTATE_STRUCT_ARRAY(eqt, XiveNVT, (XIVE_PRIORITY_MAX + 1), 1,
@@ -470,6 +511,7 @@ static const TypeInfo xive_nvt_info = {
.instance_size = sizeof(XiveNVT),
.instance_init = xive_nvt_init,
.class_init = xive_nvt_class_init,
+ .class_size = sizeof(XiveNVTClass),
};
/*
@@ -819,8 +861,13 @@ static void xive_source_set_irq(void *opaque, int srcno,
int val)
void xive_source_pic_print_info(XiveSource *xsrc, Monitor *mon)
{
+ XiveSourceClass *xsc = XIVE_SOURCE_GET_CLASS(xsrc);
int i;
+ if (xsc->synchronize_state) {
+ xsc->synchronize_state(xsrc);
+ }
+
monitor_printf(mon, "XIVE Source %6x ..%6x\n",
xsrc->offset, xsrc->offset + xsrc->nr_irqs - 1);
for (i = 0; i < xsrc->nr_irqs; i++) {
@@ -840,6 +887,7 @@ void xive_source_pic_print_info(XiveSource *xsrc, Monitor
*mon)
static void xive_source_reset(DeviceState *dev)
{
XiveSource *xsrc = XIVE_SOURCE(dev);
+ XiveSourceClass *xsc = XIVE_SOURCE_GET_CLASS(xsrc);
int i;
/* Keep the IRQ type */
@@ -849,6 +897,10 @@ static void xive_source_reset(DeviceState *dev)
/* SBEs are initialized to 0b01 which corresponds to "ints off" */
memset(xsrc->sbe, 0x55, xsrc->sbe_size);
+
+ if (xsc->reset) {
+ xsc->reset(xsrc);
+ }
}
static void xive_source_realize(DeviceState *dev, Error **errp)
@@ -895,10 +947,36 @@ static void xive_source_realize(DeviceState *dev, Error
**errp)
sysbus_init_mmio(SYS_BUS_DEVICE(dev), &xsrc->esb_mmio);
}
+static int vmstate_xive_source_pre_save(void *opaque)
+{
+ XiveSource *xsrc = opaque;
+ XiveSourceClass *xsc = XIVE_SOURCE_GET_CLASS(xsrc);
+
+ if (xsc->pre_save) {
+ xsc->pre_save(xsrc);
+ }
+
+ return 0;
+}
+
+static int vmstate_xive_source_post_load(void *opaque, int version_id)
+{
+ XiveSource *xsrc = opaque;
+ XiveSourceClass *xsc = XIVE_SOURCE_GET_CLASS(xsrc);
+
+ if (xsc->post_load) {
+ xsc->post_load(xsrc, version_id);
+ }
+
+ return 0;
+}
+
static const VMStateDescription vmstate_xive_source = {
.name = TYPE_XIVE_SOURCE,
.version_id = 1,
.minimum_version_id = 1,
+ .pre_save = vmstate_xive_source_pre_save,
+ .post_load = vmstate_xive_source_post_load,
.fields = (VMStateField[]) {
VMSTATE_UINT32_EQUAL(nr_irqs, XiveSource, NULL),
VMSTATE_VBUFFER_UINT32(sbe, XiveSource, 1, NULL, sbe_size),
@@ -934,6 +1012,7 @@ static const TypeInfo xive_source_info = {
.parent = TYPE_SYS_BUS_DEVICE,
.instance_size = sizeof(XiveSource),
.class_init = xive_source_class_init,
+ .class_size = sizeof(XiveSourceClass),
};
static void xive_register_types(void)
diff --git a/include/hw/ppc/spapr_xive.h b/include/hw/ppc/spapr_xive.h
index df87e68b3d05..41e2784403b2 100644
--- a/include/hw/ppc/spapr_xive.h
+++ b/include/hw/ppc/spapr_xive.h
@@ -32,6 +32,19 @@ typedef struct sPAPRXive {
MemoryRegion tm_mmio_os;
} sPAPRXive;
+#define SPAPR_XIVE_CLASS(klass) \
+ OBJECT_CLASS_CHECK(sPAPRXiveClass, (klass), TYPE_SPAPR_XIVE)
+#define SPAPR_XIVE_GET_CLASS(obj) \
+ OBJECT_GET_CLASS(sPAPRXiveClass, (obj), TYPE_SPAPR_XIVE)
+
+typedef struct sPAPRXiveClass {
+ SysBusDeviceClass parent_class;
+
+ void (*synchronize_state)(sPAPRXive *xive);
+ void (*pre_save)(sPAPRXive *xsrc);
+ int (*post_load)(sPAPRXive *xsrc, int version_id);
+} sPAPRXiveClass;
+
bool spapr_xive_irq_enable(sPAPRXive *xive, uint32_t lisn, bool lsi);
bool spapr_xive_irq_disable(sPAPRXive *xive, uint32_t lisn);
void spapr_xive_pic_print_info(sPAPRXive *xive, Monitor *mon);
diff --git a/include/hw/ppc/xive.h b/include/hw/ppc/xive.h
index 24ce58812a7c..36de10af0109 100644
--- a/include/hw/ppc/xive.h
+++ b/include/hw/ppc/xive.h
@@ -60,6 +60,20 @@ typedef struct XiveSource {
XiveFabric *xive;
} XiveSource;
+#define XIVE_SOURCE_CLASS(klass) \
+ OBJECT_CLASS_CHECK(XiveSourceClass, (klass), TYPE_XIVE_SOURCE)
+#define XIVE_SOURCE_GET_CLASS(obj) \
+ OBJECT_GET_CLASS(XiveSourceClass, (obj), TYPE_XIVE_SOURCE)
+
+typedef struct XiveSourceClass {
+ SysBusDeviceClass parent_class;
+
+ void (*synchronize_state)(XiveSource *xsrc);
+ void (*reset)(XiveSource *xsrc);
+ void (*pre_save)(XiveSource *xsrc);
+ int (*post_load)(XiveSource *xsrc, int version_id);
+} XiveSourceClass;
+
/*
* ESB MMIO setting. Can be one page, for both source triggering and
* source management, or two different pages. See below for magic
@@ -186,6 +200,22 @@ typedef struct XiveNVT {
XiveEQ eqt[XIVE_PRIORITY_MAX + 1];
} XiveNVT;
+
+#define XIVE_NVT_CLASS(klass) \
+ OBJECT_CLASS_CHECK(XiveNVTClass, (klass), TYPE_XIVE_NVT)
+#define XIVE_NVT_GET_CLASS(obj) \
+ OBJECT_GET_CLASS(XiveNVTClass, (obj), TYPE_XIVE_NVT)
+
+typedef struct XiveNVTClass {
+ DeviceClass parent_class;
+
+ void (*realize)(XiveNVT *nvt, Error **errp);
+ void (*synchronize_state)(XiveNVT *nvt);
+ void (*reset)(XiveNVT *nvt);
+ void (*pre_save)(XiveNVT *nvt);
+ int (*post_load)(XiveNVT *nvt, int version_id);
+} XiveNVTClass;
+
extern const MemoryRegionOps xive_tm_user_ops;
extern const MemoryRegionOps xive_tm_os_ops;
--
2.13.6
- [Qemu-ppc] [PATCH v3 12/35] spapr: add a sPAPRXive object to the machine, (continued)
- [Qemu-ppc] [PATCH v3 12/35] spapr: add a sPAPRXive object to the machine, Cédric Le Goater, 2018/04/19
- [Qemu-ppc] [PATCH v3 14/35] spapr: add device tree support for the XIVE exploitation mode, Cédric Le Goater, 2018/04/19
- [Qemu-ppc] [PATCH v3 13/35] spapr: add hcalls support for the XIVE exploitation interrupt mode, Cédric Le Goater, 2018/04/19
- [Qemu-ppc] [PATCH v3 15/35] sysbus: add a sysbus_mmio_unmap() helper, Cédric Le Goater, 2018/04/19
- [Qemu-ppc] [PATCH v3 16/35] spapr: introduce a helper to map the XIVE memory regions, Cédric Le Goater, 2018/04/19
- [Qemu-ppc] [PATCH v3 17/35] spapr: add XIVE support to spapr_qirq(), Cédric Le Goater, 2018/04/19
- [Qemu-ppc] [PATCH v3 18/35] spapr: introduce a spapr_icp_create() helper, Cédric Le Goater, 2018/04/19
- [Qemu-ppc] [PATCH v3 19/35] spapr: toggle the ICP depending on the selected interrupt mode, Cédric Le Goater, 2018/04/19
- [Qemu-ppc] [PATCH v3 20/35] spapr: add support to dump XIVE information, Cédric Le Goater, 2018/04/19
- [Qemu-ppc] [PATCH v3 21/35] spapr: advertise XIVE exploitation mode in CAS, Cédric Le Goater, 2018/04/19
- [Qemu-ppc] [PATCH v3 22/35] spapr: add classes for the XIVE models,
Cédric Le Goater <=
- [Qemu-ppc] [PATCH v3 23/35] target/ppc/kvm: add Linux KVM definitions for XIVE, Cédric Le Goater, 2018/04/19
- [Qemu-ppc] [PATCH v3 24/35] spapr/xive: add common realize routine for KVM, Cédric Le Goater, 2018/04/19
- [Qemu-ppc] [PATCH v3 25/35] spapr/xive: add KVM support, Cédric Le Goater, 2018/04/19
- [Qemu-ppc] [PATCH v3 26/35] spapr/xive: add a XIVE KVM device to the machine, Cédric Le Goater, 2018/04/19
- [Qemu-ppc] [PATCH v3 27/35] migration: discard non-migratable RAMBlocks, Cédric Le Goater, 2018/04/19
- [Qemu-ppc] [PATCH v3 28/35] intc: introduce a CPUIntc interface, Cédric Le Goater, 2018/04/19
- [Qemu-ppc] [PATCH v3 29/35] spapr/xive, xics: use the CPU_INTC handlers to reset KVM, Cédric Le Goater, 2018/04/19
- [Qemu-ppc] [PATCH v3 30/35] spapr/xive, xics: reset KVM at machine reset, Cédric Le Goater, 2018/04/19
- [Qemu-ppc] [PATCH v3 31/35] spapr/xive: raise migration priority of the machine, Cédric Le Goater, 2018/04/19
- [Qemu-ppc] [PATCH v3 32/35] ppc/pnv: introduce a pnv_icp_create() helper, Cédric Le Goater, 2018/04/19