1 From 5053a6cf1d50d785078562470d2a63695a9f3bf2 Mon Sep 17 00:00:00 2001
2 From: =?UTF-8?q?Ar=C4=B1n=C3=A7=20=C3=9CNAL?= <arinc.unal@arinc9.com>
3 Date: Thu, 18 Apr 2024 08:35:30 +0300
4 Subject: [PATCH 4/5] net: dsa: mt7530-mdio: read PHY address of switch from
7 Content-Type: text/plain; charset=UTF-8
8 Content-Transfer-Encoding: 8bit
10 Read the PHY address the switch listens on from the reg property of the
11 switch node on the device tree. This change brings support for MT7530
12 switches on boards with such bootstrapping configuration where the switch
13 listens on a different PHY address than the hardcoded PHY address on the
16 As described on the "MT7621 Programming Guide v0.4" document, the MT7530
17 switch and its PHYs can be configured to listen on the range of 7-12,
18 15-20, 23-28, and 31 and 0-4 PHY addresses.
20 There are operations where the switch PHY registers are used. For the PHY
21 address of the control PHY, transform the MT753X_CTRL_PHY_ADDR constant
22 into a macro and use it. The PHY address for the control PHY is 0 when the
23 switch listens on 31. In any other case, it is one greater than the PHY
24 address the switch listens on.
26 Reviewed-by: Daniel Golle <daniel@makrotopia.org>
27 Tested-by: Daniel Golle <daniel@makrotopia.org>
28 Reviewed-by: Florian Fainelli <florian.fainelli@broadcom.com>
29 Signed-off-by: Arınç ÜNAL <arinc.unal@arinc9.com>
30 Signed-off-by: Paolo Abeni <pabeni@redhat.com>
32 drivers/net/dsa/mt7530-mdio.c | 28 +++++++++++++-------------
33 drivers/net/dsa/mt7530.c | 37 +++++++++++++++++++++++------------
34 drivers/net/dsa/mt7530.h | 4 +++-
35 3 files changed, 41 insertions(+), 28 deletions(-)
37 --- a/drivers/net/dsa/mt7530-mdio.c
38 +++ b/drivers/net/dsa/mt7530-mdio.c
41 mt7530_regmap_write(void *context, unsigned int reg, unsigned int val)
43 - struct mii_bus *bus = context;
44 + struct mt7530_priv *priv = context;
45 + struct mii_bus *bus = priv->bus;
49 @@ -27,36 +28,35 @@ mt7530_regmap_write(void *context, unsig
53 - /* MT7530 uses 31 as the pseudo port */
54 - ret = bus->write(bus, 0x1f, 0x1f, page);
55 + ret = bus->write(bus, priv->mdiodev->addr, 0x1f, page);
59 - ret = bus->write(bus, 0x1f, r, lo);
60 + ret = bus->write(bus, priv->mdiodev->addr, r, lo);
64 - ret = bus->write(bus, 0x1f, 0x10, hi);
65 + ret = bus->write(bus, priv->mdiodev->addr, 0x10, hi);
70 mt7530_regmap_read(void *context, unsigned int reg, unsigned int *val)
72 - struct mii_bus *bus = context;
73 + struct mt7530_priv *priv = context;
74 + struct mii_bus *bus = priv->bus;
78 page = (reg >> 6) & 0x3ff;
81 - /* MT7530 uses 31 as the pseudo port */
82 - ret = bus->write(bus, 0x1f, 0x1f, page);
83 + ret = bus->write(bus, priv->mdiodev->addr, 0x1f, page);
87 - lo = bus->read(bus, 0x1f, r);
88 - hi = bus->read(bus, 0x1f, 0x10);
89 + lo = bus->read(bus, priv->mdiodev->addr, r);
90 + hi = bus->read(bus, priv->mdiodev->addr, 0x10);
92 *val = (hi << 16) | (lo & 0xffff);
94 @@ -107,8 +107,7 @@ mt7531_create_sgmii(struct mt7530_priv *
95 mt7531_pcs_config[i]->unlock = mt7530_mdio_regmap_unlock;
96 mt7531_pcs_config[i]->lock_arg = &priv->bus->mdio_lock;
98 - regmap = devm_regmap_init(priv->dev,
99 - &mt7530_regmap_bus, priv->bus,
100 + regmap = devm_regmap_init(priv->dev, &mt7530_regmap_bus, priv,
101 mt7531_pcs_config[i]);
102 if (IS_ERR(regmap)) {
103 ret = PTR_ERR(regmap);
104 @@ -153,6 +152,7 @@ mt7530_probe(struct mdio_device *mdiodev
106 priv->bus = mdiodev->bus;
107 priv->dev = &mdiodev->dev;
108 + priv->mdiodev = mdiodev;
110 ret = mt7530_probe_common(priv);
112 @@ -203,8 +203,8 @@ mt7530_probe(struct mdio_device *mdiodev
113 regmap_config->reg_stride = 4;
114 regmap_config->max_register = MT7530_CREV;
115 regmap_config->disable_locking = true;
116 - priv->regmap = devm_regmap_init(priv->dev, &mt7530_regmap_bus,
117 - priv->bus, regmap_config);
118 + priv->regmap = devm_regmap_init(priv->dev, &mt7530_regmap_bus, priv,
120 if (IS_ERR(priv->regmap))
121 return PTR_ERR(priv->regmap);
123 --- a/drivers/net/dsa/mt7530.c
124 +++ b/drivers/net/dsa/mt7530.c
125 @@ -86,22 +86,26 @@ core_read_mmd_indirect(struct mt7530_pri
128 /* Write the desired MMD Devad */
129 - ret = bus->write(bus, 0, MII_MMD_CTRL, devad);
130 + ret = bus->write(bus, MT753X_CTRL_PHY_ADDR(priv->mdiodev->addr),
131 + MII_MMD_CTRL, devad);
135 /* Write the desired MMD register address */
136 - ret = bus->write(bus, 0, MII_MMD_DATA, prtad);
137 + ret = bus->write(bus, MT753X_CTRL_PHY_ADDR(priv->mdiodev->addr),
138 + MII_MMD_DATA, prtad);
142 /* Select the Function : DATA with no post increment */
143 - ret = bus->write(bus, 0, MII_MMD_CTRL, (devad | MII_MMD_CTRL_NOINCR));
144 + ret = bus->write(bus, MT753X_CTRL_PHY_ADDR(priv->mdiodev->addr),
145 + MII_MMD_CTRL, devad | MII_MMD_CTRL_NOINCR);
149 /* Read the content of the MMD's selected register */
150 - value = bus->read(bus, 0, MII_MMD_DATA);
151 + value = bus->read(bus, MT753X_CTRL_PHY_ADDR(priv->mdiodev->addr),
156 @@ -118,22 +122,26 @@ core_write_mmd_indirect(struct mt7530_pr
159 /* Write the desired MMD Devad */
160 - ret = bus->write(bus, 0, MII_MMD_CTRL, devad);
161 + ret = bus->write(bus, MT753X_CTRL_PHY_ADDR(priv->mdiodev->addr),
162 + MII_MMD_CTRL, devad);
166 /* Write the desired MMD register address */
167 - ret = bus->write(bus, 0, MII_MMD_DATA, prtad);
168 + ret = bus->write(bus, MT753X_CTRL_PHY_ADDR(priv->mdiodev->addr),
169 + MII_MMD_DATA, prtad);
173 /* Select the Function : DATA with no post increment */
174 - ret = bus->write(bus, 0, MII_MMD_CTRL, (devad | MII_MMD_CTRL_NOINCR));
175 + ret = bus->write(bus, MT753X_CTRL_PHY_ADDR(priv->mdiodev->addr),
176 + MII_MMD_CTRL, devad | MII_MMD_CTRL_NOINCR);
180 /* Write the data into MMD's selected register */
181 - ret = bus->write(bus, 0, MII_MMD_DATA, data);
182 + ret = bus->write(bus, MT753X_CTRL_PHY_ADDR(priv->mdiodev->addr),
183 + MII_MMD_DATA, data);
187 @@ -2679,16 +2687,19 @@ mt7531_setup(struct dsa_switch *ds)
188 * phy_[read,write]_mmd_indirect is called, we provide our own
189 * mt7531_ind_mmd_phy_[read,write] to complete this function.
191 - val = mt7531_ind_c45_phy_read(priv, MT753X_CTRL_PHY_ADDR,
192 + val = mt7531_ind_c45_phy_read(priv,
193 + MT753X_CTRL_PHY_ADDR(priv->mdiodev->addr),
194 MDIO_MMD_VEND2, CORE_PLL_GROUP4);
195 val |= MT7531_RG_SYSPLL_DMY2 | MT7531_PHY_PLL_BYPASS_MODE;
196 val &= ~MT7531_PHY_PLL_OFF;
197 - mt7531_ind_c45_phy_write(priv, MT753X_CTRL_PHY_ADDR, MDIO_MMD_VEND2,
198 - CORE_PLL_GROUP4, val);
199 + mt7531_ind_c45_phy_write(priv,
200 + MT753X_CTRL_PHY_ADDR(priv->mdiodev->addr),
201 + MDIO_MMD_VEND2, CORE_PLL_GROUP4, val);
203 /* Disable EEE advertisement on the switch PHYs. */
204 - for (i = MT753X_CTRL_PHY_ADDR;
205 - i < MT753X_CTRL_PHY_ADDR + MT7530_NUM_PHYS; i++) {
206 + for (i = MT753X_CTRL_PHY_ADDR(priv->mdiodev->addr);
207 + i < MT753X_CTRL_PHY_ADDR(priv->mdiodev->addr) + MT7530_NUM_PHYS;
209 mt7531_ind_c45_phy_write(priv, i, MDIO_MMD_AN, MDIO_AN_EEE_ADV,
212 --- a/drivers/net/dsa/mt7530.h
213 +++ b/drivers/net/dsa/mt7530.h
214 @@ -629,7 +629,7 @@ enum mt7531_clk_skew {
215 #define MT7531_PHY_PLL_OFF BIT(5)
216 #define MT7531_PHY_PLL_BYPASS_MODE BIT(4)
218 -#define MT753X_CTRL_PHY_ADDR 0
219 +#define MT753X_CTRL_PHY_ADDR(addr) ((addr + 1) & 0x1f)
221 #define CORE_PLL_GROUP5 0x404
222 #define RG_LCDDS_PCW_NCPO1(x) ((x) & 0xffff)
223 @@ -778,6 +778,7 @@ struct mt753x_info {
224 * @irq_enable: IRQ enable bits, synced to SYS_INT_EN
225 * @create_sgmii: Pointer to function creating SGMII PCS instance(s)
226 * @active_cpu_ports: Holding the active CPU ports
227 + * @mdiodev: The pointer to the MDIO device structure
231 @@ -804,6 +805,7 @@ struct mt7530_priv {
233 int (*create_sgmii)(struct mt7530_priv *priv);
235 + struct mdio_device *mdiodev;
238 struct mt7530_hw_vlan_entry {