您的位置:首页 > 运维架构 > Linux

使用busybox构建linux根文件系统

2014-01-26 16:02 417 查看
使用busybox构建linux根文件系统
(2012-04-13 21:18)

标签: 
转载 
原文地址使用busybox构建linux根文件系统 作者charles413

主机:Windows 7旗舰版,VMware7.1.2,Fedora9

编译环境:arm-linux-gcc 4.4.3

Linux版本:linux-2.6.32.2

busybox版本:busybox-1.19.4

busybox源码下载地址:http://www.busybox.net/downloads/ 

参考资料:《嵌入式Linux应用开发完全手册》 韦东山

所谓创建根文件系统,就是创建各种目录,并且在里面创建各种文件。比如在/bin、/sbin目录下存放各种可执行程序,在/etc目录下存放配置文件,在/lib目录下存放库文件。Busybox主要用来创建/bin、/sbin等目录下的可执行文件,如命令行下经常使用的命令ls、mv、cp等。

编译busybox

Busybox的编译较为简单,一般使用默认配置即可,如果熟悉配置选项的话也可以执行make menuconfig进行手动裁剪。具体配置说明可参考《嵌入式Linux应用开发完全手册》。

修改busybox顶层目录的Makefile文件,修改如下两行:

ARCH  ?= arm

CROSS_COMPILE
?= arm-linux

然后执行make,编译busybox。编译完成后执行:

make CONFIG_PREFIX=/home/nfs/rootfs install

将busybox安装到目录/home/nfs/rootfs下。/home/nfs/rootfs是目标板文件系统的根目录。执行命令查看安装busybox后生成的文件:

# ls -l /home/nfs/rootfs/

drwxr-xr-x 2 root root 4096 2012-04-05 15:24 bin

lrwxrwxrwx 1 root root   11 2012-03-31 08:17 linuxrc -> bin/busybox

drwxr-xr-x 2 root root 4096 2012-03-31 08:17 sbin

drwxr-xr-x 5 root root 4096 2012-04-03 07:25 usr

linuxrc是内核启动的init进程,那内核又如何知道要启动的init进程是哪个呢?它是由uboot传递给linux内核参数中"init=xxx"决定的。在我的目标板的uboot中传递给内核的参数为"init=/linuxrc"。内核如何启动init进程可以查看内核代码init/main.c中的init_post函数。

构建lib库

虽然通过编译busybox生成了我们需要的可执行文件,但现在在目标板上仍然无法运行,需要添加lib库来支持可执行文件运行。可以使用uclibc和glibc来构建lib库。由于编译lib库相对复杂,而我们又有现成的lib库可以使用,这里我们就实行拿来主义。现成的lib库就在我们的交叉编译工具arm-linux-gcc的目录下,在本人主机上的绝对路径为/opt/FriendlyARM/toolschain/4.4.3/arm-none-linux-gnueabi/lib,

把该lib目录下的所有文件复制到目标板文件系统lib下,执行命令:

#cp -r /opt/FriendlyARM/toolschain/4.4.3/arm-none-linux-gnueabi/lib /home/nfs/rootfs/lib

PS:注意要加-r选项,把软链接文件原样复制过来,不加-r会复制软链接的链接文件,造成存储空间的浪费。

构建etc目录

创建etc/inittab,参照busybox的examples/inittab文件,内容如下:

点击(此处)折叠或打开

#
/etc/inittab

# Boot-time
system configuration/initialization script.

# This is run
first except when booting in single-user mode.

#

::sysinit:/etc/init.d/rcS

# /bin/sh
invocations on selected ttys

#

# Note below that
we prefix the shell commands with a "-" to indicate to
the

# shell that it
is supposed to be a login shell. Normally this is handled
by

# login, but
since we are bypassing login in this case, BusyBox lets you
do

# this
yourself...

#

# Start an
"askfirst" shell on the console (whatever that may be)

console::askfirst:-/bin/sh

#tty1::askfirst:-/bin/sh

# Stuff to do
before rebooting

::ctrlaltdel:/sbin/reboot

::shutdown:/bin/umount -a
-r

PS:这里的console是在构建/dev目录时创建的设备节点,对应的设备是启动Linux内核前传入的命令行参数“console=xxx”指定的控制台,我传递的参数为“console=ttySAC0,115200”,表示使用串口0,波特率为115200。

创建etc/init.d/rcS文件。rcS是系统启动后执行的第一个脚本文件,如果想把自己编写的应用程序设置为开机启动,在本文件中中加入运行该程序的命令即可。内容如下:

点击(此处)折叠或打开

#!/bin/sh

ifconfig eth0
192.168.1.158

