【发布时间】:2013-12-29 00:28:39
【问题描述】:
我有以下 CUDA 内核,似乎很难优化:
__global__ void DataLayoutTransformKernel(cuDoubleComplex* d_origx, cuDoubleComplex* d_origx_remap, int n, int filter_size, int ai )
{
for(int idx = blockIdx.x * blockDim.x + threadIdx.x; idx < filter_size; idx+=blockDim.x * gridDim.x)
{
int index = (idx * ai) & (n-1);
d_origx_remap[idx] = d_origx[index];
}
}
//Parameters were defined before
int permute[loops] = {29165143,3831769,17603771,9301169,32350975, ...}
int n = 33554432;
int filter_size = 1783157;
for(int i=0; i<loops; i++)
{
DataLayoutTransformKernel<<<dimGrid, dimBlock, 0, stream[i]>>>((cuDoubleComplex*) d_origx,(cuDoubleComplex*)d_origx_remap+i*filter_size, n, filter_size, permute[i]);
}
内核的目的是将d_origx[]的数据布局从不规则重新排序为规则(d_origx_remap)。内核以不同的访问步幅启动多次 (ai)。
这里的挑战是引用d_origx[index] 数组时的不规则内存访问模式。我的想法是使用共享内存。但是对于这种情况,似乎很难使用共享内存来合并全局内存访问。
有人对如何优化这个内核有建议吗?
【问题讨论】:
-
也许你可以通过启动内核来隐藏一些延迟,该内核以交错的方式同时处理重新映射的缓冲区和转换内核。第一次迭代只是重新映射内核。第二次迭代同时启动重映射内核和处理第一次重映射结果的内核等。也许还考虑将此功能直接滚动到下一个内核中(让内核在跨步位置提取其值)。