Bootloader -- U-Boot 介绍

Bootloader -- U-Boot 介绍

  • 1 介绍
    • 1.1 概述
    • 1.2 知名 Bootloader
      • LILO (Linux Loader)
      • GRUB (GNU GRand Unified Bootloader)
      • Loadlin
      • ROLO (Rockbox Loader)
      • Etherboot
      • LinuxBIOS (现在叫 coreboot)
      • BLOB
      • U-Boot
      • RedBoot
    • 1.3 BootLoader 和 Monitor 区别
    • 1.4 U-Boot 的源码结构
    • 1.5 U-Boot 的主要版本
    • 1.6 U-Boot 的作用和功能
  • 2 U-Boot 命令与启动
    • 启动
    • 命令
      • 全部命令
      • 常用命令
      • mmc 命令
      • 文件系统类型操作命令
      • FAT 格式文件系统操作
      • ext4 格式文件系统操作
    • uboot 启动内核过程
      • 嵌入式之家画的流程图
    • uboot 环境参数介绍
  • 3 U-Boot 编译
    • 3.1 系统
    • 3.2 安装依赖和编译工具
    • 3.3 获取 U-Boot
    • 3.4 uboot 工程结构 & 变量 & 子功能
      • 3.4.1 uboot 工程结构
      • 3.4.2 uboot 变量
      • 3.4.3 uboot 子功能
    • 3.5 uboot 编译
      • 来自 lzd626 的图解
      • 赵建辉理解的 u-boot.imx 目标依赖关系图
      • 野火 ebf_v2020_10_imx 分支
    • 3.6 编译产物分析
  • 4 U-Boot 烧录
    • 4.1 Mfgtool 烧写 Uboot 到内部存储(EMMC/NAND 通用)
      • 介绍
      • 烧录步骤分析
    • 4.2 Uboot 烧写到 SD 卡镜像(常用于做 uboot 测试)
  • 5 U-Boot 移植
  • 6 U-Boot 控制 GPIO & 定制自己的 Uboot 单板
    • 6.1 U-Boot 控制 GPIO
    • 6.2 U-Boot 定制自己的 Uboot 单板
  • 7 电脑 与 嵌入式设备 系统启动区别
  • 知识点
    • 1 BIOS、UEFI、MBR、GPT、GRUB 区别联系
      • 基本输入输出系统【BIOS、UEFI】
      • 硬盘分区初始化格式【MBR、GPT】
      • bootloader【GRUB】
        • 如下图所示为GRUB加载引导流程
  • 参考

1 介绍

1.1 概述

Bootloader,引导加载程序,是一种负责启动计算机的计算机程序。

U-Boot是Das U-Boot的简写,是一种开源引导加载程序,用于嵌入式设备执行各种低级硬件初始化任务并引导设备的操作系统内核。它适用于多种计算机架构,包括M68000、ARM、Blackfin、MicroBlaze、IBM S360、My66、MOS 6502、ARM64、MIPS、Nios、SuperH、PPC、RISC-V和x86。

U-Boot 一开始是由一个德国大神Magnus Damm(马格努斯 达姆)发起的一个项目。

U-Boot 既是第一阶段的引导加载程序,也是第二阶段的引导加载程序。它由系统的 ROM(例如 ARM CPU 的片上 ROM)从受支持的启动设备(例如 SD 卡、SATA 驱动器、NOR 闪存(例如使用SPI或I²C)或 NAND 闪存)加载。如果有大小限制,U-Boot 可能会分为两个阶段:平台将加载一个小型 SPL(辅助程序加载器),它是 U-Boot 的精简版,SPL 将执行一些初始硬件配置(例如使用 CPU 缓存作为 RAM 进行DRAM初始化)并加载更大、功能齐全的 U-Boot 版本。无论是否使用 SPL,U-Boot 都会执行第一阶段(例如配置内存控制器和 SDRAM)和第二阶段引导(执行多个步骤从必须配置的各种设备加载现代操作系统、显示菜单供用户交互和控制引导过程等)。

U-Boot 的主要作用是用来启动操作系统内核,它分为两个阶段,即 boot + loader,boot 阶段启动系统,初始化硬件设备,建立内存空间映射图,将系统的软硬件带到一个合适的状态,loader 阶段将操作系统内核文件加载至内存,之后跳转到内核所在地址运行。

U-Boot 有众多命令,如信息查询,环境变量操作,内存操作,网络操作,mmc操作,文件系统操作,nand操作,boot操作,reset, go(到指定地址执行程序),run(运行环境变量中的命令),metest(内存测试)。

1.2 知名 Bootloader

Bootloader,引导加载程序,是一种负责启动计算机的计算机程序。
在这里插入图片描述

LILO (Linux Loader)

一度很火,2009年起被 GRUB 替代,2015年停止进一步开发;

GRUB (GNU GRand Unified Bootloader)

GRUB 是最为常见的Linux Bootloader之一。它支持多种操作系统,包括Linux、Windows、Mac OS 等。GRUB具有强大的功能和灵活的配置选项,因此被广泛使用。GRUB可以通过配置文件进行定制,例如添加启动项、设置启动顺序等。

GRUB 最初是为 GNU Hurd 操作系统设计的,目的是提供一个统一的引导程序,以替代当时众多不兼容的PC启动方式。

发展历程:

  • 1995年:GRUB由Erich Boleyn开发,最初是为了启动GNU Hurd操作系统。
  • 2002年:Yoshinori K. Okuji开始开发GRUB 2,旨在重写GRUB的核心,使其更加模块化、安全和强大。
  • 2005年:GRUB Legacy 的最后一个版本0.97发布,之后的开发重点转移到 GRUB 2上。
  • 2007年:一些GNU/Linux发行版开始使用GRUB 2,到2009年底,多个主要发行版默认安装GRUB 2。

Loadlin

运行在 16 位的实模式DOS (包括Windows 95、Windows 98和Windows Me启动盘的 MS-DOS 模式)下的Linux 启动加载程序。它允许 Linux 系统加载和替换正在运行的 DOS,而无需更改现有的 DOS 系统文件。

ROLO (Rockbox Loader)

Rockbox 是一种免费的数字音乐播放器替代固件。它可以在多种播放器上运行。适用于 Archos Jukebox 5000、6000、Studio、Recorder、Recorder V2 和 FM Recorder MP3 播放器。

Etherboot

Etherboot 是一个免费软件包,用于制作引导 ROM,以便使用 Internet 协议(即 bootp/DHCP 和 tftp)通过网络在 x86 PC 上引导 GNU/Linux 和其他操作系统。Etherboot 通常用于无盘引导 PC,这对于集群、路由器、远程服务器和在磁盘不友好的环境中工作的机器特别有用。

LinuxBIOS (现在叫 coreboot)

coreboot,以前称为LinuxBIOS,是一个软件项目,旨在用轻量级固件取代大多数计算机中的专有固件(BIOS或UEFI),轻量级固件旨在仅执行加载和运行现代32 位或64 位 操作系统所需的最少任务。

由于 coreboot 会初始化裸硬件,因此必须将其移植到其支持的每个芯片组和主板上。因此,coreboot 仅适用于有限数量的硬件平台和主板型号。

BLOB

Blob是一个为基于StrongARM平台设计的简单引导加载程序,由Jan-Derk Bakker和Erik Mouw编写,并采用GPL许可证。

Blob的最后版本是blob-2.0.5。

U-Boot

U-Boot是Das U-Boot的简写,是一种开源引导加载程序,用于嵌入式设备执行各种低级硬件初始化任务并引导设备的操作系统内核。它适用于多种计算机架构,包括M68000、ARM、Blackfin、MicroBlaze、IBM S360、My66、MOS 6502、ARM64、MIPS、Nios、SuperH、PPC、RISC-V和x86。

U-Boot 一开始是由一个德国大神Magnus Damm(马格努斯 达姆)发起的一个项目。

RedBoot

RedBoot(Red Hat 嵌入式调试和引导固件的缩写)是一个开源应用程序,它使用eCos实时操作系统硬件抽象层为嵌入式系统提供引导固件。

1.3 BootLoader 和 Monitor 区别

BootLoader,严格来说只是引导设备并且执行主程序的固件;
Monitor,提供了更多的命令行接口,可以进行调试、读写内存、烧写Flash、配置环境变量等。

Monitor在嵌入式系统开发过程中可以提供很好的调试功能,开发完成以后,就完全设置成了一个BootLoader。所以,习惯上大家把它们统称为BootLoader。

