Parallel processing OpenCL:工作组概念

Parallel processing OpenCL:工作组概念,parallel-processing,opencl,Parallel Processing,Opencl,我真的不理解OpenCL中工作组的目的 我知道它们是一组工作项(据说是硬件线程),这些工作项是并行执行的 然而,为什么需要更粗的细分呢?只有线程网格(事实上只有一个W-G)不是很好吗 一个工作组应该精确地映射到一个物理核心吗?例如,据说特斯拉c1060卡有240个核心。工作组将如何映射到这一点 另外,据我所知,由于内存限制,工作组中的工作项可以同步。工作组是否可以同步,或者是否需要同步?它们是通过共享内存相互通信还是仅针对工作项(此项不确定)?使用工作组可以对内核编译器进行更多优化。这是因为数据

我真的不理解OpenCL中工作组的目的

我知道它们是一组工作项(据说是硬件线程),这些工作项是并行执行的

然而,为什么需要更粗的细分呢?只有线程网格(事实上只有一个W-G)不是很好吗

一个工作组应该精确地映射到一个物理核心吗?例如,据说特斯拉c1060卡有240个核心。工作组将如何映射到这一点


另外,据我所知,由于内存限制,工作组中的工作项可以同步。工作组是否可以同步,或者是否需要同步?它们是通过共享内存相互通信还是仅针对工作项(此项不确定)?

使用工作组可以对内核编译器进行更多优化。这是因为数据不会在工作组之间传输。根据使用的OpenCL设备的不同,可能存在可用于本地变量的缓存,以实现更快的数据访问。如果只有一个工作组,则局部变量将与全局变量相同,这将导致较慢的数据访问

此外,OpenCL设备通常使用单指令多数据(SIMD)扩展来实现良好的并行性。一个工作组可以与SIMD扩展并行运行

 Should a Work-Group exactly map to a physical core ?
我认为,找到最快工作组规模的唯一方法是尝试不同的工作组规模。还可以从具有的设备查询CL_内核_首选_工作_组_大小_倍数。最快的大小应该是它的倍数

 Can work-groups synchronize or is that even needed ?

工作组。这样,它们之间就没有数据依赖关系,如果认为这是运行它们的最快方式,它们也可以按顺序运行。为了获得相同的结果,与工作组之间的同步相比,内核需要拆分为多个内核。变量可以通过缓冲区在内核之间传输。

工作组的一个好处是,它们可以使用共享本地内存作为程序员定义的缓存。从全局内存读取的值可以存储在共享工作组本地内存中,然后由工作组中的任何工作项快速访问。生命的游戏就是一个很好的例子:每个细胞都依赖于自身和周围的8个细胞。如果每个工作项都读取此信息,则会有9倍的全局内存读取。通过使用工作组和共享本地内存,您可以接近1x全局内存读取(仅此一种方法,因为在边缘存在冗余读取)。

我认为这里的混淆部分归结于术语。GPU人们通常称之为核心的东西并不是真的,而GPU人们通常称之为线程的东西只是在某种意义上

核心 在GPU营销术语中,核心可能指CPU核心,也可能指SIMD单元的单通道——实际上,单核x86 CPU就是这种简单类型的四个核心。这就是为什么GPU内核数量会如此之高。这并不是一个真正公平的比较,你必须除以16、32或类似的数字才能得到更直接可比的核心数量

工作项 OpenCL中的每个工作项就其控制流和内存模型而言都是一个线程。硬件可能在单个线程上运行多个工作项,您可以通过想象四个OpenCL工作项在SSE向量的单独通道上运行来轻松描述这一点。实现这一点的只是编译器的诡计,而在GPU上,它往往是编译器诡计和硬件辅助的混合体。OpenCL2.0实际上通过子组公开了这个底层硬件线程概念,因此需要处理另一个层次结构

工作组 每个工作组包含一组工作项,这些工作项必须能够在存在障碍的情况下取得进展。实际上,这意味着它是一个集合,其所有状态都能够同时存在,因此当遇到同步原语时,在它们之间切换的开销很小,并且可以保证切换是可能的

一个工作组必须映射到一个单独的计算单元,这实际上意味着整个工作组可以放在一个单独的实体上,CPU用户可以称之为核心-CUDA可以称之为多处理器(取决于代数),AMD可以称之为计算单元,其他则有不同的名称。这种执行的局部性导致更高效的同步,但也意味着工作项集可以访问本地构造的内存单元。它们需要频繁通信,否则就不会使用屏障,为了提高通信效率,可能会使用本地缓存(类似于CPU L1)或暂存器内存(OpenCL中的本地内存)

只要使用了屏障,工作组就可以在内部、工作项之间、使用本地内存或使用全局内存进行同步。工作组不能相互同步,标准也不能保证工作组之间的相对进度,这使得构建便携式锁定和同步原语实际上是不可能的


这在很大程度上是由于历史而不是设计。GPU硬件长期以来一直被设计用于构造向量线程,并以最佳处理三角形的方式将它们分配给执行单元。OpenCL没有将硬件泛化为对其他事物有用的东西,但没有将其泛化到实现效率低下的程度。

为了进一步理解OpenCL的术语,已经有很多很好的答案(“Jonathan Tompson和Kristofer Schlachter的OpenCL编程模型简介”)实际上很好地描述了所有的概念