CPU 如何提高吞吐量

210 阅读5分钟

之前我们分析过 CPU 是如何工作的,经过「取指、译码、执行、访存、写回、更新」等几个阶段,说成白话就是:

取指:从内存获取要执行的地址(PC);

译码:拿到 PC 地址后,根据地址提示去哪个寄存器取数据;

执行:取到数据后,执行计算「加减乘除」;

访存:计算完成后,根据地址提示去哪个寄存器写数据;

写回:根据寄存器地址,把结果通过端口输出计算结果;

更新:流程结束后,更新 PC 地址,来执行下一次的操作。

有限循环上面的工作逻辑。

具体流程如图所示:

image.png

上面 3 条指令,一条指令完成后,才能开始下一条。也就是说第 1 条指令在执行期间,第 2 条指令只能等待。

我们以每秒十亿条指令为单位来描述吞吐量,按上面的指令逻辑来计算:吞吐量为每秒 30 亿条指令。

流水线吞吐量的计算公式是:

吞吐量 = 每个阶段处理的指令数 / 流水线的时钟周期

这样有个很明显的问题,等待时间太长了。

于是聪明人想到了一个好办法:让 CPU 增加流水线作业。

流水线有个重要的特征,它提高了系统的吞吐量,在单位时间内,提高了执行指令的数量。不过,会增加一些延迟,也就是一整条指令完成的时间(因为会增加中间流程状态)。

如何做到的呢?

拿江南皮革厂举例:

1染色、2补边、3烘干、4包装,里面的工序分工明确,哪个阶段负责什么作业,各自负责自己的作业。当一只鞋离开当前工序时,另一只新鞋就可以进入了。所以 … 当第一只鞋进入补边阶段,第二只鞋就可以进入染色阶段了。

如下图:

image.png

图片来自于普客园(zhangly)

在 CPU 周期里,第一条指令进入译码阶段的时候,指令2就可以进入取指阶段。这样流水化一套流程下来,吞吐量达到了 80 亿条指令。

那是不是我一直堆硬件,一直增加并行指令的逻辑就可以无限增长了?

其实 … 流水线也有自己的局限性。

不一致的化分

如果处理器的一些硬件单元无法划分成多个较小的单元,那它需要更多的时间来完成作业,而另一些指令完成时间会很快。这样的差异会导致某些阶段时间特别长,难以优化。

木桶原理:以最端的板为

所以,需要尽量将处理器划分成多个任务阶段,每个阶段负责处理特定的任务,尽量保持时间相对一致,来平衡整个处理过程的性能。

将系统设计成具有相同作业的阶段,是一个严峻的挑战。

流水线不能过深

在处理器中,为了实现流水线的切换和同步,需要加入「流水线寄存器」,流水线寄存器用于在各个阶段之间传递数据和控制信号,保证数据的执行和正确性。

当流水线划分成多个阶段的时候,每个阶段都需要一定的时间来完成切换处理,在一个时钟周期内,一个指令仅完成一个阶段的处理,然后传递给下一个阶段。阶段执行时间大于时钟周期,就会产生错误,小于时钟周期会产生等待。

如果把流水线分成 6 个阶段,每个阶段需要 50ps,在每个时钟周期内同时会有 6 条指令在流水线中执行,那吞吐量可以达到 140 亿条。

为了提高效率,现代的处理器采用了很深的流水线(15条或者更多)。处理器架构师将指令的执行划分成很多简单的步聚,这样每个阶段使用的时间就会更小,从而整体提高效率。

而较深的流水线可能会增加指令间的依赖关系和冲突,导致流水线停顿和清空。所以在处理器设计的时候,需要考虑流水线深度、指令复杂性。

总结两句

流水线技术是提高CPU性能的关键。它将指令划分成多个阶段,允许同时执行多条指令,从而显著提高吞吐量。

然而,设计流水线需要考虑阶段任务的均衡分配和流水线深度的合理选择,以避免繁重阶段成为瓶颈,并处理指令间的冲突。

流水线深度的增加可以增加吞吐量,但也可能引入依赖关系和停顿。因此,在处理器设计中需要综合考虑这些因素,以实现更高效的CPU性能。


内容来源:《深入理解计算机系统》

如果您对本篇文章中提到的问题有任何疑问或想法,请在评论区留言,我将尽力回复。

微信公众号「小道研究」,获取更多关于前端技术的深入分析和实践经验。