1.4 U-Boot 的源码结构

子目录描述
board开发板相关
common通用的函数
cpucpu相关,对应不同的架构的cpu,子目录进一步细分了
disk磁盘驱动和相关的操作代码
doc开发文档,还有使用文档
lib_generic通用库函数
lib_xxxxxx架构下的通用文件,支持平台设备树的库,基于open firmware结构,一般不会用到
libfdt支持平台设备树的库,基于open firmware结构,一般不会用到
driver各类设备的驱动,根据平台配置会编译不同的驱动
fs文件系统
include头文件和开发板的配置文件
net网络子系统
nand_spl支持从nand flash启动,但支持的cpu的种类也不是很多
onenand_ipl支持从onenand flash启动的代码,三星公司开发的结合了nand和nor技术的flash
post上电自检程序
tools制作S-Record(motorola 制定的一种烧写格式,很简单), u-boot镜像等的工具
example一些可以在u-boot上运行的小示例程序
api些扩展应用的独立的api
api_exampleapi的示例程序

1.5 U-Boot 的主要版本

类别描述
uboot 官方的uboot 代码由uboot 官方维护开发的uboot 版本,版本更新快,基本包含所有常用的芯片。
半导体厂商的uboot代码半导体厂商维护的一个uboot,专门针对自家的芯片,在对自家芯片支持上要比uboot官方的好。
开发板厂商的 uboot 代码开发板厂商在半导体厂商提供的uboot基础上加入了对自家开发板的支持。

1.6 U-Boot 的作用和功能

在这里插入图片描述

2 U-Boot 命令与启动

启动

在开发板上电 uboot 启动 kernel 之前按下键盘的空格或回车键, 进入 uboot 的命令模式。如下所示:

可以看出 uboot 打印出了板子的一些基本信息,包括 CPU、内存等信息。

uboot 2020.10-g4f79a1a2 (Feb 20 2021 - 11:25:18 +0800)

CPU: Freescale i.MX6ULL rev1.1 792 MHz (running at 396 MHz)
CPU: Industrial temperature grade (-40C to 105C) at 49C
Reset cause: WDOG
Model: Freescale i.MX6 UltraLiteLite 14x14 EVK Board
Board: MX6ULL 14x14 EVK
DRAM: 512 MiB
MMC: FSL_SDHC: 0, FSL_SDHC: 1
Loading Environment from MMC... OK
In: serial
Out: serial
Err: serial
Net: eth1: ethernet@20b4000 [PRIME]Could not get PHY for FEC0: addr 2

Hit any key to stop autoboot: 0
=>
U-Boot 2016.03-00001-gb0f94c6 (Apr 22 2020 - 09:29:24 +0800)

CPU:   Freescale i.MX6Q rev1.5 996 MHz (running at 792 MHz)
CPU:   Automotive temperature grade (-40C to 125C) at 24C
Reset cause: POR
Board: MX6-SabreSD
I2C:   ready
DRAM:  1 GiB
PMIC:  PFUZE100 ID=0x10
MMC:   FSL_SDHC: 0, FSL_SDHC: 1, FSL_SDHC: 2
Display: CLAA-WVGA (800x480)
reading logo.bmp
1152054 bytes read in 47 ms (23.4 MiB/s)
In:    serial
Out:   serial
Err:   serial
switch to partitions #0, OK
mmc2(part 0) is current device
Net:   FEC [PRIME]
Normal Boot
Hit any key to stop autoboot:  0
----------------------Main Menu-----------------------
0 -- exit to uboot shell
1 -- set mxcfb0 parameters
2 -- set mxcfb1 parameters
3 -- set ldb mode
4 -- select boot mode
------------------------------------------------------
0 -- exit to uboot shell
选择此选项将退出当前的菜单或配置界面,返回到U-Boot的命令行界面(shell)。
1 -- set mxcfb0 parameters
mxcfb 通常是用于i.MX系列处理器上帧缓冲管理的驱动程序。选择此选项可能允许您配置与mxcfb0(可能是第一个显示接口)相关的参数,如分辨率、颜色深度等。
2 -- set mxcfb1 parameters
类似于mxcfb0,但此选项是为mxcfb1(可能是第二个显示接口)配置参数。
3 -- set ldb mode
LDB (LVDS Display Bridge) 是一种用于连接LVDS(低电压差分信号)显示器的接口。此选项可能允许您配置与LDB相关的模式或参数。
4 -- select boot mode
选择此选项可能允许您从多种不同的启动模式中选择一个,如从SD卡、NAND闪存、网络或其他存储设备启动。

命令

全部命令

关于 uboot 命令的使用可参考 uboot 官方链接:
https://docs.u-boot.org/en/latest/ -【shell-commands】

可输入 help 或 ? 可查看 uboot 支持的命令列表:

Normal Boot
Hit any key to stop autoboot:  0
----------------------Main Menu-----------------------
0 -- exit to uboot shell
1 -- set mxcfb0 parameters
2 -- set mxcfb1 parameters
3 -- set ldb mode
4 -- select boot mode
------------------------------------------------------
:0
=> help
?       - alias for 'help'
base    - print or set address offset
bdinfo  - print Board Info structure
bmode   - sd2|sd3|emmc|normal|usb|sata|ecspi1:0|ecspi1:1|ecspi1:2|ecspi1:3|esdhc1|esdhc2|esdhc3|esdhc4 [noreset]
bmp     - manipulate BMP image data
boot    - boot default, i.e., run 'bootcmd'
bootd   - boot default, i.e., run 'bootcmd'
bootelf - Boot from an ELF image in memory
bootm   - boot application image from memory
bootp   - boot image via network using BOOTP/TFTP protocol
bootvx  - Boot vxWorks from an ELF image
bootz   - boot Linux zImage image from memory
clocks  - display clocks
clrlogo - fill the boot logo area with black
cmp     - memory compare
coninfo - print console devices and information
cp      - memory copy
cpu     - Multiprocessor CPU boot manipulation and release
crc32   - checksum calculation
dcache  - enable or disable data cache
dfu     - Device Firmware Upgrade
dhcp    - boot image via network using DHCP/TFTP protocol
dm      - Driver model low level access
echo    - echo args to console
editenv - edit environment variable
env     - environment handling commands
erase   - erase FLASH memory
exit    - exit script
ext2load- load binary file from a Ext2 filesystem
ext2ls  - list files in a directory (default /)
ext4load- load binary file from a Ext4 filesystem
ext4ls  - list files in a directory (default /)
ext4size- determine a file's size
ext4write- create a file in the root directory
false   - do nothing, unsuccessfully
fatinfo - print information about filesystem
fatload - load binary file from a dos filesystem
fatls   - list files in a directory (default /)
fatsize - determine a file's size
fdt     - flattened device tree utility commands
flinfo  - print FLASH memory information
fstype  - Look up a filesystem type
fuse    - Fuse sub-system
go      - start application at address 'addr'
gpio    - query and control gpio pins
help    - print command description/usage
i2c     - I2C sub-system
icache  - enable or disable instruction cache
iminfo  - print header information for application image
imxtract- extract a part of a multi-image
itest   - return true/false on integer compare
load    - load binary file from a filesystem
loadb   - load binary file over serial line (kermit mode)
loads   - load S-Record file over serial line
loadx   - load binary file over serial line (xmodem mode)
loady   - load binary file over serial line (ymodem mode)
loop    - infinite loop on address range
ls      - list files in a directory (default /)
md      - memory display
mdio    - MDIO utility commands
mii     - MII utility commands
mm      - memory modify (auto-incrementing address)
mmc     - MMC sub system
mmcinfo - display MMC info
mtest   - simple RAM read/write test
mw      - memory write (fill)
nfs     - boot image via network using NFS protocol
nm      - memory modify (constant address)
ping    - send ICMP ECHO_REQUEST to network host
pmic    - PMIC
printenv- print environment variables
protect - enable or disable FLASH write protection
reset   - Perform RESET of the CPU
run     - run commands in an environment variable
save    - save file to a filesystem
saveenv - save environment variables to persistent storage
scr_menu- menu - display a menu, to select the items to do something

setenv  - set environment variables
setexpr - set environment variable as the result of eval expression
sf      - SPI flash sub-system
showvar - print local hushshell variables
size    - determine a file's size
sleep   - delay execution for some time
source  - run script from memory
test    - minimal test like /bin/sh
tftpboot- boot image via network using TFTP protocol
true    - do nothing, successfully
ums     - Use the UMS [USB Mass Storage]
usb     - USB sub-system
usbboot - boot from USB device
version - print monitor, compiler and linker version
=>

