Improve wait for interrupt routines
This commit is contained in:
parent
02ce96eed8
commit
5f44f8df98
Binary file not shown.
|
@ -45,36 +45,34 @@ void configure_irq(size_t irq_num, function_ptr_t handler, unsigned char prio=1)
|
||||||
}
|
}
|
||||||
|
|
||||||
void wait_for_spn1_interrupt() {
|
void wait_for_spn1_interrupt() {
|
||||||
clear_csr(mie, MIP_MEIP);
|
// This is a time critical part. It must be ensured that no interrupt is processed between flag checking and wfi.
|
||||||
|
// Disable interrupts and wait a few more clocks for the instruction to take effect before checking the flag.
|
||||||
|
asm volatile ("csrrc x0, mie, %0; nop; nop" : : "r"(MIP_MEIP));
|
||||||
while(spn1_hw_interrupt) {
|
while(spn1_hw_interrupt) {
|
||||||
set_csr(mie, MIP_MEIP);
|
// Enable interrupts and immediately enter wfi.
|
||||||
asm("wfi");
|
asm volatile ("csrrs x0, mie, %0; wfi; nop" : : "r"(MIP_MEIP));
|
||||||
clear_csr(mie, MIP_MEIP);
|
// Disable interrupts again before examine the flag value.
|
||||||
asm("nop");
|
asm volatile ("csrrc x0, mie, %0; nop; nop" : : "r"(MIP_MEIP));
|
||||||
}
|
}
|
||||||
spn1_hw_interrupt=true;
|
spn1_hw_interrupt=true;
|
||||||
set_csr(mie, MIP_MEIP);
|
set_csr(mie, MIP_MEIP);
|
||||||
}
|
}
|
||||||
|
|
||||||
void wait_for_spn2_interrupt() {
|
void wait_for_spn2_interrupt() {
|
||||||
clear_csr(mie, MIP_MEIP);
|
asm volatile ("csrrc x0, mie, %0; nop; nop" : : "r"(MIP_MEIP));
|
||||||
while(spn2_hw_interrupt) {
|
while(spn2_hw_interrupt) {
|
||||||
set_csr(mie, MIP_MEIP);
|
asm volatile ("csrrs x0, mie, %0; wfi; nop" : : "r"(MIP_MEIP));
|
||||||
asm("wfi");
|
asm volatile ("csrrc x0, mie, %0; nop; nop" : : "r"(MIP_MEIP));
|
||||||
clear_csr(mie, MIP_MEIP);
|
|
||||||
asm("nop");
|
|
||||||
}
|
}
|
||||||
spn2_hw_interrupt=true;
|
spn2_hw_interrupt=true;
|
||||||
set_csr(mie, MIP_MEIP);
|
set_csr(mie, MIP_MEIP);
|
||||||
}
|
}
|
||||||
|
|
||||||
void wait_for_spn_interrupts() {
|
void wait_for_spn_interrupts() {
|
||||||
clear_csr(mie, MIP_MEIP);
|
asm volatile ("csrrc x0, mie, %0; nop; nop" : : "r"(MIP_MEIP));
|
||||||
while(spn1_hw_interrupt || spn2_hw_interrupt) {
|
while(spn1_hw_interrupt || spn2_hw_interrupt) {
|
||||||
set_csr(mie, MIP_MEIP);
|
asm volatile ("csrrs x0, mie, %0; wfi; nop" : : "r"(MIP_MEIP));
|
||||||
asm("wfi");
|
asm volatile ("csrrc x0, mie, %0; nop; nop" : : "r"(MIP_MEIP));
|
||||||
asm("nop");
|
|
||||||
clear_csr(mie, MIP_MEIP);
|
|
||||||
}
|
}
|
||||||
spn1_hw_interrupt=true;
|
spn1_hw_interrupt=true;
|
||||||
spn2_hw_interrupt=true;
|
spn2_hw_interrupt=true;
|
||||||
|
|
Loading…
Reference in New Issue