#define MPSCTRL_ENCRYPTION (0x1<<1)
#define MPSCTRL_VALID (0x1<<0)
+/* CLKSEL Register */
+#define DWMCI_DIVRATIO_BIT 24
+#define DWMCI_DIVRATIO_MASK 0x7
+
#ifdef CONFIG_OF_CONTROL
int exynos_dwmmc_init(const void *blob);
#endif
* host->bus_hz should be set from user.
*/
if (host->get_mmc_clk)
- sclk = host->get_mmc_clk(host->dev_index);
+ sclk = host->get_mmc_clk(host);
else if (host->bus_hz)
sclk = host->bus_hz;
else {
dwmci_writel(host, DWMCI_CLKSEL, host->clksel_val);
}
-unsigned int exynos_dwmci_get_clk(int dev_index)
+unsigned int exynos_dwmci_get_clk(struct dwmci_host *host)
{
- return get_mmc_clk(dev_index);
+ unsigned long sclk;
+ int8_t clk_div;
+
+ /*
+ * Since SDCLKIN is divided inside controller by the DIVRATIO
+ * value set in the CLKSEL register, we need to use the same output
+ * clock value to calculate the CLKDIV value.
+ * as per user manual:cclk_in = SDCLKIN / (DIVRATIO + 1)
+ */
+ clk_div = ((dwmci_readl(host, DWMCI_CLKSEL) >> DWMCI_DIVRATIO_BIT)
+ & DWMCI_DIVRATIO_MASK) + 1;
+ sclk = get_mmc_clk(host->dev_index);
+
+ return sclk / clk_div;
}
static void exynos_dwmci_board_init(struct dwmci_host *host)
void (*clksel)(struct dwmci_host *host);
void (*board_init)(struct dwmci_host *host);
- unsigned int (*get_mmc_clk)(int dev_index);
+ unsigned int (*get_mmc_clk)(struct dwmci_host *host);
};
struct dwmci_idmac {