forked from ~ljy/RK356X_SDK_RELEASE

hc
2023-12-08 01573e231f18eb2d99162747186f59511f56b64d
kernel/drivers/net/wireless/broadcom/brcm80211/brcmfmac/cfg80211.c
....@@ -1,17 +1,6 @@
1
+// SPDX-License-Identifier: ISC
12 /*
23 * Copyright (c) 2010 Broadcom Corporation
3
- *
4
- * Permission to use, copy, modify, and/or distribute this software for any
5
- * purpose with or without fee is hereby granted, provided that the above
6
- * copyright notice and this permission notice appear in all copies.
7
- *
8
- * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
9
- * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
10
- * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY
11
- * SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
12
- * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION
13
- * OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN
14
- * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
154 */
165
176 /* Toplevel file. Relies on dhd_linux.c to send commands to the dongle. */
....@@ -22,6 +11,7 @@
2211 #include <linux/vmalloc.h>
2312 #include <net/cfg80211.h>
2413 #include <net/netlink.h>
14
+#include <uapi/linux/if_arp.h>
2515
2616 #include <brcmu_utils.h>
2717 #include <defs.h>
....@@ -33,6 +23,7 @@
3323 #include "p2p.h"
3424 #include "btcoex.h"
3525 #include "pno.h"
26
+#include "fwsignal.h"
3627 #include "cfg80211.h"
3728 #include "feature.h"
3829 #include "fwil.h"
....@@ -65,6 +56,7 @@
6556 #define RSN_AKM_PSK 2 /* Pre-shared Key */
6657 #define RSN_AKM_SHA256_1X 5 /* SHA256, 802.1X */
6758 #define RSN_AKM_SHA256_PSK 6 /* SHA256, Pre-shared Key */
59
+#define RSN_AKM_SAE 8 /* SAE */
6860 #define RSN_CAP_LEN 2 /* Length of RSN capabilities */
6961 #define RSN_CAP_PTK_REPLAY_CNTR_MASK (BIT(2) | BIT(3))
7062 #define RSN_CAP_MFPR_MASK BIT(6)
....@@ -92,6 +84,8 @@
9284 #define BRCMF_SCAN_PASSIVE_TIME 120
9385
9486 #define BRCMF_ND_INFO_TIMEOUT msecs_to_jiffies(2000)
87
+
88
+#define BRCMF_PS_MAX_TIMEOUT_MS 2000
9589
9690 #define BRCMF_ASSOC_PARAMS_FIXED_SIZE \
9791 (sizeof(struct brcmf_assoc_params_le) - sizeof(u16))
....@@ -200,9 +194,9 @@
200194 */
201195 REG_RULE(2484-10, 2484+10, 20, 6, 20, 0),
202196 /* IEEE 802.11a, channel 36..64 */
203
- REG_RULE(5150-10, 5350+10, 80, 6, 20, 0),
197
+ REG_RULE(5150-10, 5350+10, 160, 6, 20, 0),
204198 /* IEEE 802.11a, channel 100..165 */
205
- REG_RULE(5470-10, 5850+10, 80, 6, 20, 0), }
199
+ REG_RULE(5470-10, 5850+10, 160, 6, 20, 0), }
206200 };
207201
208202 /* Note: brcmf_cipher_suites is an array of int defining which cipher suites
....@@ -287,8 +281,26 @@
287281 else
288282 ch_inf.sb = BRCMU_CHAN_SB_UU;
289283 break;
290
- case NL80211_CHAN_WIDTH_80P80:
291284 case NL80211_CHAN_WIDTH_160:
285
+ ch_inf.bw = BRCMU_CHAN_BW_160;
286
+ if (primary_offset == -70)
287
+ ch_inf.sb = BRCMU_CHAN_SB_LLL;
288
+ else if (primary_offset == -50)
289
+ ch_inf.sb = BRCMU_CHAN_SB_LLU;
290
+ else if (primary_offset == -30)
291
+ ch_inf.sb = BRCMU_CHAN_SB_LUL;
292
+ else if (primary_offset == -10)
293
+ ch_inf.sb = BRCMU_CHAN_SB_LUU;
294
+ else if (primary_offset == 10)
295
+ ch_inf.sb = BRCMU_CHAN_SB_ULL;
296
+ else if (primary_offset == 30)
297
+ ch_inf.sb = BRCMU_CHAN_SB_ULU;
298
+ else if (primary_offset == 50)
299
+ ch_inf.sb = BRCMU_CHAN_SB_UUL;
300
+ else
301
+ ch_inf.sb = BRCMU_CHAN_SB_UUU;
302
+ break;
303
+ case NL80211_CHAN_WIDTH_80P80:
292304 case NL80211_CHAN_WIDTH_5:
293305 case NL80211_CHAN_WIDTH_10:
294306 default:
....@@ -307,6 +319,7 @@
307319 }
308320 d11inf->encchspec(&ch_inf);
309321
322
+ brcmf_dbg(TRACE, "chanspec: 0x%x\n", ch_inf.chspec);
310323 return ch_inf.chspec;
311324 }
312325
....@@ -457,6 +470,7 @@
457470 static int
458471 send_key_to_dongle(struct brcmf_if *ifp, struct brcmf_wsec_key *key)
459472 {
473
+ struct brcmf_pub *drvr = ifp->drvr;
460474 int err;
461475 struct brcmf_wsec_key_le key_le;
462476
....@@ -468,7 +482,7 @@
468482 sizeof(key_le));
469483
470484 if (err)
471
- brcmf_err("wsec_key error (%d)\n", err);
485
+ bphy_err(drvr, "wsec_key error (%d)\n", err);
472486 return err;
473487 }
474488
....@@ -508,6 +522,7 @@
508522
509523 static int brcmf_cfg80211_request_ap_if(struct brcmf_if *ifp)
510524 {
525
+ struct brcmf_pub *drvr = ifp->drvr;
511526 struct brcmf_mbss_ssid_le mbss_ssid_le;
512527 int bsscfgidx;
513528 int err;
....@@ -524,7 +539,7 @@
524539 err = brcmf_fil_bsscfg_data_set(ifp, "bsscfg:ssid", &mbss_ssid_le,
525540 sizeof(mbss_ssid_le));
526541 if (err < 0)
527
- brcmf_err("setting ssid failed %d\n", err);
542
+ bphy_err(drvr, "setting ssid failed %d\n", err);
528543
529544 return err;
530545 }
....@@ -542,6 +557,7 @@
542557 {
543558 struct brcmf_cfg80211_info *cfg = wiphy_to_cfg(wiphy);
544559 struct brcmf_if *ifp = netdev_priv(cfg_to_ndev(cfg));
560
+ struct brcmf_pub *drvr = cfg->pub;
545561 struct brcmf_cfg80211_vif *vif;
546562 int err;
547563
....@@ -567,7 +583,7 @@
567583 BRCMF_VIF_EVENT_TIMEOUT);
568584 brcmf_cfg80211_arm_vif_event(cfg, NULL);
569585 if (!err) {
570
- brcmf_err("timeout occurred\n");
586
+ bphy_err(drvr, "timeout occurred\n");
571587 err = -EIO;
572588 goto fail;
573589 }
....@@ -575,7 +591,7 @@
575591 /* interface created in firmware */
576592 ifp = vif->ifp;
577593 if (!ifp) {
578
- brcmf_err("no if pointer provided\n");
594
+ bphy_err(drvr, "no if pointer provided\n");
579595 err = -ENOENT;
580596 goto fail;
581597 }
....@@ -583,7 +599,7 @@
583599 strncpy(ifp->ndev->name, name, sizeof(ifp->ndev->name) - 1);
584600 err = brcmf_net_attach(ifp, true);
585601 if (err) {
586
- brcmf_err("Registering netdevice failed\n");
602
+ bphy_err(drvr, "Registering netdevice failed\n");
587603 free_netdev(ifp->ndev);
588604 goto fail;
589605 }
....@@ -608,19 +624,97 @@
608624 return vif->wdev.iftype == NL80211_IFTYPE_ADHOC;
609625 }
610626
627
+/**
628
+ * brcmf_mon_add_vif() - create monitor mode virtual interface
629
+ *
630
+ * @wiphy: wiphy device of new interface.
631
+ * @name: name of the new interface.
632
+ */
633
+static struct wireless_dev *brcmf_mon_add_vif(struct wiphy *wiphy,
634
+ const char *name)
635
+{
636
+ struct brcmf_cfg80211_info *cfg = wiphy_to_cfg(wiphy);
637
+ struct brcmf_cfg80211_vif *vif;
638
+ struct net_device *ndev;
639
+ struct brcmf_if *ifp;
640
+ int err;
641
+
642
+ if (cfg->pub->mon_if) {
643
+ err = -EEXIST;
644
+ goto err_out;
645
+ }
646
+
647
+ vif = brcmf_alloc_vif(cfg, NL80211_IFTYPE_MONITOR);
648
+ if (IS_ERR(vif)) {
649
+ err = PTR_ERR(vif);
650
+ goto err_out;
651
+ }
652
+
653
+ ndev = alloc_netdev(sizeof(*ifp), name, NET_NAME_UNKNOWN, ether_setup);
654
+ if (!ndev) {
655
+ err = -ENOMEM;
656
+ goto err_free_vif;
657
+ }
658
+ ndev->type = ARPHRD_IEEE80211_RADIOTAP;
659
+ ndev->ieee80211_ptr = &vif->wdev;
660
+ ndev->needs_free_netdev = true;
661
+ ndev->priv_destructor = brcmf_cfg80211_free_netdev;
662
+ SET_NETDEV_DEV(ndev, wiphy_dev(cfg->wiphy));
663
+
664
+ ifp = netdev_priv(ndev);
665
+ ifp->vif = vif;
666
+ ifp->ndev = ndev;
667
+ ifp->drvr = cfg->pub;
668
+
669
+ vif->ifp = ifp;
670
+ vif->wdev.netdev = ndev;
671
+
672
+ err = brcmf_net_mon_attach(ifp);
673
+ if (err) {
674
+ brcmf_err("Failed to attach %s device\n", ndev->name);
675
+ free_netdev(ndev);
676
+ goto err_free_vif;
677
+ }
678
+
679
+ cfg->pub->mon_if = ifp;
680
+
681
+ return &vif->wdev;
682
+
683
+err_free_vif:
684
+ brcmf_free_vif(vif);
685
+err_out:
686
+ return ERR_PTR(err);
687
+}
688
+
689
+static int brcmf_mon_del_vif(struct wiphy *wiphy, struct wireless_dev *wdev)
690
+{
691
+ struct brcmf_cfg80211_info *cfg = wiphy_to_cfg(wiphy);
692
+ struct net_device *ndev = wdev->netdev;
693
+
694
+ ndev->netdev_ops->ndo_stop(ndev);
695
+
696
+ brcmf_net_detach(ndev, true);
697
+
698
+ cfg->pub->mon_if = NULL;
699
+
700
+ return 0;
701
+}
702
+
611703 static struct wireless_dev *brcmf_cfg80211_add_iface(struct wiphy *wiphy,
612704 const char *name,
613705 unsigned char name_assign_type,
614706 enum nl80211_iftype type,
615707 struct vif_params *params)
616708 {
709
+ struct brcmf_cfg80211_info *cfg = wiphy_to_cfg(wiphy);
710
+ struct brcmf_pub *drvr = cfg->pub;
617711 struct wireless_dev *wdev;
618712 int err;
619713
620714 brcmf_dbg(TRACE, "enter: %s type %d\n", name, type);
621715 err = brcmf_vif_add_validate(wiphy_to_cfg(wiphy), type);
622716 if (err) {
623
- brcmf_err("iface validation failed: err=%d\n", err);
717
+ bphy_err(drvr, "iface validation failed: err=%d\n", err);
624718 return ERR_PTR(err);
625719 }
626720 switch (type) {
....@@ -628,9 +722,10 @@
628722 case NL80211_IFTYPE_STATION:
629723 case NL80211_IFTYPE_AP_VLAN:
630724 case NL80211_IFTYPE_WDS:
631
- case NL80211_IFTYPE_MONITOR:
632725 case NL80211_IFTYPE_MESH_POINT:
633726 return ERR_PTR(-EOPNOTSUPP);
727
+ case NL80211_IFTYPE_MONITOR:
728
+ return brcmf_mon_add_vif(wiphy, name);
634729 case NL80211_IFTYPE_AP:
635730 wdev = brcmf_ap_add_vif(wiphy, name, params);
636731 break;
....@@ -645,8 +740,8 @@
645740 }
646741
647742 if (IS_ERR(wdev))
648
- brcmf_err("add iface %s type %d failed: err=%d\n",
649
- name, type, (int)PTR_ERR(wdev));
743
+ bphy_err(drvr, "add iface %s type %d failed: err=%d\n", name,
744
+ type, (int)PTR_ERR(wdev));
650745 else
651746 brcmf_cfg80211_update_proto_addr_mode(wdev);
652747
....@@ -661,12 +756,13 @@
661756
662757 void brcmf_set_mpc(struct brcmf_if *ifp, int mpc)
663758 {
759
+ struct brcmf_pub *drvr = ifp->drvr;
664760 s32 err = 0;
665761
666762 if (check_vif_up(ifp->vif)) {
667763 err = brcmf_fil_iovar_int_set(ifp, "mpc", mpc);
668764 if (err) {
669
- brcmf_err("fail to set mpc\n");
765
+ bphy_err(drvr, "fail to set mpc\n");
670766 return;
671767 }
672768 brcmf_dbg(INFO, "MPC : %d\n", mpc);
....@@ -677,6 +773,7 @@
677773 struct brcmf_if *ifp, bool aborted,
678774 bool fw_abort)
679775 {
776
+ struct brcmf_pub *drvr = cfg->pub;
680777 struct brcmf_scan_params_le params_le;
681778 struct cfg80211_scan_request *scan_request;
682779 u64 reqid;
....@@ -711,7 +808,7 @@
711808 err = brcmf_fil_cmd_data_set(ifp, BRCMF_C_SCAN,
712809 &params_le, sizeof(params_le));
713810 if (err)
714
- brcmf_err("Scan abort failed\n");
811
+ bphy_err(drvr, "Scan abort failed\n");
715812 }
716813
717814 brcmf_scan_config_mpc(ifp, 1);
....@@ -756,6 +853,7 @@
756853 struct brcmf_cfg80211_info *cfg = wiphy_to_cfg(wiphy);
757854 struct net_device *ndev = wdev->netdev;
758855 struct brcmf_if *ifp = netdev_priv(ndev);
856
+ struct brcmf_pub *drvr = cfg->pub;
759857 int ret;
760858 int err;
761859
....@@ -763,7 +861,7 @@
763861
764862 err = brcmf_fil_bsscfg_data_set(ifp, "interface_remove", NULL, 0);
765863 if (err) {
766
- brcmf_err("interface_remove failed %d\n", err);
864
+ bphy_err(drvr, "interface_remove failed %d\n", err);
767865 goto err_unarm;
768866 }
769867
....@@ -771,7 +869,7 @@
771869 ret = brcmf_cfg80211_wait_vif_event(cfg, BRCMF_E_IF_DEL,
772870 BRCMF_VIF_EVENT_TIMEOUT);
773871 if (!ret) {
774
- brcmf_err("timeout occurred\n");
872
+ bphy_err(drvr, "timeout occurred\n");
775873 err = -EIO;
776874 goto err_unarm;
777875 }
....@@ -810,9 +908,10 @@
810908 case NL80211_IFTYPE_STATION:
811909 case NL80211_IFTYPE_AP_VLAN:
812910 case NL80211_IFTYPE_WDS:
813
- case NL80211_IFTYPE_MONITOR:
814911 case NL80211_IFTYPE_MESH_POINT:
815912 return -EOPNOTSUPP;
913
+ case NL80211_IFTYPE_MONITOR:
914
+ return brcmf_mon_del_vif(wiphy, wdev);
816915 case NL80211_IFTYPE_AP:
817916 return brcmf_cfg80211_del_ap_iface(wiphy, wdev);
818917 case NL80211_IFTYPE_P2P_CLIENT:
....@@ -834,6 +933,7 @@
834933 struct brcmf_cfg80211_info *cfg = wiphy_to_cfg(wiphy);
835934 struct brcmf_if *ifp = netdev_priv(ndev);
836935 struct brcmf_cfg80211_vif *vif = ifp->vif;
936
+ struct brcmf_pub *drvr = cfg->pub;
837937 s32 infra = 0;
838938 s32 ap = 0;
839939 s32 err = 0;
....@@ -873,14 +973,14 @@
873973 }
874974 err = brcmf_vif_change_validate(wiphy_to_cfg(wiphy), vif, type);
875975 if (err) {
876
- brcmf_err("iface validation failed: err=%d\n", err);
976
+ bphy_err(drvr, "iface validation failed: err=%d\n", err);
877977 return err;
878978 }
879979 switch (type) {
880980 case NL80211_IFTYPE_MONITOR:
881981 case NL80211_IFTYPE_WDS:
882
- brcmf_err("type (%d) : currently we do not support this type\n",
883
- type);
982
+ bphy_err(drvr, "type (%d) : currently we do not support this type\n",
983
+ type);
884984 return -EOPNOTSUPP;
885985 case NL80211_IFTYPE_ADHOC:
886986 infra = 0;
....@@ -908,7 +1008,7 @@
9081008 } else {
9091009 err = brcmf_fil_cmd_int_set(ifp, BRCMF_C_SET_INFRA, infra);
9101010 if (err) {
911
- brcmf_err("WLC_SET_INFRA error (%d)\n", err);
1011
+ bphy_err(drvr, "WLC_SET_INFRA error (%d)\n", err);
9121012 err = -EAGAIN;
9131013 goto done;
9141014 }
....@@ -999,6 +1099,7 @@
9991099 brcmf_run_escan(struct brcmf_cfg80211_info *cfg, struct brcmf_if *ifp,
10001100 struct cfg80211_scan_request *request)
10011101 {
1102
+ struct brcmf_pub *drvr = cfg->pub;
10021103 s32 params_size = BRCMF_SCAN_PARAMS_FIXED_SIZE +
10031104 offsetof(struct brcmf_escan_params_le, params_le);
10041105 struct brcmf_escan_params_le *params;
....@@ -1030,7 +1131,7 @@
10301131 if (err == -EBUSY)
10311132 brcmf_dbg(INFO, "system busy : escan canceled\n");
10321133 else
1033
- brcmf_err("error (%d)\n", err);
1134
+ bphy_err(drvr, "error (%d)\n", err);
10341135 }
10351136
10361137 kfree(params);
....@@ -1067,6 +1168,7 @@
10671168 brcmf_cfg80211_scan(struct wiphy *wiphy, struct cfg80211_scan_request *request)
10681169 {
10691170 struct brcmf_cfg80211_info *cfg = wiphy_to_cfg(wiphy);
1171
+ struct brcmf_pub *drvr = cfg->pub;
10701172 struct brcmf_cfg80211_vif *vif;
10711173 s32 err = 0;
10721174
....@@ -1076,21 +1178,22 @@
10761178 return -EIO;
10771179
10781180 if (test_bit(BRCMF_SCAN_STATUS_BUSY, &cfg->scan_status)) {
1079
- brcmf_err("Scanning already: status (%lu)\n", cfg->scan_status);
1181
+ bphy_err(drvr, "Scanning already: status (%lu)\n",
1182
+ cfg->scan_status);
10801183 return -EAGAIN;
10811184 }
10821185 if (test_bit(BRCMF_SCAN_STATUS_ABORT, &cfg->scan_status)) {
1083
- brcmf_err("Scanning being aborted: status (%lu)\n",
1084
- cfg->scan_status);
1186
+ bphy_err(drvr, "Scanning being aborted: status (%lu)\n",
1187
+ cfg->scan_status);
10851188 return -EAGAIN;
10861189 }
10871190 if (test_bit(BRCMF_SCAN_STATUS_SUPPRESS, &cfg->scan_status)) {
1088
- brcmf_err("Scanning suppressed: status (%lu)\n",
1089
- cfg->scan_status);
1191
+ bphy_err(drvr, "Scanning suppressed: status (%lu)\n",
1192
+ cfg->scan_status);
10901193 return -EAGAIN;
10911194 }
10921195 if (test_bit(BRCMF_VIF_STATUS_CONNECTING, &vif->sme_state)) {
1093
- brcmf_err("Connecting: status (%lu)\n", vif->sme_state);
1196
+ bphy_err(drvr, "Connecting: status (%lu)\n", vif->sme_state);
10941197 return -EAGAIN;
10951198 }
10961199
....@@ -1124,7 +1227,7 @@
11241227 return 0;
11251228
11261229 scan_out:
1127
- brcmf_err("scan error (%d)\n", err);
1230
+ bphy_err(drvr, "scan error (%d)\n", err);
11281231 clear_bit(BRCMF_SCAN_STATUS_BUSY, &cfg->scan_status);
11291232 cfg->scan_request = NULL;
11301233 return err;
....@@ -1132,36 +1235,41 @@
11321235
11331236 static s32 brcmf_set_rts(struct net_device *ndev, u32 rts_threshold)
11341237 {
1238
+ struct brcmf_if *ifp = netdev_priv(ndev);
1239
+ struct brcmf_pub *drvr = ifp->drvr;
11351240 s32 err = 0;
11361241
1137
- err = brcmf_fil_iovar_int_set(netdev_priv(ndev), "rtsthresh",
1138
- rts_threshold);
1242
+ err = brcmf_fil_iovar_int_set(ifp, "rtsthresh", rts_threshold);
11391243 if (err)
1140
- brcmf_err("Error (%d)\n", err);
1244
+ bphy_err(drvr, "Error (%d)\n", err);
11411245
11421246 return err;
11431247 }
11441248
11451249 static s32 brcmf_set_frag(struct net_device *ndev, u32 frag_threshold)
11461250 {
1251
+ struct brcmf_if *ifp = netdev_priv(ndev);
1252
+ struct brcmf_pub *drvr = ifp->drvr;
11471253 s32 err = 0;
11481254
1149
- err = brcmf_fil_iovar_int_set(netdev_priv(ndev), "fragthresh",
1255
+ err = brcmf_fil_iovar_int_set(ifp, "fragthresh",
11501256 frag_threshold);
11511257 if (err)
1152
- brcmf_err("Error (%d)\n", err);
1258
+ bphy_err(drvr, "Error (%d)\n", err);
11531259
11541260 return err;
11551261 }
11561262
11571263 static s32 brcmf_set_retry(struct net_device *ndev, u32 retry, bool l)
11581264 {
1265
+ struct brcmf_if *ifp = netdev_priv(ndev);
1266
+ struct brcmf_pub *drvr = ifp->drvr;
11591267 s32 err = 0;
11601268 u32 cmd = (l ? BRCMF_C_SET_LRL : BRCMF_C_SET_SRL);
11611269
1162
- err = brcmf_fil_cmd_int_set(netdev_priv(ndev), cmd, retry);
1270
+ err = brcmf_fil_cmd_int_set(ifp, cmd, retry);
11631271 if (err) {
1164
- brcmf_err("cmd (%d) , error (%d)\n", cmd, err);
1272
+ bphy_err(drvr, "cmd (%d) , error (%d)\n", cmd, err);
11651273 return err;
11661274 }
11671275 return err;
....@@ -1237,6 +1345,7 @@
12371345
12381346 static int brcmf_set_pmk(struct brcmf_if *ifp, const u8 *pmk_data, u16 pmk_len)
12391347 {
1348
+ struct brcmf_pub *drvr = ifp->drvr;
12401349 struct brcmf_wsec_pmk_le pmk;
12411350 int i, err;
12421351
....@@ -1250,36 +1359,68 @@
12501359 err = brcmf_fil_cmd_data_set(ifp, BRCMF_C_SET_WSEC_PMK,
12511360 &pmk, sizeof(pmk));
12521361 if (err < 0)
1253
- brcmf_err("failed to change PSK in firmware (len=%u)\n",
1254
- pmk_len);
1362
+ bphy_err(drvr, "failed to change PSK in firmware (len=%u)\n",
1363
+ pmk_len);
12551364
12561365 return err;
12571366 }
12581367
1259
-static void brcmf_link_down(struct brcmf_cfg80211_vif *vif, u16 reason)
1368
+static int brcmf_set_sae_password(struct brcmf_if *ifp, const u8 *pwd_data,
1369
+ u16 pwd_len)
1370
+{
1371
+ struct brcmf_pub *drvr = ifp->drvr;
1372
+ struct brcmf_wsec_sae_pwd_le sae_pwd;
1373
+ int err;
1374
+
1375
+ if (pwd_len > BRCMF_WSEC_MAX_SAE_PASSWORD_LEN) {
1376
+ bphy_err(drvr, "sae_password must be less than %d\n",
1377
+ BRCMF_WSEC_MAX_SAE_PASSWORD_LEN);
1378
+ return -EINVAL;
1379
+ }
1380
+
1381
+ sae_pwd.key_len = cpu_to_le16(pwd_len);
1382
+ memcpy(sae_pwd.key, pwd_data, pwd_len);
1383
+
1384
+ err = brcmf_fil_iovar_data_set(ifp, "sae_password", &sae_pwd,
1385
+ sizeof(sae_pwd));
1386
+ if (err < 0)
1387
+ bphy_err(drvr, "failed to set SAE password in firmware (len=%u)\n",
1388
+ pwd_len);
1389
+
1390
+ return err;
1391
+}
1392
+
1393
+static void brcmf_link_down(struct brcmf_cfg80211_vif *vif, u16 reason,
1394
+ bool locally_generated)
12601395 {
12611396 struct brcmf_cfg80211_info *cfg = wiphy_to_cfg(vif->wdev.wiphy);
1397
+ struct brcmf_pub *drvr = cfg->pub;
1398
+ bool bus_up = drvr->bus_if->state == BRCMF_BUS_UP;
12621399 s32 err = 0;
12631400
12641401 brcmf_dbg(TRACE, "Enter\n");
12651402
12661403 if (test_and_clear_bit(BRCMF_VIF_STATUS_CONNECTED, &vif->sme_state)) {
1267
- brcmf_dbg(INFO, "Call WLC_DISASSOC to stop excess roaming\n");
1268
- err = brcmf_fil_cmd_data_set(vif->ifp,
1269
- BRCMF_C_DISASSOC, NULL, 0);
1270
- if (err) {
1271
- brcmf_err("WLC_DISASSOC failed (%d)\n", err);
1404
+ if (bus_up) {
1405
+ brcmf_dbg(INFO, "Call WLC_DISASSOC to stop excess roaming\n");
1406
+ err = brcmf_fil_cmd_data_set(vif->ifp,
1407
+ BRCMF_C_DISASSOC, NULL, 0);
1408
+ if (err)
1409
+ bphy_err(drvr, "WLC_DISASSOC failed (%d)\n",
1410
+ err);
12721411 }
1412
+
12731413 if ((vif->wdev.iftype == NL80211_IFTYPE_STATION) ||
12741414 (vif->wdev.iftype == NL80211_IFTYPE_P2P_CLIENT))
12751415 cfg80211_disconnected(vif->wdev.netdev, reason, NULL, 0,
1276
- true, GFP_KERNEL);
1416
+ locally_generated, GFP_KERNEL);
12771417 }
12781418 clear_bit(BRCMF_VIF_STATUS_CONNECTING, &vif->sme_state);
12791419 clear_bit(BRCMF_SCAN_STATUS_SUPPRESS, &cfg->scan_status);
12801420 brcmf_btcoex_set_mode(vif, BRCMF_BTCOEX_ENABLED, 0);
12811421 if (vif->profile.use_fwsup != BRCMF_PROFILE_FWSUP_NONE) {
1282
- brcmf_set_pmk(vif->ifp, NULL, 0);
1422
+ if (bus_up)
1423
+ brcmf_set_pmk(vif->ifp, NULL, 0);
12831424 vif->profile.use_fwsup = BRCMF_PROFILE_FWSUP_NONE;
12841425 }
12851426 brcmf_dbg(TRACE, "Exit\n");
....@@ -1292,6 +1433,7 @@
12921433 struct brcmf_cfg80211_info *cfg = wiphy_to_cfg(wiphy);
12931434 struct brcmf_if *ifp = netdev_priv(ndev);
12941435 struct brcmf_cfg80211_profile *profile = &ifp->vif->profile;
1436
+ struct brcmf_pub *drvr = cfg->pub;
12951437 struct brcmf_join_params join_params;
12961438 size_t join_params_size = 0;
12971439 s32 err = 0;
....@@ -1356,7 +1498,7 @@
13561498
13571499 err = brcmf_fil_iovar_int_set(ifp, "wsec", wsec);
13581500 if (err) {
1359
- brcmf_err("wsec failed (%d)\n", err);
1501
+ bphy_err(drvr, "wsec failed (%d)\n", err);
13601502 goto done;
13611503 }
13621504
....@@ -1368,7 +1510,7 @@
13681510
13691511 err = brcmf_fil_cmd_int_set(ifp, BRCMF_C_SET_BCNPRD, bcnprd);
13701512 if (err) {
1371
- brcmf_err("WLC_SET_BCNPRD failed (%d)\n", err);
1513
+ bphy_err(drvr, "WLC_SET_BCNPRD failed (%d)\n", err);
13721514 goto done;
13731515 }
13741516
....@@ -1413,7 +1555,7 @@
14131555 err = brcmf_fil_cmd_int_set(ifp, BRCMF_C_SET_CHANNEL,
14141556 target_channel);
14151557 if (err) {
1416
- brcmf_err("WLC_SET_CHANNEL failed (%d)\n", err);
1558
+ bphy_err(drvr, "WLC_SET_CHANNEL failed (%d)\n", err);
14171559 goto done;
14181560 }
14191561 } else
....@@ -1425,7 +1567,7 @@
14251567 err = brcmf_fil_cmd_data_set(ifp, BRCMF_C_SET_SSID,
14261568 &join_params, join_params_size);
14271569 if (err) {
1428
- brcmf_err("WLC_SET_SSID failed (%d)\n", err);
1570
+ bphy_err(drvr, "WLC_SET_SSID failed (%d)\n", err);
14291571 goto done;
14301572 }
14311573
....@@ -1450,7 +1592,7 @@
14501592 return 0;
14511593 }
14521594
1453
- brcmf_link_down(ifp->vif, WLAN_REASON_DEAUTH_LEAVING);
1595
+ brcmf_link_down(ifp->vif, WLAN_REASON_DEAUTH_LEAVING, true);
14541596 brcmf_net_setcarrier(ifp, false);
14551597
14561598 brcmf_dbg(TRACE, "Exit\n");
....@@ -1461,7 +1603,9 @@
14611603 static s32 brcmf_set_wpa_version(struct net_device *ndev,
14621604 struct cfg80211_connect_params *sme)
14631605 {
1606
+ struct brcmf_if *ifp = netdev_priv(ndev);
14641607 struct brcmf_cfg80211_profile *profile = ndev_to_prof(ndev);
1608
+ struct brcmf_pub *drvr = ifp->drvr;
14651609 struct brcmf_cfg80211_security *sec;
14661610 s32 val = 0;
14671611 s32 err = 0;
....@@ -1470,12 +1614,14 @@
14701614 val = WPA_AUTH_PSK | WPA_AUTH_UNSPECIFIED;
14711615 else if (sme->crypto.wpa_versions & NL80211_WPA_VERSION_2)
14721616 val = WPA2_AUTH_PSK | WPA2_AUTH_UNSPECIFIED;
1617
+ else if (sme->crypto.wpa_versions & NL80211_WPA_VERSION_3)
1618
+ val = WPA3_AUTH_SAE_PSK;
14731619 else
14741620 val = WPA_AUTH_DISABLED;
14751621 brcmf_dbg(CONN, "setting wpa_auth to 0x%0x\n", val);
1476
- err = brcmf_fil_bsscfg_int_set(netdev_priv(ndev), "wpa_auth", val);
1622
+ err = brcmf_fil_bsscfg_int_set(ifp, "wpa_auth", val);
14771623 if (err) {
1478
- brcmf_err("set wpa_auth failed (%d)\n", err);
1624
+ bphy_err(drvr, "set wpa_auth failed (%d)\n", err);
14791625 return err;
14801626 }
14811627 sec = &profile->sec;
....@@ -1486,7 +1632,9 @@
14861632 static s32 brcmf_set_auth_type(struct net_device *ndev,
14871633 struct cfg80211_connect_params *sme)
14881634 {
1635
+ struct brcmf_if *ifp = netdev_priv(ndev);
14891636 struct brcmf_cfg80211_profile *profile = ndev_to_prof(ndev);
1637
+ struct brcmf_pub *drvr = ifp->drvr;
14901638 struct brcmf_cfg80211_security *sec;
14911639 s32 val = 0;
14921640 s32 err = 0;
....@@ -1500,15 +1648,19 @@
15001648 val = 1;
15011649 brcmf_dbg(CONN, "shared key\n");
15021650 break;
1651
+ case NL80211_AUTHTYPE_SAE:
1652
+ val = 3;
1653
+ brcmf_dbg(CONN, "SAE authentication\n");
1654
+ break;
15031655 default:
15041656 val = 2;
15051657 brcmf_dbg(CONN, "automatic, auth type (%d)\n", sme->auth_type);
15061658 break;
15071659 }
15081660
1509
- err = brcmf_fil_bsscfg_int_set(netdev_priv(ndev), "auth", val);
1661
+ err = brcmf_fil_bsscfg_int_set(ifp, "auth", val);
15101662 if (err) {
1511
- brcmf_err("set auth failed (%d)\n", err);
1663
+ bphy_err(drvr, "set auth failed (%d)\n", err);
15121664 return err;
15131665 }
15141666 sec = &profile->sec;
....@@ -1520,7 +1672,9 @@
15201672 brcmf_set_wsec_mode(struct net_device *ndev,
15211673 struct cfg80211_connect_params *sme)
15221674 {
1675
+ struct brcmf_if *ifp = netdev_priv(ndev);
15231676 struct brcmf_cfg80211_profile *profile = ndev_to_prof(ndev);
1677
+ struct brcmf_pub *drvr = ifp->drvr;
15241678 struct brcmf_cfg80211_security *sec;
15251679 s32 pval = 0;
15261680 s32 gval = 0;
....@@ -1543,8 +1697,8 @@
15431697 pval = AES_ENABLED;
15441698 break;
15451699 default:
1546
- brcmf_err("invalid cipher pairwise (%d)\n",
1547
- sme->crypto.ciphers_pairwise[0]);
1700
+ bphy_err(drvr, "invalid cipher pairwise (%d)\n",
1701
+ sme->crypto.ciphers_pairwise[0]);
15481702 return -EINVAL;
15491703 }
15501704 }
....@@ -1564,8 +1718,8 @@
15641718 gval = AES_ENABLED;
15651719 break;
15661720 default:
1567
- brcmf_err("invalid cipher group (%d)\n",
1568
- sme->crypto.cipher_group);
1721
+ bphy_err(drvr, "invalid cipher group (%d)\n",
1722
+ sme->crypto.cipher_group);
15691723 return -EINVAL;
15701724 }
15711725 }
....@@ -1578,9 +1732,9 @@
15781732 pval = AES_ENABLED;
15791733
15801734 wsec = pval | gval;
1581
- err = brcmf_fil_bsscfg_int_set(netdev_priv(ndev), "wsec", wsec);
1735
+ err = brcmf_fil_bsscfg_int_set(ifp, "wsec", wsec);
15821736 if (err) {
1583
- brcmf_err("error (%d)\n", err);
1737
+ bphy_err(drvr, "error (%d)\n", err);
15841738 return err;
15851739 }
15861740
....@@ -1596,6 +1750,7 @@
15961750 {
15971751 struct brcmf_if *ifp = netdev_priv(ndev);
15981752 struct brcmf_cfg80211_profile *profile = &ifp->vif->profile;
1753
+ struct brcmf_pub *drvr = ifp->drvr;
15991754 s32 val;
16001755 s32 err;
16011756 const struct brcmf_tlv *rsn_ie;
....@@ -1607,13 +1762,14 @@
16071762 u16 count;
16081763
16091764 profile->use_fwsup = BRCMF_PROFILE_FWSUP_NONE;
1765
+ profile->is_ft = false;
16101766
16111767 if (!sme->crypto.n_akm_suites)
16121768 return 0;
16131769
16141770 err = brcmf_fil_bsscfg_int_get(netdev_priv(ndev), "wpa_auth", &val);
16151771 if (err) {
1616
- brcmf_err("could not get wpa_auth (%d)\n", err);
1772
+ bphy_err(drvr, "could not get wpa_auth (%d)\n", err);
16171773 return err;
16181774 }
16191775 if (val & (WPA_AUTH_PSK | WPA_AUTH_UNSPECIFIED)) {
....@@ -1627,8 +1783,8 @@
16271783 val = WPA_AUTH_PSK;
16281784 break;
16291785 default:
1630
- brcmf_err("invalid cipher group (%d)\n",
1631
- sme->crypto.cipher_group);
1786
+ bphy_err(drvr, "invalid cipher group (%d)\n",
1787
+ sme->crypto.cipher_group);
16321788 return -EINVAL;
16331789 }
16341790 } else if (val & (WPA2_AUTH_PSK | WPA2_AUTH_UNSPECIFIED)) {
....@@ -1649,9 +1805,33 @@
16491805 case WLAN_AKM_SUITE_PSK:
16501806 val = WPA2_AUTH_PSK;
16511807 break;
1808
+ case WLAN_AKM_SUITE_FT_8021X:
1809
+ val = WPA2_AUTH_UNSPECIFIED | WPA2_AUTH_FT;
1810
+ profile->is_ft = true;
1811
+ if (sme->want_1x)
1812
+ profile->use_fwsup = BRCMF_PROFILE_FWSUP_1X;
1813
+ break;
1814
+ case WLAN_AKM_SUITE_FT_PSK:
1815
+ val = WPA2_AUTH_PSK | WPA2_AUTH_FT;
1816
+ profile->is_ft = true;
1817
+ break;
16521818 default:
1653
- brcmf_err("invalid cipher group (%d)\n",
1654
- sme->crypto.cipher_group);
1819
+ bphy_err(drvr, "invalid cipher group (%d)\n",
1820
+ sme->crypto.cipher_group);
1821
+ return -EINVAL;
1822
+ }
1823
+ } else if (val & WPA3_AUTH_SAE_PSK) {
1824
+ switch (sme->crypto.akm_suites[0]) {
1825
+ case WLAN_AKM_SUITE_SAE:
1826
+ val = WPA3_AUTH_SAE_PSK;
1827
+ if (sme->crypto.sae_pwd) {
1828
+ brcmf_dbg(INFO, "using SAE offload\n");
1829
+ profile->use_fwsup = BRCMF_PROFILE_FWSUP_SAE;
1830
+ }
1831
+ break;
1832
+ default:
1833
+ bphy_err(drvr, "invalid cipher group (%d)\n",
1834
+ sme->crypto.cipher_group);
16551835 return -EINVAL;
16561836 }
16571837 }
....@@ -1697,7 +1877,7 @@
16971877 brcmf_dbg(CONN, "setting wpa_auth to %d\n", val);
16981878 err = brcmf_fil_bsscfg_int_set(netdev_priv(ndev), "wpa_auth", val);
16991879 if (err) {
1700
- brcmf_err("could not set wpa_auth (%d)\n", err);
1880
+ bphy_err(drvr, "could not set wpa_auth (%d)\n", err);
17011881 return err;
17021882 }
17031883
....@@ -1708,6 +1888,8 @@
17081888 brcmf_set_sharedkey(struct net_device *ndev,
17091889 struct cfg80211_connect_params *sme)
17101890 {
1891
+ struct brcmf_if *ifp = netdev_priv(ndev);
1892
+ struct brcmf_pub *drvr = ifp->drvr;
17111893 struct brcmf_cfg80211_profile *profile = ndev_to_prof(ndev);
17121894 struct brcmf_cfg80211_security *sec;
17131895 struct brcmf_wsec_key key;
....@@ -1723,7 +1905,8 @@
17231905 brcmf_dbg(CONN, "wpa_versions 0x%x cipher_pairwise 0x%x\n",
17241906 sec->wpa_versions, sec->cipher_pairwise);
17251907
1726
- if (sec->wpa_versions & (NL80211_WPA_VERSION_1 | NL80211_WPA_VERSION_2))
1908
+ if (sec->wpa_versions & (NL80211_WPA_VERSION_1 | NL80211_WPA_VERSION_2 |
1909
+ NL80211_WPA_VERSION_3))
17271910 return 0;
17281911
17291912 if (!(sec->cipher_pairwise &
....@@ -1734,7 +1917,7 @@
17341917 key.len = (u32) sme->key_len;
17351918 key.index = (u32) sme->key_idx;
17361919 if (key.len > sizeof(key.data)) {
1737
- brcmf_err("Too long key length (%u)\n", key.len);
1920
+ bphy_err(drvr, "Too long key length (%u)\n", key.len);
17381921 return -EINVAL;
17391922 }
17401923 memcpy(key.data, sme->key, key.len);
....@@ -1747,24 +1930,24 @@
17471930 key.algo = CRYPTO_ALGO_WEP128;
17481931 break;
17491932 default:
1750
- brcmf_err("Invalid algorithm (%d)\n",
1751
- sme->crypto.ciphers_pairwise[0]);
1933
+ bphy_err(drvr, "Invalid algorithm (%d)\n",
1934
+ sme->crypto.ciphers_pairwise[0]);
17521935 return -EINVAL;
17531936 }
17541937 /* Set the new key/index */
17551938 brcmf_dbg(CONN, "key length (%d) key index (%d) algo (%d)\n",
17561939 key.len, key.index, key.algo);
17571940 brcmf_dbg(CONN, "key \"%s\"\n", key.data);
1758
- err = send_key_to_dongle(netdev_priv(ndev), &key);
1941
+ err = send_key_to_dongle(ifp, &key);
17591942 if (err)
17601943 return err;
17611944
17621945 if (sec->auth_type == NL80211_AUTHTYPE_SHARED_KEY) {
17631946 brcmf_dbg(CONN, "set auth_type to shared key\n");
17641947 val = WL_AUTH_SHARED_KEY; /* shared key */
1765
- err = brcmf_fil_bsscfg_int_set(netdev_priv(ndev), "auth", val);
1948
+ err = brcmf_fil_bsscfg_int_set(ifp, "auth", val);
17661949 if (err)
1767
- brcmf_err("set auth failed (%d)\n", err);
1950
+ bphy_err(drvr, "set auth failed (%d)\n", err);
17681951 }
17691952 return err;
17701953 }
....@@ -1784,6 +1967,7 @@
17841967 static void brcmf_set_join_pref(struct brcmf_if *ifp,
17851968 struct cfg80211_bss_selection *bss_select)
17861969 {
1970
+ struct brcmf_pub *drvr = ifp->drvr;
17871971 struct brcmf_join_pref_params join_pref_params[2];
17881972 enum nl80211_band band;
17891973 int err, i = 0;
....@@ -1822,7 +2006,7 @@
18222006 err = brcmf_fil_iovar_data_set(ifp, "join_pref", join_pref_params,
18232007 sizeof(join_pref_params));
18242008 if (err)
1825
- brcmf_err("Set join_pref error (%d)\n", err);
2009
+ bphy_err(drvr, "Set join_pref error (%d)\n", err);
18262010 }
18272011
18282012 static s32
....@@ -1833,6 +2017,7 @@
18332017 struct brcmf_if *ifp = netdev_priv(ndev);
18342018 struct brcmf_cfg80211_profile *profile = &ifp->vif->profile;
18352019 struct ieee80211_channel *chan = sme->channel;
2020
+ struct brcmf_pub *drvr = ifp->drvr;
18362021 struct brcmf_join_params join_params;
18372022 size_t join_params_size;
18382023 const struct brcmf_tlv *rsn_ie;
....@@ -1849,7 +2034,7 @@
18492034 return -EIO;
18502035
18512036 if (!sme->ssid) {
1852
- brcmf_err("Invalid ssid\n");
2037
+ bphy_err(drvr, "Invalid ssid\n");
18532038 return -EOPNOTSUPP;
18542039 }
18552040
....@@ -1878,7 +2063,7 @@
18782063 err = brcmf_vif_set_mgmt_ie(ifp->vif, BRCMF_VNDR_IE_ASSOCREQ_FLAG,
18792064 sme->ie, sme->ie_len);
18802065 if (err)
1881
- brcmf_err("Set Assoc REQ IE Failed\n");
2066
+ bphy_err(drvr, "Set Assoc REQ IE Failed\n");
18822067 else
18832068 brcmf_dbg(TRACE, "Applied Vndr IEs for Assoc request\n");
18842069
....@@ -1899,36 +2084,37 @@
18992084
19002085 err = brcmf_set_wpa_version(ndev, sme);
19012086 if (err) {
1902
- brcmf_err("wl_set_wpa_version failed (%d)\n", err);
2087
+ bphy_err(drvr, "wl_set_wpa_version failed (%d)\n", err);
19032088 goto done;
19042089 }
19052090
19062091 sme->auth_type = brcmf_war_auth_type(ifp, sme->auth_type);
19072092 err = brcmf_set_auth_type(ndev, sme);
19082093 if (err) {
1909
- brcmf_err("wl_set_auth_type failed (%d)\n", err);
2094
+ bphy_err(drvr, "wl_set_auth_type failed (%d)\n", err);
19102095 goto done;
19112096 }
19122097
19132098 err = brcmf_set_wsec_mode(ndev, sme);
19142099 if (err) {
1915
- brcmf_err("wl_set_set_cipher failed (%d)\n", err);
2100
+ bphy_err(drvr, "wl_set_set_cipher failed (%d)\n", err);
19162101 goto done;
19172102 }
19182103
19192104 err = brcmf_set_key_mgmt(ndev, sme);
19202105 if (err) {
1921
- brcmf_err("wl_set_key_mgmt failed (%d)\n", err);
2106
+ bphy_err(drvr, "wl_set_key_mgmt failed (%d)\n", err);
19222107 goto done;
19232108 }
19242109
19252110 err = brcmf_set_sharedkey(ndev, sme);
19262111 if (err) {
1927
- brcmf_err("brcmf_set_sharedkey failed (%d)\n", err);
2112
+ bphy_err(drvr, "brcmf_set_sharedkey failed (%d)\n", err);
19282113 goto done;
19292114 }
19302115
1931
- if (sme->crypto.psk) {
2116
+ if (sme->crypto.psk &&
2117
+ profile->use_fwsup != BRCMF_PROFILE_FWSUP_SAE) {
19322118 if (WARN_ON(profile->use_fwsup != BRCMF_PROFILE_FWSUP_NONE)) {
19332119 err = -EINVAL;
19342120 goto done;
....@@ -1941,17 +2127,29 @@
19412127 /* enable firmware supplicant for this interface */
19422128 err = brcmf_fil_iovar_int_set(ifp, "sup_wpa", 1);
19432129 if (err < 0) {
1944
- brcmf_err("failed to enable fw supplicant\n");
2130
+ bphy_err(drvr, "failed to enable fw supplicant\n");
19452131 goto done;
19462132 }
19472133 }
19482134
1949
- if (profile->use_fwsup == BRCMF_PROFILE_FWSUP_PSK) {
2135
+ if (profile->use_fwsup == BRCMF_PROFILE_FWSUP_PSK)
19502136 err = brcmf_set_pmk(ifp, sme->crypto.psk,
19512137 BRCMF_WSEC_MAX_PSK_LEN);
1952
- if (err)
2138
+ else if (profile->use_fwsup == BRCMF_PROFILE_FWSUP_SAE) {
2139
+ /* clean up user-space RSNE */
2140
+ err = brcmf_fil_iovar_data_set(ifp, "wpaie", NULL, 0);
2141
+ if (err) {
2142
+ bphy_err(drvr, "failed to clean up user-space RSNE\n");
19532143 goto done;
2144
+ }
2145
+ err = brcmf_set_sae_password(ifp, sme->crypto.sae_pwd,
2146
+ sme->crypto.sae_pwd_len);
2147
+ if (!err && sme->crypto.psk)
2148
+ err = brcmf_set_pmk(ifp, sme->crypto.psk,
2149
+ BRCMF_WSEC_MAX_PSK_LEN);
19542150 }
2151
+ if (err)
2152
+ goto done;
19552153
19562154 /* Join with specific BSSID and cached SSID
19572155 * If SSID is zero join based on BSSID only
....@@ -2036,7 +2234,7 @@
20362234 err = brcmf_fil_cmd_data_set(ifp, BRCMF_C_SET_SSID,
20372235 &join_params, join_params_size);
20382236 if (err)
2039
- brcmf_err("BRCMF_C_SET_SSID failed (%d)\n", err);
2237
+ bphy_err(drvr, "BRCMF_C_SET_SSID failed (%d)\n", err);
20402238
20412239 done:
20422240 if (err)
....@@ -2049,8 +2247,10 @@
20492247 brcmf_cfg80211_disconnect(struct wiphy *wiphy, struct net_device *ndev,
20502248 u16 reason_code)
20512249 {
2250
+ struct brcmf_cfg80211_info *cfg = wiphy_to_cfg(wiphy);
20522251 struct brcmf_if *ifp = netdev_priv(ndev);
20532252 struct brcmf_cfg80211_profile *profile = &ifp->vif->profile;
2253
+ struct brcmf_pub *drvr = cfg->pub;
20542254 struct brcmf_scb_val_le scbval;
20552255 s32 err = 0;
20562256
....@@ -2067,7 +2267,7 @@
20672267 err = brcmf_fil_cmd_data_set(ifp, BRCMF_C_DISASSOC,
20682268 &scbval, sizeof(scbval));
20692269 if (err)
2070
- brcmf_err("error (%d)\n", err);
2270
+ bphy_err(drvr, "error (%d)\n", err);
20712271
20722272 brcmf_dbg(TRACE, "Exit\n");
20732273 return err;
....@@ -2080,6 +2280,7 @@
20802280 struct brcmf_cfg80211_info *cfg = wiphy_to_cfg(wiphy);
20812281 struct net_device *ndev = cfg_to_ndev(cfg);
20822282 struct brcmf_if *ifp = netdev_priv(ndev);
2283
+ struct brcmf_pub *drvr = cfg->pub;
20832284 s32 err;
20842285 s32 disable;
20852286 u32 qdbm = 127;
....@@ -2094,7 +2295,7 @@
20942295 case NL80211_TX_POWER_LIMITED:
20952296 case NL80211_TX_POWER_FIXED:
20962297 if (mbm < 0) {
2097
- brcmf_err("TX_POWER_FIXED - dbm is negative\n");
2298
+ bphy_err(drvr, "TX_POWER_FIXED - dbm is negative\n");
20982299 err = -EINVAL;
20992300 goto done;
21002301 }
....@@ -2104,7 +2305,7 @@
21042305 qdbm |= WL_TXPWR_OVERRIDE;
21052306 break;
21062307 default:
2107
- brcmf_err("Unsupported type %d\n", type);
2308
+ bphy_err(drvr, "Unsupported type %d\n", type);
21082309 err = -EINVAL;
21092310 goto done;
21102311 }
....@@ -2112,11 +2313,11 @@
21122313 disable = WL_RADIO_SW_DISABLE << 16;
21132314 err = brcmf_fil_cmd_int_set(ifp, BRCMF_C_SET_RADIO, disable);
21142315 if (err)
2115
- brcmf_err("WLC_SET_RADIO error (%d)\n", err);
2316
+ bphy_err(drvr, "WLC_SET_RADIO error (%d)\n", err);
21162317
21172318 err = brcmf_fil_iovar_int_set(ifp, "qtxpower", qdbm);
21182319 if (err)
2119
- brcmf_err("qtxpower error (%d)\n", err);
2320
+ bphy_err(drvr, "qtxpower error (%d)\n", err);
21202321
21212322 done:
21222323 brcmf_dbg(TRACE, "Exit %d (qdbm)\n", qdbm & ~WL_TXPWR_OVERRIDE);
....@@ -2127,7 +2328,9 @@
21272328 brcmf_cfg80211_get_tx_power(struct wiphy *wiphy, struct wireless_dev *wdev,
21282329 s32 *dbm)
21292330 {
2331
+ struct brcmf_cfg80211_info *cfg = wiphy_to_cfg(wiphy);
21302332 struct brcmf_cfg80211_vif *vif = wdev_to_vif(wdev);
2333
+ struct brcmf_pub *drvr = cfg->pub;
21312334 s32 qdbm = 0;
21322335 s32 err;
21332336
....@@ -2137,7 +2340,7 @@
21372340
21382341 err = brcmf_fil_iovar_int_get(vif->ifp, "qtxpower", &qdbm);
21392342 if (err) {
2140
- brcmf_err("error (%d)\n", err);
2343
+ bphy_err(drvr, "error (%d)\n", err);
21412344 goto done;
21422345 }
21432346 *dbm = (qdbm & ~WL_TXPWR_OVERRIDE) / 4;
....@@ -2152,6 +2355,7 @@
21522355 u8 key_idx, bool unicast, bool multicast)
21532356 {
21542357 struct brcmf_if *ifp = netdev_priv(ndev);
2358
+ struct brcmf_pub *drvr = ifp->drvr;
21552359 u32 index;
21562360 u32 wsec;
21572361 s32 err = 0;
....@@ -2163,7 +2367,7 @@
21632367
21642368 err = brcmf_fil_bsscfg_int_get(ifp, "wsec", &wsec);
21652369 if (err) {
2166
- brcmf_err("WLC_GET_WSEC error (%d)\n", err);
2370
+ bphy_err(drvr, "WLC_GET_WSEC error (%d)\n", err);
21672371 goto done;
21682372 }
21692373
....@@ -2173,7 +2377,7 @@
21732377 err = brcmf_fil_cmd_int_set(ifp,
21742378 BRCMF_C_SET_KEY_PRIMARY, index);
21752379 if (err)
2176
- brcmf_err("error (%d)\n", err);
2380
+ bphy_err(drvr, "error (%d)\n", err);
21772381 }
21782382 done:
21792383 brcmf_dbg(TRACE, "Exit\n");
....@@ -2222,7 +2426,9 @@
22222426 u8 key_idx, bool pairwise, const u8 *mac_addr,
22232427 struct key_params *params)
22242428 {
2429
+ struct brcmf_cfg80211_info *cfg = wiphy_to_cfg(wiphy);
22252430 struct brcmf_if *ifp = netdev_priv(ndev);
2431
+ struct brcmf_pub *drvr = cfg->pub;
22262432 struct brcmf_wsec_key *key;
22272433 s32 val;
22282434 s32 wsec;
....@@ -2237,7 +2443,7 @@
22372443
22382444 if (key_idx >= BRCMF_MAX_DEFAULT_KEYS) {
22392445 /* we ignore this key index in this case */
2240
- brcmf_err("invalid key index (%d)\n", key_idx);
2446
+ bphy_err(drvr, "invalid key index (%d)\n", key_idx);
22412447 return -EINVAL;
22422448 }
22432449
....@@ -2246,7 +2452,7 @@
22462452 mac_addr);
22472453
22482454 if (params->key_len > sizeof(key->data)) {
2249
- brcmf_err("Too long key length (%u)\n", params->key_len);
2455
+ bphy_err(drvr, "Too long key length (%u)\n", params->key_len);
22502456 return -EINVAL;
22512457 }
22522458
....@@ -2266,6 +2472,17 @@
22662472 memcpy(key->data, params->key, key->len);
22672473 if (!ext_key)
22682474 key->flags = BRCMF_PRIMARY_KEY;
2475
+
2476
+ if (params->seq && params->seq_len == 6) {
2477
+ /* rx iv */
2478
+ u8 *ivptr;
2479
+
2480
+ ivptr = (u8 *)params->seq;
2481
+ key->rxiv.hi = (ivptr[5] << 24) | (ivptr[4] << 16) |
2482
+ (ivptr[3] << 8) | ivptr[2];
2483
+ key->rxiv.lo = (ivptr[1] << 8) | ivptr[0];
2484
+ key->iv_initialized = true;
2485
+ }
22692486
22702487 switch (params->cipher) {
22712488 case WLAN_CIPHER_SUITE_WEP40:
....@@ -2300,7 +2517,7 @@
23002517 brcmf_dbg(CONN, "WLAN_CIPHER_SUITE_CCMP\n");
23012518 break;
23022519 default:
2303
- brcmf_err("Invalid cipher (0x%x)\n", params->cipher);
2520
+ bphy_err(drvr, "Invalid cipher (0x%x)\n", params->cipher);
23042521 err = -EINVAL;
23052522 goto done;
23062523 }
....@@ -2311,13 +2528,13 @@
23112528
23122529 err = brcmf_fil_bsscfg_int_get(ifp, "wsec", &wsec);
23132530 if (err) {
2314
- brcmf_err("get wsec error (%d)\n", err);
2531
+ bphy_err(drvr, "get wsec error (%d)\n", err);
23152532 goto done;
23162533 }
23172534 wsec |= val;
23182535 err = brcmf_fil_bsscfg_int_set(ifp, "wsec", wsec);
23192536 if (err) {
2320
- brcmf_err("set wsec error (%d)\n", err);
2537
+ bphy_err(drvr, "set wsec error (%d)\n", err);
23212538 goto done;
23222539 }
23232540
....@@ -2332,9 +2549,11 @@
23322549 void (*callback)(void *cookie,
23332550 struct key_params *params))
23342551 {
2552
+ struct brcmf_cfg80211_info *cfg = wiphy_to_cfg(wiphy);
23352553 struct key_params params;
23362554 struct brcmf_if *ifp = netdev_priv(ndev);
23372555 struct brcmf_cfg80211_profile *profile = &ifp->vif->profile;
2556
+ struct brcmf_pub *drvr = cfg->pub;
23382557 struct brcmf_cfg80211_security *sec;
23392558 s32 wsec;
23402559 s32 err = 0;
....@@ -2348,7 +2567,7 @@
23482567
23492568 err = brcmf_fil_bsscfg_int_get(ifp, "wsec", &wsec);
23502569 if (err) {
2351
- brcmf_err("WLC_GET_WSEC error (%d)\n", err);
2570
+ bphy_err(drvr, "WLC_GET_WSEC error (%d)\n", err);
23522571 /* Ignore this error, may happen during DISASSOC */
23532572 err = -EAGAIN;
23542573 goto done;
....@@ -2369,7 +2588,7 @@
23692588 params.cipher = WLAN_CIPHER_SUITE_AES_CMAC;
23702589 brcmf_dbg(CONN, "WLAN_CIPHER_SUITE_AES_CMAC\n");
23712590 } else {
2372
- brcmf_err("Invalid algo (0x%x)\n", wsec);
2591
+ bphy_err(drvr, "Invalid algo (0x%x)\n", wsec);
23732592 err = -EINVAL;
23742593 goto done;
23752594 }
....@@ -2399,6 +2618,7 @@
23992618 static void
24002619 brcmf_cfg80211_reconfigure_wep(struct brcmf_if *ifp)
24012620 {
2621
+ struct brcmf_pub *drvr = ifp->drvr;
24022622 s32 err;
24032623 u8 key_idx;
24042624 struct brcmf_wsec_key *key;
....@@ -2415,18 +2635,18 @@
24152635
24162636 err = send_key_to_dongle(ifp, key);
24172637 if (err) {
2418
- brcmf_err("Setting WEP key failed (%d)\n", err);
2638
+ bphy_err(drvr, "Setting WEP key failed (%d)\n", err);
24192639 return;
24202640 }
24212641 err = brcmf_fil_bsscfg_int_get(ifp, "wsec", &wsec);
24222642 if (err) {
2423
- brcmf_err("get wsec error (%d)\n", err);
2643
+ bphy_err(drvr, "get wsec error (%d)\n", err);
24242644 return;
24252645 }
24262646 wsec |= WEP_ENABLED;
24272647 err = brcmf_fil_bsscfg_int_set(ifp, "wsec", wsec);
24282648 if (err)
2429
- brcmf_err("set wsec error (%d)\n", err);
2649
+ bphy_err(drvr, "set wsec error (%d)\n", err);
24302650 }
24312651
24322652 static void brcmf_convert_sta_flags(u32 fw_sta_flags, struct station_info *si)
....@@ -2452,6 +2672,7 @@
24522672
24532673 static void brcmf_fill_bss_param(struct brcmf_if *ifp, struct station_info *si)
24542674 {
2675
+ struct brcmf_pub *drvr = ifp->drvr;
24552676 struct {
24562677 __le32 len;
24572678 struct brcmf_bss_info_le bss_le;
....@@ -2467,7 +2688,7 @@
24672688 err = brcmf_fil_cmd_data_get(ifp, BRCMF_C_GET_BSS_INFO, buf,
24682689 WL_BSS_INFO_MAX);
24692690 if (err) {
2470
- brcmf_err("Failed to get bss info (%d)\n", err);
2691
+ bphy_err(drvr, "Failed to get bss info (%d)\n", err);
24712692 goto out_kfree;
24722693 }
24732694 si->filled |= BIT_ULL(NL80211_STA_INFO_BSS_PARAM);
....@@ -2489,6 +2710,7 @@
24892710 brcmf_cfg80211_get_station_ibss(struct brcmf_if *ifp,
24902711 struct station_info *sinfo)
24912712 {
2713
+ struct brcmf_pub *drvr = ifp->drvr;
24922714 struct brcmf_scb_val_le scbval;
24932715 struct brcmf_pktcnt_le pktcnt;
24942716 s32 err;
....@@ -2498,7 +2720,7 @@
24982720 /* Get the current tx rate */
24992721 err = brcmf_fil_cmd_int_get(ifp, BRCMF_C_GET_RATE, &rate);
25002722 if (err < 0) {
2501
- brcmf_err("BRCMF_C_GET_RATE error (%d)\n", err);
2723
+ bphy_err(drvr, "BRCMF_C_GET_RATE error (%d)\n", err);
25022724 return err;
25032725 }
25042726 sinfo->filled |= BIT_ULL(NL80211_STA_INFO_TX_BITRATE);
....@@ -2508,7 +2730,7 @@
25082730 err = brcmf_fil_cmd_data_get(ifp, BRCMF_C_GET_RSSI, &scbval,
25092731 sizeof(scbval));
25102732 if (err) {
2511
- brcmf_err("BRCMF_C_GET_RSSI error (%d)\n", err);
2733
+ bphy_err(drvr, "BRCMF_C_GET_RSSI error (%d)\n", err);
25122734 return err;
25132735 }
25142736 rssi = le32_to_cpu(scbval.val);
....@@ -2518,7 +2740,7 @@
25182740 err = brcmf_fil_cmd_data_get(ifp, BRCMF_C_GET_GET_PKTCNTS, &pktcnt,
25192741 sizeof(pktcnt));
25202742 if (err) {
2521
- brcmf_err("BRCMF_C_GET_GET_PKTCNTS error (%d)\n", err);
2743
+ bphy_err(drvr, "BRCMF_C_GET_GET_PKTCNTS error (%d)\n", err);
25222744 return err;
25232745 }
25242746 sinfo->filled |= BIT_ULL(NL80211_STA_INFO_RX_PACKETS) |
....@@ -2537,7 +2759,9 @@
25372759 brcmf_cfg80211_get_station(struct wiphy *wiphy, struct net_device *ndev,
25382760 const u8 *mac, struct station_info *sinfo)
25392761 {
2762
+ struct brcmf_cfg80211_info *cfg = wiphy_to_cfg(wiphy);
25402763 struct brcmf_if *ifp = netdev_priv(ndev);
2764
+ struct brcmf_pub *drvr = cfg->pub;
25412765 struct brcmf_scb_val_le scb_val;
25422766 s32 err = 0;
25432767 struct brcmf_sta_info_le sta_info_le;
....@@ -2567,7 +2791,7 @@
25672791 &sta_info_le,
25682792 sizeof(sta_info_le));
25692793 if (err < 0) {
2570
- brcmf_err("GET STA INFO failed, %d\n", err);
2794
+ bphy_err(drvr, "GET STA INFO failed, %d\n", err);
25712795 goto done;
25722796 }
25732797 }
....@@ -2638,7 +2862,8 @@
26382862 err = brcmf_fil_cmd_data_get(ifp, BRCMF_C_GET_RSSI,
26392863 &scb_val, sizeof(scb_val));
26402864 if (err) {
2641
- brcmf_err("Could not get rssi (%d)\n", err);
2865
+ bphy_err(drvr, "Could not get rssi (%d)\n",
2866
+ err);
26422867 goto done;
26432868 } else {
26442869 rssi = le32_to_cpu(scb_val.val);
....@@ -2659,6 +2884,7 @@
26592884 {
26602885 struct brcmf_cfg80211_info *cfg = wiphy_to_cfg(wiphy);
26612886 struct brcmf_if *ifp = netdev_priv(ndev);
2887
+ struct brcmf_pub *drvr = cfg->pub;
26622888 s32 err;
26632889
26642890 brcmf_dbg(TRACE, "Enter, idx %d\n", idx);
....@@ -2669,8 +2895,8 @@
26692895 &cfg->assoclist,
26702896 sizeof(cfg->assoclist));
26712897 if (err) {
2672
- brcmf_err("BRCMF_C_GET_ASSOCLIST unsupported, err=%d\n",
2673
- err);
2898
+ bphy_err(drvr, "BRCMF_C_GET_ASSOCLIST unsupported, err=%d\n",
2899
+ err);
26742900 cfg->assoclist.count = 0;
26752901 return -EOPNOTSUPP;
26762902 }
....@@ -2690,6 +2916,7 @@
26902916 s32 err = 0;
26912917 struct brcmf_cfg80211_info *cfg = wiphy_to_cfg(wiphy);
26922918 struct brcmf_if *ifp = netdev_priv(ndev);
2919
+ struct brcmf_pub *drvr = cfg->pub;
26932920
26942921 brcmf_dbg(TRACE, "Enter\n");
26952922
....@@ -2718,10 +2945,16 @@
27182945 err = brcmf_fil_cmd_int_set(ifp, BRCMF_C_SET_PM, pm);
27192946 if (err) {
27202947 if (err == -ENODEV)
2721
- brcmf_err("net_device is not ready yet\n");
2948
+ bphy_err(drvr, "net_device is not ready yet\n");
27222949 else
2723
- brcmf_err("error (%d)\n", err);
2950
+ bphy_err(drvr, "error (%d)\n", err);
27242951 }
2952
+
2953
+ err = brcmf_fil_iovar_int_set(ifp, "pm2_sleep_ret",
2954
+ min_t(u32, timeout, BRCMF_PS_MAX_TIMEOUT_MS));
2955
+ if (err)
2956
+ bphy_err(drvr, "Unable to set pm timeout, (%d)\n", err);
2957
+
27252958 done:
27262959 brcmf_dbg(TRACE, "Exit\n");
27272960 return err;
....@@ -2731,6 +2964,7 @@
27312964 struct brcmf_bss_info_le *bi)
27322965 {
27332966 struct wiphy *wiphy = cfg_to_wiphy(cfg);
2967
+ struct brcmf_pub *drvr = cfg->pub;
27342968 struct cfg80211_bss *bss;
27352969 enum nl80211_band band;
27362970 struct brcmu_chan ch;
....@@ -2743,8 +2977,8 @@
27432977 struct cfg80211_inform_bss bss_data = {};
27442978
27452979 if (le32_to_cpu(bi->length) > WL_BSS_INFO_MAX) {
2746
- brcmf_err("Bss info is larger than buffer. Discarding\n");
2747
- return 0;
2980
+ bphy_err(drvr, "Bss info is larger than buffer. Discarding\n");
2981
+ return -EINVAL;
27482982 }
27492983
27502984 if (!bi->ctl_ch) {
....@@ -2802,6 +3036,7 @@
28023036
28033037 static s32 brcmf_inform_bss(struct brcmf_cfg80211_info *cfg)
28043038 {
3039
+ struct brcmf_pub *drvr = cfg->pub;
28053040 struct brcmf_scan_results *bss_list;
28063041 struct brcmf_bss_info_le *bi = NULL; /* must be initialized */
28073042 s32 err = 0;
....@@ -2810,8 +3045,8 @@
28103045 bss_list = (struct brcmf_scan_results *)cfg->escan_info.escan_buf;
28113046 if (bss_list->count != 0 &&
28123047 bss_list->version != BRCMF_BSS_INFO_VERSION) {
2813
- brcmf_err("Version %d != WL_BSS_INFO_VERSION\n",
2814
- bss_list->version);
3048
+ bphy_err(drvr, "Version %d != WL_BSS_INFO_VERSION\n",
3049
+ bss_list->version);
28153050 return -EOPNOTSUPP;
28163051 }
28173052 brcmf_dbg(SCAN, "scanned AP count (%d)\n", bss_list->count);
....@@ -2828,6 +3063,7 @@
28283063 struct net_device *ndev, const u8 *bssid)
28293064 {
28303065 struct wiphy *wiphy = cfg_to_wiphy(cfg);
3066
+ struct brcmf_pub *drvr = cfg->pub;
28313067 struct ieee80211_channel *notify_channel;
28323068 struct brcmf_bss_info_le *bi = NULL;
28333069 struct ieee80211_supported_band *band;
....@@ -2855,7 +3091,7 @@
28553091 err = brcmf_fil_cmd_data_get(netdev_priv(ndev), BRCMF_C_GET_BSS_INFO,
28563092 buf, WL_BSS_INFO_MAX);
28573093 if (err) {
2858
- brcmf_err("WLC_GET_BSS_INFO failed: %d\n", err);
3094
+ bphy_err(drvr, "WLC_GET_BSS_INFO failed: %d\n", err);
28593095 goto CleanUp;
28603096 }
28613097
....@@ -2909,10 +3145,9 @@
29093145 static s32 brcmf_update_bss_info(struct brcmf_cfg80211_info *cfg,
29103146 struct brcmf_if *ifp)
29113147 {
3148
+ struct brcmf_pub *drvr = cfg->pub;
29123149 struct brcmf_bss_info_le *bi;
29133150 const struct brcmf_tlv *tim;
2914
- u16 beacon_interval;
2915
- u8 dtim_period;
29163151 size_t ie_len;
29173152 u8 *ie;
29183153 s32 err = 0;
....@@ -2925,7 +3160,7 @@
29253160 err = brcmf_fil_cmd_data_get(ifp, BRCMF_C_GET_BSS_INFO,
29263161 cfg->extra_buf, WL_EXTRA_BUF_MAX);
29273162 if (err) {
2928
- brcmf_err("Could not get bss info %d\n", err);
3163
+ bphy_err(drvr, "Could not get bss info %d\n", err);
29293164 goto update_bss_info_out;
29303165 }
29313166
....@@ -2936,12 +3171,9 @@
29363171
29373172 ie = ((u8 *)bi) + le16_to_cpu(bi->ie_offset);
29383173 ie_len = le32_to_cpu(bi->ie_length);
2939
- beacon_interval = le16_to_cpu(bi->beacon_period);
29403174
29413175 tim = brcmf_parse_tlvs(ie, ie_len, WLAN_EID_TIM);
2942
- if (tim)
2943
- dtim_period = tim->data[1];
2944
- else {
3176
+ if (!tim) {
29453177 /*
29463178 * active scan was done so we could not get dtim
29473179 * information out of probe response.
....@@ -2950,10 +3182,9 @@
29503182 u32 var;
29513183 err = brcmf_fil_iovar_int_get(ifp, "dtim_assoc", &var);
29523184 if (err) {
2953
- brcmf_err("wl dtim_assoc failed (%d)\n", err);
3185
+ bphy_err(drvr, "wl dtim_assoc failed (%d)\n", err);
29543186 goto update_bss_info_out;
29553187 }
2956
- dtim_period = (u8)var;
29573188 }
29583189
29593190 update_bss_info_out:
....@@ -2988,9 +3219,10 @@
29883219 {
29893220 struct brcmf_cfg80211_info *cfg =
29903221 from_timer(cfg, t, escan_timeout);
3222
+ struct brcmf_pub *drvr = cfg->pub;
29913223
29923224 if (cfg->int_escan_map || cfg->scan_request) {
2993
- brcmf_err("timer expired\n");
3225
+ bphy_err(drvr, "timer expired\n");
29943226 schedule_work(&cfg->escan_timeout_work);
29953227 }
29963228 }
....@@ -3038,7 +3270,8 @@
30383270 brcmf_cfg80211_escan_handler(struct brcmf_if *ifp,
30393271 const struct brcmf_event_msg *e, void *data)
30403272 {
3041
- struct brcmf_cfg80211_info *cfg = ifp->drvr->config;
3273
+ struct brcmf_pub *drvr = ifp->drvr;
3274
+ struct brcmf_cfg80211_info *cfg = drvr->config;
30423275 s32 status;
30433276 struct brcmf_escan_result_le *escan_result_le;
30443277 u32 escan_buflen;
....@@ -3055,32 +3288,33 @@
30553288 goto exit;
30563289
30573290 if (!test_bit(BRCMF_SCAN_STATUS_BUSY, &cfg->scan_status)) {
3058
- brcmf_err("scan not ready, bsscfgidx=%d\n", ifp->bsscfgidx);
3291
+ bphy_err(drvr, "scan not ready, bsscfgidx=%d\n",
3292
+ ifp->bsscfgidx);
30593293 return -EPERM;
30603294 }
30613295
30623296 if (status == BRCMF_E_STATUS_PARTIAL) {
30633297 brcmf_dbg(SCAN, "ESCAN Partial result\n");
30643298 if (e->datalen < sizeof(*escan_result_le)) {
3065
- brcmf_err("invalid event data length\n");
3299
+ bphy_err(drvr, "invalid event data length\n");
30663300 goto exit;
30673301 }
30683302 escan_result_le = (struct brcmf_escan_result_le *) data;
30693303 if (!escan_result_le) {
3070
- brcmf_err("Invalid escan result (NULL pointer)\n");
3304
+ bphy_err(drvr, "Invalid escan result (NULL pointer)\n");
30713305 goto exit;
30723306 }
30733307 escan_buflen = le32_to_cpu(escan_result_le->buflen);
30743308 if (escan_buflen > BRCMF_ESCAN_BUF_SIZE ||
30753309 escan_buflen > e->datalen ||
30763310 escan_buflen < sizeof(*escan_result_le)) {
3077
- brcmf_err("Invalid escan buffer length: %d\n",
3078
- escan_buflen);
3311
+ bphy_err(drvr, "Invalid escan buffer length: %d\n",
3312
+ escan_buflen);
30793313 goto exit;
30803314 }
30813315 if (le16_to_cpu(escan_result_le->bss_count) != 1) {
3082
- brcmf_err("Invalid bss_count %d: ignoring\n",
3083
- escan_result_le->bss_count);
3316
+ bphy_err(drvr, "Invalid bss_count %d: ignoring\n",
3317
+ escan_result_le->bss_count);
30843318 goto exit;
30853319 }
30863320 bss_info_le = &escan_result_le->bss_info_le;
....@@ -3095,8 +3329,8 @@
30953329
30963330 bi_length = le32_to_cpu(bss_info_le->length);
30973331 if (bi_length != escan_buflen - WL_ESCAN_RESULTS_FIXED_SIZE) {
3098
- brcmf_err("Ignoring invalid bss_info length: %d\n",
3099
- bi_length);
3332
+ bphy_err(drvr, "Ignoring invalid bss_info length: %d\n",
3333
+ bi_length);
31003334 goto exit;
31013335 }
31023336
....@@ -3104,7 +3338,7 @@
31043338 BIT(NL80211_IFTYPE_ADHOC))) {
31053339 if (le16_to_cpu(bss_info_le->capability) &
31063340 WLAN_CAPABILITY_IBSS) {
3107
- brcmf_err("Ignoring IBSS result\n");
3341
+ bphy_err(drvr, "Ignoring IBSS result\n");
31083342 goto exit;
31093343 }
31103344 }
....@@ -3112,7 +3346,7 @@
31123346 list = (struct brcmf_scan_results *)
31133347 cfg->escan_info.escan_buf;
31143348 if (bi_length > BRCMF_ESCAN_BUF_SIZE - list->buflen) {
3115
- brcmf_err("Buffer is too small: ignoring\n");
3349
+ bphy_err(drvr, "Buffer is too small: ignoring\n");
31163350 goto exit;
31173351 }
31183352
....@@ -3248,7 +3482,7 @@
32483482 switch (pfn_v1->version) {
32493483 default:
32503484 WARN_ON(1);
3251
- /* fall-thru */
3485
+ fallthrough;
32523486 case cpu_to_le32(1):
32533487 netinfo = (struct brcmf_pno_net_info_le *)(pfn_v1 + 1);
32543488 break;
....@@ -3271,7 +3505,8 @@
32713505 brcmf_notify_sched_scan_results(struct brcmf_if *ifp,
32723506 const struct brcmf_event_msg *e, void *data)
32733507 {
3274
- struct brcmf_cfg80211_info *cfg = ifp->drvr->config;
3508
+ struct brcmf_pub *drvr = ifp->drvr;
3509
+ struct brcmf_cfg80211_info *cfg = drvr->config;
32753510 struct brcmf_pno_net_info_le *netinfo, *netinfo_start;
32763511 struct cfg80211_scan_request *request = NULL;
32773512 struct wiphy *wiphy = cfg_to_wiphy(cfg);
....@@ -3304,14 +3539,14 @@
33043539 WARN_ON(status != BRCMF_PNO_SCAN_COMPLETE);
33053540 brcmf_dbg(SCAN, "PFN NET FOUND event. count: %d\n", result_count);
33063541 if (!result_count) {
3307
- brcmf_err("FALSE PNO Event. (pfn_count == 0)\n");
3542
+ bphy_err(drvr, "FALSE PNO Event. (pfn_count == 0)\n");
33083543 goto out_err;
33093544 }
33103545
33113546 netinfo_start = brcmf_get_netinfo_array(pfn_result);
33123547 datalen = e->datalen - ((void *)netinfo_start - (void *)pfn_result);
33133548 if (datalen < result_count * sizeof(*netinfo)) {
3314
- brcmf_err("insufficient event data\n");
3549
+ bphy_err(drvr, "insufficient event data\n");
33153550 goto out_err;
33163551 }
33173552
....@@ -3358,15 +3593,16 @@
33583593 struct net_device *ndev,
33593594 struct cfg80211_sched_scan_request *req)
33603595 {
3361
- struct brcmf_if *ifp = netdev_priv(ndev);
33623596 struct brcmf_cfg80211_info *cfg = wiphy_to_cfg(wiphy);
3597
+ struct brcmf_if *ifp = netdev_priv(ndev);
3598
+ struct brcmf_pub *drvr = cfg->pub;
33633599
33643600 brcmf_dbg(SCAN, "Enter: n_match_sets=%d n_ssids=%d\n",
33653601 req->n_match_sets, req->n_ssids);
33663602
33673603 if (test_bit(BRCMF_SCAN_STATUS_SUPPRESS, &cfg->scan_status)) {
3368
- brcmf_err("Scanning suppressed: status=%lu\n",
3369
- cfg->scan_status);
3604
+ bphy_err(drvr, "Scanning suppressed: status=%lu\n",
3605
+ cfg->scan_status);
33703606 return -EAGAIN;
33713607 }
33723608
....@@ -3444,7 +3680,8 @@
34443680 brcmf_wowl_nd_results(struct brcmf_if *ifp, const struct brcmf_event_msg *e,
34453681 void *data)
34463682 {
3447
- struct brcmf_cfg80211_info *cfg = ifp->drvr->config;
3683
+ struct brcmf_pub *drvr = ifp->drvr;
3684
+ struct brcmf_cfg80211_info *cfg = drvr->config;
34483685 struct brcmf_pno_scanresults_le *pfn_result;
34493686 struct brcmf_pno_net_info_le *netinfo;
34503687
....@@ -3463,8 +3700,8 @@
34633700 }
34643701
34653702 if (le32_to_cpu(pfn_result->count) < 1) {
3466
- brcmf_err("Invalid result count, expected 1 (%d)\n",
3467
- le32_to_cpu(pfn_result->count));
3703
+ bphy_err(drvr, "Invalid result count, expected 1 (%d)\n",
3704
+ le32_to_cpu(pfn_result->count));
34683705 return -EINVAL;
34693706 }
34703707
....@@ -3493,6 +3730,7 @@
34933730 static void brcmf_report_wowl_wakeind(struct wiphy *wiphy, struct brcmf_if *ifp)
34943731 {
34953732 struct brcmf_cfg80211_info *cfg = wiphy_to_cfg(wiphy);
3733
+ struct brcmf_pub *drvr = cfg->pub;
34963734 struct brcmf_wowl_wakeind_le wake_ind_le;
34973735 struct cfg80211_wowlan_wakeup wakeup_data;
34983736 struct cfg80211_wowlan_wakeup *wakeup;
....@@ -3503,7 +3741,7 @@
35033741 err = brcmf_fil_iovar_data_get(ifp, "wowl_wakeind", &wake_ind_le,
35043742 sizeof(wake_ind_le));
35053743 if (err) {
3506
- brcmf_err("Get wowl_wakeind failed, err = %d\n", err);
3744
+ bphy_err(drvr, "Get wowl_wakeind failed, err = %d\n", err);
35073745 return;
35083746 }
35093747
....@@ -3544,7 +3782,7 @@
35443782 cfg->wowl.nd_data_completed,
35453783 BRCMF_ND_INFO_TIMEOUT);
35463784 if (!timeout)
3547
- brcmf_err("No result for wowl net detect\n");
3785
+ bphy_err(drvr, "No result for wowl net detect\n");
35483786 else
35493787 wakeup_data.net_detect = cfg->wowl.nd_info;
35503788 }
....@@ -3683,7 +3921,7 @@
36833921 * disassociate from AP to save power while system is
36843922 * in suspended state
36853923 */
3686
- brcmf_link_down(vif, WLAN_REASON_UNSPECIFIED);
3924
+ brcmf_link_down(vif, WLAN_REASON_UNSPECIFIED, true);
36873925 /* Make sure WPA_Supplicant receives all the event
36883926 * generated due to DISASSOC call to the fw to keep
36893927 * the state fw and WPA_Supplicant state consistent
....@@ -3733,6 +3971,7 @@
37333971 struct brcmf_cfg80211_info *cfg = wiphy_to_cfg(wiphy);
37343972 struct brcmf_if *ifp = netdev_priv(ndev);
37353973 struct brcmf_pmksa *pmk = &cfg->pmk_list.pmk[0];
3974
+ struct brcmf_pub *drvr = cfg->pub;
37363975 s32 err;
37373976 u32 npmk, i;
37383977
....@@ -3752,15 +3991,12 @@
37523991 cfg->pmk_list.npmk = cpu_to_le32(npmk);
37533992 }
37543993 } else {
3755
- brcmf_err("Too many PMKSA entries cached %d\n", npmk);
3994
+ bphy_err(drvr, "Too many PMKSA entries cached %d\n", npmk);
37563995 return -EINVAL;
37573996 }
37583997
37593998 brcmf_dbg(CONN, "set_pmksa - PMK bssid: %pM =\n", pmk[npmk].bssid);
3760
- for (i = 0; i < WLAN_PMKID_LEN; i += 4)
3761
- brcmf_dbg(CONN, "%02x %02x %02x %02x\n", pmk[npmk].pmkid[i],
3762
- pmk[npmk].pmkid[i + 1], pmk[npmk].pmkid[i + 2],
3763
- pmk[npmk].pmkid[i + 3]);
3999
+ brcmf_dbg(CONN, "%*ph\n", WLAN_PMKID_LEN, pmk[npmk].pmkid);
37644000
37654001 err = brcmf_update_pmklist(cfg, ifp);
37664002
....@@ -3775,6 +4011,7 @@
37754011 struct brcmf_cfg80211_info *cfg = wiphy_to_cfg(wiphy);
37764012 struct brcmf_if *ifp = netdev_priv(ndev);
37774013 struct brcmf_pmksa *pmk = &cfg->pmk_list.pmk[0];
4014
+ struct brcmf_pub *drvr = cfg->pub;
37784015 s32 err;
37794016 u32 npmk, i;
37804017
....@@ -3798,7 +4035,7 @@
37984035 memset(&pmk[i], 0, sizeof(*pmk));
37994036 cfg->pmk_list.npmk = cpu_to_le32(npmk - 1);
38004037 } else {
3801
- brcmf_err("Cache entry not found\n");
4038
+ bphy_err(drvr, "Cache entry not found\n");
38024039 return -EINVAL;
38034040 }
38044041
....@@ -3830,19 +4067,20 @@
38304067
38314068 static s32 brcmf_configure_opensecurity(struct brcmf_if *ifp)
38324069 {
4070
+ struct brcmf_pub *drvr = ifp->drvr;
38334071 s32 err;
38344072 s32 wpa_val;
38354073
38364074 /* set auth */
38374075 err = brcmf_fil_bsscfg_int_set(ifp, "auth", 0);
38384076 if (err < 0) {
3839
- brcmf_err("auth error %d\n", err);
4077
+ bphy_err(drvr, "auth error %d\n", err);
38404078 return err;
38414079 }
38424080 /* set wsec */
38434081 err = brcmf_fil_bsscfg_int_set(ifp, "wsec", 0);
38444082 if (err < 0) {
3845
- brcmf_err("wsec error %d\n", err);
4083
+ bphy_err(drvr, "wsec error %d\n", err);
38464084 return err;
38474085 }
38484086 /* set upper-layer auth */
....@@ -3852,7 +4090,7 @@
38524090 wpa_val = WPA_AUTH_DISABLED;
38534091 err = brcmf_fil_bsscfg_int_set(ifp, "wpa_auth", wpa_val);
38544092 if (err < 0) {
3855
- brcmf_err("wpa_auth error %d\n", err);
4093
+ bphy_err(drvr, "wpa_auth error %d\n", err);
38564094 return err;
38574095 }
38584096
....@@ -3872,6 +4110,7 @@
38724110 const struct brcmf_vs_tlv *wpa_ie,
38734111 bool is_rsn_ie)
38744112 {
4113
+ struct brcmf_pub *drvr = ifp->drvr;
38754114 u32 auth = 0; /* d11 open authentication */
38764115 u16 count;
38774116 s32 err = 0;
....@@ -3902,13 +4141,13 @@
39024141 /* check for multicast cipher suite */
39034142 if (offset + WPA_IE_MIN_OUI_LEN > len) {
39044143 err = -EINVAL;
3905
- brcmf_err("no multicast cipher suite\n");
4144
+ bphy_err(drvr, "no multicast cipher suite\n");
39064145 goto exit;
39074146 }
39084147
39094148 if (!brcmf_valid_wpa_oui(&data[offset], is_rsn_ie)) {
39104149 err = -EINVAL;
3911
- brcmf_err("ivalid OUI\n");
4150
+ bphy_err(drvr, "ivalid OUI\n");
39124151 goto exit;
39134152 }
39144153 offset += TLV_OUI_LEN;
....@@ -3930,7 +4169,7 @@
39304169 break;
39314170 default:
39324171 err = -EINVAL;
3933
- brcmf_err("Invalid multi cast cipher info\n");
4172
+ bphy_err(drvr, "Invalid multi cast cipher info\n");
39344173 goto exit;
39354174 }
39364175
....@@ -3941,13 +4180,13 @@
39414180 /* Check for unicast suite(s) */
39424181 if (offset + (WPA_IE_MIN_OUI_LEN * count) > len) {
39434182 err = -EINVAL;
3944
- brcmf_err("no unicast cipher suite\n");
4183
+ bphy_err(drvr, "no unicast cipher suite\n");
39454184 goto exit;
39464185 }
39474186 for (i = 0; i < count; i++) {
39484187 if (!brcmf_valid_wpa_oui(&data[offset], is_rsn_ie)) {
39494188 err = -EINVAL;
3950
- brcmf_err("ivalid OUI\n");
4189
+ bphy_err(drvr, "ivalid OUI\n");
39514190 goto exit;
39524191 }
39534192 offset += TLV_OUI_LEN;
....@@ -3965,7 +4204,7 @@
39654204 pval |= AES_ENABLED;
39664205 break;
39674206 default:
3968
- brcmf_err("Invalid unicast security info\n");
4207
+ bphy_err(drvr, "Invalid unicast security info\n");
39694208 }
39704209 offset++;
39714210 }
....@@ -3975,13 +4214,13 @@
39754214 /* Check for auth key management suite(s) */
39764215 if (offset + (WPA_IE_MIN_OUI_LEN * count) > len) {
39774216 err = -EINVAL;
3978
- brcmf_err("no auth key mgmt suite\n");
4217
+ bphy_err(drvr, "no auth key mgmt suite\n");
39794218 goto exit;
39804219 }
39814220 for (i = 0; i < count; i++) {
39824221 if (!brcmf_valid_wpa_oui(&data[offset], is_rsn_ie)) {
39834222 err = -EINVAL;
3984
- brcmf_err("ivalid OUI\n");
4223
+ bphy_err(drvr, "ivalid OUI\n");
39854224 goto exit;
39864225 }
39874226 offset += TLV_OUI_LEN;
....@@ -4008,8 +4247,12 @@
40084247 brcmf_dbg(TRACE, "RSN_AKM_MFP_1X\n");
40094248 wpa_auth |= WPA2_AUTH_1X_SHA256;
40104249 break;
4250
+ case RSN_AKM_SAE:
4251
+ brcmf_dbg(TRACE, "RSN_AKM_SAE\n");
4252
+ wpa_auth |= WPA3_AUTH_SAE_PSK;
4253
+ break;
40114254 default:
4012
- brcmf_err("Invalid key mgmt info\n");
4255
+ bphy_err(drvr, "Invalid key mgmt info\n");
40134256 }
40144257 offset++;
40154258 }
....@@ -4025,11 +4268,12 @@
40254268 brcmf_dbg(TRACE, "MFP Required\n");
40264269 mfp = BRCMF_MFP_REQUIRED;
40274270 /* Firmware only supports mfp required in
4028
- * combination with WPA2_AUTH_PSK_SHA256 or
4029
- * WPA2_AUTH_1X_SHA256.
4271
+ * combination with WPA2_AUTH_PSK_SHA256,
4272
+ * WPA2_AUTH_1X_SHA256, or WPA3_AUTH_SAE_PSK.
40304273 */
40314274 if (!(wpa_auth & (WPA2_AUTH_PSK_SHA256 |
4032
- WPA2_AUTH_1X_SHA256))) {
4275
+ WPA2_AUTH_1X_SHA256 |
4276
+ WPA3_AUTH_SAE_PSK))) {
40334277 err = -EINVAL;
40344278 goto exit;
40354279 }
....@@ -4051,7 +4295,7 @@
40514295 err = brcmf_fil_bsscfg_int_set(ifp, "wme_bss_disable",
40524296 wme_bss_disable);
40534297 if (err < 0) {
4054
- brcmf_err("wme_bss_disable error %d\n", err);
4298
+ bphy_err(drvr, "wme_bss_disable error %d\n", err);
40554299 goto exit;
40564300 }
40574301
....@@ -4065,7 +4309,7 @@
40654309 &data[offset],
40664310 WPA_IE_MIN_OUI_LEN);
40674311 if (err < 0) {
4068
- brcmf_err("bip error %d\n", err);
4312
+ bphy_err(drvr, "bip error %d\n", err);
40694313 goto exit;
40704314 }
40714315 }
....@@ -4076,13 +4320,13 @@
40764320 /* set auth */
40774321 err = brcmf_fil_bsscfg_int_set(ifp, "auth", auth);
40784322 if (err < 0) {
4079
- brcmf_err("auth error %d\n", err);
4323
+ bphy_err(drvr, "auth error %d\n", err);
40804324 goto exit;
40814325 }
40824326 /* set wsec */
40834327 err = brcmf_fil_bsscfg_int_set(ifp, "wsec", wsec);
40844328 if (err < 0) {
4085
- brcmf_err("wsec error %d\n", err);
4329
+ bphy_err(drvr, "wsec error %d\n", err);
40864330 goto exit;
40874331 }
40884332 /* Configure MFP, this needs to go after wsec otherwise the wsec command
....@@ -4091,14 +4335,14 @@
40914335 if (brcmf_feat_is_enabled(ifp, BRCMF_FEAT_MFP)) {
40924336 err = brcmf_fil_bsscfg_int_set(ifp, "mfp", mfp);
40934337 if (err < 0) {
4094
- brcmf_err("mfp error %d\n", err);
4338
+ bphy_err(drvr, "mfp error %d\n", err);
40954339 goto exit;
40964340 }
40974341 }
40984342 /* set upper-layer auth */
40994343 err = brcmf_fil_bsscfg_int_set(ifp, "wpa_auth", wpa_auth);
41004344 if (err < 0) {
4101
- brcmf_err("wpa_auth error %d\n", err);
4345
+ bphy_err(drvr, "wpa_auth error %d\n", err);
41024346 goto exit;
41034347 }
41044348
....@@ -4146,10 +4390,8 @@
41464390
41474391 vndr_ies->count++;
41484392
4149
- brcmf_dbg(TRACE, "** OUI %02x %02x %02x, type 0x%02x\n",
4150
- parsed_info->vndrie.oui[0],
4151
- parsed_info->vndrie.oui[1],
4152
- parsed_info->vndrie.oui[2],
4393
+ brcmf_dbg(TRACE, "** OUI %3ph, type 0x%02x\n",
4394
+ parsed_info->vndrie.oui,
41534395 parsed_info->vndrie.oui_type);
41544396
41554397 if (vndr_ies->count >= VNDR_IE_PARSE_LIMIT)
....@@ -4168,9 +4410,7 @@
41684410 static u32
41694411 brcmf_vndr_ie(u8 *iebuf, s32 pktflag, u8 *ie_ptr, u32 ie_len, s8 *add_del_cmd)
41704412 {
4171
-
4172
- strncpy(iebuf, add_del_cmd, VNDR_IE_CMD_LEN - 1);
4173
- iebuf[VNDR_IE_CMD_LEN - 1] = '\0';
4413
+ strscpy(iebuf, add_del_cmd, VNDR_IE_CMD_LEN);
41744414
41754415 put_unaligned_le32(1, &iebuf[VNDR_IE_COUNT_OFFSET]);
41764416
....@@ -4184,6 +4424,7 @@
41844424 s32 brcmf_vif_set_mgmt_ie(struct brcmf_cfg80211_vif *vif, s32 pktflag,
41854425 const u8 *vndr_ie_buf, u32 vndr_ie_len)
41864426 {
4427
+ struct brcmf_pub *drvr;
41874428 struct brcmf_if *ifp;
41884429 struct vif_saved_ie *saved_ie;
41894430 s32 err = 0;
....@@ -4205,6 +4446,7 @@
42054446 if (!vif)
42064447 return -ENODEV;
42074448 ifp = vif->ifp;
4449
+ drvr = ifp->drvr;
42084450 saved_ie = &vif->saved_ie;
42094451
42104452 brcmf_dbg(TRACE, "bsscfgidx %d, pktflag : 0x%02X\n", ifp->bsscfgidx,
....@@ -4234,15 +4476,20 @@
42344476 mgmt_ie_len = &saved_ie->assoc_req_ie_len;
42354477 mgmt_ie_buf_len = sizeof(saved_ie->assoc_req_ie);
42364478 break;
4479
+ case BRCMF_VNDR_IE_ASSOCRSP_FLAG:
4480
+ mgmt_ie_buf = saved_ie->assoc_res_ie;
4481
+ mgmt_ie_len = &saved_ie->assoc_res_ie_len;
4482
+ mgmt_ie_buf_len = sizeof(saved_ie->assoc_res_ie);
4483
+ break;
42374484 default:
42384485 err = -EPERM;
4239
- brcmf_err("not suitable type\n");
4486
+ bphy_err(drvr, "not suitable type\n");
42404487 goto exit;
42414488 }
42424489
42434490 if (vndr_ie_len > mgmt_ie_buf_len) {
42444491 err = -ENOMEM;
4245
- brcmf_err("extra IE size too big\n");
4492
+ bphy_err(drvr, "extra IE size too big\n");
42464493 goto exit;
42474494 }
42484495
....@@ -4273,12 +4520,10 @@
42734520 for (i = 0; i < old_vndr_ies.count; i++) {
42744521 vndrie_info = &old_vndr_ies.ie_info[i];
42754522
4276
- brcmf_dbg(TRACE, "DEL ID : %d, Len: %d , OUI:%02x:%02x:%02x\n",
4523
+ brcmf_dbg(TRACE, "DEL ID : %d, Len: %d , OUI:%3ph\n",
42774524 vndrie_info->vndrie.id,
42784525 vndrie_info->vndrie.len,
4279
- vndrie_info->vndrie.oui[0],
4280
- vndrie_info->vndrie.oui[1],
4281
- vndrie_info->vndrie.oui[2]);
4526
+ vndrie_info->vndrie.oui);
42824527
42834528 del_add_ie_buf_len = brcmf_vndr_ie(curr_ie_buf, pktflag,
42844529 vndrie_info->ie_ptr,
....@@ -4303,19 +4548,17 @@
43034548 /* verify remained buf size before copy data */
43044549 if (remained_buf_len < (vndrie_info->vndrie.len +
43054550 VNDR_IE_VSIE_OFFSET)) {
4306
- brcmf_err("no space in mgmt_ie_buf: len left %d",
4307
- remained_buf_len);
4551
+ bphy_err(drvr, "no space in mgmt_ie_buf: len left %d",
4552
+ remained_buf_len);
43084553 break;
43094554 }
43104555 remained_buf_len -= (vndrie_info->ie_len +
43114556 VNDR_IE_VSIE_OFFSET);
43124557
4313
- brcmf_dbg(TRACE, "ADDED ID : %d, Len: %d, OUI:%02x:%02x:%02x\n",
4558
+ brcmf_dbg(TRACE, "ADDED ID : %d, Len: %d, OUI:%3ph\n",
43144559 vndrie_info->vndrie.id,
43154560 vndrie_info->vndrie.len,
4316
- vndrie_info->vndrie.oui[0],
4317
- vndrie_info->vndrie.oui[1],
4318
- vndrie_info->vndrie.oui[2]);
4561
+ vndrie_info->vndrie.oui);
43194562
43204563 del_add_ie_buf_len = brcmf_vndr_ie(curr_ie_buf, pktflag,
43214564 vndrie_info->ie_ptr,
....@@ -4335,7 +4578,7 @@
43354578 err = brcmf_fil_bsscfg_data_set(ifp, "vndr_ie", iovar_ie_buf,
43364579 total_ie_buf_len);
43374580 if (err)
4338
- brcmf_err("vndr ie set error : %d\n", err);
4581
+ bphy_err(drvr, "vndr ie set error : %d\n", err);
43394582 }
43404583
43414584 exit:
....@@ -4363,13 +4606,14 @@
43634606 brcmf_config_ap_mgmt_ie(struct brcmf_cfg80211_vif *vif,
43644607 struct cfg80211_beacon_data *beacon)
43654608 {
4609
+ struct brcmf_pub *drvr = vif->ifp->drvr;
43664610 s32 err;
43674611
43684612 /* Set Beacon IEs to FW */
43694613 err = brcmf_vif_set_mgmt_ie(vif, BRCMF_VNDR_IE_BEACON_FLAG,
43704614 beacon->tail, beacon->tail_len);
43714615 if (err) {
4372
- brcmf_err("Set Beacon IE Failed\n");
4616
+ bphy_err(drvr, "Set Beacon IE Failed\n");
43734617 return err;
43744618 }
43754619 brcmf_dbg(TRACE, "Applied Vndr IEs for Beacon\n");
....@@ -4379,9 +4623,60 @@
43794623 beacon->proberesp_ies,
43804624 beacon->proberesp_ies_len);
43814625 if (err)
4382
- brcmf_err("Set Probe Resp IE Failed\n");
4626
+ bphy_err(drvr, "Set Probe Resp IE Failed\n");
43834627 else
43844628 brcmf_dbg(TRACE, "Applied Vndr IEs for Probe Resp\n");
4629
+
4630
+ /* Set Assoc Response IEs to FW */
4631
+ err = brcmf_vif_set_mgmt_ie(vif, BRCMF_VNDR_IE_ASSOCRSP_FLAG,
4632
+ beacon->assocresp_ies,
4633
+ beacon->assocresp_ies_len);
4634
+ if (err)
4635
+ brcmf_err("Set Assoc Resp IE Failed\n");
4636
+ else
4637
+ brcmf_dbg(TRACE, "Applied Vndr IEs for Assoc Resp\n");
4638
+
4639
+ return err;
4640
+}
4641
+
4642
+static s32
4643
+brcmf_parse_configure_security(struct brcmf_if *ifp,
4644
+ struct cfg80211_ap_settings *settings,
4645
+ enum nl80211_iftype dev_role)
4646
+{
4647
+ const struct brcmf_tlv *rsn_ie;
4648
+ const struct brcmf_vs_tlv *wpa_ie;
4649
+ s32 err = 0;
4650
+
4651
+ /* find the RSN_IE */
4652
+ rsn_ie = brcmf_parse_tlvs((u8 *)settings->beacon.tail,
4653
+ settings->beacon.tail_len, WLAN_EID_RSN);
4654
+
4655
+ /* find the WPA_IE */
4656
+ wpa_ie = brcmf_find_wpaie((u8 *)settings->beacon.tail,
4657
+ settings->beacon.tail_len);
4658
+
4659
+ if (wpa_ie || rsn_ie) {
4660
+ brcmf_dbg(TRACE, "WPA(2) IE is found\n");
4661
+ if (wpa_ie) {
4662
+ /* WPA IE */
4663
+ err = brcmf_configure_wpaie(ifp, wpa_ie, false);
4664
+ if (err < 0)
4665
+ return err;
4666
+ } else {
4667
+ struct brcmf_vs_tlv *tmp_ie;
4668
+
4669
+ tmp_ie = (struct brcmf_vs_tlv *)rsn_ie;
4670
+
4671
+ /* RSN IE */
4672
+ err = brcmf_configure_wpaie(ifp, tmp_ie, true);
4673
+ if (err < 0)
4674
+ return err;
4675
+ }
4676
+ } else {
4677
+ brcmf_dbg(TRACE, "No WPA(2) IEs found\n");
4678
+ brcmf_configure_opensecurity(ifp);
4679
+ }
43854680
43864681 return err;
43874682 }
....@@ -4393,12 +4688,13 @@
43934688 s32 ie_offset;
43944689 struct brcmf_cfg80211_info *cfg = wiphy_to_cfg(wiphy);
43954690 struct brcmf_if *ifp = netdev_priv(ndev);
4691
+ struct brcmf_pub *drvr = cfg->pub;
4692
+ struct brcmf_cfg80211_profile *profile = &ifp->vif->profile;
4693
+ struct cfg80211_crypto_settings *crypto = &settings->crypto;
43964694 const struct brcmf_tlv *ssid_ie;
43974695 const struct brcmf_tlv *country_ie;
43984696 struct brcmf_ssid_le ssid_le;
43994697 s32 err = -EPERM;
4400
- const struct brcmf_tlv *rsn_ie;
4401
- const struct brcmf_vs_tlv *wpa_ie;
44024698 struct brcmf_join_params join_params;
44034699 enum nl80211_iftype dev_role;
44044700 struct brcmf_fil_bss_enable_le bss_enable;
....@@ -4452,43 +4748,14 @@
44524748 brcmf_configure_arp_nd_offload(ifp, false);
44534749 }
44544750
4455
- /* find the RSN_IE */
4456
- rsn_ie = brcmf_parse_tlvs((u8 *)settings->beacon.tail,
4457
- settings->beacon.tail_len, WLAN_EID_RSN);
4458
-
4459
- /* find the WPA_IE */
4460
- wpa_ie = brcmf_find_wpaie((u8 *)settings->beacon.tail,
4461
- settings->beacon.tail_len);
4462
-
4463
- if ((wpa_ie != NULL || rsn_ie != NULL)) {
4464
- brcmf_dbg(TRACE, "WPA(2) IE is found\n");
4465
- if (wpa_ie != NULL) {
4466
- /* WPA IE */
4467
- err = brcmf_configure_wpaie(ifp, wpa_ie, false);
4468
- if (err < 0)
4469
- goto exit;
4470
- } else {
4471
- struct brcmf_vs_tlv *tmp_ie;
4472
-
4473
- tmp_ie = (struct brcmf_vs_tlv *)rsn_ie;
4474
-
4475
- /* RSN IE */
4476
- err = brcmf_configure_wpaie(ifp, tmp_ie, true);
4477
- if (err < 0)
4478
- goto exit;
4479
- }
4480
- } else {
4481
- brcmf_dbg(TRACE, "No WPA(2) IEs found\n");
4482
- brcmf_configure_opensecurity(ifp);
4483
- }
4484
-
44854751 /* Parameters shared by all radio interfaces */
44864752 if (!mbss) {
44874753 if ((supports_11d) && (is_11d != ifp->vif->is_11d)) {
44884754 err = brcmf_fil_cmd_int_set(ifp, BRCMF_C_SET_REGULATORY,
44894755 is_11d);
44904756 if (err < 0) {
4491
- brcmf_err("Regulatory Set Error, %d\n", err);
4757
+ bphy_err(drvr, "Regulatory Set Error, %d\n",
4758
+ err);
44924759 goto exit;
44934760 }
44944761 }
....@@ -4496,8 +4763,8 @@
44964763 err = brcmf_fil_cmd_int_set(ifp, BRCMF_C_SET_BCNPRD,
44974764 settings->beacon_interval);
44984765 if (err < 0) {
4499
- brcmf_err("Beacon Interval Set Error, %d\n",
4500
- err);
4766
+ bphy_err(drvr, "Beacon Interval Set Error, %d\n",
4767
+ err);
45014768 goto exit;
45024769 }
45034770 }
....@@ -4505,17 +4772,20 @@
45054772 err = brcmf_fil_cmd_int_set(ifp, BRCMF_C_SET_DTIMPRD,
45064773 settings->dtim_period);
45074774 if (err < 0) {
4508
- brcmf_err("DTIM Interval Set Error, %d\n", err);
4775
+ bphy_err(drvr, "DTIM Interval Set Error, %d\n",
4776
+ err);
45094777 goto exit;
45104778 }
45114779 }
45124780
45134781 if ((dev_role == NL80211_IFTYPE_AP) &&
45144782 ((ifp->ifidx == 0) ||
4515
- !brcmf_feat_is_enabled(ifp, BRCMF_FEAT_RSDB))) {
4783
+ (!brcmf_feat_is_enabled(ifp, BRCMF_FEAT_RSDB) &&
4784
+ !brcmf_feat_is_enabled(ifp, BRCMF_FEAT_MCHAN)))) {
45164785 err = brcmf_fil_cmd_int_set(ifp, BRCMF_C_DOWN, 1);
45174786 if (err < 0) {
4518
- brcmf_err("BRCMF_C_DOWN error %d\n", err);
4787
+ bphy_err(drvr, "BRCMF_C_DOWN error %d\n",
4788
+ err);
45194789 goto exit;
45204790 }
45214791 brcmf_fil_iovar_int_set(ifp, "apsta", 0);
....@@ -4523,7 +4793,7 @@
45234793
45244794 err = brcmf_fil_cmd_int_set(ifp, BRCMF_C_SET_INFRA, 1);
45254795 if (err < 0) {
4526
- brcmf_err("SET INFRA error %d\n", err);
4796
+ bphy_err(drvr, "SET INFRA error %d\n", err);
45274797 goto exit;
45284798 }
45294799 } else if (WARN_ON(supports_11d && (is_11d != ifp->vif->is_11d))) {
....@@ -4539,7 +4809,8 @@
45394809
45404810 err = brcmf_fil_cmd_int_set(ifp, BRCMF_C_SET_AP, 1);
45414811 if (err < 0) {
4542
- brcmf_err("setting AP mode failed %d\n", err);
4812
+ bphy_err(drvr, "setting AP mode failed %d\n",
4813
+ err);
45434814 goto exit;
45444815 }
45454816 if (!mbss) {
....@@ -4548,16 +4819,43 @@
45484819 */
45494820 err = brcmf_fil_iovar_int_set(ifp, "chanspec", chanspec);
45504821 if (err < 0) {
4551
- brcmf_err("Set Channel failed: chspec=%d, %d\n",
4552
- chanspec, err);
4822
+ bphy_err(drvr, "Set Channel failed: chspec=%d, %d\n",
4823
+ chanspec, err);
45534824 goto exit;
45544825 }
45554826 }
45564827 err = brcmf_fil_cmd_int_set(ifp, BRCMF_C_UP, 1);
45574828 if (err < 0) {
4558
- brcmf_err("BRCMF_C_UP error (%d)\n", err);
4829
+ bphy_err(drvr, "BRCMF_C_UP error (%d)\n", err);
45594830 goto exit;
45604831 }
4832
+
4833
+ if (crypto->psk) {
4834
+ brcmf_dbg(INFO, "using PSK offload\n");
4835
+ profile->use_fwauth |= BIT(BRCMF_PROFILE_FWAUTH_PSK);
4836
+ err = brcmf_set_pmk(ifp, crypto->psk,
4837
+ BRCMF_WSEC_MAX_PSK_LEN);
4838
+ if (err < 0)
4839
+ goto exit;
4840
+ }
4841
+ if (crypto->sae_pwd) {
4842
+ brcmf_dbg(INFO, "using SAE offload\n");
4843
+ profile->use_fwauth |= BIT(BRCMF_PROFILE_FWAUTH_SAE);
4844
+ err = brcmf_set_sae_password(ifp, crypto->sae_pwd,
4845
+ crypto->sae_pwd_len);
4846
+ if (err < 0)
4847
+ goto exit;
4848
+ }
4849
+ if (profile->use_fwauth == 0)
4850
+ profile->use_fwauth = BIT(BRCMF_PROFILE_FWAUTH_NONE);
4851
+
4852
+ err = brcmf_parse_configure_security(ifp, settings,
4853
+ NL80211_IFTYPE_AP);
4854
+ if (err < 0) {
4855
+ bphy_err(drvr, "brcmf_parse_configure_security error\n");
4856
+ goto exit;
4857
+ }
4858
+
45614859 /* On DOWN the firmware removes the WEP keys, reconfigure
45624860 * them if they were set.
45634861 */
....@@ -4570,30 +4868,40 @@
45704868 err = brcmf_fil_cmd_data_set(ifp, BRCMF_C_SET_SSID,
45714869 &join_params, sizeof(join_params));
45724870 if (err < 0) {
4573
- brcmf_err("SET SSID error (%d)\n", err);
4871
+ bphy_err(drvr, "SET SSID error (%d)\n", err);
45744872 goto exit;
45754873 }
45764874
4577
- if (settings->hidden_ssid) {
4578
- err = brcmf_fil_iovar_int_set(ifp, "closednet", 1);
4579
- if (err) {
4580
- brcmf_err("closednet error (%d)\n", err);
4581
- goto exit;
4582
- }
4875
+ err = brcmf_fil_iovar_int_set(ifp, "closednet",
4876
+ settings->hidden_ssid);
4877
+ if (err) {
4878
+ bphy_err(drvr, "%s closednet error (%d)\n",
4879
+ settings->hidden_ssid ?
4880
+ "enabled" : "disabled",
4881
+ err);
4882
+ goto exit;
45834883 }
45844884
45854885 brcmf_dbg(TRACE, "AP mode configuration complete\n");
45864886 } else if (dev_role == NL80211_IFTYPE_P2P_GO) {
45874887 err = brcmf_fil_iovar_int_set(ifp, "chanspec", chanspec);
45884888 if (err < 0) {
4589
- brcmf_err("Set Channel failed: chspec=%d, %d\n",
4590
- chanspec, err);
4889
+ bphy_err(drvr, "Set Channel failed: chspec=%d, %d\n",
4890
+ chanspec, err);
45914891 goto exit;
45924892 }
4893
+
4894
+ err = brcmf_parse_configure_security(ifp, settings,
4895
+ NL80211_IFTYPE_P2P_GO);
4896
+ if (err < 0) {
4897
+ brcmf_err("brcmf_parse_configure_security error\n");
4898
+ goto exit;
4899
+ }
4900
+
45934901 err = brcmf_fil_bsscfg_data_set(ifp, "ssid", &ssid_le,
45944902 sizeof(ssid_le));
45954903 if (err < 0) {
4596
- brcmf_err("setting ssid failed %d\n", err);
4904
+ bphy_err(drvr, "setting ssid failed %d\n", err);
45974905 goto exit;
45984906 }
45994907 bss_enable.bsscfgidx = cpu_to_le32(ifp->bsscfgidx);
....@@ -4601,7 +4909,7 @@
46014909 err = brcmf_fil_iovar_data_set(ifp, "bss", &bss_enable,
46024910 sizeof(bss_enable));
46034911 if (err < 0) {
4604
- brcmf_err("bss_enable config failed %d\n", err);
4912
+ bphy_err(drvr, "bss_enable config failed %d\n", err);
46054913 goto exit;
46064914 }
46074915
....@@ -4624,7 +4932,10 @@
46244932
46254933 static int brcmf_cfg80211_stop_ap(struct wiphy *wiphy, struct net_device *ndev)
46264934 {
4935
+ struct brcmf_cfg80211_info *cfg = wiphy_to_cfg(wiphy);
46274936 struct brcmf_if *ifp = netdev_priv(ndev);
4937
+ struct brcmf_pub *drvr = cfg->pub;
4938
+ struct brcmf_cfg80211_profile *profile = &ifp->vif->profile;
46284939 s32 err;
46294940 struct brcmf_fil_bss_enable_le bss_enable;
46304941 struct brcmf_join_params join_params;
....@@ -4635,6 +4946,14 @@
46354946 /* Due to most likely deauths outstanding we sleep */
46364947 /* first to make sure they get processed by fw. */
46374948 msleep(400);
4949
+
4950
+ if (profile->use_fwauth != BIT(BRCMF_PROFILE_FWAUTH_NONE)) {
4951
+ if (profile->use_fwauth & BIT(BRCMF_PROFILE_FWAUTH_PSK))
4952
+ brcmf_set_pmk(ifp, NULL, 0);
4953
+ if (profile->use_fwauth & BIT(BRCMF_PROFILE_FWAUTH_SAE))
4954
+ brcmf_set_sae_password(ifp, NULL, 0);
4955
+ profile->use_fwauth = BIT(BRCMF_PROFILE_FWAUTH_NONE);
4956
+ }
46384957
46394958 if (ifp->vif->mbss) {
46404959 err = brcmf_fil_cmd_int_set(ifp, BRCMF_C_DOWN, 1);
....@@ -4649,13 +4968,13 @@
46494968 err = brcmf_fil_cmd_data_set(ifp, BRCMF_C_SET_SSID,
46504969 &join_params, sizeof(join_params));
46514970 if (err < 0)
4652
- brcmf_err("SET SSID error (%d)\n", err);
4971
+ bphy_err(drvr, "SET SSID error (%d)\n", err);
46534972 err = brcmf_fil_cmd_int_set(ifp, BRCMF_C_DOWN, 1);
46544973 if (err < 0)
4655
- brcmf_err("BRCMF_C_DOWN error %d\n", err);
4974
+ bphy_err(drvr, "BRCMF_C_DOWN error %d\n", err);
46564975 err = brcmf_fil_cmd_int_set(ifp, BRCMF_C_SET_AP, 0);
46574976 if (err < 0)
4658
- brcmf_err("setting AP mode failed %d\n", err);
4977
+ bphy_err(drvr, "setting AP mode failed %d\n", err);
46594978 if (brcmf_feat_is_enabled(ifp, BRCMF_FEAT_MBSS))
46604979 brcmf_fil_iovar_int_set(ifp, "mbss", 0);
46614980 brcmf_fil_cmd_int_set(ifp, BRCMF_C_SET_REGULATORY,
....@@ -4663,7 +4982,7 @@
46634982 /* Bring device back up so it can be used again */
46644983 err = brcmf_fil_cmd_int_set(ifp, BRCMF_C_UP, 1);
46654984 if (err < 0)
4666
- brcmf_err("BRCMF_C_UP error %d\n", err);
4985
+ bphy_err(drvr, "BRCMF_C_UP error %d\n", err);
46674986
46684987 brcmf_vif_clear_mgmt_ies(ifp->vif);
46694988 } else {
....@@ -4672,7 +4991,7 @@
46724991 err = brcmf_fil_iovar_data_set(ifp, "bss", &bss_enable,
46734992 sizeof(bss_enable));
46744993 if (err < 0)
4675
- brcmf_err("bss_enable config failed %d\n", err);
4994
+ bphy_err(drvr, "bss_enable config failed %d\n", err);
46764995 }
46774996 brcmf_set_mpc(ifp, 1);
46784997 brcmf_configure_arp_nd_offload(ifp, true);
....@@ -4701,6 +5020,7 @@
47015020 struct station_del_parameters *params)
47025021 {
47035022 struct brcmf_cfg80211_info *cfg = wiphy_to_cfg(wiphy);
5023
+ struct brcmf_pub *drvr = cfg->pub;
47045024 struct brcmf_scb_val_le scbval;
47055025 struct brcmf_if *ifp = netdev_priv(ndev);
47065026 s32 err;
....@@ -4720,7 +5040,8 @@
47205040 err = brcmf_fil_cmd_data_set(ifp, BRCMF_C_SCB_DEAUTHENTICATE_FOR_REASON,
47215041 &scbval, sizeof(scbval));
47225042 if (err)
4723
- brcmf_err("SCB_DEAUTHENTICATE_FOR_REASON failed %d\n", err);
5043
+ bphy_err(drvr, "SCB_DEAUTHENTICATE_FOR_REASON failed %d\n",
5044
+ err);
47245045
47255046 brcmf_dbg(TRACE, "Exit\n");
47265047 return err;
....@@ -4730,6 +5051,8 @@
47305051 brcmf_cfg80211_change_station(struct wiphy *wiphy, struct net_device *ndev,
47315052 const u8 *mac, struct station_parameters *params)
47325053 {
5054
+ struct brcmf_cfg80211_info *cfg = wiphy_to_cfg(wiphy);
5055
+ struct brcmf_pub *drvr = cfg->pub;
47335056 struct brcmf_if *ifp = netdev_priv(ndev);
47345057 s32 err;
47355058
....@@ -4750,27 +5073,21 @@
47505073 err = brcmf_fil_cmd_data_set(ifp, BRCMF_C_SET_SCB_DEAUTHORIZE,
47515074 (void *)mac, ETH_ALEN);
47525075 if (err < 0)
4753
- brcmf_err("Setting SCB (de-)authorize failed, %d\n", err);
5076
+ bphy_err(drvr, "Setting SCB (de-)authorize failed, %d\n", err);
47545077
47555078 return err;
47565079 }
47575080
47585081 static void
4759
-brcmf_cfg80211_mgmt_frame_register(struct wiphy *wiphy,
4760
- struct wireless_dev *wdev,
4761
- u16 frame_type, bool reg)
5082
+brcmf_cfg80211_update_mgmt_frame_registrations(struct wiphy *wiphy,
5083
+ struct wireless_dev *wdev,
5084
+ struct mgmt_frame_regs *upd)
47625085 {
47635086 struct brcmf_cfg80211_vif *vif;
4764
- u16 mgmt_type;
47655087
4766
- brcmf_dbg(TRACE, "Enter, frame_type %04x, reg=%d\n", frame_type, reg);
4767
-
4768
- mgmt_type = (frame_type & IEEE80211_FCTL_STYPE) >> 4;
47695088 vif = container_of(wdev, struct brcmf_cfg80211_vif, wdev);
4770
- if (reg)
4771
- vif->mgmt_rx_reg |= BIT(mgmt_type);
4772
- else
4773
- vif->mgmt_rx_reg &= ~BIT(mgmt_type);
5089
+
5090
+ vif->mgmt_rx_reg = upd->interface_stypes;
47745091 }
47755092
47765093
....@@ -4780,6 +5097,7 @@
47805097 {
47815098 struct brcmf_cfg80211_info *cfg = wiphy_to_cfg(wiphy);
47825099 struct ieee80211_channel *chan = params->chan;
5100
+ struct brcmf_pub *drvr = cfg->pub;
47835101 const u8 *buf = params->buf;
47845102 size_t len = params->len;
47855103 const struct ieee80211_mgmt *mgmt;
....@@ -4800,7 +5118,7 @@
48005118 mgmt = (const struct ieee80211_mgmt *)buf;
48015119
48025120 if (!ieee80211_is_mgmt(mgmt->frame_control)) {
4803
- brcmf_err("Driver only allows MGMT packet type\n");
5121
+ bphy_err(drvr, "Driver only allows MGMT packet type\n");
48045122 return -EPERM;
48055123 }
48065124
....@@ -4831,13 +5149,13 @@
48315149 GFP_KERNEL);
48325150 } else if (ieee80211_is_action(mgmt->frame_control)) {
48335151 if (len > BRCMF_FIL_ACTION_FRAME_SIZE + DOT11_MGMT_HDR_LEN) {
4834
- brcmf_err("invalid action frame length\n");
5152
+ bphy_err(drvr, "invalid action frame length\n");
48355153 err = -EINVAL;
48365154 goto exit;
48375155 }
48385156 af_params = kzalloc(sizeof(*af_params), GFP_KERNEL);
48395157 if (af_params == NULL) {
4840
- brcmf_err("unable to allocate frame\n");
5158
+ bphy_err(drvr, "unable to allocate frame\n");
48415159 err = -ENOMEM;
48425160 goto exit;
48435161 }
....@@ -4859,7 +5177,7 @@
48595177 &freq);
48605178 chan_nr = ieee80211_frequency_to_channel(freq);
48615179 af_params->channel = cpu_to_le32(chan_nr);
4862
-
5180
+ af_params->dwell_time = cpu_to_le32(params->wait);
48635181 memcpy(action_frame->data, &buf[DOT11_MGMT_HDR_LEN],
48645182 le16_to_cpu(action_frame->len));
48655183
....@@ -4888,6 +5206,7 @@
48885206 u64 cookie)
48895207 {
48905208 struct brcmf_cfg80211_info *cfg = wiphy_to_cfg(wiphy);
5209
+ struct brcmf_pub *drvr = cfg->pub;
48915210 struct brcmf_cfg80211_vif *vif;
48925211 int err = 0;
48935212
....@@ -4895,7 +5214,7 @@
48955214
48965215 vif = cfg->p2p.bss_idx[P2PAPI_BSSCFG_DEVICE].vif;
48975216 if (vif == NULL) {
4898
- brcmf_err("No p2p device available for probe response\n");
5217
+ bphy_err(drvr, "No p2p device available for probe response\n");
48995218 err = -ENODEV;
49005219 goto exit;
49015220 }
....@@ -4910,20 +5229,19 @@
49105229 {
49115230 struct brcmf_cfg80211_info *cfg = wiphy_to_cfg(wiphy);
49125231 struct net_device *ndev = wdev->netdev;
4913
- struct brcmf_if *ifp;
5232
+ struct brcmf_pub *drvr = cfg->pub;
49145233 struct brcmu_chan ch;
49155234 enum nl80211_band band = 0;
49165235 enum nl80211_chan_width width = 0;
49175236 u32 chanspec;
49185237 int freq, err;
49195238
4920
- if (!ndev)
5239
+ if (!ndev || drvr->bus_if->state != BRCMF_BUS_UP)
49215240 return -ENODEV;
4922
- ifp = netdev_priv(ndev);
49235241
4924
- err = brcmf_fil_iovar_int_get(ifp, "chanspec", &chanspec);
5242
+ err = brcmf_fil_iovar_int_get(netdev_priv(ndev), "chanspec", &chanspec);
49255243 if (err) {
4926
- brcmf_err("chanspec failed (%d)\n", err);
5244
+ bphy_err(drvr, "chanspec failed (%d)\n", err);
49275245 return err;
49285246 }
49295247
....@@ -5045,6 +5363,8 @@
50455363 struct net_device *ndev, const u8 *peer,
50465364 enum nl80211_tdls_operation oper)
50475365 {
5366
+ struct brcmf_cfg80211_info *cfg = wiphy_to_cfg(wiphy);
5367
+ struct brcmf_pub *drvr = cfg->pub;
50485368 struct brcmf_if *ifp;
50495369 struct brcmf_tdls_iovar_le info;
50505370 int ret = 0;
....@@ -5062,7 +5382,7 @@
50625382 ret = brcmf_fil_iovar_data_set(ifp, "tdls_endpoint",
50635383 &info, sizeof(info));
50645384 if (ret < 0)
5065
- brcmf_err("tdls_endpoint iovar failed: ret=%d\n", ret);
5385
+ bphy_err(drvr, "tdls_endpoint iovar failed: ret=%d\n", ret);
50665386
50675387 return ret;
50685388 }
....@@ -5073,6 +5393,8 @@
50735393 struct cfg80211_connect_params *sme,
50745394 u32 changed)
50755395 {
5396
+ struct brcmf_cfg80211_info *cfg = wiphy_to_cfg(wiphy);
5397
+ struct brcmf_pub *drvr = cfg->pub;
50765398 struct brcmf_if *ifp;
50775399 int err;
50785400
....@@ -5083,7 +5405,7 @@
50835405 err = brcmf_vif_set_mgmt_ie(ifp->vif, BRCMF_VNDR_IE_ASSOCREQ_FLAG,
50845406 sme->ie, sme->ie_len);
50855407 if (err)
5086
- brcmf_err("Set Assoc REQ IE Failed\n");
5408
+ bphy_err(drvr, "Set Assoc REQ IE Failed\n");
50875409 else
50885410 brcmf_dbg(TRACE, "Applied Vndr IEs for Assoc request\n");
50895411
....@@ -5095,6 +5417,8 @@
50955417 brcmf_cfg80211_set_rekey_data(struct wiphy *wiphy, struct net_device *ndev,
50965418 struct cfg80211_gtk_rekey_data *gtk)
50975419 {
5420
+ struct brcmf_cfg80211_info *cfg = wiphy_to_cfg(wiphy);
5421
+ struct brcmf_pub *drvr = cfg->pub;
50985422 struct brcmf_if *ifp = netdev_priv(ndev);
50995423 struct brcmf_gtk_keyinfo_le gtk_le;
51005424 int ret;
....@@ -5109,7 +5433,7 @@
51095433 ret = brcmf_fil_iovar_data_set(ifp, "gtk_key_info", &gtk_le,
51105434 sizeof(gtk_le));
51115435 if (ret < 0)
5112
- brcmf_err("gtk_key_info iovar failed: ret=%d\n", ret);
5436
+ bphy_err(drvr, "gtk_key_info iovar failed: ret=%d\n", ret);
51135437
51145438 return ret;
51155439 }
....@@ -5178,7 +5502,8 @@
51785502 .change_station = brcmf_cfg80211_change_station,
51795503 .sched_scan_start = brcmf_cfg80211_sched_scan_start,
51805504 .sched_scan_stop = brcmf_cfg80211_sched_scan_stop,
5181
- .mgmt_frame_register = brcmf_cfg80211_mgmt_frame_register,
5505
+ .update_mgmt_frame_registrations =
5506
+ brcmf_cfg80211_update_mgmt_frame_registrations,
51825507 .mgmt_tx = brcmf_cfg80211_mgmt_tx,
51835508 .remain_on_channel = brcmf_p2p_remain_on_channel,
51845509 .cancel_remain_on_channel = brcmf_cfg80211_cancel_remain_on_channel,
....@@ -5212,6 +5537,7 @@
52125537 struct brcmf_cfg80211_vif *vif_walk;
52135538 struct brcmf_cfg80211_vif *vif;
52145539 bool mbss;
5540
+ struct brcmf_if *ifp = brcmf_get_ifp(cfg->pub, 0);
52155541
52165542 brcmf_dbg(TRACE, "allocating virtual interface (size=%zu)\n",
52175543 sizeof(*vif));
....@@ -5224,7 +5550,8 @@
52245550
52255551 brcmf_init_prof(&vif->profile);
52265552
5227
- if (type == NL80211_IFTYPE_AP) {
5553
+ if (type == NL80211_IFTYPE_AP &&
5554
+ brcmf_feat_is_enabled(ifp, BRCMF_FEAT_MBSS)) {
52285555 mbss = false;
52295556 list_for_each_entry(vif_walk, &cfg->vif_list, list) {
52305557 if (vif_walk->wdev.iftype == NL80211_IFTYPE_AP) {
....@@ -5263,14 +5590,16 @@
52635590 u32 event = e->event_code;
52645591 u32 status = e->status;
52655592
5266
- if (vif->profile.use_fwsup == BRCMF_PROFILE_FWSUP_PSK &&
5593
+ if ((vif->profile.use_fwsup == BRCMF_PROFILE_FWSUP_PSK ||
5594
+ vif->profile.use_fwsup == BRCMF_PROFILE_FWSUP_SAE) &&
52675595 event == BRCMF_E_PSK_SUP &&
52685596 status == BRCMF_E_STATUS_FWSUP_COMPLETED)
52695597 set_bit(BRCMF_VIF_STATUS_EAP_SUCCESS, &vif->sme_state);
52705598 if (event == BRCMF_E_SET_SSID && status == BRCMF_E_STATUS_SUCCESS) {
52715599 brcmf_dbg(CONN, "Processing set ssid\n");
52725600 memcpy(vif->profile.bssid, e->addr, ETH_ALEN);
5273
- if (vif->profile.use_fwsup != BRCMF_PROFILE_FWSUP_PSK)
5601
+ if (vif->profile.use_fwsup != BRCMF_PROFILE_FWSUP_PSK &&
5602
+ vif->profile.use_fwsup != BRCMF_PROFILE_FWSUP_SAE)
52745603 return true;
52755604
52765605 set_bit(BRCMF_VIF_STATUS_ASSOC_SUCCESS, &vif->sme_state);
....@@ -5341,11 +5670,151 @@
53415670 conn_info->resp_ie_len = 0;
53425671 }
53435672
5673
+u8 brcmf_map_prio_to_prec(void *config, u8 prio)
5674
+{
5675
+ struct brcmf_cfg80211_info *cfg = (struct brcmf_cfg80211_info *)config;
5676
+
5677
+ if (!cfg)
5678
+ return (prio == PRIO_8021D_NONE || prio == PRIO_8021D_BE) ?
5679
+ (prio ^ 2) : prio;
5680
+
5681
+ /* For those AC(s) with ACM flag set to 1, convert its 4-level priority
5682
+ * to an 8-level precedence which is the same as BE's
5683
+ */
5684
+ if (prio > PRIO_8021D_EE &&
5685
+ cfg->ac_priority[prio] == cfg->ac_priority[PRIO_8021D_BE])
5686
+ return cfg->ac_priority[prio] * 2;
5687
+
5688
+ /* Conversion of 4-level priority to 8-level precedence */
5689
+ if (prio == PRIO_8021D_BE || prio == PRIO_8021D_BK ||
5690
+ prio == PRIO_8021D_CL || prio == PRIO_8021D_VO)
5691
+ return cfg->ac_priority[prio] * 2;
5692
+ else
5693
+ return cfg->ac_priority[prio] * 2 + 1;
5694
+}
5695
+
5696
+u8 brcmf_map_prio_to_aci(void *config, u8 prio)
5697
+{
5698
+ /* Prio here refers to the 802.1d priority in range of 0 to 7.
5699
+ * ACI here refers to the WLAN AC Index in range of 0 to 3.
5700
+ * This function will return ACI corresponding to input prio.
5701
+ */
5702
+ struct brcmf_cfg80211_info *cfg = (struct brcmf_cfg80211_info *)config;
5703
+
5704
+ if (cfg)
5705
+ return cfg->ac_priority[prio];
5706
+
5707
+ return prio;
5708
+}
5709
+
5710
+static void brcmf_init_wmm_prio(u8 *priority)
5711
+{
5712
+ /* Initialize AC priority array to default
5713
+ * 802.1d priority as per following table:
5714
+ * 802.1d prio 0,3 maps to BE
5715
+ * 802.1d prio 1,2 maps to BK
5716
+ * 802.1d prio 4,5 maps to VI
5717
+ * 802.1d prio 6,7 maps to VO
5718
+ */
5719
+ priority[0] = BRCMF_FWS_FIFO_AC_BE;
5720
+ priority[3] = BRCMF_FWS_FIFO_AC_BE;
5721
+ priority[1] = BRCMF_FWS_FIFO_AC_BK;
5722
+ priority[2] = BRCMF_FWS_FIFO_AC_BK;
5723
+ priority[4] = BRCMF_FWS_FIFO_AC_VI;
5724
+ priority[5] = BRCMF_FWS_FIFO_AC_VI;
5725
+ priority[6] = BRCMF_FWS_FIFO_AC_VO;
5726
+ priority[7] = BRCMF_FWS_FIFO_AC_VO;
5727
+}
5728
+
5729
+static void brcmf_wifi_prioritize_acparams(const
5730
+ struct brcmf_cfg80211_edcf_acparam *acp, u8 *priority)
5731
+{
5732
+ u8 aci;
5733
+ u8 aifsn;
5734
+ u8 ecwmin;
5735
+ u8 ecwmax;
5736
+ u8 acm;
5737
+ u8 ranking_basis[EDCF_AC_COUNT];
5738
+ u8 aci_prio[EDCF_AC_COUNT]; /* AC_BE, AC_BK, AC_VI, AC_VO */
5739
+ u8 index;
5740
+
5741
+ for (aci = 0; aci < EDCF_AC_COUNT; aci++, acp++) {
5742
+ aifsn = acp->ACI & EDCF_AIFSN_MASK;
5743
+ acm = (acp->ACI & EDCF_ACM_MASK) ? 1 : 0;
5744
+ ecwmin = acp->ECW & EDCF_ECWMIN_MASK;
5745
+ ecwmax = (acp->ECW & EDCF_ECWMAX_MASK) >> EDCF_ECWMAX_SHIFT;
5746
+ brcmf_dbg(CONN, "ACI %d aifsn %d acm %d ecwmin %d ecwmax %d\n",
5747
+ aci, aifsn, acm, ecwmin, ecwmax);
5748
+ /* Default AC_VO will be the lowest ranking value */
5749
+ ranking_basis[aci] = aifsn + ecwmin + ecwmax;
5750
+ /* Initialise priority starting at 0 (AC_BE) */
5751
+ aci_prio[aci] = 0;
5752
+
5753
+ /* If ACM is set, STA can't use this AC as per 802.11.
5754
+ * Change the ranking to BE
5755
+ */
5756
+ if (aci != AC_BE && aci != AC_BK && acm == 1)
5757
+ ranking_basis[aci] = ranking_basis[AC_BE];
5758
+ }
5759
+
5760
+ /* Ranking method which works for AC priority
5761
+ * swapping when values for cwmin, cwmax and aifsn are varied
5762
+ * Compare each aci_prio against each other aci_prio
5763
+ */
5764
+ for (aci = 0; aci < EDCF_AC_COUNT; aci++) {
5765
+ for (index = 0; index < EDCF_AC_COUNT; index++) {
5766
+ if (index != aci) {
5767
+ /* Smaller ranking value has higher priority,
5768
+ * so increment priority for each ACI which has
5769
+ * a higher ranking value
5770
+ */
5771
+ if (ranking_basis[aci] < ranking_basis[index])
5772
+ aci_prio[aci]++;
5773
+ }
5774
+ }
5775
+ }
5776
+
5777
+ /* By now, aci_prio[] will be in range of 0 to 3.
5778
+ * Use ACI prio to get the new priority value for
5779
+ * each 802.1d traffic type, in this range.
5780
+ */
5781
+ if (!(aci_prio[AC_BE] == aci_prio[AC_BK] &&
5782
+ aci_prio[AC_BK] == aci_prio[AC_VI] &&
5783
+ aci_prio[AC_VI] == aci_prio[AC_VO])) {
5784
+ /* 802.1d 0,3 maps to BE */
5785
+ priority[0] = aci_prio[AC_BE];
5786
+ priority[3] = aci_prio[AC_BE];
5787
+
5788
+ /* 802.1d 1,2 maps to BK */
5789
+ priority[1] = aci_prio[AC_BK];
5790
+ priority[2] = aci_prio[AC_BK];
5791
+
5792
+ /* 802.1d 4,5 maps to VO */
5793
+ priority[4] = aci_prio[AC_VI];
5794
+ priority[5] = aci_prio[AC_VI];
5795
+
5796
+ /* 802.1d 6,7 maps to VO */
5797
+ priority[6] = aci_prio[AC_VO];
5798
+ priority[7] = aci_prio[AC_VO];
5799
+ } else {
5800
+ /* Initialize to default priority */
5801
+ brcmf_init_wmm_prio(priority);
5802
+ }
5803
+
5804
+ brcmf_dbg(CONN, "Adj prio BE 0->%d, BK 1->%d, BK 2->%d, BE 3->%d\n",
5805
+ priority[0], priority[1], priority[2], priority[3]);
5806
+
5807
+ brcmf_dbg(CONN, "Adj prio VI 4->%d, VI 5->%d, VO 6->%d, VO 7->%d\n",
5808
+ priority[4], priority[5], priority[6], priority[7]);
5809
+}
5810
+
53445811 static s32 brcmf_get_assoc_ies(struct brcmf_cfg80211_info *cfg,
53455812 struct brcmf_if *ifp)
53465813 {
5814
+ struct brcmf_pub *drvr = cfg->pub;
53475815 struct brcmf_cfg80211_assoc_ielen_le *assoc_info;
53485816 struct brcmf_cfg80211_connect_info *conn_info = cfg_to_conn(cfg);
5817
+ struct brcmf_cfg80211_edcf_acparam edcf_acparam_info[EDCF_AC_COUNT];
53495818 u32 req_len;
53505819 u32 resp_len;
53515820 s32 err = 0;
....@@ -5355,7 +5824,7 @@
53555824 err = brcmf_fil_iovar_data_get(ifp, "assoc_info",
53565825 cfg->extra_buf, WL_ASSOC_INFO_MAX);
53575826 if (err) {
5358
- brcmf_err("could not get assoc info (%d)\n", err);
5827
+ bphy_err(drvr, "could not get assoc info (%d)\n", err);
53595828 return err;
53605829 }
53615830 assoc_info =
....@@ -5367,7 +5836,7 @@
53675836 cfg->extra_buf,
53685837 WL_ASSOC_INFO_MAX);
53695838 if (err) {
5370
- brcmf_err("could not get assoc req (%d)\n", err);
5839
+ bphy_err(drvr, "could not get assoc req (%d)\n", err);
53715840 return err;
53725841 }
53735842 conn_info->req_ie_len = req_len;
....@@ -5385,7 +5854,7 @@
53855854 cfg->extra_buf,
53865855 WL_ASSOC_INFO_MAX);
53875856 if (err) {
5388
- brcmf_err("could not get assoc resp (%d)\n", err);
5857
+ bphy_err(drvr, "could not get assoc resp (%d)\n", err);
53895858 return err;
53905859 }
53915860 conn_info->resp_ie_len = resp_len;
....@@ -5394,6 +5863,17 @@
53945863 GFP_KERNEL);
53955864 if (!conn_info->resp_ie)
53965865 conn_info->resp_ie_len = 0;
5866
+
5867
+ err = brcmf_fil_iovar_data_get(ifp, "wme_ac_sta",
5868
+ edcf_acparam_info,
5869
+ sizeof(edcf_acparam_info));
5870
+ if (err) {
5871
+ brcmf_err("could not get wme_ac_sta (%d)\n", err);
5872
+ return err;
5873
+ }
5874
+
5875
+ brcmf_wifi_prioritize_acparams(edcf_acparam_info,
5876
+ cfg->ac_priority);
53975877 } else {
53985878 conn_info->resp_ie_len = 0;
53995879 conn_info->resp_ie = NULL;
....@@ -5467,6 +5947,11 @@
54675947 cfg80211_roamed(ndev, &roam_info, GFP_KERNEL);
54685948 brcmf_dbg(CONN, "Report roaming result\n");
54695949
5950
+ if (profile->use_fwsup == BRCMF_PROFILE_FWSUP_1X && profile->is_ft) {
5951
+ cfg80211_port_authorized(ndev, profile->bssid, GFP_KERNEL);
5952
+ brcmf_dbg(CONN, "Report port authorized\n");
5953
+ }
5954
+
54705955 set_bit(BRCMF_VIF_STATUS_CONNECTED, &ifp->vif->sme_state);
54715956 brcmf_dbg(TRACE, "Exit\n");
54725957 return err;
....@@ -5514,6 +5999,7 @@
55145999 struct net_device *ndev,
55156000 const struct brcmf_event_msg *e, void *data)
55166001 {
6002
+ struct brcmf_pub *drvr = cfg->pub;
55176003 static int generation;
55186004 u32 event = e->event_code;
55196005 u32 reason = e->reason;
....@@ -5531,7 +6017,7 @@
55316017 if (((event == BRCMF_E_ASSOC_IND) || (event == BRCMF_E_REASSOC_IND)) &&
55326018 (reason == BRCMF_E_STATUS_SUCCESS)) {
55336019 if (!data) {
5534
- brcmf_err("No IEs present in ASSOC/REASSOC_IND");
6020
+ bphy_err(drvr, "No IEs present in ASSOC/REASSOC_IND\n");
55356021 return -EINVAL;
55366022 }
55376023
....@@ -5589,10 +6075,19 @@
55896075 brcmf_net_setcarrier(ifp, true);
55906076 } else if (brcmf_is_linkdown(ifp->vif, e)) {
55916077 brcmf_dbg(CONN, "Linkdown\n");
5592
- if (!brcmf_is_ibssmode(ifp->vif)) {
6078
+ if (!brcmf_is_ibssmode(ifp->vif) &&
6079
+ test_bit(BRCMF_VIF_STATUS_CONNECTED,
6080
+ &ifp->vif->sme_state)) {
6081
+ if (memcmp(profile->bssid, e->addr, ETH_ALEN))
6082
+ return err;
6083
+
55936084 brcmf_bss_connect_done(cfg, ndev, e, false);
55946085 brcmf_link_down(ifp->vif,
5595
- brcmf_map_fw_linkdown_reason(e));
6086
+ brcmf_map_fw_linkdown_reason(e),
6087
+ e->event_code &
6088
+ (BRCMF_E_DEAUTH_IND |
6089
+ BRCMF_E_DISASSOC_IND)
6090
+ ? false : true);
55966091 brcmf_init_prof(ndev_to_prof(ndev));
55976092 if (ndev != cfg_to_ndev(cfg))
55986093 complete(&cfg->vif_disabled);
....@@ -5804,6 +6299,7 @@
58046299 mutex_init(&cfg->usr_sync);
58056300 brcmf_init_escan(cfg);
58066301 brcmf_init_conf(cfg->conf);
6302
+ brcmf_init_wmm_prio(cfg->ac_priority);
58076303 init_completion(&cfg->vif_disabled);
58086304 return err;
58096305 }
....@@ -5823,6 +6319,7 @@
58236319
58246320 static s32 brcmf_dongle_roam(struct brcmf_if *ifp)
58256321 {
6322
+ struct brcmf_pub *drvr = ifp->drvr;
58266323 s32 err;
58276324 u32 bcn_timeout;
58286325 __le32 roamtrigger[2];
....@@ -5835,7 +6332,7 @@
58356332 bcn_timeout = BRCMF_DEFAULT_BCN_TIMEOUT_ROAM_ON;
58366333 err = brcmf_fil_iovar_int_set(ifp, "bcn_timeout", bcn_timeout);
58376334 if (err) {
5838
- brcmf_err("bcn_timeout error (%d)\n", err);
6335
+ bphy_err(drvr, "bcn_timeout error (%d)\n", err);
58396336 goto roam_setup_done;
58406337 }
58416338
....@@ -5847,7 +6344,7 @@
58476344 err = brcmf_fil_iovar_int_set(ifp, "roam_off",
58486345 ifp->drvr->settings->roamoff);
58496346 if (err) {
5850
- brcmf_err("roam_off error (%d)\n", err);
6347
+ bphy_err(drvr, "roam_off error (%d)\n", err);
58516348 goto roam_setup_done;
58526349 }
58536350
....@@ -5855,19 +6352,17 @@
58556352 roamtrigger[1] = cpu_to_le32(BRCM_BAND_ALL);
58566353 err = brcmf_fil_cmd_data_set(ifp, BRCMF_C_SET_ROAM_TRIGGER,
58576354 (void *)roamtrigger, sizeof(roamtrigger));
5858
- if (err) {
5859
- brcmf_err("WLC_SET_ROAM_TRIGGER error (%d)\n", err);
5860
- goto roam_setup_done;
5861
- }
6355
+ if (err)
6356
+ bphy_err(drvr, "WLC_SET_ROAM_TRIGGER error (%d)\n", err);
58626357
58636358 roam_delta[0] = cpu_to_le32(WL_ROAM_DELTA);
58646359 roam_delta[1] = cpu_to_le32(BRCM_BAND_ALL);
58656360 err = brcmf_fil_cmd_data_set(ifp, BRCMF_C_SET_ROAM_DELTA,
58666361 (void *)roam_delta, sizeof(roam_delta));
5867
- if (err) {
5868
- brcmf_err("WLC_SET_ROAM_DELTA error (%d)\n", err);
5869
- goto roam_setup_done;
5870
- }
6362
+ if (err)
6363
+ bphy_err(drvr, "WLC_SET_ROAM_DELTA error (%d)\n", err);
6364
+
6365
+ return 0;
58716366
58726367 roam_setup_done:
58736368 return err;
....@@ -5876,25 +6371,26 @@
58766371 static s32
58776372 brcmf_dongle_scantime(struct brcmf_if *ifp)
58786373 {
6374
+ struct brcmf_pub *drvr = ifp->drvr;
58796375 s32 err = 0;
58806376
58816377 err = brcmf_fil_cmd_int_set(ifp, BRCMF_C_SET_SCAN_CHANNEL_TIME,
58826378 BRCMF_SCAN_CHANNEL_TIME);
58836379 if (err) {
5884
- brcmf_err("Scan assoc time error (%d)\n", err);
6380
+ bphy_err(drvr, "Scan assoc time error (%d)\n", err);
58856381 goto dongle_scantime_out;
58866382 }
58876383 err = brcmf_fil_cmd_int_set(ifp, BRCMF_C_SET_SCAN_UNASSOC_TIME,
58886384 BRCMF_SCAN_UNASSOC_TIME);
58896385 if (err) {
5890
- brcmf_err("Scan unassoc time error (%d)\n", err);
6386
+ bphy_err(drvr, "Scan unassoc time error (%d)\n", err);
58916387 goto dongle_scantime_out;
58926388 }
58936389
58946390 err = brcmf_fil_cmd_int_set(ifp, BRCMF_C_SET_SCAN_PASSIVE_TIME,
58956391 BRCMF_SCAN_PASSIVE_TIME);
58966392 if (err) {
5897
- brcmf_err("Scan passive time error (%d)\n", err);
6393
+ bphy_err(drvr, "Scan passive time error (%d)\n", err);
58986394 goto dongle_scantime_out;
58996395 }
59006396
....@@ -5926,10 +6422,11 @@
59266422 static int brcmf_construct_chaninfo(struct brcmf_cfg80211_info *cfg,
59276423 u32 bw_cap[])
59286424 {
5929
- struct brcmf_if *ifp = brcmf_get_ifp(cfg->pub, 0);
6425
+ struct wiphy *wiphy = cfg_to_wiphy(cfg);
6426
+ struct brcmf_pub *drvr = cfg->pub;
6427
+ struct brcmf_if *ifp = brcmf_get_ifp(drvr, 0);
59306428 struct ieee80211_supported_band *band;
59316429 struct ieee80211_channel *channel;
5932
- struct wiphy *wiphy;
59336430 struct brcmf_chanspec_list *list;
59346431 struct brcmu_chan ch;
59356432 int err;
....@@ -5948,11 +6445,10 @@
59486445 err = brcmf_fil_iovar_data_get(ifp, "chanspecs", pbuf,
59496446 BRCMF_DCMD_MEDLEN);
59506447 if (err) {
5951
- brcmf_err("get chanspecs error (%d)\n", err);
6448
+ bphy_err(drvr, "get chanspecs error (%d)\n", err);
59526449 goto fail_pbuf;
59536450 }
59546451
5955
- wiphy = cfg_to_wiphy(cfg);
59566452 band = wiphy->bands[NL80211_BAND_2GHZ];
59576453 if (band)
59586454 for (i = 0; i < band->n_channels; i++)
....@@ -5972,7 +6468,8 @@
59726468 } else if (ch.band == BRCMU_CHAN_BAND_5G) {
59736469 band = wiphy->bands[NL80211_BAND_5GHZ];
59746470 } else {
5975
- brcmf_err("Invalid channel Spec. 0x%x.\n", ch.chspec);
6471
+ bphy_err(drvr, "Invalid channel Spec. 0x%x.\n",
6472
+ ch.chspec);
59766473 continue;
59776474 }
59786475 if (!band)
....@@ -5995,8 +6492,8 @@
59956492 /* It seems firmware supports some channel we never
59966493 * considered. Something new in IEEE standard?
59976494 */
5998
- brcmf_err("Ignoring unexpected firmware channel %d\n",
5999
- ch.control_ch_num);
6495
+ bphy_err(drvr, "Ignoring unexpected firmware channel %d\n",
6496
+ ch.control_ch_num);
60006497 continue;
60016498 }
60026499
....@@ -6006,11 +6503,21 @@
60066503 /* assuming the chanspecs order is HT20,
60076504 * HT40 upper, HT40 lower, and VHT80.
60086505 */
6009
- if (ch.bw == BRCMU_CHAN_BW_80) {
6506
+ switch (ch.bw) {
6507
+ case BRCMU_CHAN_BW_160:
6508
+ channel->flags &= ~IEEE80211_CHAN_NO_160MHZ;
6509
+ break;
6510
+ case BRCMU_CHAN_BW_80:
60106511 channel->flags &= ~IEEE80211_CHAN_NO_80MHZ;
6011
- } else if (ch.bw == BRCMU_CHAN_BW_40) {
6512
+ break;
6513
+ case BRCMU_CHAN_BW_40:
60126514 brcmf_update_bw40_channel_flag(channel, &ch);
6013
- } else {
6515
+ break;
6516
+ default:
6517
+ wiphy_warn(wiphy, "Firmware reported unsupported bandwidth %d\n",
6518
+ ch.bw);
6519
+ fallthrough;
6520
+ case BRCMU_CHAN_BW_20:
60146521 /* enable the channel and disable other bandwidths
60156522 * for now as mentioned order assure they are enabled
60166523 * for subsequent chanspecs.
....@@ -6042,7 +6549,8 @@
60426549
60436550 static int brcmf_enable_bw40_2g(struct brcmf_cfg80211_info *cfg)
60446551 {
6045
- struct brcmf_if *ifp = brcmf_get_ifp(cfg->pub, 0);
6552
+ struct brcmf_pub *drvr = cfg->pub;
6553
+ struct brcmf_if *ifp = brcmf_get_ifp(drvr, 0);
60466554 struct ieee80211_supported_band *band;
60476555 struct brcmf_fil_bwcap_le band_bwcap;
60486556 struct brcmf_chanspec_list *list;
....@@ -6088,7 +6596,7 @@
60886596 err = brcmf_fil_iovar_data_get(ifp, "chanspecs", pbuf,
60896597 BRCMF_DCMD_MEDLEN);
60906598 if (err) {
6091
- brcmf_err("get chanspecs error (%d)\n", err);
6599
+ bphy_err(drvr, "get chanspecs error (%d)\n", err);
60926600 kfree(pbuf);
60936601 return err;
60946602 }
....@@ -6119,6 +6627,7 @@
61196627
61206628 static void brcmf_get_bwcap(struct brcmf_if *ifp, u32 bw_cap[])
61216629 {
6630
+ struct brcmf_pub *drvr = ifp->drvr;
61226631 u32 band, mimo_bwcap;
61236632 int err;
61246633
....@@ -6145,16 +6654,16 @@
61456654 switch (mimo_bwcap) {
61466655 case WLC_N_BW_40ALL:
61476656 bw_cap[NL80211_BAND_2GHZ] |= WLC_BW_40MHZ_BIT;
6148
- /* fall-thru */
6657
+ fallthrough;
61496658 case WLC_N_BW_20IN2G_40IN5G:
61506659 bw_cap[NL80211_BAND_5GHZ] |= WLC_BW_40MHZ_BIT;
6151
- /* fall-thru */
6660
+ fallthrough;
61526661 case WLC_N_BW_20ALL:
61536662 bw_cap[NL80211_BAND_2GHZ] |= WLC_BW_20MHZ_BIT;
61546663 bw_cap[NL80211_BAND_5GHZ] |= WLC_BW_20MHZ_BIT;
61556664 break;
61566665 default:
6157
- brcmf_err("invalid mimo_bw_cap value\n");
6666
+ bphy_err(drvr, "invalid mimo_bw_cap value\n");
61586667 }
61596668 }
61606669
....@@ -6229,8 +6738,9 @@
62296738
62306739 static int brcmf_setup_wiphybands(struct brcmf_cfg80211_info *cfg)
62316740 {
6232
- struct brcmf_if *ifp = brcmf_get_ifp(cfg->pub, 0);
6233
- struct wiphy *wiphy;
6741
+ struct brcmf_pub *drvr = cfg->pub;
6742
+ struct brcmf_if *ifp = brcmf_get_ifp(drvr, 0);
6743
+ struct wiphy *wiphy = cfg_to_wiphy(cfg);
62346744 u32 nmode = 0;
62356745 u32 vhtmode = 0;
62366746 u32 bw_cap[2] = { WLC_BW_20MHZ_BIT, WLC_BW_20MHZ_BIT };
....@@ -6246,7 +6756,7 @@
62466756 (void)brcmf_fil_iovar_int_get(ifp, "vhtmode", &vhtmode);
62476757 err = brcmf_fil_iovar_int_get(ifp, "nmode", &nmode);
62486758 if (err) {
6249
- brcmf_err("nmode error (%d)\n", err);
6759
+ bphy_err(drvr, "nmode error (%d)\n", err);
62506760 } else {
62516761 brcmf_get_bwcap(ifp, bw_cap);
62526762 }
....@@ -6256,7 +6766,7 @@
62566766
62576767 err = brcmf_fil_iovar_int_get(ifp, "rxchain", &rxchain);
62586768 if (err) {
6259
- brcmf_err("rxchain error (%d)\n", err);
6769
+ bphy_err(drvr, "rxchain error (%d)\n", err);
62606770 nchain = 1;
62616771 } else {
62626772 for (nchain = 0; rxchain; nchain++)
....@@ -6266,7 +6776,7 @@
62666776
62676777 err = brcmf_construct_chaninfo(cfg, bw_cap);
62686778 if (err) {
6269
- brcmf_err("brcmf_construct_chaninfo failed (%d)\n", err);
6779
+ bphy_err(drvr, "brcmf_construct_chaninfo failed (%d)\n", err);
62706780 return err;
62716781 }
62726782
....@@ -6278,7 +6788,6 @@
62786788 &txbf_bfr_cap);
62796789 }
62806790
6281
- wiphy = cfg_to_wiphy(cfg);
62826791 for (i = 0; i < ARRAY_SIZE(wiphy->bands); i++) {
62836792 band = wiphy->bands[i];
62846793 if (band == NULL)
....@@ -6351,6 +6860,9 @@
63516860 * #STA <= 1, #AP <= 1, channels = 1, 2 total
63526861 * #AP <= 4, matching BI, channels = 1, 4 total
63536862 *
6863
+ * no p2p and rsdb:
6864
+ * #STA <= 1, #AP <= 2, channels = 2, 4 total
6865
+ *
63546866 * p2p, no mchan, and mbss:
63556867 *
63566868 * #STA <= 1, #P2P-DEV <= 1, #{P2P-CL, P2P-GO} <= 1, channels = 1, 3 total
....@@ -6362,6 +6874,10 @@
63626874 * #STA <= 1, #P2P-DEV <= 1, #{P2P-CL, P2P-GO} <= 1, channels = 2, 3 total
63636875 * #STA <= 1, #P2P-DEV <= 1, #AP <= 1, #P2P-CL <= 1, channels = 1, 4 total
63646876 * #AP <= 4, matching BI, channels = 1, 4 total
6877
+ *
6878
+ * p2p, rsdb, and no mbss:
6879
+ * #STA <= 1, #P2P-DEV <= 1, #{P2P-CL, P2P-GO} <= 2, AP <= 2,
6880
+ * channels = 2, 4 total
63656881 */
63666882 static int brcmf_setup_ifmodes(struct wiphy *wiphy, struct brcmf_if *ifp)
63676883 {
....@@ -6369,13 +6885,16 @@
63696885 struct ieee80211_iface_limit *c0_limits = NULL;
63706886 struct ieee80211_iface_limit *p2p_limits = NULL;
63716887 struct ieee80211_iface_limit *mbss_limits = NULL;
6372
- bool mbss, p2p;
6373
- int i, c, n_combos;
6888
+ bool mon_flag, mbss, p2p, rsdb, mchan;
6889
+ int i, c, n_combos, n_limits;
63746890
6891
+ mon_flag = brcmf_feat_is_enabled(ifp, BRCMF_FEAT_MONITOR_FLAG);
63756892 mbss = brcmf_feat_is_enabled(ifp, BRCMF_FEAT_MBSS);
63766893 p2p = brcmf_feat_is_enabled(ifp, BRCMF_FEAT_P2P);
6894
+ rsdb = brcmf_feat_is_enabled(ifp, BRCMF_FEAT_RSDB);
6895
+ mchan = brcmf_feat_is_enabled(ifp, BRCMF_FEAT_MCHAN);
63776896
6378
- n_combos = 1 + !!p2p + !!mbss;
6897
+ n_combos = 1 + !!(p2p && !rsdb) + !!mbss;
63796898 combo = kcalloc(n_combos, sizeof(*combo), GFP_KERNEL);
63806899 if (!combo)
63816900 goto err;
....@@ -6383,37 +6902,53 @@
63836902 wiphy->interface_modes = BIT(NL80211_IFTYPE_STATION) |
63846903 BIT(NL80211_IFTYPE_ADHOC) |
63856904 BIT(NL80211_IFTYPE_AP);
6386
-
6387
- c = 0;
6388
- i = 0;
6389
- c0_limits = kcalloc(p2p ? 3 : 2, sizeof(*c0_limits), GFP_KERNEL);
6390
- if (!c0_limits)
6391
- goto err;
6392
- c0_limits[i].max = 1;
6393
- c0_limits[i++].types = BIT(NL80211_IFTYPE_STATION);
6394
- if (p2p) {
6395
- if (brcmf_feat_is_enabled(ifp, BRCMF_FEAT_MCHAN))
6396
- combo[c].num_different_channels = 2;
6397
- else
6398
- combo[c].num_different_channels = 1;
6905
+ if (mon_flag)
6906
+ wiphy->interface_modes |= BIT(NL80211_IFTYPE_MONITOR);
6907
+ if (p2p)
63996908 wiphy->interface_modes |= BIT(NL80211_IFTYPE_P2P_CLIENT) |
64006909 BIT(NL80211_IFTYPE_P2P_GO) |
64016910 BIT(NL80211_IFTYPE_P2P_DEVICE);
6911
+
6912
+ c = 0;
6913
+ i = 0;
6914
+ n_limits = 1 + mon_flag + (p2p ? 2 : 0) + (rsdb || !p2p);
6915
+ c0_limits = kcalloc(n_limits, sizeof(*c0_limits), GFP_KERNEL);
6916
+ if (!c0_limits)
6917
+ goto err;
6918
+
6919
+ combo[c].num_different_channels = 1 + (rsdb || (p2p && mchan));
6920
+ c0_limits[i].max = 1;
6921
+ c0_limits[i++].types = BIT(NL80211_IFTYPE_STATION);
6922
+ if (mon_flag) {
6923
+ c0_limits[i].max = 1;
6924
+ c0_limits[i++].types = BIT(NL80211_IFTYPE_MONITOR);
6925
+ }
6926
+ if (p2p) {
64026927 c0_limits[i].max = 1;
64036928 c0_limits[i++].types = BIT(NL80211_IFTYPE_P2P_DEVICE);
6404
- c0_limits[i].max = 1;
6929
+ c0_limits[i].max = 1 + rsdb;
64056930 c0_limits[i++].types = BIT(NL80211_IFTYPE_P2P_CLIENT) |
64066931 BIT(NL80211_IFTYPE_P2P_GO);
6932
+ }
6933
+ if (p2p && rsdb) {
6934
+ c0_limits[i].max = 2;
6935
+ c0_limits[i++].types = BIT(NL80211_IFTYPE_AP);
6936
+ combo[c].max_interfaces = 4;
6937
+ } else if (p2p) {
6938
+ combo[c].max_interfaces = i;
6939
+ } else if (rsdb) {
6940
+ c0_limits[i].max = 2;
6941
+ c0_limits[i++].types = BIT(NL80211_IFTYPE_AP);
6942
+ combo[c].max_interfaces = 3;
64076943 } else {
6408
- combo[c].num_different_channels = 1;
64096944 c0_limits[i].max = 1;
64106945 c0_limits[i++].types = BIT(NL80211_IFTYPE_AP);
6946
+ combo[c].max_interfaces = i;
64116947 }
6412
- combo[c].max_interfaces = i;
64136948 combo[c].n_limits = i;
64146949 combo[c].limits = c0_limits;
64156950
6416
- if (p2p) {
6951
+ if (p2p && !rsdb) {
64176952 c++;
64186953 i = 0;
64196954 p2p_limits = kcalloc(4, sizeof(*p2p_limits), GFP_KERNEL);
....@@ -6436,14 +6971,20 @@
64366971 if (mbss) {
64376972 c++;
64386973 i = 0;
6439
- mbss_limits = kcalloc(1, sizeof(*mbss_limits), GFP_KERNEL);
6974
+ n_limits = 1 + mon_flag;
6975
+ mbss_limits = kcalloc(n_limits, sizeof(*mbss_limits),
6976
+ GFP_KERNEL);
64406977 if (!mbss_limits)
64416978 goto err;
64426979 mbss_limits[i].max = 4;
64436980 mbss_limits[i++].types = BIT(NL80211_IFTYPE_AP);
6981
+ if (mon_flag) {
6982
+ mbss_limits[i].max = 1;
6983
+ mbss_limits[i++].types = BIT(NL80211_IFTYPE_MONITOR);
6984
+ }
64446985 combo[c].beacon_int_infra_match = true;
64456986 combo[c].num_different_channels = 1;
6446
- combo[c].max_interfaces = 4;
6987
+ combo[c].max_interfaces = 4 + mon_flag;
64476988 combo[c].n_limits = i;
64486989 combo[c].limits = mbss_limits;
64496990 }
....@@ -6474,12 +7015,13 @@
64747015 {
64757016 #ifdef CONFIG_PM
64767017 struct brcmf_cfg80211_info *cfg = wiphy_to_cfg(wiphy);
7018
+ struct brcmf_pub *drvr = cfg->pub;
64777019 struct wiphy_wowlan_support *wowl;
64787020
64797021 wowl = kmemdup(&brcmf_wowlan_support, sizeof(brcmf_wowlan_support),
64807022 GFP_KERNEL);
64817023 if (!wowl) {
6482
- brcmf_err("only support basic wowlan features\n");
7024
+ bphy_err(drvr, "only support basic wowlan features\n");
64837025 wiphy->wowlan = &brcmf_wowlan_support;
64847026 return;
64857027 }
....@@ -6560,6 +7102,16 @@
65607102 NL80211_EXT_FEATURE_4WAY_HANDSHAKE_STA_PSK);
65617103 wiphy_ext_feature_set(wiphy,
65627104 NL80211_EXT_FEATURE_4WAY_HANDSHAKE_STA_1X);
7105
+ if (brcmf_feat_is_enabled(ifp, BRCMF_FEAT_SAE))
7106
+ wiphy_ext_feature_set(wiphy,
7107
+ NL80211_EXT_FEATURE_SAE_OFFLOAD);
7108
+ }
7109
+ if (brcmf_feat_is_enabled(ifp, BRCMF_FEAT_FWAUTH)) {
7110
+ wiphy_ext_feature_set(wiphy,
7111
+ NL80211_EXT_FEATURE_4WAY_HANDSHAKE_AP_PSK);
7112
+ if (brcmf_feat_is_enabled(ifp, BRCMF_FEAT_SAE))
7113
+ wiphy_ext_feature_set(wiphy,
7114
+ NL80211_EXT_FEATURE_SAE_OFFLOAD_AP);
65637115 }
65647116 wiphy->mgmt_stypes = brcmf_txrx_stypes;
65657117 wiphy->max_remain_on_channel_duration = 5000;
....@@ -6576,7 +7128,7 @@
65767128 err = brcmf_fil_cmd_data_get(ifp, BRCMF_C_GET_BANDLIST, &bandlist,
65777129 sizeof(bandlist));
65787130 if (err) {
6579
- brcmf_err("could not obtain band info: err=%d\n", err);
7131
+ bphy_err(drvr, "could not obtain band info: err=%d\n", err);
65807132 return err;
65817133 }
65827134 /* first entry in bandlist is number of bands */
....@@ -6618,6 +7170,11 @@
66187170 }
66197171 }
66207172
7173
+ if (wiphy->bands[NL80211_BAND_5GHZ] &&
7174
+ brcmf_feat_is_enabled(ifp, BRCMF_FEAT_DOT11H))
7175
+ wiphy_ext_feature_set(wiphy,
7176
+ NL80211_EXT_FEATURE_DFS_OFFLOAD);
7177
+
66217178 wiphy_read_of_freq_limits(wiphy);
66227179
66237180 return 0;
....@@ -6625,6 +7182,7 @@
66257182
66267183 static s32 brcmf_config_dongle(struct brcmf_cfg80211_info *cfg)
66277184 {
7185
+ struct brcmf_pub *drvr = cfg->pub;
66287186 struct net_device *ndev;
66297187 struct wireless_dev *wdev;
66307188 struct brcmf_if *ifp;
....@@ -6660,6 +7218,12 @@
66607218
66617219 brcmf_configure_arp_nd_offload(ifp, true);
66627220
7221
+ err = brcmf_fil_cmd_int_set(ifp, BRCMF_C_SET_FAKEFRAG, 1);
7222
+ if (err) {
7223
+ bphy_err(drvr, "failed to set frameburst mode\n");
7224
+ goto default_conf_out;
7225
+ }
7226
+
66637227 cfg->dongle_up = true;
66647228 default_conf_out:
66657229
....@@ -6683,7 +7247,7 @@
66837247 * from AP to save power
66847248 */
66857249 if (check_vif_up(ifp->vif)) {
6686
- brcmf_link_down(ifp->vif, WLAN_REASON_UNSPECIFIED);
7250
+ brcmf_link_down(ifp->vif, WLAN_REASON_UNSPECIFIED, true);
66877251
66887252 /* Make sure WPA_Supplicant receives all the event
66897253 generated due to DISASSOC call to the fw to keep
....@@ -6837,6 +7401,7 @@
68377401 {
68387402 struct brcmf_cfg80211_info *cfg = wiphy_to_cfg(wiphy);
68397403 struct brcmf_if *ifp = brcmf_get_ifp(cfg->pub, 0);
7404
+ struct brcmf_pub *drvr = cfg->pub;
68407405 struct brcmf_fil_country_le ccreq;
68417406 s32 err;
68427407 int i;
....@@ -6848,8 +7413,8 @@
68487413 /* ignore non-ISO3166 country codes */
68497414 for (i = 0; i < 2; i++)
68507415 if (req->alpha2[i] < 'A' || req->alpha2[i] > 'Z') {
6851
- brcmf_err("not an ISO3166 code (0x%02x 0x%02x)\n",
6852
- req->alpha2[0], req->alpha2[1]);
7416
+ bphy_err(drvr, "not an ISO3166 code (0x%02x 0x%02x)\n",
7417
+ req->alpha2[0], req->alpha2[1]);
68537418 return;
68547419 }
68557420
....@@ -6858,7 +7423,7 @@
68587423
68597424 err = brcmf_fil_iovar_data_get(ifp, "country", &ccreq, sizeof(ccreq));
68607425 if (err) {
6861
- brcmf_err("Country code iovar returned err = %d\n", err);
7426
+ bphy_err(drvr, "Country code iovar returned err = %d\n", err);
68627427 return;
68637428 }
68647429
....@@ -6868,7 +7433,7 @@
68687433
68697434 err = brcmf_fil_iovar_data_set(ifp, "country", &ccreq, sizeof(ccreq));
68707435 if (err) {
6871
- brcmf_err("Firmware rejected country setting\n");
7436
+ bphy_err(drvr, "Firmware rejected country setting\n");
68727437 return;
68737438 }
68747439 brcmf_setup_wiphybands(cfg);
....@@ -6914,13 +7479,13 @@
69147479 u16 *cap = NULL;
69157480
69167481 if (!ndev) {
6917
- brcmf_err("ndev is invalid\n");
7482
+ bphy_err(drvr, "ndev is invalid\n");
69187483 return NULL;
69197484 }
69207485
69217486 cfg = kzalloc(sizeof(*cfg), GFP_KERNEL);
69227487 if (!cfg) {
6923
- brcmf_err("Could not allocate wiphy device\n");
7488
+ bphy_err(drvr, "Could not allocate wiphy device\n");
69247489 return NULL;
69257490 }
69267491
....@@ -6941,7 +7506,7 @@
69417506
69427507 err = wl_init_priv(cfg);
69437508 if (err) {
6944
- brcmf_err("Failed to init iwm_priv (%d)\n", err);
7509
+ bphy_err(drvr, "Failed to init iwm_priv (%d)\n", err);
69457510 brcmf_free_vif(vif);
69467511 goto wiphy_out;
69477512 }
....@@ -6950,7 +7515,7 @@
69507515 /* determine d11 io type before wiphy setup */
69517516 err = brcmf_fil_cmd_int_get(ifp, BRCMF_C_GET_VERSION, &io_type);
69527517 if (err) {
6953
- brcmf_err("Failed to get D11 version (%d)\n", err);
7518
+ bphy_err(drvr, "Failed to get D11 version (%d)\n", err);
69547519 goto priv_out;
69557520 }
69567521 cfg->d11inf.io_type = (u8)io_type;
....@@ -6984,13 +7549,13 @@
69847549 #endif
69857550 err = wiphy_register(wiphy);
69867551 if (err < 0) {
6987
- brcmf_err("Could not register wiphy device (%d)\n", err);
7552
+ bphy_err(drvr, "Could not register wiphy device (%d)\n", err);
69887553 goto priv_out;
69897554 }
69907555
69917556 err = brcmf_setup_wiphybands(cfg);
69927557 if (err) {
6993
- brcmf_err("Setting wiphy bands failed (%d)\n", err);
7558
+ bphy_err(drvr, "Setting wiphy bands failed (%d)\n", err);
69947559 goto wiphy_unreg_out;
69957560 }
69967561
....@@ -7008,24 +7573,24 @@
70087573
70097574 err = brcmf_fweh_activate_events(ifp);
70107575 if (err) {
7011
- brcmf_err("FWEH activation failed (%d)\n", err);
7576
+ bphy_err(drvr, "FWEH activation failed (%d)\n", err);
70127577 goto wiphy_unreg_out;
70137578 }
70147579
70157580 err = brcmf_p2p_attach(cfg, p2pdev_forced);
70167581 if (err) {
7017
- brcmf_err("P2P initialisation failed (%d)\n", err);
7582
+ bphy_err(drvr, "P2P initialisation failed (%d)\n", err);
70187583 goto wiphy_unreg_out;
70197584 }
70207585 err = brcmf_btcoex_attach(cfg);
70217586 if (err) {
7022
- brcmf_err("BT-coex initialisation failed (%d)\n", err);
7587
+ bphy_err(drvr, "BT-coex initialisation failed (%d)\n", err);
70237588 brcmf_p2p_detach(&cfg->p2p);
70247589 goto wiphy_unreg_out;
70257590 }
70267591 err = brcmf_pno_attach(cfg);
70277592 if (err) {
7028
- brcmf_err("PNO initialisation failed (%d)\n", err);
7593
+ bphy_err(drvr, "PNO initialisation failed (%d)\n", err);
70297594 brcmf_btcoex_detach(cfg);
70307595 brcmf_p2p_detach(&cfg->p2p);
70317596 goto wiphy_unreg_out;
....@@ -7045,7 +7610,7 @@
70457610 /* (re-) activate FWEH event handling */
70467611 err = brcmf_fweh_activate_events(ifp);
70477612 if (err) {
7048
- brcmf_err("FWEH activation failed (%d)\n", err);
7613
+ bphy_err(drvr, "FWEH activation failed (%d)\n", err);
70497614 goto detach;
70507615 }
70517616
....@@ -7085,7 +7650,6 @@
70857650 brcmf_pno_detach(cfg);
70867651 brcmf_btcoex_detach(cfg);
70877652 wiphy_unregister(cfg->wiphy);
7088
- kfree(cfg->ops);
70897653 wl_deinit_priv(cfg);
70907654 brcmf_free_wiphy(cfg->wiphy);
70917655 kfree(cfg);