移植较新(Linux3.19)内核至mini2440开发板(一)

本人大二在校生一枚,最近开始接触嵌入式Linux系统,跟着友善提供的Linux移植手册操作了一遍后决定自己移植一个当前较新的内核(3.19)作为练习,为了避免日后遗忘,同时也是作为学习的一个记录,决定在此将整个移植的过程进行详细的记录。因为自己也是个新手,难免会有许多错误,还请读者能够指出。

下面开始正题


注:内核启动时可能会出现乱码,可以在u-boot下设置如下环境变量:setenv bootargs noinitrd root=/dev/mtdblock3 init=/linuxrc console=ttySAC0,115200
saveenv 


1.1下载Linux3.19的源代码

从Linux kernel的官方网站可以下载最新的内核代码,我们选择linux-3.19.4.tar.gz这个文件下载。下载后解压至工作目录。进入内核目录,打开Makefile文件,修改如下两行:

-ARCH		?= $(SUBARCH)
-CROSS_COMPILE	?= $(CONFIG_CROSS_COMPILE:"%"=%)
+ARCH		?= $(SUBARCH)
+CROSS_COMPILE	?= $(CONFIG_CROSS_COMPILE:"%"=%)

保存退出后执行
root@ginger-virtual-machine:/home/ginger/mini2440/linux-3.19.3# make menuconfig

打开内核配置界面,不做任何操作直接退出,然后在终端执行
root@ginger-virtual-machine:/home/ginger/mini2440/linux-3.19.3# make mini2440_defconfig
显示
 ## configuration written to .config 
  

#

说明已经对采用了内核自带的mini2440的配置,这样可以减少我们手动配置内核的工作量。此时我们执行

root@ginger-virtual-machine:/home/ginger/mini2440/linux-3.19.3# make zImage

发现已经可以编译内核并生成内核镜像,这是因为新版本的Linux内核已经添加了对mini2440的支持.

1.2添加对平台的支持

在/linux-3.19.3/arch/arm/mach-s3c24xx目录下有一个名为mach-mini2440.c的源文件, 但是我们不使用它,将其删除后将该目录下的mach-smdk2440.c文件复制一份并改名为mach-mini2440.c.打开mach-mini2440.c文件,将其中关于LCD的定义均删除,后续我们将自己添加LCD驱动相关代码。

/* LCD driver info */

static struct s3c2410fb_display smdk2440_lcd_cfg __initdata = {

	.lcdcon5	= S3C2410_LCDCON5_FRM565 |
			  S3C2410_LCDCON5_INVVLINE |
			  S3C2410_LCDCON5_INVVFRAME |
			  S3C2410_LCDCON5_PWREN |
			  S3C2410_LCDCON5_HWSWP,

	.type		= S3C2410_LCDCON1_TFT,

	.width		= 240,
	.height		= 320,

	.pixclock	= 166667, /* HCLK 60 MHz, divisor 10 */
	.xres		= 240,
	.yres		= 320,
	.bpp		= 16,
	.left_margin	= 20,
	.right_margin	= 8,
	.hsync_len	= 4,
	.upper_margin	= 8,
	.lower_margin	= 7,
	.vsync_len	= 4,
};

static struct s3c2410fb_mach_info smdk2440_fb_info __initdata = {
	.displays	= &smdk2440_lcd_cfg,
	.num_displays	= 1,
	.default_display = 0,

#if 0
	/* currently setup by downloader */
	.gpccon		= 0xaa940659,
	.gpccon_mask	= 0xffffffff,
	.gpcup		= 0x0000ffff,
	.gpcup_mask	= 0xffffffff,
	.gpdcon		= 0xaa84aaa0,
	.gpdcon_mask	= 0xffffffff,
	.gpdup		= 0x0000faff,
	.gpdup_mask	= 0xffffffff,
#endif

	.lpcsel		= ((0xCE6) & ~7) | 1<<4,
};
同时将static struct platform_device *mini2440_devices[] __initdata 函数中的&s3c_device_lcd,注释,将static void __init mini2440_machine_init(void)函数中的s3c24xx_fb_set_platdata(&mini2440_fb_info)和smdk_machine_init();注释。然后使用替换功能将代码中的所有smdk2440均替换为mini2440.

