[Skiboot] [PATCH v2 05/11] xive/p9: Clarify the escalation IRQ encoding

Cédric Le Goater clg at kaod.org
Fri Jun 12 21:37:26 AEST 2020

When an interrupt can not be delivered, an escalation interrupt can be
triggered. The EQ descriptor of the pending interrupt should be
configured to generate an escalation event, using the EQ_W0_ESCALATE_CTL
'e' bit, and words 4 and 5 of the EQ descriptor should contain an IVE
pointing to the escalation EQ to trigger. This is why EQ descriptors
are considered as interrupt sources and registered as such when
initializing the interrupt controller.

These interrupts are identified as escalations by the OPAL XIVE
interface, OPAL calls and internal routines, by setting a special bit
in their global interrupt number. Clarify that and check that the
number of EQ descriptors is not overflowing the global interrupt

Reviewed-by: Gustavo Romero <gromero at linux.ibm.com>
Signed-off-by: Cédric Le Goater <clg at kaod.org>
 hw/xive.c | 13 +++++++++----
 1 file changed, 9 insertions(+), 4 deletions(-)

diff --git a/hw/xive.c b/hw/xive.c
index 5a6d56323a7e..3e7b87fdfd17 100644
--- a/hw/xive.c
+++ b/hw/xive.c
@@ -497,8 +497,8 @@ static uint32_t xive_chip_to_block(uint32_t chip_id)
  *      8      4           20
  * the E bit indicates that this is an escalation interrupt, in
- * that case, the BLOC/INDEX represents the EQ containig the
- * corresponding escalation descriptor.
+ * that case, the BLOCK/INDEX points to the EQ descriptor associated
+ * with the escalation.
  * Global interrupt numbers for non-escalation interrupts are thus
  * limited to 24 bits because the XICS emulation encodes the CPPR
@@ -507,16 +507,21 @@ static uint32_t xive_chip_to_block(uint32_t chip_id)
  * number.
 #define INT_SHIFT		20
+#define INT_ESC_SHIFT		(INT_SHIFT + 4) /* 4bits block id */
 #error "Too many ESBs for IRQ encoding"
+#error "Too many EQs for escalation IRQ number encoding"
 #define GIRQ_TO_BLK(__g)	(((__g) >> INT_SHIFT) & 0xf)
 #define GIRQ_TO_IDX(__g)	((__g) & ((1 << INT_SHIFT) - 1))
 #define BLKIDX_TO_GIRQ(__b,__i)	(((uint32_t)(__b)) << INT_SHIFT | (__i))
-#define GIRQ_IS_ESCALATION(__g)	((__g) & 0x01000000)
-#define MAKE_ESCALATION_GIRQ(__b,__i)(BLKIDX_TO_GIRQ(__b,__i) | 0x01000000)
+#define GIRQ_IS_ESCALATION(__g)	((__g) & (1 << INT_ESC_SHIFT))
+#define MAKE_ESCALATION_GIRQ(__b,__i)(BLKIDX_TO_GIRQ(__b,__i) | (1 << INT_ESC_SHIFT))
 /* Block/IRQ to chip# conversions */
 #define PC_BLK_TO_CHIP(__b)	(xive_block_to_chip[__b])

More information about the Skiboot mailing list