嵌入式Linux的構(gòu)建_第1頁
嵌入式Linux的構(gòu)建_第2頁
嵌入式Linux的構(gòu)建_第3頁
嵌入式Linux的構(gòu)建_第4頁
嵌入式Linux的構(gòu)建_第5頁
已閱讀5頁,還剩100頁未讀, 繼續(xù)免費(fèi)閱讀

下載本文檔

版權(quán)說明:本文檔由用戶提供并上傳,收益歸屬內(nèi)容提供方,若內(nèi)容存在侵權(quán),請進(jìn)行舉報(bào)或認(rèn)領(lǐng)

文檔簡介

1、第4章 嵌入式Linux的構(gòu)建(u jin)4.1嵌入式BootLoader技術(shù)4.2嵌入式Linux根文件系統(tǒng)構(gòu)建4.3Linux內(nèi)核及啟動過程4.4 基于ARM目標(biāo)(mbio)板的 Linux系統(tǒng)及應(yīng)用程序的燒寫共一百零五頁4.1嵌入式BootLoader技術(shù)(jsh)4.1.1Bootloader的概念(ginin) 簡單地說,Boot Loader 就是在操作系統(tǒng)內(nèi)核運(yùn)行之前運(yùn)行的一段小程序。通過這段小程序,可以初始化硬件設(shè)備、建立內(nèi)存空間的映射圖,從而將系統(tǒng)的軟硬件環(huán)境帶到一個合適的狀態(tài),以便為最終調(diào)用操作系統(tǒng)內(nèi)核準(zhǔn)備好正確的環(huán)境。 通常,Boot Loader 是嚴(yán)重地依賴于硬件而

2、實(shí)現(xiàn)的,特別是在嵌入式系統(tǒng)。因此,在嵌入式系統(tǒng)里建立一個通用的 Boot Loader 幾乎是不可能的。盡管如此,仍然可以對 Boot Loader 歸納出一些通用的概念來,以指導(dǎo)用戶特定的 Boot Loader 設(shè)計(jì)與實(shí)現(xiàn)。共一百零五頁 每種不同的 CPU 體系結(jié)構(gòu)都有不同的 Boot Loader。有些 Boot Loader 也支持多種體系結(jié)構(gòu)的 CPU,比如 U-Boot 就同時支持 ARM 體系結(jié)構(gòu)和MIPS 體系結(jié)構(gòu)。除了依賴于 CPU 的體系結(jié)構(gòu)外,Boot Loader 實(shí)際上也依賴于具體的嵌入式板級設(shè)備的配置。這也就是說,對于兩塊不同的嵌入式板而言,即使(jsh)它們是基于

3、同一種 CPU 而構(gòu)建的,要想讓運(yùn)行在一塊板子上的 Boot Loader 程序也能運(yùn)行在另一塊板子上,通常也都需要修改 Boot Loader 的源程序。 1. Boot Loader 所支持(zhch)的 CPU 和嵌入式開發(fā)板共一百零五頁2. Boot Loader 的安裝(nzhung)媒介(Installation Medium)系統(tǒng)加電或復(fù)位后,所有的 CPU 通常都從某個由 CPU 制造商預(yù)先安排的地址上取指令。比如,基于 ARM920T核的 CPU 在復(fù)位時通常都從地址 0 x00000000 取它的第一條指令。而基于 CPU 構(gòu)建的嵌入式系統(tǒng)通常都有某種類型的固態(tài)存儲設(shè)備(比

4、如:ROM、EEPROM 或 FLASH 等)被映射到這個預(yù)先安排的地址上。因此在系統(tǒng)加電后,CPU 將首先執(zhí)行(zhxng) Boot Loader 程序。 圖4.1所示的就是一個同時裝有 Boot Loader、內(nèi)核的啟動參數(shù)、內(nèi)核映像和根文件系統(tǒng)映像的固態(tài)存儲設(shè)備的典型空間分配結(jié)構(gòu)圖。 共一百零五頁圖4.1 固態(tài)存儲設(shè)備的典型空間(kngjin)分配結(jié)構(gòu)共一百零五頁3. 用來(yn li)控制 Boot Loader 的設(shè)備或機(jī)制主機(jī)和目標(biāo)(mbio)機(jī)之間一般通過串口建立連接,Boot Loader 軟件在執(zhí)行時通常會通過串口來進(jìn)行 I/O,比如:輸出打印信息到串口,從串口讀取用戶控制

5、字符等。 4. Boot Loader 的啟動過程是單階段(Single Stage)還是多階段(Multi-Stage)通常多階段的 Boot Loader 能提供更為復(fù)雜的功能,以及更好的可移植性。從固態(tài)存儲設(shè)備上啟動的 Boot Loader 大多都是 2 階段的啟動過程,也即啟動過程可以分為 stage 1 和 stage 2 兩部分。而至于在 stage 1 和 stage 2 具體完成哪些任務(wù)將在下面討論。 共一百零五頁5. Boot Loader 的操作(cozu)模式 (Operation Mode) 啟動加載(Boot loading)模式:這種模式也稱為自主(Autonom

6、ous)模式。也即 Boot Loader 從目標(biāo)機(jī)上的某個固態(tài)存儲設(shè)備上將操作系統(tǒng)加載到 RAM 中運(yùn)行,整個過程并沒有用戶(yngh)的介入。這種模式是 Boot Loader 的正常工作模式,因此在嵌入式產(chǎn)品發(fā)布的時侯,Boot Loader 顯然必須工作在這種模式下。 下載(Downloading)模式:在這種模式下,目標(biāo)機(jī)上的 Boot Loader 將通過串口連接或網(wǎng)絡(luò)連接等通信手段從主機(jī)(Host)下載文件,比如:下載內(nèi)核映像和根文件系統(tǒng)映像等。從主機(jī)下載的文件通常首先被 Boot Loader 保存到目標(biāo)機(jī)的 RAM 中,然后再被 Boot Loader 寫到目標(biāo)機(jī)上的FLAS

