启动过程及原理

1、

A20板,开机启动首先检测TF卡是否有卡及启动程序,如果有,就TF卡引导系统;如果没有,就接着检测Nand Flash中是否有启动程序去引导系统。

关于启动:

分区篇

如何引导系统之前了解一下机器内部Flash空间是如何划分的各个分区又是用作存储什么内容的.

下面以我手头上4G A20为例内部Flash芯片空间是4G, 4G空间一共被分为9个分区.

+---------------------+

分区1: BOOTLOADER   (64M) | 存放的是官方多系统引导方案的文件 (官方说可引导多系统,但我配置不出来)

厂商引导分区        关机充电控制代码也在这里分区中也负责部分核心硬件的地址配置和初始化工作

+---------------------+

分区2: ENV     (2M) | 这个分区保存的是UBOOT引导器的配置信息包括启动时执行的命令从那个分区加载

内核配置信息        内核又是从哪个分区加载恢复系统内核

+---------------------+ 

分区3: BOOT(32M) | 存放基础的Linux内核文件(boot.img)分区没有文件系统是直接把可运行的内核

| Linux内核分区       文件写入分区空间, BOOT分区的uboot引导区会加载本分区内容到内存运行

+---------------------+

分区4: SYSTEM (400M)| Android系统分区也就是/system目录下的所有文件存放的分区ext3/ext4格式

| Android系统分区     本分区包括Java格式的系统运行库还有部分没有编译进内核的硬件驱动库(bin格式)

+---------------------+

分区5: DATA (1G)    | Android数据分区也就是/data目录对应的分区ext3/ext4格式

| Android数据分区     这就是我们所说的把应用安装到机器内存所对应的空间同时保存各种动态系统设置

+---------------------+

分区6: MISC (1M)    | 这个分区一般不使用唯一作用是为了让Android系统与内核引导时交流可以指引

| Android配置分区     重启机器后让内核进行一些特殊的操作:进入恢复程序更新系统文件等操作

+---------------------+

分区7: RECOVERY(32M)| 一个特殊的微型Linux系统可以不依靠BOOTSYSTEM分区启动类似PC的一键还原

| Android恢复系统     可对其他分区进行更新或备份如何实现恢复损坏的系统或者系统内核在后面说明.

+---------------------+

分区8: CACHE(256M)  | 这个分区并不是做虚拟内存之类的缓存这个分区最大的 作用是做系统升级时保存

缓存分区            更新文件的(FAT格式). 配合MISC分区的配置语句来使用详细以后介绍.

+---------------------+

分区9: STORAGE(所有)| 没错剩下的所有空间都被划分给内置卡作为存储空间, 4G空间扣除1-7分区的

内置存储卡分区      使用后大概就是剩下的空间这就是为什么内置卡容量只有很小一部分

+---------------------+

 

引导篇

A20的上电引导大致上可以分为以下阶段: BROM -> Boot0 -> Boot1 -> Boot.axf -> u-boot -> kernel -> Android

 

下面介绍每个阶段所完成的事情.

BROM

BROM, 其实是一段已经固化在A20芯片里面的引导代码, BROM代码存放的地址是0xFFFF0000, A20芯片上电后,CPU自动的从0xFFFF0000地址上加载第一条指令并执行因此这里的BROM就和我们电脑主板上的BIOS是一样的只是BROM完成的功能没有BIOS强大简单的说, BROM只有2个功能第一个就是正常启动从外部存储器中加载运行代码,第二个也是最重要的一个就是FEL功能。FEL功能就是我们接触到的刷机接口官方的ROM更新程序就是通过FEL功能刷写机器的闪存的.

 

正是由于刷机接口的代码是固化在CPU内部不能被改写的原因,可以说,所有A20的机器都是刷不死的,没有变砖的可能。所以喜欢折腾的朋友请用力折腾,只要做好数据的备份,大不了就是重新用官方的升级工具重刷固件就可以了。机器进入FEL功能的有两种情况第一种就是常用的正常刷机方法关机状态下按住菜单键不放连接USB接口。另外一种就是Boot0代码的验证标记不正确,BROM也会自动进入FEL功能。

如果机器完全变砖,没有任何显示,正常按住菜单键连接USB也不能进入FEL,那可能就是你机器根本没有完全关闭,一般A20芯片方案所配合使用的电源控制芯片都是AXP209, 该芯片长按电源开关6秒以上会强制断电可先确认断电后再操作。

