buildroot快速构建

buildroot 快速构建

buildroot 简介

前面我们讲解了busybox构建根文件系统,只是帮我们构建好了一些常用的命令和文件,像 lib 库、/etc 目录下的一些文件都需要我们自己手动创建,而且 busybox 构建的根文件系统默认没有用户名和密码设置。后续我们还要自己去移植一些第三方软件和库,比如 alsa、iperf、mplayer 等等。

那么有没有一种傻瓜式的方法或软件,它不仅包含了 busybox 的功能,而且里面还集成了各种软件,需要什么软件就选择什么软件,不需要我们去移植。答案肯定是有的,buildroot 就是这样一种工具,buildroot比 busybox 更上一层楼,buildroot 不仅集成了 busybox,而且还集成了各种常见的第三方库和软件,需要什么就选择什么,就跟我们去吃自助餐一样,想吃什么就拿什么。buildroot 极大的方便了我们Linux 开发人员构建实用的根文件系统。

从 busybox 开始一步一步的构建根文件系统适合学习、了解根文件系统的组成,但是不适合做产品(主要是自己构建的话会有很多不完善、没有注意到的细节)。buildroot 会帮我们处理好各种细节,根文件系统也会更加的合理、有效。因此在做产品的时候推荐大家使用 buildroot 来构建自己的根文件系统,当然了,类似 buildroot 的软件还有很多,比如后面要讲的 yocto。

buildroot 和 uboot、Linux Kernel 很类似,我们需要到其官网上下载源码,然后对其进行配置,比如设置交叉编译器、设置目标 CPU 参数等,最主要的就是选择所需要的第三方库或软件。一切配置好以后就可以进行编译,编译完成了以后就会在一个文件夹里面存放好编译结果,也就是根文件系统。

buildroot下载

buildroot源码需要从官网下载,官网地址为https://buildroot.org/

构建根文件系统

配置buildroot

首先对源码包进行解压

1
tar -xvJf buildroot-2025.02.3.tar.xz

目录下的文件如图所示:

buildroot 和 uboot、Linux kernel 一样也支持图形化配置,输入如下命令即可打开图形化配置界:

1
make menuconfig

buildroot 和 uboot、Linux kernel 一样也支持图形化配置,输入如下命令即可打开图形化配置界:

配置 Target options

首先配置 Target options 选项,需要配置的项目和其对应的内容如下(“=”号后面是配置项要选择的内容!):

1
2
3
4
5
6
7
Target options
-> Target Architecture = ARM (little endian)
-> Target Binary Format = ELF
-> Target Architecture Variant = cortex-A7
-> Target ABI = EABIhf
-> Floating point strategy = NEON/VFPv4
-> ARM instruction set = ARM
配置 Toolchain

此配置项用于配置交叉编译工具链,也就是交叉编译器,这里设置为我们自己所使用的交叉编译器即可。buildroot 其实是可以自动下载交叉编译器的,但是都是从国外服务器下载的,鉴于国内的网络环境,强烈推荐大家设置成自己所使用的交叉编译器。需要配置的项目和其对应的内容如下:

1
2
3
4
5
6
7
8
9
10
11
12
13
Toolchain
-> Toolchain type = External toolchain
-> Toolchain = Custom toolchain //用户自己的交叉编译器
-> Toolchain origin = Pre-installed toolchain //预装的编译器
-> Toolchain path =/usr/arm-linux-gnueabihf
-> Toolchain prefix = $(ARCH)-linux-gnueabihf //前缀
-> External toolchain gcc version = 4.9.x
-> External toolchain kernel headers series = 4.1.x
-> External toolchain C library = glibc/eglibc
-> [*] Toolchain has SSP support? (NEW) //选中
-> [*] Toolchain has RPC support? (NEW) //选中
-> [*] Toolchain has C++ support? //选中
-> [*] Enable MMU support (NEW) //选中

Toolchain 下几个比较重要的选项需要说明一下,如下所示:

