summaryrefslogtreecommitdiff
path: root/drivers/mmc/host/sdhci-of-dwcmshc.c
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/mmc/host/sdhci-of-dwcmshc.c')
-rw-r--r--drivers/mmc/host/sdhci-of-dwcmshc.c19
1 files changed, 15 insertions, 4 deletions
diff --git a/drivers/mmc/host/sdhci-of-dwcmshc.c b/drivers/mmc/host/sdhci-of-dwcmshc.c
index a7343d4bc50e..d1490469184b 100644
--- a/drivers/mmc/host/sdhci-of-dwcmshc.c
+++ b/drivers/mmc/host/sdhci-of-dwcmshc.c
@@ -48,6 +48,7 @@
#define DWCMSHC_EMMC_DLL_RXCLK_SRCSEL 29
#define DWCMSHC_EMMC_DLL_START_POINT 16
#define DWCMSHC_EMMC_DLL_INC 8
+#define DWCMSHC_EMMC_DLL_BYPASS BIT(24)
#define DWCMSHC_EMMC_DLL_DLYENA BIT(27)
#define DLL_TXCLK_TAPNUM_DEFAULT 0x10
#define DLL_TXCLK_TAPNUM_90_DEGREES 0xA
@@ -60,6 +61,7 @@
#define DLL_RXCLK_NO_INVERTER 1
#define DLL_RXCLK_INVERTER 0
#define DLL_CMDOUT_TAPNUM_90_DEGREES 0x8
+#define DLL_RXCLK_ORI_GATE BIT(31)
#define DLL_CMDOUT_TAPNUM_FROM_SW BIT(24)
#define DLL_CMDOUT_SRC_CLK_NEG BIT(28)
#define DLL_CMDOUT_EN_SRC_CLK_NEG BIT(29)
@@ -234,9 +236,12 @@ static void dwcmshc_rk3568_set_clock(struct sdhci_host *host, unsigned int clock
sdhci_writel(host, extra, reg);
if (clock <= 52000000) {
- /* Disable DLL and reset both of sample and drive clock */
- sdhci_writel(host, 0, DWCMSHC_EMMC_DLL_CTRL);
- sdhci_writel(host, 0, DWCMSHC_EMMC_DLL_RXCLK);
+ /*
+ * Disable DLL and reset both of sample and drive clock.
+ * The bypass bit and start bit need to be set if DLL is not locked.
+ */
+ sdhci_writel(host, DWCMSHC_EMMC_DLL_BYPASS | DWCMSHC_EMMC_DLL_START, DWCMSHC_EMMC_DLL_CTRL);
+ sdhci_writel(host, DLL_RXCLK_ORI_GATE, DWCMSHC_EMMC_DLL_RXCLK);
sdhci_writel(host, 0, DWCMSHC_EMMC_DLL_TXCLK);
sdhci_writel(host, 0, DECMSHC_EMMC_DLL_CMDOUT);
/*
@@ -279,7 +284,7 @@ static void dwcmshc_rk3568_set_clock(struct sdhci_host *host, unsigned int clock
}
extra = 0x1 << 16 | /* tune clock stop en */
- 0x2 << 17 | /* pre-change delay */
+ 0x3 << 17 | /* pre-change delay */
0x3 << 19; /* post-change delay */
sdhci_writel(host, extra, dwc_priv->vendor_specific_area1 + DWCMSHC_EMMC_ATCTRL);
@@ -446,6 +451,7 @@ static const struct acpi_device_id sdhci_dwcmshc_acpi_ids[] = {
},
{}
};
+MODULE_DEVICE_TABLE(acpi, sdhci_dwcmshc_acpi_ids);
#endif
static int dwcmshc_probe(struct platform_device *pdev)
@@ -528,6 +534,11 @@ static int dwcmshc_probe(struct platform_device *pdev)
goto err_clk;
}
+#ifdef CONFIG_ACPI
+ if (pltfm_data == &sdhci_dwcmshc_bf3_pdata)
+ sdhci_enable_v4_mode(host);
+#endif
+
host->mmc->caps |= MMC_CAP_WAIT_WHILE_BUSY;
err = sdhci_setup_host(host);