|
@@ -1219,6 +1219,8 @@ static void mmc_select_driver_type(struct mmc_card *card)
|
|
|
static int mmc_select_hs200(struct mmc_card *card)
|
|
|
{
|
|
|
struct mmc_host *host = card->host;
|
|
|
+ bool send_status = true;
|
|
|
+ unsigned int old_timing;
|
|
|
int err = -EINVAL;
|
|
|
u8 val;
|
|
|
|
|
@@ -1234,6 +1236,9 @@ static int mmc_select_hs200(struct mmc_card *card)
|
|
|
|
|
|
mmc_select_driver_type(card);
|
|
|
|
|
|
+ if (host->caps & MMC_CAP_WAIT_WHILE_BUSY)
|
|
|
+ send_status = false;
|
|
|
+
|
|
|
/*
|
|
|
* Set the bus width(4 or 8) with host's support and
|
|
|
* switch to HS200 mode if bus width is set successfully.
|
|
@@ -1245,11 +1250,25 @@ static int mmc_select_hs200(struct mmc_card *card)
|
|
|
err = __mmc_switch(card, EXT_CSD_CMD_SET_NORMAL,
|
|
|
EXT_CSD_HS_TIMING, val,
|
|
|
card->ext_csd.generic_cmd6_time,
|
|
|
- true, true, true);
|
|
|
- if (!err)
|
|
|
- mmc_set_timing(host, MMC_TIMING_MMC_HS200);
|
|
|
+ true, send_status, true);
|
|
|
+ if (err)
|
|
|
+ goto err;
|
|
|
+ old_timing = host->ios.timing;
|
|
|
+ mmc_set_timing(host, MMC_TIMING_MMC_HS200);
|
|
|
+ if (!send_status) {
|
|
|
+ err = mmc_switch_status(card);
|
|
|
+ /*
|
|
|
+ * mmc_select_timing() assumes timing has not changed if
|
|
|
+ * it is a switch error.
|
|
|
+ */
|
|
|
+ if (err == -EBADMSG)
|
|
|
+ mmc_set_timing(host, old_timing);
|
|
|
+ }
|
|
|
}
|
|
|
err:
|
|
|
+ if (err)
|
|
|
+ pr_err("%s: %s failed, error %d\n", mmc_hostname(card->host),
|
|
|
+ __func__, err);
|
|
|
return err;
|
|
|
}
|
|
|
|