可看到 uboot 支持很多的命令,功能十分强大,与 linux 类似,在执行某条 uboot 命令时,可使用 tab 自动补全命令,在没有命令名冲突的情况下可以使用命令的前几个字母作为命令的输入,例如想要执行 reset 命令,输入 res 或 re 即可。

当需要具体使用哪个命令时,可使用 “help 命令”或 “? 命令”的方式查看具体命令的使用说
明。以 “help printenv”为例,

=> help printenv
printenv - print environment variables

Usage:
printenv [-a]
    - print [all] values of all environment variables
printenv name ...
    - print value of environment variable 'name'
=>

可以看到 printenv 命令的说明以及使用方法。

常用命令

命令说明举例
help列出当前 uboot 所有支持的命令
help[命令]查看指定命令的帮助help printenv
reset重启 uboot
printenv打印所有环境参数的值
printenv[环境参数名]查看指定的环境参数值printenv bootdelay
setenv设置/修改/删除环境参数的值setenv bootdelay 3
saveenv保存环境参数
ping检测网络是否连通ping 192.168.0.1
md查看内存地址上的值md.b 0x80000000 10
mw用于修改内存地址上的值mw.b 0x80000000 ff 10
echo打印信息,与 linux下的 echo 类似
run在执行某条环境参数命令run bootcmd,执行 bootcmd
bootz在内存中引导内核启动
ls查看文件系统中目录下的文件
load从文件系统中加载二进制文件到内存

mmc 命令

mmc 命令能够对如 sd 卡以及 emmc 类的存储介质进行操作。

命令说明
mmc list查看板子上 mmc 设备
mmc dev查看/切换当前默认 mmc 设备
mmc info查看当前 mmc 设备信息
mmc part查看当前 mmc 设备分区
mmc read读取当前 mmc 设备数据
mmc write写入当前 mmc 设备数据
mmc erase擦除当前 mmc 设备数据
=> mmc list
FSL_SDHC: 0
FSL_SDHC: 1
FSL_SDHC: 2 (eMMC)

=> mmc info
Device: FSL_SDHC
Manufacturer ID: d6
OEM: 103
Name: 88A39
Tran Speed: 52000000
Rd Block Len: 512
MMC version 4.0
High Capacity: Yes
Capacity: 7.3 GiB
Bus Width: 8-bit
Erase Group Size: 512 KiB

=> mmc part

Partition Map for MMC device 2  --   Partition Type: DOS

Part    Start Sector    Num Sectors     UUID            Type
  1     20480           184320          4d6f4290-01     0c
  2     204800          5242880         4d6f4290-02     83
  3     5447680         4194304         4d6f4290-03     83
  4     9641984         5627904         4d6f4290-04     85 Extd
  5     9658368         2097152         4d6f4290-05     83
  6     11771904        2097152         4d6f4290-06     83
  7     13885440        1384448         4d6f4290-07     83

=> mmc dev
switch to partitions #0, OK
mmc2(part 0) is current device
=>

文件系统类型操作命令

uboot 能够对 ext2/3/4 以及 fat 文件系统设备进行访问,可使用 fstype 命令判断存储介质分区使用的是什么类型的文件系统。以 mmc 介质为例,判断 sd 的两个分区的文件系统类型。

=> fstype help
fstype - Look up a filesystem type

Usage:
fstype <interface> <dev>:<part>
- print filesystem type
fstype <interface> <dev>:<part> <varname>
- set environment variable to filesystem type
devpart
设备号分区号
=> mmc list
FSL_SDHC: 0
FSL_SDHC: 1
FSL_SDHC: 2 (eMMC)

=> mmc part

Partition Map for MMC device 2  --   Partition Type: DOS

Part    Start Sector    Num Sectors     UUID            Type
  1     20480           184320          4d6f4290-01     0c
  2     204800          5242880         4d6f4290-02     83
  3     5447680         4194304         4d6f4290-03     83
  4     9641984         5627904         4d6f4290-04     85 Extd
  5     9658368         2097152         4d6f4290-05     83
  6     11771904        2097152         4d6f4290-06     83
  7     13885440        1384448         4d6f4290-07     83

=> fstype help
fstype - Look up a filesystem type

Usage:
fstype <interface> <dev>:<part>
- print filesystem type
fstype <interface> <dev>:<part> <varname>
- set environment variable to filesystem type

| <dev> | <part> |
| 设备号 | 分区号 |

=> fstype mmc 2:1
fat
=> fstype mmc 2:2
ext4
=> fstype mmc 2:3
ext4
=> fstype mmc 2:4
** Invalid partition 4 **
=> fstype mmc 2:5
ext4
=> fstype mmc 2:6
ext4
=> fstype mmc 2:7
ext4
=>

FAT 格式文件系统操作

uboot 提供了能够对于 FAT 格式文件系统操作的各个指令。

命令说明
fatinfo打印关于文件系统的信息
fatls查看存储设备的 fat 分区里的内容
fatload从 fat 分区里读出文件到指定的内存地址
fatwrite把内存上的数据存储到 fat 分区的一个文件里
fatmkdir创建文件夹
fatrm删除文件
=> mmc list
FSL_SDHC: 0
FSL_SDHC: 1
FSL_SDHC: 2 (eMMC)

=> fatinfo mmc 2:1
Interface:  MMC
  Device 2: Vendor: Man 0000d6 Snr 2ff7b3a0 Rev: 1.1 Prod: 88A398
            Type: Removable Hard Disk
            Capacity: 7456.0 MB = 7.2 GB (15269888 x 512)
Filesystem: FAT16 "NO NAME    "

=> fatls mmc 2:1
  7334040   zimage
  7332312   zimage.orig
  1152054   logo.bmp
    53092   imx6q-c-sabresd.dtb
    52758   imx6q-c-sabresd.dtb.orig

5 file(s), 0 dir(s)

=>

ext4 格式文件系统操作

命令说明
ext4ls查看存储设备的 ext4 分区里的内容
ext4load从 ext4 分区里读出文件到指定的内存地址
ext4write把内存上的数据存储到 ext4 分区的一个文件里
=> mmc list
FSL_SDHC: 0
FSL_SDHC: 1
FSL_SDHC: 2 (eMMC)

=> mmc part

Partition Map for MMC device 2  --   Partition Type: DOS

Part    Start Sector    Num Sectors     UUID            Type
  1     20480           184320          4d6f4290-01     0c
  2     204800          5242880         4d6f4290-02     83
  3     5447680         4194304         4d6f4290-03     83
  4     9641984         5627904         4d6f4290-04     85 Extd
  5     9658368         2097152         4d6f4290-05     83
  6     11771904        2097152         4d6f4290-06     83
  7     13885440        1384448         4d6f4290-07     83

=> fatls mmc 2:1   【/boot/】
  7334040   zimage
  7332312   zimage.orig
  1152054   logo.bmp
    53092   imx6q-c-sabresd.dtb
    52758   imx6q-c-sabresd.dtb.orig

5 file(s), 0 dir(s)

=> ext4ls mmc 2:2   【/】
<DIR>       4096 .
<DIR>       4096 ..
<DIR>      16384 lost+found
<DIR>       4096 run
<DIR>       4096 var
<DIR>       4096 mnt
<DIR>       4096 bin
<DIR>       4096 tmp
<DIR>       4096 root
               0 .dockerenv
<DIR>       4096 sys
<DIR>       4096 sbin
<DIR>       4096 etc
<DIR>       4096 opt
<DIR>       4096 media
<DIR>       4096 srv
<DIR>       4096 home
<DIR>       4096 usr
<DIR>       4096 lib
<DIR>       4096 boot
<DIR>       4096 dev
<DIR>       4096 proc

=> ext4ls mmc 2:3   【/opt/sen/】

=> ext4ls mmc 2:2 /opt
<DIR>       4096 .
<DIR>       4096 ..
<DIR>       4096 log
<DIR>       4096 sen
<DIR>       4096 test

uboot 启动内核过程

bootcmd 与 bootargs 可以说是 uboot 最重要的两个环境参数,uboot 执行完毕之后,如果没有按下回车,则会自动执行 bootcmd 命环境参数里的内容,而 bootargs 则是传递给内核的启动参数。
使用 printenv bootcmd 可查看 bootcmd 的内容。

