一、MTK启动流程

1-3:设备上电起来后,跳转到Boot ROM(不是flash)中的boot code中执行把pre-loader加载起到ISRAM, 因为当前DRAM(RAM分SRAM跟DRAM,简单来说SRAM就是cache,DRAM就是普通内存)还没有准备好,所以要先把pre-loader load到芯片内部的ISRAM(Internal SRAM)中。4-6:pre-loader初始化好DRAM后就将lk从flash(nand/emmc)中加载到DRAM中运行;7-8:解压bootimage成ramdisk跟kernel并载入DRAM中,初始化dtb;9-11:lk跳转到kernl初始化, kernel初始化完成后fork出init进程, 然后拉起ramdisk中的init程序,进入用户空间初始化,init进程fork出zygote进程,直到整个Android启动完成.

上面一篇已经简要分析了PL的启动代码流程

二、LK启动分析

1:/home/ubuntu/Mediatek/code/vendor/mediatek/proprietary/bootable/bootloader/lk/arch/arm/crt0.S

/** Copyright (c) 2008 Travis Geiselbrecht** Permission is hereby granted, free of charge, to any person obtaining* a copy of this software and associated documentation files* (the "Software"), to deal in the Software without restriction,* including without limitation the rights to use, copy, modify, merge,* publish, distribute, sublicense, and/or sell copies of the Software,* and to permit persons to whom the Software is furnished to do so,* subject to the following conditions:** The above copyright notice and this permission notice shall be* included in all copies or substantial portions of the Software.** THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,* EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF* MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.* IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY* CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,* TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE* SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.*/#define DSB .byte 0x4f, 0xf0, 0x7f, 0xf5
#define ISB .byte 0x6f, 0xf0, 0x7f, 0xf5.section ".text.boot"
.globl _start
_start:b    resetb  arm_undefinedb  arm_syscallb    arm_prefetch_abortb arm_data_abortb arm_reservedb   arm_irqb    arm_fiq/*pre-loader to uboot argument Location*/
.global BOOT_ARGUMENT_LOCATION
BOOT_ARGUMENT_LOCATION:.word 0x00000000reset:ldr     r6, =BOOT_ARGUMENT_LOCATION str     r4, [r6]
#ifdef ARM_CPU_CORTEX_A7/*Enable SMP bit*/mrc             p15, 0, r0, c1, c0, 1orr      r0, r0, #0x40mcr        p15, 0, r0, c1, c0, 1
#endif
#ifdef ENABLE_TRUSTZONE/*Add reference to TZ symbol so linker includes it in final image */ldr r7, =_binary_tzbsp_tzbsp_bin_start
#endif/* do some cpu setup */
#if ARM_WITH_CP15/* Read SCTLR */mrc        p15, 0, r0, c1, c0, 0/* XXX this is currently for arm926, revist with armv6 cores *//* new thumb behavior, low exception vectors, i/d cache disable, mmu disabled */bic     r0, r0, #(1<<15| 1<<13 | 1<<12)bic        r0, r0, #(1<<2 | 1<<0)/* enable alignment faults */orr      r0, r0, #(1<<1)/* Write SCTLR */mcr       p15, 0, r0, c1, c0, 0
#ifdef ENABLE_TRUSTZONE/*nkazi: not needed ? Setting VBAR to location of new vector table : 0x80000      */ldr             r0, =0x00080000mcr             p15, 0, r0, c12, c0, 0
#endif
#endif#if WITH_CPU_EARLY_INIT/* call platform/arch/etc specific init code */
#ifndef ENABLE_TRUSTZONE/* Not needed when TrustZone is the first bootloader that runs.*/bl __cpu_early_init
#endif/* declare return address as global to avoid using stack */
.globl _cpu_early_init_complete_cpu_early_init_complete:#endif#if (!ENABLE_NANDWRITE)
#if WITH_CPU_WARM_BOOTldr   r0, warm_boot_tagcmp    r0, #1/* if set, warm boot */ldreq  pc, =BASE_ADDRmov  r0, #1str   r0, warm_boot_tag
#endif
#endif/* see if we need to relocate */mov       r0, pcsub       r0, r0, #(.Laddr - _start)
.Laddr:ldr      r1, =_startcmp     r0, r1beq       .Lstack_setup/* we need to relocate ourselves to the proper spot */ldr      r2, =__data_end    .Lrelocate_loop:ldr     r3, [r0], #4str     r3, [r1], #4cmp     r1, r2bne       .Lrelocate_loop/* we're relocated, jump to the right address */ldr     r0, =.Lstack_setupbx       r0.ltorg
#if WITH_CPU_WARM_BOOT
warm_boot_tag:.word 0
#endif.Lstack_setup:/* set up the stack for irq, fiq, abort, undefined, system/user, and lastly supervisor mode */mrs     r0, cpsrbic     r0, r0, #0x1fldr      r2, =abort_stack_toporr     r1, r0, #0x12 // irqmsr     cpsr_c, r1ldr      r13, =irq_save_spot        /* save a pointer to a temporary dumping spot used during irq delivery */orr     r1, r0, #0x11 // fiqmsr     cpsr_c, r1mov      sp, r2orr     r1, r0, #0x17 // abortmsr     cpsr_c, r1mov       sp, r2orr     r1, r0, #0x1b // undefinedmsr     cpsr_c, r1mov       sp, r2orr     r1, r0, #0x1f // systemmsr     cpsr_c, r1mov      sp, r2orr       r1, r0, #0x13 // supervisormsr      cpsr_c, r1mov       sp, r2/* copy the initialized data segment out of rom if necessary */ldr        r0, =__data_start_romldr       r1, =__data_startldr       r2, =__data_endcmp     r0, r1beq       .L__do_bss.L__copy_loop:cmp     r1, r2ldrlt r3, [r0], #4strlt   r3, [r1], #4blt     .L__copy_loop.L__do_bss:/* clear out the bss */ldr      r0, =__bss_startldr        r1, =_endmov       r2, #0
.L__bss_loop:cmp        r0, r1strlt r2, [r0], #4blt     .L__bss_loop#if defined(ARM_CPU_CORTEX_A8) || defined(ARM_CPU_CORTEX_A9)DSBISB
#endifbl        kmainb      ..ltorg.bss
.align 2/* the abort stack is for unrecoverable errors.* also note the initial working stack is set to here.* when the threading system starts up it'll switch to a new * dynamically allocated stack, so we don't need it for very long*/
abort_stack:.skip 1024
abort_stack_top:.section ".rodata"
.align 2/* define the heap end as read-only data containing the end defined in the* linker script. other archs that use dynamic memory length discovery can make* this read-write and update it during init.*/
.global _heap_end
_heap_end:.int _end_of_ram

