IMX6ULL驱动开发前奏三:根文件系统构建步骤明细

Linux搭建根文件系统

根文件系统首先是内核启动时所 mount(挂载)的第一个文件系统,内核代码映像文件保存在根文件系统中,而系统引导启动程序会在根文件系统挂载之后从中把一些基本的初始化脚本和服务等加载到内存中去运行。

使用BusyBox构建根文件系统

先在NFS服务器目录下创建一个rootfs文件夹,用于通过NFS挂载根文件系统。(存放在NFS下的文件夹)

获取的busybox压缩包

放入任意文件夹中并解压。(存放在自定义任意文件夹)

/*命令*/
mkdir rootfs
tar -vxjf busybox-1.29.0.tar.bz2

完成后如下:
在这里插入图片描述
接下来打开顶层Makefile,添加 ARCH 和 CROSS_COMPILE(绝对路径) 的值。
在这里插入图片描述

让busybox支持中文

首先打开busybox-1.29.0/libbb目录下的 printable_string.c 文件,找到 printable_string 函数。

在vim编辑器中,在命令行模式下:用以下命令可以搜索字符串。

/xxx

修改后的代码如下

const char* FAST_FUNC printable_string(uni_stat_t *stats, const char *str)
{
    char *dst;
    const char *s;

    s = str;
    while (1) {
        unsigned char c = *s;
        if (c == '\0') {
            /* 99+% of inputs do not need conversion */
            if (stats) {
                stats->byte_count = (s - str);
                stats->unicode_count = (s - str);
                stats->unicode_width = (s - str);
            }
            return str;
        }
        if (c < ' ')
            break;
        /*      if (c >= 0x7f)
                        break;  */
        s++;
    }

    #if ENABLE_UNICODE_SUPPORT
    dst = unicode_conv_to_printable(stats, str);
    #else
    {
        char *d = dst = xstrdup(str);
        while (1) {
            unsigned char c = *d;
            if (c == '\0')
                /*      if (c < ' ' || c >= 0x7f)*/
                if(c < ' ')
                    *d = '?';
            d++;
        }
        if (stats) {
            stats->byte_count = (d - dst);
            stats->unicode_count = (d - dst);
            stats->unicode_width = (d - dst);
        }
    }
    #endif
    return auto_string(dst);
}

再打开 unicode.c 文件,找到 unicode_conv_to_printable2 函数,修改后如下

static char* FAST_FUNC unicode_conv_to_printable2(uni_stat_t *stats, const char *src, unsigned width, int flags)
{
    char *dst;
    unsigned dst_len;
    unsigned uni_count;
    unsigned uni_width;

    if (unicode_status != UNICODE_ON) {
        char *d;
        if (flags & UNI_FLAG_PAD) {
            d = dst = xmalloc(width + 1);
            while ((int)--width >= 0) {
                unsigned char c = *src;
                if (c == '\0') {
                    do
                        *d++ = ' ';
                    while ((int)--width >= 0);
                    break;
                }
                /*      *d++ = (c >= ' ' && c < 0x7f) ? c : '?';        */
                *d++ = (c >= ' ') ? c : '?';
                src++;
            }
            *d = '\0';
        } else {
            d = dst = xstrndup(src, width);
            while (*d) {
                unsigned char c = *d;
                /*      if (c < ' ' || c >= 0x7f) */
                if(c < ' ')
                    *d = '?';
                d++;
            }
        }
        if (stats) {
            stats->byte_count = (d - dst);
            stats->unicode_count = (d - dst);
            stats->unicode_width = (d - dst);
        }
        return dst;
    }

    ......

}

配置busybox

默认配置命令:

make defconfig

利用图形化配置界面进行配置,命令:

make menuconfig

打开后如下图所示:
在这里插入图片描述
要配置的路径:

1.
Location: 
	 -> Settings 
		-> Build static binary (no shared libs)		//不选中
		
2.
Location: 
	-> Settings 
		-> vi-style line editing commands			//选中
		
3.
Location: 
	-> Linux Module Utilities
		-> Simplified modutils						//不选中
		
4.
Location: 
	-> Linux System Utilities 
		 -> mdev (16 kb)//确保下面的全部选中,默认都是选中的
		 
5.
Location: 
	-> Settings
 		-> Support Unicode 												//选中
		-> Check $LC_ALL, $LC_CTYPE and $LANG environment variables 	//选中

编译busybox

make
make install CONFIG_PREFIX=/home/swiler/workdir/rootfs

编译完成后如下所示:
在这里插入图片描述

向根文件系统添加lib库

