Cache 基本原理

  • 直接映射
  • 组相联映射
  • 全相联映射

组相联高速缓存

在组相联 Cache 中,每个块可悲放置的位置数是固定的。每个块有 n 个位置可放的 Cache 被称为 n 路组相联 Cache。一个 n 路组相联 Cache 中有 n 个组,每个组里有 n 块。

以下是被解析了的地址:

1
2
3
-------------------------------------
| Tag | Index | Offset |
-------------------------------------

其中 Index 用来选择包含所需地址的组,该组中的所有块都要被索引,所以被选中的组中的所有块的标记并行检索。

首先 Cache 获取到需要读取的地址,随后根据 Index 找到对应的组,根据 Tag 并行找到对应的行(可能出现 Cache Miss),最后根据 Offset 获取到读取的字节数。

Cache 的设计

Cache 模块的数据通路设计

1. 读写操作访问的 Cache 执行过程

  • 第一拍:首先将 Index 读出来同时找到对应的组,并将组里的所有块读出来。同时将虚地址送向 TLB 并获取到物理地址,此时需要将物理地址锁存起来供第二拍使用
  • 第二拍:得到 Cache RAM 读出的两个 Cache line 的 Tag 信息,将其与锁存下来的物理地址的 Tag 进行对比,如果某个 Cache line 上面的 Tag 相等,且该 Cache line 的有效位等于 1 时,则表示访问命中在这个 Cache line 上面。在进行 Tag 比较的同时,可以根据锁存下来的虚地址对 Cache line 的 Data 信息进行选择。

写操作前面的操作与读步骤基本一致,区别仅在于写操作开始时可以不读取 Cache 的 Data 信息。它只需要读取两个 Cache line 中的 Tag、V 信息来判断 Cache 是否命中。

读写缺失时的操作步骤:

  • 将 Cache 缺失的地址和操作类型记录下来
  • 通过 AXI 总线接口向外发起对缺失 Cache line 的访问。这个访问的地址是缺失 Cache line 的起始地址,大小是一个 Cache line 的大小。
  • 在等待读请求数据返回的时候,根据替换算法从 Cache Miss 地址对应的 index 的中的 Cache line 中选择一个。将其整个读出。如果发现该 Cache line 的 V = 1,D = 1,意味着这是一个有小脏数据的 Cache line,那么需要将这个 Cache line 的数据通过 AXI 总线接口模块写出去;否则直接丢弃。
  • 待缺失请求的数据从总线返回后,生成将要填入 Cache 的 Cache line 信息,其中 Cache line 的 V 置为 1,Tag 信息来自之前保存的 Cache 缺失的地址。如果这个 Cache Miss 请求操作是由写操作引起的,那么 Cache line 的 D 置为 1,Data 信息是 store 操作待写入值部分覆盖总线返回数据之后形成的新数据;否则 D 置为 0,Data 信息金来自总线返回的数据。
  • 将这个 Cache line 填入之前第三步所记录下来的那个位置。

提高 Cache 的性能

写缓存(Write Buffer)

在处理器中不管是执行 load 指令还是 stote 指令,当 D-Cache 发生缺失时,需要从下一级存储器中读取数据,并写到一个选定的 Cache line 中,如果这个 line 是脏的话,那么首先需要将它写到下级存储器中,考虑一般的下级存储器,例如 L2 Cache 或者物理内存,一般只有一个读写端口,这就要求上面的过程是串行完成的,也就是说,先要将脏状态的 Cache line 中的数据写回到下级存储器中,然后才能读取下级存储器而得到缺失的数据,由于下级存储器的访问时间都比较长,这种串行过程导致 D-Cache 发生缺失的处理时间变得很长,此时就可以采用写缓存(Write Buffer) 来解决这个问题,脏数据的 Cache line 会首先放到写缓存中,等到下级存储器有空闲的时候,才会将写缓存中的数据写到下级存储器中。

References

  • 《CPU 设计实战》
  • 《超标量处理器设计》
  • 《Computer Architecture: A Quantitative Approach》