对于一个项目,我不得不深入研究OpenCL:事情进展顺利,除非我现在需要原子操作。
我正在使用最后的驱动程序在Nvidia GPU上执行OpenCL代码。 clGetDeviceInfo()
查询CL_DEVICE_VERSION
会让我回复:
OpenCL 1.0 CUDA
,因此我想我必须参考OpenCL 1.0规范。
我开始在atom_add
缓冲区的内核中使用__global int* vnumber
操作:
atom_add(&vnumber[0], 1);
。这给了我明显错误的结果。因此,作为一个额外的检查,我已经在内核的开头移动了add指令,以便为每个线程执行它。当内核以512 x 512个线程启动时,vnumber[0]
的内容为:524288
,正好是2 x 512 x 512,是我应该得到的值的两倍。有趣的是,通过将添加操作更改为atom_add(&vnumber[0], 2);
,返回的值为65536
,这是我应该得到的两倍。
有人已经体验过类似的东西吗?我错过了非常基本的东西吗?我已经检查了数据类型的正确性,但似乎没问题(我正在使用*int
缓冲区,并使用sizeof(cl_int)
分配它。)
答案 0 :(得分:3)
您正在使用atom_add,它是本地内存的OpenCL 1.0扩展。然而,你正在传递全球记忆。相反,尝试使用OpenCL 1.1的atomic_add,它与全局内存一起使用。