一、移植环境
CPU:S3C2440; SDRAM:HY57V561620FTP-H; NOR flash:SST_39VF1601(2M);
NAND flash:K9F1G08U0B(128M); 网卡芯片:DM9000EP
二、博客地址
http://blog.csdn.net/liuqiqi677
如有错误,欢迎指正。
三、参考资料
主要参考了黄刚的博客http://blogold.chinaunix.net/u3/101649/ ,他的博客写得相当不错,将嵌入式开发各个阶段的知识以边做边学的方式,辅以图片、解释,清晰地呈现给读者,能够让读者把握主线,对嵌入式开发有整体的了解。强烈推荐!!!
四、问题及解决方法
10、使用 arm-linux-gcc 4.3.2 编译内核,必须启用内核中的 Use the ARM EABI 选项
没有选中这个选项的时候,系统启动,会出现下面的错误:
Freeing init memory: 128K
Kernel panic - not syncing: Attempted to kill init!
Backtrace:
[<c00259c0>] (dump_backtrace+0x0/0x114) from [<c026d674>] (dump_stack+0x18/0x1c)
r7:c5818000 r6:c5817a40 r5:c5817a40 r4:c03291c4
[<c026d65c>] (dump_stack+0x0/0x1c) from [<c026d6c4>] (panic+0x4c/0x120)
[<c026d678>] (panic+0x0/0x120) from [<c00406e0>] (do_exit+0x70/0x58c)
r3:c0313004 r2:c5817a40 r1:c5819d0c r0:c02cbdcb
[<c0040670>] (do_exit+0x0/0x58c) from [<c0040c90>] (do_group_exit+0x94/0xc8)
[<c0040bfc>] (do_group_exit+0x0/0xc8) from [<c004ae40>] (get_signal_to_deliver+0x2ec/0x324)
r7:c5293a74 r6:c5818000 r5:c5819ed4 r4:00000004
[<c004ab54>] (get_signal_to_deliver+0x0/0x324) from [<c0024024>] (do_signal+0x58/0x528)
[<c0023fcc>] (do_signal+0x0/0x528) from [<c0024524>] (do_notify_resume+0x30/0x34)
[<c00244f4>] (do_notify_resume+0x0/0x34) from [<c0021e8c>] (work_pending+0x1c/0x20)
错误的原因是因为 arm-linux-gcc-4.3.2 使用了EABI方式,所以这就需要内核同样配置EABI编译属性,才能支持EABI编译出来的busybox。
解决方法是:在linux内核配置菜单里的 Kernel Features 选项下,将‘User the ARM EABI to compile the kernel’选上,并且将它选上之后自动多出的一行‘Allow old ABI binaries to run with this kernel (EXPERIMENTAL)’ 也选上,如图11所示。重新编译内核,下载,问题解决。
图11 使用EABI方式编译内核
11、文件系统只能读,不能写的解决方法
我顺着黄刚的博客一路下来,在学习RTC时钟驱动移植的时候,试着用 mknod 命令建立设备文件的时候,系统一直提示‘Read-only file system ’。我仔细查看了系统的启动信息,发现有这么一行提示 ‘VFS: Mounted root (yaffs filesystem) readonly on device 31:3’, 看来是中间那个环节出现了问题,导致文件系统只能读取,不能写入。我继续往上看,在前面几行又发现一条警告信息‘Warning: bad configuration page, trying to continue ’,我去网上搜了一下,出现这种警告的原因是因为bootargs参数没有传递到内核,但是,他给的解决方法十分复杂。这时,我想起之前师兄发给我的资料,有一篇是根据黄刚的博客整理的移植教程,上面有说明bootargs参数没有传递到内核的解决方法,虽然并不是针对这个警告的。我把那篇教程翻出来,试着改了一下,在u-boot里的 include/configs/my2440.h 头文件里添加以下3个宏定义:
#define CONFIG_CMDLINE_TAG 1
#define CONFIG_SETUP_MEMORY_TAGS 1
#define CONFIG_INITRD_TAG 1
重新编译u-boot,下载到开发板运行,警告消失了,也没有‘Read-only’的提示了,在开发板上,也能够正常建立文件了。
12、启动信息里提示很多‘Partially written block * detected’
出现这个提示的原因是因为yaffs2文件系统,在关闭之前,要将dirty数据写入nand flash,否则下一次开机 yaffs2 scan 的时候,就会发现这些block是 Partially written 部分写入的,因此就会提示。
网上给的一个解决方法是,每次要关机之前,要去做一次:sync,让yaffs2将dirty的数据写入到nand flash里面。但是,作者也说明了这之中也还是存在一些问题的。以下是作者原文:
同理地,每次关机之前要通过系统去关机,这样会调用到poweroff等工具,其底层实现也是会调用到sync,去写数据。不过这个办法也存在缺陷,那就是,如果是意外断电,那就还是会遇到同样问题。
一般情况下,自己断电之前去sync一下,是可以避免那个警告的,但是,后来经过长时间使用发现,sync只能表面地去解决数据写回,而不能清除那些Partially written 的块,这种错误,是累积性的,也就是,比如第一次意外断电是提示:
Partially written block 176 detected
....
而第二次又意外断电了,那么可能破外到别的block了,比如是175,那么下次警告的信息又会多很多:
Partially written block 175 detected
所以,随着不能正常sync而关机,会导致这些yaffs2的警告累积性地增加。我此刻就遇到从175到104(中间部分block没有这些提示),一直打印这些警告,很是烦人。而实际上,rootfs是可以正常使用的。
作者把原因说得很清楚,但是解决方法并不容易操作,因为开发板通常直接就关电源了。其实,还有另一种比较简单的方案:
将linux内核里 fs/yaffs2/yaffs_gut.c中的 YAFFS_TRACE_ALWAYS 改为 YAFFS_TRACE_SCAN ,重新编译即可。
static int yaffs_ScanBackwards(yaffs_Device *dev) } else {
T(YAFFS_TRACE_ALWAYS ,
(TSTR("Partially written block %d detected" TENDSTR),
blk));
}
}
...
}
u-boot的学习暂时告一个段落, 现在我正在学习Linux下设备驱动的开发,其后会在S3C2440上移植QT,并且实现一个简单的图形界面的应用。现在各方面都还没有深入下去,我想迅速把这个流程走通,对嵌入式开发有个整体的概念,以后再回过头来扩充各个方面的知识。^_^