ARM系列 -- 缓存维护指令

文摘   科技   2023-01-21 23:50   河北  
给大家拜年啦!
AArch64指令集中有两条关于缓存维护(cache maintenance)的指令,分别是ICDC。看名字就能猜到,IC是用于指令缓存操作,DC是用于数据缓存操作。
ICDC指令都属于系统指令(system instruction)。系统指令还包括ATBRBCFPCPPDVPTLBI,这些留到以后再分析。
再来回忆一下高速缓存的一致性问题:
  • 当前PE对某内存位置的更改可能没有被其它也可以访问该内存位置的观测者(observers)看见。
  • 其它观测者对内存的更改没有被当前的PE看见。

Arm架构文档中用了“观测者”这个词,泛指所有可以访问内存的硬件单元,不仅仅是处理器。

为了解决一致性问题,处理器需要有对缓存进行维护的能力。
  • 清除(Clean):高速缓存清除指令确保控制高速缓存的观察者所做的更新对其他观察者可见。一旦清理完成,新的内存值保证在执行指令的点(例如PoU)可见。也就是说,当前的处理器把缓存中的内容(已更改,标记为“脏”)写回到下一级缓存或者内存,这样保证下一级缓存或内存中的数据是最新的,其它观测者可见。
  • 无效(Invalidate):当前处理器把缓存中的内容无效,这可能会丢弃掉缓存中的更改。
  • 清除并无效(Clean and Invalidate):先执行清除操作,然后执行无效操作。

IC指令的编码格式如下图

IC指令的语法格式如下:

IC <ic_op>{, <Xt>}

其中,<Xt>是可选的64-bit通用源寄存器,对应上图中的“Rt”;<ic_op>IC指令的操作码,由上图中的“op1”,“op2”和“CRm”定义,目前的操作码有以下三种:

DC指令的编码格式:

DC指令的语法格式如下:

DC <dc_op>, <Xt>

其中,<Xt>是可选的64-bit通用源寄存器,对应上图中的“Rt”;<dc_op>IC指令的操作码,由上图中的“op1”,“op2”和“CRm”定义。DC指令的操作码比较多:

ICDC指令看上去比较简单,重点是指令操作码的含义。在分析操作码之前,先来搞清楚几个概念:
  • PoCPoint of coherency):在此处确保所有可以访问内存的代理都能看到相同的副本(copy)。在许多情况下,PoC实际上就是系统内存。
  • PoUPoint of Unification):在此处确保PE的指令和数据缓存以及地址转换表遍历能够看到相同副本。对于单核处理器来说,PoU就是系统内存;对于多核处理器,PoU取决于共享域(shareability domain)属性。
在官方的程序员指南里面截取了两张图,帮大家理解PoCPoU

当对高速缓存进行操作时,需要知道操作的范围。设置共享域属性就是为了指定所有可以访问内存的PE实现一致性的范围。
弄明白了PoCPoU的概念,再来看指令操作码。以IC指令的操作码IALLU为例,其代表的是“Invalidate All to PoU”,即在PoU角度看,无效PE的全部指令缓存;而IALLUIS是“Invalidate All to PoU Inner Shareable”,站在PoU角度,无效内部共享域PE的全部指令缓存,也就是这个无效操作会广播到整个内部共享域;IVAU是“Invalidate by VA to PoU”,无效指定的虚拟地址。
缓存维护操作可以通过缓存组(set),路(way)或虚拟地址(VA)执行。在做高速缓存维护操作前,需要知道高速缓存的一些信息,比如系统中有多少级高速缓存,缓存行的大小,每一级缓存的组织结构等等。这些基本信息保存在系统寄存器中,在系统上电过程中,操作系统访问这些寄存器来获得缓存的信息。这些寄存器有CLIDR_EL1CSSELR_EL1CCSIDR_EL1CTR_EL1等。

CLIDR_EL1寄存器

CSSELR_EL1寄存器

CCSIDR_EL1寄存器

CTR_EL0寄存器

今天就到这里吧,是不是没用的知识又增加了一些呢?

老秦谈芯
交流ASIC技术