summaryrefslogtreecommitdiff
path: root/chip/stm32/system.c
diff options
context:
space:
mode:
Diffstat (limited to 'chip/stm32/system.c')
-rw-r--r--chip/stm32/system.c36
1 files changed, 26 insertions, 10 deletions
diff --git a/chip/stm32/system.c b/chip/stm32/system.c
index 47052dfccf..ceb19089ed 100644
--- a/chip/stm32/system.c
+++ b/chip/stm32/system.c
@@ -30,9 +30,13 @@
#define BDCR_ENABLE_MASK (BDCR_ENABLE_VALUE | BDCR_RTCSEL_MASK | \
STM32_RCC_BDCR_BDRST)
+/* We use 16-bit BKP / BBRAM entries. */
+#define STM32_BKP_ENTRIES (STM32_BKP_BYTES / 2)
+
enum bkpdata_index {
BKPDATA_INDEX_SCRATCHPAD, /* General-purpose scratchpad */
BKPDATA_INDEX_SAVED_RESET_FLAGS, /* Saved reset flags */
+#ifdef CONFIG_HOSTCMD_VBNV_CONTEXT
BKPDATA_INDEX_VBNV_CONTEXT0,
BKPDATA_INDEX_VBNV_CONTEXT1,
BKPDATA_INDEX_VBNV_CONTEXT2,
@@ -41,14 +45,23 @@ enum bkpdata_index {
BKPDATA_INDEX_VBNV_CONTEXT5,
BKPDATA_INDEX_VBNV_CONTEXT6,
BKPDATA_INDEX_VBNV_CONTEXT7,
+#endif
#ifdef CONFIG_SOFTWARE_PANIC
BKPDATA_INDEX_SAVED_PANIC_REASON, /* Saved panic reason */
BKPDATA_INDEX_SAVED_PANIC_INFO, /* Saved panic data */
BKPDATA_INDEX_SAVED_PANIC_EXCEPTION, /* Saved panic exception code */
#endif
+#ifdef CONFIG_USB_PD_DUAL_ROLE
BKPDATA_INDEX_PD0, /* USB-PD saved port0 state */
BKPDATA_INDEX_PD1, /* USB-PD saved port1 state */
+#endif
+ BKPDATA_COUNT
};
+BUILD_ASSERT(STM32_BKP_ENTRIES >= BKPDATA_COUNT);
+
+#ifdef CONFIG_USB_PD_DUAL_ROLE
+BUILD_ASSERT(CONFIG_USB_PD_PORT_COUNT <= 2);
+#endif
/**
* Read backup register at specified index.
@@ -60,15 +73,10 @@ static uint16_t bkpdata_read(enum bkpdata_index index)
if (index < 0 || index >= STM32_BKP_ENTRIES)
return 0;
-#if defined(CHIP_FAMILY_STM32L) || defined(CHIP_FAMILY_STM32F0) || \
- defined(CHIP_FAMILY_STM32F3)
if (index & 1)
return STM32_BKP_DATA(index >> 1) >> 16;
else
return STM32_BKP_DATA(index >> 1) & 0xFFFF;
-#else
- return STM32_BKP_DATA(index);
-#endif
}
/**
@@ -78,11 +86,16 @@ static uint16_t bkpdata_read(enum bkpdata_index index)
*/
static int bkpdata_write(enum bkpdata_index index, uint16_t value)
{
+ static struct mutex bkpdata_write_mutex;
+
if (index < 0 || index >= STM32_BKP_ENTRIES)
return EC_ERROR_INVAL;
-#if defined(CHIP_FAMILY_STM32L) || defined(CHIP_FAMILY_STM32F0) || \
- defined(CHIP_FAMILY_STM32F3)
+ /*
+ * Two entries share a single 32-bit register, lock mutex to prevent
+ * read/mask/write races.
+ */
+ mutex_lock(&bkpdata_write_mutex);
if (index & 1) {
uint32_t val = STM32_BKP_DATA(index >> 1);
val = (val & 0x0000FFFF) | (value << 16);
@@ -92,9 +105,8 @@ static int bkpdata_write(enum bkpdata_index index, uint16_t value)
val = (val & 0xFFFF0000) | value;
STM32_BKP_DATA(index >> 1) = val;
}
-#else
- STM32_BKP_DATA(index) = value;
-#endif
+ mutex_unlock(&bkpdata_write_mutex);
+
return EC_SUCCESS;
}
@@ -333,6 +345,8 @@ void system_reset(int flags)
if (flags & SYSTEM_RESET_HARD)
save_flags |= RESET_FLAG_HARD;
+ /* Reset flags are 32-bits, but BBRAM entry is only 16 bits. */
+ ASSERT(!(save_flags >> 16));
bkpdata_write(BKPDATA_INDEX_SAVED_RESET_FLAGS, save_flags);
if (flags & SYSTEM_RESET_HARD) {
@@ -428,12 +442,14 @@ static int bkpdata_index_lookup(enum system_bbram_idx idx, int *msb)
{
*msb = 0;
+#ifdef CONFIG_HOSTCMD_VBNV_CONTEXT
if (idx >= SYSTEM_BBRAM_IDX_VBNVBLOCK0 &&
idx <= SYSTEM_BBRAM_IDX_VBNVBLOCK15) {
*msb = (idx - SYSTEM_BBRAM_IDX_VBNVBLOCK0) % 2;
return BKPDATA_INDEX_VBNV_CONTEXT0 +
(idx - SYSTEM_BBRAM_IDX_VBNVBLOCK0) / 2;
}
+#endif
#ifdef CONFIG_USB_PD_DUAL_ROLE
if (idx == SYSTEM_BBRAM_IDX_PD0)
return BKPDATA_INDEX_PD0;