According to the SD Host Controller Standard Specification:

"...Transfer Complete has higher priority than Data Timeout
Error. If both bits are set to 1, execution of a command
can be considered to be completed."

Adjust the checking of SDHCI_INT_DATA_TIMEOUT and
SDHCI_INT_DATA_END (Transfer Complete) accordingly.

Signed-off-by: Adrian Hunter <[email protected]>
---
 drivers/mmc/host/sdhci.c | 13 +++++++------
 1 file changed, 7 insertions(+), 6 deletions(-)

diff --git a/drivers/mmc/host/sdhci.c b/drivers/mmc/host/sdhci.c
index 8588550..6ada726 100644
--- a/drivers/mmc/host/sdhci.c
+++ b/drivers/mmc/host/sdhci.c
@@ -2332,11 +2332,6 @@ static void sdhci_data_irq(struct sdhci_host *host, u32 
intmask)
                 * above in sdhci_cmd_irq().
                 */
                if (host->cmd && (host->cmd->flags & MMC_RSP_BUSY)) {
-                       if (intmask & SDHCI_INT_DATA_TIMEOUT) {
-                               host->cmd->error = -ETIMEDOUT;
-                               tasklet_schedule(&host->finish_tasklet);
-                               return;
-                       }
                        if (intmask & SDHCI_INT_DATA_END) {
                                /*
                                 * Some cards handle busy-end interrupt
@@ -2349,6 +2344,11 @@ static void sdhci_data_irq(struct sdhci_host *host, u32 
intmask)
                                        host->busy_handle = 1;
                                return;
                        }
+                       if (intmask & SDHCI_INT_DATA_TIMEOUT) {
+                               host->cmd->error = -ETIMEDOUT;
+                               tasklet_schedule(&host->finish_tasklet);
+                               return;
+                       }
                }
 
                pr_err("%s: Got data interrupt 0x%08x even "
@@ -2359,7 +2359,8 @@ static void sdhci_data_irq(struct sdhci_host *host, u32 
intmask)
                return;
        }
 
-       if (intmask & SDHCI_INT_DATA_TIMEOUT)
+       if ((intmask & SDHCI_INT_DATA_TIMEOUT) &&
+           !(intmask & SDHCI_INT_DATA_END))
                host->data->error = -ETIMEDOUT;
        else if (intmask & SDHCI_INT_DATA_END_BIT)
                host->data->error = -EILSEQ;
-- 
1.8.3.2

--
To unsubscribe from this list: send the line "unsubscribe linux-mmc" in
the body of a message to [email protected]
More majordomo info at  http://vger.kernel.org/majordomo-info.html

Reply via email to