summaryrefslogtreecommitdiff
path: root/batman-adv/patches/0037-batman-adv-Avoid-race-in-TT-TVLV-allocator-helper.patch
diff options
context:
space:
mode:
Diffstat (limited to 'batman-adv/patches/0037-batman-adv-Avoid-race-in-TT-TVLV-allocator-helper.patch')
-rw-r--r--batman-adv/patches/0037-batman-adv-Avoid-race-in-TT-TVLV-allocator-helper.patch75
1 files changed, 75 insertions, 0 deletions
diff --git a/batman-adv/patches/0037-batman-adv-Avoid-race-in-TT-TVLV-allocator-helper.patch b/batman-adv/patches/0037-batman-adv-Avoid-race-in-TT-TVLV-allocator-helper.patch
new file mode 100644
index 0000000..964089e
--- /dev/null
+++ b/batman-adv/patches/0037-batman-adv-Avoid-race-in-TT-TVLV-allocator-helper.patch
@@ -0,0 +1,75 @@
+From: Sven Eckelmann <sven@narfation.org>
+Date: Wed, 9 May 2018 21:07:40 +0200
+Subject: [PATCH] batman-adv: Avoid race in TT TVLV allocator helper
+
+The functions batadv_tt_prepare_tvlv_local_data and
+batadv_tt_prepare_tvlv_global_data are responsible for preparing a buffer
+which can be used to store the TVLV container for TT and add the VLAN
+information to it.
+
+This will be done in three phases:
+
+1. count the number of VLANs and their entries
+2. allocate the buffer using the counters from the previous step and limits
+ from the caller (parameter tt_len)
+3. insert the VLAN information to the buffer
+
+The step 1 and 3 operate on a list which contains the VLANs. The access to
+these lists must be protected with an appropriate lock or otherwise they
+might operate on on different entries. This could for example happen when
+another context is adding VLAN entries to this list.
+
+This could lead to a buffer overflow in these functions when enough entries
+were added between step 1 and 3 to the VLAN lists that the buffer room for
+the entries (*tt_change) is smaller then the now required extra buffer for
+new VLAN entries.
+
+Fixes: 21a57f6e7a3b ("batman-adv: make the TT CRC logic VLAN specific")
+Signed-off-by: Sven Eckelmann <sven@narfation.org>
+Acked-by: Antonio Quartulli <a@unstable.cc>
+
+Origin: upstream, https://git.open-mesh.org/batman-adv.git/commit/286be89a33497ba9000aa5c2960f1f4114953522
+---
+ net/batman-adv/translation-table.c | 8 ++++----
+ 1 file changed, 4 insertions(+), 4 deletions(-)
+
+diff --git a/net/batman-adv/translation-table.c b/net/batman-adv/translation-table.c
+index a64003b824e0d0b05f0a9e44ccc32ba0cb3018fc..933ac64b5707846ddee9f828b538ade86b968986 100644
+--- a/net/batman-adv/translation-table.c
++++ b/net/batman-adv/translation-table.c
+@@ -860,7 +860,7 @@ batadv_tt_prepare_tvlv_global_data(struct batadv_orig_node *orig_node,
+ struct batadv_orig_node_vlan *vlan;
+ u8 *tt_change_ptr;
+
+- rcu_read_lock();
++ spin_lock_bh(&orig_node->vlan_list_lock);
+ hlist_for_each_entry_rcu(vlan, &orig_node->vlan_list, list) {
+ num_vlan++;
+ num_entries += atomic_read(&vlan->tt.num_entries);
+@@ -898,7 +898,7 @@ batadv_tt_prepare_tvlv_global_data(struct batadv_orig_node *orig_node,
+ *tt_change = (struct batadv_tvlv_tt_change *)tt_change_ptr;
+
+ out:
+- rcu_read_unlock();
++ spin_unlock_bh(&orig_node->vlan_list_lock);
+ return tvlv_len;
+ }
+
+@@ -934,7 +934,7 @@ batadv_tt_prepare_tvlv_local_data(struct batadv_priv *bat_priv,
+ u8 *tt_change_ptr;
+ int change_offset;
+
+- rcu_read_lock();
++ spin_lock_bh(&bat_priv->softif_vlan_list_lock);
+ hlist_for_each_entry_rcu(vlan, &bat_priv->softif_vlan_list, list) {
+ num_vlan++;
+ num_entries += atomic_read(&vlan->tt.num_entries);
+@@ -972,7 +972,7 @@ batadv_tt_prepare_tvlv_local_data(struct batadv_priv *bat_priv,
+ *tt_change = (struct batadv_tvlv_tt_change *)tt_change_ptr;
+
+ out:
+- rcu_read_unlock();
++ spin_unlock_bh(&bat_priv->softif_vlan_list_lock);
+ return tvlv_len;
+ }
+