最终跳转到kmain函数

2:/home/ubuntu/Mediatek/code/vendor/mediatek/proprietary/bootable/bootloader/lk/kernel/main.c

/** Copyright (c) 2008 Travis Geiselbrecht** Copyright (c) 2009, Code Aurora Forum. All rights reserved.** Permission is hereby granted, free of charge, to any person obtaining* a copy of this software and associated documentation files* (the "Software"), to deal in the Software without restriction,* including without limitation the rights to use, copy, modify, merge,* publish, distribute, sublicense, and/or sell copies of the Software,* and to permit persons to whom the Software is furnished to do so,* subject to the following conditions:** The above copyright notice and this permission notice shall be* included in all copies or substantial portions of the Software.** THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,* EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF* MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.* IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY* CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,* TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE* SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.*/
#include <compiler.h>
#include <debug.h>
#include <string.h>
#include <app.h>
#include <arch.h>
#include <platform.h>
#include <target.h>
#include <lib/heap.h>
#include <kernel/thread.h>
#include <kernel/timer.h>
#include <kernel/dpc.h>
#include <platform/mt_gpt.h>#ifdef MTK_LK_IRRX_SUPPORT
#include <platform/mtk_ir_lk_core.h>
#endifextern void *__ctor_list;
extern void *__ctor_end;
extern int __bss_start;
extern int _end;/* boot_time is calculated form kmain to kernel jump */
volatile unsigned int boot_time = 0;static int bootstrap2(void *arg);#if (ENABLE_NANDWRITE)
void bootstrap_nandwrite(void);
#endifstatic void call_constructors(void)
{void **ctor;ctor = &__ctor_list;while(ctor != &__ctor_end) {void (*func)(void);func = (void (*)())*ctor;func();ctor++;}
}/* called from crt0.S */
void kmain(void) __NO_RETURN __EXTERNALLY_VISIBLE;
void kmain(void)
{
#if !defined(MACH_FPGA) && !defined(SB_LK_BRINGUP)boot_time = get_timer(0);
#endif// get us into some sort of thread contextthread_init_early();// early arch stuffarch_early_init();// do any super early platform initializationplatform_early_init();#if defined(MACH_FPGA) || defined(SB_LK_BRINGUP)boot_time = get_timer(0);
#endif// do any super early target initializationtarget_early_init();dprintf(INFO, "welcome to lk\n\n");// deal with any static constructorsdprintf(SPEW, "calling constructors\n");call_constructors();// bring up the kernel heapdprintf(SPEW, "initializing heap\n");heap_init();// initialize the threading systemdprintf(SPEW, "initializing threads\n");thread_init();// initialize the dpc systemdprintf(SPEW, "initializing dpc\n");dpc_init();// initialize kernel timersdprintf(SPEW, "initializing timers\n");timer_init();#ifdef  MTK_LK_IRRX_SUPPORTmtk_ir_init(0);
#endif#if (!ENABLE_NANDWRITE)// create a thread to complete system initializationdprintf(SPEW, "creating bootstrap completion thread\n");thread_resume(thread_create("bootstrap2", &bootstrap2, NULL, DEFAULT_PRIORITY, DEFAULT_STACK_SIZE));// enable interruptsexit_critical_section();// become the idle threadthread_become_idle();
#elsebootstrap_nandwrite();
#endif
}int main(void);static int bootstrap2(void *arg)
{dprintf(SPEW, "top of bootstrap2()\n");arch_init();// XXX put this somewhere else
#if WITH_LIB_BIObio_init();
#endif
#if WITH_LIB_FSfs_init();
#endif// initialize the rest of the platformdprintf(SPEW, "initializing platform\n");platform_init();// initialize the targetdprintf(SPEW, "initializing target\n");target_init();dprintf(SPEW, "calling apps_init()\n");apps_init();return 0;
}#if (ENABLE_NANDWRITE)
void bootstrap_nandwrite(void)
{dprintf(SPEW, "top of bootstrap2()\n");arch_init();// initialize the rest of the platformdprintf(SPEW, "initializing platform\n");platform_init();// initialize the targetdprintf(SPEW, "initializing target\n");target_init();dprintf(SPEW, "calling nandwrite_init()\n");nandwrite_init();return 0;
}
#endif

