@@ -1011,6 +1011,27 @@ static int spi_stm32_clock_configure(const struct spi_stm32_config *cfg)
10111011 return 0 ;
10121012}
10131013
1014+ #ifdef CONFIG_PM
1015+ /**
1016+ * @brief Reinitialization of SPI context
1017+ *
1018+ * This function reenables clocks, which is required upon exiting certain
1019+ * low-power modes on select SoCs.
1020+ *
1021+ * @param dev SPI device struct
1022+ *
1023+ * @return 0
1024+ */
1025+ static void spi_stm32_reinit (uint8_t direction , void * ctx )
1026+ {
1027+ ARG_UNUSED (direction );
1028+ const struct device * dev = ctx ;
1029+ const struct spi_stm32_config * cfg = dev -> config ;
1030+
1031+ spi_stm32_clock_configure (cfg );
1032+ }
1033+ #endif /* CONFIG_PM */
1034+
10141035static int spi_stm32_init (const struct device * dev )
10151036{
10161037 struct spi_stm32_data * data __attribute__((unused )) = dev -> data ;
@@ -1059,6 +1080,15 @@ static int spi_stm32_init(const struct device *dev)
10591080
10601081 spi_context_unlock_unconditionally (& data -> ctx );
10611082
1083+ #ifdef CONFIG_PM
1084+ if (cfg -> reinit_states_size > 0 ) {
1085+ for (size_t i = 0 ; i < cfg -> reinit_states_size ; i ++ ) {
1086+ pm_notifier_register (cfg -> notifier , cfg -> reinit_states [i ].state ,
1087+ cfg -> reinit_states [i ].substate_id );
1088+ }
1089+ }
1090+ #endif /* CONFIG_PM */
1091+
10621092 return 0 ;
10631093}
10641094
@@ -1130,11 +1160,30 @@ static void spi_stm32_irq_config_func_##id(const struct device *dev) \
11301160#define STM32_SPI_USE_SUBGHZSPI_NSS_CONFIG (id )
11311161#endif
11321162
1163+ #ifdef CONFIG_PM
1164+ #define STM32_SPI_REINIT_STATE_INIT (id ) \
1165+ static const struct pm_state_info reinit_states_##id[] \
1166+ = PM_STATE_INFO_LIST_FROM_DT_REINIT(DT_DRV_INST(id))
1167+
1168+ #define STM32_SPI_REINIT_CFG_INIT (id ) \
1169+ .notifier = &PM_NOTIFIER(DT_INST_DEP_ORD(id)), \
1170+ .reinit_states = reinit_states_##id, \
1171+ .reinit_states_size = ARRAY_SIZE(reinit_states_##id),
1172+ #else
1173+ #define STM32_SPI_REINIT_STATE_INIT (id )
1174+ #define STM32_SPI_REINIT_CFG_INIT (id )
1175+ #endif /* CONFIG_PM */
1176+
11331177#define STM32_SPI_INIT (id ) \
11341178STM32_SPI_IRQ_HANDLER_DECL(id); \
11351179 \
11361180PINCTRL_DT_INST_DEFINE(id); \
11371181 \
1182+ STM32_SPI_REINIT_STATE_INIT(id); \
1183+ \
1184+ PM_NOTIFIER_DEFINE(DT_INST_DEP_ORD(id), PM_STATE_EXIT, \
1185+ spi_stm32_reinit, DEVICE_DT_INST_GET(id)); \
1186+ \
11381187static const struct stm32_pclken pclken_##id[] = \
11391188 STM32_DT_INST_CLOCKS(id);\
11401189 \
@@ -1145,6 +1194,7 @@ static const struct spi_stm32_config spi_stm32_cfg_##id = { \
11451194 .pcfg = PINCTRL_DT_INST_DEV_CONFIG_GET(id), \
11461195 STM32_SPI_IRQ_HANDLER_FUNC(id) \
11471196 STM32_SPI_USE_SUBGHZSPI_NSS_CONFIG(id) \
1197+ STM32_SPI_REINIT_CFG_INIT(id) \
11481198}; \
11491199 \
11501200static struct spi_stm32_data spi_stm32_dev_data_##id = { \
0 commit comments