2013-04-07 56 views
0

CUDA的减少让我非常困惑!首先,Mark Harris的this教程和Mike Giles的this one均使用声明extern __shared__ temp[]。在进行声明时,C中使用关键字extern,但分配发生在“elsewhre”(例如,通常在另一个C文件上下文中)。 extern这里的相关性是什么?我们为什么不使用:CUDA总结减少难题

__shared__ float temp[N/2]; 

例如?或者为什么我们不宣布temp是一个全局变量,例如

#define N 1024 
__shared__ float temp[N/2]; 

__global__ void sum(float *sum, float *data){ ... } 

int main(){ 
... 
sum<<<M,L>>>(sum, data); 
} 

我还有其他问题吗?应该用多少个块和线程来调用求和内核?我试过this example(根据this)。

注意:您可以找到有关我的设备here的信息。

+2

有两种不同的分配共享内存的方法,一种是静态分配的大小,另一种是动态分配的大小。阅读[这里](http://docs.nvidia.com/cuda/cuda-c-programming-guide/index.html#shared)。如果你说'__shared__ float temp [256];'你正在做一个静态分配。如果你说'extern __shared__ float temp [];'你正在做一个动态的(在运行时)分配。 – 2013-04-07 15:00:48

回答

2

对第一个问题的回答是,CUDA支持在运行时动态共享内存分配(有关更多详细信息,请参阅this SO问题和the documentation)。使用extern共享存储器的声明表示至该共享存储器的大小将在内核启动来确定,(经由API函数或等价)以字节为单位作为参数传递到<<< >>>语法,像编译器:

sum<<< gridsize, blocksize, sharedmem_size >>>(....); 

第二个问题通常是启动将完全填充GPU上所有流式多处理器的块数。最明智的减少内核将积累每个线程的许多值,然后执行共享内存减少。减少要求每块的线程数是2的幂:通常给你32,64,128,256,512(或1024,如果你有一个费米或开普勒GPU)。这是一个非常有限的搜索空间,只是基准点,看看什么在你的硬件上最好。你可以找到关于块和网格尺寸的更一般的讨论herehere

+0

这也是我的失职,不要指出我发布的答案中的所有内容都在文档中,或者可以通过阅读SO CUDA常见问题或与您所选择的搜索引擎一起找到.... – talonmies 2013-04-07 15:34:37

+0

谢谢,主要问题的确是我必须指定应该分配的共享内存的大小。其次,这个函数在编写时会返回一个数组,每个数据块应该在最后加起来。我将不得不修改最终的代码... – 2013-04-08 12:57:05