3:/home/ubuntu/Mediatek/code/vendor/mediatek/proprietary/bootable/bootloader/lk/platform/mt6735/platform.c

void platform_init(void)
{
#ifdef LK_PROFILINGunsigned int time_nand_emmc;unsigned int time_led_init;unsigned int time_env;unsigned int time_disp_init;unsigned int time_load_logo;unsigned int time_backlight;unsigned int time_boot_mode;
#ifdef MTK_SECURITY_SW_SUPPORTunsigned int time_security_init;
#endifunsigned int time_bat_init;unsigned int time_RTC_boot_Check;unsigned int time_show_logo;unsigned int time_sw_env;unsigned int time_platform_init;time_platform_init = get_timer(0);
#endifdprintf(CRITICAL," ==LK info ==\n");dprintf(CRITICAL," Build time:%s, %s\n",  __DATE__,__TIME__);dprintf(CRITICAL," chip_code[0x%x]\n",  mt_get_chip_hw_code());dprintf(CRITICAL," chip_ver[0x%x]\n",   mt_get_chip_sw_ver());dprintf(CRITICAL," ==LK info ==\n");dprintf(CRITICAL, "platform_init()\n");#ifdef DUMMY_APdummy_ap_entry();
#endif#ifdef LK_PROFILINGtime_nand_emmc = get_timer(0);
#endif
#ifdef MTK_EMMC_SUPPORTmmc_legacy_init(1);
#else
#ifndef MACH_FPGAnand_init();nand_driver_test();
#endif
#endif
#ifdef LK_PROFILINGdprintf(INFO, "[PROFILE] ------- NAND/EMMC init takes %d ms -------- \n", (int)get_timer(time_nand_emmc));
#endif
#if defined(CFG_DTB_EARLY_LOADER_SUPPORT)if (bldr_load_dtb()<0)dprintf(CRITICAL, "bldr_load_dtb fail\n");
#endif#ifndef MACH_FPGA
#ifdef LK_PROFILINGtime_led_init = get_timer(0);
#endifleds_init();
#ifdef LK_PROFILINGdprintf(INFO, "[PROFILE] ------- led init takes %d ms -------- \n", (int)get_timer(time_led_init));
#endif
#endif#ifdef MTK_KERNEL_POWER_OFF_CHARGINGif ((g_boot_arg->boot_reason == BR_USB) && (upmu_is_chr_det() == KAL_FALSE)) {dprintf(INFO, "[%s] Unplugged Charger/Usb between Pre-loader and Uboot in Kernel Charging Mode, Power Off \n", __func__);mt6575_power_off();}
#endif#ifdef LK_PROFILINGtime_env = get_timer(0);
#endifenv_init();print_env();
#ifdef LK_PROFILINGdprintf(INFO, "[PROFILE] ------- ENV init takes %d ms -------- \n", (int)get_timer(time_env));
#endif#ifdef LK_PROFILINGtime_disp_init = get_timer(0);
#endif/* initialize the frame buffet information */
#ifndef MACH_FPGA_NO_DISPLAYg_fb_size = mt_disp_get_vram_size();
#elseg_fb_size = 0x1000000;
#endif
#if 0g_fb_base = memory_size() - g_fb_size + DRAM_PHY_ADDR;
#else#if 0if (g_is_64bit_kernel) {g_fb_base = mblock_reserve(&g_boot_arg->mblock_info, g_fb_size, 0x200000, 0x100000000, RANKMAX);g_fb_base = ALIGN_TO(g_fb_base,0x200000); // size 2MB align} else {g_fb_base = mblock_reserve(&g_boot_arg->mblock_info, g_fb_size, 0x100000, 0x100000000, RANKMAX);}
#elseg_fb_base = mblock_reserve(&g_boot_arg->mblock_info, g_fb_size, 0x10000, 0x100000000, RANKMAX);
#endifif (!g_fb_base) {/* ERROR */}
#endifdprintf(CRITICAL, "FB base = 0x%x, FB size = %d\n", g_fb_base, g_fb_size);#ifndef MACH_FPGA_NO_DISPLAYmt_disp_init((void *)g_fb_base);/* show black picture fisrtly in case of  backlight is on before nothing is drawed*/mt_disp_fill_rect(0, 0, CFG_DISPLAY_WIDTH, CFG_DISPLAY_HEIGHT, 0x0);mt_disp_update(0, 0, CFG_DISPLAY_WIDTH, CFG_DISPLAY_HEIGHT);
#ifdef LK_PROFILINGdprintf(INFO, "[PROFILE] ------- disp init takes %d ms -------- \n", (int)get_timer(time_disp_init));
#endif#ifdef MTK_SECURITY_SW_SUPPORT
#ifdef LK_PROFILINGtime_security_init = get_timer(0);
#endif/* initialize security library */
#ifdef MTK_EMMC_SUPPORT
#ifdef MTK_NEW_COMBO_EMMC_SUPPORTsec_func_init(3);
#elsesec_func_init(1);
#endif
#elsesec_func_init(0);
#endif
#ifdef LK_PROFILINGdprintf(INFO,"[PROFILE] ------- Security init takes %d ms -------- \n", (int)get_timer(time_security_init));
#endifseclib_set_oemkey(g_oemkey, OEM_PUBK_SZ);/*Verify logo before use it*/if ( 0 != sec_logo_check() ) {dprintf(CRITICAL,"<ASSERT> %s:line %d\n",__FILE__,__LINE__);while (1);}
#endif#ifdef LK_PROFILINGtime_load_logo = get_timer(0);
#endifdrv_video_init();mboot_common_load_logo((unsigned long)mt_get_logo_db_addr_pa(), "logo");
#ifdef LK_PROFILINGdprintf(INFO, "[PROFILE] ------- load_logo takes %d ms -------- \n", (int)get_timer(time_load_logo));
#endif
#endif/*for kpd pmic mode setting*/set_kpd_pmic_mode();#ifndef MACH_FPGA
#ifdef LK_PROFILINGtime_boot_mode = get_timer(0);
#endifboot_mode_select();
#ifdef LK_PROFILINGdprintf(INFO, "[PROFILE] ------- boot mode select takes %d ms -------- \n", (int)get_timer(time_boot_mode));
#endif
#endif/*Show download logo & message on screen */if (g_boot_arg->boot_mode == DOWNLOAD_BOOT) {dprintf(CRITICAL, "[LK] boot mode is DOWNLOAD_BOOT\n");#ifdef MTK_SECURITY_SW_SUPPORT/* verify da before jumping to da*/if (sec_usbdl_enabled()) {u8  *da_addr = (u8*)g_boot_arg->da_info.addr;u32 da_len   = g_boot_arg->da_info.len;u32 sig_len  = g_boot_arg->da_info.sig_len;u8  *sig_addr = (unsigned char *)da_addr + (da_len - sig_len);if (da_len == 0 || sig_len == 0) {dprintf(INFO, "[LK] da argument is invalid\n");dprintf(INFO, "da_addr = 0x%x\n", (int)da_addr);dprintf(INFO, "da_len  = 0x%x\n", da_len);dprintf(INFO, "sig_len = 0x%x\n", sig_len);}if (sec_usbdl_verify_da(da_addr, (da_len - sig_len), sig_addr, sig_len)) {/* da verify fail */video_printf(" => Not authenticated tool, download stop...\n");while (1); /* fix me, should not be infinite loop in lk */}} else
#endif{dprintf(INFO, " DA verification disabled...\n");}#ifndef MACH_FPGA_NO_DISPLAYmt_disp_show_boot_logo();
#endifvideo_printf(" => Downloading...\n");dprintf(CRITICAL, "enable backlight after show bootlogo! \n");mt65xx_backlight_on();mtk_wdt_disable(); //Disable wdt before jump to DAplatform_uninit();
#ifdef HAVE_CACHE_PL310l2_disable();
#endifarch_disable_cache(UCACHE);arch_disable_mmu();
#ifdef ENABLE_L2_SHARINGconfig_shared_SRAM_size();
#endifjump_da(g_boot_arg->da_info.addr, g_boot_arg->da_info.arg1, g_boot_arg->da_info.arg2);}#ifdef LK_PROFILINGtime_bat_init = get_timer(0);
#endifmt65xx_bat_init();
#ifdef LK_PROFILINGdprintf(INFO, "[PROFILE] ------- battery init takes %d ms -------- \n", (int)get_timer(time_bat_init));
#endif#ifndef CFG_POWER_CHARGING
#ifdef LK_PROFILINGtime_RTC_boot_Check = get_timer(0);
#endif/* NOTE: if define CFG_POWER_CHARGING, will rtc_boot_check() in mt65xx_bat_init() */rtc_boot_check(false);
#ifdef LK_PROFILINGdprintf(INFO, "[PROFILE] ------- RTC boot check Init  takes %d ms -------- \n", (int)get_timer(time_RTC_boot_Check));
#endif
#endif#ifdef LK_PROFILINGtime_show_logo = get_timer(0);
#endif
#ifdef MTK_KERNEL_POWER_OFF_CHARGINGif (kernel_charging_boot() == 1) {
#ifdef MTK_BATLOWV_NO_PANEL_ON_EARLYCHARGER_TYPE CHR_Type_num = CHARGER_UNKNOWN;CHR_Type_num = hw_charging_get_charger_type();if ((g_boot_mode != LOW_POWER_OFF_CHARGING_BOOT) ||((CHR_Type_num != STANDARD_HOST) && (CHR_Type_num != NONSTANDARD_CHARGER))) {
#endifmt_disp_power(TRUE);mt_disp_show_low_battery();mt65xx_leds_brightness_set(6, 110);
#ifdef MTK_BATLOWV_NO_PANEL_ON_EARLY}
#endif} else if (g_boot_mode != KERNEL_POWER_OFF_CHARGING_BOOT && g_boot_mode != LOW_POWER_OFF_CHARGING_BOOT) {if (g_boot_mode != ALARM_BOOT && (g_boot_mode != FASTBOOT)) {
#ifndef MACH_FPGA_NO_DISPLAYmt_disp_show_boot_logo();
#endif}}
#elseif (g_boot_mode != ALARM_BOOT && (g_boot_mode != FASTBOOT)) {
#ifndef MACH_FPGA_NO_DISPLAYmt_disp_show_boot_logo();
#endif}
#endif
#ifdef LK_PROFILINGtime_backlight = get_timer(0);
#endif#ifdef MTK_BATLOWV_NO_PANEL_ON_EARLYif (!is_low_battery(0)) {
#endifmt65xx_backlight_on();
#ifndef MACH_FPGA_NO_DISPLAY//pwm need display sofmt_disp_update(0, 0, CFG_DISPLAY_WIDTH, CFG_DISPLAY_HEIGHT);
#endif
#ifdef MTK_BATLOWV_NO_PANEL_ON_EARLY}
#endif#ifdef LK_PROFILINGdprintf(INFO, "[PROFILE] ------- backlight takes %d ms -------- \n", (int)get_timer(time_backlight));
#endif#ifdef LK_PROFILINGdprintf(INFO, "[PROFILE] ------- show logo takes %d ms -------- \n", (int)get_timer(time_show_logo));
#endif#ifndef MACH_FPGA
#ifdef LK_PROFILINGtime_sw_env = get_timer(0);
#endifsw_env();
#ifdef LK_PROFILINGdprintf(INFO, "[PROFILE] ------- sw_env takes %d ms -------- \n", (int)get_timer(time_sw_env));
#endif
#endif#ifdef LK_PROFILINGdprintf(INFO, "[PROFILE] ------- platform_init takes %d ms -------- \n", (int)get_timer(time_platform_init));
#endif
}

