When the frame is transmitted due to scanning rather than regular operation on the interface, ignore the bitrate mask. Reported-by: syzbot+fdc5123366fb9c3fdc6d@xxxxxxxxxxxxxxxxxxxxxxxxx Closes: https://syzkaller.appspot.com/bug?extid=fdc5123366fb9c3fdc6d Suggested-by: Johannes Berg <johannes@xxxxxxxxxxxxxxxx> Signed-off-by: Dmitry Antipov <dmantipov@xxxxxxxxx> --- include/net/mac80211.h | 3 +++ net/mac80211/rate.c | 4 +++- net/mac80211/scan.c | 2 ++ 3 files changed, 8 insertions(+), 1 deletion(-) diff --git a/include/net/mac80211.h b/include/net/mac80211.h index d400fe2e8668..df9b578e58bb 100644 --- a/include/net/mac80211.h +++ b/include/net/mac80211.h @@ -932,6 +932,8 @@ enum mac80211_tx_info_flags { * of their QoS TID or other priority field values. * @IEEE80211_TX_CTRL_MCAST_MLO_FIRST_TX: first MLO TX, used mostly internally * for sequence number assignment + * @IEEE80211_TX_CTRL_SCAN_TX: Indicates that this frame is transmitted + * due to scanning, not in normal operation on the interface. * @IEEE80211_TX_CTRL_MLO_LINK: If not @IEEE80211_LINK_UNSPECIFIED, this * frame should be transmitted on the specific link. This really is * only relevant for frames that do not have data present, and is @@ -952,6 +954,7 @@ enum mac80211_tx_control_flags { IEEE80211_TX_CTRL_NO_SEQNO = BIT(7), IEEE80211_TX_CTRL_DONT_REORDER = BIT(8), IEEE80211_TX_CTRL_MCAST_MLO_FIRST_TX = BIT(9), + IEEE80211_TX_CTRL_SCAN_TX = BIT(10), IEEE80211_TX_CTRL_MLO_LINK = 0xf0000000, }; diff --git a/net/mac80211/rate.c b/net/mac80211/rate.c index d5ea5f5bcf3a..6878fe454c36 100644 --- a/net/mac80211/rate.c +++ b/net/mac80211/rate.c @@ -351,6 +351,7 @@ static void __rate_control_send_low(struct ieee80211_hw *hw, int i; u32 rate_flags = ieee80211_chandef_rate_flags(&hw->conf.chandef); + bool scanning = !!(info->control.flags & IEEE80211_TX_CTRL_SCAN_TX); if (sband->band == NL80211_BAND_S1GHZ) { info->control.rates[0].flags |= IEEE80211_TX_RC_S1G_MCS; @@ -364,7 +365,8 @@ static void __rate_control_send_low(struct ieee80211_hw *hw, info->control.rates[0].idx = 0; for (i = 0; i < sband->n_bitrates; i++) { - if (!(rate_mask & BIT(i))) + /* Do not use the bitrate mask when scanning. */ + if (!scanning && !(rate_mask & BIT(i))) continue; if ((rate_flags & sband->bitrates[i].flags) != rate_flags) diff --git a/net/mac80211/scan.c b/net/mac80211/scan.c index 645355e5f1bc..dd68dfe46e0e 100644 --- a/net/mac80211/scan.c +++ b/net/mac80211/scan.c @@ -632,6 +632,8 @@ static void ieee80211_send_scan_probe_req(struct ieee80211_sub_if_data *sdata, cpu_to_le16(IEEE80211_SN_TO_SEQ(sn)); } IEEE80211_SKB_CB(skb)->flags |= tx_flags; + IEEE80211_SKB_CB(skb)->control.flags |= + IEEE80211_TX_CTRL_SCAN_TX; ieee80211_tx_skb_tid_band(sdata, skb, 7, channel->band); } } -- 2.43.0