ARMv7-A小系统实践(十一):启动CPU1,走通SCU与SGI核间通信

本章记录什么

这一章把单核可运行系统扩展为 Cortex-A9 双核启动底座。重点是共享状态和每核状态的边界:BSS、页表和 Distributor 只能由主核负责共享初始化;模式栈、GICC、PPI、CP15、TLB 和 L1 Cache 则必须由每个 CPU 分别建立。

在这一章之前做了什么

单核路径已经能够启动 MMU、Cache、GIC 和任务调度,但直接让 CPU1 执行同一入口会引入竞争:两个核可能同时清 BSS、重复初始化全局对象,或者共用一份 SVC/IRQ 栈。为此启动入口先读取 MPIDR 分流,CPU1 在 release flag 上等待,CPU0 完成发布后再用 cache clean、屏障和事件唤醒次核。

本章给出启动时序、SGI 往返验证和次核初始化代码,同时明确“第二个核在线”不等于“已经完成 SMP 调度器”。

ARMv7-A小系统实践(十):L1、L2、屏障与Cache一致性

本章记录什么

这一章解释 L1 I/D Cache、分支预测、SCU 和 L2C-310 的启用与维护。核心问题不是“把 SCTLR 的某一位置 1”,而是旧缓存状态何时失效、页表何时需要 clean、跨核共享何时依赖 SCU,以及 DMA 或自修改代码出现后软件应怎样维护一致性。

在这一章之前做了什么

上一章已经为普通内存和 MMIO 建立了不同的页表属性。只有在属性正确后,Cache 的行为才有可推导基础。启动阶段还要先无效化旧状态,再按顺序启用 SCU、ACTLR.SMP、L1 和 L2;运行阶段则要区分 clean、invalidate 和 clean+invalidate。

本章从概念、顺序和屏障开始,随后给出完整的 Cache 实现代码。最后会明确当前小系统证明了哪些 CPU 一致性能力,以及尚未通过 DMA 场景证明什么。

ARMv7-A小系统实践(一):从Cortex-A9与Zynq-7020开始

本章记录什么

这一章不急着写第一条汇编,而是先回答一个更容易被忽略的问题:要在 ARMv7-A、Cortex-A9 和 Zynq-7020 上做出一个能启动、能切换任务、能响应中断的小系统,究竟需要建立哪些知识和软件部件?如果一开始不把层次分清,后面很容易把 ARMv7-A 的架构规定、Cortex-A9 的实现细节和 Zynq-7020 的片上地址混成一张表,遇到故障时也不知道该查哪一本手册。

本系列的目标不是照抄一份现成工程,也不是把 x86_64 汇编逐行翻译成 ARM 汇编。真正要迁移的是系统能力:处理器从复位入口进入 C 环境,任务拥有独立栈和可恢复现场,定时器能够触发 IRQ,GIC 能够完成中断状态闭环,MMU 与 Cache 按内存属性工作,第二个处理器核能够被安全释放。每一项能力都要给出可观察证据和明确边界。

在这一章之前做了什么

动手前已经具备一个很小的 x86_64 参考系统和两套 ARM 侧参照:一套是按同样功能合同搭建的 Zynq-7020 教学实现,另一套是 RTEMS 6.2 的成熟 ARM 端口。前者适合看最小闭环,后者适合验证设计方向。官方架构手册、Cortex-A9 MPCore 技术参考手册和 Zynq-7000 技术参考手册负责裁决寄存器和硬件语义。

接下来的文章会从处理器模式开始,逐步走到 ABI、启动、任务上下文、异常现场、GIC、抢占、MMU、Cache、SMP 和调试。读者只看博客也能顺着这条链完成推演;文中出现的源码路径只用于说明工程如何组织,不作为理解前提。


:D 一言句子获取中...