Parallel processing OpenCL中的clEnqueueReadBuffer函数问题-在数组和示例中
各位,, 我是OpenCL的初学者,我用C写了一些简单的代码,对两个数组求和。以下是代码的一部分:Parallel processing OpenCL中的clEnqueueReadBuffer函数问题-在数组和示例中,parallel-processing,opencl,Parallel Processing,Opencl,各位,, 我是OpenCL的初学者,我用C写了一些简单的代码,对两个数组求和。以下是代码的一部分: // Create Kernel. cl_kernel kernelSum = clCreateKernel( myProgram, "sum", &error ); // Set Input Array. size_t arraySize = 1000; char* a = ( char* ) malloc( sizeof( char ) * arraySize ); char
// Create Kernel.
cl_kernel kernelSum = clCreateKernel( myProgram, "sum", &error );
// Set Input Array.
size_t arraySize = 1000;
char* a = ( char* ) malloc( sizeof( char ) * arraySize );
char* b = ( char* ) malloc( sizeof( char ) * arraySize );
char* c = ( char* ) malloc( sizeof( char ) * arraySize );
for (int i = 0; i < arraySize; i += 1)
{
a[ i ] = 1;
b[ i ] = 2;
c[ i ] = -1;
}
// Set Buffers.
cl_mem a_buffer = clCreateBuffer(
myContext,
CL_MEM_READ_ONLY | CL_MEM_COPY_HOST_PTR,
arraySize * sizeof( char ), a,
&error );
cl_mem b_buffer = clCreateBuffer(
myContext,
CL_MEM_READ_ONLY | CL_MEM_COPY_HOST_PTR,
arraySize * sizeof( char ), b,
&error );
cl_mem c_buffer = clCreateBuffer(
myContext,
CL_MEM_WRITE_ONLY,
arraySize * sizeof( char ), NULL,
&error );
printf( "Buffers created.\n" );
// Setting Kernel Arguments.
error = clSetKernelArg( kernelSum, 0, sizeof( cl_mem ), &a_buffer );
error |= clSetKernelArg( kernelSum, 1, sizeof( cl_mem ), &b_buffer );
error |= clSetKernelArg( kernelSum, 2, sizeof( cl_mem ), &c_buffer );
printf( "Arguments Set.\n" );
// Enqueue kernels to execute.
cl_event event;
size_t globalWorkOffset = 0;
size_t globalWorkSize[ 1 ] = { arraySize };
size_t localWorkSize[ 1 ] = { 1 };
clEnqueueNDRangeKernel(
myCommandQueue,
kernelSum,
1, // work_dim
0, // global work offset
globalWorkSize,
localWorkSize, // local work offset
0, NULL,
&event
);
printf( "Kernel Enqueued.\n" );
error = clEnqueueReadBuffer(
myCommandQueue,
c_buffer,
CL_TRUE, // blocking option
( size_t ) 0, arraySize * sizeof( char ), // offset, data_size
c, // host_ptr
0, NULL,
&event );
if ( error != CL_SUCCESS )
{
printf( "Buffer Reading Back Failed.\n" );
exit( 1 );
}
然而,我得到了错误的结果:c数组中的所有数字都是零。我认为这与克伦奎雷亚德缓冲区有关,也许不是。对这个问题有什么想法吗?期待您的建议!:- 对clEnqueueReadBuffer的调用不会等待内核完成。它很可能与内核同时执行。将呼叫更改为:
error = clEnqueueReadBuffer(
myCommandQueue,
c_buffer,
CL_TRUE, // blocking option
( size_t ) 0, arraySize * sizeof( char ), // offset, data_size
c, // host_ptr
1, &event,
NULL );
这将导致clEnqueueReadBuffer在开始读取缓冲区之前等待内核事件完成。。你所有的建议都很有帮助。在你的帮助下,我终于发现我做错了什么: clBuildProgram myProgram,1,&设备,NULL,NULL,&错误; 这是我的原始代码。 该功能的官方定义为: CLU int CLBUILD program CLU program, cl_uint num_设备, const cl_device_id*device_list, 常量字符*选项, 无效CL_回调*pfn_通知 cl_计划, void*用户_数据, void*用户数据 我发现我将参数列表的最后一个设置为&error;我把这个函数和其他一些函数混合在一起,它们的参数列表通常以错误号结尾。在这里,我应该这样称呼它: clBuildProgram myProgram,1,&设备,NULL,NULL,NULL; 最后一个设置为NULL。然后程序正常运行
非常感谢大家!:- 问题可能出现在调用clenqueueredbuffer之前。要获得一个idea,请在每次发出命令时检查错误变量。您是对的。检查之后,我发现错误源于内核创建失败。clCreateKernelsInProgram返回的错误号与CL_INVALID_KERNEL匹配,这是我的内核:uuu KERNEL void sum uuu global const char*a,uuu global const char*b,uuuu global char*c{int tid=get_global_id 0;c[tid]=a[tid]+b[tid];}当我调用clCreateKernelsInProgram myProgram时,NULL,NULL,NULL,&numbers,数字变为0!我不知道我在哪里处理不当。你是在同时调用clCreateKernel和CLCreateKernelsInProgramm吗?为什么?很抱歉我没有解释。在使用StackOverflow之后,我做了一些修改。我发现clEnqueueNDRangeKernel的返回值与CL_INVALID_KERNEL匹配。我最初使用的是clCreateKernel,在我发现内核排队失败后,添加了CLCreateKernelsInProgramm来查询可用内核的总数,然后我发现该数字为零,这意味着没有可用内核。基于这一点,我意识到造成这种情况的真正原因是一个早期的API调用。谢谢,你的建议是正确的,但我认为我的命令队列具有默认属性,将按顺序执行命令,因为我没有指定CL_OUT_of_ORDER_EXEC_MODE_ENABLE。好吧,我的错误,我总是使用这个标志,所以我习惯了程序以这种方式运行。