]> git.ipfire.org Git - thirdparty/kernel/stable-queue.git/commitdiff
5.4-stable patches
authorGreg Kroah-Hartman <gregkh@linuxfoundation.org>
Mon, 21 Oct 2024 10:19:53 +0000 (12:19 +0200)
committerGreg Kroah-Hartman <gregkh@linuxfoundation.org>
Mon, 21 Oct 2024 10:19:53 +0000 (12:19 +0200)
added patches:
mac80211-fix-null-ptr-deref-for-injected-rate-info.patch

queue-5.4/mac80211-fix-null-ptr-deref-for-injected-rate-info.patch [new file with mode: 0644]
queue-5.4/series

diff --git a/queue-5.4/mac80211-fix-null-ptr-deref-for-injected-rate-info.patch b/queue-5.4/mac80211-fix-null-ptr-deref-for-injected-rate-info.patch
new file mode 100644 (file)
index 0000000..3726dc9
--- /dev/null
@@ -0,0 +1,165 @@
+From bddc0c411a45d3718ac535a070f349be8eca8d48 Mon Sep 17 00:00:00 2001
+From: Mathy Vanhoef <Mathy.Vanhoef@kuleuven.be>
+Date: Sun, 30 May 2021 15:32:26 +0200
+Subject: mac80211: Fix NULL ptr deref for injected rate info
+
+From: Mathy Vanhoef <Mathy.Vanhoef@kuleuven.be>
+
+commit bddc0c411a45d3718ac535a070f349be8eca8d48 upstream.
+
+The commit cb17ed29a7a5 ("mac80211: parse radiotap header when selecting Tx
+queue") moved the code to validate the radiotap header from
+ieee80211_monitor_start_xmit to ieee80211_parse_tx_radiotap. This made is
+possible to share more code with the new Tx queue selection code for
+injected frames. But at the same time, it now required the call of
+ieee80211_parse_tx_radiotap at the beginning of functions which wanted to
+handle the radiotap header. And this broke the rate parser for radiotap
+header parser.
+
+The radiotap parser for rates is operating most of the time only on the
+data in the actual radiotap header. But for the 802.11a/b/g rates, it must
+also know the selected band from the chandef information. But this
+information is only written to the ieee80211_tx_info at the end of the
+ieee80211_monitor_start_xmit - long after ieee80211_parse_tx_radiotap was
+already called. The info->band information was therefore always 0
+(NL80211_BAND_2GHZ) when the parser code tried to access it.
+
+For a 5GHz only device, injecting a frame with 802.11a rates would cause a
+NULL pointer dereference because local->hw.wiphy->bands[NL80211_BAND_2GHZ]
+would most likely have been NULL when the radiotap parser searched for the
+correct rate index of the driver.
+
+Cc: stable@vger.kernel.org
+Reported-by: Ben Greear <greearb@candelatech.com>
+Fixes: cb17ed29a7a5 ("mac80211: parse radiotap header when selecting Tx queue")
+Signed-off-by: Mathy Vanhoef <Mathy.Vanhoef@kuleuven.be>
+[sven@narfation.org: added commit message]
+Signed-off-by: Sven Eckelmann <sven@narfation.org>
+Link: https://lore.kernel.org/r/20210530133226.40587-1-sven@narfation.org
+Signed-off-by: Johannes Berg <johannes.berg@intel.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+---
+ include/net/mac80211.h |    8 ++++++-
+ net/mac80211/tx.c      |   52 +++++++++++++++++++++++++++++++++----------------
+ 2 files changed, 43 insertions(+), 17 deletions(-)
+
+--- a/include/net/mac80211.h
++++ b/include/net/mac80211.h
+@@ -6135,7 +6135,13 @@ bool ieee80211_tx_prepare_skb(struct iee
+                             int band, struct ieee80211_sta **sta);
+ /**
+- * Sanity-check and parse the radiotap header of injected frames
++ * ieee80211_parse_tx_radiotap - Sanity-check and parse the radiotap header
++ *                             of injected frames.
++ *
++ * To accurately parse and take into account rate and retransmission fields,
++ * you must initialize the chandef field in the ieee80211_tx_info structure
++ * of the skb before calling this function.
++ *
+  * @skb: packet injected by userspace
+  * @dev: the &struct device of this 802.11 device
+  */
+--- a/net/mac80211/tx.c
++++ b/net/mac80211/tx.c
+@@ -2034,6 +2034,26 @@ void ieee80211_xmit(struct ieee80211_sub
+       ieee80211_tx(sdata, sta, skb, false, txdata_flags);
+ }
++static bool ieee80211_validate_radiotap_len(struct sk_buff *skb)
++{
++      struct ieee80211_radiotap_header *rthdr =
++              (struct ieee80211_radiotap_header *)skb->data;
++
++      /* check for not even having the fixed radiotap header part */
++      if (unlikely(skb->len < sizeof(struct ieee80211_radiotap_header)))
++              return false; /* too short to be possibly valid */
++
++      /* is it a header version we can trust to find length from? */
++      if (unlikely(rthdr->it_version))
++              return false; /* only version 0 is supported */
++
++      /* does the skb contain enough to deliver on the alleged length? */
++      if (unlikely(skb->len < ieee80211_get_radiotap_len(skb->data)))
++              return false; /* skb too short for claimed rt header extent */
++
++      return true;
++}
++
+ bool ieee80211_parse_tx_radiotap(struct sk_buff *skb,
+                                struct net_device *dev)
+ {
+@@ -2042,8 +2062,6 @@ bool ieee80211_parse_tx_radiotap(struct
+       struct ieee80211_radiotap_header *rthdr =
+               (struct ieee80211_radiotap_header *) skb->data;
+       struct ieee80211_tx_info *info = IEEE80211_SKB_CB(skb);
+-      struct ieee80211_supported_band *sband =
+-              local->hw.wiphy->bands[info->band];
+       int ret = ieee80211_radiotap_iterator_init(&iterator, rthdr, skb->len,
+                                                  NULL);
+       u16 txflags;
+@@ -2056,17 +2074,8 @@ bool ieee80211_parse_tx_radiotap(struct
+       u8 vht_mcs = 0, vht_nss = 0;
+       int i;
+-      /* check for not even having the fixed radiotap header part */
+-      if (unlikely(skb->len < sizeof(struct ieee80211_radiotap_header)))
+-              return false; /* too short to be possibly valid */
+-
+-      /* is it a header version we can trust to find length from? */
+-      if (unlikely(rthdr->it_version))
+-              return false; /* only version 0 is supported */
+-
+-      /* does the skb contain enough to deliver on the alleged length? */
+-      if (unlikely(skb->len < ieee80211_get_radiotap_len(skb->data)))
+-              return false; /* skb too short for claimed rt header extent */
++      if (!ieee80211_validate_radiotap_len(skb))
++              return false;
+       info->flags |= IEEE80211_TX_INTFL_DONT_ENCRYPT |
+                      IEEE80211_TX_CTL_DONTFRAG;
+@@ -2192,6 +2201,9 @@ bool ieee80211_parse_tx_radiotap(struct
+               return false;
+       if (rate_found) {
++              struct ieee80211_supported_band *sband =
++                      local->hw.wiphy->bands[info->band];
++
+               info->control.flags |= IEEE80211_TX_CTRL_RATE_INJECT;
+               for (i = 0; i < IEEE80211_TX_MAX_RATES; i++) {
+@@ -2205,7 +2217,7 @@ bool ieee80211_parse_tx_radiotap(struct
+               } else if (rate_flags & IEEE80211_TX_RC_VHT_MCS) {
+                       ieee80211_rate_set_vht(info->control.rates, vht_mcs,
+                                              vht_nss);
+-              } else {
++              } else if (sband) {
+                       for (i = 0; i < sband->n_bitrates; i++) {
+                               if (rate * 5 != sband->bitrates[i].bitrate)
+                                       continue;
+@@ -2242,8 +2254,8 @@ netdev_tx_t ieee80211_monitor_start_xmit
+       info->flags = IEEE80211_TX_CTL_REQ_TX_STATUS |
+                     IEEE80211_TX_CTL_INJECTED;
+-      /* Sanity-check and process the injection radiotap header */
+-      if (!ieee80211_parse_tx_radiotap(skb, dev))
++      /* Sanity-check the length of the radiotap header */
++      if (!ieee80211_validate_radiotap_len(skb))
+               goto fail;
+       /* we now know there is a radiotap header with a length we can use */
+@@ -2356,6 +2368,14 @@ netdev_tx_t ieee80211_monitor_start_xmit
+       info->band = chandef->chan->band;
++      /*
++       * Process the radiotap header. This will now take into account the
++       * selected chandef above to accurately set injection rates and
++       * retransmissions.
++       */
++      if (!ieee80211_parse_tx_radiotap(skb, dev))
++              goto fail_rcu;
++
+       /* remove the injection radiotap header */
+       skb_pull(skb, len_rthdr);
index 9307db83f5cc5fef222c50f187577466150fe4bb..15767054f9746d67349928d83d141af2ac976214 100644 (file)
@@ -381,3 +381,4 @@ x86-resctrl-annotate-get_mem_config-functions-as-__init.patch
 x86-apic-always-explicitly-disarm-tsc-deadline-timer.patch
 nilfs2-propagate-directory-read-errors-from-nilfs_find_entry.patch
 erofs-fix-lz4-inplace-decompression.patch
+mac80211-fix-null-ptr-deref-for-injected-rate-info.patch