提示: 若从 uboot 中直接使用 printenv 查看 boot 的内容会显得格式很乱,推荐在 uboot 源码 include/configs/mx6ullfire.h 中查看。

#if defined(CONFIG_SYS_BOOT_NAND)
#define CONFIG_EXTRA_ENV_SETTINGS \
	"panel=TFT50AB\0" \
	"splashimage=0x82000000\0" \
	"fdt_addr=0x83000000\0" \
	"fdt_high=0xffffffff\0"	  \
	"console=ttymxc0\0" \
	"console=ttymxc0\0" \
	"loaduEnv=" \
		"load ramblock 0:1 ${loadaddr} /uEnv.txt;\0" \
	"importbootenv=echo Importing environment from ${devtype} ...; " \
		"env import -t ${loadaddr} ${filesize}\0" \
	"bootargs=console=ttymxc0 bootargs=console=ttymxc0,115200 ubi.mtd=1 "  \
		"root=ubi0:rootfs rw rootfstype=ubifs "		     \
		"mtdparts=gpmi-nand:8m(uboot),-(rootfs) ${cmdline} ${flashtype}\0"\
	"bootcmd=mmc check;ubi part rootfs;ubifsmount ubi0;"\
		"ubifsload ${ramblock_addr} /lib/firmware/fatboot.img;"\
		"echo loading /uEnv.txt ...; "\
		"if run loaduEnv; then " \
			"run importbootenv;" \
			"if test ${second_flash} = emmc; then " \
					"setenv dtb ${mmc_dtb};"  \
					"setenv storage_media init=/opt/scripts/tools/eMMC/init-eMMC-flasher-v3.sh;"  \
				"else " \
					"setenv dtb ${nand_dtb};"  \
					"setenv storage_media init=/opt/scripts/tools/Nand/init-Nand-flasher-v1.sh;"  \
				"fi; " \
			"if test -n ${flash_firmware}; then "  \
					"echo setting flash firmware...;"  \
					"setenv flashtype ${storage_media};"  \
			"fi;" \
			"echo loading vmlinuz-${uname_r} ...; "\
			"load ramblock 0:1 0x80800000 /kernel/vmlinuz-${uname_r};"\
			"echo loading ${dtb} ...; "\
			"ubifsload 0x83000000 /usr/lib/linux-image-${uname_r}/${dtb};"\
			"dtfile 0x83000000 0x87000000  /uEnv.txt ${loadaddr};"   \
			"load ramblock 0:1 0x88000000 /kernel/initrd.img-${uname_r};"\
			"echo debug: [${bootargs}] ... ;" \
			"echo debug: [bootz] ...  ;" \
			"bootz 0x80800000 0x88000000:${filesize} 0x83000000;"	\
		"fi;\0"
#else
#define CONFIG_EXTRA_ENV_SETTINGS \
	"script=boot.scr\0" \
	"image=zImage\0" \
	"console=ttymxc0\0" \
	"fdt_high=0xffffffff\0" \
	"initrd_high=0xffffffff\0" \
	"fdt_file=undefined\0" \
	"fdt_addr=0x83000000\0" \
	"boot_fdt=try\0" \
	"ip_dyn=yes\0" \
	"videomode=video=ctfb:x:480,y:272,depth:24,pclk:108695,le:8,ri:4,up:2,lo:4,hs:41,vs:10,sync:0,vmode:0\0" \
	"mmcdev="__stringify(CONFIG_SYS_MMC_ENV_DEV)"\0" \
	"mmcpart=" __stringify(CONFIG_SYS_MMC_IMG_LOAD_PART) "\0" \
	"mmcroot=" CONFIG_MMCROOT " rootwait rw\0" \
	"mmcautodetect=yes\0" \
	"mmcargs=setenv bootargs console=${console},${baudrate} " \
		"root=${mmcroot}\0" \
	"loadbootscript=" \
		"load mmc ${mmcdev}:${mmcpart} ${loadaddr} ${script};\0" \
	"loaduEnv=" \
		"load ${devtype} ${bootpart} ${loadaddr} /uEnv.txt;\0" \
	"importbootenv=echo Importing environment from ${devtype} ...; " \
		"env import -t ${loadaddr} ${filesize}\0" \
	"bootscript=echo Running bootscript from mmc ...; " \
		"source\0" \
	"loadimage=load mmc ${mmcdev}:${mmcpart} ${loadaddr} ${image};\0" \
	"loadfdt=load mmc ${mmcdev}:${mmcpart} ${fdt_addr} ${fdt_file};\0" \
	"mmcboot=echo Booting from mmc ...; " \
		"run mmcargs; " \
		"if test ${boot_fdt} = yes || test ${boot_fdt} = try; then " \
			"if run loadfdt; then " \
				"bootz ${loadaddr} - ${fdt_addr}; " \
			"else " \
				"if test ${boot_fdt} = try; then " \
					"bootz; " \
				"else " \
					"echo WARN: Cannot load the DT; " \
				"fi; " \
			"fi; " \
		"else " \
			"bootz; " \
		"fi;\0" \
		"findfdt="\
			"if test $fdt_file = undefined; then " \
				"if test $board_name = ULZ-EVK && test $board_rev = 14X14; then " \
					"setenv fdt_file imx6ulz-14x14-evk.dtb; fi; " \
				"if test $board_name = EVK && test $board_rev = 14X14; then " \
					"setenv fdt_file imx6ull-14x14-evk.dtb; fi; " \
				"if test $fdt_file = undefined; then " \
					"echo WARNING: Could not determine dtb to use; " \
				"fi; " \
			"fi;\0" \
	"netargs=setenv bootargs console=${console},${baudrate} " \
		"root=/dev/nfs " \
	"ip=dhcp nfsroot=${serverip}:${nfsroot},v3,tcp\0" \
		"netboot=echo Booting from net ...; " \
		"run netargs; " \
		"if test ${ip_dyn} = yes; then " \
			"setenv get_cmd dhcp; " \
		"else " \
			"setenv get_cmd tftp; " \
		"fi; " \
		"${get_cmd} ${image}; " \
		"if test ${boot_fdt} = yes || test ${boot_fdt} = try; then " \
			"if ${get_cmd} ${fdt_addr} ${fdt_file}; then " \
				"bootz ${loadaddr} - ${fdt_addr}; " \
			"else " \
				"if test ${boot_fdt} = try; then " \
					"bootz; " \
				"else " \
					"echo WARN: Cannot load the DT; " \
				"fi; " \
			"fi; " \
		"else " \
			"bootz; " \
		"fi;\0" \
	"args_mmc_old=setenv bootargs console=ttymxc0 " \
		"root=/dev/mmcblk${mmcdev}p2 rw " \
		"rootfstype=ext4 " \
		"rootwait ${cmdline} ${flashtype}\0" \
	"boot=mmc check;${devtype} dev ${mmcdev};mmc rescan; " \
		"echo loading [${devtype} ${bootpart}] /uEnv.txt ...; "\
		"if run loaduEnv; then " \
			"run importbootenv;" \
			"if test ${second_flash} = emmc; then " \
					"setenv dtb ${mmc_dtb};"  \
					"setenv storage_media init=/opt/scripts/tools/eMMC/init-eMMC-flasher-v3.sh;"  \
				"else " \
					"setenv dtb ${nand_dtb};"  \
					"setenv storage_media init=/opt/scripts/tools/Nand/init-Nand-flasher-v1.sh;"  \
				"fi; " \
			"if test -n ${flash_firmware}; then "  \
					"echo setting flash firmware...;"  \
					"setenv flashtype ${storage_media};"  \
			"fi;" \
			"run args_mmc_old;" \
			"echo loading vmlinuz-${uname_r} ...; "\
			"load ${devtype} ${bootpart} 0x80800000 /kernel/vmlinuz-${uname_r};"\
			"echo loading ${dtb} ...; "\
			"load ${devtype} ${rootfpart} 0x83000000 /usr/lib/linux-image-${uname_r}/${dtb};"\
			"dtfile 0x83000000 0x87000000  /uEnv.txt ${loadaddr};"   \
			"load ${devtype} ${bootpart} 0x88000000 /kernel/initrd.img-${uname_r};"\
			"echo debug: [${bootargs}] ... ;" \
			"echo debug: [bootz] ...  ;" \
			"bootz 0x80800000 0x88000000:${filesize} 0x83000000;"	\
		"fi;\0" \
	BOOTENV
