1 前言 嵌入式Linux下的應(yīng)用程序的開(kāi)發(fā),與Windows下應(yīng)用程序的開(kāi)發(fā)大不相同。在Windows環(huán)境中,可以直接在PC上使用各種集成編譯開(kāi)發(fā)工具,完成程序編輯、編譯和運(yùn)行,而在嵌入式Linux環(huán)境下,缺少簡(jiǎn)單、高效的開(kāi)發(fā)工具,程序的開(kāi)發(fā)需要在PC+嵌入式Linux平臺(tái)完成。因此,在程序的調(diào)試運(yùn)行過(guò)程中,需要在Linux服務(wù)器和嵌入式開(kāi)發(fā)板間交換信息,這種信息交換目前最常用的方式是FTP方式,即:先在Linux服務(wù)器上編輯源文件,然后交叉編譯生成可執(zhí)行文件,再通過(guò)FTP下載到嵌入式主機(jī)系統(tǒng)中運(yùn)行,如出現(xiàn)錯(cuò)誤則回到Linux服務(wù)器上重新編譯,再下載運(yùn)行,直到程序正確運(yùn)行為止。但FTP方式缺點(diǎn)是效率比較低,而且無(wú)法在線調(diào)試。這里筆者討論另一種更高效率的信息交換方式,即:NFS(網(wǎng)絡(luò)文件系統(tǒng))方式下嵌入式Linux下的應(yīng)用程序的實(shí)現(xiàn)方法。本文以三星公司ARM9內(nèi)核芯片S3C2410開(kāi)發(fā)板接口為基礎(chǔ),軟件采用Linux 2.4.21,編譯器為arm-linux-gcc的交叉編譯器。 2 嵌入式Linux開(kāi)發(fā)平臺(tái)的建立 在嵌入式Linux下開(kāi)發(fā)應(yīng)用程序,必須建立一個(gè)完善的嵌入式Linux開(kāi)發(fā)環(huán)境。 2.1 嵌入式Linux開(kāi)發(fā)平臺(tái)構(gòu)架 嵌入式Linux 開(kāi)發(fā)平臺(tái)構(gòu)架主要包括:嵌入式Linux 服務(wù)器、工作站、嵌入式開(kāi)發(fā)板系統(tǒng),其結(jié)構(gòu)如圖1所示。 嵌入式Linux 服務(wù)器由一臺(tái)PC充當(dāng),主要作為嵌入式Linux內(nèi)核編譯、應(yīng)用程序編譯的公共平臺(tái),這里安裝標(biāo)準(zhǔn)的Redhat Linux操作系統(tǒng) ,工作站為普通局域網(wǎng)計(jì)算機(jī),可以是一臺(tái)或多臺(tái),安裝Windows操作系統(tǒng),一般用來(lái)完成各種日常工作,可視需要與Linux 服務(wù)器、嵌入式開(kāi)發(fā)板系統(tǒng)連接,嵌入式開(kāi)發(fā)板系統(tǒng)是用來(lái)開(kāi)發(fā)嵌入式應(yīng)用程序,它必須與Linux 服務(wù)器進(jìn)行網(wǎng)絡(luò)連接,目的是建立網(wǎng)絡(luò)文件系統(tǒng),把Linux服務(wù)器上的特定目錄共享到待調(diào)試的嵌入式開(kāi)發(fā)板系統(tǒng)上,從而實(shí)時(shí)地對(duì)應(yīng)用程序進(jìn)行編輯、編譯、調(diào)試。另外嵌入式開(kāi)發(fā)板系統(tǒng)可通過(guò)串口與工作站RS232連接,使用工作站上的超級(jí)終端作為嵌入式開(kāi)發(fā)板系統(tǒng)上的輸入/輸出終端。 2.2 嵌入式開(kāi)發(fā)板操作系統(tǒng)的移植 嵌入式開(kāi)發(fā)板操作系統(tǒng)就是嵌入式Linux,它指的是標(biāo)準(zhǔn)Linux操作系統(tǒng)的內(nèi)核,把標(biāo)準(zhǔn)Linux操作系統(tǒng)的進(jìn)行適當(dāng)?shù)牟眉簦尤胍恍┨囟ǖ墓δ埽纬梢粋(gè)小巧、高效的滿足特定需要的專用操作系統(tǒng),然后移植到ARM體系結(jié)構(gòu)的開(kāi)發(fā)板系統(tǒng)上,移植主要包括建立交叉編譯環(huán)境、修改內(nèi)核源碼、內(nèi)核裁剪和內(nèi)核編譯4個(gè)環(huán)節(jié)。 2.2.1建立交叉編譯環(huán)境 交叉編譯是指利用運(yùn)行在某臺(tái)計(jì)算機(jī)上的編譯器編譯某個(gè)源程序生成在另一種結(jié)構(gòu)計(jì)算機(jī)上運(yùn)行的目標(biāo)代碼的過(guò)程。編譯器的生成依賴于相應(yīng)的函數(shù)庫(kù),而這些函數(shù)庫(kù)又得依靠編譯器來(lái)編譯。建立交叉編譯環(huán)境就是將ARM使用的編譯器(如:arm-linux-gcc)和函數(shù)庫(kù)(如:glibc)安裝到指定目錄,并使用configure配置好Makefile文件。 2.2.2 修改內(nèi)核源代碼 Linux內(nèi)核分為體系結(jié)構(gòu)相關(guān)部分和體系結(jié)構(gòu)無(wú)關(guān)部分。在Linux啟動(dòng)的第一階段,內(nèi)核與體系結(jié)構(gòu)相關(guān)部分首先執(zhí)行,它會(huì)完成硬件寄存器設(shè)置,內(nèi)存映射等初始化工作。然后把控制權(quán)轉(zhuǎn)給內(nèi)核中與系統(tǒng)體系結(jié)構(gòu)無(wú)關(guān)的部分。在移植工作中要修改的代碼主要集中在與體系結(jié)構(gòu)相關(guān)的部分。ARM芯片的體系結(jié)構(gòu)在arch/arm目錄下。首先根據(jù)芯片手冊(cè)修改boot/init.S文件中的:片選組基地址寄存器、DRAM存儲(chǔ)配置寄存器、DRAM片選寄存器、中斷屏蔽寄存器等。然后修改內(nèi)核的鏈接及裝入ELF。最后將系統(tǒng)中可用頁(yè)面的數(shù)目、文件系統(tǒng)大小等信息以參數(shù)形式從啟動(dòng)代碼傳給內(nèi)核,完成設(shè)置陷阱,初始化中斷,初始化計(jì)時(shí)器,初始化控制臺(tái)等一系列操作而使內(nèi)核正常啟動(dòng)。 2.2.3 內(nèi)核裁剪和編譯 Linux內(nèi)核的裁剪支持三種配置方式,即make confg、make menuconfig、make xconfg,一般采用菜單式用命令make menuconfig對(duì)系統(tǒng)進(jìn)行裁剪樣較為簡(jiǎn)單(具體見(jiàn)ARM9配置手冊(cè))。內(nèi)核裁剪之后,最后要進(jìn)行交叉編譯后在arch/arm目錄下生成內(nèi)核映象文件zImage,分別使用命令如下:make clean(清理編譯環(huán)境);make dep(編譯依賴文件);make zImage(編譯內(nèi)核)進(jìn)行內(nèi)核編譯。 3 嵌入式Linux NFS開(kāi)發(fā)環(huán)境的建立 NFS(Network File System)即:網(wǎng)絡(luò)文件系統(tǒng),它是一種將遠(yuǎn)程主機(jī)上的目錄通過(guò)網(wǎng)絡(luò)連接到本地主機(jī)的一種機(jī)制。通過(guò)對(duì)網(wǎng)絡(luò)文件系統(tǒng)的支持,用戶可以很方便地在本地主機(jī)上操作遠(yuǎn)程主機(jī)上的共享目錄。因此,可以通過(guò)建立網(wǎng)絡(luò)文件系統(tǒng),把Linux服務(wù)器上的特定目錄共享到嵌入式開(kāi)發(fā)板系統(tǒng)上,這樣就可以直接在嵌入式開(kāi)發(fā)板上操作Linux服務(wù)器,特別是能夠?qū)崟r(shí)在線地對(duì)程序進(jìn)行編輯、調(diào)試、運(yùn)行,極大地提高了嵌入式Linux下的應(yīng)用程序的開(kāi)發(fā)的效率。 嵌入式Linux 開(kāi)發(fā)平臺(tái)下的NFS環(huán)境配置,主要是對(duì)嵌入式Linux服務(wù)器端的NFS配置和嵌入式開(kāi)發(fā)板系統(tǒng)的NFS客戶端配置,使其支持NFS。 3.1 Linux服務(wù)器端的NFS配置 以root賬戶登錄Linux服務(wù)器,編輯共享目錄配置文件exports,設(shè)定共享目錄及權(quán)限,執(zhí)行# vi/etc/exports命令,在exports文件中添加 /home/work 192.168.33.*(rw)后保存,其作用是是將/home/work設(shè)為共享目錄,IP地址在192.168.33.*范圍內(nèi)的計(jì)算機(jī)可以用讀寫(xiě)的方式訪問(wèn)共享目錄/home/work;接著執(zhí)著命令 #/etc /rc.d /init.d /protmap start來(lái)進(jìn)行端口映射;最后執(zhí)行命令 #/etc /rc.d /init.d /nfs start來(lái)啟動(dòng)NFS服務(wù),啟動(dòng)NFS服務(wù)后,還需檢查L(zhǎng)inux服務(wù)器的iptables、ipchains等選項(xiàng)及文件/etc/hosts.deny、/etc/hosts.allow來(lái)確保沒(méi)有屏蔽NFS使用的端口和允許通信的主機(jī)。配置完畢后,可以在Linux服務(wù)器上運(yùn)行如下命令: # mount –t nfs 192.168.33.1:/home/work /mnt 進(jìn)行NFS服務(wù)器的回環(huán)測(cè)試,驗(yàn)證共享目錄是否能夠被訪問(wèn),若配置成功,執(zhí)行 # is/mnt命令后,能夠在/mnt目錄中看到/home/work共享目錄中的內(nèi)容。 3.2 嵌入式開(kāi)發(fā)板系統(tǒng)NFS客戶端的配置 首先運(yùn)行在嵌入式開(kāi)發(fā)板系統(tǒng)的Linux內(nèi)核支持NFS客戶端,運(yùn)行#make menuconfig命令后,選擇菜單中Fils System--->選項(xiàng),按車回鍵后選擇下級(jí)菜單中的Network File System--- >選項(xiàng),按車回鍵后選中級(jí)菜單中的NFS system support和Provide NFSv3 client support兩項(xiàng),保存退出;然后分別運(yùn)行# make clean、# make dep、# make zImage命令來(lái)重新編譯內(nèi)核,最后在arch/arm/boot中生成一個(gè)內(nèi)核映像文件zImage;然后在Redboot下運(yùn)行命令Redboot >load –v –r –b 0x312000,將Linux內(nèi)核文件zImage下載到嵌入式開(kāi)發(fā)板系統(tǒng)的SDRAM并燒寫(xiě)到FLASH中,其中0x312000為開(kāi)發(fā)板系統(tǒng)SDRAM的地址,文件下載完畢后出現(xiàn)如下提示信息:Raw file loaded 0x00312000-0x003fae5f,再運(yùn)行命令Redboot >fis create –b 0x312000 -1 0xc37df zImage將其保存在FLASH文件系統(tǒng)中;最后分別執(zhí)行命令fis load ramdisk.gz、 load zImageis、exec –r ox1000000 0x312000后,開(kāi)發(fā)板系統(tǒng)中的配置好嵌入式Linux NFS開(kāi)始運(yùn)行。在嵌入式開(kāi)發(fā)板系統(tǒng)的Linux Shell下,運(yùn)行# mkdir /mnt/nfs命令來(lái)建立Linux服務(wù)器輸出共享目錄的掛載點(diǎn),運(yùn)行# mount –o nolock –t nfs 92.168.33.1: /home/work /mnt/nfs命令使Linux服務(wù)器的輸出目錄:/home/work通過(guò)NFS映射到了嵌入開(kāi)發(fā)板系統(tǒng)的/mnt/nfs。 4 嵌入式Linux NFS方式下應(yīng)用程序的實(shí)現(xiàn) 完成了對(duì)Linux服務(wù)器端的NFS配置和嵌入式開(kāi)發(fā)板系統(tǒng)NFS客戶端的配置后,使雙方均能支持NFS才能在此方式下進(jìn)行應(yīng)用程序的開(kāi)發(fā)。 4.1 NFS方式的應(yīng)用程序開(kāi)發(fā)流程 首先在Linux服務(wù)器上編輯源文件,然后交叉編譯,最后生成可執(zhí)行文件,生成的執(zhí)行文件在嵌入式開(kāi)發(fā)板端通過(guò)NFS方式掛載Linux服務(wù)器的共享目錄,讓?xiě)?yīng)用程序直接運(yùn)行在嵌入式開(kāi)發(fā)板系統(tǒng)中,進(jìn)行編譯、調(diào)試。其具體開(kāi)發(fā)流程如圖2所示。 當(dāng)完成了應(yīng)用程序的調(diào)試與運(yùn)行后,就可以將調(diào)試好的應(yīng)用程序下載到嵌入式開(kāi)發(fā)板系統(tǒng)的FLASH文件系統(tǒng),或直接編譯到嵌入式Linux內(nèi)核并燒寫(xiě)到系統(tǒng)的FLASH,從而最終形成一個(gè)獨(dú)立的嵌入式應(yīng)用系統(tǒng)。 4.2 NFS方式下的一個(gè)應(yīng)用程序?qū)嵗?/strong> 下面是一個(gè)求n!的階乘的簡(jiǎn)單示例,來(lái)說(shuō)明基于嵌入式Linux的應(yīng)用程序的實(shí)現(xiàn)方法。 第一步:編輯應(yīng)用程序: 在Linux服務(wù)器的工作目錄:即輸出共享目錄/home/work下使用Vi文本編輯器來(lái)編輯應(yīng)用程序,應(yīng)用程序取名為jiecheng.c。輸入命令 # vi jieccheng.c,完成源程序代碼編輯后,保存文件并退出Vi。 源程序代碼如下: 第二步:編譯應(yīng)用程序: 輸入命令 # arm-linux-gcc –o jiecheng jieccheng.c來(lái)編譯應(yīng)用程序,當(dāng)命令執(zhí)行完畢后,會(huì)在/home/work目錄下生成可執(zhí)行文件jiecheng。 第三步:在嵌入式開(kāi)發(fā)板端掛載Linux服務(wù)器的輸出共享目錄: 啟動(dòng)在嵌入式開(kāi)發(fā)板端系統(tǒng)的配置好的Linux,使用PC超級(jí)終端作為用戶操作界面,輸入如下命令樣 # mkdir /mnt/fns //建立Linux服務(wù)器的輸出共享目錄掛載點(diǎn) # mount –o nolock –t fns 1992.169.3.1:/home/work/ /mnt/nfs //Linux服務(wù)器的輸出目錄:/home/work通過(guò)NFS映射到了嵌入開(kāi)發(fā)板系統(tǒng)的/mnt/nfs。 # cd /mnt/nfs //進(jìn)入目錄 # ls //顯示目?jī)?nèi)容 # ./jiecheng //運(yùn)行求階乘程序 程序運(yùn)行后,用戶可以在使用PC超級(jí)終端上輸入一個(gè)整數(shù)后可以看到輸出結(jié)果。 5 結(jié)束語(yǔ) 由于采用NFS方式避免了將可執(zhí)行文件從Linux服務(wù)器頻繁下載到嵌入式開(kāi)發(fā)板端的過(guò)程,因此用這種方式開(kāi)發(fā)應(yīng)用程序可以大大提高應(yīng)用程序的開(kāi)發(fā)效率。本文的創(chuàng)新點(diǎn)是:在自已構(gòu)造的基于ARM9內(nèi)核芯片,處理器為S3C2410為基礎(chǔ)的開(kāi)發(fā)板系統(tǒng)上,實(shí)現(xiàn)了NFS方式下的應(yīng)用程序開(kāi)發(fā)。 |