【问题标题】:Pipeline stall after a load instruction but not after an add instruction加载指令后但添加指令后流水线停止
【发布时间】:2016-05-23 16:54:44
【问题描述】:

我正在做一些关于管道的问题。这个我需要帮助。

为什么在加载指令之后会出现流水线停顿,而在加载指令之后却不会 添加指令?

我知道管道中未使用的插槽称为管道停顿。我的猜测是,它可能是加载指令后的流水线停顿,因为我们需要等待可能更新的寄存器。但是我想不出为什么添加指令不能创建管道停顿的答案。也许是因为在这个阶段我们已经从寄存器中读取了?

【问题讨论】:

  • Add 通常只有 1 个周期延迟,因此通过转发(也称为绕过),下一条指令可以使用 add 的结果。 This Q&A might be relevant,但我没看过。

标签: cpu-architecture


【解决方案1】:

管道停顿用于解决通常由数据依赖性引起的危险。 add 实际上会产生管道停顿,但让我们首先考虑一个不会产生流水线停顿的示例。

SUB r2, r3
ADD r1, r2

即使加法指令使用减法的结果,也没有停顿。这是因为 EX 阶段可以访问前一个 EX 阶段的数据。

现在让我们考虑一个 add 可以产生停顿的例子。

LOAD r2, RAM[a]
ADD r1, r2

这里,加载指令的 MEM 阶段产生的数据需要作为 ADD 指令的 EX 阶段的输入。 EX 阶段只能访问前一个 EX 阶段的数据,因此会因先读后写的风险而停止流水线。这张图说明了这一点

这是通过在管道中引入气泡(如 NOP)来解决的,该气泡解决了数据依赖性,而无需及时向后传播数据(这是不可能的)。

您可以通过阅读 hazardsbubblesforwarding 来更详细地了解此内容

【讨论】:

  • 添加消耗的负载中的数据并不是真正的add 产生的停顿,IMO。我将其归因于负载,而不是消费者,因为负载在管道中产生结果的时间比 ALU 操作晚。
  • 另外,在经典 RISC 流水线示例的 EX 阶段是否需要准备好加载地址,或者它是否可以在 1c 延迟的情况下进行指针追踪,只需将加载的数据从 MEM 阶段转发回来进入MEM阶段?
  • @PeterCordes 我会争辩说添加是在产生一个停顿。这是因为没有该指令,不会发生停顿。停顿是由导致数据依赖的指令产生的。如果您删除了 add 指令,则不会发生停顿。因此,我认为“添加”确实会产生失速。至于您的第二个问题,通过操作数转发可以实现指针追踪。与“EX”阶段可以从前一个“EX”阶段读取数据的方式相同,“MEM”阶段可以从前一个“MEM”阶段读取数据。
  • 谢谢。我认为 MEM 输出可能必须转到 EX 输入,用于具有偏移的寻址模式。 (不过,我想只有一个寄存器寻址模式,MEM 阶段中的专用 AGU 只是一个加法器,无论如何你都可能需要它。) Re:归咎于 add 或 load:这很公平,实际上只是将它们安排在一起。这个问题,不是任何一个本身。我从这样的角度来看待它,如果add 的输入是由 ALU 指令而不是加载产生的,那么就不会出现停顿。
猜你喜欢
  • 2013-09-08
  • 2015-04-07
  • 2014-11-25
  • 1970-01-01
  • 2015-09-09
  • 2020-10-23
  • 1970-01-01
  • 2016-04-19
  • 1970-01-01
相关资源
最近更新 更多