【问题标题】:What's right order to queue multiple opencl kernels in loop在循环中排队多个opencl内核的正确顺序是什么
【发布时间】:2015-07-19 13:49:46
【问题描述】:

在循环中将多个 opencl 内核排队的正确算法是什么? 代码如下:

for(int i=0;i<numIter;i++){ // numIter = 1000
//
status = clEnqueueNDRangeKernel(commandQueue,kernel1,2,NULL,globalThreads,localThreads,0,NULL,NULL);
ASSERT_CL(status);
status = clEnqueueNDRangeKernel(commandQueue,kernel2,2,NULL,globalThreads,localThreads,0,NULL,&ndrEvt);
ASSERT_CL(status);
if(i>0 && i%16==0){ // 16 - just
status = clFlush(commandQueue);
ASSERT_CL(status);
spinForEventsComplete( 1, &ndrEvt );
//status = clWaitForEvents(1, &ndrEvt);
//ASSERT_CL(status);
}
}
status = clFlush(commandQueue);
ASSERT_CL(status);
spinForEventsComplete( 1, &ndrEvt );

还是应该在每次 clEnqueueNDRangeKernel 调用后使用 wait?

谢谢!

【问题讨论】:

    标签: loops kernel opencl


    【解决方案1】:

    我看不出你所做的有什么问题。您是否尝试过在每个 NDRange 之后等待?您是否尝试过根本不等待并将所有 NDRange 排队?任何一种选择都更适合您吗?

    【讨论】:

    • 谢谢,我正在尝试不同的变体,有/没有等待,问题是结果不稳定,两个内核在全局内存中交换数据,但有时最终缓冲区中的数据错误。内核非常简单,只是计算,没有本地内存,没有内部循环,没有障碍。
    • 不同的内核调用可能会覆盖之前的结果。当您一次等待每个 NDRange 时,您是否还有最终数据问题?
    • 是的,任何有或没有等待的变体,都没有稳定的工作。我正在使用 amd app sdk 3.0 斗鱼
    【解决方案2】:

    这在很大程度上取决于您的内核有多大。如果它们需要很长时间才能运行,那么主机上的大量等待可能无关紧要。如果它们很小,您可能希望将大量它们排队以减少每次启动的开销。

    我自然会编写该循环而无需等待直到最后,但可能会像您一样每隔几次迭代插入一次刷新。您想要刷新的频率将取决于架构和一个很好的调整参数。

    我也倾向于编写包含所有事件依赖项的代码,即使您的代码可以愉快地依赖于有序队列,这也是一个好习惯。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2019-05-26
      • 1970-01-01
      • 2022-11-01
      • 1970-01-01
      • 1970-01-01
      • 2021-08-24
      • 1970-01-01
      相关资源
      最近更新 更多