如何由硬件warp调度程序形成和处理warp?

时间:2014-02-03 18:58:52

标签: cuda gpu scheduling

我的问题是关于扭曲和调度。我在这里使用NVIDIA Fermi术语。我的观察如下,它们是否正确?

一个。同一warp中的线程执行相同的指令。每个warp包含32个线程。

根据费米白皮书: “Fermi的双w​​arp调度器选择两个warp,并发出一个warp 从每个warp到一组16个内核,16个加载/存储单元或4个SFU的指令。 “

从这里开始,我认为warp(32个线程)被安排两次,因为32个中的16个核心被组合在一起。每个调度程序在一个周期内将一半的warp发布到16个核心,总​​之,两个调度程序在一个循环中将两个warmp-half发布到两个16核心调度组中。换句话说,在这个Fermi架构中,需要将一个经线安排两次,一半调整一半。如果warp仅包含SFU操作,则此warp需要发出8次(32/4),因为SM中只有4个SFPU。

B中。当启动大量线程(比如1-D阵列,320个线程)时,连续线程将自动分组为10个warp,每个线程有32个线程。因此,如果所有线程都在执行相同的工作,它们将执行完全相同的指令。在这种情况下,所有经线总是带有相同的指令。

问题: Q1。哪个部分处理线程分组(进入warp)?软件还是硬件?如果是硬件,它是warp调度程序吗?以及硬件warp调度程序如何实现和工作?

Q2。如果我有64个线程,线程0-15和32-47正在执行相同的指令,而16-31和48-63执行另一条指令,调度程序是否足够聪明,可以将非连续线程(使用相同的指令)分组到同一个warp中(即,将线程0-15和32-47分组为相同的warp,并将线程16-31和48-63分组为另一个warp)?

Q3。将warp大小(32)大于调度组大小(16个核心)有什么意义?(这是一个硬件问题)因为在这种情况下(Fermi),无论如何,warp将被安排两次(两个周期)。如果warp为16宽,则只安排两个warp(也是两个周期),这与前一个案例相同。我想知道这个组织是否是由于性能问题。

我现在可以想象的是:同一warp中的线程可以保证同步,这有时很有用,或者其他资源(如寄存器和内存)以warp大小为基础进行组织。我不确定这是否正确。

2 个答案:

答案 0 :(得分:4)

纠正一些误解:

  

一个。 ...从这里开始,我认为一个warp(32个线程)被安排两次,因为32个中的16个核心被组合在一起。

当warp指令发送给一组16个内核时,整个warp执行指令,因为内核被计时两次(Fermi的“hotclock”),因此每个内核实际上在一个周期内执行两个线程的计算值(= 2个hotclocks)。当调度warp指令时,整个warp得到服务。它不需要安排两次。

  

B中。 ...因此,如果所有线程都在执行相同的工作,它们将执行完全相同的指令。在这种情况下,所有经线总是带有相同的指令。

确实,块中的所有线程(以及所有warp)都是从相同的指令流执行的,但它们不一定执行相同的指令。当然,warp中的所有线程在任何给定时间都执行相同的指令。但是warp彼此独立地执行,因此块内的不同warp可以在任何给定时间执行来自流的不同指令。 Fermi whitepaper第10页上的图表说明了这一点。

  

Q1:哪个部分处理线程分组(进入warp)?软件还是硬件?

它由硬件完成,如编程指南的hardware implementation部分所述:“块被分区为warp的方式总是相同的;每个warp包含连续的,增加的线程ID的线程第一个包含线程0的warp。线程层次结构描述了线程ID如何与块中的线程索引相关。“

  

以及硬件warp调度程序如何实现和工作?

我不相信这在任何地方都有正式记录。格雷格史密斯已经提供了各种解释,你可能希望找到“用户:124092调度程序”或类似的搜索,阅读他的一些评论。

  

Q2。如果我有64个线程,线程0-15和32-47正在执行相同的指令,而16-31和48-63执行另一条指令,调度程序是否足够聪明,可以将非连续线程(使用相同的指令)分组到同一个warp中(即,将线程0-15和32-47分组为相同的warp,并将线程16-31和48-63分组为另一个warp)?

这个问题是基于前面概述的误解。将线程分组为warp是不是动态的;它在线程块启动时固定,并遵循上面Q1中给出的方法。此外,线程0-15永远不会被安排在除16-31之外的任何线程,因为0-31包含一个warp,这在调度方面是不可分割的,在Fermi上。

  

Q3。如果warp大小(32)大于调度组大小(16个核心),那有什么意义呢?

同样,我认为这个问题是基于先前的误解。用于为warp提供资源的硬件单元可能在某个功能级别上以16个单位(或其他一些数字)存在,但是从操作级别,warp被调度为32个线程,并且每个指令计划在整个变形过程中,并在一些Fermi hotclock中一起执行

答案 1 :(得分:1)

据我所知:

Q1 - 调度在硬件级别完成,warp是调度单元和warp,它们的通道成分(laneid是warp中线程索引的硬件等价物),SM和此级别的其他组件都是硬件单元它们是通过CUDA编程模型抽象和编程的。

Q2 - 它还取决于网格:如果您正在启动两个包含单个线程的块,则最终会得到两个warp,每个warp只包含一个活动线程。正如我所说的那样,所有的调度和执行都是在基于warp的基础上进行的,硬件有更多的扭曲,它可以调度的越多(尽管它们可能包含虚拟的NOP线程),并试图隐藏延迟/更少的指令流水线停滞。

Q3 - 一旦分配了资源,线程总是分为32线程warp。在Fermi warp调度程序中,每个周期选择两个warp并将它们分配给执行单元。在前费米架构上,SM的线程处理器少于32个。现在Fermi has 32 thread processors。但是,完整内存请求一次只能检索128个字节。因此,对于每个事务每个线程大于32位的数据大小,存储器控制器仍然可以将请求分解为半经线大小(https://stackoverflow.com/a/14927626/1938163)。除了

  

SM调度32个并行线程组中的线程   扭曲。每个SM都有两个warp调度程序和两个指令   派遣单位,允许发行和执行两个经线   同时。 Fermi的双w​​arp调度器选择两个warp,和   从每个warp向一组16个核心发出一条指令,   十六个加载/存储单元,或四个SFU。

您在编写时没有在线程级别拥有“调度组大小”,但如果您重新阅读上述语句,您将拥有16个核心(或16个加载/存储单元或4个SFU)准备好来自每个32线程扭曲的一条指令。如果你问“为什么16?”那......这是另一个建筑故事......我怀疑这是一个精心设计的权衡。对不起,我不知道更多。