The keys trusted for FIT signature verification are supposed to be embedded in the device tree built into u-boot. When running in Qemu it's convenient to use the device tree provided by the VM which doesn't know about signatures though. So merge both device trees at startup.
Signed-off-by: Ludwig Nussel <[email protected]> --- Changes in v4: - mention arm in subject - correctly change defconfig Changes in v3: - enable CONFIG_OF_OMIT_DTB=n in defconfig - add error returns - document decission about dt merging direction board/emulation/qemu-arm/qemu-arm.c | 47 +++++++++++++++++++++++++++-- configs/qemu_arm64_defconfig | 1 + 2 files changed, 46 insertions(+), 2 deletions(-) diff --git a/board/emulation/qemu-arm/qemu-arm.c b/board/emulation/qemu-arm/qemu-arm.c index 38f0ec5f2fb..ecaddceb756 100644 --- a/board/emulation/qemu-arm/qemu-arm.c +++ b/board/emulation/qemu-arm/qemu-arm.c @@ -144,10 +144,53 @@ int dram_init_banksize(void) return 0; } +/* QEMU loads a generated DTB for us at the start of RAM. + * When using signatures we may have a built-in FDT that contains + * our known public keys nevertheless. So merge the built in FDT + * into QEMU's. We cannot merge the other way around (eg in + * fdtdec_board_setup()) or board_fix_fdt() at this stage as U-Boot + * might be started from a ROM location. At the same time U-Boot + * needs QEMU's FDT to initialize serial devices even before + * relocation. + */ int board_fdt_blob_setup(void **fdtp) { - /* QEMU loads a generated DTB for us at the start of RAM. */ - *fdtp = (void *)CFG_SYS_SDRAM_BASE; + void *qemu_fdt = (void *)CFG_SYS_SDRAM_BASE; + int ret; + + if (fdt_check_header(qemu_fdt) != 0) { + log_err("Invalid QEMU FDT at %p\n", qemu_fdt); + return -EINVAL; + } + + if (fdt_check_header(*fdtp) != 0) { + /* this was a perfectly normal condition before + * (CONFIG_OF_OMIT_DTB was set for qemu). So to avoid + * breaking existing configs don't error out. This + * might mean that we don't have keys in case + * FIT_SIGNATURE is on. We can't know though as + * existing setups might have injected them into + * QEMU's FDT already. + */ + goto out; + } + + log_debug("Found built-in FDT at %p. Merging into %p...\n", *fdtp, qemu_fdt); + + ret = fdt_increase_size(qemu_fdt, 1024 + fdt_totalsize(*fdtp)); + if (ret) { + log_err("Failed to resize FDT overlay: %s", fdt_strerror(ret)); + goto out; + } + + ret = fdt_overlay_apply_node(qemu_fdt, 0, (void *)*fdtp, 0); + if (ret) { + log_err("Failed to apply FDT overlay: %s\n", fdt_strerror(ret)); + goto out; + } + +out: + *fdtp = qemu_fdt; return 0; } diff --git a/configs/qemu_arm64_defconfig b/configs/qemu_arm64_defconfig index 5bdbd6fb59a..0fd7016c045 100644 --- a/configs/qemu_arm64_defconfig +++ b/configs/qemu_arm64_defconfig @@ -38,6 +38,7 @@ CONFIG_CMD_EFIDEBUG=y CONFIG_CMD_TPM=y CONFIG_CMD_MTDPARTS=y CONFIG_CMD_SPAWN=y +# CONFIG_OF_OMIT_DTB is not set CONFIG_ENV_IS_IN_FLASH=y CONFIG_AHCI=y CONFIG_SCSI_AHCI=y -- 2.43.0

