mtk启动流程分析

1、mtk开机基本流程:

boot rom ————》preloader ————》lk ————》kernel ————》android

2、boot rom:

每个芯片有自己的boot rom,上电时启动,然后将preloader加载到内部sram中,因为此时外部ram还没有初始化,需要preloader去初始化

3、preloader:

vendor/mediatek/proprietary/bootable/bootloader/preloader/platform/mt6765/src

init:init.S

汇编完成,主要四切换系统到SVC模式(超级用户模式),平台要是有实现EL3,preloader就运行在EL3,否则运行在EL1,还有负责禁止irq/fiq,设置stack等,然后会jump到C语言开始的main函数中

core:C开始的main.c中的main函数

完成各种硬件的基本初始化,如uart、timer、rtc、wdt、mem、pmic等
获取rtc记录的系统的启动模式,启动原因等,保存到全局变量bootargs中
security check,和安全相关
找到 lk加载到dram的地址(是一个固定的地址),从rom中找到lk分区的地址,
battery check,如果没有电池就一直while(1)
jump到lk

重点函数:

bldr_load_images:找到lk分区地址和lk加载到dram中的地址,准备jump到lk
bldr_post_process:主要是里面的platform_post_init函数,会检查电池是否存在
platform_init:rtc、pmic、wdt、gpio、i2c、battery、mem等初始化,
也是在这里通过usb phy监听握手识别是否有usb插入

4、lk(little kernel):

进入lk之后,部分硬件可能还需要重新reset初始化,来保证一个比较干净的环境,比如timer

lk/arch/arm/crt0.S:
lk/kernel/main.c:kmain

使能 MMU、cache

使能 Uart、中断、定时器、DRAM Banks、wot、display

创建一个 bootstrap2 线程

bootstrap2:

platform_init:启动模式选择、电池、显示 Logo、背光打开、设置软件的环境变量

target_init:空

apps_init:

lk/app/app.c下的app.c中start_app,创建一个app_thread_entry线程

__apps_start 和 __apps_end 的定义,这两个变量符号在所有源文件中并不存在,而是在 arch/arm/*.ld 链接脚本中存在,所有的 app 都通过在特殊的段 .apps 中注册实现了一套插件系统,是一个十分精巧的设计。后续的任何新的 app 只需要使用以下两个宏声明即可注册到 .apps 段中,遍历 .apps 段就可以获取 aboot 的描述信息,调用 aboot 的 init 函数了

实例:

APP_START(aboot)

APP_START(mt_boot)

如果 g_boot_mode 为 FASTBOOT 就走 fastboot 模式 否则 boot_linux_from_storage()

boot_linux_from_storage()
boot_linux跳转到kernel

这里具体进入哪种boot_mode,通过全局变量g_boot_mode来分化

平台platform.c中的platform_init:

全局环境变量读取
led backlight disp等init
根据不同模式显示第一帧logo

boot_mode_select:

会检测power和其他按键是否按下,按照boot_mode.c中的按键和组合键走对应的流程,如果当前启动的原因是 USB 充电器,而不是 power 按键,电池模块将等待用户按下 power 按键启动

5、kernel:

lk下通过boot_linux跳转到kernel和ramdisk镜像地址

head.S:

解压zimage,head.S 首先初始化自解压相关的如内存等环境,接下来调用 decompress_kernel 进行解压(./arch/arm/boot/compressed/misc.c)

start_kernel:

satrt kernel启动内核,在init/main.c中
start_kernel 是任何版本 Linux 内核的通用初始化函数,它会初始化很多东西,输出 Linux 版本信息、设置体系结构相关的环境,页表结构初始化,设置系统自陷入口,初始化系统 IRQ,初始化核心调度器等

最后调用 rest_init:

调用kernel_init线程,然后kernel初始化完成后fork出init进程, 然后拉起ramdisk(ramdisk作用)中的init程序,执行 schedule 开始任务调度,进入用户空间初始化,init进程fork出zygote进程…直到整个Android启动完成

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值