A20芯片的BROM还有一个的特性,那就是会优先从0SD卡引导系统,没错,是SD卡,不是内部闪存NAND。而一般0SD卡所对应的都是机器的的TF卡槽,因此制作SD卡上的系统完全可以的。

正是由于是优先从TF引导,所以通过在TF卡上写入特殊的,不能通过检验的Boot0代码,就可以通过插入TF卡后开机强制机器进入FEL功能进行刷机。

 

再总结一下BROM的启动流程

(1). BROM是一段固化在CPU内部的代码,不能被修改和删除。代码会初始化外部存 储设备(内部FlashSD);

(2). 检查刷机按钮是否被按下,有就跳转到3,没有就跳转到4继续执行;

(3). 启动FEL功能,初始化USB接口等等PC端连接;

(3). 正常引导过程,检查是否有0SD卡插入,有则跳转到4,没有则跳转到7

(4). 读取0SD卡的8K地址处的内容,检查是否有Boot0标志,有则跳转到5,没 有则跳转到7

(5). 根据Boot0头部指定的大小加载所有的Boot0代码到内存中检验校验值正确跳 转到6, 不正确跳转到3;

(6). CPU跳转到内存中的Boot0代码上继续执行, BROM工作完成控制权交给Boot0 的代码;

(7). 检查NAND(内部闪存)是否存在存在跳转到8, 不存在则跳转到3;

(8). 读取NAND8K地址处的内容检查是否有Boot0标志有则跳转到9, 没有则跳 转到3;

(9). 根据Boot0头部指定的大小加载所有的Boot0代码到内存中检验校验值正确跳 转到6, 不正确跳转到3;

2、针对A20 EVB

A20启动代码流程分析:

(1)全志的启动包括boot0boot1u-bootboot0boot1源码在lichee/boot/目录下,机器上电执行boot0boot0就会引导boot1boot1再引导u-boot

(2)lichee/boot/目录下的Makefile文件指定了boot1的编译目录,例如

make -f make_sdmmc  -C boot1/core -j8  

//命令就是调用lichee/boot/boot1/core目录下make_sdmmc脚本编译,  make_sdmmc最终又调用make.cfg脚本编译,所以lichee/boot/目录下的Makefile文件指定的编译路径最终都会调用各自目录下的make.cfg来编译。

(3)、使用make_nandmake_sdmmc脚本是core目录生成的boot1_nand.binboot1_sdcard.bin,同时在

lichee/boot/workspace/egon/

lichee/tools/pack/chips/sun7i/eGon/目录生成,他们分别调用

lichee/boot/boot1/driver/drv_nand/lichee/boot/boot1/driver/drv_sd/目录下的文件;boot1_nand.binboot1_sdcard.bin分别对应启动模式:nandflashinand启动,配置文件是在lichee/boot/pack/chips/sun7i/configs/android/sugar-cubieboard2目录下sys_config.fex文件指定,由storage_type字段指定,1card0启动,0nandflash启动,-1为自动扫描;

Boot_Android是正常启动模式,Boot_Burn是调试模式,Card_Android是升级模式,他们分别生成boot.axfprvt.axfsprite.axf镜像,同

lichee/boot/workspace/wboot/bootfs/

lichee/tools/pack/chips/sun7i/wboot/bootfs/目录生成;

lichee/boot/boot1/driver/drv_de/目录是多媒体库源码,是LcdHDMI等显示源码,同时在

lichee/boot/workspace/wboot/bootfs/

lichee/tools/pack/chips/sun7i/wboot/bootfs/目录生成drv_de.drv镜像。

(4)

arm_start.S(boot1/core/arm_board)->eGon2_swi_handler->eGon2_swi_handler_entry->eGon2_init->eGon2_start->eGon2_storage_type_set(判断启动模式,加载boot.axf或者sprite.axf)eGon2_run_app->FS_fread(加载.axf文件)elf_loader[*entry = (__u32)priv->main;],func(argc, argv)[该函数就是 BootMain()的指针]->BootMain

 A正常启动模式:

      BootMain->BoardInit_Display[加载drv_de.drv,判断显示模式,LCDTVHDMI]check_power_status[检测电压与电池状态,判断是否开机]BootOS_detect_os_type[加载u-boot.binPreBootOS-> boot_dsipatch_kernal[设置u-boot的物理地址是

*kernal_addr=0x4a000000]->wBoot_fopen("c:\\linux\\u-boot.bin","rb")],                 

