summaryrefslogtreecommitdiff
path: root/drivers/mmc/core
diff options
context:
space:
mode:
authorShawn Lin <shawn.lin@rock-chips.com>2018-02-26 17:35:30 +0800
committerTao Huang <huangtao@rock-chips.com>2018-02-27 11:31:21 +0800
commite61fd89e2fa3ff2d13fa39b279ee24f403c97eb9 (patch)
tree59711edeef6958091ba6883e24a8fa1d57cd0d15 /drivers/mmc/core
parentfcb45dce598e7ad86023b91becad8856712a7212 (diff)
BACKPORT: FROMLIST: mmc: core: Don't try UHS-I mode if 4-bit mode isn't supported
Per SD specification physical layer v4.0, section 3.9.4, it says "UHS-I supports only 4-bit mode. Host shall select 4-bit mode by ACMD6. However mmc_sd_init_uhs_card() still go ahead to initialize the cards anyway, whether card or host won't support 4-bit mode. This breaks the platforms which only support 1-bit mode but with a UHS-I card inserted, as all the tuning process is broken due to this. Alternatively, we should check the return value from mmc_set_bus_width to see if host could finish the request to switch the bus with on its side. But that needs more thing to do than this patch that just bails out early to try to use high speed mode if 4-bit mode isn't available for whatever reason. And this patch could also fix the same problem for sdio since R4_18V_PRESENT won't be set for ocr when mmc_sdio_init_card() finds mmc_host_uhs() is false. Note that This patch doesn't keep the checking of card->scr.sda_spec3 and comparing card->scr.bus_widths with SD_SCR_BUS_WIDTH_4 within mmc_sd_init_uhs_card since if the sd cards response with SD_ROCR_S18A, it definitely support UHS-I mode, which implicitly means these checks are always true. Change-Id: I2e91418b3216d9efac672af604014d7095bf4a1a Signed-off-by: Shawn Lin <shawn.lin@rock-chips.com> (cherry picked from https://patchwork.kernel.org/patch/10241773/)
Diffstat (limited to 'drivers/mmc/core')
-rw-r--r--drivers/mmc/core/sd.c16
1 files changed, 5 insertions, 11 deletions
diff --git a/drivers/mmc/core/sd.c b/drivers/mmc/core/sd.c
index ee145d4cc541..cd437d6b1843 100644
--- a/drivers/mmc/core/sd.c
+++ b/drivers/mmc/core/sd.c
@@ -577,9 +577,6 @@ static int mmc_sd_init_uhs_card(struct mmc_card *card)
int err;
u8 *status;
- if (!card->scr.sda_spec3)
- return 0;
-
if (!(card->csd.cmdclass & CCC_SWITCH))
return 0;
@@ -591,14 +588,11 @@ static int mmc_sd_init_uhs_card(struct mmc_card *card)
}
/* Set 4-bit bus width */
- if ((card->host->caps & MMC_CAP_4_BIT_DATA) &&
- (card->scr.bus_widths & SD_SCR_BUS_WIDTH_4)) {
- err = mmc_app_set_bus_width(card, MMC_BUS_WIDTH_4);
- if (err)
- goto out;
+ err = mmc_app_set_bus_width(card, MMC_BUS_WIDTH_4);
+ if (err)
+ goto out;
- mmc_set_bus_width(card->host, MMC_BUS_WIDTH_4);
- }
+ mmc_set_bus_width(card->host, MMC_BUS_WIDTH_4);
/*
* Select the bus speed mode depending on host
@@ -988,7 +982,7 @@ static int mmc_sd_init_card(struct mmc_host *host, u32 ocr,
goto free_card;
/* Initialization sequence for UHS-I cards */
- if (rocr & SD_ROCR_S18A) {
+ if (rocr & SD_ROCR_S18A && mmc_host_uhs(host)) {
err = mmc_sd_init_uhs_card(card);
if (err)
goto free_card;