当前位置: 首页 > news >正文

Firefly RK3399 - 从零构建Ubuntu 20.04.4根文件系统实战指南

1. 准备工作与环境搭建

第一次接触Firefly RK3399开发板时,我就被它强大的性能吸引住了。这块六核ARM开发板搭载了双Cortex-A72和四Cortex-A53处理器,性能足以运行完整的Ubuntu桌面系统。不过要从零开始构建根文件系统,确实需要做好充分准备。

首先需要准备一台运行Ubuntu的宿主机,我使用的是Ubuntu 20.04 LTS版本。建议选择这个版本,因为它与我们要构建的目标系统版本一致,可以避免很多兼容性问题。宿主机需要至少100GB的可用磁盘空间,因为编译过程中会产生大量中间文件。

在宿主机上安装必要的工具链:

sudo apt update sudo apt install -y git build-essential bc kmod cpio flex libncurses5-dev libelf-dev libssl-dev dwarves bison

特别提醒一下,如果你和我一样使用的是虚拟机作为宿主机,记得给虚拟机分配足够的内存和CPU资源。我刚开始只给了4GB内存,编译内核时频繁卡死,后来增加到8GB才顺畅。另外,建议使用SSD硬盘,机械硬盘的编译速度会让你怀疑人生。

2. 获取Ubuntu基础文件系统

Ubuntu-base是一个最小化的根文件系统,它只包含最基本的运行环境,非常适合嵌入式系统定制。我们可以从Ubuntu官方或国内镜像站下载。

我推荐使用清华大学的镜像源,速度更快:

wget https://mirrors.tuna.tsinghua.edu.cn/ubuntu-cdimage/ubuntu-base/releases/20.04/release/ubuntu-base-20.04.4-base-arm64.tar.gz

下载完成后,我们需要解压这个文件系统包。这里有个小技巧:必须使用root权限并保留文件权限:

mkdir -p rootfs/ubuntu sudo tar -xpvf ubuntu-base-20.04.4-base-arm64.tar.gz -C rootfs/ubuntu/

解压后,你会得到一个约100MB的基础系统。这个系统小得惊人,连最基本的文本编辑器都没有。但正是这种精简,让我们可以按需定制,避免不必要的软件占用宝贵的内存和存储空间。

3. 配置交叉编译环境

由于RK3399是ARM架构,我们需要配置交叉编译环境。这里我推荐使用Linaro的工具链:

wget https://releases.linaro.org/components/toolchain/binaries/7.5-2019.12/aarch64-linux-gnu/gcc-linaro-7.5.0-2019.12-x86_64_aarch64-linux-gnu.tar.xz sudo tar -xvf gcc-linaro-7.5.0-2019.12-x86_64_aarch64-linux-gnu.tar.xz -C /opt/

设置环境变量,方便后续使用:

export PATH=/opt/gcc-linaro-7.5.0-2019.12-x86_64_aarch64-linux-gnu/bin:$PATH export CROSS_COMPILE=aarch64-linux-gnu- export ARCH=arm64

验证工具链是否安装成功:

aarch64-linux-gnu-gcc --version

如果看到版本信息输出,说明工具链已经准备就绪。这一步很关键,后续的内核编译和驱动编译都依赖这个工具链。

4. 安装QEMU模拟器

由于我们的宿主机是x86架构,而目标系统是ARM架构,我们需要QEMU来进行模拟运行:

sudo apt install -y qemu-user-static

安装完成后,将QEMU的ARM64模拟器复制到目标文件系统中:

sudo cp /usr/bin/qemu-aarch64-static rootfs/ubuntu/usr/bin/

这个小技巧非常实用,它允许我们在x86主机上直接chroot到ARM文件系统进行配置和安装软件。我第一次尝试时跳过了这一步,结果chroot后所有命令都无法执行,浪费了不少时间排查问题。

5. 配置软件源和网络

为了让目标系统能够安装软件,我们需要配置合适的软件源。国内用户建议使用华为或清华的镜像源:

