U-Boot makes use of the so-called environment variables to define various aspects of the target functionality. The U-Boot environment is stored in the SD Card memory and is persistent across power or reset cycles. Parameters defined by the U-boot environment variables include: target IP address, target MAC address, location in RAM where a Linux bootable image will be loaded, and many others.
In various use case scenarios, it may be needed to read or update U-Boot environment variables from Linux. Probably, the most obvious scenario would be when a remote target is accessible only through an Ethernet or WiFi link and no access to the serial console is available. In that scenario, it is impossible to get access to the U-Boot serial line command monitor, however the target still can be connected to over a telnet or ssh
link providing access to the Linux shell interface. This application note explains how to read and update U-Boot environment variables from Linux.
The Linux utilities are called fw_printenv
(read U-Boot environment) and fw_setenv
(modify U-Boot environment). The two utitlies are in fact implemented as a single utility, and the name of the executable file is used to distinguish between the fw_printenv
and fw_setenv
use cases on the target.
When you boot the newly installed Linux image on the target, you will be able to read and update the U-Boot environment. Here are some examples.
The following command reads the whole U-Boot environment:
/ # fw_printenv addip=setenv bootargs ${bootargs} ip=${ipaddr}:${serverip}:${gatewayip}:${netmask}:${hostname}:eth0:off arch=arm baudrate=115200 board=imxrt1170-evk board_name=imxrt1170-evk bootcmd=run mmcboot bootdelay=2 cpu=armv7m ... / #
Here is how you can read a specific environment variable:
/ # fw_printenv bootdelay bootdelay=0 / #
Here is how you change the value of an environment variable:
/ # fw_setenv bootdelay 5 / #
Having updated bootdelay
as shown above, on the next reset U-Boot will wait for 5 seconds for you to press a keyboard and enter the U-Boot command monitor before proceeding to boot Linux.
The source files of the fw_printenv
utility reside in the U-boot source tree, which is located in the u-boot/ sub-directory in the Emcraft software distribution.
fw_setenv
and fw_printenv
are included in the default rootfs
project. The utilities are built during the rootfs compilation according to the rules specified in the projects/rootfs/env/Makefile
:
The U-Boot source tree is configured for the NXP i.MX RT1170 EVK board;
The
fw_printenv
utility is built.
When run on the target, the utility makes use of a configuration file that defines the geometry of the device and where the U-Boot environment is located in it. Since we keep the environment on the SD Card here is what the configuration file looks like for the NXP i.MX RT1170 EVK board:
-bash-4.2$ cat projects/rootfs/etc/fw_env.config.mmc # Configuration file for fw_(printenv/setenv) utility. # Up to two entries are valid, in this case the redundant # environment sector is assumed present. # Configuration for a board with CONFIG_ENV_IS_IN_MMC # # MTD device name Device offset Env. size /dev/mmcblk0 0x80000 0x1f000
In theĀ rootfs
project, the fw_setenv
and the configuration file are added to rootfs.initramfs
:
... file /bin/fw_printenv ${INSTALL_ROOT}/u-boot/tools/env/fw_printenv 755 0 0 slink /bin/fw_setenv fw_printenv 755 0 0 ... ifarch IMXRT117X_NXPEVK file /etc/fw_env.config ${INSTALL_ROOT}/projects/${SAMPLE}/etc/fw_env.config.mmc 644 0 0 ...
Several U-Boot environment variables are used very early during the Linux bootstrap, at the /etc/rc stage.