嵌入式操作系統的實現(幾年前的畢業設計之四)

當系統在虛擬機中測試完畢,就可以將其移植到U盤上了。本系統是在U盤上實現的,如在其他載體上類同。
51 U盤的分區格式化
首先將U盤分區格式化。可用Linux下的fdisk分區工具進行分區,用mkfs工具進行格式化。本人就一塊32MB的U盤,還要用來保存一些windows文件,故將其分爲兩個區,一個linux分區,一個windows分區。
#fdisk /dev/sdc
利用fdisk命令對U盤進行分區。

    Disk /dev/sdc: 32 MB, 32768000 bytes

3 heads, 32 sectors/track, 666 cylinders
Units = cylinders of 96 * 512 = 49152 bytes
 

device Boot Start     End    Blocks   Id  System

/dev/sdc1      1       600     28784   83 Linux

/dev/sdc2     601      666      3168    5 Extended

/dev/sdc5     601      666      3152    4 FAT16 <32M

分區中sdc1是用來裝linux系統的(28M)
sdc5是fat16格式,主要用來下載網頁用。
 
#mkfs t ext2 /dev/sdc1
#mkfs t vfat /dev/sdc5
用mkfs對分區格式化。
52 U盤的初始化
如果在系統剪裁中進行了第四步剪裁,即壓縮了根文件系統,將內核模擬成硬盤使用,將不必考慮U盤的初始化問題。如不進行第四步,雖然usb-storage模塊已包括在內核,但是由於U盤的初始化過程比執行/sbin/init慢,導致內核已經啓動完成了,優盤還沒有完成初始化工作,因此根文件系統沒有加載,這時執行/sbin/init命令肯定不成功。有兩種方式能使內核等待3秒等待U盤初始化完畢再啓動。
(1)利用busybox重新構造initrd.
在啓動內核時加載initrd.img文件到內存中,利用initrd文件中的busybox的sleep命令,使內核等待3秒使U盤完成初始化工作,再執行/sbin/init指令。該方式需要自己構造initrd文件,而且會增大initrd文件(增大300kb)。
①建立initrd.img文件

#mkdir -p /mnt/initrd

#cd /tmp

#cp /usr/src/linux-2.6.0/drivers/scsi/BusLogic.ko /lib/modules/2.6.0/kernel/drivers/scsi

//mkinitrd需要BusLogic.ko
# mkinitrd /tmp/initrd.gz 2.6.0
  
   ②編譯busybox
   由於initrd中沒有libc.so.6和ld-linux.so.2兩個庫文件,所以在編譯busybox時要把選擇不帶共享庫,因這裏只用到它的sleep命令功能,所以編譯選項中只選sleep選項。具體詳見文件系統剪裁中busybox的使用方法。
 
③解壓initrd.img文件,修改啓動腳本linuxrc

#gunzip initrd.gz

#mount -o loop /tmp/initrd /mnt/initrd

#cp /sbin/busybox /mnt/initrd/bin

#cd /mnt/initrd/bin

#ln -s busybox sleep

#vi /mnt/initrd/linuxrc

  加入如下內容:
  echo 'wait 3 seconds.....'
/bin/sleep 3
 
④重新生成initrd.img文件
  由於缺省建立的initrd文件比較大(爲4MB),爲了加快優盤的啓動,必須減小它。具體操作如下:
  #mkdir -p /mnt/initrdusb
  #cd /tmp
  #dd if =/dev/zero of= /tmp/initrdusb bs=1M count=1
  #mke2fs -m 0 initrdusb
  #mount -o loop /tmp/initrdusb /mnt/initrdusb

#cp -a /mnt/initrd/* /mnt/initrdusb

#cd /mnt/initrdusb
#rm ./bin/insmod        //因不用加載模塊,故不//insmod可節省200K空間。
#rm ./bin/modporbe      //同上

#rm ./lib/BusLogic.ko      // BusLogic.ko已編入內核,//故可刪。

#cd /
  # umount /mnt/initrd
  # umount /mnt/initrdusb
  # cd /tmp
  # gzip -9 initrdusb

# cp initrdusb.gz /boot/initrd-2.6.0-usb.img

 
(2)通過更改linux2.6.0/init/do_mounts.c內核文件,再重新編譯內核,使系統初始化時等3秒。該方式不會增大initrd文件,但需要修改內核文件。文件修改如下(+號後面爲添加的內容):
void __init mount_block_root(char *name, int flags)
{
       char *fs_names = __getname();
       char *p;
       char b[BDEVNAME_SIZE];
       get_fs_names(fs_names);

+     printk("Please wait for 3 seconds....../n");

+      __set_current_state(TASK_INTERRUPTIBLE);

+      schedule_timeout(HZ);

+     __set_current_state(TASK_INTERRUPTIBLE);
+      schedule_timeout(HZ);
+     __set_current_state(TASK_INTERRUPTIBLE);
+     schedule_timeout(HZ); 
53 系統整合及測試
當完成U盤初始化initrd的構造後(也可以重新編譯內核或採用ramdisk),就可以在U盤上整合系統了。

(1)             將測試好的系統打包

#mount /dev/sdb1 /mnt/sdb1
#cd /mnt/sdb1

#tar cvzf /mnt/hgfs/windows/redhat9-usb-ok.tar.gz *

(2)             將打包好的系統恢復到U盤上(被系統識爲sdd)

#mkdir  p  /mnt/sdd1
#mount /dev/sdd1  /mnt/sdd1
#cd /mnt/sdd1

#tar zxvf /mnt/hgfs/windows/redhat9-usb-ok.tar.gz

(3)             修改U盤系統中的grub.conf文件

改爲:
default=0
timeout=10
splashimage=(hd0,0)/boot/grub/splash.xpm.gz
title Red Hat Linux (2.6.0)
        root (hd0,0)

        kernel /boot/vmlinuz-2.6.0 ro root=LABEL=/

        initrd /boot/initrd-2.6.0.img

(4)             增加根目錄標識

#e2label /dev/sdc1 /
如不進行這步,系統將無法啓動。
mount: error 6 mounting ext2

pivotroot pivot_root(/sysroot,/sysroot/initrd) failed:2

umount /initrd/proc
的錯誤提示。

(5)             安裝grub

因爲系統最終將在機器上運行,不是在虛擬機上運行,故安裝grub應在真實的linux下進行。而且虛擬機上的BOIS不支持從U盤啓動。在機器上啓動Redhat9.0
#grub
grub>root (hd1,0)
grub>setup (hd1)

(6)             設置BIOS

在BIOS中設置
Advanced BIOS Features
    First Boot Device (USB-HDD)
First Boot Device (HDD-0)
這需要你的主板支持從U盤啓動。
最後插入U重新啓動系統。測試系統的網絡功能和安全服務是否正常運轉。
本章主要介紹了嵌入式操作系統如何在U盤上實現的,其中詳細介紹瞭如何實現U盤的初始化以使內核在U盤上能正常啓動,簡單說明了在整合系統時要注意的幾個要點。
 
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章