天天看點

TI Davinci DM6446開發攻略——根檔案系統的裁剪和移植

<b>一、補充檔案系統知識</b>

Linux根檔案系統是<b>存放tool軟體、lib檔案、script(腳本)、配置檔案、其他特殊檔案、自己開發的應用程式<b>的地方</b>。嵌入式linux的根檔案系統rootfs就像windows作業系統的C、D盤這種概念機制,FLASH對應硬碟。但linux是挂載點的概念,根檔案系統是一個整體,組織到一個樹狀的目錄結構中。這種檔案組織遵守檔案系統科學分類标準FHS,一種國際标準。</b>運作、維護系統所必須的各種

在開發、測試階段,基本上都是使用NFS(網絡檔案系統),NFS檔案系統是在你的開發主機HOST裡,不是在你的闆子裡。制作嵌入式産品根檔案系統,就是要把NFS指向的檔案系統檔案夾裡所有的内容,通過其他少數幾種的Linux檔案系統打包生産一個2進制鏡像檔案,然後以某種方式燒寫到FLASH晶片内。開發階段,特别是應用程式開發、動态加載的驅動子產品開發,使用NFS,可以省去麻煩的根檔案系統鏡像檔案的下載下傳和燒寫過程,便可以在自己闆子上運作這些開發的程式和子產品。

Linux支援超過50種檔案系統,但是隻有少數幾種在嵌入式OS中常用,見下圖。linux嵌入式産品的根檔案系統是需要燒寫到Flash晶片裡。

<a href="http://blog.51cto.com/attachment/201006/135801250.jpg" target="_blank"></a>

Cramfs檔案系統:(Compressed ROM File System)是個簡單,壓縮的,隻讀的檔案系統。除了可以用于MTD下隻讀并且極少更新img的NOR/NAND,IDE的CF,FTL/NFTL的NOR/NAND,可作為RAM disk的IMG存儲。由于簡單,Cramfs有一些限制,例如最大支援16M(?256M),沒有目前(.)和父(..)目錄,頁大小固定為4096,gid(8位)最大為255,所有的連結檔案計數都是1等等。在cramfs檔案系統中,每一頁(4KB)被單獨壓縮,可以随機頁通路,其壓縮比高達2:1,為嵌入式系統節省大量的Flash存儲空間,使系統可通過更低容量的FLASH存儲相同的檔案,進而降低系統成本。Cramfs檔案系統以壓縮方式存儲,在運作時解壓縮,是以不支援應用程式以XIP方式運作,所有的應用程式要求被拷到RAM裡去運作,但這并不代表比Ramfs需求的RAM空間要大一點,因為Cramfs是采用分頁壓縮的方式存放檔案,在讀取檔案時,不會一下子就耗用過多的記憶體空間,隻針對目前實際讀取的部分配置設定記憶體,尚沒有讀取的部分不配置設定記憶體空間,當我們讀取的檔案不在記憶體時,Cramfs檔案系統自動計算壓縮後的資料所存的位置,再即時解壓縮到RAM中。另外,它的速度快,效率高,其隻讀的特點有利于保護檔案系統免受破壞,提高了系統的可靠性。由于以上特性,Cramfs在嵌入式系統中應用廣泛。但是它的隻讀屬性同時又是它的一大缺陷,使得使用者無法對其内容對進擴充。

制作Cramfs根檔案系統指令如下:

#mkcramfs [-h] [-e edition] [-i file] [-n name] dirname outfile

mkcramfs的各個參數解釋如下:

 -h:顯示幫助資訊

-e edition:設定生成的檔案系統中的版本号

-i file:将一個檔案映像插入這個檔案系統之中(隻能在Linux2.4.0以後的核心版本中使用)

-n name:設定cramfs檔案系統的名字

dirname:指明需要被壓縮的整個目錄樹

outfile:最終輸出的檔案

cramfsck的指令格式:

