Commit add2c844 authored by Horatiu Vultur's avatar Horatiu Vultur Committed by David S. Miller
Browse files

net: lan966x: Update mdb when enabling/disabling mcast_snooping



When the multicast snooping is disabled, the mdb entries should be
removed from the HW, but they still need to be kept in memory for when
the mcast_snooping will be enabled again.

Signed-off-by: default avatarHoratiu Vultur <horatiu.vultur@microchip.com>
Signed-off-by: default avatarDavid S. Miller <davem@davemloft.net>
parent 47aeea0d
Loading
Loading
Loading
Loading
+2 −0
Original line number Diff line number Diff line
@@ -267,6 +267,8 @@ int lan966x_handle_port_mdb_del(struct lan966x_port *port,
				const struct switchdev_obj *obj);
void lan966x_mdb_erase_entries(struct lan966x *lan966x, u16 vid);
void lan966x_mdb_write_entries(struct lan966x *lan966x, u16 vid);
void lan966x_mdb_clear_entries(struct lan966x *lan966x);
void lan966x_mdb_restore_entries(struct lan966x *lan966x);

int lan966x_ptp_init(struct lan966x *lan966x);
void lan966x_ptp_deinit(struct lan966x *lan966x);
+45 −0
Original line number Diff line number Diff line
@@ -504,3 +504,48 @@ void lan966x_mdb_erase_entries(struct lan966x *lan966x, u16 vid)
			lan966x_mdb_l2_cpu_remove(lan966x, mdb_entry, type);
	}
}

void lan966x_mdb_clear_entries(struct lan966x *lan966x)
{
	struct lan966x_mdb_entry *mdb_entry;
	enum macaccess_entry_type type;
	unsigned char mac[ETH_ALEN];

	list_for_each_entry(mdb_entry, &lan966x->mdb_entries, list) {
		type = lan966x_mdb_classify(mdb_entry->mac);

		lan966x_mdb_encode_mac(mac, mdb_entry, type);
		/* Remove just the MAC entry, still keep the PGID in case of L2
		 * entries because this can be restored at later point
		 */
		lan966x_mac_forget(lan966x, mac, mdb_entry->vid, type);
	}
}

void lan966x_mdb_restore_entries(struct lan966x *lan966x)
{
	struct lan966x_mdb_entry *mdb_entry;
	enum macaccess_entry_type type;
	unsigned char mac[ETH_ALEN];
	bool cpu_copy = false;

	list_for_each_entry(mdb_entry, &lan966x->mdb_entries, list) {
		type = lan966x_mdb_classify(mdb_entry->mac);

		lan966x_mdb_encode_mac(mac, mdb_entry, type);
		if (type == ENTRYTYPE_MACV4 || type == ENTRYTYPE_MACV6) {
			/* Copy the frame to CPU only if the CPU is in the VLAN */
			if (lan966x_vlan_cpu_member_cpu_vlan_mask(lan966x,
								  mdb_entry->vid) &&
			    mdb_entry->cpu_copy)
				cpu_copy = true;

			lan966x_mac_ip_learn(lan966x, cpu_copy, mac,
					     mdb_entry->vid, type);
		} else {
			lan966x_mac_learn(lan966x, mdb_entry->pgid->index,
					  mdb_entry->mac,
					  mdb_entry->vid, type);
		}
	}
}
+4 −0
Original line number Diff line number Diff line
@@ -185,6 +185,10 @@ static void lan966x_port_mc_set(struct lan966x_port *port, bool mcast_ena)
	struct lan966x *lan966x = port->lan966x;

	port->mcast_ena = mcast_ena;
	if (mcast_ena)
		lan966x_mdb_restore_entries(lan966x);
	else
		lan966x_mdb_clear_entries(lan966x);

	lan_rmw(ANA_CPU_FWD_CFG_IGMP_REDIR_ENA_SET(mcast_ena) |
		ANA_CPU_FWD_CFG_MLD_REDIR_ENA_SET(mcast_ena) |