7、H 類固態(tài)存儲設(shè)備中。Boot Loader 的這種模式通常在第一次安裝內(nèi)核與根文件系統(tǒng)時被使用;此外,以后的系統(tǒng)更新也會使用 Boot Loader 的這種工作模式。工作于這種模式下的 Boot Loader 通常都會向它的終端用戶提供一個簡單的命令行接口。共一百零五頁6. BootLoader 與主機(jī)之間進(jìn)行文件傳輸所用(su yn)的通信設(shè)備及協(xié)議一般情況,目標(biāo)機(jī)上的 Boot Loader 通過串口與主機(jī)之間進(jìn)行文件傳輸(chun sh),傳輸(chun sh)協(xié)議通常是 xmodemymodemzmodem 協(xié)議中的一種。但是,串口傳輸?shù)乃俣仁怯邢薜模虼送ㄟ^以太網(wǎng)連接并借助 TFT

8、P 協(xié)議來下載文件是個更好的選擇。 還必須考慮主機(jī)方所用的軟件。比如,在通過以太網(wǎng)連接和 TFTP 協(xié)議來下載文件時,主機(jī)方必須有一個軟件用來的提供 TFTP 服務(wù)。 共一百零五頁4.1.2 Bootloader引導(dǎo)(yndo)程序 Bootloader引導(dǎo)程序是嵌入式開發(fā)很重要的組成部分。它是嵌入式系統(tǒng)上電后執(zhí)行的第一個程序,并由它最終將操作系統(tǒng)啟動起來并將控制權(quán)交給操作系統(tǒng)。Bootloader引導(dǎo)程序最基本的功能是對硬件(yn jin)系統(tǒng)的初始化和內(nèi)核啟動參數(shù)設(shè)置并啟動內(nèi)核。 Bootloader的主要功能有:(1)初始化CPU 的主頻、SDRAM、中斷、串口等硬件;(2)啟動Linu

9、x內(nèi)核并提供一個RAMDISK;(3)通過串口下載內(nèi)核或RAMDISK到目標(biāo)板上;(4)將修改過的內(nèi)核或RAMDISK寫入到Flash內(nèi);(5)為用戶提供一個命令接口。共一百零五頁 Bootloader的stage1stage1是Bootloader一開始就執(zhí)行的操作,其目的是為了stage2的執(zhí)行以及隨后的內(nèi)核的執(zhí)行,設(shè)置好一些基本的硬件環(huán)境。包括以下步驟:屏蔽所有的中斷 。為中斷提供服務(wù)的通常是操作系統(tǒng),因此在執(zhí)行Bootloader的過程中可以不響應(yīng)任何中斷。中斷屏蔽通過寫CPU的中斷屏蔽寄存器來完成。設(shè)置CPU的時鐘頻率和速度。初始化RAM設(shè)置系統(tǒng)內(nèi)存(ni cn)控制器的功能寄存器和

10、各內(nèi)存(ni cn)庫控制寄存器等。為加載stage2準(zhǔn)備RAM空間??截恠tage2到RAM中。跳轉(zhuǎn)到stage2的入口點(diǎn)。共一百零五頁 Bootloader的stage2 stage2的主要的功能是通過串口下載Linux內(nèi)核到目標(biāo)板上。包括以下幾個步驟:初始化本階段要使用到的硬件設(shè)備。通常包括:初始化至少一個串口,以便和終端用戶進(jìn)行I/O輸出信息;初始化計(jì)時器等。檢測系統(tǒng)的內(nèi)存映射。所謂內(nèi)存映射就是指在整個4GB物理地址空間中有哪些地址范圍被分配(fnpi)用來尋址系統(tǒng)的RAM單元。加載內(nèi)核映像和根文件系統(tǒng)從Flash讀入到Rom中。包括兩個方面:第一方面是內(nèi)核映像所占用的內(nèi)存范圍;第二方

11、面是根文件系統(tǒng)所占用的內(nèi)存范圍。在規(guī)劃內(nèi)存占用布局時,主要考慮基地址和映像的大小兩個方面。設(shè)置內(nèi)核的啟動參數(shù)。調(diào)用內(nèi)核。Bootloader調(diào)用Linux內(nèi)核的方法是直接跳轉(zhuǎn)到內(nèi)核的第一條指令處。共一百零五頁2BootLoader代碼(di m)分析 下面對引導(dǎo)程序2410INIT.S進(jìn)行分析,以加深對BootLoader的理解(lji)。在第一階段完成依賴于體系結(jié)構(gòu)硬件初始化的代碼,包括禁止看門狗、禁止中斷、初始化各控制寄存器拷貝自身到RAM等。IMPORT Main AREA Init,CODE,READONLYENTRY bResetHandler ResetHandlerldrr0,=

12、WTCON ldrr1,=0 x0共一百零五頁strr1,r0ldrr0,=INTMSKldrr1,=0 xffffffffstrr1,r0ldrr0,=INTSUBMSKldrr1,=0 x7ffstrr1,r0ldrr0,=LOCKTIMEldrr1,=0 xffffffstrr1,r0ldrr0,=SMRDATAldrr1,=BWSCONaddr2, r0, #52共一百零五頁ldrr3, r0, #4strr3, r1, #4cmpr2, r0bne%B0共一百零五頁第二階段通常用C語言實(shí)現(xiàn)(shxin),包括內(nèi)存管理單元初始化、時鐘設(shè)置、端口設(shè)置和串口初始化等。void Isr_In

13、it(void) rINTMOD = 0 x0; /工作在IRQ模式 rINTMSK = BIT_ALLMSK; /屏蔽中斷 rINTSUBMSK = BIT_SUB_ALLMSK; /屏蔽子中斷void Main(void) MMU_Init(); /MMU初始化 ChangeClockDivider(1,1); / 設(shè)置(shzh)時鐘除法器-1:2:4 ChangeMPllValue(0 xa1,0 x3,0 x1); / 時鐘值FCLK=202.8MHz Port_Init(); Isr_Init();共一百零五頁 Uart_Init(0,115200); Uart_Select(0)

