今天来看看CHI协议里面关于一致性的内容。下图中包括三个主组件,每个主组件都有一个本地缓存和相关协议节点。该协议允许相同内存位置的缓存副本驻留在本地缓存中一个或多个主组件。协议要求:
- 当一条缓存行是系统中的唯一拷贝时,拥有该缓存行的主机可以修改数值,不需要通知其它的主机
- 如果一条缓存行可能存在其它备份,主机想要修改自己的备份,必须通过正确的transaction通知其它主机
这两个要求很好理解,如果一条缓存行是系统中的唯一拷贝,无论拥有它的处理器怎么改写,都不涉及到缓存一致性的问题;但是如果缓存中的数据(可能)不唯一,就牵扯到了缓存一致性,修改它的处理器必须通知其它也拥有该拷贝的缓存控制器并得到响应,要么无效掉(invalidate)其它的拷贝,要么更新(update)其它的拷贝,这些就是高速缓存的“写无效”和“写更新”策略,忘了的同学可以看看前面讲cache的文章《CPU设计之Cache -- 写/包含/替换策略》。
为了使得一个组件在访问缓存时,可以确定是否该执行某操作,CHI协议定义了缓存状态模型(Cache State Model)。不同以往,这次定义了七种状态,多出的两种状态是UCE和UDP:
- I:Invalid,该缓存行的数据不在当前缓存中;
- UC:Unique Clean,该缓存行的数据只在当前缓存中,且和主存的数据一致;缓存行的数据可以被修改,而不需要通知其它的缓存;在收到snoop请求时,该缓存行可以,但不必需返回数据给HN或RN;
- UCE:Unique Clean Empty,该缓存行的数据只在当前缓存中,但是所有的数据都是无效的,可以不知会其它RN就对该缓存行的数据进行修改。在收到snoop请求时,该cache line必须不能返回数据给HN或RN;
- UD:Unique Dirty,该缓存行的数据只在当前缓存中,且和主存的数据不一致,已经被修改过了;如果该缓存行的数据不用了,那需要写回到下级缓存或主存。可以不知会其它RN就对该缓存行的数据进行修改。在收到snoop请求时,该缓存行必须返回数据给HN或RN;
- UDP:Unique Dirty Partial,该缓存行的数据只在当前缓存中,且和主存的数据不一致,部分被修改且有效;如果该缓存行的数据不用了,那需要和下级缓存或主存的数据组成一个完成有效的缓存行。可以不知会其它RN就对该缓存行的数据进行修改。在收到snoop请求时,该缓存行必须返回数据给HN,但不能直接将数据给Requester;
- SC:Shared Clean,其它缓存可能也存在该缓存行的拷贝;该缓存行可能已经被修改了;当不需要该缓存行数据时,cache没有义务必须将该数据写回到主存;必须对其它缓存的该缓存行进行无效(invalidate)后,获得U态才能将该缓存行进行改写;在收到snoop请求时,该缓存行在RetToSrc没有置位时不需要返回数据,如果RetToSrc置位,则需要返回数据,可以直接fwd数据给Requester;
- SD:Shared Dirty,其它缓存可能也存在该缓存行的拷贝;该缓存行相对于主存已经被修改了;当该缓存行不需要的时候,当前缓存需要将它写回下游缓存或主存;必须对其它缓存的该缓存行进行无效后,获得U态后才能将该缓存行进行改写。在收到snoop请求时,该缓存行必须返回数据给HN和Requester;
需要解释一下UCE。UCE表示缓存行是unique的,但是数据是invalid的。什么情况下会产生UCE呢:
- Requester故意获取空缓存行。在开始写操作之前,为了节省系统带宽,requester可以获得具有store权限的空缓存行,而不是获得缓存行的有效副本
- 请求者可以转换为空状态。Requester在获得store权限前已经有该缓存行的副本,但是数据是无效的。Requester获得store后,该缓存行变成UCE
CHI协议中的请求(request)可以分为以下几类:
读请求
- 需要向请求者(requester)提供数据响应。
- 可能导致系统中其它agent之间的数据移动(比如从其它缓存搬移数据到请求者)
- 可能导致请求者的缓存状态发生更改(比如从I状态变为S状态)
- 可能导致系统中其它请求者的缓存状态发生更改(比如从E状态变为S状态)
写请求
- 需要从请求者移动数据。
- 可能导致系统中其它代理之间的数据移动(比如更新其它的缓存数据)
- 可能导致请求者的缓存状态发生更改(比如从S状态变为M状态)
- 可能导致系统中其它请求者的缓存状态发生更改(比如从S状态变为I状态)
无数据请求
- 无需向请求者提供数据响应
- 可能导致系统中其他代理之间的数据移动
- 可能导致请求者的缓存状态发生更改
- 可能导致系统中其他请求者的缓存状态发生更改
原子请求
- 需要从请求者移动数据
- 数据响应以某些请求类型提供给请求者
- 可能导致系统中其它代理之间的数据移动
- 可能导致请求者的缓存状态发生更改
- 可能导致系统中其它请求者的缓存状态发生更改
其它请求
- 不要在系统中移动数据
- 可用于协助分布式虚拟内存(DVM)维护。
- 可用于为随后的读取请求预热内存控制器
对于每个transaction对数据大小和缓存状态的影响,可以参考CHI协议的第四章。这里就不一一列举了。对于ICN,会产生snoop请求,以响应于来自RN的请求或由于内部缓存或snoop filter维护操作。同样,大家如果对细节感兴趣,建议去看第四章。
这里再提一句,由于内部事件,缓存行的状态可以悄悄转变,而不必去通知其它的缓存。CHI协议中规定了合法的静默缓存状态转换(silent cache state transitions),如下图。
CHI协议允许requester超发多个请求,并接受超发的snoop请求。这时候,如果对同一条缓存行有多个transaction,那么ICN需要对这些transaction进行排序,并且要保证对所有的组件来说,看到的顺序是相同的。Spec中花了一个小节去描述RN-F节点和HN-F节点要如何处理。
【未完】
作者:老秦谈芯
来源:https://mp.weixin.qq.com/s/gM-u0Hq8SJgyLid6gDgwYg
微信公众号:
相关文章推荐
更多AMBA协议相关知识请关注</span>Arm AMBA 协议集专栏。