mail archive of the barebox mailing list
 help / color / mirror / Atom feed
* [PATCH] ARM: i.MX8M: enable MMU in PBL around fw-external BL32 verify
@ 2026-06-16 14:49 Johannes Schneider
  2026-06-16 14:49 ` [PATCH] crypto: sha256: PBL multi-block transform via ARMv8 Crypto Extensions Crypto Extensions Johannes Schneider
  0 siblings, 1 reply; 2+ messages in thread
From: Johannes Schneider @ 2026-06-16 14:49 UTC (permalink / raw)
  To: barebox; +Cc: Johannes Schneider

The BL32 fw-external blob is loaded into DRAM by the PBL and then
SHA-256-verified inside get_builtin_firmware_ext(). The verify runs
in PBL phase 1 with the MMU off and D-cache cold, walking ~720 KiB
through uncached DRAM accesses; on a Cortex-A53 this costs around
2 s of pre-BL31 wall-clock on every boot.

The verify is the only thing anchoring the BL32 content to the
signed PBL: HABv4 on i.MX8M only signs and loads what fits in
on-chip SRAM (= the PBL), and BL31/BL32 reach DRAM via PBL-driven
copies, so skipping the SHA-256 would be a security regression.

Turn on MMU + D-cache once the DRAM is populated and right before
the SHA-256 verify + BL31/BL32 memcpy run, and drop the MMU again
right before the BL31 entry (BL31 expects MMU off). Mirrors the
Rockchip handling in commits f2ae1a4a85 ("ARM: rockchip: atf:
enable MMU in PBL") and a0ef3a1b5c ("ARM: rockchip: atf: pass
correct memsize to mmu_early_enable()").

Measured on i.MX8MM and i.MX8MP (Cortex-A53, ~720 KiB BL32 blob):
the BL32 verify drops from ~2 s to ~300 ms (generic-C SHA-256 in
both cases, the difference is the D-cache state) and the BL31
early-init also benefits from the warm cache (~200 ms saved).

Assisted-by: Claude:claude-opus-4-7
Signed-off-by: Johannes Schneider <johannes.schneider@leica-geosystems.com>
---
--- a/arch/arm/mach-imx/atf.c
+++ b/arch/arm/mach-imx/atf.c
@@ -20,6 +20,7 @@
 #include <mach/imx/xload.h>
 #include <mach/imx/snvs.h>
 #include <pbl.h>
+#include <asm/mmu.h>
 
 static void imx_adjust_optee_memory(void **bl32, void **bl32_image, size_t *bl32_size)
 {
@@ -187,6 +188,9 @@
 		     "r" (tfa_dest - 16) :
 		     "cc");
 
+	/* BL31 expects MMU off. */
+	mmu_disable();
+
 	/*
 	 * If enabled the bl_params are passed via x0 to the TF-A, except for
 	 * the i.MX8MQ which doesn't support bl_params yet.
@@ -284,6 +288,12 @@
 	imx8m_setup_snvs();
 	imx8mm_load_bl33(bl33);
 
+	/* Cache DRAM for the BL32 verify + BL31/BL32 memcpy that follow. */
+	mmu_early_enable(MX8M_DDR_CSD1_BASE_ADDR,
+			 imx8m_barebox_earlymem_size(32),
+			 MX8M_DDR_CSD1_BASE_ADDR +
+			 imx8m_barebox_earlymem_size(32) - OPTEE_SIZE);
+
 	if (IS_ENABLED(CONFIG_FIRMWARE_IMX8MM_OPTEE)) {
 		get_builtin_firmware_ext(imx8mm_bl32_bin, bl33, &bl32, &bl32_size);
 		get_builtin_firmware(imx8mm_bl31_bin_optee, &bl31, &bl31_size);
@@ -349,6 +359,12 @@
 	imx8m_setup_snvs();
 	imx8mp_load_bl33(bl33);
 
+	/* Cache DRAM for the BL32 verify + BL31/BL32 memcpy that follow. */
+	mmu_early_enable(MX8M_DDR_CSD1_BASE_ADDR,
+			 imx8m_barebox_earlymem_size(32),
+			 MX8M_DDR_CSD1_BASE_ADDR +
+			 imx8m_barebox_earlymem_size(32) - OPTEE_SIZE);
+
 	if (IS_ENABLED(CONFIG_FIRMWARE_IMX8MP_OPTEE)) {
 		get_builtin_firmware_ext(imx8mp_bl32_bin, bl33, &bl32, &bl32_size);
 		get_builtin_firmware(imx8mp_bl31_bin_optee, &bl31, &bl31_size);
@@ -414,6 +430,12 @@
 	imx8m_setup_snvs();
 	imx8mn_load_bl33(bl33);
 
+	/* Cache DRAM for the BL32 verify + BL31/BL32 memcpy that follow. */
+	mmu_early_enable(MX8M_DDR_CSD1_BASE_ADDR,
+			 imx8m_barebox_earlymem_size(16),
+			 MX8M_DDR_CSD1_BASE_ADDR +
+			 imx8m_barebox_earlymem_size(16) - OPTEE_SIZE);
+
 	if (IS_ENABLED(CONFIG_FIRMWARE_IMX8MN_OPTEE)) {
 		get_builtin_firmware_ext(imx8mn_bl32_bin, bl33, &bl32, &bl32_size);
 		get_builtin_firmware(imx8mn_bl31_bin_optee, &bl31, &bl31_size);
@@ -473,6 +495,12 @@
 	imx8m_setup_snvs();
 	imx8mq_load_bl33(bl33);
 
+	/* Cache DRAM for the BL32 verify + BL31/BL32 memcpy that follow. */
+	mmu_early_enable(MX8M_DDR_CSD1_BASE_ADDR,
+			 imx8m_barebox_earlymem_size(32),
+			 MX8M_DDR_CSD1_BASE_ADDR +
+			 imx8m_barebox_earlymem_size(32) - OPTEE_SIZE);
+
 	if (IS_ENABLED(CONFIG_FIRMWARE_IMX8MQ_OPTEE)) {
 		get_builtin_firmware_ext(imx8mq_bl32_bin, bl33, &bl32, &bl32_size);
 		get_builtin_firmware(imx8mq_bl31_bin_optee, &bl31, &bl31_size);



^ permalink raw reply	[flat|nested] 2+ messages in thread

end of thread, other threads:[~2026-06-16 15:01 UTC | newest]

Thread overview: 2+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2026-06-16 14:49 [PATCH] ARM: i.MX8M: enable MMU in PBL around fw-external BL32 verify Johannes Schneider
2026-06-16 14:49 ` [PATCH] crypto: sha256: PBL multi-block transform via ARMv8 Crypto Extensions Crypto Extensions Johannes Schneider

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox