Skip to contentSkip to conversation

mmc_of_parse() adaptations, switch mvsdio to mmc_of_parse()

PATCH RESEND New Simon Baatz 4 participants 13 messages Jun 9, 2013 – Jun 27, 2013

Subsystems (7)
lore
Share & tools
lore
#0 lore raw

v3 cover mmc_of_parse() adaptations, switch mvsdio to mmc_of_parse()

Hi,

RESEND V3:
- Dropped patches 9 and 10, they are part of linux-next already
NB: patch 7 as well, but I did not want to change the numbering

V3 changes:
- Patch 01/10: Added EPROBE_DEFER case to mmc_of_parse()
- Added Acked-By to (unmodified) patches 02 and 03.

V2 changes:
- Converted mvsdio to use mmc_of_parse()
- Adapted DTS files using mvsdio accordingly
- Changed mmc_of_parse() to return errors to the caller

While adding DT support for the Sheevaplugs by Globalscale Technologies (Kirkwood), it turned out that the DT binding of mvsdio lacked features to properly support the hardware (active high/low of CD and WP pins could not be described in DT).

This is standard functionality provided by the mmc_of_parse() helper function. However, mmc_of_parse() may allocate GPIO lines. If the allocation fails, it outputs an error, but does not return an error to its caller. Therefore, a proposal to handle errors in mmc_of_parse() is made. This also allows to handle the EPROBE_DEFER case when GPIO is not loaded yet.

The patch set is structured as follows:

1 Adapt mmc_of_parse() to return errors
2-6 Handle errors in current drivers using mmc_of_parse() (compile tested
only)
7-8 Convert mvsdio and respective dts files to mmc_of_parse() (tested on
kirkwood)

Simon Baatz (8):
mmc: return mmc_of_parse() errors to caller
mmc: sh_mmcif: handle mmc_of_parse() errors during probe
mmc: tmio-mmc: handle mmc_of_parse() errors during probe
mmc: mxcmmc: handle mmc_of_parse() errors during probe
mmc: sdhci-pxav3: handle mmc_of_parse() errors during probe
mmc: tegra: handle mmc_of_parse() errors during probe
ARM: mvebu: Use standard MMC binding for all users of mvsdio
mmc: mvsdio: use standard MMC device-tree binding parser

    mmc_of_parse()
 arch/arm/boot/dts/armada-370-db.dts                |    1 +
 arch/arm/boot/dts/armada-370-mirabox.dts           |    1 +
 arch/arm/boot/dts/armada-370-rd.dts                |    1 +
 arch/arm/boot/dts/armada-370-xp.dtsi               |    4 ++
 arch/arm/boot/dts/armada-xp-db.dts                 |    1 +
 arch/arm/boot/dts/kirkwood-dreamplug.dts           |    1 +
 .../arm/boot/dts/kirkwood-guruplug-server-plus.dts |    2 +
 arch/arm/boot/dts/kirkwood-mplcec4.dts             |    2 +-
 arch/arm/boot/dts/kirkwood-topkick.dts             |    1 +
 arch/arm/boot/dts/kirkwood.dtsi                    |    4 ++
 drivers/mmc/core/host.c                            |   30 ++++++--
 drivers/mmc/host/mvsdio.c                          |   73 +++++++++++---------
 drivers/mmc/host/mxcmmc.c                          |    4 +-
 drivers/mmc/host/sdhci-pxav3.c                     |    7 +-
 drivers/mmc/host/sdhci-tegra.c                     |    9 ++-
 drivers/mmc/host/sh_mmcif.c                        |    7 +-
 drivers/mmc/host/tmio_mmc_pio.c                    |    4 +-
 include/linux/mmc/host.h                           |    2 +-
 18 files changed, 106 insertions(+), 48 deletions(-)
Signature · 1 line
1.7.9.5
#1 lore raw

PATCH RESEND v3 1/8 mmc: return mmc_of_parse() errors to caller

In addition to just logging errors encountered during DT parsing or allocating GPIO slots for CD/WP, mmc_of_parse() now returns with an error.

In particular, this is needed if the GPIO allocation may return EPROBE_DEFER.

---

changes in V3:
- Handle EPROBE_DEFER case

 drivers/mmc/core/host.c  |   30 +++++++++++++++++++++++++-----
 include/linux/mmc/host.h |    2 +-
 2 files changed, 26 insertions(+), 6 deletions(-)
