为ARM(AT91RM9200)编译Linux Kernel

一、获取Linux Kernel和对应的AT91 patch
1、获取Linux内核(以2.6.25版为例),解压到当前目录,然后进入解压生成的内核目录:
代码
wget http://www.kernel.org/pub/linux/kernel/v2.6/linux-2.6.25.tar.bz2
tar xvjf linux-2.6.25.tar.bz2
cd linux-2.6.25/


2、下载Linux的AT91 patch,该patch所在的网站http://maxim.org.za/由于某种原因在国内无法访问(想办法解决便可),而后应用该patch:
http://maxim.org.za/AT91RM9200/2.6/2.6.25-at91.patch.gz

http://maxim.org.za/at91_26.html

代码
zcat -cf 2.6.25-at91.patch.gz | patch -p1


二、配置并编译Linux Kernel
1、清除所有旧配置及旧编译结果:
代码
make mrproper

2、在图形界面下配置内核(可能提示图形界面所需的几个库没安装,装好它们 sudo apt-get install libgtk2.0-dev libglade2-dev):
代码
make ARCH=arm at91rm9200dk_defconfig
make ARCH=arm gconfig

3、交叉编译它:
代码
make ARCH=arm CROSS_COMPILE=arm-linux-

由于电脑比较慢,于是我出去喝了一杯水……

结果会在arch/arm/boot下生成几个文件,以下是编译的一点片断:
引用
OBJCOPY arch/arm/boot/Image
Kernel: arch/arm/boot/Image is ready
AS arch/arm/boot/compressed/head.o
GZIP arch/arm/boot/compressed/piggy.gz
AS arch/arm/boot/compressed/piggy.o
CC arch/arm/boot/compressed/misc.o
LD arch/arm/boot/compressed/vmlinux
OBJCOPY arch/arm/boot/zImage
Kernel: arch/arm/boot/zImage is ready
Building modules, stage 2.
MODPOST 1 modules
CC drivers/char/hw_random/rng-core.mod.o
LD [M] drivers/char/hw_random/rng-core.ko

在生成内核映像之后把arch/arm/boot/compressed目录下的vmlinux用交叉objcopy转成二进binary文件:
代码
arm-linux-objcopy -O binary -S vmlinux arm_linux.bin


用gzip将其压缩:
代码
gzip -v9 arm_linux.bin

生成的文件为arm_linux.bin.gz

然后复制到U-Boot目录下的tools中,因为要用那里的mkimage将该文件转换成U-Boot能够识别的uImage:
代码
cp arm_linux.bin.gz /tools
cd /tools
./mkimage -n 'AT91 Kernel' -A arm -O linux -C gzip -a 0x20008000 -e 0x20008000 -d arm_linux.bin.gz uImage20008000


利用U-Boot将其下载到目标板(我选择放置kernel的FLASH地址从0x100a0000开始)。

由于未设置启动参数,因此重新上电后仍停留在U-Boot>提示符,需要手动启动内核。

先检查一下是否识别出内核映像:
代码
U-Boot> imls
Image at 100A0000:
   Image Name:   AT91 Kernel
   Image Type:   ARM Linux Kernel Image (gzip compressed)
   Data Size:    1121309 Bytes =  1.1 MB
   Load Address: 20008000
   Entry Point:  20008000
   Verifying Checksum ... OK

可见能够识别且校验和通过。手动启动内核:
代码
U-Boot> bootm 100a0000
## Booting image at 100a0000 ...
   Image Name:   AT91 Kernel
   Image Type:   ARM Linux Kernel Image (gzip compressed)
   Data Size:    1121309 Bytes =  1.1 MB
   Load Address: 20008000
   Entry Point:  20008000
   Verifying Checksum ... OK
   Uncompressing Kernel Image ... OK
No initrd
## Transferring control to Linux (at address 20008000) ...

Starting kernel ...

Uncompressing Linux.......................................................................... done, booting the kernel.

Error: unrecognized/unsupported machine ID (r1 = 0x000000fb).

Available machine support:

ID (hex)    NAME
00000106    Atmel AT91RM9200-DK

Please check your kernel config and/or bootloader.

无疑问内核尝试跑起来了,还没有RAM Disk,因此 No initrd
U-Boot将控制权交给Linux之后,Linux先解压缩后启动,问题是识别的机器ID为0xFB(251),和内核支持的机器ID0x106(262)不符,得改一下machine ID才行。

我选择了修改Linux Kernel中linux-2.6.25/arch/arm/mach-at91目录下的board-dk.c文件:
将文件最后的MACHINE_START(AT91RM9200DK, "Atmel AT91RM9200-DK")
   修改为MACHINE_START(AT91RM9200, "Atmel AT91RM9200")

重新编译内核并更新到目标板,启动的信息如下:
引用
U-Boot> bootm 100a0000
## Booting image at 100a0000 ...
Image Name: AT91 Kernel
Image Type: ARM Linux Kernel Image (gzip compressed)
Data Size: 1121241 Bytes = 1.1 MB
Load Address: 20008000
Entry Point: 20008000
Verifying Checksum ... OK
Uncompressing Kernel Image ... OK
No initrd
## Transferring control to Linux (at address 20008000) ...

Starting kernel ...

