操作系统之段页式内存管理
分段
分段可以说是Intel的CPU一直保持着的一种机制,而分页只是保护模式下的一种内存管理策略。不过想开启分页机制,CPU就必须工作在保护模式,而工作在保护模式时候可以不开启分页。
首先是全局段描述符表:
结构体后的__attribute__((packed))是GCC的扩展,用来设置该结构体不进行字节对齐。
段描述符表定义:
GDTR定义:
段描述符表的部分以二进制位来表示的设置信息合并到了相应的字节里,这里按照位域去定义不是不可以,但是太过于臃肿了。
全局描述符表的定义以及设置一项描述符的函数实现:
初始化函数:
最后有一个加载全局描述附表的函数,这个函数用汇编来实现了。代码如下:
CPU在保护模式下分页未开启和分页开启的不同状态时,MMU组件处理地址的流程。
如果没有开启分页:
逻辑地址->段机制处理->线性地址=物理地址
如果开启分页:
逻辑地址->段机制处理->线性地址->页机制处理->物理地址
因为我们采用了平坦模式,所以给出的访问地址实际上已经是线性地址了(段基址为0),那么剩下的问题就是所谓的页机制处理了。
分页
在逻辑上把内存划分为定长的物理页,同时将一个程序执行时候的线性地址地址空间划分为逻辑页,在分页机制工作的前提下,给硬件提供一组数据结构来保存这种映射关系。也就是说,线性地址是连续的,但是其实际指向的物理地址就不见得是连续的了。
以32位的地址来说,分为3段来寻址,分别是地址的低12位,中间10位和高10位。高10位表示当前地址项在页目录中的偏移,最终偏移处指向对应的页表,中间10位是当前地址在该页表中的偏移,我们按照这个偏移就能查出来最终指向的物理页了,最低的12位表示当前地址在该物理页中的偏移。就这样,我们就实现了分级页表。
本博客所有文章除特别声明外,均采用 CC BY-NC-SA 4.0 许可协议。转载请注明来自 Ansore!











