流水线处理器基础知识
基础概念
1. 流水线的结构本质上是增加更多的寄存器来提高指令的吞吐率,并以此来提高处理器的性能。
2. 流水线带来的加速比约等于流水线级数,5级流水线带来的加速比接近5(指令足够多时)。
3. 经典流水线的五个阶段:IF(取指),ID(译码),EX(执行),MEM(访存(如有必要)),WB(写回(如有必要))。
4. 流水线时在顺序指令流中的指令间并行技术。
流水线冒险
1. 结构冒险:两个指令同时对一个资源进行使用时,容易出现结构冒险。
2. 数据冒险: 两个前后指令同时依赖一个数据,比如:
add x19,x0,x1
sub x2,x19,x3
此时,指令1的输出被指令2依赖,然后指令2进行译码阶段时,指令1还没有进行到WB阶段,寄存器的值还并没有刷新,指令2的计算结果就会出现问题。
3. 数据冒险解决办法: 增加旁路(bypassing)或前递(forwarding)。 这是指,在2的例子中,x19的新值是可以在EX阶段后将值直接传递给指令2的EX阶段之前(ID阶段之后),由于指令2比指令1慢一个阶段,bypassing可以刚刚好解决这个问题。
4. 流水线停顿(pipeline stall 俗称: bubble): 虽然bypassing是很好的解决方案,但是这并不能避免所有的冒险。比如 ld指令取指一个值,然后一个紧跟的算术指令依赖这个被ld取的值,那么前递就无法解决问题。因为ld指令需要访存(MEM)阶段才能成功取值,此时后面的算术指令已经过了EX阶段,我们无法使用bypassing传递此时的值给第二条指令的ID阶段后,因为这是时光回溯(不可能的)。所以我们必须停顿流水线一个节拍后,那么对应的,第二条指令就会慢一拍,那么指令就刚执行到ID阶段后,此时,再使用bypassing,就可以解决问题。
5. 控制冒险:控制冒险是当遇到分支指令会发生的情况,所以也被叫做分支冒险。因为指令在完成IF阶段后,就会对PC进行运算,此时PC中的下一条指令已经进入流水线,但是很可能因为分支指令,这条指令其实是不该被运算的,那么就会出现冒险的情况。处理分支冒险比较复杂,简单的思路是,我们需要在ID阶段计算分支目标地址以及更新PC,所以这需要额外的资源,并且需要停顿流水线,来保证下一条指令不会被执行错误。然而,如果本身分支判定会失败,这意味着我们白白停顿了一次流水线。为了解决这个问题,需要使用分支预测。
分支预测
1. 分支预测是通过预测下一条指令可能的位置来尽量实现处理器流水线全速运转。
2. 简单预测: 总是预测分支不会成立,也就是总是预测分支不会发生,那么当预测成功的时候处理器就会全速运行。当分支发生时,使用流水线停顿的方法(并清空下一条指令),然后将目标指令加入流水线。
3. 动态预测:一种常见的动态预测方法是 保存每个条件分支是否发生分支的历史记录,然后根据最近的一次行为来预测未来。历史记录的数据足够多时,动态分支正确率达到90%。当预测错误时,需要重启流水线,因为在取指阶段其实就会预测,所以当进行到ID以及EX时才能知道是否进行分支时,被预测的指令已经加入流水线,为了保证程序正确运行,需要重新从真正的新指令来开始流水线的运行。
Comments
Post a Comment