【问题标题】:OpenCL execute kernel wrile copying data to CPUOpenCL 执行内核写入将数据复制到 CPU
【发布时间】:2018-04-21 07:12:56
【问题描述】:

我正在学习 OpenCL,我听说有可能在 GPU 上共同计算并同时复制数据。我有这样的想法:

queue.enqueueNDRangeKernel(ker, cl::NullRange, cl::NDRange(1024*1024));
queue.enqueueReadBuffer(buff, true, 0, 1024*1024, &buffer[0]);

我能以某种方式立即执行那里的操作吗?在执行具有更高索引的内核时将第一个结果复制回 CPU?

我想做这样的事情:

for(int i=0; i<1024; ++i){
    queue.enqueueNDRangeKernel(ker, cl::Range(i*1024), cl::NDRange(1024));
    queue.enqueueReadBuffer(buff, true, i*1024, 1024, &buffer[i*1024]);
}

但是要异步执行内核和读取。这样的事情可能吗?两个队列和内核完成事件是正确的解决方案吗?

感谢您的宝贵时间。

【问题讨论】:

    标签: opencl gpu


    【解决方案1】:

    是的,使用单独的命令队列进行上传、计算和下载(以及要同步的事件!)是重叠复制和计算的正确方法。在某些专业级硬件上,您甚至可以重叠上传和下载,因为它们有两个 DMA 引擎。

    【讨论】:

      【解决方案2】:

      如果您阅读the spec,您会发现您可以回答自己的问题。特别是,查看几个 OpenCL 函数的“cl_event”参数。

      此外,如果您仔细查看您自己的代码,您会发现您将阻塞参数设置为true(如果您想阻塞,它应该是CL_TRUE,尽管这可能是由您的队列对象处理的?)。您需要更改它并改用事件,并在获取事件和在事件列表中使用它之间使用必要的 clFlush()

      最后,假设您每次都使用新数据多次执行内核,您可以将内核的多个实例排队,尽管这需要在设备的内存中保存更多数据,因此您可能需要小心不要用完内存。

      编辑:如果您将多个实例排队,您将需要使用CL_QUEUE_OUT_OF_ORDER_EXEC_MODE_ENABLE 或多个命令队列(甚至两者)。我发现前者在适当的事件用法下更易于使用,但这实际上取决于个人喜好。

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 2019-01-16
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2015-10-04
        • 1970-01-01
        • 1970-01-01
        • 2011-09-07
        相关资源
        最近更新 更多