此时的rootfs目录下的内容如图所示:
在这里插入图片描述
接下来在根目录下新建 lib 目录,添加动态库,动态库位于交叉编译器中

目录
/usr/local/arm/gcc-linaro-4.9.4-2017.01-x86_64_arm-linux-gnueabihf/arm-linux-gnueabihf/libc/lib

拷贝所有的带so和.a的文件到lib目录下

cp *so* *.a /home/swiler/workdir/rootfs/lib/ -d

注意要将 ld-linux-armhf.so.3 这个换成文件本身,不能是一个软链接文件。删除原来的软链接文件,再复制一份其本身即可。

/* 命令 */
rm 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/swiler/workdir/rootfs/lib/

再进入另一个目录下,拷贝其它的库文件

目录
/usr/local/arm/gcc-linaro-4.9.4-2017.01-x86_64_arm-linux-gnueabihf/arm-linux-gnueabihf/lib

/* 命令 */
cd /usr/local/arm/gcc-linaro-4.9.4-2017.01-x86_64_arm-linux-gnueabihf/arm-linux-gnueabihf/lib

cp *so* *.a /home/swiler/workdir/rootfs/lib/ -d

拷贝完成后lib目录内容如下图所示
在这里插入图片描述
接着在usr目录下新建lib目录添加库文件

再进入到如下目录拷贝库文件到usr/lib目录下

目录:
/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/swiler/workdir/rootfs/usr/lib/ -d

拷贝完成后 usr/lib 目录内容如下图所示
在这里插入图片描述

创建其它文件夹

创建完如下图所示
在这里插入图片描述

测试

进入uboot模式,配置bootargs变量

格式如下:

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 地址
root-dir根文件系统的存放路径
nfs-optionsNFS 的其他可选选项,一般不设置
client-ip客户端 IP 地址
server-ip服务器 IP 地址
gw-ip网关地址
netmask子网掩码
hostname客户机的名字,一般不设置,此值可以空着
device设备名,也就是网卡名,一般是 eth0,eth1
autoconf自动配置,一般不使用,所以设置为 off
dns0-ipDNS0 服务器 IP 地址,不使用
dns1-ipDNS1 服务器 IP 地址,不使用

完整命令例子:

命令
setenv bootargs 'console=ttymxc0,115200 root=/dev/nfs nfsroot=192.168.1.250:
/home/swiler/workdir/rootfs,proto=tcp rw ip=192.168.1.251:192.168.1.250:192.168.1.1:
255.255.255.0::eth0:off' //设置 bootargs

saveenv //保存环境变量

启动Linux内核

boot命令启动内核,进入后可以用 ls 命令看看根文件系统是否工作

下图就是正常启动后的样子

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-0zF8xie8-1651580862231)(C:\Users\15894\AppData\Roaming\Typora\typora-user-images\image-20220503195502573.png)]
在这里插入图片描述

进一步完善根文件系统

rcS脚本

在 /etc/init.d 目录创建rcS脚本,帮助Linux内核启动后需要启动的一些服务。

内容如下:

#!/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

给予文件可执行权限

chmod 777 rcS

之后要修改该文件时,如果碰到 Read-only file system 的错误时,可以利用以下命令修改目录为可读写模式

/data 指的是 data 目录

mount -o remount -rw  /data

fstab文件

在 /etc 目录下创建 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
file system要挂载的特殊的设备
mount point挂载点
type文件系统类型
options挂载选项,“man mount”命令可以查看具体的选项
dump为 1 的话表示允许备份,为 0 不备份
pass磁盘检查设置,为 0 表示不检查。只有根目录设置为1

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
动作描述
sysinit在系统初始化的时候 process 才会执行一次
respawn当 process 终止以后马上启动一个新的
askfirst和 respawn 类似,在运行 process 之前在控制台上显示“Please press Enter to activate this console.”。只要用户按下“Enter”键以后才会执行 process
wait告诉 init,要等待相应的进程执行完以后才能继续执行
once仅执行一次,而且不会等待 process 执行完成
restart当 init 重启的时候才会执行 procee
ctrlaltdel当按下 ctrl+alt+del 组合键才会执行 process
shutdown关机的时候执行 process

resolv.conf文件

该文件是用来配置域名解析服务器的 IP 地址,一般域名解析地址可以设置为所处网络的网关地址,比如 192.168.1.1。也可以设置为 114.114.114.114,这个是运营商的域名解析服务器地址。配置完,重启后就可以联网了。

文件创建在 /etc 目录下,内容如下:

nameserver 114.114.114.114
nameserver 192.168.1.1

ping成功则如下图所示:
在这里插入图片描述
这样根文件系统也就配置好了。

  • 0
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值