mount
-a

修改添加文件可执行权限:#chmod +x etc/init.d/rcS。

创建etc/fstab文件,内容如下:

点击(此处)折叠或打开

#device
mount-poin type options dump fsck order

proc /proc proc
defaults 0 0

tmpfs /tmp tmpfs
defaults 0 0

构建dev目录

这里使用busybox的mdev创建设备文件,mdev是udev的简化版本,它也是通过读取内核信息来创建设备文件。

要使用mdev,需要内核支持sysfs文件系统,为了减少对Flash的读写,还要支持tmpfs文件系统。先确保内核已经设置了CONFIG_SYSFS、CONFIG_TMPFS配置项。

使用mdev的命令如下,请参考它们的注释以了解其作用:

#mount -t tmpfs mdev /dev
(使用内存文件系统,减少对Flash的读写)

#mkdir /dev/pts
(dev/pts用来支持外部网络连接(telnet)的虚拟终端)

#mount -t devpts devpts /dev/pts

#mount -t sysfs sysfs /sys
(mdev通过sysfs文件系统获得设备信息)

#echo /bin/mdev > /proc/sys/kernel/hotplug
(设置内核,当有设备插拔时调用/bin/mdev程序)

#mdev -s
(在/dev目录下生成内核支持的所有设备的节点)

要在内核启动后,自动运行mdev。需要修改etc目录下的两个文件:修改etc/fstab来自动挂载文件系统、修改etc/init.d/rcS加入要自动运行的命令。修改后的文件如下:

etc/fstab
 

点击(此处)折叠或打开

#device
mount-poin 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

etc/init.d/rcS
 

点击(此处)折叠或打开

#!/bin/sh

ifconfig eth0
192.168.1.158

mount
-a

mkdir
/dev/pts

mount -t devpts
devpts /dev/pts

echo /sbin/mdev
> /proc/sys/kernel/hotplug

mdev
-s

添加mdev配置文件etc/mdev.conf,mdev.conf可以用来控制设备节点的所有者和权限,格式如下:

<device regex> <uid>:<gid> <octal permissions> 

mdev.conf还可以设置mdev在dev目录下生成的设备节点的名字,Linux内核串口驱动原本对S3C2410、S3C2440注册的设备名是s3c2410_serial0、s3c2410_serial1、s3c2410_serial2,我们可以修改mdev.conf文件,使mdev在/dev目录下对应生成ttySAC0, ttySAC1和ttySAC2,以符合应用程序对于串口设备操作的习惯。配置文件mdev.conf的内容如下:

  
 mdev.conf

 

点击(此处)折叠或打开

# system
all-writable devices

full 0:0
0666

null 0:0
0666

ptmx 0:0
0666

random 0:0
0666

tty 0:0
0666

zero 0:0
0666

# console
devices

tty[0-9]* 0:5
0660

vc/[0-9]* 0:5
0660

# serial port
devices

s3c2410_serial0 0:5 0666
=ttySAC0

s3c2410_serial1 0:5 0666
=ttySAC1

s3c2410_serial2 0:5 0666
=ttySAC2

s3c2410_serial3 0:5 0666
=ttySAC3

# loop
devices

loop[0-9]* 0:0
0660 =loop/

# i2c
devices

i2c-0 0:0 0666
=i2c/0

i2c-1 0:0 0666
=i2c/1

# frame buffer
devices

fb[0-9] 0:0
0666

# input
devices

mice 0:0 0660
=input/

mouse.* 0:0 0660
=input/

event.* 0:0 0660
=input/

ts.* 0:0 0660
=input/

# rtc
devices

rtc0 0:0 0644
>rtc

rtc[1-9] 0:0
0644

# misc
devices

mmcblk0p1 0:0
0600 =sdcard */etc/rc.d/init.d/sd

sda1 0:0 0600
=udisk * /etc/rc.d/init.d/udisk

 

重要的一点忘写了,希望没有误导之前看这篇文章的网友。现补充如下:

由于mdev是通过init进程来启动的,在使用mdev构造/dev目录之前,init进程至少要用到两个设备文件/dev/console、/dev/null,所以要建立这两个设备文件。

# mkdir -r /home/nfs/rootfs/dev

# cd /home/nfs/rootfs/dev

# mknod console c 5 1

# mknod null c 1 3

构建其他目录

# mkdir proc mnt tmp sys root

到此,我们的根文件系统构建完毕,/home/nfs/rootfs目录下就是我们的根文件系统。目标板可以把它通过作为网络根文件系统,通过nfs直接启动。也可以把它制作为映像文件烧写到目标板的Flash启动。
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: