Uboot从flash加载自定义应用镜像并通过bootm启动的方案咨询
U-Boot 从Flash启动预设镜像操作方案
以下操作默认基于SPI Flash存储介质,若使用NAND Flash、eMMC等介质,仅需替换对应存储读写命令即可,地址参数需根据你的硬件实际配置修改。
一、手动单步启动指定镜像操作
假设你两个镜像在Flash中的偏移分别为0x100000(镜像1)、0x600000(镜像2),内存加载目标地址为0x80008000,镜像最大大小为4MB(0x400000),操作步骤如下:
- 第一步:初始化存储介质,确认Flash识别正常
sf probe - 第二步:将指定Flash分区的镜像读取到内存
启动镜像1的读命令:
启动镜像2的读命令:sf read 0x80008000 0x100000 0x400000
命令参数说明:第一个参数为内存目标地址,第二个为Flash起始偏移,第三个为读取数据长度,长度可略大于实际镜像大小。sf read 0x80008000 0x600000 0x400000 - 第三步:启动加载完成的镜像
若你存储的是uImage格式镜像,使用bootm启动:
若你存储的是zImage+独立DTB的格式,需先将对应DTB读到内存另一地址(例bootm 0x800080000x83000000),再用bootz启动:bootz 0x80008000 - 0x83000000
二、带条件判断的自动启动脚本实现
如果你需要开机时根据自定义条件自动选择加载镜像,可以将判断逻辑写入U-Boot环境变量的bootcmd中,以下是两个常见判断场景的示例:
场景1:根据GPIO电平选择启动镜像
假设需要根据GPIO3第5引脚的电平选择镜像,高电平启动镜像1,低电平启动镜像2,执行以下命令写入环境变量:
setenv boot_select ' gpio input 3 5 if test $? -eq 1; then echo "Loading image 1 from flash..." sf read 0x80008000 0x100000 0x400000 # 若为独立DTB,此处加对应DTB读入命令:sf read 0x83000000 0x500000 0x10000 else echo "Loading image 2 from flash..." sf read 0x80008000 0x600000 0x400000 # 若为独立DTB,此处加对应DTB读入命令:sf read 0x83000000 0xA00000 0x10000 fi bootm 0x80008000 ' setenv bootcmd 'run boot_select' saveenv
配置完成后下次开机就会自动读取GPIO电平选择对应镜像启动。
场景2:根据Flash存储的标志位选择启动镜像
假设标志位存在Flash偏移0xF0000位置,标志位值为0x12345678时启动镜像1,否则启动镜像2,示例脚本如下:
setenv boot_select ' # 读取4字节标志位到内存0x80000000位置 sf read 0x80000000 0xF0000 0x4 # 读取内存值存入变量 mw.l 0x80000004 0x12345678 if cmp.l 0x80000000 0x80000004 1; then echo "Loading image 1 from flash..." sf read 0x80008000 0x100000 0x400000 else echo "Loading image 2 from flash..." sf read 0x80008000 0x600000 0x400000 fi bootm 0x80008000 ' setenv bootcmd 'run boot_select' saveenv
三、注意事项
- 不同存储介质的读写命令不同:SPI Flash用
sf命令,NAND Flash用nand read,eMMC用mmc read,操作前必须确认存储介质已正常识别。 - 选择的内存加载地址不能和U-Boot本身的运行地址、栈地址重叠,否则镜像会被覆盖导致启动失败。
- 对可靠性要求高的场景可以在读入镜像后增加
crc32校验步骤,和预设的镜像校验值对比,确认读取正常后再启动。
内容的提问来源于stack exchange,提问作者rkohli2000 gmail
相关产品推荐
相关产品推荐

