Nested interrupts in Embedded C - Step-by-Step Execution
volatile int flag1 = 0; volatile int flag2 = 0; void ISR1() { flag1 = 1; // Higher priority interrupt can occur here flag1 = 2; } void ISR2() { flag2 = 1; }
| Step | Event | Current Context | Action | Variable Changes |
|---|---|---|---|---|
| 1 | Main program running | Main | Running main code | flag1=0, flag2=0 |
| 2 | Interrupt 1 occurs | Main | Enter ISR1 | flag1=0, flag2=0 |
| 3 | ISR1 sets flag1=1 | ISR1 | flag1=1 | flag1=1, flag2=0 |
| 4 | Interrupt 2 occurs (higher priority) | ISR1 | Preempt ISR1, enter ISR2 | flag1=1, flag2=0 |
| 5 | ISR2 sets flag2=1 | ISR2 | flag2=1 | flag1=1, flag2=1 |
| 6 | ISR2 ends | ISR2 | Return to ISR1 | flag1=1, flag2=1 |
| 7 | ISR1 resumes, sets flag1=2 | ISR1 | flag1=2 | flag1=2, flag2=1 |
| 8 | ISR1 ends | ISR1 | Return to main | flag1=2, flag2=1 |
| 9 | Main program resumes | Main | Continue main code | flag1=2, flag2=1 |
| Variable | Start | After Step 3 | After Step 5 | After Step 7 | Final |
|---|---|---|---|---|---|
| flag1 | 0 | 1 | 1 | 2 | 2 |
| flag2 | 0 | 0 | 1 | 1 | 1 |
Nested interrupts allow higher priority interrupts to interrupt lower priority ones. The processor saves the current interrupt state before handling the higher priority one. After the higher priority ISR finishes, the previous ISR resumes. This ensures urgent tasks get immediate attention without losing progress on others. Variables keep their values during nested interrupts. Proper priority configuration is essential to avoid conflicts.
Practice
What is the main purpose of enabling nested interrupts in embedded C?
Solution
Step 1: Understand interrupt priority
Interrupts have priorities; higher priority interrupts can preempt lower priority ones if nesting is enabled.Step 2: Role of nested interrupts
Nested interrupts allow a higher priority interrupt to interrupt an ISR of a lower priority interrupt, improving responsiveness.Final Answer:
Allow higher priority interrupts to interrupt lower priority ISRs -> Option AQuick Check:
Nested interrupts = higher priority preempts lower priority [OK]
- Thinking nested interrupts disable all interrupts
- Assuming nested interrupts increase ISR execution time
- Believing nested interrupts prevent interrupts
Which of the following code snippets correctly enables nested interrupts inside an ISR in embedded C?
void ISR_Handler(void) {
// Enable global interrupts
__enable_irq();
// ISR code
}Solution
Step 1: Identify function to enable interrupts
In embedded C, __enable_irq() enables global interrupts, allowing nesting.Step 2: Confirm correct usage inside ISR
Calling __enable_irq() inside ISR allows higher priority interrupts to nest.Final Answer:
__enable_irq(); // enables global interrupts inside ISR -> Option DQuick Check:
__enable_irq() enables interrupts inside ISR [OK]
- Using __disable_irq() which disables interrupts
- Confusing cli() and sei() functions
- Not enabling interrupts inside ISR
Consider the following code snippet in embedded C where nested interrupts are enabled:
volatile int count = 0;
void ISR_LowPriority(void) {
__enable_irq();
for(int i = 0; i < 5; i++) {
count++;
}
}
void ISR_HighPriority(void) {
count += 10;
}
int main() {
// Assume interrupts are configured and enabled
while(1) {}
}If ISR_HighPriority interrupts ISR_LowPriority exactly once during the loop, what is the final value of count after ISR_LowPriority finishes?
Solution
Step 1: Analyze ISR_LowPriority increments
ISR_LowPriority increments count 5 times, so count increases by 5.Step 2: Account for ISR_HighPriority interrupt
ISR_HighPriority adds 10 to count during ISR_LowPriority execution.Step 3: Calculate final count
Count = 5 (from low priority) + 10 (from high priority) = 15.Final Answer:
15 -> Option CQuick Check:
5 + 10 = 15 [OK]
- Ignoring the interrupt during the loop
- Counting only one ISR's increments
- Assuming interrupts don't nest
Given the following ISR code, identify the error that prevents nested interrupts from working correctly:
void ISR_Handler(void) {
// ISR code
__disable_irq();
// Critical section
__enable_irq();
}Solution
Step 1: Understand effect of __disable_irq()
Calling __disable_irq() inside ISR disables global interrupts, blocking nesting.Step 2: Check interrupt enabling
Although __enable_irq() is called later, interrupts remain disabled during critical section, so nesting is blocked.Final Answer:
__disable_irq() disables interrupts inside ISR, preventing nesting -> Option AQuick Check:
Disabling interrupts inside ISR blocks nesting [OK]
- Thinking __disable_irq() enables interrupts
- Assuming __enable_irq() disables interrupts
- Believing ISR should never control interrupts
You have two interrupts: ISR_A with priority 1 and ISR_B with priority 2 (2 is higher). You want ISR_B to interrupt ISR_A when it occurs. Which of the following is the correct approach to implement nested interrupts in embedded C?
void ISR_A(void) {
// Enable nested interrupts
__enable_irq();
// ISR_A code
}
void ISR_B(void) {
// ISR_B code
}Solution
Step 1: Understand priority and nesting
Higher priority ISR_B (priority 2) should interrupt lower priority ISR_A (priority 1).Step 2: Enable nested interrupts inside ISR_A
Calling __enable_irq() inside ISR_A allows ISR_B to interrupt ISR_A.Step 3: Avoid disabling interrupts or wrong priority settings
Disabling interrupts or reversing priorities prevents correct nesting.Final Answer:
Enable global interrupts inside ISR_A using __enable_irq() to allow ISR_B nesting -> Option BQuick Check:
Enable interrupts inside lower priority ISR for nesting [OK]
- Disabling interrupts inside ISR_A
- Manually calling ISR_B instead of nesting
- Setting wrong priority order
Ready to prove it?
Pass the test and this pattern moves unknown
