diff options
Diffstat (limited to 'net/bridge/br_vlan.c')
| -rw-r--r-- | net/bridge/br_vlan.c | 27 | 
1 files changed, 21 insertions, 6 deletions
| diff --git a/net/bridge/br_vlan.c b/net/bridge/br_vlan.c index 4ca4d0a0151c..8249ca764c79 100644 --- a/net/bridge/br_vlan.c +++ b/net/bridge/br_vlan.c @@ -275,9 +275,7 @@ int br_vlan_delete(struct net_bridge *br, u16 vid)  	if (!pv)  		return -EINVAL; -	spin_lock_bh(&br->hash_lock); -	fdb_delete_by_addr(br, br->dev->dev_addr, vid); -	spin_unlock_bh(&br->hash_lock); +	br_fdb_find_delete_local(br, NULL, br->dev->dev_addr, vid);  	__vlan_del(pv, vid);  	return 0; @@ -295,6 +293,25 @@ void br_vlan_flush(struct net_bridge *br)  	__vlan_flush(pv);  } +bool br_vlan_find(struct net_bridge *br, u16 vid) +{ +	struct net_port_vlans *pv; +	bool found = false; + +	rcu_read_lock(); +	pv = rcu_dereference(br->vlan_info); + +	if (!pv) +		goto out; + +	if (test_bit(vid, pv->vlan_bitmap)) +		found = true; + +out: +	rcu_read_unlock(); +	return found; +} +  int br_vlan_filter_toggle(struct net_bridge *br, unsigned long val)  {  	if (!rtnl_trylock()) @@ -359,9 +376,7 @@ int nbp_vlan_delete(struct net_bridge_port *port, u16 vid)  	if (!pv)  		return -EINVAL; -	spin_lock_bh(&port->br->hash_lock); -	fdb_delete_by_addr(port->br, port->dev->dev_addr, vid); -	spin_unlock_bh(&port->br->hash_lock); +	br_fdb_find_delete_local(port->br, port, port->dev->dev_addr, vid);  	return __vlan_del(pv, vid);  } |