14、; while(1) Uart_Printf(nnSMDK2410 Board (MCU S3C2410) Example Program Ver 1.0(20020521) FCLK = %d Hznn, FCLK); 共一百零五頁 與一般的C語言程序一樣(yyng),第二階段程序從Main()函數(shù)開始。因?yàn)樗捎玫腟3C2410X處理器內(nèi)含存儲器管理單元MMU,所以首先需要進(jìn)行存儲器管理單元的初始化。緊接著設(shè)置系統(tǒng)工作主時鐘,若使用USB設(shè)備則USB時鐘也需要做相應(yīng)初始化。其次對端口工作狀態(tài)進(jìn)行設(shè)定。然后設(shè)定處理器工作模式,以及中斷控制。最后初始化串口,與宿主機(jī)建立聯(lián)系,以利于顯示調(diào)試信息

15、。啟動成功后,可以執(zhí)行主程序。共一百零五頁4.1.3 VIVI簡介(jin ji) VIVI是韓國Mizi公司開發(fā)的BootLoader,可用于ARM9處理器的引導(dǎo)。VIVI利用串行通信為用戶提供接口。為連接VIVI,首先利用串口電纜連接宿主機(jī)和目標(biāo)板,然后在主機(jī)上運(yùn)行串口通信程序,并在目標(biāo)板上正確設(shè)置VIVI以支持串口。在宿主機(jī)進(jìn)入超級終端后,打開目標(biāo)板電源或按目標(biāo)板復(fù)位鍵,就可以由串口通信程序顯示(xinsh)提示信息,提示信息的最后一行如下所示:共一百零五頁P(yáng)ress Return to start the LINUX now, any other key for vivi.VIVI也有

16、前面說過的兩種工作模式,啟動模式可以在一段時間后自行啟動Linux內(nèi)核,這是VIVI的默認(rèn)方式。出現(xiàn)上述信息后,如果按除回車鍵外的任意鍵,即可進(jìn)入下載模式,出現(xiàn)“vivi”提示符。有如下作用: 把內(nèi)核(kernel)從flash復(fù)制到RAM,然后啟動; 初始化硬件; 下載程序(chngx)并寫入flash(通常由串口或者網(wǎng)口先把內(nèi)核下載到RAM中,然后寫入flash); 檢測目標(biāo)板(bootloader會有一些簡單的代碼用以測試目標(biāo)板硬件的好壞)。在下載模式下,VIVI為用戶提供了一個命令行接口,通過該接口可以使用VIVI提供的一些命令。 共一百零五頁1. VIVI的命令(mng lng) (

17、1)load命令 將二進(jìn)制文件載入到Flash或者RAM,命令格式:load | 其中命令行參數(shù)描述裝載(zhungzi)位置,有flash和ram兩種選項(xiàng);參數(shù) 或 描述裝載的地址,如果有提前定義的mtd分區(qū)信息,可以只輸入分區(qū)名稱,否則需要指定地址和大??;參數(shù) 確定文件的傳輸協(xié)議,常采用的選項(xiàng)“x”用來指定采用xmodem協(xié)議。 例如:vivi load flash kernel x,裝載壓縮映像文件zImage到flash存儲器中,地址是kernel分區(qū),采用xmodem傳輸協(xié)議。也可以指定地址和大小,例如:vivi load flash 0 x80000 0 xc0000 x。共一百零

18、五頁(2)part命令操作MTD分區(qū)信息,比如,顯示(xinsh)、增加、刪除、復(fù)位、保存MTD分區(qū)等。 part show:顯示mtd分區(qū)信息。 part add :增加新的mtd分區(qū),其中為新mtd分區(qū)名稱,是mtd器件的偏移,表示mtd分區(qū)的大小,表示分區(qū)類型,可選項(xiàng)有JFFS2、LOCKED和BONFS。 part del :刪除一個mtd分區(qū)。 part reset:恢復(fù)mtd 分區(qū)為默認(rèn)值。 part save:在flash中永久保存參數(shù)值和分區(qū)信息。(3)param命令(mng lng)用來設(shè)置或者察看參數(shù)。例如:改變“l(fā)inux command line”,使用 vivi pa

19、ram set linux_cmd_line you wish.。也可以改變引導(dǎo)程序啟動的時間,使用vivi param set boot_delay 100000實(shí)現(xiàn)。共一百零五頁 (4)boot命令 用來引導(dǎo)存儲在flash存儲器或ram中的linux內(nèi)核。命令格式: boot | 參數(shù) 設(shè)定存儲linux內(nèi)核映像的位置,可選項(xiàng)有ram、nor和smc。 參數(shù) 或 描述存儲內(nèi)核的地址,如果有提前定義的mtd分區(qū)信息,可以只輸入分區(qū)名稱,否則需要(xyo)指定地址和大小。例如:vivi boot nor 0 x80000表示從flash存儲器中讀出linux內(nèi)核,偏移是0 x80000。 (

20、5)flash命令 存儲器管理命令,例如:flash erase | ,表示擦除flash存儲器。共一百零五頁2VIVI的目錄(ml)樹(1)arch:此目錄包括了所有VIVI支持的目標(biāo)板的子目錄,本書附帶的代碼中只包含S3C2410X。(2)Documentation:存放了許多文檔,其中包括VIVI的使用指南。(3)drivers:其中包括了引導(dǎo)內(nèi)核所需的MTD設(shè)備和串口驅(qū)動程序。MTD目錄下分maps、nand和nor三個目錄,實(shí)現(xiàn)(shxin)對Nand Flash和Nor Flash的讀寫控制。Serial目錄下的文件實(shí)現(xiàn)對串口的控制,并支持xmodem和ymodem協(xié)議。(4)in

21、clude:頭文件的公共目錄,其中的S3C2410.h定義了處理器的一些寄存器,以及NAND Flash的一些寄存器等。Platform/smdk2410.h定義了與目標(biāo)板相關(guān)的資源配置參數(shù),修改波特率、引導(dǎo)參數(shù)和物理內(nèi)存映射等參數(shù)即可配置目標(biāo)板。共一百零五頁(5)init:此目錄(ml)只有main.c和version.c兩個文件。與普通的C程序一樣,VIVI將從main函數(shù)開始執(zhí)行。(6)lib:一些平臺公共的接口代碼,比如,time.c里的udelay()和mdelay()。(7)scripts:此目錄存放了配置所需的腳本文件,如Menuconfig和Configure文件,以方便對VI

