Skip to content

Commit 29a4eb3

Browse files
erwangolaurenmurphyx64
authored andcommitted
divers: disk: stm32 sdmmc: Configure clock through device tree
Similarly to what was done in USB or RNG drivers, configure 48MHz domain clock using device tree. By default a freq clock check is enabled. Signed-off-by: Erwan Gouriou <erwan.gouriou@linaro.org>
1 parent a8c0545 commit 29a4eb3

File tree

2 files changed

+34
-37
lines changed

2 files changed

+34
-37
lines changed

drivers/disk/Kconfig.sdmmc

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -72,6 +72,15 @@ config SDMMC_STM32_HWFC
7272
Enable SDMMC Hardware Flow Control to avoid FIFO underrun (TX mode) and
7373
overrun (RX mode) errors.
7474

75+
config SDMMC_STM32_CLOCK_CHECK
76+
bool "Runtime SDMMC 48MHz clock check"
77+
depends on SDMMC_STM32
78+
default y
79+
help
80+
Enable SDMMC clock 48MHz configuration runtime check.
81+
In specific cases, this check might provide wrong verdict and should
82+
be disabled.
83+
7584
module = SDMMC
7685
module-str = sdmmc
7786
source "subsys/logging/Kconfig.template.log_config"

drivers/disk/sdmmc_stm32.c

Lines changed: 25 additions & 37 deletions
Original file line numberDiff line numberDiff line change
@@ -74,7 +74,7 @@ struct stm32_sdmmc_priv {
7474
struct gpio_callback cd_cb;
7575
struct gpio_dt_spec cd;
7676
struct gpio_dt_spec pe;
77-
struct stm32_pclken pclken;
77+
struct stm32_pclken *pclken;
7878
const struct pinctrl_dev_config *pcfg;
7979
const struct reset_dt_spec reset;
8080

@@ -133,49 +133,37 @@ void HAL_SD_ErrorCallback(SD_HandleTypeDef *hsd)
133133
static int stm32_sdmmc_clock_enable(struct stm32_sdmmc_priv *priv)
134134
{
135135
const struct device *clock;
136+
int res;
136137

137-
#if CONFIG_SOC_SERIES_STM32L4X
138-
LL_RCC_PLLSAI1_Disable();
139-
/* Configure PLLSA11 to enable 48M domain */
140-
LL_RCC_PLLSAI1_ConfigDomain_48M(LL_RCC_PLLSOURCE_HSI,
141-
LL_RCC_PLLM_DIV_1,
142-
8, LL_RCC_PLLSAI1Q_DIV_8);
143-
144-
/* Enable PLLSA1 */
145-
LL_RCC_PLLSAI1_Enable();
146-
147-
/* Enable PLLSAI1 output mapped on 48MHz domain clock */
148-
LL_RCC_PLLSAI1_EnableDomain_48M();
138+
/* HSI48 Clock is enabled through using the device tree */
139+
clock = DEVICE_DT_GET(STM32_CLOCK_CONTROL_NODE);
149140

150-
/* Wait for PLLSA1 ready flag */
151-
while (LL_RCC_PLLSAI1_IsReady() != 1)
152-
;
141+
if (DT_INST_NUM_CLOCKS(0) > 1) {
142+
if (clock_control_configure(clock,
143+
(clock_control_subsys_t *)&priv->pclken[1],
144+
NULL) != 0) {
145+
LOG_ERR("Failed to enable SDMMC domain clock");
146+
return -EIO;
147+
}
153148

154-
LL_RCC_SetSDMMCClockSource(LL_RCC_SDMMC1_CLKSOURCE_PLLSAI1);
155-
#endif
149+
if (IS_ENABLED(CONFIG_SDMMC_STM32_CLOCK_CHECK)) {
150+
uint32_t sdmmc_clock_rate;
156151

157-
#if defined(CONFIG_SOC_SERIES_STM32L5X) || \
158-
defined(CONFIG_SOC_SERIES_STM32U5X)
159-
#if !STM32_HSI48_ENABLED
160-
/* Deprecated: enable HSI48 using device tree */
161-
#warning USB device requires HSI48 clock to be enabled using device tree
162-
/*
163-
* Keeping this sequence for legacy :
164-
* By default the SDMMC clock source is set to 0 --> 48MHz, must be enabled
165-
*/
166-
LL_RCC_HSI48_Enable();
167-
while (!LL_RCC_HSI48_IsReady()) {
168-
}
169-
#endif /* !STM32_HSI48_ENABLED */
170-
#endif /* CONFIG_SOC_SERIES_STM32L5X ||
171-
* CONFIG_SOC_SERIES_STM32U5X
172-
*/
152+
if (clock_control_get_rate(clk,
153+
(clock_control_subsys_t *)&pclken[1],
154+
&sdmmc_clock_rate) != 0) {
155+
LOG_ERR("Failed to get SDMMC domain clock rate");
156+
return -EIO;
157+
}
173158

174-
/* HSI48 Clock is enabled through using the device tree */
175-
clock = DEVICE_DT_GET(STM32_CLOCK_CONTROL_NODE);
159+
if (sdmmc_clock_rate != MHZ(48)) {
160+
LOG_ERR("SDMMC Clock is not 48MHz (%d)", sdmmc_clock_rate);
161+
return -ENOTSUP;
162+
}
163+
}
176164

177165
/* Enable the APB clock for stm32_sdmmc */
178-
return clock_control_on(clock, (clock_control_subsys_t *)&priv->pclken);
166+
return clock_control_on(clock, (clock_control_subsys_t *)&priv->pclken[0]);
179167
}
180168

181169
static int stm32_sdmmc_clock_disable(struct stm32_sdmmc_priv *priv)

0 commit comments

Comments
 (0)