sudo vim rootfs/ubuntu/etc/apt/sources.list

替换为以下内容:

deb http://mirrors.huaweicloud.com/ubuntu-ports/ focal main multiverse restricted universe deb http://mirrors.huaweicloud.com/ubuntu-ports/ focal-security main multiverse restricted universe deb http://mirrors.huaweicloud.com/ubuntu-ports/ focal-updates main multiverse restricted universe

配置DNS,确保网络连接正常:

sudo cp /etc/resolv.conf rootfs/ubuntu/etc/resolv.conf

在实际操作中,我发现有时候resolv.conf会被覆盖,所以更稳妥的做法是在文件系统中固定DNS配置:

sudo vim rootfs/ubuntu/etc/systemd/resolved.conf

添加:

[Resolve] DNS=8.8.8.8 114.114.114.114

6. 挂载和进入目标系统

现在我们可以挂载目标文件系统并进行配置了。创建一个挂载脚本mnt_ubuntu.sh:

#!/bin/bash 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} } 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 trailing '/')" echo "" echo "For example: ch-mount -m /media/sdcard/" echo "" echo 1st parameter : ${1} echo 2nd parameter : ${2} fi

给脚本执行权限并挂载:

sudo chmod +x mnt_ubuntu.sh ./mnt_ubuntu.sh -m rootfs/ubuntu/

成功执行后,你会发现命令行提示符变了,这时你已经进入了目标系统的环境。这个步骤看似简单,但却是整个过程中最关键的一环,后续的所有配置都在这个环境中进行。

7. 安装基础软件和桌面环境

在目标系统环境中,首先更新软件包列表:

apt update

安装一些基础工具:

apt install -y net-tools ethtool ifupdown psmisc nfs-common htop vim rsyslog iputils-ping language-pack-en-base sudo network-manager systemd openssh-sftp-server

接下来安装桌面环境。RK3399性能不错,可以运行完整的Ubuntu桌面:

apt install -y ubuntu-desktop

这个安装过程会比较长,大约需要下载1GB的数据。我在第一次安装时因为网络不稳定失败了,后来发现可以用apt的缓存机制:

apt -o Acquire::http::Timeout=30 -o Acquire::https::Timeout=30 -o Acquire::ftp::Timeout=30 install -y ubuntu-desktop

安装完成后,建议安装一些常用的多媒体支持:

add-apt-repository multiverse apt install -y ubuntu-restricted-extras

8. 系统配置和优化

设置root密码:

passwd root

配置SSH允许root登录:

vim /etc/ssh/sshd_config

找到PermitRootLogin并修改为:

PermitRootLogin yes

设置主机名和网络:

echo "rk3399" > /etc/hostname echo "127.0.0.1 localhost" >> /etc/hosts echo "127.0.0.1 rk3399" >> /etc/hosts

配置有线网络使用DHCP:

echo auto eth0 > /etc/network/interfaces.d/eth0 echo iface eth0 inet dhcp >> /etc/network/interfaces.d/eth0

优化系统启动速度:

vim /lib/systemd/system/networking.service

将TimeoutStartSec=5min改为:

TimeoutStartSec=1sec

配置开机自动登录图形界面:

vim /etc/gdm3/custom.conf

添加:

[daemon] AutomaticLoginEnable=true AutomaticLogin=root

9. 安装内核头文件和驱动模块

退出chroot环境,回到宿主机:

exit

编译内核头文件:

cd linux-5.2.8 make -j$(nproc) bindeb-pkg

将生成的头文件包复制到目标系统:

sudo cp linux-headers-5.2.8_5.2.8-1_arm64.deb rootfs/ubuntu/opt/

重新进入chroot环境安装头文件:

./mnt_ubuntu.sh -m rootfs/ubuntu/ cd /opt dpkg -i linux-headers-*.deb

编译内核模块:

