为什么 x86-64系统只有48位的虚拟地址空间?

我在一本书中读到了以下内容:

32位处理器有2 ^ 32个可能的地址,而当前的64位处理器有一个48位的地址空间

我的期望是,如果它是一个64位处理器,地址空间也应该是2 ^ 64。

所以我想知道这个限制的原因是什么?

58149 次浏览

阅读 维基百科文章的限制部分:

一台个人电脑不能包含4拍字节的内存(由于当前内存芯片的大小,如果没有别的) ,但 AMD 设想的大型服务器,共享内存集群,以及其他物理地址空间的使用,可能在可预见的未来接近这一点,52位物理地址提供了充足的扩展空间,同时不会产生实现64位物理地址的成本

也就是说,在这一点上实现完整的64位寻址是没有意义的,因为我们不能构建一个能够充分利用这样一个地址空间的系统——所以我们选择一些对今天(和未来)的系统实用的东西。

因为这就够了。48位给你一个256TB 的地址空间。那可不少。你不会很快看到一个需要更多的系统。

所以 CPU 制造商走了捷径。它们使用的指令集允许完整的64位地址空间,但当前的 CPU 只使用较低的48位。另一种选择是将晶体管浪费在处理更大的地址空间上,而这些地址空间在很多年内都不会被需要。

因此,一旦我们接近48位的限制,只需要释放处理完整地址空间的 CPU,但它不需要对指令集进行任何更改,也不会破坏兼容性。

内部本机寄存器/操作宽度不会反映在外部地址总线宽度中。

假设您有一个64位处理器,它只需要访问1MB 的 RAM。只需要一个20位的地址总线。为什么要为那些你不会使用的额外引脚的成本和硬件复杂性而烦恼呢?

摩托罗拉68000是这样的: 32位内部,但与23位地址总线(和16位数据总线)。CPU 可以访问16MB 的 RAM,加载本机数据类型(32位)需要两次内存访问(每次访问带有16位数据)。

任何关于总线大小和物理内存的回答都有点错误,因为 OP 的问题是关于 虚拟地址空间虚拟地址空间而不是 物理地址空间物理地址空间。例如,一些386上的类似限制是对他们可以使用的物理内存的限制,而不是虚拟地址空间,虚拟地址空间总是32位。原则上,即使只有几 MB 的物理内存,你也可以使用64位的虚拟地址空间; 当然,你也可以通过交换来实现这一点,或者在特定的任务中,你可以在大多数地址映射同一页面(例如某些稀疏数据操作)。

我认为真正的答案是,AMD 只是便宜,并希望没有人会关心现在,但我没有参考引用。

还有一个比仅仅在 CPU 地址路径中保存晶体管更严重的原因: 如果您增加地址空间的大小,您需要增加页面大小,增加页表的大小,或具有更深的页表结构(即更多级别的转换表)。所有这些都会增加 TLB 漏接的成本,从而影响性能。

从我的角度来看,这是由于页面大小。每页最多包含4096/8 = 512个页表条目。2 ^ 9 = 512.所以9 * 4 + 12 = 48。

至少在 Intel 64中,只使用64位 VA 的低阶48位是不正确的。上面的16位是用来。

第3.3.7.1节 Intel 64和 IA-32架构软件开发者手册中的规范称呼说:

规范地址必须将位63到位48设置为0或1(取决于位47是0还是1)

所以从47位到63位构成一个超级位,要么全部1,要么全部0。如果地址不是规范形式,那么实现就会出错。

在 AArch64上,这是不同的。根据 ARMv8指令集概述,它是一个49位的 VA。

AArch64内存转换系统支持49位虚拟地址(每个转换表48位)。虚拟地址是从49位进行符号扩展的,并存储在一个64位指针中。可选地,在系统寄存器的控制下,64位指针的最高8位可能包含一个“标记”,当用作装载/存储地址或间接分支的目标时,这个“标记”将被忽略

很多人都有这种误解。但是我向你们保证,如果你们仔细阅读这篇文章,在阅读完这篇文章之后,你们所有的误解都会变得清晰。

说一个处理器32位或64位并不意味着它应该有32位地址总线或64位地址总线分别!... 我再说一遍,没有! !

32位处理器意味着它有32位 ALU (算术和逻辑单元) ... 这意味着它可以操作32位二进制操作数(或者简单地说一个二进制数有32位) ,同样64位处理器可以操作64位二进制操作数。因此,32位或64位的处理器并不意味着可以安装的最大内存量。它们只是展示了操作数可以有多大... (打个比方,你可以想象一个10位数的计算器可以计算出多达10位数的结果... 它不能给我们11位数或任何其他更大的结果... 虽然它是十进制的,但为了简单起见,我要说这个类比) ... 但是你说的是地址空间,这是内存(RAM)可直接接口的最大大小。RAM 的最大可能大小取决于地址总线的大小,而不是数据总线的大小,甚至也不是定义处理器大小的 ALU 的大小(32/64位)。是的,如果一个处理器有32位的“地址总线”,那么它可以寻址2 ^ 32字节 = 4 GB 的 RAM (或者对于64位它将是2 ^ 64) ... 但是说一个处理器32位或64位与这个地址空间没有任何关系(地址空间 = 它可以访问多远的内存或 RAM 的最大大小) ,它只取决于它的 ALU 的大小。当然,数据总线和地址总线的大小可能是相同的,然后似乎32位处理器意味着它将访问2 ^ 32字节或4 GB 的内存... 但这只是一个巧合,它不会是相同的所有... 例如,英特尔8086是一个16位处理器(因为它有16位 ALU) ,所以如你所说,它应该访问到2 ^ 16字节 = 64 KB 的内存,但它不是真的。它可以访问高达1MB 的内存有20位地址总线... 你可以谷歌,如果你有任何疑问:)

