diff options
Diffstat (limited to 'drivers/net/ipvlan/ipvlan_main.c')
-rw-r--r-- | drivers/net/ipvlan/ipvlan_main.c | 20 |
1 files changed, 6 insertions, 14 deletions
diff --git a/drivers/net/ipvlan/ipvlan_main.c b/drivers/net/ipvlan/ipvlan_main.c index a16d3017fdc3..1acc283160d9 100644 --- a/drivers/net/ipvlan/ipvlan_main.c +++ b/drivers/net/ipvlan/ipvlan_main.c | |||
@@ -218,17 +218,6 @@ static void ipvlan_change_rx_flags(struct net_device *dev, int change) | |||
218 | dev_set_allmulti(phy_dev, dev->flags & IFF_ALLMULTI? 1 : -1); | 218 | dev_set_allmulti(phy_dev, dev->flags & IFF_ALLMULTI? 1 : -1); |
219 | } | 219 | } |
220 | 220 | ||
221 | static void ipvlan_set_broadcast_mac_filter(struct ipvl_dev *ipvlan, bool set) | ||
222 | { | ||
223 | struct net_device *dev = ipvlan->dev; | ||
224 | unsigned int hashbit = ipvlan_mac_hash(dev->broadcast); | ||
225 | |||
226 | if (set && !test_bit(hashbit, ipvlan->mac_filters)) | ||
227 | __set_bit(hashbit, ipvlan->mac_filters); | ||
228 | else if (!set && test_bit(hashbit, ipvlan->mac_filters)) | ||
229 | __clear_bit(hashbit, ipvlan->mac_filters); | ||
230 | } | ||
231 | |||
232 | static void ipvlan_set_multicast_mac_filter(struct net_device *dev) | 221 | static void ipvlan_set_multicast_mac_filter(struct net_device *dev) |
233 | { | 222 | { |
234 | struct ipvl_dev *ipvlan = netdev_priv(dev); | 223 | struct ipvl_dev *ipvlan = netdev_priv(dev); |
@@ -243,6 +232,12 @@ static void ipvlan_set_multicast_mac_filter(struct net_device *dev) | |||
243 | netdev_for_each_mc_addr(ha, dev) | 232 | netdev_for_each_mc_addr(ha, dev) |
244 | __set_bit(ipvlan_mac_hash(ha->addr), mc_filters); | 233 | __set_bit(ipvlan_mac_hash(ha->addr), mc_filters); |
245 | 234 | ||
235 | /* Turn-on broadcast bit irrespective of address family, | ||
236 | * since broadcast is deferred to a work-queue, hence no | ||
237 | * impact on fast-path processing. | ||
238 | */ | ||
239 | __set_bit(ipvlan_mac_hash(dev->broadcast), mc_filters); | ||
240 | |||
246 | bitmap_copy(ipvlan->mac_filters, mc_filters, | 241 | bitmap_copy(ipvlan->mac_filters, mc_filters, |
247 | IPVLAN_MAC_FILTER_SIZE); | 242 | IPVLAN_MAC_FILTER_SIZE); |
248 | } | 243 | } |
@@ -710,7 +705,6 @@ static int ipvlan_add_addr4(struct ipvl_dev *ipvlan, struct in_addr *ip4_addr) | |||
710 | */ | 705 | */ |
711 | if (netif_running(ipvlan->dev)) | 706 | if (netif_running(ipvlan->dev)) |
712 | ipvlan_ht_addr_add(ipvlan, addr); | 707 | ipvlan_ht_addr_add(ipvlan, addr); |
713 | ipvlan_set_broadcast_mac_filter(ipvlan, true); | ||
714 | 708 | ||
715 | return 0; | 709 | return 0; |
716 | } | 710 | } |
@@ -727,8 +721,6 @@ static void ipvlan_del_addr4(struct ipvl_dev *ipvlan, struct in_addr *ip4_addr) | |||
727 | list_del(&addr->anode); | 721 | list_del(&addr->anode); |
728 | ipvlan->ipv4cnt--; | 722 | ipvlan->ipv4cnt--; |
729 | WARN_ON(ipvlan->ipv4cnt < 0); | 723 | WARN_ON(ipvlan->ipv4cnt < 0); |
730 | if (!ipvlan->ipv4cnt) | ||
731 | ipvlan_set_broadcast_mac_filter(ipvlan, false); | ||
732 | kfree_rcu(addr, rcu); | 724 | kfree_rcu(addr, rcu); |
733 | 725 | ||
734 | return; | 726 | return; |