Merge tag 'mmc-v5.7-rc4' of git://git.kernel.org/pub/scm/linux/kernel/git/ulfh/mmc
authorLinus Torvalds <torvalds@linux-foundation.org>
Thu, 14 May 2020 20:24:23 +0000 (13:24 -0700)
committerLinus Torvalds <torvalds@linux-foundation.org>
Thu, 14 May 2020 20:24:23 +0000 (13:24 -0700)
Pull MMC fixes from Ulf Hansson:
 "MMC core:
   - Fix a couple of quite severe issues for the CQE request path

  MMC host:
   - alcor: Fix a resource leak in the error path for ->probe()
   - sdhci-acpi: Fix the DMA support for the AMD eMMC v5.0 variant
   - sdhci-pci-gli: Fix system resume support for GL975x
   - sdhci-pci-gli: Fix reboot error for GL9750"

* tag 'mmc-v5.7-rc4' of git://git.kernel.org/pub/scm/linux/kernel/git/ulfh/mmc:
  mmc: sdhci-acpi: Add SDHCI_QUIRK2_BROKEN_64_BIT_DMA for AMDI0040
  mmc: block: Fix request completion in the CQE timeout path
  mmc: core: Fix recursive locking issue in CQE recovery path
  mmc: core: Check request type before completing the request
  mmc: sdhci-pci-gli: Fix can not access GL9750 after reboot from Windows 10
  mmc: alcor: Fix a resource leak in the error path for ->probe()
  mmc: sdhci-pci-gli: Fix no irq handler from suspend

drivers/mmc/core/block.c
drivers/mmc/core/queue.c
drivers/mmc/host/alcor.c
drivers/mmc/host/sdhci-acpi.c
drivers/mmc/host/sdhci-pci-gli.c

index 8499b56..c5367e2 100644 (file)
@@ -1370,6 +1370,7 @@ static void mmc_blk_cqe_complete_rq(struct mmc_queue *mq, struct request *req)
        struct mmc_request *mrq = &mqrq->brq.mrq;
        struct request_queue *q = req->q;
        struct mmc_host *host = mq->card->host;
+       enum mmc_issue_type issue_type = mmc_issue_type(mq, req);
        unsigned long flags;
        bool put_card;
        int err;
@@ -1399,7 +1400,7 @@ static void mmc_blk_cqe_complete_rq(struct mmc_queue *mq, struct request *req)
 
        spin_lock_irqsave(&mq->lock, flags);
 
-       mq->in_flight[mmc_issue_type(mq, req)] -= 1;
+       mq->in_flight[issue_type] -= 1;
 
        put_card = (mmc_tot_in_flight(mq) == 0);
 
index 25bee3d..4b1eb89 100644 (file)
@@ -107,11 +107,10 @@ static enum blk_eh_timer_return mmc_cqe_timed_out(struct request *req)
        case MMC_ISSUE_DCMD:
                if (host->cqe_ops->cqe_timeout(host, mrq, &recovery_needed)) {
                        if (recovery_needed)
-                               __mmc_cqe_recovery_notifier(mq);
+                               mmc_cqe_recovery_notifier(mrq);
                        return BLK_EH_RESET_TIMER;
                }
-               /* No timeout (XXX: huh? comment doesn't make much sense) */
-               blk_mq_complete_request(req);
+               /* The request has gone already */
                return BLK_EH_DONE;
        default:
                /* Timeout is handled by mmc core */
@@ -127,18 +126,13 @@ static enum blk_eh_timer_return mmc_mq_timed_out(struct request *req,
        struct mmc_card *card = mq->card;
        struct mmc_host *host = card->host;
        unsigned long flags;
-       int ret;
+       bool ignore_tout;
 
        spin_lock_irqsave(&mq->lock, flags);
-
-       if (mq->recovery_needed || !mq->use_cqe || host->hsq_enabled)
-               ret = BLK_EH_RESET_TIMER;
-       else
-               ret = mmc_cqe_timed_out(req);
-
+       ignore_tout = mq->recovery_needed || !mq->use_cqe || host->hsq_enabled;
        spin_unlock_irqrestore(&mq->lock, flags);
 
-       return ret;
+       return ignore_tout ? BLK_EH_RESET_TIMER : mmc_cqe_timed_out(req);
 }
 
 static void mmc_mq_recovery_handler(struct work_struct *work)
index 1aee485..026ca91 100644 (file)
@@ -1104,7 +1104,7 @@ static int alcor_pci_sdmmc_drv_probe(struct platform_device *pdev)
 
        if (ret) {
                dev_err(&pdev->dev, "Failed to get irq for data line\n");
-               return ret;
+               goto free_host;
        }
 
        mutex_init(&host->cmd_mutex);
