summaryrefslogtreecommitdiffstats
path: root/include
diff options
context:
space:
mode:
authorVlad Yasevich <vyasevic@redhat.com>2014-05-16 17:20:38 -0400
committerDavid S. Miller <davem@davemloft.net>2014-05-16 22:29:05 -0400
commit44a4085538c844e79d6ee6bcf46fabf7c57a9a38 (patch)
tree60844a84ba8ca60a71ecb75eb496f8eb509c1ac4 /include
parent6bd64ac0f9c264082241da0db0dcc72a13e672a8 (diff)
downloadlinux-44a4085538c844e79d6ee6bcf46fabf7c57a9a38.tar.gz
linux-44a4085538c844e79d6ee6bcf46fabf7c57a9a38.tar.bz2
linux-44a4085538c844e79d6ee6bcf46fabf7c57a9a38.zip
bonding: Fix stacked device detection in arp monitoring
Prior to commit fbd929f2dce460456807a51e18d623db3db9f077 bonding: support QinQ for bond arp interval the arp monitoring code allowed for proper detection of devices stacked on top of vlans. Since the above commit, the code can still detect a device stacked on top of single vlan, but not a device stacked on top of Q-in-Q configuration. The search will only set the inner vlan tag if the route device is the vlan device. However, this is not always the case, as it is possible to extend the stacked configuration. With this patch it is possible to provision devices on top Q-in-Q vlan configuration that should be used as a source of ARP monitoring information. For example: ip link add link bond0 vlan10 type vlan proto 802.1q id 10 ip link add link vlan10 vlan100 type vlan proto 802.1q id 100 ip link add link vlan100 type macvlan Note: This patch limites the number of stacked VLANs to 2, just like before. The original, however had another issue in that if we had more then 2 levels of VLANs, we would end up generating incorrectly tagged traffic. This is no longer possible. Fixes: fbd929f2dce460456807a51e18d623db3db9f077 (bonding: support QinQ for bond arp interval) CC: Jay Vosburgh <j.vosburgh@gmail.com> CC: Veaceslav Falico <vfalico@redhat.com> CC: Andy Gospodarek <andy@greyhouse.net> CC: Ding Tianhong <dingtianhong@huawei.com> CC: Patric McHardy <kaber@trash.net> Signed-off-by: Vlad Yasevich <vyasevic@redhat.com> Signed-off-by: David S. Miller <davem@davemloft.net>
Diffstat (limited to 'include')
-rw-r--r--include/linux/if_vlan.h6
-rw-r--r--include/linux/netdevice.h9
2 files changed, 15 insertions, 0 deletions
diff --git a/include/linux/if_vlan.h b/include/linux/if_vlan.h
index 724bde8477b2..c901b13b6f03 100644
--- a/include/linux/if_vlan.h
+++ b/include/linux/if_vlan.h
@@ -484,4 +484,10 @@ static inline void vlan_set_encap_proto(struct sk_buff *skb,
*/
skb->protocol = htons(ETH_P_802_2);
}
+
+static inline int vlan_get_encap_level(struct net_device *dev)
+{
+ BUG_ON(!is_vlan_dev(dev));
+ return vlan_dev_priv(dev)->nest_level;
+}
#endif /* !(_LINUX_IF_VLAN_H_) */
diff --git a/include/linux/netdevice.h b/include/linux/netdevice.h
index 9d4b1f1b6b75..b42d07b0390b 100644
--- a/include/linux/netdevice.h
+++ b/include/linux/netdevice.h
@@ -3056,10 +3056,19 @@ extern int weight_p;
extern int bpf_jit_enable;
bool netdev_has_upper_dev(struct net_device *dev, struct net_device *upper_dev);
+struct net_device *netdev_upper_get_next_dev_rcu(struct net_device *dev,
+ struct list_head **iter);
struct net_device *netdev_all_upper_get_next_dev_rcu(struct net_device *dev,
struct list_head **iter);
/* iterate through upper list, must be called under RCU read lock */
+#define netdev_for_each_upper_dev_rcu(dev, updev, iter) \
+ for (iter = &(dev)->adj_list.upper, \
+ updev = netdev_upper_get_next_dev_rcu(dev, &(iter)); \
+ updev; \
+ updev = netdev_upper_get_next_dev_rcu(dev, &(iter)))
+
+/* iterate through upper list, must be called under RCU read lock */
#define netdev_for_each_all_upper_dev_rcu(dev, updev, iter) \
for (iter = &(dev)->all_adj_list.upper, \
updev = netdev_all_upper_get_next_dev_rcu(dev, &(iter)); \