1427541df31688eaeec2b5aa6b6ea3c5e5a9db2f
[platform/kernel/linux-rpi.git] / drivers / net / dsa / mv88e6xxx / chip.c
1 /*
2  * Marvell 88e6xxx Ethernet switch single-chip support
3  *
4  * Copyright (c) 2008 Marvell Semiconductor
5  *
6  * Copyright (c) 2016 Andrew Lunn <andrew@lunn.ch>
7  *
8  * Copyright (c) 2016-2017 Savoir-faire Linux Inc.
9  *      Vivien Didelot <vivien.didelot@savoirfairelinux.com>
10  *
11  * This program is free software; you can redistribute it and/or modify
12  * it under the terms of the GNU General Public License as published by
13  * the Free Software Foundation; either version 2 of the License, or
14  * (at your option) any later version.
15  */
16
17 #include <linux/delay.h>
18 #include <linux/etherdevice.h>
19 #include <linux/ethtool.h>
20 #include <linux/if_bridge.h>
21 #include <linux/interrupt.h>
22 #include <linux/irq.h>
23 #include <linux/irqdomain.h>
24 #include <linux/jiffies.h>
25 #include <linux/list.h>
26 #include <linux/mdio.h>
27 #include <linux/module.h>
28 #include <linux/of_device.h>
29 #include <linux/of_irq.h>
30 #include <linux/of_mdio.h>
31 #include <linux/platform_data/mv88e6xxx.h>
32 #include <linux/netdevice.h>
33 #include <linux/gpio/consumer.h>
34 #include <linux/phy.h>
35 #include <linux/phylink.h>
36 #include <net/dsa.h>
37
38 #include "chip.h"
39 #include "global1.h"
40 #include "global2.h"
41 #include "hwtstamp.h"
42 #include "phy.h"
43 #include "port.h"
44 #include "ptp.h"
45 #include "serdes.h"
46
47 static void assert_reg_lock(struct mv88e6xxx_chip *chip)
48 {
49         if (unlikely(!mutex_is_locked(&chip->reg_lock))) {
50                 dev_err(chip->dev, "Switch registers lock not held!\n");
51                 dump_stack();
52         }
53 }
54
55 /* The switch ADDR[4:1] configuration pins define the chip SMI device address
56  * (ADDR[0] is always zero, thus only even SMI addresses can be strapped).
57  *
58  * When ADDR is all zero, the chip uses Single-chip Addressing Mode, assuming it
59  * is the only device connected to the SMI master. In this mode it responds to
60  * all 32 possible SMI addresses, and thus maps directly the internal devices.
61  *
62  * When ADDR is non-zero, the chip uses Multi-chip Addressing Mode, allowing
63  * multiple devices to share the SMI interface. In this mode it responds to only
64  * 2 registers, used to indirectly access the internal SMI devices.
65  */
66
67 static int mv88e6xxx_smi_read(struct mv88e6xxx_chip *chip,
68                               int addr, int reg, u16 *val)
69 {
70         if (!chip->smi_ops)
71                 return -EOPNOTSUPP;
72
73         return chip->smi_ops->read(chip, addr, reg, val);
74 }
75
76 static int mv88e6xxx_smi_write(struct mv88e6xxx_chip *chip,
77                                int addr, int reg, u16 val)
78 {
79         if (!chip->smi_ops)
80                 return -EOPNOTSUPP;
81
82         return chip->smi_ops->write(chip, addr, reg, val);
83 }
84
85 static int mv88e6xxx_smi_single_chip_read(struct mv88e6xxx_chip *chip,
86                                           int addr, int reg, u16 *val)
87 {
88         int ret;
89
90         ret = mdiobus_read_nested(chip->bus, addr, reg);
91         if (ret < 0)
92                 return ret;
93
94         *val = ret & 0xffff;
95
96         return 0;
97 }
98
99 static int mv88e6xxx_smi_single_chip_write(struct mv88e6xxx_chip *chip,
100                                            int addr, int reg, u16 val)
101 {
102         int ret;
103
104         ret = mdiobus_write_nested(chip->bus, addr, reg, val);
105         if (ret < 0)
106                 return ret;
107
108         return 0;
109 }
110
111 static const struct mv88e6xxx_bus_ops mv88e6xxx_smi_single_chip_ops = {
112         .read = mv88e6xxx_smi_single_chip_read,
113         .write = mv88e6xxx_smi_single_chip_write,
114 };
115
116 static int mv88e6xxx_smi_multi_chip_wait(struct mv88e6xxx_chip *chip)
117 {
118         int ret;
119         int i;
120
121         for (i = 0; i < 16; i++) {
122                 ret = mdiobus_read_nested(chip->bus, chip->sw_addr, SMI_CMD);
123                 if (ret < 0)
124                         return ret;
125
126                 if ((ret & SMI_CMD_BUSY) == 0)
127                         return 0;
128         }
129
130         return -ETIMEDOUT;
131 }
132
133 static int mv88e6xxx_smi_multi_chip_read(struct mv88e6xxx_chip *chip,
134                                          int addr, int reg, u16 *val)
135 {
136         int ret;
137
138         /* Wait for the bus to become free. */
139         ret = mv88e6xxx_smi_multi_chip_wait(chip);
140         if (ret < 0)
141                 return ret;
142
143         /* Transmit the read command. */
144         ret = mdiobus_write_nested(chip->bus, chip->sw_addr, SMI_CMD,
145                                    SMI_CMD_OP_22_READ | (addr << 5) | reg);
146         if (ret < 0)
147                 return ret;
148
149         /* Wait for the read command to complete. */
150         ret = mv88e6xxx_smi_multi_chip_wait(chip);
151         if (ret < 0)
152                 return ret;
153
154         /* Read the data. */
155         ret = mdiobus_read_nested(chip->bus, chip->sw_addr, SMI_DATA);
156         if (ret < 0)
157                 return ret;
158
159         *val = ret & 0xffff;
160
161         return 0;
162 }
163
164 static int mv88e6xxx_smi_multi_chip_write(struct mv88e6xxx_chip *chip,
165                                           int addr, int reg, u16 val)
166 {
167         int ret;
168
169         /* Wait for the bus to become free. */
170         ret = mv88e6xxx_smi_multi_chip_wait(chip);
171         if (ret < 0)
172                 return ret;
173
174         /* Transmit the data to write. */
175         ret = mdiobus_write_nested(chip->bus, chip->sw_addr, SMI_DATA, val);
176         if (ret < 0)
177                 return ret;
178
179         /* Transmit the write command. */
180         ret = mdiobus_write_nested(chip->bus, chip->sw_addr, SMI_CMD,
181                                    SMI_CMD_OP_22_WRITE | (addr << 5) | reg);
182         if (ret < 0)
183                 return ret;
184
185         /* Wait for the write command to complete. */
186         ret = mv88e6xxx_smi_multi_chip_wait(chip);
187         if (ret < 0)
188                 return ret;
189
190         return 0;
191 }
192
193 static const struct mv88e6xxx_bus_ops mv88e6xxx_smi_multi_chip_ops = {
194         .read = mv88e6xxx_smi_multi_chip_read,
195         .write = mv88e6xxx_smi_multi_chip_write,
196 };
197
198 int mv88e6xxx_read(struct mv88e6xxx_chip *chip, int addr, int reg, u16 *val)
199 {
200         int err;
201
202         assert_reg_lock(chip);
203
204         err = mv88e6xxx_smi_read(chip, addr, reg, val);
205         if (err)
206                 return err;
207
208         dev_dbg(chip->dev, "<- addr: 0x%.2x reg: 0x%.2x val: 0x%.4x\n",
209                 addr, reg, *val);
210
211         return 0;
212 }
213
214 int mv88e6xxx_write(struct mv88e6xxx_chip *chip, int addr, int reg, u16 val)
215 {
216         int err;
217
218         assert_reg_lock(chip);
219
220         err = mv88e6xxx_smi_write(chip, addr, reg, val);
221         if (err)
222                 return err;
223
224         dev_dbg(chip->dev, "-> addr: 0x%.2x reg: 0x%.2x val: 0x%.4x\n",
225                 addr, reg, val);
226
227         return 0;
228 }
229
230 struct mii_bus *mv88e6xxx_default_mdio_bus(struct mv88e6xxx_chip *chip)
231 {
232         struct mv88e6xxx_mdio_bus *mdio_bus;
233
234         mdio_bus = list_first_entry(&chip->mdios, struct mv88e6xxx_mdio_bus,
235                                     list);
236         if (!mdio_bus)
237                 return NULL;
238
239         return mdio_bus->bus;
240 }
241
242 static void mv88e6xxx_g1_irq_mask(struct irq_data *d)
243 {
244         struct mv88e6xxx_chip *chip = irq_data_get_irq_chip_data(d);
245         unsigned int n = d->hwirq;
246
247         chip->g1_irq.masked |= (1 << n);
248 }
249
250 static void mv88e6xxx_g1_irq_unmask(struct irq_data *d)
251 {
252         struct mv88e6xxx_chip *chip = irq_data_get_irq_chip_data(d);
253         unsigned int n = d->hwirq;
254
255         chip->g1_irq.masked &= ~(1 << n);
256 }
257
258 static irqreturn_t mv88e6xxx_g1_irq_thread_work(struct mv88e6xxx_chip *chip)
259 {
260         unsigned int nhandled = 0;
261         unsigned int sub_irq;
262         unsigned int n;
263         u16 reg;
264         int err;
265
266         mutex_lock(&chip->reg_lock);
267         err = mv88e6xxx_g1_read(chip, MV88E6XXX_G1_STS, &reg);
268         mutex_unlock(&chip->reg_lock);
269
270         if (err)
271                 goto out;
272
273         for (n = 0; n < chip->g1_irq.nirqs; ++n) {
274                 if (reg & (1 << n)) {
275                         sub_irq = irq_find_mapping(chip->g1_irq.domain, n);
276                         handle_nested_irq(sub_irq);
277                         ++nhandled;
278                 }
279         }
280 out:
281         return (nhandled > 0 ? IRQ_HANDLED : IRQ_NONE);
282 }
283
284 static irqreturn_t mv88e6xxx_g1_irq_thread_fn(int irq, void *dev_id)
285 {
286         struct mv88e6xxx_chip *chip = dev_id;
287
288         return mv88e6xxx_g1_irq_thread_work(chip);
289 }
290
291 static void mv88e6xxx_g1_irq_bus_lock(struct irq_data *d)
292 {
293         struct mv88e6xxx_chip *chip = irq_data_get_irq_chip_data(d);
294
295         mutex_lock(&chip->reg_lock);
296 }
297
298 static void mv88e6xxx_g1_irq_bus_sync_unlock(struct irq_data *d)
299 {
300         struct mv88e6xxx_chip *chip = irq_data_get_irq_chip_data(d);
301         u16 mask = GENMASK(chip->g1_irq.nirqs, 0);
302         u16 reg;
303         int err;
304
305         err = mv88e6xxx_g1_read(chip, MV88E6XXX_G1_CTL1, &reg);
306         if (err)
307                 goto out;
308
309         reg &= ~mask;
310         reg |= (~chip->g1_irq.masked & mask);
311
312         err = mv88e6xxx_g1_write(chip, MV88E6XXX_G1_CTL1, reg);
313         if (err)
314                 goto out;
315
316 out:
317         mutex_unlock(&chip->reg_lock);
318 }
319
320 static const struct irq_chip mv88e6xxx_g1_irq_chip = {
321         .name                   = "mv88e6xxx-g1",
322         .irq_mask               = mv88e6xxx_g1_irq_mask,
323         .irq_unmask             = mv88e6xxx_g1_irq_unmask,
324         .irq_bus_lock           = mv88e6xxx_g1_irq_bus_lock,
325         .irq_bus_sync_unlock    = mv88e6xxx_g1_irq_bus_sync_unlock,
326 };
327
328 static int mv88e6xxx_g1_irq_domain_map(struct irq_domain *d,
329                                        unsigned int irq,
330                                        irq_hw_number_t hwirq)
331 {
332         struct mv88e6xxx_chip *chip = d->host_data;
333
334         irq_set_chip_data(irq, d->host_data);
335         irq_set_chip_and_handler(irq, &chip->g1_irq.chip, handle_level_irq);
336         irq_set_noprobe(irq);
337
338         return 0;
339 }
340
341 static const struct irq_domain_ops mv88e6xxx_g1_irq_domain_ops = {
342         .map    = mv88e6xxx_g1_irq_domain_map,
343         .xlate  = irq_domain_xlate_twocell,
344 };
345
346 /* To be called with reg_lock held */
347 static void mv88e6xxx_g1_irq_free_common(struct mv88e6xxx_chip *chip)
348 {
349         int irq, virq;
350         u16 mask;
351
352         mv88e6xxx_g1_read(chip, MV88E6XXX_G1_CTL1, &mask);
353         mask &= ~GENMASK(chip->g1_irq.nirqs, 0);
354         mv88e6xxx_g1_write(chip, MV88E6XXX_G1_CTL1, mask);
355
356         for (irq = 0; irq < chip->g1_irq.nirqs; irq++) {
357                 virq = irq_find_mapping(chip->g1_irq.domain, irq);
358                 irq_dispose_mapping(virq);
359         }
360
361         irq_domain_remove(chip->g1_irq.domain);
362 }
363
364 static void mv88e6xxx_g1_irq_free(struct mv88e6xxx_chip *chip)
365 {
366         /*
367          * free_irq must be called without reg_lock taken because the irq
368          * handler takes this lock, too.
369          */
370         free_irq(chip->irq, chip);
371
372         mutex_lock(&chip->reg_lock);
373         mv88e6xxx_g1_irq_free_common(chip);
374         mutex_unlock(&chip->reg_lock);
375 }
376
377 static int mv88e6xxx_g1_irq_setup_common(struct mv88e6xxx_chip *chip)
378 {
379         int err, irq, virq;
380         u16 reg, mask;
381
382         chip->g1_irq.nirqs = chip->info->g1_irqs;
383         chip->g1_irq.domain = irq_domain_add_simple(
384                 NULL, chip->g1_irq.nirqs, 0,
385                 &mv88e6xxx_g1_irq_domain_ops, chip);
386         if (!chip->g1_irq.domain)
387                 return -ENOMEM;
388
389         for (irq = 0; irq < chip->g1_irq.nirqs; irq++)
390                 irq_create_mapping(chip->g1_irq.domain, irq);
391
392         chip->g1_irq.chip = mv88e6xxx_g1_irq_chip;
393         chip->g1_irq.masked = ~0;
394
395         err = mv88e6xxx_g1_read(chip, MV88E6XXX_G1_CTL1, &mask);
396         if (err)
397                 goto out_mapping;
398
399         mask &= ~GENMASK(chip->g1_irq.nirqs, 0);
400
401         err = mv88e6xxx_g1_write(chip, MV88E6XXX_G1_CTL1, mask);
402         if (err)
403                 goto out_disable;
404
405         /* Reading the interrupt status clears (most of) them */
406         err = mv88e6xxx_g1_read(chip, MV88E6XXX_G1_STS, &reg);
407         if (err)
408                 goto out_disable;
409
410         return 0;
411
412 out_disable:
413         mask &= ~GENMASK(chip->g1_irq.nirqs, 0);
414         mv88e6xxx_g1_write(chip, MV88E6XXX_G1_CTL1, mask);
415
416 out_mapping:
417         for (irq = 0; irq < 16; irq++) {
418                 virq = irq_find_mapping(chip->g1_irq.domain, irq);
419                 irq_dispose_mapping(virq);
420         }
421
422         irq_domain_remove(chip->g1_irq.domain);
423
424         return err;
425 }
426
427 static int mv88e6xxx_g1_irq_setup(struct mv88e6xxx_chip *chip)
428 {
429         int err;
430
431         err = mv88e6xxx_g1_irq_setup_common(chip);
432         if (err)
433                 return err;
434
435         err = request_threaded_irq(chip->irq, NULL,
436                                    mv88e6xxx_g1_irq_thread_fn,
437                                    IRQF_ONESHOT,
438                                    dev_name(chip->dev), chip);
439         if (err)
440                 mv88e6xxx_g1_irq_free_common(chip);
441
442         return err;
443 }
444
445 static void mv88e6xxx_irq_poll(struct kthread_work *work)
446 {
447         struct mv88e6xxx_chip *chip = container_of(work,
448                                                    struct mv88e6xxx_chip,
449                                                    irq_poll_work.work);
450         mv88e6xxx_g1_irq_thread_work(chip);
451
452         kthread_queue_delayed_work(chip->kworker, &chip->irq_poll_work,
453                                    msecs_to_jiffies(100));
454 }
455
456 static int mv88e6xxx_irq_poll_setup(struct mv88e6xxx_chip *chip)
457 {
458         int err;
459
460         err = mv88e6xxx_g1_irq_setup_common(chip);
461         if (err)
462                 return err;
463
464         kthread_init_delayed_work(&chip->irq_poll_work,
465                                   mv88e6xxx_irq_poll);
466
467         chip->kworker = kthread_create_worker(0, dev_name(chip->dev));
468         if (IS_ERR(chip->kworker))
469                 return PTR_ERR(chip->kworker);
470
471         kthread_queue_delayed_work(chip->kworker, &chip->irq_poll_work,
472                                    msecs_to_jiffies(100));
473
474         return 0;
475 }
476
477 static void mv88e6xxx_irq_poll_free(struct mv88e6xxx_chip *chip)
478 {
479         kthread_cancel_delayed_work_sync(&chip->irq_poll_work);
480         kthread_destroy_worker(chip->kworker);
481
482         mutex_lock(&chip->reg_lock);
483         mv88e6xxx_g1_irq_free_common(chip);
484         mutex_unlock(&chip->reg_lock);
485 }
486
487 int mv88e6xxx_wait(struct mv88e6xxx_chip *chip, int addr, int reg, u16 mask)
488 {
489         int i;
490
491         for (i = 0; i < 16; i++) {
492                 u16 val;
493                 int err;
494
495                 err = mv88e6xxx_read(chip, addr, reg, &val);
496                 if (err)
497                         return err;
498
499                 if (!(val & mask))
500                         return 0;
501
502                 usleep_range(1000, 2000);
503         }
504
505         dev_err(chip->dev, "Timeout while waiting for switch\n");
506         return -ETIMEDOUT;
507 }
508
509 /* Indirect write to single pointer-data register with an Update bit */
510 int mv88e6xxx_update(struct mv88e6xxx_chip *chip, int addr, int reg, u16 update)
511 {
512         u16 val;
513         int err;
514
515         /* Wait until the previous operation is completed */
516         err = mv88e6xxx_wait(chip, addr, reg, BIT(15));
517         if (err)
518                 return err;
519
520         /* Set the Update bit to trigger a write operation */
521         val = BIT(15) | update;
522
523         return mv88e6xxx_write(chip, addr, reg, val);
524 }
525
526 static int mv88e6xxx_port_setup_mac(struct mv88e6xxx_chip *chip, int port,
527                                     int link, int speed, int duplex, int pause,
528                                     phy_interface_t mode)
529 {
530         int err;
531
532         if (!chip->info->ops->port_set_link)
533                 return 0;
534
535         /* Port's MAC control must not be changed unless the link is down */
536         err = chip->info->ops->port_set_link(chip, port, 0);
537         if (err)
538                 return err;
539
540         if (chip->info->ops->port_set_speed) {
541                 err = chip->info->ops->port_set_speed(chip, port, speed);
542                 if (err && err != -EOPNOTSUPP)
543                         goto restore_link;
544         }
545
546         if (chip->info->ops->port_set_pause) {
547                 err = chip->info->ops->port_set_pause(chip, port, pause);
548                 if (err)
549                         goto restore_link;
550         }
551
552         if (chip->info->ops->port_set_duplex) {
553                 err = chip->info->ops->port_set_duplex(chip, port, duplex);
554                 if (err && err != -EOPNOTSUPP)
555                         goto restore_link;
556         }
557
558         if (chip->info->ops->port_set_rgmii_delay) {
559                 err = chip->info->ops->port_set_rgmii_delay(chip, port, mode);
560                 if (err && err != -EOPNOTSUPP)
561                         goto restore_link;
562         }
563
564         if (chip->info->ops->port_set_cmode) {
565                 err = chip->info->ops->port_set_cmode(chip, port, mode);
566                 if (err && err != -EOPNOTSUPP)
567                         goto restore_link;
568         }
569
570         err = 0;
571 restore_link:
572         if (chip->info->ops->port_set_link(chip, port, link))
573                 dev_err(chip->dev, "p%d: failed to restore MAC's link\n", port);
574
575         return err;
576 }
577
578 /* We expect the switch to perform auto negotiation if there is a real
579  * phy. However, in the case of a fixed link phy, we force the port
580  * settings from the fixed link settings.
581  */
582 static void mv88e6xxx_adjust_link(struct dsa_switch *ds, int port,
583                                   struct phy_device *phydev)
584 {
585         struct mv88e6xxx_chip *chip = ds->priv;
586         int err;
587
588         if (!phy_is_pseudo_fixed_link(phydev))
589                 return;
590
591         mutex_lock(&chip->reg_lock);
592         err = mv88e6xxx_port_setup_mac(chip, port, phydev->link, phydev->speed,
593                                        phydev->duplex, phydev->pause,
594                                        phydev->interface);
595         mutex_unlock(&chip->reg_lock);
596
597         if (err && err != -EOPNOTSUPP)
598                 dev_err(ds->dev, "p%d: failed to configure MAC\n", port);
599 }
600
601 static void mv88e6065_phylink_validate(struct mv88e6xxx_chip *chip, int port,
602                                        unsigned long *mask,
603                                        struct phylink_link_state *state)
604 {
605         if (!phy_interface_mode_is_8023z(state->interface)) {
606                 /* 10M and 100M are only supported in non-802.3z mode */
607                 phylink_set(mask, 10baseT_Half);
608                 phylink_set(mask, 10baseT_Full);
609                 phylink_set(mask, 100baseT_Half);
610                 phylink_set(mask, 100baseT_Full);
611         }
612 }
613
614 static void mv88e6185_phylink_validate(struct mv88e6xxx_chip *chip, int port,
615                                        unsigned long *mask,
616                                        struct phylink_link_state *state)
617 {
618         /* FIXME: if the port is in 1000Base-X mode, then it only supports
619          * 1000M FD speeds.  In this case, CMODE will indicate 5.
620          */
621         phylink_set(mask, 1000baseT_Full);
622         phylink_set(mask, 1000baseX_Full);
623
624         mv88e6065_phylink_validate(chip, port, mask, state);
625 }
626
627 static void mv88e6352_phylink_validate(struct mv88e6xxx_chip *chip, int port,
628                                        unsigned long *mask,
629                                        struct phylink_link_state *state)
630 {
631         /* No ethtool bits for 200Mbps */
632         phylink_set(mask, 1000baseT_Full);
633         phylink_set(mask, 1000baseX_Full);
634
635         mv88e6065_phylink_validate(chip, port, mask, state);
636 }
637
638 static void mv88e6390_phylink_validate(struct mv88e6xxx_chip *chip, int port,
639                                        unsigned long *mask,
640                                        struct phylink_link_state *state)
641 {
642         if (port >= 9)
643                 phylink_set(mask, 2500baseX_Full);
644
645         /* No ethtool bits for 200Mbps */
646         phylink_set(mask, 1000baseT_Full);
647         phylink_set(mask, 1000baseX_Full);
648
649         mv88e6065_phylink_validate(chip, port, mask, state);
650 }
651
652 static void mv88e6390x_phylink_validate(struct mv88e6xxx_chip *chip, int port,
653                                         unsigned long *mask,
654                                         struct phylink_link_state *state)
655 {
656         if (port >= 9) {
657                 phylink_set(mask, 10000baseT_Full);
658                 phylink_set(mask, 10000baseKR_Full);
659         }
660
661         mv88e6390_phylink_validate(chip, port, mask, state);
662 }
663
664 static void mv88e6xxx_validate(struct dsa_switch *ds, int port,
665                                unsigned long *supported,
666                                struct phylink_link_state *state)
667 {
668         __ETHTOOL_DECLARE_LINK_MODE_MASK(mask) = { 0, };
669         struct mv88e6xxx_chip *chip = ds->priv;
670
671         /* Allow all the expected bits */
672         phylink_set(mask, Autoneg);
673         phylink_set(mask, Pause);
674         phylink_set_port_modes(mask);
675
676         if (chip->info->ops->phylink_validate)
677                 chip->info->ops->phylink_validate(chip, port, mask, state);
678
679         bitmap_and(supported, supported, mask, __ETHTOOL_LINK_MODE_MASK_NBITS);
680         bitmap_and(state->advertising, state->advertising, mask,
681                    __ETHTOOL_LINK_MODE_MASK_NBITS);
682
683         /* We can only operate at 2500BaseX or 1000BaseX.  If requested
684          * to advertise both, only report advertising at 2500BaseX.
685          */
686         phylink_helper_basex_speed(state);
687 }
688
689 static int mv88e6xxx_link_state(struct dsa_switch *ds, int port,
690                                 struct phylink_link_state *state)
691 {
692         struct mv88e6xxx_chip *chip = ds->priv;
693         int err;
694
695         mutex_lock(&chip->reg_lock);
696         if (chip->info->ops->port_link_state)
697                 err = chip->info->ops->port_link_state(chip, port, state);
698         else
699                 err = -EOPNOTSUPP;
700         mutex_unlock(&chip->reg_lock);
701
702         return err;
703 }
704
705 static void mv88e6xxx_mac_config(struct dsa_switch *ds, int port,
706                                  unsigned int mode,
707                                  const struct phylink_link_state *state)
708 {
709         struct mv88e6xxx_chip *chip = ds->priv;
710         int speed, duplex, link, pause, err;
711
712         if (mode == MLO_AN_PHY)
713                 return;
714
715         if (mode == MLO_AN_FIXED) {
716                 link = LINK_FORCED_UP;
717                 speed = state->speed;
718                 duplex = state->duplex;
719         } else {
720                 speed = SPEED_UNFORCED;
721                 duplex = DUPLEX_UNFORCED;
722                 link = LINK_UNFORCED;
723         }
724         pause = !!phylink_test(state->advertising, Pause);
725
726         mutex_lock(&chip->reg_lock);
727         err = mv88e6xxx_port_setup_mac(chip, port, link, speed, duplex, pause,
728                                        state->interface);
729         mutex_unlock(&chip->reg_lock);
730
731         if (err && err != -EOPNOTSUPP)
732                 dev_err(ds->dev, "p%d: failed to configure MAC\n", port);
733 }
734
735 static void mv88e6xxx_mac_link_force(struct dsa_switch *ds, int port, int link)
736 {
737         struct mv88e6xxx_chip *chip = ds->priv;
738         int err;
739
740         mutex_lock(&chip->reg_lock);
741         err = chip->info->ops->port_set_link(chip, port, link);
742         mutex_unlock(&chip->reg_lock);
743
744         if (err)
745                 dev_err(chip->dev, "p%d: failed to force MAC link\n", port);
746 }
747
748 static void mv88e6xxx_mac_link_down(struct dsa_switch *ds, int port,
749                                     unsigned int mode,
750                                     phy_interface_t interface)
751 {
752         if (mode == MLO_AN_FIXED)
753                 mv88e6xxx_mac_link_force(ds, port, LINK_FORCED_DOWN);
754 }
755
756 static void mv88e6xxx_mac_link_up(struct dsa_switch *ds, int port,
757                                   unsigned int mode, phy_interface_t interface,
758                                   struct phy_device *phydev)
759 {
760         if (mode == MLO_AN_FIXED)
761                 mv88e6xxx_mac_link_force(ds, port, LINK_FORCED_UP);
762 }
763
764 static int mv88e6xxx_stats_snapshot(struct mv88e6xxx_chip *chip, int port)
765 {
766         if (!chip->info->ops->stats_snapshot)
767                 return -EOPNOTSUPP;
768
769         return chip->info->ops->stats_snapshot(chip, port);
770 }
771
772 static struct mv88e6xxx_hw_stat mv88e6xxx_hw_stats[] = {
773         { "in_good_octets",             8, 0x00, STATS_TYPE_BANK0, },
774         { "in_bad_octets",              4, 0x02, STATS_TYPE_BANK0, },
775         { "in_unicast",                 4, 0x04, STATS_TYPE_BANK0, },
776         { "in_broadcasts",              4, 0x06, STATS_TYPE_BANK0, },
777         { "in_multicasts",              4, 0x07, STATS_TYPE_BANK0, },
778         { "in_pause",                   4, 0x16, STATS_TYPE_BANK0, },
779         { "in_undersize",               4, 0x18, STATS_TYPE_BANK0, },
780         { "in_fragments",               4, 0x19, STATS_TYPE_BANK0, },
781         { "in_oversize",                4, 0x1a, STATS_TYPE_BANK0, },
782         { "in_jabber",                  4, 0x1b, STATS_TYPE_BANK0, },
783         { "in_rx_error",                4, 0x1c, STATS_TYPE_BANK0, },
784         { "in_fcs_error",               4, 0x1d, STATS_TYPE_BANK0, },
785         { "out_octets",                 8, 0x0e, STATS_TYPE_BANK0, },
786         { "out_unicast",                4, 0x10, STATS_TYPE_BANK0, },
787         { "out_broadcasts",             4, 0x13, STATS_TYPE_BANK0, },
788         { "out_multicasts",             4, 0x12, STATS_TYPE_BANK0, },
789         { "out_pause",                  4, 0x15, STATS_TYPE_BANK0, },
790         { "excessive",                  4, 0x11, STATS_TYPE_BANK0, },
791         { "collisions",                 4, 0x1e, STATS_TYPE_BANK0, },
792         { "deferred",                   4, 0x05, STATS_TYPE_BANK0, },
793         { "single",                     4, 0x14, STATS_TYPE_BANK0, },
794         { "multiple",                   4, 0x17, STATS_TYPE_BANK0, },
795         { "out_fcs_error",              4, 0x03, STATS_TYPE_BANK0, },
796         { "late",                       4, 0x1f, STATS_TYPE_BANK0, },
797         { "hist_64bytes",               4, 0x08, STATS_TYPE_BANK0, },
798         { "hist_65_127bytes",           4, 0x09, STATS_TYPE_BANK0, },
799         { "hist_128_255bytes",          4, 0x0a, STATS_TYPE_BANK0, },
800         { "hist_256_511bytes",          4, 0x0b, STATS_TYPE_BANK0, },
801         { "hist_512_1023bytes",         4, 0x0c, STATS_TYPE_BANK0, },
802         { "hist_1024_max_bytes",        4, 0x0d, STATS_TYPE_BANK0, },
803         { "sw_in_discards",             4, 0x10, STATS_TYPE_PORT, },
804         { "sw_in_filtered",             2, 0x12, STATS_TYPE_PORT, },
805         { "sw_out_filtered",            2, 0x13, STATS_TYPE_PORT, },
806         { "in_discards",                4, 0x00, STATS_TYPE_BANK1, },
807         { "in_filtered",                4, 0x01, STATS_TYPE_BANK1, },
808         { "in_accepted",                4, 0x02, STATS_TYPE_BANK1, },
809         { "in_bad_accepted",            4, 0x03, STATS_TYPE_BANK1, },
810         { "in_good_avb_class_a",        4, 0x04, STATS_TYPE_BANK1, },
811         { "in_good_avb_class_b",        4, 0x05, STATS_TYPE_BANK1, },
812         { "in_bad_avb_class_a",         4, 0x06, STATS_TYPE_BANK1, },
813         { "in_bad_avb_class_b",         4, 0x07, STATS_TYPE_BANK1, },
814         { "tcam_counter_0",             4, 0x08, STATS_TYPE_BANK1, },
815         { "tcam_counter_1",             4, 0x09, STATS_TYPE_BANK1, },
816         { "tcam_counter_2",             4, 0x0a, STATS_TYPE_BANK1, },
817         { "tcam_counter_3",             4, 0x0b, STATS_TYPE_BANK1, },
818         { "in_da_unknown",              4, 0x0e, STATS_TYPE_BANK1, },
819         { "in_management",              4, 0x0f, STATS_TYPE_BANK1, },
820         { "out_queue_0",                4, 0x10, STATS_TYPE_BANK1, },
821         { "out_queue_1",                4, 0x11, STATS_TYPE_BANK1, },
822         { "out_queue_2",                4, 0x12, STATS_TYPE_BANK1, },
823         { "out_queue_3",                4, 0x13, STATS_TYPE_BANK1, },
824         { "out_queue_4",                4, 0x14, STATS_TYPE_BANK1, },
825         { "out_queue_5",                4, 0x15, STATS_TYPE_BANK1, },
826         { "out_queue_6",                4, 0x16, STATS_TYPE_BANK1, },
827         { "out_queue_7",                4, 0x17, STATS_TYPE_BANK1, },
828         { "out_cut_through",            4, 0x18, STATS_TYPE_BANK1, },
829         { "out_octets_a",               4, 0x1a, STATS_TYPE_BANK1, },
830         { "out_octets_b",               4, 0x1b, STATS_TYPE_BANK1, },
831         { "out_management",             4, 0x1f, STATS_TYPE_BANK1, },
832 };
833
834 static uint64_t _mv88e6xxx_get_ethtool_stat(struct mv88e6xxx_chip *chip,
835                                             struct mv88e6xxx_hw_stat *s,
836                                             int port, u16 bank1_select,
837                                             u16 histogram)
838 {
839         u32 low;
840         u32 high = 0;
841         u16 reg = 0;
842         int err;
843         u64 value;
844
845         switch (s->type) {
846         case STATS_TYPE_PORT:
847                 err = mv88e6xxx_port_read(chip, port, s->reg, &reg);
848                 if (err)
849                         return U64_MAX;
850
851                 low = reg;
852                 if (s->size == 4) {
853                         err = mv88e6xxx_port_read(chip, port, s->reg + 1, &reg);
854                         if (err)
855                                 return U64_MAX;
856                         high = reg;
857                 }
858                 break;
859         case STATS_TYPE_BANK1:
860                 reg = bank1_select;
861                 /* fall through */
862         case STATS_TYPE_BANK0:
863                 reg |= s->reg | histogram;
864                 mv88e6xxx_g1_stats_read(chip, reg, &low);
865                 if (s->size == 8)
866                         mv88e6xxx_g1_stats_read(chip, reg + 1, &high);
867                 break;
868         default:
869                 return U64_MAX;
870         }
871         value = (((u64)high) << 16) | low;
872         return value;
873 }
874
875 static int mv88e6xxx_stats_get_strings(struct mv88e6xxx_chip *chip,
876                                        uint8_t *data, int types)
877 {
878         struct mv88e6xxx_hw_stat *stat;
879         int i, j;
880
881         for (i = 0, j = 0; i < ARRAY_SIZE(mv88e6xxx_hw_stats); i++) {
882                 stat = &mv88e6xxx_hw_stats[i];
883                 if (stat->type & types) {
884                         memcpy(data + j * ETH_GSTRING_LEN, stat->string,
885                                ETH_GSTRING_LEN);
886                         j++;
887                 }
888         }
889
890         return j;
891 }
892
893 static int mv88e6095_stats_get_strings(struct mv88e6xxx_chip *chip,
894                                        uint8_t *data)
895 {
896         return mv88e6xxx_stats_get_strings(chip, data,
897                                            STATS_TYPE_BANK0 | STATS_TYPE_PORT);
898 }
899
900 static int mv88e6320_stats_get_strings(struct mv88e6xxx_chip *chip,
901                                        uint8_t *data)
902 {
903         return mv88e6xxx_stats_get_strings(chip, data,
904                                            STATS_TYPE_BANK0 | STATS_TYPE_BANK1);
905 }
906
907 static const uint8_t *mv88e6xxx_atu_vtu_stats_strings[] = {
908         "atu_member_violation",
909         "atu_miss_violation",
910         "atu_full_violation",
911         "vtu_member_violation",
912         "vtu_miss_violation",
913 };
914
915 static void mv88e6xxx_atu_vtu_get_strings(uint8_t *data)
916 {
917         unsigned int i;
918
919         for (i = 0; i < ARRAY_SIZE(mv88e6xxx_atu_vtu_stats_strings); i++)
920                 strlcpy(data + i * ETH_GSTRING_LEN,
921                         mv88e6xxx_atu_vtu_stats_strings[i],
922                         ETH_GSTRING_LEN);
923 }
924
925 static void mv88e6xxx_get_strings(struct dsa_switch *ds, int port,
926                                   u32 stringset, uint8_t *data)
927 {
928         struct mv88e6xxx_chip *chip = ds->priv;
929         int count = 0;
930
931         if (stringset != ETH_SS_STATS)
932                 return;
933
934         mutex_lock(&chip->reg_lock);
935
936         if (chip->info->ops->stats_get_strings)
937                 count = chip->info->ops->stats_get_strings(chip, data);
938
939         if (chip->info->ops->serdes_get_strings) {
940                 data += count * ETH_GSTRING_LEN;
941                 count = chip->info->ops->serdes_get_strings(chip, port, data);
942         }
943
944         data += count * ETH_GSTRING_LEN;
945         mv88e6xxx_atu_vtu_get_strings(data);
946
947         mutex_unlock(&chip->reg_lock);
948 }
949
950 static int mv88e6xxx_stats_get_sset_count(struct mv88e6xxx_chip *chip,
951                                           int types)
952 {
953         struct mv88e6xxx_hw_stat *stat;
954         int i, j;
955
956         for (i = 0, j = 0; i < ARRAY_SIZE(mv88e6xxx_hw_stats); i++) {
957                 stat = &mv88e6xxx_hw_stats[i];
958                 if (stat->type & types)
959                         j++;
960         }
961         return j;
962 }
963
964 static int mv88e6095_stats_get_sset_count(struct mv88e6xxx_chip *chip)
965 {
966         return mv88e6xxx_stats_get_sset_count(chip, STATS_TYPE_BANK0 |
967                                               STATS_TYPE_PORT);
968 }
969
970 static int mv88e6320_stats_get_sset_count(struct mv88e6xxx_chip *chip)
971 {
972         return mv88e6xxx_stats_get_sset_count(chip, STATS_TYPE_BANK0 |
973                                               STATS_TYPE_BANK1);
974 }
975
976 static int mv88e6xxx_get_sset_count(struct dsa_switch *ds, int port, int sset)
977 {
978         struct mv88e6xxx_chip *chip = ds->priv;
979         int serdes_count = 0;
980         int count = 0;
981
982         if (sset != ETH_SS_STATS)
983                 return 0;
984
985         mutex_lock(&chip->reg_lock);
986         if (chip->info->ops->stats_get_sset_count)
987                 count = chip->info->ops->stats_get_sset_count(chip);
988         if (count < 0)
989                 goto out;
990
991         if (chip->info->ops->serdes_get_sset_count)
992                 serdes_count = chip->info->ops->serdes_get_sset_count(chip,
993                                                                       port);
994         if (serdes_count < 0) {
995                 count = serdes_count;
996                 goto out;
997         }
998         count += serdes_count;
999         count += ARRAY_SIZE(mv88e6xxx_atu_vtu_stats_strings);
1000
1001 out:
1002         mutex_unlock(&chip->reg_lock);
1003
1004         return count;
1005 }
1006
1007 static int mv88e6xxx_stats_get_stats(struct mv88e6xxx_chip *chip, int port,
1008                                      uint64_t *data, int types,
1009                                      u16 bank1_select, u16 histogram)
1010 {
1011         struct mv88e6xxx_hw_stat *stat;
1012         int i, j;
1013
1014         for (i = 0, j = 0; i < ARRAY_SIZE(mv88e6xxx_hw_stats); i++) {
1015                 stat = &mv88e6xxx_hw_stats[i];
1016                 if (stat->type & types) {
1017                         mutex_lock(&chip->reg_lock);
1018                         data[j] = _mv88e6xxx_get_ethtool_stat(chip, stat, port,
1019                                                               bank1_select,
1020                                                               histogram);
1021                         mutex_unlock(&chip->reg_lock);
1022
1023                         j++;
1024                 }
1025         }
1026         return j;
1027 }
1028
1029 static int mv88e6095_stats_get_stats(struct mv88e6xxx_chip *chip, int port,
1030                                      uint64_t *data)
1031 {
1032         return mv88e6xxx_stats_get_stats(chip, port, data,
1033                                          STATS_TYPE_BANK0 | STATS_TYPE_PORT,
1034                                          0, MV88E6XXX_G1_STATS_OP_HIST_RX_TX);
1035 }
1036
1037 static int mv88e6320_stats_get_stats(struct mv88e6xxx_chip *chip, int port,
1038                                      uint64_t *data)
1039 {
1040         return mv88e6xxx_stats_get_stats(chip, port, data,
1041                                          STATS_TYPE_BANK0 | STATS_TYPE_BANK1,
1042                                          MV88E6XXX_G1_STATS_OP_BANK_1_BIT_9,
1043                                          MV88E6XXX_G1_STATS_OP_HIST_RX_TX);
1044 }
1045
1046 static int mv88e6390_stats_get_stats(struct mv88e6xxx_chip *chip, int port,
1047                                      uint64_t *data)
1048 {
1049         return mv88e6xxx_stats_get_stats(chip, port, data,
1050                                          STATS_TYPE_BANK0 | STATS_TYPE_BANK1,
1051                                          MV88E6XXX_G1_STATS_OP_BANK_1_BIT_10,
1052                                          0);
1053 }
1054
1055 static void mv88e6xxx_atu_vtu_get_stats(struct mv88e6xxx_chip *chip, int port,
1056                                         uint64_t *data)
1057 {
1058         *data++ = chip->ports[port].atu_member_violation;
1059         *data++ = chip->ports[port].atu_miss_violation;
1060         *data++ = chip->ports[port].atu_full_violation;
1061         *data++ = chip->ports[port].vtu_member_violation;
1062         *data++ = chip->ports[port].vtu_miss_violation;
1063 }
1064
1065 static void mv88e6xxx_get_stats(struct mv88e6xxx_chip *chip, int port,
1066                                 uint64_t *data)
1067 {
1068         int count = 0;
1069
1070         if (chip->info->ops->stats_get_stats)
1071                 count = chip->info->ops->stats_get_stats(chip, port, data);
1072
1073         mutex_lock(&chip->reg_lock);
1074         if (chip->info->ops->serdes_get_stats) {
1075                 data += count;
1076                 count = chip->info->ops->serdes_get_stats(chip, port, data);
1077         }
1078         data += count;
1079         mv88e6xxx_atu_vtu_get_stats(chip, port, data);
1080         mutex_unlock(&chip->reg_lock);
1081 }
1082
1083 static void mv88e6xxx_get_ethtool_stats(struct dsa_switch *ds, int port,
1084                                         uint64_t *data)
1085 {
1086         struct mv88e6xxx_chip *chip = ds->priv;
1087         int ret;
1088
1089         mutex_lock(&chip->reg_lock);
1090
1091         ret = mv88e6xxx_stats_snapshot(chip, port);
1092         mutex_unlock(&chip->reg_lock);
1093
1094         if (ret < 0)
1095                 return;
1096
1097         mv88e6xxx_get_stats(chip, port, data);
1098
1099 }
1100
1101 static int mv88e6xxx_get_regs_len(struct dsa_switch *ds, int port)
1102 {
1103         return 32 * sizeof(u16);
1104 }
1105
1106 static void mv88e6xxx_get_regs(struct dsa_switch *ds, int port,
1107                                struct ethtool_regs *regs, void *_p)
1108 {
1109         struct mv88e6xxx_chip *chip = ds->priv;
1110         int err;
1111         u16 reg;
1112         u16 *p = _p;
1113         int i;
1114
1115         regs->version = 0;
1116
1117         memset(p, 0xff, 32 * sizeof(u16));
1118
1119         mutex_lock(&chip->reg_lock);
1120
1121         for (i = 0; i < 32; i++) {
1122
1123                 err = mv88e6xxx_port_read(chip, port, i, &reg);
1124                 if (!err)
1125                         p[i] = reg;
1126         }
1127
1128         mutex_unlock(&chip->reg_lock);
1129 }
1130
1131 static int mv88e6xxx_get_mac_eee(struct dsa_switch *ds, int port,
1132                                  struct ethtool_eee *e)
1133 {
1134         /* Nothing to do on the port's MAC */
1135         return 0;
1136 }
1137
1138 static int mv88e6xxx_set_mac_eee(struct dsa_switch *ds, int port,
1139                                  struct ethtool_eee *e)
1140 {
1141         /* Nothing to do on the port's MAC */
1142         return 0;
1143 }
1144
1145 static u16 mv88e6xxx_port_vlan(struct mv88e6xxx_chip *chip, int dev, int port)
1146 {
1147         struct dsa_switch *ds = NULL;
1148         struct net_device *br;
1149         u16 pvlan;
1150         int i;
1151
1152         if (dev < DSA_MAX_SWITCHES)
1153                 ds = chip->ds->dst->ds[dev];
1154
1155         /* Prevent frames from unknown switch or port */
1156         if (!ds || port >= ds->num_ports)
1157                 return 0;
1158
1159         /* Frames from DSA links and CPU ports can egress any local port */
1160         if (dsa_is_cpu_port(ds, port) || dsa_is_dsa_port(ds, port))
1161                 return mv88e6xxx_port_mask(chip);
1162
1163         br = ds->ports[port].bridge_dev;
1164         pvlan = 0;
1165
1166         /* Frames from user ports can egress any local DSA links and CPU ports,
1167          * as well as any local member of their bridge group.
1168          */
1169         for (i = 0; i < mv88e6xxx_num_ports(chip); ++i)
1170                 if (dsa_is_cpu_port(chip->ds, i) ||
1171                     dsa_is_dsa_port(chip->ds, i) ||
1172                     (br && dsa_to_port(chip->ds, i)->bridge_dev == br))
1173                         pvlan |= BIT(i);
1174
1175         return pvlan;
1176 }
1177
1178 static int mv88e6xxx_port_vlan_map(struct mv88e6xxx_chip *chip, int port)
1179 {
1180         u16 output_ports = mv88e6xxx_port_vlan(chip, chip->ds->index, port);
1181
1182         /* prevent frames from going back out of the port they came in on */
1183         output_ports &= ~BIT(port);
1184
1185         return mv88e6xxx_port_set_vlan_map(chip, port, output_ports);
1186 }
1187
1188 static void mv88e6xxx_port_stp_state_set(struct dsa_switch *ds, int port,
1189                                          u8 state)
1190 {
1191         struct mv88e6xxx_chip *chip = ds->priv;
1192         int err;
1193
1194         mutex_lock(&chip->reg_lock);
1195         err = mv88e6xxx_port_set_state(chip, port, state);
1196         mutex_unlock(&chip->reg_lock);
1197
1198         if (err)
1199                 dev_err(ds->dev, "p%d: failed to update state\n", port);
1200 }
1201
1202 static int mv88e6xxx_pri_setup(struct mv88e6xxx_chip *chip)
1203 {
1204         int err;
1205
1206         if (chip->info->ops->ieee_pri_map) {
1207                 err = chip->info->ops->ieee_pri_map(chip);
1208                 if (err)
1209                         return err;
1210         }
1211
1212         if (chip->info->ops->ip_pri_map) {
1213                 err = chip->info->ops->ip_pri_map(chip);
1214                 if (err)
1215                         return err;
1216         }
1217
1218         return 0;
1219 }
1220
1221 static int mv88e6xxx_devmap_setup(struct mv88e6xxx_chip *chip)
1222 {
1223         int target, port;
1224         int err;
1225
1226         if (!chip->info->global2_addr)
1227                 return 0;
1228
1229         /* Initialize the routing port to the 32 possible target devices */
1230         for (target = 0; target < 32; target++) {
1231                 port = 0x1f;
1232                 if (target < DSA_MAX_SWITCHES)
1233                         if (chip->ds->rtable[target] != DSA_RTABLE_NONE)
1234                                 port = chip->ds->rtable[target];
1235
1236                 err = mv88e6xxx_g2_device_mapping_write(chip, target, port);
1237                 if (err)
1238                         return err;
1239         }
1240
1241         if (chip->info->ops->set_cascade_port) {
1242                 port = MV88E6XXX_CASCADE_PORT_MULTIPLE;
1243                 err = chip->info->ops->set_cascade_port(chip, port);
1244                 if (err)
1245                         return err;
1246         }
1247
1248         err = mv88e6xxx_g1_set_device_number(chip, chip->ds->index);
1249         if (err)
1250                 return err;
1251
1252         return 0;
1253 }
1254
1255 static int mv88e6xxx_trunk_setup(struct mv88e6xxx_chip *chip)
1256 {
1257         /* Clear all trunk masks and mapping */
1258         if (chip->info->global2_addr)
1259                 return mv88e6xxx_g2_trunk_clear(chip);
1260
1261         return 0;
1262 }
1263
1264 static int mv88e6xxx_rmu_setup(struct mv88e6xxx_chip *chip)
1265 {
1266         if (chip->info->ops->rmu_disable)
1267                 return chip->info->ops->rmu_disable(chip);
1268
1269         return 0;
1270 }
1271
1272 static int mv88e6xxx_pot_setup(struct mv88e6xxx_chip *chip)
1273 {
1274         if (chip->info->ops->pot_clear)
1275                 return chip->info->ops->pot_clear(chip);
1276
1277         return 0;
1278 }
1279
1280 static int mv88e6xxx_rsvd2cpu_setup(struct mv88e6xxx_chip *chip)
1281 {
1282         if (chip->info->ops->mgmt_rsvd2cpu)
1283                 return chip->info->ops->mgmt_rsvd2cpu(chip);
1284
1285         return 0;
1286 }
1287
1288 static int mv88e6xxx_atu_setup(struct mv88e6xxx_chip *chip)
1289 {
1290         int err;
1291
1292         err = mv88e6xxx_g1_atu_flush(chip, 0, true);
1293         if (err)
1294                 return err;
1295
1296         err = mv88e6xxx_g1_atu_set_learn2all(chip, true);
1297         if (err)
1298                 return err;
1299
1300         return mv88e6xxx_g1_atu_set_age_time(chip, 300000);
1301 }
1302
1303 static int mv88e6xxx_irl_setup(struct mv88e6xxx_chip *chip)
1304 {
1305         int port;
1306         int err;
1307
1308         if (!chip->info->ops->irl_init_all)
1309                 return 0;
1310
1311         for (port = 0; port < mv88e6xxx_num_ports(chip); port++) {
1312                 /* Disable ingress rate limiting by resetting all per port
1313                  * ingress rate limit resources to their initial state.
1314                  */
1315                 err = chip->info->ops->irl_init_all(chip, port);
1316                 if (err)
1317                         return err;
1318         }
1319
1320         return 0;
1321 }
1322
1323 static int mv88e6xxx_mac_setup(struct mv88e6xxx_chip *chip)
1324 {
1325         if (chip->info->ops->set_switch_mac) {
1326                 u8 addr[ETH_ALEN];
1327
1328                 eth_random_addr(addr);
1329
1330                 return chip->info->ops->set_switch_mac(chip, addr);
1331         }
1332
1333         return 0;
1334 }
1335
1336 static int mv88e6xxx_pvt_map(struct mv88e6xxx_chip *chip, int dev, int port)
1337 {
1338         u16 pvlan = 0;
1339
1340         if (!mv88e6xxx_has_pvt(chip))
1341                 return -EOPNOTSUPP;
1342
1343         /* Skip the local source device, which uses in-chip port VLAN */
1344         if (dev != chip->ds->index)
1345                 pvlan = mv88e6xxx_port_vlan(chip, dev, port);
1346
1347         return mv88e6xxx_g2_pvt_write(chip, dev, port, pvlan);
1348 }
1349
1350 static int mv88e6xxx_pvt_setup(struct mv88e6xxx_chip *chip)
1351 {
1352         int dev, port;
1353         int err;
1354
1355         if (!mv88e6xxx_has_pvt(chip))
1356                 return 0;
1357
1358         /* Clear 5 Bit Port for usage with Marvell Link Street devices:
1359          * use 4 bits for the Src_Port/Src_Trunk and 5 bits for the Src_Dev.
1360          */
1361         err = mv88e6xxx_g2_misc_4_bit_port(chip);
1362         if (err)
1363                 return err;
1364
1365         for (dev = 0; dev < MV88E6XXX_MAX_PVT_SWITCHES; ++dev) {
1366                 for (port = 0; port < MV88E6XXX_MAX_PVT_PORTS; ++port) {
1367                         err = mv88e6xxx_pvt_map(chip, dev, port);
1368                         if (err)
1369                                 return err;
1370                 }
1371         }
1372
1373         return 0;
1374 }
1375
1376 static void mv88e6xxx_port_fast_age(struct dsa_switch *ds, int port)
1377 {
1378         struct mv88e6xxx_chip *chip = ds->priv;
1379         int err;
1380
1381         mutex_lock(&chip->reg_lock);
1382         err = mv88e6xxx_g1_atu_remove(chip, 0, port, false);
1383         mutex_unlock(&chip->reg_lock);
1384
1385         if (err)
1386                 dev_err(ds->dev, "p%d: failed to flush ATU\n", port);
1387 }
1388
1389 static int mv88e6xxx_vtu_setup(struct mv88e6xxx_chip *chip)
1390 {
1391         if (!chip->info->max_vid)
1392                 return 0;
1393
1394         return mv88e6xxx_g1_vtu_flush(chip);
1395 }
1396
1397 static int mv88e6xxx_vtu_getnext(struct mv88e6xxx_chip *chip,
1398                                  struct mv88e6xxx_vtu_entry *entry)
1399 {
1400         if (!chip->info->ops->vtu_getnext)
1401                 return -EOPNOTSUPP;
1402
1403         return chip->info->ops->vtu_getnext(chip, entry);
1404 }
1405
1406 static int mv88e6xxx_vtu_loadpurge(struct mv88e6xxx_chip *chip,
1407                                    struct mv88e6xxx_vtu_entry *entry)
1408 {
1409         if (!chip->info->ops->vtu_loadpurge)
1410                 return -EOPNOTSUPP;
1411
1412         return chip->info->ops->vtu_loadpurge(chip, entry);
1413 }
1414
1415 static int mv88e6xxx_atu_new(struct mv88e6xxx_chip *chip, u16 *fid)
1416 {
1417         DECLARE_BITMAP(fid_bitmap, MV88E6XXX_N_FID);
1418         struct mv88e6xxx_vtu_entry vlan = {
1419                 .vid = chip->info->max_vid,
1420         };
1421         int i, err;
1422
1423         bitmap_zero(fid_bitmap, MV88E6XXX_N_FID);
1424
1425         /* Set every FID bit used by the (un)bridged ports */
1426         for (i = 0; i < mv88e6xxx_num_ports(chip); ++i) {
1427                 err = mv88e6xxx_port_get_fid(chip, i, fid);
1428                 if (err)
1429                         return err;
1430
1431                 set_bit(*fid, fid_bitmap);
1432         }
1433
1434         /* Set every FID bit used by the VLAN entries */
1435         do {
1436                 err = mv88e6xxx_vtu_getnext(chip, &vlan);
1437                 if (err)
1438                         return err;
1439
1440                 if (!vlan.valid)
1441                         break;
1442
1443                 set_bit(vlan.fid, fid_bitmap);
1444         } while (vlan.vid < chip->info->max_vid);
1445
1446         /* The reset value 0x000 is used to indicate that multiple address
1447          * databases are not needed. Return the next positive available.
1448          */
1449         *fid = find_next_zero_bit(fid_bitmap, MV88E6XXX_N_FID, 1);
1450         if (unlikely(*fid >= mv88e6xxx_num_databases(chip)))
1451                 return -ENOSPC;
1452
1453         /* Clear the database */
1454         return mv88e6xxx_g1_atu_flush(chip, *fid, true);
1455 }
1456
1457 static int mv88e6xxx_vtu_get(struct mv88e6xxx_chip *chip, u16 vid,
1458                              struct mv88e6xxx_vtu_entry *entry, bool new)
1459 {
1460         int err;
1461
1462         if (!vid)
1463                 return -EINVAL;
1464
1465         entry->vid = vid - 1;
1466         entry->valid = false;
1467
1468         err = mv88e6xxx_vtu_getnext(chip, entry);
1469         if (err)
1470                 return err;
1471
1472         if (entry->vid == vid && entry->valid)
1473                 return 0;
1474
1475         if (new) {
1476                 int i;
1477
1478                 /* Initialize a fresh VLAN entry */
1479                 memset(entry, 0, sizeof(*entry));
1480                 entry->valid = true;
1481                 entry->vid = vid;
1482
1483                 /* Exclude all ports */
1484                 for (i = 0; i < mv88e6xxx_num_ports(chip); ++i)
1485                         entry->member[i] =
1486                                 MV88E6XXX_G1_VTU_DATA_MEMBER_TAG_NON_MEMBER;
1487
1488                 return mv88e6xxx_atu_new(chip, &entry->fid);
1489         }
1490
1491         /* switchdev expects -EOPNOTSUPP to honor software VLANs */
1492         return -EOPNOTSUPP;
1493 }
1494
1495 static int mv88e6xxx_port_check_hw_vlan(struct dsa_switch *ds, int port,
1496                                         u16 vid_begin, u16 vid_end)
1497 {
1498         struct mv88e6xxx_chip *chip = ds->priv;
1499         struct mv88e6xxx_vtu_entry vlan = {
1500                 .vid = vid_begin - 1,
1501         };
1502         int i, err;
1503
1504         /* DSA and CPU ports have to be members of multiple vlans */
1505         if (dsa_is_dsa_port(ds, port) || dsa_is_cpu_port(ds, port))
1506                 return 0;
1507
1508         if (!vid_begin)
1509                 return -EOPNOTSUPP;
1510
1511         mutex_lock(&chip->reg_lock);
1512
1513         do {
1514                 err = mv88e6xxx_vtu_getnext(chip, &vlan);
1515                 if (err)
1516                         goto unlock;
1517
1518                 if (!vlan.valid)
1519                         break;
1520
1521                 if (vlan.vid > vid_end)
1522                         break;
1523
1524                 for (i = 0; i < mv88e6xxx_num_ports(chip); ++i) {
1525                         if (dsa_is_dsa_port(ds, i) || dsa_is_cpu_port(ds, i))
1526                                 continue;
1527
1528                         if (!ds->ports[i].slave)
1529                                 continue;
1530
1531                         if (vlan.member[i] ==
1532                             MV88E6XXX_G1_VTU_DATA_MEMBER_TAG_NON_MEMBER)
1533                                 continue;
1534
1535                         if (dsa_to_port(ds, i)->bridge_dev ==
1536                             ds->ports[port].bridge_dev)
1537                                 break; /* same bridge, check next VLAN */
1538
1539                         if (!dsa_to_port(ds, i)->bridge_dev)
1540                                 continue;
1541
1542                         dev_err(ds->dev, "p%d: hw VLAN %d already used by port %d in %s\n",
1543                                 port, vlan.vid, i,
1544                                 netdev_name(dsa_to_port(ds, i)->bridge_dev));
1545                         err = -EOPNOTSUPP;
1546                         goto unlock;
1547                 }
1548         } while (vlan.vid < vid_end);
1549
1550 unlock:
1551         mutex_unlock(&chip->reg_lock);
1552
1553         return err;
1554 }
1555
1556 static int mv88e6xxx_port_vlan_filtering(struct dsa_switch *ds, int port,
1557                                          bool vlan_filtering)
1558 {
1559         struct mv88e6xxx_chip *chip = ds->priv;
1560         u16 mode = vlan_filtering ? MV88E6XXX_PORT_CTL2_8021Q_MODE_SECURE :
1561                 MV88E6XXX_PORT_CTL2_8021Q_MODE_DISABLED;
1562         int err;
1563
1564         if (!chip->info->max_vid)
1565                 return -EOPNOTSUPP;
1566
1567         mutex_lock(&chip->reg_lock);
1568         err = mv88e6xxx_port_set_8021q_mode(chip, port, mode);
1569         mutex_unlock(&chip->reg_lock);
1570
1571         return err;
1572 }
1573
1574 static int
1575 mv88e6xxx_port_vlan_prepare(struct dsa_switch *ds, int port,
1576                             const struct switchdev_obj_port_vlan *vlan)
1577 {
1578         struct mv88e6xxx_chip *chip = ds->priv;
1579         int err;
1580
1581         if (!chip->info->max_vid)
1582                 return -EOPNOTSUPP;
1583
1584         /* If the requested port doesn't belong to the same bridge as the VLAN
1585          * members, do not support it (yet) and fallback to software VLAN.
1586          */
1587         err = mv88e6xxx_port_check_hw_vlan(ds, port, vlan->vid_begin,
1588                                            vlan->vid_end);
1589         if (err)
1590                 return err;
1591
1592         /* We don't need any dynamic resource from the kernel (yet),
1593          * so skip the prepare phase.
1594          */
1595         return 0;
1596 }
1597
1598 static int mv88e6xxx_port_db_load_purge(struct mv88e6xxx_chip *chip, int port,
1599                                         const unsigned char *addr, u16 vid,
1600                                         u8 state)
1601 {
1602         struct mv88e6xxx_vtu_entry vlan;
1603         struct mv88e6xxx_atu_entry entry;
1604         int err;
1605
1606         /* Null VLAN ID corresponds to the port private database */
1607         if (vid == 0)
1608                 err = mv88e6xxx_port_get_fid(chip, port, &vlan.fid);
1609         else
1610                 err = mv88e6xxx_vtu_get(chip, vid, &vlan, false);
1611         if (err)
1612                 return err;
1613
1614         entry.state = MV88E6XXX_G1_ATU_DATA_STATE_UNUSED;
1615         ether_addr_copy(entry.mac, addr);
1616         eth_addr_dec(entry.mac);
1617
1618         err = mv88e6xxx_g1_atu_getnext(chip, vlan.fid, &entry);
1619         if (err)
1620                 return err;
1621
1622         /* Initialize a fresh ATU entry if it isn't found */
1623         if (entry.state == MV88E6XXX_G1_ATU_DATA_STATE_UNUSED ||
1624             !ether_addr_equal(entry.mac, addr)) {
1625                 memset(&entry, 0, sizeof(entry));
1626                 ether_addr_copy(entry.mac, addr);
1627         }
1628
1629         /* Purge the ATU entry only if no port is using it anymore */
1630         if (state == MV88E6XXX_G1_ATU_DATA_STATE_UNUSED) {
1631                 entry.portvec &= ~BIT(port);
1632                 if (!entry.portvec)
1633                         entry.state = MV88E6XXX_G1_ATU_DATA_STATE_UNUSED;
1634         } else {
1635                 entry.portvec |= BIT(port);
1636                 entry.state = state;
1637         }
1638
1639         return mv88e6xxx_g1_atu_loadpurge(chip, vlan.fid, &entry);
1640 }
1641
1642 static int mv88e6xxx_port_add_broadcast(struct mv88e6xxx_chip *chip, int port,
1643                                         u16 vid)
1644 {
1645         const char broadcast[6] = { 0xff, 0xff, 0xff, 0xff, 0xff, 0xff };
1646         u8 state = MV88E6XXX_G1_ATU_DATA_STATE_MC_STATIC;
1647
1648         return mv88e6xxx_port_db_load_purge(chip, port, broadcast, vid, state);
1649 }
1650
1651 static int mv88e6xxx_broadcast_setup(struct mv88e6xxx_chip *chip, u16 vid)
1652 {
1653         int port;
1654         int err;
1655
1656         for (port = 0; port < mv88e6xxx_num_ports(chip); port++) {
1657                 err = mv88e6xxx_port_add_broadcast(chip, port, vid);
1658                 if (err)
1659                         return err;
1660         }
1661
1662         return 0;
1663 }
1664
1665 static int _mv88e6xxx_port_vlan_add(struct mv88e6xxx_chip *chip, int port,
1666                                     u16 vid, u8 member)
1667 {
1668         struct mv88e6xxx_vtu_entry vlan;
1669         int err;
1670
1671         err = mv88e6xxx_vtu_get(chip, vid, &vlan, true);
1672         if (err)
1673                 return err;
1674
1675         vlan.member[port] = member;
1676
1677         err = mv88e6xxx_vtu_loadpurge(chip, &vlan);
1678         if (err)
1679                 return err;
1680
1681         return mv88e6xxx_broadcast_setup(chip, vid);
1682 }
1683
1684 static void mv88e6xxx_port_vlan_add(struct dsa_switch *ds, int port,
1685                                     const struct switchdev_obj_port_vlan *vlan)
1686 {
1687         struct mv88e6xxx_chip *chip = ds->priv;
1688         bool untagged = vlan->flags & BRIDGE_VLAN_INFO_UNTAGGED;
1689         bool pvid = vlan->flags & BRIDGE_VLAN_INFO_PVID;
1690         u8 member;
1691         u16 vid;
1692
1693         if (!chip->info->max_vid)
1694                 return;
1695
1696         if (dsa_is_dsa_port(ds, port) || dsa_is_cpu_port(ds, port))
1697                 member = MV88E6XXX_G1_VTU_DATA_MEMBER_TAG_UNMODIFIED;
1698         else if (untagged)
1699                 member = MV88E6XXX_G1_VTU_DATA_MEMBER_TAG_UNTAGGED;
1700         else
1701                 member = MV88E6XXX_G1_VTU_DATA_MEMBER_TAG_TAGGED;
1702
1703         mutex_lock(&chip->reg_lock);
1704
1705         for (vid = vlan->vid_begin; vid <= vlan->vid_end; ++vid)
1706                 if (_mv88e6xxx_port_vlan_add(chip, port, vid, member))
1707                         dev_err(ds->dev, "p%d: failed to add VLAN %d%c\n", port,
1708                                 vid, untagged ? 'u' : 't');
1709
1710         if (pvid && mv88e6xxx_port_set_pvid(chip, port, vlan->vid_end))
1711                 dev_err(ds->dev, "p%d: failed to set PVID %d\n", port,
1712                         vlan->vid_end);
1713
1714         mutex_unlock(&chip->reg_lock);
1715 }
1716
1717 static int _mv88e6xxx_port_vlan_del(struct mv88e6xxx_chip *chip,
1718                                     int port, u16 vid)
1719 {
1720         struct mv88e6xxx_vtu_entry vlan;
1721         int i, err;
1722
1723         err = mv88e6xxx_vtu_get(chip, vid, &vlan, false);
1724         if (err)
1725                 return err;
1726
1727         /* Tell switchdev if this VLAN is handled in software */
1728         if (vlan.member[port] == MV88E6XXX_G1_VTU_DATA_MEMBER_TAG_NON_MEMBER)
1729                 return -EOPNOTSUPP;
1730
1731         vlan.member[port] = MV88E6XXX_G1_VTU_DATA_MEMBER_TAG_NON_MEMBER;
1732
1733         /* keep the VLAN unless all ports are excluded */
1734         vlan.valid = false;
1735         for (i = 0; i < mv88e6xxx_num_ports(chip); ++i) {
1736                 if (vlan.member[i] !=
1737                     MV88E6XXX_G1_VTU_DATA_MEMBER_TAG_NON_MEMBER) {
1738                         vlan.valid = true;
1739                         break;
1740                 }
1741         }
1742
1743         err = mv88e6xxx_vtu_loadpurge(chip, &vlan);
1744         if (err)
1745                 return err;
1746
1747         return mv88e6xxx_g1_atu_remove(chip, vlan.fid, port, false);
1748 }
1749
1750 static int mv88e6xxx_port_vlan_del(struct dsa_switch *ds, int port,
1751                                    const struct switchdev_obj_port_vlan *vlan)
1752 {
1753         struct mv88e6xxx_chip *chip = ds->priv;
1754         u16 pvid, vid;
1755         int err = 0;
1756
1757         if (!chip->info->max_vid)
1758                 return -EOPNOTSUPP;
1759
1760         mutex_lock(&chip->reg_lock);
1761
1762         err = mv88e6xxx_port_get_pvid(chip, port, &pvid);
1763         if (err)
1764                 goto unlock;
1765
1766         for (vid = vlan->vid_begin; vid <= vlan->vid_end; ++vid) {
1767                 err = _mv88e6xxx_port_vlan_del(chip, port, vid);
1768                 if (err)
1769                         goto unlock;
1770
1771                 if (vid == pvid) {
1772                         err = mv88e6xxx_port_set_pvid(chip, port, 0);
1773                         if (err)
1774                                 goto unlock;
1775                 }
1776         }
1777
1778 unlock:
1779         mutex_unlock(&chip->reg_lock);
1780
1781         return err;
1782 }
1783
1784 static int mv88e6xxx_port_fdb_add(struct dsa_switch *ds, int port,
1785                                   const unsigned char *addr, u16 vid)
1786 {
1787         struct mv88e6xxx_chip *chip = ds->priv;
1788         int err;
1789
1790         mutex_lock(&chip->reg_lock);
1791         err = mv88e6xxx_port_db_load_purge(chip, port, addr, vid,
1792                                            MV88E6XXX_G1_ATU_DATA_STATE_UC_STATIC);
1793         mutex_unlock(&chip->reg_lock);
1794
1795         return err;
1796 }
1797
1798 static int mv88e6xxx_port_fdb_del(struct dsa_switch *ds, int port,
1799                                   const unsigned char *addr, u16 vid)
1800 {
1801         struct mv88e6xxx_chip *chip = ds->priv;
1802         int err;
1803
1804         mutex_lock(&chip->reg_lock);
1805         err = mv88e6xxx_port_db_load_purge(chip, port, addr, vid,
1806                                            MV88E6XXX_G1_ATU_DATA_STATE_UNUSED);
1807         mutex_unlock(&chip->reg_lock);
1808
1809         return err;
1810 }
1811
1812 static int mv88e6xxx_port_db_dump_fid(struct mv88e6xxx_chip *chip,
1813                                       u16 fid, u16 vid, int port,
1814                                       dsa_fdb_dump_cb_t *cb, void *data)
1815 {
1816         struct mv88e6xxx_atu_entry addr;
1817         bool is_static;
1818         int err;
1819
1820         addr.state = MV88E6XXX_G1_ATU_DATA_STATE_UNUSED;
1821         eth_broadcast_addr(addr.mac);
1822
1823         do {
1824                 mutex_lock(&chip->reg_lock);
1825                 err = mv88e6xxx_g1_atu_getnext(chip, fid, &addr);
1826                 mutex_unlock(&chip->reg_lock);
1827                 if (err)
1828                         return err;
1829
1830                 if (addr.state == MV88E6XXX_G1_ATU_DATA_STATE_UNUSED)
1831                         break;
1832
1833                 if (addr.trunk || (addr.portvec & BIT(port)) == 0)
1834                         continue;
1835
1836                 if (!is_unicast_ether_addr(addr.mac))
1837                         continue;
1838
1839                 is_static = (addr.state ==
1840                              MV88E6XXX_G1_ATU_DATA_STATE_UC_STATIC);
1841                 err = cb(addr.mac, vid, is_static, data);
1842                 if (err)
1843                         return err;
1844         } while (!is_broadcast_ether_addr(addr.mac));
1845
1846         return err;
1847 }
1848
1849 static int mv88e6xxx_port_db_dump(struct mv88e6xxx_chip *chip, int port,
1850                                   dsa_fdb_dump_cb_t *cb, void *data)
1851 {
1852         struct mv88e6xxx_vtu_entry vlan = {
1853                 .vid = chip->info->max_vid,
1854         };
1855         u16 fid;
1856         int err;
1857
1858         /* Dump port's default Filtering Information Database (VLAN ID 0) */
1859         mutex_lock(&chip->reg_lock);
1860         err = mv88e6xxx_port_get_fid(chip, port, &fid);
1861         mutex_unlock(&chip->reg_lock);
1862
1863         if (err)
1864                 return err;
1865
1866         err = mv88e6xxx_port_db_dump_fid(chip, fid, 0, port, cb, data);
1867         if (err)
1868                 return err;
1869
1870         /* Dump VLANs' Filtering Information Databases */
1871         do {
1872                 mutex_lock(&chip->reg_lock);
1873                 err = mv88e6xxx_vtu_getnext(chip, &vlan);
1874                 mutex_unlock(&chip->reg_lock);
1875                 if (err)
1876                         return err;
1877
1878                 if (!vlan.valid)
1879                         break;
1880
1881                 err = mv88e6xxx_port_db_dump_fid(chip, vlan.fid, vlan.vid, port,
1882                                                  cb, data);
1883                 if (err)
1884                         return err;
1885         } while (vlan.vid < chip->info->max_vid);
1886
1887         return err;
1888 }
1889
1890 static int mv88e6xxx_port_fdb_dump(struct dsa_switch *ds, int port,
1891                                    dsa_fdb_dump_cb_t *cb, void *data)
1892 {
1893         struct mv88e6xxx_chip *chip = ds->priv;
1894
1895         return mv88e6xxx_port_db_dump(chip, port, cb, data);
1896 }
1897
1898 static int mv88e6xxx_bridge_map(struct mv88e6xxx_chip *chip,
1899                                 struct net_device *br)
1900 {
1901         struct dsa_switch *ds;
1902         int port;
1903         int dev;
1904         int err;
1905
1906         /* Remap the Port VLAN of each local bridge group member */
1907         for (port = 0; port < mv88e6xxx_num_ports(chip); ++port) {
1908                 if (chip->ds->ports[port].bridge_dev == br) {
1909                         err = mv88e6xxx_port_vlan_map(chip, port);
1910                         if (err)
1911                                 return err;
1912                 }
1913         }
1914
1915         if (!mv88e6xxx_has_pvt(chip))
1916                 return 0;
1917
1918         /* Remap the Port VLAN of each cross-chip bridge group member */
1919         for (dev = 0; dev < DSA_MAX_SWITCHES; ++dev) {
1920                 ds = chip->ds->dst->ds[dev];
1921                 if (!ds)
1922                         break;
1923
1924                 for (port = 0; port < ds->num_ports; ++port) {
1925                         if (ds->ports[port].bridge_dev == br) {
1926                                 err = mv88e6xxx_pvt_map(chip, dev, port);
1927                                 if (err)
1928                                         return err;
1929                         }
1930                 }
1931         }
1932
1933         return 0;
1934 }
1935
1936 static int mv88e6xxx_port_bridge_join(struct dsa_switch *ds, int port,
1937                                       struct net_device *br)
1938 {
1939         struct mv88e6xxx_chip *chip = ds->priv;
1940         int err;
1941
1942         mutex_lock(&chip->reg_lock);
1943         err = mv88e6xxx_bridge_map(chip, br);
1944         mutex_unlock(&chip->reg_lock);
1945
1946         return err;
1947 }
1948
1949 static void mv88e6xxx_port_bridge_leave(struct dsa_switch *ds, int port,
1950                                         struct net_device *br)
1951 {
1952         struct mv88e6xxx_chip *chip = ds->priv;
1953
1954         mutex_lock(&chip->reg_lock);
1955         if (mv88e6xxx_bridge_map(chip, br) ||
1956             mv88e6xxx_port_vlan_map(chip, port))
1957                 dev_err(ds->dev, "failed to remap in-chip Port VLAN\n");
1958         mutex_unlock(&chip->reg_lock);
1959 }
1960
1961 static int mv88e6xxx_crosschip_bridge_join(struct dsa_switch *ds, int dev,
1962                                            int port, struct net_device *br)
1963 {
1964         struct mv88e6xxx_chip *chip = ds->priv;
1965         int err;
1966
1967         if (!mv88e6xxx_has_pvt(chip))
1968                 return 0;
1969
1970         mutex_lock(&chip->reg_lock);
1971         err = mv88e6xxx_pvt_map(chip, dev, port);
1972         mutex_unlock(&chip->reg_lock);
1973
1974         return err;
1975 }
1976
1977 static void mv88e6xxx_crosschip_bridge_leave(struct dsa_switch *ds, int dev,
1978                                              int port, struct net_device *br)
1979 {
1980         struct mv88e6xxx_chip *chip = ds->priv;
1981
1982         if (!mv88e6xxx_has_pvt(chip))
1983                 return;
1984
1985         mutex_lock(&chip->reg_lock);
1986         if (mv88e6xxx_pvt_map(chip, dev, port))
1987                 dev_err(ds->dev, "failed to remap cross-chip Port VLAN\n");
1988         mutex_unlock(&chip->reg_lock);
1989 }
1990
1991 static int mv88e6xxx_software_reset(struct mv88e6xxx_chip *chip)
1992 {
1993         if (chip->info->ops->reset)
1994                 return chip->info->ops->reset(chip);
1995
1996         return 0;
1997 }
1998
1999 static void mv88e6xxx_hardware_reset(struct mv88e6xxx_chip *chip)
2000 {
2001         struct gpio_desc *gpiod = chip->reset;
2002
2003         /* If there is a GPIO connected to the reset pin, toggle it */
2004         if (gpiod) {
2005                 gpiod_set_value_cansleep(gpiod, 1);
2006                 usleep_range(10000, 20000);
2007                 gpiod_set_value_cansleep(gpiod, 0);
2008                 usleep_range(10000, 20000);
2009         }
2010 }
2011
2012 static int mv88e6xxx_disable_ports(struct mv88e6xxx_chip *chip)
2013 {
2014         int i, err;
2015
2016         /* Set all ports to the Disabled state */
2017         for (i = 0; i < mv88e6xxx_num_ports(chip); i++) {
2018                 err = mv88e6xxx_port_set_state(chip, i, BR_STATE_DISABLED);
2019                 if (err)
2020                         return err;
2021         }
2022
2023         /* Wait for transmit queues to drain,
2024          * i.e. 2ms for a maximum frame to be transmitted at 10 Mbps.
2025          */
2026         usleep_range(2000, 4000);
2027
2028         return 0;
2029 }
2030
2031 static int mv88e6xxx_switch_reset(struct mv88e6xxx_chip *chip)
2032 {
2033         int err;
2034
2035         err = mv88e6xxx_disable_ports(chip);
2036         if (err)
2037                 return err;
2038
2039         mv88e6xxx_hardware_reset(chip);
2040
2041         return mv88e6xxx_software_reset(chip);
2042 }
2043
2044 static int mv88e6xxx_set_port_mode(struct mv88e6xxx_chip *chip, int port,
2045                                    enum mv88e6xxx_frame_mode frame,
2046                                    enum mv88e6xxx_egress_mode egress, u16 etype)
2047 {
2048         int err;
2049
2050         if (!chip->info->ops->port_set_frame_mode)
2051                 return -EOPNOTSUPP;
2052
2053         err = mv88e6xxx_port_set_egress_mode(chip, port, egress);
2054         if (err)
2055                 return err;
2056
2057         err = chip->info->ops->port_set_frame_mode(chip, port, frame);
2058         if (err)
2059                 return err;
2060
2061         if (chip->info->ops->port_set_ether_type)
2062                 return chip->info->ops->port_set_ether_type(chip, port, etype);
2063
2064         return 0;
2065 }
2066
2067 static int mv88e6xxx_set_port_mode_normal(struct mv88e6xxx_chip *chip, int port)
2068 {
2069         return mv88e6xxx_set_port_mode(chip, port, MV88E6XXX_FRAME_MODE_NORMAL,
2070                                        MV88E6XXX_EGRESS_MODE_UNMODIFIED,
2071                                        MV88E6XXX_PORT_ETH_TYPE_DEFAULT);
2072 }
2073
2074 static int mv88e6xxx_set_port_mode_dsa(struct mv88e6xxx_chip *chip, int port)
2075 {
2076         return mv88e6xxx_set_port_mode(chip, port, MV88E6XXX_FRAME_MODE_DSA,
2077                                        MV88E6XXX_EGRESS_MODE_UNMODIFIED,
2078                                        MV88E6XXX_PORT_ETH_TYPE_DEFAULT);
2079 }
2080
2081 static int mv88e6xxx_set_port_mode_edsa(struct mv88e6xxx_chip *chip, int port)
2082 {
2083         return mv88e6xxx_set_port_mode(chip, port,
2084                                        MV88E6XXX_FRAME_MODE_ETHERTYPE,
2085                                        MV88E6XXX_EGRESS_MODE_ETHERTYPE,
2086                                        ETH_P_EDSA);
2087 }
2088
2089 static int mv88e6xxx_setup_port_mode(struct mv88e6xxx_chip *chip, int port)
2090 {
2091         if (dsa_is_dsa_port(chip->ds, port))
2092                 return mv88e6xxx_set_port_mode_dsa(chip, port);
2093
2094         if (dsa_is_user_port(chip->ds, port))
2095                 return mv88e6xxx_set_port_mode_normal(chip, port);
2096
2097         /* Setup CPU port mode depending on its supported tag format */
2098         if (chip->info->tag_protocol == DSA_TAG_PROTO_DSA)
2099                 return mv88e6xxx_set_port_mode_dsa(chip, port);
2100
2101         if (chip->info->tag_protocol == DSA_TAG_PROTO_EDSA)
2102                 return mv88e6xxx_set_port_mode_edsa(chip, port);
2103
2104         return -EINVAL;
2105 }
2106
2107 static int mv88e6xxx_setup_message_port(struct mv88e6xxx_chip *chip, int port)
2108 {
2109         bool message = dsa_is_dsa_port(chip->ds, port);
2110
2111         return mv88e6xxx_port_set_message_port(chip, port, message);
2112 }
2113
2114 static int mv88e6xxx_setup_egress_floods(struct mv88e6xxx_chip *chip, int port)
2115 {
2116         struct dsa_switch *ds = chip->ds;
2117         bool flood;
2118
2119         /* Upstream ports flood frames with unknown unicast or multicast DA */
2120         flood = dsa_is_cpu_port(ds, port) || dsa_is_dsa_port(ds, port);
2121         if (chip->info->ops->port_set_egress_floods)
2122                 return chip->info->ops->port_set_egress_floods(chip, port,
2123                                                                flood, flood);
2124
2125         return 0;
2126 }
2127
2128 static int mv88e6xxx_serdes_power(struct mv88e6xxx_chip *chip, int port,
2129                                   bool on)
2130 {
2131         if (chip->info->ops->serdes_power)
2132                 return chip->info->ops->serdes_power(chip, port, on);
2133
2134         return 0;
2135 }
2136
2137 static int mv88e6xxx_setup_upstream_port(struct mv88e6xxx_chip *chip, int port)
2138 {
2139         struct dsa_switch *ds = chip->ds;
2140         int upstream_port;
2141         int err;
2142
2143         upstream_port = dsa_upstream_port(ds, port);
2144         if (chip->info->ops->port_set_upstream_port) {
2145                 err = chip->info->ops->port_set_upstream_port(chip, port,
2146                                                               upstream_port);
2147                 if (err)
2148                         return err;
2149         }
2150
2151         if (port == upstream_port) {
2152                 if (chip->info->ops->set_cpu_port) {
2153                         err = chip->info->ops->set_cpu_port(chip,
2154                                                             upstream_port);
2155                         if (err)
2156                                 return err;
2157                 }
2158
2159                 if (chip->info->ops->set_egress_port) {
2160                         err = chip->info->ops->set_egress_port(chip,
2161                                                                upstream_port);
2162                         if (err)
2163                                 return err;
2164                 }
2165         }
2166
2167         return 0;
2168 }
2169
2170 static int mv88e6xxx_setup_port(struct mv88e6xxx_chip *chip, int port)
2171 {
2172         struct dsa_switch *ds = chip->ds;
2173         int err;
2174         u16 reg;
2175
2176         /* MAC Forcing register: don't force link, speed, duplex or flow control
2177          * state to any particular values on physical ports, but force the CPU
2178          * port and all DSA ports to their maximum bandwidth and full duplex.
2179          */
2180         if (dsa_is_cpu_port(ds, port) || dsa_is_dsa_port(ds, port))
2181                 err = mv88e6xxx_port_setup_mac(chip, port, LINK_FORCED_UP,
2182                                                SPEED_MAX, DUPLEX_FULL,
2183                                                PAUSE_OFF,
2184                                                PHY_INTERFACE_MODE_NA);
2185         else
2186                 err = mv88e6xxx_port_setup_mac(chip, port, LINK_UNFORCED,
2187                                                SPEED_UNFORCED, DUPLEX_UNFORCED,
2188                                                PAUSE_ON,
2189                                                PHY_INTERFACE_MODE_NA);
2190         if (err)
2191                 return err;
2192
2193         /* Port Control: disable Drop-on-Unlock, disable Drop-on-Lock,
2194          * disable Header mode, enable IGMP/MLD snooping, disable VLAN
2195          * tunneling, determine priority by looking at 802.1p and IP
2196          * priority fields (IP prio has precedence), and set STP state
2197          * to Forwarding.
2198          *
2199          * If this is the CPU link, use DSA or EDSA tagging depending
2200          * on which tagging mode was configured.
2201          *
2202          * If this is a link to another switch, use DSA tagging mode.
2203          *
2204          * If this is the upstream port for this switch, enable
2205          * forwarding of unknown unicasts and multicasts.
2206          */
2207         reg = MV88E6XXX_PORT_CTL0_IGMP_MLD_SNOOP |
2208                 MV88E6185_PORT_CTL0_USE_TAG | MV88E6185_PORT_CTL0_USE_IP |
2209                 MV88E6XXX_PORT_CTL0_STATE_FORWARDING;
2210         err = mv88e6xxx_port_write(chip, port, MV88E6XXX_PORT_CTL0, reg);
2211         if (err)
2212                 return err;
2213
2214         err = mv88e6xxx_setup_port_mode(chip, port);
2215         if (err)
2216                 return err;
2217
2218         err = mv88e6xxx_setup_egress_floods(chip, port);
2219         if (err)
2220                 return err;
2221
2222         /* Enable the SERDES interface for DSA and CPU ports. Normal
2223          * ports SERDES are enabled when the port is enabled, thus
2224          * saving a bit of power.
2225          */
2226         if ((dsa_is_cpu_port(ds, port) || dsa_is_dsa_port(ds, port))) {
2227                 err = mv88e6xxx_serdes_power(chip, port, true);
2228                 if (err)
2229                         return err;
2230         }
2231
2232         /* Port Control 2: don't force a good FCS, set the maximum frame size to
2233          * 10240 bytes, disable 802.1q tags checking, don't discard tagged or
2234          * untagged frames on this port, do a destination address lookup on all
2235          * received packets as usual, disable ARP mirroring and don't send a
2236          * copy of all transmitted/received frames on this port to the CPU.
2237          */
2238         err = mv88e6xxx_port_set_map_da(chip, port);
2239         if (err)
2240                 return err;
2241
2242         err = mv88e6xxx_setup_upstream_port(chip, port);
2243         if (err)
2244                 return err;
2245
2246         err = mv88e6xxx_port_set_8021q_mode(chip, port,
2247                                 MV88E6XXX_PORT_CTL2_8021Q_MODE_DISABLED);
2248         if (err)
2249                 return err;
2250
2251         if (chip->info->ops->port_set_jumbo_size) {
2252                 err = chip->info->ops->port_set_jumbo_size(chip, port, 10240);
2253                 if (err)
2254                         return err;
2255         }
2256
2257         /* Port Association Vector: when learning source addresses
2258          * of packets, add the address to the address database using
2259          * a port bitmap that has only the bit for this port set and
2260          * the other bits clear.
2261          */
2262         reg = 1 << port;
2263         /* Disable learning for CPU port */
2264         if (dsa_is_cpu_port(ds, port))
2265                 reg = 0;
2266
2267         err = mv88e6xxx_port_write(chip, port, MV88E6XXX_PORT_ASSOC_VECTOR,
2268                                    reg);
2269         if (err)
2270                 return err;
2271
2272         /* Egress rate control 2: disable egress rate control. */
2273         err = mv88e6xxx_port_write(chip, port, MV88E6XXX_PORT_EGRESS_RATE_CTL2,
2274                                    0x0000);
2275         if (err)
2276                 return err;
2277
2278         if (chip->info->ops->port_pause_limit) {
2279                 err = chip->info->ops->port_pause_limit(chip, port, 0, 0);
2280                 if (err)
2281                         return err;
2282         }
2283
2284         if (chip->info->ops->port_disable_learn_limit) {
2285                 err = chip->info->ops->port_disable_learn_limit(chip, port);
2286                 if (err)
2287                         return err;
2288         }
2289
2290         if (chip->info->ops->port_disable_pri_override) {
2291                 err = chip->info->ops->port_disable_pri_override(chip, port);
2292                 if (err)
2293                         return err;
2294         }
2295
2296         if (chip->info->ops->port_tag_remap) {
2297                 err = chip->info->ops->port_tag_remap(chip, port);
2298                 if (err)
2299                         return err;
2300         }
2301
2302         if (chip->info->ops->port_egress_rate_limiting) {
2303                 err = chip->info->ops->port_egress_rate_limiting(chip, port);
2304                 if (err)
2305                         return err;
2306         }
2307
2308         err = mv88e6xxx_setup_message_port(chip, port);
2309         if (err)
2310                 return err;
2311
2312         /* Port based VLAN map: give each port the same default address
2313          * database, and allow bidirectional communication between the
2314          * CPU and DSA port(s), and the other ports.
2315          */
2316         err = mv88e6xxx_port_set_fid(chip, port, 0);
2317         if (err)
2318                 return err;
2319
2320         err = mv88e6xxx_port_vlan_map(chip, port);
2321         if (err)
2322                 return err;
2323
2324         /* Default VLAN ID and priority: don't set a default VLAN
2325          * ID, and set the default packet priority to zero.
2326          */
2327         return mv88e6xxx_port_write(chip, port, MV88E6XXX_PORT_DEFAULT_VLAN, 0);
2328 }
2329
2330 static int mv88e6xxx_port_enable(struct dsa_switch *ds, int port,
2331                                  struct phy_device *phydev)
2332 {
2333         struct mv88e6xxx_chip *chip = ds->priv;
2334         int err;
2335
2336         mutex_lock(&chip->reg_lock);
2337         err = mv88e6xxx_serdes_power(chip, port, true);
2338         mutex_unlock(&chip->reg_lock);
2339
2340         return err;
2341 }
2342
2343 static void mv88e6xxx_port_disable(struct dsa_switch *ds, int port,
2344                                    struct phy_device *phydev)
2345 {
2346         struct mv88e6xxx_chip *chip = ds->priv;
2347
2348         mutex_lock(&chip->reg_lock);
2349         if (mv88e6xxx_serdes_power(chip, port, false))
2350                 dev_err(chip->dev, "failed to power off SERDES\n");
2351         mutex_unlock(&chip->reg_lock);
2352 }
2353
2354 static int mv88e6xxx_set_ageing_time(struct dsa_switch *ds,
2355                                      unsigned int ageing_time)
2356 {
2357         struct mv88e6xxx_chip *chip = ds->priv;
2358         int err;
2359
2360         mutex_lock(&chip->reg_lock);
2361         err = mv88e6xxx_g1_atu_set_age_time(chip, ageing_time);
2362         mutex_unlock(&chip->reg_lock);
2363
2364         return err;
2365 }
2366
2367 static int mv88e6xxx_stats_setup(struct mv88e6xxx_chip *chip)
2368 {
2369         int err;
2370
2371         /* Initialize the statistics unit */
2372         if (chip->info->ops->stats_set_histogram) {
2373                 err = chip->info->ops->stats_set_histogram(chip);
2374                 if (err)
2375                         return err;
2376         }
2377
2378         return mv88e6xxx_g1_stats_clear(chip);
2379 }
2380
2381 static int mv88e6xxx_setup(struct dsa_switch *ds)
2382 {
2383         struct mv88e6xxx_chip *chip = ds->priv;
2384         int err;
2385         int i;
2386
2387         chip->ds = ds;
2388         ds->slave_mii_bus = mv88e6xxx_default_mdio_bus(chip);
2389
2390         mutex_lock(&chip->reg_lock);
2391
2392         /* Setup Switch Port Registers */
2393         for (i = 0; i < mv88e6xxx_num_ports(chip); i++) {
2394                 if (dsa_is_unused_port(ds, i))
2395                         continue;
2396
2397                 err = mv88e6xxx_setup_port(chip, i);
2398                 if (err)
2399                         goto unlock;
2400         }
2401
2402         err = mv88e6xxx_irl_setup(chip);
2403         if (err)
2404                 goto unlock;
2405
2406         err = mv88e6xxx_mac_setup(chip);
2407         if (err)
2408                 goto unlock;
2409
2410         err = mv88e6xxx_phy_setup(chip);
2411         if (err)
2412                 goto unlock;
2413
2414         err = mv88e6xxx_vtu_setup(chip);
2415         if (err)
2416                 goto unlock;
2417
2418         err = mv88e6xxx_pvt_setup(chip);
2419         if (err)
2420                 goto unlock;
2421
2422         err = mv88e6xxx_atu_setup(chip);
2423         if (err)
2424                 goto unlock;
2425
2426         err = mv88e6xxx_broadcast_setup(chip, 0);
2427         if (err)
2428                 goto unlock;
2429
2430         err = mv88e6xxx_pot_setup(chip);
2431         if (err)
2432                 goto unlock;
2433
2434         err = mv88e6xxx_rmu_setup(chip);
2435         if (err)
2436                 goto unlock;
2437
2438         err = mv88e6xxx_rsvd2cpu_setup(chip);
2439         if (err)
2440                 goto unlock;
2441
2442         err = mv88e6xxx_trunk_setup(chip);
2443         if (err)
2444                 goto unlock;
2445
2446         err = mv88e6xxx_devmap_setup(chip);
2447         if (err)
2448                 goto unlock;
2449
2450         err = mv88e6xxx_pri_setup(chip);
2451         if (err)
2452                 goto unlock;
2453
2454         /* Setup PTP Hardware Clock and timestamping */
2455         if (chip->info->ptp_support) {
2456                 err = mv88e6xxx_ptp_setup(chip);
2457                 if (err)
2458                         goto unlock;
2459
2460                 err = mv88e6xxx_hwtstamp_setup(chip);
2461                 if (err)
2462                         goto unlock;
2463         }
2464
2465         err = mv88e6xxx_stats_setup(chip);
2466         if (err)
2467                 goto unlock;
2468
2469 unlock:
2470         mutex_unlock(&chip->reg_lock);
2471
2472         return err;
2473 }
2474
2475 static int mv88e6xxx_mdio_read(struct mii_bus *bus, int phy, int reg)
2476 {
2477         struct mv88e6xxx_mdio_bus *mdio_bus = bus->priv;
2478         struct mv88e6xxx_chip *chip = mdio_bus->chip;
2479         u16 val;
2480         int err;
2481
2482         if (!chip->info->ops->phy_read)
2483                 return -EOPNOTSUPP;
2484
2485         mutex_lock(&chip->reg_lock);
2486         err = chip->info->ops->phy_read(chip, bus, phy, reg, &val);
2487         mutex_unlock(&chip->reg_lock);
2488
2489         if (reg == MII_PHYSID2) {
2490                 /* Some internal PHYS don't have a model number.  Use
2491                  * the mv88e6390 family model number instead.
2492                  */
2493                 if (!(val & 0x3f0))
2494                         val |= MV88E6XXX_PORT_SWITCH_ID_PROD_6390 >> 4;
2495         }
2496
2497         return err ? err : val;
2498 }
2499
2500 static int mv88e6xxx_mdio_write(struct mii_bus *bus, int phy, int reg, u16 val)
2501 {
2502         struct mv88e6xxx_mdio_bus *mdio_bus = bus->priv;
2503         struct mv88e6xxx_chip *chip = mdio_bus->chip;
2504         int err;
2505
2506         if (!chip->info->ops->phy_write)
2507                 return -EOPNOTSUPP;
2508
2509         mutex_lock(&chip->reg_lock);
2510         err = chip->info->ops->phy_write(chip, bus, phy, reg, val);
2511         mutex_unlock(&chip->reg_lock);
2512
2513         return err;
2514 }
2515
2516 static int mv88e6xxx_mdio_register(struct mv88e6xxx_chip *chip,
2517                                    struct device_node *np,
2518                                    bool external)
2519 {
2520         static int index;
2521         struct mv88e6xxx_mdio_bus *mdio_bus;
2522         struct mii_bus *bus;
2523         int err;
2524
2525         if (external) {
2526                 mutex_lock(&chip->reg_lock);
2527                 err = mv88e6xxx_g2_scratch_gpio_set_smi(chip, true);
2528                 mutex_unlock(&chip->reg_lock);
2529
2530                 if (err)
2531                         return err;
2532         }
2533
2534         bus = devm_mdiobus_alloc_size(chip->dev, sizeof(*mdio_bus));
2535         if (!bus)
2536                 return -ENOMEM;
2537
2538         mdio_bus = bus->priv;
2539         mdio_bus->bus = bus;
2540         mdio_bus->chip = chip;
2541         INIT_LIST_HEAD(&mdio_bus->list);
2542         mdio_bus->external = external;
2543
2544         if (np) {
2545                 bus->name = np->full_name;
2546                 snprintf(bus->id, MII_BUS_ID_SIZE, "%pOF", np);
2547         } else {
2548                 bus->name = "mv88e6xxx SMI";
2549                 snprintf(bus->id, MII_BUS_ID_SIZE, "mv88e6xxx-%d", index++);
2550         }
2551
2552         bus->read = mv88e6xxx_mdio_read;
2553         bus->write = mv88e6xxx_mdio_write;
2554         bus->parent = chip->dev;
2555
2556         if (!external) {
2557                 err = mv88e6xxx_g2_irq_mdio_setup(chip, bus);
2558                 if (err)
2559                         return err;
2560         }
2561
2562         err = of_mdiobus_register(bus, np);
2563         if (err) {
2564                 dev_err(chip->dev, "Cannot register MDIO bus (%d)\n", err);
2565                 mv88e6xxx_g2_irq_mdio_free(chip, bus);
2566                 return err;
2567         }
2568
2569         if (external)
2570                 list_add_tail(&mdio_bus->list, &chip->mdios);
2571         else
2572                 list_add(&mdio_bus->list, &chip->mdios);
2573
2574         return 0;
2575 }
2576
2577 static const struct of_device_id mv88e6xxx_mdio_external_match[] = {
2578         { .compatible = "marvell,mv88e6xxx-mdio-external",
2579           .data = (void *)true },
2580         { },
2581 };
2582
2583 static void mv88e6xxx_mdios_unregister(struct mv88e6xxx_chip *chip)
2584
2585 {
2586         struct mv88e6xxx_mdio_bus *mdio_bus;
2587         struct mii_bus *bus;
2588
2589         list_for_each_entry(mdio_bus, &chip->mdios, list) {
2590                 bus = mdio_bus->bus;
2591
2592                 if (!mdio_bus->external)
2593                         mv88e6xxx_g2_irq_mdio_free(chip, bus);
2594
2595                 mdiobus_unregister(bus);
2596         }
2597 }
2598
2599 static int mv88e6xxx_mdios_register(struct mv88e6xxx_chip *chip,
2600                                     struct device_node *np)
2601 {
2602         const struct of_device_id *match;
2603         struct device_node *child;
2604         int err;
2605
2606         /* Always register one mdio bus for the internal/default mdio
2607          * bus. This maybe represented in the device tree, but is
2608          * optional.
2609          */
2610         child = of_get_child_by_name(np, "mdio");
2611         err = mv88e6xxx_mdio_register(chip, child, false);
2612         if (err)
2613                 return err;
2614
2615         /* Walk the device tree, and see if there are any other nodes
2616          * which say they are compatible with the external mdio
2617          * bus.
2618          */
2619         for_each_available_child_of_node(np, child) {
2620                 match = of_match_node(mv88e6xxx_mdio_external_match, child);
2621                 if (match) {
2622                         err = mv88e6xxx_mdio_register(chip, child, true);
2623                         if (err) {
2624                                 mv88e6xxx_mdios_unregister(chip);
2625                                 return err;
2626                         }
2627                 }
2628         }
2629
2630         return 0;
2631 }
2632
2633 static int mv88e6xxx_get_eeprom_len(struct dsa_switch *ds)
2634 {
2635         struct mv88e6xxx_chip *chip = ds->priv;
2636
2637         return chip->eeprom_len;
2638 }
2639
2640 static int mv88e6xxx_get_eeprom(struct dsa_switch *ds,
2641                                 struct ethtool_eeprom *eeprom, u8 *data)
2642 {
2643         struct mv88e6xxx_chip *chip = ds->priv;
2644         int err;
2645
2646         if (!chip->info->ops->get_eeprom)
2647                 return -EOPNOTSUPP;
2648
2649         mutex_lock(&chip->reg_lock);
2650         err = chip->info->ops->get_eeprom(chip, eeprom, data);
2651         mutex_unlock(&chip->reg_lock);
2652
2653         if (err)
2654                 return err;
2655
2656         eeprom->magic = 0xc3ec4951;
2657
2658         return 0;
2659 }
2660
2661 static int mv88e6xxx_set_eeprom(struct dsa_switch *ds,
2662                                 struct ethtool_eeprom *eeprom, u8 *data)
2663 {
2664         struct mv88e6xxx_chip *chip = ds->priv;
2665         int err;
2666
2667         if (!chip->info->ops->set_eeprom)
2668                 return -EOPNOTSUPP;
2669
2670         if (eeprom->magic != 0xc3ec4951)
2671                 return -EINVAL;
2672
2673         mutex_lock(&chip->reg_lock);
2674         err = chip->info->ops->set_eeprom(chip, eeprom, data);
2675         mutex_unlock(&chip->reg_lock);
2676
2677         return err;
2678 }
2679
2680 static const struct mv88e6xxx_ops mv88e6085_ops = {
2681         /* MV88E6XXX_FAMILY_6097 */
2682         .ieee_pri_map = mv88e6085_g1_ieee_pri_map,
2683         .ip_pri_map = mv88e6085_g1_ip_pri_map,
2684         .irl_init_all = mv88e6352_g2_irl_init_all,
2685         .set_switch_mac = mv88e6xxx_g1_set_switch_mac,
2686         .phy_read = mv88e6185_phy_ppu_read,
2687         .phy_write = mv88e6185_phy_ppu_write,
2688         .port_set_link = mv88e6xxx_port_set_link,
2689         .port_set_duplex = mv88e6xxx_port_set_duplex,
2690         .port_set_speed = mv88e6185_port_set_speed,
2691         .port_tag_remap = mv88e6095_port_tag_remap,
2692         .port_set_frame_mode = mv88e6351_port_set_frame_mode,
2693         .port_set_egress_floods = mv88e6352_port_set_egress_floods,
2694         .port_set_ether_type = mv88e6351_port_set_ether_type,
2695         .port_egress_rate_limiting = mv88e6097_port_egress_rate_limiting,
2696         .port_pause_limit = mv88e6097_port_pause_limit,
2697         .port_disable_learn_limit = mv88e6xxx_port_disable_learn_limit,
2698         .port_disable_pri_override = mv88e6xxx_port_disable_pri_override,
2699         .port_link_state = mv88e6352_port_link_state,
2700         .stats_snapshot = mv88e6xxx_g1_stats_snapshot,
2701         .stats_set_histogram = mv88e6095_g1_stats_set_histogram,
2702         .stats_get_sset_count = mv88e6095_stats_get_sset_count,
2703         .stats_get_strings = mv88e6095_stats_get_strings,
2704         .stats_get_stats = mv88e6095_stats_get_stats,
2705         .set_cpu_port = mv88e6095_g1_set_cpu_port,
2706         .set_egress_port = mv88e6095_g1_set_egress_port,
2707         .watchdog_ops = &mv88e6097_watchdog_ops,
2708         .mgmt_rsvd2cpu = mv88e6352_g2_mgmt_rsvd2cpu,
2709         .pot_clear = mv88e6xxx_g2_pot_clear,
2710         .ppu_enable = mv88e6185_g1_ppu_enable,
2711         .ppu_disable = mv88e6185_g1_ppu_disable,
2712         .reset = mv88e6185_g1_reset,
2713         .rmu_disable = mv88e6085_g1_rmu_disable,
2714         .vtu_getnext = mv88e6352_g1_vtu_getnext,
2715         .vtu_loadpurge = mv88e6352_g1_vtu_loadpurge,
2716         .phylink_validate = mv88e6185_phylink_validate,
2717 };
2718
2719 static const struct mv88e6xxx_ops mv88e6095_ops = {
2720         /* MV88E6XXX_FAMILY_6095 */
2721         .ieee_pri_map = mv88e6085_g1_ieee_pri_map,
2722         .ip_pri_map = mv88e6085_g1_ip_pri_map,
2723         .set_switch_mac = mv88e6xxx_g1_set_switch_mac,
2724         .phy_read = mv88e6185_phy_ppu_read,
2725         .phy_write = mv88e6185_phy_ppu_write,
2726         .port_set_link = mv88e6xxx_port_set_link,
2727         .port_set_duplex = mv88e6xxx_port_set_duplex,
2728         .port_set_speed = mv88e6185_port_set_speed,
2729         .port_set_frame_mode = mv88e6085_port_set_frame_mode,
2730         .port_set_egress_floods = mv88e6185_port_set_egress_floods,
2731         .port_set_upstream_port = mv88e6095_port_set_upstream_port,
2732         .port_link_state = mv88e6185_port_link_state,
2733         .stats_snapshot = mv88e6xxx_g1_stats_snapshot,
2734         .stats_set_histogram = mv88e6095_g1_stats_set_histogram,
2735         .stats_get_sset_count = mv88e6095_stats_get_sset_count,
2736         .stats_get_strings = mv88e6095_stats_get_strings,
2737         .stats_get_stats = mv88e6095_stats_get_stats,
2738         .mgmt_rsvd2cpu = mv88e6185_g2_mgmt_rsvd2cpu,
2739         .ppu_enable = mv88e6185_g1_ppu_enable,
2740         .ppu_disable = mv88e6185_g1_ppu_disable,
2741         .reset = mv88e6185_g1_reset,
2742         .vtu_getnext = mv88e6185_g1_vtu_getnext,
2743         .vtu_loadpurge = mv88e6185_g1_vtu_loadpurge,
2744         .phylink_validate = mv88e6185_phylink_validate,
2745 };
2746
2747 static const struct mv88e6xxx_ops mv88e6097_ops = {
2748         /* MV88E6XXX_FAMILY_6097 */
2749         .ieee_pri_map = mv88e6085_g1_ieee_pri_map,
2750         .ip_pri_map = mv88e6085_g1_ip_pri_map,
2751         .irl_init_all = mv88e6352_g2_irl_init_all,
2752         .set_switch_mac = mv88e6xxx_g2_set_switch_mac,
2753         .phy_read = mv88e6xxx_g2_smi_phy_read,
2754         .phy_write = mv88e6xxx_g2_smi_phy_write,
2755         .port_set_link = mv88e6xxx_port_set_link,
2756         .port_set_duplex = mv88e6xxx_port_set_duplex,
2757         .port_set_speed = mv88e6185_port_set_speed,
2758         .port_tag_remap = mv88e6095_port_tag_remap,
2759         .port_set_frame_mode = mv88e6351_port_set_frame_mode,
2760         .port_set_egress_floods = mv88e6352_port_set_egress_floods,
2761         .port_set_ether_type = mv88e6351_port_set_ether_type,
2762         .port_set_jumbo_size = mv88e6165_port_set_jumbo_size,
2763         .port_egress_rate_limiting = mv88e6095_port_egress_rate_limiting,
2764         .port_pause_limit = mv88e6097_port_pause_limit,
2765         .port_disable_learn_limit = mv88e6xxx_port_disable_learn_limit,
2766         .port_disable_pri_override = mv88e6xxx_port_disable_pri_override,
2767         .port_link_state = mv88e6352_port_link_state,
2768         .stats_snapshot = mv88e6xxx_g1_stats_snapshot,
2769         .stats_set_histogram = mv88e6095_g1_stats_set_histogram,
2770         .stats_get_sset_count = mv88e6095_stats_get_sset_count,
2771         .stats_get_strings = mv88e6095_stats_get_strings,
2772         .stats_get_stats = mv88e6095_stats_get_stats,
2773         .set_cpu_port = mv88e6095_g1_set_cpu_port,
2774         .set_egress_port = mv88e6095_g1_set_egress_port,
2775         .watchdog_ops = &mv88e6097_watchdog_ops,
2776         .mgmt_rsvd2cpu = mv88e6352_g2_mgmt_rsvd2cpu,
2777         .pot_clear = mv88e6xxx_g2_pot_clear,
2778         .reset = mv88e6352_g1_reset,
2779         .rmu_disable = mv88e6085_g1_rmu_disable,
2780         .vtu_getnext = mv88e6352_g1_vtu_getnext,
2781         .vtu_loadpurge = mv88e6352_g1_vtu_loadpurge,
2782         .phylink_validate = mv88e6185_phylink_validate,
2783 };
2784
2785 static const struct mv88e6xxx_ops mv88e6123_ops = {
2786         /* MV88E6XXX_FAMILY_6165 */
2787         .ieee_pri_map = mv88e6085_g1_ieee_pri_map,
2788         .ip_pri_map = mv88e6085_g1_ip_pri_map,
2789         .irl_init_all = mv88e6352_g2_irl_init_all,
2790         .set_switch_mac = mv88e6xxx_g2_set_switch_mac,
2791         .phy_read = mv88e6xxx_g2_smi_phy_read,
2792         .phy_write = mv88e6xxx_g2_smi_phy_write,
2793         .port_set_link = mv88e6xxx_port_set_link,
2794         .port_set_duplex = mv88e6xxx_port_set_duplex,
2795         .port_set_speed = mv88e6185_port_set_speed,
2796         .port_set_frame_mode = mv88e6085_port_set_frame_mode,
2797         .port_set_egress_floods = mv88e6352_port_set_egress_floods,
2798         .port_disable_learn_limit = mv88e6xxx_port_disable_learn_limit,
2799         .port_disable_pri_override = mv88e6xxx_port_disable_pri_override,
2800         .port_link_state = mv88e6352_port_link_state,
2801         .stats_snapshot = mv88e6320_g1_stats_snapshot,
2802         .stats_set_histogram = mv88e6095_g1_stats_set_histogram,
2803         .stats_get_sset_count = mv88e6095_stats_get_sset_count,
2804         .stats_get_strings = mv88e6095_stats_get_strings,
2805         .stats_get_stats = mv88e6095_stats_get_stats,
2806         .set_cpu_port = mv88e6095_g1_set_cpu_port,
2807         .set_egress_port = mv88e6095_g1_set_egress_port,
2808         .watchdog_ops = &mv88e6097_watchdog_ops,
2809         .mgmt_rsvd2cpu = mv88e6352_g2_mgmt_rsvd2cpu,
2810         .pot_clear = mv88e6xxx_g2_pot_clear,
2811         .reset = mv88e6352_g1_reset,
2812         .vtu_getnext = mv88e6352_g1_vtu_getnext,
2813         .vtu_loadpurge = mv88e6352_g1_vtu_loadpurge,
2814         .phylink_validate = mv88e6185_phylink_validate,
2815 };
2816
2817 static const struct mv88e6xxx_ops mv88e6131_ops = {
2818         /* MV88E6XXX_FAMILY_6185 */
2819         .ieee_pri_map = mv88e6085_g1_ieee_pri_map,
2820         .ip_pri_map = mv88e6085_g1_ip_pri_map,
2821         .set_switch_mac = mv88e6xxx_g1_set_switch_mac,
2822         .phy_read = mv88e6185_phy_ppu_read,
2823         .phy_write = mv88e6185_phy_ppu_write,
2824         .port_set_link = mv88e6xxx_port_set_link,
2825         .port_set_duplex = mv88e6xxx_port_set_duplex,
2826         .port_set_speed = mv88e6185_port_set_speed,
2827         .port_tag_remap = mv88e6095_port_tag_remap,
2828         .port_set_frame_mode = mv88e6351_port_set_frame_mode,
2829         .port_set_egress_floods = mv88e6185_port_set_egress_floods,
2830         .port_set_ether_type = mv88e6351_port_set_ether_type,
2831         .port_set_upstream_port = mv88e6095_port_set_upstream_port,
2832         .port_set_jumbo_size = mv88e6165_port_set_jumbo_size,
2833         .port_egress_rate_limiting = mv88e6097_port_egress_rate_limiting,
2834         .port_pause_limit = mv88e6097_port_pause_limit,
2835         .port_set_pause = mv88e6185_port_set_pause,
2836         .port_link_state = mv88e6352_port_link_state,
2837         .stats_snapshot = mv88e6xxx_g1_stats_snapshot,
2838         .stats_set_histogram = mv88e6095_g1_stats_set_histogram,
2839         .stats_get_sset_count = mv88e6095_stats_get_sset_count,
2840         .stats_get_strings = mv88e6095_stats_get_strings,
2841         .stats_get_stats = mv88e6095_stats_get_stats,
2842         .set_cpu_port = mv88e6095_g1_set_cpu_port,
2843         .set_egress_port = mv88e6095_g1_set_egress_port,
2844         .watchdog_ops = &mv88e6097_watchdog_ops,
2845         .mgmt_rsvd2cpu = mv88e6185_g2_mgmt_rsvd2cpu,
2846         .ppu_enable = mv88e6185_g1_ppu_enable,
2847         .set_cascade_port = mv88e6185_g1_set_cascade_port,
2848         .ppu_disable = mv88e6185_g1_ppu_disable,
2849         .reset = mv88e6185_g1_reset,
2850         .vtu_getnext = mv88e6185_g1_vtu_getnext,
2851         .vtu_loadpurge = mv88e6185_g1_vtu_loadpurge,
2852         .phylink_validate = mv88e6185_phylink_validate,
2853 };
2854
2855 static const struct mv88e6xxx_ops mv88e6141_ops = {
2856         /* MV88E6XXX_FAMILY_6341 */
2857         .ieee_pri_map = mv88e6085_g1_ieee_pri_map,
2858         .ip_pri_map = mv88e6085_g1_ip_pri_map,
2859         .irl_init_all = mv88e6352_g2_irl_init_all,
2860         .get_eeprom = mv88e6xxx_g2_get_eeprom8,
2861         .set_eeprom = mv88e6xxx_g2_set_eeprom8,
2862         .set_switch_mac = mv88e6xxx_g2_set_switch_mac,
2863         .phy_read = mv88e6xxx_g2_smi_phy_read,
2864         .phy_write = mv88e6xxx_g2_smi_phy_write,
2865         .port_set_link = mv88e6xxx_port_set_link,
2866         .port_set_duplex = mv88e6xxx_port_set_duplex,
2867         .port_set_rgmii_delay = mv88e6390_port_set_rgmii_delay,
2868         .port_set_speed = mv88e6390_port_set_speed,
2869         .port_tag_remap = mv88e6095_port_tag_remap,
2870         .port_set_frame_mode = mv88e6351_port_set_frame_mode,
2871         .port_set_egress_floods = mv88e6352_port_set_egress_floods,
2872         .port_set_ether_type = mv88e6351_port_set_ether_type,
2873         .port_set_jumbo_size = mv88e6165_port_set_jumbo_size,
2874         .port_egress_rate_limiting = mv88e6097_port_egress_rate_limiting,
2875         .port_pause_limit = mv88e6097_port_pause_limit,
2876         .port_disable_learn_limit = mv88e6xxx_port_disable_learn_limit,
2877         .port_disable_pri_override = mv88e6xxx_port_disable_pri_override,
2878         .port_link_state = mv88e6352_port_link_state,
2879         .stats_snapshot = mv88e6390_g1_stats_snapshot,
2880         .stats_set_histogram = mv88e6095_g1_stats_set_histogram,
2881         .stats_get_sset_count = mv88e6320_stats_get_sset_count,
2882         .stats_get_strings = mv88e6320_stats_get_strings,
2883         .stats_get_stats = mv88e6390_stats_get_stats,
2884         .set_cpu_port = mv88e6390_g1_set_cpu_port,
2885         .set_egress_port = mv88e6390_g1_set_egress_port,
2886         .watchdog_ops = &mv88e6390_watchdog_ops,
2887         .mgmt_rsvd2cpu =  mv88e6390_g1_mgmt_rsvd2cpu,
2888         .pot_clear = mv88e6xxx_g2_pot_clear,
2889         .reset = mv88e6352_g1_reset,
2890         .vtu_getnext = mv88e6352_g1_vtu_getnext,
2891         .vtu_loadpurge = mv88e6352_g1_vtu_loadpurge,
2892         .serdes_power = mv88e6341_serdes_power,
2893         .gpio_ops = &mv88e6352_gpio_ops,
2894         .phylink_validate = mv88e6390_phylink_validate,
2895 };
2896
2897 static const struct mv88e6xxx_ops mv88e6161_ops = {
2898         /* MV88E6XXX_FAMILY_6165 */
2899         .ieee_pri_map = mv88e6085_g1_ieee_pri_map,
2900         .ip_pri_map = mv88e6085_g1_ip_pri_map,
2901         .irl_init_all = mv88e6352_g2_irl_init_all,
2902         .set_switch_mac = mv88e6xxx_g2_set_switch_mac,
2903         .phy_read = mv88e6xxx_g2_smi_phy_read,
2904         .phy_write = mv88e6xxx_g2_smi_phy_write,
2905         .port_set_link = mv88e6xxx_port_set_link,
2906         .port_set_duplex = mv88e6xxx_port_set_duplex,
2907         .port_set_speed = mv88e6185_port_set_speed,
2908         .port_tag_remap = mv88e6095_port_tag_remap,
2909         .port_set_frame_mode = mv88e6351_port_set_frame_mode,
2910         .port_set_egress_floods = mv88e6352_port_set_egress_floods,
2911         .port_set_ether_type = mv88e6351_port_set_ether_type,
2912         .port_set_jumbo_size = mv88e6165_port_set_jumbo_size,
2913         .port_egress_rate_limiting = mv88e6097_port_egress_rate_limiting,
2914         .port_pause_limit = mv88e6097_port_pause_limit,
2915         .port_disable_learn_limit = mv88e6xxx_port_disable_learn_limit,
2916         .port_disable_pri_override = mv88e6xxx_port_disable_pri_override,
2917         .port_link_state = mv88e6352_port_link_state,
2918         .stats_snapshot = mv88e6320_g1_stats_snapshot,
2919         .stats_set_histogram = mv88e6095_g1_stats_set_histogram,
2920         .stats_get_sset_count = mv88e6095_stats_get_sset_count,
2921         .stats_get_strings = mv88e6095_stats_get_strings,
2922         .stats_get_stats = mv88e6095_stats_get_stats,
2923         .set_cpu_port = mv88e6095_g1_set_cpu_port,
2924         .set_egress_port = mv88e6095_g1_set_egress_port,
2925         .watchdog_ops = &mv88e6097_watchdog_ops,
2926         .mgmt_rsvd2cpu = mv88e6352_g2_mgmt_rsvd2cpu,
2927         .pot_clear = mv88e6xxx_g2_pot_clear,
2928         .reset = mv88e6352_g1_reset,
2929         .vtu_getnext = mv88e6352_g1_vtu_getnext,
2930         .vtu_loadpurge = mv88e6352_g1_vtu_loadpurge,
2931         .avb_ops = &mv88e6165_avb_ops,
2932         .ptp_ops = &mv88e6165_ptp_ops,
2933         .phylink_validate = mv88e6185_phylink_validate,
2934 };
2935
2936 static const struct mv88e6xxx_ops mv88e6165_ops = {
2937         /* MV88E6XXX_FAMILY_6165 */
2938         .ieee_pri_map = mv88e6085_g1_ieee_pri_map,
2939         .ip_pri_map = mv88e6085_g1_ip_pri_map,
2940         .irl_init_all = mv88e6352_g2_irl_init_all,
2941         .set_switch_mac = mv88e6xxx_g2_set_switch_mac,
2942         .phy_read = mv88e6165_phy_read,
2943         .phy_write = mv88e6165_phy_write,
2944         .port_set_link = mv88e6xxx_port_set_link,
2945         .port_set_duplex = mv88e6xxx_port_set_duplex,
2946         .port_set_speed = mv88e6185_port_set_speed,
2947         .port_disable_learn_limit = mv88e6xxx_port_disable_learn_limit,
2948         .port_disable_pri_override = mv88e6xxx_port_disable_pri_override,
2949         .port_link_state = mv88e6352_port_link_state,
2950         .stats_snapshot = mv88e6xxx_g1_stats_snapshot,
2951         .stats_set_histogram = mv88e6095_g1_stats_set_histogram,
2952         .stats_get_sset_count = mv88e6095_stats_get_sset_count,
2953         .stats_get_strings = mv88e6095_stats_get_strings,
2954         .stats_get_stats = mv88e6095_stats_get_stats,
2955         .set_cpu_port = mv88e6095_g1_set_cpu_port,
2956         .set_egress_port = mv88e6095_g1_set_egress_port,
2957         .watchdog_ops = &mv88e6097_watchdog_ops,
2958         .mgmt_rsvd2cpu = mv88e6352_g2_mgmt_rsvd2cpu,
2959         .pot_clear = mv88e6xxx_g2_pot_clear,
2960         .reset = mv88e6352_g1_reset,
2961         .vtu_getnext = mv88e6352_g1_vtu_getnext,
2962         .vtu_loadpurge = mv88e6352_g1_vtu_loadpurge,
2963         .avb_ops = &mv88e6165_avb_ops,
2964         .ptp_ops = &mv88e6165_ptp_ops,
2965         .phylink_validate = mv88e6185_phylink_validate,
2966 };
2967
2968 static const struct mv88e6xxx_ops mv88e6171_ops = {
2969         /* MV88E6XXX_FAMILY_6351 */
2970         .ieee_pri_map = mv88e6085_g1_ieee_pri_map,
2971         .ip_pri_map = mv88e6085_g1_ip_pri_map,
2972         .irl_init_all = mv88e6352_g2_irl_init_all,
2973         .set_switch_mac = mv88e6xxx_g2_set_switch_mac,
2974         .phy_read = mv88e6xxx_g2_smi_phy_read,
2975         .phy_write = mv88e6xxx_g2_smi_phy_write,
2976         .port_set_link = mv88e6xxx_port_set_link,
2977         .port_set_duplex = mv88e6xxx_port_set_duplex,
2978         .port_set_rgmii_delay = mv88e6352_port_set_rgmii_delay,
2979         .port_set_speed = mv88e6185_port_set_speed,
2980         .port_tag_remap = mv88e6095_port_tag_remap,
2981         .port_set_frame_mode = mv88e6351_port_set_frame_mode,
2982         .port_set_egress_floods = mv88e6352_port_set_egress_floods,
2983         .port_set_ether_type = mv88e6351_port_set_ether_type,
2984         .port_set_jumbo_size = mv88e6165_port_set_jumbo_size,
2985         .port_egress_rate_limiting = mv88e6097_port_egress_rate_limiting,
2986         .port_pause_limit = mv88e6097_port_pause_limit,
2987         .port_disable_learn_limit = mv88e6xxx_port_disable_learn_limit,
2988         .port_disable_pri_override = mv88e6xxx_port_disable_pri_override,
2989         .port_link_state = mv88e6352_port_link_state,
2990         .stats_snapshot = mv88e6320_g1_stats_snapshot,
2991         .stats_set_histogram = mv88e6095_g1_stats_set_histogram,
2992         .stats_get_sset_count = mv88e6095_stats_get_sset_count,
2993         .stats_get_strings = mv88e6095_stats_get_strings,
2994         .stats_get_stats = mv88e6095_stats_get_stats,
2995         .set_cpu_port = mv88e6095_g1_set_cpu_port,
2996         .set_egress_port = mv88e6095_g1_set_egress_port,
2997         .watchdog_ops = &mv88e6097_watchdog_ops,
2998         .mgmt_rsvd2cpu = mv88e6352_g2_mgmt_rsvd2cpu,
2999         .pot_clear = mv88e6xxx_g2_pot_clear,
3000         .reset = mv88e6352_g1_reset,
3001         .vtu_getnext = mv88e6352_g1_vtu_getnext,
3002         .vtu_loadpurge = mv88e6352_g1_vtu_loadpurge,
3003         .phylink_validate = mv88e6185_phylink_validate,
3004 };
3005
3006 static const struct mv88e6xxx_ops mv88e6172_ops = {
3007         /* MV88E6XXX_FAMILY_6352 */
3008         .ieee_pri_map = mv88e6085_g1_ieee_pri_map,
3009         .ip_pri_map = mv88e6085_g1_ip_pri_map,
3010         .irl_init_all = mv88e6352_g2_irl_init_all,
3011         .get_eeprom = mv88e6xxx_g2_get_eeprom16,
3012         .set_eeprom = mv88e6xxx_g2_set_eeprom16,
3013         .set_switch_mac = mv88e6xxx_g2_set_switch_mac,
3014         .phy_read = mv88e6xxx_g2_smi_phy_read,
3015         .phy_write = mv88e6xxx_g2_smi_phy_write,
3016         .port_set_link = mv88e6xxx_port_set_link,
3017         .port_set_duplex = mv88e6xxx_port_set_duplex,
3018         .port_set_rgmii_delay = mv88e6352_port_set_rgmii_delay,
3019         .port_set_speed = mv88e6352_port_set_speed,
3020         .port_tag_remap = mv88e6095_port_tag_remap,
3021         .port_set_frame_mode = mv88e6351_port_set_frame_mode,
3022         .port_set_egress_floods = mv88e6352_port_set_egress_floods,
3023         .port_set_ether_type = mv88e6351_port_set_ether_type,
3024         .port_set_jumbo_size = mv88e6165_port_set_jumbo_size,
3025         .port_egress_rate_limiting = mv88e6097_port_egress_rate_limiting,
3026         .port_pause_limit = mv88e6097_port_pause_limit,
3027         .port_disable_learn_limit = mv88e6xxx_port_disable_learn_limit,
3028         .port_disable_pri_override = mv88e6xxx_port_disable_pri_override,
3029         .port_link_state = mv88e6352_port_link_state,
3030         .stats_snapshot = mv88e6320_g1_stats_snapshot,
3031         .stats_set_histogram = mv88e6095_g1_stats_set_histogram,
3032         .stats_get_sset_count = mv88e6095_stats_get_sset_count,
3033         .stats_get_strings = mv88e6095_stats_get_strings,
3034         .stats_get_stats = mv88e6095_stats_get_stats,
3035         .set_cpu_port = mv88e6095_g1_set_cpu_port,
3036         .set_egress_port = mv88e6095_g1_set_egress_port,
3037         .watchdog_ops = &mv88e6097_watchdog_ops,
3038         .mgmt_rsvd2cpu = mv88e6352_g2_mgmt_rsvd2cpu,
3039         .pot_clear = mv88e6xxx_g2_pot_clear,
3040         .reset = mv88e6352_g1_reset,
3041         .rmu_disable = mv88e6352_g1_rmu_disable,
3042         .vtu_getnext = mv88e6352_g1_vtu_getnext,
3043         .vtu_loadpurge = mv88e6352_g1_vtu_loadpurge,
3044         .serdes_power = mv88e6352_serdes_power,
3045         .gpio_ops = &mv88e6352_gpio_ops,
3046         .phylink_validate = mv88e6352_phylink_validate,
3047 };
3048
3049 static const struct mv88e6xxx_ops mv88e6175_ops = {
3050         /* MV88E6XXX_FAMILY_6351 */
3051         .ieee_pri_map = mv88e6085_g1_ieee_pri_map,
3052         .ip_pri_map = mv88e6085_g1_ip_pri_map,
3053         .irl_init_all = mv88e6352_g2_irl_init_all,
3054         .set_switch_mac = mv88e6xxx_g2_set_switch_mac,
3055         .phy_read = mv88e6xxx_g2_smi_phy_read,
3056         .phy_write = mv88e6xxx_g2_smi_phy_write,
3057         .port_set_link = mv88e6xxx_port_set_link,
3058         .port_set_duplex = mv88e6xxx_port_set_duplex,
3059         .port_set_rgmii_delay = mv88e6352_port_set_rgmii_delay,
3060         .port_set_speed = mv88e6185_port_set_speed,
3061         .port_tag_remap = mv88e6095_port_tag_remap,
3062         .port_set_frame_mode = mv88e6351_port_set_frame_mode,
3063         .port_set_egress_floods = mv88e6352_port_set_egress_floods,
3064         .port_set_ether_type = mv88e6351_port_set_ether_type,
3065         .port_set_jumbo_size = mv88e6165_port_set_jumbo_size,
3066         .port_egress_rate_limiting = mv88e6097_port_egress_rate_limiting,
3067         .port_pause_limit = mv88e6097_port_pause_limit,
3068         .port_disable_learn_limit = mv88e6xxx_port_disable_learn_limit,
3069         .port_disable_pri_override = mv88e6xxx_port_disable_pri_override,
3070         .port_link_state = mv88e6352_port_link_state,
3071         .stats_snapshot = mv88e6320_g1_stats_snapshot,
3072         .stats_set_histogram = mv88e6095_g1_stats_set_histogram,
3073         .stats_get_sset_count = mv88e6095_stats_get_sset_count,
3074         .stats_get_strings = mv88e6095_stats_get_strings,
3075         .stats_get_stats = mv88e6095_stats_get_stats,
3076         .set_cpu_port = mv88e6095_g1_set_cpu_port,
3077         .set_egress_port = mv88e6095_g1_set_egress_port,
3078         .watchdog_ops = &mv88e6097_watchdog_ops,
3079         .mgmt_rsvd2cpu = mv88e6352_g2_mgmt_rsvd2cpu,
3080         .pot_clear = mv88e6xxx_g2_pot_clear,
3081         .reset = mv88e6352_g1_reset,
3082         .vtu_getnext = mv88e6352_g1_vtu_getnext,
3083         .vtu_loadpurge = mv88e6352_g1_vtu_loadpurge,
3084         .phylink_validate = mv88e6185_phylink_validate,
3085 };
3086
3087 static const struct mv88e6xxx_ops mv88e6176_ops = {
3088         /* MV88E6XXX_FAMILY_6352 */
3089         .ieee_pri_map = mv88e6085_g1_ieee_pri_map,
3090         .ip_pri_map = mv88e6085_g1_ip_pri_map,
3091         .irl_init_all = mv88e6352_g2_irl_init_all,
3092         .get_eeprom = mv88e6xxx_g2_get_eeprom16,
3093         .set_eeprom = mv88e6xxx_g2_set_eeprom16,
3094         .set_switch_mac = mv88e6xxx_g2_set_switch_mac,
3095         .phy_read = mv88e6xxx_g2_smi_phy_read,
3096         .phy_write = mv88e6xxx_g2_smi_phy_write,
3097         .port_set_link = mv88e6xxx_port_set_link,
3098         .port_set_duplex = mv88e6xxx_port_set_duplex,
3099         .port_set_rgmii_delay = mv88e6352_port_set_rgmii_delay,
3100         .port_set_speed = mv88e6352_port_set_speed,
3101         .port_tag_remap = mv88e6095_port_tag_remap,
3102         .port_set_frame_mode = mv88e6351_port_set_frame_mode,
3103         .port_set_egress_floods = mv88e6352_port_set_egress_floods,
3104         .port_set_ether_type = mv88e6351_port_set_ether_type,
3105         .port_set_jumbo_size = mv88e6165_port_set_jumbo_size,
3106         .port_egress_rate_limiting = mv88e6097_port_egress_rate_limiting,
3107         .port_pause_limit = mv88e6097_port_pause_limit,
3108         .port_disable_learn_limit = mv88e6xxx_port_disable_learn_limit,
3109         .port_disable_pri_override = mv88e6xxx_port_disable_pri_override,
3110         .port_link_state = mv88e6352_port_link_state,
3111         .stats_snapshot = mv88e6320_g1_stats_snapshot,
3112         .stats_set_histogram = mv88e6095_g1_stats_set_histogram,
3113         .stats_get_sset_count = mv88e6095_stats_get_sset_count,
3114         .stats_get_strings = mv88e6095_stats_get_strings,
3115         .stats_get_stats = mv88e6095_stats_get_stats,
3116         .set_cpu_port = mv88e6095_g1_set_cpu_port,
3117         .set_egress_port = mv88e6095_g1_set_egress_port,
3118         .watchdog_ops = &mv88e6097_watchdog_ops,
3119         .mgmt_rsvd2cpu = mv88e6352_g2_mgmt_rsvd2cpu,
3120         .pot_clear = mv88e6xxx_g2_pot_clear,
3121         .reset = mv88e6352_g1_reset,
3122         .rmu_disable = mv88e6352_g1_rmu_disable,
3123         .vtu_getnext = mv88e6352_g1_vtu_getnext,
3124         .vtu_loadpurge = mv88e6352_g1_vtu_loadpurge,
3125         .serdes_power = mv88e6352_serdes_power,
3126         .gpio_ops = &mv88e6352_gpio_ops,
3127         .phylink_validate = mv88e6352_phylink_validate,
3128 };
3129
3130 static const struct mv88e6xxx_ops mv88e6185_ops = {
3131         /* MV88E6XXX_FAMILY_6185 */
3132         .ieee_pri_map = mv88e6085_g1_ieee_pri_map,
3133         .ip_pri_map = mv88e6085_g1_ip_pri_map,
3134         .set_switch_mac = mv88e6xxx_g1_set_switch_mac,
3135         .phy_read = mv88e6185_phy_ppu_read,
3136         .phy_write = mv88e6185_phy_ppu_write,
3137         .port_set_link = mv88e6xxx_port_set_link,
3138         .port_set_duplex = mv88e6xxx_port_set_duplex,
3139         .port_set_speed = mv88e6185_port_set_speed,
3140         .port_set_frame_mode = mv88e6085_port_set_frame_mode,
3141         .port_set_egress_floods = mv88e6185_port_set_egress_floods,
3142         .port_egress_rate_limiting = mv88e6095_port_egress_rate_limiting,
3143         .port_set_upstream_port = mv88e6095_port_set_upstream_port,
3144         .port_set_pause = mv88e6185_port_set_pause,
3145         .port_link_state = mv88e6185_port_link_state,
3146         .stats_snapshot = mv88e6xxx_g1_stats_snapshot,
3147         .stats_set_histogram = mv88e6095_g1_stats_set_histogram,
3148         .stats_get_sset_count = mv88e6095_stats_get_sset_count,
3149         .stats_get_strings = mv88e6095_stats_get_strings,
3150         .stats_get_stats = mv88e6095_stats_get_stats,
3151         .set_cpu_port = mv88e6095_g1_set_cpu_port,
3152         .set_egress_port = mv88e6095_g1_set_egress_port,
3153         .watchdog_ops = &mv88e6097_watchdog_ops,
3154         .mgmt_rsvd2cpu = mv88e6185_g2_mgmt_rsvd2cpu,
3155         .set_cascade_port = mv88e6185_g1_set_cascade_port,
3156         .ppu_enable = mv88e6185_g1_ppu_enable,
3157         .ppu_disable = mv88e6185_g1_ppu_disable,
3158         .reset = mv88e6185_g1_reset,
3159         .vtu_getnext = mv88e6185_g1_vtu_getnext,
3160         .vtu_loadpurge = mv88e6185_g1_vtu_loadpurge,
3161         .phylink_validate = mv88e6185_phylink_validate,
3162 };
3163
3164 static const struct mv88e6xxx_ops mv88e6190_ops = {
3165         /* MV88E6XXX_FAMILY_6390 */
3166         .irl_init_all = mv88e6390_g2_irl_init_all,
3167         .get_eeprom = mv88e6xxx_g2_get_eeprom8,
3168         .set_eeprom = mv88e6xxx_g2_set_eeprom8,
3169         .set_switch_mac = mv88e6xxx_g2_set_switch_mac,
3170         .phy_read = mv88e6xxx_g2_smi_phy_read,
3171         .phy_write = mv88e6xxx_g2_smi_phy_write,
3172         .port_set_link = mv88e6xxx_port_set_link,
3173         .port_set_duplex = mv88e6xxx_port_set_duplex,
3174         .port_set_rgmii_delay = mv88e6390_port_set_rgmii_delay,
3175         .port_set_speed = mv88e6390_port_set_speed,
3176         .port_tag_remap = mv88e6390_port_tag_remap,
3177         .port_set_frame_mode = mv88e6351_port_set_frame_mode,
3178         .port_set_egress_floods = mv88e6352_port_set_egress_floods,
3179         .port_set_ether_type = mv88e6351_port_set_ether_type,
3180         .port_pause_limit = mv88e6390_port_pause_limit,
3181         .port_disable_learn_limit = mv88e6xxx_port_disable_learn_limit,
3182         .port_disable_pri_override = mv88e6xxx_port_disable_pri_override,
3183         .port_link_state = mv88e6352_port_link_state,
3184         .stats_snapshot = mv88e6390_g1_stats_snapshot,
3185         .stats_set_histogram = mv88e6390_g1_stats_set_histogram,
3186         .stats_get_sset_count = mv88e6320_stats_get_sset_count,
3187         .stats_get_strings = mv88e6320_stats_get_strings,
3188         .stats_get_stats = mv88e6390_stats_get_stats,
3189         .set_cpu_port = mv88e6390_g1_set_cpu_port,
3190         .set_egress_port = mv88e6390_g1_set_egress_port,
3191         .watchdog_ops = &mv88e6390_watchdog_ops,
3192         .mgmt_rsvd2cpu = mv88e6390_g1_mgmt_rsvd2cpu,
3193         .pot_clear = mv88e6xxx_g2_pot_clear,
3194         .reset = mv88e6352_g1_reset,
3195         .rmu_disable = mv88e6390_g1_rmu_disable,
3196         .vtu_getnext = mv88e6390_g1_vtu_getnext,
3197         .vtu_loadpurge = mv88e6390_g1_vtu_loadpurge,
3198         .serdes_power = mv88e6390_serdes_power,
3199         .gpio_ops = &mv88e6352_gpio_ops,
3200         .phylink_validate = mv88e6390_phylink_validate,
3201 };
3202
3203 static const struct mv88e6xxx_ops mv88e6190x_ops = {
3204         /* MV88E6XXX_FAMILY_6390 */
3205         .irl_init_all = mv88e6390_g2_irl_init_all,
3206         .get_eeprom = mv88e6xxx_g2_get_eeprom8,
3207         .set_eeprom = mv88e6xxx_g2_set_eeprom8,
3208         .set_switch_mac = mv88e6xxx_g2_set_switch_mac,
3209         .phy_read = mv88e6xxx_g2_smi_phy_read,
3210         .phy_write = mv88e6xxx_g2_smi_phy_write,
3211         .port_set_link = mv88e6xxx_port_set_link,
3212         .port_set_duplex = mv88e6xxx_port_set_duplex,
3213         .port_set_rgmii_delay = mv88e6390_port_set_rgmii_delay,
3214         .port_set_speed = mv88e6390x_port_set_speed,
3215         .port_tag_remap = mv88e6390_port_tag_remap,
3216         .port_set_frame_mode = mv88e6351_port_set_frame_mode,
3217         .port_set_egress_floods = mv88e6352_port_set_egress_floods,
3218         .port_set_ether_type = mv88e6351_port_set_ether_type,
3219         .port_pause_limit = mv88e6390_port_pause_limit,
3220         .port_disable_learn_limit = mv88e6xxx_port_disable_learn_limit,
3221         .port_disable_pri_override = mv88e6xxx_port_disable_pri_override,
3222         .port_link_state = mv88e6352_port_link_state,
3223         .stats_snapshot = mv88e6390_g1_stats_snapshot,
3224         .stats_set_histogram = mv88e6390_g1_stats_set_histogram,
3225         .stats_get_sset_count = mv88e6320_stats_get_sset_count,
3226         .stats_get_strings = mv88e6320_stats_get_strings,
3227         .stats_get_stats = mv88e6390_stats_get_stats,
3228         .set_cpu_port = mv88e6390_g1_set_cpu_port,
3229         .set_egress_port = mv88e6390_g1_set_egress_port,
3230         .watchdog_ops = &mv88e6390_watchdog_ops,
3231         .mgmt_rsvd2cpu = mv88e6390_g1_mgmt_rsvd2cpu,
3232         .pot_clear = mv88e6xxx_g2_pot_clear,
3233         .reset = mv88e6352_g1_reset,
3234         .rmu_disable = mv88e6390_g1_rmu_disable,
3235         .vtu_getnext = mv88e6390_g1_vtu_getnext,
3236         .vtu_loadpurge = mv88e6390_g1_vtu_loadpurge,
3237         .serdes_power = mv88e6390_serdes_power,
3238         .gpio_ops = &mv88e6352_gpio_ops,
3239         .phylink_validate = mv88e6390x_phylink_validate,
3240 };
3241
3242 static const struct mv88e6xxx_ops mv88e6191_ops = {
3243         /* MV88E6XXX_FAMILY_6390 */
3244         .irl_init_all = mv88e6390_g2_irl_init_all,
3245         .get_eeprom = mv88e6xxx_g2_get_eeprom8,
3246         .set_eeprom = mv88e6xxx_g2_set_eeprom8,
3247         .set_switch_mac = mv88e6xxx_g2_set_switch_mac,
3248         .phy_read = mv88e6xxx_g2_smi_phy_read,
3249         .phy_write = mv88e6xxx_g2_smi_phy_write,
3250         .port_set_link = mv88e6xxx_port_set_link,
3251         .port_set_duplex = mv88e6xxx_port_set_duplex,
3252         .port_set_rgmii_delay = mv88e6390_port_set_rgmii_delay,
3253         .port_set_speed = mv88e6390_port_set_speed,
3254         .port_tag_remap = mv88e6390_port_tag_remap,
3255         .port_set_frame_mode = mv88e6351_port_set_frame_mode,
3256         .port_set_egress_floods = mv88e6352_port_set_egress_floods,
3257         .port_set_ether_type = mv88e6351_port_set_ether_type,
3258         .port_pause_limit = mv88e6390_port_pause_limit,
3259         .port_disable_learn_limit = mv88e6xxx_port_disable_learn_limit,
3260         .port_disable_pri_override = mv88e6xxx_port_disable_pri_override,
3261         .port_link_state = mv88e6352_port_link_state,
3262         .stats_snapshot = mv88e6390_g1_stats_snapshot,
3263         .stats_set_histogram = mv88e6390_g1_stats_set_histogram,
3264         .stats_get_sset_count = mv88e6320_stats_get_sset_count,
3265         .stats_get_strings = mv88e6320_stats_get_strings,
3266         .stats_get_stats = mv88e6390_stats_get_stats,
3267         .set_cpu_port = mv88e6390_g1_set_cpu_port,
3268         .set_egress_port = mv88e6390_g1_set_egress_port,
3269         .watchdog_ops = &mv88e6390_watchdog_ops,
3270         .mgmt_rsvd2cpu = mv88e6390_g1_mgmt_rsvd2cpu,
3271         .pot_clear = mv88e6xxx_g2_pot_clear,
3272         .reset = mv88e6352_g1_reset,
3273         .rmu_disable = mv88e6390_g1_rmu_disable,
3274         .vtu_getnext = mv88e6390_g1_vtu_getnext,
3275         .vtu_loadpurge = mv88e6390_g1_vtu_loadpurge,
3276         .serdes_power = mv88e6390_serdes_power,
3277         .avb_ops = &mv88e6390_avb_ops,
3278         .ptp_ops = &mv88e6352_ptp_ops,
3279         .phylink_validate = mv88e6390_phylink_validate,
3280 };
3281
3282 static const struct mv88e6xxx_ops mv88e6240_ops = {
3283         /* MV88E6XXX_FAMILY_6352 */
3284         .ieee_pri_map = mv88e6085_g1_ieee_pri_map,
3285         .ip_pri_map = mv88e6085_g1_ip_pri_map,
3286         .irl_init_all = mv88e6352_g2_irl_init_all,
3287         .get_eeprom = mv88e6xxx_g2_get_eeprom16,
3288         .set_eeprom = mv88e6xxx_g2_set_eeprom16,
3289         .set_switch_mac = mv88e6xxx_g2_set_switch_mac,
3290         .phy_read = mv88e6xxx_g2_smi_phy_read,
3291         .phy_write = mv88e6xxx_g2_smi_phy_write,
3292         .port_set_link = mv88e6xxx_port_set_link,
3293         .port_set_duplex = mv88e6xxx_port_set_duplex,
3294         .port_set_rgmii_delay = mv88e6352_port_set_rgmii_delay,
3295         .port_set_speed = mv88e6352_port_set_speed,
3296         .port_tag_remap = mv88e6095_port_tag_remap,
3297         .port_set_frame_mode = mv88e6351_port_set_frame_mode,
3298         .port_set_egress_floods = mv88e6352_port_set_egress_floods,
3299         .port_set_ether_type = mv88e6351_port_set_ether_type,
3300         .port_set_jumbo_size = mv88e6165_port_set_jumbo_size,
3301         .port_egress_rate_limiting = mv88e6097_port_egress_rate_limiting,
3302         .port_pause_limit = mv88e6097_port_pause_limit,
3303         .port_disable_learn_limit = mv88e6xxx_port_disable_learn_limit,
3304         .port_disable_pri_override = mv88e6xxx_port_disable_pri_override,
3305         .port_link_state = mv88e6352_port_link_state,
3306         .stats_snapshot = mv88e6320_g1_stats_snapshot,
3307         .stats_set_histogram = mv88e6095_g1_stats_set_histogram,
3308         .stats_get_sset_count = mv88e6095_stats_get_sset_count,
3309         .stats_get_strings = mv88e6095_stats_get_strings,
3310         .stats_get_stats = mv88e6095_stats_get_stats,
3311         .set_cpu_port = mv88e6095_g1_set_cpu_port,
3312         .set_egress_port = mv88e6095_g1_set_egress_port,
3313         .watchdog_ops = &mv88e6097_watchdog_ops,
3314         .mgmt_rsvd2cpu = mv88e6352_g2_mgmt_rsvd2cpu,
3315         .pot_clear = mv88e6xxx_g2_pot_clear,
3316         .reset = mv88e6352_g1_reset,
3317         .rmu_disable = mv88e6352_g1_rmu_disable,
3318         .vtu_getnext = mv88e6352_g1_vtu_getnext,
3319         .vtu_loadpurge = mv88e6352_g1_vtu_loadpurge,
3320         .serdes_power = mv88e6352_serdes_power,
3321         .gpio_ops = &mv88e6352_gpio_ops,
3322         .avb_ops = &mv88e6352_avb_ops,
3323         .ptp_ops = &mv88e6352_ptp_ops,
3324         .phylink_validate = mv88e6352_phylink_validate,
3325 };
3326
3327 static const struct mv88e6xxx_ops mv88e6290_ops = {
3328         /* MV88E6XXX_FAMILY_6390 */
3329         .irl_init_all = mv88e6390_g2_irl_init_all,
3330         .get_eeprom = mv88e6xxx_g2_get_eeprom8,
3331         .set_eeprom = mv88e6xxx_g2_set_eeprom8,
3332         .set_switch_mac = mv88e6xxx_g2_set_switch_mac,
3333         .phy_read = mv88e6xxx_g2_smi_phy_read,
3334         .phy_write = mv88e6xxx_g2_smi_phy_write,
3335         .port_set_link = mv88e6xxx_port_set_link,
3336         .port_set_duplex = mv88e6xxx_port_set_duplex,
3337         .port_set_rgmii_delay = mv88e6390_port_set_rgmii_delay,
3338         .port_set_speed = mv88e6390_port_set_speed,
3339         .port_tag_remap = mv88e6390_port_tag_remap,
3340         .port_set_frame_mode = mv88e6351_port_set_frame_mode,
3341         .port_set_egress_floods = mv88e6352_port_set_egress_floods,
3342         .port_set_ether_type = mv88e6351_port_set_ether_type,
3343         .port_pause_limit = mv88e6390_port_pause_limit,
3344         .port_set_cmode = mv88e6390x_port_set_cmode,
3345         .port_disable_learn_limit = mv88e6xxx_port_disable_learn_limit,
3346         .port_disable_pri_override = mv88e6xxx_port_disable_pri_override,
3347         .port_link_state = mv88e6352_port_link_state,
3348         .stats_snapshot = mv88e6390_g1_stats_snapshot,
3349         .stats_set_histogram = mv88e6390_g1_stats_set_histogram,
3350         .stats_get_sset_count = mv88e6320_stats_get_sset_count,
3351         .stats_get_strings = mv88e6320_stats_get_strings,
3352         .stats_get_stats = mv88e6390_stats_get_stats,
3353         .set_cpu_port = mv88e6390_g1_set_cpu_port,
3354         .set_egress_port = mv88e6390_g1_set_egress_port,
3355         .watchdog_ops = &mv88e6390_watchdog_ops,
3356         .mgmt_rsvd2cpu = mv88e6390_g1_mgmt_rsvd2cpu,
3357         .pot_clear = mv88e6xxx_g2_pot_clear,
3358         .reset = mv88e6352_g1_reset,
3359         .rmu_disable = mv88e6390_g1_rmu_disable,
3360         .vtu_getnext = mv88e6390_g1_vtu_getnext,
3361         .vtu_loadpurge = mv88e6390_g1_vtu_loadpurge,
3362         .serdes_power = mv88e6390_serdes_power,
3363         .gpio_ops = &mv88e6352_gpio_ops,
3364         .avb_ops = &mv88e6390_avb_ops,
3365         .ptp_ops = &mv88e6352_ptp_ops,
3366         .phylink_validate = mv88e6390_phylink_validate,
3367 };
3368
3369 static const struct mv88e6xxx_ops mv88e6320_ops = {
3370         /* MV88E6XXX_FAMILY_6320 */
3371         .ieee_pri_map = mv88e6085_g1_ieee_pri_map,
3372         .ip_pri_map = mv88e6085_g1_ip_pri_map,
3373         .irl_init_all = mv88e6352_g2_irl_init_all,
3374         .get_eeprom = mv88e6xxx_g2_get_eeprom16,
3375         .set_eeprom = mv88e6xxx_g2_set_eeprom16,
3376         .set_switch_mac = mv88e6xxx_g2_set_switch_mac,
3377         .phy_read = mv88e6xxx_g2_smi_phy_read,
3378         .phy_write = mv88e6xxx_g2_smi_phy_write,
3379         .port_set_link = mv88e6xxx_port_set_link,
3380         .port_set_duplex = mv88e6xxx_port_set_duplex,
3381         .port_set_speed = mv88e6185_port_set_speed,
3382         .port_tag_remap = mv88e6095_port_tag_remap,
3383         .port_set_frame_mode = mv88e6351_port_set_frame_mode,
3384         .port_set_egress_floods = mv88e6352_port_set_egress_floods,
3385         .port_set_ether_type = mv88e6351_port_set_ether_type,
3386         .port_set_jumbo_size = mv88e6165_port_set_jumbo_size,
3387         .port_egress_rate_limiting = mv88e6097_port_egress_rate_limiting,
3388         .port_pause_limit = mv88e6097_port_pause_limit,
3389         .port_disable_learn_limit = mv88e6xxx_port_disable_learn_limit,
3390         .port_disable_pri_override = mv88e6xxx_port_disable_pri_override,
3391         .port_link_state = mv88e6352_port_link_state,
3392         .stats_snapshot = mv88e6320_g1_stats_snapshot,
3393         .stats_set_histogram = mv88e6095_g1_stats_set_histogram,
3394         .stats_get_sset_count = mv88e6320_stats_get_sset_count,
3395         .stats_get_strings = mv88e6320_stats_get_strings,
3396         .stats_get_stats = mv88e6320_stats_get_stats,
3397         .set_cpu_port = mv88e6095_g1_set_cpu_port,
3398         .set_egress_port = mv88e6095_g1_set_egress_port,
3399         .mgmt_rsvd2cpu = mv88e6352_g2_mgmt_rsvd2cpu,
3400         .pot_clear = mv88e6xxx_g2_pot_clear,
3401         .reset = mv88e6352_g1_reset,
3402         .vtu_getnext = mv88e6185_g1_vtu_getnext,
3403         .vtu_loadpurge = mv88e6185_g1_vtu_loadpurge,
3404         .gpio_ops = &mv88e6352_gpio_ops,
3405         .avb_ops = &mv88e6352_avb_ops,
3406         .ptp_ops = &mv88e6352_ptp_ops,
3407         .phylink_validate = mv88e6185_phylink_validate,
3408 };
3409
3410 static const struct mv88e6xxx_ops mv88e6321_ops = {
3411         /* MV88E6XXX_FAMILY_6320 */
3412         .ieee_pri_map = mv88e6085_g1_ieee_pri_map,
3413         .ip_pri_map = mv88e6085_g1_ip_pri_map,
3414         .irl_init_all = mv88e6352_g2_irl_init_all,
3415         .get_eeprom = mv88e6xxx_g2_get_eeprom16,
3416         .set_eeprom = mv88e6xxx_g2_set_eeprom16,
3417         .set_switch_mac = mv88e6xxx_g2_set_switch_mac,
3418         .phy_read = mv88e6xxx_g2_smi_phy_read,
3419         .phy_write = mv88e6xxx_g2_smi_phy_write,
3420         .port_set_link = mv88e6xxx_port_set_link,
3421         .port_set_duplex = mv88e6xxx_port_set_duplex,
3422         .port_set_speed = mv88e6185_port_set_speed,
3423         .port_tag_remap = mv88e6095_port_tag_remap,
3424         .port_set_frame_mode = mv88e6351_port_set_frame_mode,
3425         .port_set_egress_floods = mv88e6352_port_set_egress_floods,
3426         .port_set_ether_type = mv88e6351_port_set_ether_type,
3427         .port_set_jumbo_size = mv88e6165_port_set_jumbo_size,
3428         .port_egress_rate_limiting = mv88e6097_port_egress_rate_limiting,
3429         .port_pause_limit = mv88e6097_port_pause_limit,
3430         .port_disable_learn_limit = mv88e6xxx_port_disable_learn_limit,
3431         .port_disable_pri_override = mv88e6xxx_port_disable_pri_override,
3432         .port_link_state = mv88e6352_port_link_state,
3433         .stats_snapshot = mv88e6320_g1_stats_snapshot,
3434         .stats_set_histogram = mv88e6095_g1_stats_set_histogram,
3435         .stats_get_sset_count = mv88e6320_stats_get_sset_count,
3436         .stats_get_strings = mv88e6320_stats_get_strings,
3437         .stats_get_stats = mv88e6320_stats_get_stats,
3438         .set_cpu_port = mv88e6095_g1_set_cpu_port,
3439         .set_egress_port = mv88e6095_g1_set_egress_port,
3440         .reset = mv88e6352_g1_reset,
3441         .vtu_getnext = mv88e6185_g1_vtu_getnext,
3442         .vtu_loadpurge = mv88e6185_g1_vtu_loadpurge,
3443         .gpio_ops = &mv88e6352_gpio_ops,
3444         .avb_ops = &mv88e6352_avb_ops,
3445         .ptp_ops = &mv88e6352_ptp_ops,
3446         .phylink_validate = mv88e6185_phylink_validate,
3447 };
3448
3449 static const struct mv88e6xxx_ops mv88e6341_ops = {
3450         /* MV88E6XXX_FAMILY_6341 */
3451         .ieee_pri_map = mv88e6085_g1_ieee_pri_map,
3452         .ip_pri_map = mv88e6085_g1_ip_pri_map,
3453         .irl_init_all = mv88e6352_g2_irl_init_all,
3454         .get_eeprom = mv88e6xxx_g2_get_eeprom8,
3455         .set_eeprom = mv88e6xxx_g2_set_eeprom8,
3456         .set_switch_mac = mv88e6xxx_g2_set_switch_mac,
3457         .phy_read = mv88e6xxx_g2_smi_phy_read,
3458         .phy_write = mv88e6xxx_g2_smi_phy_write,
3459         .port_set_link = mv88e6xxx_port_set_link,
3460         .port_set_duplex = mv88e6xxx_port_set_duplex,
3461         .port_set_rgmii_delay = mv88e6390_port_set_rgmii_delay,
3462         .port_set_speed = mv88e6390_port_set_speed,
3463         .port_tag_remap = mv88e6095_port_tag_remap,
3464         .port_set_frame_mode = mv88e6351_port_set_frame_mode,
3465         .port_set_egress_floods = mv88e6352_port_set_egress_floods,
3466         .port_set_ether_type = mv88e6351_port_set_ether_type,
3467         .port_set_jumbo_size = mv88e6165_port_set_jumbo_size,
3468         .port_egress_rate_limiting = mv88e6097_port_egress_rate_limiting,
3469         .port_pause_limit = mv88e6097_port_pause_limit,
3470         .port_disable_learn_limit = mv88e6xxx_port_disable_learn_limit,
3471         .port_disable_pri_override = mv88e6xxx_port_disable_pri_override,
3472         .port_link_state = mv88e6352_port_link_state,
3473         .stats_snapshot = mv88e6390_g1_stats_snapshot,
3474         .stats_set_histogram = mv88e6095_g1_stats_set_histogram,
3475         .stats_get_sset_count = mv88e6320_stats_get_sset_count,
3476         .stats_get_strings = mv88e6320_stats_get_strings,
3477         .stats_get_stats = mv88e6390_stats_get_stats,
3478         .set_cpu_port = mv88e6390_g1_set_cpu_port,
3479         .set_egress_port = mv88e6390_g1_set_egress_port,
3480         .watchdog_ops = &mv88e6390_watchdog_ops,
3481         .mgmt_rsvd2cpu =  mv88e6390_g1_mgmt_rsvd2cpu,
3482         .pot_clear = mv88e6xxx_g2_pot_clear,
3483         .reset = mv88e6352_g1_reset,
3484         .vtu_getnext = mv88e6352_g1_vtu_getnext,
3485         .vtu_loadpurge = mv88e6352_g1_vtu_loadpurge,
3486         .serdes_power = mv88e6341_serdes_power,
3487         .gpio_ops = &mv88e6352_gpio_ops,
3488         .avb_ops = &mv88e6390_avb_ops,
3489         .ptp_ops = &mv88e6352_ptp_ops,
3490         .phylink_validate = mv88e6390_phylink_validate,
3491 };
3492
3493 static const struct mv88e6xxx_ops mv88e6350_ops = {
3494         /* MV88E6XXX_FAMILY_6351 */
3495         .ieee_pri_map = mv88e6085_g1_ieee_pri_map,
3496         .ip_pri_map = mv88e6085_g1_ip_pri_map,
3497         .irl_init_all = mv88e6352_g2_irl_init_all,
3498         .set_switch_mac = mv88e6xxx_g2_set_switch_mac,
3499         .phy_read = mv88e6xxx_g2_smi_phy_read,
3500         .phy_write = mv88e6xxx_g2_smi_phy_write,
3501         .port_set_link = mv88e6xxx_port_set_link,
3502         .port_set_duplex = mv88e6xxx_port_set_duplex,
3503         .port_set_rgmii_delay = mv88e6352_port_set_rgmii_delay,
3504         .port_set_speed = mv88e6185_port_set_speed,
3505         .port_tag_remap = mv88e6095_port_tag_remap,
3506         .port_set_frame_mode = mv88e6351_port_set_frame_mode,
3507         .port_set_egress_floods = mv88e6352_port_set_egress_floods,
3508         .port_set_ether_type = mv88e6351_port_set_ether_type,
3509         .port_set_jumbo_size = mv88e6165_port_set_jumbo_size,
3510         .port_egress_rate_limiting = mv88e6097_port_egress_rate_limiting,
3511         .port_pause_limit = mv88e6097_port_pause_limit,
3512         .port_disable_learn_limit = mv88e6xxx_port_disable_learn_limit,
3513         .port_disable_pri_override = mv88e6xxx_port_disable_pri_override,
3514         .port_link_state = mv88e6352_port_link_state,
3515         .stats_snapshot = mv88e6320_g1_stats_snapshot,
3516         .stats_set_histogram = mv88e6095_g1_stats_set_histogram,
3517         .stats_get_sset_count = mv88e6095_stats_get_sset_count,
3518         .stats_get_strings = mv88e6095_stats_get_strings,
3519         .stats_get_stats = mv88e6095_stats_get_stats,
3520         .set_cpu_port = mv88e6095_g1_set_cpu_port,
3521         .set_egress_port = mv88e6095_g1_set_egress_port,
3522         .watchdog_ops = &mv88e6097_watchdog_ops,
3523         .mgmt_rsvd2cpu = mv88e6352_g2_mgmt_rsvd2cpu,
3524         .pot_clear = mv88e6xxx_g2_pot_clear,
3525         .reset = mv88e6352_g1_reset,
3526         .vtu_getnext = mv88e6352_g1_vtu_getnext,
3527         .vtu_loadpurge = mv88e6352_g1_vtu_loadpurge,
3528         .phylink_validate = mv88e6185_phylink_validate,
3529 };
3530
3531 static const struct mv88e6xxx_ops mv88e6351_ops = {
3532         /* MV88E6XXX_FAMILY_6351 */
3533         .ieee_pri_map = mv88e6085_g1_ieee_pri_map,
3534         .ip_pri_map = mv88e6085_g1_ip_pri_map,
3535         .irl_init_all = mv88e6352_g2_irl_init_all,
3536         .set_switch_mac = mv88e6xxx_g2_set_switch_mac,
3537         .phy_read = mv88e6xxx_g2_smi_phy_read,
3538         .phy_write = mv88e6xxx_g2_smi_phy_write,
3539         .port_set_link = mv88e6xxx_port_set_link,
3540         .port_set_duplex = mv88e6xxx_port_set_duplex,
3541         .port_set_rgmii_delay = mv88e6352_port_set_rgmii_delay,
3542         .port_set_speed = mv88e6185_port_set_speed,
3543         .port_tag_remap = mv88e6095_port_tag_remap,
3544         .port_set_frame_mode = mv88e6351_port_set_frame_mode,
3545         .port_set_egress_floods = mv88e6352_port_set_egress_floods,
3546         .port_set_ether_type = mv88e6351_port_set_ether_type,
3547         .port_set_jumbo_size = mv88e6165_port_set_jumbo_size,
3548         .port_egress_rate_limiting = mv88e6097_port_egress_rate_limiting,
3549         .port_pause_limit = mv88e6097_port_pause_limit,
3550         .port_disable_learn_limit = mv88e6xxx_port_disable_learn_limit,
3551         .port_disable_pri_override = mv88e6xxx_port_disable_pri_override,
3552         .port_link_state = mv88e6352_port_link_state,
3553         .stats_snapshot = mv88e6320_g1_stats_snapshot,
3554         .stats_set_histogram = mv88e6095_g1_stats_set_histogram,
3555         .stats_get_sset_count = mv88e6095_stats_get_sset_count,
3556         .stats_get_strings = mv88e6095_stats_get_strings,
3557         .stats_get_stats = mv88e6095_stats_get_stats,
3558         .set_cpu_port = mv88e6095_g1_set_cpu_port,
3559         .set_egress_port = mv88e6095_g1_set_egress_port,
3560         .watchdog_ops = &mv88e6097_watchdog_ops,
3561         .mgmt_rsvd2cpu = mv88e6352_g2_mgmt_rsvd2cpu,
3562         .pot_clear = mv88e6xxx_g2_pot_clear,
3563         .reset = mv88e6352_g1_reset,
3564         .vtu_getnext = mv88e6352_g1_vtu_getnext,
3565         .vtu_loadpurge = mv88e6352_g1_vtu_loadpurge,
3566         .avb_ops = &mv88e6352_avb_ops,
3567         .ptp_ops = &mv88e6352_ptp_ops,
3568         .phylink_validate = mv88e6185_phylink_validate,
3569 };
3570
3571 static const struct mv88e6xxx_ops mv88e6352_ops = {
3572         /* MV88E6XXX_FAMILY_6352 */
3573         .ieee_pri_map = mv88e6085_g1_ieee_pri_map,
3574         .ip_pri_map = mv88e6085_g1_ip_pri_map,
3575         .irl_init_all = mv88e6352_g2_irl_init_all,
3576         .get_eeprom = mv88e6xxx_g2_get_eeprom16,
3577         .set_eeprom = mv88e6xxx_g2_set_eeprom16,
3578         .set_switch_mac = mv88e6xxx_g2_set_switch_mac,
3579         .phy_read = mv88e6xxx_g2_smi_phy_read,
3580         .phy_write = mv88e6xxx_g2_smi_phy_write,
3581         .port_set_link = mv88e6xxx_port_set_link,
3582         .port_set_duplex = mv88e6xxx_port_set_duplex,
3583         .port_set_rgmii_delay = mv88e6352_port_set_rgmii_delay,
3584         .port_set_speed = mv88e6352_port_set_speed,
3585         .port_tag_remap = mv88e6095_port_tag_remap,
3586         .port_set_frame_mode = mv88e6351_port_set_frame_mode,
3587         .port_set_egress_floods = mv88e6352_port_set_egress_floods,
3588         .port_set_ether_type = mv88e6351_port_set_ether_type,
3589         .port_set_jumbo_size = mv88e6165_port_set_jumbo_size,
3590         .port_egress_rate_limiting = mv88e6097_port_egress_rate_limiting,
3591         .port_pause_limit = mv88e6097_port_pause_limit,
3592         .port_disable_learn_limit = mv88e6xxx_port_disable_learn_limit,
3593         .port_disable_pri_override = mv88e6xxx_port_disable_pri_override,
3594         .port_link_state = mv88e6352_port_link_state,
3595         .stats_snapshot = mv88e6320_g1_stats_snapshot,
3596         .stats_set_histogram = mv88e6095_g1_stats_set_histogram,
3597         .stats_get_sset_count = mv88e6095_stats_get_sset_count,
3598         .stats_get_strings = mv88e6095_stats_get_strings,
3599         .stats_get_stats = mv88e6095_stats_get_stats,
3600         .set_cpu_port = mv88e6095_g1_set_cpu_port,
3601         .set_egress_port = mv88e6095_g1_set_egress_port,
3602         .watchdog_ops = &mv88e6097_watchdog_ops,
3603         .mgmt_rsvd2cpu = mv88e6352_g2_mgmt_rsvd2cpu,
3604         .pot_clear = mv88e6xxx_g2_pot_clear,
3605         .reset = mv88e6352_g1_reset,
3606         .rmu_disable = mv88e6352_g1_rmu_disable,
3607         .vtu_getnext = mv88e6352_g1_vtu_getnext,
3608         .vtu_loadpurge = mv88e6352_g1_vtu_loadpurge,
3609         .serdes_power = mv88e6352_serdes_power,
3610         .gpio_ops = &mv88e6352_gpio_ops,
3611         .avb_ops = &mv88e6352_avb_ops,
3612         .ptp_ops = &mv88e6352_ptp_ops,
3613         .serdes_get_sset_count = mv88e6352_serdes_get_sset_count,
3614         .serdes_get_strings = mv88e6352_serdes_get_strings,
3615         .serdes_get_stats = mv88e6352_serdes_get_stats,
3616         .phylink_validate = mv88e6352_phylink_validate,
3617 };
3618
3619 static const struct mv88e6xxx_ops mv88e6390_ops = {
3620         /* MV88E6XXX_FAMILY_6390 */
3621         .irl_init_all = mv88e6390_g2_irl_init_all,
3622         .get_eeprom = mv88e6xxx_g2_get_eeprom8,
3623         .set_eeprom = mv88e6xxx_g2_set_eeprom8,
3624         .set_switch_mac = mv88e6xxx_g2_set_switch_mac,
3625         .phy_read = mv88e6xxx_g2_smi_phy_read,
3626         .phy_write = mv88e6xxx_g2_smi_phy_write,
3627         .port_set_link = mv88e6xxx_port_set_link,
3628         .port_set_duplex = mv88e6xxx_port_set_duplex,
3629         .port_set_rgmii_delay = mv88e6390_port_set_rgmii_delay,
3630         .port_set_speed = mv88e6390_port_set_speed,
3631         .port_tag_remap = mv88e6390_port_tag_remap,
3632         .port_set_frame_mode = mv88e6351_port_set_frame_mode,
3633         .port_set_egress_floods = mv88e6352_port_set_egress_floods,
3634         .port_set_ether_type = mv88e6351_port_set_ether_type,
3635         .port_set_jumbo_size = mv88e6165_port_set_jumbo_size,
3636         .port_egress_rate_limiting = mv88e6097_port_egress_rate_limiting,
3637         .port_pause_limit = mv88e6390_port_pause_limit,
3638         .port_set_cmode = mv88e6390x_port_set_cmode,
3639         .port_disable_learn_limit = mv88e6xxx_port_disable_learn_limit,
3640         .port_disable_pri_override = mv88e6xxx_port_disable_pri_override,
3641         .port_link_state = mv88e6352_port_link_state,
3642         .stats_snapshot = mv88e6390_g1_stats_snapshot,
3643         .stats_set_histogram = mv88e6390_g1_stats_set_histogram,
3644         .stats_get_sset_count = mv88e6320_stats_get_sset_count,
3645         .stats_get_strings = mv88e6320_stats_get_strings,
3646         .stats_get_stats = mv88e6390_stats_get_stats,
3647         .set_cpu_port = mv88e6390_g1_set_cpu_port,
3648         .set_egress_port = mv88e6390_g1_set_egress_port,
3649         .watchdog_ops = &mv88e6390_watchdog_ops,
3650         .mgmt_rsvd2cpu = mv88e6390_g1_mgmt_rsvd2cpu,
3651         .pot_clear = mv88e6xxx_g2_pot_clear,
3652         .reset = mv88e6352_g1_reset,
3653         .rmu_disable = mv88e6390_g1_rmu_disable,
3654         .vtu_getnext = mv88e6390_g1_vtu_getnext,
3655         .vtu_loadpurge = mv88e6390_g1_vtu_loadpurge,
3656         .serdes_power = mv88e6390_serdes_power,
3657         .gpio_ops = &mv88e6352_gpio_ops,
3658         .avb_ops = &mv88e6390_avb_ops,
3659         .ptp_ops = &mv88e6352_ptp_ops,
3660         .phylink_validate = mv88e6390_phylink_validate,
3661 };
3662
3663 static const struct mv88e6xxx_ops mv88e6390x_ops = {
3664         /* MV88E6XXX_FAMILY_6390 */
3665         .irl_init_all = mv88e6390_g2_irl_init_all,
3666         .get_eeprom = mv88e6xxx_g2_get_eeprom8,
3667         .set_eeprom = mv88e6xxx_g2_set_eeprom8,
3668         .set_switch_mac = mv88e6xxx_g2_set_switch_mac,
3669         .phy_read = mv88e6xxx_g2_smi_phy_read,
3670         .phy_write = mv88e6xxx_g2_smi_phy_write,
3671         .port_set_link = mv88e6xxx_port_set_link,
3672         .port_set_duplex = mv88e6xxx_port_set_duplex,
3673         .port_set_rgmii_delay = mv88e6390_port_set_rgmii_delay,
3674         .port_set_speed = mv88e6390x_port_set_speed,
3675         .port_tag_remap = mv88e6390_port_tag_remap,
3676         .port_set_frame_mode = mv88e6351_port_set_frame_mode,
3677         .port_set_egress_floods = mv88e6352_port_set_egress_floods,
3678         .port_set_ether_type = mv88e6351_port_set_ether_type,
3679         .port_set_jumbo_size = mv88e6165_port_set_jumbo_size,
3680         .port_egress_rate_limiting = mv88e6097_port_egress_rate_limiting,
3681         .port_pause_limit = mv88e6390_port_pause_limit,
3682         .port_set_cmode = mv88e6390x_port_set_cmode,
3683         .port_disable_learn_limit = mv88e6xxx_port_disable_learn_limit,
3684         .port_disable_pri_override = mv88e6xxx_port_disable_pri_override,
3685         .port_link_state = mv88e6352_port_link_state,
3686         .stats_snapshot = mv88e6390_g1_stats_snapshot,
3687         .stats_set_histogram = mv88e6390_g1_stats_set_histogram,
3688         .stats_get_sset_count = mv88e6320_stats_get_sset_count,
3689         .stats_get_strings = mv88e6320_stats_get_strings,
3690         .stats_get_stats = mv88e6390_stats_get_stats,
3691         .set_cpu_port = mv88e6390_g1_set_cpu_port,
3692         .set_egress_port = mv88e6390_g1_set_egress_port,
3693         .watchdog_ops = &mv88e6390_watchdog_ops,
3694         .mgmt_rsvd2cpu = mv88e6390_g1_mgmt_rsvd2cpu,
3695         .pot_clear = mv88e6xxx_g2_pot_clear,
3696         .reset = mv88e6352_g1_reset,
3697         .rmu_disable = mv88e6390_g1_rmu_disable,
3698         .vtu_getnext = mv88e6390_g1_vtu_getnext,
3699         .vtu_loadpurge = mv88e6390_g1_vtu_loadpurge,
3700         .serdes_power = mv88e6390_serdes_power,
3701         .gpio_ops = &mv88e6352_gpio_ops,
3702         .avb_ops = &mv88e6390_avb_ops,
3703         .ptp_ops = &mv88e6352_ptp_ops,
3704         .phylink_validate = mv88e6390x_phylink_validate,
3705 };
3706
3707 static const struct mv88e6xxx_info mv88e6xxx_table[] = {
3708         [MV88E6085] = {
3709                 .prod_num = MV88E6XXX_PORT_SWITCH_ID_PROD_6085,
3710                 .family = MV88E6XXX_FAMILY_6097,
3711                 .name = "Marvell 88E6085",
3712                 .num_databases = 4096,
3713                 .num_ports = 10,
3714                 .num_internal_phys = 5,
3715                 .max_vid = 4095,
3716                 .port_base_addr = 0x10,
3717                 .phy_base_addr = 0x0,
3718                 .global1_addr = 0x1b,
3719                 .global2_addr = 0x1c,
3720                 .age_time_coeff = 15000,
3721                 .g1_irqs = 8,
3722                 .g2_irqs = 10,
3723                 .atu_move_port_mask = 0xf,
3724                 .pvt = true,
3725                 .multi_chip = true,
3726                 .tag_protocol = DSA_TAG_PROTO_DSA,
3727                 .ops = &mv88e6085_ops,
3728         },
3729
3730         [MV88E6095] = {
3731                 .prod_num = MV88E6XXX_PORT_SWITCH_ID_PROD_6095,
3732                 .family = MV88E6XXX_FAMILY_6095,
3733                 .name = "Marvell 88E6095/88E6095F",
3734                 .num_databases = 256,
3735                 .num_ports = 11,
3736                 .num_internal_phys = 0,
3737                 .max_vid = 4095,
3738                 .port_base_addr = 0x10,
3739                 .phy_base_addr = 0x0,
3740                 .global1_addr = 0x1b,
3741                 .global2_addr = 0x1c,
3742                 .age_time_coeff = 15000,
3743                 .g1_irqs = 8,
3744                 .atu_move_port_mask = 0xf,
3745                 .multi_chip = true,
3746                 .tag_protocol = DSA_TAG_PROTO_DSA,
3747                 .ops = &mv88e6095_ops,
3748         },
3749
3750         [MV88E6097] = {
3751                 .prod_num = MV88E6XXX_PORT_SWITCH_ID_PROD_6097,
3752                 .family = MV88E6XXX_FAMILY_6097,
3753                 .name = "Marvell 88E6097/88E6097F",
3754                 .num_databases = 4096,
3755                 .num_ports = 11,
3756                 .num_internal_phys = 8,
3757                 .max_vid = 4095,
3758                 .port_base_addr = 0x10,
3759                 .phy_base_addr = 0x0,
3760                 .global1_addr = 0x1b,
3761                 .global2_addr = 0x1c,
3762                 .age_time_coeff = 15000,
3763                 .g1_irqs = 8,
3764                 .g2_irqs = 10,
3765                 .atu_move_port_mask = 0xf,
3766                 .pvt = true,
3767                 .multi_chip = true,
3768                 .tag_protocol = DSA_TAG_PROTO_EDSA,
3769                 .ops = &mv88e6097_ops,
3770         },
3771
3772         [MV88E6123] = {
3773                 .prod_num = MV88E6XXX_PORT_SWITCH_ID_PROD_6123,
3774                 .family = MV88E6XXX_FAMILY_6165,
3775                 .name = "Marvell 88E6123",
3776                 .num_databases = 4096,
3777                 .num_ports = 3,
3778                 .num_internal_phys = 5,
3779                 .max_vid = 4095,
3780                 .port_base_addr = 0x10,
3781                 .phy_base_addr = 0x0,
3782                 .global1_addr = 0x1b,
3783                 .global2_addr = 0x1c,
3784                 .age_time_coeff = 15000,
3785                 .g1_irqs = 9,
3786                 .g2_irqs = 10,
3787                 .atu_move_port_mask = 0xf,
3788                 .pvt = true,
3789                 .multi_chip = true,
3790                 .tag_protocol = DSA_TAG_PROTO_EDSA,
3791                 .ops = &mv88e6123_ops,
3792         },
3793
3794         [MV88E6131] = {
3795                 .prod_num = MV88E6XXX_PORT_SWITCH_ID_PROD_6131,
3796                 .family = MV88E6XXX_FAMILY_6185,
3797                 .name = "Marvell 88E6131",
3798                 .num_databases = 256,
3799                 .num_ports = 8,
3800                 .num_internal_phys = 0,
3801                 .max_vid = 4095,
3802                 .port_base_addr = 0x10,
3803                 .phy_base_addr = 0x0,
3804                 .global1_addr = 0x1b,
3805                 .global2_addr = 0x1c,
3806                 .age_time_coeff = 15000,
3807                 .g1_irqs = 9,
3808                 .atu_move_port_mask = 0xf,
3809                 .multi_chip = true,
3810                 .tag_protocol = DSA_TAG_PROTO_DSA,
3811                 .ops = &mv88e6131_ops,
3812         },
3813
3814         [MV88E6141] = {
3815                 .prod_num = MV88E6XXX_PORT_SWITCH_ID_PROD_6141,
3816                 .family = MV88E6XXX_FAMILY_6341,
3817                 .name = "Marvell 88E6141",
3818                 .num_databases = 4096,
3819                 .num_ports = 6,
3820                 .num_internal_phys = 5,
3821                 .num_gpio = 11,
3822                 .max_vid = 4095,
3823                 .port_base_addr = 0x10,
3824                 .phy_base_addr = 0x10,
3825                 .global1_addr = 0x1b,
3826                 .global2_addr = 0x1c,
3827                 .age_time_coeff = 3750,
3828                 .atu_move_port_mask = 0x1f,
3829                 .g1_irqs = 9,
3830                 .g2_irqs = 10,
3831                 .pvt = true,
3832                 .multi_chip = true,
3833                 .tag_protocol = DSA_TAG_PROTO_EDSA,
3834                 .ops = &mv88e6141_ops,
3835         },
3836
3837         [MV88E6161] = {
3838                 .prod_num = MV88E6XXX_PORT_SWITCH_ID_PROD_6161,
3839                 .family = MV88E6XXX_FAMILY_6165,
3840                 .name = "Marvell 88E6161",
3841                 .num_databases = 4096,
3842                 .num_ports = 6,
3843                 .num_internal_phys = 5,
3844                 .max_vid = 4095,
3845                 .port_base_addr = 0x10,
3846                 .phy_base_addr = 0x0,
3847                 .global1_addr = 0x1b,
3848                 .global2_addr = 0x1c,
3849                 .age_time_coeff = 15000,
3850                 .g1_irqs = 9,
3851                 .g2_irqs = 10,
3852                 .atu_move_port_mask = 0xf,
3853                 .pvt = true,
3854                 .multi_chip = true,
3855                 .tag_protocol = DSA_TAG_PROTO_EDSA,
3856                 .ptp_support = true,
3857                 .ops = &mv88e6161_ops,
3858         },
3859
3860         [MV88E6165] = {
3861                 .prod_num = MV88E6XXX_PORT_SWITCH_ID_PROD_6165,
3862                 .family = MV88E6XXX_FAMILY_6165,
3863                 .name = "Marvell 88E6165",
3864                 .num_databases = 4096,
3865                 .num_ports = 6,
3866                 .num_internal_phys = 0,
3867                 .max_vid = 4095,
3868                 .port_base_addr = 0x10,
3869                 .phy_base_addr = 0x0,
3870                 .global1_addr = 0x1b,
3871                 .global2_addr = 0x1c,
3872                 .age_time_coeff = 15000,
3873                 .g1_irqs = 9,
3874                 .g2_irqs = 10,
3875                 .atu_move_port_mask = 0xf,
3876                 .pvt = true,
3877                 .multi_chip = true,
3878                 .tag_protocol = DSA_TAG_PROTO_DSA,
3879                 .ptp_support = true,
3880                 .ops = &mv88e6165_ops,
3881         },
3882
3883         [MV88E6171] = {
3884                 .prod_num = MV88E6XXX_PORT_SWITCH_ID_PROD_6171,
3885                 .family = MV88E6XXX_FAMILY_6351,
3886                 .name = "Marvell 88E6171",
3887                 .num_databases = 4096,
3888                 .num_ports = 7,
3889                 .num_internal_phys = 5,
3890                 .max_vid = 4095,
3891                 .port_base_addr = 0x10,
3892                 .phy_base_addr = 0x0,
3893                 .global1_addr = 0x1b,
3894                 .global2_addr = 0x1c,
3895                 .age_time_coeff = 15000,
3896                 .g1_irqs = 9,
3897                 .g2_irqs = 10,
3898                 .atu_move_port_mask = 0xf,
3899                 .pvt = true,
3900                 .multi_chip = true,
3901                 .tag_protocol = DSA_TAG_PROTO_EDSA,
3902                 .ops = &mv88e6171_ops,
3903         },
3904
3905         [MV88E6172] = {
3906                 .prod_num = MV88E6XXX_PORT_SWITCH_ID_PROD_6172,
3907                 .family = MV88E6XXX_FAMILY_6352,
3908                 .name = "Marvell 88E6172",
3909                 .num_databases = 4096,
3910                 .num_ports = 7,
3911                 .num_internal_phys = 5,
3912                 .num_gpio = 15,
3913                 .max_vid = 4095,
3914                 .port_base_addr = 0x10,
3915                 .phy_base_addr = 0x0,
3916                 .global1_addr = 0x1b,
3917                 .global2_addr = 0x1c,
3918                 .age_time_coeff = 15000,
3919                 .g1_irqs = 9,
3920                 .g2_irqs = 10,
3921                 .atu_move_port_mask = 0xf,
3922                 .pvt = true,
3923                 .multi_chip = true,
3924                 .tag_protocol = DSA_TAG_PROTO_EDSA,
3925                 .ops = &mv88e6172_ops,
3926         },
3927
3928         [MV88E6175] = {
3929                 .prod_num = MV88E6XXX_PORT_SWITCH_ID_PROD_6175,
3930                 .family = MV88E6XXX_FAMILY_6351,
3931                 .name = "Marvell 88E6175",
3932                 .num_databases = 4096,
3933                 .num_ports = 7,
3934                 .num_internal_phys = 5,
3935                 .max_vid = 4095,
3936                 .port_base_addr = 0x10,
3937                 .phy_base_addr = 0x0,
3938                 .global1_addr = 0x1b,
3939                 .global2_addr = 0x1c,
3940                 .age_time_coeff = 15000,
3941                 .g1_irqs = 9,
3942                 .g2_irqs = 10,
3943                 .atu_move_port_mask = 0xf,
3944                 .pvt = true,
3945                 .multi_chip = true,
3946                 .tag_protocol = DSA_TAG_PROTO_EDSA,
3947                 .ops = &mv88e6175_ops,
3948         },
3949
3950         [MV88E6176] = {
3951                 .prod_num = MV88E6XXX_PORT_SWITCH_ID_PROD_6176,
3952                 .family = MV88E6XXX_FAMILY_6352,
3953                 .name = "Marvell 88E6176",
3954                 .num_databases = 4096,
3955                 .num_ports = 7,
3956                 .num_internal_phys = 5,
3957                 .num_gpio = 15,
3958                 .max_vid = 4095,
3959                 .port_base_addr = 0x10,
3960                 .phy_base_addr = 0x0,
3961                 .global1_addr = 0x1b,
3962                 .global2_addr = 0x1c,
3963                 .age_time_coeff = 15000,
3964                 .g1_irqs = 9,
3965                 .g2_irqs = 10,
3966                 .atu_move_port_mask = 0xf,
3967                 .pvt = true,
3968                 .multi_chip = true,
3969                 .tag_protocol = DSA_TAG_PROTO_EDSA,
3970                 .ops = &mv88e6176_ops,
3971         },
3972
3973         [MV88E6185] = {
3974                 .prod_num = MV88E6XXX_PORT_SWITCH_ID_PROD_6185,
3975                 .family = MV88E6XXX_FAMILY_6185,
3976                 .name = "Marvell 88E6185",
3977                 .num_databases = 256,
3978                 .num_ports = 10,
3979                 .num_internal_phys = 0,
3980                 .max_vid = 4095,
3981                 .port_base_addr = 0x10,
3982                 .phy_base_addr = 0x0,
3983                 .global1_addr = 0x1b,
3984                 .global2_addr = 0x1c,
3985                 .age_time_coeff = 15000,
3986                 .g1_irqs = 8,
3987                 .atu_move_port_mask = 0xf,
3988                 .multi_chip = true,
3989                 .tag_protocol = DSA_TAG_PROTO_EDSA,
3990                 .ops = &mv88e6185_ops,
3991         },
3992
3993         [MV88E6190] = {
3994                 .prod_num = MV88E6XXX_PORT_SWITCH_ID_PROD_6190,
3995                 .family = MV88E6XXX_FAMILY_6390,
3996                 .name = "Marvell 88E6190",
3997                 .num_databases = 4096,
3998                 .num_ports = 11,        /* 10 + Z80 */
3999                 .num_internal_phys = 11,
4000                 .num_gpio = 16,
4001                 .max_vid = 8191,
4002                 .port_base_addr = 0x0,
4003                 .phy_base_addr = 0x0,
4004                 .global1_addr = 0x1b,
4005                 .global2_addr = 0x1c,
4006                 .tag_protocol = DSA_TAG_PROTO_DSA,
4007                 .age_time_coeff = 3750,
4008                 .g1_irqs = 9,
4009                 .g2_irqs = 14,
4010                 .pvt = true,
4011                 .multi_chip = true,
4012                 .atu_move_port_mask = 0x1f,
4013                 .ops = &mv88e6190_ops,
4014         },
4015
4016         [MV88E6190X] = {
4017                 .prod_num = MV88E6XXX_PORT_SWITCH_ID_PROD_6190X,
4018                 .family = MV88E6XXX_FAMILY_6390,
4019                 .name = "Marvell 88E6190X",
4020                 .num_databases = 4096,
4021                 .num_ports = 11,        /* 10 + Z80 */
4022                 .num_internal_phys = 11,
4023                 .num_gpio = 16,
4024                 .max_vid = 8191,
4025                 .port_base_addr = 0x0,
4026                 .phy_base_addr = 0x0,
4027                 .global1_addr = 0x1b,
4028                 .global2_addr = 0x1c,
4029                 .age_time_coeff = 3750,
4030                 .g1_irqs = 9,
4031                 .g2_irqs = 14,
4032                 .atu_move_port_mask = 0x1f,
4033                 .pvt = true,
4034                 .multi_chip = true,
4035                 .tag_protocol = DSA_TAG_PROTO_DSA,
4036                 .ops = &mv88e6190x_ops,
4037         },
4038
4039         [MV88E6191] = {
4040                 .prod_num = MV88E6XXX_PORT_SWITCH_ID_PROD_6191,
4041                 .family = MV88E6XXX_FAMILY_6390,
4042                 .name = "Marvell 88E6191",
4043                 .num_databases = 4096,
4044                 .num_ports = 11,        /* 10 + Z80 */
4045                 .num_internal_phys = 11,
4046                 .max_vid = 8191,
4047                 .port_base_addr = 0x0,
4048                 .phy_base_addr = 0x0,
4049                 .global1_addr = 0x1b,
4050                 .global2_addr = 0x1c,
4051                 .age_time_coeff = 3750,
4052                 .g1_irqs = 9,
4053                 .g2_irqs = 14,
4054                 .atu_move_port_mask = 0x1f,
4055                 .pvt = true,
4056                 .multi_chip = true,
4057                 .tag_protocol = DSA_TAG_PROTO_DSA,
4058                 .ptp_support = true,
4059                 .ops = &mv88e6191_ops,
4060         },
4061
4062         [MV88E6240] = {
4063                 .prod_num = MV88E6XXX_PORT_SWITCH_ID_PROD_6240,
4064                 .family = MV88E6XXX_FAMILY_6352,
4065                 .name = "Marvell 88E6240",
4066                 .num_databases = 4096,
4067                 .num_ports = 7,
4068                 .num_internal_phys = 5,
4069                 .num_gpio = 15,
4070                 .max_vid = 4095,
4071                 .port_base_addr = 0x10,
4072                 .phy_base_addr = 0x0,
4073                 .global1_addr = 0x1b,
4074                 .global2_addr = 0x1c,
4075                 .age_time_coeff = 15000,
4076                 .g1_irqs = 9,
4077                 .g2_irqs = 10,
4078                 .atu_move_port_mask = 0xf,
4079                 .pvt = true,
4080                 .multi_chip = true,
4081                 .tag_protocol = DSA_TAG_PROTO_EDSA,
4082                 .ptp_support = true,
4083                 .ops = &mv88e6240_ops,
4084         },
4085
4086         [MV88E6290] = {
4087                 .prod_num = MV88E6XXX_PORT_SWITCH_ID_PROD_6290,
4088                 .family = MV88E6XXX_FAMILY_6390,
4089                 .name = "Marvell 88E6290",
4090                 .num_databases = 4096,
4091                 .num_ports = 11,        /* 10 + Z80 */
4092                 .num_internal_phys = 11,
4093                 .num_gpio = 16,
4094                 .max_vid = 8191,
4095                 .port_base_addr = 0x0,
4096                 .phy_base_addr = 0x0,
4097                 .global1_addr = 0x1b,
4098                 .global2_addr = 0x1c,
4099                 .age_time_coeff = 3750,
4100                 .g1_irqs = 9,
4101                 .g2_irqs = 14,
4102                 .atu_move_port_mask = 0x1f,
4103                 .pvt = true,
4104                 .multi_chip = true,
4105                 .tag_protocol = DSA_TAG_PROTO_DSA,
4106                 .ptp_support = true,
4107                 .ops = &mv88e6290_ops,
4108         },
4109
4110         [MV88E6320] = {
4111                 .prod_num = MV88E6XXX_PORT_SWITCH_ID_PROD_6320,
4112                 .family = MV88E6XXX_FAMILY_6320,
4113                 .name = "Marvell 88E6320",
4114                 .num_databases = 4096,
4115                 .num_ports = 7,
4116                 .num_internal_phys = 5,
4117                 .num_gpio = 15,
4118                 .max_vid = 4095,
4119                 .port_base_addr = 0x10,
4120                 .phy_base_addr = 0x0,
4121                 .global1_addr = 0x1b,
4122                 .global2_addr = 0x1c,
4123                 .age_time_coeff = 15000,
4124                 .g1_irqs = 8,
4125                 .g2_irqs = 10,
4126                 .atu_move_port_mask = 0xf,
4127                 .pvt = true,
4128                 .multi_chip = true,
4129                 .tag_protocol = DSA_TAG_PROTO_EDSA,
4130                 .ptp_support = true,
4131                 .ops = &mv88e6320_ops,
4132         },
4133
4134         [MV88E6321] = {
4135                 .prod_num = MV88E6XXX_PORT_SWITCH_ID_PROD_6321,
4136                 .family = MV88E6XXX_FAMILY_6320,
4137                 .name = "Marvell 88E6321",
4138                 .num_databases = 4096,
4139                 .num_ports = 7,
4140                 .num_internal_phys = 5,
4141                 .num_gpio = 15,
4142                 .max_vid = 4095,
4143                 .port_base_addr = 0x10,
4144                 .phy_base_addr = 0x0,
4145                 .global1_addr = 0x1b,
4146                 .global2_addr = 0x1c,
4147                 .age_time_coeff = 15000,
4148                 .g1_irqs = 8,
4149                 .g2_irqs = 10,
4150                 .atu_move_port_mask = 0xf,
4151                 .multi_chip = true,
4152                 .tag_protocol = DSA_TAG_PROTO_EDSA,
4153                 .ptp_support = true,
4154                 .ops = &mv88e6321_ops,
4155         },
4156
4157         [MV88E6341] = {
4158                 .prod_num = MV88E6XXX_PORT_SWITCH_ID_PROD_6341,
4159                 .family = MV88E6XXX_FAMILY_6341,
4160                 .name = "Marvell 88E6341",
4161                 .num_databases = 4096,
4162                 .num_internal_phys = 5,
4163                 .num_ports = 6,
4164                 .num_gpio = 11,
4165                 .max_vid = 4095,
4166                 .port_base_addr = 0x10,
4167                 .phy_base_addr = 0x10,
4168                 .global1_addr = 0x1b,
4169                 .global2_addr = 0x1c,
4170                 .age_time_coeff = 3750,
4171                 .atu_move_port_mask = 0x1f,
4172                 .g1_irqs = 9,
4173                 .g2_irqs = 10,
4174                 .pvt = true,
4175                 .multi_chip = true,
4176                 .tag_protocol = DSA_TAG_PROTO_EDSA,
4177                 .ptp_support = true,
4178                 .ops = &mv88e6341_ops,
4179         },
4180
4181         [MV88E6350] = {
4182                 .prod_num = MV88E6XXX_PORT_SWITCH_ID_PROD_6350,
4183                 .family = MV88E6XXX_FAMILY_6351,
4184                 .name = "Marvell 88E6350",
4185                 .num_databases = 4096,
4186                 .num_ports = 7,
4187                 .num_internal_phys = 5,
4188                 .max_vid = 4095,
4189                 .port_base_addr = 0x10,
4190                 .phy_base_addr = 0x0,
4191                 .global1_addr = 0x1b,
4192                 .global2_addr = 0x1c,
4193                 .age_time_coeff = 15000,
4194                 .g1_irqs = 9,
4195                 .g2_irqs = 10,
4196                 .atu_move_port_mask = 0xf,
4197                 .pvt = true,
4198                 .multi_chip = true,
4199                 .tag_protocol = DSA_TAG_PROTO_EDSA,
4200                 .ops = &mv88e6350_ops,
4201         },
4202
4203         [MV88E6351] = {
4204                 .prod_num = MV88E6XXX_PORT_SWITCH_ID_PROD_6351,
4205                 .family = MV88E6XXX_FAMILY_6351,
4206                 .name = "Marvell 88E6351",
4207                 .num_databases = 4096,
4208                 .num_ports = 7,
4209                 .num_internal_phys = 5,
4210                 .max_vid = 4095,
4211                 .port_base_addr = 0x10,
4212                 .phy_base_addr = 0x0,
4213                 .global1_addr = 0x1b,
4214                 .global2_addr = 0x1c,
4215                 .age_time_coeff = 15000,
4216                 .g1_irqs = 9,
4217                 .g2_irqs = 10,
4218                 .atu_move_port_mask = 0xf,
4219                 .pvt = true,
4220                 .multi_chip = true,
4221                 .tag_protocol = DSA_TAG_PROTO_EDSA,
4222                 .ops = &mv88e6351_ops,
4223         },
4224
4225         [MV88E6352] = {
4226                 .prod_num = MV88E6XXX_PORT_SWITCH_ID_PROD_6352,
4227                 .family = MV88E6XXX_FAMILY_6352,
4228                 .name = "Marvell 88E6352",
4229                 .num_databases = 4096,
4230                 .num_ports = 7,
4231                 .num_internal_phys = 5,
4232                 .num_gpio = 15,
4233                 .max_vid = 4095,
4234                 .port_base_addr = 0x10,
4235                 .phy_base_addr = 0x0,
4236                 .global1_addr = 0x1b,
4237                 .global2_addr = 0x1c,
4238                 .age_time_coeff = 15000,
4239                 .g1_irqs = 9,
4240                 .g2_irqs = 10,
4241                 .atu_move_port_mask = 0xf,
4242                 .pvt = true,
4243                 .multi_chip = true,
4244                 .tag_protocol = DSA_TAG_PROTO_EDSA,
4245                 .ptp_support = true,
4246                 .ops = &mv88e6352_ops,
4247         },
4248         [MV88E6390] = {
4249                 .prod_num = MV88E6XXX_PORT_SWITCH_ID_PROD_6390,
4250                 .family = MV88E6XXX_FAMILY_6390,
4251                 .name = "Marvell 88E6390",
4252                 .num_databases = 4096,
4253                 .num_ports = 11,        /* 10 + Z80 */
4254                 .num_internal_phys = 11,
4255                 .num_gpio = 16,
4256                 .max_vid = 8191,
4257                 .port_base_addr = 0x0,
4258                 .phy_base_addr = 0x0,
4259                 .global1_addr = 0x1b,
4260                 .global2_addr = 0x1c,
4261                 .age_time_coeff = 3750,
4262                 .g1_irqs = 9,
4263                 .g2_irqs = 14,
4264                 .atu_move_port_mask = 0x1f,
4265                 .pvt = true,
4266                 .multi_chip = true,
4267                 .tag_protocol = DSA_TAG_PROTO_DSA,
4268                 .ptp_support = true,
4269                 .ops = &mv88e6390_ops,
4270         },
4271         [MV88E6390X] = {
4272                 .prod_num = MV88E6XXX_PORT_SWITCH_ID_PROD_6390X,
4273                 .family = MV88E6XXX_FAMILY_6390,
4274                 .name = "Marvell 88E6390X",
4275                 .num_databases = 4096,
4276                 .num_ports = 11,        /* 10 + Z80 */
4277                 .num_internal_phys = 11,
4278                 .num_gpio = 16,
4279                 .max_vid = 8191,
4280                 .port_base_addr = 0x0,
4281                 .phy_base_addr = 0x0,
4282                 .global1_addr = 0x1b,
4283                 .global2_addr = 0x1c,
4284                 .age_time_coeff = 3750,
4285                 .g1_irqs = 9,
4286                 .g2_irqs = 14,
4287                 .atu_move_port_mask = 0x1f,
4288                 .pvt = true,
4289                 .multi_chip = true,
4290                 .tag_protocol = DSA_TAG_PROTO_DSA,
4291                 .ptp_support = true,
4292                 .ops = &mv88e6390x_ops,
4293         },
4294 };
4295
4296 static const struct mv88e6xxx_info *mv88e6xxx_lookup_info(unsigned int prod_num)
4297 {
4298         int i;
4299
4300         for (i = 0; i < ARRAY_SIZE(mv88e6xxx_table); ++i)
4301                 if (mv88e6xxx_table[i].prod_num == prod_num)
4302                         return &mv88e6xxx_table[i];
4303
4304         return NULL;
4305 }
4306
4307 static int mv88e6xxx_detect(struct mv88e6xxx_chip *chip)
4308 {
4309         const struct mv88e6xxx_info *info;
4310         unsigned int prod_num, rev;
4311         u16 id;
4312         int err;
4313
4314         mutex_lock(&chip->reg_lock);
4315         err = mv88e6xxx_port_read(chip, 0, MV88E6XXX_PORT_SWITCH_ID, &id);
4316         mutex_unlock(&chip->reg_lock);
4317         if (err)
4318                 return err;
4319
4320         prod_num = id & MV88E6XXX_PORT_SWITCH_ID_PROD_MASK;
4321         rev = id & MV88E6XXX_PORT_SWITCH_ID_REV_MASK;
4322
4323         info = mv88e6xxx_lookup_info(prod_num);
4324         if (!info)
4325                 return -ENODEV;
4326
4327         /* Update the compatible info with the probed one */
4328         chip->info = info;
4329
4330         err = mv88e6xxx_g2_require(chip);
4331         if (err)
4332                 return err;
4333
4334         dev_info(chip->dev, "switch 0x%x detected: %s, revision %u\n",
4335                  chip->info->prod_num, chip->info->name, rev);
4336
4337         return 0;
4338 }
4339
4340 static struct mv88e6xxx_chip *mv88e6xxx_alloc_chip(struct device *dev)
4341 {
4342         struct mv88e6xxx_chip *chip;
4343
4344         chip = devm_kzalloc(dev, sizeof(*chip), GFP_KERNEL);
4345         if (!chip)
4346                 return NULL;
4347
4348         chip->dev = dev;
4349
4350         mutex_init(&chip->reg_lock);
4351         INIT_LIST_HEAD(&chip->mdios);
4352
4353         return chip;
4354 }
4355
4356 static int mv88e6xxx_smi_init(struct mv88e6xxx_chip *chip,
4357                               struct mii_bus *bus, int sw_addr)
4358 {
4359         if (sw_addr == 0)
4360                 chip->smi_ops = &mv88e6xxx_smi_single_chip_ops;
4361         else if (chip->info->multi_chip)
4362                 chip->smi_ops = &mv88e6xxx_smi_multi_chip_ops;
4363         else
4364                 return -EINVAL;
4365
4366         chip->bus = bus;
4367         chip->sw_addr = sw_addr;
4368
4369         return 0;
4370 }
4371
4372 static enum dsa_tag_protocol mv88e6xxx_get_tag_protocol(struct dsa_switch *ds,
4373                                                         int port)
4374 {
4375         struct mv88e6xxx_chip *chip = ds->priv;
4376
4377         return chip->info->tag_protocol;
4378 }
4379
4380 #if IS_ENABLED(CONFIG_NET_DSA_LEGACY)
4381 static const char *mv88e6xxx_drv_probe(struct device *dsa_dev,
4382                                        struct device *host_dev, int sw_addr,
4383                                        void **priv)
4384 {
4385         struct mv88e6xxx_chip *chip;
4386         struct mii_bus *bus;
4387         int err;
4388
4389         bus = dsa_host_dev_to_mii_bus(host_dev);
4390         if (!bus)
4391                 return NULL;
4392
4393         chip = mv88e6xxx_alloc_chip(dsa_dev);
4394         if (!chip)
4395                 return NULL;
4396
4397         /* Legacy SMI probing will only support chips similar to 88E6085 */
4398         chip->info = &mv88e6xxx_table[MV88E6085];
4399
4400         err = mv88e6xxx_smi_init(chip, bus, sw_addr);
4401         if (err)
4402                 goto free;
4403
4404         err = mv88e6xxx_detect(chip);
4405         if (err)
4406                 goto free;
4407
4408         mutex_lock(&chip->reg_lock);
4409         err = mv88e6xxx_switch_reset(chip);
4410         mutex_unlock(&chip->reg_lock);
4411         if (err)
4412                 goto free;
4413
4414         mv88e6xxx_phy_init(chip);
4415
4416         err = mv88e6xxx_mdios_register(chip, NULL);
4417         if (err)
4418                 goto free;
4419
4420         *priv = chip;
4421
4422         return chip->info->name;
4423 free:
4424         devm_kfree(dsa_dev, chip);
4425
4426         return NULL;
4427 }
4428 #endif
4429
4430 static int mv88e6xxx_port_mdb_prepare(struct dsa_switch *ds, int port,
4431                                       const struct switchdev_obj_port_mdb *mdb)
4432 {
4433         /* We don't need any dynamic resource from the kernel (yet),
4434          * so skip the prepare phase.
4435          */
4436
4437         return 0;
4438 }
4439
4440 static void mv88e6xxx_port_mdb_add(struct dsa_switch *ds, int port,
4441                                    const struct switchdev_obj_port_mdb *mdb)
4442 {
4443         struct mv88e6xxx_chip *chip = ds->priv;
4444
4445         mutex_lock(&chip->reg_lock);
4446         if (mv88e6xxx_port_db_load_purge(chip, port, mdb->addr, mdb->vid,
4447                                          MV88E6XXX_G1_ATU_DATA_STATE_MC_STATIC))
4448                 dev_err(ds->dev, "p%d: failed to load multicast MAC address\n",
4449                         port);
4450         mutex_unlock(&chip->reg_lock);
4451 }
4452
4453 static int mv88e6xxx_port_mdb_del(struct dsa_switch *ds, int port,
4454                                   const struct switchdev_obj_port_mdb *mdb)
4455 {
4456         struct mv88e6xxx_chip *chip = ds->priv;
4457         int err;
4458
4459         mutex_lock(&chip->reg_lock);
4460         err = mv88e6xxx_port_db_load_purge(chip, port, mdb->addr, mdb->vid,
4461                                            MV88E6XXX_G1_ATU_DATA_STATE_UNUSED);
4462         mutex_unlock(&chip->reg_lock);
4463
4464         return err;
4465 }
4466
4467 static const struct dsa_switch_ops mv88e6xxx_switch_ops = {
4468 #if IS_ENABLED(CONFIG_NET_DSA_LEGACY)
4469         .probe                  = mv88e6xxx_drv_probe,
4470 #endif
4471         .get_tag_protocol       = mv88e6xxx_get_tag_protocol,
4472         .setup                  = mv88e6xxx_setup,
4473         .adjust_link            = mv88e6xxx_adjust_link,
4474         .phylink_validate       = mv88e6xxx_validate,
4475         .phylink_mac_link_state = mv88e6xxx_link_state,
4476         .phylink_mac_config     = mv88e6xxx_mac_config,
4477         .phylink_mac_link_down  = mv88e6xxx_mac_link_down,
4478         .phylink_mac_link_up    = mv88e6xxx_mac_link_up,
4479         .get_strings            = mv88e6xxx_get_strings,
4480         .get_ethtool_stats      = mv88e6xxx_get_ethtool_stats,
4481         .get_sset_count         = mv88e6xxx_get_sset_count,
4482         .port_enable            = mv88e6xxx_port_enable,
4483         .port_disable           = mv88e6xxx_port_disable,
4484         .get_mac_eee            = mv88e6xxx_get_mac_eee,
4485         .set_mac_eee            = mv88e6xxx_set_mac_eee,
4486         .get_eeprom_len         = mv88e6xxx_get_eeprom_len,
4487         .get_eeprom             = mv88e6xxx_get_eeprom,
4488         .set_eeprom             = mv88e6xxx_set_eeprom,
4489         .get_regs_len           = mv88e6xxx_get_regs_len,
4490         .get_regs               = mv88e6xxx_get_regs,
4491         .set_ageing_time        = mv88e6xxx_set_ageing_time,
4492         .port_bridge_join       = mv88e6xxx_port_bridge_join,
4493         .port_bridge_leave      = mv88e6xxx_port_bridge_leave,
4494         .port_stp_state_set     = mv88e6xxx_port_stp_state_set,
4495         .port_fast_age          = mv88e6xxx_port_fast_age,
4496         .port_vlan_filtering    = mv88e6xxx_port_vlan_filtering,
4497         .port_vlan_prepare      = mv88e6xxx_port_vlan_prepare,
4498         .port_vlan_add          = mv88e6xxx_port_vlan_add,
4499         .port_vlan_del          = mv88e6xxx_port_vlan_del,
4500         .port_fdb_add           = mv88e6xxx_port_fdb_add,
4501         .port_fdb_del           = mv88e6xxx_port_fdb_del,
4502         .port_fdb_dump          = mv88e6xxx_port_fdb_dump,
4503         .port_mdb_prepare       = mv88e6xxx_port_mdb_prepare,
4504         .port_mdb_add           = mv88e6xxx_port_mdb_add,
4505         .port_mdb_del           = mv88e6xxx_port_mdb_del,
4506         .crosschip_bridge_join  = mv88e6xxx_crosschip_bridge_join,
4507         .crosschip_bridge_leave = mv88e6xxx_crosschip_bridge_leave,
4508         .port_hwtstamp_set      = mv88e6xxx_port_hwtstamp_set,
4509         .port_hwtstamp_get      = mv88e6xxx_port_hwtstamp_get,
4510         .port_txtstamp          = mv88e6xxx_port_txtstamp,
4511         .port_rxtstamp          = mv88e6xxx_port_rxtstamp,
4512         .get_ts_info            = mv88e6xxx_get_ts_info,
4513 };
4514
4515 static struct dsa_switch_driver mv88e6xxx_switch_drv = {
4516         .ops                    = &mv88e6xxx_switch_ops,
4517 };
4518
4519 static int mv88e6xxx_register_switch(struct mv88e6xxx_chip *chip)
4520 {
4521         struct device *dev = chip->dev;
4522         struct dsa_switch *ds;
4523
4524         ds = dsa_switch_alloc(dev, mv88e6xxx_num_ports(chip));
4525         if (!ds)
4526                 return -ENOMEM;
4527
4528         ds->priv = chip;
4529         ds->dev = dev;
4530         ds->ops = &mv88e6xxx_switch_ops;
4531         ds->ageing_time_min = chip->info->age_time_coeff;
4532         ds->ageing_time_max = chip->info->age_time_coeff * U8_MAX;
4533
4534         dev_set_drvdata(dev, ds);
4535
4536         return dsa_register_switch(ds);
4537 }
4538
4539 static void mv88e6xxx_unregister_switch(struct mv88e6xxx_chip *chip)
4540 {
4541         dsa_unregister_switch(chip->ds);
4542 }
4543
4544 static const void *pdata_device_get_match_data(struct device *dev)
4545 {
4546         const struct of_device_id *matches = dev->driver->of_match_table;
4547         const struct dsa_mv88e6xxx_pdata *pdata = dev->platform_data;
4548
4549         for (; matches->name[0] || matches->type[0] || matches->compatible[0];
4550              matches++) {
4551                 if (!strcmp(pdata->compatible, matches->compatible))
4552                         return matches->data;
4553         }
4554         return NULL;
4555 }
4556
4557 static int mv88e6xxx_probe(struct mdio_device *mdiodev)
4558 {
4559         struct dsa_mv88e6xxx_pdata *pdata = mdiodev->dev.platform_data;
4560         const struct mv88e6xxx_info *compat_info = NULL;
4561         struct device *dev = &mdiodev->dev;
4562         struct device_node *np = dev->of_node;
4563         struct mv88e6xxx_chip *chip;
4564         int port;
4565         int err;
4566
4567         if (!np && !pdata)
4568                 return -EINVAL;
4569
4570         if (np)
4571                 compat_info = of_device_get_match_data(dev);
4572
4573         if (pdata) {
4574                 compat_info = pdata_device_get_match_data(dev);
4575
4576                 if (!pdata->netdev)
4577                         return -EINVAL;
4578
4579                 for (port = 0; port < DSA_MAX_PORTS; port++) {
4580                         if (!(pdata->enabled_ports & (1 << port)))
4581                                 continue;
4582                         if (strcmp(pdata->cd.port_names[port], "cpu"))
4583                                 continue;
4584                         pdata->cd.netdev[port] = &pdata->netdev->dev;
4585                         break;
4586                 }
4587         }
4588
4589         if (!compat_info)
4590                 return -EINVAL;
4591
4592         chip = mv88e6xxx_alloc_chip(dev);
4593         if (!chip) {
4594                 err = -ENOMEM;
4595                 goto out;
4596         }
4597
4598         chip->info = compat_info;
4599
4600         err = mv88e6xxx_smi_init(chip, mdiodev->bus, mdiodev->addr);
4601         if (err)
4602                 goto out;
4603
4604         chip->reset = devm_gpiod_get_optional(dev, "reset", GPIOD_OUT_LOW);
4605         if (IS_ERR(chip->reset)) {
4606                 err = PTR_ERR(chip->reset);
4607                 goto out;
4608         }
4609
4610         err = mv88e6xxx_detect(chip);
4611         if (err)
4612                 goto out;
4613
4614         mv88e6xxx_phy_init(chip);
4615
4616         if (chip->info->ops->get_eeprom) {
4617                 if (np)
4618                         of_property_read_u32(np, "eeprom-length",
4619                                              &chip->eeprom_len);
4620                 else
4621                         chip->eeprom_len = pdata->eeprom_len;
4622         }
4623
4624         mutex_lock(&chip->reg_lock);
4625         err = mv88e6xxx_switch_reset(chip);
4626         mutex_unlock(&chip->reg_lock);
4627         if (err)
4628                 goto out;
4629
4630         chip->irq = of_irq_get(np, 0);
4631         if (chip->irq == -EPROBE_DEFER) {
4632                 err = chip->irq;
4633                 goto out;
4634         }
4635
4636         /* Has to be performed before the MDIO bus is created, because
4637          * the PHYs will link their interrupts to these interrupt
4638          * controllers
4639          */
4640         mutex_lock(&chip->reg_lock);
4641         if (chip->irq > 0)
4642                 err = mv88e6xxx_g1_irq_setup(chip);
4643         else
4644                 err = mv88e6xxx_irq_poll_setup(chip);
4645         mutex_unlock(&chip->reg_lock);
4646
4647         if (err)
4648                 goto out;
4649
4650         if (chip->info->g2_irqs > 0) {
4651                 err = mv88e6xxx_g2_irq_setup(chip);
4652                 if (err)
4653                         goto out_g1_irq;
4654         }
4655
4656         err = mv88e6xxx_g1_atu_prob_irq_setup(chip);
4657         if (err)
4658                 goto out_g2_irq;
4659
4660         err = mv88e6xxx_g1_vtu_prob_irq_setup(chip);
4661         if (err)
4662                 goto out_g1_atu_prob_irq;
4663
4664         err = mv88e6xxx_mdios_register(chip, np);
4665         if (err)
4666                 goto out_g1_vtu_prob_irq;
4667
4668         err = mv88e6xxx_register_switch(chip);
4669         if (err)
4670                 goto out_mdio;
4671
4672         return 0;
4673
4674 out_mdio:
4675         mv88e6xxx_mdios_unregister(chip);
4676 out_g1_vtu_prob_irq:
4677         mv88e6xxx_g1_vtu_prob_irq_free(chip);
4678 out_g1_atu_prob_irq:
4679         mv88e6xxx_g1_atu_prob_irq_free(chip);
4680 out_g2_irq:
4681         if (chip->info->g2_irqs > 0)
4682                 mv88e6xxx_g2_irq_free(chip);
4683 out_g1_irq:
4684         if (chip->irq > 0)
4685                 mv88e6xxx_g1_irq_free(chip);
4686         else
4687                 mv88e6xxx_irq_poll_free(chip);
4688 out:
4689         if (pdata)
4690                 dev_put(pdata->netdev);
4691
4692         return err;
4693 }
4694
4695 static void mv88e6xxx_remove(struct mdio_device *mdiodev)
4696 {
4697         struct dsa_switch *ds = dev_get_drvdata(&mdiodev->dev);
4698         struct mv88e6xxx_chip *chip = ds->priv;
4699
4700         if (chip->info->ptp_support) {
4701                 mv88e6xxx_hwtstamp_free(chip);
4702                 mv88e6xxx_ptp_free(chip);
4703         }
4704
4705         mv88e6xxx_phy_destroy(chip);
4706         mv88e6xxx_unregister_switch(chip);
4707         mv88e6xxx_mdios_unregister(chip);
4708
4709         mv88e6xxx_g1_vtu_prob_irq_free(chip);
4710         mv88e6xxx_g1_atu_prob_irq_free(chip);
4711
4712         if (chip->info->g2_irqs > 0)
4713                 mv88e6xxx_g2_irq_free(chip);
4714
4715         if (chip->irq > 0)
4716                 mv88e6xxx_g1_irq_free(chip);
4717         else
4718                 mv88e6xxx_irq_poll_free(chip);
4719 }
4720
4721 static const struct of_device_id mv88e6xxx_of_match[] = {
4722         {
4723                 .compatible = "marvell,mv88e6085",
4724                 .data = &mv88e6xxx_table[MV88E6085],
4725         },
4726         {
4727                 .compatible = "marvell,mv88e6190",
4728                 .data = &mv88e6xxx_table[MV88E6190],
4729         },
4730         { /* sentinel */ },
4731 };
4732
4733 MODULE_DEVICE_TABLE(of, mv88e6xxx_of_match);
4734
4735 static struct mdio_driver mv88e6xxx_driver = {
4736         .probe  = mv88e6xxx_probe,
4737         .remove = mv88e6xxx_remove,
4738         .mdiodrv.driver = {
4739                 .name = "mv88e6085",
4740                 .of_match_table = mv88e6xxx_of_match,
4741         },
4742 };
4743
4744 static int __init mv88e6xxx_init(void)
4745 {
4746         register_switch_driver(&mv88e6xxx_switch_drv);
4747         return mdio_driver_register(&mv88e6xxx_driver);
4748 }
4749 module_init(mv88e6xxx_init);
4750
4751 static void __exit mv88e6xxx_cleanup(void)
4752 {
4753         mdio_driver_unregister(&mv88e6xxx_driver);
4754         unregister_switch_driver(&mv88e6xxx_switch_drv);
4755 }
4756 module_exit(mv88e6xxx_cleanup);
4757
4758 MODULE_AUTHOR("Lennert Buytenhek <buytenh@wantstofly.org>");
4759 MODULE_DESCRIPTION("Driver for Marvell 88E6XXX ethernet switch chips");
4760 MODULE_LICENSE("GPL");