diff options
Diffstat (limited to 'drivers/mmc')
-rw-r--r-- | drivers/mmc/ca_dw_mmc.c | 4 | ||||
-rw-r--r-- | drivers/mmc/dw_mmc.c | 9 | ||||
-rw-r--r-- | drivers/mmc/exynos_dw_mmc.c | 4 | ||||
-rw-r--r-- | drivers/mmc/fsl_esdhc_spl.c | 3 | ||||
-rw-r--r-- | drivers/mmc/nexell_dw_mmc.c | 4 | ||||
-rw-r--r-- | drivers/mmc/pci_mmc.c | 6 | ||||
-rw-r--r-- | drivers/mmc/socfpga_dw_mmc.c | 18 | ||||
-rw-r--r-- | drivers/mmc/stm32_sdmmc2.c | 84 | ||||
-rw-r--r-- | drivers/mmc/xenon_sdhci.c | 12 |
9 files changed, 81 insertions, 63 deletions
diff --git a/drivers/mmc/ca_dw_mmc.c b/drivers/mmc/ca_dw_mmc.c index fad2ff5aaf6..2b79356a20e 100644 --- a/drivers/mmc/ca_dw_mmc.c +++ b/drivers/mmc/ca_dw_mmc.c @@ -40,7 +40,7 @@ struct ca_dwmmc_priv_data { u8 ds; }; -static void ca_dwmci_clksel(struct dwmci_host *host) +static int ca_dwmci_clksel(struct dwmci_host *host) { struct ca_dwmmc_priv_data *priv = host->priv; u32 val = readl(priv->sd_dll_reg); @@ -52,6 +52,8 @@ static void ca_dwmci_clksel(struct dwmci_host *host) val |= SD_CLK_SEL_100MHZ; writel(val, priv->sd_dll_reg); + + return 0; } static void ca_dwmci_board_init(struct dwmci_host *host) diff --git a/drivers/mmc/dw_mmc.c b/drivers/mmc/dw_mmc.c index 7702f4be3f8..7c8a312fa71 100644 --- a/drivers/mmc/dw_mmc.c +++ b/drivers/mmc/dw_mmc.c @@ -496,8 +496,13 @@ static int dwmci_set_ios(struct mmc *mmc) dwmci_writel(host, DWMCI_UHS_REG, regs); - if (host->clksel) - host->clksel(host); + if (host->clksel) { + int ret; + + ret = host->clksel(host); + if (ret) + return ret; + } #if CONFIG_IS_ENABLED(DM_REGULATOR) if (mmc->vqmmc_supply) { diff --git a/drivers/mmc/exynos_dw_mmc.c b/drivers/mmc/exynos_dw_mmc.c index edb5a52c960..b4ff1c3fb4b 100644 --- a/drivers/mmc/exynos_dw_mmc.c +++ b/drivers/mmc/exynos_dw_mmc.c @@ -44,7 +44,7 @@ struct dwmci_exynos_priv_data { * Function used as callback function to initialise the * CLKSEL register for every mmc channel. */ -static void exynos_dwmci_clksel(struct dwmci_host *host) +static int exynos_dwmci_clksel(struct dwmci_host *host) { #ifdef CONFIG_DM_MMC struct dwmci_exynos_priv_data *priv = @@ -53,6 +53,8 @@ static void exynos_dwmci_clksel(struct dwmci_host *host) struct dwmci_exynos_priv_data *priv = host->priv; #endif dwmci_writel(host, DWMCI_CLKSEL, priv->sdr_timing); + + return 0; } unsigned int exynos_dwmci_get_clk(struct dwmci_host *host, uint freq) diff --git a/drivers/mmc/fsl_esdhc_spl.c b/drivers/mmc/fsl_esdhc_spl.c index afe55fad9de..bee76572ac6 100644 --- a/drivers/mmc/fsl_esdhc_spl.c +++ b/drivers/mmc/fsl_esdhc_spl.c @@ -91,20 +91,17 @@ void __noreturn mmc_boot(void) CONFIG_CFG_DATA_SECTOR, 1, tmp_buf); if (err != 1) { puts("spl: mmc read failed!!\n"); - free(tmp_buf); hang(); } val = *(tmp_buf + MBRDBR_BOOT_SIG_55); if (0x55 != val) { puts("spl: mmc signature is not valid!!\n"); - free(tmp_buf); hang(); } val = *(tmp_buf + MBRDBR_BOOT_SIG_AA); if (0xAA != val) { puts("spl: mmc signature is not valid!!\n"); - free(tmp_buf); hang(); } diff --git a/drivers/mmc/nexell_dw_mmc.c b/drivers/mmc/nexell_dw_mmc.c index 753c89d278c..2723e4887cf 100644 --- a/drivers/mmc/nexell_dw_mmc.c +++ b/drivers/mmc/nexell_dw_mmc.c @@ -51,7 +51,7 @@ struct nexell_dwmmc_priv { struct clk *clk_get(const char *id); -static void nx_dw_mmc_clksel(struct dwmci_host *host) +static int nx_dw_mmc_clksel(struct dwmci_host *host) { /* host->priv is pointer to "struct udevice" */ struct nexell_dwmmc_priv *priv = dev_get_priv(host->priv); @@ -65,6 +65,8 @@ static void nx_dw_mmc_clksel(struct dwmci_host *host) DWMCI_SET_DRV_CLK(DWMCI_SHIFT_0) | DWMCI_SET_DIV_RATIO(3); dwmci_writel(host, DWMCI_CLKSEL, val); + + return 0; } static void nx_dw_mmc_reset(int ch) diff --git a/drivers/mmc/pci_mmc.c b/drivers/mmc/pci_mmc.c index c71c495d581..b26eb034d07 100644 --- a/drivers/mmc/pci_mmc.c +++ b/drivers/mmc/pci_mmc.c @@ -52,9 +52,11 @@ static int pci_mmc_probe(struct udevice *dev) static int pci_mmc_of_to_plat(struct udevice *dev) { - struct pci_mmc_priv *priv = dev_get_priv(dev); + if (CONFIG_IS_ENABLED(DM_GPIO)) { + struct pci_mmc_priv *priv = dev_get_priv(dev); - gpio_request_by_name(dev, "cd-gpios", 0, &priv->cd_gpio, GPIOD_IS_IN); + gpio_request_by_name(dev, "cd-gpios", 0, &priv->cd_gpio, GPIOD_IS_IN); + } return 0; } diff --git a/drivers/mmc/socfpga_dw_mmc.c b/drivers/mmc/socfpga_dw_mmc.c index dc008c5e2f0..aa0d3a22221 100644 --- a/drivers/mmc/socfpga_dw_mmc.c +++ b/drivers/mmc/socfpga_dw_mmc.c @@ -6,6 +6,7 @@ #include <common.h> #include <log.h> #include <asm/arch/clock_manager.h> +#include <asm/arch/secure_reg_helper.h> #include <asm/arch/system_manager.h> #include <clk.h> #include <dm.h> @@ -13,6 +14,7 @@ #include <errno.h> #include <fdtdec.h> #include <dm/device_compat.h> +#include <linux/intel-smc.h> #include <linux/libfdt.h> #include <linux/err.h> #include <malloc.h> @@ -46,7 +48,7 @@ static void socfpga_dwmci_reset(struct udevice *dev) reset_deassert_bulk(&reset_bulk); } -static void socfpga_dwmci_clksel(struct dwmci_host *host) +static int socfpga_dwmci_clksel(struct dwmci_host *host) { struct dwmci_socfpga_priv_data *priv = host->priv; u32 sdmmc_mask = ((priv->smplsel & 0x7) << SYSMGR_SDMMC_SMPLSEL_SHIFT) | @@ -58,14 +60,28 @@ static void socfpga_dwmci_clksel(struct dwmci_host *host) debug("%s: drvsel %d smplsel %d\n", __func__, priv->drvsel, priv->smplsel); + +#if !defined(CONFIG_SPL_BUILD) && defined(CONFIG_SPL_ATF) + int ret; + + ret = socfpga_secure_reg_write32(SOCFPGA_SECURE_REG_SYSMGR_SOC64_SDMMC, + sdmmc_mask); + if (ret) { + printf("DWMMC: Failed to set clksel via SMC call"); + return ret; + } +#else writel(sdmmc_mask, socfpga_get_sysmgr_addr() + SYSMGR_SDMMC); debug("%s: SYSMGR_SDMMCGRP_CTRL_REG = 0x%x\n", __func__, readl(socfpga_get_sysmgr_addr() + SYSMGR_SDMMC)); +#endif /* Enable SDMMC clock */ setbits_le32(socfpga_get_clkmgr_addr() + CLKMGR_PERPLL_EN, CLKMGR_PERPLLGRP_EN_SDMMCCLK_MASK); + + return 0; } static int socfpga_dwmmc_get_clk_rate(struct udevice *dev) diff --git a/drivers/mmc/stm32_sdmmc2.c b/drivers/mmc/stm32_sdmmc2.c index 3246f6b5e03..a3cdf7bcd9f 100644 --- a/drivers/mmc/stm32_sdmmc2.c +++ b/drivers/mmc/stm32_sdmmc2.c @@ -4,6 +4,8 @@ * Author(s): Patrice Chotard, <patrice.chotard@foss.st.com> for STMicroelectronics. */ +#define LOG_CATEGORY UCLASS_MMC + #include <common.h> #include <clk.h> #include <cpu_func.h> @@ -13,6 +15,7 @@ #include <malloc.h> #include <asm/bitops.h> #include <asm/cache.h> +#include <dm/device_compat.h> #include <linux/bitops.h> #include <linux/delay.h> #include <linux/libfdt.h> @@ -200,10 +203,11 @@ struct stm32_sdmmc2_ctx { #define SDMMC_CMD_TIMEOUT 0xFFFFFFFF #define SDMMC_BUSYD0END_TIMEOUT_US 2000000 -static void stm32_sdmmc2_start_data(struct stm32_sdmmc2_priv *priv, +static void stm32_sdmmc2_start_data(struct udevice *dev, struct mmc_data *data, struct stm32_sdmmc2_ctx *ctx) { + struct stm32_sdmmc2_priv *priv = dev_get_priv(dev); u32 data_ctrl, idmabase0; /* Configure the SDMMC DPSM (Data Path State Machine) */ @@ -241,10 +245,11 @@ static void stm32_sdmmc2_start_data(struct stm32_sdmmc2_priv *priv, writel(SDMMC_IDMACTRL_IDMAEN, priv->base + SDMMC_IDMACTRL); } -static void stm32_sdmmc2_start_cmd(struct stm32_sdmmc2_priv *priv, +static void stm32_sdmmc2_start_cmd(struct udevice *dev, struct mmc_cmd *cmd, u32 cmd_param, struct stm32_sdmmc2_ctx *ctx) { + struct stm32_sdmmc2_priv *priv = dev_get_priv(dev); u32 timeout = 0; if (readl(priv->base + SDMMC_CMD) & SDMMC_CMD_CPSMEN) @@ -290,10 +295,11 @@ static void stm32_sdmmc2_start_cmd(struct stm32_sdmmc2_priv *priv, writel(cmd_param, priv->base + SDMMC_CMD); } -static int stm32_sdmmc2_end_cmd(struct stm32_sdmmc2_priv *priv, +static int stm32_sdmmc2_end_cmd(struct udevice *dev, struct mmc_cmd *cmd, struct stm32_sdmmc2_ctx *ctx) { + struct stm32_sdmmc2_priv *priv = dev_get_priv(dev); u32 mask = SDMMC_STA_CTIMEOUT; u32 status; int ret; @@ -311,22 +317,22 @@ static int stm32_sdmmc2_end_cmd(struct stm32_sdmmc2_priv *priv, 10000); if (ret < 0) { - debug("%s: timeout reading SDMMC_STA register\n", __func__); + dev_dbg(dev, "timeout reading SDMMC_STA register\n"); ctx->dpsm_abort = true; return ret; } /* Check status */ if (status & SDMMC_STA_CTIMEOUT) { - debug("%s: error SDMMC_STA_CTIMEOUT (0x%x) for cmd %d\n", - __func__, status, cmd->cmdidx); + dev_dbg(dev, "error SDMMC_STA_CTIMEOUT (0x%x) for cmd %d\n", + status, cmd->cmdidx); ctx->dpsm_abort = true; return -ETIMEDOUT; } if (status & SDMMC_STA_CCRCFAIL && cmd->resp_type & MMC_RSP_CRC) { - debug("%s: error SDMMC_STA_CCRCFAIL (0x%x) for cmd %d\n", - __func__, status, cmd->cmdidx); + dev_dbg(dev, "error SDMMC_STA_CCRCFAIL (0x%x) for cmd %d\n", + status, cmd->cmdidx); ctx->dpsm_abort = true; return -EILSEQ; } @@ -350,15 +356,15 @@ static int stm32_sdmmc2_end_cmd(struct stm32_sdmmc2_priv *priv, SDMMC_BUSYD0END_TIMEOUT_US); if (ret < 0) { - debug("%s: timeout reading SDMMC_STA\n", - __func__); + dev_dbg(dev, "timeout reading SDMMC_STA\n"); ctx->dpsm_abort = true; return ret; } if (status & SDMMC_STA_DTIMEOUT) { - debug("%s: error SDMMC_STA_DTIMEOUT (0x%x)\n", - __func__, status); + dev_dbg(dev, + "error SDMMC_STA_DTIMEOUT (0x%x)\n", + status); ctx->dpsm_abort = true; return -ETIMEDOUT; } @@ -368,11 +374,12 @@ static int stm32_sdmmc2_end_cmd(struct stm32_sdmmc2_priv *priv, return 0; } -static int stm32_sdmmc2_end_data(struct stm32_sdmmc2_priv *priv, +static int stm32_sdmmc2_end_data(struct udevice *dev, struct mmc_cmd *cmd, struct mmc_data *data, struct stm32_sdmmc2_ctx *ctx) { + struct stm32_sdmmc2_priv *priv = dev_get_priv(dev); u32 mask = SDMMC_STA_DCRCFAIL | SDMMC_STA_DTIMEOUT | SDMMC_STA_IDMATE | SDMMC_STA_DATAEND; u32 status; @@ -394,37 +401,37 @@ static int stm32_sdmmc2_end_data(struct stm32_sdmmc2_priv *priv, invalidate_dcache_range(ctx->cache_start, ctx->cache_end); if (status & SDMMC_STA_DCRCFAIL) { - debug("%s: error SDMMC_STA_DCRCFAIL (0x%x) for cmd %d\n", - __func__, status, cmd->cmdidx); + dev_dbg(dev, "error SDMMC_STA_DCRCFAIL (0x%x) for cmd %d\n", + status, cmd->cmdidx); if (readl(priv->base + SDMMC_DCOUNT)) ctx->dpsm_abort = true; return -EILSEQ; } if (status & SDMMC_STA_DTIMEOUT) { - debug("%s: error SDMMC_STA_DTIMEOUT (0x%x) for cmd %d\n", - __func__, status, cmd->cmdidx); + dev_dbg(dev, "error SDMMC_STA_DTIMEOUT (0x%x) for cmd %d\n", + status, cmd->cmdidx); ctx->dpsm_abort = true; return -ETIMEDOUT; } if (status & SDMMC_STA_TXUNDERR) { - debug("%s: error SDMMC_STA_TXUNDERR (0x%x) for cmd %d\n", - __func__, status, cmd->cmdidx); + dev_dbg(dev, "error SDMMC_STA_TXUNDERR (0x%x) for cmd %d\n", + status, cmd->cmdidx); ctx->dpsm_abort = true; return -EIO; } if (status & SDMMC_STA_RXOVERR) { - debug("%s: error SDMMC_STA_RXOVERR (0x%x) for cmd %d\n", - __func__, status, cmd->cmdidx); + dev_dbg(dev, "error SDMMC_STA_RXOVERR (0x%x) for cmd %d\n", + status, cmd->cmdidx); ctx->dpsm_abort = true; return -EIO; } if (status & SDMMC_STA_IDMATE) { - debug("%s: error SDMMC_STA_IDMATE (0x%x) for cmd %d\n", - __func__, status, cmd->cmdidx); + dev_dbg(dev, "error SDMMC_STA_IDMATE (0x%x) for cmd %d\n", + status, cmd->cmdidx); ctx->dpsm_abort = true; return -EIO; } @@ -448,19 +455,18 @@ retry_cmd: if (data) { ctx.data_length = data->blocks * data->blocksize; - stm32_sdmmc2_start_data(priv, data, &ctx); + stm32_sdmmc2_start_data(dev, data, &ctx); } - stm32_sdmmc2_start_cmd(priv, cmd, cmdat, &ctx); + stm32_sdmmc2_start_cmd(dev, cmd, cmdat, &ctx); - debug("%s: send cmd %d data: 0x%x @ 0x%x\n", - __func__, cmd->cmdidx, - data ? ctx.data_length : 0, (unsigned int)data); + dev_dbg(dev, "send cmd %d data: 0x%x @ 0x%x\n", + cmd->cmdidx, data ? ctx.data_length : 0, (unsigned int)data); - ret = stm32_sdmmc2_end_cmd(priv, cmd, &ctx); + ret = stm32_sdmmc2_end_cmd(dev, cmd, &ctx); if (data && !ret) - ret = stm32_sdmmc2_end_data(priv, cmd, data, &ctx); + ret = stm32_sdmmc2_end_data(dev, cmd, data, &ctx); /* Clear flags */ writel(SDMMC_ICR_STATIC_FLAGS, priv->base + SDMMC_ICR); @@ -478,26 +484,24 @@ retry_cmd: stop_cmd.cmdarg = 0; stop_cmd.resp_type = MMC_RSP_R1b; - debug("%s: send STOP command to abort dpsm treatments\n", - __func__); + dev_dbg(dev, "send STOP command to abort dpsm treatments\n"); ctx.data_length = 0; - stm32_sdmmc2_start_cmd(priv, &stop_cmd, + stm32_sdmmc2_start_cmd(dev, &stop_cmd, SDMMC_CMD_CMDSTOP, &ctx); - stm32_sdmmc2_end_cmd(priv, &stop_cmd, &ctx); + stm32_sdmmc2_end_cmd(dev, &stop_cmd, &ctx); writel(SDMMC_ICR_STATIC_FLAGS, priv->base + SDMMC_ICR); } if ((ret != -ETIMEDOUT) && (ret != 0) && retry) { - printf("%s: cmd %d failed, retrying ...\n", - __func__, cmd->cmdidx); + dev_err(dev, "cmd %d failed, retrying ...\n", cmd->cmdidx); retry--; goto retry_cmd; } - debug("%s: end for CMD %d, ret = %d\n", __func__, cmd->cmdidx, ret); + dev_dbg(dev, "end for CMD %d, ret = %d\n", cmd->cmdidx, ret); return ret; } @@ -579,8 +583,8 @@ static int stm32_sdmmc2_set_ios(struct udevice *dev) u32 sys_clock = clk_get_rate(&priv->clk); u32 clk = 0; - debug("%s: bus_with = %d, clock = %d\n", __func__, - mmc->bus_width, mmc->clock); + dev_dbg(dev, "bus_with = %d, clock = %d\n", + mmc->bus_width, mmc->clock); if (mmc->clk_disable) stm32_sdmmc2_pwrcycle(priv); @@ -616,7 +620,7 @@ static int stm32_sdmmc2_getcd(struct udevice *dev) { struct stm32_sdmmc2_priv *priv = dev_get_priv(dev); - debug("stm32_sdmmc2_getcd called\n"); + dev_dbg(dev, "%s called\n", __func__); if (dm_gpio_is_valid(&priv->cd_gpio)) return dm_gpio_get_value(&priv->cd_gpio); diff --git a/drivers/mmc/xenon_sdhci.c b/drivers/mmc/xenon_sdhci.c index b8e833e6a3c..14fec4b8e78 100644 --- a/drivers/mmc/xenon_sdhci.c +++ b/drivers/mmc/xenon_sdhci.c @@ -104,18 +104,6 @@ DECLARE_GLOBAL_DATA_PTR; /* Hyperion only have one slot 0 */ #define XENON_MMC_SLOT_ID_HYPERION 0 -#define MMC_TIMING_LEGACY 0 -#define MMC_TIMING_MMC_HS 1 -#define MMC_TIMING_SD_HS 2 -#define MMC_TIMING_UHS_SDR12 3 -#define MMC_TIMING_UHS_SDR25 4 -#define MMC_TIMING_UHS_SDR50 5 -#define MMC_TIMING_UHS_SDR104 6 -#define MMC_TIMING_UHS_DDR50 7 -#define MMC_TIMING_MMC_DDR52 8 -#define MMC_TIMING_MMC_HS200 9 -#define MMC_TIMING_MMC_HS400 10 - #define XENON_MMC_MAX_CLK 400000000 #define XENON_MMC_3V3_UV 3300000 #define XENON_MMC_1V8_UV 1800000 |