[第3天]32位模式和c语言

       终于到了第3天,这次作者太坑。搞的我差点放弃。这次是真的一天,一整天,拼起来24小时。今天我也终于实现了第一个内核,不再是简单的引导了。而且也进入CPU保护模式,这个就吊了。我还要吐槽下,为何其他很多中文博客TMD都是直接复制粘帖代码?坑啊。

IPL:

       IPL(Initial Program Load),就是把系统导入内存然后跳入系统的入口。跟Booting是一个意思我才知道。这个阶段BIOS读入磁盘上的第一个扇区,一共512Bytes。在这个阶段,就是所谓的实模式。在这个阶段,只有16位,但是借助段寄存器使用超过16位的内存。主要任务,是读取操作系统所在扇区的内存并载入到相应内存位置。我后来用的是0x1000部分的内存(Memory Map)。

读取磁盘:

      读取磁盘只要知道INT 0x13就行了。CH是柱面,DH是磁头,CL是要读的扇区位置, AL是要读的扇区数, AH=02表示读取。关键这里有的DL很坑,代表哪个磁盘,当然是0x00,但是我就傻逼了。我是直接生成img然后当作磁盘来跑,然后死也读不了。原因这时候要设成0x80。还有寄存器地址,主要跟ES和BX有关,具体地址是    ES:BX = ES*16 + BX, 一共fffff位,131072Bytes。还是不够用,这就是BIOS实模式的一个缺点。具体代码都在github

 载入内核:

        这里的内核只是让CPU空转。具体步骤是,读入磁盘内容到内存,找到函数入口的地址(编译后找img中相应字段),然后再修改读完磁盘内容后jump的地址。我的地址是0x4400,作者的是0x4200,然后开始的位置是对应内存0x8000,加起来就是入口地址就是0xc400。jump即可。具体代码github。这个不是重点,重点是我学会了怎么挂载镜像,就像虚拟光驱一样的。并可以写入文件到这个img。

entry

32位保护模式:

      进入保护模式。这个是最复杂的部分,作者挖了个大坑,GDT,这个太复杂了。今天也不想说明了。然后作者的引导方式很奇怪,是要根据编译后的函数入口地址来调节的,很蛋疼,而且好像跟COFF和ELF的格式有关,我试了很久都没办法不用作者的工具成功实验。(我做这个系统的原则是不使用作者的工具)。 后来实在没有办法,我是看了这个指导,重新写了个逻辑结构好的内核。直接调用,编译后直接拼接,免去了上一步,挂载磁盘的麻烦,而且还要读那么多扇区麻烦。这个版本只要读第二个扇区。代码我新建了一个Scratch,说是Scratch,但我感觉要在这个基础上进行下一步了。看看结果。我超前了一点点,把图像显示了一下。

 

video

链接:

  1. boot sector code, LILO
  2. Write a 16-bit os, Tiny bootloader