Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux
1
fork

Configure Feed

Select the types of activity you want to include in your feed.

at v3.13-rc8 2141 lines 61 kB view raw
1/* 2 * Copyright (c) 1996, 2003 VIA Networking Technologies, Inc. 3 * All rights reserved. 4 * 5 * This program is free software; you can redistribute it and/or modify 6 * it under the terms of the GNU General Public License as published by 7 * the Free Software Foundation; either version 2 of the License, or 8 * (at your option) any later version. 9 * 10 * This program is distributed in the hope that it will be useful, 11 * but WITHOUT ANY WARRANTY; without even the implied warranty of 12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 13 * GNU General Public License for more details. 14 * 15 * You should have received a copy of the GNU General Public License along 16 * with this program; if not, write to the Free Software Foundation, Inc., 17 * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA. 18 * 19 * File: iwctl.c 20 * 21 * Purpose: wireless ext & ioctl functions 22 * 23 * Author: Lyndon Chen 24 * 25 * Date: July 5, 2006 26 * 27 * Functions: 28 * 29 * Revision History: 30 * 31 */ 32 33#include "device.h" 34#include "ioctl.h" 35#include "iocmd.h" 36#include "mac.h" 37#include "card.h" 38#include "hostap.h" 39#include "power.h" 40#include "rf.h" 41 42#ifdef WPA_SUPPLICANT_DRIVER_WEXT_SUPPORT 43#include "iowpa.h" 44#include "wpactl.h" 45#endif 46 47#include <net/iw_handler.h> 48extern unsigned short TxRate_iwconfig;//2008-5-8 <add> by chester 49 50/*--------------------- Static Definitions -------------------------*/ 51 52//2008-0409-07, <Add> by Einsn Liu 53#ifdef WPA_SUPPLICANT_DRIVER_WEXT_SUPPORT 54#define SUPPORTED_WIRELESS_EXT 18 55#else 56#define SUPPORTED_WIRELESS_EXT 17 57#endif 58 59static const long frequency_list[] = { 60 2412, 2417, 2422, 2427, 2432, 2437, 2442, 2447, 2452, 2457, 2462, 2467, 2472, 2484, 61 4915, 4920, 4925, 4935, 4940, 4945, 4960, 4980, 62 5035, 5040, 5045, 5055, 5060, 5080, 5170, 5180, 5190, 5200, 5210, 5220, 5230, 5240, 63 5260, 5280, 5300, 5320, 5500, 5520, 5540, 5560, 5580, 5600, 5620, 5640, 5660, 5680, 64 5700, 5745, 5765, 5785, 5805, 5825 65}; 66 67/*--------------------- Static Classes ----------------------------*/ 68 69//static int msglevel =MSG_LEVEL_DEBUG; 70static int msglevel = MSG_LEVEL_INFO; 71 72/*--------------------- Static Variables --------------------------*/ 73/*--------------------- Static Functions --------------------------*/ 74 75/*--------------------- Export Variables --------------------------*/ 76 77struct iw_statistics *iwctl_get_wireless_stats(struct net_device *dev) 78{ 79 PSDevice pDevice = netdev_priv(dev); 80 long ldBm; 81 82 pDevice->wstats.status = pDevice->eOPMode; 83#ifdef Calcu_LinkQual 84 if (pDevice->scStatistic.LinkQuality > 100) 85 pDevice->scStatistic.LinkQuality = 100; 86 pDevice->wstats.qual.qual = (unsigned char)pDevice->scStatistic.LinkQuality; 87#else 88 pDevice->wstats.qual.qual = pDevice->byCurrSQ; 89#endif 90 RFvRSSITodBm(pDevice, (unsigned char)(pDevice->uCurrRSSI), &ldBm); 91 pDevice->wstats.qual.level = ldBm; 92 //pDevice->wstats.qual.level = 0x100 - pDevice->uCurrRSSI; 93 pDevice->wstats.qual.noise = 0; 94 pDevice->wstats.qual.updated = 1; 95 pDevice->wstats.discard.nwid = 0; 96 pDevice->wstats.discard.code = 0; 97 pDevice->wstats.discard.fragment = 0; 98 pDevice->wstats.discard.retries = (unsigned long)pDevice->scStatistic.dwTsrErr; 99 pDevice->wstats.discard.misc = 0; 100 pDevice->wstats.miss.beacon = 0; 101 102 return &pDevice->wstats; 103} 104 105/*------------------------------------------------------------------*/ 106 107static int iwctl_commit(struct net_device *dev, 108 struct iw_request_info *info, 109 void *wrq, 110 char *extra) 111{ 112 DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO " SIOCSIWCOMMIT \n"); 113 114 return 0; 115} 116/* 117 * Wireless Handler : get protocol name 118 */ 119 120int iwctl_giwname(struct net_device *dev, 121 struct iw_request_info *info, 122 char *wrq, 123 char *extra) 124{ 125 strcpy(wrq, "802.11-a/b/g"); 126 return 0; 127} 128 129/* 130 * Wireless Handler : set scan 131 */ 132 133int iwctl_siwscan(struct net_device *dev, 134 struct iw_request_info *info, 135 struct iw_point *wrq, 136 char *extra) 137{ 138 PSDevice pDevice = (PSDevice)netdev_priv(dev); 139 PSMgmtObject pMgmt = &(pDevice->sMgmtObj); 140 struct iw_scan_req *req = (struct iw_scan_req *)extra; 141 unsigned char abyScanSSID[WLAN_IEHDR_LEN + WLAN_SSID_MAXLEN + 1]; 142 PWLAN_IE_SSID pItemSSID = NULL; 143 DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO " SIOCSIWSCAN \n"); 144 145 if (pDevice->byReAssocCount > 0) { //reject scan when re-associating! 146//send scan event to wpa_Supplicant 147 union iwreq_data wrqu; 148 PRINT_K("wireless_send_event--->SIOCGIWSCAN(scan done)\n"); 149 memset(&wrqu, 0, sizeof(wrqu)); 150 wireless_send_event(pDevice->dev, SIOCGIWSCAN, &wrqu, NULL); 151 return 0; 152 } 153 154 spin_lock_irq(&pDevice->lock); 155 BSSvClearBSSList((void *)pDevice, pDevice->bLinkPass); 156 157//mike add: active scan OR passive scan OR desire_ssid scan 158 if (wrq->length == sizeof(struct iw_scan_req)) { 159 if (wrq->flags & IW_SCAN_THIS_ESSID) { //desire_ssid scan 160 memset(abyScanSSID, 0, WLAN_IEHDR_LEN + WLAN_SSID_MAXLEN + 1); 161 pItemSSID = (PWLAN_IE_SSID)abyScanSSID; 162 pItemSSID->byElementID = WLAN_EID_SSID; 163 memcpy(pItemSSID->abySSID, req->essid, (int)req->essid_len); 164 if (pItemSSID->abySSID[req->essid_len - 1] == '\0') { 165 if (req->essid_len > 0) 166 pItemSSID->len = req->essid_len - 1; 167 } else 168 pItemSSID->len = req->essid_len; 169 pMgmt->eScanType = WMAC_SCAN_PASSIVE; 170 PRINT_K("SIOCSIWSCAN:[desired_ssid=%s,len=%d]\n", ((PWLAN_IE_SSID)abyScanSSID)->abySSID, 171 ((PWLAN_IE_SSID)abyScanSSID)->len); 172 bScheduleCommand((void *)pDevice, WLAN_CMD_BSSID_SCAN, abyScanSSID); 173 spin_unlock_irq(&pDevice->lock); 174 175 return 0; 176 } else if (req->scan_type == IW_SCAN_TYPE_PASSIVE) { //passive scan 177 pMgmt->eScanType = WMAC_SCAN_PASSIVE; 178 } 179 } else { //active scan 180 pMgmt->eScanType = WMAC_SCAN_ACTIVE; 181 } 182 183 pMgmt->eScanType = WMAC_SCAN_PASSIVE; 184 bScheduleCommand((void *)pDevice, WLAN_CMD_BSSID_SCAN, NULL); 185 spin_unlock_irq(&pDevice->lock); 186 187 return 0; 188} 189 190/* 191 * Wireless Handler : get scan results 192 */ 193 194int iwctl_giwscan(struct net_device *dev, 195 struct iw_request_info *info, 196 struct iw_point *wrq, 197 char *extra) 198{ 199 int ii, jj, kk; 200 PSDevice pDevice = (PSDevice)netdev_priv(dev); 201 PSMgmtObject pMgmt = &(pDevice->sMgmtObj); 202 PKnownBSS pBSS; 203 PWLAN_IE_SSID pItemSSID; 204 PWLAN_IE_SUPP_RATES pSuppRates, pExtSuppRates; 205 char *current_ev = extra; 206 char *end_buf = extra + IW_SCAN_MAX_DATA; 207 char *current_val = NULL; 208 struct iw_event iwe; 209 long ldBm; 210 char buf[MAX_WPA_IE_LEN * 2 + 30]; 211 212 DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO " SIOCGIWSCAN \n"); 213 214 if (pMgmt->eScanState == WMAC_IS_SCANNING) { 215 // In scanning.. 216 return -EAGAIN; 217 } 218 pBSS = &(pMgmt->sBSSList[0]); 219 for (ii = 0, jj = 0; jj < MAX_BSS_NUM; jj++) { 220 if (current_ev >= end_buf) 221 break; 222 pBSS = &(pMgmt->sBSSList[jj]); 223 if (pBSS->bActive) { 224 //ADD mac address 225 memset(&iwe, 0, sizeof(iwe)); 226 iwe.cmd = SIOCGIWAP; 227 iwe.u.ap_addr.sa_family = ARPHRD_ETHER; 228 memcpy(iwe.u.ap_addr.sa_data, pBSS->abyBSSID, WLAN_BSSID_LEN); 229 current_ev = iwe_stream_add_event(info, current_ev, end_buf, &iwe, IW_EV_ADDR_LEN); 230 //ADD ssid 231 memset(&iwe, 0, sizeof(iwe)); 232 iwe.cmd = SIOCGIWESSID; 233 pItemSSID = (PWLAN_IE_SSID)pBSS->abySSID; 234 iwe.u.data.length = pItemSSID->len; 235 iwe.u.data.flags = 1; 236 current_ev = iwe_stream_add_point(info, current_ev, end_buf, &iwe, pItemSSID->abySSID); 237 //ADD mode 238 memset(&iwe, 0, sizeof(iwe)); 239 iwe.cmd = SIOCGIWMODE; 240 if (WLAN_GET_CAP_INFO_ESS(pBSS->wCapInfo)) { 241 iwe.u.mode = IW_MODE_INFRA; 242 } else { 243 iwe.u.mode = IW_MODE_ADHOC; 244 } 245 iwe.len = IW_EV_UINT_LEN; 246 current_ev = iwe_stream_add_event(info, current_ev, end_buf, &iwe, IW_EV_UINT_LEN); 247 //ADD frequency 248 pSuppRates = (PWLAN_IE_SUPP_RATES)pBSS->abySuppRates; 249 pExtSuppRates = (PWLAN_IE_SUPP_RATES)pBSS->abyExtSuppRates; 250 memset(&iwe, 0, sizeof(iwe)); 251 iwe.cmd = SIOCGIWFREQ; 252 iwe.u.freq.m = pBSS->uChannel; 253 iwe.u.freq.e = 0; 254 iwe.u.freq.i = 0; 255 current_ev = iwe_stream_add_event(info, current_ev, end_buf, &iwe, IW_EV_FREQ_LEN); 256 //2008-0409-04, <Add> by Einsn Liu 257 { 258 int f = (int)pBSS->uChannel - 1; 259 if (f < 0)f = 0; 260 iwe.u.freq.m = frequency_list[f] * 100000; 261 iwe.u.freq.e = 1; 262 } 263 current_ev = iwe_stream_add_event(info, current_ev, end_buf, &iwe, IW_EV_FREQ_LEN); 264 //ADD quality 265 memset(&iwe, 0, sizeof(iwe)); 266 iwe.cmd = IWEVQUAL; 267 RFvRSSITodBm(pDevice, (unsigned char)(pBSS->uRSSI), &ldBm); 268 iwe.u.qual.level = ldBm; 269 iwe.u.qual.noise = 0; 270//2008-0409-01, <Add> by Einsn Liu 271 if (-ldBm < 50) { 272 iwe.u.qual.qual = 100; 273 } else if (-ldBm > 90) { 274 iwe.u.qual.qual = 0; 275 } else { 276 iwe.u.qual.qual = (40 - (-ldBm - 50)) * 100 / 40; 277 } 278 iwe.u.qual.updated = 7; 279 280 // iwe.u.qual.qual = 0; 281 current_ev = iwe_stream_add_event(info, current_ev, end_buf, &iwe, IW_EV_QUAL_LEN); 282 283 memset(&iwe, 0, sizeof(iwe)); 284 iwe.cmd = SIOCGIWENCODE; 285 iwe.u.data.length = 0; 286 if (WLAN_GET_CAP_INFO_PRIVACY(pBSS->wCapInfo)) { 287 iwe.u.data.flags = IW_ENCODE_ENABLED | IW_ENCODE_NOKEY; 288 } else { 289 iwe.u.data.flags = IW_ENCODE_DISABLED; 290 } 291 current_ev = iwe_stream_add_point(info, current_ev, end_buf, &iwe, pItemSSID->abySSID); 292 293 memset(&iwe, 0, sizeof(iwe)); 294 iwe.cmd = SIOCGIWRATE; 295 iwe.u.bitrate.fixed = iwe.u.bitrate.disabled = 0; 296 current_val = current_ev + IW_EV_LCP_LEN; 297 298 for (kk = 0; kk < 12; kk++) { 299 if (pSuppRates->abyRates[kk] == 0) 300 break; 301 // Bit rate given in 500 kb/s units (+ 0x80) 302 iwe.u.bitrate.value = ((pSuppRates->abyRates[kk] & 0x7f) * 500000); 303 current_val = iwe_stream_add_value(info, current_ev, current_val, end_buf, &iwe, IW_EV_PARAM_LEN); 304 } 305 for (kk = 0; kk < 8; kk++) { 306 if (pExtSuppRates->abyRates[kk] == 0) 307 break; 308 // Bit rate given in 500 kb/s units (+ 0x80) 309 iwe.u.bitrate.value = ((pExtSuppRates->abyRates[kk] & 0x7f) * 500000); 310 current_val = iwe_stream_add_value(info, current_ev, current_val, end_buf, &iwe, IW_EV_PARAM_LEN); 311 } 312 313 if ((current_val - current_ev) > IW_EV_LCP_LEN) 314 current_ev = current_val; 315 316 memset(&iwe, 0, sizeof(iwe)); 317 iwe.cmd = IWEVCUSTOM; 318 sprintf(buf, "bcn_int=%d", pBSS->wBeaconInterval); 319 iwe.u.data.length = strlen(buf); 320 current_ev = iwe_stream_add_point(info, current_ev, end_buf, &iwe, buf); 321 322 if ((pBSS->wWPALen > 0) && (pBSS->wWPALen <= MAX_WPA_IE_LEN)) { 323 memset(&iwe, 0, sizeof(iwe)); 324 iwe.cmd = IWEVGENIE; 325 iwe.u.data.length = pBSS->wWPALen; 326 current_ev = iwe_stream_add_point(info, current_ev, end_buf, &iwe, pBSS->byWPAIE); 327 } 328 329 if ((pBSS->wRSNLen > 0) && (pBSS->wRSNLen <= MAX_WPA_IE_LEN)) { 330 memset(&iwe, 0, sizeof(iwe)); 331 iwe.cmd = IWEVGENIE; 332 iwe.u.data.length = pBSS->wRSNLen; 333 current_ev = iwe_stream_add_point(info, current_ev, end_buf, &iwe, pBSS->byRSNIE); 334 } 335 336 } 337 }// for 338 339 wrq->length = current_ev - extra; 340 return 0; 341} 342 343/* 344 * Wireless Handler : set frequency or channel 345 */ 346 347int iwctl_siwfreq(struct net_device *dev, 348 struct iw_request_info *info, 349 struct iw_freq *wrq, 350 char *extra) 351{ 352 PSDevice pDevice = (PSDevice)netdev_priv(dev); 353 int rc = 0; 354 355 DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO " SIOCSIWFREQ \n"); 356 357 // If setting by frequency, convert to a channel 358 if ((wrq->e == 1) && 359 (wrq->m >= (int) 2.412e8) && 360 (wrq->m <= (int) 2.487e8)) { 361 int f = wrq->m / 100000; 362 int c = 0; 363 while ((c < 14) && (f != frequency_list[c])) 364 c++; 365 wrq->e = 0; 366 wrq->m = c + 1; 367 } 368 // Setting by channel number 369 if ((wrq->m > 14) || (wrq->e > 0)) 370 rc = -EOPNOTSUPP; 371 else { 372 int channel = wrq->m; 373 if ((channel < 1) || (channel > 14)) { 374 DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO "%s: New channel value of %d is invalid!\n", dev->name, wrq->m); 375 rc = -EINVAL; 376 } else { 377 // Yes ! We can set it !!! 378 DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO " Set to channel = %d\n", channel); 379 pDevice->uChannel = channel; 380 //2007-0207-04,<Add> by EinsnLiu 381 //Make change effect at once 382 pDevice->bCommit = true; 383 } 384 } 385 386 return rc; 387} 388 389/* 390 * Wireless Handler : get frequency or channel 391 */ 392 393int iwctl_giwfreq(struct net_device *dev, 394 struct iw_request_info *info, 395 struct iw_freq *wrq, 396 char *extra) 397{ 398 PSDevice pDevice = (PSDevice)netdev_priv(dev); 399 PSMgmtObject pMgmt = &(pDevice->sMgmtObj); 400 401 DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO " SIOCGIWFREQ \n"); 402 403#ifdef WEXT_USECHANNELS 404 wrq->m = (int)pMgmt->uCurrChannel; 405 wrq->e = 0; 406#else 407 { 408 int f = (int)pMgmt->uCurrChannel - 1; 409 if (f < 0) 410 f = 0; 411 wrq->m = frequency_list[f] * 100000; 412 wrq->e = 1; 413 } 414#endif 415 416 return 0; 417} 418 419/* 420 * Wireless Handler : set operation mode 421 */ 422 423int iwctl_siwmode(struct net_device *dev, 424 struct iw_request_info *info, 425 __u32 *wmode, 426 char *extra) 427{ 428 PSDevice pDevice = (PSDevice)netdev_priv(dev); 429 PSMgmtObject pMgmt = &(pDevice->sMgmtObj); 430 int rc = 0; 431 432 DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO " SIOCSIWMODE \n"); 433 434 if (pMgmt->eCurrMode == WMAC_MODE_ESS_AP && pDevice->bEnableHostapd) { 435 DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO "Can't set operation mode, hostapd is running \n"); 436 return rc; 437 } 438 439 switch (*wmode) { 440 case IW_MODE_ADHOC: 441 if (pMgmt->eConfigMode != WMAC_CONFIG_IBSS_STA) { 442 pMgmt->eConfigMode = WMAC_CONFIG_IBSS_STA; 443 if (pDevice->flags & DEVICE_FLAGS_OPENED) { 444 pDevice->bCommit = true; 445 } 446 } 447 DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO "set mode to ad-hoc \n"); 448 break; 449 case IW_MODE_AUTO: 450 case IW_MODE_INFRA: 451 if (pMgmt->eConfigMode != WMAC_CONFIG_ESS_STA) { 452 pMgmt->eConfigMode = WMAC_CONFIG_ESS_STA; 453 if (pDevice->flags & DEVICE_FLAGS_OPENED) { 454 pDevice->bCommit = true; 455 } 456 } 457 DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO "set mode to infrastructure \n"); 458 break; 459 case IW_MODE_MASTER: 460 461 pMgmt->eConfigMode = WMAC_CONFIG_ESS_STA; 462 rc = -EOPNOTSUPP; 463 break; 464 465 if (pMgmt->eConfigMode != WMAC_CONFIG_AP) { 466 pMgmt->eConfigMode = WMAC_CONFIG_AP; 467 if (pDevice->flags & DEVICE_FLAGS_OPENED) { 468 pDevice->bCommit = true; 469 } 470 } 471 DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO "set mode to Access Point \n"); 472 break; 473 474 case IW_MODE_REPEAT: 475 pMgmt->eConfigMode = WMAC_CONFIG_ESS_STA; 476 rc = -EOPNOTSUPP; 477 break; 478 default: 479 rc = -EINVAL; 480 } 481 482 return rc; 483} 484 485/* 486 * Wireless Handler : get operation mode 487 */ 488 489int iwctl_giwmode(struct net_device *dev, 490 struct iw_request_info *info, 491 __u32 *wmode, 492 char *extra) 493{ 494 PSDevice pDevice = (PSDevice)netdev_priv(dev); 495 PSMgmtObject pMgmt = &(pDevice->sMgmtObj); 496 497 DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO " SIOCGIWMODE \n"); 498 // If not managed, assume it's ad-hoc 499 switch (pMgmt->eConfigMode) { 500 case WMAC_CONFIG_ESS_STA: 501 *wmode = IW_MODE_INFRA; 502 break; 503 case WMAC_CONFIG_IBSS_STA: 504 *wmode = IW_MODE_ADHOC; 505 break; 506 case WMAC_CONFIG_AUTO: 507 *wmode = IW_MODE_INFRA; 508 break; 509 case WMAC_CONFIG_AP: 510 *wmode = IW_MODE_MASTER; 511 break; 512 default: 513 *wmode = IW_MODE_ADHOC; 514 } 515 516 return 0; 517} 518 519/* 520 * Wireless Handler : get capability range 521 */ 522 523int iwctl_giwrange(struct net_device *dev, 524 struct iw_request_info *info, 525 struct iw_point *wrq, 526 char *extra) 527{ 528 struct iw_range *range = (struct iw_range *)extra; 529 int i, k; 530 unsigned char abySupportedRates[13] = {0x02, 0x04, 0x0B, 0x16, 0x0c, 0x12, 0x18, 0x24, 0x30, 0x48, 0x60, 0x6C, 0x90}; 531 532 DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO " SIOCGIWRANGE \n"); 533 if (wrq->pointer) { 534 wrq->length = sizeof(struct iw_range); 535 memset(range, 0, sizeof(struct iw_range)); 536 range->min_nwid = 0x0000; 537 range->max_nwid = 0x0000; 538 range->num_channels = 14; 539 // Should be based on cap_rid.country to give only 540 // what the current card support 541 k = 0; 542 for (i = 0; i < 14; i++) { 543 range->freq[k].i = i + 1; // List index 544 range->freq[k].m = frequency_list[i] * 100000; 545 range->freq[k++].e = 1; // Values in table in MHz -> * 10^5 * 10 546 } 547 range->num_frequency = k; 548 // Hum... Should put the right values there 549#ifdef Calcu_LinkQual 550 range->max_qual.qual = 100; 551#else 552 range->max_qual.qual = 255; 553#endif 554 range->max_qual.level = 0; 555 range->max_qual.noise = 0; 556 range->sensitivity = 255; 557 558 for (i = 0; i < 13; i++) { 559 range->bitrate[i] = abySupportedRates[i] * 500000; 560 if (range->bitrate[i] == 0) 561 break; 562 } 563 range->num_bitrates = i; 564 565 // Set an indication of the max TCP throughput 566 // in bit/s that we can expect using this interface. 567 // May be use for QoS stuff... Jean II 568 if (i > 2) 569 range->throughput = 5 * 1000 * 1000; 570 else 571 range->throughput = 1.5 * 1000 * 1000; 572 573 range->min_rts = 0; 574 range->max_rts = 2312; 575 range->min_frag = 256; 576 range->max_frag = 2312; 577 578 // the encoding capabilities 579 range->num_encoding_sizes = 3; 580 // 64(40) bits WEP 581 range->encoding_size[0] = 5; 582 // 128(104) bits WEP 583 range->encoding_size[1] = 13; 584 // 256 bits for WPA-PSK 585 range->encoding_size[2] = 32; 586 // 4 keys are allowed 587 range->max_encoding_tokens = 4; 588 589 range->enc_capa = IW_ENC_CAPA_WPA | IW_ENC_CAPA_WPA2 | 590 IW_ENC_CAPA_CIPHER_TKIP | IW_ENC_CAPA_CIPHER_CCMP; 591 592 range->min_pmp = 0; 593 range->max_pmp = 1000000;// 1 secs 594 range->min_pmt = 0; 595 range->max_pmt = 1000000;// 1 secs 596 range->pmp_flags = IW_POWER_PERIOD; 597 range->pmt_flags = IW_POWER_TIMEOUT; 598 range->pm_capa = IW_POWER_PERIOD | IW_POWER_TIMEOUT | IW_POWER_ALL_R; 599 600 // Transmit Power - values are in mW 601 602 range->txpower[0] = 100; 603 range->num_txpower = 1; 604 range->txpower_capa = IW_TXPOW_MWATT; 605 range->we_version_source = SUPPORTED_WIRELESS_EXT; 606 range->we_version_compiled = WIRELESS_EXT; 607 range->retry_capa = IW_RETRY_LIMIT | IW_RETRY_LIFETIME; 608 range->retry_flags = IW_RETRY_LIMIT; 609 range->r_time_flags = IW_RETRY_LIFETIME; 610 range->min_retry = 1; 611 range->max_retry = 65535; 612 range->min_r_time = 1024; 613 range->max_r_time = 65535 * 1024; 614 // Experimental measurements - boundary 11/5.5 Mb/s 615 // Note : with or without the (local->rssi), results 616 // are somewhat different. - Jean II 617 range->avg_qual.qual = 6; 618 range->avg_qual.level = 176; // -80 dBm 619 range->avg_qual.noise = 0; 620 } 621 622 return 0; 623} 624 625/* 626 * Wireless Handler : set ap mac address 627 */ 628 629int iwctl_siwap(struct net_device *dev, 630 struct iw_request_info *info, 631 struct sockaddr *wrq, 632 char *extra) 633{ 634 PSDevice pDevice = (PSDevice)netdev_priv(dev); 635 PSMgmtObject pMgmt = &(pDevice->sMgmtObj); 636 int rc = 0; 637 unsigned char ZeroBSSID[WLAN_BSSID_LEN] = {0x00, 0x00, 0x00, 0x00, 0x00, 0x00}; 638 639 DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO " SIOCSIWAP \n"); 640 if (pMgmt->eScanState == WMAC_IS_SCANNING) { 641 // In scanning.. 642 printk("SIOCSIWAP(??)-->In scanning...\n"); 643 // return -EAGAIN; 644 } 645 if (wrq->sa_family != ARPHRD_ETHER) 646 rc = -EINVAL; 647 else { 648 memcpy(pMgmt->abyDesireBSSID, wrq->sa_data, 6); 649 //2008-0409-05, <Add> by Einsn Liu 650 if ((pDevice->bLinkPass == true) && 651 (memcmp(pMgmt->abyDesireBSSID, pMgmt->abyCurrBSSID, 6) == 0)) { 652 return rc; 653 } 654 //mike :add 655 if ((is_broadcast_ether_addr(pMgmt->abyDesireBSSID)) || 656 (memcmp(pMgmt->abyDesireBSSID, ZeroBSSID, 6) == 0)) { 657 PRINT_K("SIOCSIWAP:invalid desired BSSID return!\n"); 658 return rc; 659 } 660 //mike add: if desired AP is hidden ssid(there are two same BSSID in list), 661 // then ignore,because you don't known which one to be connect with?? 662 { 663 unsigned int ii, uSameBssidNum = 0; 664 for (ii = 0; ii < MAX_BSS_NUM; ii++) { 665 if (pMgmt->sBSSList[ii].bActive && 666 ether_addr_equal(pMgmt->sBSSList[ii].abyBSSID, 667 pMgmt->abyDesireBSSID)) { 668 uSameBssidNum++; 669 } 670 } 671 if (uSameBssidNum >= 2) { //hit: desired AP is in hidden ssid mode!!! 672 PRINT_K("SIOCSIWAP:ignore for desired AP in hidden mode\n"); 673 return rc; 674 } 675 } 676 677 if (pDevice->flags & DEVICE_FLAGS_OPENED) { 678 pDevice->bCommit = true; 679 } 680 } 681 return rc; 682} 683 684/* 685 * Wireless Handler : get ap mac address 686 */ 687 688int iwctl_giwap(struct net_device *dev, 689 struct iw_request_info *info, 690 struct sockaddr *wrq, 691 char *extra) 692{ 693 PSDevice pDevice = (PSDevice)netdev_priv(dev); 694 PSMgmtObject pMgmt = &(pDevice->sMgmtObj); 695 696 DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO " SIOCGIWAP \n"); 697 698 memcpy(wrq->sa_data, pMgmt->abyCurrBSSID, 6); 699 //2008-0410,<Modify> by Einsn Liu 700 if ((pDevice->bLinkPass == false) && (pMgmt->eCurrMode != WMAC_MODE_ESS_AP)) 701 memset(wrq->sa_data, 0, 6); 702 703 if (pMgmt->eCurrMode == WMAC_MODE_ESS_AP) { 704 memcpy(wrq->sa_data, pMgmt->abyCurrBSSID, 6); 705 } 706 707 wrq->sa_family = ARPHRD_ETHER; 708 709 return 0; 710} 711 712/* 713 * Wireless Handler : get ap list 714 */ 715 716int iwctl_giwaplist(struct net_device *dev, 717 struct iw_request_info *info, 718 struct iw_point *wrq, 719 char *extra) 720{ 721 int ii, jj, rc = 0; 722 struct sockaddr sock[IW_MAX_AP]; 723 struct iw_quality qual[IW_MAX_AP]; 724 PSDevice pDevice = (PSDevice)netdev_priv(dev); 725 PSMgmtObject pMgmt = &(pDevice->sMgmtObj); 726 727 DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO " SIOCGIWAPLIST \n"); 728 // Only super-user can see AP list 729 730 if (!capable(CAP_NET_ADMIN)) { 731 rc = -EPERM; 732 return rc; 733 } 734 735 if (wrq->pointer) { 736 PKnownBSS pBSS = &(pMgmt->sBSSList[0]); 737 738 for (ii = 0, jj = 0; ii < MAX_BSS_NUM; ii++) { 739 pBSS = &(pMgmt->sBSSList[ii]); 740 if (!pBSS->bActive) 741 continue; 742 if (jj >= IW_MAX_AP) 743 break; 744 memcpy(sock[jj].sa_data, pBSS->abyBSSID, 6); 745 sock[jj].sa_family = ARPHRD_ETHER; 746 qual[jj].level = pBSS->uRSSI; 747 qual[jj].qual = qual[jj].noise = 0; 748 qual[jj].updated = 2; 749 jj++; 750 } 751 752 wrq->flags = 1; // Should be define'd 753 wrq->length = jj; 754 memcpy(extra, sock, sizeof(struct sockaddr)*jj); 755 memcpy(extra + sizeof(struct sockaddr)*jj, qual, sizeof(struct iw_quality)*jj); 756 } 757 758 return rc; 759} 760 761/* 762 * Wireless Handler : set essid 763 */ 764 765int iwctl_siwessid(struct net_device *dev, 766 struct iw_request_info *info, 767 struct iw_point *wrq, 768 char *extra) 769{ 770 PSDevice pDevice = (PSDevice)netdev_priv(dev); 771 PSMgmtObject pMgmt = &(pDevice->sMgmtObj); 772 PWLAN_IE_SSID pItemSSID; 773 //2008-0409-05, <Add> by Einsn Liu 774 unsigned char len; 775 776 DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO " SIOCSIWESSID \n"); 777 pDevice->fWPA_Authened = false; 778 if (pMgmt->eScanState == WMAC_IS_SCANNING) { 779 // In scanning.. 780 printk("SIOCSIWESSID(??)-->In scanning...\n"); 781 // return -EAGAIN; 782 } 783 // Check if we asked for `any' 784 if (wrq->flags == 0) { 785 // Just send an empty SSID list 786 memset(pMgmt->abyDesireSSID, 0, WLAN_IEHDR_LEN + WLAN_SSID_MAXLEN + 1); 787 memset(pMgmt->abyDesireBSSID, 0xFF, 6); 788 PRINT_K("set essid to 'any' \n"); 789#ifdef WPA_SUPPLICANT_DRIVER_WEXT_SUPPORT 790 return 0; 791#endif 792 } else { 793 // Set the SSID 794 memset(pMgmt->abyDesireSSID, 0, WLAN_IEHDR_LEN + WLAN_SSID_MAXLEN + 1); 795 pItemSSID = (PWLAN_IE_SSID)pMgmt->abyDesireSSID; 796 pItemSSID->byElementID = WLAN_EID_SSID; 797 798 memcpy(pItemSSID->abySSID, extra, wrq->length); 799 if (pItemSSID->abySSID[wrq->length - 1] == '\0') { 800 if (wrq->length > 0) 801 pItemSSID->len = wrq->length - 1; 802 } else 803 pItemSSID->len = wrq->length; 804 printk("set essid to %s \n", pItemSSID->abySSID); 805 //2008-0409-05, <Add> by Einsn Liu 806 len = (pItemSSID->len > ((PWLAN_IE_SSID)pMgmt->abyCurrSSID)->len) ? pItemSSID->len : ((PWLAN_IE_SSID)pMgmt->abyCurrSSID)->len; 807 if ((pDevice->bLinkPass == true) && 808 (memcmp(pItemSSID->abySSID, ((PWLAN_IE_SSID)pMgmt->abyCurrSSID)->abySSID, len) == 0)) 809 return 0; 810 811 //mike:need clear desiredBSSID 812 if (pItemSSID->len == 0) { 813 memset(pMgmt->abyDesireBSSID, 0xFF, 6); 814 return 0; 815 } 816 817#ifdef WPA_SUPPLICANT_DRIVER_WEXT_SUPPORT 818 //Wext wil order another command of siwap to link with desired AP, 819 //so here need not associate?? 820 if (pDevice->bWPASuppWextEnabled == true) { 821 /*******search if in hidden ssid mode ****/ 822 { 823 PKnownBSS pCurr = NULL; 824 unsigned char abyTmpDesireSSID[WLAN_IEHDR_LEN + WLAN_SSID_MAXLEN + 1]; 825 unsigned int ii, uSameBssidNum = 0; 826 827 memcpy(abyTmpDesireSSID, pMgmt->abyDesireSSID, sizeof(abyTmpDesireSSID)); 828 pCurr = BSSpSearchBSSList(pDevice, 829 NULL, 830 abyTmpDesireSSID, 831 pMgmt->eConfigPHYMode 832); 833 834 if (pCurr == NULL) { 835 PRINT_K("SIOCSIWESSID:hidden ssid site survey before associate.......\n"); 836 vResetCommandTimer((void *)pDevice); 837 pMgmt->eScanType = WMAC_SCAN_ACTIVE; 838 bScheduleCommand((void *)pDevice, WLAN_CMD_BSSID_SCAN, pMgmt->abyDesireSSID); 839 bScheduleCommand((void *)pDevice, WLAN_CMD_SSID, pMgmt->abyDesireSSID); 840 } else { //mike:to find out if that desired SSID is a hidden-ssid AP , 841 // by means of judging if there are two same BSSID exist in list ? 842 for (ii = 0; ii < MAX_BSS_NUM; ii++) { 843 if (pMgmt->sBSSList[ii].bActive && 844 ether_addr_equal(pMgmt->sBSSList[ii].abyBSSID, 845 pCurr->abyBSSID)) { 846 uSameBssidNum++; 847 } 848 } 849 if (uSameBssidNum >= 2) { //hit: desired AP is in hidden ssid mode!!! 850 printk("SIOCSIWESSID:hidden ssid directly associate.......\n"); 851 vResetCommandTimer((void *)pDevice); 852 pMgmt->eScanType = WMAC_SCAN_PASSIVE; //this scan type,you'll submit scan result! 853 bScheduleCommand((void *)pDevice, WLAN_CMD_BSSID_SCAN, pMgmt->abyDesireSSID); 854 bScheduleCommand((void *)pDevice, WLAN_CMD_SSID, pMgmt->abyDesireSSID); 855 } 856 } 857 } 858 return 0; 859 } 860#endif 861 862 DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO "set essid = %s \n", pItemSSID->abySSID); 863 } 864 865 if (pDevice->flags & DEVICE_FLAGS_OPENED) { 866 pDevice->bCommit = true; 867 } 868 869 return 0; 870} 871 872/* 873 * Wireless Handler : get essid 874 */ 875 876int iwctl_giwessid(struct net_device *dev, 877 struct iw_request_info *info, 878 struct iw_point *wrq, 879 char *extra) 880{ 881 PSDevice pDevice = (PSDevice)netdev_priv(dev); 882 PSMgmtObject pMgmt = &(pDevice->sMgmtObj); 883 PWLAN_IE_SSID pItemSSID; 884 885 DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO " SIOCGIWESSID \n"); 886 887 // Note : if wrq->u.data.flags != 0, we should 888 // get the relevant SSID from the SSID list... 889 890 // Get the current SSID 891 pItemSSID = (PWLAN_IE_SSID)pMgmt->abyCurrSSID; 892 //pItemSSID = (PWLAN_IE_SSID)pMgmt->abyDesireSSID; 893 memcpy(extra, pItemSSID->abySSID , pItemSSID->len); 894 extra[pItemSSID->len] = '\0'; 895 wrq->length = pItemSSID->len + 1; 896 //2008-0409-03, <Add> by Einsn Liu 897 wrq->length = pItemSSID->len; 898 wrq->flags = 1; // active 899 900 return 0; 901} 902 903/* 904 * Wireless Handler : set data rate 905 */ 906 907int iwctl_siwrate(struct net_device *dev, 908 struct iw_request_info *info, 909 struct iw_param *wrq, 910 char *extra) 911{ 912 PSDevice pDevice = (PSDevice)netdev_priv(dev); 913 int rc = 0; 914 u8 brate = 0; 915 int i; 916 unsigned char abySupportedRates[13] = {0x02, 0x04, 0x0B, 0x16, 0x0c, 0x12, 0x18, 0x24, 0x30, 0x48, 0x60, 0x6C, 0x90}; 917 918 DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO " SIOCSIWRATE \n"); 919 if (!(pDevice->flags & DEVICE_FLAGS_OPENED)) { 920 rc = -EINVAL; 921 return rc; 922 } 923 924 // First : get a valid bit rate value 925 926 // Which type of value 927 if ((wrq->value < 13) && 928 (wrq->value >= 0)) { 929 // Setting by rate index 930 // Find value in the magic rate table 931 brate = wrq->value; 932 } else { 933 // Setting by frequency value 934 u8 normvalue = (u8) (wrq->value/500000); 935 936 // Check if rate is valid 937 for (i = 0; i < 13; i++) { 938 if (normvalue == abySupportedRates[i]) { 939 brate = i; 940 break; 941 } 942 } 943 } 944 // -1 designed the max rate (mostly auto mode) 945 if (wrq->value == -1) { 946 // Get the highest available rate 947 for (i = 0; i < 13; i++) { 948 if (abySupportedRates[i] == 0) 949 break; 950 } 951 if (i != 0) 952 brate = i - 1; 953 954 } 955 // Check that it is valid 956 // brate is index of abySupportedRates[] 957 if (brate > 13) { 958 rc = -EINVAL; 959 return rc; 960 } 961 962 // Now, check if we want a fixed or auto value 963 if (wrq->fixed != 0) { 964 // Fixed mode 965 // One rate, fixed 966 printk("Rate Fix\n"); 967 pDevice->bFixRate = true; 968 if ((pDevice->byBBType == BB_TYPE_11B) && (brate > 3)) { 969 pDevice->uConnectionRate = 3; 970 } else { 971 pDevice->uConnectionRate = brate; 972 DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO "Fixed to Rate %d \n", pDevice->uConnectionRate); 973 } 974 975 } else { 976 pDevice->bFixRate = false; 977 pDevice->uConnectionRate = 13; 978 printk("auto rate:connection_rate is 13\n"); 979 } 980 981 return rc; 982} 983 984/* 985 * Wireless Handler : get data rate 986 */ 987 988int iwctl_giwrate(struct net_device *dev, 989 struct iw_request_info *info, 990 struct iw_param *wrq, 991 char *extra) 992{ 993 PSDevice pDevice = (PSDevice)netdev_priv(dev); 994//2007-0118-05,<Mark> by EinsnLiu 995//Mark the unnecessary sentences. 996// PSMgmtObject pMgmt = &(pDevice->sMgmtObj); 997 998 DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO " SIOCGIWRATE \n"); 999 { 1000 unsigned char abySupportedRates[13] = {0x02, 0x04, 0x0B, 0x16, 0x0c, 0x12, 0x18, 0x24, 0x30, 0x48, 0x60, 0x6C, 0x90}; 1001 int brate = 0; 1002//2008-5-8 <modify> by chester 1003 if (pDevice->bLinkPass) { 1004 if (pDevice->bFixRate == true) { 1005 if (pDevice->uConnectionRate < 13) { 1006 brate = abySupportedRates[pDevice->uConnectionRate]; 1007 } else { 1008 if (pDevice->byBBType == BB_TYPE_11B) 1009 brate = 0x16; 1010 if (pDevice->byBBType == BB_TYPE_11G) 1011 brate = 0x6C; 1012 if (pDevice->byBBType == BB_TYPE_11A) 1013 brate = 0x6C; 1014 } 1015 } else { 1016 brate = abySupportedRates[TxRate_iwconfig]; 1017 } 1018 } else brate = 0; 1019//2007-0118-05,<Mark> by EinsnLiu 1020//Mark the unnecessary sentences. 1021/* 1022 if (pMgmt->eCurrMode == WMAC_MODE_ESS_AP) { 1023 if (pDevice->byBBType == BB_TYPE_11B) 1024 brate = 0x16; 1025 if (pDevice->byBBType == BB_TYPE_11G) 1026 brate = 0x6C; 1027 if (pDevice->byBBType == BB_TYPE_11A) 1028 brate = 0x6C; 1029 } 1030*/ 1031 1032// if (pDevice->uConnectionRate == 13) 1033// brate = abySupportedRates[pDevice->wCurrentRate]; 1034 wrq->value = brate * 500000; 1035 // If more than one rate, set auto 1036 if (pDevice->bFixRate == true) 1037 wrq->fixed = true; 1038 } 1039 1040 return 0; 1041} 1042 1043/* 1044 * Wireless Handler : set rts threshold 1045 */ 1046 1047int iwctl_siwrts(struct net_device *dev, 1048 struct iw_request_info *info, 1049 struct iw_param *wrq, 1050 char *extra) 1051{ 1052 PSDevice pDevice = (PSDevice)netdev_priv(dev); 1053 int rc = 0; 1054 1055 DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO " SIOCSIWRTS \n"); 1056 1057 { 1058 int rthr = wrq->value; 1059 if (wrq->disabled) 1060 rthr = 2312; 1061 if ((rthr < 0) || (rthr > 2312)) { 1062 rc = -EINVAL; 1063 } else { 1064 pDevice->wRTSThreshold = rthr; 1065 } 1066 } 1067 1068 return 0; 1069} 1070 1071/* 1072 * Wireless Handler : get rts 1073 */ 1074 1075int iwctl_giwrts(struct net_device *dev, 1076 struct iw_request_info *info, 1077 struct iw_param *wrq, 1078 char *extra) 1079{ 1080 PSDevice pDevice = (PSDevice)netdev_priv(dev); 1081 1082 DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO " SIOCGIWRTS \n"); 1083 wrq->value = pDevice->wRTSThreshold; 1084 wrq->disabled = (wrq->value >= 2312); 1085 wrq->fixed = 1; 1086 1087 return 0; 1088} 1089 1090/* 1091 * Wireless Handler : set fragment threshold 1092 */ 1093 1094int iwctl_siwfrag(struct net_device *dev, 1095 struct iw_request_info *info, 1096 struct iw_param *wrq, 1097 char *extra) 1098{ 1099 PSDevice pDevice = (PSDevice)netdev_priv(dev); 1100 int rc = 0; 1101 int fthr = wrq->value; 1102 1103 DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO " SIOCSIWFRAG \n"); 1104 1105 if (wrq->disabled) 1106 fthr = 2312; 1107 if ((fthr < 256) || (fthr > 2312)) { 1108 rc = -EINVAL; 1109 } else { 1110 fthr &= ~0x1; // Get an even value 1111 pDevice->wFragmentationThreshold = (u16)fthr; 1112 } 1113 1114 return rc; 1115} 1116 1117/* 1118 * Wireless Handler : get fragment threshold 1119 */ 1120 1121int iwctl_giwfrag(struct net_device *dev, 1122 struct iw_request_info *info, 1123 struct iw_param *wrq, 1124 char *extra) 1125{ 1126 PSDevice pDevice = (PSDevice)netdev_priv(dev); 1127 1128 DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO " SIOCGIWFRAG \n"); 1129 wrq->value = pDevice->wFragmentationThreshold; 1130 wrq->disabled = (wrq->value >= 2312); 1131 wrq->fixed = 1; 1132 1133 return 0; 1134} 1135 1136/* 1137 * Wireless Handler : set retry threshold 1138 */ 1139int iwctl_siwretry(struct net_device *dev, 1140 struct iw_request_info *info, 1141 struct iw_param *wrq, 1142 char *extra) 1143{ 1144 PSDevice pDevice = (PSDevice)netdev_priv(dev); 1145 int rc = 0; 1146 1147 DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO " SIOCSIWRETRY \n"); 1148 1149 if (wrq->disabled) { 1150 rc = -EINVAL; 1151 return rc; 1152 } 1153 1154 if (wrq->flags & IW_RETRY_LIMIT) { 1155 if (wrq->flags & IW_RETRY_MAX) 1156 pDevice->byLongRetryLimit = wrq->value; 1157 else if (wrq->flags & IW_RETRY_MIN) 1158 pDevice->byShortRetryLimit = wrq->value; 1159 else { 1160 // No modifier : set both 1161 pDevice->byShortRetryLimit = wrq->value; 1162 pDevice->byLongRetryLimit = wrq->value; 1163 } 1164 } 1165 if (wrq->flags & IW_RETRY_LIFETIME) { 1166 pDevice->wMaxTransmitMSDULifetime = wrq->value; 1167 } 1168 1169 return rc; 1170} 1171 1172/* 1173 * Wireless Handler : get retry threshold 1174 */ 1175int iwctl_giwretry(struct net_device *dev, 1176 struct iw_request_info *info, 1177 struct iw_param *wrq, 1178 char *extra) 1179{ 1180 PSDevice pDevice = (PSDevice)netdev_priv(dev); 1181 DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO " SIOCGIWRETRY \n"); 1182 wrq->disabled = 0; // Can't be disabled 1183 1184 // Note : by default, display the min retry number 1185 if ((wrq->flags & IW_RETRY_TYPE) == IW_RETRY_LIFETIME) { 1186 wrq->flags = IW_RETRY_LIFETIME; 1187 wrq->value = (int)pDevice->wMaxTransmitMSDULifetime; //ms 1188 } else if ((wrq->flags & IW_RETRY_MAX)) { 1189 wrq->flags = IW_RETRY_LIMIT | IW_RETRY_MAX; 1190 wrq->value = (int)pDevice->byLongRetryLimit; 1191 } else { 1192 wrq->flags = IW_RETRY_LIMIT; 1193 wrq->value = (int)pDevice->byShortRetryLimit; 1194 if ((int)pDevice->byShortRetryLimit != (int)pDevice->byLongRetryLimit) 1195 wrq->flags |= IW_RETRY_MIN; 1196 } 1197 1198 return 0; 1199} 1200 1201/* 1202 * Wireless Handler : set encode mode 1203 */ 1204int iwctl_siwencode(struct net_device *dev, 1205 struct iw_request_info *info, 1206 struct iw_point *wrq, 1207 char *extra) 1208{ 1209 PSDevice pDevice = (PSDevice)netdev_priv(dev); 1210 PSMgmtObject pMgmt = &(pDevice->sMgmtObj); 1211 unsigned long dwKeyIndex = (unsigned long)(wrq->flags & IW_ENCODE_INDEX); 1212 int ii, uu, rc = 0; 1213 int index = (wrq->flags & IW_ENCODE_INDEX); 1214 1215//2007-0207-07,<Modify> by EinsnLiu 1216//There are some problems when using iwconfig encode/key command to set the WEP key. 1217//I almost rewrite this function. 1218//now it support:(assume the wireless interface's name is eth0) 1219//iwconfig eth0 key [1] 1122334455 open /*set key stirng to index 1,and driver using key index is set to 1*/ 1220//iwconfig eth0 key [3] /*set driver using key index to 3,the key string no change */ 1221//iwconfig eth0 key 1122334455 /*set key string to driver using index*/ 1222//iwconfig eth0 key restricted /*enable share key*/ 1223 1224 PSKeyTable pkeytab; 1225 1226 DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO " SIOCSIWENCODE \n"); 1227 1228 if ((wrq->flags & IW_ENCODE_DISABLED) == 0) { 1229 //Not disable encryption 1230 1231 if (dwKeyIndex > WLAN_WEP_NKEYS) { 1232 rc = -EINVAL; 1233 return rc; 1234 } 1235 1236 if (dwKeyIndex < 1 && ((wrq->flags & IW_ENCODE_NOKEY) == 0)) {//set default key 1237 if (pDevice->byKeyIndex < WLAN_WEP_NKEYS) { 1238 dwKeyIndex = pDevice->byKeyIndex; 1239 } else dwKeyIndex = 0; 1240 } else dwKeyIndex--; 1241 1242 // Check the size of the key 1243 if (wrq->length > WLAN_WEP232_KEYLEN) { 1244 rc = -EINVAL; 1245 return rc; 1246 } 1247 1248 if (wrq->length > 0) {//have key 1249 1250 if (wrq->length == WLAN_WEP232_KEYLEN) { 1251 DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO "Set 232 bit wep key\n"); 1252 } else if (wrq->length == WLAN_WEP104_KEYLEN) { 1253 DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO "Set 104 bit wep key\n"); 1254 } else if (wrq->length == WLAN_WEP40_KEYLEN) { 1255 DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO "Set 40 bit wep key, index= %d\n", (int)dwKeyIndex); 1256 } else {//no support length 1257 rc = -EINVAL; 1258 return rc; 1259 } 1260 memset(pDevice->abyKey, 0, WLAN_WEP232_KEYLEN); 1261 memcpy(pDevice->abyKey, extra, wrq->length); 1262 1263 DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO "abyKey: "); 1264 for (ii = 0; ii < wrq->length; ii++) { 1265 DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO "%02x ", pDevice->abyKey[ii]); 1266 } 1267 1268 if (pDevice->flags & DEVICE_FLAGS_OPENED) { 1269 spin_lock_irq(&pDevice->lock); 1270 KeybSetDefaultKey(&(pDevice->sKey), 1271 (unsigned long)(dwKeyIndex | (1 << 31)), 1272 wrq->length, 1273 NULL, 1274 pDevice->abyKey, 1275 KEY_CTL_WEP, 1276 pDevice->PortOffset, 1277 pDevice->byLocalID 1278); 1279 spin_unlock_irq(&pDevice->lock); 1280 } 1281 pDevice->byKeyIndex = (unsigned char)dwKeyIndex; 1282 pDevice->uKeyLength = wrq->length; 1283 pDevice->bTransmitKey = true; 1284 pDevice->bEncryptionEnable = true; 1285 pDevice->eEncryptionStatus = Ndis802_11Encryption1Enabled; 1286 1287 } else if (index > 0) { 1288 //when the length is 0 the request only changes the default transmit key index 1289 //check the new key if it has a non zero length 1290 if (pDevice->bEncryptionEnable == false) { 1291 rc = -EINVAL; 1292 return rc; 1293 } 1294 DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO "Just set Default key Index:\n"); 1295 pkeytab = &(pDevice->sKey.KeyTable[MAX_KEY_TABLE - 1]); 1296 if (pkeytab->GroupKey[(unsigned char)dwKeyIndex].uKeyLength == 0) { 1297 DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO "Default key len is 0\n"); 1298 rc = -EINVAL; 1299 return rc; 1300 } 1301 pDevice->byKeyIndex = (unsigned char)dwKeyIndex; 1302 pkeytab->dwGTKeyIndex = dwKeyIndex | (1 << 31); 1303 pkeytab->GroupKey[(unsigned char)dwKeyIndex].dwKeyIndex = dwKeyIndex | (1 << 31); 1304 } 1305 1306 } else {//disable the key 1307 DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO "Disable WEP function\n"); 1308 if (pDevice->bEncryptionEnable == false) 1309 return 0; 1310 pMgmt->bShareKeyAlgorithm = false; 1311 pDevice->bEncryptionEnable = false; 1312 pDevice->eEncryptionStatus = Ndis802_11EncryptionDisabled; 1313 if (pDevice->flags & DEVICE_FLAGS_OPENED) { 1314 spin_lock_irq(&pDevice->lock); 1315 for (uu = 0; uu < MAX_KEY_TABLE; uu++) 1316 MACvDisableKeyEntry(pDevice->PortOffset, uu); 1317 spin_unlock_irq(&pDevice->lock); 1318 } 1319 } 1320//End Modify,Einsn 1321 1322/* 1323 DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO " SIOCSIWENCODE \n"); 1324 1325 // Check the size of the key 1326 if (wrq->length > WLAN_WEP232_KEYLEN) { 1327 rc = -EINVAL; 1328 return rc; 1329 } 1330 1331 if (dwKeyIndex > WLAN_WEP_NKEYS) { 1332 rc = -EINVAL; 1333 return rc; 1334 } 1335 1336 if (dwKeyIndex > 0) 1337 dwKeyIndex--; 1338 1339 // Send the key to the card 1340 if (wrq->length > 0) { 1341 if (wrq->length == WLAN_WEP232_KEYLEN) { 1342 DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO "Set 232 bit wep key\n"); 1343 } else if (wrq->length == WLAN_WEP104_KEYLEN) { 1344 DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO "Set 104 bit wep key\n"); 1345 } else if (wrq->length == WLAN_WEP40_KEYLEN) { 1346 DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO "Set 40 bit wep key, index= %d\n", (int)dwKeyIndex); 1347 } 1348 memset(pDevice->abyKey, 0, WLAN_WEP232_KEYLEN); 1349 memcpy(pDevice->abyKey, extra, wrq->length); 1350 1351 DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO "abyKey: "); 1352 for (ii = 0; ii < wrq->length; ii++) { 1353 DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO "%02x ", pDevice->abyKey[ii]); 1354 } 1355 1356 if (pDevice->flags & DEVICE_FLAGS_OPENED) { 1357 spin_lock_irq(&pDevice->lock); 1358 KeybSetDefaultKey(&(pDevice->sKey), 1359 (unsigned long)(pDevice->byKeyIndex | (1 << 31)), 1360 pDevice->uKeyLength, 1361 NULL, 1362 pDevice->abyKey, 1363 KEY_CTL_WEP, 1364 pDevice->PortOffset, 1365 pDevice->byLocalID 1366); 1367 spin_unlock_irq(&pDevice->lock); 1368 } 1369 pDevice->byKeyIndex = (unsigned char)dwKeyIndex; 1370 pDevice->uKeyLength = wrq->length; 1371 pDevice->bTransmitKey = true; 1372 pDevice->bEncryptionEnable = true; 1373 pDevice->eEncryptionStatus = Ndis802_11Encryption1Enabled; 1374 1375 // Do we want to just set the transmit key index ? 1376 if (index < 4) { 1377 pDevice->byKeyIndex = index; 1378 } else if (!(wrq->flags & IW_ENCODE_MODE)) { 1379 rc = -EINVAL; 1380 return rc; 1381 } 1382 } 1383 // Read the flags 1384 if (wrq->flags & IW_ENCODE_DISABLED) { 1385 DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO "Disable WEP function\n"); 1386 pMgmt->bShareKeyAlgorithm = false; 1387 pDevice->bEncryptionEnable = false; 1388 pDevice->eEncryptionStatus = Ndis802_11EncryptionDisabled; 1389 if (pDevice->flags & DEVICE_FLAGS_OPENED) { 1390 spin_lock_irq(&pDevice->lock); 1391 for (uu=0; uu<MAX_KEY_TABLE; uu++) 1392 MACvDisableKeyEntry(pDevice->PortOffset, uu); 1393 spin_unlock_irq(&pDevice->lock); 1394 } 1395 } 1396*/ 1397 1398 if (wrq->flags & IW_ENCODE_RESTRICTED) { 1399 DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO "Enable WEP & ShareKey System\n"); 1400 pMgmt->bShareKeyAlgorithm = true; 1401 } 1402 if (wrq->flags & IW_ENCODE_OPEN) { 1403 DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO "Enable WEP & Open System\n"); 1404 pMgmt->bShareKeyAlgorithm = false; 1405 } 1406 return rc; 1407} 1408 1409/* 1410 * Wireless Handler : get encode mode 1411 */ 1412/* 1413 int iwctl_giwencode(struct net_device *dev, 1414 struct iw_request_info *info, 1415 struct iw_point *wrq, 1416 char *extra) { 1417 PSDevice pDevice = (PSDevice)netdev_priv(dev); 1418 PSMgmtObject pMgmt = &(pDevice->sMgmtObj); 1419 int rc = 0; 1420 char abyKey[WLAN_WEP232_KEYLEN]; 1421 unsigned int index = (unsigned int)(wrq->flags & IW_ENCODE_INDEX); 1422 PSKeyItem pKey = NULL; 1423 1424 DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO " SIOCGIWENCODE\n"); 1425//2007-0207-06,<Add> by EinsnLiu 1426//the key index in iwconfig is 1-4 when our driver is 0-3 1427//so it can't be used directly. 1428//if the index is 0,we should used the index set by driver. 1429if (index > WLAN_WEP_NKEYS) { 1430rc = -EINVAL; 1431return rc; 1432} 1433if (index<1) {//set default key 1434if (pDevice->byKeyIndex<WLAN_WEP_NKEYS) { 1435index=pDevice->byKeyIndex; 1436} 1437else index=0; 1438} else index--; 1439//End Add,Einsn 1440 1441memset(abyKey, 0, sizeof(abyKey)); 1442// Check encryption mode 1443wrq->flags = IW_ENCODE_NOKEY; 1444// Is WEP enabled ??? 1445if (pDevice->bEncryptionEnable) 1446wrq->flags |= IW_ENCODE_ENABLED; 1447else 1448wrq->flags |= IW_ENCODE_DISABLED; 1449 1450if (pMgmt->bShareKeyAlgorithm) 1451wrq->flags |= IW_ENCODE_RESTRICTED; 1452else 1453wrq->flags |= IW_ENCODE_OPEN; 1454 1455if (KeybGetKey(&(pDevice->sKey), pDevice->abyBroadcastAddr, (unsigned char)index , &pKey)) { 1456wrq->length = pKey->uKeyLength; 1457memcpy(abyKey, pKey->abyKey, pKey->uKeyLength); 1458//2007-0207-06,<Modify> by EinsnLiu 1459//only get key success need to copy data 1460//index should +1. 1461//there is not necessary to return -EINVAL when get key failed 1462//if return -EINVAL,the encryption item can't be display by the command "iwconfig". 1463wrq->flags |= index+1; 1464memcpy(extra, abyKey, WLAN_WEP232_KEYLEN); 1465} 1466 1467//else { 1468// rc = -EINVAL; 1469// return rc; 1470// } 1471 1472//End Modify,Einsn 1473 1474return 0; 1475} 1476*/ 1477 1478//2008-0409-06, <Add> by Einsn Liu 1479 1480int iwctl_giwencode(struct net_device *dev, 1481 struct iw_request_info *info, 1482 struct iw_point *wrq, 1483 char *extra) 1484{ 1485 PSDevice pDevice = (PSDevice)netdev_priv(dev); 1486 PSMgmtObject pMgmt = &(pDevice->sMgmtObj); 1487 char abyKey[WLAN_WEP232_KEYLEN]; 1488 1489 unsigned int index = (unsigned int)(wrq->flags & IW_ENCODE_INDEX); 1490 PSKeyItem pKey = NULL; 1491 1492 DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO " SIOCGIWENCODE\n"); 1493 1494 if (index > WLAN_WEP_NKEYS) { 1495 return -EINVAL; 1496 } 1497 if (index < 1) {//get default key 1498 if (pDevice->byKeyIndex < WLAN_WEP_NKEYS) { 1499 index = pDevice->byKeyIndex; 1500 } else 1501 index = 0; 1502 } else 1503 index--; 1504 1505 memset(abyKey, 0, WLAN_WEP232_KEYLEN); 1506 // Check encryption mode 1507 wrq->flags = IW_ENCODE_NOKEY; 1508 // Is WEP enabled ??? 1509 if (pDevice->bEncryptionEnable) 1510 wrq->flags |= IW_ENCODE_ENABLED; 1511 else 1512 wrq->flags |= IW_ENCODE_DISABLED; 1513 1514 if (pMgmt->bShareKeyAlgorithm) 1515 wrq->flags |= IW_ENCODE_RESTRICTED; 1516 else 1517 wrq->flags |= IW_ENCODE_OPEN; 1518 wrq->length = 0; 1519 1520 if ((index == 0) && (pDevice->eEncryptionStatus == Ndis802_11Encryption2Enabled || 1521 pDevice->eEncryptionStatus == Ndis802_11Encryption3Enabled)) {//get wpa pairwise key 1522 if (KeybGetKey(&(pDevice->sKey), pMgmt->abyCurrBSSID, 0xffffffff, &pKey)) { 1523 wrq->length = pKey->uKeyLength; 1524 memcpy(abyKey, pKey->abyKey, pKey->uKeyLength); 1525 memcpy(extra, abyKey, WLAN_WEP232_KEYLEN); 1526 } 1527 } else if (KeybGetKey(&(pDevice->sKey), pDevice->abyBroadcastAddr, (unsigned char)index , &pKey)) { 1528 wrq->length = pKey->uKeyLength; 1529 memcpy(abyKey, pKey->abyKey, pKey->uKeyLength); 1530 memcpy(extra, abyKey, WLAN_WEP232_KEYLEN); 1531 } 1532 1533 wrq->flags |= index+1; 1534 1535 return 0; 1536} 1537 1538/* 1539 * Wireless Handler : set power mode 1540 */ 1541int iwctl_siwpower(struct net_device *dev, 1542 struct iw_request_info *info, 1543 struct iw_param *wrq, 1544 char *extra) 1545{ 1546 PSDevice pDevice = (PSDevice)netdev_priv(dev); 1547 PSMgmtObject pMgmt = &(pDevice->sMgmtObj); 1548 int rc = 0; 1549 1550 DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO " SIOCSIWPOWER \n"); 1551 1552 if (!(pDevice->flags & DEVICE_FLAGS_OPENED)) { 1553 rc = -EINVAL; 1554 return rc; 1555 } 1556 1557 if (wrq->disabled) { 1558 pDevice->ePSMode = WMAC_POWER_CAM; 1559 PSvDisablePowerSaving(pDevice); 1560 return rc; 1561 } 1562 if ((wrq->flags & IW_POWER_TYPE) == IW_POWER_TIMEOUT) { 1563 pDevice->ePSMode = WMAC_POWER_FAST; 1564 PSvEnablePowerSaving((void *)pDevice, pMgmt->wListenInterval); 1565 1566 } else if ((wrq->flags & IW_POWER_TYPE) == IW_POWER_PERIOD) { 1567 pDevice->ePSMode = WMAC_POWER_FAST; 1568 PSvEnablePowerSaving((void *)pDevice, pMgmt->wListenInterval); 1569 } 1570 switch (wrq->flags & IW_POWER_MODE) { 1571 case IW_POWER_UNICAST_R: 1572 DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO " SIOCSIWPOWER: IW_POWER_UNICAST_R \n"); 1573 rc = -EINVAL; 1574 break; 1575 case IW_POWER_ALL_R: 1576 DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO " SIOCSIWPOWER: IW_POWER_ALL_R \n"); 1577 rc = -EINVAL; 1578 case IW_POWER_ON: 1579 DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO " SIOCSIWPOWER: IW_POWER_ON \n"); 1580 break; 1581 default: 1582 rc = -EINVAL; 1583 } 1584 1585 return rc; 1586} 1587 1588/* 1589 * Wireless Handler : get power mode 1590 */ 1591int iwctl_giwpower(struct net_device *dev, 1592 struct iw_request_info *info, 1593 struct iw_param *wrq, 1594 char *extra) 1595{ 1596 PSDevice pDevice = (PSDevice)netdev_priv(dev); 1597 PSMgmtObject pMgmt = &(pDevice->sMgmtObj); 1598 int mode = pDevice->ePSMode; 1599 1600 DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO " SIOCGIWPOWER \n"); 1601 1602 wrq->disabled = (mode == WMAC_POWER_CAM); 1603 if (wrq->disabled) 1604 return 0; 1605 1606 if ((wrq->flags & IW_POWER_TYPE) == IW_POWER_TIMEOUT) { 1607 wrq->value = (int)((pMgmt->wListenInterval * pMgmt->wCurrBeaconPeriod) << 10); 1608 wrq->flags = IW_POWER_TIMEOUT; 1609 } else { 1610 wrq->value = (int)((pMgmt->wListenInterval * pMgmt->wCurrBeaconPeriod) << 10); 1611 wrq->flags = IW_POWER_PERIOD; 1612 } 1613 wrq->flags |= IW_POWER_ALL_R; 1614 1615 return 0; 1616} 1617 1618/* 1619 * Wireless Handler : get Sensitivity 1620 */ 1621int iwctl_giwsens(struct net_device *dev, 1622 struct iw_request_info *info, 1623 struct iw_param *wrq, 1624 char *extra) 1625{ 1626 PSDevice pDevice = (PSDevice)netdev_priv(dev); 1627 long ldBm; 1628 1629 DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO " SIOCGIWSENS \n"); 1630 if (pDevice->bLinkPass == true) { 1631 RFvRSSITodBm(pDevice, (unsigned char)(pDevice->uCurrRSSI), &ldBm); 1632 wrq->value = ldBm; 1633 } else { 1634 wrq->value = 0; 1635 }; 1636 wrq->disabled = (wrq->value == 0); 1637 wrq->fixed = 1; 1638 1639 return 0; 1640} 1641 1642//2008-0409-07, <Add> by Einsn Liu 1643#ifdef WPA_SUPPLICANT_DRIVER_WEXT_SUPPORT 1644 1645int iwctl_siwauth(struct net_device *dev, 1646 struct iw_request_info *info, 1647 struct iw_param *wrq, 1648 char *extra) 1649{ 1650 PSDevice pDevice = (PSDevice)netdev_priv(dev); 1651 PSMgmtObject pMgmt = &(pDevice->sMgmtObj); 1652 int ret = 0; 1653 static int wpa_version = 0; //must be static to save the last value,einsn liu 1654 static int pairwise = 0; 1655 1656 DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO " SIOCSIWAUTH \n"); 1657 switch (wrq->flags & IW_AUTH_INDEX) { 1658 case IW_AUTH_WPA_VERSION: 1659 wpa_version = wrq->value; 1660 if (wrq->value == IW_AUTH_WPA_VERSION_DISABLED) { 1661 PRINT_K("iwctl_siwauth:set WPADEV to disable at 1??????\n"); 1662 //pDevice->bWPADevEnable = false; 1663 } else if (wrq->value == IW_AUTH_WPA_VERSION_WPA) { 1664 PRINT_K("iwctl_siwauth:set WPADEV to WPA1******\n"); 1665 } else { 1666 PRINT_K("iwctl_siwauth:set WPADEV to WPA2******\n"); 1667 } 1668 //pDevice->bWPASuppWextEnabled =true; 1669 break; 1670 case IW_AUTH_CIPHER_PAIRWISE: 1671 pairwise = wrq->value; 1672 if (pairwise == IW_AUTH_CIPHER_CCMP) { 1673 pDevice->eEncryptionStatus = Ndis802_11Encryption3Enabled; 1674 } else if (pairwise == IW_AUTH_CIPHER_TKIP) { 1675 pDevice->eEncryptionStatus = Ndis802_11Encryption2Enabled; 1676 } else if (pairwise == IW_AUTH_CIPHER_WEP40 || pairwise == IW_AUTH_CIPHER_WEP104) { 1677 pDevice->eEncryptionStatus = Ndis802_11Encryption1Enabled; 1678 } else if (pairwise == IW_AUTH_CIPHER_NONE) { 1679 //do nothing,einsn liu 1680 } else pDevice->eEncryptionStatus = Ndis802_11EncryptionDisabled; 1681 1682 break; 1683 case IW_AUTH_CIPHER_GROUP: 1684 if (wpa_version == IW_AUTH_WPA_VERSION_DISABLED) 1685 break; 1686 if (pairwise == IW_AUTH_CIPHER_NONE) { 1687 if (wrq->value == IW_AUTH_CIPHER_CCMP) { 1688 pDevice->eEncryptionStatus = Ndis802_11Encryption3Enabled; 1689 } else { 1690 pDevice->eEncryptionStatus = Ndis802_11Encryption2Enabled; 1691 } 1692 } 1693 break; 1694 case IW_AUTH_KEY_MGMT: 1695 1696 if (wpa_version == IW_AUTH_WPA_VERSION_WPA2) { 1697 if (wrq->value == IW_AUTH_KEY_MGMT_PSK) 1698 pMgmt->eAuthenMode = WMAC_AUTH_WPA2PSK; 1699 else pMgmt->eAuthenMode = WMAC_AUTH_WPA2; 1700 } else if (wpa_version == IW_AUTH_WPA_VERSION_WPA) { 1701 if (wrq->value == 0) { 1702 pMgmt->eAuthenMode = WMAC_AUTH_WPANONE; 1703 } else if (wrq->value == IW_AUTH_KEY_MGMT_PSK) 1704 pMgmt->eAuthenMode = WMAC_AUTH_WPAPSK; 1705 else pMgmt->eAuthenMode = WMAC_AUTH_WPA; 1706 } 1707 1708 break; 1709 case IW_AUTH_TKIP_COUNTERMEASURES: 1710 break; /* FIXME */ 1711 case IW_AUTH_DROP_UNENCRYPTED: 1712 break; 1713 case IW_AUTH_80211_AUTH_ALG: 1714 if (wrq->value == IW_AUTH_ALG_OPEN_SYSTEM) { 1715 pMgmt->bShareKeyAlgorithm = false; 1716 } else if (wrq->value == IW_AUTH_ALG_SHARED_KEY) { 1717 pMgmt->bShareKeyAlgorithm = true; 1718 } 1719 break; 1720 case IW_AUTH_WPA_ENABLED: 1721 //pDevice->bWPADevEnable = !! wrq->value; 1722 break; 1723 case IW_AUTH_RX_UNENCRYPTED_EAPOL: 1724 break; 1725 case IW_AUTH_ROAMING_CONTROL: 1726 ret = -EOPNOTSUPP; 1727 break; 1728 case IW_AUTH_PRIVACY_INVOKED: 1729 pDevice->bEncryptionEnable = !!wrq->value; 1730 if (pDevice->bEncryptionEnable == false) { 1731 wpa_version = 0; 1732 pairwise = 0; 1733 pDevice->eEncryptionStatus = Ndis802_11EncryptionDisabled; 1734 pMgmt->bShareKeyAlgorithm = false; 1735 pMgmt->eAuthenMode = false; 1736 //pDevice->bWPADevEnable = false; 1737 } 1738 1739 break; 1740 default: 1741 ret = -EOPNOTSUPP; 1742 break; 1743 } 1744/* 1745 DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO "wpa_version = %d\n",wpa_version); 1746 DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO "pairwise = %d\n",pairwise); 1747 DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO "pDevice->eEncryptionStatus = %d\n",pDevice->eEncryptionStatus); 1748 DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO "pMgmt->eAuthenMode = %d\n",pMgmt->eAuthenMode); 1749 DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO "pMgmt->bShareKeyAlgorithm = %s\n",pMgmt->bShareKeyAlgorithm?"true":"false"); 1750 DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO "pDevice->bEncryptionEnable = %s\n",pDevice->bEncryptionEnable?"true":"false"); 1751 DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO "pDevice->bWPADevEnable = %s\n",pDevice->bWPADevEnable?"true":"false"); 1752*/ 1753 return ret; 1754} 1755 1756int iwctl_giwauth(struct net_device *dev, 1757 struct iw_request_info *info, 1758 struct iw_param *wrq, 1759 char *extra) 1760{ 1761 return -EOPNOTSUPP; 1762} 1763 1764int iwctl_siwgenie(struct net_device *dev, 1765 struct iw_request_info *info, 1766 struct iw_point *wrq, 1767 char *extra) 1768{ 1769 PSDevice pDevice = (PSDevice)netdev_priv(dev); 1770 PSMgmtObject pMgmt = &(pDevice->sMgmtObj); 1771 int ret = 0; 1772 1773 if (wrq->length) { 1774 if ((wrq->length < 2) || (extra[1]+2 != wrq->length)) { 1775 ret = -EINVAL; 1776 goto out; 1777 } 1778 if (wrq->length > MAX_WPA_IE_LEN) { 1779 ret = -ENOMEM; 1780 goto out; 1781 } 1782 memset(pMgmt->abyWPAIE, 0, MAX_WPA_IE_LEN); 1783 if (copy_from_user(pMgmt->abyWPAIE, extra, wrq->length)) { 1784 ret = -EFAULT; 1785 goto out; 1786 } 1787 pMgmt->wWPAIELen = wrq->length; 1788 } else { 1789 memset(pMgmt->abyWPAIE, 0, MAX_WPA_IE_LEN); 1790 pMgmt->wWPAIELen = 0; 1791 } 1792 1793out://not completely ...not necessary in wpa_supplicant 0.5.8 1794 return ret; 1795} 1796 1797int iwctl_giwgenie(struct net_device *dev, 1798 struct iw_request_info *info, 1799 struct iw_point *wrq, 1800 char *extra) 1801{ 1802 PSDevice pDevice = (PSDevice)netdev_priv(dev); 1803 PSMgmtObject pMgmt = &(pDevice->sMgmtObj); 1804 int ret = 0; 1805 int space = wrq->length; 1806 1807 wrq->length = 0; 1808 if (pMgmt->wWPAIELen > 0) { 1809 wrq->length = pMgmt->wWPAIELen; 1810 if (pMgmt->wWPAIELen <= space) { 1811 if (copy_to_user(extra, pMgmt->abyWPAIE, pMgmt->wWPAIELen)) { 1812 ret = -EFAULT; 1813 } 1814 } else 1815 ret = -E2BIG; 1816 } 1817 1818 return ret; 1819} 1820 1821int iwctl_siwencodeext(struct net_device *dev, 1822 struct iw_request_info *info, 1823 struct iw_point *wrq, 1824 char *extra) 1825{ 1826 PSDevice pDevice = (PSDevice)netdev_priv(dev); 1827 struct iw_encode_ext *ext = (struct iw_encode_ext *)extra; 1828 struct viawget_wpa_param *param = NULL; 1829//original member 1830 wpa_alg alg_name; 1831 u8 addr[6]; 1832 int key_idx, set_tx = 0; 1833 u8 seq[IW_ENCODE_SEQ_MAX_SIZE]; 1834 u8 key[64]; 1835 size_t seq_len = 0, key_len = 0; 1836// 1837 // int ii; 1838 u8 *buf; 1839 size_t blen; 1840 u8 key_array[64]; 1841 int ret = 0; 1842 1843 PRINT_K("SIOCSIWENCODEEXT...... \n"); 1844 1845 blen = sizeof(*param); 1846 buf = kmalloc((int)blen, (int)GFP_KERNEL); 1847 if (buf == NULL) 1848 return -ENOMEM; 1849 memset(buf, 0, blen); 1850 param = (struct viawget_wpa_param *)buf; 1851 1852//recover alg_name 1853 switch (ext->alg) { 1854 case IW_ENCODE_ALG_NONE: 1855 alg_name = WPA_ALG_NONE; 1856 break; 1857 case IW_ENCODE_ALG_WEP: 1858 alg_name = WPA_ALG_WEP; 1859 break; 1860 case IW_ENCODE_ALG_TKIP: 1861 alg_name = WPA_ALG_TKIP; 1862 break; 1863 case IW_ENCODE_ALG_CCMP: 1864 alg_name = WPA_ALG_CCMP; 1865 break; 1866 default: 1867 PRINT_K("Unknown alg = %d\n", ext->alg); 1868 ret = -ENOMEM; 1869 goto error; 1870 } 1871//recover addr 1872 memcpy(addr, ext->addr.sa_data, ETH_ALEN); 1873//recover key_idx 1874 key_idx = (wrq->flags&IW_ENCODE_INDEX) - 1; 1875//recover set_tx 1876 if (ext->ext_flags & IW_ENCODE_EXT_SET_TX_KEY) 1877 set_tx = 1; 1878//recover seq,seq_len 1879 if (ext->ext_flags & IW_ENCODE_EXT_RX_SEQ_VALID) { 1880 seq_len = IW_ENCODE_SEQ_MAX_SIZE; 1881 memcpy(seq, ext->rx_seq, seq_len); 1882 } 1883//recover key,key_len 1884 if (ext->key_len) { 1885 key_len = ext->key_len; 1886 memcpy(key, &ext->key[0], key_len); 1887 } 1888 1889 memset(key_array, 0, 64); 1890 if (key_len > 0) { 1891 memcpy(key_array, key, key_len); 1892 if (key_len == 32) { 1893 // notice ! the oder 1894 memcpy(&key_array[16], &key[24], 8); 1895 memcpy(&key_array[24], &key[16], 8); 1896 } 1897 } 1898 1899/**************Translate iw_encode_ext to viawget_wpa_param****************/ 1900 memcpy(param->addr, addr, ETH_ALEN); 1901 param->u.wpa_key.alg_name = (int)alg_name; 1902 param->u.wpa_key.set_tx = set_tx; 1903 param->u.wpa_key.key_index = key_idx; 1904 param->u.wpa_key.key_len = key_len; 1905 param->u.wpa_key.key = (u8 *)key_array; 1906 param->u.wpa_key.seq = (u8 *)seq; 1907 param->u.wpa_key.seq_len = seq_len; 1908 1909//****set if current action is Network Manager count?? 1910//****this method is so foolish,but there is no other way??? 1911 if (param->u.wpa_key.alg_name == WPA_ALG_NONE) { 1912 if (param->u.wpa_key.key_index == 0) { 1913 pDevice->bwextcount++; 1914 } 1915 if ((pDevice->bwextcount == 1) && (param->u.wpa_key.key_index == 1)) { 1916 pDevice->bwextcount++; 1917 } 1918 if ((pDevice->bwextcount == 2) && (param->u.wpa_key.key_index == 2)) { 1919 pDevice->bwextcount++; 1920 } 1921 if ((pDevice->bwextcount == 3) && (param->u.wpa_key.key_index == 3)) { 1922 pDevice->bwextcount++; 1923 } 1924 } 1925 if (pDevice->bwextcount == 4) { 1926 printk("SIOCSIWENCODEEXT:Enable WPA WEXT SUPPORT!!!!!\n"); 1927 pDevice->bwextcount = 0; 1928 pDevice->bWPASuppWextEnabled = true; 1929 } 1930//****** 1931 1932 spin_lock_irq(&pDevice->lock); 1933 ret = wpa_set_keys(pDevice, param, true); 1934 spin_unlock_irq(&pDevice->lock); 1935 1936error: 1937 kfree(param); 1938 return ret; 1939} 1940 1941int iwctl_giwencodeext(struct net_device *dev, 1942 struct iw_request_info *info, 1943 struct iw_point *wrq, 1944 char *extra) 1945{ 1946 return -EOPNOTSUPP; 1947} 1948 1949int iwctl_siwmlme(struct net_device *dev, 1950 struct iw_request_info *info, 1951 struct iw_point *wrq, 1952 char *extra) 1953{ 1954 PSDevice pDevice = (PSDevice)netdev_priv(dev); 1955 PSMgmtObject pMgmt = &(pDevice->sMgmtObj); 1956 struct iw_mlme *mlme = (struct iw_mlme *)extra; 1957 //u16 reason = cpu_to_le16(mlme->reason_code); 1958 int ret = 0; 1959 1960 if (memcmp(pMgmt->abyCurrBSSID, mlme->addr.sa_data, ETH_ALEN)) { 1961 ret = -EINVAL; 1962 return ret; 1963 } 1964 switch (mlme->cmd) { 1965 case IW_MLME_DEAUTH: 1966 //this command seems to be not complete,please test it --einsnliu 1967 //bScheduleCommand((void *) pDevice, WLAN_CMD_DEAUTH, (unsigned char *)&reason); 1968 break; 1969 case IW_MLME_DISASSOC: 1970 if (pDevice->bLinkPass == true) { 1971 printk("iwctl_siwmlme--->send DISASSOCIATE\n"); 1972 //clear related flags 1973 memset(pMgmt->abyDesireBSSID, 0xFF, 6); 1974 KeyvInitTable(&pDevice->sKey, pDevice->PortOffset); 1975 bScheduleCommand((void *)pDevice, WLAN_CMD_DISASSOCIATE, NULL); 1976 } 1977 break; 1978 default: 1979 ret = -EOPNOTSUPP; 1980 } 1981 1982 return ret; 1983} 1984 1985#endif 1986 1987/*------------------------------------------------------------------*/ 1988/* 1989 * Structures to export the Wireless Handlers 1990 */ 1991 1992/* 1993 static const iw_handler iwctl_handler[] = 1994 { 1995 (iw_handler) iwctl_commit, // SIOCSIWCOMMIT 1996 (iw_handler) iwctl_giwname, // SIOCGIWNAME 1997 (iw_handler) NULL, // SIOCSIWNWID 1998 (iw_handler) NULL, // SIOCGIWNWID 1999 (iw_handler) iwctl_siwfreq, // SIOCSIWFREQ 2000 (iw_handler) iwctl_giwfreq, // SIOCGIWFREQ 2001 (iw_handler) iwctl_siwmode, // SIOCSIWMODE 2002 (iw_handler) iwctl_giwmode, // SIOCGIWMODE 2003 (iw_handler) NULL, // SIOCSIWSENS 2004 (iw_handler) iwctl_giwsens, // SIOCGIWSENS 2005 (iw_handler) NULL, // SIOCSIWRANGE 2006 (iw_handler) iwctl_giwrange, // SIOCGIWRANGE 2007 (iw_handler) NULL, // SIOCSIWPRIV 2008 (iw_handler) NULL, // SIOCGIWPRIV 2009 (iw_handler) NULL, // SIOCSIWSTATS 2010 (iw_handler) NULL, // SIOCGIWSTATS 2011 (iw_handler) NULL, // SIOCSIWSPY 2012 (iw_handler) NULL, // SIOCGIWSPY 2013 (iw_handler) NULL, // -- hole -- 2014 (iw_handler) NULL, // -- hole -- 2015 (iw_handler) iwctl_siwap, // SIOCSIWAP 2016 (iw_handler) iwctl_giwap, // SIOCGIWAP 2017 (iw_handler) NULL, // -- hole -- 0x16 2018 (iw_handler) iwctl_giwaplist, // SIOCGIWAPLIST 2019 (iw_handler) iwctl_siwscan, // SIOCSIWSCAN 2020 (iw_handler) iwctl_giwscan, // SIOCGIWSCAN 2021 (iw_handler) iwctl_siwessid, // SIOCSIWESSID 2022 (iw_handler) iwctl_giwessid, // SIOCGIWESSID 2023 (iw_handler) NULL, // SIOCSIWNICKN 2024 (iw_handler) NULL, // SIOCGIWNICKN 2025 (iw_handler) NULL, // -- hole -- 2026 (iw_handler) NULL, // -- hole -- 2027 (iw_handler) iwctl_siwrate, // SIOCSIWRATE 0x20 2028 (iw_handler) iwctl_giwrate, // SIOCGIWRATE 2029 (iw_handler) iwctl_siwrts, // SIOCSIWRTS 2030 (iw_handler) iwctl_giwrts, // SIOCGIWRTS 2031 (iw_handler) iwctl_siwfrag, // SIOCSIWFRAG 2032 (iw_handler) iwctl_giwfrag, // SIOCGIWFRAG 2033 (iw_handler) NULL, // SIOCSIWTXPOW 2034 (iw_handler) NULL, // SIOCGIWTXPOW 2035 (iw_handler) iwctl_siwretry, // SIOCSIWRETRY 2036 (iw_handler) iwctl_giwretry, // SIOCGIWRETRY 2037 (iw_handler) iwctl_siwencode, // SIOCSIWENCODE 2038 (iw_handler) iwctl_giwencode, // SIOCGIWENCODE 2039 (iw_handler) iwctl_siwpower, // SIOCSIWPOWER 2040 (iw_handler) iwctl_giwpower, // SIOCGIWPOWER 2041 (iw_handler) NULL, // -- hole -- 2042 (iw_handler) NULL, // -- hole -- 2043 (iw_handler) iwctl_siwgenie, // SIOCSIWGENIE 2044 (iw_handler) iwctl_giwgenie, // SIOCGIWGENIE 2045 (iw_handler) iwctl_siwauth, // SIOCSIWAUTH 2046 (iw_handler) iwctl_giwauth, // SIOCGIWAUTH 2047 (iw_handler) iwctl_siwencodeext, // SIOCSIWENCODEEXT 2048 (iw_handler) iwctl_giwencodeext, // SIOCGIWENCODEEXT 2049 (iw_handler) NULL, // SIOCSIWPMKSA 2050 (iw_handler) NULL, // -- hole -- 2051 2052 }; 2053*/ 2054 2055static const iw_handler iwctl_handler[] = 2056{ 2057 (iw_handler) iwctl_commit, // SIOCSIWCOMMIT 2058 (iw_handler) NULL, // SIOCGIWNAME 2059 (iw_handler) NULL, // SIOCSIWNWID 2060 (iw_handler) NULL, // SIOCGIWNWID 2061 (iw_handler) NULL, // SIOCSIWFREQ 2062 (iw_handler) NULL, // SIOCGIWFREQ 2063 (iw_handler) NULL, // SIOCSIWMODE 2064 (iw_handler) NULL, // SIOCGIWMODE 2065 (iw_handler) NULL, // SIOCSIWSENS 2066 (iw_handler) NULL, // SIOCGIWSENS 2067 (iw_handler) NULL, // SIOCSIWRANGE 2068 (iw_handler) iwctl_giwrange, // SIOCGIWRANGE 2069 (iw_handler) NULL, // SIOCSIWPRIV 2070 (iw_handler) NULL, // SIOCGIWPRIV 2071 (iw_handler) NULL, // SIOCSIWSTATS 2072 (iw_handler) NULL, // SIOCGIWSTATS 2073 (iw_handler) NULL, // SIOCSIWSPY 2074 (iw_handler) NULL, // SIOCGIWSPY 2075 (iw_handler) NULL, // -- hole -- 2076 (iw_handler) NULL, // -- hole -- 2077 (iw_handler) NULL, // SIOCSIWAP 2078 (iw_handler) NULL, // SIOCGIWAP 2079 (iw_handler) NULL, // -- hole -- 0x16 2080 (iw_handler) NULL, // SIOCGIWAPLIST 2081 (iw_handler) iwctl_siwscan, // SIOCSIWSCAN 2082 (iw_handler) iwctl_giwscan, // SIOCGIWSCAN 2083 (iw_handler) NULL, // SIOCSIWESSID 2084 (iw_handler) NULL, // SIOCGIWESSID 2085 (iw_handler) NULL, // SIOCSIWNICKN 2086 (iw_handler) NULL, // SIOCGIWNICKN 2087 (iw_handler) NULL, // -- hole -- 2088 (iw_handler) NULL, // -- hole -- 2089 (iw_handler) NULL, // SIOCSIWRATE 0x20 2090 (iw_handler) NULL, // SIOCGIWRATE 2091 (iw_handler) NULL, // SIOCSIWRTS 2092 (iw_handler) NULL, // SIOCGIWRTS 2093 (iw_handler) NULL, // SIOCSIWFRAG 2094 (iw_handler) NULL, // SIOCGIWFRAG 2095 (iw_handler) NULL, // SIOCSIWTXPOW 2096 (iw_handler) NULL, // SIOCGIWTXPOW 2097 (iw_handler) NULL, // SIOCSIWRETRY 2098 (iw_handler) NULL, // SIOCGIWRETRY 2099 (iw_handler) NULL, // SIOCSIWENCODE 2100 (iw_handler) NULL, // SIOCGIWENCODE 2101 (iw_handler) NULL, // SIOCSIWPOWER 2102 (iw_handler) NULL, // SIOCGIWPOWER 2103 2104//2008-0409-07, <Add> by Einsn Liu 2105 (iw_handler) NULL, // -- hole -- 2106 (iw_handler) NULL, // -- hole -- 2107 (iw_handler) NULL, // SIOCSIWGENIE 2108 (iw_handler) NULL, // SIOCGIWGENIE 2109 (iw_handler) NULL, // SIOCSIWAUTH 2110 (iw_handler) NULL, // SIOCGIWAUTH 2111 (iw_handler) NULL, // SIOCSIWENCODEEXT 2112 (iw_handler) NULL, // SIOCGIWENCODEEXT 2113 (iw_handler) NULL, // SIOCSIWPMKSA 2114 (iw_handler) NULL, // -- hole -- 2115}; 2116 2117static const iw_handler iwctl_private_handler[] = 2118{ 2119 NULL, // SIOCIWFIRSTPRIV 2120}; 2121 2122struct iw_priv_args iwctl_private_args[] = { 2123 { IOCTL_CMD_SET, 2124 IW_PRIV_TYPE_CHAR | 1024, 0, 2125 "set"}, 2126}; 2127 2128const struct iw_handler_def iwctl_handler_def = 2129{ 2130 .get_wireless_stats = &iwctl_get_wireless_stats, 2131 .num_standard = sizeof(iwctl_handler)/sizeof(iw_handler), 2132// .num_private = sizeof(iwctl_private_handler)/sizeof(iw_handler), 2133// .num_private_args = sizeof(iwctl_private_args)/sizeof(struct iw_priv_args), 2134 .num_private = 0, 2135 .num_private_args = 0, 2136 .standard = (iw_handler *)iwctl_handler, 2137// .private = (iw_handler *) iwctl_private_handler, 2138// .private_args = (struct iw_priv_args *)iwctl_private_args, 2139 .private = NULL, 2140 .private_args = NULL, 2141};