|
@@ -2121,18 +2121,36 @@ int _mmc_detect_card_removed(struct mmc_host *host)
|
|
|
int mmc_detect_card_removed(struct mmc_host *host)
|
|
|
{
|
|
|
struct mmc_card *card = host->card;
|
|
|
+ int ret;
|
|
|
|
|
|
WARN_ON(!host->claimed);
|
|
|
+
|
|
|
+ if (!card)
|
|
|
+ return 1;
|
|
|
+
|
|
|
+ ret = mmc_card_removed(card);
|
|
|
/*
|
|
|
* The card will be considered unchanged unless we have been asked to
|
|
|
* detect a change or host requires polling to provide card detection.
|
|
|
*/
|
|
|
- if (card && !host->detect_change && !(host->caps & MMC_CAP_NEEDS_POLL))
|
|
|
- return mmc_card_removed(card);
|
|
|
+ if (!host->detect_change && !(host->caps & MMC_CAP_NEEDS_POLL) &&
|
|
|
+ !(host->caps2 & MMC_CAP2_DETECT_ON_ERR))
|
|
|
+ return ret;
|
|
|
|
|
|
host->detect_change = 0;
|
|
|
+ if (!ret) {
|
|
|
+ ret = _mmc_detect_card_removed(host);
|
|
|
+ if (ret && (host->caps2 & MMC_CAP2_DETECT_ON_ERR)) {
|
|
|
+ /*
|
|
|
+ * Schedule a detect work as soon as possible to let a
|
|
|
+ * rescan handle the card removal.
|
|
|
+ */
|
|
|
+ cancel_delayed_work(&host->detect);
|
|
|
+ mmc_detect_change(host, 0);
|
|
|
+ }
|
|
|
+ }
|
|
|
|
|
|
- return _mmc_detect_card_removed(host);
|
|
|
+ return ret;
|
|
|
}
|
|
|
EXPORT_SYMBOL(mmc_detect_card_removed);
|
|
|
|