summaryrefslogtreecommitdiff
path: root/drivers/mmc
diff options
context:
space:
mode:
authorAsutosh Das <asutoshd@codeaurora.org>2015-02-27 00:02:02 +0530
committerSubhash Jadavani <subhashj@codeaurora.org>2016-05-31 15:26:32 -0700
commitf446730be194afa78404fd8d1e474305218a000c (patch)
tree1c25c4218705b77926fcf8a63c31e86874f9a7f9 /drivers/mmc
parent444223d88485b28d8b4f02906c314c3081c8aa96 (diff)
mmc: sdhci: propagate error to command queue engine
eMMC controller detects error, generates error interrupt and notifies the CQE. Hence, parse the correct error and propagate it to CQE handler for further processing. Command queue interrupt handler may return IRQ_NONE or IRQ_HANDLED. Check for the return value and either proceed or return from handler. Change-Id: I29c7b22848d3d728a79ba215f8d2f594d19fba63 Signed-off-by: Asutosh Das <asutoshd@codeaurora.org> Signed-off-by: Venkat Gopalakrishnan <venkatg@codeaurora.org>
Diffstat (limited to 'drivers/mmc')
-rw-r--r--drivers/mmc/host/sdhci.c33
1 files changed, 31 insertions, 2 deletions
diff --git a/drivers/mmc/host/sdhci.c b/drivers/mmc/host/sdhci.c
index 1522405f5567..d964ced872f7 100644
--- a/drivers/mmc/host/sdhci.c
+++ b/drivers/mmc/host/sdhci.c
@@ -2920,9 +2920,37 @@ static void sdhci_data_irq(struct sdhci_host *host, u32 intmask)
}
#ifdef CONFIG_MMC_CQ_HCI
+static int sdhci_get_cmd_err(u32 intmask)
+{
+ if (intmask & SDHCI_INT_TIMEOUT)
+ return -ETIMEDOUT;
+ else if (intmask & (SDHCI_INT_CRC | SDHCI_INT_END_BIT |
+ SDHCI_INT_INDEX))
+ return -EILSEQ;
+ return 0;
+}
+
+static int sdhci_get_data_err(u32 intmask)
+{
+ if (intmask & SDHCI_INT_DATA_TIMEOUT)
+ return -ETIMEDOUT;
+ else if (intmask & (SDHCI_INT_DATA_END_BIT | SDHCI_INT_DATA_CRC))
+ return -EILSEQ;
+ else if (intmask & SDHCI_INT_ADMA_ERROR)
+ return -EIO;
+ return 0;
+}
+
static irqreturn_t sdhci_cmdq_irq(struct mmc_host *mmc, u32 intmask)
{
- return cmdq_irq(mmc, intmask);
+ int err = 0;
+
+ if (intmask & SDHCI_INT_CMD_MASK)
+ err = sdhci_get_cmd_err(intmask);
+ else if (intmask & SDHCI_INT_DATA_MASK)
+ err = sdhci_get_data_err(intmask);
+
+ return cmdq_irq(mmc, err);
}
#else
@@ -2960,7 +2988,8 @@ static irqreturn_t sdhci_irq(int irq, void *dev_id)
mmc_hostname(host->mmc),
intmask);
result = sdhci_cmdq_irq(host->mmc, intmask);
- goto out;
+ if (result == IRQ_HANDLED)
+ goto out;
}
if (intmask & SDHCI_INT_AUTO_CMD_ERR)