diff options
author | David Bauer <mail@david-bauer.net> | 2020-03-13 01:07:39 +0100 |
---|---|---|
committer | David Bauer <mail@david-bauer.net> | 2020-03-13 20:43:57 +0100 |
commit | 32726846c85985fbc320d123a7b26b32124cd47a (patch) | |
tree | 6c374c2f4825162ca58c65b2b1beba013ab2412b /target/linux/ath79/files/drivers/net/ethernet/atheros/ag71xx/ag71xx_phy.c | |
parent | 0933d1363b262017a815a538a0017f301f34883b (diff) | |
download | upstream-32726846c85985fbc320d123a7b26b32124cd47a.tar.gz upstream-32726846c85985fbc320d123a7b26b32124cd47a.tar.bz2 upstream-32726846c85985fbc320d123a7b26b32124cd47a.zip |
ath79: use downstream ag71xx for Kernel 5.4
The ag71xx driver from Linux 5.4 currently has various shortcomings
when used with OpenWrt compared to our downstream version.
For example, the upstream driver does not support modifying the ethernet
clock and configuring RGMII delays on the MAC side.
While we should certainly switch to the upstream driver, the amount of
necessary patches would make it cumbersome to work with. It's also
highly likely we won't be able to finish patching the upstream driver in
time for a Linux 5.4 release.
Tested on Siemens WS-AP3610.
CC: Hauke Mehrtens <hauke@hauke-m.de>
Signed-off-by: David Bauer <mail@david-bauer.net>
Acked-by: Hauke Mehrtens <hauke@hauke-m.de>
Diffstat (limited to 'target/linux/ath79/files/drivers/net/ethernet/atheros/ag71xx/ag71xx_phy.c')
-rw-r--r-- | target/linux/ath79/files/drivers/net/ethernet/atheros/ag71xx/ag71xx_phy.c | 92 |
1 files changed, 92 insertions, 0 deletions
diff --git a/target/linux/ath79/files/drivers/net/ethernet/atheros/ag71xx/ag71xx_phy.c b/target/linux/ath79/files/drivers/net/ethernet/atheros/ag71xx/ag71xx_phy.c new file mode 100644 index 0000000000..ac1af26860 --- /dev/null +++ b/target/linux/ath79/files/drivers/net/ethernet/atheros/ag71xx/ag71xx_phy.c @@ -0,0 +1,92 @@ +/* + * Atheros AR71xx built-in ethernet mac driver + * + * Copyright (C) 2008-2010 Gabor Juhos <juhosg@openwrt.org> + * Copyright (C) 2008 Imre Kaloz <kaloz@openwrt.org> + * + * Based on Atheros' AG7100 driver + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 as published + * by the Free Software Foundation. + */ + +#include <linux/of_mdio.h> +#include "ag71xx.h" + +static void ag71xx_phy_link_adjust(struct net_device *dev) +{ + struct ag71xx *ag = netdev_priv(dev); + struct phy_device *phydev = ag->phy_dev; + unsigned long flags; + int status_change = 0; + + spin_lock_irqsave(&ag->lock, flags); + + if (phydev->link) { + if (ag->duplex != phydev->duplex + || ag->speed != phydev->speed) { + status_change = 1; + } + } + + if (phydev->link != ag->link) + status_change = 1; + + ag->link = phydev->link; + ag->duplex = phydev->duplex; + ag->speed = phydev->speed; + + if (status_change) + ag71xx_link_adjust(ag); + + spin_unlock_irqrestore(&ag->lock, flags); +} + +int ag71xx_phy_connect(struct ag71xx *ag) +{ + struct device_node *np = ag->pdev->dev.of_node; + struct device_node *phy_node; + int ret; + + if (of_phy_is_fixed_link(np)) { + ret = of_phy_register_fixed_link(np); + if (ret < 0) { + dev_err(&ag->pdev->dev, + "Failed to register fixed PHY link: %d\n", ret); + return ret; + } + + phy_node = of_node_get(np); + } else { + phy_node = of_parse_phandle(np, "phy-handle", 0); + } + + if (!phy_node) { + dev_err(&ag->pdev->dev, + "Could not find valid phy node\n"); + return -ENODEV; + } + + ag->phy_dev = of_phy_connect(ag->dev, phy_node, ag71xx_phy_link_adjust, + 0, ag->phy_if_mode); + + of_node_put(phy_node); + + if (!ag->phy_dev) { + dev_err(&ag->pdev->dev, + "Could not connect to PHY device. Deferring probe.\n"); + return -EPROBE_DEFER; + } + + dev_info(&ag->pdev->dev, "connected to PHY at %s [uid=%08x, driver=%s]\n", + phydev_name(ag->phy_dev), + ag->phy_dev->phy_id, ag->phy_dev->drv->name); + + return 0; +} + +void ag71xx_phy_disconnect(struct ag71xx *ag) +{ + phy_disconnect(ag->phy_dev); +} |