2013-07-09 76 views
0

我正尝试在CUDA(200x200x100)中使用3D数组。三维阵列的分割错误

当我将z维(model_num)从4更改为5时,出现了分段错误。为什么,我该如何解决它?

const int nrcells = 200; 
const int nphicells = 200; 
const int model_num = 5; //So far, 4 is the maximum model_num that works. At 5 and after, there is a segmentation fault 

    __global__ void kernel(float* mgridb) 
{ 
    const unsigned long long int i = (blockIdx.y * gridDim.x + blockIdx.x) * blockDim.x + threadIdx.x; 

    if(tx >= 0 && tx < nphicells && ty >=0 && ty < nrcells && tz >= 0 && tz < model_num){ 
     //Do stuff with mgridb[i] 
    } 
} 

int main (void) 
{ 

    unsigned long long int size_matrices = nphicells*nrcells*model_num; 
    unsigned long long int mem_size_matrices = sizeof(float) * size_matrices; 

    float *h_mgridb = (float *)malloc(mem_size_matrices); 
    float mgridb[nphicells][nrcells][model_num]; 

    for(int k = 0; k < model_num; k++){ 
     for(int j = 0; j < nrcells; j++){ 
      for(int i = 0; i < nphicells; i++){ 
       mgridb[i][j][k] = 0; 
      } 
     } 
    } 
    float *d_mgridb; 

    cudaMalloc((void**)&d_mgridb, mem_size_matrices); 
    cudaMemcpy(d_mgridb, h_mgridb, mem_size_matrices, cudaMemcpyHostToDevice); 

    int threads = nphicells; 
    uint3 blocks = make_uint3(nrcells,model_num,1); 
    kernel<<<blocks,threads>>>(d_mgridb); 
    cudaMemcpy(h_mgridb, d_mgridb, mem_size_matrices, cudaMemcpyDeviceToHost); 
    cudaFree(d_mgridb); 
    return 0; 
} 
+0

请多关注一下您在问题中发布的代码的格式和内容。您发布的代码不必要的难以阅读并且包含不平衡{}。 – talonmies

+0

会做。谢谢。 –

回答

3

这是得到存储在堆栈上:

float mgridb[nphicells][nrcells][model_num]; 

你的栈空间是有限的。当您超过可存储在堆栈上的金额you are getting a seg fault时,无论是在分配点,还是尝试访问它时。

改为使用malloc。这分配堆存储,它有更高的限制。

以上都与CUDA无关。

您可能还需要调整访问数组的方式,但使用指针索引处理a flattened array并不困难。

您的代码实际上是奇怪的看,因为你正在使用malloc创建一个适当大小的数组h_mgridb,然后复制该数组到设备(进入d_mgridb)。目前还不清楚mgridb在代码中的作用。 h_mgridbmgridb是不一样的。

+0

谢谢你,罗伯特!这解决了这个问题。 –

+0

这解决了这个问题。我将float mgridb [nphicells] [nrcells] [model_num]更改为float * mgridb =(float *)malloc(mem_size_matrices)。此外,在初始化“for”循环中,我将它引用为一维数组,因此mgridb [i +(j * nphicells)+(k * nphicells * nrcells)] = 0。我可以看到你在说什么,它如果我已经分配了mgridb,那么拥有h_mgridb没有什么意义。 –