1 /******************************************************************************
3 * Copyright(c) 2007 - 2012 Realtek Corporation. All rights reserved.
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.
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
14 * You should have received a copy of the GNU General Public License along with
15 * this program; if not, write to the Free Software Foundation, Inc.,
16 * 51 Franklin Street, Fifth Floor, Boston, MA 02110, USA
19 ******************************************************************************/
20 #define _IOCTL_LINUX_C_
22 #include <linux/ieee80211.h>
24 #include <osdep_service.h>
25 #include <drv_types.h>
26 #include <wlan_bssdef.h>
27 #include <rtw_debug.h>
30 #include <rtw_mlme_ext.h>
31 #include <rtw_ioctl.h>
32 #include <rtw_ioctl_set.h>
33 #include <rtl8188e_hal.h>
36 #include <linux/vmalloc.h>
37 #include <linux/etherdevice.h>
39 #include "osdep_intf.h"
41 #define RTL_IOCTL_WPA_SUPPLICANT (SIOCIWFIRSTPRIV + 30)
43 #define SCAN_ITEM_SIZE 768
44 #define MAX_CUSTOM_LEN 64
48 #define WEXT_CSCAN_AMOUNT 9
49 #define WEXT_CSCAN_BUF_LEN 360
50 #define WEXT_CSCAN_HEADER "CSCAN S\x01\x00\x00S\x00"
51 #define WEXT_CSCAN_HEADER_SIZE 12
52 #define WEXT_CSCAN_SSID_SECTION 'S'
53 #define WEXT_CSCAN_CHANNEL_SECTION 'C'
54 #define WEXT_CSCAN_NPROBE_SECTION 'N'
55 #define WEXT_CSCAN_ACTV_DWELL_SECTION 'A'
56 #define WEXT_CSCAN_PASV_DWELL_SECTION 'P'
57 #define WEXT_CSCAN_HOME_DWELL_SECTION 'H'
58 #define WEXT_CSCAN_TYPE_SECTION 'T'
60 static u32 rtw_rates
[] = {1000000, 2000000, 5500000, 11000000,
61 6000000, 9000000, 12000000, 18000000, 24000000, 36000000,
64 static const char * const iw_operation_mode
[] = {
65 "Auto", "Ad-Hoc", "Managed", "Master", "Repeater",
66 "Secondary", "Monitor"
69 void indicate_wx_scan_complete_event(struct adapter
*padapter
)
71 union iwreq_data wrqu
;
73 memset(&wrqu
, 0, sizeof(union iwreq_data
));
74 wireless_send_event(padapter
->pnetdev
, SIOCGIWSCAN
, &wrqu
, NULL
);
77 void rtw_indicate_wx_assoc_event(struct adapter
*padapter
)
79 union iwreq_data wrqu
;
80 struct mlme_priv
*pmlmepriv
= &padapter
->mlmepriv
;
82 memset(&wrqu
, 0, sizeof(union iwreq_data
));
84 wrqu
.ap_addr
.sa_family
= ARPHRD_ETHER
;
86 memcpy(wrqu
.ap_addr
.sa_data
, pmlmepriv
->cur_network
.network
.MacAddress
, ETH_ALEN
);
88 DBG_88E_LEVEL(_drv_always_
, "assoc success\n");
89 wireless_send_event(padapter
->pnetdev
, SIOCGIWAP
, &wrqu
, NULL
);
92 void rtw_indicate_wx_disassoc_event(struct adapter
*padapter
)
94 union iwreq_data wrqu
;
96 memset(&wrqu
, 0, sizeof(union iwreq_data
));
98 wrqu
.ap_addr
.sa_family
= ARPHRD_ETHER
;
99 eth_zero_addr(wrqu
.ap_addr
.sa_data
);
101 DBG_88E_LEVEL(_drv_always_
, "indicate disassoc\n");
102 wireless_send_event(padapter
->pnetdev
, SIOCGIWAP
, &wrqu
, NULL
);
105 static char *translate_scan(struct adapter
*padapter
,
106 struct iw_request_info
*info
,
107 struct wlan_network
*pnetwork
,
108 char *start
, char *stop
)
110 struct mlme_priv
*pmlmepriv
= &(padapter
->mlmepriv
);
115 char custom
[MAX_CUSTOM_LEN
];
117 u16 max_rate
= 0, rate
, ht_cap
= false;
119 u8 bw_40MHz
= 0, short_GI
= 0;
125 iwe
.u
.ap_addr
.sa_family
= ARPHRD_ETHER
;
127 memcpy(iwe
.u
.ap_addr
.sa_data
, pnetwork
->network
.MacAddress
, ETH_ALEN
);
128 start
= iwe_stream_add_event(info
, start
, stop
, &iwe
, IW_EV_ADDR_LEN
);
131 iwe
.cmd
= SIOCGIWESSID
;
132 iwe
.u
.data
.flags
= 1;
133 iwe
.u
.data
.length
= min_t(u16
, pnetwork
->network
.Ssid
.SsidLength
, 32);
134 start
= iwe_stream_add_point(info
, start
, stop
, &iwe
, pnetwork
->network
.Ssid
.Ssid
);
136 /* parsing HT_CAP_IE */
137 p
= rtw_get_ie(&pnetwork
->network
.IEs
[12], _HT_CAPABILITY_IE_
, &ht_ielen
, pnetwork
->network
.IELength
-12);
139 if (p
&& ht_ielen
> 0) {
140 struct rtw_ieee80211_ht_cap
*pht_capie
;
142 pht_capie
= (struct rtw_ieee80211_ht_cap
*)(p
+2);
143 memcpy(&mcs_rate
, pht_capie
->supp_mcs_set
, 2);
144 bw_40MHz
= (pht_capie
->cap_info
&IEEE80211_HT_CAP_SUP_WIDTH
) ? 1 : 0;
145 short_GI
= (pht_capie
->cap_info
&(IEEE80211_HT_CAP_SGI_20
|IEEE80211_HT_CAP_SGI_40
)) ? 1 : 0;
148 /* Add the protocol name */
149 iwe
.cmd
= SIOCGIWNAME
;
150 if ((rtw_is_cckratesonly_included((u8
*)&pnetwork
->network
.SupportedRates
))) {
152 snprintf(iwe
.u
.name
, IFNAMSIZ
, "IEEE 802.11bn");
154 snprintf(iwe
.u
.name
, IFNAMSIZ
, "IEEE 802.11b");
155 } else if ((rtw_is_cckrates_included((u8
*)&pnetwork
->network
.SupportedRates
))) {
157 snprintf(iwe
.u
.name
, IFNAMSIZ
, "IEEE 802.11bgn");
159 snprintf(iwe
.u
.name
, IFNAMSIZ
, "IEEE 802.11bg");
161 if (pnetwork
->network
.Configuration
.DSConfig
> 14) {
163 snprintf(iwe
.u
.name
, IFNAMSIZ
, "IEEE 802.11an");
165 snprintf(iwe
.u
.name
, IFNAMSIZ
, "IEEE 802.11a");
168 snprintf(iwe
.u
.name
, IFNAMSIZ
, "IEEE 802.11gn");
170 snprintf(iwe
.u
.name
, IFNAMSIZ
, "IEEE 802.11g");
174 start
= iwe_stream_add_event(info
, start
, stop
, &iwe
, IW_EV_CHAR_LEN
);
177 iwe
.cmd
= SIOCGIWMODE
;
178 memcpy(&le_tmp
, rtw_get_capability_from_ie(pnetwork
->network
.IEs
), 2);
180 cap
= le16_to_cpu(le_tmp
);
182 if (!WLAN_CAPABILITY_IS_STA_BSS(cap
)) {
183 if (cap
& WLAN_CAPABILITY_ESS
)
184 iwe
.u
.mode
= IW_MODE_MASTER
;
186 iwe
.u
.mode
= IW_MODE_ADHOC
;
188 start
= iwe_stream_add_event(info
, start
, stop
, &iwe
, IW_EV_UINT_LEN
);
191 if (pnetwork
->network
.Configuration
.DSConfig
< 1)
192 pnetwork
->network
.Configuration
.DSConfig
= 1;
194 /* Add frequency/channel */
195 iwe
.cmd
= SIOCGIWFREQ
;
196 iwe
.u
.freq
.m
= rtw_ch2freq(pnetwork
->network
.Configuration
.DSConfig
) * 100000;
198 iwe
.u
.freq
.i
= pnetwork
->network
.Configuration
.DSConfig
;
199 start
= iwe_stream_add_event(info
, start
, stop
, &iwe
, IW_EV_FREQ_LEN
);
201 /* Add encryption capability */
202 iwe
.cmd
= SIOCGIWENCODE
;
203 if (cap
& WLAN_CAPABILITY_PRIVACY
)
204 iwe
.u
.data
.flags
= IW_ENCODE_ENABLED
| IW_ENCODE_NOKEY
;
206 iwe
.u
.data
.flags
= IW_ENCODE_DISABLED
;
207 iwe
.u
.data
.length
= 0;
208 start
= iwe_stream_add_point(info
, start
, stop
, &iwe
, pnetwork
->network
.Ssid
.Ssid
);
210 /*Add basic and extended rates */
213 p
+= snprintf(p
, MAX_CUSTOM_LEN
- (p
- custom
), " Rates (Mb/s): ");
214 while (pnetwork
->network
.SupportedRates
[i
] != 0) {
215 rate
= pnetwork
->network
.SupportedRates
[i
]&0x7F;
218 p
+= snprintf(p
, MAX_CUSTOM_LEN
- (p
- custom
),
219 "%d%s ", rate
>> 1, (rate
& 1) ? ".5" : "");
224 if (mcs_rate
&0x8000)/* MCS15 */
225 max_rate
= (bw_40MHz
) ? ((short_GI
) ? 300 : 270) : ((short_GI
) ? 144 : 130);
226 else if (mcs_rate
&0x0080)/* MCS7 */
228 else/* default MCS7 */
229 max_rate
= (bw_40MHz
) ? ((short_GI
) ? 150 : 135) : ((short_GI
) ? 72 : 65);
231 max_rate
= max_rate
*2;/* Mbps/2; */
234 iwe
.cmd
= SIOCGIWRATE
;
235 iwe
.u
.bitrate
.fixed
= 0;
236 iwe
.u
.bitrate
.disabled
= 0;
237 iwe
.u
.bitrate
.value
= max_rate
* 500000;
238 start
= iwe_stream_add_event(info
, start
, stop
, &iwe
, IW_EV_PARAM_LEN
);
240 /* parsing WPA/WPA2 IE */
242 u8 buf
[MAX_WPA_IE_LEN
];
243 u8 wpa_ie
[255], rsn_ie
[255];
244 u16 wpa_len
= 0, rsn_len
= 0;
247 rtw_get_sec_ie(pnetwork
->network
.IEs
, pnetwork
->network
.IELength
, rsn_ie
, &rsn_len
, wpa_ie
, &wpa_len
);
248 RT_TRACE(_module_rtl871x_mlme_c_
, _drv_info_
, ("rtw_wx_get_scan: ssid =%s\n", pnetwork
->network
.Ssid
.Ssid
));
249 RT_TRACE(_module_rtl871x_mlme_c_
, _drv_info_
, ("rtw_wx_get_scan: wpa_len =%d rsn_len =%d\n", wpa_len
, rsn_len
));
253 memset(buf
, 0, MAX_WPA_IE_LEN
);
254 p
+= sprintf(p
, "wpa_ie=");
255 for (i
= 0; i
< wpa_len
; i
++)
256 p
+= sprintf(p
, "%02x", wpa_ie
[i
]);
258 memset(&iwe
, 0, sizeof(iwe
));
259 iwe
.cmd
= IWEVCUSTOM
;
260 iwe
.u
.data
.length
= strlen(buf
);
261 start
= iwe_stream_add_point(info
, start
, stop
, &iwe
, buf
);
263 memset(&iwe
, 0, sizeof(iwe
));
265 iwe
.u
.data
.length
= wpa_len
;
266 start
= iwe_stream_add_point(info
, start
, stop
, &iwe
, wpa_ie
);
270 memset(buf
, 0, MAX_WPA_IE_LEN
);
271 p
+= sprintf(p
, "rsn_ie=");
272 for (i
= 0; i
< rsn_len
; i
++)
273 p
+= sprintf(p
, "%02x", rsn_ie
[i
]);
274 memset(&iwe
, 0, sizeof(iwe
));
275 iwe
.cmd
= IWEVCUSTOM
;
276 iwe
.u
.data
.length
= strlen(buf
);
277 start
= iwe_stream_add_point(info
, start
, stop
, &iwe
, buf
);
279 memset(&iwe
, 0, sizeof(iwe
));
281 iwe
.u
.data
.length
= rsn_len
;
282 start
= iwe_stream_add_point(info
, start
, stop
, &iwe
, rsn_ie
);
286 {/* parsing WPS IE */
287 uint cnt
= 0, total_ielen
;
288 u8
*wpsie_ptr
= NULL
;
291 u8
*ie_ptr
= pnetwork
->network
.IEs
+ _FIXED_IE_LENGTH_
;
292 total_ielen
= pnetwork
->network
.IELength
- _FIXED_IE_LENGTH_
;
294 while (cnt
< total_ielen
) {
295 if (rtw_is_wps_ie(&ie_ptr
[cnt
], &wps_ielen
) && (wps_ielen
> 2)) {
296 wpsie_ptr
= &ie_ptr
[cnt
];
298 iwe
.u
.data
.length
= (u16
)wps_ielen
;
299 start
= iwe_stream_add_point(info
, start
, stop
, &iwe
, wpsie_ptr
);
301 cnt
+= ie_ptr
[cnt
+1]+2; /* goto next */
305 /* Add quality statistics */
307 iwe
.u
.qual
.updated
= IW_QUAL_QUAL_UPDATED
| IW_QUAL_LEVEL_UPDATED
| IW_QUAL_NOISE_INVALID
;
309 if (check_fwstate(pmlmepriv
, _FW_LINKED
) == true &&
310 is_same_network(&pmlmepriv
->cur_network
.network
, &pnetwork
->network
)) {
311 ss
= padapter
->recvpriv
.signal_strength
;
312 sq
= padapter
->recvpriv
.signal_qual
;
314 ss
= pnetwork
->network
.PhyInfo
.SignalStrength
;
315 sq
= pnetwork
->network
.PhyInfo
.SignalQuality
;
318 iwe
.u
.qual
.level
= (u8
)ss
;
319 iwe
.u
.qual
.qual
= (u8
)sq
; /* signal quality */
320 iwe
.u
.qual
.noise
= 0; /* noise level */
321 start
= iwe_stream_add_event(info
, start
, stop
, &iwe
, IW_EV_QUAL_LEN
);
325 static int wpa_set_auth_algs(struct net_device
*dev
, u32 value
)
327 struct adapter
*padapter
= (struct adapter
*)rtw_netdev_priv(dev
);
330 if ((value
& AUTH_ALG_SHARED_KEY
) && (value
& AUTH_ALG_OPEN_SYSTEM
)) {
331 DBG_88E("wpa_set_auth_algs, AUTH_ALG_SHARED_KEY and AUTH_ALG_OPEN_SYSTEM [value:0x%x]\n", value
);
332 padapter
->securitypriv
.ndisencryptstatus
= Ndis802_11Encryption1Enabled
;
333 padapter
->securitypriv
.ndisauthtype
= Ndis802_11AuthModeAutoSwitch
;
334 padapter
->securitypriv
.dot11AuthAlgrthm
= dot11AuthAlgrthm_Auto
;
335 } else if (value
& AUTH_ALG_SHARED_KEY
) {
336 DBG_88E("wpa_set_auth_algs, AUTH_ALG_SHARED_KEY [value:0x%x]\n", value
);
337 padapter
->securitypriv
.ndisencryptstatus
= Ndis802_11Encryption1Enabled
;
339 padapter
->securitypriv
.ndisauthtype
= Ndis802_11AuthModeShared
;
340 padapter
->securitypriv
.dot11AuthAlgrthm
= dot11AuthAlgrthm_Shared
;
341 } else if (value
& AUTH_ALG_OPEN_SYSTEM
) {
342 DBG_88E("wpa_set_auth_algs, AUTH_ALG_OPEN_SYSTEM\n");
343 if (padapter
->securitypriv
.ndisauthtype
< Ndis802_11AuthModeWPAPSK
) {
344 padapter
->securitypriv
.ndisauthtype
= Ndis802_11AuthModeOpen
;
345 padapter
->securitypriv
.dot11AuthAlgrthm
= dot11AuthAlgrthm_Open
;
347 } else if (value
& AUTH_ALG_LEAP
) {
348 DBG_88E("wpa_set_auth_algs, AUTH_ALG_LEAP\n");
350 DBG_88E("wpa_set_auth_algs, error!\n");
356 static int wpa_set_encryption(struct net_device
*dev
, struct ieee_param
*param
, u32 param_len
)
359 u32 wep_key_idx
, wep_key_len
, wep_total_len
;
360 struct ndis_802_11_wep
*pwep
= NULL
;
361 struct adapter
*padapter
= (struct adapter
*)rtw_netdev_priv(dev
);
362 struct mlme_priv
*pmlmepriv
= &padapter
->mlmepriv
;
363 struct security_priv
*psecuritypriv
= &padapter
->securitypriv
;
365 param
->u
.crypt
.err
= 0;
366 param
->u
.crypt
.alg
[IEEE_CRYPT_ALG_NAME_LEN
- 1] = '\0';
368 if (param_len
< (u32
)((u8
*)param
->u
.crypt
.key
- (u8
*)param
) + param
->u
.crypt
.key_len
) {
373 if (param
->sta_addr
[0] == 0xff && param
->sta_addr
[1] == 0xff &&
374 param
->sta_addr
[2] == 0xff && param
->sta_addr
[3] == 0xff &&
375 param
->sta_addr
[4] == 0xff && param
->sta_addr
[5] == 0xff) {
376 if (param
->u
.crypt
.idx
>= WEP_KEYS
) {
385 if (strcmp(param
->u
.crypt
.alg
, "WEP") == 0) {
386 RT_TRACE(_module_rtl871x_ioctl_os_c
, _drv_err_
, ("wpa_set_encryption, crypt.alg = WEP\n"));
387 DBG_88E("wpa_set_encryption, crypt.alg = WEP\n");
389 padapter
->securitypriv
.ndisencryptstatus
= Ndis802_11Encryption1Enabled
;
390 padapter
->securitypriv
.dot11PrivacyAlgrthm
= _WEP40_
;
391 padapter
->securitypriv
.dot118021XGrpPrivacy
= _WEP40_
;
393 wep_key_idx
= param
->u
.crypt
.idx
;
394 wep_key_len
= param
->u
.crypt
.key_len
;
396 RT_TRACE(_module_rtl871x_ioctl_os_c
, _drv_info_
, ("(1)wep_key_idx =%d\n", wep_key_idx
));
397 DBG_88E("(1)wep_key_idx =%d\n", wep_key_idx
);
399 if (wep_key_idx
> WEP_KEYS
)
402 RT_TRACE(_module_rtl871x_ioctl_os_c
, _drv_info_
, ("(2)wep_key_idx =%d\n", wep_key_idx
));
404 if (wep_key_len
> 0) {
405 wep_key_len
= wep_key_len
<= 5 ? 5 : 13;
406 wep_total_len
= wep_key_len
+ FIELD_OFFSET(struct ndis_802_11_wep
, KeyMaterial
);
407 pwep
= (struct ndis_802_11_wep
*)rtw_malloc(wep_total_len
);
409 RT_TRACE(_module_rtl871x_ioctl_os_c
, _drv_err_
, (" wpa_set_encryption: pwep allocate fail !!!\n"));
412 memset(pwep
, 0, wep_total_len
);
413 pwep
->KeyLength
= wep_key_len
;
414 pwep
->Length
= wep_total_len
;
415 if (wep_key_len
== 13) {
416 padapter
->securitypriv
.dot11PrivacyAlgrthm
= _WEP104_
;
417 padapter
->securitypriv
.dot118021XGrpPrivacy
= _WEP104_
;
423 pwep
->KeyIndex
= wep_key_idx
;
424 pwep
->KeyIndex
|= 0x80000000;
425 memcpy(pwep
->KeyMaterial
, param
->u
.crypt
.key
, pwep
->KeyLength
);
426 if (param
->u
.crypt
.set_tx
) {
427 DBG_88E("wep, set_tx = 1\n");
428 if (rtw_set_802_11_add_wep(padapter
, pwep
) == (u8
)_FAIL
)
431 DBG_88E("wep, set_tx = 0\n");
432 if (wep_key_idx
>= WEP_KEYS
) {
436 memcpy(&(psecuritypriv
->dot11DefKey
[wep_key_idx
].skey
[0]), pwep
->KeyMaterial
, pwep
->KeyLength
);
437 psecuritypriv
->dot11DefKeylen
[wep_key_idx
] = pwep
->KeyLength
;
438 rtw_set_key(padapter
, psecuritypriv
, wep_key_idx
, 0);
443 if (padapter
->securitypriv
.dot11AuthAlgrthm
== dot11AuthAlgrthm_8021X
) { /* 802_1x */
444 struct sta_info
*psta
, *pbcmc_sta
;
445 struct sta_priv
*pstapriv
= &padapter
->stapriv
;
447 if (check_fwstate(pmlmepriv
, WIFI_STATION_STATE
| WIFI_MP_STATE
)) { /* sta mode */
448 psta
= rtw_get_stainfo(pstapriv
, get_bssid(pmlmepriv
));
452 if (strcmp(param
->u
.crypt
.alg
, "none") != 0)
453 psta
->ieee8021x_blocked
= false;
455 if ((padapter
->securitypriv
.ndisencryptstatus
== Ndis802_11Encryption2Enabled
) ||
456 (padapter
->securitypriv
.ndisencryptstatus
== Ndis802_11Encryption3Enabled
))
457 psta
->dot118021XPrivacy
= padapter
->securitypriv
.dot11PrivacyAlgrthm
;
459 if (param
->u
.crypt
.set_tx
== 1) { /* pairwise key */
460 memcpy(psta
->dot118021x_UncstKey
.skey
, param
->u
.crypt
.key
, min_t(u16
, param
->u
.crypt
.key_len
, 16));
462 if (strcmp(param
->u
.crypt
.alg
, "TKIP") == 0) { /* set mic key */
463 memcpy(psta
->dot11tkiptxmickey
.skey
, &(param
->u
.crypt
.key
[16]), 8);
464 memcpy(psta
->dot11tkiprxmickey
.skey
, &(param
->u
.crypt
.key
[24]), 8);
465 padapter
->securitypriv
.busetkipkey
= false;
468 DBG_88E(" ~~~~set sta key:unicastkey\n");
470 rtw_setstakey_cmd(padapter
, (unsigned char *)psta
, true);
471 } else { /* group key */
472 memcpy(padapter
->securitypriv
.dot118021XGrpKey
[param
->u
.crypt
.idx
].skey
, param
->u
.crypt
.key
, min_t(u16
, param
->u
.crypt
.key_len
, 16 ));
473 memcpy(padapter
->securitypriv
.dot118021XGrptxmickey
[param
->u
.crypt
.idx
].skey
, &(param
->u
.crypt
.key
[16]), 8);
474 memcpy(padapter
->securitypriv
.dot118021XGrprxmickey
[param
->u
.crypt
.idx
].skey
, &(param
->u
.crypt
.key
[24]), 8);
475 padapter
->securitypriv
.binstallGrpkey
= true;
476 DBG_88E(" ~~~~set sta key:groupkey\n");
478 padapter
->securitypriv
.dot118021XGrpKeyid
= param
->u
.crypt
.idx
;
480 rtw_set_key(padapter
, &padapter
->securitypriv
, param
->u
.crypt
.idx
, 1);
483 pbcmc_sta
= rtw_get_bcmc_stainfo(padapter
);
484 if (pbcmc_sta
== NULL
) {
487 /* Jeff: don't disable ieee8021x_blocked while clearing key */
488 if (strcmp(param
->u
.crypt
.alg
, "none") != 0)
489 pbcmc_sta
->ieee8021x_blocked
= false;
491 if ((padapter
->securitypriv
.ndisencryptstatus
== Ndis802_11Encryption2Enabled
) ||
492 (padapter
->securitypriv
.ndisencryptstatus
== Ndis802_11Encryption3Enabled
))
493 pbcmc_sta
->dot118021XPrivacy
= padapter
->securitypriv
.dot11PrivacyAlgrthm
;
504 static int rtw_set_wpa_ie(struct adapter
*padapter
, char *pie
, unsigned short ielen
)
507 int group_cipher
= 0, pairwise_cipher
= 0;
510 if ((ielen
> MAX_WPA_IE_LEN
) || (pie
== NULL
)) {
511 _clr_fwstate_(&padapter
->mlmepriv
, WIFI_UNDER_WPS
);
519 buf
= kmemdup(pie
, ielen
, GFP_KERNEL
);
528 DBG_88E("\n wpa_ie(length:%d):\n", ielen
);
529 for (i
= 0; i
< ielen
; i
+= 8)
530 DBG_88E("0x%.2x 0x%.2x 0x%.2x 0x%.2x 0x%.2x 0x%.2x 0x%.2x 0x%.2x\n", buf
[i
], buf
[i
+1], buf
[i
+2], buf
[i
+3], buf
[i
+4], buf
[i
+5], buf
[i
+6], buf
[i
+7]);
533 if (ielen
< RSN_HEADER_LEN
) {
534 RT_TRACE(_module_rtl871x_ioctl_os_c
, _drv_err_
, ("Ie len too short %d\n", ielen
));
539 if (rtw_parse_wpa_ie(buf
, ielen
, &group_cipher
, &pairwise_cipher
, NULL
) == _SUCCESS
) {
540 padapter
->securitypriv
.dot11AuthAlgrthm
= dot11AuthAlgrthm_8021X
;
541 padapter
->securitypriv
.ndisauthtype
= Ndis802_11AuthModeWPAPSK
;
542 memcpy(padapter
->securitypriv
.supplicant_ie
, &buf
[0], ielen
);
545 if (rtw_parse_wpa2_ie(buf
, ielen
, &group_cipher
, &pairwise_cipher
, NULL
) == _SUCCESS
) {
546 padapter
->securitypriv
.dot11AuthAlgrthm
= dot11AuthAlgrthm_8021X
;
547 padapter
->securitypriv
.ndisauthtype
= Ndis802_11AuthModeWPA2PSK
;
548 memcpy(padapter
->securitypriv
.supplicant_ie
, &buf
[0], ielen
);
551 switch (group_cipher
) {
552 case WPA_CIPHER_NONE
:
553 padapter
->securitypriv
.dot118021XGrpPrivacy
= _NO_PRIVACY_
;
554 padapter
->securitypriv
.ndisencryptstatus
= Ndis802_11EncryptionDisabled
;
556 case WPA_CIPHER_WEP40
:
557 padapter
->securitypriv
.dot118021XGrpPrivacy
= _WEP40_
;
558 padapter
->securitypriv
.ndisencryptstatus
= Ndis802_11Encryption1Enabled
;
560 case WPA_CIPHER_TKIP
:
561 padapter
->securitypriv
.dot118021XGrpPrivacy
= _TKIP_
;
562 padapter
->securitypriv
.ndisencryptstatus
= Ndis802_11Encryption2Enabled
;
564 case WPA_CIPHER_CCMP
:
565 padapter
->securitypriv
.dot118021XGrpPrivacy
= _AES_
;
566 padapter
->securitypriv
.ndisencryptstatus
= Ndis802_11Encryption3Enabled
;
568 case WPA_CIPHER_WEP104
:
569 padapter
->securitypriv
.dot118021XGrpPrivacy
= _WEP104_
;
570 padapter
->securitypriv
.ndisencryptstatus
= Ndis802_11Encryption1Enabled
;
574 switch (pairwise_cipher
) {
575 case WPA_CIPHER_NONE
:
576 padapter
->securitypriv
.dot11PrivacyAlgrthm
= _NO_PRIVACY_
;
577 padapter
->securitypriv
.ndisencryptstatus
= Ndis802_11EncryptionDisabled
;
579 case WPA_CIPHER_WEP40
:
580 padapter
->securitypriv
.dot11PrivacyAlgrthm
= _WEP40_
;
581 padapter
->securitypriv
.ndisencryptstatus
= Ndis802_11Encryption1Enabled
;
583 case WPA_CIPHER_TKIP
:
584 padapter
->securitypriv
.dot11PrivacyAlgrthm
= _TKIP_
;
585 padapter
->securitypriv
.ndisencryptstatus
= Ndis802_11Encryption2Enabled
;
587 case WPA_CIPHER_CCMP
:
588 padapter
->securitypriv
.dot11PrivacyAlgrthm
= _AES_
;
589 padapter
->securitypriv
.ndisencryptstatus
= Ndis802_11Encryption3Enabled
;
591 case WPA_CIPHER_WEP104
:
592 padapter
->securitypriv
.dot11PrivacyAlgrthm
= _WEP104_
;
593 padapter
->securitypriv
.ndisencryptstatus
= Ndis802_11Encryption1Enabled
;
597 _clr_fwstate_(&padapter
->mlmepriv
, WIFI_UNDER_WPS
);
600 u8 eid
, wps_oui
[4] = {0x0, 0x50, 0xf2, 0x04};
602 while (cnt
< ielen
) {
604 if ((eid
== _VENDOR_SPECIFIC_IE_
) && (!memcmp(&buf
[cnt
+2], wps_oui
, 4))) {
605 DBG_88E("SET WPS_IE\n");
607 padapter
->securitypriv
.wps_ie_len
= min(buf
[cnt
+ 1] + 2, MAX_WPA_IE_LEN
<< 2);
609 memcpy(padapter
->securitypriv
.wps_ie
, &buf
[cnt
], padapter
->securitypriv
.wps_ie_len
);
611 set_fwstate(&padapter
->mlmepriv
, WIFI_UNDER_WPS
);
615 cnt
+= buf
[cnt
+1]+2; /* goto next */
621 RT_TRACE(_module_rtl871x_ioctl_os_c
, _drv_info_
,
622 ("rtw_set_wpa_ie: pairwise_cipher = 0x%08x padapter->securitypriv.ndisencryptstatus =%d padapter->securitypriv.ndisauthtype =%d\n",
623 pairwise_cipher
, padapter
->securitypriv
.ndisencryptstatus
, padapter
->securitypriv
.ndisauthtype
));
629 typedef unsigned char NDIS_802_11_RATES_EX
[NDIS_802_11_LENGTH_RATES_EX
];
631 static int rtw_wx_get_name(struct net_device
*dev
,
632 struct iw_request_info
*info
,
633 union iwreq_data
*wrqu
, char *extra
)
635 struct adapter
*padapter
= (struct adapter
*)rtw_netdev_priv(dev
);
639 struct mlme_priv
*pmlmepriv
= &(padapter
->mlmepriv
);
640 struct wlan_bssid_ex
*pcur_bss
= &pmlmepriv
->cur_network
.network
;
641 NDIS_802_11_RATES_EX
*prates
= NULL
;
643 RT_TRACE(_module_rtl871x_mlme_c_
, _drv_info_
, ("cmd_code =%x\n", info
->cmd
));
645 if (check_fwstate(pmlmepriv
, _FW_LINKED
|WIFI_ADHOC_MASTER_STATE
) == true) {
646 /* parsing HT_CAP_IE */
647 p
= rtw_get_ie(&pcur_bss
->IEs
[12], _HT_CAPABILITY_IE_
, &ht_ielen
, pcur_bss
->IELength
-12);
648 if (p
&& ht_ielen
> 0)
651 prates
= &pcur_bss
->SupportedRates
;
653 if (rtw_is_cckratesonly_included((u8
*)prates
) == true) {
655 snprintf(wrqu
->name
, IFNAMSIZ
, "IEEE 802.11bn");
657 snprintf(wrqu
->name
, IFNAMSIZ
, "IEEE 802.11b");
658 } else if ((rtw_is_cckrates_included((u8
*)prates
)) == true) {
660 snprintf(wrqu
->name
, IFNAMSIZ
, "IEEE 802.11bgn");
662 snprintf(wrqu
->name
, IFNAMSIZ
, "IEEE 802.11bg");
664 if (pcur_bss
->Configuration
.DSConfig
> 14) {
666 snprintf(wrqu
->name
, IFNAMSIZ
, "IEEE 802.11an");
668 snprintf(wrqu
->name
, IFNAMSIZ
, "IEEE 802.11a");
671 snprintf(wrqu
->name
, IFNAMSIZ
, "IEEE 802.11gn");
673 snprintf(wrqu
->name
, IFNAMSIZ
, "IEEE 802.11g");
677 snprintf(wrqu
->name
, IFNAMSIZ
, "unassociated");
682 static int rtw_wx_set_freq(struct net_device
*dev
,
683 struct iw_request_info
*info
,
684 union iwreq_data
*wrqu
, char *extra
)
686 RT_TRACE(_module_rtl871x_mlme_c_
, _drv_notice_
, ("+rtw_wx_set_freq\n"));
690 static int rtw_wx_get_freq(struct net_device
*dev
,
691 struct iw_request_info
*info
,
692 union iwreq_data
*wrqu
, char *extra
)
694 struct adapter
*padapter
= (struct adapter
*)rtw_netdev_priv(dev
);
695 struct mlme_priv
*pmlmepriv
= &(padapter
->mlmepriv
);
696 struct wlan_bssid_ex
*pcur_bss
= &pmlmepriv
->cur_network
.network
;
698 if (check_fwstate(pmlmepriv
, _FW_LINKED
)) {
699 /* wrqu->freq.m = ieee80211_wlan_frequencies[pcur_bss->Configuration.DSConfig-1] * 100000; */
700 wrqu
->freq
.m
= rtw_ch2freq(pcur_bss
->Configuration
.DSConfig
) * 100000;
702 wrqu
->freq
.i
= pcur_bss
->Configuration
.DSConfig
;
704 wrqu
->freq
.m
= rtw_ch2freq(padapter
->mlmeextpriv
.cur_channel
) * 100000;
706 wrqu
->freq
.i
= padapter
->mlmeextpriv
.cur_channel
;
712 static int rtw_wx_set_mode(struct net_device
*dev
, struct iw_request_info
*a
,
713 union iwreq_data
*wrqu
, char *b
)
715 struct adapter
*padapter
= (struct adapter
*)rtw_netdev_priv(dev
);
716 enum ndis_802_11_network_infra networkType
;
719 if (_FAIL
== rtw_pwr_wakeup(padapter
)) {
724 if (!padapter
->hw_init_completed
) {
729 switch (wrqu
->mode
) {
731 networkType
= Ndis802_11AutoUnknown
;
732 DBG_88E("set_mode = IW_MODE_AUTO\n");
735 networkType
= Ndis802_11IBSS
;
736 DBG_88E("set_mode = IW_MODE_ADHOC\n");
739 networkType
= Ndis802_11APMode
;
740 DBG_88E("set_mode = IW_MODE_MASTER\n");
743 networkType
= Ndis802_11Infrastructure
;
744 DBG_88E("set_mode = IW_MODE_INFRA\n");
748 RT_TRACE(_module_rtl871x_ioctl_os_c
, _drv_err_
, ("\n Mode: %s is not supported\n", iw_operation_mode
[wrqu
->mode
]));
751 if (rtw_set_802_11_infrastructure_mode(padapter
, networkType
) == false) {
755 rtw_setopmode_cmd(padapter
, networkType
);
760 static int rtw_wx_get_mode(struct net_device
*dev
, struct iw_request_info
*a
,
761 union iwreq_data
*wrqu
, char *b
)
763 struct adapter
*padapter
= (struct adapter
*)rtw_netdev_priv(dev
);
764 struct mlme_priv
*pmlmepriv
= &(padapter
->mlmepriv
);
766 RT_TRACE(_module_rtl871x_mlme_c_
, _drv_info_
, (" rtw_wx_get_mode\n"));
768 if (check_fwstate(pmlmepriv
, WIFI_STATION_STATE
))
769 wrqu
->mode
= IW_MODE_INFRA
;
770 else if ((check_fwstate(pmlmepriv
, WIFI_ADHOC_MASTER_STATE
)) ||
771 (check_fwstate(pmlmepriv
, WIFI_ADHOC_STATE
)))
772 wrqu
->mode
= IW_MODE_ADHOC
;
773 else if (check_fwstate(pmlmepriv
, WIFI_AP_STATE
))
774 wrqu
->mode
= IW_MODE_MASTER
;
776 wrqu
->mode
= IW_MODE_AUTO
;
781 static int rtw_wx_set_pmkid(struct net_device
*dev
,
782 struct iw_request_info
*a
,
783 union iwreq_data
*wrqu
, char *extra
)
785 struct adapter
*padapter
= (struct adapter
*)rtw_netdev_priv(dev
);
786 u8 j
, blInserted
= false;
788 struct security_priv
*psecuritypriv
= &padapter
->securitypriv
;
789 struct iw_pmksa
*pPMK
= (struct iw_pmksa
*)extra
;
790 u8 strZeroMacAddress
[ETH_ALEN
] = {0x00};
791 u8 strIssueBssid
[ETH_ALEN
] = {0x00};
793 memcpy(strIssueBssid
, pPMK
->bssid
.sa_data
, ETH_ALEN
);
794 if (pPMK
->cmd
== IW_PMKSA_ADD
) {
795 DBG_88E("[rtw_wx_set_pmkid] IW_PMKSA_ADD!\n");
796 if (!memcmp(strIssueBssid
, strZeroMacAddress
, ETH_ALEN
))
802 /* overwrite PMKID */
803 for (j
= 0; j
< NUM_PMKID_CACHE
; j
++) {
804 if (!memcmp(psecuritypriv
->PMKIDList
[j
].Bssid
, strIssueBssid
, ETH_ALEN
)) {
805 /* BSSID is matched, the same AP => rewrite with new PMKID. */
806 DBG_88E("[rtw_wx_set_pmkid] BSSID exists in the PMKList.\n");
807 memcpy(psecuritypriv
->PMKIDList
[j
].PMKID
, pPMK
->pmkid
, IW_PMKID_LEN
);
808 psecuritypriv
->PMKIDList
[j
].bUsed
= true;
809 psecuritypriv
->PMKIDIndex
= j
+1;
816 /* Find a new entry */
817 DBG_88E("[rtw_wx_set_pmkid] Use the new entry index = %d for this PMKID.\n",
818 psecuritypriv
->PMKIDIndex
);
820 memcpy(psecuritypriv
->PMKIDList
[psecuritypriv
->PMKIDIndex
].Bssid
, strIssueBssid
, ETH_ALEN
);
821 memcpy(psecuritypriv
->PMKIDList
[psecuritypriv
->PMKIDIndex
].PMKID
, pPMK
->pmkid
, IW_PMKID_LEN
);
823 psecuritypriv
->PMKIDList
[psecuritypriv
->PMKIDIndex
].bUsed
= true;
824 psecuritypriv
->PMKIDIndex
++;
825 if (psecuritypriv
->PMKIDIndex
== 16)
826 psecuritypriv
->PMKIDIndex
= 0;
828 } else if (pPMK
->cmd
== IW_PMKSA_REMOVE
) {
829 DBG_88E("[rtw_wx_set_pmkid] IW_PMKSA_REMOVE!\n");
831 for (j
= 0; j
< NUM_PMKID_CACHE
; j
++) {
832 if (!memcmp(psecuritypriv
->PMKIDList
[j
].Bssid
, strIssueBssid
, ETH_ALEN
)) {
833 /* BSSID is matched, the same AP => Remove this PMKID information and reset it. */
834 eth_zero_addr(psecuritypriv
->PMKIDList
[j
].Bssid
);
835 psecuritypriv
->PMKIDList
[j
].bUsed
= false;
839 } else if (pPMK
->cmd
== IW_PMKSA_FLUSH
) {
840 DBG_88E("[rtw_wx_set_pmkid] IW_PMKSA_FLUSH!\n");
841 memset(&psecuritypriv
->PMKIDList
[0], 0x00, sizeof(struct rt_pmkid_list
) * NUM_PMKID_CACHE
);
842 psecuritypriv
->PMKIDIndex
= 0;
848 static int rtw_wx_get_sens(struct net_device
*dev
,
849 struct iw_request_info
*info
,
850 union iwreq_data
*wrqu
, char *extra
)
852 wrqu
->sens
.value
= 0;
853 wrqu
->sens
.fixed
= 0; /* no auto select */
854 wrqu
->sens
.disabled
= 1;
858 static int rtw_wx_get_range(struct net_device
*dev
,
859 struct iw_request_info
*info
,
860 union iwreq_data
*wrqu
, char *extra
)
862 struct iw_range
*range
= (struct iw_range
*)extra
;
863 struct adapter
*padapter
= (struct adapter
*)rtw_netdev_priv(dev
);
864 struct mlme_ext_priv
*pmlmeext
= &padapter
->mlmeextpriv
;
869 RT_TRACE(_module_rtl871x_mlme_c_
, _drv_info_
, ("rtw_wx_get_range. cmd_code =%x\n", info
->cmd
));
871 wrqu
->data
.length
= sizeof(*range
);
872 memset(range
, 0, sizeof(*range
));
874 /* Let's try to keep this struct in the same order as in
875 * linux/include/wireless.h
878 /* TODO: See what values we can set, and remove the ones we can't
879 * set, or fill them with some default data.
882 /* ~5 Mb/s real (802.11b) */
883 range
->throughput
= 5 * 1000 * 1000;
885 /* signal level threshold range */
887 /* percent values between 0 and 100. */
888 range
->max_qual
.qual
= 100;
889 range
->max_qual
.level
= 100;
890 range
->max_qual
.noise
= 100;
891 range
->max_qual
.updated
= 7; /* Updated all three */
893 range
->avg_qual
.qual
= 92; /* > 8% missed beacons is 'bad' */
894 /* TODO: Find real 'good' to 'bad' threshol value for RSSI */
895 range
->avg_qual
.level
= 178; /* -78 dBm */
896 range
->avg_qual
.noise
= 0;
897 range
->avg_qual
.updated
= 7; /* Updated all three */
899 range
->num_bitrates
= RATE_COUNT
;
901 for (i
= 0; i
< RATE_COUNT
&& i
< IW_MAX_BITRATES
; i
++)
902 range
->bitrate
[i
] = rtw_rates
[i
];
904 range
->min_frag
= MIN_FRAG_THRESHOLD
;
905 range
->max_frag
= MAX_FRAG_THRESHOLD
;
909 range
->we_version_compiled
= WIRELESS_EXT
;
910 range
->we_version_source
= 16;
912 for (i
= 0, val
= 0; i
< MAX_CHANNEL_NUM
; i
++) {
913 /* Include only legal frequencies for some countries */
914 if (pmlmeext
->channel_set
[i
].ChannelNum
!= 0) {
915 range
->freq
[val
].i
= pmlmeext
->channel_set
[i
].ChannelNum
;
916 range
->freq
[val
].m
= rtw_ch2freq(pmlmeext
->channel_set
[i
].ChannelNum
) * 100000;
917 range
->freq
[val
].e
= 1;
921 if (val
== IW_MAX_FREQUENCIES
)
925 range
->num_channels
= val
;
926 range
->num_frequency
= val
;
928 /* The following code will proivde the security capability to network manager. */
929 /* If the driver doesn't provide this capability to network manager, */
930 /* the WPA/WPA2 routers can't be chosen in the network manager. */
933 #define IW_SCAN_CAPA_NONE 0x00
934 #define IW_SCAN_CAPA_ESSID 0x01
935 #define IW_SCAN_CAPA_BSSID 0x02
936 #define IW_SCAN_CAPA_CHANNEL 0x04
937 #define IW_SCAN_CAPA_MODE 0x08
938 #define IW_SCAN_CAPA_RATE 0x10
939 #define IW_SCAN_CAPA_TYPE 0x20
940 #define IW_SCAN_CAPA_TIME 0x40
943 range
->enc_capa
= IW_ENC_CAPA_WPA
| IW_ENC_CAPA_WPA2
|
944 IW_ENC_CAPA_CIPHER_TKIP
| IW_ENC_CAPA_CIPHER_CCMP
;
946 range
->scan_capa
= IW_SCAN_CAPA_ESSID
| IW_SCAN_CAPA_TYPE
|
947 IW_SCAN_CAPA_BSSID
| IW_SCAN_CAPA_CHANNEL
|
948 IW_SCAN_CAPA_MODE
| IW_SCAN_CAPA_RATE
;
953 /* s1. rtw_set_802_11_infrastructure_mode() */
954 /* s2. rtw_set_802_11_authentication_mode() */
955 /* s3. set_802_11_encryption_mode() */
956 /* s4. rtw_set_802_11_bssid() */
957 static int rtw_wx_set_wap(struct net_device
*dev
,
958 struct iw_request_info
*info
,
959 union iwreq_data
*awrq
,
963 struct adapter
*padapter
= (struct adapter
*)rtw_netdev_priv(dev
);
964 struct sockaddr
*temp
= (struct sockaddr
*)awrq
;
965 struct mlme_priv
*pmlmepriv
= &(padapter
->mlmepriv
);
966 struct list_head
*phead
;
967 u8
*dst_bssid
, *src_bssid
;
968 struct __queue
*queue
= &(pmlmepriv
->scanned_queue
);
969 struct wlan_network
*pnetwork
= NULL
;
970 enum ndis_802_11_auth_mode authmode
;
972 if (_FAIL
== rtw_pwr_wakeup(padapter
)) {
977 if (!padapter
->bup
) {
982 if (temp
->sa_family
!= ARPHRD_ETHER
) {
987 authmode
= padapter
->securitypriv
.ndisauthtype
;
988 spin_lock_bh(&queue
->lock
);
989 phead
= get_list_head(queue
);
990 pmlmepriv
->pscanned
= phead
->next
;
992 while (phead
!= pmlmepriv
->pscanned
) {
993 pnetwork
= container_of(pmlmepriv
->pscanned
, struct wlan_network
, list
);
995 pmlmepriv
->pscanned
= pmlmepriv
->pscanned
->next
;
997 dst_bssid
= pnetwork
->network
.MacAddress
;
999 src_bssid
= temp
->sa_data
;
1001 if ((!memcmp(dst_bssid
, src_bssid
, ETH_ALEN
))) {
1002 if (!rtw_set_802_11_infrastructure_mode(padapter
, pnetwork
->network
.InfrastructureMode
)) {
1004 spin_unlock_bh(&queue
->lock
);
1011 spin_unlock_bh(&queue
->lock
);
1013 rtw_set_802_11_authentication_mode(padapter
, authmode
);
1014 /* set_802_11_encryption_mode(padapter, padapter->securitypriv.ndisencryptstatus); */
1015 if (rtw_set_802_11_bssid(padapter
, temp
->sa_data
) == false) {
1025 static int rtw_wx_get_wap(struct net_device
*dev
,
1026 struct iw_request_info
*info
,
1027 union iwreq_data
*wrqu
, char *extra
)
1029 struct adapter
*padapter
= (struct adapter
*)rtw_netdev_priv(dev
);
1030 struct mlme_priv
*pmlmepriv
= &(padapter
->mlmepriv
);
1031 struct wlan_bssid_ex
*pcur_bss
= &pmlmepriv
->cur_network
.network
;
1033 wrqu
->ap_addr
.sa_family
= ARPHRD_ETHER
;
1035 eth_zero_addr(wrqu
->ap_addr
.sa_data
);
1037 RT_TRACE(_module_rtl871x_mlme_c_
, _drv_info_
, ("rtw_wx_get_wap\n"));
1039 if (((check_fwstate(pmlmepriv
, _FW_LINKED
)) == true) ||
1040 ((check_fwstate(pmlmepriv
, WIFI_ADHOC_MASTER_STATE
)) == true) ||
1041 ((check_fwstate(pmlmepriv
, WIFI_AP_STATE
)) == true))
1042 memcpy(wrqu
->ap_addr
.sa_data
, pcur_bss
->MacAddress
, ETH_ALEN
);
1044 eth_zero_addr(wrqu
->ap_addr
.sa_data
);
1048 static int rtw_wx_set_mlme(struct net_device
*dev
,
1049 struct iw_request_info
*info
,
1050 union iwreq_data
*wrqu
, char *extra
)
1054 struct adapter
*padapter
= (struct adapter
*)rtw_netdev_priv(dev
);
1055 struct iw_mlme
*mlme
= (struct iw_mlme
*)extra
;
1060 DBG_88E("%s\n", __func__
);
1062 reason
= mlme
->reason_code
;
1064 DBG_88E("%s, cmd =%d, reason =%d\n", __func__
, mlme
->cmd
, reason
);
1066 switch (mlme
->cmd
) {
1067 case IW_MLME_DEAUTH
:
1068 if (!rtw_set_802_11_disassociate(padapter
))
1071 case IW_MLME_DISASSOC
:
1072 if (!rtw_set_802_11_disassociate(padapter
))
1081 static int rtw_wx_set_scan(struct net_device
*dev
, struct iw_request_info
*a
,
1082 union iwreq_data
*wrqu
, char *extra
)
1086 struct adapter
*padapter
= (struct adapter
*)rtw_netdev_priv(dev
);
1087 struct mlme_priv
*pmlmepriv
= &padapter
->mlmepriv
;
1088 struct ndis_802_11_ssid ssid
[RTW_SSID_SCAN_AMOUNT
];
1089 RT_TRACE(_module_rtl871x_mlme_c_
, _drv_info_
, ("rtw_wx_set_scan\n"));
1091 if (padapter
->registrypriv
.mp_mode
== 1) {
1092 if (check_fwstate(pmlmepriv
, WIFI_MP_STATE
)) {
1097 if (_FAIL
== rtw_pwr_wakeup(padapter
)) {
1102 if (padapter
->bDriverStopped
) {
1103 DBG_88E("bDriverStopped =%d\n", padapter
->bDriverStopped
);
1108 if (!padapter
->bup
) {
1113 if (!padapter
->hw_init_completed
) {
1118 /* When Busy Traffic, driver do not site survey. So driver return success. */
1119 /* wpa_supplicant will not issue SIOCSIWSCAN cmd again after scan timeout. */
1120 /* modify by thomas 2011-02-22. */
1121 if (pmlmepriv
->LinkDetectInfo
.bBusyTraffic
) {
1122 indicate_wx_scan_complete_event(padapter
);
1126 if (check_fwstate(pmlmepriv
, _FW_UNDER_SURVEY
|_FW_UNDER_LINKING
)) {
1127 indicate_wx_scan_complete_event(padapter
);
1131 /* For the DMP WiFi Display project, the driver won't to scan because */
1132 /* the pmlmepriv->scan_interval is always equal to 3. */
1133 /* So, the wpa_supplicant won't find out the WPS SoftAP. */
1135 memset(ssid
, 0, sizeof(struct ndis_802_11_ssid
)*RTW_SSID_SCAN_AMOUNT
);
1137 if (wrqu
->data
.length
== sizeof(struct iw_scan_req
)) {
1138 struct iw_scan_req
*req
= (struct iw_scan_req
*)extra
;
1140 if (wrqu
->data
.flags
& IW_SCAN_THIS_ESSID
) {
1141 int len
= min_t(int, req
->essid_len
,
1144 memcpy(ssid
[0].Ssid
, req
->essid
, len
);
1145 ssid
[0].SsidLength
= len
;
1147 DBG_88E("IW_SCAN_THIS_ESSID, ssid =%s, len =%d\n", req
->essid
, req
->essid_len
);
1149 spin_lock_bh(&pmlmepriv
->lock
);
1151 _status
= rtw_sitesurvey_cmd(padapter
, ssid
, 1, NULL
, 0);
1153 spin_unlock_bh(&pmlmepriv
->lock
);
1154 } else if (req
->scan_type
== IW_SCAN_TYPE_PASSIVE
) {
1155 DBG_88E("rtw_wx_set_scan, req->scan_type == IW_SCAN_TYPE_PASSIVE\n");
1158 if (wrqu
->data
.length
>= WEXT_CSCAN_HEADER_SIZE
&&
1159 !memcmp(extra
, WEXT_CSCAN_HEADER
, WEXT_CSCAN_HEADER_SIZE
)) {
1160 int len
= wrqu
->data
.length
- WEXT_CSCAN_HEADER_SIZE
;
1161 char *pos
= extra
+WEXT_CSCAN_HEADER_SIZE
;
1171 case WEXT_CSCAN_SSID_SECTION
:
1176 sec_len
= *(pos
++); len
-= 1;
1177 if (sec_len
> 0 && sec_len
<= len
) {
1178 ssid
[ssid_index
].SsidLength
= sec_len
;
1179 memcpy(ssid
[ssid_index
].Ssid
, pos
, ssid
[ssid_index
].SsidLength
);
1185 case WEXT_CSCAN_TYPE_SECTION
:
1186 case WEXT_CSCAN_CHANNEL_SECTION
:
1190 case WEXT_CSCAN_PASV_DWELL_SECTION
:
1191 case WEXT_CSCAN_HOME_DWELL_SECTION
:
1192 case WEXT_CSCAN_ACTV_DWELL_SECTION
:
1197 len
= 0; /* stop parsing */
1201 /* it has still some scan parameter to parse, we only do this now... */
1202 _status
= rtw_set_802_11_bssid_list_scan(padapter
, ssid
, RTW_SSID_SCAN_AMOUNT
);
1204 _status
= rtw_set_802_11_bssid_list_scan(padapter
, NULL
, 0);
1216 static int rtw_wx_get_scan(struct net_device
*dev
, struct iw_request_info
*a
,
1217 union iwreq_data
*wrqu
, char *extra
)
1219 struct list_head
*plist
, *phead
;
1220 struct adapter
*padapter
= (struct adapter
*)rtw_netdev_priv(dev
);
1221 struct mlme_priv
*pmlmepriv
= &(padapter
->mlmepriv
);
1222 struct __queue
*queue
= &(pmlmepriv
->scanned_queue
);
1223 struct wlan_network
*pnetwork
= NULL
;
1225 char *stop
= ev
+ wrqu
->data
.length
;
1228 u32 wait_for_surveydone
;
1230 RT_TRACE(_module_rtl871x_mlme_c_
, _drv_info_
, ("rtw_wx_get_scan\n"));
1231 RT_TRACE(_module_rtl871x_ioctl_os_c
, _drv_info_
, (" Start of Query SIOCGIWSCAN .\n"));
1233 if (padapter
->pwrctrlpriv
.brfoffbyhw
&& padapter
->bDriverStopped
) {
1238 wait_for_surveydone
= 100;
1240 wait_status
= _FW_UNDER_SURVEY
| _FW_UNDER_LINKING
;
1242 while (check_fwstate(pmlmepriv
, wait_status
)) {
1245 if (cnt
> wait_for_surveydone
)
1249 spin_lock_bh(&(pmlmepriv
->scanned_queue
.lock
));
1251 phead
= get_list_head(queue
);
1252 plist
= phead
->next
;
1254 while (phead
!= plist
) {
1255 if ((stop
- ev
) < SCAN_ITEM_SIZE
) {
1260 pnetwork
= container_of(plist
, struct wlan_network
, list
);
1262 /* report network only if the current channel set contains the channel to which this network belongs */
1263 if (rtw_ch_set_search_ch(padapter
->mlmeextpriv
.channel_set
, pnetwork
->network
.Configuration
.DSConfig
) >= 0)
1264 ev
= translate_scan(padapter
, a
, pnetwork
, ev
, stop
);
1266 plist
= plist
->next
;
1269 spin_unlock_bh(&pmlmepriv
->scanned_queue
.lock
);
1271 wrqu
->data
.length
= ev
-extra
;
1272 wrqu
->data
.flags
= 0;
1279 /* s1. rtw_set_802_11_infrastructure_mode() */
1280 /* s2. set_802_11_authenticaion_mode() */
1281 /* s3. set_802_11_encryption_mode() */
1282 /* s4. rtw_set_802_11_ssid() */
1283 static int rtw_wx_set_essid(struct net_device
*dev
,
1284 struct iw_request_info
*a
,
1285 union iwreq_data
*wrqu
, char *extra
)
1287 struct adapter
*padapter
= (struct adapter
*)rtw_netdev_priv(dev
);
1288 struct mlme_priv
*pmlmepriv
= &padapter
->mlmepriv
;
1289 struct __queue
*queue
= &pmlmepriv
->scanned_queue
;
1290 struct list_head
*phead
;
1291 struct wlan_network
*pnetwork
= NULL
;
1292 enum ndis_802_11_auth_mode authmode
;
1293 struct ndis_802_11_ssid ndis_ssid
;
1294 u8
*dst_ssid
, *src_ssid
;
1299 RT_TRACE(_module_rtl871x_ioctl_os_c
, _drv_info_
,
1300 ("+rtw_wx_set_essid: fw_state = 0x%08x\n", get_fwstate(pmlmepriv
)));
1301 if (_FAIL
== rtw_pwr_wakeup(padapter
)) {
1306 if (!padapter
->bup
) {
1311 if (wrqu
->essid
.length
> IW_ESSID_MAX_SIZE
) {
1316 if (check_fwstate(pmlmepriv
, WIFI_AP_STATE
)) {
1321 authmode
= padapter
->securitypriv
.ndisauthtype
;
1322 DBG_88E("=>%s\n", __func__
);
1323 if (wrqu
->essid
.flags
&& wrqu
->essid
.length
) {
1324 len
= min_t(uint
, wrqu
->essid
.length
, IW_ESSID_MAX_SIZE
);
1326 if (wrqu
->essid
.length
!= 33)
1327 DBG_88E("ssid =%s, len =%d\n", extra
, wrqu
->essid
.length
);
1329 memset(&ndis_ssid
, 0, sizeof(struct ndis_802_11_ssid
));
1330 ndis_ssid
.SsidLength
= len
;
1331 memcpy(ndis_ssid
.Ssid
, extra
, len
);
1332 src_ssid
= ndis_ssid
.Ssid
;
1334 RT_TRACE(_module_rtl871x_ioctl_os_c
, _drv_info_
, ("rtw_wx_set_essid: ssid =[%s]\n", src_ssid
));
1335 spin_lock_bh(&queue
->lock
);
1336 phead
= get_list_head(queue
);
1337 pmlmepriv
->pscanned
= phead
->next
;
1339 while (phead
!= pmlmepriv
->pscanned
) {
1340 pnetwork
= container_of(pmlmepriv
->pscanned
, struct wlan_network
, list
);
1342 pmlmepriv
->pscanned
= pmlmepriv
->pscanned
->next
;
1344 dst_ssid
= pnetwork
->network
.Ssid
.Ssid
;
1346 RT_TRACE(_module_rtl871x_ioctl_os_c
, _drv_info_
,
1347 ("rtw_wx_set_essid: dst_ssid =%s\n",
1348 pnetwork
->network
.Ssid
.Ssid
));
1350 if ((!memcmp(dst_ssid
, src_ssid
, ndis_ssid
.SsidLength
)) &&
1351 (pnetwork
->network
.Ssid
.SsidLength
== ndis_ssid
.SsidLength
)) {
1352 RT_TRACE(_module_rtl871x_ioctl_os_c
, _drv_info_
,
1353 ("rtw_wx_set_essid: find match, set infra mode\n"));
1355 if (check_fwstate(pmlmepriv
, WIFI_ADHOC_STATE
) == true) {
1356 if (pnetwork
->network
.InfrastructureMode
!= pmlmepriv
->cur_network
.network
.InfrastructureMode
)
1360 if (!rtw_set_802_11_infrastructure_mode(padapter
, pnetwork
->network
.InfrastructureMode
)) {
1362 spin_unlock_bh(&queue
->lock
);
1369 spin_unlock_bh(&queue
->lock
);
1370 RT_TRACE(_module_rtl871x_ioctl_os_c
, _drv_info_
,
1371 ("set ssid: set_802_11_auth. mode =%d\n", authmode
));
1372 rtw_set_802_11_authentication_mode(padapter
, authmode
);
1373 if (rtw_set_802_11_ssid(padapter
, &ndis_ssid
) == false) {
1381 DBG_88E("<=%s, ret %d\n", __func__
, ret
);
1387 static int rtw_wx_get_essid(struct net_device
*dev
,
1388 struct iw_request_info
*a
,
1389 union iwreq_data
*wrqu
, char *extra
)
1392 struct adapter
*padapter
= (struct adapter
*)rtw_netdev_priv(dev
);
1393 struct mlme_priv
*pmlmepriv
= &(padapter
->mlmepriv
);
1394 struct wlan_bssid_ex
*pcur_bss
= &pmlmepriv
->cur_network
.network
;
1396 RT_TRACE(_module_rtl871x_mlme_c_
, _drv_info_
, ("rtw_wx_get_essid\n"));
1399 if ((check_fwstate(pmlmepriv
, _FW_LINKED
)) ||
1400 (check_fwstate(pmlmepriv
, WIFI_ADHOC_MASTER_STATE
))) {
1401 len
= pcur_bss
->Ssid
.SsidLength
;
1403 wrqu
->essid
.length
= len
;
1405 memcpy(extra
, pcur_bss
->Ssid
.Ssid
, len
);
1407 wrqu
->essid
.flags
= 1;
1419 static int rtw_wx_set_rate(struct net_device
*dev
,
1420 struct iw_request_info
*a
,
1421 union iwreq_data
*wrqu
, char *extra
)
1424 u8 datarates
[NumRates
];
1425 u32 target_rate
= wrqu
->bitrate
.value
;
1426 u32 fixed
= wrqu
->bitrate
.fixed
;
1428 u8 mpdatarate
[NumRates
] = {11, 10, 9, 8, 7, 6, 5, 4, 3, 2, 1, 0, 0xff};
1431 RT_TRACE(_module_rtl871x_mlme_c_
, _drv_info_
, (" rtw_wx_set_rate\n"));
1432 RT_TRACE(_module_rtl871x_ioctl_os_c
, _drv_info_
, ("target_rate = %d, fixed = %d\n", target_rate
, fixed
));
1434 if (target_rate
== -1) {
1438 target_rate
= target_rate
/100000;
1440 switch (target_rate
) {
1484 for (i
= 0; i
< NumRates
; i
++) {
1485 if (ratevalue
== mpdatarate
[i
]) {
1486 datarates
[i
] = mpdatarate
[i
];
1490 datarates
[i
] = 0xff;
1493 RT_TRACE(_module_rtl871x_ioctl_os_c
, _drv_info_
, ("datarate_inx =%d\n", datarates
[i
]));
1499 static int rtw_wx_get_rate(struct net_device
*dev
,
1500 struct iw_request_info
*info
,
1501 union iwreq_data
*wrqu
, char *extra
)
1505 max_rate
= rtw_get_cur_max_rate((struct adapter
*)rtw_netdev_priv(dev
));
1510 wrqu
->bitrate
.fixed
= 0; /* no auto select */
1511 wrqu
->bitrate
.value
= max_rate
* 100000;
1516 static int rtw_wx_set_rts(struct net_device
*dev
,
1517 struct iw_request_info
*info
,
1518 union iwreq_data
*wrqu
, char *extra
)
1520 struct adapter
*padapter
= (struct adapter
*)rtw_netdev_priv(dev
);
1523 if (wrqu
->rts
.disabled
) {
1524 padapter
->registrypriv
.rts_thresh
= 2347;
1526 if (wrqu
->rts
.value
< 0 ||
1527 wrqu
->rts
.value
> 2347)
1530 padapter
->registrypriv
.rts_thresh
= wrqu
->rts
.value
;
1533 DBG_88E("%s, rts_thresh =%d\n", __func__
, padapter
->registrypriv
.rts_thresh
);
1539 static int rtw_wx_get_rts(struct net_device
*dev
,
1540 struct iw_request_info
*info
,
1541 union iwreq_data
*wrqu
, char *extra
)
1543 struct adapter
*padapter
= (struct adapter
*)rtw_netdev_priv(dev
);
1546 DBG_88E("%s, rts_thresh =%d\n", __func__
, padapter
->registrypriv
.rts_thresh
);
1548 wrqu
->rts
.value
= padapter
->registrypriv
.rts_thresh
;
1549 wrqu
->rts
.fixed
= 0; /* no auto select */
1550 /* wrqu->rts.disabled = (wrqu->rts.value == DEFAULT_RTS_THRESHOLD); */
1556 static int rtw_wx_set_frag(struct net_device
*dev
,
1557 struct iw_request_info
*info
,
1558 union iwreq_data
*wrqu
, char *extra
)
1560 struct adapter
*padapter
= (struct adapter
*)rtw_netdev_priv(dev
);
1563 if (wrqu
->frag
.disabled
) {
1564 padapter
->xmitpriv
.frag_len
= MAX_FRAG_THRESHOLD
;
1566 if (wrqu
->frag
.value
< MIN_FRAG_THRESHOLD
||
1567 wrqu
->frag
.value
> MAX_FRAG_THRESHOLD
)
1570 padapter
->xmitpriv
.frag_len
= wrqu
->frag
.value
& ~0x1;
1573 DBG_88E("%s, frag_len =%d\n", __func__
, padapter
->xmitpriv
.frag_len
);
1579 static int rtw_wx_get_frag(struct net_device
*dev
,
1580 struct iw_request_info
*info
,
1581 union iwreq_data
*wrqu
, char *extra
)
1583 struct adapter
*padapter
= (struct adapter
*)rtw_netdev_priv(dev
);
1586 DBG_88E("%s, frag_len =%d\n", __func__
, padapter
->xmitpriv
.frag_len
);
1588 wrqu
->frag
.value
= padapter
->xmitpriv
.frag_len
;
1589 wrqu
->frag
.fixed
= 0; /* no auto select */
1595 static int rtw_wx_get_retry(struct net_device
*dev
,
1596 struct iw_request_info
*info
,
1597 union iwreq_data
*wrqu
, char *extra
)
1599 wrqu
->retry
.value
= 7;
1600 wrqu
->retry
.fixed
= 0; /* no auto select */
1601 wrqu
->retry
.disabled
= 1;
1606 static int rtw_wx_set_enc(struct net_device
*dev
,
1607 struct iw_request_info
*info
,
1608 union iwreq_data
*wrqu
, char *keybuf
)
1611 u32 keyindex_provided
;
1612 struct ndis_802_11_wep wep
;
1613 enum ndis_802_11_auth_mode authmode
;
1615 struct iw_point
*erq
= &(wrqu
->encoding
);
1616 struct adapter
*padapter
= (struct adapter
*)rtw_netdev_priv(dev
);
1617 struct pwrctrl_priv
*pwrpriv
= &padapter
->pwrctrlpriv
;
1618 DBG_88E("+rtw_wx_set_enc, flags = 0x%x\n", erq
->flags
);
1620 memset(&wep
, 0, sizeof(struct ndis_802_11_wep
));
1622 key
= erq
->flags
& IW_ENCODE_INDEX
;
1625 if (erq
->flags
& IW_ENCODE_DISABLED
) {
1626 DBG_88E("EncryptionDisabled\n");
1627 padapter
->securitypriv
.ndisencryptstatus
= Ndis802_11EncryptionDisabled
;
1628 padapter
->securitypriv
.dot11PrivacyAlgrthm
= _NO_PRIVACY_
;
1629 padapter
->securitypriv
.dot118021XGrpPrivacy
= _NO_PRIVACY_
;
1630 padapter
->securitypriv
.dot11AuthAlgrthm
= dot11AuthAlgrthm_Open
;
1631 authmode
= Ndis802_11AuthModeOpen
;
1632 padapter
->securitypriv
.ndisauthtype
= authmode
;
1641 keyindex_provided
= 1;
1643 keyindex_provided
= 0;
1644 key
= padapter
->securitypriv
.dot11PrivacyKeyIndex
;
1645 DBG_88E("rtw_wx_set_enc, key =%d\n", key
);
1648 /* set authentication mode */
1649 if (erq
->flags
& IW_ENCODE_OPEN
) {
1650 DBG_88E("rtw_wx_set_enc():IW_ENCODE_OPEN\n");
1651 padapter
->securitypriv
.ndisencryptstatus
= Ndis802_11Encryption1Enabled
;/* Ndis802_11EncryptionDisabled; */
1652 padapter
->securitypriv
.dot11AuthAlgrthm
= dot11AuthAlgrthm_Open
;
1653 padapter
->securitypriv
.dot11PrivacyAlgrthm
= _NO_PRIVACY_
;
1654 padapter
->securitypriv
.dot118021XGrpPrivacy
= _NO_PRIVACY_
;
1655 authmode
= Ndis802_11AuthModeOpen
;
1656 padapter
->securitypriv
.ndisauthtype
= authmode
;
1657 } else if (erq
->flags
& IW_ENCODE_RESTRICTED
) {
1658 DBG_88E("rtw_wx_set_enc():IW_ENCODE_RESTRICTED\n");
1659 padapter
->securitypriv
.ndisencryptstatus
= Ndis802_11Encryption1Enabled
;
1660 padapter
->securitypriv
.dot11AuthAlgrthm
= dot11AuthAlgrthm_Shared
;
1661 padapter
->securitypriv
.dot11PrivacyAlgrthm
= _WEP40_
;
1662 padapter
->securitypriv
.dot118021XGrpPrivacy
= _WEP40_
;
1663 authmode
= Ndis802_11AuthModeShared
;
1664 padapter
->securitypriv
.ndisauthtype
= authmode
;
1666 DBG_88E("rtw_wx_set_enc():erq->flags = 0x%x\n", erq
->flags
);
1668 padapter
->securitypriv
.ndisencryptstatus
= Ndis802_11Encryption1Enabled
;/* Ndis802_11EncryptionDisabled; */
1669 padapter
->securitypriv
.dot11AuthAlgrthm
= dot11AuthAlgrthm_Open
;
1670 padapter
->securitypriv
.dot11PrivacyAlgrthm
= _NO_PRIVACY_
;
1671 padapter
->securitypriv
.dot118021XGrpPrivacy
= _NO_PRIVACY_
;
1672 authmode
= Ndis802_11AuthModeOpen
;
1673 padapter
->securitypriv
.ndisauthtype
= authmode
;
1677 if (erq
->length
> 0) {
1678 wep
.KeyLength
= erq
->length
<= 5 ? 5 : 13;
1680 wep
.Length
= wep
.KeyLength
+ FIELD_OFFSET(struct ndis_802_11_wep
, KeyMaterial
);
1684 if (keyindex_provided
== 1) {
1685 /* set key_id only, no given KeyMaterial(erq->length == 0). */
1686 padapter
->securitypriv
.dot11PrivacyKeyIndex
= key
;
1688 DBG_88E("(keyindex_provided == 1), keyid =%d, key_len =%d\n", key
, padapter
->securitypriv
.dot11DefKeylen
[key
]);
1690 switch (padapter
->securitypriv
.dot11DefKeylen
[key
]) {
1692 padapter
->securitypriv
.dot11PrivacyAlgrthm
= _WEP40_
;
1695 padapter
->securitypriv
.dot11PrivacyAlgrthm
= _WEP104_
;
1698 padapter
->securitypriv
.dot11PrivacyAlgrthm
= _NO_PRIVACY_
;
1706 wep
.KeyIndex
|= 0x80000000;
1708 memcpy(wep
.KeyMaterial
, keybuf
, wep
.KeyLength
);
1710 if (rtw_set_802_11_add_wep(padapter
, &wep
) == false) {
1711 if (rf_on
== pwrpriv
->rf_pwrstate
)
1722 static int rtw_wx_get_enc(struct net_device
*dev
,
1723 struct iw_request_info
*info
,
1724 union iwreq_data
*wrqu
, char *keybuf
)
1727 struct adapter
*padapter
= (struct adapter
*)rtw_netdev_priv(dev
);
1728 struct iw_point
*erq
= &(wrqu
->encoding
);
1729 struct mlme_priv
*pmlmepriv
= &(padapter
->mlmepriv
);
1732 if (check_fwstate(pmlmepriv
, _FW_LINKED
) != true) {
1733 if (!check_fwstate(pmlmepriv
, WIFI_ADHOC_MASTER_STATE
)) {
1735 erq
->flags
|= IW_ENCODE_DISABLED
;
1740 key
= erq
->flags
& IW_ENCODE_INDEX
;
1747 key
= padapter
->securitypriv
.dot11PrivacyKeyIndex
;
1750 erq
->flags
= key
+ 1;
1752 switch (padapter
->securitypriv
.ndisencryptstatus
) {
1753 case Ndis802_11EncryptionNotSupported
:
1754 case Ndis802_11EncryptionDisabled
:
1756 erq
->flags
|= IW_ENCODE_DISABLED
;
1758 case Ndis802_11Encryption1Enabled
:
1759 erq
->length
= padapter
->securitypriv
.dot11DefKeylen
[key
];
1761 memcpy(keybuf
, padapter
->securitypriv
.dot11DefKey
[key
].skey
, padapter
->securitypriv
.dot11DefKeylen
[key
]);
1763 erq
->flags
|= IW_ENCODE_ENABLED
;
1765 if (padapter
->securitypriv
.ndisauthtype
== Ndis802_11AuthModeOpen
)
1766 erq
->flags
|= IW_ENCODE_OPEN
;
1767 else if (padapter
->securitypriv
.ndisauthtype
== Ndis802_11AuthModeShared
)
1768 erq
->flags
|= IW_ENCODE_RESTRICTED
;
1771 erq
->flags
|= IW_ENCODE_DISABLED
;
1774 case Ndis802_11Encryption2Enabled
:
1775 case Ndis802_11Encryption3Enabled
:
1777 erq
->flags
|= (IW_ENCODE_ENABLED
| IW_ENCODE_OPEN
| IW_ENCODE_NOKEY
);
1781 erq
->flags
|= IW_ENCODE_DISABLED
;
1788 static int rtw_wx_get_power(struct net_device
*dev
,
1789 struct iw_request_info
*info
,
1790 union iwreq_data
*wrqu
, char *extra
)
1792 wrqu
->power
.value
= 0;
1793 wrqu
->power
.fixed
= 0; /* no auto select */
1794 wrqu
->power
.disabled
= 1;
1799 static int rtw_wx_set_gen_ie(struct net_device
*dev
,
1800 struct iw_request_info
*info
,
1801 union iwreq_data
*wrqu
, char *extra
)
1803 struct adapter
*padapter
= (struct adapter
*)rtw_netdev_priv(dev
);
1805 return rtw_set_wpa_ie(padapter
, extra
, wrqu
->data
.length
);
1808 static int rtw_wx_set_auth(struct net_device
*dev
,
1809 struct iw_request_info
*info
,
1810 union iwreq_data
*wrqu
, char *extra
)
1812 struct adapter
*padapter
= (struct adapter
*)rtw_netdev_priv(dev
);
1813 struct iw_param
*param
= (struct iw_param
*)&(wrqu
->param
);
1816 switch (param
->flags
& IW_AUTH_INDEX
) {
1817 case IW_AUTH_WPA_VERSION
:
1819 case IW_AUTH_CIPHER_PAIRWISE
:
1822 case IW_AUTH_CIPHER_GROUP
:
1825 case IW_AUTH_KEY_MGMT
:
1827 * ??? does not use these parameters
1830 case IW_AUTH_TKIP_COUNTERMEASURES
:
1832 /* wpa_supplicant is enabling the tkip countermeasure. */
1833 padapter
->securitypriv
.btkip_countermeasure
= true;
1835 /* wpa_supplicant is disabling the tkip countermeasure. */
1836 padapter
->securitypriv
.btkip_countermeasure
= false;
1839 case IW_AUTH_DROP_UNENCRYPTED
:
1842 * wpa_supplicant calls set_wpa_enabled when the driver
1843 * is loaded and unloaded, regardless of if WPA is being
1844 * used. No other calls are made which can be used to
1845 * determine if encryption will be used or not prior to
1846 * association being expected. If encryption is not being
1847 * used, drop_unencrypted is set to false, else true -- we
1848 * can use this to determine if the CAP_PRIVACY_ON bit should
1852 if (padapter
->securitypriv
.ndisencryptstatus
== Ndis802_11Encryption1Enabled
)
1853 break;/* it means init value, or using wep, ndisencryptstatus = Ndis802_11Encryption1Enabled, */
1854 /* then it needn't reset it; */
1857 padapter
->securitypriv
.ndisencryptstatus
= Ndis802_11EncryptionDisabled
;
1858 padapter
->securitypriv
.dot11PrivacyAlgrthm
= _NO_PRIVACY_
;
1859 padapter
->securitypriv
.dot118021XGrpPrivacy
= _NO_PRIVACY_
;
1860 padapter
->securitypriv
.dot11AuthAlgrthm
= dot11AuthAlgrthm_Open
;
1861 padapter
->securitypriv
.ndisauthtype
= Ndis802_11AuthModeOpen
;
1865 case IW_AUTH_80211_AUTH_ALG
:
1867 * It's the starting point of a link layer connection using wpa_supplicant
1869 if (check_fwstate(&padapter
->mlmepriv
, _FW_LINKED
)) {
1870 LeaveAllPowerSaveMode(padapter
);
1871 rtw_disassoc_cmd(padapter
, 500, false);
1872 DBG_88E("%s...call rtw_indicate_disconnect\n ", __func__
);
1873 rtw_indicate_disconnect(padapter
);
1874 rtw_free_assoc_resources(padapter
);
1876 ret
= wpa_set_auth_algs(dev
, (u32
)param
->value
);
1878 case IW_AUTH_WPA_ENABLED
:
1880 case IW_AUTH_RX_UNENCRYPTED_EAPOL
:
1882 case IW_AUTH_PRIVACY_INVOKED
:
1891 static int rtw_wx_set_enc_ext(struct net_device
*dev
,
1892 struct iw_request_info
*info
,
1893 union iwreq_data
*wrqu
, char *extra
)
1897 struct ieee_param
*param
= NULL
;
1898 struct iw_point
*pencoding
= &wrqu
->encoding
;
1899 struct iw_encode_ext
*pext
= (struct iw_encode_ext
*)extra
;
1902 param_len
= sizeof(struct ieee_param
) + pext
->key_len
;
1903 param
= (struct ieee_param
*)rtw_malloc(param_len
);
1907 memset(param
, 0, param_len
);
1909 param
->cmd
= IEEE_CMD_SET_ENCRYPTION
;
1910 memset(param
->sta_addr
, 0xff, ETH_ALEN
);
1912 switch (pext
->alg
) {
1913 case IW_ENCODE_ALG_NONE
:
1914 /* todo: remove key */
1918 case IW_ENCODE_ALG_WEP
:
1921 case IW_ENCODE_ALG_TKIP
:
1924 case IW_ENCODE_ALG_CCMP
:
1932 strncpy((char *)param
->u
.crypt
.alg
, alg_name
, IEEE_CRYPT_ALG_NAME_LEN
);
1934 if (pext
->ext_flags
& IW_ENCODE_EXT_SET_TX_KEY
)
1935 param
->u
.crypt
.set_tx
= 1;
1937 /* cliW: WEP does not have group key
1938 * just not checking GROUP key setting
1940 if ((pext
->alg
!= IW_ENCODE_ALG_WEP
) &&
1941 (pext
->ext_flags
& IW_ENCODE_EXT_GROUP_KEY
))
1942 param
->u
.crypt
.set_tx
= 0;
1944 param
->u
.crypt
.idx
= (pencoding
->flags
&0x00FF) - 1;
1946 if (pext
->ext_flags
& IW_ENCODE_EXT_RX_SEQ_VALID
)
1947 memcpy(param
->u
.crypt
.seq
, pext
->rx_seq
, 8);
1949 if (pext
->key_len
) {
1950 param
->u
.crypt
.key_len
= pext
->key_len
;
1951 memcpy(param
->u
.crypt
.key
, pext
+ 1, pext
->key_len
);
1954 ret
= wpa_set_encryption(dev
, param
, param_len
);
1961 static int rtw_wx_get_nick(struct net_device
*dev
,
1962 struct iw_request_info
*info
,
1963 union iwreq_data
*wrqu
, char *extra
)
1966 wrqu
->data
.length
= 14;
1967 wrqu
->data
.flags
= 1;
1968 memcpy(extra
, "<WIFI@REALTEK>", 14);
1971 /* dump debug info here */
1975 static int dummy(struct net_device
*dev
, struct iw_request_info
*a
,
1976 union iwreq_data
*wrqu
, char *b
)
1981 static int wpa_set_param(struct net_device
*dev
, u8 name
, u32 value
)
1984 struct adapter
*padapter
= (struct adapter
*)rtw_netdev_priv(dev
);
1987 case IEEE_PARAM_WPA_ENABLED
:
1988 padapter
->securitypriv
.dot11AuthAlgrthm
= dot11AuthAlgrthm_8021X
; /* 802.1x */
1989 switch ((value
)&0xff) {
1991 padapter
->securitypriv
.ndisauthtype
= Ndis802_11AuthModeWPAPSK
; /* WPA_PSK */
1992 padapter
->securitypriv
.ndisencryptstatus
= Ndis802_11Encryption2Enabled
;
1995 padapter
->securitypriv
.ndisauthtype
= Ndis802_11AuthModeWPA2PSK
; /* WPA2_PSK */
1996 padapter
->securitypriv
.ndisencryptstatus
= Ndis802_11Encryption3Enabled
;
1999 RT_TRACE(_module_rtl871x_ioctl_os_c
, _drv_info_
,
2000 ("wpa_set_param:padapter->securitypriv.ndisauthtype =%d\n", padapter
->securitypriv
.ndisauthtype
));
2002 case IEEE_PARAM_TKIP_COUNTERMEASURES
:
2004 case IEEE_PARAM_DROP_UNENCRYPTED
: {
2007 * wpa_supplicant calls set_wpa_enabled when the driver
2008 * is loaded and unloaded, regardless of if WPA is being
2009 * used. No other calls are made which can be used to
2010 * determine if encryption will be used or not prior to
2011 * association being expected. If encryption is not being
2012 * used, drop_unencrypted is set to false, else true -- we
2013 * can use this to determine if the CAP_PRIVACY_ON bit should
2019 case IEEE_PARAM_PRIVACY_INVOKED
:
2022 case IEEE_PARAM_AUTH_ALGS
:
2023 ret
= wpa_set_auth_algs(dev
, value
);
2025 case IEEE_PARAM_IEEE_802_1X
:
2027 case IEEE_PARAM_WPAX_SELECT
:
2036 static int wpa_mlme(struct net_device
*dev
, u32 command
, u32 reason
)
2039 struct adapter
*padapter
= (struct adapter
*)rtw_netdev_priv(dev
);
2042 case IEEE_MLME_STA_DEAUTH
:
2043 if (!rtw_set_802_11_disassociate(padapter
))
2046 case IEEE_MLME_STA_DISASSOC
:
2047 if (!rtw_set_802_11_disassociate(padapter
))
2058 static int wpa_supplicant_ioctl(struct net_device
*dev
, struct iw_point
*p
)
2060 struct ieee_param
*param
;
2063 if (p
->length
< sizeof(struct ieee_param
) || !p
->pointer
) {
2068 param
= (struct ieee_param
*)rtw_malloc(p
->length
);
2069 if (param
== NULL
) {
2074 if (copy_from_user(param
, p
->pointer
, p
->length
)) {
2080 switch (param
->cmd
) {
2081 case IEEE_CMD_SET_WPA_PARAM
:
2082 ret
= wpa_set_param(dev
, param
->u
.wpa_param
.name
, param
->u
.wpa_param
.value
);
2085 case IEEE_CMD_SET_WPA_IE
:
2086 ret
= rtw_set_wpa_ie((struct adapter
*)rtw_netdev_priv(dev
),
2087 (char *)param
->u
.wpa_ie
.data
, (u16
)param
->u
.wpa_ie
.len
);
2090 case IEEE_CMD_SET_ENCRYPTION
:
2091 ret
= wpa_set_encryption(dev
, param
, p
->length
);
2095 ret
= wpa_mlme(dev
, param
->u
.mlme
.command
, param
->u
.mlme
.reason_code
);
2099 DBG_88E("Unknown WPA supplicant request: %d\n", param
->cmd
);
2104 if (ret
== 0 && copy_to_user(p
->pointer
, param
, p
->length
))
2114 #ifdef CONFIG_88EU_AP_MODE
2115 static u8
set_pairwise_key(struct adapter
*padapter
, struct sta_info
*psta
)
2117 struct cmd_obj
*ph2c
;
2118 struct set_stakey_parm
*psetstakey_para
;
2119 struct cmd_priv
*pcmdpriv
= &padapter
->cmdpriv
;
2122 ph2c
= kzalloc(sizeof(struct cmd_obj
), GFP_KERNEL
);
2128 psetstakey_para
= kzalloc(sizeof(struct set_stakey_parm
), GFP_KERNEL
);
2129 if (psetstakey_para
== NULL
) {
2135 init_h2fwcmd_w_parm_no_rsp(ph2c
, psetstakey_para
, _SetStaKey_CMD_
);
2137 psetstakey_para
->algorithm
= (u8
)psta
->dot118021XPrivacy
;
2139 memcpy(psetstakey_para
->addr
, psta
->hwaddr
, ETH_ALEN
);
2141 memcpy(psetstakey_para
->key
, &psta
->dot118021x_UncstKey
, 16);
2143 res
= rtw_enqueue_cmd(pcmdpriv
, ph2c
);
2150 static int set_group_key(struct adapter
*padapter
, u8
*key
, u8 alg
, int keyid
)
2153 struct cmd_obj
*pcmd
;
2154 struct setkey_parm
*psetkeyparm
;
2155 struct cmd_priv
*pcmdpriv
= &(padapter
->cmdpriv
);
2158 DBG_88E("%s\n", __func__
);
2160 pcmd
= kzalloc(sizeof(struct cmd_obj
), GFP_KERNEL
);
2165 psetkeyparm
= kzalloc(sizeof(struct setkey_parm
), GFP_KERNEL
);
2166 if (psetkeyparm
== NULL
) {
2172 memset(psetkeyparm
, 0, sizeof(struct setkey_parm
));
2174 psetkeyparm
->keyid
= (u8
)keyid
;
2176 psetkeyparm
->algorithm
= alg
;
2178 psetkeyparm
->set_tx
= 1;
2194 memcpy(&(psetkeyparm
->key
[0]), key
, keylen
);
2196 pcmd
->cmdcode
= _SetKey_CMD_
;
2197 pcmd
->parmbuf
= (u8
*)psetkeyparm
;
2198 pcmd
->cmdsz
= (sizeof(struct setkey_parm
));
2202 INIT_LIST_HEAD(&pcmd
->list
);
2204 res
= rtw_enqueue_cmd(pcmdpriv
, pcmd
);
2211 static int set_wep_key(struct adapter
*padapter
, u8
*key
, u8 keylen
, int keyid
)
2226 return set_group_key(padapter
, key
, alg
, keyid
);
2229 static int rtw_set_encryption(struct net_device
*dev
, struct ieee_param
*param
, u32 param_len
)
2232 u32 wep_key_idx
, wep_key_len
, wep_total_len
;
2233 struct ndis_802_11_wep
*pwep
= NULL
;
2234 struct sta_info
*psta
= NULL
, *pbcmc_sta
= NULL
;
2235 struct adapter
*padapter
= (struct adapter
*)rtw_netdev_priv(dev
);
2236 struct mlme_priv
*pmlmepriv
= &padapter
->mlmepriv
;
2237 struct security_priv
*psecuritypriv
= &(padapter
->securitypriv
);
2238 struct sta_priv
*pstapriv
= &padapter
->stapriv
;
2240 DBG_88E("%s\n", __func__
);
2241 param
->u
.crypt
.err
= 0;
2242 param
->u
.crypt
.alg
[IEEE_CRYPT_ALG_NAME_LEN
- 1] = '\0';
2243 if (param_len
!= sizeof(struct ieee_param
) + param
->u
.crypt
.key_len
) {
2247 if (param
->sta_addr
[0] == 0xff && param
->sta_addr
[1] == 0xff &&
2248 param
->sta_addr
[2] == 0xff && param
->sta_addr
[3] == 0xff &&
2249 param
->sta_addr
[4] == 0xff && param
->sta_addr
[5] == 0xff) {
2250 if (param
->u
.crypt
.idx
>= WEP_KEYS
) {
2255 psta
= rtw_get_stainfo(pstapriv
, param
->sta_addr
);
2257 DBG_88E("rtw_set_encryption(), sta has already been removed or never been added\n");
2262 if (strcmp(param
->u
.crypt
.alg
, "none") == 0 && (psta
== NULL
)) {
2263 /* todo:clear default encryption keys */
2265 DBG_88E("clear default encryption keys, keyid =%d\n", param
->u
.crypt
.idx
);
2268 if (strcmp(param
->u
.crypt
.alg
, "WEP") == 0 && (psta
== NULL
)) {
2269 DBG_88E("r871x_set_encryption, crypt.alg = WEP\n");
2270 wep_key_idx
= param
->u
.crypt
.idx
;
2271 wep_key_len
= param
->u
.crypt
.key_len
;
2272 DBG_88E("r871x_set_encryption, wep_key_idx=%d, len=%d\n", wep_key_idx
, wep_key_len
);
2273 if ((wep_key_idx
>= WEP_KEYS
) || (wep_key_len
<= 0)) {
2278 if (wep_key_len
> 0) {
2279 wep_key_len
= wep_key_len
<= 5 ? 5 : 13;
2280 wep_total_len
= wep_key_len
+ FIELD_OFFSET(struct ndis_802_11_wep
, KeyMaterial
);
2281 pwep
= (struct ndis_802_11_wep
*)rtw_malloc(wep_total_len
);
2283 DBG_88E(" r871x_set_encryption: pwep allocate fail !!!\n");
2287 memset(pwep
, 0, wep_total_len
);
2289 pwep
->KeyLength
= wep_key_len
;
2290 pwep
->Length
= wep_total_len
;
2293 pwep
->KeyIndex
= wep_key_idx
;
2295 memcpy(pwep
->KeyMaterial
, param
->u
.crypt
.key
, pwep
->KeyLength
);
2297 if (param
->u
.crypt
.set_tx
) {
2298 DBG_88E("wep, set_tx = 1\n");
2300 psecuritypriv
->ndisencryptstatus
= Ndis802_11Encryption1Enabled
;
2301 psecuritypriv
->dot11PrivacyAlgrthm
= _WEP40_
;
2302 psecuritypriv
->dot118021XGrpPrivacy
= _WEP40_
;
2304 if (pwep
->KeyLength
== 13) {
2305 psecuritypriv
->dot11PrivacyAlgrthm
= _WEP104_
;
2306 psecuritypriv
->dot118021XGrpPrivacy
= _WEP104_
;
2309 psecuritypriv
->dot11PrivacyKeyIndex
= wep_key_idx
;
2311 memcpy(&(psecuritypriv
->dot11DefKey
[wep_key_idx
].skey
[0]), pwep
->KeyMaterial
, pwep
->KeyLength
);
2313 psecuritypriv
->dot11DefKeylen
[wep_key_idx
] = pwep
->KeyLength
;
2315 set_wep_key(padapter
, pwep
->KeyMaterial
, pwep
->KeyLength
, wep_key_idx
);
2317 DBG_88E("wep, set_tx = 0\n");
2319 /* don't update "psecuritypriv->dot11PrivacyAlgrthm" and */
2320 /* psecuritypriv->dot11PrivacyKeyIndex = keyid", but can rtw_set_key to cam */
2322 memcpy(&(psecuritypriv
->dot11DefKey
[wep_key_idx
].skey
[0]), pwep
->KeyMaterial
, pwep
->KeyLength
);
2324 psecuritypriv
->dot11DefKeylen
[wep_key_idx
] = pwep
->KeyLength
;
2326 set_wep_key(padapter
, pwep
->KeyMaterial
, pwep
->KeyLength
, wep_key_idx
);
2332 if (!psta
&& check_fwstate(pmlmepriv
, WIFI_AP_STATE
)) { /* group key */
2333 if (param
->u
.crypt
.set_tx
== 1) {
2334 if (strcmp(param
->u
.crypt
.alg
, "WEP") == 0) {
2335 DBG_88E("%s, set group_key, WEP\n", __func__
);
2337 memcpy(psecuritypriv
->dot118021XGrpKey
[param
->u
.crypt
.idx
].skey
,
2338 param
->u
.crypt
.key
, min_t(u16
, param
->u
.crypt
.key_len
, 16));
2340 psecuritypriv
->dot118021XGrpPrivacy
= _WEP40_
;
2341 if (param
->u
.crypt
.key_len
== 13)
2342 psecuritypriv
->dot118021XGrpPrivacy
= _WEP104_
;
2343 } else if (strcmp(param
->u
.crypt
.alg
, "TKIP") == 0) {
2344 DBG_88E("%s, set group_key, TKIP\n", __func__
);
2345 psecuritypriv
->dot118021XGrpPrivacy
= _TKIP_
;
2346 memcpy(psecuritypriv
->dot118021XGrpKey
[param
->u
.crypt
.idx
].skey
,
2347 param
->u
.crypt
.key
, min_t(u16
, param
->u
.crypt
.key_len
, 16));
2349 memcpy(psecuritypriv
->dot118021XGrptxmickey
[param
->u
.crypt
.idx
].skey
, &(param
->u
.crypt
.key
[16]), 8);
2350 memcpy(psecuritypriv
->dot118021XGrprxmickey
[param
->u
.crypt
.idx
].skey
, &(param
->u
.crypt
.key
[24]), 8);
2352 psecuritypriv
->busetkipkey
= true;
2353 } else if (strcmp(param
->u
.crypt
.alg
, "CCMP") == 0) {
2354 DBG_88E("%s, set group_key, CCMP\n", __func__
);
2355 psecuritypriv
->dot118021XGrpPrivacy
= _AES_
;
2356 memcpy(psecuritypriv
->dot118021XGrpKey
[param
->u
.crypt
.idx
].skey
,
2357 param
->u
.crypt
.key
, min_t(u16
, param
->u
.crypt
.key_len
, 16));
2359 DBG_88E("%s, set group_key, none\n", __func__
);
2360 psecuritypriv
->dot118021XGrpPrivacy
= _NO_PRIVACY_
;
2362 psecuritypriv
->dot118021XGrpKeyid
= param
->u
.crypt
.idx
;
2363 psecuritypriv
->binstallGrpkey
= true;
2364 psecuritypriv
->dot11PrivacyAlgrthm
= psecuritypriv
->dot118021XGrpPrivacy
;/* */
2365 set_group_key(padapter
, param
->u
.crypt
.key
, psecuritypriv
->dot118021XGrpPrivacy
, param
->u
.crypt
.idx
);
2366 pbcmc_sta
= rtw_get_bcmc_stainfo(padapter
);
2368 pbcmc_sta
->ieee8021x_blocked
= false;
2369 pbcmc_sta
->dot118021XPrivacy
= psecuritypriv
->dot118021XGrpPrivacy
;/* rx will use bmc_sta's dot118021XPrivacy */
2375 if (psecuritypriv
->dot11AuthAlgrthm
== dot11AuthAlgrthm_8021X
&& psta
) { /* psk/802_1x */
2376 if (check_fwstate(pmlmepriv
, WIFI_AP_STATE
)) {
2377 if (param
->u
.crypt
.set_tx
== 1) {
2378 memcpy(psta
->dot118021x_UncstKey
.skey
, param
->u
.crypt
.key
, min_t(u16
, param
->u
.crypt
.key_len
, 16));
2380 if (strcmp(param
->u
.crypt
.alg
, "WEP") == 0) {
2381 DBG_88E("%s, set pairwise key, WEP\n", __func__
);
2383 psta
->dot118021XPrivacy
= _WEP40_
;
2384 if (param
->u
.crypt
.key_len
== 13)
2385 psta
->dot118021XPrivacy
= _WEP104_
;
2386 } else if (strcmp(param
->u
.crypt
.alg
, "TKIP") == 0) {
2387 DBG_88E("%s, set pairwise key, TKIP\n", __func__
);
2389 psta
->dot118021XPrivacy
= _TKIP_
;
2392 memcpy(psta
->dot11tkiptxmickey
.skey
, &(param
->u
.crypt
.key
[16]), 8);
2393 memcpy(psta
->dot11tkiprxmickey
.skey
, &(param
->u
.crypt
.key
[24]), 8);
2395 psecuritypriv
->busetkipkey
= true;
2396 } else if (strcmp(param
->u
.crypt
.alg
, "CCMP") == 0) {
2397 DBG_88E("%s, set pairwise key, CCMP\n", __func__
);
2399 psta
->dot118021XPrivacy
= _AES_
;
2401 DBG_88E("%s, set pairwise key, none\n", __func__
);
2403 psta
->dot118021XPrivacy
= _NO_PRIVACY_
;
2406 set_pairwise_key(padapter
, psta
);
2408 psta
->ieee8021x_blocked
= false;
2409 } else { /* group key??? */
2410 if (strcmp(param
->u
.crypt
.alg
, "WEP") == 0) {
2411 memcpy(psecuritypriv
->dot118021XGrpKey
[param
->u
.crypt
.idx
].skey
,
2412 param
->u
.crypt
.key
, min_t(u16
, param
->u
.crypt
.key_len
, 16));
2413 psecuritypriv
->dot118021XGrpPrivacy
= _WEP40_
;
2414 if (param
->u
.crypt
.key_len
== 13)
2415 psecuritypriv
->dot118021XGrpPrivacy
= _WEP104_
;
2416 } else if (strcmp(param
->u
.crypt
.alg
, "TKIP") == 0) {
2417 psecuritypriv
->dot118021XGrpPrivacy
= _TKIP_
;
2419 memcpy(psecuritypriv
->dot118021XGrpKey
[param
->u
.crypt
.idx
].skey
,
2420 param
->u
.crypt
.key
, min_t(u16
, param
->u
.crypt
.key_len
, 16));
2423 memcpy(psecuritypriv
->dot118021XGrptxmickey
[param
->u
.crypt
.idx
].skey
, &(param
->u
.crypt
.key
[16]), 8);
2424 memcpy(psecuritypriv
->dot118021XGrprxmickey
[param
->u
.crypt
.idx
].skey
, &(param
->u
.crypt
.key
[24]), 8);
2426 psecuritypriv
->busetkipkey
= true;
2427 } else if (strcmp(param
->u
.crypt
.alg
, "CCMP") == 0) {
2428 psecuritypriv
->dot118021XGrpPrivacy
= _AES_
;
2430 memcpy(psecuritypriv
->dot118021XGrpKey
[param
->u
.crypt
.idx
].skey
,
2431 param
->u
.crypt
.key
, min_t(u16
, param
->u
.crypt
.key_len
, 16));
2433 psecuritypriv
->dot118021XGrpPrivacy
= _NO_PRIVACY_
;
2436 psecuritypriv
->dot118021XGrpKeyid
= param
->u
.crypt
.idx
;
2438 psecuritypriv
->binstallGrpkey
= true;
2440 psecuritypriv
->dot11PrivacyAlgrthm
= psecuritypriv
->dot118021XGrpPrivacy
;/* */
2442 set_group_key(padapter
, param
->u
.crypt
.key
, psecuritypriv
->dot118021XGrpPrivacy
, param
->u
.crypt
.idx
);
2444 pbcmc_sta
= rtw_get_bcmc_stainfo(padapter
);
2446 pbcmc_sta
->ieee8021x_blocked
= false;
2447 pbcmc_sta
->dot118021XPrivacy
= psecuritypriv
->dot118021XGrpPrivacy
;/* rx will use bmc_sta's dot118021XPrivacy */
2460 static int rtw_set_beacon(struct net_device
*dev
, struct ieee_param
*param
, int len
)
2463 struct adapter
*padapter
= (struct adapter
*)rtw_netdev_priv(dev
);
2464 struct mlme_priv
*pmlmepriv
= &(padapter
->mlmepriv
);
2465 struct sta_priv
*pstapriv
= &padapter
->stapriv
;
2466 unsigned char *pbuf
= param
->u
.bcn_ie
.buf
;
2468 DBG_88E("%s, len =%d\n", __func__
, len
);
2470 if (check_fwstate(pmlmepriv
, WIFI_AP_STATE
) != true)
2473 memcpy(&pstapriv
->max_num_sta
, param
->u
.bcn_ie
.reserved
, 2);
2475 if ((pstapriv
->max_num_sta
> NUM_STA
) || (pstapriv
->max_num_sta
<= 0))
2476 pstapriv
->max_num_sta
= NUM_STA
;
2478 if (rtw_check_beacon_data(padapter
, pbuf
, (len
-12-2)) == _SUCCESS
)/* 12 = param header, 2:no packed */
2486 static int rtw_hostapd_sta_flush(struct net_device
*dev
)
2488 struct adapter
*padapter
= (struct adapter
*)rtw_netdev_priv(dev
);
2490 DBG_88E("%s\n", __func__
);
2492 flush_all_cam_entry(padapter
); /* clear CAM */
2494 return rtw_sta_flush(padapter
);
2497 static int rtw_add_sta(struct net_device
*dev
, struct ieee_param
*param
)
2500 struct sta_info
*psta
= NULL
;
2501 struct adapter
*padapter
= (struct adapter
*)rtw_netdev_priv(dev
);
2502 struct mlme_priv
*pmlmepriv
= &(padapter
->mlmepriv
);
2503 struct sta_priv
*pstapriv
= &padapter
->stapriv
;
2505 DBG_88E("rtw_add_sta(aid =%d) =%pM\n", param
->u
.add_sta
.aid
, (param
->sta_addr
));
2507 if (!check_fwstate(pmlmepriv
, (_FW_LINKED
|WIFI_AP_STATE
)))
2510 if (param
->sta_addr
[0] == 0xff && param
->sta_addr
[1] == 0xff &&
2511 param
->sta_addr
[2] == 0xff && param
->sta_addr
[3] == 0xff &&
2512 param
->sta_addr
[4] == 0xff && param
->sta_addr
[5] == 0xff)
2515 psta
= rtw_get_stainfo(pstapriv
, param
->sta_addr
);
2517 int flags
= param
->u
.add_sta
.flags
;
2519 psta
->aid
= param
->u
.add_sta
.aid
;/* aid = 1~2007 */
2521 memcpy(psta
->bssrateset
, param
->u
.add_sta
.tx_supp_rates
, 16);
2523 /* check wmm cap. */
2524 if (WLAN_STA_WME
&flags
)
2525 psta
->qos_option
= 1;
2527 psta
->qos_option
= 0;
2529 if (pmlmepriv
->qospriv
.qos_option
== 0)
2530 psta
->qos_option
= 0;
2532 /* chec 802.11n ht cap. */
2533 if (WLAN_STA_HT
&flags
) {
2534 psta
->htpriv
.ht_option
= true;
2535 psta
->qos_option
= 1;
2536 memcpy((void *)&psta
->htpriv
.ht_cap
, (void *)¶m
->u
.add_sta
.ht_cap
, sizeof(struct rtw_ieee80211_ht_cap
));
2538 psta
->htpriv
.ht_option
= false;
2541 if (pmlmepriv
->htpriv
.ht_option
== false)
2542 psta
->htpriv
.ht_option
= false;
2544 update_sta_info_apmode(padapter
, psta
);
2552 static int rtw_del_sta(struct net_device
*dev
, struct ieee_param
*param
)
2555 struct sta_info
*psta
= NULL
;
2556 struct adapter
*padapter
= (struct adapter
*)rtw_netdev_priv(dev
);
2557 struct mlme_priv
*pmlmepriv
= &(padapter
->mlmepriv
);
2558 struct sta_priv
*pstapriv
= &padapter
->stapriv
;
2561 DBG_88E("rtw_del_sta =%pM\n", (param
->sta_addr
));
2563 if (check_fwstate(pmlmepriv
, (_FW_LINKED
|WIFI_AP_STATE
)) != true)
2566 if (param
->sta_addr
[0] == 0xff && param
->sta_addr
[1] == 0xff &&
2567 param
->sta_addr
[2] == 0xff && param
->sta_addr
[3] == 0xff &&
2568 param
->sta_addr
[4] == 0xff && param
->sta_addr
[5] == 0xff)
2571 psta
= rtw_get_stainfo(pstapriv
, param
->sta_addr
);
2573 spin_lock_bh(&pstapriv
->asoc_list_lock
);
2574 if (!list_empty(&psta
->asoc_list
)) {
2575 list_del_init(&psta
->asoc_list
);
2576 pstapriv
->asoc_list_cnt
--;
2577 updated
= ap_free_sta(padapter
, psta
, true, WLAN_REASON_DEAUTH_LEAVING
);
2579 spin_unlock_bh(&pstapriv
->asoc_list_lock
);
2580 associated_clients_update(padapter
, updated
);
2583 DBG_88E("rtw_del_sta(), sta has already been removed or never been added\n");
2589 static int rtw_ioctl_get_sta_data(struct net_device
*dev
, struct ieee_param
*param
, int len
)
2592 struct sta_info
*psta
= NULL
;
2593 struct adapter
*padapter
= (struct adapter
*)rtw_netdev_priv(dev
);
2594 struct mlme_priv
*pmlmepriv
= &(padapter
->mlmepriv
);
2595 struct sta_priv
*pstapriv
= &padapter
->stapriv
;
2596 struct ieee_param_ex
*param_ex
= (struct ieee_param_ex
*)param
;
2597 struct sta_data
*psta_data
= (struct sta_data
*)param_ex
->data
;
2599 DBG_88E("rtw_ioctl_get_sta_info, sta_addr: %pM\n", (param_ex
->sta_addr
));
2601 if (check_fwstate(pmlmepriv
, (_FW_LINKED
|WIFI_AP_STATE
)) != true)
2604 if (param_ex
->sta_addr
[0] == 0xff && param_ex
->sta_addr
[1] == 0xff &&
2605 param_ex
->sta_addr
[2] == 0xff && param_ex
->sta_addr
[3] == 0xff &&
2606 param_ex
->sta_addr
[4] == 0xff && param_ex
->sta_addr
[5] == 0xff)
2609 psta
= rtw_get_stainfo(pstapriv
, param_ex
->sta_addr
);
2611 psta_data
->aid
= (u16
)psta
->aid
;
2612 psta_data
->capability
= psta
->capability
;
2613 psta_data
->flags
= psta
->flags
;
2617 no_short_slot_time_set : BIT(1)
2618 no_short_preamble_set : BIT(2)
2619 no_ht_gf_set : BIT(3)
2621 ht_20mhz_set : BIT(5)
2624 psta_data
->sta_set
= ((psta
->nonerp_set
) |
2625 (psta
->no_short_slot_time_set
<< 1) |
2626 (psta
->no_short_preamble_set
<< 2) |
2627 (psta
->no_ht_gf_set
<< 3) |
2628 (psta
->no_ht_set
<< 4) |
2629 (psta
->ht_20mhz_set
<< 5));
2630 psta_data
->tx_supp_rates_len
= psta
->bssratelen
;
2631 memcpy(psta_data
->tx_supp_rates
, psta
->bssrateset
, psta
->bssratelen
);
2632 memcpy(&psta_data
->ht_cap
, &psta
->htpriv
.ht_cap
, sizeof(struct rtw_ieee80211_ht_cap
));
2633 psta_data
->rx_pkts
= psta
->sta_stats
.rx_data_pkts
;
2634 psta_data
->rx_bytes
= psta
->sta_stats
.rx_bytes
;
2635 psta_data
->rx_drops
= psta
->sta_stats
.rx_drops
;
2636 psta_data
->tx_pkts
= psta
->sta_stats
.tx_pkts
;
2637 psta_data
->tx_bytes
= psta
->sta_stats
.tx_bytes
;
2638 psta_data
->tx_drops
= psta
->sta_stats
.tx_drops
;
2646 static int rtw_get_sta_wpaie(struct net_device
*dev
, struct ieee_param
*param
)
2649 struct sta_info
*psta
= NULL
;
2650 struct adapter
*padapter
= (struct adapter
*)rtw_netdev_priv(dev
);
2651 struct mlme_priv
*pmlmepriv
= &(padapter
->mlmepriv
);
2652 struct sta_priv
*pstapriv
= &padapter
->stapriv
;
2654 DBG_88E("rtw_get_sta_wpaie, sta_addr: %pM\n", (param
->sta_addr
));
2656 if (check_fwstate(pmlmepriv
, (_FW_LINKED
|WIFI_AP_STATE
)) != true)
2659 if (param
->sta_addr
[0] == 0xff && param
->sta_addr
[1] == 0xff &&
2660 param
->sta_addr
[2] == 0xff && param
->sta_addr
[3] == 0xff &&
2661 param
->sta_addr
[4] == 0xff && param
->sta_addr
[5] == 0xff)
2664 psta
= rtw_get_stainfo(pstapriv
, param
->sta_addr
);
2666 if (psta
->wpa_ie
[0] == WLAN_EID_RSN
||
2667 psta
->wpa_ie
[0] == WLAN_EID_VENDOR_SPECIFIC
) {
2671 wpa_ie_len
= psta
->wpa_ie
[1];
2672 copy_len
= min_t(int, wpa_ie_len
+ 2, sizeof(psta
->wpa_ie
));
2673 param
->u
.wpa_ie
.len
= copy_len
;
2674 memcpy(param
->u
.wpa_ie
.reserved
, psta
->wpa_ie
, copy_len
);
2676 DBG_88E("sta's wpa_ie is NONE\n");
2685 static int rtw_set_wps_beacon(struct net_device
*dev
, struct ieee_param
*param
, int len
)
2688 unsigned char wps_oui
[4] = {0x0, 0x50, 0xf2, 0x04};
2689 struct adapter
*padapter
= (struct adapter
*)rtw_netdev_priv(dev
);
2690 struct mlme_priv
*pmlmepriv
= &(padapter
->mlmepriv
);
2691 struct mlme_ext_priv
*pmlmeext
= &(padapter
->mlmeextpriv
);
2694 DBG_88E("%s, len =%d\n", __func__
, len
);
2696 if (check_fwstate(pmlmepriv
, WIFI_AP_STATE
) != true)
2699 ie_len
= len
-12-2;/* 12 = param header, 2:no packed */
2701 kfree(pmlmepriv
->wps_beacon_ie
);
2702 pmlmepriv
->wps_beacon_ie
= NULL
;
2705 pmlmepriv
->wps_beacon_ie
= rtw_malloc(ie_len
);
2706 pmlmepriv
->wps_beacon_ie_len
= ie_len
;
2707 if (pmlmepriv
->wps_beacon_ie
== NULL
) {
2708 DBG_88E("%s()-%d: rtw_malloc() ERROR!\n", __func__
, __LINE__
);
2712 memcpy(pmlmepriv
->wps_beacon_ie
, param
->u
.bcn_ie
.buf
, ie_len
);
2714 update_beacon(padapter
, _VENDOR_SPECIFIC_IE_
, wps_oui
, true);
2716 pmlmeext
->bstart_bss
= true;
2722 static int rtw_set_wps_probe_resp(struct net_device
*dev
, struct ieee_param
*param
, int len
)
2725 struct adapter
*padapter
= (struct adapter
*)rtw_netdev_priv(dev
);
2726 struct mlme_priv
*pmlmepriv
= &(padapter
->mlmepriv
);
2729 DBG_88E("%s, len =%d\n", __func__
, len
);
2731 if (check_fwstate(pmlmepriv
, WIFI_AP_STATE
) != true)
2734 ie_len
= len
-12-2;/* 12 = param header, 2:no packed */
2736 kfree(pmlmepriv
->wps_probe_resp_ie
);
2737 pmlmepriv
->wps_probe_resp_ie
= NULL
;
2740 pmlmepriv
->wps_probe_resp_ie
= rtw_malloc(ie_len
);
2741 pmlmepriv
->wps_probe_resp_ie_len
= ie_len
;
2742 if (pmlmepriv
->wps_probe_resp_ie
== NULL
) {
2743 DBG_88E("%s()-%d: rtw_malloc() ERROR!\n", __func__
, __LINE__
);
2746 memcpy(pmlmepriv
->wps_probe_resp_ie
, param
->u
.bcn_ie
.buf
, ie_len
);
2752 static int rtw_set_wps_assoc_resp(struct net_device
*dev
, struct ieee_param
*param
, int len
)
2755 struct adapter
*padapter
= (struct adapter
*)rtw_netdev_priv(dev
);
2756 struct mlme_priv
*pmlmepriv
= &(padapter
->mlmepriv
);
2759 DBG_88E("%s, len =%d\n", __func__
, len
);
2761 if (check_fwstate(pmlmepriv
, WIFI_AP_STATE
) != true)
2764 ie_len
= len
-12-2;/* 12 = param header, 2:no packed */
2766 kfree(pmlmepriv
->wps_assoc_resp_ie
);
2767 pmlmepriv
->wps_assoc_resp_ie
= NULL
;
2770 pmlmepriv
->wps_assoc_resp_ie
= rtw_malloc(ie_len
);
2771 pmlmepriv
->wps_assoc_resp_ie_len
= ie_len
;
2772 if (pmlmepriv
->wps_assoc_resp_ie
== NULL
) {
2773 DBG_88E("%s()-%d: rtw_malloc() ERROR!\n", __func__
, __LINE__
);
2777 memcpy(pmlmepriv
->wps_assoc_resp_ie
, param
->u
.bcn_ie
.buf
, ie_len
);
2783 static int rtw_set_hidden_ssid(struct net_device
*dev
, struct ieee_param
*param
, int len
)
2786 struct adapter
*padapter
= (struct adapter
*)rtw_netdev_priv(dev
);
2787 struct mlme_priv
*pmlmepriv
= &(padapter
->mlmepriv
);
2788 struct mlme_ext_priv
*pmlmeext
= &(padapter
->mlmeextpriv
);
2789 struct mlme_ext_info
*pmlmeinfo
= &(pmlmeext
->mlmext_info
);
2793 if (check_fwstate(pmlmepriv
, WIFI_AP_STATE
) != true)
2796 if (param
->u
.wpa_param
.name
!= 0) /* dummy test... */
2797 DBG_88E("%s name(%u) != 0\n", __func__
, param
->u
.wpa_param
.name
);
2798 value
= param
->u
.wpa_param
.value
;
2800 /* use the same definition of hostapd's ignore_broadcast_ssid */
2801 if (value
!= 1 && value
!= 2)
2803 DBG_88E("%s value(%u)\n", __func__
, value
);
2804 pmlmeinfo
->hidden_ssid_mode
= value
;
2808 static int rtw_ioctl_acl_remove_sta(struct net_device
*dev
, struct ieee_param
*param
, int len
)
2810 struct adapter
*padapter
= (struct adapter
*)rtw_netdev_priv(dev
);
2811 struct mlme_priv
*pmlmepriv
= &(padapter
->mlmepriv
);
2813 if (check_fwstate(pmlmepriv
, WIFI_AP_STATE
) != true)
2816 if (param
->sta_addr
[0] == 0xff && param
->sta_addr
[1] == 0xff &&
2817 param
->sta_addr
[2] == 0xff && param
->sta_addr
[3] == 0xff &&
2818 param
->sta_addr
[4] == 0xff && param
->sta_addr
[5] == 0xff)
2820 return rtw_acl_remove_sta(padapter
, param
->sta_addr
);
2823 static int rtw_ioctl_acl_add_sta(struct net_device
*dev
, struct ieee_param
*param
, int len
)
2825 struct adapter
*padapter
= (struct adapter
*)rtw_netdev_priv(dev
);
2826 struct mlme_priv
*pmlmepriv
= &(padapter
->mlmepriv
);
2828 if (check_fwstate(pmlmepriv
, WIFI_AP_STATE
) != true)
2831 if (param
->sta_addr
[0] == 0xff && param
->sta_addr
[1] == 0xff &&
2832 param
->sta_addr
[2] == 0xff && param
->sta_addr
[3] == 0xff &&
2833 param
->sta_addr
[4] == 0xff && param
->sta_addr
[5] == 0xff)
2835 return rtw_acl_add_sta(padapter
, param
->sta_addr
);
2838 static int rtw_ioctl_set_macaddr_acl(struct net_device
*dev
, struct ieee_param
*param
, int len
)
2841 struct adapter
*padapter
= (struct adapter
*)rtw_netdev_priv(dev
);
2842 struct mlme_priv
*pmlmepriv
= &(padapter
->mlmepriv
);
2844 if (check_fwstate(pmlmepriv
, WIFI_AP_STATE
) != true)
2847 rtw_set_macaddr_acl(padapter
, param
->u
.mlme
.command
);
2852 static int rtw_hostapd_ioctl(struct net_device
*dev
, struct iw_point
*p
)
2854 struct ieee_param
*param
;
2856 struct adapter
*padapter
= (struct adapter
*)rtw_netdev_priv(dev
);
2859 * this function is expect to call in master mode, which allows no power saving
2860 * so, we just check hw_init_completed
2863 if (!padapter
->hw_init_completed
) {
2873 param
= (struct ieee_param
*)rtw_malloc(p
->length
);
2874 if (param
== NULL
) {
2879 if (copy_from_user(param
, p
->pointer
, p
->length
)) {
2885 switch (param
->cmd
) {
2886 case RTL871X_HOSTAPD_FLUSH
:
2887 ret
= rtw_hostapd_sta_flush(dev
);
2889 case RTL871X_HOSTAPD_ADD_STA
:
2890 ret
= rtw_add_sta(dev
, param
);
2892 case RTL871X_HOSTAPD_REMOVE_STA
:
2893 ret
= rtw_del_sta(dev
, param
);
2895 case RTL871X_HOSTAPD_SET_BEACON
:
2896 ret
= rtw_set_beacon(dev
, param
, p
->length
);
2898 case RTL871X_SET_ENCRYPTION
:
2899 ret
= rtw_set_encryption(dev
, param
, p
->length
);
2901 case RTL871X_HOSTAPD_GET_WPAIE_STA
:
2902 ret
= rtw_get_sta_wpaie(dev
, param
);
2904 case RTL871X_HOSTAPD_SET_WPS_BEACON
:
2905 ret
= rtw_set_wps_beacon(dev
, param
, p
->length
);
2907 case RTL871X_HOSTAPD_SET_WPS_PROBE_RESP
:
2908 ret
= rtw_set_wps_probe_resp(dev
, param
, p
->length
);
2910 case RTL871X_HOSTAPD_SET_WPS_ASSOC_RESP
:
2911 ret
= rtw_set_wps_assoc_resp(dev
, param
, p
->length
);
2913 case RTL871X_HOSTAPD_SET_HIDDEN_SSID
:
2914 ret
= rtw_set_hidden_ssid(dev
, param
, p
->length
);
2916 case RTL871X_HOSTAPD_GET_INFO_STA
:
2917 ret
= rtw_ioctl_get_sta_data(dev
, param
, p
->length
);
2919 case RTL871X_HOSTAPD_SET_MACADDR_ACL
:
2920 ret
= rtw_ioctl_set_macaddr_acl(dev
, param
, p
->length
);
2922 case RTL871X_HOSTAPD_ACL_ADD_STA
:
2923 ret
= rtw_ioctl_acl_add_sta(dev
, param
, p
->length
);
2925 case RTL871X_HOSTAPD_ACL_REMOVE_STA
:
2926 ret
= rtw_ioctl_acl_remove_sta(dev
, param
, p
->length
);
2929 DBG_88E("Unknown hostapd request: %d\n", param
->cmd
);
2934 if (ret
== 0 && copy_to_user(p
->pointer
, param
, p
->length
))
2942 #include <rtw_android.h>
2943 static int rtw_wx_set_priv(struct net_device
*dev
,
2944 struct iw_request_info
*info
,
2945 union iwreq_data
*awrq
,
2951 struct adapter
*padapter
= (struct adapter
*)rtw_netdev_priv(dev
);
2952 struct iw_point
*dwrq
= (struct iw_point
*)awrq
;
2954 if (dwrq
->length
== 0)
2962 if (copy_from_user(ext
, dwrq
->pointer
, len
)) {
2967 /* added for wps2.0 @20110524 */
2968 if (dwrq
->flags
== 0x8766 && len
> 8) {
2970 struct mlme_priv
*pmlmepriv
= &(padapter
->mlmepriv
);
2971 u8
*probereq_wpsie
= ext
;
2972 int probereq_wpsie_len
= len
;
2973 u8 wps_oui
[4] = {0x0, 0x50, 0xf2, 0x04};
2975 if ((_VENDOR_SPECIFIC_IE_
== probereq_wpsie
[0]) &&
2976 (!memcmp(&probereq_wpsie
[2], wps_oui
, 4))) {
2977 cp_sz
= min(probereq_wpsie_len
, MAX_WPS_IE_LEN
);
2979 pmlmepriv
->wps_probe_req_ie_len
= 0;
2980 kfree(pmlmepriv
->wps_probe_req_ie
);
2981 pmlmepriv
->wps_probe_req_ie
= NULL
;
2983 pmlmepriv
->wps_probe_req_ie
= rtw_malloc(cp_sz
);
2984 if (pmlmepriv
->wps_probe_req_ie
== NULL
) {
2985 pr_info("%s()-%d: rtw_malloc() ERROR!\n", __func__
, __LINE__
);
2989 memcpy(pmlmepriv
->wps_probe_req_ie
, probereq_wpsie
, cp_sz
);
2990 pmlmepriv
->wps_probe_req_ie_len
= cp_sz
;
2995 if (len
>= WEXT_CSCAN_HEADER_SIZE
&&
2996 !memcmp(ext
, WEXT_CSCAN_HEADER
, WEXT_CSCAN_HEADER_SIZE
)) {
2997 ret
= rtw_wx_set_scan(dev
, info
, awrq
, ext
);
3008 static iw_handler rtw_handlers
[] = {
3009 NULL
, /* SIOCSIWCOMMIT */
3010 rtw_wx_get_name
, /* SIOCGIWNAME */
3011 dummy
, /* SIOCSIWNWID */
3012 dummy
, /* SIOCGIWNWID */
3013 rtw_wx_set_freq
, /* SIOCSIWFREQ */
3014 rtw_wx_get_freq
, /* SIOCGIWFREQ */
3015 rtw_wx_set_mode
, /* SIOCSIWMODE */
3016 rtw_wx_get_mode
, /* SIOCGIWMODE */
3017 dummy
, /* SIOCSIWSENS */
3018 rtw_wx_get_sens
, /* SIOCGIWSENS */
3019 NULL
, /* SIOCSIWRANGE */
3020 rtw_wx_get_range
, /* SIOCGIWRANGE */
3021 rtw_wx_set_priv
, /* SIOCSIWPRIV */
3022 NULL
, /* SIOCGIWPRIV */
3023 NULL
, /* SIOCSIWSTATS */
3024 NULL
, /* SIOCGIWSTATS */
3025 dummy
, /* SIOCSIWSPY */
3026 dummy
, /* SIOCGIWSPY */
3027 NULL
, /* SIOCGIWTHRSPY */
3028 NULL
, /* SIOCWIWTHRSPY */
3029 rtw_wx_set_wap
, /* SIOCSIWAP */
3030 rtw_wx_get_wap
, /* SIOCGIWAP */
3031 rtw_wx_set_mlme
, /* request MLME operation; uses struct iw_mlme */
3032 dummy
, /* SIOCGIWAPLIST -- depricated */
3033 rtw_wx_set_scan
, /* SIOCSIWSCAN */
3034 rtw_wx_get_scan
, /* SIOCGIWSCAN */
3035 rtw_wx_set_essid
, /* SIOCSIWESSID */
3036 rtw_wx_get_essid
, /* SIOCGIWESSID */
3037 dummy
, /* SIOCSIWNICKN */
3038 rtw_wx_get_nick
, /* SIOCGIWNICKN */
3039 NULL
, /* -- hole -- */
3040 NULL
, /* -- hole -- */
3041 rtw_wx_set_rate
, /* SIOCSIWRATE */
3042 rtw_wx_get_rate
, /* SIOCGIWRATE */
3043 rtw_wx_set_rts
, /* SIOCSIWRTS */
3044 rtw_wx_get_rts
, /* SIOCGIWRTS */
3045 rtw_wx_set_frag
, /* SIOCSIWFRAG */
3046 rtw_wx_get_frag
, /* SIOCGIWFRAG */
3047 dummy
, /* SIOCSIWTXPOW */
3048 dummy
, /* SIOCGIWTXPOW */
3049 dummy
, /* SIOCSIWRETRY */
3050 rtw_wx_get_retry
, /* SIOCGIWRETRY */
3051 rtw_wx_set_enc
, /* SIOCSIWENCODE */
3052 rtw_wx_get_enc
, /* SIOCGIWENCODE */
3053 dummy
, /* SIOCSIWPOWER */
3054 rtw_wx_get_power
, /* SIOCGIWPOWER */
3055 NULL
, /*---hole---*/
3056 NULL
, /*---hole---*/
3057 rtw_wx_set_gen_ie
, /* SIOCSIWGENIE */
3058 NULL
, /* SIOCGWGENIE */
3059 rtw_wx_set_auth
, /* SIOCSIWAUTH */
3060 NULL
, /* SIOCGIWAUTH */
3061 rtw_wx_set_enc_ext
, /* SIOCSIWENCODEEXT */
3062 NULL
, /* SIOCGIWENCODEEXT */
3063 rtw_wx_set_pmkid
, /* SIOCSIWPMKSA */
3064 NULL
, /*---hole---*/
3067 static struct iw_statistics
*rtw_get_wireless_stats(struct net_device
*dev
)
3069 struct adapter
*padapter
= (struct adapter
*)rtw_netdev_priv(dev
);
3070 struct iw_statistics
*piwstats
= &padapter
->iwstats
;
3075 if (!check_fwstate(&padapter
->mlmepriv
, _FW_LINKED
)) {
3076 piwstats
->qual
.qual
= 0;
3077 piwstats
->qual
.level
= 0;
3078 piwstats
->qual
.noise
= 0;
3080 tmp_level
= padapter
->recvpriv
.signal_strength
;
3081 tmp_qual
= padapter
->recvpriv
.signal_qual
;
3082 tmp_noise
= padapter
->recvpriv
.noise
;
3084 piwstats
->qual
.level
= tmp_level
;
3085 piwstats
->qual
.qual
= tmp_qual
;
3086 piwstats
->qual
.noise
= tmp_noise
;
3088 piwstats
->qual
.updated
= IW_QUAL_ALL_UPDATED
;/* IW_QUAL_DBM; */
3089 return &padapter
->iwstats
;
3092 struct iw_handler_def rtw_handlers_def
= {
3093 .standard
= rtw_handlers
,
3094 .num_standard
= ARRAY_SIZE(rtw_handlers
),
3095 .get_wireless_stats
= rtw_get_wireless_stats
,
3098 #include <rtw_android.h>
3099 int rtw_ioctl(struct net_device
*dev
, struct ifreq
*rq
, int cmd
)
3101 struct iwreq
*wrq
= (struct iwreq
*)rq
;
3105 case RTL_IOCTL_WPA_SUPPLICANT
:
3106 ret
= wpa_supplicant_ioctl(dev
, &wrq
->u
.data
);
3108 #ifdef CONFIG_88EU_AP_MODE
3109 case RTL_IOCTL_HOSTAPD
:
3110 ret
= rtw_hostapd_ioctl(dev
, &wrq
->u
.data
);
3112 #endif /* CONFIG_88EU_AP_MODE */
3113 case (SIOCDEVPRIVATE
+1):
3114 ret
= rtw_android_priv_cmd(dev
, rq
, cmd
);