diff --git a/plat/allwinner/common/include/sunxi_private.h b/plat/allwinner/common/include/sunxi_private.h index b68d23f3d..6cf46704f 100644 --- a/plat/allwinner/common/include/sunxi_private.h +++ b/plat/allwinner/common/include/sunxi_private.h @@ -41,4 +41,12 @@ void sunxi_set_gpio_out(char port, int pin, bool level_high); int sunxi_init_platform_r_twi(uint16_t socid, bool use_rsb); void sunxi_execute_arisc_code(uint32_t *code, size_t size, uint16_t param); +#ifdef SUNXI_BL31_IN_DRAM +void sunxi_prepare_dtb(void *fdt); +#else +static inline void sunxi_prepare_dtb(void *fdt) +{ +} +#endif + #endif /* SUNXI_PRIVATE_H */ diff --git a/plat/allwinner/common/sunxi_bl31_setup.c b/plat/allwinner/common/sunxi_bl31_setup.c index d3c450762..72bfbd966 100644 --- a/plat/allwinner/common/sunxi_bl31_setup.c +++ b/plat/allwinner/common/sunxi_bl31_setup.c @@ -13,6 +13,8 @@ #include #include #include +#include +#include #include #include #include @@ -175,6 +177,8 @@ void bl31_platform_setup(void) sunxi_pmic_setup(soc_id, fdt); + sunxi_prepare_dtb(fdt); + INFO("BL31: Platform setup done\n"); } diff --git a/plat/allwinner/common/sunxi_common.c b/plat/allwinner/common/sunxi_common.c index 27321cccd..d47d3605b 100644 --- a/plat/allwinner/common/sunxi_common.c +++ b/plat/allwinner/common/sunxi_common.c @@ -26,7 +26,7 @@ static const mmap_region_t sunxi_mmap[PLATFORM_MMAP_REGIONS + 1] = { MAP_REGION(SUNXI_DRAM_BASE, SUNXI_DRAM_VIRT_BASE, SUNXI_DRAM_SEC_SIZE, MT_RW_DATA | MT_SECURE), MAP_REGION(PRELOADED_BL33_BASE, SUNXI_BL33_VIRT_BASE, - SUNXI_DRAM_MAP_SIZE, MT_RO_DATA | MT_NS), + SUNXI_DRAM_MAP_SIZE, MT_RW_DATA | MT_NS), {}, }; diff --git a/plat/allwinner/sun50i_h616/platform.mk b/plat/allwinner/sun50i_h616/platform.mk index 1003aab7c..fc09af7c1 100644 --- a/plat/allwinner/sun50i_h616/platform.mk +++ b/plat/allwinner/sun50i_h616/platform.mk @@ -17,6 +17,8 @@ ifeq (${SUNXI_PSCI_USE_SCPI}, 1) endif BL31_SOURCES += drivers/allwinner/axp/axp805.c \ - drivers/allwinner/sunxi_rsb.c + drivers/allwinner/sunxi_rsb.c \ + common/fdt_fixup.c \ + ${AW_PLAT}/${PLAT}/prepare_dtb.c $(eval $(call add_define,SUNXI_BL31_IN_DRAM)) diff --git a/plat/allwinner/sun50i_h616/prepare_dtb.c b/plat/allwinner/sun50i_h616/prepare_dtb.c new file mode 100644 index 000000000..e94b0b4be --- /dev/null +++ b/plat/allwinner/sun50i_h616/prepare_dtb.c @@ -0,0 +1,43 @@ +/* + * Copyright (c) 2021, ARM Limited. All rights reserved. + * + * SPDX-License-Identifier: BSD-3-Clause + */ + +#include + +#include +#include +#include + +#include + +void sunxi_prepare_dtb(void *fdt) +{ + int ret; + + if (fdt == NULL || fdt_check_header(fdt) != 0) { + return; + } + ret = fdt_open_into(fdt, fdt, 0x100000); + if (ret < 0) { + ERROR("Preparing devicetree at %p: error %d\n", fdt, ret); + return; + } + + /* Reserve memory used by Trusted Firmware. */ + if (fdt_add_reserved_memory(fdt, "tf-a@40000000", BL31_BASE, + BL31_LIMIT - BL31_BASE)) { + WARN("Failed to add reserved memory nodes to DT.\n"); + return; + } + + ret = fdt_pack(fdt); + if (ret < 0) { + ERROR("Failed to pack devicetree at %p: error %d\n", + fdt, ret); + } else { + clean_dcache_range((uintptr_t)fdt, fdt_blob_size(fdt)); + INFO("Changed devicetree to reserve BL31 memory.\n"); + } +}