drivers/mmc/core/host.c +25 -5
index 2a3593d..89f5849 100644
@@ -306,7 +306,7 @@ static inline void mmc_host_clk_sysfs_init(struct mmc_host *host)
  * parse the properties and set respective generic mmc-host flags and
  * parameters.
  */
-void mmc_of_parse(struct mmc_host *host)
+int mmc_of_parse(struct mmc_host *host)
 {
 	struct device_node *np;
 	u32 bus_width;
@@ -315,7 +315,7 @@ void mmc_of_parse(struct mmc_host *host)
 	int len, ret, gpio;
 
 	if (!host->parent || !host->parent->of_node)
-		return;
+		return 0;
 
 	np = host->parent->of_node;
 
@@ -338,6 +338,7 @@ void mmc_of_parse(struct mmc_host *host)
 	default:
 		dev_err(host->parent,
 			"Invalid \"bus-width\" value %ud!\n", bus_width);
+		return -EINVAL;
 	}
 
 	/* f_max is obtained from the optional "max-frequency" property */
@@ -367,18 +368,22 @@ void mmc_of_parse(struct mmc_host *host)
 			host->caps |= MMC_CAP_NEEDS_POLL;
 
 		gpio = of_get_named_gpio_flags(np, "cd-gpios", 0, &flags);
+		if (gpio == -EPROBE_DEFER)
+			return gpio;
 		if (gpio_is_valid(gpio)) {
 			if (!(flags & OF_GPIO_ACTIVE_LOW))
 				gpio_inv_cd = true;
 
 			ret = mmc_gpio_request_cd(host, gpio);
-			if (ret < 0)
+			if (ret < 0) {
 				dev_err(host->parent,
 					"Failed to request CD GPIO #%d: %d!\n",
 					gpio, ret);
-			else
+				return ret;
+			} else {
 				dev_info(host->parent, "Got CD GPIO #%d.\n",
 					 gpio);
+			}
 		}
 
 		if (explicit_inv_cd ^ gpio_inv_cd)
@@ -389,14 +394,23 @@ void mmc_of_parse(struct mmc_host *host)
 	explicit_inv_wp = of_property_read_bool(np, "wp-inverted");
 
 	gpio = of_get_named_gpio_flags(np, "wp-gpios", 0, &flags);
+	if (gpio == -EPROBE_DEFER) {
+		ret = -EPROBE_DEFER;
+		goto out;
+	}
 	if (gpio_is_valid(gpio)) {
 		if (!(flags & OF_GPIO_ACTIVE_LOW))
 			gpio_inv_wp = true;
 
 		ret = mmc_gpio_request_ro(host, gpio);
-		if (ret < 0)
+		if (ret < 0) {
 			dev_err(host->parent,
 				"Failed to request WP GPIO: %d!\n", ret);
+			goto out;
+		} else {
+				dev_info(host->parent, "Got WP GPIO #%d.\n",
+					 gpio);
+		}
 	}
 	if (explicit_inv_wp ^ gpio_inv_wp)
 		host->caps2 |= MMC_CAP2_RO_ACTIVE_HIGH;
@@ -413,6 +427,12 @@ void mmc_of_parse(struct mmc_host *host)
 		host->pm_caps |= MMC_PM_KEEP_POWER;
 	if (of_find_property(np, "enable-sdio-wakeup", &len))
 		host->pm_caps |= MMC_PM_WAKE_SDIO_IRQ;
+
+	return 0;
+
+out:
+	mmc_gpio_free_cd(host);
+	return ret;
 }
 
 EXPORT_SYMBOL(mmc_of_parse);
include/linux/mmc/host.h +1 -1
index e326ae2..c8c4fbc 100644
@@ -369,7 +369,7 @@ struct mmc_host *mmc_alloc_host(int extra, struct device *);
 int mmc_add_host(struct mmc_host *);
 void mmc_remove_host(struct mmc_host *);
 void mmc_free_host(struct mmc_host *);
-void mmc_of_parse(struct mmc_host *host);
+int mmc_of_parse(struct mmc_host *host);
 
 static inline void *mmc_priv(struct mmc_host *host)
 {
Signature · 1 line
1.7.9.5
#2 lore raw

PATCH RESEND v3 2/8 mmc: sh_mmcif: handle mmc_of_parse() errors during probe

In reply to Simon Baatz
---
 drivers/mmc/host/sh_mmcif.c |    7 ++++++-
 1 file changed, 6 insertions(+), 1 deletion(-)
drivers/mmc/host/sh_mmcif.c +6 -1
index ba76a53..6ded7fb 100644
@@ -1369,7 +1369,11 @@ static int sh_mmcif_probe(struct platform_device *pdev)
 		ret = -ENOMEM;
 		goto ealloch;
 	}
-	mmc_of_parse(mmc);
+
+	ret = mmc_of_parse(mmc);
+	if (ret < 0)
+		goto eofparse;
+
 	host		= mmc_priv(mmc);
 	host->mmc	= mmc;
 	host->addr	= reg;
@@ -1464,6 +1468,7 @@ eclkupdate:
 	clk_put(host->hclk);
 eclkget:
 	pm_runtime_disable(&pdev->dev);
+eofparse:
 	mmc_free_host(mmc);
 ealloch:
 	iounmap(reg);
Signature · 1 line
1.7.9.5
#3 lore raw

PATCH RESEND v3 3/8 mmc: tmio-mmc: handle mmc_of_parse() errors during probe

In reply to Simon Baatz
---
 drivers/mmc/host/tmio_mmc_pio.c |    4 +++-
 1 file changed, 3 insertions(+), 1 deletion(-)
drivers/mmc/host/tmio_mmc_pio.c +3 -1
index f508ecb..f1a9d4a 100644
@@ -988,7 +988,9 @@ int tmio_mmc_host_probe(struct tmio_mmc_host **host,
 	if (!mmc)
 		return -ENOMEM;
 
-	mmc_of_parse(mmc);
+	ret = mmc_of_parse(mmc);
+	if (ret < 0)
+		goto host_free;
 
 	pdata->dev = &pdev->dev;
 	_host = mmc_priv(mmc);
Signature · 1 line
1.7.9.5
#4 lore raw

PATCH RESEND v3 4/8 mmc: mxcmmc: handle mmc_of_parse() errors during probe

In reply to Simon Baatz
---
 drivers/mmc/host/mxcmmc.c |    4 +++-
 1 file changed, 3 insertions(+), 1 deletion(-)
drivers/mmc/host/mxcmmc.c +3 -1
index d503635..f47546f 100644
@@ -1067,7 +1067,9 @@ static int mxcmci_probe(struct platform_device *pdev)
 		goto out_release_mem;
 	}
 
-	mmc_of_parse(mmc);
+	ret = mmc_of_parse(mmc);
+	if (ret)
+		goto out_free;
 	mmc->ops = &mxcmci_ops;
 
 	/* For devicetree parsing, the bus width is read from devicetree */
Signature · 1 line
1.7.9.5
#5 lore raw

PATCH RESEND v3 5/8 mmc: sdhci-pxav3: handle mmc_of_parse() errors during probe

In reply to Simon Baatz
---
 drivers/mmc/host/sdhci-pxav3.c |    7 +++++--
 1 file changed, 5 insertions(+), 2 deletions(-)
