跳到主要内容

基于网络的启动方式

什么意思?

就是将 kernel rootfs system.bit system.dtb 改为全从电脑的服务器上读取。

核心需求:

  1. 已经对重复插拔 SD 卡厌倦了,曾经烧过一个 zynq 7020(大概率是 DDR 设置成正常电压,但实际上需要设置成 low voltage,然后重复上电..)
  2. petalinux 用 jtag 启动还蛮慢的
  3. 修改 kernel/dts 之类的也还是要插拔 SD 卡

正点原子的版本最优方案是隔离了 设备树bitstream

但是最近涉及到了一些 kernel hacking ,需要频繁调整 kernel 的 config

最好的方案就是固定 fsbl & uboot,然后调整 boot.cmd 从网络上启动 kernel dtb 和 rootfs

环境

  • 全文基于 Ubuntu 22.04 物理机下进行,且以电脑物理网口为网关,一对一连接板子。

  • petalinux 2023.1

不推荐使用 wsl2, systemd 有点坑,设置了很久的 NFS server 搞不通...

同时物理机的编译效率很高(不能长时间摸鱼了)

NFS 服务器

用途:挂载 rootfs,文件夹在/nfs/rootfs

比较坑的是 rootfs 的文件夹权限问题。

安装过程略过,之前就安装了,没办法写了

和 tftp 流程差不多。

更新 rootfs 且处理权限问题脚本如下,每次 petalinux-build 后可以用于更新 rootfs

#!/bin/bash

# 项目 images/linux 目录
PROJECT_DIR=<项目路径>/images/linux

# NFS 导出目录
NFS_ROOT=/nfs/rootfs

# 新生成的 rootfs.tar.gz
TAR_FILE=$PROJECT_DIR/rootfs.tar.gz

if [ ! -f "$TAR_FILE" ]; then
echo "错误: $TAR_FILE 不存在!先运行 petalinux-build"
exit 1
fi

echo "正在清理旧 rootfs..."
sudo rm -rf $NFS_ROOT/*

echo "正在解压新 rootfs 到 $NFS_ROOT ..."
sudo tar -xzf "$TAR_FILE" -C $NFS_ROOT

echo "修复权限..."
sudo chown -R root:root $NFS_ROOT 2>/dev/null || true
sudo chmod -R 755 $NFS_ROOT

echo "重新导出 NFS..."
sudo exportfs -ra

echo "完成!板子重启即可加载新 rootfs"

tftp 服务器

安装服务器

sudo apt-get install tftpd-hpa

文件夹路径可以设置成/tftpboot,与 petalinux 默认的保持一致

设置配置目录: 编辑配置文件 sudo vim /etc/default/tftpd-hpa。通常配置如下:

  • TFTP_DIRECTORY="/tftpboot"(这是你存放文件的文件夹路径)
  • TFTP_OPTIONS="--secure --create"--create 允许上传文件)

准备文件夹并给权限

sudo mkdir /tftpboot
sudo chmod 777 /tftpboot

重启服务

sudo service tftpd-hpa restart

修改boot.cmd.default

下面的网络配置按需设置

bootargs 多了个 earlyprintk

备注

在开发驱动、移植新内核,或者遇到系统一开机就黑屏死机,加上 earlyprintk 能帮你看到那些被隐藏的报错信息。如果系统运行稳定,这个参数通常是不需要的,因为它会略微拖慢一点点启动速度。

记得在内核配置中开启 CONFIG_EARLY_PRINTK=y

# --- 网络配置参数 ---
setenv ipaddr 192.168.3.2 # 开发板 IP
setenv serverip 192.168.3.1 # 电脑 IP
setenv gatewayip 192.168.3.1 # 网关

# --- 核心:TFTP 下载 + NFS 挂载参数 ---
# root=/dev/nfs 表示从网络挂载根文件系统
# rw 表示可读写,v3,tcp 是为了更好的稳定性
setenv bootargs "console=ttyPS0,115200 earlyprintk root=/dev/nfs nfsroot=${serverip}:/nfs/rootfs,v3,tcp ip=${ipaddr}:${serverip}:${gatewayip}:255.255.255.0::eth0:off"

# --- 执行下载与启动 ---
# 1. 下载位流文件 (FPGA Bitstream)
tftpboot 0x00800000 system.bit
fpga loadb 0 0x00800000 ${filesize}

# 2. 下载内核 (uImage)
tftpboot 0x00200000 uImage

# 3. 下载设备树 (DTB)
tftpboot 0x00100000 system.dtb

# 4. 启动内核 (跳过 Ramdisk,使用 '-' 代替)
bootm 0x00200000 - 0x00100000

记得生成 boot.scr

mkimage -c none -A arm -T script -d boot.cmd.default boot.scr

之后的 BOOT.bin 可以轻量化

petalinux-package --boot --fsbl --u-boot --force

之后 SD 卡只需要有 BOOT.bin boot.scr 即可