aboutsummaryrefslogtreecommitdiffstats
path: root/net/mac80211
diff options
context:
space:
mode:
Diffstat (limited to 'net/mac80211')
-rw-r--r--net/mac80211/aes_ccm.c6
-rw-r--r--net/mac80211/cfg.c33
-rw-r--r--net/mac80211/debugfs_netdev.c15
-rw-r--r--net/mac80211/driver-ops.h3
-rw-r--r--net/mac80211/ht.c4
-rw-r--r--net/mac80211/ibss.c49
-rw-r--r--net/mac80211/ieee80211_i.h28
-rw-r--r--net/mac80211/iface.c34
-rw-r--r--net/mac80211/key.c24
-rw-r--r--net/mac80211/key.h15
-rw-r--r--net/mac80211/main.c4
-rw-r--r--net/mac80211/mesh.c38
-rw-r--r--net/mac80211/mesh_plink.c7
-rw-r--r--net/mac80211/mlme.c345
-rw-r--r--net/mac80211/rx.c30
-rw-r--r--net/mac80211/sta_info.c2
-rw-r--r--net/mac80211/sta_info.h5
-rw-r--r--net/mac80211/tx.c5
-rw-r--r--net/mac80211/util.c36
-rw-r--r--net/mac80211/wep.c48
-rw-r--r--net/mac80211/wpa.c68
21 files changed, 372 insertions, 427 deletions
diff --git a/net/mac80211/aes_ccm.c b/net/mac80211/aes_ccm.c
index 0785e95c9924..be7614b9ed27 100644
--- a/net/mac80211/aes_ccm.c
+++ b/net/mac80211/aes_ccm.c
@@ -85,7 +85,7 @@ void ieee80211_aes_ccm_encrypt(struct crypto_cipher *tfm, u8 *scratch,
85 *cpos++ = *pos++ ^ e[i]; 85 *cpos++ = *pos++ ^ e[i];
86 } 86 }
87 87
88 for (i = 0; i < CCMP_MIC_LEN; i++) 88 for (i = 0; i < IEEE80211_CCMP_MIC_LEN; i++)
89 mic[i] = b[i] ^ s_0[i]; 89 mic[i] = b[i] ^ s_0[i];
90} 90}
91 91
@@ -123,7 +123,7 @@ int ieee80211_aes_ccm_decrypt(struct crypto_cipher *tfm, u8 *scratch,
123 crypto_cipher_encrypt_one(tfm, a, a); 123 crypto_cipher_encrypt_one(tfm, a, a);
124 } 124 }
125 125
126 for (i = 0; i < CCMP_MIC_LEN; i++) { 126 for (i = 0; i < IEEE80211_CCMP_MIC_LEN; i++) {
127 if ((mic[i] ^ s_0[i]) != a[i]) 127 if ((mic[i] ^ s_0[i]) != a[i])
128 return -1; 128 return -1;
129 } 129 }
@@ -138,7 +138,7 @@ struct crypto_cipher *ieee80211_aes_key_setup_encrypt(const u8 key[])
138 138
139 tfm = crypto_alloc_cipher("aes", 0, CRYPTO_ALG_ASYNC); 139 tfm = crypto_alloc_cipher("aes", 0, CRYPTO_ALG_ASYNC);
140 if (!IS_ERR(tfm)) 140 if (!IS_ERR(tfm))
141 crypto_cipher_setkey(tfm, key, ALG_CCMP_KEY_LEN); 141 crypto_cipher_setkey(tfm, key, WLAN_KEY_LEN_CCMP);
142 142
143 return tfm; 143 return tfm;
144} 144}
diff --git a/net/mac80211/cfg.c b/net/mac80211/cfg.c
index 4fdb306e42e0..a1c6e1ceede8 100644
--- a/net/mac80211/cfg.c
+++ b/net/mac80211/cfg.c
@@ -73,16 +73,19 @@ static int ieee80211_change_iface(struct wiphy *wiphy,
73 struct ieee80211_local *local = sdata->local; 73 struct ieee80211_local *local = sdata->local;
74 74
75 if (ieee80211_sdata_running(sdata)) { 75 if (ieee80211_sdata_running(sdata)) {
76 u32 mask = MONITOR_FLAG_COOK_FRAMES |
77 MONITOR_FLAG_ACTIVE;
78
76 /* 79 /*
77 * Prohibit MONITOR_FLAG_COOK_FRAMES to be 80 * Prohibit MONITOR_FLAG_COOK_FRAMES and
78 * changed while the interface is up. 81 * MONITOR_FLAG_ACTIVE to be changed while the
82 * interface is up.
79 * Else we would need to add a lot of cruft 83 * Else we would need to add a lot of cruft
80 * to update everything: 84 * to update everything:
81 * cooked_mntrs, monitor and all fif_* counters 85 * cooked_mntrs, monitor and all fif_* counters
82 * reconfigure hardware 86 * reconfigure hardware
83 */ 87 */
84 if ((*flags & MONITOR_FLAG_COOK_FRAMES) != 88 if ((*flags & mask) != (sdata->u.mntr_flags & mask))
85 (sdata->u.mntr_flags & MONITOR_FLAG_COOK_FRAMES))
86 return -EBUSY; 89 return -EBUSY;
87 90
88 ieee80211_adjust_monitor_flags(sdata, -1); 91 ieee80211_adjust_monitor_flags(sdata, -1);
@@ -444,7 +447,7 @@ static void sta_set_sinfo(struct sta_info *sta, struct station_info *sinfo)
444 struct ieee80211_local *local = sdata->local; 447 struct ieee80211_local *local = sdata->local;
445 struct timespec uptime; 448 struct timespec uptime;
446 u64 packets = 0; 449 u64 packets = 0;
447 int ac; 450 int i, ac;
448 451
449 sinfo->generation = sdata->local->sta_generation; 452 sinfo->generation = sdata->local->sta_generation;
450 453
@@ -488,6 +491,17 @@ static void sta_set_sinfo(struct sta_info *sta, struct station_info *sinfo)
488 sinfo->signal = (s8)sta->last_signal; 491 sinfo->signal = (s8)sta->last_signal;
489 sinfo->signal_avg = (s8) -ewma_read(&sta->avg_signal); 492 sinfo->signal_avg = (s8) -ewma_read(&sta->avg_signal);
490 } 493 }
494 if (sta->chains) {
495 sinfo->filled |= STATION_INFO_CHAIN_SIGNAL |
496 STATION_INFO_CHAIN_SIGNAL_AVG;
497
498 sinfo->chains = sta->chains;
499 for (i = 0; i < ARRAY_SIZE(sinfo->chain_signal); i++) {
500 sinfo->chain_signal[i] = sta->chain_signal_last[i];
501 sinfo->chain_signal_avg[i] =
502 (s8) -ewma_read(&sta->chain_signal_avg[i]);
503 }
504 }
491 505
492 sta_set_rate_info_tx(sta, &sta->last_tx_rate, &sinfo->txrate); 506 sta_set_rate_info_tx(sta, &sta->last_tx_rate, &sinfo->txrate);
493 sta_set_rate_info_rx(sta, &sinfo->rxrate); 507 sta_set_rate_info_rx(sta, &sinfo->rxrate);
@@ -728,7 +742,7 @@ static void ieee80211_get_et_strings(struct wiphy *wiphy,
728 742
729 if (sset == ETH_SS_STATS) { 743 if (sset == ETH_SS_STATS) {
730 sz_sta_stats = sizeof(ieee80211_gstrings_sta_stats); 744 sz_sta_stats = sizeof(ieee80211_gstrings_sta_stats);
731 memcpy(data, *ieee80211_gstrings_sta_stats, sz_sta_stats); 745 memcpy(data, ieee80211_gstrings_sta_stats, sz_sta_stats);
732 } 746 }
733 drv_get_et_strings(sdata, sset, &(data[sz_sta_stats])); 747 drv_get_et_strings(sdata, sset, &(data[sz_sta_stats]));
734} 748}
@@ -1741,6 +1755,7 @@ static int copy_mesh_setup(struct ieee80211_if_mesh *ifmsh,
1741 ifmsh->mesh_pp_id = setup->path_sel_proto; 1755 ifmsh->mesh_pp_id = setup->path_sel_proto;
1742 ifmsh->mesh_pm_id = setup->path_metric; 1756 ifmsh->mesh_pm_id = setup->path_metric;
1743 ifmsh->user_mpm = setup->user_mpm; 1757 ifmsh->user_mpm = setup->user_mpm;
1758 ifmsh->mesh_auth_id = setup->auth_id;
1744 ifmsh->security = IEEE80211_MESH_SEC_NONE; 1759 ifmsh->security = IEEE80211_MESH_SEC_NONE;
1745 if (setup->is_authenticated) 1760 if (setup->is_authenticated)
1746 ifmsh->security |= IEEE80211_MESH_SEC_AUTHED; 1761 ifmsh->security |= IEEE80211_MESH_SEC_AUTHED;
@@ -2312,7 +2327,7 @@ int __ieee80211_request_smps(struct ieee80211_sub_if_data *sdata,
2312 enum ieee80211_smps_mode old_req; 2327 enum ieee80211_smps_mode old_req;
2313 int err; 2328 int err;
2314 2329
2315 lockdep_assert_held(&sdata->u.mgd.mtx); 2330 lockdep_assert_held(&sdata->wdev.mtx);
2316 2331
2317 old_req = sdata->u.mgd.req_smps; 2332 old_req = sdata->u.mgd.req_smps;
2318 sdata->u.mgd.req_smps = smps_mode; 2333 sdata->u.mgd.req_smps = smps_mode;
@@ -2369,9 +2384,9 @@ static int ieee80211_set_power_mgmt(struct wiphy *wiphy, struct net_device *dev,
2369 local->dynamic_ps_forced_timeout = timeout; 2384 local->dynamic_ps_forced_timeout = timeout;
2370 2385
2371 /* no change, but if automatic follow powersave */ 2386 /* no change, but if automatic follow powersave */
2372 mutex_lock(&sdata->u.mgd.mtx); 2387 sdata_lock(sdata);
2373 __ieee80211_request_smps(sdata, sdata->u.mgd.req_smps); 2388 __ieee80211_request_smps(sdata, sdata->u.mgd.req_smps);
2374 mutex_unlock(&sdata->u.mgd.mtx); 2389 sdata_unlock(sdata);
2375 2390
2376 if (local->hw.flags & IEEE80211_HW_SUPPORTS_DYNAMIC_PS) 2391 if (local->hw.flags & IEEE80211_HW_SUPPORTS_DYNAMIC_PS)
2377 ieee80211_hw_config(local, IEEE80211_CONF_CHANGE_PS); 2392 ieee80211_hw_config(local, IEEE80211_CONF_CHANGE_PS);
diff --git a/net/mac80211/debugfs_netdev.c b/net/mac80211/debugfs_netdev.c
index 14abcf44f974..cafe614ef93d 100644
--- a/net/mac80211/debugfs_netdev.c
+++ b/net/mac80211/debugfs_netdev.c
@@ -228,9 +228,9 @@ static int ieee80211_set_smps(struct ieee80211_sub_if_data *sdata,
228 if (sdata->vif.type != NL80211_IFTYPE_STATION) 228 if (sdata->vif.type != NL80211_IFTYPE_STATION)
229 return -EOPNOTSUPP; 229 return -EOPNOTSUPP;
230 230
231 mutex_lock(&sdata->u.mgd.mtx); 231 sdata_lock(sdata);
232 err = __ieee80211_request_smps(sdata, smps_mode); 232 err = __ieee80211_request_smps(sdata, smps_mode);
233 mutex_unlock(&sdata->u.mgd.mtx); 233 sdata_unlock(sdata);
234 234
235 return err; 235 return err;
236} 236}
@@ -313,16 +313,16 @@ static ssize_t ieee80211_if_parse_tkip_mic_test(
313 case NL80211_IFTYPE_STATION: 313 case NL80211_IFTYPE_STATION:
314 fc |= cpu_to_le16(IEEE80211_FCTL_TODS); 314 fc |= cpu_to_le16(IEEE80211_FCTL_TODS);
315 /* BSSID SA DA */ 315 /* BSSID SA DA */
316 mutex_lock(&sdata->u.mgd.mtx); 316 sdata_lock(sdata);
317 if (!sdata->u.mgd.associated) { 317 if (!sdata->u.mgd.associated) {
318 mutex_unlock(&sdata->u.mgd.mtx); 318 sdata_unlock(sdata);
319 dev_kfree_skb(skb); 319 dev_kfree_skb(skb);
320 return -ENOTCONN; 320 return -ENOTCONN;
321 } 321 }
322 memcpy(hdr->addr1, sdata->u.mgd.associated->bssid, ETH_ALEN); 322 memcpy(hdr->addr1, sdata->u.mgd.associated->bssid, ETH_ALEN);
323 memcpy(hdr->addr2, sdata->vif.addr, ETH_ALEN); 323 memcpy(hdr->addr2, sdata->vif.addr, ETH_ALEN);
324 memcpy(hdr->addr3, addr, ETH_ALEN); 324 memcpy(hdr->addr3, addr, ETH_ALEN);
325 mutex_unlock(&sdata->u.mgd.mtx); 325 sdata_unlock(sdata);
326 break; 326 break;
327 default: 327 default:
328 dev_kfree_skb(skb); 328 dev_kfree_skb(skb);
@@ -471,6 +471,8 @@ __IEEE80211_IF_FILE_W(tsf);
471IEEE80211_IF_FILE(peer, u.wds.remote_addr, MAC); 471IEEE80211_IF_FILE(peer, u.wds.remote_addr, MAC);
472 472
473#ifdef CONFIG_MAC80211_MESH 473#ifdef CONFIG_MAC80211_MESH
474IEEE80211_IF_FILE(estab_plinks, u.mesh.estab_plinks, ATOMIC);
475
474/* Mesh stats attributes */ 476/* Mesh stats attributes */
475IEEE80211_IF_FILE(fwded_mcast, u.mesh.mshstats.fwded_mcast, DEC); 477IEEE80211_IF_FILE(fwded_mcast, u.mesh.mshstats.fwded_mcast, DEC);
476IEEE80211_IF_FILE(fwded_unicast, u.mesh.mshstats.fwded_unicast, DEC); 478IEEE80211_IF_FILE(fwded_unicast, u.mesh.mshstats.fwded_unicast, DEC);
@@ -480,7 +482,6 @@ IEEE80211_IF_FILE(dropped_frames_congestion,
480 u.mesh.mshstats.dropped_frames_congestion, DEC); 482 u.mesh.mshstats.dropped_frames_congestion, DEC);
481IEEE80211_IF_FILE(dropped_frames_no_route, 483IEEE80211_IF_FILE(dropped_frames_no_route,
482 u.mesh.mshstats.dropped_frames_no_route, DEC); 484 u.mesh.mshstats.dropped_frames_no_route, DEC);
483IEEE80211_IF_FILE(estab_plinks, u.mesh.estab_plinks, ATOMIC);
484 485
485/* Mesh parameters */ 486/* Mesh parameters */
486IEEE80211_IF_FILE(dot11MeshMaxRetries, 487IEEE80211_IF_FILE(dot11MeshMaxRetries,
@@ -583,6 +584,7 @@ static void add_wds_files(struct ieee80211_sub_if_data *sdata)
583static void add_mesh_files(struct ieee80211_sub_if_data *sdata) 584static void add_mesh_files(struct ieee80211_sub_if_data *sdata)
584{ 585{
585 DEBUGFS_ADD_MODE(tsf, 0600); 586 DEBUGFS_ADD_MODE(tsf, 0600);
587 DEBUGFS_ADD_MODE(estab_plinks, 0400);
586} 588}
587 589
588static void add_mesh_stats(struct ieee80211_sub_if_data *sdata) 590static void add_mesh_stats(struct ieee80211_sub_if_data *sdata)
@@ -598,7 +600,6 @@ static void add_mesh_stats(struct ieee80211_sub_if_data *sdata)
598 MESHSTATS_ADD(dropped_frames_ttl); 600 MESHSTATS_ADD(dropped_frames_ttl);
599 MESHSTATS_ADD(dropped_frames_no_route); 601 MESHSTATS_ADD(dropped_frames_no_route);
600 MESHSTATS_ADD(dropped_frames_congestion); 602 MESHSTATS_ADD(dropped_frames_congestion);
601 MESHSTATS_ADD(estab_plinks);
602#undef MESHSTATS_ADD 603#undef MESHSTATS_ADD
603} 604}
604 605
diff --git a/net/mac80211/driver-ops.h b/net/mac80211/driver-ops.h
index 169664c122e2..b931c96a596f 100644
--- a/net/mac80211/driver-ops.h
+++ b/net/mac80211/driver-ops.h
@@ -146,7 +146,8 @@ static inline int drv_add_interface(struct ieee80211_local *local,
146 146
147 if (WARN_ON(sdata->vif.type == NL80211_IFTYPE_AP_VLAN || 147 if (WARN_ON(sdata->vif.type == NL80211_IFTYPE_AP_VLAN ||
148 (sdata->vif.type == NL80211_IFTYPE_MONITOR && 148 (sdata->vif.type == NL80211_IFTYPE_MONITOR &&
149 !(local->hw.flags & IEEE80211_HW_WANT_MONITOR_VIF)))) 149 !(local->hw.flags & IEEE80211_HW_WANT_MONITOR_VIF) &&
150 !(sdata->u.mntr_flags & MONITOR_FLAG_ACTIVE))))
150 return -EINVAL; 151 return -EINVAL;
151 152
152 trace_drv_add_interface(local, sdata); 153 trace_drv_add_interface(local, sdata);
diff --git a/net/mac80211/ht.c b/net/mac80211/ht.c
index af8cee06e4f3..75dff338f581 100644
--- a/net/mac80211/ht.c
+++ b/net/mac80211/ht.c
@@ -429,9 +429,9 @@ void ieee80211_request_smps_work(struct work_struct *work)
429 container_of(work, struct ieee80211_sub_if_data, 429 container_of(work, struct ieee80211_sub_if_data,
430 u.mgd.request_smps_work); 430 u.mgd.request_smps_work);
431 431
432 mutex_lock(&sdata->u.mgd.mtx); 432 sdata_lock(sdata);
433 __ieee80211_request_smps(sdata, sdata->u.mgd.driver_smps_mode); 433 __ieee80211_request_smps(sdata, sdata->u.mgd.driver_smps_mode);
434 mutex_unlock(&sdata->u.mgd.mtx); 434 sdata_unlock(sdata);
435} 435}
436 436
437void ieee80211_request_smps(struct ieee80211_vif *vif, 437void ieee80211_request_smps(struct ieee80211_vif *vif,
diff --git a/net/mac80211/ibss.c b/net/mac80211/ibss.c
index 170f9a7fa319..caa4b4f7f6e4 100644
--- a/net/mac80211/ibss.c
+++ b/net/mac80211/ibss.c
@@ -54,7 +54,7 @@ static void __ieee80211_sta_join_ibss(struct ieee80211_sub_if_data *sdata,
54 struct beacon_data *presp; 54 struct beacon_data *presp;
55 int frame_len; 55 int frame_len;
56 56
57 lockdep_assert_held(&ifibss->mtx); 57 sdata_assert_lock(sdata);
58 58
59 /* Reset own TSF to allow time synchronization work. */ 59 /* Reset own TSF to allow time synchronization work. */
60 drv_reset_tsf(local, sdata); 60 drv_reset_tsf(local, sdata);
@@ -74,7 +74,7 @@ static void __ieee80211_sta_join_ibss(struct ieee80211_sub_if_data *sdata,
74 } 74 }
75 75
76 presp = rcu_dereference_protected(ifibss->presp, 76 presp = rcu_dereference_protected(ifibss->presp,
77 lockdep_is_held(&ifibss->mtx)); 77 lockdep_is_held(&sdata->wdev.mtx));
78 rcu_assign_pointer(ifibss->presp, NULL); 78 rcu_assign_pointer(ifibss->presp, NULL);
79 if (presp) 79 if (presp)
80 kfree_rcu(presp, rcu_head); 80 kfree_rcu(presp, rcu_head);
@@ -263,7 +263,7 @@ static void ieee80211_sta_join_ibss(struct ieee80211_sub_if_data *sdata,
263 const struct cfg80211_bss_ies *ies; 263 const struct cfg80211_bss_ies *ies;
264 u64 tsf; 264 u64 tsf;
265 265
266 lockdep_assert_held(&sdata->u.ibss.mtx); 266 sdata_assert_lock(sdata);
267 267
268 if (beacon_int < 10) 268 if (beacon_int < 10)
269 beacon_int = 10; 269 beacon_int = 10;
@@ -341,6 +341,7 @@ ieee80211_ibss_add_sta(struct ieee80211_sub_if_data *sdata,
341 struct ieee80211_local *local = sdata->local; 341 struct ieee80211_local *local = sdata->local;
342 struct sta_info *sta; 342 struct sta_info *sta;
343 struct ieee80211_chanctx_conf *chanctx_conf; 343 struct ieee80211_chanctx_conf *chanctx_conf;
344 struct ieee80211_supported_band *sband;
344 int band; 345 int band;
345 346
346 /* 347 /*
@@ -380,8 +381,9 @@ ieee80211_ibss_add_sta(struct ieee80211_sub_if_data *sdata,
380 sta->last_rx = jiffies; 381 sta->last_rx = jiffies;
381 382
382 /* make sure mandatory rates are always added */ 383 /* make sure mandatory rates are always added */
384 sband = local->hw.wiphy->bands[band];
383 sta->sta.supp_rates[band] = supp_rates | 385 sta->sta.supp_rates[band] = supp_rates |
384 ieee80211_mandatory_rates(local, band); 386 ieee80211_mandatory_rates(sband);
385 387
386 return ieee80211_ibss_finish_sta(sta, auth); 388 return ieee80211_ibss_finish_sta(sta, auth);
387} 389}
@@ -408,7 +410,7 @@ static void ieee80211_rx_mgmt_auth_ibss(struct ieee80211_sub_if_data *sdata,
408 struct sta_info *sta; 410 struct sta_info *sta;
409 u8 deauth_frame_buf[IEEE80211_DEAUTH_FRAME_LEN]; 411 u8 deauth_frame_buf[IEEE80211_DEAUTH_FRAME_LEN];
410 412
411 lockdep_assert_held(&sdata->u.ibss.mtx); 413 sdata_assert_lock(sdata);
412 414
413 if (len < 24 + 6) 415 if (len < 24 + 6)
414 return; 416 return;
@@ -492,7 +494,7 @@ static void ieee80211_rx_bss_info(struct ieee80211_sub_if_data *sdata,
492 prev_rates = sta->sta.supp_rates[band]; 494 prev_rates = sta->sta.supp_rates[band];
493 /* make sure mandatory rates are always added */ 495 /* make sure mandatory rates are always added */
494 sta->sta.supp_rates[band] = supp_rates | 496 sta->sta.supp_rates[band] = supp_rates |
495 ieee80211_mandatory_rates(local, band); 497 ieee80211_mandatory_rates(sband);
496 498
497 if (sta->sta.supp_rates[band] != prev_rates) { 499 if (sta->sta.supp_rates[band] != prev_rates) {
498 ibss_dbg(sdata, 500 ibss_dbg(sdata,
@@ -624,6 +626,7 @@ void ieee80211_ibss_rx_no_sta(struct ieee80211_sub_if_data *sdata,
624 struct ieee80211_local *local = sdata->local; 626 struct ieee80211_local *local = sdata->local;
625 struct sta_info *sta; 627 struct sta_info *sta;
626 struct ieee80211_chanctx_conf *chanctx_conf; 628 struct ieee80211_chanctx_conf *chanctx_conf;
629 struct ieee80211_supported_band *sband;
627 int band; 630 int band;
628 631
629 /* 632 /*
@@ -658,8 +661,9 @@ void ieee80211_ibss_rx_no_sta(struct ieee80211_sub_if_data *sdata,
658 sta->last_rx = jiffies; 661 sta->last_rx = jiffies;
659 662
660 /* make sure mandatory rates are always added */ 663 /* make sure mandatory rates are always added */
664 sband = local->hw.wiphy->bands[band];
661 sta->sta.supp_rates[band] = supp_rates | 665 sta->sta.supp_rates[band] = supp_rates |
662 ieee80211_mandatory_rates(local, band); 666 ieee80211_mandatory_rates(sband);
663 667
664 spin_lock(&ifibss->incomplete_lock); 668 spin_lock(&ifibss->incomplete_lock);
665 list_add(&sta->list, &ifibss->incomplete_stations); 669 list_add(&sta->list, &ifibss->incomplete_stations);
@@ -673,7 +677,7 @@ static int ieee80211_sta_active_ibss(struct ieee80211_sub_if_data *sdata)
673 int active = 0; 677 int active = 0;
674 struct sta_info *sta; 678 struct sta_info *sta;
675 679
676 lockdep_assert_held(&sdata->u.ibss.mtx); 680 sdata_assert_lock(sdata);
677 681
678 rcu_read_lock(); 682 rcu_read_lock();
679 683
@@ -699,7 +703,7 @@ static void ieee80211_sta_merge_ibss(struct ieee80211_sub_if_data *sdata)
699{ 703{
700 struct ieee80211_if_ibss *ifibss = &sdata->u.ibss; 704 struct ieee80211_if_ibss *ifibss = &sdata->u.ibss;
701 705
702 lockdep_assert_held(&ifibss->mtx); 706 sdata_assert_lock(sdata);
703 707
704 mod_timer(&ifibss->timer, 708 mod_timer(&ifibss->timer,
705 round_jiffies(jiffies + IEEE80211_IBSS_MERGE_INTERVAL)); 709 round_jiffies(jiffies + IEEE80211_IBSS_MERGE_INTERVAL));
@@ -730,7 +734,7 @@ static void ieee80211_sta_create_ibss(struct ieee80211_sub_if_data *sdata)
730 u16 capability; 734 u16 capability;
731 int i; 735 int i;
732 736
733 lockdep_assert_held(&ifibss->mtx); 737 sdata_assert_lock(sdata);
734 738
735 if (ifibss->fixed_bssid) { 739 if (ifibss->fixed_bssid) {
736 memcpy(bssid, ifibss->bssid, ETH_ALEN); 740 memcpy(bssid, ifibss->bssid, ETH_ALEN);
@@ -773,7 +777,7 @@ static void ieee80211_sta_find_ibss(struct ieee80211_sub_if_data *sdata)
773 int active_ibss; 777 int active_ibss;
774 u16 capability; 778 u16 capability;
775 779
776 lockdep_assert_held(&ifibss->mtx); 780 sdata_assert_lock(sdata);
777 781
778 active_ibss = ieee80211_sta_active_ibss(sdata); 782 active_ibss = ieee80211_sta_active_ibss(sdata);
779 ibss_dbg(sdata, "sta_find_ibss (active_ibss=%d)\n", active_ibss); 783 ibss_dbg(sdata, "sta_find_ibss (active_ibss=%d)\n", active_ibss);
@@ -843,10 +847,10 @@ static void ieee80211_rx_mgmt_probe_req(struct ieee80211_sub_if_data *sdata,
843 struct beacon_data *presp; 847 struct beacon_data *presp;
844 u8 *pos, *end; 848 u8 *pos, *end;
845 849
846 lockdep_assert_held(&ifibss->mtx); 850 sdata_assert_lock(sdata);
847 851
848 presp = rcu_dereference_protected(ifibss->presp, 852 presp = rcu_dereference_protected(ifibss->presp,
849 lockdep_is_held(&ifibss->mtx)); 853 lockdep_is_held(&sdata->wdev.mtx));
850 854
851 if (ifibss->state != IEEE80211_IBSS_MLME_JOINED || 855 if (ifibss->state != IEEE80211_IBSS_MLME_JOINED ||
852 len < 24 + 2 || !presp) 856 len < 24 + 2 || !presp)
@@ -930,7 +934,7 @@ void ieee80211_ibss_rx_queued_mgmt(struct ieee80211_sub_if_data *sdata,
930 mgmt = (struct ieee80211_mgmt *) skb->data; 934 mgmt = (struct ieee80211_mgmt *) skb->data;
931 fc = le16_to_cpu(mgmt->frame_control); 935 fc = le16_to_cpu(mgmt->frame_control);
932 936
933 mutex_lock(&sdata->u.ibss.mtx); 937 sdata_lock(sdata);
934 938
935 if (!sdata->u.ibss.ssid_len) 939 if (!sdata->u.ibss.ssid_len)
936 goto mgmt_out; /* not ready to merge yet */ 940 goto mgmt_out; /* not ready to merge yet */
@@ -953,7 +957,7 @@ void ieee80211_ibss_rx_queued_mgmt(struct ieee80211_sub_if_data *sdata,
953 } 957 }
954 958
955 mgmt_out: 959 mgmt_out:
956 mutex_unlock(&sdata->u.ibss.mtx); 960 sdata_unlock(sdata);
957} 961}
958 962
959void ieee80211_ibss_work(struct ieee80211_sub_if_data *sdata) 963void ieee80211_ibss_work(struct ieee80211_sub_if_data *sdata)
@@ -961,7 +965,7 @@ void ieee80211_ibss_work(struct ieee80211_sub_if_data *sdata)
961 struct ieee80211_if_ibss *ifibss = &sdata->u.ibss; 965 struct ieee80211_if_ibss *ifibss = &sdata->u.ibss;
962 struct sta_info *sta; 966 struct sta_info *sta;
963 967
964 mutex_lock(&ifibss->mtx); 968 sdata_lock(sdata);
965 969
966 /* 970 /*
967 * Work could be scheduled after scan or similar 971 * Work could be scheduled after scan or similar
@@ -997,7 +1001,7 @@ void ieee80211_ibss_work(struct ieee80211_sub_if_data *sdata)
997 } 1001 }
998 1002
999 out: 1003 out:
1000 mutex_unlock(&ifibss->mtx); 1004 sdata_unlock(sdata);
1001} 1005}
1002 1006
1003static void ieee80211_ibss_timer(unsigned long data) 1007static void ieee80211_ibss_timer(unsigned long data)
@@ -1014,7 +1018,6 @@ void ieee80211_ibss_setup_sdata(struct ieee80211_sub_if_data *sdata)
1014 1018
1015 setup_timer(&ifibss->timer, ieee80211_ibss_timer, 1019 setup_timer(&ifibss->timer, ieee80211_ibss_timer,
1016 (unsigned long) sdata); 1020 (unsigned long) sdata);
1017 mutex_init(&ifibss->mtx);
1018 INIT_LIST_HEAD(&ifibss->incomplete_stations); 1021 INIT_LIST_HEAD(&ifibss->incomplete_stations);
1019 spin_lock_init(&ifibss->incomplete_lock); 1022 spin_lock_init(&ifibss->incomplete_lock);
1020} 1023}
@@ -1041,8 +1044,6 @@ int ieee80211_ibss_join(struct ieee80211_sub_if_data *sdata,
1041{ 1044{
1042 u32 changed = 0; 1045 u32 changed = 0;
1043 1046
1044 mutex_lock(&sdata->u.ibss.mtx);
1045
1046 if (params->bssid) { 1047 if (params->bssid) {
1047 memcpy(sdata->u.ibss.bssid, params->bssid, ETH_ALEN); 1048 memcpy(sdata->u.ibss.bssid, params->bssid, ETH_ALEN);
1048 sdata->u.ibss.fixed_bssid = true; 1049 sdata->u.ibss.fixed_bssid = true;
@@ -1075,8 +1076,6 @@ int ieee80211_ibss_join(struct ieee80211_sub_if_data *sdata,
1075 memcpy(sdata->u.ibss.ssid, params->ssid, params->ssid_len); 1076 memcpy(sdata->u.ibss.ssid, params->ssid, params->ssid_len);
1076 sdata->u.ibss.ssid_len = params->ssid_len; 1077 sdata->u.ibss.ssid_len = params->ssid_len;
1077 1078
1078 mutex_unlock(&sdata->u.ibss.mtx);
1079
1080 /* 1079 /*
1081 * 802.11n-2009 9.13.3.1: In an IBSS, the HT Protection field is 1080 * 802.11n-2009 9.13.3.1: In an IBSS, the HT Protection field is
1082 * reserved, but an HT STA shall protect HT transmissions as though 1081 * reserved, but an HT STA shall protect HT transmissions as though
@@ -1112,8 +1111,6 @@ int ieee80211_ibss_leave(struct ieee80211_sub_if_data *sdata)
1112 struct sta_info *sta; 1111 struct sta_info *sta;
1113 struct beacon_data *presp; 1112 struct beacon_data *presp;
1114 1113
1115 mutex_lock(&sdata->u.ibss.mtx);
1116
1117 active_ibss = ieee80211_sta_active_ibss(sdata); 1114 active_ibss = ieee80211_sta_active_ibss(sdata);
1118 1115
1119 if (!active_ibss && !is_zero_ether_addr(ifibss->bssid)) { 1116 if (!active_ibss && !is_zero_ether_addr(ifibss->bssid)) {
@@ -1157,7 +1154,7 @@ int ieee80211_ibss_leave(struct ieee80211_sub_if_data *sdata)
1157 /* remove beacon */ 1154 /* remove beacon */
1158 kfree(sdata->u.ibss.ie); 1155 kfree(sdata->u.ibss.ie);
1159 presp = rcu_dereference_protected(ifibss->presp, 1156 presp = rcu_dereference_protected(ifibss->presp,
1160 lockdep_is_held(&sdata->u.ibss.mtx)); 1157 lockdep_is_held(&sdata->wdev.mtx));
1161 RCU_INIT_POINTER(sdata->u.ibss.presp, NULL); 1158 RCU_INIT_POINTER(sdata->u.ibss.presp, NULL);
1162 sdata->vif.bss_conf.ibss_joined = false; 1159 sdata->vif.bss_conf.ibss_joined = false;
1163 sdata->vif.bss_conf.ibss_creator = false; 1160 sdata->vif.bss_conf.ibss_creator = false;
@@ -1173,7 +1170,5 @@ int ieee80211_ibss_leave(struct ieee80211_sub_if_data *sdata)
1173 1170
1174 del_timer_sync(&sdata->u.ibss.timer); 1171 del_timer_sync(&sdata->u.ibss.timer);
1175 1172
1176 mutex_unlock(&sdata->u.ibss.mtx);
1177
1178 return 0; 1173 return 0;
1179} 1174}
diff --git a/net/mac80211/ieee80211_i.h b/net/mac80211/ieee80211_i.h
index 9ca8e3278cc0..923e1772e8f3 100644
--- a/net/mac80211/ieee80211_i.h
+++ b/net/mac80211/ieee80211_i.h
@@ -394,7 +394,6 @@ struct ieee80211_if_managed {
394 bool nullfunc_failed; 394 bool nullfunc_failed;
395 bool connection_loss; 395 bool connection_loss;
396 396
397 struct mutex mtx;
398 struct cfg80211_bss *associated; 397 struct cfg80211_bss *associated;
399 struct ieee80211_mgd_auth_data *auth_data; 398 struct ieee80211_mgd_auth_data *auth_data;
400 struct ieee80211_mgd_assoc_data *assoc_data; 399 struct ieee80211_mgd_assoc_data *assoc_data;
@@ -488,8 +487,6 @@ struct ieee80211_if_managed {
488struct ieee80211_if_ibss { 487struct ieee80211_if_ibss {
489 struct timer_list timer; 488 struct timer_list timer;
490 489
491 struct mutex mtx;
492
493 unsigned long last_scan_completed; 490 unsigned long last_scan_completed;
494 491
495 u32 basic_rates; 492 u32 basic_rates;
@@ -580,8 +577,6 @@ struct ieee80211_if_mesh {
580 bool accepting_plinks; 577 bool accepting_plinks;
581 int num_gates; 578 int num_gates;
582 struct beacon_data __rcu *beacon; 579 struct beacon_data __rcu *beacon;
583 /* just protects beacon updates for now */
584 struct mutex mtx;
585 const u8 *ie; 580 const u8 *ie;
586 u8 ie_len; 581 u8 ie_len;
587 enum { 582 enum {
@@ -778,6 +773,26 @@ struct ieee80211_sub_if_data *vif_to_sdata(struct ieee80211_vif *p)
778 return container_of(p, struct ieee80211_sub_if_data, vif); 773 return container_of(p, struct ieee80211_sub_if_data, vif);
779} 774}
780 775
776static inline void sdata_lock(struct ieee80211_sub_if_data *sdata)
777 __acquires(&sdata->wdev.mtx)
778{
779 mutex_lock(&sdata->wdev.mtx);
780 __acquire(&sdata->wdev.mtx);
781}
782
783static inline void sdata_unlock(struct ieee80211_sub_if_data *sdata)
784 __releases(&sdata->wdev.mtx)
785{
786 mutex_unlock(&sdata->wdev.mtx);
787 __release(&sdata->wdev.mtx);
788}
789
790static inline void
791sdata_assert_lock(struct ieee80211_sub_if_data *sdata)
792{
793 lockdep_assert_held(&sdata->wdev.mtx);
794}
795
781static inline enum ieee80211_band 796static inline enum ieee80211_band
782ieee80211_get_sdata_band(struct ieee80211_sub_if_data *sdata) 797ieee80211_get_sdata_band(struct ieee80211_sub_if_data *sdata)
783{ 798{
@@ -1507,9 +1522,6 @@ static inline void ieee802_11_parse_elems(const u8 *start, size_t len,
1507 ieee802_11_parse_elems_crc(start, len, action, elems, 0, 0); 1522 ieee802_11_parse_elems_crc(start, len, action, elems, 0, 0);
1508} 1523}
1509 1524
1510u32 ieee80211_mandatory_rates(struct ieee80211_local *local,
1511 enum ieee80211_band band);
1512
1513void ieee80211_dynamic_ps_enable_work(struct work_struct *work); 1525void ieee80211_dynamic_ps_enable_work(struct work_struct *work);
1514void ieee80211_dynamic_ps_disable_work(struct work_struct *work); 1526void ieee80211_dynamic_ps_disable_work(struct work_struct *work);
1515void ieee80211_dynamic_ps_timer(unsigned long data); 1527void ieee80211_dynamic_ps_timer(unsigned long data);
diff --git a/net/mac80211/iface.c b/net/mac80211/iface.c
index 98d20c0f6fed..cc117591f678 100644
--- a/net/mac80211/iface.c
+++ b/net/mac80211/iface.c
@@ -159,7 +159,8 @@ static int ieee80211_change_mtu(struct net_device *dev, int new_mtu)
159 return 0; 159 return 0;
160} 160}
161 161
162static int ieee80211_verify_mac(struct ieee80211_sub_if_data *sdata, u8 *addr) 162static int ieee80211_verify_mac(struct ieee80211_sub_if_data *sdata, u8 *addr,
163 bool check_dup)
163{ 164{
164 struct ieee80211_local *local = sdata->local; 165 struct ieee80211_local *local = sdata->local;
165 struct ieee80211_sub_if_data *iter; 166 struct ieee80211_sub_if_data *iter;
@@ -180,13 +181,16 @@ static int ieee80211_verify_mac(struct ieee80211_sub_if_data *sdata, u8 *addr)
180 ((u64)m[2] << 3*8) | ((u64)m[3] << 2*8) | 181 ((u64)m[2] << 3*8) | ((u64)m[3] << 2*8) |
181 ((u64)m[4] << 1*8) | ((u64)m[5] << 0*8); 182 ((u64)m[4] << 1*8) | ((u64)m[5] << 0*8);
182 183
184 if (!check_dup)
185 return ret;
183 186
184 mutex_lock(&local->iflist_mtx); 187 mutex_lock(&local->iflist_mtx);
185 list_for_each_entry(iter, &local->interfaces, list) { 188 list_for_each_entry(iter, &local->interfaces, list) {
186 if (iter == sdata) 189 if (iter == sdata)
187 continue; 190 continue;
188 191
189 if (iter->vif.type == NL80211_IFTYPE_MONITOR) 192 if (iter->vif.type == NL80211_IFTYPE_MONITOR &&
193 !(iter->u.mntr_flags & MONITOR_FLAG_ACTIVE))
190 continue; 194 continue;
191 195
192 m = iter->vif.addr; 196 m = iter->vif.addr;
@@ -208,12 +212,17 @@ static int ieee80211_change_mac(struct net_device *dev, void *addr)
208{ 212{
209 struct ieee80211_sub_if_data *sdata = IEEE80211_DEV_TO_SUB_IF(dev); 213 struct ieee80211_sub_if_data *sdata = IEEE80211_DEV_TO_SUB_IF(dev);
210 struct sockaddr *sa = addr; 214 struct sockaddr *sa = addr;
215 bool check_dup = true;
211 int ret; 216 int ret;
212 217
213 if (ieee80211_sdata_running(sdata)) 218 if (ieee80211_sdata_running(sdata))
214 return -EBUSY; 219 return -EBUSY;
215 220
216 ret = ieee80211_verify_mac(sdata, sa->sa_data); 221 if (sdata->vif.type == NL80211_IFTYPE_MONITOR &&
222 !(sdata->u.mntr_flags & MONITOR_FLAG_ACTIVE))
223 check_dup = false;
224
225 ret = ieee80211_verify_mac(sdata, sa->sa_data, check_dup);
217 if (ret) 226 if (ret)
218 return ret; 227 return ret;
219 228
@@ -545,7 +554,11 @@ int ieee80211_do_open(struct wireless_dev *wdev, bool coming_up)
545 break; 554 break;
546 } 555 }
547 556
548 if (local->monitors == 0 && local->open_count == 0) { 557 if (sdata->u.mntr_flags & MONITOR_FLAG_ACTIVE) {
558 res = drv_add_interface(local, sdata);
559 if (res)
560 goto err_stop;
561 } else if (local->monitors == 0 && local->open_count == 0) {
549 res = ieee80211_add_virtual_monitor(local); 562 res = ieee80211_add_virtual_monitor(local);
550 if (res) 563 if (res)
551 goto err_stop; 564 goto err_stop;
@@ -923,7 +936,11 @@ static void ieee80211_do_stop(struct ieee80211_sub_if_data *sdata,
923 mutex_lock(&local->mtx); 936 mutex_lock(&local->mtx);
924 ieee80211_recalc_idle(local); 937 ieee80211_recalc_idle(local);
925 mutex_unlock(&local->mtx); 938 mutex_unlock(&local->mtx);
926 break; 939
940 if (!(sdata->u.mntr_flags & MONITOR_FLAG_ACTIVE))
941 break;
942
943 /* fall through */
927 default: 944 default:
928 if (going_down) 945 if (going_down)
929 drv_remove_interface(local, sdata); 946 drv_remove_interface(local, sdata);
@@ -1072,7 +1089,7 @@ static const struct net_device_ops ieee80211_monitorif_ops = {
1072 .ndo_start_xmit = ieee80211_monitor_start_xmit, 1089 .ndo_start_xmit = ieee80211_monitor_start_xmit,
1073 .ndo_set_rx_mode = ieee80211_set_multicast_list, 1090 .ndo_set_rx_mode = ieee80211_set_multicast_list,
1074 .ndo_change_mtu = ieee80211_change_mtu, 1091 .ndo_change_mtu = ieee80211_change_mtu,
1075 .ndo_set_mac_address = eth_mac_addr, 1092 .ndo_set_mac_address = ieee80211_change_mac,
1076 .ndo_select_queue = ieee80211_monitor_select_queue, 1093 .ndo_select_queue = ieee80211_monitor_select_queue,
1077}; 1094};
1078 1095
@@ -1747,10 +1764,9 @@ void ieee80211_remove_interfaces(struct ieee80211_local *local)
1747} 1764}
1748 1765
1749static int netdev_notify(struct notifier_block *nb, 1766static int netdev_notify(struct notifier_block *nb,
1750 unsigned long state, 1767 unsigned long state, void *ptr)
1751 void *ndev)
1752{ 1768{
1753 struct net_device *dev = ndev; 1769 struct net_device *dev = netdev_notifier_info_to_dev(ptr);
1754 struct ieee80211_sub_if_data *sdata; 1770 struct ieee80211_sub_if_data *sdata;
1755 1771
1756 if (state != NETDEV_CHANGENAME) 1772 if (state != NETDEV_CHANGENAME)
diff --git a/net/mac80211/key.c b/net/mac80211/key.c
index 67059b88fea5..e39cc91d0cf1 100644
--- a/net/mac80211/key.c
+++ b/net/mac80211/key.c
@@ -335,12 +335,12 @@ struct ieee80211_key *ieee80211_key_alloc(u32 cipher, int idx, size_t key_len,
335 switch (cipher) { 335 switch (cipher) {
336 case WLAN_CIPHER_SUITE_WEP40: 336 case WLAN_CIPHER_SUITE_WEP40:
337 case WLAN_CIPHER_SUITE_WEP104: 337 case WLAN_CIPHER_SUITE_WEP104:
338 key->conf.iv_len = WEP_IV_LEN; 338 key->conf.iv_len = IEEE80211_WEP_IV_LEN;
339 key->conf.icv_len = WEP_ICV_LEN; 339 key->conf.icv_len = IEEE80211_WEP_ICV_LEN;
340 break; 340 break;
341 case WLAN_CIPHER_SUITE_TKIP: 341 case WLAN_CIPHER_SUITE_TKIP:
342 key->conf.iv_len = TKIP_IV_LEN; 342 key->conf.iv_len = IEEE80211_TKIP_IV_LEN;
343 key->conf.icv_len = TKIP_ICV_LEN; 343 key->conf.icv_len = IEEE80211_TKIP_ICV_LEN;
344 if (seq) { 344 if (seq) {
345 for (i = 0; i < IEEE80211_NUM_TIDS; i++) { 345 for (i = 0; i < IEEE80211_NUM_TIDS; i++) {
346 key->u.tkip.rx[i].iv32 = 346 key->u.tkip.rx[i].iv32 =
@@ -352,13 +352,13 @@ struct ieee80211_key *ieee80211_key_alloc(u32 cipher, int idx, size_t key_len,
352 spin_lock_init(&key->u.tkip.txlock); 352 spin_lock_init(&key->u.tkip.txlock);
353 break; 353 break;
354 case WLAN_CIPHER_SUITE_CCMP: 354 case WLAN_CIPHER_SUITE_CCMP:
355 key->conf.iv_len = CCMP_HDR_LEN; 355 key->conf.iv_len = IEEE80211_CCMP_HDR_LEN;
356 key->conf.icv_len = CCMP_MIC_LEN; 356 key->conf.icv_len = IEEE80211_CCMP_MIC_LEN;
357 if (seq) { 357 if (seq) {
358 for (i = 0; i < IEEE80211_NUM_TIDS + 1; i++) 358 for (i = 0; i < IEEE80211_NUM_TIDS + 1; i++)
359 for (j = 0; j < CCMP_PN_LEN; j++) 359 for (j = 0; j < IEEE80211_CCMP_PN_LEN; j++)
360 key->u.ccmp.rx_pn[i][j] = 360 key->u.ccmp.rx_pn[i][j] =
361 seq[CCMP_PN_LEN - j - 1]; 361 seq[IEEE80211_CCMP_PN_LEN - j - 1];
362 } 362 }
363 /* 363 /*
364 * Initialize AES key state here as an optimization so that 364 * Initialize AES key state here as an optimization so that
@@ -375,9 +375,9 @@ struct ieee80211_key *ieee80211_key_alloc(u32 cipher, int idx, size_t key_len,
375 key->conf.iv_len = 0; 375 key->conf.iv_len = 0;
376 key->conf.icv_len = sizeof(struct ieee80211_mmie); 376 key->conf.icv_len = sizeof(struct ieee80211_mmie);
377 if (seq) 377 if (seq)
378 for (j = 0; j < CMAC_PN_LEN; j++) 378 for (j = 0; j < IEEE80211_CMAC_PN_LEN; j++)
379 key->u.aes_cmac.rx_pn[j] = 379 key->u.aes_cmac.rx_pn[j] =
380 seq[CMAC_PN_LEN - j - 1]; 380 seq[IEEE80211_CMAC_PN_LEN - j - 1];
381 /* 381 /*
382 * Initialize AES key state here as an optimization so that 382 * Initialize AES key state here as an optimization so that
383 * it does not need to be initialized for every packet. 383 * it does not need to be initialized for every packet.
@@ -740,13 +740,13 @@ void ieee80211_get_key_rx_seq(struct ieee80211_key_conf *keyconf,
740 pn = key->u.ccmp.rx_pn[IEEE80211_NUM_TIDS]; 740 pn = key->u.ccmp.rx_pn[IEEE80211_NUM_TIDS];
741 else 741 else
742 pn = key->u.ccmp.rx_pn[tid]; 742 pn = key->u.ccmp.rx_pn[tid];
743 memcpy(seq->ccmp.pn, pn, CCMP_PN_LEN); 743 memcpy(seq->ccmp.pn, pn, IEEE80211_CCMP_PN_LEN);
744 break; 744 break;
745 case WLAN_CIPHER_SUITE_AES_CMAC: 745 case WLAN_CIPHER_SUITE_AES_CMAC:
746 if (WARN_ON(tid != 0)) 746 if (WARN_ON(tid != 0))
747 return; 747 return;
748 pn = key->u.aes_cmac.rx_pn; 748 pn = key->u.aes_cmac.rx_pn;
749 memcpy(seq->aes_cmac.pn, pn, CMAC_PN_LEN); 749 memcpy(seq->aes_cmac.pn, pn, IEEE80211_CMAC_PN_LEN);
750 break; 750 break;
751 } 751 }
752} 752}
diff --git a/net/mac80211/key.h b/net/mac80211/key.h
index e8de3e6d7804..036d57e76a5e 100644
--- a/net/mac80211/key.h
+++ b/net/mac80211/key.h
@@ -19,17 +19,6 @@
19#define NUM_DEFAULT_KEYS 4 19#define NUM_DEFAULT_KEYS 4
20#define NUM_DEFAULT_MGMT_KEYS 2 20#define NUM_DEFAULT_MGMT_KEYS 2
21 21
22#define WEP_IV_LEN 4
23#define WEP_ICV_LEN 4
24#define ALG_CCMP_KEY_LEN 16
25#define CCMP_HDR_LEN 8
26#define CCMP_MIC_LEN 8
27#define CCMP_TK_LEN 16
28#define CCMP_PN_LEN 6
29#define TKIP_IV_LEN 8
30#define TKIP_ICV_LEN 4
31#define CMAC_PN_LEN 6
32
33struct ieee80211_local; 22struct ieee80211_local;
34struct ieee80211_sub_if_data; 23struct ieee80211_sub_if_data;
35struct sta_info; 24struct sta_info;
@@ -93,13 +82,13 @@ struct ieee80211_key {
93 * frames and the last counter is used with Robust 82 * frames and the last counter is used with Robust
94 * Management frames. 83 * Management frames.
95 */ 84 */
96 u8 rx_pn[IEEE80211_NUM_TIDS + 1][CCMP_PN_LEN]; 85 u8 rx_pn[IEEE80211_NUM_TIDS + 1][IEEE80211_CCMP_PN_LEN];
97 struct crypto_cipher *tfm; 86 struct crypto_cipher *tfm;
98 u32 replays; /* dot11RSNAStatsCCMPReplays */ 87 u32 replays; /* dot11RSNAStatsCCMPReplays */
99 } ccmp; 88 } ccmp;
100 struct { 89 struct {
101 atomic64_t tx_pn; 90 atomic64_t tx_pn;
102 u8 rx_pn[CMAC_PN_LEN]; 91 u8 rx_pn[IEEE80211_CMAC_PN_LEN];
103 struct crypto_cipher *tfm; 92 struct crypto_cipher *tfm;
104 u32 replays; /* dot11RSNAStatsCMACReplays */ 93 u32 replays; /* dot11RSNAStatsCMACReplays */
105 u32 icverrors; /* dot11RSNAStatsCMACICVErrors */ 94 u32 icverrors; /* dot11RSNAStatsCMACICVErrors */
diff --git a/net/mac80211/main.c b/net/mac80211/main.c
index 8a7bfc47d577..1998f1475267 100644
--- a/net/mac80211/main.c
+++ b/net/mac80211/main.c
@@ -331,7 +331,7 @@ static int ieee80211_ifa_changed(struct notifier_block *nb,
331 return NOTIFY_DONE; 331 return NOTIFY_DONE;
332 332
333 ifmgd = &sdata->u.mgd; 333 ifmgd = &sdata->u.mgd;
334 mutex_lock(&ifmgd->mtx); 334 sdata_lock(sdata);
335 335
336 /* Copy the addresses to the bss_conf list */ 336 /* Copy the addresses to the bss_conf list */
337 ifa = idev->ifa_list; 337 ifa = idev->ifa_list;
@@ -349,7 +349,7 @@ static int ieee80211_ifa_changed(struct notifier_block *nb,
349 ieee80211_bss_info_change_notify(sdata, 349 ieee80211_bss_info_change_notify(sdata,
350 BSS_CHANGED_ARP_FILTER); 350 BSS_CHANGED_ARP_FILTER);
351 351
352 mutex_unlock(&ifmgd->mtx); 352 sdata_unlock(sdata);
353 353
354 return NOTIFY_DONE; 354 return NOTIFY_DONE;
355} 355}
diff --git a/net/mac80211/mesh.c b/net/mac80211/mesh.c
index 6952760881c8..b3d1fdd46368 100644
--- a/net/mac80211/mesh.c
+++ b/net/mac80211/mesh.c
@@ -161,8 +161,11 @@ void mesh_sta_cleanup(struct sta_info *sta)
161 del_timer_sync(&sta->plink_timer); 161 del_timer_sync(&sta->plink_timer);
162 } 162 }
163 163
164 if (changed) 164 if (changed) {
165 sdata_lock(sdata);
165 ieee80211_mbss_info_change_notify(sdata, changed); 166 ieee80211_mbss_info_change_notify(sdata, changed);
167 sdata_unlock(sdata);
168 }
166} 169}
167 170
168int mesh_rmc_init(struct ieee80211_sub_if_data *sdata) 171int mesh_rmc_init(struct ieee80211_sub_if_data *sdata)
@@ -577,7 +580,9 @@ static void ieee80211_mesh_housekeeping(struct ieee80211_sub_if_data *sdata)
577 mesh_path_expire(sdata); 580 mesh_path_expire(sdata);
578 581
579 changed = mesh_accept_plinks_update(sdata); 582 changed = mesh_accept_plinks_update(sdata);
583 sdata_lock(sdata);
580 ieee80211_mbss_info_change_notify(sdata, changed); 584 ieee80211_mbss_info_change_notify(sdata, changed);
585 sdata_unlock(sdata);
581 586
582 mod_timer(&ifmsh->housekeeping_timer, 587 mod_timer(&ifmsh->housekeeping_timer,
583 round_jiffies(jiffies + 588 round_jiffies(jiffies +
@@ -697,25 +702,21 @@ out_free:
697} 702}
698 703
699static int 704static int
700ieee80211_mesh_rebuild_beacon(struct ieee80211_if_mesh *ifmsh) 705ieee80211_mesh_rebuild_beacon(struct ieee80211_sub_if_data *sdata)
701{ 706{
702 struct beacon_data *old_bcn; 707 struct beacon_data *old_bcn;
703 int ret; 708 int ret;
704 709
705 mutex_lock(&ifmsh->mtx); 710 old_bcn = rcu_dereference_protected(sdata->u.mesh.beacon,
706 711 lockdep_is_held(&sdata->wdev.mtx));
707 old_bcn = rcu_dereference_protected(ifmsh->beacon, 712 ret = ieee80211_mesh_build_beacon(&sdata->u.mesh);
708 lockdep_is_held(&ifmsh->mtx));
709 ret = ieee80211_mesh_build_beacon(ifmsh);
710 if (ret) 713 if (ret)
711 /* just reuse old beacon */ 714 /* just reuse old beacon */
712 goto out; 715 return ret;
713 716
714 if (old_bcn) 717 if (old_bcn)
715 kfree_rcu(old_bcn, rcu_head); 718 kfree_rcu(old_bcn, rcu_head);
716out: 719 return 0;
717 mutex_unlock(&ifmsh->mtx);
718 return ret;
719} 720}
720 721
721void ieee80211_mbss_info_change_notify(struct ieee80211_sub_if_data *sdata, 722void ieee80211_mbss_info_change_notify(struct ieee80211_sub_if_data *sdata,
@@ -726,7 +727,7 @@ void ieee80211_mbss_info_change_notify(struct ieee80211_sub_if_data *sdata,
726 BSS_CHANGED_HT | 727 BSS_CHANGED_HT |
727 BSS_CHANGED_BASIC_RATES | 728 BSS_CHANGED_BASIC_RATES |
728 BSS_CHANGED_BEACON_INT))) 729 BSS_CHANGED_BEACON_INT)))
729 if (ieee80211_mesh_rebuild_beacon(&sdata->u.mesh)) 730 if (ieee80211_mesh_rebuild_beacon(sdata))
730 return; 731 return;
731 ieee80211_bss_info_change_notify(sdata, changed); 732 ieee80211_bss_info_change_notify(sdata, changed);
732} 733}
@@ -741,6 +742,8 @@ int ieee80211_start_mesh(struct ieee80211_sub_if_data *sdata)
741 BSS_CHANGED_BASIC_RATES | 742 BSS_CHANGED_BASIC_RATES |
742 BSS_CHANGED_BEACON_INT; 743 BSS_CHANGED_BEACON_INT;
743 enum ieee80211_band band = ieee80211_get_sdata_band(sdata); 744 enum ieee80211_band band = ieee80211_get_sdata_band(sdata);
745 struct ieee80211_supported_band *sband =
746 sdata->local->hw.wiphy->bands[band];
744 747
745 local->fif_other_bss++; 748 local->fif_other_bss++;
746 /* mesh ifaces must set allmulti to forward mcast traffic */ 749 /* mesh ifaces must set allmulti to forward mcast traffic */
@@ -748,7 +751,6 @@ int ieee80211_start_mesh(struct ieee80211_sub_if_data *sdata)
748 ieee80211_configure_filter(local); 751 ieee80211_configure_filter(local);
749 752
750 ifmsh->mesh_cc_id = 0; /* Disabled */ 753 ifmsh->mesh_cc_id = 0; /* Disabled */
751 ifmsh->mesh_auth_id = 0; /* Disabled */
752 /* register sync ops from extensible synchronization framework */ 754 /* register sync ops from extensible synchronization framework */
753 ifmsh->sync_ops = ieee80211_mesh_sync_ops_get(ifmsh->mesh_sp_id); 755 ifmsh->sync_ops = ieee80211_mesh_sync_ops_get(ifmsh->mesh_sp_id);
754 ifmsh->adjusting_tbtt = false; 756 ifmsh->adjusting_tbtt = false;
@@ -759,8 +761,7 @@ int ieee80211_start_mesh(struct ieee80211_sub_if_data *sdata)
759 sdata->vif.bss_conf.ht_operation_mode = 761 sdata->vif.bss_conf.ht_operation_mode =
760 ifmsh->mshcfg.ht_opmode; 762 ifmsh->mshcfg.ht_opmode;
761 sdata->vif.bss_conf.enable_beacon = true; 763 sdata->vif.bss_conf.enable_beacon = true;
762 sdata->vif.bss_conf.basic_rates = 764 sdata->vif.bss_conf.basic_rates = ieee80211_mandatory_rates(sband);
763 ieee80211_mandatory_rates(local, band);
764 765
765 changed |= ieee80211_mps_local_status_update(sdata); 766 changed |= ieee80211_mps_local_status_update(sdata);
766 767
@@ -788,12 +789,12 @@ void ieee80211_stop_mesh(struct ieee80211_sub_if_data *sdata)
788 sdata->vif.bss_conf.enable_beacon = false; 789 sdata->vif.bss_conf.enable_beacon = false;
789 clear_bit(SDATA_STATE_OFFCHANNEL_BEACON_STOPPED, &sdata->state); 790 clear_bit(SDATA_STATE_OFFCHANNEL_BEACON_STOPPED, &sdata->state);
790 ieee80211_bss_info_change_notify(sdata, BSS_CHANGED_BEACON_ENABLED); 791 ieee80211_bss_info_change_notify(sdata, BSS_CHANGED_BEACON_ENABLED);
791 mutex_lock(&ifmsh->mtx); 792 sdata_lock(sdata);
792 bcn = rcu_dereference_protected(ifmsh->beacon, 793 bcn = rcu_dereference_protected(ifmsh->beacon,
793 lockdep_is_held(&ifmsh->mtx)); 794 lockdep_is_held(&sdata->wdev.mtx));
794 rcu_assign_pointer(ifmsh->beacon, NULL); 795 rcu_assign_pointer(ifmsh->beacon, NULL);
795 kfree_rcu(bcn, rcu_head); 796 kfree_rcu(bcn, rcu_head);
796 mutex_unlock(&ifmsh->mtx); 797 sdata_unlock(sdata);
797 798
798 /* flush STAs and mpaths on this iface */ 799 /* flush STAs and mpaths on this iface */
799 sta_info_flush(sdata); 800 sta_info_flush(sdata);
@@ -1041,7 +1042,6 @@ void ieee80211_mesh_init_sdata(struct ieee80211_sub_if_data *sdata)
1041 spin_lock_init(&ifmsh->mesh_preq_queue_lock); 1042 spin_lock_init(&ifmsh->mesh_preq_queue_lock);
1042 spin_lock_init(&ifmsh->sync_offset_lock); 1043 spin_lock_init(&ifmsh->sync_offset_lock);
1043 RCU_INIT_POINTER(ifmsh->beacon, NULL); 1044 RCU_INIT_POINTER(ifmsh->beacon, NULL);
1044 mutex_init(&ifmsh->mtx);
1045 1045
1046 sdata->vif.bss_conf.bssid = zero_addr; 1046 sdata->vif.bss_conf.bssid = zero_addr;
1047} 1047}
diff --git a/net/mac80211/mesh_plink.c b/net/mac80211/mesh_plink.c
index 09bebed99416..6c4da99bc4fb 100644
--- a/net/mac80211/mesh_plink.c
+++ b/net/mac80211/mesh_plink.c
@@ -517,7 +517,9 @@ void mesh_neighbour_update(struct ieee80211_sub_if_data *sdata,
517 ieee80211_mps_frame_release(sta, elems); 517 ieee80211_mps_frame_release(sta, elems);
518out: 518out:
519 rcu_read_unlock(); 519 rcu_read_unlock();
520 sdata_lock(sdata);
520 ieee80211_mbss_info_change_notify(sdata, changed); 521 ieee80211_mbss_info_change_notify(sdata, changed);
522 sdata_unlock(sdata);
521} 523}
522 524
523static void mesh_plink_timer(unsigned long data) 525static void mesh_plink_timer(unsigned long data)
@@ -1068,6 +1070,9 @@ void mesh_rx_plink_frame(struct ieee80211_sub_if_data *sdata,
1068 1070
1069 rcu_read_unlock(); 1071 rcu_read_unlock();
1070 1072
1071 if (changed) 1073 if (changed) {
1074 sdata_lock(sdata);
1072 ieee80211_mbss_info_change_notify(sdata, changed); 1075 ieee80211_mbss_info_change_notify(sdata, changed);
1076 sdata_unlock(sdata);
1077 }
1073} 1078}
diff --git a/net/mac80211/mlme.c b/net/mac80211/mlme.c
index 741448b30825..118540b16729 100644
--- a/net/mac80211/mlme.c
+++ b/net/mac80211/mlme.c
@@ -91,41 +91,6 @@ MODULE_PARM_DESC(probe_wait_ms,
91#define IEEE80211_SIGNAL_AVE_MIN_COUNT 4 91#define IEEE80211_SIGNAL_AVE_MIN_COUNT 4
92 92
93/* 93/*
94 * All cfg80211 functions have to be called outside a locked
95 * section so that they can acquire a lock themselves... This
96 * is much simpler than queuing up things in cfg80211, but we
97 * do need some indirection for that here.
98 */
99enum rx_mgmt_action {
100 /* no action required */
101 RX_MGMT_NONE,
102
103 /* caller must call cfg80211_send_deauth() */
104 RX_MGMT_CFG80211_DEAUTH,
105
106 /* caller must call cfg80211_send_disassoc() */
107 RX_MGMT_CFG80211_DISASSOC,
108
109 /* caller must call cfg80211_send_rx_auth() */
110 RX_MGMT_CFG80211_RX_AUTH,
111
112 /* caller must call cfg80211_send_rx_assoc() */
113 RX_MGMT_CFG80211_RX_ASSOC,
114
115 /* caller must call cfg80211_send_assoc_timeout() */
116 RX_MGMT_CFG80211_ASSOC_TIMEOUT,
117
118 /* used when a processed beacon causes a deauth */
119 RX_MGMT_CFG80211_TX_DEAUTH,
120};
121
122/* utils */
123static inline void ASSERT_MGD_MTX(struct ieee80211_if_managed *ifmgd)
124{
125 lockdep_assert_held(&ifmgd->mtx);
126}
127
128/*
129 * We can have multiple work items (and connection probing) 94 * We can have multiple work items (and connection probing)
130 * scheduling this timer, but we need to take care to only 95 * scheduling this timer, but we need to take care to only
131 * reschedule it when it should fire _earlier_ than it was 96 * reschedule it when it should fire _earlier_ than it was
@@ -135,13 +100,14 @@ static inline void ASSERT_MGD_MTX(struct ieee80211_if_managed *ifmgd)
135 * has happened -- the work that runs from this timer will 100 * has happened -- the work that runs from this timer will
136 * do that. 101 * do that.
137 */ 102 */
138static void run_again(struct ieee80211_if_managed *ifmgd, unsigned long timeout) 103static void run_again(struct ieee80211_sub_if_data *sdata,
104 unsigned long timeout)
139{ 105{
140 ASSERT_MGD_MTX(ifmgd); 106 sdata_assert_lock(sdata);
141 107
142 if (!timer_pending(&ifmgd->timer) || 108 if (!timer_pending(&sdata->u.mgd.timer) ||
143 time_before(timeout, ifmgd->timer.expires)) 109 time_before(timeout, sdata->u.mgd.timer.expires))
144 mod_timer(&ifmgd->timer, timeout); 110 mod_timer(&sdata->u.mgd.timer, timeout);
145} 111}
146 112
147void ieee80211_sta_reset_beacon_monitor(struct ieee80211_sub_if_data *sdata) 113void ieee80211_sta_reset_beacon_monitor(struct ieee80211_sub_if_data *sdata)
@@ -652,7 +618,7 @@ static void ieee80211_send_assoc(struct ieee80211_sub_if_data *sdata)
652 struct ieee80211_channel *chan; 618 struct ieee80211_channel *chan;
653 u32 rates = 0; 619 u32 rates = 0;
654 620
655 lockdep_assert_held(&ifmgd->mtx); 621 sdata_assert_lock(sdata);
656 622
657 rcu_read_lock(); 623 rcu_read_lock();
658 chanctx_conf = rcu_dereference(sdata->vif.chanctx_conf); 624 chanctx_conf = rcu_dereference(sdata->vif.chanctx_conf);
@@ -962,7 +928,7 @@ static void ieee80211_chswitch_work(struct work_struct *work)
962 if (!ieee80211_sdata_running(sdata)) 928 if (!ieee80211_sdata_running(sdata))
963 return; 929 return;
964 930
965 mutex_lock(&ifmgd->mtx); 931 sdata_lock(sdata);
966 if (!ifmgd->associated) 932 if (!ifmgd->associated)
967 goto out; 933 goto out;
968 934
@@ -985,7 +951,7 @@ static void ieee80211_chswitch_work(struct work_struct *work)
985 IEEE80211_QUEUE_STOP_REASON_CSA); 951 IEEE80211_QUEUE_STOP_REASON_CSA);
986 out: 952 out:
987 ifmgd->flags &= ~IEEE80211_STA_CSA_RECEIVED; 953 ifmgd->flags &= ~IEEE80211_STA_CSA_RECEIVED;
988 mutex_unlock(&ifmgd->mtx); 954 sdata_unlock(sdata);
989} 955}
990 956
991void ieee80211_chswitch_done(struct ieee80211_vif *vif, bool success) 957void ieee80211_chswitch_done(struct ieee80211_vif *vif, bool success)
@@ -1036,7 +1002,7 @@ ieee80211_sta_process_chanswitch(struct ieee80211_sub_if_data *sdata,
1036 const struct ieee80211_ht_operation *ht_oper; 1002 const struct ieee80211_ht_operation *ht_oper;
1037 int secondary_channel_offset = -1; 1003 int secondary_channel_offset = -1;
1038 1004
1039 ASSERT_MGD_MTX(ifmgd); 1005 sdata_assert_lock(sdata);
1040 1006
1041 if (!cbss) 1007 if (!cbss)
1042 return; 1008 return;
@@ -1390,6 +1356,9 @@ static bool ieee80211_powersave_allowed(struct ieee80211_sub_if_data *sdata)
1390 IEEE80211_STA_CONNECTION_POLL)) 1356 IEEE80211_STA_CONNECTION_POLL))
1391 return false; 1357 return false;
1392 1358
1359 if (!sdata->vif.bss_conf.dtim_period)
1360 return false;
1361
1393 rcu_read_lock(); 1362 rcu_read_lock();
1394 sta = sta_info_get(sdata, mgd->bssid); 1363 sta = sta_info_get(sdata, mgd->bssid);
1395 if (sta) 1364 if (sta)
@@ -1842,7 +1811,7 @@ static void ieee80211_set_disassoc(struct ieee80211_sub_if_data *sdata,
1842 struct ieee80211_local *local = sdata->local; 1811 struct ieee80211_local *local = sdata->local;
1843 u32 changed = 0; 1812 u32 changed = 0;
1844 1813
1845 ASSERT_MGD_MTX(ifmgd); 1814 sdata_assert_lock(sdata);
1846 1815
1847 if (WARN_ON_ONCE(tx && !frame_buf)) 1816 if (WARN_ON_ONCE(tx && !frame_buf))
1848 return; 1817 return;
@@ -2051,7 +2020,7 @@ static void ieee80211_mgd_probe_ap_send(struct ieee80211_sub_if_data *sdata)
2051 } 2020 }
2052 2021
2053 ifmgd->probe_timeout = jiffies + msecs_to_jiffies(probe_wait_ms); 2022 ifmgd->probe_timeout = jiffies + msecs_to_jiffies(probe_wait_ms);
2054 run_again(ifmgd, ifmgd->probe_timeout); 2023 run_again(sdata, ifmgd->probe_timeout);
2055 if (sdata->local->hw.flags & IEEE80211_HW_REPORTS_TX_ACK_STATUS) 2024 if (sdata->local->hw.flags & IEEE80211_HW_REPORTS_TX_ACK_STATUS)
2056 ieee80211_flush_queues(sdata->local, sdata); 2025 ieee80211_flush_queues(sdata->local, sdata);
2057} 2026}
@@ -2065,7 +2034,7 @@ static void ieee80211_mgd_probe_ap(struct ieee80211_sub_if_data *sdata,
2065 if (!ieee80211_sdata_running(sdata)) 2034 if (!ieee80211_sdata_running(sdata))
2066 return; 2035 return;
2067 2036
2068 mutex_lock(&ifmgd->mtx); 2037 sdata_lock(sdata);
2069 2038
2070 if (!ifmgd->associated) 2039 if (!ifmgd->associated)
2071 goto out; 2040 goto out;
@@ -2119,7 +2088,7 @@ static void ieee80211_mgd_probe_ap(struct ieee80211_sub_if_data *sdata,
2119 ifmgd->probe_send_count = 0; 2088 ifmgd->probe_send_count = 0;
2120 ieee80211_mgd_probe_ap_send(sdata); 2089 ieee80211_mgd_probe_ap_send(sdata);
2121 out: 2090 out:
2122 mutex_unlock(&ifmgd->mtx); 2091 sdata_unlock(sdata);
2123} 2092}
2124 2093
2125struct sk_buff *ieee80211_ap_probereq_get(struct ieee80211_hw *hw, 2094struct sk_buff *ieee80211_ap_probereq_get(struct ieee80211_hw *hw,
@@ -2135,7 +2104,7 @@ struct sk_buff *ieee80211_ap_probereq_get(struct ieee80211_hw *hw,
2135 if (WARN_ON(sdata->vif.type != NL80211_IFTYPE_STATION)) 2104 if (WARN_ON(sdata->vif.type != NL80211_IFTYPE_STATION))
2136 return NULL; 2105 return NULL;
2137 2106
2138 ASSERT_MGD_MTX(ifmgd); 2107 sdata_assert_lock(sdata);
2139 2108
2140 if (ifmgd->associated) 2109 if (ifmgd->associated)
2141 cbss = ifmgd->associated; 2110 cbss = ifmgd->associated;
@@ -2168,9 +2137,9 @@ static void __ieee80211_disconnect(struct ieee80211_sub_if_data *sdata)
2168 struct ieee80211_if_managed *ifmgd = &sdata->u.mgd; 2137 struct ieee80211_if_managed *ifmgd = &sdata->u.mgd;
2169 u8 frame_buf[IEEE80211_DEAUTH_FRAME_LEN]; 2138 u8 frame_buf[IEEE80211_DEAUTH_FRAME_LEN];
2170 2139
2171 mutex_lock(&ifmgd->mtx); 2140 sdata_lock(sdata);
2172 if (!ifmgd->associated) { 2141 if (!ifmgd->associated) {
2173 mutex_unlock(&ifmgd->mtx); 2142 sdata_unlock(sdata);
2174 return; 2143 return;
2175 } 2144 }
2176 2145
@@ -2181,13 +2150,9 @@ static void __ieee80211_disconnect(struct ieee80211_sub_if_data *sdata)
2181 ieee80211_wake_queues_by_reason(&sdata->local->hw, 2150 ieee80211_wake_queues_by_reason(&sdata->local->hw,
2182 IEEE80211_MAX_QUEUE_MAP, 2151 IEEE80211_MAX_QUEUE_MAP,
2183 IEEE80211_QUEUE_STOP_REASON_CSA); 2152 IEEE80211_QUEUE_STOP_REASON_CSA);
2184 mutex_unlock(&ifmgd->mtx);
2185 2153
2186 /*
2187 * must be outside lock due to cfg80211,
2188 * but that's not a problem.
2189 */
2190 cfg80211_send_deauth(sdata->dev, frame_buf, IEEE80211_DEAUTH_FRAME_LEN); 2154 cfg80211_send_deauth(sdata->dev, frame_buf, IEEE80211_DEAUTH_FRAME_LEN);
2155 sdata_unlock(sdata);
2191} 2156}
2192 2157
2193static void ieee80211_beacon_connection_loss_work(struct work_struct *work) 2158static void ieee80211_beacon_connection_loss_work(struct work_struct *work)
@@ -2254,7 +2219,7 @@ static void ieee80211_destroy_auth_data(struct ieee80211_sub_if_data *sdata,
2254{ 2219{
2255 struct ieee80211_mgd_auth_data *auth_data = sdata->u.mgd.auth_data; 2220 struct ieee80211_mgd_auth_data *auth_data = sdata->u.mgd.auth_data;
2256 2221
2257 lockdep_assert_held(&sdata->u.mgd.mtx); 2222 sdata_assert_lock(sdata);
2258 2223
2259 if (!assoc) { 2224 if (!assoc) {
2260 sta_info_destroy_addr(sdata, auth_data->bss->bssid); 2225 sta_info_destroy_addr(sdata, auth_data->bss->bssid);
@@ -2295,27 +2260,26 @@ static void ieee80211_auth_challenge(struct ieee80211_sub_if_data *sdata,
2295 auth_data->key_idx, tx_flags); 2260 auth_data->key_idx, tx_flags);
2296} 2261}
2297 2262
2298static enum rx_mgmt_action __must_check 2263static void ieee80211_rx_mgmt_auth(struct ieee80211_sub_if_data *sdata,
2299ieee80211_rx_mgmt_auth(struct ieee80211_sub_if_data *sdata, 2264 struct ieee80211_mgmt *mgmt, size_t len)
2300 struct ieee80211_mgmt *mgmt, size_t len)
2301{ 2265{
2302 struct ieee80211_if_managed *ifmgd = &sdata->u.mgd; 2266 struct ieee80211_if_managed *ifmgd = &sdata->u.mgd;
2303 u8 bssid[ETH_ALEN]; 2267 u8 bssid[ETH_ALEN];
2304 u16 auth_alg, auth_transaction, status_code; 2268 u16 auth_alg, auth_transaction, status_code;
2305 struct sta_info *sta; 2269 struct sta_info *sta;
2306 2270
2307 lockdep_assert_held(&ifmgd->mtx); 2271 sdata_assert_lock(sdata);
2308 2272
2309 if (len < 24 + 6) 2273 if (len < 24 + 6)
2310 return RX_MGMT_NONE; 2274 return;
2311 2275
2312 if (!ifmgd->auth_data || ifmgd->auth_data->done) 2276 if (!ifmgd->auth_data || ifmgd->auth_data->done)
2313 return RX_MGMT_NONE; 2277 return;
2314 2278
2315 memcpy(bssid, ifmgd->auth_data->bss->bssid, ETH_ALEN); 2279 memcpy(bssid, ifmgd->auth_data->bss->bssid, ETH_ALEN);
2316 2280
2317 if (!ether_addr_equal(bssid, mgmt->bssid)) 2281 if (!ether_addr_equal(bssid, mgmt->bssid))
2318 return RX_MGMT_NONE; 2282 return;
2319 2283
2320 auth_alg = le16_to_cpu(mgmt->u.auth.auth_alg); 2284 auth_alg = le16_to_cpu(mgmt->u.auth.auth_alg);
2321 auth_transaction = le16_to_cpu(mgmt->u.auth.auth_transaction); 2285 auth_transaction = le16_to_cpu(mgmt->u.auth.auth_transaction);
@@ -2327,14 +2291,15 @@ ieee80211_rx_mgmt_auth(struct ieee80211_sub_if_data *sdata,
2327 mgmt->sa, auth_alg, ifmgd->auth_data->algorithm, 2291 mgmt->sa, auth_alg, ifmgd->auth_data->algorithm,
2328 auth_transaction, 2292 auth_transaction,
2329 ifmgd->auth_data->expected_transaction); 2293 ifmgd->auth_data->expected_transaction);
2330 return RX_MGMT_NONE; 2294 return;
2331 } 2295 }
2332 2296
2333 if (status_code != WLAN_STATUS_SUCCESS) { 2297 if (status_code != WLAN_STATUS_SUCCESS) {
2334 sdata_info(sdata, "%pM denied authentication (status %d)\n", 2298 sdata_info(sdata, "%pM denied authentication (status %d)\n",
2335 mgmt->sa, status_code); 2299 mgmt->sa, status_code);
2336 ieee80211_destroy_auth_data(sdata, false); 2300 ieee80211_destroy_auth_data(sdata, false);
2337 return RX_MGMT_CFG80211_RX_AUTH; 2301 cfg80211_send_rx_auth(sdata->dev, (u8 *)mgmt, len);
2302 return;
2338 } 2303 }
2339 2304
2340 switch (ifmgd->auth_data->algorithm) { 2305 switch (ifmgd->auth_data->algorithm) {
@@ -2347,20 +2312,20 @@ ieee80211_rx_mgmt_auth(struct ieee80211_sub_if_data *sdata,
2347 if (ifmgd->auth_data->expected_transaction != 4) { 2312 if (ifmgd->auth_data->expected_transaction != 4) {
2348 ieee80211_auth_challenge(sdata, mgmt, len); 2313 ieee80211_auth_challenge(sdata, mgmt, len);
2349 /* need another frame */ 2314 /* need another frame */
2350 return RX_MGMT_NONE; 2315 return;
2351 } 2316 }
2352 break; 2317 break;
2353 default: 2318 default:
2354 WARN_ONCE(1, "invalid auth alg %d", 2319 WARN_ONCE(1, "invalid auth alg %d",
2355 ifmgd->auth_data->algorithm); 2320 ifmgd->auth_data->algorithm);
2356 return RX_MGMT_NONE; 2321 return;
2357 } 2322 }
2358 2323
2359 sdata_info(sdata, "authenticated\n"); 2324 sdata_info(sdata, "authenticated\n");
2360 ifmgd->auth_data->done = true; 2325 ifmgd->auth_data->done = true;
2361 ifmgd->auth_data->timeout = jiffies + IEEE80211_AUTH_WAIT_ASSOC; 2326 ifmgd->auth_data->timeout = jiffies + IEEE80211_AUTH_WAIT_ASSOC;
2362 ifmgd->auth_data->timeout_started = true; 2327 ifmgd->auth_data->timeout_started = true;
2363 run_again(ifmgd, ifmgd->auth_data->timeout); 2328 run_again(sdata, ifmgd->auth_data->timeout);
2364 2329
2365 if (ifmgd->auth_data->algorithm == WLAN_AUTH_SAE && 2330 if (ifmgd->auth_data->algorithm == WLAN_AUTH_SAE &&
2366 ifmgd->auth_data->expected_transaction != 2) { 2331 ifmgd->auth_data->expected_transaction != 2) {
@@ -2368,7 +2333,8 @@ ieee80211_rx_mgmt_auth(struct ieee80211_sub_if_data *sdata,
2368 * Report auth frame to user space for processing since another 2333 * Report auth frame to user space for processing since another
2369 * round of Authentication frames is still needed. 2334 * round of Authentication frames is still needed.
2370 */ 2335 */
2371 return RX_MGMT_CFG80211_RX_AUTH; 2336 cfg80211_send_rx_auth(sdata->dev, (u8 *)mgmt, len);
2337 return;
2372 } 2338 }
2373 2339
2374 /* move station state to auth */ 2340 /* move station state to auth */
@@ -2384,30 +2350,29 @@ ieee80211_rx_mgmt_auth(struct ieee80211_sub_if_data *sdata,
2384 } 2350 }
2385 mutex_unlock(&sdata->local->sta_mtx); 2351 mutex_unlock(&sdata->local->sta_mtx);
2386 2352
2387 return RX_MGMT_CFG80211_RX_AUTH; 2353 cfg80211_send_rx_auth(sdata->dev, (u8 *)mgmt, len);
2354 return;
2388 out_err: 2355 out_err:
2389 mutex_unlock(&sdata->local->sta_mtx); 2356 mutex_unlock(&sdata->local->sta_mtx);
2390 /* ignore frame -- wait for timeout */ 2357 /* ignore frame -- wait for timeout */
2391 return RX_MGMT_NONE;
2392} 2358}
2393 2359
2394 2360
2395static enum rx_mgmt_action __must_check 2361static void ieee80211_rx_mgmt_deauth(struct ieee80211_sub_if_data *sdata,
2396ieee80211_rx_mgmt_deauth(struct ieee80211_sub_if_data *sdata, 2362 struct ieee80211_mgmt *mgmt, size_t len)
2397 struct ieee80211_mgmt *mgmt, size_t len)
2398{ 2363{
2399 struct ieee80211_if_managed *ifmgd = &sdata->u.mgd; 2364 struct ieee80211_if_managed *ifmgd = &sdata->u.mgd;
2400 const u8 *bssid = NULL; 2365 const u8 *bssid = NULL;
2401 u16 reason_code; 2366 u16 reason_code;
2402 2367
2403 lockdep_assert_held(&ifmgd->mtx); 2368 sdata_assert_lock(sdata);
2404 2369
2405 if (len < 24 + 2) 2370 if (len < 24 + 2)
2406 return RX_MGMT_NONE; 2371 return;
2407 2372
2408 if (!ifmgd->associated || 2373 if (!ifmgd->associated ||
2409 !ether_addr_equal(mgmt->bssid, ifmgd->associated->bssid)) 2374 !ether_addr_equal(mgmt->bssid, ifmgd->associated->bssid))
2410 return RX_MGMT_NONE; 2375 return;
2411 2376
2412 bssid = ifmgd->associated->bssid; 2377 bssid = ifmgd->associated->bssid;
2413 2378
@@ -2418,25 +2383,24 @@ ieee80211_rx_mgmt_deauth(struct ieee80211_sub_if_data *sdata,
2418 2383
2419 ieee80211_set_disassoc(sdata, 0, 0, false, NULL); 2384 ieee80211_set_disassoc(sdata, 0, 0, false, NULL);
2420 2385
2421 return RX_MGMT_CFG80211_DEAUTH; 2386 cfg80211_send_deauth(sdata->dev, (u8 *)mgmt, len);
2422} 2387}
2423 2388
2424 2389
2425static enum rx_mgmt_action __must_check 2390static void ieee80211_rx_mgmt_disassoc(struct ieee80211_sub_if_data *sdata,
2426ieee80211_rx_mgmt_disassoc(struct ieee80211_sub_if_data *sdata, 2391 struct ieee80211_mgmt *mgmt, size_t len)
2427 struct ieee80211_mgmt *mgmt, size_t len)
2428{ 2392{
2429 struct ieee80211_if_managed *ifmgd = &sdata->u.mgd; 2393 struct ieee80211_if_managed *ifmgd = &sdata->u.mgd;
2430 u16 reason_code; 2394 u16 reason_code;
2431 2395
2432 lockdep_assert_held(&ifmgd->mtx); 2396 sdata_assert_lock(sdata);
2433 2397
2434 if (len < 24 + 2) 2398 if (len < 24 + 2)
2435 return RX_MGMT_NONE; 2399 return;
2436 2400
2437 if (!ifmgd->associated || 2401 if (!ifmgd->associated ||
2438 !ether_addr_equal(mgmt->bssid, ifmgd->associated->bssid)) 2402 !ether_addr_equal(mgmt->bssid, ifmgd->associated->bssid))
2439 return RX_MGMT_NONE; 2403 return;
2440 2404
2441 reason_code = le16_to_cpu(mgmt->u.disassoc.reason_code); 2405 reason_code = le16_to_cpu(mgmt->u.disassoc.reason_code);
2442 2406
@@ -2445,7 +2409,7 @@ ieee80211_rx_mgmt_disassoc(struct ieee80211_sub_if_data *sdata,
2445 2409
2446 ieee80211_set_disassoc(sdata, 0, 0, false, NULL); 2410 ieee80211_set_disassoc(sdata, 0, 0, false, NULL);
2447 2411
2448 return RX_MGMT_CFG80211_DISASSOC; 2412 cfg80211_send_disassoc(sdata->dev, (u8 *)mgmt, len);
2449} 2413}
2450 2414
2451static void ieee80211_get_rates(struct ieee80211_supported_band *sband, 2415static void ieee80211_get_rates(struct ieee80211_supported_band *sband,
@@ -2495,7 +2459,7 @@ static void ieee80211_destroy_assoc_data(struct ieee80211_sub_if_data *sdata,
2495{ 2459{
2496 struct ieee80211_mgd_assoc_data *assoc_data = sdata->u.mgd.assoc_data; 2460 struct ieee80211_mgd_assoc_data *assoc_data = sdata->u.mgd.assoc_data;
2497 2461
2498 lockdep_assert_held(&sdata->u.mgd.mtx); 2462 sdata_assert_lock(sdata);
2499 2463
2500 if (!assoc) { 2464 if (!assoc) {
2501 sta_info_destroy_addr(sdata, assoc_data->bss->bssid); 2465 sta_info_destroy_addr(sdata, assoc_data->bss->bssid);
@@ -2749,10 +2713,9 @@ static bool ieee80211_assoc_success(struct ieee80211_sub_if_data *sdata,
2749 return ret; 2713 return ret;
2750} 2714}
2751 2715
2752static enum rx_mgmt_action __must_check 2716static void ieee80211_rx_mgmt_assoc_resp(struct ieee80211_sub_if_data *sdata,
2753ieee80211_rx_mgmt_assoc_resp(struct ieee80211_sub_if_data *sdata, 2717 struct ieee80211_mgmt *mgmt,
2754 struct ieee80211_mgmt *mgmt, size_t len, 2718 size_t len)
2755 struct cfg80211_bss **bss)
2756{ 2719{
2757 struct ieee80211_if_managed *ifmgd = &sdata->u.mgd; 2720 struct ieee80211_if_managed *ifmgd = &sdata->u.mgd;
2758 struct ieee80211_mgd_assoc_data *assoc_data = ifmgd->assoc_data; 2721 struct ieee80211_mgd_assoc_data *assoc_data = ifmgd->assoc_data;
@@ -2760,13 +2723,14 @@ ieee80211_rx_mgmt_assoc_resp(struct ieee80211_sub_if_data *sdata,
2760 struct ieee802_11_elems elems; 2723 struct ieee802_11_elems elems;
2761 u8 *pos; 2724 u8 *pos;
2762 bool reassoc; 2725 bool reassoc;
2726 struct cfg80211_bss *bss;
2763 2727
2764 lockdep_assert_held(&ifmgd->mtx); 2728 sdata_assert_lock(sdata);
2765 2729
2766 if (!assoc_data) 2730 if (!assoc_data)
2767 return RX_MGMT_NONE; 2731 return;
2768 if (!ether_addr_equal(assoc_data->bss->bssid, mgmt->bssid)) 2732 if (!ether_addr_equal(assoc_data->bss->bssid, mgmt->bssid))
2769 return RX_MGMT_NONE; 2733 return;
2770 2734
2771 /* 2735 /*
2772 * AssocResp and ReassocResp have identical structure, so process both 2736 * AssocResp and ReassocResp have identical structure, so process both
@@ -2774,7 +2738,7 @@ ieee80211_rx_mgmt_assoc_resp(struct ieee80211_sub_if_data *sdata,
2774 */ 2738 */
2775 2739
2776 if (len < 24 + 6) 2740 if (len < 24 + 6)
2777 return RX_MGMT_NONE; 2741 return;
2778 2742
2779 reassoc = ieee80211_is_reassoc_req(mgmt->frame_control); 2743 reassoc = ieee80211_is_reassoc_req(mgmt->frame_control);
2780 capab_info = le16_to_cpu(mgmt->u.assoc_resp.capab_info); 2744 capab_info = le16_to_cpu(mgmt->u.assoc_resp.capab_info);
@@ -2801,22 +2765,23 @@ ieee80211_rx_mgmt_assoc_resp(struct ieee80211_sub_if_data *sdata,
2801 assoc_data->timeout = jiffies + msecs_to_jiffies(ms); 2765 assoc_data->timeout = jiffies + msecs_to_jiffies(ms);
2802 assoc_data->timeout_started = true; 2766 assoc_data->timeout_started = true;
2803 if (ms > IEEE80211_ASSOC_TIMEOUT) 2767 if (ms > IEEE80211_ASSOC_TIMEOUT)
2804 run_again(ifmgd, assoc_data->timeout); 2768 run_again(sdata, assoc_data->timeout);
2805 return RX_MGMT_NONE; 2769 return;
2806 } 2770 }
2807 2771
2808 *bss = assoc_data->bss; 2772 bss = assoc_data->bss;
2809 2773
2810 if (status_code != WLAN_STATUS_SUCCESS) { 2774 if (status_code != WLAN_STATUS_SUCCESS) {
2811 sdata_info(sdata, "%pM denied association (code=%d)\n", 2775 sdata_info(sdata, "%pM denied association (code=%d)\n",
2812 mgmt->sa, status_code); 2776 mgmt->sa, status_code);
2813 ieee80211_destroy_assoc_data(sdata, false); 2777 ieee80211_destroy_assoc_data(sdata, false);
2814 } else { 2778 } else {
2815 if (!ieee80211_assoc_success(sdata, *bss, mgmt, len)) { 2779 if (!ieee80211_assoc_success(sdata, bss, mgmt, len)) {
2816 /* oops -- internal error -- send timeout for now */ 2780 /* oops -- internal error -- send timeout for now */
2817 ieee80211_destroy_assoc_data(sdata, false); 2781 ieee80211_destroy_assoc_data(sdata, false);
2818 cfg80211_put_bss(sdata->local->hw.wiphy, *bss); 2782 cfg80211_put_bss(sdata->local->hw.wiphy, bss);
2819 return RX_MGMT_CFG80211_ASSOC_TIMEOUT; 2783 cfg80211_send_assoc_timeout(sdata->dev, mgmt->bssid);
2784 return;
2820 } 2785 }
2821 sdata_info(sdata, "associated\n"); 2786 sdata_info(sdata, "associated\n");
2822 2787
@@ -2828,7 +2793,7 @@ ieee80211_rx_mgmt_assoc_resp(struct ieee80211_sub_if_data *sdata,
2828 ieee80211_destroy_assoc_data(sdata, true); 2793 ieee80211_destroy_assoc_data(sdata, true);
2829 } 2794 }
2830 2795
2831 return RX_MGMT_CFG80211_RX_ASSOC; 2796 cfg80211_send_rx_assoc(sdata->dev, bss, (u8 *)mgmt, len);
2832} 2797}
2833 2798
2834static void ieee80211_rx_bss_info(struct ieee80211_sub_if_data *sdata, 2799static void ieee80211_rx_bss_info(struct ieee80211_sub_if_data *sdata,
@@ -2842,7 +2807,7 @@ static void ieee80211_rx_bss_info(struct ieee80211_sub_if_data *sdata,
2842 struct ieee80211_channel *channel; 2807 struct ieee80211_channel *channel;
2843 bool need_ps = false; 2808 bool need_ps = false;
2844 2809
2845 lockdep_assert_held(&sdata->u.mgd.mtx); 2810 sdata_assert_lock(sdata);
2846 2811
2847 if ((sdata->u.mgd.associated && 2812 if ((sdata->u.mgd.associated &&
2848 ether_addr_equal(mgmt->bssid, sdata->u.mgd.associated->bssid)) || 2813 ether_addr_equal(mgmt->bssid, sdata->u.mgd.associated->bssid)) ||
@@ -2901,7 +2866,7 @@ static void ieee80211_rx_mgmt_probe_resp(struct ieee80211_sub_if_data *sdata,
2901 2866
2902 ifmgd = &sdata->u.mgd; 2867 ifmgd = &sdata->u.mgd;
2903 2868
2904 ASSERT_MGD_MTX(ifmgd); 2869 sdata_assert_lock(sdata);
2905 2870
2906 if (!ether_addr_equal(mgmt->da, sdata->vif.addr)) 2871 if (!ether_addr_equal(mgmt->da, sdata->vif.addr))
2907 return; /* ignore ProbeResp to foreign address */ 2872 return; /* ignore ProbeResp to foreign address */
@@ -2926,7 +2891,7 @@ static void ieee80211_rx_mgmt_probe_resp(struct ieee80211_sub_if_data *sdata,
2926 ifmgd->auth_data->tries = 0; 2891 ifmgd->auth_data->tries = 0;
2927 ifmgd->auth_data->timeout = jiffies; 2892 ifmgd->auth_data->timeout = jiffies;
2928 ifmgd->auth_data->timeout_started = true; 2893 ifmgd->auth_data->timeout_started = true;
2929 run_again(ifmgd, ifmgd->auth_data->timeout); 2894 run_again(sdata, ifmgd->auth_data->timeout);
2930 } 2895 }
2931} 2896}
2932 2897
@@ -2951,10 +2916,9 @@ static const u64 care_about_ies =
2951 (1ULL << WLAN_EID_HT_CAPABILITY) | 2916 (1ULL << WLAN_EID_HT_CAPABILITY) |
2952 (1ULL << WLAN_EID_HT_OPERATION); 2917 (1ULL << WLAN_EID_HT_OPERATION);
2953 2918
2954static enum rx_mgmt_action 2919static void ieee80211_rx_mgmt_beacon(struct ieee80211_sub_if_data *sdata,
2955ieee80211_rx_mgmt_beacon(struct ieee80211_sub_if_data *sdata, 2920 struct ieee80211_mgmt *mgmt, size_t len,
2956 struct ieee80211_mgmt *mgmt, size_t len, 2921 struct ieee80211_rx_status *rx_status)
2957 u8 *deauth_buf, struct ieee80211_rx_status *rx_status)
2958{ 2922{
2959 struct ieee80211_if_managed *ifmgd = &sdata->u.mgd; 2923 struct ieee80211_if_managed *ifmgd = &sdata->u.mgd;
2960 struct ieee80211_bss_conf *bss_conf = &sdata->vif.bss_conf; 2924 struct ieee80211_bss_conf *bss_conf = &sdata->vif.bss_conf;
@@ -2969,24 +2933,25 @@ ieee80211_rx_mgmt_beacon(struct ieee80211_sub_if_data *sdata,
2969 u8 erp_value = 0; 2933 u8 erp_value = 0;
2970 u32 ncrc; 2934 u32 ncrc;
2971 u8 *bssid; 2935 u8 *bssid;
2936 u8 deauth_buf[IEEE80211_DEAUTH_FRAME_LEN];
2972 2937
2973 lockdep_assert_held(&ifmgd->mtx); 2938 sdata_assert_lock(sdata);
2974 2939
2975 /* Process beacon from the current BSS */ 2940 /* Process beacon from the current BSS */
2976 baselen = (u8 *) mgmt->u.beacon.variable - (u8 *) mgmt; 2941 baselen = (u8 *) mgmt->u.beacon.variable - (u8 *) mgmt;
2977 if (baselen > len) 2942 if (baselen > len)
2978 return RX_MGMT_NONE; 2943 return;
2979 2944
2980 rcu_read_lock(); 2945 rcu_read_lock();
2981 chanctx_conf = rcu_dereference(sdata->vif.chanctx_conf); 2946 chanctx_conf = rcu_dereference(sdata->vif.chanctx_conf);
2982 if (!chanctx_conf) { 2947 if (!chanctx_conf) {
2983 rcu_read_unlock(); 2948 rcu_read_unlock();
2984 return RX_MGMT_NONE; 2949 return;
2985 } 2950 }
2986 2951
2987 if (rx_status->freq != chanctx_conf->def.chan->center_freq) { 2952 if (rx_status->freq != chanctx_conf->def.chan->center_freq) {
2988 rcu_read_unlock(); 2953 rcu_read_unlock();
2989 return RX_MGMT_NONE; 2954 return;
2990 } 2955 }
2991 chan = chanctx_conf->def.chan; 2956 chan = chanctx_conf->def.chan;
2992 rcu_read_unlock(); 2957 rcu_read_unlock();
@@ -3013,13 +2978,13 @@ ieee80211_rx_mgmt_beacon(struct ieee80211_sub_if_data *sdata,
3013 /* continue assoc process */ 2978 /* continue assoc process */
3014 ifmgd->assoc_data->timeout = jiffies; 2979 ifmgd->assoc_data->timeout = jiffies;
3015 ifmgd->assoc_data->timeout_started = true; 2980 ifmgd->assoc_data->timeout_started = true;
3016 run_again(ifmgd, ifmgd->assoc_data->timeout); 2981 run_again(sdata, ifmgd->assoc_data->timeout);
3017 return RX_MGMT_NONE; 2982 return;
3018 } 2983 }
3019 2984
3020 if (!ifmgd->associated || 2985 if (!ifmgd->associated ||
3021 !ether_addr_equal(mgmt->bssid, ifmgd->associated->bssid)) 2986 !ether_addr_equal(mgmt->bssid, ifmgd->associated->bssid))
3022 return RX_MGMT_NONE; 2987 return;
3023 bssid = ifmgd->associated->bssid; 2988 bssid = ifmgd->associated->bssid;
3024 2989
3025 /* Track average RSSI from the Beacon frames of the current AP */ 2990 /* Track average RSSI from the Beacon frames of the current AP */
@@ -3165,7 +3130,7 @@ ieee80211_rx_mgmt_beacon(struct ieee80211_sub_if_data *sdata,
3165 } 3130 }
3166 3131
3167 if (ncrc == ifmgd->beacon_crc && ifmgd->beacon_crc_valid) 3132 if (ncrc == ifmgd->beacon_crc && ifmgd->beacon_crc_valid)
3168 return RX_MGMT_NONE; 3133 return;
3169 ifmgd->beacon_crc = ncrc; 3134 ifmgd->beacon_crc = ncrc;
3170 ifmgd->beacon_crc_valid = true; 3135 ifmgd->beacon_crc_valid = true;
3171 3136
@@ -3199,6 +3164,7 @@ ieee80211_rx_mgmt_beacon(struct ieee80211_sub_if_data *sdata,
3199 } 3164 }
3200 3165
3201 changed |= BSS_CHANGED_DTIM_PERIOD; 3166 changed |= BSS_CHANGED_DTIM_PERIOD;
3167 ieee80211_recalc_ps_vif(sdata);
3202 } 3168 }
3203 3169
3204 if (elems.erp_info) { 3170 if (elems.erp_info) {
@@ -3220,7 +3186,9 @@ ieee80211_rx_mgmt_beacon(struct ieee80211_sub_if_data *sdata,
3220 ieee80211_set_disassoc(sdata, IEEE80211_STYPE_DEAUTH, 3186 ieee80211_set_disassoc(sdata, IEEE80211_STYPE_DEAUTH,
3221 WLAN_REASON_DEAUTH_LEAVING, 3187 WLAN_REASON_DEAUTH_LEAVING,
3222 true, deauth_buf); 3188 true, deauth_buf);
3223 return RX_MGMT_CFG80211_TX_DEAUTH; 3189 cfg80211_send_deauth(sdata->dev, deauth_buf,
3190 sizeof(deauth_buf));
3191 return;
3224 } 3192 }
3225 3193
3226 if (sta && elems.opmode_notif) 3194 if (sta && elems.opmode_notif)
@@ -3237,19 +3205,13 @@ ieee80211_rx_mgmt_beacon(struct ieee80211_sub_if_data *sdata,
3237 elems.pwr_constr_elem); 3205 elems.pwr_constr_elem);
3238 3206
3239 ieee80211_bss_info_change_notify(sdata, changed); 3207 ieee80211_bss_info_change_notify(sdata, changed);
3240
3241 return RX_MGMT_NONE;
3242} 3208}
3243 3209
3244void ieee80211_sta_rx_queued_mgmt(struct ieee80211_sub_if_data *sdata, 3210void ieee80211_sta_rx_queued_mgmt(struct ieee80211_sub_if_data *sdata,
3245 struct sk_buff *skb) 3211 struct sk_buff *skb)
3246{ 3212{
3247 struct ieee80211_if_managed *ifmgd = &sdata->u.mgd;
3248 struct ieee80211_rx_status *rx_status; 3213 struct ieee80211_rx_status *rx_status;
3249 struct ieee80211_mgmt *mgmt; 3214 struct ieee80211_mgmt *mgmt;
3250 struct cfg80211_bss *bss = NULL;
3251 enum rx_mgmt_action rma = RX_MGMT_NONE;
3252 u8 deauth_buf[IEEE80211_DEAUTH_FRAME_LEN];
3253 u16 fc; 3215 u16 fc;
3254 struct ieee802_11_elems elems; 3216 struct ieee802_11_elems elems;
3255 int ies_len; 3217 int ies_len;
@@ -3258,28 +3220,27 @@ void ieee80211_sta_rx_queued_mgmt(struct ieee80211_sub_if_data *sdata,
3258 mgmt = (struct ieee80211_mgmt *) skb->data; 3220 mgmt = (struct ieee80211_mgmt *) skb->data;
3259 fc = le16_to_cpu(mgmt->frame_control); 3221 fc = le16_to_cpu(mgmt->frame_control);
3260 3222
3261 mutex_lock(&ifmgd->mtx); 3223 sdata_lock(sdata);
3262 3224
3263 switch (fc & IEEE80211_FCTL_STYPE) { 3225 switch (fc & IEEE80211_FCTL_STYPE) {
3264 case IEEE80211_STYPE_BEACON: 3226 case IEEE80211_STYPE_BEACON:
3265 rma = ieee80211_rx_mgmt_beacon(sdata, mgmt, skb->len, 3227 ieee80211_rx_mgmt_beacon(sdata, mgmt, skb->len, rx_status);
3266 deauth_buf, rx_status);
3267 break; 3228 break;
3268 case IEEE80211_STYPE_PROBE_RESP: 3229 case IEEE80211_STYPE_PROBE_RESP:
3269 ieee80211_rx_mgmt_probe_resp(sdata, skb); 3230 ieee80211_rx_mgmt_probe_resp(sdata, skb);
3270 break; 3231 break;
3271 case IEEE80211_STYPE_AUTH: 3232 case IEEE80211_STYPE_AUTH:
3272 rma = ieee80211_rx_mgmt_auth(sdata, mgmt, skb->len); 3233 ieee80211_rx_mgmt_auth(sdata, mgmt, skb->len);
3273 break; 3234 break;
3274 case IEEE80211_STYPE_DEAUTH: 3235 case IEEE80211_STYPE_DEAUTH:
3275 rma = ieee80211_rx_mgmt_deauth(sdata, mgmt, skb->len); 3236 ieee80211_rx_mgmt_deauth(sdata, mgmt, skb->len);
3276 break; 3237 break;
3277 case IEEE80211_STYPE_DISASSOC: 3238 case IEEE80211_STYPE_DISASSOC:
3278 rma = ieee80211_rx_mgmt_disassoc(sdata, mgmt, skb->len); 3239 ieee80211_rx_mgmt_disassoc(sdata, mgmt, skb->len);
3279 break; 3240 break;
3280 case IEEE80211_STYPE_ASSOC_RESP: 3241 case IEEE80211_STYPE_ASSOC_RESP:
3281 case IEEE80211_STYPE_REASSOC_RESP: 3242 case IEEE80211_STYPE_REASSOC_RESP:
3282 rma = ieee80211_rx_mgmt_assoc_resp(sdata, mgmt, skb->len, &bss); 3243 ieee80211_rx_mgmt_assoc_resp(sdata, mgmt, skb->len);
3283 break; 3244 break;
3284 case IEEE80211_STYPE_ACTION: 3245 case IEEE80211_STYPE_ACTION:
3285 if (mgmt->u.action.category == WLAN_CATEGORY_SPECTRUM_MGMT) { 3246 if (mgmt->u.action.category == WLAN_CATEGORY_SPECTRUM_MGMT) {
@@ -3325,34 +3286,7 @@ void ieee80211_sta_rx_queued_mgmt(struct ieee80211_sub_if_data *sdata,
3325 } 3286 }
3326 break; 3287 break;
3327 } 3288 }
3328 mutex_unlock(&ifmgd->mtx); 3289 sdata_unlock(sdata);
3329
3330 switch (rma) {
3331 case RX_MGMT_NONE:
3332 /* no action */
3333 break;
3334 case RX_MGMT_CFG80211_DEAUTH:
3335 cfg80211_send_deauth(sdata->dev, (u8 *)mgmt, skb->len);
3336 break;
3337 case RX_MGMT_CFG80211_DISASSOC:
3338 cfg80211_send_disassoc(sdata->dev, (u8 *)mgmt, skb->len);
3339 break;
3340 case RX_MGMT_CFG80211_RX_AUTH:
3341 cfg80211_send_rx_auth(sdata->dev, (u8 *)mgmt, skb->len);
3342 break;
3343 case RX_MGMT_CFG80211_RX_ASSOC:
3344 cfg80211_send_rx_assoc(sdata->dev, bss, (u8 *)mgmt, skb->len);
3345 break;
3346 case RX_MGMT_CFG80211_ASSOC_TIMEOUT:
3347 cfg80211_send_assoc_timeout(sdata->dev, mgmt->bssid);
3348 break;
3349 case RX_MGMT_CFG80211_TX_DEAUTH:
3350 cfg80211_send_deauth(sdata->dev, deauth_buf,
3351 sizeof(deauth_buf));
3352 break;
3353 default:
3354 WARN(1, "unexpected: %d", rma);
3355 }
3356} 3290}
3357 3291
3358static void ieee80211_sta_timer(unsigned long data) 3292static void ieee80211_sta_timer(unsigned long data)
@@ -3366,20 +3300,12 @@ static void ieee80211_sta_timer(unsigned long data)
3366static void ieee80211_sta_connection_lost(struct ieee80211_sub_if_data *sdata, 3300static void ieee80211_sta_connection_lost(struct ieee80211_sub_if_data *sdata,
3367 u8 *bssid, u8 reason, bool tx) 3301 u8 *bssid, u8 reason, bool tx)
3368{ 3302{
3369 struct ieee80211_if_managed *ifmgd = &sdata->u.mgd;
3370 u8 frame_buf[IEEE80211_DEAUTH_FRAME_LEN]; 3303 u8 frame_buf[IEEE80211_DEAUTH_FRAME_LEN];
3371 3304
3372 ieee80211_set_disassoc(sdata, IEEE80211_STYPE_DEAUTH, reason, 3305 ieee80211_set_disassoc(sdata, IEEE80211_STYPE_DEAUTH, reason,
3373 tx, frame_buf); 3306 tx, frame_buf);
3374 mutex_unlock(&ifmgd->mtx);
3375 3307
3376 /*
3377 * must be outside lock due to cfg80211,
3378 * but that's not a problem.
3379 */
3380 cfg80211_send_deauth(sdata->dev, frame_buf, IEEE80211_DEAUTH_FRAME_LEN); 3308 cfg80211_send_deauth(sdata->dev, frame_buf, IEEE80211_DEAUTH_FRAME_LEN);
3381
3382 mutex_lock(&ifmgd->mtx);
3383} 3309}
3384 3310
3385static int ieee80211_probe_auth(struct ieee80211_sub_if_data *sdata) 3311static int ieee80211_probe_auth(struct ieee80211_sub_if_data *sdata)
@@ -3389,7 +3315,7 @@ static int ieee80211_probe_auth(struct ieee80211_sub_if_data *sdata)
3389 struct ieee80211_mgd_auth_data *auth_data = ifmgd->auth_data; 3315 struct ieee80211_mgd_auth_data *auth_data = ifmgd->auth_data;
3390 u32 tx_flags = 0; 3316 u32 tx_flags = 0;
3391 3317
3392 lockdep_assert_held(&ifmgd->mtx); 3318 sdata_assert_lock(sdata);
3393 3319
3394 if (WARN_ON_ONCE(!auth_data)) 3320 if (WARN_ON_ONCE(!auth_data))
3395 return -EINVAL; 3321 return -EINVAL;
@@ -3462,7 +3388,7 @@ static int ieee80211_probe_auth(struct ieee80211_sub_if_data *sdata)
3462 if (tx_flags == 0) { 3388 if (tx_flags == 0) {
3463 auth_data->timeout = jiffies + IEEE80211_AUTH_TIMEOUT; 3389 auth_data->timeout = jiffies + IEEE80211_AUTH_TIMEOUT;
3464 ifmgd->auth_data->timeout_started = true; 3390 ifmgd->auth_data->timeout_started = true;
3465 run_again(ifmgd, auth_data->timeout); 3391 run_again(sdata, auth_data->timeout);
3466 } else { 3392 } else {
3467 auth_data->timeout_started = false; 3393 auth_data->timeout_started = false;
3468 } 3394 }
@@ -3475,7 +3401,7 @@ static int ieee80211_do_assoc(struct ieee80211_sub_if_data *sdata)
3475 struct ieee80211_mgd_assoc_data *assoc_data = sdata->u.mgd.assoc_data; 3401 struct ieee80211_mgd_assoc_data *assoc_data = sdata->u.mgd.assoc_data;
3476 struct ieee80211_local *local = sdata->local; 3402 struct ieee80211_local *local = sdata->local;
3477 3403
3478 lockdep_assert_held(&sdata->u.mgd.mtx); 3404 sdata_assert_lock(sdata);
3479 3405
3480 assoc_data->tries++; 3406 assoc_data->tries++;
3481 if (assoc_data->tries > IEEE80211_ASSOC_MAX_TRIES) { 3407 if (assoc_data->tries > IEEE80211_ASSOC_MAX_TRIES) {
@@ -3499,7 +3425,7 @@ static int ieee80211_do_assoc(struct ieee80211_sub_if_data *sdata)
3499 if (!(local->hw.flags & IEEE80211_HW_REPORTS_TX_ACK_STATUS)) { 3425 if (!(local->hw.flags & IEEE80211_HW_REPORTS_TX_ACK_STATUS)) {
3500 assoc_data->timeout = jiffies + IEEE80211_ASSOC_TIMEOUT; 3426 assoc_data->timeout = jiffies + IEEE80211_ASSOC_TIMEOUT;
3501 assoc_data->timeout_started = true; 3427 assoc_data->timeout_started = true;
3502 run_again(&sdata->u.mgd, assoc_data->timeout); 3428 run_again(sdata, assoc_data->timeout);
3503 } else { 3429 } else {
3504 assoc_data->timeout_started = false; 3430 assoc_data->timeout_started = false;
3505 } 3431 }
@@ -3524,7 +3450,7 @@ void ieee80211_sta_work(struct ieee80211_sub_if_data *sdata)
3524 struct ieee80211_local *local = sdata->local; 3450 struct ieee80211_local *local = sdata->local;
3525 struct ieee80211_if_managed *ifmgd = &sdata->u.mgd; 3451 struct ieee80211_if_managed *ifmgd = &sdata->u.mgd;
3526 3452
3527 mutex_lock(&ifmgd->mtx); 3453 sdata_lock(sdata);
3528 3454
3529 if (ifmgd->status_received) { 3455 if (ifmgd->status_received) {
3530 __le16 fc = ifmgd->status_fc; 3456 __le16 fc = ifmgd->status_fc;
@@ -3536,7 +3462,7 @@ void ieee80211_sta_work(struct ieee80211_sub_if_data *sdata)
3536 if (status_acked) { 3462 if (status_acked) {
3537 ifmgd->auth_data->timeout = 3463 ifmgd->auth_data->timeout =
3538 jiffies + IEEE80211_AUTH_TIMEOUT_SHORT; 3464 jiffies + IEEE80211_AUTH_TIMEOUT_SHORT;
3539 run_again(ifmgd, ifmgd->auth_data->timeout); 3465 run_again(sdata, ifmgd->auth_data->timeout);
3540 } else { 3466 } else {
3541 ifmgd->auth_data->timeout = jiffies - 1; 3467 ifmgd->auth_data->timeout = jiffies - 1;
3542 } 3468 }
@@ -3547,7 +3473,7 @@ void ieee80211_sta_work(struct ieee80211_sub_if_data *sdata)
3547 if (status_acked) { 3473 if (status_acked) {
3548 ifmgd->assoc_data->timeout = 3474 ifmgd->assoc_data->timeout =
3549 jiffies + IEEE80211_ASSOC_TIMEOUT_SHORT; 3475 jiffies + IEEE80211_ASSOC_TIMEOUT_SHORT;
3550 run_again(ifmgd, ifmgd->assoc_data->timeout); 3476 run_again(sdata, ifmgd->assoc_data->timeout);
3551 } else { 3477 } else {
3552 ifmgd->assoc_data->timeout = jiffies - 1; 3478 ifmgd->assoc_data->timeout = jiffies - 1;
3553 } 3479 }
@@ -3570,12 +3496,10 @@ void ieee80211_sta_work(struct ieee80211_sub_if_data *sdata)
3570 3496
3571 ieee80211_destroy_auth_data(sdata, false); 3497 ieee80211_destroy_auth_data(sdata, false);
3572 3498
3573 mutex_unlock(&ifmgd->mtx);
3574 cfg80211_send_auth_timeout(sdata->dev, bssid); 3499 cfg80211_send_auth_timeout(sdata->dev, bssid);
3575 mutex_lock(&ifmgd->mtx);
3576 } 3500 }
3577 } else if (ifmgd->auth_data && ifmgd->auth_data->timeout_started) 3501 } else if (ifmgd->auth_data && ifmgd->auth_data->timeout_started)
3578 run_again(ifmgd, ifmgd->auth_data->timeout); 3502 run_again(sdata, ifmgd->auth_data->timeout);
3579 3503
3580 if (ifmgd->assoc_data && ifmgd->assoc_data->timeout_started && 3504 if (ifmgd->assoc_data && ifmgd->assoc_data->timeout_started &&
3581 time_after(jiffies, ifmgd->assoc_data->timeout)) { 3505 time_after(jiffies, ifmgd->assoc_data->timeout)) {
@@ -3588,12 +3512,10 @@ void ieee80211_sta_work(struct ieee80211_sub_if_data *sdata)
3588 3512
3589 ieee80211_destroy_assoc_data(sdata, false); 3513 ieee80211_destroy_assoc_data(sdata, false);
3590 3514
3591 mutex_unlock(&ifmgd->mtx);
3592 cfg80211_send_assoc_timeout(sdata->dev, bssid); 3515 cfg80211_send_assoc_timeout(sdata->dev, bssid);
3593 mutex_lock(&ifmgd->mtx);
3594 } 3516 }
3595 } else if (ifmgd->assoc_data && ifmgd->assoc_data->timeout_started) 3517 } else if (ifmgd->assoc_data && ifmgd->assoc_data->timeout_started)
3596 run_again(ifmgd, ifmgd->assoc_data->timeout); 3518 run_again(sdata, ifmgd->assoc_data->timeout);
3597 3519
3598 if (ifmgd->flags & (IEEE80211_STA_BEACON_POLL | 3520 if (ifmgd->flags & (IEEE80211_STA_BEACON_POLL |
3599 IEEE80211_STA_CONNECTION_POLL) && 3521 IEEE80211_STA_CONNECTION_POLL) &&
@@ -3627,7 +3549,7 @@ void ieee80211_sta_work(struct ieee80211_sub_if_data *sdata)
3627 false); 3549 false);
3628 } 3550 }
3629 } else if (time_is_after_jiffies(ifmgd->probe_timeout)) 3551 } else if (time_is_after_jiffies(ifmgd->probe_timeout))
3630 run_again(ifmgd, ifmgd->probe_timeout); 3552 run_again(sdata, ifmgd->probe_timeout);
3631 else if (local->hw.flags & IEEE80211_HW_REPORTS_TX_ACK_STATUS) { 3553 else if (local->hw.flags & IEEE80211_HW_REPORTS_TX_ACK_STATUS) {
3632 mlme_dbg(sdata, 3554 mlme_dbg(sdata,
3633 "Failed to send nullfunc to AP %pM after %dms, disconnecting\n", 3555 "Failed to send nullfunc to AP %pM after %dms, disconnecting\n",
@@ -3656,7 +3578,7 @@ void ieee80211_sta_work(struct ieee80211_sub_if_data *sdata)
3656 } 3578 }
3657 } 3579 }
3658 3580
3659 mutex_unlock(&ifmgd->mtx); 3581 sdata_unlock(sdata);
3660} 3582}
3661 3583
3662static void ieee80211_sta_bcn_mon_timer(unsigned long data) 3584static void ieee80211_sta_bcn_mon_timer(unsigned long data)
@@ -3717,9 +3639,9 @@ void ieee80211_sta_restart(struct ieee80211_sub_if_data *sdata)
3717{ 3639{
3718 struct ieee80211_if_managed *ifmgd = &sdata->u.mgd; 3640 struct ieee80211_if_managed *ifmgd = &sdata->u.mgd;
3719 3641
3720 mutex_lock(&ifmgd->mtx); 3642 sdata_lock(sdata);
3721 if (!ifmgd->associated) { 3643 if (!ifmgd->associated) {
3722 mutex_unlock(&ifmgd->mtx); 3644 sdata_unlock(sdata);
3723 return; 3645 return;
3724 } 3646 }
3725 3647
@@ -3730,10 +3652,10 @@ void ieee80211_sta_restart(struct ieee80211_sub_if_data *sdata)
3730 ifmgd->associated->bssid, 3652 ifmgd->associated->bssid,
3731 WLAN_REASON_UNSPECIFIED, 3653 WLAN_REASON_UNSPECIFIED,
3732 true); 3654 true);
3733 mutex_unlock(&ifmgd->mtx); 3655 sdata_unlock(sdata);
3734 return; 3656 return;
3735 } 3657 }
3736 mutex_unlock(&ifmgd->mtx); 3658 sdata_unlock(sdata);
3737} 3659}
3738#endif 3660#endif
3739 3661
@@ -3765,8 +3687,6 @@ void ieee80211_sta_setup_sdata(struct ieee80211_sub_if_data *sdata)
3765 ifmgd->uapsd_max_sp_len = sdata->local->hw.uapsd_max_sp_len; 3687 ifmgd->uapsd_max_sp_len = sdata->local->hw.uapsd_max_sp_len;
3766 ifmgd->p2p_noa_index = -1; 3688 ifmgd->p2p_noa_index = -1;
3767 3689
3768 mutex_init(&ifmgd->mtx);
3769
3770 if (sdata->local->hw.flags & IEEE80211_HW_SUPPORTS_DYNAMIC_SMPS) 3690 if (sdata->local->hw.flags & IEEE80211_HW_SUPPORTS_DYNAMIC_SMPS)
3771 ifmgd->req_smps = IEEE80211_SMPS_AUTOMATIC; 3691 ifmgd->req_smps = IEEE80211_SMPS_AUTOMATIC;
3772 else 3692 else
@@ -4122,8 +4042,6 @@ int ieee80211_mgd_auth(struct ieee80211_sub_if_data *sdata,
4122 4042
4123 /* try to authenticate/probe */ 4043 /* try to authenticate/probe */
4124 4044
4125 mutex_lock(&ifmgd->mtx);
4126
4127 if ((ifmgd->auth_data && !ifmgd->auth_data->done) || 4045 if ((ifmgd->auth_data && !ifmgd->auth_data->done) ||
4128 ifmgd->assoc_data) { 4046 ifmgd->assoc_data) {
4129 err = -EBUSY; 4047 err = -EBUSY;
@@ -4143,8 +4061,8 @@ int ieee80211_mgd_auth(struct ieee80211_sub_if_data *sdata,
4143 WLAN_REASON_UNSPECIFIED, 4061 WLAN_REASON_UNSPECIFIED,
4144 false, frame_buf); 4062 false, frame_buf);
4145 4063
4146 __cfg80211_send_deauth(sdata->dev, frame_buf, 4064 cfg80211_send_deauth(sdata->dev, frame_buf,
4147 sizeof(frame_buf)); 4065 sizeof(frame_buf));
4148 } 4066 }
4149 4067
4150 sdata_info(sdata, "authenticate with %pM\n", req->bss->bssid); 4068 sdata_info(sdata, "authenticate with %pM\n", req->bss->bssid);
@@ -4161,8 +4079,7 @@ int ieee80211_mgd_auth(struct ieee80211_sub_if_data *sdata,
4161 4079
4162 /* hold our own reference */ 4080 /* hold our own reference */
4163 cfg80211_ref_bss(local->hw.wiphy, auth_data->bss); 4081 cfg80211_ref_bss(local->hw.wiphy, auth_data->bss);
4164 err = 0; 4082 return 0;
4165 goto out_unlock;
4166 4083
4167 err_clear: 4084 err_clear:
4168 memset(ifmgd->bssid, 0, ETH_ALEN); 4085 memset(ifmgd->bssid, 0, ETH_ALEN);
@@ -4170,9 +4087,6 @@ int ieee80211_mgd_auth(struct ieee80211_sub_if_data *sdata,
4170 ifmgd->auth_data = NULL; 4087 ifmgd->auth_data = NULL;
4171 err_free: 4088 err_free:
4172 kfree(auth_data); 4089 kfree(auth_data);
4173 out_unlock:
4174 mutex_unlock(&ifmgd->mtx);
4175
4176 return err; 4090 return err;
4177} 4091}
4178 4092
@@ -4203,8 +4117,6 @@ int ieee80211_mgd_assoc(struct ieee80211_sub_if_data *sdata,
4203 assoc_data->ssid_len = ssidie[1]; 4117 assoc_data->ssid_len = ssidie[1];
4204 rcu_read_unlock(); 4118 rcu_read_unlock();
4205 4119
4206 mutex_lock(&ifmgd->mtx);
4207
4208 if (ifmgd->associated) { 4120 if (ifmgd->associated) {
4209 u8 frame_buf[IEEE80211_DEAUTH_FRAME_LEN]; 4121 u8 frame_buf[IEEE80211_DEAUTH_FRAME_LEN];
4210 4122
@@ -4212,8 +4124,8 @@ int ieee80211_mgd_assoc(struct ieee80211_sub_if_data *sdata,
4212 WLAN_REASON_UNSPECIFIED, 4124 WLAN_REASON_UNSPECIFIED,
4213 false, frame_buf); 4125 false, frame_buf);
4214 4126
4215 __cfg80211_send_deauth(sdata->dev, frame_buf, 4127 cfg80211_send_deauth(sdata->dev, frame_buf,
4216 sizeof(frame_buf)); 4128 sizeof(frame_buf));
4217 } 4129 }
4218 4130
4219 if (ifmgd->auth_data && !ifmgd->auth_data->done) { 4131 if (ifmgd->auth_data && !ifmgd->auth_data->done) {
@@ -4407,7 +4319,7 @@ int ieee80211_mgd_assoc(struct ieee80211_sub_if_data *sdata,
4407 } 4319 }
4408 rcu_read_unlock(); 4320 rcu_read_unlock();
4409 4321
4410 run_again(ifmgd, assoc_data->timeout); 4322 run_again(sdata, assoc_data->timeout);
4411 4323
4412 if (bss->corrupt_data) { 4324 if (bss->corrupt_data) {
4413 char *corrupt_type = "data"; 4325 char *corrupt_type = "data";
@@ -4423,17 +4335,13 @@ int ieee80211_mgd_assoc(struct ieee80211_sub_if_data *sdata,
4423 corrupt_type); 4335 corrupt_type);
4424 } 4336 }
4425 4337
4426 err = 0; 4338 return 0;
4427 goto out;
4428 err_clear: 4339 err_clear:
4429 memset(ifmgd->bssid, 0, ETH_ALEN); 4340 memset(ifmgd->bssid, 0, ETH_ALEN);
4430 ieee80211_bss_info_change_notify(sdata, BSS_CHANGED_BSSID); 4341 ieee80211_bss_info_change_notify(sdata, BSS_CHANGED_BSSID);
4431 ifmgd->assoc_data = NULL; 4342 ifmgd->assoc_data = NULL;
4432 err_free: 4343 err_free:
4433 kfree(assoc_data); 4344 kfree(assoc_data);
4434 out:
4435 mutex_unlock(&ifmgd->mtx);
4436
4437 return err; 4345 return err;
4438} 4346}
4439 4347
@@ -4445,8 +4353,6 @@ int ieee80211_mgd_deauth(struct ieee80211_sub_if_data *sdata,
4445 bool tx = !req->local_state_change; 4353 bool tx = !req->local_state_change;
4446 bool report_frame = false; 4354 bool report_frame = false;
4447 4355
4448 mutex_lock(&ifmgd->mtx);
4449
4450 sdata_info(sdata, 4356 sdata_info(sdata,
4451 "deauthenticating from %pM by local choice (reason=%d)\n", 4357 "deauthenticating from %pM by local choice (reason=%d)\n",
4452 req->bssid, req->reason_code); 4358 req->bssid, req->reason_code);
@@ -4458,7 +4364,6 @@ int ieee80211_mgd_deauth(struct ieee80211_sub_if_data *sdata,
4458 req->reason_code, tx, 4364 req->reason_code, tx,
4459 frame_buf); 4365 frame_buf);
4460 ieee80211_destroy_auth_data(sdata, false); 4366 ieee80211_destroy_auth_data(sdata, false);
4461 mutex_unlock(&ifmgd->mtx);
4462 4367
4463 report_frame = true; 4368 report_frame = true;
4464 goto out; 4369 goto out;
@@ -4470,12 +4375,11 @@ int ieee80211_mgd_deauth(struct ieee80211_sub_if_data *sdata,
4470 req->reason_code, tx, frame_buf); 4375 req->reason_code, tx, frame_buf);
4471 report_frame = true; 4376 report_frame = true;
4472 } 4377 }
4473 mutex_unlock(&ifmgd->mtx);
4474 4378
4475 out: 4379 out:
4476 if (report_frame) 4380 if (report_frame)
4477 __cfg80211_send_deauth(sdata->dev, frame_buf, 4381 cfg80211_send_deauth(sdata->dev, frame_buf,
4478 IEEE80211_DEAUTH_FRAME_LEN); 4382 IEEE80211_DEAUTH_FRAME_LEN);
4479 4383
4480 return 0; 4384 return 0;
4481} 4385}
@@ -4487,18 +4391,14 @@ int ieee80211_mgd_disassoc(struct ieee80211_sub_if_data *sdata,
4487 u8 bssid[ETH_ALEN]; 4391 u8 bssid[ETH_ALEN];
4488 u8 frame_buf[IEEE80211_DEAUTH_FRAME_LEN]; 4392 u8 frame_buf[IEEE80211_DEAUTH_FRAME_LEN];
4489 4393
4490 mutex_lock(&ifmgd->mtx);
4491
4492 /* 4394 /*
4493 * cfg80211 should catch this ... but it's racy since 4395 * cfg80211 should catch this ... but it's racy since
4494 * we can receive a disassoc frame, process it, hand it 4396 * we can receive a disassoc frame, process it, hand it
4495 * to cfg80211 while that's in a locked section already 4397 * to cfg80211 while that's in a locked section already
4496 * trying to tell us that the user wants to disconnect. 4398 * trying to tell us that the user wants to disconnect.
4497 */ 4399 */
4498 if (ifmgd->associated != req->bss) { 4400 if (ifmgd->associated != req->bss)
4499 mutex_unlock(&ifmgd->mtx);
4500 return -ENOLINK; 4401 return -ENOLINK;
4501 }
4502 4402
4503 sdata_info(sdata, 4403 sdata_info(sdata,
4504 "disassociating from %pM by local choice (reason=%d)\n", 4404 "disassociating from %pM by local choice (reason=%d)\n",
@@ -4508,10 +4408,9 @@ int ieee80211_mgd_disassoc(struct ieee80211_sub_if_data *sdata,
4508 ieee80211_set_disassoc(sdata, IEEE80211_STYPE_DISASSOC, 4408 ieee80211_set_disassoc(sdata, IEEE80211_STYPE_DISASSOC,
4509 req->reason_code, !req->local_state_change, 4409 req->reason_code, !req->local_state_change,
4510 frame_buf); 4410 frame_buf);
4511 mutex_unlock(&ifmgd->mtx);
4512 4411
4513 __cfg80211_send_disassoc(sdata->dev, frame_buf, 4412 cfg80211_send_disassoc(sdata->dev, frame_buf,
4514 IEEE80211_DEAUTH_FRAME_LEN); 4413 IEEE80211_DEAUTH_FRAME_LEN);
4515 4414
4516 return 0; 4415 return 0;
4517} 4416}
@@ -4531,13 +4430,13 @@ void ieee80211_mgd_stop(struct ieee80211_sub_if_data *sdata)
4531 cancel_work_sync(&ifmgd->csa_connection_drop_work); 4430 cancel_work_sync(&ifmgd->csa_connection_drop_work);
4532 cancel_work_sync(&ifmgd->chswitch_work); 4431 cancel_work_sync(&ifmgd->chswitch_work);
4533 4432
4534 mutex_lock(&ifmgd->mtx); 4433 sdata_lock(sdata);
4535 if (ifmgd->assoc_data) 4434 if (ifmgd->assoc_data)
4536 ieee80211_destroy_assoc_data(sdata, false); 4435 ieee80211_destroy_assoc_data(sdata, false);
4537 if (ifmgd->auth_data) 4436 if (ifmgd->auth_data)
4538 ieee80211_destroy_auth_data(sdata, false); 4437 ieee80211_destroy_auth_data(sdata, false);
4539 del_timer_sync(&ifmgd->timer); 4438 del_timer_sync(&ifmgd->timer);
4540 mutex_unlock(&ifmgd->mtx); 4439 sdata_unlock(sdata);
4541} 4440}
4542 4441
4543void ieee80211_cqm_rssi_notify(struct ieee80211_vif *vif, 4442void ieee80211_cqm_rssi_notify(struct ieee80211_vif *vif,
diff --git a/net/mac80211/rx.c b/net/mac80211/rx.c
index 8e2952620256..bdd7b4a719e9 100644
--- a/net/mac80211/rx.c
+++ b/net/mac80211/rx.c
@@ -258,6 +258,8 @@ ieee80211_add_rx_radiotap_header(struct ieee80211_local *local,
258 pos += 2; 258 pos += 2;
259 259
260 if (status->flag & RX_FLAG_HT) { 260 if (status->flag & RX_FLAG_HT) {
261 unsigned int stbc;
262
261 rthdr->it_present |= cpu_to_le32(1 << IEEE80211_RADIOTAP_MCS); 263 rthdr->it_present |= cpu_to_le32(1 << IEEE80211_RADIOTAP_MCS);
262 *pos++ = local->hw.radiotap_mcs_details; 264 *pos++ = local->hw.radiotap_mcs_details;
263 *pos = 0; 265 *pos = 0;
@@ -267,6 +269,8 @@ ieee80211_add_rx_radiotap_header(struct ieee80211_local *local,
267 *pos |= IEEE80211_RADIOTAP_MCS_BW_40; 269 *pos |= IEEE80211_RADIOTAP_MCS_BW_40;
268 if (status->flag & RX_FLAG_HT_GF) 270 if (status->flag & RX_FLAG_HT_GF)
269 *pos |= IEEE80211_RADIOTAP_MCS_FMT_GF; 271 *pos |= IEEE80211_RADIOTAP_MCS_FMT_GF;
272 stbc = (status->flag & RX_FLAG_STBC_MASK) >> RX_FLAG_STBC_SHIFT;
273 *pos |= stbc << IEEE80211_RADIOTAP_MCS_STBC_SHIFT;
270 pos++; 274 pos++;
271 *pos++ = status->rate_idx; 275 *pos++ = status->rate_idx;
272 } 276 }
@@ -1372,6 +1376,7 @@ ieee80211_rx_h_sta_process(struct ieee80211_rx_data *rx)
1372 struct sk_buff *skb = rx->skb; 1376 struct sk_buff *skb = rx->skb;
1373 struct ieee80211_rx_status *status = IEEE80211_SKB_RXCB(skb); 1377 struct ieee80211_rx_status *status = IEEE80211_SKB_RXCB(skb);
1374 struct ieee80211_hdr *hdr = (struct ieee80211_hdr *)skb->data; 1378 struct ieee80211_hdr *hdr = (struct ieee80211_hdr *)skb->data;
1379 int i;
1375 1380
1376 if (!sta) 1381 if (!sta)
1377 return RX_CONTINUE; 1382 return RX_CONTINUE;
@@ -1422,6 +1427,19 @@ ieee80211_rx_h_sta_process(struct ieee80211_rx_data *rx)
1422 ewma_add(&sta->avg_signal, -status->signal); 1427 ewma_add(&sta->avg_signal, -status->signal);
1423 } 1428 }
1424 1429
1430 if (status->chains) {
1431 sta->chains = status->chains;
1432 for (i = 0; i < ARRAY_SIZE(status->chain_signal); i++) {
1433 int signal = status->chain_signal[i];
1434
1435 if (!(status->chains & BIT(i)))
1436 continue;
1437
1438 sta->chain_signal_last[i] = signal;
1439 ewma_add(&sta->chain_signal_avg[i], -signal);
1440 }
1441 }
1442
1425 /* 1443 /*
1426 * Change STA power saving mode only at the end of a frame 1444 * Change STA power saving mode only at the end of a frame
1427 * exchange sequence. 1445 * exchange sequence.
@@ -1608,7 +1626,7 @@ ieee80211_rx_h_defragment(struct ieee80211_rx_data *rx)
1608 entry->ccmp = 1; 1626 entry->ccmp = 1;
1609 memcpy(entry->last_pn, 1627 memcpy(entry->last_pn,
1610 rx->key->u.ccmp.rx_pn[queue], 1628 rx->key->u.ccmp.rx_pn[queue],
1611 CCMP_PN_LEN); 1629 IEEE80211_CCMP_PN_LEN);
1612 } 1630 }
1613 return RX_QUEUED; 1631 return RX_QUEUED;
1614 } 1632 }
@@ -1627,21 +1645,21 @@ ieee80211_rx_h_defragment(struct ieee80211_rx_data *rx)
1627 * (IEEE 802.11i, 8.3.3.4.5) */ 1645 * (IEEE 802.11i, 8.3.3.4.5) */
1628 if (entry->ccmp) { 1646 if (entry->ccmp) {
1629 int i; 1647 int i;
1630 u8 pn[CCMP_PN_LEN], *rpn; 1648 u8 pn[IEEE80211_CCMP_PN_LEN], *rpn;
1631 int queue; 1649 int queue;
1632 if (!rx->key || rx->key->conf.cipher != WLAN_CIPHER_SUITE_CCMP) 1650 if (!rx->key || rx->key->conf.cipher != WLAN_CIPHER_SUITE_CCMP)
1633 return RX_DROP_UNUSABLE; 1651 return RX_DROP_UNUSABLE;
1634 memcpy(pn, entry->last_pn, CCMP_PN_LEN); 1652 memcpy(pn, entry->last_pn, IEEE80211_CCMP_PN_LEN);
1635 for (i = CCMP_PN_LEN - 1; i >= 0; i--) { 1653 for (i = IEEE80211_CCMP_PN_LEN - 1; i >= 0; i--) {
1636 pn[i]++; 1654 pn[i]++;
1637 if (pn[i]) 1655 if (pn[i])
1638 break; 1656 break;
1639 } 1657 }
1640 queue = rx->security_idx; 1658 queue = rx->security_idx;
1641 rpn = rx->key->u.ccmp.rx_pn[queue]; 1659 rpn = rx->key->u.ccmp.rx_pn[queue];
1642 if (memcmp(pn, rpn, CCMP_PN_LEN)) 1660 if (memcmp(pn, rpn, IEEE80211_CCMP_PN_LEN))
1643 return RX_DROP_UNUSABLE; 1661 return RX_DROP_UNUSABLE;
1644 memcpy(entry->last_pn, pn, CCMP_PN_LEN); 1662 memcpy(entry->last_pn, pn, IEEE80211_CCMP_PN_LEN);
1645 } 1663 }
1646 1664
1647 skb_pull(rx->skb, ieee80211_hdrlen(fc)); 1665 skb_pull(rx->skb, ieee80211_hdrlen(fc));
diff --git a/net/mac80211/sta_info.c b/net/mac80211/sta_info.c
index 11216bc13b27..a04c5671d7fd 100644
--- a/net/mac80211/sta_info.c
+++ b/net/mac80211/sta_info.c
@@ -358,6 +358,8 @@ struct sta_info *sta_info_alloc(struct ieee80211_sub_if_data *sdata,
358 do_posix_clock_monotonic_gettime(&uptime); 358 do_posix_clock_monotonic_gettime(&uptime);
359 sta->last_connected = uptime.tv_sec; 359 sta->last_connected = uptime.tv_sec;
360 ewma_init(&sta->avg_signal, 1024, 8); 360 ewma_init(&sta->avg_signal, 1024, 8);
361 for (i = 0; i < ARRAY_SIZE(sta->chain_signal_avg); i++)
362 ewma_init(&sta->chain_signal_avg[i], 1024, 8);
361 363
362 if (sta_prepare_rate_control(local, sta, gfp)) { 364 if (sta_prepare_rate_control(local, sta, gfp)) {
363 kfree(sta); 365 kfree(sta);
diff --git a/net/mac80211/sta_info.h b/net/mac80211/sta_info.h
index adc30045f99e..41c28b977f7c 100644
--- a/net/mac80211/sta_info.h
+++ b/net/mac80211/sta_info.h
@@ -344,6 +344,11 @@ struct sta_info {
344 int last_signal; 344 int last_signal;
345 struct ewma avg_signal; 345 struct ewma avg_signal;
346 int last_ack_signal; 346 int last_ack_signal;
347
348 u8 chains;
349 s8 chain_signal_last[IEEE80211_MAX_CHAINS];
350 struct ewma chain_signal_avg[IEEE80211_MAX_CHAINS];
351
347 /* Plus 1 for non-QoS frames */ 352 /* Plus 1 for non-QoS frames */
348 __le16 last_seq_ctrl[IEEE80211_NUM_TIDS + 1]; 353 __le16 last_seq_ctrl[IEEE80211_NUM_TIDS + 1];
349 354
diff --git a/net/mac80211/tx.c b/net/mac80211/tx.c
index 9972e07a2f96..34be9336b5d1 100644
--- a/net/mac80211/tx.c
+++ b/net/mac80211/tx.c
@@ -398,13 +398,14 @@ ieee80211_tx_h_multicast_ps_buf(struct ieee80211_tx_data *tx)
398 if (ieee80211_has_order(hdr->frame_control)) 398 if (ieee80211_has_order(hdr->frame_control))
399 return TX_CONTINUE; 399 return TX_CONTINUE;
400 400
401 if (tx->local->hw.flags & IEEE80211_HW_QUEUE_CONTROL)
402 info->hw_queue = tx->sdata->vif.cab_queue;
403
401 /* no stations in PS mode */ 404 /* no stations in PS mode */
402 if (!atomic_read(&ps->num_sta_ps)) 405 if (!atomic_read(&ps->num_sta_ps))
403 return TX_CONTINUE; 406 return TX_CONTINUE;
404 407
405 info->flags |= IEEE80211_TX_CTL_SEND_AFTER_DTIM; 408 info->flags |= IEEE80211_TX_CTL_SEND_AFTER_DTIM;
406 if (tx->local->hw.flags & IEEE80211_HW_QUEUE_CONTROL)
407 info->hw_queue = tx->sdata->vif.cab_queue;
408 409
409 /* device releases frame after DTIM beacon */ 410 /* device releases frame after DTIM beacon */
410 if (!(tx->local->hw.flags & IEEE80211_HW_HOST_BROADCAST_PS_BUFFERING)) 411 if (!(tx->local->hw.flags & IEEE80211_HW_HOST_BROADCAST_PS_BUFFERING))
diff --git a/net/mac80211/util.c b/net/mac80211/util.c
index 72e6292955bb..c75d3db2a31c 100644
--- a/net/mac80211/util.c
+++ b/net/mac80211/util.c
@@ -560,6 +560,9 @@ void ieee80211_iterate_active_interfaces(
560 list_for_each_entry(sdata, &local->interfaces, list) { 560 list_for_each_entry(sdata, &local->interfaces, list) {
561 switch (sdata->vif.type) { 561 switch (sdata->vif.type) {
562 case NL80211_IFTYPE_MONITOR: 562 case NL80211_IFTYPE_MONITOR:
563 if (!(sdata->u.mntr_flags & MONITOR_FLAG_ACTIVE))
564 continue;
565 break;
563 case NL80211_IFTYPE_AP_VLAN: 566 case NL80211_IFTYPE_AP_VLAN:
564 continue; 567 continue;
565 default: 568 default:
@@ -598,6 +601,9 @@ void ieee80211_iterate_active_interfaces_atomic(
598 list_for_each_entry_rcu(sdata, &local->interfaces, list) { 601 list_for_each_entry_rcu(sdata, &local->interfaces, list) {
599 switch (sdata->vif.type) { 602 switch (sdata->vif.type) {
600 case NL80211_IFTYPE_MONITOR: 603 case NL80211_IFTYPE_MONITOR:
604 if (!(sdata->u.mntr_flags & MONITOR_FLAG_ACTIVE))
605 continue;
606 break;
601 case NL80211_IFTYPE_AP_VLAN: 607 case NL80211_IFTYPE_AP_VLAN:
602 continue; 608 continue;
603 default: 609 default:
@@ -1072,32 +1078,6 @@ void ieee80211_sta_def_wmm_params(struct ieee80211_sub_if_data *sdata,
1072 ieee80211_set_wmm_default(sdata, true); 1078 ieee80211_set_wmm_default(sdata, true);
1073} 1079}
1074 1080
1075u32 ieee80211_mandatory_rates(struct ieee80211_local *local,
1076 enum ieee80211_band band)
1077{
1078 struct ieee80211_supported_band *sband;
1079 struct ieee80211_rate *bitrates;
1080 u32 mandatory_rates;
1081 enum ieee80211_rate_flags mandatory_flag;
1082 int i;
1083
1084 sband = local->hw.wiphy->bands[band];
1085 if (WARN_ON(!sband))
1086 return 1;
1087
1088 if (band == IEEE80211_BAND_2GHZ)
1089 mandatory_flag = IEEE80211_RATE_MANDATORY_B;
1090 else
1091 mandatory_flag = IEEE80211_RATE_MANDATORY_A;
1092
1093 bitrates = sband->bitrates;
1094 mandatory_rates = 0;
1095 for (i = 0; i < sband->n_bitrates; i++)
1096 if (bitrates[i].flags & mandatory_flag)
1097 mandatory_rates |= BIT(i);
1098 return mandatory_rates;
1099}
1100
1101void ieee80211_send_auth(struct ieee80211_sub_if_data *sdata, 1081void ieee80211_send_auth(struct ieee80211_sub_if_data *sdata,
1102 u16 transaction, u16 auth_alg, u16 status, 1082 u16 transaction, u16 auth_alg, u16 status,
1103 const u8 *extra, size_t extra_len, const u8 *da, 1083 const u8 *extra, size_t extra_len, const u8 *da,
@@ -1607,9 +1587,9 @@ int ieee80211_reconfig(struct ieee80211_local *local)
1607 if (sdata->u.mgd.dtim_period) 1587 if (sdata->u.mgd.dtim_period)
1608 changed |= BSS_CHANGED_DTIM_PERIOD; 1588 changed |= BSS_CHANGED_DTIM_PERIOD;
1609 1589
1610 mutex_lock(&sdata->u.mgd.mtx); 1590 sdata_lock(sdata);
1611 ieee80211_bss_info_change_notify(sdata, changed); 1591 ieee80211_bss_info_change_notify(sdata, changed);
1612 mutex_unlock(&sdata->u.mgd.mtx); 1592 sdata_unlock(sdata);
1613 break; 1593 break;
1614 case NL80211_IFTYPE_ADHOC: 1594 case NL80211_IFTYPE_ADHOC:
1615 changed |= BSS_CHANGED_IBSS; 1595 changed |= BSS_CHANGED_IBSS;
diff --git a/net/mac80211/wep.c b/net/mac80211/wep.c
index c04d401dae92..6ee2b5863572 100644
--- a/net/mac80211/wep.c
+++ b/net/mac80211/wep.c
@@ -28,7 +28,7 @@
28int ieee80211_wep_init(struct ieee80211_local *local) 28int ieee80211_wep_init(struct ieee80211_local *local)
29{ 29{
30 /* start WEP IV from a random value */ 30 /* start WEP IV from a random value */
31 get_random_bytes(&local->wep_iv, WEP_IV_LEN); 31 get_random_bytes(&local->wep_iv, IEEE80211_WEP_IV_LEN);
32 32
33 local->wep_tx_tfm = crypto_alloc_cipher("arc4", 0, CRYPTO_ALG_ASYNC); 33 local->wep_tx_tfm = crypto_alloc_cipher("arc4", 0, CRYPTO_ALG_ASYNC);
34 if (IS_ERR(local->wep_tx_tfm)) { 34 if (IS_ERR(local->wep_tx_tfm)) {
@@ -98,20 +98,21 @@ static u8 *ieee80211_wep_add_iv(struct ieee80211_local *local,
98 98
99 hdr->frame_control |= cpu_to_le16(IEEE80211_FCTL_PROTECTED); 99 hdr->frame_control |= cpu_to_le16(IEEE80211_FCTL_PROTECTED);
100 100
101 if (WARN_ON(skb_tailroom(skb) < WEP_ICV_LEN || 101 if (WARN_ON(skb_tailroom(skb) < IEEE80211_WEP_ICV_LEN ||
102 skb_headroom(skb) < WEP_IV_LEN)) 102 skb_headroom(skb) < IEEE80211_WEP_IV_LEN))
103 return NULL; 103 return NULL;
104 104
105 hdrlen = ieee80211_hdrlen(hdr->frame_control); 105 hdrlen = ieee80211_hdrlen(hdr->frame_control);
106 newhdr = skb_push(skb, WEP_IV_LEN); 106 newhdr = skb_push(skb, IEEE80211_WEP_IV_LEN);
107 memmove(newhdr, newhdr + WEP_IV_LEN, hdrlen); 107 memmove(newhdr, newhdr + IEEE80211_WEP_IV_LEN, hdrlen);
108 108
109 /* the HW only needs room for the IV, but not the actual IV */ 109 /* the HW only needs room for the IV, but not the actual IV */
110 if (info->control.hw_key && 110 if (info->control.hw_key &&
111 (info->control.hw_key->flags & IEEE80211_KEY_FLAG_PUT_IV_SPACE)) 111 (info->control.hw_key->flags & IEEE80211_KEY_FLAG_PUT_IV_SPACE))
112 return newhdr + hdrlen; 112 return newhdr + hdrlen;
113 113
114 skb_set_network_header(skb, skb_network_offset(skb) + WEP_IV_LEN); 114 skb_set_network_header(skb, skb_network_offset(skb) +
115 IEEE80211_WEP_IV_LEN);
115 ieee80211_wep_get_iv(local, keylen, keyidx, newhdr + hdrlen); 116 ieee80211_wep_get_iv(local, keylen, keyidx, newhdr + hdrlen);
116 return newhdr + hdrlen; 117 return newhdr + hdrlen;
117} 118}
@@ -125,8 +126,8 @@ static void ieee80211_wep_remove_iv(struct ieee80211_local *local,
125 unsigned int hdrlen; 126 unsigned int hdrlen;
126 127
127 hdrlen = ieee80211_hdrlen(hdr->frame_control); 128 hdrlen = ieee80211_hdrlen(hdr->frame_control);
128 memmove(skb->data + WEP_IV_LEN, skb->data, hdrlen); 129 memmove(skb->data + IEEE80211_WEP_IV_LEN, skb->data, hdrlen);
129 skb_pull(skb, WEP_IV_LEN); 130 skb_pull(skb, IEEE80211_WEP_IV_LEN);
130} 131}
131 132
132 133
@@ -146,7 +147,7 @@ int ieee80211_wep_encrypt_data(struct crypto_cipher *tfm, u8 *rc4key,
146 put_unaligned(icv, (__le32 *)(data + data_len)); 147 put_unaligned(icv, (__le32 *)(data + data_len));
147 148
148 crypto_cipher_setkey(tfm, rc4key, klen); 149 crypto_cipher_setkey(tfm, rc4key, klen);
149 for (i = 0; i < data_len + WEP_ICV_LEN; i++) 150 for (i = 0; i < data_len + IEEE80211_WEP_ICV_LEN; i++)
150 crypto_cipher_encrypt_one(tfm, data + i, data + i); 151 crypto_cipher_encrypt_one(tfm, data + i, data + i);
151 152
152 return 0; 153 return 0;
@@ -172,7 +173,7 @@ int ieee80211_wep_encrypt(struct ieee80211_local *local,
172 if (!iv) 173 if (!iv)
173 return -1; 174 return -1;
174 175
175 len = skb->len - (iv + WEP_IV_LEN - skb->data); 176 len = skb->len - (iv + IEEE80211_WEP_IV_LEN - skb->data);
176 177
177 /* Prepend 24-bit IV to RC4 key */ 178 /* Prepend 24-bit IV to RC4 key */
178 memcpy(rc4key, iv, 3); 179 memcpy(rc4key, iv, 3);
@@ -181,10 +182,10 @@ int ieee80211_wep_encrypt(struct ieee80211_local *local,
181 memcpy(rc4key + 3, key, keylen); 182 memcpy(rc4key + 3, key, keylen);
182 183
183 /* Add room for ICV */ 184 /* Add room for ICV */
184 skb_put(skb, WEP_ICV_LEN); 185 skb_put(skb, IEEE80211_WEP_ICV_LEN);
185 186
186 return ieee80211_wep_encrypt_data(local->wep_tx_tfm, rc4key, keylen + 3, 187 return ieee80211_wep_encrypt_data(local->wep_tx_tfm, rc4key, keylen + 3,
187 iv + WEP_IV_LEN, len); 188 iv + IEEE80211_WEP_IV_LEN, len);
188} 189}
189 190
190 191
@@ -201,11 +202,11 @@ int ieee80211_wep_decrypt_data(struct crypto_cipher *tfm, u8 *rc4key,
201 return -1; 202 return -1;
202 203
203 crypto_cipher_setkey(tfm, rc4key, klen); 204 crypto_cipher_setkey(tfm, rc4key, klen);
204 for (i = 0; i < data_len + WEP_ICV_LEN; i++) 205 for (i = 0; i < data_len + IEEE80211_WEP_ICV_LEN; i++)
205 crypto_cipher_decrypt_one(tfm, data + i, data + i); 206 crypto_cipher_decrypt_one(tfm, data + i, data + i);
206 207
207 crc = cpu_to_le32(~crc32_le(~0, data, data_len)); 208 crc = cpu_to_le32(~crc32_le(~0, data, data_len));
208 if (memcmp(&crc, data + data_len, WEP_ICV_LEN) != 0) 209 if (memcmp(&crc, data + data_len, IEEE80211_WEP_ICV_LEN) != 0)
209 /* ICV mismatch */ 210 /* ICV mismatch */
210 return -1; 211 return -1;
211 212
@@ -237,10 +238,10 @@ static int ieee80211_wep_decrypt(struct ieee80211_local *local,
237 return -1; 238 return -1;
238 239
239 hdrlen = ieee80211_hdrlen(hdr->frame_control); 240 hdrlen = ieee80211_hdrlen(hdr->frame_control);
240 if (skb->len < hdrlen + WEP_IV_LEN + WEP_ICV_LEN) 241 if (skb->len < hdrlen + IEEE80211_WEP_IV_LEN + IEEE80211_WEP_ICV_LEN)
241 return -1; 242 return -1;
242 243
243 len = skb->len - hdrlen - WEP_IV_LEN - WEP_ICV_LEN; 244 len = skb->len - hdrlen - IEEE80211_WEP_IV_LEN - IEEE80211_WEP_ICV_LEN;
244 245
245 keyidx = skb->data[hdrlen + 3] >> 6; 246 keyidx = skb->data[hdrlen + 3] >> 6;
246 247
@@ -256,16 +257,16 @@ static int ieee80211_wep_decrypt(struct ieee80211_local *local,
256 memcpy(rc4key + 3, key->conf.key, key->conf.keylen); 257 memcpy(rc4key + 3, key->conf.key, key->conf.keylen);
257 258
258 if (ieee80211_wep_decrypt_data(local->wep_rx_tfm, rc4key, klen, 259 if (ieee80211_wep_decrypt_data(local->wep_rx_tfm, rc4key, klen,
259 skb->data + hdrlen + WEP_IV_LEN, 260 skb->data + hdrlen +
260 len)) 261 IEEE80211_WEP_IV_LEN, len))
261 ret = -1; 262 ret = -1;
262 263
263 /* Trim ICV */ 264 /* Trim ICV */
264 skb_trim(skb, skb->len - WEP_ICV_LEN); 265 skb_trim(skb, skb->len - IEEE80211_WEP_ICV_LEN);
265 266
266 /* Remove IV */ 267 /* Remove IV */
267 memmove(skb->data + WEP_IV_LEN, skb->data, hdrlen); 268 memmove(skb->data + IEEE80211_WEP_IV_LEN, skb->data, hdrlen);
268 skb_pull(skb, WEP_IV_LEN); 269 skb_pull(skb, IEEE80211_WEP_IV_LEN);
269 270
270 return ret; 271 return ret;
271} 272}
@@ -305,13 +306,14 @@ ieee80211_crypto_wep_decrypt(struct ieee80211_rx_data *rx)
305 if (ieee80211_wep_decrypt(rx->local, rx->skb, rx->key)) 306 if (ieee80211_wep_decrypt(rx->local, rx->skb, rx->key))
306 return RX_DROP_UNUSABLE; 307 return RX_DROP_UNUSABLE;
307 } else if (!(status->flag & RX_FLAG_IV_STRIPPED)) { 308 } else if (!(status->flag & RX_FLAG_IV_STRIPPED)) {
308 if (!pskb_may_pull(rx->skb, ieee80211_hdrlen(fc) + WEP_IV_LEN)) 309 if (!pskb_may_pull(rx->skb, ieee80211_hdrlen(fc) +
310 IEEE80211_WEP_IV_LEN))
309 return RX_DROP_UNUSABLE; 311 return RX_DROP_UNUSABLE;
310 if (rx->sta && ieee80211_wep_is_weak_iv(rx->skb, rx->key)) 312 if (rx->sta && ieee80211_wep_is_weak_iv(rx->skb, rx->key))
311 rx->sta->wep_weak_iv_count++; 313 rx->sta->wep_weak_iv_count++;
312 ieee80211_wep_remove_iv(rx->local, rx->skb, rx->key); 314 ieee80211_wep_remove_iv(rx->local, rx->skb, rx->key);
313 /* remove ICV */ 315 /* remove ICV */
314 if (pskb_trim(rx->skb, rx->skb->len - WEP_ICV_LEN)) 316 if (pskb_trim(rx->skb, rx->skb->len - IEEE80211_WEP_ICV_LEN))
315 return RX_DROP_UNUSABLE; 317 return RX_DROP_UNUSABLE;
316 } 318 }
317 319
diff --git a/net/mac80211/wpa.c b/net/mac80211/wpa.c
index c7c6d644486f..c9edfcb7a13b 100644
--- a/net/mac80211/wpa.c
+++ b/net/mac80211/wpa.c
@@ -62,10 +62,10 @@ ieee80211_tx_h_michael_mic_add(struct ieee80211_tx_data *tx)
62 62
63 tail = MICHAEL_MIC_LEN; 63 tail = MICHAEL_MIC_LEN;
64 if (!info->control.hw_key) 64 if (!info->control.hw_key)
65 tail += TKIP_ICV_LEN; 65 tail += IEEE80211_TKIP_ICV_LEN;
66 66
67 if (WARN_ON(skb_tailroom(skb) < tail || 67 if (WARN_ON(skb_tailroom(skb) < tail ||
68 skb_headroom(skb) < TKIP_IV_LEN)) 68 skb_headroom(skb) < IEEE80211_TKIP_IV_LEN))
69 return TX_DROP; 69 return TX_DROP;
70 70
71 key = &tx->key->conf.key[NL80211_TKIP_DATA_OFFSET_TX_MIC_KEY]; 71 key = &tx->key->conf.key[NL80211_TKIP_DATA_OFFSET_TX_MIC_KEY];
@@ -198,15 +198,16 @@ static int tkip_encrypt_skb(struct ieee80211_tx_data *tx, struct sk_buff *skb)
198 if (info->control.hw_key) 198 if (info->control.hw_key)
199 tail = 0; 199 tail = 0;
200 else 200 else
201 tail = TKIP_ICV_LEN; 201 tail = IEEE80211_TKIP_ICV_LEN;
202 202
203 if (WARN_ON(skb_tailroom(skb) < tail || 203 if (WARN_ON(skb_tailroom(skb) < tail ||
204 skb_headroom(skb) < TKIP_IV_LEN)) 204 skb_headroom(skb) < IEEE80211_TKIP_IV_LEN))
205 return -1; 205 return -1;
206 206
207 pos = skb_push(skb, TKIP_IV_LEN); 207 pos = skb_push(skb, IEEE80211_TKIP_IV_LEN);
208 memmove(pos, pos + TKIP_IV_LEN, hdrlen); 208 memmove(pos, pos + IEEE80211_TKIP_IV_LEN, hdrlen);
209 skb_set_network_header(skb, skb_network_offset(skb) + TKIP_IV_LEN); 209 skb_set_network_header(skb, skb_network_offset(skb) +
210 IEEE80211_TKIP_IV_LEN);
210 pos += hdrlen; 211 pos += hdrlen;
211 212
212 /* the HW only needs room for the IV, but not the actual IV */ 213 /* the HW only needs room for the IV, but not the actual IV */
@@ -227,7 +228,7 @@ static int tkip_encrypt_skb(struct ieee80211_tx_data *tx, struct sk_buff *skb)
227 return 0; 228 return 0;
228 229
229 /* Add room for ICV */ 230 /* Add room for ICV */
230 skb_put(skb, TKIP_ICV_LEN); 231 skb_put(skb, IEEE80211_TKIP_ICV_LEN);
231 232
232 return ieee80211_tkip_encrypt_data(tx->local->wep_tx_tfm, 233 return ieee80211_tkip_encrypt_data(tx->local->wep_tx_tfm,
233 key, skb, pos, len); 234 key, skb, pos, len);
@@ -290,11 +291,11 @@ ieee80211_crypto_tkip_decrypt(struct ieee80211_rx_data *rx)
290 return RX_DROP_UNUSABLE; 291 return RX_DROP_UNUSABLE;
291 292
292 /* Trim ICV */ 293 /* Trim ICV */
293 skb_trim(skb, skb->len - TKIP_ICV_LEN); 294 skb_trim(skb, skb->len - IEEE80211_TKIP_ICV_LEN);
294 295
295 /* Remove IV */ 296 /* Remove IV */
296 memmove(skb->data + TKIP_IV_LEN, skb->data, hdrlen); 297 memmove(skb->data + IEEE80211_TKIP_IV_LEN, skb->data, hdrlen);
297 skb_pull(skb, TKIP_IV_LEN); 298 skb_pull(skb, IEEE80211_TKIP_IV_LEN);
298 299
299 return RX_CONTINUE; 300 return RX_CONTINUE;
300} 301}
@@ -337,9 +338,9 @@ static void ccmp_special_blocks(struct sk_buff *skb, u8 *pn, u8 *scratch,
337 else 338 else
338 qos_tid = 0; 339 qos_tid = 0;
339 340
340 data_len = skb->len - hdrlen - CCMP_HDR_LEN; 341 data_len = skb->len - hdrlen - IEEE80211_CCMP_HDR_LEN;
341 if (encrypted) 342 if (encrypted)
342 data_len -= CCMP_MIC_LEN; 343 data_len -= IEEE80211_CCMP_MIC_LEN;
343 344
344 /* First block, b_0 */ 345 /* First block, b_0 */
345 b_0[0] = 0x59; /* flags: Adata: 1, M: 011, L: 001 */ 346 b_0[0] = 0x59; /* flags: Adata: 1, M: 011, L: 001 */
@@ -348,7 +349,7 @@ static void ccmp_special_blocks(struct sk_buff *skb, u8 *pn, u8 *scratch,
348 */ 349 */
349 b_0[1] = qos_tid | (mgmt << 4); 350 b_0[1] = qos_tid | (mgmt << 4);
350 memcpy(&b_0[2], hdr->addr2, ETH_ALEN); 351 memcpy(&b_0[2], hdr->addr2, ETH_ALEN);
351 memcpy(&b_0[8], pn, CCMP_PN_LEN); 352 memcpy(&b_0[8], pn, IEEE80211_CCMP_PN_LEN);
352 /* l(m) */ 353 /* l(m) */
353 put_unaligned_be16(data_len, &b_0[14]); 354 put_unaligned_be16(data_len, &b_0[14]);
354 355
@@ -424,15 +425,16 @@ static int ccmp_encrypt_skb(struct ieee80211_tx_data *tx, struct sk_buff *skb)
424 if (info->control.hw_key) 425 if (info->control.hw_key)
425 tail = 0; 426 tail = 0;
426 else 427 else
427 tail = CCMP_MIC_LEN; 428 tail = IEEE80211_CCMP_MIC_LEN;
428 429
429 if (WARN_ON(skb_tailroom(skb) < tail || 430 if (WARN_ON(skb_tailroom(skb) < tail ||
430 skb_headroom(skb) < CCMP_HDR_LEN)) 431 skb_headroom(skb) < IEEE80211_CCMP_HDR_LEN))
431 return -1; 432 return -1;
432 433
433 pos = skb_push(skb, CCMP_HDR_LEN); 434 pos = skb_push(skb, IEEE80211_CCMP_HDR_LEN);
434 memmove(pos, pos + CCMP_HDR_LEN, hdrlen); 435 memmove(pos, pos + IEEE80211_CCMP_HDR_LEN, hdrlen);
435 skb_set_network_header(skb, skb_network_offset(skb) + CCMP_HDR_LEN); 436 skb_set_network_header(skb, skb_network_offset(skb) +
437 IEEE80211_CCMP_HDR_LEN);
436 438
437 /* the HW only needs room for the IV, but not the actual IV */ 439 /* the HW only needs room for the IV, but not the actual IV */
438 if (info->control.hw_key && 440 if (info->control.hw_key &&
@@ -457,10 +459,10 @@ static int ccmp_encrypt_skb(struct ieee80211_tx_data *tx, struct sk_buff *skb)
457 if (info->control.hw_key) 459 if (info->control.hw_key)
458 return 0; 460 return 0;
459 461
460 pos += CCMP_HDR_LEN; 462 pos += IEEE80211_CCMP_HDR_LEN;
461 ccmp_special_blocks(skb, pn, scratch, 0); 463 ccmp_special_blocks(skb, pn, scratch, 0);
462 ieee80211_aes_ccm_encrypt(key->u.ccmp.tfm, scratch, pos, len, 464 ieee80211_aes_ccm_encrypt(key->u.ccmp.tfm, scratch, pos, len,
463 pos, skb_put(skb, CCMP_MIC_LEN)); 465 pos, skb_put(skb, IEEE80211_CCMP_MIC_LEN));
464 466
465 return 0; 467 return 0;
466} 468}
@@ -490,7 +492,7 @@ ieee80211_crypto_ccmp_decrypt(struct ieee80211_rx_data *rx)
490 struct ieee80211_key *key = rx->key; 492 struct ieee80211_key *key = rx->key;
491 struct sk_buff *skb = rx->skb; 493 struct sk_buff *skb = rx->skb;
492 struct ieee80211_rx_status *status = IEEE80211_SKB_RXCB(skb); 494 struct ieee80211_rx_status *status = IEEE80211_SKB_RXCB(skb);
493 u8 pn[CCMP_PN_LEN]; 495 u8 pn[IEEE80211_CCMP_PN_LEN];
494 int data_len; 496 int data_len;
495 int queue; 497 int queue;
496 498
@@ -500,12 +502,13 @@ ieee80211_crypto_ccmp_decrypt(struct ieee80211_rx_data *rx)
500 !ieee80211_is_robust_mgmt_frame(hdr)) 502 !ieee80211_is_robust_mgmt_frame(hdr))
501 return RX_CONTINUE; 503 return RX_CONTINUE;
502 504
503 data_len = skb->len - hdrlen - CCMP_HDR_LEN - CCMP_MIC_LEN; 505 data_len = skb->len - hdrlen - IEEE80211_CCMP_HDR_LEN -
506 IEEE80211_CCMP_MIC_LEN;
504 if (!rx->sta || data_len < 0) 507 if (!rx->sta || data_len < 0)
505 return RX_DROP_UNUSABLE; 508 return RX_DROP_UNUSABLE;
506 509
507 if (status->flag & RX_FLAG_DECRYPTED) { 510 if (status->flag & RX_FLAG_DECRYPTED) {
508 if (!pskb_may_pull(rx->skb, hdrlen + CCMP_HDR_LEN)) 511 if (!pskb_may_pull(rx->skb, hdrlen + IEEE80211_CCMP_HDR_LEN))
509 return RX_DROP_UNUSABLE; 512 return RX_DROP_UNUSABLE;
510 } else { 513 } else {
511 if (skb_linearize(rx->skb)) 514 if (skb_linearize(rx->skb))
@@ -516,7 +519,7 @@ ieee80211_crypto_ccmp_decrypt(struct ieee80211_rx_data *rx)
516 519
517 queue = rx->security_idx; 520 queue = rx->security_idx;
518 521
519 if (memcmp(pn, key->u.ccmp.rx_pn[queue], CCMP_PN_LEN) <= 0) { 522 if (memcmp(pn, key->u.ccmp.rx_pn[queue], IEEE80211_CCMP_PN_LEN) <= 0) {
520 key->u.ccmp.replays++; 523 key->u.ccmp.replays++;
521 return RX_DROP_UNUSABLE; 524 return RX_DROP_UNUSABLE;
522 } 525 }
@@ -528,19 +531,20 @@ ieee80211_crypto_ccmp_decrypt(struct ieee80211_rx_data *rx)
528 531
529 if (ieee80211_aes_ccm_decrypt( 532 if (ieee80211_aes_ccm_decrypt(
530 key->u.ccmp.tfm, scratch, 533 key->u.ccmp.tfm, scratch,
531 skb->data + hdrlen + CCMP_HDR_LEN, data_len, 534 skb->data + hdrlen + IEEE80211_CCMP_HDR_LEN,
532 skb->data + skb->len - CCMP_MIC_LEN, 535 data_len,
533 skb->data + hdrlen + CCMP_HDR_LEN)) 536 skb->data + skb->len - IEEE80211_CCMP_MIC_LEN,
537 skb->data + hdrlen + IEEE80211_CCMP_HDR_LEN))
534 return RX_DROP_UNUSABLE; 538 return RX_DROP_UNUSABLE;
535 } 539 }
536 540
537 memcpy(key->u.ccmp.rx_pn[queue], pn, CCMP_PN_LEN); 541 memcpy(key->u.ccmp.rx_pn[queue], pn, IEEE80211_CCMP_PN_LEN);
538 542
539 /* Remove CCMP header and MIC */ 543 /* Remove CCMP header and MIC */
540 if (pskb_trim(skb, skb->len - CCMP_MIC_LEN)) 544 if (pskb_trim(skb, skb->len - IEEE80211_CCMP_MIC_LEN))
541 return RX_DROP_UNUSABLE; 545 return RX_DROP_UNUSABLE;
542 memmove(skb->data + CCMP_HDR_LEN, skb->data, hdrlen); 546 memmove(skb->data + IEEE80211_CCMP_HDR_LEN, skb->data, hdrlen);
543 skb_pull(skb, CCMP_HDR_LEN); 547 skb_pull(skb, IEEE80211_CCMP_HDR_LEN);
544 548
545 return RX_CONTINUE; 549 return RX_CONTINUE;
546} 550}