drivers/mmc/host/sdhci-pxav3.c +5 -2
index 1ae358e..67ea388 100644
@@ -252,7 +252,9 @@ static int sdhci_pxav3_probe(struct platform_device *pdev)
 
 	match = of_match_device(of_match_ptr(sdhci_pxav3_of_match), &pdev->dev);
 	if (match) {
-		mmc_of_parse(host->mmc);
+		ret = mmc_of_parse(host->mmc);
+		if (ret)
+			goto err_of_parse;
 		sdhci_get_of_property(pdev);
 		pdata = pxav3_get_mmc_pdata(dev);
 	} else if (pdata) {
@@ -313,10 +315,11 @@ static int sdhci_pxav3_probe(struct platform_device *pdev)
 
 	return 0;
 
+err_of_parse:
+err_cd_req:
 err_add_host:
 	clk_disable_unprepare(clk);
 	clk_put(clk);
-err_cd_req:
 err_clk_get:
 	sdhci_pltfm_free(pdev);
 	kfree(pxa);
Signature · 1 line
1.7.9.5
#6 lore raw

PATCH RESEND v3 6/8 mmc: tegra: handle mmc_of_parse() errors during probe

In reply to Simon Baatz
---
 drivers/mmc/host/sdhci-tegra.c |    9 ++++++---
 1 file changed, 6 insertions(+), 3 deletions(-)
drivers/mmc/host/sdhci-tegra.c +6 -3
index e0dba74..7eb62f8 100644
@@ -205,7 +205,7 @@ static const struct of_device_id sdhci_tegra_dt_match[] = {
 };
 MODULE_DEVICE_TABLE(of, sdhci_tegra_dt_match);
 
-static void sdhci_tegra_parse_dt(struct device *dev)
+static int sdhci_tegra_parse_dt(struct device *dev)
 {
 	struct device_node *np = dev->of_node;
 	struct sdhci_host *host = dev_get_drvdata(dev);
@@ -213,7 +213,7 @@ static void sdhci_tegra_parse_dt(struct device *dev)
 	struct sdhci_tegra *tegra_host = pltfm_host->priv;
 
 	tegra_host->power_gpio = of_get_named_gpio(np, "power-gpios", 0);
-	mmc_of_parse(host->mmc);
+	return mmc_of_parse(host->mmc);
 }
 
 static int sdhci_tegra_probe(struct platform_device *pdev)
@@ -245,7 +245,9 @@ static int sdhci_tegra_probe(struct platform_device *pdev)
 	tegra_host->soc_data = soc_data;
 	pltfm_host->priv = tegra_host;
 
-	sdhci_tegra_parse_dt(&pdev->dev);
+	rc = sdhci_tegra_parse_dt(&pdev->dev);
+	if (rc)
+		goto err_parse_dt;
 
 	if (gpio_is_valid(tegra_host->power_gpio)) {
 		rc = gpio_request(tegra_host->power_gpio, "sdhci_power");
@@ -278,6 +280,7 @@ err_add_host:
 err_clk_get:
 	if (gpio_is_valid(tegra_host->power_gpio))
 		gpio_free(tegra_host->power_gpio);
+err_parse_dt:
 err_power_req:
 err_alloc_tegra_host:
 	sdhci_pltfm_free(pdev);
Signature · 1 line
1.7.9.5
#7 lore raw

PATCH RESEND v3 6/8 mmc: tegra: handle mmc_of_parse() errors during probe

Quoted 1 line · Simon Baatz

(On Seaboard/Springbank board, i.e. Tegra20)

drivers/mmc/host/sdhci-tegra.c err_add_host: · line 285

Quoted 5 lines
drivers/mmc/host/sdhci-tegra.c +1 -0
 
+err_parse_dt:
 err_power_req:
 err_alloc_tegra_host:

Nit: It'd be nice if that new label got inserted into the middle of the list, so err_power_req, err_parse_dt, err_alloc_tegra_host. That way if we ever needed to add separate code there, they'd be in the right order already. Still, this isn't worth fixing unless you have to repost for some other reason I guess.

#8 lore raw

PATCH RESEND v3 6/8 mmc: tegra: handle mmc_of_parse() errors during probe

Hi Stephen,

Quoted 4 lines · Stephen Warren
Quoted 1 line · Simon Baatz

Thanks!

Quoted 8 lines

(On Seaboard/Springbank board, i.e. Tegra20)

drivers/mmc/host/sdhci-tegra.c err_add_host: · line 285

Quoted 5 lines
drivers/mmc/host/sdhci-tegra.c +1 -0
 
+err_parse_dt:
 err_power_req:
 err_alloc_tegra_host:
Quoted 5 lines

Nit: It'd be nice if that new label got inserted into the middle of the list, so err_power_req, err_parse_dt, err_alloc_tegra_host. That way if we ever needed to add separate code there, they'd be in the right order already. Still, this isn't worth fixing unless you have to repost for some other reason I guess.

Yes, you are right. I updated the patch locally, so the update will be in if I need to repost (or if the nicer version is explicitly requested).

Since this change is only syntactical, I simply assume that your Tested-by is still valid even with the change ;-)

- Simon

#9 lore raw

PATCH RESEND v3 7/8 ARM: mvebu: Use standard MMC binding for all users of mvsdio

In reply to Simon Baatz

In order to prepare the switch to the standard MMC device tree parser for mvsdio, adapt all current uses of mvsdio in the dts files to the standard format.

---
 arch/arm/boot/dts/armada-370-db.dts                |    1 +
 arch/arm/boot/dts/armada-370-mirabox.dts           |    1 +
 arch/arm/boot/dts/armada-370-rd.dts                |    1 +
 arch/arm/boot/dts/armada-370-xp.dtsi               |    4 ++++
 arch/arm/boot/dts/armada-xp-db.dts                 |    1 +
 arch/arm/boot/dts/kirkwood-dreamplug.dts           |    1 +
 .../arm/boot/dts/kirkwood-guruplug-server-plus.dts |    2 ++
 arch/arm/boot/dts/kirkwood-mplcec4.dts             |    2 +-
 arch/arm/boot/dts/kirkwood-topkick.dts             |    1 +
 arch/arm/boot/dts/kirkwood.dtsi                    |    4 ++++
 10 files changed, 17 insertions(+), 1 deletion(-)
arch/arm/boot/dts/armada-370-db.dts +1 -0
index 2353b1f..beee169 100644
@@ -74,6 +74,7 @@
 				 */
 				status = "disabled";
 				/* No CD or WP GPIOs */
+				broken-cd;
 			};
 
 			usb at 50000 {
arch/arm/boot/dts/armada-370-mirabox.dts +1 -0
index 14e36e1..45b1077 100644
@@ -99,6 +99,7 @@
 				 * No CD or WP GPIOs: SDIO interface used for
 				 * Wifi/Bluetooth chip
 				 */
+				 broken-cd;
 			};
 
 			usb at 50000 {
arch/arm/boot/dts/armada-370-rd.dts +1 -0
index 130f839..89c2110 100644
@@ -64,6 +64,7 @@
 				pinctrl-names = "default";
 				status = "okay";
 				/* No CD or WP GPIOs */
+				broken-cd;
 			};
 
 			usb at 50000 {
arch/arm/boot/dts/armada-370-xp.dtsi +4 -0
index 550eb77..0d73570 100644
@@ -143,6 +143,10 @@
 				reg = <0xd4000 0x200>;
 				interrupts = <54>;
 				clocks = <&gateclk 17>;
+				bus-width = <4>;
+				cap-sdio-irq;
+				cap-sd-highspeed;
+				cap-mmc-highspeed;
 				status = "disabled";
 			};
 
