2

我正在阅读有关如何在 ARM 中处理中断的信息,并且知道每当有任何硬件中断出现在地址 0x00000018 处的指令被执行时,这通常是跳转到受尊重的中断处理程序,但不同模块可能有许多中断处理程序。

那么,这些不同的处理程序是如何映射到地址 0x00000018 的呢?

此外,arm cpu 如何知道中断引发是 irq 或 fiq,谁来决定它以及哪个设备引发了中断,如何映射到该中断的相关处理程序。

任何人都可以将我指向一个简单的中断处理程序代码,我可以在其中看到所有中断处理程序的作用吗?

4

2 回答 2

5

ARM CPU 通常有两个引脚(FIQ 和 IRQ),当设备想要生成中断时,它们会被置位。发生这种情况时,CPU 只需切换模式并跳转到 address 0x00000018

但是,由于设备数量通常多于中断引脚的数量,因此通常在 CPU 和设备之间有一个中断控制器。您可以将其视为将更多中断连接到 CPU 的集线器。中断控制器可以配置为针对它接收到的某些类型的中断断言 FIQ。

中断处理程序通常询问中断控制器是哪个引脚引起了中断,然后调用适当的处理程序。

这是一个精简版本,没有对我在一个小项目中使用的中断处理程序代码进行错误检查。

#include <types.h>
#include <irq.h>

static void (*irq_handlers[32])(void);

void __attribute__((interrupt)) handle_irq() {
    int irq = irq_hw_get_and_ack();

    if (irq_handlers[irq]) {
        irq_handlers[irq]();
    }
}

void setup_irq() {
    irq_hw_init();
    cpu_enable_irq();
}

void irq_request(int irq, void (*func)(void)) {
    irq_handlers[irq] = func;
    irq_hw_enable(irq);
}

void irq_unrequest(int irq) {
    irq_hw_disable(irq);
    irq_handlers[irq] = NULL;
}
于 2013-11-09T23:52:29.697 回答
2

处理器只有一个中断是相当典型的。x86 有一段时间是这样的,也许现在仍然如此。Arm 传统上有两个,但较新的内核现在有很多,32、256 等。

在你有共享中断线的地方,正如 tangrs 所提到的,你通常在处理器之外有一些东西,在 arm 的情况下,在芯片内部但在 arm 核心本身之外。确实有许多中断输入和输出到处理器的一个或几个中断的东西。当处理器中断发生时,您可以检查处理器/内核之外的这个逻辑/硬件,看看是谁造成的,然后就可以了。

嵌套中断控制器也不是非典型的,例如一个 8 输入和一个输出。对于这 8 个输入中的一些或每个输入,另一个 8 对 1 中断控制器。然后,软件将需要简单地遵循路径。检查第一级中断控制器以查看哪个(S)触发了中断,然后从那里你知道你需要与之交谈的下一层控制器等等,直到你隔离单个中断。

还知道并理解,对于这些共享中断系统,基本上从您的程序开始停止并调用中断向量的时间开始,很有可能“同时”发生多个中断,然后您执行中断启动工作并最终读取中断状态寄存器,不止一个可以进入。您需要决定如何处理它,并且取决于系统/逻辑,如果您要从其中一个返回,其他被断言的可能会将您带回中断处理程序,因此实施将/可能仅处理其中一个待处理。其他逻辑可能要求您在返回之前处理所有待处理的事务。

由于 arm 不一定控制与中断或 fiq 线相关的内容,因此您可以从不同的供应商处获得各种解决方案,了解中断系统如何适用于特定的 arm 芯片。

于 2013-11-10T05:52:14.060 回答