[PATCH] ls1028a: hdp: Add config support for HDP firmware loading
From: Alison Wang This patch adds config support for HDP firmware loading on LS1028A. Signed-off-by: Oliver Brown Signed-off-by: Alison Wang Signed-off-by: Ye Li Signed-off-by: Yangbo Lu --- board/freescale/ls1028a/ls1028a.c| 7 ++- configs/ls1028aqds_tfa_SECURE_BOOT_defconfig | 2 ++ configs/ls1028aqds_tfa_defconfig | 2 ++ configs/ls1028ardb_tfa_SECURE_BOOT_defconfig | 2 ++ configs/ls1028ardb_tfa_defconfig | 2 ++ 5 files changed, 14 insertions(+), 1 deletion(-) diff --git a/board/freescale/ls1028a/ls1028a.c b/board/freescale/ls1028a/ls1028a.c index 71a086ef67..1a7806fad7 100644 --- a/board/freescale/ls1028a/ls1028a.c +++ b/board/freescale/ls1028a/ls1028a.c @@ -1,6 +1,6 @@ // SPDX-License-Identifier: GPL-2.0+ /* - * Copyright 2019, 2021 NXP + * Copyright 2019-2022 NXP */ #include @@ -328,3 +328,8 @@ int checkboard(void) return 0; } #endif + +void *video_hw_init(void) +{ + return NULL; +} diff --git a/configs/ls1028aqds_tfa_SECURE_BOOT_defconfig b/configs/ls1028aqds_tfa_SECURE_BOOT_defconfig index 2e4db036a4..26613168f1 100644 --- a/configs/ls1028aqds_tfa_SECURE_BOOT_defconfig +++ b/configs/ls1028aqds_tfa_SECURE_BOOT_defconfig @@ -98,3 +98,5 @@ CONFIG_WDT_SP805=y CONFIG_RSA=y CONFIG_OF_LIBFDT_OVERLAY=y CONFIG_EFI_LOADER_BOUNCE_BUFFER=y +CONFIG_VIDEO=y +CONFIG_VIDEO_LS_HDP_LOAD=y diff --git a/configs/ls1028aqds_tfa_defconfig b/configs/ls1028aqds_tfa_defconfig index 556f77e222..7e66e681fe 100644 --- a/configs/ls1028aqds_tfa_defconfig +++ b/configs/ls1028aqds_tfa_defconfig @@ -103,3 +103,5 @@ CONFIG_WDT=y CONFIG_WDT_SP805=y CONFIG_OF_LIBFDT_OVERLAY=y CONFIG_EFI_LOADER_BOUNCE_BUFFER=y +CONFIG_VIDEO=y +CONFIG_VIDEO_LS_HDP_LOAD=y diff --git a/configs/ls1028ardb_tfa_SECURE_BOOT_defconfig b/configs/ls1028ardb_tfa_SECURE_BOOT_defconfig index 20cb844b01..024f9394b1 100644 --- a/configs/ls1028ardb_tfa_SECURE_BOOT_defconfig +++ b/configs/ls1028ardb_tfa_SECURE_BOOT_defconfig @@ -92,3 +92,5 @@ CONFIG_WDT_SP805=y CONFIG_RSA=y CONFIG_OF_LIBFDT_OVERLAY=y CONFIG_EFI_LOADER_BOUNCE_BUFFER=y +CONFIG_VIDEO=y +CONFIG_VIDEO_LS_HDP_LOAD=y diff --git a/configs/ls1028ardb_tfa_defconfig b/configs/ls1028ardb_tfa_defconfig index fdfdf39c61..97e979ca97 100644 --- a/configs/ls1028ardb_tfa_defconfig +++ b/configs/ls1028ardb_tfa_defconfig @@ -101,3 +101,5 @@ CONFIG_WDT=y CONFIG_WDT_SP805=y CONFIG_OF_LIBFDT_OVERLAY=y CONFIG_EFI_LOADER_BOUNCE_BUFFER=y +CONFIG_VIDEO=y +CONFIG_VIDEO_LS_HDP_LOAD=y -- 2.25.1
[v3, 3/3] armv8: layerscape: drop CONFIG_SYS_FSL_MMC_HAS_CAPBLT_VS33
Drop CONFIG_SYS_FSL_MMC_HAS_CAPBLT_VS33. CONFIG_FSL_ESDHC_VS33_NOT_SUPPORT is used instead. Signed-off-by: Yangbo Lu --- Changes for v2: - Updated copyright. Changes for v3: - Dropped wrong copyright. --- include/configs/T208xQDS.h | 3 +-- include/configs/T208xRDB.h | 3 +-- include/configs/T4240RDB.h | 3 +-- include/configs/kontron_sl28.h | 5 - include/configs/ls1012a2g5rdb.h | 7 +-- include/configs/ls1012afrwy.h| 7 +-- include/configs/ls1012aqds.h | 6 +- include/configs/ls1012ardb.h | 8 +--- include/configs/ls1028a_common.h | 7 +-- include/configs/ls1043a_common.h | 9 + include/configs/ls1046a_common.h | 9 + include/configs/ls1088aqds.h | 3 +-- include/configs/ls1088ardb.h | 7 +-- include/configs/ls2080aqds.h | 7 +-- include/configs/ls2080ardb.h | 7 +-- include/configs/lx2160a_common.h | 7 +-- scripts/config_whitelist.txt | 1 - 17 files changed, 15 insertions(+), 84 deletions(-) diff --git a/include/configs/T208xQDS.h b/include/configs/T208xQDS.h index b1acb564c3..7bc792b8d1 100644 --- a/include/configs/T208xQDS.h +++ b/include/configs/T208xQDS.h @@ -1,7 +1,7 @@ /* SPDX-License-Identifier: GPL-2.0+ */ /* * Copyright 2011-2013 Freescale Semiconductor, Inc. - * Copyright 2020 NXP + * Copyright 2020-2021 NXP */ /* @@ -618,7 +618,6 @@ unsigned long get_board_ddr_clk(void); #ifdef CONFIG_MMC #define CONFIG_SYS_FSL_ESDHC_ADDR CONFIG_SYS_MPC85xx_ESDHC_ADDR #define CONFIG_SYS_FSL_ESDHC_BROKEN_TIMEOUT -#define CONFIG_SYS_FSL_MMC_HAS_CAPBLT_VS33 #endif /* diff --git a/include/configs/T208xRDB.h b/include/configs/T208xRDB.h index e467ef453d..b5197b3ed9 100644 --- a/include/configs/T208xRDB.h +++ b/include/configs/T208xRDB.h @@ -1,7 +1,7 @@ /* SPDX-License-Identifier: GPL-2.0+ */ /* * Copyright 2014 Freescale Semiconductor, Inc. - * Copyright 2020 NXP + * Copyright 2020-2021 NXP */ /* @@ -574,7 +574,6 @@ unsigned long get_board_ddr_clk(void); #ifdef CONFIG_MMC #define CONFIG_SYS_FSL_ESDHC_ADDR CONFIG_SYS_MPC85xx_ESDHC_ADDR #define CONFIG_SYS_FSL_ESDHC_BROKEN_TIMEOUT -#define CONFIG_SYS_FSL_MMC_HAS_CAPBLT_VS33 #endif /* diff --git a/include/configs/T4240RDB.h b/include/configs/T4240RDB.h index a04d9137b3..139beae08d 100644 --- a/include/configs/T4240RDB.h +++ b/include/configs/T4240RDB.h @@ -1,7 +1,7 @@ /* SPDX-License-Identifier: GPL-2.0+ */ /* * Copyright 2014 Freescale Semiconductor, Inc. - * Copyright 2020 NXP + * Copyright 2020-2021 NXP */ /* @@ -585,7 +585,6 @@ unsigned long get_board_ddr_clk(void); #ifdef CONFIG_MMC #define CONFIG_SYS_FSL_ESDHC_ADDR CONFIG_SYS_MPC85xx_ESDHC_ADDR #define CONFIG_SYS_FSL_ESDHC_BROKEN_TIMEOUT -#define CONFIG_SYS_FSL_MMC_HAS_CAPBLT_VS33 #endif diff --git a/include/configs/kontron_sl28.h b/include/configs/kontron_sl28.h index 5f11205802..bfb4e67c8f 100644 --- a/include/configs/kontron_sl28.h +++ b/include/configs/kontron_sl28.h @@ -56,11 +56,6 @@ #define CONFIG_DDR_CLK_FREQ1 #define COUNTER_FREQUENCY_REAL (CONFIG_SYS_CLK_FREQ / 4) -/* MMC */ -#ifdef CONFIG_MMC -#define CONFIG_SYS_FSL_MMC_HAS_CAPBLT_VS33 -#endif - /* ethernet */ #define CONFIG_SYS_RX_ETH_BUFFER 8 diff --git a/include/configs/ls1012a2g5rdb.h b/include/configs/ls1012a2g5rdb.h index 9962b9872a..1c016dee97 100644 --- a/include/configs/ls1012a2g5rdb.h +++ b/include/configs/ls1012a2g5rdb.h @@ -1,6 +1,6 @@ /* SPDX-License-Identifier: GPL-2.0+ */ /* - * Copyright 2017 NXP + * Copyright 2017, 2021 NXP */ #ifndef __LS1012A2G5RDB_H__ @@ -13,11 +13,6 @@ #define CONFIG_CHIP_SELECTS_PER_CTRL 1 #define CONFIG_SYS_SDRAM_SIZE 0x4000 -/* MMC */ -#ifdef CONFIG_MMC -#define CONFIG_SYS_FSL_MMC_HAS_CAPBLT_VS33 -#endif - /* SATA */ #define CONFIG_LIBATA #define CONFIG_SCSI_AHCI diff --git a/include/configs/ls1012afrwy.h b/include/configs/ls1012afrwy.h index ba152834d5..9024d5e10f 100644 --- a/include/configs/ls1012afrwy.h +++ b/include/configs/ls1012afrwy.h @@ -1,6 +1,6 @@ /* SPDX-License-Identifier: GPL-2.0+ */ /* - * Copyright 2018 NXP + * Copyright 2018, 2021 NXP */ #ifndef __LS1012AFRWY_H__ @@ -33,11 +33,6 @@ func(DHCP, dhcp, na) #endif -/* MMC */ -#ifdef CONFIG_MMC -#define CONFIG_SYS_FSL_MMC_HAS_CAPBLT_VS33 -#endif - #define CONFIG_PCIE1 /* PCIE controller 1 */ #define CONFIG_PCI_SCAN_SHOW diff --git a/include/configs/ls1012aqds.h b/include/configs/ls1012aqds.h index 36be8f42c9..e76f5ef23b 100644 --- a/include/configs/ls1012aqds.h +++ b/include/configs/ls1012aqds.h @@ -1,6 +1,7 @@ /* SPDX-License-Identifier: GPL-2.0+ */ /* * Copyright 2016 Freescale Semiconductor, Inc. + * Copyright 2021 NXP */ #ifndef __LS1012AQDS_H__ @@ -93,11 +94,6 @@ DSPI_CTAR_DT(0)) #define CONFIG_SPI_FLASH_EON /* cs3 */ -/* MMC */ -#ifdef CONFIG_MMC -#define CONFIG_SYS_FSL_MMC_HAS_CAPBLT_VS33 -#endif
[v3, 2/3] mmc: fsl_esdhc_imx: drop CONFIG_SYS_FSL_MMC_HAS_CAPBLT_VS33
There is no i.MX board using such option. Drop it. Signed-off-by: Yangbo Lu --- Changes for v2: - Updated copyright. Changes for v3: - None. --- drivers/mmc/fsl_esdhc_imx.c | 7 +-- 1 file changed, 1 insertion(+), 6 deletions(-) diff --git a/drivers/mmc/fsl_esdhc_imx.c b/drivers/mmc/fsl_esdhc_imx.c index a4675838e5..566ce046ae 100644 --- a/drivers/mmc/fsl_esdhc_imx.c +++ b/drivers/mmc/fsl_esdhc_imx.c @@ -1,7 +1,7 @@ // SPDX-License-Identifier: GPL-2.0+ /* * Copyright 2007, 2010-2011 Freescale Semiconductor, Inc - * Copyright 2019 NXP Semiconductors + * Copyright 2019, 2021 NXP * Andy Fleming * Yangbo Lu * @@ -1234,11 +1234,6 @@ static int fsl_esdhc_init(struct fsl_esdhc_priv *priv, ESDHC_HOSTCAPBLT_VS18 | ESDHC_HOSTCAPBLT_VS30); #endif -/* T4240 host controller capabilities register should have VS33 bit */ -#ifdef CONFIG_SYS_FSL_MMC_HAS_CAPBLT_VS33 - caps = caps | ESDHC_HOSTCAPBLT_VS33; -#endif - if (caps & ESDHC_HOSTCAPBLT_VS18) voltage_caps |= MMC_VDD_165_195; if (caps & ESDHC_HOSTCAPBLT_VS30) -- 2.25.1
[v3, 1/3] mmc: fsl_esdhc: convert to CONFIG_FSL_ESDHC_VS33_NOT_SUPPORT
For eSDHC, power supply is through peripheral circuit. Some eSDHC versions have value 0 of the bit but that does not reflect the truth. 3.3V is common for SD/MMC, and is supported for all boards with eSDHC in current u-boot. So, make 3.3V is supported in default in code. CONFIG_FSL_ESDHC_VS33_NOT_SUPPORT can be enabled if future board does not support 3.3V. This is also a fix-up for one previous patch, which converted to use IS_ENABLED() for CONFIG_SYS_FSL_MMC_HAS_CAPBLT_VS33 that is not a Kconfig option. Fixes: 52faec31827e ("mmc: fsl_esdhc: replace most #ifdefs by IS_ENABLED()") Signed-off-by: Yangbo Lu --- Changes for v2: - Updated copyright. Chagnes for v3: - Fixed code logic. --- drivers/mmc/Kconfig | 7 +++ drivers/mmc/fsl_esdhc.c | 17 ++--- 2 files changed, 21 insertions(+), 3 deletions(-) diff --git a/drivers/mmc/Kconfig b/drivers/mmc/Kconfig index 8901456967..0909f502a1 100644 --- a/drivers/mmc/Kconfig +++ b/drivers/mmc/Kconfig @@ -798,6 +798,13 @@ config FSL_ESDHC_33V_IO_RELIABILITY_WORKAROUND This option assumes no hotplug, and u-boot has to make all the way to to linux to use 1.8v UHS-I speed mode if has card. +config FSL_ESDHC_VS33_NOT_SUPPORT + bool "3.3V power supply not supported" + depends on FSL_ESDHC + help + For eSDHC, power supply is through peripheral circuit. 3.3V support is + common. Select this if 3.3V power supply not supported. + config FSL_ESDHC_IMX bool "Freescale/NXP i.MX eSDHC controller support" help diff --git a/drivers/mmc/fsl_esdhc.c b/drivers/mmc/fsl_esdhc.c index 7501fdb71e..1d98fa65c4 100644 --- a/drivers/mmc/fsl_esdhc.c +++ b/drivers/mmc/fsl_esdhc.c @@ -1,7 +1,7 @@ // SPDX-License-Identifier: GPL-2.0+ /* * Copyright 2007, 2010-2011 Freescale Semiconductor, Inc - * Copyright 2019-2020 NXP + * Copyright 2019-2021 NXP * Andy Fleming * * Based vaguely on the pxa mmc code: @@ -795,10 +795,21 @@ static void fsl_esdhc_get_cfg_common(struct fsl_esdhc_priv *priv, u32 caps; caps = esdhc_read32(>hostcapblt); + + /* +* For eSDHC, power supply is through peripheral circuit. Some eSDHC +* versions have value 0 of the bit but that does not reflect the +* truth. 3.3V is common for SD/MMC, and is supported for all boards +* with eSDHC in current u-boot. So, make 3.3V is supported in +* default in code. CONFIG_FSL_ESDHC_VS33_NOT_SUPPORT can be enabled +* if future board does not support 3.3V. +*/ + caps |= HOSTCAPBLT_VS33; + if (IS_ENABLED(CONFIG_FSL_ESDHC_VS33_NOT_SUPPORT)) + caps &= ~HOSTCAPBLT_VS33; + if (IS_ENABLED(CONFIG_SYS_FSL_ERRATUM_ESDHC135)) caps &= ~(HOSTCAPBLT_SRS | HOSTCAPBLT_VS18 | HOSTCAPBLT_VS30); - if (IS_ENABLED(CONFIG_SYS_FSL_MMC_HAS_CAPBLT_VS33)) - caps |= HOSTCAPBLT_VS33; if (caps & HOSTCAPBLT_VS18) cfg->voltages |= MMC_VDD_165_195; if (caps & HOSTCAPBLT_VS30) -- 2.25.1
[v3, 0/3] Drop CONFIG_FSL_ESDHC_VS33_NOT_SUPPORT
For eSDHC, power supply is through peripheral circuit. Some eSDHC versions have value 0 of the bit but that does not reflect the truth. 3.3V is common for SD/MMC, and is supported for all boards with eSDHC in current u-boot. So, make 3.3V is supported in default in code. CONFIG_FSL_ESDHC_VS33_NOT_SUPPORT can be enabled if future board does not support 3.3V. Then CONFIG_SYS_FSL_MMC_HAS_CAPBLT_VS33 can be dropped. And i.MX eSDHC driver should drop it too, since it's not used by any one of i.MX board. Changes for v2: - Updated copyright. Changes for v3: - Fixed code logic in patch#1. - Dropped wrong copyright. Yangbo Lu (3): mmc: fsl_esdhc: convert to CONFIG_FSL_ESDHC_VS33_NOT_SUPPORT mmc: fsl_esdhc_imx: drop CONFIG_SYS_FSL_MMC_HAS_CAPBLT_VS33 armv8: layerscape: drop CONFIG_SYS_FSL_MMC_HAS_CAPBLT_VS33 drivers/mmc/Kconfig | 7 +++ drivers/mmc/fsl_esdhc.c | 17 ++--- drivers/mmc/fsl_esdhc_imx.c | 7 +-- include/configs/T208xQDS.h | 3 +-- include/configs/T208xRDB.h | 3 +-- include/configs/T4240RDB.h | 3 +-- include/configs/kontron_sl28.h | 5 - include/configs/ls1012a2g5rdb.h | 7 +-- include/configs/ls1012afrwy.h| 7 +-- include/configs/ls1012aqds.h | 6 +- include/configs/ls1012ardb.h | 8 +--- include/configs/ls1028a_common.h | 7 +-- include/configs/ls1043a_common.h | 9 + include/configs/ls1046a_common.h | 9 + include/configs/ls1088aqds.h | 3 +-- include/configs/ls1088ardb.h | 7 +-- include/configs/ls2080aqds.h | 7 +-- include/configs/ls2080ardb.h | 7 +-- include/configs/lx2160a_common.h | 7 +-- scripts/config_whitelist.txt | 1 - 20 files changed, 37 insertions(+), 93 deletions(-) base-commit: 89be8e31ccd1c53b010385ed0807eb00f0eec06a -- 2.25.1
[v2, 3/3] armv8: layerscape: drop CONFIG_SYS_FSL_MMC_HAS_CAPBLT_VS33
Drop CONFIG_SYS_FSL_MMC_HAS_CAPBLT_VS33. CONFIG_FSL_ESDHC_VS33_NOT_SUPPORT is used instead. Signed-off-by: Yangbo Lu --- Changes for v2: - Updated copyright. --- include/configs/T208xQDS.h | 3 +-- include/configs/T208xRDB.h | 3 +-- include/configs/T4240RDB.h | 3 +-- include/configs/kontron_sl28.h | 8 +++- include/configs/ls1012a2g5rdb.h | 7 +-- include/configs/ls1012afrwy.h| 7 +-- include/configs/ls1012aqds.h | 6 +- include/configs/ls1012ardb.h | 8 +--- include/configs/ls1028a_common.h | 7 +-- include/configs/ls1043a_common.h | 9 + include/configs/ls1046a_common.h | 9 + include/configs/ls1088aqds.h | 3 +-- include/configs/ls1088ardb.h | 7 +-- include/configs/ls2080aqds.h | 7 +-- include/configs/ls2080ardb.h | 7 +-- include/configs/lx2160a_common.h | 7 +-- scripts/config_whitelist.txt | 1 - 17 files changed, 18 insertions(+), 84 deletions(-) diff --git a/include/configs/T208xQDS.h b/include/configs/T208xQDS.h index b1acb564c3..7bc792b8d1 100644 --- a/include/configs/T208xQDS.h +++ b/include/configs/T208xQDS.h @@ -1,7 +1,7 @@ /* SPDX-License-Identifier: GPL-2.0+ */ /* * Copyright 2011-2013 Freescale Semiconductor, Inc. - * Copyright 2020 NXP + * Copyright 2020-2021 NXP */ /* @@ -618,7 +618,6 @@ unsigned long get_board_ddr_clk(void); #ifdef CONFIG_MMC #define CONFIG_SYS_FSL_ESDHC_ADDR CONFIG_SYS_MPC85xx_ESDHC_ADDR #define CONFIG_SYS_FSL_ESDHC_BROKEN_TIMEOUT -#define CONFIG_SYS_FSL_MMC_HAS_CAPBLT_VS33 #endif /* diff --git a/include/configs/T208xRDB.h b/include/configs/T208xRDB.h index e467ef453d..b5197b3ed9 100644 --- a/include/configs/T208xRDB.h +++ b/include/configs/T208xRDB.h @@ -1,7 +1,7 @@ /* SPDX-License-Identifier: GPL-2.0+ */ /* * Copyright 2014 Freescale Semiconductor, Inc. - * Copyright 2020 NXP + * Copyright 2020-2021 NXP */ /* @@ -574,7 +574,6 @@ unsigned long get_board_ddr_clk(void); #ifdef CONFIG_MMC #define CONFIG_SYS_FSL_ESDHC_ADDR CONFIG_SYS_MPC85xx_ESDHC_ADDR #define CONFIG_SYS_FSL_ESDHC_BROKEN_TIMEOUT -#define CONFIG_SYS_FSL_MMC_HAS_CAPBLT_VS33 #endif /* diff --git a/include/configs/T4240RDB.h b/include/configs/T4240RDB.h index a04d9137b3..139beae08d 100644 --- a/include/configs/T4240RDB.h +++ b/include/configs/T4240RDB.h @@ -1,7 +1,7 @@ /* SPDX-License-Identifier: GPL-2.0+ */ /* * Copyright 2014 Freescale Semiconductor, Inc. - * Copyright 2020 NXP + * Copyright 2020-2021 NXP */ /* @@ -585,7 +585,6 @@ unsigned long get_board_ddr_clk(void); #ifdef CONFIG_MMC #define CONFIG_SYS_FSL_ESDHC_ADDR CONFIG_SYS_MPC85xx_ESDHC_ADDR #define CONFIG_SYS_FSL_ESDHC_BROKEN_TIMEOUT -#define CONFIG_SYS_FSL_MMC_HAS_CAPBLT_VS33 #endif diff --git a/include/configs/kontron_sl28.h b/include/configs/kontron_sl28.h index 5f11205802..4e9ea9d7fe 100644 --- a/include/configs/kontron_sl28.h +++ b/include/configs/kontron_sl28.h @@ -1,4 +1,7 @@ /* SPDX-License-Identifier: GPL-2.0+ */ +/* + * Copyright 2021 NXP + */ #ifndef __SL28_H #define __SL28_H @@ -56,11 +59,6 @@ #define CONFIG_DDR_CLK_FREQ1 #define COUNTER_FREQUENCY_REAL (CONFIG_SYS_CLK_FREQ / 4) -/* MMC */ -#ifdef CONFIG_MMC -#define CONFIG_SYS_FSL_MMC_HAS_CAPBLT_VS33 -#endif - /* ethernet */ #define CONFIG_SYS_RX_ETH_BUFFER 8 diff --git a/include/configs/ls1012a2g5rdb.h b/include/configs/ls1012a2g5rdb.h index 9962b9872a..1c016dee97 100644 --- a/include/configs/ls1012a2g5rdb.h +++ b/include/configs/ls1012a2g5rdb.h @@ -1,6 +1,6 @@ /* SPDX-License-Identifier: GPL-2.0+ */ /* - * Copyright 2017 NXP + * Copyright 2017, 2021 NXP */ #ifndef __LS1012A2G5RDB_H__ @@ -13,11 +13,6 @@ #define CONFIG_CHIP_SELECTS_PER_CTRL 1 #define CONFIG_SYS_SDRAM_SIZE 0x4000 -/* MMC */ -#ifdef CONFIG_MMC -#define CONFIG_SYS_FSL_MMC_HAS_CAPBLT_VS33 -#endif - /* SATA */ #define CONFIG_LIBATA #define CONFIG_SCSI_AHCI diff --git a/include/configs/ls1012afrwy.h b/include/configs/ls1012afrwy.h index ba152834d5..9024d5e10f 100644 --- a/include/configs/ls1012afrwy.h +++ b/include/configs/ls1012afrwy.h @@ -1,6 +1,6 @@ /* SPDX-License-Identifier: GPL-2.0+ */ /* - * Copyright 2018 NXP + * Copyright 2018, 2021 NXP */ #ifndef __LS1012AFRWY_H__ @@ -33,11 +33,6 @@ func(DHCP, dhcp, na) #endif -/* MMC */ -#ifdef CONFIG_MMC -#define CONFIG_SYS_FSL_MMC_HAS_CAPBLT_VS33 -#endif - #define CONFIG_PCIE1 /* PCIE controller 1 */ #define CONFIG_PCI_SCAN_SHOW diff --git a/include/configs/ls1012aqds.h b/include/configs/ls1012aqds.h index 36be8f42c9..e76f5ef23b 100644 --- a/include/configs/ls1012aqds.h +++ b/include/configs/ls1012aqds.h @@ -1,6 +1,7 @@ /* SPDX-License-Identifier: GPL-2.0+ */ /* * Copyright 2016 Freescale Semiconductor, Inc. + * Copyright 2021 NXP */ #ifndef __LS1012AQDS_H__ @@ -93,11 +94,6 @@ DSPI_CTAR_DT(0)) #define CONFIG_SPI_FLASH_EON /* cs3 */ -/* MMC
[v2, 2/3] mmc: fsl_esdhc_imx: drop CONFIG_SYS_FSL_MMC_HAS_CAPBLT_VS33
There is no i.MX board using such option. Drop it. Signed-off-by: Yangbo Lu --- Changes for v2: - Updated copyright. --- drivers/mmc/fsl_esdhc_imx.c | 7 +-- 1 file changed, 1 insertion(+), 6 deletions(-) diff --git a/drivers/mmc/fsl_esdhc_imx.c b/drivers/mmc/fsl_esdhc_imx.c index a4675838e5..566ce046ae 100644 --- a/drivers/mmc/fsl_esdhc_imx.c +++ b/drivers/mmc/fsl_esdhc_imx.c @@ -1,7 +1,7 @@ // SPDX-License-Identifier: GPL-2.0+ /* * Copyright 2007, 2010-2011 Freescale Semiconductor, Inc - * Copyright 2019 NXP Semiconductors + * Copyright 2019, 2021 NXP * Andy Fleming * Yangbo Lu * @@ -1234,11 +1234,6 @@ static int fsl_esdhc_init(struct fsl_esdhc_priv *priv, ESDHC_HOSTCAPBLT_VS18 | ESDHC_HOSTCAPBLT_VS30); #endif -/* T4240 host controller capabilities register should have VS33 bit */ -#ifdef CONFIG_SYS_FSL_MMC_HAS_CAPBLT_VS33 - caps = caps | ESDHC_HOSTCAPBLT_VS33; -#endif - if (caps & ESDHC_HOSTCAPBLT_VS18) voltage_caps |= MMC_VDD_165_195; if (caps & ESDHC_HOSTCAPBLT_VS30) -- 2.25.1
[v2, 1/3] mmc: fsl_esdhc: convert to CONFIG_FSL_ESDHC_VS33_NOT_SUPPORT
For eSDHC, power supply is through peripheral circuit. So, 3.3V power supply capability from register bit does not reflect the truth. 3.3V is common for SD/MMC, and is supported for all boards with eSDHC in current u-boot. So, let's use a Kconfig CONFIG_FSL_ESDHC_VS33_NOT_SUPPORT making 3.3V is supported in default. This is also a fix-up for one previous patch, which converted to use IS_ENABLED() for CONFIG_SYS_FSL_MMC_HAS_CAPBLT_VS33 that is not a Kconfig option. Fixes: 52faec31827e ("mmc: fsl_esdhc: replace most #ifdefs by IS_ENABLED()") Signed-off-by: Yangbo Lu --- Changes for v2: - Updated copyright. --- drivers/mmc/Kconfig | 7 +++ drivers/mmc/fsl_esdhc.c | 8 +--- 2 files changed, 12 insertions(+), 3 deletions(-) diff --git a/drivers/mmc/Kconfig b/drivers/mmc/Kconfig index 8901456967..0909f502a1 100644 --- a/drivers/mmc/Kconfig +++ b/drivers/mmc/Kconfig @@ -798,6 +798,13 @@ config FSL_ESDHC_33V_IO_RELIABILITY_WORKAROUND This option assumes no hotplug, and u-boot has to make all the way to to linux to use 1.8v UHS-I speed mode if has card. +config FSL_ESDHC_VS33_NOT_SUPPORT + bool "3.3V power supply not supported" + depends on FSL_ESDHC + help + For eSDHC, power supply is through peripheral circuit. 3.3V support is + common. Select this if 3.3V power supply not supported. + config FSL_ESDHC_IMX bool "Freescale/NXP i.MX eSDHC controller support" help diff --git a/drivers/mmc/fsl_esdhc.c b/drivers/mmc/fsl_esdhc.c index 7501fdb71e..b3c71c8695 100644 --- a/drivers/mmc/fsl_esdhc.c +++ b/drivers/mmc/fsl_esdhc.c @@ -1,7 +1,7 @@ // SPDX-License-Identifier: GPL-2.0+ /* * Copyright 2007, 2010-2011 Freescale Semiconductor, Inc - * Copyright 2019-2020 NXP + * Copyright 2019-2021 NXP * Andy Fleming * * Based vaguely on the pxa mmc code: @@ -795,10 +795,12 @@ static void fsl_esdhc_get_cfg_common(struct fsl_esdhc_priv *priv, u32 caps; caps = esdhc_read32(>hostcapblt); + + if (!IS_ENABLED(CONFIG_FSL_ESDHC_VS33_NOT_SUPPORT)) + caps |= HOSTCAPBLT_VS33; + if (IS_ENABLED(CONFIG_SYS_FSL_ERRATUM_ESDHC135)) caps &= ~(HOSTCAPBLT_SRS | HOSTCAPBLT_VS18 | HOSTCAPBLT_VS30); - if (IS_ENABLED(CONFIG_SYS_FSL_MMC_HAS_CAPBLT_VS33)) - caps |= HOSTCAPBLT_VS33; if (caps & HOSTCAPBLT_VS18) cfg->voltages |= MMC_VDD_165_195; if (caps & HOSTCAPBLT_VS30) -- 2.25.1
[v2, 0/3] Drop CONFIG_FSL_ESDHC_VS33_NOT_SUPPORT
For eSDHC, power supply is through peripheral circuit. So, 3.3V power supply capability from register bit does not reflect the truth. 3.3V is common for SD/MMC, and is supported for all boards with eSDHC in current u-boot. So, let's use a Kconfig CONFIG_FSL_ESDHC_VS33_NOT_SUPPORT making 3.3V is supported in default. Then CONFIG_SYS_FSL_MMC_HAS_CAPBLT_VS33 can be dropped. And i.MX eSDHC driver should drop it too, since it's not used by any one of i.MX board. Changes for v2: - Updated copyright. Yangbo Lu (3): mmc: fsl_esdhc: convert to CONFIG_FSL_ESDHC_VS33_NOT_SUPPORT mmc: fsl_esdhc_imx: drop CONFIG_SYS_FSL_MMC_HAS_CAPBLT_VS33 armv8: layerscape: drop CONFIG_SYS_FSL_MMC_HAS_CAPBLT_VS33 drivers/mmc/Kconfig | 7 +++ drivers/mmc/fsl_esdhc.c | 8 +--- drivers/mmc/fsl_esdhc_imx.c | 7 +-- include/configs/T208xQDS.h | 3 +-- include/configs/T208xRDB.h | 3 +-- include/configs/T4240RDB.h | 3 +-- include/configs/kontron_sl28.h | 8 +++- include/configs/ls1012a2g5rdb.h | 7 +-- include/configs/ls1012afrwy.h| 7 +-- include/configs/ls1012aqds.h | 6 +- include/configs/ls1012ardb.h | 8 +--- include/configs/ls1028a_common.h | 7 +-- include/configs/ls1043a_common.h | 9 + include/configs/ls1046a_common.h | 9 + include/configs/ls1088aqds.h | 3 +-- include/configs/ls1088ardb.h | 7 +-- include/configs/ls2080aqds.h | 7 +-- include/configs/ls2080ardb.h | 7 +-- include/configs/lx2160a_common.h | 7 +-- scripts/config_whitelist.txt | 1 - 20 files changed, 31 insertions(+), 93 deletions(-) base-commit: 89be8e31ccd1c53b010385ed0807eb00f0eec06a -- 2.25.1
[PATCH 3/3] armv8: layerscape: drop CONFIG_SYS_FSL_MMC_HAS_CAPBLT_VS33
Drop CONFIG_SYS_FSL_MMC_HAS_CAPBLT_VS33. CONFIG_FSL_ESDHC_VS33_NOT_SUPPORT is used instead. Signed-off-by: Yangbo Lu --- include/configs/T208xQDS.h | 1 - include/configs/T208xRDB.h | 1 - include/configs/T4240RDB.h | 1 - include/configs/kontron_sl28.h | 5 - include/configs/ls1012a2g5rdb.h | 5 - include/configs/ls1012afrwy.h| 5 - include/configs/ls1012aqds.h | 5 - include/configs/ls1012ardb.h | 6 -- include/configs/ls1028a_common.h | 5 - include/configs/ls1043a_common.h | 7 --- include/configs/ls1046a_common.h | 7 --- include/configs/ls1088aqds.h | 1 - include/configs/ls1088ardb.h | 5 - include/configs/ls2080aqds.h | 5 - include/configs/ls2080ardb.h | 5 - include/configs/lx2160a_common.h | 5 - scripts/config_whitelist.txt | 1 - 17 files changed, 70 deletions(-) diff --git a/include/configs/T208xQDS.h b/include/configs/T208xQDS.h index b1acb564c3..c2bc778809 100644 --- a/include/configs/T208xQDS.h +++ b/include/configs/T208xQDS.h @@ -618,7 +618,6 @@ unsigned long get_board_ddr_clk(void); #ifdef CONFIG_MMC #define CONFIG_SYS_FSL_ESDHC_ADDR CONFIG_SYS_MPC85xx_ESDHC_ADDR #define CONFIG_SYS_FSL_ESDHC_BROKEN_TIMEOUT -#define CONFIG_SYS_FSL_MMC_HAS_CAPBLT_VS33 #endif /* diff --git a/include/configs/T208xRDB.h b/include/configs/T208xRDB.h index e467ef453d..b12289f703 100644 --- a/include/configs/T208xRDB.h +++ b/include/configs/T208xRDB.h @@ -574,7 +574,6 @@ unsigned long get_board_ddr_clk(void); #ifdef CONFIG_MMC #define CONFIG_SYS_FSL_ESDHC_ADDR CONFIG_SYS_MPC85xx_ESDHC_ADDR #define CONFIG_SYS_FSL_ESDHC_BROKEN_TIMEOUT -#define CONFIG_SYS_FSL_MMC_HAS_CAPBLT_VS33 #endif /* diff --git a/include/configs/T4240RDB.h b/include/configs/T4240RDB.h index a04d9137b3..003aa55e6c 100644 --- a/include/configs/T4240RDB.h +++ b/include/configs/T4240RDB.h @@ -585,7 +585,6 @@ unsigned long get_board_ddr_clk(void); #ifdef CONFIG_MMC #define CONFIG_SYS_FSL_ESDHC_ADDR CONFIG_SYS_MPC85xx_ESDHC_ADDR #define CONFIG_SYS_FSL_ESDHC_BROKEN_TIMEOUT -#define CONFIG_SYS_FSL_MMC_HAS_CAPBLT_VS33 #endif diff --git a/include/configs/kontron_sl28.h b/include/configs/kontron_sl28.h index 5f11205802..bfb4e67c8f 100644 --- a/include/configs/kontron_sl28.h +++ b/include/configs/kontron_sl28.h @@ -56,11 +56,6 @@ #define CONFIG_DDR_CLK_FREQ1 #define COUNTER_FREQUENCY_REAL (CONFIG_SYS_CLK_FREQ / 4) -/* MMC */ -#ifdef CONFIG_MMC -#define CONFIG_SYS_FSL_MMC_HAS_CAPBLT_VS33 -#endif - /* ethernet */ #define CONFIG_SYS_RX_ETH_BUFFER 8 diff --git a/include/configs/ls1012a2g5rdb.h b/include/configs/ls1012a2g5rdb.h index 9962b9872a..e651e5f90a 100644 --- a/include/configs/ls1012a2g5rdb.h +++ b/include/configs/ls1012a2g5rdb.h @@ -13,11 +13,6 @@ #define CONFIG_CHIP_SELECTS_PER_CTRL 1 #define CONFIG_SYS_SDRAM_SIZE 0x4000 -/* MMC */ -#ifdef CONFIG_MMC -#define CONFIG_SYS_FSL_MMC_HAS_CAPBLT_VS33 -#endif - /* SATA */ #define CONFIG_LIBATA #define CONFIG_SCSI_AHCI diff --git a/include/configs/ls1012afrwy.h b/include/configs/ls1012afrwy.h index ba152834d5..c5096101b4 100644 --- a/include/configs/ls1012afrwy.h +++ b/include/configs/ls1012afrwy.h @@ -33,11 +33,6 @@ func(DHCP, dhcp, na) #endif -/* MMC */ -#ifdef CONFIG_MMC -#define CONFIG_SYS_FSL_MMC_HAS_CAPBLT_VS33 -#endif - #define CONFIG_PCIE1 /* PCIE controller 1 */ #define CONFIG_PCI_SCAN_SHOW diff --git a/include/configs/ls1012aqds.h b/include/configs/ls1012aqds.h index 36be8f42c9..226d42f182 100644 --- a/include/configs/ls1012aqds.h +++ b/include/configs/ls1012aqds.h @@ -93,11 +93,6 @@ DSPI_CTAR_DT(0)) #define CONFIG_SPI_FLASH_EON /* cs3 */ -/* MMC */ -#ifdef CONFIG_MMC -#define CONFIG_SYS_FSL_MMC_HAS_CAPBLT_VS33 -#endif - #define CONFIG_PCIE1 /* PCIE controller 1 */ #define CONFIG_PCI_SCAN_SHOW diff --git a/include/configs/ls1012ardb.h b/include/configs/ls1012ardb.h index 582945b2ab..f896d5516f 100644 --- a/include/configs/ls1012ardb.h +++ b/include/configs/ls1012ardb.h @@ -38,12 +38,6 @@ #define __PHY_ETH2_MASK0xFB #define __PHY_ETH1_MASK0xFD -/* MMC */ -#ifdef CONFIG_MMC -#define CONFIG_SYS_FSL_MMC_HAS_CAPBLT_VS33 -#endif - - #define CONFIG_PCIE1 /* PCIE controller 1 */ #define CONFIG_PCI_SCAN_SHOW diff --git a/include/configs/ls1028a_common.h b/include/configs/ls1028a_common.h index 31fcdae986..09d8f0c707 100644 --- a/include/configs/ls1028a_common.h +++ b/include/configs/ls1028a_common.h @@ -93,11 +93,6 @@ #define CONFIG_SYS_BOOTM_LEN (64 << 20) /* Increase max gunzip size */ -/* MMC */ -#ifdef CONFIG_MMC -#define CONFIG_SYS_FSL_MMC_HAS_CAPBLT_VS33 -#endif - #define OCRAM_NONSECURE_SIZE 0x0001 #define CONFIG_SYS_FSL_QSPI_BASE 0x2000 diff --git a/include/configs/ls1043a_common.h b/include/configs/ls1043a_common.h
[PATCH 2/3] mmc: fsl_esdhc_imx: drop CONFIG_SYS_FSL_MMC_HAS_CAPBLT_VS33
There is no i.MX board using such option. Drop it. Signed-off-by: Yangbo Lu --- drivers/mmc/fsl_esdhc_imx.c | 5 - 1 file changed, 5 deletions(-) diff --git a/drivers/mmc/fsl_esdhc_imx.c b/drivers/mmc/fsl_esdhc_imx.c index a4675838e5..d767795b58 100644 --- a/drivers/mmc/fsl_esdhc_imx.c +++ b/drivers/mmc/fsl_esdhc_imx.c @@ -1234,11 +1234,6 @@ static int fsl_esdhc_init(struct fsl_esdhc_priv *priv, ESDHC_HOSTCAPBLT_VS18 | ESDHC_HOSTCAPBLT_VS30); #endif -/* T4240 host controller capabilities register should have VS33 bit */ -#ifdef CONFIG_SYS_FSL_MMC_HAS_CAPBLT_VS33 - caps = caps | ESDHC_HOSTCAPBLT_VS33; -#endif - if (caps & ESDHC_HOSTCAPBLT_VS18) voltage_caps |= MMC_VDD_165_195; if (caps & ESDHC_HOSTCAPBLT_VS30) -- 2.25.1
[PATCH 1/3] mmc: fsl_esdhc: convert to CONFIG_FSL_ESDHC_VS33_NOT_SUPPORT
For eSDHC, power supply is through peripheral circuit. So, 3.3V power supply capability from register bit does not reflect the truth. 3.3V is common for SD/MMC, and is supported for all boards with eSDHC in current u-boot. So, let's use a Kconfig CONFIG_FSL_ESDHC_VS33_NOT_SUPPORT making 3.3V is supported in default. This is also a fix-up for one previous patch, which converted to use IS_ENABLED() for CONFIG_SYS_FSL_MMC_HAS_CAPBLT_VS33 that is not a Kconfig option. Fixes: 52faec31827e ("mmc: fsl_esdhc: replace most #ifdefs by IS_ENABLED()") Signed-off-by: Yangbo Lu --- drivers/mmc/Kconfig | 7 +++ drivers/mmc/fsl_esdhc.c | 6 -- 2 files changed, 11 insertions(+), 2 deletions(-) diff --git a/drivers/mmc/Kconfig b/drivers/mmc/Kconfig index 8901456967..0909f502a1 100644 --- a/drivers/mmc/Kconfig +++ b/drivers/mmc/Kconfig @@ -798,6 +798,13 @@ config FSL_ESDHC_33V_IO_RELIABILITY_WORKAROUND This option assumes no hotplug, and u-boot has to make all the way to to linux to use 1.8v UHS-I speed mode if has card. +config FSL_ESDHC_VS33_NOT_SUPPORT + bool "3.3V power supply not supported" + depends on FSL_ESDHC + help + For eSDHC, power supply is through peripheral circuit. 3.3V support is + common. Select this if 3.3V power supply not supported. + config FSL_ESDHC_IMX bool "Freescale/NXP i.MX eSDHC controller support" help diff --git a/drivers/mmc/fsl_esdhc.c b/drivers/mmc/fsl_esdhc.c index 7501fdb71e..d20f32b530 100644 --- a/drivers/mmc/fsl_esdhc.c +++ b/drivers/mmc/fsl_esdhc.c @@ -795,10 +795,12 @@ static void fsl_esdhc_get_cfg_common(struct fsl_esdhc_priv *priv, u32 caps; caps = esdhc_read32(>hostcapblt); + + if (!IS_ENABLED(CONFIG_FSL_ESDHC_VS33_NOT_SUPPORT)) + caps |= HOSTCAPBLT_VS33; + if (IS_ENABLED(CONFIG_SYS_FSL_ERRATUM_ESDHC135)) caps &= ~(HOSTCAPBLT_SRS | HOSTCAPBLT_VS18 | HOSTCAPBLT_VS30); - if (IS_ENABLED(CONFIG_SYS_FSL_MMC_HAS_CAPBLT_VS33)) - caps |= HOSTCAPBLT_VS33; if (caps & HOSTCAPBLT_VS18) cfg->voltages |= MMC_VDD_165_195; if (caps & HOSTCAPBLT_VS30) -- 2.25.1
[PATCH 0/3] Drop CONFIG_FSL_ESDHC_VS33_NOT_SUPPORT
For eSDHC, power supply is through peripheral circuit. So, 3.3V power supply capability from register bit does not reflect the truth. 3.3V is common for SD/MMC, and is supported for all boards with eSDHC in current u-boot. So, let's use a Kconfig CONFIG_FSL_ESDHC_VS33_NOT_SUPPORT making 3.3V is supported in default. Then CONFIG_SYS_FSL_MMC_HAS_CAPBLT_VS33 can be dropped. And i.MX eSDHC driver should drop it too, since it's not used by any one of i.MX board. Yangbo Lu (3): mmc: fsl_esdhc: convert to CONFIG_FSL_ESDHC_VS33_NOT_SUPPORT mmc: fsl_esdhc_imx: drop CONFIG_SYS_FSL_MMC_HAS_CAPBLT_VS33 armv8: layerscape: drop CONFIG_SYS_FSL_MMC_HAS_CAPBLT_VS33 drivers/mmc/Kconfig | 7 +++ drivers/mmc/fsl_esdhc.c | 6 -- drivers/mmc/fsl_esdhc_imx.c | 5 - include/configs/T208xQDS.h | 1 - include/configs/T208xRDB.h | 1 - include/configs/T4240RDB.h | 1 - include/configs/kontron_sl28.h | 5 - include/configs/ls1012a2g5rdb.h | 5 - include/configs/ls1012afrwy.h| 5 - include/configs/ls1012aqds.h | 5 - include/configs/ls1012ardb.h | 6 -- include/configs/ls1028a_common.h | 5 - include/configs/ls1043a_common.h | 7 --- include/configs/ls1046a_common.h | 7 --- include/configs/ls1088aqds.h | 1 - include/configs/ls1088ardb.h | 5 - include/configs/ls2080aqds.h | 5 - include/configs/ls2080ardb.h | 5 - include/configs/lx2160a_common.h | 5 - scripts/config_whitelist.txt | 1 - 20 files changed, 11 insertions(+), 77 deletions(-) base-commit: 89be8e31ccd1c53b010385ed0807eb00f0eec06a -- 2.25.1
[v2] arm: dts: lx2162aqds: support eMMC HS400 mode on esdhc1
Add properties related to eMMC HS400 mode for esdhc1. Signed-off-by: Yangbo Lu --- Changes for v2: - Updated copyright. --- arch/arm/dts/fsl-lx2162a-qds-sd1-17.dtsi | 8 +++- arch/arm/dts/fsl-lx2162a-qds-sd1-18.dtsi | 8 +++- arch/arm/dts/fsl-lx2162a-qds-sd1-20.dtsi | 8 +++- arch/arm/dts/fsl-lx2162a-qds.dts | 8 +++- 4 files changed, 28 insertions(+), 4 deletions(-) diff --git a/arch/arm/dts/fsl-lx2162a-qds-sd1-17.dtsi b/arch/arm/dts/fsl-lx2162a-qds-sd1-17.dtsi index 60f5a4ee43..d1e4a8567f 100644 --- a/arch/arm/dts/fsl-lx2162a-qds-sd1-17.dtsi +++ b/arch/arm/dts/fsl-lx2162a-qds-sd1-17.dtsi @@ -5,7 +5,7 @@ * Some assumptions are made: ** mezzanine card M8 is connected to IO SLOT1 (25g-aui for DPMAC 3,4,5,6) * - * Copyright 2020 NXP + * Copyright 2020-2021 NXP * */ @@ -56,3 +56,9 @@ reg = <0x3>; }; }; + + { + mmc-hs200-1_8v; + mmc-hs400-1_8v; + bus-width = <8>; +}; diff --git a/arch/arm/dts/fsl-lx2162a-qds-sd1-18.dtsi b/arch/arm/dts/fsl-lx2162a-qds-sd1-18.dtsi index 8e11b0680a..e9a743b3a2 100644 --- a/arch/arm/dts/fsl-lx2162a-qds-sd1-18.dtsi +++ b/arch/arm/dts/fsl-lx2162a-qds-sd1-18.dtsi @@ -6,7 +6,7 @@ ** mezzanine card M11 is connected to IO SLOT1 (usxgmii for DPMAC 3,4) ** mezzanine card M13/M8 is connected to IO SLOT6 (25g-aui for DPMAC 5,6) * - * Copyright 2020 NXP + * Copyright 2020-2021 NXP * */ @@ -59,3 +59,9 @@ reg = <0x1>; }; }; + + { + mmc-hs200-1_8v; + mmc-hs400-1_8v; + bus-width = <8>; +}; diff --git a/arch/arm/dts/fsl-lx2162a-qds-sd1-20.dtsi b/arch/arm/dts/fsl-lx2162a-qds-sd1-20.dtsi index faf4285eab..d9ad1c6a4b 100644 --- a/arch/arm/dts/fsl-lx2162a-qds-sd1-20.dtsi +++ b/arch/arm/dts/fsl-lx2162a-qds-sd1-20.dtsi @@ -6,7 +6,7 @@ ** Mezzanine card M8 is connected to IO SLOT1 *(xlaui4 for DPMAC 1) * - * Copyright 2020 NXP + * Copyright 2020-2021 NXP * */ @@ -24,3 +24,9 @@ reg = <0x0>; }; }; + + { + mmc-hs200-1_8v; + mmc-hs400-1_8v; + bus-width = <8>; +}; diff --git a/arch/arm/dts/fsl-lx2162a-qds.dts b/arch/arm/dts/fsl-lx2162a-qds.dts index 341610ccf4..0ca30df862 100644 --- a/arch/arm/dts/fsl-lx2162a-qds.dts +++ b/arch/arm/dts/fsl-lx2162a-qds.dts @@ -2,7 +2,7 @@ /* * NXP LX2162AQDS device tree source * - * Copyright 2020 NXP + * Copyright 2020-2021 NXP * */ @@ -135,3 +135,9 @@ reg = <2>; }; }; + + { + mmc-hs200-1_8v; + mmc-hs400-1_8v; + bus-width = <8>; +}; -- 2.25.1
[PATCH] armv8: layerscape: enable eMMC HS400 workarounds for LX2160A/LX2162A
Enable eMMC HS400 workarounds for LX2160A/LX2162A. Signed-off-by: Yangbo Lu --- arch/arm/cpu/armv8/fsl-layerscape/Kconfig | 4 1 file changed, 4 insertions(+) diff --git a/arch/arm/cpu/armv8/fsl-layerscape/Kconfig b/arch/arm/cpu/armv8/fsl-layerscape/Kconfig index 9d1ba4c771..395e5ccaad 100644 --- a/arch/arm/cpu/armv8/fsl-layerscape/Kconfig +++ b/arch/arm/cpu/armv8/fsl-layerscape/Kconfig @@ -224,6 +224,8 @@ config ARCH_LX2162A select SYS_FSL_EC1 select SYS_FSL_EC2 select SYS_FSL_ERRATUM_A050106 + select SYS_FSL_ERRATUM_A011334 + select SYS_FSL_ESDHC_UNRELIABLE_PULSE_DETECTION_WORKAROUND select SYS_FSL_HAS_RGMII select SYS_FSL_HAS_SEC select SYS_FSL_HAS_CCN508 @@ -254,6 +256,8 @@ config ARCH_LX2160A select SYS_FSL_EC1 select SYS_FSL_EC2 select SYS_FSL_ERRATUM_A050106 + select SYS_FSL_ERRATUM_A011334 + select SYS_FSL_ESDHC_UNRELIABLE_PULSE_DETECTION_WORKAROUND select SYS_FSL_HAS_RGMII select SYS_FSL_HAS_SEC select SYS_FSL_HAS_CCN508 -- 2.25.1
[PATCH] arm: dts: lx2162aqds: support eMMC HS400 mode on esdhc1
Add properties related to eMMC HS400 mode for esdhc1. Signed-off-by: Yangbo Lu --- arch/arm/dts/fsl-lx2162a-qds-sd1-17.dtsi | 6 ++ arch/arm/dts/fsl-lx2162a-qds-sd1-18.dtsi | 6 ++ arch/arm/dts/fsl-lx2162a-qds-sd1-20.dtsi | 6 ++ arch/arm/dts/fsl-lx2162a-qds.dts | 6 ++ 4 files changed, 24 insertions(+) diff --git a/arch/arm/dts/fsl-lx2162a-qds-sd1-17.dtsi b/arch/arm/dts/fsl-lx2162a-qds-sd1-17.dtsi index 60f5a4ee43..3b6fddba7c 100644 --- a/arch/arm/dts/fsl-lx2162a-qds-sd1-17.dtsi +++ b/arch/arm/dts/fsl-lx2162a-qds-sd1-17.dtsi @@ -56,3 +56,9 @@ reg = <0x3>; }; }; + + { + mmc-hs200-1_8v; + mmc-hs400-1_8v; + bus-width = <8>; +}; diff --git a/arch/arm/dts/fsl-lx2162a-qds-sd1-18.dtsi b/arch/arm/dts/fsl-lx2162a-qds-sd1-18.dtsi index 8e11b0680a..0f4329f587 100644 --- a/arch/arm/dts/fsl-lx2162a-qds-sd1-18.dtsi +++ b/arch/arm/dts/fsl-lx2162a-qds-sd1-18.dtsi @@ -59,3 +59,9 @@ reg = <0x1>; }; }; + + { + mmc-hs200-1_8v; + mmc-hs400-1_8v; + bus-width = <8>; +}; diff --git a/arch/arm/dts/fsl-lx2162a-qds-sd1-20.dtsi b/arch/arm/dts/fsl-lx2162a-qds-sd1-20.dtsi index faf4285eab..8c856a19d4 100644 --- a/arch/arm/dts/fsl-lx2162a-qds-sd1-20.dtsi +++ b/arch/arm/dts/fsl-lx2162a-qds-sd1-20.dtsi @@ -24,3 +24,9 @@ reg = <0x0>; }; }; + + { + mmc-hs200-1_8v; + mmc-hs400-1_8v; + bus-width = <8>; +}; diff --git a/arch/arm/dts/fsl-lx2162a-qds.dts b/arch/arm/dts/fsl-lx2162a-qds.dts index 341610ccf4..68cb328716 100644 --- a/arch/arm/dts/fsl-lx2162a-qds.dts +++ b/arch/arm/dts/fsl-lx2162a-qds.dts @@ -135,3 +135,9 @@ reg = <2>; }; }; + + { + mmc-hs200-1_8v; + mmc-hs400-1_8v; + bus-width = <8>; +}; -- 2.25.1
[v2, 1/2] mmc: fsl_esdhc: set sysctl register for clock initialization
The initial clock setting should be through sysctl register only, while the mmc_set_clock() will call mmc_set_ios() introduce other configurations like bus width, mode, and so on. Signed-off-by: Yangbo Lu Reviewed-by: Jaehoon Chung --- Changes for v2: - Added "Reviewed-by". --- drivers/mmc/fsl_esdhc.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/mmc/fsl_esdhc.c b/drivers/mmc/fsl_esdhc.c index 642784e..68130ee 100644 --- a/drivers/mmc/fsl_esdhc.c +++ b/drivers/mmc/fsl_esdhc.c @@ -715,7 +715,7 @@ static int esdhc_init_common(struct fsl_esdhc_priv *priv, struct mmc *mmc) esdhc_setbits32(>sysctl, SYSCTL_HCKEN | SYSCTL_IPGEN); /* Set the initial clock speed */ - mmc_set_clock(mmc, 40, MMC_CLK_ENABLE); + set_sysctl(priv, mmc, 40); /* Disable the BRR and BWR bits in IRQSTAT */ esdhc_clrbits32(>irqstaten, IRQSTATEN_BRR | IRQSTATEN_BWR); -- 2.7.4
[v2, 2/2] mmc: fsl_esdhc: make sure delay chain locked for HS400
For eMMC HS400 mode, the DLL reset is a required step for mmc rescan. This step has not been documented in reference manual, but the RM will be fixed sooner or later. In previous commit to support eMMC HS400, db8f936 mmc: fsl_esdhc: support eMMC HS400 mode the steps to configure DLL could be found in commit message, 13. Set DLLCFG0[DLL_ENABLE] and DLLCFG0[DLL_FREQ_SEL]. 14. Wait for delay chain to lock. these would be fixed as, 13. Set DLLCFG0[DLL_ENABLE] and DLLCFG0[DLL_FREQ_SEL]. 13.1 Write DLLCFG0[DLL_RESET] to 1 and wait for 1us, then write DLLCFG0[DLL_RESET] 14. Wait for delay chain to lock. This patch is to add the step of DLL reset, and make sure delay chain locked for HS400. Fixes: db8f93672b42 ("mmc: fsl_esdhc: support eMMC HS400 mode") Signed-off-by: Yangbo Lu Reviewed-by: Jaehoon Chung --- Changes for v2: - Added "Reviewed-by". - Explained more in commit message. --- drivers/mmc/fsl_esdhc.c | 28 +--- include/fsl_esdhc.h | 4 2 files changed, 29 insertions(+), 3 deletions(-) diff --git a/drivers/mmc/fsl_esdhc.c b/drivers/mmc/fsl_esdhc.c index 68130ee..a18316e 100644 --- a/drivers/mmc/fsl_esdhc.c +++ b/drivers/mmc/fsl_esdhc.c @@ -70,7 +70,9 @@ struct fsl_esdhc { uintsdtimingctl;/* SD timing control register */ charreserved8[20]; /* reserved */ uintdllcfg0;/* DLL config 0 register */ - charreserved9[680]; /* reserved */ + charreserved9[12]; /* reserved */ + uintdllstat0; /* DLL status 0 register */ + charreserved10[664];/* reserved */ uintesdhcctl; /* eSDHC control register */ }; @@ -617,9 +619,11 @@ static void esdhc_exit_hs400(struct fsl_esdhc_priv *priv) esdhc_tuning_block_enable(priv, false); } -static void esdhc_set_timing(struct fsl_esdhc_priv *priv, enum bus_mode mode) +static int esdhc_set_timing(struct fsl_esdhc_priv *priv, enum bus_mode mode) { struct fsl_esdhc *regs = priv->esdhc_regs; + ulong start; + u32 val; /* Exit HS400 mode before setting any other mode */ if (esdhc_read32(>tbctl) & HS400_MODE && @@ -640,17 +644,33 @@ static void esdhc_set_timing(struct fsl_esdhc_priv *priv, enum bus_mode mode) esdhc_setbits32(>dllcfg0, DLL_FREQ_SEL); esdhc_setbits32(>dllcfg0, DLL_ENABLE); + + esdhc_setbits32(>dllcfg0, DLL_RESET); + udelay(1); + esdhc_clrbits32(>dllcfg0, DLL_RESET); + + start = get_timer(0); + val = DLL_STS_SLV_LOCK; + while (!(esdhc_read32(>dllstat0) & val)) { + if (get_timer(start) > 1000) { + printf("fsl_esdhc: delay chain lock timeout\n"); + return -ETIMEDOUT; + } + } + esdhc_setbits32(>tbctl, HS400_WNDW_ADJUST); esdhc_clock_control(priv, false); esdhc_flush_async_fifo(priv); } esdhc_clock_control(priv, true); + return 0; } static int esdhc_set_ios_common(struct fsl_esdhc_priv *priv, struct mmc *mmc) { struct fsl_esdhc *regs = priv->esdhc_regs; + int ret; if (priv->is_sdhc_per_clk) { /* Select to use peripheral clock */ @@ -667,7 +687,9 @@ static int esdhc_set_ios_common(struct fsl_esdhc_priv *priv, struct mmc *mmc) set_sysctl(priv, mmc, mmc->clock); /* Set timing */ - esdhc_set_timing(priv, mmc->selected_mode); + ret = esdhc_set_timing(priv, mmc->selected_mode); + if (ret) + return ret; /* Set the bus width */ esdhc_clrbits32(>proctl, PROCTL_DTW_4 | PROCTL_DTW_8); diff --git a/include/fsl_esdhc.h b/include/fsl_esdhc.h index e6f1c75..850a304 100644 --- a/include/fsl_esdhc.h +++ b/include/fsl_esdhc.h @@ -187,8 +187,12 @@ /* DLL config 0 register */ #define DLL_ENABLE 0x8000 +#define DLL_RESET 0x4000 #define DLL_FREQ_SEL 0x0800 +/* DLL status 0 register */ +#define DLL_STS_SLV_LOCK 0x0800 + #define MAX_TUNING_LOOP40 #define HOSTVER_VENDOR(x) (((x) >> 8) & 0xff) -- 2.7.4
[v2, 0/2] mmc: fsl_esdhc: fix up for eMMC HS400
This patch-set provides fix up for eMMC HS400 for a potential DLL lock issue during mmc rescan. Changes for v2: - Added "Reviewed-by". - Explained more in patch 2 commit message. Yangbo Lu (2): mmc: fsl_esdhc: set sysctl register for clock initialization mmc: fsl_esdhc: make sure delay chain locked for HS400 drivers/mmc/fsl_esdhc.c | 30 ++ include/fsl_esdhc.h | 4 2 files changed, 30 insertions(+), 4 deletions(-) -- 2.7.4
[PATCH 1/2] mmc: fsl_esdhc: set sysctl register for clock initialization
The initial clock setting should be through sysctl register only, while the mmc_set_clock() will call mmc_set_ios() introduce other configurations like bus width, mode, and so on. Signed-off-by: Yangbo Lu --- drivers/mmc/fsl_esdhc.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/mmc/fsl_esdhc.c b/drivers/mmc/fsl_esdhc.c index 642784e..68130ee 100644 --- a/drivers/mmc/fsl_esdhc.c +++ b/drivers/mmc/fsl_esdhc.c @@ -715,7 +715,7 @@ static int esdhc_init_common(struct fsl_esdhc_priv *priv, struct mmc *mmc) esdhc_setbits32(>sysctl, SYSCTL_HCKEN | SYSCTL_IPGEN); /* Set the initial clock speed */ - mmc_set_clock(mmc, 40, MMC_CLK_ENABLE); + set_sysctl(priv, mmc, 40); /* Disable the BRR and BWR bits in IRQSTAT */ esdhc_clrbits32(>irqstaten, IRQSTATEN_BRR | IRQSTATEN_BWR); -- 2.7.4
[PATCH 0/2] mmc: fsl_esdhc: fix up for eMMC HS400
This patch-set provides fix up for eMMC HS400 for a potential DLL lock issue during mmc rescan. Yangbo Lu (2): mmc: fsl_esdhc: set sysctl register for clock initialization mmc: fsl_esdhc: make sure delay chain locked for HS400 drivers/mmc/fsl_esdhc.c | 30 ++ include/fsl_esdhc.h | 4 2 files changed, 30 insertions(+), 4 deletions(-) -- 2.7.4
[PATCH 2/2] mmc: fsl_esdhc: make sure delay chain locked for HS400
For eMMC HS400 mode, the DLL reset is a required step for mmc rescan. This step has not been documented in reference manual, but the RM will be fixed sooner or later. This patch is to add the step of DLL reset, and make sure delay chain locked for HS400. Fixes: db8f93672b42 ("mmc: fsl_esdhc: support eMMC HS400 mode") Signed-off-by: Yangbo Lu --- drivers/mmc/fsl_esdhc.c | 28 +--- include/fsl_esdhc.h | 4 2 files changed, 29 insertions(+), 3 deletions(-) diff --git a/drivers/mmc/fsl_esdhc.c b/drivers/mmc/fsl_esdhc.c index 68130ee..a18316e 100644 --- a/drivers/mmc/fsl_esdhc.c +++ b/drivers/mmc/fsl_esdhc.c @@ -70,7 +70,9 @@ struct fsl_esdhc { uintsdtimingctl;/* SD timing control register */ charreserved8[20]; /* reserved */ uintdllcfg0;/* DLL config 0 register */ - charreserved9[680]; /* reserved */ + charreserved9[12]; /* reserved */ + uintdllstat0; /* DLL status 0 register */ + charreserved10[664];/* reserved */ uintesdhcctl; /* eSDHC control register */ }; @@ -617,9 +619,11 @@ static void esdhc_exit_hs400(struct fsl_esdhc_priv *priv) esdhc_tuning_block_enable(priv, false); } -static void esdhc_set_timing(struct fsl_esdhc_priv *priv, enum bus_mode mode) +static int esdhc_set_timing(struct fsl_esdhc_priv *priv, enum bus_mode mode) { struct fsl_esdhc *regs = priv->esdhc_regs; + ulong start; + u32 val; /* Exit HS400 mode before setting any other mode */ if (esdhc_read32(>tbctl) & HS400_MODE && @@ -640,17 +644,33 @@ static void esdhc_set_timing(struct fsl_esdhc_priv *priv, enum bus_mode mode) esdhc_setbits32(>dllcfg0, DLL_FREQ_SEL); esdhc_setbits32(>dllcfg0, DLL_ENABLE); + + esdhc_setbits32(>dllcfg0, DLL_RESET); + udelay(1); + esdhc_clrbits32(>dllcfg0, DLL_RESET); + + start = get_timer(0); + val = DLL_STS_SLV_LOCK; + while (!(esdhc_read32(>dllstat0) & val)) { + if (get_timer(start) > 1000) { + printf("fsl_esdhc: delay chain lock timeout\n"); + return -ETIMEDOUT; + } + } + esdhc_setbits32(>tbctl, HS400_WNDW_ADJUST); esdhc_clock_control(priv, false); esdhc_flush_async_fifo(priv); } esdhc_clock_control(priv, true); + return 0; } static int esdhc_set_ios_common(struct fsl_esdhc_priv *priv, struct mmc *mmc) { struct fsl_esdhc *regs = priv->esdhc_regs; + int ret; if (priv->is_sdhc_per_clk) { /* Select to use peripheral clock */ @@ -667,7 +687,9 @@ static int esdhc_set_ios_common(struct fsl_esdhc_priv *priv, struct mmc *mmc) set_sysctl(priv, mmc, mmc->clock); /* Set timing */ - esdhc_set_timing(priv, mmc->selected_mode); + ret = esdhc_set_timing(priv, mmc->selected_mode); + if (ret) + return ret; /* Set the bus width */ esdhc_clrbits32(>proctl, PROCTL_DTW_4 | PROCTL_DTW_8); diff --git a/include/fsl_esdhc.h b/include/fsl_esdhc.h index e6f1c75..850a304 100644 --- a/include/fsl_esdhc.h +++ b/include/fsl_esdhc.h @@ -187,8 +187,12 @@ /* DLL config 0 register */ #define DLL_ENABLE 0x8000 +#define DLL_RESET 0x4000 #define DLL_FREQ_SEL 0x0800 +/* DLL status 0 register */ +#define DLL_STS_SLV_LOCK 0x0800 + #define MAX_TUNING_LOOP40 #define HOSTVER_VENDOR(x) (((x) >> 8) & 0xff) -- 2.7.4
[v2] configs: lx2162aqds: enable eMMC HS400 mode support
Enable eMMC HS400 mode support on LX2162AQDS. Signed-off-by: Yangbo Lu --- Depends on http://patchwork.ozlabs.org/project/uboot/list/?series=199900=* Changes for v2: - Fix typo. --- configs/lx2162aqds_tfa_SECURE_BOOT_defconfig | 1 + configs/lx2162aqds_tfa_defconfig | 1 + configs/lx2162aqds_tfa_verified_boot_defconfig | 1 + 3 files changed, 3 insertions(+) diff --git a/configs/lx2162aqds_tfa_SECURE_BOOT_defconfig b/configs/lx2162aqds_tfa_SECURE_BOOT_defconfig index 0b48b19..6adf8bd 100644 --- a/configs/lx2162aqds_tfa_SECURE_BOOT_defconfig +++ b/configs/lx2162aqds_tfa_SECURE_BOOT_defconfig @@ -37,6 +37,7 @@ CONFIG_NET_RANDOM_ETHADDR=y CONFIG_DM=y CONFIG_SATA_CEVA=y CONFIG_DM_MMC=y +CONFIG_MMC_HS400_SUPPORT=y CONFIG_FSL_ESDHC=y CONFIG_MTD=y CONFIG_DM_SPI_FLASH=y diff --git a/configs/lx2162aqds_tfa_defconfig b/configs/lx2162aqds_tfa_defconfig index 1f5b318..6c51d0d 100644 --- a/configs/lx2162aqds_tfa_defconfig +++ b/configs/lx2162aqds_tfa_defconfig @@ -43,6 +43,7 @@ CONFIG_DM=y CONFIG_SATA_CEVA=y CONFIG_FSL_CAAM=y CONFIG_DM_MMC=y +CONFIG_MMC_HS400_SUPPORT=y CONFIG_FSL_ESDHC=y CONFIG_MTD=y CONFIG_DM_SPI_FLASH=y diff --git a/configs/lx2162aqds_tfa_verified_boot_defconfig b/configs/lx2162aqds_tfa_verified_boot_defconfig index 5ee627a..be9c242 100644 --- a/configs/lx2162aqds_tfa_verified_boot_defconfig +++ b/configs/lx2162aqds_tfa_verified_boot_defconfig @@ -45,6 +45,7 @@ CONFIG_DM=y CONFIG_SATA_CEVA=y CONFIG_FSL_CAAM=y CONFIG_DM_MMC=y +CONFIG_MMC_HS400_SUPPORT=y CONFIG_FSL_ESDHC=y CONFIG_MTD=y CONFIG_DM_SPI_FLASH=y -- 2.7.4
arm: dts: lx2162aqds: support eMMC HS400 mode
From: Guanhua Gao From: Yangbo Lu Add properties related to eMMC HS400 mode. Signed-off-by: Yangbo Lu diff --git a/arch/arm/dts/fsl-lx2162a-qds.dts b/arch/arm/dts/fsl-lx2162a-qds.dts index 8c29fd2..a2be9ac 100644 --- a/arch/arm/dts/fsl-lx2162a-qds.dts +++ b/arch/arm/dts/fsl-lx2162a-qds.dts @@ -55,6 +55,9 @@ { status = "okay"; + mmc-hs200-1_8v; + mmc-hs400-1_8v; + bus-width = <8>; }; {
configs: lx2162aqds: enable CONFIG_BOARD_EARLY_INIT_R
From: Guanhua Gao From: Yangbo Lu Enable CONFIG_BOARD_EARLY_INIT_R for SDHC adapter card identification and configuration. Signed-off-by: Yangbo Lu diff --git a/configs/lx2162aqds_tfa_SECURE_BOOT_defconfig b/configs/lx2162aqds_tfa_SECURE_BOOT_defconfig index 9b1850c..e658592 100644 --- a/configs/lx2162aqds_tfa_SECURE_BOOT_defconfig +++ b/configs/lx2162aqds_tfa_SECURE_BOOT_defconfig @@ -16,6 +16,7 @@ CONFIG_OF_STDOUT_VIA_ALIAS=y CONFIG_USE_BOOTARGS=y CONFIG_BOOTARGS="console=ttyAMA0,115200 root=/dev/ram0 earlycon=pl011,mmio32,0x21c ramdisk_size=0x200 default_hugepagesz=1024m hugepagesz=1024m hugepages=2 pci=pcie_bus_perf" # CONFIG_USE_BOOTCOMMAND is not set +CONFIG_BOARD_EARLY_INIT_R=y CONFIG_MISC_INIT_R=y CONFIG_CMD_GREPENV=y CONFIG_CMD_EEPROM=y diff --git a/configs/lx2162aqds_tfa_defconfig b/configs/lx2162aqds_tfa_defconfig index 07837b9..ade6b7b 100644 --- a/configs/lx2162aqds_tfa_defconfig +++ b/configs/lx2162aqds_tfa_defconfig @@ -18,6 +18,7 @@ CONFIG_BOOTDELAY=10 CONFIG_USE_BOOTARGS=y CONFIG_BOOTARGS="console=ttyAMA0,115200 root=/dev/ram0 earlycon=pl011,mmio32,0x21c ramdisk_size=0x200 default_hugepagesz=1024m hugepagesz=1024m hugepages=2 pci=pcie_bus_perf" # CONFIG_USE_BOOTCOMMAND is not set +CONFIG_BOARD_EARLY_INIT_R=y CONFIG_MISC_INIT_R=y CONFIG_CMD_GREPENV=y CONFIG_CMD_EEPROM=y diff --git a/configs/lx2162aqds_tfa_verified_boot_defconfig b/configs/lx2162aqds_tfa_verified_boot_defconfig index 5d4ad47..3131fb3 100644 --- a/configs/lx2162aqds_tfa_verified_boot_defconfig +++ b/configs/lx2162aqds_tfa_verified_boot_defconfig @@ -20,6 +20,7 @@ CONFIG_BOOTDELAY=10 CONFIG_USE_BOOTARGS=y CONFIG_BOOTARGS="console=ttyAMA0,115200 root=/dev/ram0 earlycon=pl011,mmio32,0x21c ramdisk_size=0x200 default_hugepagesz=1024m hugepagesz=1024m hugepages=2 pci=pcie_bus_perf" # CONFIG_USE_BOOTCOMMAND is not set +CONFIG_BOARD_EARLY_INIT_R=y CONFIG_MISC_INIT_R=y CONFIG_CMD_GREPENV=y CONFIG_CMD_EEPROM=y
configs: lx2162aqds: enable eMMC HS400 mode support
From: Guanhua Gao From: Yangbo Lu Enable eMMC HS400 mode support on LX2162AQDS. Signed-off-by: Yangbo Lu diff --git a/configs/lx2162aqds_tfa_SECURE_BOOT_defconfig b/configs/lx2162aqds_tfa_SECURE_BOOT_defconfig index 9b1850c..75ee76d 100644 --- a/configs/lx2162aqds_tfa_SECURE_BOOT_defconfig +++ b/configs/lx2162aqds_tfa_SECURE_BOOT_defconfig @@ -36,6 +36,7 @@ CONFIG_NET_RANDOM_ETHADDR=y CONFIG_DM=y CONFIG_SATA_CEVA=y CONFIG_DM_MMC=y +CONFIG_MMC_HS400_SUPPORT=y CONFIG_FSL_ESDHC=y CONFIG_MTD=y CONFIG_DM_SPI_FLASH=y diff --git a/configs/lx2162aqds_tfa_defconfig b/configs/lx2162aqds_tfa_defconfig index 07837b9..181b8d1 100644 --- a/configs/lx2162aqds_tfa_defconfig +++ b/configs/lx2162aqds_tfa_defconfig @@ -42,6 +42,7 @@ CONFIG_DM=y CONFIG_SATA_CEVA=y CONFIG_FSL_CAAM=y CONFIG_DM_MMC=y +CONFIG_MMC_HS400_SUPPORT=y CONFIG_FSL_ESDHC=y CONFIG_MTD=y CONFIG_DM_SPI_FLASH=y diff --git a/configs/lx2162aqds_tfa_verified_boot_defconfig b/configs/lx2162aqds_tfa_verified_boot_defconfig index 5d4ad47..4008412 100644 --- a/configs/lx2162aqds_tfa_verified_boot_defconfig +++ b/configs/lx2162aqds_tfa_verified_boot_defconfig @@ -44,6 +44,7 @@ CONFIG_DM=y CONFIG_SATA_CEVA=y CONFIG_FSL_CAAM=y CONFIG_DM_MMC=y +ONFIG_MMC_HS400_SUPPORT=y CONFIG_FSL_ESDHC=y CONFIG_MTD=y CONFIG_DM_SPI_FLASH=y
[v4, 11/11] configs: lx2160ardb: enable eMMC HS400 mode support
Enable eMMC HS400 mode support on LX2160ARDB. Signed-off-by: Yangbo Lu --- Changes for v2: - None. Changes for v3: - None. Changes for v4: - None. --- configs/lx2160ardb_tfa_SECURE_BOOT_defconfig | 1 + configs/lx2160ardb_tfa_defconfig | 1 + configs/lx2160ardb_tfa_stmm_defconfig| 1 + 3 files changed, 3 insertions(+) diff --git a/configs/lx2160ardb_tfa_SECURE_BOOT_defconfig b/configs/lx2160ardb_tfa_SECURE_BOOT_defconfig index 5e30890..159ae9d 100644 --- a/configs/lx2160ardb_tfa_SECURE_BOOT_defconfig +++ b/configs/lx2160ardb_tfa_SECURE_BOOT_defconfig @@ -41,6 +41,7 @@ CONFIG_DM_I2C=y CONFIG_I2C_SET_DEFAULT_BUS_NUM=y CONFIG_I2C_DEFAULT_BUS_NUMBER=0 CONFIG_DM_MMC=y +CONFIG_MMC_HS400_SUPPORT=y CONFIG_FSL_ESDHC=y CONFIG_MTD=y CONFIG_DM_SPI_FLASH=y diff --git a/configs/lx2160ardb_tfa_defconfig b/configs/lx2160ardb_tfa_defconfig index 7021223..8a4e6ef 100644 --- a/configs/lx2160ardb_tfa_defconfig +++ b/configs/lx2160ardb_tfa_defconfig @@ -48,6 +48,7 @@ CONFIG_DM_I2C=y CONFIG_I2C_SET_DEFAULT_BUS_NUM=y CONFIG_I2C_DEFAULT_BUS_NUMBER=0 CONFIG_DM_MMC=y +CONFIG_MMC_HS400_SUPPORT=y CONFIG_FSL_ESDHC=y CONFIG_MTD=y CONFIG_DM_SPI_FLASH=y diff --git a/configs/lx2160ardb_tfa_stmm_defconfig b/configs/lx2160ardb_tfa_stmm_defconfig index b0dc3c0..bd9c1e9 100644 --- a/configs/lx2160ardb_tfa_stmm_defconfig +++ b/configs/lx2160ardb_tfa_stmm_defconfig @@ -49,6 +49,7 @@ CONFIG_DM_I2C=y CONFIG_I2C_SET_DEFAULT_BUS_NUM=y CONFIG_I2C_DEFAULT_BUS_NUMBER=0 CONFIG_DM_MMC=y +CONFIG_MMC_HS400_SUPPORT=y CONFIG_SUPPORT_EMMC_RPMB=y CONFIG_FSL_ESDHC=y CONFIG_MTD=y -- 2.7.4
[v4, 07/11] mmc: fsl_esdhc: support eMMC HS400 mode
The process for eMMC HS400 mode for eSDHC is, 1. Perform the Tuning Process at the HS400 target operating frequency. Latched the clock division value. 2. if read transaction, then set the SDTIMNGCTL[FLW_CTL_BG]. 3. Switch to High Speed mode and then set the card clock frequency to a value not greater than 52Mhz 4. Clear TBCTL[TB_EN],tuning block enable bit. 5. Change to 8 bit DDR Mode 6. Switch the card to HS400 mode. 7. Set TBCTL[TB_EN], tuning block enable bit. 8. Clear SYSCTL[SDCLKEN] 9. Wait for PRSSTAT[SDSTB] to be set 10. Change the clock division to latched value.Set TBCTL[HS 400 mode] and Set SDCLKCTL[CMD_CLK_CTRL] 11. Set SYSCTL[SDCLKEN] 12. Wait for PRSSTAT[SDSTB] to be set 13. Set DLLCFG0[DLL_ENABLE] and DLLCFG0[DLL_FREQ_SEL]. 14. Wait for delay chain to lock. 15. Set TBCTL[HS400_WNDW_ADJUST] 16. Again clear SYSCTL[SDCLKEN] 17. Wait for PRSSTAT[SDSTB] to be set 18. Set ESDHCCTL[FAF] 19. Wait for ESDHCCTL[FAF] to be cleared 20. Set SYSCTL[SDCLKEN] 21. Wait for PRSSTAT[SDSTB] to be set. Signed-off-by: Yangbo Lu --- Changes for v2: - None. Changes for v3: - Added HS400 exit code for downgrade. Changes for v4: - None. --- drivers/mmc/fsl_esdhc.c | 120 ++-- include/fsl_esdhc.h | 12 + 2 files changed, 98 insertions(+), 34 deletions(-) diff --git a/drivers/mmc/fsl_esdhc.c b/drivers/mmc/fsl_esdhc.c index e7db55d..c53751d 100644 --- a/drivers/mmc/fsl_esdhc.c +++ b/drivers/mmc/fsl_esdhc.c @@ -62,7 +62,12 @@ struct fsl_esdhc { uinthostcapblt2;/* Host controller capabilities register 2 */ charreserved6[8]; /* reserved */ uinttbctl; /* Tuning block control register */ - charreserved7[744]; /* reserved */ + charreserved7[32]; /* reserved */ + uintsdclkctl; /* SD clock control register */ + uintsdtimingctl;/* SD timing control register */ + charreserved8[20]; /* reserved */ + uintdllcfg0;/* DLL config 0 register */ + charreserved9[680]; /* reserved */ uintesdhcctl; /* eSDHC control register */ }; @@ -568,16 +573,80 @@ static void esdhc_clock_control(struct fsl_esdhc_priv *priv, bool enable) } } +static void esdhc_flush_async_fifo(struct fsl_esdhc_priv *priv) +{ + struct fsl_esdhc *regs = priv->esdhc_regs; + u32 time_out; + + esdhc_setbits32(>esdhcctl, ESDHCCTL_FAF); + + time_out = 20; + while (esdhc_read32(>esdhcctl) & ESDHCCTL_FAF) { + if (time_out == 0) { + printf("fsl_esdhc: Flush asynchronous FIFO timeout.\n"); + break; + } + time_out--; + mdelay(1); + } +} + +static void esdhc_tuning_block_enable(struct fsl_esdhc_priv *priv, + bool en) +{ + struct fsl_esdhc *regs = priv->esdhc_regs; + + esdhc_clock_control(priv, false); + esdhc_flush_async_fifo(priv); + if (en) + esdhc_setbits32(>tbctl, TBCTL_TB_EN); + else + esdhc_clrbits32(>tbctl, TBCTL_TB_EN); + esdhc_clock_control(priv, true); +} + +static void esdhc_exit_hs400(struct fsl_esdhc_priv *priv) +{ + struct fsl_esdhc *regs = priv->esdhc_regs; + + esdhc_clrbits32(>sdtimingctl, FLW_CTL_BG); + esdhc_clrbits32(>sdclkctl, CMD_CLK_CTL); + + esdhc_clock_control(priv, false); + esdhc_clrbits32(>tbctl, HS400_MODE); + esdhc_clock_control(priv, true); + + esdhc_clrbits32(>dllcfg0, DLL_FREQ_SEL | DLL_ENABLE); + esdhc_clrbits32(>tbctl, HS400_WNDW_ADJUST); + + esdhc_tuning_block_enable(priv, false); +} + static void esdhc_set_timing(struct fsl_esdhc_priv *priv, enum bus_mode mode) { struct fsl_esdhc *regs = priv->esdhc_regs; + /* Exit HS400 mode before setting any other mode */ + if (esdhc_read32(>tbctl) & HS400_MODE && + mode != MMC_HS_400) + esdhc_exit_hs400(priv); + esdhc_clock_control(priv, false); if (mode == MMC_HS_200) esdhc_clrsetbits32(>autoc12err, UHSM_MASK, UHSM_SDR104_HS200); + if (mode == MMC_HS_400) { + esdhc_setbits32(>tbctl, HS400_MODE); + esdhc_setbits32(>sdclkctl, CMD_CLK_CTL); + esdhc_clock_control(priv, true); + esdhc_setbits32(>dllcfg0, DLL_ENABLE | DLL_FREQ_SEL); + esdhc_setbits32(>tbctl, HS400_WNDW_ADJUST); + + esdhc_clock_control(priv, false); + esdhc_flush_async_fifo(priv); + } esdhc_clock_control(priv, true); } @@ -592,6 +661,9 @@ static int esdhc_set_ios_common(struct fsl_esdhc_priv *priv, struct mmc *mmc) esdhc_clock_control(priv, true); } + i
[v4, 08/11] mmc: fsl_esdhc: fix mmc->clock with actual clock
Fix mmc->clock with actual clock which is divided by the controller, and record it with priv->clock which was removed accidentally. Signed-off-by: Yangbo Lu --- Changes for v2: - Added this patch. Changes for v3: - None. Changes for v4: - None. --- drivers/mmc/fsl_esdhc.c | 3 +++ 1 file changed, 3 insertions(+) diff --git a/drivers/mmc/fsl_esdhc.c b/drivers/mmc/fsl_esdhc.c index c53751d..ce87416 100644 --- a/drivers/mmc/fsl_esdhc.c +++ b/drivers/mmc/fsl_esdhc.c @@ -523,6 +523,9 @@ static void set_sysctl(struct fsl_esdhc_priv *priv, struct mmc *mmc, uint clock) while (sdhc_clk / (div * pre_div) > clock && div < 16) div++; + mmc->clock = sdhc_clk / pre_div / div; + priv->clock = mmc->clock; + pre_div >>= 1; div -= 1; -- 2.7.4
[v4, 10/11] arm: dts: lx2160ardb: support eMMC HS400 mode
Add properties related to eMMC HS400 mode. mmc-hs400-1_8v; bus-width = <8>; They had been already in kernel dts file since the first lx2160ardb dts patch. b068890 arm64: dts: add LX2160ARDB board support Signed-off-by: Yangbo Lu --- Changes for v2: - None. Changes for v3: - Explained more in commit message. Changes for v4: - None. --- arch/arm/dts/fsl-lx2160a-rdb.dts | 2 ++ 1 file changed, 2 insertions(+) diff --git a/arch/arm/dts/fsl-lx2160a-rdb.dts b/arch/arm/dts/fsl-lx2160a-rdb.dts index d787778..5fbdd90 100644 --- a/arch/arm/dts/fsl-lx2160a-rdb.dts +++ b/arch/arm/dts/fsl-lx2160a-rdb.dts @@ -80,6 +80,8 @@ { status = "okay"; mmc-hs200-1_8v; + mmc-hs400-1_8v; + bus-width = <8>; }; { -- 2.7.4
[v4, 05/11] mmc: add a hs400_tuning flag
Some controllers may have difference between HS200 tuning and HS400 tuning, such as different registers setting, different procedure, or different errata. This patch is to add a hs400_tuning flag to identify the tuning for HS400 mode. Signed-off-by: Yangbo Lu --- Changes for v2: - None. Changes for v3: - Explained more in commit messages. Changes for v4: - None. --- drivers/mmc/mmc.c | 2 ++ include/mmc.h | 1 + 2 files changed, 3 insertions(+) diff --git a/drivers/mmc/mmc.c b/drivers/mmc/mmc.c index 0727505..b75c2bc 100644 --- a/drivers/mmc/mmc.c +++ b/drivers/mmc/mmc.c @@ -1982,7 +1982,9 @@ static int mmc_select_hs400(struct mmc *mmc) mmc_set_clock(mmc, mmc->tran_speed, false); /* execute tuning if needed */ + mmc->hs400_tuning = 1; err = mmc_execute_tuning(mmc, MMC_CMD_SEND_TUNING_BLOCK_HS200); + mmc->hs400_tuning = 0; if (err) { debug("tuning failed\n"); return err; diff --git a/include/mmc.h b/include/mmc.h index 161b8bc..2399cc2 100644 --- a/include/mmc.h +++ b/include/mmc.h @@ -707,6 +707,7 @@ struct mmc { * accessing the boot partitions */ u32 quirks; + u8 hs400_tuning; }; struct mmc_hwpart_conf { -- 2.7.4
[v4, 09/11] mmc: fsl_esdhc: fix eMMC HS400 stability issue
There was a fix-up for eMMC HS400 stability issue in Linux. Patch link: https://git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git/ commit/?id=58d0bf843b49fa99588ac9f85178bd8dfd651b53 Description: Currently only LX2160A eSDHC supports eMMC HS400. According to a large number of tests, eMMC HS400 failed to work at 150MHz, and for a few boards failed to work at 175MHz. But eMMC HS400 worked fine on 200MHz. We hadn't found the root cause but setting eSDHC_DLLCFG0[DLL_FREQ_SEL] = 0 using slow delay chain seemed to resovle this issue. Let's use this as fixup for now. Introduce the fix-up in u-boot since the issue could be reproduced in u-boot too. Signed-off-by: Yangbo Lu --- Changes for v2: - Added this patch. Changes for v3: - None. Changes for v4: - None. --- drivers/mmc/fsl_esdhc.c | 5 - 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/drivers/mmc/fsl_esdhc.c b/drivers/mmc/fsl_esdhc.c index ce87416..a6092ad 100644 --- a/drivers/mmc/fsl_esdhc.c +++ b/drivers/mmc/fsl_esdhc.c @@ -644,7 +644,10 @@ static void esdhc_set_timing(struct fsl_esdhc_priv *priv, enum bus_mode mode) esdhc_setbits32(>sdclkctl, CMD_CLK_CTL); esdhc_clock_control(priv, true); - esdhc_setbits32(>dllcfg0, DLL_ENABLE | DLL_FREQ_SEL); + if (priv->clock == 2) + esdhc_setbits32(>dllcfg0, DLL_FREQ_SEL); + + esdhc_setbits32(>dllcfg0, DLL_ENABLE); esdhc_setbits32(>tbctl, HS400_WNDW_ADJUST); esdhc_clock_control(priv, false); -- 2.7.4
[v4, 03/11] mmc: fsl_esdhc: support tuning for eMMC HS200
Support tuning process for eMMC HS200 for eSDHC. Signed-off-by: Yangbo Lu --- Changes for v2: - None. Changes for v3: - Rebased. Changes for v4: - None. --- drivers/mmc/fsl_esdhc.c | 106 ++-- include/fsl_esdhc.h | 17 ++-- 2 files changed, 116 insertions(+), 7 deletions(-) diff --git a/drivers/mmc/fsl_esdhc.c b/drivers/mmc/fsl_esdhc.c index 83feaf1..4e04c10 100644 --- a/drivers/mmc/fsl_esdhc.c +++ b/drivers/mmc/fsl_esdhc.c @@ -60,7 +60,9 @@ struct fsl_esdhc { uintdmaerrattr; /* DMA error attribute register */ charreserved5[4]; /* reserved */ uinthostcapblt2;/* Host controller capabilities register 2 */ - charreserved6[756]; /* reserved */ + charreserved6[8]; /* reserved */ + uinttbctl; /* Tuning block control register */ + charreserved7[744]; /* reserved */ uintesdhcctl; /* eSDHC control register */ }; @@ -101,7 +103,9 @@ static uint esdhc_xfertyp(struct mmc_cmd *cmd, struct mmc_data *data) if (data) { xfertyp |= XFERTYP_DPSEL; #ifndef CONFIG_SYS_FSL_ESDHC_USE_PIO - xfertyp |= XFERTYP_DMAEN; + if (cmd->cmdidx != MMC_CMD_SEND_TUNING_BLOCK && + cmd->cmdidx != MMC_CMD_SEND_TUNING_BLOCK_HS200) + xfertyp |= XFERTYP_DMAEN; #endif if (data->blocks > 1) { xfertyp |= XFERTYP_MSBSEL; @@ -380,6 +384,10 @@ static int esdhc_send_cmd_common(struct fsl_esdhc_priv *priv, struct mmc *mmc, esdhc_write32(>cmdarg, cmd->cmdarg); esdhc_write32(>xfertyp, xfertyp); + if (cmd->cmdidx == MMC_CMD_SEND_TUNING_BLOCK || + cmd->cmdidx == MMC_CMD_SEND_TUNING_BLOCK_HS200) + flags = IRQSTAT_BRR; + /* Wait for the command to complete */ start = get_timer(0); while (!(esdhc_read32(>irqstat) & flags)) { @@ -439,6 +447,11 @@ static int esdhc_send_cmd_common(struct fsl_esdhc_priv *priv, struct mmc *mmc, #ifdef CONFIG_SYS_FSL_ESDHC_USE_PIO esdhc_pio_read_write(priv, data); #else + flags = DATA_COMPLETE; + if (cmd->cmdidx == MMC_CMD_SEND_TUNING_BLOCK || + cmd->cmdidx == MMC_CMD_SEND_TUNING_BLOCK_HS200) + flags = IRQSTAT_BRR; + do { irqstat = esdhc_read32(>irqstat); @@ -451,7 +464,7 @@ static int esdhc_send_cmd_common(struct fsl_esdhc_priv *priv, struct mmc *mmc, err = -ECOMM; goto out; } - } while ((irqstat & DATA_COMPLETE) != DATA_COMPLETE); + } while ((irqstat & flags) != flags); /* * Need invalidate the dcache here again to avoid any @@ -555,6 +568,19 @@ static void esdhc_clock_control(struct fsl_esdhc_priv *priv, bool enable) } } +static void esdhc_set_timing(struct fsl_esdhc_priv *priv, enum bus_mode mode) +{ + struct fsl_esdhc *regs = priv->esdhc_regs; + + esdhc_clock_control(priv, false); + + if (mode == MMC_HS_200) + esdhc_clrsetbits32(>autoc12err, UHSM_MASK, + UHSM_SDR104_HS200); + + esdhc_clock_control(priv, true); +} + static int esdhc_set_ios_common(struct fsl_esdhc_priv *priv, struct mmc *mmc) { struct fsl_esdhc *regs = priv->esdhc_regs; @@ -570,6 +596,9 @@ static int esdhc_set_ios_common(struct fsl_esdhc_priv *priv, struct mmc *mmc) if (priv->clock != mmc->clock) set_sysctl(priv, mmc, mmc->clock); + /* Set timing */ + esdhc_set_timing(priv, mmc->selected_mode); + /* Set the bus width */ esdhc_clrbits32(>proctl, PROCTL_DTW_4 | PROCTL_DTW_8); @@ -915,6 +944,77 @@ static int fsl_esdhc_reinit(struct udevice *dev) return esdhc_init_common(priv, >mmc); } +#ifdef MMC_SUPPORTS_TUNING +static void esdhc_flush_async_fifo(struct fsl_esdhc_priv *priv) +{ + struct fsl_esdhc *regs = priv->esdhc_regs; + u32 time_out; + + esdhc_setbits32(>esdhcctl, ESDHCCTL_FAF); + + time_out = 20; + while (esdhc_read32(>esdhcctl) & ESDHCCTL_FAF) { + if (time_out == 0) { + printf("fsl_esdhc: Flush asynchronous FIFO timeout.\n"); + break; + } + time_out--; + mdelay(1); + } +} + +static void esdhc_tuning_block_enable(struct fsl_esdhc_priv *priv, + bool en) +{ + struct fsl_esdhc *regs = priv->esdhc_regs; + + esdhc_clock_control(priv, false); + esdhc_flush_async_fifo(priv); + if (en) + esdhc_setbits32(>tbctl, TBCT
[v4, 06/11] mmc: add a mmc_hs400_prepare_ddr() interface
Add a mmc_hs400_prepare_ddr() interface for controllers which needs preparation before switching to DDR mode for HS400 mode. Signed-off-by: Yangbo Lu --- Changes for v2: - None. Changes for v3: - None. Changes for v4: - Checked returning of mmc_hs400_prepare_ddr(). --- drivers/mmc/mmc-uclass.c | 15 +++ drivers/mmc/mmc.c| 4 include/mmc.h| 15 ++- 3 files changed, 33 insertions(+), 1 deletion(-) diff --git a/drivers/mmc/mmc-uclass.c b/drivers/mmc/mmc-uclass.c index b90e1ee..ec59bcd 100644 --- a/drivers/mmc/mmc-uclass.c +++ b/drivers/mmc/mmc-uclass.c @@ -142,6 +142,21 @@ int mmc_set_enhanced_strobe(struct mmc *mmc) } #endif +int dm_mmc_hs400_prepare_ddr(struct udevice *dev) +{ + struct dm_mmc_ops *ops = mmc_get_ops(dev); + + if (ops->hs400_prepare_ddr) + return ops->hs400_prepare_ddr(dev); + + return 0; +} + +int mmc_hs400_prepare_ddr(struct mmc *mmc) +{ + return dm_mmc_hs400_prepare_ddr(mmc->dev); +} + int dm_mmc_host_power_cycle(struct udevice *dev) { struct dm_mmc_ops *ops = mmc_get_ops(dev); diff --git a/drivers/mmc/mmc.c b/drivers/mmc/mmc.c index b75c2bc..8502503 100644 --- a/drivers/mmc/mmc.c +++ b/drivers/mmc/mmc.c @@ -1993,6 +1993,10 @@ static int mmc_select_hs400(struct mmc *mmc) /* Set back to HS */ mmc_set_card_speed(mmc, MMC_HS, true); + err = mmc_hs400_prepare_ddr(mmc); + if (err) + return err; + err = mmc_switch(mmc, EXT_CSD_CMD_SET_NORMAL, EXT_CSD_BUS_WIDTH, EXT_CSD_BUS_WIDTH_8 | EXT_CSD_DDR_FLAG); if (err) diff --git a/include/mmc.h b/include/mmc.h index 2399cc2..659df75 100644 --- a/include/mmc.h +++ b/include/mmc.h @@ -513,6 +513,14 @@ struct dm_mmc_ops { * @return maximum number of blocks for this transfer */ int (*get_b_max)(struct udevice *dev, void *dst, lbaint_t blkcnt); + + /** +* hs400_prepare_ddr - prepare to switch to DDR mode +* +* @dev:Device to check +* @return 0 if success, -ve on error +*/ + int (*hs400_prepare_ddr)(struct udevice *dev); }; #define mmc_get_ops(dev)((struct dm_mmc_ops *)(dev)->driver->ops) @@ -540,7 +548,7 @@ int mmc_host_power_cycle(struct mmc *mmc); int mmc_deferred_probe(struct mmc *mmc); int mmc_reinit(struct mmc *mmc); int mmc_get_b_max(struct mmc *mmc, void *dst, lbaint_t blkcnt); - +int mmc_hs400_prepare_ddr(struct mmc *mmc); #else struct mmc_ops { int (*send_cmd)(struct mmc *mmc, @@ -552,6 +560,11 @@ struct mmc_ops { int (*host_power_cycle)(struct mmc *mmc); int (*get_b_max)(struct mmc *mmc, void *dst, lbaint_t blkcnt); }; + +static inline int mmc_hs400_prepare_ddr(struct mmc *mmc) +{ + return 0; +} #endif struct mmc_config { -- 2.7.4
[v4, 04/11] mmc: fsl_esdhc: clean TBCTL[TB_EN] manually during init
Clean TBCTL[TB_EN] manually during init since it is not able to be reset by reset all operation. Signed-off-by: Yangbo Lu --- Changes for v2: - None. Changes for v3: - None. Changes for v4: - None. --- drivers/mmc/fsl_esdhc.c | 3 +++ 1 file changed, 3 insertions(+) diff --git a/drivers/mmc/fsl_esdhc.c b/drivers/mmc/fsl_esdhc.c index 4e04c10..e7db55d 100644 --- a/drivers/mmc/fsl_esdhc.c +++ b/drivers/mmc/fsl_esdhc.c @@ -637,6 +637,9 @@ static int esdhc_init_common(struct fsl_esdhc_priv *priv, struct mmc *mmc) return -ETIMEDOUT; } + /* Clean TBCTL[TB_EN] which is not able to be reset by reset all */ + esdhc_clrbits32(>tbctl, TBCTL_TB_EN); + esdhc_enable_cache_snooping(regs); esdhc_setbits32(>sysctl, SYSCTL_HCKEN | SYSCTL_IPGEN); -- 2.7.4
[v4, 01/11] mmc: add a reinit() API
For DM_MMC, the controller re-initialization is needed to clear old configuration for mmc rescan. Signed-off-by: Yangbo Lu Reviewed-by: Jaehoon Chung --- Changes for v2: - None. Changes for v3: - None. Changes for v4: - Added Reviewed-by. --- drivers/mmc/mmc-uclass.c | 15 +++ drivers/mmc/mmc.c| 8 ++-- include/mmc.h| 10 ++ 3 files changed, 31 insertions(+), 2 deletions(-) diff --git a/drivers/mmc/mmc-uclass.c b/drivers/mmc/mmc-uclass.c index 90690c8..b90e1ee 100644 --- a/drivers/mmc/mmc-uclass.c +++ b/drivers/mmc/mmc-uclass.c @@ -171,6 +171,21 @@ int mmc_deferred_probe(struct mmc *mmc) return dm_mmc_deferred_probe(mmc->dev); } +int dm_mmc_reinit(struct udevice *dev) +{ + struct dm_mmc_ops *ops = mmc_get_ops(dev); + + if (ops->reinit) + return ops->reinit(dev); + + return 0; +} + +int mmc_reinit(struct mmc *mmc) +{ + return dm_mmc_reinit(mmc->dev); +} + int mmc_of_parse(struct udevice *dev, struct mmc_config *cfg) { int val; diff --git a/drivers/mmc/mmc.c b/drivers/mmc/mmc.c index d79cdef..0727505 100644 --- a/drivers/mmc/mmc.c +++ b/drivers/mmc/mmc.c @@ -2816,13 +2816,17 @@ int mmc_get_op_cond(struct mmc *mmc) return err; #if CONFIG_IS_ENABLED(DM_MMC) - /* The device has already been probed ready for use */ + /* +* Re-initialization is needed to clear old configuration for +* mmc rescan. +*/ + err = mmc_reinit(mmc); #else /* made sure it's not NULL earlier */ err = mmc->cfg->ops->init(mmc); +#endif if (err) return err; -#endif mmc->ddr_mode = 0; retry: diff --git a/include/mmc.h b/include/mmc.h index 8256219..161b8bc 100644 --- a/include/mmc.h +++ b/include/mmc.h @@ -422,6 +422,14 @@ struct dm_mmc_ops { */ int (*deferred_probe)(struct udevice *dev); /** +* reinit() - Re-initialization to clear old configuration for +* mmc rescan. +* +* @dev:Device to reinit +* @return 0 if Ok, -ve if error +*/ + int (*reinit)(struct udevice *dev); + /** * send_cmd() - Send a command to the MMC device * * @dev:Device to receive the command @@ -518,6 +526,7 @@ int dm_mmc_execute_tuning(struct udevice *dev, uint opcode); int dm_mmc_wait_dat0(struct udevice *dev, int state, int timeout_us); int dm_mmc_host_power_cycle(struct udevice *dev); int dm_mmc_deferred_probe(struct udevice *dev); +int dm_mmc_reinit(struct udevice *dev); int dm_mmc_get_b_max(struct udevice *dev, void *dst, lbaint_t blkcnt); /* Transition functions for compatibility */ @@ -529,6 +538,7 @@ int mmc_wait_dat0(struct mmc *mmc, int state, int timeout_us); int mmc_set_enhanced_strobe(struct mmc *mmc); int mmc_host_power_cycle(struct mmc *mmc); int mmc_deferred_probe(struct mmc *mmc); +int mmc_reinit(struct mmc *mmc); int mmc_get_b_max(struct mmc *mmc, void *dst, lbaint_t blkcnt); #else -- 2.7.4
[v4, 02/11] mmc: fsl_esdhc: add a reinit() callback
Add a reinit() callback for mmc rescan. Signed-off-by: Yangbo Lu Reviewed-by: Jaehoon Chung --- Changes for v2: - None. Changes for v3: - None. Changes for v4: - Added Reviewed-by. --- drivers/mmc/fsl_esdhc.c | 9 + 1 file changed, 9 insertions(+) diff --git a/drivers/mmc/fsl_esdhc.c b/drivers/mmc/fsl_esdhc.c index de9fe01..83feaf1 100644 --- a/drivers/mmc/fsl_esdhc.c +++ b/drivers/mmc/fsl_esdhc.c @@ -907,6 +907,14 @@ static int fsl_esdhc_set_ios(struct udevice *dev) return esdhc_set_ios_common(priv, >mmc); } +static int fsl_esdhc_reinit(struct udevice *dev) +{ + struct fsl_esdhc_plat *plat = dev_get_platdata(dev); + struct fsl_esdhc_priv *priv = dev_get_priv(dev); + + return esdhc_init_common(priv, >mmc); +} + static const struct dm_mmc_ops fsl_esdhc_ops = { .get_cd = fsl_esdhc_get_cd, .send_cmd = fsl_esdhc_send_cmd, @@ -914,6 +922,7 @@ static const struct dm_mmc_ops fsl_esdhc_ops = { #ifdef MMC_SUPPORTS_TUNING .execute_tuning = fsl_esdhc_execute_tuning, #endif + .reinit = fsl_esdhc_reinit, }; static const struct udevice_id fsl_esdhc_ids[] = { -- 2.7.4
[v4, 00/11] mmc: fsl_esdhc: support eMMC HS200/HS400 modes
This patch-set is to support eMMC HS200 and HS400 speed modes for eSDHC, and enable them on LX2160ARDB board. CI build link https://travis-ci.org/github/yangbolu1991/u-boot-test/builds/720875619 Changes for v2: - Added two patches to fix stability issue. Changes for v3: - Explained more in commit messages. - Added HS400 exit code for downgrade. Changes for v4: - Checked returning of mmc_hs400_prepare_ddr(). - Added Reviewed-by. - Rebased. Yangbo Lu (11): mmc: add a reinit() API mmc: fsl_esdhc: add a reinit() callback mmc: fsl_esdhc: support tuning for eMMC HS200 mmc: fsl_esdhc: clean TBCTL[TB_EN] manually during init mmc: add a hs400_tuning flag mmc: add a mmc_hs400_prepare_ddr() interface mmc: fsl_esdhc: support eMMC HS400 mode mmc: fsl_esdhc: fix mmc->clock with actual clock mmc: fsl_esdhc: fix eMMC HS400 stability issue arm: dts: lx2160ardb: support eMMC HS400 mode configs: lx2160ardb: enable eMMC HS400 mode support arch/arm/dts/fsl-lx2160a-rdb.dts | 2 + configs/lx2160ardb_tfa_SECURE_BOOT_defconfig | 1 + configs/lx2160ardb_tfa_defconfig | 1 + configs/lx2160ardb_tfa_stmm_defconfig| 1 + drivers/mmc/fsl_esdhc.c | 176 ++- drivers/mmc/mmc-uclass.c | 30 + drivers/mmc/mmc.c| 14 ++- include/fsl_esdhc.h | 29 - include/mmc.h| 26 +++- 9 files changed, 270 insertions(+), 10 deletions(-) -- 2.7.4
[v3, 11/11] configs: lx2160ardb: enable eMMC HS400 mode support
Enable eMMC HS400 mode support on LX2160ARDB. Signed-off-by: Yangbo Lu --- Changes for v2: - None. Changes for v3: - None. --- configs/lx2160ardb_tfa_SECURE_BOOT_defconfig | 1 + configs/lx2160ardb_tfa_defconfig | 1 + configs/lx2160ardb_tfa_stmm_defconfig| 1 + 3 files changed, 3 insertions(+) diff --git a/configs/lx2160ardb_tfa_SECURE_BOOT_defconfig b/configs/lx2160ardb_tfa_SECURE_BOOT_defconfig index 12e224f..6c65853 100644 --- a/configs/lx2160ardb_tfa_SECURE_BOOT_defconfig +++ b/configs/lx2160ardb_tfa_SECURE_BOOT_defconfig @@ -40,6 +40,7 @@ CONFIG_DM_I2C=y CONFIG_I2C_SET_DEFAULT_BUS_NUM=y CONFIG_I2C_DEFAULT_BUS_NUMBER=0 CONFIG_DM_MMC=y +CONFIG_MMC_HS400_SUPPORT=y CONFIG_FSL_ESDHC=y CONFIG_MTD=y CONFIG_DM_SPI_FLASH=y diff --git a/configs/lx2160ardb_tfa_defconfig b/configs/lx2160ardb_tfa_defconfig index a5c78d2..a5c60c8 100644 --- a/configs/lx2160ardb_tfa_defconfig +++ b/configs/lx2160ardb_tfa_defconfig @@ -46,6 +46,7 @@ CONFIG_DM_I2C=y CONFIG_I2C_SET_DEFAULT_BUS_NUM=y CONFIG_I2C_DEFAULT_BUS_NUMBER=0 CONFIG_DM_MMC=y +CONFIG_MMC_HS400_SUPPORT=y CONFIG_FSL_ESDHC=y CONFIG_MTD=y CONFIG_DM_SPI_FLASH=y diff --git a/configs/lx2160ardb_tfa_stmm_defconfig b/configs/lx2160ardb_tfa_stmm_defconfig index e97c9b0..869d4e2 100644 --- a/configs/lx2160ardb_tfa_stmm_defconfig +++ b/configs/lx2160ardb_tfa_stmm_defconfig @@ -48,6 +48,7 @@ CONFIG_DM_I2C=y CONFIG_I2C_SET_DEFAULT_BUS_NUM=y CONFIG_I2C_DEFAULT_BUS_NUMBER=0 CONFIG_DM_MMC=y +CONFIG_MMC_HS400_SUPPORT=y CONFIG_SUPPORT_EMMC_RPMB=y CONFIG_FSL_ESDHC=y CONFIG_MTD=y -- 2.7.4
[v3, 08/11] mmc: fsl_esdhc: fix mmc->clock with actual clock
Fix mmc->clock with actual clock which is divided by the controller, and record it with priv->clock which was removed accidentally. Signed-off-by: Yangbo Lu --- Changes for v2: - Added this patch. Changes for v3: - None. --- drivers/mmc/fsl_esdhc.c | 3 +++ 1 file changed, 3 insertions(+) diff --git a/drivers/mmc/fsl_esdhc.c b/drivers/mmc/fsl_esdhc.c index f2ab75c..716f53e 100644 --- a/drivers/mmc/fsl_esdhc.c +++ b/drivers/mmc/fsl_esdhc.c @@ -523,6 +523,9 @@ static void set_sysctl(struct fsl_esdhc_priv *priv, struct mmc *mmc, uint clock) while (sdhc_clk / (div * pre_div) > clock && div < 16) div++; + mmc->clock = sdhc_clk / pre_div / div; + priv->clock = mmc->clock; + pre_div >>= 1; div -= 1; -- 2.7.4
[v3, 07/11] mmc: fsl_esdhc: support eMMC HS400 mode
The process for eMMC HS400 mode for eSDHC is, 1. Perform the Tuning Process at the HS400 target operating frequency. Latched the clock division value. 2. if read transaction, then set the SDTIMNGCTL[FLW_CTL_BG]. 3. Switch to High Speed mode and then set the card clock frequency to a value not greater than 52Mhz 4. Clear TBCTL[TB_EN],tuning block enable bit. 5. Change to 8 bit DDR Mode 6. Switch the card to HS400 mode. 7. Set TBCTL[TB_EN], tuning block enable bit. 8. Clear SYSCTL[SDCLKEN] 9. Wait for PRSSTAT[SDSTB] to be set 10. Change the clock division to latched value.Set TBCTL[HS 400 mode] and Set SDCLKCTL[CMD_CLK_CTRL] 11. Set SYSCTL[SDCLKEN] 12. Wait for PRSSTAT[SDSTB] to be set 13. Set DLLCFG0[DLL_ENABLE] and DLLCFG0[DLL_FREQ_SEL]. 14. Wait for delay chain to lock. 15. Set TBCTL[HS400_WNDW_ADJUST] 16. Again clear SYSCTL[SDCLKEN] 17. Wait for PRSSTAT[SDSTB] to be set 18. Set ESDHCCTL[FAF] 19. Wait for ESDHCCTL[FAF] to be cleared 20. Set SYSCTL[SDCLKEN] 21. Wait for PRSSTAT[SDSTB] to be set. Signed-off-by: Yangbo Lu --- Changes for v2: - None. Changes for v3: - Added HS400 exit code for downgrade. --- drivers/mmc/fsl_esdhc.c | 120 ++-- include/fsl_esdhc.h | 12 + 2 files changed, 98 insertions(+), 34 deletions(-) diff --git a/drivers/mmc/fsl_esdhc.c b/drivers/mmc/fsl_esdhc.c index c52ab0f..f2ab75c 100644 --- a/drivers/mmc/fsl_esdhc.c +++ b/drivers/mmc/fsl_esdhc.c @@ -62,7 +62,12 @@ struct fsl_esdhc { uinthostcapblt2;/* Host controller capabilities register 2 */ charreserved6[8]; /* reserved */ uinttbctl; /* Tuning block control register */ - charreserved7[744]; /* reserved */ + charreserved7[32]; /* reserved */ + uintsdclkctl; /* SD clock control register */ + uintsdtimingctl;/* SD timing control register */ + charreserved8[20]; /* reserved */ + uintdllcfg0;/* DLL config 0 register */ + charreserved9[680]; /* reserved */ uintesdhcctl; /* eSDHC control register */ }; @@ -568,16 +573,80 @@ static void esdhc_clock_control(struct fsl_esdhc_priv *priv, bool enable) } } +static void esdhc_flush_async_fifo(struct fsl_esdhc_priv *priv) +{ + struct fsl_esdhc *regs = priv->esdhc_regs; + u32 time_out; + + esdhc_setbits32(>esdhcctl, ESDHCCTL_FAF); + + time_out = 20; + while (esdhc_read32(>esdhcctl) & ESDHCCTL_FAF) { + if (time_out == 0) { + printf("fsl_esdhc: Flush asynchronous FIFO timeout.\n"); + break; + } + time_out--; + mdelay(1); + } +} + +static void esdhc_tuning_block_enable(struct fsl_esdhc_priv *priv, + bool en) +{ + struct fsl_esdhc *regs = priv->esdhc_regs; + + esdhc_clock_control(priv, false); + esdhc_flush_async_fifo(priv); + if (en) + esdhc_setbits32(>tbctl, TBCTL_TB_EN); + else + esdhc_clrbits32(>tbctl, TBCTL_TB_EN); + esdhc_clock_control(priv, true); +} + +static void esdhc_exit_hs400(struct fsl_esdhc_priv *priv) +{ + struct fsl_esdhc *regs = priv->esdhc_regs; + + esdhc_clrbits32(>sdtimingctl, FLW_CTL_BG); + esdhc_clrbits32(>sdclkctl, CMD_CLK_CTL); + + esdhc_clock_control(priv, false); + esdhc_clrbits32(>tbctl, HS400_MODE); + esdhc_clock_control(priv, true); + + esdhc_clrbits32(>dllcfg0, DLL_FREQ_SEL | DLL_ENABLE); + esdhc_clrbits32(>tbctl, HS400_WNDW_ADJUST); + + esdhc_tuning_block_enable(priv, false); +} + static void esdhc_set_timing(struct fsl_esdhc_priv *priv, enum bus_mode mode) { struct fsl_esdhc *regs = priv->esdhc_regs; + /* Exit HS400 mode before setting any other mode */ + if (esdhc_read32(>tbctl) & HS400_MODE && + mode != MMC_HS_400) + esdhc_exit_hs400(priv); + esdhc_clock_control(priv, false); if (mode == MMC_HS_200) esdhc_clrsetbits32(>autoc12err, UHSM_MASK, UHSM_SDR104_HS200); + if (mode == MMC_HS_400) { + esdhc_setbits32(>tbctl, HS400_MODE); + esdhc_setbits32(>sdclkctl, CMD_CLK_CTL); + esdhc_clock_control(priv, true); + esdhc_setbits32(>dllcfg0, DLL_ENABLE | DLL_FREQ_SEL); + esdhc_setbits32(>tbctl, HS400_WNDW_ADJUST); + + esdhc_clock_control(priv, false); + esdhc_flush_async_fifo(priv); + } esdhc_clock_control(priv, true); } @@ -592,6 +661,9 @@ static int esdhc_set_ios_common(struct fsl_esdhc_priv *priv, struct mmc *mmc) esdhc_clock_control(priv, true); } + if (mmc->selected_mode == MMC_HS_
[v3, 09/11] mmc: fsl_esdhc: fix eMMC HS400 stability issue
There was a fix-up for eMMC HS400 stability issue in Linux. Patch link: https://git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git/ commit/?id=58d0bf843b49fa99588ac9f85178bd8dfd651b53 Description: Currently only LX2160A eSDHC supports eMMC HS400. According to a large number of tests, eMMC HS400 failed to work at 150MHz, and for a few boards failed to work at 175MHz. But eMMC HS400 worked fine on 200MHz. We hadn't found the root cause but setting eSDHC_DLLCFG0[DLL_FREQ_SEL] = 0 using slow delay chain seemed to resovle this issue. Let's use this as fixup for now. Introduce the fix-up in u-boot since the issue could be reproduced in u-boot too. Signed-off-by: Yangbo Lu --- Changes for v2: - Added this patch. Changes for v3: - None. --- drivers/mmc/fsl_esdhc.c | 5 - 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/drivers/mmc/fsl_esdhc.c b/drivers/mmc/fsl_esdhc.c index 716f53e..20e3ff9 100644 --- a/drivers/mmc/fsl_esdhc.c +++ b/drivers/mmc/fsl_esdhc.c @@ -644,7 +644,10 @@ static void esdhc_set_timing(struct fsl_esdhc_priv *priv, enum bus_mode mode) esdhc_setbits32(>sdclkctl, CMD_CLK_CTL); esdhc_clock_control(priv, true); - esdhc_setbits32(>dllcfg0, DLL_ENABLE | DLL_FREQ_SEL); + if (priv->clock == 2) + esdhc_setbits32(>dllcfg0, DLL_FREQ_SEL); + + esdhc_setbits32(>dllcfg0, DLL_ENABLE); esdhc_setbits32(>tbctl, HS400_WNDW_ADJUST); esdhc_clock_control(priv, false); -- 2.7.4
[v3, 06/11] mmc: add a mmc_hs400_prepare_ddr() interface
Add a mmc_hs400_prepare_ddr() interface for controllers which needs preparation before switching to DDR mode for HS400 mode. Signed-off-by: Yangbo Lu --- Changes for v2: - None. Changes for v3: - None. --- drivers/mmc/mmc-uclass.c | 15 +++ drivers/mmc/mmc.c| 2 ++ include/mmc.h| 15 ++- 3 files changed, 31 insertions(+), 1 deletion(-) diff --git a/drivers/mmc/mmc-uclass.c b/drivers/mmc/mmc-uclass.c index b9f0880..240b205 100644 --- a/drivers/mmc/mmc-uclass.c +++ b/drivers/mmc/mmc-uclass.c @@ -141,6 +141,21 @@ int mmc_set_enhanced_strobe(struct mmc *mmc) } #endif +int dm_mmc_hs400_prepare_ddr(struct udevice *dev) +{ + struct dm_mmc_ops *ops = mmc_get_ops(dev); + + if (ops->hs400_prepare_ddr) + return ops->hs400_prepare_ddr(dev); + + return 0; +} + +int mmc_hs400_prepare_ddr(struct mmc *mmc) +{ + return dm_mmc_hs400_prepare_ddr(mmc->dev); +} + int dm_mmc_host_power_cycle(struct udevice *dev) { struct dm_mmc_ops *ops = mmc_get_ops(dev); diff --git a/drivers/mmc/mmc.c b/drivers/mmc/mmc.c index f020a8e..935fa72 100644 --- a/drivers/mmc/mmc.c +++ b/drivers/mmc/mmc.c @@ -1992,6 +1992,8 @@ static int mmc_select_hs400(struct mmc *mmc) /* Set back to HS */ mmc_set_card_speed(mmc, MMC_HS, true); + mmc_hs400_prepare_ddr(mmc); + err = mmc_switch(mmc, EXT_CSD_CMD_SET_NORMAL, EXT_CSD_BUS_WIDTH, EXT_CSD_BUS_WIDTH_8 | EXT_CSD_DDR_FLAG); if (err) diff --git a/include/mmc.h b/include/mmc.h index 2399cc2..659df75 100644 --- a/include/mmc.h +++ b/include/mmc.h @@ -513,6 +513,14 @@ struct dm_mmc_ops { * @return maximum number of blocks for this transfer */ int (*get_b_max)(struct udevice *dev, void *dst, lbaint_t blkcnt); + + /** +* hs400_prepare_ddr - prepare to switch to DDR mode +* +* @dev:Device to check +* @return 0 if success, -ve on error +*/ + int (*hs400_prepare_ddr)(struct udevice *dev); }; #define mmc_get_ops(dev)((struct dm_mmc_ops *)(dev)->driver->ops) @@ -540,7 +548,7 @@ int mmc_host_power_cycle(struct mmc *mmc); int mmc_deferred_probe(struct mmc *mmc); int mmc_reinit(struct mmc *mmc); int mmc_get_b_max(struct mmc *mmc, void *dst, lbaint_t blkcnt); - +int mmc_hs400_prepare_ddr(struct mmc *mmc); #else struct mmc_ops { int (*send_cmd)(struct mmc *mmc, @@ -552,6 +560,11 @@ struct mmc_ops { int (*host_power_cycle)(struct mmc *mmc); int (*get_b_max)(struct mmc *mmc, void *dst, lbaint_t blkcnt); }; + +static inline int mmc_hs400_prepare_ddr(struct mmc *mmc) +{ + return 0; +} #endif struct mmc_config { -- 2.7.4
[v3, 10/11] arm: dts: lx2160ardb: support eMMC HS400 mode
Add properties related to eMMC HS400 mode. mmc-hs400-1_8v; bus-width = <8>; They had been already in kernel dts file since the first lx2160ardb dts patch. b068890 arm64: dts: add LX2160ARDB board support Signed-off-by: Yangbo Lu --- Changes for v2: - None. Changes for v3: - Explained more in commit message. --- arch/arm/dts/fsl-lx2160a-rdb.dts | 2 ++ 1 file changed, 2 insertions(+) diff --git a/arch/arm/dts/fsl-lx2160a-rdb.dts b/arch/arm/dts/fsl-lx2160a-rdb.dts index d787778..5fbdd90 100644 --- a/arch/arm/dts/fsl-lx2160a-rdb.dts +++ b/arch/arm/dts/fsl-lx2160a-rdb.dts @@ -80,6 +80,8 @@ { status = "okay"; mmc-hs200-1_8v; + mmc-hs400-1_8v; + bus-width = <8>; }; { -- 2.7.4
[v3, 05/11] mmc: add a hs400_tuning flag
Some controllers may have difference between HS200 tuning and HS400 tuning, such as different registers setting, different procedure, or different errata. This patch is to add a hs400_tuning flag to identify the tuning for HS400 mode. Signed-off-by: Yangbo Lu --- Changes for v2: - None. Changes for v3: - Explained more in commit messages. --- drivers/mmc/mmc.c | 2 ++ include/mmc.h | 1 + 2 files changed, 3 insertions(+) diff --git a/drivers/mmc/mmc.c b/drivers/mmc/mmc.c index a4c6153..f020a8e 100644 --- a/drivers/mmc/mmc.c +++ b/drivers/mmc/mmc.c @@ -1981,7 +1981,9 @@ static int mmc_select_hs400(struct mmc *mmc) mmc_set_clock(mmc, mmc->tran_speed, false); /* execute tuning if needed */ + mmc->hs400_tuning = 1; err = mmc_execute_tuning(mmc, MMC_CMD_SEND_TUNING_BLOCK_HS200); + mmc->hs400_tuning = 0; if (err) { debug("tuning failed\n"); return err; diff --git a/include/mmc.h b/include/mmc.h index 161b8bc..2399cc2 100644 --- a/include/mmc.h +++ b/include/mmc.h @@ -707,6 +707,7 @@ struct mmc { * accessing the boot partitions */ u32 quirks; + u8 hs400_tuning; }; struct mmc_hwpart_conf { -- 2.7.4
[v3, 04/11] mmc: fsl_esdhc: clean TBCTL[TB_EN] manually during init
Clean TBCTL[TB_EN] manually during init since it is not able to be reset by reset all operation. Signed-off-by: Yangbo Lu --- Changes for v2: - None. Changes for v3: - None. --- drivers/mmc/fsl_esdhc.c | 3 +++ 1 file changed, 3 insertions(+) diff --git a/drivers/mmc/fsl_esdhc.c b/drivers/mmc/fsl_esdhc.c index fc9d0c9..c52ab0f 100644 --- a/drivers/mmc/fsl_esdhc.c +++ b/drivers/mmc/fsl_esdhc.c @@ -637,6 +637,9 @@ static int esdhc_init_common(struct fsl_esdhc_priv *priv, struct mmc *mmc) return -ETIMEDOUT; } + /* Clean TBCTL[TB_EN] which is not able to be reset by reset all */ + esdhc_clrbits32(>tbctl, TBCTL_TB_EN); + esdhc_enable_cache_snooping(regs); esdhc_setbits32(>sysctl, SYSCTL_HCKEN | SYSCTL_IPGEN); -- 2.7.4
[v3, 03/11] mmc: fsl_esdhc: support tuning for eMMC HS200
Support tuning process for eMMC HS200 for eSDHC. Signed-off-by: Yangbo Lu --- Changes for v2: - None. Changes for v3: - Rebased. --- drivers/mmc/fsl_esdhc.c | 106 ++-- include/fsl_esdhc.h | 17 ++-- 2 files changed, 116 insertions(+), 7 deletions(-) diff --git a/drivers/mmc/fsl_esdhc.c b/drivers/mmc/fsl_esdhc.c index 4fff7b5..fc9d0c9 100644 --- a/drivers/mmc/fsl_esdhc.c +++ b/drivers/mmc/fsl_esdhc.c @@ -60,7 +60,9 @@ struct fsl_esdhc { uintdmaerrattr; /* DMA error attribute register */ charreserved5[4]; /* reserved */ uinthostcapblt2;/* Host controller capabilities register 2 */ - charreserved6[756]; /* reserved */ + charreserved6[8]; /* reserved */ + uinttbctl; /* Tuning block control register */ + charreserved7[744]; /* reserved */ uintesdhcctl; /* eSDHC control register */ }; @@ -101,7 +103,9 @@ static uint esdhc_xfertyp(struct mmc_cmd *cmd, struct mmc_data *data) if (data) { xfertyp |= XFERTYP_DPSEL; #ifndef CONFIG_SYS_FSL_ESDHC_USE_PIO - xfertyp |= XFERTYP_DMAEN; + if (cmd->cmdidx != MMC_CMD_SEND_TUNING_BLOCK && + cmd->cmdidx != MMC_CMD_SEND_TUNING_BLOCK_HS200) + xfertyp |= XFERTYP_DMAEN; #endif if (data->blocks > 1) { xfertyp |= XFERTYP_MSBSEL; @@ -380,6 +384,10 @@ static int esdhc_send_cmd_common(struct fsl_esdhc_priv *priv, struct mmc *mmc, esdhc_write32(>cmdarg, cmd->cmdarg); esdhc_write32(>xfertyp, xfertyp); + if (cmd->cmdidx == MMC_CMD_SEND_TUNING_BLOCK || + cmd->cmdidx == MMC_CMD_SEND_TUNING_BLOCK_HS200) + flags = IRQSTAT_BRR; + /* Wait for the command to complete */ start = get_timer(0); while (!(esdhc_read32(>irqstat) & flags)) { @@ -439,6 +447,11 @@ static int esdhc_send_cmd_common(struct fsl_esdhc_priv *priv, struct mmc *mmc, #ifdef CONFIG_SYS_FSL_ESDHC_USE_PIO esdhc_pio_read_write(priv, data); #else + flags = DATA_COMPLETE; + if (cmd->cmdidx == MMC_CMD_SEND_TUNING_BLOCK || + cmd->cmdidx == MMC_CMD_SEND_TUNING_BLOCK_HS200) + flags = IRQSTAT_BRR; + do { irqstat = esdhc_read32(>irqstat); @@ -451,7 +464,7 @@ static int esdhc_send_cmd_common(struct fsl_esdhc_priv *priv, struct mmc *mmc, err = -ECOMM; goto out; } - } while ((irqstat & DATA_COMPLETE) != DATA_COMPLETE); + } while ((irqstat & flags) != flags); /* * Need invalidate the dcache here again to avoid any @@ -555,6 +568,19 @@ static void esdhc_clock_control(struct fsl_esdhc_priv *priv, bool enable) } } +static void esdhc_set_timing(struct fsl_esdhc_priv *priv, enum bus_mode mode) +{ + struct fsl_esdhc *regs = priv->esdhc_regs; + + esdhc_clock_control(priv, false); + + if (mode == MMC_HS_200) + esdhc_clrsetbits32(>autoc12err, UHSM_MASK, + UHSM_SDR104_HS200); + + esdhc_clock_control(priv, true); +} + static int esdhc_set_ios_common(struct fsl_esdhc_priv *priv, struct mmc *mmc) { struct fsl_esdhc *regs = priv->esdhc_regs; @@ -570,6 +596,9 @@ static int esdhc_set_ios_common(struct fsl_esdhc_priv *priv, struct mmc *mmc) if (priv->clock != mmc->clock) set_sysctl(priv, mmc, mmc->clock); + /* Set timing */ + esdhc_set_timing(priv, mmc->selected_mode); + /* Set the bus width */ esdhc_clrbits32(>proctl, PROCTL_DTW_4 | PROCTL_DTW_8); @@ -954,6 +983,77 @@ static int fsl_esdhc_reinit(struct udevice *dev) return esdhc_init_common(priv, >mmc); } +#ifdef MMC_SUPPORTS_TUNING +static void esdhc_flush_async_fifo(struct fsl_esdhc_priv *priv) +{ + struct fsl_esdhc *regs = priv->esdhc_regs; + u32 time_out; + + esdhc_setbits32(>esdhcctl, ESDHCCTL_FAF); + + time_out = 20; + while (esdhc_read32(>esdhcctl) & ESDHCCTL_FAF) { + if (time_out == 0) { + printf("fsl_esdhc: Flush asynchronous FIFO timeout.\n"); + break; + } + time_out--; + mdelay(1); + } +} + +static void esdhc_tuning_block_enable(struct fsl_esdhc_priv *priv, + bool en) +{ + struct fsl_esdhc *regs = priv->esdhc_regs; + + esdhc_clock_control(priv, false); + esdhc_flush_async_fifo(priv); + if (en) + esdhc_setbits32(>tbctl, TBCTL_TB_EN); + e
[v3, 02/11] mmc: fsl_esdhc: add a reinit() callback
Add a reinit() callback for mmc rescan. Signed-off-by: Yangbo Lu --- Changes for v2: - None. Changes for v3: - None. --- drivers/mmc/fsl_esdhc.c | 9 + 1 file changed, 9 insertions(+) diff --git a/drivers/mmc/fsl_esdhc.c b/drivers/mmc/fsl_esdhc.c index f6e0d43..4fff7b5 100644 --- a/drivers/mmc/fsl_esdhc.c +++ b/drivers/mmc/fsl_esdhc.c @@ -946,6 +946,14 @@ static int fsl_esdhc_set_ios(struct udevice *dev) return esdhc_set_ios_common(priv, >mmc); } +static int fsl_esdhc_reinit(struct udevice *dev) +{ + struct fsl_esdhc_plat *plat = dev_get_platdata(dev); + struct fsl_esdhc_priv *priv = dev_get_priv(dev); + + return esdhc_init_common(priv, >mmc); +} + static const struct dm_mmc_ops fsl_esdhc_ops = { .get_cd = fsl_esdhc_get_cd, .send_cmd = fsl_esdhc_send_cmd, @@ -953,6 +961,7 @@ static const struct dm_mmc_ops fsl_esdhc_ops = { #ifdef MMC_SUPPORTS_TUNING .execute_tuning = fsl_esdhc_execute_tuning, #endif + .reinit = fsl_esdhc_reinit, }; static const struct udevice_id fsl_esdhc_ids[] = { -- 2.7.4
[v3, 00/11] mmc: fsl_esdhc: support eMMC HS200/HS400 modes
This patch-set is to support eMMC HS200 and HS400 speed modes for eSDHC, and enable them on LX2160ARDB board. CI build link https://travis-ci.org/github/yangbolu1991/u-boot-test/builds/710977092 Changes for v2: - Added two patches to fix stability issue. Changes for v3: - Explained more in commit messages. - Added HS400 exit code for downgrade. Yangbo Lu (11): mmc: add a reinit() API mmc: fsl_esdhc: add a reinit() callback mmc: fsl_esdhc: support tuning for eMMC HS200 mmc: fsl_esdhc: clean TBCTL[TB_EN] manually during init mmc: add a hs400_tuning flag mmc: add a mmc_hs400_prepare_ddr() interface mmc: fsl_esdhc: support eMMC HS400 mode mmc: fsl_esdhc: fix mmc->clock with actual clock mmc: fsl_esdhc: fix eMMC HS400 stability issue arm: dts: lx2160ardb: support eMMC HS400 mode configs: lx2160ardb: enable eMMC HS400 mode support arch/arm/dts/fsl-lx2160a-rdb.dts | 2 + configs/lx2160ardb_tfa_SECURE_BOOT_defconfig | 1 + configs/lx2160ardb_tfa_defconfig | 1 + configs/lx2160ardb_tfa_stmm_defconfig| 1 + drivers/mmc/fsl_esdhc.c | 176 ++- drivers/mmc/mmc-uclass.c | 30 + drivers/mmc/mmc.c| 12 +- include/fsl_esdhc.h | 29 - include/mmc.h| 26 +++- 9 files changed, 268 insertions(+), 10 deletions(-) -- 2.7.4
[v3, 01/11] mmc: add a reinit() API
For DM_MMC, the controller re-initialization is needed to clear old configuration for mmc rescan. Signed-off-by: Yangbo Lu --- Changes for v2: - None. Changes for v3: - None. --- drivers/mmc/mmc-uclass.c | 15 +++ drivers/mmc/mmc.c| 8 ++-- include/mmc.h| 10 ++ 3 files changed, 31 insertions(+), 2 deletions(-) diff --git a/drivers/mmc/mmc-uclass.c b/drivers/mmc/mmc-uclass.c index c5b7872..b9f0880 100644 --- a/drivers/mmc/mmc-uclass.c +++ b/drivers/mmc/mmc-uclass.c @@ -170,6 +170,21 @@ int mmc_deferred_probe(struct mmc *mmc) return dm_mmc_deferred_probe(mmc->dev); } +int dm_mmc_reinit(struct udevice *dev) +{ + struct dm_mmc_ops *ops = mmc_get_ops(dev); + + if (ops->reinit) + return ops->reinit(dev); + + return 0; +} + +int mmc_reinit(struct mmc *mmc) +{ + return dm_mmc_reinit(mmc->dev); +} + int mmc_of_parse(struct udevice *dev, struct mmc_config *cfg) { int val; diff --git a/drivers/mmc/mmc.c b/drivers/mmc/mmc.c index f36d11d..a4c6153 100644 --- a/drivers/mmc/mmc.c +++ b/drivers/mmc/mmc.c @@ -2818,13 +2818,17 @@ int mmc_get_op_cond(struct mmc *mmc) return err; #if CONFIG_IS_ENABLED(DM_MMC) - /* The device has already been probed ready for use */ + /* +* Re-initialization is needed to clear old configuration for +* mmc rescan. +*/ + err = mmc_reinit(mmc); #else /* made sure it's not NULL earlier */ err = mmc->cfg->ops->init(mmc); +#endif if (err) return err; -#endif mmc->ddr_mode = 0; retry: diff --git a/include/mmc.h b/include/mmc.h index 8256219..161b8bc 100644 --- a/include/mmc.h +++ b/include/mmc.h @@ -422,6 +422,14 @@ struct dm_mmc_ops { */ int (*deferred_probe)(struct udevice *dev); /** +* reinit() - Re-initialization to clear old configuration for +* mmc rescan. +* +* @dev:Device to reinit +* @return 0 if Ok, -ve if error +*/ + int (*reinit)(struct udevice *dev); + /** * send_cmd() - Send a command to the MMC device * * @dev:Device to receive the command @@ -518,6 +526,7 @@ int dm_mmc_execute_tuning(struct udevice *dev, uint opcode); int dm_mmc_wait_dat0(struct udevice *dev, int state, int timeout_us); int dm_mmc_host_power_cycle(struct udevice *dev); int dm_mmc_deferred_probe(struct udevice *dev); +int dm_mmc_reinit(struct udevice *dev); int dm_mmc_get_b_max(struct udevice *dev, void *dst, lbaint_t blkcnt); /* Transition functions for compatibility */ @@ -529,6 +538,7 @@ int mmc_wait_dat0(struct mmc *mmc, int state, int timeout_us); int mmc_set_enhanced_strobe(struct mmc *mmc); int mmc_host_power_cycle(struct mmc *mmc); int mmc_deferred_probe(struct mmc *mmc); +int mmc_reinit(struct mmc *mmc); int mmc_get_b_max(struct mmc *mmc, void *dst, lbaint_t blkcnt); #else -- 2.7.4
[v2, 11/11] configs: lx2160ardb: enable eMMC HS400 mode support
Enable eMMC HS400 mode support on LX2160ARDB. Signed-off-by: Yangbo Lu --- Changes for v2: - None. --- configs/lx2160ardb_tfa_SECURE_BOOT_defconfig | 1 + configs/lx2160ardb_tfa_defconfig | 1 + configs/lx2160ardb_tfa_stmm_defconfig| 1 + 3 files changed, 3 insertions(+) diff --git a/configs/lx2160ardb_tfa_SECURE_BOOT_defconfig b/configs/lx2160ardb_tfa_SECURE_BOOT_defconfig index 12e224f..6c65853 100644 --- a/configs/lx2160ardb_tfa_SECURE_BOOT_defconfig +++ b/configs/lx2160ardb_tfa_SECURE_BOOT_defconfig @@ -40,6 +40,7 @@ CONFIG_DM_I2C=y CONFIG_I2C_SET_DEFAULT_BUS_NUM=y CONFIG_I2C_DEFAULT_BUS_NUMBER=0 CONFIG_DM_MMC=y +CONFIG_MMC_HS400_SUPPORT=y CONFIG_FSL_ESDHC=y CONFIG_MTD=y CONFIG_DM_SPI_FLASH=y diff --git a/configs/lx2160ardb_tfa_defconfig b/configs/lx2160ardb_tfa_defconfig index a5c78d2..a5c60c8 100644 --- a/configs/lx2160ardb_tfa_defconfig +++ b/configs/lx2160ardb_tfa_defconfig @@ -46,6 +46,7 @@ CONFIG_DM_I2C=y CONFIG_I2C_SET_DEFAULT_BUS_NUM=y CONFIG_I2C_DEFAULT_BUS_NUMBER=0 CONFIG_DM_MMC=y +CONFIG_MMC_HS400_SUPPORT=y CONFIG_FSL_ESDHC=y CONFIG_MTD=y CONFIG_DM_SPI_FLASH=y diff --git a/configs/lx2160ardb_tfa_stmm_defconfig b/configs/lx2160ardb_tfa_stmm_defconfig index e97c9b0..869d4e2 100644 --- a/configs/lx2160ardb_tfa_stmm_defconfig +++ b/configs/lx2160ardb_tfa_stmm_defconfig @@ -48,6 +48,7 @@ CONFIG_DM_I2C=y CONFIG_I2C_SET_DEFAULT_BUS_NUM=y CONFIG_I2C_DEFAULT_BUS_NUMBER=0 CONFIG_DM_MMC=y +CONFIG_MMC_HS400_SUPPORT=y CONFIG_SUPPORT_EMMC_RPMB=y CONFIG_FSL_ESDHC=y CONFIG_MTD=y -- 2.7.4
[v2, 07/11] mmc: fsl_esdhc: support eMMC HS400 mode
The process for eMMC HS400 mode for eSDHC is, 1. Perform the Tuning Process at the HS400 target operating frequency. Latched the clock division value. 2. if read transaction, then set the SDTIMNGCTL[FLW_CTL_BG]. 3. Switch to High Speed mode and then set the card clock frequency to a value not greater than 52Mhz 4. Clear TBCTL[TB_EN],tuning block enable bit. 5. Change to 8 bit DDR Mode 6. Switch the card to HS400 mode. 7. Set TBCTL[TB_EN], tuning block enable bit. 8. Clear SYSCTL[SDCLKEN] 9. Wait for PRSSTAT[SDSTB] to be set 10. Change the clock division to latched value.Set TBCTL[HS 400 mode] and Set SDCLKCTL[CMD_CLK_CTRL] 11. Set SYSCTL[SDCLKEN] 12. Wait for PRSSTAT[SDSTB] to be set 13. Set DLLCFG0[DLL_ENABLE] and DLLCFG0[DLL_FREQ_SEL]. 14. Wait for delay chain to lock. 15. Set TBCTL[HS400_WNDW_ADJUST] 16. Again clear SYSCTL[SDCLKEN] 17. Wait for PRSSTAT[SDSTB] to be set 18. Set ESDHCCTL[FAF] 19. Wait for ESDHCCTL[FAF] to be cleared 20. Set SYSCTL[SDCLKEN] 21. Wait for PRSSTAT[SDSTB] to be set. Signed-off-by: Yangbo Lu --- Changes for v2: - None. --- drivers/mmc/fsl_esdhc.c | 98 - include/fsl_esdhc.h | 12 ++ 2 files changed, 76 insertions(+), 34 deletions(-) diff --git a/drivers/mmc/fsl_esdhc.c b/drivers/mmc/fsl_esdhc.c index 607b420..c1a127c 100644 --- a/drivers/mmc/fsl_esdhc.c +++ b/drivers/mmc/fsl_esdhc.c @@ -62,7 +62,12 @@ struct fsl_esdhc { uinthostcapblt2;/* Host controller capabilities register 2 */ charreserved6[8]; /* reserved */ uinttbctl; /* Tuning block control register */ - charreserved7[744]; /* reserved */ + charreserved7[32]; /* reserved */ + uintsdclkctl; /* SD clock control register */ + uintsdtimingctl;/* SD timing control register */ + charreserved8[20]; /* reserved */ + uintdllcfg0;/* DLL config 0 register */ + charreserved9[680]; /* reserved */ uintesdhcctl; /* eSDHC control register */ }; @@ -568,6 +573,38 @@ static void esdhc_clock_control(struct fsl_esdhc_priv *priv, bool enable) } } +static void esdhc_flush_async_fifo(struct fsl_esdhc_priv *priv) +{ + struct fsl_esdhc *regs = priv->esdhc_regs; + u32 time_out; + + esdhc_setbits32(>esdhcctl, ESDHCCTL_FAF); + + time_out = 20; + while (esdhc_read32(>esdhcctl) & ESDHCCTL_FAF) { + if (time_out == 0) { + printf("fsl_esdhc: Flush asynchronous FIFO timeout.\n"); + break; + } + time_out--; + mdelay(1); + } +} + +static void esdhc_tuning_block_enable(struct fsl_esdhc_priv *priv, + bool en) +{ + struct fsl_esdhc *regs = priv->esdhc_regs; + + esdhc_clock_control(priv, false); + esdhc_flush_async_fifo(priv); + if (en) + esdhc_setbits32(>tbctl, TBCTL_TB_EN); + else + esdhc_clrbits32(>tbctl, TBCTL_TB_EN); + esdhc_clock_control(priv, true); +} + static void esdhc_set_timing(struct fsl_esdhc_priv *priv, enum bus_mode mode) { struct fsl_esdhc *regs = priv->esdhc_regs; @@ -577,7 +614,17 @@ static void esdhc_set_timing(struct fsl_esdhc_priv *priv, enum bus_mode mode) if (mode == MMC_HS_200) esdhc_clrsetbits32(>autoc12err, UHSM_MASK, UHSM_SDR104_HS200); + if (mode == MMC_HS_400) { + esdhc_setbits32(>tbctl, HS400_MODE); + esdhc_setbits32(>sdclkctl, CMD_CLK_CTL); + esdhc_clock_control(priv, true); + esdhc_setbits32(>dllcfg0, DLL_ENABLE | DLL_FREQ_SEL); + esdhc_setbits32(>tbctl, HS400_WNDW_ADJUST); + + esdhc_clock_control(priv, false); + esdhc_flush_async_fifo(priv); + } esdhc_clock_control(priv, true); } @@ -592,6 +639,9 @@ static int esdhc_set_ios_common(struct fsl_esdhc_priv *priv, struct mmc *mmc) esdhc_clock_control(priv, true); } + if (mmc->selected_mode == MMC_HS_400) + esdhc_tuning_block_enable(priv, true); + /* Set the clock speed */ if (priv->clock != mmc->clock) set_sysctl(priv, mmc, mmc->clock); @@ -987,38 +1037,6 @@ static int fsl_esdhc_reinit(struct udevice *dev) } #ifdef MMC_SUPPORTS_TUNING -static void esdhc_flush_async_fifo(struct fsl_esdhc_priv *priv) -{ - struct fsl_esdhc *regs = priv->esdhc_regs; - u32 time_out; - - esdhc_setbits32(>esdhcctl, ESDHCCTL_FAF); - - time_out = 20; - while (esdhc_read32(>esdhcctl) & ESDHCCTL_FAF) { - if (time_out == 0) { - printf("fsl_esdhc: Flush asynchronous FIFO timeout.\n"); -
[v2, 08/11] mmc: fsl_esdhc: fix mmc->clock with actual clock
Fix mmc->clock with actual clock which is divided by the controller, and record it with priv->clock which was removed accidentally. Signed-off-by: Yangbo Lu --- Changes for v2: - Added this patch. --- drivers/mmc/fsl_esdhc.c | 3 +++ 1 file changed, 3 insertions(+) diff --git a/drivers/mmc/fsl_esdhc.c b/drivers/mmc/fsl_esdhc.c index c1a127c..8999b74 100644 --- a/drivers/mmc/fsl_esdhc.c +++ b/drivers/mmc/fsl_esdhc.c @@ -523,6 +523,9 @@ static void set_sysctl(struct fsl_esdhc_priv *priv, struct mmc *mmc, uint clock) while (sdhc_clk / (div * pre_div) > clock && div < 16) div++; + mmc->clock = sdhc_clk / pre_div / div; + priv->clock = mmc->clock; + pre_div >>= 1; div -= 1; -- 2.7.4
[v2, 06/11] mmc: add a mmc_hs400_prepare_ddr() interface
Add a mmc_hs400_prepare_ddr() interface for controllers which needs preparation before switching to DDR mode for HS400 mode. Signed-off-by: Yangbo Lu --- Changes for v2: - None. --- drivers/mmc/mmc-uclass.c | 15 +++ drivers/mmc/mmc.c| 2 ++ include/mmc.h| 15 ++- 3 files changed, 31 insertions(+), 1 deletion(-) diff --git a/drivers/mmc/mmc-uclass.c b/drivers/mmc/mmc-uclass.c index b9f0880..240b205 100644 --- a/drivers/mmc/mmc-uclass.c +++ b/drivers/mmc/mmc-uclass.c @@ -141,6 +141,21 @@ int mmc_set_enhanced_strobe(struct mmc *mmc) } #endif +int dm_mmc_hs400_prepare_ddr(struct udevice *dev) +{ + struct dm_mmc_ops *ops = mmc_get_ops(dev); + + if (ops->hs400_prepare_ddr) + return ops->hs400_prepare_ddr(dev); + + return 0; +} + +int mmc_hs400_prepare_ddr(struct mmc *mmc) +{ + return dm_mmc_hs400_prepare_ddr(mmc->dev); +} + int dm_mmc_host_power_cycle(struct udevice *dev) { struct dm_mmc_ops *ops = mmc_get_ops(dev); diff --git a/drivers/mmc/mmc.c b/drivers/mmc/mmc.c index a18e75d..e396207 100644 --- a/drivers/mmc/mmc.c +++ b/drivers/mmc/mmc.c @@ -1987,6 +1987,8 @@ static int mmc_select_hs400(struct mmc *mmc) /* Set back to HS */ mmc_set_card_speed(mmc, MMC_HS, true); + mmc_hs400_prepare_ddr(mmc); + err = mmc_switch(mmc, EXT_CSD_CMD_SET_NORMAL, EXT_CSD_BUS_WIDTH, EXT_CSD_BUS_WIDTH_8 | EXT_CSD_DDR_FLAG); if (err) diff --git a/include/mmc.h b/include/mmc.h index 2399cc2..659df75 100644 --- a/include/mmc.h +++ b/include/mmc.h @@ -513,6 +513,14 @@ struct dm_mmc_ops { * @return maximum number of blocks for this transfer */ int (*get_b_max)(struct udevice *dev, void *dst, lbaint_t blkcnt); + + /** +* hs400_prepare_ddr - prepare to switch to DDR mode +* +* @dev:Device to check +* @return 0 if success, -ve on error +*/ + int (*hs400_prepare_ddr)(struct udevice *dev); }; #define mmc_get_ops(dev)((struct dm_mmc_ops *)(dev)->driver->ops) @@ -540,7 +548,7 @@ int mmc_host_power_cycle(struct mmc *mmc); int mmc_deferred_probe(struct mmc *mmc); int mmc_reinit(struct mmc *mmc); int mmc_get_b_max(struct mmc *mmc, void *dst, lbaint_t blkcnt); - +int mmc_hs400_prepare_ddr(struct mmc *mmc); #else struct mmc_ops { int (*send_cmd)(struct mmc *mmc, @@ -552,6 +560,11 @@ struct mmc_ops { int (*host_power_cycle)(struct mmc *mmc); int (*get_b_max)(struct mmc *mmc, void *dst, lbaint_t blkcnt); }; + +static inline int mmc_hs400_prepare_ddr(struct mmc *mmc) +{ + return 0; +} #endif struct mmc_config { -- 2.7.4
[v2, 09/11] mmc: fsl_esdhc: fix eMMC HS400 stability issue
There was a fix-up for eMMC HS400 stability issue in Linux. Patch link: https://git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git/ commit/?id=58d0bf843b49fa99588ac9f85178bd8dfd651b53 Description: Currently only LX2160A eSDHC supports eMMC HS400. According to a large number of tests, eMMC HS400 failed to work at 150MHz, and for a few boards failed to work at 175MHz. But eMMC HS400 worked fine on 200MHz. We hadn't found the root cause but setting eSDHC_DLLCFG0[DLL_FREQ_SEL] = 0 using slow delay chain seemed to resovle this issue. Let's use this as fixup for now. Introduce the fix-up in u-boot since the issue could be reproduced in u-boot too. Signed-off-by: Yangbo Lu --- Changes for v2: - Added this patch. --- drivers/mmc/fsl_esdhc.c | 5 - 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/drivers/mmc/fsl_esdhc.c b/drivers/mmc/fsl_esdhc.c index 8999b74..0879739 100644 --- a/drivers/mmc/fsl_esdhc.c +++ b/drivers/mmc/fsl_esdhc.c @@ -622,7 +622,10 @@ static void esdhc_set_timing(struct fsl_esdhc_priv *priv, enum bus_mode mode) esdhc_setbits32(>sdclkctl, CMD_CLK_CTL); esdhc_clock_control(priv, true); - esdhc_setbits32(>dllcfg0, DLL_ENABLE | DLL_FREQ_SEL); + if (priv->clock == 2) + esdhc_setbits32(>dllcfg0, DLL_FREQ_SEL); + + esdhc_setbits32(>dllcfg0, DLL_ENABLE); esdhc_setbits32(>tbctl, HS400_WNDW_ADJUST); esdhc_clock_control(priv, false); -- 2.7.4
[v2, 10/11] arm: dts: lx2160ardb: support eMMC HS400 mode
Add properties related to eMMC HS400 mode. mmc-hs400-1_8v; bus-width = <8>; Signed-off-by: Yangbo Lu --- Changes for v2: - None. --- arch/arm/dts/fsl-lx2160a-rdb.dts | 2 ++ 1 file changed, 2 insertions(+) diff --git a/arch/arm/dts/fsl-lx2160a-rdb.dts b/arch/arm/dts/fsl-lx2160a-rdb.dts index d787778..5fbdd90 100644 --- a/arch/arm/dts/fsl-lx2160a-rdb.dts +++ b/arch/arm/dts/fsl-lx2160a-rdb.dts @@ -80,6 +80,8 @@ { status = "okay"; mmc-hs200-1_8v; + mmc-hs400-1_8v; + bus-width = <8>; }; { -- 2.7.4
[v2, 03/11] mmc: fsl_esdhc: support tuning for eMMC HS200
Support tuning process for eMMC HS200 for eSDHC. Signed-off-by: Yangbo Lu --- Changes for v2: - None. --- drivers/mmc/fsl_esdhc.c | 106 ++-- include/fsl_esdhc.h | 17 ++-- 2 files changed, 116 insertions(+), 7 deletions(-) diff --git a/drivers/mmc/fsl_esdhc.c b/drivers/mmc/fsl_esdhc.c index d1f2e4a..5ad01ac 100644 --- a/drivers/mmc/fsl_esdhc.c +++ b/drivers/mmc/fsl_esdhc.c @@ -60,7 +60,9 @@ struct fsl_esdhc { uintdmaerrattr; /* DMA error attribute register */ charreserved5[4]; /* reserved */ uinthostcapblt2;/* Host controller capabilities register 2 */ - charreserved6[756]; /* reserved */ + charreserved6[8]; /* reserved */ + uinttbctl; /* Tuning block control register */ + charreserved7[744]; /* reserved */ uintesdhcctl; /* eSDHC control register */ }; @@ -101,7 +103,9 @@ static uint esdhc_xfertyp(struct mmc_cmd *cmd, struct mmc_data *data) if (data) { xfertyp |= XFERTYP_DPSEL; #ifndef CONFIG_SYS_FSL_ESDHC_USE_PIO - xfertyp |= XFERTYP_DMAEN; + if (cmd->cmdidx != MMC_CMD_SEND_TUNING_BLOCK && + cmd->cmdidx != MMC_CMD_SEND_TUNING_BLOCK_HS200) + xfertyp |= XFERTYP_DMAEN; #endif if (data->blocks > 1) { xfertyp |= XFERTYP_MSBSEL; @@ -380,6 +384,10 @@ static int esdhc_send_cmd_common(struct fsl_esdhc_priv *priv, struct mmc *mmc, esdhc_write32(>cmdarg, cmd->cmdarg); esdhc_write32(>xfertyp, xfertyp); + if (cmd->cmdidx == MMC_CMD_SEND_TUNING_BLOCK || + cmd->cmdidx == MMC_CMD_SEND_TUNING_BLOCK_HS200) + flags = IRQSTAT_BRR; + /* Wait for the command to complete */ start = get_timer(0); while (!(esdhc_read32(>irqstat) & flags)) { @@ -439,6 +447,11 @@ static int esdhc_send_cmd_common(struct fsl_esdhc_priv *priv, struct mmc *mmc, #ifdef CONFIG_SYS_FSL_ESDHC_USE_PIO esdhc_pio_read_write(priv, data); #else + flags = DATA_COMPLETE; + if (cmd->cmdidx == MMC_CMD_SEND_TUNING_BLOCK || + cmd->cmdidx == MMC_CMD_SEND_TUNING_BLOCK_HS200) + flags = IRQSTAT_BRR; + do { irqstat = esdhc_read32(>irqstat); @@ -451,7 +464,7 @@ static int esdhc_send_cmd_common(struct fsl_esdhc_priv *priv, struct mmc *mmc, err = -ECOMM; goto out; } - } while ((irqstat & DATA_COMPLETE) != DATA_COMPLETE); + } while ((irqstat & flags) != flags); /* * Need invalidate the dcache here again to avoid any @@ -555,6 +568,19 @@ static void esdhc_clock_control(struct fsl_esdhc_priv *priv, bool enable) } } +static void esdhc_set_timing(struct fsl_esdhc_priv *priv, enum bus_mode mode) +{ + struct fsl_esdhc *regs = priv->esdhc_regs; + + esdhc_clock_control(priv, false); + + if (mode == MMC_HS_200) + esdhc_clrsetbits32(>autoc12err, UHSM_MASK, + UHSM_SDR104_HS200); + + esdhc_clock_control(priv, true); +} + static int esdhc_set_ios_common(struct fsl_esdhc_priv *priv, struct mmc *mmc) { struct fsl_esdhc *regs = priv->esdhc_regs; @@ -570,6 +596,9 @@ static int esdhc_set_ios_common(struct fsl_esdhc_priv *priv, struct mmc *mmc) if (priv->clock != mmc->clock) set_sysctl(priv, mmc, mmc->clock); + /* Set timing */ + esdhc_set_timing(priv, mmc->selected_mode); + /* Set the bus width */ esdhc_clrbits32(>proctl, PROCTL_DTW_4 | PROCTL_DTW_8); @@ -954,6 +983,77 @@ static int fsl_esdhc_reinit(struct udevice *dev) return esdhc_init_common(priv, >mmc); } +#ifdef MMC_SUPPORTS_TUNING +static void esdhc_flush_async_fifo(struct fsl_esdhc_priv *priv) +{ + struct fsl_esdhc *regs = priv->esdhc_regs; + u32 time_out; + + esdhc_setbits32(>esdhcctl, ESDHCCTL_FAF); + + time_out = 20; + while (esdhc_read32(>esdhcctl) & ESDHCCTL_FAF) { + if (time_out == 0) { + printf("fsl_esdhc: Flush asynchronous FIFO timeout.\n"); + break; + } + time_out--; + mdelay(1); + } +} + +static void esdhc_tuning_block_enable(struct fsl_esdhc_priv *priv, + bool en) +{ + struct fsl_esdhc *regs = priv->esdhc_regs; + + esdhc_clock_control(priv, false); + esdhc_flush_async_fifo(priv); + if (en) + esdhc_setbits32(>tbctl, TBCTL_TB_EN); + else + esdhc_clrbits32(>tbctl
[v2, 05/11] mmc: add a hs400_tuning flag
Add a hs400_tuning flag to identify the tuning for HS400 mode. Signed-off-by: Yangbo Lu --- Changes for v2: - None. --- drivers/mmc/mmc.c | 2 ++ include/mmc.h | 1 + 2 files changed, 3 insertions(+) diff --git a/drivers/mmc/mmc.c b/drivers/mmc/mmc.c index a53f93a..a18e75d 100644 --- a/drivers/mmc/mmc.c +++ b/drivers/mmc/mmc.c @@ -1976,7 +1976,9 @@ static int mmc_select_hs400(struct mmc *mmc) mmc_set_clock(mmc, mmc->tran_speed, false); /* execute tuning if needed */ + mmc->hs400_tuning = 1; err = mmc_execute_tuning(mmc, MMC_CMD_SEND_TUNING_BLOCK_HS200); + mmc->hs400_tuning = 0; if (err) { debug("tuning failed\n"); return err; diff --git a/include/mmc.h b/include/mmc.h index 161b8bc..2399cc2 100644 --- a/include/mmc.h +++ b/include/mmc.h @@ -707,6 +707,7 @@ struct mmc { * accessing the boot partitions */ u32 quirks; + u8 hs400_tuning; }; struct mmc_hwpart_conf { -- 2.7.4
[v2, 04/11] mmc: fsl_esdhc: clean TBCTL[TB_EN] manually during init
Clean TBCTL[TB_EN] manually during init since it is not able to be reset by reset all operation. Signed-off-by: Yangbo Lu --- Changes for v2: - None. --- drivers/mmc/fsl_esdhc.c | 3 +++ 1 file changed, 3 insertions(+) diff --git a/drivers/mmc/fsl_esdhc.c b/drivers/mmc/fsl_esdhc.c index 5ad01ac..607b420 100644 --- a/drivers/mmc/fsl_esdhc.c +++ b/drivers/mmc/fsl_esdhc.c @@ -637,6 +637,9 @@ static int esdhc_init_common(struct fsl_esdhc_priv *priv, struct mmc *mmc) return -ETIMEDOUT; } + /* Clean TBCTL[TB_EN] which is not able to be reset by reset all */ + esdhc_clrbits32(>tbctl, TBCTL_TB_EN); + esdhc_enable_cache_snooping(regs); esdhc_setbits32(>sysctl, SYSCTL_HCKEN | SYSCTL_IPGEN); -- 2.7.4
[v2, 01/11] mmc: add a reinit() API
For DM_MMC, the controller re-initialization is needed to clear old configuration for mmc rescan. Signed-off-by: Yangbo Lu --- Changes for v2: - None. --- drivers/mmc/mmc-uclass.c | 15 +++ drivers/mmc/mmc.c| 8 ++-- include/mmc.h| 10 ++ 3 files changed, 31 insertions(+), 2 deletions(-) diff --git a/drivers/mmc/mmc-uclass.c b/drivers/mmc/mmc-uclass.c index c5b7872..b9f0880 100644 --- a/drivers/mmc/mmc-uclass.c +++ b/drivers/mmc/mmc-uclass.c @@ -170,6 +170,21 @@ int mmc_deferred_probe(struct mmc *mmc) return dm_mmc_deferred_probe(mmc->dev); } +int dm_mmc_reinit(struct udevice *dev) +{ + struct dm_mmc_ops *ops = mmc_get_ops(dev); + + if (ops->reinit) + return ops->reinit(dev); + + return 0; +} + +int mmc_reinit(struct mmc *mmc) +{ + return dm_mmc_reinit(mmc->dev); +} + int mmc_of_parse(struct udevice *dev, struct mmc_config *cfg) { int val; diff --git a/drivers/mmc/mmc.c b/drivers/mmc/mmc.c index 50f47d4..a53f93a 100644 --- a/drivers/mmc/mmc.c +++ b/drivers/mmc/mmc.c @@ -2813,13 +2813,17 @@ int mmc_get_op_cond(struct mmc *mmc) return err; #if CONFIG_IS_ENABLED(DM_MMC) - /* The device has already been probed ready for use */ + /* +* Re-initialization is needed to clear old configuration for +* mmc rescan. +*/ + err = mmc_reinit(mmc); #else /* made sure it's not NULL earlier */ err = mmc->cfg->ops->init(mmc); +#endif if (err) return err; -#endif mmc->ddr_mode = 0; retry: diff --git a/include/mmc.h b/include/mmc.h index 8256219..161b8bc 100644 --- a/include/mmc.h +++ b/include/mmc.h @@ -422,6 +422,14 @@ struct dm_mmc_ops { */ int (*deferred_probe)(struct udevice *dev); /** +* reinit() - Re-initialization to clear old configuration for +* mmc rescan. +* +* @dev:Device to reinit +* @return 0 if Ok, -ve if error +*/ + int (*reinit)(struct udevice *dev); + /** * send_cmd() - Send a command to the MMC device * * @dev:Device to receive the command @@ -518,6 +526,7 @@ int dm_mmc_execute_tuning(struct udevice *dev, uint opcode); int dm_mmc_wait_dat0(struct udevice *dev, int state, int timeout_us); int dm_mmc_host_power_cycle(struct udevice *dev); int dm_mmc_deferred_probe(struct udevice *dev); +int dm_mmc_reinit(struct udevice *dev); int dm_mmc_get_b_max(struct udevice *dev, void *dst, lbaint_t blkcnt); /* Transition functions for compatibility */ @@ -529,6 +538,7 @@ int mmc_wait_dat0(struct mmc *mmc, int state, int timeout_us); int mmc_set_enhanced_strobe(struct mmc *mmc); int mmc_host_power_cycle(struct mmc *mmc); int mmc_deferred_probe(struct mmc *mmc); +int mmc_reinit(struct mmc *mmc); int mmc_get_b_max(struct mmc *mmc, void *dst, lbaint_t blkcnt); #else -- 2.7.4
[v2, 02/11] mmc: fsl_esdhc: add a reinit() callback
Add a reinit() callback for mmc rescan. Signed-off-by: Yangbo Lu --- Changes for v2: - None. --- drivers/mmc/fsl_esdhc.c | 9 + 1 file changed, 9 insertions(+) diff --git a/drivers/mmc/fsl_esdhc.c b/drivers/mmc/fsl_esdhc.c index a4b923a..d1f2e4a 100644 --- a/drivers/mmc/fsl_esdhc.c +++ b/drivers/mmc/fsl_esdhc.c @@ -946,6 +946,14 @@ static int fsl_esdhc_set_ios(struct udevice *dev) return esdhc_set_ios_common(priv, >mmc); } +static int fsl_esdhc_reinit(struct udevice *dev) +{ + struct fsl_esdhc_plat *plat = dev_get_platdata(dev); + struct fsl_esdhc_priv *priv = dev_get_priv(dev); + + return esdhc_init_common(priv, >mmc); +} + static const struct dm_mmc_ops fsl_esdhc_ops = { .get_cd = fsl_esdhc_get_cd, .send_cmd = fsl_esdhc_send_cmd, @@ -953,6 +961,7 @@ static const struct dm_mmc_ops fsl_esdhc_ops = { #ifdef MMC_SUPPORTS_TUNING .execute_tuning = fsl_esdhc_execute_tuning, #endif + .reinit = fsl_esdhc_reinit, }; static const struct udevice_id fsl_esdhc_ids[] = { -- 2.7.4
[v2, 00/11] mmc: fsl_esdhc: support eMMC HS200/HS400 modes
This patch-set is to support eMMC HS200 and HS400 speed modes for eSDHC, and enable them on LX2160ARDB board. CI build link https://travis-ci.org/github/yangbolu1991/u-boot-test/builds/709088861 Changes for v2: - Added two patches to fix stability issue. Yangbo Lu (11): mmc: add a reinit() API mmc: fsl_esdhc: add a reinit() callback mmc: fsl_esdhc: support tuning for eMMC HS200 mmc: fsl_esdhc: clean TBCTL[TB_EN] manually during init mmc: add a hs400_tuning flag mmc: add a mmc_hs400_prepare_ddr() interface mmc: fsl_esdhc: support eMMC HS400 mode mmc: fsl_esdhc: fix mmc->clock with actual clock mmc: fsl_esdhc: fix eMMC HS400 stability issue arm: dts: lx2160ardb: support eMMC HS400 mode configs: lx2160ardb: enable eMMC HS400 mode support arch/arm/dts/fsl-lx2160a-rdb.dts | 2 + configs/lx2160ardb_tfa_SECURE_BOOT_defconfig | 1 + configs/lx2160ardb_tfa_defconfig | 1 + configs/lx2160ardb_tfa_stmm_defconfig| 1 + drivers/mmc/fsl_esdhc.c | 154 ++- drivers/mmc/mmc-uclass.c | 30 ++ drivers/mmc/mmc.c| 12 ++- include/fsl_esdhc.h | 29 - include/mmc.h| 26 - 9 files changed, 246 insertions(+), 10 deletions(-) -- 2.7.4
[PATCH 8/9] arm: dts: lx2160ardb: support eMMC HS400 mode
Add properties related to eMMC HS400 mode. mmc-hs400-1_8v; bus-width = <8>; Signed-off-by: Yangbo Lu --- arch/arm/dts/fsl-lx2160a-rdb.dts | 2 ++ 1 file changed, 2 insertions(+) diff --git a/arch/arm/dts/fsl-lx2160a-rdb.dts b/arch/arm/dts/fsl-lx2160a-rdb.dts index d787778..5fbdd90 100644 --- a/arch/arm/dts/fsl-lx2160a-rdb.dts +++ b/arch/arm/dts/fsl-lx2160a-rdb.dts @@ -80,6 +80,8 @@ { status = "okay"; mmc-hs200-1_8v; + mmc-hs400-1_8v; + bus-width = <8>; }; { -- 2.7.4
[PATCH 9/9] configs: lx2160ardb: enable eMMC HS400 mode support
Enable eMMC HS400 mode support on LX2160ARDB. Signed-off-by: Yangbo Lu --- configs/lx2160ardb_tfa_SECURE_BOOT_defconfig | 1 + configs/lx2160ardb_tfa_defconfig | 1 + configs/lx2160ardb_tfa_stmm_defconfig| 1 + 3 files changed, 3 insertions(+) diff --git a/configs/lx2160ardb_tfa_SECURE_BOOT_defconfig b/configs/lx2160ardb_tfa_SECURE_BOOT_defconfig index 12e224f..6c65853 100644 --- a/configs/lx2160ardb_tfa_SECURE_BOOT_defconfig +++ b/configs/lx2160ardb_tfa_SECURE_BOOT_defconfig @@ -40,6 +40,7 @@ CONFIG_DM_I2C=y CONFIG_I2C_SET_DEFAULT_BUS_NUM=y CONFIG_I2C_DEFAULT_BUS_NUMBER=0 CONFIG_DM_MMC=y +CONFIG_MMC_HS400_SUPPORT=y CONFIG_FSL_ESDHC=y CONFIG_MTD=y CONFIG_DM_SPI_FLASH=y diff --git a/configs/lx2160ardb_tfa_defconfig b/configs/lx2160ardb_tfa_defconfig index a5c78d2..a5c60c8 100644 --- a/configs/lx2160ardb_tfa_defconfig +++ b/configs/lx2160ardb_tfa_defconfig @@ -46,6 +46,7 @@ CONFIG_DM_I2C=y CONFIG_I2C_SET_DEFAULT_BUS_NUM=y CONFIG_I2C_DEFAULT_BUS_NUMBER=0 CONFIG_DM_MMC=y +CONFIG_MMC_HS400_SUPPORT=y CONFIG_FSL_ESDHC=y CONFIG_MTD=y CONFIG_DM_SPI_FLASH=y diff --git a/configs/lx2160ardb_tfa_stmm_defconfig b/configs/lx2160ardb_tfa_stmm_defconfig index e97c9b0..869d4e2 100644 --- a/configs/lx2160ardb_tfa_stmm_defconfig +++ b/configs/lx2160ardb_tfa_stmm_defconfig @@ -48,6 +48,7 @@ CONFIG_DM_I2C=y CONFIG_I2C_SET_DEFAULT_BUS_NUM=y CONFIG_I2C_DEFAULT_BUS_NUMBER=0 CONFIG_DM_MMC=y +CONFIG_MMC_HS400_SUPPORT=y CONFIG_SUPPORT_EMMC_RPMB=y CONFIG_FSL_ESDHC=y CONFIG_MTD=y -- 2.7.4
[PATCH 6/9] mmc: add a mmc_hs400_prepare_ddr() interface
Add a mmc_hs400_prepare_ddr() interface for controllers which needs preparation before switching to DDR mode for HS400 mode. Signed-off-by: Yangbo Lu --- drivers/mmc/mmc-uclass.c | 15 +++ drivers/mmc/mmc.c| 2 ++ include/mmc.h| 15 ++- 3 files changed, 31 insertions(+), 1 deletion(-) diff --git a/drivers/mmc/mmc-uclass.c b/drivers/mmc/mmc-uclass.c index b9f0880..240b205 100644 --- a/drivers/mmc/mmc-uclass.c +++ b/drivers/mmc/mmc-uclass.c @@ -141,6 +141,21 @@ int mmc_set_enhanced_strobe(struct mmc *mmc) } #endif +int dm_mmc_hs400_prepare_ddr(struct udevice *dev) +{ + struct dm_mmc_ops *ops = mmc_get_ops(dev); + + if (ops->hs400_prepare_ddr) + return ops->hs400_prepare_ddr(dev); + + return 0; +} + +int mmc_hs400_prepare_ddr(struct mmc *mmc) +{ + return dm_mmc_hs400_prepare_ddr(mmc->dev); +} + int dm_mmc_host_power_cycle(struct udevice *dev) { struct dm_mmc_ops *ops = mmc_get_ops(dev); diff --git a/drivers/mmc/mmc.c b/drivers/mmc/mmc.c index a18e75d..e396207 100644 --- a/drivers/mmc/mmc.c +++ b/drivers/mmc/mmc.c @@ -1987,6 +1987,8 @@ static int mmc_select_hs400(struct mmc *mmc) /* Set back to HS */ mmc_set_card_speed(mmc, MMC_HS, true); + mmc_hs400_prepare_ddr(mmc); + err = mmc_switch(mmc, EXT_CSD_CMD_SET_NORMAL, EXT_CSD_BUS_WIDTH, EXT_CSD_BUS_WIDTH_8 | EXT_CSD_DDR_FLAG); if (err) diff --git a/include/mmc.h b/include/mmc.h index 2399cc2..659df75 100644 --- a/include/mmc.h +++ b/include/mmc.h @@ -513,6 +513,14 @@ struct dm_mmc_ops { * @return maximum number of blocks for this transfer */ int (*get_b_max)(struct udevice *dev, void *dst, lbaint_t blkcnt); + + /** +* hs400_prepare_ddr - prepare to switch to DDR mode +* +* @dev:Device to check +* @return 0 if success, -ve on error +*/ + int (*hs400_prepare_ddr)(struct udevice *dev); }; #define mmc_get_ops(dev)((struct dm_mmc_ops *)(dev)->driver->ops) @@ -540,7 +548,7 @@ int mmc_host_power_cycle(struct mmc *mmc); int mmc_deferred_probe(struct mmc *mmc); int mmc_reinit(struct mmc *mmc); int mmc_get_b_max(struct mmc *mmc, void *dst, lbaint_t blkcnt); - +int mmc_hs400_prepare_ddr(struct mmc *mmc); #else struct mmc_ops { int (*send_cmd)(struct mmc *mmc, @@ -552,6 +560,11 @@ struct mmc_ops { int (*host_power_cycle)(struct mmc *mmc); int (*get_b_max)(struct mmc *mmc, void *dst, lbaint_t blkcnt); }; + +static inline int mmc_hs400_prepare_ddr(struct mmc *mmc) +{ + return 0; +} #endif struct mmc_config { -- 2.7.4
[PATCH 4/9] mmc: fsl_esdhc: clean TBCTL[TB_EN] manually during init
Clean TBCTL[TB_EN] manually during init since it is not able to be reset by reset all operation. Signed-off-by: Yangbo Lu --- drivers/mmc/fsl_esdhc.c | 3 +++ 1 file changed, 3 insertions(+) diff --git a/drivers/mmc/fsl_esdhc.c b/drivers/mmc/fsl_esdhc.c index 5ad01ac..607b420 100644 --- a/drivers/mmc/fsl_esdhc.c +++ b/drivers/mmc/fsl_esdhc.c @@ -637,6 +637,9 @@ static int esdhc_init_common(struct fsl_esdhc_priv *priv, struct mmc *mmc) return -ETIMEDOUT; } + /* Clean TBCTL[TB_EN] which is not able to be reset by reset all */ + esdhc_clrbits32(>tbctl, TBCTL_TB_EN); + esdhc_enable_cache_snooping(regs); esdhc_setbits32(>sysctl, SYSCTL_HCKEN | SYSCTL_IPGEN); -- 2.7.4
[PATCH 7/9] mmc: fsl_esdhc: support eMMC HS400 mode
The process for eMMC HS400 mode for eSDHC is, 1. Perform the Tuning Process at the HS400 target operating frequency. Latched the clock division value. 2. if read transaction, then set the SDTIMNGCTL[FLW_CTL_BG]. 3. Switch to High Speed mode and then set the card clock frequency to a value not greater than 52Mhz 4. Clear TBCTL[TB_EN],tuning block enable bit. 5. Change to 8 bit DDR Mode 6. Switch the card to HS400 mode. 7. Set TBCTL[TB_EN], tuning block enable bit. 8. Clear SYSCTL[SDCLKEN] 9. Wait for PRSSTAT[SDSTB] to be set 10. Change the clock division to latched value.Set TBCTL[HS 400 mode] and Set SDCLKCTL[CMD_CLK_CTRL] 11. Set SYSCTL[SDCLKEN] 12. Wait for PRSSTAT[SDSTB] to be set 13. Set DLLCFG0[DLL_ENABLE] and DLLCFG0[DLL_FREQ_SEL]. 14. Wait for delay chain to lock. 15. Set TBCTL[HS400_WNDW_ADJUST] 16. Again clear SYSCTL[SDCLKEN] 17. Wait for PRSSTAT[SDSTB] to be set 18. Set ESDHCCTL[FAF] 19. Wait for ESDHCCTL[FAF] to be cleared 20. Set SYSCTL[SDCLKEN] 21. Wait for PRSSTAT[SDSTB] to be set. Signed-off-by: Yangbo Lu --- drivers/mmc/fsl_esdhc.c | 98 - include/fsl_esdhc.h | 12 ++ 2 files changed, 76 insertions(+), 34 deletions(-) diff --git a/drivers/mmc/fsl_esdhc.c b/drivers/mmc/fsl_esdhc.c index 607b420..c1a127c 100644 --- a/drivers/mmc/fsl_esdhc.c +++ b/drivers/mmc/fsl_esdhc.c @@ -62,7 +62,12 @@ struct fsl_esdhc { uinthostcapblt2;/* Host controller capabilities register 2 */ charreserved6[8]; /* reserved */ uinttbctl; /* Tuning block control register */ - charreserved7[744]; /* reserved */ + charreserved7[32]; /* reserved */ + uintsdclkctl; /* SD clock control register */ + uintsdtimingctl;/* SD timing control register */ + charreserved8[20]; /* reserved */ + uintdllcfg0;/* DLL config 0 register */ + charreserved9[680]; /* reserved */ uintesdhcctl; /* eSDHC control register */ }; @@ -568,6 +573,38 @@ static void esdhc_clock_control(struct fsl_esdhc_priv *priv, bool enable) } } +static void esdhc_flush_async_fifo(struct fsl_esdhc_priv *priv) +{ + struct fsl_esdhc *regs = priv->esdhc_regs; + u32 time_out; + + esdhc_setbits32(>esdhcctl, ESDHCCTL_FAF); + + time_out = 20; + while (esdhc_read32(>esdhcctl) & ESDHCCTL_FAF) { + if (time_out == 0) { + printf("fsl_esdhc: Flush asynchronous FIFO timeout.\n"); + break; + } + time_out--; + mdelay(1); + } +} + +static void esdhc_tuning_block_enable(struct fsl_esdhc_priv *priv, + bool en) +{ + struct fsl_esdhc *regs = priv->esdhc_regs; + + esdhc_clock_control(priv, false); + esdhc_flush_async_fifo(priv); + if (en) + esdhc_setbits32(>tbctl, TBCTL_TB_EN); + else + esdhc_clrbits32(>tbctl, TBCTL_TB_EN); + esdhc_clock_control(priv, true); +} + static void esdhc_set_timing(struct fsl_esdhc_priv *priv, enum bus_mode mode) { struct fsl_esdhc *regs = priv->esdhc_regs; @@ -577,7 +614,17 @@ static void esdhc_set_timing(struct fsl_esdhc_priv *priv, enum bus_mode mode) if (mode == MMC_HS_200) esdhc_clrsetbits32(>autoc12err, UHSM_MASK, UHSM_SDR104_HS200); + if (mode == MMC_HS_400) { + esdhc_setbits32(>tbctl, HS400_MODE); + esdhc_setbits32(>sdclkctl, CMD_CLK_CTL); + esdhc_clock_control(priv, true); + esdhc_setbits32(>dllcfg0, DLL_ENABLE | DLL_FREQ_SEL); + esdhc_setbits32(>tbctl, HS400_WNDW_ADJUST); + + esdhc_clock_control(priv, false); + esdhc_flush_async_fifo(priv); + } esdhc_clock_control(priv, true); } @@ -592,6 +639,9 @@ static int esdhc_set_ios_common(struct fsl_esdhc_priv *priv, struct mmc *mmc) esdhc_clock_control(priv, true); } + if (mmc->selected_mode == MMC_HS_400) + esdhc_tuning_block_enable(priv, true); + /* Set the clock speed */ if (priv->clock != mmc->clock) set_sysctl(priv, mmc, mmc->clock); @@ -987,38 +1037,6 @@ static int fsl_esdhc_reinit(struct udevice *dev) } #ifdef MMC_SUPPORTS_TUNING -static void esdhc_flush_async_fifo(struct fsl_esdhc_priv *priv) -{ - struct fsl_esdhc *regs = priv->esdhc_regs; - u32 time_out; - - esdhc_setbits32(>esdhcctl, ESDHCCTL_FAF); - - time_out = 20; - while (esdhc_read32(>esdhcctl) & ESDHCCTL_FAF) { - if (time_out == 0) { - printf("fsl_esdhc: Flush asynchronous FIFO timeout.\n"); - break; -
[PATCH 5/9] mmc: add a hs400_tuning flag
Add a hs400_tuning flag to identify the tuning for HS400 mode. Signed-off-by: Yangbo Lu --- drivers/mmc/mmc.c | 2 ++ include/mmc.h | 1 + 2 files changed, 3 insertions(+) diff --git a/drivers/mmc/mmc.c b/drivers/mmc/mmc.c index a53f93a..a18e75d 100644 --- a/drivers/mmc/mmc.c +++ b/drivers/mmc/mmc.c @@ -1976,7 +1976,9 @@ static int mmc_select_hs400(struct mmc *mmc) mmc_set_clock(mmc, mmc->tran_speed, false); /* execute tuning if needed */ + mmc->hs400_tuning = 1; err = mmc_execute_tuning(mmc, MMC_CMD_SEND_TUNING_BLOCK_HS200); + mmc->hs400_tuning = 0; if (err) { debug("tuning failed\n"); return err; diff --git a/include/mmc.h b/include/mmc.h index 161b8bc..2399cc2 100644 --- a/include/mmc.h +++ b/include/mmc.h @@ -707,6 +707,7 @@ struct mmc { * accessing the boot partitions */ u32 quirks; + u8 hs400_tuning; }; struct mmc_hwpart_conf { -- 2.7.4
[PATCH 2/9] mmc: fsl_esdhc: add a reinit() callback
Add a reinit() callback for mmc rescan. Signed-off-by: Yangbo Lu --- drivers/mmc/fsl_esdhc.c | 9 + 1 file changed, 9 insertions(+) diff --git a/drivers/mmc/fsl_esdhc.c b/drivers/mmc/fsl_esdhc.c index a4b923a..d1f2e4a 100644 --- a/drivers/mmc/fsl_esdhc.c +++ b/drivers/mmc/fsl_esdhc.c @@ -946,6 +946,14 @@ static int fsl_esdhc_set_ios(struct udevice *dev) return esdhc_set_ios_common(priv, >mmc); } +static int fsl_esdhc_reinit(struct udevice *dev) +{ + struct fsl_esdhc_plat *plat = dev_get_platdata(dev); + struct fsl_esdhc_priv *priv = dev_get_priv(dev); + + return esdhc_init_common(priv, >mmc); +} + static const struct dm_mmc_ops fsl_esdhc_ops = { .get_cd = fsl_esdhc_get_cd, .send_cmd = fsl_esdhc_send_cmd, @@ -953,6 +961,7 @@ static const struct dm_mmc_ops fsl_esdhc_ops = { #ifdef MMC_SUPPORTS_TUNING .execute_tuning = fsl_esdhc_execute_tuning, #endif + .reinit = fsl_esdhc_reinit, }; static const struct udevice_id fsl_esdhc_ids[] = { -- 2.7.4
[PATCH 3/9] mmc: fsl_esdhc: support tuning for eMMC HS200
Support tuning process for eMMC HS200 for eSDHC. Signed-off-by: Yangbo Lu --- drivers/mmc/fsl_esdhc.c | 106 ++-- include/fsl_esdhc.h | 17 ++-- 2 files changed, 116 insertions(+), 7 deletions(-) diff --git a/drivers/mmc/fsl_esdhc.c b/drivers/mmc/fsl_esdhc.c index d1f2e4a..5ad01ac 100644 --- a/drivers/mmc/fsl_esdhc.c +++ b/drivers/mmc/fsl_esdhc.c @@ -60,7 +60,9 @@ struct fsl_esdhc { uintdmaerrattr; /* DMA error attribute register */ charreserved5[4]; /* reserved */ uinthostcapblt2;/* Host controller capabilities register 2 */ - charreserved6[756]; /* reserved */ + charreserved6[8]; /* reserved */ + uinttbctl; /* Tuning block control register */ + charreserved7[744]; /* reserved */ uintesdhcctl; /* eSDHC control register */ }; @@ -101,7 +103,9 @@ static uint esdhc_xfertyp(struct mmc_cmd *cmd, struct mmc_data *data) if (data) { xfertyp |= XFERTYP_DPSEL; #ifndef CONFIG_SYS_FSL_ESDHC_USE_PIO - xfertyp |= XFERTYP_DMAEN; + if (cmd->cmdidx != MMC_CMD_SEND_TUNING_BLOCK && + cmd->cmdidx != MMC_CMD_SEND_TUNING_BLOCK_HS200) + xfertyp |= XFERTYP_DMAEN; #endif if (data->blocks > 1) { xfertyp |= XFERTYP_MSBSEL; @@ -380,6 +384,10 @@ static int esdhc_send_cmd_common(struct fsl_esdhc_priv *priv, struct mmc *mmc, esdhc_write32(>cmdarg, cmd->cmdarg); esdhc_write32(>xfertyp, xfertyp); + if (cmd->cmdidx == MMC_CMD_SEND_TUNING_BLOCK || + cmd->cmdidx == MMC_CMD_SEND_TUNING_BLOCK_HS200) + flags = IRQSTAT_BRR; + /* Wait for the command to complete */ start = get_timer(0); while (!(esdhc_read32(>irqstat) & flags)) { @@ -439,6 +447,11 @@ static int esdhc_send_cmd_common(struct fsl_esdhc_priv *priv, struct mmc *mmc, #ifdef CONFIG_SYS_FSL_ESDHC_USE_PIO esdhc_pio_read_write(priv, data); #else + flags = DATA_COMPLETE; + if (cmd->cmdidx == MMC_CMD_SEND_TUNING_BLOCK || + cmd->cmdidx == MMC_CMD_SEND_TUNING_BLOCK_HS200) + flags = IRQSTAT_BRR; + do { irqstat = esdhc_read32(>irqstat); @@ -451,7 +464,7 @@ static int esdhc_send_cmd_common(struct fsl_esdhc_priv *priv, struct mmc *mmc, err = -ECOMM; goto out; } - } while ((irqstat & DATA_COMPLETE) != DATA_COMPLETE); + } while ((irqstat & flags) != flags); /* * Need invalidate the dcache here again to avoid any @@ -555,6 +568,19 @@ static void esdhc_clock_control(struct fsl_esdhc_priv *priv, bool enable) } } +static void esdhc_set_timing(struct fsl_esdhc_priv *priv, enum bus_mode mode) +{ + struct fsl_esdhc *regs = priv->esdhc_regs; + + esdhc_clock_control(priv, false); + + if (mode == MMC_HS_200) + esdhc_clrsetbits32(>autoc12err, UHSM_MASK, + UHSM_SDR104_HS200); + + esdhc_clock_control(priv, true); +} + static int esdhc_set_ios_common(struct fsl_esdhc_priv *priv, struct mmc *mmc) { struct fsl_esdhc *regs = priv->esdhc_regs; @@ -570,6 +596,9 @@ static int esdhc_set_ios_common(struct fsl_esdhc_priv *priv, struct mmc *mmc) if (priv->clock != mmc->clock) set_sysctl(priv, mmc, mmc->clock); + /* Set timing */ + esdhc_set_timing(priv, mmc->selected_mode); + /* Set the bus width */ esdhc_clrbits32(>proctl, PROCTL_DTW_4 | PROCTL_DTW_8); @@ -954,6 +983,77 @@ static int fsl_esdhc_reinit(struct udevice *dev) return esdhc_init_common(priv, >mmc); } +#ifdef MMC_SUPPORTS_TUNING +static void esdhc_flush_async_fifo(struct fsl_esdhc_priv *priv) +{ + struct fsl_esdhc *regs = priv->esdhc_regs; + u32 time_out; + + esdhc_setbits32(>esdhcctl, ESDHCCTL_FAF); + + time_out = 20; + while (esdhc_read32(>esdhcctl) & ESDHCCTL_FAF) { + if (time_out == 0) { + printf("fsl_esdhc: Flush asynchronous FIFO timeout.\n"); + break; + } + time_out--; + mdelay(1); + } +} + +static void esdhc_tuning_block_enable(struct fsl_esdhc_priv *priv, + bool en) +{ + struct fsl_esdhc *regs = priv->esdhc_regs; + + esdhc_clock_control(priv, false); + esdhc_flush_async_fifo(priv); + if (en) + esdhc_setbits32(>tbctl, TBCTL_TB_EN); + else + esdhc_clrbits32(>tbctl, TBCTL_TB_EN); + esdhc_clock_
[PATCH 1/9] mmc: add a reinit() API
For DM_MMC, the controller re-initialization is needed to clear old configuration for mmc rescan. Signed-off-by: Yangbo Lu --- drivers/mmc/mmc-uclass.c | 15 +++ drivers/mmc/mmc.c| 8 ++-- include/mmc.h| 10 ++ 3 files changed, 31 insertions(+), 2 deletions(-) diff --git a/drivers/mmc/mmc-uclass.c b/drivers/mmc/mmc-uclass.c index c5b7872..b9f0880 100644 --- a/drivers/mmc/mmc-uclass.c +++ b/drivers/mmc/mmc-uclass.c @@ -170,6 +170,21 @@ int mmc_deferred_probe(struct mmc *mmc) return dm_mmc_deferred_probe(mmc->dev); } +int dm_mmc_reinit(struct udevice *dev) +{ + struct dm_mmc_ops *ops = mmc_get_ops(dev); + + if (ops->reinit) + return ops->reinit(dev); + + return 0; +} + +int mmc_reinit(struct mmc *mmc) +{ + return dm_mmc_reinit(mmc->dev); +} + int mmc_of_parse(struct udevice *dev, struct mmc_config *cfg) { int val; diff --git a/drivers/mmc/mmc.c b/drivers/mmc/mmc.c index 50f47d4..a53f93a 100644 --- a/drivers/mmc/mmc.c +++ b/drivers/mmc/mmc.c @@ -2813,13 +2813,17 @@ int mmc_get_op_cond(struct mmc *mmc) return err; #if CONFIG_IS_ENABLED(DM_MMC) - /* The device has already been probed ready for use */ + /* +* Re-initialization is needed to clear old configuration for +* mmc rescan. +*/ + err = mmc_reinit(mmc); #else /* made sure it's not NULL earlier */ err = mmc->cfg->ops->init(mmc); +#endif if (err) return err; -#endif mmc->ddr_mode = 0; retry: diff --git a/include/mmc.h b/include/mmc.h index 8256219..161b8bc 100644 --- a/include/mmc.h +++ b/include/mmc.h @@ -422,6 +422,14 @@ struct dm_mmc_ops { */ int (*deferred_probe)(struct udevice *dev); /** +* reinit() - Re-initialization to clear old configuration for +* mmc rescan. +* +* @dev:Device to reinit +* @return 0 if Ok, -ve if error +*/ + int (*reinit)(struct udevice *dev); + /** * send_cmd() - Send a command to the MMC device * * @dev:Device to receive the command @@ -518,6 +526,7 @@ int dm_mmc_execute_tuning(struct udevice *dev, uint opcode); int dm_mmc_wait_dat0(struct udevice *dev, int state, int timeout_us); int dm_mmc_host_power_cycle(struct udevice *dev); int dm_mmc_deferred_probe(struct udevice *dev); +int dm_mmc_reinit(struct udevice *dev); int dm_mmc_get_b_max(struct udevice *dev, void *dst, lbaint_t blkcnt); /* Transition functions for compatibility */ @@ -529,6 +538,7 @@ int mmc_wait_dat0(struct mmc *mmc, int state, int timeout_us); int mmc_set_enhanced_strobe(struct mmc *mmc); int mmc_host_power_cycle(struct mmc *mmc); int mmc_deferred_probe(struct mmc *mmc); +int mmc_reinit(struct mmc *mmc); int mmc_get_b_max(struct mmc *mmc, void *dst, lbaint_t blkcnt); #else -- 2.7.4
[PATCH 0/9] mmc: fsl_esdhc: support eMMC HS200/HS400 modes
This patch-set is to support eMMC HS200 and HS400 speed modes for eSDHC, and enable them on LX2160ARDB board. CI build link https://travis-ci.org/github/yangbolu1991/u-boot-test/builds/708215558 Yangbo Lu (9): mmc: add a reinit() API mmc: fsl_esdhc: add a reinit() callback mmc: fsl_esdhc: support tuning for eMMC HS200 mmc: fsl_esdhc: clean TBCTL[TB_EN] manually during init mmc: add a hs400_tuning flag mmc: add a mmc_hs400_prepare_ddr() interface mmc: fsl_esdhc: support eMMC HS400 mode arm: dts: lx2160ardb: support eMMC HS400 mode configs: lx2160ardb: enable eMMC HS400 mode support arch/arm/dts/fsl-lx2160a-rdb.dts | 2 + configs/lx2160ardb_tfa_SECURE_BOOT_defconfig | 1 + configs/lx2160ardb_tfa_defconfig | 1 + configs/lx2160ardb_tfa_stmm_defconfig| 1 + drivers/mmc/fsl_esdhc.c | 148 ++- drivers/mmc/mmc-uclass.c | 30 ++ drivers/mmc/mmc.c| 12 ++- include/fsl_esdhc.h | 29 +- include/mmc.h| 26 - 9 files changed, 240 insertions(+), 10 deletions(-) -- 2.7.4
[PATCH 2/4] Move eSDHC adapter card identification to board files
The eSDHC adapter card identification and multiplexing configuration through FPGA had been implemented in both common mmc driver and fsl_esdhc driver. However it is proper to move these code to board files and do it during board initialization. The FPGA registers are also board specific. This patch is to move eSDHC adapter card identification and multiplexing configuration from mmc driver to specific board files. And the option CONFIG_FSL_ESDHC_ADAPTER_IDENT is no longer needed. Signed-off-by: Yangbo Lu --- board/freescale/common/qixis.h | 3 +-- board/freescale/t1040qds/t1040qds.c | 29 +++- board/freescale/t208xqds/t208xqds.c | 29 +++- doc/README.fsl-esdhc| 14 -- drivers/mmc/fsl_esdhc.c | 38 - drivers/mmc/mmc-uclass.c| 4 +--- drivers/mmc/mmc.c | 7 +-- drivers/mmc/mmc_legacy.c| 7 +-- drivers/mmc/mmc_private.h | 4 +--- include/configs/T1040QDS.h | 1 - include/configs/T208xQDS.h | 1 - include/fsl_esdhc.h | 4 scripts/config_whitelist.txt| 1 - 13 files changed, 61 insertions(+), 81 deletions(-) diff --git a/board/freescale/common/qixis.h b/board/freescale/common/qixis.h index c11062e..ac5abc3 100644 --- a/board/freescale/common/qixis.h +++ b/board/freescale/common/qixis.h @@ -1,6 +1,7 @@ /* SPDX-License-Identifier: GPL-2.0+ */ /* * Copyright 2011 Freescale Semiconductor + * Copyright 2020 NXP * Author: Shengzhou Liu * * This file provides support for the QIXIS of some Freescale reference boards. @@ -115,7 +116,6 @@ void qixis_write_i2c(unsigned int reg, u8 value); #endif /* Use for SDHC adapter card type identification and operation */ -#ifdef CONFIG_FSL_ESDHC_ADAPTER_IDENT #define QIXIS_SDID_MASK 0x07 #define QIXIS_ESDHC_ADAPTER_TYPE_EMMC45 0x1/* eMMC Card Rev4.5 */ #define QIXIS_ESDHC_ADAPTER_TYPE_SDMMC_LEGACY 0x2/* SD/MMC Legacy Card */ @@ -131,6 +131,5 @@ void qixis_write_i2c(unsigned int reg, u8 value); #define QIXIS_DAT4 0X01 #define QIXIS_EVDD_BY_SDHC_VS 0x0c -#endif #endif diff --git a/board/freescale/t1040qds/t1040qds.c b/board/freescale/t1040qds/t1040qds.c index cf38d84..18eb395 100644 --- a/board/freescale/t1040qds/t1040qds.c +++ b/board/freescale/t1040qds/t1040qds.c @@ -131,6 +131,33 @@ static void qe_board_setup(void) } } +static void esdhc_adapter_card_ident(void) +{ + u8 card_id, value; + + card_id = QIXIS_READ(present) & QIXIS_SDID_MASK; + + switch (card_id) { + case QIXIS_ESDHC_ADAPTER_TYPE_EMMC45: + value = QIXIS_READ(brdcfg[5]); + value |= (QIXIS_DAT4 | QIXIS_DAT5_6_7); + QIXIS_WRITE(brdcfg[5], value); + break; + case QIXIS_ESDHC_ADAPTER_TYPE_SDMMC_LEGACY: + value = QIXIS_READ(pwr_ctl[1]); + value |= QIXIS_EVDD_BY_SDHC_VS; + QIXIS_WRITE(pwr_ctl[1], value); + break; + case QIXIS_ESDHC_ADAPTER_TYPE_EMMC44: + value = QIXIS_READ(brdcfg[5]); + value |= (QIXIS_SDCLKIN | QIXIS_SDCLKOUT); + QIXIS_WRITE(brdcfg[5], value); + break; + default: + break; + } +} + int board_early_init_f(void) { #if defined(CONFIG_DEEP_SLEEP) @@ -170,7 +197,7 @@ int board_early_init_r(void) 0, flash_esel, BOOKE_PAGESZ_256M, 1); #endif select_i2c_ch_pca9547(I2C_MUX_CH_DEFAULT, 0); - + esdhc_adapter_card_ident(); return 0; } diff --git a/board/freescale/t208xqds/t208xqds.c b/board/freescale/t208xqds/t208xqds.c index 4d980e1..88169ae 100644 --- a/board/freescale/t208xqds/t208xqds.c +++ b/board/freescale/t208xqds/t208xqds.c @@ -345,6 +345,33 @@ int brd_mux_lane_to_slot(void) return 0; } +static void esdhc_adapter_card_ident(void) +{ + u8 card_id, value; + + card_id = QIXIS_READ(present) & QIXIS_SDID_MASK; + + switch (card_id) { + case QIXIS_ESDHC_ADAPTER_TYPE_EMMC45: + value = QIXIS_READ(brdcfg[5]); + value |= (QIXIS_DAT4 | QIXIS_DAT5_6_7); + QIXIS_WRITE(brdcfg[5], value); + break; + case QIXIS_ESDHC_ADAPTER_TYPE_SDMMC_LEGACY: + value = QIXIS_READ(pwr_ctl[1]); + value |= QIXIS_EVDD_BY_SDHC_VS; + QIXIS_WRITE(pwr_ctl[1], value); + break; + case QIXIS_ESDHC_ADAPTER_TYPE_EMMC44: + value = QIXIS_READ(brdcfg[5]); + value |= (QIXIS_SDCLKIN | QIXIS_SDCLKOUT); + QIXIS_WRITE(brdcfg[5], value); + break; + default: + break; + } +} + int board_early_init_r(void) { const unsigned int flashbase = CONFIG_SYS_FLASH_BASE; @@ -384,7 +411,7 @@ int board_early_ini
[PATCH 4/4] configs: lx2160aqds: enable CONFIG_BOARD_EARLY_INIT_R
Enable CONFIG_BOARD_EARLY_INIT_R for SDHC adapter card identification and configuration. Signed-off-by: Yangbo Lu --- configs/lx2160aqds_tfa_SECURE_BOOT_defconfig | 1 + configs/lx2160aqds_tfa_defconfig | 1 + 2 files changed, 2 insertions(+) diff --git a/configs/lx2160aqds_tfa_SECURE_BOOT_defconfig b/configs/lx2160aqds_tfa_SECURE_BOOT_defconfig index 51d5dc3..50635d2 100644 --- a/configs/lx2160aqds_tfa_SECURE_BOOT_defconfig +++ b/configs/lx2160aqds_tfa_SECURE_BOOT_defconfig @@ -18,6 +18,7 @@ CONFIG_OF_STDOUT_VIA_ALIAS=y CONFIG_USE_BOOTARGS=y CONFIG_BOOTARGS="console=ttyAMA0,115200 root=/dev/ram0 earlycon=pl011,mmio32,0x21c ramdisk_size=0x200 default_hugepagesz=1024m hugepagesz=1024m hugepages=2 pci=pcie_bus_perf" # CONFIG_USE_BOOTCOMMAND is not set +CONFIG_BOARD_EARLY_INIT_R=y CONFIG_MISC_INIT_R=y CONFIG_CMD_GREPENV=y CONFIG_CMD_EEPROM=y diff --git a/configs/lx2160aqds_tfa_defconfig b/configs/lx2160aqds_tfa_defconfig index 716c089..2eb944e 100644 --- a/configs/lx2160aqds_tfa_defconfig +++ b/configs/lx2160aqds_tfa_defconfig @@ -20,6 +20,7 @@ CONFIG_BOOTDELAY=10 CONFIG_USE_BOOTARGS=y CONFIG_BOOTARGS="console=ttyAMA0,115200 root=/dev/ram0 earlycon=pl011,mmio32,0x21c ramdisk_size=0x200 default_hugepagesz=1024m hugepagesz=1024m hugepages=2 pci=pcie_bus_perf" # CONFIG_USE_BOOTCOMMAND is not set +CONFIG_BOARD_EARLY_INIT_R=y CONFIG_MISC_INIT_R=y CONFIG_CMD_GREPENV=y CONFIG_CMD_EEPROM=y -- 2.7.4
[PATCH 0/4] Move eSDHC adapter card code to board files
The eSDHC adapter card identification and multiplexing configuration through FPGA had been implemented in both common mmc driver and fsl_esdhc driver. However it is proper to move these code to board files and do it during board initialization. The FPGA registers are also board specific. This patch-set is to move eSDHC adapter card identification and multiplexing configuration from mmc driver to specific board files. Add eSDHC adapter card identification for LX2 QDS. And the option CONFIG_FSL_ESDHC_ADAPTER_IDENT is no longer needed. CI build result https://travis-ci.org/github/yangbolu1991/u-boot-test/builds/699180417 Yangbo Lu (4): Drop global data sdhc_adapter for powerpc Move eSDHC adapter card identification to board files board: fsl: lx2160aqds: identify SDHC adapter during board init configs: lx2160aqds: enable CONFIG_BOARD_EARLY_INIT_R arch/powerpc/include/asm/global_data.h | 4 +-- board/freescale/common/qixis.h | 14 +++--- board/freescale/lx2160a/lx2160a.c| 36 +++-- board/freescale/t1040qds/t1040qds.c | 29 - board/freescale/t208xqds/t208xqds.c | 29 - configs/lx2160aqds_tfa_SECURE_BOOT_defconfig | 1 + configs/lx2160aqds_tfa_defconfig | 1 + doc/README.fsl-esdhc | 14 -- drivers/mmc/fsl_esdhc.c | 39 drivers/mmc/mmc-uclass.c | 4 +-- drivers/mmc/mmc.c| 7 + drivers/mmc/mmc_legacy.c | 7 + drivers/mmc/mmc_private.h| 4 +-- include/configs/T1040QDS.h | 1 - include/configs/T208xQDS.h | 1 - include/fsl_esdhc.h | 4 --- scripts/config_whitelist.txt | 1 - 17 files changed, 108 insertions(+), 88 deletions(-) -- 2.7.4
[PATCH 1/4] Drop global data sdhc_adapter for powerpc
The sdhc_adapter of global data has not been used, and we do not have to use it as global data even we may need it in the future. Signed-off-by: Yangbo Lu --- arch/powerpc/include/asm/global_data.h | 4 +--- drivers/mmc/fsl_esdhc.c| 1 - 2 files changed, 1 insertion(+), 4 deletions(-) diff --git a/arch/powerpc/include/asm/global_data.h b/arch/powerpc/include/asm/global_data.h index 1620fba..192a02d 100644 --- a/arch/powerpc/include/asm/global_data.h +++ b/arch/powerpc/include/asm/global_data.h @@ -1,6 +1,7 @@ /* SPDX-License-Identifier: GPL-2.0+ */ /* * (C) Copyright 2002-2010 + * Copyright 2020 NXP * Wolfgang Denk, DENX Software Engineering, w...@denx.de. */ @@ -15,9 +16,6 @@ struct arch_global_data { #if defined(CONFIG_FSL_ESDHC) u32 sdhc_clk; u32 sdhc_per_clk; -#if defined(CONFIG_FSL_ESDHC_ADAPTER_IDENT) - u8 sdhc_adapter; -#endif #endif #if defined(CONFIG_MPC8xx) unsigned long brg_clk; diff --git a/drivers/mmc/fsl_esdhc.c b/drivers/mmc/fsl_esdhc.c index a4b923a..38cbca1 100644 --- a/drivers/mmc/fsl_esdhc.c +++ b/drivers/mmc/fsl_esdhc.c @@ -678,7 +678,6 @@ void mmc_adapter_card_type_ident(void) u8 value; card_id = QIXIS_READ(present) & QIXIS_SDID_MASK; - gd->arch.sdhc_adapter = card_id; switch (card_id) { case QIXIS_ESDHC_ADAPTER_TYPE_EMMC45: -- 2.7.4
[PATCH 3/4] board: fsl: lx2160aqds: identify SDHC adapter during board init
Add support for SDHC adapter identification and configuration during board init. Signed-off-by: Yangbo Lu --- board/freescale/common/qixis.h| 11 ++- board/freescale/lx2160a/lx2160a.c | 36 ++-- 2 files changed, 44 insertions(+), 3 deletions(-) diff --git a/board/freescale/common/qixis.h b/board/freescale/common/qixis.h index ac5abc3..93638d2 100644 --- a/board/freescale/common/qixis.h +++ b/board/freescale/common/qixis.h @@ -36,7 +36,12 @@ struct qixis { u8 gdc; u8 gdd; /* DCM Debug Data Register,0x17 */ u8 dmack; - u8 res1[6]; + u8 res1; + u8 sdhc1; + u8 sdhc2; + u8 stat_pres3; + u8 los_stat; + u8 usb_ctl; u8 watch; /* Watchdog Register,0x1F */ u8 pwr_ctl[2]; /* Power Control Register,0x20 */ u8 res2[2]; @@ -117,6 +122,7 @@ void qixis_write_i2c(unsigned int reg, u8 value); /* Use for SDHC adapter card type identification and operation */ #define QIXIS_SDID_MASK 0x07 + #define QIXIS_ESDHC_ADAPTER_TYPE_EMMC45 0x1/* eMMC Card Rev4.5 */ #define QIXIS_ESDHC_ADAPTER_TYPE_SDMMC_LEGACY 0x2/* SD/MMC Legacy Card */ #define QIXIS_ESDHC_ADAPTER_TYPE_EMMC44 0x3/* eMMC Card Rev4.4 */ @@ -125,6 +131,9 @@ void qixis_write_i2c(unsigned int reg, u8 value); #define QIXIS_ESDHC_ADAPTER_TYPE_SD 0x6/* SD Card Rev2.0 3.0 */ #define QIXIS_ESDHC_NO_ADAPTER 0x7/* No Card is Present*/ +#define QIXIS_SDHC1_S1V3 0x80/* SDHC1: SDHC1 3.3V power control */ +#define QIXIS_SDHC1_VS 0x30/* BRDCFG11: route to SDHC1_VS */ + #define QIXIS_SDCLKIN 0x08 #define QIXIS_SDCLKOUT 0x02 #define QIXIS_DAT5_6_7 0X02 diff --git a/board/freescale/lx2160a/lx2160a.c b/board/freescale/lx2160a/lx2160a.c index 73e05ee..97e72b1 100644 --- a/board/freescale/lx2160a/lx2160a.c +++ b/board/freescale/lx2160a/lx2160a.c @@ -18,6 +18,7 @@ #include #include #include +#include #include #include #include @@ -379,7 +380,7 @@ int checkboard(void) */ u8 qixis_esdhc_detect_quirk(void) { - /* for LX2160AQDS res1[1] @ offset 0x1A is SDHC1 Control/Status (SDHC1) + /* * SDHC1 Card ID: * Specifies the type of card installed in the SDHC1 adapter slot. * 000= (reserved) @@ -391,10 +392,35 @@ u8 qixis_esdhc_detect_quirk(void) * 110= SDCard V2/V3 adapter installed. * 111= no adapter is installed. */ - return ((QIXIS_READ(res1[1]) & QIXIS_SDID_MASK) != + return ((QIXIS_READ(sdhc1) & QIXIS_SDID_MASK) != QIXIS_ESDHC_NO_ADAPTER); } +static void esdhc_adapter_card_ident(void) +{ + u8 card_id, val; + + val = QIXIS_READ(sdhc1); + card_id = val & QIXIS_SDID_MASK; + + switch (card_id) { + case QIXIS_ESDHC_ADAPTER_TYPE_SD: + /* Power cycle to card */ + val &= ~QIXIS_SDHC1_S1V3; + QIXIS_WRITE(sdhc1, val); + mdelay(1); + val |= QIXIS_SDHC1_S1V3; + QIXIS_WRITE(sdhc1, val); + /* Route to SDHC1_VS */ + val = QIXIS_READ(brdcfg[11]); + val |= QIXIS_SDHC1_VS; + QIXIS_WRITE(brdcfg[11], val); + break; + default: + break; + } +} + int config_board_mux(void) { u8 reg11, reg5, reg13; @@ -501,6 +527,12 @@ int config_board_mux(void) return 0; } + +int board_early_init_r(void) +{ + esdhc_adapter_card_ident(); + return 0; +} #elif defined(CONFIG_TARGET_LX2160ARDB) int config_board_mux(void) { -- 2.7.4
[v2, 1/2] mmc: fsl_esdhc: read register once for card inserted status
No need to poll register for card inserted status. Signed-off-by: Yangbo Lu --- Changes for v2: - Updated copyright. --- drivers/mmc/fsl_esdhc.c | 9 - 1 file changed, 4 insertions(+), 5 deletions(-) diff --git a/drivers/mmc/fsl_esdhc.c b/drivers/mmc/fsl_esdhc.c index 386781d..02d9230 100644 --- a/drivers/mmc/fsl_esdhc.c +++ b/drivers/mmc/fsl_esdhc.c @@ -1,7 +1,7 @@ // SPDX-License-Identifier: GPL-2.0+ /* * Copyright 2007, 2010-2011 Freescale Semiconductor, Inc - * Copyright 2019 NXP Semiconductors + * Copyright 2019-2020 NXP * Andy Fleming * * Based vaguely on the pxa mmc code: @@ -627,16 +627,15 @@ static int esdhc_init_common(struct fsl_esdhc_priv *priv, struct mmc *mmc) static int esdhc_getcd_common(struct fsl_esdhc_priv *priv) { struct fsl_esdhc *regs = priv->esdhc_regs; - int timeout = 1000; #ifdef CONFIG_ESDHC_DETECT_QUIRK if (CONFIG_ESDHC_DETECT_QUIRK) return 1; #endif - while (!(esdhc_read32(>prsstat) & PRSSTAT_CINS) && --timeout) - udelay(1000); + if (esdhc_read32(>prsstat) & PRSSTAT_CINS) + return 1; - return timeout > 0; + return 0; } static void fsl_esdhc_get_cfg_common(struct fsl_esdhc_priv *priv, -- 2.7.4
[v2, 2/2] mmc: fsl_esdhc: workaround for hardware 3.3v IO reliability issue
When eSDHC operates at 3.3v, damage can accumulate in an internal level shifter at a higher than expected rate. The faster the interface runs, the more damage accumulates. This issue now is found on LX2160A eSDHC1 for only SD card. The hardware workaround is recommended to use an on-board level shifter that is 1.8v on SoC side and 3.3v on SD card side. For boards without hardware workaround, this option could be enabled, ensuring 1.8v IO voltage and disabling eSDHC if no card. This option assumes no hotplug, and u-boot has to make all the way to to linux to use 1.8v UHS-I speed mode if has card. If you do not want the workaround for better user experience, of course you can choose to not select it running eSDHC in unsafe mode. Signed-off-by: Yangbo Lu --- Changes for v2: - Updated copyright. --- drivers/mmc/Kconfig | 15 +++ drivers/mmc/fsl_esdhc.c | 38 -- include/fsl_esdhc.h | 2 ++ 3 files changed, 53 insertions(+), 2 deletions(-) diff --git a/drivers/mmc/Kconfig b/drivers/mmc/Kconfig index 3c4f057..8f56572 100644 --- a/drivers/mmc/Kconfig +++ b/drivers/mmc/Kconfig @@ -727,6 +727,21 @@ config FSL_ESDHC This selects support for the eSDHC (Enhanced Secure Digital Host Controller) found on numerous Freescale/NXP SoCs. +config FSL_ESDHC_33V_IO_RELIABILITY_WORKAROUND + bool "enable eSDHC workaround for 3.3v IO reliability issue" + depends on FSL_ESDHC && DM_MMC + default n + help + When eSDHC operates at 3.3v, damage can accumulate in an internal + level shifter at a higher than expected rate. The faster the interface + runs, the more damage accumulates. This issue now is found on LX2160A + eSDHC1 for only SD card. The hardware workaround is recommended to use + an on-board level shifter that is 1.8v on SoC side and 3.3v on SD card + side. For boards without hardware workaround, this option could be + enabled, ensuring 1.8v IO voltage and disabling eSDHC if no card. + This option assumes no hotplug, and u-boot has to make all the way to + to linux to use 1.8v UHS-I speed mode if has card. + config FSL_ESDHC_IMX bool "Freescale/NXP i.MX eSDHC controller support" help diff --git a/drivers/mmc/fsl_esdhc.c b/drivers/mmc/fsl_esdhc.c index 02d9230..98da568 100644 --- a/drivers/mmc/fsl_esdhc.c +++ b/drivers/mmc/fsl_esdhc.c @@ -720,13 +720,38 @@ __weak int esdhc_status_fixup(void *blob, const char *compat) return 0; } +#ifdef CONFIG_FSL_ESDHC_33V_IO_RELIABILITY_WORKAROUND +static int fsl_esdhc_get_cd(struct udevice *dev); + +static void esdhc_disable_for_no_card(void *blob) +{ + struct udevice *dev; + + for (uclass_first_device(UCLASS_MMC, ); +dev; +uclass_next_device()) { + char esdhc_path[50]; + + if (fsl_esdhc_get_cd(dev)) + continue; + + snprintf(esdhc_path, sizeof(esdhc_path), "/soc/esdhc@%lx", +(unsigned long)dev_read_addr(dev)); + do_fixup_by_path(blob, esdhc_path, "status", "disabled", +sizeof("disabled"), 1); + } +} +#endif + void fdt_fixup_esdhc(void *blob, bd_t *bd) { const char *compat = "fsl,esdhc"; if (esdhc_status_fixup(blob, compat)) return; - +#ifdef CONFIG_FSL_ESDHC_33V_IO_RELIABILITY_WORKAROUND + esdhc_disable_for_no_card(blob); +#endif do_fixup_by_compat_u32(blob, compat, "clock-frequency", gd->arch.sdhc_clk, 1); } @@ -845,6 +870,7 @@ static int fsl_esdhc_probe(struct udevice *dev) struct fsl_esdhc_priv *priv = dev_get_priv(dev); fdt_addr_t addr; struct mmc *mmc; + int ret; addr = dev_read_addr(dev); if (addr == FDT_ADDR_T_NONE) @@ -878,7 +904,15 @@ static int fsl_esdhc_probe(struct udevice *dev) upriv->mmc = mmc; - return esdhc_init_common(priv, mmc); + ret = esdhc_init_common(priv, mmc); + if (ret) + return ret; + +#ifdef CONFIG_FSL_ESDHC_33V_IO_RELIABILITY_WORKAROUND + if (!fsl_esdhc_get_cd(dev)) + esdhc_setbits32(>esdhc_regs->proctl, PROCTL_VOLT_SEL); +#endif + return 0; } static int fsl_esdhc_get_cd(struct udevice *dev) diff --git a/include/fsl_esdhc.h b/include/fsl_esdhc.h index 8e8cd2c..e148eaa 100644 --- a/include/fsl_esdhc.h +++ b/include/fsl_esdhc.h @@ -4,6 +4,7 @@ *--- * * Copyright 2007-2008,2010-2011 Freescale Semiconductor, Inc + * Copyright 2020 NXP */ #ifndef __FSL_ESDHC_H__ @@ -98,6 +99,7 @@ #define PROCTL_DTW_4 0x0002 #define PROCTL_DTW_8 0x0004 #define PROCTL_D3CD0x
[PATCH] mmc: fsl_esdhc: workaround for hardware 3.3v IO reliability issue
When eSDHC operates at 3.3v, damage can accumulate in an internal level shifter at a higher than expected rate. The faster the interface runs, the more damage accumulates. This issue now is found on LX2160A eSDHC1 for only SD card. The hardware workaround is recommended to use an on-board level shifter that is 1.8v on SoC side and 3.3v on SD card side. For boards without hardware workaround, this option could be enabled, ensuring 1.8v IO voltage and disabling eSDHC if no card. This option assumes no hotplug, and u-boot has to make all the way to to linux to use 1.8v UHS-I speed mode if has card. If you do not want the workaround for better user experience, of course you can choose to not select it running eSDHC in unsafe mode. Signed-off-by: Yangbo Lu --- drivers/mmc/Kconfig | 15 +++ drivers/mmc/fsl_esdhc.c | 38 -- include/fsl_esdhc.h | 1 + 3 files changed, 52 insertions(+), 2 deletions(-) diff --git a/drivers/mmc/Kconfig b/drivers/mmc/Kconfig index 8f0df56..b783f3f 100644 --- a/drivers/mmc/Kconfig +++ b/drivers/mmc/Kconfig @@ -727,6 +727,21 @@ config FSL_ESDHC This selects support for the eSDHC (Enhanced Secure Digital Host Controller) found on numerous Freescale/NXP SoCs. +config FSL_ESDHC_33V_IO_RELIABILITY_WORKAROUND + bool "enable eSDHC workaround for 3.3v IO reliability issue" + depends on FSL_ESDHC && DM_MMC + default n + help + When eSDHC operates at 3.3v, damage can accumulate in an internal + level shifter at a higher than expected rate. The faster the interface + runs, the more damage accumulates. This issue now is found on LX2160A + eSDHC1 for only SD card. The hardware workaround is recommended to use + an on-board level shifter that is 1.8v on SoC side and 3.3v on SD card + side. For boards without hardware workaround, this option could be + enabled, ensuring 1.8v IO voltage and disabling eSDHC if no card. + This option assumes no hotplug, and u-boot has to make all the way to + to linux to use 1.8v UHS-I speed mode if has card. + config FSL_ESDHC_IMX bool "Freescale/NXP i.MX eSDHC controller support" help diff --git a/drivers/mmc/fsl_esdhc.c b/drivers/mmc/fsl_esdhc.c index 386781d..e64ea76 100644 --- a/drivers/mmc/fsl_esdhc.c +++ b/drivers/mmc/fsl_esdhc.c @@ -721,13 +721,38 @@ __weak int esdhc_status_fixup(void *blob, const char *compat) return 0; } +#ifdef CONFIG_FSL_ESDHC_33V_IO_RELIABILITY_WORKAROUND +static int fsl_esdhc_get_cd(struct udevice *dev); + +static void esdhc_disable_for_no_card(void *blob) +{ + struct udevice *dev; + + for (uclass_first_device(UCLASS_MMC, ); +dev; +uclass_next_device()) { + char esdhc_path[50]; + + if (fsl_esdhc_get_cd(dev)) + continue; + + snprintf(esdhc_path, sizeof(esdhc_path), "/soc/esdhc@%lx", +(unsigned long)dev_read_addr(dev)); + do_fixup_by_path(blob, esdhc_path, "status", "disabled", +sizeof("disabled"), 1); + } +} +#endif + void fdt_fixup_esdhc(void *blob, bd_t *bd) { const char *compat = "fsl,esdhc"; if (esdhc_status_fixup(blob, compat)) return; - +#ifdef CONFIG_FSL_ESDHC_33V_IO_RELIABILITY_WORKAROUND + esdhc_disable_for_no_card(blob); +#endif do_fixup_by_compat_u32(blob, compat, "clock-frequency", gd->arch.sdhc_clk, 1); } @@ -846,6 +871,7 @@ static int fsl_esdhc_probe(struct udevice *dev) struct fsl_esdhc_priv *priv = dev_get_priv(dev); fdt_addr_t addr; struct mmc *mmc; + int ret; addr = dev_read_addr(dev); if (addr == FDT_ADDR_T_NONE) @@ -879,7 +905,15 @@ static int fsl_esdhc_probe(struct udevice *dev) upriv->mmc = mmc; - return esdhc_init_common(priv, mmc); + ret = esdhc_init_common(priv, mmc); + if (ret) + return ret; + +#ifdef CONFIG_FSL_ESDHC_33V_IO_RELIABILITY_WORKAROUND + if (!fsl_esdhc_get_cd(dev)) + esdhc_setbits32(>esdhc_regs->proctl, PROCTL_VOLT_SEL); +#endif + return 0; } static int fsl_esdhc_get_cd(struct udevice *dev) diff --git a/include/fsl_esdhc.h b/include/fsl_esdhc.h index 8e8cd2c..865a214 100644 --- a/include/fsl_esdhc.h +++ b/include/fsl_esdhc.h @@ -98,6 +98,7 @@ #define PROCTL_DTW_4 0x0002 #define PROCTL_DTW_8 0x0004 #define PROCTL_D3CD0x0008 +#define PROCTL_VOLT_SEL0x0400 #define CMDARG 0x0002e008 -- 2.7.4
[PATCH] mmc: fsl_esdhc: read register once for card inserted status
No need to poll register for card inserted status. Signed-off-by: Yangbo Lu --- drivers/mmc/fsl_esdhc.c | 7 +++ 1 file changed, 3 insertions(+), 4 deletions(-) diff --git a/drivers/mmc/fsl_esdhc.c b/drivers/mmc/fsl_esdhc.c index e64ea76..7e8993f 100644 --- a/drivers/mmc/fsl_esdhc.c +++ b/drivers/mmc/fsl_esdhc.c @@ -627,16 +627,15 @@ static int esdhc_init_common(struct fsl_esdhc_priv *priv, struct mmc *mmc) static int esdhc_getcd_common(struct fsl_esdhc_priv *priv) { struct fsl_esdhc *regs = priv->esdhc_regs; - int timeout = 1000; #ifdef CONFIG_ESDHC_DETECT_QUIRK if (CONFIG_ESDHC_DETECT_QUIRK) return 1; #endif - while (!(esdhc_read32(>prsstat) & PRSSTAT_CINS) && --timeout) - udelay(1000); + if (esdhc_read32(>prsstat) & PRSSTAT_CINS) + return 1; - return timeout > 0; + return 0; } static void fsl_esdhc_get_cfg_common(struct fsl_esdhc_priv *priv, -- 2.7.4
[PATCH] board: fsl: lx2160a: fix SDHC1_DAT4 signal routing
The SDHC1_DAT4 signal could be routes to SDHC1_VS or SDHC1 adapter slot for SDHC1 usage. When SDHC1 is selected in RCW, do not force to route it to SDHC1 adapter slot if find it has already been configued for SDHC1_VS. Signed-off-by: Yangbo Lu --- board/freescale/lx2160a/lx2160a.c | 12 +--- 1 file changed, 9 insertions(+), 3 deletions(-) diff --git a/board/freescale/lx2160a/lx2160a.c b/board/freescale/lx2160a/lx2160a.c index 103b0cc..5ee46f4 100644 --- a/board/freescale/lx2160a/lx2160a.c +++ b/board/freescale/lx2160a/lx2160a.c @@ -469,10 +469,16 @@ int config_board_mux(void) reg11 = SET_CFG_MUX3_SDHC1_SPI(reg11, 0x01); QIXIS_WRITE(brdcfg[11], reg11); } else { - /* Routes {SDHC1_DAT4} to SDHC1 adapter slot */ + /* +* If {SDHC1_DAT4} has been configured to route to SDHC1_VS, +* do not change it. +* Otherwise route {SDHC1_DAT4} to SDHC1 adapter slot. +*/ reg11 = QIXIS_READ(brdcfg[11]); - reg11 = SET_CFG_MUX2_SDHC1_SPI(reg11, 0x00); - QIXIS_WRITE(brdcfg[11], reg11); + if ((reg11 & 0x30) != 0x30) { + reg11 = SET_CFG_MUX2_SDHC1_SPI(reg11, 0x00); + QIXIS_WRITE(brdcfg[11], reg11); + } /* - Routes {SDHC1_DAT5, SDHC1_DAT6} to SDHC1 adapter slot. * {SDHC1_DAT7, SDHC1_DS } to SDHC1 adapter slot. -- 2.7.4
[PATCH] configs: disable eMMC HS200 support on layerscape platforms
The eMMC HS200 speed mode on Layerscape platforms has not been supported properly. The eSDHC clock tuning has not been implemented by now. So disable it until it is supported properly in case of any potential issues. Signed-off-by: Yangbo Lu --- configs/ls1012ardb_tfa_defconfig | 1 - configs/ls1028ardb_tfa_defconfig | 1 - configs/lx2160ardb_tfa_defconfig | 1 - 3 files changed, 3 deletions(-) diff --git a/configs/ls1012ardb_tfa_defconfig b/configs/ls1012ardb_tfa_defconfig index b47a47d..0e994f5 100644 --- a/configs/ls1012ardb_tfa_defconfig +++ b/configs/ls1012ardb_tfa_defconfig @@ -38,7 +38,6 @@ CONFIG_NET_RANDOM_ETHADDR=y CONFIG_DM=y CONFIG_SATA_CEVA=y CONFIG_DM_MMC=y -CONFIG_MMC_HS200_SUPPORT=y CONFIG_FSL_ESDHC=y CONFIG_MTD=y CONFIG_DM_SPI_FLASH=y diff --git a/configs/ls1028ardb_tfa_defconfig b/configs/ls1028ardb_tfa_defconfig index 3ef5520..7ffd1c3 100644 --- a/configs/ls1028ardb_tfa_defconfig +++ b/configs/ls1028ardb_tfa_defconfig @@ -45,7 +45,6 @@ CONFIG_I2C_DEFAULT_BUS_NUMBER=0 CONFIG_I2C_MUX=y CONFIG_I2C_MUX_PCA954x=y CONFIG_DM_MMC=y -CONFIG_MMC_HS200_SUPPORT=y CONFIG_FSL_ESDHC=y CONFIG_MTD=y CONFIG_DM_SPI_FLASH=y diff --git a/configs/lx2160ardb_tfa_defconfig b/configs/lx2160ardb_tfa_defconfig index b998cb6..0799cd4 100644 --- a/configs/lx2160ardb_tfa_defconfig +++ b/configs/lx2160ardb_tfa_defconfig @@ -41,7 +41,6 @@ CONFIG_DM_I2C=y CONFIG_I2C_SET_DEFAULT_BUS_NUM=y CONFIG_I2C_DEFAULT_BUS_NUMBER=0 CONFIG_DM_MMC=y -CONFIG_MMC_HS200_SUPPORT=y CONFIG_FSL_ESDHC=y CONFIG_MTD=y CONFIG_DM_SPI_FLASH=y -- 2.7.4
[PATCH 3/6] powerpc/mpc85xx: drop eSDHC periperhal clock code
The below patch added eSDHC periperhal clock code initially. 2d9ca2c mmc: fsl_esdhc: Add peripheral clock support The purpose was to fix up device tree properties "peripheral-frequency" so that linux could get the periperhal clock by it. However the implementation on both u-boot and linux was only for a Freescale SDK release. The linux part implementation had never been upstreamed. These code should not have been exist on u-boot mainline. Let's remove the powerpc part changes but keep the changes in fsl_esdhc driver. The changes in fsl_esdhc driver could be utilized to support SD UHS and eMMC HS200/HS400 speed modes for current Layerscape ARM platforms. Signed-off-by: Yangbo Lu --- arch/powerpc/cpu/mpc85xx/speed.c | 49 +-- arch/powerpc/include/asm/config_mpc85xx.h | 8 - include/configs/T1040QDS.h| 1 - include/configs/T208xQDS.h| 1 - include/e500.h| 1 - scripts/config_whitelist.txt | 2 -- 6 files changed, 1 insertion(+), 61 deletions(-) diff --git a/arch/powerpc/cpu/mpc85xx/speed.c b/arch/powerpc/cpu/mpc85xx/speed.c index 15b05fc..0c5252e 100644 --- a/arch/powerpc/cpu/mpc85xx/speed.c +++ b/arch/powerpc/cpu/mpc85xx/speed.c @@ -69,8 +69,7 @@ void get_sys_info(sys_info_t *sys_info) [14] = 4, /* CC4 PPL / 4 */ }; uint i, freq_c_pll[CONFIG_SYS_FSL_NUM_CC_PLLS]; -#if !defined(CONFIG_FM_PLAT_CLK_DIV) || !defined(CONFIG_PME_PLAT_CLK_DIV) || \ - defined(CONFIG_FSL_ESDHC_USE_PERIPHERAL_CLK) +#if !defined(CONFIG_FM_PLAT_CLK_DIV) || !defined(CONFIG_PME_PLAT_CLK_DIV) uint rcw_tmp; #endif uint ratio[CONFIG_SYS_FSL_NUM_CC_PLLS]; @@ -450,48 +449,6 @@ void get_sys_info(sys_info_t *sys_info) #endif #endif -#ifdef CONFIG_FSL_ESDHC_USE_PERIPHERAL_CLK -#if defined(CONFIG_ARCH_T2080) -#define ESDHC_CLK_SEL 0x0007 -#define ESDHC_CLK_SHIFT0 -#define ESDHC_CLK_RCWSR15 -#else /* Support T1040 T1024 by now */ -#define ESDHC_CLK_SEL 0xe000 -#define ESDHC_CLK_SHIFT29 -#define ESDHC_CLK_RCWSR7 -#endif - rcw_tmp = in_be32(>rcwsr[ESDHC_CLK_RCWSR]); - switch ((rcw_tmp & ESDHC_CLK_SEL) >> ESDHC_CLK_SHIFT) { - case 1: - sys_info->freq_sdhc = freq_c_pll[CONFIG_SYS_SDHC_CLK]; - break; - case 2: - sys_info->freq_sdhc = freq_c_pll[CONFIG_SYS_SDHC_CLK] / 2; - break; - case 3: - sys_info->freq_sdhc = freq_c_pll[CONFIG_SYS_SDHC_CLK] / 3; - break; -#if defined(CONFIG_SYS_SDHC_CLK_2_PLL) - case 4: - sys_info->freq_sdhc = freq_c_pll[CONFIG_SYS_SDHC_CLK] / 4; - break; -#if defined(CONFIG_ARCH_T2080) - case 5: - sys_info->freq_sdhc = freq_c_pll[1 - CONFIG_SYS_SDHC_CLK]; - break; -#endif - case 6: - sys_info->freq_sdhc = freq_c_pll[1 - CONFIG_SYS_SDHC_CLK] / 2; - break; - case 7: - sys_info->freq_sdhc = freq_c_pll[1 - CONFIG_SYS_SDHC_CLK] / 3; - break; -#endif - default: - sys_info->freq_sdhc = 0; - printf("Error: Unknown SDHC peripheral clock select!\n"); - } -#endif #else /* CONFIG_SYS_FSL_QORIQ_CHASSIS2 */ for_each_cpu(i, cpu, cpu_numcores(), cpu_mask()) { @@ -673,15 +630,11 @@ int get_clocks (void) gd->arch.i2c2_clk = gd->arch.i2c1_clk; #if defined(CONFIG_FSL_ESDHC) -#ifdef CONFIG_FSL_ESDHC_USE_PERIPHERAL_CLK - gd->arch.sdhc_clk = sys_info.freq_sdhc / 2; -#else #if defined(CONFIG_ARCH_MPC8569) || defined(CONFIG_ARCH_P1010) gd->arch.sdhc_clk = gd->bus_clk; #else gd->arch.sdhc_clk = gd->bus_clk / 2; #endif -#endif #endif /* defined(CONFIG_FSL_ESDHC) */ #if defined(CONFIG_CPM2) diff --git a/arch/powerpc/include/asm/config_mpc85xx.h b/arch/powerpc/include/asm/config_mpc85xx.h index 946e74a..4ca1e2b 100644 --- a/arch/powerpc/include/asm/config_mpc85xx.h +++ b/arch/powerpc/include/asm/config_mpc85xx.h @@ -331,9 +331,6 @@ #define CONFIG_SYS_FMAN_V3 #define CONFIG_FM_PLAT_CLK_DIV 1 #define CONFIG_SYS_FM1_CLK CONFIG_FM_PLAT_CLK_DIV -#define CONFIG_SYS_SDHC_CLK0/* Select SDHC CLK begining from PLL1 - per rcw field value */ -#define CONFIG_SYS_SDHC_CLK_2_PLL /* Select SDHC CLK from 2 PLLs */ #define CONFIG_SYS_FM_MURAM_SIZE 0x3 #define CONFIG_SYS_FSL_SINGLE_SOURCE_CLK #define CONFIG_SYS_FSL_TBCLK_DIV 16 @@ -362,8 +359,6 @@ #define CONFIG_USB_MAX_CONTROLLER_COUNT2 #define CONFIG_SYS_FSL_IFC_BANK_COUNT 8 #define CONFIG_SYS_FM1_CLK 0 -#define CONFIG_SYS_SDHC_CLK0/* Select SDHC CLK begining from PLL1 - per rcw field value */ #define CONFIG_QBMA
[PATCH 1/6] mmc: fsl_esdhc_imx: drop QorIQ eSDHC specific peripheral clock code
Drop QorIQ eSDHC specific peripheral clock code. Signed-off-by: Yangbo Lu --- drivers/mmc/fsl_esdhc_imx.c | 40 1 file changed, 40 deletions(-) diff --git a/drivers/mmc/fsl_esdhc_imx.c b/drivers/mmc/fsl_esdhc_imx.c index f1afab7..e1528e7 100644 --- a/drivers/mmc/fsl_esdhc_imx.c +++ b/drivers/mmc/fsl_esdhc_imx.c @@ -658,35 +658,6 @@ static void set_sysctl(struct fsl_esdhc_priv *priv, struct mmc *mmc, uint clock) priv->clock = clock; } -#ifdef CONFIG_FSL_ESDHC_USE_PERIPHERAL_CLK -static void esdhc_clock_control(struct fsl_esdhc_priv *priv, bool enable) -{ - struct fsl_esdhc *regs = priv->esdhc_regs; - u32 value; - u32 time_out; - - value = esdhc_read32(>sysctl); - - if (enable) - value |= SYSCTL_CKEN; - else - value &= ~SYSCTL_CKEN; - - esdhc_write32(>sysctl, value); - - time_out = 20; - value = PRSSTAT_SDSTB; - while (!(esdhc_read32(>prsstat) & value)) { - if (time_out == 0) { - printf("fsl_esdhc: Internal clock never stabilised.\n"); - break; - } - time_out--; - mdelay(1); - } -} -#endif - #ifdef MMC_SUPPORTS_TUNING static int esdhc_change_pinstate(struct udevice *dev) { @@ -958,12 +929,6 @@ static int esdhc_set_ios_common(struct fsl_esdhc_priv *priv, struct mmc *mmc) int ret __maybe_unused; u32 clock; -#ifdef CONFIG_FSL_ESDHC_USE_PERIPHERAL_CLK - /* Select to use peripheral clock */ - esdhc_clock_control(priv, false); - esdhc_setbits32(>scr, ESDHCCTL_PCS); - esdhc_clock_control(priv, true); -#endif /* Set the clock speed */ clock = mmc->clock; if (clock < mmc->cfg->f_min) @@ -1388,13 +1353,8 @@ void fdt_fixup_esdhc(void *blob, bd_t *bd) if (esdhc_status_fixup(blob, compat)) return; -#ifdef CONFIG_FSL_ESDHC_USE_PERIPHERAL_CLK - do_fixup_by_compat_u32(blob, compat, "peripheral-frequency", - gd->arch.sdhc_clk, 1); -#else do_fixup_by_compat_u32(blob, compat, "clock-frequency", gd->arch.sdhc_clk, 1); -#endif } #endif -- 2.7.4
[PATCH 6/6] Drop CONFIG_FSL_ESDHC_USE_PERIPHERAL_CLK usage
The eSDHC reference clocks should be provided by speed.c in arch/. And we do not need CONFIG_FSL_ESDHC_USE_PERIPHERAL_CLK option to select which clock to use. Because we can make the driver to select the periperhal clock which is better (provides higher frequency) automatically if its value is provided by speed.c. This patch is to drop this option and make driver to select clock automatically. Also fix peripheral clock calculation issue in fsl_lsch2_speed.c/fsl_lsch3_speed.c. Signed-off-by: Yangbo Lu --- .../arm/cpu/armv8/fsl-layerscape/fsl_lsch2_speed.c | 29 +++- .../arm/cpu/armv8/fsl-layerscape/fsl_lsch3_speed.c | 22 +++ drivers/mmc/Kconfig| 9 -- drivers/mmc/fsl_esdhc.c| 32 +++--- 4 files changed, 42 insertions(+), 50 deletions(-) diff --git a/arch/arm/cpu/armv8/fsl-layerscape/fsl_lsch2_speed.c b/arch/arm/cpu/armv8/fsl-layerscape/fsl_lsch2_speed.c index 25e9a49..fec2318 100644 --- a/arch/arm/cpu/armv8/fsl-layerscape/fsl_lsch2_speed.c +++ b/arch/arm/cpu/armv8/fsl-layerscape/fsl_lsch2_speed.c @@ -125,7 +125,6 @@ void get_sys_info(struct sys_info *sys_info) } #endif -#ifdef CONFIG_FSL_ESDHC #define HWA_CGA_M2_CLK_SEL 0x0007 #define HWA_CGA_M2_CLK_SHIFT 0 #if defined(CONFIG_TARGET_LS1046ARDB) || defined(CONFIG_TARGET_LS1043ARDB) @@ -148,11 +147,10 @@ void get_sys_info(struct sys_info *sys_info) break; #endif default: - printf("Error: Unknown peripheral clock select!\n"); + printf("Error: Unknown cluster group A mux 2 clock select!\n"); break; } #endif -#endif #if defined(CONFIG_FSL_IFC) sys_info->freq_localbus = sys_info->freq_systembus / @@ -179,28 +177,21 @@ unsigned long get_qman_freq(void) int get_clocks(void) { struct sys_info sys_info; - +#ifdef CONFIG_FSL_ESDHC + u32 clock = 0; +#endif get_sys_info(_info); gd->cpu_clk = sys_info.freq_processor[0]; gd->bus_clk = sys_info.freq_systembus / CONFIG_SYS_FSL_PCLK_DIV; gd->mem_clk = sys_info.freq_ddrbus; - #ifdef CONFIG_FSL_ESDHC -#if defined(CONFIG_FSL_ESDHC_USE_PERIPHERAL_CLK) -#if defined(CONFIG_TARGET_LS1046ARDB) - gd->arch.sdhc_clk = sys_info.freq_cga_m2 / 2; -#endif -#if defined(CONFIG_TARGET_LS1043ARDB) - gd->arch.sdhc_clk = sys_info.freq_cga_m2; -#endif -#if defined(CONFIG_TARGET_LS1012ARDB) - gd->arch.sdhc_clk = sys_info.freq_systembus; -#endif -#else - gd->arch.sdhc_clk = (sys_info.freq_systembus / - CONFIG_SYS_FSL_PCLK_DIV) / - CONFIG_SYS_FSL_SDHC_CLK_DIV; +#if defined(CONFIG_ARCH_LS1012A) + clock = sys_info.freq_systembus; +#elif defined(CONFIG_ARCH_LS1043A) || defined(CONFIG_ARCH_LS1046A) + clock = sys_info.freq_cga_m2; #endif + gd->arch.sdhc_per_clk = clock / CONFIG_SYS_FSL_SDHC_CLK_DIV; + gd->arch.sdhc_clk = gd->bus_clk / CONFIG_SYS_FSL_SDHC_CLK_DIV; #endif if (gd->cpu_clk != 0) return 0; diff --git a/arch/arm/cpu/armv8/fsl-layerscape/fsl_lsch3_speed.c b/arch/arm/cpu/armv8/fsl-layerscape/fsl_lsch3_speed.c index 4b047a3..bd8b9cb 100644 --- a/arch/arm/cpu/armv8/fsl-layerscape/fsl_lsch3_speed.c +++ b/arch/arm/cpu/armv8/fsl-layerscape/fsl_lsch3_speed.c @@ -160,14 +160,14 @@ void get_sys_info(struct sys_info *sys_info) break; } #endif -#if defined(CONFIG_ARCH_LX2160A) || defined(CONFIG_ARCH_LS2080A) - sys_info->freq_cga_m2 = sys_info->freq_systembus; -#endif } int get_clocks(void) { struct sys_info sys_info; +#ifdef CONFIG_FSL_ESDHC + u32 clock = 0; +#endif get_sys_info(_info); gd->cpu_clk = sys_info.freq_processor[0]; gd->bus_clk = sys_info.freq_systembus / CONFIG_SYS_FSL_PCLK_DIV; @@ -175,18 +175,16 @@ int get_clocks(void) #ifdef CONFIG_SYS_FSL_HAS_DP_DDR gd->arch.mem2_clk = sys_info.freq_ddrbus2; #endif -#if defined(CONFIG_FSL_ESDHC) -#if defined(CONFIG_FSL_ESDHC_USE_PERIPHERAL_CLK) -#if defined(CONFIG_ARCH_LS1028A) || defined(CONFIG_ARCH_LX2160A) - gd->arch.sdhc_clk = sys_info.freq_cga_m2 / 2; -#endif -#if defined(CONFIG_ARCH_LS2080A) || defined(CONFIG_ARCH_LS1088A) - gd->arch.sdhc_clk = sys_info.freq_cga_m2; + +#ifdef CONFIG_FSL_ESDHC +#if defined(CONFIG_ARCH_LS1028A) || defined(CONFIG_ARCH_LS1088A) + clock = sys_info.freq_cga_m2; +#elif defined(CONFIG_ARCH_LX2160A) || defined(CONFIG_ARCH_LS2080A) + clock = sys_info.freq_systembus; #endif -#else + gd->arch.sdhc_per_clk = clock / CONFIG_SYS_FSL_SDHC_CLK_DIV; gd->arch.sdhc_clk = gd->bus_clk / CONFIG_SYS_FSL_SDHC_CLK_DIV; #endif -#endif /* defined(CONFIG_FSL_ESDHC) */ if (gd->cpu_clk != 0) return 0; diff --git a/drivers/mmc/Kconfig b/drivers/mmc/Kconfig index 85
[PATCH 2/6] mmc: fsl_esdhc: drop useless fdt fixup
The fdt fixup for properties "peripheral-frequency" and "adapter-type" was once for a Freescale SDK release. The properties haven't been existed in linux mainline. Drop these useless code. Signed-off-by: Yangbo Lu --- drivers/mmc/fsl_esdhc.c | 9 - 1 file changed, 9 deletions(-) diff --git a/drivers/mmc/fsl_esdhc.c b/drivers/mmc/fsl_esdhc.c index 1e7d606..8655503 100644 --- a/drivers/mmc/fsl_esdhc.c +++ b/drivers/mmc/fsl_esdhc.c @@ -716,17 +716,8 @@ void fdt_fixup_esdhc(void *blob, bd_t *bd) if (esdhc_status_fixup(blob, compat)) return; -#ifdef CONFIG_FSL_ESDHC_USE_PERIPHERAL_CLK - do_fixup_by_compat_u32(blob, compat, "peripheral-frequency", - gd->arch.sdhc_clk, 1); -#else do_fixup_by_compat_u32(blob, compat, "clock-frequency", gd->arch.sdhc_clk, 1); -#endif -#ifdef CONFIG_FSL_ESDHC_ADAPTER_IDENT - do_fixup_by_compat_u32(blob, compat, "adapter-type", - (u32)(gd->arch.sdhc_adapter), 1); -#endif } #endif -- 2.7.4
[PATCH 4/6] Add global variable sdhc_per_clk for arm/powerpc
The QorIQ eSDHC controller supports two reference clocks. They are platform clock and periperhal clock. The global variable sdhc_clk has already been used for platform clock. This patch is to add another global variable sdhc_per_clk for periperhal clock, which provides higher frequency and is required to be used for SD UHS and eMMC HS200/HS400 speed modes. Signed-off-by: Yangbo Lu --- arch/arm/include/asm/global_data.h | 4 arch/powerpc/include/asm/global_data.h | 1 + 2 files changed, 5 insertions(+) diff --git a/arch/arm/include/asm/global_data.h b/arch/arm/include/asm/global_data.h index 1774014..f23b6bf 100644 --- a/arch/arm/include/asm/global_data.h +++ b/arch/arm/include/asm/global_data.h @@ -13,6 +13,10 @@ struct arch_global_data { u32 sdhc_clk; #endif +#if defined(CONFIG_FSL_ESDHC) + u32 sdhc_per_clk; +#endif + #if defined(CONFIG_U_QE) u32 qe_clk; u32 brg_clk; diff --git a/arch/powerpc/include/asm/global_data.h b/arch/powerpc/include/asm/global_data.h index b6e4dd6..1620fba 100644 --- a/arch/powerpc/include/asm/global_data.h +++ b/arch/powerpc/include/asm/global_data.h @@ -14,6 +14,7 @@ struct arch_global_data { #if defined(CONFIG_FSL_ESDHC) u32 sdhc_clk; + u32 sdhc_per_clk; #if defined(CONFIG_FSL_ESDHC_ADAPTER_IDENT) u8 sdhc_adapter; #endif -- 2.7.4
[PATCH 5/6] configs: ls1028a: use default SDHC clock divider value
The SDHC clock divider value for LS1028A should be default 2, not 1. Signed-off-by: Yangbo Lu --- configs/ls1028aqds_tfa_SECURE_BOOT_defconfig | 1 - configs/ls1028aqds_tfa_defconfig | 1 - configs/ls1028ardb_tfa_SECURE_BOOT_defconfig | 1 - configs/ls1028ardb_tfa_defconfig | 1 - 4 files changed, 4 deletions(-) diff --git a/configs/ls1028aqds_tfa_SECURE_BOOT_defconfig b/configs/ls1028aqds_tfa_SECURE_BOOT_defconfig index a69e892..149f0b6 100644 --- a/configs/ls1028aqds_tfa_SECURE_BOOT_defconfig +++ b/configs/ls1028aqds_tfa_SECURE_BOOT_defconfig @@ -3,7 +3,6 @@ CONFIG_TARGET_LS1028AQDS=y CONFIG_TFABOOT=y CONFIG_SYS_MALLOC_F_LEN=0x6000 CONFIG_NXP_ESBC=y -CONFIG_SYS_FSL_SDHC_CLK_DIV=1 CONFIG_ENV_SIZE=0x2000 CONFIG_NR_DRAM_BANKS=2 CONFIG_ARMV8_SEC_FIRMWARE_SUPPORT=y diff --git a/configs/ls1028aqds_tfa_defconfig b/configs/ls1028aqds_tfa_defconfig index 538830d..da59b9c 100644 --- a/configs/ls1028aqds_tfa_defconfig +++ b/configs/ls1028aqds_tfa_defconfig @@ -2,7 +2,6 @@ CONFIG_ARM=y CONFIG_TARGET_LS1028AQDS=y CONFIG_TFABOOT=y CONFIG_SYS_MALLOC_F_LEN=0x6000 -CONFIG_SYS_FSL_SDHC_CLK_DIV=1 CONFIG_ENV_SIZE=0x2000 CONFIG_ENV_OFFSET=0x50 CONFIG_NR_DRAM_BANKS=2 diff --git a/configs/ls1028ardb_tfa_SECURE_BOOT_defconfig b/configs/ls1028ardb_tfa_SECURE_BOOT_defconfig index 55769c7..e287d08 100644 --- a/configs/ls1028ardb_tfa_SECURE_BOOT_defconfig +++ b/configs/ls1028ardb_tfa_SECURE_BOOT_defconfig @@ -3,7 +3,6 @@ CONFIG_TARGET_LS1028ARDB=y CONFIG_TFABOOT=y CONFIG_SYS_MALLOC_F_LEN=0x6000 CONFIG_NXP_ESBC=y -CONFIG_SYS_FSL_SDHC_CLK_DIV=1 CONFIG_ENV_SIZE=0x2000 CONFIG_NR_DRAM_BANKS=2 CONFIG_ARMV8_SEC_FIRMWARE_SUPPORT=y diff --git a/configs/ls1028ardb_tfa_defconfig b/configs/ls1028ardb_tfa_defconfig index 870d6b7..4ceecbc 100644 --- a/configs/ls1028ardb_tfa_defconfig +++ b/configs/ls1028ardb_tfa_defconfig @@ -2,7 +2,6 @@ CONFIG_ARM=y CONFIG_TARGET_LS1028ARDB=y CONFIG_TFABOOT=y CONFIG_SYS_MALLOC_F_LEN=0x6000 -CONFIG_SYS_FSL_SDHC_CLK_DIV=1 CONFIG_ENV_SIZE=0x2000 CONFIG_ENV_OFFSET=0x50 CONFIG_NR_DRAM_BANKS=2 -- 2.7.4
[PATCH 0/6] Clean up eSDHC periperhal clock code
This patch-set is to clean up eSDHC peripheral clock code. - Drop useless code in esdhc/esdhc_imx drivers and powerpc/. - Add global variable sdhc_per_clk for peripehral clock. - Drop CONFIG_FSL_ESDHC_USE_PERIPHERAL_CLK option and let driver decides which clock to use. - Some fixes for peripehral clock calcualtion. Yangbo Lu (6): mmc: fsl_esdhc_imx: drop QorIQ eSDHC specific peripheral clock code mmc: fsl_esdhc: drop useless fdt fixup powerpc/mpc85xx: drop eSDHC periperhal clock code Add global variable sdhc_per_clk for arm/powerpc configs: ls1028a: use default SDHC clock divider value Drop CONFIG_FSL_ESDHC_USE_PERIPHERAL_CLK usage .../arm/cpu/armv8/fsl-layerscape/fsl_lsch2_speed.c | 29 + .../arm/cpu/armv8/fsl-layerscape/fsl_lsch3_speed.c | 22 +- arch/arm/include/asm/global_data.h | 4 ++ arch/powerpc/cpu/mpc85xx/speed.c | 49 +- arch/powerpc/include/asm/config_mpc85xx.h | 8 arch/powerpc/include/asm/global_data.h | 1 + configs/ls1028aqds_tfa_SECURE_BOOT_defconfig | 1 - configs/ls1028aqds_tfa_defconfig | 1 - configs/ls1028ardb_tfa_SECURE_BOOT_defconfig | 1 - configs/ls1028ardb_tfa_defconfig | 1 - drivers/mmc/Kconfig| 9 drivers/mmc/fsl_esdhc.c| 41 +- drivers/mmc/fsl_esdhc_imx.c| 40 -- include/configs/T1040QDS.h | 1 - include/configs/T208xQDS.h | 1 - include/e500.h | 1 - scripts/config_whitelist.txt | 2 - 17 files changed, 48 insertions(+), 164 deletions(-) -- 2.7.4
[U-Boot] [PATCH 3/4] arm: drop eSDHC clock getting in mxc_get_clock() for layerscape
Although layerscape platforms reuse mxc_get_clock() of i.MX platforms, eSDHC clock getting do not have to use it. It uses global data gd->arch.sdhc_clk directly in fsl_esdhc driver. Even there are more than one eSDHC controllers on SoC, they use same reference clock. Signed-off-by: Yangbo Lu --- arch/arm/cpu/armv7/ls102xa/clock.c | 2 -- arch/arm/cpu/armv8/fsl-layerscape/fsl_lsch2_speed.c | 15 --- arch/arm/cpu/armv8/fsl-layerscape/fsl_lsch3_speed.c | 15 --- arch/arm/include/asm/arch-fsl-layerscape/clock.h| 2 -- arch/arm/include/asm/arch-ls102xa/clock.h | 1 - 5 files changed, 35 deletions(-) diff --git a/arch/arm/cpu/armv7/ls102xa/clock.c b/arch/arm/cpu/armv7/ls102xa/clock.c index 30c7b37..7a1053c 100644 --- a/arch/arm/cpu/armv7/ls102xa/clock.c +++ b/arch/arm/cpu/armv7/ls102xa/clock.c @@ -109,8 +109,6 @@ unsigned int mxc_get_clock(enum mxc_clock clk) switch (clk) { case MXC_I2C_CLK: return get_bus_freq(0) / 2; - case MXC_ESDHC_CLK: - return get_bus_freq(0); case MXC_DSPI_CLK: return get_bus_freq(0) / 2; case MXC_UART_CLK: diff --git a/arch/arm/cpu/armv8/fsl-layerscape/fsl_lsch2_speed.c b/arch/arm/cpu/armv8/fsl-layerscape/fsl_lsch2_speed.c index df4df9a..6d82cfe 100644 --- a/arch/arm/cpu/armv8/fsl-layerscape/fsl_lsch2_speed.c +++ b/arch/arm/cpu/armv8/fsl-layerscape/fsl_lsch2_speed.c @@ -227,16 +227,6 @@ ulong get_ddr_freq(ulong dummy) return gd->mem_clk; } -#ifdef CONFIG_FSL_ESDHC -int get_sdhc_freq(ulong dummy) -{ - if (!gd->arch.sdhc_clk) - get_clocks(); - - return gd->arch.sdhc_clk; -} -#endif - int get_serial_clock(void) { return get_bus_freq(0) / CONFIG_SYS_FSL_DUART_CLK_DIV; @@ -264,11 +254,6 @@ unsigned int mxc_get_clock(enum mxc_clock clk) switch (clk) { case MXC_I2C_CLK: return get_i2c_freq(0); -#if defined(CONFIG_FSL_ESDHC) - case MXC_ESDHC_CLK: - case MXC_ESDHC2_CLK: - return get_sdhc_freq(0); -#endif case MXC_DSPI_CLK: return get_dspi_freq(0); #ifdef CONFIG_FSL_LPUART diff --git a/arch/arm/cpu/armv8/fsl-layerscape/fsl_lsch3_speed.c b/arch/arm/cpu/armv8/fsl-layerscape/fsl_lsch3_speed.c index b3e6732..1f8289d 100644 --- a/arch/arm/cpu/armv8/fsl-layerscape/fsl_lsch3_speed.c +++ b/arch/arm/cpu/armv8/fsl-layerscape/fsl_lsch3_speed.c @@ -236,16 +236,6 @@ int get_dspi_freq(ulong dummy) return get_bus_freq(0) / CONFIG_SYS_FSL_DSPI_CLK_DIV; } -#ifdef CONFIG_FSL_ESDHC -int get_sdhc_freq(ulong dummy) -{ - if (!gd->arch.sdhc_clk) - get_clocks(); - - return gd->arch.sdhc_clk; -} -#endif - int get_serial_clock(void) { return get_bus_freq(0) / CONFIG_SYS_FSL_DUART_CLK_DIV; @@ -256,11 +246,6 @@ unsigned int mxc_get_clock(enum mxc_clock clk) switch (clk) { case MXC_I2C_CLK: return get_i2c_freq(0); -#if defined(CONFIG_FSL_ESDHC) - case MXC_ESDHC_CLK: - case MXC_ESDHC2_CLK: - return get_sdhc_freq(0); -#endif case MXC_DSPI_CLK: return get_dspi_freq(0); default: diff --git a/arch/arm/include/asm/arch-fsl-layerscape/clock.h b/arch/arm/include/asm/arch-fsl-layerscape/clock.h index b37a08d..95d6156 100644 --- a/arch/arm/include/asm/arch-fsl-layerscape/clock.h +++ b/arch/arm/include/asm/arch-fsl-layerscape/clock.h @@ -14,8 +14,6 @@ enum mxc_clock { MXC_ARM_CLK = 0, MXC_BUS_CLK, MXC_UART_CLK, - MXC_ESDHC_CLK, - MXC_ESDHC2_CLK, MXC_I2C_CLK, MXC_DSPI_CLK, }; diff --git a/arch/arm/include/asm/arch-ls102xa/clock.h b/arch/arm/include/asm/arch-ls102xa/clock.h index bf67df5..e66e57f 100644 --- a/arch/arm/include/asm/arch-ls102xa/clock.h +++ b/arch/arm/include/asm/arch-ls102xa/clock.h @@ -12,7 +12,6 @@ enum mxc_clock { MXC_ARM_CLK = 0, MXC_UART_CLK, - MXC_ESDHC_CLK, MXC_I2C_CLK, MXC_DSPI_CLK, }; -- 2.7.4 ___ U-Boot mailing list U-Boot@lists.denx.de https://lists.denx.de/listinfo/u-boot
[U-Boot] [PATCH 2/4] arm: ls1021a: drop redundant board_mmc_init()
The board_mmc_init() defined in board files is actually doing same thing with the cpu_mmc_init() defined in arch/arm/cpu/armv7/ls102xa/cpu.c. So drop it. Signed-off-by: Yangbo Lu --- board/freescale/ls1021aiot/ls1021aiot.c | 15 --- board/freescale/ls1021aqds/ls1021aqds.c | 14 -- board/freescale/ls1021atwr/ls1021atwr.c | 14 -- 3 files changed, 43 deletions(-) diff --git a/board/freescale/ls1021aiot/ls1021aiot.c b/board/freescale/ls1021aiot/ls1021aiot.c index 70992a5..621a3db 100644 --- a/board/freescale/ls1021aiot/ls1021aiot.c +++ b/board/freescale/ls1021aiot/ls1021aiot.c @@ -12,7 +12,6 @@ #include #include #include -#include #include #include #include @@ -103,20 +102,6 @@ int dram_init(void) return 0; } -#ifdef CONFIG_FSL_ESDHC -struct fsl_esdhc_cfg esdhc_cfg[1] = { - {CONFIG_SYS_FSL_ESDHC_ADDR}, -}; - -int board_mmc_init(bd_t *bis) -{ - esdhc_cfg[0].sdhc_clk = mxc_get_clock(MXC_ESDHC_CLK); - - return fsl_esdhc_initialize(bis, _cfg[0]); -} - -#endif - #ifdef CONFIG_TSEC_ENET int board_eth_init(bd_t *bis) { diff --git a/board/freescale/ls1021aqds/ls1021aqds.c b/board/freescale/ls1021aqds/ls1021aqds.c index 2ca2bd9..4034b7d 100644 --- a/board/freescale/ls1021aqds/ls1021aqds.c +++ b/board/freescale/ls1021aqds/ls1021aqds.c @@ -14,7 +14,6 @@ #include #include #include -#include #include #include #include @@ -161,19 +160,6 @@ int dram_init(void) return fsl_initdram(); } -#ifdef CONFIG_FSL_ESDHC -struct fsl_esdhc_cfg esdhc_cfg[1] = { - {CONFIG_SYS_FSL_ESDHC_ADDR}, -}; - -int board_mmc_init(bd_t *bis) -{ - esdhc_cfg[0].sdhc_clk = mxc_get_clock(MXC_ESDHC_CLK); - - return fsl_esdhc_initialize(bis, _cfg[0]); -} -#endif - int board_early_init_f(void) { struct ccsr_scfg *scfg = (struct ccsr_scfg *)CONFIG_SYS_FSL_SCFG_ADDR; diff --git a/board/freescale/ls1021atwr/ls1021atwr.c b/board/freescale/ls1021atwr/ls1021atwr.c index fcf2ec9..1a412ee 100644 --- a/board/freescale/ls1021atwr/ls1021atwr.c +++ b/board/freescale/ls1021atwr/ls1021atwr.c @@ -14,7 +14,6 @@ #include #include #include -#include #include #include #include @@ -233,19 +232,6 @@ int dram_init(void) return 0; } -#ifdef CONFIG_FSL_ESDHC -struct fsl_esdhc_cfg esdhc_cfg[1] = { - {CONFIG_SYS_FSL_ESDHC_ADDR}, -}; - -int board_mmc_init(bd_t *bis) -{ - esdhc_cfg[0].sdhc_clk = mxc_get_clock(MXC_ESDHC_CLK); - - return fsl_esdhc_initialize(bis, _cfg[0]); -} -#endif - int board_eth_init(bd_t *bis) { return pci_eth_init(bis); -- 2.7.4 ___ U-Boot mailing list U-Boot@lists.denx.de https://lists.denx.de/listinfo/u-boot
[U-Boot] [PATCH 4/4] mpc83xx: remove unused clock.h
The clock.h was to define mxc_get_clock() providing clock value to fsl_esdhc driver. Since fsl_esdhc driver is using global data gd->arch.sdhc_clk directly now, we can remove this file. Signed-off-by: Yangbo Lu --- arch/powerpc/include/asm/arch-mpc83xx/clock.h | 22 -- 1 file changed, 22 deletions(-) delete mode 100644 arch/powerpc/include/asm/arch-mpc83xx/clock.h diff --git a/arch/powerpc/include/asm/arch-mpc83xx/clock.h b/arch/powerpc/include/asm/arch-mpc83xx/clock.h deleted file mode 100644 index d57e93c..000 --- a/arch/powerpc/include/asm/arch-mpc83xx/clock.h +++ /dev/null @@ -1,22 +0,0 @@ -/* - * (C) Copyright 2018 - * Mario Six, Guntermann & Drunck GmbH, mario@gdsys.cc - * - * SPDX-License-Identifier:GPL-2.0+ - */ - -#ifndef __ASM_POWERPC_CLOCK_H -#define __ASM_POWERPC_CLOCK_H - -/* Make fsl_esdhc driver happy */ -enum mxc_clock { - MXC_ESDHC_CLK, -}; - -DECLARE_GLOBAL_DATA_PTR; - -uint mxc_get_clock(int clk) -{ - return gd->arch.sdhc_clk; -} -#endif /* __ASM_POWERPC_CLOCK_H */ -- 2.7.4 ___ U-Boot mailing list U-Boot@lists.denx.de https://lists.denx.de/listinfo/u-boot
[U-Boot] [PATCH 1/4] mmc: fsl_esdhc: get clock directly from global data
This patch is to get clock directly from global data. - Remove uclass clk api method. This was what i.MX platforms were using, while QorIQ platforms weren't. - Get clock only from global data, dropping mxc_get_clock(). QorIQ eSDHC controllers on one silicon use same reference clock. Signed-off-by: Yangbo Lu --- drivers/mmc/fsl_esdhc.c | 34 -- 1 file changed, 4 insertions(+), 30 deletions(-) diff --git a/drivers/mmc/fsl_esdhc.c b/drivers/mmc/fsl_esdhc.c index 8ff84aa..09cb773 100644 --- a/drivers/mmc/fsl_esdhc.c +++ b/drivers/mmc/fsl_esdhc.c @@ -12,7 +12,6 @@ #include #include #include -#include #include #include #include @@ -81,7 +80,6 @@ struct fsl_esdhc_plat { struct fsl_esdhc_priv { struct fsl_esdhc *esdhc_regs; unsigned int sdhc_clk; - struct clk per_clk; unsigned int clock; #if !CONFIG_IS_ENABLED(DM_MMC) struct mmc *mmc; @@ -831,9 +829,6 @@ int fsl_esdhc_mmc_init(bd_t *bis) return fsl_esdhc_initialize(bis, cfg); } #else /* DM_MMC */ -#ifndef CONFIG_PPC -#include -#endif static int fsl_esdhc_probe(struct udevice *dev) { struct mmc_uclass_priv *upriv = dev_get_uclass_priv(dev); @@ -841,7 +836,6 @@ static int fsl_esdhc_probe(struct udevice *dev) struct fsl_esdhc_priv *priv = dev_get_priv(dev); fdt_addr_t addr; struct mmc *mmc; - int ret; addr = dev_read_addr(dev); if (addr == FDT_ADDR_T_NONE) @@ -853,30 +847,10 @@ static int fsl_esdhc_probe(struct udevice *dev) #endif priv->dev = dev; - if (IS_ENABLED(CONFIG_CLK)) { - /* Assigned clock already set clock */ - ret = clk_get_by_name(dev, "per", >per_clk); - if (ret) { - printf("Failed to get per_clk\n"); - return ret; - } - ret = clk_enable(>per_clk); - if (ret) { - printf("Failed to enable per_clk\n"); - return ret; - } - - priv->sdhc_clk = clk_get_rate(>per_clk); - } else { -#ifndef CONFIG_PPC - priv->sdhc_clk = mxc_get_clock(MXC_ESDHC_CLK + dev->seq); -#else - priv->sdhc_clk = gd->arch.sdhc_clk; -#endif - if (priv->sdhc_clk <= 0) { - dev_err(dev, "Unable to get clk for %s\n", dev->name); - return -EINVAL; - } + priv->sdhc_clk = gd->arch.sdhc_clk; + if (priv->sdhc_clk <= 0) { + dev_err(dev, "Unable to get clk for %s\n", dev->name); + return -EINVAL; } fsl_esdhc_get_cfg_common(priv, >cfg); -- 2.7.4 ___ U-Boot mailing list U-Boot@lists.denx.de https://lists.denx.de/listinfo/u-boot
[U-Boot] [PATCH 0/4] Drop redundant code for eSDHC clock getting
This patch-set is to drop redundant code for eSDHC clock getting. The fsl_esdhc driver is able to simply get clock from gd->arch.sdhc_clk. The CI build link: https://travis-ci.org/yangbolu1991/u-boot-test/builds/610688748 Yangbo Lu (4): mmc: fsl_esdhc: get clock directly from global data arm: ls1021a: drop redundant board_mmc_init() arm: drop eSDHC clock getting in mxc_get_clock() for layerscape mpc83xx: remove unused clock.h arch/arm/cpu/armv7/ls102xa/clock.c | 2 -- .../arm/cpu/armv8/fsl-layerscape/fsl_lsch2_speed.c | 15 -- .../arm/cpu/armv8/fsl-layerscape/fsl_lsch3_speed.c | 15 -- arch/arm/include/asm/arch-fsl-layerscape/clock.h | 2 -- arch/arm/include/asm/arch-ls102xa/clock.h | 1 - arch/powerpc/include/asm/arch-mpc83xx/clock.h | 22 -- board/freescale/ls1021aiot/ls1021aiot.c| 15 -- board/freescale/ls1021aqds/ls1021aqds.c| 14 - board/freescale/ls1021atwr/ls1021atwr.c| 14 - drivers/mmc/fsl_esdhc.c| 34 +++--- 10 files changed, 4 insertions(+), 130 deletions(-) delete mode 100644 arch/powerpc/include/asm/arch-mpc83xx/clock.h -- 2.7.4 ___ U-Boot mailing list U-Boot@lists.denx.de https://lists.denx.de/listinfo/u-boot
[U-Boot] [PATCH 6/7] mmc: fsl_esdhc: always check write protect state
The QorIQ eSDHC on all platforms supports checking write protect state through register bit. So check it always. Signed-off-by: Yangbo Lu --- drivers/mmc/fsl_esdhc.c | 15 --- include/fsl_esdhc.h | 1 - 2 files changed, 4 insertions(+), 12 deletions(-) diff --git a/drivers/mmc/fsl_esdhc.c b/drivers/mmc/fsl_esdhc.c index 25a8fe3..bdc0ca6 100644 --- a/drivers/mmc/fsl_esdhc.c +++ b/drivers/mmc/fsl_esdhc.c @@ -75,7 +75,6 @@ struct fsl_esdhc_plat { * @mmc: mmc * Following is used when Driver Model is enabled for MMC * @dev: pointer for the device - * @wp_enable: 1: enable checking wp; 0: no check * @cd_gpio: gpio for card detection * @wp_gpio: gpio for write protection */ @@ -88,7 +87,6 @@ struct fsl_esdhc_priv { struct mmc *mmc; #endif struct udevice *dev; - int wp_enable; }; /* Return the XFERTYP flags for a given command and data packet */ @@ -231,12 +229,10 @@ static int esdhc_setup_data(struct fsl_esdhc_priv *priv, struct mmc *mmc, #endif if (wml_value > WML_WR_WML_MAX) wml_value = WML_WR_WML_MAX_VAL; - if (priv->wp_enable) { - if ((esdhc_read32(>prsstat) & - PRSSTAT_WPSPL) == 0) { - printf("\nThe SD card is locked. Can not write to a locked card.\n\n"); - return -ETIMEDOUT; - } + + if (!(esdhc_read32(>prsstat) & PRSSTAT_WPSPL)) { + printf("Can not write to locked SD card.\n"); + return -EINVAL; } esdhc_clrsetbits32(>wml, WML_WR_WML_MASK, @@ -722,7 +718,6 @@ int fsl_esdhc_initialize(bd_t *bis, struct fsl_esdhc_cfg *cfg) priv->esdhc_regs = (struct fsl_esdhc *)(unsigned long)(cfg->esdhc_base); priv->sdhc_clk = cfg->sdhc_clk; - priv->wp_enable = cfg->wp_enable; mmc_cfg = >cfg; @@ -862,8 +857,6 @@ static int fsl_esdhc_probe(struct udevice *dev) #endif priv->dev = dev; - priv->wp_enable = 1; - if (IS_ENABLED(CONFIG_CLK)) { /* Assigned clock already set clock */ ret = clk_get_by_name(dev, "per", >per_clk); diff --git a/include/fsl_esdhc.h b/include/fsl_esdhc.h index a015df1..8e8cd2c 100644 --- a/include/fsl_esdhc.h +++ b/include/fsl_esdhc.h @@ -168,7 +168,6 @@ struct fsl_esdhc_cfg { phys_addr_t esdhc_base; u32 sdhc_clk; u8 max_bus_width; - int wp_enable; int vs18_enable; /* Use 1.8V if set to 1 */ struct mmc_config cfg; }; -- 2.7.4 ___ U-Boot mailing list U-Boot@lists.denx.de https://lists.denx.de/listinfo/u-boot
[U-Boot] [PATCH 7/7] mmc: fsl_esdhc: clean up DM and non-DM code
Make DM and non-DM code clear using below structure. #if !CONFIG_IS_ENABLED(DM_MMC) #else #endif Signed-off-by: Yangbo Lu --- drivers/mmc/fsl_esdhc.c | 204 1 file changed, 100 insertions(+), 104 deletions(-) diff --git a/drivers/mmc/fsl_esdhc.c b/drivers/mmc/fsl_esdhc.c index bdc0ca6..8ff84aa 100644 --- a/drivers/mmc/fsl_esdhc.c +++ b/drivers/mmc/fsl_esdhc.c @@ -628,44 +628,6 @@ static int esdhc_getcd_common(struct fsl_esdhc_priv *priv) return timeout > 0; } -#if !CONFIG_IS_ENABLED(DM_MMC) -static int esdhc_getcd(struct mmc *mmc) -{ - struct fsl_esdhc_priv *priv = mmc->priv; - - return esdhc_getcd_common(priv); -} - -static int esdhc_init(struct mmc *mmc) -{ - struct fsl_esdhc_priv *priv = mmc->priv; - - return esdhc_init_common(priv, mmc); -} - -static int esdhc_send_cmd(struct mmc *mmc, struct mmc_cmd *cmd, - struct mmc_data *data) -{ - struct fsl_esdhc_priv *priv = mmc->priv; - - return esdhc_send_cmd_common(priv, mmc, cmd, data); -} - -static int esdhc_set_ios(struct mmc *mmc) -{ - struct fsl_esdhc_priv *priv = mmc->priv; - - return esdhc_set_ios_common(priv, mmc); -} - -static const struct mmc_ops esdhc_ops = { - .getcd = esdhc_getcd, - .init = esdhc_init, - .send_cmd = esdhc_send_cmd, - .set_ios= esdhc_set_ios, -}; -#endif - static void fsl_esdhc_get_cfg_common(struct fsl_esdhc_priv *priv, struct mmc_config *cfg) { @@ -696,71 +658,6 @@ static void fsl_esdhc_get_cfg_common(struct fsl_esdhc_priv *priv, cfg->b_max = CONFIG_SYS_MMC_MAX_BLK_COUNT; } -#if !CONFIG_IS_ENABLED(DM_MMC) -int fsl_esdhc_initialize(bd_t *bis, struct fsl_esdhc_cfg *cfg) -{ - struct fsl_esdhc_plat *plat; - struct fsl_esdhc_priv *priv; - struct mmc_config *mmc_cfg; - struct mmc *mmc; - - if (!cfg) - return -EINVAL; - - priv = calloc(sizeof(struct fsl_esdhc_priv), 1); - if (!priv) - return -ENOMEM; - plat = calloc(sizeof(struct fsl_esdhc_plat), 1); - if (!plat) { - free(priv); - return -ENOMEM; - } - - priv->esdhc_regs = (struct fsl_esdhc *)(unsigned long)(cfg->esdhc_base); - priv->sdhc_clk = cfg->sdhc_clk; - - mmc_cfg = >cfg; - - if (cfg->max_bus_width == 8) { - mmc_cfg->host_caps |= MMC_MODE_1BIT | MMC_MODE_4BIT | - MMC_MODE_8BIT; - } else if (cfg->max_bus_width == 4) { - mmc_cfg->host_caps |= MMC_MODE_1BIT | MMC_MODE_4BIT; - } else if (cfg->max_bus_width == 1) { - mmc_cfg->host_caps |= MMC_MODE_1BIT; - } else { - mmc_cfg->host_caps |= MMC_MODE_1BIT | MMC_MODE_4BIT | - MMC_MODE_8BIT; - printf("No max bus width provided. Assume 8-bit supported.\n"); - } - -#ifdef CONFIG_ESDHC_DETECT_8_BIT_QUIRK - if (CONFIG_ESDHC_DETECT_8_BIT_QUIRK) - mmc_cfg->host_caps &= ~MMC_MODE_8BIT; -#endif - mmc_cfg->ops = _ops; - - fsl_esdhc_get_cfg_common(priv, mmc_cfg); - - mmc = mmc_create(mmc_cfg, priv); - if (!mmc) - return -EIO; - - priv->mmc = mmc; - return 0; -} - -int fsl_esdhc_mmc_init(bd_t *bis) -{ - struct fsl_esdhc_cfg *cfg; - - cfg = calloc(sizeof(struct fsl_esdhc_cfg), 1); - cfg->esdhc_base = CONFIG_SYS_FSL_ESDHC_ADDR; - cfg->sdhc_clk = gd->arch.sdhc_clk; - return fsl_esdhc_initialize(bis, cfg); -} -#endif - #ifdef CONFIG_FSL_ESDHC_ADAPTER_IDENT void mmc_adapter_card_type_ident(void) { @@ -834,7 +731,106 @@ void fdt_fixup_esdhc(void *blob, bd_t *bd) } #endif -#if CONFIG_IS_ENABLED(DM_MMC) +#if !CONFIG_IS_ENABLED(DM_MMC) +static int esdhc_getcd(struct mmc *mmc) +{ + struct fsl_esdhc_priv *priv = mmc->priv; + + return esdhc_getcd_common(priv); +} + +static int esdhc_init(struct mmc *mmc) +{ + struct fsl_esdhc_priv *priv = mmc->priv; + + return esdhc_init_common(priv, mmc); +} + +static int esdhc_send_cmd(struct mmc *mmc, struct mmc_cmd *cmd, + struct mmc_data *data) +{ + struct fsl_esdhc_priv *priv = mmc->priv; + + return esdhc_send_cmd_common(priv, mmc, cmd, data); +} + +static int esdhc_set_ios(struct mmc *mmc) +{ + struct fsl_esdhc_priv *priv = mmc->priv; + + return esdhc_set_ios_common(priv, mmc); +} + +static const struct mmc_ops esdhc_ops = { + .getcd = esdhc_getcd, + .init = esdhc_init, + .send_cmd = esdhc_send_cmd, + .set_ios= esdhc_set_ios, +}; + +int fsl_esdhc_initialize(bd_t *bis, struct fsl_esdhc_cfg
[U-Boot] [PATCH 4/7] mmc: fsl_esdhc: convert to use fsl_esdhc_get_cfg_common()
The fsl_esdhc_init() was actually to get configuration of mmc_config. So rename it to fsl_esdhc_get_cfg_common() and make it common for both DM_MMC and non-DM_MMC. Signed-off-by: Yangbo Lu --- drivers/mmc/fsl_esdhc.c | 43 --- 1 file changed, 8 insertions(+), 35 deletions(-) diff --git a/drivers/mmc/fsl_esdhc.c b/drivers/mmc/fsl_esdhc.c index e5276f6..2b7bcab 100644 --- a/drivers/mmc/fsl_esdhc.c +++ b/drivers/mmc/fsl_esdhc.c @@ -678,23 +678,12 @@ static const struct mmc_ops esdhc_ops = { }; #endif -static int fsl_esdhc_init(struct fsl_esdhc_priv *priv, - struct fsl_esdhc_plat *plat) +static void fsl_esdhc_get_cfg_common(struct fsl_esdhc_priv *priv, +struct mmc_config *cfg) { - struct mmc_config *cfg; - struct fsl_esdhc *regs; + struct fsl_esdhc *regs = priv->esdhc_regs; u32 caps; - if (!priv) - return -EINVAL; - - regs = priv->esdhc_regs; - - cfg = >cfg; -#ifndef CONFIG_DM_MMC - memset(cfg, '\0', sizeof(*cfg)); -#endif - caps = esdhc_read32(>hostcapblt); #ifdef CONFIG_SYS_FSL_ERRATUM_ESDHC135 caps &= ~(HOSTCAPBLT_SRS | HOSTCAPBLT_VS18 | HOSTCAPBLT_VS30); @@ -710,19 +699,13 @@ static int fsl_esdhc_init(struct fsl_esdhc_priv *priv, cfg->voltages |= MMC_VDD_32_33 | MMC_VDD_33_34; cfg->name = "FSL_SDHC"; -#if !CONFIG_IS_ENABLED(DM_MMC) - cfg->ops = _ops; -#endif if (caps & HOSTCAPBLT_HSS) cfg->host_caps |= MMC_MODE_HS_52MHz | MMC_MODE_HS; cfg->f_min = 40; cfg->f_max = min(priv->sdhc_clk, (u32)2); - cfg->b_max = CONFIG_SYS_MMC_MAX_BLK_COUNT; - - return 0; } #if !CONFIG_IS_ENABLED(DM_MMC) @@ -732,7 +715,6 @@ int fsl_esdhc_initialize(bd_t *bis, struct fsl_esdhc_cfg *cfg) struct fsl_esdhc_priv *priv; struct mmc_config *mmc_cfg; struct mmc *mmc; - int ret; if (!cfg) return -EINVAL; @@ -769,20 +751,15 @@ int fsl_esdhc_initialize(bd_t *bis, struct fsl_esdhc_cfg *cfg) if (CONFIG_ESDHC_DETECT_8_BIT_QUIRK) mmc_cfg->host_caps &= ~MMC_MODE_8BIT; #endif - ret = fsl_esdhc_init(priv, plat); - if (ret) { - debug("%s init failure\n", __func__); - free(plat); - free(priv); - return ret; - } + mmc_cfg->ops = _ops; + + fsl_esdhc_get_cfg_common(priv, mmc_cfg); - mmc = mmc_create(>cfg, priv); + mmc = mmc_create(mmc_cfg, priv); if (!mmc) return -EIO; priv->mmc = mmc; - return 0; } @@ -927,11 +904,7 @@ static int fsl_esdhc_probe(struct udevice *dev) } } - ret = fsl_esdhc_init(priv, plat); - if (ret) { - dev_err(dev, "fsl_esdhc_init failure\n"); - return ret; - } + fsl_esdhc_get_cfg_common(priv, >cfg); mmc_of_parse(dev, >cfg); -- 2.7.4 ___ U-Boot mailing list U-Boot@lists.denx.de https://lists.denx.de/listinfo/u-boot
[U-Boot] [PATCH 3/7] mmc: fsl_esdhc: clean up bus width configuration code
This patch is to clean up bus width setting code. - For DM_MMC, remove getting "bus-width" from device tree. This has been done in mmc_of_parse(). - For non-DM_MMC, move bus width configuration from fsl_esdhc_init() to fsl_esdhc_initialize() which is non-DM_MMC specific. And fix up bus width configuration to support only 1-bit, 4-bit, or 8-bit. Keep using 8-bit if it's not set because many platforms use driver without providing max bus width. - Remove bus_width member from fsl_esdhc_priv structure. Signed-off-by: Yangbo Lu --- drivers/mmc/fsl_esdhc.c | 70 - 1 file changed, 22 insertions(+), 48 deletions(-) diff --git a/drivers/mmc/fsl_esdhc.c b/drivers/mmc/fsl_esdhc.c index 40fd6af..e5276f6 100644 --- a/drivers/mmc/fsl_esdhc.c +++ b/drivers/mmc/fsl_esdhc.c @@ -85,7 +85,6 @@ struct fsl_esdhc_priv { unsigned int sdhc_clk; struct clk per_clk; unsigned int clock; - unsigned int bus_width; #if !CONFIG_IS_ENABLED(DM_MMC) struct mmc *mmc; #endif @@ -714,28 +713,10 @@ static int fsl_esdhc_init(struct fsl_esdhc_priv *priv, #if !CONFIG_IS_ENABLED(DM_MMC) cfg->ops = _ops; #endif - if (priv->bus_width == 8) - cfg->host_caps = MMC_MODE_4BIT | MMC_MODE_8BIT; - else if (priv->bus_width == 4) - cfg->host_caps = MMC_MODE_4BIT; - - cfg->host_caps = MMC_MODE_4BIT | MMC_MODE_8BIT; - - if (priv->bus_width > 0) { - if (priv->bus_width < 8) - cfg->host_caps &= ~MMC_MODE_8BIT; - if (priv->bus_width < 4) - cfg->host_caps &= ~MMC_MODE_4BIT; - } if (caps & HOSTCAPBLT_HSS) cfg->host_caps |= MMC_MODE_HS_52MHz | MMC_MODE_HS; -#ifdef CONFIG_ESDHC_DETECT_8_BIT_QUIRK - if (CONFIG_ESDHC_DETECT_8_BIT_QUIRK) - cfg->host_caps &= ~MMC_MODE_8BIT; -#endif - cfg->f_min = 40; cfg->f_max = min(priv->sdhc_clk, (u32)2); @@ -745,24 +726,11 @@ static int fsl_esdhc_init(struct fsl_esdhc_priv *priv, } #if !CONFIG_IS_ENABLED(DM_MMC) -static int fsl_esdhc_cfg_to_priv(struct fsl_esdhc_cfg *cfg, -struct fsl_esdhc_priv *priv) -{ - if (!cfg || !priv) - return -EINVAL; - - priv->esdhc_regs = (struct fsl_esdhc *)(unsigned long)(cfg->esdhc_base); - priv->bus_width = cfg->max_bus_width; - priv->sdhc_clk = cfg->sdhc_clk; - priv->wp_enable = cfg->wp_enable; - - return 0; -}; - int fsl_esdhc_initialize(bd_t *bis, struct fsl_esdhc_cfg *cfg) { struct fsl_esdhc_plat *plat; struct fsl_esdhc_priv *priv; + struct mmc_config *mmc_cfg; struct mmc *mmc; int ret; @@ -778,14 +746,29 @@ int fsl_esdhc_initialize(bd_t *bis, struct fsl_esdhc_cfg *cfg) return -ENOMEM; } - ret = fsl_esdhc_cfg_to_priv(cfg, priv); - if (ret) { - debug("%s xlate failure\n", __func__); - free(plat); - free(priv); - return ret; + priv->esdhc_regs = (struct fsl_esdhc *)(unsigned long)(cfg->esdhc_base); + priv->sdhc_clk = cfg->sdhc_clk; + priv->wp_enable = cfg->wp_enable; + + mmc_cfg = >cfg; + + if (cfg->max_bus_width == 8) { + mmc_cfg->host_caps |= MMC_MODE_1BIT | MMC_MODE_4BIT | + MMC_MODE_8BIT; + } else if (cfg->max_bus_width == 4) { + mmc_cfg->host_caps |= MMC_MODE_1BIT | MMC_MODE_4BIT; + } else if (cfg->max_bus_width == 1) { + mmc_cfg->host_caps |= MMC_MODE_1BIT; + } else { + mmc_cfg->host_caps |= MMC_MODE_1BIT | MMC_MODE_4BIT | + MMC_MODE_8BIT; + printf("No max bus width provided. Assume 8-bit supported.\n"); } +#ifdef CONFIG_ESDHC_DETECT_8_BIT_QUIRK + if (CONFIG_ESDHC_DETECT_8_BIT_QUIRK) + mmc_cfg->host_caps &= ~MMC_MODE_8BIT; +#endif ret = fsl_esdhc_init(priv, plat); if (ret) { debug("%s init failure\n", __func__); @@ -897,7 +880,6 @@ static int fsl_esdhc_probe(struct udevice *dev) struct fsl_esdhc_plat *plat = dev_get_platdata(dev); struct fsl_esdhc_priv *priv = dev_get_priv(dev); fdt_addr_t addr; - unsigned int val; struct mmc *mmc; int ret; @@ -911,14 +893,6 @@ static int fsl_esdhc_probe(struct udevice *dev) #endif priv->dev = dev; - val = dev_read_u32_default(dev, "bus-width", -1); - if (val == 8) - priv->bus_width = 8; - else if (val == 4) - priv->bus_width = 4; - else - priv->bus_
[U-Boot] [PATCH 5/7] mmc: fsl_esdhc: drop redundant code for non-removable feature
Drop redundant code for non-removable feature. "non-removable" property has been read in mmc_of_parse(). Signed-off-by: Yangbo Lu --- drivers/mmc/fsl_esdhc.c | 18 -- 1 file changed, 4 insertions(+), 14 deletions(-) diff --git a/drivers/mmc/fsl_esdhc.c b/drivers/mmc/fsl_esdhc.c index 2b7bcab..25a8fe3 100644 --- a/drivers/mmc/fsl_esdhc.c +++ b/drivers/mmc/fsl_esdhc.c @@ -75,7 +75,6 @@ struct fsl_esdhc_plat { * @mmc: mmc * Following is used when Driver Model is enabled for MMC * @dev: pointer for the device - * @non_removable: 0: removable; 1: non-removable * @wp_enable: 1: enable checking wp; 0: no check * @cd_gpio: gpio for card detection * @wp_gpio: gpio for write protection @@ -89,7 +88,6 @@ struct fsl_esdhc_priv { struct mmc *mmc; #endif struct udevice *dev; - int non_removable; int wp_enable; }; @@ -628,12 +626,6 @@ static int esdhc_getcd_common(struct fsl_esdhc_priv *priv) if (CONFIG_ESDHC_DETECT_QUIRK) return 1; #endif - -#if CONFIG_IS_ENABLED(DM_MMC) - if (priv->non_removable) - return 1; -#endif - while (!(esdhc_read32(>prsstat) & PRSSTAT_CINS) && --timeout) udelay(1000); @@ -870,12 +862,6 @@ static int fsl_esdhc_probe(struct udevice *dev) #endif priv->dev = dev; - if (dev_read_bool(dev, "non-removable")) { - priv->non_removable = 1; -} else { - priv->non_removable = 0; - } - priv->wp_enable = 1; if (IS_ENABLED(CONFIG_CLK)) { @@ -919,8 +905,12 @@ static int fsl_esdhc_probe(struct udevice *dev) static int fsl_esdhc_get_cd(struct udevice *dev) { + struct fsl_esdhc_plat *plat = dev_get_platdata(dev); struct fsl_esdhc_priv *priv = dev_get_priv(dev); + if (plat->cfg.host_caps & MMC_CAP_NONREMOVABLE) + return 1; + return esdhc_getcd_common(priv); } -- 2.7.4 ___ U-Boot mailing list U-Boot@lists.denx.de https://lists.denx.de/listinfo/u-boot