arch/arm/boot/dts/armada-xp-db.dts +1 -0
index d6cc8bf..7c22a20 100644
@@ -97,6 +97,7 @@
 				pinctrl-names = "default";
 				status = "okay";
 				/* No CD or WP GPIOs */
+				broken-cd;
 			};
 
 			usb at 50000 {
arch/arm/boot/dts/kirkwood-dreamplug.dts +1 -0
index 289e51d..be16a84 100644
@@ -79,6 +79,7 @@
 			pinctrl-names = "default";
 			status = "okay";
 			/* No CD or WP GPIOs */
+			broken-cd;
 		};
 	};
 
arch/arm/boot/dts/kirkwood-guruplug-server-plus.dts +2 -0
index 44fd97d..484a2a6 100644
@@ -72,6 +72,8 @@
 
 		mvsdio at 90000 {
 			status = "okay";
+			/* No CD or WP GPIOs */
+			broken-cd;
 		};
 	};
 
arch/arm/boot/dts/kirkwood-mplcec4.dts +1 -1
index 7588241..bf3a58c 100644
@@ -136,7 +136,7 @@
 			pinctrl-0 = <&pmx_sdio &pmx_sdio_cd>;
 			pinctrl-names = "default";
 			status = "okay";
-			cd-gpios = <&gpio1 15 0>;
+			cd-gpios = <&gpio1 15 1>;
 			/* No WP GPIO */
 		};
 	};
arch/arm/boot/dts/kirkwood-topkick.dts +1 -0
index 66eb45b..7dc14f4 100644
@@ -154,6 +154,7 @@
 			pinctrl-names = "default";
 			status = "okay";
 			/* No CD or WP GPIOs */
+			broken-cd;
 		};
 	};
 
arch/arm/boot/dts/kirkwood.dtsi +4 -0
index fada7e6..e2a28db 100644
@@ -200,6 +200,10 @@
 			reg = <0x90000 0x200>;
 			interrupts = <28>;
 			clocks = <&gate_clk 4>;
+			bus-width = <4>;
+			cap-sdio-irq;
+			cap-sd-highspeed;
+			cap-mmc-highspeed;
 			status = "disabled";
 		};
 	};