22、VI的配置。 VIVI的運(yùn)行也可以分為兩個階段。在第一階段完成含有依賴于CPU體系結(jié)構(gòu)硬件初始化的代碼,利用匯編語言完成。第二階段是用C語言完成的。即在VIVI中以head.S作為第一階段,main()作為第二階段。在跳轉(zhuǎn)進(jìn)main()函數(shù)之前,利用匯編語言編寫了一段trampoline程序作為階段2可執(zhí)行鏡像的執(zhí)行入口點(diǎn)。之后可以在trampoline中用處理器的跳轉(zhuǎn)指令進(jìn)入main()函數(shù)中去執(zhí)行。當(dāng)main()函數(shù)返回時,CPU就進(jìn)行復(fù)位。VIVI的程序代碼請參考本書提供的光盤:2410sexpbootloaderviviarchs3c2410的文件夾中的head.S程序,VIVI的下載

23、燒寫在4.7節(jié)詳細(xì)介紹。共一百零五頁3. 配置(pizh)和編譯vivi 如果vivi的源代碼已根據(jù)開發(fā)板作了相應(yīng)改動,則需要對源代碼進(jìn)行配置和編譯,以生成燒入flash的vivi 二進(jìn)制映象文件(wnjin)。 由于vivi要用到kernel的一些頭文件,所以需要kernel的源代碼,所以先要把linux的kernel準(zhǔn)備好。將vivi和kernel都解到相應(yīng)目錄下(例如將光盤提供的vivi源代碼解壓到/home/xiongmh目錄下,光盤提供的Linux kernel源碼kernel- h2410eb.041024.tar.gz也解壓到/home/xiongmh目錄下,解壓后的文件名為ke

24、rne-h2410eb)。共一百零五頁然后需修改/vivi/Makefile文件中的一些變量設(shè)置: LINUX_INCLUDE_DIR = /kernel/include/ 修改為: LINUX_INCLUDE_DIR =/home/xiongmh/ kerne-h2410eb/include/ ? CROSS_COMPILE = /usr/local/arm/2.95.3/bin/arm-linux- 修改為: CROSS_COMPILE = /usr/local/arm/2.95.3/bin/arm-linux- ARM_GCC_LIBS = /usr/local/arm/2.95.3/l

25、ib/gcc-lib/arm-linux/2.95.3 進(jìn)入(jnr)/vivi目錄執(zhí)行make distclean。(目的是確保編譯的有效性,在編譯之前將vivi里所有的“*.o”和“*.o.flag”文件刪掉) 進(jìn)入/vivi目錄里,輸入make menuconfig,開始選擇配置。也可用Load裝入一個寫好的配置文件。注意,選Exit退出時一定要選“Yes”保存配置。再輸入make正式開始編譯直至完成。如果不報(bào)錯,配置和編譯得到的“vivi”在/vivi的文件夾中。這個就是后面要燒寫到flash中的bootloader。共一百零五頁4.1.4 vivi代碼(di m)分析vivi的運(yùn)行也

26、可以分為兩個階段: 1. vivi的第一階段完成含依賴于CPU的體系結(jié)構(gòu)硬件初始化的代碼,包括禁止中斷、初始化串口、復(fù)制自身到RAM等。相關(guān)(xinggun)代碼集中在head.S(viviarchs3c2410目錄下): Head.S: #include config.h #include linkage.h #include machine.h Start of executable code ENTRY(_start) ENTRY(ResetEntryPoint) Exception vector table (physical address = 0 x00000000) ;異常向量表

27、物理地址 共一百零五頁0 x00: Reset ;復(fù)位b Reset 0 x04: Undefined instruction exception ;未定義的指令異常UndefEntryPoint: b HandleUndef 0 x08: Software interrupt exception ;軟件中斷異常SWIEntryPoint: b HandleSWI 0 x0c: Prefetch Abort (Instruction Fetch Memory Abort) ;內(nèi)存操作異常PrefetchAbortEnteryPoint: b HandlePrefetchAbort 0 x10:

28、 Data Access Memory Abort ;數(shù)據(jù)(shj)異常DataAbortEntryPoint: b HandleDataAbort 0 x14: Not used ;未使用NotUsedEntryPoint: b HandleNotUsed 0 x18: IRQ(Interrupt Request) exception ;慢速中斷處理共一百零五頁IRQEntryPoint: b HandleIRQ 0 x1c: FIQ(Fast Interrupt Request) exception ;快速中斷(zhngdun)處理FIQEntryPoint: b HandleFIQ VI

29、VI magics 0 x20: magic number so we can verify that we only put .long 0 0 x24: .long 0 0 x28: where this vivi was linked, so we can put it in memory in the right place .long _start 0 x2C: this contains the platform, cpu and machine id .long ARCHITECTURE_MAGIC 0 x30: vivi capabilities 共一百零五頁.long 0 #

30、ifdef CONFIG_PM ;vivi考慮不需要(xyo)使用電源管理 0 x34: b SleepRamProc #endif #ifdef CONFIG_TEST 0 x38: b hmi #endif Start VIVI head Reset: disable watch dog timer ;禁止看門狗計(jì)時器mov r1, #0 x53000000 ;WTCON寄存器地址是0 x53000000,清0 mov r2, #0 x0 str r2, r1 共一百零五頁#ifdef CONFIG_S3C2410_MPORT3 ;不符合條件,跳到下面(xi mian)的關(guān)中斷/* 在/v

31、ivi/include/autoconf.h中#undef CONFIG_S3C2410_MPORT3*/ mov r1, #0 x56000000 ;GPACON寄存器地址是0 x56000000 mov r2, #0 x00000005 str r2, r1, #0 x70 ;配置GPHCON寄存器mov r2, #0 x00000001 str r2, r1, #0 x78 ;配置GPHUP寄存器mov r2, #0 x00000001 str r2, r1, #0 x74 ;配置GPHDAT寄存器#endif disable all interrupts ;禁止全部中斷mov r1,

