Opencl NVIDIA上的CL_OUT_OF_资源错误

Opencl NVIDIA上的CL_OUT_OF_资源错误,opencl,nvidia,Opencl,Nvidia,我正在尝试在NVIDIA GPU上运行代码。重复执行CL\u命令\u读取\u缓冲区时,我的CL\u资源不足错误。同样的代码在英特尔CPU上运行,有8个计算单元,完美无缺 在CPU上: 本地大小=1 全局大小=8 DEVICE\u GLOBAL\u MEM\u SIZE=12431327232 在GPU上: 本地大小=32(扭曲大小) 全局大小=32*8 设备全局内存大小=1072889856 我知道CL\u OUT\u OF \u RESOURCES错误是由于在分配的缓冲区之外访问内存造

我正在尝试在NVIDIA GPU上运行代码。重复执行
CL\u命令\u读取\u缓冲区时,我的
CL\u资源不足
错误。同样的代码在英特尔CPU上运行,有8个计算单元,完美无缺

在CPU上:

  • 本地大小=1
  • 全局大小=8
  • DEVICE\u GLOBAL\u MEM\u SIZE
    =12431327232
在GPU上:

  • 本地大小=32(扭曲大小)
  • 全局大小=32*8
  • 设备全局内存大小
    =1072889856
我知道
CL\u OUT\u OF \u RESOURCES
错误是由于在分配的缓冲区之外访问内存造成的。但我不知道为什么这个错误只在GPU中出现。可能是什么错误?我遗漏了什么吗

编辑:

h_ref[add]读取的结构数据与预期不符。在主机端打印sizeof(h_ref)时,设备端返回8,设备端返回4。在英特尔CPU上运行时,主机和设备上的读数为8。如何确保数据的正确传输

规格GeForce GTX 560 Ti

内核代码:

