我有两个OpenCL内核:第一个是并行任务,第二个是线性(LZW)。 第一个是并行的,在GPU上运行,第二个是线性的,在CPU上运行。我有一个多核CPU,我真的只想在单核上运行一个内核实例,而不是在2+核上运行2+实例。这不是生产所必需的,而是我关于各种类型任务执行的学术研究。
我现在使用的相当愚蠢的方法是:
if (global_id == 0) then execute();
else do_nothing();
有没有比这更好的方法?
谢谢。
答案 0 :(得分:6)
您可以使用clEnqueueTask运行内核。这应该启动一个工作项。你可以用它来运行单个线程的内核。
另一种情况: OpenCL是为并行计算开发的,如果使用clEnqueueNDRangeKernel运行内核,则将工作组大小设置为1是实现所需效果的唯一可能方法。另一方面,编译器可能希望优化某些东西并并行运行。只要OpenCL编译器支持此选项,就可以禁用clBuildProgram选项的“-cl-opt-disable”选项。如果需要运行clEnqueueNDRangeKernel,可以执行此操作。但我认为没有必要。
答案 1 :(得分:1)
据我所知,基于对OpenCL规范的快速搜索,没有可移植的方法来限制内核到单个处理器的执行。请考虑规范中的以下定义:
可以想象,基于CPU的实现可以将单个芯片的若干核心视为包括单个计算单元的处理元件。然后,即使在将内核排入队列时将全局和本地工作组大小设置为1,OpenCL内核编译器也可以自由地利用内核中的任何并行性。处理元素:虚拟标量处理器。工作项可以在一个或多个处理元素上执行。
计算单元:OpenCL 设备具有一个或多个计算单元。 工作组在单个计算单元上执行。 计算单元由一个或多个处理元素组成。 计算单元还可以包括可由其处理元素访问的专用纹理过滤单元。
但是,我怀疑是否有人为x86制作这样一个聪明的OpenCL实现而烦恼,所以通过只将一个内核实例(即使用全局和本地工作组大小为1)排队,并使用在命令命令队列中如果要运行多个作业,则可能会使您的任务仅使用单个CPU进行计算。主机端OpenCL工作(比如编译内核)可能仍会使用其他CPU。