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

1 // SPDX-License-Identifier: (GPL-2.0 OR MIT)
2 /* Microsemi Ocelot Switch driver
8 * Copyright 2020-2021 NXP
11 #include <linux/dsa/ocelot.h>
16 #include "ocelot.h"
32 static struct ocelot *devlink_port_to_ocelot(struct devlink_port *dlp) in devlink_port_to_ocelot()
34 return devlink_priv(dlp->devlink); in devlink_port_to_ocelot()
39 struct ocelot *ocelot = devlink_port_to_ocelot(dlp); in devlink_port_to_port() local
41 return dlp - ocelot->devlink_ports; in devlink_port_to_port()
48 struct ocelot *ocelot = devlink_priv(dl); in ocelot_devlink_sb_pool_get() local
50 return ocelot_sb_pool_get(ocelot, sb_index, pool_index, pool_info); in ocelot_devlink_sb_pool_get()
58 struct ocelot *ocelot = devlink_priv(dl); in ocelot_devlink_sb_pool_set() local
60 return ocelot_sb_pool_set(ocelot, sb_index, pool_index, size, in ocelot_devlink_sb_pool_set()
68 struct ocelot *ocelot = devlink_port_to_ocelot(dlp); in ocelot_devlink_sb_port_pool_get() local
71 return ocelot_sb_port_pool_get(ocelot, port, sb_index, pool_index, in ocelot_devlink_sb_port_pool_get()
80 struct ocelot *ocelot = devlink_port_to_ocelot(dlp); in ocelot_devlink_sb_port_pool_set() local
83 return ocelot_sb_port_pool_set(ocelot, port, sb_index, pool_index, in ocelot_devlink_sb_port_pool_set()
93 struct ocelot *ocelot = devlink_port_to_ocelot(dlp); in ocelot_devlink_sb_tc_pool_bind_get() local
96 return ocelot_sb_tc_pool_bind_get(ocelot, port, sb_index, tc_index, in ocelot_devlink_sb_tc_pool_bind_get()
108 struct ocelot *ocelot = devlink_port_to_ocelot(dlp); in ocelot_devlink_sb_tc_pool_bind_set() local
111 return ocelot_sb_tc_pool_bind_set(ocelot, port, sb_index, tc_index, in ocelot_devlink_sb_tc_pool_bind_set()
119 struct ocelot *ocelot = devlink_priv(dl); in ocelot_devlink_sb_occ_snapshot() local
121 return ocelot_sb_occ_snapshot(ocelot, sb_index); in ocelot_devlink_sb_occ_snapshot()
127 struct ocelot *ocelot = devlink_priv(dl); in ocelot_devlink_sb_occ_max_clear() local
129 return ocelot_sb_occ_max_clear(ocelot, sb_index); in ocelot_devlink_sb_occ_max_clear()
137 struct ocelot *ocelot = devlink_port_to_ocelot(dlp); in ocelot_devlink_sb_occ_port_pool_get() local
140 return ocelot_sb_occ_port_pool_get(ocelot, port, sb_index, pool_index, in ocelot_devlink_sb_occ_port_pool_get()
150 struct ocelot *ocelot = devlink_port_to_ocelot(dlp); in ocelot_devlink_sb_occ_tc_port_bind_get() local
153 return ocelot_sb_occ_tc_port_bind_get(ocelot, port, sb_index, in ocelot_devlink_sb_occ_tc_port_bind_get()
171 int ocelot_port_devlink_init(struct ocelot *ocelot, int port, in ocelot_port_devlink_init() argument
174 struct devlink_port *dlp = &ocelot->devlink_ports[port]; in ocelot_port_devlink_init()
175 int id_len = sizeof(ocelot->base_mac); in ocelot_port_devlink_init()
176 struct devlink *dl = ocelot->devlink; in ocelot_port_devlink_init()
180 memcpy(attrs.switch_id.id, &ocelot->base_mac, id_len); in ocelot_port_devlink_init()
190 void ocelot_port_devlink_teardown(struct ocelot *ocelot, int port) in ocelot_port_devlink_teardown() argument
192 struct devlink_port *dlp = &ocelot->devlink_ports[port]; in ocelot_port_devlink_teardown()
201 struct ocelot *ocelot = priv->port.ocelot; in ocelot_setup_tc_cls_flower() local
202 int port = priv->port.index; in ocelot_setup_tc_cls_flower()
205 return -EOPNOTSUPP; in ocelot_setup_tc_cls_flower()
207 switch (f->command) { in ocelot_setup_tc_cls_flower()
209 return ocelot_cls_flower_replace(ocelot, port, f, ingress); in ocelot_setup_tc_cls_flower()
211 return ocelot_cls_flower_destroy(ocelot, port, f, ingress); in ocelot_setup_tc_cls_flower()
213 return ocelot_cls_flower_stats(ocelot, port, f, ingress); in ocelot_setup_tc_cls_flower()
215 return -EOPNOTSUPP; in ocelot_setup_tc_cls_flower()
224 struct flow_action_entry *action = &f->rule->action.entries[0]; in ocelot_setup_tc_cls_matchall_police()
225 struct ocelot *ocelot = priv->port.ocelot; in ocelot_setup_tc_cls_matchall_police() local
227 int port = priv->port.index; in ocelot_setup_tc_cls_matchall_police()
232 return -EOPNOTSUPP; in ocelot_setup_tc_cls_matchall_police()
235 if (priv->tc.police_id && priv->tc.police_id != f->cookie) { in ocelot_setup_tc_cls_matchall_police()
238 return -EEXIST; in ocelot_setup_tc_cls_matchall_police()
241 err = ocelot_policer_validate(&f->rule->action, action, extack); in ocelot_setup_tc_cls_matchall_police()
245 pol.rate = (u32)div_u64(action->police.rate_bytes_ps, 1000) * 8; in ocelot_setup_tc_cls_matchall_police()
246 pol.burst = action->police.burst; in ocelot_setup_tc_cls_matchall_police()
248 err = ocelot_port_policer_add(ocelot, port, &pol); in ocelot_setup_tc_cls_matchall_police()
254 priv->tc.police_id = f->cookie; in ocelot_setup_tc_cls_matchall_police()
255 priv->tc.offload_cnt++; in ocelot_setup_tc_cls_matchall_police()
265 struct flow_action *action = &f->rule->action; in ocelot_setup_tc_cls_matchall_mirred()
266 struct ocelot *ocelot = priv->port.ocelot; in ocelot_setup_tc_cls_matchall_mirred() local
271 if (f->common.protocol != htons(ETH_P_ALL)) in ocelot_setup_tc_cls_matchall_mirred()
272 return -EOPNOTSUPP; in ocelot_setup_tc_cls_matchall_mirred()
275 return -EOPNOTSUPP; in ocelot_setup_tc_cls_matchall_mirred()
277 a = &action->entries[0]; in ocelot_setup_tc_cls_matchall_mirred()
278 if (!a->dev) in ocelot_setup_tc_cls_matchall_mirred()
279 return -EINVAL; in ocelot_setup_tc_cls_matchall_mirred()
281 if (!ocelot_netdevice_dev_check(a->dev)) { in ocelot_setup_tc_cls_matchall_mirred()
283 "Destination not an ocelot port"); in ocelot_setup_tc_cls_matchall_mirred()
284 return -EOPNOTSUPP; in ocelot_setup_tc_cls_matchall_mirred()
287 other_priv = netdev_priv(a->dev); in ocelot_setup_tc_cls_matchall_mirred()
289 err = ocelot_port_mirror_add(ocelot, priv->port.index, in ocelot_setup_tc_cls_matchall_mirred()
290 other_priv->port.index, ingress, extack); in ocelot_setup_tc_cls_matchall_mirred()
295 priv->tc.ingress_mirred_id = f->cookie; in ocelot_setup_tc_cls_matchall_mirred()
297 priv->tc.egress_mirred_id = f->cookie; in ocelot_setup_tc_cls_matchall_mirred()
298 priv->tc.offload_cnt++; in ocelot_setup_tc_cls_matchall_mirred()
306 struct ocelot *ocelot = priv->port.ocelot; in ocelot_del_tc_cls_matchall_police() local
307 int port = priv->port.index; in ocelot_del_tc_cls_matchall_police()
310 err = ocelot_port_policer_del(ocelot, port); in ocelot_del_tc_cls_matchall_police()
317 priv->tc.police_id = 0; in ocelot_del_tc_cls_matchall_police()
318 priv->tc.offload_cnt--; in ocelot_del_tc_cls_matchall_police()
327 struct ocelot *ocelot = priv->port.ocelot; in ocelot_del_tc_cls_matchall_mirred() local
328 int port = priv->port.index; in ocelot_del_tc_cls_matchall_mirred()
330 ocelot_port_mirror_del(ocelot, port, ingress); in ocelot_del_tc_cls_matchall_mirred()
333 priv->tc.ingress_mirred_id = 0; in ocelot_del_tc_cls_matchall_mirred()
335 priv->tc.egress_mirred_id = 0; in ocelot_del_tc_cls_matchall_mirred()
336 priv->tc.offload_cnt--; in ocelot_del_tc_cls_matchall_mirred()
345 struct netlink_ext_ack *extack = f->common.extack; in ocelot_setup_tc_cls_matchall()
348 switch (f->command) { in ocelot_setup_tc_cls_matchall()
350 if (!flow_offload_has_one_action(&f->rule->action)) { in ocelot_setup_tc_cls_matchall()
353 return -EOPNOTSUPP; in ocelot_setup_tc_cls_matchall()
356 if (priv->tc.block_shared) { in ocelot_setup_tc_cls_matchall()
359 return -EOPNOTSUPP; in ocelot_setup_tc_cls_matchall()
362 action = &f->rule->action.entries[0]; in ocelot_setup_tc_cls_matchall()
364 switch (action->id) { in ocelot_setup_tc_cls_matchall()
376 return -EOPNOTSUPP; in ocelot_setup_tc_cls_matchall()
381 action = &f->rule->action.entries[0]; in ocelot_setup_tc_cls_matchall()
383 if (f->cookie == priv->tc.police_id) in ocelot_setup_tc_cls_matchall()
385 else if (f->cookie == priv->tc.ingress_mirred_id || in ocelot_setup_tc_cls_matchall()
386 f->cookie == priv->tc.egress_mirred_id) in ocelot_setup_tc_cls_matchall()
390 return -ENOENT; in ocelot_setup_tc_cls_matchall()
395 return -EOPNOTSUPP; in ocelot_setup_tc_cls_matchall()
405 if (!tc_cls_can_offload_and_chain0(priv->dev, type_data)) in ocelot_setup_tc_block_cb()
406 return -EOPNOTSUPP; in ocelot_setup_tc_block_cb()
414 return -EOPNOTSUPP; in ocelot_setup_tc_block_cb()
442 if (f->binder_type == FLOW_BLOCK_BINDER_TYPE_CLSACT_INGRESS) { in ocelot_setup_tc_block()
444 priv->tc.block_shared = f->block_shared; in ocelot_setup_tc_block()
445 } else if (f->binder_type == FLOW_BLOCK_BINDER_TYPE_CLSACT_EGRESS) { in ocelot_setup_tc_block()
448 return -EOPNOTSUPP; in ocelot_setup_tc_block()
451 f->driver_block_list = &ocelot_block_cb_list; in ocelot_setup_tc_block()
453 switch (f->command) { in ocelot_setup_tc_block()
456 return -EBUSY; in ocelot_setup_tc_block()
463 list_add_tail(&block_cb->driver_list, f->driver_block_list); in ocelot_setup_tc_block()
466 block_cb = flow_block_cb_lookup(f->block, cb, priv); in ocelot_setup_tc_block()
468 return -ENOENT; in ocelot_setup_tc_block()
471 list_del(&block_cb->driver_list); in ocelot_setup_tc_block()
474 return -EOPNOTSUPP; in ocelot_setup_tc_block()
487 return -EOPNOTSUPP; in ocelot_setup_tc()
496 struct ocelot_port *ocelot_port = &priv->port; in ocelot_vlan_vid_add()
497 struct ocelot *ocelot = ocelot_port->ocelot; in ocelot_vlan_vid_add() local
498 int port = priv->port.index; in ocelot_vlan_vid_add()
501 ret = ocelot_vlan_add(ocelot, port, vid, pvid, untagged); in ocelot_vlan_vid_add()
506 ocelot_mact_learn(ocelot, PGID_CPU, dev->dev_addr, vid, in ocelot_vlan_vid_add()
515 struct ocelot *ocelot = priv->port.ocelot; in ocelot_vlan_vid_del() local
516 int port = priv->port.index; in ocelot_vlan_vid_del()
526 ret = ocelot_vlan_del(ocelot, port, vid); in ocelot_vlan_vid_del()
531 ocelot_mact_forget(ocelot, dev->dev_addr, vid); in ocelot_vlan_vid_del()
540 phylink_start(priv->phylink); in ocelot_port_open()
549 phylink_stop(priv->phylink); in ocelot_port_stop()
557 struct ocelot_port *ocelot_port = &priv->port; in ocelot_port_xmit()
558 struct ocelot *ocelot = ocelot_port->ocelot; in ocelot_port_xmit() local
559 int port = priv->port.index; in ocelot_port_xmit()
563 !ocelot_can_inject(ocelot, 0)) in ocelot_port_xmit()
567 if (ocelot->ptp && (skb_shinfo(skb)->tx_flags & SKBTX_HW_TSTAMP)) { in ocelot_port_xmit()
570 if (ocelot_port_txtstamp_request(ocelot, port, skb, &clone)) { in ocelot_port_xmit()
576 OCELOT_SKB_CB(skb)->clone = clone; in ocelot_port_xmit()
582 ocelot_fdma_inject_frame(ocelot, port, rew_op, skb, dev); in ocelot_port_xmit()
584 ocelot_port_inject_frame(ocelot, port, 0, rew_op, skb); in ocelot_port_xmit()
599 struct ocelot *ocelot; member
623 struct ocelot *ocelot = w->ocelot; in ocelot_mact_work() local
625 switch (w->type) { in ocelot_mact_work()
627 ocelot_mact_learn(ocelot, w->learn.pgid, w->learn.addr, in ocelot_mact_work()
628 w->learn.vid, w->learn.entry_type); in ocelot_mact_work()
631 ocelot_mact_forget(ocelot, w->forget.addr, w->forget.vid); in ocelot_mact_work()
640 static int ocelot_enqueue_mact_action(struct ocelot *ocelot, in ocelot_enqueue_mact_action() argument
646 return -ENOMEM; in ocelot_enqueue_mact_action()
648 w->ocelot = ocelot; in ocelot_enqueue_mact_action()
649 INIT_WORK(&w->work, ocelot_mact_work); in ocelot_enqueue_mact_action()
650 queue_work(ocelot->owq, &w->work); in ocelot_enqueue_mact_action()
658 struct ocelot_port *ocelot_port = &priv->port; in ocelot_mc_unsync()
659 struct ocelot *ocelot = ocelot_port->ocelot; in ocelot_mc_unsync() local
666 return ocelot_enqueue_mact_action(ocelot, &w); in ocelot_mc_unsync()
672 struct ocelot_port *ocelot_port = &priv->port; in ocelot_mc_sync()
673 struct ocelot *ocelot = ocelot_port->ocelot; in ocelot_mc_sync() local
682 return ocelot_enqueue_mact_action(ocelot, &w); in ocelot_mc_sync()
688 struct ocelot *ocelot = priv->port.ocelot; in ocelot_set_rx_mode() local
696 val = GENMASK(ocelot->num_phys_ports - 1, 0); in ocelot_set_rx_mode()
697 for_each_nonreserved_multicast_dest_pgid(ocelot, i) in ocelot_set_rx_mode()
698 ocelot_write_rix(ocelot, val, ANA_PGID_PGID, i); in ocelot_set_rx_mode()
706 struct ocelot_port *ocelot_port = &priv->port; in ocelot_port_set_mac_address()
707 struct ocelot *ocelot = ocelot_port->ocelot; in ocelot_port_set_mac_address() local
711 ocelot_mact_learn(ocelot, PGID_CPU, addr->sa_data, in ocelot_port_set_mac_address()
714 ocelot_mact_forget(ocelot, dev->dev_addr, OCELOT_STANDALONE_PVID); in ocelot_port_set_mac_address()
716 eth_hw_addr_set(dev, addr->sa_data); in ocelot_port_set_mac_address()
724 struct ocelot *ocelot = priv->port.ocelot; in ocelot_get_stats64() local
725 int port = priv->port.index; in ocelot_get_stats64()
727 return ocelot_port_get_stats64(ocelot, port, stats); in ocelot_get_stats64()
737 struct ocelot_port *ocelot_port = &priv->port; in ocelot_port_fdb_add()
738 struct ocelot *ocelot = ocelot_port->ocelot; in ocelot_port_fdb_add() local
739 int port = priv->port.index; in ocelot_port_fdb_add()
741 return ocelot_fdb_add(ocelot, port, addr, vid, ocelot_port->bridge); in ocelot_port_fdb_add()
750 struct ocelot_port *ocelot_port = &priv->port; in ocelot_port_fdb_del()
751 struct ocelot *ocelot = ocelot_port->ocelot; in ocelot_port_fdb_del() local
752 int port = priv->port.index; in ocelot_port_fdb_del()
754 return ocelot_fdb_del(ocelot, port, addr, vid, ocelot_port->bridge); in ocelot_port_fdb_del()
761 u32 portid = NETLINK_CB(dump->cb->skb).portid; in ocelot_port_fdb_do_dump()
762 u32 seq = dump->cb->nlh->nlmsg_seq; in ocelot_port_fdb_do_dump()
766 if (dump->idx < dump->cb->args[2]) in ocelot_port_fdb_do_dump()
769 nlh = nlmsg_put(dump->skb, portid, seq, RTM_NEWNEIGH, in ocelot_port_fdb_do_dump()
772 return -EMSGSIZE; in ocelot_port_fdb_do_dump()
775 ndm->ndm_family = AF_BRIDGE; in ocelot_port_fdb_do_dump()
776 ndm->ndm_pad1 = 0; in ocelot_port_fdb_do_dump()
777 ndm->ndm_pad2 = 0; in ocelot_port_fdb_do_dump()
778 ndm->ndm_flags = NTF_SELF; in ocelot_port_fdb_do_dump()
779 ndm->ndm_type = 0; in ocelot_port_fdb_do_dump()
780 ndm->ndm_ifindex = dump->dev->ifindex; in ocelot_port_fdb_do_dump()
781 ndm->ndm_state = is_static ? NUD_NOARP : NUD_REACHABLE; in ocelot_port_fdb_do_dump()
783 if (nla_put(dump->skb, NDA_LLADDR, ETH_ALEN, addr)) in ocelot_port_fdb_do_dump()
786 if (vid && nla_put_u16(dump->skb, NDA_VLAN, vid)) in ocelot_port_fdb_do_dump()
789 nlmsg_end(dump->skb, nlh); in ocelot_port_fdb_do_dump()
792 dump->idx++; in ocelot_port_fdb_do_dump()
796 nlmsg_cancel(dump->skb, nlh); in ocelot_port_fdb_do_dump()
797 return -EMSGSIZE; in ocelot_port_fdb_do_dump()
806 struct ocelot *ocelot = priv->port.ocelot; in ocelot_port_fdb_dump() local
813 int port = priv->port.index; in ocelot_port_fdb_dump()
816 ret = ocelot_fdb_dump(ocelot, port, ocelot_port_fdb_do_dump, &dump); in ocelot_port_fdb_dump()
835 static void ocelot_vlan_mode(struct ocelot *ocelot, int port, in ocelot_vlan_mode() argument
841 val = ocelot_read(ocelot, ANA_VLANMASK); in ocelot_vlan_mode()
846 ocelot_write(ocelot, val, ANA_VLANMASK); in ocelot_vlan_mode()
852 netdev_features_t changed = dev->features ^ features; in ocelot_set_features()
854 struct ocelot *ocelot = priv->port.ocelot; in ocelot_set_features() local
855 int port = priv->port.index; in ocelot_set_features()
857 if ((dev->features & NETIF_F_HW_TC) > (features & NETIF_F_HW_TC) && in ocelot_set_features()
858 priv->tc.offload_cnt) { in ocelot_set_features()
861 return -EBUSY; in ocelot_set_features()
865 ocelot_vlan_mode(ocelot, port, features); in ocelot_set_features()
873 struct ocelot *ocelot = priv->port.ocelot; in ocelot_ioctl() local
874 int port = priv->port.index; in ocelot_ioctl()
879 if (!phy_has_hwtstamp(dev->phydev) && ocelot->ptp) { in ocelot_ioctl()
882 return ocelot_hwstamp_set(ocelot, port, ifr); in ocelot_ioctl()
884 return ocelot_hwstamp_get(ocelot, port, ifr); in ocelot_ioctl()
888 return phy_mii_ioctl(dev->phydev, ifr, cmd); in ocelot_ioctl()
894 struct ocelot_port *ocelot_port = &priv->port; in ocelot_change_mtu()
895 struct ocelot *ocelot = ocelot_port->ocelot; in ocelot_change_mtu() local
897 ocelot_port_set_maxlen(ocelot, priv->port.index, new_mtu); in ocelot_change_mtu()
898 WRITE_ONCE(dev->mtu, new_mtu); in ocelot_change_mtu()
921 struct net_device *ocelot_port_to_netdev(struct ocelot *ocelot, int port) in ocelot_port_to_netdev() argument
923 struct ocelot_port *ocelot_port = ocelot->ports[port]; in ocelot_port_to_netdev()
931 return priv->dev; in ocelot_port_to_netdev()
937 return dev->netdev_ops == &ocelot_port_netdev_ops; in ocelot_netdevice_dev_check()
945 return -EINVAL; in ocelot_netdev_to_port()
949 return priv->port.index; in ocelot_netdev_to_port()
956 struct ocelot *ocelot = priv->port.ocelot; in ocelot_port_get_strings() local
957 int port = priv->port.index; in ocelot_port_get_strings()
959 ocelot_get_strings(ocelot, port, sset, data); in ocelot_port_get_strings()
967 struct ocelot *ocelot = priv->port.ocelot; in ocelot_port_get_ethtool_stats() local
968 int port = priv->port.index; in ocelot_port_get_ethtool_stats()
970 ocelot_get_ethtool_stats(ocelot, port, data); in ocelot_port_get_ethtool_stats()
976 struct ocelot *ocelot = priv->port.ocelot; in ocelot_port_get_sset_count() local
977 int port = priv->port.index; in ocelot_port_get_sset_count()
979 return ocelot_get_sset_count(ocelot, port, sset); in ocelot_port_get_sset_count()
986 struct ocelot *ocelot = priv->port.ocelot; in ocelot_port_get_ts_info() local
987 int port = priv->port.index; in ocelot_port_get_ts_info()
989 if (!ocelot->ptp) in ocelot_port_get_ts_info()
992 return ocelot_get_ts_info(ocelot, port, info); in ocelot_port_get_ts_info()
1004 static void ocelot_port_attr_stp_state_set(struct ocelot *ocelot, int port, in ocelot_port_attr_stp_state_set() argument
1007 ocelot_bridge_stp_state_set(ocelot, port, state); in ocelot_port_attr_stp_state_set()
1010 static void ocelot_port_attr_ageing_set(struct ocelot *ocelot, int port, in ocelot_port_attr_ageing_set() argument
1016 ocelot_set_ageing_time(ocelot, ageing_time); in ocelot_port_attr_ageing_set()
1019 static void ocelot_port_attr_mc_set(struct ocelot *ocelot, int port, bool mc) in ocelot_port_attr_mc_set() argument
1029 ocelot_rmw_gix(ocelot, val, cpu_fwd_mcast, in ocelot_port_attr_mc_set()
1038 struct ocelot *ocelot = priv->port.ocelot; in ocelot_port_attr_set() local
1039 int port = priv->port.index; in ocelot_port_attr_set()
1045 switch (attr->id) { in ocelot_port_attr_set()
1047 ocelot_port_attr_stp_state_set(ocelot, port, attr->u.stp_state); in ocelot_port_attr_set()
1050 ocelot_port_attr_ageing_set(ocelot, port, attr->u.ageing_time); in ocelot_port_attr_set()
1053 ocelot_port_vlan_filtering(ocelot, port, attr->u.vlan_filtering, in ocelot_port_attr_set()
1057 ocelot_port_attr_mc_set(ocelot, port, !attr->u.mc_disabled); in ocelot_port_attr_set()
1060 err = ocelot_port_pre_bridge_flags(ocelot, port, in ocelot_port_attr_set()
1061 attr->u.brport_flags); in ocelot_port_attr_set()
1064 ocelot_port_bridge_flags(ocelot, port, attr->u.brport_flags); in ocelot_port_attr_set()
1067 err = -EOPNOTSUPP; in ocelot_port_attr_set()
1078 struct ocelot_port *ocelot_port = &priv->port; in ocelot_vlan_vid_prepare()
1079 struct ocelot *ocelot = ocelot_port->ocelot; in ocelot_vlan_vid_prepare() local
1080 int port = priv->port.index; in ocelot_vlan_vid_prepare()
1082 return ocelot_vlan_prepare(ocelot, port, vid, pvid, untagged, extack); in ocelot_vlan_vid_prepare()
1089 bool untagged = vlan->flags & BRIDGE_VLAN_INFO_UNTAGGED; in ocelot_port_obj_add_vlan()
1090 bool pvid = vlan->flags & BRIDGE_VLAN_INFO_PVID; in ocelot_port_obj_add_vlan()
1093 ret = ocelot_vlan_vid_prepare(dev, vlan->vid, pvid, untagged, extack); in ocelot_port_obj_add_vlan()
1097 return ocelot_vlan_vid_add(dev, vlan->vid, pvid, untagged); in ocelot_port_obj_add_vlan()
1104 struct ocelot_port *ocelot_port = &priv->port; in ocelot_port_obj_add_mdb()
1105 struct ocelot *ocelot = ocelot_port->ocelot; in ocelot_port_obj_add_mdb() local
1106 int port = priv->port.index; in ocelot_port_obj_add_mdb()
1108 return ocelot_port_mdb_add(ocelot, port, mdb, ocelot_port->bridge); in ocelot_port_obj_add_mdb()
1115 struct ocelot_port *ocelot_port = &priv->port; in ocelot_port_obj_del_mdb()
1116 struct ocelot *ocelot = ocelot_port->ocelot; in ocelot_port_obj_del_mdb() local
1117 int port = priv->port.index; in ocelot_port_obj_del_mdb()
1119 return ocelot_port_mdb_del(ocelot, port, mdb, ocelot_port->bridge); in ocelot_port_obj_del_mdb()
1126 struct ocelot_port *ocelot_port = &priv->port; in ocelot_port_obj_mrp_add()
1127 struct ocelot *ocelot = ocelot_port->ocelot; in ocelot_port_obj_mrp_add() local
1128 int port = priv->port.index; in ocelot_port_obj_mrp_add()
1130 return ocelot_mrp_add(ocelot, port, mrp); in ocelot_port_obj_mrp_add()
1137 struct ocelot_port *ocelot_port = &priv->port; in ocelot_port_obj_mrp_del()
1138 struct ocelot *ocelot = ocelot_port->ocelot; in ocelot_port_obj_mrp_del() local
1139 int port = priv->port.index; in ocelot_port_obj_mrp_del()
1141 return ocelot_mrp_del(ocelot, port, mrp); in ocelot_port_obj_mrp_del()
1149 struct ocelot_port *ocelot_port = &priv->port; in ocelot_port_obj_mrp_add_ring_role()
1150 struct ocelot *ocelot = ocelot_port->ocelot; in ocelot_port_obj_mrp_add_ring_role() local
1151 int port = priv->port.index; in ocelot_port_obj_mrp_add_ring_role()
1153 return ocelot_mrp_add_ring_role(ocelot, port, mrp); in ocelot_port_obj_mrp_add_ring_role()
1161 struct ocelot_port *ocelot_port = &priv->port; in ocelot_port_obj_mrp_del_ring_role()
1162 struct ocelot *ocelot = ocelot_port->ocelot; in ocelot_port_obj_mrp_del_ring_role() local
1163 int port = priv->port.index; in ocelot_port_obj_mrp_del_ring_role()
1165 return ocelot_mrp_del_ring_role(ocelot, port, mrp); in ocelot_port_obj_mrp_del_ring_role()
1178 switch (obj->id) { in ocelot_port_obj_add()
1195 return -EOPNOTSUPP; in ocelot_port_obj_add()
1210 switch (obj->id) { in ocelot_port_obj_del()
1213 SWITCHDEV_OBJ_PORT_VLAN(obj)->vid); in ocelot_port_obj_del()
1226 return -EOPNOTSUPP; in ocelot_port_obj_del()
1232 static void ocelot_inherit_brport_flags(struct ocelot *ocelot, int port, in ocelot_inherit_brport_flags() argument
1244 ocelot_port_bridge_flags(ocelot, port, flags); in ocelot_inherit_brport_flags()
1247 static void ocelot_clear_brport_flags(struct ocelot *ocelot, int port) in ocelot_clear_brport_flags() argument
1254 ocelot_port_bridge_flags(ocelot, port, flags); in ocelot_clear_brport_flags()
1257 static int ocelot_switchdev_sync(struct ocelot *ocelot, int port, in ocelot_switchdev_sync() argument
1265 ocelot_inherit_brport_flags(ocelot, port, brport_dev); in ocelot_switchdev_sync()
1268 ocelot_bridge_stp_state_set(ocelot, port, stp_state); in ocelot_switchdev_sync()
1271 ocelot_port_attr_ageing_set(ocelot, port, ageing_time); in ocelot_switchdev_sync()
1273 return ocelot_port_vlan_filtering(ocelot, port, in ocelot_switchdev_sync()
1278 static int ocelot_switchdev_unsync(struct ocelot *ocelot, int port) in ocelot_switchdev_unsync() argument
1282 err = ocelot_port_vlan_filtering(ocelot, port, false, NULL); in ocelot_switchdev_unsync()
1286 ocelot_clear_brport_flags(ocelot, port); in ocelot_switchdev_unsync()
1288 ocelot_bridge_stp_state_set(ocelot, port, BR_STATE_FORWARDING); in ocelot_switchdev_unsync()
1293 static int ocelot_bridge_num_get(struct ocelot *ocelot, in ocelot_bridge_num_get() argument
1296 int bridge_num = ocelot_bridge_num_find(ocelot, bridge_dev); in ocelot_bridge_num_get()
1300 bridge_num = find_first_zero_bit(&ocelot->bridges, in ocelot_bridge_num_get()
1301 ocelot->num_phys_ports); in ocelot_bridge_num_get()
1303 set_bit(bridge_num, &ocelot->bridges); in ocelot_bridge_num_get()
1309 static void ocelot_bridge_num_put(struct ocelot *ocelot, in ocelot_bridge_num_put() argument
1316 if (!ocelot_bridge_num_find(ocelot, bridge_dev)) in ocelot_bridge_num_put()
1317 clear_bit(bridge_num, &ocelot->bridges); in ocelot_bridge_num_put()
1326 struct ocelot_port *ocelot_port = &priv->port; in ocelot_netdevice_bridge_join()
1327 struct ocelot *ocelot = ocelot_port->ocelot; in ocelot_netdevice_bridge_join() local
1328 int port = priv->port.index; in ocelot_netdevice_bridge_join()
1331 bridge_num = ocelot_bridge_num_get(ocelot, bridge); in ocelot_netdevice_bridge_join()
1333 err = ocelot_port_bridge_join(ocelot, port, bridge, bridge_num, in ocelot_netdevice_bridge_join()
1345 err = ocelot_switchdev_sync(ocelot, port, brport_dev, bridge, extack); in ocelot_netdevice_bridge_join()
1356 ocelot_port_bridge_leave(ocelot, port, bridge); in ocelot_netdevice_bridge_join()
1358 ocelot_bridge_num_put(ocelot, bridge, bridge_num); in ocelot_netdevice_bridge_join()
1377 struct ocelot_port *ocelot_port = &priv->port; in ocelot_netdevice_bridge_leave()
1378 struct ocelot *ocelot = ocelot_port->ocelot; in ocelot_netdevice_bridge_leave() local
1379 int bridge_num = ocelot_port->bridge_num; in ocelot_netdevice_bridge_leave()
1380 int port = priv->port.index; in ocelot_netdevice_bridge_leave()
1383 err = ocelot_switchdev_unsync(ocelot, port); in ocelot_netdevice_bridge_leave()
1387 ocelot_port_bridge_leave(ocelot, port, bridge); in ocelot_netdevice_bridge_leave()
1388 ocelot_bridge_num_put(ocelot, bridge, bridge_num); in ocelot_netdevice_bridge_leave()
1399 struct ocelot_port *ocelot_port = &priv->port; in ocelot_netdevice_lag_join()
1400 struct ocelot *ocelot = ocelot_port->ocelot; in ocelot_netdevice_lag_join() local
1402 int port = priv->port.index; in ocelot_netdevice_lag_join()
1405 err = ocelot_port_lag_join(ocelot, port, bond, info, extack); in ocelot_netdevice_lag_join()
1406 if (err == -EOPNOTSUPP) in ocelot_netdevice_lag_join()
1421 ocelot_port_lag_leave(ocelot, port, bond); in ocelot_netdevice_lag_join()
1441 struct ocelot_port *ocelot_port = &priv->port; in ocelot_netdevice_lag_leave()
1442 struct ocelot *ocelot = ocelot_port->ocelot; in ocelot_netdevice_lag_leave() local
1444 int port = priv->port.index; in ocelot_netdevice_lag_leave()
1446 ocelot_port_lag_leave(ocelot, port, bond); in ocelot_netdevice_lag_leave()
1462 extack = netdev_notifier_info_to_extack(&info->info); in ocelot_netdevice_changeupper()
1464 if (netif_is_bridge_master(info->upper_dev)) { in ocelot_netdevice_changeupper()
1465 if (info->linking) in ocelot_netdevice_changeupper()
1467 info->upper_dev, in ocelot_netdevice_changeupper()
1471 info->upper_dev); in ocelot_netdevice_changeupper()
1473 if (netif_is_lag_master(info->upper_dev)) { in ocelot_netdevice_changeupper()
1474 if (info->linking) in ocelot_netdevice_changeupper()
1475 err = ocelot_netdevice_lag_join(dev, info->upper_dev, in ocelot_netdevice_changeupper()
1476 info->upper_info, extack); in ocelot_netdevice_changeupper()
1478 ocelot_netdevice_lag_leave(dev, info->upper_dev); in ocelot_netdevice_changeupper()
1500 struct ocelot_port *ocelot_port = &priv->port; in ocelot_netdevice_lag_changeupper()
1502 if (ocelot_port->bond != dev) in ocelot_netdevice_lag_changeupper()
1518 if (netif_is_bridge_master(info->upper_dev) && !info->linking) in ocelot_netdevice_prechangeupper()
1521 if (netif_is_lag_master(info->upper_dev) && !info->linking) in ocelot_netdevice_prechangeupper()
1522 ocelot_netdevice_pre_lag_leave(dev, info->upper_dev); in ocelot_netdevice_prechangeupper()
1537 struct ocelot_port *ocelot_port = &priv->port; in ocelot_netdevice_lag_prechangeupper()
1539 if (ocelot_port->bond != dev) in ocelot_netdevice_lag_prechangeupper()
1555 bool is_active = info->link_up && info->tx_enabled; in ocelot_netdevice_changelowerstate()
1556 struct ocelot_port *ocelot_port = &priv->port; in ocelot_netdevice_changelowerstate()
1557 struct ocelot *ocelot = ocelot_port->ocelot; in ocelot_netdevice_changelowerstate() local
1558 int port = priv->port.index; in ocelot_netdevice_changelowerstate()
1560 if (!ocelot_port->bond) in ocelot_netdevice_changelowerstate()
1563 if (ocelot_port->lag_tx_active == is_active) in ocelot_netdevice_changelowerstate()
1566 ocelot_port_lag_change(ocelot, port, is_active); in ocelot_netdevice_changelowerstate()
1606 info->lower_state_info); in ocelot_netdevice_event()
1676 struct net_device *ndev = to_net_dev(config->dev); in vsc7514_phylink_mac_config()
1678 struct ocelot *ocelot = priv->port.ocelot; in vsc7514_phylink_mac_config() local
1679 int port = priv->port.index; in vsc7514_phylink_mac_config()
1681 ocelot_phylink_mac_config(ocelot, port, link_an_mode, state); in vsc7514_phylink_mac_config()
1688 struct net_device *ndev = to_net_dev(config->dev); in vsc7514_phylink_mac_link_down()
1690 struct ocelot *ocelot = priv->port.ocelot; in vsc7514_phylink_mac_link_down() local
1691 int port = priv->port.index; in vsc7514_phylink_mac_link_down()
1693 ocelot_phylink_mac_link_down(ocelot, port, link_an_mode, interface, in vsc7514_phylink_mac_link_down()
1704 struct net_device *ndev = to_net_dev(config->dev); in vsc7514_phylink_mac_link_up()
1706 struct ocelot *ocelot = priv->port.ocelot; in vsc7514_phylink_mac_link_up() local
1707 int port = priv->port.index; in vsc7514_phylink_mac_link_up()
1709 ocelot_phylink_mac_link_up(ocelot, port, phydev, link_an_mode, in vsc7514_phylink_mac_link_up()
1720 static int ocelot_port_phylink_create(struct ocelot *ocelot, int port, in ocelot_port_phylink_create() argument
1723 struct ocelot_port *ocelot_port = ocelot->ports[port]; in ocelot_port_phylink_create()
1725 struct device *dev = ocelot->dev; in ocelot_port_phylink_create()
1732 * specify a phy-mode in ocelot_port_phylink_create()
1742 return -EINVAL; in ocelot_port_phylink_create()
1745 ocelot_port->phy_mode = phy_mode; in ocelot_port_phylink_create()
1747 err = ocelot_port_configure_serdes(ocelot, port, portnp); in ocelot_port_phylink_create()
1753 priv->phylink_config.dev = &priv->dev->dev; in ocelot_port_phylink_create()
1754 priv->phylink_config.type = PHYLINK_NETDEV; in ocelot_port_phylink_create()
1755 priv->phylink_config.mac_capabilities = MAC_ASYM_PAUSE | MAC_SYM_PAUSE | in ocelot_port_phylink_create()
1758 __set_bit(ocelot_port->phy_mode, in ocelot_port_phylink_create()
1759 priv->phylink_config.supported_interfaces); in ocelot_port_phylink_create()
1761 phylink = phylink_create(&priv->phylink_config, in ocelot_port_phylink_create()
1770 priv->phylink = phylink; in ocelot_port_phylink_create()
1776 priv->phylink = NULL; in ocelot_port_phylink_create()
1783 int ocelot_probe_port(struct ocelot *ocelot, int port, struct regmap *target, in ocelot_probe_port() argument
1793 return -ENOMEM; in ocelot_probe_port()
1794 SET_NETDEV_DEV(dev, ocelot->dev); in ocelot_probe_port()
1796 priv->dev = dev; in ocelot_probe_port()
1797 ocelot_port = &priv->port; in ocelot_probe_port()
1798 ocelot_port->ocelot = ocelot; in ocelot_probe_port()
1799 ocelot_port->index = port; in ocelot_probe_port()
1800 ocelot_port->target = target; in ocelot_probe_port()
1801 ocelot->ports[port] = ocelot_port; in ocelot_probe_port()
1803 dev->netdev_ops = &ocelot_port_netdev_ops; in ocelot_probe_port()
1804 dev->ethtool_ops = &ocelot_ethtool_ops; in ocelot_probe_port()
1805 dev->max_mtu = OCELOT_JUMBO_MTU; in ocelot_probe_port()
1807 dev->hw_features |= NETIF_F_HW_VLAN_CTAG_FILTER | NETIF_F_RXFCS | in ocelot_probe_port()
1809 dev->features |= NETIF_F_HW_VLAN_CTAG_FILTER | NETIF_F_HW_TC; in ocelot_probe_port()
1813 eth_hw_addr_gen(dev, ocelot->base_mac, port); in ocelot_probe_port()
1815 ocelot_mact_learn(ocelot, PGID_CPU, dev->dev_addr, in ocelot_probe_port()
1818 ocelot_init_port(ocelot, port); in ocelot_probe_port()
1820 err = ocelot_port_phylink_create(ocelot, port, portnp); in ocelot_probe_port()
1824 if (ocelot->fdma) in ocelot_probe_port()
1825 ocelot_fdma_netdev_init(ocelot, dev); in ocelot_probe_port()
1827 SET_NETDEV_DEVLINK_PORT(dev, &ocelot->devlink_ports[port]); in ocelot_probe_port()
1830 dev_err(ocelot->dev, "register_netdev failed\n"); in ocelot_probe_port()
1837 if (ocelot->fdma) in ocelot_probe_port()
1838 ocelot_fdma_netdev_deinit(ocelot, dev); in ocelot_probe_port()
1840 ocelot->ports[port] = NULL; in ocelot_probe_port()
1851 struct ocelot *ocelot = ocelot_port->ocelot; in ocelot_release_port() local
1852 struct ocelot_fdma *fdma = ocelot->fdma; in ocelot_release_port()
1854 unregister_netdev(priv->dev); in ocelot_release_port()
1857 ocelot_fdma_netdev_deinit(ocelot, priv->dev); in ocelot_release_port()
1859 if (priv->phylink) { in ocelot_release_port()
1861 phylink_disconnect_phy(priv->phylink); in ocelot_release_port()
1864 phylink_destroy(priv->phylink); in ocelot_release_port()
1867 free_netdev(priv->dev); in ocelot_release_port()