diff --git a/drivers/st/mmc/stm32_sdmmc2.c b/drivers/st/mmc/stm32_sdmmc2.c index cff3a344f..d3adeab13 100644 --- a/drivers/st/mmc/stm32_sdmmc2.c +++ b/drivers/st/mmc/stm32_sdmmc2.c @@ -628,6 +628,7 @@ static int stm32_sdmmc2_dt_get_config(void) int sdmmc_node; void *fdt = NULL; const fdt32_t *cuint; + struct dt_node_info dt_info; if (fdt_get_address(&fdt) == 0) { return -FDT_ERR_NOTFOUND; @@ -637,27 +638,14 @@ static int stm32_sdmmc2_dt_get_config(void) return -FDT_ERR_NOTFOUND; } - sdmmc_node = fdt_node_offset_by_compatible(fdt, -1, DT_SDMMC2_COMPAT); - - while (sdmmc_node != -FDT_ERR_NOTFOUND) { - cuint = fdt_getprop(fdt, sdmmc_node, "reg", NULL); - if (cuint == NULL) { - continue; - } - - if (fdt32_to_cpu(*cuint) == sdmmc2_params.reg_base) { - break; - } - - sdmmc_node = fdt_node_offset_by_compatible(fdt, sdmmc_node, - DT_SDMMC2_COMPAT); - } - + sdmmc_node = dt_match_instance_by_compatible(DT_SDMMC2_COMPAT, + sdmmc2_params.reg_base); if (sdmmc_node == -FDT_ERR_NOTFOUND) { return -FDT_ERR_NOTFOUND; } - if (fdt_get_status(sdmmc_node) == DT_DISABLED) { + dt_fill_device_info(&dt_info, sdmmc_node); + if (dt_info.status == DT_DISABLED) { return -FDT_ERR_NOTFOUND; } @@ -665,21 +653,8 @@ static int stm32_sdmmc2_dt_get_config(void) return -FDT_ERR_BADVALUE; } - cuint = fdt_getprop(fdt, sdmmc_node, "clocks", NULL); - if (cuint == NULL) { - return -FDT_ERR_NOTFOUND; - } - - cuint++; - sdmmc2_params.clock_id = fdt32_to_cpu(*cuint); - - cuint = fdt_getprop(fdt, sdmmc_node, "resets", NULL); - if (cuint == NULL) { - return -FDT_ERR_NOTFOUND; - } - - cuint++; - sdmmc2_params.reset_id = fdt32_to_cpu(*cuint); + sdmmc2_params.clock_id = dt_info.clock; + sdmmc2_params.reset_id = dt_info.reset; if ((fdt_getprop(fdt, sdmmc_node, "st,use-ckin", NULL)) != NULL) { sdmmc2_params.pin_ckin = SDMMC_CLKCR_SELCLKRX_0; diff --git a/plat/st/common/include/stm32mp_dt.h b/plat/st/common/include/stm32mp_dt.h index 299c0b1cb..f7201c0d9 100644 --- a/plat/st/common/include/stm32mp_dt.h +++ b/plat/st/common/include/stm32mp_dt.h @@ -34,6 +34,7 @@ int dt_set_stdout_pinctrl(void); void dt_fill_device_info(struct dt_node_info *info, int node); int dt_get_node(struct dt_node_info *info, int offset, const char *compat); int dt_get_stdout_uart_info(struct dt_node_info *info); +int dt_match_instance_by_compatible(const char *compatible, uintptr_t address); uint32_t dt_get_ddr_size(void); uint32_t dt_get_pwr_vdd_voltage(void); const char *dt_get_board_model(void); diff --git a/plat/st/common/stm32mp_dt.c b/plat/st/common/stm32mp_dt.c index 0b3564692..4dc990896 100644 --- a/plat/st/common/stm32mp_dt.c +++ b/plat/st/common/stm32mp_dt.c @@ -203,6 +203,33 @@ int dt_get_stdout_uart_info(struct dt_node_info *info) return node; } +/******************************************************************************* + * This function returns the node offset matching compatible string in the DT, + * and also matching the reg property with the given address. + * Returns value on success, and error value on failure. + ******************************************************************************/ +int dt_match_instance_by_compatible(const char *compatible, uintptr_t address) +{ + int node; + + fdt_for_each_compatible_node(fdt, node, compatible) { + const fdt32_t *cuint; + + assert(fdt_get_node_parent_address_cells(node) == 1); + + cuint = fdt_getprop(fdt, node, "reg", NULL); + if (cuint == NULL) { + continue; + } + + if ((uintptr_t)fdt32_to_cpu(*cuint) == address) { + return node; + } + } + + return -FDT_ERR_NOTFOUND; +} + /******************************************************************************* * This function gets DDR size information from the DT. * Returns value in bytes on success, and 0 on failure.