diff options
Diffstat (limited to 'target/linux/generic/backport-5.10/747-v5.16-06-net-dsa-qca8k-rework-rgmii-delay-logic-and-scan-for-.patch')
-rw-r--r-- | target/linux/generic/backport-5.10/747-v5.16-06-net-dsa-qca8k-rework-rgmii-delay-logic-and-scan-for-.patch | 295 |
1 files changed, 0 insertions, 295 deletions
diff --git a/target/linux/generic/backport-5.10/747-v5.16-06-net-dsa-qca8k-rework-rgmii-delay-logic-and-scan-for-.patch b/target/linux/generic/backport-5.10/747-v5.16-06-net-dsa-qca8k-rework-rgmii-delay-logic-and-scan-for-.patch deleted file mode 100644 index de201764f9..0000000000 --- a/target/linux/generic/backport-5.10/747-v5.16-06-net-dsa-qca8k-rework-rgmii-delay-logic-and-scan-for-.patch +++ /dev/null @@ -1,295 +0,0 @@ -From 5654ec78dd7e64b1e04777b24007344329e6a63b Mon Sep 17 00:00:00 2001 -From: Ansuel Smith <ansuelsmth@gmail.com> -Date: Thu, 14 Oct 2021 00:39:11 +0200 -Subject: net: dsa: qca8k: rework rgmii delay logic and scan for cpu port 6 - -Future proof commit. This switch have 2 CPU ports and one valid -configuration is first CPU port set to sgmii and second CPU port set to -rgmii-id. The current implementation detects delay only for CPU port -zero set to rgmii and doesn't count any delay set in a secondary CPU -port. Drop the current delay scan function and move it to the sgmii -parser function to generalize and implicitly add support for secondary -CPU port set to rgmii-id. Introduce new logic where delay is enabled -also with internal delay binding declared and rgmii set as PHY mode. - -Signed-off-by: Ansuel Smith <ansuelsmth@gmail.com> -Signed-off-by: David S. Miller <davem@davemloft.net> ---- - drivers/net/dsa/qca8k.c | 165 ++++++++++++++++++++++++------------------------ - drivers/net/dsa/qca8k.h | 10 ++- - 2 files changed, 89 insertions(+), 86 deletions(-) - ---- a/drivers/net/dsa/qca8k.c -+++ b/drivers/net/dsa/qca8k.c -@@ -889,68 +889,6 @@ qca8k_setup_mdio_bus(struct qca8k_priv * - } - - static int --qca8k_setup_of_rgmii_delay(struct qca8k_priv *priv) --{ -- struct device_node *port_dn; -- phy_interface_t mode; -- struct dsa_port *dp; -- u32 val; -- -- /* CPU port is already checked */ -- dp = dsa_to_port(priv->ds, 0); -- -- port_dn = dp->dn; -- -- /* Check if port 0 is set to the correct type */ -- of_get_phy_mode(port_dn, &mode); -- if (mode != PHY_INTERFACE_MODE_RGMII_ID && -- mode != PHY_INTERFACE_MODE_RGMII_RXID && -- mode != PHY_INTERFACE_MODE_RGMII_TXID) { -- return 0; -- } -- -- switch (mode) { -- case PHY_INTERFACE_MODE_RGMII_ID: -- case PHY_INTERFACE_MODE_RGMII_RXID: -- if (of_property_read_u32(port_dn, "rx-internal-delay-ps", &val)) -- val = 2; -- else -- /* Switch regs accept value in ns, convert ps to ns */ -- val = val / 1000; -- -- if (val > QCA8K_MAX_DELAY) { -- dev_err(priv->dev, "rgmii rx delay is limited to a max value of 3ns, setting to the max value"); -- val = 3; -- } -- -- priv->rgmii_rx_delay = val; -- /* Stop here if we need to check only for rx delay */ -- if (mode != PHY_INTERFACE_MODE_RGMII_ID) -- break; -- -- fallthrough; -- case PHY_INTERFACE_MODE_RGMII_TXID: -- if (of_property_read_u32(port_dn, "tx-internal-delay-ps", &val)) -- val = 1; -- else -- /* Switch regs accept value in ns, convert ps to ns */ -- val = val / 1000; -- -- if (val > QCA8K_MAX_DELAY) { -- dev_err(priv->dev, "rgmii tx delay is limited to a max value of 3ns, setting to the max value"); -- val = 3; -- } -- -- priv->rgmii_tx_delay = val; -- break; -- default: -- return 0; -- } -- -- return 0; --} -- --static int - qca8k_setup_mac_pwr_sel(struct qca8k_priv *priv) - { - u32 mask = 0; -@@ -996,19 +934,21 @@ static int qca8k_find_cpu_port(struct ds - static int - qca8k_parse_port_config(struct qca8k_priv *priv) - { -+ int port, cpu_port_index = 0, ret; - struct device_node *port_dn; - phy_interface_t mode; - struct dsa_port *dp; -- int port, ret; -+ u32 delay; - - /* We have 2 CPU port. Check them */ -- for (port = 0; port < QCA8K_NUM_PORTS; port++) { -+ for (port = 0; port < QCA8K_NUM_PORTS && cpu_port_index < QCA8K_NUM_CPU_PORTS; port++) { - /* Skip every other port */ - if (port != 0 && port != 6) - continue; - - dp = dsa_to_port(priv->ds, port); - port_dn = dp->dn; -+ cpu_port_index++; - - if (!of_device_is_available(port_dn)) - continue; -@@ -1017,12 +957,54 @@ qca8k_parse_port_config(struct qca8k_pri - if (ret) - continue; - -- if (mode == PHY_INTERFACE_MODE_SGMII) { -+ switch (mode) { -+ case PHY_INTERFACE_MODE_RGMII: -+ case PHY_INTERFACE_MODE_RGMII_ID: -+ case PHY_INTERFACE_MODE_RGMII_TXID: -+ case PHY_INTERFACE_MODE_RGMII_RXID: -+ delay = 0; -+ -+ if (!of_property_read_u32(port_dn, "tx-internal-delay-ps", &delay)) -+ /* Switch regs accept value in ns, convert ps to ns */ -+ delay = delay / 1000; -+ else if (mode == PHY_INTERFACE_MODE_RGMII_ID || -+ mode == PHY_INTERFACE_MODE_RGMII_TXID) -+ delay = 1; -+ -+ if (delay > QCA8K_MAX_DELAY) { -+ dev_err(priv->dev, "rgmii tx delay is limited to a max value of 3ns, setting to the max value"); -+ delay = 3; -+ } -+ -+ priv->rgmii_tx_delay[cpu_port_index] = delay; -+ -+ delay = 0; -+ -+ if (!of_property_read_u32(port_dn, "rx-internal-delay-ps", &delay)) -+ /* Switch regs accept value in ns, convert ps to ns */ -+ delay = delay / 1000; -+ else if (mode == PHY_INTERFACE_MODE_RGMII_ID || -+ mode == PHY_INTERFACE_MODE_RGMII_RXID) -+ delay = 2; -+ -+ if (delay > QCA8K_MAX_DELAY) { -+ dev_err(priv->dev, "rgmii rx delay is limited to a max value of 3ns, setting to the max value"); -+ delay = 3; -+ } -+ -+ priv->rgmii_rx_delay[cpu_port_index] = delay; -+ -+ break; -+ case PHY_INTERFACE_MODE_SGMII: - if (of_property_read_bool(port_dn, "qca,sgmii-txclk-falling-edge")) - priv->sgmii_tx_clk_falling_edge = true; - - if (of_property_read_bool(port_dn, "qca,sgmii-rxclk-falling-edge")) - priv->sgmii_rx_clk_falling_edge = true; -+ -+ break; -+ default: -+ continue; - } - } - -@@ -1059,10 +1041,6 @@ qca8k_setup(struct dsa_switch *ds) - if (ret) - return ret; - -- ret = qca8k_setup_of_rgmii_delay(priv); -- if (ret) -- return ret; -- - ret = qca8k_setup_mac_pwr_sel(priv); - if (ret) - return ret; -@@ -1229,8 +1207,8 @@ qca8k_phylink_mac_config(struct dsa_swit - const struct phylink_link_state *state) - { - struct qca8k_priv *priv = ds->priv; -- u32 reg, val; -- int ret; -+ int cpu_port_index, ret; -+ u32 reg, val, delay; - - switch (port) { - case 0: /* 1st CPU port */ -@@ -1242,6 +1220,7 @@ qca8k_phylink_mac_config(struct dsa_swit - return; - - reg = QCA8K_REG_PORT0_PAD_CTRL; -+ cpu_port_index = QCA8K_CPU_PORT0; - break; - case 1: - case 2: -@@ -1260,6 +1239,7 @@ qca8k_phylink_mac_config(struct dsa_swit - return; - - reg = QCA8K_REG_PORT6_PAD_CTRL; -+ cpu_port_index = QCA8K_CPU_PORT6; - break; - default: - dev_err(ds->dev, "%s: unsupported port: %i\n", __func__, port); -@@ -1274,23 +1254,40 @@ qca8k_phylink_mac_config(struct dsa_swit - - switch (state->interface) { - case PHY_INTERFACE_MODE_RGMII: -- /* RGMII mode means no delay so don't enable the delay */ -- qca8k_write(priv, reg, QCA8K_PORT_PAD_RGMII_EN); -- break; - case PHY_INTERFACE_MODE_RGMII_ID: - case PHY_INTERFACE_MODE_RGMII_TXID: - case PHY_INTERFACE_MODE_RGMII_RXID: -- /* RGMII_ID needs internal delay. This is enabled through -- * PORT5_PAD_CTRL for all ports, rather than individual port -- * registers -+ val = QCA8K_PORT_PAD_RGMII_EN; -+ -+ /* Delay can be declared in 3 different way. -+ * Mode to rgmii and internal-delay standard binding defined -+ * rgmii-id or rgmii-tx/rx phy mode set. -+ * The parse logic set a delay different than 0 only when one -+ * of the 3 different way is used. In all other case delay is -+ * not enabled. With ID or TX/RXID delay is enabled and set -+ * to the default and recommended value. -+ */ -+ if (priv->rgmii_tx_delay[cpu_port_index]) { -+ delay = priv->rgmii_tx_delay[cpu_port_index]; -+ -+ val |= QCA8K_PORT_PAD_RGMII_TX_DELAY(delay) | -+ QCA8K_PORT_PAD_RGMII_TX_DELAY_EN; -+ } -+ -+ if (priv->rgmii_rx_delay[cpu_port_index]) { -+ delay = priv->rgmii_rx_delay[cpu_port_index]; -+ -+ val |= QCA8K_PORT_PAD_RGMII_RX_DELAY(delay) | -+ QCA8K_PORT_PAD_RGMII_RX_DELAY_EN; -+ } -+ -+ /* Set RGMII delay based on the selected values */ -+ qca8k_write(priv, reg, val); -+ -+ /* QCA8337 requires to set rgmii rx delay for all ports. -+ * This is enabled through PORT5_PAD_CTRL for all ports, -+ * rather than individual port registers. - */ -- qca8k_write(priv, reg, -- QCA8K_PORT_PAD_RGMII_EN | -- QCA8K_PORT_PAD_RGMII_TX_DELAY(priv->rgmii_tx_delay) | -- QCA8K_PORT_PAD_RGMII_RX_DELAY(priv->rgmii_rx_delay) | -- QCA8K_PORT_PAD_RGMII_TX_DELAY_EN | -- QCA8K_PORT_PAD_RGMII_RX_DELAY_EN); -- /* QCA8337 requires to set rgmii rx delay */ - if (priv->switch_id == QCA8K_ID_QCA8337) - qca8k_write(priv, QCA8K_REG_PORT5_PAD_CTRL, - QCA8K_PORT_PAD_RGMII_RX_DELAY_EN); ---- a/drivers/net/dsa/qca8k.h -+++ b/drivers/net/dsa/qca8k.h -@@ -13,6 +13,7 @@ - #include <linux/gpio.h> - - #define QCA8K_NUM_PORTS 7 -+#define QCA8K_NUM_CPU_PORTS 2 - #define QCA8K_MAX_MTU 9000 - - #define PHY_ID_QCA8327 0x004dd034 -@@ -255,13 +256,18 @@ struct qca8k_match_data { - u8 id; - }; - -+enum { -+ QCA8K_CPU_PORT0, -+ QCA8K_CPU_PORT6, -+}; -+ - struct qca8k_priv { - u8 switch_id; - u8 switch_revision; -- u8 rgmii_tx_delay; -- u8 rgmii_rx_delay; - bool sgmii_rx_clk_falling_edge; - bool sgmii_tx_clk_falling_edge; -+ u8 rgmii_rx_delay[QCA8K_NUM_CPU_PORTS]; /* 0: CPU port0, 1: CPU port6 */ -+ u8 rgmii_tx_delay[QCA8K_NUM_CPU_PORTS]; /* 0: CPU port0, 1: CPU port6 */ - bool legacy_phy_port_mapping; - struct regmap *regmap; - struct mii_bus *bus; |