给出以下简单矩阵乘法内核
`__global__ void MatrixMulKernel(float* M, float* N, float* P, int
Width)
{
int Row = blockIdx.y*blockDim.y+threadIdx.y;
int Col = blockIdx.x*blockDim.x+threadIdx.x;
if ((Row < Width) && (Col < Width)) {
float Pvalue = 0;
for (int k = 0; k < Width; ++k)
{
Pvalue += M[Row*Width+k]*N[k*Width+Col];
}
P[Row*Width+Col] = Pvalue;
}
}`
如果我们在1000X1000矩阵上启动块大小为16X16的内核,那么有多少warp会有控件偏差?
答案:500
说明:水平方向有63个方块。 每行x维度中的8个线程将处于无效范围内。每两行形成一个warp。因此,有1000/2 = 500个经线将跨越水平方向上的有效和无效范围。对于底部块中的扭曲,有效范围内有8个扭曲,无效范围内有8个扭曲。这些经线中的线程要么完全处于有效范围内,要么无效范围。
问题:我试图理解为什么在这种情况下,x维度中的8个线程将处于无效范围内?
答案 0 :(得分:2)
每个块覆盖16x16元素阵列。为了覆盖1000x1000个元素的矩阵,我需要一个方形螺纹块阵列,其水平方向尺寸为1000/16 = 62.5块,垂直方向尺寸为62.5块。
但是我无法启动62.5x62.5块,所以为了完全覆盖,我必须启动63x63块,确认这将在“无效范围”中创建额外的线程(即,它将映射到元素位置在1000x1000矩阵之外)。
当我在水平方向上发射63个块时,我在水平方向上得到63x16 = 1008个线程。但我只需要1000个,所以8个线程(每行)都处于“无效范围”。