我想我已经说得很清楚了。现在回到你的问题... 作为64位处理器并不意味着它必须有64位地址总线,所以有一个48位地址总线在64位处理器没有什么错... 他们保持地址空间较小,使设计和制造成本低廉... 因为没有人会使用这么大的内存(2 ^ 64字节) ... 其中2 ^ 48字节是足够的现在。

CPU 被认为是“ N 位”的主要原因是它的数据总线大小,以及它的大部分实体(内部架构) : 寄存器、累加器、算术逻辑单元(ALU)、指令集等。例如: 老式的 Motorola 6800(或者 Intel 8050) CPU 是一个8位 CPU。它具有8位数据总线、8位内部架构和16位地址总线。


  • 虽然 N 位 CPU 可能有一些其他的 N 大小的实体。例如,6809对6800的改进(两者都是8位 CPU 和8位数据总线)。在6809中引入的重要增强之一是使用两个8位累加器(A 和 B,可以组合成单个16位寄存器 D) ,两个16位索引寄存器(X,Y)和两个16位堆栈指针。

回答最初的问题: 不需要添加超过48位的 PA。

服务器需要最大的内存量,因此让我们更深入地研究一下。

1)最大的(常用的)服务器配置是8 Socket 系统。一个8S 系统只不过是8个服务器 CPU 通过一个高速相干互连(或简单地说,一个高速“总线”)连接起来形成一个单一的节点。有更大的集群存在,但是它们非常少,我们在这里讨论的是常用的配置。注意,在实际使用中,2 Socket 系统是最常用的服务器之一,8S 通常被认为是非常高端的。

2)服务器使用的主要内存类型是字节寻址的常规 DRAM 内存(如 DDR3/DDR4内存) ,内存映射 IO-MMIO (如插件卡使用的内存) ,以及用于配置系统中设备的位形空间。第一种类型的内存通常是最大的(因此需要最大数量的地址位)。一些高端服务器也使用大量的 MMIO,这取决于系统的实际配置。

3)假设每个服务器 CPU 在每个槽中可以容纳16个 DDR4 DIMM。最大大小为256GB 的 DDR4DIMM。(根据服务器的版本,每个套接字可能的 DIMM 数量实际上少于16个 DIMM,但为了示例的目的,请继续阅读)。

所以理论上每个套接字可以有16 * 256GB = 4096GB = 4TB。 对于我们的示例8S 系统,DRAM 的最大大小可以是4 * 8 = 32TB 处理这个 DRAM 空间所需的最大位数为45(= log232TB/log22)。

我们不会详细介绍其他类型的内存(MMIO,MMCFG 等) ,但是这里的要点是,对于一个8 Socket 系统来说,最“苛刻”的内存类型是最大类型的 DDR4 DIMM (256 GB DIMM) ,它只使用45位。

对于一个支持48位(例如 WS16)的操作系统,还有(48-45 =)3个剩余位。 这意味着,如果我们仅为32TB 的 DRAM 使用较低的45位,我们仍然有2 ^ 3倍的可寻址内存,可用于 MMIO/MMCFG,总共有256TB 的可寻址空间。

总结一下: 1)48位的物理地址足以支持当今最大的系统,这些系统“完全加载”了大量的 DDR4和其他大量需要 MMIO 空间的 IO 设备。确切的说是256TB。

请注意,这个256TB 地址空间(= 48位物理地址)不包括任何像 SATA 驱动器这样的磁盘驱动器,因为它们不是地址映射的一部分,它们只包括可字节寻址的内存,并且暴露给操作系统。

2) CPU 硬件可以根据服务器的生成选择实现46位、48位或 > 48位。但另一个重要因素是操作系统能识别多少位。 今天,WS16支持48位物理地址(= 256TB)。

这对用户意味着什么,即使有一个巨大的,超现代的服务器 CPU,可以支持 > 48位寻址,如果你运行的操作系统只支持48位 PA,那么你只能利用256TB 的优势。

3)总而言之,有两个主要因素可以利用更高的地址位数(= 更大的内存容量)。

A)您的 CPU HW 支持多少位? (这可以由英特尔 CPU 中的 CPUID 指令决定)。

B)你运行的是什么操作系统版本,以及它能识别/支持多少位 PA。

(a,b)的最小值将最终决定系统可以利用的可寻址空间量。

我在写这个回复的时候并没有仔细研究其他的回复。另外,我还没有详细研究 MMIO、 MMCFG 和整个地址映射结构的细微差别。但我真心希望这能有所帮助。

谢谢, Anand K Enamandram, 服务器平台架构师 英特尔公司