32、#INT_CTL_BASE mov r2, #0 xffffffff str r2, r1, #oINTMSK ;掩碼關(guān)閉所有中斷共一百零五頁2. vivi的第二階段vivi的第二階段是從main()函數(shù)開始,同一般的C語言程序一樣,該函數(shù)在/init/main.c文件中,總共可以分為8個步驟。(1)函數(shù)開始,通過putstr(vivi_banner)打印出vivi的版本。Vivi_banner在/init/version.c文件中定義(2)對開發(fā)板進(jìn)行初始化(board_init函數(shù)),board_init是與開發(fā)板緊密相關(guān)的,這個(zh ge)函數(shù)在/arch/s3c2410/smdk.c

33、文件中。開發(fā)板初始化主要完成兩個功能,時鐘初始化(init_time())和通用IO口設(shè)置(set_gpios())。共一百零五頁void set_gpios(void) GPACON = vGPACON; GPBCON = vGPBCON; GPBUP = vGPBUP; GPCCON = vGPCCON; GPCUP = vGPCUP; GPDCON = vGPDCON; GPDUP = vGPDUP; GPECON = vGPECON; GPEUP = vGPEUP; GPFCON = vGPFCON; GPFUP = vGPFUP; GPGCON = vGPGCON; GPGUP =

34、vGPGUP; GPHCON = vGPHCON; 共一百零五頁GPHUP = vGPHUP; EXTINT0 = vEXTINT0; EXTINT1 = vEXTINT1; EXTINT2 = vEXTINT2; 其中(qzhng),GPIO口在smdk2410.h(viviincludeplatform目錄下)文件中定義。共一百零五頁(3)內(nèi)存映射(yngsh)初始化和內(nèi)存管理單元的初始化工作: mem_map_init(); mmu_init(); 這兩個函數(shù)都在/arch/s3c2410/mmu.c文件中。void mem_map_init(void) #ifdef CONFIG_S3

35、C2410_NAND_BOOT mem_map_nand_boot(); #else mem_map_nor(); #endif cache_clean_invalidate(); tlb_invalidate(); 共一百零五頁如果配置vivi時使用了NAND作為啟動設(shè)備(shbi),則執(zhí)行mem_map_nand_boot(),否則執(zhí)行mem_map_nor()。這里要注意的是,如果使用NOR啟動,則必須先把vivi代碼復(fù)制到RAM中。這個過程是由copy_vivi_to_ram()函數(shù)來完成的。代碼如下: static void copy_vivi_to_ram(void) putstr

36、_hex(Evacuating 1MB of Flash to DRAM at 0 x, VIVI_RAM_BASE); memcpy(void *)VIVI_RAM_BASE, (void *)VIVI_ROM_BASE, VIVI_RAM_SIZE); VIVI_RAM_BASE、VIVI_ROM_BASE、VIVI_RAM_SIZE這些值都可以在smdk2410.h中查到,并且這些值必須根據(jù)自己開發(fā)板的RAM實(shí)際大小修改。這也是在移植vivi的過程中需要注意的一個地方。共一百零五頁mmu_init()函數(shù)中執(zhí)行(zhxng)了arm920_setup函數(shù)。這段代碼是用匯編語言實(shí)現(xiàn)的,針對

37、arm920t核的處理器。(4)初始化堆棧,heap_init()。(定義在vivilibheap.c文件中) int heap_init(void) return mmalloc_init(unsigned char *)(HEAP_BASE), HEAP_SIZE); 共一百零五頁(5)初始化mtd設(shè)備(shbi),mtd_dev_init()。int mtd_init(void) int ret; #ifdef CONFIG_MTD_CFI ret = cfi_init(); #endif #ifdef CONFIG_MTD_SMC ret = smc_init(); #endif #i

38、fdef CONFIG_S3C2410_AMD_BOOT ret = amd_init(); #endif if (ret) mymtd = NULL; return ret; return 0; 共一百零五頁這幾個函數(shù)可以在/drivers/mtd/maps/s3c2410_flash.c里找到。(6)初始化私有數(shù)據(jù),init_priv_data()。(定義在vivilibpriv_datarw.c文件中) (7)初始化內(nèi)置命令,init_builtin_cmds()。通過add_command函數(shù),加載vivi內(nèi)置的幾個命令。(8)啟動boot_or_vivi()。啟動成功(chnggng

39、)后,將通過vivi_shell()啟動一個shell(如果配置了CONFIG_SERIAL_TERM),此時vivi的任務(wù)完成。共一百零五頁4.2嵌入式Linux根文件系統(tǒng)構(gòu)建(u jin)4.2.1 Linux文件系統(tǒng)介紹(jisho) 理論上說一個嵌入式設(shè)備如果內(nèi)核能夠運(yùn)行起來,且不需要運(yùn)行用戶進(jìn)程的話,是不需要文件系統(tǒng)的,文件系統(tǒng)簡單的說就是一種目錄結(jié)構(gòu),由于 linux操作系統(tǒng)的設(shè)備在系統(tǒng)中是以文件的形式存在,將這些文件進(jìn)行分類管理以及提供和內(nèi)核交互的接口,就形成一定的目錄結(jié)構(gòu)也就是文件系統(tǒng),文件系統(tǒng)是為用戶反映系統(tǒng)的一種形式,為用戶提供一個檢測控制系統(tǒng)的接口。 根文件系統(tǒng),我認(rèn)為根

40、文件系統(tǒng)就是一種特殊的文件系統(tǒng),那么根文件系統(tǒng)和普通的文件系統(tǒng)有什么區(qū)別呢?由于根文件系統(tǒng)是內(nèi)核啟動時掛在的第一個文件系統(tǒng),那么根文件系統(tǒng)就要包括Linux啟動時所必須的目錄和關(guān)鍵性的文件,例如Linux啟動時都需要有init目錄下的相關(guān)文件,在 Linux掛載分區(qū)時Linux一定會找/etc/fstab這個掛載文件等,根文件系統(tǒng)中還包括了許多的應(yīng)用程序bin目錄等,任何包括這些Linux 系統(tǒng)啟動所必須的文件都可以成為根文件系統(tǒng)。共一百零五頁圖4.3 Linux系統(tǒng)結(jié)構(gòu)Linux支持多種文件系統(tǒng),包括ext2、ext3、vfat、ntfs、iso9660、jffs、romfs和nfs等,為了

