Linux三巨头己经完成了2个了,就剩最后一个rootfs(根文件系统)了,根文件系统的组成以及如何构建根文件系统是Liux移植的最后一步,根文件系统构建好以后就意味着我们己经拥有了一个完整的、可以运行的最小系统。以后我们就在这个最小系统上编写、测试Linux驱动,移植一些第三方组件,逐步的完善这个最小系统。最终得到一个功能完善、驱动齐全、相对完善的操作系统。
一、BusyBox构建根文件系统
1.1 BusyBox简介
BusyBox 就是一个大的工具箱,这个工具箱里面集成了 Linux 的许多工具和命令。一般下载 BusyBox 的源码,然后配置 BusyBox,选择自己想要的功能,最后编译即可。BusyBox 可以在其官网下载到,官网地址为:https://busybox.net/,官网比较简陋,如图
在官网左侧的“Get BusyBox”栏有一行“Download Source”,点击“Download Source”即可打开 BusyBox 的下载页,如图所示:
从图可以看出,目前最新的 BusyBox 版本是 1.31.0,不过我建议大家使用我们开发板光盘里面提供的 1.29.0 版本的 BusyBox。因为笔者测试 1.29.0 版本目前还没有出现任何问题,路径为:1、例程源码->6、BusyBox 源码->busybox-1.29.0.tar.bz2,BusyBox 准备好以后就可以构建根文件系统了。
1.2 编译BusyBox构建根文件系统
一般我们在 Linux 驱动开发的时候都是通过 nfs 挂载根文件系统的,当产品最终上市开卖的时候才会将根文件系统烧写到 EMMC 或者 NAND 中。所以要在nfs 服务器目录中创建一个名为 rootfs 的子目录(名字大家可以随意起,为了方便就用了 rootfs),比如我的电脑中/home/zhiguoxin/linux/nfs
就是我设置的 NFS 服务器目录,使用如下命令创建名为 rootfs 的子目录:
mkdir rootfs
创建好的 rootfs 子目录就用来存放我们的根文件系统了。
将busybox-1.29.0.tar.bz2 发送到 Ubuntu 中,存放位置大家随便选择。我这里放在/home/zhiguoxin/linux/IMX6ULL/roofts
,然后使用如下命令将其解压:
tar -vxjf busybox-1.29.0.tar.bz2
解压完成以后进入到 busybox-1.29.0目录中,此目录中的文件和文件夹如图所示:
1.2.1 修改 Makefile,添加编译器
同 Uboot 和 Linux 移植一样,打开 busybox 的顶层 Makefile,添加 ARCH 和 CROSS_COMPILE的值,如下所示:
CROSS_COMPILE ?= /usr/local/arm/gcc-linaro-4.9.4-2017.01-x86_64_arm-linux-gnueabihf/bin/arm-linux-gnueabihf-
ARCH ?= arm
1.2.2 busybox中文字符支持
如果默认直接编译 busybox 的话,在使用 SecureCRT 的时候中文字符是显示不正常的,中文字符会显示为“?”,比如你的中文目录,中文文件都显示为“?”。不知道从哪个版本开始 busybox中的 shell 命令对中文输入即显示做了限制,即使内核支持中文但在 shell 下也依然无法正确显示。
所以我们需要修改 busybox 源码,取消 busybox 对中文显示的限制,打开文件busybox-1.29.0/libbb/printable_string.c
,找到函数printable_string
,缩减后的函数内容如下:
vi libbb/printable_string.c
主要就是禁止字符大于0X7F以后break和输出‘?’。
接着打开文件busybox-1.29.0/libbb/unicode.c
,找到如下内容:
vi libbb/unicode.c
红色部分的代码就是被修改以后的,同样主要是禁止字符大于 0X7F 的时候设置为‘?’。busybox 中文字符支持跟代码修改有关的就改好了,最后还需要配置 busybox来使能 unicode 码,这个稍后我们配置 busybox 的时候在设置。
1.2.3 配置 busybox
根我们编译 Uboot、Linux kernel 一样,我们要先对 busybox 进行默认的配置,有以下几种配置选项:
- ①、defconfig,缺省配置,也就是默认配置选项。
- ②、allyesconfig,全选配置,也就是选中 busybox 的所有功能。
- ③、allnoconfig,最小配置。
我们一般使用默认配置即可,因此使用如下命令先使用默认配置来配置一下 busybox:
make defconfig
busybox 也支持图形化配置,通过图形化配置我们可以进一步选择自己想要的功能,输入如下命令打开图形化配置界面:
make menuconfig
打开以后如图所示:
配置路径如下:
Location:
-> Settings
-> Build static binary (no shared libs)
选项“Build static binary (no shared libs)”用来决定是静态编译 busybox 还是动态编译,静态编译的话就不需要库文件,但是编译出来的库会很大。动态编译的话要求根文件系统中有库文件,但是编译出来的 busybox 会小很多。这里我们不能采用静态编译!因为采用静态编译的话 DNS 会出问题!无法进行域名解析,配置如图所示:
继续配置如下路径配置项:
Location:
-> Settings
-> vi-style line editing commands
结果如图所示:
继续配置如下路径配置项:
Location:
-> Linux Module Utilities
-> Simplified modutils
默认会选中“Simplified modutils”,这里我们要取消勾选!!结果如图所示:
继续配置如下路径配置项:
Location:
-> Linux System Utilities
-> mdev (16 kb) //确保下面的全部选中,默认都是选中的
结果如图所示:
最后就是使能 busybox 的 unicode 编码以支持中文,配置路径如下:
Location:
-> Settings
-> Support Unicode //选中
-> Check $LC_ALL, $LC_CTYPE and $LANG environment variables //选中
结果如图所示:
busybox 的配置就到此结束了,大家也可以根据自己的实际需求选择配置其他的选项,不过对于初学者笔者不建议再做其他的修改,可能会出现编译出错的情况发生。
1.2.4 编译 busybox
配置好 busybox 以后就可以编译了,我们可以指定编译结果的存放目录,我们肯定要将编译结果存放到前面创建的 rootfs 目录中,输入如下命令:
make
make install CONFIG_PREFIX=/home/zhiguoxin/linux/nfs/rootfs
COFIG_PREFIX 指 定 编 译 结 果 的 存 放 目 录 , 比 如 我 存 放 到/home/zhiguoxin/linux/nfs/rootfs
目录中,等待编译完成。编译完成以后如图所示:
编译完成以后会在 busybox 的所有工具和文件就会被安装到 rootfs 目录中,rootfs 目录内容如图 所示:
从图可以看出,rootfs 目录下有 bin、sbin 和 usr 这三个目录,以及 linuxrc 这个文件。前面说过Linux 内核 init 进程最后会查找用户空间的 init 程序,找到以后就会运行这个用户空间的 init 程序,从而切换到用户态。如果 bootargs 设置 init=/linuxrc,那么 linuxrc 就是可以作为用户空间的 init 程序,所以用户态空间的 init 程序是 busybox 来生成的。
busybox 的工作就完成了,但是此时的根文件系统还不能使用,还需要一些其他的文件,我们继续来完善 rootfs。
1.3 向根文件系统添加lib库
1.3.1 向rootfs的/lib目录添加库文件
Linux 中的应用程序一般都是需要动态库的,当然你也可以编译成静态的,但是静态的可执行文件会很大。如果编译为动态的话就需要动态库,所以我们需要先根文件系统中添加动态库。在 rootfs 中创建一个名为“lib”的文件夹,命令如下:
mkdir lib
lib文件夹创建好了,库文件从哪里来呢?lib 库文件从交叉编译器中获取,前面我们搭建交叉编译环境的时候将交叉编译器存放到了/usr/local/arm/
目录中。交叉编译器里面有很多的库文件,这些库文件具体是做什么的我们作为初学者肯定不知道,既然我不知道那就简单粗暴的把所有的库文件都放到我们的根文件系统中。这样做出来的根文件系统肯定很大,但是我们现在是学习阶段,还做不了裁剪。
进入如下路径对应的目录:
cd /usr/local/arm/gcc-linaro-4.9.4-2017.01-x86_64_arm-linux-gnueabihf/arm-linux-gnueabihf/libc/lib
此目录下有很多的so(是通配符)和.a 文件,这些就是库文件,将此目录下所有的so*和.a文件都拷贝到 rootfs/lib目录中,拷贝命令如下:
cp *so* *.a /home/zhiguoxin/linux/nfs/rootfs/lib/ -d
后面的-d
表示拷贝符号链接,这里有个比较特殊的库文件:ld-linux-armhf.so.3
,此库文件也是个符号链接,相当于 Windows 下的快捷方式。会链接到库 ld-2.19-2014.08-1-git.so 上,输入命令ls ld-linux-armhf.so.3 -l
查看此文件详细信息,如图所示:
ls ld-linux-armhf.so.3 -l
从图 38.2.3.1 可以看出,ld-linux-armhf.so.3 后面有个“->”,表示其是个软连接文件,链接到文件 ld-2.19-2014.08-1-git.so,因为其是一个“快捷方式”,因此大小只有 24B。但是,ld-linux-armhf.so.3 不能作为符号链接,否则的话在根文件系统中执行程序无法执行!所以我们需要 ld-linux-armhf.so.3 完成逆袭,由“快捷方式”变为“本尊”,方法很简单,那就是重新复制 ld-linux-armhf.so.3,只是不复制软链接即可,先将 rootfs/lib 中的 ld-linux-armhf.so.3 文件删除掉,命令如下:
rm ld-linux-armhf.so.3
然后重新进入到/usr/local/arm/gcc-linaro-4.9.4-2017.01-x86_64_arm-linux-gnueabihf/arm-linux-gnueabihf/libc/lib 目录中,重新拷贝ld-linux-armhf.so.3,命令如下:
cd /usr/local/arm/gcc-linaro-4.9.4-2017.01-x86_64_arm-linux-gnueabihf/arm-linux-gnueabihf/libc/lib
cp ld-linux-armhf.so.3 /home/zhiguoxin/linux/nfs/rootfs/lib/
拷贝完成以后再到 rootfs/lib 目录下查看 ld-linux-armhf.so.3 文件详细信息,如图所示:
从图 38.2.3.2 可以看出,此时 ld-linux-armhf.so.3 已经不是软连接了,而是实实在在的一个库文件,而且文件大小为 724392B。
继续进入如下目录中:
cd /usr/local/arm/gcc-linaro-4.9.4-2017.01-x86_64_arm-linux-gnueabihf/arm-linux-gnueabihf/lib
此目录下也有很多的的so和.a 库文件,我们将其也拷贝到rootfs/lib 目录中,命令如下:
cp *so* *.a /home/zhiguoxin/linux/nfs/rootfs/lib/ -d
rootfs/lib 目录的库文件就这些了,完成以后的 rootfs/lib 目录如图所示:
1.3.2 向rootfs的usr/lib目录添加库文件
在rootfs的usr目录下创建一个名为 lib 的目录,将如下目录中的库文件拷贝到rootfs/usr/lib目录下:/usr/local/arm/gcc-linaro-4.9.4-2017.01-x86_64_arm-linux-gnueabihf/arm-linux-gnueabihf/libc/usr/lib
cd usr
mkdir lib
将此目录下的 so 和.a 库文件都拷贝到 rootfs/usr/lib 目录中,命令如下:
cd /usr/local/arm/gcc-linaro-4.9.4-2017.01-x86_64_arm-linux-gnueabihf/arm-linux-gnueabihf/libc/usr/lib
cp *so* *.a /home/zhiguoxin/linux/nfs/rootfs/usr/lib/ -d
完成以后的 rootfs/usr/lib 目录如图所示:
至此,根文件系统的库文件就全部添加好了,可以使用“du”命令来查看一下 rootfs/lib 和rootfs/usr/lib 这两个目录的大小,命令如下:
cd rootfs //进入根文件系统目录
du ./lib ./usr/lib/ -sh //查看 lib 和 usr/lib 这两个目录的大小
结果如图所示:
可以看出lib和usr/lib这两个文件的大小分别为57MB和68MB,加起来就是57+68=125MB。非常大!
1.3.3 创建其他文件夹
在根文件系统中创建其他文件夹,如dev、proc、mnt、sys、tmp 和root等,创建完成以后,如图所示:
目前来看,这个根文件系统好像已经准备好了,究竟有没有准备好,直接测一下就知道了!
二、根文件系统初步测试
接下来我们使用测试一下前面创建好的根文件系统 rootfs,测试方法就是使用 NFS 挂载,uboot 里面的 bootargs 环境变量会设置“root”的值,所以我们将 root 的值改为 NFS 挂载即可。
在 Linux 内核源码里面有相应的文档讲解如何设置,文档为 Documentation/filesystems/nfs/
nfsroot.txt,格式如下:
root=/dev/nfs nfsroot=[<server-ip>:]<root-dir>[,<nfs-options>] ip=<client-ip>:<server-ip>:<gw-ip>:<netmask>:<hostname>:<device>:<autoconf>:<dns0-ip>:<dns1-ip>
< server-ip>:服务器 IP 地址,也就是存放根文件系统主机的 IP 地址,那就是 Ubuntu 的 IP
地址,比如我的 Ubuntu 主机 IP 地址为 192.168.10.100。
< root-dir> :根文件系统的存放路径,比如我的就是/home/zhiguoxin/linux/nfs/rootfs。
< nfs-options>:NFS 的其他可选选项,一般不设置。
< client-ip> :客户端 IP 地址,也就是我们开发板的 IP 地址,Linux 内核启动以后就会使用
此 IP 地址来配置开发板。此地址一定要和 Ubuntu 主机在同一个网段内,并且没有被其他的设
备使用,在 Ubuntu 中使用 ping 命令 ping 一下就知道要设置的 IP 地址有没有被使用,如果不能
ping 通就说明没有被使用,那么就可以设置为开发板的 IP 地址,比如我就可以设置为
192.168.10.50。
< server-ip> :服务器 IP 地址,前面已经说了。
< gw-ip> :网关地址,我的就是 192.168.10.1。
< netmask>:子网掩码,我的就是 255.255.255.0。
< hostname>:客户机的名字,一般不设置,此值可以空着。
< device> :设备名,也就是网卡名,一般是 eth0,eth1….,正点原子的 I.MX6U-ALPHA 开
发板的 ENET2 为 eth0,ENET1 为 eth1。如果你的电脑只有一个网卡,那么基本只能是 eth0。
这里我们使用 ENET2,所以网卡名就是 eth0。
< autoconf> :自动配置,一般不使用,所以设置为 off。
< dns0-ip> :DNS0 服务器 IP 地址,不使用。
< dns1-ip> :DNS1 服务器 IP 地址,不使用。
根据上面的格式 bootargs 环境变量的 root 值如下:
root=/dev/nfs nfsroot=192.168.10.100:/home/zhiguoxin/linux/nfs/rootfs,proto=tcp rw ip=192.168.10.50:192.168.10.100:192.168.10.1:255.255.255.0::eth0:off
“proto=tcp”表示使用 TCP 协议,“rw”表示 nfs 挂载的根文件系统为可读可写。启动开发板,进入 uboot 命令行模式,然后重新设置 bootargs 环境变量,命令如下:
setenv bootargs 'console=tty0 console=ttymxc0,115200 root=/dev/nfs nfsroot=192.168.10.100:/home/zhiguoxin/linux/nfs/rootfs,proto=tcp rw ip=192.168.10.50:192.168.10.100:192.168.10.1:255.255.255.0::eth0:off'
saveenv
设置好以后使用boot
命令启动Linux内核,结果如图所示:
在进入根文件系统的时候会有下面这一行错误提示:
can't run '/etc/init.d/rcS': No such file or directory
提示很简单,说是无法运行/etc/init.d/rcS
这个文件,因为这个文件不存在。看来我们的 rootfs 还是缺文件,还需要一步一步的完善。
三、完善根文件系统
3.1 创建/etc/init.d/rcS 文件
rcS 是个 shell 脚本,Linux内核启动以后需要启动一些服务,而rcS就是规定启动哪些文件的脚本文件。在 rootfs 中创建/etc/init.d/rcS 文件,然后在rcS中输入如下所示内容:
ls
mkdir etc
cd etc
mkdir init.d
cd init.d
vi rcS
#!/bin/sh
PATH=/sbin:/bin:/usr/sbin:/usr/bin:$PATH
LD_LIBRARY_PATH=$LD_LIBRARY_PATH:/lib:/usr/lib
export PATH LD_LIBRARY_PATH
mount -a
mkdir /dev/pts
mount -t devpts devpts /dev/pts
echo /sbin/mdev > /proc/sys/kernel/hotplug
mdev -s
- 第 1 行,表示这是一个 shell 脚本。
- 第 3 行,PATH 环境变量保存着可执行文件可能存在的目录,这样我们在执行一些命令或者可执行文件的时候就不会提示找不到文件这样的错误。
- 第 4 行,LD_LIBRARY_PATH 环境变量保存着库文件所在的目录。
- 第 5 行,使用 export 来导出上面这些环境变量,相当于声明一些“全局变量”。
- 第 7 行,使用 mount 命令来挂载所有的文件系统,这些文件系统由文件/etc/fstab 来指定,所以我们一会还要创建/etc/fstab 文件。
- 第 8 和 9 行,创建目录/dev/pts,然后将 devpts 挂载到/dev/pts 目录中。
- 第 11 和 12 行,使用 mdev 来管理热插拔设备,通过这两行,Linux 内核就可以在/dev 目录下自动创建设备节点。关于 mdev 的详细内容可以参考 busybox 中的 docs/mdev.txt 文档。
示例代码中的 rcS 文件内容是最精简的,大家如果去看 Ubuntu 或者其他大型 Linux操作系统中的rcS 文件,就会发现其非常复杂。因为我们是初次学习,所以不用搞这么复杂的,而且这么复杂的 rcS 文件也是借助其他工具创建的,比如 buildroot 等。
创建好文件/etc/init.d/rcS以后一定要给其可执行权限!使用如下命令给予/ec/init.d/rcS 可执行权限:
chmod 777 rcS
设置好以后就重新启动 Linux 内核,启动以后如图所示:
从图可以看到,提示找不到/etc/fstab 文件,还有一些其他的错误,我们先把/etc/fstab这个错误解决了。说不定把这个问题解决以后其他的错误也就解决了。前面我们说了“mount -a”挂载所有根文件系统的时候需要读取/etc/fstab,因为/etc、fstab 里面定义了该挂载哪些文件,好了,接下来就是创建/etc/fstab 文件。
3.2 创建/etc/fstab文件
在 rootfs中创建/etc/fstab 文件,fstab在Linux开机以后自动配置哪些需要自动挂载的分区,格式如下:
< file system> < mount point> < type> < options> < dump> < pass>
< file system>:要挂载的特殊的设备,也可以是块设备,比如/dev/sda 等等。
< mount point>:挂载点。
< type>:文件系统类型,比如 ext2、ext3、proc、romfs、tmpfs 等等。
< options>:挂载选项,在 Ubuntu 中输入“man mount”命令可以查看具体的选项。一般使用 defaults,也就是默认选项,defaults 包含了 rw、suid、 dev、 exec、 auto、 nouser 和 async。
< dump>:为 1 的话表示允许备份,为 0 不备份,一般不备份,因此设置为 0。
< pass>:磁盘检查设置,为 0 表示不检查。根目录‘/’设置为 1,其他的都不能设置为 1,其他的分区从 2 开始。一般不在 fstab 中挂载根目录,因此这里一般设置为 0。
按照上述格式,在 fstab 文件中输入如下内容:
#<file system> <mount point> <type> <options> <dump> <pass>
proc /proc proc defaults 0 0
tmpfs /tmp tmpfs defaults 0 0
sysfs /sys sysfs defaults 0 0
fstab 文件创建完成以后重新启动 Linux,结果如图所示:
可以看出,启动成功,而且没有任何错误提示。但是我们要还需要创建一个文件/etc/inittab。
3.3 创建/etc/inittab文件
inittab的详细内容可以参考 busybox 下的文件examples/inittab。init 程序会读取/etc/inittab这个文件,inittab 由若干条指令组成。每条指令的结构都是一样的,由以:
分隔的 4 个段组成,格式如下:
<id>:<runlevels>:<action>:<process>
< id >:每个指令的标识符,不能重复。但是对于 busybox 的 init 来说,有着特殊意义。对于busybox 而言< id>用来指定启动进程的控制 tty,一般我们将串口或者 LCD 屏幕设置为控制 tty。
< runlevels > :对 busybox 来说此项完全没用,所以空着。
< action >:动作,用于指定< process>可能用到的动作。busybox 支持的动作如表所示:
< process> :具体的动作,比如程序、脚本或命令等。
参考 busybox 的examples/inittab 文件,我们也创建一个/etc/inittab,在里面输入如下内容:
# etc/inittab
::sysinit:/etc/init.d/rcS
console::askfirst:-/bin/sh
::restart:/sbin/init
::ctrlaltdel:/sbin/reboot
::shutdown:/bin/umount -a -r
::shutdown:/sbin/swapoff -a
- 第 2 行,系统启动以后运行/etc/init.d/rcS 这个脚本文件。
- 第 3 行,将 console 作为控制台终端,也就是 ttymxc0。
- 第 4 行,重启的话运行/sbin/init。
- 第 5 行,按下 ctrl+alt+del 组合键的话就运行/sbin/reboot,看来 ctrl+alt+del 组合键用于重启系统。
- 第 6 行,关机的时候执行/bin/umount,也就是卸载各个文件系统。
- 第 7 行,关机的时候执行/sbin/swapoff,也就是关闭交换分区。
/etc/inittab文件创建好以后就可以重启开发板即可,至此!根文件系统要创建的文件就已经全部完成了。接下来就要对根文件系统进行其他的测试,比如是我们自己编写的软件运行收费正常、是否支持软件开机自启动、中文支持是否正常以及能不能链接等。
四、根文件系统其他功能测试
4.1 软件运行测试
我们使用 Linux 的目的就是运行我们自己的软件,我们编译的应用软件一般都使用动态库,使用动态库的话应用软件体积就很小,但是得提供库文件,库文件我们已经添加到了根文件系统中。我们编写一个小小的测试软件来测试一下库文件是否工作正常,在根文件系统下创建一个名为“drivers”的文件夹,以后我们学习 Linux 驱动的时候就把所有的实验文件放到这个文件夹里面。
在 ubuntu下使用vim编辑器新建一个hello.c文件,在hello.c里面输入如下内容:
#include <stdio.h>
int main(void)
{
while(1)
{
printf("hello world!\r\n");
sleep(2);
}
return 0;
}
arm-linux-gnueabihf-gcc hello.c -o hello
将其拷贝到 rootfs/drivers 目录下,在开发板中输入如下命令来执行这个可执行文件:
cd /drivers
./hello
可以看出,hello 这个软件运行正常,说明我们的根文件系统中的共享库是没问题的,要想终止 hello 的运行,按下“ctrl+c”组合键即可。此时大家应该能感觉到,hello 执行的时候终端是没法用的,除非使用“ctrl+c”来关闭 hello,那么有没有办法既能让 hello 正常运行,而且终端能够正常使用?那肯定是有的,让 hello 进入后台运行就行了。
让一个软件进入后台的方法很简单,运行软件的时候加上&
即可,比如./hello &
就是让 hello 在后台运行。在后台运行的软件可以使用kill -9 pid(进程 ID)
命令来关闭掉,首先使用ps
命令查看要关闭的软件 PID 是多少,ps 命令用于查看所有当前正在运行的进程,并且会给出进程的 PID。输入ps
命令,结果如图所示:
从图可以看出 hello 对应的 PID 为 445,因此我们使用如下命令关闭在后台运行的hello 软件:
kill -9 445
因为 hello 在不断的输出“hello world”所以我们的输入看起来会被打断,其实是没有的,因为我们是输入,而 hello 是输出。在数据流上是没有打断的,只是显示在 SecureCRT 上就好像被打断了,所以只管输入kill -9 445
即可。
再去用 ps 命令查看一下当前的进程,发现没有 hello 了。这个就是 Linux 下的软件后台运行以及如何关闭软件的方法,重点就是 3 个操作:软件后面加&
、使用 ps 查看要关闭的软件 PID、使用kill -9 pid
来关闭指定的软件。
4.2 外网连接测试
这里说的外网不是外国哪些 404 网站的连接测试,而是百度、淘宝等这些网站的测试。也就是说看看我们的开发板能不能上网,能不能和我们的局域网外的这些网站进行通信。测试方法很简单,就是通过 ping 命令来 ping 一下百度的官网:www.baidu.com。输入如下命令:
ping www.baidu.com
结果如图所示:
可以看出,测试失败,提示 www.baidu.com 是个“bad address”,也就是地址不对,显然我们的地址是正确的。之所以出现这个错误提示是因为 www.baidu.com 的地址解析失败了,并没有解析出其对应的 IP 地址。我们需要配置域名解析服务器的 IP 地址,一般域名解析地址可以设置为所处网络的网关地址,比如 192.168.10.1。也可以设置为 114.114.1144.114,这个是运营商的域名解析服务器地址。
在 rootfs 中新建文件/etc/resolv.conf,然后在里面输入如下内容:
nameserver 114.114.114.114
nameserver 192.168.10.1
设置很简单,nameserver 表示这是个域名服务器,设置了两个域名服务器地址:114.114.114.114 和 192.168.10.1,大家也可以改为其他的域名服务器试试。如果使用“udhcpc”命令自动获取 IP 地址,“udhcpc”命令会修改 nameserver 的值,一般是将其设置为对应的网关地址。修改好以后保存退出,重启开发板!重启以后重新 ping 一下百度官网,可以成功。
至此!我们的根文件系统就彻底的制作完成,这个根文件系统最好打包保存一下,防止以后做实验不小心破坏了根文件系统而功亏一篑,又得从头制作根文件系统。uboot、Linux kernel、rootfs 这三个共同构成了一个完整的Linux 系统,现在的系统至少是一个可以正常运行的系统。