cramfsck [-hv] [-x dir] file

cramfsck的各個參數解釋如下:

-h:顯示幫助資訊

-x dir:釋放檔案到dir所指出的目錄中

-v:輸出資訊更加詳細

file:希望測試的目标檔案

例子:#mkcramfs rootfs rootfs.cramfs生成rootfs.cramfs檔案系統鏡像.其中rootfs是你調試的根檔案系統的檔案夾,rootfs.cramfs是生産鏡像檔案的名字。

Squashfs檔案系統:是壓縮的隻讀的fs,保留了Cramfs很多優點,去掉它的限制。壓縮比更高。是一個不錯的檔案系統。指令為:#mksquashfs [source] [dest]

JFFS2檔案系統:可寫、保留資料、壓縮、掉電保護,提供wear leveling,适合闆載NOR、NAND和Doc。JFFS2提供垃圾回收機制,通常可以很好地工作。但是當檔案系統接近極限或者要求更新一個非常大的檔案,垃圾回收的時間會很長,将會延遲檔案系統的操作,這會對沒有考慮到這種情況的某些實時要求的軟體帶來負面的影響。當空間滿的時候,嘗試更新或者階段檔案内容會被提示檔案系統已滿并失敗,即使看起來不要求添加存儲block,這是因為日志結構檔案系統,需要在log中增加log。在使用的時候,我們應保證存儲空間的充足,上面的應用能夠容忍時延(避免快滿時候垃圾回收的消耗影響)。 JFFS2用途很廣,但是對于現在容量巨大的閃存不适合,新的UBI檔案系統出現。JFFS2的不可擴充性是最大的問題,作為JFFS2的更新,JFFS3支援大容量的閃存。JFFS2使用MTD工具:

#mkfs.jffs2 –r ottfs/ –o images/rootfs-jffs2.img –e 128kiB 其中128是指擦寫block的大小,如果超過實際閃存的大小,會引起檔案系統的崩潰,如果太小,block内有部分存儲空間沒能利用。

#sumtool –i rootfs-jffs2.img –o rootfs-jffs2-summed.img –e 128KiB 增減erase block的summary node。

YAFFS2檔案系統:是可寫,下電保護的檔案系統,廣泛引用于Linux和RTOSeS。和JFFS2相比,它減少一些功能,是以速度更快、占用記憶體資源更少。YAFFS2自帶NAND晶片的驅動,是專門為NAND閃存設計的。以前的YAFFS隻支援512-BYTE/Page的NAND,而YAFFS2不但相容512-BYTE/Page,還支援目前流行的2048-BYTE/Page大容量NAND FLASH。YAFFS2檔案系統的鏡像工具是mkyaffs2img。随便在GOOGLE上輸入mkyaffs2img就可以找到滿螢幕的制作方法,這裡不用介紹。

RAMFS檔案系統:

讨論RAMFS,就不得不讨論RAM disk,在RAM中,而作為一個block裝置,核心可以同時支援多個RAM disk。通常用于儲存磁盤檔案系統中壓縮的img。這在嵌入式作業系統的初始化中使用,kernel可以從儲存設備中提取initial RAM disk(initrd)img作為的他的根檔案系統。一開始,kernel根據boot的參數是否表面intrid,如果是,他将從特定的存貯媒體提取檔案系統的img并放入RAM disk,同時mount為根檔案系統。initrd的機制是以最簡單的方式提供一個帶根檔案系統的核心在RAM中。對于新的系統,推薦使用Initramfs機制。

Tmpfs檔案系統:也是RAM disk的一種,可以使用實體記憶體,是一個存放在虛拟memory的檔案系統,不提供永久儲存,适合于存儲臨時的資料,例如/tmp,用于Linux的page cache和dentry chache。

RAM disk的特點就是速度快,因為在RAM運作的。缺點就是每次重新啟動系統時,前面的工作就無法儲存。建立RAM Disk使用的指令式mke2fs。

