如何在 OpenCL 中自动增加全局计数器
How to atomic increment a global counter in OpenCL
我想在 OpenCL 中有一个全局计数器,每个工作组中的每个工作项都可以增加它。
在我的内核中我这样做:
#pragma OPENCL EXTENSION cl_khr_global_int32_base_atomics : enable
void increase(volatile __global int* counter)
{
atomic_inc(counter);
}
__kernel void test()
{
volatile __global int* counter = 0;
increase(counter);
printf("Counter: %i",&counter);
}
我的主机代码是使内核排队的最小 pyopencl:
import pyopencl as cl
platform = cl.get_platforms()[0]
devs = platform.get_devices()
device = devs[0]
ctx = cl.Context([device])
queue = cl.CommandQueue(ctx)
mf = cl.mem_flags
f = open('Minimal.cl', 'r')
fstr = "".join(f.readlines())
prg = cl.Program(ctx, fstr).build()
test_knl = prg.test
def f():
cl.enqueue_nd_range_kernel(queue,test_knl,(1,1,2),None)
f()
我希望输出显示 "Counter: i"
的(可能是随机排序的)外观,其中 i
是工作项总数(在我的例子中为 2)。
相反,我没有得到打印输出。当我重新运行程序时,它失败并显示
pyopencl.cffi_cl.LogicError: clcreatecontext failed: <unknown error -9999>
完全杀死我的 IDE (Spyder)。
volatile __global int* counter = 0;
创建指向全局内存的指针是不够的。后面一定有一些全局内存存储。
至少有两个选项:
1) 如果您使用 OpenCL 2.0 实现,您可以创建一个程序范围变量:
void increase(volatile __global int* counter)
{
atomic_inc(counter);
}
__global int counter = 0;
__kernel void test()
{
volatile __global int* counterPtr = &counter;
increase(counterPtr); // or increase(&counter);
printf("Counter: %i",*counterPtr);
}
2) 创建一个 OpenCL 缓冲区并通过内核参数传递它:
void increase(volatile __global int* counter)
{
atomic_inc(counter);
}
__kernel void test(__global int *counterArg)
{
volatile __global int* counterPtr = counterArg;
increase(counterPtr); // or increase(counterArg);
printf("Counter: %i",*counterPtr);
}
我想在 OpenCL 中有一个全局计数器,每个工作组中的每个工作项都可以增加它。
在我的内核中我这样做:
#pragma OPENCL EXTENSION cl_khr_global_int32_base_atomics : enable
void increase(volatile __global int* counter)
{
atomic_inc(counter);
}
__kernel void test()
{
volatile __global int* counter = 0;
increase(counter);
printf("Counter: %i",&counter);
}
我的主机代码是使内核排队的最小 pyopencl:
import pyopencl as cl
platform = cl.get_platforms()[0]
devs = platform.get_devices()
device = devs[0]
ctx = cl.Context([device])
queue = cl.CommandQueue(ctx)
mf = cl.mem_flags
f = open('Minimal.cl', 'r')
fstr = "".join(f.readlines())
prg = cl.Program(ctx, fstr).build()
test_knl = prg.test
def f():
cl.enqueue_nd_range_kernel(queue,test_knl,(1,1,2),None)
f()
我希望输出显示 "Counter: i"
的(可能是随机排序的)外观,其中 i
是工作项总数(在我的例子中为 2)。
相反,我没有得到打印输出。当我重新运行程序时,它失败并显示
pyopencl.cffi_cl.LogicError: clcreatecontext failed: <unknown error -9999>
完全杀死我的 IDE (Spyder)。
volatile __global int* counter = 0;
创建指向全局内存的指针是不够的。后面一定有一些全局内存存储。
至少有两个选项:
1) 如果您使用 OpenCL 2.0 实现,您可以创建一个程序范围变量:
void increase(volatile __global int* counter)
{
atomic_inc(counter);
}
__global int counter = 0;
__kernel void test()
{
volatile __global int* counterPtr = &counter;
increase(counterPtr); // or increase(&counter);
printf("Counter: %i",*counterPtr);
}
2) 创建一个 OpenCL 缓冲区并通过内核参数传递它:
void increase(volatile __global int* counter)
{
atomic_inc(counter);
}
__kernel void test(__global int *counterArg)
{
volatile __global int* counterPtr = counterArg;
increase(counterPtr); // or increase(counterArg);
printf("Counter: %i",*counterPtr);
}