From a420b757acc46d02bdaf4e0bcbeb0660c9df9209 Mon Sep 17 00:00:00 2001 From: "Russell King (Oracle)" Date: Fri, 25 Feb 2022 11:56:02 +0000 Subject: [PATCH 1/6] net: dsa: sja1105: populate supported_interfaces MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Populate the supported interfaces bitmap for the SJA1105 DSA switch. This switch only supports a static model of configuration, so we restrict the interface modes to the configured setting. Reviewed-by: Vladimir Oltean Signed-off-by: Russell King (Oracle) Signed-off-by: Vladimir Oltean Signed-off-by: Vladimir Oltean --- drivers/net/dsa/sja1105/sja1105_main.c | 13 +++++++++++++ 1 file changed, 13 insertions(+) diff --git a/drivers/net/dsa/sja1105/sja1105_main.c b/drivers/net/dsa/sja1105/sja1105_main.c index b513713be610..90e73a982faf 100644 --- a/drivers/net/dsa/sja1105/sja1105_main.c +++ b/drivers/net/dsa/sja1105/sja1105_main.c @@ -1412,6 +1412,18 @@ static void sja1105_mac_link_up(struct dsa_switch *ds, int port, sja1105_inhibit_tx(priv, BIT(port), false); } +static void sja1105_phylink_get_caps(struct dsa_switch *ds, int port, + struct phylink_config *config) +{ + struct sja1105_private *priv = ds->priv; + + /* The SJA1105 MAC programming model is through the static config + * (the xMII Mode table cannot be dynamically reconfigured), and + * we have to program that early. + */ + __set_bit(priv->phy_mode[port], config->supported_interfaces); +} + static void sja1105_phylink_validate(struct dsa_switch *ds, int port, unsigned long *supported, struct phylink_link_state *state) @@ -3152,6 +3164,7 @@ static const struct dsa_switch_ops sja1105_switch_ops = { .set_ageing_time = sja1105_set_ageing_time, .port_change_mtu = sja1105_change_mtu, .port_max_mtu = sja1105_get_max_mtu, + .phylink_get_caps = sja1105_phylink_get_caps, .phylink_validate = sja1105_phylink_validate, .phylink_mac_config = sja1105_mac_config, .phylink_mac_link_up = sja1105_mac_link_up, From c2b8e1e3d81e701af2aa88e7fda7b730ed001db3 Mon Sep 17 00:00:00 2001 From: "Russell King (Oracle)" Date: Fri, 25 Feb 2022 11:56:07 +0000 Subject: [PATCH 2/6] net: dsa: sja1105: remove interface checks When the supported interfaces bitmap is populated, phylink will itself check that the interface mode is present in this bitmap. Drivers no longer need to perform this check themselves. Remove these checks. Reviewed-by: Vladimir Oltean Signed-off-by: Russell King (Oracle) Signed-off-by: David S. Miller --- drivers/net/dsa/sja1105/sja1105_main.c | 29 -------------------------- 1 file changed, 29 deletions(-) diff --git a/drivers/net/dsa/sja1105/sja1105_main.c b/drivers/net/dsa/sja1105/sja1105_main.c index 90e73a982faf..e278bd86e3c6 100644 --- a/drivers/net/dsa/sja1105/sja1105_main.c +++ b/drivers/net/dsa/sja1105/sja1105_main.c @@ -1358,19 +1358,6 @@ static int sja1105_adjust_port_config(struct sja1105_private *priv, int port, return sja1105_clocking_setup_port(priv, port); } -/* The SJA1105 MAC programming model is through the static config (the xMII - * Mode table cannot be dynamically reconfigured), and we have to program - * that early (earlier than PHYLINK calls us, anyway). - * So just error out in case the connected PHY attempts to change the initial - * system interface MII protocol from what is defined in the DT, at least for - * now. - */ -static bool sja1105_phy_mode_mismatch(struct sja1105_private *priv, int port, - phy_interface_t interface) -{ - return priv->phy_mode[port] != interface; -} - static void sja1105_mac_config(struct dsa_switch *ds, int port, unsigned int mode, const struct phylink_link_state *state) @@ -1379,12 +1366,6 @@ static void sja1105_mac_config(struct dsa_switch *ds, int port, struct sja1105_private *priv = ds->priv; struct dw_xpcs *xpcs; - if (sja1105_phy_mode_mismatch(priv, port, state->interface)) { - dev_err(ds->dev, "Changing PHY mode to %s not supported!\n", - phy_modes(state->interface)); - return; - } - xpcs = priv->xpcs[port]; if (xpcs) @@ -1438,16 +1419,6 @@ static void sja1105_phylink_validate(struct dsa_switch *ds, int port, mii = priv->static_config.tables[BLK_IDX_XMII_PARAMS].entries; - /* include/linux/phylink.h says: - * When @state->interface is %PHY_INTERFACE_MODE_NA, phylink - * expects the MAC driver to return all supported link modes. - */ - if (state->interface != PHY_INTERFACE_MODE_NA && - sja1105_phy_mode_mismatch(priv, port, state->interface)) { - linkmode_zero(supported); - return; - } - /* The MAC does not support pause frames, and also doesn't * support half-duplex traffic modes. */ From 827b4ef2772f819747d1dd7b5ec088e3892156a3 Mon Sep 17 00:00:00 2001 From: "Russell King (Oracle)" Date: Fri, 25 Feb 2022 11:56:12 +0000 Subject: [PATCH 3/6] net: dsa: sja1105: use .mac_select_pcs() interface Convert the PCS selection to use mac_select_pcs, which allows the PCS to perform any validation it needs, and removes the need to set the PCS in the mac_config() callback, delving into the higher DSA levels to do so. Reviewed-by: Vladimir Oltean Signed-off-by: Russell King (Oracle) Signed-off-by: David S. Miller --- drivers/net/dsa/sja1105/sja1105_main.c | 16 +++++++--------- 1 file changed, 7 insertions(+), 9 deletions(-) diff --git a/drivers/net/dsa/sja1105/sja1105_main.c b/drivers/net/dsa/sja1105/sja1105_main.c index e278bd86e3c6..b5c36f808df1 100644 --- a/drivers/net/dsa/sja1105/sja1105_main.c +++ b/drivers/net/dsa/sja1105/sja1105_main.c @@ -1358,18 +1358,16 @@ static int sja1105_adjust_port_config(struct sja1105_private *priv, int port, return sja1105_clocking_setup_port(priv, port); } -static void sja1105_mac_config(struct dsa_switch *ds, int port, - unsigned int mode, - const struct phylink_link_state *state) +static struct phylink_pcs * +sja1105_mac_select_pcs(struct dsa_switch *ds, int port, phy_interface_t iface) { - struct dsa_port *dp = dsa_to_port(ds, port); struct sja1105_private *priv = ds->priv; - struct dw_xpcs *xpcs; - - xpcs = priv->xpcs[port]; + struct dw_xpcs *xpcs = priv->xpcs[port]; if (xpcs) - phylink_set_pcs(dp->pl, &xpcs->pcs); + return &xpcs->pcs; + + return NULL; } static void sja1105_mac_link_down(struct dsa_switch *ds, int port, @@ -3137,7 +3135,7 @@ static const struct dsa_switch_ops sja1105_switch_ops = { .port_max_mtu = sja1105_get_max_mtu, .phylink_get_caps = sja1105_phylink_get_caps, .phylink_validate = sja1105_phylink_validate, - .phylink_mac_config = sja1105_mac_config, + .phylink_mac_select_pcs = sja1105_mac_select_pcs, .phylink_mac_link_up = sja1105_mac_link_up, .phylink_mac_link_down = sja1105_mac_link_down, .get_strings = sja1105_get_strings, From 2d1d548ec14478fc9705d8e1e5a8fe35933e54f0 Mon Sep 17 00:00:00 2001 From: "Russell King (Oracle)" Date: Fri, 25 Feb 2022 11:56:17 +0000 Subject: [PATCH 4/6] net: dsa: sja1105: mark as non-legacy The sja1105 DSA driver does not have a phylink_mac_config() method implementation, it is safe to mark this as a non-legacy driver. Reviewed-by: Vladimir Oltean Signed-off-by: Russell King (Oracle) Signed-off-by: David S. Miller --- drivers/net/dsa/sja1105/sja1105_main.c | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/drivers/net/dsa/sja1105/sja1105_main.c b/drivers/net/dsa/sja1105/sja1105_main.c index b5c36f808df1..8f061cce77f0 100644 --- a/drivers/net/dsa/sja1105/sja1105_main.c +++ b/drivers/net/dsa/sja1105/sja1105_main.c @@ -1396,6 +1396,12 @@ static void sja1105_phylink_get_caps(struct dsa_switch *ds, int port, { struct sja1105_private *priv = ds->priv; + /* This driver does not make use of the speed, duplex, pause or the + * advertisement in its mac_config, so it is safe to mark this driver + * as non-legacy. + */ + config->legacy_pre_march2020 = false; + /* The SJA1105 MAC programming model is through the static config * (the xMII Mode table cannot be dynamically reconfigured), and * we have to program that early. From 9c318be13ca051ca7fa567765a0f92b00dcdd75c Mon Sep 17 00:00:00 2001 From: "Russell King (Oracle)" Date: Fri, 25 Feb 2022 11:56:23 +0000 Subject: [PATCH 5/6] net: dsa: sja1105: convert to phylink_generic_validate() Populate the MAC capabilities for the SJA1105 DSA switch using the same decision making which sja1105_phylink_validate() uses. Remove the now obsolete sja1105_phylink_validate() implementation to allow DSA to use phylink_generic_validate() for this switch driver. As noted by Vladimir, this fixes an inconsequential bug which allowed gigabit and lower interface modes to be indicated when operating in 2500base-X mode. Reviewed-by: Vladimir Oltean Signed-off-by: Russell King (Oracle) Signed-off-by: David S. Miller --- drivers/net/dsa/sja1105/sja1105_main.c | 35 ++++++-------------------- 1 file changed, 7 insertions(+), 28 deletions(-) diff --git a/drivers/net/dsa/sja1105/sja1105_main.c b/drivers/net/dsa/sja1105/sja1105_main.c index 8f061cce77f0..5beef06d8ff7 100644 --- a/drivers/net/dsa/sja1105/sja1105_main.c +++ b/drivers/net/dsa/sja1105/sja1105_main.c @@ -1395,6 +1395,7 @@ static void sja1105_phylink_get_caps(struct dsa_switch *ds, int port, struct phylink_config *config) { struct sja1105_private *priv = ds->priv; + struct sja1105_xmii_params_entry *mii; /* This driver does not make use of the speed, duplex, pause or the * advertisement in its mac_config, so it is safe to mark this driver @@ -1407,40 +1408,19 @@ static void sja1105_phylink_get_caps(struct dsa_switch *ds, int port, * we have to program that early. */ __set_bit(priv->phy_mode[port], config->supported_interfaces); -} - -static void sja1105_phylink_validate(struct dsa_switch *ds, int port, - unsigned long *supported, - struct phylink_link_state *state) -{ - /* Construct a new mask which exhaustively contains all link features - * supported by the MAC, and then apply that (logical AND) to what will - * be sent to the PHY for "marketing". - */ - __ETHTOOL_DECLARE_LINK_MODE_MASK(mask) = { 0, }; - struct sja1105_private *priv = ds->priv; - struct sja1105_xmii_params_entry *mii; - - mii = priv->static_config.tables[BLK_IDX_XMII_PARAMS].entries; /* The MAC does not support pause frames, and also doesn't * support half-duplex traffic modes. */ - phylink_set(mask, Autoneg); - phylink_set(mask, MII); - phylink_set(mask, 10baseT_Full); - phylink_set(mask, 100baseT_Full); - phylink_set(mask, 100baseT1_Full); + config->mac_capabilities = MAC_10FD | MAC_100FD; + + mii = priv->static_config.tables[BLK_IDX_XMII_PARAMS].entries; if (mii->xmii_mode[port] == XMII_MODE_RGMII || mii->xmii_mode[port] == XMII_MODE_SGMII) - phylink_set(mask, 1000baseT_Full); - if (priv->info->supports_2500basex[port]) { - phylink_set(mask, 2500baseT_Full); - phylink_set(mask, 2500baseX_Full); - } + config->mac_capabilities |= MAC_1000FD; - linkmode_and(supported, supported, mask); - linkmode_and(state->advertising, state->advertising, mask); + if (priv->info->supports_2500basex[port]) + config->mac_capabilities |= MAC_2500FD; } static int @@ -3140,7 +3120,6 @@ static const struct dsa_switch_ops sja1105_switch_ops = { .port_change_mtu = sja1105_change_mtu, .port_max_mtu = sja1105_get_max_mtu, .phylink_get_caps = sja1105_phylink_get_caps, - .phylink_validate = sja1105_phylink_validate, .phylink_mac_select_pcs = sja1105_mac_select_pcs, .phylink_mac_link_up = sja1105_mac_link_up, .phylink_mac_link_down = sja1105_mac_link_down, From 83dc4c2af682f3d9dd7ff95c3b24484738311805 Mon Sep 17 00:00:00 2001 From: "Russell King (Oracle)" Date: Fri, 25 Feb 2022 11:56:28 +0000 Subject: [PATCH 6/6] net: dsa: sja1105: support switching between SGMII and 2500BASE-X Vladimir Oltean suggests that sja1105 can support switching between SGMII and 2500BASE-X modes. Augment sja1105_phylink_get_caps() to fill in both interface modes if they can be supported. Signed-off-by: Russell King (Oracle) Signed-off-by: David S. Miller --- drivers/net/dsa/sja1105/sja1105_main.c | 27 +++++++++++++++++++++----- 1 file changed, 22 insertions(+), 5 deletions(-) diff --git a/drivers/net/dsa/sja1105/sja1105_main.c b/drivers/net/dsa/sja1105/sja1105_main.c index 5beef06d8ff7..8fc309446e1e 100644 --- a/drivers/net/dsa/sja1105/sja1105_main.c +++ b/drivers/net/dsa/sja1105/sja1105_main.c @@ -1396,6 +1396,7 @@ static void sja1105_phylink_get_caps(struct dsa_switch *ds, int port, { struct sja1105_private *priv = ds->priv; struct sja1105_xmii_params_entry *mii; + phy_interface_t phy_mode; /* This driver does not make use of the speed, duplex, pause or the * advertisement in its mac_config, so it is safe to mark this driver @@ -1403,11 +1404,27 @@ static void sja1105_phylink_get_caps(struct dsa_switch *ds, int port, */ config->legacy_pre_march2020 = false; - /* The SJA1105 MAC programming model is through the static config - * (the xMII Mode table cannot be dynamically reconfigured), and - * we have to program that early. - */ - __set_bit(priv->phy_mode[port], config->supported_interfaces); + phy_mode = priv->phy_mode[port]; + if (phy_mode == PHY_INTERFACE_MODE_SGMII || + phy_mode == PHY_INTERFACE_MODE_2500BASEX) { + /* Changing the PHY mode on SERDES ports is possible and makes + * sense, because that is done through the XPCS. We allow + * changes between SGMII and 2500base-X. + */ + if (priv->info->supports_sgmii[port]) + __set_bit(PHY_INTERFACE_MODE_SGMII, + config->supported_interfaces); + + if (priv->info->supports_2500basex[port]) + __set_bit(PHY_INTERFACE_MODE_2500BASEX, + config->supported_interfaces); + } else { + /* The SJA1105 MAC programming model is through the static + * config (the xMII Mode table cannot be dynamically + * reconfigured), and we have to program that early. + */ + __set_bit(phy_mode, config->supported_interfaces); + } /* The MAC does not support pause frames, and also doesn't * support half-duplex traffic modes.