bsp/qoriq: Ignore spurious interrupts

For example, with edge triggered external interrupts we may see spurious
interrupts.   Ignore them instead of issuing a fatal error.

Use eieio to synchronize access to the IACK and EOI registers.

Use a loop to immediately services the next pending interrupt without
having to go through the exception epiloge and prologue.

Close #5173.
This commit is contained in:
Sebastian Huber
2024-12-05 10:52:15 +01:00
committed by Gedare Bloom
parent e36ba91110
commit e421c922a8

View File

@@ -9,7 +9,7 @@
*/ */
/* /*
* Copyright (C) 2010, 2017 embedded brains GmbH & Co. KG * Copyright (C) 2010, 2024 embedded brains GmbH & Co. KG
* *
* Redistribution and use in source and binary forms, with or without * Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions * modification, are permitted provided that the following conditions
@@ -162,8 +162,6 @@ rtems_status_code bsp_interrupt_vector_disable(rtems_vector_number vector)
void bsp_interrupt_dispatch(uintptr_t exception_number) void bsp_interrupt_dispatch(uintptr_t exception_number)
{ {
unsigned int vector;
if (exception_number == 10) { if (exception_number == 10) {
qoriq_decrementer_dispatch(); qoriq_decrementer_dispatch();
return; return;
@@ -176,22 +174,25 @@ void bsp_interrupt_dispatch(uintptr_t exception_number)
} }
#endif #endif
/* while (true) {
* This works only if the "has-external-proxy" property is present in the unsigned int vector;
* "epapr,hv-pic" device tree node.
*/
PPC_SPECIAL_PURPOSE_REGISTER(FSL_EIS_EPR, vector);
if (vector != SPURIOUS) {
uint32_t msr; uint32_t msr;
/*
* This works only if the "has-external-proxy" property is present in the
* "epapr,hv-pic" device tree node.
*/
PPC_SPECIAL_PURPOSE_REGISTER(FSL_EIS_EPR, vector);
if (vector == SPURIOUS) {
return;
}
msr = ppc_external_exceptions_enable(); msr = ppc_external_exceptions_enable();
bsp_interrupt_handler_dispatch(vector); bsp_interrupt_handler_dispatch(vector);
ppc_external_exceptions_disable(msr); ppc_external_exceptions_disable(msr);
ev_int_eoi(vector); ev_int_eoi(vector);
} else {
bsp_interrupt_handler_default(vector);
} }
} }
@@ -586,19 +587,20 @@ rtems_status_code bsp_interrupt_vector_disable(rtems_vector_number vector)
void bsp_interrupt_dispatch(uintptr_t exception_number) void bsp_interrupt_dispatch(uintptr_t exception_number)
{ {
rtems_vector_number vector = qoriq.pic.iack; while (true) {
rtems_vector_number vector = qoriq.pic.iack;
uint32_t msr;
if (vector != SPURIOUS) { if (vector == SPURIOUS) {
uint32_t msr = ppc_external_exceptions_enable(); return;
}
msr = ppc_external_exceptions_enable();
bsp_interrupt_handler_dispatch(vector); bsp_interrupt_handler_dispatch(vector);
ppc_external_exceptions_disable(msr); ppc_external_exceptions_disable(msr);
qoriq.pic.eoi = 0; qoriq.pic.eoi = 0;
qoriq.pic.whoami; ppc_enforce_in_order_execution_of_io();
} else {
bsp_interrupt_handler_default(vector);
} }
} }