/*
#define CONFIG_BOOTCOMMAND \
	   "run findfdt;" \
	   "mmc dev ${mmcdev};" \
	   "mmc dev ${mmcdev}; if mmc rescan; then " \
		   "if run loadbootscript; then " \
			   "run bootscript; " \
		   "else " \
			   "if run loadimage; then " \
				   "run mmcboot; " \
			   "else run netboot; " \
			   "fi; " \
		   "fi; " \
	   "else run netboot; fi"
*/
#endif
*****************************完整环境参数*****************************

=> printenv
baudrate=115200
board_name=SABRESD
board_rev=MX6Q
boot_fdt=try
bootcmd=run findfdt;mmc dev ${mmcdev};if mmc rescan; then if run loadbootscript; then run bootscript; else if run loadimage; then run mmcboot; else run netboot; fi; fi; else run netboot; fi
bootcmd_mfg=run mfgtool_args;bootz ${loadaddr} ${initrd_addr} ${fdt_addr};
bootdelay=3
bootscript=echo Running bootscript from mmc ...; source
console=ttymxc0
dfu_alt_info=spl raw 0x400
dfu_alt_info_img=u-boot raw 0x10000
dfu_alt_info_spl=spl raw 0x400
dfuspi=dfu 0 sf 0:0:10000000:0
emmcdev=2
epdc_waveform=epdc_splash.bin
ethact=FEC
ethaddr=22:C1:F4:A2:2A:B0
ethprime=FEC
fdt_addr=0x18000000
fdt_file=undefined
fdt_high=0xffffffff
fec_mac=22:C1:F4:A2:2A:B0
fileaddr=20000000
filesize=119436
findfdt=if test $fdt_file = undefined; then if test $board_name = SABREAUTO && test $board_rev = MX6QP; then setenv fdt_file imx6qp-sabreauto.dtb; fi; if test $board_name = SABREAUTO && test $board_rev = MX6Q; then setenv fdt_file imx6q-sabreauto.dtb; fi; if test $board_name = SABREAUTO && test $board_rev = MX6DL; then setenv fdt_file imx6dl-sabreauto.dtb; fi; if test $board_name = SABRESD && test $board_rev = MX6QP; then setenv fdt_file imx6qp-sabresd.dtb; fi; if test $board_name = SABRESD && test $board_rev = MX6Q; then setenv fdt_file imx6q-c-sabresd.dtb; fi; if test $board_name = SABRESD && test $board_rev = MX6DL; then setenv fdt_file imx6dl-c-sabresd.dtb; fi; if test $fdt_file = undefined; then echo WARNING: Could not determine dtb to use; fi; fi;
image=zImage
initrd_addr=0x12C00000
initrd_high=0xffffffff
ip_dyn=yes
ldbmode=ldb=sin0
loadaddr=0x12000000
loadbootscript=fatload mmc ${mmcdev}:${mmcpart} ${loadaddr} ${script};
loadfdt=fatload mmc ${mmcdev}:${mmcpart} ${fdt_addr} ${fdt_file}
loadimage=fatload mmc ${mmcdev}:${mmcpart} ${loadaddr} ${image}
mfgtool_args=setenv bootargs console=ttymxc0,115200 rdinit=/linuxrc g_mass_storage.stall=0 g_mass_storage.removable=1 g_mass_storage.file=/fat g_mass_storage.ro=1 g_mass_storage.idVendor=0x066F g_mass_storage.idProduct=0x37FF g_mass_storage.iSerialNumber="" enable_wait_mode=off
mmcargs=setenv bootargs console=${console},${baudrate} ${mxcfb0} ${mxcfb1} ${ldbmode} ${smp} root=${mmcroot} fec.macaddr=${fec_mac}
mmcautodetect=yes
mmcboot=echo Booting from mmc ...; run mmcargs; if test ${boot_fdt} = yes || test ${boot_fdt} = try; then if run loadfdt; then bootz ${loadaddr} - ${fdt_addr}; else if test ${boot_fdt} = try; then bootz; else echo WARN: Cannot load the DT; fi; fi; else bootz; fi;
mmcdev=2
mmcpart=1
mmcroot=/dev/mmcblk3p2 rootwait rw
mxcfb0=video=mxcfb0:dev=mipi_dsi,TRULY-EK79007-WVGA,if=RGB24,bpp=16
mxcfb1=video=mxcfb1:dev=hdmi,1920x1080M@60,if=RGB24,bpp=16
netargs=setenv bootargs console=${console},${baudrate} ${smp} root=/dev/nfs ip=dhcp nfsroot=${serverip}:${nfsroot},v3,tcp
netboot=echo Booting from net ...; run netargs; if test ${ip_dyn} = yes; then setenv get_cmd dhcp; else setenv get_cmd tftp; fi; ${get_cmd} ${image}; if test ${boot_fdt} = yes || test ${boot_fdt} = try; then if ${get_cmd} ${fdt_addr} ${fdt_file}; then bootz ${loadaddr} - ${fdt_addr}; else if test ${boot_fdt} = try; then bootz; else echo WARN: Cannot load the DT; fi; fi; else bootz; fi;
panel=TRULY-EK79007-WVGA
script=boot.scr
splashpos=m,m
update_emmc_firmware=if test ${ip_dyn} = yes; then setenv get_cmd dhcp; else setenv get_cmd tftp; fi; if ${get_cmd} ${update_sd_firmware_filename}; then if mmc dev ${emmcdev} 1; then setexpr fw_sz ${filesize} / 0x200; setexpr fw_sz ${fw_sz} + 1; mmc write ${loadaddr} 0x2 ${fw_sz}; fi; fi
update_sd_firmware=if test ${ip_dyn} = yes; then setenv get_cmd dhcp; else setenv get_cmd tftp; fi; if mmc dev ${mmcdev}; then if ${get_cmd} ${update_sd_firmware_filename}; then setexpr fw_sz ${filesize} / 0x200; setexpr fw_sz ${fw_sz} + 1; mmc write ${loadaddr} 0x2 ${fw_sz}; fi; fi

Environment size: 3932/8188 bytes
=>

*****************************命令及子命令*****************************

=> mmc list
FSL_SDHC: 0
FSL_SDHC: 1
FSL_SDHC: 2 (eMMC)
=> printenv bootcmd
bootcmd=run findfdt;mmc dev ${mmcdev};if mmc rescan; then if run loadbootscript; then run bootscript; else if run loadimage; then run mmcboot; else run netboot; fi; fi; else run netboot; fi
=> printenv findfdt
findfdt=if test $fdt_file = undefined; then if test $board_name = SABREAUTO && test $board_rev = MX6QP; then setenv fdt_file imx6qp-sabreauto.dtb; fi; if test $board_name = SABREAUTO && test $board_rev = MX6Q; then setenv fdt_file imx6q-sabreauto.dtb; fi; if test $board_name = SABREAUTO && test $board_rev = MX6DL; then setenv fdt_file imx6dl-sabreauto.dtb; fi; if test $board_name = SABRESD && test $board_rev = MX6QP; then setenv fdt_file imx6qp-sabresd.dtb; fi; if test $board_name = SABRESD && test $board_rev = MX6Q; then setenv fdt_file imx6q-c-sabresd.dtb; fi; if test $board_name = SABRESD && test $board_rev = MX6DL; then setenv 
=> printenv mmcdev
mmcdev=2
=> printenv loadbootscript
loadbootscript=fatload mmc ${mmcdev}:${mmcpart} ${loadaddr} ${script};
=> printenv bootscript
bootscript=echo Running bootscript from mmc ...; source
=> printenv loadimage
loadimage=fatload mmc ${mmcdev}:${mmcpart} ${loadaddr} ${image}
=> printenv mmcboot
mmcboot=echo Booting from mmc ...; run mmcargs; if test ${boot_fdt} = yes || test ${boot_fdt} = try; then if run loadfdt; then bootz ${loadaddr} - ${fdt_addr}; else if test ${boot_fdt} = try; then bootz; else echo WARN: Cannot load the DT; fi; fi; else bootz; fi;
=> printenv netboot
netboot=echo Booting from net ...; run netargs; if test ${ip_dyn} = yes; then setenv get_cmd dhcp; else setenv get_cmd tftp; fi; ${get_cmd} ${image}; if test ${boot_fdt} = yes || test ${boot_fdt} = try; then if ${get_cmd} ${fdt_addr} ${fdt_file}; then bootz ${loadaddr} - ${fdt_addr}; else if test ${boot_fdt} = try; then bootz; else echo WARN: Cannot load the DT; fi; fi; else bootz; fi;
=>

