嵌入式Linux引导过程之1.2——Xloader的XLOADER_ENTRY

来源:互联网 发布:淘宝卖什么东西最好卖 编辑:程序博客网 时间:2024/04/28 08:47

--by FeCen

根据上文中获得的线索,本文分析init.S中的XLOADER_ENTRY。

在init.S中,定义了好多与平台相关的寄存器地址宏以及好多其他函数,我们在用到的时候再回过头来分析,这里,我们只看其中的一个函数(其实是一个标号,我们暂且称之为函数也无妨)——XLOADER_ENTRY。

好了,废话不多说,来贴代码:
 80 .global XLOADER_ENTRY
 81 XLOADER_ENTRY:
 82  
 83 /*;   IMPORT sys_init    */
 84    BL sys_init
 85 /*;   IMPORT ddr_init */
 86    BL ddr_init   
 87 /* ;   IMPORT Xloader_Entry   ; The C main routine has C_main label. */                   
 88
 89    LDR R14, =Xloader_Entry    /* ; Get the address of the C entry point. */
 90    MOV pc, R14

可以看到,这一段代码很简单,我们对其做一下简单的分析。

首先看到的是一个伪指令.global,对于这个伪指令的说明如下:
.global <symbol> 全局声明标志,这样声明的标号将可以被外部使用。(与armasm中的EXPORT相同)。
也就是相当于在C语言里面的非静态函数和非静态全局变量,可以被外部的函数调用,也就是说对全局可见。

在这个整个程序的入口标号中,所做的事情很简单,无非就是对系统做了一些初始化(sys_init),对外部SDRAM初始化(ddr_init),然后就跳转到了另一个函数(Xloader_Entry)去执行了,Xloader_Entry是在另一个C源文件中定义的,我们下次再来看。

由于代码中直接使用了MOV pc, r14,因此当跳转出去之后,就再也不会回来了,因为不知道回来的路。聪明人在做任何事情之前都会为自己留好退路,就像BL sys_init和BL ddr_init那样,在走之前首先保存了返回地址。而MOV pc, r14直接为pc赋值并且没有额外手动保存返回地址,所以是没有办法回来的。
也正因为如此,当代码执行到这里的时候,XLOADER_ENTRY的使命也就完成了。

XLOADER_ENTRY很简单,它确实很简单。但不要得意的太早,想到我们的终极目标是成功引导Linux kernel,而现在,仅仅只是最初的第一步而已!

参考文章:
GNU ARM汇编快速入门
http://hi.baidu.com/chenzhuoyou/blog/item/a031b509a26adc276b60fb5f.html