Commit 78f87df2 authored by Ulf Hansson's avatar Ulf Hansson

mmc: mmci: Use the common mmc DT parser

Let mmci DT parser only handle the specific bindings related to mmci
and extend the DT support by converting to the common mmc DT parser.

While both DT and platform data exist, DT takes precedence. If there
are supplied DT data, the card detect and write protect GPIOS are
enforced to be provided through it.
Signed-off-by: default avatarUlf Hansson <ulf.hansson@linaro.org>
parent 1a7e99c1
...@@ -1386,12 +1386,9 @@ static struct mmc_host_ops mmci_ops = { ...@@ -1386,12 +1386,9 @@ static struct mmc_host_ops mmci_ops = {
.start_signal_voltage_switch = mmci_sig_volt_switch, .start_signal_voltage_switch = mmci_sig_volt_switch,
}; };
#ifdef CONFIG_OF
static void mmci_dt_populate_generic_pdata(struct device_node *np, static void mmci_dt_populate_generic_pdata(struct device_node *np,
struct mmci_platform_data *pdata) struct mmci_platform_data *pdata)
{ {
int bus_width = 0;
if (of_get_property(np, "st,sig-dir-dat0", NULL)) if (of_get_property(np, "st,sig-dir-dat0", NULL))
pdata->sigdir |= MCI_ST_DATA0DIREN; pdata->sigdir |= MCI_ST_DATA0DIREN;
if (of_get_property(np, "st,sig-dir-dat2", NULL)) if (of_get_property(np, "st,sig-dir-dat2", NULL))
...@@ -1404,46 +1401,22 @@ static void mmci_dt_populate_generic_pdata(struct device_node *np, ...@@ -1404,46 +1401,22 @@ static void mmci_dt_populate_generic_pdata(struct device_node *np,
pdata->sigdir |= MCI_ST_CMDDIREN; pdata->sigdir |= MCI_ST_CMDDIREN;
if (of_get_property(np, "st,sig-pin-fbclk", NULL)) if (of_get_property(np, "st,sig-pin-fbclk", NULL))
pdata->sigdir |= MCI_ST_FBCLKEN; pdata->sigdir |= MCI_ST_FBCLKEN;
}
pdata->gpio_wp = of_get_named_gpio(np, "wp-gpios", 0); static int mmci_of_parse(struct device_node *np, struct mmc_host *mmc)
pdata->gpio_cd = of_get_named_gpio(np, "cd-gpios", 0); {
int ret = mmc_of_parse(mmc);
if (of_get_property(np, "cd-inverted", NULL))
pdata->cd_invert = true;
else
pdata->cd_invert = false;
of_property_read_u32(np, "max-frequency", &pdata->f_max); if (ret)
if (!pdata->f_max) return ret;
pr_warn("%s has no 'max-frequency' property\n", np->full_name);
if (of_get_property(np, "mmc-cap-mmc-highspeed", NULL)) if (of_get_property(np, "mmc-cap-mmc-highspeed", NULL))
pdata->capabilities |= MMC_CAP_MMC_HIGHSPEED; mmc->caps |= MMC_CAP_MMC_HIGHSPEED;
if (of_get_property(np, "mmc-cap-sd-highspeed", NULL)) if (of_get_property(np, "mmc-cap-sd-highspeed", NULL))
pdata->capabilities |= MMC_CAP_SD_HIGHSPEED; mmc->caps |= MMC_CAP_SD_HIGHSPEED;
of_property_read_u32(np, "bus-width", &bus_width); return 0;
switch (bus_width) {
case 0 :
/* No bus-width supplied. */
break;
case 4 :
pdata->capabilities |= MMC_CAP_4_BIT_DATA;
break;
case 8 :
pdata->capabilities |= MMC_CAP_8_BIT_DATA;
break;
default :
pr_warn("%s: Unsupported bus width\n", np->full_name);
}
}
#else
static void mmci_dt_populate_generic_pdata(struct device_node *np,
struct mmci_platform_data *pdata)
{
return;
} }
#endif
static int mmci_probe(struct amba_device *dev, static int mmci_probe(struct amba_device *dev,
const struct amba_id *id) const struct amba_id *id)
...@@ -1474,6 +1447,10 @@ static int mmci_probe(struct amba_device *dev, ...@@ -1474,6 +1447,10 @@ static int mmci_probe(struct amba_device *dev,
if (!mmc) if (!mmc)
return -ENOMEM; return -ENOMEM;
ret = mmci_of_parse(np, mmc);
if (ret)
goto host_free;
host = mmc_priv(mmc); host = mmc_priv(mmc);
host->mmc = mmc; host->mmc = mmc;
...@@ -1526,14 +1503,15 @@ static int mmci_probe(struct amba_device *dev, ...@@ -1526,14 +1503,15 @@ static int mmci_probe(struct amba_device *dev,
else else
mmc->f_min = DIV_ROUND_UP(host->mclk, 512); mmc->f_min = DIV_ROUND_UP(host->mclk, 512);
/* /*
* If the platform data supplies a maximum operating * If no maximum operating frequency is supplied, fall back to use
* frequency, this takes precedence. Else, we fall back * the module parameter, which has a (low) default value in case it
* to using the module parameter, which has a (low) * is not specified. Either value must not exceed the clock rate into
* default value in case it is not specified. Either * the block, of course. Also note that DT takes precedence over
* value must not exceed the clock rate into the block, * platform data.
* of course.
*/ */
if (plat->f_max) if (mmc->f_max)
mmc->f_max = min(host->mclk, mmc->f_max);
else if (plat->f_max)
mmc->f_max = min(host->mclk, plat->f_max); mmc->f_max = min(host->mclk, plat->f_max);
else else
mmc->f_max = min(host->mclk, fmax); mmc->f_max = min(host->mclk, fmax);
...@@ -1546,11 +1524,14 @@ static int mmci_probe(struct amba_device *dev, ...@@ -1546,11 +1524,14 @@ static int mmci_probe(struct amba_device *dev,
else if (plat->ocr_mask) else if (plat->ocr_mask)
dev_warn(mmc_dev(mmc), "Platform OCR mask is ignored\n"); dev_warn(mmc_dev(mmc), "Platform OCR mask is ignored\n");
mmc->caps = plat->capabilities; /* DT takes precedence over platform data. */
mmc->caps2 = plat->capabilities2; mmc->caps = np ? mmc->caps : plat->capabilities;
mmc->caps2 = np ? mmc->caps2 : plat->capabilities2;
if (!np) {
if (!plat->cd_invert) if (!plat->cd_invert)
mmc->caps2 |= MMC_CAP2_CD_ACTIVE_HIGH; mmc->caps2 |= MMC_CAP2_CD_ACTIVE_HIGH;
mmc->caps2 |= MMC_CAP2_RO_ACTIVE_HIGH; mmc->caps2 |= MMC_CAP2_RO_ACTIVE_HIGH;
}
if (variant->busy_detect) { if (variant->busy_detect) {
mmci_ops.card_busy = mmci_card_busy; mmci_ops.card_busy = mmci_card_busy;
...@@ -1562,7 +1543,7 @@ static int mmci_probe(struct amba_device *dev, ...@@ -1562,7 +1543,7 @@ static int mmci_probe(struct amba_device *dev,
mmc->ops = &mmci_ops; mmc->ops = &mmci_ops;
/* We support these PM capabilities. */ /* We support these PM capabilities. */
mmc->pm_caps = MMC_PM_KEEP_POWER; mmc->pm_caps |= MMC_PM_KEEP_POWER;
/* /*
* We can do SGIO * We can do SGIO
...@@ -1599,20 +1580,13 @@ static int mmci_probe(struct amba_device *dev, ...@@ -1599,20 +1580,13 @@ static int mmci_probe(struct amba_device *dev,
writel(0, host->base + MMCIMASK1); writel(0, host->base + MMCIMASK1);
writel(0xfff, host->base + MMCICLEAR); writel(0xfff, host->base + MMCICLEAR);
if (plat->gpio_cd == -EPROBE_DEFER) { /* If DT, cd/wp gpios must be supplied through it. */
ret = -EPROBE_DEFER; if (!np && gpio_is_valid(plat->gpio_cd)) {
goto clk_disable;
}
if (gpio_is_valid(plat->gpio_cd)) {
ret = mmc_gpio_request_cd(mmc, plat->gpio_cd, 0); ret = mmc_gpio_request_cd(mmc, plat->gpio_cd, 0);
if (ret) if (ret)
goto clk_disable; goto clk_disable;
} }
if (plat->gpio_wp == -EPROBE_DEFER) { if (!np && gpio_is_valid(plat->gpio_wp)) {
ret = -EPROBE_DEFER;
goto clk_disable;
}
if (gpio_is_valid(plat->gpio_wp)) {
ret = mmc_gpio_request_ro(mmc, plat->gpio_wp); ret = mmc_gpio_request_ro(mmc, plat->gpio_wp);
if (ret) if (ret)
goto clk_disable; goto clk_disable;
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment