BootLoader的启动过程分为stage1 和 stage2两个阶段,通常stage1是用汇编语言完成的,而stage2是用C语言完成的,以便在stage2阶段实现更加复杂的功能和取得更加好的代码可读性和可移植性。下面我们来简析两个阶段的工作。
1
(1)基本的硬件初始化工作:
(2)准备RAM空间加载stage2 。为了获得更好的速度,通常把stage2加载到RAM空间来执行,所以必须准备好一段可用的RAM空间范围用来加载BootLoader的stage2.
(3)复制stage2到RAM中,执行复制时要确定两类地址:第一,stage2的可执行映像在固态存储设备的存储起始地址和终止地址;第二,RAM的空间的起始地址。
(4)设置堆栈的指针SP。设置堆栈的指针是为了C语言的代码执行做准备,在设置堆栈指针SP之前,也可以关闭LED灯,以提示用户准备跳转到stage2
(5)跳转到stage2的C入口点。在RAM处理器中,实现跳转的方法是通过修改PC寄存器为合适的地址
2
(1)使用汇编语言跳转到main()入口函数。用汇编语言写一段trampoline小程序,并且将这段小程序作为stage2可执行映像的入口点。然后在trampoline汇编小程序中使用CPU跳转指令跳入mian()函数中去执行;而当mian()函数返回时,CPU执行路径再次回到了trampoline程序,这种思想是:用这段trampoline小程序作为main()函数的外部包裹
(2)初始化本阶段要使用到的硬件设备,初始化至少一个串口,以便和终端用户进行I/O输出信息、初始化计时器等
(3)检测系统的内存映射。所谓系统的内存映射是指在整个4GB物理地址空间中,有哪些地址范围被分配用来寻址系统的RAM单元
(4)加载内核映像文件和根文件系统映像文件。包括规划内存分配布局和从flash上复制数据。规划内存分配布局包括内核映像所占用的内存范围和根文件系统所占用的内存范围
(5)设置内核的启动参数。在将内核映像和根文件系统映像复制到RAM空间中后,就可以准备启动Linux内核了。在调用内核之前,应该做一步准备工作,即设置Linux内核的启动参数。
(完)