1.3修改晶振频率

将static void __init mini2440_init_time(void)函数中的s3c2440_init_clocks(16934400);更改为s3c2440_init_clocks(12000000)

1.4找到MACHINE_START(S3C2440, "SMDK2440")函数,将其修改为MACHINE_START(MINI2440, "Ginger's board"),如果不修改,将导致内核启动时直接卡在Starting kernel .......................处。此时保存后编译,内核已可以正常编译,但此时还有大部分驱动未编写,内核还无法正常启动。下一步我们将在源码中增加关于nand flash分区表的相关内容

1.5添加nand flash的支持

在mach-mini2440.c中增加以下内容

/* NAND Flash on MINI2440 board */

static struct mtd_partition mini2440_default_nand_part[]  = {
 	[0] = {
 		.name	= "supervivi",
 		.size	= 0x00040000,
 		.offset	= 0,
 	},
 	[1] = {
 		.name	= "param",
 		.offset = 0x00040000,
 		.size	= 0x00020000,
 	},
 	[2] = {
 		.name	= "Kernel",
 		.offset = 0x00060000,
 		.size	= 0x00500000,
 	},
 	[3] = {
 		.name	= "root",
 		.offset = 0x00560000,
		.size	= 1024 * 1024 * 1024, //
	},
	[4] = {
		.name	= "nand",
		.offset = 0x00000000,
		.size	= 1024 * 1024 * 1024, //
	},
};

static struct s3c2410_nand_set mini2440_nand_sets[]  = {
	[0] = {
		.name		= "nand",
		.nr_chips	= 1,
		.nr_partitions	= ARRAY_SIZE(mini2440_default_nand_part),
		.partitions	= mini2440_default_nand_part,
		.flash_bbt 	= 1, /* we use u-boot to create a BBT */
	},
};

static struct s3c2410_platform_nand mini2440_nand_info = {
	.tacls		= 0,
	.twrph0		= 25,
	.twrph1		= 15,
	.nr_sets	= ARRAY_SIZE(mini2440_nand_sets),
	.sets		= mini2440_nand_sets,
	.ignore_unset_ecc = 1,
};
添加如下头文件

#include 
#include 
#include 
#include 
#include 
在static struct platform_device *mini2440_devices[] __initdata函数中增加&s3c_device_nand,在static void __init mini2440_machine_init(void)函数中增加s3c_nand_set_platdata(&mini2440_nand_info);

 
  
保存后编译,下载到开发板上,可看到如下启动信息:
s3c24xx-nand s3c2440-nand: Tacls=1, 9ns Twrph0=3 29ns, Twrph1=2 19ns
s3c24xx-nand s3c2440-nand: NAND soft ECC
nand: device found, Manufacturer ID: 0xec, Chip ID: 0xda
nand: Samsung NAND 256MiB 3,3V 8-bit
nand: 256 MiB, SLC, erase size: 128 KiB, page size: 2048, OOB size: 64
Creating 5 MTD partitions on "nand":
0x000000000000-0x000000040000 : "supervivi"
__nand_correct_data: uncorrectable ECC error
0x000000040000-0x000000060000 : "param"
ftl_cs: FTL header not found.
0x000000060000-0x000000560000 : "Kernel"
ftl_cs: FTL header not found.
0x000000560000-0x000040560000 : "root"
mtd: partition "root" extends beyond the end of device "nand" -- size truncated to 0xfaa0000
ftl_cs: FTL header not found.
0x000000000000-0x000040000000 : "nand"
mtd: partition "nand" extends beyond the end of device "nand" -- size truncated to 0x10000000
__nand_correct_data: uncorrectable ECC error

发现开发板已经可以识别nand flash的信息,但是打印出如下信息:
ftl_cs: FTL header not found.
解决方法如下:在内核根目录下执行make menuconfig,进入

Device Drivers ->

Memory Technology Devices (MTD) ->

去掉如下选项

<>FTL (Flash Translation Layer) support

<> NFTL (NAND Flash Translation Layer) support

<>INFTL (Inverse NAND Flash Translation Layer) support

 
  

保存后重新编译即可。

