mirror of
https://source.denx.de/u-boot/u-boot.git
synced 2026-06-02 09:46:37 +03:00
Merge patch series "Add support for DT overlays handoff"
Raymond Mao <raymond.mao@linaro.org> says: The series include refactoring on bloblist and fdtdec to support handoff of multiple DT overlays and applying them into the DT base during setup. All changes are aligned to the spec update for supporting DT overlay handoff[1]. Notes for testing: Currently DT overlay is not yet enabled in TF-A, but with the test patches I provided for TF-A and OP-TEE build, importing a DT overlay blob file from QEMU to TF-A reserved memory is supported. Follow below instructions to build and run for test: $ repo init -u https://github.com/OP-TEE/manifest.git -m qemu_v8.xml Replace your local qemu_v8.xml with [2], which contains all necessary changes in both TF-A and OP-TEE build. $ repo sync $ cd build $ make toolchains $ make ARM_FIRMWARE_HANDOFF=y all Copy and rename your DT overlay blob as 'qemu_v8.dtb' into out/bin $ make ARM_FIRMWARE_HANDOFF=y run-only [1] Add Transfer Entry for Devicetree Overlay https://github.com/FirmwareHandoff/firmware_handoff/pull/74 [2] https://github.com/raymo200915/optee_manifest/blob/dt_overlay_handoff/qemu_v8.xml Link: https://lore.kernel.org/r/20250718141621.3147633-1-raymond.mao@linaro.org
This commit is contained in:
80
lib/fdtdec.c
80
lib/fdtdec.c
@@ -1709,6 +1709,83 @@ void fdtdec_setup_embed(void)
|
||||
gd->fdt_src = FDTSRC_EMBED;
|
||||
}
|
||||
|
||||
static int fdtdec_match_dto_compatible(const void *base, const void *dto)
|
||||
{
|
||||
const char *compat_base;
|
||||
const char *compat_dto;
|
||||
int len;
|
||||
|
||||
compat_base = (const char *)fdt_getprop(base, 0, "compatible", &len);
|
||||
if (!compat_base || len <= 0)
|
||||
return -ENOENT;
|
||||
|
||||
compat_dto = (const char *)fdt_getprop(dto, 0, "compatible", &len);
|
||||
if (!compat_dto || len <= 0)
|
||||
return -ENOENT;
|
||||
|
||||
if (strcmp(compat_base, compat_dto))
|
||||
return -EPERM;
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int fdtdec_apply_dto_blob(void **blob, __maybe_unused int size)
|
||||
{
|
||||
int ret;
|
||||
|
||||
ret = fdt_check_header(*blob);
|
||||
if (ret)
|
||||
return ret;
|
||||
|
||||
ret = fdtdec_match_dto_compatible(gd->fdt_blob, *blob);
|
||||
if (ret)
|
||||
return ret;
|
||||
|
||||
return fdt_overlay_apply_verbose((void *)gd->fdt_blob, *blob);
|
||||
}
|
||||
|
||||
static int fdtdec_apply_bloblist_dtos(void)
|
||||
{
|
||||
int ret;
|
||||
struct fdt_header *live_fdt;
|
||||
int blob_size;
|
||||
size_t padded_size, max_size;
|
||||
|
||||
if (!CONFIG_IS_ENABLED(OF_LIBFDT_OVERLAY) ||
|
||||
!CONFIG_IS_ENABLED(BLOBLIST))
|
||||
return 0;
|
||||
|
||||
/* Get the total space reserved for FDT in blob */
|
||||
live_fdt = bloblist_get_blob(BLOBLISTT_CONTROL_FDT, &blob_size);
|
||||
if (live_fdt != gd->fdt_blob)
|
||||
return -ENOENT;
|
||||
|
||||
/* Calculate the allowed padded size */
|
||||
padded_size = fdt_totalsize(live_fdt) + CONFIG_SYS_FDT_PAD;
|
||||
max_size = bloblist_get_total_size() - bloblist_get_size() + blob_size;
|
||||
if (padded_size > max_size)
|
||||
padded_size = max_size;
|
||||
|
||||
/* Resize if the current space is not sufficient */
|
||||
if (blob_size < padded_size) {
|
||||
ret = bloblist_resize(BLOBLISTT_CONTROL_FDT, padded_size);
|
||||
if (ret)
|
||||
return ret;
|
||||
|
||||
ret = fdt_open_into(live_fdt, live_fdt, padded_size);
|
||||
if (ret)
|
||||
return ret;
|
||||
}
|
||||
|
||||
ret = bloblist_apply_blobs(BLOBLISTT_FDT_OVERLAY, fdtdec_apply_dto_blob);
|
||||
if (ret)
|
||||
return ret;
|
||||
|
||||
/* Shink the blob to the actual FDT size */
|
||||
fdt_pack(live_fdt);
|
||||
return bloblist_resize(BLOBLISTT_CONTROL_FDT, fdt_totalsize(live_fdt));
|
||||
}
|
||||
|
||||
int fdtdec_setup(void)
|
||||
{
|
||||
int ret = -ENOENT;
|
||||
@@ -1730,6 +1807,9 @@ int fdtdec_setup(void)
|
||||
gd->fdt_src = FDTSRC_BLOBLIST;
|
||||
log_debug("Devicetree is in bloblist at %p\n",
|
||||
gd->fdt_blob);
|
||||
ret = fdtdec_apply_bloblist_dtos();
|
||||
if (ret)
|
||||
return ret;
|
||||
goto setup_fdt;
|
||||
} else {
|
||||
log_debug("No FDT found in bloblist\n");
|
||||
|
||||
Reference in New Issue
Block a user