首页 > 操作系统 > x86 保护模式浅析(二)
2019
05-28

x86 保护模式浅析(二)

走进保护模式

A20 地址线

在本文中,要完全解释 A20 地址线的作用以及原理是不太现实的。对于我们程序员而言,我们只需要了解一些大致的概念。简单来说,因为考虑到向下兼容性,A20 地址线在默认情况下是禁用的。于是,我们得启用它,这样我们就可以访问全部内存,这对于 CPU 在保护模式下正常工作是十分重要的

至于如何启用 A20 地址线,OSDev 上面列举了很多方法,可以参考链接:https://wiki.osdev.org/A20
这里,我们列举比较简单的一种方法,在大多数情况下是可正常使用的(对于一些老主板,需要主板CMOS设置中启用快速 A20 支持 )

  • 快速 A20 门(Fast A20 Gate)
in al, 92h    ; 从 92h 端口读一字节
or al, 2      ; 置字节的第 2 位为 1
out 92h, al   ; 写回 92h 端口

上述的 Fast A20 Gate 方式只需要 3 条指令就可以启用 A20 地址线,当执行完这 3 条指令后,CPU 就有能力访问全部内存了

关闭中断(包括 NMI 在内)

保护模式下,CPU 的中断机制与实模式是不相同的。BIOS 中断、中断向量表都不再适用于保护模式,在进入保护模式之前,需要先使用 CLI 指令以关闭中断

cli    ; 关闭中断

设置 GDTR 寄存器

在上一篇文章中,我们讲到 GDT、段选择子的概念,在进入保护模式前,首先要正确地设置 GDTR 寄存器,确保 GDT 的设置是有效的

lgdt m48    ; 48 位(6字节)向量,低字表示 GDT 界限(字节大小减1),高双字表示 GDT 头部的线性地址

设置控制寄存器的PE位

CPU 内部的 0 号控制寄存器(CR0)中的最低位即是PE(Protection Enable,保护生效)位,将其置为 1 时,CPU 将工作在保护模式下,汇编代码可以像下面这样写

mov eax, cr0
or al, 1      ; 置 PE 位为 1
mov cr0, eax

命运的跳转(jmp dword 方式)

jmp dword 段选择子偏移:跳转到的地址

其中,段选择子偏移就是对应段选择子(一般是代码段选择子)相对于GDT头部的偏移字节数,而跳转到的地址,即是在段选择子的段界限内的地址。因为 PE 位的设置,现在 CPU 在保护模式下,所以得用段选择子和线性地址的方式去访问内存

至于为什么要 jmp dword,是因为现在 CPU 还在 16 位机器代码上执行跳转,但是跳转的地址却是用 32 位保护模式的方式寻址的。jmp dword 能够使 CPU 的流水线清空,并串行化执行跳转后的 32 位机器代码,这样 CPU 就能在保护模式下正常运行。

后续

光说不练假把式,也许你还是只有一些笼统的概念。下一篇文章,笔者将用整个实例来演示并穿插解释一段引导扇区程序是如何一步步进入保护模式的。感谢阅读本文!


打赏 赞(2)
微信
支付宝
微信二维码图片

微信扫描二维码打赏

支付宝二维码图片

支付宝扫描二维码打赏

最后编辑:
作者:Yenyu
Yenyu
编程爱好者

留下一个回复

你的email不会被公开。