嵌入式之家画的流程图

在这里插入图片描述

uboot 环境参数介绍

uboot 中环境参数为我们提供一种不修改 uboot 源码的情况下,能够修改 kernel 启动倒计时、ip 地址、以及向内核传递不同的参数等。
在板子上使用 printenv 可查看板子上所有的环境参数,使用 setenv 添加/修改/删除环境参数,具体说明如下所示:

# 设置新的环境参数名为 sen,值为 100
=> setenv sen 100
=> echo $sen
100

# 将值修改为 200
=> setenv sen 200
=> echo $sen
200

# 删除 sen 环境参数
=> setenv sen
=> echo $sen

=>

默认情况下使用 setenv 命令修改环境参数重启后就会消失,若想要掉电保存需要执行 saveenv 将环境参数保存到存储介质。
uboot 上有一些官方规定的环境变量,这些环境变量在 uboot 有着特殊的作用,可通过以下链接查看:https://www.denx.de/wiki/view/DULG/UBootEnvVariables

3 U-Boot 编译

3.1 系统

Ubuntu 18.04 LTS

3.2 安装依赖和编译工具

sudo apt install make git gcc-arm-none-eabi gcc bison flex libssl-dev dpkg-dev lzop libncurses5-dev

3.3 获取 U-Boot

(1)下载源代码
官方 uboot GitHub:
https://github.com/u-boot/u-boot

映射到gitee
https://gitee.com/ingenic-dev/u-boot

NXP 提供的 uboot 下载链接:
https://github.com/Freescale/u-boot-fslc

映射到gitee
https://gitee.com/xrke/u-boot-fslc

野火提供的 uboot 下载链接:
https://gitee.com/Embedfire/ebf_linux_uboot

  • 如下尝试下载 Freescale 的都失败,网络不行
# 直接全部下载报错
bot@u18:~/worthsen/u-boot$ git clone https://github.com/Freescale/u-boot-fslc.git
Cloning into 'u-boot-fslc'...
remote: Enumerating objects: 975157, done.
remote: Counting objects: 100% (135382/135382), done.
remote: Compressing objects: 100% (26711/26711), done.
error: RPC failed; curl 18 transfer closed with outstanding read data remaining
fatal: The remote end hung up unexpectedly
fatal: early EOF
fatal: index-pack failed

# 只拉取 2020.10+fslc 分支
# -b 2020.10+fslc 为只拉取该分支内容,可以改为其他分支名称
# --depth 1为只拉取最近一次提交的内容
bot@u18:~/worthsen/u-boot$ git clone -b 2020.10+fslc https://github.com/Freescale/u-boot-fslc.git
Cloning into 'u-boot-fslc'...
remote: Enumerating objects: 975157, done.
remote: Counting objects: 100% (135382/135382), done.
remote: Compressing objects: 100% (26711/26711), done.
error: RPC failed; curl 18 transfer closed with outstanding read data remaining
fatal: The remote end hung up unexpectedly
fatal: early EOF
fatal: index-pack failed

# 增加缓存,设置为500M
bot@u18:~/worthsen/u-boot$ git config --global http.postBuffer 524288000
bot@u18:~/worthsen/u-boot$ git config --global --get http.postBuffer
524288000

bot@u18:~/worthsen/u-boot$ git clone -b 2020.10+fslc https://github.com/Freescale/u-boot-fslc.git
Cloning into 'u-boot-fslc'...
remote: Enumerating objects: 975157, done.
remote: Counting objects: 100% (135382/135382), done.
remote: Compressing objects: 100% (26714/26714), done.
error: RPC failed; curl 18 transfer closed with outstanding read data remaining
fatal: The remote end hung up unexpectedly
fatal: early EOF
fatal: index-pack failed
  • 借助码云来下载 u-boot 的:https://gitee.com/ingenic-dev/u-boot.git
bot@u18:~/worthsen/u-boot$ git clone https://gitee.com/ingenic-dev/u-boot.git
Cloning into 'u-boot'...
remote: Enumerating objects: 999393, done.
remote: Counting objects: 100% (999393/999393), done.
remote: Compressing objects: 100% (192876/192876), done.
remote: Total 999393 (delta 794995), reused 999393 (delta 794995), pack-reused 0
Receiving objects: 100% (999393/999393), 286.59 MiB | 1.66 MiB/s, done.
Resolving deltas: 100% (794995/794995), done.
Checking out files: 100% (31968/31968), done.
  • 借助码云来下载 Freescale 的:https://gitee.com/xrke/u-boot-fslc
bot@u18:~/worthsen/u-boot$ git clone https://gitee.com/xrke/u-boot-fslc.git
Cloning into 'u-boot-fslc'...
remote: Enumerating objects: 975157, done.
remote: Counting objects: 100% (975157/975157), done.
remote: Compressing objects: 100% (164034/164034), done.
remote: Total 975157 (delta 799792), reused 975157 (delta 799792), pack-reused 0
Receiving objects: 100% (975157/975157), 241.30 MiB | 9.14 MiB/s, done.
Resolving deltas: 100% (799792/799792), done.
Checking out files: 100% (19492/19492), done.
bot@u18:~/worthsen/u-boot$ cd u-boot-fslc/
bot@u18:~/worthsen/u-boot/u-boot-fslc$ git branch -a
* 2023.04+fslc
  remotes/origin/2015.07+fslc
  remotes/origin/2015.10+fslc
  ...
bot@u18:~/worthsen/u-boot/u-boot-fslc$ git checkout 2020.10+fslc
Branch '2020.10+fslc' set up to track remote branch '2020.10+fslc' from 'origin'.
Switched to a new branch '2020.10+fslc'
bot@u18:~/worthsen/u-boot/u-boot-fslc$ git branch 
* 2020.10+fslc
  2023.04+fslc
bot@u18:~/worthsen/u-boot/u-boot-fslc$
  • 下载野火的
    https://gitee.com/Embedfire/ebf_linux_uboot
git clone https://gitee.com/Embedfire/ebf_linux_uboot

(2)查看切换分支

3.4 uboot 工程结构 & 变量 & 子功能

3.4.1 uboot 工程结构

uboot 的源代码布局和 Linux 类似,使用了按照模块划分的结构,并且充分考虑了体系结构和跨平台问题,其源代码树结构请参考如下:

目录/文件说明
api通用的 API 函数相关目录
arch与芯片架构相关的目录
board板级相关信息目录
boot包含与启动过程相关的代码,如自举加载程序(bootstrap)代码。
cmduboot 命令相关的目录
common通用代码目录
configsboot 配置文件目录
disk磁盘相关内容目录
doc说明文档
drivers驱动代码相关目录
dtoverlay设备树相关目录
dts设备树相关目录
envuboot 环境相关
examples示例代码目录
fs文件系统相关目录
include头文件相关目录
liblib库文件目录
Licenses许可证相关目录
net网络相关代码目录
post上电自检相关目录
scripts相关脚本目录
test测试代码目录
toolsuboot 构建工具相关的目录
Kconfig图形配置界面相关目录
MakefileMakefile 文件

3.4.2 uboot 变量

变量数值描述
__image_copy_start0x87800000uboot拷贝的首地址
__image_copy_end0x8785dd54uboot拷贝的结束地址
__rel_dyn_start0x8785dd54.rel.dyn段起始地址
__rel_dyn_end0x878668f4.rel.dyn段结束地址
__image_binary_end0x878668f4镜像结束地址
__bss_start0x8785dd54.bss段起始地址
__bss_end0x878a8e74.bss段结束地址

3.4.3 uboot 子功能

  • bootz流程
    在这里插入图片描述

3.5 uboot 编译

来自 lzd626 的图解

  • 配置:当输入“make xxx_defconfig”的时候就会匹配到%config 目标,目标“%config”依赖于 scripts_basic、outputmakefile 和 FORCE
    在这里插入图片描述

  • 编译:过程如下
    在这里插入图片描述

赵建辉理解的 u-boot.imx 目标依赖关系图

https://github.com/zhaojh329/U-boot-1/blob/master/%E7%AC%AC9%E7%AB%A0-U-boot%E7%BC%96%E8%AF%91%E4%B9%8B%E4%BA%8C%E7%BC%96%E8%AF%91%E8%BF%87%E7%A8%8B.md
在这里插入图片描述

