寄存器是真的吗?它们在物理上存在于 CPU 中吗?

Are registers real? Do they exist in CPU physically?

我开始学习x86_64汇编,我注意到的一件事是寄存器的使用,如rdi、rbp、rax、rbx。它们是否存在于 CPU 中,或者这是汇编程序使用的某种抽象机制?

例如,如果我这样做

mov       rax, 60

这是否在硬件中找到了具有此指定名称的寄存器?

CPU 硬件无法通过 name 找到寄存器,由汇编程序将 rax 之类的名称翻译为 3或机器代码中的 4 位寄存器 numbers(并且寄存器名称暗示的操作数大小也通过操作码和(缺少)前缀进行编码)。

例如add ecx, edx 组装成 01 d1Opcode 01 is add r/m32, r。第二个字节,ModRM 0xd1 = 0b0b11010001,对操作数进行编码:高 2 位 (11) 是寻址模式,普通寄存器,而不是内存(对于本例中的目标,因为它是 01 add r/m32, r 而不是 03 add r32, r/m32).
中间3位是/r字段,010 = 2是edx的寄存器号。
低3位是r/m字段,001是ECX的寄存器号。
(编号为 EAX、ECX、EDX、EBX,...,可能是因为 8086 是 designed for asm source compatibility with 8080 - 即在每条指令的基础上“移植”足够简单,机器可以自动执行。)

这就是 CPU 实际解码的内容,以及它用来“寻址”其内部寄存器的内容。没有 register renaming 的简单有序 CPU 可以直接使用这些数字作为实现寄存器文件的 SRAM 中的地址。 (特别是如果它是像 MIPS 或 ARM 这样的 RISC。x86 很复杂,因为您可以使用具有不同宽度的相同寄存器编号,并且您有部分寄存器,如 AH 和 AL 映射到 AX 的一半。但这仍然只是一个问题将寄存器编号映射到 SRAM 中的位置,如果您没有进行寄存器重命名。)


对于 x86-64,寄存器编号始终是 4 位,但有时前导零是隐式的,例如在没有 REX 前缀的指令中,如 mov eax, 60。寄存器编号在该特殊编码的操作码的低 3 位中。

物理上,现代 CPUs 使用物理寄存器文件和寄存器重命名 table (RAT) 来实现架构寄存器。因此他们可以在多个时间点跟踪 RAX 的价值。例如mov eax, 60 / push rax / mov eax, 12345 / push rax 可以 运行 两条 mov 指令并行写入单独的物理寄存器。但仍在整理每个 push 应该阅读哪一个。


if thats the case, i am wondering why there are only 16 registers in x86_64 architecture ...

为 x86 竞争的高性能用例设计的新 ISA 很可能 有 32 个整数寄存器。但是将其硬塞到 x86 机器代码中(就像 AVX-512 对矢量 reg 所做的那样),不值得代码大小的成本。

x86-64 是从 1979 年设计的 16 位 8086 演化而来的。当时做出的许多设计选择都不是您现在以现代晶体管预算重新开始时会做出的选择。 (并且不针对与 8 位 8080 的 asm 源代码级兼容性)。

更多的架构寄存器在每个操作数的机器代码中花费更多的位。更多的物理寄存器意味着更多的无序执行能力来处理更多的寄存器重命名。 (物理寄存器编号是一个内部细节。)This article 测量隐藏缓存未命中延迟的实际乱序 window 大小,并将其与已知的 ROB 和 PRF 大小进行比较 - 在​​某些情况下 CPU 运行s out of physical registers to renamed onto, before it fills the ROB, for that selected mix of filler instructions.


, doesn't more registers means more performance ?

更多的体系结构寄存器通常确实有助于提高性能,但会逐渐减少 returns。与 8 相比,16 避免了很多 store/reload 工作,但增加到 32 只会节省更多 store/reload 工作; 16 通常足以让编译器将他们想要的所有内容保存在寄存器中。

AMD 设法将其扩展到 16 个寄存器(从 8 个增加)这一事实已经是一项重大改进。是的,32 个整数 regs 有时会好一些,但如果不重新设计机器代码格式或使用更长的前缀(如 AVX-512 的 4 字节 EVEX 前缀,它允许 32 个 SIMD 寄存器,x/y/zmm0..31 用于 AVX-512 指令。)

另请参阅:

相关问答:

  • How many EAX register do modern processor have?