aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/mmc/core/core.c
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/mmc/core/core.c')
-rw-r--r--drivers/mmc/core/core.c20
1 files changed, 17 insertions, 3 deletions
diff --git a/drivers/mmc/core/core.c b/drivers/mmc/core/core.c
index d996d39c0d6f..e68a19c0fc21 100644
--- a/drivers/mmc/core/core.c
+++ b/drivers/mmc/core/core.c
@@ -464,6 +464,7 @@ int mmc_cqe_start_req(struct mmc_host *host, struct mmc_request *mrq)
goto out_err;
trace_mmc_request_start(host, mrq);
+ led_trigger_event(host->led, LED_FULL);
return 0;
@@ -551,10 +552,18 @@ int mmc_cqe_recovery(struct mmc_host *host)
* Recovery is expected seldom, if at all, but it reduces performance,
* so make sure it is not completely silent.
*/
- pr_warn("%s: running CQE recovery\n", mmc_hostname(host));
+ pr_warn_ratelimited("%s: running CQE recovery\n", mmc_hostname(host));
host->cqe_ops->cqe_recovery_start(host);
+ err = mmc_detect_card_removed(host);
+ if (err) {
+ host->cqe_ops->cqe_recovery_finish(host);
+ host->cqe_ops->cqe_off(host);
+ mmc_retune_release(host);
+ return err;
+ }
+
memset(&cmd, 0, sizeof(cmd));
cmd.opcode = MMC_STOP_TRANSMISSION;
cmd.flags = MMC_RSP_R1B | MMC_CMD_AC;
@@ -565,7 +574,11 @@ int mmc_cqe_recovery(struct mmc_host *host)
mmc_poll_for_busy(host->card, MMC_CQE_RECOVERY_TIMEOUT, true, MMC_BUSY_IO);
memset(&cmd, 0, sizeof(cmd));
- cmd.opcode = MMC_CMDQ_TASK_MGMT;
+ if (mmc_card_sd(host->card))
+ cmd.opcode = SD_CMDQ_TASK_MGMT;
+ else
+ cmd.opcode = MMC_CMDQ_TASK_MGMT;
+
cmd.arg = 1; /* Discard entire queue */
cmd.flags = MMC_RSP_R1B | MMC_CMD_AC;
cmd.flags &= ~MMC_RSP_CRC; /* Ignore CRC */
@@ -1842,7 +1855,8 @@ EXPORT_SYMBOL(mmc_erase);
int mmc_can_erase(struct mmc_card *card)
{
- if (card->csd.cmdclass & CCC_ERASE && card->erase_size)
+ if (card->csd.cmdclass & CCC_ERASE && card->erase_size &&
+ !(card->quirks & MMC_QUIRK_ERASE_BROKEN))
return 1;
return 0;
}