Toolchain:设置为 Custom toolchain,表示使用用户自己的交叉编译器。

Toolchain origin:设置为 Pre-installed toolchain,表示使用预装的交叉编译器。

Toolchain path:设置自己安装的交叉编译器绝对路径!buildroot 要用到。

Toolchain prefix:设置交叉编译器前缀,要根据自己实际所使用的交叉编译器来设置,比如我们使用的是 aarch64-linux-gnu-gcc,因此前缀就是$(ARCH)-linux-gnueabihf,其中 ARCH我们前面已经设置为了 arm。

配置 System configuration

此选项用于设置一些系统配置,比如主板名字、欢迎语、用户名、密码等。需要配置的项目和其对应的内容如下:

1
2
3
4
5
6
7
System configuration
-> System hostname = alpha_imx6ull //平台名字,自行设置
-> System banner = Welcome to alpha i.mx6ull //欢迎语
-> Init system = BusyBox //使用 busybox
-> /dev management = Dynamic using devtmpfs + mdev //使用 mdev
-> [*] Enable root login with password (NEW) //使能登录密码
-> Root password = 123456 //登录密码为 123456
配置 Filesystem images

此选项配置我们最终制作的根文件系统为什么格式的,配置如下:

1
2
3
4
-> Filesystem images
-> [*] ext2/3/4 root filesystem //如果是 EMMC 或 SD 卡的话就用 ext3/ext4
-> ext2/3/4 variant = ext4 //选择 ext4 格式
-> [*] ubi image containing an ubifs root filesystem //如果使用 NAND 的话就用 ubifs
禁止编译 Linux 内核和 uboot

buildroot不仅仅能构建根文件系统,也可以编译 linux 内核和 uboot。当配置 buildroot,使能 linux 内核和 uboot 以后 buildroot 就会自动下载最新的 linux 内核和 uboot 源码并编译。但是我们一般都不会使用 buildroot 下载的 linux 内核和 uboot,因为 buildroot 下载的 linux 和 uboot官方源码,里面会缺少很多驱动文件,而且最新的 linux 内核和 uboot 会对编译器版本号有要求,可能导致编译失败。因此我们需要配置 buildroot,关闭 linux 内核和 uboot 的编译,只使用buildroot 来构建根文件系统,首先是禁止 Linux 内核的编译,配置如下:

1
2
-> Kernel 
-> [ ] Linux Kernel //不要选择编译 Linux Kernel 选项!

接着禁止编译 Uboot,配置如下:

1
2
-> Bootloaders 
-> [ ] U-Boot //不要选择编译 U-Boot 选项!
配置 Target packages

此选项用于配置要选择的第三方库或软件、比如 alsa-utils、ffmpeg、iperf 等工具,但是现在我们先不选择第三方库,防止编译不下去!先编译一下最基本的根文件系统,如果没有问题的话再重新配置选择第三方库和软件。否则一口吃太多会容易撑着的,编译出问题的时候都不知道怎么找问题。

编译 buildroot

配置完成以后就可以编译 buildroot 了,编译完成以后 buildroot 就会生成编译出来的根文件系统压缩包,我们可以直接使用。输入如下命令开始编译:

1
sudo make 	//注意,一定要加 sudo,而且不能通过-jx 来指定多核编译!!!

buildroot 编译的时候会先从网上下载所需的软件源码,有些软件源码可能下载不下来,这个时候就需要我们自行处理,这个后面会详细的讲解。

buildroot 编译过程会很耗时,可能需要几个小时,请耐心等待!

buildroot 因为要从网上下载源码,因此可能存在有些源码无法下载或下载很慢的情况,如图所示:

