2010-12-07 128 views
2

传递ARGS考虑我们正在编写固件的baremetal MCU,即没有操作系统。我被告知它不可能(非法?)将参数传递给中断处理函数?在中断处理程序

我无法准确理解为什么是这样吗?这有什么问题?

PS。是否有可能在某些RTOS-es,嵌入式Linux等中使用,或者它从根本上错误?

回答

3

唯一的其他东西我会指出(尚未到目前为止提到)是一个“软件中断”的概念(有时称为“陷阱”),其中大部分处理器的支持。

的想法是,一个特殊的指令导致异常发生,并经常与软件中断,无论是操作码导致异常,或登记成立前的异常,可以包含值/参数。

例如,在ARM处理器中,根据您的体系结构查找“SWI”或“SVC”。我相信随着SWI指令,低8位不是操作码的一部分 - 你可以填写任何你想要的值0-255(这里的内存有点模糊)。

不同于硬件启动中断,这是完全异步的CPU上运行的代码,软件中断是同步的 - 它在执行启动指令时(禁止中断屏蔽,嵌套等)

3

中断处理程序是由硬件调用。无论硬件通过它的“参数”是“通过”。

就是这样。

4

没有参数可以明确地传递给中断处理程序,因为它的设计是由硬件来调用。每个体系结构在调用时会施加特定的堆栈帧,通常包括CPU的已保存状态。

如果您还打算从代码中的其他地方调用中断处理程序,那么您有一个设计缺陷,或者有一些可能被分解出来以便在中断处理程序和算法代码之间共享的代码。

+0

感谢您的答复。如果我理解你的话,最重要的是IRQ处理程序与程序流异步调用,编译器在传递参数时不知道*何时。 – Mark 2010-12-07 03:40:18

4

中断。做那个......中断。想象一下家中的门铃,在任何特定的随机时间白天或晚上打断你。您是否可以期望在任何时候都可以在您的手中拥有所有可能发生的特定中断的正确项目。您必须能够烹饪晚餐,洗澡,折叠衣物,但是在门铃响起之前,您必须根据敲响铃声的人准确掌握正确的物品,而无需知道它们在那里,或者即将或即将响起的钟声。不太可能。同样的处理,中断在任何特定时间发生,对于大多数处理器在当前正在执行的指令之后立即调用中断处理程序,这意味着每一条指令都必须尝试执行前台应用程序,同时保留中断的所有参数处理程序,并在一个指令时间内完成所有这些操作。

现在是什么是可能与操作系统或RTOS或者叫什么你会,一些层。为了让真正的中断处理程序知道什么都没有进入并且必须弄清楚,一旦它发现中断将收集信息,然后调用传递参数的高级中断处理程序。当然可能和大多数/多种操作系统都是这样做的。

+0

很好的例子!最佳答案。换句话说:在裸机硬件层面上,没有参数,没有返回值等。在Linux {和其他RTOSes}平台上,有一个“中断驱动程序”(所有中断使用的通用代码)该驱动程序( 1)通常读取硬件寄存器以确定发生了哪个中断,(2)将该数字用作索引软件在表格中查找以查找处理函数和可能的参数。相反,微芯片RTOS(Cortex M3)在硬件上做了一些不同的事情,硬件为每个中断调用不同的功能 – user3696153 2014-06-14 04:46:56

0
发生

当你使用下面的调用设置中断处理程序时,它看起来像中断处理程序需要一些参数并返回irqreturn_t。这是不是中断处理程序OP在说什么?

int request_irq(unsigned int irq, 
       irqreturn_t (*handler)(int, void *, struct pt_regs *), 
       unsigned long flags, 
       const char *dev_name, 
       void *dev_id); 
0

可以使用共享变量正常码流期间设置影响下一次它运行的中断处理程序的行为。但是因为你不直接调用ISR,所以你不能传递参数。这不是合法性问题,而是技术性问题。

如:

volatile enum 
{ 
    DO_NOTHING, 
    DO_A, 
    DO_B, 
    DO_C 

} isr_action ; 

__interrupt (SOME_IRQ) myISR() 
{ 
    switch isr_action 
    { 
     case DO_A : 
     { 
      // A 
     } 
     break ; 

     case DO_B : 
     { 
      // B 
     } 
     break ; 

     case DO_C : 
     { 
      // C 
     } 
     break ; 
    } 
} 

int main() 
{ 
    // Make ISR do A on next SOME_IRQ 
    isr_action = DO_A ; 

    for(;;) 
    { 
     // wait for interrupt 
    } 
} 
相关问题