diff options
Diffstat (limited to 'drivers/mmc')
-rw-r--r-- | drivers/mmc/Kconfig | 7 | ||||
-rw-r--r-- | drivers/mmc/dw_mmc.c | 6 | ||||
-rw-r--r-- | drivers/mmc/fsl_esdhc.c | 17 | ||||
-rw-r--r-- | drivers/mmc/fsl_esdhc_imx.c | 38 | ||||
-rw-r--r-- | drivers/mmc/mmc-uclass.c | 24 | ||||
-rw-r--r-- | drivers/mmc/mmc_private.h | 1 | ||||
-rw-r--r-- | drivers/mmc/mtk-sd.c | 5 | ||||
-rw-r--r-- | drivers/mmc/socfpga_dw_mmc.c | 2 |
8 files changed, 53 insertions, 47 deletions
diff --git a/drivers/mmc/Kconfig b/drivers/mmc/Kconfig index 8901456..0909f50 100644 --- a/drivers/mmc/Kconfig +++ b/drivers/mmc/Kconfig @@ -798,6 +798,13 @@ config FSL_ESDHC_33V_IO_RELIABILITY_WORKAROUND This option assumes no hotplug, and u-boot has to make all the way to to linux to use 1.8v UHS-I speed mode if has card. +config FSL_ESDHC_VS33_NOT_SUPPORT + bool "3.3V power supply not supported" + depends on FSL_ESDHC + help + For eSDHC, power supply is through peripheral circuit. 3.3V support is + common. Select this if 3.3V power supply not supported. + config FSL_ESDHC_IMX bool "Freescale/NXP i.MX eSDHC controller support" help diff --git a/drivers/mmc/dw_mmc.c b/drivers/mmc/dw_mmc.c index 7c8a312..a949dad 100644 --- a/drivers/mmc/dw_mmc.c +++ b/drivers/mmc/dw_mmc.c @@ -166,7 +166,9 @@ static int dwmci_data_transfer(struct dwmci_host *host, struct mmc_data *data) if (host->fifo_mode && size) { len = 0; if (data->flags == MMC_DATA_READ && - (mask & DWMCI_INTMSK_RXDR)) { + (mask & (DWMCI_INTMSK_RXDR | DWMCI_INTMSK_DTO))) { + dwmci_writel(host, DWMCI_RINTSTS, + DWMCI_INTMSK_RXDR | DWMCI_INTMSK_DTO); while (size) { ret = dwmci_fifo_ready(host, DWMCI_FIFO_EMPTY, @@ -182,8 +184,6 @@ static int dwmci_data_transfer(struct dwmci_host *host, struct mmc_data *data) dwmci_readl(host, DWMCI_DATA); size = size > len ? (size - len) : 0; } - dwmci_writel(host, DWMCI_RINTSTS, - DWMCI_INTMSK_RXDR); } else if (data->flags == MMC_DATA_WRITE && (mask & DWMCI_INTMSK_TXDR)) { while (size) { diff --git a/drivers/mmc/fsl_esdhc.c b/drivers/mmc/fsl_esdhc.c index 7501fdb..1d98fa6 100644 --- a/drivers/mmc/fsl_esdhc.c +++ b/drivers/mmc/fsl_esdhc.c @@ -1,7 +1,7 @@ // SPDX-License-Identifier: GPL-2.0+ /* * Copyright 2007, 2010-2011 Freescale Semiconductor, Inc - * Copyright 2019-2020 NXP + * Copyright 2019-2021 NXP * Andy Fleming * * Based vaguely on the pxa mmc code: @@ -795,10 +795,21 @@ static void fsl_esdhc_get_cfg_common(struct fsl_esdhc_priv *priv, u32 caps; caps = esdhc_read32(®s->hostcapblt); + + /* + * For eSDHC, power supply is through peripheral circuit. Some eSDHC + * versions have value 0 of the bit but that does not reflect the + * truth. 3.3V is common for SD/MMC, and is supported for all boards + * with eSDHC in current u-boot. So, make 3.3V is supported in + * default in code. CONFIG_FSL_ESDHC_VS33_NOT_SUPPORT can be enabled + * if future board does not support 3.3V. + */ + caps |= HOSTCAPBLT_VS33; + if (IS_ENABLED(CONFIG_FSL_ESDHC_VS33_NOT_SUPPORT)) + caps &= ~HOSTCAPBLT_VS33; + if (IS_ENABLED(CONFIG_SYS_FSL_ERRATUM_ESDHC135)) caps &= ~(HOSTCAPBLT_SRS | HOSTCAPBLT_VS18 | HOSTCAPBLT_VS30); - if (IS_ENABLED(CONFIG_SYS_FSL_MMC_HAS_CAPBLT_VS33)) - caps |= HOSTCAPBLT_VS33; if (caps & HOSTCAPBLT_VS18) cfg->voltages |= MMC_VDD_165_195; if (caps & HOSTCAPBLT_VS30) diff --git a/drivers/mmc/fsl_esdhc_imx.c b/drivers/mmc/fsl_esdhc_imx.c index a467583..465d935 100644 --- a/drivers/mmc/fsl_esdhc_imx.c +++ b/drivers/mmc/fsl_esdhc_imx.c @@ -1,7 +1,7 @@ // SPDX-License-Identifier: GPL-2.0+ /* * Copyright 2007, 2010-2011 Freescale Semiconductor, Inc - * Copyright 2019 NXP Semiconductors + * Copyright 2019, 2021 NXP * Andy Fleming * Yangbo Lu <yangbo.lu@nxp.com> * @@ -653,10 +653,7 @@ static void set_sysctl(struct fsl_esdhc_priv *priv, struct mmc *mmc, uint clock) clk = (pre_div << 8) | (div << 4); #ifdef CONFIG_FSL_USDHC - esdhc_clrbits32(®s->vendorspec, VENDORSPEC_FRC_SDCLK_ON); - ret = readx_poll_timeout(esdhc_read32, ®s->prsstat, tmp, tmp & PRSSTAT_SDOFF, 100); - if (ret) - pr_warn("fsl_esdhc_imx: Internal clock never gate off.\n"); + esdhc_clrbits32(®s->vendorspec, VENDORSPEC_CKEN); #else esdhc_clrbits32(®s->sysctl, SYSCTL_CKEN); #endif @@ -668,7 +665,7 @@ static void set_sysctl(struct fsl_esdhc_priv *priv, struct mmc *mmc, uint clock) pr_warn("fsl_esdhc_imx: Internal clock never stabilised.\n"); #ifdef CONFIG_FSL_USDHC - esdhc_setbits32(®s->vendorspec, VENDORSPEC_FRC_SDCLK_ON); + esdhc_setbits32(®s->vendorspec, VENDORSPEC_PEREN | VENDORSPEC_CKEN); #else esdhc_setbits32(®s->sysctl, SYSCTL_PEREN | SYSCTL_CKEN); #endif @@ -723,14 +720,8 @@ static void esdhc_set_strobe_dll(struct mmc *mmc) struct fsl_esdhc_priv *priv = dev_get_priv(mmc->dev); struct fsl_esdhc *regs = priv->esdhc_regs; u32 val; - u32 tmp; - int ret; if (priv->clock > ESDHC_STROBE_DLL_CLK_FREQ) { - esdhc_clrbits32(®s->vendorspec, VENDORSPEC_FRC_SDCLK_ON); - ret = readx_poll_timeout(esdhc_read32, ®s->prsstat, tmp, tmp & PRSSTAT_SDOFF, 100); - if (ret) - pr_warn("fsl_esdhc_imx: Internal clock never gate off.\n"); esdhc_write32(®s->strobe_dllctrl, ESDHC_STROBE_DLL_CTRL_RESET); /* @@ -748,7 +739,6 @@ static void esdhc_set_strobe_dll(struct mmc *mmc) pr_warn("HS400 strobe DLL status REF not lock!\n"); if (!(val & ESDHC_STROBE_DLL_STS_SLV_LOCK)) pr_warn("HS400 strobe DLL status SLV not lock!\n"); - esdhc_setbits32(®s->vendorspec, VENDORSPEC_FRC_SDCLK_ON); } } @@ -865,7 +855,7 @@ static void esdhc_stop_tuning(struct mmc *mmc) cmd.cmdarg = 0; cmd.resp_type = MMC_RSP_R1b; - dm_mmc_send_cmd(mmc->dev, &cmd, NULL); + mmc_send_cmd(mmc, &cmd, NULL); } static int fsl_esdhc_execute_tuning(struct udevice *dev, uint32_t opcode) @@ -980,18 +970,14 @@ static int esdhc_set_ios_common(struct fsl_esdhc_priv *priv, struct mmc *mmc) #ifdef MMC_SUPPORTS_TUNING if (mmc->clk_disable) { #ifdef CONFIG_FSL_USDHC - u32 tmp; - - esdhc_clrbits32(®s->vendorspec, VENDORSPEC_FRC_SDCLK_ON); - ret = readx_poll_timeout(esdhc_read32, ®s->prsstat, tmp, tmp & PRSSTAT_SDOFF, 100); - if (ret) - pr_warn("fsl_esdhc_imx: Internal clock never gate off.\n"); + esdhc_clrbits32(®s->vendorspec, VENDORSPEC_CKEN); #else esdhc_clrbits32(®s->sysctl, SYSCTL_CKEN); #endif } else { #ifdef CONFIG_FSL_USDHC - esdhc_setbits32(®s->vendorspec, VENDORSPEC_FRC_SDCLK_ON); + esdhc_setbits32(®s->vendorspec, VENDORSPEC_PEREN | + VENDORSPEC_CKEN); #else esdhc_setbits32(®s->sysctl, SYSCTL_PEREN | SYSCTL_CKEN); #endif @@ -1067,7 +1053,7 @@ static int esdhc_init_common(struct fsl_esdhc_priv *priv, struct mmc *mmc) #ifndef CONFIG_FSL_USDHC esdhc_setbits32(®s->sysctl, SYSCTL_HCKEN | SYSCTL_IPGEN); #else - esdhc_setbits32(®s->vendorspec, VENDORSPEC_FRC_SDCLK_ON); + esdhc_setbits32(®s->vendorspec, VENDORSPEC_HCKEN | VENDORSPEC_IPGEN); #endif /* Set the initial clock speed */ @@ -1205,7 +1191,8 @@ static int fsl_esdhc_init(struct fsl_esdhc_priv *priv, esdhc_write32(®s->autoc12err, 0); esdhc_write32(®s->clktunectrlstatus, 0); #else - esdhc_setbits32(®s->vendorspec, VENDORSPEC_FRC_SDCLK_ON); + esdhc_setbits32(®s->vendorspec, VENDORSPEC_PEREN | + VENDORSPEC_HCKEN | VENDORSPEC_IPGEN | VENDORSPEC_CKEN); #endif if (priv->vs18_enable) @@ -1234,11 +1221,6 @@ static int fsl_esdhc_init(struct fsl_esdhc_priv *priv, ESDHC_HOSTCAPBLT_VS18 | ESDHC_HOSTCAPBLT_VS30); #endif -/* T4240 host controller capabilities register should have VS33 bit */ -#ifdef CONFIG_SYS_FSL_MMC_HAS_CAPBLT_VS33 - caps = caps | ESDHC_HOSTCAPBLT_VS33; -#endif - if (caps & ESDHC_HOSTCAPBLT_VS18) voltage_caps |= MMC_VDD_165_195; if (caps & ESDHC_HOSTCAPBLT_VS30) diff --git a/drivers/mmc/mmc-uclass.c b/drivers/mmc/mmc-uclass.c index d36aae3..579d7a1 100644 --- a/drivers/mmc/mmc-uclass.c +++ b/drivers/mmc/mmc-uclass.c @@ -15,7 +15,7 @@ #include <linux/compat.h> #include "mmc_private.h" -int dm_mmc_get_b_max(struct udevice *dev, void *dst, lbaint_t blkcnt) +static int dm_mmc_get_b_max(struct udevice *dev, void *dst, lbaint_t blkcnt) { struct dm_mmc_ops *ops = mmc_get_ops(dev); struct mmc *mmc = mmc_get_mmc_dev(dev); @@ -31,7 +31,7 @@ int mmc_get_b_max(struct mmc *mmc, void *dst, lbaint_t blkcnt) return dm_mmc_get_b_max(mmc->dev, dst, blkcnt); } -int dm_mmc_send_cmd(struct udevice *dev, struct mmc_cmd *cmd, +static int dm_mmc_send_cmd(struct udevice *dev, struct mmc_cmd *cmd, struct mmc_data *data) { struct mmc *mmc = mmc_get_mmc_dev(dev); @@ -53,7 +53,7 @@ int mmc_send_cmd(struct mmc *mmc, struct mmc_cmd *cmd, struct mmc_data *data) return dm_mmc_send_cmd(mmc->dev, cmd, data); } -int dm_mmc_set_ios(struct udevice *dev) +static int dm_mmc_set_ios(struct udevice *dev) { struct dm_mmc_ops *ops = mmc_get_ops(dev); @@ -67,7 +67,7 @@ int mmc_set_ios(struct mmc *mmc) return dm_mmc_set_ios(mmc->dev); } -int dm_mmc_wait_dat0(struct udevice *dev, int state, int timeout_us) +static int dm_mmc_wait_dat0(struct udevice *dev, int state, int timeout_us) { struct dm_mmc_ops *ops = mmc_get_ops(dev); @@ -81,7 +81,7 @@ int mmc_wait_dat0(struct mmc *mmc, int state, int timeout_us) return dm_mmc_wait_dat0(mmc->dev, state, timeout_us); } -int dm_mmc_get_wp(struct udevice *dev) +static int dm_mmc_get_wp(struct udevice *dev) { struct dm_mmc_ops *ops = mmc_get_ops(dev); @@ -95,7 +95,7 @@ int mmc_getwp(struct mmc *mmc) return dm_mmc_get_wp(mmc->dev); } -int dm_mmc_get_cd(struct udevice *dev) +static int dm_mmc_get_cd(struct udevice *dev) { struct dm_mmc_ops *ops = mmc_get_ops(dev); @@ -110,7 +110,7 @@ int mmc_getcd(struct mmc *mmc) } #ifdef MMC_SUPPORTS_TUNING -int dm_mmc_execute_tuning(struct udevice *dev, uint opcode) +static int dm_mmc_execute_tuning(struct udevice *dev, uint opcode) { struct dm_mmc_ops *ops = mmc_get_ops(dev); @@ -126,7 +126,7 @@ int mmc_execute_tuning(struct mmc *mmc, uint opcode) #endif #if CONFIG_IS_ENABLED(MMC_HS400_ES_SUPPORT) -int dm_mmc_set_enhanced_strobe(struct udevice *dev) +static int dm_mmc_set_enhanced_strobe(struct udevice *dev) { struct dm_mmc_ops *ops = mmc_get_ops(dev); @@ -142,7 +142,7 @@ int mmc_set_enhanced_strobe(struct mmc *mmc) } #endif -int dm_mmc_hs400_prepare_ddr(struct udevice *dev) +static int dm_mmc_hs400_prepare_ddr(struct udevice *dev) { struct dm_mmc_ops *ops = mmc_get_ops(dev); @@ -157,7 +157,7 @@ int mmc_hs400_prepare_ddr(struct mmc *mmc) return dm_mmc_hs400_prepare_ddr(mmc->dev); } -int dm_mmc_host_power_cycle(struct udevice *dev) +static int dm_mmc_host_power_cycle(struct udevice *dev) { struct dm_mmc_ops *ops = mmc_get_ops(dev); @@ -171,7 +171,7 @@ int mmc_host_power_cycle(struct mmc *mmc) return dm_mmc_host_power_cycle(mmc->dev); } -int dm_mmc_deferred_probe(struct udevice *dev) +static int dm_mmc_deferred_probe(struct udevice *dev) { struct dm_mmc_ops *ops = mmc_get_ops(dev); @@ -186,7 +186,7 @@ int mmc_deferred_probe(struct mmc *mmc) return dm_mmc_deferred_probe(mmc->dev); } -int dm_mmc_reinit(struct udevice *dev) +static int dm_mmc_reinit(struct udevice *dev) { struct dm_mmc_ops *ops = mmc_get_ops(dev); diff --git a/drivers/mmc/mmc_private.h b/drivers/mmc/mmc_private.h index a0900e8..a6cd250 100644 --- a/drivers/mmc/mmc_private.h +++ b/drivers/mmc/mmc_private.h @@ -12,7 +12,6 @@ #include <mmc.h> -int mmc_send_cmd(struct mmc *mmc, struct mmc_cmd *cmd, struct mmc_data *data); int mmc_send_status(struct mmc *mmc, unsigned int *status); int mmc_poll_for_busy(struct mmc *mmc, int timeout); diff --git a/drivers/mmc/mtk-sd.c b/drivers/mmc/mtk-sd.c index 48a764b..8599f09 100644 --- a/drivers/mmc/mtk-sd.c +++ b/drivers/mmc/mtk-sd.c @@ -232,6 +232,8 @@ #define SCLK_CYCLES_SHIFT 20 +#define MIN_BUS_CLK 200000 + #define CMD_INTS_MASK \ (MSDC_INT_CMDRDY | MSDC_INT_RSPCRCERR | MSDC_INT_CMDTMO) @@ -1639,6 +1641,9 @@ static int msdc_drv_probe(struct udevice *dev) else cfg->f_min = host->src_clk_freq / (4 * 4095); + if (cfg->f_min < MIN_BUS_CLK) + cfg->f_min = MIN_BUS_CLK; + if (cfg->f_max < cfg->f_min || cfg->f_max > host->src_clk_freq) cfg->f_max = host->src_clk_freq; diff --git a/drivers/mmc/socfpga_dw_mmc.c b/drivers/mmc/socfpga_dw_mmc.c index d6d2d57..be3d8bf 100644 --- a/drivers/mmc/socfpga_dw_mmc.c +++ b/drivers/mmc/socfpga_dw_mmc.c @@ -144,6 +144,8 @@ static int socfpga_dwmmc_of_to_plat(struct udevice *dev) "smplsel", 0); host->priv = priv; + host->fifo_mode = dev_read_bool(dev, "fifo-mode"); + return 0; } |