1.6到目前为止已经完成了对nand flash的支持,但是因为缺少根文件系统,内核依旧无法正常启动。接下去我们将为内核添加对yaffs2的支持。

在终端下执行#git clone git://www.aleph1.co.uk/yaffs2 获取最新的yaffs2源码。同步完后,进入yaffs2目录,执行# ./patch-ker.sh c m 内核源码路径,既可对内核打上yaffs2的补丁。进入内核目录,执行make menuconfig

选择File systems  --->  

 [*] Miscellaneous filesystems  --->       
 │    <*>   yaffs2 file system support
保存后退出,重新编译,此时会遇到几个错误,因为新版的Linux内核有一些对文件操作的函数进行了修改,我们需要按照错误逐一进行修改。按照错误:
fs/yaffs2/yaffs_vfs.c: In function 'yaffs_readpage_nolock':
fs/yaffs2/yaffs_vfs.c:286: error: 'struct file' has no member named 'f_dentry'
fs/yaffs2/yaffs_vfs.c: In function 'yaffs_hold_space':
fs/yaffs2/yaffs_vfs.c:484: error: 'struct file' has no member named 'f_dentry'
fs/yaffs2/yaffs_vfs.c: In function 'yaffs_release_space':
fs/yaffs2/yaffs_vfs.c:502: error: 'struct file' has no member named 'f_dentry'
fs/yaffs2/yaffs_vfs.c: In function 'yaffs_file_write':
fs/yaffs2/yaffs_vfs.c:594: error: 'struct file' has no member named 'f_dentry'
fs/yaffs2/yaffs_vfs.c:606: error: 'struct file' has no member named 'f_dentry'
fs/yaffs2/yaffs_vfs.c: In function 'yaffs_file_flush':
fs/yaffs2/yaffs_vfs.c:730: error: 'struct file' has no member named 'f_dentry'
fs/yaffs2/yaffs_vfs.c:741: error: too few arguments to function 'yaffs_flush_file'
fs/yaffs2/yaffs_vfs.c: In function 'yaffs_sync_object':
fs/yaffs2/yaffs_vfs.c:771: error: too few arguments to function 'yaffs_flush_file'
fs/yaffs2/yaffs_vfs.c: At top level:
fs/yaffs2/yaffs_vfs.c:781: error: 'generic_file_aio_read' undeclared here (not in a function)
fs/yaffs2/yaffs_vfs.c:782: error: 'generic_file_aio_write' undeclared here (not in a function)
fs/yaffs2/yaffs_vfs.c:787: error: 'generic_file_splice_write' undeclared here (not in a function)
fs/yaffs2/yaffs_vfs.c: In function 'yaffs_iterate':
fs/yaffs2/yaffs_vfs.c:1719: error: 'struct file' has no member named 'f_dentry'
fs/yaffs2/yaffs_vfs.c: In function 'yaffs_flush_inodes':
fs/yaffs2/yaffs_vfs.c:2190: error: too few arguments to function 'yaffs_flush_file'
fs/yaffs2/yaffs_vfs.c: In function 'yaffs_flush_super':
fs/yaffs2/yaffs_vfs.c:2203: error: too few arguments to function 'yaffs_flush_whole_cache'

打开/fs/yaffs2/yaffs_vfs.c,使用替换功能,将代码中的所有f_dentry均替换为f_path.dentry,将所有的yaffs_flush_file(obj, 1, 0);替换为yaffs_flush_file(obj, 1, 0,1);将yaffs_flush_file(obj, 1, datasync);替换为 yaffs_flush_file(obj, 1, datasync,1);将yaffs_flush_file(obj, 1, 0);替换为yaffs_flush_file(obj, 1, 0,1);yaffs_flush_whole_cache(dev);替换为yaffs_flush_whole_cache(dev,1);
718行附近
-	.read = do_sync_read,
-	.write = do_sync_write,
+	.read = new_sync_read,
+	.write = new_sync_write,
-	.aio_read = generic_file_aio_read,
-	.aio_write = generic_file_aio_write,
+       .read_iter =	generic_file_read_iter,
+       .write_iter =	generic_file_write_iter,
-	.splice_write = generic_file_splice_write,
+	.splice_write = iter_file_splice_write,

