[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
[Qemu-ppc] [PATCH 09/25] spapr: introduce handlers for XIVE interrupt so
From: |
Cédric Le Goater |
Subject: |
[Qemu-ppc] [PATCH 09/25] spapr: introduce handlers for XIVE interrupt sources |
Date: |
Thu, 23 Nov 2017 14:29:39 +0100 |
These are very similar to the XICS handlers in a simpler form. They make
use of a status array for the LSI interrupts. The spapr_xive_irq() routine
in charge of triggering the CPU interrupt line will be filled later on.
Signed-off-by: Cédric Le Goater <address@hidden>
---
hw/intc/spapr_xive.c | 55 +++++++++++++++++++++++++++++++++++++++++++--
include/hw/ppc/spapr_xive.h | 14 +++++++++++-
2 files changed, 66 insertions(+), 3 deletions(-)
diff --git a/hw/intc/spapr_xive.c b/hw/intc/spapr_xive.c
index b2fc3007c85f..66c533fb1d78 100644
--- a/hw/intc/spapr_xive.c
+++ b/hw/intc/spapr_xive.c
@@ -26,6 +26,47 @@
#include "xive-internal.h"
+static void spapr_xive_irq(sPAPRXive *xive, int lisn)
+{
+
+}
+
+/*
+ * XIVE Interrupt Source
+ */
+static void spapr_xive_source_set_irq_msi(sPAPRXive *xive, int lisn, int val)
+{
+ if (val) {
+ spapr_xive_irq(xive, lisn);
+ }
+}
+
+static void spapr_xive_source_set_irq_lsi(sPAPRXive *xive, int lisn, int val)
+{
+ if (val) {
+ xive->status[lisn] |= XIVE_STATUS_ASSERTED;
+ } else {
+ xive->status[lisn] &= ~XIVE_STATUS_ASSERTED;
+ }
+
+ if (xive->status[lisn] & XIVE_STATUS_ASSERTED &&
+ !(xive->status[lisn] & XIVE_STATUS_SENT)) {
+ xive->status[lisn] |= XIVE_STATUS_SENT;
+ spapr_xive_irq(xive, lisn);
+ }
+}
+
+static void spapr_xive_source_set_irq(void *opaque, int lisn, int val)
+{
+ sPAPRXive *xive = SPAPR_XIVE(opaque);
+
+ if (spapr_xive_irq_is_lsi(xive, lisn)) {
+ spapr_xive_source_set_irq_lsi(xive, lisn, val);
+ } else {
+ spapr_xive_source_set_irq_msi(xive, lisn, val);
+ }
+}
+
/*
* Main XIVE object
*/
@@ -41,7 +82,8 @@ void spapr_xive_pic_print_info(sPAPRXive *xive, Monitor *mon)
continue;
}
- monitor_printf(mon, " %4x %s %08x %08x\n", i,
+ monitor_printf(mon, " %4x %s %s %08x %08x\n", i,
+ spapr_xive_irq_is_lsi(xive, i) ? "LSI" : "MSI",
ive->w & IVE_MASKED ? "M" : " ",
(int) GETFIELD(IVE_EQ_INDEX, ive->w),
(int) GETFIELD(IVE_EQ_DATA, ive->w));
@@ -53,6 +95,8 @@ void spapr_xive_reset(void *dev)
sPAPRXive *xive = SPAPR_XIVE(dev);
int i;
+ /* Do not clear IRQs status */
+
/* Mask all valid IVEs in the IRQ number space. */
for (i = 0; i < xive->nr_irqs; i++) {
XiveIVE *ive = &xive->ivt[i];
@@ -71,6 +115,11 @@ static void spapr_xive_realize(DeviceState *dev, Error
**errp)
return;
}
+ /* QEMU IRQs */
+ xive->qirqs = qemu_allocate_irqs(spapr_xive_source_set_irq, xive,
+ xive->nr_irqs);
+ xive->status = g_malloc0(xive->nr_irqs);
+
/* Allocate the IVT (Interrupt Virtualization Table) */
xive->ivt = g_malloc0(xive->nr_irqs * sizeof(XiveIVE));
@@ -102,6 +151,7 @@ static const VMStateDescription vmstate_spapr_xive = {
VMSTATE_UINT32_EQUAL(nr_irqs, sPAPRXive, NULL),
VMSTATE_STRUCT_VARRAY_UINT32_ALLOC(ivt, sPAPRXive, nr_irqs, 1,
vmstate_spapr_xive_ive, XiveIVE),
+ VMSTATE_VBUFFER_UINT32(status, sPAPRXive, 1, NULL, nr_irqs),
VMSTATE_END_OF_LIST()
},
};
@@ -140,7 +190,7 @@ XiveIVE *spapr_xive_get_ive(sPAPRXive *xive, uint32_t lisn)
return lisn < xive->nr_irqs ? &xive->ivt[lisn] : NULL;
}
-bool spapr_xive_irq_set(sPAPRXive *xive, uint32_t lisn)
+bool spapr_xive_irq_set(sPAPRXive *xive, uint32_t lisn, bool lsi)
{
XiveIVE *ive = spapr_xive_get_ive(xive, lisn);
@@ -149,6 +199,7 @@ bool spapr_xive_irq_set(sPAPRXive *xive, uint32_t lisn)
}
ive->w |= IVE_VALID;
+ xive->status[lisn] |= lsi ? XIVE_STATUS_LSI : 0;
return true;
}
diff --git a/include/hw/ppc/spapr_xive.h b/include/hw/ppc/spapr_xive.h
index 795b3f4ded7c..6a799cdaba66 100644
--- a/include/hw/ppc/spapr_xive.h
+++ b/include/hw/ppc/spapr_xive.h
@@ -33,11 +33,23 @@ struct sPAPRXive {
/* Properties */
uint32_t nr_irqs;
+ /* IRQ */
+ qemu_irq *qirqs;
+#define XIVE_STATUS_LSI 0x1
+#define XIVE_STATUS_ASSERTED 0x2
+#define XIVE_STATUS_SENT 0x4
+ uint8_t *status;
+
/* XIVE internal tables */
XiveIVE *ivt;
};
-bool spapr_xive_irq_set(sPAPRXive *xive, uint32_t lisn);
+static inline bool spapr_xive_irq_is_lsi(sPAPRXive *xive, int lisn)
+{
+ return xive->status[lisn] & XIVE_STATUS_LSI;
+}
+
+bool spapr_xive_irq_set(sPAPRXive *xive, uint32_t lisn, bool lsi);
bool spapr_xive_irq_unset(sPAPRXive *xive, uint32_t lisn);
void spapr_xive_pic_print_info(sPAPRXive *xive, Monitor *mon);
--
2.13.6
[Qemu-ppc] [PATCH 09/25] spapr: introduce handlers for XIVE interrupt sources,
Cédric Le Goater <=
[Qemu-ppc] [PATCH 10/25] spapr: add MMIO handlers for the XIVE interrupt sources, Cédric Le Goater, 2017/11/23
- Re: [Qemu-ppc] [PATCH 10/25] spapr: add MMIO handlers for the XIVE interrupt sources, David Gibson, 2017/11/28
- Re: [Qemu-ppc] [PATCH 10/25] spapr: add MMIO handlers for the XIVE interrupt sources, Cédric Le Goater, 2017/11/28
- Re: [Qemu-ppc] [PATCH 10/25] spapr: add MMIO handlers for the XIVE interrupt sources, David Gibson, 2017/11/29
- Re: [Qemu-ppc] [PATCH 10/25] spapr: add MMIO handlers for the XIVE interrupt sources, Cédric Le Goater, 2017/11/29
- Re: [Qemu-ppc] [PATCH 10/25] spapr: add MMIO handlers for the XIVE interrupt sources, Cédric Le Goater, 2017/11/29
- Re: [Qemu-ppc] [PATCH 10/25] spapr: add MMIO handlers for the XIVE interrupt sources, David Gibson, 2017/11/30
- Re: [Qemu-ppc] [PATCH 10/25] spapr: add MMIO handlers for the XIVE interrupt sources, Cédric Le Goater, 2017/11/30