Lines Matching +full:ocelot +full:- +full:1

1 // SPDX-License-Identifier: (GPL-2.0 OR MIT)
3 * Microsemi Ocelot Switch driver
7 #include <linux/dsa/ocelot.h>
20 #include <soc/mscc/ocelot.h>
24 #include "ocelot.h"
29 static int ocelot_chip_init(struct ocelot *ocelot, const struct ocelot_ops *ops) in ocelot_chip_init() argument
33 ocelot->map = vsc7514_regmap; in ocelot_chip_init()
34 ocelot->num_mact_rows = 1024; in ocelot_chip_init()
35 ocelot->ops = ops; in ocelot_chip_init()
37 ret = ocelot_regfields_init(ocelot, vsc7514_regfields); in ocelot_chip_init()
41 ocelot_pll5_init(ocelot); in ocelot_chip_init()
43 eth_random_addr(ocelot->base_mac); in ocelot_chip_init()
44 ocelot->base_mac[5] &= 0xf0; in ocelot_chip_init()
51 struct ocelot *ocelot = arg; in ocelot_xtr_irq_handler() local
54 while (ocelot_read(ocelot, QS_XTR_DATA_PRESENT) & BIT(grp)) { in ocelot_xtr_irq_handler()
57 err = ocelot_xtr_poll_frame(ocelot, grp, &skb); in ocelot_xtr_irq_handler()
61 skb->dev->stats.rx_bytes += skb->len; in ocelot_xtr_irq_handler()
62 skb->dev->stats.rx_packets++; in ocelot_xtr_irq_handler()
70 ocelot_drain_cpu_queue(ocelot, 0); in ocelot_xtr_irq_handler()
77 struct ocelot *ocelot = arg; in ocelot_ptp_rdy_irq_handler() local
79 ocelot_get_txtstamp(ocelot); in ocelot_ptp_rdy_irq_handler()
85 { .compatible = "mscc,vsc7514-switch" },
101 .name = "ocelot ptp",
116 static void mscc_ocelot_teardown_devlink_ports(struct ocelot *ocelot) in mscc_ocelot_teardown_devlink_ports() argument
120 for (port = 0; port < ocelot->num_phys_ports; port++) in mscc_ocelot_teardown_devlink_ports()
121 ocelot_port_devlink_teardown(ocelot, port); in mscc_ocelot_teardown_devlink_ports()
124 static void mscc_ocelot_release_ports(struct ocelot *ocelot) in mscc_ocelot_release_ports() argument
128 for (port = 0; port < ocelot->num_phys_ports; port++) { in mscc_ocelot_release_ports()
131 ocelot_port = ocelot->ports[port]; in mscc_ocelot_release_ports()
135 ocelot_deinit_port(ocelot, port); in mscc_ocelot_release_ports()
143 struct ocelot *ocelot = platform_get_drvdata(pdev); in mscc_ocelot_init_ports() local
149 ocelot->ports = devm_kcalloc(ocelot->dev, ocelot->num_phys_ports, in mscc_ocelot_init_ports()
151 if (!ocelot->ports) in mscc_ocelot_init_ports()
152 return -ENOMEM; in mscc_ocelot_init_ports()
154 ocelot->devlink_ports = devm_kcalloc(ocelot->dev, in mscc_ocelot_init_ports()
155 ocelot->num_phys_ports, in mscc_ocelot_init_ports()
156 sizeof(*ocelot->devlink_ports), in mscc_ocelot_init_ports()
158 if (!ocelot->devlink_ports) in mscc_ocelot_init_ports()
159 return -ENOMEM; in mscc_ocelot_init_ports()
170 if (port < 0 || port >= ocelot->num_phys_ports) { in mscc_ocelot_init_ports()
171 dev_err(ocelot->dev, in mscc_ocelot_init_ports()
173 ocelot->num_phys_ports); in mscc_ocelot_init_ports()
181 target = ocelot_regmap_init(ocelot, res); in mscc_ocelot_init_ports()
188 err = ocelot_port_devlink_init(ocelot, port, in mscc_ocelot_init_ports()
195 err = ocelot_probe_port(ocelot, port, target, portnp); in mscc_ocelot_init_ports()
197 ocelot_port_devlink_teardown(ocelot, port); in mscc_ocelot_init_ports()
205 for (port = 0; port < ocelot->num_phys_ports; port++) { in mscc_ocelot_init_ports()
209 err = ocelot_port_devlink_init(ocelot, port, in mscc_ocelot_init_ports()
221 mscc_ocelot_release_ports(ocelot); in mscc_ocelot_init_ports()
223 for (port = 0; port < ocelot->num_phys_ports; port++) { in mscc_ocelot_init_ports()
225 ocelot_port_devlink_teardown(ocelot, port); in mscc_ocelot_init_ports()
232 struct device_node *np = pdev->dev.of_node; in mscc_ocelot_probe()
236 struct ocelot *ocelot; in mscc_ocelot_probe() local
243 u8 optional:1; in mscc_ocelot_probe()
253 { PTP, "ptp", 1 }, in mscc_ocelot_probe()
254 { FDMA, "fdma", 1 }, in mscc_ocelot_probe()
257 if (!np && !pdev->dev.platform_data) in mscc_ocelot_probe()
258 return -ENODEV; in mscc_ocelot_probe()
261 devlink_alloc(&ocelot_devlink_ops, sizeof(*ocelot), &pdev->dev); in mscc_ocelot_probe()
263 return -ENOMEM; in mscc_ocelot_probe()
265 ocelot = devlink_priv(devlink); in mscc_ocelot_probe()
266 ocelot->devlink = priv_to_devlink(ocelot); in mscc_ocelot_probe()
267 platform_set_drvdata(pdev, ocelot); in mscc_ocelot_probe()
268 ocelot->dev = &pdev->dev; in mscc_ocelot_probe()
277 target = ocelot_regmap_init(ocelot, res); in mscc_ocelot_probe()
280 ocelot->targets[io_target[i].id] = NULL; in mscc_ocelot_probe()
287 ocelot->targets[io_target[i].id] = target; in mscc_ocelot_probe()
290 if (ocelot->targets[FDMA]) in mscc_ocelot_probe()
291 ocelot_fdma_init(pdev, ocelot); in mscc_ocelot_probe()
293 hsio = syscon_regmap_lookup_by_compatible("mscc,ocelot-hsio"); in mscc_ocelot_probe()
295 dev_err(&pdev->dev, "missing hsio syscon\n"); in mscc_ocelot_probe()
300 ocelot->targets[HSIO] = hsio; in mscc_ocelot_probe()
302 err = ocelot_chip_init(ocelot, &ocelot_ops); in mscc_ocelot_probe()
312 err = devm_request_threaded_irq(&pdev->dev, irq_xtr, NULL, in mscc_ocelot_probe()
314 "frame extraction", ocelot); in mscc_ocelot_probe()
319 if (irq_ptp_rdy > 0 && ocelot->targets[PTP]) { in mscc_ocelot_probe()
320 err = devm_request_threaded_irq(&pdev->dev, irq_ptp_rdy, NULL, in mscc_ocelot_probe()
323 ocelot); in mscc_ocelot_probe()
328 ocelot->ptp = 1; in mscc_ocelot_probe()
331 ports = of_get_child_by_name(np, "ethernet-ports"); in mscc_ocelot_probe()
333 dev_err(ocelot->dev, "no ethernet-ports child node found\n"); in mscc_ocelot_probe()
334 err = -ENODEV; in mscc_ocelot_probe()
338 ocelot->num_phys_ports = of_get_child_count(ports); in mscc_ocelot_probe()
339 ocelot->num_flooding_pgids = 1; in mscc_ocelot_probe()
341 ocelot->vcap = vsc7514_vcap_props; in mscc_ocelot_probe()
343 ocelot->vcap_pol.base = VSC7514_VCAP_POLICER_BASE; in mscc_ocelot_probe()
344 ocelot->vcap_pol.max = VSC7514_VCAP_POLICER_MAX; in mscc_ocelot_probe()
346 ocelot->npi = -1; in mscc_ocelot_probe()
348 err = ocelot_init(ocelot); in mscc_ocelot_probe()
356 if (ocelot->fdma) in mscc_ocelot_probe()
357 ocelot_fdma_start(ocelot); in mscc_ocelot_probe()
359 err = ocelot_devlink_sb_register(ocelot); in mscc_ocelot_probe()
363 if (ocelot->ptp) { in mscc_ocelot_probe()
364 err = ocelot_init_timestamp(ocelot, &ocelot_ptp_clock_info); in mscc_ocelot_probe()
366 dev_err(ocelot->dev, in mscc_ocelot_probe()
368 ocelot->ptp = 0; in mscc_ocelot_probe()
379 dev_info(&pdev->dev, "Ocelot switch probed\n"); in mscc_ocelot_probe()
384 mscc_ocelot_release_ports(ocelot); in mscc_ocelot_probe()
385 mscc_ocelot_teardown_devlink_ports(ocelot); in mscc_ocelot_probe()
387 ocelot_deinit(ocelot); in mscc_ocelot_probe()
397 struct ocelot *ocelot = platform_get_drvdata(pdev); in mscc_ocelot_remove() local
399 if (ocelot->fdma) in mscc_ocelot_remove()
400 ocelot_fdma_deinit(ocelot); in mscc_ocelot_remove()
401 devlink_unregister(ocelot->devlink); in mscc_ocelot_remove()
402 ocelot_deinit_timestamp(ocelot); in mscc_ocelot_remove()
403 ocelot_devlink_sb_unregister(ocelot); in mscc_ocelot_remove()
404 mscc_ocelot_release_ports(ocelot); in mscc_ocelot_remove()
405 mscc_ocelot_teardown_devlink_ports(ocelot); in mscc_ocelot_remove()
406 ocelot_deinit(ocelot); in mscc_ocelot_remove()
410 devlink_free(ocelot->devlink); in mscc_ocelot_remove()
417 .name = "ocelot-switch",
424 MODULE_DESCRIPTION("Microsemi Ocelot switch driver");