mmc: block: Check for transfer state in card_busy_detect()
The card is required to return to transfer state. Since that is the state required to start another transfer, check for that state instead of programming state. Signed-off-by: Adrian Hunter <adrian.hunter@intel.com> Acked-by: Linus Walleij <linus.walleij@linaro.org> Signed-off-by: Ulf Hansson <ulf.hansson@linaro.org> Tested-by: Linus Walleij <linus.walleij@linaro.org>
This commit is contained in:
parent
7701885e56
commit
0987c6b046
@ -922,6 +922,16 @@ static int mmc_sd_num_wr_blocks(struct mmc_card *card, u32 *written_blocks)
|
||||
return 0;
|
||||
}
|
||||
|
||||
static inline bool mmc_blk_in_tran_state(u32 status)
|
||||
{
|
||||
/*
|
||||
* Some cards mishandle the status bits, so make sure to check both the
|
||||
* busy indication and the card state.
|
||||
*/
|
||||
return status & R1_READY_FOR_DATA &&
|
||||
(R1_CURRENT_STATE(status) == R1_STATE_TRAN);
|
||||
}
|
||||
|
||||
static int card_busy_detect(struct mmc_card *card, unsigned int timeout_ms,
|
||||
bool hw_busy_detect, struct request *req,
|
||||
u32 *resp_errs)
|
||||
@ -954,9 +964,9 @@ static int card_busy_detect(struct mmc_card *card, unsigned int timeout_ms,
|
||||
* leaves the program state.
|
||||
*/
|
||||
if (done) {
|
||||
pr_err("%s: Card stuck in programming state! %s %s\n",
|
||||
pr_err("%s: Card stuck in wrong state! %s %s status: %#x\n",
|
||||
mmc_hostname(card->host),
|
||||
req->rq_disk->disk_name, __func__);
|
||||
req->rq_disk->disk_name, __func__, status);
|
||||
return -ETIMEDOUT;
|
||||
}
|
||||
|
||||
@ -965,8 +975,7 @@ static int card_busy_detect(struct mmc_card *card, unsigned int timeout_ms,
|
||||
* so make sure to check both the busy
|
||||
* indication and the card state.
|
||||
*/
|
||||
} while (!(status & R1_READY_FOR_DATA) ||
|
||||
(R1_CURRENT_STATE(status) == R1_STATE_PRG));
|
||||
} while (!mmc_blk_in_tran_state(status));
|
||||
|
||||
return err;
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user