有關嵌入式常用的檔案系統詳細介紹和制作指令、方法,大家可以在網上搜尋得到。

<b>二、</b><b>TI davinci</b><b>根檔案系統</b><b>target</b><b>介紹</b>

在mv_pro_5.0.0/montavista/pro/devkit/arm/v5t_le目錄下,有個target的檔案夾,這個就是TI EVM的根檔案系統了。Target裡的内容,見下圖,本人是單獨COPY出來到自己工作目錄下,這點在《開發環境篇》有介紹。TI在這個target檔案系統包裡放置很多開發工具,其實就是一個開發應用程式的環境,你進到usr目錄下就明白這點,裡邊包括交叉編譯指令、很多頭檔案和應用程式的源代碼、usr/lib裡的lib檔案,等等。其實這些東西肯定是不能全部燒到自己的闆子裡的。單單這個usr裡相關的檔案大小就達1G!!!因為TI EVM東西多,複雜,是以我們裁減的時候,最好做好備份。當然,有些朋友是自己手動重新制作根檔案系統,再借助“Busybox”這個大名鼎鼎的嵌入式linux瑞士軍刀,一個精簡的檔案系統就出來了。本人在S3C2440、2410的闆子上玩過,挺不錯的,非常精簡。本文暫且不讨論這種方法。

<a href="http://blog.51cto.com/attachment/201006/135858285.jpg" target="_blank"></a>

<b>三、</b><b>TI davinci</b><b>根檔案系統</b><b>target</b><b>的裁減</b>

進入自己工作的target檔案夾裡,見上圖:

bin檔案夾:裡邊主要是一些linux shell指令,所有使用者都可以使用的、基本的指令,都是很基本的東西,暫時不用動它,保留。

boot檔案夾:是存放編譯核心的一些相關檔案,比如uImage等,這些東西沒必要放到闆子上的檔案系統裡,删除掉。

dev檔案夾:存放非常多的裝置節點,如果你對這些節點不是很熟悉,分不清哪些是你系統用到的,哪些是不用的,可以保留,整個dev隻有16~17k的大小。當然節點太多也不好。

 home檔案夾:空的檔案夾,系統運作會用到,普通使用者的主目錄,一定要保留。

 lib檔案夾:很多工具和應用程式使用的庫檔案,不是高高手,最好不要删掉裡邊的檔案。

 media檔案夾:空的檔案夾,保留。

 mnt檔案夾:空檔案夾,以後使用U盤和SD卡時,會挂到該目錄,是以保留。

 opt檔案夾:空檔案夾,自己開發的一些應用程式可以放到這裡,比如TI evm的一些應用程式就放在/opt/dvsdk/dm6446/,存放encode,decode,encodedecode的應用程式,等等。

 proc檔案夾:空的檔案夾,系統運作會用到,proc檔案系統的挂載點,保留。

 root檔案夾:空的檔案夾,系統運作會用到,root使用者的主目錄,一定要保留。

 sbin檔案夾:存放很多工具和基本的系統指令,它們用于啟動系統、修複系統,在嵌入式産品裡,可以把不常用的mkfs.xx的檔案全部去掉。其他有很多工具和指令,要根據你自己的産品,不用到的都删掉,裁減sbin建議再單獨備份一下sbin,通過NFS,一邊删除,一邊測試,保證删除掉後你的産品還很好地工作。這是一種笨辦法,畢竟要全部了解裡邊的每個指令和工具的作用也需要很多時間。建議這個檔案夾最好不要動太多手腳。

 srv檔案夾:空的檔案夾,保留。

 sys檔案夾:空的檔案夾,系統運作會用到,比如sysfs,保留。

 tmp檔案夾:空的檔案夾,系統運作會用到,存放臨時檔案,保留。

 usr檔案夾:上面提到,這個檔案有很多在産品出廠不用到的東西,armv5tl-montavista-linux-gnueabi檔案夾直接删除掉;bin檔案夾裡的arm_v5t_le-XXXXX和armv5tl-montavista-linux-gnueabi-XXX也去掉吧;include、local、share、src、X11R6檔案夾全部去掉;Usr/lib/tcng/test幹掉;然後根據自己産品的,像perl5、python2.4、X11等等,不用到就搞定它們。笨辦法就是使用NFS和闆子共同測試,這樣下來usr就小多了。

