Lines Matching +full:asym +full:- +full:pause

1 // SPDX-License-Identifier: GPL-2.0
16 #include <linux/platform_data/microchip-ksz.h>
47 regs = dev->info->regs; in ksz8_ind_write8()
49 mutex_lock(&dev->alu_mutex); in ksz8_ind_write8()
56 mutex_unlock(&dev->alu_mutex); in ksz8_ind_write8()
113 if (!dsa_is_cpu_port(dev->ds, port)) in ksz8_change_mtu()
118 switch (dev->chip_id) { in ksz8_change_mtu()
127 return -EOPNOTSUPP; in ksz8_change_mtu()
172 masks = dev->info->masks; in ksz8_r_mib_cnt()
173 regs = dev->info->regs; in ksz8_r_mib_cnt()
175 ctrl_addr = addr + dev->info->reg_mib_cnt * port; in ksz8_r_mib_cnt()
178 mutex_lock(&dev->alu_mutex); in ksz8_r_mib_cnt()
184 for (loop = 2; loop > 0; loop--) { in ksz8_r_mib_cnt()
195 mutex_unlock(&dev->alu_mutex); in ksz8_r_mib_cnt()
208 masks = dev->info->masks; in ksz8795_r_mib_pkt()
209 regs = dev->info->regs; in ksz8795_r_mib_pkt()
211 addr -= dev->info->reg_mib_cnt; in ksz8795_r_mib_pkt()
212 ctrl_addr = (KSZ8795_MIB_TOTAL_RX_1 - KSZ8795_MIB_TOTAL_RX_0) * port; in ksz8795_r_mib_pkt()
216 mutex_lock(&dev->alu_mutex); in ksz8795_r_mib_pkt()
222 for (loop = 2; loop > 0; loop--) { in ksz8795_r_mib_pkt()
247 mutex_unlock(&dev->alu_mutex); in ksz8795_r_mib_pkt()
259 regs = dev->info->regs; in ksz8863_r_mib_pkt()
261 addr -= dev->info->reg_mib_cnt; in ksz8863_r_mib_pkt()
267 mutex_lock(&dev->alu_mutex); in ksz8863_r_mib_pkt()
270 mutex_unlock(&dev->alu_mutex); in ksz8863_r_mib_pkt()
278 data -= cur; in ksz8863_r_mib_pkt()
309 struct ksz_port_mib *mib = &dev->ports[port].mib; in ksz8_port_init_cnt()
319 mib->cnt_ptr = 0; in ksz8_port_init_cnt()
322 while (mib->cnt_ptr < dev->info->reg_mib_cnt) { in ksz8_port_init_cnt()
323 dev->dev_ops->r_mib_cnt(dev, port, mib->cnt_ptr, in ksz8_port_init_cnt()
324 &mib->counters[mib->cnt_ptr]); in ksz8_port_init_cnt()
325 ++mib->cnt_ptr; in ksz8_port_init_cnt()
329 dropped = &mib->counters[dev->info->mib_cnt]; in ksz8_port_init_cnt()
332 while (mib->cnt_ptr < dev->info->mib_cnt) { in ksz8_port_init_cnt()
333 dev->dev_ops->r_mib_pkt(dev, port, mib->cnt_ptr, in ksz8_port_init_cnt()
334 dropped, &mib->counters[mib->cnt_ptr]); in ksz8_port_init_cnt()
335 ++mib->cnt_ptr; in ksz8_port_init_cnt()
345 regs = dev->info->regs; in ksz8_r_table()
349 mutex_lock(&dev->alu_mutex); in ksz8_r_table()
356 mutex_unlock(&dev->alu_mutex); in ksz8_r_table()
367 regs = dev->info->regs; in ksz8_w_table()
371 mutex_lock(&dev->alu_mutex); in ksz8_w_table()
378 mutex_unlock(&dev->alu_mutex); in ksz8_w_table()
389 masks = dev->info->masks; in ksz8_valid_dyn_entry()
390 regs = dev->info->regs; in ksz8_valid_dyn_entry()
394 timeout--; in ksz8_valid_dyn_entry()
399 return -EAGAIN; in ksz8_valid_dyn_entry()
406 return -ENXIO; in ksz8_valid_dyn_entry()
422 shifts = dev->info->shifts; in ksz8_r_dyn_mac_table()
423 masks = dev->info->masks; in ksz8_r_dyn_mac_table()
424 regs = dev->info->regs; in ksz8_r_dyn_mac_table()
428 mutex_lock(&dev->alu_mutex); in ksz8_r_dyn_mac_table()
432 if (rc == -EAGAIN) { in ksz8_r_dyn_mac_table()
435 } else if (rc == -ENXIO) { in ksz8_r_dyn_mac_table()
469 mutex_unlock(&dev->alu_mutex); in ksz8_r_dyn_mac_table()
483 shifts = dev->info->shifts; in ksz8_r_sta_mac_table()
484 masks = dev->info->masks; in ksz8_r_sta_mac_table()
499 alu->mac[5] = (u8)data_lo; in ksz8_r_sta_mac_table()
500 alu->mac[4] = (u8)(data_lo >> 8); in ksz8_r_sta_mac_table()
501 alu->mac[3] = (u8)(data_lo >> 16); in ksz8_r_sta_mac_table()
502 alu->mac[2] = (u8)(data_lo >> 24); in ksz8_r_sta_mac_table()
503 alu->mac[1] = (u8)data_hi; in ksz8_r_sta_mac_table()
504 alu->mac[0] = (u8)(data_hi >> 8); in ksz8_r_sta_mac_table()
505 alu->port_forward = in ksz8_r_sta_mac_table()
508 alu->is_override = (data_hi & masks[STATIC_MAC_TABLE_OVERRIDE]) ? 1 : 0; in ksz8_r_sta_mac_table()
516 alu->is_static = true; in ksz8_r_sta_mac_table()
517 alu->is_use_fid = (data_hi & masks[STATIC_MAC_TABLE_USE_FID]) ? 1 : 0; in ksz8_r_sta_mac_table()
518 alu->fid = (data_hi & masks[STATIC_MAC_TABLE_FID]) >> in ksz8_r_sta_mac_table()
534 shifts = dev->info->shifts; in ksz8_w_sta_mac_table()
535 masks = dev->info->masks; in ksz8_w_sta_mac_table()
537 data_lo = ((u32)alu->mac[2] << 24) | in ksz8_w_sta_mac_table()
538 ((u32)alu->mac[3] << 16) | in ksz8_w_sta_mac_table()
539 ((u32)alu->mac[4] << 8) | alu->mac[5]; in ksz8_w_sta_mac_table()
540 data_hi = ((u32)alu->mac[0] << 8) | alu->mac[1]; in ksz8_w_sta_mac_table()
541 data_hi |= (u32)alu->port_forward << shifts[STATIC_MAC_FWD_PORTS]; in ksz8_w_sta_mac_table()
543 if (alu->is_override) in ksz8_w_sta_mac_table()
545 if (alu->is_use_fid) { in ksz8_w_sta_mac_table()
547 data_hi |= (u32)alu->fid << shifts[STATIC_MAC_FID]; in ksz8_w_sta_mac_table()
549 if (alu->is_static) in ksz8_w_sta_mac_table()
565 shifts = dev->info->shifts; in ksz8_from_vlan()
566 masks = dev->info->masks; in ksz8_from_vlan()
580 shifts = dev->info->shifts; in ksz8_to_vlan()
581 masks = dev->info->masks; in ksz8_to_vlan()
595 shifts = dev->info->shifts; in ksz8_r_vlan_entries()
600 dev->vlan_cache[addr + i].table[0] = (u16)data; in ksz8_r_vlan_entries()
631 dev->vlan_cache[vid].table[0] = vlan; in ksz8_w_vlan_table()
636 * ksz8_r_phy_ctrl - Translates and reads from the SMI interface to a MIIM PHY
650 const u16 *regs = dev->info->regs; in ksz8_r_phy_ctrl()
689 regs = dev->info->regs; in ksz8_r_phy()
832 * ksz8_w_phy_ctrl - Translates and writes to the SMI interface from a MIIM PHY
870 regs = dev->info->regs; in ksz8_w_phy()
910 /* Fiber port does not support auto-negotiation. */ in ksz8_w_phy()
911 if (dev->ports[p].fiber) in ksz8_w_phy()
1022 data |= (member & dev->port_mask); in ksz8_cfg_port_member()
1032 regs = dev->info->regs; in ksz8_flush_dyn_mac_table()
1034 if ((uint)port < dev->info->port_cnt) { in ksz8_flush_dyn_mac_table()
1040 cnt = dev->info->port_cnt; in ksz8_flush_dyn_mac_table()
1090 for (index = 0; index < dev->info->num_statics; index++) { in ksz8_add_sta_mac()
1108 if (index == dev->info->num_statics && !empty) in ksz8_add_sta_mac()
1109 return -ENOSPC; in ksz8_add_sta_mac()
1112 if (index == dev->info->num_statics) { in ksz8_add_sta_mac()
1113 index = empty - 1; in ksz8_add_sta_mac()
1135 for (index = 0; index < dev->info->num_statics; index++) { in ksz8_del_sta_mac()
1149 if (index == dev->info->num_statics) in ksz8_del_sta_mac()
1163 return ksz8_add_sta_mac(dev, port, mdb->addr, mdb->vid); in ksz8_mdb_add()
1169 return ksz8_del_sta_mac(dev, port, mdb->addr, mdb->vid); in ksz8_mdb_del()
1188 return -ENOTSUPP; in ksz8_port_vlan_filtering()
1194 for (port = 0; port < dev->phy_port_cnt; ++port) in ksz8_port_vlan_filtering()
1205 0x03 << (4 - 2 * port), state); in ksz8_port_enable_pvid()
1215 bool untagged = vlan->flags & BRIDGE_VLAN_INFO_UNTAGGED; in ksz8_port_vlan_add()
1216 struct ksz_port *p = &dev->ports[port]; in ksz8_port_vlan_add()
1221 return -ENOTSUPP; in ksz8_port_vlan_add()
1228 if (untagged != p->remove_tag && vlan->vid != 0 && in ksz8_port_vlan_add()
1229 port != dev->cpu_port) { in ksz8_port_vlan_add()
1236 for (vid = 1; vid < dev->info->num_vlans; ++vid) { in ksz8_port_vlan_add()
1238 if (vid == vlan->vid) in ksz8_port_vlan_add()
1241 ksz8_from_vlan(dev, dev->vlan_cache[vid].table[0], in ksz8_port_vlan_add()
1244 return -EINVAL; in ksz8_port_vlan_add()
1248 p->remove_tag = untagged; in ksz8_port_vlan_add()
1251 ksz8_r_vlan_table(dev, vlan->vid, &data); in ksz8_port_vlan_add()
1263 ksz8_w_vlan_table(dev, vlan->vid, data); in ksz8_port_vlan_add()
1266 if (vlan->flags & BRIDGE_VLAN_INFO_PVID) in ksz8_port_vlan_add()
1267 new_pvid = vlan->vid; in ksz8_port_vlan_add()
1290 return -ENOTSUPP; in ksz8_port_vlan_del()
1295 ksz8_r_vlan_table(dev, vlan->vid, &data); in ksz8_port_vlan_del()
1307 ksz8_w_vlan_table(dev, vlan->vid, data); in ksz8_port_vlan_del()
1309 if (pvid == vlan->vid) in ksz8_port_vlan_del()
1321 dev->mirror_rx |= BIT(port); in ksz8_port_mirror_add()
1324 dev->mirror_tx |= BIT(port); in ksz8_port_mirror_add()
1330 if (dev->mirror_rx || dev->mirror_tx) in ksz8_port_mirror_add()
1331 ksz_port_cfg(dev, mirror->to_local_port, P_MIRROR_CTRL, in ksz8_port_mirror_add()
1342 if (mirror->ingress) { in ksz8_port_mirror_del()
1344 dev->mirror_rx &= ~BIT(port); in ksz8_port_mirror_del()
1347 dev->mirror_tx &= ~BIT(port); in ksz8_port_mirror_del()
1352 if (!dev->mirror_rx && !dev->mirror_tx) in ksz8_port_mirror_del()
1353 ksz_port_cfg(dev, mirror->to_local_port, P_MIRROR_CTRL, in ksz8_port_mirror_del()
1359 struct ksz_port *p = &dev->ports[port]; in ksz8795_cpu_interface_select()
1364 if (!p->interface && dev->compat_interface) { in ksz8795_cpu_interface_select()
1365 dev_warn(dev->dev, in ksz8795_cpu_interface_select()
1366 "Using legacy switch \"phy-mode\" property, because it is missing on port %d node. " in ksz8795_cpu_interface_select()
1369 p->interface = dev->compat_interface; in ksz8795_cpu_interface_select()
1375 struct dsa_switch *ds = dev->ds; in ksz8_port_setup()
1379 masks = dev->info->masks; in ksz8_port_setup()
1407 struct dsa_port *cpu_dp = dsa_to_port(dev->ds, dev->cpu_port); in ksz88x3_config_rmii_clk()
1413 rmii_clk_internal = of_property_read_bool(cpu_dp->dn, in ksz88x3_config_rmii_clk()
1414 "microchip,rmii-clk-internal"); in ksz88x3_config_rmii_clk()
1422 struct ksz_device *dev = ds->priv; in ksz8_config_cpu_port()
1429 masks = dev->info->masks; in ksz8_config_cpu_port()
1430 regs = dev->info->regs; in ksz8_config_cpu_port()
1434 ksz8_port_setup(dev, dev->cpu_port, true); in ksz8_config_cpu_port()
1436 ksz8795_cpu_interface_select(dev, dev->cpu_port); in ksz8_config_cpu_port()
1439 for (i = 0; i < dev->phy_port_cnt; i++) { in ksz8_config_cpu_port()
1442 for (i = 0; i < dev->phy_port_cnt; i++) { in ksz8_config_cpu_port()
1443 p = &dev->ports[i]; in ksz8_config_cpu_port()
1448 p->fiber = 1; in ksz8_config_cpu_port()
1450 if (p->fiber) in ksz8_config_cpu_port()
1460 * ksz8_phy_port_link_up - Configures ports with integrated PHYs
1464 * @tx_pause: If true, enables transmit pause.
1465 * @rx_pause: If true, enables receive pause.
1474 * "1 = will always enable full-duplex flow control on the port, regardless
1476 * 0 = full-duplex flow control is enabled based on AN result."
1479 * - If PORT_FORCE_FLOW_CTRL is set to 1, the switch will ignore AN results and
1481 * - If PORT_FORCE_FLOW_CTRL is set to 0, the switch will enable or disable
1486 * advertise pause support. While such a configuration is not currently
1493 const u16 *regs = dev->info->regs; in ksz8_phy_port_link_up()
1497 * asymmetric pause control. However, since a single bit is used to in ksz8_phy_port_link_up()
1498 * control both RX and TX pause, we can't enforce asymmetric pause in ksz8_phy_port_link_up()
1499 * control - both TX and RX pause will be either enabled or disabled in ksz8_phy_port_link_up()
1502 * If auto-negotiation is enabled, we usually allow the flow control to in ksz8_phy_port_link_up()
1503 * be determined by the auto-negotiation process based on the in ksz8_phy_port_link_up()
1506 * ignoring the auto-negotiation result. Thus, even in auto-negotiation in ksz8_phy_port_link_up()
1510 * In the absence of pause auto-negotiation, we will enforce symmetric in ksz8_phy_port_link_up()
1511 * pause control for both variants of switches - KSZ8873 and KSZ8795. in ksz8_phy_port_link_up()
1513 * Autoneg Pause Autoneg rx,tx PORT_FORCE_FLOW_CTRL in ksz8_phy_port_link_up()
1521 if (dev->ports[port].manual_flow && tx_pause) in ksz8_phy_port_link_up()
1528 * ksz8_cpu_port_link_up - Configures the CPU port of the switch.
1532 * @tx_pause: If true, enables transmit pause.
1533 * @rx_pause: If true, enables receive pause.
1543 const u16 *regs = dev->info->regs; in ksz8_cpu_port_link_up()
1574 if (dev->cpu_port == port) in ksz8_phylink_mac_link_up()
1576 else if (dev->info->internal_phy[port]) in ksz8_phylink_mac_link_up()
1582 struct ksz_device *dev = ds->priv; in ksz8_handle_global_errata()
1591 if (dev->info->ksz87xx_eee_link_erratum) in ksz8_handle_global_errata()
1606 alu.port_forward = dev->info->cpu_ports; in ksz8_enable_stp_addr()
1613 struct ksz_device *dev = ds->priv; in ksz8_setup()
1616 ds->mtu_enforcement_ingress = true; in ksz8_setup()
1621 ds->untag_bridge_pvid = true; in ksz8_setup()
1626 ds->vlan_filtering_is_global = true; in ksz8_setup()
1650 for (i = 0; i < (dev->info->num_vlans / 4); i++) in ksz8_setup()
1659 config->mac_capabilities = MAC_10 | MAC_100; in ksz8_get_caps()
1662 * "Port 1 does not respond to received flow control PAUSE frames" in ksz8_get_caps()
1663 * So, disable Pause support on "Port 1" (port == 0) for all ksz88x3 in ksz8_get_caps()
1667 config->mac_capabilities |= MAC_SYM_PAUSE; in ksz8_get_caps()
1669 /* Asym pause is not supported on KSZ8863 and KSZ8873 */ in ksz8_get_caps()
1671 config->mac_capabilities |= MAC_ASYM_PAUSE; in ksz8_get_caps()
1681 dev->cpu_port = fls(dev->info->cpu_ports) - 1; in ksz8_switch_init()
1682 dev->phy_port_cnt = dev->info->port_cnt - 1; in ksz8_switch_init()
1683 dev->port_mask = (BIT(dev->phy_port_cnt) - 1) | dev->info->cpu_ports; in ksz8_switch_init()