41、(wi le)對各類文件系統(tǒng)進(jìn)行統(tǒng)一管理,Linux引入了虛擬文件系統(tǒng)VFS(Virtual File System),為各類文件系統(tǒng)提供一個統(tǒng)一的操作界面和應(yīng)用編程接口。如4.3所示的Linux系統(tǒng)結(jié)構(gòu)圖。Linux啟動時,第一個必須掛載的是根文件系統(tǒng);若系統(tǒng)不能從指定設(shè)備上掛載根文件系統(tǒng),則系統(tǒng)會出錯而退出啟動。之后可以自動或手動掛載其他的文件系統(tǒng)。因此,一個系統(tǒng)中可以同時(tngsh)存在不同的文件系統(tǒng)。共一百零五頁不同的文件系統(tǒng)類型有不同的特點(diǎn),因而根據(jù)存儲設(shè)備的硬件特性、系統(tǒng)需求等有不同的應(yīng)用場合。在嵌入式Linux應(yīng)用中,主要的存儲設(shè)備為 RAM(DRAM, SDRAM)和ROM(

42、常采用FLASH存儲器),常用的基于(jy)存儲設(shè)備的文件系統(tǒng)類型包括:jffs2, yaffs, cramfs, romfs, ramdisk, ramfs/tmpfs等。共一百零五頁4.2.2 根文件系統(tǒng)的目錄(ml)結(jié)構(gòu)內(nèi)核啟動的最后步驟是掛載根文件系統(tǒng),包含:Init進(jìn)程、Shell、文件系統(tǒng)、網(wǎng)絡(luò)系統(tǒng)等等的工具集、系統(tǒng)配置文件和鏈接庫等。根文件系統(tǒng)是由目錄、Shell、庫、腳本等組成,根文件系統(tǒng)根目錄下除了(ch le)可能的標(biāo)準(zhǔn)的系統(tǒng)引導(dǎo)映象/vmlinuz外一般不含任何文件,所有其他文件是在根文件系統(tǒng)的子目錄中。嵌入式根文件系統(tǒng)要包含了一些必須有的目錄,如:/dev、/bin、/

43、usr、/sbin、/lib、/etc、/proc、/sys 。下面介紹根文件系統(tǒng)中的主要子目錄。/bin :必要的用戶命令(二進(jìn)制文件)。*/boot :引導(dǎo)加載程序使用的靜態(tài)文件。/dev :設(shè)備文件及其他特殊文件。/etc :系統(tǒng)配置文件。共一百零五頁*/home :用戶主目錄。/lib :必要的鏈接庫,例如:C鏈接庫、內(nèi)核模塊。/mnt :臨時(ln sh)掛載的文件系統(tǒng)的掛載點(diǎn)。*/opt :附加軟件的安裝目錄。proc :提供內(nèi)核和進(jìn)程信息的proc文件系統(tǒng)。*/root :root用戶主目錄。sbin :必要的系統(tǒng)管理員命令。tmp :臨時文件目錄。usr :大多數(shù)用戶使用的應(yīng)用

44、程序和文件目錄。var :監(jiān)控程序和工具程序存放的可變數(shù)據(jù)。注意:“*” 目錄在嵌入式Linux上為可選的。共一百零五頁(1)/dev目錄在/dev目錄中,包括設(shè)備文件及其他特殊文件,當(dāng)配置內(nèi)核支持(zhch)設(shè)備文件系統(tǒng)devfs時,此目錄中的設(shè)備節(jié)點(diǎn)由內(nèi)核和驅(qū)動程序自動創(chuàng)建??稍?dev目錄下用ls命令查看該目錄下的內(nèi)容。共一百零五頁(2)/lib目錄在/lib目錄下,包括了glibc鏈接庫,glibc存放系統(tǒng)必要的動態(tài)鏈接庫,支持系統(tǒng)的正常啟動,包括: ld:動態(tài)鏈接(lin ji)器。 libc:主C鏈接器進(jìn)程。 libm :數(shù)學(xué)進(jìn)程,在數(shù)學(xué)函數(shù)中需要用到。 ibcrypt:密碼學(xué)進(jìn)程

45、,多數(shù)涉及認(rèn)證的應(yīng)用程序中需要使用。完整說明參見glibc使用手冊,相應(yīng)的連接庫可以從編譯器的lib目錄下拷取。共一百零五頁(3)/lib目錄在etc 目錄包含很多文件。主要的子目錄如下。 /etc/rc 、/etc/rc.d 、/etc/rc*.d :啟動、或改變運(yùn)行時運(yùn)行的scripts或scripts的目錄。 /etc/passwd :用戶數(shù)據(jù)庫,其中的域給出了用戶名、真實(shí)姓名、家目錄、加密的口令和用戶的其他信息。 /etc/fstab :啟動時mount -a命令(在/etc/rc 或等效的啟動文件中)自動mount的文件系統(tǒng)列表。 /etc/inittab :nit 的配置文件。 /

