[U-Boot] [PATCH v3 04/24] mmc: omap_hsmmc: set MMC mode in the UHSMS bit field

Jean-Jacques Hiblot jjhiblot at ti.com
Tue Jan 30 15:01:33 UTC 2018


Use the timing parameter set in the MMC core to set the
mode in UHSMS  bit field. This is in preparation for
adding HS200 support in omap hsmmc driver.

Signed-off-by: Kishon Vijay Abraham I <kishon at ti.com>
Signed-off-by: Jean-Jacques Hiblot <jjhiblot at ti.com>

---

Changes in v3:
- prefer the usage of the BIT() macro over the construct ( 1 << x )

 arch/arm/include/asm/omap_mmc.h | 12 ++++++++++-
 drivers/mmc/omap_hsmmc.c        | 47 +++++++++++++++++++++++++++++++++++++++++
 2 files changed, 58 insertions(+), 1 deletion(-)

diff --git a/arch/arm/include/asm/omap_mmc.h b/arch/arm/include/asm/omap_mmc.h
index c4d326d..507435a 100644
--- a/arch/arm/include/asm/omap_mmc.h
+++ b/arch/arm/include/asm/omap_mmc.h
@@ -53,7 +53,8 @@ struct hsmmc {
 	unsigned int sysctl;		/* 0x12C */
 	unsigned int stat;		/* 0x130 */
 	unsigned int ie;		/* 0x134 */
-	unsigned char res4[0x8];
+	unsigned char res4[0x4];
+	unsigned int ac12;		/* 0x13C */
 	unsigned int capa;		/* 0x140 */
 	unsigned char res5[0x10];
 	unsigned int admaes;		/* 0x154 */
@@ -170,6 +171,15 @@ struct omap_hsmmc_plat {
 #define IOV_3V0				3000000
 #define IOV_1V8				1800000
 
+#define AC12_ET				BIT(22)
+#define AC12_UHSMC_MASK			(7 << 16)
+#define AC12_UHSMC_DDR50		(4 << 16)
+#define AC12_UHSMC_SDR104		(3 << 16)
+#define AC12_UHSMC_SDR50		(2 << 16)
+#define AC12_UHSMC_SDR25		(1 << 16)
+#define AC12_UHSMC_SDR12		(0 << 16)
+#define AC12_UHSMC_RES			(0x7 << 16)
+
 /* Driver definitions */
 #define MMCSD_SECTOR_SIZE		512
 #define MMC_CARD			0
diff --git a/drivers/mmc/omap_hsmmc.c b/drivers/mmc/omap_hsmmc.c
index 5141bf6..c6b74a1 100644
--- a/drivers/mmc/omap_hsmmc.c
+++ b/drivers/mmc/omap_hsmmc.c
@@ -76,6 +76,7 @@ struct omap_hsmmc_data {
 #endif
 #if CONFIG_IS_ENABLED(DM_MMC)
 	uint iov;
+	enum bus_mode mode;
 #endif
 	u8 controller_flags;
 #ifndef CONFIG_OMAP34XX
@@ -258,6 +259,48 @@ void mmc_init_stream(struct hsmmc *mmc_base)
 }
 
 #if CONFIG_IS_ENABLED(DM_MMC)
+static void omap_hsmmc_set_timing(struct mmc *mmc)
+{
+	u32 val;
+	struct hsmmc *mmc_base;
+	struct omap_hsmmc_data *priv = omap_hsmmc_get_data(mmc);
+
+	mmc_base = priv->base_addr;
+
+	val = readl(&mmc_base->ac12);
+	val &= ~AC12_UHSMC_MASK;
+	priv->mode = mmc->selected_mode;
+
+	switch (priv->mode) {
+	case MMC_HS_200:
+	case UHS_SDR104:
+		val |= AC12_UHSMC_SDR104;
+		break;
+	case UHS_SDR50:
+		val |= AC12_UHSMC_SDR50;
+		break;
+	case MMC_DDR_52:
+	case UHS_DDR50:
+		val |= AC12_UHSMC_DDR50;
+		break;
+	case SD_HS:
+	case MMC_HS_52:
+	case UHS_SDR25:
+		val |= AC12_UHSMC_SDR25;
+		break;
+	case MMC_LEGACY:
+	case MMC_HS:
+	case SD_LEGACY:
+	case UHS_SDR12:
+		val |= AC12_UHSMC_SDR12;
+		break;
+	default:
+		val |= AC12_UHSMC_RES;
+		break;
+	}
+	writel(val, &mmc_base->ac12);
+}
+
 static void omap_hsmmc_conf_bus_power(struct mmc *mmc)
 {
 	struct hsmmc *mmc_base;
@@ -928,6 +971,10 @@ static int omap_hsmmc_set_ios(struct udevice *dev)
 	if (priv->clock != mmc->clock)
 		omap_hsmmc_set_clock(mmc);
 
+#if CONFIG_IS_ENABLED(DM_MMC)
+	if (priv->mode != mmc->selected_mode)
+		omap_hsmmc_set_timing(mmc);
+#endif
 	return 0;
 }
 
-- 
1.9.1



More information about the U-Boot mailing list