@@ -1116,6 +1116,10 @@ static int alcor_pci_sdmmc_drv_probe(struct platform_device *pdev)
        dev_set_drvdata(&pdev->dev, host);
        mmc_add_host(mmc);
        return 0;
+
+free_host:
+       mmc_free_host(mmc);
+       return ret;
 }
 
 static int alcor_pci_sdmmc_drv_remove(struct platform_device *pdev)
index faba53c..d8b76cb 100644 (file)
@@ -605,10 +605,12 @@ static int sdhci_acpi_emmc_amd_probe_slot(struct platform_device *pdev,
 }
 
 static const struct sdhci_acpi_slot sdhci_acpi_slot_amd_emmc = {
-       .chip   = &sdhci_acpi_chip_amd,
-       .caps   = MMC_CAP_8_BIT_DATA | MMC_CAP_NONREMOVABLE,
-       .quirks = SDHCI_QUIRK_32BIT_DMA_ADDR | SDHCI_QUIRK_32BIT_DMA_SIZE |
-                       SDHCI_QUIRK_32BIT_ADMA_SIZE,
+       .chip           = &sdhci_acpi_chip_amd,
+       .caps           = MMC_CAP_8_BIT_DATA | MMC_CAP_NONREMOVABLE,
+       .quirks         = SDHCI_QUIRK_32BIT_DMA_ADDR |
+                         SDHCI_QUIRK_32BIT_DMA_SIZE |
+                         SDHCI_QUIRK_32BIT_ADMA_SIZE,
+       .quirks2        = SDHCI_QUIRK2_BROKEN_64_BIT_DMA,
        .probe_slot     = sdhci_acpi_emmc_amd_probe_slot,
 };
 
index ce15a05..fd76aa6 100644 (file)
@@ -26,6 +26,9 @@
 #define   SDHCI_GLI_9750_DRIVING_2    GENMASK(27, 26)
 #define   GLI_9750_DRIVING_1_VALUE    0xFFF
 #define   GLI_9750_DRIVING_2_VALUE    0x3
+#define   SDHCI_GLI_9750_SEL_1        BIT(29)
+#define   SDHCI_GLI_9750_SEL_2        BIT(31)
+#define   SDHCI_GLI_9750_ALL_RST      (BIT(24)|BIT(25)|BIT(28)|BIT(30))
 
 #define SDHCI_GLI_9750_PLL           0x864
 #define   SDHCI_GLI_9750_PLL_TX2_INV    BIT(23)
@@ -122,6 +125,8 @@ static void gli_set_9750(struct sdhci_host *host)
                                    GLI_9750_DRIVING_1_VALUE);
        driving_value |= FIELD_PREP(SDHCI_GLI_9750_DRIVING_2,
                                    GLI_9750_DRIVING_2_VALUE);
+       driving_value &= ~(SDHCI_GLI_9750_SEL_1|SDHCI_GLI_9750_SEL_2|SDHCI_GLI_9750_ALL_RST);
+       driving_value |= SDHCI_GLI_9750_SEL_2;
        sdhci_writel(host, driving_value, SDHCI_GLI_9750_DRIVING);
 
        sw_ctrl_value &= ~SDHCI_GLI_9750_SW_CTRL_4;
@@ -334,6 +339,18 @@ static u32 sdhci_gl9750_readl(struct sdhci_host *host, int reg)
        return value;
 }
 
+#ifdef CONFIG_PM_SLEEP
+static int sdhci_pci_gli_resume(struct sdhci_pci_chip *chip)
+{
+       struct sdhci_pci_slot *slot = chip->slots[0];
+
+       pci_free_irq_vectors(slot->chip->pdev);
+       gli_pcie_enable_msi(slot);
+
+       return sdhci_pci_resume_host(chip);
+}
+#endif
+
 static const struct sdhci_ops sdhci_gl9755_ops = {
        .set_clock              = sdhci_set_clock,
        .enable_dma             = sdhci_pci_enable_dma,
@@ -348,6 +365,9 @@ const struct sdhci_pci_fixes sdhci_gl9755 = {
        .quirks2        = SDHCI_QUIRK2_BROKEN_DDR50,
        .probe_slot     = gli_probe_slot_gl9755,
        .ops            = &sdhci_gl9755_ops,
+#ifdef CONFIG_PM_SLEEP
+       .resume         = sdhci_pci_gli_resume,
+#endif
 };
 
 static const struct sdhci_ops sdhci_gl9750_ops = {
@@ -366,4 +386,7 @@ const struct sdhci_pci_fixes sdhci_gl9750 = {
        .quirks2        = SDHCI_QUIRK2_BROKEN_DDR50,
        .probe_slot     = gli_probe_slot_gl9750,
        .ops            = &sdhci_gl9750_ops,
+#ifdef CONFIG_PM_SLEEP
+       .resume         = sdhci_pci_gli_resume,
+#endif
 };