mmc: dw_mmc: add an option to force 32-bit access to 64-bit FIFO
PATCH v5 2/3 mmc: dw_mmc: add an option to force 32-bit access to 64-bit FIFO
Some Samsung Exynos boards using the arm64 architecture have DW MMC controllers configured for a 32-bit data bus but a 64-bit FIFO. On these systems the 64-bit FIFO registers must be accessed in two 32-bit halves.
--- drivers/mmc/host/dw_mmc-exynos.c | 43 ++++++++++- drivers/mmc/host/dw_mmc.c | 122 ++++++++++++++++++++++++++++++- drivers/mmc/host/dw_mmc.h | 2 + 3 files changed, 164 insertions(+), 3 deletions(-)
drivers/mmc/host/dw_mmc-exynos.c +42 -1
@@ -28,6 +28,8 @@ enum dw_mci_exynos_type {DW_MCI_TYPE_EXYNOS5420_SMU ,DW_MCI_TYPE_EXYNOS7 ,DW_MCI_TYPE_EXYNOS7_SMU , +DW_MCI_TYPE_EXYNOS78XX , +DW_MCI_TYPE_EXYNOS78XX_SMU , DW_MCI_TYPE_ARTPEC8, };
@@ -70,6 +72,12 @@ static struct dw_mci_exynos_compatible { }, { .compatible = "samsung,exynos7-dw-mshc-smu", .ctrl_type = DW_MCI_TYPE_EXYNOS7_SMU, + }, { + .compatible = "samsung,exynos7885-dw-mshc", + .ctrl_type = DW_MCI_TYPE_EXYNOS78XX, + }, { + .compatible = "samsung,exynos7885-dw-mshc-smu", + .ctrl_type = DW_MCI_TYPE_EXYNOS78XX_SMU, }, { .compatible = "axis,artpec8-dw-mshc", .ctrl_type = DW_MCI_TYPE_ARTPEC8,
@@ -86,6 +94,8 @@ static inline u8 dw_mci_exynos_get_ciu_div(struct dw_mci *host)return EXYNOS4210_FIXED_CIU_CLK_DIV ; else if (priv->ctrl_type == DW_MCI_TYPE_EXYNOS7 || priv->ctrl_type == DW_MCI_TYPE_EXYNOS7_SMU || + priv->ctrl_type == DW_MCI_TYPE_EXYNOS78XX || + priv->ctrl_type == DW_MCI_TYPE_EXYNOS78XX_SMU || priv->ctrl_type == DW_MCI_TYPE_ARTPEC8) return SDMMC_CLKSEL_GET_DIV(mci_readl(host, CLKSEL64)) + 1; else
@@ -101,7 +111,8 @@ static void dw_mci_exynos_config_smu(struct dw_mci *host)* set for non-ecryption mode at this time. */ if (priv->ctrl_type ==DW_MCI_TYPE_EXYNOS5420_SMU || - priv->ctrl_type ==DW_MCI_TYPE_EXYNOS7_SMU ) { + priv->ctrl_type ==DW_MCI_TYPE_EXYNOS7_SMU || + priv->ctrl_type ==DW_MCI_TYPE_EXYNOS78XX_SMU ) {mci_writel (host,MPSBEGIN0 ,0 );mci_writel (host,MPSEND0 ,SDMMC_ENDING_SEC_NR_MAX ); mci_writel(host, MPSCTRL0, SDMMC_MPSCTRL_SECURE_WRITE_BIT |
@@ -127,6 +138,12 @@ static int dw_mci_exynos_priv_init(struct dw_mci *host)DQS_CTRL_GET_RD_DELAY (priv->saved_strobe_ctrl); } +if (priv->ctrl_type ==DW_MCI_TYPE_EXYNOS78XX || + priv->ctrl_type ==DW_MCI_TYPE_EXYNOS78XX_SMU ) { +/* Quirk needed for certain Exynos SoCs */ + host->quirks |=DW_MMC_QUIRK_FIFO64_32 ; + } +if (priv->ctrl_type ==DW_MCI_TYPE_ARTPEC8 ) {/* Quirk needed for the ARTPEC-8 SoC */ host->quirks |=DW_MMC_QUIRK_EXTENDED_TMOUT ;
@@ -144,6 +161,8 @@ static void dw_mci_exynos_set_clksel_timing(struct dw_mci *host, u32 timing)if (priv->ctrl_type ==DW_MCI_TYPE_EXYNOS7 || priv->ctrl_type ==DW_MCI_TYPE_EXYNOS7_SMU || + priv->ctrl_type ==DW_MCI_TYPE_EXYNOS78XX || + priv->ctrl_type ==DW_MCI_TYPE_EXYNOS78XX_SMU || priv->ctrl_type ==DW_MCI_TYPE_ARTPEC8 ) clksel =mci_readl (host,CLKSEL64 );else
@@ -153,6 +172,8 @@ static void dw_mci_exynos_set_clksel_timing(struct dw_mci *host, u32 timing)if (priv->ctrl_type ==DW_MCI_TYPE_EXYNOS7 || priv->ctrl_type ==DW_MCI_TYPE_EXYNOS7_SMU || + priv->ctrl_type ==DW_MCI_TYPE_EXYNOS78XX || + priv->ctrl_type ==DW_MCI_TYPE_EXYNOS78XX_SMU || priv->ctrl_type ==DW_MCI_TYPE_ARTPEC8 )mci_writel (host,CLKSEL64 , clksel);else
@@ -223,6 +244,8 @@ static int dw_mci_exynos_resume_noirq(struct device *dev)if (priv->ctrl_type ==DW_MCI_TYPE_EXYNOS7 || priv->ctrl_type ==DW_MCI_TYPE_EXYNOS7_SMU || + priv->ctrl_type ==DW_MCI_TYPE_EXYNOS78XX || + priv->ctrl_type ==DW_MCI_TYPE_EXYNOS78XX_SMU || priv->ctrl_type ==DW_MCI_TYPE_ARTPEC8 ) clksel =mci_readl (host,CLKSEL64 );else
@@ -231,6 +254,8 @@ static int dw_mci_exynos_resume_noirq(struct device *dev)if (clksel &SDMMC_CLKSEL_WAKEUP_INT ) {if (priv->ctrl_type ==DW_MCI_TYPE_EXYNOS7 || priv->ctrl_type ==DW_MCI_TYPE_EXYNOS7_SMU || + priv->ctrl_type ==DW_MCI_TYPE_EXYNOS78XX || + priv->ctrl_type ==DW_MCI_TYPE_EXYNOS78XX_SMU || priv->ctrl_type ==DW_MCI_TYPE_ARTPEC8 )mci_writel (host,CLKSEL64 , clksel);else
@@ -410,6 +435,8 @@ static inline u8 dw_mci_exynos_get_clksmpl(struct dw_mci *host)if (priv->ctrl_type ==DW_MCI_TYPE_EXYNOS7 || priv->ctrl_type ==DW_MCI_TYPE_EXYNOS7_SMU || + priv->ctrl_type ==DW_MCI_TYPE_EXYNOS78XX || + priv->ctrl_type ==DW_MCI_TYPE_EXYNOS78XX_SMU || priv->ctrl_type ==DW_MCI_TYPE_ARTPEC8 )return SDMMC_CLKSEL_CCLK_SAMPLE (mci_readl (host,CLKSEL64 ));else
@@ -423,6 +450,8 @@ static inline void dw_mci_exynos_set_clksmpl(struct dw_mci *host, u8 sample)if (priv->ctrl_type ==DW_MCI_TYPE_EXYNOS7 || priv->ctrl_type ==DW_MCI_TYPE_EXYNOS7_SMU || + priv->ctrl_type ==DW_MCI_TYPE_EXYNOS78XX || + priv->ctrl_type ==DW_MCI_TYPE_EXYNOS78XX_SMU || priv->ctrl_type ==DW_MCI_TYPE_ARTPEC8 ) clksel =mci_readl (host,CLKSEL64 );else
@@ -430,6 +459,8 @@ static inline void dw_mci_exynos_set_clksmpl(struct dw_mci *host, u8 sample) clksel =SDMMC_CLKSEL_UP_SAMPLE (clksel, sample);if (priv->ctrl_type ==DW_MCI_TYPE_EXYNOS7 || priv->ctrl_type ==DW_MCI_TYPE_EXYNOS7_SMU || + priv->ctrl_type ==DW_MCI_TYPE_EXYNOS78XX || + priv->ctrl_type ==DW_MCI_TYPE_EXYNOS78XX_SMU || priv->ctrl_type ==DW_MCI_TYPE_ARTPEC8 )mci_writel (host,CLKSEL64 , clksel);else
@@ -444,6 +475,8 @@ static inline u8 dw_mci_exynos_move_next_clksmpl(struct dw_mci *host)if (priv->ctrl_type ==DW_MCI_TYPE_EXYNOS7 || priv->ctrl_type ==DW_MCI_TYPE_EXYNOS7_SMU || + priv->ctrl_type ==DW_MCI_TYPE_EXYNOS78XX || + priv->ctrl_type ==DW_MCI_TYPE_EXYNOS78XX_SMU || priv->ctrl_type ==DW_MCI_TYPE_ARTPEC8 ) clksel =mci_readl (host,CLKSEL64 );else
@@ -454,6 +487,8 @@ static inline u8 dw_mci_exynos_move_next_clksmpl(struct dw_mci *host)if (priv->ctrl_type ==DW_MCI_TYPE_EXYNOS7 || priv->ctrl_type ==DW_MCI_TYPE_EXYNOS7_SMU || + priv->ctrl_type ==DW_MCI_TYPE_EXYNOS78XX || + priv->ctrl_type ==DW_MCI_TYPE_EXYNOS78XX_SMU || priv->ctrl_type ==DW_MCI_TYPE_ARTPEC8 )mci_writel (host,CLKSEL64 , clksel);else
@@ -633,6 +668,12 @@ static const struct of_device_id dw_mci_exynos_match[] = { .data = &exynos_drv_data, }, { .compatible = "samsung,exynos7-dw-mshc-smu", .data = &exynos_drv_data, }, + /* XXX: more SoCs probably have the same quirk, + the compatible should be something more generic */ + { .compatible = "samsung,exynos7885-dw-mshc", + .data = &exynos_drv_data, }, + { .compatible = "samsung,exynos7885-dw-mshc-smu", + .data = &exynos_drv_data, }, { .compatible = "axis,artpec8-dw-mshc", .data = &artpec_drv_data, }, {},
drivers/mmc/host/dw_mmc.c +120 -2
134 lines not on this page · raw message
drivers/mmc/host/dw_mmc.h +2 -0
@@ -280,6 +280,8 @@ struct dw_mci_board {/* Support for longer data read timeout */ #define DW_MMC_QUIRK_EXTENDED_TMOUT BIT(0) +/* Force 32-bit access to the FIFO */ +#define DW_MMC_QUIRK_FIFO64_32 BIT(1)#define DW_MMC_240A 0x240a#define DW_MMC_280A 0x280a
Signature · 1 line
2.38.3