OPTEE-OS-STM32MP: 3.16.0-stm32mp-r2.1
Change-Id: Ibb1ea4150d8102d80865f1fef87ecc0309b440d1 Signed-off-by: Lionel VITTE <lionel.vitte@st.com>
This commit is contained in:
parent
b0bb59f9c2
commit
91c9734966
|
|
@ -9,13 +9,14 @@ SRC_URI += " \
|
|||
file://fonts.tar.gz;subdir=git;name=fonts \
|
||||
file://0001-3.16.0-stm32mp-r1.patch \
|
||||
file://0002-3.16.0-stm32mp-r2.patch \
|
||||
file://0003-3.16.0-stm32mp-r2.1.patch \
|
||||
"
|
||||
|
||||
SRC_URI[fonts.sha256sum] = "4941e8bb6d8ac377838e27b214bf43008c496a24a8f897e0b06433988cbd53b2"
|
||||
|
||||
OPTEE_VERSION = "3.16.0"
|
||||
OPTEE_SUBVERSION = "stm32mp"
|
||||
OPTEE_RELEASE = "r2"
|
||||
OPTEE_RELEASE = "r2.1"
|
||||
|
||||
PV = "${OPTEE_VERSION}-${OPTEE_SUBVERSION}-${OPTEE_RELEASE}"
|
||||
|
||||
|
|
@ -50,7 +51,7 @@ include ${@oe.utils.ifelse(d.getVar('ST_ARCHIVER_ENABLE') == '1', 'optee-os-stm3
|
|||
BBCLASSEXTEND = "devupstream:target"
|
||||
|
||||
SRC_URI:class-devupstream = "git://github.com/STMicroelectronics/optee_os.git;protocol=https;branch=${ARCHIVER_ST_BRANCH}"
|
||||
SRCREV:class-devupstream = "0f631da995da50fe7e19e0b7291032d77f7048bc"
|
||||
SRCREV:class-devupstream = "b8750c4600166f0019a8c1cf35362b1889840ec3"
|
||||
|
||||
# ---------------------------------
|
||||
# Configure default preference to manage dynamic selection between tarball and github
|
||||
|
|
|
|||
|
|
@ -0,0 +1,848 @@
|
|||
From 40bea7e6dd305b8fec278fa56bc38eed127ce946 Mon Sep 17 00:00:00 2001
|
||||
From: Lionel VITTE <lionel.vitte@st.com>
|
||||
Date: Mon, 3 Jul 2023 10:30:06 +0200
|
||||
Subject: [PATCH] 3.16.0-stm32mp-r2.1-rc1
|
||||
|
||||
---
|
||||
core/arch/arm/dts/stm32mp135f-dk.dts | 4 +-
|
||||
core/arch/arm/plat-stm32mp1/conf.mk | 4 +-
|
||||
.../arm/plat-stm32mp1/drivers/stm32mp1_pmic.c | 151 +++++++++++++-----
|
||||
.../plat-stm32mp1/drivers/stm32mp1_pwr_irq.c | 78 ++++++---
|
||||
core/arch/arm/plat-stm32mp1/main.c | 4 +-
|
||||
core/arch/arm/plat-stm32mp1/pm/context.c | 12 +-
|
||||
core/arch/arm/plat-stm32mp1/pm/low_power.c | 15 +-
|
||||
core/drivers/crypto/stm32/stm32_saes.c | 7 +
|
||||
core/drivers/regulator/core.c | 5 +
|
||||
core/drivers/stm32_iwdg.c | 18 ++-
|
||||
core/drivers/stm32_rng.c | 12 +-
|
||||
core/drivers/stm32_uart.c | 4 +-
|
||||
core/include/drivers/stpmic1.h | 35 ----
|
||||
core/include/kernel/huk_subkey.h | 5 +
|
||||
core/kernel/huk_subkey.c | 16 +-
|
||||
.../devicetree/bindings/mfd/st,stpmic1.yaml | 51 ++++++
|
||||
16 files changed, 293 insertions(+), 128 deletions(-)
|
||||
|
||||
diff --git a/core/arch/arm/dts/stm32mp135f-dk.dts b/core/arch/arm/dts/stm32mp135f-dk.dts
|
||||
index 4400b2b13..710446101 100644
|
||||
--- a/core/arch/arm/dts/stm32mp135f-dk.dts
|
||||
+++ b/core/arch/arm/dts/stm32mp135f-dk.dts
|
||||
@@ -9,6 +9,7 @@
|
||||
#include <dt-bindings/clock/stm32mp13-clksrc.h>
|
||||
#include <dt-bindings/gpio/gpio.h>
|
||||
#include <dt-bindings/gpio/stm32mp_gpio.h>
|
||||
+#include <dt-bindings/mfd/st,stpmic1.h>
|
||||
#include <dt-bindings/power/stm32mp1-power.h>
|
||||
#include <dt-bindings/rtc/rtc-stm32.h>
|
||||
#include <dt-bindings/soc/stm32mp-tzc400-macro.h>
|
||||
@@ -192,7 +193,8 @@
|
||||
reg = <0x33>;
|
||||
status = "okay";
|
||||
st,wakeup-pin-number = <1>;
|
||||
- st,notif-it-id = <0>;
|
||||
+ st,pmic-it-id = <IT_PONKEY_F IT_PONKEY_R>;
|
||||
+ st,notif-it-id = <0 2>;
|
||||
|
||||
regulators {
|
||||
compatible = "st,stpmic1-regulators";
|
||||
diff --git a/core/arch/arm/plat-stm32mp1/conf.mk b/core/arch/arm/plat-stm32mp1/conf.mk
|
||||
index 6c959d4bc..05229e61e 100644
|
||||
--- a/core/arch/arm/plat-stm32mp1/conf.mk
|
||||
+++ b/core/arch/arm/plat-stm32mp1/conf.mk
|
||||
@@ -310,10 +310,8 @@ CFG_ENABLE_EMBEDDED_TESTS ?= y
|
||||
CFG_WITH_STATS ?= y
|
||||
CFG_WERROR ?= y
|
||||
|
||||
-# Enable to allow debug
|
||||
-ifeq ($(CFG_TEE_CORE_DEBUG),y)
|
||||
+# Enable OTP update with BSEC driver
|
||||
CFG_STM32_BSEC_WRITE ?= y
|
||||
-endif
|
||||
|
||||
# Default disable some support for pager memory size constraint
|
||||
ifeq ($(CFG_WITH_PAGER),y)
|
||||
diff --git a/core/arch/arm/plat-stm32mp1/drivers/stm32mp1_pmic.c b/core/arch/arm/plat-stm32mp1/drivers/stm32mp1_pmic.c
|
||||
index 4eda619cf..653ac4f7d 100644
|
||||
--- a/core/arch/arm/plat-stm32mp1/drivers/stm32mp1_pmic.c
|
||||
+++ b/core/arch/arm/plat-stm32mp1/drivers/stm32mp1_pmic.c
|
||||
@@ -12,6 +12,7 @@
|
||||
#include <drivers/stm32mp1_pmic.h>
|
||||
#include <drivers/stm32mp1_pwr.h>
|
||||
#include <drivers/stpmic1.h>
|
||||
+#include <dt-bindings/mfd/st,stpmic1.h>
|
||||
#include <io.h>
|
||||
#include <keep.h>
|
||||
#include <kernel/boot.h>
|
||||
@@ -26,6 +27,7 @@
|
||||
#include <platform_config.h>
|
||||
#include <stdbool.h>
|
||||
#include <stm32_util.h>
|
||||
+#include <sys/queue.h>
|
||||
#include <trace.h>
|
||||
#include <util.h>
|
||||
|
||||
@@ -42,6 +44,17 @@
|
||||
static struct i2c_handle_s *i2c_pmic_handle;
|
||||
static uint32_t pmic_i2c_addr;
|
||||
|
||||
+struct pmic_it_handle_s {
|
||||
+ uint8_t pmic_reg;
|
||||
+ uint8_t pmic_bit;
|
||||
+ uint8_t notif_id;
|
||||
+
|
||||
+ SLIST_ENTRY(pmic_it_handle_s) link;
|
||||
+};
|
||||
+
|
||||
+static SLIST_HEAD(pmic_it_handle_head, pmic_it_handle_s) pmic_it_handle_list =
|
||||
+ SLIST_HEAD_INITIALIZER(pmic_it_handle_list);
|
||||
+
|
||||
/* CPU voltage supplier if found */
|
||||
static char cpu_supply_name[PMIC_REGU_SUPPLY_NAME_LEN];
|
||||
|
||||
@@ -508,11 +521,10 @@ static void register_non_secure_pmic(void)
|
||||
}
|
||||
}
|
||||
|
||||
-static enum itr_return stpmic1_irq_handler(struct itr_handler *handler)
|
||||
+static enum itr_return stpmic1_irq_handler(struct itr_handler *handler __unused)
|
||||
{
|
||||
uint8_t read_val = 0U;
|
||||
unsigned int i = 0U;
|
||||
- uint32_t *it_id = handler->data;
|
||||
|
||||
FMSG("Stpmic1 irq handler");
|
||||
|
||||
@@ -523,16 +535,22 @@ static enum itr_return stpmic1_irq_handler(struct itr_handler *handler)
|
||||
panic();
|
||||
|
||||
if (read_val) {
|
||||
+ struct pmic_it_handle_s *prv = NULL;
|
||||
+
|
||||
FMSG("Stpmic1 irq pending %u: %#"PRIx8, i, read_val);
|
||||
|
||||
if (stpmic1_register_write(ITCLEARLATCH1_REG + i,
|
||||
read_val))
|
||||
panic();
|
||||
|
||||
- /* forward falling interrupt to non-secure */
|
||||
- if (i == 0 && (read_val & BIT(IT_PONKEY_F)))
|
||||
- if (it_id)
|
||||
- notif_send_it(*it_id);
|
||||
+ SLIST_FOREACH(prv, &pmic_it_handle_list, link)
|
||||
+ if ((prv->pmic_reg == ITCLEARMASK1_REG + i) &&
|
||||
+ (read_val & BIT(prv->pmic_bit))) {
|
||||
+ FMSG("STPMIC1 send notif %u",
|
||||
+ prv->notif_id);
|
||||
+
|
||||
+ notif_send_it(prv->notif_id);
|
||||
+ }
|
||||
}
|
||||
}
|
||||
|
||||
@@ -587,57 +605,104 @@ static void initialize_pmic(const void *fdt, int pmic_node)
|
||||
stm32mp_put_pmic();
|
||||
}
|
||||
|
||||
-static TEE_Result stm32_pmic_probe(const void *fdt, int node,
|
||||
- const void *compat_data __unused)
|
||||
+static TEE_Result stm32_pmic_init_it(const void *fdt, int node)
|
||||
{
|
||||
- TEE_Result res = TEE_SUCCESS;
|
||||
- const fdt32_t *cuint = NULL;
|
||||
+ TEE_Result res = TEE_ERROR_GENERIC;
|
||||
+ const uint32_t *notif_ids = NULL;
|
||||
+ int nb_notif = 0;
|
||||
+ size_t pwr_it = 0;
|
||||
struct itr_handler *hdl = NULL;
|
||||
- size_t it = 0;
|
||||
- uint32_t *it_id = NULL;
|
||||
+ const fdt32_t *cuint = NULL;
|
||||
|
||||
- res = i2c_dt_get_by_subnode(fdt, node, &i2c_pmic_handle);
|
||||
- if (res)
|
||||
- return res;
|
||||
+ cuint = fdt_getprop(fdt, node, "st,wakeup-pin-number", NULL);
|
||||
+ if (!cuint) {
|
||||
+ IMSG("Missing wake-up pin description");
|
||||
+ return TEE_SUCCESS;
|
||||
+ }
|
||||
|
||||
- initialize_pmic(fdt, node);
|
||||
+ pwr_it = fdt32_to_cpu(*cuint) - 1U;
|
||||
|
||||
- if (IS_ENABLED(CFG_STM32MP13)) {
|
||||
- cuint = fdt_getprop(fdt, node, "st,wakeup-pin-number", NULL);
|
||||
- if (!cuint) {
|
||||
- IMSG("Missing wake-up pin description");
|
||||
- return TEE_SUCCESS;
|
||||
- }
|
||||
+ notif_ids = fdt_getprop(fdt, node, "st,notif-it-id", &nb_notif);
|
||||
+ if (!notif_ids)
|
||||
+ return TEE_ERROR_ITEM_NOT_FOUND;
|
||||
|
||||
- it = fdt32_to_cpu(*cuint) - 1U;
|
||||
+ if (nb_notif > 0) {
|
||||
+ struct pmic_it_handle_s *prv = NULL;
|
||||
+ unsigned int i = 0;
|
||||
+ const uint32_t *pmic_its = NULL;
|
||||
+ int nb_it = 0;
|
||||
|
||||
- cuint = fdt_getprop(fdt, node, "st,notif-it-id", NULL);
|
||||
- if (cuint) {
|
||||
- it_id = calloc(1, sizeof(it_id));
|
||||
- if (!it_id)
|
||||
- return TEE_ERROR_OUT_OF_MEMORY;
|
||||
+ pmic_its = fdt_getprop(fdt, node, "st,pmic-it-id", &nb_it);
|
||||
+ if (!pmic_its)
|
||||
+ return TEE_ERROR_ITEM_NOT_FOUND;
|
||||
|
||||
- *it_id = fdt32_to_cpu(*cuint);
|
||||
- }
|
||||
+ if (nb_it != nb_notif)
|
||||
+ panic("st,notif-it-id incorrect description");
|
||||
|
||||
- res = stm32mp1_pwr_itr_alloc_add(it, stpmic1_irq_handler,
|
||||
- PWR_WKUP_FLAG_FALLING |
|
||||
- PWR_WKUP_FLAG_THREADED,
|
||||
- it_id, &hdl);
|
||||
- if (res)
|
||||
- panic("pmic: Couldn't allocate itr");
|
||||
+ for (i = 0; i < (nb_notif / sizeof(uint32_t)); i++) {
|
||||
+ uint8_t val = 0;
|
||||
+ uint8_t pmic_it = 0;
|
||||
|
||||
- stm32mp1_pwr_itr_enable(hdl->it);
|
||||
+ prv = calloc(1, sizeof(*prv));
|
||||
+ if (!prv)
|
||||
+ panic("pmic: Couldn't allocate pmic it");
|
||||
|
||||
- /* Enable ponkey irq */
|
||||
- stm32mp_get_pmic();
|
||||
- if (stpmic1_register_write(ITCLEARMASK1_REG,
|
||||
- BIT(IT_PONKEY_F) | BIT(IT_PONKEY_R)))
|
||||
- panic();
|
||||
+ pmic_it = fdt32_to_cpu(pmic_its[i]);
|
||||
+
|
||||
+ assert(pmic_it <= IT_SWIN_R);
|
||||
+
|
||||
+ prv->pmic_reg = ITCLEARMASK1_REG + pmic_it / U(8);
|
||||
+ prv->pmic_bit = pmic_it % U(8);
|
||||
+ prv->notif_id = fdt32_to_cpu(notif_ids[i]);
|
||||
+
|
||||
+ SLIST_INSERT_HEAD(&pmic_it_handle_list, prv, link);
|
||||
+
|
||||
+ stm32mp_get_pmic();
|
||||
|
||||
- stm32mp_put_pmic();
|
||||
+ /* Enable requested interrupt */
|
||||
+ if (stpmic1_register_read(prv->pmic_reg, &val))
|
||||
+ panic();
|
||||
+
|
||||
+ val |= BIT(prv->pmic_bit);
|
||||
+
|
||||
+ if (stpmic1_register_write(prv->pmic_reg, val))
|
||||
+ panic();
|
||||
+
|
||||
+ stm32mp_put_pmic();
|
||||
+ }
|
||||
+
|
||||
+ SLIST_FOREACH(prv, &pmic_it_handle_list, link) {
|
||||
+ FMSG("STPMIC1 forwards irq reg:%u bit:%u as notif:%u",
|
||||
+ prv->pmic_reg, prv->pmic_bit, prv->notif_id);
|
||||
+ }
|
||||
}
|
||||
|
||||
+ res = stm32mp1_pwr_itr_alloc_add(pwr_it, stpmic1_irq_handler,
|
||||
+ PWR_WKUP_FLAG_FALLING |
|
||||
+ PWR_WKUP_FLAG_THREADED,
|
||||
+ NULL, &hdl);
|
||||
+ if (res)
|
||||
+ panic("pmic: Couldn't allocate itr");
|
||||
+
|
||||
+ stm32mp1_pwr_itr_enable(hdl->it);
|
||||
+
|
||||
+ return res;
|
||||
+}
|
||||
+
|
||||
+static TEE_Result stm32_pmic_probe(const void *fdt, int node,
|
||||
+ const void *compat_data __unused)
|
||||
+{
|
||||
+ TEE_Result res = TEE_SUCCESS;
|
||||
+
|
||||
+ res = i2c_dt_get_by_subnode(fdt, node, &i2c_pmic_handle);
|
||||
+ if (res)
|
||||
+ return res;
|
||||
+
|
||||
+ initialize_pmic(fdt, node);
|
||||
+
|
||||
+ if (IS_ENABLED(CFG_STM32MP13))
|
||||
+ res = stm32_pmic_init_it(fdt, node);
|
||||
+
|
||||
return res;
|
||||
}
|
||||
|
||||
diff --git a/core/arch/arm/plat-stm32mp1/drivers/stm32mp1_pwr_irq.c b/core/arch/arm/plat-stm32mp1/drivers/stm32mp1_pwr_irq.c
|
||||
index 0913e9151..ca2761a81 100644
|
||||
--- a/core/arch/arm/plat-stm32mp1/drivers/stm32mp1_pwr_irq.c
|
||||
+++ b/core/arch/arm/plat-stm32mp1/drivers/stm32mp1_pwr_irq.c
|
||||
@@ -13,6 +13,7 @@
|
||||
#include <kernel/dt.h>
|
||||
#include <kernel/notif.h>
|
||||
#include <kernel/panic.h>
|
||||
+#include <kernel/spinlock.h>
|
||||
#include <libfdt.h>
|
||||
#include <platform_config.h>
|
||||
#include <stm32_util.h>
|
||||
@@ -47,6 +48,7 @@ struct stm32_pwr_data {
|
||||
struct itr_handler *gic_hdl;
|
||||
bool threaded[PWR_NB_WAKEUPPINS];
|
||||
bool pending[PWR_NB_WAKEUPPINS];
|
||||
+ unsigned int spinlock;
|
||||
};
|
||||
|
||||
static struct stm32_pwr_data *pwr_data;
|
||||
@@ -148,6 +150,7 @@ static TEE_Result
|
||||
stm32_pwr_irq_set_pull_config(size_t it, enum wkup_pull_setting config)
|
||||
{
|
||||
struct stm32_pwr_data *priv = pwr_data;
|
||||
+ uint32_t exceptions = 0;
|
||||
|
||||
VERBOSE_PWR("irq:%zu pull config:0%#"PRIx32, it, config);
|
||||
|
||||
@@ -156,29 +159,59 @@ stm32_pwr_irq_set_pull_config(size_t it, enum wkup_pull_setting config)
|
||||
return TEE_ERROR_GENERIC;
|
||||
}
|
||||
|
||||
+ exceptions = cpu_spin_lock_xsave(&priv->spinlock);
|
||||
+
|
||||
io_mask32(priv->base + WKUPCR,
|
||||
(config & WKUP_PULL_MASK) << (WKUP_PULL_SHIFT + it * 2),
|
||||
(WKUP_PULL_MASK) << (WKUP_PULL_SHIFT + it * 2));
|
||||
|
||||
+ cpu_spin_unlock_xrestore(&priv->spinlock, exceptions);
|
||||
+
|
||||
return TEE_SUCCESS;
|
||||
}
|
||||
|
||||
-static TEE_Result
|
||||
-stm32_pwr_irq_set_trig(size_t it, enum pwr_wkup_flags trig)
|
||||
+static void stm32mp1_pwr_itr_enable_nolock(size_t it)
|
||||
+{
|
||||
+ struct stm32_pwr_data *priv = pwr_data;
|
||||
+
|
||||
+ VERBOSE_PWR("Pwr irq enable");
|
||||
+
|
||||
+ if (IS_ENABLED(CFG_STM32_EXTI))
|
||||
+ stm32_exti_enable_wake(PWR_EXTI_WKUP1 + it);
|
||||
+
|
||||
+ io_setbits32(priv->base + MPUWKUPENR, BIT(it));
|
||||
+}
|
||||
+
|
||||
+static void stm32mp1_pwr_itr_disable_nolock(size_t it)
|
||||
+{
|
||||
+ struct stm32_pwr_data *priv = pwr_data;
|
||||
+
|
||||
+ VERBOSE_PWR("Pwr irq disable");
|
||||
+
|
||||
+ io_clrbits32(priv->base + MPUWKUPENR, BIT(it));
|
||||
+
|
||||
+ if (IS_ENABLED(CFG_STM32_EXTI))
|
||||
+ stm32_exti_disable_wake(PWR_EXTI_WKUP1 + it);
|
||||
+}
|
||||
+
|
||||
+static TEE_Result stm32_pwr_irq_set_trig(size_t it, enum pwr_wkup_flags trig)
|
||||
{
|
||||
struct stm32_pwr_data *priv = pwr_data;
|
||||
+ uint32_t exceptions = 0;
|
||||
uint32_t wkupcr = 0;
|
||||
int en = 0;
|
||||
|
||||
VERBOSE_PWR("irq:%zu trig:%#"PRIx32, it, trig);
|
||||
|
||||
+ exceptions = cpu_spin_lock_xsave(&priv->spinlock);
|
||||
+
|
||||
en = io_read32(priv->base + MPUWKUPENR) & BIT(it);
|
||||
/*
|
||||
* Reference manual request to disable the wakeup pin while
|
||||
- * changing the edge detection setting
|
||||
+ * changing the edge detection setting.
|
||||
*/
|
||||
if (en)
|
||||
- stm32mp1_pwr_itr_disable(it);
|
||||
+ stm32mp1_pwr_itr_disable_nolock(it);
|
||||
|
||||
wkupcr = io_read32(priv->base + WKUPCR);
|
||||
switch (trig) {
|
||||
@@ -195,7 +228,9 @@ stm32_pwr_irq_set_trig(size_t it, enum pwr_wkup_flags trig)
|
||||
io_write32(priv->base + WKUPCR, wkupcr);
|
||||
|
||||
if (en)
|
||||
- stm32mp1_pwr_itr_enable(it);
|
||||
+ stm32mp1_pwr_itr_enable_nolock(it);
|
||||
+
|
||||
+ cpu_spin_unlock_xrestore(&priv->spinlock, exceptions);
|
||||
|
||||
return TEE_SUCCESS;
|
||||
}
|
||||
@@ -203,25 +238,21 @@ stm32_pwr_irq_set_trig(size_t it, enum pwr_wkup_flags trig)
|
||||
void stm32mp1_pwr_itr_enable(size_t it)
|
||||
{
|
||||
struct stm32_pwr_data *priv = pwr_data;
|
||||
+ uint32_t exceptions = 0;
|
||||
|
||||
- VERBOSE_PWR("Pwr irq enable");
|
||||
-
|
||||
- if (IS_ENABLED(CFG_STM32_EXTI))
|
||||
- stm32_exti_enable_wake(PWR_EXTI_WKUP1 + it);
|
||||
-
|
||||
- io_setbits32(priv->base + MPUWKUPENR, BIT(it));
|
||||
+ exceptions = cpu_spin_lock_xsave(&priv->spinlock);
|
||||
+ stm32mp1_pwr_itr_enable_nolock(it);
|
||||
+ cpu_spin_unlock_xrestore(&priv->spinlock, exceptions);
|
||||
}
|
||||
|
||||
void stm32mp1_pwr_itr_disable(size_t it)
|
||||
{
|
||||
struct stm32_pwr_data *priv = pwr_data;
|
||||
+ uint32_t exceptions = 0;
|
||||
|
||||
- VERBOSE_PWR("Pwr irq disable");
|
||||
-
|
||||
- io_clrbits32(priv->base + MPUWKUPENR, BIT(it));
|
||||
-
|
||||
- if (IS_ENABLED(CFG_STM32_EXTI))
|
||||
- stm32_exti_disable_wake(PWR_EXTI_WKUP1 + it);
|
||||
+ exceptions = cpu_spin_lock_xsave(&priv->spinlock);
|
||||
+ stm32mp1_pwr_itr_disable_nolock(it);
|
||||
+ cpu_spin_unlock_xrestore(&priv->spinlock, exceptions);
|
||||
}
|
||||
|
||||
static TEE_Result stm32mp1_pwr_irt_add(struct itr_handler *hdl)
|
||||
@@ -231,7 +262,9 @@ static TEE_Result stm32mp1_pwr_irt_add(struct itr_handler *hdl)
|
||||
struct stm32_pinctrl_list pinctrl_list = { };
|
||||
struct stm32_pinctrl pin = { };
|
||||
struct stm32_pinctrl *pinctrl = NULL;
|
||||
+ uint32_t exceptions = 0;
|
||||
unsigned int i = 0;
|
||||
+ bool itr_free = false;
|
||||
|
||||
VERBOSE_PWR("Pwr IRQ add");
|
||||
|
||||
@@ -241,10 +274,15 @@ static TEE_Result stm32mp1_pwr_irt_add(struct itr_handler *hdl)
|
||||
}
|
||||
|
||||
assert(it >= PWR_WKUP_PIN1 && it < PWR_NB_WAKEUPPINS);
|
||||
- /* check IRQ not already in use */
|
||||
- assert(!priv->hdl[it]);
|
||||
|
||||
- priv->hdl[it] = hdl;
|
||||
+ /* Use PWR lock to ensure consistent interrupt registering */
|
||||
+ exceptions = cpu_spin_lock_xsave(&priv->spinlock);
|
||||
+ itr_free = !priv->hdl[it];
|
||||
+ if (itr_free)
|
||||
+ priv->hdl[it] = hdl;
|
||||
+ cpu_spin_unlock_xrestore(&priv->spinlock, exceptions);
|
||||
+ if (!itr_free)
|
||||
+ return TEE_ERROR_GENERIC;
|
||||
|
||||
if (hdl->flags & PWR_WKUP_FLAG_THREADED)
|
||||
priv->threaded[it] = true;
|
||||
diff --git a/core/arch/arm/plat-stm32mp1/main.c b/core/arch/arm/plat-stm32mp1/main.c
|
||||
index 2e9f7a699..3ae327ee5 100644
|
||||
--- a/core/arch/arm/plat-stm32mp1/main.c
|
||||
+++ b/core/arch/arm/plat-stm32mp1/main.c
|
||||
@@ -165,9 +165,9 @@ static TEE_Result init_console_from_dt(void)
|
||||
/* Replace early console with the new one */
|
||||
console_flush();
|
||||
console_data = *pd;
|
||||
- free(pd);
|
||||
register_serial_console(&console_data.chip);
|
||||
IMSG("DTB enables console (%ssecure)", pd->secure ? "" : "non-");
|
||||
+ free(pd);
|
||||
|
||||
return TEE_SUCCESS;
|
||||
}
|
||||
@@ -727,7 +727,7 @@ static TEE_Result stm32_configure_tamp(void)
|
||||
return TEE_SUCCESS;
|
||||
}
|
||||
|
||||
-driver_init_late(stm32_configure_tamp);
|
||||
+service_init(stm32_configure_tamp);
|
||||
#endif
|
||||
|
||||
#ifdef CFG_STM32_HSE_MONITORING
|
||||
diff --git a/core/arch/arm/plat-stm32mp1/pm/context.c b/core/arch/arm/plat-stm32mp1/pm/context.c
|
||||
index c9d26ee37..7e08bc0a2 100644
|
||||
--- a/core/arch/arm/plat-stm32mp1/pm/context.c
|
||||
+++ b/core/arch/arm/plat-stm32mp1/pm/context.c
|
||||
@@ -213,7 +213,7 @@ static void __maybe_unused print_ccm_decryption_duration(void)
|
||||
((unsigned long long)ctx->stgen_cnt * 1000) /
|
||||
io_read32(stgen + CNTFID_OFFSET));
|
||||
|
||||
- clk_enable(pm_clocks.bkpsram);
|
||||
+ clk_disable(pm_clocks.bkpsram);
|
||||
}
|
||||
#else
|
||||
static void __maybe_unused print_ccm_decryption_duration(void)
|
||||
@@ -582,15 +582,17 @@ TEE_Result stm32mp_pm_call_bl2_lp_entry(unsigned int soc_mode)
|
||||
|
||||
dcache_op_all(DCACHE_OP_CLEAN_INV);
|
||||
|
||||
+ /* Disable Cache & MMU before calling low_power section */
|
||||
+ write_sctlr(read_sctlr() & ~(SCTLR_C | SCTLR_M));
|
||||
+
|
||||
dsb();
|
||||
+ isb();
|
||||
|
||||
- /* Disable MMU before calling low_power section */
|
||||
- write_sctlr(read_sctlr() & ~SCTLR_M);
|
||||
|
||||
(*stm32_pwr_down_wfi)(true, soc_mode);
|
||||
|
||||
- /* Enable MMU */
|
||||
- write_sctlr(read_sctlr() | SCTLR_M);
|
||||
+ /* Enable Cache & MMU */
|
||||
+ write_sctlr(read_sctlr() | SCTLR_C | SCTLR_M);
|
||||
|
||||
clk_disable(pm_clocks.bkpsram);
|
||||
|
||||
diff --git a/core/arch/arm/plat-stm32mp1/pm/low_power.c b/core/arch/arm/plat-stm32mp1/pm/low_power.c
|
||||
index cbc5fa151..653c3dfb7 100644
|
||||
--- a/core/arch/arm/plat-stm32mp1/pm/low_power.c
|
||||
+++ b/core/arch/arm/plat-stm32mp1/pm/low_power.c
|
||||
@@ -292,13 +292,6 @@ void stm32_enter_cstop(uint32_t mode)
|
||||
io_clrsetbits32(pwr_base + PWR_CR3_OFF, PWR_CR3_POPL_MASK,
|
||||
20U << PWR_CR3_POPL_SHIFT);
|
||||
|
||||
- /* Keep backup RAM content in standby */
|
||||
- io_setbits32(pwr_base + PWR_CR2_OFF, PWR_CR2_BREN);
|
||||
-
|
||||
- // TODO add a timeout?
|
||||
- while (!(io_read32(pwr_base + PWR_CR2_OFF) & PWR_CR2_BRRDY))
|
||||
- ;
|
||||
-
|
||||
#ifndef CFG_STM32MP13
|
||||
if (stm32mp1_is_retram_during_standby()) {
|
||||
/* Keep retention in standby */
|
||||
@@ -344,9 +337,6 @@ void stm32_exit_cstop(void)
|
||||
dsb();
|
||||
isb();
|
||||
|
||||
- /* Disable retention and backup RAM content after stop */
|
||||
- io_clrbits32(stm32_pwr_base() + PWR_CR2_OFF, PWR_CR2_BREN);
|
||||
-
|
||||
#ifndef CFG_STM32MP13
|
||||
/* Disable retention and backup RAM content after stop */
|
||||
io_clrbits32(stm32_pwr_base() + PWR_CR2_OFF, PWR_CR2_RREN);
|
||||
@@ -525,6 +515,11 @@ static TEE_Result init_low_power(void)
|
||||
RCC_MP_SREQSETR_STPREQ_P0 | RCC_MP_SREQSETR_STPREQ_P1);
|
||||
#endif
|
||||
|
||||
+ /* Keep backup RAM content in standby */
|
||||
+ io_setbits32(pwr_base + PWR_CR2_OFF, PWR_CR2_BREN);
|
||||
+ while (!(io_read32(pwr_base + PWR_CR2_OFF) & PWR_CR2_BRRDY))
|
||||
+ ;
|
||||
+
|
||||
return TEE_SUCCESS;
|
||||
}
|
||||
driver_init_late(init_low_power);
|
||||
diff --git a/core/drivers/crypto/stm32/stm32_saes.c b/core/drivers/crypto/stm32/stm32_saes.c
|
||||
index 9453d0d52..d8495a16e 100644
|
||||
--- a/core/drivers/crypto/stm32/stm32_saes.c
|
||||
+++ b/core/drivers/crypto/stm32/stm32_saes.c
|
||||
@@ -1337,6 +1337,13 @@ TEE_Result huk_subkey_derive(enum huk_subkey_usage usage,
|
||||
struct stm32_saes_context ctx = { };
|
||||
uint8_t separator = 0;
|
||||
|
||||
+ // Check if driver is probed
|
||||
+ if (saes_pdata.base.pa == 0) {
|
||||
+ DMSG("Use __huk_subkey_derive instead of SAES IP features");
|
||||
+ return __huk_subkey_derive(usage, const_data, const_data_len,
|
||||
+ subkey, subkey_len);
|
||||
+ }
|
||||
+
|
||||
input = malloc(const_data_len + sizeof(separator) + sizeof(usage) +
|
||||
sizeof(subkey_bitlen) + AES_BLOCK_SIZE);
|
||||
if (!input)
|
||||
diff --git a/core/drivers/regulator/core.c b/core/drivers/regulator/core.c
|
||||
index d4dc3751d..7ef58b268 100644
|
||||
--- a/core/drivers/regulator/core.c
|
||||
+++ b/core/drivers/regulator/core.c
|
||||
@@ -575,6 +575,11 @@ static TEE_Result parse_properties(const void *fdt, struct rdev *rdev, int node)
|
||||
}
|
||||
|
||||
rdev->reg_name = fdt_getprop(fdt, node, "regulator-name", NULL);
|
||||
+ if (rdev->reg_name) {
|
||||
+ rdev->reg_name = strdup(rdev->reg_name);
|
||||
+ if (!rdev->reg_name)
|
||||
+ panic();
|
||||
+ }
|
||||
|
||||
return TEE_SUCCESS;
|
||||
}
|
||||
diff --git a/core/drivers/stm32_iwdg.c b/core/drivers/stm32_iwdg.c
|
||||
index 49e4fad50..fba4abe7e 100644
|
||||
--- a/core/drivers/stm32_iwdg.c
|
||||
+++ b/core/drivers/stm32_iwdg.c
|
||||
@@ -35,6 +35,7 @@
|
||||
#define IWDG_EWCR_OFFSET U(0x14)
|
||||
|
||||
/* Registers values */
|
||||
+#define IWDG_KR_WPROT_KEY U(0x0000)
|
||||
#define IWDG_KR_ACCESS_KEY U(0x5555)
|
||||
#define IWDG_KR_RELOAD_KEY U(0xAAAA)
|
||||
#define IWDG_KR_START_KEY U(0xCCCC)
|
||||
@@ -45,6 +46,7 @@
|
||||
#define IWDG_RLR_RL_MASK GENMASK_32(11, 0)
|
||||
|
||||
#define IWDG_SR_EWU BIT(3)
|
||||
+#define IWDG_SR_EWIF BIT(14)
|
||||
|
||||
#define IWDG_EWCR_EWIE BIT(15)
|
||||
#define IWDG_EWCR_EWIC BIT(14)
|
||||
@@ -88,10 +90,22 @@ static enum itr_return stm32_iwdg_it_handler(struct itr_handler *handler)
|
||||
|
||||
stm32mp_dump_core_registers(true);
|
||||
|
||||
- iwdg_refresh(iwdg);
|
||||
-
|
||||
clk_enable(iwdg->pdata.clock);
|
||||
|
||||
+ /* Check for spurious interrupt */
|
||||
+ if (!(io_read32(iwdg_base + IWDG_SR_OFFSET) & IWDG_SR_EWIF)) {
|
||||
+ clk_disable(iwdg->pdata.clock);
|
||||
+ return ITRR_NONE;
|
||||
+ }
|
||||
+
|
||||
+ /*
|
||||
+ * Writing IWDG_EWCR_EWIT triggers a watchdog refresh.
|
||||
+ * To prevent the watchdog refresh, write-protect all the registers;
|
||||
+ * this makes read-only all IWDG_EWCR fields except IWDG_EWCR_EWIC.
|
||||
+ */
|
||||
+ io_write32(iwdg_base + IWDG_KR_OFFSET, IWDG_KR_WPROT_KEY);
|
||||
+
|
||||
+ /* Disable early interrupt */
|
||||
io_setbits32(iwdg_base + IWDG_EWCR_OFFSET, IWDG_EWCR_EWIC);
|
||||
|
||||
clk_disable(iwdg->pdata.clock);
|
||||
diff --git a/core/drivers/stm32_rng.c b/core/drivers/stm32_rng.c
|
||||
index ef5862308..363aeee00 100644
|
||||
--- a/core/drivers/stm32_rng.c
|
||||
+++ b/core/drivers/stm32_rng.c
|
||||
@@ -140,9 +140,19 @@ static TEE_Result stm32_rng_read_available(struct stm32_rng_device *dev,
|
||||
|
||||
/* RNG is ready: read up to 4 32bit words */
|
||||
while (size) {
|
||||
- uint32_t data32 = io_read32(base + RNG_DR);
|
||||
+ uint32_t data32 = 0;
|
||||
size_t sz = MIN(size, sizeof(uint32_t));
|
||||
|
||||
+ if (!(io_read32(base + RNG_SR) & RNG_SR_DRDY))
|
||||
+ return TEE_ERROR_NO_DATA;
|
||||
+
|
||||
+ data32 = io_read32(base + RNG_DR);
|
||||
+ /* Late seed error case: DR being 0 is an error status */
|
||||
+ if (!data32) {
|
||||
+ conceal_seed_error(dev);
|
||||
+ return TEE_ERROR_NO_DATA;
|
||||
+ }
|
||||
+
|
||||
memcpy(buf, &data32, sz);
|
||||
buf += sz;
|
||||
size -= sz;
|
||||
diff --git a/core/drivers/stm32_uart.c b/core/drivers/stm32_uart.c
|
||||
index 5105b14bc..1ffc99117 100644
|
||||
--- a/core/drivers/stm32_uart.c
|
||||
+++ b/core/drivers/stm32_uart.c
|
||||
@@ -38,12 +38,12 @@
|
||||
* Bit 5 RXNE: Read data register not empty/RXFIFO not empty
|
||||
* Bit 6 TC: Transmission complete
|
||||
* Bit 7 TXE/TXFNF: Transmit data register empty/TXFIFO not full
|
||||
- * Bit 27 TXFE: TXFIFO threshold reached
|
||||
+ * Bit 23 TXFE: TXFIFO empty
|
||||
*/
|
||||
#define USART_ISR_RXNE_RXFNE BIT(5)
|
||||
#define USART_ISR_TC BIT(6)
|
||||
#define USART_ISR_TXE_TXFNF BIT(7)
|
||||
-#define USART_ISR_TXFE BIT(27)
|
||||
+#define USART_ISR_TXFE BIT(23)
|
||||
|
||||
static vaddr_t loc_chip_to_base(struct serial_chip *chip)
|
||||
{
|
||||
diff --git a/core/include/drivers/stpmic1.h b/core/include/drivers/stpmic1.h
|
||||
index 5fe48232f..b293c846f 100644
|
||||
--- a/core/include/drivers/stpmic1.h
|
||||
+++ b/core/include/drivers/stpmic1.h
|
||||
@@ -171,41 +171,6 @@
|
||||
#define USBSW_OTG_SWITCH_ENABLED_POS 1
|
||||
#define BOOST_ENABLED_POS 0
|
||||
|
||||
-/* IRQ definitions */
|
||||
-#define IT_PONKEY_F 0
|
||||
-#define IT_PONKEY_R 1
|
||||
-#define IT_WAKEUP_F 2
|
||||
-#define IT_WAKEUP_R 3
|
||||
-#define IT_VBUS_OTG_F 4
|
||||
-#define IT_VBUS_OTG_R 5
|
||||
-#define IT_SWOUT_F 6
|
||||
-#define IT_SWOUT_R 7
|
||||
-
|
||||
-#define IT_CURLIM_BUCK1 0
|
||||
-#define IT_CURLIM_BUCK2 1
|
||||
-#define IT_CURLIM_BUCK3 2
|
||||
-#define IT_CURLIM_BUCK4 3
|
||||
-#define IT_OCP_OTG 4
|
||||
-#define IT_OCP_SWOUT 5
|
||||
-#define IT_OCP_BOOST 6
|
||||
-#define IT_OVP_BOOST 7
|
||||
-
|
||||
-#define IT_CURLIM_LDO1 0
|
||||
-#define IT_CURLIM_LDO2 1
|
||||
-#define IT_CURLIM_LDO3 2
|
||||
-#define IT_CURLIM_LDO4 3
|
||||
-#define IT_CURLIM_LDO5 4
|
||||
-#define IT_CURLIM_LDO6 5
|
||||
-#define IT_SHORT_SWOTG 6
|
||||
-#define IT_SHORT_SWOUT 7
|
||||
-
|
||||
-#define IT_TWARN_F 0
|
||||
-#define IT_TWARN_R 1
|
||||
-#define IT_VINLOW_F 2
|
||||
-#define IT_VINLOW_R 3
|
||||
-#define IT_SWIN_F 4
|
||||
-#define IT_SWIN_R 5
|
||||
-
|
||||
/*
|
||||
* Bind SPMIC1 device driver with a specific I2C bus instance
|
||||
* @i2c_handle: target I2C instance to use
|
||||
diff --git a/core/include/kernel/huk_subkey.h b/core/include/kernel/huk_subkey.h
|
||||
index 59bcf2773..a6a18e953 100644
|
||||
--- a/core/include/kernel/huk_subkey.h
|
||||
+++ b/core/include/kernel/huk_subkey.h
|
||||
@@ -49,12 +49,17 @@ enum huk_subkey_usage {
|
||||
*
|
||||
* Returns a subkey derived from the hardware unique key. Given the same
|
||||
* input the same subkey is returned each time.
|
||||
+ * Function huk_subkey_derive is __weak to allow platform custom implementation.
|
||||
+ * __huk_subkey_derive implements the default behavior of huk_subkey_derive.
|
||||
*
|
||||
* Return TEE_SUCCES on success or an error code on failure.
|
||||
*/
|
||||
TEE_Result huk_subkey_derive(enum huk_subkey_usage usage,
|
||||
const void *const_data, size_t const_data_len,
|
||||
uint8_t *subkey, size_t subkey_len);
|
||||
+TEE_Result __huk_subkey_derive(enum huk_subkey_usage usage,
|
||||
+ const void *const_data, size_t const_data_len,
|
||||
+ uint8_t *subkey, size_t subkey_len);
|
||||
|
||||
|
||||
#endif /*__KERNEL_HUK_SUBKEY_H*/
|
||||
diff --git a/core/kernel/huk_subkey.c b/core/kernel/huk_subkey.c
|
||||
index 5481120b6..3db2cfe5f 100644
|
||||
--- a/core/kernel/huk_subkey.c
|
||||
+++ b/core/kernel/huk_subkey.c
|
||||
@@ -58,10 +58,9 @@ static TEE_Result huk_compat(void *ctx, enum huk_subkey_usage usage)
|
||||
}
|
||||
#endif /*CFG_CORE_HUK_SUBKEY_COMPAT*/
|
||||
|
||||
-__weak
|
||||
-TEE_Result huk_subkey_derive(enum huk_subkey_usage usage,
|
||||
- const void *const_data, size_t const_data_len,
|
||||
- uint8_t *subkey, size_t subkey_len)
|
||||
+TEE_Result __huk_subkey_derive(enum huk_subkey_usage usage,
|
||||
+ const void *const_data, size_t const_data_len,
|
||||
+ uint8_t *subkey, size_t subkey_len)
|
||||
{
|
||||
void *ctx = NULL;
|
||||
struct tee_hw_unique_key huk = { };
|
||||
@@ -106,3 +105,12 @@ out:
|
||||
crypto_mac_free_ctx(ctx);
|
||||
return res;
|
||||
}
|
||||
+
|
||||
+__weak
|
||||
+TEE_Result huk_subkey_derive(enum huk_subkey_usage usage,
|
||||
+ const void *const_data, size_t const_data_len,
|
||||
+ uint8_t *subkey, size_t subkey_len)
|
||||
+{
|
||||
+ return __huk_subkey_derive(usage, const_data, const_data_len, subkey,
|
||||
+ subkey_len);
|
||||
+}
|
||||
diff --git a/documentation/devicetree/bindings/mfd/st,stpmic1.yaml b/documentation/devicetree/bindings/mfd/st,stpmic1.yaml
|
||||
index 344623f1f..7d97a7082 100644
|
||||
--- a/documentation/devicetree/bindings/mfd/st,stpmic1.yaml
|
||||
+++ b/documentation/devicetree/bindings/mfd/st,stpmic1.yaml
|
||||
@@ -262,6 +262,51 @@ properties:
|
||||
minItems: 1
|
||||
maxItems: 1
|
||||
|
||||
+ st,pmic-it-id:
|
||||
+ description: PMIC interruptions id to forward to the non-secure world
|
||||
+ in the form of OPTEE notifications described by st,notif-it-id.
|
||||
+ IT_PONKEY_F = 0
|
||||
+ IT_PONKEY_R = 1
|
||||
+ IT_WAKEUP_F = 2
|
||||
+ IT_WAKEUP_R = 3
|
||||
+ IT_VBUS_OTG_F = 4
|
||||
+ IT_VBUS_OTG_R = 5
|
||||
+ IT_SWOUT_F = 6
|
||||
+ IT_SWOUT_R = 7
|
||||
+ IT_CURLIM_BUCK1 = 8
|
||||
+ IT_CURLIM_BUCK2 = 9
|
||||
+ IT_CURLIM_BUCK3 = 10
|
||||
+ IT_CURLIM_BUCK4 = 11
|
||||
+ IT_OCP_OTG = 12
|
||||
+ IT_OCP_SWOUT = 13
|
||||
+ IT_OCP_BOOST = 14
|
||||
+ IT_OVP_BOOST = 15
|
||||
+ IT_CURLIM_LDO1 = 16
|
||||
+ IT_CURLIM_LDO2 = 17
|
||||
+ IT_CURLIM_LDO3 = 18
|
||||
+ IT_CURLIM_LDO4 = 19
|
||||
+ IT_CURLIM_LDO5 = 20
|
||||
+ IT_CURLIM_LDO6 = 21
|
||||
+ IT_SHORT_SWOTG = 22
|
||||
+ IT_SHORT_SWOUT = 23
|
||||
+ IT_TWARN_F = 24
|
||||
+ IT_TWARN_R = 25
|
||||
+ IT_VINLOW_F = 26
|
||||
+ IT_VINLOW_R = 27
|
||||
+ IT_SWIN_F = 30
|
||||
+ IT_SWIN_R = 31
|
||||
+ $ref: /schemas/types.yaml#/definitions/uint32
|
||||
+ minItems: 1
|
||||
+ maxItems: 32
|
||||
+
|
||||
+ st,notif-it-id:
|
||||
+ description: OPTEE notification numbers to send to the non-secure world.
|
||||
+ One notification is needed for each interruption listed by st,pmic-it-id,
|
||||
+ so the number of notifications must be eaqual to the number of interrupts.
|
||||
+ $ref: /schemas/types.yaml#/definitions/uint32
|
||||
+ minItems: 1
|
||||
+ maxItems: 32
|
||||
+
|
||||
additionalProperties: false
|
||||
|
||||
required:
|
||||
@@ -271,6 +316,10 @@ required:
|
||||
- "#interrupt-cells"
|
||||
- interrupt-controller
|
||||
|
||||
+dependencies:
|
||||
+ st,notif-it-id: [ 'st,pmic-it-id' ]
|
||||
+ st,pmic-it-id: [ 'st,notif-it-id' ]
|
||||
+
|
||||
examples:
|
||||
- |
|
||||
#include <dt-bindings/mfd/st,stpmic1.h>
|
||||
@@ -289,6 +338,8 @@ examples:
|
||||
#interrupt-cells = <2>;
|
||||
|
||||
st,wakeup-pin-number = <1>;
|
||||
+ st,pmic-it-id = <IT_PONKEY_F IT_PONKEY_R>;
|
||||
+ st,notif-it-id = <0 2>;
|
||||
|
||||
onkey {
|
||||
compatible = "st,stpmic1-onkey";
|
||||
--
|
||||
2.25.1
|
||||
|
||||
Loading…
Reference in New Issue