var檔案夾:存放可變的資料,var/cache/cracklib裡的檔案很大,不知在TI EVM有什麼用,本人不用;var\lib\rpm裡的檔案本人也不用;var/www/html/manual是在開發html的時候用到,本人不用。這幾個都是var裡耗空間的檔案夾。另外,在使用NFS調試的時候,var/log下的檔案會儲存每次核心啟動的列印資訊,測試多了,debug,kern.log,messages等檔案也加大,是以制作時要注意這些檔案的裁減。

    按照上面的動作下來,一個可以用的根檔案系統也出來了,但還不是簡潔高效的,有些東西還得根據自己的闆子要支援的功能選擇性保留和裁減。有些工具、指令、應用程式開始沒用到,但是後來更新産品會用到,是以,裁減要有針對性和規劃性。特别是有些産品使用小于等于64M NAND的嵌入式産品,要做的工作就更多,這裡僅供學習和參考。

<b>四、</b><b>TI davinci</b><b>根檔案系統</b><b>target</b><b>的移植</b>

<b>1</b><b>、系統的分區:</b>

在linux-2.6.18移植的部落格文章介紹了FLASH的分區,這裡就不用重複了,一般分區是: Bootloader(UBL+U-BOOT)+參數 為mtdblock0,kernel為mtdblock1,根檔案系統rootfs為mtdblock2。也有這樣分的:Bootloader(UBL+U-BOOT) 為mtdblock0,參數為mtdblock1,kernel為mtdblock2,根檔案系統為mtdblock3。Bootloader要從FLASH 加載根檔案系統,比如jffs2的根檔案系統,u-boot的bootargs應該是:mem=118M console=ttyS0,115200n8 rootfstype=jffs2 root=/dev/mtdblock2 noinitrd rw ip=off或者是其他類型的檔案系統。同時,u-boot對根檔案系統的燒寫要支援,因為jffs2,cramfs,yaffs2等每種檔案系統的燒寫格式都不一樣,燒寫的位址一定要和核心的FLASH分區位址一一對應。(補充:在DVSDK2.0中,U-BOOT的參數mem=118M,不再是120M,因為TI DVSDK2.0 CODEC ENGINE要求配置設定給cmem的大小是10M)。

<b>2</b><b>、核心選擇支援對應的檔案系統</b>

   通過make menuconfig的配置界面,你的闆子要支援什麼樣的檔案系統,是cramfs,Squashfs,jffs2還yaffs2,則要對對MTD等相關選項進行選擇,見linux-2.6.18移植的部落格。

 <b>  3<b>、對根檔案系統權限操作</b></b>

Target下每個目錄的權限不是全部一樣的,根據自己的檔案系統的類型,比如yaffs2,tmp、var等目錄可以使用chmod –R 777 tmp , chmod –R 777 var指令設定,檔案夾域的設定使用chown的指令。為什麼要這樣強調呢?也許很多人調試DAVINCI 闆子會碰到:Starting OpenBSD Secure Shell server: sshd/var/empty/sshd must be owned by root and not group or world-writable. failed (255: ).這個就是根檔案系統權限和域得設定有問題。

