aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/mmc
diff options
context:
space:
mode:
authorJaehoon Chung <jh80.chung@samsung.com>2016-01-20 21:01:06 -0500
committerUlf Hansson <ulf.hansson@linaro.org>2016-02-29 05:03:09 -0500
commitaaaaeb7a933471f6413ca44dd36efd57f2fa9429 (patch)
tree4685e0bdfe50b969e2661e758f7e676bddd9bfe6 /drivers/mmc
parent07d97d872359d15f0f50f3bceb8f932be99a2226 (diff)
mmc: dw_mmc: remove the prepare_command hook
This patch removes the prepare_command hook from entire dw_mmc driver. Now, almost all SoCs are using by default, except Exynos. It seems that dwmmc controller is using unnecessary hook. To know whether needs to set this bit or not, add the DW_MMC_CARD_NO_USE_HOLD bit. If some SoCs need to disable this in future, just set the DW_MMC_CARD_NO_USE_HOLD bit. set_bit(DW_MMC_CARD_NO_USE_HOLD, &slot->flags), Signed-off-by: Jaehoon Chung <jh80.chung@samsung.com> Tested-by: Shawn Lin <shawn.lin@rock-chips.com> Reviewed-by: Shawn Lin <shawn.lin@rock-chips.com> Signed-off-by: Ulf Hansson <ulf.hansson@linaro.org>
Diffstat (limited to 'drivers/mmc')
-rw-r--r--drivers/mmc/host/dw_mmc-exynos.c31
-rw-r--r--drivers/mmc/host/dw_mmc-pltfm.c19
-rw-r--r--drivers/mmc/host/dw_mmc-rockchip.c7
-rw-r--r--drivers/mmc/host/dw_mmc.c5
-rw-r--r--drivers/mmc/host/dw_mmc.h3
5 files changed, 15 insertions, 50 deletions
diff --git a/drivers/mmc/host/dw_mmc-exynos.c b/drivers/mmc/host/dw_mmc-exynos.c
index 3a7e835a0033..8790f2afc057 100644
--- a/drivers/mmc/host/dw_mmc-exynos.c
+++ b/drivers/mmc/host/dw_mmc-exynos.c
@@ -145,6 +145,16 @@ static void dw_mci_exynos_set_clksel_timing(struct dw_mci *host, u32 timing)
145 mci_writel(host, CLKSEL64, clksel); 145 mci_writel(host, CLKSEL64, clksel);
146 else 146 else
147 mci_writel(host, CLKSEL, clksel); 147 mci_writel(host, CLKSEL, clksel);
148
149 /*
150 * Exynos4412 and Exynos5250 extends the use of CMD register with the
151 * use of bit 29 (which is reserved on standard MSHC controllers) for
152 * optionally bypassing the HOLD register for command and data. The
153 * HOLD register should be bypassed in case there is no phase shift
154 * applied on CMD/DATA that is sent to the card.
155 */
156 if (!SDMMC_CLKSEL_GET_DRV_WD3(clksel))
157 set_bit(DW_MMC_CARD_NO_USE_HOLD, &host->cur_slot->flags);
148} 158}
149 159
150#ifdef CONFIG_PM_SLEEP 160#ifdef CONFIG_PM_SLEEP
@@ -202,26 +212,6 @@ static int dw_mci_exynos_resume_noirq(struct device *dev)
202#define dw_mci_exynos_resume_noirq NULL 212#define dw_mci_exynos_resume_noirq NULL
203#endif /* CONFIG_PM_SLEEP */ 213#endif /* CONFIG_PM_SLEEP */
204 214
205static void dw_mci_exynos_prepare_command(struct dw_mci *host, u32 *cmdr)
206{
207 struct dw_mci_exynos_priv_data *priv = host->priv;
208 /*
209 * Exynos4412 and Exynos5250 extends the use of CMD register with the
210 * use of bit 29 (which is reserved on standard MSHC controllers) for
211 * optionally bypassing the HOLD register for command and data. The
212 * HOLD register should be bypassed in case there is no phase shift
213 * applied on CMD/DATA that is sent to the card.
214 */
215 if (priv->ctrl_type == DW_MCI_TYPE_EXYNOS7 ||
216 priv->ctrl_type == DW_MCI_TYPE_EXYNOS7_SMU) {
217 if (SDMMC_CLKSEL_GET_DRV_WD3(mci_readl(host, CLKSEL64)))
218 *cmdr |= SDMMC_CMD_USE_HOLD_REG;
219 } else {
220 if (SDMMC_CLKSEL_GET_DRV_WD3(mci_readl(host, CLKSEL)))
221 *cmdr |= SDMMC_CMD_USE_HOLD_REG;
222 }
223}
224
225static void dw_mci_exynos_config_hs400(struct dw_mci *host, u32 timing) 215static void dw_mci_exynos_config_hs400(struct dw_mci *host, u32 timing)
226{ 216{
227 struct dw_mci_exynos_priv_data *priv = host->priv; 217 struct dw_mci_exynos_priv_data *priv = host->priv;
@@ -500,7 +490,6 @@ static const struct dw_mci_drv_data exynos_drv_data = {
500 .caps = exynos_dwmmc_caps, 490 .caps = exynos_dwmmc_caps,
501 .init = dw_mci_exynos_priv_init, 491 .init = dw_mci_exynos_priv_init,
502 .setup_clock = dw_mci_exynos_setup_clock, 492 .setup_clock = dw_mci_exynos_setup_clock,
503 .prepare_command = dw_mci_exynos_prepare_command,
504 .set_ios = dw_mci_exynos_set_ios, 493 .set_ios = dw_mci_exynos_set_ios,
505 .parse_dt = dw_mci_exynos_parse_dt, 494 .parse_dt = dw_mci_exynos_parse_dt,
506 .execute_tuning = dw_mci_exynos_execute_tuning, 495 .execute_tuning = dw_mci_exynos_execute_tuning,
diff --git a/drivers/mmc/host/dw_mmc-pltfm.c b/drivers/mmc/host/dw_mmc-pltfm.c
index 81bdeeb05a4d..c0bb0c793e84 100644
--- a/drivers/mmc/host/dw_mmc-pltfm.c
+++ b/drivers/mmc/host/dw_mmc-pltfm.c
@@ -26,19 +26,6 @@
26#include "dw_mmc.h" 26#include "dw_mmc.h"
27#include "dw_mmc-pltfm.h" 27#include "dw_mmc-pltfm.h"
28 28
29static void dw_mci_pltfm_prepare_command(struct dw_mci *host, u32 *cmdr)
30{
31 *cmdr |= SDMMC_CMD_USE_HOLD_REG;
32}
33
34static const struct dw_mci_drv_data socfpga_drv_data = {
35 .prepare_command = dw_mci_pltfm_prepare_command,
36};
37
38static const struct dw_mci_drv_data pistachio_drv_data = {
39 .prepare_command = dw_mci_pltfm_prepare_command,
40};
41
42int dw_mci_pltfm_register(struct platform_device *pdev, 29int dw_mci_pltfm_register(struct platform_device *pdev,
43 const struct dw_mci_drv_data *drv_data) 30 const struct dw_mci_drv_data *drv_data)
44{ 31{
@@ -94,10 +81,8 @@ EXPORT_SYMBOL_GPL(dw_mci_pltfm_pmops);
94 81
95static const struct of_device_id dw_mci_pltfm_match[] = { 82static const struct of_device_id dw_mci_pltfm_match[] = {
96 { .compatible = "snps,dw-mshc", }, 83 { .compatible = "snps,dw-mshc", },
97 { .compatible = "altr,socfpga-dw-mshc", 84 { .compatible = "altr,socfpga-dw-mshc", },
98 .data = &socfpga_drv_data }, 85 { .compatible = "img,pistachio-dw-mshc", },
99 { .compatible = "img,pistachio-dw-mshc",
100 .data = &pistachio_drv_data },
101 {}, 86 {},
102}; 87};
103MODULE_DEVICE_TABLE(of, dw_mci_pltfm_match); 88MODULE_DEVICE_TABLE(of, dw_mci_pltfm_match);
diff --git a/drivers/mmc/host/dw_mmc-rockchip.c b/drivers/mmc/host/dw_mmc-rockchip.c
index d9c92f31da64..84e50f3a64b6 100644
--- a/drivers/mmc/host/dw_mmc-rockchip.c
+++ b/drivers/mmc/host/dw_mmc-rockchip.c
@@ -26,11 +26,6 @@ struct dw_mci_rockchip_priv_data {
26 int default_sample_phase; 26 int default_sample_phase;
27}; 27};
28 28
29static void dw_mci_rockchip_prepare_command(struct dw_mci *host, u32 *cmdr)
30{
31 *cmdr |= SDMMC_CMD_USE_HOLD_REG;
32}
33
34static int dw_mci_rk3288_setup_clock(struct dw_mci *host) 29static int dw_mci_rk3288_setup_clock(struct dw_mci *host)
35{ 30{
36 host->bus_hz /= RK3288_CLKGEN_DIV; 31 host->bus_hz /= RK3288_CLKGEN_DIV;
@@ -240,12 +235,10 @@ static int dw_mci_rockchip_init(struct dw_mci *host)
240} 235}
241 236
242static const struct dw_mci_drv_data rk2928_drv_data = { 237static const struct dw_mci_drv_data rk2928_drv_data = {
243 .prepare_command = dw_mci_rockchip_prepare_command,
244 .init = dw_mci_rockchip_init, 238 .init = dw_mci_rockchip_init,
245}; 239};
246 240
247static const struct dw_mci_drv_data rk3288_drv_data = { 241static const struct dw_mci_drv_data rk3288_drv_data = {
248 .prepare_command = dw_mci_rockchip_prepare_command,
249 .set_ios = dw_mci_rk3288_set_ios, 242 .set_ios = dw_mci_rk3288_set_ios,
250 .execute_tuning = dw_mci_rk3288_execute_tuning, 243 .execute_tuning = dw_mci_rk3288_execute_tuning,
251 .parse_dt = dw_mci_rk3288_parse_dt, 244 .parse_dt = dw_mci_rk3288_parse_dt,
diff --git a/drivers/mmc/host/dw_mmc.c b/drivers/mmc/host/dw_mmc.c
index 40fcf9e6bfc6..7d6bd9d32b48 100644
--- a/drivers/mmc/host/dw_mmc.c
+++ b/drivers/mmc/host/dw_mmc.c
@@ -234,7 +234,6 @@ static u32 dw_mci_prepare_command(struct mmc_host *mmc, struct mmc_command *cmd)
234 struct mmc_data *data; 234 struct mmc_data *data;
235 struct dw_mci_slot *slot = mmc_priv(mmc); 235 struct dw_mci_slot *slot = mmc_priv(mmc);
236 struct dw_mci *host = slot->host; 236 struct dw_mci *host = slot->host;
237 const struct dw_mci_drv_data *drv_data = slot->host->drv_data;
238 u32 cmdr; 237 u32 cmdr;
239 238
240 cmd->error = -EINPROGRESS; 239 cmd->error = -EINPROGRESS;
@@ -294,8 +293,8 @@ static u32 dw_mci_prepare_command(struct mmc_host *mmc, struct mmc_command *cmd)
294 cmdr |= SDMMC_CMD_DAT_WR; 293 cmdr |= SDMMC_CMD_DAT_WR;
295 } 294 }
296 295
297 if (drv_data && drv_data->prepare_command) 296 if (!test_bit(DW_MMC_CARD_NO_USE_HOLD, &slot->flags))
298 drv_data->prepare_command(slot->host, &cmdr); 297 cmdr |= SDMMC_CMD_USE_HOLD_REG;
299 298
300 return cmdr; 299 return cmdr;
301} 300}
diff --git a/drivers/mmc/host/dw_mmc.h b/drivers/mmc/host/dw_mmc.h
index f695b58f0613..6fc84b61dc8c 100644
--- a/drivers/mmc/host/dw_mmc.h
+++ b/drivers/mmc/host/dw_mmc.h
@@ -265,6 +265,7 @@ struct dw_mci_slot {
265#define DW_MMC_CARD_PRESENT 0 265#define DW_MMC_CARD_PRESENT 0
266#define DW_MMC_CARD_NEED_INIT 1 266#define DW_MMC_CARD_NEED_INIT 1
267#define DW_MMC_CARD_NO_LOW_PWR 2 267#define DW_MMC_CARD_NO_LOW_PWR 2
268#define DW_MMC_CARD_NO_USE_HOLD 3
268 int id; 269 int id;
269 int sdio_id; 270 int sdio_id;
270}; 271};
@@ -274,7 +275,6 @@ struct dw_mci_slot {
274 * @caps: mmc subsystem specified capabilities of the controller(s). 275 * @caps: mmc subsystem specified capabilities of the controller(s).
275 * @init: early implementation specific initialization. 276 * @init: early implementation specific initialization.
276 * @setup_clock: implementation specific clock configuration. 277 * @setup_clock: implementation specific clock configuration.
277 * @prepare_command: handle CMD register extensions.
278 * @set_ios: handle bus specific extensions. 278 * @set_ios: handle bus specific extensions.
279 * @parse_dt: parse implementation specific device tree properties. 279 * @parse_dt: parse implementation specific device tree properties.
280 * @execute_tuning: implementation specific tuning procedure. 280 * @execute_tuning: implementation specific tuning procedure.
@@ -287,7 +287,6 @@ struct dw_mci_drv_data {
287 unsigned long *caps; 287 unsigned long *caps;
288 int (*init)(struct dw_mci *host); 288 int (*init)(struct dw_mci *host);
289 int (*setup_clock)(struct dw_mci *host); 289 int (*setup_clock)(struct dw_mci *host);
290 void (*prepare_command)(struct dw_mci *host, u32 *cmdr);
291 void (*set_ios)(struct dw_mci *host, struct mmc_ios *ios); 290 void (*set_ios)(struct dw_mci *host, struct mmc_ios *ios);
292 int (*parse_dt)(struct dw_mci *host); 291 int (*parse_dt)(struct dw_mci *host);
293 int (*execute_tuning)(struct dw_mci_slot *slot, u32 opcode); 292 int (*execute_tuning)(struct dw_mci_slot *slot, u32 opcode);