[英]Understanding CUDA shfl instruction
我已经阅读了Shuffle Tips and Tricks的文章,但不确定如何将其应用于继承的一些易懂的代码:
extern __shared__ unsigned int lpSharedMem[];
int tid = threadIdx.x;
lpSharedMem[tid] = startValue;
volatile unsigned int *srt = lpSharedMem;
// ...various stuff
srt[tid] = min( srt[tid], srt[tid+32] );
srt[tid] = min( srt[tid], srt[tid+16] );
srt[tid] = min( srt[tid], srt[tid+8] );
srt[tid] = min( srt[tid], srt[tid+4] );
srt[tid] = min( srt[tid], srt[tid+2] );
srt[tid] = min( srt[tid], srt[tid+1] );
__syncthreads();
即使没有CUDA,此代码也相当狡猾,但查看此实现,我会看到:
__device__ inline int min_warp(int val) {
val = min(val, __shfl_xor(val, 16));
val = min(val, __shfl_xor(val, 8));
val = min(val, __shfl_xor(val, 4));
val = min(val, __shfl_xor(val, 2));
val = min(val, __shfl_xor(val, 1));
return __shfl(val, 0);
}
此代码可通过以下方式调用:
int minVal = min_warp(startValue);
因此,我可以用上面的代码替换我那狡猾的volatile
。 但是,我无法真正理解发生了什么。 有人可以解释我是否正确,以及min_warp()
函数中到底发生了什么。
从int __shfl_xor(int var, int laneMask, int width=warpSize);
:
__shfl_xor()通过对调用者的通道ID与laneMask进行按位XOR运算来计算源行ID:返回由所得通道ID保持的var值。 (...)
通道ID是线程束中从0到31的线程索引。因此,硬件会对每个线程执行按位XOR:sourceLaneId XOR laneMask => destinationLaneId
例如,使用线程0和:
__shfl_xor(val, 16)
laneMask = 0b00000000000000000000000000010000 = 16(十进制)
srclaneID = 0b00000000000000000000000000000000 = 0(十进制)
XOR ------------------------------------------------- ---------
dstLaneID = 0b0000000000000000000000000001000010000 = 16(十进制)
然后线程0获得线程16的值。
现在使用线程4:
laneMask = 0b00000000000000000000000000010000 = 16(十进制)
srclaneID = 0b00000000000000000000000000000100 = 4(十进制)
XOR ------------------------------------------------- ---------
dstLaneID = 0b00000000000000000000000000000000010100 = 20(十进制)
因此,线程4获得线程20的值。
如果我们回到实际的算法,我们会看到这是应用min
运算符的并行约简。 在步骤:
PD:请注意,两个代码并不完全相同。 此偏移量“ 32”告诉我们您的共享内存阵列的长度为2 * WARP。 (您正在将2 * WARP值减少为1)
srt[tid] = min( srt[tid], srt[tid+32] );
洗牌一将WARP值减小为1。
这些幻灯片在第27页上有一个直观的图表,如下所示:
xor 1首先交换奇/偶单输入
xor 2然后交换奇数/偶数对先前交换的输入
xor 4然后交换奇/偶四边形
等等
另一种方法是计算一个完整的“异或”掩码和原始输入值的“异或”值。 有多种方法可以使用不同的经纱混洗指令来完成此操作。 此异或模式也用于FFT / DFT转换,也称为“蝴蝶图”。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.