From f7a2bd6544657f125d2c8a8b4f231a8cd225ee8f Mon Sep 17 00:00:00 2001 From: Sven Eckelmann Date: Wed, 22 Feb 2017 17:16:42 +0100 Subject: batman-adv: Convert BATADV_PRINT_VID macro to function The BATADV_PRINT_VID is not free of of possible side-effects. This can be avoided when the the macro is converted to a simple inline function. Signed-off-by: Sven Eckelmann Signed-off-by: Simon Wunderlich --- net/batman-adv/distributed-arp-table.c | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) (limited to 'net/batman-adv/distributed-arp-table.c') diff --git a/net/batman-adv/distributed-arp-table.c b/net/batman-adv/distributed-arp-table.c index 1bfd1dbc2feb..4f643fdb5bc6 100644 --- a/net/batman-adv/distributed-arp-table.c +++ b/net/batman-adv/distributed-arp-table.c @@ -330,7 +330,7 @@ static void batadv_dat_entry_add(struct batadv_priv *bat_priv, __be32 ip, batadv_dbg(BATADV_DBG_DAT, bat_priv, "Entry updated: %pI4 %pM (vid: %d)\n", &dat_entry->ip, dat_entry->mac_addr, - BATADV_PRINT_VID(vid)); + batadv_print_vid(vid)); goto out; } @@ -356,7 +356,7 @@ static void batadv_dat_entry_add(struct batadv_priv *bat_priv, __be32 ip, } batadv_dbg(BATADV_DBG_DAT, bat_priv, "New entry added: %pI4 %pM (vid: %d)\n", - &dat_entry->ip, dat_entry->mac_addr, BATADV_PRINT_VID(vid)); + &dat_entry->ip, dat_entry->mac_addr, batadv_print_vid(vid)); out: if (dat_entry) @@ -835,7 +835,7 @@ int batadv_dat_cache_seq_print_text(struct seq_file *seq, void *offset) seq_printf(seq, " * %15pI4 %14pM %4i %6i:%02i\n", &dat_entry->ip, dat_entry->mac_addr, - BATADV_PRINT_VID(dat_entry->vid), + batadv_print_vid(dat_entry->vid), last_seen_mins, last_seen_secs); } rcu_read_unlock(); -- cgit From 00311de5fbf998877f2c3109688857a99f45fdd8 Mon Sep 17 00:00:00 2001 From: Andreas Pape Date: Mon, 5 Sep 2016 13:20:25 +0200 Subject: batman-adv: prevent multiple ARP replies sent by gateways if dat enabled If dat is enabled it must be made sure that only the backbone gw which has claimed the remote destination for the ARP request answers the ARP request directly if the MAC address is known due to the local dat table. This prevents multiple ARP replies in a common backbone if more than one gateway already knows the remote mac searched for in the ARP request. Signed-off-by: Andreas Pape Acked-by: Simon Wunderlich [sven@narfation.org: fix conflicts with current version] Signed-off-by: Sven Eckelmann Signed-off-by: Simon Wunderlich --- net/batman-adv/distributed-arp-table.c | 15 +++++++++++++++ 1 file changed, 15 insertions(+) (limited to 'net/batman-adv/distributed-arp-table.c') diff --git a/net/batman-adv/distributed-arp-table.c b/net/batman-adv/distributed-arp-table.c index 4f643fdb5bc6..28cfa53837e1 100644 --- a/net/batman-adv/distributed-arp-table.c +++ b/net/batman-adv/distributed-arp-table.c @@ -43,6 +43,7 @@ #include #include +#include "bridge_loop_avoidance.h" #include "hard-interface.h" #include "hash.h" #include "log.h" @@ -1040,6 +1041,20 @@ bool batadv_dat_snoop_outgoing_arp_request(struct batadv_priv *bat_priv, goto out; } + /* If BLA is enabled, only send ARP replies if we have claimed + * the destination for the ARP request or if no one else of + * the backbone gws belonging to our backbone has claimed the + * destination. + */ + if (!batadv_bla_check_claim(bat_priv, + dat_entry->mac_addr, vid)) { + batadv_dbg(BATADV_DBG_DAT, bat_priv, + "Device %pM claimed by another backbone gw. Don't send ARP reply!", + dat_entry->mac_addr); + ret = true; + goto out; + } + skb_new = batadv_dat_arp_create_reply(bat_priv, ip_dst, ip_src, dat_entry->mac_addr, hw_src, vid); -- cgit From 9aa5cd79b5abde1d0ebcff825726e242e0b7efea Mon Sep 17 00:00:00 2001 From: Andreas Pape Date: Mon, 5 Sep 2016 13:20:26 +0200 Subject: batman-adv: prevent duplication of ARP replies when DAT is used If none of the backbone gateways in a bla setup has already knowledge of the mac address searched for in an incoming ARP request from the backbone an address resolution via the DHT of DAT is started. The gateway can send several ARP requests to different DHT nodes and therefore can get several replies. This patch assures that not all of the possible ARP replies are returned to the backbone by checking the local DAT cache of the gateway. If there is an entry in the local cache the gateway has already learned the requested address and there is no need to forward the additional reply to the backbone. Furthermore it is checked if this gateway has claimed the source of the ARP reply and only forwards it to the backbone if it has claimed the source or if there is no claim at all. Signed-off-by: Andreas Pape Acked-by: Simon Wunderlich [sven@narfation.org: fix conflicts with current version] Signed-off-by: Sven Eckelmann Signed-off-by: Simon Wunderlich --- net/batman-adv/distributed-arp-table.c | 32 ++++++++++++++++++++++++++++++++ 1 file changed, 32 insertions(+) (limited to 'net/batman-adv/distributed-arp-table.c') diff --git a/net/batman-adv/distributed-arp-table.c b/net/batman-adv/distributed-arp-table.c index 28cfa53837e1..77ede40ff529 100644 --- a/net/batman-adv/distributed-arp-table.c +++ b/net/batman-adv/distributed-arp-table.c @@ -1203,6 +1203,7 @@ void batadv_dat_snoop_outgoing_arp_reply(struct batadv_priv *bat_priv, bool batadv_dat_snoop_incoming_arp_reply(struct batadv_priv *bat_priv, struct sk_buff *skb, int hdr_size) { + struct batadv_dat_entry *dat_entry = NULL; u16 type; __be32 ip_src, ip_dst; u8 *hw_src, *hw_dst; @@ -1225,12 +1226,41 @@ bool batadv_dat_snoop_incoming_arp_reply(struct batadv_priv *bat_priv, hw_dst = batadv_arp_hw_dst(skb, hdr_size); ip_dst = batadv_arp_ip_dst(skb, hdr_size); + /* If ip_dst is already in cache and has the right mac address, + * drop this frame if this ARP reply is destined for us because it's + * most probably an ARP reply generated by another node of the DHT. + * We have most probably received already a reply earlier. Delivering + * this frame would lead to doubled receive of an ARP reply. + */ + dat_entry = batadv_dat_entry_hash_find(bat_priv, ip_src, vid); + if (dat_entry && batadv_compare_eth(hw_src, dat_entry->mac_addr)) { + batadv_dbg(BATADV_DBG_DAT, bat_priv, "Doubled ARP reply removed: ARP MSG = [src: %pM-%pI4 dst: %pM-%pI4]; dat_entry: %pM-%pI4\n", + hw_src, &ip_src, hw_dst, &ip_dst, + dat_entry->mac_addr, &dat_entry->ip); + dropped = true; + goto out; + } + /* Update our internal cache with both the IP addresses the node got * within the ARP reply */ batadv_dat_entry_add(bat_priv, ip_src, hw_src, vid); batadv_dat_entry_add(bat_priv, ip_dst, hw_dst, vid); + /* If BLA is enabled, only forward ARP replies if we have claimed the + * source of the ARP reply or if no one else of the same backbone has + * already claimed that client. This prevents that different gateways + * to the same backbone all forward the ARP reply leading to multiple + * replies in the backbone. + */ + if (!batadv_bla_check_claim(bat_priv, hw_src, vid)) { + batadv_dbg(BATADV_DBG_DAT, bat_priv, + "Device %pM claimed by another backbone gw. Drop ARP reply.\n", + hw_src); + dropped = true; + goto out; + } + /* if this REPLY is directed to a client of mine, let's deliver the * packet to the interface */ @@ -1243,6 +1273,8 @@ bool batadv_dat_snoop_incoming_arp_reply(struct batadv_priv *bat_priv, out: if (dropped) kfree_skb(skb); + if (dat_entry) + batadv_dat_entry_put(dat_entry); /* if dropped == false -> deliver to the interface */ return dropped; } -- cgit From e2d9ba43559e5fcd94a365ba86718332737b0817 Mon Sep 17 00:00:00 2001 From: Linus Lüssing Date: Fri, 17 Feb 2017 11:17:07 +0100 Subject: batman-adv: restructure rebroadcast counter into forw_packet API MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit This patch refactors the num_packets counter of a forw_packet in the following three ways: 1) Removed dual-use of forw_packet::num_packets: -> now for aggregation purposes only 2) Using forw_packet::skb::cb::num_bcasts instead: -> for easier access in aggregation code later 3) make access to num_bcasts private to batadv_forw_packet_*() Signed-off-by: Linus Lüssing [sven@narfation.org: Change num_bcasts to unsigned] Signed-off-by: Sven Eckelmann Signed-off-by: Simon Wunderlich --- net/batman-adv/distributed-arp-table.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'net/batman-adv/distributed-arp-table.c') diff --git a/net/batman-adv/distributed-arp-table.c b/net/batman-adv/distributed-arp-table.c index 77ede40ff529..0608fcf99e7b 100644 --- a/net/batman-adv/distributed-arp-table.c +++ b/net/batman-adv/distributed-arp-table.c @@ -1303,7 +1303,7 @@ bool batadv_dat_drop_broadcast_packet(struct batadv_priv *bat_priv, /* If this packet is an ARP_REQUEST and the node already has the * information that it is going to ask, then the packet can be dropped */ - if (forw_packet->num_packets) + if (batadv_forw_packet_is_rebroadcast(forw_packet)) goto out; vid = batadv_dat_get_vid(forw_packet->skb, &hdr_size); -- cgit From ab044f8e3eaf84c4cc95d7606fadfdfa006dc8ec Mon Sep 17 00:00:00 2001 From: Tobias Klauser Date: Wed, 5 Apr 2017 13:46:31 +0200 Subject: batman-adv: Use net_device_stats from struct net_device Instead of using a private copy of struct net_device_stats in struct batadv_priv, use stats from struct net_device. Signed-off-by: Tobias Klauser Signed-off-by: Sven Eckelmann Signed-off-by: Simon Wunderlich --- net/batman-adv/distributed-arp-table.c | 9 +++++---- 1 file changed, 5 insertions(+), 4 deletions(-) (limited to 'net/batman-adv/distributed-arp-table.c') diff --git a/net/batman-adv/distributed-arp-table.c b/net/batman-adv/distributed-arp-table.c index 0608fcf99e7b..013e970eff39 100644 --- a/net/batman-adv/distributed-arp-table.c +++ b/net/batman-adv/distributed-arp-table.c @@ -1003,6 +1003,7 @@ bool batadv_dat_snoop_outgoing_arp_request(struct batadv_priv *bat_priv, bool ret = false; struct batadv_dat_entry *dat_entry = NULL; struct sk_buff *skb_new; + struct net_device *soft_iface = bat_priv->soft_iface; int hdr_size = 0; unsigned short vid; @@ -1061,10 +1062,10 @@ bool batadv_dat_snoop_outgoing_arp_request(struct batadv_priv *bat_priv, if (!skb_new) goto out; - skb_new->protocol = eth_type_trans(skb_new, - bat_priv->soft_iface); - bat_priv->stats.rx_packets++; - bat_priv->stats.rx_bytes += skb->len + ETH_HLEN + hdr_size; + skb_new->protocol = eth_type_trans(skb_new, soft_iface); + + soft_iface->stats.rx_packets++; + soft_iface->stats.rx_bytes += skb->len + ETH_HLEN + hdr_size; netif_rx(skb_new); batadv_dbg(BATADV_DBG_DAT, bat_priv, "ARP request replied locally\n"); -- cgit