标签:io os 使用 数据 sp c 代码 r linux
开机上电的阶段
开机上电时CPU寄存器的值CS:0xffff, IP: 0x0000, 此时CPU处于实模式因此会去执行地址 addr = cs * 16 + ip = 0xffff0 此处就是固化在ROM中的
一段程序也就是BIOS, 然后BIOS 会去读MBR(引导扇区 512B) , 将这512B(也是bootsect.s的内容)的程序加载到0x7c00:0处。
bootsect.s的阶段
将自己从0x7c00:0处移到0x9000:0处, 接着读随后的4个扇区的内容到0x9000:0x200 处, 接着读取system img到 0x1000:0处并显示Loading system...
然后jmp 到 0x9000:0x200处 开始执行setup.s的内容
setup.s阶段
保存硬盘参数等信息到0x90000处, 将0x10000处的system img 移动到绝对地址0x0000处, 设置gdt ( NULL, 代码段, 数据段, 保留 ), 设置idt(NULL)
使用lgdt 加载gdt 表, lidt 加载idt 表, 关中段并开启A20 地址线, 置CR0 寄存器PE 位, 进入保护模式, jmp 0x8:0 此时已经是保护模式, 所以会去寻找gdt中的
第二项也就是代码段的段描述符, 跳转到段描述符中的保存的地址( 已经设置成了 0) , 会去执行0x0000的代码 也就是head.s
head.s 阶段
因为寄存器的值已经改变 需要重新加载gdt和idt的内容, push _main 到栈中, call 设置页目标和4个页表的子程序, 设置CR0 寄存器的PG位, 开启分页模式, 执行ret 指令弹出_main到ip中, 执行main函数进入内核初始化的过程。
标签:io os 使用 数据 sp c 代码 r linux
原文地址:http://www.cnblogs.com/nhblog/p/4004298.html