计算能力 7.5 中的缓存行为

rm9*_*m95 1 caching cuda gpgpu nsight compute-capability

这些是我的假设:

  1. 有两种类型的加载:缓存和非缓存。在第一个中,流量经过 L1 和 L2,而在第二个中,流量仅经过 L2。
  2. Compute Capability 6.x 和 7.x 中的默认行为是缓存访问。
  3. L1 缓存行为 128 字节,L2 缓存行为 32 字节,因此对于生成的每个 L1 事务,应该有四个 L2 事务(每个扇区一个)。
  4. 在Nsight中,SM->TEX请求意味着由32个线程合并而成的warp级指令。L2->TEX Returns 和 TEX->SM Returns 是每个内存单元之间传输的扇区数量的度量。

假设计算能力为 7.5,我的问题如下:

  1. 第三个假设似乎暗示对于全局缓存加载,L2->TEX 返回应该始终是四的倍数,但情况并非总是如此。这里发生了什么?
  2. 用 const 和 __restrict__ 限定符标记指针还有意义吗?这曾经是向编译器暗示数据是只读的,因此可以缓存在 L1/纹理缓存中,但现在所有数据都缓存在那里,无论是只读的还是非只读的。
  3. 根据我的第四个假设,我认为只要 TEX->SM Returns 大于 L2->TEX Returns,差异就来自缓存命中。这是因为当缓存命中时,您会从 L1 读取一些扇区,但不会从 L2 读取任何扇区。这是真的?

Gre*_*ith 6

CC 6.x/7.x

  • L1 缓存行大小为 128 字节,分为 4 个 32 字节扇区。如果未命中,则只会从 L2 获取已寻址的扇区。
  • L2 高速缓存行大小为 128 字节,分为 4 个 32 字节扇区。
    • CC 7.0 (HBM) 64B 升级已启用。如果缓存行的低 64 字节未命中,则将从 DRAM 中获取低 64 字节。如果高速缓存行的高 64 字节未命中,则将获取高 64 字节。
    • CC 6.x/7.5 仅会从 DRAM 中获取访问的 32B 扇区。
  • 在L1缓存策略方面
    • CC 6.0 默认启用加载缓存
    • CC 6.x 默认禁用加载缓存 - 请参阅编程指南
    • CC 7.x 默认启用加载缓存 - 有关缓存控制的详细信息,请参阅 PTX

在 Nsight Compute 中,术语“请求”在 6.x 和 7.x 之间变化。

  • 对于 5.x-6.x,每条指令的请求数量因操作类型和数据宽度而异。例如,32 位负载为 8 个线程/请求,64 位负载为 4 个线程/请求,128 位负载为 2 个线程/请求。
  • 对于 7.x,请求应等同于指令,除非访问模式具有导致序列化的地址分歧。

回答您的 CC 7.5 问题

  1. 第三个假设似乎暗示对于全局缓存加载,L2->TEX 返回应该始终是四的倍数,但情况并非总是如此。这里发生了什么?

L1TEX 单元只会获取缓存行中丢失的 32B 扇区。

  1. 用 const 和limit 限定符标记指针还有意义吗?这曾经是向编译器暗示数据是只读的,因此可以缓存在 L1/纹理缓存中,但现在所有数据都缓存在那里,无论是只读的还是非只读的。

如果已知数据是只读的,则编译器可以执行其他优化。

  1. 根据我的第四个假设,我认为只要 TEX->SM Returns 大于 L2->TEX Returns,差异就来自缓存命中。这是因为当缓存命中时,您会从 L1 读取一些扇区,但不会从 L2 读取任何扇区。这是真的?

L1TEX 到 SM 返回 B/W 为 128B/周期。L2 到 SM 返回 B/W 位于 32B 扇区中。

Nsight 计算内存工作负载分析 | L1/TEX 缓存表显示

  • 扇区未到达 L2(32B 扇区)
  • 返回 SM(周期 == 1-128B)