BootOS[wBoot_jump_to_linux->EGON2_SWI_JUMP_TO_LINUX->eGon2_jump_to_android_linux直接进入u-boot接口]

 B升级模式:

      BootMain->boot_ui_init[加载drv_de.drv,判断显示模式,LCDTVHDMI]card_sprite->update_flash_hardware_scan[扫描当前存储设备是nand还是inandupdate_boot0update_boot1,根据sprite_type判断升级nand还是inand]

(5)、

Alichee/tools/pack/pack脚本打包镜像文件。

B编译kernel的时候首调用

./build.sh -p sun7i_android->buildroot/scripts/common.sh-> 

lichee/linux-3.3/build.sh->lichee/buildroot/scripts/build_sun7i_android.sh编译。

在编译kernel的时候也编译u-boot,调用

./build.sh -p sun7i_android->buildroot/scripts/common.sh->

                         lichee/u-boot/build.sh编译。

(6)、

lichee/boot/pack/chips/sun7i/wboot/bootfs.ini

lichee/tools/pack/chips/sun7i/wboot/bootfs.ini

把文件系统盘符映射成C盘,就是代码中使用的c:\\boot.ini""c:\\sprite.axf"等。 lichee/tools/pack/chips/sun7i/configs/android/default/下有env.cfgimage.cfg配置文件,nv.cfgu-boot使用的配置文件,包括nand_rootmmc_rootloglevelbootcmd等参数;image.cfgboot使用的文件列表与ITEM_ROOTFSFAT32等重要符号。                

(7)、sys_partition.fex文件中各个分区与下载对应的文件如下:

bootloader分区保存bootloader.fexbootloader.fex就是由boot.axf u-boot.bin等组成。

env分区保存env.fexenv.fex就是

lichee/tools/pack/chips/sun4i/configs/crane/default/env.cfg文件,它是u-boot的基本配置。

boot分区保存boot.fexboot.fexboot.img的链接,它由kernelramdisk组成,使用fastboot下载的时候就是下载boot.img

system分区保存system.fexsystem.fexsystem.img的链接,它是android系统,使用fastboot下载的时候就是下载system.img

recovery分区保存recovery.fexrecovery.fexrecovery.img的链接,它也是由kernelramdisk组成,用于系统恢复,使用fastboot下载的时候就是下载recovery.img

misc分区用于恢复系统设置的时候在uboot中保存一些变量与命令的值。

*.fex文件在lichee/tools/pack/out/目录,*.imganroid/out/...下。

        

(8)A20的分区如下:单位:512B

        --------fastboot partitions--------

        -total partitions:11-

        -name-        -start-       -size-      

        bootloader  : 8000          8000        

        env         : 10000         8000        

        boot        : 18000         8000        

        system      : 20000         100000      

        data        : 120000        100000      

        misc        : 220000        8000        

        recovery    : 228000        10000       

        cache       : 238000        80000       

        private     : 2b8000        8000        

        databk      : 2c0000        80000       

        UDISK       : 340000        3e0000      

        -----------------------------------

其中UDISK就是作为SDCARD分区,bootloader是从16MB开始,在bootloader的前面是16KBMBR_SIZE16KBDL_SIZE

        

(9)各个镜像的对应的内存地址:

 在read_boot_img()或者do_boota()都可以打印这些信息。

 u-boot的地址为0x4a000000,在boot_dsipatch_kernal函数里强制赋值,也在该函数里

使用wBoot_fopen("c:\\linux\\u-boot.bin", "rb")

wBoot_fread((void *)(*kernal_addr), 1, file_length, hd_file)

u-boot.bin从存储设备加载到0x4a000000内存地址,之后boot1BootOS(para_addr, kernal_addr)跳转到u-boot

*kernal_addr = 0x4a000000

kernel地址为0x40008000ramdisk地址为0x41000000,在CONFIG_EXTRA_ENV_SETTINGS中的boota 40007800其实是把boot.img下载到内存中的地址,由于boot.img中包含了kernelramdisk,也包含了这两个镜像在内存中的地址,还有检查boot.imgmagic是不是ANDROID,从存储设备加载这个两个镜像到内存的操作是在read_boot_img函数里,在u-bootdo_boota函数里再次检查boot.img的合法性。

  • 3
    点赞
  • 11
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值