保存后重新编译,下载内核至开发板,同时烧录文件系统(为了测试方便,这次我先使用友善提供的制作好的文件系统root_qtopia.img在以后的教程中我们也会制作自己的文件系统),重启开发板,看到如下引导信息
Starting kernel ...

Booting Linux on physical CPU 0x0
Linux version 3.19.3 (root@ginger-virtual-machine) (gcc version 4.4.3 (ctng-1.6.1) ) #6 Sat Apr 25 13:37:14 CST 2015
CPU: ARM920T [41129200] revision 0 (ARMv4T), cr=c000717f
CPU: VIVT data cache, VIVT instruction cache
Machine: Ginger's board
Memory policy: Data cache writeback
CPU S3C2440A (id 0x32440001)
Built 1 zonelists in Zone order, mobility grouping on.  Total pages: 16256
Kernel command line: noinitrd root=/dev/mtdblock3 init=/linuxrc console=ttySAC0,115200
PID hash table entries: 256 (order: -2, 1024 bytes)
Dentry cache hash table entries: 8192 (order: 3, 32768 bytes)
Inode-cache hash table entries: 4096 (order: 2, 16384 bytes)
Memory: 59192K/65536K available (4003K kernel code, 193K rwdata, 1072K rodata, 160K init, 246K bss, 6344K reserved, 0K cma-reserved)
Virtual kernel memory layout:
    vector  : 0xffff0000 - 0xffff1000   (   4 kB)
    fixmap  : 0xffc00000 - 0xfff00000   (3072 kB)
    vmalloc : 0xc4800000 - 0xff000000   ( 936 MB)
    lowmem  : 0xc0000000 - 0xc4000000   (  64 MB)
    modules : 0xbf000000 - 0xc0000000   (  16 MB)
      .text : 0xc0008000 - 0xc04fd0a0   (5077 kB)
      .init : 0xc04fe000 - 0xc0526000   ( 160 kB)
      .data : 0xc0526000 - 0xc0556640   ( 194 kB)
       .bss : 0xc0556640 - 0xc0594098   ( 247 kB)