Uncompressing Linux.......................................................................... done, booting the kernel.
Linux version 2.6.25 (mifarelight@mifarelight-desktop) (gcc version 4.0.0 (DENX ELDK 4.1 4.0.0)) #2 Thu May 22 15:07:58 CST 2008
CPU: ARM920T [41129200] revision 0 (ARMv4T), cr=c0007177
Machine: Atmel AT91RM9200
Memory policy: ECC disabled, Data cache writeback
Clocks: CPU 179 MHz, master 59 MHz, main 18.432 MHz
CPU0: D VIVT write-back cache
CPU0: I cache: 16384 bytes, associativity 64, 32 byte lines, 8 sets
CPU0: D cache: 16384 bytes, associativity 64, 32 byte lines, 8 sets
Built 1 zonelists in Zone order, mobility grouping on. Total pages: 8128
Kernel command line: mem=32M console=ttyS0,115200 initrd=0x20410000,3145728 root=/dev/ram0 rw
AT91: 128 gpio irqs in 4 banks
PID hash table entries: 128 (order: 7, 512 bytes)
Console: colour dummy device 80x30
console [ttyS0] enabled
Dentry cache hash table entries: 4096 (order: 2, 16384 bytes)
Inode-cache hash table entries: 2048 (order: 1, 8192 bytes)
Memory: 32MB = 32MB total
Memory: 27016KB available (2064K code, 186K data, 104K init)
SLUB: Genslabs=12, HWalign=32, Order=0-1, MinObjects=4, CPUs=1, Nodes=1
Mount-cache hash table entries: 512
CPU: Testing write buffer coherency: ok
net_namespace: 152 bytes
NET: Registered protocol family 16
usbcore: registered new interface driver usbfs
usbcore: registered new interface driver hub
usbcore: registered new device driver usb
NET: Registered protocol family 2
IP route cache hash table entries: 1024 (order: 0, 4096 bytes)
TCP established hash table entries: 1024 (order: 1, 8192 bytes)
TCP bind hash table entries: 1024 (order: 0, 4096 bytes)
TCP: Hash tables configured (established 1024 bind 1024)
TCP reno registered
checking if image is initramfs...it isn't (bad gzip magic numbers); looks like an initrd
Freeing initrd memory: 3072K
NetWinder Floating Point Emulator V0.97 (double precision)
io scheduler noop registered
io scheduler anticipatory registered (default)
at91_spi: Baud rate set to 5990400
AT91 SPI driver loaded
atmel_usart.0: ttyS0 at MMIO 0xfefff200 (irq = 1) is a ATMEL_SERIAL
atmel_usart.1: ttyS1 at MMIO 0xfffc4000 (irq = 7) is a ATMEL_SERIAL
brd: module loaded
at91_ether: Your bootloader did not configure a MAC address.
eth0: Link down.
eth0: AT91 ethernet at 0xfefbc000 int=24 10-HalfDuplex (00:00:00:00:00:00)
eth0: Realtek RTL8201( L PHY
physmap platform flash device: 00200000 at 10000000
physmap-flash.0: Found 1 x16 devices at 0x0 in 16-bit bank
NOR chip too large to fit in mapping. Attempting to cope...
Amd/Fujitsu Extended Query Table at 0x0040
number of CFI chips: 1
cfi_cmdset_0002: Disabling erase-suspend-program due to code brokenness.
Reducing visibility of 8192KiB chip to 2048KiB
RedBoot partition parsing not available
at91_cf: irqs det #64, io #0
usbmon: debugfs is not available
at91_ohci at91_ohci: AT91 OHCI
at91_ohci at91_ohci: new USB bus registered, assigned bus number 1
at91_ohci at91_ohci: irq 23, io mem 0x00300000
usb usb1: configuration #1 chosen from 1 choice
hub 1-0:1.0: USB hub found
hub 1-0:1.0: 2 ports detected
usb usb1: New USB device found, idVendor=1d6b, idProduct=0001
usb usb1: New USB device strings: Mfr=3, Product=2, SerialNumber=1
usb usb1: Product: AT91 OHCI
usb usb1: Manufacturer: Linux 2.6.25 ohci_hcd
usb usb1: SerialNumber: at91
udc: at91_udc version 3 May 2006
mice: PS/2 mouse device common for all mice
at91_rtc at91_rtc: rtc core: registered at91_rtc as rtc0
AT91 Real Time Clock driver.
i2c /dev entries driver
i2c-gpio i2c-gpio: using pins 57 (SDA) and 58 (SCL)
AT91 Watchdog Timer enabled (5 seconds, nowayout)
TCP cubic registered
NET: Registered protocol family 1
NET: Registered protocol family 17
at91_rtc at91_rtc: setting system clock to 1998-01-01 00:08:16 UTC (883613296)
RAMDISK: Couldn't find valid RAM disk image starting at 0.
List of all partitions:
0100 8192 ram0 (driver?)
0101 8192 ram1 (driver?)
0102 8192 ram2 (driver?)
0103 8192 ram3 (driver?)
0104 8192 ram4 (driver?)
0105 8192 ram5 (driver?)
0106 8192 ram6 (driver?)
0107 8192 ram7 (driver?)
0108 8192 ram8 (driver?)
0109 8192 ram9 (driver?)
010a 8192 ram10 (driver?)
010b 8192 ram11 (driver?)
010c 8192 ram12 (driver?)
010d 8192 ram13 (driver?)
010e 8192 ram14 (driver?)
010f 8192 ram15 (driver?)
1f00 2048 mtdblock0 (driver?)
No filesystem could mount root, tried: ext2 cramfs
Kernel panic - not syncing: VFS: Unable to mount root fs on unknown-block(1,0)

启动成功!就差ROOT文件系统了,哈哈

你可能感兴趣的:(为ARM(AT91RM9200)编译Linux Kernel)