为什么ARM的PC寄存器指向的指令要执行的下一个后? [英] Why does the ARM PC register point to the instruction after the next one to be executed?

查看:1329
本文介绍了为什么ARM的PC寄存器指向的指令要执行的下一个后?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

据ARM的芯片。

在ARM状态下,PC的值是当前指令的地址加上8个字节。

In ARM state, the value of the PC is the address of the current instruction plus 8 bytes.

在Thumb状态:


      
  • 对于B,BL CBNZ,和CBZ指令时,PC的值是当前指令加上4字节的地址。

  •   
  • 对于使用标签所有其他指令,PC的值是当前指令加上4字节的地址,与位[1]清0的结果,使其字对齐的。

  •   

简单地说,PC寄存器指向的指令的下一个指令之后的值。这是我没有得到的东西。通常(尤其是在x86)程序计数器寄存器用来指向要被执行的下一条指令的地址。

Simply saying, the value of the PC register points to the instruction after the next instruction. This is the thing I don't get. Usually (particularly on the x86) program counter register is used to point to the address of the next instruction to be executed.

那么,什么是premises背后是什么?条件执行,也许?

So, what are the premises underlying that? Conditional execution, maybe?

推荐答案

这是传统的抽象泄漏的讨厌的一点。

It's a nasty bit of legacy abstraction leakage.

最初的ARM设计有一个3级流水线(取德code-执行)。为了简化他们选择了在PC读为目前的指令的值取地址线,而不是从2个周期前的当前执行指令的设计。由于大多数PC相对地址是在链接时计算的,它更容易有器/连接器弥补了2指令所抵消设计所有的逻辑正确的PC寄存器。

The original ARM design had a 3-stage pipeline (fetch-decode-execute). To simplify the design they chose to have the PC read as the value currently on the instruction fetch address lines, rather than that of the currently executing instruction from 2 cycles ago. Since most PC-relative addresses are calculated at link time, it's easier to have the assembler/linker compensate for that 2-instruction offset than to design all the logic to 'correct' the PC register.

当然,这一切都坚定地对的事情,30年前是有道理的堆。现在想象如何才能保持一个有意义的值在寄存器今天的15+级,多发射,乱序管道,你可能AP preciate为什么它很难找到一个CPU的设计师,这些天谁认为露出PC作为寄存器是一个不错的主意。

Of course, that's all firmly on the "things that made sense 30 years ago" pile. Now imagine what it takes to keep a meaningful value in that register on today's 15+ stage, multiple-issue, out-of-order pipelines, and you might appreciate why it's hard to find a CPU designer these days who thinks exposing the PC as a register is a good idea.

不过,上档,至少是不是很可怕的延迟槽的。相反,违背了你想什么,有每个指令执行所有条件真的围绕prefetch抵消只是另一种优化。而不是总是有分支条件左右code(或仍在执行任何剩下的管道像一个疯狂的人),你能避免极短的树枝完全时采取管道冲洗延误;管道保持忙碌,和去codeD指令可以只作为NOP执行时,标志不匹配 * 。同样,这些天我们已经有效分枝predictors和它最终被更多的是帮倒忙的,但对于1985年这很酷。

Still, on the upside, at least it's not quite as horrible as delay slots. Instead, contrary to what you suppose, having every instruction execute conditionally was really just another optimisation around that prefetch offset. Rather than always having to take pipeline flush delays when branching around conditional code (or still executing whatever's left in the pipe like a crazy person), you can avoid very short branches entirely; the pipeline stays busy, and the decoded instructions can just execute as NOPs when the flags don't match*. Again, these days we have effective branch predictors and it ends up being more of a hindrance than a help, but for 1985 it was cool.

<子> * <一个href=\"https://soundcloud.com/university-of-cambridge/a-history-of-the-arm-architecture-and-the-lessons-learned-while-building-it\"相对=nofollow> ...的指令与这个星球上最NOP指令集。

这篇关于为什么ARM的PC寄存器指向的指令要执行的下一个后?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