diff options
author | Venkat Gopalakrishnan <venkatg@codeaurora.org> | 2015-02-03 16:10:07 -0800 |
---|---|---|
committer | Subhash Jadavani <subhashj@codeaurora.org> | 2016-05-31 15:26:08 -0700 |
commit | 3426f39922bb0dec96a07a270cea0937f0096579 (patch) | |
tree | bbfa6efb5768d6764d053ccb0e547d5735a3f6fc /drivers | |
parent | 8b70321d56d4c4ca94b6a165ea22d45387d47c61 (diff) |
mmc: sdhci-msm: Update DLL reset sequence
The latest version of the SDCC core requires a change in the reset
sequence for DLL tuning. Make necessary changes as needed.
Change-Id: I69e972c08e89efebff9822de6d0e59692784652e
Signed-off-by: Venkat Gopalakrishnan <venkatg@codeaurora.org>
Diffstat (limited to 'drivers')
-rw-r--r-- | drivers/mmc/host/sdhci-msm.c | 48 |
1 files changed, 48 insertions, 0 deletions
diff --git a/drivers/mmc/host/sdhci-msm.c b/drivers/mmc/host/sdhci-msm.c index ebc160a17ce6..96a16ac05a9c 100644 --- a/drivers/mmc/host/sdhci-msm.c +++ b/drivers/mmc/host/sdhci-msm.c @@ -153,6 +153,8 @@ #define CORE_DLL_CONFIG_2 0x1B4 #define CORE_DDR_CAL_EN (1 << 0) +#define CORE_FLL_CYCLE_CNT (1 << 18) +#define CORE_DLL_CLOCK_DISABLE (1 << 21) #define CORE_DDR_CONFIG 0x1B8 #define DDR_CONFIG_POR_VAL 0x80040853 @@ -162,6 +164,7 @@ #define SDHCI_MSM_MMC_CLK_GATE_DELAY 200 /* msecs */ #define CORE_FREQ_100MHZ (100 * 1000 * 1000) +#define TCXO_FREQ 19200000 #define INVALID_TUNING_PHASE -1 @@ -313,6 +316,7 @@ struct sdhci_msm_host { struct device_attribute auto_cmd21_attr; atomic_t controller_clock; bool use_cdclp533; + bool use_updated_dll_reset; }; enum vdd_io_level { @@ -643,6 +647,8 @@ static inline void msm_cm_dll_set_freq(struct sdhci_host *host) /* Initialize the DLL (Programmable Delay Line ) */ static int msm_init_cm_dll(struct sdhci_host *host) { + struct sdhci_pltfm_host *pltfm_host = sdhci_priv(host); + struct sdhci_msm_host *msm_host = pltfm_host->priv; struct mmc_host *mmc = host->mmc; int rc = 0; unsigned long flags; @@ -667,6 +673,17 @@ static int msm_init_cm_dll(struct sdhci_host *host) curr_pwrsave = false; } + if (msm_host->use_updated_dll_reset) { + /* Disable the DLL clock */ + writel_relaxed((readl_relaxed(host->ioaddr + CORE_DLL_CONFIG) + & ~CORE_CK_OUT_EN), + host->ioaddr + CORE_DLL_CONFIG); + + writel_relaxed((readl_relaxed(host->ioaddr + CORE_DLL_CONFIG_2) + | CORE_DLL_CLOCK_DISABLE), + host->ioaddr + CORE_DLL_CONFIG_2); + } + /* Write 1 to DLL_RST bit of DLL_CONFIG register */ writel_relaxed((readl_relaxed(host->ioaddr + CORE_DLL_CONFIG) | CORE_DLL_RST), host->ioaddr + CORE_DLL_CONFIG); @@ -676,6 +693,22 @@ static int msm_init_cm_dll(struct sdhci_host *host) | CORE_DLL_PDN), host->ioaddr + CORE_DLL_CONFIG); msm_cm_dll_set_freq(host); + if (msm_host->use_updated_dll_reset) { + u32 mclk_freq = 0; + + if ((readl_relaxed(host->ioaddr + CORE_DLL_CONFIG_2) + & CORE_FLL_CYCLE_CNT)) + mclk_freq = (u32) ((host->clock / TCXO_FREQ) * 8); + else + mclk_freq = (u32) ((host->clock / TCXO_FREQ) * 4); + + writel_relaxed(((readl_relaxed(host->ioaddr + CORE_DLL_CONFIG_2) + & ~(0xFF << 10)) | (mclk_freq << 10)), + host->ioaddr + CORE_DLL_CONFIG_2); + /* wait for 5us before enabling DLL clock */ + udelay(5); + } + /* Write 0 to DLL_RST bit of DLL_CONFIG register */ writel_relaxed((readl_relaxed(host->ioaddr + CORE_DLL_CONFIG) & ~CORE_DLL_RST), host->ioaddr + CORE_DLL_CONFIG); @@ -684,6 +717,14 @@ static int msm_init_cm_dll(struct sdhci_host *host) writel_relaxed((readl_relaxed(host->ioaddr + CORE_DLL_CONFIG) & ~CORE_DLL_PDN), host->ioaddr + CORE_DLL_CONFIG); + if (msm_host->use_updated_dll_reset) { + msm_cm_dll_set_freq(host); + /* Enable the DLL clock */ + writel_relaxed((readl_relaxed(host->ioaddr + CORE_DLL_CONFIG_2) + & ~CORE_DLL_CLOCK_DISABLE), + host->ioaddr + CORE_DLL_CONFIG_2); + } + /* Set DLL_EN bit to 1. */ writel_relaxed((readl_relaxed(host->ioaddr + CORE_DLL_CONFIG) | CORE_DLL_EN), host->ioaddr + CORE_DLL_CONFIG); @@ -2815,6 +2856,13 @@ static void sdhci_set_default_hw_caps(struct sdhci_msm_host *msm_host, msm_host->use_cdclp533 = true; /* + * SDCC 5 controller with major version 1, minor version 0x42 and later + * will require additional steps when resetting DLL. + */ + if ((major == 1) && (minor >= 0x42)) + msm_host->use_updated_dll_reset = true; + + /* * Mask 64-bit support for controller with 32-bit address bus so that * smaller descriptor size will be used and improve memory consumption. * In case bus addressing ever changes, controller version should be |