我正在阅读《了解Linux内核》一书,并且想知道Linux如何在3或2级分页系统中折叠Page Upper Directory或Page Middle目录。
根据我的理解:
这对我来说似乎是矛盾的:如果以上三个假设是正确的,则意味着地址转换将通过以下条目进行:
Page Global Directory Entry -> (Singleton) Page Upper Directory Entry -> (Singleton) Page Middle Directory Entry -> Page Table Entry
但是,为什么同一个页面中间目录条目可以指向不同的页面表条目呢?
我不太记得这本书。我认为它们的意思是不使用“页面上层目录”和“页面中间目录”,而“页面全局目录”是选择页面表的表。你的其余假设似乎都是正确的。假设你在32位模式下拥有虚拟地址0x12345678。0x678是物理页中的偏移量(12位)。中间的10位是页面表中的偏移量,而最高的10位是页面全局目录中的偏移量。
对于没有物理地址扩展的32位体系结构,两个分页级别就足够了。Linux本质上通过说它们包含零位来消除“ Page Upper Directory”和“ Page Middle Directory”字段。但是,将保留页面上目录和页面中间目录在指针序列中的位置,以便相同的代码可以在32位和64位体系结构上工作。内核通过将它们中的条目数设置为1并将这两个条目映射到Page Global Directory的适当条目中,来保持Page Upper Directory和Page Middle Directory的位置。
作者在这里的意思是消除了中间的两个级别。更改表时(交换过程时)仅维护指针序列。这是为了在32位或64位CPU上保持相同的代码。
你不了解的是要使用32位模式,CPU需要处于32位模式。如果你使用32位Linux,则Linux将不会以64位模式启动处理器。因此,CPU将处于32位模式和64位模式(长模式)之间的“过渡”状态。这是由Intel和AMD完成的,以便它们的CPU保持向后兼容性。因此,你可以将CPU引导到32位模式,并决定不切换到64位模式。这是通过将某些位设置到处理器的控制寄存器中来完成的。当处理器处于32位模式时,它仅使用2级页面表而不是4级表来转换虚拟地址。
谢谢!是的,在32位模式下的CPU将仅使用2个级别的页表是有道理的,感谢您指出我的误解!只是为了确认一下,因此对于32位体系结构,没有用于Page Upper Directory和Page Middle Directory的特定条目,只是内核将Page Upper Directory条目(和Page Middle Directory条目)映射回了相应的条目。 Page Global Directory条目:与0x12345678一样,Page Upper Directory条目与0x12345678的10个最高有效位的Page Global Directory条目相同,对吗?
我不确定内核到底能做什么。这很复杂。我必须进一步阅读。重要的是要理解内核以某种方式忘记了这些级别。另一件事是RAM中的实际表没有任何对PUD或PMD的引用。这是必需的,因为处理器只是一台机器。对于32位模式,它将使用2级页面表转换虚拟地址,而不管它在RAM中找到什么内容。内核必须确保全局目录不包含对上层目录或中间目录的任何实际引用。