OpenCL内核数学输出不正确的结果

时间:2018-01-15 13:32:22

标签: opencl

我目前正在尝试实现OpenCL内核。内核应该输出一些先前计算的元素除以重新映射的元素总数为0到255的值。

内核在一个工作组中运行,其中包含256个工作项,其中LX是本地ID:

#define LX get_local_id(0)

kernel void reduceStatistic(global int *inout, int nr_workgroups, int nr_pixels)
{
    int i = 1;
    for (; i < nr_workgroups; i++)
    {
        inout[LX] += inout[LX + i * 256];
    }

    inout[LX] = (int)floor(((float)inout[LX] / (float)nr_pixels) * 256.0f);
}

重映射操作之前的计算是在先前对同一缓冲区进行计算后进行清理。

清理后的inout [LX]的第一项是17176,nr_pixels是160000,所以使用上面的计算得到的值为27。但是,代码返回6。

相关的主机端代码如下:

// nr_workgroups is of type int
cl_mem outputBuffer = clCreateBuffer(mgr->context, CL_MEM_READ_WRITE, nr_workgroups * 256 * sizeof(cl_int), NULL, NULL);

// another kernel writes into outputBuffer

// set kernel arguments
clSetKernelArg(mgr->reduceStatisticKernel, 0, sizeof(outputBuffer), &outputBuffer);
clSetKernelArg(mgr->reduceStatisticKernel, 1, sizeof(cl_int), &nr_workgroups);
clSetKernelArg(mgr->reduceStatisticKernel, 2, sizeof(cl_int), &imgSeqSize);

size_t global_work_size_statistics[1] = { 256 };
size_t local_work_size_statistics[1] = { 256 };

// run the kernel
clEnqueueNDRangeKernel(mgr->commandQueue, mgr->reduceStatisticKernel, 1, NULL, global_work_size_statistics, local_work_size_statistics, 0, NULL, NULL);

// read result
cl_int *reducedResult = new cl_int[256];
clEnqueueReadBuffer(mgr->commandQueue, outputBuffer, CL_TRUE, 0, 256 * sizeof(cl_int), reducedResult, 0, NULL, NULL);

非常感谢! (:

1 个答案:

答案 0 :(得分:0)

我们在评论中确定全局缓冲区索引计算错误:

    inout[LX] += inout[LX + i * 265];
                      ----------^^^
                      Should be 256

超出缓冲区的范围会导致未定义的行为,因此这始终是寻找的主要元凶之一。