1 From a0405999ebecf21ed9f76f1dc9420682cd3feba0 Mon Sep 17 00:00:00 2001
2 From: Weijie Gao <weijie.gao@mediatek.com>
3 Date: Wed, 19 Jul 2023 17:16:54 +0800
4 Subject: [PATCH 16/29] net: mediatek: connect switch to PSE only when starting
7 So far the switch is initialized in probe stage and is connected to PSE
8 unconditionally. This will cause all packets being flooded to PSE and may
9 cause PSE hang before entering linux.
11 This patch changes the connection between switch and PSE:
12 - Still initialize switch in probe stage, but disconnect it with PSE
13 - Connect switch with PSE on eth start
14 - Disconnect on eth stop
16 Signed-off-by: Weijie Gao <weijie.gao@mediatek.com>
18 drivers/net/mtk_eth.c | 44 ++++++++++++++++++++++++++++++++++++++++---
19 1 file changed, 41 insertions(+), 3 deletions(-)
21 --- a/drivers/net/mtk_eth.c
22 +++ b/drivers/net/mtk_eth.c
23 @@ -123,8 +123,10 @@ struct mtk_eth_priv {
26 int (*switch_init)(struct mtk_eth_priv *priv);
27 + void (*switch_mac_control)(struct mtk_eth_priv *priv, bool enable);
32 struct gpio_desc rst_gpio;
34 @@ -613,6 +615,16 @@ static int mt7530_pad_clk_setup(struct m
38 +static void mt7530_mac_control(struct mtk_eth_priv *priv, bool enable)
40 + u32 pmcr = FORCE_MODE;
43 + pmcr = priv->mt753x_pmcr;
45 + mt753x_reg_write(priv, PMCR_REG(6), pmcr);
48 static int mt7530_setup(struct mtk_eth_priv *priv)
50 u16 phy_addr, phy_val;
51 @@ -663,11 +675,14 @@ static int mt7530_setup(struct mtk_eth_p
52 FORCE_DPX | FORCE_LINK;
54 /* MT7530 Port6: Forced 1000M/FD, FC disabled */
55 - mt753x_reg_write(priv, PMCR_REG(6), val);
56 + priv->mt753x_pmcr = val;
58 /* MT7530 Port5: Forced link down */
59 mt753x_reg_write(priv, PMCR_REG(5), FORCE_MODE);
61 + /* Keep MAC link down before starting eth */
62 + mt753x_reg_write(priv, PMCR_REG(6), FORCE_MODE);
64 /* MT7530 Port6: Set to RGMII */
65 mt753x_reg_rmw(priv, MT7530_P6ECR, P6_INTF_MODE_M, P6_INTF_MODE_RGMII);
67 @@ -823,6 +838,17 @@ static void mt7531_phy_setting(struct mt
71 +static void mt7531_mac_control(struct mtk_eth_priv *priv, bool enable)
73 + u32 pmcr = FORCE_MODE_LNK;
76 + pmcr = priv->mt753x_pmcr;
78 + mt753x_reg_write(priv, PMCR_REG(5), pmcr);
79 + mt753x_reg_write(priv, PMCR_REG(6), pmcr);
82 static int mt7531_setup(struct mtk_eth_priv *priv)
84 u16 phy_addr, phy_val;
85 @@ -882,8 +908,11 @@ static int mt7531_setup(struct mtk_eth_p
86 (SPEED_1000M << FORCE_SPD_S) | FORCE_DPX |
89 - mt753x_reg_write(priv, PMCR_REG(5), pmcr);
90 - mt753x_reg_write(priv, PMCR_REG(6), pmcr);
91 + priv->mt753x_pmcr = pmcr;
93 + /* Keep MAC link down before starting eth */
94 + mt753x_reg_write(priv, PMCR_REG(5), FORCE_MODE_LNK);
95 + mt753x_reg_write(priv, PMCR_REG(6), FORCE_MODE_LNK);
98 for (i = 0; i < MT753X_NUM_PHYS; i++) {
99 @@ -1227,6 +1256,9 @@ static int mtk_eth_start(struct udevice
101 mtk_eth_fifo_init(priv);
103 + if (priv->switch_mac_control)
104 + priv->switch_mac_control(priv, true);
107 if (priv->sw == SW_NONE) {
108 ret = mtk_phy_start(priv);
109 @@ -1245,6 +1277,9 @@ static void mtk_eth_stop(struct udevice
111 struct mtk_eth_priv *priv = dev_get_priv(dev);
113 + if (priv->switch_mac_control)
114 + priv->switch_mac_control(priv, false);
116 mtk_pdma_rmw(priv, PDMA_GLO_CFG_REG,
117 TX_WB_DDONE | RX_DMA_EN | TX_DMA_EN, 0);
119 @@ -1484,16 +1519,19 @@ static int mtk_eth_of_to_plat(struct ude
120 /* check for switch first, otherwise phy will be used */
122 priv->switch_init = NULL;
123 + priv->switch_mac_control = NULL;
124 str = dev_read_string(dev, "mediatek,switch");
127 if (!strcmp(str, "mt7530")) {
128 priv->sw = SW_MT7530;
129 priv->switch_init = mt7530_setup;
130 + priv->switch_mac_control = mt7530_mac_control;
131 priv->mt753x_smi_addr = MT753X_DFL_SMI_ADDR;
132 } else if (!strcmp(str, "mt7531")) {
133 priv->sw = SW_MT7531;
134 priv->switch_init = mt7531_setup;
135 + priv->switch_mac_control = mt7531_mac_control;
136 priv->mt753x_smi_addr = MT753X_DFL_SMI_ADDR;
138 printf("error: unsupported switch\n");