diff --git a/batman-adv/Makefile b/batman-adv/Makefile index 7de2eab..d222c0b 100644 --- a/batman-adv/Makefile +++ b/batman-adv/Makefile @@ -11,7 +11,7 @@ include $(TOPDIR)/rules.mk PKG_NAME:=batman-adv PKG_VERSION:=2016.1 -PKG_RELEASE:=1 +PKG_RELEASE:=2 PKG_MD5SUM:=8c8e449009b4d29512d26ee308960bb5 PKG_SOURCE:=$(PKG_NAME)-$(PKG_VERSION).tar.gz diff --git a/batman-adv/patches/0007-batman-adv-Add-missing-include-for-batadv_v_neigh_is.patch b/batman-adv/patches/0007-batman-adv-Add-missing-include-for-batadv_v_neigh_is.patch new file mode 100644 index 0000000..82ffd07 --- /dev/null +++ b/batman-adv/patches/0007-batman-adv-Add-missing-include-for-batadv_v_neigh_is.patch @@ -0,0 +1,28 @@ +From: Sven Eckelmann +Date: Sat, 7 May 2016 09:50:44 +0200 +Subject: [PATCH] batman-adv: Add missing include for batadv_v_neigh_is_sob + +batadv_v_neigh_is_sob started to use false which is defined in +linux/stddef.h. + +Fixes: 036aa7b7181e ("batman-adv: Avoid nullptr derefence in batadv_v_neigh_is_sob") +Signed-off-by: Sven Eckelmann +Signed-off-by: Marek Lindner + +Origin: upstream, https://git.open-mesh.org/batman-adv.git/commit/9685688ae7dd85804aec2f6ce760611551fe9635 +--- + net/batman-adv/bat_v.c | 1 + + 1 file changed, 1 insertion(+) + +diff --git a/net/batman-adv/bat_v.c b/net/batman-adv/bat_v.c +index 0caca2f..1f960c9 100644 +--- a/net/batman-adv/bat_v.c ++++ b/net/batman-adv/bat_v.c +@@ -27,6 +27,7 @@ + #include + #include + #include ++#include + #include + #include + diff --git a/batman-adv/patches/0008-batman-adv-fix-skb-deref-after-free.patch b/batman-adv/patches/0008-batman-adv-fix-skb-deref-after-free.patch new file mode 100644 index 0000000..5c8bfd8 --- /dev/null +++ b/batman-adv/patches/0008-batman-adv-fix-skb-deref-after-free.patch @@ -0,0 +1,46 @@ +From: Florian Westphal +Date: Tue, 10 May 2016 23:17:59 +0200 +Subject: [PATCH] batman-adv: fix skb deref after free + +batadv_send_skb_to_orig() calls dev_queue_xmit() so we can't use skb->len. + +Fixes: d28785996ad8 ("batman-adv: network coding - buffer unicast packets before forward") + +Signed-off-by: Florian Westphal +Reviewed-by: Sven Eckelmann +Signed-off-by: Marek Lindner + +Origin: upstream, https://git.open-mesh.org/batman-adv.git/commit/6863d3b59fd1f1bef3c4b86707a0b1c5d21e0a07 +--- + net/batman-adv/routing.c | 4 +++- + 1 file changed, 3 insertions(+), 1 deletion(-) + +diff --git a/net/batman-adv/routing.c b/net/batman-adv/routing.c +index b781bf7..0c0c30e 100644 +--- a/net/batman-adv/routing.c ++++ b/net/batman-adv/routing.c +@@ -601,6 +601,7 @@ static int batadv_route_unicast_packet(struct sk_buff *skb, + struct batadv_unicast_packet *unicast_packet; + struct ethhdr *ethhdr = eth_hdr(skb); + int res, hdr_len, ret = NET_RX_DROP; ++ unsigned int len; + + unicast_packet = (struct batadv_unicast_packet *)skb->data; + +@@ -641,6 +642,7 @@ static int batadv_route_unicast_packet(struct sk_buff *skb, + if (hdr_len > 0) + batadv_skb_set_priority(skb, hdr_len); + ++ len = skb->len; + res = batadv_send_skb_to_orig(skb, orig_node, recv_if); + + /* translate transmit result into receive result */ +@@ -648,7 +650,7 @@ static int batadv_route_unicast_packet(struct sk_buff *skb, + /* skb was transmitted and consumed */ + batadv_inc_counter(bat_priv, BATADV_CNT_FORWARD); + batadv_add_counter(bat_priv, BATADV_CNT_FORWARD_BYTES, +- skb->len + ETH_HLEN); ++ len + ETH_HLEN); + + ret = NET_RX_SUCCESS; + } else if (res == NET_XMIT_POLICED) { diff --git a/batman-adv/patches/0009-batman-adv-replace-WARN-with-rate-limited-output-on-.patch b/batman-adv/patches/0009-batman-adv-replace-WARN-with-rate-limited-output-on-.patch new file mode 100644 index 0000000..07274b6 --- /dev/null +++ b/batman-adv/patches/0009-batman-adv-replace-WARN-with-rate-limited-output-on-.patch @@ -0,0 +1,40 @@ +From: Simon Wunderlich +Date: Thu, 12 May 2016 18:52:03 +0200 +Subject: [PATCH] batman-adv: replace WARN with rate limited output on non-existing VLAN + +If a VLAN tagged frame is received and the corresponding VLAN is not +configured on the soft interface, it will splat a WARN on every packet +received. This is a quite annoying behaviour for some scenarios, e.g. if +bat0 is bridged with eth0, and there are arbitrary VLAN tagged frames +from Ethernet coming in without having any VLAN configuration on bat0. + +The code should probably create vlan objects on the fly and +transparently transport these VLAN-tagged Ethernet frames, but until +this is done, at least the WARN splat should be replaced by a rate +limited output. + +Signed-off-by: Simon Wunderlich +Signed-off-by: Marek Lindner + +Origin: upstream, https://git.open-mesh.org/batman-adv.git/commit/04792115d24408a72bf8fccd5c4059478fc15eae +--- + net/batman-adv/translation-table.c | 6 ++++-- + 1 file changed, 4 insertions(+), 2 deletions(-) + +diff --git a/net/batman-adv/translation-table.c b/net/batman-adv/translation-table.c +index 9b4551a..48adb91 100644 +--- a/net/batman-adv/translation-table.c ++++ b/net/batman-adv/translation-table.c +@@ -650,8 +650,10 @@ bool batadv_tt_local_add(struct net_device *soft_iface, const u8 *addr, + + /* increase the refcounter of the related vlan */ + vlan = batadv_softif_vlan_get(bat_priv, vid); +- if (WARN(!vlan, "adding TT local entry %pM to non-existent VLAN %d", +- addr, BATADV_PRINT_VID(vid))) { ++ if (!vlan) { ++ net_ratelimited_function(batadv_info, soft_iface, ++ "adding TT local entry %pM to non-existent VLAN %d\n", ++ addr, BATADV_PRINT_VID(vid)); + kfree(tt_local); + tt_local = NULL; + goto out; diff --git a/batman-adv/patches/0010-batman-adv-Fix-build-against-recent-Debian-Stretch-k.patch b/batman-adv/patches/0010-batman-adv-Fix-build-against-recent-Debian-Stretch-k.patch new file mode 100644 index 0000000..127cac8 --- /dev/null +++ b/batman-adv/patches/0010-batman-adv-Fix-build-against-recent-Debian-Stretch-k.patch @@ -0,0 +1,58 @@ +From: Sven Eckelmann +Date: Sat, 28 May 2016 10:32:48 +0200 +Subject: [PATCH] batman-adv: Fix build against recent Debian Stretch kernels + +The kernels for Debian stretch require some special CFLAGS settings which +are only correctly defined when NOSTDINC_FLAGS is defined inside the +execution of the Makefile via kbuild. But batman-adv sets it currently +outside to insert compatibility include headers and compat-sources. + +This can be avoided by making the top Makefile kbuild compatible and +redefining the NOSTDINC_FLAGS when kbuild include this Makefile. The actual +build of the batman-adv module is then done by adding the subdirectory to +obj-y. + +Signed-off-by: Sven Eckelmann +Tested-by: Martin Weinelt + +Origin: https://git.open-mesh.org/batman-adv.git/commit/f8fd441e1e30f3a274c9bf44cc33372d4065cbb6 +--- + Makefile | 10 +++++++--- + 1 file changed, 7 insertions(+), 3 deletions(-) + +diff --git a/Makefile b/Makefile +index 5d2c058..2568fb2 100644 +--- a/Makefile ++++ b/Makefile +@@ -43,7 +43,7 @@ RM ?= rm -f + REVISION= $(shell if [ -d "$(PWD)/.git" ]; then \ + echo $$(git --git-dir="$(PWD)/.git" describe --always --dirty --match "v*" |sed 's/^v//' 2> /dev/null || echo "[unknown]"); \ + fi) +-export NOSTDINC_FLAGS := \ ++NOSTDINC_FLAGS += \ + -I$(PWD)/compat-include/ \ + -include $(PWD)/compat.h \ + $(CFLAGS) +@@ -52,8 +52,12 @@ ifneq ($(REVISION),) + NOSTDINC_FLAGS += -DBATADV_SOURCE_VERSION=\"$(REVISION)\" + endif + ++obj-y += net/batman-adv/ ++ + BUILD_FLAGS := \ +- M=$(PWD)/net/batman-adv \ ++ M=$(PWD) \ ++ PWD=$(PWD) \ ++ REVISION=$(REVISION) \ + CONFIG_BATMAN_ADV=m \ + CONFIG_BATMAN_ADV_DEBUG=$(CONFIG_BATMAN_ADV_DEBUG) \ + CONFIG_BATMAN_ADV_BLA=$(CONFIG_BATMAN_ADV_BLA) \ +@@ -61,7 +65,7 @@ BUILD_FLAGS := \ + CONFIG_BATMAN_ADV_NC=$(CONFIG_BATMAN_ADV_NC) \ + CONFIG_BATMAN_ADV_MCAST=$(CONFIG_BATMAN_ADV_MCAST) \ + CONFIG_BATMAN_ADV_BATMAN_V=$(CONFIG_BATMAN_ADV_BATMAN_V) \ +- INSTALL_MOD_DIR=updates/net/batman-adv/ ++ INSTALL_MOD_DIR=updates/ + + all: config + $(MAKE) -C $(KERNELPATH) $(BUILD_FLAGS) modules diff --git a/batman-adv/patches/0011-batman-adv-Clean-up-untagged-vlan-when-destroying-vi.patch b/batman-adv/patches/0011-batman-adv-Clean-up-untagged-vlan-when-destroying-vi.patch new file mode 100644 index 0000000..b03d795 --- /dev/null +++ b/batman-adv/patches/0011-batman-adv-Clean-up-untagged-vlan-when-destroying-vi.patch @@ -0,0 +1,45 @@ +From: Sven Eckelmann +Date: Sat, 28 May 2016 14:38:26 +0200 +Subject: [PATCH] batman-adv: Clean up untagged vlan when destroying via rtnl-link + +The untagged vlan object is only destroyed when the interface is removed +via the legacy sysfs interface. But it also has to be destroyed when the +standard rtnl-link interface is used. + +Fixes: 952cebb57518 ("batman-adv: add per VLAN interface attribute framework") +Signed-off-by: Sven Eckelmann +Cc: Antonio Quartulli + +Origin: https://git.open-mesh.org/batman-adv.git/commit/e721749d57ff57d6df4017d62797626eab9902f1 +--- + net/batman-adv/soft-interface.c | 9 +++++++++ + 1 file changed, 9 insertions(+) + +diff --git a/net/batman-adv/soft-interface.c b/net/batman-adv/soft-interface.c +index 8a136b6..3710620 100644 +--- a/net/batman-adv/soft-interface.c ++++ b/net/batman-adv/soft-interface.c +@@ -1017,7 +1017,9 @@ void batadv_softif_destroy_sysfs(struct net_device *soft_iface) + static void batadv_softif_destroy_netlink(struct net_device *soft_iface, + struct list_head *head) + { ++ struct batadv_priv *bat_priv = netdev_priv(soft_iface); + struct batadv_hard_iface *hard_iface; ++ struct batadv_softif_vlan *vlan; + + list_for_each_entry(hard_iface, &batadv_hardif_list, list) { + if (hard_iface->soft_iface == soft_iface) +@@ -1025,6 +1027,13 @@ static void batadv_softif_destroy_netlink(struct net_device *soft_iface, + BATADV_IF_CLEANUP_KEEP); + } + ++ /* destroy the "untagged" VLAN */ ++ vlan = batadv_softif_vlan_get(bat_priv, BATADV_NO_FLAGS); ++ if (vlan) { ++ batadv_softif_destroy_vlan(bat_priv, vlan); ++ batadv_softif_vlan_put(vlan); ++ } ++ + batadv_sysfs_del_meshif(soft_iface); + unregister_netdevice_queue(soft_iface, head); + } diff --git a/batman-adv/patches/0012-batman-adv-Fix-ICMP-RR-ethernet-access-after-skb_lin.patch b/batman-adv/patches/0012-batman-adv-Fix-ICMP-RR-ethernet-access-after-skb_lin.patch new file mode 100644 index 0000000..5204cdc --- /dev/null +++ b/batman-adv/patches/0012-batman-adv-Fix-ICMP-RR-ethernet-access-after-skb_lin.patch @@ -0,0 +1,31 @@ +From: Sven Eckelmann +Date: Sun, 29 May 2016 21:25:52 +0200 +Subject: [PATCH] batman-adv: Fix ICMP RR ethernet access after skb_linearize + +The skb_linearize may reallocate the skb. This makes the calculated pointer +for ethhdr invalid. But it the pointer is used later to fill in the RR +field of the batadv_icmp_packet_rr packet. + +Instead re-evaluate eth_hdr after the skb_linearize+skb_cow to fix the +pointer and avoid the invalid read. + +Fixes: bb69cb678d37 ("batman-adv: generalize batman-adv icmp packet handling") +Signed-off-by: Sven Eckelmann + +Origin: upstream, https://git.open-mesh.org/batman-adv.git/commit/f6c80c29ef4e8b45b715976107b7ae06fc0be3a0 +--- + net/batman-adv/routing.c | 1 + + 1 file changed, 1 insertion(+) + +diff --git a/net/batman-adv/routing.c b/net/batman-adv/routing.c +index 0c0c30e..27e07dd 100644 +--- a/net/batman-adv/routing.c ++++ b/net/batman-adv/routing.c +@@ -374,6 +374,7 @@ int batadv_recv_icmp_packet(struct sk_buff *skb, + if (skb_cow(skb, ETH_HLEN) < 0) + goto out; + ++ ethhdr = eth_hdr(skb); + icmph = (struct batadv_icmp_header *)skb->data; + icmp_packet_rr = (struct batadv_icmp_packet_rr *)icmph; + if (icmp_packet_rr->rr_cur >= BATADV_RR_LEN) diff --git a/batman-adv/patches/0013-batman-adv-Fix-double-put-of-vlan-object.patch b/batman-adv/patches/0013-batman-adv-Fix-double-put-of-vlan-object.patch new file mode 100644 index 0000000..6ea8311 --- /dev/null +++ b/batman-adv/patches/0013-batman-adv-Fix-double-put-of-vlan-object.patch @@ -0,0 +1,32 @@ +From: Ben Hutchings +Date: Fri, 3 Jun 2016 00:00:44 +0100 +Subject: [PATCH] batman-adv: Fix double-put of vlan object + +Commit a33d970d0b54 "batman-adv: Fix reference counting of vlan object +for tt_local_entry") makes each batadv_tt_local_entry hold a single +reference to a batadv_softif_vlan. In case a new entry cannot be +added to the hash table, the error path puts the reference, but the +reference will also now be dropped by batadv_tt_local_entry_release(). + +Fixes: a33d970d0b54 ("batman-adv: Fix reference counting of vlan object ...") +Cc: Sven Eckelmann +Signed-off-by: Ben Hutchings +Acked-by: Sven Eckelmann + +Origin: upstream, https://git.open-mesh.org/batman-adv.git/commit/22bb8b894900064d3fb09032a47577e89fc30d7c +--- + net/batman-adv/translation-table.c | 1 - + 1 file changed, 1 deletion(-) + +diff --git a/net/batman-adv/translation-table.c b/net/batman-adv/translation-table.c +index 48adb91..5ed782b 100644 +--- a/net/batman-adv/translation-table.c ++++ b/net/batman-adv/translation-table.c +@@ -693,7 +693,6 @@ bool batadv_tt_local_add(struct net_device *soft_iface, const u8 *addr, + if (unlikely(hash_added != 0)) { + /* remove the reference for the hash */ + batadv_tt_local_entry_put(tt_local); +- batadv_softif_vlan_put(vlan); + goto out; + } + diff --git a/batman-adv/patches/0014-batman-adv-Fix-use-after-free-double-free-of-tt_req_.patch b/batman-adv/patches/0014-batman-adv-Fix-use-after-free-double-free-of-tt_req_.patch new file mode 100644 index 0000000..33c7f3b --- /dev/null +++ b/batman-adv/patches/0014-batman-adv-Fix-use-after-free-double-free-of-tt_req_.patch @@ -0,0 +1,172 @@ +From: Sven Eckelmann +Date: Sat, 4 Jun 2016 08:52:12 +0200 +Subject: [PATCH] batman-adv: Fix use-after-free/double-free of tt_req_node + +The tt_req_node is added and removed from a list inside a spinlock. But the +locking is sometimes removed even when the object is still referenced and +will be used later via this reference. For example batadv_send_tt_request +can create a new tt_req_node (including add to a list) and later +re-acquires the lock to remove it from the list and to free it. But at this +time another context could have already removed this tt_req_node from the +list and freed it. + +CPU#0 + + batadv_batman_skb_recv from net_device 0 + -> batadv_iv_ogm_receive + -> batadv_iv_ogm_process + -> batadv_iv_ogm_process_per_outif + -> batadv_tvlv_ogm_receive + -> batadv_tvlv_ogm_receive + -> batadv_tvlv_containers_process + -> batadv_tvlv_call_handler + -> batadv_tt_tvlv_ogm_handler_v1 + -> batadv_tt_update_orig + -> batadv_send_tt_request + -> batadv_tt_req_node_new + spin_lock(...) + allocates new tt_req_node and adds it to list + spin_unlock(...) + return tt_req_node + +CPU#1 + + batadv_batman_skb_recv from net_device 1 + -> batadv_recv_unicast_tvlv + -> batadv_tvlv_containers_process + -> batadv_tvlv_call_handler + -> batadv_tt_tvlv_unicast_handler_v1 + -> batadv_handle_tt_response + spin_lock(...) + tt_req_node gets removed from list and is freed + spin_unlock(...) + +CPU#0 + + <- returned to batadv_send_tt_request + spin_lock(...) + tt_req_node gets removed from list and is freed + MEMORY CORRUPTION/SEGFAULT/... + spin_unlock(...) + +This can only be solved via reference counting to allow multiple contexts +to handle the list manipulation while making sure that only the last +context holding a reference will free the object. + +Fixes: cea194d90b11 ("batman-adv: improved client announcement mechanism") +Signed-off-by: Sven Eckelmann +Tested-by: Martin Weinelt +Tested-by: Amadeus Alfa + +Origin: upstream, https://git.open-mesh.org/batman-adv.git/commit/c3fef3d9ec6e8b882f321ec20f6f2cb2ee906503 +--- + net/batman-adv/translation-table.c | 37 +++++++++++++++++++++++++++++++++---- + net/batman-adv/types.h | 2 ++ + 2 files changed, 35 insertions(+), 4 deletions(-) + +diff --git a/net/batman-adv/translation-table.c b/net/batman-adv/translation-table.c +index 5ed782b..23fb7ea 100644 +--- a/net/batman-adv/translation-table.c ++++ b/net/batman-adv/translation-table.c +@@ -2271,6 +2271,29 @@ static u32 batadv_tt_local_crc(struct batadv_priv *bat_priv, + return crc; + } + ++/** ++ * batadv_tt_req_node_release - free tt_req node entry ++ * @ref: kref pointer of the tt req_node entry ++ */ ++static void batadv_tt_req_node_release(struct kref *ref) ++{ ++ struct batadv_tt_req_node *tt_req_node; ++ ++ tt_req_node = container_of(ref, struct batadv_tt_req_node, refcount); ++ ++ kfree(tt_req_node); ++} ++ ++/** ++ * batadv_tt_req_node_put - decrement the tt_req_node refcounter and ++ * possibly release it ++ * @tt_req_node: tt_req_node to be free'd ++ */ ++static void batadv_tt_req_node_put(struct batadv_tt_req_node *tt_req_node) ++{ ++ kref_put(&tt_req_node->refcount, batadv_tt_req_node_release); ++} ++ + static void batadv_tt_req_list_free(struct batadv_priv *bat_priv) + { + struct batadv_tt_req_node *node; +@@ -2280,7 +2303,7 @@ static void batadv_tt_req_list_free(struct batadv_priv *bat_priv) + + hlist_for_each_entry_safe(node, safe, &bat_priv->tt.req_list, list) { + hlist_del_init(&node->list); +- kfree(node); ++ batadv_tt_req_node_put(node); + } + + spin_unlock_bh(&bat_priv->tt.req_list_lock); +@@ -2317,7 +2340,7 @@ static void batadv_tt_req_purge(struct batadv_priv *bat_priv) + if (batadv_has_timed_out(node->issued_at, + BATADV_TT_REQUEST_TIMEOUT)) { + hlist_del_init(&node->list); +- kfree(node); ++ batadv_tt_req_node_put(node); + } + } + spin_unlock_bh(&bat_priv->tt.req_list_lock); +@@ -2349,9 +2372,11 @@ batadv_tt_req_node_new(struct batadv_priv *bat_priv, + if (!tt_req_node) + goto unlock; + ++ kref_init(&tt_req_node->refcount); + ether_addr_copy(tt_req_node->addr, orig_node->orig); + tt_req_node->issued_at = jiffies; + ++ kref_get(&tt_req_node->refcount); + hlist_add_head(&tt_req_node->list, &bat_priv->tt.req_list); + unlock: + spin_unlock_bh(&bat_priv->tt.req_list_lock); +@@ -2618,9 +2643,13 @@ out: + spin_lock_bh(&bat_priv->tt.req_list_lock); + /* hlist_del_init() verifies tt_req_node still is in the list */ + hlist_del_init(&tt_req_node->list); ++ batadv_tt_req_node_put(tt_req_node); + spin_unlock_bh(&bat_priv->tt.req_list_lock); +- kfree(tt_req_node); + } ++ ++ if (tt_req_node) ++ batadv_tt_req_node_put(tt_req_node); ++ + kfree(tvlv_tt_data); + return ret; + } +@@ -3056,7 +3085,7 @@ static void batadv_handle_tt_response(struct batadv_priv *bat_priv, + if (!batadv_compare_eth(node->addr, resp_src)) + continue; + hlist_del_init(&node->list); +- kfree(node); ++ batadv_tt_req_node_put(node); + } + + spin_unlock_bh(&bat_priv->tt.req_list_lock); +diff --git a/net/batman-adv/types.h b/net/batman-adv/types.h +index 1e47fbe..d75beef 100644 +--- a/net/batman-adv/types.h ++++ b/net/batman-adv/types.h +@@ -1129,11 +1129,13 @@ struct batadv_tt_change_node { + * struct batadv_tt_req_node - data to keep track of the tt requests in flight + * @addr: mac address address of the originator this request was sent to + * @issued_at: timestamp used for purging stale tt requests ++ * @refcount: number of contexts the object is used by + * @list: list node for batadv_priv_tt::req_list + */ + struct batadv_tt_req_node { + u8 addr[ETH_ALEN]; + unsigned long issued_at; ++ struct kref refcount; + struct hlist_node list; + }; +