当前位置: 首页 > 知识库问答 >
问题:

为什么更长的管道会使单个延迟槽不足?

简培
2023-03-14

我读了Patterson的以下声明

随着处理器进入更长的流水线并在每个时钟周期发出多条指令,分支延迟变得更长,单个延迟槽是不够的。

我可以理解为什么“每个时钟周期发出多条指令”会导致单个延迟槽不足,但我不知道为什么“更长的管道”会导致它。

另外,我不明白为什么更长的管道会导致分支延迟变得更长。即使管道更长(完成一条指令的步骤),也不能保证周期会增加,那么为什么分支延迟会增加呢?

共有1个答案

宫俊远
2023-03-14

如果您在检测分支的阶段之前添加任何阶段(并评估有条件分支的已采取/未采取),1个延迟槽不再隐藏进入管道第一阶段的分支和正确的程序之间的“延迟”分支被知道后的计数器地址。

第一个获取阶段需要管道中稍后的信息来知道下一步要获取什么,因为它本身不会检测分支。例如,在具有分支预测的超标量CPU中,他们需要预测下一步要获取的指令块,分别和更早地预测分支在解码后的走向。

1个延迟时隙仅在MIPS I中足够,因为在EX的前半个时钟周期中评估分支条件,以便及时转发到IF的后半部分,在此之前,IF不需要获取地址。(原始MIPS是一种经典的5级RISC:IF ID EX MEM WB。)有关更多详细信息,请参阅维基百科关于经典RISC管道的文章,特别是控制危险部分。

这就是为什么MIPS仅限于简单的条件,如beq(从异或中查找任何不匹配项)或bltz(符号位检查)。它不能做任何需要加法器进行进位传播的事情(因此两个寄存器之间的通用blt只是一条伪指令)。

这是非常有限制的:较长的前端可以吸收来自更大/更关联的L1指令缓存的延迟,该缓存需要超过半个周期才能对命中做出响应。(不过,MIPS I解码非常简单,其指令格式是有意设计的,因此机器代码位可以直接作为内部控制信号连接。因此,您可以将解码作为“半周期”阶段,读取获得1个完整周期,但即使是1个周期仍然很低,在更高的时钟速度下循环时间更短。)

提高时钟速度可能需要添加另一个获取阶段。解码确实必须检测数据危险并设置绕过转发;最初的MIPS通过不检测负载使用危险来简化这一点,相反,软件必须在MIPS II之前尊重负载延迟槽。超标量CPU有更多可能的危险,即使有1周期ALU延迟,因此检测必须转发到需要更复杂逻辑的内容,以便将旧指令中的目标寄存器与年轻指令中的源进行匹配。

超标量管道甚至可能需要在指令提取中进行一些缓冲以避免冒泡。多端口寄存器文件的读取速度可能稍慢,可能需要额外的解码管道阶段,尽管这可能仍可以在1个周期内完成。

因此,除了由于超标量执行的本质而使1个分支延迟槽不足外,如果额外的阶段位于fetch和分支解析之间,那么更长的管道也会增加分支延迟。e、 g.一个额外的fetch阶段和一个2宽的管道可以在分支后有4条指令,而不是1条。

但实际解决方案不是引入更多的分支延迟时隙来隐藏这种分支延迟,而是分支预测。(然而,一些DSP或高性能微控制器确实有2甚至3个分支延迟时隙。)

分支延迟槽使异常处理复杂化;您需要一个故障返回和一个后续地址,以防故障发生在已获取分支的延迟槽中。

 类似资料:
  • 问题内容: 我需要在循环中对数据库进行SQL查询: 更好的方法是:保持原样或循环后移动: 或者是其他东西 ? 问题答案: 整个要点是直到函数返回才执行,因此将其放置在要关闭的资源打开后的适当位置。但是,由于要在循环内创建资源,因此根本不要使用defer- 否则,在函数退出之前,您不会关闭在循环内创建的任何资源,因此它们会堆积直到然后。相反,您应该在每次循环迭代结束时关闭它们, 而无需 :

  • 问题内容: 我很难处理Java垃圾回收问题并解释日志。 我的应用程序要求GC的时间不要超过2秒,理想情况下是少于100ms。 根据先前的一些建议,我正在尝试以下命令行选项: 该应用程序具有大量长期存储的对象,这些对象保存在ConcurrentLinkedHashMap中。我偶尔会出现长时间的停顿,在最坏的情况下可能会长达10秒(这是倒数第二次,如下面的GC日志所示)! 这是我得到的一些输出: 我已

  • 当我阅读RISC-V用户级ISA手册时,我注意到它说“OpenRISC有条件代码和分支延迟槽,这使更高性能的实现变得复杂。”所以RISC-V没有分支延迟槽RISC-V用户级ISA手动链接。此外,维基百科说,大多数较新的RISC设计都省略了分支延迟槽。为什么大多数较新的RISC架构逐渐省略了分支延迟槽?

  • 我的要求是将数据发送到不同的ES接收器(基于数据)。例如:如果数据包含特定信息,则将其发送到sink1,否则将其发送到sink2等(基本上是根据数据动态发送到任何一个接收器)。我还想分别为ES sink1、ES sink2、ES sink3等设置并行度。 有什么简单的方法可以在flink中实现上述目标吗? 我的解决方案:(但并不满意) 我可以想出一个解决方案,但有中间Kafka主题,我写(topi

  • 我在计算一个简单蒸汽的最大值,结果是: (S11000,S1,值:999) (S12000,S1,值:41) 最后一行数据明显迟到了: 为什么按第一个窗口(0-1000)计算? 我认为第一个窗口应该在到达时触发。 对于这个结果,我很疑惑。 MyReductingMax(),MyWindowFunction()

  • 我有一个ScheduledExecutorService,我想用它来计划一个具有一定延迟的Runnable的执行。然而,当我调用它的schedule方法时,延迟被完全忽略,Runnable被立即执行。这是我的代码: 我的SchduledExecutorService构造函数: 这是对其调度方法的调用(由日志包围): 日志允许我看到,“计划前”和“设置清除…”之间只有20-30毫秒的延迟,而不是我预