野火 ebf_v2020_10_imx 分支

野火提供的 imx6ull uboot 分为 nand 版本和 emmc 版本,以编译 emmc 版本为例

bot@u18:~/worthsen/u-boot/ebf_linux_uboot$ git branch -a
* master
  remotes/origin/HEAD -> origin/master
  remotes/origin/ebf_v2017_09_rk3328
  remotes/origin/ebf_v2017_09_rk3399
  remotes/origin/ebf_v2018.11_star
  remotes/origin/ebf_v2020_10_imx
  remotes/origin/ebf_v2021_07_rk3399
  remotes/origin/imx_v2019.04_ls1043ardb
  remotes/origin/imx_v2020.04_5.4.47_2.2.0
  remotes/origin/master
bot@u18:~/worthsen/u-boot/ebf_linux_uboot$ git checkout ebf_v2020_10_imx
Branch 'ebf_v2020_10_imx' set up to track remote branch 'ebf_v2020_10_imx' from 'origin'.
Switched to a new branch 'ebf_v2020_10_imx'
bot@u18:~/worthsen/u-boot/ebf_linux_uboot$ git branch
* ebf_v2020_10_imx
  master

# (1)sudo make distclean 清除上次生成的编译环境,避免之前的环境干扰影响编译结果
bot@u18:~/worthsen/u-boot/ebf_linux_uboot$ sudo make distclean
# (2)sudo make ARCH=arm CROSS_COMPILE=arm-none-eabi- mx6ull_fire_mmc_defconfig
# 加载板级配置文件,具体的板级配置文件在 uboot 根目录下的 configs 目录下
bot@u18:~/worthsen/u-boot/ebf_linux_uboot$ sudo make ARCH=arm CROSS_COMPILE=arm-none-eabi- mx6ull_fire_mmc_defconfig
  HOSTCC  scripts/basic/fixdep
  HOSTCC  scripts/kconfig/conf.o
  YACC    scripts/kconfig/zconf.tab.c
  LEX     scripts/kconfig/zconf.lex.c
  HOSTCC  scripts/kconfig/zconf.tab.o
  HOSTLD  scripts/kconfig/conf
#
# configuration written to .config
#
# (3)sudo make ARCH=arm CROSS_COMPILE=arm-none-eabi-
# 设置编译架构为 arm 编译工具链为 arm-none-eabi- 然后开始编译
bot@u18:~/worthsen/u-boot/ebf_linux_uboot$ sudo make ARCH=arm CROSS_COMPILE=arm-none-eabi-
scripts/kconfig/conf  --syncconfig Kconfig
  UPD     include/config.h
  CFG     u-boot.cfg
  ...
  CFGCHK  u-boot.cfg
bot@u18:~/worthsen/u-boot/ebf_linux_uboot$ 

3.6 编译产物分析

文件说明
u-boot初步链接后得到的uboot文件
u-boot-nodtb.bin在u-boot的基础上,经过objcopy去除符号表信息之后的可执行程序
u-boot.dtbdtb文件
u-boot-dtb.bin将u-boot-nodtb.bin和u-boot.dtb打包在一起的文件
u-boot.bin在需要dtb的情况下,直接由u-boot-dtb.bin复制而来,也就是编译u-boot的最终目标
u-boot.ldsuboot的连接脚本
System.map连接之后的符号表文件
u-boot.cfg由uboot配置生成的文件

4 U-Boot 烧录

4.1 Mfgtool 烧写 Uboot 到内部存储(EMMC/NAND 通用)

系统烧写工具–MfgTool

介绍

MFGTool 工具是 NXP 官方推荐的一个使用 USB OTG 来升级镜像的软件工具,它是 NXP 针对 i.MX 系列处理器专门使用的烧录工具,可以用来升级 linux,单独烧录某一系统分区,独立地烧录 spi flash、nor flash、sd card、nand flash,emmc 等,只需简单的配置,就可以使用该工具将编译好的文件系统和镜像文件烧录到开发板上,使用起来非常方便。

烧录步骤分析

MFGtool 工具的烧录步骤分为两个阶段:BurnStarp 和 Updater。
第一阶段先烧录媒介镜像到 DDR,然后启动媒介系统;
第二阶段通过该系统把目标镜像固化到存储设备中。

第二阶段严格根据 ucl2.xml 文件来处理。

4.2 Uboot 烧写到 SD 卡镜像(常用于做 uboot 测试)

系统烧写工具–MfgTool

5 U-Boot 移植

6 U-Boot 控制 GPIO & 定制自己的 Uboot 单板

6.1 U-Boot 控制 GPIO

  • 介绍
    Uboot 的 GPIO 是常用的功能,在开发中常常需要在上电时进行控制。

  • 详见文件
    [野火]《嵌入式Linux镜像构建与部署——基于LubanCat-i.MX6ULL开发板》

6.2 U-Boot 定制自己的 Uboot 单板

  • 详见文件
    [野火]《嵌入式Linux镜像构建与部署——基于LubanCat-i.MX6ULL开发板》

7 电脑 与 嵌入式设备 系统启动区别

在 一只嵌入式爱好者 的图上加了补充
一张图看懂嵌入式与PC启动流程
在这里插入图片描述

知识点

1 BIOS、UEFI、MBR、GPT、GRUB 区别联系

基本输入输出系统【BIOS、UEFI】

BIOS(Basic Input Output System),直译成中文名称就是"基本输入输出系统"。它是一组固化到主板中一个ROM芯片上的程序,它可以从CMOS中读写系统设置的具体信息。此程序保存着计算机最重要的基本输入输出程序、开机后的自检程序和系统自启动程序。

UEFI(Unified Extensible Firmware Interface)则是取代传统 BIOS 的,相比传统BIOS来说,它更易实现,容错和纠错特性也更强。传统 BIOS 主要支持 MBR 引导,UEFI则是取代传统BIOS,使用 GPT 替代 MBR 引导,从而支持2TB以上硬盘。

特性UEFIBIOS
开源/闭源开源闭源
开发效率
标准接口
接口混乱
代码构成绝大多数是C代码主要是汇编
性能异步+时钟中断中断机制
扩展和兼容性模块化驱动设计静态链接
安全安全未考虑安全
其它支持容量超过2TB的驱动器不支持容量超过2TB的驱动器

硬盘分区初始化格式【MBR、GPT】

硬盘分区初始化的格式主要有两种,分别为MBR格式和GPT格式。

MBR 最大的缺点则是不支持容量大于2T的硬盘。

GPT是另一种更先进的磁盘系统分区方式,它的出现弥补了MBR这个缺点,最大支持18EB的硬盘,是基于UEFI使用的磁盘分区架构。

bootloader【GRUB】

GRUB(GRand unified bootloader),多操作系统启动程序。它允许用户可以在计算机内同时拥有多个操作系统,并在计算机启动时选择希望运行的操作系统。

GRUB可用于选择操作系统分区上的不同内核,也可用于向这些内核传递启动参数。它是一个多重操作系统启动管理器,用来引导不同系统,如Windows、Linux。Linux常见的引导程序包括LILO、GRUB、GRUB2。

如下图所示为GRUB加载引导流程

在这里插入图片描述

参考

1、yocto 手册
2、[野火]《嵌入式Linux镜像构建与部署——基于LubanCat-i.MX6ULL开发板》
3、BitBake 手册
4、The U-Boot Documentation
5、嵌入式 Linux 开发的基本概念和学习新路线
6、BootLoader 介绍 与 uboot 简介
7、[架构之路-26]:目标系统 - 系统软件 - bootloader uboot使用方法、常用命令
8、wiki–Bootloader
9、wiki–Das U-Boot
10、rockbox–官网
11、rockbox–Rockbox User Manual
12、【干货】BIOS、UEFI、MBR、GPT、GRUB 到底是什么意思?
13、BIOS、UEFI、Boot Loader都是些什么
14、全网最全面最易懂的U-Boot解读
15、嵌入式Linux系统 的组成(BootLoader,Kernel,Root Filesystem)
16、一张图看懂嵌入式与PC启动流程
17、Linux学习笔记(7)——u-boot常用指令
18、制作rk3588镜像及烧写
19、Yocto/docs
/0007_MFGTool_initramfs_Boot_Root_Filesystem.md
20、Linux学习笔记(7)——u-boot常用指令
21、UBoot之bootcmd和bootarg环境变量
22、Uboot中bootargs以及bootcmd设置
23、2. 如何学习linux开发
24、Linux/u-boot 代码目录结构
25、uboot学习(1)-uboot目录详解
26、uboot_imx_2016浅析
27、uboot启动流程详细分析(基于i.m6ull)
28、good–u-boot 的编译和配置
29、U-Boot启动过程概述 U-Boot启动代码具体分析
30、uboot 的配置和编译过程
31、U-boot学习笔记 嵌入式项目,基于imx6q的编译执行
32、[uboot] (第四章)uboot流程——uboot编译流程

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:/a/734204.html

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

