在OpenCL中全局内存是连续的吗
我是OpenCL的新手,尝试在OpenCL中使用全局内存进行2D扫描 我在输出数组中有一些无效值,这让人怀疑 如果全局内存是连续的。因为通过运行下面的内核,我在输出数组中发现了一些垃圾值 这是我的内核。输入和输出均为8×8二维阵列在OpenCL中全局内存是连续的吗,opencl,Opencl,我是OpenCL的新手,尝试在OpenCL中使用全局内存进行2D扫描 我在输出数组中有一些无效值,这让人怀疑 如果全局内存是连续的。因为通过运行下面的内核,我在输出数组中发现了一些垃圾值 这是我的内核。输入和输出均为8×8二维阵列 #define SWAP(a,b) {__global uint *tmp=a;a=b;b=tmp;} __kernel void 2dScan( const __global uint * const input, __global uint *
#define SWAP(a,b) {__global uint *tmp=a;a=b;b=tmp;}
__kernel void 2dScan(
const __global uint * const input,
__global uint * const output,
__global uint *lb,
__global uint *lc
)
{
const uint x = get_global_id(0);
const uint y = get_global_id(1);
const uint xm = get_global_size(0);
const uint ym = get_global_size(1);
uint gs = get_global_size(0) * get_global_size(1);
uint index = y * xm + x;
lb[index] = lc[index] = input[index];
barrier(CLK_GLOBAL_MEM_FENCE);
for(uint s = 1; s < gs; s <<= 1) {
if(index > (s-1)) {
lc[index] = lb[index]+lb[index-s];
} else {
lc[index] = lb[index];
}
barrier(CLK_GLOBAL_MEM_FENCE);
SWAP(lb,lc);
}
output[index]= lb[index];
}
#定义交换(a,b){{全局uint*tmp=a;a=b;b=tmp;}
__内核空二维扫描(
常量uu全局单位*常量输入,
__全局uint*常量输出,
__全球单位*lb,
__全球uint*lc
)
{
consuint x=获取全局id(0);
consuint y=获取全局id(1);
const uint xm=获取全局大小(0);
const uint ym=获取全局大小(1);
uint gs=获取全局大小(0)*获取全局大小(1);
单位指数=y*xm+x;
lb[索引]=lc[索引]=输入[索引];
屏障(CLK_GLOBAL_MEM_围栏);
对于(uint s=1;s
在我看来,for循环中存在一个问题。您的访问是不确定的,这就是,您无法确保哪一个将返回结果,例如,输出[2]
例如,工作项#2在循环内执行(s=1):lc[2]=lb[2]+lb[1];
好的,问题是:lb[1]的值是否已经被工作项#1修改了?您的屏障同步了属于同一工作组的工作项。我认为lc[index]=lb[index]+lb[index-s]中的访问
超出了工作组的“限制”,因为s
值导致了不确定性问题。您正在覆盖每个工作项中的lb
和lc
。因此结果未定义,因为OpenCL在全局项之间没有同步。屏障(CLK\u global\u MEM\u FENCE);
在全局内存范围内同步本地工作组
您将得到的结果是基于日程模式的,并且在任何方面都是不可预测的。但是,它只会发生在本地组边界
您需要更改您的算法。我想您的意思是“连续”。谢谢。我更正了它。非常感谢您的回答。垃圾值指的是未初始化的值。现在我明白了问题所在。谢谢!谢谢您的回答!现在我明白了屏障(CLK\u GLOCAL\u MEM\u FENCE);
将不会同步全局项目。非常感谢!