ARM Linux 嵌入式中断全流程解析:从 GPIO 到 GIC 架构实战

本文基于 Cortex-A 系列处理器(imx6ull/Cortex-A7/A53)整理,覆盖中断处理全流程、GIC 架构演进、CP15 协处理器操作、底层汇编指令,适合嵌入式 Linux / 裸机开发入门与复习。


一、中断处理的 6 个标准步骤

ARM 体系中,一个完整的中断流程如下:

  1. 中断源发出中断请求

    • 如 GPIO 按键、定时器、UART 等外设触发
  2. CPU 检查是否响应中断 & 是否被屏蔽

    • 检查 CPSR 中的 I/F 位
  3. 比较中断优先级

    • 由 GIC(通用中断控制器)仲裁
  4. 保护现场

    • 保存 CPSR、LR,压栈寄存器
  5. 执行中断服务函数(ISR)

  6. 恢复现场

    • 出栈,返回被中断的程序继续执行

二、GIC 架构与版本演进

GIC(Generic Interrupt Controller)是 ARM 官方定义的中断控制器标准。

1️⃣ GIC 版本对比

GIC 版本 适用处理器 典型场景
GIC v1 Cortex-A5 早期 32 位嵌入式
GIC v2 Cortex-A7(32 位) imx6ull、树莓派等
GIC v3/v4 Cortex-A53(64 位) 手机 SoC
GIC v5 重架构,支持数百核 服务器 / 高性能计算

👉 imx6ull 实际支持 160 个中断号(0--159)


三、GIC 中断类型详解

GIC 将中断分为三类:

中断类型 缩写 中断号范围 说明
软件中断 SGI 0 -- 15 CPU 核间通信
私有外设中断 PPI 16 -- 31 每个核独享
共享外设中断 SPI 32 -- 1019 GPIO、UART、Timer 等

我们常用的 GPIO 中断属于 SPI


四、CP15 协处理器与 GIC 基地址

ARM 中很多系统控制功能都通过 CP15 协处理器完成。

1️⃣ 常用指令

复制代码
mrc p15, 0, Rt, CRn, CRm, opc2   ; 读 CP15 寄存器
mcr p15, 0, Rt, CRn, CRm, opc2   ; 写 CP15 寄存器

2️⃣ 读取 GIC 基地址(CBAR)

复制代码
mrc p15, 4, r1, c15, c0, 0   ; 读取 CBAR,得到 GIC 基地址到 r1

五、中断关键寄存器

GIC 接口中有两个非常关键的寄存器:

复制代码
uint32_t ICC_IAR;   /* Offset: 0x200C (R)  中断应答寄存器 */
uint32_t ICC_EOIR;  /* Offset: 0x2010 (W)  中断结束寄存器 */
  • ICC_IAR:CPU 读取后,表示"我知道这个中断了"

  • ICC_EOIR:CPU 写入后,表示"中断处理完毕"

⚠️ 两者缺一不可,否则中断会一直挂起。


六、开关中断与控制指令

1️⃣ cps 指令(最常用)

复制代码
cpsie i     ; 使能 IRQ 中断
cpsid i     ; 关闭 IRQ 中断
标志 含义
I IRQ 中断
F FIQ 快速中断

2️⃣ SCTLR 控制示例

复制代码
mrc p15, 0, r0, c1, c0, 0      ; 读 SCTLR
bic r0, r0, #(1 << 13)
orr r0, r0, #(1 << 12)
mcr p15, 0, r0, c1, c0, 0      ; 写回 SCTLR

七、GPIO 中断实战示例(Key0:GPIO1_18)

GPIO1_18 按键中断为例,典型流程如下:

  1. 配置 GPIO 为中断模式

  2. 设置触发方式(下降沿 / 上升沿)

  3. 使能 GPIO 中断

  4. 在 GIC 中使能对应 SPI 中断

  5. 设置中断优先级

  6. ISR 中读取 ICC_IAR

  7. 清除中断标志

  8. ICC_EOIR 结束中断

📌 GPIO → GIC → CPU 内核​ 是标准的硬件中断链路。


八、完整中断调用链总结

复制代码
外设中断(GPIO/UART/Timer)
        ↓
       GIC(SPI/PPI/SGI)
        ↓
    CPU(IRQ/FIQ)
        ↓
    保护现场
        ↓
   执行 ISR
        ↓
    恢复现场
        ↓
    ICC_EOIR
        ↓
   返回原程序

九、常见踩坑提醒 ⚠️

  • ❌ 只清 GPIO 中断标志,不写 ICC_EOIR → 中断反复进入

  • ❌ 忘记 cpsie i → 中断永远进不来

  • ❌ 混淆 SPI / PPI / SGI 的中断号范围

  • ❌ 在多核平台未正确绑定中断亲和性(GICv3+)


十、总结一句话

中断 = 硬件触发 + GIC 仲裁 + CPU 响应 + 现场保护 + ISR 执行 + 中断结束

相关推荐
不悔哥1 天前
开源OV-Watch:怎么做一个智能手表
单片机·开源·嵌入式
XiHongShi20161 天前
STM32F407 RTC定时器例程,建议保存
stm32·单片机·学习
深圳老胡1 天前
STM32F407 控制 L6470 步进电机驱动 —— 控制过程简介
笔记·stm32·单片机·嵌入式硬件·代码规范
女神下凡1 天前
嵌入式设计的各种存储芯片的硬件/软件设计规范,非常全面。
arm开发·单片机·嵌入式硬件
梅梅9661 天前
一款mipi转lvds的lcd调试(LT8912B)
单片机·计算机外设·电脑·显示器·pd芯片
开发笔记-阿牛1 天前
蓝牙音乐灯拆解,又一次拆到蓝牙音乐灯芯片CK6865L
人工智能·单片机·嵌入式硬件·音视频·音频
从零开始的嵌入式之旅1 天前
day47
arm开发·经验分享·笔记·嵌入式硬件
恒锐丰科技林技术员1 天前
EG1164 高压大电流升压同步整流芯片解析
经验分享·嵌入式硬件·硬件工程
CHENKONG_CK1 天前
破解制鞋打磨痛点:RFID赋能去毛刺工序自动化升级
网络·单片机·嵌入式硬件·网络协议·tcp/ip
祖力551 天前
ARM时钟
嵌入式硬件·arm·时钟·imx6ull