CUDA - 多处理器,Warp大小和每个块的最大线程数:确切的关系是什么?

时间:2012-07-19 15:52:04

标签: caching memory cuda textures

我知道CUDA GPU上有多处理器,其中包含CUDA核心。在我的工作场所,我使用的是GTX 590,它包含512个CUDA内核,16个多处理器,其warp大小为32.因此,这意味着每个多处理器中有32个CUDA内核,它们在同一个warp中完全相同的代码。最后,每块大小的最大线程数为1024。

我的问题是块大小和多处理器数量 - warp大小是如何完全相关的。让我告诉我对情况的理解:例如,我在GTX 590上分配了最大threadPerBlock大小为1024的N个块。据我从CUDA编程指南和其他来源的理解,这些块首先由硬件枚举。在这种情况下,来自N个块的16被分配给不同的多处理器。每个块包含1024个线程,硬件调度程序将32个这些线程分配给单个多处理器中的32个核心。同一多处理器(warp)中的线程处理代码的同一行,并使用当前多进程的共享内存。如果当前的32个线程遇到像存储器读写这样的片外操作,则它们将替换为来自当前块的另一组32个线程。因此,在一个块中实际上有32个线程在任何给定时间内在多处理器上并行运行完全,而不是整个1024.最后,如果块由多处理器完全处理,将来自N个线程块列表的新线程块插入当前多处理器。最后,在执行CUDA内核期间,GPU中总共有512个并行运行的线程。 (我知道如果一个块使用的寄存器多于单个多处理器上可用的寄存器,那么它将分为两个多处理器,但我们假设在我们的情况下每个块可以适合单个多处理器。)

那么,我的CUDA并行执行模型是否正确?如果没有,有什么不对或缺失?我想微调我正在处理的当前项目,所以我需要最正确的工作模型。

1 个答案:

答案 0 :(得分:18)

  

在我的工作场所,我正在使用GTX 590,它包含512个CUDA内核,16个多处理器,其warp大小为32.因此,这意味着每个多处理器中有32个CUDA内核,它们完全适用于相同的代码。同样的扭曲。最后,每块大小的最大线程数为1024。

GTX590包含您提到的数字的2倍,因为卡上有2个GPU。下面,我专注于一个芯片。

  

让我告诉我对情况的理解:例如,我在GTX 590上分配了最大threadPerBlock大小为1024的N个块。据我从CUDA编程指南和其他来源的理解,首先列出这些块。由硬件。在这种情况下,N个块中的16个被分配给不同的多处理器。

块不一定在多处理器(SM)之间均匀分布。如果你准确地安排了16个块,那么一些SM可以获得2个或3个块,而其中一些块空闲。我不知道为什么。

  

每个块包含1024个线程,硬件调度程序将32个这些线程分配给单个多处理器中的32个核心。

线程和核心之间的关系不直接。每个SM中有32个“基本”ALU。那些处理诸如单精度浮点和大多数32位整数和逻辑指令之类的东西。但是只有16个加载/存储单元,因此如果当前正在处理的warp指令是加载/存储,则必须将其调度两次。并且只有4个特殊功能单元,用于执行三角测量等操作。所以这些说明必须安排32/4 = 8次。

  

同一个多处理器(warp)中的线程处理相同的代码行,并使用当前多进程的共享内存。

不,在单个SM中可以同时“飞行”多于32个线程。

  

如果当前的32个线程遇到像存储器读写这样的片外操作,则它们将替换为来自当前块的另一组32个线程。因此,在一个块中实际上有32个线程在任何给定时间内在多处理器上并行运行,而不是整个1024.

不,不仅是内存操作会导致更换warp。 ALU也是深度流水线的,因此新的warp将被交换,因为仍然在管道中的值会发生数据依赖性。因此,如果代码包含两个指令,其中第二个使用第一个的输出,则warp将被保持,而第一个指令的值通过管道。

  

最后,如果一个块由多处理器完全处理,则N个线程块列表中的新线程块将插入到当前的多处理器中。

多处理器一次可以处理多个块,但是一旦处理开始,块就无法移动到另一个MP。当前正在运行的块中的线程数取决于块使用的资源数量。 CUDA占用计算器将根据您特定内核的资源使用情况,告诉您同时有多少块将在飞行中。

  

最后,在执行CUDA内核时,GPU中总共有512个并行运行的线程。 (我知道如果一个块使用的寄存器多于单个多处理器上可用的寄存器,那么它将分为两个多处理器,但我们假设在我们的情况下每个块可以适合单个多处理器。)

不,一个块不能分为两个多处理器。整个块总是由单个多处理器处理。如果给定的多处理器没有足够的资源来处理内核中至少一个块,则会出现内核启动错误,并且程序根本不会运行。

这取决于您如何将线程定义为“正在运行”。 GPU通常会有超过512个线程同时消耗芯片上的各种资源。

在这个问题中查看@harrism的回答:CUDA: How many concurrent threads in total?