Signature · 1 line
1.7.9.5
#10 lore raw

PATCH RESEND v3 8/8 mmc: mvsdio: use standard MMC device-tree binding parser mmc_of_parse()

In reply to Simon Baatz

Instead of parsing the DT binding on our own, use the standard parser mmc_of_parse(), introduced by commit 6c56e7a.

---
 drivers/mmc/host/mvsdio.c |   73 +++++++++++++++++++++++++--------------------
 1 file changed, 40 insertions(+), 33 deletions(-)
drivers/mmc/host/mvsdio.c +40 -33
index 8960fc8..edfc481 100644
@@ -35,7 +35,7 @@
 
 #define DRIVER_NAME	"mvsdio"
 
-static int maxfreq = MVSD_CLOCKRATE_MAX;
+static int maxfreq;
 static int nodma;
 
 struct mvsd_host {
@@ -685,7 +685,6 @@ static int __init mvsd_probe(struct platform_device *pdev)
 	const struct mbus_dram_target_info *dram;
 	struct resource *r;
 	int ret, irq;
-	int gpio_card_detect, gpio_write_protect;
 	struct pinctrl *pinctrl;
 
 	r = platform_get_resource(pdev, IORESOURCE_MEM, 0);
@@ -718,6 +717,20 @@ static int __init mvsd_probe(struct platform_device *pdev)
 	if (!IS_ERR(host->clk))
 		clk_prepare_enable(host->clk);
 
+	mmc->ops = &mvsd_ops;
+
+	mmc->ocr_avail = MMC_VDD_32_33 | MMC_VDD_33_34;
+
+	mmc->f_min = DIV_ROUND_UP(host->base_clock, MVSD_BASE_DIV_MAX);
+	mmc->f_max = MVSD_CLOCKRATE_MAX;
+
+	mmc->max_blk_size = 2048;
+	mmc->max_blk_count = 65535;
+
+	mmc->max_segs = 1;
+	mmc->max_seg_size = mmc->max_blk_size * mmc->max_blk_count;
+	mmc->max_req_size = mmc->max_blk_size * mmc->max_blk_count;
+
 	if (np) {
 		if (IS_ERR(host->clk)) {
 			dev_err(&pdev->dev, "DT platforms must have a clock associated\n");
@@ -726,35 +739,38 @@ static int __init mvsd_probe(struct platform_device *pdev)
 		}
 
 		host->base_clock = clk_get_rate(host->clk) / 2;
-		gpio_card_detect = of_get_named_gpio(np, "cd-gpios", 0);
-		gpio_write_protect = of_get_named_gpio(np, "wp-gpios", 0);
+		ret = mmc_of_parse(mmc);
+		if (ret < 0)
+			goto out;
 	} else {
 		const struct mvsdio_platform_data *mvsd_data;
+
 		mvsd_data = pdev->dev.platform_data;
 		if (!mvsd_data) {
 			ret = -ENXIO;
 			goto out;
 		}
+		mmc->caps = MMC_CAP_4_BIT_DATA | MMC_CAP_SDIO_IRQ |
+			    MMC_CAP_SD_HIGHSPEED | MMC_CAP_MMC_HIGHSPEED;
 		host->base_clock = mvsd_data->clock / 2;
-		gpio_card_detect = mvsd_data->gpio_card_detect ? : -EINVAL;
-		gpio_write_protect = mvsd_data->gpio_write_protect ? : -EINVAL;
-	}
-
-	mmc->ops = &mvsd_ops;
-
-	mmc->ocr_avail = MMC_VDD_32_33 | MMC_VDD_33_34;
-	mmc->caps = MMC_CAP_4_BIT_DATA | MMC_CAP_SDIO_IRQ |
-		    MMC_CAP_SD_HIGHSPEED | MMC_CAP_MMC_HIGHSPEED;
-
-	mmc->f_min = DIV_ROUND_UP(host->base_clock, MVSD_BASE_DIV_MAX);
-	mmc->f_max = maxfreq;
+		/* GPIO 0 regarded as invalid for backward compatibility */
+		if (mvsd_data->gpio_card_detect &&
+		    gpio_is_valid(mvsd_data->gpio_card_detect)) {
+			ret = mmc_gpio_request_cd(mmc,
+						  mvsd_data->gpio_card_detect);
+			if (ret)
+				goto out;
+		} else {
+			mmc->caps |= MMC_CAP_NEEDS_POLL;
+		}
 
-	mmc->max_blk_size = 2048;
-	mmc->max_blk_count = 65535;
+		if (mvsd_data->gpio_write_protect &&
+		    gpio_is_valid(mvsd_data->gpio_write_protect))
+			mmc_gpio_request_ro(mmc, mvsd_data->gpio_write_protect);
+	}
 
