關鍵詞 :內核,
bootload:
①:把內核讀入內存
②:設置TAG參數
③:啓動
1、R0 = 0;
2、R1 = 機器ID
3、R2 = TAG參數地址
內核: 根據R1,判斷能否支持該機器,調用機器相關的初始化函數
- 解析TAG參數
- 裝載驅動程序:網卡,FALASH
- 掛接根文件系統
- 啓動應用程序
一. 內核啓動流程,據此配置內核(機器ID)
1.1 修改Makefile
ARCH ?= arm
CROSS_COMPILE ?= arm-linux-
1.2 選擇默認配置 :
find -name “*defconfig” //找到defconfig相關文件
/arch/arm/configs //我們是arm架構,我們進入這個文件夾,就會出現一大堆配置文件
ls 2440
ls 2410 //發現了ls的新用法
make s3c2410_defconfig
生成.config
#
# configuration written to .config
#
1.3 make uImage
步驟1:
在UBOOT裏:
set machid 16a // smdk2440 mach-smdk2440.c
或
set machid 7CF // mini2440 mach-mini2440.c
上面分析:設置機器ID
步驟2:
arch\arm\mach-s3c24xx\mach-smdk2440.c
s3c24xx_init_clocks(16934400);
改爲
s3c24xx_init_clocks(12000000);
分析:修改晶振時鐘;
步驟3:
配置/編譯:
make s3c2410_defconfig 或 make mini2440_defconfig
分析:s3c2410_defconfig 這個配置的話支持的單板非常多,如果 make mini2440_defconfig的話只支持mini2440
然後
make uImage
步驟4:
在uboot裏:set bootargs console=ttySAC0,115200 …..
分析:在u-boot裏面必須指定波特率,否則的話就會亂碼;
uboot的默認MACH ID:
Bootm.c(arch\arm\lib):
s= getenv("machid"):
從環境變量中得到machineID
如果s = getenv("machid");成功,則使用它;
如果沒有的話就使用下面的默認值
Smdk2410.c(board\samsung\smdk2440):
gd->bd->bi_arch_number = MACH_TYPE_SMDK2410; // 193
u-boot傳入的值R1,通過
vi ./arch/arm/include/asm/mach-types.h
vi include/generated/mach-types.h //generated 這些文件應該是臨時生成的、
裏面就有:
#define MACH_TYPE S3C2440 362
這個是u-boot傳入的R1的值(也就是上面的362)然後找到這個結構體,調用裏面的s3c244x_restart這個初始化函數
MACHINE_START(S3C2440, "SMDK2440")
/* Maintainer: Ben Dooks <[email protected]> */
.atag_offset = 0x100,
.init_irq = s3c24xx_init_irq,
.map_io = smdk2440_map_io,
.init_machine = smdk2440_machine_init,
.timer = &s3c24xx_timer,
.restart = s3c244x_restart,
MACHINE_END
nfs 32000000 192.168.1.103:/work/nfs_root/uImage_new
bootm 32000000
grep “\”Boot\ Agent\”” * -nR
arch/arm/mach-s3c24xx/common-smdk.c:113: .nmae = “Boot Agent”,
二. 修改分區, 製作新的文件
nfs 30000000 192.168.1.103:/work/nfs_root/fs_mini_mdev.yaffs2
nand erase.part rootfs
nand write.yaffs 30000000 260000 889bc0
nfs 30000000 192.168.1.103:/work/nfs_root/fs_mini_mdev.jffs2
nand erase.part rootfs
nand write.jffs2 30000000 260000 $(filesize
分析:$filesize這個表示下載文件的大小;新版本不用括號,嘗試過&(filesize這樣可以
set bootargs console=ttySAC0,115200 root=/dev/mtdblock3 rootfstype=jffs2
三.製作文件系統
1. 交叉編譯busybox
- tar xjf busybox-1.20.0.tar.bz2
- cd busybox-1.20.0/
- make menuconfig
- make
cd /work/system/busybox-1.20.0
安裝:make install CONFIG_PREFIX=/work/nfs_root/fs_mini_mdev_new
echo $PATH
/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin:/usr/games:/usr/local/arm/4.3.2/bin
查看之後得交叉編譯的目錄在/usr/local/arm/4.3.2/bin
於是進入:cd /usr/local/arm/4.3.2/bin
搜索有關的lib文件
find -name lib
./arm-none-linux-gnueabi/libc/thumb2/lib
./arm-none-linux-gnueabi/libc/thumb2/usr/lib
./arm-none-linux-gnueabi/libc/armv4t/lib
./arm-none-linux-gnueabi/libc/armv4t/usr/lib
./arm-none-linux-gnueabi/libc/lib
./arm-none-linux-gnueabi/libc/usr/lib
./arm-none-linux-gnueabi/lib
./lib
主要選擇
./arm-none-linux-gnueabi/libc/armv4t/lib
./arm-none-linux-gnueabi/libc/armv4t/usr/lib
- 安裝庫
mkdir /work/nfs_root/fs_mini_mdev_new/lib
mkdir /work/nfs_root/fs_mini_mdev_new/usr/lib -p
cp /usr/local/arm/4.3.2/arm-none-linux-gnueabi/libc/armv4t/lib/so
到/work/nfs_root/fs_mini_mdev_new/lib -d 和/work/nfs_root/fs_mini_mdev_new/usr/lib
分析:加上-d選項,意思就是原來它這鏈接你拷貝過來,也把它當成鏈接文件,否則的話就會當成實際文件,到時文件系統非常龐大
3. 構建etc目錄
fs_mini_mdev_new/etc$ ls
fstab init.d inittab
inittab:
# /etc/inittab
::sysinit:/etc/init.d/rcS
s3c2410_serial0::askfirst:-/bin/sh
::ctrlaltdel:/sbin/reboot
::shutdown:/bin/umount -a -r
分析:
::sysinit:/etc/init.d/rcS
先執行這個腳本
s3c2410_serial0::askfirst:-/bin/sh
問1:執行完上面那個腳本之後啓動sh,sh從哪裏得到輸入呢?
答1:從s3c2410_serial0這個設備得到輸入
s3c2410_serial0::askfirst:-/bin/sh改成console::askfirst:-/bin/sh
**問2:**console對應什麼設備呢?
**答2:**set bootargs console=ttySAC0,115200 root=/dev/mtdblock3 rootfstype=jffs2
對應的時ttySAC0,也就是第0個串口
vi init.d/rcS:
#!/bin/sh
ifconfig eth0 192.168.1.17
mount -a
mkdir /dev/pts
mount -t devpts devpts /dev/pts
echo /sbin/mdev > /proc/sys/kernel/hotplug
mdev -s
分析:mount -a根據fstab這個文件的內容來掛接各種根文件系統
cat fstab
# device mount-point type options dump fsck order
proc /proc proc defaults 0 0
tmpfs /tmp tmpfs defaults 0 0
sysfs /sys sysfs defaults 0 0
tmpfs /dev tmpfs defaults 0 0
4. 構建dev目錄,在fs_mini_mdev_new目錄下
ls -l /dev/console /dev/null
crw------- 1 root root 5, 1 2017-03-06 23:01 /dev/console
crw-rw-rw- 1 root root 1, 3 2017-03-06 22:31 /dev/null
在dev目錄下,創建console和null
sudo mknod dev/console c 5 1
sudo mknod dev/null c 1 3
5. 其他空目錄
mkdir proc tmp mnt sys root
mkfs.jffs2 -n -s 2048 -e 128KiB -d fs_mini_mdev_new -o fs_mini_mdev_new.jffs2
分析:
-s是扇區的大小,nandflash一個扇區的大小是2048,
-e是可擦除塊,128KiB
-d是目錄
-o是輸出文件
燒寫:
nfs 30000000 192.168.1.103:/work/nfs_root/fs_mini_mdev_new.jffs2
nand erase.part rootfs
nand write.jffs2 30000000 260000 $filesize
set bootargs console=ttySAC0,115200 root=/dev/mtdblock3 rootfstype=jffs2
nfs 32000000 192.168.1.103:/work/nfs_root/uImage_new
bootm 32000000
SIGILL illegal instruction
6. 重新配置內核支持EABI
set bootargs console=ttySAC0,115200 root=/dev/mtdblock3 rootfstype=jffs2
nfs 32000000 192.168.1.103:/work/nfs_root/uImage_eabi
bootm 32000000
四. 移植YAFFS文件系統/YAFFS文件系統是專門爲nandflash而制定的
1. 獲得源碼
如果系統沒有裝git命令的話
sudo apt-install git
git clone git://www.aleph1.co.uk/yaffs2
2. 打補丁
cd yaffs-dir
./patch-ker.sh c m linux-tree
比如 ./patch-ker.sh c m /work/system/linux-3.4.2
3. 配置內核支持YAFFS
/work/system/linux-3.4.2
make menuconfig
| Location: |
| -> File systems |
| -> Miscellaneous filesystems (MISC_FILESYSTEMS [=y]) |
| -> yaffs2 file system support (YAFFS_FS [=y]) // 選擇Y |
| -> 512 byte / page devices (YAFFS_YAFFS1 [=y]) |
| -> Use older-style on-NAND data format with pageStatus byte (YAFFS_9BYTE_TAGS [=n])
4. 編譯、使用uImage
make uImage
5. 製作、燒寫yaffs映象
mkyaffs2image fs_mini_mdev_new fs_mini_mdev_new.yaffs2
uboot:
nfs 30000000 192.168.1.105:/work/nfs_root/fs_mini_mdev_new.yaffs2
nand erase.part rootfs
nand write.yaffs 30000000 260000 $filesize
- 啓動
set bootargs console=ttySAC0,115200 root=/dev/mtdblock3
nfs 32000000 192.168.1.105:/work/nfs_root/uImage_yaffs
bootm 32000000
7. 沒成功,用替代法查找問題
7.1 UBOOT可能有問題:換上1.1.6的UBOOT
tftp 30000000 u-boot.bin
nand erase.part u-boot
nand write 30000000 u-boot
reset
nfs 30000000 192.168.1.103:/work/nfs_root/fs_mini_mdev_new.yaffs2
nand erase rootfs
nand write.yaffs 30000000 260000 $(filesize)
set bootargs console=ttySAC0,115200 root=/dev/mtdblock3
nfs 32000000 192.168.1.103:/work/nfs_root/uImage_yaffs
bootm 32000000
發現1.1.6的UBOOT沒問題,所以就是我們移植的新UBOOT有BUG:
drivers\mtd\nand\Nand_util.c
if (!need_skip && !(flags & WITH_DROP_FFS)) {
改爲
if (!need_skip && !(flags & WITH_DROP_FFS) && !(flags & WITH_YAFFS_OOB)) {
7.2 YAFFS映象可能有問題
製作了u-boot_new.bin, uImage_new, fs_mini_mdev_new.yaffs
重燒整個系統:
使用jtag工具燒u-boot_new.bin
或使用uboot來更新自己: tftp 30000000 u-boot_new.bin; nand erase.part u-boot; nand write 30000000 u-boot
啓動uboot,用它來燒寫內核、FS k
tftp 30000000 uImage_new; nand erase.part kernel; nand write 30000000 kernel
tftp 30000000 fs_mini_mdev_new.yaffs2; nand erase.part rootfs;
nand write.yaffs 30000000 260000 $filesize
設置參數
set 'nand read 30000000 kernel;bootm 30000000'
set bootargs console=ttySAC0,115200 root=/dev/mtdblock3
set machid 16a
save
使用內核補丁:
patch -p1 < ../linux-3.4.2_100ask.patch
cp config_ok .config
make uImage
生成補丁:
different -urN linux-3.4.2 linux-3.4.2_100ask > linux-3.4.2_100ask.patch