[OpenWrt-Devel,2/5] ar8216: add link change detection for switch ports
diff mbox

Message ID 54C170C3.8040109@gmail.com
State Accepted
Headers show

Commit Message

Heiner Kallweit Jan. 22, 2015, 9:50 p.m. UTC
Check for switch port link changes and
- flush ATU in case of a change
- report link change via syslog

Signed-off-by: Heiner Kallweit <hkallweit1@gmail.com>
---
 .../linux/generic/files/drivers/net/phy/ar8216.c   | 35 ++++++++++++++++++++++
 .../linux/generic/files/drivers/net/phy/ar8216.h   |  1 +
 2 files changed, 36 insertions(+)

Patch
diff mbox

diff --git a/target/linux/generic/files/drivers/net/phy/ar8216.c b/target/linux/generic/files/drivers/net/phy/ar8216.c
index 370f1ac..130ebf7 100644
--- a/target/linux/generic/files/drivers/net/phy/ar8216.c
+++ b/target/linux/generic/files/drivers/net/phy/ar8216.c
@@ -1707,12 +1707,47 @@  ar8xxx_phy_config_init(struct phy_device *phydev)
 	return 0;
 }
 
+static bool
+ar8xxx_check_link_states(struct ar8xxx_priv *priv)
+{
+	bool link_new, changed = false;
+	u32 status;
+	int i;
+
+	mutex_lock(&priv->reg_mutex);
+
+	for (i = 0; i < priv->dev.ports; i++) {
+		status = priv->chip->read_port_status(priv, i);
+		link_new = !!(status & AR8216_PORT_STATUS_LINK_UP);
+		if (link_new == priv->link_up[i])
+			continue;
+
+		priv->link_up[i] = link_new;
+		changed = true;
+		dev_info(&priv->phy->dev, "Port %d is %s\n",
+			 i, link_new ? "up" : "down");
+	}
+
+	if (changed)
+		priv->chip->atu_flush(priv);
+
+	mutex_unlock(&priv->reg_mutex);
+
+	return changed;
+}
+
 static int
 ar8xxx_phy_read_status(struct phy_device *phydev)
 {
 	struct ar8xxx_priv *priv = phydev->priv;
 	struct switch_port_link link;
 
+	/* check for link changes and flush ATU
+	 * if a change was detected
+	 */
+	if (phydev->state == PHY_CHANGELINK)
+		ar8xxx_check_link_states(priv);
+
 	if (phydev->addr != 0)
 		return genphy_read_status(phydev);
 
diff --git a/target/linux/generic/files/drivers/net/phy/ar8216.h b/target/linux/generic/files/drivers/net/phy/ar8216.h
index 8487c3e..2d025ae 100644
--- a/target/linux/generic/files/drivers/net/phy/ar8216.h
+++ b/target/linux/generic/files/drivers/net/phy/ar8216.h
@@ -396,6 +396,7 @@  struct ar8xxx_priv {
 	bool initialized;
 	bool port4_phy;
 	char buf[2048];
+	bool link_up[AR8X16_MAX_PORTS];
 
 	bool init;