[PATCH 2/4] bootmeth: efi: source the devicetree from a firmware partition

Simon Glass sjg at chromium.org
Thu Jul 9 22:18:43 CEST 2026


Hi Carlo,

On 2026-07-06T15:06:41, Carlo Caione <ccaione at baylibre.com> wrote:
> bootmeth: efi: source the devicetree from a firmware partition
>
> When a firmware-owned devicetree source is configured (EBBR / Arm
> SystemReady IR), assemble the devicetree from the FIT manifest on
> the firmware partition instead of reading a DTB from the EFI System
> Partition, and hand it to the EFI application through the normal
> bflow->fdt_addr path (efi_install_fdt()).
>
> Signed-off-by: Carlo Caione <ccaione at baylibre.com>
>
> boot/bootmeth_efi.c | 81 +++++++++++++++++++++++++++++++++++++++++++++++++++++
>  1 file changed, 81 insertions(+)

> diff --git a/boot/bootmeth_efi.c b/boot/bootmeth_efi.c
> @@ -73,6 +74,61 @@ static int efiload_read_file(struct bootflow *bflow, ulong addr)
> +     ret = firmware_fdt_load(&fw);
> +     if (ret) {
> +             if (ret != -ENOENT)
> +                     log_err("Failed to assemble the firmware devicetree (err %d)\n",
> +                             ret);
> +             return ret;
> +     }
> +
> +     /* stage it at fdt_addr_r, like any other devicetree */
> +     fdt_addr = env_get_hex('fdt_addr_r', 0);
> +     if (!fdt_addr || fw.size > SZ_4M) {
> +             firmware_fdt_free(&fw);
> +             return log_msg_ret('fwa', -EINVAL);
> +     }

Please move the fdt_addr_r lookup above firmware_fdt_load():
assembling the manifest, applying overlays and running
fdt_check_full() only to discover we have nowhere to put the result
is wasted work. The SZ_4M cap also duplicates FW_FDT_MAX_SIZE inside
firmware_fdt.c - please share the constant via firmware_fdt.h

> diff --git a/boot/bootmeth_efi.c b/boot/bootmeth_efi.c
> @@ -130,6 +186,18 @@ static int distro_efi_try_bootflow_files(struct udevice *dev,
> +     /*
> +      * A staged firmware-owned devicetree is complete and authoritative,
> +      * so return without considering any other devicetree source. The
> +      * extension overlays below are deliberately not applied on top:
> +      * such combinations belong in the manifest as configurations.
> +      */
> +     ret = distro_efi_firmware_fdt(bflow);
> +     if (!ret)
> +             return 0;
> +     if (ret != -ENOENT)
> +             return log_msg_ret('fwf', ret);

Just to check - once you move the env lookup into the helper, the
outer fdt_addr = env_get_hex(...) still needs to run for the ESP
fall-back path. Please make sure the two lookups cannot disagree and
state the contract in the doc-comment.

> diff --git a/boot/bootmeth_efi.c b/boot/bootmeth_efi.c
> @@ -268,6 +336,19 @@ static int distro_efi_read_bootflow_net(struct bootflow *bflow)
> +     /*
> +      * A configured firmware-owned devicetree outranks the network-provided
> +      * one (and the prior-stage / built-in devicetree below): a DHCP/TFTP
> +      * server must not be able to replace it.
> +      */
> +     ret = distro_efi_firmware_fdt(bflow);
> +     if (!ret) {
> +             bflow->state = BOOTFLOWST_READY;
> +             return 0;
> +     }
> +     if (ret != -ENOENT)
> +             return log_msg_ret('fwf', ret);

The two call sites are essentially identical except for the extra
bflow->state = BOOTFLOWST_READY here. Please factor the "try
firmware fdt, return on success, fail on hard error, otherwise
continue" logic into a small helper - patch 3 adds a third caller
in efi_bootmgr.c and it would be easy to forget one of the checks.

> diff --git a/boot/bootmeth_efi.c b/boot/bootmeth_efi.c
> @@ -73,6 +74,61 @@ static int efiload_read_file(struct bootflow *bflow, ulong addr)
> +     if (!CONFIG_IS_ENABLED(BOOTSTD_FIRMWARE_FDT))
> +             return -ENOENT;

BTW the stub in firmware_fdt.h returns -ENOSYS when the option is
disabled, so this early-return exists purely to remap that to
-ENOENT. Cleaner to have the stub return -ENOENT directly and drop
this guard.

Regards,
Simon


More information about the U-Boot mailing list