Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux

wifi: mac80211: Support Tx of action frame for NAN

Add support for sending management frame over a NAN Device
interface:

- Declare support for the supported management frames types.
- Since action frame transmissions over a NAN Device interface
do not necessarily require a channel configuration, e.g., they
can be transmitted during DW, modify the Tx path to avoid
accessing channel information for NAN Device interface.
- In addition modify the points in the Tx path logic to account
for cases that a band is not specified in the Tx information.

Signed-off-by: Ilan Peer <ilan.peer@intel.com>
Signed-off-by: Miri Korenblit <miriam.rachel.korenblit@intel.com>
Link: https://patch.msgid.link/20250908140015.23b160089228.I65a58af753bcbcfb5c4ad8ef372d546f889725ba@changeid
Signed-off-by: Johannes Berg <johannes.berg@intel.com>

authored by

Ilan Peer and committed by
Johannes Berg
fc41f4a2 1884e259

+33 -4
+4
include/net/mac80211.h
··· 3192 3192 { 3193 3193 if (WARN_ON_ONCE(c->control.rates[0].idx < 0)) 3194 3194 return NULL; 3195 + 3196 + if (c->band >= NUM_NL80211_BANDS) 3197 + return NULL; 3198 + 3195 3199 return &hw->wiphy->bands[c->band]->bitrates[c->control.rates[0].idx]; 3196 3200 } 3197 3201
+5
net/mac80211/main.c
··· 746 746 BIT(IEEE80211_STYPE_PROBE_REQ >> 4) | 747 747 BIT(IEEE80211_STYPE_AUTH >> 4), 748 748 }, 749 + [NL80211_IFTYPE_NAN] = { 750 + .tx = 0xffff, 751 + .rx = BIT(IEEE80211_STYPE_ACTION >> 4) | 752 + BIT(IEEE80211_STYPE_AUTH >> 4), 753 + }, 749 754 }; 750 755 751 756 static const struct ieee80211_ht_cap mac80211_ht_capa_mod_mask = {
+4 -1
net/mac80211/offchannel.c
··· 8 8 * Copyright 2006-2007 Jiri Benc <jbenc@suse.cz> 9 9 * Copyright 2007, Michael Wu <flamingice@sourmilk.net> 10 10 * Copyright 2009 Johannes Berg <johannes@sipsolutions.net> 11 - * Copyright (C) 2019, 2022-2024 Intel Corporation 11 + * Copyright (C) 2019, 2022-2025 Intel Corporation 12 12 */ 13 13 #include <linux/export.h> 14 14 #include <net/mac80211.h> ··· 897 897 need_offchan = true; 898 898 break; 899 899 case NL80211_IFTYPE_NAN: 900 + break; 900 901 default: 901 902 return -EOPNOTSUPP; 902 903 } ··· 911 910 /* Check if the operating channel is the requested channel */ 912 911 if (!params->chan && mlo_sta) { 913 912 need_offchan = false; 913 + } else if (sdata->vif.type == NL80211_IFTYPE_NAN) { 914 + /* Frames can be sent during NAN schedule */ 914 915 } else if (!need_offchan) { 915 916 struct ieee80211_chanctx_conf *chanctx_conf = NULL; 916 917 int i;
+10 -1
net/mac80211/rate.c
··· 4 4 * Copyright 2005-2006, Devicescape Software, Inc. 5 5 * Copyright (c) 2006 Jiri Benc <jbenc@suse.cz> 6 6 * Copyright 2017 Intel Deutschland GmbH 7 - * Copyright (C) 2019, 2022-2024 Intel Corporation 7 + * Copyright (C) 2019, 2022-2025 Intel Corporation 8 8 */ 9 9 10 10 #include <linux/kernel.h> ··· 96 96 struct ieee80211_supported_band *sband; 97 97 98 98 if (!ref || !test_sta_flag(sta, WLAN_STA_RATE_CONTROL)) 99 + return; 100 + 101 + if (st->info->band >= NUM_NL80211_BANDS) 99 102 return; 100 103 101 104 sband = local->hw.wiphy->bands[st->info->band]; ··· 421 418 struct sta_info *sta; 422 419 int mcast_rate; 423 420 bool use_basicrate = false; 421 + 422 + if (!sband) 423 + return false; 424 424 425 425 if (!pubsta || rc_no_data_or_no_ack_use_min(txrc)) { 426 426 __rate_control_send_low(txrc->hw, sband, pubsta, info, ··· 904 898 return; 905 899 906 900 sdata = vif_to_sdata(vif); 901 + if (info->band >= NUM_NL80211_BANDS) 902 + return; 903 + 907 904 sband = sdata->local->hw.wiphy->bands[info->band]; 908 905 909 906 if (ieee80211_is_tx_data(skb))
+10 -2
net/mac80211/tx.c
··· 59 59 if (WARN_ON_ONCE(tx->rate.idx < 0)) 60 60 return 0; 61 61 62 + if (info->band >= NUM_NL80211_BANDS) 63 + return 0; 64 + 62 65 sband = local->hw.wiphy->bands[info->band]; 63 66 txrate = &sband->bitrates[tx->rate.idx]; 64 67 ··· 686 683 687 684 memset(&txrc, 0, sizeof(txrc)); 688 685 689 - sband = tx->local->hw.wiphy->bands[info->band]; 686 + if (info->band < NUM_NL80211_BANDS) 687 + sband = tx->local->hw.wiphy->bands[info->band]; 688 + else 689 + return TX_CONTINUE; 690 690 691 691 len = min_t(u32, tx->skb->len + FCS_LEN, 692 692 tx->local->hw.wiphy->frag_threshold); ··· 6294 6288 enum nl80211_band band; 6295 6289 6296 6290 rcu_read_lock(); 6297 - if (!ieee80211_vif_is_mld(&sdata->vif)) { 6291 + if (sdata->vif.type == NL80211_IFTYPE_NAN) { 6292 + band = NUM_NL80211_BANDS; 6293 + } else if (!ieee80211_vif_is_mld(&sdata->vif)) { 6298 6294 WARN_ON(link_id >= 0); 6299 6295 chanctx_conf = 6300 6296 rcu_dereference(sdata->vif.bss_conf.chanctx_conf);