export KMODULES_OUTDIR=`pwd`/out/output_rk3399_kmodules make modules -j$(nproc) make INSTALL_MOD_PATH=${KMODULES_OUTDIR} modules_install

将编译好的驱动模块复制到目标系统:

cp -af ${KMODULES_OUTDIR}/lib/modules/* rootfs/ubuntu/lib/modules/

10. 制作根文件系统镜像

退出chroot环境,开始制作镜像:

exit mkdir ubuntu_rootfs dd if=/dev/zero of=ubuntu_ext4_rootfs.img bs=1M count=6144 mkfs.ext4 ubuntu_ext4_rootfs.img

挂载镜像并复制文件:

mount ubuntu_ext4_rootfs.img ubuntu_rootfs/ cp rootfs/ubuntu/* ubuntu_rootfs/ -af umount ubuntu_rootfs

优化镜像大小:

e2fsck -p -f ubuntu_ext4_rootfs.img resize2fs -M ubuntu_ext4_rootfs.img

最终得到的镜像文件就可以烧录到开发板了。整个过程虽然步骤繁多,但只要按部就班操作,就能成功构建一个完整的Ubuntu根文件系统。

http://www.cnnetsun.cn/news/2084193.html

相关文章:

  • Meshroom终极指南:免费开源3D重建软件从零到精通
  • Spire.Office for .NET 8实战:从许可证困惑到成功激活,我的踩坑与避坑记录
  • 番茄小说下载器终极指南:一站式小说资源管理与格式转换工具
  • NumPy高效科学计算全解析
  • Spotify音乐下载器:3步打造永久个人音乐库
  • GetQzonehistory:一键备份QQ空间历史说说的免费开源工具
  • 别再扔了!手把手教你用美工刀和砂纸复活严重氧化的烙铁头(附日常保养技巧)
  • 3分钟终极指南:DBeaver驱动一键配置,彻底告别网络下载烦恼
  • Mac百度网盘下载加速终极指南:告别龟速下载的完整解决方案
  • 像素艺术视觉特效的终极节点化解决方案:Pixel-Composer完全指南
  • 3种创新方案解决Unity游戏马赛克去除难题:深度技术解析与实战指南
  • 2026年Hermes/OpenClaw Agent怎么部署?手把手教你部署及token Plan配置流程
  • 【新手必备】2026年OpenClaw/Hermes Agent京东云零基础快速集成新手指南
  • 如何高效解决视觉小说语言障碍?LunaTranslator智能翻译方案全解析
  • Pentaho Kettle:3大核心功能让数据集成变得像搭积木一样简单
  • 如何快速构建高可用QQ签名API服务:5步终极指南
  • 深度强化学习实战:基于DQN与经验回放的《超级马里奥世界》AI训练指南
  • 别再死记硬背了!用TensorFlow 1.x的变量与占位符,手把手带你理解计算图的运作逻辑
  • 安卓虚拟摄像头终极指南:如何用VCAM轻松替换摄像头画面
  • 从时域到频域:深入解析Jitter与相位噪声的关联与测量
  • GoWxDump:如何在5分钟内完成微信取证分析的终极指南
  • 别再死记硬背了!用这3个实战项目理解SGD、Adam和梯度消失(附代码)
  • 1553B总线芯片BU64843的存储空间与访问模式深度解析
  • 朋友家信号差,我用手机和Python脚本‘借’了个网:记一次小米路由器4A千兆版的WIFI渗透与提权实战
  • Figma设计稿AI智能体集成:基于MCP协议实现设计与开发自动化
  • 别再问OA运维难不难了!从B/S到C/S,我用一台Windows Server和SQL Server带你走通全流程
  • 如何3分钟免费解密网易云音乐NCM文件:ncmdump完整使用指南
  • DC-DC反馈电阻取值:效率、精度与稳定性的权衡艺术
  • 终极LRC歌词制作指南:如何用免费开源工具轻松制作专业歌词
  • 5分钟彻底解决Minecraft模组语言障碍:MASA全家桶汉化包完全指南