dai*_*isy 31 linux x86 kernel cpu-architecture
x86架构上的Linux内核的默认内存页面大小是4 KB,我想知道这是如何计算的,为什么?
Hri*_*iev 34
默认页面大小由CPU的MMU(内存管理单元)支持.在32位保护模式下,x86支持两种页面:
并非所有x86处理器都支持大页面.需要具有页面大小扩展(PSE)功能的CPU.这不包括奔腾前处理器.实际上,所有当前的x86 CPU都实现了它.
4 KiB在其他架构中也是广泛的popuplar页面粒度.有人可能会争辩说,这个大小来自于将32位虚拟地址划分为页目录/表中的两个10位索引,剩下的12位给出4 KiB页面大小.
sle*_*ort 22
设计4KB普通页面大小的32位架构实际上非常有趣:)
我想补充一个额外的答案来证明它是合理的.
x86使用"2级页表"将虚拟内存地址转换为物理内存地址.
因此,假设页面目录和页面表都包含 条目,页面大小是
字节.充分利用
地址,我们有:
页面目录/表中的每个条目占用4个字节(32位),因此:
因此y = 12,并且页面大小以字节为单位 =
= 4KB.
那么'1级页表'怎么样?这很有趣,因为从逻辑上讲,我们可以使用单个页面表进行地址查找.
假设页面目录包含 条目,每个映射一个地址到相应的页面,页面大小是
字节.
再次,充分利用 地址,我们需要:
和:
我们得到y = 17,页面大小是 =
= 128KB.
我们也可能会争辩说,在"2级页面表"版本中,页面目录和页面表可能具有不同的大小.但是,这意味着我们将使用更大的页面目录,这将占用多个内存页面.遗憾的是,每次生成新的用户进程时,对于自己的页面目录,操作系统必须分配连续的页面,这在设计上并不优雅.
第一款支持分页虚拟内存技术的英特尔处理器是英特尔80386.处理器支持单页大小,4 KB.自1985年发布以来,我们必须回到那段时间才能理解英特尔选择特定页面大小的原因.
Atlas是第一台支持页面大小为3 KB的分页的计算机,它对虚拟内存的设计和动机相关研究产生了深远的影响.该系统设计于1958年至1962年之间.值得注意的是,80386支持的页面大小有点接近Atlas支持的页面大小,即使80386设计大约20年后,计算机(以及它们运行的工作负载)在此期间发生了根本性的变化.时间!事实上,那个时期的许多计算机使用的页面大小介于0.5-5 KB之间.当时的研究人员实际上花了大量精力研究虚拟内存系统(分页和分段).
其中一个重要问题是:最佳页面大小是多少?在60年代和70年代发布了大量作品,试图研究和理解页面大小对应用程序性能的影响,并推荐或提供有关如何选择页面大小的指南.肯定有很多论文从未发表过.据我所知,这包括来自英特尔的文档"...因此,页面大小应为4 KB." 但影响页面大小或与页面大小相关的因素以及选择页面大小(或多个页面大小)的过程是众所周知的,这就是我将在本答案中讨论的基本层面.我还将特别解释为什么页面大小为4 KB是合理的.
在寻呼方法中,物理存储器被组织为一系列连续的存储器区域,称为页面帧,具有相同的大小(这是寻呼1的定义特征).每个页面框架可以映射到虚拟地址空间的同等大小的块,称为虚拟页面.
假设页面由N
字节2组成(这意味着页面框架的N
大小也是字节大小)并考虑由P
页面组成的虚拟地址空间(即页面编号为{0,1,2,... ,P
- 1}和虚拟地址的总数是N
*P
).还假设物理地址空间由F
页面帧组成(即,页面帧号是{0,1,2,...,F
- 1},并且物理地址的总数是N
*F
).
给定虚拟地址VA
,需要一种机制(映射设备)来确定物理地址PA
,它被映射到或者如果未映射则应该引发页面错误.映射设备使用存储在某处的数据结构(页表)来执行映射.对于每个已分配的虚拟页面,该表中应该有一个条目,用于描述页面的映射方式以及可能的一些其他属性(例如保护属性).正如您将看到的,页表条目的设计与页面大小进行交互.我稍后将讨论英特尔80386中页表条目的设计.
虚拟地址的大小是log 2(N
*P
),物理地址的大小是log 2(N
*F
).一些比特VA
表示页面内的偏移,而其他比特表示页码,其使用映射设备识别页面.
我们为页面大小提供了多少选项?好吧,它可以是一个字节,直到N
*P
或N
*F
,以较小者为准.这有很多选择.
虚拟地址VA
等同于一对页码和偏移量(PN
,OFF
).翻译过程应尽可能高效.程序员3方便地使页面内的字节在地址空间中是连续的.以这种方式,可以通过对单个地址的简单算术来计算多字节数据结构内的项的地址,这将构成数据结构的基地址.这可以通过使用虚拟地址的最低有效log 2(N
)位(四舍五入)来表示偏移量来实现,而其余位用来表示页码.
如果N
不是2的幂,则在偏移量和页码之间将共享一些位,具体取决于这些位的值.通过使N
功率为2,不存在这种复杂性.因此,使用2的幂的页面大小是很简洁的.所有支持分页的实际处理器都使用2的幂的页面大小(尽管可寻址单位可能不是8位),这是有道理的.但说实话,目前尚不清楚这是否真的重要.使用当今的技术,N
2的幂是否可能对性能或任何其他感兴趣的度量没有任何可衡量的影响.实际上,在将来需要越来越大的页面大小时,可能会出现一些不是2的幂的页面大小更好.但到目前为止,这还没有发生.我想在这里提出的观点是,不应该自动忽略使页面大小不是幂2的设计选项.我相信这是未来虚拟内存系统研究的好机会.
无论如何,请记住,在80年代选择4 KB页面,显示页面大小的极小变化(理论上和实验上)都不重要.因此,2页功率的便利性取得了成功.这减少了以指数方式考虑的页面大小的数量.但我们仍然有很多选择.
由于映射设备在页面级别工作,因此从操作系统的角度来看,分配单元是虚拟页面4.即使应用程序只需要分配1个字节,它仍然必须告诉操作系统为该1个字节分配整个虚拟页面.此问题称为内部碎片.每个应用程序(或者甚至是应用程序的每个组件)都有自己的虚拟地址空间,从中可以以页面大小的块分配内存.每个应用程序都希望不将单个页面用于它分配的单个对象,而是在分配更多页面之前从同一页面分配尽可能多的对象.但是,因为页面属性在页面级别工作,所以同一应用程序可能使用多个用户模式内存管理器(例如使用多个C/C++运行时),并且应用程序很难共享它们未使用的部分页面与其他应用程序一样,系统中的许多页面都可能发生内部碎片.使用较小的页面大小有助于减少浪费的物理(对于整个系统)和虚拟(每个进程)内存的数量.
此外,通常应用程序在其整个生命周期中经历多个阶段,其中它们在不同阶段表现出不同的存储器需求.如果页面大小是16 KB,但许多应用程序的许多阶段可能只需要10 KB以下,那么会浪费大量物理内存,这可能会导致内存不足的情况.如果支持较小的页面大小(例如8或4 KB),则应避免使用.
较小的页面大小对于处理写时复制软页面错误是优选的,因为页面越小,创建它的副本所花费的时间就越少.对于非常小的页面大小,这可能不会产生任何可测量的差异,具体取决于内存总线带宽.
70年代计算机中可用的典型物理内存量在10秒或100秒KB范围内.页面大小为数百KB或更大是没有意义的.实际上,当时的应用程序工作集通常只有几个或几十KB.因此,即使是小到16 KB的页面大小也不太可行,因为只有几页可能会占用所有可用的物理内存.页面大小应与物理内存量保持一致.这个论点当然可以应用于今天的系统(例如,拥有128-GB的页面是没有意义的).
因此,考虑到70年代和80年代早期的工作集大小和物理内存可用性,页面大小应该是2 0 -2 14范围内的2的幂.很酷,现在我们只有15种选择可供选择.
我们还可以争辩说,更大的页面尺寸更好.对于相同的工作集,较小的页面大小意味着每个应用程序的页面数量较多,这需要页表条目才能启用转换.这基本上需要更大的页表,而不管页表的结构如何(尽管确切的开销取决于页表项本身的设计,我将在后面讨论).想象一下,例如4字节页面和数十KB的典型工作集.然后,实际上将分配大部分物理内存来保存页表,而不是数据.将页面表分页到附加存储会导致单个内存引用出现双页错误,这对于性能来说是非常糟糕的.这样的设计显然是荒谬的.
从本质上讲,页面大小不应该(很大)小于可能的最小可能工作集大小.这会立即排除大小为2 0 -2 6的页面,为我们留下8个选项.研究页面大小的70年代和80年代早期的论文大多只研究这8个选项.
还有另一个原因可以使更大的页面尺寸变得有利.虚拟内存的一个好处是除了主内存之外还能够透明地使用辅助存储来保存易失性数据.但是,二级存储设备是机械的,并且在批量传输时性能最佳.这更像是一个指南,我们不应该排除任何页面大小.有些设备具有不同的设计和特性,最终,批量传输的性能优势将在某些时候饱和.但在衡量页面大小对性能的影响时,肯定会考虑到这一点.如果考虑的应用程序类型表现出很小的空间局部性,那么较小的页面大小仍然是优选的,因为从磁盘复制额外的字节并不是完全免费的.
参考的空间局部性鼓励使用某些页面大小.对于非常小的页面大小,页面中的所有字节很可能会在很短的时间内使用.随着页面的大小变大,不太可能使用的字节数增加.但是,对于非常大的页面,所有工作集都可以适合少量页面,而与地点无关.因此,为了最大限度地减少页面错误的数量,页面大小应该太小或太大,但不能介于两者之间.但最终,这种情况因应用程序而异.新兴的编程范例,例如面向对象的编程和函数编程,以及诸如多线程的技术实际上可能由于链接结构的广泛使用以及由于不同应用程序彼此交互的方式而减少空间局部性.较大的页面大小更适合减少页面错误的数量.但是,较小的页面大小可能更适合多个应用程序之间共享的内存,以减少共享页面的内部碎片.实验还表明,可以保存在主存储器中的页面帧数与页面错误数相关,有利于较小的页面大小.
TLB的需求在当时得到了充分认可.英特尔称他们的专利中存在页面缓存(不确定英特尔是否首先使用该术语).快速TLB非常重要,因为地址转换是执行指令的关键路径.为了使它们尽可能快,它们应该变得很小,但是它们只能缓存少量的页表条目.这促使使用更大的页面大小.
在搜索最佳页面大小时,事实证明没有一个.当时已知需要支持多个页面大小.事实上,1965年设计的Multics系统支持64或1,024字的页面(一个字的大小为36位).在不同情况下,在2 7 -2 14范围内的页面大小在经验和理论上都被证明是最佳的.英特尔必须观察到,4 KB页面可以为客户在80年代使用的应用程序带来最佳平均性能.对于今天的计算机和应用程序来说,页面大小的微小差异并没有像过去那样在70年代和80年代产生太大的差异.
在英特尔专利中详细讨论了页面目录条目和页表条目的设计.这很重要,因为在许多关于页面大小的研究中考虑了页表条目的大小和页表的整体结构,因为它们都相互交互.我不想更详细地讨论这个问题,以保持答案的简短.
英特尔已获得专利几个月前,显然提出了具有64 KB的默认页面大小的系统,但同时支持4 KB页(和其他IA-32E页面大小)的向后兼容性.我从专利中引用:
由于支持将64 KB页面映射到4 KB子页面,VA64直接支持4 KB页面上所有当前定义的操作,包括每4 KB页面的独立保护位和任意4 KB对齐的地址映射.VA64还支持4 KB边界上的OS内核页面管理,即使操作系统内核以64 KB为单位分配内存也是如此.由于支持大页面,VA64支持虚拟地址范围的所有部分,以及现有寻呼系统(如Intel Corporation的IA-32e寻呼系统)支持的页面.因此,VA64支持使用4 KB页面Windows®操作系统内核的应用程序和硬件设备,同时还可以在使用64 KB页面时充分利用64 KB页面.
OS64的功能可以由OS内核逐步采用,而不是要求它们在第一代支持VA64的OS内核中得到支持.例如,VA64功能的OS内核可以通过所有页面映射到当前大小启动(例如,4 KB/2 GB/1 TB在英特尔公司的IA-32E寻呼系统),但改变到一个新的页表格式.页表格式更改后,可以修改操作系统内核以64 KB为单位映射虚拟内存,并更改为在其空闲列表中存储64 KB页面.然后,只要对齐和保护允许,OS内核就可以开始使用64 KB页面,并添加对其他VA64功能的支持.
除了专利中所写的内容之外,我对VA64寻呼系统一无所知.互联网上的任何地方都没有任何东西.我想我们会很快发现.
Denning,PJ(1970).虚拟内存.ACM Computing Surveys第2卷第3期,153-189.
Gelenbe,E.,Tiberio,P.,&Boekhorst,JCA(1973).需求分页系统中的页面大小.Acta Informatica,3(1),1-23.
Alanko,TO,&Verkamo,AI(1983).虚拟内存中的分段,分页和最佳页面大小.绩效评估,3(1),13-33.
Corbató,FJ,和Vyssotsky,VA(1965).Multics系统的介绍和概述.在1965年11月30日至12月1日的会议录中,秋季联合计算机会议,第一部分(第185-196页).
(1)实际上,单个虚拟页面的大小可以是页面框架大小的倍数,但是不要去那里.
(2)我们可以推广公式并使用术语"字"来表示存储器的最小可寻址单位而不是字节,但这在这里并不重要.
(3)可能不是程序员,取决于编程语言,而是编译器,链接器,汇编器和使用二进制代码的工具.
(4)当然可以设计一个支持同时使用分页和非分页的系统,从而可能支持多个分配单元,但是我们不能去那里.
归档时间: |
|
查看次数: |
27285 次 |
最近记录: |