46、etc/login.defs :login 命令的配置文件。 /etc/profile :登錄時執(zhí)行的文件。系統(tǒng)管理員可為所有用戶建立全局缺省環(huán)境。 /etc/securetty :確認(rèn)安全(nqun)終端,即哪個終端允許root登錄。 /etc/shells :列出可信任的shell。chsh 命令允許用戶在本文件指定范圍內(nèi)改變登錄shell共一百零五頁4.2.3 使用(shyng)Busybox生成工具集Busybox在設(shè)計(jì)上就充分考慮了硬件資源受限的特殊工作環(huán)境,采用一種很巧妙的辦法減少自己的體積,即所有的命令都通過“插件”的方式集中到一個可執(zhí)行文件中,在實(shí)際應(yīng)用過程中通過不同(b tn

47、)的符號鏈接來確定到底要執(zhí)行哪個操作。采用單一執(zhí)行文件的方式最大限度地共享了程序代碼,甚至連文件頭、內(nèi)存中的程序控制塊等其他操作系統(tǒng)資源都共享了,對于資源比較緊張的系統(tǒng)來說,真是最合適不過了。在busybox的編譯過程中,可以非常方便地加減它的“插件”,最后的符號鏈接也可以由編譯系統(tǒng)自動生成。共一百零五頁1Busybox的配置和交叉編譯Busybox的編譯過程(guchng)與內(nèi)核的編譯過程(guchng)很接近,都是先make menuconfig進(jìn)行配置,然后在make進(jìn)行編譯。(1)從/downloads/下載busybox工具。這里選擇busybox-1.1.0.tar.bz2(注:交

48、叉編譯器用arm-linux-gcc 3.4.1/3.3.2)。(2)解壓busybox-1.1.0.tar.bz2,使用命令是:tar jxvf busybox-1.1.0.tar.bz2。(3)進(jìn)入busybox目錄,修改Makefile中的ARCH和CROSS_COMPILE,改成:ARCH ?= armCROSS_COMPILE ?= /usr/local/arm/3.4.1/bin/arm-linux-當(dāng)然CROSS_COMPILE可由開發(fā)者的編譯器位置決定。(4)Make menuconfig進(jìn)行配置,可以選擇靜態(tài)編譯,如果是動態(tài)編譯則要拷貝相應(yīng)的庫文件,默認(rèn)配置保存即可。共一百零

49、五頁圖4.3 配置(pizh)菜單共一百零五頁1. 選擇Busybox的編譯方式:Build Options Build BusyBox as a static binary (no shared libs) 缺省配置為使用(shyng)鏈接庫。2.配置交叉編譯器:Build Options* Do you want to build BusyBox with a Cross Compiler? (/usr/local/arm/3.4.1/bin/arm-linux-)Cross Compiler prefix 3.安裝路徑:Installation Options (./_install)

50、BusyBox installation prefix4.配置其他工具集:Archival Utilities CoreutilsConsole UtilitiesDebian UtilitieEditors共一百零五頁Finding UtilitiesInit UtilitiesLogin/Password Management UtilitiesMiscellaneous UtilitiesLinux Module UtilitiesNetworking UtilitiesProcess UtilitiesShells System Logging UtilitiesLinux Syste

51、m UtilitiesInit Utilities * init * Support reading an inittab file? * Support running init from within an initrd?共一百零五頁5. 配置其他工具集: Archival Utilities工具:tar、zip、unzip Coreutils常用命令:basename cat chgrp chmod date dd df echo env ln ls mkdir mknod mv pwd rm rmdir sleep sort sync wc whoami等等。 Editors編輯命令:

52、vi awk sed等。 Finding Utilities查找(ch zho)命令:find grep xargs Login/Password Management UtilitiesLogin:getty login passwd Networking Utilities網(wǎng)絡(luò)命令集:hostname ifconfig inetd netstat ping route Process Utilities 進(jìn)程命令:free ps sysctl top Shells shell工具:ash等共一百零五頁 System Logging Utilities 日志工具:syslogd klogd

53、Linux System Utilities 系統(tǒng)工具:dmesg fdisk getopt more mount umount(5)#make dep(6)#make(7)#make install之后,在busybox目錄(ml)下生成_install文件夾。其結(jié)構(gòu)( _install )為:/bin/linuxrc/sbin/usr/usr/bin/usr/sbin也可用make all install命令完成編譯。共一百零五頁2文件系統(tǒng)打包用Busybox配置和交叉編譯創(chuàng)建的根文件系統(tǒng)還需用cramfs工具對根文件系統(tǒng)進(jìn)行打包成root.cramfs文件。步驟如下。(1)從/cramf

54、s/下載cramfs工具。(2)解壓cramfs-1.1.tar.gz使用命令:tar zxvf cramfs-1.1.tar.gz。(3)進(jìn)入cramfs工具的根目錄執(zhí)行(zhxng)make。(4)Make后在cramfs工具的根目錄中就會生成一個mkcramfs文件,這就是根文件系統(tǒng)的打包工具。(5)打包,即執(zhí)行命令mkcramfs _install rootfs之后就可產(chǎn)生打包后的根文件系統(tǒng)root.cramfs。共一百零五頁4.2.4 根文件系統(tǒng)啟動(qdng)流程KERNEL起來之后,將運(yùn)行第一個進(jìn)程init,實(shí)際上執(zhí)行的為Busybox的/sbin/init。init的工作是根據(jù)

55、/etc/inittab腳本來進(jìn)行系統(tǒng)的初始化,其格式和命令的含義如下(rxi)::runlevels:action:processsysinit :指定運(yùn)行的第一個程序/腳本。respawn :如果process字段指定的進(jìn)程不存在,則啟動該進(jìn)程,init不等待處理結(jié)束,而是繼續(xù)掃描inittab文件中的后續(xù)進(jìn)程,當(dāng)這樣的進(jìn)程終止時,init會重新啟動它,如果這樣的進(jìn)程已存在,則什么也不做。ctrlaltdel :指定在用戶按下Ctrl-Alt-Del時執(zhí)行的命令。shutdown :當(dāng)系統(tǒng)關(guān)機(jī)時,執(zhí)行相應(yīng)的進(jìn)程。restart :當(dāng)init重新啟動時,執(zhí)行相應(yīng)的進(jìn)程,通常此處所執(zhí)行的進(jìn)程就

56、是init本身。askfirst :類似respawn,不少系統(tǒng)上執(zhí)行的終端應(yīng)用程序的數(shù)量。共一百零五頁注意:加上“-”的語句會在登錄終端之后調(diào)用/etc/目錄下的profile文件(wnjin),而不加“-”的不會執(zhí)行這個腳本。/etccat inittab:sysinit:/etc/init.d/rcS:respawn:-/bin/sh:restart:/sbin/inittty2:askfirst:-/bin/sh:ctrlaltdel:/bin/umount -a r:shutdown:/bin/umount -a r:shutdown:/sbin/swapoff a共一百零五頁這個i