SSRF(2)

Gopher协议的利用 gopher协议是ssrf利用中最强大的协议 gopher协议支持发出GET、POST请求&#xff1a; 可以先截获get请求包和post请求包&#xff0c;再构成符合gopher协议的请求。 默认端口为70,一般需发送到80端口 如果发起post请求&#xff0c;回车换行需要使用%0D%0A&…

Docker:centos79-docker-compose安装记录

1.安装环境&#xff1a;centos7.9 x86 2.安装最新版&#xff1a; [rootlocalhost ~]# curl -fsSL get.docker.com -o get-docker.sh [rootlocalhost ~]# sh get-docker.sh # Executing docker install script, commit: e5543d473431b782227f8908005543bb4389b8desh -c yum in…

PHPMailer发送的中文内容乱码如何解决

一&#xff1a; PHPMailer sdk 文件中有个设置默认编码的位置&#xff1a; vendor/phpmailer/phpmailer/src/PHPMailer.php 二&#xff1a; 实际业务代码中&#xff1a; require /sdk/PHPMailer/vendor/autoload.php;$mail new PHPMailer(true);try {//Server settings$mai…

基于Spring Boot+VUE职称评审管理系统

1管理员功能模块 管理员登录&#xff0c;通过填写注册时输入的用户名、密码、角色进行登录&#xff0c;如图1所示。 图1管理员登录界面图 管理员登录进入职称评审管理系统可以查看首页、个人中心、用户管理、评审员管理、省份管理、评审条件管理、职称申请管理、结果公布管理、…

containerd手动配置容器网络

containerd手动配置容器网络 机器详情nerdctl启动一个不带网络的容器获取容器ID、PID与network namespace路径准备bridge插件的执行配置文件通过下面的命令调用bridge插件准备tuning插件文件执行下面的命令调用tuning插件准备portmap插件文件执行下面的命令调用portmap插件删除…

Android记录9--实现转盘效果

自定义View /2013.10.16_TurnPlate_Demo/src/com/wwj/turnplate/TurnPlateView.java package com.wwj.turnplate; import android.content.Context; import android.content.res.Resources; import android.graphics.Bitmap; import android.graphics.BitmapFactory; im…

日本新入管法通过:2027年起实施[育成就劳]制度,新制度更适合外国劳工在日本工作和生活!

最近&#xff0c;日本新入管法&#xff1a;新的育成就业制度预计将在2027年开始实施&#xff0c;而1993年开始的旧的技能实习制度将被废除。 新制度的主要内容 新制度的目的是解决日本国内的劳动力不足问题&#xff0c;确保有足够的劳动者。表示&#xff1a;“为了让日本成为…

上手微服务框架go-zero

文章目录 微服务框架与web框架的区别点在哪儿&#xff1f;为什么还要有微服务框架微服务框架与web框架的对比小结 为什么选go-zero&#xff1f;框架对比 下载并认识go-zero认识go-zero环境要求组成下载 实践go-zero基础功能案例apirpc服务功能说明准备构建rpc服务构建api服务服…

头歌资源库(14)残缺棋盘

一、 问题描述 二、算法思想 首先&#xff0c;将2^k 2^k的棋盘划分为四个相等大小的子棋盘&#xff0c;定义为左上、左下、右上和右下四个子棋盘。 然后&#xff0c;根据残缺格的坐标&#xff0c;确定其中一个子棋盘是不完整的&#xff0c;即残缺子棋盘。假设残缺子棋盘是左…

导入别人的net文件报红问题

1. 使用cmd命令 dotnet --info 查看自己使用的SDK版本 2.直接找到项目中的 global.json 文件&#xff0c;右键打开&#xff0c;直接修改版本为本机的SDK版本&#xff0c;就可以用了

区块链媒体发布推广秘籍大揭秘-华媒舍

区块链技术迅猛发展&#xff0c;成为全球瞩目的热门领域。随之而来的是区块链媒体的兴起&#xff0c;成为传播和推广区块链知识、项目和应用的重要平台。本文将揭示区块链媒体发布推广的秘籍&#xff0c;为读者深入了解该领域提供详尽科普介绍。 一、什么是区块链媒体&#xff…

Python爬虫学习 | Scrapy框架详解

一.Scrapy框架简介 何为框架&#xff0c;就相当于一个封装了很多功能的结构体&#xff0c;它帮我们把主要的结构给搭建好了&#xff0c;我们只需往骨架里添加内容就行。scrapy框架是一个为了爬取网站数据&#xff0c;提取数据的框架&#xff0c;我们熟知爬虫总共有四大部分&am…

C语言| 数组的折半查找

数组的折半查找 折半查找&#xff1a;在已经排好序的一组数据中快速查找数据。 先排序&#xff0c;再使用折半查找。 【折半查找的运行过程】 1 存储数组下标 low最小的下标&#xff0c;mid中间的下标&#xff0c; high最大的下标 2 key存放查找的值&#xff0c;每一次对比后…

【AI工作流-AI-Agent】FastGPT新建应用并用openai接口调用

FastGPT 简介 FastGPT是一个AI工作流搭建平台&#xff0c;它是一个开源框架&#xff0c;支持聊天&#xff0c;RAG&#xff08;知识库&#xff09;&#xff0c;工作流编排。 缺点是不支持AI搜索&#xff0c;模型支持需要依赖于第三方部署框架例如oneapi&#xff0c;ollama等。…

关于飞浆文字识别技术的运用

飞桨PaddlePaddle-源于产业实践的开源深度学习平台&#xff0c;有关文章可以在此进行查询 飞桨&#xff08;PaddlePaddle&#xff09;是一个由百度开源的深度学习平台&#xff0c;它提供了丰富的机器学习算法库&#xff0c;支持多种深度学习模型的构建、训练和部署。飞桨平台具…

【pytorch02】手写数字问题引入

1.数据集 现实生活中遇到的问题 车牌识别身份证号码识别快递单的识别 都会涉及到数字识别 MNIST&#xff08;收集了很多人手写的0到9数字的图片&#xff09; 每个数字拥有7000个图像train/test splitting:60k vs 10k 图片大小28 28 数据集划分成训练集和测试集合的意义…

学生选课系统

摘 要 随着学校规模的日渐庞大与课程种类的丰富&#xff0c;传统手工选课方式的局限日益凸显&#xff0c;其繁琐和易错性在处理庞大数据时尤为明显。在追求个性化学习路径的现代教育浪潮中&#xff0c;学生们对自主选课的需求愈发强烈&#xff0c;他们渴望根据兴趣和职业规划自…

Android系统 抓trace方法(手机及车机)

1、先说说什么是trace trace是一种以perfetto.trace结尾的文件。一般用来分析卡顿、启动时间慢等问题&#xff0c;还可以用来分析方法耗时&#xff0c;android系统的性能、功耗等等问题。所需要使用到的网站是&#xff1a; Perfetto UI 他的前身是Systrace&#xff0c;不过Pe…

Ubuntu24使用kubeadm部署高可用K8S集群

Ubuntu24使用kubeadm部署高可用K8S集群 使用kubeadm部署一个k8s集群&#xff0c;3个master1个worker节点。 1. 环境信息 操作系统&#xff1a;ubuntu24.04内存: 2GBCPU: 2网络: 能够互访&#xff0c;能够访问互联网 hostnameip备注k8s-master1192.168.0.51master1k8s-maste…

已解决!!!mamba2替换mamba,速度提升2到8倍

mamba已经发布有一段时间了&#xff0c;打着击败transformer的口号&#xff0c;确实引起了一大波关注&#xff0c;核心架构的改进也给研究者提供了新的水论文的思路 mamba2已经发布&#xff0c;号称比第一代mamba要提速2到8倍&#xff0c;实际上手时却挺打击信心的&#xff0c;…