__kernel void product(__global double* h_inputvec,__global struct Reference* h_ref ,__global double* h_res,const int num_ipvec,const int N,const int numb)
 {  
 const int indicator = get_group_id(0);

const int add = (int)(indicator*num_ipvec)/N;
unsigned int ipv_size = h_ref[add].num ;

const int fract = (int)(ipv_size*N/num_ipvec); 
int fractn = (int) fract/numb;
const int div = (int)ipv_size/fractn  ; 

struct Node temp = h_ref[add].noderef ; 


__local double centroid[441];
double value;
int tempo ;

const int th_id = get_local_id(0);
int te = 14;

for(int i=0; i< 14 ; i++) // assuming that number of work items allotted are greater than centroids
{
    int val =  (441*(indicator % numb));
    centroid[(32*i+th_id)%441] = temp.centroids[(32*i+th_id)%441 + val] ;
}   


for( int i = 0 ; i<= div ; i++)
{           
    value = 0;
    int inc = (int) (indicator / numb);
    tempo = h_ref[add].input_vec[(i*fractn+inc)%ipv_size];


    for(int j=0 ; j<441 ;j++)
    {                       
        double diff = centroid[j]- h_inputvec[441*tempo + j];
        value += pow(diff,2);
    }
    double norm =  sqrt(value);
    h_res[N*tempo+(indicator%numb)] =  norm;
}                                                                       
\u内核无效乘积(\u全局双精度*h\u输入向量,\u全局结构引用*h\u引用,\u全局双精度*h\u res,常量int num\u ipvec,常量int N,常量int numb)
{  
const int indicator=get_group_id(0);
常量int add=(int)(指标*num_ipvec)/N;
无符号整数ipv_size=h_ref[add].num;
常数整数分形=(整数)(ipv_大小*N/num_ipvec);
int fractn=(int)fract/numb;
常量int div=(int)ipv_大小/分形;
结构节点temp=h_ref[add].noderef;
__局部双质心[441];
双重价值;
内拍;
const int th_id=get_local_id(0);
int te=14;
for(int i=0;i<14;i++)//假设分配的工作项数量大于质心
{
int val=(441*(指标%numb));
质心[(32*i+th_id)%441]=温度质心[(32*i+th_id)%441+val];
}   

对于(int i=0;i加载相关代码。尝试生成一个。我很想知道CL_OF_RESOURCES是否有错误。这可能是因为内存不足,还是仅仅是因为内存访问超出了分配的缓冲区?我们很想看到您的代码。我们可以编出您看到错误的可能原因,但这并不是有效的。同时,我可以告诉您u只有一个指针:我做了一个快速搜索,发现提到如果使用NVIDIA硬件,
CL_OUT_OF_RESOURCES
是一种“通用”错误,当出现错误时由驱动程序返回。这只会加强我的观点。显示代码!阵列
双质心[441]在您的内核中声明的需要3528字节的私有内存,即Nvidia GPU上的882个32位寄存器。英伟达CUDA 6编程指南中,没有Nvidia GPU存在,每个线程可以有那么多寄存器。这是<>代码> CyOutux的至少一个原因。我仍然得到相同的错误。这个NVIDIA GPU的每个块共享内存:49152字节。
 struct Node {
 public:
 cl_uint num
 cl_double *dic;
 cl_double *c;
 cl_double *di;
 cl_double *bs;
 Node *bs;
 };

 struct Reference{
 public:
 cl_uint* inec;
 cl_uint nu;
 Node nref;
 };

     N=8
     size_t local[1] = {32};
     size_t global[1] = {32*8};

    size_t sz_ipv = 441*num_ipvec*sizeof(double);
    size_t sz_ref = sizeof(temp_ref);
    size_t  sz_res = N*num_ipvec*sizeof(double); 
    size_t sz_minres = num_ipvec*sizeof(int)*(N/2);

    /* create host array */

    double *h_inputvec = (double*) calloc(441*num_ipvec,sizeof(double));
    Reference *h_ref = (Reference*) calloc(1,sizeof(temp_ref)); // change
    double *h_res = (double*) calloc(N*num_ipvec,sizeof(double)); // N,X data forward
    int *h_minres = (int*) calloc(num_ipvec*(N/2),sizeof(int));

            for(int in =0 ; in<N*num_ipvec ; in++) // initialze result to maximum value (padding) 
    {
            h_res[in] = numeric_limits<int>::max();
            h_minres[in%(N/2*num_ipvec)] = in % int(N/2) ;
    }

    cl_mem c_inputvec = clCreateBuffer(context, CL_MEM_READ_WRITE | CL_MEM_COPY_HOST_PTR, sz_ipv, h_inputvec, &err);
    cl_mem c_ref = clCreateBuffer(context, CL_MEM_READ_WRITE | CL_MEM_COPY_HOST_PTR,sz_ref, h_ref, &err);
    cl_mem c_res = clCreateBuffer(context, CL_MEM_READ_WRITE | CL_MEM_COPY_HOST_PTR,sz_res, h_res, &err);
    cl_mem c_minres =  clCreateBuffer(context, CL_MEM_READ_WRITE | CL_MEM_COPY_HOST_PTR,sz_minres, h_minres, &err);


    // set arguments    

    clSetKernelArg(kernel, 0, sizeof(cl_mem), &c_inputvec);
    clSetKernelArg(kernel, 1, sizeof(cl_mem), &c_ref);
    clSetKernelArg(kernel, 2, sizeof(cl_mem), &c_res);
    clSetKernelArg(kernel, 3, sizeof(const int), &num_ipvec);
    clSetKernelArg(kernel, 4, sizeof(const int), &N);
    clSetKernelArg(kernel, 5, sizeof(const int), &numb);
    printf(" arguments to kernel \n");

    //launch kernel         
    clEnqueueNDRangeKernel(queue, kernel, dim, 0, global, local, 0, (cl_event*)NULL, &event_time);