<b>4</b><b>、</b><b>etc</b><b>目錄下的移植</b>

   A、拷貝你的LINUX開發主機etc目錄下的passwd、group、shadow檔案到etc目錄下。這樣目标闆就使用和你LINUX主機一樣的登入賬号和密碼了。如果passwd、group、shadow被破壞了,如何都進不去闆子的shell指令行,而且你的産品沒有嚴重網絡安全要求,這裡還有一個絕招:把target/etc 下的securetty檔案改個名字,不用securetty就可以了,這樣輸入賬号直接回車就可以了。

   B、etc目錄下建立一個目錄sysconfig,并建立檔案HOSTNAME,内容為“你公司名字或你喜歡的名字”。同時在etc/init.d/下RcS檔案最後面加入:/bin/hostname –F /etc/sysconfig/HOSTNAME,在profile最後面加入:

<b>USER="`id -un`" </b><b>(注意</b><b> ` </b><b>是鍵盤</b><b>1</b><b>旁邊的</b><b> ` </b><b>)</b>

<b>LOGNAME=$USER</b>

<b>PS1='[\u@\h \W]# '  </b><b>(注意</b><b> ‘ </b><b>是鍵盤</b><b> ; </b><b>旁邊的</b><b> ‘ </b><b>在</b><b>linux</b><b>檔案下顯示不一樣)</b>

<b>PATH=$PATH</b>

<b>HOSTNAME=`/bin/hostname` </b><b>(注意</b><b> ` </b><b>是鍵盤</b><b>1</b><b>旁邊的</b><b> ` </b><b>)</b>

<b>export USER LOGNAME PS1 PATH</b>

這樣在闆子上進入shell的指令行時,會顯示“[root@你定義的名字~]#”的格式。

   C、etc/fstab檔案修改:目前這個本人直接使用TI的,但是自己的産品有時會定義

sysfs              /sys         sysfs       noauto                          0 0

tmpfs             /dev/shm tmpfs      noauto                                 0 0

目前沒有驗證,如果哪個網友對這方面熟悉,可以在部落格上讨論。

   D、流程介紹

      根檔案系統挂接到VFS(linux虛拟檔案系統,一種軟體接口機制,原理這裡不描述)成功後,會根據腳本和配置一步一步運作。我們可以通過以下流程去熟悉:

先看inittab

      次看init.d/rcS

然後etc/rc.d/rcS.d,rcS.x等檔案,開機是啟動/etc/rc.d/rcS.d/下的腳本,然後是/etc/rc.d/rc3.d/下的腳本。隻需把使用者的程式編譯稱shell腳本,放在rc3.d下面就可以了。

      S開頭的腳本基本上是系統運作初始化要做的工作,K開頭就是關機要做的工作。

     客戶如果要在開機運作自己的某些應用程式,也可以修改etc/init.d/rcS,在

for i in /etc/rc.d/rcS.d/S??*

do

           # Ignore dangling symlinks for now.

           [ ! -f "$i" ] &amp;&amp; continue

           case "$i" in

                 *.sh)

                      # Source shell script for speed.

                      (

                          trap - INT QUIT TSTP

                          set start

                          . $i

                      )

                      ;;

               *)

                     # No sh extension, so fork subprocess.

                     $i start

                     ;;

            esac

done

在這後面加自己的運作指令就可以了。

   E、制作根檔案系統映像檔案

      就是使用mkcramfs、mkyaffs2image這些指令對整個修改的target檔案進行鏡像打包了,格式上面已經介紹了。

<b>五、點評</b>

以上是本人的經驗之談,肯定有描述不足的地方,希望網友能在部落格裡指出來,大家一起學習。到目前為止,有關DM6446開發攻略的主架構的文章,基本上接近尾聲,最後1篇,有關自己開發的GPIO驅動移植的文章,近期也會出來。以後要寫也是某個環節的補充。其實寫這些文章,就是希望有這方面的開發高手過來點評一下,指出不足和錯誤的地方。畢竟本人在這方面還有很多東西要學習。

本文轉自 zjb_integrated 51CTO部落格,原文連結:http://blog.51cto.com/zjbintsystem/339865,如需轉載請自行聯系原作者

繼續閱讀