From: Roger Quadros <rogerq@ti.com> To: <davem@davemloft.net>, Andrew Lunn <andrew@lunn.ch>, Florian Fainelli <f.fainelli@gmail.com> Cc: <tony@atomide.com>, <nsekhar@ti.com>, <jsarha@ti.com>, <netdev@vger.kernel.org>, <linux-omap@vger.kernel.org>, <linux-kernel@vger.kernel.org>, <rogerq@ti.com> Subject: [PATCH] mdio_bus: Issue GPIO RESET to PHYs. Date: Wed, 19 Apr 2017 12:24:26 +0300 [thread overview] Message-ID: <64d6494d-41d2-0faf-a434-057f796637fe@ti.com> (raw) In-Reply-To: <1491381237-24635-1-git-send-email-rogerq@ti.com> Some boards [1] leave the PHYs at an invalid state during system power-up or reset thus causing unreliability issues with the PHY which manifests as PHY not being detected or link not functional. To fix this, these PHYs need to be RESET via a GPIO connected to the PHY's RESET pin. Some boards have a single GPIO controlling the PHY RESET pin of all PHYs on the bus whereas some others have separate GPIOs controlling individual PHY RESETs. In both cases, the RESET de-assertion cannot be done in the PHY driver as the PHY will not probe till its reset is de-asserted. So do the RESET de-assertion in the MDIO bus driver. [1] - am572x-idk, am571x-idk, a437x-idk Signed-off-by: Roger Quadros <rogerq@ti.com> --- drivers/net/phy/mdio_bus.c | 26 ++++++++++++++++++++++++++ drivers/of/of_mdio.c | 4 ++++ include/linux/phy.h | 5 +++++ 3 files changed, 35 insertions(+) diff --git a/drivers/net/phy/mdio_bus.c b/drivers/net/phy/mdio_bus.c index fa7d51f..25fda2b 100644 --- a/drivers/net/phy/mdio_bus.c +++ b/drivers/net/phy/mdio_bus.c @@ -22,8 +22,11 @@ #include <linux/init.h> #include <linux/delay.h> #include <linux/device.h> +#include <linux/gpio.h> +#include <linux/gpio/consumer.h> #include <linux/of_device.h> #include <linux/of_mdio.h> +#include <linux/of_gpio.h> #include <linux/netdevice.h> #include <linux/etherdevice.h> #include <linux/skbuff.h> @@ -43,6 +46,8 @@ #include "mdio-boardinfo.h" +#define DEFAULT_GPIO_RESET_DELAY 10 /* in microseconds */ + int mdiobus_register_device(struct mdio_device *mdiodev) { if (mdiodev->bus->mdio_map[mdiodev->addr]) @@ -307,6 +312,7 @@ int __mdiobus_register(struct mii_bus *bus, struct module *owner) { struct mdio_device *mdiodev; int i, err; + struct gpio_desc *gpiod; if (NULL == bus || NULL == bus->name || NULL == bus->read || NULL == bus->write) @@ -333,6 +339,26 @@ int __mdiobus_register(struct mii_bus *bus, struct module *owner) if (bus->reset) bus->reset(bus); + /* de-assert bus level PHY GPIO resets */ + for (i = 0; i < bus->num_reset_gpios; i++) { + gpiod = devm_gpiod_get_index(&bus->dev, "reset", i, + GPIOD_OUT_LOW); + if (IS_ERR(gpiod)) { + err = PTR_ERR(gpiod); + if (err != -ENOENT) { + pr_err("mii_bus %s couldn't get reset GPIO\n", + bus->id); + return err; + } + } else { + gpiod_set_value_cansleep(gpiod, 1); + if (!bus->reset_delay_us) + bus->reset_delay_us = DEFAULT_GPIO_RESET_DELAY; + udelay(bus->reset_delay_us); + gpiod_set_value_cansleep(gpiod, 0); + } + } + for (i = 0; i < PHY_MAX_ADDR; i++) { if ((bus->phy_mask & (1 << i)) == 0) { struct phy_device *phydev; diff --git a/drivers/of/of_mdio.c b/drivers/of/of_mdio.c index 0b29798..83a62e4 100644 --- a/drivers/of/of_mdio.c +++ b/drivers/of/of_mdio.c @@ -221,6 +221,10 @@ int of_mdiobus_register(struct mii_bus *mdio, struct device_node *np) mdio->dev.of_node = np; + /* Get bus level PHY reset GPIO details */ + of_property_read_u32(np, "reset-delay-us", &mdio->reset_delay_us); + mdio->num_reset_gpios = of_gpio_named_count(np, "reset-gpios"); + /* Register the MDIO bus */ rc = mdiobus_register(mdio); if (rc) diff --git a/include/linux/phy.h b/include/linux/phy.h index 43a7748..80a6574 100644 --- a/include/linux/phy.h +++ b/include/linux/phy.h @@ -217,6 +217,11 @@ struct mii_bus { * matching its address */ int irq[PHY_MAX_ADDR]; + + /* GPIO reset pulse width in uS */ + int reset_delay_us; + /* Number of reset GPIOs */ + int num_reset_gpios; }; #define to_mii_bus(d) container_of(d, struct mii_bus, dev) -- 2.7.4
WARNING: multiple messages have this Message-ID (diff)
From: Roger Quadros <rogerq@ti.com> To: davem@davemloft.net, Andrew Lunn <andrew@lunn.ch>, Florian Fainelli <f.fainelli@gmail.com> Cc: tony@atomide.com, nsekhar@ti.com, jsarha@ti.com, netdev@vger.kernel.org, linux-omap@vger.kernel.org, linux-kernel@vger.kernel.org, rogerq@ti.com Subject: [PATCH] mdio_bus: Issue GPIO RESET to PHYs. Date: Wed, 19 Apr 2017 12:24:26 +0300 [thread overview] Message-ID: <64d6494d-41d2-0faf-a434-057f796637fe@ti.com> (raw) In-Reply-To: <1491381237-24635-1-git-send-email-rogerq@ti.com> Some boards [1] leave the PHYs at an invalid state during system power-up or reset thus causing unreliability issues with the PHY which manifests as PHY not being detected or link not functional. To fix this, these PHYs need to be RESET via a GPIO connected to the PHY's RESET pin. Some boards have a single GPIO controlling the PHY RESET pin of all PHYs on the bus whereas some others have separate GPIOs controlling individual PHY RESETs. In both cases, the RESET de-assertion cannot be done in the PHY driver as the PHY will not probe till its reset is de-asserted. So do the RESET de-assertion in the MDIO bus driver. [1] - am572x-idk, am571x-idk, a437x-idk Signed-off-by: Roger Quadros <rogerq@ti.com> --- drivers/net/phy/mdio_bus.c | 26 ++++++++++++++++++++++++++ drivers/of/of_mdio.c | 4 ++++ include/linux/phy.h | 5 +++++ 3 files changed, 35 insertions(+) diff --git a/drivers/net/phy/mdio_bus.c b/drivers/net/phy/mdio_bus.c index fa7d51f..25fda2b 100644 --- a/drivers/net/phy/mdio_bus.c +++ b/drivers/net/phy/mdio_bus.c @@ -22,8 +22,11 @@ #include <linux/init.h> #include <linux/delay.h> #include <linux/device.h> +#include <linux/gpio.h> +#include <linux/gpio/consumer.h> #include <linux/of_device.h> #include <linux/of_mdio.h> +#include <linux/of_gpio.h> #include <linux/netdevice.h> #include <linux/etherdevice.h> #include <linux/skbuff.h> @@ -43,6 +46,8 @@ #include "mdio-boardinfo.h" +#define DEFAULT_GPIO_RESET_DELAY 10 /* in microseconds */ + int mdiobus_register_device(struct mdio_device *mdiodev) { if (mdiodev->bus->mdio_map[mdiodev->addr]) @@ -307,6 +312,7 @@ int __mdiobus_register(struct mii_bus *bus, struct module *owner) { struct mdio_device *mdiodev; int i, err; + struct gpio_desc *gpiod; if (NULL == bus || NULL == bus->name || NULL == bus->read || NULL == bus->write) @@ -333,6 +339,26 @@ int __mdiobus_register(struct mii_bus *bus, struct module *owner) if (bus->reset) bus->reset(bus); + /* de-assert bus level PHY GPIO resets */ + for (i = 0; i < bus->num_reset_gpios; i++) { + gpiod = devm_gpiod_get_index(&bus->dev, "reset", i, + GPIOD_OUT_LOW); + if (IS_ERR(gpiod)) { + err = PTR_ERR(gpiod); + if (err != -ENOENT) { + pr_err("mii_bus %s couldn't get reset GPIO\n", + bus->id); + return err; + } + } else { + gpiod_set_value_cansleep(gpiod, 1); + if (!bus->reset_delay_us) + bus->reset_delay_us = DEFAULT_GPIO_RESET_DELAY; + udelay(bus->reset_delay_us); + gpiod_set_value_cansleep(gpiod, 0); + } + } + for (i = 0; i < PHY_MAX_ADDR; i++) { if ((bus->phy_mask & (1 << i)) == 0) { struct phy_device *phydev; diff --git a/drivers/of/of_mdio.c b/drivers/of/of_mdio.c index 0b29798..83a62e4 100644 --- a/drivers/of/of_mdio.c +++ b/drivers/of/of_mdio.c @@ -221,6 +221,10 @@ int of_mdiobus_register(struct mii_bus *mdio, struct device_node *np) mdio->dev.of_node = np; + /* Get bus level PHY reset GPIO details */ + of_property_read_u32(np, "reset-delay-us", &mdio->reset_delay_us); + mdio->num_reset_gpios = of_gpio_named_count(np, "reset-gpios"); + /* Register the MDIO bus */ rc = mdiobus_register(mdio); if (rc) diff --git a/include/linux/phy.h b/include/linux/phy.h index 43a7748..80a6574 100644 --- a/include/linux/phy.h +++ b/include/linux/phy.h @@ -217,6 +217,11 @@ struct mii_bus { * matching its address */ int irq[PHY_MAX_ADDR]; + + /* GPIO reset pulse width in uS */ + int reset_delay_us; + /* Number of reset GPIOs */ + int num_reset_gpios; }; #define to_mii_bus(d) container_of(d, struct mii_bus, dev) -- 2.7.4
next prev parent reply other threads:[~2017-04-19 9:24 UTC|newest] Thread overview: 48+ messages / expand[flat|nested] mbox.gz Atom feed top 2017-04-05 8:33 [PATCH] net: davinci_mdio: add GPIO reset logic Roger Quadros 2017-04-05 8:33 ` Roger Quadros 2017-04-05 15:03 ` Andrew Lunn 2017-04-06 9:15 ` Roger Quadros 2017-04-06 9:15 ` Roger Quadros 2017-04-06 12:05 ` Andrew Lunn 2017-04-06 16:48 ` Roger Quadros 2017-04-06 16:48 ` Roger Quadros 2017-04-08 13:55 ` David Miller 2017-04-08 15:10 ` Andrew Lunn 2017-04-08 15:18 ` Florian Fainelli 2017-04-10 7:52 ` Roger Quadros 2017-04-10 7:52 ` Roger Quadros 2017-04-19 9:24 ` Roger Quadros [this message] 2017-04-19 9:24 ` [PATCH] mdio_bus: Issue GPIO RESET to PHYs Roger Quadros 2017-04-19 11:39 ` Andrew Lunn 2017-04-19 11:56 ` Roger Quadros 2017-04-19 11:56 ` Roger Quadros 2017-04-19 13:38 ` Andrew Lunn 2017-04-20 7:58 ` Roger Quadros 2017-04-20 7:58 ` Roger Quadros 2017-04-20 8:39 ` [PATCH v2] " Roger Quadros 2017-04-20 8:39 ` Roger Quadros 2017-04-20 13:13 ` Andrew Lunn 2017-04-20 13:56 ` Roger Quadros 2017-04-20 13:56 ` Roger Quadros 2017-04-20 14:11 ` [PATCH v3 net-next] " Roger Quadros 2017-04-20 14:11 ` Roger Quadros 2017-04-21 1:12 ` Andrew Lunn 2017-04-21 1:23 ` Florian Fainelli 2017-04-21 1:38 ` Andrew Lunn 2017-04-21 8:04 ` Roger Quadros 2017-04-21 8:04 ` Roger Quadros 2017-04-21 13:15 ` [PATCH v4 " Roger Quadros 2017-04-21 13:15 ` Roger Quadros 2017-04-21 13:31 ` Lars-Peter Clausen 2017-04-23 23:35 ` Andrew Lunn 2017-04-24 9:04 ` Roger Quadros 2017-04-24 9:04 ` Roger Quadros 2017-04-24 16:32 ` Florian Fainelli 2017-04-25 16:22 ` Lars-Peter Clausen 2017-04-25 16:31 ` Florian Fainelli 2017-04-26 10:46 ` Roger Quadros 2017-04-26 10:46 ` Roger Quadros 2017-04-26 12:27 ` Andrew Lunn 2017-04-26 10:43 ` Roger Quadros 2017-04-26 10:43 ` Roger Quadros 2017-04-24 16:40 ` David Miller
Reply instructions: You may reply publicly to this message via plain-text email using any one of the following methods: * Save the following mbox file, import it into your mail client, and reply-to-all from there: mbox Avoid top-posting and favor interleaved quoting: https://en.wikipedia.org/wiki/Posting_style#Interleaved_style * Reply using the --to, --cc, and --in-reply-to switches of git-send-email(1): git send-email \ --in-reply-to=64d6494d-41d2-0faf-a434-057f796637fe@ti.com \ --to=rogerq@ti.com \ --cc=andrew@lunn.ch \ --cc=davem@davemloft.net \ --cc=f.fainelli@gmail.com \ --cc=jsarha@ti.com \ --cc=linux-kernel@vger.kernel.org \ --cc=linux-omap@vger.kernel.org \ --cc=netdev@vger.kernel.org \ --cc=nsekhar@ti.com \ --cc=tony@atomide.com \ /path/to/YOUR_REPLY https://kernel.org/pub/software/scm/git/docs/git-send-email.html * If your mail client supports setting the In-Reply-To header via mailto: links, try the mailto: linkBe sure your reply has a Subject: header at the top and a blank line before the message body.
This is an external index of several public inboxes, see mirroring instructions on how to clone and mirror all data and code used by this external index.