7c3a58f89a6aaec48f0b15b4f828926293e63aba
[deliverable/linux.git] / drivers / staging / rtl8723au / os_dep / ioctl_cfg80211.c
1 /******************************************************************************
2 *
3 * Copyright(c) 2007 - 2012 Realtek Corporation. All rights reserved.
4 *
5 * This program is free software; you can redistribute it and/or modify it
6 * under the terms of version 2 of the GNU General Public License as
7 * published by the Free Software Foundation.
8 *
9 * This program is distributed in the hope that it will be useful, but WITHOUT
10 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
11 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
12 * more details.
13 *
14 ******************************************************************************/
15 #define _IOCTL_CFG80211_C_
16
17 #include <osdep_service.h>
18 #include <drv_types.h>
19 #include <xmit_osdep.h>
20
21 #include "ioctl_cfg80211.h"
22
23 #define RTW_MAX_MGMT_TX_CNT 8
24
25 #define RTW_MAX_REMAIN_ON_CHANNEL_DURATION 65535 /* ms */
26 #define RTW_MAX_NUM_PMKIDS 4
27
28 static const u32 rtw_cipher_suites[] = {
29 WLAN_CIPHER_SUITE_WEP40,
30 WLAN_CIPHER_SUITE_WEP104,
31 WLAN_CIPHER_SUITE_TKIP,
32 WLAN_CIPHER_SUITE_CCMP,
33 };
34
35 #define RATETAB_ENT(_rate, _rateid, _flags) { \
36 .bitrate = (_rate), \
37 .hw_value = (_rateid), \
38 .flags = (_flags), \
39 }
40
41 #define CHAN2G(_channel, _freq, _flags) { \
42 .band = IEEE80211_BAND_2GHZ, \
43 .center_freq = (_freq), \
44 .hw_value = (_channel), \
45 .flags = (_flags), \
46 .max_antenna_gain = 0, \
47 .max_power = 30, \
48 }
49
50 #define CHAN5G(_channel, _flags) { \
51 .band = IEEE80211_BAND_5GHZ, \
52 .center_freq = 5000 + (5 * (_channel)), \
53 .hw_value = (_channel), \
54 .flags = (_flags), \
55 .max_antenna_gain = 0, \
56 .max_power = 30, \
57 }
58
59 static struct ieee80211_rate rtw_rates[] = {
60 RATETAB_ENT(10, 0x1, 0),
61 RATETAB_ENT(20, 0x2, 0),
62 RATETAB_ENT(55, 0x4, 0),
63 RATETAB_ENT(110, 0x8, 0),
64 RATETAB_ENT(60, 0x10, 0),
65 RATETAB_ENT(90, 0x20, 0),
66 RATETAB_ENT(120, 0x40, 0),
67 RATETAB_ENT(180, 0x80, 0),
68 RATETAB_ENT(240, 0x100, 0),
69 RATETAB_ENT(360, 0x200, 0),
70 RATETAB_ENT(480, 0x400, 0),
71 RATETAB_ENT(540, 0x800, 0),
72 };
73
74 #define rtw_a_rates (rtw_rates + 4)
75 #define RTW_A_RATES_NUM 8
76 #define rtw_g_rates (rtw_rates + 0)
77 #define RTW_G_RATES_NUM 12
78
79 #define RTW_2G_CHANNELS_NUM 14
80 #define RTW_5G_CHANNELS_NUM 37
81
82 static struct ieee80211_channel rtw_2ghz_channels[] = {
83 CHAN2G(1, 2412, 0),
84 CHAN2G(2, 2417, 0),
85 CHAN2G(3, 2422, 0),
86 CHAN2G(4, 2427, 0),
87 CHAN2G(5, 2432, 0),
88 CHAN2G(6, 2437, 0),
89 CHAN2G(7, 2442, 0),
90 CHAN2G(8, 2447, 0),
91 CHAN2G(9, 2452, 0),
92 CHAN2G(10, 2457, 0),
93 CHAN2G(11, 2462, 0),
94 CHAN2G(12, 2467, 0),
95 CHAN2G(13, 2472, 0),
96 CHAN2G(14, 2484, 0),
97 };
98
99 static struct ieee80211_channel rtw_5ghz_a_channels[] = {
100 CHAN5G(34, 0), CHAN5G(36, 0),
101 CHAN5G(38, 0), CHAN5G(40, 0),
102 CHAN5G(42, 0), CHAN5G(44, 0),
103 CHAN5G(46, 0), CHAN5G(48, 0),
104 CHAN5G(52, 0), CHAN5G(56, 0),
105 CHAN5G(60, 0), CHAN5G(64, 0),
106 CHAN5G(100, 0), CHAN5G(104, 0),
107 CHAN5G(108, 0), CHAN5G(112, 0),
108 CHAN5G(116, 0), CHAN5G(120, 0),
109 CHAN5G(124, 0), CHAN5G(128, 0),
110 CHAN5G(132, 0), CHAN5G(136, 0),
111 CHAN5G(140, 0), CHAN5G(149, 0),
112 CHAN5G(153, 0), CHAN5G(157, 0),
113 CHAN5G(161, 0), CHAN5G(165, 0),
114 CHAN5G(184, 0), CHAN5G(188, 0),
115 CHAN5G(192, 0), CHAN5G(196, 0),
116 CHAN5G(200, 0), CHAN5G(204, 0),
117 CHAN5G(208, 0), CHAN5G(212, 0),
118 CHAN5G(216, 0),
119 };
120
121 static void rtw_2g_channels_init(struct ieee80211_channel *channels)
122 {
123 memcpy((void *)channels, (void *)rtw_2ghz_channels,
124 sizeof(struct ieee80211_channel) * RTW_2G_CHANNELS_NUM);
125 }
126
127 static void rtw_5g_channels_init(struct ieee80211_channel *channels)
128 {
129 memcpy((void *)channels, (void *)rtw_5ghz_a_channels,
130 sizeof(struct ieee80211_channel) * RTW_5G_CHANNELS_NUM);
131 }
132
133 static void rtw_2g_rates_init(struct ieee80211_rate *rates)
134 {
135 memcpy(rates, rtw_g_rates,
136 sizeof(struct ieee80211_rate) * RTW_G_RATES_NUM);
137 }
138
139 static void rtw_5g_rates_init(struct ieee80211_rate *rates)
140 {
141 memcpy(rates, rtw_a_rates,
142 sizeof(struct ieee80211_rate) * RTW_A_RATES_NUM);
143 }
144
145 static struct ieee80211_supported_band *
146 rtw_spt_band_alloc(enum ieee80211_band band)
147 {
148 struct ieee80211_supported_band *spt_band = NULL;
149 int n_channels, n_bitrates;
150
151 if (band == IEEE80211_BAND_2GHZ) {
152 n_channels = RTW_2G_CHANNELS_NUM;
153 n_bitrates = RTW_G_RATES_NUM;
154 } else if (band == IEEE80211_BAND_5GHZ) {
155 n_channels = RTW_5G_CHANNELS_NUM;
156 n_bitrates = RTW_A_RATES_NUM;
157 } else {
158 goto exit;
159 }
160 spt_band = kzalloc(sizeof(struct ieee80211_supported_band) +
161 sizeof(struct ieee80211_channel) * n_channels +
162 sizeof(struct ieee80211_rate) * n_bitrates,
163 GFP_KERNEL);
164 if (!spt_band)
165 goto exit;
166
167 spt_band->channels =
168 (struct ieee80211_channel *)(((u8 *) spt_band) +
169 sizeof(struct
170 ieee80211_supported_band));
171 spt_band->bitrates =
172 (struct ieee80211_rate *)(((u8 *) spt_band->channels) +
173 sizeof(struct ieee80211_channel) *
174 n_channels);
175 spt_band->band = band;
176 spt_band->n_channels = n_channels;
177 spt_band->n_bitrates = n_bitrates;
178
179 if (band == IEEE80211_BAND_2GHZ) {
180 rtw_2g_channels_init(spt_band->channels);
181 rtw_2g_rates_init(spt_band->bitrates);
182 } else if (band == IEEE80211_BAND_5GHZ) {
183 rtw_5g_channels_init(spt_band->channels);
184 rtw_5g_rates_init(spt_band->bitrates);
185 }
186
187 /* spt_band.ht_cap */
188
189 exit:
190 return spt_band;
191 }
192
193 static const struct ieee80211_txrx_stypes
194 rtw_cfg80211_default_mgmt_stypes[NUM_NL80211_IFTYPES] = {
195 [NL80211_IFTYPE_ADHOC] = {
196 .tx = 0xffff,
197 .rx = BIT(IEEE80211_STYPE_ACTION >> 4)
198 },
199 [NL80211_IFTYPE_STATION] = {
200 .tx = 0xffff,
201 .rx = BIT(IEEE80211_STYPE_ACTION >> 4) |
202 BIT(IEEE80211_STYPE_PROBE_REQ >> 4)
203 },
204 [NL80211_IFTYPE_AP] = {
205 .tx = 0xffff,
206 .rx = BIT(IEEE80211_STYPE_ASSOC_REQ >> 4) |
207 BIT(IEEE80211_STYPE_REASSOC_REQ >> 4) |
208 BIT(IEEE80211_STYPE_PROBE_REQ >> 4) |
209 BIT(IEEE80211_STYPE_DISASSOC >> 4) |
210 BIT(IEEE80211_STYPE_AUTH >> 4) |
211 BIT(IEEE80211_STYPE_DEAUTH >> 4) |
212 BIT(IEEE80211_STYPE_ACTION >> 4)
213 },
214 [NL80211_IFTYPE_AP_VLAN] = {
215 /* copy AP */
216 .tx = 0xffff,
217 .rx = BIT(IEEE80211_STYPE_ASSOC_REQ >> 4) |
218 BIT(IEEE80211_STYPE_REASSOC_REQ >> 4) |
219 BIT(IEEE80211_STYPE_PROBE_REQ >> 4) |
220 BIT(IEEE80211_STYPE_DISASSOC >> 4) |
221 BIT(IEEE80211_STYPE_AUTH >> 4) |
222 BIT(IEEE80211_STYPE_DEAUTH >> 4) |
223 BIT(IEEE80211_STYPE_ACTION >> 4)
224 },
225 [NL80211_IFTYPE_P2P_CLIENT] = {
226 .tx = 0xffff,
227 .rx = BIT(IEEE80211_STYPE_ACTION >> 4) |
228 BIT(IEEE80211_STYPE_PROBE_REQ >> 4)
229 },
230 [NL80211_IFTYPE_P2P_GO] = {
231 .tx = 0xffff,
232 .rx = BIT(IEEE80211_STYPE_ASSOC_REQ >> 4) |
233 BIT(IEEE80211_STYPE_REASSOC_REQ >> 4) |
234 BIT(IEEE80211_STYPE_PROBE_REQ >> 4) |
235 BIT(IEEE80211_STYPE_DISASSOC >> 4) |
236 BIT(IEEE80211_STYPE_AUTH >> 4) |
237 BIT(IEEE80211_STYPE_DEAUTH >> 4) |
238 BIT(IEEE80211_STYPE_ACTION >> 4)
239 },
240 };
241
242 static int rtw_cfg80211_inform_bss(struct rtw_adapter *padapter,
243 struct wlan_network *pnetwork)
244 {
245 int ret = 0;
246 struct ieee80211_channel *notify_channel;
247 struct cfg80211_bss *bss;
248 u16 channel;
249 u32 freq;
250 u8 *notify_ie;
251 size_t notify_ielen;
252 s32 notify_signal;
253 struct wireless_dev *wdev = padapter->rtw_wdev;
254 struct wiphy *wiphy = wdev->wiphy;
255 struct mlme_priv *pmlmepriv = &padapter->mlmepriv;
256
257 channel = pnetwork->network.DSConfig;
258 if (channel <= RTW_CH_MAX_2G_CHANNEL)
259 freq = ieee80211_channel_to_frequency(channel,
260 IEEE80211_BAND_2GHZ);
261 else
262 freq = ieee80211_channel_to_frequency(channel,
263 IEEE80211_BAND_5GHZ);
264
265 notify_channel = ieee80211_get_channel(wiphy, freq);
266
267 notify_ie = pnetwork->network.IEs;
268 notify_ielen = pnetwork->network.IELength;
269
270 /* We've set wiphy's signal_type as CFG80211_SIGNAL_TYPE_MBM:
271 * signal strength in mBm (100*dBm)
272 */
273 if (check_fwstate(pmlmepriv, _FW_LINKED) &&
274 is_same_network23a(&pmlmepriv->cur_network.network,
275 &pnetwork->network)) {
276 notify_signal = 100 * translate_percentage_to_dbm(padapter->recvpriv.signal_strength); /* dbm */
277 } else {
278 notify_signal = 100 * translate_percentage_to_dbm(pnetwork->network.PhyInfo.SignalStrength); /* dbm */
279 }
280
281 bss = cfg80211_inform_bss(wiphy, notify_channel,
282 pnetwork->network.MacAddress,
283 pnetwork->network.tsf,
284 pnetwork->network.capability,
285 pnetwork->network.beacon_interval,
286 notify_ie, notify_ielen,
287 notify_signal, GFP_ATOMIC);
288
289 if (unlikely(!bss)) {
290 DBG_8723A("rtw_cfg80211_inform_bss error\n");
291 return -EINVAL;
292 }
293
294 cfg80211_put_bss(wiphy, bss);
295
296 return ret;
297 }
298
299 void rtw_cfg80211_indicate_connect(struct rtw_adapter *padapter)
300 {
301 struct mlme_priv *pmlmepriv = &padapter->mlmepriv;
302 struct wlan_network *cur_network = &pmlmepriv->cur_network;
303 struct wireless_dev *pwdev = padapter->rtw_wdev;
304
305 DBG_8723A("%s(padapter =%p)\n", __func__, padapter);
306
307 if (pwdev->iftype != NL80211_IFTYPE_STATION &&
308 pwdev->iftype != NL80211_IFTYPE_P2P_CLIENT)
309 return;
310
311 if (check_fwstate(pmlmepriv, WIFI_AP_STATE))
312 return;
313
314 if (padapter->mlmepriv.to_roaming > 0) {
315 struct wiphy *wiphy = pwdev->wiphy;
316 struct ieee80211_channel *notify_channel;
317 u32 freq;
318 u16 channel = cur_network->network.DSConfig;
319
320 if (channel <= RTW_CH_MAX_2G_CHANNEL)
321 freq =
322 ieee80211_channel_to_frequency(channel,
323 IEEE80211_BAND_2GHZ);
324 else
325 freq =
326 ieee80211_channel_to_frequency(channel,
327 IEEE80211_BAND_5GHZ);
328
329 notify_channel = ieee80211_get_channel(wiphy, freq);
330
331 DBG_8723A("%s call cfg80211_roamed\n", __func__);
332 cfg80211_roamed(padapter->pnetdev, notify_channel,
333 cur_network->network.MacAddress,
334 pmlmepriv->assoc_req +
335 sizeof(struct ieee80211_hdr_3addr) + 2,
336 pmlmepriv->assoc_req_len -
337 sizeof(struct ieee80211_hdr_3addr) - 2,
338 pmlmepriv->assoc_rsp +
339 sizeof(struct ieee80211_hdr_3addr) + 6,
340 pmlmepriv->assoc_rsp_len -
341 sizeof(struct ieee80211_hdr_3addr) - 6,
342 GFP_ATOMIC);
343 } else {
344 cfg80211_connect_result(padapter->pnetdev,
345 cur_network->network.MacAddress,
346 pmlmepriv->assoc_req +
347 sizeof(struct ieee80211_hdr_3addr) + 2,
348 pmlmepriv->assoc_req_len -
349 sizeof(struct ieee80211_hdr_3addr) - 2,
350 pmlmepriv->assoc_rsp +
351 sizeof(struct ieee80211_hdr_3addr) + 6,
352 pmlmepriv->assoc_rsp_len -
353 sizeof(struct ieee80211_hdr_3addr) - 6,
354 WLAN_STATUS_SUCCESS, GFP_ATOMIC);
355 }
356 }
357
358 void rtw_cfg80211_indicate_disconnect(struct rtw_adapter *padapter)
359 {
360 struct mlme_priv *pmlmepriv = &padapter->mlmepriv;
361 struct wireless_dev *pwdev = padapter->rtw_wdev;
362
363 DBG_8723A("%s(padapter =%p)\n", __func__, padapter);
364
365 if (pwdev->iftype != NL80211_IFTYPE_STATION &&
366 pwdev->iftype != NL80211_IFTYPE_P2P_CLIENT)
367 return;
368
369 if (check_fwstate(pmlmepriv, WIFI_AP_STATE))
370 return;
371
372 if (!padapter->mlmepriv.not_indic_disco) {
373 if (check_fwstate(&padapter->mlmepriv, WIFI_UNDER_LINKING)) {
374 cfg80211_connect_result(padapter->pnetdev, NULL, NULL,
375 0, NULL, 0,
376 WLAN_STATUS_UNSPECIFIED_FAILURE,
377 GFP_ATOMIC);
378 } else {
379 cfg80211_disconnected(padapter->pnetdev, 0, NULL,
380 0, GFP_ATOMIC);
381 }
382 }
383 }
384
385 #ifdef CONFIG_8723AU_AP_MODE
386 static int set_pairwise_key(struct rtw_adapter *padapter, struct sta_info *psta)
387 {
388 struct cmd_obj *ph2c;
389 struct set_stakey_parm *psetstakey_para;
390 struct cmd_priv *pcmdpriv = &padapter->cmdpriv;
391 int res = _SUCCESS;
392
393 ph2c = kzalloc(sizeof(struct cmd_obj), GFP_KERNEL);
394 if (ph2c == NULL) {
395 res = _FAIL;
396 goto exit;
397 }
398
399 psetstakey_para = kzalloc(sizeof(struct set_stakey_parm), GFP_KERNEL);
400 if (psetstakey_para == NULL) {
401 kfree(ph2c);
402 res = _FAIL;
403 goto exit;
404 }
405
406 init_h2fwcmd_w_parm_no_rsp(ph2c, psetstakey_para, _SetStaKey_CMD_);
407
408 psetstakey_para->algorithm = psta->dot118021XPrivacy;
409
410 ether_addr_copy(psetstakey_para->addr, psta->hwaddr);
411
412 memcpy(psetstakey_para->key, &psta->dot118021x_UncstKey, 16);
413
414 res = rtw_enqueue_cmd23a(pcmdpriv, ph2c);
415
416 exit:
417 return res;
418 }
419
420 static int set_group_key(struct rtw_adapter *padapter, const u8 *key, u32 alg,
421 u8 keyid)
422 {
423 u8 keylen;
424 struct cmd_obj *pcmd;
425 struct setkey_parm *psetkeyparm;
426 struct cmd_priv *pcmdpriv = &padapter->cmdpriv;
427 int res = _SUCCESS;
428
429 DBG_8723A("%s\n", __func__);
430
431 if (keyid >= 4) {
432 res = _FAIL;
433 goto exit;
434 }
435
436 pcmd = kzalloc(sizeof(struct cmd_obj), GFP_KERNEL);
437 if (!pcmd) {
438 res = _FAIL;
439 goto exit;
440 }
441 psetkeyparm = kzalloc(sizeof(struct setkey_parm), GFP_KERNEL);
442 if (!psetkeyparm) {
443 kfree(pcmd);
444 res = _FAIL;
445 goto exit;
446 }
447
448 psetkeyparm->keyid = keyid;
449 if (is_wep_enc(alg))
450 padapter->mlmepriv.key_mask |= BIT(psetkeyparm->keyid);
451
452 psetkeyparm->algorithm = alg;
453
454 psetkeyparm->set_tx = 1;
455
456 switch (alg) {
457 case WLAN_CIPHER_SUITE_WEP40:
458 keylen = 5;
459 break;
460 case WLAN_CIPHER_SUITE_WEP104:
461 keylen = 13;
462 break;
463 case WLAN_CIPHER_SUITE_TKIP:
464 case WLAN_CIPHER_SUITE_CCMP:
465 default:
466 keylen = 16;
467 }
468
469 memcpy(&psetkeyparm->key[0], key, keylen);
470
471 pcmd->cmdcode = _SetKey_CMD_;
472 pcmd->parmbuf = (u8 *) psetkeyparm;
473 pcmd->cmdsz = (sizeof(struct setkey_parm));
474 pcmd->rsp = NULL;
475 pcmd->rspsz = 0;
476
477 res = rtw_enqueue_cmd23a(pcmdpriv, pcmd);
478
479 exit:
480 return res;
481 }
482
483 static int set_wep_key(struct rtw_adapter *padapter, const u8 *key, u16 keylen,
484 u8 keyid)
485 {
486 u32 alg;
487
488 switch (keylen) {
489 case 5:
490 alg = WLAN_CIPHER_SUITE_WEP40;
491 break;
492 case 13:
493 alg = WLAN_CIPHER_SUITE_WEP104;
494 break;
495 default:
496 alg = 0;
497 }
498
499 return set_group_key(padapter, key, alg, keyid);
500 }
501
502 static int rtw_cfg80211_ap_set_encryption(struct net_device *dev,
503 struct ieee_param *param,
504 u32 param_len,
505 struct key_params *keyparms)
506 {
507 int ret = 0;
508 int key_len;
509 u8 wep_key_idx;
510 struct sta_info *psta = NULL, *pbcmc_sta = NULL;
511 struct rtw_adapter *padapter = netdev_priv(dev);
512 struct security_priv *psecuritypriv = &padapter->securitypriv;
513 struct sta_priv *pstapriv = &padapter->stapriv;
514
515 DBG_8723A("%s\n", __func__);
516
517 param->u.crypt.err = 0;
518 param->u.crypt.alg[IEEE_CRYPT_ALG_NAME_LEN - 1] = '\0';
519
520 /* sizeof(struct ieee_param) = 64 bytes; */
521 /* if (param_len != (u32) ((u8 *) param->u.crypt.key -
522 (u8 *) param) + param->u.crypt.key_len) */
523 if (param_len != sizeof(struct ieee_param) + param->u.crypt.key_len) {
524 ret = -EINVAL;
525 goto exit;
526 }
527
528 if (is_broadcast_ether_addr(param->sta_addr)) {
529 if (param->u.crypt.idx >= WEP_KEYS) {
530 ret = -EINVAL;
531 goto exit;
532 }
533 switch (keyparms->cipher) {
534 case WLAN_CIPHER_SUITE_WEP40:
535 case WLAN_CIPHER_SUITE_WEP104:
536 case WLAN_CIPHER_SUITE_TKIP:
537 case WLAN_CIPHER_SUITE_CCMP:
538 break;
539 default:
540 ret = -EINVAL;
541 goto exit;
542 }
543
544 } else {
545 psta = rtw_get_stainfo23a(pstapriv, param->sta_addr);
546 if (!psta) {
547 /* ret = -EINVAL; */
548 DBG_8723A("rtw_set_encryption(), sta has already "
549 "been removed or never been added\n");
550 goto exit;
551 }
552 }
553
554 key_len = keyparms->key_len;
555
556 if (!psta && (keyparms->cipher == WLAN_CIPHER_SUITE_WEP40 ||
557 keyparms->cipher == WLAN_CIPHER_SUITE_WEP104)) {
558 DBG_8723A("r871x_set_encryption, crypt.alg = WEP\n");
559
560 wep_key_idx = param->u.crypt.idx;
561
562 DBG_8723A("r871x_set_encryption, wep_key_idx =%d, len =%d\n",
563 wep_key_idx, key_len);
564
565 if (wep_key_idx >= WEP_KEYS || key_len <= 0) {
566 ret = -EINVAL;
567 goto exit;
568 }
569
570 if (key_len > 0) {
571 key_len = key_len <= 5 ? 5 : 13;
572 }
573
574 if (psecuritypriv->bWepDefaultKeyIdxSet == 0) {
575 /* wep default key has not been set, so use
576 this key index as default key. */
577
578 psecuritypriv->ndisencryptstatus =
579 Ndis802_11Encryption1Enabled;
580 psecuritypriv->dot11PrivacyAlgrthm = keyparms->cipher;
581 psecuritypriv->dot118021XGrpPrivacy = keyparms->cipher;
582
583 psecuritypriv->dot11PrivacyKeyIndex = wep_key_idx;
584 }
585
586 memcpy(&psecuritypriv->wep_key[wep_key_idx].key,
587 keyparms->key, key_len);
588
589 psecuritypriv->wep_key[wep_key_idx].keylen = key_len;
590
591 set_wep_key(padapter, keyparms->key, key_len, wep_key_idx);
592
593 goto exit;
594 }
595
596 if (!psta) { /* group key */
597 if (param->u.crypt.set_tx == 0) { /* group key */
598 if (keyparms->cipher == WLAN_CIPHER_SUITE_WEP40 ||
599 keyparms->cipher == WLAN_CIPHER_SUITE_WEP104) {
600 DBG_8723A("%s, set group_key, WEP\n", __func__);
601
602 memcpy(psecuritypriv->
603 dot118021XGrpKey[param->u.crypt.idx].
604 skey, keyparms->key,
605 (key_len > 16 ? 16 : key_len));
606
607 psecuritypriv->dot118021XGrpPrivacy =
608 keyparms->cipher;
609 } else if (keyparms->cipher == WLAN_CIPHER_SUITE_TKIP) {
610 DBG_8723A("%s, set group_key, TKIP\n",
611 __func__);
612
613 psecuritypriv->dot118021XGrpPrivacy =
614 WLAN_CIPHER_SUITE_TKIP;
615
616 memcpy(psecuritypriv->
617 dot118021XGrpKey[param->u.crypt.idx].
618 skey, param->u.crypt.key,
619 (key_len > 16 ? 16 : key_len));
620
621 /* DEBUG_ERR("set key length :param->u.crypt.key_len =%d\n", param->u.crypt.key_len); */
622 /* set mic key */
623 memcpy(psecuritypriv->
624 dot118021XGrptxmickey[param->u.crypt.
625 idx].skey,
626 &param->u.crypt.key[16], 8);
627 memcpy(psecuritypriv->
628 dot118021XGrprxmickey[param->u.crypt.
629 idx].skey,
630 &param->u.crypt.key[24], 8);
631
632 psecuritypriv->busetkipkey = 1;
633
634 } else if (keyparms->cipher == WLAN_CIPHER_SUITE_CCMP) {
635 DBG_8723A("%s, set group_key, CCMP\n",
636 __func__);
637
638 psecuritypriv->dot118021XGrpPrivacy =
639 WLAN_CIPHER_SUITE_CCMP;
640
641 memcpy(psecuritypriv->
642 dot118021XGrpKey[param->u.crypt.idx].
643 skey, param->u.crypt.key,
644 (key_len > 16 ? 16 : key_len));
645 } else {
646 DBG_8723A("%s, set group_key, none\n",
647 __func__);
648
649 psecuritypriv->dot118021XGrpPrivacy =
650 0;
651 }
652
653 psecuritypriv->dot118021XGrpKeyid = param->u.crypt.idx;
654
655 psecuritypriv->binstallGrpkey = 1;
656
657 psecuritypriv->dot11PrivacyAlgrthm =
658 psecuritypriv->dot118021XGrpPrivacy;
659
660 set_group_key(padapter, param->u.crypt.key,
661 psecuritypriv->dot118021XGrpPrivacy,
662 param->u.crypt.idx);
663
664 pbcmc_sta = rtw_get_bcmc_stainfo23a(padapter);
665 if (pbcmc_sta) {
666 pbcmc_sta->ieee8021x_blocked = false;
667 /* rx will use bmc_sta's dot118021XPrivacy */
668 pbcmc_sta->dot118021XPrivacy =
669 psecuritypriv->dot118021XGrpPrivacy;
670
671 }
672
673 }
674
675 goto exit;
676 }
677
678 if (psecuritypriv->dot11AuthAlgrthm == dot11AuthAlgrthm_8021X && psta) {
679 /* psk/802_1x */
680 if (param->u.crypt.set_tx == 1) {
681 /* pairwise key */
682 memcpy(psta->dot118021x_UncstKey.skey,
683 param->u.crypt.key,
684 (key_len > 16 ? 16 : key_len));
685
686 if (keyparms->cipher == WLAN_CIPHER_SUITE_WEP40 ||
687 keyparms->cipher == WLAN_CIPHER_SUITE_WEP104) {
688 DBG_8723A("%s, set pairwise key, WEP\n",
689 __func__);
690
691 psecuritypriv->dot118021XGrpPrivacy =
692 keyparms->cipher;
693 } else if (keyparms->cipher == WLAN_CIPHER_SUITE_TKIP) {
694 DBG_8723A("%s, set pairwise key, TKIP\n",
695 __func__);
696
697 psta->dot118021XPrivacy =
698 WLAN_CIPHER_SUITE_TKIP;
699
700 /* DEBUG_ERR("set key length :param->u.crypt.key_len =%d\n", param->u.crypt.key_len); */
701 /* set mic key */
702 memcpy(psta->dot11tkiptxmickey.skey,
703 &param->u.crypt.key[16], 8);
704 memcpy(psta->dot11tkiprxmickey.skey,
705 &param->u.crypt.key[24], 8);
706
707 psecuritypriv->busetkipkey = 1;
708
709 } else if (keyparms->cipher == WLAN_CIPHER_SUITE_CCMP) {
710 DBG_8723A("%s, set pairwise key, CCMP\n",
711 __func__);
712
713 psta->dot118021XPrivacy =
714 WLAN_CIPHER_SUITE_CCMP;
715 } else {
716 DBG_8723A("%s, set pairwise key, none\n",
717 __func__);
718
719 psta->dot118021XPrivacy = 0;
720 }
721
722 set_pairwise_key(padapter, psta);
723
724 psta->ieee8021x_blocked = false;
725
726 psta->bpairwise_key_installed = true;
727 } else { /* group key??? */
728 if (keyparms->cipher == WLAN_CIPHER_SUITE_WEP40 ||
729 keyparms->cipher == WLAN_CIPHER_SUITE_WEP104) {
730 memcpy(psecuritypriv->
731 dot118021XGrpKey[param->u.crypt.
732 idx].skey,
733 param->u.crypt.key,
734 (key_len > 16 ? 16 : key_len));
735
736 psecuritypriv->dot118021XGrpPrivacy =
737 keyparms->cipher;
738 } else if (keyparms->cipher == WLAN_CIPHER_SUITE_TKIP) {
739 psecuritypriv->dot118021XGrpPrivacy =
740 WLAN_CIPHER_SUITE_TKIP;
741
742 memcpy(psecuritypriv->
743 dot118021XGrpKey[param->u.crypt.
744 idx].skey,
745 param->u.crypt.key,
746 (key_len > 16 ? 16 : key_len));
747
748 /* DEBUG_ERR("set key length :param->u"
749 ".crypt.key_len =%d\n",
750 param->u.crypt.key_len); */
751 /* set mic key */
752 memcpy(psecuritypriv->
753 dot118021XGrptxmickey[param->u.
754 crypt.idx].skey,
755 &param->u.crypt.key[16], 8);
756 memcpy(psecuritypriv->
757 dot118021XGrprxmickey[param->u.
758 crypt.idx].skey,
759 &param->u.crypt.key[24], 8);
760
761 psecuritypriv->busetkipkey = 1;
762
763 } else if (keyparms->cipher == WLAN_CIPHER_SUITE_CCMP) {
764 psecuritypriv->dot118021XGrpPrivacy =
765 WLAN_CIPHER_SUITE_CCMP;
766
767 memcpy(psecuritypriv->
768 dot118021XGrpKey[param->u.crypt.
769 idx].skey,
770 param->u.crypt.key,
771 (key_len > 16 ? 16 : key_len));
772 } else {
773 psecuritypriv->dot118021XGrpPrivacy = 0;
774 }
775
776 psecuritypriv->dot118021XGrpKeyid = param->u.crypt.idx;
777
778 psecuritypriv->binstallGrpkey = 1;
779
780 psecuritypriv->dot11PrivacyAlgrthm =
781 psecuritypriv->dot118021XGrpPrivacy;
782
783 set_group_key(padapter, param->u.crypt.key,
784 psecuritypriv->dot118021XGrpPrivacy,
785 param->u.crypt.idx);
786
787 pbcmc_sta = rtw_get_bcmc_stainfo23a(padapter);
788 if (pbcmc_sta) {
789 /* rx will use bmc_sta's
790 dot118021XPrivacy */
791 pbcmc_sta->ieee8021x_blocked = false;
792 pbcmc_sta->dot118021XPrivacy =
793 psecuritypriv->dot118021XGrpPrivacy;
794 }
795 }
796 }
797
798 exit:
799
800 return ret;
801 }
802 #endif
803
804 static int rtw_cfg80211_set_encryption(struct net_device *dev,
805 struct ieee_param *param, u32 param_len,
806 struct key_params *keyparms)
807 {
808 int ret = 0;
809 u32 wep_key_idx;
810 u16 wep_key_len;
811 struct rtw_adapter *padapter = netdev_priv(dev);
812 struct mlme_priv *pmlmepriv = &padapter->mlmepriv;
813 struct security_priv *psecuritypriv = &padapter->securitypriv;
814
815 DBG_8723A("%s\n", __func__);
816
817 param->u.crypt.err = 0;
818 param->u.crypt.alg[IEEE_CRYPT_ALG_NAME_LEN - 1] = '\0';
819
820 if (param_len <
821 (u32) ((u8 *) param->u.crypt.key - (u8 *) param) +
822 param->u.crypt.key_len) {
823 ret = -EINVAL;
824 goto exit;
825 }
826
827 if (is_broadcast_ether_addr(param->sta_addr)) {
828 if (param->u.crypt.idx >= WEP_KEYS) {
829 ret = -EINVAL;
830 goto exit;
831 }
832 } else {
833 ret = -EINVAL;
834 goto exit;
835 }
836
837 if (strcmp(param->u.crypt.alg, "WEP") == 0) {
838 RT_TRACE(_module_rtl871x_ioctl_os_c, _drv_err_,
839 ("wpa_set_encryption, crypt.alg = WEP\n"));
840 DBG_8723A("wpa_set_encryption, crypt.alg = WEP\n");
841
842 wep_key_idx = param->u.crypt.idx;
843 wep_key_len = param->u.crypt.key_len;
844
845 if ((wep_key_idx > WEP_KEYS) || (wep_key_len <= 0)) {
846 ret = -EINVAL;
847 goto exit;
848 }
849
850 if (psecuritypriv->bWepDefaultKeyIdxSet == 0) {
851 /* wep default key has not been set, so use this
852 key index as default key. */
853
854 wep_key_len = wep_key_len <= 5 ? 5 : 13;
855
856 psecuritypriv->ndisencryptstatus =
857 Ndis802_11Encryption1Enabled;
858 psecuritypriv->dot11PrivacyAlgrthm = WLAN_CIPHER_SUITE_WEP40;
859 psecuritypriv->dot118021XGrpPrivacy = WLAN_CIPHER_SUITE_WEP40;
860
861 if (wep_key_len == 13) {
862 psecuritypriv->dot11PrivacyAlgrthm = WLAN_CIPHER_SUITE_WEP104;
863 psecuritypriv->dot118021XGrpPrivacy = WLAN_CIPHER_SUITE_WEP104;
864 }
865
866 psecuritypriv->dot11PrivacyKeyIndex = wep_key_idx;
867 }
868
869 memcpy(&psecuritypriv->wep_key[wep_key_idx].key,
870 param->u.crypt.key, wep_key_len);
871
872 psecuritypriv->wep_key[wep_key_idx].keylen = wep_key_len;
873
874 rtw_set_key23a(padapter, psecuritypriv, wep_key_idx, 0);
875
876 goto exit;
877 }
878
879 if (padapter->securitypriv.dot11AuthAlgrthm ==
880 dot11AuthAlgrthm_8021X) { /* 802_1x */
881 struct sta_info *psta, *pbcmc_sta;
882 struct sta_priv *pstapriv = &padapter->stapriv;
883
884 if (check_fwstate(pmlmepriv,
885 WIFI_STATION_STATE | WIFI_MP_STATE)) {
886 /* sta mode */
887 psta = rtw_get_stainfo23a(pstapriv, get_bssid(pmlmepriv));
888 if (psta == NULL) {
889 DBG_8723A("%s, : Obtain Sta_info fail\n",
890 __func__);
891 } else {
892 /* Jeff: don't disable ieee8021x_blocked
893 while clearing key */
894 if (strcmp(param->u.crypt.alg, "none") != 0)
895 psta->ieee8021x_blocked = false;
896
897 if ((padapter->securitypriv.ndisencryptstatus ==
898 Ndis802_11Encryption2Enabled) ||
899 (padapter->securitypriv.ndisencryptstatus ==
900 Ndis802_11Encryption3Enabled)) {
901 psta->dot118021XPrivacy =
902 padapter->securitypriv.
903 dot11PrivacyAlgrthm;
904 }
905
906 if (param->u.crypt.set_tx == 1) {
907 /* pairwise key */
908 DBG_8723A("%s, : param->u.crypt.set_tx"
909 " == 1\n", __func__);
910
911 memcpy(psta->dot118021x_UncstKey.skey,
912 param->u.crypt.key,
913 (param->u.crypt.key_len >
914 16 ? 16 : param->u.crypt.
915 key_len));
916
917 if (strcmp(param->u.crypt.alg,
918 "TKIP") == 0) {
919 memcpy(psta->dot11tkiptxmickey.
920 skey,
921 &param->u.crypt.key[16],
922 8);
923 memcpy(psta->dot11tkiprxmickey.
924 skey,
925 &param->u.crypt.key[24],
926 8);
927
928 padapter->securitypriv.
929 busetkipkey = 0;
930 }
931 DBG_8723A(" ~~~~set sta key:unicastkey\n");
932
933 rtw_setstakey_cmd23a(padapter,
934 (unsigned char *)psta,
935 true);
936 } else { /* group key */
937 memcpy(padapter->securitypriv.
938 dot118021XGrpKey[param->u.crypt.
939 idx].skey,
940 param->u.crypt.key,
941 (param->u.crypt.key_len >
942 16 ? 16 : param->u.crypt.
943 key_len));
944 memcpy(padapter->securitypriv.
945 dot118021XGrptxmickey[param->u.
946 crypt.idx].
947 skey, &param->u.crypt.key[16],
948 8);
949 memcpy(padapter->securitypriv.
950 dot118021XGrprxmickey[param->u.
951 crypt.idx].
952 skey, &param->u.crypt.key[24],
953 8);
954 padapter->securitypriv.binstallGrpkey =
955 1;
956 /* DEBUG_ERR((" param->u.crypt.key_len"
957 "=%d\n", param->u.crypt.key_len)); */
958 DBG_8723A
959 (" ~~~~set sta key:groupkey\n");
960
961 padapter->securitypriv.
962 dot118021XGrpKeyid =
963 param->u.crypt.idx;
964
965 rtw_set_key23a(padapter,
966 &padapter->securitypriv,
967 param->u.crypt.idx, 1);
968 }
969 }
970
971 pbcmc_sta = rtw_get_bcmc_stainfo23a(padapter);
972 if (pbcmc_sta) {
973 /* Jeff: don't disable ieee8021x_blocked
974 while clearing key */
975 if (strcmp(param->u.crypt.alg, "none") != 0)
976 pbcmc_sta->ieee8021x_blocked = false;
977
978 if ((padapter->securitypriv.ndisencryptstatus ==
979 Ndis802_11Encryption2Enabled) ||
980 (padapter->securitypriv.ndisencryptstatus ==
981 Ndis802_11Encryption3Enabled)) {
982 pbcmc_sta->dot118021XPrivacy =
983 padapter->securitypriv.
984 dot11PrivacyAlgrthm;
985 }
986 }
987 } else if (check_fwstate(pmlmepriv, WIFI_ADHOC_STATE)) { /* adhoc mode */
988 }
989 }
990
991 exit:
992
993 DBG_8723A("%s, ret =%d\n", __func__, ret);
994
995
996
997 return ret;
998 }
999
1000 static int cfg80211_rtw_add_key(struct wiphy *wiphy, struct net_device *ndev,
1001 u8 key_index, bool pairwise,
1002 const u8 *mac_addr, struct key_params *params)
1003 {
1004 char *alg_name;
1005 u32 param_len;
1006 struct ieee_param *param;
1007 int ret = 0;
1008 struct wireless_dev *rtw_wdev = wiphy_to_wdev(wiphy);
1009 struct rtw_adapter *padapter = wiphy_to_adapter(wiphy);
1010 struct mlme_priv *pmlmepriv = &padapter->mlmepriv;
1011
1012 DBG_8723A("%s(%s): adding key for %pM\n", __func__, ndev->name,
1013 mac_addr);
1014 DBG_8723A("cipher = 0x%x\n", params->cipher);
1015 DBG_8723A("key_len = 0x%x\n", params->key_len);
1016 DBG_8723A("seq_len = 0x%x\n", params->seq_len);
1017 DBG_8723A("key_index =%d\n", key_index);
1018 DBG_8723A("pairwise =%d\n", pairwise);
1019
1020 param_len = sizeof(struct ieee_param) + params->key_len;
1021 param = kzalloc(param_len, GFP_KERNEL);
1022 if (!param)
1023 return -ENOMEM;
1024
1025 param->cmd = IEEE_CMD_SET_ENCRYPTION;
1026 eth_broadcast_addr(param->sta_addr);
1027
1028 switch (params->cipher) {
1029 case IW_AUTH_CIPHER_NONE:
1030 /* todo: remove key */
1031 /* remove = 1; */
1032 alg_name = "none";
1033 break;
1034 case WLAN_CIPHER_SUITE_WEP40:
1035 case WLAN_CIPHER_SUITE_WEP104:
1036 alg_name = "WEP";
1037 break;
1038 case WLAN_CIPHER_SUITE_TKIP:
1039 alg_name = "TKIP";
1040 break;
1041 case WLAN_CIPHER_SUITE_CCMP:
1042 alg_name = "CCMP";
1043 break;
1044
1045 default:
1046 ret = -ENOTSUPP;
1047 goto addkey_end;
1048 }
1049
1050 strncpy((char *)param->u.crypt.alg, alg_name, IEEE_CRYPT_ALG_NAME_LEN);
1051
1052 if (!mac_addr || is_broadcast_ether_addr(mac_addr)) {
1053 param->u.crypt.set_tx = 0; /* for wpa/wpa2 group key */
1054 } else {
1055 param->u.crypt.set_tx = 1; /* for wpa/wpa2 pairwise key */
1056 }
1057
1058 /* param->u.crypt.idx = key_index - 1; */
1059 param->u.crypt.idx = key_index;
1060
1061 if (params->seq_len && params->seq) {
1062 memcpy(param->u.crypt.seq, params->seq, params->seq_len);
1063 }
1064
1065 if (params->key_len && params->key) {
1066 param->u.crypt.key_len = params->key_len;
1067 memcpy(param->u.crypt.key, params->key, params->key_len);
1068 }
1069
1070 if (check_fwstate(pmlmepriv, WIFI_STATION_STATE)) {
1071 ret = rtw_cfg80211_set_encryption(ndev, param, param_len,
1072 params);
1073 } else if (check_fwstate(pmlmepriv, WIFI_AP_STATE)) {
1074 #ifdef CONFIG_8723AU_AP_MODE
1075 if (mac_addr)
1076 ether_addr_copy(param->sta_addr, mac_addr);
1077
1078 ret = rtw_cfg80211_ap_set_encryption(ndev, param, param_len,
1079 params);
1080 #endif
1081 } else {
1082 DBG_8723A("error! fw_state = 0x%x, iftype =%d\n",
1083 pmlmepriv->fw_state, rtw_wdev->iftype);
1084
1085 }
1086
1087 addkey_end:
1088 kfree(param);
1089
1090 return ret;
1091 }
1092
1093 static int
1094 cfg80211_rtw_get_key(struct wiphy *wiphy, struct net_device *ndev,
1095 u8 key_index, bool pairwise, const u8 *mac_addr,
1096 void *cookie,
1097 void (*callback) (void *cookie, struct key_params *))
1098 {
1099 DBG_8723A("%s(%s)\n", __func__, ndev->name);
1100 return 0;
1101 }
1102
1103 static int cfg80211_rtw_del_key(struct wiphy *wiphy, struct net_device *ndev,
1104 u8 key_index, bool pairwise,
1105 const u8 *mac_addr)
1106 {
1107 struct rtw_adapter *padapter = netdev_priv(ndev);
1108 struct security_priv *psecuritypriv = &padapter->securitypriv;
1109
1110 DBG_8723A("%s(%s): key_index =%d\n", __func__, ndev->name, key_index);
1111
1112 if (key_index == psecuritypriv->dot11PrivacyKeyIndex) {
1113 /* clear the flag of wep default key set. */
1114 psecuritypriv->bWepDefaultKeyIdxSet = 0;
1115 }
1116
1117 return 0;
1118 }
1119
1120 static int cfg80211_rtw_set_default_key(struct wiphy *wiphy,
1121 struct net_device *ndev, u8 key_index,
1122 bool unicast, bool multicast)
1123 {
1124 struct rtw_adapter *padapter = netdev_priv(ndev);
1125 struct security_priv *psecuritypriv = &padapter->securitypriv;
1126
1127 DBG_8723A("%s(%s): key_index =%d, unicast =%d, multicast =%d.\n",
1128 __func__, ndev->name, key_index, unicast, multicast);
1129
1130 if (key_index < NUM_WEP_KEYS &&
1131 (psecuritypriv->dot11PrivacyAlgrthm == WLAN_CIPHER_SUITE_WEP40 ||
1132 psecuritypriv->dot11PrivacyAlgrthm == WLAN_CIPHER_SUITE_WEP104)) {
1133 /* set wep default key */
1134 psecuritypriv->ndisencryptstatus = Ndis802_11Encryption1Enabled;
1135
1136 psecuritypriv->dot11PrivacyKeyIndex = key_index;
1137
1138 psecuritypriv->dot11PrivacyAlgrthm = WLAN_CIPHER_SUITE_WEP40;
1139 psecuritypriv->dot118021XGrpPrivacy = WLAN_CIPHER_SUITE_WEP40;
1140 if (psecuritypriv->wep_key[key_index].keylen == 13) {
1141 psecuritypriv->dot11PrivacyAlgrthm =
1142 WLAN_CIPHER_SUITE_WEP104;
1143 psecuritypriv->dot118021XGrpPrivacy =
1144 WLAN_CIPHER_SUITE_WEP104;
1145 }
1146
1147 /* set the flag to represent that wep default key
1148 has been set */
1149 psecuritypriv->bWepDefaultKeyIdxSet = 1;
1150 }
1151
1152 return 0;
1153 }
1154
1155 static u16 rtw_get_cur_max_rate(struct rtw_adapter *adapter)
1156 {
1157 int i = 0;
1158 const u8 *p;
1159 u16 rate = 0, max_rate = 0;
1160 struct mlme_ext_priv *pmlmeext = &adapter->mlmeextpriv;
1161 struct mlme_ext_info *pmlmeinfo = &pmlmeext->mlmext_info;
1162 struct registry_priv *pregistrypriv = &adapter->registrypriv;
1163 struct mlme_priv *pmlmepriv = &adapter->mlmepriv;
1164 struct wlan_bssid_ex *pcur_bss = &pmlmepriv->cur_network.network;
1165 struct ieee80211_ht_cap *pht_capie;
1166 u8 rf_type = 0;
1167 u8 bw_40MHz = 0, short_GI_20 = 0, short_GI_40 = 0;
1168 u16 mcs_rate = 0;
1169
1170 p = cfg80211_find_ie(WLAN_EID_HT_CAPABILITY,
1171 pcur_bss->IEs, pcur_bss->IELength);
1172 if (p && p[1] > 0) {
1173 pht_capie = (struct ieee80211_ht_cap *)(p + 2);
1174
1175 memcpy(&mcs_rate, &pht_capie->mcs, 2);
1176
1177 /* bw_40MHz = (pht_capie->cap_info&
1178 IEEE80211_HT_CAP_SUP_WIDTH_20_40) ? 1:0; */
1179 /* cur_bwmod is updated by beacon, pmlmeinfo is
1180 updated by association response */
1181 bw_40MHz = (pmlmeext->cur_bwmode &&
1182 (pmlmeinfo->HT_info.ht_param &
1183 IEEE80211_HT_PARAM_CHAN_WIDTH_ANY)) ? 1:0;
1184
1185 /* short_GI = (pht_capie->cap_info & (IEEE80211_HT_CAP
1186 _SGI_20|IEEE80211_HT_CAP_SGI_40)) ? 1 : 0; */
1187 short_GI_20 = (pmlmeinfo->ht_cap.cap_info &
1188 cpu_to_le16(IEEE80211_HT_CAP_SGI_20)) ? 1:0;
1189 short_GI_40 = (pmlmeinfo->ht_cap.cap_info &
1190 cpu_to_le16(IEEE80211_HT_CAP_SGI_40)) ? 1:0;
1191
1192 rf_type = rtl8723a_get_rf_type(adapter);
1193 max_rate = rtw_mcs_rate23a(rf_type, bw_40MHz &
1194 pregistrypriv->cbw40_enable,
1195 short_GI_20, short_GI_40,
1196 &pmlmeinfo->ht_cap.mcs);
1197 } else {
1198 while (pcur_bss->SupportedRates[i] != 0 &&
1199 pcur_bss->SupportedRates[i] != 0xFF) {
1200 rate = pcur_bss->SupportedRates[i] & 0x7F;
1201 if (rate>max_rate)
1202 max_rate = rate;
1203 i++;
1204 }
1205
1206 max_rate = max_rate * 10 / 2;
1207 }
1208
1209 return max_rate;
1210 }
1211
1212 static int cfg80211_rtw_get_station(struct wiphy *wiphy,
1213 struct net_device *ndev,
1214 const u8 *mac, struct station_info *sinfo)
1215 {
1216 int ret = 0;
1217 struct rtw_adapter *padapter = wiphy_to_adapter(wiphy);
1218 struct mlme_priv *pmlmepriv = &padapter->mlmepriv;
1219 struct sta_info *psta = NULL;
1220 struct sta_priv *pstapriv = &padapter->stapriv;
1221
1222 sinfo->filled = 0;
1223
1224 if (!mac) {
1225 DBG_8723A("%s(%s): mac ==%p\n", __func__, ndev->name, mac);
1226 ret = -ENOENT;
1227 goto exit;
1228 }
1229
1230 psta = rtw_get_stainfo23a(pstapriv, mac);
1231 if (psta == NULL) {
1232 DBG_8723A("%s, sta_info is null\n", __func__);
1233 ret = -ENOENT;
1234 goto exit;
1235 }
1236 DBG_8723A("%s(%s): mac =" MAC_FMT "\n", __func__, ndev->name,
1237 MAC_ARG(mac));
1238
1239 /* for infra./P2PClient mode */
1240 if (check_fwstate(pmlmepriv, WIFI_STATION_STATE) &&
1241 check_fwstate(pmlmepriv, _FW_LINKED)) {
1242 struct wlan_network *cur_network = &pmlmepriv->cur_network;
1243
1244 if (!ether_addr_equal(mac, cur_network->network.MacAddress)) {
1245 DBG_8723A("%s, mismatch bssid =" MAC_FMT "\n", __func__,
1246 MAC_ARG(cur_network->network.MacAddress));
1247 ret = -ENOENT;
1248 goto exit;
1249 }
1250
1251 sinfo->filled |= STATION_INFO_SIGNAL;
1252 sinfo->signal = translate_percentage_to_dbm(padapter->recvpriv.
1253 signal_strength);
1254
1255 sinfo->filled |= STATION_INFO_TX_BITRATE;
1256 sinfo->txrate.legacy = rtw_get_cur_max_rate(padapter);
1257
1258 sinfo->filled |= STATION_INFO_RX_PACKETS;
1259 sinfo->rx_packets = sta_rx_data_pkts(psta);
1260
1261 sinfo->filled |= STATION_INFO_TX_PACKETS;
1262 sinfo->tx_packets = psta->sta_stats.tx_pkts;
1263 }
1264
1265 /* for Ad-Hoc/AP mode */
1266 if ((check_fwstate(pmlmepriv, WIFI_ADHOC_STATE) ||
1267 check_fwstate(pmlmepriv, WIFI_ADHOC_MASTER_STATE) ||
1268 check_fwstate(pmlmepriv, WIFI_AP_STATE)) &&
1269 check_fwstate(pmlmepriv, _FW_LINKED)
1270 ) {
1271 /* TODO: should acquire station info... */
1272 }
1273
1274 exit:
1275 return ret;
1276 }
1277
1278 int cfg80211_infrastructure_mode(struct rtw_adapter* padapter,
1279 enum nl80211_iftype ifmode)
1280 {
1281 struct mlme_priv *pmlmepriv = &padapter->mlmepriv;
1282 struct wlan_network *cur_network = &pmlmepriv->cur_network;
1283 enum nl80211_iftype old_mode;
1284
1285 old_mode = cur_network->network.ifmode;
1286
1287 RT_TRACE(_module_rtl871x_ioctl_set_c_, _drv_notice_,
1288 ("+%s: old =%d new =%d fw_state = 0x%08x\n", __func__,
1289 old_mode, ifmode, get_fwstate(pmlmepriv)));
1290
1291 if (old_mode != ifmode) {
1292 spin_lock_bh(&pmlmepriv->lock);
1293
1294 RT_TRACE(_module_rtl871x_ioctl_set_c_, _drv_info_,
1295 (" change mode!"));
1296
1297 if (old_mode == NL80211_IFTYPE_AP ||
1298 old_mode == NL80211_IFTYPE_P2P_GO) {
1299 /* change to other mode from Ndis802_11APMode */
1300 cur_network->join_res = -1;
1301
1302 #ifdef CONFIG_8723AU_AP_MODE
1303 stop_ap_mode23a(padapter);
1304 #endif
1305 }
1306
1307 if (check_fwstate(pmlmepriv, _FW_LINKED) ||
1308 old_mode == NL80211_IFTYPE_ADHOC)
1309 rtw_disassoc_cmd23a(padapter, 0, true);
1310
1311 if (check_fwstate(pmlmepriv, _FW_LINKED) ||
1312 check_fwstate(pmlmepriv, WIFI_ADHOC_MASTER_STATE))
1313 rtw_free_assoc_resources23a(padapter, 1);
1314
1315 if (old_mode == NL80211_IFTYPE_STATION ||
1316 old_mode == NL80211_IFTYPE_P2P_CLIENT ||
1317 old_mode == NL80211_IFTYPE_ADHOC) {
1318 if (check_fwstate(pmlmepriv, _FW_LINKED)) {
1319 /* will clr Linked_state; before this function,
1320 we must have chked whether issue
1321 dis-assoc_cmd or not */
1322 rtw_indicate_disconnect23a(padapter);
1323 }
1324 }
1325
1326 cur_network->network.ifmode = ifmode;
1327
1328 _clr_fwstate_(pmlmepriv, ~WIFI_NULL_STATE);
1329
1330 switch (ifmode) {
1331 case NL80211_IFTYPE_ADHOC:
1332 set_fwstate(pmlmepriv, WIFI_ADHOC_STATE);
1333 break;
1334
1335 case NL80211_IFTYPE_P2P_CLIENT:
1336 case NL80211_IFTYPE_STATION:
1337 set_fwstate(pmlmepriv, WIFI_STATION_STATE);
1338 break;
1339
1340 case NL80211_IFTYPE_P2P_GO:
1341 case NL80211_IFTYPE_AP:
1342 set_fwstate(pmlmepriv, WIFI_AP_STATE);
1343 #ifdef CONFIG_8723AU_AP_MODE
1344 start_ap_mode23a(padapter);
1345 /* rtw_indicate_connect23a(padapter); */
1346 #endif
1347 break;
1348
1349 default:
1350 break;
1351 }
1352
1353 /* SecClearAllKeys(adapter); */
1354
1355 /* RT_TRACE(COMP_OID_SET, DBG_LOUD,
1356 ("set_infrastructure: fw_state:%x after changing mode\n", */
1357 /* get_fwstate(pmlmepriv))); */
1358
1359 spin_unlock_bh(&pmlmepriv->lock);
1360 }
1361
1362 return _SUCCESS;
1363 }
1364
1365 static int cfg80211_rtw_change_iface(struct wiphy *wiphy,
1366 struct net_device *ndev,
1367 enum nl80211_iftype type, u32 *flags,
1368 struct vif_params *params)
1369 {
1370 enum nl80211_iftype old_type;
1371 struct rtw_adapter *padapter = wiphy_to_adapter(wiphy);
1372 struct mlme_ext_priv *pmlmeext = &padapter->mlmeextpriv;
1373 struct wireless_dev *rtw_wdev = wiphy_to_wdev(wiphy);
1374 int ret = 0;
1375
1376 DBG_8723A("%s(%s): call netdev_open23a\n", __func__, ndev->name);
1377
1378 old_type = rtw_wdev->iftype;
1379 DBG_8723A("%s(%s): old_iftype =%d, new_iftype =%d\n",
1380 __func__, ndev->name, old_type, type);
1381
1382 if (old_type != type) {
1383 pmlmeext->action_public_rxseq = 0xffff;
1384 pmlmeext->action_public_dialog_token = 0xff;
1385 }
1386
1387 switch (type) {
1388 case NL80211_IFTYPE_ADHOC:
1389 case NL80211_IFTYPE_P2P_CLIENT:
1390 case NL80211_IFTYPE_STATION:
1391 case NL80211_IFTYPE_P2P_GO:
1392 case NL80211_IFTYPE_AP:
1393 case NL80211_IFTYPE_UNSPECIFIED:
1394 break;
1395 default:
1396 return -EOPNOTSUPP;
1397 }
1398
1399 rtw_wdev->iftype = type;
1400
1401 if (cfg80211_infrastructure_mode(padapter, type) != _SUCCESS) {
1402 rtw_wdev->iftype = old_type;
1403 ret = -EPERM;
1404 goto exit;
1405 }
1406
1407 rtw_setopmode_cmd23a(padapter, type);
1408
1409 exit:
1410 return ret;
1411 }
1412
1413 void rtw_cfg80211_indicate_scan_done(struct rtw_wdev_priv *pwdev_priv,
1414 bool aborted)
1415 {
1416 spin_lock_bh(&pwdev_priv->scan_req_lock);
1417 if (pwdev_priv->scan_request != NULL) {
1418 DBG_8723A("%s with scan req\n", __func__);
1419
1420 if (pwdev_priv->scan_request->wiphy !=
1421 pwdev_priv->rtw_wdev->wiphy)
1422 DBG_8723A("error wiphy compare\n");
1423 else
1424 cfg80211_scan_done(pwdev_priv->scan_request, aborted);
1425
1426 pwdev_priv->scan_request = NULL;
1427 } else {
1428 DBG_8723A("%s without scan req\n", __func__);
1429 }
1430 spin_unlock_bh(&pwdev_priv->scan_req_lock);
1431 }
1432
1433 void rtw_cfg80211_surveydone_event_callback(struct rtw_adapter *padapter)
1434 {
1435 struct list_head *plist, *phead, *ptmp;
1436 struct mlme_priv *pmlmepriv = &padapter->mlmepriv;
1437 struct rtw_queue *queue = &pmlmepriv->scanned_queue;
1438 struct wlan_network *pnetwork;
1439
1440 spin_lock_bh(&pmlmepriv->scanned_queue.lock);
1441
1442 phead = get_list_head(queue);
1443
1444 list_for_each_safe(plist, ptmp, phead) {
1445 pnetwork = container_of(plist, struct wlan_network, list);
1446
1447 /* report network only if the current channel set
1448 contains the channel to which this network belongs */
1449 if (rtw_ch_set_search_ch23a
1450 (padapter->mlmeextpriv.channel_set,
1451 pnetwork->network.DSConfig) >= 0)
1452 rtw_cfg80211_inform_bss(padapter, pnetwork);
1453 }
1454
1455 spin_unlock_bh(&pmlmepriv->scanned_queue.lock);
1456
1457 /* call this after other things have been done */
1458 rtw_cfg80211_indicate_scan_done(wdev_to_priv(padapter->rtw_wdev),
1459 false);
1460 }
1461
1462 static int rtw_cfg80211_set_probe_req_wpsp2pie(struct rtw_adapter *padapter,
1463 char *buf, int len)
1464 {
1465 int ret = 0;
1466 const u8 *wps_ie;
1467 struct mlme_priv *pmlmepriv = &padapter->mlmepriv;
1468
1469 DBG_8723A("%s, ielen =%d\n", __func__, len);
1470
1471 if (len > 0) {
1472 wps_ie = cfg80211_find_vendor_ie(WLAN_OUI_MICROSOFT,
1473 WLAN_OUI_TYPE_MICROSOFT_WPS,
1474 buf, len);
1475 if (wps_ie) {
1476 DBG_8723A("probe_req_wps_ielen =%d\n", wps_ie[1]);
1477
1478 if (pmlmepriv->wps_probe_req_ie) {
1479 pmlmepriv->wps_probe_req_ie_len = 0;
1480 kfree(pmlmepriv->wps_probe_req_ie);
1481 pmlmepriv->wps_probe_req_ie = NULL;
1482 }
1483
1484 pmlmepriv->wps_probe_req_ie = kmemdup(wps_ie, wps_ie[1],
1485 GFP_KERNEL);
1486 if (pmlmepriv->wps_probe_req_ie == NULL) {
1487 DBG_8723A("%s()-%d: kmalloc() ERROR!\n",
1488 __func__, __LINE__);
1489 return -EINVAL;
1490 }
1491 pmlmepriv->wps_probe_req_ie_len = wps_ie[1];
1492 }
1493 }
1494
1495 return ret;
1496 }
1497
1498 static int cfg80211_rtw_scan(struct wiphy *wiphy,
1499 struct cfg80211_scan_request *request)
1500 {
1501 int i;
1502 u8 _status = false;
1503 int ret = 0;
1504 struct rtw_adapter *padapter = wiphy_to_adapter(wiphy);
1505 struct mlme_priv *pmlmepriv = &padapter->mlmepriv;
1506 struct cfg80211_ssid ssid[RTW_SSID_SCAN_AMOUNT];
1507 struct rtw_ieee80211_channel ch[RTW_CHANNEL_SCAN_AMOUNT];
1508 struct rtw_wdev_priv *pwdev_priv = wdev_to_priv(padapter->rtw_wdev);
1509 struct cfg80211_ssid *ssids = request->ssids;
1510 bool need_indicate_scan_done = false;
1511
1512 DBG_8723A("%s(%s)\n", __func__, padapter->pnetdev->name);
1513
1514 spin_lock_bh(&pwdev_priv->scan_req_lock);
1515 pwdev_priv->scan_request = request;
1516 spin_unlock_bh(&pwdev_priv->scan_req_lock);
1517
1518 if (check_fwstate(pmlmepriv, WIFI_AP_STATE)) {
1519 DBG_8723A("%s under WIFI_AP_STATE\n", __func__);
1520 /* need_indicate_scan_done = true; */
1521 /* goto check_need_indicate_scan_done; */
1522 }
1523
1524 if (rtw_pwr_wakeup(padapter) == _FAIL) {
1525 need_indicate_scan_done = true;
1526 goto check_need_indicate_scan_done;
1527 }
1528
1529 if (request->ie && request->ie_len > 0) {
1530 rtw_cfg80211_set_probe_req_wpsp2pie(padapter,
1531 (u8 *) request->ie,
1532 request->ie_len);
1533 }
1534
1535 if (pmlmepriv->LinkDetectInfo.bBusyTraffic == true) {
1536 DBG_8723A("%s, bBusyTraffic == true\n", __func__);
1537 need_indicate_scan_done = true;
1538 goto check_need_indicate_scan_done;
1539 }
1540 if (rtw_is_scan_deny(padapter)) {
1541 DBG_8723A("%s(%s): scan deny\n", __func__,
1542 padapter->pnetdev->name);
1543 need_indicate_scan_done = true;
1544 goto check_need_indicate_scan_done;
1545 }
1546
1547 if (check_fwstate(pmlmepriv, _FW_UNDER_SURVEY | _FW_UNDER_LINKING) ==
1548 true) {
1549 DBG_8723A("%s, fwstate = 0x%x\n", __func__, pmlmepriv->fw_state);
1550 need_indicate_scan_done = true;
1551 goto check_need_indicate_scan_done;
1552 }
1553
1554 memset(ssid, 0, sizeof(struct cfg80211_ssid) * RTW_SSID_SCAN_AMOUNT);
1555 /* parsing request ssids, n_ssids */
1556 for (i = 0; i < request->n_ssids && i < RTW_SSID_SCAN_AMOUNT; i++) {
1557 DBG_8723A("ssid =%s, len =%d\n", ssids[i].ssid,
1558 ssids[i].ssid_len);
1559 memcpy(ssid[i].ssid, ssids[i].ssid, ssids[i].ssid_len);
1560 ssid[i].ssid_len = ssids[i].ssid_len;
1561 }
1562
1563 /* parsing channels, n_channels */
1564 memset(ch, 0,
1565 sizeof(struct rtw_ieee80211_channel) * RTW_CHANNEL_SCAN_AMOUNT);
1566
1567 if (request->n_channels == 1) {
1568 for (i = 0; i < request->n_channels &&
1569 i < RTW_CHANNEL_SCAN_AMOUNT; i++) {
1570 DBG_8723A("%s:(%s):" CHAN_FMT "\n",
1571 __func__, padapter->pnetdev->name,
1572 CHAN_ARG(request->channels[i]));
1573 ch[i].hw_value = request->channels[i]->hw_value;
1574 ch[i].flags = request->channels[i]->flags;
1575 }
1576 }
1577
1578 spin_lock_bh(&pmlmepriv->lock);
1579 if (request->n_channels == 1) {
1580 memcpy(&ch[1], &ch[0], sizeof(struct rtw_ieee80211_channel));
1581 memcpy(&ch[2], &ch[0], sizeof(struct rtw_ieee80211_channel));
1582 _status = rtw_sitesurvey_cmd23a(padapter, ssid,
1583 RTW_SSID_SCAN_AMOUNT, ch, 3);
1584 } else {
1585 _status = rtw_sitesurvey_cmd23a(padapter, ssid,
1586 RTW_SSID_SCAN_AMOUNT, NULL, 0);
1587 }
1588 spin_unlock_bh(&pmlmepriv->lock);
1589
1590 if (_status == false)
1591 ret = -1;
1592
1593 check_need_indicate_scan_done:
1594 if (need_indicate_scan_done)
1595 rtw_cfg80211_surveydone_event_callback(padapter);
1596 return ret;
1597 }
1598
1599 static int cfg80211_rtw_set_wiphy_params(struct wiphy *wiphy, u32 changed)
1600 {
1601 DBG_8723A("%s\n", __func__);
1602 return 0;
1603 }
1604
1605 static int cfg80211_rtw_join_ibss(struct wiphy *wiphy, struct net_device *ndev,
1606 struct cfg80211_ibss_params *params)
1607 {
1608 DBG_8723A("%s(%s)\n", __func__, ndev->name);
1609 return 0;
1610 }
1611
1612 static int cfg80211_rtw_leave_ibss(struct wiphy *wiphy, struct net_device *ndev)
1613 {
1614 DBG_8723A("%s(%s)\n", __func__, ndev->name);
1615 return 0;
1616 }
1617
1618 static int rtw_cfg80211_set_wpa_version(struct security_priv *psecuritypriv,
1619 u32 wpa_version)
1620 {
1621 DBG_8723A("%s, wpa_version =%d\n", __func__, wpa_version);
1622
1623 if (!wpa_version) {
1624 psecuritypriv->ndisauthtype = Ndis802_11AuthModeOpen;
1625 return 0;
1626 }
1627
1628 if (wpa_version & (NL80211_WPA_VERSION_1 | NL80211_WPA_VERSION_2)) {
1629 psecuritypriv->ndisauthtype = Ndis802_11AuthModeWPAPSK;
1630 }
1631
1632 /*
1633 if (wpa_version & NL80211_WPA_VERSION_2)
1634 {
1635 psecuritypriv->ndisauthtype = Ndis802_11AuthModeWPA2PSK;
1636 }
1637 */
1638
1639 return 0;
1640 }
1641
1642 static int rtw_cfg80211_set_auth_type(struct security_priv *psecuritypriv,
1643 enum nl80211_auth_type sme_auth_type)
1644 {
1645 DBG_8723A("%s, nl80211_auth_type =%d\n", __func__, sme_auth_type);
1646
1647 switch (sme_auth_type) {
1648 case NL80211_AUTHTYPE_AUTOMATIC:
1649 psecuritypriv->dot11AuthAlgrthm = dot11AuthAlgrthm_Auto;
1650
1651 break;
1652 case NL80211_AUTHTYPE_OPEN_SYSTEM:
1653 psecuritypriv->dot11AuthAlgrthm = dot11AuthAlgrthm_Open;
1654
1655 if (psecuritypriv->ndisauthtype > Ndis802_11AuthModeWPA)
1656 psecuritypriv->dot11AuthAlgrthm =
1657 dot11AuthAlgrthm_8021X;
1658 break;
1659 case NL80211_AUTHTYPE_SHARED_KEY:
1660 psecuritypriv->dot11AuthAlgrthm = dot11AuthAlgrthm_Shared;
1661
1662 psecuritypriv->ndisencryptstatus = Ndis802_11Encryption1Enabled;
1663 break;
1664 default:
1665 psecuritypriv->dot11AuthAlgrthm = dot11AuthAlgrthm_Open;
1666 /* return -ENOTSUPP; */
1667 }
1668
1669 return 0;
1670 }
1671
1672 static int rtw_cfg80211_set_cipher(struct security_priv *psecuritypriv,
1673 u32 cipher, bool ucast)
1674 {
1675 u32 ndisencryptstatus = Ndis802_11EncryptionDisabled;
1676
1677 u32 *profile_cipher = ucast ? &psecuritypriv->dot11PrivacyAlgrthm :
1678 &psecuritypriv->dot118021XGrpPrivacy;
1679
1680 DBG_8723A("%s, ucast =%d, cipher = 0x%x\n", __func__, ucast, cipher);
1681
1682 if (!cipher) {
1683 *profile_cipher = 0;
1684 psecuritypriv->ndisencryptstatus = ndisencryptstatus;
1685 return 0;
1686 }
1687
1688 switch (cipher) {
1689 case IW_AUTH_CIPHER_NONE:
1690 *profile_cipher = 0;
1691 ndisencryptstatus = Ndis802_11EncryptionDisabled;
1692 break;
1693 case WLAN_CIPHER_SUITE_WEP40:
1694 *profile_cipher = WLAN_CIPHER_SUITE_WEP40;
1695 ndisencryptstatus = Ndis802_11Encryption1Enabled;
1696 break;
1697 case WLAN_CIPHER_SUITE_WEP104:
1698 *profile_cipher = WLAN_CIPHER_SUITE_WEP104;
1699 ndisencryptstatus = Ndis802_11Encryption1Enabled;
1700 break;
1701 case WLAN_CIPHER_SUITE_TKIP:
1702 *profile_cipher = WLAN_CIPHER_SUITE_TKIP;
1703 ndisencryptstatus = Ndis802_11Encryption2Enabled;
1704 break;
1705 case WLAN_CIPHER_SUITE_CCMP:
1706 *profile_cipher = WLAN_CIPHER_SUITE_CCMP;
1707 ndisencryptstatus = Ndis802_11Encryption3Enabled;
1708 break;
1709 default:
1710 DBG_8723A("Unsupported cipher: 0x%x\n", cipher);
1711 return -ENOTSUPP;
1712 }
1713
1714 if (ucast)
1715 psecuritypriv->ndisencryptstatus = ndisencryptstatus;
1716
1717 return 0;
1718 }
1719
1720 static int rtw_cfg80211_set_key_mgt(struct security_priv *psecuritypriv,
1721 u32 key_mgt)
1722 {
1723 DBG_8723A("%s, key_mgt = 0x%x\n", __func__, key_mgt);
1724
1725 if (key_mgt == WLAN_AKM_SUITE_8021X)
1726 psecuritypriv->dot11AuthAlgrthm = dot11AuthAlgrthm_8021X;
1727 else if (key_mgt == WLAN_AKM_SUITE_PSK)
1728 psecuritypriv->dot11AuthAlgrthm = dot11AuthAlgrthm_8021X;
1729 else
1730 DBG_8723A("Invalid key mgt: 0x%x\n", key_mgt);
1731
1732 return 0;
1733 }
1734
1735 static int rtw_cfg80211_set_wpa_ie(struct rtw_adapter *padapter, const u8 *pie,
1736 size_t ielen)
1737 {
1738 const u8 *wps_ie;
1739 int group_cipher = 0, pairwise_cipher = 0;
1740 int ret = 0;
1741 const u8 *pwpa, *pwpa2;
1742 int i;
1743
1744 if (!pie || !ielen) {
1745 /* Treat this as normal case, but need to clear
1746 WIFI_UNDER_WPS */
1747 _clr_fwstate_(&padapter->mlmepriv, WIFI_UNDER_WPS);
1748 goto exit;
1749 }
1750 if (ielen > MAX_WPA_IE_LEN + MAX_WPS_IE_LEN + MAX_P2P_IE_LEN) {
1751 ret = -EINVAL;
1752 goto exit;
1753 }
1754
1755 /* dump */
1756 DBG_8723A("set wpa_ie(length:%zu):\n", ielen);
1757 for (i = 0; i < ielen; i = i + 8)
1758 DBG_8723A("0x%.2x 0x%.2x 0x%.2x 0x%.2x "
1759 "0x%.2x 0x%.2x 0x%.2x 0x%.2x\n",
1760 pie[i], pie[i + 1], pie[i + 2], pie[i + 3],
1761 pie[i + 4], pie[i + 5], pie[i + 6], pie[i + 7]);
1762 if (ielen < RSN_HEADER_LEN) {
1763 RT_TRACE(_module_rtl871x_ioctl_os_c, _drv_err_,
1764 ("Ie len too short %d\n", (int)ielen));
1765 ret = -1;
1766 goto exit;
1767 }
1768
1769 pwpa = cfg80211_find_vendor_ie(WLAN_OUI_MICROSOFT,
1770 WLAN_OUI_TYPE_MICROSOFT_WPA,
1771 pie, ielen);
1772 if (pwpa && pwpa[1] > 0) {
1773 if (rtw_parse_wpa_ie23a(pwpa, pwpa[1] + 2, &group_cipher,
1774 &pairwise_cipher, NULL) == _SUCCESS) {
1775 padapter->securitypriv.dot11AuthAlgrthm =
1776 dot11AuthAlgrthm_8021X;
1777 padapter->securitypriv.ndisauthtype =
1778 Ndis802_11AuthModeWPAPSK;
1779 memcpy(padapter->securitypriv.supplicant_ie, pwpa,
1780 pwpa[1] + 2);
1781
1782 DBG_8723A("got wpa_ie, wpa_ielen:%u\n", pwpa[1]);
1783 }
1784 }
1785
1786 pwpa2 = cfg80211_find_ie(WLAN_EID_RSN, pie, ielen);
1787 if (pwpa2 && pwpa2[1] > 0) {
1788 if (rtw_parse_wpa2_ie23a (pwpa2, pwpa2[1] + 2, &group_cipher,
1789 &pairwise_cipher, NULL) == _SUCCESS) {
1790 padapter->securitypriv.dot11AuthAlgrthm =
1791 dot11AuthAlgrthm_8021X;
1792 padapter->securitypriv.ndisauthtype =
1793 Ndis802_11AuthModeWPA2PSK;
1794 memcpy(padapter->securitypriv.supplicant_ie, pwpa2,
1795 pwpa2[1] + 2);
1796
1797 DBG_8723A("got wpa2_ie, wpa2_ielen:%u\n", pwpa2[1]);
1798 }
1799 }
1800
1801 if (group_cipher == 0) {
1802 group_cipher = WPA_CIPHER_NONE;
1803 }
1804 if (pairwise_cipher == 0) {
1805 pairwise_cipher = WPA_CIPHER_NONE;
1806 }
1807
1808 switch (group_cipher) {
1809 case WPA_CIPHER_NONE:
1810 padapter->securitypriv.dot118021XGrpPrivacy = 0;
1811 padapter->securitypriv.ndisencryptstatus =
1812 Ndis802_11EncryptionDisabled;
1813 break;
1814 case WPA_CIPHER_WEP40:
1815 padapter->securitypriv.dot118021XGrpPrivacy = WLAN_CIPHER_SUITE_WEP40;
1816 padapter->securitypriv.ndisencryptstatus =
1817 Ndis802_11Encryption1Enabled;
1818 break;
1819 case WPA_CIPHER_TKIP:
1820 padapter->securitypriv.dot118021XGrpPrivacy = WLAN_CIPHER_SUITE_TKIP;
1821 padapter->securitypriv.ndisencryptstatus =
1822 Ndis802_11Encryption2Enabled;
1823 break;
1824 case WPA_CIPHER_CCMP:
1825 padapter->securitypriv.dot118021XGrpPrivacy = WLAN_CIPHER_SUITE_CCMP;
1826 padapter->securitypriv.ndisencryptstatus =
1827 Ndis802_11Encryption3Enabled;
1828 break;
1829 case WPA_CIPHER_WEP104:
1830 padapter->securitypriv.dot118021XGrpPrivacy = WLAN_CIPHER_SUITE_WEP104;
1831 padapter->securitypriv.ndisencryptstatus =
1832 Ndis802_11Encryption1Enabled;
1833 break;
1834 }
1835
1836 switch (pairwise_cipher) {
1837 case WPA_CIPHER_NONE:
1838 padapter->securitypriv.dot11PrivacyAlgrthm = 0;
1839 padapter->securitypriv.ndisencryptstatus =
1840 Ndis802_11EncryptionDisabled;
1841 break;
1842 case WPA_CIPHER_WEP40:
1843 padapter->securitypriv.dot11PrivacyAlgrthm = WLAN_CIPHER_SUITE_WEP40;
1844 padapter->securitypriv.ndisencryptstatus =
1845 Ndis802_11Encryption1Enabled;
1846 break;
1847 case WPA_CIPHER_TKIP:
1848 padapter->securitypriv.dot11PrivacyAlgrthm = WLAN_CIPHER_SUITE_TKIP;
1849 padapter->securitypriv.ndisencryptstatus =
1850 Ndis802_11Encryption2Enabled;
1851 break;
1852 case WPA_CIPHER_CCMP:
1853 padapter->securitypriv.dot11PrivacyAlgrthm = WLAN_CIPHER_SUITE_CCMP;
1854 padapter->securitypriv.ndisencryptstatus =
1855 Ndis802_11Encryption3Enabled;
1856 break;
1857 case WPA_CIPHER_WEP104:
1858 padapter->securitypriv.dot11PrivacyAlgrthm = WLAN_CIPHER_SUITE_WEP104;
1859 padapter->securitypriv.ndisencryptstatus =
1860 Ndis802_11Encryption1Enabled;
1861 break;
1862 }
1863
1864 wps_ie = cfg80211_find_vendor_ie(WLAN_OUI_MICROSOFT,
1865 WLAN_OUI_TYPE_MICROSOFT_WPS,
1866 pie, ielen);
1867 if (wps_ie && wps_ie[1] > 0) {
1868 DBG_8723A("got wps_ie, wps_ielen:%u\n", wps_ie[1]);
1869 padapter->securitypriv.wps_ie_len = wps_ie[1];
1870 memcpy(padapter->securitypriv.wps_ie, wps_ie,
1871 padapter->securitypriv.wps_ie_len);
1872 set_fwstate(&padapter->mlmepriv, WIFI_UNDER_WPS);
1873 } else {
1874 _clr_fwstate_(&padapter->mlmepriv, WIFI_UNDER_WPS);
1875 }
1876
1877 /* TKIP and AES disallow multicast packets until installing group key */
1878 if (padapter->securitypriv.dot11PrivacyAlgrthm ==
1879 WLAN_CIPHER_SUITE_TKIP ||
1880 padapter->securitypriv.dot11PrivacyAlgrthm ==
1881 WLAN_CIPHER_SUITE_CCMP)
1882 /* WPS open need to enable multicast */
1883 /* check_fwstate(&padapter->mlmepriv, WIFI_UNDER_WPS) == true)*/
1884 rtl8723a_off_rcr_am(padapter);
1885
1886 RT_TRACE(_module_rtl871x_ioctl_os_c, _drv_info_,
1887 ("rtw_set_wpa_ie: pairwise_cipher = 0x%08x padapter->"
1888 "securitypriv.ndisencryptstatus =%d padapter->"
1889 "securitypriv.ndisauthtype =%d\n", pairwise_cipher,
1890 padapter->securitypriv.ndisencryptstatus,
1891 padapter->securitypriv.ndisauthtype));
1892
1893 exit:
1894 if (ret)
1895 _clr_fwstate_(&padapter->mlmepriv, WIFI_UNDER_WPS);
1896 return ret;
1897 }
1898
1899 static int rtw_cfg80211_add_wep(struct rtw_adapter *padapter,
1900 struct rtw_wep_key *wep, u8 keyid)
1901 {
1902 int res;
1903 struct security_priv *psecuritypriv = &padapter->securitypriv;
1904
1905 if (keyid >= NUM_WEP_KEYS) {
1906 RT_TRACE(_module_rtl871x_ioctl_set_c_, _drv_err_,
1907 ("%s:keyid>4 =>fail\n", __func__));
1908 res = _FAIL;
1909 goto exit;
1910 }
1911
1912 switch (wep->keylen) {
1913 case WLAN_KEY_LEN_WEP40:
1914 psecuritypriv->dot11PrivacyAlgrthm = WLAN_CIPHER_SUITE_WEP40;
1915 RT_TRACE(_module_rtl871x_ioctl_set_c_, _drv_info_,
1916 ("%s:wep->KeyLength = 5\n", __func__));
1917 break;
1918 case WLAN_KEY_LEN_WEP104:
1919 psecuritypriv->dot11PrivacyAlgrthm = WLAN_CIPHER_SUITE_WEP104;
1920 RT_TRACE(_module_rtl871x_ioctl_set_c_, _drv_info_,
1921 ("%s:wep->KeyLength = 13\n", __func__));
1922 break;
1923 default:
1924 psecuritypriv->dot11PrivacyAlgrthm = 0;
1925 RT_TRACE(_module_rtl871x_ioctl_set_c_, _drv_info_,
1926 ("%s:wep->KeyLength!= 5 or 13\n", __func__));
1927 res = _FAIL;
1928 goto exit;
1929 }
1930
1931 RT_TRACE(_module_rtl871x_ioctl_set_c_, _drv_info_,
1932 ("%s:before memcpy, wep->KeyLength = 0x%x keyid =%x\n",
1933 __func__, wep->keylen, keyid));
1934
1935 memcpy(&psecuritypriv->wep_key[keyid], wep, sizeof(struct rtw_wep_key));
1936
1937 psecuritypriv->dot11PrivacyKeyIndex = keyid;
1938
1939 RT_TRACE(_module_rtl871x_ioctl_set_c_, _drv_info_,
1940 ("%s:security key material : "
1941 "%x %x %x %x %x %x %x %x %x %x %x %x %x\n", __func__,
1942 psecuritypriv->wep_key[keyid].key[0],
1943 psecuritypriv->wep_key[keyid].key[1],
1944 psecuritypriv->wep_key[keyid].key[2],
1945 psecuritypriv->wep_key[keyid].key[3],
1946 psecuritypriv->wep_key[keyid].key[4],
1947 psecuritypriv->wep_key[keyid].key[5],
1948 psecuritypriv->wep_key[keyid].key[6],
1949 psecuritypriv->wep_key[keyid].key[7],
1950 psecuritypriv->wep_key[keyid].key[8],
1951 psecuritypriv->wep_key[keyid].key[9],
1952 psecuritypriv->wep_key[keyid].key[10],
1953 psecuritypriv->wep_key[keyid].key[11],
1954 psecuritypriv->wep_key[keyid].key[12]));
1955
1956 res = rtw_set_key23a(padapter, psecuritypriv, keyid, 1);
1957
1958 exit:
1959
1960 return res;
1961 }
1962
1963 static int rtw_set_ssid(struct rtw_adapter *padapter,
1964 struct wlan_network *newnetwork)
1965 {
1966 struct mlme_priv *pmlmepriv = &padapter->mlmepriv;
1967 struct wlan_network *pnetwork = &pmlmepriv->cur_network;
1968 int status = _SUCCESS;
1969 u32 cur_time = 0;
1970
1971 DBG_8723A_LEVEL(_drv_always_, "set ssid [%s] fw_state = 0x%08x\n",
1972 newnetwork->network.Ssid.ssid, get_fwstate(pmlmepriv));
1973
1974 if (padapter->hw_init_completed == false) {
1975 RT_TRACE(_module_rtl871x_ioctl_set_c_, _drv_err_,
1976 ("set_ssid: hw_init_completed == false =>exit!!!\n"));
1977 status = _FAIL;
1978 goto exit;
1979 }
1980
1981 spin_lock_bh(&pmlmepriv->lock);
1982
1983 DBG_8723A("Set SSID under fw_state = 0x%08x\n", get_fwstate(pmlmepriv));
1984 if (check_fwstate(pmlmepriv, _FW_UNDER_SURVEY))
1985 goto handle_tkip_countermeasure;
1986
1987 if (check_fwstate(pmlmepriv, _FW_LINKED|WIFI_ADHOC_MASTER_STATE)) {
1988 RT_TRACE(_module_rtl871x_ioctl_set_c_, _drv_info_,
1989 ("set_ssid: _FW_LINKED||WIFI_ADHOC_MASTER_STATE\n"));
1990
1991 if (pmlmepriv->assoc_ssid.ssid_len ==
1992 newnetwork->network.Ssid.ssid_len &&
1993 !memcmp(&pmlmepriv->assoc_ssid.ssid,
1994 newnetwork->network.Ssid.ssid,
1995 newnetwork->network.Ssid.ssid_len)) {
1996 if (!check_fwstate(pmlmepriv, WIFI_STATION_STATE)) {
1997 RT_TRACE(_module_rtl871x_ioctl_set_c_,
1998 _drv_err_, ("New SSID is same SSID, "
1999 "fw_state = 0x%08x\n",
2000 get_fwstate(pmlmepriv)));
2001
2002 if (rtw_is_same_ibss23a(padapter, pnetwork)) {
2003 /*
2004 * it means driver is in
2005 * WIFI_ADHOC_MASTER_STATE, we needn't
2006 * create bss again.
2007 */
2008 goto release_mlme_lock;
2009 }
2010
2011 /*
2012 * if in WIFI_ADHOC_MASTER_STATE |
2013 * WIFI_ADHOC_STATE, create bss or
2014 * rejoin again
2015 */
2016 rtw_disassoc_cmd23a(padapter, 0, true);
2017
2018 if (check_fwstate(pmlmepriv, _FW_LINKED))
2019 rtw_indicate_disconnect23a(padapter);
2020
2021 rtw_free_assoc_resources23a(padapter, 1);
2022
2023 if (check_fwstate(pmlmepriv,
2024 WIFI_ADHOC_MASTER_STATE)) {
2025 _clr_fwstate_(pmlmepriv,
2026 WIFI_ADHOC_MASTER_STATE);
2027 set_fwstate(pmlmepriv,
2028 WIFI_ADHOC_STATE);
2029 }
2030 } else {
2031 rtw_lps_ctrl_wk_cmd23a(padapter,
2032 LPS_CTRL_JOINBSS, 1);
2033 }
2034 } else {
2035 RT_TRACE(_module_rtl871x_ioctl_set_c_, _drv_info_,
2036 ("Set SSID not the same ssid\n"));
2037 RT_TRACE(_module_rtl871x_ioctl_set_c_, _drv_info_,
2038 ("set_ssid =[%s] len = 0x%x\n",
2039 newnetwork->network.Ssid.ssid,
2040 newnetwork->network.Ssid.ssid_len));
2041 RT_TRACE(_module_rtl871x_ioctl_set_c_, _drv_info_,
2042 ("assoc_ssid =[%s] len = 0x%x\n",
2043 pmlmepriv->assoc_ssid.ssid,
2044 pmlmepriv->assoc_ssid.ssid_len));
2045
2046 rtw_disassoc_cmd23a(padapter, 0, true);
2047
2048 if (check_fwstate(pmlmepriv, _FW_LINKED))
2049 rtw_indicate_disconnect23a(padapter);
2050
2051 rtw_free_assoc_resources23a(padapter, 1);
2052
2053 if (check_fwstate(pmlmepriv, WIFI_ADHOC_MASTER_STATE)) {
2054 _clr_fwstate_(pmlmepriv, WIFI_ADHOC_MASTER_STATE);
2055 set_fwstate(pmlmepriv, WIFI_ADHOC_STATE);
2056 }
2057 }
2058 }
2059
2060 handle_tkip_countermeasure:
2061
2062 if (padapter->securitypriv.btkip_countermeasure == true) {
2063 cur_time = jiffies;
2064
2065 if ((cur_time -
2066 padapter->securitypriv.btkip_countermeasure_time) >
2067 60 * HZ) {
2068 padapter->securitypriv.btkip_countermeasure = false;
2069 padapter->securitypriv.btkip_countermeasure_time = 0;
2070 } else {
2071 status = _FAIL;
2072 goto release_mlme_lock;
2073 }
2074 }
2075
2076 memcpy(&pmlmepriv->assoc_ssid, &newnetwork->network.Ssid,
2077 sizeof(struct cfg80211_ssid));
2078
2079 pmlmepriv->assoc_by_bssid = false;
2080
2081 pmlmepriv->to_join = true;
2082
2083 if (!check_fwstate(pmlmepriv, _FW_UNDER_SURVEY)) {
2084 pmlmepriv->cur_network.join_res = -2;
2085
2086 status = rtw_do_join_network(padapter, newnetwork);
2087 if (status == _SUCCESS) {
2088 pmlmepriv->to_join = false;
2089 } else {
2090 if (check_fwstate(pmlmepriv, WIFI_ADHOC_STATE)) {
2091 /* switch to ADHOC_MASTER */
2092 status = rtw_do_join_adhoc(padapter);
2093 if (status != _SUCCESS)
2094 goto release_mlme_lock;
2095 } else {
2096 /* can't associate ; reset under-linking */
2097 _clr_fwstate_(pmlmepriv, _FW_UNDER_LINKING);
2098 status = _FAIL;
2099 pmlmepriv->to_join = false;
2100 }
2101 }
2102 }
2103 release_mlme_lock:
2104 spin_unlock_bh(&pmlmepriv->lock);
2105
2106 exit:
2107 RT_TRACE(_module_rtl871x_ioctl_set_c_, _drv_err_,
2108 ("-%s: status =%d\n", __func__, status));
2109
2110 return status;
2111 }
2112
2113 static int cfg80211_rtw_connect(struct wiphy *wiphy, struct net_device *ndev,
2114 struct cfg80211_connect_params *sme)
2115 {
2116 int ret = 0;
2117 struct list_head *phead, *plist, *ptmp;
2118 struct wlan_network *pnetwork = NULL;
2119 /* u8 matched_by_bssid = false; */
2120 /* u8 matched_by_ssid = false; */
2121 u8 matched = false;
2122 struct rtw_adapter *padapter = wiphy_to_adapter(wiphy);
2123 struct mlme_priv *pmlmepriv = &padapter->mlmepriv;
2124 struct security_priv *psecuritypriv = &padapter->securitypriv;
2125 struct rtw_queue *queue = &pmlmepriv->scanned_queue;
2126
2127 DBG_8723A("=>" "%s(%s)\n", __func__, ndev->name);
2128 DBG_8723A("privacy =%d, key =%p, key_len =%d, key_idx =%d\n",
2129 sme->privacy, sme->key, sme->key_len, sme->key_idx);
2130
2131 if (_FAIL == rtw_pwr_wakeup(padapter)) {
2132 ret = -EPERM;
2133 goto exit;
2134 }
2135
2136 if (check_fwstate(pmlmepriv, WIFI_AP_STATE)) {
2137 ret = -EPERM;
2138 goto exit;
2139 }
2140
2141 if (!sme->ssid || !sme->ssid_len ||
2142 sme->ssid_len > IEEE80211_MAX_SSID_LEN) {
2143 ret = -EINVAL;
2144 goto exit;
2145 }
2146
2147 DBG_8723A("ssid =%s, len =%zu\n", sme->ssid, sme->ssid_len);
2148
2149 if (sme->bssid)
2150 DBG_8723A("bssid =" MAC_FMT "\n", MAC_ARG(sme->bssid));
2151
2152 if (check_fwstate(pmlmepriv, _FW_UNDER_LINKING)) {
2153 ret = -EBUSY;
2154 DBG_8723A("%s, fw_state = 0x%x, goto exit\n", __func__,
2155 pmlmepriv->fw_state);
2156 goto exit;
2157 }
2158 if (check_fwstate(pmlmepriv, _FW_UNDER_SURVEY)) {
2159 rtw_scan_abort23a(padapter);
2160 }
2161
2162 spin_lock_bh(&queue->lock);
2163
2164 phead = get_list_head(queue);
2165
2166 list_for_each_safe(plist, ptmp, phead) {
2167 pnetwork = container_of(plist, struct wlan_network, list);
2168
2169 if (sme->bssid) {
2170 if (!ether_addr_equal(pnetwork->network.MacAddress,
2171 sme->bssid))
2172 continue;
2173 }
2174
2175 if (sme->ssid && sme->ssid_len) {
2176 if (pnetwork->network.Ssid.ssid_len != sme->ssid_len ||
2177 memcmp(pnetwork->network.Ssid.ssid, sme->ssid,
2178 sme->ssid_len))
2179 continue;
2180 }
2181
2182 if (sme->bssid) {
2183 if (ether_addr_equal(pnetwork->network.MacAddress,
2184 sme->bssid)) {
2185 DBG_8723A("matched by bssid\n");
2186
2187 matched = true;
2188 break;
2189 }
2190 } else if (sme->ssid && sme->ssid_len) {
2191 if (!memcmp(pnetwork->network.Ssid.ssid,
2192 sme->ssid, sme->ssid_len) &&
2193 pnetwork->network.Ssid.ssid_len == sme->ssid_len) {
2194 DBG_8723A("matched by ssid\n");
2195
2196 matched = true;
2197 break;
2198 }
2199 }
2200 }
2201
2202 spin_unlock_bh(&queue->lock);
2203
2204 if (!matched || !pnetwork) {
2205 ret = -ENOENT;
2206 DBG_8723A("connect, matched == false, goto exit\n");
2207 goto exit;
2208 }
2209
2210 if (cfg80211_infrastructure_mode(
2211 padapter, pnetwork->network.ifmode) != _SUCCESS) {
2212 ret = -EPERM;
2213 goto exit;
2214 }
2215
2216 psecuritypriv->ndisencryptstatus = Ndis802_11EncryptionDisabled;
2217 psecuritypriv->dot11PrivacyAlgrthm = 0;
2218 psecuritypriv->dot118021XGrpPrivacy = 0;
2219 psecuritypriv->dot11AuthAlgrthm = dot11AuthAlgrthm_Open;
2220 psecuritypriv->ndisauthtype = Ndis802_11AuthModeOpen;
2221
2222 ret = rtw_cfg80211_set_wpa_version(psecuritypriv,
2223 sme->crypto.wpa_versions);
2224 if (ret < 0)
2225 goto exit;
2226
2227 ret = rtw_cfg80211_set_auth_type(psecuritypriv, sme->auth_type);
2228
2229 if (ret < 0)
2230 goto exit;
2231
2232 DBG_8723A("%s, ie_len =%zu\n", __func__, sme->ie_len);
2233
2234 ret = rtw_cfg80211_set_wpa_ie(padapter, sme->ie, sme->ie_len);
2235 if (ret < 0)
2236 goto exit;
2237
2238 if (sme->crypto.n_ciphers_pairwise) {
2239 ret = rtw_cfg80211_set_cipher(psecuritypriv,
2240 sme->crypto.ciphers_pairwise[0],
2241 true);
2242 if (ret < 0)
2243 goto exit;
2244 }
2245
2246 /* For WEP Shared auth */
2247 if ((psecuritypriv->dot11AuthAlgrthm == dot11AuthAlgrthm_Shared ||
2248 psecuritypriv->dot11AuthAlgrthm == dot11AuthAlgrthm_Auto) &&
2249 sme->key) {
2250 struct rtw_wep_key wep_key;
2251 u8 wep_key_idx, wep_key_len;
2252 DBG_8723A("%s(): Shared/Auto WEP\n", __func__);
2253
2254 wep_key_idx = sme->key_idx;
2255 wep_key_len = sme->key_len;
2256
2257 if (wep_key_idx > WEP_KEYS || !wep_key_len ||
2258 wep_key_len > WLAN_KEY_LEN_WEP104) {
2259 ret = -EINVAL;
2260 goto exit;
2261 }
2262
2263 wep_key_len = wep_key_len <= 5 ? 5 : 13;
2264
2265 memset(&wep_key, 0, sizeof(struct rtw_wep_key));
2266
2267 wep_key.keylen = wep_key_len;
2268
2269 if (wep_key_len == 13) {
2270 padapter->securitypriv.dot11PrivacyAlgrthm =
2271 WLAN_CIPHER_SUITE_WEP104;
2272 padapter->securitypriv.dot118021XGrpPrivacy =
2273 WLAN_CIPHER_SUITE_WEP104;
2274 } else {
2275 padapter->securitypriv.dot11PrivacyAlgrthm =
2276 WLAN_CIPHER_SUITE_WEP40;
2277 padapter->securitypriv.dot118021XGrpPrivacy =
2278 WLAN_CIPHER_SUITE_WEP40;
2279 }
2280
2281 memcpy(wep_key.key, (void *)sme->key, wep_key.keylen);
2282
2283 if (rtw_cfg80211_add_wep(padapter, &wep_key, wep_key_idx) !=
2284 _SUCCESS)
2285 ret = -EOPNOTSUPP;
2286
2287 if (ret < 0)
2288 goto exit;
2289 }
2290
2291 ret = rtw_cfg80211_set_cipher(psecuritypriv,
2292 sme->crypto.cipher_group, false);
2293 if (ret < 0)
2294 goto exit;
2295
2296 if (sme->crypto.n_akm_suites) {
2297 ret = rtw_cfg80211_set_key_mgt(psecuritypriv,
2298 sme->crypto.akm_suites[0]);
2299 if (ret < 0)
2300 goto exit;
2301 }
2302
2303 if (psecuritypriv->ndisauthtype > 3)
2304 psecuritypriv->dot11AuthAlgrthm = dot11AuthAlgrthm_8021X;
2305
2306 if (rtw_set_auth23a(padapter, psecuritypriv) != _SUCCESS) {
2307 ret = -EBUSY;
2308 goto exit;
2309 }
2310
2311 /* rtw_set_802_11_encryption_mode(padapter,
2312 padapter->securitypriv.ndisencryptstatus); */
2313
2314 if (rtw_set_ssid(padapter, pnetwork) != _SUCCESS) {
2315 ret = -EBUSY;
2316 goto exit;
2317 }
2318
2319 DBG_8723A("set ssid:dot11AuthAlgrthm =%d, dot11PrivacyAlgrthm =%d, "
2320 "dot118021XGrpPrivacy =%d\n", psecuritypriv->dot11AuthAlgrthm,
2321 psecuritypriv->dot11PrivacyAlgrthm,
2322 psecuritypriv->dot118021XGrpPrivacy);
2323
2324 exit:
2325
2326 DBG_8723A("<=%s, ret %d\n", __func__, ret);
2327
2328 return ret;
2329 }
2330
2331 static int cfg80211_rtw_disconnect(struct wiphy *wiphy, struct net_device *ndev,
2332 u16 reason_code)
2333 {
2334 struct rtw_adapter *padapter = wiphy_to_adapter(wiphy);
2335
2336 DBG_8723A("%s(%s)\n", __func__, ndev->name);
2337
2338 rtw_set_roaming(padapter, 0);
2339
2340 if (check_fwstate(&padapter->mlmepriv, _FW_LINKED)) {
2341 rtw_scan_abort23a(padapter);
2342 LeaveAllPowerSaveMode23a(padapter);
2343 rtw_disassoc_cmd23a(padapter, 500, false);
2344
2345 DBG_8723A("%s...call rtw_indicate_disconnect23a\n", __func__);
2346
2347 padapter->mlmepriv.not_indic_disco = true;
2348 rtw_indicate_disconnect23a(padapter);
2349 padapter->mlmepriv.not_indic_disco = false;
2350
2351 rtw_free_assoc_resources23a(padapter, 1);
2352 }
2353
2354 return 0;
2355 }
2356
2357 static int cfg80211_rtw_set_txpower(struct wiphy *wiphy,
2358 struct wireless_dev *wdev,
2359 enum nl80211_tx_power_setting type, int mbm)
2360 {
2361 DBG_8723A("%s\n", __func__);
2362 return 0;
2363 }
2364
2365 static int cfg80211_rtw_get_txpower(struct wiphy *wiphy,
2366 struct wireless_dev *wdev, int *dbm)
2367 {
2368 DBG_8723A("%s\n", __func__);
2369 *dbm = (12);
2370 return 0;
2371 }
2372
2373 inline bool rtw_cfg80211_pwr_mgmt(struct rtw_adapter *adapter)
2374 {
2375 struct rtw_wdev_priv *rtw_wdev_priv = wdev_to_priv(adapter->rtw_wdev);
2376 return rtw_wdev_priv->power_mgmt;
2377 }
2378
2379 static int cfg80211_rtw_set_power_mgmt(struct wiphy *wiphy,
2380 struct net_device *ndev,
2381 bool enabled, int timeout)
2382 {
2383 struct rtw_adapter *padapter = wiphy_to_adapter(wiphy);
2384 struct rtw_wdev_priv *rtw_wdev_priv = wdev_to_priv(padapter->rtw_wdev);
2385
2386 DBG_8723A("%s(%s): enabled:%u, timeout:%d\n",
2387 __func__, ndev->name, enabled, timeout);
2388
2389 rtw_wdev_priv->power_mgmt = enabled;
2390
2391 if (!enabled)
2392 LPS_Leave23a(padapter);
2393
2394 return 0;
2395 }
2396
2397 static int cfg80211_rtw_set_pmksa(struct wiphy *wiphy,
2398 struct net_device *netdev,
2399 struct cfg80211_pmksa *pmksa)
2400 {
2401 u8 index, blInserted = false;
2402 struct rtw_adapter *padapter = wiphy_to_adapter(wiphy);
2403 struct security_priv *psecuritypriv = &padapter->securitypriv;
2404
2405 DBG_8723A("%s(%s)\n", __func__, netdev->name);
2406
2407 if (is_zero_ether_addr(pmksa->bssid))
2408 return -EINVAL;
2409
2410 blInserted = false;
2411
2412 /* overwrite PMKID */
2413 for (index = 0; index < NUM_PMKID_CACHE; index++) {
2414 if (ether_addr_equal(psecuritypriv->PMKIDList[index].Bssid,
2415 pmksa->bssid)) {
2416 /* BSSID is matched, the same AP => rewrite with
2417 new PMKID. */
2418 DBG_8723A("%s(%s): BSSID exists in the PMKList.\n",
2419 __func__, netdev->name);
2420
2421 memcpy(psecuritypriv->PMKIDList[index].PMKID,
2422 pmksa->pmkid, WLAN_PMKID_LEN);
2423 psecuritypriv->PMKIDList[index].bUsed = true;
2424 psecuritypriv->PMKIDIndex = index + 1;
2425 blInserted = true;
2426 break;
2427 }
2428 }
2429
2430 if (!blInserted) {
2431 /* Find a new entry */
2432 DBG_8723A("%s(%s): Use new entry index = %d for this PMKID\n",
2433 __func__, netdev->name, psecuritypriv->PMKIDIndex);
2434
2435 ether_addr_copy(
2436 psecuritypriv->PMKIDList[psecuritypriv->PMKIDIndex].
2437 Bssid, pmksa->bssid);
2438 memcpy(psecuritypriv->PMKIDList[psecuritypriv->PMKIDIndex].
2439 PMKID, pmksa->pmkid, WLAN_PMKID_LEN);
2440
2441 psecuritypriv->PMKIDList[psecuritypriv->PMKIDIndex].bUsed =
2442 true;
2443 psecuritypriv->PMKIDIndex++;
2444 if (psecuritypriv->PMKIDIndex == 16) {
2445 psecuritypriv->PMKIDIndex = 0;
2446 }
2447 }
2448
2449 return 0;
2450 }
2451
2452 static int cfg80211_rtw_del_pmksa(struct wiphy *wiphy,
2453 struct net_device *netdev,
2454 struct cfg80211_pmksa *pmksa)
2455 {
2456 u8 index, bMatched = false;
2457 struct rtw_adapter *padapter = wiphy_to_adapter(wiphy);
2458 struct security_priv *psecuritypriv = &padapter->securitypriv;
2459
2460 DBG_8723A("%s(%s)\n", __func__, netdev->name);
2461
2462 for (index = 0; index < NUM_PMKID_CACHE; index++) {
2463 if (ether_addr_equal(psecuritypriv->PMKIDList[index].Bssid,
2464 pmksa->bssid)) {
2465 /* BSSID is matched, the same AP => Remove this PMKID
2466 information and reset it. */
2467 eth_zero_addr(psecuritypriv->PMKIDList[index].Bssid);
2468 memset(psecuritypriv->PMKIDList[index].PMKID, 0x00,
2469 WLAN_PMKID_LEN);
2470 psecuritypriv->PMKIDList[index].bUsed = false;
2471 bMatched = true;
2472 break;
2473 }
2474 }
2475
2476 if (false == bMatched) {
2477 DBG_8723A("%s(%s): do not have matched BSSID\n", __func__,
2478 netdev->name);
2479 return -EINVAL;
2480 }
2481
2482 return 0;
2483 }
2484
2485 static int cfg80211_rtw_flush_pmksa(struct wiphy *wiphy,
2486 struct net_device *netdev)
2487 {
2488 struct rtw_adapter *padapter = wiphy_to_adapter(wiphy);
2489 struct security_priv *psecuritypriv = &padapter->securitypriv;
2490
2491 DBG_8723A("%s(%s)\n", __func__, netdev->name);
2492
2493 memset(&psecuritypriv->PMKIDList[0], 0x00,
2494 sizeof(struct rt_pmkid_list) * NUM_PMKID_CACHE);
2495 psecuritypriv->PMKIDIndex = 0;
2496
2497 return 0;
2498 }
2499
2500 #ifdef CONFIG_8723AU_AP_MODE
2501 void rtw_cfg80211_indicate_sta_assoc(struct rtw_adapter *padapter,
2502 u8 *pmgmt_frame, uint frame_len)
2503 {
2504 s32 freq;
2505 int channel;
2506 struct mlme_ext_priv *pmlmeext = &padapter->mlmeextpriv;
2507 struct net_device *ndev = padapter->pnetdev;
2508
2509 DBG_8723A("%s(padapter =%p,%s)\n", __func__, padapter, ndev->name);
2510
2511 #if defined(RTW_USE_CFG80211_STA_EVENT)
2512 {
2513 struct station_info sinfo;
2514 u8 ie_offset;
2515
2516 if (ieee80211_is_assoc_req(hdr->frame_control))
2517 ie_offset = offsetof(struct ieee80211_mgmt,
2518 u.assoc_req.variable);
2519 else /* WIFI_REASSOCREQ */
2520 ie_offset = offsetof(struct ieee80211_mgmt,
2521 u.reassoc_req.variable);
2522
2523 sinfo.filled = 0;
2524 sinfo.filled = STATION_INFO_ASSOC_REQ_IES;
2525 sinfo.assoc_req_ies = pmgmt_frame + ie_offset;
2526 sinfo.assoc_req_ies_len = frame_len - ie_offset;
2527 cfg80211_new_sta(ndev, hdr->addr2, &sinfo, GFP_ATOMIC);
2528 }
2529 #else /* defined(RTW_USE_CFG80211_STA_EVENT) */
2530 channel = pmlmeext->cur_channel;
2531 if (channel <= RTW_CH_MAX_2G_CHANNEL)
2532 freq = ieee80211_channel_to_frequency(channel,
2533 IEEE80211_BAND_2GHZ);
2534 else
2535 freq = ieee80211_channel_to_frequency(channel,
2536 IEEE80211_BAND_5GHZ);
2537
2538 cfg80211_rx_mgmt(padapter->rtw_wdev, freq, 0, pmgmt_frame, frame_len,
2539 0, GFP_ATOMIC);
2540 #endif /* defined(RTW_USE_CFG80211_STA_EVENT) */
2541 }
2542
2543 void rtw_cfg80211_indicate_sta_disassoc(struct rtw_adapter *padapter,
2544 unsigned char *da,
2545 unsigned short reason)
2546 {
2547 s32 freq;
2548 int channel;
2549 uint frame_len;
2550 struct ieee80211_mgmt mgmt;
2551 struct mlme_ext_priv *pmlmeext = &padapter->mlmeextpriv;
2552 struct mlme_ext_info *pmlmeinfo = &pmlmeext->mlmext_info;
2553 struct net_device *ndev = padapter->pnetdev;
2554
2555 DBG_8723A("%s(padapter =%p,%s)\n", __func__, padapter, ndev->name);
2556
2557 memset(&mgmt, 0, sizeof(struct ieee80211_mgmt));
2558
2559 #if defined(RTW_USE_CFG80211_STA_EVENT)
2560 cfg80211_del_sta(ndev, da, GFP_ATOMIC);
2561 #else /* defined(RTW_USE_CFG80211_STA_EVENT) */
2562 channel = pmlmeext->cur_channel;
2563 if (channel <= RTW_CH_MAX_2G_CHANNEL)
2564 freq = ieee80211_channel_to_frequency(channel,
2565 IEEE80211_BAND_2GHZ);
2566 else
2567 freq = ieee80211_channel_to_frequency(channel,
2568 IEEE80211_BAND_5GHZ);
2569
2570 mgmt.frame_control =
2571 cpu_to_le16(IEEE80211_FTYPE_MGMT | IEEE80211_STYPE_DEAUTH);
2572
2573 ether_addr_copy(mgmt.da, myid(&padapter->eeprompriv));
2574 ether_addr_copy(mgmt.sa, da);
2575 ether_addr_copy(mgmt.bssid, get_my_bssid23a(&pmlmeinfo->network));
2576
2577 mgmt.seq_ctrl = cpu_to_le16(IEEE80211_SN_TO_SEQ(pmlmeext->mgnt_seq));
2578 pmlmeext->mgnt_seq++;
2579
2580 mgmt.u.disassoc.reason_code = cpu_to_le16(reason);
2581
2582 frame_len = sizeof(struct ieee80211_hdr_3addr) + 2;
2583
2584 cfg80211_rx_mgmt(padapter->rtw_wdev, freq, 0, (u8 *)&mgmt, frame_len,
2585 0, GFP_ATOMIC);
2586 #endif /* defined(RTW_USE_CFG80211_STA_EVENT) */
2587 }
2588
2589 static int rtw_cfg80211_monitor_if_open(struct net_device *ndev)
2590 {
2591 int ret = 0;
2592
2593 DBG_8723A("%s\n", __func__);
2594
2595 return ret;
2596 }
2597
2598 static int rtw_cfg80211_monitor_if_close(struct net_device *ndev)
2599 {
2600 int ret = 0;
2601
2602 DBG_8723A("%s\n", __func__);
2603
2604 return ret;
2605 }
2606
2607 static int rtw_cfg80211_monitor_if_xmit_entry(struct sk_buff *skb,
2608 struct net_device *ndev)
2609 {
2610 int ret = 0;
2611 int rtap_len;
2612 int qos_len = 0;
2613 int dot11_hdr_len = 24;
2614 int snap_len = 6;
2615 unsigned char *pdata;
2616 unsigned char src_mac_addr[6];
2617 unsigned char dst_mac_addr[6];
2618 struct ieee80211_hdr *dot11_hdr;
2619 struct ieee80211_radiotap_header *rtap_hdr;
2620 struct rtw_adapter *padapter = netdev_priv(ndev);
2621
2622 DBG_8723A("%s(%s)\n", __func__, ndev->name);
2623
2624 if (unlikely(skb->len < sizeof(struct ieee80211_radiotap_header)))
2625 goto fail;
2626
2627 rtap_hdr = (struct ieee80211_radiotap_header *)skb->data;
2628 if (unlikely(rtap_hdr->it_version))
2629 goto fail;
2630
2631 rtap_len = ieee80211_get_radiotap_len(skb->data);
2632 if (unlikely(skb->len < rtap_len))
2633 goto fail;
2634
2635 if (rtap_len != 14) {
2636 DBG_8723A("radiotap len (should be 14): %d\n", rtap_len);
2637 goto fail;
2638 }
2639
2640 /* Skip the ratio tap header */
2641 skb_pull(skb, rtap_len);
2642
2643 dot11_hdr = (struct ieee80211_hdr *)skb->data;
2644 /* Check if the QoS bit is set */
2645 if (ieee80211_is_data(dot11_hdr->frame_control)) {
2646 /* Check if this ia a Wireless Distribution System (WDS) frame
2647 * which has 4 MAC addresses
2648 */
2649 if (ieee80211_is_data_qos(dot11_hdr->frame_control))
2650 qos_len = IEEE80211_QOS_CTL_LEN;
2651 if (ieee80211_has_a4(dot11_hdr->frame_control))
2652 dot11_hdr_len += 6;
2653
2654 memcpy(dst_mac_addr, dot11_hdr->addr1, sizeof(dst_mac_addr));
2655 memcpy(src_mac_addr, dot11_hdr->addr2, sizeof(src_mac_addr));
2656
2657 /*
2658 * Skip the 802.11 header, QoS (if any) and SNAP,
2659 * but leave spaces for two MAC addresses
2660 */
2661 skb_pull(skb, dot11_hdr_len + qos_len + snap_len -
2662 ETH_ALEN * 2);
2663 pdata = (unsigned char *)skb->data;
2664 ether_addr_copy(pdata, dst_mac_addr);
2665 ether_addr_copy(pdata + ETH_ALEN, src_mac_addr);
2666
2667 DBG_8723A("should be eapol packet\n");
2668
2669 /* Use the real net device to transmit the packet */
2670 ret = rtw_xmit23a_entry23a(skb, padapter->pnetdev);
2671
2672 return ret;
2673
2674 } else if (ieee80211_is_action(dot11_hdr->frame_control)) {
2675 struct ieee80211_mgmt *mgmt;
2676 /* only for action frames */
2677 struct xmit_frame *pmgntframe;
2678 struct pkt_attrib *pattrib;
2679 unsigned char *pframe;
2680 /* u8 category, action, OUI_Subtype, dialogToken = 0; */
2681 /* unsigned char *frame_body; */
2682 struct xmit_priv *pxmitpriv = &padapter->xmitpriv;
2683 struct mlme_ext_priv *pmlmeext = &padapter->mlmeextpriv;
2684 u32 len = skb->len;
2685 u8 category, action;
2686
2687 mgmt = (struct ieee80211_mgmt *)dot11_hdr;
2688
2689 DBG_8723A("RTW_Tx:da =" MAC_FMT " via %s(%s)\n",
2690 MAC_ARG(mgmt->da), __func__, ndev->name);
2691 category = mgmt->u.action.category;
2692 action = mgmt->u.action.u.wme_action.action_code;
2693 DBG_8723A("RTW_Tx:category(%u), action(%u)\n",
2694 category, action);
2695
2696 /* starting alloc mgmt frame to dump it */
2697 pmgntframe = alloc_mgtxmitframe23a(pxmitpriv);
2698 if (pmgntframe == NULL)
2699 goto fail;
2700
2701 /* update attribute */
2702 pattrib = &pmgntframe->attrib;
2703 update_mgntframe_attrib23a(padapter, pattrib);
2704 pattrib->retry_ctrl = false;
2705
2706 memset(pmgntframe->buf_addr, 0, WLANHDR_OFFSET + TXDESC_OFFSET);
2707
2708 pframe = (u8 *)(pmgntframe->buf_addr) + TXDESC_OFFSET;
2709
2710 memcpy(pframe, skb->data, len);
2711 pattrib->pktlen = len;
2712
2713 /* update seq number */
2714 pmlmeext->mgnt_seq = le16_to_cpu(dot11_hdr->seq_ctrl) >> 4;
2715 pattrib->seqnum = pmlmeext->mgnt_seq;
2716 pmlmeext->mgnt_seq++;
2717
2718 pattrib->last_txcmdsz = pattrib->pktlen;
2719
2720 dump_mgntframe23a(padapter, pmgntframe);
2721 }
2722
2723 fail:
2724
2725 dev_kfree_skb(skb);
2726
2727 return 0;
2728 }
2729
2730 static int
2731 rtw_cfg80211_monitor_if_set_mac_address(struct net_device *ndev, void *addr)
2732 {
2733 int ret = 0;
2734
2735 DBG_8723A("%s\n", __func__);
2736
2737 return ret;
2738 }
2739
2740 static const struct net_device_ops rtw_cfg80211_monitor_if_ops = {
2741 .ndo_open = rtw_cfg80211_monitor_if_open,
2742 .ndo_stop = rtw_cfg80211_monitor_if_close,
2743 .ndo_start_xmit = rtw_cfg80211_monitor_if_xmit_entry,
2744 .ndo_set_mac_address = rtw_cfg80211_monitor_if_set_mac_address,
2745 };
2746
2747 static int rtw_cfg80211_add_monitor_if(struct rtw_adapter *padapter, char *name,
2748 struct net_device **ndev)
2749 {
2750 int ret = 0;
2751 struct net_device *mon_ndev = NULL;
2752 struct wireless_dev *mon_wdev = NULL;
2753 struct rtw_wdev_priv *pwdev_priv = wdev_to_priv(padapter->rtw_wdev);
2754
2755 if (!name) {
2756 DBG_8723A("%s(%s): without specific name\n",
2757 __func__, padapter->pnetdev->name);
2758 ret = -EINVAL;
2759 goto out;
2760 }
2761
2762 if (pwdev_priv->pmon_ndev) {
2763 DBG_8723A("%s(%s): monitor interface exist: %s\n", __func__,
2764 padapter->pnetdev->name, pwdev_priv->pmon_ndev->name);
2765 ret = -EBUSY;
2766 goto out;
2767 }
2768
2769 mon_ndev = alloc_etherdev(sizeof(struct rtw_adapter));
2770 if (!mon_ndev) {
2771 DBG_8723A("%s(%s): allocate ndev fail\n", __func__,
2772 padapter->pnetdev->name);
2773 ret = -ENOMEM;
2774 goto out;
2775 }
2776
2777 mon_ndev->type = ARPHRD_IEEE80211_RADIOTAP;
2778 strncpy(mon_ndev->name, name, IFNAMSIZ);
2779 mon_ndev->name[IFNAMSIZ - 1] = 0;
2780 mon_ndev->destructor = rtw_ndev_destructor;
2781
2782 mon_ndev->netdev_ops = &rtw_cfg80211_monitor_if_ops;
2783
2784 /* wdev */
2785 mon_wdev = kzalloc(sizeof(struct wireless_dev), GFP_KERNEL);
2786 if (!mon_wdev) {
2787 DBG_8723A("%s(%s): allocate mon_wdev fail\n", __func__,
2788 padapter->pnetdev->name);
2789 ret = -ENOMEM;
2790 goto out;
2791 }
2792
2793 mon_wdev->wiphy = padapter->rtw_wdev->wiphy;
2794 mon_wdev->netdev = mon_ndev;
2795 mon_wdev->iftype = NL80211_IFTYPE_MONITOR;
2796 mon_ndev->ieee80211_ptr = mon_wdev;
2797
2798 ret = register_netdevice(mon_ndev);
2799 if (ret) {
2800 goto out;
2801 }
2802
2803 *ndev = pwdev_priv->pmon_ndev = mon_ndev;
2804 memcpy(pwdev_priv->ifname_mon, name, IFNAMSIZ + 1);
2805
2806 out:
2807 if (ret) {
2808 kfree(mon_wdev);
2809 mon_wdev = NULL;
2810 }
2811
2812 if (ret && mon_ndev) {
2813 free_netdev(mon_ndev);
2814 *ndev = mon_ndev = NULL;
2815 }
2816
2817 return ret;
2818 }
2819
2820 static struct wireless_dev *
2821 cfg80211_rtw_add_virtual_intf(struct wiphy *wiphy, const char *name,
2822 enum nl80211_iftype type, u32 *flags,
2823 struct vif_params *params)
2824 {
2825 int ret = 0;
2826 struct net_device *ndev = NULL;
2827 struct rtw_adapter *padapter = wiphy_to_adapter(wiphy);
2828
2829 DBG_8723A("%s(%s): wiphy:%s, name:%s, type:%d\n", __func__,
2830 padapter->pnetdev->name, wiphy_name(wiphy), name, type);
2831
2832 switch (type) {
2833 case NL80211_IFTYPE_ADHOC:
2834 case NL80211_IFTYPE_AP_VLAN:
2835 case NL80211_IFTYPE_WDS:
2836 case NL80211_IFTYPE_MESH_POINT:
2837 ret = -ENODEV;
2838 break;
2839 case NL80211_IFTYPE_MONITOR:
2840 ret =
2841 rtw_cfg80211_add_monitor_if(padapter, (char *)name, &ndev);
2842 break;
2843
2844 case NL80211_IFTYPE_P2P_CLIENT:
2845 case NL80211_IFTYPE_STATION:
2846 ret = -ENODEV;
2847 break;
2848
2849 case NL80211_IFTYPE_P2P_GO:
2850 case NL80211_IFTYPE_AP:
2851 ret = -ENODEV;
2852 break;
2853 default:
2854 ret = -ENODEV;
2855 DBG_8723A("Unsupported interface type\n");
2856 break;
2857 }
2858
2859 DBG_8723A("%s(%s): ndev:%p, ret:%d\n", __func__,
2860 padapter->pnetdev->name,
2861 ndev, ret);
2862
2863 return ndev ? ndev->ieee80211_ptr : ERR_PTR(ret);
2864 }
2865
2866 static int cfg80211_rtw_del_virtual_intf(struct wiphy *wiphy,
2867 struct wireless_dev *wdev)
2868 {
2869 struct rtw_wdev_priv *pwdev_priv =
2870 (struct rtw_wdev_priv *)wiphy_priv(wiphy);
2871 struct net_device *ndev;
2872 ndev = wdev ? wdev->netdev : NULL;
2873
2874 if (!ndev)
2875 goto exit;
2876
2877 unregister_netdevice(ndev);
2878
2879 if (ndev == pwdev_priv->pmon_ndev) {
2880 pwdev_priv->pmon_ndev = NULL;
2881 pwdev_priv->ifname_mon[0] = '\0';
2882 DBG_8723A("%s(%s): remove monitor interface\n",
2883 __func__, ndev->name);
2884 }
2885
2886 exit:
2887 return 0;
2888 }
2889
2890 static int rtw_add_beacon(struct rtw_adapter *adapter, const u8 *head,
2891 size_t head_len, const u8 *tail, size_t tail_len)
2892 {
2893 int ret = 0;
2894 u8 *pbuf;
2895 uint len, ielen, wps_ielen = 0;
2896 struct mlme_priv *pmlmepriv = &adapter->mlmepriv;
2897 struct wlan_bssid_ex *bss = &pmlmepriv->cur_network.network;
2898 const struct ieee80211_mgmt *mgmt = (struct ieee80211_mgmt *)head;
2899 struct ieee80211_mgmt *tmpmgmt;
2900 /* struct sta_priv *pstapriv = &padapter->stapriv; */
2901
2902 DBG_8723A("%s beacon_head_len =%zu, beacon_tail_len =%zu\n",
2903 __func__, head_len, tail_len);
2904
2905 if (check_fwstate(pmlmepriv, WIFI_AP_STATE) != true)
2906 return -EINVAL;
2907
2908 if (head_len < offsetof(struct ieee80211_mgmt, u.beacon.variable))
2909 return -EINVAL;
2910
2911 pbuf = kzalloc(head_len + tail_len, GFP_KERNEL);
2912 if (!pbuf)
2913 return -ENOMEM;
2914 tmpmgmt = (struct ieee80211_mgmt *)pbuf;
2915
2916 bss->beacon_interval = get_unaligned_le16(&mgmt->u.beacon.beacon_int);
2917 bss->capability = get_unaligned_le16(&mgmt->u.beacon.capab_info);
2918 bss->tsf = get_unaligned_le64(&mgmt->u.beacon.timestamp);
2919
2920 /* 24 = beacon header len. */
2921 memcpy(pbuf, (void *)head, head_len);
2922 memcpy(pbuf + head_len, (void *)tail, tail_len);
2923
2924 len = head_len + tail_len;
2925 ielen = len - offsetof(struct ieee80211_mgmt, u.beacon.variable);
2926 /* check wps ie if inclued */
2927 if (cfg80211_find_vendor_ie(WLAN_OUI_MICROSOFT,
2928 WLAN_OUI_TYPE_MICROSOFT_WPS,
2929 tmpmgmt->u.beacon.variable, ielen))
2930 DBG_8723A("add bcn, wps_ielen =%d\n", wps_ielen);
2931
2932 /* pbss_network->IEs will not include p2p_ie, wfd ie */
2933 rtw_ies_remove_ie23a(tmpmgmt->u.beacon.variable, &ielen, 0,
2934 WLAN_EID_VENDOR_SPECIFIC, P2P_OUI23A, 4);
2935 rtw_ies_remove_ie23a(tmpmgmt->u.beacon.variable, &ielen, 0,
2936 WLAN_EID_VENDOR_SPECIFIC, WFD_OUI23A, 4);
2937
2938 len = ielen + offsetof(struct ieee80211_mgmt, u.beacon.variable);
2939 if (rtw_check_beacon_data23a(adapter, tmpmgmt, len) == _SUCCESS) {
2940 ret = 0;
2941 } else {
2942 ret = -EINVAL;
2943 }
2944
2945 kfree(pbuf);
2946
2947 return ret;
2948 }
2949
2950 static int cfg80211_rtw_start_ap(struct wiphy *wiphy, struct net_device *ndev,
2951 struct cfg80211_ap_settings *settings)
2952 {
2953 int ret = 0;
2954 struct rtw_adapter *adapter = wiphy_to_adapter(wiphy);
2955
2956 DBG_8723A("%s(%s): hidden_ssid:%d, auth_type:%d\n",
2957 __func__, ndev->name, settings->hidden_ssid,
2958 settings->auth_type);
2959
2960 ret = rtw_add_beacon(adapter, settings->beacon.head,
2961 settings->beacon.head_len, settings->beacon.tail,
2962 settings->beacon.tail_len);
2963
2964 adapter->mlmeextpriv.mlmext_info.hidden_ssid_mode =
2965 settings->hidden_ssid;
2966
2967 if (settings->ssid && settings->ssid_len) {
2968 struct wlan_bssid_ex *pbss_network =
2969 &adapter->mlmepriv.cur_network.network;
2970 struct wlan_bssid_ex *pbss_network_ext =
2971 &adapter->mlmeextpriv.mlmext_info.network;
2972
2973 memcpy(pbss_network->Ssid.ssid, (void *)settings->ssid,
2974 settings->ssid_len);
2975 pbss_network->Ssid.ssid_len = settings->ssid_len;
2976 memcpy(pbss_network_ext->Ssid.ssid, (void *)settings->ssid,
2977 settings->ssid_len);
2978 pbss_network_ext->Ssid.ssid_len = settings->ssid_len;
2979 }
2980
2981 return ret;
2982 }
2983
2984 static int cfg80211_rtw_change_beacon(struct wiphy *wiphy,
2985 struct net_device *ndev,
2986 struct cfg80211_beacon_data *info)
2987 {
2988 int ret = 0;
2989 struct rtw_adapter *adapter = wiphy_to_adapter(wiphy);
2990
2991 DBG_8723A("%s(%s)\n", __func__, ndev->name);
2992
2993 ret = rtw_add_beacon(adapter, info->head, info->head_len, info->tail,
2994 info->tail_len);
2995
2996 return ret;
2997 }
2998
2999 static int cfg80211_rtw_stop_ap(struct wiphy *wiphy, struct net_device *ndev)
3000 {
3001 DBG_8723A("%s(%s)\n", __func__, ndev->name);
3002 return 0;
3003 }
3004
3005 static int cfg80211_rtw_add_station(struct wiphy *wiphy,
3006 struct net_device *ndev, const u8 *mac,
3007 struct station_parameters *params)
3008 {
3009 DBG_8723A("%s(%s)\n", __func__, ndev->name);
3010
3011 return 0;
3012 }
3013
3014 static int cfg80211_rtw_del_station(struct wiphy *wiphy,
3015 struct net_device *ndev, const u8 *mac)
3016 {
3017 int ret = 0;
3018 struct list_head *phead, *plist, *ptmp;
3019 u8 updated = 0;
3020 struct sta_info *psta;
3021 struct rtw_adapter *padapter = netdev_priv(ndev);
3022 struct mlme_priv *pmlmepriv = &padapter->mlmepriv;
3023 struct sta_priv *pstapriv = &padapter->stapriv;
3024
3025 DBG_8723A("+%s(%s)\n", __func__, ndev->name);
3026
3027 if (check_fwstate(pmlmepriv, (_FW_LINKED | WIFI_AP_STATE)) != true) {
3028 DBG_8723A("%s, fw_state != FW_LINKED|WIFI_AP_STATE\n",
3029 __func__);
3030 return -EINVAL;
3031 }
3032
3033 if (!mac) {
3034 DBG_8723A("flush all sta, and cam_entry\n");
3035
3036 flush_all_cam_entry23a(padapter); /* clear CAM */
3037
3038 ret = rtw_sta_flush23a(padapter);
3039
3040 return ret;
3041 }
3042
3043 DBG_8723A("free sta macaddr =" MAC_FMT "\n", MAC_ARG(mac));
3044
3045 if (is_broadcast_ether_addr(mac))
3046 return -EINVAL;
3047
3048 spin_lock_bh(&pstapriv->asoc_list_lock);
3049
3050 phead = &pstapriv->asoc_list;
3051
3052 /* check asoc_queue */
3053 list_for_each_safe(plist, ptmp, phead) {
3054 psta = container_of(plist, struct sta_info, asoc_list);
3055
3056 if (ether_addr_equal(mac, psta->hwaddr)) {
3057 if (psta->dot8021xalg == 1 &&
3058 psta->bpairwise_key_installed == false) {
3059 DBG_8723A("%s, sta's dot8021xalg = 1 and "
3060 "key_installed = false\n", __func__);
3061 } else {
3062 DBG_8723A("free psta =%p, aid =%d\n", psta,
3063 psta->aid);
3064
3065 list_del_init(&psta->asoc_list);
3066 pstapriv->asoc_list_cnt--;
3067
3068 /* spin_unlock_bh(&pstapriv->asoc_list_lock); */
3069 updated =
3070 ap_free_sta23a(padapter, psta, true,
3071 WLAN_REASON_DEAUTH_LEAVING);
3072 /* spin_lock_bh(&pstapriv->asoc_list_lock); */
3073
3074 psta = NULL;
3075
3076 break;
3077 }
3078 }
3079 }
3080
3081 spin_unlock_bh(&pstapriv->asoc_list_lock);
3082
3083 associated_clients_update23a(padapter, updated);
3084
3085 DBG_8723A("-%s(%s)\n", __func__, ndev->name);
3086
3087 return ret;
3088 }
3089
3090 static int cfg80211_rtw_change_station(struct wiphy *wiphy,
3091 struct net_device *ndev, const u8 *mac,
3092 struct station_parameters *params)
3093 {
3094 DBG_8723A("%s(%s)\n", __func__, ndev->name);
3095 return 0;
3096 }
3097
3098 static int cfg80211_rtw_dump_station(struct wiphy *wiphy,
3099 struct net_device *ndev, int idx, u8 *mac,
3100 struct station_info *sinfo)
3101 {
3102 DBG_8723A("%s(%s)\n", __func__, ndev->name);
3103
3104 /* TODO: dump scanned queue */
3105
3106 return -ENOENT;
3107 }
3108
3109 static int cfg80211_rtw_change_bss(struct wiphy *wiphy, struct net_device *ndev,
3110 struct bss_parameters *params)
3111 {
3112 DBG_8723A("%s(%s)\n", __func__, ndev->name);
3113 return 0;
3114 }
3115 #endif /* CONFIG_8723AU_AP_MODE */
3116
3117 static int _cfg80211_rtw_mgmt_tx(struct rtw_adapter *padapter, u8 tx_ch,
3118 const u8 *buf, size_t len)
3119 {
3120 struct xmit_frame *pmgntframe;
3121 struct pkt_attrib *pattrib;
3122 unsigned char *pframe;
3123 int ret = _FAIL;
3124 struct ieee80211_hdr *pwlanhdr;
3125 struct xmit_priv *pxmitpriv = &padapter->xmitpriv;
3126 struct mlme_ext_priv *pmlmeext = &padapter->mlmeextpriv;
3127
3128 if (_FAIL == rtw_pwr_wakeup(padapter)) {
3129 ret = -EFAULT;
3130 goto exit;
3131 }
3132
3133 rtw_set_scan_deny(padapter, 1000);
3134
3135 rtw_scan_abort23a(padapter);
3136
3137 if (tx_ch != rtw_get_oper_ch23a(padapter)) {
3138 if (!check_fwstate(&padapter->mlmepriv, _FW_LINKED))
3139 pmlmeext->cur_channel = tx_ch;
3140 set_channel_bwmode23a(padapter, tx_ch,
3141 HAL_PRIME_CHNL_OFFSET_DONT_CARE,
3142 HT_CHANNEL_WIDTH_20);
3143 }
3144
3145 /* starting alloc mgmt frame to dump it */
3146 pmgntframe = alloc_mgtxmitframe23a(pxmitpriv);
3147 if (!pmgntframe) {
3148 /* ret = -ENOMEM; */
3149 ret = _FAIL;
3150 goto exit;
3151 }
3152
3153 /* update attribute */
3154 pattrib = &pmgntframe->attrib;
3155 update_mgntframe_attrib23a(padapter, pattrib);
3156 pattrib->retry_ctrl = false;
3157
3158 memset(pmgntframe->buf_addr, 0, WLANHDR_OFFSET + TXDESC_OFFSET);
3159
3160 pframe = (u8 *) (pmgntframe->buf_addr) + TXDESC_OFFSET;
3161
3162 memcpy(pframe, (void *)buf, len);
3163 pattrib->pktlen = len;
3164
3165 pwlanhdr = (struct ieee80211_hdr *)pframe;
3166 /* update seq number */
3167 pmlmeext->mgnt_seq = le16_to_cpu(pwlanhdr->seq_ctrl) >> 4;
3168 pattrib->seqnum = pmlmeext->mgnt_seq;
3169 pmlmeext->mgnt_seq++;
3170
3171 pattrib->last_txcmdsz = pattrib->pktlen;
3172
3173 ret = dump_mgntframe23a_and_wait_ack23a(padapter, pmgntframe);
3174
3175 if (ret != _SUCCESS)
3176 DBG_8723A("%s, ack == false\n", __func__);
3177 else
3178 DBG_8723A("%s, ack == true\n", __func__);
3179
3180 exit:
3181
3182 DBG_8723A("%s, ret =%d\n", __func__, ret);
3183
3184 return ret;
3185 }
3186
3187 static int cfg80211_rtw_mgmt_tx(struct wiphy *wiphy, struct wireless_dev *wdev,
3188 struct cfg80211_mgmt_tx_params *params,
3189 u64 *cookie)
3190 {
3191 struct rtw_adapter *padapter =
3192 (struct rtw_adapter *)wiphy_to_adapter(wiphy);
3193 int ret = 0;
3194 int tx_ret;
3195 u32 dump_limit = RTW_MAX_MGMT_TX_CNT;
3196 u32 dump_cnt = 0;
3197 bool ack = true;
3198 u8 category, action;
3199 unsigned long start = jiffies;
3200 size_t len = params->len;
3201 struct ieee80211_channel *chan = params->chan;
3202 const u8 *buf = params->buf;
3203 struct ieee80211_mgmt *hdr = (struct ieee80211_mgmt *)buf;
3204 u8 tx_ch = (u8) ieee80211_frequency_to_channel(chan->center_freq);
3205
3206 if (!ieee80211_is_action(hdr->frame_control))
3207 return -EINVAL;
3208
3209 /* cookie generation */
3210 *cookie = (unsigned long)buf;
3211
3212 DBG_8723A("%s(%s): len =%zu, ch =%d\n", __func__,
3213 padapter->pnetdev->name, len, tx_ch);
3214
3215 /* indicate ack before issue frame to avoid racing with rsp frame */
3216 cfg80211_mgmt_tx_status(padapter->rtw_wdev, *cookie, buf, len, ack,
3217 GFP_KERNEL);
3218
3219 DBG_8723A("RTW_Tx:tx_ch =%d, da =" MAC_FMT "\n", tx_ch,
3220 MAC_ARG(hdr->da));
3221 category = hdr->u.action.category;
3222 action = hdr->u.action.u.wme_action.action_code;
3223 DBG_8723A("RTW_Tx:category(%u), action(%u)\n", category, action);
3224
3225 do {
3226 dump_cnt++;
3227 tx_ret = _cfg80211_rtw_mgmt_tx(padapter, tx_ch, buf, len);
3228 } while (dump_cnt < dump_limit && tx_ret != _SUCCESS);
3229
3230 if (tx_ret != _SUCCESS || dump_cnt > 1) {
3231 DBG_8723A("%s(%s): %s (%d/%d) in %d ms\n",
3232 __func__, padapter->pnetdev->name,
3233 tx_ret == _SUCCESS ? "OK" : "FAIL", dump_cnt,
3234 dump_limit, jiffies_to_msecs(jiffies - start));
3235 }
3236
3237 return ret;
3238 }
3239
3240 static void cfg80211_rtw_mgmt_frame_register(struct wiphy *wiphy,
3241 struct wireless_dev *wdev,
3242 u16 frame_type, bool reg)
3243 {
3244 if (frame_type != (IEEE80211_FTYPE_MGMT | IEEE80211_STYPE_PROBE_REQ))
3245 return;
3246
3247 return;
3248 }
3249
3250 static struct cfg80211_ops rtw_cfg80211_ops = {
3251 .change_virtual_intf = cfg80211_rtw_change_iface,
3252 .add_key = cfg80211_rtw_add_key,
3253 .get_key = cfg80211_rtw_get_key,
3254 .del_key = cfg80211_rtw_del_key,
3255 .set_default_key = cfg80211_rtw_set_default_key,
3256 .get_station = cfg80211_rtw_get_station,
3257 .scan = cfg80211_rtw_scan,
3258 .set_wiphy_params = cfg80211_rtw_set_wiphy_params,
3259 .connect = cfg80211_rtw_connect,
3260 .disconnect = cfg80211_rtw_disconnect,
3261 .join_ibss = cfg80211_rtw_join_ibss,
3262 .leave_ibss = cfg80211_rtw_leave_ibss,
3263 .set_tx_power = cfg80211_rtw_set_txpower,
3264 .get_tx_power = cfg80211_rtw_get_txpower,
3265 .set_power_mgmt = cfg80211_rtw_set_power_mgmt,
3266 .set_pmksa = cfg80211_rtw_set_pmksa,
3267 .del_pmksa = cfg80211_rtw_del_pmksa,
3268 .flush_pmksa = cfg80211_rtw_flush_pmksa,
3269
3270 #ifdef CONFIG_8723AU_AP_MODE
3271 .add_virtual_intf = cfg80211_rtw_add_virtual_intf,
3272 .del_virtual_intf = cfg80211_rtw_del_virtual_intf,
3273
3274 .start_ap = cfg80211_rtw_start_ap,
3275 .change_beacon = cfg80211_rtw_change_beacon,
3276 .stop_ap = cfg80211_rtw_stop_ap,
3277
3278 .add_station = cfg80211_rtw_add_station,
3279 .del_station = cfg80211_rtw_del_station,
3280 .change_station = cfg80211_rtw_change_station,
3281 .dump_station = cfg80211_rtw_dump_station,
3282 .change_bss = cfg80211_rtw_change_bss,
3283 #endif /* CONFIG_8723AU_AP_MODE */
3284
3285 .mgmt_tx = cfg80211_rtw_mgmt_tx,
3286 .mgmt_frame_register = cfg80211_rtw_mgmt_frame_register,
3287 };
3288
3289 static void rtw_cfg80211_init_ht_capab(struct ieee80211_sta_ht_cap *ht_cap,
3290 enum ieee80211_band band, u8 rf_type)
3291 {
3292
3293 #define MAX_BIT_RATE_40MHZ_MCS15 300 /* Mbps */
3294 #define MAX_BIT_RATE_40MHZ_MCS7 150 /* Mbps */
3295
3296 ht_cap->ht_supported = true;
3297
3298 ht_cap->cap = IEEE80211_HT_CAP_SUP_WIDTH_20_40 |
3299 IEEE80211_HT_CAP_SGI_40 | IEEE80211_HT_CAP_SGI_20 |
3300 IEEE80211_HT_CAP_DSSSCCK40 | IEEE80211_HT_CAP_MAX_AMSDU;
3301
3302 /*
3303 *Maximum length of AMPDU that the STA can receive.
3304 *Length = 2 ^ (13 + max_ampdu_length_exp) - 1 (octets)
3305 */
3306 ht_cap->ampdu_factor = IEEE80211_HT_MAX_AMPDU_64K;
3307
3308 /*Minimum MPDU start spacing , */
3309 ht_cap->ampdu_density = IEEE80211_HT_MPDU_DENSITY_16;
3310
3311 ht_cap->mcs.tx_params = IEEE80211_HT_MCS_TX_DEFINED;
3312
3313 /*
3314 *hw->wiphy->bands[IEEE80211_BAND_2GHZ]
3315 *base on ant_num
3316 *rx_mask: RX mask
3317 *if rx_ant = 1 rx_mask[0]= 0xff;==>MCS0-MCS7
3318 *if rx_ant = 2 rx_mask[1]= 0xff;==>MCS8-MCS15
3319 *if rx_ant >= 3 rx_mask[2]= 0xff;
3320 *if BW_40 rx_mask[4]= 0x01;
3321 *highest supported RX rate
3322 */
3323 if (rf_type == RF_1T1R) {
3324 ht_cap->mcs.rx_mask[0] = 0xFF;
3325 ht_cap->mcs.rx_mask[1] = 0x00;
3326 ht_cap->mcs.rx_mask[4] = 0x01;
3327
3328 ht_cap->mcs.rx_highest = MAX_BIT_RATE_40MHZ_MCS7;
3329 } else if ((rf_type == RF_1T2R) || (rf_type == RF_2T2R)) {
3330 ht_cap->mcs.rx_mask[0] = 0xFF;
3331 ht_cap->mcs.rx_mask[1] = 0xFF;
3332 ht_cap->mcs.rx_mask[4] = 0x01;
3333
3334 ht_cap->mcs.rx_highest = MAX_BIT_RATE_40MHZ_MCS15;
3335 } else {
3336 DBG_8723A("%s, error rf_type =%d\n", __func__, rf_type);
3337 }
3338
3339 }
3340
3341 void rtw_cfg80211_init_wiphy(struct rtw_adapter *padapter)
3342 {
3343 u8 rf_type;
3344 struct ieee80211_supported_band *bands;
3345 struct wireless_dev *pwdev = padapter->rtw_wdev;
3346 struct wiphy *wiphy = pwdev->wiphy;
3347
3348 rf_type = rtl8723a_get_rf_type(padapter);
3349
3350 DBG_8723A("%s:rf_type =%d\n", __func__, rf_type);
3351
3352 /* if (padapter->registrypriv.wireless_mode & WIRELESS_11G) */
3353 {
3354 bands = wiphy->bands[IEEE80211_BAND_2GHZ];
3355 if (bands)
3356 rtw_cfg80211_init_ht_capab(&bands->ht_cap,
3357 IEEE80211_BAND_2GHZ,
3358 rf_type);
3359 }
3360
3361 /* if (padapter->registrypriv.wireless_mode & WIRELESS_11A) */
3362 {
3363 bands = wiphy->bands[IEEE80211_BAND_5GHZ];
3364 if (bands)
3365 rtw_cfg80211_init_ht_capab(&bands->ht_cap,
3366 IEEE80211_BAND_5GHZ,
3367 rf_type);
3368 }
3369 }
3370
3371 static void rtw_cfg80211_preinit_wiphy(struct rtw_adapter *padapter,
3372 struct wiphy *wiphy)
3373 {
3374 wiphy->signal_type = CFG80211_SIGNAL_TYPE_MBM;
3375
3376 wiphy->max_scan_ssids = RTW_SSID_SCAN_AMOUNT;
3377 wiphy->max_scan_ie_len = IEEE80211_MAX_DATA_LEN;
3378 wiphy->max_num_pmkids = RTW_MAX_NUM_PMKIDS;
3379
3380 wiphy->max_remain_on_channel_duration =
3381 RTW_MAX_REMAIN_ON_CHANNEL_DURATION;
3382
3383 wiphy->interface_modes = BIT(NL80211_IFTYPE_STATION) |
3384 BIT(NL80211_IFTYPE_ADHOC) |
3385 #ifdef CONFIG_8723AU_AP_MODE
3386 BIT(NL80211_IFTYPE_AP) | BIT(NL80211_IFTYPE_MONITOR) |
3387 #endif
3388 0;
3389
3390 #ifdef CONFIG_8723AU_AP_MODE
3391 wiphy->mgmt_stypes = rtw_cfg80211_default_mgmt_stypes;
3392 #endif /* CONFIG_8723AU_AP_MODE */
3393
3394 wiphy->software_iftypes |= BIT(NL80211_IFTYPE_MONITOR);
3395
3396 /*
3397 wiphy->iface_combinations = &rtw_combinations;
3398 wiphy->n_iface_combinations = 1;
3399 */
3400
3401 wiphy->cipher_suites = rtw_cipher_suites;
3402 wiphy->n_cipher_suites = ARRAY_SIZE(rtw_cipher_suites);
3403
3404 /* if (padapter->registrypriv.wireless_mode & WIRELESS_11G) */
3405 wiphy->bands[IEEE80211_BAND_2GHZ] =
3406 rtw_spt_band_alloc(IEEE80211_BAND_2GHZ);
3407 /* if (padapter->registrypriv.wireless_mode & WIRELESS_11A) */
3408 wiphy->bands[IEEE80211_BAND_5GHZ] =
3409 rtw_spt_band_alloc(IEEE80211_BAND_5GHZ);
3410
3411 wiphy->flags |= WIPHY_FLAG_HAS_REMAIN_ON_CHANNEL;
3412 wiphy->flags |= WIPHY_FLAG_OFFCHAN_TX | WIPHY_FLAG_HAVE_AP_SME;
3413
3414 if (padapter->registrypriv.power_mgnt != PS_MODE_ACTIVE)
3415 wiphy->flags |= WIPHY_FLAG_PS_ON_BY_DEFAULT;
3416 else
3417 wiphy->flags &= ~WIPHY_FLAG_PS_ON_BY_DEFAULT;
3418 }
3419
3420 int rtw_wdev_alloc(struct rtw_adapter *padapter, struct device *dev)
3421 {
3422 int ret = 0;
3423 struct wiphy *wiphy;
3424 struct wireless_dev *wdev;
3425 struct rtw_wdev_priv *pwdev_priv;
3426 struct net_device *pnetdev = padapter->pnetdev;
3427
3428 DBG_8723A("%s(padapter =%p)\n", __func__, padapter);
3429
3430 /* wiphy */
3431 wiphy = wiphy_new(&rtw_cfg80211_ops, sizeof(struct rtw_wdev_priv));
3432 if (!wiphy) {
3433 DBG_8723A("Couldn't allocate wiphy device\n");
3434 ret = -ENOMEM;
3435 goto exit;
3436 }
3437
3438 /* wdev */
3439 wdev = kzalloc(sizeof(struct wireless_dev), GFP_KERNEL);
3440 if (!wdev) {
3441 DBG_8723A("Couldn't allocate wireless device\n");
3442 ret = -ENOMEM;
3443 goto free_wiphy;
3444 }
3445
3446 set_wiphy_dev(wiphy, dev);
3447 rtw_cfg80211_preinit_wiphy(padapter, wiphy);
3448
3449 ret = wiphy_register(wiphy);
3450 if (ret < 0) {
3451 DBG_8723A("Couldn't register wiphy device\n");
3452 goto free_wdev;
3453 }
3454
3455 wdev->wiphy = wiphy;
3456 wdev->netdev = pnetdev;
3457 /* wdev->iftype = NL80211_IFTYPE_STATION; */
3458 /* for rtw_setopmode_cmd23a() in cfg80211_rtw_change_iface() */
3459 wdev->iftype = NL80211_IFTYPE_MONITOR;
3460 padapter->rtw_wdev = wdev;
3461 pnetdev->ieee80211_ptr = wdev;
3462
3463 /* init pwdev_priv */
3464 pwdev_priv = wdev_to_priv(wdev);
3465 pwdev_priv->rtw_wdev = wdev;
3466 pwdev_priv->pmon_ndev = NULL;
3467 pwdev_priv->ifname_mon[0] = '\0';
3468 pwdev_priv->padapter = padapter;
3469 pwdev_priv->scan_request = NULL;
3470 spin_lock_init(&pwdev_priv->scan_req_lock);
3471
3472 pwdev_priv->p2p_enabled = false;
3473
3474 if (padapter->registrypriv.power_mgnt != PS_MODE_ACTIVE)
3475 pwdev_priv->power_mgmt = true;
3476 else
3477 pwdev_priv->power_mgmt = false;
3478
3479 return ret;
3480 free_wdev:
3481 kfree(wdev);
3482 free_wiphy:
3483 wiphy_free(wiphy);
3484 exit:
3485 return ret;
3486 }
3487
3488 void rtw_wdev_free(struct wireless_dev *wdev)
3489 {
3490 DBG_8723A("%s(wdev =%p)\n", __func__, wdev);
3491
3492 if (!wdev)
3493 return;
3494
3495 kfree(wdev->wiphy->bands[IEEE80211_BAND_2GHZ]);
3496 kfree(wdev->wiphy->bands[IEEE80211_BAND_5GHZ]);
3497
3498 wiphy_free(wdev->wiphy);
3499
3500 kfree(wdev);
3501 }
3502
3503 void rtw_wdev_unregister(struct wireless_dev *wdev)
3504 {
3505 struct rtw_wdev_priv *pwdev_priv;
3506
3507 DBG_8723A("%s(wdev =%p)\n", __func__, wdev);
3508
3509 if (!wdev)
3510 return;
3511
3512 pwdev_priv = wdev_to_priv(wdev);
3513
3514 rtw_cfg80211_indicate_scan_done(pwdev_priv, true);
3515
3516 if (pwdev_priv->pmon_ndev) {
3517 DBG_8723A("%s, unregister monitor interface\n", __func__);
3518 unregister_netdev(pwdev_priv->pmon_ndev);
3519 }
3520
3521 wiphy_unregister(wdev->wiphy);
3522 }
This page took 0.10207 seconds and 4 git commands to generate.