57、nittab執(zhí)行下列動作功能如下:(1)將/etc/init.d/rcS設(shè)置成系統(tǒng)的初始化文件。(2)一直啟動shell。(3)在虛擬終端上啟動askfirst動作的shell。(4)如果init重新啟動,將/sbin/init設(shè)置成它會執(zhí)行的程序。(5)告訴init,在系統(tǒng)關(guān)機(jī)或重啟的時候執(zhí)行umount命令卸載所有文件系統(tǒng),并且在卸載失敗時用只讀模式?jīng)_新安裝以保護(hù)文件系統(tǒng)。init進(jìn)程運(yùn)行(ynxng)腳本是/etc/init.d/rcS,在rcS中掛載文件系統(tǒng),并且執(zhí)行腳本/usr/etc/rc.local;在rc.local中繼續(xù)設(shè)置,最后運(yùn)行用戶的啟動運(yùn)行腳本init.sh。登錄終端

58、之前運(yùn)行腳本/etc/profile。共一百零五頁4.3Linux內(nèi)核(ni h)及啟動過程 Linux系統(tǒng)實(shí)際上由兩個比較獨(dú)立的部分組成,即內(nèi)核部分和系統(tǒng)部分。通常一個Linux系統(tǒng)的啟動過程如下:首先一個不隸屬于任何操作系統(tǒng)的加載程序?qū)inux部分內(nèi)核調(diào)入內(nèi)存,并將控制權(quán)交給內(nèi)存中Linux內(nèi)核的第一行代碼,加載程序的工作就完成了。此后Linux要將自己的剩余部分全部加載到內(nèi)存、初始化所有的設(shè)備、在內(nèi)存中建立好所需的數(shù)據(jù)結(jié)構(gòu)(有關(guān)進(jìn)程、設(shè)備、內(nèi)存等)。到此為止,Linux內(nèi)核的工作告一段落,內(nèi)核已經(jīng)控制了所有硬件設(shè)備。至于操作和使用這些硬件設(shè)備,則是系統(tǒng)部分任務(wù)。內(nèi)核加載設(shè)備并啟動ini

59、t守護(hù)進(jìn)程,init守護(hù)進(jìn)程會根據(jù)配置(pizh)文件加載文件系統(tǒng)、配置(pizh)網(wǎng)絡(luò)、服務(wù)進(jìn)程、終端等。也就是說,內(nèi)核部分初始化并控制大部分硬件設(shè)備,為內(nèi)存管理、進(jìn)程管理、設(shè)備讀、寫等工作做好一切準(zhǔn)備;系統(tǒng)部分加載必需的設(shè)備,配置(pizh)各種環(huán)境以便用戶可以使用整個系統(tǒng)。共一百零五頁4.3.1 Linux內(nèi)核(ni h)結(jié)構(gòu)Linux內(nèi)核主要由五個子系統(tǒng)組成:進(jìn)程調(diào)度,內(nèi)存管理,虛擬文件系統(tǒng),網(wǎng)絡(luò)接口,進(jìn)程間通信。 進(jìn)程調(diào)度(SCHED):控制進(jìn)程對CPU的訪問。當(dāng)需要選擇下一個進(jìn)程運(yùn)行時,由調(diào)度程序選擇最值得運(yùn)行的進(jìn)程。可運(yùn)行進(jìn)程實(shí)際上是僅等待CPU資源的進(jìn)程,如果某個進(jìn)程在等待其它

60、資源,則該進(jìn)程是不可運(yùn)行進(jìn)程。Linux使用了比較簡單的基于優(yōu)先級的進(jìn)程調(diào)度算法選擇新的進(jìn)程。 內(nèi)存管理(MM):允許多個進(jìn)程安全的共享主內(nèi)存區(qū)域。Linux的內(nèi)存管理支持虛擬內(nèi)存,即在計(jì)算機(jī)中運(yùn)行的程序,其代碼、數(shù)據(jù)、堆棧的總量可以超過實(shí)際內(nèi)存的大小,操作系統(tǒng)只是把當(dāng)前使用的程序塊保留在內(nèi)存中,其余的程序塊則保留在磁盤中。必要時,操作系統(tǒng)負(fù)責(zé)在磁盤和內(nèi)存間交換程序塊。內(nèi)存管理從邏輯上分為硬件(yn jin)無關(guān)部分和硬件(yn jin)有關(guān)部分。硬件(yn jin)無關(guān)部分提供了進(jìn)程的映射和邏輯內(nèi)存的對換;硬件(yn jin)相關(guān)的部分為內(nèi)存管理硬件(yn jin)提供了虛擬接口。共一百零五

溫馨提示

  • 1. 本站所有資源如無特殊說明,都需要本地電腦安裝OFFICE2007和PDF閱讀器。圖紙軟件為CAD,CAXA,PROE,UG,SolidWorks等.壓縮文件請下載最新的WinRAR軟件解壓。
  • 2. 本站的文檔不包含任何第三方提供的附件圖紙等,如果需要附件,請聯(lián)系上傳者。文件的所有權(quán)益歸上傳用戶所有。
  • 3. 本站RAR壓縮包中若帶圖紙,網(wǎng)頁內(nèi)容里面會有圖紙預(yù)覽,若沒有圖紙預(yù)覽就沒有圖紙。
  • 4. 未經(jīng)權(quán)益所有人同意不得將文件中的內(nèi)容挪作商業(yè)或盈利用途。
  • 5. 人人文庫網(wǎng)僅提供信息存儲空間,僅對用戶上傳內(nèi)容的表現(xiàn)方式做保護(hù)處理,對用戶上傳分享的文檔內(nèi)容本身不做任何修改或編輯,并不能對任何下載內(nèi)容負(fù)責(zé)。
  • 6. 下載文件中如有侵權(quán)或不適當(dāng)內(nèi)容,請與我們聯(lián)系,我們立即糾正。
  • 7. 本站不保證下載資源的準(zhǔn)確性、安全性和完整性, 同時也不承擔(dān)用戶因使用這些下載資源對自己和他人造成任何形式的傷害或損失。

評論

0/150

提交評論