Lines Matching +full:data +full:- +full:bus

1 // SPDX-License-Identifier: GPL-2.0 OR BSD-3-Clause
21 #define MDIO_MODE_DIV(x) FIELD_PREP(MDIO_MODE_DIV_MASK, (x) - 1)
58 static int ipq4019_mdio_wait_busy(struct mii_bus *bus) in ipq4019_mdio_wait_busy() argument
60 struct ipq4019_mdio_data *priv = bus->priv; in ipq4019_mdio_wait_busy()
63 return readl_poll_timeout(priv->membase + MDIO_CMD_REG, busy, in ipq4019_mdio_wait_busy()
68 static int ipq4019_mdio_read_c45(struct mii_bus *bus, int mii_id, int mmd, in ipq4019_mdio_read_c45() argument
71 struct ipq4019_mdio_data *priv = bus->priv; in ipq4019_mdio_read_c45()
72 unsigned int data; in ipq4019_mdio_read_c45() local
75 if (ipq4019_mdio_wait_busy(bus)) in ipq4019_mdio_read_c45()
76 return -ETIMEDOUT; in ipq4019_mdio_read_c45()
78 data = readl(priv->membase + MDIO_MODE_REG); in ipq4019_mdio_read_c45()
80 data |= MDIO_MODE_C45; in ipq4019_mdio_read_c45()
82 writel(data, priv->membase + MDIO_MODE_REG); in ipq4019_mdio_read_c45()
85 writel((mii_id << 8) | mmd, priv->membase + MDIO_ADDR_REG); in ipq4019_mdio_read_c45()
88 writel(reg, priv->membase + MDIO_DATA_WRITE_REG); in ipq4019_mdio_read_c45()
93 writel(cmd, priv->membase + MDIO_CMD_REG); in ipq4019_mdio_read_c45()
96 if (ipq4019_mdio_wait_busy(bus)) in ipq4019_mdio_read_c45()
97 return -ETIMEDOUT; in ipq4019_mdio_read_c45()
101 writel(cmd, priv->membase + MDIO_CMD_REG); in ipq4019_mdio_read_c45()
103 if (ipq4019_mdio_wait_busy(bus)) in ipq4019_mdio_read_c45()
104 return -ETIMEDOUT; in ipq4019_mdio_read_c45()
106 /* Read and return data */ in ipq4019_mdio_read_c45()
107 return readl(priv->membase + MDIO_DATA_READ_REG); in ipq4019_mdio_read_c45()
110 static int ipq4019_mdio_read_c22(struct mii_bus *bus, int mii_id, int regnum) in ipq4019_mdio_read_c22() argument
112 struct ipq4019_mdio_data *priv = bus->priv; in ipq4019_mdio_read_c22()
113 unsigned int data; in ipq4019_mdio_read_c22() local
116 if (ipq4019_mdio_wait_busy(bus)) in ipq4019_mdio_read_c22()
117 return -ETIMEDOUT; in ipq4019_mdio_read_c22()
119 data = readl(priv->membase + MDIO_MODE_REG); in ipq4019_mdio_read_c22()
121 data &= ~MDIO_MODE_C45; in ipq4019_mdio_read_c22()
123 writel(data, priv->membase + MDIO_MODE_REG); in ipq4019_mdio_read_c22()
126 writel((mii_id << 8) | regnum, priv->membase + MDIO_ADDR_REG); in ipq4019_mdio_read_c22()
131 writel(cmd, priv->membase + MDIO_CMD_REG); in ipq4019_mdio_read_c22()
134 if (ipq4019_mdio_wait_busy(bus)) in ipq4019_mdio_read_c22()
135 return -ETIMEDOUT; in ipq4019_mdio_read_c22()
137 /* Read and return data */ in ipq4019_mdio_read_c22()
138 return readl(priv->membase + MDIO_DATA_READ_REG); in ipq4019_mdio_read_c22()
141 static int ipq4019_mdio_write_c45(struct mii_bus *bus, int mii_id, int mmd, in ipq4019_mdio_write_c45() argument
144 struct ipq4019_mdio_data *priv = bus->priv; in ipq4019_mdio_write_c45()
145 unsigned int data; in ipq4019_mdio_write_c45() local
148 if (ipq4019_mdio_wait_busy(bus)) in ipq4019_mdio_write_c45()
149 return -ETIMEDOUT; in ipq4019_mdio_write_c45()
151 data = readl(priv->membase + MDIO_MODE_REG); in ipq4019_mdio_write_c45()
153 data |= MDIO_MODE_C45; in ipq4019_mdio_write_c45()
155 writel(data, priv->membase + MDIO_MODE_REG); in ipq4019_mdio_write_c45()
158 writel((mii_id << 8) | mmd, priv->membase + MDIO_ADDR_REG); in ipq4019_mdio_write_c45()
161 writel(reg, priv->membase + MDIO_DATA_WRITE_REG); in ipq4019_mdio_write_c45()
165 writel(cmd, priv->membase + MDIO_CMD_REG); in ipq4019_mdio_write_c45()
167 if (ipq4019_mdio_wait_busy(bus)) in ipq4019_mdio_write_c45()
168 return -ETIMEDOUT; in ipq4019_mdio_write_c45()
170 /* issue write data */ in ipq4019_mdio_write_c45()
171 writel(value, priv->membase + MDIO_DATA_WRITE_REG); in ipq4019_mdio_write_c45()
174 writel(cmd, priv->membase + MDIO_CMD_REG); in ipq4019_mdio_write_c45()
177 if (ipq4019_mdio_wait_busy(bus)) in ipq4019_mdio_write_c45()
178 return -ETIMEDOUT; in ipq4019_mdio_write_c45()
183 static int ipq4019_mdio_write_c22(struct mii_bus *bus, int mii_id, int regnum, in ipq4019_mdio_write_c22() argument
186 struct ipq4019_mdio_data *priv = bus->priv; in ipq4019_mdio_write_c22()
187 unsigned int data; in ipq4019_mdio_write_c22() local
190 if (ipq4019_mdio_wait_busy(bus)) in ipq4019_mdio_write_c22()
191 return -ETIMEDOUT; in ipq4019_mdio_write_c22()
194 data = readl(priv->membase + MDIO_MODE_REG); in ipq4019_mdio_write_c22()
196 data &= ~MDIO_MODE_C45; in ipq4019_mdio_write_c22()
198 writel(data, priv->membase + MDIO_MODE_REG); in ipq4019_mdio_write_c22()
201 writel((mii_id << 8) | regnum, priv->membase + MDIO_ADDR_REG); in ipq4019_mdio_write_c22()
203 /* issue write data */ in ipq4019_mdio_write_c22()
204 writel(value, priv->membase + MDIO_DATA_WRITE_REG); in ipq4019_mdio_write_c22()
209 writel(cmd, priv->membase + MDIO_CMD_REG); in ipq4019_mdio_write_c22()
212 if (ipq4019_mdio_wait_busy(bus)) in ipq4019_mdio_write_c22()
213 return -ETIMEDOUT; in ipq4019_mdio_write_c22()
226 if (priv->mdio_clk) in ipq4019_mdio_set_div()
227 ahb_rate = clk_get_rate(priv->mdio_clk); in ipq4019_mdio_set_div()
231 * assure correct functionality of the MDIO bus in ipq4019_mdio_set_div()
236 if (priv->mdc_rate == DIV_ROUND_UP(ahb_rate, div)) { in ipq4019_mdio_set_div()
237 val = readl(priv->membase + MDIO_MODE_REG); in ipq4019_mdio_set_div()
240 writel(val, priv->membase + MDIO_MODE_REG); in ipq4019_mdio_set_div()
247 return -EINVAL; in ipq4019_mdio_set_div()
250 static int ipq_mdio_reset(struct mii_bus *bus) in ipq_mdio_reset() argument
252 struct ipq4019_mdio_data *priv = bus->priv; in ipq_mdio_reset()
259 if (priv->eth_ldo_rdy) { in ipq_mdio_reset()
260 val = readl(priv->eth_ldo_rdy); in ipq_mdio_reset()
262 writel(val, priv->eth_ldo_rdy); in ipq_mdio_reset()
267 ret = clk_set_rate(priv->mdio_clk, IPQ_MDIO_CLK_RATE); in ipq_mdio_reset()
271 ret = clk_prepare_enable(priv->mdio_clk); in ipq_mdio_reset()
289 if (!of_property_read_u32(pdev->dev.of_node, "clock-frequency", in ipq4019_mdio_select_mdc_rate()
290 &priv->mdc_rate)) in ipq4019_mdio_select_mdc_rate()
295 if (priv->mdio_clk) in ipq4019_mdio_select_mdc_rate()
296 ahb_rate = clk_get_rate(priv->mdio_clk); in ipq4019_mdio_select_mdc_rate()
299 val = readl(priv->membase + MDIO_MODE_REG); in ipq4019_mdio_select_mdc_rate()
307 priv->mdc_rate = DIV_ROUND_UP(ahb_rate, div + 1); in ipq4019_mdio_select_mdc_rate()
322 priv->mdc_rate = DIV_ROUND_UP(ahb_rate, div); in ipq4019_mdio_select_mdc_rate()
329 struct mii_bus *bus; in ipq4019_mdio_probe() local
333 bus = devm_mdiobus_alloc_size(&pdev->dev, sizeof(*priv)); in ipq4019_mdio_probe()
334 if (!bus) in ipq4019_mdio_probe()
335 return -ENOMEM; in ipq4019_mdio_probe()
337 priv = bus->priv; in ipq4019_mdio_probe()
339 priv->membase = devm_platform_ioremap_resource(pdev, 0); in ipq4019_mdio_probe()
340 if (IS_ERR(priv->membase)) in ipq4019_mdio_probe()
341 return PTR_ERR(priv->membase); in ipq4019_mdio_probe()
343 priv->mdio_clk = devm_clk_get_optional(&pdev->dev, "gcc_mdio_ahb_clk"); in ipq4019_mdio_probe()
344 if (IS_ERR(priv->mdio_clk)) in ipq4019_mdio_probe()
345 return PTR_ERR(priv->mdio_clk); in ipq4019_mdio_probe()
356 priv->eth_ldo_rdy = devm_ioremap_resource(&pdev->dev, res); in ipq4019_mdio_probe()
358 bus->name = "ipq4019_mdio"; in ipq4019_mdio_probe()
359 bus->read = ipq4019_mdio_read_c22; in ipq4019_mdio_probe()
360 bus->write = ipq4019_mdio_write_c22; in ipq4019_mdio_probe()
361 bus->read_c45 = ipq4019_mdio_read_c45; in ipq4019_mdio_probe()
362 bus->write_c45 = ipq4019_mdio_write_c45; in ipq4019_mdio_probe()
363 bus->reset = ipq_mdio_reset; in ipq4019_mdio_probe()
364 bus->parent = &pdev->dev; in ipq4019_mdio_probe()
365 snprintf(bus->id, MII_BUS_ID_SIZE, "%s%d", pdev->name, pdev->id); in ipq4019_mdio_probe()
367 ret = of_mdiobus_register(bus, pdev->dev.of_node); in ipq4019_mdio_probe()
369 dev_err(&pdev->dev, "Cannot register MDIO bus!\n"); in ipq4019_mdio_probe()
373 platform_set_drvdata(pdev, bus); in ipq4019_mdio_probe()
380 struct mii_bus *bus = platform_get_drvdata(pdev); in ipq4019_mdio_remove() local
382 mdiobus_unregister(bus); in ipq4019_mdio_remove()
386 { .compatible = "qcom,ipq4019-mdio" },
387 { .compatible = "qcom,ipq5018-mdio" },
396 .name = "ipq4019-mdio",