可以看出图中正在下载 cmake-3.8.2.tar.gz 这个压缩包,大小是 7.2MB,当前下载网速是 1.6KB/S , 需 要 用 时 71 分 钟 , 显 然 这 是 无 法 忍 受 的 ! 我 们 可 以 自 行 到https://cmake.org/files/v3.8/cmake-3.8.2.tar.gz 这个网站上去将 cmake-3.8.2.tar.gz 这个源码下载下来,然后拷贝到 Ubuntu 中 buildroot 源码目录下的 dl 文件夹中,dl 文件夹专用用于存放下载下来的源码。

等待编译完成,编译完成以后就会在 buildroot-2019.02.6/output/images 下生成根文件系统:

1
2
uos@uos:~/Desktop$ ls
rootfs.ext2 rootfs.ext4 rootfs.tar rootfs.ubi rootfs.ubifs

从图中可以看出,编译出来了多种格式的 rootfs,比如 ext2、ext4、ubi 等。其中rootfs.tar 就是打包好的根文件系统,我们就使用 rootfs.tar 进行测试。然后将图中的 rootfs.tar 拷贝到 buildrootfs 目录下并解压,命令如下:

1
2
3
4
tar -xvf rootfs.tar

uos@uos:~/Desktop/buildrootfs$ ls
bin etc lib32 media opt root sbin tmp var dev lib linuxrc mnt proc run sys usr

buildroot 第三方软件和库的配置

我在前面学习的时候需要自行移植一些第三方的库和软件,比如 alsa-lib、alsa-utils 等等,现在我们不需要自行移植这些第三方软件和库了,可以直接在 buildroot 里面配置使能。比如我们现在配置使能 alsa-lib、alsa-utils 这两个软件和库。

使能 alsa-lib

输入 make menuconfig,打开 buildroot 配置界面,配置路径如下:

1
2
3
4
Target packages
-> Libraries
-> Audio/Sound
-> -*- alsa-lib ---> 此配置项下的文件全部选中
使能 alsa-utils

接下来使能alsa-utils

1
2
3
Target packages 
-> Audio and video applications
-> alsa-utils 此目录下的软件全部选中

等待编译完成就可以使用新的根文件系统进行测试了,将 buildroot/images/rootfs.tar 拷贝到rootfs目录下的 buildroot 目录中,然后重新解压。注意,以前自己添加的文件并不会被删除掉的,解压命令如下:

1
tar -vxf rootfs.tar

解压完成以后就可以使用 alsa-utils 相关的软件了,比如 alsamixer,想想我们自行移植 alsa-utils 的时候,那个过程叫一个复杂。通过 buildroot 的话直接一个配置就可以搞定全部,方便快捷,大家可以自行尝试去配置使能一些其他的第三方库和软件。

buildroot 下的 busybox 配置

busybox 配置

buildroot 在构建根文件系统的时候也是要用到 busybox 的,既然用到了 busybox 那么就涉及到 busybox 的配置。buildroot 会自动下载 busybox 压缩包,buildroot 下载的源码压缩包都存放在/dl 目录下,在 dl 目录下就有一个叫做“busybox”的文件夹,此目录下保存着 busybox 压缩包。

1
2
uos@uos:~/Desktop/buildrootfs/dl$ ls
busybox-1.29.3.tar.bz2

可以看出,buildroot 下载的 busybox 版本为 1.29.3。要想编译 busybox,必须对压缩包进行解压缩,buildroot 将所有解压缩后的软件保存在/output/build 软件中,我们可以在找到/output/build/busybox-1.29.3 这个文件夹,此文件夹就是解压后的 busybox 源码

如果大家想要修改 busybox 源码的话就直接在目录中找到相应的文件,然后修改即可。我们现在是要配置 buildroot 下的 busybox,因此肯定要打开 busybox 的配置界面,在 buildroot下打开 busybox 的配置界面输入如下命令:

1
sudo make busybox-menuconfig

输入以后就会打开 buildroot 下的 busybox 配置界面

例如配置busybox中文字符支持,参考busybox制作根文件系统里面

编译busybox

