On 7/01/19 12:11 PM, BOUGH CHEN wrote: > Currently, USDHC do not generate transfer complete interrupt > when send a non-data-command with R1b response. But if want > to support DCMD in CMDQ, need to change this, the DCMD IC > logic require the USDHC to enable this function, otherwise > DCMD will never get a CC(command complete) interrupt. > > This patch set ESDHC_VEND_SPEC2_EN_BUSY_IRQ and add DCMD support. > > Signed-off-by: Haibo Chen <haibo.chen@xxxxxxx> Acked-by: Adrian Hunter <adrian.hunter@xxxxxxxxx> > --- > drivers/mmc/host/sdhci-esdhc-imx.c | 22 +++++++++++++++++++++- > 1 file changed, 21 insertions(+), 1 deletion(-) > > diff --git a/drivers/mmc/host/sdhci-esdhc-imx.c b/drivers/mmc/host/sdhci-esdhc-imx.c > index 3ada951f9df5..e5676beb7ec1 100644 > --- a/drivers/mmc/host/sdhci-esdhc-imx.c > +++ b/drivers/mmc/host/sdhci-esdhc-imx.c > @@ -80,6 +80,9 @@ > #define ESDHC_STROBE_DLL_STS_REF_LOCK (1 << 1) > #define ESDHC_STROBE_DLL_STS_SLV_LOCK 0x1 > > +#define ESDHC_VEND_SPEC2 0xc8 > +#define ESDHC_VEND_SPEC2_EN_BUSY_IRQ (1 << 8) > + > #define ESDHC_TUNING_CTRL 0xcc > #define ESDHC_STD_TUNING_EN (1 << 24) > /* NOTE: the minimum valid tuning start tap for mx6sl is 1 */ > @@ -1145,6 +1148,23 @@ static void sdhci_esdhc_imx_hwinit(struct sdhci_host *host) > /* disable DLL_CTRL delay line settings */ > writel(0x0, host->ioaddr + ESDHC_DLL_CTRL); > > + /* > + * For the case of command with busy, if set the bit > + * ESDHC_VEND_SPEC2_EN_BUSY_IRQ, USDHC will generate a > + * transfer complete interrupt when busy is deasserted. > + * When CQHCI use DCMD to send a CMD need R1b respons, > + * CQHCI require to set ESDHC_VEND_SPEC2_EN_BUSY_IRQ, > + * otherwise DCMD will always meet timeout waiting for > + * hardware interrupt issue. > + */ > + if (imx_data->socdata->flags & ESDHC_FLAG_CQHCI) { > + tmp = readl(host->ioaddr + ESDHC_VEND_SPEC2); > + tmp |= ESDHC_VEND_SPEC2_EN_BUSY_IRQ; > + writel(tmp, host->ioaddr + ESDHC_VEND_SPEC2); > + > + host->quirks &= ~SDHCI_QUIRK_NO_BUSY_IRQ; > + } > + > if (imx_data->socdata->flags & ESDHC_FLAG_STD_TUNING) { > tmp = readl(host->ioaddr + ESDHC_TUNING_CTRL); > tmp |= ESDHC_STD_TUNING_EN | > @@ -1435,7 +1455,7 @@ static int sdhci_esdhc_imx_probe(struct platform_device *pdev) > } > > if (imx_data->socdata->flags & ESDHC_FLAG_CQHCI) { > - host->mmc->caps2 |= MMC_CAP2_CQE; > + host->mmc->caps2 |= MMC_CAP2_CQE | MMC_CAP2_CQE_DCMD; > cq_host = devm_kzalloc(&pdev->dev, sizeof(*cq_host), GFP_KERNEL); > if (IS_ERR(cq_host)) { > err = PTR_ERR(cq_host); >