RPI2 上的 MMU 初始化时缓存失效

Cache invalidation while MMU init on RPI2

最近我在 raspberry pi 2 上尝试了 MMU 初始化代码并遇到了奇怪的行为。我想做的是建立琐碎的 部分 映射。

我使用 this 代码作为参考基础。虽然,简短的审查表明此代码是为 bcm2835 编写的,但仍然没有比这更好的东西。

我遇到的问题是缓存刷新后死胡同。这是 start_mmu 函数

的完整示例
.globl start_mmu
start_mmu:
    mov r2,#0
    mcr p15,0,r2,c7,c7,0 ;@ invalidate caches
    mcr p15,0,r2,c8,c7,0 ;@ invalidate tlb
    mcr p15,0,r2,c7,c10,4 ;@ DSB ??

    mvn r2,#0
    bic r2,#0xC
    mcr p15,0,r2,c3,c0,0 ;@ domain

    mcr p15,0,r0,c2,c0,0 ;@ tlb base
    mcr p15,0,r0,c2,c0,1 ;@ tlb base

    mrc p15,0,r2,c1,c0,0
    orr r2,r2,r1
    mcr p15,0,r2,c1,c0,0

换句话说,我在缓存失效行上遇到了死胡同:

 mcr p15,0,r2,c7,c7,0 ;@ invalidate caches

我所说的死胡同是指执行此行后我无法打印某些内容。似乎我在那一刻陷入了某种例外。 如果我省略这个缓存无效行,我可以继续,但似乎在我设置后 MMU 映射没有正确建立(但这是另一个问题)。 我想知道的是:

1.) 为什么我们需要在 MMU 启动之前使缓存和 tlb 失效?

2.)死胡同的原因是什么?

Why do we need invalidate caches and tlb before MMU startup?

因为它们可能包含未初始化的垃圾(或只是重置后的陈旧条目)。一旦你打开 MMU,instruction/data 访问的地址可能会在 TLB 中查找,如果任何垃圾恰好看起来足够像与相关虚拟地址匹配的有效条目,那么你将要过得不好。启用缓存后,instructions/data 本身也类似。

What could be the reason of dead-end problem?

您正在执行无效指令。

如果您想编写裸机代码,了解您 运行 使用的金属是有好处的 - Raspberry Pi 2 具有 Cortex-A7 内核,这与其他模型中的 ARM1176 内核,因此表现不同。具体来说,在这种情况下,ARMv6 架构下统一缓存操作所在的 CP15 c7,0,c7 系统寄存器 space 不再分配在 ARMv7 中,因此尝试访问它会导致不可预测的行为。您需要分别使您的 I-cache 和 D-cache 失效。我建议至少看看 Cortex-A7 TRM, and ideally the Architecture Reference Manual. Also for real-world examples, there's always Linux 和朋友们。是的,要接受的东西太多了,但是嘿,这是一个成熟的多核移动-class 应用程序处理器,而不是一些微控制器 ;)

现在,首要任务应该是设置一些异常向量处理程序,以便在出现问题时提供一些调试输出,因为从现在开始,更多的事情肯定会出错...