给定一个运行以下代码的微控制器:
volatile bool has_flag = false;
void interrupt(void) //called when an interrupt is received
{
    clear_interrupt_flag(); //clear interrupt flag
    has_flag = true; //signal that we have an interrupt to process
}
int main()
{
    while(1)
    {
        if(has_flag) //if we had an interrupt
        {
            has_flag = false; //clear the interrupt flag
            process(); //process the interrupt
        }
        else
            sleep(); //place the micro to sleep
    }
}
假设if(has_flag)条件评估为假,我们将执行睡眠指令。  右我们执行睡眠指令之前,我们接收中断。离开中断后,我们执行睡眠指令。  
此执行顺序是不理想的,因为:
- 微控制器进入睡眠状态,而不是唤醒并调用
process()。 - 如果此后未接收到中断,则微控制器可能永远不会唤醒。
 - 呼叫
process()被推迟到下一个中断为止。 
如何编写代码以防止发生这种竞争情况?
编辑
某些ATMega等微控制器具有休眠使能位,可以防止这种情况的发生(感谢Kvegaoro指出这一点)。JRoberts提供了一个示例实现来例证这种行为。
其他微控制器(如PIC18s)没有此位,问题仍然存在。但是,这些微控制器的设计使得无论是否设置了全局中断允许位,中断仍可以唤醒内核(感谢您的超级猫指出)。对于此类架构,解决方案是在进入睡眠之前禁用全局中断。如果恰好在执行睡眠指令之前触发了中断,则不会执行中断处理程序,内核将唤醒,并且一旦重新启用全局中断,就会执行中断处理程序。在伪代码中,实现如下所示:
int main()
{
    while(1)
    {
        //clear global interrupt enable bit.
        //if the flag tested below is not set, then we enter
        //sleep with the global interrupt bit cleared, which is
        //the intended behavior.
        disable_global_interrupts();
        if(has_flag) //if we had an interrupt
        {
            has_flag = false; //clear the interrupt flag
            enable_global_interrupts();  //set global interrupt enable bit.
            process(); //process the interrupt
        }
        else
            sleep(); //place the micro to sleep
    }
}
          interrupt_flag作为int,并在每次发生中断时将其递增。然后更改if(has_flag)为while (interrupts_count),然后进入睡眠状态。但是,退出while循环后可能会发生中断。如果这是一个问题,那么在中断本身中进行处理吗?