配置好以后就可以重新编译 buildroot 下的 busybox,进入到 buildroot 源码目录下,输入如下命令查看当前 buildroot 所有配置了的目标软件包,也就是 packages:

1
sudo make show-targets

图中列出了当前 buildroot 中所有使能了的 packages 包,其中就包括 busybox,如果我们想单独编译并安装 busybox 的话执行下面命令即可:

1
sudo make busybox

上述命令就会重新编译 busybox。编译完成以后重新编译 buildroot,主要是对其进行打包,输入如下命令:

1
sudo make

重新编译完成以后查看一下 output/images 目录下 rootfs.tar 的创建时间是否为刚刚编译的,如果不是的话就删除掉 rootfs.tar,然后重新执行“sudo make”重新编译一下即可。最后我们使用新的 rootfs.tar 启动 Linux 系统。

根文件系统测试

buildroot 的根文件系统制作好以后就是测试工作了。这里我们重点说一下另外一个问题,我们使用构建的根文件系统启动以后会发现,输入命令的时候命令行前面一直都是“#”,如果我们进入到某个目录的话前面并不会显示当前目录路径,如图所示:

从图可以看出,我们当前所处的目录是/etc,但是前面的提示符一直是“#”,这样不利于我们查看自己当前所处的路径。最好能像其他操作系统一样,可以指出当前登录的用户名,主机名以及所处的目录,如图所示:

我们现在就来设置,实现图中所示的效果。我们要先了解一下“PS1”这个环境变量,PS1 用于设置命令提示符格式,格式如下:

1
PS1 = '命令列表'

命令列表中可选参数如下:

1
2
3
4
5
6
7
8
9
10
11
12
13
\! 显示该命令的历史记录编号。
\# 显示当前命令的命令编号。
\$ 显示$符作为提示符,如果用户是 root 的话,则显示#号。
\\ 显示反斜杠。
\d 显示当前日期。
\h 显示主机名。
\n 打印新行。
\nnn 显示 nnn 的八进制值。
\s 显示当前运行的 shell 的名字。
\t 显示当前时间。
\u 显示当前用户的用户名。
\W 显示当前工作目录的名字。
\w 显示当前工作目录的路径

我们打开/etc/profile 文件,找到如下所示内容,然后将其屏蔽掉:

1
2
3
4
5
6
7
3 if [ "$PS1" ]; then
4 if [ "`id -u`" -eq 0 ]; then
5 export PS1='# '
6 else
7 export PS1='$ '
8 fi
9 fi

上述代码就是原始的设置 PS1 环境变量的配置代码,就是它将命令提示符设置为了固定的“#”,我们将其屏蔽掉,然后输入如下所示内容:

1
2
1 PS1='[\u@\h]:\w$:'
2 export PS1

第 2 行就是设置 PS1 环境变量,格式就是:

1
[user@hostname]:currentpath$:

再次使用可以看出,命令提示符显示正常了,完整的显示除了用户名、主机名和当前路径。

至此,buildroot 构建根文件系统就已经全部完成了,当然了,很多第三方软件本章并没有使能,大家可以自行根据实际需求选择对应的第三方软件和库。

打包成initramfs

1
2
cd rootfs
find . | cpio -o -H newc | gzip > ../initramfs.cpio.gz

打包成initrd

1
2
3
4
5
6
7
8
9
10
11
# 生成1G的空镜像文件
dd if=/dev/zero of=initrd.img bs=1M count=1024
# 设定镜像文件系统格式
mkfs.ext4 initrd.img
# 挂在镜像到一个空文件夹
mkdir fs
sudo mount -t ext4 initrd.img fs
# 把rootfs内容拷贝到镜像文件夹fs
cp -a rootfs/* fs/.
# 搞定了,卸载镜像
sudo umount fs

参考链接:


buildroot快速构建
https://tomwithkernel.github.io/rootfs/buildroot构建/
作者
Tom
发布于
2025年6月20日
更新于
2025年6月20日
许可协议