4:/home/ubuntu/Mediatek/code/vendor/mediatek/proprietary/bootable/bootloader/lk/app/mt_boot/mt_boot.c

void mt_boot_init(const struct app_descriptor *app)
{unsigned usb_init = 0;unsigned sz = 0;int sec_ret = 0;
#ifdef SERIAL_NUM_FROM_BARCODEchar tmp[SN_BUF_LEN+1] = {0};unsigned ser_len = 0;
#endif
#ifdef CONFIG_MTK_USB_UNIQUE_SERIALu64 key;u32 chip_code;
#endifchar serial_num[SERIALNO_LEN];#ifdef CONFIG_MTK_USB_UNIQUE_SERIAL/* Please enable EFUSE clock in platform.c before reading sn key *//* serial string adding */key = get_devinfo_with_index(13);key = (key << 32) | (unsigned int)get_devinfo_with_index(12);chip_code = board_machtype();if (key != 0)get_serial(key, chip_code, serial_num);elsememcpy(serial_num, DEFAULT_SERIAL_NUM, SN_BUF_LEN);/* copy serial from serial_num to sn_buf */memcpy(sn_buf, serial_num, SN_BUF_LEN);dprintf(CRITICAL,"serial number %s\n",serial_num);
#elsememcpy(sn_buf, DEFAULT_SERIAL_NUM, strlen(DEFAULT_SERIAL_NUM));
#endif#ifdef SERIAL_NUM_FROM_BARCODEser_len = read_product_info(tmp);if (ser_len == 0) {ser_len = strlen(DEFAULT_SERIAL_NUM);strncpy(tmp, DEFAULT_SERIAL_NUM, ser_len);}memset( sn_buf, 0, sizeof(sn_buf));strncpy( sn_buf, tmp, ser_len);
#endifsn_buf[SN_BUF_LEN] = '\0';surf_udc_device.serialno = sn_buf;if (g_boot_mode == FASTBOOT)goto fastboot;#ifdef MTK_SECURITY_SW_SUPPORT/* Do not block fastboot if check failed */if (0 != sec_boot_check(0)) {dprintf(CRITICAL,"<ASSERT> %s:line %d\n",__FILE__,__LINE__);while (1);}
#endifextern void platform_sec_post_init(void)__attribute__((weak));if (platform_sec_post_init) {platform_sec_post_init();}/* Will not return */boot_linux_from_storage();fastboot:target_fastboot_init();if (!usb_init)/*Hong-Rong: wait for porting*/udc_init(&surf_udc_device);mt_part_dump();sz = target_get_max_flash_size();fastboot_init(target_get_scratch_address(), sz);udc_start();}APP_START(mt_boot)
.init = mt_boot_init,APP_END

启动APP进行Linux系统DTB和镜像的加载

Android OrangePi 4G IOT(四) - MTK LK分析相关推荐

  1. Android OrangePi 4G IOT(二) - MTK更换调试串口

    一.Debug LOG串口更改 orangepi 4G iot的默认的log调试串口是在板子后面的,使用起来不方便,之前UART0焊接不好导致焊盘弄坏了,没办法,准备修改成插针的40pin引脚的的UA ...

  2. Android Camera 四 Camera HAL 分析

    Android Camera 一 源码路径 Android Camera 二 JNI JAVA和C/CPP图像数据传输流程分析 Android Camera 三 CameraService 和 Cli ...

  3. Android 8.1/9.0 MTK Camera源码分析之录像快门声音控制流程

    前面已经针对拍照快门声音控制流程进行了分析,接下来分析一下录像快门声音的控制流程. Android 8.1/9.0 MTK Camera源码分析之快门声音控制流程 这两篇文章其实都是相对于手机系统RO ...

  4. Android 8.1/9.0 MTK Camera源码分析之快门声音控制流程

    Android 8.1/9.0 MTK Camera源码分析之快门声音控制 在Android 8.1上mtk camera有控制快门声音的接口,但是并没有了控制录像快门声音的接口.之所以会有这个现象, ...

  5. Android 源码 Camera2 预览流程分析四

    <Android 源码 Camera2 预览流程分析二>中进行了流启动,这是调用 QCamera3Channel start() 方法实现的,对应于 HAL_PIXEL_FORMAT_YC ...

  6. Android 系统(126)---Android的死机、重启问题分析方法

    Android的死机.重启问题分析方法 阅读数:11986 Android的死机.重启问题分析方法 1.     死机现象 1.1      死机定义 当手机长时间无法再被用户控制操作时,我们称为死机 ...

  7. Android的死机、重启问题分析方法

    Android的死机.重启问题分析方法 原文链接:https://blog.csdn.net/jinlu7611/article/details/50592385 1.死机现象 1.1 死机定义 当手 ...

  8. mtk LK流程简介

    mtk LK流程简介 一.LK简介 Lk的主要功能: 1.初始化硬件模块,比如时钟,中断,UART,USB,LCD,PMIC,eMMC等.打开MMU,使能I/D-cache,加速lk执行,显示logo ...

  9. 【SemiDrive源码分析】【X9芯片启动流程】30 - AP1 Android Kernel 启动流程 start_kernel 函数详细分析(一)

    [SemiDrive源码分析][X9芯片启动流程]30 - AP1 Android Kernel 启动流程 start_kernel 函数详细分析(一) 一.Android Kernel 启动流程分析 ...

最新文章

  1. KeyWordHelper-关键字提取类(注:使用第三方组件DictSeg.dll)
  2. 软件工程2018第二次团队作业
  3. 【区块链与未来】区块链技术将重塑我们的世界
  4. oracle 每日归档量,小知识:统计Oracle的日归档量
  5. 去月球“你知道戴维会变身成哪种动物吗?”
  6. QueryPath, php上的jQuery
  7. 动手为王 | Oracle 数据库跨版本升级迁移实践
  8. Linux学习总结(33)——Linux Java启动关闭bash脚本
  9. 使用 ‘In Place’ 直接从MySQL 5.0升级至5.7
  10. 常用计算机名词解释,计算机常用名词解释
  11. 多线程之间通讯JDK1.5-Lock
  12. 小程序内嵌H5页面判断微信及小程序环境
  13. SM2258XT固态硬盘不认盘量产修复开卡工具 SM2258XT开卡教程
  14. NUBT 1480 懒惰的风纪委Elaine
  15. php写的公告栏代码,可爱的公告栏代码
  16. routerOS做wan口的交换机扩展和带宽叠加
  17. 快牛策略——PowerPoint 2003:红头文件的制作及标准
  18. 马丁福勒《UML精粹》读书笔记_第四章
  19. 用Assimp模型加载库加载一个Crytek的游戏孤岛危机(Crysis)中的原版纳米装(Nanosuit)
  20. 狗眼看人低的十种职业~

热门文章

  1. Linux学习笔记-RH135之Apache的管理及优化
  2. 金融专业术语之——信用转换+期限转换+流动性转换
  3. 计算机主板上的ide,主板上的IDE是什么?作用?
  4. 《重构:改善既有代码的设计》读书笔记(下)
  5. C语言 学习笔记 存个档而已
  6. 重磅丨十四五国家信息规划:部署了10项重大任务,10项优先行动(附PDF原文)...
  7. win10磁盘管理_Win10系统如何分区
  8. 自定义UI 基础知识
  9. stegano(图片隐写、摩斯密码)
  10. PaxosLease