2 * Copyright (c) 2004-2011 Atheros Communications Inc.
3 * Copyright (c) 2011-2012 Qualcomm Atheros, Inc.
5 * Permission to use, copy, modify, and/or distribute this software for any
6 * purpose with or without fee is hereby granted, provided that the above
7 * copyright notice and this permission notice appear in all copies.
9 * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
10 * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
11 * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
12 * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
13 * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
14 * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
15 * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
18 #define pr_fmt(fmt) KBUILD_MODNAME ": " fmt
20 #include <linux/moduleparam.h>
21 #include <linux/inetdevice.h>
22 #include <linux/export.h>
30 #define RATETAB_ENT(_rate, _rateid, _flags) { \
33 .hw_value = (_rateid), \
36 #define CHAN2G(_channel, _freq, _flags) { \
37 .band = IEEE80211_BAND_2GHZ, \
38 .hw_value = (_channel), \
39 .center_freq = (_freq), \
41 .max_antenna_gain = 0, \
45 #define CHAN5G(_channel, _flags) { \
46 .band = IEEE80211_BAND_5GHZ, \
47 .hw_value = (_channel), \
48 .center_freq = 5000 + (5 * (_channel)), \
50 .max_antenna_gain = 0, \
54 #define DEFAULT_BG_SCAN_PERIOD 60
56 static struct ieee80211_rate ath6kl_rates
[] = {
57 RATETAB_ENT(10, 0x1, 0),
58 RATETAB_ENT(20, 0x2, 0),
59 RATETAB_ENT(55, 0x4, 0),
60 RATETAB_ENT(110, 0x8, 0),
61 RATETAB_ENT(60, 0x10, 0),
62 RATETAB_ENT(90, 0x20, 0),
63 RATETAB_ENT(120, 0x40, 0),
64 RATETAB_ENT(180, 0x80, 0),
65 RATETAB_ENT(240, 0x100, 0),
66 RATETAB_ENT(360, 0x200, 0),
67 RATETAB_ENT(480, 0x400, 0),
68 RATETAB_ENT(540, 0x800, 0),
71 #define ath6kl_a_rates (ath6kl_rates + 4)
72 #define ath6kl_a_rates_size 8
73 #define ath6kl_g_rates (ath6kl_rates + 0)
74 #define ath6kl_g_rates_size 12
76 #define ath6kl_g_htcap IEEE80211_HT_CAP_SGI_20
77 #define ath6kl_a_htcap (IEEE80211_HT_CAP_SUP_WIDTH_20_40 | \
78 IEEE80211_HT_CAP_SGI_20 | \
79 IEEE80211_HT_CAP_SGI_40)
81 static struct ieee80211_channel ath6kl_2ghz_channels
[] = {
98 static struct ieee80211_channel ath6kl_5ghz_a_channels
[] = {
99 CHAN5G(34, 0), CHAN5G(36, 0),
100 CHAN5G(38, 0), CHAN5G(40, 0),
101 CHAN5G(42, 0), CHAN5G(44, 0),
102 CHAN5G(46, 0), CHAN5G(48, 0),
103 CHAN5G(52, 0), CHAN5G(56, 0),
104 CHAN5G(60, 0), CHAN5G(64, 0),
105 CHAN5G(100, 0), CHAN5G(104, 0),
106 CHAN5G(108, 0), CHAN5G(112, 0),
107 CHAN5G(116, 0), CHAN5G(120, 0),
108 CHAN5G(124, 0), CHAN5G(128, 0),
109 CHAN5G(132, 0), CHAN5G(136, 0),
110 CHAN5G(140, 0), CHAN5G(149, 0),
111 CHAN5G(153, 0), CHAN5G(157, 0),
112 CHAN5G(161, 0), CHAN5G(165, 0),
113 CHAN5G(184, 0), CHAN5G(188, 0),
114 CHAN5G(192, 0), CHAN5G(196, 0),
115 CHAN5G(200, 0), CHAN5G(204, 0),
116 CHAN5G(208, 0), CHAN5G(212, 0),
120 static struct ieee80211_supported_band ath6kl_band_2ghz
= {
121 .n_channels
= ARRAY_SIZE(ath6kl_2ghz_channels
),
122 .channels
= ath6kl_2ghz_channels
,
123 .n_bitrates
= ath6kl_g_rates_size
,
124 .bitrates
= ath6kl_g_rates
,
125 .ht_cap
.cap
= ath6kl_g_htcap
,
126 .ht_cap
.ht_supported
= true,
129 static struct ieee80211_supported_band ath6kl_band_5ghz
= {
130 .n_channels
= ARRAY_SIZE(ath6kl_5ghz_a_channels
),
131 .channels
= ath6kl_5ghz_a_channels
,
132 .n_bitrates
= ath6kl_a_rates_size
,
133 .bitrates
= ath6kl_a_rates
,
134 .ht_cap
.cap
= ath6kl_a_htcap
,
135 .ht_cap
.ht_supported
= true,
138 #define CCKM_KRK_CIPHER_SUITE 0x004096ff /* use for KRK */
140 /* returns true if scheduled scan was stopped */
141 static bool __ath6kl_cfg80211_sscan_stop(struct ath6kl_vif
*vif
)
143 struct ath6kl
*ar
= vif
->ar
;
145 if (ar
->state
!= ATH6KL_STATE_SCHED_SCAN
)
148 del_timer_sync(&vif
->sched_scan_timer
);
150 ath6kl_wmi_set_host_sleep_mode_cmd(ar
->wmi
, vif
->fw_vif_idx
,
151 ATH6KL_HOST_MODE_AWAKE
);
153 ar
->state
= ATH6KL_STATE_ON
;
158 static void ath6kl_cfg80211_sscan_disable(struct ath6kl_vif
*vif
)
160 struct ath6kl
*ar
= vif
->ar
;
163 stopped
= __ath6kl_cfg80211_sscan_stop(vif
);
168 cfg80211_sched_scan_stopped(ar
->wiphy
);
171 static int ath6kl_set_wpa_version(struct ath6kl_vif
*vif
,
172 enum nl80211_wpa_versions wpa_version
)
174 ath6kl_dbg(ATH6KL_DBG_WLAN_CFG
, "%s: %u\n", __func__
, wpa_version
);
177 vif
->auth_mode
= NONE_AUTH
;
178 } else if (wpa_version
& NL80211_WPA_VERSION_2
) {
179 vif
->auth_mode
= WPA2_AUTH
;
180 } else if (wpa_version
& NL80211_WPA_VERSION_1
) {
181 vif
->auth_mode
= WPA_AUTH
;
183 ath6kl_err("%s: %u not supported\n", __func__
, wpa_version
);
190 static int ath6kl_set_auth_type(struct ath6kl_vif
*vif
,
191 enum nl80211_auth_type auth_type
)
193 ath6kl_dbg(ATH6KL_DBG_WLAN_CFG
, "%s: 0x%x\n", __func__
, auth_type
);
196 case NL80211_AUTHTYPE_OPEN_SYSTEM
:
197 vif
->dot11_auth_mode
= OPEN_AUTH
;
199 case NL80211_AUTHTYPE_SHARED_KEY
:
200 vif
->dot11_auth_mode
= SHARED_AUTH
;
202 case NL80211_AUTHTYPE_NETWORK_EAP
:
203 vif
->dot11_auth_mode
= LEAP_AUTH
;
206 case NL80211_AUTHTYPE_AUTOMATIC
:
207 vif
->dot11_auth_mode
= OPEN_AUTH
| SHARED_AUTH
;
211 ath6kl_err("%s: 0x%x not supported\n", __func__
, auth_type
);
218 static int ath6kl_set_cipher(struct ath6kl_vif
*vif
, u32 cipher
, bool ucast
)
220 u8
*ar_cipher
= ucast
? &vif
->prwise_crypto
: &vif
->grp_crypto
;
221 u8
*ar_cipher_len
= ucast
? &vif
->prwise_crypto_len
:
222 &vif
->grp_crypto_len
;
224 ath6kl_dbg(ATH6KL_DBG_WLAN_CFG
, "%s: cipher 0x%x, ucast %u\n",
225 __func__
, cipher
, ucast
);
229 /* our own hack to use value 0 as no crypto used */
230 *ar_cipher
= NONE_CRYPT
;
233 case WLAN_CIPHER_SUITE_WEP40
:
234 *ar_cipher
= WEP_CRYPT
;
237 case WLAN_CIPHER_SUITE_WEP104
:
238 *ar_cipher
= WEP_CRYPT
;
241 case WLAN_CIPHER_SUITE_TKIP
:
242 *ar_cipher
= TKIP_CRYPT
;
245 case WLAN_CIPHER_SUITE_CCMP
:
246 *ar_cipher
= AES_CRYPT
;
249 case WLAN_CIPHER_SUITE_SMS4
:
250 *ar_cipher
= WAPI_CRYPT
;
254 ath6kl_err("cipher 0x%x not supported\n", cipher
);
261 static void ath6kl_set_key_mgmt(struct ath6kl_vif
*vif
, u32 key_mgmt
)
263 ath6kl_dbg(ATH6KL_DBG_WLAN_CFG
, "%s: 0x%x\n", __func__
, key_mgmt
);
265 if (key_mgmt
== WLAN_AKM_SUITE_PSK
) {
266 if (vif
->auth_mode
== WPA_AUTH
)
267 vif
->auth_mode
= WPA_PSK_AUTH
;
268 else if (vif
->auth_mode
== WPA2_AUTH
)
269 vif
->auth_mode
= WPA2_PSK_AUTH
;
270 } else if (key_mgmt
== 0x00409600) {
271 if (vif
->auth_mode
== WPA_AUTH
)
272 vif
->auth_mode
= WPA_AUTH_CCKM
;
273 else if (vif
->auth_mode
== WPA2_AUTH
)
274 vif
->auth_mode
= WPA2_AUTH_CCKM
;
275 } else if (key_mgmt
!= WLAN_AKM_SUITE_8021X
) {
276 vif
->auth_mode
= NONE_AUTH
;
280 static bool ath6kl_cfg80211_ready(struct ath6kl_vif
*vif
)
282 struct ath6kl
*ar
= vif
->ar
;
284 if (!test_bit(WMI_READY
, &ar
->flag
)) {
285 ath6kl_err("wmi is not ready\n");
289 if (!test_bit(WLAN_ENABLED
, &vif
->flags
)) {
290 ath6kl_err("wlan disabled\n");
297 static bool ath6kl_is_wpa_ie(const u8
*pos
)
299 return pos
[0] == WLAN_EID_WPA
&& pos
[1] >= 4 &&
300 pos
[2] == 0x00 && pos
[3] == 0x50 &&
301 pos
[4] == 0xf2 && pos
[5] == 0x01;
304 static bool ath6kl_is_rsn_ie(const u8
*pos
)
306 return pos
[0] == WLAN_EID_RSN
;
309 static bool ath6kl_is_wps_ie(const u8
*pos
)
311 return (pos
[0] == WLAN_EID_VENDOR_SPECIFIC
&&
313 pos
[2] == 0x00 && pos
[3] == 0x50 && pos
[4] == 0xf2 &&
317 static int ath6kl_set_assoc_req_ies(struct ath6kl_vif
*vif
, const u8
*ies
,
320 struct ath6kl
*ar
= vif
->ar
;
327 * Clear previously set flag
330 ar
->connect_ctrl_flags
&= ~CONNECT_WPS_FLAG
;
333 * Filter out RSN/WPA IE(s)
336 if (ies
&& ies_len
) {
337 buf
= kmalloc(ies_len
, GFP_KERNEL
);
342 while (pos
+ 1 < ies
+ ies_len
) {
343 if (pos
+ 2 + pos
[1] > ies
+ ies_len
)
345 if (!(ath6kl_is_wpa_ie(pos
) || ath6kl_is_rsn_ie(pos
))) {
346 memcpy(buf
+ len
, pos
, 2 + pos
[1]);
350 if (ath6kl_is_wps_ie(pos
))
351 ar
->connect_ctrl_flags
|= CONNECT_WPS_FLAG
;
357 ret
= ath6kl_wmi_set_appie_cmd(ar
->wmi
, vif
->fw_vif_idx
,
358 WMI_FRAME_ASSOC_REQ
, buf
, len
);
363 static int ath6kl_nliftype_to_drv_iftype(enum nl80211_iftype type
, u8
*nw_type
)
366 case NL80211_IFTYPE_STATION
:
367 *nw_type
= INFRA_NETWORK
;
369 case NL80211_IFTYPE_ADHOC
:
370 *nw_type
= ADHOC_NETWORK
;
372 case NL80211_IFTYPE_AP
:
373 *nw_type
= AP_NETWORK
;
375 case NL80211_IFTYPE_P2P_CLIENT
:
376 *nw_type
= INFRA_NETWORK
;
378 case NL80211_IFTYPE_P2P_GO
:
379 *nw_type
= AP_NETWORK
;
382 ath6kl_err("invalid interface type %u\n", type
);
389 static bool ath6kl_is_valid_iftype(struct ath6kl
*ar
, enum nl80211_iftype type
,
390 u8
*if_idx
, u8
*nw_type
)
394 if (ath6kl_nliftype_to_drv_iftype(type
, nw_type
))
397 if (ar
->ibss_if_active
|| ((type
== NL80211_IFTYPE_ADHOC
) &&
401 if (type
== NL80211_IFTYPE_STATION
||
402 type
== NL80211_IFTYPE_AP
|| type
== NL80211_IFTYPE_ADHOC
) {
403 for (i
= 0; i
< ar
->vif_max
; i
++) {
404 if ((ar
->avail_idx_map
>> i
) & BIT(0)) {
411 if (type
== NL80211_IFTYPE_P2P_CLIENT
||
412 type
== NL80211_IFTYPE_P2P_GO
) {
413 for (i
= ar
->max_norm_iface
; i
< ar
->vif_max
; i
++) {
414 if ((ar
->avail_idx_map
>> i
) & BIT(0)) {
424 static bool ath6kl_is_tx_pending(struct ath6kl
*ar
)
426 return ar
->tx_pending
[ath6kl_wmi_get_control_ep(ar
->wmi
)] == 0;
430 static int ath6kl_cfg80211_connect(struct wiphy
*wiphy
, struct net_device
*dev
,
431 struct cfg80211_connect_params
*sme
)
433 struct ath6kl
*ar
= ath6kl_priv(dev
);
434 struct ath6kl_vif
*vif
= netdev_priv(dev
);
436 u8 nw_subtype
= (ar
->p2p
) ? SUBTYPE_P2PDEV
: SUBTYPE_NONE
;
439 ath6kl_cfg80211_sscan_disable(vif
);
441 vif
->sme_state
= SME_CONNECTING
;
443 if (!ath6kl_cfg80211_ready(vif
))
446 if (test_bit(DESTROY_IN_PROGRESS
, &ar
->flag
)) {
447 ath6kl_err("destroy in progress\n");
451 if (test_bit(SKIP_SCAN
, &ar
->flag
) &&
452 ((sme
->channel
&& sme
->channel
->center_freq
== 0) ||
453 (sme
->bssid
&& is_zero_ether_addr(sme
->bssid
)))) {
454 ath6kl_err("SkipScan: channel or bssid invalid\n");
458 if (down_interruptible(&ar
->sem
)) {
459 ath6kl_err("busy, couldn't get access\n");
463 if (test_bit(DESTROY_IN_PROGRESS
, &ar
->flag
)) {
464 ath6kl_err("busy, destroy in progress\n");
469 if (ar
->tx_pending
[ath6kl_wmi_get_control_ep(ar
->wmi
)]) {
471 * sleep until the command queue drains
473 wait_event_interruptible_timeout(ar
->event_wq
,
474 ath6kl_is_tx_pending(ar
),
476 if (signal_pending(current
)) {
477 ath6kl_err("cmd queue drain timeout\n");
483 status
= ath6kl_set_assoc_req_ies(vif
, sme
->ie
, sme
->ie_len
);
489 if (sme
->ie
== NULL
|| sme
->ie_len
== 0)
490 ar
->connect_ctrl_flags
&= ~CONNECT_WPS_FLAG
;
492 if (test_bit(CONNECTED
, &vif
->flags
) &&
493 vif
->ssid_len
== sme
->ssid_len
&&
494 !memcmp(vif
->ssid
, sme
->ssid
, vif
->ssid_len
)) {
495 vif
->reconnect_flag
= true;
496 status
= ath6kl_wmi_reconnect_cmd(ar
->wmi
, vif
->fw_vif_idx
,
502 ath6kl_err("wmi_reconnect_cmd failed\n");
506 } else if (vif
->ssid_len
== sme
->ssid_len
&&
507 !memcmp(vif
->ssid
, sme
->ssid
, vif
->ssid_len
)) {
508 ath6kl_disconnect(vif
);
511 memset(vif
->ssid
, 0, sizeof(vif
->ssid
));
512 vif
->ssid_len
= sme
->ssid_len
;
513 memcpy(vif
->ssid
, sme
->ssid
, sme
->ssid_len
);
516 vif
->ch_hint
= sme
->channel
->center_freq
;
518 memset(vif
->req_bssid
, 0, sizeof(vif
->req_bssid
));
519 if (sme
->bssid
&& !is_broadcast_ether_addr(sme
->bssid
))
520 memcpy(vif
->req_bssid
, sme
->bssid
, sizeof(vif
->req_bssid
));
522 ath6kl_set_wpa_version(vif
, sme
->crypto
.wpa_versions
);
524 status
= ath6kl_set_auth_type(vif
, sme
->auth_type
);
530 if (sme
->crypto
.n_ciphers_pairwise
)
531 ath6kl_set_cipher(vif
, sme
->crypto
.ciphers_pairwise
[0], true);
533 ath6kl_set_cipher(vif
, 0, true);
535 ath6kl_set_cipher(vif
, sme
->crypto
.cipher_group
, false);
537 if (sme
->crypto
.n_akm_suites
)
538 ath6kl_set_key_mgmt(vif
, sme
->crypto
.akm_suites
[0]);
540 if ((sme
->key_len
) &&
541 (vif
->auth_mode
== NONE_AUTH
) &&
542 (vif
->prwise_crypto
== WEP_CRYPT
)) {
543 struct ath6kl_key
*key
= NULL
;
545 if (sme
->key_idx
> WMI_MAX_KEY_INDEX
) {
546 ath6kl_err("key index %d out of bounds\n",
552 key
= &vif
->keys
[sme
->key_idx
];
553 key
->key_len
= sme
->key_len
;
554 memcpy(key
->key
, sme
->key
, key
->key_len
);
555 key
->cipher
= vif
->prwise_crypto
;
556 vif
->def_txkey_index
= sme
->key_idx
;
558 ath6kl_wmi_addkey_cmd(ar
->wmi
, vif
->fw_vif_idx
, sme
->key_idx
,
560 GROUP_USAGE
| TX_USAGE
,
563 key
->key
, KEY_OP_INIT_VAL
, NULL
,
567 if (!ar
->usr_bss_filter
) {
568 clear_bit(CLEAR_BSSFILTER_ON_BEACON
, &vif
->flags
);
569 if (ath6kl_wmi_bssfilter_cmd(ar
->wmi
, vif
->fw_vif_idx
,
570 ALL_BSS_FILTER
, 0) != 0) {
571 ath6kl_err("couldn't set bss filtering\n");
577 vif
->nw_type
= vif
->next_mode
;
579 if (vif
->wdev
.iftype
== NL80211_IFTYPE_P2P_CLIENT
)
580 nw_subtype
= SUBTYPE_P2PCLIENT
;
582 ath6kl_dbg(ATH6KL_DBG_WLAN_CFG
,
583 "%s: connect called with authmode %d dot11 auth %d"
584 " PW crypto %d PW crypto len %d GRP crypto %d"
585 " GRP crypto len %d channel hint %u\n",
587 vif
->auth_mode
, vif
->dot11_auth_mode
, vif
->prwise_crypto
,
588 vif
->prwise_crypto_len
, vif
->grp_crypto
,
589 vif
->grp_crypto_len
, vif
->ch_hint
);
591 vif
->reconnect_flag
= 0;
593 if (vif
->nw_type
== INFRA_NETWORK
) {
594 interval
= max_t(u16
, vif
->listen_intvl_t
,
595 ATH6KL_MAX_WOW_LISTEN_INTL
);
596 status
= ath6kl_wmi_listeninterval_cmd(ar
->wmi
, vif
->fw_vif_idx
,
600 ath6kl_err("couldn't set listen intervel\n");
606 status
= ath6kl_wmi_connect_cmd(ar
->wmi
, vif
->fw_vif_idx
, vif
->nw_type
,
607 vif
->dot11_auth_mode
, vif
->auth_mode
,
609 vif
->prwise_crypto_len
,
610 vif
->grp_crypto
, vif
->grp_crypto_len
,
611 vif
->ssid_len
, vif
->ssid
,
612 vif
->req_bssid
, vif
->ch_hint
,
613 ar
->connect_ctrl_flags
, nw_subtype
);
615 /* disable background scan if period is 0 */
616 if (sme
->bg_scan_period
== 0)
617 sme
->bg_scan_period
= 0xffff;
619 /* configure default value if not specified */
620 if (sme
->bg_scan_period
== -1)
621 sme
->bg_scan_period
= DEFAULT_BG_SCAN_PERIOD
;
623 ath6kl_wmi_scanparams_cmd(ar
->wmi
, vif
->fw_vif_idx
, 0, 0,
624 sme
->bg_scan_period
, 0, 0, 0, 3, 0, 0, 0);
628 if (status
== -EINVAL
) {
629 memset(vif
->ssid
, 0, sizeof(vif
->ssid
));
631 ath6kl_err("invalid request\n");
634 ath6kl_err("ath6kl_wmi_connect_cmd failed\n");
638 if ((!(ar
->connect_ctrl_flags
& CONNECT_DO_WPA_OFFLOAD
)) &&
639 ((vif
->auth_mode
== WPA_PSK_AUTH
) ||
640 (vif
->auth_mode
== WPA2_PSK_AUTH
))) {
641 mod_timer(&vif
->disconnect_timer
,
642 jiffies
+ msecs_to_jiffies(DISCON_TIMER_INTVAL
));
645 ar
->connect_ctrl_flags
&= ~CONNECT_DO_WPA_OFFLOAD
;
646 set_bit(CONNECT_PEND
, &vif
->flags
);
651 static struct cfg80211_bss
*
652 ath6kl_add_bss_if_needed(struct ath6kl_vif
*vif
,
653 enum network_type nw_type
,
655 struct ieee80211_channel
*chan
,
657 size_t beacon_ie_len
)
659 struct ath6kl
*ar
= vif
->ar
;
660 struct cfg80211_bss
*bss
;
661 u16 cap_mask
, cap_val
;
664 if (nw_type
& ADHOC_NETWORK
) {
665 cap_mask
= WLAN_CAPABILITY_IBSS
;
666 cap_val
= WLAN_CAPABILITY_IBSS
;
668 cap_mask
= WLAN_CAPABILITY_ESS
;
669 cap_val
= WLAN_CAPABILITY_ESS
;
672 bss
= cfg80211_get_bss(ar
->wiphy
, chan
, bssid
,
673 vif
->ssid
, vif
->ssid_len
,
677 * Since cfg80211 may not yet know about the BSS,
678 * generate a partial entry until the first BSS info
679 * event becomes available.
681 * Prepend SSID element since it is not included in the Beacon
682 * IEs from the target.
684 ie
= kmalloc(2 + vif
->ssid_len
+ beacon_ie_len
, GFP_KERNEL
);
687 ie
[0] = WLAN_EID_SSID
;
688 ie
[1] = vif
->ssid_len
;
689 memcpy(ie
+ 2, vif
->ssid
, vif
->ssid_len
);
690 memcpy(ie
+ 2 + vif
->ssid_len
, beacon_ie
, beacon_ie_len
);
691 bss
= cfg80211_inform_bss(ar
->wiphy
, chan
,
692 bssid
, 0, cap_val
, 100,
693 ie
, 2 + vif
->ssid_len
+ beacon_ie_len
,
696 ath6kl_dbg(ATH6KL_DBG_WLAN_CFG
, "added bss %pM to "
697 "cfg80211\n", bssid
);
700 ath6kl_dbg(ATH6KL_DBG_WLAN_CFG
, "cfg80211 already has a bss\n");
705 void ath6kl_cfg80211_connect_event(struct ath6kl_vif
*vif
, u16 channel
,
706 u8
*bssid
, u16 listen_intvl
,
708 enum network_type nw_type
,
709 u8 beacon_ie_len
, u8 assoc_req_len
,
710 u8 assoc_resp_len
, u8
*assoc_info
)
712 struct ieee80211_channel
*chan
;
713 struct ath6kl
*ar
= vif
->ar
;
714 struct cfg80211_bss
*bss
;
716 /* capinfo + listen interval */
717 u8 assoc_req_ie_offset
= sizeof(u16
) + sizeof(u16
);
719 /* capinfo + status code + associd */
720 u8 assoc_resp_ie_offset
= sizeof(u16
) + sizeof(u16
) + sizeof(u16
);
722 u8
*assoc_req_ie
= assoc_info
+ beacon_ie_len
+ assoc_req_ie_offset
;
723 u8
*assoc_resp_ie
= assoc_info
+ beacon_ie_len
+ assoc_req_len
+
724 assoc_resp_ie_offset
;
726 assoc_req_len
-= assoc_req_ie_offset
;
727 assoc_resp_len
-= assoc_resp_ie_offset
;
730 * Store Beacon interval here; DTIM period will be available only once
731 * a Beacon frame from the AP is seen.
733 vif
->assoc_bss_beacon_int
= beacon_intvl
;
734 clear_bit(DTIM_PERIOD_AVAIL
, &vif
->flags
);
736 if (nw_type
& ADHOC_NETWORK
) {
737 if (vif
->wdev
.iftype
!= NL80211_IFTYPE_ADHOC
) {
738 ath6kl_dbg(ATH6KL_DBG_WLAN_CFG
,
739 "%s: ath6k not in ibss mode\n", __func__
);
744 if (nw_type
& INFRA_NETWORK
) {
745 if (vif
->wdev
.iftype
!= NL80211_IFTYPE_STATION
&&
746 vif
->wdev
.iftype
!= NL80211_IFTYPE_P2P_CLIENT
) {
747 ath6kl_dbg(ATH6KL_DBG_WLAN_CFG
,
748 "%s: ath6k not in station mode\n", __func__
);
753 chan
= ieee80211_get_channel(ar
->wiphy
, (int) channel
);
755 bss
= ath6kl_add_bss_if_needed(vif
, nw_type
, bssid
, chan
,
756 assoc_info
, beacon_ie_len
);
758 ath6kl_err("could not add cfg80211 bss entry\n");
762 if (nw_type
& ADHOC_NETWORK
) {
763 ath6kl_dbg(ATH6KL_DBG_WLAN_CFG
, "ad-hoc %s selected\n",
764 nw_type
& ADHOC_CREATOR
? "creator" : "joiner");
765 cfg80211_ibss_joined(vif
->ndev
, bssid
, GFP_KERNEL
);
766 cfg80211_put_bss(bss
);
770 if (vif
->sme_state
== SME_CONNECTING
) {
771 /* inform connect result to cfg80211 */
772 vif
->sme_state
= SME_CONNECTED
;
773 cfg80211_connect_result(vif
->ndev
, bssid
,
774 assoc_req_ie
, assoc_req_len
,
775 assoc_resp_ie
, assoc_resp_len
,
776 WLAN_STATUS_SUCCESS
, GFP_KERNEL
);
777 cfg80211_put_bss(bss
);
778 } else if (vif
->sme_state
== SME_CONNECTED
) {
779 /* inform roam event to cfg80211 */
780 cfg80211_roamed_bss(vif
->ndev
, bss
, assoc_req_ie
, assoc_req_len
,
781 assoc_resp_ie
, assoc_resp_len
, GFP_KERNEL
);
785 static int ath6kl_cfg80211_disconnect(struct wiphy
*wiphy
,
786 struct net_device
*dev
, u16 reason_code
)
788 struct ath6kl
*ar
= ath6kl_priv(dev
);
789 struct ath6kl_vif
*vif
= netdev_priv(dev
);
791 ath6kl_dbg(ATH6KL_DBG_WLAN_CFG
, "%s: reason=%u\n", __func__
,
794 ath6kl_cfg80211_sscan_disable(vif
);
796 if (!ath6kl_cfg80211_ready(vif
))
799 if (test_bit(DESTROY_IN_PROGRESS
, &ar
->flag
)) {
800 ath6kl_err("busy, destroy in progress\n");
804 if (down_interruptible(&ar
->sem
)) {
805 ath6kl_err("busy, couldn't get access\n");
809 vif
->reconnect_flag
= 0;
810 ath6kl_disconnect(vif
);
811 memset(vif
->ssid
, 0, sizeof(vif
->ssid
));
814 if (!test_bit(SKIP_SCAN
, &ar
->flag
))
815 memset(vif
->req_bssid
, 0, sizeof(vif
->req_bssid
));
819 vif
->sme_state
= SME_DISCONNECTED
;
824 void ath6kl_cfg80211_disconnect_event(struct ath6kl_vif
*vif
, u8 reason
,
825 u8
*bssid
, u8 assoc_resp_len
,
826 u8
*assoc_info
, u16 proto_reason
)
828 struct ath6kl
*ar
= vif
->ar
;
831 cfg80211_scan_done(vif
->scan_req
, true);
832 vif
->scan_req
= NULL
;
835 if (vif
->nw_type
& ADHOC_NETWORK
) {
836 if (vif
->wdev
.iftype
!= NL80211_IFTYPE_ADHOC
) {
837 ath6kl_dbg(ATH6KL_DBG_WLAN_CFG
,
838 "%s: ath6k not in ibss mode\n", __func__
);
841 memset(bssid
, 0, ETH_ALEN
);
842 cfg80211_ibss_joined(vif
->ndev
, bssid
, GFP_KERNEL
);
846 if (vif
->nw_type
& INFRA_NETWORK
) {
847 if (vif
->wdev
.iftype
!= NL80211_IFTYPE_STATION
&&
848 vif
->wdev
.iftype
!= NL80211_IFTYPE_P2P_CLIENT
) {
849 ath6kl_dbg(ATH6KL_DBG_WLAN_CFG
,
850 "%s: ath6k not in station mode\n", __func__
);
856 * Send a disconnect command to target when a disconnect event is
857 * received with reason code other than 3 (DISCONNECT_CMD - disconnect
858 * request from host) to make the firmware stop trying to connect even
859 * after giving disconnect event. There will be one more disconnect
860 * event for this disconnect command with reason code DISCONNECT_CMD
861 * which will be notified to cfg80211.
864 if (reason
!= DISCONNECT_CMD
) {
865 ath6kl_wmi_disconnect_cmd(ar
->wmi
, vif
->fw_vif_idx
);
869 clear_bit(CONNECT_PEND
, &vif
->flags
);
871 if (vif
->sme_state
== SME_CONNECTING
) {
872 cfg80211_connect_result(vif
->ndev
,
875 WLAN_STATUS_UNSPECIFIED_FAILURE
,
877 } else if (vif
->sme_state
== SME_CONNECTED
) {
878 cfg80211_disconnected(vif
->ndev
, reason
,
879 NULL
, 0, GFP_KERNEL
);
882 vif
->sme_state
= SME_DISCONNECTED
;
885 static int ath6kl_cfg80211_scan(struct wiphy
*wiphy
, struct net_device
*ndev
,
886 struct cfg80211_scan_request
*request
)
888 struct ath6kl
*ar
= ath6kl_priv(ndev
);
889 struct ath6kl_vif
*vif
= netdev_priv(ndev
);
891 u16
*channels
= NULL
;
893 u32 force_fg_scan
= 0;
895 if (!ath6kl_cfg80211_ready(vif
))
898 ath6kl_cfg80211_sscan_disable(vif
);
900 if (!ar
->usr_bss_filter
) {
901 clear_bit(CLEAR_BSSFILTER_ON_BEACON
, &vif
->flags
);
902 ret
= ath6kl_wmi_bssfilter_cmd(
903 ar
->wmi
, vif
->fw_vif_idx
,
904 (test_bit(CONNECTED
, &vif
->flags
) ?
905 ALL_BUT_BSS_FILTER
: ALL_BSS_FILTER
), 0);
907 ath6kl_err("couldn't set bss filtering\n");
912 if (request
->n_ssids
&& request
->ssids
[0].ssid_len
) {
915 if (request
->n_ssids
> (MAX_PROBED_SSID_INDEX
- 1))
916 request
->n_ssids
= MAX_PROBED_SSID_INDEX
- 1;
918 for (i
= 0; i
< request
->n_ssids
; i
++)
919 ath6kl_wmi_probedssid_cmd(ar
->wmi
, vif
->fw_vif_idx
,
920 i
+ 1, SPECIFIC_SSID_FLAG
,
921 request
->ssids
[i
].ssid_len
,
922 request
->ssids
[i
].ssid
);
925 /* this also clears IE in fw if it's not set */
926 ret
= ath6kl_wmi_set_appie_cmd(ar
->wmi
, vif
->fw_vif_idx
,
928 request
->ie
, request
->ie_len
);
930 ath6kl_err("failed to set Probe Request appie for "
936 * Scan only the requested channels if the request specifies a set of
937 * channels. If the list is longer than the target supports, do not
938 * configure the list and instead, scan all available channels.
940 if (request
->n_channels
> 0 &&
941 request
->n_channels
<= WMI_MAX_CHANNELS
) {
944 n_channels
= request
->n_channels
;
946 channels
= kzalloc(n_channels
* sizeof(u16
), GFP_KERNEL
);
947 if (channels
== NULL
) {
948 ath6kl_warn("failed to set scan channels, "
949 "scan all channels");
953 for (i
= 0; i
< n_channels
; i
++)
954 channels
[i
] = request
->channels
[i
]->center_freq
;
957 if (test_bit(CONNECTED
, &vif
->flags
))
960 vif
->scan_req
= request
;
962 if (test_bit(ATH6KL_FW_CAPABILITY_STA_P2PDEV_DUPLEX
,
963 ar
->fw_capabilities
)) {
965 * If capable of doing P2P mgmt operations using
966 * station interface, send additional information like
967 * supported rates to advertise and xmit rates for
970 ret
= ath6kl_wmi_beginscan_cmd(ar
->wmi
, vif
->fw_vif_idx
,
971 WMI_LONG_SCAN
, force_fg_scan
,
973 ATH6KL_FG_SCAN_INTERVAL
,
974 n_channels
, channels
,
978 ret
= ath6kl_wmi_startscan_cmd(ar
->wmi
, vif
->fw_vif_idx
,
979 WMI_LONG_SCAN
, force_fg_scan
,
981 ATH6KL_FG_SCAN_INTERVAL
,
982 n_channels
, channels
);
985 ath6kl_err("wmi_startscan_cmd failed\n");
986 vif
->scan_req
= NULL
;
994 void ath6kl_cfg80211_scan_complete_event(struct ath6kl_vif
*vif
, bool aborted
)
996 struct ath6kl
*ar
= vif
->ar
;
999 ath6kl_dbg(ATH6KL_DBG_WLAN_CFG
, "%s: status%s\n", __func__
,
1000 aborted
? " aborted" : "");
1008 if (vif
->scan_req
->n_ssids
&& vif
->scan_req
->ssids
[0].ssid_len
) {
1009 for (i
= 0; i
< vif
->scan_req
->n_ssids
; i
++) {
1010 ath6kl_wmi_probedssid_cmd(ar
->wmi
, vif
->fw_vif_idx
,
1011 i
+ 1, DISABLE_SSID_FLAG
,
1017 cfg80211_scan_done(vif
->scan_req
, aborted
);
1018 vif
->scan_req
= NULL
;
1021 void ath6kl_cfg80211_ch_switch_notify(struct ath6kl_vif
*vif
, int freq
,
1022 enum wmi_phy_mode mode
)
1024 enum nl80211_channel_type type
;
1026 ath6kl_dbg(ATH6KL_DBG_WLAN_CFG
,
1027 "channel switch notify nw_type %d freq %d mode %d\n",
1028 vif
->nw_type
, freq
, mode
);
1030 type
= (mode
== WMI_11G_HT20
) ? NL80211_CHAN_HT20
: NL80211_CHAN_NO_HT
;
1032 cfg80211_ch_switch_notify(vif
->ndev
, freq
, type
);
1035 static int ath6kl_cfg80211_add_key(struct wiphy
*wiphy
, struct net_device
*ndev
,
1036 u8 key_index
, bool pairwise
,
1038 struct key_params
*params
)
1040 struct ath6kl
*ar
= ath6kl_priv(ndev
);
1041 struct ath6kl_vif
*vif
= netdev_priv(ndev
);
1042 struct ath6kl_key
*key
= NULL
;
1047 if (!ath6kl_cfg80211_ready(vif
))
1050 if (params
->cipher
== CCKM_KRK_CIPHER_SUITE
) {
1051 if (params
->key_len
!= WMI_KRK_LEN
)
1053 return ath6kl_wmi_add_krk_cmd(ar
->wmi
, vif
->fw_vif_idx
,
1057 if (key_index
> WMI_MAX_KEY_INDEX
) {
1058 ath6kl_dbg(ATH6KL_DBG_WLAN_CFG
,
1059 "%s: key index %d out of bounds\n", __func__
,
1064 key
= &vif
->keys
[key_index
];
1065 memset(key
, 0, sizeof(struct ath6kl_key
));
1068 key_usage
= PAIRWISE_USAGE
;
1070 key_usage
= GROUP_USAGE
;
1072 seq_len
= params
->seq_len
;
1073 if (params
->cipher
== WLAN_CIPHER_SUITE_SMS4
&&
1074 seq_len
> ATH6KL_KEY_SEQ_LEN
) {
1075 /* Only first half of the WPI PN is configured */
1076 seq_len
= ATH6KL_KEY_SEQ_LEN
;
1078 if (params
->key_len
> WLAN_MAX_KEY_LEN
||
1079 seq_len
> sizeof(key
->seq
))
1082 key
->key_len
= params
->key_len
;
1083 memcpy(key
->key
, params
->key
, key
->key_len
);
1084 key
->seq_len
= seq_len
;
1085 memcpy(key
->seq
, params
->seq
, key
->seq_len
);
1086 key
->cipher
= params
->cipher
;
1088 switch (key
->cipher
) {
1089 case WLAN_CIPHER_SUITE_WEP40
:
1090 case WLAN_CIPHER_SUITE_WEP104
:
1091 key_type
= WEP_CRYPT
;
1094 case WLAN_CIPHER_SUITE_TKIP
:
1095 key_type
= TKIP_CRYPT
;
1098 case WLAN_CIPHER_SUITE_CCMP
:
1099 key_type
= AES_CRYPT
;
1101 case WLAN_CIPHER_SUITE_SMS4
:
1102 key_type
= WAPI_CRYPT
;
1109 if (((vif
->auth_mode
== WPA_PSK_AUTH
) ||
1110 (vif
->auth_mode
== WPA2_PSK_AUTH
)) &&
1111 (key_usage
& GROUP_USAGE
))
1112 del_timer(&vif
->disconnect_timer
);
1114 ath6kl_dbg(ATH6KL_DBG_WLAN_CFG
,
1115 "%s: index %d, key_len %d, key_type 0x%x, key_usage 0x%x, seq_len %d\n",
1116 __func__
, key_index
, key
->key_len
, key_type
,
1117 key_usage
, key
->seq_len
);
1119 if (vif
->nw_type
== AP_NETWORK
&& !pairwise
&&
1120 (key_type
== TKIP_CRYPT
|| key_type
== AES_CRYPT
||
1121 key_type
== WAPI_CRYPT
)) {
1122 ar
->ap_mode_bkey
.valid
= true;
1123 ar
->ap_mode_bkey
.key_index
= key_index
;
1124 ar
->ap_mode_bkey
.key_type
= key_type
;
1125 ar
->ap_mode_bkey
.key_len
= key
->key_len
;
1126 memcpy(ar
->ap_mode_bkey
.key
, key
->key
, key
->key_len
);
1127 if (!test_bit(CONNECTED
, &vif
->flags
)) {
1128 ath6kl_dbg(ATH6KL_DBG_WLAN_CFG
, "Delay initial group "
1129 "key configuration until AP mode has been "
1132 * The key will be set in ath6kl_connect_ap_mode() once
1133 * the connected event is received from the target.
1139 if (vif
->next_mode
== AP_NETWORK
&& key_type
== WEP_CRYPT
&&
1140 !test_bit(CONNECTED
, &vif
->flags
)) {
1142 * Store the key locally so that it can be re-configured after
1143 * the AP mode has properly started
1144 * (ath6kl_install_statioc_wep_keys).
1146 ath6kl_dbg(ATH6KL_DBG_WLAN_CFG
, "Delay WEP key configuration "
1147 "until AP mode has been started\n");
1148 vif
->wep_key_list
[key_index
].key_len
= key
->key_len
;
1149 memcpy(vif
->wep_key_list
[key_index
].key
, key
->key
,
1154 return ath6kl_wmi_addkey_cmd(ar
->wmi
, vif
->fw_vif_idx
, key_index
,
1155 key_type
, key_usage
, key
->key_len
,
1156 key
->seq
, key
->seq_len
, key
->key
,
1158 (u8
*) mac_addr
, SYNC_BOTH_WMIFLAG
);
1161 static int ath6kl_cfg80211_del_key(struct wiphy
*wiphy
, struct net_device
*ndev
,
1162 u8 key_index
, bool pairwise
,
1165 struct ath6kl
*ar
= ath6kl_priv(ndev
);
1166 struct ath6kl_vif
*vif
= netdev_priv(ndev
);
1168 ath6kl_dbg(ATH6KL_DBG_WLAN_CFG
, "%s: index %d\n", __func__
, key_index
);
1170 if (!ath6kl_cfg80211_ready(vif
))
1173 if (key_index
> WMI_MAX_KEY_INDEX
) {
1174 ath6kl_dbg(ATH6KL_DBG_WLAN_CFG
,
1175 "%s: key index %d out of bounds\n", __func__
,
1180 if (!vif
->keys
[key_index
].key_len
) {
1181 ath6kl_dbg(ATH6KL_DBG_WLAN_CFG
,
1182 "%s: index %d is empty\n", __func__
, key_index
);
1186 vif
->keys
[key_index
].key_len
= 0;
1188 return ath6kl_wmi_deletekey_cmd(ar
->wmi
, vif
->fw_vif_idx
, key_index
);
1191 static int ath6kl_cfg80211_get_key(struct wiphy
*wiphy
, struct net_device
*ndev
,
1192 u8 key_index
, bool pairwise
,
1193 const u8
*mac_addr
, void *cookie
,
1194 void (*callback
) (void *cookie
,
1195 struct key_params
*))
1197 struct ath6kl_vif
*vif
= netdev_priv(ndev
);
1198 struct ath6kl_key
*key
= NULL
;
1199 struct key_params params
;
1201 ath6kl_dbg(ATH6KL_DBG_WLAN_CFG
, "%s: index %d\n", __func__
, key_index
);
1203 if (!ath6kl_cfg80211_ready(vif
))
1206 if (key_index
> WMI_MAX_KEY_INDEX
) {
1207 ath6kl_dbg(ATH6KL_DBG_WLAN_CFG
,
1208 "%s: key index %d out of bounds\n", __func__
,
1213 key
= &vif
->keys
[key_index
];
1214 memset(¶ms
, 0, sizeof(params
));
1215 params
.cipher
= key
->cipher
;
1216 params
.key_len
= key
->key_len
;
1217 params
.seq_len
= key
->seq_len
;
1218 params
.seq
= key
->seq
;
1219 params
.key
= key
->key
;
1221 callback(cookie
, ¶ms
);
1223 return key
->key_len
? 0 : -ENOENT
;
1226 static int ath6kl_cfg80211_set_default_key(struct wiphy
*wiphy
,
1227 struct net_device
*ndev
,
1228 u8 key_index
, bool unicast
,
1231 struct ath6kl
*ar
= ath6kl_priv(ndev
);
1232 struct ath6kl_vif
*vif
= netdev_priv(ndev
);
1233 struct ath6kl_key
*key
= NULL
;
1235 enum crypto_type key_type
= NONE_CRYPT
;
1237 ath6kl_dbg(ATH6KL_DBG_WLAN_CFG
, "%s: index %d\n", __func__
, key_index
);
1239 if (!ath6kl_cfg80211_ready(vif
))
1242 if (key_index
> WMI_MAX_KEY_INDEX
) {
1243 ath6kl_dbg(ATH6KL_DBG_WLAN_CFG
,
1244 "%s: key index %d out of bounds\n",
1245 __func__
, key_index
);
1249 if (!vif
->keys
[key_index
].key_len
) {
1250 ath6kl_dbg(ATH6KL_DBG_WLAN_CFG
, "%s: invalid key index %d\n",
1251 __func__
, key_index
);
1255 vif
->def_txkey_index
= key_index
;
1256 key
= &vif
->keys
[vif
->def_txkey_index
];
1257 key_usage
= GROUP_USAGE
;
1258 if (vif
->prwise_crypto
== WEP_CRYPT
)
1259 key_usage
|= TX_USAGE
;
1261 key_type
= vif
->prwise_crypto
;
1263 key_type
= vif
->grp_crypto
;
1265 if (vif
->next_mode
== AP_NETWORK
&& !test_bit(CONNECTED
, &vif
->flags
))
1266 return 0; /* Delay until AP mode has been started */
1268 return ath6kl_wmi_addkey_cmd(ar
->wmi
, vif
->fw_vif_idx
,
1269 vif
->def_txkey_index
,
1270 key_type
, key_usage
,
1271 key
->key_len
, key
->seq
, key
->seq_len
,
1273 KEY_OP_INIT_VAL
, NULL
,
1277 void ath6kl_cfg80211_tkip_micerr_event(struct ath6kl_vif
*vif
, u8 keyid
,
1280 ath6kl_dbg(ATH6KL_DBG_WLAN_CFG
,
1281 "%s: keyid %d, ismcast %d\n", __func__
, keyid
, ismcast
);
1283 cfg80211_michael_mic_failure(vif
->ndev
, vif
->bssid
,
1284 (ismcast
? NL80211_KEYTYPE_GROUP
:
1285 NL80211_KEYTYPE_PAIRWISE
), keyid
, NULL
,
1289 static int ath6kl_cfg80211_set_wiphy_params(struct wiphy
*wiphy
, u32 changed
)
1291 struct ath6kl
*ar
= (struct ath6kl
*)wiphy_priv(wiphy
);
1292 struct ath6kl_vif
*vif
;
1295 ath6kl_dbg(ATH6KL_DBG_WLAN_CFG
, "%s: changed 0x%x\n", __func__
,
1298 vif
= ath6kl_vif_first(ar
);
1302 if (!ath6kl_cfg80211_ready(vif
))
1305 if (changed
& WIPHY_PARAM_RTS_THRESHOLD
) {
1306 ret
= ath6kl_wmi_set_rts_cmd(ar
->wmi
, wiphy
->rts_threshold
);
1308 ath6kl_err("ath6kl_wmi_set_rts_cmd failed\n");
1317 * The type nl80211_tx_power_setting replaces the following
1318 * data type from 2.6.36 onwards
1320 static int ath6kl_cfg80211_set_txpower(struct wiphy
*wiphy
,
1321 enum nl80211_tx_power_setting type
,
1324 struct ath6kl
*ar
= (struct ath6kl
*)wiphy_priv(wiphy
);
1325 struct ath6kl_vif
*vif
;
1326 int dbm
= MBM_TO_DBM(mbm
);
1328 ath6kl_dbg(ATH6KL_DBG_WLAN_CFG
, "%s: type 0x%x, dbm %d\n", __func__
,
1331 vif
= ath6kl_vif_first(ar
);
1335 if (!ath6kl_cfg80211_ready(vif
))
1339 case NL80211_TX_POWER_AUTOMATIC
:
1341 case NL80211_TX_POWER_LIMITED
:
1345 ath6kl_dbg(ATH6KL_DBG_WLAN_CFG
, "%s: type 0x%x not supported\n",
1350 ath6kl_wmi_set_tx_pwr_cmd(ar
->wmi
, vif
->fw_vif_idx
, dbm
);
1355 static int ath6kl_cfg80211_get_txpower(struct wiphy
*wiphy
, int *dbm
)
1357 struct ath6kl
*ar
= (struct ath6kl
*)wiphy_priv(wiphy
);
1358 struct ath6kl_vif
*vif
;
1360 vif
= ath6kl_vif_first(ar
);
1364 if (!ath6kl_cfg80211_ready(vif
))
1367 if (test_bit(CONNECTED
, &vif
->flags
)) {
1370 if (ath6kl_wmi_get_tx_pwr_cmd(ar
->wmi
, vif
->fw_vif_idx
) != 0) {
1371 ath6kl_err("ath6kl_wmi_get_tx_pwr_cmd failed\n");
1375 wait_event_interruptible_timeout(ar
->event_wq
, ar
->tx_pwr
!= 0,
1378 if (signal_pending(current
)) {
1379 ath6kl_err("target did not respond\n");
1388 static int ath6kl_cfg80211_set_power_mgmt(struct wiphy
*wiphy
,
1389 struct net_device
*dev
,
1390 bool pmgmt
, int timeout
)
1392 struct ath6kl
*ar
= ath6kl_priv(dev
);
1393 struct wmi_power_mode_cmd mode
;
1394 struct ath6kl_vif
*vif
= netdev_priv(dev
);
1396 ath6kl_dbg(ATH6KL_DBG_WLAN_CFG
, "%s: pmgmt %d, timeout %d\n",
1397 __func__
, pmgmt
, timeout
);
1399 if (!ath6kl_cfg80211_ready(vif
))
1403 ath6kl_dbg(ATH6KL_DBG_WLAN_CFG
, "%s: max perf\n", __func__
);
1404 mode
.pwr_mode
= REC_POWER
;
1406 ath6kl_dbg(ATH6KL_DBG_WLAN_CFG
, "%s: rec power\n", __func__
);
1407 mode
.pwr_mode
= MAX_PERF_POWER
;
1410 if (ath6kl_wmi_powermode_cmd(ar
->wmi
, vif
->fw_vif_idx
,
1411 mode
.pwr_mode
) != 0) {
1412 ath6kl_err("wmi_powermode_cmd failed\n");
1419 static struct net_device
*ath6kl_cfg80211_add_iface(struct wiphy
*wiphy
,
1421 enum nl80211_iftype type
,
1423 struct vif_params
*params
)
1425 struct ath6kl
*ar
= wiphy_priv(wiphy
);
1426 struct net_device
*ndev
;
1429 if (ar
->num_vif
== ar
->vif_max
) {
1430 ath6kl_err("Reached maximum number of supported vif\n");
1431 return ERR_PTR(-EINVAL
);
1434 if (!ath6kl_is_valid_iftype(ar
, type
, &if_idx
, &nw_type
)) {
1435 ath6kl_err("Not a supported interface type\n");
1436 return ERR_PTR(-EINVAL
);
1439 ndev
= ath6kl_interface_add(ar
, name
, type
, if_idx
, nw_type
);
1441 return ERR_PTR(-ENOMEM
);
1448 static int ath6kl_cfg80211_del_iface(struct wiphy
*wiphy
,
1449 struct net_device
*ndev
)
1451 struct ath6kl
*ar
= wiphy_priv(wiphy
);
1452 struct ath6kl_vif
*vif
= netdev_priv(ndev
);
1454 spin_lock_bh(&ar
->list_lock
);
1455 list_del(&vif
->list
);
1456 spin_unlock_bh(&ar
->list_lock
);
1458 ath6kl_cleanup_vif(vif
, test_bit(WMI_READY
, &ar
->flag
));
1460 ath6kl_cfg80211_vif_cleanup(vif
);
1465 static int ath6kl_cfg80211_change_iface(struct wiphy
*wiphy
,
1466 struct net_device
*ndev
,
1467 enum nl80211_iftype type
, u32
*flags
,
1468 struct vif_params
*params
)
1470 struct ath6kl_vif
*vif
= netdev_priv(ndev
);
1473 ath6kl_dbg(ATH6KL_DBG_WLAN_CFG
, "%s: type %u\n", __func__
, type
);
1476 * Don't bring up p2p on an interface which is not initialized
1477 * for p2p operation where fw does not have capability to switch
1478 * dynamically between non-p2p and p2p type interface.
1480 if (!test_bit(ATH6KL_FW_CAPABILITY_STA_P2PDEV_DUPLEX
,
1481 vif
->ar
->fw_capabilities
) &&
1482 (type
== NL80211_IFTYPE_P2P_CLIENT
||
1483 type
== NL80211_IFTYPE_P2P_GO
)) {
1484 if (vif
->ar
->vif_max
== 1) {
1485 if (vif
->fw_vif_idx
!= 0)
1488 goto set_iface_type
;
1491 for (i
= vif
->ar
->max_norm_iface
; i
< vif
->ar
->vif_max
; i
++) {
1492 if (i
== vif
->fw_vif_idx
)
1496 if (i
== vif
->ar
->vif_max
) {
1497 ath6kl_err("Invalid interface to bring up P2P\n");
1504 case NL80211_IFTYPE_STATION
:
1505 vif
->next_mode
= INFRA_NETWORK
;
1507 case NL80211_IFTYPE_ADHOC
:
1508 vif
->next_mode
= ADHOC_NETWORK
;
1510 case NL80211_IFTYPE_AP
:
1511 vif
->next_mode
= AP_NETWORK
;
1513 case NL80211_IFTYPE_P2P_CLIENT
:
1514 vif
->next_mode
= INFRA_NETWORK
;
1516 case NL80211_IFTYPE_P2P_GO
:
1517 vif
->next_mode
= AP_NETWORK
;
1520 ath6kl_err("invalid interface type %u\n", type
);
1524 vif
->wdev
.iftype
= type
;
1529 static int ath6kl_cfg80211_join_ibss(struct wiphy
*wiphy
,
1530 struct net_device
*dev
,
1531 struct cfg80211_ibss_params
*ibss_param
)
1533 struct ath6kl
*ar
= ath6kl_priv(dev
);
1534 struct ath6kl_vif
*vif
= netdev_priv(dev
);
1537 if (!ath6kl_cfg80211_ready(vif
))
1540 vif
->ssid_len
= ibss_param
->ssid_len
;
1541 memcpy(vif
->ssid
, ibss_param
->ssid
, vif
->ssid_len
);
1543 if (ibss_param
->channel
)
1544 vif
->ch_hint
= ibss_param
->channel
->center_freq
;
1546 if (ibss_param
->channel_fixed
) {
1548 * TODO: channel_fixed: The channel should be fixed, do not
1549 * search for IBSSs to join on other channels. Target
1550 * firmware does not support this feature, needs to be
1556 memset(vif
->req_bssid
, 0, sizeof(vif
->req_bssid
));
1557 if (ibss_param
->bssid
&& !is_broadcast_ether_addr(ibss_param
->bssid
))
1558 memcpy(vif
->req_bssid
, ibss_param
->bssid
,
1559 sizeof(vif
->req_bssid
));
1561 ath6kl_set_wpa_version(vif
, 0);
1563 status
= ath6kl_set_auth_type(vif
, NL80211_AUTHTYPE_OPEN_SYSTEM
);
1567 if (ibss_param
->privacy
) {
1568 ath6kl_set_cipher(vif
, WLAN_CIPHER_SUITE_WEP40
, true);
1569 ath6kl_set_cipher(vif
, WLAN_CIPHER_SUITE_WEP40
, false);
1571 ath6kl_set_cipher(vif
, 0, true);
1572 ath6kl_set_cipher(vif
, 0, false);
1575 vif
->nw_type
= vif
->next_mode
;
1577 ath6kl_dbg(ATH6KL_DBG_WLAN_CFG
,
1578 "%s: connect called with authmode %d dot11 auth %d"
1579 " PW crypto %d PW crypto len %d GRP crypto %d"
1580 " GRP crypto len %d channel hint %u\n",
1582 vif
->auth_mode
, vif
->dot11_auth_mode
, vif
->prwise_crypto
,
1583 vif
->prwise_crypto_len
, vif
->grp_crypto
,
1584 vif
->grp_crypto_len
, vif
->ch_hint
);
1586 status
= ath6kl_wmi_connect_cmd(ar
->wmi
, vif
->fw_vif_idx
, vif
->nw_type
,
1587 vif
->dot11_auth_mode
, vif
->auth_mode
,
1589 vif
->prwise_crypto_len
,
1590 vif
->grp_crypto
, vif
->grp_crypto_len
,
1591 vif
->ssid_len
, vif
->ssid
,
1592 vif
->req_bssid
, vif
->ch_hint
,
1593 ar
->connect_ctrl_flags
, SUBTYPE_NONE
);
1594 set_bit(CONNECT_PEND
, &vif
->flags
);
1599 static int ath6kl_cfg80211_leave_ibss(struct wiphy
*wiphy
,
1600 struct net_device
*dev
)
1602 struct ath6kl_vif
*vif
= netdev_priv(dev
);
1604 if (!ath6kl_cfg80211_ready(vif
))
1607 ath6kl_disconnect(vif
);
1608 memset(vif
->ssid
, 0, sizeof(vif
->ssid
));
1614 static const u32 cipher_suites
[] = {
1615 WLAN_CIPHER_SUITE_WEP40
,
1616 WLAN_CIPHER_SUITE_WEP104
,
1617 WLAN_CIPHER_SUITE_TKIP
,
1618 WLAN_CIPHER_SUITE_CCMP
,
1619 CCKM_KRK_CIPHER_SUITE
,
1620 WLAN_CIPHER_SUITE_SMS4
,
1623 static bool is_rate_legacy(s32 rate
)
1625 static const s32 legacy
[] = { 1000, 2000, 5500, 11000,
1626 6000, 9000, 12000, 18000, 24000,
1631 for (i
= 0; i
< ARRAY_SIZE(legacy
); i
++)
1632 if (rate
== legacy
[i
])
1638 static bool is_rate_ht20(s32 rate
, u8
*mcs
, bool *sgi
)
1640 static const s32 ht20
[] = { 6500, 13000, 19500, 26000, 39000,
1641 52000, 58500, 65000, 72200
1645 for (i
= 0; i
< ARRAY_SIZE(ht20
); i
++) {
1646 if (rate
== ht20
[i
]) {
1647 if (i
== ARRAY_SIZE(ht20
) - 1)
1648 /* last rate uses sgi */
1660 static bool is_rate_ht40(s32 rate
, u8
*mcs
, bool *sgi
)
1662 static const s32 ht40
[] = { 13500, 27000, 40500, 54000,
1663 81000, 108000, 121500, 135000,
1668 for (i
= 0; i
< ARRAY_SIZE(ht40
); i
++) {
1669 if (rate
== ht40
[i
]) {
1670 if (i
== ARRAY_SIZE(ht40
) - 1)
1671 /* last rate uses sgi */
1684 static int ath6kl_get_station(struct wiphy
*wiphy
, struct net_device
*dev
,
1685 u8
*mac
, struct station_info
*sinfo
)
1687 struct ath6kl
*ar
= ath6kl_priv(dev
);
1688 struct ath6kl_vif
*vif
= netdev_priv(dev
);
1695 if (memcmp(mac
, vif
->bssid
, ETH_ALEN
) != 0)
1698 if (down_interruptible(&ar
->sem
))
1701 set_bit(STATS_UPDATE_PEND
, &vif
->flags
);
1703 ret
= ath6kl_wmi_get_stats_cmd(ar
->wmi
, vif
->fw_vif_idx
);
1710 left
= wait_event_interruptible_timeout(ar
->event_wq
,
1711 !test_bit(STATS_UPDATE_PEND
,
1722 if (vif
->target_stats
.rx_byte
) {
1723 sinfo
->rx_bytes
= vif
->target_stats
.rx_byte
;
1724 sinfo
->filled
|= STATION_INFO_RX_BYTES
;
1725 sinfo
->rx_packets
= vif
->target_stats
.rx_pkt
;
1726 sinfo
->filled
|= STATION_INFO_RX_PACKETS
;
1729 if (vif
->target_stats
.tx_byte
) {
1730 sinfo
->tx_bytes
= vif
->target_stats
.tx_byte
;
1731 sinfo
->filled
|= STATION_INFO_TX_BYTES
;
1732 sinfo
->tx_packets
= vif
->target_stats
.tx_pkt
;
1733 sinfo
->filled
|= STATION_INFO_TX_PACKETS
;
1736 sinfo
->signal
= vif
->target_stats
.cs_rssi
;
1737 sinfo
->filled
|= STATION_INFO_SIGNAL
;
1739 rate
= vif
->target_stats
.tx_ucast_rate
;
1741 if (is_rate_legacy(rate
)) {
1742 sinfo
->txrate
.legacy
= rate
/ 100;
1743 } else if (is_rate_ht20(rate
, &mcs
, &sgi
)) {
1745 sinfo
->txrate
.flags
|= RATE_INFO_FLAGS_SHORT_GI
;
1746 sinfo
->txrate
.mcs
= mcs
- 1;
1748 sinfo
->txrate
.mcs
= mcs
;
1751 sinfo
->txrate
.flags
|= RATE_INFO_FLAGS_MCS
;
1752 } else if (is_rate_ht40(rate
, &mcs
, &sgi
)) {
1754 sinfo
->txrate
.flags
|= RATE_INFO_FLAGS_SHORT_GI
;
1755 sinfo
->txrate
.mcs
= mcs
- 1;
1757 sinfo
->txrate
.mcs
= mcs
;
1760 sinfo
->txrate
.flags
|= RATE_INFO_FLAGS_40_MHZ_WIDTH
;
1761 sinfo
->txrate
.flags
|= RATE_INFO_FLAGS_MCS
;
1763 ath6kl_dbg(ATH6KL_DBG_WLAN_CFG
,
1764 "invalid rate from stats: %d\n", rate
);
1765 ath6kl_debug_war(ar
, ATH6KL_WAR_INVALID_RATE
);
1769 sinfo
->filled
|= STATION_INFO_TX_BITRATE
;
1771 if (test_bit(CONNECTED
, &vif
->flags
) &&
1772 test_bit(DTIM_PERIOD_AVAIL
, &vif
->flags
) &&
1773 vif
->nw_type
== INFRA_NETWORK
) {
1774 sinfo
->filled
|= STATION_INFO_BSS_PARAM
;
1775 sinfo
->bss_param
.flags
= 0;
1776 sinfo
->bss_param
.dtim_period
= vif
->assoc_bss_dtim_period
;
1777 sinfo
->bss_param
.beacon_interval
= vif
->assoc_bss_beacon_int
;
1783 static int ath6kl_set_pmksa(struct wiphy
*wiphy
, struct net_device
*netdev
,
1784 struct cfg80211_pmksa
*pmksa
)
1786 struct ath6kl
*ar
= ath6kl_priv(netdev
);
1787 struct ath6kl_vif
*vif
= netdev_priv(netdev
);
1789 return ath6kl_wmi_setpmkid_cmd(ar
->wmi
, vif
->fw_vif_idx
, pmksa
->bssid
,
1790 pmksa
->pmkid
, true);
1793 static int ath6kl_del_pmksa(struct wiphy
*wiphy
, struct net_device
*netdev
,
1794 struct cfg80211_pmksa
*pmksa
)
1796 struct ath6kl
*ar
= ath6kl_priv(netdev
);
1797 struct ath6kl_vif
*vif
= netdev_priv(netdev
);
1799 return ath6kl_wmi_setpmkid_cmd(ar
->wmi
, vif
->fw_vif_idx
, pmksa
->bssid
,
1800 pmksa
->pmkid
, false);
1803 static int ath6kl_flush_pmksa(struct wiphy
*wiphy
, struct net_device
*netdev
)
1805 struct ath6kl
*ar
= ath6kl_priv(netdev
);
1806 struct ath6kl_vif
*vif
= netdev_priv(netdev
);
1808 if (test_bit(CONNECTED
, &vif
->flags
))
1809 return ath6kl_wmi_setpmkid_cmd(ar
->wmi
, vif
->fw_vif_idx
,
1810 vif
->bssid
, NULL
, false);
1814 static int ath6kl_wow_usr(struct ath6kl
*ar
, struct ath6kl_vif
*vif
,
1815 struct cfg80211_wowlan
*wow
, u32
*filter
)
1818 u8 mask
[WOW_MASK_SIZE
];
1821 /* Configure the patterns that we received from the user. */
1822 for (i
= 0; i
< wow
->n_patterns
; i
++) {
1825 * Convert given nl80211 specific mask value to equivalent
1826 * driver specific mask value and send it to the chip along
1827 * with patterns. For example, If the mask value defined in
1828 * struct cfg80211_wowlan is 0xA (equivalent binary is 1010),
1829 * then equivalent driver specific mask value is
1830 * "0xFF 0x00 0xFF 0x00".
1832 memset(&mask
, 0, sizeof(mask
));
1833 for (pos
= 0; pos
< wow
->patterns
[i
].pattern_len
; pos
++) {
1834 if (wow
->patterns
[i
].mask
[pos
/ 8] & (0x1 << (pos
% 8)))
1838 * Note: Pattern's offset is not passed as part of wowlan
1839 * parameter from CFG layer. So it's always passed as ZERO
1840 * to the firmware. It means, given WOW patterns are always
1841 * matched from the first byte of received pkt in the firmware.
1843 ret
= ath6kl_wmi_add_wow_pattern_cmd(ar
->wmi
,
1844 vif
->fw_vif_idx
, WOW_LIST_ID
,
1845 wow
->patterns
[i
].pattern_len
,
1846 0 /* pattern offset */,
1847 wow
->patterns
[i
].pattern
, mask
);
1852 if (wow
->disconnect
)
1853 *filter
|= WOW_FILTER_OPTION_NWK_DISASSOC
;
1856 *filter
|= WOW_FILTER_OPTION_MAGIC_PACKET
;
1858 if (wow
->gtk_rekey_failure
)
1859 *filter
|= WOW_FILTER_OPTION_GTK_ERROR
;
1861 if (wow
->eap_identity_req
)
1862 *filter
|= WOW_FILTER_OPTION_EAP_REQ
;
1864 if (wow
->four_way_handshake
)
1865 *filter
|= WOW_FILTER_OPTION_8021X_4WAYHS
;
1870 static int ath6kl_wow_ap(struct ath6kl
*ar
, struct ath6kl_vif
*vif
)
1872 static const u8 unicst_pattern
[] = { 0x00, 0x00, 0x00,
1873 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
1874 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
1876 static const u8 unicst_mask
[] = { 0x01, 0x00, 0x00,
1877 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
1878 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
1880 u8 unicst_offset
= 0;
1881 static const u8 arp_pattern
[] = { 0x08, 0x06 };
1882 static const u8 arp_mask
[] = { 0xff, 0xff };
1884 static const u8 discvr_pattern
[] = { 0xe0, 0x00, 0x00, 0xf8 };
1885 static const u8 discvr_mask
[] = { 0xf0, 0x00, 0x00, 0xf8 };
1886 u8 discvr_offset
= 38;
1887 static const u8 dhcp_pattern
[] = { 0xff, 0xff, 0xff, 0xff,
1888 0xff, 0xff, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
1889 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x08, 0x00,
1890 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
1891 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
1892 0x00, 0x00, 0x00, 0x00, 0x00, 0x43 /* port 67 */ };
1893 static const u8 dhcp_mask
[] = { 0xff, 0xff, 0xff, 0xff,
1894 0xff, 0xff, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
1895 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xff, 0xff,
1896 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
1897 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
1898 0x00, 0x00, 0x00, 0x00, 0xff, 0xff /* port 67 */ };
1902 /* Setup unicast IP, EAPOL-like and ARP pkt pattern */
1903 ret
= ath6kl_wmi_add_wow_pattern_cmd(ar
->wmi
,
1904 vif
->fw_vif_idx
, WOW_LIST_ID
,
1905 sizeof(unicst_pattern
), unicst_offset
,
1906 unicst_pattern
, unicst_mask
);
1908 ath6kl_err("failed to add WOW unicast IP pattern\n");
1912 /* Setup all ARP pkt pattern */
1913 ret
= ath6kl_wmi_add_wow_pattern_cmd(ar
->wmi
,
1914 vif
->fw_vif_idx
, WOW_LIST_ID
,
1915 sizeof(arp_pattern
), arp_offset
,
1916 arp_pattern
, arp_mask
);
1918 ath6kl_err("failed to add WOW ARP pattern\n");
1923 * Setup multicast pattern for mDNS 224.0.0.251,
1924 * SSDP 239.255.255.250 and LLMNR 224.0.0.252
1926 ret
= ath6kl_wmi_add_wow_pattern_cmd(ar
->wmi
,
1927 vif
->fw_vif_idx
, WOW_LIST_ID
,
1928 sizeof(discvr_pattern
), discvr_offset
,
1929 discvr_pattern
, discvr_mask
);
1931 ath6kl_err("failed to add WOW mDNS/SSDP/LLMNR pattern\n");
1935 /* Setup all DHCP broadcast pkt pattern */
1936 ret
= ath6kl_wmi_add_wow_pattern_cmd(ar
->wmi
,
1937 vif
->fw_vif_idx
, WOW_LIST_ID
,
1938 sizeof(dhcp_pattern
), dhcp_offset
,
1939 dhcp_pattern
, dhcp_mask
);
1941 ath6kl_err("failed to add WOW DHCP broadcast pattern\n");
1948 static int ath6kl_wow_sta(struct ath6kl
*ar
, struct ath6kl_vif
*vif
)
1950 struct net_device
*ndev
= vif
->ndev
;
1951 static const u8 discvr_pattern
[] = { 0xe0, 0x00, 0x00, 0xf8 };
1952 static const u8 discvr_mask
[] = { 0xf0, 0x00, 0x00, 0xf8 };
1953 u8 discvr_offset
= 38;
1954 u8 mac_mask
[ETH_ALEN
];
1957 /* Setup unicast pkt pattern */
1958 memset(mac_mask
, 0xff, ETH_ALEN
);
1959 ret
= ath6kl_wmi_add_wow_pattern_cmd(ar
->wmi
,
1960 vif
->fw_vif_idx
, WOW_LIST_ID
,
1961 ETH_ALEN
, 0, ndev
->dev_addr
,
1964 ath6kl_err("failed to add WOW unicast pattern\n");
1969 * Setup multicast pattern for mDNS 224.0.0.251,
1970 * SSDP 239.255.255.250 and LLMNR 224.0.0.252
1972 if ((ndev
->flags
& IFF_ALLMULTI
) ||
1973 (ndev
->flags
& IFF_MULTICAST
&& netdev_mc_count(ndev
) > 0)) {
1974 ret
= ath6kl_wmi_add_wow_pattern_cmd(ar
->wmi
,
1975 vif
->fw_vif_idx
, WOW_LIST_ID
,
1976 sizeof(discvr_pattern
), discvr_offset
,
1977 discvr_pattern
, discvr_mask
);
1979 ath6kl_err("failed to add WOW mDNS/SSDP/LLMNR "
1988 static int is_hsleep_mode_procsed(struct ath6kl_vif
*vif
)
1990 return test_bit(HOST_SLEEP_MODE_CMD_PROCESSED
, &vif
->flags
);
1993 static bool is_ctrl_ep_empty(struct ath6kl
*ar
)
1995 return !ar
->tx_pending
[ar
->ctrl_ep
];
1998 static int ath6kl_cfg80211_host_sleep(struct ath6kl
*ar
, struct ath6kl_vif
*vif
)
2002 clear_bit(HOST_SLEEP_MODE_CMD_PROCESSED
, &vif
->flags
);
2004 ret
= ath6kl_wmi_set_host_sleep_mode_cmd(ar
->wmi
, vif
->fw_vif_idx
,
2005 ATH6KL_HOST_MODE_ASLEEP
);
2009 left
= wait_event_interruptible_timeout(ar
->event_wq
,
2010 is_hsleep_mode_procsed(vif
),
2013 ath6kl_warn("timeout, didn't get host sleep cmd processed event\n");
2015 } else if (left
< 0) {
2016 ath6kl_warn("error while waiting for host sleep cmd processed event %d\n",
2021 if (ar
->tx_pending
[ar
->ctrl_ep
]) {
2022 left
= wait_event_interruptible_timeout(ar
->event_wq
,
2023 is_ctrl_ep_empty(ar
),
2026 ath6kl_warn("clear wmi ctrl data timeout\n");
2028 } else if (left
< 0) {
2029 ath6kl_warn("clear wmi ctrl data failed: %d\n", left
);
2037 static int ath6kl_wow_suspend(struct ath6kl
*ar
, struct cfg80211_wowlan
*wow
)
2039 struct in_device
*in_dev
;
2040 struct in_ifaddr
*ifa
;
2041 struct ath6kl_vif
*vif
;
2046 __be32 ips
[MAX_IP_ADDRS
];
2048 vif
= ath6kl_vif_first(ar
);
2052 if (!ath6kl_cfg80211_ready(vif
))
2055 if (!test_bit(CONNECTED
, &vif
->flags
))
2058 if (wow
&& (wow
->n_patterns
> WOW_MAX_FILTERS_PER_LIST
))
2061 /* Clear existing WOW patterns */
2062 for (i
= 0; i
< WOW_MAX_FILTERS_PER_LIST
; i
++)
2063 ath6kl_wmi_del_wow_pattern_cmd(ar
->wmi
, vif
->fw_vif_idx
,
2067 * Skip the default WOW pattern configuration
2068 * if the driver receives any WOW patterns from
2072 ret
= ath6kl_wow_usr(ar
, vif
, wow
, &filter
);
2073 else if (vif
->nw_type
== AP_NETWORK
)
2074 ret
= ath6kl_wow_ap(ar
, vif
);
2076 ret
= ath6kl_wow_sta(ar
, vif
);
2081 netif_stop_queue(vif
->ndev
);
2083 if (vif
->nw_type
!= AP_NETWORK
) {
2084 ret
= ath6kl_wmi_listeninterval_cmd(ar
->wmi
, vif
->fw_vif_idx
,
2085 ATH6KL_MAX_WOW_LISTEN_INTL
,
2090 /* Set listen interval x 15 times as bmiss time */
2091 bmiss_time
= ATH6KL_MAX_WOW_LISTEN_INTL
* 15;
2092 if (bmiss_time
> ATH6KL_MAX_BMISS_TIME
)
2093 bmiss_time
= ATH6KL_MAX_BMISS_TIME
;
2095 ret
= ath6kl_wmi_bmisstime_cmd(ar
->wmi
, vif
->fw_vif_idx
,
2100 ret
= ath6kl_wmi_scanparams_cmd(ar
->wmi
, vif
->fw_vif_idx
,
2101 0xFFFF, 0, 0xFFFF, 0, 0, 0,
2107 ar
->state
= ATH6KL_STATE_SUSPENDING
;
2109 /* Setup own IP addr for ARP agent. */
2110 in_dev
= __in_dev_get_rtnl(vif
->ndev
);
2114 ifa
= in_dev
->ifa_list
;
2115 memset(&ips
, 0, sizeof(ips
));
2117 /* Configure IP addr only if IP address count < MAX_IP_ADDRS */
2118 while (index
< MAX_IP_ADDRS
&& ifa
) {
2119 ips
[index
] = ifa
->ifa_local
;
2120 ifa
= ifa
->ifa_next
;
2125 ath6kl_err("total IP addr count is exceeding fw limit\n");
2129 ret
= ath6kl_wmi_set_ip_cmd(ar
->wmi
, vif
->fw_vif_idx
, ips
[0], ips
[1]);
2131 ath6kl_err("fail to setup ip for arp agent\n");
2136 ret
= ath6kl_wmi_set_wow_mode_cmd(ar
->wmi
, vif
->fw_vif_idx
,
2137 ATH6KL_WOW_MODE_ENABLE
,
2139 WOW_HOST_REQ_DELAY
);
2143 ret
= ath6kl_cfg80211_host_sleep(ar
, vif
);
2150 static int ath6kl_wow_resume(struct ath6kl
*ar
)
2152 struct ath6kl_vif
*vif
;
2155 vif
= ath6kl_vif_first(ar
);
2159 ar
->state
= ATH6KL_STATE_RESUMING
;
2161 ret
= ath6kl_wmi_set_host_sleep_mode_cmd(ar
->wmi
, vif
->fw_vif_idx
,
2162 ATH6KL_HOST_MODE_AWAKE
);
2164 ath6kl_warn("Failed to configure host sleep mode for "
2165 "wow resume: %d\n", ret
);
2166 ar
->state
= ATH6KL_STATE_WOW
;
2170 if (vif
->nw_type
!= AP_NETWORK
) {
2171 ret
= ath6kl_wmi_scanparams_cmd(ar
->wmi
, vif
->fw_vif_idx
,
2172 0, 0, 0, 0, 0, 0, 3, 0, 0, 0);
2176 ret
= ath6kl_wmi_listeninterval_cmd(ar
->wmi
, vif
->fw_vif_idx
,
2177 vif
->listen_intvl_t
, 0);
2181 ret
= ath6kl_wmi_bmisstime_cmd(ar
->wmi
, vif
->fw_vif_idx
,
2182 vif
->bmiss_time_t
, 0);
2187 ar
->state
= ATH6KL_STATE_ON
;
2189 netif_wake_queue(vif
->ndev
);
2194 static int ath6kl_cfg80211_deepsleep_suspend(struct ath6kl
*ar
)
2196 struct ath6kl_vif
*vif
;
2199 vif
= ath6kl_vif_first(ar
);
2203 if (!ath6kl_cfg80211_ready(vif
))
2206 ath6kl_cfg80211_stop_all(ar
);
2208 /* Save the current power mode before enabling power save */
2209 ar
->wmi
->saved_pwr_mode
= ar
->wmi
->pwr_mode
;
2211 ret
= ath6kl_wmi_powermode_cmd(ar
->wmi
, 0, REC_POWER
);
2215 /* Disable WOW mode */
2216 ret
= ath6kl_wmi_set_wow_mode_cmd(ar
->wmi
, vif
->fw_vif_idx
,
2217 ATH6KL_WOW_MODE_DISABLE
,
2222 /* Flush all non control pkts in TX path */
2223 ath6kl_tx_data_cleanup(ar
);
2225 ret
= ath6kl_cfg80211_host_sleep(ar
, vif
);
2232 static int ath6kl_cfg80211_deepsleep_resume(struct ath6kl
*ar
)
2234 struct ath6kl_vif
*vif
;
2237 vif
= ath6kl_vif_first(ar
);
2242 if (ar
->wmi
->pwr_mode
!= ar
->wmi
->saved_pwr_mode
) {
2243 ret
= ath6kl_wmi_powermode_cmd(ar
->wmi
, 0,
2244 ar
->wmi
->saved_pwr_mode
);
2249 ret
= ath6kl_wmi_set_host_sleep_mode_cmd(ar
->wmi
, vif
->fw_vif_idx
,
2250 ATH6KL_HOST_MODE_AWAKE
);
2254 ar
->state
= ATH6KL_STATE_ON
;
2256 /* Reset scan parameter to default values */
2257 ret
= ath6kl_wmi_scanparams_cmd(ar
->wmi
, vif
->fw_vif_idx
,
2258 0, 0, 0, 0, 0, 0, 3, 0, 0, 0);
2265 int ath6kl_cfg80211_suspend(struct ath6kl
*ar
,
2266 enum ath6kl_cfg_suspend_mode mode
,
2267 struct cfg80211_wowlan
*wow
)
2269 struct ath6kl_vif
*vif
;
2270 enum ath6kl_state prev_state
;
2274 case ATH6KL_CFG_SUSPEND_WOW
:
2276 ath6kl_dbg(ATH6KL_DBG_SUSPEND
, "wow mode suspend\n");
2278 /* Flush all non control pkts in TX path */
2279 ath6kl_tx_data_cleanup(ar
);
2281 prev_state
= ar
->state
;
2283 ret
= ath6kl_wow_suspend(ar
, wow
);
2285 ar
->state
= prev_state
;
2289 ar
->state
= ATH6KL_STATE_WOW
;
2292 case ATH6KL_CFG_SUSPEND_DEEPSLEEP
:
2294 ath6kl_dbg(ATH6KL_DBG_SUSPEND
, "deep sleep suspend\n");
2296 ret
= ath6kl_cfg80211_deepsleep_suspend(ar
);
2298 ath6kl_err("deepsleep suspend failed: %d\n", ret
);
2302 ar
->state
= ATH6KL_STATE_DEEPSLEEP
;
2306 case ATH6KL_CFG_SUSPEND_CUTPOWER
:
2308 ath6kl_cfg80211_stop_all(ar
);
2310 if (ar
->state
== ATH6KL_STATE_OFF
) {
2311 ath6kl_dbg(ATH6KL_DBG_SUSPEND
,
2312 "suspend hw off, no action for cutpower\n");
2316 ath6kl_dbg(ATH6KL_DBG_SUSPEND
, "suspend cutting power\n");
2318 ret
= ath6kl_init_hw_stop(ar
);
2320 ath6kl_warn("failed to stop hw during suspend: %d\n",
2324 ar
->state
= ATH6KL_STATE_CUTPOWER
;
2328 case ATH6KL_CFG_SUSPEND_SCHED_SCAN
:
2330 * Nothing needed for schedule scan, firmware is already in
2331 * wow mode and sleeping most of the time.
2339 list_for_each_entry(vif
, &ar
->vif_list
, list
)
2340 ath6kl_cfg80211_scan_complete_event(vif
, true);
2344 EXPORT_SYMBOL(ath6kl_cfg80211_suspend
);
2346 int ath6kl_cfg80211_resume(struct ath6kl
*ar
)
2350 switch (ar
->state
) {
2351 case ATH6KL_STATE_WOW
:
2352 ath6kl_dbg(ATH6KL_DBG_SUSPEND
, "wow mode resume\n");
2354 ret
= ath6kl_wow_resume(ar
);
2356 ath6kl_warn("wow mode resume failed: %d\n", ret
);
2362 case ATH6KL_STATE_DEEPSLEEP
:
2363 ath6kl_dbg(ATH6KL_DBG_SUSPEND
, "deep sleep resume\n");
2365 ret
= ath6kl_cfg80211_deepsleep_resume(ar
);
2367 ath6kl_warn("deep sleep resume failed: %d\n", ret
);
2372 case ATH6KL_STATE_CUTPOWER
:
2373 ath6kl_dbg(ATH6KL_DBG_SUSPEND
, "resume restoring power\n");
2375 ret
= ath6kl_init_hw_start(ar
);
2377 ath6kl_warn("Failed to boot hw in resume: %d\n", ret
);
2382 case ATH6KL_STATE_SCHED_SCAN
:
2391 EXPORT_SYMBOL(ath6kl_cfg80211_resume
);
2395 /* hif layer decides what suspend mode to use */
2396 static int __ath6kl_cfg80211_suspend(struct wiphy
*wiphy
,
2397 struct cfg80211_wowlan
*wow
)
2399 struct ath6kl
*ar
= wiphy_priv(wiphy
);
2401 return ath6kl_hif_suspend(ar
, wow
);
2404 static int __ath6kl_cfg80211_resume(struct wiphy
*wiphy
)
2406 struct ath6kl
*ar
= wiphy_priv(wiphy
);
2408 return ath6kl_hif_resume(ar
);
2412 * FIXME: WOW suspend mode is selected if the host sdio controller supports
2413 * both sdio irq wake up and keep power. The target pulls sdio data line to
2414 * wake up the host when WOW pattern matches. This causes sdio irq handler
2415 * is being called in the host side which internally hits ath6kl's RX path.
2417 * Since sdio interrupt is not disabled, RX path executes even before
2418 * the host executes the actual resume operation from PM module.
2420 * In the current scenario, WOW resume should happen before start processing
2421 * any data from the target. So It's required to perform WOW resume in RX path.
2422 * Ideally we should perform WOW resume only in the actual platform
2423 * resume path. This area needs bit rework to avoid WOW resume in RX path.
2425 * ath6kl_check_wow_status() is called from ath6kl_rx().
2427 void ath6kl_check_wow_status(struct ath6kl
*ar
)
2429 if (ar
->state
== ATH6KL_STATE_SUSPENDING
)
2432 if (ar
->state
== ATH6KL_STATE_WOW
)
2433 ath6kl_cfg80211_resume(ar
);
2438 void ath6kl_check_wow_status(struct ath6kl
*ar
)
2443 static int ath6kl_set_htcap(struct ath6kl_vif
*vif
, enum ieee80211_band band
,
2446 struct ath6kl_htcap
*htcap
= &vif
->htcap
;
2448 if (htcap
->ht_enable
== ht_enable
)
2452 /* Set default ht capabilities */
2453 htcap
->ht_enable
= true;
2454 htcap
->cap_info
= (band
== IEEE80211_BAND_2GHZ
) ?
2455 ath6kl_g_htcap
: ath6kl_a_htcap
;
2456 htcap
->ampdu_factor
= IEEE80211_HT_MAX_AMPDU_16K
;
2457 } else /* Disable ht */
2458 memset(htcap
, 0, sizeof(*htcap
));
2460 return ath6kl_wmi_set_htcap_cmd(vif
->ar
->wmi
, vif
->fw_vif_idx
,
2464 static bool ath6kl_is_p2p_ie(const u8
*pos
)
2466 return pos
[0] == WLAN_EID_VENDOR_SPECIFIC
&& pos
[1] >= 4 &&
2467 pos
[2] == 0x50 && pos
[3] == 0x6f &&
2468 pos
[4] == 0x9a && pos
[5] == 0x09;
2471 static int ath6kl_set_ap_probe_resp_ies(struct ath6kl_vif
*vif
,
2472 const u8
*ies
, size_t ies_len
)
2474 struct ath6kl
*ar
= vif
->ar
;
2481 * Filter out P2P IE(s) since they will be included depending on
2482 * the Probe Request frame in ath6kl_send_go_probe_resp().
2485 if (ies
&& ies_len
) {
2486 buf
= kmalloc(ies_len
, GFP_KERNEL
);
2490 while (pos
+ 1 < ies
+ ies_len
) {
2491 if (pos
+ 2 + pos
[1] > ies
+ ies_len
)
2493 if (!ath6kl_is_p2p_ie(pos
)) {
2494 memcpy(buf
+ len
, pos
, 2 + pos
[1]);
2501 ret
= ath6kl_wmi_set_appie_cmd(ar
->wmi
, vif
->fw_vif_idx
,
2502 WMI_FRAME_PROBE_RESP
, buf
, len
);
2507 static int ath6kl_set_ies(struct ath6kl_vif
*vif
,
2508 struct cfg80211_beacon_data
*info
)
2510 struct ath6kl
*ar
= vif
->ar
;
2513 /* this also clears IE in fw if it's not set */
2514 res
= ath6kl_wmi_set_appie_cmd(ar
->wmi
, vif
->fw_vif_idx
,
2517 info
->beacon_ies_len
);
2521 /* this also clears IE in fw if it's not set */
2522 res
= ath6kl_set_ap_probe_resp_ies(vif
, info
->proberesp_ies
,
2523 info
->proberesp_ies_len
);
2527 /* this also clears IE in fw if it's not set */
2528 res
= ath6kl_wmi_set_appie_cmd(ar
->wmi
, vif
->fw_vif_idx
,
2529 WMI_FRAME_ASSOC_RESP
,
2530 info
->assocresp_ies
,
2531 info
->assocresp_ies_len
);
2538 static int ath6kl_set_channel(struct wiphy
*wiphy
, struct net_device
*dev
,
2539 struct ieee80211_channel
*chan
,
2540 enum nl80211_channel_type channel_type
)
2542 struct ath6kl_vif
*vif
;
2545 * 'dev' could be NULL if a channel change is required for the hardware
2546 * device itself, instead of a particular VIF.
2548 * FIXME: To be handled properly when monitor mode is supported.
2553 vif
= netdev_priv(dev
);
2555 if (!ath6kl_cfg80211_ready(vif
))
2558 ath6kl_dbg(ATH6KL_DBG_WLAN_CFG
, "%s: center_freq=%u hw_value=%u\n",
2559 __func__
, chan
->center_freq
, chan
->hw_value
);
2560 vif
->next_chan
= chan
->center_freq
;
2561 vif
->next_ch_type
= channel_type
;
2562 vif
->next_ch_band
= chan
->band
;
2567 static int ath6kl_get_rsn_capab(struct cfg80211_beacon_data
*beacon
,
2577 rsn_ie
= cfg80211_find_ie(WLAN_EID_RSN
, beacon
->tail
, beacon
->tail_len
);
2581 rsn_ie_len
= *(rsn_ie
+ 1);
2582 /* skip element id and length */
2585 /* skip version, group cipher */
2591 /* skip pairwise cipher suite */
2594 cnt
= get_unaligned_le16(rsn_ie
);
2595 rsn_ie
+= (2 + cnt
* 4);
2596 rsn_ie_len
-= (2 + cnt
* 4);
2598 /* skip akm suite */
2601 cnt
= get_unaligned_le16(rsn_ie
);
2602 rsn_ie
+= (2 + cnt
* 4);
2603 rsn_ie_len
-= (2 + cnt
* 4);
2608 memcpy(rsn_capab
, rsn_ie
, 2);
2613 static int ath6kl_start_ap(struct wiphy
*wiphy
, struct net_device
*dev
,
2614 struct cfg80211_ap_settings
*info
)
2616 struct ath6kl
*ar
= ath6kl_priv(dev
);
2617 struct ath6kl_vif
*vif
= netdev_priv(dev
);
2618 struct ieee80211_mgmt
*mgmt
;
2619 bool hidden
= false;
2622 struct wmi_connect_cmd p
;
2627 ath6kl_dbg(ATH6KL_DBG_WLAN_CFG
, "%s:\n", __func__
);
2629 if (!ath6kl_cfg80211_ready(vif
))
2632 if (vif
->next_mode
!= AP_NETWORK
)
2635 res
= ath6kl_set_ies(vif
, &info
->beacon
);
2637 ar
->ap_mode_bkey
.valid
= false;
2644 if (info
->beacon
.head
== NULL
)
2646 mgmt
= (struct ieee80211_mgmt
*) info
->beacon
.head
;
2647 ies
= mgmt
->u
.beacon
.variable
;
2648 if (ies
> info
->beacon
.head
+ info
->beacon
.head_len
)
2650 ies_len
= info
->beacon
.head
+ info
->beacon
.head_len
- ies
;
2652 if (info
->ssid
== NULL
)
2654 memcpy(vif
->ssid
, info
->ssid
, info
->ssid_len
);
2655 vif
->ssid_len
= info
->ssid_len
;
2656 if (info
->hidden_ssid
!= NL80211_HIDDEN_SSID_NOT_IN_USE
)
2659 res
= ath6kl_wmi_ap_hidden_ssid(ar
->wmi
, vif
->fw_vif_idx
, hidden
);
2663 ret
= ath6kl_set_auth_type(vif
, info
->auth_type
);
2667 memset(&p
, 0, sizeof(p
));
2669 for (i
= 0; i
< info
->crypto
.n_akm_suites
; i
++) {
2670 switch (info
->crypto
.akm_suites
[i
]) {
2671 case WLAN_AKM_SUITE_8021X
:
2672 if (info
->crypto
.wpa_versions
& NL80211_WPA_VERSION_1
)
2673 p
.auth_mode
|= WPA_AUTH
;
2674 if (info
->crypto
.wpa_versions
& NL80211_WPA_VERSION_2
)
2675 p
.auth_mode
|= WPA2_AUTH
;
2677 case WLAN_AKM_SUITE_PSK
:
2678 if (info
->crypto
.wpa_versions
& NL80211_WPA_VERSION_1
)
2679 p
.auth_mode
|= WPA_PSK_AUTH
;
2680 if (info
->crypto
.wpa_versions
& NL80211_WPA_VERSION_2
)
2681 p
.auth_mode
|= WPA2_PSK_AUTH
;
2685 if (p
.auth_mode
== 0)
2686 p
.auth_mode
= NONE_AUTH
;
2687 vif
->auth_mode
= p
.auth_mode
;
2689 for (i
= 0; i
< info
->crypto
.n_ciphers_pairwise
; i
++) {
2690 switch (info
->crypto
.ciphers_pairwise
[i
]) {
2691 case WLAN_CIPHER_SUITE_WEP40
:
2692 case WLAN_CIPHER_SUITE_WEP104
:
2693 p
.prwise_crypto_type
|= WEP_CRYPT
;
2695 case WLAN_CIPHER_SUITE_TKIP
:
2696 p
.prwise_crypto_type
|= TKIP_CRYPT
;
2698 case WLAN_CIPHER_SUITE_CCMP
:
2699 p
.prwise_crypto_type
|= AES_CRYPT
;
2701 case WLAN_CIPHER_SUITE_SMS4
:
2702 p
.prwise_crypto_type
|= WAPI_CRYPT
;
2706 if (p
.prwise_crypto_type
== 0) {
2707 p
.prwise_crypto_type
= NONE_CRYPT
;
2708 ath6kl_set_cipher(vif
, 0, true);
2709 } else if (info
->crypto
.n_ciphers_pairwise
== 1)
2710 ath6kl_set_cipher(vif
, info
->crypto
.ciphers_pairwise
[0], true);
2712 switch (info
->crypto
.cipher_group
) {
2713 case WLAN_CIPHER_SUITE_WEP40
:
2714 case WLAN_CIPHER_SUITE_WEP104
:
2715 p
.grp_crypto_type
= WEP_CRYPT
;
2717 case WLAN_CIPHER_SUITE_TKIP
:
2718 p
.grp_crypto_type
= TKIP_CRYPT
;
2720 case WLAN_CIPHER_SUITE_CCMP
:
2721 p
.grp_crypto_type
= AES_CRYPT
;
2723 case WLAN_CIPHER_SUITE_SMS4
:
2724 p
.grp_crypto_type
= WAPI_CRYPT
;
2727 p
.grp_crypto_type
= NONE_CRYPT
;
2730 ath6kl_set_cipher(vif
, info
->crypto
.cipher_group
, false);
2732 p
.nw_type
= AP_NETWORK
;
2733 vif
->nw_type
= vif
->next_mode
;
2735 p
.ssid_len
= vif
->ssid_len
;
2736 memcpy(p
.ssid
, vif
->ssid
, vif
->ssid_len
);
2737 p
.dot11_auth_mode
= vif
->dot11_auth_mode
;
2738 p
.ch
= cpu_to_le16(vif
->next_chan
);
2740 /* Enable uAPSD support by default */
2741 res
= ath6kl_wmi_ap_set_apsd(ar
->wmi
, vif
->fw_vif_idx
, true);
2745 if (vif
->wdev
.iftype
== NL80211_IFTYPE_P2P_GO
) {
2746 p
.nw_subtype
= SUBTYPE_P2PGO
;
2749 * Due to firmware limitation, it is not possible to
2750 * do P2P mgmt operations in AP mode
2752 p
.nw_subtype
= SUBTYPE_NONE
;
2755 if (info
->inactivity_timeout
) {
2756 res
= ath6kl_wmi_set_inact_period(ar
->wmi
, vif
->fw_vif_idx
,
2757 info
->inactivity_timeout
);
2762 if (ath6kl_set_htcap(vif
, vif
->next_ch_band
,
2763 vif
->next_ch_type
!= NL80211_CHAN_NO_HT
))
2767 * Get the PTKSA replay counter in the RSN IE. Supplicant
2768 * will use the RSN IE in M3 message and firmware has to
2769 * advertise the same in beacon/probe response. Send
2770 * the complete RSN IE capability field to firmware
2772 if (!ath6kl_get_rsn_capab(&info
->beacon
, (u8
*) &rsn_capab
) &&
2773 test_bit(ATH6KL_FW_CAPABILITY_RSN_CAP_OVERRIDE
,
2774 ar
->fw_capabilities
)) {
2775 res
= ath6kl_wmi_set_ie_cmd(ar
->wmi
, vif
->fw_vif_idx
,
2776 WLAN_EID_RSN
, WMI_RSN_IE_CAPB
,
2777 (const u8
*) &rsn_capab
,
2783 memcpy(&vif
->profile
, &p
, sizeof(p
));
2784 res
= ath6kl_wmi_ap_profile_commit(ar
->wmi
, vif
->fw_vif_idx
, &p
);
2791 static int ath6kl_change_beacon(struct wiphy
*wiphy
, struct net_device
*dev
,
2792 struct cfg80211_beacon_data
*beacon
)
2794 struct ath6kl_vif
*vif
= netdev_priv(dev
);
2796 if (!ath6kl_cfg80211_ready(vif
))
2799 if (vif
->next_mode
!= AP_NETWORK
)
2802 return ath6kl_set_ies(vif
, beacon
);
2805 static int ath6kl_stop_ap(struct wiphy
*wiphy
, struct net_device
*dev
)
2807 struct ath6kl
*ar
= ath6kl_priv(dev
);
2808 struct ath6kl_vif
*vif
= netdev_priv(dev
);
2810 if (vif
->nw_type
!= AP_NETWORK
)
2812 if (!test_bit(CONNECTED
, &vif
->flags
))
2815 ath6kl_wmi_disconnect_cmd(ar
->wmi
, vif
->fw_vif_idx
);
2816 clear_bit(CONNECTED
, &vif
->flags
);
2818 /* Restore ht setting in firmware */
2819 if (ath6kl_set_htcap(vif
, IEEE80211_BAND_2GHZ
, true))
2822 if (ath6kl_set_htcap(vif
, IEEE80211_BAND_5GHZ
, true))
2828 static const u8 bcast_addr
[ETH_ALEN
] = { 0xff, 0xff, 0xff, 0xff, 0xff, 0xff };
2830 static int ath6kl_del_station(struct wiphy
*wiphy
, struct net_device
*dev
,
2833 struct ath6kl
*ar
= ath6kl_priv(dev
);
2834 struct ath6kl_vif
*vif
= netdev_priv(dev
);
2835 const u8
*addr
= mac
? mac
: bcast_addr
;
2837 return ath6kl_wmi_ap_set_mlme(ar
->wmi
, vif
->fw_vif_idx
, WMI_AP_DEAUTH
,
2838 addr
, WLAN_REASON_PREV_AUTH_NOT_VALID
);
2841 static int ath6kl_change_station(struct wiphy
*wiphy
, struct net_device
*dev
,
2842 u8
*mac
, struct station_parameters
*params
)
2844 struct ath6kl
*ar
= ath6kl_priv(dev
);
2845 struct ath6kl_vif
*vif
= netdev_priv(dev
);
2847 if (vif
->nw_type
!= AP_NETWORK
)
2850 /* Use this only for authorizing/unauthorizing a station */
2851 if (!(params
->sta_flags_mask
& BIT(NL80211_STA_FLAG_AUTHORIZED
)))
2854 if (params
->sta_flags_set
& BIT(NL80211_STA_FLAG_AUTHORIZED
))
2855 return ath6kl_wmi_ap_set_mlme(ar
->wmi
, vif
->fw_vif_idx
,
2856 WMI_AP_MLME_AUTHORIZE
, mac
, 0);
2857 return ath6kl_wmi_ap_set_mlme(ar
->wmi
, vif
->fw_vif_idx
,
2858 WMI_AP_MLME_UNAUTHORIZE
, mac
, 0);
2861 static int ath6kl_remain_on_channel(struct wiphy
*wiphy
,
2862 struct net_device
*dev
,
2863 struct ieee80211_channel
*chan
,
2864 enum nl80211_channel_type channel_type
,
2865 unsigned int duration
,
2868 struct ath6kl
*ar
= ath6kl_priv(dev
);
2869 struct ath6kl_vif
*vif
= netdev_priv(dev
);
2872 /* TODO: if already pending or ongoing remain-on-channel,
2874 id
= ++vif
->last_roc_id
;
2876 /* Do not use 0 as the cookie value */
2877 id
= ++vif
->last_roc_id
;
2881 return ath6kl_wmi_remain_on_chnl_cmd(ar
->wmi
, vif
->fw_vif_idx
,
2882 chan
->center_freq
, duration
);
2885 static int ath6kl_cancel_remain_on_channel(struct wiphy
*wiphy
,
2886 struct net_device
*dev
,
2889 struct ath6kl
*ar
= ath6kl_priv(dev
);
2890 struct ath6kl_vif
*vif
= netdev_priv(dev
);
2892 if (cookie
!= vif
->last_roc_id
)
2894 vif
->last_cancel_roc_id
= cookie
;
2896 return ath6kl_wmi_cancel_remain_on_chnl_cmd(ar
->wmi
, vif
->fw_vif_idx
);
2899 static int ath6kl_send_go_probe_resp(struct ath6kl_vif
*vif
,
2900 const u8
*buf
, size_t len
,
2903 struct ath6kl
*ar
= vif
->ar
;
2908 const struct ieee80211_mgmt
*mgmt
;
2910 mgmt
= (const struct ieee80211_mgmt
*) buf
;
2912 /* Include P2P IE(s) from the frame generated in user space. */
2914 p2p
= kmalloc(len
, GFP_KERNEL
);
2919 pos
= mgmt
->u
.probe_resp
.variable
;
2920 while (pos
+ 1 < buf
+ len
) {
2921 if (pos
+ 2 + pos
[1] > buf
+ len
)
2923 if (ath6kl_is_p2p_ie(pos
)) {
2924 memcpy(p2p
+ p2p_len
, pos
, 2 + pos
[1]);
2925 p2p_len
+= 2 + pos
[1];
2930 ret
= ath6kl_wmi_send_probe_response_cmd(ar
->wmi
, vif
->fw_vif_idx
, freq
,
2931 mgmt
->da
, p2p
, p2p_len
);
2936 static bool ath6kl_mgmt_powersave_ap(struct ath6kl_vif
*vif
,
2945 struct ieee80211_mgmt
*mgmt
;
2946 struct ath6kl_sta
*conn
;
2947 bool is_psq_empty
= false;
2948 struct ath6kl_mgmt_buff
*mgmt_buf
;
2949 size_t mgmt_buf_size
;
2950 struct ath6kl
*ar
= vif
->ar
;
2952 mgmt
= (struct ieee80211_mgmt
*) buf
;
2953 if (is_multicast_ether_addr(mgmt
->da
))
2956 conn
= ath6kl_find_sta(vif
, mgmt
->da
);
2960 if (conn
->sta_flags
& STA_PS_SLEEP
) {
2961 if (!(conn
->sta_flags
& STA_PS_POLLED
)) {
2962 /* Queue the frames if the STA is sleeping */
2963 mgmt_buf_size
= len
+ sizeof(struct ath6kl_mgmt_buff
);
2964 mgmt_buf
= kmalloc(mgmt_buf_size
, GFP_KERNEL
);
2968 INIT_LIST_HEAD(&mgmt_buf
->list
);
2970 mgmt_buf
->freq
= freq
;
2971 mgmt_buf
->wait
= wait
;
2972 mgmt_buf
->len
= len
;
2973 mgmt_buf
->no_cck
= no_cck
;
2974 memcpy(mgmt_buf
->buf
, buf
, len
);
2975 spin_lock_bh(&conn
->psq_lock
);
2976 is_psq_empty
= skb_queue_empty(&conn
->psq
) &&
2977 (conn
->mgmt_psq_len
== 0);
2978 list_add_tail(&mgmt_buf
->list
, &conn
->mgmt_psq
);
2979 conn
->mgmt_psq_len
++;
2980 spin_unlock_bh(&conn
->psq_lock
);
2983 * If this is the first pkt getting queued
2984 * for this STA, update the PVB for this
2988 ath6kl_wmi_set_pvb_cmd(ar
->wmi
, vif
->fw_vif_idx
,
2994 * This tx is because of a PsPoll.
2995 * Determine if MoreData bit has to be set.
2997 spin_lock_bh(&conn
->psq_lock
);
2998 if (!skb_queue_empty(&conn
->psq
) || (conn
->mgmt_psq_len
!= 0))
3000 spin_unlock_bh(&conn
->psq_lock
);
3006 /* Check if SSID length is greater than DIRECT- */
3007 static bool ath6kl_is_p2p_go_ssid(const u8
*buf
, size_t len
)
3009 const struct ieee80211_mgmt
*mgmt
;
3010 mgmt
= (const struct ieee80211_mgmt
*) buf
;
3012 /* variable[1] contains the SSID tag length */
3013 if (buf
+ len
>= &mgmt
->u
.probe_resp
.variable
[1] &&
3014 (mgmt
->u
.probe_resp
.variable
[1] > P2P_WILDCARD_SSID_LEN
)) {
3021 static int ath6kl_mgmt_tx(struct wiphy
*wiphy
, struct net_device
*dev
,
3022 struct ieee80211_channel
*chan
, bool offchan
,
3023 enum nl80211_channel_type channel_type
,
3024 bool channel_type_valid
, unsigned int wait
,
3025 const u8
*buf
, size_t len
, bool no_cck
,
3026 bool dont_wait_for_ack
, u64
*cookie
)
3028 struct ath6kl
*ar
= ath6kl_priv(dev
);
3029 struct ath6kl_vif
*vif
= netdev_priv(dev
);
3031 const struct ieee80211_mgmt
*mgmt
;
3032 bool more_data
, queued
;
3034 mgmt
= (const struct ieee80211_mgmt
*) buf
;
3035 if (vif
->nw_type
== AP_NETWORK
&& test_bit(CONNECTED
, &vif
->flags
) &&
3036 ieee80211_is_probe_resp(mgmt
->frame_control
) &&
3037 ath6kl_is_p2p_go_ssid(buf
, len
)) {
3039 * Send Probe Response frame in GO mode using a separate WMI
3040 * command to allow the target to fill in the generic IEs.
3042 *cookie
= 0; /* TX status not supported */
3043 return ath6kl_send_go_probe_resp(vif
, buf
, len
,
3047 id
= vif
->send_action_id
++;
3050 * 0 is a reserved value in the WMI command and shall not be
3051 * used for the command.
3053 id
= vif
->send_action_id
++;
3058 /* AP mode Power saving processing */
3059 if (vif
->nw_type
== AP_NETWORK
) {
3060 queued
= ath6kl_mgmt_powersave_ap(vif
,
3061 id
, chan
->center_freq
,
3063 len
, &more_data
, no_cck
);
3068 return ath6kl_wmi_send_mgmt_cmd(ar
->wmi
, vif
->fw_vif_idx
, id
,
3069 chan
->center_freq
, wait
,
3073 static void ath6kl_mgmt_frame_register(struct wiphy
*wiphy
,
3074 struct net_device
*dev
,
3075 u16 frame_type
, bool reg
)
3077 struct ath6kl_vif
*vif
= netdev_priv(dev
);
3079 ath6kl_dbg(ATH6KL_DBG_WLAN_CFG
, "%s: frame_type=0x%x reg=%d\n",
3080 __func__
, frame_type
, reg
);
3081 if (frame_type
== IEEE80211_STYPE_PROBE_REQ
) {
3083 * Note: This notification callback is not allowed to sleep, so
3084 * we cannot send WMI_PROBE_REQ_REPORT_CMD here. Instead, we
3085 * hardcode target to report Probe Request frames all the time.
3087 vif
->probe_req_report
= reg
;
3091 static int ath6kl_cfg80211_sscan_start(struct wiphy
*wiphy
,
3092 struct net_device
*dev
,
3093 struct cfg80211_sched_scan_request
*request
)
3095 struct ath6kl
*ar
= ath6kl_priv(dev
);
3096 struct ath6kl_vif
*vif
= netdev_priv(dev
);
3101 if (ar
->state
!= ATH6KL_STATE_ON
)
3104 if (vif
->sme_state
!= SME_DISCONNECTED
)
3107 ath6kl_cfg80211_scan_complete_event(vif
, true);
3109 for (i
= 0; i
< ar
->wiphy
->max_sched_scan_ssids
; i
++) {
3110 ath6kl_wmi_probedssid_cmd(ar
->wmi
, vif
->fw_vif_idx
,
3111 i
, DISABLE_SSID_FLAG
,
3115 /* fw uses seconds, also make sure that it's >0 */
3116 interval
= max_t(u16
, 1, request
->interval
/ 1000);
3118 ath6kl_wmi_scanparams_cmd(ar
->wmi
, vif
->fw_vif_idx
,
3120 10, 0, 0, 0, 3, 0, 0, 0);
3122 if (request
->n_ssids
&& request
->ssids
[0].ssid_len
) {
3123 for (i
= 0; i
< request
->n_ssids
; i
++) {
3124 ath6kl_wmi_probedssid_cmd(ar
->wmi
, vif
->fw_vif_idx
,
3125 i
, SPECIFIC_SSID_FLAG
,
3126 request
->ssids
[i
].ssid_len
,
3127 request
->ssids
[i
].ssid
);
3131 ret
= ath6kl_wmi_set_wow_mode_cmd(ar
->wmi
, vif
->fw_vif_idx
,
3132 ATH6KL_WOW_MODE_ENABLE
,
3134 WOW_HOST_REQ_DELAY
);
3136 ath6kl_warn("Failed to enable wow with ssid filter: %d\n", ret
);
3140 /* this also clears IE in fw if it's not set */
3141 ret
= ath6kl_wmi_set_appie_cmd(ar
->wmi
, vif
->fw_vif_idx
,
3142 WMI_FRAME_PROBE_REQ
,
3143 request
->ie
, request
->ie_len
);
3145 ath6kl_warn("Failed to set probe request IE for scheduled scan: %d",
3150 ret
= ath6kl_wmi_set_host_sleep_mode_cmd(ar
->wmi
, vif
->fw_vif_idx
,
3151 ATH6KL_HOST_MODE_ASLEEP
);
3153 ath6kl_warn("Failed to enable host sleep mode for sched scan: %d\n",
3158 ar
->state
= ATH6KL_STATE_SCHED_SCAN
;
3163 static int ath6kl_cfg80211_sscan_stop(struct wiphy
*wiphy
,
3164 struct net_device
*dev
)
3166 struct ath6kl_vif
*vif
= netdev_priv(dev
);
3169 stopped
= __ath6kl_cfg80211_sscan_stop(vif
);
3177 static const struct ieee80211_txrx_stypes
3178 ath6kl_mgmt_stypes
[NUM_NL80211_IFTYPES
] = {
3179 [NL80211_IFTYPE_STATION
] = {
3180 .tx
= BIT(IEEE80211_STYPE_ACTION
>> 4) |
3181 BIT(IEEE80211_STYPE_PROBE_RESP
>> 4),
3182 .rx
= BIT(IEEE80211_STYPE_ACTION
>> 4) |
3183 BIT(IEEE80211_STYPE_PROBE_REQ
>> 4)
3185 [NL80211_IFTYPE_AP
] = {
3186 .tx
= BIT(IEEE80211_STYPE_ACTION
>> 4) |
3187 BIT(IEEE80211_STYPE_PROBE_RESP
>> 4),
3188 .rx
= BIT(IEEE80211_STYPE_ACTION
>> 4) |
3189 BIT(IEEE80211_STYPE_PROBE_REQ
>> 4)
3191 [NL80211_IFTYPE_P2P_CLIENT
] = {
3192 .tx
= BIT(IEEE80211_STYPE_ACTION
>> 4) |
3193 BIT(IEEE80211_STYPE_PROBE_RESP
>> 4),
3194 .rx
= BIT(IEEE80211_STYPE_ACTION
>> 4) |
3195 BIT(IEEE80211_STYPE_PROBE_REQ
>> 4)
3197 [NL80211_IFTYPE_P2P_GO
] = {
3198 .tx
= BIT(IEEE80211_STYPE_ACTION
>> 4) |
3199 BIT(IEEE80211_STYPE_PROBE_RESP
>> 4),
3200 .rx
= BIT(IEEE80211_STYPE_ACTION
>> 4) |
3201 BIT(IEEE80211_STYPE_PROBE_REQ
>> 4)
3205 static struct cfg80211_ops ath6kl_cfg80211_ops
= {
3206 .add_virtual_intf
= ath6kl_cfg80211_add_iface
,
3207 .del_virtual_intf
= ath6kl_cfg80211_del_iface
,
3208 .change_virtual_intf
= ath6kl_cfg80211_change_iface
,
3209 .scan
= ath6kl_cfg80211_scan
,
3210 .connect
= ath6kl_cfg80211_connect
,
3211 .disconnect
= ath6kl_cfg80211_disconnect
,
3212 .add_key
= ath6kl_cfg80211_add_key
,
3213 .get_key
= ath6kl_cfg80211_get_key
,
3214 .del_key
= ath6kl_cfg80211_del_key
,
3215 .set_default_key
= ath6kl_cfg80211_set_default_key
,
3216 .set_wiphy_params
= ath6kl_cfg80211_set_wiphy_params
,
3217 .set_tx_power
= ath6kl_cfg80211_set_txpower
,
3218 .get_tx_power
= ath6kl_cfg80211_get_txpower
,
3219 .set_power_mgmt
= ath6kl_cfg80211_set_power_mgmt
,
3220 .join_ibss
= ath6kl_cfg80211_join_ibss
,
3221 .leave_ibss
= ath6kl_cfg80211_leave_ibss
,
3222 .get_station
= ath6kl_get_station
,
3223 .set_pmksa
= ath6kl_set_pmksa
,
3224 .del_pmksa
= ath6kl_del_pmksa
,
3225 .flush_pmksa
= ath6kl_flush_pmksa
,
3226 CFG80211_TESTMODE_CMD(ath6kl_tm_cmd
)
3228 .suspend
= __ath6kl_cfg80211_suspend
,
3229 .resume
= __ath6kl_cfg80211_resume
,
3231 .set_channel
= ath6kl_set_channel
,
3232 .start_ap
= ath6kl_start_ap
,
3233 .change_beacon
= ath6kl_change_beacon
,
3234 .stop_ap
= ath6kl_stop_ap
,
3235 .del_station
= ath6kl_del_station
,
3236 .change_station
= ath6kl_change_station
,
3237 .remain_on_channel
= ath6kl_remain_on_channel
,
3238 .cancel_remain_on_channel
= ath6kl_cancel_remain_on_channel
,
3239 .mgmt_tx
= ath6kl_mgmt_tx
,
3240 .mgmt_frame_register
= ath6kl_mgmt_frame_register
,
3241 .sched_scan_start
= ath6kl_cfg80211_sscan_start
,
3242 .sched_scan_stop
= ath6kl_cfg80211_sscan_stop
,
3245 void ath6kl_cfg80211_stop(struct ath6kl_vif
*vif
)
3247 ath6kl_cfg80211_sscan_disable(vif
);
3249 switch (vif
->sme_state
) {
3250 case SME_DISCONNECTED
:
3252 case SME_CONNECTING
:
3253 cfg80211_connect_result(vif
->ndev
, vif
->bssid
, NULL
, 0,
3255 WLAN_STATUS_UNSPECIFIED_FAILURE
,
3259 cfg80211_disconnected(vif
->ndev
, 0, NULL
, 0, GFP_KERNEL
);
3263 if (test_bit(CONNECTED
, &vif
->flags
) ||
3264 test_bit(CONNECT_PEND
, &vif
->flags
))
3265 ath6kl_wmi_disconnect_cmd(vif
->ar
->wmi
, vif
->fw_vif_idx
);
3267 vif
->sme_state
= SME_DISCONNECTED
;
3268 clear_bit(CONNECTED
, &vif
->flags
);
3269 clear_bit(CONNECT_PEND
, &vif
->flags
);
3271 /* disable scanning */
3272 if (ath6kl_wmi_scanparams_cmd(vif
->ar
->wmi
, vif
->fw_vif_idx
, 0xFFFF,
3273 0, 0, 0, 0, 0, 0, 0, 0, 0) != 0)
3274 ath6kl_warn("failed to disable scan during stop\n");
3276 ath6kl_cfg80211_scan_complete_event(vif
, true);
3279 void ath6kl_cfg80211_stop_all(struct ath6kl
*ar
)
3281 struct ath6kl_vif
*vif
;
3283 vif
= ath6kl_vif_first(ar
);
3285 /* save the current power mode before enabling power save */
3286 ar
->wmi
->saved_pwr_mode
= ar
->wmi
->pwr_mode
;
3288 if (ath6kl_wmi_powermode_cmd(ar
->wmi
, 0, REC_POWER
) != 0)
3289 ath6kl_warn("ath6kl_deep_sleep_enable: "
3290 "wmi_powermode_cmd failed\n");
3295 * FIXME: we should take ar->list_lock to protect changes in the
3296 * vif_list, but that's not trivial to do as ath6kl_cfg80211_stop()
3299 list_for_each_entry(vif
, &ar
->vif_list
, list
)
3300 ath6kl_cfg80211_stop(vif
);
3303 static int ath6kl_cfg80211_vif_init(struct ath6kl_vif
*vif
)
3305 vif
->aggr_cntxt
= aggr_init(vif
);
3306 if (!vif
->aggr_cntxt
) {
3307 ath6kl_err("failed to initialize aggr\n");
3311 setup_timer(&vif
->disconnect_timer
, disconnect_timer_handler
,
3312 (unsigned long) vif
->ndev
);
3313 setup_timer(&vif
->sched_scan_timer
, ath6kl_wmi_sscan_timer
,
3314 (unsigned long) vif
);
3316 set_bit(WMM_ENABLED
, &vif
->flags
);
3317 spin_lock_init(&vif
->if_lock
);
3319 INIT_LIST_HEAD(&vif
->mc_filter
);
3324 void ath6kl_cfg80211_vif_cleanup(struct ath6kl_vif
*vif
)
3326 struct ath6kl
*ar
= vif
->ar
;
3327 struct ath6kl_mc_filter
*mc_filter
, *tmp
;
3329 aggr_module_destroy(vif
->aggr_cntxt
);
3331 ar
->avail_idx_map
|= BIT(vif
->fw_vif_idx
);
3333 if (vif
->nw_type
== ADHOC_NETWORK
)
3334 ar
->ibss_if_active
= false;
3336 list_for_each_entry_safe(mc_filter
, tmp
, &vif
->mc_filter
, list
) {
3337 list_del(&mc_filter
->list
);
3341 unregister_netdevice(vif
->ndev
);
3346 struct net_device
*ath6kl_interface_add(struct ath6kl
*ar
, char *name
,
3347 enum nl80211_iftype type
, u8 fw_vif_idx
,
3350 struct net_device
*ndev
;
3351 struct ath6kl_vif
*vif
;
3353 ndev
= alloc_netdev(sizeof(*vif
), name
, ether_setup
);
3357 vif
= netdev_priv(ndev
);
3358 ndev
->ieee80211_ptr
= &vif
->wdev
;
3359 vif
->wdev
.wiphy
= ar
->wiphy
;
3362 SET_NETDEV_DEV(ndev
, wiphy_dev(vif
->wdev
.wiphy
));
3363 vif
->wdev
.netdev
= ndev
;
3364 vif
->wdev
.iftype
= type
;
3365 vif
->fw_vif_idx
= fw_vif_idx
;
3366 vif
->nw_type
= nw_type
;
3367 vif
->next_mode
= nw_type
;
3368 vif
->listen_intvl_t
= ATH6KL_DEFAULT_LISTEN_INTVAL
;
3369 vif
->bmiss_time_t
= ATH6KL_DEFAULT_BMISS_TIME
;
3370 vif
->htcap
.ht_enable
= true;
3372 memcpy(ndev
->dev_addr
, ar
->mac_addr
, ETH_ALEN
);
3373 if (fw_vif_idx
!= 0)
3374 ndev
->dev_addr
[0] = (ndev
->dev_addr
[0] ^ (1 << fw_vif_idx
)) |
3379 ath6kl_init_control_info(vif
);
3381 if (ath6kl_cfg80211_vif_init(vif
))
3384 if (register_netdevice(ndev
))
3387 ar
->avail_idx_map
&= ~BIT(fw_vif_idx
);
3388 vif
->sme_state
= SME_DISCONNECTED
;
3389 set_bit(WLAN_ENABLED
, &vif
->flags
);
3390 ar
->wlan_pwr_state
= WLAN_POWER_STATE_ON
;
3391 set_bit(NETDEV_REGISTERED
, &vif
->flags
);
3393 if (type
== NL80211_IFTYPE_ADHOC
)
3394 ar
->ibss_if_active
= true;
3396 spin_lock_bh(&ar
->list_lock
);
3397 list_add_tail(&vif
->list
, &ar
->vif_list
);
3398 spin_unlock_bh(&ar
->list_lock
);
3403 aggr_module_destroy(vif
->aggr_cntxt
);
3408 int ath6kl_cfg80211_init(struct ath6kl
*ar
)
3410 struct wiphy
*wiphy
= ar
->wiphy
;
3413 wiphy
->mgmt_stypes
= ath6kl_mgmt_stypes
;
3415 wiphy
->max_remain_on_channel_duration
= 5000;
3417 /* set device pointer for wiphy */
3418 set_wiphy_dev(wiphy
, ar
->dev
);
3420 wiphy
->interface_modes
= BIT(NL80211_IFTYPE_STATION
) |
3421 BIT(NL80211_IFTYPE_ADHOC
) |
3422 BIT(NL80211_IFTYPE_AP
);
3424 wiphy
->interface_modes
|= BIT(NL80211_IFTYPE_P2P_GO
) |
3425 BIT(NL80211_IFTYPE_P2P_CLIENT
);
3428 /* max num of ssids that can be probed during scanning */
3429 wiphy
->max_scan_ssids
= MAX_PROBED_SSID_INDEX
;
3430 wiphy
->max_scan_ie_len
= 1000; /* FIX: what is correct limit? */
3431 wiphy
->bands
[IEEE80211_BAND_2GHZ
] = &ath6kl_band_2ghz
;
3432 wiphy
->bands
[IEEE80211_BAND_5GHZ
] = &ath6kl_band_5ghz
;
3433 wiphy
->signal_type
= CFG80211_SIGNAL_TYPE_MBM
;
3435 wiphy
->cipher_suites
= cipher_suites
;
3436 wiphy
->n_cipher_suites
= ARRAY_SIZE(cipher_suites
);
3438 wiphy
->wowlan
.flags
= WIPHY_WOWLAN_MAGIC_PKT
|
3439 WIPHY_WOWLAN_DISCONNECT
|
3440 WIPHY_WOWLAN_GTK_REKEY_FAILURE
|
3441 WIPHY_WOWLAN_SUPPORTS_GTK_REKEY
|
3442 WIPHY_WOWLAN_EAP_IDENTITY_REQ
|
3443 WIPHY_WOWLAN_4WAY_HANDSHAKE
;
3444 wiphy
->wowlan
.n_patterns
= WOW_MAX_FILTERS_PER_LIST
;
3445 wiphy
->wowlan
.pattern_min_len
= 1;
3446 wiphy
->wowlan
.pattern_max_len
= WOW_PATTERN_SIZE
;
3448 wiphy
->max_sched_scan_ssids
= 10;
3450 ar
->wiphy
->flags
|= WIPHY_FLAG_SUPPORTS_FW_ROAM
|
3451 WIPHY_FLAG_HAVE_AP_SME
|
3452 WIPHY_FLAG_HAS_REMAIN_ON_CHANNEL
|
3453 WIPHY_FLAG_AP_PROBE_RESP_OFFLOAD
;
3455 if (test_bit(ATH6KL_FW_CAPABILITY_SCHED_SCAN
, ar
->fw_capabilities
))
3456 ar
->wiphy
->flags
|= WIPHY_FLAG_SUPPORTS_SCHED_SCAN
;
3458 if (test_bit(ATH6KL_FW_CAPABILITY_INACTIVITY_TIMEOUT
,
3459 ar
->fw_capabilities
))
3460 ar
->wiphy
->features
= NL80211_FEATURE_INACTIVITY_TIMER
;
3462 ar
->wiphy
->probe_resp_offload
=
3463 NL80211_PROBE_RESP_OFFLOAD_SUPPORT_WPS
|
3464 NL80211_PROBE_RESP_OFFLOAD_SUPPORT_WPS2
|
3465 NL80211_PROBE_RESP_OFFLOAD_SUPPORT_P2P
|
3466 NL80211_PROBE_RESP_OFFLOAD_SUPPORT_80211U
;
3468 ret
= wiphy_register(wiphy
);
3470 ath6kl_err("couldn't register wiphy device\n");
3474 ar
->wiphy_registered
= true;
3479 void ath6kl_cfg80211_cleanup(struct ath6kl
*ar
)
3481 wiphy_unregister(ar
->wiphy
);
3483 ar
->wiphy_registered
= false;
3486 struct ath6kl
*ath6kl_cfg80211_create(void)
3489 struct wiphy
*wiphy
;
3491 /* create a new wiphy for use with cfg80211 */
3492 wiphy
= wiphy_new(&ath6kl_cfg80211_ops
, sizeof(struct ath6kl
));
3495 ath6kl_err("couldn't allocate wiphy device\n");
3499 ar
= wiphy_priv(wiphy
);
3505 /* Note: ar variable must not be accessed after calling this! */
3506 void ath6kl_cfg80211_destroy(struct ath6kl
*ar
)
3510 for (i
= 0; i
< AP_MAX_NUM_STA
; i
++)
3511 kfree(ar
->sta_list
[i
].aggr_conn
);
3513 wiphy_free(ar
->wiphy
);