GICv3 ITS 翻译表实战:搞懂 MSI 中断路由的 5 个关键点
发布时间:2026/8/29 14:41:32 作者:尧图编辑部 阅读量:1,286

GICv3 ITS 翻译表实战搞懂 MSI 中断路由的 5 个关键点【免费下载链接】linuxLinux kernel source tree项目地址: https://gitcode.com/GitHub_Trending/li/linux某台 ARM 服务器的 16 队列 NVMesoftirq 却全压在 CPU0 上其余核心几乎闲着。排查中断风暴时这类现场很常见。问题多半不在盘而在于 MSI 中断路由没按预期工作GICv3 下 PCIe 设备发出的不是传统 SPI而是 LPILocality-specific Peripheral Interrupt必须先经 ITS 翻译表把消息翻成一个具体的 LPI 编号才能投递。看懂这张表你就看懂了中断为什么找不上门。30 秒速通GICv3 各部件分工 ⚙️部件一句话职责GICDDistributor总前台管 SPI/PPI 的优先级与全局路由GICRRedistributor每核一个的收发口LPI 最终都从这里进 CPUITSTranslation Service翻译窗口把 MSI 消息里的 (DeviceID, EventID) 翻成 LPI 编号GICV/GICH虚拟化代理GICv4 在此之上增强中断注入一句话记住分工SPI 是外设拉线拉出来的LPI 是设备往 PCIe 总线发包发出来的包要能送到就得先查地址簿——这本地址簿就是 ITS 翻译表。类比设备 ID 事件 ID 如何送到目标 CPU把 ITS 想成一个国际包裹转运站。设备发一条 MSI等于往转运站扔进一个包裹面单上有两个编号寄件方编号DeviceID和商品编号EventID。ITS 手里有三本册子Device Table按寄件方编号索引的公司名录告诉你这家公司的包裹清单放在哪ITT中断翻译表该公司的包裹清单按商品编号索引查出最终投递编号LPI INTIDCollection收件方登记簿——每个投递编号绑定一个 Collection由它决定中断投到哪个 CPU 的 Redistributor。所以一条 MSI 走完 Device Table → ITT → Collection 三次查表就成了LPI 编号 目标 CPU。表是内核提前用命令队列填好的运行时硬件纯查表速度快且不占 CPU。内核落点从 ITS 探测到 MSI 控制器注册内核把 ITS 拉起来用一条链就能串完探测its_of_probe遍历设备树对每个 ITS 节点调用its_probe_one复位硬件、读尺寸寄存器再由its_alloc_tables和its_alloc_collections分配三张表填表内核按 MAPD → MAPC → MAPTI → MOV → SYNC 的顺序往命令队列里塞命令——MAPD 绑设备、MAPC 把 Collection 绑到 CPU、MAPTI 写入 EventID→LPI 映射、MOV 改亲和性、SYNC 让硬件失效本地缓存注册最后挂上一个标准 MSI domain 交给 PCIe 栈此后驱动调pci_enable_msi_range即可翻译细节全透明。源码入口在 drivers/irqchip/irq-gic-v3-its.c约 5900 行本文主线都在这一个文件里。3 步配好 ITS 设备树 第 1 步GICv3 父节点compatible arm,gic-v3reg给两条——GICD 基址0x3e000000长 0x10000GICR 区0x3e100000长 0x200000再写#interrupt-cells 3和interrupt-controller;两行属性。第 2 步ITS 节点its: msi-controller3e200000 { compatible arm,gic-v3-its; msi-controller; #msi-cells 1; reg 0x3e200000 0x20000; };逐字段说compatible让内核按its_device_id匹配msi-controller是硬开关漏了它its_of_probe会打印 no msi-controller property, ITS ignored 直接跳过#msi-cells 1表示 MSI 数据是一个 32 位 EventIDreg是 ITS 寄存器空间物理地址和大小。第 3 步把设备指给 ITS在 PCIe 主机桥或外设节点上加一条 phandlepcie80000000 { compatible arm,pcie-host; msi-parent its; reg 0x80000000 0x100000; };这样该桥下所有设备的 MSI 都走这个 ITS 翻译。避坑清单亲和性与多 ITS 的三个常见坑现象原因对策写smp_affinity后smp_affinity_list纹丝不动写入的掩码里一个在线 CPU 都没有内核保留原亲和先cat /sys/devices/system/cpu/online只写在线位亲和改了中断却总在同一个 CPU 上跑目标 CPU 的 Redistributor 未在线、Collection 未注册LPI 落到默认投递路径只指向在线 CPU用dmesg \| grep -i gic确认各 CPU 初始化完成dmesg 出现 ITS ignored部分设备收不到中断ITS 节点漏写msi-controller属性多 ITS 时 GICv4 还要求全局编号唯一撞号会报 Duplicate ITSList每个 ITS 节点都补齐属性多实例时错开物理地址、别共用 ITSList 编号延伸阅读源码drivers/irqchip/irq-gic-v3.c、drivers/irqchip/irq-gic-v3-its.c设备树绑定Documentation/devicetree/bindings/interrupt-controller/arm,gic-v3.yaml规范ARM IHI 0069GICv3/GICv4 架构规范下一步建议先在目标机上跑dmesg | grep -E GICv3: (Using LPIs|ITS)确认 ITS 已拉起再对照/proc/interrupts里 LPI 列在 16 个 CPU 上是否均匀分布——不均匀就回到上面的避坑表逐条查。【免费下载链接】linuxLinux kernel source tree项目地址: https://gitcode.com/GitHub_Trending/li/linux创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考