最近,我在显卡上的象素着色器执行中遇到了“波前”这个术语。
从上下文来看,我假设一个波前是将多个像素或顶点打包成一个结构,可以用一系列SIMD指令来处理,但如果有人能给出更详细的解释,我会很感激。
发布于 2021-12-06 17:57:44
你从上下文中所假设的是正确的。
在英特尔和nVidia的GPU上,硬件的SIMD宽度为32。在AMD,它通常是64,但在较新的AMD GPU也可以是32。这种方法有助于提高功耗和性能,因为GPU核心共享在这32或64个线程上执行指令获取和解码的晶体管。当前指令指针也在整个波前共享。
在硬件层面,GPU实际上有那么多的执行单元。除了FP64数学指令等少数例外,这些SIMD寄存器中的车道由不同的执行单元并行计算。GPU核心丢失了许多在CPU中发现的部分。GPU不做分支预测、推测执行、指令重新排序。它们的RAM访问要简单得多,因为对吞吐量进行了优化,并且不太关心延迟,而且它们的缓存一致性保证非常有限。这就是他们能够负担得起花费更大比例的晶体管在执行单位谁实际计算的东西。例如,我的旧1080 TFlops有120亿个晶体管,3584个着色器单元(组织成28个核心,当做FP32运算时,每个处理器可以处理4个波前=128个线程并行),并提供多达11个TFlops FP32。我的CPU有大约相同数量的晶体管,但只能提供1 TFlops FP32。
在最近的硬件(特征级别12.2)上,对于像素和计算着色器,程序员甚至可以通过波浪本质访问这些波前。
对于计算机着色器来说,事情很简单。如果您编写[numthreads( 64, 1, 1 )]和分派线程数为64倍,计算着色器的每个线程组将运行为nVidia上的两个波前和nVidia上的一个波前。如果您使用x线程数不超过64的倍数分派该着色器,最后一个波前将包含较少的线程,其中一些线程将处于非活动状态。GPU在每个运行的波前维护一个活动线程的位掩码。
对于像素着色器,事情就不那么简单了,因为GPU需要偏导数。因此,象素着色器波前被组织为2x2平方。像往常一样计算三角形外的像素,但是它们的输出值不会被写入任何地方。并且,用于像素着色器的波动本质包括读取这些2x2方格的其他像素的功能。
对于顶点着色器和它们的其余部分,如何分配到波前是一个没有意义的点。它不仅依赖于实现,甚至依赖于GPU模型和驱动程序。如果在VS的流水线上有一个几何着色器,GPU以这样的方式组织工作,这样顶点着色器的输出在传递给几何图形着色器之前就会停留在片内存储器中。同样适用于镶嵌着色器。另外,大多数真实的网格都是索引的,GPU是知道的,并且它们有一个转换顶点的缓存。每个顶点的顶点着色器调用的计数取决于该缓存的大小以及索引缓冲区中的网格拓扑。GPU尽力避免通过外部VRAM在着色器各阶段之间编组数据。就其规模而言,外部内存在延迟和电的访问上都是非常昂贵的。
https://stackoverflow.com/questions/70244508
复制相似问题