]> git.ipfire.org Git - thirdparty/u-boot.git/commitdiff
mmc: sdhci: add SDHCI_QUIRK_BROKEN_HISPD_MODE
authorHannes Schmelzer <oe5hpm@oevsv.at>
Wed, 7 Mar 2018 07:00:56 +0000 (08:00 +0100)
committerMichal Simek <michal.simek@xilinx.com>
Wed, 30 May 2018 06:24:08 +0000 (08:24 +0200)
Some IP-core implementations of the SDHCI have different troubles on the
silicon where they are placed.

On ZYNQ platform for example Xilinx doesn't accept the hold timing of an
eMMC chip which operates in High-Speed mode and must be forced to
operate in non high-speed mode. To get rid of this
"SDHCI_QUIRK_BROKEN_HISPD_MODE" is introduced.

For more details about this refer to the Xilinx answer-recor #59999
https://www.xilinx.com/support/answers/59999.html

This commit:
- doesn't set HISPD bit on the host-conroller
- reflects this fact within the host-controller capabilities

Upon this the layer above (mmc-driver) can setup the card correctly.

Otherwise the MMC card will be switched into high-speed mode and causes
possible timing violation on the host-controller side.

Signed-off-by: Hannes Schmelzer <oe5hpm@oevsv.at>
Signed-off-by: Hannes Schmelzer <hannes.schmelzer@br-automation.com>
drivers/mmc/sdhci.c
include/sdhci.h

index 8a1edf5c6454d3d9fe73fece6cbcf7f6203e9140..cbc4333e6b4edd42a637f0c8b0b5ad5fff0202c8 100644 (file)
@@ -640,7 +640,8 @@ static int sdhci_set_ios(struct mmc *mmc)
        else
                ctrl &= ~SDHCI_CTRL_HISPD;
 
-       if (host->quirks & SDHCI_QUIRK_NO_HISPD_BIT)
+       if ((host->quirks & SDHCI_QUIRK_NO_HISPD_BIT) ||
+           (host->quirks & SDHCI_QUIRK_BROKEN_HISPD_MODE))
                ctrl &= ~SDHCI_CTRL_HISPD;
 
        sdhci_writeb(host, ctrl, SDHCI_HOST_CONTROL);
@@ -838,6 +839,11 @@ int sdhci_setup_cfg(struct mmc_config *cfg, struct sdhci_host *host,
        if (caps_1 & SDHCI_USE_SDR50_TUNING)
                cfg->host_caps |= MMC_MODE_NEEDS_TUNING;
 
+       if (host->quirks & SDHCI_QUIRK_BROKEN_HISPD_MODE) {
+               cfg->host_caps &= ~MMC_MODE_HS;
+               cfg->host_caps &= ~MMC_MODE_HS_52MHz;
+       }
+
        if (host->host_caps)
                cfg->host_caps |= host->host_caps;
 
index 4476c06729a97ba057f0e544e1412b1dad747599..f1f14a6fa0111860e053ab54b74a3ce171baa0db 100644 (file)
 #define SDHCI_QUIRK_BROKEN_R1B         (1 << 2)
 #define SDHCI_QUIRK_NO_HISPD_BIT       (1 << 3)
 #define SDHCI_QUIRK_BROKEN_VOLTAGE     (1 << 4)
+/*
+ * SDHCI_QUIRK_BROKEN_HISPD_MODE
+ * the hardware cannot operate correctly in high-speed mode,
+ * this quirk forces the sdhci host-controller to non high-speed mode
+ */
+#define SDHCI_QUIRK_BROKEN_HISPD_MODE  BIT(5)
 #define SDHCI_QUIRK_WAIT_SEND_CMD      (1 << 6)
 #define SDHCI_QUIRK_USE_WIDE8          (1 << 8)
 #define SDHCI_QUIRK_NO_1_8_V           (1 << 9)