1 /*
2  *************************************************************************
3  * Ralink Tech Inc.
4  * 5F., No.36, Taiyuan St., Jhubei City,
5  * Hsinchu County 302,
6  * Taiwan, R.O.C.
7  *
8  * (c) Copyright 2002-2007, Ralink Technology, Inc.
9  *
10  * This program is free software; you can redistribute it and/or modify  *
11  * it under the terms of the GNU General Public License as published by  *
12  * the Free Software Foundation; either version 2 of the License, or     *
13  * (at your option) any later version.                                   *
14  *                                                                       *
15  * This program is distributed in the hope that it will be useful,       *
16  * but WITHOUT ANY WARRANTY; without even the implied warranty of        *
17  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the         *
18  * GNU General Public License for more details.                          *
19  *                                                                       *
20  * You should have received a copy of the GNU General Public License     *
21  * along with this program; if not, write to the                         *
22  * Free Software Foundation, Inc.,                                       *
23  * 59 Temple Place - Suite 330, Boston, MA  02111-1307, USA.             *
24  *                                                                       *
25  *************************************************************************
26 
27     Module Name:
28     sta_ioctl.c
29 
30     Abstract:
31     IOCTL related subroutines
32 
33     Revision History:
34     	Who        		 When          What
35     --------    ----------    ----------------------------------------------
36    	Rory Chen   		01-03-2003    	created
37 	Rory Chen   		02-14-2005    	modify to support RT61
38 	Justin P. Mattock	11/07/2010	Fix typos
39 */
40 
41 #include	"rt_config.h"
42 
43 #ifdef DBG
44 extern unsigned long RTDebugLevel;
45 #endif
46 
47 #define NR_WEP_KEYS 				4
48 #define WEP_SMALL_KEY_LEN 			(40/8)
49 #define WEP_LARGE_KEY_LEN 			(104/8)
50 
51 #define GROUP_KEY_NO                4
52 
53 extern u8 CipherWpa2Template[];
54 
55 struct PACKED rt_version_info {
56 	u8 DriverVersionW;
57 	u8 DriverVersionX;
58 	u8 DriverVersionY;
59 	u8 DriverVersionZ;
60 	u32 DriverBuildYear;
61 	u32 DriverBuildMonth;
62 	u32 DriverBuildDay;
63 };
64 
65 static __s32 ralinkrate[] = { 2, 4, 11, 22,	/* CCK */
66 	12, 18, 24, 36, 48, 72, 96, 108,	/* OFDM */
67 	13, 26, 39, 52, 78, 104, 117, 130, 26, 52, 78, 104, 156, 208, 234, 260,	/* 20MHz, 800ns GI, MCS: 0 ~ 15 */
68 	39, 78, 117, 156, 234, 312, 351, 390,	/* 20MHz, 800ns GI, MCS: 16 ~ 23 */
69 	27, 54, 81, 108, 162, 216, 243, 270, 54, 108, 162, 216, 324, 432, 486, 540,	/* 40MHz, 800ns GI, MCS: 0 ~ 15 */
70 	81, 162, 243, 324, 486, 648, 729, 810,	/* 40MHz, 800ns GI, MCS: 16 ~ 23 */
71 	14, 29, 43, 57, 87, 115, 130, 144, 29, 59, 87, 115, 173, 230, 260, 288,	/* 20MHz, 400ns GI, MCS: 0 ~ 15 */
72 	43, 87, 130, 173, 260, 317, 390, 433,	/* 20MHz, 400ns GI, MCS: 16 ~ 23 */
73 	30, 60, 90, 120, 180, 240, 270, 300, 60, 120, 180, 240, 360, 480, 540, 600,	/* 40MHz, 400ns GI, MCS: 0 ~ 15 */
74 	90, 180, 270, 360, 540, 720, 810, 900
75 };
76 
77 int Set_SSID_Proc(struct rt_rtmp_adapter *pAdapter, char *arg);
78 
79 int Set_NetworkType_Proc(struct rt_rtmp_adapter *pAdapter, char *arg);
80 
RTMPAddKey(struct rt_rtmp_adapter * pAd,struct rt_ndis_802_11_key * pKey)81 void RTMPAddKey(struct rt_rtmp_adapter *pAd, struct rt_ndis_802_11_key *pKey)
82 {
83 	unsigned long KeyIdx;
84 	struct rt_mac_table_entry *pEntry;
85 
86 	DBGPRINT(RT_DEBUG_TRACE, ("RTMPAddKey ------>\n"));
87 
88 	if (pAd->StaCfg.AuthMode >= Ndis802_11AuthModeWPA) {
89 		if (pKey->KeyIndex & 0x80000000) {
90 			if (pAd->StaCfg.AuthMode == Ndis802_11AuthModeWPANone) {
91 				NdisZeroMemory(pAd->StaCfg.PMK, 32);
92 				NdisMoveMemory(pAd->StaCfg.PMK,
93 					       pKey->KeyMaterial,
94 					       pKey->KeyLength);
95 				goto end;
96 			}
97 			/* Update PTK */
98 			NdisZeroMemory(&pAd->SharedKey[BSS0][0],
99 				       sizeof(struct rt_cipher_key));
100 			pAd->SharedKey[BSS0][0].KeyLen = LEN_TKIP_EK;
101 			NdisMoveMemory(pAd->SharedKey[BSS0][0].Key,
102 				       pKey->KeyMaterial, LEN_TKIP_EK);
103 
104 			if (pAd->StaCfg.PairCipher ==
105 			    Ndis802_11Encryption2Enabled) {
106 				NdisMoveMemory(pAd->SharedKey[BSS0][0].RxMic,
107 					       pKey->KeyMaterial + LEN_TKIP_EK,
108 					       LEN_TKIP_TXMICK);
109 				NdisMoveMemory(pAd->SharedKey[BSS0][0].TxMic,
110 					       pKey->KeyMaterial + LEN_TKIP_EK +
111 					       LEN_TKIP_TXMICK,
112 					       LEN_TKIP_RXMICK);
113 			} else {
114 				NdisMoveMemory(pAd->SharedKey[BSS0][0].TxMic,
115 					       pKey->KeyMaterial + LEN_TKIP_EK,
116 					       LEN_TKIP_TXMICK);
117 				NdisMoveMemory(pAd->SharedKey[BSS0][0].RxMic,
118 					       pKey->KeyMaterial + LEN_TKIP_EK +
119 					       LEN_TKIP_TXMICK,
120 					       LEN_TKIP_RXMICK);
121 			}
122 
123 			/* Decide its ChiperAlg */
124 			if (pAd->StaCfg.PairCipher ==
125 			    Ndis802_11Encryption2Enabled)
126 				pAd->SharedKey[BSS0][0].CipherAlg = CIPHER_TKIP;
127 			else if (pAd->StaCfg.PairCipher ==
128 				 Ndis802_11Encryption3Enabled)
129 				pAd->SharedKey[BSS0][0].CipherAlg = CIPHER_AES;
130 			else
131 				pAd->SharedKey[BSS0][0].CipherAlg = CIPHER_NONE;
132 
133 			/* Update these related information to struct rt_mac_table_entry */
134 			pEntry = &pAd->MacTab.Content[BSSID_WCID];
135 			NdisMoveMemory(pEntry->PairwiseKey.Key,
136 				       pAd->SharedKey[BSS0][0].Key,
137 				       LEN_TKIP_EK);
138 			NdisMoveMemory(pEntry->PairwiseKey.RxMic,
139 				       pAd->SharedKey[BSS0][0].RxMic,
140 				       LEN_TKIP_RXMICK);
141 			NdisMoveMemory(pEntry->PairwiseKey.TxMic,
142 				       pAd->SharedKey[BSS0][0].TxMic,
143 				       LEN_TKIP_TXMICK);
144 			pEntry->PairwiseKey.CipherAlg =
145 			    pAd->SharedKey[BSS0][0].CipherAlg;
146 
147 			/* Update pairwise key information to ASIC Shared Key Table */
148 			AsicAddSharedKeyEntry(pAd,
149 					      BSS0,
150 					      0,
151 					      pAd->SharedKey[BSS0][0].CipherAlg,
152 					      pAd->SharedKey[BSS0][0].Key,
153 					      pAd->SharedKey[BSS0][0].TxMic,
154 					      pAd->SharedKey[BSS0][0].RxMic);
155 
156 			/* Update ASIC WCID attribute table and IVEIV table */
157 			RTMPAddWcidAttributeEntry(pAd,
158 						  BSS0,
159 						  0,
160 						  pAd->SharedKey[BSS0][0].
161 						  CipherAlg, pEntry);
162 
163 			if (pAd->StaCfg.AuthMode >= Ndis802_11AuthModeWPA2) {
164 				/* set 802.1x port control */
165 				/*pAd->StaCfg.PortSecured = WPA_802_1X_PORT_SECURED; */
166 				STA_PORT_SECURED(pAd);
167 
168 				/* Indicate Connected for GUI */
169 				pAd->IndicateMediaState =
170 				    NdisMediaStateConnected;
171 			}
172 		} else {
173 			/* Update GTK */
174 			pAd->StaCfg.DefaultKeyId = (pKey->KeyIndex & 0xFF);
175 			NdisZeroMemory(&pAd->
176 				       SharedKey[BSS0][pAd->StaCfg.
177 						       DefaultKeyId],
178 				       sizeof(struct rt_cipher_key));
179 			pAd->SharedKey[BSS0][pAd->StaCfg.DefaultKeyId].KeyLen =
180 			    LEN_TKIP_EK;
181 			NdisMoveMemory(pAd->
182 				       SharedKey[BSS0][pAd->StaCfg.
183 						       DefaultKeyId].Key,
184 				       pKey->KeyMaterial, LEN_TKIP_EK);
185 
186 			if (pAd->StaCfg.GroupCipher ==
187 			    Ndis802_11Encryption2Enabled) {
188 				NdisMoveMemory(pAd->
189 					       SharedKey[BSS0][pAd->StaCfg.
190 							       DefaultKeyId].
191 					       RxMic,
192 					       pKey->KeyMaterial + LEN_TKIP_EK,
193 					       LEN_TKIP_TXMICK);
194 				NdisMoveMemory(pAd->
195 					       SharedKey[BSS0][pAd->StaCfg.
196 							       DefaultKeyId].
197 					       TxMic,
198 					       pKey->KeyMaterial + LEN_TKIP_EK +
199 					       LEN_TKIP_TXMICK,
200 					       LEN_TKIP_RXMICK);
201 			} else {
202 				NdisMoveMemory(pAd->
203 					       SharedKey[BSS0][pAd->StaCfg.
204 							       DefaultKeyId].
205 					       TxMic,
206 					       pKey->KeyMaterial + LEN_TKIP_EK,
207 					       LEN_TKIP_TXMICK);
208 				NdisMoveMemory(pAd->
209 					       SharedKey[BSS0][pAd->StaCfg.
210 							       DefaultKeyId].
211 					       RxMic,
212 					       pKey->KeyMaterial + LEN_TKIP_EK +
213 					       LEN_TKIP_TXMICK,
214 					       LEN_TKIP_RXMICK);
215 			}
216 
217 			/* Update Shared Key CipherAlg */
218 			pAd->SharedKey[BSS0][pAd->StaCfg.DefaultKeyId].
219 			    CipherAlg = CIPHER_NONE;
220 			if (pAd->StaCfg.GroupCipher ==
221 			    Ndis802_11Encryption2Enabled)
222 				pAd->SharedKey[BSS0][pAd->StaCfg.DefaultKeyId].
223 				    CipherAlg = CIPHER_TKIP;
224 			else if (pAd->StaCfg.GroupCipher ==
225 				 Ndis802_11Encryption3Enabled)
226 				pAd->SharedKey[BSS0][pAd->StaCfg.DefaultKeyId].
227 				    CipherAlg = CIPHER_AES;
228 
229 			/* Update group key information to ASIC Shared Key Table */
230 			AsicAddSharedKeyEntry(pAd,
231 					      BSS0,
232 					      pAd->StaCfg.DefaultKeyId,
233 					      pAd->SharedKey[BSS0][pAd->StaCfg.
234 								   DefaultKeyId].
235 					      CipherAlg,
236 					      pAd->SharedKey[BSS0][pAd->StaCfg.
237 								   DefaultKeyId].
238 					      Key,
239 					      pAd->SharedKey[BSS0][pAd->StaCfg.
240 								   DefaultKeyId].
241 					      TxMic,
242 					      pAd->SharedKey[BSS0][pAd->StaCfg.
243 								   DefaultKeyId].
244 					      RxMic);
245 
246 			/* Update ASIC WCID attribute table and IVEIV table */
247 			RTMPAddWcidAttributeEntry(pAd,
248 						  BSS0,
249 						  pAd->StaCfg.DefaultKeyId,
250 						  pAd->SharedKey[BSS0][pAd->
251 								       StaCfg.
252 								       DefaultKeyId].
253 						  CipherAlg, NULL);
254 
255 			/* set 802.1x port control */
256 			/*pAd->StaCfg.PortSecured = WPA_802_1X_PORT_SECURED; */
257 			STA_PORT_SECURED(pAd);
258 
259 			/* Indicate Connected for GUI */
260 			pAd->IndicateMediaState = NdisMediaStateConnected;
261 		}
262 	} else			/* dynamic WEP from wpa_supplicant */
263 	{
264 		u8 CipherAlg;
265 		u8 *Key;
266 
267 		if (pKey->KeyLength == 32)
268 			goto end;
269 
270 		KeyIdx = pKey->KeyIndex & 0x0fffffff;
271 
272 		if (KeyIdx < 4) {
273 			/* it is a default shared key, for Pairwise key setting */
274 			if (pKey->KeyIndex & 0x80000000) {
275 				pEntry = MacTableLookup(pAd, pKey->BSSID);
276 
277 				if (pEntry) {
278 					DBGPRINT(RT_DEBUG_TRACE,
279 						 ("RTMPAddKey: Set Pair-wise Key\n"));
280 
281 					/* set key material and key length */
282 					pEntry->PairwiseKey.KeyLen =
283 					    (u8)pKey->KeyLength;
284 					NdisMoveMemory(pEntry->PairwiseKey.Key,
285 						       &pKey->KeyMaterial,
286 						       pKey->KeyLength);
287 
288 					/* set Cipher type */
289 					if (pKey->KeyLength == 5)
290 						pEntry->PairwiseKey.CipherAlg =
291 						    CIPHER_WEP64;
292 					else
293 						pEntry->PairwiseKey.CipherAlg =
294 						    CIPHER_WEP128;
295 
296 					/* Add Pair-wise key to Asic */
297 					AsicAddPairwiseKeyEntry(pAd,
298 								pEntry->Addr,
299 								(u8)pEntry->
300 								Aid,
301 								&pEntry->
302 								PairwiseKey);
303 
304 					/* update WCID attribute table and IVEIV table for this entry */
305 					RTMPAddWcidAttributeEntry(pAd, BSS0, KeyIdx,	/* The value may be not zero */
306 								  pEntry->
307 								  PairwiseKey.
308 								  CipherAlg,
309 								  pEntry);
310 
311 				}
312 			} else {
313 				/* Default key for tx (shared key) */
314 				pAd->StaCfg.DefaultKeyId = (u8)KeyIdx;
315 
316 				/* set key material and key length */
317 				pAd->SharedKey[BSS0][KeyIdx].KeyLen =
318 				    (u8)pKey->KeyLength;
319 				NdisMoveMemory(pAd->SharedKey[BSS0][KeyIdx].Key,
320 					       &pKey->KeyMaterial,
321 					       pKey->KeyLength);
322 
323 				/* Set Ciper type */
324 				if (pKey->KeyLength == 5)
325 					pAd->SharedKey[BSS0][KeyIdx].CipherAlg =
326 					    CIPHER_WEP64;
327 				else
328 					pAd->SharedKey[BSS0][KeyIdx].CipherAlg =
329 					    CIPHER_WEP128;
330 
331 				CipherAlg =
332 				    pAd->SharedKey[BSS0][KeyIdx].CipherAlg;
333 				Key = pAd->SharedKey[BSS0][KeyIdx].Key;
334 
335 				/* Set Group key material to Asic */
336 				AsicAddSharedKeyEntry(pAd, BSS0, KeyIdx,
337 						      CipherAlg, Key, NULL,
338 						      NULL);
339 
340 				/* Update WCID attribute table and IVEIV table for this group key table */
341 				RTMPAddWcidAttributeEntry(pAd, BSS0, KeyIdx,
342 							  CipherAlg, NULL);
343 
344 			}
345 		}
346 	}
347 end:
348 	return;
349 }
350 
rtstrchr(const char * s,int c)351 char *rtstrchr(const char *s, int c)
352 {
353 	for (; *s != (char)c; ++s)
354 		if (*s == '\0')
355 			return NULL;
356 	return (char *)s;
357 }
358 
359 /*
360 This is required for LinEX2004/kernel2.6.7 to provide iwlist scanning function
361 */
362 
363 int
rt_ioctl_giwname(struct net_device * dev,struct iw_request_info * info,char * name,char * extra)364 rt_ioctl_giwname(struct net_device *dev,
365 		 struct iw_request_info *info, char *name, char *extra)
366 {
367 	strncpy(name, "Ralink STA", IFNAMSIZ);
368 	/* RT2870 2.1.0.0 uses "RT2870 Wireless" */
369 	/* RT3090 2.1.0.0 uses "RT2860 Wireless" */
370 	return 0;
371 }
372 
rt_ioctl_siwfreq(struct net_device * dev,struct iw_request_info * info,struct iw_freq * freq,char * extra)373 int rt_ioctl_siwfreq(struct net_device *dev,
374 		     struct iw_request_info *info,
375 		     struct iw_freq *freq, char *extra)
376 {
377 	struct rt_rtmp_adapter *pAdapter = NULL;
378 	int chan = -1;
379 
380 	GET_PAD_FROM_NET_DEV(pAdapter, dev);
381 
382 	/*check if the interface is down */
383 	if (!RTMP_TEST_FLAG(pAdapter, fRTMP_ADAPTER_INTERRUPT_IN_USE)) {
384 		DBGPRINT(RT_DEBUG_TRACE, ("INFO::Network is down!\n"));
385 		return -ENETDOWN;
386 	}
387 
388 	if (freq->e > 1)
389 		return -EINVAL;
390 
391 	if ((freq->e == 0) && (freq->m <= 1000))
392 		chan = freq->m;	/* Setting by channel number */
393 	else
394 		MAP_KHZ_TO_CHANNEL_ID((freq->m / 100), chan);	/* Setting by frequency - search the table , like 2.412G, 2.422G, */
395 
396 	if (ChannelSanity(pAdapter, chan) == TRUE) {
397 		pAdapter->CommonCfg.Channel = chan;
398 		DBGPRINT(RT_DEBUG_ERROR,
399 			 ("==>rt_ioctl_siwfreq::SIOCSIWFREQ[cmd=0x%x] (Channel=%d)\n",
400 			  SIOCSIWFREQ, pAdapter->CommonCfg.Channel));
401 	} else
402 		return -EINVAL;
403 
404 	return 0;
405 }
406 
rt_ioctl_giwfreq(struct net_device * dev,struct iw_request_info * info,struct iw_freq * freq,char * extra)407 int rt_ioctl_giwfreq(struct net_device *dev,
408 		     struct iw_request_info *info,
409 		     struct iw_freq *freq, char *extra)
410 {
411 	struct rt_rtmp_adapter *pAdapter = NULL;
412 	u8 ch;
413 	unsigned long m = 2412000;
414 
415 	GET_PAD_FROM_NET_DEV(pAdapter, dev);
416 
417 	ch = pAdapter->CommonCfg.Channel;
418 
419 	DBGPRINT(RT_DEBUG_TRACE, ("==>rt_ioctl_giwfreq  %d\n", ch));
420 
421 	MAP_CHANNEL_ID_TO_KHZ(ch, m);
422 	freq->m = m * 100;
423 	freq->e = 1;
424 	return 0;
425 }
426 
rt_ioctl_siwmode(struct net_device * dev,struct iw_request_info * info,__u32 * mode,char * extra)427 int rt_ioctl_siwmode(struct net_device *dev,
428 		     struct iw_request_info *info, __u32 * mode, char *extra)
429 {
430 	struct rt_rtmp_adapter *pAdapter = NULL;
431 
432 	GET_PAD_FROM_NET_DEV(pAdapter, dev);
433 
434 	/*check if the interface is down */
435 	if (!RTMP_TEST_FLAG(pAdapter, fRTMP_ADAPTER_INTERRUPT_IN_USE)) {
436 		DBGPRINT(RT_DEBUG_TRACE, ("INFO::Network is down!\n"));
437 		return -ENETDOWN;
438 	}
439 
440 	switch (*mode) {
441 	case IW_MODE_ADHOC:
442 		Set_NetworkType_Proc(pAdapter, "Adhoc");
443 		break;
444 	case IW_MODE_INFRA:
445 		Set_NetworkType_Proc(pAdapter, "Infra");
446 		break;
447 	case IW_MODE_MONITOR:
448 		Set_NetworkType_Proc(pAdapter, "Monitor");
449 		break;
450 	default:
451 		DBGPRINT(RT_DEBUG_TRACE,
452 			 ("===>rt_ioctl_siwmode::SIOCSIWMODE (unknown %d)\n",
453 			  *mode));
454 		return -EINVAL;
455 	}
456 
457 	/* Reset Ralink supplicant to not use, it will be set to start when UI set PMK key */
458 	pAdapter->StaCfg.WpaState = SS_NOTUSE;
459 
460 	return 0;
461 }
462 
rt_ioctl_giwmode(struct net_device * dev,struct iw_request_info * info,__u32 * mode,char * extra)463 int rt_ioctl_giwmode(struct net_device *dev,
464 		     struct iw_request_info *info, __u32 * mode, char *extra)
465 {
466 	struct rt_rtmp_adapter *pAdapter = NULL;
467 
468 	GET_PAD_FROM_NET_DEV(pAdapter, dev);
469 
470 	if (ADHOC_ON(pAdapter))
471 		*mode = IW_MODE_ADHOC;
472 	else if (INFRA_ON(pAdapter))
473 		*mode = IW_MODE_INFRA;
474 	else if (MONITOR_ON(pAdapter)) {
475 		*mode = IW_MODE_MONITOR;
476 	} else
477 		*mode = IW_MODE_AUTO;
478 
479 	DBGPRINT(RT_DEBUG_TRACE, ("==>rt_ioctl_giwmode(mode=%d)\n", *mode));
480 	return 0;
481 }
482 
rt_ioctl_siwsens(struct net_device * dev,struct iw_request_info * info,char * name,char * extra)483 int rt_ioctl_siwsens(struct net_device *dev,
484 		     struct iw_request_info *info, char *name, char *extra)
485 {
486 	struct rt_rtmp_adapter *pAdapter = NULL;
487 
488 	GET_PAD_FROM_NET_DEV(pAdapter, dev);
489 
490 	/*check if the interface is down */
491 	if (!RTMP_TEST_FLAG(pAdapter, fRTMP_ADAPTER_INTERRUPT_IN_USE)) {
492 		DBGPRINT(RT_DEBUG_TRACE, ("INFO::Network is down!\n"));
493 		return -ENETDOWN;
494 	}
495 
496 	return 0;
497 }
498 
rt_ioctl_giwsens(struct net_device * dev,struct iw_request_info * info,char * name,char * extra)499 int rt_ioctl_giwsens(struct net_device *dev,
500 		     struct iw_request_info *info, char *name, char *extra)
501 {
502 	return 0;
503 }
504 
rt_ioctl_giwrange(struct net_device * dev,struct iw_request_info * info,struct iw_point * data,char * extra)505 int rt_ioctl_giwrange(struct net_device *dev,
506 		      struct iw_request_info *info,
507 		      struct iw_point *data, char *extra)
508 {
509 	struct rt_rtmp_adapter *pAdapter = NULL;
510 	struct iw_range *range = (struct iw_range *)extra;
511 	u16 val;
512 	int i;
513 
514 	GET_PAD_FROM_NET_DEV(pAdapter, dev);
515 
516 	DBGPRINT(RT_DEBUG_TRACE, ("===>rt_ioctl_giwrange\n"));
517 	data->length = sizeof(struct iw_range);
518 	memset(range, 0, sizeof(struct iw_range));
519 
520 	range->txpower_capa = IW_TXPOW_DBM;
521 
522 	if (INFRA_ON(pAdapter) || ADHOC_ON(pAdapter)) {
523 		range->min_pmp = 1 * 1024;
524 		range->max_pmp = 65535 * 1024;
525 		range->min_pmt = 1 * 1024;
526 		range->max_pmt = 1000 * 1024;
527 		range->pmp_flags = IW_POWER_PERIOD;
528 		range->pmt_flags = IW_POWER_TIMEOUT;
529 		range->pm_capa = IW_POWER_PERIOD | IW_POWER_TIMEOUT |
530 		    IW_POWER_UNICAST_R | IW_POWER_ALL_R;
531 	}
532 
533 	range->we_version_compiled = WIRELESS_EXT;
534 	range->we_version_source = 14;
535 
536 	range->retry_capa = IW_RETRY_LIMIT;
537 	range->retry_flags = IW_RETRY_LIMIT;
538 	range->min_retry = 0;
539 	range->max_retry = 255;
540 
541 	range->num_channels = pAdapter->ChannelListNum;
542 
543 	val = 0;
544 	for (i = 1; i <= range->num_channels; i++) {
545 		u32 m = 2412000;
546 		range->freq[val].i = pAdapter->ChannelList[i - 1].Channel;
547 		MAP_CHANNEL_ID_TO_KHZ(pAdapter->ChannelList[i - 1].Channel, m);
548 		range->freq[val].m = m * 100;	/* OS_HZ */
549 
550 		range->freq[val].e = 1;
551 		val++;
552 		if (val == IW_MAX_FREQUENCIES)
553 			break;
554 	}
555 	range->num_frequency = val;
556 
557 	range->max_qual.qual = 100;	/* what is correct max? This was not
558 					 * documented exactly. At least
559 					 * 69 has been observed. */
560 	range->max_qual.level = 0;	/* dB */
561 	range->max_qual.noise = 0;	/* dB */
562 
563 	/* What would be suitable values for "average/typical" qual? */
564 	range->avg_qual.qual = 20;
565 	range->avg_qual.level = -60;
566 	range->avg_qual.noise = -95;
567 	range->sensitivity = 3;
568 
569 	range->max_encoding_tokens = NR_WEP_KEYS;
570 	range->num_encoding_sizes = 2;
571 	range->encoding_size[0] = 5;
572 	range->encoding_size[1] = 13;
573 
574 	range->min_rts = 0;
575 	range->max_rts = 2347;
576 	range->min_frag = 256;
577 	range->max_frag = 2346;
578 
579 	/* IW_ENC_CAPA_* bit field */
580 	range->enc_capa = IW_ENC_CAPA_WPA | IW_ENC_CAPA_WPA2 |
581 	    IW_ENC_CAPA_CIPHER_TKIP | IW_ENC_CAPA_CIPHER_CCMP;
582 
583 	return 0;
584 }
585 
rt_ioctl_siwap(struct net_device * dev,struct iw_request_info * info,struct sockaddr * ap_addr,char * extra)586 int rt_ioctl_siwap(struct net_device *dev,
587 		   struct iw_request_info *info,
588 		   struct sockaddr *ap_addr, char *extra)
589 {
590 	struct rt_rtmp_adapter *pAdapter = NULL;
591 	NDIS_802_11_MAC_ADDRESS Bssid;
592 
593 	GET_PAD_FROM_NET_DEV(pAdapter, dev);
594 
595 	/*check if the interface is down */
596 	if (!RTMP_TEST_FLAG(pAdapter, fRTMP_ADAPTER_INTERRUPT_IN_USE)) {
597 		DBGPRINT(RT_DEBUG_TRACE, ("INFO::Network is down!\n"));
598 		return -ENETDOWN;
599 	}
600 
601 	if (pAdapter->Mlme.CntlMachine.CurrState != CNTL_IDLE) {
602 		RTMP_MLME_RESET_STATE_MACHINE(pAdapter);
603 		DBGPRINT(RT_DEBUG_TRACE,
604 			 ("MLME busy, reset MLME state machine!\n"));
605 	}
606 	/* tell CNTL state machine to call NdisMSetInformationComplete() after completing */
607 	/* this request, because this request is initiated by NDIS. */
608 	pAdapter->MlmeAux.CurrReqIsFromNdis = FALSE;
609 	/* Prevent to connect AP again in STAMlmePeriodicExec */
610 	pAdapter->MlmeAux.AutoReconnectSsidLen = 32;
611 
612 	memcpy(Bssid, ap_addr->sa_data, MAC_ADDR_LEN);
613 	MlmeEnqueue(pAdapter,
614 		    MLME_CNTL_STATE_MACHINE,
615 		    OID_802_11_BSSID,
616 		    sizeof(NDIS_802_11_MAC_ADDRESS), (void *) & Bssid);
617 
618 	DBGPRINT(RT_DEBUG_TRACE, ("IOCTL::SIOCSIWAP %pM\n", Bssid));
619 
620 	return 0;
621 }
622 
rt_ioctl_giwap(struct net_device * dev,struct iw_request_info * info,struct sockaddr * ap_addr,char * extra)623 int rt_ioctl_giwap(struct net_device *dev,
624 		   struct iw_request_info *info,
625 		   struct sockaddr *ap_addr, char *extra)
626 {
627 	struct rt_rtmp_adapter *pAdapter = NULL;
628 
629 	GET_PAD_FROM_NET_DEV(pAdapter, dev);
630 
631 	if (INFRA_ON(pAdapter) || ADHOC_ON(pAdapter)) {
632 		ap_addr->sa_family = ARPHRD_ETHER;
633 		memcpy(ap_addr->sa_data, &pAdapter->CommonCfg.Bssid, ETH_ALEN);
634 	}
635 	/* Add for RT2870 */
636 	else if (pAdapter->StaCfg.WpaSupplicantUP != WPA_SUPPLICANT_DISABLE) {
637 		ap_addr->sa_family = ARPHRD_ETHER;
638 		memcpy(ap_addr->sa_data, &pAdapter->MlmeAux.Bssid, ETH_ALEN);
639 	} else {
640 		DBGPRINT(RT_DEBUG_TRACE, ("IOCTL::SIOCGIWAP(=EMPTY)\n"));
641 		return -ENOTCONN;
642 	}
643 
644 	return 0;
645 }
646 
647 /*
648  * Units are in db above the noise floor. That means the
649  * rssi values reported in the tx/rx descriptors in the
650  * driver are the SNR expressed in db.
651  *
652  * If you assume that the noise floor is -95, which is an
653  * excellent assumption 99.5 % of the time, then you can
654  * derive the absolute signal level (i.e. -95 + rssi).
655  * There are some other slight factors to take into account
656  * depending on whether the rssi measurement is from 11b,
657  * 11g, or 11a.   These differences are at most 2db and
658  * can be documented.
659  *
660  * NB: various calculations are based on the orinoco/wavelan
661  *     drivers for compatibility
662  */
set_quality(struct rt_rtmp_adapter * pAdapter,struct iw_quality * iq,signed char rssi)663 static void set_quality(struct rt_rtmp_adapter *pAdapter,
664 			struct iw_quality *iq, signed char rssi)
665 {
666 	__u8 ChannelQuality;
667 
668 	/* Normalize Rssi */
669 	if (rssi >= -50)
670 		ChannelQuality = 100;
671 	else if (rssi >= -80)	/* between -50 ~ -80dbm */
672 		ChannelQuality = (__u8) (24 + ((rssi + 80) * 26) / 10);
673 	else if (rssi >= -90)	/* between -80 ~ -90dbm */
674 		ChannelQuality = (__u8) ((rssi + 90) * 26) / 10;
675 	else
676 		ChannelQuality = 0;
677 
678 	iq->qual = (__u8) ChannelQuality;
679 
680 	iq->level = (__u8) (rssi);
681 	iq->noise = (pAdapter->BbpWriteLatch[66] > pAdapter->BbpTuning.FalseCcaUpperThreshold) ? ((__u8) pAdapter->BbpTuning.FalseCcaUpperThreshold) : ((__u8) pAdapter->BbpWriteLatch[66]);	/* noise level (dBm) */
682 	iq->noise += 256 - 143;
683 	iq->updated = pAdapter->iw_stats.qual.updated;
684 }
685 
rt_ioctl_iwaplist(struct net_device * dev,struct iw_request_info * info,struct iw_point * data,char * extra)686 int rt_ioctl_iwaplist(struct net_device *dev,
687 		      struct iw_request_info *info,
688 		      struct iw_point *data, char *extra)
689 {
690 	struct rt_rtmp_adapter *pAdapter = NULL;
691 
692 	struct sockaddr addr[IW_MAX_AP];
693 	struct iw_quality qual[IW_MAX_AP];
694 	int i;
695 
696 	GET_PAD_FROM_NET_DEV(pAdapter, dev);
697 
698 	/*check if the interface is down */
699 	if (!RTMP_TEST_FLAG(pAdapter, fRTMP_ADAPTER_INTERRUPT_IN_USE)) {
700 		DBGPRINT(RT_DEBUG_TRACE, ("INFO::Network is down!\n"));
701 		data->length = 0;
702 		return 0;
703 		/*return -ENETDOWN; */
704 	}
705 
706 	for (i = 0; i < IW_MAX_AP; i++) {
707 		if (i >= pAdapter->ScanTab.BssNr)
708 			break;
709 		addr[i].sa_family = ARPHRD_ETHER;
710 		memcpy(addr[i].sa_data, &pAdapter->ScanTab.BssEntry[i].Bssid,
711 		       MAC_ADDR_LEN);
712 		set_quality(pAdapter, &qual[i],
713 			    pAdapter->ScanTab.BssEntry[i].Rssi);
714 	}
715 	data->length = i;
716 	memcpy(extra, &addr, i * sizeof(addr[0]));
717 	data->flags = 1;	/* signal quality present (sort of) */
718 	memcpy(extra + i * sizeof(addr[0]), &qual, i * sizeof(qual[i]));
719 
720 	return 0;
721 }
722 
rt_ioctl_siwscan(struct net_device * dev,struct iw_request_info * info,struct iw_point * data,char * extra)723 int rt_ioctl_siwscan(struct net_device *dev,
724 		     struct iw_request_info *info,
725 		     struct iw_point *data, char *extra)
726 {
727 	struct rt_rtmp_adapter *pAdapter = NULL;
728 
729 	unsigned long Now;
730 	int Status = NDIS_STATUS_SUCCESS;
731 
732 	GET_PAD_FROM_NET_DEV(pAdapter, dev);
733 
734 	/*check if the interface is down */
735 	if (!RTMP_TEST_FLAG(pAdapter, fRTMP_ADAPTER_INTERRUPT_IN_USE)) {
736 		DBGPRINT(RT_DEBUG_TRACE, ("INFO::Network is down!\n"));
737 		return -ENETDOWN;
738 	}
739 
740 	if (MONITOR_ON(pAdapter)) {
741 		DBGPRINT(RT_DEBUG_TRACE,
742 			 ("Driver is in Monitor Mode now!\n"));
743 		return -EINVAL;
744 	}
745 
746 	if (pAdapter->StaCfg.WpaSupplicantUP == WPA_SUPPLICANT_ENABLE) {
747 		pAdapter->StaCfg.WpaSupplicantScanCount++;
748 	}
749 
750 	pAdapter->StaCfg.bScanReqIsFromWebUI = TRUE;
751 	if (RTMP_TEST_FLAG(pAdapter, fRTMP_ADAPTER_BSS_SCAN_IN_PROGRESS))
752 		return NDIS_STATUS_SUCCESS;
753 	do {
754 		Now = jiffies;
755 
756 		if ((pAdapter->StaCfg.WpaSupplicantUP == WPA_SUPPLICANT_ENABLE)
757 		    && (pAdapter->StaCfg.WpaSupplicantScanCount > 3)) {
758 			DBGPRINT(RT_DEBUG_TRACE,
759 				 ("WpaSupplicantScanCount > 3\n"));
760 			Status = NDIS_STATUS_SUCCESS;
761 			break;
762 		}
763 
764 		if ((OPSTATUS_TEST_FLAG
765 		     (pAdapter, fOP_STATUS_MEDIA_STATE_CONNECTED))
766 		    && ((pAdapter->StaCfg.AuthMode == Ndis802_11AuthModeWPA)
767 			|| (pAdapter->StaCfg.AuthMode ==
768 			    Ndis802_11AuthModeWPAPSK))
769 		    && (pAdapter->StaCfg.PortSecured ==
770 			WPA_802_1X_PORT_NOT_SECURED)) {
771 			DBGPRINT(RT_DEBUG_TRACE,
772 				 ("Link UP, Port Not Secured! ignore this set::OID_802_11_BSSID_LIST_SCAN\n"));
773 			Status = NDIS_STATUS_SUCCESS;
774 			break;
775 		}
776 
777 		if (pAdapter->Mlme.CntlMachine.CurrState != CNTL_IDLE) {
778 			RTMP_MLME_RESET_STATE_MACHINE(pAdapter);
779 			DBGPRINT(RT_DEBUG_TRACE,
780 				 ("MLME busy, reset MLME state machine!\n"));
781 		}
782 		/* tell CNTL state machine to call NdisMSetInformationComplete() after completing */
783 		/* this request, because this request is initiated by NDIS. */
784 		pAdapter->MlmeAux.CurrReqIsFromNdis = FALSE;
785 		/* Reset allowed scan retries */
786 		pAdapter->StaCfg.ScanCnt = 0;
787 		pAdapter->StaCfg.LastScanTime = Now;
788 
789 		MlmeEnqueue(pAdapter,
790 			    MLME_CNTL_STATE_MACHINE,
791 			    OID_802_11_BSSID_LIST_SCAN, 0, NULL);
792 
793 		Status = NDIS_STATUS_SUCCESS;
794 		RTMP_MLME_HANDLER(pAdapter);
795 	} while (0);
796 	return NDIS_STATUS_SUCCESS;
797 }
798 
rt_ioctl_giwscan(struct net_device * dev,struct iw_request_info * info,struct iw_point * data,char * extra)799 int rt_ioctl_giwscan(struct net_device *dev,
800 		     struct iw_request_info *info,
801 		     struct iw_point *data, char *extra)
802 {
803 	struct rt_rtmp_adapter *pAdapter = NULL;
804 	int i = 0;
805 	char *current_ev = extra, *previous_ev = extra;
806 	char *end_buf;
807 	char *current_val;
808 	char custom[MAX_CUSTOM_LEN] = { 0 };
809 	struct iw_event iwe;
810 
811 	GET_PAD_FROM_NET_DEV(pAdapter, dev);
812 
813 	if (RTMP_TEST_FLAG(pAdapter, fRTMP_ADAPTER_BSS_SCAN_IN_PROGRESS)) {
814 		/*
815 		 * Still scanning, indicate the caller should try again.
816 		 */
817 		return -EAGAIN;
818 	}
819 
820 	if (pAdapter->StaCfg.WpaSupplicantUP == WPA_SUPPLICANT_ENABLE) {
821 		pAdapter->StaCfg.WpaSupplicantScanCount = 0;
822 	}
823 
824 	if (pAdapter->ScanTab.BssNr == 0) {
825 		data->length = 0;
826 		return 0;
827 	}
828 
829 	if (data->length > 0)
830 		end_buf = extra + data->length;
831 	else
832 		end_buf = extra + IW_SCAN_MAX_DATA;
833 
834 	for (i = 0; i < pAdapter->ScanTab.BssNr; i++) {
835 		if (current_ev >= end_buf) {
836 			return -E2BIG;
837 		}
838 		/*MAC address */
839 		/*================================ */
840 		memset(&iwe, 0, sizeof(iwe));
841 		iwe.cmd = SIOCGIWAP;
842 		iwe.u.ap_addr.sa_family = ARPHRD_ETHER;
843 		memcpy(iwe.u.ap_addr.sa_data,
844 		       &pAdapter->ScanTab.BssEntry[i].Bssid, ETH_ALEN);
845 
846 		previous_ev = current_ev;
847 		current_ev =
848 		    iwe_stream_add_event(info, current_ev, end_buf, &iwe,
849 					 IW_EV_ADDR_LEN);
850 		if (current_ev == previous_ev)
851 			return -E2BIG;
852 
853 		/*
854 		   Protocol:
855 		   it will show scanned AP's WirelessMode.
856 		   it might be
857 		   802.11a
858 		   802.11a/n
859 		   802.11g/n
860 		   802.11b/g/n
861 		   802.11g
862 		   802.11b/g
863 		 */
864 		memset(&iwe, 0, sizeof(iwe));
865 		iwe.cmd = SIOCGIWNAME;
866 
867 		{
868 			struct rt_bss_entry *pBssEntry = &pAdapter->ScanTab.BssEntry[i];
869 			BOOLEAN isGonly = FALSE;
870 			int rateCnt = 0;
871 
872 			if (pBssEntry->Channel > 14) {
873 				if (pBssEntry->HtCapabilityLen != 0)
874 					strcpy(iwe.u.name, "802.11a/n");
875 				else
876 					strcpy(iwe.u.name, "802.11a");
877 			} else {
878 				/*
879 				   if one of non B mode rate is set supported rate, it means G only.
880 				 */
881 				for (rateCnt = 0;
882 				     rateCnt < pBssEntry->SupRateLen;
883 				     rateCnt++) {
884 					/*
885 					   6Mbps(140) 9Mbps(146) and >=12Mbps(152) are supported rate, it means G only.
886 					 */
887 					if (pBssEntry->SupRate[rateCnt] == 140
888 					    || pBssEntry->SupRate[rateCnt] ==
889 					    146
890 					    || pBssEntry->SupRate[rateCnt] >=
891 					    152)
892 						isGonly = TRUE;
893 				}
894 
895 				for (rateCnt = 0;
896 				     rateCnt < pBssEntry->ExtRateLen;
897 				     rateCnt++) {
898 					if (pBssEntry->ExtRate[rateCnt] == 140
899 					    || pBssEntry->ExtRate[rateCnt] ==
900 					    146
901 					    || pBssEntry->ExtRate[rateCnt] >=
902 					    152)
903 						isGonly = TRUE;
904 				}
905 
906 				if (pBssEntry->HtCapabilityLen != 0) {
907 					if (isGonly == TRUE)
908 						strcpy(iwe.u.name, "802.11g/n");
909 					else
910 						strcpy(iwe.u.name,
911 						       "802.11b/g/n");
912 				} else {
913 					if (isGonly == TRUE)
914 						strcpy(iwe.u.name, "802.11g");
915 					else {
916 						if (pBssEntry->SupRateLen == 4
917 						    && pBssEntry->ExtRateLen ==
918 						    0)
919 							strcpy(iwe.u.name,
920 							       "802.11b");
921 						else
922 							strcpy(iwe.u.name,
923 							       "802.11b/g");
924 					}
925 				}
926 			}
927 		}
928 
929 		previous_ev = current_ev;
930 		current_ev =
931 		    iwe_stream_add_event(info, current_ev, end_buf, &iwe,
932 					 IW_EV_ADDR_LEN);
933 		if (current_ev == previous_ev)
934 			return -E2BIG;
935 
936 		/*ESSID */
937 		/*================================ */
938 		memset(&iwe, 0, sizeof(iwe));
939 		iwe.cmd = SIOCGIWESSID;
940 		iwe.u.data.length = pAdapter->ScanTab.BssEntry[i].SsidLen;
941 		iwe.u.data.flags = 1;
942 
943 		previous_ev = current_ev;
944 		current_ev =
945 		    iwe_stream_add_point(info, current_ev, end_buf, &iwe,
946 					 (char *)pAdapter->ScanTab.
947 					 BssEntry[i].Ssid);
948 		if (current_ev == previous_ev)
949 			return -E2BIG;
950 
951 		/*Network Type */
952 		/*================================ */
953 		memset(&iwe, 0, sizeof(iwe));
954 		iwe.cmd = SIOCGIWMODE;
955 		if (pAdapter->ScanTab.BssEntry[i].BssType == Ndis802_11IBSS) {
956 			iwe.u.mode = IW_MODE_ADHOC;
957 		} else if (pAdapter->ScanTab.BssEntry[i].BssType ==
958 			   Ndis802_11Infrastructure) {
959 			iwe.u.mode = IW_MODE_INFRA;
960 		} else {
961 			iwe.u.mode = IW_MODE_AUTO;
962 		}
963 		iwe.len = IW_EV_UINT_LEN;
964 
965 		previous_ev = current_ev;
966 		current_ev =
967 		    iwe_stream_add_event(info, current_ev, end_buf, &iwe,
968 					 IW_EV_UINT_LEN);
969 		if (current_ev == previous_ev)
970 			return -E2BIG;
971 
972 		/*Channel and Frequency */
973 		/*================================ */
974 		memset(&iwe, 0, sizeof(iwe));
975 		iwe.cmd = SIOCGIWFREQ;
976 		iwe.u.freq.m = pAdapter->ScanTab.BssEntry[i].Channel;
977 		iwe.u.freq.e = 0;
978 		iwe.u.freq.i = 0;
979 
980 		previous_ev = current_ev;
981 		current_ev =
982 		    iwe_stream_add_event(info, current_ev, end_buf, &iwe,
983 					 IW_EV_FREQ_LEN);
984 		if (current_ev == previous_ev)
985 			return -E2BIG;
986 
987 		/*Add quality statistics */
988 		/*================================ */
989 		memset(&iwe, 0, sizeof(iwe));
990 		iwe.cmd = IWEVQUAL;
991 		iwe.u.qual.level = 0;
992 		iwe.u.qual.noise = 0;
993 		set_quality(pAdapter, &iwe.u.qual,
994 			    pAdapter->ScanTab.BssEntry[i].Rssi);
995 		current_ev =
996 		    iwe_stream_add_event(info, current_ev, end_buf, &iwe,
997 					 IW_EV_QUAL_LEN);
998 		if (current_ev == previous_ev)
999 			return -E2BIG;
1000 
1001 		/*Encyption key */
1002 		/*================================ */
1003 		memset(&iwe, 0, sizeof(iwe));
1004 		iwe.cmd = SIOCGIWENCODE;
1005 		if (CAP_IS_PRIVACY_ON
1006 		    (pAdapter->ScanTab.BssEntry[i].CapabilityInfo))
1007 			iwe.u.data.flags = IW_ENCODE_ENABLED | IW_ENCODE_NOKEY;
1008 		else
1009 			iwe.u.data.flags = IW_ENCODE_DISABLED;
1010 
1011 		previous_ev = current_ev;
1012 		current_ev =
1013 		    iwe_stream_add_point(info, current_ev, end_buf, &iwe,
1014 					 (char *)pAdapter->
1015 					 SharedKey[BSS0][(iwe.u.data.
1016 							  flags &
1017 							  IW_ENCODE_INDEX) -
1018 							 1].Key);
1019 		if (current_ev == previous_ev)
1020 			return -E2BIG;
1021 
1022 		/*Bit Rate */
1023 		/*================================ */
1024 		if (pAdapter->ScanTab.BssEntry[i].SupRateLen) {
1025 			u8 tmpRate =
1026 			    pAdapter->ScanTab.BssEntry[i].SupRate[pAdapter->
1027 								  ScanTab.
1028 								  BssEntry[i].
1029 								  SupRateLen -
1030 								  1];
1031 			memset(&iwe, 0, sizeof(iwe));
1032 			iwe.cmd = SIOCGIWRATE;
1033 			current_val = current_ev + IW_EV_LCP_LEN;
1034 			if (tmpRate == 0x82)
1035 				iwe.u.bitrate.value = 1 * 1000000;
1036 			else if (tmpRate == 0x84)
1037 				iwe.u.bitrate.value = 2 * 1000000;
1038 			else if (tmpRate == 0x8B)
1039 				iwe.u.bitrate.value = 5.5 * 1000000;
1040 			else if (tmpRate == 0x96)
1041 				iwe.u.bitrate.value = 11 * 1000000;
1042 			else
1043 				iwe.u.bitrate.value = (tmpRate / 2) * 1000000;
1044 
1045 			if (tmpRate == 0x6c
1046 			    && pAdapter->ScanTab.BssEntry[i].HtCapabilityLen >
1047 			    0) {
1048 				int rate_count = ARRAY_SIZE(ralinkrate);
1049 				struct rt_ht_cap_info capInfo =
1050 				    pAdapter->ScanTab.BssEntry[i].HtCapability.
1051 				    HtCapInfo;
1052 				int shortGI =
1053 				    capInfo.ChannelWidth ? capInfo.
1054 				    ShortGIfor40 : capInfo.ShortGIfor20;
1055 				int maxMCS =
1056 				    pAdapter->ScanTab.BssEntry[i].HtCapability.
1057 				    MCSSet[1] ? 15 : 7;
1058 				int rate_index =
1059 				    12 + ((u8)capInfo.ChannelWidth * 24) +
1060 				    ((u8)shortGI * 48) + ((u8)maxMCS);
1061 
1062 				if (rate_index < 0)
1063 					rate_index = 0;
1064 				if (rate_index >= rate_count)
1065 					rate_index = rate_count - 1;
1066 				iwe.u.bitrate.value =
1067 				    ralinkrate[rate_index] * 500000;
1068 			}
1069 
1070 			iwe.u.bitrate.disabled = 0;
1071 			current_val = iwe_stream_add_value(info, current_ev,
1072 							   current_val, end_buf,
1073 							   &iwe,
1074 							   IW_EV_PARAM_LEN);
1075 
1076 			if ((current_val - current_ev) > IW_EV_LCP_LEN)
1077 				current_ev = current_val;
1078 			else
1079 				return -E2BIG;
1080 		}
1081 		/*WPA IE */
1082 		if (pAdapter->ScanTab.BssEntry[i].WpaIE.IELen > 0) {
1083 			memset(&iwe, 0, sizeof(iwe));
1084 			memset(&custom[0], 0, MAX_CUSTOM_LEN);
1085 			memcpy(custom,
1086 			       &(pAdapter->ScanTab.BssEntry[i].WpaIE.IE[0]),
1087 			       pAdapter->ScanTab.BssEntry[i].WpaIE.IELen);
1088 			iwe.cmd = IWEVGENIE;
1089 			iwe.u.data.length =
1090 			    pAdapter->ScanTab.BssEntry[i].WpaIE.IELen;
1091 			current_ev =
1092 			    iwe_stream_add_point(info, current_ev, end_buf,
1093 						 &iwe, custom);
1094 			if (current_ev == previous_ev)
1095 				return -E2BIG;
1096 		}
1097 		/*WPA2 IE */
1098 		if (pAdapter->ScanTab.BssEntry[i].RsnIE.IELen > 0) {
1099 			memset(&iwe, 0, sizeof(iwe));
1100 			memset(&custom[0], 0, MAX_CUSTOM_LEN);
1101 			memcpy(custom,
1102 			       &(pAdapter->ScanTab.BssEntry[i].RsnIE.IE[0]),
1103 			       pAdapter->ScanTab.BssEntry[i].RsnIE.IELen);
1104 			iwe.cmd = IWEVGENIE;
1105 			iwe.u.data.length =
1106 			    pAdapter->ScanTab.BssEntry[i].RsnIE.IELen;
1107 			current_ev =
1108 			    iwe_stream_add_point(info, current_ev, end_buf,
1109 						 &iwe, custom);
1110 			if (current_ev == previous_ev)
1111 				return -E2BIG;
1112 		}
1113 	}
1114 
1115 	data->length = current_ev - extra;
1116 	pAdapter->StaCfg.bScanReqIsFromWebUI = FALSE;
1117 	DBGPRINT(RT_DEBUG_ERROR,
1118 		 ("===>rt_ioctl_giwscan. %d(%d) BSS returned, data->length = %d\n",
1119 		  i, pAdapter->ScanTab.BssNr, data->length));
1120 	return 0;
1121 }
1122 
rt_ioctl_siwessid(struct net_device * dev,struct iw_request_info * info,struct iw_point * data,char * essid)1123 int rt_ioctl_siwessid(struct net_device *dev,
1124 		      struct iw_request_info *info,
1125 		      struct iw_point *data, char *essid)
1126 {
1127 	struct rt_rtmp_adapter *pAdapter = NULL;
1128 
1129 	GET_PAD_FROM_NET_DEV(pAdapter, dev);
1130 
1131 	/*check if the interface is down */
1132 	if (!RTMP_TEST_FLAG(pAdapter, fRTMP_ADAPTER_INTERRUPT_IN_USE)) {
1133 		DBGPRINT(RT_DEBUG_TRACE, ("INFO::Network is down!\n"));
1134 		return -ENETDOWN;
1135 	}
1136 
1137 	if (data->flags) {
1138 		char *pSsidString = NULL;
1139 
1140 		/* Includes null character. */
1141 		if (data->length > (IW_ESSID_MAX_SIZE + 1))
1142 			return -E2BIG;
1143 
1144 		pSsidString = kmalloc(MAX_LEN_OF_SSID + 1, MEM_ALLOC_FLAG);
1145 		if (pSsidString) {
1146 			NdisZeroMemory(pSsidString, MAX_LEN_OF_SSID + 1);
1147 			NdisMoveMemory(pSsidString, essid, data->length);
1148 			if (Set_SSID_Proc(pAdapter, pSsidString) == FALSE)
1149 				return -EINVAL;
1150 		} else
1151 			return -ENOMEM;
1152 	} else {
1153 		/* ANY ssid */
1154 		if (Set_SSID_Proc(pAdapter, "") == FALSE)
1155 			return -EINVAL;
1156 	}
1157 	return 0;
1158 }
1159 
rt_ioctl_giwessid(struct net_device * dev,struct iw_request_info * info,struct iw_point * data,char * essid)1160 int rt_ioctl_giwessid(struct net_device *dev,
1161 		      struct iw_request_info *info,
1162 		      struct iw_point *data, char *essid)
1163 {
1164 	struct rt_rtmp_adapter *pAdapter = NULL;
1165 
1166 	GET_PAD_FROM_NET_DEV(pAdapter, dev);
1167 
1168 	data->flags = 1;
1169 	if (MONITOR_ON(pAdapter)) {
1170 		data->length = 0;
1171 		return 0;
1172 	}
1173 
1174 	if (OPSTATUS_TEST_FLAG(pAdapter, fOP_STATUS_MEDIA_STATE_CONNECTED)) {
1175 		DBGPRINT(RT_DEBUG_TRACE, ("MediaState is connected\n"));
1176 		data->length = pAdapter->CommonCfg.SsidLen;
1177 		memcpy(essid, pAdapter->CommonCfg.Ssid,
1178 		       pAdapter->CommonCfg.SsidLen);
1179 	}
1180 #ifdef RTMP_MAC_USB
1181 	/* Add for RT2870 */
1182 	else if (pAdapter->StaCfg.WpaSupplicantUP != WPA_SUPPLICANT_DISABLE) {
1183 		data->length = pAdapter->CommonCfg.SsidLen;
1184 		memcpy(essid, pAdapter->CommonCfg.Ssid,
1185 		       pAdapter->CommonCfg.SsidLen);
1186 	}
1187 #endif /* RTMP_MAC_USB // */
1188 	else {			/*the ANY ssid was specified */
1189 		data->length = 0;
1190 		DBGPRINT(RT_DEBUG_TRACE,
1191 			 ("MediaState is not connected, ess\n"));
1192 	}
1193 
1194 	return 0;
1195 
1196 }
1197 
rt_ioctl_siwnickn(struct net_device * dev,struct iw_request_info * info,struct iw_point * data,char * nickname)1198 int rt_ioctl_siwnickn(struct net_device *dev,
1199 		      struct iw_request_info *info,
1200 		      struct iw_point *data, char *nickname)
1201 {
1202 	struct rt_rtmp_adapter *pAdapter = NULL;
1203 
1204 	GET_PAD_FROM_NET_DEV(pAdapter, dev);
1205 
1206 	/*check if the interface is down */
1207 	if (!RTMP_TEST_FLAG(pAdapter, fRTMP_ADAPTER_INTERRUPT_IN_USE)) {
1208 		DBGPRINT(RT_DEBUG_TRACE, ("INFO::Network is down!\n"));
1209 		return -ENETDOWN;
1210 	}
1211 
1212 	if (data->length > IW_ESSID_MAX_SIZE)
1213 		return -EINVAL;
1214 
1215 	memset(pAdapter->nickname, 0, IW_ESSID_MAX_SIZE + 1);
1216 	memcpy(pAdapter->nickname, nickname, data->length);
1217 
1218 	return 0;
1219 }
1220 
rt_ioctl_giwnickn(struct net_device * dev,struct iw_request_info * info,struct iw_point * data,char * nickname)1221 int rt_ioctl_giwnickn(struct net_device *dev,
1222 		      struct iw_request_info *info,
1223 		      struct iw_point *data, char *nickname)
1224 {
1225 	struct rt_rtmp_adapter *pAdapter = NULL;
1226 
1227 	GET_PAD_FROM_NET_DEV(pAdapter, dev);
1228 
1229 	if (data->length > strlen((char *)pAdapter->nickname) + 1)
1230 		data->length = strlen((char *)pAdapter->nickname) + 1;
1231 	if (data->length > 0) {
1232 		memcpy(nickname, pAdapter->nickname, data->length - 1);
1233 		nickname[data->length - 1] = '\0';
1234 	}
1235 	return 0;
1236 }
1237 
rt_ioctl_siwrts(struct net_device * dev,struct iw_request_info * info,struct iw_param * rts,char * extra)1238 int rt_ioctl_siwrts(struct net_device *dev,
1239 		    struct iw_request_info *info,
1240 		    struct iw_param *rts, char *extra)
1241 {
1242 	struct rt_rtmp_adapter *pAdapter = NULL;
1243 	u16 val;
1244 
1245 	GET_PAD_FROM_NET_DEV(pAdapter, dev);
1246 
1247 	/*check if the interface is down */
1248 	if (!RTMP_TEST_FLAG(pAdapter, fRTMP_ADAPTER_INTERRUPT_IN_USE)) {
1249 		DBGPRINT(RT_DEBUG_TRACE, ("INFO::Network is down!\n"));
1250 		return -ENETDOWN;
1251 	}
1252 
1253 	if (rts->disabled)
1254 		val = MAX_RTS_THRESHOLD;
1255 	else if (rts->value < 0 || rts->value > MAX_RTS_THRESHOLD)
1256 		return -EINVAL;
1257 	else if (rts->value == 0)
1258 		val = MAX_RTS_THRESHOLD;
1259 	else
1260 		val = rts->value;
1261 
1262 	if (val != pAdapter->CommonCfg.RtsThreshold)
1263 		pAdapter->CommonCfg.RtsThreshold = val;
1264 
1265 	return 0;
1266 }
1267 
rt_ioctl_giwrts(struct net_device * dev,struct iw_request_info * info,struct iw_param * rts,char * extra)1268 int rt_ioctl_giwrts(struct net_device *dev,
1269 		    struct iw_request_info *info,
1270 		    struct iw_param *rts, char *extra)
1271 {
1272 	struct rt_rtmp_adapter *pAdapter = NULL;
1273 
1274 	GET_PAD_FROM_NET_DEV(pAdapter, dev);
1275 
1276 	/*check if the interface is down */
1277 	if (!RTMP_TEST_FLAG(pAdapter, fRTMP_ADAPTER_INTERRUPT_IN_USE)) {
1278 		DBGPRINT(RT_DEBUG_TRACE, ("INFO::Network is down!\n"));
1279 		return -ENETDOWN;
1280 	}
1281 
1282 	rts->value = pAdapter->CommonCfg.RtsThreshold;
1283 	rts->disabled = (rts->value == MAX_RTS_THRESHOLD);
1284 	rts->fixed = 1;
1285 
1286 	return 0;
1287 }
1288 
rt_ioctl_siwfrag(struct net_device * dev,struct iw_request_info * info,struct iw_param * frag,char * extra)1289 int rt_ioctl_siwfrag(struct net_device *dev,
1290 		     struct iw_request_info *info,
1291 		     struct iw_param *frag, char *extra)
1292 {
1293 	struct rt_rtmp_adapter *pAdapter = NULL;
1294 	u16 val;
1295 
1296 	GET_PAD_FROM_NET_DEV(pAdapter, dev);
1297 
1298 	/*check if the interface is down */
1299 	if (!RTMP_TEST_FLAG(pAdapter, fRTMP_ADAPTER_INTERRUPT_IN_USE)) {
1300 		DBGPRINT(RT_DEBUG_TRACE, ("INFO::Network is down!\n"));
1301 		return -ENETDOWN;
1302 	}
1303 
1304 	if (frag->disabled)
1305 		val = MAX_FRAG_THRESHOLD;
1306 	else if (frag->value >= MIN_FRAG_THRESHOLD
1307 		 && frag->value <= MAX_FRAG_THRESHOLD)
1308 		val = __cpu_to_le16(frag->value & ~0x1);	/* even numbers only */
1309 	else if (frag->value == 0)
1310 		val = MAX_FRAG_THRESHOLD;
1311 	else
1312 		return -EINVAL;
1313 
1314 	pAdapter->CommonCfg.FragmentThreshold = val;
1315 	return 0;
1316 }
1317 
rt_ioctl_giwfrag(struct net_device * dev,struct iw_request_info * info,struct iw_param * frag,char * extra)1318 int rt_ioctl_giwfrag(struct net_device *dev,
1319 		     struct iw_request_info *info,
1320 		     struct iw_param *frag, char *extra)
1321 {
1322 	struct rt_rtmp_adapter *pAdapter = NULL;
1323 
1324 	GET_PAD_FROM_NET_DEV(pAdapter, dev);
1325 
1326 	/*check if the interface is down */
1327 	if (!RTMP_TEST_FLAG(pAdapter, fRTMP_ADAPTER_INTERRUPT_IN_USE)) {
1328 		DBGPRINT(RT_DEBUG_TRACE, ("INFO::Network is down!\n"));
1329 		return -ENETDOWN;
1330 	}
1331 
1332 	frag->value = pAdapter->CommonCfg.FragmentThreshold;
1333 	frag->disabled = (frag->value == MAX_FRAG_THRESHOLD);
1334 	frag->fixed = 1;
1335 
1336 	return 0;
1337 }
1338 
1339 #define MAX_WEP_KEY_SIZE 13
1340 #define MIN_WEP_KEY_SIZE 5
rt_ioctl_siwencode(struct net_device * dev,struct iw_request_info * info,struct iw_point * erq,char * extra)1341 int rt_ioctl_siwencode(struct net_device *dev,
1342 		       struct iw_request_info *info,
1343 		       struct iw_point *erq, char *extra)
1344 {
1345 	struct rt_rtmp_adapter *pAdapter = NULL;
1346 
1347 	GET_PAD_FROM_NET_DEV(pAdapter, dev);
1348 
1349 	/*check if the interface is down */
1350 	if (!RTMP_TEST_FLAG(pAdapter, fRTMP_ADAPTER_INTERRUPT_IN_USE)) {
1351 		DBGPRINT(RT_DEBUG_TRACE, ("INFO::Network is down!\n"));
1352 		return -ENETDOWN;
1353 	}
1354 
1355 	if ((erq->length == 0) && (erq->flags & IW_ENCODE_DISABLED)) {
1356 		pAdapter->StaCfg.PairCipher = Ndis802_11WEPDisabled;
1357 		pAdapter->StaCfg.GroupCipher = Ndis802_11WEPDisabled;
1358 		pAdapter->StaCfg.WepStatus = Ndis802_11WEPDisabled;
1359 		pAdapter->StaCfg.OrigWepStatus = pAdapter->StaCfg.WepStatus;
1360 		pAdapter->StaCfg.AuthMode = Ndis802_11AuthModeOpen;
1361 		goto done;
1362 	} else if (erq->flags & IW_ENCODE_RESTRICTED
1363 		   || erq->flags & IW_ENCODE_OPEN) {
1364 		/*pAdapter->StaCfg.PortSecured = WPA_802_1X_PORT_SECURED; */
1365 		STA_PORT_SECURED(pAdapter);
1366 		pAdapter->StaCfg.PairCipher = Ndis802_11WEPEnabled;
1367 		pAdapter->StaCfg.GroupCipher = Ndis802_11WEPEnabled;
1368 		pAdapter->StaCfg.WepStatus = Ndis802_11WEPEnabled;
1369 		pAdapter->StaCfg.OrigWepStatus = pAdapter->StaCfg.WepStatus;
1370 		if (erq->flags & IW_ENCODE_RESTRICTED)
1371 			pAdapter->StaCfg.AuthMode = Ndis802_11AuthModeShared;
1372 		else
1373 			pAdapter->StaCfg.AuthMode = Ndis802_11AuthModeOpen;
1374 	}
1375 
1376 	if (erq->length > 0) {
1377 		int keyIdx = (erq->flags & IW_ENCODE_INDEX) - 1;
1378 		/* Check the size of the key */
1379 		if (erq->length > MAX_WEP_KEY_SIZE) {
1380 			return -EINVAL;
1381 		}
1382 		/* Check key index */
1383 		if ((keyIdx < 0) || (keyIdx >= NR_WEP_KEYS)) {
1384 			DBGPRINT(RT_DEBUG_TRACE,
1385 				 ("==>rt_ioctl_siwencode::Wrong keyIdx=%d! Using default key instead (%d)\n",
1386 				  keyIdx, pAdapter->StaCfg.DefaultKeyId));
1387 
1388 			/*Using default key */
1389 			keyIdx = pAdapter->StaCfg.DefaultKeyId;
1390 		} else
1391 			pAdapter->StaCfg.DefaultKeyId = keyIdx;
1392 
1393 		NdisZeroMemory(pAdapter->SharedKey[BSS0][keyIdx].Key, 16);
1394 
1395 		if (erq->length == MAX_WEP_KEY_SIZE) {
1396 			pAdapter->SharedKey[BSS0][keyIdx].KeyLen =
1397 			    MAX_WEP_KEY_SIZE;
1398 			pAdapter->SharedKey[BSS0][keyIdx].CipherAlg =
1399 			    CIPHER_WEP128;
1400 		} else if (erq->length == MIN_WEP_KEY_SIZE) {
1401 			pAdapter->SharedKey[BSS0][keyIdx].KeyLen =
1402 			    MIN_WEP_KEY_SIZE;
1403 			pAdapter->SharedKey[BSS0][keyIdx].CipherAlg =
1404 			    CIPHER_WEP64;
1405 		} else
1406 			/* Disable the key */
1407 			pAdapter->SharedKey[BSS0][keyIdx].KeyLen = 0;
1408 
1409 		/* Check if the key is not marked as invalid */
1410 		if (!(erq->flags & IW_ENCODE_NOKEY)) {
1411 			/* Copy the key in the driver */
1412 			NdisMoveMemory(pAdapter->SharedKey[BSS0][keyIdx].Key,
1413 				       extra, erq->length);
1414 		}
1415 	} else {
1416 		/* Do we want to just set the transmit key index ? */
1417 		int index = (erq->flags & IW_ENCODE_INDEX) - 1;
1418 		if ((index >= 0) && (index < 4)) {
1419 			pAdapter->StaCfg.DefaultKeyId = index;
1420 		} else
1421 			/* Don't complain if the mode is only changed */
1422 		if (!(erq->flags & IW_ENCODE_MODE))
1423 			return -EINVAL;
1424 	}
1425 
1426 done:
1427 	DBGPRINT(RT_DEBUG_TRACE,
1428 		 ("==>rt_ioctl_siwencode::erq->flags=%x\n", erq->flags));
1429 	DBGPRINT(RT_DEBUG_TRACE,
1430 		 ("==>rt_ioctl_siwencode::AuthMode=%x\n",
1431 		  pAdapter->StaCfg.AuthMode));
1432 	DBGPRINT(RT_DEBUG_TRACE,
1433 		 ("==>rt_ioctl_siwencode::DefaultKeyId=%x, KeyLen = %d\n",
1434 		  pAdapter->StaCfg.DefaultKeyId,
1435 		  pAdapter->SharedKey[BSS0][pAdapter->StaCfg.DefaultKeyId].
1436 		  KeyLen));
1437 	DBGPRINT(RT_DEBUG_TRACE,
1438 		 ("==>rt_ioctl_siwencode::WepStatus=%x\n",
1439 		  pAdapter->StaCfg.WepStatus));
1440 	return 0;
1441 }
1442 
1443 int
rt_ioctl_giwencode(struct net_device * dev,struct iw_request_info * info,struct iw_point * erq,char * key)1444 rt_ioctl_giwencode(struct net_device *dev,
1445 		   struct iw_request_info *info,
1446 		   struct iw_point *erq, char *key)
1447 {
1448 	int kid;
1449 	struct rt_rtmp_adapter *pAdapter = NULL;
1450 
1451 	GET_PAD_FROM_NET_DEV(pAdapter, dev);
1452 
1453 	/*check if the interface is down */
1454 	if (!RTMP_TEST_FLAG(pAdapter, fRTMP_ADAPTER_INTERRUPT_IN_USE)) {
1455 		DBGPRINT(RT_DEBUG_TRACE, ("INFO::Network is down!\n"));
1456 		return -ENETDOWN;
1457 	}
1458 
1459 	kid = erq->flags & IW_ENCODE_INDEX;
1460 	DBGPRINT(RT_DEBUG_TRACE,
1461 		 ("===>rt_ioctl_giwencode %d\n", erq->flags & IW_ENCODE_INDEX));
1462 
1463 	if (pAdapter->StaCfg.WepStatus == Ndis802_11WEPDisabled) {
1464 		erq->length = 0;
1465 		erq->flags = IW_ENCODE_DISABLED;
1466 	} else if ((kid > 0) && (kid <= 4)) {
1467 		/* copy wep key */
1468 		erq->flags = kid;	/* NB: base 1 */
1469 		if (erq->length > pAdapter->SharedKey[BSS0][kid - 1].KeyLen)
1470 			erq->length = pAdapter->SharedKey[BSS0][kid - 1].KeyLen;
1471 		memcpy(key, pAdapter->SharedKey[BSS0][kid - 1].Key,
1472 		       erq->length);
1473 		/*if ((kid == pAdapter->PortCfg.DefaultKeyId)) */
1474 		/*erq->flags |= IW_ENCODE_ENABLED; */	/* XXX */
1475 		if (pAdapter->StaCfg.AuthMode == Ndis802_11AuthModeShared)
1476 			erq->flags |= IW_ENCODE_RESTRICTED;	/* XXX */
1477 		else
1478 			erq->flags |= IW_ENCODE_OPEN;	/* XXX */
1479 
1480 	} else if (kid == 0) {
1481 		if (pAdapter->StaCfg.AuthMode == Ndis802_11AuthModeShared)
1482 			erq->flags |= IW_ENCODE_RESTRICTED;	/* XXX */
1483 		else
1484 			erq->flags |= IW_ENCODE_OPEN;	/* XXX */
1485 		erq->length =
1486 		    pAdapter->SharedKey[BSS0][pAdapter->StaCfg.DefaultKeyId].
1487 		    KeyLen;
1488 		memcpy(key,
1489 		       pAdapter->SharedKey[BSS0][pAdapter->StaCfg.DefaultKeyId].
1490 		       Key, erq->length);
1491 		/* copy default key ID */
1492 		if (pAdapter->StaCfg.AuthMode == Ndis802_11AuthModeShared)
1493 			erq->flags |= IW_ENCODE_RESTRICTED;	/* XXX */
1494 		else
1495 			erq->flags |= IW_ENCODE_OPEN;	/* XXX */
1496 		erq->flags = pAdapter->StaCfg.DefaultKeyId + 1;	/* NB: base 1 */
1497 		erq->flags |= IW_ENCODE_ENABLED;	/* XXX */
1498 	}
1499 
1500 	return 0;
1501 
1502 }
1503 
getBaInfo(struct rt_rtmp_adapter * pAd,char * pOutBuf)1504 void getBaInfo(struct rt_rtmp_adapter *pAd, char *pOutBuf)
1505 {
1506 	int i, j;
1507 	struct rt_ba_ori_entry *pOriBAEntry;
1508 	struct rt_ba_rec_entry *pRecBAEntry;
1509 
1510 	for (i = 0; i < MAX_LEN_OF_MAC_TABLE; i++) {
1511 		struct rt_mac_table_entry *pEntry = &pAd->MacTab.Content[i];
1512 		if (((pEntry->ValidAsCLI || pEntry->ValidAsApCli)
1513 		     && (pEntry->Sst == SST_ASSOC))
1514 		    || (pEntry->ValidAsWDS) || (pEntry->ValidAsMesh)) {
1515 			sprintf(pOutBuf + strlen(pOutBuf), "\n%pM (Aid = %d) "
1516 				"(AP) -\n", pEntry->Addr, pEntry->Aid);
1517 
1518 			sprintf(pOutBuf, "%s[Recipient]\n", pOutBuf);
1519 			for (j = 0; j < NUM_OF_TID; j++) {
1520 				if (pEntry->BARecWcidArray[j] != 0) {
1521 					pRecBAEntry =
1522 					    &pAd->BATable.BARecEntry[pEntry->
1523 								     BARecWcidArray
1524 								     [j]];
1525 					sprintf(pOutBuf + strlen(pOutBuf),
1526 						"TID=%d, BAWinSize=%d, LastIndSeq=%d, ReorderingPkts=%d\n",
1527 						j, pRecBAEntry->BAWinSize,
1528 						pRecBAEntry->LastIndSeq,
1529 						pRecBAEntry->list.qlen);
1530 				}
1531 			}
1532 			sprintf(pOutBuf, "%s\n", pOutBuf);
1533 
1534 			sprintf(pOutBuf, "%s[Originator]\n", pOutBuf);
1535 			for (j = 0; j < NUM_OF_TID; j++) {
1536 				if (pEntry->BAOriWcidArray[j] != 0) {
1537 					pOriBAEntry =
1538 					    &pAd->BATable.BAOriEntry[pEntry->
1539 								     BAOriWcidArray
1540 								     [j]];
1541 					sprintf(pOutBuf + strlen(pOutBuf),
1542 						"TID=%d, BAWinSize=%d, StartSeq=%d, CurTxSeq=%d\n",
1543 						j, pOriBAEntry->BAWinSize,
1544 						pOriBAEntry->Sequence,
1545 						pEntry->TxSeq[j]);
1546 				}
1547 			}
1548 			sprintf(pOutBuf, "%s\n\n", pOutBuf);
1549 		}
1550 		if (strlen(pOutBuf) > (IW_PRIV_SIZE_MASK - 30))
1551 			break;
1552 	}
1553 
1554 	return;
1555 }
1556 
rt_ioctl_siwmlme(struct net_device * dev,struct iw_request_info * info,union iwreq_data * wrqu,char * extra)1557 int rt_ioctl_siwmlme(struct net_device *dev,
1558 		     struct iw_request_info *info,
1559 		     union iwreq_data *wrqu, char *extra)
1560 {
1561 	struct rt_rtmp_adapter *pAd = NULL;
1562 	struct iw_mlme *pMlme = (struct iw_mlme *)wrqu->data.pointer;
1563 	struct rt_mlme_queue_elem MsgElem;
1564 	struct rt_mlme_disassoc_req DisAssocReq;
1565 	struct rt_mlme_deauth_req DeAuthReq;
1566 
1567 	GET_PAD_FROM_NET_DEV(pAd, dev);
1568 
1569 	DBGPRINT(RT_DEBUG_TRACE, ("====> %s\n", __func__));
1570 
1571 	if (pMlme == NULL)
1572 		return -EINVAL;
1573 
1574 	switch (pMlme->cmd) {
1575 #ifdef IW_MLME_DEAUTH
1576 	case IW_MLME_DEAUTH:
1577 		DBGPRINT(RT_DEBUG_TRACE,
1578 			 ("====> %s - IW_MLME_DEAUTH\n", __func__));
1579 		COPY_MAC_ADDR(DeAuthReq.Addr, pAd->CommonCfg.Bssid);
1580 		DeAuthReq.Reason = pMlme->reason_code;
1581 		MsgElem.MsgLen = sizeof(struct rt_mlme_deauth_req);
1582 		NdisMoveMemory(MsgElem.Msg, &DeAuthReq,
1583 			       sizeof(struct rt_mlme_deauth_req));
1584 		MlmeDeauthReqAction(pAd, &MsgElem);
1585 		if (INFRA_ON(pAd)) {
1586 			LinkDown(pAd, FALSE);
1587 			pAd->Mlme.AssocMachine.CurrState = ASSOC_IDLE;
1588 		}
1589 		break;
1590 #endif /* IW_MLME_DEAUTH // */
1591 #ifdef IW_MLME_DISASSOC
1592 	case IW_MLME_DISASSOC:
1593 		DBGPRINT(RT_DEBUG_TRACE,
1594 			 ("====> %s - IW_MLME_DISASSOC\n", __func__));
1595 		COPY_MAC_ADDR(DisAssocReq.Addr, pAd->CommonCfg.Bssid);
1596 		DisAssocReq.Reason = pMlme->reason_code;
1597 
1598 		MsgElem.Machine = ASSOC_STATE_MACHINE;
1599 		MsgElem.MsgType = MT2_MLME_DISASSOC_REQ;
1600 		MsgElem.MsgLen = sizeof(struct rt_mlme_disassoc_req);
1601 		NdisMoveMemory(MsgElem.Msg, &DisAssocReq,
1602 			       sizeof(struct rt_mlme_disassoc_req));
1603 
1604 		pAd->Mlme.CntlMachine.CurrState = CNTL_WAIT_OID_DISASSOC;
1605 		MlmeDisassocReqAction(pAd, &MsgElem);
1606 		break;
1607 #endif /* IW_MLME_DISASSOC // */
1608 	default:
1609 		DBGPRINT(RT_DEBUG_TRACE,
1610 			 ("====> %s - Unknow Command\n", __func__));
1611 		break;
1612 	}
1613 
1614 	return 0;
1615 }
1616 
rt_ioctl_siwauth(struct net_device * dev,struct iw_request_info * info,union iwreq_data * wrqu,char * extra)1617 int rt_ioctl_siwauth(struct net_device *dev,
1618 		     struct iw_request_info *info,
1619 		     union iwreq_data *wrqu, char *extra)
1620 {
1621 	struct rt_rtmp_adapter *pAdapter = NULL;
1622 	struct iw_param *param = &wrqu->param;
1623 
1624 	GET_PAD_FROM_NET_DEV(pAdapter, dev);
1625 
1626 	/*check if the interface is down */
1627 	if (!RTMP_TEST_FLAG(pAdapter, fRTMP_ADAPTER_INTERRUPT_IN_USE)) {
1628 		DBGPRINT(RT_DEBUG_TRACE, ("INFO::Network is down!\n"));
1629 		return -ENETDOWN;
1630 	}
1631 	switch (param->flags & IW_AUTH_INDEX) {
1632 	case IW_AUTH_WPA_VERSION:
1633 		if (param->value == IW_AUTH_WPA_VERSION_WPA) {
1634 			pAdapter->StaCfg.AuthMode = Ndis802_11AuthModeWPAPSK;
1635 			if (pAdapter->StaCfg.BssType == BSS_ADHOC)
1636 				pAdapter->StaCfg.AuthMode =
1637 				    Ndis802_11AuthModeWPANone;
1638 		} else if (param->value == IW_AUTH_WPA_VERSION_WPA2)
1639 			pAdapter->StaCfg.AuthMode = Ndis802_11AuthModeWPA2PSK;
1640 
1641 		DBGPRINT(RT_DEBUG_TRACE,
1642 			 ("%s::IW_AUTH_WPA_VERSION - param->value = %d!\n",
1643 			  __func__, param->value));
1644 		break;
1645 	case IW_AUTH_CIPHER_PAIRWISE:
1646 		if (param->value == IW_AUTH_CIPHER_NONE) {
1647 			pAdapter->StaCfg.WepStatus = Ndis802_11WEPDisabled;
1648 			pAdapter->StaCfg.OrigWepStatus =
1649 			    pAdapter->StaCfg.WepStatus;
1650 			pAdapter->StaCfg.PairCipher = Ndis802_11WEPDisabled;
1651 		} else if (param->value == IW_AUTH_CIPHER_WEP40 ||
1652 			   param->value == IW_AUTH_CIPHER_WEP104) {
1653 			pAdapter->StaCfg.WepStatus = Ndis802_11WEPEnabled;
1654 			pAdapter->StaCfg.OrigWepStatus =
1655 			    pAdapter->StaCfg.WepStatus;
1656 			pAdapter->StaCfg.PairCipher = Ndis802_11WEPEnabled;
1657 			pAdapter->StaCfg.IEEE8021X = FALSE;
1658 		} else if (param->value == IW_AUTH_CIPHER_TKIP) {
1659 			pAdapter->StaCfg.WepStatus =
1660 			    Ndis802_11Encryption2Enabled;
1661 			pAdapter->StaCfg.OrigWepStatus =
1662 			    pAdapter->StaCfg.WepStatus;
1663 			pAdapter->StaCfg.PairCipher =
1664 			    Ndis802_11Encryption2Enabled;
1665 		} else if (param->value == IW_AUTH_CIPHER_CCMP) {
1666 			pAdapter->StaCfg.WepStatus =
1667 			    Ndis802_11Encryption3Enabled;
1668 			pAdapter->StaCfg.OrigWepStatus =
1669 			    pAdapter->StaCfg.WepStatus;
1670 			pAdapter->StaCfg.PairCipher =
1671 			    Ndis802_11Encryption3Enabled;
1672 		}
1673 		DBGPRINT(RT_DEBUG_TRACE,
1674 			 ("%s::IW_AUTH_CIPHER_PAIRWISE - param->value = %d!\n",
1675 			  __func__, param->value));
1676 		break;
1677 	case IW_AUTH_CIPHER_GROUP:
1678 		if (param->value == IW_AUTH_CIPHER_NONE) {
1679 			pAdapter->StaCfg.GroupCipher = Ndis802_11WEPDisabled;
1680 		} else if (param->value == IW_AUTH_CIPHER_WEP40 ||
1681 			   param->value == IW_AUTH_CIPHER_WEP104) {
1682 			pAdapter->StaCfg.GroupCipher = Ndis802_11WEPEnabled;
1683 		} else if (param->value == IW_AUTH_CIPHER_TKIP) {
1684 			pAdapter->StaCfg.GroupCipher =
1685 			    Ndis802_11Encryption2Enabled;
1686 		} else if (param->value == IW_AUTH_CIPHER_CCMP) {
1687 			pAdapter->StaCfg.GroupCipher =
1688 			    Ndis802_11Encryption3Enabled;
1689 		}
1690 		DBGPRINT(RT_DEBUG_TRACE,
1691 			 ("%s::IW_AUTH_CIPHER_GROUP - param->value = %d!\n",
1692 			  __func__, param->value));
1693 		break;
1694 	case IW_AUTH_KEY_MGMT:
1695 		if (param->value == IW_AUTH_KEY_MGMT_802_1X) {
1696 			if (pAdapter->StaCfg.AuthMode ==
1697 			    Ndis802_11AuthModeWPAPSK) {
1698 				pAdapter->StaCfg.AuthMode =
1699 				    Ndis802_11AuthModeWPA;
1700 				pAdapter->StaCfg.IEEE8021X = FALSE;
1701 			} else if (pAdapter->StaCfg.AuthMode ==
1702 				   Ndis802_11AuthModeWPA2PSK) {
1703 				pAdapter->StaCfg.AuthMode =
1704 				    Ndis802_11AuthModeWPA2;
1705 				pAdapter->StaCfg.IEEE8021X = FALSE;
1706 			} else
1707 				/* WEP 1x */
1708 				pAdapter->StaCfg.IEEE8021X = TRUE;
1709 		} else if (param->value == 0) {
1710 			/*pAdapter->StaCfg.PortSecured = WPA_802_1X_PORT_SECURED; */
1711 			STA_PORT_SECURED(pAdapter);
1712 		}
1713 		DBGPRINT(RT_DEBUG_TRACE,
1714 			 ("%s::IW_AUTH_KEY_MGMT - param->value = %d!\n",
1715 			  __func__, param->value));
1716 		break;
1717 	case IW_AUTH_RX_UNENCRYPTED_EAPOL:
1718 		break;
1719 	case IW_AUTH_PRIVACY_INVOKED:
1720 		/*if (param->value == 0)
1721 		   {
1722 		   pAdapter->StaCfg.AuthMode = Ndis802_11AuthModeOpen;
1723 		   pAdapter->StaCfg.WepStatus = Ndis802_11WEPDisabled;
1724 		   pAdapter->StaCfg.OrigWepStatus = pAdapter->StaCfg.WepStatus;
1725 		   pAdapter->StaCfg.PairCipher = Ndis802_11WEPDisabled;
1726 		   pAdapter->StaCfg.GroupCipher = Ndis802_11WEPDisabled;
1727 		   } */
1728 		DBGPRINT(RT_DEBUG_TRACE,
1729 			 ("%s::IW_AUTH_PRIVACY_INVOKED - param->value = %d!\n",
1730 			  __func__, param->value));
1731 		break;
1732 	case IW_AUTH_DROP_UNENCRYPTED:
1733 		if (param->value != 0)
1734 			pAdapter->StaCfg.PortSecured =
1735 			    WPA_802_1X_PORT_NOT_SECURED;
1736 		else {
1737 			/*pAdapter->StaCfg.PortSecured = WPA_802_1X_PORT_SECURED; */
1738 			STA_PORT_SECURED(pAdapter);
1739 		}
1740 		DBGPRINT(RT_DEBUG_TRACE,
1741 			 ("%s::IW_AUTH_WPA_VERSION - param->value = %d!\n",
1742 			  __func__, param->value));
1743 		break;
1744 	case IW_AUTH_80211_AUTH_ALG:
1745 		if (param->value & IW_AUTH_ALG_SHARED_KEY) {
1746 			pAdapter->StaCfg.AuthMode = Ndis802_11AuthModeShared;
1747 		} else if (param->value & IW_AUTH_ALG_OPEN_SYSTEM) {
1748 			pAdapter->StaCfg.AuthMode = Ndis802_11AuthModeOpen;
1749 		} else
1750 			return -EINVAL;
1751 		DBGPRINT(RT_DEBUG_TRACE,
1752 			 ("%s::IW_AUTH_80211_AUTH_ALG - param->value = %d!\n",
1753 			  __func__, param->value));
1754 		break;
1755 	case IW_AUTH_WPA_ENABLED:
1756 		DBGPRINT(RT_DEBUG_TRACE,
1757 			 ("%s::IW_AUTH_WPA_ENABLED - Driver supports WPA!(param->value = %d)\n",
1758 			  __func__, param->value));
1759 		break;
1760 	default:
1761 		return -EOPNOTSUPP;
1762 	}
1763 
1764 	return 0;
1765 }
1766 
rt_ioctl_giwauth(struct net_device * dev,struct iw_request_info * info,union iwreq_data * wrqu,char * extra)1767 int rt_ioctl_giwauth(struct net_device *dev,
1768 		     struct iw_request_info *info,
1769 		     union iwreq_data *wrqu, char *extra)
1770 {
1771 	struct rt_rtmp_adapter *pAdapter = NULL;
1772 	struct iw_param *param = &wrqu->param;
1773 
1774 	GET_PAD_FROM_NET_DEV(pAdapter, dev);
1775 
1776 	/*check if the interface is down */
1777 	if (!RTMP_TEST_FLAG(pAdapter, fRTMP_ADAPTER_INTERRUPT_IN_USE)) {
1778 		DBGPRINT(RT_DEBUG_TRACE, ("INFO::Network is down!\n"));
1779 		return -ENETDOWN;
1780 	}
1781 
1782 	switch (param->flags & IW_AUTH_INDEX) {
1783 	case IW_AUTH_DROP_UNENCRYPTED:
1784 		param->value =
1785 		    (pAdapter->StaCfg.WepStatus ==
1786 		     Ndis802_11WEPDisabled) ? 0 : 1;
1787 		break;
1788 
1789 	case IW_AUTH_80211_AUTH_ALG:
1790 		param->value =
1791 		    (pAdapter->StaCfg.AuthMode ==
1792 		     Ndis802_11AuthModeShared) ? IW_AUTH_ALG_SHARED_KEY :
1793 		    IW_AUTH_ALG_OPEN_SYSTEM;
1794 		break;
1795 
1796 	case IW_AUTH_WPA_ENABLED:
1797 		param->value =
1798 		    (pAdapter->StaCfg.AuthMode >=
1799 		     Ndis802_11AuthModeWPA) ? 1 : 0;
1800 		break;
1801 
1802 	default:
1803 		return -EOPNOTSUPP;
1804 	}
1805 	DBGPRINT(RT_DEBUG_TRACE,
1806 		 ("rt_ioctl_giwauth::param->value = %d!\n", param->value));
1807 	return 0;
1808 }
1809 
fnSetCipherKey(struct rt_rtmp_adapter * pAdapter,int keyIdx,u8 CipherAlg,IN BOOLEAN bGTK,IN struct iw_encode_ext * ext)1810 void fnSetCipherKey(struct rt_rtmp_adapter *pAdapter,
1811 		    int keyIdx,
1812 		    u8 CipherAlg,
1813 		    IN BOOLEAN bGTK, IN struct iw_encode_ext *ext)
1814 {
1815 	NdisZeroMemory(&pAdapter->SharedKey[BSS0][keyIdx], sizeof(struct rt_cipher_key));
1816 	pAdapter->SharedKey[BSS0][keyIdx].KeyLen = LEN_TKIP_EK;
1817 	NdisMoveMemory(pAdapter->SharedKey[BSS0][keyIdx].Key, ext->key,
1818 		       LEN_TKIP_EK);
1819 	NdisMoveMemory(pAdapter->SharedKey[BSS0][keyIdx].TxMic,
1820 		       ext->key + LEN_TKIP_EK, LEN_TKIP_TXMICK);
1821 	NdisMoveMemory(pAdapter->SharedKey[BSS0][keyIdx].RxMic,
1822 		       ext->key + LEN_TKIP_EK + LEN_TKIP_TXMICK,
1823 		       LEN_TKIP_RXMICK);
1824 	pAdapter->SharedKey[BSS0][keyIdx].CipherAlg = CipherAlg;
1825 
1826 	/* Update group key information to ASIC Shared Key Table */
1827 	AsicAddSharedKeyEntry(pAdapter,
1828 			      BSS0,
1829 			      keyIdx,
1830 			      pAdapter->SharedKey[BSS0][keyIdx].CipherAlg,
1831 			      pAdapter->SharedKey[BSS0][keyIdx].Key,
1832 			      pAdapter->SharedKey[BSS0][keyIdx].TxMic,
1833 			      pAdapter->SharedKey[BSS0][keyIdx].RxMic);
1834 
1835 	if (bGTK)
1836 		/* Update ASIC WCID attribute table and IVEIV table */
1837 		RTMPAddWcidAttributeEntry(pAdapter,
1838 					  BSS0,
1839 					  keyIdx,
1840 					  pAdapter->SharedKey[BSS0][keyIdx].
1841 					  CipherAlg, NULL);
1842 	else
1843 		/* Update ASIC WCID attribute table and IVEIV table */
1844 		RTMPAddWcidAttributeEntry(pAdapter,
1845 					  BSS0,
1846 					  keyIdx,
1847 					  pAdapter->SharedKey[BSS0][keyIdx].
1848 					  CipherAlg,
1849 					  &pAdapter->MacTab.
1850 					  Content[BSSID_WCID]);
1851 }
1852 
rt_ioctl_siwencodeext(struct net_device * dev,struct iw_request_info * info,union iwreq_data * wrqu,char * extra)1853 int rt_ioctl_siwencodeext(struct net_device *dev,
1854 			  struct iw_request_info *info,
1855 			  union iwreq_data *wrqu, char *extra)
1856 {
1857 	struct rt_rtmp_adapter *pAdapter = NULL;
1858 	struct iw_point *encoding = &wrqu->encoding;
1859 	struct iw_encode_ext *ext = (struct iw_encode_ext *)extra;
1860 	int keyIdx, alg = ext->alg;
1861 
1862 	GET_PAD_FROM_NET_DEV(pAdapter, dev);
1863 
1864 	/*check if the interface is down */
1865 	if (!RTMP_TEST_FLAG(pAdapter, fRTMP_ADAPTER_INTERRUPT_IN_USE)) {
1866 		DBGPRINT(RT_DEBUG_TRACE, ("INFO::Network is down!\n"));
1867 		return -ENETDOWN;
1868 	}
1869 
1870 	if (encoding->flags & IW_ENCODE_DISABLED) {
1871 		keyIdx = (encoding->flags & IW_ENCODE_INDEX) - 1;
1872 		/* set BSSID wcid entry of the Pair-wise Key table as no-security mode */
1873 		AsicRemovePairwiseKeyEntry(pAdapter, BSS0, BSSID_WCID);
1874 		pAdapter->SharedKey[BSS0][keyIdx].KeyLen = 0;
1875 		pAdapter->SharedKey[BSS0][keyIdx].CipherAlg = CIPHER_NONE;
1876 		AsicRemoveSharedKeyEntry(pAdapter, 0, (u8)keyIdx);
1877 		NdisZeroMemory(&pAdapter->SharedKey[BSS0][keyIdx],
1878 			       sizeof(struct rt_cipher_key));
1879 		DBGPRINT(RT_DEBUG_TRACE,
1880 			 ("%s::Remove all keys!(encoding->flags = %x)\n",
1881 			  __func__, encoding->flags));
1882 	} else {
1883 		/* Get Key Index and convet to our own defined key index */
1884 		keyIdx = (encoding->flags & IW_ENCODE_INDEX) - 1;
1885 		if ((keyIdx < 0) || (keyIdx >= NR_WEP_KEYS))
1886 			return -EINVAL;
1887 
1888 		if (ext->ext_flags & IW_ENCODE_EXT_SET_TX_KEY) {
1889 			pAdapter->StaCfg.DefaultKeyId = keyIdx;
1890 			DBGPRINT(RT_DEBUG_TRACE,
1891 				 ("%s::DefaultKeyId = %d\n", __func__,
1892 				  pAdapter->StaCfg.DefaultKeyId));
1893 		}
1894 
1895 		switch (alg) {
1896 		case IW_ENCODE_ALG_NONE:
1897 			DBGPRINT(RT_DEBUG_TRACE,
1898 				 ("%s::IW_ENCODE_ALG_NONE\n", __func__));
1899 			break;
1900 		case IW_ENCODE_ALG_WEP:
1901 			DBGPRINT(RT_DEBUG_TRACE,
1902 				 ("%s::IW_ENCODE_ALG_WEP - ext->key_len = %d, keyIdx = %d\n",
1903 				  __func__, ext->key_len, keyIdx));
1904 			if (ext->key_len == MAX_WEP_KEY_SIZE) {
1905 				pAdapter->SharedKey[BSS0][keyIdx].KeyLen =
1906 				    MAX_WEP_KEY_SIZE;
1907 				pAdapter->SharedKey[BSS0][keyIdx].CipherAlg =
1908 				    CIPHER_WEP128;
1909 			} else if (ext->key_len == MIN_WEP_KEY_SIZE) {
1910 				pAdapter->SharedKey[BSS0][keyIdx].KeyLen =
1911 				    MIN_WEP_KEY_SIZE;
1912 				pAdapter->SharedKey[BSS0][keyIdx].CipherAlg =
1913 				    CIPHER_WEP64;
1914 			} else
1915 				return -EINVAL;
1916 
1917 			NdisZeroMemory(pAdapter->SharedKey[BSS0][keyIdx].Key,
1918 				       16);
1919 			NdisMoveMemory(pAdapter->SharedKey[BSS0][keyIdx].Key,
1920 				       ext->key, ext->key_len);
1921 			if (pAdapter->StaCfg.GroupCipher ==
1922 			    Ndis802_11GroupWEP40Enabled
1923 			    || pAdapter->StaCfg.GroupCipher ==
1924 			    Ndis802_11GroupWEP104Enabled) {
1925 				/* Set Group key material to Asic */
1926 				AsicAddSharedKeyEntry(pAdapter, BSS0, keyIdx,
1927 						      pAdapter->
1928 						      SharedKey[BSS0][keyIdx].
1929 						      CipherAlg,
1930 						      pAdapter->
1931 						      SharedKey[BSS0][keyIdx].
1932 						      Key, NULL, NULL);
1933 
1934 				/* Update WCID attribute table and IVEIV table for this group key table */
1935 				RTMPAddWcidAttributeEntry(pAdapter, BSS0,
1936 							  keyIdx,
1937 							  pAdapter->
1938 							  SharedKey[BSS0]
1939 							  [keyIdx].CipherAlg,
1940 							  NULL);
1941 
1942 				STA_PORT_SECURED(pAdapter);
1943 
1944 				/* Indicate Connected for GUI */
1945 				pAdapter->IndicateMediaState =
1946 				    NdisMediaStateConnected;
1947 			}
1948 			break;
1949 		case IW_ENCODE_ALG_TKIP:
1950 			DBGPRINT(RT_DEBUG_TRACE,
1951 				 ("%s::IW_ENCODE_ALG_TKIP - keyIdx = %d, ext->key_len = %d\n",
1952 				  __func__, keyIdx, ext->key_len));
1953 			if (ext->key_len == 32) {
1954 				if (ext->ext_flags & IW_ENCODE_EXT_SET_TX_KEY) {
1955 					fnSetCipherKey(pAdapter, keyIdx,
1956 						       CIPHER_TKIP, FALSE, ext);
1957 					if (pAdapter->StaCfg.AuthMode >=
1958 					    Ndis802_11AuthModeWPA2) {
1959 						/*pAdapter->StaCfg.PortSecured = WPA_802_1X_PORT_SECURED; */
1960 						STA_PORT_SECURED(pAdapter);
1961 						pAdapter->IndicateMediaState =
1962 						    NdisMediaStateConnected;
1963 					}
1964 				} else if (ext->
1965 					   ext_flags & IW_ENCODE_EXT_GROUP_KEY)
1966 				{
1967 					fnSetCipherKey(pAdapter, keyIdx,
1968 						       CIPHER_TKIP, TRUE, ext);
1969 
1970 					/* set 802.1x port control */
1971 					/*pAdapter->StaCfg.PortSecured = WPA_802_1X_PORT_SECURED; */
1972 					STA_PORT_SECURED(pAdapter);
1973 					pAdapter->IndicateMediaState =
1974 					    NdisMediaStateConnected;
1975 				}
1976 			} else
1977 				return -EINVAL;
1978 			break;
1979 		case IW_ENCODE_ALG_CCMP:
1980 			if (ext->ext_flags & IW_ENCODE_EXT_SET_TX_KEY) {
1981 				fnSetCipherKey(pAdapter, keyIdx, CIPHER_AES,
1982 					       FALSE, ext);
1983 				if (pAdapter->StaCfg.AuthMode >=
1984 				    Ndis802_11AuthModeWPA2)
1985 					/*pAdapter->StaCfg.PortSecured = WPA_802_1X_PORT_SECURED; */
1986 					STA_PORT_SECURED(pAdapter);
1987 				pAdapter->IndicateMediaState =
1988 				    NdisMediaStateConnected;
1989 			} else if (ext->ext_flags & IW_ENCODE_EXT_GROUP_KEY) {
1990 				fnSetCipherKey(pAdapter, keyIdx, CIPHER_AES,
1991 					       TRUE, ext);
1992 
1993 				/* set 802.1x port control */
1994 				/*pAdapter->StaCfg.PortSecured = WPA_802_1X_PORT_SECURED; */
1995 				STA_PORT_SECURED(pAdapter);
1996 				pAdapter->IndicateMediaState =
1997 				    NdisMediaStateConnected;
1998 			}
1999 			break;
2000 		default:
2001 			return -EINVAL;
2002 		}
2003 	}
2004 
2005 	return 0;
2006 }
2007 
2008 int
rt_ioctl_giwencodeext(struct net_device * dev,struct iw_request_info * info,union iwreq_data * wrqu,char * extra)2009 rt_ioctl_giwencodeext(struct net_device *dev,
2010 		      struct iw_request_info *info,
2011 		      union iwreq_data *wrqu, char *extra)
2012 {
2013 	struct rt_rtmp_adapter *pAd = NULL;
2014 	char *pKey = NULL;
2015 	struct iw_point *encoding = &wrqu->encoding;
2016 	struct iw_encode_ext *ext = (struct iw_encode_ext *)extra;
2017 	int idx, max_key_len;
2018 
2019 	GET_PAD_FROM_NET_DEV(pAd, dev);
2020 
2021 	DBGPRINT(RT_DEBUG_TRACE, ("===> rt_ioctl_giwencodeext\n"));
2022 
2023 	max_key_len = encoding->length - sizeof(*ext);
2024 	if (max_key_len < 0)
2025 		return -EINVAL;
2026 
2027 	idx = encoding->flags & IW_ENCODE_INDEX;
2028 	if (idx) {
2029 		if (idx < 1 || idx > 4)
2030 			return -EINVAL;
2031 		idx--;
2032 
2033 		if ((pAd->StaCfg.WepStatus == Ndis802_11Encryption2Enabled) ||
2034 		    (pAd->StaCfg.WepStatus == Ndis802_11Encryption3Enabled)) {
2035 			if (idx != pAd->StaCfg.DefaultKeyId) {
2036 				ext->key_len = 0;
2037 				return 0;
2038 			}
2039 		}
2040 	} else
2041 		idx = pAd->StaCfg.DefaultKeyId;
2042 
2043 	encoding->flags = idx + 1;
2044 	memset(ext, 0, sizeof(*ext));
2045 
2046 	ext->key_len = 0;
2047 	switch (pAd->StaCfg.WepStatus) {
2048 	case Ndis802_11WEPDisabled:
2049 		ext->alg = IW_ENCODE_ALG_NONE;
2050 		encoding->flags |= IW_ENCODE_DISABLED;
2051 		break;
2052 	case Ndis802_11WEPEnabled:
2053 		ext->alg = IW_ENCODE_ALG_WEP;
2054 		if (pAd->SharedKey[BSS0][idx].KeyLen > max_key_len)
2055 			return -E2BIG;
2056 		else {
2057 			ext->key_len = pAd->SharedKey[BSS0][idx].KeyLen;
2058 			pKey = (char *)& (pAd->SharedKey[BSS0][idx].Key[0]);
2059 		}
2060 		break;
2061 	case Ndis802_11Encryption2Enabled:
2062 	case Ndis802_11Encryption3Enabled:
2063 		if (pAd->StaCfg.WepStatus == Ndis802_11Encryption2Enabled)
2064 			ext->alg = IW_ENCODE_ALG_TKIP;
2065 		else
2066 			ext->alg = IW_ENCODE_ALG_CCMP;
2067 
2068 		if (max_key_len < 32)
2069 			return -E2BIG;
2070 		else {
2071 			ext->key_len = 32;
2072 			pKey = (char *)& pAd->StaCfg.PMK[0];
2073 		}
2074 		break;
2075 	default:
2076 		return -EINVAL;
2077 	}
2078 
2079 	if (ext->key_len && pKey) {
2080 		encoding->flags |= IW_ENCODE_ENABLED;
2081 		memcpy(ext->key, pKey, ext->key_len);
2082 	}
2083 
2084 	return 0;
2085 }
2086 
rt_ioctl_siwgenie(struct net_device * dev,struct iw_request_info * info,union iwreq_data * wrqu,char * extra)2087 int rt_ioctl_siwgenie(struct net_device *dev,
2088 		      struct iw_request_info *info,
2089 		      union iwreq_data *wrqu, char *extra)
2090 {
2091 	struct rt_rtmp_adapter *pAd = NULL;
2092 
2093 	GET_PAD_FROM_NET_DEV(pAd, dev);
2094 
2095 	DBGPRINT(RT_DEBUG_TRACE, ("===> rt_ioctl_siwgenie\n"));
2096 	pAd->StaCfg.bRSN_IE_FromWpaSupplicant = FALSE;
2097 	if (wrqu->data.length > MAX_LEN_OF_RSNIE ||
2098 	    (wrqu->data.length && extra == NULL))
2099 		return -EINVAL;
2100 
2101 	if (wrqu->data.length) {
2102 		pAd->StaCfg.RSNIE_Len = wrqu->data.length;
2103 		NdisMoveMemory(&pAd->StaCfg.RSN_IE[0], extra,
2104 			       pAd->StaCfg.RSNIE_Len);
2105 		pAd->StaCfg.bRSN_IE_FromWpaSupplicant = TRUE;
2106 	} else {
2107 		pAd->StaCfg.RSNIE_Len = 0;
2108 		NdisZeroMemory(&pAd->StaCfg.RSN_IE[0], MAX_LEN_OF_RSNIE);
2109 	}
2110 
2111 	return 0;
2112 }
2113 
rt_ioctl_giwgenie(struct net_device * dev,struct iw_request_info * info,union iwreq_data * wrqu,char * extra)2114 int rt_ioctl_giwgenie(struct net_device *dev,
2115 		      struct iw_request_info *info,
2116 		      union iwreq_data *wrqu, char *extra)
2117 {
2118 	struct rt_rtmp_adapter *pAd = NULL;
2119 
2120 	GET_PAD_FROM_NET_DEV(pAd, dev);
2121 
2122 	if ((pAd->StaCfg.RSNIE_Len == 0) ||
2123 	    (pAd->StaCfg.AuthMode < Ndis802_11AuthModeWPA)) {
2124 		wrqu->data.length = 0;
2125 		return 0;
2126 	}
2127 
2128 	if (pAd->StaCfg.WpaSupplicantUP == WPA_SUPPLICANT_ENABLE) {
2129 		if (wrqu->data.length < pAd->StaCfg.RSNIE_Len)
2130 			return -E2BIG;
2131 
2132 		wrqu->data.length = pAd->StaCfg.RSNIE_Len;
2133 		memcpy(extra, &pAd->StaCfg.RSN_IE[0], pAd->StaCfg.RSNIE_Len);
2134 	} else {
2135 		u8 RSNIe = IE_WPA;
2136 
2137 		if (wrqu->data.length < (pAd->StaCfg.RSNIE_Len + 2))	/* ID, Len */
2138 			return -E2BIG;
2139 		wrqu->data.length = pAd->StaCfg.RSNIE_Len + 2;
2140 
2141 		if ((pAd->StaCfg.AuthMode == Ndis802_11AuthModeWPA2PSK) ||
2142 		    (pAd->StaCfg.AuthMode == Ndis802_11AuthModeWPA2))
2143 			RSNIe = IE_RSN;
2144 
2145 		extra[0] = (char)RSNIe;
2146 		extra[1] = pAd->StaCfg.RSNIE_Len;
2147 		memcpy(extra + 2, &pAd->StaCfg.RSN_IE[0],
2148 		       pAd->StaCfg.RSNIE_Len);
2149 	}
2150 
2151 	return 0;
2152 }
2153 
rt_ioctl_siwpmksa(struct net_device * dev,struct iw_request_info * info,union iwreq_data * wrqu,char * extra)2154 int rt_ioctl_siwpmksa(struct net_device *dev,
2155 		      struct iw_request_info *info,
2156 		      union iwreq_data *wrqu, char *extra)
2157 {
2158 	struct rt_rtmp_adapter *pAd = NULL;
2159 	struct iw_pmksa *pPmksa = (struct iw_pmksa *)wrqu->data.pointer;
2160 	int CachedIdx = 0, idx = 0;
2161 
2162 	GET_PAD_FROM_NET_DEV(pAd, dev);
2163 
2164 	if (pPmksa == NULL)
2165 		return -EINVAL;
2166 
2167 	DBGPRINT(RT_DEBUG_TRACE, ("===> rt_ioctl_siwpmksa\n"));
2168 	switch (pPmksa->cmd) {
2169 	case IW_PMKSA_FLUSH:
2170 		NdisZeroMemory(pAd->StaCfg.SavedPMK,
2171 			       sizeof(struct rt_bssid_info) * PMKID_NO);
2172 		DBGPRINT(RT_DEBUG_TRACE,
2173 			 ("rt_ioctl_siwpmksa - IW_PMKSA_FLUSH\n"));
2174 		break;
2175 	case IW_PMKSA_REMOVE:
2176 		for (CachedIdx = 0; CachedIdx < pAd->StaCfg.SavedPMKNum;
2177 		     CachedIdx++) {
2178 			/* compare the BSSID */
2179 			if (NdisEqualMemory
2180 			    (pPmksa->bssid.sa_data,
2181 			     pAd->StaCfg.SavedPMK[CachedIdx].BSSID,
2182 			     MAC_ADDR_LEN)) {
2183 				NdisZeroMemory(pAd->StaCfg.SavedPMK[CachedIdx].
2184 					       BSSID, MAC_ADDR_LEN);
2185 				NdisZeroMemory(pAd->StaCfg.SavedPMK[CachedIdx].
2186 					       PMKID, 16);
2187 				for (idx = CachedIdx;
2188 				     idx < (pAd->StaCfg.SavedPMKNum - 1);
2189 				     idx++) {
2190 					NdisMoveMemory(&pAd->StaCfg.
2191 						       SavedPMK[idx].BSSID[0],
2192 						       &pAd->StaCfg.
2193 						       SavedPMK[idx +
2194 								1].BSSID[0],
2195 						       MAC_ADDR_LEN);
2196 					NdisMoveMemory(&pAd->StaCfg.
2197 						       SavedPMK[idx].PMKID[0],
2198 						       &pAd->StaCfg.
2199 						       SavedPMK[idx +
2200 								1].PMKID[0],
2201 						       16);
2202 				}
2203 				pAd->StaCfg.SavedPMKNum--;
2204 				break;
2205 			}
2206 		}
2207 
2208 		DBGPRINT(RT_DEBUG_TRACE,
2209 			 ("rt_ioctl_siwpmksa - IW_PMKSA_REMOVE\n"));
2210 		break;
2211 	case IW_PMKSA_ADD:
2212 		for (CachedIdx = 0; CachedIdx < pAd->StaCfg.SavedPMKNum;
2213 		     CachedIdx++) {
2214 			/* compare the BSSID */
2215 			if (NdisEqualMemory
2216 			    (pPmksa->bssid.sa_data,
2217 			     pAd->StaCfg.SavedPMK[CachedIdx].BSSID,
2218 			     MAC_ADDR_LEN))
2219 				break;
2220 		}
2221 
2222 		/* Found, replace it */
2223 		if (CachedIdx < PMKID_NO) {
2224 			DBGPRINT(RT_DEBUG_OFF,
2225 				 ("Update PMKID, idx = %d\n", CachedIdx));
2226 			NdisMoveMemory(&pAd->StaCfg.SavedPMK[CachedIdx].
2227 				       BSSID[0], pPmksa->bssid.sa_data,
2228 				       MAC_ADDR_LEN);
2229 			NdisMoveMemory(&pAd->StaCfg.SavedPMK[CachedIdx].
2230 				       PMKID[0], pPmksa->pmkid, 16);
2231 			pAd->StaCfg.SavedPMKNum++;
2232 		}
2233 		/* Not found, replace the last one */
2234 		else {
2235 			/* Randomly replace one */
2236 			CachedIdx = (pPmksa->bssid.sa_data[5] % PMKID_NO);
2237 			DBGPRINT(RT_DEBUG_OFF,
2238 				 ("Update PMKID, idx = %d\n", CachedIdx));
2239 			NdisMoveMemory(&pAd->StaCfg.SavedPMK[CachedIdx].
2240 				       BSSID[0], pPmksa->bssid.sa_data,
2241 				       MAC_ADDR_LEN);
2242 			NdisMoveMemory(&pAd->StaCfg.SavedPMK[CachedIdx].
2243 				       PMKID[0], pPmksa->pmkid, 16);
2244 		}
2245 
2246 		DBGPRINT(RT_DEBUG_TRACE,
2247 			 ("rt_ioctl_siwpmksa - IW_PMKSA_ADD\n"));
2248 		break;
2249 	default:
2250 		DBGPRINT(RT_DEBUG_TRACE,
2251 			 ("rt_ioctl_siwpmksa - Unknown Command!\n"));
2252 		break;
2253 	}
2254 
2255 	return 0;
2256 }
2257 
rt_ioctl_siwrate(struct net_device * dev,struct iw_request_info * info,union iwreq_data * wrqu,char * extra)2258 int rt_ioctl_siwrate(struct net_device *dev,
2259 		     struct iw_request_info *info,
2260 		     union iwreq_data *wrqu, char *extra)
2261 {
2262 	struct rt_rtmp_adapter *pAd = NULL;
2263 	u32 rate = wrqu->bitrate.value, fixed = wrqu->bitrate.fixed;
2264 
2265 	GET_PAD_FROM_NET_DEV(pAd, dev);
2266 
2267 	/*check if the interface is down */
2268 	if (!RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_INTERRUPT_IN_USE)) {
2269 		DBGPRINT(RT_DEBUG_TRACE,
2270 			 ("rt_ioctl_siwrate::Network is down!\n"));
2271 		return -ENETDOWN;
2272 	}
2273 
2274 	DBGPRINT(RT_DEBUG_TRACE,
2275 		 ("rt_ioctl_siwrate::(rate = %d, fixed = %d)\n", rate, fixed));
2276 	/* rate = -1 => auto rate
2277 	   rate = X, fixed = 1 => (fixed rate X)
2278 	 */
2279 	if (rate == -1) {
2280 		/*Auto Rate */
2281 		pAd->StaCfg.DesiredTransmitSetting.field.MCS = MCS_AUTO;
2282 		pAd->StaCfg.bAutoTxRateSwitch = TRUE;
2283 		if ((pAd->CommonCfg.PhyMode <= PHY_11G) ||
2284 		    (pAd->MacTab.Content[BSSID_WCID].HTPhyMode.field.MODE <=
2285 		     MODE_OFDM))
2286 			RTMPSetDesiredRates(pAd, -1);
2287 
2288 		SetCommonHT(pAd);
2289 	} else {
2290 		if (fixed) {
2291 			pAd->StaCfg.bAutoTxRateSwitch = FALSE;
2292 			if ((pAd->CommonCfg.PhyMode <= PHY_11G) ||
2293 			    (pAd->MacTab.Content[BSSID_WCID].HTPhyMode.field.
2294 			     MODE <= MODE_OFDM))
2295 				RTMPSetDesiredRates(pAd, rate);
2296 			else {
2297 				pAd->StaCfg.DesiredTransmitSetting.field.MCS =
2298 				    MCS_AUTO;
2299 				SetCommonHT(pAd);
2300 			}
2301 			DBGPRINT(RT_DEBUG_TRACE,
2302 				 ("rt_ioctl_siwrate::(HtMcs=%d)\n",
2303 				  pAd->StaCfg.DesiredTransmitSetting.field.
2304 				  MCS));
2305 		} else {
2306 			/* TODO: rate = X, fixed = 0 => (rates <= X) */
2307 			return -EOPNOTSUPP;
2308 		}
2309 	}
2310 
2311 	return 0;
2312 }
2313 
rt_ioctl_giwrate(struct net_device * dev,struct iw_request_info * info,union iwreq_data * wrqu,char * extra)2314 int rt_ioctl_giwrate(struct net_device *dev,
2315 		     struct iw_request_info *info,
2316 		     union iwreq_data *wrqu, char *extra)
2317 {
2318 	struct rt_rtmp_adapter *pAd = NULL;
2319 	int rate_index = 0, rate_count = 0;
2320 	HTTRANSMIT_SETTING ht_setting;
2321 /* Remove to global variable
2322     __s32 ralinkrate[] =
2323 	{2,  4,   11,  22, // CCK
2324 	12, 18,   24,  36, 48, 72, 96, 108, // OFDM
2325 	13, 26,   39,  52,  78, 104, 117, 130, 26,  52,  78, 104, 156, 208, 234, 260, // 20MHz, 800ns GI, MCS: 0 ~ 15
2326 	39, 78,  117, 156, 234, 312, 351, 390,										  // 20MHz, 800ns GI, MCS: 16 ~ 23
2327 	27, 54,   81, 108, 162, 216, 243, 270, 54, 108, 162, 216, 324, 432, 486, 540, // 40MHz, 800ns GI, MCS: 0 ~ 15
2328 	81, 162, 243, 324, 486, 648, 729, 810,										  // 40MHz, 800ns GI, MCS: 16 ~ 23
2329 	14, 29,   43,  57,  87, 115, 130, 144, 29, 59,   87, 115, 173, 230, 260, 288, // 20MHz, 400ns GI, MCS: 0 ~ 15
2330 	43, 87,  130, 173, 260, 317, 390, 433,										  // 20MHz, 400ns GI, MCS: 16 ~ 23
2331 	30, 60,   90, 120, 180, 240, 270, 300, 60, 120, 180, 240, 360, 480, 540, 600, // 40MHz, 400ns GI, MCS: 0 ~ 15
2332 	90, 180, 270, 360, 540, 720, 810, 900};										  // 40MHz, 400ns GI, MCS: 16 ~ 23
2333 */
2334 	GET_PAD_FROM_NET_DEV(pAd, dev);
2335 
2336 	rate_count = ARRAY_SIZE(ralinkrate);
2337 	/*check if the interface is down */
2338 	if (!RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_INTERRUPT_IN_USE)) {
2339 		DBGPRINT(RT_DEBUG_TRACE, ("INFO::Network is down!\n"));
2340 		return -ENETDOWN;
2341 	}
2342 
2343 	if ((pAd->StaCfg.bAutoTxRateSwitch == FALSE) &&
2344 	    (INFRA_ON(pAd)) &&
2345 	    ((pAd->CommonCfg.PhyMode <= PHY_11G)
2346 	     || (pAd->MacTab.Content[BSSID_WCID].HTPhyMode.field.MODE <=
2347 		 MODE_OFDM)))
2348 		ht_setting.word = pAd->StaCfg.HTPhyMode.word;
2349 	else
2350 		ht_setting.word =
2351 		    pAd->MacTab.Content[BSSID_WCID].HTPhyMode.word;
2352 
2353 	if (ht_setting.field.MODE >= MODE_HTMIX) {
2354 /*      rate_index = 12 + ((u8)ht_setting.field.BW *16) + ((u8)ht_setting.field.ShortGI *32) + ((u8)ht_setting.field.MCS); */
2355 		rate_index =
2356 		    12 + ((u8)ht_setting.field.BW * 24) +
2357 		    ((u8)ht_setting.field.ShortGI * 48) +
2358 		    ((u8)ht_setting.field.MCS);
2359 	} else if (ht_setting.field.MODE == MODE_OFDM)
2360 		rate_index = (u8)(ht_setting.field.MCS) + 4;
2361 	else if (ht_setting.field.MODE == MODE_CCK)
2362 		rate_index = (u8)(ht_setting.field.MCS);
2363 
2364 	if (rate_index < 0)
2365 		rate_index = 0;
2366 
2367 	if (rate_index >= rate_count)
2368 		rate_index = rate_count - 1;
2369 
2370 	wrqu->bitrate.value = ralinkrate[rate_index] * 500000;
2371 	wrqu->bitrate.disabled = 0;
2372 
2373 	return 0;
2374 }
2375 
2376 static const iw_handler rt_handler[] = {
2377 	(iw_handler) NULL,	/* SIOCSIWCOMMIT */
2378 	(iw_handler) rt_ioctl_giwname,	/* SIOCGIWNAME   */
2379 	(iw_handler) NULL,	/* SIOCSIWNWID   */
2380 	(iw_handler) NULL,	/* SIOCGIWNWID   */
2381 	(iw_handler) rt_ioctl_siwfreq,	/* SIOCSIWFREQ   */
2382 	(iw_handler) rt_ioctl_giwfreq,	/* SIOCGIWFREQ   */
2383 	(iw_handler) rt_ioctl_siwmode,	/* SIOCSIWMODE   */
2384 	(iw_handler) rt_ioctl_giwmode,	/* SIOCGIWMODE   */
2385 	(iw_handler) NULL,	/* SIOCSIWSENS   */
2386 	(iw_handler) NULL,	/* SIOCGIWSENS   */
2387 	(iw_handler) NULL /* not used */ ,	/* SIOCSIWRANGE  */
2388 	(iw_handler) rt_ioctl_giwrange,	/* SIOCGIWRANGE  */
2389 	(iw_handler) NULL /* not used */ ,	/* SIOCSIWPRIV   */
2390 	(iw_handler) NULL /* kernel code */ ,	/* SIOCGIWPRIV   */
2391 	(iw_handler) NULL /* not used */ ,	/* SIOCSIWSTATS  */
2392 	(iw_handler) rt28xx_get_wireless_stats /* kernel code */ ,	/* SIOCGIWSTATS  */
2393 	(iw_handler) NULL,	/* SIOCSIWSPY    */
2394 	(iw_handler) NULL,	/* SIOCGIWSPY    */
2395 	(iw_handler) NULL,	/* SIOCSIWTHRSPY */
2396 	(iw_handler) NULL,	/* SIOCGIWTHRSPY */
2397 	(iw_handler) rt_ioctl_siwap,	/* SIOCSIWAP     */
2398 	(iw_handler) rt_ioctl_giwap,	/* SIOCGIWAP     */
2399 	(iw_handler) rt_ioctl_siwmlme,	/* SIOCSIWMLME   */
2400 	(iw_handler) rt_ioctl_iwaplist,	/* SIOCGIWAPLIST */
2401 	(iw_handler) rt_ioctl_siwscan,	/* SIOCSIWSCAN   */
2402 	(iw_handler) rt_ioctl_giwscan,	/* SIOCGIWSCAN   */
2403 	(iw_handler) rt_ioctl_siwessid,	/* SIOCSIWESSID  */
2404 	(iw_handler) rt_ioctl_giwessid,	/* SIOCGIWESSID  */
2405 	(iw_handler) rt_ioctl_siwnickn,	/* SIOCSIWNICKN  */
2406 	(iw_handler) rt_ioctl_giwnickn,	/* SIOCGIWNICKN  */
2407 	(iw_handler) NULL,	/* -- hole --    */
2408 	(iw_handler) NULL,	/* -- hole --    */
2409 	(iw_handler) rt_ioctl_siwrate,	/* SIOCSIWRATE   */
2410 	(iw_handler) rt_ioctl_giwrate,	/* SIOCGIWRATE   */
2411 	(iw_handler) rt_ioctl_siwrts,	/* SIOCSIWRTS    */
2412 	(iw_handler) rt_ioctl_giwrts,	/* SIOCGIWRTS    */
2413 	(iw_handler) rt_ioctl_siwfrag,	/* SIOCSIWFRAG   */
2414 	(iw_handler) rt_ioctl_giwfrag,	/* SIOCGIWFRAG   */
2415 	(iw_handler) NULL,	/* SIOCSIWTXPOW  */
2416 	(iw_handler) NULL,	/* SIOCGIWTXPOW  */
2417 	(iw_handler) NULL,	/* SIOCSIWRETRY  */
2418 	(iw_handler) NULL,	/* SIOCGIWRETRY  */
2419 	(iw_handler) rt_ioctl_siwencode,	/* SIOCSIWENCODE */
2420 	(iw_handler) rt_ioctl_giwencode,	/* SIOCGIWENCODE */
2421 	(iw_handler) NULL,	/* SIOCSIWPOWER  */
2422 	(iw_handler) NULL,	/* SIOCGIWPOWER  */
2423 	(iw_handler) NULL,	/* -- hole -- */
2424 	(iw_handler) NULL,	/* -- hole -- */
2425 	(iw_handler) rt_ioctl_siwgenie,	/* SIOCSIWGENIE  */
2426 	(iw_handler) rt_ioctl_giwgenie,	/* SIOCGIWGENIE  */
2427 	(iw_handler) rt_ioctl_siwauth,	/* SIOCSIWAUTH   */
2428 	(iw_handler) rt_ioctl_giwauth,	/* SIOCGIWAUTH   */
2429 	(iw_handler) rt_ioctl_siwencodeext,	/* SIOCSIWENCODEEXT */
2430 	(iw_handler) rt_ioctl_giwencodeext,	/* SIOCGIWENCODEEXT */
2431 	(iw_handler) rt_ioctl_siwpmksa,	/* SIOCSIWPMKSA  */
2432 };
2433 
2434 const struct iw_handler_def rt28xx_iw_handler_def = {
2435 	.standard = (iw_handler *) rt_handler,
2436 	.num_standard = sizeof(rt_handler) / sizeof(iw_handler),
2437 #if IW_HANDLER_VERSION >= 7
2438 	.get_wireless_stats = rt28xx_get_wireless_stats,
2439 #endif
2440 };
2441 
rt28xx_sta_ioctl(IN struct net_device * net_dev,IN OUT struct ifreq * rq,int cmd)2442 int rt28xx_sta_ioctl(IN struct net_device *net_dev,
2443 		     IN OUT struct ifreq *rq, int cmd)
2444 {
2445 	struct os_cookie *pObj;
2446 	struct rt_rtmp_adapter *pAd = NULL;
2447 	struct iwreq *wrq = (struct iwreq *)rq;
2448 	BOOLEAN StateMachineTouched = FALSE;
2449 	int Status = NDIS_STATUS_SUCCESS;
2450 
2451 	GET_PAD_FROM_NET_DEV(pAd, net_dev);
2452 
2453 	pObj = (struct os_cookie *)pAd->OS_Cookie;
2454 
2455 	/*check if the interface is down */
2456 	if (!RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_INTERRUPT_IN_USE)) {
2457 		{
2458 			DBGPRINT(RT_DEBUG_TRACE, ("INFO::Network is down!\n"));
2459 			return -ENETDOWN;
2460 		}
2461 	}
2462 
2463 	{			/* determine this ioctl command is coming from which interface. */
2464 		pObj->ioctl_if_type = INT_MAIN;
2465 		pObj->ioctl_if = MAIN_MBSSID;
2466 	}
2467 
2468 	switch (cmd) {
2469 	case SIOCGIFHWADDR:
2470 		DBGPRINT(RT_DEBUG_TRACE, ("IOCTL::SIOCGIFHWADDR\n"));
2471 		memcpy(wrq->u.name, pAd->CurrentAddress, ETH_ALEN);
2472 		break;
2473 	case SIOCGIWNAME:
2474 		{
2475 			char *name = &wrq->u.name[0];
2476 			rt_ioctl_giwname(net_dev, NULL, name, NULL);
2477 			break;
2478 		}
2479 	case SIOCGIWESSID:	/*Get ESSID */
2480 		{
2481 			struct iw_point *essid = &wrq->u.essid;
2482 			rt_ioctl_giwessid(net_dev, NULL, essid, essid->pointer);
2483 			break;
2484 		}
2485 	case SIOCSIWESSID:	/*Set ESSID */
2486 		{
2487 			struct iw_point *essid = &wrq->u.essid;
2488 			rt_ioctl_siwessid(net_dev, NULL, essid, essid->pointer);
2489 			break;
2490 		}
2491 	case SIOCSIWNWID:	/* set network id (the cell) */
2492 	case SIOCGIWNWID:	/* get network id */
2493 		Status = -EOPNOTSUPP;
2494 		break;
2495 	case SIOCSIWFREQ:	/*set channel/frequency (Hz) */
2496 		{
2497 			struct iw_freq *freq = &wrq->u.freq;
2498 			rt_ioctl_siwfreq(net_dev, NULL, freq, NULL);
2499 			break;
2500 		}
2501 	case SIOCGIWFREQ:	/* get channel/frequency (Hz) */
2502 		{
2503 			struct iw_freq *freq = &wrq->u.freq;
2504 			rt_ioctl_giwfreq(net_dev, NULL, freq, NULL);
2505 			break;
2506 		}
2507 	case SIOCSIWNICKN:	/*set node name/nickname */
2508 		{
2509 			/*struct iw_point *data=&wrq->u.data; */
2510 			/*rt_ioctl_siwnickn(net_dev, NULL, data, NULL); */
2511 			break;
2512 		}
2513 	case SIOCGIWNICKN:	/*get node name/nickname */
2514 		{
2515 			struct iw_point *erq = NULL;
2516 			erq = &wrq->u.data;
2517 			erq->length = strlen((char *)pAd->nickname);
2518 			Status =
2519 			    copy_to_user(erq->pointer, pAd->nickname,
2520 					 erq->length);
2521 			if (Status)
2522 				Status = -EFAULT;
2523 			break;
2524 		}
2525 	case SIOCGIWRATE:	/*get default bit rate (bps) */
2526 		rt_ioctl_giwrate(net_dev, NULL, &wrq->u, NULL);
2527 		break;
2528 	case SIOCSIWRATE:	/*set default bit rate (bps) */
2529 		rt_ioctl_siwrate(net_dev, NULL, &wrq->u, NULL);
2530 		break;
2531 	case SIOCGIWRTS:	/* get RTS/CTS threshold (bytes) */
2532 		{
2533 			struct iw_param *rts = &wrq->u.rts;
2534 			rt_ioctl_giwrts(net_dev, NULL, rts, NULL);
2535 			break;
2536 		}
2537 	case SIOCSIWRTS:	/*set RTS/CTS threshold (bytes) */
2538 		{
2539 			struct iw_param *rts = &wrq->u.rts;
2540 			rt_ioctl_siwrts(net_dev, NULL, rts, NULL);
2541 			break;
2542 		}
2543 	case SIOCGIWFRAG:	/*get fragmentation thr (bytes) */
2544 		{
2545 			struct iw_param *frag = &wrq->u.frag;
2546 			rt_ioctl_giwfrag(net_dev, NULL, frag, NULL);
2547 			break;
2548 		}
2549 	case SIOCSIWFRAG:	/*set fragmentation thr (bytes) */
2550 		{
2551 			struct iw_param *frag = &wrq->u.frag;
2552 			rt_ioctl_siwfrag(net_dev, NULL, frag, NULL);
2553 			break;
2554 		}
2555 	case SIOCGIWENCODE:	/*get encoding token & mode */
2556 		{
2557 			struct iw_point *erq = &wrq->u.encoding;
2558 			if (erq)
2559 				rt_ioctl_giwencode(net_dev, NULL, erq,
2560 						   erq->pointer);
2561 			break;
2562 		}
2563 	case SIOCSIWENCODE:	/*set encoding token & mode */
2564 		{
2565 			struct iw_point *erq = &wrq->u.encoding;
2566 			if (erq)
2567 				rt_ioctl_siwencode(net_dev, NULL, erq,
2568 						   erq->pointer);
2569 			break;
2570 		}
2571 	case SIOCGIWAP:	/*get access point MAC addresses */
2572 		{
2573 			struct sockaddr *ap_addr = &wrq->u.ap_addr;
2574 			rt_ioctl_giwap(net_dev, NULL, ap_addr,
2575 				       ap_addr->sa_data);
2576 			break;
2577 		}
2578 	case SIOCSIWAP:	/*set access point MAC addresses */
2579 		{
2580 			struct sockaddr *ap_addr = &wrq->u.ap_addr;
2581 			rt_ioctl_siwap(net_dev, NULL, ap_addr,
2582 				       ap_addr->sa_data);
2583 			break;
2584 		}
2585 	case SIOCGIWMODE:	/*get operation mode */
2586 		{
2587 			__u32 *mode = &wrq->u.mode;
2588 			rt_ioctl_giwmode(net_dev, NULL, mode, NULL);
2589 			break;
2590 		}
2591 	case SIOCSIWMODE:	/*set operation mode */
2592 		{
2593 			__u32 *mode = &wrq->u.mode;
2594 			rt_ioctl_siwmode(net_dev, NULL, mode, NULL);
2595 			break;
2596 		}
2597 	case SIOCGIWSENS:	/*get sensitivity (dBm) */
2598 	case SIOCSIWSENS:	/*set sensitivity (dBm) */
2599 	case SIOCGIWPOWER:	/*get Power Management settings */
2600 	case SIOCSIWPOWER:	/*set Power Management settings */
2601 	case SIOCGIWTXPOW:	/*get transmit power (dBm) */
2602 	case SIOCSIWTXPOW:	/*set transmit power (dBm) */
2603 	case SIOCGIWRANGE:	/*Get range of parameters */
2604 	case SIOCGIWRETRY:	/*get retry limits and lifetime */
2605 	case SIOCSIWRETRY:	/*set retry limits and lifetime */
2606 	case RT_PRIV_IOCTL:
2607 	case RT_PRIV_IOCTL_EXT:
2608 	case RTPRIV_IOCTL_SET:
2609 	case RTPRIV_IOCTL_GSITESURVEY:
2610 	case SIOCGIWPRIV:
2611 		Status = -EOPNOTSUPP;
2612 		break;
2613 	case SIOCETHTOOL:
2614 		break;
2615 	default:
2616 		DBGPRINT(RT_DEBUG_ERROR,
2617 			 ("IOCTL::unknown IOCTL's cmd = 0x%08x\n", cmd));
2618 		Status = -EOPNOTSUPP;
2619 		break;
2620 	}
2621 
2622 	if (StateMachineTouched)	/* Upper layer sent a MLME-related operations */
2623 		RTMP_MLME_HANDLER(pAd);
2624 
2625 	return Status;
2626 }
2627 
2628 /*
2629     ==========================================================================
2630     Description:
2631         Set SSID
2632     Return:
2633         TRUE if all parameters are OK, FALSE otherwise
2634     ==========================================================================
2635 */
Set_SSID_Proc(struct rt_rtmp_adapter * pAdapter,char * arg)2636 int Set_SSID_Proc(struct rt_rtmp_adapter *pAdapter, char *arg)
2637 {
2638 	struct rt_ndis_802_11_ssid Ssid, *pSsid = NULL;
2639 	BOOLEAN StateMachineTouched = FALSE;
2640 	int success = TRUE;
2641 
2642 	if (strlen(arg) <= MAX_LEN_OF_SSID) {
2643 		NdisZeroMemory(&Ssid, sizeof(struct rt_ndis_802_11_ssid));
2644 		if (strlen(arg) != 0) {
2645 			NdisMoveMemory(Ssid.Ssid, arg, strlen(arg));
2646 			Ssid.SsidLength = strlen(arg);
2647 		} else		/*ANY ssid */
2648 		{
2649 			Ssid.SsidLength = 0;
2650 			memcpy(Ssid.Ssid, "", 0);
2651 			pAdapter->StaCfg.BssType = BSS_INFRA;
2652 			pAdapter->StaCfg.AuthMode = Ndis802_11AuthModeOpen;
2653 			pAdapter->StaCfg.WepStatus =
2654 			    Ndis802_11EncryptionDisabled;
2655 		}
2656 		pSsid = &Ssid;
2657 
2658 		if (pAdapter->Mlme.CntlMachine.CurrState != CNTL_IDLE) {
2659 			RTMP_MLME_RESET_STATE_MACHINE(pAdapter);
2660 			DBGPRINT(RT_DEBUG_TRACE,
2661 				 ("MLME busy, reset MLME state machine!\n"));
2662 		}
2663 
2664 		if ((pAdapter->StaCfg.WpaPassPhraseLen >= 8) &&
2665 		    (pAdapter->StaCfg.WpaPassPhraseLen <= 64)) {
2666 			char passphrase_str[65] = { 0 };
2667 			u8 keyMaterial[40];
2668 
2669 			RTMPMoveMemory(passphrase_str,
2670 				       pAdapter->StaCfg.WpaPassPhrase,
2671 				       pAdapter->StaCfg.WpaPassPhraseLen);
2672 			RTMPZeroMemory(pAdapter->StaCfg.PMK, 32);
2673 			if (pAdapter->StaCfg.WpaPassPhraseLen == 64) {
2674 				AtoH((char *)pAdapter->StaCfg.WpaPassPhrase,
2675 				     pAdapter->StaCfg.PMK, 32);
2676 			} else {
2677 				PasswordHash((char *)pAdapter->StaCfg.
2678 					     WpaPassPhrase, Ssid.Ssid,
2679 					     Ssid.SsidLength, keyMaterial);
2680 				NdisMoveMemory(pAdapter->StaCfg.PMK,
2681 					       keyMaterial, 32);
2682 			}
2683 		}
2684 
2685 		pAdapter->MlmeAux.CurrReqIsFromNdis = TRUE;
2686 		pAdapter->StaCfg.bScanReqIsFromWebUI = FALSE;
2687 		pAdapter->bConfigChanged = TRUE;
2688 
2689 		MlmeEnqueue(pAdapter,
2690 			    MLME_CNTL_STATE_MACHINE,
2691 			    OID_802_11_SSID,
2692 			    sizeof(struct rt_ndis_802_11_ssid), (void *) pSsid);
2693 
2694 		StateMachineTouched = TRUE;
2695 		DBGPRINT(RT_DEBUG_TRACE,
2696 			 ("Set_SSID_Proc::(Len=%d,Ssid=%s)\n", Ssid.SsidLength,
2697 			  Ssid.Ssid));
2698 	} else
2699 		success = FALSE;
2700 
2701 	if (StateMachineTouched)	/* Upper layer sent a MLME-related operations */
2702 		RTMP_MLME_HANDLER(pAdapter);
2703 
2704 	return success;
2705 }
2706 
2707 /*
2708     ==========================================================================
2709     Description:
2710         Set Network Type(Infrastructure/Adhoc mode)
2711     Return:
2712         TRUE if all parameters are OK, FALSE otherwise
2713     ==========================================================================
2714 */
Set_NetworkType_Proc(struct rt_rtmp_adapter * pAdapter,char * arg)2715 int Set_NetworkType_Proc(struct rt_rtmp_adapter *pAdapter, char *arg)
2716 {
2717 	u32 Value = 0;
2718 
2719 	if (strcmp(arg, "Adhoc") == 0) {
2720 		if (pAdapter->StaCfg.BssType != BSS_ADHOC) {
2721 			/* Config has changed */
2722 			pAdapter->bConfigChanged = TRUE;
2723 			if (MONITOR_ON(pAdapter)) {
2724 				RTMP_IO_WRITE32(pAdapter, RX_FILTR_CFG,
2725 						STANORMAL);
2726 				RTMP_IO_READ32(pAdapter, MAC_SYS_CTRL, &Value);
2727 				Value &= (~0x80);
2728 				RTMP_IO_WRITE32(pAdapter, MAC_SYS_CTRL, Value);
2729 				OPSTATUS_CLEAR_FLAG(pAdapter,
2730 						    fOP_STATUS_MEDIA_STATE_CONNECTED);
2731 				pAdapter->StaCfg.bAutoReconnect = TRUE;
2732 				LinkDown(pAdapter, FALSE);
2733 			}
2734 			if (INFRA_ON(pAdapter)) {
2735 				/*BOOLEAN Cancelled; */
2736 				/* Set the AutoReconnectSsid to prevent it from reconnecting to the old SSID */
2737 				/* Since calling this indicates users don't want to connect to that SSID anymore. */
2738 				pAdapter->MlmeAux.AutoReconnectSsidLen = 32;
2739 				NdisZeroMemory(pAdapter->MlmeAux.
2740 					       AutoReconnectSsid,
2741 					       pAdapter->MlmeAux.
2742 					       AutoReconnectSsidLen);
2743 
2744 				LinkDown(pAdapter, FALSE);
2745 
2746 				DBGPRINT(RT_DEBUG_TRACE,
2747 					 ("NDIS_STATUS_MEDIA_DISCONNECT Event BB!\n"));
2748 			}
2749 		}
2750 		pAdapter->StaCfg.BssType = BSS_ADHOC;
2751 		pAdapter->net_dev->type = pAdapter->StaCfg.OriDevType;
2752 		DBGPRINT(RT_DEBUG_TRACE,
2753 			 ("===>Set_NetworkType_Proc::(AD-HOC)\n"));
2754 	} else if (strcmp(arg, "Infra") == 0) {
2755 		if (pAdapter->StaCfg.BssType != BSS_INFRA) {
2756 			/* Config has changed */
2757 			pAdapter->bConfigChanged = TRUE;
2758 			if (MONITOR_ON(pAdapter)) {
2759 				RTMP_IO_WRITE32(pAdapter, RX_FILTR_CFG,
2760 						STANORMAL);
2761 				RTMP_IO_READ32(pAdapter, MAC_SYS_CTRL, &Value);
2762 				Value &= (~0x80);
2763 				RTMP_IO_WRITE32(pAdapter, MAC_SYS_CTRL, Value);
2764 				OPSTATUS_CLEAR_FLAG(pAdapter,
2765 						    fOP_STATUS_MEDIA_STATE_CONNECTED);
2766 				pAdapter->StaCfg.bAutoReconnect = TRUE;
2767 				LinkDown(pAdapter, FALSE);
2768 			}
2769 			if (ADHOC_ON(pAdapter)) {
2770 				/* Set the AutoReconnectSsid to prevent it from reconnecting to the old SSID */
2771 				/* Since calling this indicates users don't want to connect to that SSID anymore. */
2772 				pAdapter->MlmeAux.AutoReconnectSsidLen = 32;
2773 				NdisZeroMemory(pAdapter->MlmeAux.
2774 					       AutoReconnectSsid,
2775 					       pAdapter->MlmeAux.
2776 					       AutoReconnectSsidLen);
2777 
2778 				LinkDown(pAdapter, FALSE);
2779 			}
2780 		}
2781 		pAdapter->StaCfg.BssType = BSS_INFRA;
2782 		pAdapter->net_dev->type = pAdapter->StaCfg.OriDevType;
2783 		DBGPRINT(RT_DEBUG_TRACE,
2784 			 ("===>Set_NetworkType_Proc::(INFRA)\n"));
2785 	} else if (strcmp(arg, "Monitor") == 0) {
2786 		u8 bbpValue = 0;
2787 		BCN_TIME_CFG_STRUC csr;
2788 		OPSTATUS_CLEAR_FLAG(pAdapter, fOP_STATUS_INFRA_ON);
2789 		OPSTATUS_CLEAR_FLAG(pAdapter, fOP_STATUS_ADHOC_ON);
2790 		OPSTATUS_SET_FLAG(pAdapter, fOP_STATUS_MEDIA_STATE_CONNECTED);
2791 		/* disable all periodic state machine */
2792 		pAdapter->StaCfg.bAutoReconnect = FALSE;
2793 		/* reset all mlme state machine */
2794 		RTMP_MLME_RESET_STATE_MACHINE(pAdapter);
2795 		DBGPRINT(RT_DEBUG_TRACE,
2796 			 ("fOP_STATUS_MEDIA_STATE_CONNECTED \n"));
2797 		if (pAdapter->CommonCfg.CentralChannel == 0) {
2798 			if (pAdapter->CommonCfg.PhyMode == PHY_11AN_MIXED)
2799 				pAdapter->CommonCfg.CentralChannel = 36;
2800 			else
2801 				pAdapter->CommonCfg.CentralChannel = 6;
2802 		} else
2803 			N_ChannelCheck(pAdapter);
2804 
2805 		if (pAdapter->CommonCfg.PhyMode >= PHY_11ABGN_MIXED &&
2806 		    pAdapter->CommonCfg.RegTransmitSetting.field.BW == BW_40 &&
2807 		    pAdapter->CommonCfg.RegTransmitSetting.field.EXTCHA ==
2808 		    EXTCHA_ABOVE) {
2809 			/* 40MHz ,control channel at lower */
2810 			RTMP_BBP_IO_READ8_BY_REG_ID(pAdapter, BBP_R4,
2811 						    &bbpValue);
2812 			bbpValue &= (~0x18);
2813 			bbpValue |= 0x10;
2814 			RTMP_BBP_IO_WRITE8_BY_REG_ID(pAdapter, BBP_R4,
2815 						     bbpValue);
2816 			pAdapter->CommonCfg.BBPCurrentBW = BW_40;
2817 			/*  RX : control channel at lower */
2818 			RTMP_BBP_IO_READ8_BY_REG_ID(pAdapter, BBP_R3,
2819 						    &bbpValue);
2820 			bbpValue &= (~0x20);
2821 			RTMP_BBP_IO_WRITE8_BY_REG_ID(pAdapter, BBP_R3,
2822 						     bbpValue);
2823 
2824 			RTMP_IO_READ32(pAdapter, TX_BAND_CFG, &Value);
2825 			Value &= 0xfffffffe;
2826 			RTMP_IO_WRITE32(pAdapter, TX_BAND_CFG, Value);
2827 			pAdapter->CommonCfg.CentralChannel =
2828 			    pAdapter->CommonCfg.Channel + 2;
2829 			AsicSwitchChannel(pAdapter,
2830 					  pAdapter->CommonCfg.CentralChannel,
2831 					  FALSE);
2832 			AsicLockChannel(pAdapter,
2833 					pAdapter->CommonCfg.CentralChannel);
2834 			DBGPRINT(RT_DEBUG_TRACE,
2835 				 ("BW_40 ,control_channel(%d), CentralChannel(%d) \n",
2836 				  pAdapter->CommonCfg.Channel,
2837 				  pAdapter->CommonCfg.CentralChannel));
2838 		} else if (pAdapter->CommonCfg.PhyMode >= PHY_11ABGN_MIXED
2839 			   && pAdapter->CommonCfg.RegTransmitSetting.field.BW ==
2840 			   BW_40
2841 			   && pAdapter->CommonCfg.RegTransmitSetting.field.
2842 			   EXTCHA == EXTCHA_BELOW) {
2843 			/* 40MHz ,control channel at upper */
2844 			RTMP_BBP_IO_READ8_BY_REG_ID(pAdapter, BBP_R4,
2845 						    &bbpValue);
2846 			bbpValue &= (~0x18);
2847 			bbpValue |= 0x10;
2848 			RTMP_BBP_IO_WRITE8_BY_REG_ID(pAdapter, BBP_R4,
2849 						     bbpValue);
2850 			pAdapter->CommonCfg.BBPCurrentBW = BW_40;
2851 			RTMP_IO_READ32(pAdapter, TX_BAND_CFG, &Value);
2852 			Value |= 0x1;
2853 			RTMP_IO_WRITE32(pAdapter, TX_BAND_CFG, Value);
2854 
2855 			RTMP_BBP_IO_READ8_BY_REG_ID(pAdapter, BBP_R3,
2856 						    &bbpValue);
2857 			bbpValue |= (0x20);
2858 			RTMP_BBP_IO_WRITE8_BY_REG_ID(pAdapter, BBP_R3,
2859 						     bbpValue);
2860 			pAdapter->CommonCfg.CentralChannel =
2861 			    pAdapter->CommonCfg.Channel - 2;
2862 			AsicSwitchChannel(pAdapter,
2863 					  pAdapter->CommonCfg.CentralChannel,
2864 					  FALSE);
2865 			AsicLockChannel(pAdapter,
2866 					pAdapter->CommonCfg.CentralChannel);
2867 			DBGPRINT(RT_DEBUG_TRACE,
2868 				 ("BW_40 ,control_channel(%d), CentralChannel(%d) \n",
2869 				  pAdapter->CommonCfg.Channel,
2870 				  pAdapter->CommonCfg.CentralChannel));
2871 		} else {
2872 			/* 20MHz */
2873 			RTMP_BBP_IO_READ8_BY_REG_ID(pAdapter, BBP_R4,
2874 						    &bbpValue);
2875 			bbpValue &= (~0x18);
2876 			RTMP_BBP_IO_WRITE8_BY_REG_ID(pAdapter, BBP_R4,
2877 						     bbpValue);
2878 			pAdapter->CommonCfg.BBPCurrentBW = BW_20;
2879 			AsicSwitchChannel(pAdapter, pAdapter->CommonCfg.Channel,
2880 					  FALSE);
2881 			AsicLockChannel(pAdapter, pAdapter->CommonCfg.Channel);
2882 			DBGPRINT(RT_DEBUG_TRACE,
2883 				 ("BW_20, Channel(%d)\n",
2884 				  pAdapter->CommonCfg.Channel));
2885 		}
2886 		/* Enable Rx with promiscuous reception */
2887 		RTMP_IO_WRITE32(pAdapter, RX_FILTR_CFG, 0x3);
2888 		/* ASIC supports sniffer function with replacing RSSI with timestamp. */
2889 		/*RTMP_IO_READ32(pAdapter, MAC_SYS_CTRL, &Value); */
2890 		/*Value |= (0x80); */
2891 		/*RTMP_IO_WRITE32(pAdapter, MAC_SYS_CTRL, Value); */
2892 		/* disable sync */
2893 		RTMP_IO_READ32(pAdapter, BCN_TIME_CFG, &csr.word);
2894 		csr.field.bBeaconGen = 0;
2895 		csr.field.bTBTTEnable = 0;
2896 		csr.field.TsfSyncMode = 0;
2897 		RTMP_IO_WRITE32(pAdapter, BCN_TIME_CFG, csr.word);
2898 
2899 		pAdapter->StaCfg.BssType = BSS_MONITOR;
2900 		pAdapter->net_dev->type = ARPHRD_IEEE80211_PRISM;	/*ARPHRD_IEEE80211; // IEEE80211 */
2901 		DBGPRINT(RT_DEBUG_TRACE,
2902 			 ("===>Set_NetworkType_Proc::(MONITOR)\n"));
2903 	}
2904 	/* Reset Ralink supplicant to not use, it will be set to start when UI set PMK key */
2905 	pAdapter->StaCfg.WpaState = SS_NOTUSE;
2906 
2907 	DBGPRINT(RT_DEBUG_TRACE,
2908 		 ("Set_NetworkType_Proc::(NetworkType=%d)\n",
2909 		  pAdapter->StaCfg.BssType));
2910 
2911 	return TRUE;
2912 }
2913