From 87b299813a8471a40edc1a8f74dd8e67044ff1e6 Mon Sep 17 00:00:00 2001 From: Sascha Hauer Date: Wed, 3 May 2023 16:36:59 +0200 Subject: [PATCH 1/3] drivers: imx_ele: factor out imx_ele_rng_get_random() plat_get_aslr_seed() open codes functionality for retrieving random data from the ELE. Factor out his code to a function for later reuse. Add support for being called with MMU enabled along the way. Signed-off-by: Sascha Hauer --- core/drivers/imx_ele.c | 66 +++++++++++++++++++++++++++++++++++------- 1 file changed, 56 insertions(+), 10 deletions(-) diff --git a/core/drivers/imx_ele.c b/core/drivers/imx_ele.c index 2ea1aff1f1c..8856065bf4e 100644 --- a/core/drivers/imx_ele.c +++ b/core/drivers/imx_ele.c @@ -8,9 +8,12 @@ #include #include #include +#include #include #include +#include #include +#include #include #include #include @@ -413,10 +416,22 @@ static TEE_Result imx_ele_rng_get_trng_state(void) return TEE_SUCCESS; } -unsigned long plat_get_aslr_seed(void) +/* + * Get random data from the EdgeLock Enclave. + * + * This function can be called when the MMU is off or on. + * virtual/physical address translation and cache maintenance + * is performed if needed. + * + * @buffer: data output + * @size: RNG data size + */ +static TEE_Result imx_ele_rng_get_random(void *buffer, size_t size) { TEE_Result res = TEE_ERROR_GENERIC; - uint64_t timeout = timeout_init_us(10 * 1000); + paddr_t pa; + void *buf = NULL; + struct rng_get_random_cmd { uint32_t addr_msb; uint32_t addr_lsb; @@ -429,6 +444,44 @@ unsigned long plat_get_aslr_seed(void) .header.tag = ELE_REQUEST_TAG, .header.command = ELE_CMD_RNG_GET, }; + + if (!buffer || !size) + return TEE_ERROR_BAD_PARAMETERS; + + if (cpu_mmu_enabled()) { + buf = alloc_cache_aligned(size); + if (!buf) + return TEE_ERROR_OUT_OF_MEMORY; + + cache_operation(TEE_CACHEFLUSH, buf, size); + + pa = virt_to_phys(buf); + } else { + pa = (paddr_t)buffer; + } + + reg_pair_from_64((uint64_t)pa, &cmd.addr_msb, &cmd.addr_lsb); + + cmd.size = (uint32_t)size; + + memcpy(msg.data.u8, &cmd, sizeof(cmd)); + update_crc(&msg); + + res = imx_ele_call(&msg); + + if (cpu_mmu_enabled()) { + cache_operation(TEE_CACHEINVALIDATE, buf, size); + if (res == TEE_SUCCESS) + memcpy(buffer, buf, size); + free(buf); + } + + return res; +} + +unsigned long plat_get_aslr_seed(void) +{ + uint64_t timeout = timeout_init_us(10 * 1000); unsigned long aslr __aligned(CACHELINE_SIZE) = 0; /* @@ -438,9 +491,6 @@ unsigned long plat_get_aslr_seed(void) */ assert(!cpu_mmu_enabled()); - reg_pair_from_64((uint64_t)&aslr, &cmd.addr_msb, &cmd.addr_lsb); - cmd.size = sizeof(aslr); - /* * Check the current TRNG state of the ELE. The TRNG must be * started with a command earlier in the boot to allow the TRNG @@ -450,11 +500,7 @@ unsigned long plat_get_aslr_seed(void) if (timeout_elapsed(timeout)) panic("ELE RNG is busy"); - memcpy(msg.data.u8, &cmd, sizeof(cmd)); - update_crc(&msg); - - res = imx_ele_call(&msg); - if (res) + if (imx_ele_rng_get_random((uint8_t *)&aslr, sizeof(aslr))) panic("Cannot retrieve random data from ELE"); return aslr; From 5aa7403e123fd539cc51a2bbcdb7d6e1d61999d9 Mon Sep 17 00:00:00 2001 From: Sascha Hauer Date: Fri, 24 Jan 2025 13:25:40 +0100 Subject: [PATCH 2/3] drivers: imx_ele: seed rng from ELE Implement plat_rng_init() for ELE equipped SoCs to make sure we have a non deterministic random seed. Signed-off-by: Sascha Hauer --- core/drivers/imx_ele.c | 24 ++++++++++++++++++++++++ 1 file changed, 24 insertions(+) diff --git a/core/drivers/imx_ele.c b/core/drivers/imx_ele.c index 8856065bf4e..5dd34df8d8d 100644 --- a/core/drivers/imx_ele.c +++ b/core/drivers/imx_ele.c @@ -2,6 +2,7 @@ /* * Copyright 2022-2023 NXP */ +#include #include #include #include @@ -16,6 +17,7 @@ #include #include #include +#include #include #include #include @@ -506,6 +508,28 @@ unsigned long plat_get_aslr_seed(void) return aslr; } +#ifdef CFG_WITH_SOFTWARE_PRNG +void plat_rng_init(void) +{ + TEE_Result res = TEE_ERROR_GENERIC; + uint8_t buf[32] = { }; + + res = imx_ele_rng_get_random(buf, sizeof(buf)); + if (res) { + EMSG("Failed to read RNG: %#" PRIx32, res); + panic(); + } + + res = crypto_rng_init(buf, sizeof(buf)); + if (res) { + EMSG("Failed to initialize RNG: %#" PRIx32, res); + panic(); + } + + IMSG("PRNG seeded from ELE RNG"); +} +#endif + int tee_otp_get_die_id(uint8_t *buffer, size_t len) { uint32_t session_handle = 0; From fbc768265aac155828450ff3ffe5f5c84627bfe8 Mon Sep 17 00:00:00 2001 From: Sascha Hauer Date: Fri, 24 Jan 2025 13:52:52 +0100 Subject: [PATCH 3/3] core: imx: Enable ELE by default on supported platforms The ELE provides the HUK on the SoCs which have it, so having support for it on these SoCs is really prudent. The ELE has been disabled by default in [1] and [2] because of: | There is only one MU to communicate with ELE, which cannot be | dedicated on OP-TEE side all the time. There may be ELE services | running on Linux side, which can cause conflict with OP-TEE. However, the ELE is currently only used for implementation of plat_rng_init() and tee_otp_get_hw_unique_key(). The former is used only during initialisation and the latter might be used during runtime, but the ELE is actually only accessed once and the HUK is then cached for later calls. Enable the ELE by default again to make the config for i.MX8ulp and i.MX9 more useful. [1] commit: 29b4cb6ef06f ("core: imx: disable ELE support on imx8ulp, imx93 by default") [2] commit: 136cc65fc184 ("core: imx: disable ELE support on i.MX91 by default") Signed-off-by: Sascha Hauer --- core/arch/arm/plat-imx/conf.mk | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/core/arch/arm/plat-imx/conf.mk b/core/arch/arm/plat-imx/conf.mk index 05a2243fab3..f2ce35590d8 100644 --- a/core/arch/arm/plat-imx/conf.mk +++ b/core/arch/arm/plat-imx/conf.mk @@ -228,7 +228,7 @@ CFG_TEE_CORE_NB_CORE ?= 2 $(call force,CFG_NXP_SNVS,n) $(call force,CFG_IMX_OCOTP,n) CFG_IMX_MU ?= y -CFG_IMX_ELE ?= n +CFG_IMX_ELE ?= y else ifneq (,$(filter $(PLATFORM_FLAVOR),$(mx93-flavorlist))) $(call force,CFG_MX93,y) $(call force,CFG_ARM64_core,y) @@ -241,7 +241,7 @@ $(call force,CFG_TZC380,n) $(call force,CFG_CRYPTO_DRIVER,n) $(call force,CFG_NXP_CAAM,n) CFG_IMX_MU ?= y -CFG_IMX_ELE ?= n +CFG_IMX_ELE ?= y else ifneq (,$(filter $(PLATFORM_FLAVOR),$(mx95-flavorlist))) $(call force,CFG_MX95,y) $(call force,CFG_ARM64_core,y) @@ -263,7 +263,7 @@ $(call force,CFG_IMX_OCOTP,n) $(call force,CFG_TZC380,n) $(call force,CFG_NXP_CAAM,n) CFG_IMX_MU ?= y -CFG_IMX_ELE ?= n +CFG_IMX_ELE ?= y else $(error Unsupported PLATFORM_FLAVOR "$(PLATFORM_FLAVOR)") endif