]> rtime.felk.cvut.cz Git - arc.git/commitdiff
Fixed nested interrupts problem for Cortex R4.
authormaek <devnull@localhost>
Mon, 6 Dec 2010 13:26:09 +0000 (14:26 +0100)
committermaek <devnull@localhost>
Mon, 6 Dec 2010 13:26:09 +0000 (14:26 +0100)
arch/arm/arm_cr4/kernel/irq.c
arch/arm/arm_cr4/kernel/irq_types.h

index e9e0a798f060af96aa3707e7ef8871c98cc40ae2..2c8008dd2cf166bb735eacabb0ca5334b1a1d065 100644 (file)
@@ -46,31 +46,38 @@ void *Irq_Entry( void *stack_p )
 {
        uint32_t *stack;
 
-       // Get the active interrupt channel
+       // This is the current hardware interrupt channel that we are processing.
        volatile sint8 channel;
+
+       // This is the current OS-interrupt vector that we are processing.
+       volatile sint8 virtualChannel;
+
+       // Get the highest pending interrupt.
        volatile uint32 c = 0;
        do {
                channel = IrqGetCurrentInterruptSource();
                c++;
        } while (channel < 0 && c < MAX_WAIT_COUNT);
 
-       if (c > 1) {
-               uint8 a = c;
-       }
-
        if (c >= MAX_WAIT_COUNT) {
                // No interrupt is pending
                return stack_p;
        }
 
+       // In most cases the OS-channel is the same as the hardware channel.
+       virtualChannel = channel;
+
        // Special case for software interrupts.
        if (channel == SSI) {
                // Get the emulated interrupt channel.
-               channel = systemREG1->SSISR1;
+               virtualChannel = systemREG1->SSISR1;
        }
 
        stack = (uint32_t *)stack_p;
-       stack = Os_Isr(stack, (void *)Irq_VectorTable[channel]);
+       struct OsPcb * pcb = (struct OsPcb *)Irq_VectorTable[virtualChannel];
+       // Save the hardware channel in the PCB, so that Os_Isr knows which interrupt channel to deactivate.
+       pcb->vector = channel;
+       stack = Os_Isr(stack, (void *)pcb);
 
        //Irq_Enable();
        return stack;
index 28569a6883121dd5feb6ab27c355c70c04ec259a..8f84ce713672128f4ff908e6f83d105bb96063c8 100644 (file)
 \r
 \r
 #define Irq_SOI() \\r
-       sint8 channel = IrqGetCurrentInterruptSource(); \\r
-       IrqDeactivateChannel(channel)\r
+       IrqDeactivateChannel(isrPtr->vector)\r
 \r
 \r
 #define Irq_EOI() \\r
-       IrqActivateChannel(channel)\r
+       IrqActivateChannel(isrPtr->vector)\r
 \r
 \r
 typedef enum {\r