uClinux 启动过程详细分析(一)
<!--google_ad_client = "pub-2299987709779770";/* 728x90, 创建于 08-5-27 */google_ad_slot = "2248241756";google_ad_width = 728;google_ad_height = 90;//--> <script type="text/javascript"src
uclinux启动的详细过程有着诸多的信息可以给我们巨大的启发,我们在这里讨论的就是要 对这些信息做一个具体细致的分析,通过我们的讨论,大家会对uclinux启动过程中出现的、以前感觉熟悉的、但却又似是而非的东西有一个确切的了解,并 且能了解到这些输出信息的来龙去脉。
uclinux的启动过程,它是一幅缩影图,对它有了一个详细的了解后,有助于指导我们更加深入地了解uclinux的核心。
大家对uclinux的启动应该都比较熟悉,作为一名嵌入系统开发者,你一定遇到过下面的情景:
在某论坛上看到一篇帖子,上面贴着uclinux开发板启动时的一堆信息,然后大家在帖子里讨论着这个启动过程中出现的问题,随机举例如下:
Linux version 2.4.20-uc1 (root@Local) (gcc version 2.95.3 |
上面的这些输出信息,也可能包括你自己正在做的uclinux开发板的输出信息,其中的每一行,每一个字的含义,你是否深究过,或者说大部分的含义你能确切地知道的?本人想在这里结合本人在实践中一些体会来和广大uclinux的开发者一起读懂这些信息。
我们在这里将以一个真实的uclinux系统的启动过程为例,来分析这些输出信息。启动信息的原始内容将用标记标出,以区别与注释。
uclinux的启动主要分为两个阶段:
- ① 第一部分bootloader启动阶段
- ② 第二部分linux 内核初始化和启动阶段
-
- 第一节:start_kernel
- 第二节:用户模式( user_mode )开始,start_kernel结束
- 第三节:加载linux内核完毕,转入cpu_idle进程
图 1:uclinux启动状态转移示意图
Boot loader v0.12 |
Bootloader头信息,版本,编译时间等,这个因不同的bootloader的设计而有所不同,由此你能看出bootloader的版本信息,有很多使用的是通用的bootloader,如u-boot,redboot等。
Loaded to 0x90060000 |
将bootloader加载到内存ram中的0x90060000处,即将bootloader加载到内存的高端地址处。
Linux内核将被bootloader加载到0x90090000处。
Found boot configuration |
查找到了启动boot的配置信息。
Booted from parallel flash |
<script type="text/javascript"> </script> <script type="text/javascript" src="http://pagead2.googlesyndication.com/pagead/show_ads.js"> </script>
从flash中启动代码,此处的flash为并行闪存。
注意:任何flash器件的写入操作只能在空或已擦除的单元内进行,所以大多数情况下,在进行写入操作之前必须先执行擦除。NAND器件执行擦除操作是十分简单的,而NOR则要求在进行擦除前先要将目标块内所有的位都写为0。
从上面的信息,我们可以对flash类型特点有个比较明确的了解。
CPU clock rate: 200 MHz |
开发板上所使用的CPU的主频为200MHZ。
DRAM size is 128MB (128MB/0MB) |
动态内存ram大小为128M。
在嵌入式系统中使用DRAM内存的设计比较广泛。
在uclinux的系统中,系统运行时间较长后,会出现内存碎片的问题,导致再分配大块内存时会失败。这是在uclinux系统中经常遇到的问题,解决的办法通常有使用静态内存、应用程序启动时预先分配大内存、使用内存池等。
地址辅助说明:
先说明一下内存地址数字情况,主要是为了方便记忆。
可以访问的内存为4G。
0x40000000是1GB处;
0x00040000是256K处,
0x00020000是128K处,
0x90000000是2GB多的地方。
1M->0x00100000,
2M->0x00200000,
8M->0x00800000,
16M->0x01000000,
32M->0x02000000,
256M->0x10000000,
64K->0x00010000,
注意:rootfs并不是一个具体的文件系统类型,如jffs。它只是一个理论上的概念。在具体的嵌入系统实例中,可以将某种具体的文件系统设置为根文件系统rootfs,如我们可以设置romfs为根文件系统,也可以设置jffs为根文件系统。
这里的ROMFS只读文件系统只是一种具体的文件系统类型,也是在嵌入系统中经常使用到的类型。
看完了上面的内容,以后你对出现的类似“kernel Panic:VFS:Unable to mount root fs on 0:00”的含义应该已经了解了。其中“VFS:”就是虚拟文件系统管理器操作时的输出信息了。
File linux.bin.gz found |
linux kernel内核文件名,它是在只读文件系统romfs上的一个组成部分。
Unzipping image from 0x4639DE60 to 0x90090000, size = 1316021 |
将romfs中的linux kernel解压缩到0x90090000,之后会从这个内存地址启动内核。romfs为压缩格式文件,使用压缩的只读文件系统,是为了保持制作出来的整 个系统所占用的flash空间减小。这个内核的大小为1.3M左右,这也是目前大多数嵌入系统所使用的方法。
Inptr = 0x00000014(20) |
释放……
Outcnt = 0x0030e7c8(3205064) |
做释放后的CRC检查。
Boot kernel at 0x90090000 with ROMFS at 0x46040000 |
kernel已经被从romfs中释放到内存地址0x90090000处,可以跳转到此处启动kernel了,这里是指定的kernel的起始地址。
Press 'enter' to boot |
系统等待启动,后面将看到linux kernel的启动过程了。
4K->0x00001000
这个是个快速记忆的方法,你可以根据地址中1的位置和其后0的个数来快速知道换算后的地址是在多少兆的地方。比如,1的后面5个0,代表1M的大小,6个0,代表16M,以此类推。
ROMFS found at 0x46040000, Volume name = rom 43f291aa |
romfs,只读文件系统所在的地址为:0x46040000 (flash映射后的第3分区)。卷名为rom。
romfs 和rootfs概念上有所区别。flash在内存中的的起始地址为0x46000000,而ROMFS在flash分区上的起始位置为 0x00040000,所以ROMFS在内存地址中的位置就为0x46040000。这个细节的部分可以参考flash分区时的地方,Creating 3 MTD partitions。
romfs中包括kernel和app应用,不包括bootloader和firmware信息头。romfs只读文件系统里的内容有很多种分类方法,我们可以将kernel和app同时放里面,作为根文件系统下的一个文件,也可以在flash上另外划分区域来分别存放。
<script type="text/javascript"> </script> <script type="text/javascript" src="http://pagead2.googlesyndication.com/pagead/show_ads.js"> </script>更多推荐
所有评论(0)