在中断服务程序中,如果出现过早的“return”会发生什么?

11

我正在使用AVR-GCC 4.9.2,我想知道在AVR上的ISR中如果发生早期返回会发生什么?

ISR(USART_RXC_vect)
{
    ...
    if(idx == BUFSIZE)
        return;
    ...
 }

在汇编中,return会被翻译成ret指令吗?还是我需要自己加上reti()指令?

我想要了解背后发生的详细情况。

1个回答

9
正如
ISR(USART_RXC_vect)
不是字面意义上的
USART_INTERUPT_VECTOR:
在汇编中,

return;
不是字面意义上的
ret
或者
reti
在汇编中。

在C/C++中,这两个指令将被翻译成多个汇编语句,而且在两种情况下,它们的解释都取决于上下文。在这种情况下,ISR(){}的上下文相当单一,但它很可能也包括一些推送和存储SREG。但是堆栈中推送的数量将取决于函数中发生的事情。

因此,任何return;都将在上下文中进行解释。在实际构建为子程序的普通子例程的结尾处(出于代码效率原因,许多有限用途的子例程会被编译器“内联”),它将变成一个ret指令(在处理任何所需的POP和其他低级清理之后)。在中断结束时,它实际上将意味着“弹出您之前推送的所有内容(并还原SREG),然后reti”。

当您返回将被编译成通过平台系统传输该值的类型时,需要在包括ret指令之前进行。因此,return;是一个非常上下文敏感的语句,您可以假设它会被正确解释,除非您做了非常奇怪的事情。但这些奇怪的事情至少会被像AVR-GCC这样的好编译器警告。


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接