根文件系统是Linux内核启动时挂载的第一个文件系统,系统引导程序会从中加载初始化脚本和服务到内存中运行。内核与文件系统是两个完全独立的部分。
Debian目录结构
参考RK官方的Debian源码目录,其主要结构如下:
| 目录 |
作用 |
overlay |
适配Rockchip平台的共性配置文件 |
overlay-debug |
系统常用的调试工具 |
overlay-firmware |
设备固件存放,如npu、dp等 |
packages |
包含armhf、arm64系统适配硬加速使用的预编译包 |
packages-patches |
基于官方包打上的补丁 |
ubuntu-build-service |
从官方获取Debian发行版、依赖包和定制安装包 |
mk-base-debian.sh |
获取Debian基础包并进行编译 |
mk-image.sh |
打包生成ext4格式的固件 |
mk-rootfs-buster/bullseye.sh |
适配Rockchip相关硬件加速包 |
mk-rootfs.sh |
指向具体的Rootfs版本(如Buster、Bullseye) |
readme.md |
文档指引 |
构建文件系统流程
分析开源项目(如 https://github.com/LubanCat/ubuntu22.04)可知,其构建流程通常包括以下步骤:
- 下载对应的Ubuntu base文件
- 拷贝DNS配置文件
- 下载aarch64架构的ubuntu-base,并拷贝
qemu-aarch64-static 到 ubuntu/usr/bin
- 替换为国内镜像源以加速
- 进入ubuntu的根文件系统环境
- 执行基础的
update 和 upgrade
- 根据需求(桌面版或精简版)安装桌面组件及相关软件
- 安装网络、Python等常用工具
- 下载并设置语言包
- 安装Python的pip库
- 创建用户(如用户
cat,密码cat)
- 配置串口root登录,设置主机名
- 设置localtime时区
- 修改系统服务的超时等待时间
- 禁用无线相关服务(如
wpa_supplicant, nl80211)
- 减少
systemd的日志输出
- 配置sudo组用户无需密码验证
添加预装软件包
若想在制作根文件系统时预装软件(如git和vim),可以在构建脚本(如mk-lite/desktop-rootfs.sh)中添加相应命令。在定义了安装变量 export APT_INSTALL="apt-get install -fy --allow-downgrades" 之后,添加如下内容:
echo -e "\033[47;36m ---------- LubanCat -------- \033[0m"
${APT_INSTALL} git vim
添加外设固件
如需支持无线网卡等外设,需要将对应的固件文件添加到根文件系统中。通常将固件存放在overlay-firmware目录下,并按照固件在根文件系统中的实际路径进行保存即可。
添加服务项及配置文件
如果想对系统服务配置进行自定义,可以在overlay/目录下添加或覆盖配置文件。在制作根文件系统时,这些文件会被整合进去。
例如,要自定义网络配置工具netplan,可以在overlay/etc/netplan/目录下新建文件01-network-manager-all.yaml,并添加如下内容:
network:
renderer: NetworkManager
ethernets:
eth0:
dhcp4: true
eth1:
dhcp4: true
此配置将网络渲染器设为NetworkManager,并为eth0和eth1网卡开启DHCP。添加配置文件后重新构建并烧录系统,即可生效。
添加RK overlay层并打包镜像
最后,在构建脚本中选择对应的CPU型号和所需的根文件系统版本,将RK平台的适配层(overlay)加入,并打包生成最终的ubuntu-rootfs镜像。
分区空间配置
parameter.txt配置
分区信息在parameter.txt中定义,格式为size@sector(partition_name),单位是扇区(Sector, 512字节)。例如:
0x00002000 = 8192 扇区 = 4MB
0x00008000 = 32768 扇区 = 16MB
0x0000C000 = 49152 扇区 = 24MB
0x00c00000 = 12582912 扇区 ≈ 6GB
一个典型的分区配置如下:
CMDLINE: mtdparts=:
0x00002000@0x00004000(uboot), address : 0x00004000 size : 4M
0x00002000@0x00006000(misc), address : 0x00006000 size : 4M
0x00020000@0x00008000(boot), address : 0x00008000 size : 64M
0x00040000@0x00028000(recovery), address : 0x00028000 size : 128M
0x00010000@0x00068000(backup), address : 0x00068000 size : 32M
0x00c00000@0x00078000(rootfs), address : 0x00078000 size : 6G
0x00040000@0x00c78000(oem), address : 0x00c78000 size : 128M
-@0x00cb8000(userdata:grow) address : 0x00cb8000 size : 用户数据余下空间

图:RK平台的典型分区布局
对系统分区进行扩容
如果觉得默认的rootfs分区(如6GB)不够用,可以修改parameter.txt进行扩容。例如,需要扩容到55GB:
- 计算所需扇区数:55 GB × 1024 × 1024 × 1024 ÷ 512 = 115343360 扇区
- 转换为十六进制:115343360 (十进制) = 0x6E00000 (十六进制)
然后将配置中rootfs行修改为:
0x06E00000@0x00078000(rootfs), address : 0x00078000 size : 55G
其他分区(如oem, userdata)的起始地址也需要相应顺延计算。

图:分区扩容前后使用df -h命令查看的空间对比
手动打包文件系统教程
下载并解压Ubuntu Base镜像
从Ubuntu官网下载Base镜像(如20.04.5 LTS),并解压到指定目录。
# 创建一个文件夹存放根文件系统
mkdir ubuntu_rootfs
# 解压到当前文件夹
tar -xzvf ubuntu-base-20.04.5-base-arm64.tar.gz -C ./ubuntu_rootfs/
配置根文件系统基础环境
配置网络DNS和镜像源:
# 拷贝本机的DNS配置(注意版本兼容性)
cp /etc/resolv.conf ubuntu_rootfs/etc/resolv.conf
# 更换为国内镜像源(如阿里云)
sudo vim ubuntu_rootfs/etc/apt/sources.list
Ubuntu 20.04 (Focal) 镜像源示例:
deb http://mirrors.aliyun.com/ubuntu-ports/ focal main restricted universe multiverse
deb http://mirrors.aliyun.com/ubuntu-ports/ focal-updates main restricted universe multiverse
deb http://mirrors.aliyun.com/ubuntu-ports/ focal-backports main restricted universe multiverse
deb http://mirrors.aliyun.com/ubuntu-ports/ focal-security main restricted universe multiverse
对于Ubuntu 22.04,可使用自动化脚本更换源:wget http://fishros.com/install -O fishros && . fishros。
配置ARM仿真环境:
为了使宿主机能够运行ARM架构的程序,需要安装并配置qemu-user-static。
# 1. 安装qemu-user-static仿真器
sudo apt install qemu-user-static
# 2. 拷贝qemu-aarch64-static到根文件系统内
sudo cp /usr/bin/qemu-aarch64-static ./ubuntu_rootfs/usr/bin/
挂载文件系统并安装软件
使用一个挂载脚本方便地chroot进入根文件系统环境进行配置。
挂载脚本 mount.sh:
#!/bin/bash
function mnt() {
echo "MOUNTING"
sudo mount -t proc /proc ${2}proc
sudo mount -t sysfs /sys ${2}sys
sudo mount -o bind /dev ${2}dev
sudo mount -o bind /dev/pts ${2}dev/pts
sudo chroot ${2}
}
function umnt() {
echo "UNMOUNTING"
sudo umount ${2}proc
sudo umount ${2}sys
sudo umount ${2}dev/pts
sudo umount ${2}dev
}
if [ "$1" == "-m" ] && [ -n "$2" ];
then
mnt $1 $2
elif [ "$1" == "-u" ] && [ -n "$2" ];
then
umnt $1 $2
else
echo ""
echo "Either 1'st, 2'nd or both parameters were missing"
echo ""
echo "1'st parameter can be one of these: -m(mount) OR -u(umount)"
echo "2'nd parameter is the full path of rootfs directory(with tralling '/')"
echo ""
echo "For example: ch-mount -m /media/sdcard"
echo ""
echo 1st parameter : ${1}
echo 2nd parameter : $[2]
fi
使用脚本挂载并进入根文件系统:
# 增加脚本执行权限
sudo chmod +x mount.sh
# 挂载根文件系统(将进入chroot环境)
./mount.sh -m ubuntu_rootfs/
进入chroot环境后,可以执行以下命令验证和配置系统。
# 查看当前Ubuntu版本信息
cat /etc/lsb-release

图:在chroot环境中查看系统版本信息
安装必要软件和配置系统:
# 更新软件列表并升级
apt update
apt upgrade
# 安装基础工具集
apt install vim bash-completion net-tools iputils-ping ifupdown ethtool ssh rsync udev htop rsyslog nfs-common language-pack-en-base sudo psmisc
# 安装adb工具(如需)
apt-get install android-tools-adb
# 配置系统时区和语言
apt install locales tzdata
# 选择时区,例如 Asia/Shanghai
dpkg-reconfigure tzdata
# 配置语言环境,勾选 en_US.UTF-8 和 zh_CN.UTF-8
dpkg-reconfigure locales
# 安装桌面环境(可选,根据需求)
# 安装完整Ubuntu桌面
apt install ubuntu-desktop
# 或安装更轻量的XFCE桌面
apt install xfce4 xfce4-goodies
# 设置主机名
echo "ubuntu" > /etc/hostname
# 设置主机解析
echo "127.0.0.1 localhost" >> /etc/hosts
echo "127.0.0.1 ubuntu" >> /etc/hosts
优化系统服务配置:
- 修改网络服务超时,加快启动速度:
vim /lib/systemd/system/networking.service
# 将 TimeoutStartSec=5min 修改为 TimeoutStartSec=5sec

图:修改systemd网络服务的启动超时参数
- 配置串口自动以root登录:
sed -i '/^ExecStart=/c\ExecStart=-/sbin/agetty --autologin root --noclear %I $TERM' /lib/systemd/system/serial-getty@.service

图:修改串口getty服务的systemd配置
- 禁用系统休眠:
systemctl mask sleep.target suspend.target hibernate.target hybrid-sleep.target
- 配置DHCP网络(传统ifupdown方式):
vim /etc/network/interfaces
# 添加以下内容
auto eth0
iface eth0 inet dhcp
auto eth1
iface eth1 inet dhcp
- 修改系统默认重启等待时间:
vim /etc/systemd/system.conf
# 取消以下行的注释并调整时间
# DefaultTimeoutStartSec=90s
# DefaultTimeoutStopSec=90s
集成RK平台特定依赖
需要将RK SDK中external目录下适配的驱动、固件和配置文件(如overlay目录内容)复制到正在构建的根文件系统对应位置。
关于图形显示:
RK平台的GPU驱动与Ubuntu GNOME桌面可能存在兼容性问题,可能导致窗口阴影异常或Chrome浏览器视频卡顿。如果遇到此类问题,可考虑使用XFCE等轻量桌面。在Chrome地址栏输入 chrome://gpu 可查看GPU加速状态。
ADB调试配置:
若需开启ADB,可参考以下步骤:
- 在构建文件系统时启用
debug选项,确保安装ADB相关包。
- 修改脚本文件
overlay/etc/init.d/rockchip.sh 中引用的配置,将 overlay/etc/init.d/.usb_config 文件内容设置为 usb_adb_en。
if [ $(cat /etc/init.d/.usb_config) != "usb_adb_en" ]; then
#usb configfs reset
echo run /usr/bin/usbdevice restart
/usr/bin/usbdevice restart
fi

图:修改.usb_config文件以启用ADB功能
自动登录设置:
修改 overlay/etc/gdm3/custom.conf 或对应显示管理器的配置文件,设置自动登录的用户名。
处理启动报错:
若启动时出现 rkaip_3A_server assert failure 错误,这是RK的摄像头ISP服务报错。如果不使用摄像头,可以尝试关闭或卸载相关服务。
完成制作并打包
配置完成后,退出chroot环境并卸载目录。
# 退出chroot环境
exit
# 卸载根文件系统
./mount.sh -u ubuntu_rootfs/
打包为EXT4镜像文件:
# 1. 创建一个空的镜像文件,大小根据实际需要(无桌面2-4G,有桌面6G以上)
dd if=/dev/zero of=ubuntu_rootfs.img bs=1M count=6144 # 例如创建6G镜像
# 2. 格式化为ext4文件系统
mkfs.ext4 ubuntu_rootfs.img
# 3. 挂载此空镜像,并将准备好的根文件系统内容复制进去
mkdir ubuntu_base_rootfs
chmod 777 ubuntu_base_rootfs
mount ubuntu_rootfs.img ubuntu_base_rootfs
cp -rfp ubuntu_rootfs/* ubuntu_base_rootfs/
# 4. 卸载、检查并压缩镜像体积
umount ubuntu_base_rootfs/
e2fsck -p -f ubuntu_rootfs.img
resize2fs -M ubuntu_rootfs.img
烧录到开发板
使用瑞芯微提供的烧录工具(如RKDevTool)将打包好的ubuntu_rootfs.img烧录到开发板的对应分区(通常是rootfs分区)。

图:使用RKDevTool加载并烧录rootfs镜像文件
首次启动与分区扩容
镜像烧录后,其rootfs分区可能只占用了参数文件中定义大小的一部分。首次启动后,需要使用 resize2fs 命令将该分区扩展到参数定义的完整大小。
# 假设rootfs对应设备节点为 /dev/mmcblk0p6
resize2fs /dev/mmcblk0p6

图:使用resize2fs命令将rootfs分区扩展到完整大小
如果烧录后文件系统未自动扩展,可能需要将resize2fs命令添加到启动脚本中自动执行。
常见问题与解决
通过以上步骤,你可以完成一个为RK平台定制的Ubuntu根文件系统。如果在网络配置或操作系统底层服务方面有更深入的需求,可以参考 云栈社区 网络与系统板块的讨论。关于内核与计算机系统基础原理的探讨,也可以在 云栈社区 的计算机基础板块找到更多资源。
更多嵌入式开发技巧和资源,欢迎访问 云栈社区 进行交流分享。