SLUB: HWalign=32, Order=0-3, MinObjects=0, CPUs=1, Nodes=1
NR_IRQS:103
S3C2440: IRQ Support
irq: clearing pending status 00000002
sched_clock: 16 bits at 1012kHz, resolution 987ns, wraps every 64725925ns
Console: colour dummy device 80x30
Calibrating delay loop... 201.52 BogoMIPS (lpj=503808)
pid_max: default: 32768 minimum: 301
Mount-cache hash table entries: 1024 (order: 0, 4096 bytes)
Mountpoint-cache hash table entries: 1024 (order: 0, 4096 bytes)
CPU: Testing write buffer coherency: ok
Setting up static identity map for 0x303d2488 - 0x303d24e0
NET: Registered protocol family 16
DMA: preallocated 256 KiB pool for atomic coherent allocations
cpuidle: using governor ladder
cpuidle: using governor menu
S3C2440: Initialising architecture
usbcore: registered new interface driver usbfs
usbcore: registered new interface driver hub
usbcore: registered new device driver usb
s3c-i2c s3c2440-i2c.0: slave address 0x10
s3c-i2c s3c2440-i2c.0: bus frequency set to 98 KHz
s3c-i2c s3c2440-i2c.0: i2c-0: S3C I2C adapter
Advanced Linux Sound Architecture Driver Initialized.
Switched to clocksource samsung_clocksource_timer
NET: Registered protocol family 2
TCP established hash table entries: 1024 (order: 0, 4096 bytes)
TCP bind hash table entries: 1024 (order: 0, 4096 bytes)
TCP: Hash tables configured (established 1024 bind 1024)
TCP: reno registered
UDP hash table entries: 256 (order: 0, 4096 bytes)
UDP-Lite hash table entries: 256 (order: 0, 4096 bytes)
NET: Registered protocol family 1
RPC: Registered named UNIX socket transport module.
RPC: Registered udp transport module.
RPC: Registered tcp transport module.
RPC: Registered tcp NFSv4.1 backchannel transport module.
futex hash table entries: 256 (order: -1, 3072 bytes)
NFS: Registering the id_resolver key type
Key type id_resolver registered
Key type id_legacy registered
jffs2: version 2.2. (NAND) 漏 2001-2006 Red Hat, Inc.
romfs: ROMFS MTD (C) 2007 Red Hat, Inc.
io scheduler noop registered
io scheduler deadline registered
io scheduler cfq registered (default)
s3c2440-uart.0: ttySAC0 at MMIO 0x50000000 (irq = 74, base_baud = 0) is a S3C2440
console [ttySAC0] enabled
s3c2440-uart.1: ttySAC1 at MMIO 0x50004000 (irq = 77, base_baud = 0) is a S3C2440
s3c2440-uart.2: ttySAC2 at MMIO 0x50008000 (irq = 80, base_baud = 0) is a S3C2440
brd: module loaded
s3c24xx-nand s3c2440-nand: Tacls=1, 9ns Twrph0=3 29ns, Twrph1=2 19ns
s3c24xx-nand s3c2440-nand: NAND soft ECC
nand: device found, Manufacturer ID: 0xec, Chip ID: 0xda
nand: Samsung NAND 256MiB 3,3V 8-bit
nand: 256 MiB, SLC, erase size: 128 KiB, page size: 2048, OOB size: 64
Creating 5 MTD partitions on "nand":
0x000000000000-0x000000040000 : "supervivi"
0x000000040000-0x000000060000 : "param"
0x000000060000-0x000000560000 : "Kernel"
0x000000560000-0x000040560000 : "root"
mtd: partition "root" extends beyond the end of device "nand" -- size truncated to 0xfaa0000
0x000000000000-0x000040000000 : "nand"
mtd: partition "nand" extends beyond the end of device "nand" -- size truncated to 0x10000000
ohci_hcd: USB 1.1 'Open' Host Controller (OHCI) Driver
ohci-s3c2410: OHCI S3C2410 driver
s3c2410-ohci s3c2410-ohci: OHCI Host Controller
s3c2410-ohci s3c2410-ohci: new USB bus registered, assigned bus number 1
s3c2410-ohci s3c2410-ohci: irq 42, io mem 0x49000000
hub 1-0:1.0: USB hub found
hub 1-0:1.0: 2 ports detected
mousedev: PS/2 mouse device common for all mice
i2c /dev entries driver
s3c2410-wdt s3c2410-wdt: watchdog inactive, reset disabled, irq disabled
Driver 'mmcblk' needs updating - please use bus_type methods
sdhci: Secure Digital Host Controller Interface driver
sdhci: Copyright(c) Pierre Ossman
hidraw: raw HID events driver (C) Jiri Kosina
usbcore: registered new interface driver usbhid
usbhid: USB HID core driver
TCP: cubic registered
NET: Registered protocol family 17
Key type dns_resolver registered
drivers/rtc/hctosys.c: unable to open rtc device (rtc0)
ALSA device list:
  No soundcards found.
yaffs: dev is 32505859 name is "mtdblock3" rw
yaffs: passed flags ""
VFS: Mounted root (yaffs filesystem) on device 31:3.
Freeing unused kernel memory: 160K (c04fe000 - c0526000)
mount: mounting none on /proc/bus/usb failed: No such file or directory
hwclock: can't open '/dev/misc/rtc': No such file or directory
[01/Jan/1970:00:00:07 +0000] boa: server version Boa/0.94.13
[01/Jan/1970:00:00:07 +0000] boa: server built Mar 26 2009 at 15:28:42.
[01/Jan/1970:00:00:07 +0000] boa: starting server pid=784, port 80
                        
open device leds: No such file or directory
Try to bring eth0 interface up......ifconfig: SIOCGIFFLAGS: No such device
ifconfig: SIOCSIFHWADDR: No such device
ifconfig: SIOCSIFADDR: No such device
route: SIOCADDRT: Network is unreachable
Done

Please press Enter to activate this console. 
[root@FriendlyARM /]# cat /proc/version 
Linux version 3.19.3 (root@ginger-virtual-machine) (gcc version 4.4.3 (ctng-1.6.1) ) #6 Sat Apr 25 13:37:14 CST 2015

到此我们已经初步将Linux3.19内核移植到了开发板上。在下一篇教程中我们会继续完善相关的驱动。


相关文件

你可能感兴趣的:(mini2440)