-	mmc->max_segs = 1;
-	mmc->max_seg_size = mmc->max_blk_size * mmc->max_blk_count;
-	mmc->max_req_size = mmc->max_blk_size * mmc->max_blk_count;
+	if (maxfreq)
+		mmc->f_max = maxfreq;
 
 	spin_lock_init(&host->lock);
 
@@ -777,15 +793,6 @@ static int __init mvsd_probe(struct platform_device *pdev)
 		goto out;
 	}
 
-	if (gpio_is_valid(gpio_card_detect)) {
-		ret = mmc_gpio_request_cd(mmc, gpio_card_detect);
-		if (ret)
-			goto out;
-	} else
-		mmc->caps |= MMC_CAP_NEEDS_POLL;
-
-	mmc_gpio_request_ro(mmc, gpio_write_protect);
-
 	setup_timer(&host->timer, mvsd_timeout_timer, (unsigned long)host);
 	platform_set_drvdata(pdev, mmc);
 	ret = mmc_add_host(mmc);
@@ -793,10 +800,10 @@ static int __init mvsd_probe(struct platform_device *pdev)
 		goto out;
 
 	if (!(mmc->caps & MMC_CAP_NEEDS_POLL))
-		dev_notice(&pdev->dev, "using GPIO %d for card detection\n",
-			   gpio_card_detect);
+		dev_notice(&pdev->dev, "using GPIO for card detection\n");
 	else
-		dev_notice(&pdev->dev, "lacking card detect (fall back to polling)\n");
+		dev_notice(&pdev->dev,
+			   "lacking card detect (fall back to polling)\n");
 	return 0;
 
 out:
Signature · 1 line
1.7.9.5
#11 lore raw

v3 cover mmc_of_parse() adaptations, switch mvsdio to mmc_of_parse()

In reply to Simon Baatz
Quoted 27 lines · Simon Baatz

Hi,

RESEND V3:
- Dropped patches 9 and 10, they are part of linux-next already
NB: patch 7 as well, but I did not want to change the numbering

V3 changes:
- Patch 01/10: Added EPROBE_DEFER case to mmc_of_parse()
- Added Acked-By to (unmodified) patches 02 and 03.

V2 changes:
- Converted mvsdio to use mmc_of_parse()
- Adapted DTS files using mvsdio accordingly
- Changed mmc_of_parse() to return errors to the caller

While adding DT support for the Sheevaplugs by Globalscale Technologies (Kirkwood), it turned out that the DT binding of mvsdio lacked features to properly support the hardware (active high/low of CD and WP pins could not be described in DT).

This is standard functionality provided by the mmc_of_parse() helper function. However, mmc_of_parse() may allocate GPIO lines. If the allocation fails, it outputs an error, but does not return an error to its caller. Therefore, a proposal to handle errors in mmc_of_parse() is made. This also allows to handle the EPROBE_DEFER case when GPIO is not loaded yet.

Quoted 7 lines

The patch set is structured as follows:

1 Adapt mmc_of_parse() to return errors
2-6 Handle errors in current drivers using mmc_of_parse() (compile tested
only)
7-8 Convert mvsdio and respective dts files to mmc_of_parse() (tested on
kirkwood)

Hi Simon

I tested on kirkwood topkick with DT. SDIO wifi device is found.

Andrew

#12 lore raw

v3 cover mmc_of_parse() adaptations, switch mvsdio to mmc_of_parse()

In reply to Simon Baatz

Hi Simon,

Quoted 3 lines · Simon Baatz

RESEND V3:
- Dropped patches 9 and 10, they are part of linux-next already
NB: patch 7 as well, but I did not want to change the numbering

I've pushed all patches except 7 to mmc-next for 3.11 now, and I made Stephen Warren's nit change to patch 6. Thanks!

- Chris.

Signature · 2 lines
Chris Ball   <[email protected]>   <http://printf.net/>
One Laptop Per Child