1/* IEEE 802.11 SoftMAC layer 2 * Copyright (c) 2005 Andrea Merello <andreamrl@tiscali.it> 3 * 4 * Mostly extracted from the rtl8180-sa2400 driver for the 5 * in-kernel generic ieee802.11 stack. 6 * 7 * Few lines might be stolen from other part of the ieee80211 8 * stack. Copyright who own it's copyright 9 * 10 * WPA code stolen from the ipw2200 driver. 11 * Copyright who own it's copyright. 12 * 13 * released under the GPL 14 */ 15 16 17#include "ieee80211.h" 18 19#include <linux/random.h> 20#include <linux/delay.h> 21#include <linux/slab.h> 22#include <linux/version.h> 23#include <asm/uaccess.h> 24 25#include "dot11d.h" 26u8 rsn_authen_cipher_suite[16][4] = { 27 {0x00,0x0F,0xAC,0x00}, //Use group key, //Reserved 28 {0x00,0x0F,0xAC,0x01}, //WEP-40 //RSNA default 29 {0x00,0x0F,0xAC,0x02}, //TKIP //NONE //{used just as default} 30 {0x00,0x0F,0xAC,0x03}, //WRAP-historical 31 {0x00,0x0F,0xAC,0x04}, //CCMP 32 {0x00,0x0F,0xAC,0x05}, //WEP-104 33}; 34 35short ieee80211_is_54g(struct ieee80211_network net) 36{ 37 return ((net.rates_ex_len > 0) || (net.rates_len > 4)); 38} 39 40short ieee80211_is_shortslot(struct ieee80211_network net) 41{ 42 return (net.capability & WLAN_CAPABILITY_SHORT_SLOT); 43} 44 45/* returns the total length needed for pleacing the RATE MFIE 46 * tag and the EXTENDED RATE MFIE tag if needed. 47 * It encludes two bytes per tag for the tag itself and its len 48 */ 49unsigned int ieee80211_MFIE_rate_len(struct ieee80211_device *ieee) 50{ 51 unsigned int rate_len = 0; 52 53 if (ieee->modulation & IEEE80211_CCK_MODULATION) 54 rate_len = IEEE80211_CCK_RATE_LEN + 2; 55 56 if (ieee->modulation & IEEE80211_OFDM_MODULATION) 57 58 rate_len += IEEE80211_OFDM_RATE_LEN + 2; 59 60 return rate_len; 61} 62 63/* pleace the MFIE rate, tag to the memory (double) poined. 64 * Then it updates the pointer so that 65 * it points after the new MFIE tag added. 66 */ 67void ieee80211_MFIE_Brate(struct ieee80211_device *ieee, u8 **tag_p) 68{ 69 u8 *tag = *tag_p; 70 71 if (ieee->modulation & IEEE80211_CCK_MODULATION){ 72 *tag++ = MFIE_TYPE_RATES; 73 *tag++ = 4; 74 *tag++ = IEEE80211_BASIC_RATE_MASK | IEEE80211_CCK_RATE_1MB; 75 *tag++ = IEEE80211_BASIC_RATE_MASK | IEEE80211_CCK_RATE_2MB; 76 *tag++ = IEEE80211_BASIC_RATE_MASK | IEEE80211_CCK_RATE_5MB; 77 *tag++ = IEEE80211_BASIC_RATE_MASK | IEEE80211_CCK_RATE_11MB; 78 } 79 80 /* We may add an option for custom rates that specific HW might support */ 81 *tag_p = tag; 82} 83 84void ieee80211_MFIE_Grate(struct ieee80211_device *ieee, u8 **tag_p) 85{ 86 u8 *tag = *tag_p; 87 88 if (ieee->modulation & IEEE80211_OFDM_MODULATION){ 89 90 *tag++ = MFIE_TYPE_RATES_EX; 91 *tag++ = 8; 92 *tag++ = IEEE80211_BASIC_RATE_MASK | IEEE80211_OFDM_RATE_6MB; 93 *tag++ = IEEE80211_BASIC_RATE_MASK | IEEE80211_OFDM_RATE_9MB; 94 *tag++ = IEEE80211_BASIC_RATE_MASK | IEEE80211_OFDM_RATE_12MB; 95 *tag++ = IEEE80211_BASIC_RATE_MASK | IEEE80211_OFDM_RATE_18MB; 96 *tag++ = IEEE80211_BASIC_RATE_MASK | IEEE80211_OFDM_RATE_24MB; 97 *tag++ = IEEE80211_BASIC_RATE_MASK | IEEE80211_OFDM_RATE_36MB; 98 *tag++ = IEEE80211_BASIC_RATE_MASK | IEEE80211_OFDM_RATE_48MB; 99 *tag++ = IEEE80211_BASIC_RATE_MASK | IEEE80211_OFDM_RATE_54MB; 100 101 } 102 103 /* We may add an option for custom rates that specific HW might support */ 104 *tag_p = tag; 105} 106 107 108void ieee80211_WMM_Info(struct ieee80211_device *ieee, u8 **tag_p) { 109 u8 *tag = *tag_p; 110 111 *tag++ = MFIE_TYPE_GENERIC; //0 112 *tag++ = 7; 113 *tag++ = 0x00; 114 *tag++ = 0x50; 115 *tag++ = 0xf2; 116 *tag++ = 0x02;//5 117 *tag++ = 0x00; 118 *tag++ = 0x01; 119#ifdef SUPPORT_USPD 120 if(ieee->current_network.wmm_info & 0x80) { 121 *tag++ = 0x0f|MAX_SP_Len; 122 } else { 123 *tag++ = MAX_SP_Len; 124 } 125#else 126 *tag++ = MAX_SP_Len; 127#endif 128 *tag_p = tag; 129} 130 131void ieee80211_TURBO_Info(struct ieee80211_device *ieee, u8 **tag_p) { 132 u8 *tag = *tag_p; 133 134 *tag++ = MFIE_TYPE_GENERIC; //0 135 *tag++ = 7; 136 *tag++ = 0x00; 137 *tag++ = 0xe0; 138 *tag++ = 0x4c; 139 *tag++ = 0x01;//5 140 *tag++ = 0x02; 141 *tag++ = 0x11; 142 *tag++ = 0x00; 143 144 *tag_p = tag; 145 printk(KERN_ALERT "This is enable turbo mode IE process\n"); 146} 147 148void enqueue_mgmt(struct ieee80211_device *ieee, struct sk_buff *skb) 149{ 150 int nh; 151 nh = (ieee->mgmt_queue_head +1) % MGMT_QUEUE_NUM; 152 153/* 154 * if the queue is full but we have newer frames then 155 * just overwrites the oldest. 156 * 157 * if (nh == ieee->mgmt_queue_tail) 158 * return -1; 159 */ 160 ieee->mgmt_queue_head = nh; 161 ieee->mgmt_queue_ring[nh] = skb; 162 163 //return 0; 164} 165 166struct sk_buff *dequeue_mgmt(struct ieee80211_device *ieee) 167{ 168 struct sk_buff *ret; 169 170 if(ieee->mgmt_queue_tail == ieee->mgmt_queue_head) 171 return NULL; 172 173 ret = ieee->mgmt_queue_ring[ieee->mgmt_queue_tail]; 174 175 ieee->mgmt_queue_tail = 176 (ieee->mgmt_queue_tail+1) % MGMT_QUEUE_NUM; 177 178 return ret; 179} 180 181void init_mgmt_queue(struct ieee80211_device *ieee) 182{ 183 ieee->mgmt_queue_tail = ieee->mgmt_queue_head = 0; 184} 185 186 187void ieee80211_sta_wakeup(struct ieee80211_device *ieee, short nl); 188 189inline void softmac_mgmt_xmit(struct sk_buff *skb, struct ieee80211_device *ieee) 190{ 191 unsigned long flags; 192 short single = ieee->softmac_features & IEEE_SOFTMAC_SINGLE_QUEUE; 193 struct ieee80211_hdr_3addr *header= 194 (struct ieee80211_hdr_3addr *) skb->data; 195 196 197 spin_lock_irqsave(&ieee->lock, flags); 198 199 /* called with 2nd param 0, no mgmt lock required */ 200 ieee80211_sta_wakeup(ieee,0); 201 202 if(single){ 203 if(ieee->queue_stop){ 204 205 enqueue_mgmt(ieee,skb); 206 }else{ 207 header->seq_ctrl = cpu_to_le16(ieee->seq_ctrl[0]<<4); 208 209 if (ieee->seq_ctrl[0] == 0xFFF) 210 ieee->seq_ctrl[0] = 0; 211 else 212 ieee->seq_ctrl[0]++; 213 214 /* avoid watchdog triggers */ 215 ieee->dev->trans_start = jiffies; 216 ieee->softmac_data_hard_start_xmit(skb,ieee->dev,ieee->basic_rate); 217 } 218 219 spin_unlock_irqrestore(&ieee->lock, flags); 220 }else{ 221 spin_unlock_irqrestore(&ieee->lock, flags); 222 spin_lock_irqsave(&ieee->mgmt_tx_lock, flags); 223 224 header->seq_ctrl = cpu_to_le16(ieee->seq_ctrl[0] << 4); 225 226 if (ieee->seq_ctrl[0] == 0xFFF) 227 ieee->seq_ctrl[0] = 0; 228 else 229 ieee->seq_ctrl[0]++; 230 231 /* avoid watchdog triggers */ 232 ieee->dev->trans_start = jiffies; 233 ieee->softmac_hard_start_xmit(skb,ieee->dev); 234 235 spin_unlock_irqrestore(&ieee->mgmt_tx_lock, flags); 236 } 237} 238 239 240inline void softmac_ps_mgmt_xmit(struct sk_buff *skb, struct ieee80211_device *ieee) 241{ 242 243 short single = ieee->softmac_features & IEEE_SOFTMAC_SINGLE_QUEUE; 244 struct ieee80211_hdr_3addr *header = 245 (struct ieee80211_hdr_3addr *) skb->data; 246 247 248 if(single){ 249 250 header->seq_ctrl = cpu_to_le16(ieee->seq_ctrl[0] << 4); 251 252 if (ieee->seq_ctrl[0] == 0xFFF) 253 ieee->seq_ctrl[0] = 0; 254 else 255 ieee->seq_ctrl[0]++; 256 257 /* avoid watchdog triggers */ 258 ieee->dev->trans_start = jiffies; 259 ieee->softmac_data_hard_start_xmit(skb,ieee->dev,ieee->basic_rate); 260 261 }else{ 262 263 header->seq_ctrl = cpu_to_le16(ieee->seq_ctrl[0] << 4); 264 265 if (ieee->seq_ctrl[0] == 0xFFF) 266 ieee->seq_ctrl[0] = 0; 267 else 268 ieee->seq_ctrl[0]++; 269 270 /* avoid watchdog triggers */ 271 ieee->dev->trans_start = jiffies; 272 ieee->softmac_hard_start_xmit(skb,ieee->dev); 273 274 } 275// dev_kfree_skb_any(skb);//edit by thomas 276} 277//by amy for power save 278inline struct sk_buff *ieee80211_disassociate_skb( 279 struct ieee80211_network *beacon, 280 struct ieee80211_device *ieee, 281 u8 asRsn) 282{ 283 struct sk_buff *skb; 284 struct ieee80211_disassoc_frame *disass; 285 286 skb = dev_alloc_skb(sizeof(struct ieee80211_disassoc_frame)); 287 if (!skb) 288 return NULL; 289 290 disass = (struct ieee80211_disassoc_frame *) skb_put(skb,sizeof(struct ieee80211_disassoc_frame)); 291 disass->header.frame_control = cpu_to_le16(IEEE80211_STYPE_DISASSOC); 292 disass->header.duration_id = 0; 293 294 memcpy(disass->header.addr1, beacon->bssid, ETH_ALEN); 295 memcpy(disass->header.addr2, ieee->dev->dev_addr, ETH_ALEN); 296 memcpy(disass->header.addr3, beacon->bssid, ETH_ALEN); 297 298 disass->reasoncode = asRsn; 299 return skb; 300} 301void 302SendDisassociation( 303 struct ieee80211_device *ieee, 304 u8* asSta, 305 u8 asRsn 306) 307{ 308 struct ieee80211_network *beacon = &ieee->current_network; 309 struct sk_buff *skb; 310 skb = ieee80211_disassociate_skb(beacon,ieee,asRsn); 311 if (skb){ 312 softmac_mgmt_xmit(skb, ieee); 313 //dev_kfree_skb_any(skb);//edit by thomas 314 } 315} 316 317//by amy for power save 318inline struct sk_buff *ieee80211_probe_req(struct ieee80211_device *ieee) 319{ 320 unsigned int len,rate_len; 321 u8 *tag; 322 struct sk_buff *skb; 323 struct ieee80211_probe_request *req; 324 325 len = ieee->current_network.ssid_len; 326 327 rate_len = ieee80211_MFIE_rate_len(ieee); 328 329 skb = dev_alloc_skb(sizeof(struct ieee80211_probe_request) + 330 2 + len + rate_len); 331 if (!skb) 332 return NULL; 333 334 req = (struct ieee80211_probe_request *) skb_put(skb,sizeof(struct ieee80211_probe_request)); 335 req->header.frame_ctl = cpu_to_le16(IEEE80211_STYPE_PROBE_REQ); 336 req->header.duration_id = 0; 337 338 memset(req->header.addr1, 0xff, ETH_ALEN); 339 memcpy(req->header.addr2, ieee->dev->dev_addr, ETH_ALEN); 340 memset(req->header.addr3, 0xff, ETH_ALEN); 341 342 tag = (u8 *) skb_put(skb,len+2+rate_len); 343 344 *tag++ = MFIE_TYPE_SSID; 345 *tag++ = len; 346 memcpy(tag, ieee->current_network.ssid, len); 347 tag += len; 348 ieee80211_MFIE_Brate(ieee,&tag); 349 ieee80211_MFIE_Grate(ieee,&tag); 350 351 return skb; 352} 353 354struct sk_buff *ieee80211_get_beacon_(struct ieee80211_device *ieee); 355 356void ext_ieee80211_send_beacon_wq(struct ieee80211_device *ieee) 357{ 358 struct sk_buff *skb; 359 360 //unsigned long flags; 361 362 skb = ieee80211_get_beacon_(ieee); 363 364 if (skb){ 365 softmac_mgmt_xmit(skb, ieee); 366 ieee->softmac_stats.tx_beacons++; 367 dev_kfree_skb_any(skb);//edit by thomas 368 } 369 370 371 //printk(KERN_WARNING "[1] beacon sending!\n"); 372 ieee->beacon_timer.expires = jiffies + 373 (MSECS( ieee->current_network.beacon_interval -5)); 374 375 //spin_lock_irqsave(&ieee->beacon_lock,flags); 376 if(ieee->beacon_txing) 377 add_timer(&ieee->beacon_timer); 378 //spin_unlock_irqrestore(&ieee->beacon_lock,flags); 379} 380 381void ieee80211_send_beacon(struct ieee80211_device *ieee) 382{ 383 struct sk_buff *skb; 384 385 //unsigned long flags; 386 387 skb = ieee80211_get_beacon_(ieee); 388 389 if (skb){ 390 softmac_mgmt_xmit(skb, ieee); 391 ieee->softmac_stats.tx_beacons++; 392 dev_kfree_skb_any(skb);//edit by thomas 393 } 394 395 //printk(KERN_WARNING "[1] beacon sending!\n"); 396 ieee->beacon_timer.expires = jiffies + 397 (MSECS( ieee->current_network.beacon_interval -5)); 398 399 //spin_lock_irqsave(&ieee->beacon_lock,flags); 400 if(ieee->beacon_txing) 401 add_timer(&ieee->beacon_timer); 402 //spin_unlock_irqrestore(&ieee->beacon_lock,flags); 403} 404 405 406void ieee80211_send_beacon_cb(unsigned long _ieee) 407{ 408 struct ieee80211_device *ieee = 409 (struct ieee80211_device *) _ieee; 410 unsigned long flags; 411 412 spin_lock_irqsave(&ieee->beacon_lock, flags); 413 ieee80211_send_beacon(ieee); 414 spin_unlock_irqrestore(&ieee->beacon_lock, flags); 415} 416 417void ieee80211_send_probe(struct ieee80211_device *ieee) 418{ 419 struct sk_buff *skb; 420 421 skb = ieee80211_probe_req(ieee); 422 if (skb){ 423 softmac_mgmt_xmit(skb, ieee); 424 ieee->softmac_stats.tx_probe_rq++; 425 //dev_kfree_skb_any(skb);//edit by thomas 426 } 427} 428 429void ieee80211_send_probe_requests(struct ieee80211_device *ieee) 430{ 431 if (ieee->active_scan && (ieee->softmac_features & IEEE_SOFTMAC_PROBERQ)){ 432 ieee80211_send_probe(ieee); 433 ieee80211_send_probe(ieee); 434 } 435} 436 437/* this performs syncro scan blocking the caller until all channels 438 * in the allowed channel map has been checked. 439 */ 440void ieee80211_softmac_scan_syncro(struct ieee80211_device *ieee) 441{ 442 short ch = 0; 443 u8 channel_map[MAX_CHANNEL_NUMBER+1]; 444 memcpy(channel_map, GET_DOT11D_INFO(ieee)->channel_map, MAX_CHANNEL_NUMBER+1); 445 down(&ieee->scan_sem); 446// printk("==================> Sync scan\n"); 447 448 while(1) 449 { 450 451 do{ 452 ch++; 453 if (ch > MAX_CHANNEL_NUMBER) 454 goto out; /* scan completed */ 455 456 }while(!channel_map[ch]); 457 /* this fuction can be called in two situations 458 * 1- We have switched to ad-hoc mode and we are 459 * performing a complete syncro scan before conclude 460 * there are no interesting cell and to create a 461 * new one. In this case the link state is 462 * IEEE80211_NOLINK until we found an interesting cell. 463 * If so the ieee8021_new_net, called by the RX path 464 * will set the state to IEEE80211_LINKED, so we stop 465 * scanning 466 * 2- We are linked and the root uses run iwlist scan. 467 * So we switch to IEEE80211_LINKED_SCANNING to remember 468 * that we are still logically linked (not interested in 469 * new network events, despite for updating the net list, 470 * but we are temporarly 'unlinked' as the driver shall 471 * not filter RX frames and the channel is changing. 472 * So the only situation in witch are interested is to check 473 * if the state become LINKED because of the #1 situation 474 */ 475 476 if (ieee->state == IEEE80211_LINKED) 477 goto out; 478 479 ieee->set_chan(ieee->dev, ch); 480// printk("=====>channel=%d ",ch); 481 if(channel_map[ch] == 1) 482 { 483// printk("====send probe request\n"); 484 ieee80211_send_probe_requests(ieee); 485 } 486 /* this prevent excessive time wait when we 487 * need to wait for a syncro scan to end.. 488 */ 489 if (ieee->sync_scan_hurryup) 490 goto out; 491 492 493 msleep_interruptible_rtl(IEEE80211_SOFTMAC_SCAN_TIME); 494 495 } 496out: 497 ieee->sync_scan_hurryup = 0; 498 up(&ieee->scan_sem); 499 if(IS_DOT11D_ENABLE(ieee)) 500 DOT11D_ScanComplete(ieee); 501} 502 503void ieee80211_softmac_ips_scan_syncro(struct ieee80211_device *ieee) 504{ 505 int ch; 506 unsigned int watch_dog = 0; 507 u8 channel_map[MAX_CHANNEL_NUMBER+1]; 508 memcpy(channel_map, GET_DOT11D_INFO(ieee)->channel_map, MAX_CHANNEL_NUMBER+1); 509 down(&ieee->scan_sem); 510 ch = ieee->current_network.channel; 511// if(ieee->sync_scan_hurryup) 512// { 513 514// printk("stop scan sync\n"); 515// goto out; 516// } 517// printk("=======hh===============>ips scan\n"); 518 while(1) 519 { 520 /* this fuction can be called in two situations 521 * 1- We have switched to ad-hoc mode and we are 522 * performing a complete syncro scan before conclude 523 * there are no interesting cell and to create a 524 * new one. In this case the link state is 525 * IEEE80211_NOLINK until we found an interesting cell. 526 * If so the ieee8021_new_net, called by the RX path 527 * will set the state to IEEE80211_LINKED, so we stop 528 * scanning 529 * 2- We are linked and the root uses run iwlist scan. 530 * So we switch to IEEE80211_LINKED_SCANNING to remember 531 * that we are still logically linked (not interested in 532 * new network events, despite for updating the net list, 533 * but we are temporarly 'unlinked' as the driver shall 534 * not filter RX frames and the channel is changing. 535 * So the only situation in witch are interested is to check 536 * if the state become LINKED because of the #1 situation 537 */ 538 if (ieee->state == IEEE80211_LINKED) 539 { 540 goto out; 541 } 542 if(channel_map[ieee->current_network.channel] > 0) 543 { 544 ieee->set_chan(ieee->dev, ieee->current_network.channel); 545// printk("======>channel=%d ",ieee->current_network.channel); 546 } 547 if(channel_map[ieee->current_network.channel] == 1) 548 { 549// printk("====send probe request\n"); 550 ieee80211_send_probe_requests(ieee); 551 } 552 /* this prevent excessive time wait when we 553 * need to wait for a syncro scan to end.. 554 */ 555// if (ieee->sync_scan_hurryup) 556// goto out; 557 558 msleep_interruptible_rtl(IEEE80211_SOFTMAC_SCAN_TIME); 559 560 do{ 561 if (watch_dog++ >= MAX_CHANNEL_NUMBER) 562 // if (++watch_dog >= 15);//MAX_CHANNEL_NUMBER) //YJ,modified,080630 563 goto out; /* scan completed */ 564 565 ieee->current_network.channel = (ieee->current_network.channel + 1)%MAX_CHANNEL_NUMBER; 566 }while(!channel_map[ieee->current_network.channel]); 567 } 568out: 569 //ieee->sync_scan_hurryup = 0; 570 //ieee->set_chan(ieee->dev, ch); 571 //ieee->current_network.channel = ch; 572 ieee->actscanning = false; 573 up(&ieee->scan_sem); 574 if(IS_DOT11D_ENABLE(ieee)) 575 DOT11D_ScanComplete(ieee); 576} 577 578void ieee80211_softmac_scan_wq(struct work_struct *work) 579{ 580 struct delayed_work *dwork = to_delayed_work(work); 581 struct ieee80211_device *ieee = container_of(dwork, struct ieee80211_device, softmac_scan_wq); 582 static short watchdog = 0; 583 u8 channel_map[MAX_CHANNEL_NUMBER+1]; 584 memcpy(channel_map, GET_DOT11D_INFO(ieee)->channel_map, MAX_CHANNEL_NUMBER+1); 585// printk("ieee80211_softmac_scan_wq ENABLE_IPS\n"); 586// printk("in %s\n",__func__); 587 down(&ieee->scan_sem); 588 589 do{ 590 ieee->current_network.channel = 591 (ieee->current_network.channel + 1) % MAX_CHANNEL_NUMBER; 592 if (watchdog++ > MAX_CHANNEL_NUMBER) 593 goto out; /* no good chans */ 594 595 }while(!channel_map[ieee->current_network.channel]); 596 597 //printk("current_network.channel:%d\n", ieee->current_network.channel); 598 if (ieee->scanning == 0 ) 599 { 600 printk("error out, scanning = 0\n"); 601 goto out; 602 } 603 ieee->set_chan(ieee->dev, ieee->current_network.channel); 604 if(channel_map[ieee->current_network.channel] == 1) 605 ieee80211_send_probe_requests(ieee); 606 607 queue_delayed_work(ieee->wq, &ieee->softmac_scan_wq, IEEE80211_SOFTMAC_SCAN_TIME); 608 up(&ieee->scan_sem); 609 return; 610out: 611 ieee->actscanning = false; 612 watchdog = 0; 613 ieee->scanning = 0; 614 up(&ieee->scan_sem); 615 616 if(IS_DOT11D_ENABLE(ieee)) 617 DOT11D_ScanComplete(ieee); 618 return; 619} 620 621void ieee80211_beacons_start(struct ieee80211_device *ieee) 622{ 623 unsigned long flags; 624 625 spin_lock_irqsave(&ieee->beacon_lock,flags); 626 627 ieee->beacon_txing = 1; 628 ieee80211_send_beacon(ieee); 629 630 spin_unlock_irqrestore(&ieee->beacon_lock,flags); 631} 632 633void ieee80211_beacons_stop(struct ieee80211_device *ieee) 634{ 635 unsigned long flags; 636 637 spin_lock_irqsave(&ieee->beacon_lock,flags); 638 639 ieee->beacon_txing = 0; 640 del_timer_sync(&ieee->beacon_timer); 641 642 spin_unlock_irqrestore(&ieee->beacon_lock,flags); 643 644} 645 646 647void ieee80211_stop_send_beacons(struct ieee80211_device *ieee) 648{ 649 if(ieee->stop_send_beacons) 650 ieee->stop_send_beacons(ieee->dev); 651 if (ieee->softmac_features & IEEE_SOFTMAC_BEACONS) 652 ieee80211_beacons_stop(ieee); 653} 654 655 656void ieee80211_start_send_beacons(struct ieee80211_device *ieee) 657{ 658 if(ieee->start_send_beacons) 659 ieee->start_send_beacons(ieee->dev); 660 if(ieee->softmac_features & IEEE_SOFTMAC_BEACONS) 661 ieee80211_beacons_start(ieee); 662} 663 664 665void ieee80211_softmac_stop_scan(struct ieee80211_device *ieee) 666{ 667// unsigned long flags; 668 669 //ieee->sync_scan_hurryup = 1; 670 671 down(&ieee->scan_sem); 672// spin_lock_irqsave(&ieee->lock, flags); 673 674 if (ieee->scanning == 1){ 675 ieee->scanning = 0; 676 //del_timer_sync(&ieee->scan_timer); 677 cancel_delayed_work(&ieee->softmac_scan_wq); 678 } 679 680// spin_unlock_irqrestore(&ieee->lock, flags); 681 up(&ieee->scan_sem); 682} 683 684void ieee80211_stop_scan(struct ieee80211_device *ieee) 685{ 686 if (ieee->softmac_features & IEEE_SOFTMAC_SCAN) 687 ieee80211_softmac_stop_scan(ieee); 688 else 689 ieee->stop_scan(ieee->dev); 690} 691 692/* called with ieee->lock held */ 693void ieee80211_rtl_start_scan(struct ieee80211_device *ieee) 694{ 695 if(IS_DOT11D_ENABLE(ieee) ) 696 { 697 if(IS_COUNTRY_IE_VALID(ieee)) 698 { 699 RESET_CIE_WATCHDOG(ieee); 700 } 701 } 702 if (ieee->softmac_features & IEEE_SOFTMAC_SCAN){ 703 if (ieee->scanning == 0) 704 { 705 ieee->scanning = 1; 706 //ieee80211_softmac_scan(ieee); 707 // queue_work(ieee->wq, &ieee->softmac_scan_wq); 708 //care this,1203,2007,by lawrence 709 queue_delayed_work(ieee->wq, &ieee->softmac_scan_wq,0); 710 } 711 }else 712 ieee->start_scan(ieee->dev); 713 714} 715 716/* called with wx_sem held */ 717void ieee80211_start_scan_syncro(struct ieee80211_device *ieee) 718{ 719 if(IS_DOT11D_ENABLE(ieee) ) 720 { 721 if(IS_COUNTRY_IE_VALID(ieee)) 722 { 723 RESET_CIE_WATCHDOG(ieee); 724 } 725 } 726 ieee->sync_scan_hurryup = 0; 727 728 if (ieee->softmac_features & IEEE_SOFTMAC_SCAN) 729 ieee80211_softmac_scan_syncro(ieee); 730 else 731 ieee->scan_syncro(ieee->dev); 732 733} 734 735inline struct sk_buff *ieee80211_authentication_req(struct ieee80211_network *beacon, 736 struct ieee80211_device *ieee, int challengelen) 737{ 738 struct sk_buff *skb; 739 struct ieee80211_authentication *auth; 740 741 skb = dev_alloc_skb(sizeof(struct ieee80211_authentication) + challengelen); 742 743 if (!skb) return NULL; 744 745 auth = (struct ieee80211_authentication *) 746 skb_put(skb, sizeof(struct ieee80211_authentication)); 747 748 auth->header.frame_ctl = IEEE80211_STYPE_AUTH; 749 if (challengelen) auth->header.frame_ctl |= IEEE80211_FCTL_WEP; 750 751 auth->header.duration_id = 0x013a; 752 753 memcpy(auth->header.addr1, beacon->bssid, ETH_ALEN); 754 memcpy(auth->header.addr2, ieee->dev->dev_addr, ETH_ALEN); 755 memcpy(auth->header.addr3, beacon->bssid, ETH_ALEN); 756 757 auth->algorithm = ieee->open_wep ? WLAN_AUTH_OPEN : WLAN_AUTH_SHARED_KEY; 758 759 auth->transaction = cpu_to_le16(ieee->associate_seq); 760 ieee->associate_seq++; 761 762 auth->status = cpu_to_le16(WLAN_STATUS_SUCCESS); 763 764 return skb; 765 766} 767 768static struct sk_buff* ieee80211_probe_resp(struct ieee80211_device *ieee, u8 *dest) 769{ 770 u8 *tag; 771 int beacon_size; 772 struct ieee80211_probe_response *beacon_buf; 773 struct sk_buff *skb; 774 int encrypt; 775 int atim_len,erp_len; 776 struct ieee80211_crypt_data* crypt; 777 778 char *ssid = ieee->current_network.ssid; 779 int ssid_len = ieee->current_network.ssid_len; 780 int rate_len = ieee->current_network.rates_len+2; 781 int rate_ex_len = ieee->current_network.rates_ex_len; 782 int wpa_ie_len = ieee->wpa_ie_len; 783 if(rate_ex_len > 0) rate_ex_len+=2; 784 785 if(ieee->current_network.capability & WLAN_CAPABILITY_IBSS) 786 atim_len = 4; 787 else 788 atim_len = 0; 789 790 if(ieee80211_is_54g(ieee->current_network)) 791 erp_len = 3; 792 else 793 erp_len = 0; 794 795 beacon_size = sizeof(struct ieee80211_probe_response)+ 796 ssid_len 797 +3 //channel 798 +rate_len 799 +rate_ex_len 800 +atim_len 801 +wpa_ie_len 802 +erp_len; 803 804 skb = dev_alloc_skb(beacon_size); 805 806 if (!skb) 807 return NULL; 808 809 beacon_buf = (struct ieee80211_probe_response*) skb_put(skb, beacon_size); 810 811 memcpy (beacon_buf->header.addr1, dest,ETH_ALEN); 812 memcpy (beacon_buf->header.addr2, ieee->dev->dev_addr, ETH_ALEN); 813 memcpy (beacon_buf->header.addr3, ieee->current_network.bssid, ETH_ALEN); 814 815 beacon_buf->header.duration_id = 0; 816 beacon_buf->beacon_interval = 817 cpu_to_le16(ieee->current_network.beacon_interval); 818 beacon_buf->capability = 819 cpu_to_le16(ieee->current_network.capability & WLAN_CAPABILITY_IBSS); 820 821 if(ieee->short_slot && (ieee->current_network.capability & WLAN_CAPABILITY_SHORT_SLOT)) 822 cpu_to_le16((beacon_buf->capability |= WLAN_CAPABILITY_SHORT_SLOT)); 823 824 crypt = ieee->crypt[ieee->tx_keyidx]; 825 826 encrypt = ieee->host_encrypt && crypt && crypt->ops && 827 ((0 == strcmp(crypt->ops->name, "WEP")) || wpa_ie_len); 828 829 if (encrypt) 830 beacon_buf->capability |= cpu_to_le16(WLAN_CAPABILITY_PRIVACY); 831 832 833 beacon_buf->header.frame_ctl = cpu_to_le16(IEEE80211_STYPE_PROBE_RESP); 834 835 beacon_buf->info_element.id = MFIE_TYPE_SSID; 836 beacon_buf->info_element.len = ssid_len; 837 838 tag = (u8*) beacon_buf->info_element.data; 839 840 memcpy(tag, ssid, ssid_len); 841 842 tag += ssid_len; 843 844 *(tag++) = MFIE_TYPE_RATES; 845 *(tag++) = rate_len-2; 846 memcpy(tag,ieee->current_network.rates,rate_len-2); 847 tag+=rate_len-2; 848 849 *(tag++) = MFIE_TYPE_DS_SET; 850 *(tag++) = 1; 851 *(tag++) = ieee->current_network.channel; 852 853 if(atim_len){ 854 *(tag++) = MFIE_TYPE_IBSS_SET; 855 *(tag++) = 2; 856 *((u16*)(tag)) = cpu_to_le16(ieee->current_network.atim_window); 857 tag+=2; 858 } 859 860 if(erp_len){ 861 *(tag++) = MFIE_TYPE_ERP; 862 *(tag++) = 1; 863 *(tag++) = 0; 864 } 865 866 if(rate_ex_len){ 867 *(tag++) = MFIE_TYPE_RATES_EX; 868 *(tag++) = rate_ex_len-2; 869 memcpy(tag,ieee->current_network.rates_ex,rate_ex_len-2); 870 tag+=rate_ex_len-2; 871 } 872 873 if (wpa_ie_len) 874 { 875 if (ieee->iw_mode == IW_MODE_ADHOC) 876 {//as Windows will set pairwise key same as the group key which is not allowed in Linux, so set this for IOT issue. WB 2008.07.07 877 memcpy(&ieee->wpa_ie[14], &ieee->wpa_ie[8], 4); 878 } 879 880 memcpy(tag, ieee->wpa_ie, ieee->wpa_ie_len); 881 } 882 883 skb->dev = ieee->dev; 884 return skb; 885} 886 887struct sk_buff* ieee80211_assoc_resp(struct ieee80211_device *ieee, u8 *dest) 888{ 889 struct sk_buff *skb; 890 u8* tag; 891 892 struct ieee80211_crypt_data* crypt; 893 struct ieee80211_assoc_response_frame *assoc; 894 short encrypt; 895 896 unsigned int rate_len = ieee80211_MFIE_rate_len(ieee); 897 int len = sizeof(struct ieee80211_assoc_response_frame) + rate_len; 898 899 skb = dev_alloc_skb(len); 900 901 if (!skb) 902 return NULL; 903 904 assoc = (struct ieee80211_assoc_response_frame *) 905 skb_put(skb,sizeof(struct ieee80211_assoc_response_frame)); 906 907 assoc->header.frame_control = cpu_to_le16(IEEE80211_STYPE_ASSOC_RESP); 908 memcpy(assoc->header.addr1, dest,ETH_ALEN); 909 memcpy(assoc->header.addr3, ieee->dev->dev_addr, ETH_ALEN); 910 memcpy(assoc->header.addr2, ieee->dev->dev_addr, ETH_ALEN); 911 assoc->capability = cpu_to_le16(ieee->iw_mode == IW_MODE_MASTER ? 912 WLAN_CAPABILITY_BSS : WLAN_CAPABILITY_IBSS); 913 914 915 if(ieee->short_slot) 916 assoc->capability |= cpu_to_le16(WLAN_CAPABILITY_SHORT_SLOT); 917 918 if (ieee->host_encrypt) 919 crypt = ieee->crypt[ieee->tx_keyidx]; 920 else crypt = NULL; 921 922 encrypt = ( crypt && crypt->ops); 923 924 if (encrypt) 925 assoc->capability |= cpu_to_le16(WLAN_CAPABILITY_PRIVACY); 926 927 assoc->status = 0; 928 assoc->aid = cpu_to_le16(ieee->assoc_id); 929 if (ieee->assoc_id == 0x2007) ieee->assoc_id=0; 930 else ieee->assoc_id++; 931 932 tag = (u8*) skb_put(skb, rate_len); 933 934 ieee80211_MFIE_Brate(ieee, &tag); 935 ieee80211_MFIE_Grate(ieee, &tag); 936 937 return skb; 938} 939 940struct sk_buff* ieee80211_auth_resp(struct ieee80211_device *ieee,int status, u8 *dest) 941{ 942 struct sk_buff *skb; 943 struct ieee80211_authentication *auth; 944 945 skb = dev_alloc_skb(sizeof(struct ieee80211_authentication)+1); 946 947 if (!skb) 948 return NULL; 949 950 skb->len = sizeof(struct ieee80211_authentication); 951 952 auth = (struct ieee80211_authentication *)skb->data; 953 954 auth->status = cpu_to_le16(status); 955 auth->transaction = cpu_to_le16(2); 956 auth->algorithm = cpu_to_le16(WLAN_AUTH_OPEN); 957 958 memcpy(auth->header.addr3, ieee->dev->dev_addr, ETH_ALEN); 959 memcpy(auth->header.addr2, ieee->dev->dev_addr, ETH_ALEN); 960 memcpy(auth->header.addr1, dest, ETH_ALEN); 961 auth->header.frame_ctl = cpu_to_le16(IEEE80211_STYPE_AUTH); 962 return skb; 963 964 965} 966 967struct sk_buff* ieee80211_null_func(struct ieee80211_device *ieee,short pwr) 968{ 969 struct sk_buff *skb; 970 struct ieee80211_hdr_3addr* hdr; 971 972 skb = dev_alloc_skb(sizeof(struct ieee80211_hdr_3addr)); 973 974 if (!skb) 975 return NULL; 976 977 hdr = (struct ieee80211_hdr_3addr*)skb_put(skb,sizeof(struct ieee80211_hdr_3addr)); 978 979 memcpy(hdr->addr1, ieee->current_network.bssid, ETH_ALEN); 980 memcpy(hdr->addr2, ieee->dev->dev_addr, ETH_ALEN); 981 memcpy(hdr->addr3, ieee->current_network.bssid, ETH_ALEN); 982 983 hdr->frame_control = cpu_to_le16(IEEE80211_FTYPE_DATA | 984 IEEE80211_STYPE_NULLFUNC | IEEE80211_FCTL_TODS | 985 (pwr ? IEEE80211_FCTL_PM:0)); 986 987 return skb; 988 989 990} 991 992 993void ieee80211_resp_to_assoc_rq(struct ieee80211_device *ieee, u8* dest) 994{ 995 struct sk_buff *buf = ieee80211_assoc_resp(ieee, dest); 996 997 if (buf){ 998 softmac_mgmt_xmit(buf, ieee); 999 dev_kfree_skb_any(buf);//edit by thomas 1000 } 1001} 1002 1003 1004void ieee80211_resp_to_auth(struct ieee80211_device *ieee, int s, u8* dest) 1005{ 1006 struct sk_buff *buf = ieee80211_auth_resp(ieee, s, dest); 1007 1008 if (buf){ 1009 softmac_mgmt_xmit(buf, ieee); 1010 dev_kfree_skb_any(buf);//edit by thomas 1011 } 1012} 1013 1014 1015void ieee80211_resp_to_probe(struct ieee80211_device *ieee, u8 *dest) 1016{ 1017 1018 struct sk_buff *buf = ieee80211_probe_resp(ieee, dest); 1019 1020 if (buf) { 1021 softmac_mgmt_xmit(buf, ieee); 1022 dev_kfree_skb_any(buf);//edit by thomas 1023 } 1024} 1025 1026 1027inline struct sk_buff *ieee80211_association_req(struct ieee80211_network *beacon,struct ieee80211_device *ieee) 1028{ 1029 struct sk_buff *skb; 1030 //unsigned long flags; 1031 1032 struct ieee80211_assoc_request_frame *hdr; 1033 u8 *tag; 1034 //short info_addr = 0; 1035 //int i; 1036 //u16 suite_count = 0; 1037 //u8 suit_select = 0; 1038 unsigned int wpa_len = beacon->wpa_ie_len; 1039 //struct net_device *dev = ieee->dev; 1040 //union iwreq_data wrqu; 1041 //u8 *buff; 1042 //u8 *p; 1043 // for testing purpose 1044 unsigned int rsn_len = beacon->rsn_ie_len; 1045 unsigned int rate_len = ieee80211_MFIE_rate_len(ieee); 1046 unsigned int wmm_info_len = beacon->QoS_Enable?9:0; 1047 unsigned int turbo_info_len = beacon->Turbo_Enable?9:0; 1048 1049 u8 encry_proto = ieee->wpax_type_notify & 0xff; 1050 //u8 pairwise_type = (ieee->wpax_type_notify >> 8) & 0xff; 1051 //u8 authen_type = (ieee->wpax_type_notify >> 16) & 0xff; 1052 1053 int len = 0; 1054 1055 //[0] Notify type of encryption: WPA/WPA2 1056 //[1] pair wise type 1057 //[2] authen type 1058 if(ieee->wpax_type_set) { 1059 if (IEEE_PROTO_WPA == encry_proto) { 1060 rsn_len = 0; 1061 } else if (IEEE_PROTO_RSN == encry_proto) { 1062 wpa_len = 0; 1063 } 1064 } 1065 len = sizeof(struct ieee80211_assoc_request_frame)+ 1066 + beacon->ssid_len//essid tagged val 1067 + rate_len//rates tagged val 1068 + wpa_len 1069 + rsn_len 1070 + wmm_info_len 1071 + turbo_info_len; 1072 1073 skb = dev_alloc_skb(len); 1074 1075 if (!skb) 1076 return NULL; 1077 1078 hdr = (struct ieee80211_assoc_request_frame *) 1079 skb_put(skb, sizeof(struct ieee80211_assoc_request_frame)); 1080 1081 1082 hdr->header.frame_control = IEEE80211_STYPE_ASSOC_REQ; 1083 hdr->header.duration_id= 37; 1084 memcpy(hdr->header.addr1, beacon->bssid, ETH_ALEN); 1085 memcpy(hdr->header.addr2, ieee->dev->dev_addr, ETH_ALEN); 1086 memcpy(hdr->header.addr3, beacon->bssid, ETH_ALEN); 1087 memcpy(ieee->ap_mac_addr, beacon->bssid, ETH_ALEN);//for HW security, John 1088 1089 hdr->capability = cpu_to_le16(WLAN_CAPABILITY_BSS); 1090 if (beacon->capability & WLAN_CAPABILITY_PRIVACY ) 1091 hdr->capability |= cpu_to_le16(WLAN_CAPABILITY_PRIVACY); 1092 if (beacon->capability & WLAN_CAPABILITY_SHORT_PREAMBLE) 1093 hdr->capability |= cpu_to_le16(WLAN_CAPABILITY_SHORT_PREAMBLE); 1094 1095 if(ieee->short_slot) 1096 hdr->capability |= cpu_to_le16(WLAN_CAPABILITY_SHORT_SLOT); 1097 1098 hdr->listen_interval = 0xa; 1099 1100 hdr->info_element.id = MFIE_TYPE_SSID; 1101 1102 hdr->info_element.len = beacon->ssid_len; 1103 tag = skb_put(skb, beacon->ssid_len); 1104 memcpy(tag, beacon->ssid, beacon->ssid_len); 1105 1106 tag = skb_put(skb, rate_len); 1107 1108 ieee80211_MFIE_Brate(ieee, &tag); 1109 ieee80211_MFIE_Grate(ieee, &tag); 1110 1111 //add rsn==0 condition for ap's mix security mode(wpa+wpa2), john2007.8.9 1112 //choose AES encryption as default algorithm while using mixed mode 1113 1114 tag = skb_put(skb,ieee->wpa_ie_len); 1115 memcpy(tag,ieee->wpa_ie,ieee->wpa_ie_len); 1116 1117 tag = skb_put(skb,wmm_info_len); 1118 if(wmm_info_len) { 1119 ieee80211_WMM_Info(ieee, &tag); 1120 } 1121 tag = skb_put(skb,turbo_info_len); 1122 if(turbo_info_len) { 1123 ieee80211_TURBO_Info(ieee, &tag); 1124 } 1125 1126 return skb; 1127} 1128 1129void ieee80211_associate_abort(struct ieee80211_device *ieee) 1130{ 1131 1132 unsigned long flags; 1133 spin_lock_irqsave(&ieee->lock, flags); 1134 1135 ieee->associate_seq++; 1136 1137 /* don't scan, and avoid to have the RX path possibily 1138 * try again to associate. Even do not react to AUTH or 1139 * ASSOC response. Just wait for the retry wq to be scheduled. 1140 * Here we will check if there are good nets to associate 1141 * with, so we retry or just get back to NO_LINK and scanning 1142 */ 1143 if (ieee->state == IEEE80211_ASSOCIATING_AUTHENTICATING){ 1144 IEEE80211_DEBUG_MGMT("Authentication failed\n"); 1145 ieee->softmac_stats.no_auth_rs++; 1146 }else{ 1147 IEEE80211_DEBUG_MGMT("Association failed\n"); 1148 ieee->softmac_stats.no_ass_rs++; 1149 } 1150 1151 ieee->state = IEEE80211_ASSOCIATING_RETRY; 1152 1153 queue_delayed_work(ieee->wq, &ieee->associate_retry_wq,IEEE80211_SOFTMAC_ASSOC_RETRY_TIME); 1154 1155 spin_unlock_irqrestore(&ieee->lock, flags); 1156} 1157 1158void ieee80211_associate_abort_cb(unsigned long dev) 1159{ 1160 ieee80211_associate_abort((struct ieee80211_device *) dev); 1161} 1162 1163 1164void ieee80211_associate_step1(struct ieee80211_device *ieee) 1165{ 1166 struct ieee80211_network *beacon = &ieee->current_network; 1167 struct sk_buff *skb; 1168 1169 IEEE80211_DEBUG_MGMT("Stopping scan\n"); 1170 ieee->softmac_stats.tx_auth_rq++; 1171 skb=ieee80211_authentication_req(beacon, ieee, 0); 1172 if (!skb){ 1173 1174 ieee80211_associate_abort(ieee); 1175 } 1176 else{ 1177 ieee->state = IEEE80211_ASSOCIATING_AUTHENTICATING ; 1178 IEEE80211_DEBUG_MGMT("Sending authentication request\n"); 1179 //printk("---Sending authentication request\n"); 1180 softmac_mgmt_xmit(skb, ieee); 1181 //BUGON when you try to add_timer twice, using mod_timer may be better, john0709 1182 if(!timer_pending(&ieee->associate_timer)){ 1183 ieee->associate_timer.expires = jiffies + (HZ / 2); 1184 add_timer(&ieee->associate_timer); 1185 } 1186 //If call dev_kfree_skb_any,a warning will ocur.... 1187 //KERNEL: assertion (!atomic_read(&skb->users)) failed at net/core/dev.c (1708) 1188 //So ... 1204 by lawrence. 1189 //printk("\nIn %s,line %d call kfree skb.",__func__,__LINE__); 1190 //dev_kfree_skb_any(skb);//edit by thomas 1191 } 1192} 1193 1194void ieee80211_rtl_auth_challenge(struct ieee80211_device *ieee, u8 *challenge, int chlen) 1195{ 1196 u8 *c; 1197 struct sk_buff *skb; 1198 struct ieee80211_network *beacon = &ieee->current_network; 1199// int hlen = sizeof(struct ieee80211_authentication); 1200 del_timer_sync(&ieee->associate_timer); 1201 ieee->associate_seq++; 1202 ieee->softmac_stats.tx_auth_rq++; 1203 1204 skb = ieee80211_authentication_req(beacon, ieee, chlen+2); 1205 if (!skb) 1206 ieee80211_associate_abort(ieee); 1207 else{ 1208 c = skb_put(skb, chlen+2); 1209 *(c++) = MFIE_TYPE_CHALLENGE; 1210 *(c++) = chlen; 1211 memcpy(c, challenge, chlen); 1212 1213 IEEE80211_DEBUG_MGMT("Sending authentication challenge response\n"); 1214 1215 ieee80211_encrypt_fragment(ieee, skb, sizeof(struct ieee80211_hdr_3addr )); 1216 1217 softmac_mgmt_xmit(skb, ieee); 1218 if (!timer_pending(&ieee->associate_timer)){ 1219 //printk("=========>add timer again, to crash\n"); 1220 ieee->associate_timer.expires = jiffies + (HZ / 2); 1221 add_timer(&ieee->associate_timer); 1222 } 1223 dev_kfree_skb_any(skb);//edit by thomas 1224 } 1225 kfree(challenge); 1226} 1227 1228void ieee80211_associate_step2(struct ieee80211_device *ieee) 1229{ 1230 struct sk_buff* skb; 1231 struct ieee80211_network *beacon = &ieee->current_network; 1232 1233 del_timer_sync(&ieee->associate_timer); 1234 1235 IEEE80211_DEBUG_MGMT("Sending association request\n"); 1236 ieee->softmac_stats.tx_ass_rq++; 1237 skb=ieee80211_association_req(beacon, ieee); 1238 if (!skb) 1239 ieee80211_associate_abort(ieee); 1240 else{ 1241 softmac_mgmt_xmit(skb, ieee); 1242 if (!timer_pending(&ieee->associate_timer)){ 1243 ieee->associate_timer.expires = jiffies + (HZ / 2); 1244 add_timer(&ieee->associate_timer); 1245 } 1246 //dev_kfree_skb_any(skb);//edit by thomas 1247 } 1248} 1249 1250void ieee80211_associate_complete_wq(struct work_struct *work) 1251{ 1252 struct ieee80211_device *ieee = container_of(work, struct ieee80211_device, associate_complete_wq); 1253 1254 printk(KERN_INFO "Associated successfully\n"); 1255 if(ieee80211_is_54g(ieee->current_network) && 1256 (ieee->modulation & IEEE80211_OFDM_MODULATION)){ 1257 1258 ieee->rate = 540; 1259 printk(KERN_INFO"Using G rates\n"); 1260 }else{ 1261 ieee->rate = 110; 1262 printk(KERN_INFO"Using B rates\n"); 1263 } 1264 ieee->link_change(ieee->dev); 1265 notify_wx_assoc_event(ieee); 1266 if (ieee->data_hard_resume) 1267 ieee->data_hard_resume(ieee->dev); 1268 netif_carrier_on(ieee->dev); 1269} 1270 1271void ieee80211_associate_complete(struct ieee80211_device *ieee) 1272{ 1273 int i; 1274 del_timer_sync(&ieee->associate_timer); 1275 1276 for(i = 0; i < 6; i++) { 1277 //ieee->seq_ctrl[i] = 0; 1278 } 1279 ieee->state = IEEE80211_LINKED; 1280 IEEE80211_DEBUG_MGMT("Successfully associated\n"); 1281 1282 queue_work(ieee->wq, &ieee->associate_complete_wq); 1283} 1284 1285void ieee80211_associate_procedure_wq(struct work_struct *work) 1286{ 1287 struct ieee80211_device *ieee = container_of(work, struct ieee80211_device, associate_procedure_wq); 1288 1289 ieee->sync_scan_hurryup = 1; 1290 down(&ieee->wx_sem); 1291 1292 if (ieee->data_hard_stop) 1293 ieee->data_hard_stop(ieee->dev); 1294 1295 ieee80211_stop_scan(ieee); 1296 ieee->set_chan(ieee->dev, ieee->current_network.channel); 1297 1298 ieee->associate_seq = 1; 1299 ieee80211_associate_step1(ieee); 1300 1301 up(&ieee->wx_sem); 1302} 1303 1304inline void ieee80211_softmac_new_net(struct ieee80211_device *ieee, struct ieee80211_network *net) 1305{ 1306 u8 tmp_ssid[IW_ESSID_MAX_SIZE+1]; 1307 int tmp_ssid_len = 0; 1308 1309 short apset,ssidset,ssidbroad,apmatch,ssidmatch; 1310 1311 /* we are interested in new new only if we are not associated 1312 * and we are not associating / authenticating 1313 */ 1314 if (ieee->state != IEEE80211_NOLINK) 1315 return; 1316 1317 if ((ieee->iw_mode == IW_MODE_INFRA) && !(net->capability & WLAN_CAPABILITY_BSS)) 1318 return; 1319 1320 if ((ieee->iw_mode == IW_MODE_ADHOC) && !(net->capability & WLAN_CAPABILITY_IBSS)) 1321 return; 1322 1323 1324 if (ieee->iw_mode == IW_MODE_INFRA || ieee->iw_mode == IW_MODE_ADHOC){ 1325 /* if the user specified the AP MAC, we need also the essid 1326 * This could be obtained by beacons or, if the network does not 1327 * broadcast it, it can be put manually. 1328 */ 1329 apset = ieee->wap_set;//(memcmp(ieee->current_network.bssid, zero,ETH_ALEN)!=0 ); 1330 ssidset = ieee->ssid_set;//ieee->current_network.ssid[0] != '\0'; 1331 ssidbroad = !(net->ssid_len == 0 || net->ssid[0]== '\0'); 1332 apmatch = (memcmp(ieee->current_network.bssid, net->bssid, ETH_ALEN)==0); 1333 1334 if(ieee->current_network.ssid_len != net->ssid_len) 1335 ssidmatch = 0; 1336 else 1337 ssidmatch = (0==strncmp(ieee->current_network.ssid, net->ssid, net->ssid_len)); 1338 1339 //printk("cur: %s, %d, net:%s, %d\n", ieee->current_network.ssid, ieee->current_network.ssid_len, net->ssid, net->ssid_len); 1340 //printk("apset=%d apmatch=%d ssidset=%d ssidbroad=%d ssidmatch=%d\n",apset,apmatch,ssidset,ssidbroad,ssidmatch); 1341 1342 if ( /* if the user set the AP check if match. 1343 * if the network does not broadcast essid we check the user supplyed ANY essid 1344 * if the network does broadcast and the user does not set essid it is OK 1345 * if the network does broadcast and the user did set essid chech if essid match 1346 */ 1347 ( apset && apmatch && 1348 ((ssidset && ssidbroad && ssidmatch) || (ssidbroad && !ssidset) || (!ssidbroad && ssidset)) ) || 1349 /* if the ap is not set, check that the user set the bssid 1350 * and the network does bradcast and that those two bssid matches 1351 */ 1352 (!apset && ssidset && ssidbroad && ssidmatch) 1353 ){ 1354 1355 1356 /* if the essid is hidden replace it with the 1357 * essid provided by the user. 1358 */ 1359 if (!ssidbroad){ 1360 strncpy(tmp_ssid, ieee->current_network.ssid, IW_ESSID_MAX_SIZE); 1361 tmp_ssid_len = ieee->current_network.ssid_len; 1362 } 1363 memcpy(&ieee->current_network, net, sizeof(struct ieee80211_network)); 1364 1365 if (!ssidbroad){ 1366 strncpy(ieee->current_network.ssid, tmp_ssid, IW_ESSID_MAX_SIZE); 1367 ieee->current_network.ssid_len = tmp_ssid_len; 1368 } 1369 printk(KERN_INFO"Linking with %s: channel is %d\n",ieee->current_network.ssid,ieee->current_network.channel); 1370 1371 if (ieee->iw_mode == IW_MODE_INFRA){ 1372 ieee->state = IEEE80211_ASSOCIATING; 1373 ieee->beinretry = false; 1374 queue_work(ieee->wq, &ieee->associate_procedure_wq); 1375 }else{ 1376 if(ieee80211_is_54g(ieee->current_network) && 1377 (ieee->modulation & IEEE80211_OFDM_MODULATION)){ 1378 ieee->rate = 540; 1379 printk(KERN_INFO"Using G rates\n"); 1380 }else{ 1381 ieee->rate = 110; 1382 printk(KERN_INFO"Using B rates\n"); 1383 } 1384 ieee->state = IEEE80211_LINKED; 1385 ieee->beinretry = false; 1386 } 1387 1388 } 1389 } 1390 1391} 1392 1393void ieee80211_softmac_check_all_nets(struct ieee80211_device *ieee) 1394{ 1395 unsigned long flags; 1396 struct ieee80211_network *target; 1397 1398 spin_lock_irqsave(&ieee->lock, flags); 1399 list_for_each_entry(target, &ieee->network_list, list) { 1400 1401 /* if the state become different that NOLINK means 1402 * we had found what we are searching for 1403 */ 1404 1405 if (ieee->state != IEEE80211_NOLINK) 1406 break; 1407 1408 if (ieee->scan_age == 0 || time_after(target->last_scanned + ieee->scan_age, jiffies)) 1409 ieee80211_softmac_new_net(ieee, target); 1410 } 1411 1412 spin_unlock_irqrestore(&ieee->lock, flags); 1413 1414} 1415 1416 1417static inline u16 auth_parse(struct sk_buff *skb, u8** challenge, int *chlen) 1418{ 1419 struct ieee80211_authentication *a; 1420 u8 *t; 1421 if (skb->len < (sizeof(struct ieee80211_authentication)-sizeof(struct ieee80211_info_element))){ 1422 IEEE80211_DEBUG_MGMT("invalid len in auth resp: %d\n",skb->len); 1423 return 0xcafe; 1424 } 1425 *challenge = NULL; 1426 a = (struct ieee80211_authentication*) skb->data; 1427 if(skb->len > (sizeof(struct ieee80211_authentication) +3)){ 1428 t = skb->data + sizeof(struct ieee80211_authentication); 1429 1430 if(*(t++) == MFIE_TYPE_CHALLENGE){ 1431 *chlen = *(t++); 1432 *challenge = kmalloc(*chlen, GFP_ATOMIC); 1433 memcpy(*challenge, t, *chlen); 1434 } 1435 } 1436 1437 return cpu_to_le16(a->status); 1438 1439} 1440 1441 1442int auth_rq_parse(struct sk_buff *skb,u8* dest) 1443{ 1444 struct ieee80211_authentication *a; 1445 1446 if (skb->len < (sizeof(struct ieee80211_authentication)-sizeof(struct ieee80211_info_element))){ 1447 IEEE80211_DEBUG_MGMT("invalid len in auth request: %d\n",skb->len); 1448 return -1; 1449 } 1450 a = (struct ieee80211_authentication*) skb->data; 1451 1452 memcpy(dest,a->header.addr2, ETH_ALEN); 1453 1454 if (le16_to_cpu(a->algorithm) != WLAN_AUTH_OPEN) 1455 return WLAN_STATUS_NOT_SUPPORTED_AUTH_ALG; 1456 1457 return WLAN_STATUS_SUCCESS; 1458} 1459 1460static short probe_rq_parse(struct ieee80211_device *ieee, struct sk_buff *skb, u8 *src) 1461{ 1462 u8 *tag; 1463 u8 *skbend; 1464 u8 *ssid=NULL; 1465 u8 ssidlen = 0; 1466 1467 struct ieee80211_hdr_3addr *header = 1468 (struct ieee80211_hdr_3addr *) skb->data; 1469 1470 if (skb->len < sizeof (struct ieee80211_hdr_3addr )) 1471 return -1; /* corrupted */ 1472 1473 memcpy(src,header->addr2, ETH_ALEN); 1474 1475 skbend = (u8*)skb->data + skb->len; 1476 1477 tag = skb->data + sizeof (struct ieee80211_hdr_3addr ); 1478 1479 while (tag+1 < skbend){ 1480 if (*tag == 0){ 1481 ssid = tag+2; 1482 ssidlen = *(tag+1); 1483 break; 1484 } 1485 tag++; /* point to the len field */ 1486 tag = tag + *(tag); /* point to the last data byte of the tag */ 1487 tag++; /* point to the next tag */ 1488 } 1489 1490 //IEEE80211DMESG("Card MAC address is "MACSTR, MAC2STR(src)); 1491 if (ssidlen == 0) return 1; 1492 1493 if (!ssid) return 1; /* ssid not found in tagged param */ 1494 return (!strncmp(ssid, ieee->current_network.ssid, ssidlen)); 1495 1496} 1497 1498int assoc_rq_parse(struct sk_buff *skb,u8* dest) 1499{ 1500 struct ieee80211_assoc_request_frame *a; 1501 1502 if (skb->len < (sizeof(struct ieee80211_assoc_request_frame) - 1503 sizeof(struct ieee80211_info_element))) { 1504 1505 IEEE80211_DEBUG_MGMT("invalid len in auth request:%d \n", skb->len); 1506 return -1; 1507 } 1508 1509 a = (struct ieee80211_assoc_request_frame*) skb->data; 1510 1511 memcpy(dest,a->header.addr2,ETH_ALEN); 1512 1513 return 0; 1514} 1515 1516static inline u16 assoc_parse(struct sk_buff *skb, int *aid) 1517{ 1518 struct ieee80211_assoc_response_frame *a; 1519 if (skb->len < sizeof(struct ieee80211_assoc_response_frame)){ 1520 IEEE80211_DEBUG_MGMT("invalid len in auth resp: %d\n", skb->len); 1521 return 0xcafe; 1522 } 1523 1524 a = (struct ieee80211_assoc_response_frame*) skb->data; 1525 *aid = le16_to_cpu(a->aid) & 0x3fff; 1526 return le16_to_cpu(a->status); 1527} 1528 1529static inline void 1530ieee80211_rx_probe_rq(struct ieee80211_device *ieee, struct sk_buff *skb) 1531{ 1532 u8 dest[ETH_ALEN]; 1533 1534 //IEEE80211DMESG("Rx probe"); 1535 ieee->softmac_stats.rx_probe_rq++; 1536 //DMESG("Dest is "MACSTR, MAC2STR(dest)); 1537 if (probe_rq_parse(ieee, skb, dest)){ 1538 //IEEE80211DMESG("Was for me!"); 1539 ieee->softmac_stats.tx_probe_rs++; 1540 ieee80211_resp_to_probe(ieee, dest); 1541 } 1542} 1543 1544inline void 1545ieee80211_rx_auth_rq(struct ieee80211_device *ieee, struct sk_buff *skb) 1546{ 1547 u8 dest[ETH_ALEN]; 1548 int status; 1549 //IEEE80211DMESG("Rx probe"); 1550 ieee->softmac_stats.rx_auth_rq++; 1551 1552 status = auth_rq_parse(skb, dest); 1553 if (status != -1) { 1554 ieee80211_resp_to_auth(ieee, status, dest); 1555 } 1556 //DMESG("Dest is "MACSTR, MAC2STR(dest)); 1557 1558} 1559 1560 inline void 1561ieee80211_rx_assoc_rq(struct ieee80211_device *ieee, struct sk_buff *skb) 1562{ 1563 1564 u8 dest[ETH_ALEN]; 1565 //unsigned long flags; 1566 1567 ieee->softmac_stats.rx_ass_rq++; 1568 if (assoc_rq_parse(skb,dest) != -1){ 1569 ieee80211_resp_to_assoc_rq(ieee, dest); 1570 } 1571 1572 printk(KERN_INFO"New client associated: %pM\n", dest); 1573} 1574 1575 1576 1577void ieee80211_sta_ps_send_null_frame(struct ieee80211_device *ieee, short pwr) 1578{ 1579 1580 struct sk_buff *buf = ieee80211_null_func(ieee, pwr); 1581 1582 if (buf) 1583 softmac_ps_mgmt_xmit(buf, ieee); 1584 1585} 1586 1587 1588short ieee80211_sta_ps_sleep(struct ieee80211_device *ieee, u32 *time_h, u32 *time_l) 1589{ 1590 int timeout = 0; 1591 1592 u8 dtim; 1593 /*if(ieee->ps == IEEE80211_PS_DISABLED || 1594 ieee->iw_mode != IW_MODE_INFRA || 1595 ieee->state != IEEE80211_LINKED) 1596 1597 return 0; 1598 */ 1599 dtim = ieee->current_network.dtim_data; 1600 //printk("DTIM\n"); 1601 1602 if(!(dtim & IEEE80211_DTIM_VALID)) 1603 return 0; 1604 else 1605 timeout = ieee->current_network.beacon_interval; 1606 1607 //printk("VALID\n"); 1608 ieee->current_network.dtim_data = IEEE80211_DTIM_INVALID; 1609 1610 if(dtim & ((IEEE80211_DTIM_UCAST | IEEE80211_DTIM_MBCAST)& ieee->ps)) 1611 return 2; 1612 1613 if(!time_after(jiffies, ieee->dev->trans_start + MSECS(timeout))) 1614 return 0; 1615 1616 if(!time_after(jiffies, ieee->last_rx_ps_time + MSECS(timeout))) 1617 return 0; 1618 1619 if((ieee->softmac_features & IEEE_SOFTMAC_SINGLE_QUEUE ) && 1620 (ieee->mgmt_queue_tail != ieee->mgmt_queue_head)) 1621 return 0; 1622 1623 if(time_l){ 1624 *time_l = ieee->current_network.last_dtim_sta_time[0] 1625 + MSECS((ieee->current_network.beacon_interval)); 1626 //* ieee->current_network.dtim_period)); 1627 //printk("beacon_interval:%x, dtim_period:%x, totol to Msecs:%x, HZ:%x\n", ieee->current_network.beacon_interval, ieee->current_network.dtim_period, MSECS(((ieee->current_network.beacon_interval * ieee->current_network.dtim_period))), HZ); 1628 } 1629 1630 if(time_h){ 1631 *time_h = ieee->current_network.last_dtim_sta_time[1]; 1632 if(time_l && *time_l < ieee->current_network.last_dtim_sta_time[0]) 1633 *time_h += 1; 1634 } 1635 1636 return 1; 1637 1638 1639} 1640 1641inline void ieee80211_sta_ps(struct ieee80211_device *ieee) 1642{ 1643 1644 u32 th,tl; 1645 short sleep; 1646 1647 unsigned long flags,flags2; 1648 1649 spin_lock_irqsave(&ieee->lock, flags); 1650 1651 if((ieee->ps == IEEE80211_PS_DISABLED || 1652 1653 ieee->iw_mode != IW_MODE_INFRA || 1654 ieee->state != IEEE80211_LINKED)){ 1655 1656 //#warning CHECK_LOCK_HERE 1657 spin_lock_irqsave(&ieee->mgmt_tx_lock, flags2); 1658 1659 ieee80211_sta_wakeup(ieee, 1); 1660 1661 spin_unlock_irqrestore(&ieee->mgmt_tx_lock, flags2); 1662 } 1663 1664 sleep = ieee80211_sta_ps_sleep(ieee,&th, &tl); 1665// printk("===>%s,%d[2 wake, 1 sleep, 0 do nothing], ieee->sta_sleep = %d\n",__func__, sleep,ieee->sta_sleep); 1666 /* 2 wake, 1 sleep, 0 do nothing */ 1667 if(sleep == 0) 1668 goto out; 1669 1670 if(sleep == 1){ 1671 1672 if(ieee->sta_sleep == 1) 1673 ieee->enter_sleep_state(ieee->dev,th,tl); 1674 1675 else if(ieee->sta_sleep == 0){ 1676 // printk("send null 1\n"); 1677 spin_lock_irqsave(&ieee->mgmt_tx_lock, flags2); 1678 1679 if(ieee->ps_is_queue_empty(ieee->dev)){ 1680 1681 1682 ieee->sta_sleep = 2; 1683 1684 ieee->ps_request_tx_ack(ieee->dev); 1685 1686 ieee80211_sta_ps_send_null_frame(ieee,1); 1687 1688 ieee->ps_th = th; 1689 ieee->ps_tl = tl; 1690 } 1691 spin_unlock_irqrestore(&ieee->mgmt_tx_lock, flags2); 1692 1693 } 1694 1695 1696 }else if(sleep == 2){ 1697//#warning CHECK_LOCK_HERE 1698 spin_lock_irqsave(&ieee->mgmt_tx_lock, flags2); 1699 1700 // printk("send wakeup packet\n"); 1701 ieee80211_sta_wakeup(ieee,1); 1702 1703 spin_unlock_irqrestore(&ieee->mgmt_tx_lock, flags2); 1704 } 1705 1706out: 1707 spin_unlock_irqrestore(&ieee->lock, flags); 1708 1709} 1710 1711void ieee80211_sta_wakeup(struct ieee80211_device *ieee, short nl) 1712{ 1713 if(ieee->sta_sleep == 0){ 1714 if(nl){ 1715 // printk("Warning: driver is probably failing to report TX ps error\n"); 1716 ieee->ps_request_tx_ack(ieee->dev); 1717 ieee80211_sta_ps_send_null_frame(ieee, 0); 1718 } 1719 return; 1720 1721 } 1722 1723 if(ieee->sta_sleep == 1) 1724 ieee->sta_wake_up(ieee->dev); 1725 1726 ieee->sta_sleep = 0; 1727 1728 if(nl){ 1729 ieee->ps_request_tx_ack(ieee->dev); 1730 ieee80211_sta_ps_send_null_frame(ieee, 0); 1731 } 1732} 1733 1734void ieee80211_ps_tx_ack(struct ieee80211_device *ieee, short success) 1735{ 1736 unsigned long flags,flags2; 1737 1738 spin_lock_irqsave(&ieee->lock, flags); 1739 if(ieee->sta_sleep == 2){ 1740 /* Null frame with PS bit set */ 1741 if(success){ 1742 1743 // printk("==================> %s::enter sleep state\n",__func__); 1744 ieee->sta_sleep = 1; 1745 ieee->enter_sleep_state(ieee->dev,ieee->ps_th,ieee->ps_tl); 1746 } 1747 /* if the card report not success we can't be sure the AP 1748 * has not RXed so we can't assume the AP believe us awake 1749 */ 1750 } 1751 /* 21112005 - tx again null without PS bit if lost */ 1752 else { 1753 1754 if((ieee->sta_sleep == 0) && !success){ 1755 spin_lock_irqsave(&ieee->mgmt_tx_lock, flags2); 1756 ieee80211_sta_ps_send_null_frame(ieee, 0); 1757 spin_unlock_irqrestore(&ieee->mgmt_tx_lock, flags2); 1758 } 1759 } 1760 spin_unlock_irqrestore(&ieee->lock, flags); 1761} 1762 1763inline int 1764ieee80211_rx_frame_softmac(struct ieee80211_device *ieee, struct sk_buff *skb, 1765 struct ieee80211_rx_stats *rx_stats, u16 type, 1766 u16 stype) 1767{ 1768 struct ieee80211_hdr_3addr *header = (struct ieee80211_hdr_3addr *) skb->data; 1769 u16 errcode; 1770 u8* challenge=NULL; 1771 int chlen=0; 1772 int aid=0; 1773 struct ieee80211_assoc_response_frame *assoc_resp; 1774 struct ieee80211_info_element *info_element; 1775 1776 if(!ieee->proto_started) 1777 return 0; 1778 1779 if(ieee->sta_sleep || (ieee->ps != IEEE80211_PS_DISABLED && 1780 ieee->iw_mode == IW_MODE_INFRA && 1781 ieee->state == IEEE80211_LINKED)) 1782 1783 tasklet_schedule(&ieee->ps_task); 1784 1785 if (WLAN_FC_GET_STYPE(header->frame_control) != IEEE80211_STYPE_PROBE_RESP && 1786 WLAN_FC_GET_STYPE(header->frame_control) != IEEE80211_STYPE_BEACON) 1787 ieee->last_rx_ps_time = jiffies; 1788 1789 switch (WLAN_FC_GET_STYPE(header->frame_control)) { 1790 1791 case IEEE80211_STYPE_ASSOC_RESP: 1792 case IEEE80211_STYPE_REASSOC_RESP: 1793 1794 IEEE80211_DEBUG_MGMT("received [RE]ASSOCIATION RESPONSE (%d)\n", 1795 WLAN_FC_GET_STYPE(header->frame_ctl)); 1796 if ((ieee->softmac_features & IEEE_SOFTMAC_ASSOCIATE) && 1797 ieee->state == IEEE80211_ASSOCIATING_AUTHENTICATED && 1798 ieee->iw_mode == IW_MODE_INFRA){ 1799 if (0 == (errcode=assoc_parse(skb, &aid))){ 1800 u16 left; 1801 1802 ieee->state=IEEE80211_LINKED; 1803 ieee->assoc_id = aid; 1804 ieee->softmac_stats.rx_ass_ok++; 1805 1806 //printk(KERN_WARNING "nic_type = %s", (rx_stats->nic_type == 1)?"rtl8187":"rtl8187B"); 1807 if(1 == rx_stats->nic_type) //card type is 8187 1808 { 1809 goto associate_complete; 1810 } 1811 assoc_resp = (struct ieee80211_assoc_response_frame*)skb->data; 1812 info_element = &assoc_resp->info_element; 1813 left = skb->len - ((void*)info_element - (void*)assoc_resp); 1814 1815 while (left >= sizeof(struct ieee80211_info_element_hdr)) { 1816 if (sizeof(struct ieee80211_info_element_hdr) + info_element->len > left) { 1817 printk(KERN_WARNING "[re]associate reeponse error!"); 1818 return 1; 1819 } 1820 switch (info_element->id) { 1821 case MFIE_TYPE_GENERIC: 1822 IEEE80211_DEBUG_SCAN("MFIE_TYPE_GENERIC: %d bytes\n", info_element->len); 1823 if (info_element->len >= 8 && 1824 info_element->data[0] == 0x00 && 1825 info_element->data[1] == 0x50 && 1826 info_element->data[2] == 0xf2 && 1827 info_element->data[3] == 0x02 && 1828 info_element->data[4] == 0x01) { 1829 // Not care about version at present. 1830 //WMM Parameter Element 1831 memcpy(ieee->current_network.wmm_param,(u8*)(info_element->data\ 1832 + 8),(info_element->len - 8)); 1833 1834 if (((ieee->current_network.wmm_info^info_element->data[6])& \ 1835 0x0f)||(!ieee->init_wmmparam_flag)) { 1836 // refresh parameter element for current network 1837 // update the register parameter for hardware 1838 ieee->init_wmmparam_flag = 1; 1839 queue_work(ieee->wq, &ieee->wmm_param_update_wq); 1840 1841 } 1842 //update info_element for current network 1843 ieee->current_network.wmm_info = info_element->data[6]; 1844 } 1845 break; 1846 default: 1847 //nothing to do at present!!! 1848 break; 1849 } 1850 1851 left -= sizeof(struct ieee80211_info_element_hdr) + 1852 info_element->len; 1853 info_element = (struct ieee80211_info_element *) 1854 &info_element->data[info_element->len]; 1855 } 1856 if(!ieee->init_wmmparam_flag) //legacy AP, reset the AC_xx_param register 1857 { 1858 queue_work(ieee->wq,&ieee->wmm_param_update_wq); 1859 ieee->init_wmmparam_flag = 1;//indicate AC_xx_param upated since last associate 1860 } 1861associate_complete: 1862 ieee80211_associate_complete(ieee); 1863 }else{ 1864 ieee->softmac_stats.rx_ass_err++; 1865 IEEE80211_DEBUG_MGMT( 1866 "Association response status code 0x%x\n", 1867 errcode); 1868 ieee80211_associate_abort(ieee); 1869 } 1870 } 1871 break; 1872 1873 case IEEE80211_STYPE_ASSOC_REQ: 1874 case IEEE80211_STYPE_REASSOC_REQ: 1875 1876 if ((ieee->softmac_features & IEEE_SOFTMAC_ASSOCIATE) && 1877 ieee->iw_mode == IW_MODE_MASTER) 1878 1879 ieee80211_rx_assoc_rq(ieee, skb); 1880 break; 1881 1882 case IEEE80211_STYPE_AUTH: 1883 1884 if (ieee->softmac_features & IEEE_SOFTMAC_ASSOCIATE){ 1885 if (ieee->state == IEEE80211_ASSOCIATING_AUTHENTICATING && 1886 ieee->iw_mode == IW_MODE_INFRA){ 1887 1888 IEEE80211_DEBUG_MGMT("Received authentication response"); 1889 1890 if (0 == (errcode=auth_parse(skb, &challenge, &chlen))){ 1891 if(ieee->open_wep || !challenge){ 1892 ieee->state = IEEE80211_ASSOCIATING_AUTHENTICATED; 1893 ieee->softmac_stats.rx_auth_rs_ok++; 1894 1895 ieee80211_associate_step2(ieee); 1896 }else{ 1897 ieee80211_rtl_auth_challenge(ieee, challenge, chlen); 1898 } 1899 }else{ 1900 ieee->softmac_stats.rx_auth_rs_err++; 1901 IEEE80211_DEBUG_MGMT("Authentication respose status code 0x%x",errcode); 1902 ieee80211_associate_abort(ieee); 1903 } 1904 1905 }else if (ieee->iw_mode == IW_MODE_MASTER){ 1906 ieee80211_rx_auth_rq(ieee, skb); 1907 } 1908 } 1909 break; 1910 1911 case IEEE80211_STYPE_PROBE_REQ: 1912 1913 if ((ieee->softmac_features & IEEE_SOFTMAC_PROBERS) && 1914 ((ieee->iw_mode == IW_MODE_ADHOC || 1915 ieee->iw_mode == IW_MODE_MASTER) && 1916 ieee->state == IEEE80211_LINKED)) 1917 1918 ieee80211_rx_probe_rq(ieee, skb); 1919 break; 1920 1921 case IEEE80211_STYPE_DISASSOC: 1922 case IEEE80211_STYPE_DEAUTH: 1923 if ((ieee->softmac_features & IEEE_SOFTMAC_ASSOCIATE) && 1924 (ieee->state == IEEE80211_LINKED) && 1925 (ieee->iw_mode == IW_MODE_INFRA) && 1926 (!memcmp(header->addr2,ieee->current_network.bssid,ETH_ALEN))){ 1927 ieee->state = IEEE80211_ASSOCIATING; 1928 ieee->softmac_stats.reassoc++; 1929 1930 //notify_wx_assoc_event(ieee); //YJ,del,080828, do not notify os here 1931 queue_work(ieee->wq, &ieee->associate_procedure_wq); 1932 } 1933 1934 break; 1935 1936 default: 1937 return -1; 1938 break; 1939 } 1940 1941 //dev_kfree_skb_any(skb); 1942 return 0; 1943} 1944 1945 1946 1947/* following are for a simplier TX queue management. 1948 * Instead of using netif_[stop/wake]_queue the driver 1949 * will uses these two function (plus a reset one), that 1950 * will internally uses the kernel netif_* and takes 1951 * care of the ieee802.11 fragmentation. 1952 * So the driver receives a fragment per time and might 1953 * call the stop function when it want without take care 1954 * to have enough room to TX an entire packet. 1955 * This might be useful if each fragment need it's own 1956 * descriptor, thus just keep a total free memory > than 1957 * the max fragmentation threshold is not enough.. If the 1958 * ieee802.11 stack passed a TXB struct then you needed 1959 * to keep N free descriptors where 1960 * N = MAX_PACKET_SIZE / MIN_FRAG_TRESHOLD 1961 * In this way you need just one and the 802.11 stack 1962 * will take care of buffering fragments and pass them to 1963 * to the driver later, when it wakes the queue. 1964 */ 1965 1966void ieee80211_softmac_xmit(struct ieee80211_txb *txb, struct ieee80211_device *ieee) 1967{ 1968 1969 1970 unsigned long flags; 1971 int i; 1972 1973 spin_lock_irqsave(&ieee->lock,flags); 1974 1975 /* called with 2nd parm 0, no tx mgmt lock required */ 1976 ieee80211_sta_wakeup(ieee,0); 1977 1978 for(i = 0; i < txb->nr_frags; i++) { 1979 1980 if (ieee->queue_stop){ 1981 ieee->tx_pending.txb = txb; 1982 ieee->tx_pending.frag = i; 1983 goto exit; 1984 }else{ 1985 ieee->softmac_data_hard_start_xmit( 1986 txb->fragments[i], 1987 ieee->dev,ieee->rate); 1988 //(i+1)<txb->nr_frags); 1989 ieee->stats.tx_packets++; 1990 ieee->stats.tx_bytes += txb->fragments[i]->len; 1991 ieee->dev->trans_start = jiffies; 1992 } 1993 } 1994 1995 ieee80211_txb_free(txb); 1996 1997 exit: 1998 spin_unlock_irqrestore(&ieee->lock,flags); 1999 2000} 2001 2002/* called with ieee->lock acquired */ 2003void ieee80211_resume_tx(struct ieee80211_device *ieee) 2004{ 2005 int i; 2006 for(i = ieee->tx_pending.frag; i < ieee->tx_pending.txb->nr_frags; i++) { 2007 2008 if (ieee->queue_stop){ 2009 ieee->tx_pending.frag = i; 2010 return; 2011 }else{ 2012 2013 ieee->softmac_data_hard_start_xmit( 2014 ieee->tx_pending.txb->fragments[i], 2015 ieee->dev,ieee->rate); 2016 //(i+1)<ieee->tx_pending.txb->nr_frags); 2017 ieee->stats.tx_packets++; 2018 ieee->dev->trans_start = jiffies; 2019 } 2020 } 2021 2022 2023 ieee80211_txb_free(ieee->tx_pending.txb); 2024 ieee->tx_pending.txb = NULL; 2025} 2026 2027 2028void ieee80211_reset_queue(struct ieee80211_device *ieee) 2029{ 2030 unsigned long flags; 2031 2032 spin_lock_irqsave(&ieee->lock,flags); 2033 init_mgmt_queue(ieee); 2034 if (ieee->tx_pending.txb){ 2035 ieee80211_txb_free(ieee->tx_pending.txb); 2036 ieee->tx_pending.txb = NULL; 2037 } 2038 ieee->queue_stop = 0; 2039 spin_unlock_irqrestore(&ieee->lock,flags); 2040 2041} 2042 2043void ieee80211_rtl_wake_queue(struct ieee80211_device *ieee) 2044{ 2045 2046 unsigned long flags; 2047 struct sk_buff *skb; 2048 struct ieee80211_hdr_3addr *header; 2049 2050 spin_lock_irqsave(&ieee->lock,flags); 2051 if (! ieee->queue_stop) goto exit; 2052 2053 ieee->queue_stop = 0; 2054 2055 if(ieee->softmac_features & IEEE_SOFTMAC_SINGLE_QUEUE){ 2056 while (!ieee->queue_stop && (skb = dequeue_mgmt(ieee))){ 2057 2058 header = (struct ieee80211_hdr_3addr *) skb->data; 2059 2060 header->seq_ctrl = cpu_to_le16(ieee->seq_ctrl[0] << 4); 2061 2062 if (ieee->seq_ctrl[0] == 0xFFF) 2063 ieee->seq_ctrl[0] = 0; 2064 else 2065 ieee->seq_ctrl[0]++; 2066 2067 //printk(KERN_ALERT "ieee80211_wake_queue \n"); 2068 ieee->softmac_data_hard_start_xmit(skb,ieee->dev,ieee->basic_rate); 2069 dev_kfree_skb_any(skb);//edit by thomas 2070 } 2071 } 2072 if (!ieee->queue_stop && ieee->tx_pending.txb) 2073 ieee80211_resume_tx(ieee); 2074 2075 if (!ieee->queue_stop && netif_queue_stopped(ieee->dev)){ 2076 ieee->softmac_stats.swtxawake++; 2077 netif_wake_queue(ieee->dev); 2078 } 2079 2080exit : 2081 spin_unlock_irqrestore(&ieee->lock,flags); 2082} 2083 2084 2085void ieee80211_rtl_stop_queue(struct ieee80211_device *ieee) 2086{ 2087 //unsigned long flags; 2088 //spin_lock_irqsave(&ieee->lock,flags); 2089 2090 if (! netif_queue_stopped(ieee->dev)){ 2091 netif_stop_queue(ieee->dev); 2092 ieee->softmac_stats.swtxstop++; 2093 } 2094 ieee->queue_stop = 1; 2095 //spin_unlock_irqrestore(&ieee->lock,flags); 2096 2097} 2098 2099 2100inline void ieee80211_randomize_cell(struct ieee80211_device *ieee) 2101{ 2102 2103 get_random_bytes(ieee->current_network.bssid, ETH_ALEN); 2104 2105 /* an IBSS cell address must have the two less significant 2106 * bits of the first byte = 2 2107 */ 2108 ieee->current_network.bssid[0] &= ~0x01; 2109 ieee->current_network.bssid[0] |= 0x02; 2110} 2111 2112/* called in user context only */ 2113void ieee80211_start_master_bss(struct ieee80211_device *ieee) 2114{ 2115 ieee->assoc_id = 1; 2116 2117 if (ieee->current_network.ssid_len == 0){ 2118 strncpy(ieee->current_network.ssid, 2119 IEEE80211_DEFAULT_TX_ESSID, 2120 IW_ESSID_MAX_SIZE); 2121 2122 ieee->current_network.ssid_len = strlen(IEEE80211_DEFAULT_TX_ESSID); 2123 ieee->ssid_set = 1; 2124 } 2125 2126 memcpy(ieee->current_network.bssid, ieee->dev->dev_addr, ETH_ALEN); 2127 2128 ieee->set_chan(ieee->dev, ieee->current_network.channel); 2129 ieee->state = IEEE80211_LINKED; 2130 ieee->link_change(ieee->dev); 2131 notify_wx_assoc_event(ieee); 2132 2133 if (ieee->data_hard_resume) 2134 ieee->data_hard_resume(ieee->dev); 2135 2136 netif_carrier_on(ieee->dev); 2137} 2138 2139void ieee80211_start_monitor_mode(struct ieee80211_device *ieee) 2140{ 2141 if(ieee->raw_tx){ 2142 2143 if (ieee->data_hard_resume) 2144 ieee->data_hard_resume(ieee->dev); 2145 2146 netif_carrier_on(ieee->dev); 2147 } 2148} 2149 2150void ieee80211_start_ibss_wq(struct work_struct *work) 2151{ 2152 struct delayed_work *dwork = to_delayed_work(work); 2153 struct ieee80211_device *ieee = container_of(dwork, struct ieee80211_device, start_ibss_wq); 2154 2155 /* iwconfig mode ad-hoc will schedule this and return 2156 * on the other hand this will block further iwconfig SET 2157 * operations because of the wx_sem hold. 2158 * Anyway some most set operations set a flag to speed-up 2159 * (abort) this wq (when syncro scanning) before sleeping 2160 * on the semaphore 2161 */ 2162 2163 down(&ieee->wx_sem); 2164 2165 2166 if (ieee->current_network.ssid_len == 0){ 2167 strcpy(ieee->current_network.ssid,IEEE80211_DEFAULT_TX_ESSID); 2168 ieee->current_network.ssid_len = strlen(IEEE80211_DEFAULT_TX_ESSID); 2169 ieee->ssid_set = 1; 2170 } 2171 2172 /* check if we have this cell in our network list */ 2173 ieee80211_softmac_check_all_nets(ieee); 2174 2175 if(ieee->state == IEEE80211_NOLINK) 2176 ieee->current_network.channel = 10; 2177 /* if not then the state is not linked. Maybe the user swithced to 2178 * ad-hoc mode just after being in monitor mode, or just after 2179 * being very few time in managed mode (so the card have had no 2180 * time to scan all the chans..) or we have just run up the iface 2181 * after setting ad-hoc mode. So we have to give another try.. 2182 * Here, in ibss mode, should be safe to do this without extra care 2183 * (in bss mode we had to make sure no-one tryed to associate when 2184 * we had just checked the ieee->state and we was going to start the 2185 * scan) beacause in ibss mode the ieee80211_new_net function, when 2186 * finds a good net, just set the ieee->state to IEEE80211_LINKED, 2187 * so, at worst, we waste a bit of time to initiate an unneeded syncro 2188 * scan, that will stop at the first round because it sees the state 2189 * associated. 2190 */ 2191 if (ieee->state == IEEE80211_NOLINK) 2192 ieee80211_start_scan_syncro(ieee); 2193 2194 /* the network definitively is not here.. create a new cell */ 2195 if (ieee->state == IEEE80211_NOLINK){ 2196 printk("creating new IBSS cell\n"); 2197 if(!ieee->wap_set) 2198 ieee80211_randomize_cell(ieee); 2199 2200 if(ieee->modulation & IEEE80211_CCK_MODULATION){ 2201 2202 ieee->current_network.rates_len = 4; 2203 2204 ieee->current_network.rates[0] = IEEE80211_BASIC_RATE_MASK | IEEE80211_CCK_RATE_1MB; 2205 ieee->current_network.rates[1] = IEEE80211_BASIC_RATE_MASK | IEEE80211_CCK_RATE_2MB; 2206 ieee->current_network.rates[2] = IEEE80211_BASIC_RATE_MASK | IEEE80211_CCK_RATE_5MB; 2207 ieee->current_network.rates[3] = IEEE80211_BASIC_RATE_MASK | IEEE80211_CCK_RATE_11MB; 2208 2209 }else 2210 ieee->current_network.rates_len = 0; 2211 2212 if(ieee->modulation & IEEE80211_OFDM_MODULATION){ 2213 ieee->current_network.rates_ex_len = 8; 2214 2215 ieee->current_network.rates_ex[0] = IEEE80211_BASIC_RATE_MASK | IEEE80211_OFDM_RATE_6MB; 2216 ieee->current_network.rates_ex[1] = IEEE80211_BASIC_RATE_MASK | IEEE80211_OFDM_RATE_9MB; 2217 ieee->current_network.rates_ex[2] = IEEE80211_BASIC_RATE_MASK | IEEE80211_OFDM_RATE_12MB; 2218 ieee->current_network.rates_ex[3] = IEEE80211_BASIC_RATE_MASK | IEEE80211_OFDM_RATE_18MB; 2219 ieee->current_network.rates_ex[4] = IEEE80211_BASIC_RATE_MASK | IEEE80211_OFDM_RATE_24MB; 2220 ieee->current_network.rates_ex[5] = IEEE80211_BASIC_RATE_MASK | IEEE80211_OFDM_RATE_36MB; 2221 ieee->current_network.rates_ex[6] = IEEE80211_BASIC_RATE_MASK | IEEE80211_OFDM_RATE_48MB; 2222 ieee->current_network.rates_ex[7] = IEEE80211_BASIC_RATE_MASK | IEEE80211_OFDM_RATE_54MB; 2223 2224 ieee->rate = 540; 2225 }else{ 2226 ieee->current_network.rates_ex_len = 0; 2227 ieee->rate = 110; 2228 } 2229 2230 // By default, WMM function will be disabled in IBSS mode 2231 ieee->current_network.QoS_Enable = 0; 2232 2233 ieee->current_network.atim_window = 0; 2234 ieee->current_network.capability = WLAN_CAPABILITY_IBSS; 2235 if(ieee->short_slot) 2236 ieee->current_network.capability |= WLAN_CAPABILITY_SHORT_SLOT; 2237 2238 } 2239 2240 ieee->state = IEEE80211_LINKED; 2241 ieee->set_chan(ieee->dev, ieee->current_network.channel); 2242 ieee->link_change(ieee->dev); 2243 2244 notify_wx_assoc_event(ieee); 2245 2246 ieee80211_start_send_beacons(ieee); 2247 printk(KERN_WARNING "after sending beacon packet!\n"); 2248 2249 if (ieee->data_hard_resume) 2250 ieee->data_hard_resume(ieee->dev); 2251 2252 netif_carrier_on(ieee->dev); 2253 2254 up(&ieee->wx_sem); 2255} 2256inline void ieee80211_start_ibss(struct ieee80211_device *ieee) 2257{ 2258 queue_delayed_work(ieee->wq, &ieee->start_ibss_wq, 100); 2259} 2260 2261/* this is called only in user context, with wx_sem held */ 2262void ieee80211_start_bss(struct ieee80211_device *ieee) 2263{ 2264 unsigned long flags; 2265 // 2266 // Ref: 802.11d 11.1.3.3 2267 // STA shall not start a BSS unless properly formed Beacon frame including a Country IE. 2268 // 2269 if(IS_DOT11D_ENABLE(ieee) && !IS_COUNTRY_IE_VALID(ieee)) 2270 { 2271 if(! ieee->bGlobalDomain) 2272 { 2273 return; 2274 } 2275 } 2276 /* check if we have already found the net we 2277 * are interested in (if any). 2278 * if not (we are disassociated and we are not 2279 * in associating / authenticating phase) start the background scanning. 2280 */ 2281 ieee80211_softmac_check_all_nets(ieee); 2282 2283 /* ensure no-one start an associating process (thus setting 2284 * the ieee->state to ieee80211_ASSOCIATING) while we 2285 * have just cheked it and we are going to enable scan. 2286 * The ieee80211_new_net function is always called with 2287 * lock held (from both ieee80211_softmac_check_all_nets and 2288 * the rx path), so we cannot be in the middle of such function 2289 */ 2290 spin_lock_irqsave(&ieee->lock, flags); 2291 2292//#ifdef ENABLE_IPS 2293// printk("start bss ENABLE_IPS\n"); 2294//#else 2295 if (ieee->state == IEEE80211_NOLINK){ 2296 ieee->actscanning = true; 2297 ieee80211_rtl_start_scan(ieee); 2298 } 2299//#endif 2300 spin_unlock_irqrestore(&ieee->lock, flags); 2301} 2302 2303/* called only in userspace context */ 2304void ieee80211_disassociate(struct ieee80211_device *ieee) 2305{ 2306 netif_carrier_off(ieee->dev); 2307 2308 if (ieee->softmac_features & IEEE_SOFTMAC_TX_QUEUE) 2309 ieee80211_reset_queue(ieee); 2310 2311 if (ieee->data_hard_stop) 2312 ieee->data_hard_stop(ieee->dev); 2313 2314 if(IS_DOT11D_ENABLE(ieee)) 2315 Dot11d_Reset(ieee); 2316 2317 ieee->link_change(ieee->dev); 2318 if (ieee->state == IEEE80211_LINKED) 2319 notify_wx_assoc_event(ieee); 2320 ieee->state = IEEE80211_NOLINK; 2321 2322} 2323void ieee80211_associate_retry_wq(struct work_struct *work) 2324{ 2325 struct delayed_work *dwork = to_delayed_work(work); 2326 struct ieee80211_device *ieee = container_of(dwork, struct ieee80211_device, associate_retry_wq); 2327 unsigned long flags; 2328 down(&ieee->wx_sem); 2329 if(!ieee->proto_started) 2330 goto exit; 2331 if(ieee->state != IEEE80211_ASSOCIATING_RETRY) 2332 goto exit; 2333 /* until we do not set the state to IEEE80211_NOLINK 2334 * there are no possibility to have someone else trying 2335 * to start an association procdure (we get here with 2336 * ieee->state = IEEE80211_ASSOCIATING). 2337 * When we set the state to IEEE80211_NOLINK it is possible 2338 * that the RX path run an attempt to associate, but 2339 * both ieee80211_softmac_check_all_nets and the 2340 * RX path works with ieee->lock held so there are no 2341 * problems. If we are still disassociated then start a scan. 2342 * the lock here is necessary to ensure no one try to start 2343 * an association procedure when we have just checked the 2344 * state and we are going to start the scan. 2345 */ 2346 ieee->state = IEEE80211_NOLINK; 2347 ieee->beinretry = true; 2348 ieee80211_softmac_check_all_nets(ieee); 2349 2350 spin_lock_irqsave(&ieee->lock, flags); 2351 2352 if(ieee->state == IEEE80211_NOLINK){ 2353 ieee->beinretry = false; 2354 ieee->actscanning = true; 2355 ieee80211_rtl_start_scan(ieee); 2356 } 2357 //YJ,add,080828, notify os here 2358 if(ieee->state == IEEE80211_NOLINK) 2359 { 2360 notify_wx_assoc_event(ieee); 2361 } 2362 //YJ,add,080828,end 2363 spin_unlock_irqrestore(&ieee->lock, flags); 2364 2365exit: 2366 up(&ieee->wx_sem); 2367} 2368 2369struct sk_buff *ieee80211_get_beacon_(struct ieee80211_device *ieee) 2370{ 2371 u8 broadcast_addr[] = {0xff,0xff,0xff,0xff,0xff,0xff}; 2372 2373 struct sk_buff *skb = NULL; 2374 struct ieee80211_probe_response *b; 2375 2376 skb = ieee80211_probe_resp(ieee, broadcast_addr); 2377 if (!skb) 2378 return NULL; 2379 2380 b = (struct ieee80211_probe_response *) skb->data; 2381 b->header.frame_ctl = cpu_to_le16(IEEE80211_STYPE_BEACON); 2382 2383 return skb; 2384 2385} 2386 2387struct sk_buff *ieee80211_get_beacon(struct ieee80211_device *ieee) 2388{ 2389 struct sk_buff *skb; 2390 struct ieee80211_probe_response *b; 2391 2392 skb = ieee80211_get_beacon_(ieee); 2393 if(!skb) 2394 return NULL; 2395 2396 b = (struct ieee80211_probe_response *) skb->data; 2397 b->header.seq_ctrl = cpu_to_le16(ieee->seq_ctrl[0] << 4); 2398 2399 if (ieee->seq_ctrl[0] == 0xFFF) 2400 ieee->seq_ctrl[0] = 0; 2401 else 2402 ieee->seq_ctrl[0]++; 2403 2404 return skb; 2405} 2406 2407void ieee80211_softmac_stop_protocol(struct ieee80211_device *ieee) 2408{ 2409 ieee->sync_scan_hurryup = 1; 2410 down(&ieee->wx_sem); 2411 ieee80211_stop_protocol(ieee); 2412 up(&ieee->wx_sem); 2413} 2414 2415 2416void ieee80211_stop_protocol(struct ieee80211_device *ieee) 2417{ 2418 if (!ieee->proto_started) 2419 return; 2420 2421 ieee->proto_started = 0; 2422 2423 ieee80211_stop_send_beacons(ieee); 2424 if((ieee->iw_mode == IW_MODE_INFRA)&&(ieee->state == IEEE80211_LINKED)) { 2425 SendDisassociation(ieee,NULL,WLAN_REASON_DISASSOC_STA_HAS_LEFT); 2426 } 2427 del_timer_sync(&ieee->associate_timer); 2428 cancel_delayed_work(&ieee->associate_retry_wq); 2429 cancel_delayed_work(&ieee->start_ibss_wq); 2430 ieee80211_stop_scan(ieee); 2431 2432 ieee80211_disassociate(ieee); 2433} 2434 2435void ieee80211_softmac_start_protocol(struct ieee80211_device *ieee) 2436{ 2437 ieee->sync_scan_hurryup = 0; 2438 down(&ieee->wx_sem); 2439 ieee80211_start_protocol(ieee); 2440 up(&ieee->wx_sem); 2441} 2442 2443void ieee80211_start_protocol(struct ieee80211_device *ieee) 2444{ 2445 short ch = 0; 2446 int i = 0; 2447 2448 if (ieee->proto_started) 2449 return; 2450 2451 ieee->proto_started = 1; 2452 2453 if (ieee->current_network.channel == 0){ 2454 do{ 2455 ch++; 2456 if (ch > MAX_CHANNEL_NUMBER) 2457 return; /* no channel found */ 2458 2459 }while(!GET_DOT11D_INFO(ieee)->channel_map[ch]); 2460 2461 ieee->current_network.channel = ch; 2462 } 2463 2464 if (ieee->current_network.beacon_interval == 0) 2465 ieee->current_network.beacon_interval = 100; 2466 ieee->set_chan(ieee->dev,ieee->current_network.channel); 2467 2468 for(i = 0; i < 17; i++) { 2469 ieee->last_rxseq_num[i] = -1; 2470 ieee->last_rxfrag_num[i] = -1; 2471 ieee->last_packet_time[i] = 0; 2472 } 2473 2474 ieee->init_wmmparam_flag = 0;//reinitialize AC_xx_PARAM registers. 2475 2476 2477 /* if the user set the MAC of the ad-hoc cell and then 2478 * switch to managed mode, shall we make sure that association 2479 * attempts does not fail just because the user provide the essid 2480 * and the nic is still checking for the AP MAC ?? 2481 */ 2482 switch (ieee->iw_mode) { 2483 case IW_MODE_AUTO: 2484 ieee->iw_mode = IW_MODE_INFRA; 2485 //not set break here intentionly 2486 case IW_MODE_INFRA: 2487 ieee80211_start_bss(ieee); 2488 break; 2489 2490 case IW_MODE_ADHOC: 2491 ieee80211_start_ibss(ieee); 2492 break; 2493 2494 case IW_MODE_MASTER: 2495 ieee80211_start_master_bss(ieee); 2496 break; 2497 2498 case IW_MODE_MONITOR: 2499 ieee80211_start_monitor_mode(ieee); 2500 break; 2501 2502 default: 2503 ieee->iw_mode = IW_MODE_INFRA; 2504 ieee80211_start_bss(ieee); 2505 break; 2506 } 2507} 2508 2509 2510#define DRV_NAME "Ieee80211" 2511void ieee80211_softmac_init(struct ieee80211_device *ieee) 2512{ 2513 int i; 2514 memset(&ieee->current_network, 0, sizeof(struct ieee80211_network)); 2515 2516 ieee->state = IEEE80211_NOLINK; 2517 ieee->sync_scan_hurryup = 0; 2518 for(i = 0; i < 5; i++) { 2519 ieee->seq_ctrl[i] = 0; 2520 } 2521 2522 ieee->assoc_id = 0; 2523 ieee->queue_stop = 0; 2524 ieee->scanning = 0; 2525 ieee->softmac_features = 0; //so IEEE2100-like driver are happy 2526 ieee->wap_set = 0; 2527 ieee->ssid_set = 0; 2528 ieee->proto_started = 0; 2529 ieee->basic_rate = IEEE80211_DEFAULT_BASIC_RATE; 2530 ieee->rate = 3; 2531//#ifdef ENABLE_LPS 2532 ieee->ps = IEEE80211_PS_MBCAST|IEEE80211_PS_UNICAST; 2533//#else 2534// ieee->ps = IEEE80211_PS_DISABLED; 2535//#endif 2536 ieee->sta_sleep = 0; 2537//by amy 2538 ieee->bInactivePs = false; 2539 ieee->actscanning = false; 2540 ieee->ListenInterval = 2; 2541 ieee->NumRxDataInPeriod = 0; //YJ,add,080828 2542 ieee->NumRxBcnInPeriod = 0; //YJ,add,080828 2543 ieee->NumRxOkTotal = 0;//+by amy 080312 2544 ieee->NumRxUnicast = 0;//YJ,add,080828,for keep alive 2545 ieee->beinretry = false; 2546 ieee->bHwRadioOff = false; 2547//by amy 2548 2549 init_mgmt_queue(ieee); 2550 2551 ieee->tx_pending.txb = NULL; 2552 2553 init_timer(&ieee->associate_timer); 2554 ieee->associate_timer.data = (unsigned long)ieee; 2555 ieee->associate_timer.function = ieee80211_associate_abort_cb; 2556 2557 init_timer(&ieee->beacon_timer); 2558 ieee->beacon_timer.data = (unsigned long) ieee; 2559 ieee->beacon_timer.function = ieee80211_send_beacon_cb; 2560 2561#ifdef PF_SYNCTHREAD 2562 ieee->wq = create_workqueue(DRV_NAME,0); 2563#else 2564 ieee->wq = create_workqueue(DRV_NAME); 2565#endif 2566 INIT_DELAYED_WORK(&ieee->start_ibss_wq,(void*) ieee80211_start_ibss_wq); 2567 INIT_WORK(&ieee->associate_complete_wq,(void*) ieee80211_associate_complete_wq); 2568 INIT_WORK(&ieee->associate_procedure_wq,(void*) ieee80211_associate_procedure_wq); 2569 INIT_DELAYED_WORK(&ieee->softmac_scan_wq,(void*) ieee80211_softmac_scan_wq); 2570 INIT_DELAYED_WORK(&ieee->associate_retry_wq,(void*) ieee80211_associate_retry_wq); 2571 INIT_WORK(&ieee->wx_sync_scan_wq,(void*) ieee80211_wx_sync_scan_wq); 2572// INIT_WORK(&ieee->watch_dog_wq,(void*) ieee80211_watch_dog_wq); 2573 2574 sema_init(&ieee->wx_sem, 1); 2575 sema_init(&ieee->scan_sem, 1); 2576 2577 spin_lock_init(&ieee->mgmt_tx_lock); 2578 spin_lock_init(&ieee->beacon_lock); 2579 2580 tasklet_init(&ieee->ps_task, 2581 (void(*)(unsigned long)) ieee80211_sta_ps, 2582 (unsigned long)ieee); 2583 ieee->pDot11dInfo = kmalloc(sizeof(RT_DOT11D_INFO), GFP_ATOMIC); 2584} 2585 2586void ieee80211_softmac_free(struct ieee80211_device *ieee) 2587{ 2588 down(&ieee->wx_sem); 2589 2590 del_timer_sync(&ieee->associate_timer); 2591 cancel_delayed_work(&ieee->associate_retry_wq); 2592 2593 2594 //add for RF power on power of by lizhaoming 080512 2595 cancel_delayed_work(&ieee->GPIOChangeRFWorkItem); 2596 2597 destroy_workqueue(ieee->wq); 2598 if(NULL != ieee->pDot11dInfo) 2599 kfree(ieee->pDot11dInfo); 2600 up(&ieee->wx_sem); 2601} 2602 2603/******************************************************** 2604 * Start of WPA code. * 2605 * this is stolen from the ipw2200 driver * 2606 ********************************************************/ 2607 2608 2609static int ieee80211_wpa_enable(struct ieee80211_device *ieee, int value) 2610{ 2611 /* This is called when wpa_supplicant loads and closes the driver 2612 * interface. */ 2613 printk("%s WPA\n",value ? "enabling" : "disabling"); 2614 ieee->wpa_enabled = value; 2615 return 0; 2616} 2617 2618 2619void ieee80211_wpa_assoc_frame(struct ieee80211_device *ieee, char *wpa_ie, int wpa_ie_len) 2620{ 2621 /* make sure WPA is enabled */ 2622 ieee80211_wpa_enable(ieee, 1); 2623 2624 ieee80211_disassociate(ieee); 2625} 2626 2627 2628static int ieee80211_wpa_mlme(struct ieee80211_device *ieee, int command, int reason) 2629{ 2630 2631 int ret = 0; 2632 2633 switch (command) { 2634 case IEEE_MLME_STA_DEAUTH: 2635 // silently ignore 2636 break; 2637 2638 case IEEE_MLME_STA_DISASSOC: 2639 ieee80211_disassociate(ieee); 2640 break; 2641 2642 default: 2643 printk("Unknown MLME request: %d\n", command); 2644 ret = -EOPNOTSUPP; 2645 } 2646 2647 return ret; 2648} 2649 2650 2651static int ieee80211_wpa_set_wpa_ie(struct ieee80211_device *ieee, 2652 struct ieee_param *param, int plen) 2653{ 2654 u8 *buf; 2655 2656 if (param->u.wpa_ie.len > MAX_WPA_IE_LEN || 2657 (param->u.wpa_ie.len && param->u.wpa_ie.data == NULL)) 2658 return -EINVAL; 2659 2660 if (param->u.wpa_ie.len) { 2661 buf = kmemdup(param->u.wpa_ie.data, param->u.wpa_ie.len, 2662 GFP_KERNEL); 2663 if (buf == NULL) 2664 return -ENOMEM; 2665 2666 kfree(ieee->wpa_ie); 2667 ieee->wpa_ie = buf; 2668 ieee->wpa_ie_len = param->u.wpa_ie.len; 2669 } else { 2670 kfree(ieee->wpa_ie); 2671 ieee->wpa_ie = NULL; 2672 ieee->wpa_ie_len = 0; 2673 } 2674 2675 ieee80211_wpa_assoc_frame(ieee, ieee->wpa_ie, ieee->wpa_ie_len); 2676 return 0; 2677} 2678 2679#define AUTH_ALG_OPEN_SYSTEM 0x1 2680#define AUTH_ALG_SHARED_KEY 0x2 2681 2682static int ieee80211_wpa_set_auth_algs(struct ieee80211_device *ieee, int value) 2683{ 2684 2685 struct ieee80211_security sec = { 2686 .flags = SEC_AUTH_MODE, 2687 }; 2688 int ret = 0; 2689 2690 if (value & AUTH_ALG_SHARED_KEY) { 2691 sec.auth_mode = WLAN_AUTH_SHARED_KEY; 2692 ieee->open_wep = 0; 2693 } else { 2694 sec.auth_mode = WLAN_AUTH_OPEN; 2695 ieee->open_wep = 1; 2696 } 2697 2698 if (ieee->set_security) 2699 ieee->set_security(ieee->dev, &sec); 2700 else 2701 ret = -EOPNOTSUPP; 2702 2703 return ret; 2704} 2705 2706static int ieee80211_wpa_set_param(struct ieee80211_device *ieee, u8 name, u32 value) 2707{ 2708 int ret=0; 2709 unsigned long flags; 2710 2711 switch (name) { 2712 case IEEE_PARAM_WPA_ENABLED: 2713 ret = ieee80211_wpa_enable(ieee, value); 2714 break; 2715 2716 case IEEE_PARAM_TKIP_COUNTERMEASURES: 2717 ieee->tkip_countermeasures=value; 2718 break; 2719 2720 case IEEE_PARAM_DROP_UNENCRYPTED: { 2721 /* HACK: 2722 * 2723 * wpa_supplicant calls set_wpa_enabled when the driver 2724 * is loaded and unloaded, regardless of if WPA is being 2725 * used. No other calls are made which can be used to 2726 * determine if encryption will be used or not prior to 2727 * association being expected. If encryption is not being 2728 * used, drop_unencrypted is set to false, else true -- we 2729 * can use this to determine if the CAP_PRIVACY_ON bit should 2730 * be set. 2731 */ 2732 struct ieee80211_security sec = { 2733 .flags = SEC_ENABLED, 2734 .enabled = value, 2735 }; 2736 ieee->drop_unencrypted = value; 2737 /* We only change SEC_LEVEL for open mode. Others 2738 * are set by ipw_wpa_set_encryption. 2739 */ 2740 if (!value) { 2741 sec.flags |= SEC_LEVEL; 2742 sec.level = SEC_LEVEL_0; 2743 } 2744 else { 2745 sec.flags |= SEC_LEVEL; 2746 sec.level = SEC_LEVEL_1; 2747 } 2748 if (ieee->set_security) 2749 ieee->set_security(ieee->dev, &sec); 2750 break; 2751 } 2752 2753 case IEEE_PARAM_PRIVACY_INVOKED: 2754 ieee->privacy_invoked=value; 2755 break; 2756 2757 case IEEE_PARAM_AUTH_ALGS: 2758 ret = ieee80211_wpa_set_auth_algs(ieee, value); 2759 break; 2760 2761 case IEEE_PARAM_IEEE_802_1X: 2762 ieee->ieee802_1x=value; 2763 break; 2764 case IEEE_PARAM_WPAX_SELECT: 2765 // added for WPA2 mixed mode 2766 //printk(KERN_WARNING "------------------------>wpax value = %x\n", value); 2767 spin_lock_irqsave(&ieee->wpax_suitlist_lock,flags); 2768 ieee->wpax_type_set = 1; 2769 ieee->wpax_type_notify = value; 2770 spin_unlock_irqrestore(&ieee->wpax_suitlist_lock,flags); 2771 break; 2772 2773 default: 2774 printk("Unknown WPA param: %d\n",name); 2775 ret = -EOPNOTSUPP; 2776 } 2777 2778 return ret; 2779} 2780 2781/* implementation borrowed from hostap driver */ 2782 2783static int ieee80211_wpa_set_encryption(struct ieee80211_device *ieee, 2784 struct ieee_param *param, int param_len) 2785{ 2786 int ret = 0; 2787 2788 struct ieee80211_crypto_ops *ops; 2789 struct ieee80211_crypt_data **crypt; 2790 2791 struct ieee80211_security sec = { 2792 .flags = 0, 2793 }; 2794 2795 param->u.crypt.err = 0; 2796 param->u.crypt.alg[IEEE_CRYPT_ALG_NAME_LEN - 1] = '\0'; 2797 2798 if (param_len != 2799 (int) ((char *) param->u.crypt.key - (char *) param) + 2800 param->u.crypt.key_len) { 2801 printk("Len mismatch %d, %d\n", param_len, 2802 param->u.crypt.key_len); 2803 return -EINVAL; 2804 } 2805 if (param->sta_addr[0] == 0xff && param->sta_addr[1] == 0xff && 2806 param->sta_addr[2] == 0xff && param->sta_addr[3] == 0xff && 2807 param->sta_addr[4] == 0xff && param->sta_addr[5] == 0xff) { 2808 if (param->u.crypt.idx >= WEP_KEYS) 2809 return -EINVAL; 2810 crypt = &ieee->crypt[param->u.crypt.idx]; 2811 } else { 2812 return -EINVAL; 2813 } 2814 2815 if (strcmp(param->u.crypt.alg, "none") == 0) { 2816 if (crypt) { 2817 sec.enabled = 0; 2818 //sec.encrypt = 0; 2819 sec.level = SEC_LEVEL_0; 2820 sec.flags |= SEC_ENABLED | SEC_LEVEL; 2821 ieee80211_crypt_delayed_deinit(ieee, crypt); 2822 } 2823 goto done; 2824 } 2825 sec.enabled = 1; 2826// sec.encrypt = 1; 2827 sec.flags |= SEC_ENABLED; 2828 2829 /* IPW HW cannot build TKIP MIC, host decryption still needed. */ 2830 if (!(ieee->host_encrypt || ieee->host_decrypt) && 2831 strcmp(param->u.crypt.alg, "TKIP")) 2832 goto skip_host_crypt; 2833 2834 ops = ieee80211_get_crypto_ops(param->u.crypt.alg); 2835 if (ops == NULL && strcmp(param->u.crypt.alg, "WEP") == 0) 2836 ops = ieee80211_get_crypto_ops(param->u.crypt.alg); 2837 else if (ops == NULL && strcmp(param->u.crypt.alg, "TKIP") == 0) 2838 ops = ieee80211_get_crypto_ops(param->u.crypt.alg); 2839 else if (ops == NULL && strcmp(param->u.crypt.alg, "CCMP") == 0) 2840 ops = ieee80211_get_crypto_ops(param->u.crypt.alg); 2841 if (ops == NULL) { 2842 printk("unknown crypto alg '%s'\n", param->u.crypt.alg); 2843 param->u.crypt.err = IEEE_CRYPT_ERR_UNKNOWN_ALG; 2844 ret = -EINVAL; 2845 goto done; 2846 } 2847 2848 if (*crypt == NULL || (*crypt)->ops != ops) { 2849 struct ieee80211_crypt_data *new_crypt; 2850 2851 ieee80211_crypt_delayed_deinit(ieee, crypt); 2852 2853 new_crypt = kmalloc(sizeof(*new_crypt), GFP_KERNEL); 2854 if (new_crypt == NULL) { 2855 ret = -ENOMEM; 2856 goto done; 2857 } 2858 memset(new_crypt, 0, sizeof(struct ieee80211_crypt_data)); 2859 new_crypt->ops = ops; 2860 if (new_crypt->ops) 2861 new_crypt->priv = 2862 new_crypt->ops->init(param->u.crypt.idx); 2863 2864 if (new_crypt->priv == NULL) { 2865 kfree(new_crypt); 2866 param->u.crypt.err = IEEE_CRYPT_ERR_CRYPT_INIT_FAILED; 2867 ret = -EINVAL; 2868 goto done; 2869 } 2870 2871 *crypt = new_crypt; 2872 } 2873 2874 if (param->u.crypt.key_len > 0 && (*crypt)->ops->set_key && 2875 (*crypt)->ops->set_key(param->u.crypt.key, 2876 param->u.crypt.key_len, param->u.crypt.seq, 2877 (*crypt)->priv) < 0) { 2878 printk("key setting failed\n"); 2879 param->u.crypt.err = IEEE_CRYPT_ERR_KEY_SET_FAILED; 2880 ret = -EINVAL; 2881 goto done; 2882 } 2883 2884 skip_host_crypt: 2885 if (param->u.crypt.set_tx) { 2886 ieee->tx_keyidx = param->u.crypt.idx; 2887 sec.active_key = param->u.crypt.idx; 2888 sec.flags |= SEC_ACTIVE_KEY; 2889 } else 2890 sec.flags &= ~SEC_ACTIVE_KEY; 2891 2892 if (param->u.crypt.alg != NULL) { 2893 memcpy(sec.keys[param->u.crypt.idx], 2894 param->u.crypt.key, 2895 param->u.crypt.key_len); 2896 sec.key_sizes[param->u.crypt.idx] = param->u.crypt.key_len; 2897 sec.flags |= (1 << param->u.crypt.idx); 2898 2899 if (strcmp(param->u.crypt.alg, "WEP") == 0) { 2900 sec.flags |= SEC_LEVEL; 2901 sec.level = SEC_LEVEL_1; 2902 } else if (strcmp(param->u.crypt.alg, "TKIP") == 0) { 2903 sec.flags |= SEC_LEVEL; 2904 sec.level = SEC_LEVEL_2; 2905 } else if (strcmp(param->u.crypt.alg, "CCMP") == 0) { 2906 sec.flags |= SEC_LEVEL; 2907 sec.level = SEC_LEVEL_3; 2908 } 2909 } 2910 done: 2911 if (ieee->set_security) 2912 ieee->set_security(ieee->dev, &sec); 2913 2914 /* Do not reset port if card is in Managed mode since resetting will 2915 * generate new IEEE 802.11 authentication which may end up in looping 2916 * with IEEE 802.1X. If your hardware requires a reset after WEP 2917 * configuration (for example... Prism2), implement the reset_port in 2918 * the callbacks structures used to initialize the 802.11 stack. */ 2919 if (ieee->reset_on_keychange && 2920 ieee->iw_mode != IW_MODE_INFRA && 2921 ieee->reset_port && 2922 ieee->reset_port(ieee->dev)) { 2923 printk("reset_port failed\n"); 2924 param->u.crypt.err = IEEE_CRYPT_ERR_CARD_CONF_FAILED; 2925 return -EINVAL; 2926 } 2927 2928 return ret; 2929} 2930 2931int ieee80211_wpa_supplicant_ioctl(struct ieee80211_device *ieee, struct iw_point *p) 2932{ 2933 struct ieee_param *param; 2934 int ret=0; 2935 2936 down(&ieee->wx_sem); 2937 //IEEE_DEBUG_INFO("wpa_supplicant: len=%d\n", p->length); 2938 2939 if (p->length < sizeof(struct ieee_param) || !p->pointer){ 2940 ret = -EINVAL; 2941 goto out; 2942 } 2943 2944 param = kmalloc(p->length, GFP_KERNEL); 2945 if (param == NULL){ 2946 ret = -ENOMEM; 2947 goto out; 2948 } 2949 if (copy_from_user(param, p->pointer, p->length)) { 2950 kfree(param); 2951 ret = -EFAULT; 2952 goto out; 2953 } 2954 2955 switch (param->cmd) { 2956 2957 case IEEE_CMD_SET_WPA_PARAM: 2958 ret = ieee80211_wpa_set_param(ieee, param->u.wpa_param.name, 2959 param->u.wpa_param.value); 2960 break; 2961 2962 case IEEE_CMD_SET_WPA_IE: 2963 ret = ieee80211_wpa_set_wpa_ie(ieee, param, p->length); 2964 break; 2965 2966 case IEEE_CMD_SET_ENCRYPTION: 2967 ret = ieee80211_wpa_set_encryption(ieee, param, p->length); 2968 break; 2969 2970 case IEEE_CMD_MLME: 2971 ret = ieee80211_wpa_mlme(ieee, param->u.mlme.command, 2972 param->u.mlme.reason_code); 2973 break; 2974 2975 default: 2976 printk("Unknown WPA supplicant request: %d\n",param->cmd); 2977 ret = -EOPNOTSUPP; 2978 break; 2979 } 2980 2981 if (ret == 0 && copy_to_user(p->pointer, param, p->length)) 2982 ret = -EFAULT; 2983 2984 kfree(param); 2985out: 2986 up(&ieee->wx_sem); 2987 2988 return ret; 2989} 2990 2991void notify_wx_assoc_event(struct ieee80211_device *ieee) 2992{ 2993 union iwreq_data wrqu; 2994 wrqu.ap_addr.sa_family = ARPHRD_ETHER; 2995 if (ieee->state == IEEE80211_LINKED) 2996 memcpy(wrqu.ap_addr.sa_data, ieee->current_network.bssid, ETH_ALEN); 2997 else 2998 memset(wrqu.ap_addr.sa_data, 0, ETH_ALEN); 2999 wireless_send_event(ieee->dev, SIOCGIWAP, &wrqu, NULL); 3000} 3001