preloader流程----基于MTK平台( 二 )


/*获取启动设备,为得到分区在ROM中的地址做准备*/
if (NULL == ( = ())) {
print("%scan't find boot (%d)\n", MOD, );
/* FIXME,toerror code */
-1;
………
#
/* 这个值是一个固定值,确定了lk加载的目的地址,定义在.mak中 := */
addr = ;
/*在ROM中找到lk分区,并加载到DRAM中addr位置*/
ret = ("lk", , &addr,&size);
if (ret)
ret;
* = addr;
#endif
/*如果支持ATF,在加载lk后还会加载tee分区*/
#if
addr = ;
ret = ("tee1", , &addr,0, &size);
……
ader("boot",, &addr, 0, &size);
#endif
ret;
(2)最终会执行:(bdev, part, addr, 0, size);指定读取的偏移量,检索分区头是否正确,如果正确则开始加载分区,加载分区的代码:
( *bdev,*part, u32 *addr, u32 , u32 *size)

/*检索分区头. */
if ((bdev, src,(), (u8*)hdr, part->) != 0) {
//print("[%s] bdev(%d) read error(%s)\n", MOD, bdev->type, part->name);
-1;
if (->info.magic == ){
/* 加载带分区头的image*/
->info.name[31] = '\0';
……
maddr = ->info.maddr;
dsize = ->info.dsize;
mode = ->info.mode;
src += ();
( + , , ());
++;
} else {
//print("[%s] %s image doesn'\n", MOD, part->name);
-1;
/*设置
if (maddr == ADDR) {
maddr = *addr;
#
} else if (mode == ARD){
maddr = (maddr);
#endif
3、跳转到LK (1)():内部其实是执行(),其主要作用是检查电池是否存在,确定要传给lk的参数 。
it(void)
#
/*检查电池是否存在,不存在就一直等待 */
…..
#endif
pt();
/*设置要传递给lk的参数,在.c中定义*/
gs();
(2) (,, ()):执行init.s中定义的jump,实现跳转到lk执行,跳转地址即为 。

preloader流程----基于MTK平台

文章插图
如果支持ATF就执行(,, ()):
最主要是执行:(addr, arg1, arg2)
void (u32 addr, u32 arg1,u32 arg2)
{/*初始化tee模块*/
();
……
/*执行init.s中定义的*/
(addr, arg1, arg2, ());
: 先jump到el3,然后再回到lk 。