天天看點

uboot啟動第二階段

在start.S中,經過第一階段的硬體初始化之後,進入到了u-boot的第二階段,在這個階段會對 序列槽、單闆、中斷、nand、nor等進行初始化,并設定核心需要的環境變量。

通過函數 start_armboot 進入第二階段,下面箭頭指的 init_sequence是一個函數數組,數組中的函數都是需要初始化的函數,init_fnc_ptr是一個函數指針,一個個執行init_sequence數組中的函數,進而實作初始化的任務。

uboot啟動第二階段

下面進入init_sequence中

uboot啟動第二階段
  • cpu_init是對cpu中的一些參數,點進去後設定的是 棧的空間;
  • board_init是對單闆的初始化,比如設定GPIO口,設定機器ID,設定環境變量存放的位置0x30000100
  • interrupt_init是對中斷的初始化
  • env_init是對環境變量的初始化
  • init_baudrate設定序列槽的波特率 115200
  • serial_init是對序列槽的初始化
  • dram_init是對SDRAM的初始化,設定SDRAM的位址和大小

下面是對其他部分的初始化

① 配置設定堆的空間

uboot啟動第二階段

 ② nand flash的初始化

uboot啟動第二階段

 ③ 環境變量的初始化

uboot啟動第二階段

 ④ 設定網絡位址

uboot啟動第二階段

 ⑤ 控制台的設定

uboot啟動第二階段
uboot啟動第二階段

 ⑥ 初始化網卡

uboot啟動第二階段

最後就是通過函數 main_loop 進入到main的主循環中

uboot啟動第二階段

進入到 main_loop中後就會發現,很多指令都是對環境變量的處理

關鍵的函數就是 run_command() 函數

是以需要分析run_command()函數

在run_command()函數中

uboot啟動第二階段

parse_line函數是對指令的解析,比如mw.d 0

argc = 2

argv[0] = "mw.d"    argv[1] = "0" 

解析完之後,就會根據argv[0]中的指令,按照查找名字的方式去找指令對應的函數

uboot啟動第二階段

又,在執行時,都會鍵入 bootm xxx 指令啟動核心,是以我們需要去分析一下bootm指令的作用是什麼

uboot啟動第二階段

這個是u-boot指令的格式,當鍵入bootm指令時,就會執行 do_bootm函數

uboot啟動第二階段

将核心檔案放入加載位址中

uboot啟動第二階段

準備啟動核心

uboot啟動第二階段

theKernel指向核心的入口位址

uboot啟動第二階段

啟動核心,其中

bi_arch_number中存放的是機器ID

bi_boot_params中存放的是環境變量的位址,傳遞給核心

在環境變量中設定了 bootcmd=nand read.jffs2 0x30007FC0 kernel;bootm 0x30007FC0,意思是:

利用bootcmd指令先從nand flash 0x30007FC0中讀取核心的位置,在這個位址中存放的是核心的頭部uImage,它的大小是64KB,0x30007FC0 + 64 = 0x30008000