[source] kernel: backport some upstream at803x fixes

LEDE Commits lede-commits at lists.infradead.org
Sun Dec 4 02:42:03 PST 2016


nbd pushed a commit to source.git, branch master:
https://git.lede-project.org/06a21e12ee94f43eebaabad5bad60c1120d723f9

commit 06a21e12ee94f43eebaabad5bad60c1120d723f9
Author: Felix Fietkau <nbd at nbd.name>
AuthorDate: Tue Nov 29 17:55:41 2016 +0100

    kernel: backport some upstream at803x fixes
    
    Signed-off-by: Felix Fietkau <nbd at nbd.name>
---
 .../736-at803x-fix-reset-handling.patch            | 43 ++++++++++++
 ...03x-Request-reset-GPIO-only-for-AT8030-PH.patch | 42 ++++++++++++
 ...03x-only-the-AT8030-needs-a-hardware-rese.patch | 77 ++++++++++++++++++++++
 3 files changed, 162 insertions(+)

diff --git a/target/linux/generic/patches-4.4/736-at803x-fix-reset-handling.patch b/target/linux/generic/patches-4.4/736-at803x-fix-reset-handling.patch
new file mode 100644
index 0000000..91c2334
--- /dev/null
+++ b/target/linux/generic/patches-4.4/736-at803x-fix-reset-handling.patch
@@ -0,0 +1,43 @@
+From: Sergei Shtylyov <sergei.shtylyov at cogentembedded.com>
+Date: Wed, 23 Mar 2016 00:44:40 +0300
+Subject: [PATCH] at803x: fix reset handling
+MIME-Version: 1.0
+Content-Type: text/plain; charset=UTF-8
+Content-Transfer-Encoding: 8bit
+
+The driver of course "knows" that the chip's reset signal is active low,
+so  it drives the GPIO to 0  to reset the PHY and to 1 otherwise; however
+all this will only work iff the GPIO  is  specified as active-high in the
+device tree!  I think both the driver and the device trees (if there are
+any -- I was unable to find them) need to be fixed in this case...
+
+Fixes: 13a56b449325 ("net: phy: at803x: Add support for hardware reset")
+Signed-off-by: Sergei Shtylyov <sergei.shtylyov at cogentembedded.com>
+Acked-by: Uwe Kleine-König <u.kleine-koenig at pengutronix.de>
+Signed-off-by: David S. Miller <davem at davemloft.net>
+---
+
+--- a/drivers/net/phy/at803x.c
++++ b/drivers/net/phy/at803x.c
+@@ -250,7 +250,7 @@ static int at803x_probe(struct phy_devic
+ 	if (!priv)
+ 		return -ENOMEM;
+ 
+-	gpiod_reset = devm_gpiod_get_optional(dev, "reset", GPIOD_OUT_HIGH);
++	gpiod_reset = devm_gpiod_get_optional(dev, "reset", GPIOD_OUT_LOW);
+ 	if (IS_ERR(gpiod_reset))
+ 		return PTR_ERR(gpiod_reset);
+ 
+@@ -377,10 +377,10 @@ static void at803x_link_change_notify(st
+ 
+ 				at803x_context_save(phydev, &context);
+ 
+-				gpiod_set_value(priv->gpiod_reset, 0);
+-				msleep(1);
+ 				gpiod_set_value(priv->gpiod_reset, 1);
+ 				msleep(1);
++				gpiod_set_value(priv->gpiod_reset, 0);
++				msleep(1);
+ 
+ 				at803x_context_restore(phydev, &context);
+ 
diff --git a/target/linux/generic/patches-4.4/737-net-phy-at803x-Request-reset-GPIO-only-for-AT8030-PH.patch b/target/linux/generic/patches-4.4/737-net-phy-at803x-Request-reset-GPIO-only-for-AT8030-PH.patch
new file mode 100644
index 0000000..b30ba7a
--- /dev/null
+++ b/target/linux/generic/patches-4.4/737-net-phy-at803x-Request-reset-GPIO-only-for-AT8030-PH.patch
@@ -0,0 +1,42 @@
+From: Sebastian Frias <sf84 at laposte.net>
+Date: Wed, 23 Mar 2016 11:49:09 +0100
+Subject: [PATCH] net: phy: at803x: Request 'reset' GPIO only for AT8030 PHY
+
+This removes the dependency on GPIOLIB for non faulty PHYs.
+
+Indeed, without this patch, if GPIOLIB is not selected
+devm_gpiod_get_optional() will return -ENOSYS and the driver probe
+call will fail, regardless of the actual PHY hardware.
+
+Out of the 3 PHYs supported by this driver (AT8030, AT8031, AT8035),
+only AT8030 presents the issues that commit 13a56b449325 ("net: phy:
+at803x: Add support for hardware reset") attempts to work-around by
+using a 'reset' GPIO line.
+
+Hence, only AT8030 should depend on GPIOLIB operating properly.
+
+Fixes: 13a56b449325 ("net: phy: at803x: Add support for hardware reset")
+
+Signed-off-by: Sebastian Frias <sf84 at laposte.net>
+Signed-off-by: David S. Miller <davem at davemloft.net>
+---
+
+--- a/drivers/net/phy/at803x.c
++++ b/drivers/net/phy/at803x.c
+@@ -250,12 +250,16 @@ static int at803x_probe(struct phy_devic
+ 	if (!priv)
+ 		return -ENOMEM;
+ 
++	if (phydev->drv->phy_id != ATH8030_PHY_ID)
++		goto does_not_require_reset_workaround;
++
+ 	gpiod_reset = devm_gpiod_get_optional(dev, "reset", GPIOD_OUT_LOW);
+ 	if (IS_ERR(gpiod_reset))
+ 		return PTR_ERR(gpiod_reset);
+ 
+ 	priv->gpiod_reset = gpiod_reset;
+ 
++does_not_require_reset_workaround:
+ 	phydev->priv = priv;
+ 
+ 	return 0;
diff --git a/target/linux/generic/patches-4.4/738-net-phy-at803x-only-the-AT8030-needs-a-hardware-rese.patch b/target/linux/generic/patches-4.4/738-net-phy-at803x-only-the-AT8030-needs-a-hardware-rese.patch
new file mode 100644
index 0000000..c49d53e
--- /dev/null
+++ b/target/linux/generic/patches-4.4/738-net-phy-at803x-only-the-AT8030-needs-a-hardware-rese.patch
@@ -0,0 +1,77 @@
+From: Timur Tabi <timur at codeaurora.org>
+Date: Tue, 26 Apr 2016 12:44:18 -0500
+Subject: [PATCH] net: phy: at803x: only the AT8030 needs a hardware reset on
+ link change
+
+Commit 13a56b44 ("at803x: Add support for hardware reset") added a
+work-around for a hardware bug on the AT8030.  However, the work-around
+was being called for all 803x PHYs, even those that don't need it.
+Function at803x_link_change_notify() checks to make sure that it only
+resets the PHY on the 8030, but it makes more sense to not call that
+function at all if it isn't needed.
+
+Signed-off-by: Timur Tabi <timur at codeaurora.org>
+Reviewed-by: Florian Fainelli <f.fainelli at gmail.com>
+Signed-off-by: David S. Miller <davem at davemloft.net>
+---
+
+--- a/drivers/net/phy/at803x.c
++++ b/drivers/net/phy/at803x.c
+@@ -374,27 +374,25 @@ static void at803x_link_change_notify(st
+ 	 * in the FIFO. In such cases, the FIFO enters an error mode it
+ 	 * cannot recover from by software.
+ 	 */
+-	if (phydev->drv->phy_id == ATH8030_PHY_ID) {
+-		if (phydev->state == PHY_NOLINK) {
+-			if (priv->gpiod_reset && !priv->phy_reset) {
+-				struct at803x_context context;
++	if (phydev->state == PHY_NOLINK) {
++		if (priv->gpiod_reset && !priv->phy_reset) {
++			struct at803x_context context;
+ 
+-				at803x_context_save(phydev, &context);
++			at803x_context_save(phydev, &context);
+ 
+-				gpiod_set_value(priv->gpiod_reset, 1);
+-				msleep(1);
+-				gpiod_set_value(priv->gpiod_reset, 0);
+-				msleep(1);
++			gpiod_set_value(priv->gpiod_reset, 1);
++			msleep(1);
++			gpiod_set_value(priv->gpiod_reset, 0);
++			msleep(1);
+ 
+-				at803x_context_restore(phydev, &context);
++			at803x_context_restore(phydev, &context);
+ 
+-				dev_dbg(&phydev->dev, "%s(): phy was reset\n",
+-					__func__);
+-				priv->phy_reset = true;
+-			}
+-		} else {
+-			priv->phy_reset = false;
++			dev_dbg(&phydev->dev, "%s(): phy was reset\n",
++				__func__);
++			priv->phy_reset = true;
+ 		}
++	} else {
++		priv->phy_reset = false;
+ 	}
+ 	if (pdata && pdata->fixup_rgmii_tx_delay &&
+ 	    phydev->speed != priv->prev_speed) {
+@@ -426,7 +424,6 @@ static struct phy_driver at803x_driver[]
+ 	.phy_id_mask		= AT803X_PHY_ID_MASK,
+ 	.probe			= at803x_probe,
+ 	.config_init		= at803x_config_init,
+-	.link_change_notify	= at803x_link_change_notify,
+ 	.set_wol		= at803x_set_wol,
+ 	.get_wol		= at803x_get_wol,
+ 	.suspend		= at803x_suspend,
+@@ -468,7 +465,6 @@ static struct phy_driver at803x_driver[]
+ 	.phy_id_mask		= AT803X_PHY_ID_MASK,
+ 	.probe			= at803x_probe,
+ 	.config_init		= at803x_config_init,
+-	.link_change_notify	= at803x_link_change_notify,
+ 	.set_wol		= at803x_set_wol,
+ 	.get_wol		= at803x_get_wol,
+ 	.suspend		= at803x_suspend,



More information about the lede-commits mailing list