1 /******************************************************************************
2 * Copyright(c) 2008 - 2010 Realtek Corporation. All rights reserved.
3 * Linux device driver for RTL8192U
5 * Based on the r8187 driver, which is:
6 * Copyright 2004-2005 Andrea Merello <andreamrl@tiscali.it>, et al.
7 * This program is free software; you can redistribute it and/or modify it
8 * under the terms of version 2 of the GNU General Public License as
9 * published by the Free Software Foundation.
11 * This program is distributed in the hope that it will be useful, but WITHOUT
12 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
13 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
16 * You should have received a copy of the GNU General Public License along with
17 * this program; if not, write to the Free Software Foundation, Inc.,
18 * 51 Franklin Street, Fifth Floor, Boston, MA 02110, USA
20 * The full GNU General Public License is included in this distribution in the
21 * file called LICENSE.
23 * Contact Information:
24 * Jerry chuang <wlanfae@realtek.com>
27 #ifndef CONFIG_FORCE_HARD_FLOAT
28 double __floatsidf (int i) { return i; }
29 unsigned int __fixunsdfsi (double d) { return d; }
30 double __adddf3(double a, double b) { return a+b; }
31 double __addsf3(float a, float b) { return a+b; }
32 double __subdf3(double a, double b) { return a-b; }
33 double __extendsfdf2(float a) {return a;}
40 #undef RX_DONT_PASS_UL
42 #undef DEBUG_RX_VERBOSE
48 #undef DEBUG_TX_FILLDESC
53 #undef DEBUG_REGISTERS
55 #undef DEBUG_IRQ_TASKLET
59 #define CONFIG_RTL8192_IO_MAP
61 #include <asm/uaccess.h>
62 #include "r8192U_hw.h"
64 #include "r8190_rtl8256.h" /* RTL8225 Radio frontend */
65 #include "r8180_93cx6.h" /* Card EEPROM */
66 #include "r8192U_wx.h"
67 #include "r819xU_phy.h" //added by WB 4.30.2008
68 #include "r819xU_phyreg.h"
69 #include "r819xU_cmdpkt.h"
70 #include "r8192U_dm.h"
71 //#include "r8192xU_phyreg.h"
72 #include <linux/usb.h>
73 #include <linux/slab.h>
74 // FIXME: check if 2.6.7 is ok
76 #ifdef CONFIG_RTL8192_PM
83 //set here to open your trace code. //WB
84 u32 rt_global_debug_component = \
92 // COMP_POWER_TRACKING |
103 COMP_ERR ; //always open err flags on
105 #define TOTAL_CAM_ENTRY 32
106 #define CAM_CONTENT_COUNT 8
108 static const struct usb_device_id rtl8192_usb_id_tbl[] = {
110 {USB_DEVICE(0x0bda, 0x8192)},
111 {USB_DEVICE(0x0bda, 0x8709)},
113 {USB_DEVICE(0x07aa, 0x0043)},
115 {USB_DEVICE(0x050d, 0x805E)},
117 {USB_DEVICE(0x0df6, 0x0031)},
119 {USB_DEVICE(0x1740, 0x9201)},
121 {USB_DEVICE(0x2001, 0x3301)},
123 {USB_DEVICE(0x5a57, 0x0290)},
127 MODULE_LICENSE("GPL");
128 MODULE_VERSION("V 1.1");
129 MODULE_DEVICE_TABLE(usb, rtl8192_usb_id_tbl);
130 MODULE_DESCRIPTION("Linux driver for Realtek RTL8192 USB WiFi cards");
132 static char* ifname = "wlan%d";
133 static int hwwep = 1; //default use hw. set 0 to use software security
134 static int channels = 0x3fff;
138 module_param(ifname, charp, S_IRUGO|S_IWUSR );
139 //module_param(hwseqnum,int, S_IRUGO|S_IWUSR);
140 module_param(hwwep,int, S_IRUGO|S_IWUSR);
141 module_param(channels,int, S_IRUGO|S_IWUSR);
143 MODULE_PARM_DESC(ifname," Net interface name, wlan%d=default");
144 //MODULE_PARM_DESC(hwseqnum," Try to use hardware 802.11 header sequence numbers. Zero=default");
145 MODULE_PARM_DESC(hwwep," Try to use hardware security support. ");
146 MODULE_PARM_DESC(channels," Channel bitmask for specific locales. NYI");
148 static int __devinit rtl8192_usb_probe(struct usb_interface *intf,
149 const struct usb_device_id *id);
150 static void __devexit rtl8192_usb_disconnect(struct usb_interface *intf);
153 static struct usb_driver rtl8192_usb_driver = {
154 .name = RTL819xU_MODULE_NAME, /* Driver name */
155 .id_table = rtl8192_usb_id_tbl, /* PCI_ID table */
156 .probe = rtl8192_usb_probe, /* probe fn */
157 .disconnect = rtl8192_usb_disconnect, /* remove fn */
158 #ifdef CONFIG_RTL8192_PM
159 .suspend = rtl8192_suspend, /* PM suspend fn */
160 .resume = rtl8192_resume, /* PM resume fn */
162 .suspend = NULL, /* PM suspend fn */
163 .resume = NULL, /* PM resume fn */
169 typedef struct _CHANNEL_LIST
173 }CHANNEL_LIST, *PCHANNEL_LIST;
175 static CHANNEL_LIST ChannelPlan[] = {
176 {{1,2,3,4,5,6,7,8,9,10,11,36,40,44,48,52,56,60,64,149,153,157,161,165},24}, //FCC
177 {{1,2,3,4,5,6,7,8,9,10,11},11}, //IC
178 {{1,2,3,4,5,6,7,8,9,10,11,12,13,36,40,44,48,52,56,60,64},21}, //ETSI
179 {{1,2,3,4,5,6,7,8,9,10,11,12,13},13}, //Spain. Change to ETSI.
180 {{1,2,3,4,5,6,7,8,9,10,11,12,13},13}, //France. Change to ETSI.
181 {{1,2,3,4,5,6,7,8,9,10,11,12,13,14,36,40,44,48,52,56,60,64},22}, //MKK //MKK
182 {{1,2,3,4,5,6,7,8,9,10,11,12,13,14,36,40,44,48,52,56,60,64},22},//MKK1
183 {{1,2,3,4,5,6,7,8,9,10,11,12,13},13}, //Israel.
184 {{1,2,3,4,5,6,7,8,9,10,11,12,13,14,36,40,44,48,52,56,60,64},22}, // For 11a , TELEC
185 {{1,2,3,4,5,6,7,8,9,10,11,12,13,14,36,40,44,48,52,56,60,64}, 22}, //MIC
186 {{1,2,3,4,5,6,7,8,9,10,11,12,13,14},14} //For Global Domain. 1-11:active scan, 12-14 passive scan. //+YJ, 080626
189 static void rtl819x_set_channel_map(u8 channel_plan, struct r8192_priv* priv)
191 int i, max_chan=-1, min_chan=-1;
192 struct ieee80211_device* ieee = priv->ieee80211;
193 switch (channel_plan)
195 case COUNTRY_CODE_FCC:
196 case COUNTRY_CODE_IC:
197 case COUNTRY_CODE_ETSI:
198 case COUNTRY_CODE_SPAIN:
199 case COUNTRY_CODE_FRANCE:
200 case COUNTRY_CODE_MKK:
201 case COUNTRY_CODE_MKK1:
202 case COUNTRY_CODE_ISRAEL:
203 case COUNTRY_CODE_TELEC:
204 case COUNTRY_CODE_MIC:
207 ieee->bGlobalDomain = false;
208 //acturally 8225 & 8256 rf chip only support B,G,24N mode
209 if ((priv->rf_chip == RF_8225) || (priv->rf_chip == RF_8256))
216 RT_TRACE(COMP_ERR, "unknown rf chip, can't set channel map in function:%s()\n", __FUNCTION__);
218 if (ChannelPlan[channel_plan].Len != 0){
219 // Clear old channel map
220 memset(GET_DOT11D_INFO(ieee)->channel_map, 0, sizeof(GET_DOT11D_INFO(ieee)->channel_map));
221 // Set new channel map
222 for (i=0;i<ChannelPlan[channel_plan].Len;i++)
224 if (ChannelPlan[channel_plan].Channel[i] < min_chan || ChannelPlan[channel_plan].Channel[i] > max_chan)
226 GET_DOT11D_INFO(ieee)->channel_map[ChannelPlan[channel_plan].Channel[i]] = 1;
231 case COUNTRY_CODE_GLOBAL_DOMAIN:
233 GET_DOT11D_INFO(ieee)->bEnabled = 0;//this flag enabled to follow 11d country IE setting, otherwise, it shall follow global domain settings.
235 ieee->bGlobalDomain = true;
245 #define eqMacAddr(a,b) ( ((a)[0]==(b)[0] && (a)[1]==(b)[1] && (a)[2]==(b)[2] && (a)[3]==(b)[3] && (a)[4]==(b)[4] && (a)[5]==(b)[5]) ? 1:0 )
247 #define rx_hal_is_cck_rate(_pdrvinfo)\
248 (_pdrvinfo->RxRate == DESC90_RATE1M ||\
249 _pdrvinfo->RxRate == DESC90_RATE2M ||\
250 _pdrvinfo->RxRate == DESC90_RATE5_5M ||\
251 _pdrvinfo->RxRate == DESC90_RATE11M) &&\
255 void CamResetAllEntry(struct net_device *dev)
258 //2004/02/11 In static WEP, OID_ADD_KEY or OID_ADD_WEP are set before STA associate to AP.
259 // However, ResetKey is called on OID_802_11_INFRASTRUCTURE_MODE and MlmeAssociateRequest
260 // In this condition, Cam can not be reset because upper layer will not set this static key again.
261 //if(Adapter->EncAlgorithm == WEP_Encryption)
264 //DbgPrint("========================================\n");
265 //DbgPrint(" Call ResetAllEntry \n");
266 //DbgPrint("========================================\n\n");
267 ulcommand |= BIT31|BIT30;
268 write_nic_dword(dev, RWCAM, ulcommand);
273 void write_cam(struct net_device *dev, u8 addr, u32 data)
275 write_nic_dword(dev, WCAMI, data);
276 write_nic_dword(dev, RWCAM, BIT31|BIT16|(addr&0xff) );
279 u32 read_cam(struct net_device *dev, u8 addr)
281 write_nic_dword(dev, RWCAM, 0x80000000|(addr&0xff) );
282 return read_nic_dword(dev, 0xa8);
285 void write_nic_byte_E(struct net_device *dev, int indx, u8 data)
288 struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
289 struct usb_device *udev = priv->udev;
291 status = usb_control_msg(udev, usb_sndctrlpipe(udev, 0),
292 RTL8187_REQ_SET_REGS, RTL8187_REQT_WRITE,
293 indx|0xfe00, 0, &data, 1, HZ / 2);
297 printk("write_nic_byte_E TimeOut! status:%d\n", status);
301 u8 read_nic_byte_E(struct net_device *dev, int indx)
305 struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
306 struct usb_device *udev = priv->udev;
308 status = usb_control_msg(udev, usb_rcvctrlpipe(udev, 0),
309 RTL8187_REQ_GET_REGS, RTL8187_REQT_READ,
310 indx|0xfe00, 0, &data, 1, HZ / 2);
314 printk("read_nic_byte_E TimeOut! status:%d\n", status);
319 //as 92U has extend page from 4 to 16, so modify functions below.
320 void write_nic_byte(struct net_device *dev, int indx, u8 data)
324 struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
325 struct usb_device *udev = priv->udev;
327 status = usb_control_msg(udev, usb_sndctrlpipe(udev, 0),
328 RTL8187_REQ_SET_REGS, RTL8187_REQT_WRITE,
329 (indx&0xff)|0xff00, (indx>>8)&0x0f, &data, 1, HZ / 2);
333 printk("write_nic_byte TimeOut! status:%d\n", status);
340 void write_nic_word(struct net_device *dev, int indx, u16 data)
345 struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
346 struct usb_device *udev = priv->udev;
348 status = usb_control_msg(udev, usb_sndctrlpipe(udev, 0),
349 RTL8187_REQ_SET_REGS, RTL8187_REQT_WRITE,
350 (indx&0xff)|0xff00, (indx>>8)&0x0f, &data, 2, HZ / 2);
354 printk("write_nic_word TimeOut! status:%d\n", status);
360 void write_nic_dword(struct net_device *dev, int indx, u32 data)
365 struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
366 struct usb_device *udev = priv->udev;
368 status = usb_control_msg(udev, usb_sndctrlpipe(udev, 0),
369 RTL8187_REQ_SET_REGS, RTL8187_REQT_WRITE,
370 (indx&0xff)|0xff00, (indx>>8)&0x0f, &data, 4, HZ / 2);
375 printk("write_nic_dword TimeOut! status:%d\n", status);
382 u8 read_nic_byte(struct net_device *dev, int indx)
386 struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
387 struct usb_device *udev = priv->udev;
389 status = usb_control_msg(udev, usb_rcvctrlpipe(udev, 0),
390 RTL8187_REQ_GET_REGS, RTL8187_REQT_READ,
391 (indx&0xff)|0xff00, (indx>>8)&0x0f, &data, 1, HZ / 2);
395 printk("read_nic_byte TimeOut! status:%d\n", status);
403 u16 read_nic_word(struct net_device *dev, int indx)
407 struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
408 struct usb_device *udev = priv->udev;
410 status = usb_control_msg(udev, usb_rcvctrlpipe(udev, 0),
411 RTL8187_REQ_GET_REGS, RTL8187_REQT_READ,
412 (indx&0xff)|0xff00, (indx>>8)&0x0f, &data, 2, HZ / 2);
416 printk("read_nic_word TimeOut! status:%d\n", status);
423 u16 read_nic_word_E(struct net_device *dev, int indx)
427 struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
428 struct usb_device *udev = priv->udev;
430 status = usb_control_msg(udev, usb_rcvctrlpipe(udev, 0),
431 RTL8187_REQ_GET_REGS, RTL8187_REQT_READ,
432 indx|0xfe00, 0, &data, 2, HZ / 2);
436 printk("read_nic_word TimeOut! status:%d\n", status);
443 u32 read_nic_dword(struct net_device *dev, int indx)
449 struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
450 struct usb_device *udev = priv->udev;
452 status = usb_control_msg(udev, usb_rcvctrlpipe(udev, 0),
453 RTL8187_REQ_GET_REGS, RTL8187_REQT_READ,
454 (indx&0xff)|0xff00, (indx>>8)&0x0f, &data, 4, HZ / 2);
456 // printk(KERN_WARNING "read size of data = %d\, date = %d\n", result, data);
461 printk("read_nic_dword TimeOut! status:%d\n", status);
470 //u8 read_phy_cck(struct net_device *dev, u8 adr);
471 //u8 read_phy_ofdm(struct net_device *dev, u8 adr);
472 /* this might still called in what was the PHY rtl8185/rtl8192 common code
473 * plans are to possibilty turn it again in one common code...
475 inline void force_pci_posting(struct net_device *dev)
480 static struct net_device_stats *rtl8192_stats(struct net_device *dev);
481 void rtl8192_commit(struct net_device *dev);
482 //void rtl8192_restart(struct net_device *dev);
483 void rtl8192_restart(struct work_struct *work);
484 //void rtl8192_rq_tx_ack(struct work_struct *work);
486 void watch_dog_timer_callback(unsigned long data);
488 /****************************************************************************
489 -----------------------------PROCFS STUFF-------------------------
490 *****************************************************************************/
492 static struct proc_dir_entry *rtl8192_proc = NULL;
496 static int proc_get_stats_ap(char *page, char **start,
497 off_t offset, int count,
498 int *eof, void *data)
500 struct net_device *dev = data;
501 struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
502 struct ieee80211_device *ieee = priv->ieee80211;
503 struct ieee80211_network *target;
507 list_for_each_entry(target, &ieee->network_list, list) {
509 len += snprintf(page + len, count - len,
510 "%s ", target->ssid);
512 if(target->wpa_ie_len>0 || target->rsn_ie_len>0){
513 len += snprintf(page + len, count - len,
517 len += snprintf(page + len, count - len,
527 static int proc_get_registers(char *page, char **start,
528 off_t offset, int count,
529 int *eof, void *data)
531 struct net_device *dev = data;
532 // struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
539 /* This dump the current register page */
540 len += snprintf(page + len, count - len,
541 "\n####################page 0##################\n ");
545 //printk( "\nD: %2x> ", n);
546 len += snprintf(page + len, count - len,
549 for(i=0;i<16 && n<=max;i++,n++)
550 len += snprintf(page + len, count - len,
551 "%2x ",read_nic_byte(dev,0x000|n));
553 // printk("%2x ",read_nic_byte(dev,n));
555 len += snprintf(page + len, count - len,
556 "\n####################page 1##################\n ");
559 //printk( "\nD: %2x> ", n);
560 len += snprintf(page + len, count - len,
563 for(i=0;i<16 && n<=max;i++,n++)
564 len += snprintf(page + len, count - len,
565 "%2x ",read_nic_byte(dev,0x100|n));
567 // printk("%2x ",read_nic_byte(dev,n));
569 len += snprintf(page + len, count - len,
570 "\n####################page 3##################\n ");
573 //printk( "\nD: %2x> ", n);
574 len += snprintf(page + len, count - len,
577 for(i=0;i<16 && n<=max;i++,n++)
578 len += snprintf(page + len, count - len,
579 "%2x ",read_nic_byte(dev,0x300|n));
581 // printk("%2x ",read_nic_byte(dev,n));
585 len += snprintf(page + len, count - len,"\n");
595 static int proc_get_stats_tx(char *page, char **start,
596 off_t offset, int count,
597 int *eof, void *data)
599 struct net_device *dev = data;
600 struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
604 len += snprintf(page + len, count - len,
605 "TX VI priority ok int: %lu\n"
606 "TX VI priority error int: %lu\n"
607 "TX VO priority ok int: %lu\n"
608 "TX VO priority error int: %lu\n"
609 "TX BE priority ok int: %lu\n"
610 "TX BE priority error int: %lu\n"
611 "TX BK priority ok int: %lu\n"
612 "TX BK priority error int: %lu\n"
613 "TX MANAGE priority ok int: %lu\n"
614 "TX MANAGE priority error int: %lu\n"
615 "TX BEACON priority ok int: %lu\n"
616 "TX BEACON priority error int: %lu\n"
617 // "TX high priority ok int: %lu\n"
618 // "TX high priority failed error int: %lu\n"
619 "TX queue resume: %lu\n"
620 "TX queue stopped?: %d\n"
621 "TX fifo overflow: %lu\n"
622 // "TX beacon: %lu\n"
627 // "TX HW queue: %d\n"
628 "TX VI dropped: %lu\n"
629 "TX VO dropped: %lu\n"
630 "TX BE dropped: %lu\n"
631 "TX BK dropped: %lu\n"
632 "TX total data packets %lu\n",
633 // "TX beacon aborted: %lu\n",
634 priv->stats.txviokint,
636 priv->stats.txvookint,
638 priv->stats.txbeokint,
640 priv->stats.txbkokint,
642 priv->stats.txmanageokint,
643 priv->stats.txmanageerr,
644 priv->stats.txbeaconokint,
645 priv->stats.txbeaconerr,
646 // priv->stats.txhpokint,
647 // priv->stats.txhperr,
648 priv->stats.txresumed,
649 netif_queue_stopped(dev),
650 priv->stats.txoverflow,
651 // priv->stats.txbeacon,
652 atomic_read(&(priv->tx_pending[VI_PRIORITY])),
653 atomic_read(&(priv->tx_pending[VO_PRIORITY])),
654 atomic_read(&(priv->tx_pending[BE_PRIORITY])),
655 atomic_read(&(priv->tx_pending[BK_PRIORITY])),
656 // read_nic_byte(dev, TXFIFOCOUNT),
657 priv->stats.txvidrop,
658 priv->stats.txvodrop,
659 priv->stats.txbedrop,
660 priv->stats.txbkdrop,
661 priv->stats.txdatapkt
662 // priv->stats.txbeaconerr
671 static int proc_get_stats_rx(char *page, char **start,
672 off_t offset, int count,
673 int *eof, void *data)
675 struct net_device *dev = data;
676 struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
680 len += snprintf(page + len, count - len,
682 "RX urb status error: %lu\n"
683 "RX invalid urb error: %lu\n",
684 priv->stats.rxoktotal,
685 priv->stats.rxstaterr,
686 priv->stats.rxurberr);
691 void rtl8192_proc_module_init(void)
693 RT_TRACE(COMP_INIT, "Initializing proc filesystem");
694 rtl8192_proc=create_proc_entry(RTL819xU_MODULE_NAME, S_IFDIR, init_net.proc_net);
698 void rtl8192_proc_module_remove(void)
700 remove_proc_entry(RTL819xU_MODULE_NAME, init_net.proc_net);
704 void rtl8192_proc_remove_one(struct net_device *dev)
706 struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
710 // remove_proc_entry("stats-hw", priv->dir_dev);
711 remove_proc_entry("stats-tx", priv->dir_dev);
712 remove_proc_entry("stats-rx", priv->dir_dev);
713 // remove_proc_entry("stats-ieee", priv->dir_dev);
714 remove_proc_entry("stats-ap", priv->dir_dev);
715 remove_proc_entry("registers", priv->dir_dev);
716 // remove_proc_entry("cck-registers",priv->dir_dev);
717 // remove_proc_entry("ofdm-registers",priv->dir_dev);
718 //remove_proc_entry(dev->name, rtl8192_proc);
719 remove_proc_entry("wlan0", rtl8192_proc);
720 priv->dir_dev = NULL;
725 void rtl8192_proc_init_one(struct net_device *dev)
727 struct proc_dir_entry *e;
728 struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
729 priv->dir_dev = create_proc_entry(dev->name,
730 S_IFDIR | S_IRUGO | S_IXUGO,
732 if (!priv->dir_dev) {
733 RT_TRACE(COMP_ERR, "Unable to initialize /proc/net/rtl8192/%s\n",
737 e = create_proc_read_entry("stats-rx", S_IFREG | S_IRUGO,
738 priv->dir_dev, proc_get_stats_rx, dev);
741 RT_TRACE(COMP_ERR,"Unable to initialize "
742 "/proc/net/rtl8192/%s/stats-rx\n",
747 e = create_proc_read_entry("stats-tx", S_IFREG | S_IRUGO,
748 priv->dir_dev, proc_get_stats_tx, dev);
751 RT_TRACE(COMP_ERR, "Unable to initialize "
752 "/proc/net/rtl8192/%s/stats-tx\n",
756 e = create_proc_read_entry("stats-ap", S_IFREG | S_IRUGO,
757 priv->dir_dev, proc_get_stats_ap, dev);
760 RT_TRACE(COMP_ERR, "Unable to initialize "
761 "/proc/net/rtl8192/%s/stats-ap\n",
765 e = create_proc_read_entry("registers", S_IFREG | S_IRUGO,
766 priv->dir_dev, proc_get_registers, dev);
768 RT_TRACE(COMP_ERR, "Unable to initialize "
769 "/proc/net/rtl8192/%s/registers\n",
773 /****************************************************************************
774 -----------------------------MISC STUFF-------------------------
775 *****************************************************************************/
777 /* this is only for debugging */
778 void print_buffer(u32 *buffer, int len)
781 u8 *buf =(u8*)buffer;
783 printk("ASCII BUFFER DUMP (len: %x):\n",len);
788 printk("\nBINARY BUFFER DUMP (len: %x):\n",len);
796 //short check_nic_enough_desc(struct net_device *dev, priority_t priority)
797 short check_nic_enough_desc(struct net_device *dev,int queue_index)
799 struct r8192_priv *priv = ieee80211_priv(dev);
800 int used = atomic_read(&priv->tx_pending[queue_index]);
802 return (used < MAX_TX_URB);
805 void tx_timeout(struct net_device *dev)
807 struct r8192_priv *priv = ieee80211_priv(dev);
808 //rtl8192_commit(dev);
810 schedule_work(&priv->reset_wq);
811 //DMESG("TXTIMEOUT");
815 /* this is only for debug */
816 void dump_eprom(struct net_device *dev)
820 RT_TRACE(COMP_EPROM, "EEPROM addr %x : %x", i, eprom_read(dev,i));
823 /* this is only for debug */
824 void rtl8192_dump_reg(struct net_device *dev)
830 RT_TRACE(COMP_PHY, "Dumping NIC register map");
834 printk( "\nD: %2x> ", n);
835 for(i=0;i<16 && n<=max;i++,n++)
836 printk("%2x ",read_nic_byte(dev,n));
841 /****************************************************************************
842 ------------------------------HW STUFF---------------------------
843 *****************************************************************************/
846 void rtl8192_set_mode(struct net_device *dev,int mode)
849 ecmd=read_nic_byte(dev, EPROM_CMD);
850 ecmd=ecmd &~ EPROM_CMD_OPERATING_MODE_MASK;
851 ecmd=ecmd | (mode<<EPROM_CMD_OPERATING_MODE_SHIFT);
852 ecmd=ecmd &~ (1<<EPROM_CS_SHIFT);
853 ecmd=ecmd &~ (1<<EPROM_CK_SHIFT);
854 write_nic_byte(dev, EPROM_CMD, ecmd);
858 void rtl8192_update_msr(struct net_device *dev)
860 struct r8192_priv *priv = ieee80211_priv(dev);
863 msr = read_nic_byte(dev, MSR);
864 msr &= ~ MSR_LINK_MASK;
866 /* do not change in link_state != WLAN_LINK_ASSOCIATED.
867 * msr must be updated if the state is ASSOCIATING.
868 * this is intentional and make sense for ad-hoc and
869 * master (see the create BSS/IBSS func)
871 if (priv->ieee80211->state == IEEE80211_LINKED){
873 if (priv->ieee80211->iw_mode == IW_MODE_INFRA)
874 msr |= (MSR_LINK_MANAGED<<MSR_LINK_SHIFT);
875 else if (priv->ieee80211->iw_mode == IW_MODE_ADHOC)
876 msr |= (MSR_LINK_ADHOC<<MSR_LINK_SHIFT);
877 else if (priv->ieee80211->iw_mode == IW_MODE_MASTER)
878 msr |= (MSR_LINK_MASTER<<MSR_LINK_SHIFT);
881 msr |= (MSR_LINK_NONE<<MSR_LINK_SHIFT);
883 write_nic_byte(dev, MSR, msr);
886 void rtl8192_set_chan(struct net_device *dev,short ch)
888 struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
890 RT_TRACE(COMP_CH, "=====>%s()====ch:%d\n", __FUNCTION__, ch);
893 /* this hack should avoid frame TX during channel setting*/
896 // tx = read_nic_dword(dev,TX_CONF);
897 // tx &= ~TX_LOOPBACK_MASK;
900 // write_nic_dword(dev,TX_CONF, tx |( TX_LOOPBACK_MAC<<TX_LOOPBACK_SHIFT));
902 //need to implement rf set channel here WB
904 if (priv->rf_set_chan)
905 priv->rf_set_chan(dev,priv->chan);
907 // write_nic_dword(dev,TX_CONF,tx | (TX_LOOPBACK_NONE<<TX_LOOPBACK_SHIFT));
911 static void rtl8192_rx_isr(struct urb *urb);
912 //static void rtl8192_rx_isr(struct urb *rx_urb);
914 u32 get_rxpacket_shiftbytes_819xusb(struct ieee80211_rx_stats *pstats)
917 #ifdef USB_RX_AGGREGATION_SUPPORT
918 if (pstats->bisrxaggrsubframe)
919 return (sizeof(rx_desc_819x_usb) + pstats->RxDrvInfoSize
920 + pstats->RxBufShift + 8);
923 return (sizeof(rx_desc_819x_usb) + pstats->RxDrvInfoSize
924 + pstats->RxBufShift);
927 static int rtl8192_rx_initiate(struct net_device*dev)
929 struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
932 struct rtl8192_rx_info *info;
934 /* nomal packet rx procedure */
935 while (skb_queue_len(&priv->rx_queue) < MAX_RX_URB) {
936 skb = __dev_alloc_skb(RX_URB_SIZE, GFP_KERNEL);
939 entry = usb_alloc_urb(0, GFP_KERNEL);
944 // printk("nomal packet IN request!\n");
945 usb_fill_bulk_urb(entry, priv->udev,
946 usb_rcvbulkpipe(priv->udev, 3), skb_tail_pointer(skb),
947 RX_URB_SIZE, rtl8192_rx_isr, skb);
948 info = (struct rtl8192_rx_info *) skb->cb;
951 info->out_pipe = 3; //denote rx normal packet queue
952 skb_queue_tail(&priv->rx_queue, skb);
953 usb_submit_urb(entry, GFP_KERNEL);
956 /* command packet rx procedure */
957 while (skb_queue_len(&priv->rx_queue) < MAX_RX_URB + 3) {
958 // printk("command packet IN request!\n");
959 skb = __dev_alloc_skb(RX_URB_SIZE ,GFP_KERNEL);
962 entry = usb_alloc_urb(0, GFP_KERNEL);
967 usb_fill_bulk_urb(entry, priv->udev,
968 usb_rcvbulkpipe(priv->udev, 9), skb_tail_pointer(skb),
969 RX_URB_SIZE, rtl8192_rx_isr, skb);
970 info = (struct rtl8192_rx_info *) skb->cb;
973 info->out_pipe = 9; //denote rx cmd packet queue
974 skb_queue_tail(&priv->rx_queue, skb);
975 usb_submit_urb(entry, GFP_KERNEL);
981 void rtl8192_set_rxconf(struct net_device *dev)
983 struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
986 rxconf=read_nic_dword(dev,RCR);
987 rxconf = rxconf &~ MAC_FILTER_MASK;
988 rxconf = rxconf | RCR_AMF;
989 rxconf = rxconf | RCR_ADF;
990 rxconf = rxconf | RCR_AB;
991 rxconf = rxconf | RCR_AM;
992 //rxconf = rxconf | RCR_ACF;
994 if (dev->flags & IFF_PROMISC) {DMESG ("NIC in promisc mode");}
996 if(priv->ieee80211->iw_mode == IW_MODE_MONITOR || \
997 dev->flags & IFF_PROMISC){
998 rxconf = rxconf | RCR_AAP;
999 } /*else if(priv->ieee80211->iw_mode == IW_MODE_MASTER){
1000 rxconf = rxconf | (1<<ACCEPT_ALLMAC_FRAME_SHIFT);
1001 rxconf = rxconf | (1<<RX_CHECK_BSSID_SHIFT);
1003 rxconf = rxconf | RCR_APM;
1004 rxconf = rxconf | RCR_CBSSID;
1008 if(priv->ieee80211->iw_mode == IW_MODE_MONITOR){
1009 rxconf = rxconf | RCR_AICV;
1010 rxconf = rxconf | RCR_APWRMGT;
1013 if( priv->crcmon == 1 && priv->ieee80211->iw_mode == IW_MODE_MONITOR)
1014 rxconf = rxconf | RCR_ACRC32;
1017 rxconf = rxconf &~ RX_FIFO_THRESHOLD_MASK;
1018 rxconf = rxconf | (RX_FIFO_THRESHOLD_NONE<<RX_FIFO_THRESHOLD_SHIFT);
1019 rxconf = rxconf &~ MAX_RX_DMA_MASK;
1020 rxconf = rxconf | ((u32)7<<RCR_MXDMA_OFFSET);
1022 // rxconf = rxconf | (1<<RX_AUTORESETPHY_SHIFT);
1023 rxconf = rxconf | RCR_ONLYERLPKT;
1025 // rxconf = rxconf &~ RCR_CS_MASK;
1026 // rxconf = rxconf | (1<<RCR_CS_SHIFT);
1028 write_nic_dword(dev, RCR, rxconf);
1031 DMESG("rxconf: %x %x",rxconf ,read_nic_dword(dev,RCR));
1034 //wait to be removed
1035 void rtl8192_rx_enable(struct net_device *dev)
1039 //struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
1041 rtl8192_rx_initiate(dev);
1043 // rtl8192_set_rxconf(dev);
1047 void rtl8192_tx_enable(struct net_device *dev)
1053 void rtl8192_rtx_disable(struct net_device *dev)
1056 struct r8192_priv *priv = ieee80211_priv(dev);
1057 struct sk_buff *skb;
1058 struct rtl8192_rx_info *info;
1060 cmd=read_nic_byte(dev,CMDR);
1061 write_nic_byte(dev, CMDR, cmd &~ \
1063 force_pci_posting(dev);
1066 while ((skb = __skb_dequeue(&priv->rx_queue))) {
1067 info = (struct rtl8192_rx_info *) skb->cb;
1071 usb_kill_urb(info->urb);
1075 if (skb_queue_len(&priv->skb_queue)) {
1076 printk(KERN_WARNING "skb_queue not empty\n");
1079 skb_queue_purge(&priv->skb_queue);
1084 int alloc_tx_beacon_desc_ring(struct net_device *dev, int count)
1089 inline u16 ieeerate2rtlrate(int rate)
1121 static u16 rtl_rate[] = {10,20,55,110,60,90,120,180,240,360,480,540};
1122 inline u16 rtl8192_rate2rate(short rate)
1124 if (rate >11) return 0;
1125 return rtl_rate[rate];
1129 /* The protype of rx_isr has changed since one verion of Linux Kernel */
1130 static void rtl8192_rx_isr(struct urb *urb)
1132 struct sk_buff *skb = (struct sk_buff *) urb->context;
1133 struct rtl8192_rx_info *info = (struct rtl8192_rx_info *)skb->cb;
1134 struct net_device *dev = info->dev;
1135 struct r8192_priv *priv = ieee80211_priv(dev);
1136 int out_pipe = info->out_pipe;
1140 if (unlikely(urb->status)) {
1142 priv->stats.rxstaterr++;
1143 priv->ieee80211->stats.rx_errors++;
1145 // printk("%s():rx status err\n",__FUNCTION__);
1148 skb_unlink(skb, &priv->rx_queue);
1149 skb_put(skb, urb->actual_length);
1151 skb_queue_tail(&priv->skb_queue, skb);
1152 tasklet_schedule(&priv->irq_rx_tasklet);
1154 skb = dev_alloc_skb(RX_URB_SIZE);
1155 if (unlikely(!skb)) {
1157 printk("%s():can,t alloc skb\n",__FUNCTION__);
1158 /* TODO check rx queue length and refill *somewhere* */
1162 usb_fill_bulk_urb(urb, priv->udev,
1163 usb_rcvbulkpipe(priv->udev, out_pipe), skb_tail_pointer(skb),
1164 RX_URB_SIZE, rtl8192_rx_isr, skb);
1166 info = (struct rtl8192_rx_info *) skb->cb;
1169 info->out_pipe = out_pipe;
1171 urb->transfer_buffer = skb_tail_pointer(skb);
1173 skb_queue_tail(&priv->rx_queue, skb);
1174 err = usb_submit_urb(urb, GFP_ATOMIC);
1175 if(err && err != EPERM)
1176 printk("can not submit rxurb, err is %x,URB status is %x\n",err,urb->status);
1180 rtl819xusb_rx_command_packet(
1181 struct net_device *dev,
1182 struct ieee80211_rx_stats *pstats
1187 //RT_TRACE(COMP_RECV, DBG_TRACE, ("---> RxCommandPacketHandle819xUsb()\n"));
1189 status = cmpk_message_handle_rx(dev, pstats);
1192 DMESG("rxcommandpackethandle819xusb: It is a command packet\n");
1196 //RT_TRACE(COMP_RECV, DBG_TRACE, ("RxCommandPacketHandle819xUsb: It is not a command packet\n"));
1199 //RT_TRACE(COMP_RECV, DBG_TRACE, ("<--- RxCommandPacketHandle819xUsb()\n"));
1204 void rtl8192_data_hard_stop(struct net_device *dev)
1210 void rtl8192_data_hard_resume(struct net_device *dev)
1215 /* this function TX data frames when the ieee80211 stack requires this.
1216 * It checks also if we need to stop the ieee tx queue, eventually do it
1218 void rtl8192_hard_data_xmit(struct sk_buff *skb, struct net_device *dev, int rate)
1220 struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
1222 unsigned long flags;
1223 cb_desc *tcb_desc = (cb_desc *)(skb->cb + MAX_DEV_ADDR_SIZE);
1224 u8 queue_index = tcb_desc->queue_index;
1226 /* shall not be referred by command packet */
1227 assert(queue_index != TXCMD_QUEUE);
1229 spin_lock_irqsave(&priv->tx_lock,flags);
1231 memcpy((unsigned char *)(skb->cb),&dev,sizeof(dev));
1232 // tcb_desc->RATRIndex = 7;
1233 // tcb_desc->bTxDisableRateFallBack = 1;
1234 // tcb_desc->bTxUseDriverAssingedRate = 1;
1235 tcb_desc->bTxEnableFwCalcDur = 1;
1236 skb_push(skb, priv->ieee80211->tx_headroom);
1237 ret = rtl8192_tx(dev, skb);
1239 //priv->ieee80211->stats.tx_bytes+=(skb->len - priv->ieee80211->tx_headroom);
1240 //priv->ieee80211->stats.tx_packets++;
1242 spin_unlock_irqrestore(&priv->tx_lock,flags);
1248 /* This is a rough attempt to TX a frame
1249 * This is called by the ieee 80211 stack to TX management frames.
1250 * If the ring is full packet are dropped (for data frame the queue
1251 * is stopped before this can happen).
1253 int rtl8192_hard_start_xmit(struct sk_buff *skb,struct net_device *dev)
1255 struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
1257 unsigned long flags;
1258 cb_desc *tcb_desc = (cb_desc *)(skb->cb + MAX_DEV_ADDR_SIZE);
1259 u8 queue_index = tcb_desc->queue_index;
1262 spin_lock_irqsave(&priv->tx_lock,flags);
1264 memcpy((unsigned char *)(skb->cb),&dev,sizeof(dev));
1265 if(queue_index == TXCMD_QUEUE) {
1266 skb_push(skb, USB_HWDESC_HEADER_LEN);
1267 rtl819xU_tx_cmd(dev, skb);
1269 spin_unlock_irqrestore(&priv->tx_lock,flags);
1272 skb_push(skb, priv->ieee80211->tx_headroom);
1273 ret = rtl8192_tx(dev, skb);
1276 spin_unlock_irqrestore(&priv->tx_lock,flags);
1282 void rtl8192_try_wake_queue(struct net_device *dev, int pri);
1284 #ifdef USB_TX_DRIVER_AGGREGATION_ENABLE
1285 u16 DrvAggr_PaddingAdd(struct net_device *dev, struct sk_buff *skb)
1287 u16 PaddingNum = 256 - ((skb->len + TX_PACKET_DRVAGGR_SUBFRAME_SHIFT_BYTES) % 256);
1288 return (PaddingNum&0xff);
1291 u8 MRateToHwRate8190Pci(u8 rate);
1292 u8 QueryIsShort(u8 TxHT, u8 TxRate, cb_desc *tcb_desc);
1293 u8 MapHwQueueToFirmwareQueue(u8 QueueID);
1294 struct sk_buff *DrvAggr_Aggregation(struct net_device *dev, struct ieee80211_drv_agg_txb *pSendList)
1296 struct ieee80211_device *ieee = netdev_priv(dev);
1297 struct r8192_priv *priv = ieee80211_priv(dev);
1298 cb_desc *tcb_desc = NULL;
1301 struct sk_buff *skb;
1302 struct sk_buff *agg_skb;
1303 tx_desc_819x_usb_aggr_subframe *tx_agg_desc = NULL;
1304 tx_fwinfo_819x_usb *tx_fwinfo = NULL;
1307 // Local variable initialization.
1309 /* first skb initialization */
1310 skb = pSendList->tx_agg_frames[0];
1311 TotalLength = skb->len;
1313 /* Get the total aggregation length including the padding space and
1316 for(i = 1; i < pSendList->nr_drv_agg_frames; i++) {
1317 TotalLength += DrvAggr_PaddingAdd(dev, skb);
1318 skb = pSendList->tx_agg_frames[i];
1319 TotalLength += (skb->len + TX_PACKET_DRVAGGR_SUBFRAME_SHIFT_BYTES);
1322 /* allocate skb to contain the aggregated packets */
1323 agg_skb = dev_alloc_skb(TotalLength + ieee->tx_headroom);
1324 memset(agg_skb->data, 0, agg_skb->len);
1325 skb_reserve(agg_skb, ieee->tx_headroom);
1327 // RT_DEBUG_DATA(COMP_SEND, skb->cb, sizeof(skb->cb));
1328 /* reserve info for first subframe Tx descriptor to be set in the tx function */
1329 skb = pSendList->tx_agg_frames[0];
1330 tcb_desc = (cb_desc *)(skb->cb + MAX_DEV_ADDR_SIZE);
1331 tcb_desc->drv_agg_enable = 1;
1332 tcb_desc->pkt_size = skb->len;
1333 tcb_desc->DrvAggrNum = pSendList->nr_drv_agg_frames;
1334 printk("DrvAggNum = %d\n", tcb_desc->DrvAggrNum);
1335 // RT_DEBUG_DATA(COMP_SEND, skb->cb, sizeof(skb->cb));
1336 // printk("========>skb->data ======> \n");
1337 // RT_DEBUG_DATA(COMP_SEND, skb->data, skb->len);
1338 memcpy(agg_skb->cb, skb->cb, sizeof(skb->cb));
1339 memcpy(skb_put(agg_skb,skb->len),skb->data,skb->len);
1341 for(i = 1; i < pSendList->nr_drv_agg_frames; i++) {
1342 /* push the next sub frame to be 256 byte aline */
1343 skb_put(agg_skb,DrvAggr_PaddingAdd(dev,skb));
1345 /* Subframe drv Tx descriptor and firmware info setting */
1346 skb = pSendList->tx_agg_frames[i];
1347 tcb_desc = (cb_desc *)(skb->cb + MAX_DEV_ADDR_SIZE);
1348 tx_agg_desc = (tx_desc_819x_usb_aggr_subframe *)agg_skb->tail;
1349 tx_fwinfo = (tx_fwinfo_819x_usb *)(agg_skb->tail + sizeof(tx_desc_819x_usb_aggr_subframe));
1351 memset(tx_fwinfo,0,sizeof(tx_fwinfo_819x_usb));
1353 tx_fwinfo->TxHT = (tcb_desc->data_rate&0x80)?1:0;
1354 tx_fwinfo->TxRate = MRateToHwRate8190Pci(tcb_desc->data_rate);
1355 tx_fwinfo->EnableCPUDur = tcb_desc->bTxEnableFwCalcDur;
1356 tx_fwinfo->Short = QueryIsShort(tx_fwinfo->TxHT, tx_fwinfo->TxRate, tcb_desc);
1357 if(tcb_desc->bAMPDUEnable) {//AMPDU enabled
1358 tx_fwinfo->AllowAggregation = 1;
1360 tx_fwinfo->RxMF = tcb_desc->ampdu_factor;
1361 tx_fwinfo->RxAMD = tcb_desc->ampdu_density&0x07;//ampdudensity
1363 tx_fwinfo->AllowAggregation = 0;
1365 tx_fwinfo->RxMF = 0;
1366 tx_fwinfo->RxAMD = 0;
1369 /* Protection mode related */
1370 tx_fwinfo->RtsEnable = (tcb_desc->bRTSEnable)?1:0;
1371 tx_fwinfo->CtsEnable = (tcb_desc->bCTSEnable)?1:0;
1372 tx_fwinfo->RtsSTBC = (tcb_desc->bRTSSTBC)?1:0;
1373 tx_fwinfo->RtsHT = (tcb_desc->rts_rate&0x80)?1:0;
1374 tx_fwinfo->RtsRate = MRateToHwRate8190Pci((u8)tcb_desc->rts_rate);
1375 tx_fwinfo->RtsSubcarrier = (tx_fwinfo->RtsHT==0)?(tcb_desc->RTSSC):0;
1376 tx_fwinfo->RtsBandwidth = (tx_fwinfo->RtsHT==1)?((tcb_desc->bRTSBW)?1:0):0;
1377 tx_fwinfo->RtsShort = (tx_fwinfo->RtsHT==0)?(tcb_desc->bRTSUseShortPreamble?1:0):\
1378 (tcb_desc->bRTSUseShortGI?1:0);
1380 /* Set Bandwidth and sub-channel settings. */
1381 if(priv->CurrentChannelBW == HT_CHANNEL_WIDTH_20_40)
1383 if(tcb_desc->bPacketBW) {
1384 tx_fwinfo->TxBandwidth = 1;
1385 tx_fwinfo->TxSubCarrier = 0; //By SD3's Jerry suggestion, use duplicated mode
1387 tx_fwinfo->TxBandwidth = 0;
1388 tx_fwinfo->TxSubCarrier = priv->nCur40MhzPrimeSC;
1391 tx_fwinfo->TxBandwidth = 0;
1392 tx_fwinfo->TxSubCarrier = 0;
1395 /* Fill Tx descriptor */
1396 memset(tx_agg_desc, 0, sizeof(tx_desc_819x_usb_aggr_subframe));
1398 //tx_agg_desc->LINIP = 0;
1399 //tx_agg_desc->CmdInit = 1;
1400 tx_agg_desc->Offset = sizeof(tx_fwinfo_819x_usb) + 8;
1401 /* already raw data, need not to substract header length */
1402 tx_agg_desc->PktSize = skb->len & 0xffff;
1405 tx_agg_desc->SecCAMID= 0;
1406 tx_agg_desc->RATid = tcb_desc->RATRIndex;
1409 tx_agg_desc->NoEnc = 1;
1411 tx_agg_desc->SecType = 0x0;
1413 if (tcb_desc->bHwSec) {
1414 switch (priv->ieee80211->pairwise_key_type)
1416 case KEY_TYPE_WEP40:
1417 case KEY_TYPE_WEP104:
1418 tx_agg_desc->SecType = 0x1;
1419 tx_agg_desc->NoEnc = 0;
1422 tx_agg_desc->SecType = 0x2;
1423 tx_agg_desc->NoEnc = 0;
1426 tx_agg_desc->SecType = 0x3;
1427 tx_agg_desc->NoEnc = 0;
1430 tx_agg_desc->SecType = 0x0;
1431 tx_agg_desc->NoEnc = 1;
1436 tx_agg_desc->QueueSelect = MapHwQueueToFirmwareQueue(tcb_desc->queue_index);
1437 tx_agg_desc->TxFWInfoSize = sizeof(tx_fwinfo_819x_usb);
1439 tx_agg_desc->DISFB = tcb_desc->bTxDisableRateFallBack;
1440 tx_agg_desc->USERATE = tcb_desc->bTxUseDriverAssingedRate;
1442 tx_agg_desc->OWN = 1;
1445 /* According windows driver, it seems that there no need to fill this field */
1446 //tx_agg_desc->TxBufferSize= (u32)(skb->len - USB_HWDESC_HEADER_LEN);
1448 /* to fill next packet */
1449 skb_put(agg_skb,TX_PACKET_DRVAGGR_SUBFRAME_SHIFT_BYTES);
1450 memcpy(skb_put(agg_skb,skb->len),skb->data,skb->len);
1453 for(i = 0; i < pSendList->nr_drv_agg_frames; i++) {
1454 dev_kfree_skb_any(pSendList->tx_agg_frames[i]);
1461 This function return a list of PTCB which is proper to be aggregate with the input TCB.
1462 If no proper TCB is found to do aggregation, SendList will only contain the input TCB.
1464 u8 DrvAggr_GetAggregatibleList(struct net_device *dev, struct sk_buff *skb,
1465 struct ieee80211_drv_agg_txb *pSendList)
1467 struct ieee80211_device *ieee = netdev_priv(dev);
1468 PRT_HIGH_THROUGHPUT pHTInfo = ieee->pHTInfo;
1469 u16 nMaxAggrNum = pHTInfo->UsbTxAggrNum;
1470 cb_desc *tcb_desc = (cb_desc *)(skb->cb + MAX_DEV_ADDR_SIZE);
1471 u8 QueueID = tcb_desc->queue_index;
1474 pSendList->tx_agg_frames[pSendList->nr_drv_agg_frames++] = skb;
1475 if(pSendList->nr_drv_agg_frames >= nMaxAggrNum) {
1479 } while((skb = skb_dequeue(&ieee->skb_drv_aggQ[QueueID])));
1481 RT_TRACE(COMP_AMSDU, "DrvAggr_GetAggregatibleList, nAggrTcbNum = %d \n", pSendList->nr_drv_agg_frames);
1482 return pSendList->nr_drv_agg_frames;
1486 static void rtl8192_tx_isr(struct urb *tx_urb)
1488 struct sk_buff *skb = (struct sk_buff*)tx_urb->context;
1489 struct net_device *dev = NULL;
1490 struct r8192_priv *priv = NULL;
1491 cb_desc *tcb_desc = (cb_desc *)(skb->cb + MAX_DEV_ADDR_SIZE);
1492 u8 queue_index = tcb_desc->queue_index;
1493 // bool bToSend0Byte;
1494 // u16 BufLen = skb->len;
1496 memcpy(&dev,(struct net_device*)(skb->cb),sizeof(struct net_device*));
1497 priv = ieee80211_priv(dev);
1499 if(tcb_desc->queue_index != TXCMD_QUEUE) {
1500 if(tx_urb->status == 0) {
1501 dev->trans_start = jiffies;
1502 // As act as station mode, destion shall be unicast address.
1503 //priv->ieee80211->stats.tx_bytes+=(skb->len - priv->ieee80211->tx_headroom);
1504 //priv->ieee80211->stats.tx_packets++;
1505 priv->stats.txoktotal++;
1506 priv->ieee80211->LinkDetectInfo.NumTxOkInPeriod++;
1507 priv->stats.txbytesunicast += (skb->len - priv->ieee80211->tx_headroom);
1509 priv->ieee80211->stats.tx_errors++;
1510 //priv->stats.txmanageerr++;
1515 /* free skb and tx_urb */
1517 dev_kfree_skb_any(skb);
1518 usb_free_urb(tx_urb);
1519 atomic_dec(&priv->tx_pending[queue_index]);
1524 // Handle HW Beacon:
1525 // We had transfer our beacon frame to host controler at this moment.
1529 // Handling the wait queue of command packets.
1530 // For Tx command packets, we must not do TCB fragment because it is not handled right now.
1531 // We must cut the packets to match the size of TX_CMD_PKT before we send it.
1534 /* Handle MPDU in wait queue. */
1535 if(queue_index != BEACON_QUEUE) {
1536 /* Don't send data frame during scanning.*/
1537 if((skb_queue_len(&priv->ieee80211->skb_waitQ[queue_index]) != 0)&&\
1538 (!(priv->ieee80211->queue_stop))) {
1539 if(NULL != (skb = skb_dequeue(&(priv->ieee80211->skb_waitQ[queue_index]))))
1540 priv->ieee80211->softmac_hard_start_xmit(skb, dev);
1542 return; //modified by david to avoid further processing AMSDU
1544 #ifdef USB_TX_DRIVER_AGGREGATION_ENABLE
1545 else if ((skb_queue_len(&priv->ieee80211->skb_drv_aggQ[queue_index])!= 0)&&\
1546 (!(priv->ieee80211->queue_stop))) {
1547 // Tx Driver Aggregation process
1548 /* The driver will aggregation the packets according to the following stets
1549 * 1. check whether there's tx irq available, for it's a completion return
1550 * function, it should contain enough tx irq;
1551 * 2. check pakcet type;
1552 * 3. intialize sendlist, check whether the to-be send packet no greater than 1
1553 * 4. aggregation the packets, and fill firmware info and tx desc to it, etc.
1554 * 5. check whehter the packet could be sent, otherwise just insert to wait head
1556 skb = skb_dequeue(&priv->ieee80211->skb_drv_aggQ[queue_index]);
1557 if(!check_nic_enough_desc(dev, queue_index)) {
1558 skb_queue_head(&(priv->ieee80211->skb_drv_aggQ[queue_index]), skb);
1565 u8* pHeader = skb->data;
1567 if(IsMgntQosData(pHeader) ||
1568 IsMgntQData_Ack(pHeader) ||
1569 IsMgntQData_Poll(pHeader) ||
1570 IsMgntQData_Poll_Ack(pHeader)
1574 struct ieee80211_drv_agg_txb SendList;
1576 memset(&SendList, 0, sizeof(struct ieee80211_drv_agg_txb));
1577 if(DrvAggr_GetAggregatibleList(dev, skb, &SendList) > 1) {
1578 skb = DrvAggr_Aggregation(dev, &SendList);
1582 priv->ieee80211->softmac_hard_start_xmit(skb, dev);
1591 void rtl8192_beacon_stop(struct net_device *dev)
1594 struct r8192_priv *priv = ieee80211_priv(dev);
1596 msr = read_nic_byte(dev, MSR);
1597 msrm = msr & MSR_LINK_MASK;
1598 msr2 = msr & ~MSR_LINK_MASK;
1600 if(NIC_8192U == priv->card_8192) {
1601 usb_kill_urb(priv->rx_urb[MAX_RX_URB]);
1603 if ((msrm == (MSR_LINK_ADHOC<<MSR_LINK_SHIFT) ||
1604 (msrm == (MSR_LINK_MASTER<<MSR_LINK_SHIFT)))){
1605 write_nic_byte(dev, MSR, msr2 | MSR_LINK_NONE);
1606 write_nic_byte(dev, MSR, msr);
1610 void rtl8192_config_rate(struct net_device* dev, u16* rate_config)
1612 struct r8192_priv *priv = ieee80211_priv(dev);
1613 struct ieee80211_network *net;
1614 u8 i=0, basic_rate = 0;
1615 net = & priv->ieee80211->current_network;
1617 for (i=0; i<net->rates_len; i++)
1619 basic_rate = net->rates[i]&0x7f;
1622 case MGN_1M: *rate_config |= RRSR_1M; break;
1623 case MGN_2M: *rate_config |= RRSR_2M; break;
1624 case MGN_5_5M: *rate_config |= RRSR_5_5M; break;
1625 case MGN_11M: *rate_config |= RRSR_11M; break;
1626 case MGN_6M: *rate_config |= RRSR_6M; break;
1627 case MGN_9M: *rate_config |= RRSR_9M; break;
1628 case MGN_12M: *rate_config |= RRSR_12M; break;
1629 case MGN_18M: *rate_config |= RRSR_18M; break;
1630 case MGN_24M: *rate_config |= RRSR_24M; break;
1631 case MGN_36M: *rate_config |= RRSR_36M; break;
1632 case MGN_48M: *rate_config |= RRSR_48M; break;
1633 case MGN_54M: *rate_config |= RRSR_54M; break;
1636 for (i=0; i<net->rates_ex_len; i++)
1638 basic_rate = net->rates_ex[i]&0x7f;
1641 case MGN_1M: *rate_config |= RRSR_1M; break;
1642 case MGN_2M: *rate_config |= RRSR_2M; break;
1643 case MGN_5_5M: *rate_config |= RRSR_5_5M; break;
1644 case MGN_11M: *rate_config |= RRSR_11M; break;
1645 case MGN_6M: *rate_config |= RRSR_6M; break;
1646 case MGN_9M: *rate_config |= RRSR_9M; break;
1647 case MGN_12M: *rate_config |= RRSR_12M; break;
1648 case MGN_18M: *rate_config |= RRSR_18M; break;
1649 case MGN_24M: *rate_config |= RRSR_24M; break;
1650 case MGN_36M: *rate_config |= RRSR_36M; break;
1651 case MGN_48M: *rate_config |= RRSR_48M; break;
1652 case MGN_54M: *rate_config |= RRSR_54M; break;
1658 #define SHORT_SLOT_TIME 9
1659 #define NON_SHORT_SLOT_TIME 20
1661 void rtl8192_update_cap(struct net_device* dev, u16 cap)
1664 struct r8192_priv *priv = ieee80211_priv(dev);
1665 struct ieee80211_network *net = &priv->ieee80211->current_network;
1666 priv->short_preamble = cap & WLAN_CAPABILITY_SHORT_PREAMBLE;
1667 tmp = priv->basic_rate;
1668 if (priv->short_preamble)
1669 tmp |= BRSR_AckShortPmb;
1670 write_nic_dword(dev, RRSR, tmp);
1672 if (net->mode & (IEEE_G|IEEE_N_24G))
1675 if ((cap & WLAN_CAPABILITY_SHORT_SLOT)&&(!priv->ieee80211->pHTInfo->bCurrentRT2RTLongSlotTime))
1677 slot_time = SHORT_SLOT_TIME;
1679 else //long slot time
1680 slot_time = NON_SHORT_SLOT_TIME;
1681 priv->slot_time = slot_time;
1682 write_nic_byte(dev, SLOT_TIME, slot_time);
1686 void rtl8192_net_update(struct net_device *dev)
1689 struct r8192_priv *priv = ieee80211_priv(dev);
1690 struct ieee80211_network *net;
1691 u16 BcnTimeCfg = 0, BcnCW = 6, BcnIFS = 0xf;
1692 u16 rate_config = 0;
1693 net = & priv->ieee80211->current_network;
1695 rtl8192_config_rate(dev, &rate_config);
1696 priv->basic_rate = rate_config &= 0x15f;
1698 write_nic_dword(dev,BSSIDR,((u32*)net->bssid)[0]);
1699 write_nic_word(dev,BSSIDR+4,((u16*)net->bssid)[2]);
1700 //for(i=0;i<ETH_ALEN;i++)
1701 // write_nic_byte(dev,BSSID+i,net->bssid[i]);
1703 rtl8192_update_msr(dev);
1704 // rtl8192_update_cap(dev, net->capability);
1705 if (priv->ieee80211->iw_mode == IW_MODE_ADHOC)
1707 write_nic_word(dev, ATIMWND, 2);
1708 write_nic_word(dev, BCN_DMATIME, 1023);
1709 write_nic_word(dev, BCN_INTERVAL, net->beacon_interval);
1710 // write_nic_word(dev, BcnIntTime, 100);
1711 write_nic_word(dev, BCN_DRV_EARLY_INT, 1);
1712 write_nic_byte(dev, BCN_ERR_THRESH, 100);
1713 BcnTimeCfg |= (BcnCW<<BCN_TCFG_CW_SHIFT);
1714 // TODO: BcnIFS may required to be changed on ASIC
1715 BcnTimeCfg |= BcnIFS<<BCN_TCFG_IFS;
1717 write_nic_word(dev, BCN_TCFG, BcnTimeCfg);
1724 //temporary hw beacon is not used any more.
1725 //open it when necessary
1726 void rtl819xusb_beacon_tx(struct net_device *dev,u16 tx_rate)
1730 inline u8 rtl8192_IsWirelessBMode(u16 rate)
1732 if( ((rate <= 110) && (rate != 60) && (rate != 90)) || (rate == 220) )
1737 u16 N_DBPSOfRate(u16 DataRate);
1742 u8 bManagementFrame,
1750 if( rtl8192_IsWirelessBMode(DataRate) )
1752 if( bManagementFrame || !bShortPreamble || DataRate == 10 )
1754 FrameTime = (u16)(144+48+(FrameLength*8/(DataRate/10)));
1758 FrameTime = (u16)(72+24+(FrameLength*8/(DataRate/10)));
1760 if( ( FrameLength*8 % (DataRate/10) ) != 0 ) //Get the Ceilling
1762 } else { //802.11g DSSS-OFDM PLCP length field calculation.
1763 N_DBPS = N_DBPSOfRate(DataRate);
1764 Ceiling = (16 + 8*FrameLength + 6) / N_DBPS
1765 + (((16 + 8*FrameLength + 6) % N_DBPS) ? 1 : 0);
1766 FrameTime = (u16)(16 + 4 + 4*Ceiling + 6);
1771 u16 N_DBPSOfRate(u16 DataRate)
1816 void rtl819xU_cmd_isr(struct urb *tx_cmd_urb, struct pt_regs *regs)
1818 usb_free_urb(tx_cmd_urb);
1821 unsigned int txqueue2outpipe(struct r8192_priv* priv,unsigned int tx_queue) {
1825 RT_TRACE(COMP_ERR,"%s():Unknown queue ID!!!\n",__FUNCTION__);
1828 return priv->txqueue_to_outpipemap[tx_queue];
1831 short rtl819xU_tx_cmd(struct net_device *dev, struct sk_buff *skb)
1833 struct r8192_priv *priv = ieee80211_priv(dev);
1838 unsigned int idx_pipe;
1839 tx_desc_cmd_819x_usb *pdesc = (tx_desc_cmd_819x_usb *)skb->data;
1840 cb_desc *tcb_desc = (cb_desc *)(skb->cb + MAX_DEV_ADDR_SIZE);
1841 u8 queue_index = tcb_desc->queue_index;
1843 //printk("\n %s::queue_index = %d\n",__FUNCTION__, queue_index);
1844 atomic_inc(&priv->tx_pending[queue_index]);
1845 tx_urb = usb_alloc_urb(0,GFP_ATOMIC);
1851 memset(pdesc, 0, USB_HWDESC_HEADER_LEN);
1852 /* Tx descriptor ought to be set according to the skb->cb */
1853 pdesc->FirstSeg = 1;//bFirstSeg;
1854 pdesc->LastSeg = 1;//bLastSeg;
1855 pdesc->CmdInit = tcb_desc->bCmdOrInit;
1856 pdesc->TxBufferSize = tcb_desc->txbuf_size;
1858 pdesc->LINIP = tcb_desc->bLastIniPkt;
1860 //----------------------------------------------------------------------------
1861 // Fill up USB_OUT_CONTEXT.
1862 //----------------------------------------------------------------------------
1863 // Get index to out pipe from specified QueueID.
1864 #ifndef USE_ONE_PIPE
1865 idx_pipe = txqueue2outpipe(priv,queue_index);
1869 #ifdef JOHN_DUMP_TXDESC
1871 printk("<Tx descriptor>--rate %x---",rate);
1872 for (i = 0; i < 8; i++)
1873 printk("%8x ", tx[i]);
1876 usb_fill_bulk_urb(tx_urb,priv->udev, usb_sndbulkpipe(priv->udev,idx_pipe), \
1877 skb->data, skb->len, rtl8192_tx_isr, skb);
1879 status = usb_submit_urb(tx_urb, GFP_ATOMIC);
1884 DMESGE("Error TX CMD URB, error %d",
1891 * Mapping Software/Hardware descriptor queue id to "Queue Select Field"
1892 * in TxFwInfo data structure
1893 * 2006.10.30 by Emily
1895 * \param QUEUEID Software Queue
1897 u8 MapHwQueueToFirmwareQueue(u8 QueueID)
1899 u8 QueueSelect = 0x0; //defualt set to
1903 QueueSelect = QSLT_BE; //or QSelect = pTcb->priority;
1907 QueueSelect = QSLT_BK; //or QSelect = pTcb->priority;
1911 QueueSelect = QSLT_VO; //or QSelect = pTcb->priority;
1915 QueueSelect = QSLT_VI; //or QSelect = pTcb->priority;
1918 QueueSelect = QSLT_MGNT;
1922 QueueSelect = QSLT_BEACON;
1925 // TODO: 2006.10.30 mark other queue selection until we verify it is OK
1926 // TODO: Remove Assertions
1927 //#if (RTL819X_FPGA_VER & RTL819X_FPGA_GUANGAN_070502)
1929 QueueSelect = QSLT_CMD;
1933 QueueSelect = QSLT_HIGH;
1937 RT_TRACE(COMP_ERR, "TransmitTCB(): Impossible Queue Selection: %d \n", QueueID);
1943 u8 MRateToHwRate8190Pci(u8 rate)
1945 u8 ret = DESC90_RATE1M;
1948 case MGN_1M: ret = DESC90_RATE1M; break;
1949 case MGN_2M: ret = DESC90_RATE2M; break;
1950 case MGN_5_5M: ret = DESC90_RATE5_5M; break;
1951 case MGN_11M: ret = DESC90_RATE11M; break;
1952 case MGN_6M: ret = DESC90_RATE6M; break;
1953 case MGN_9M: ret = DESC90_RATE9M; break;
1954 case MGN_12M: ret = DESC90_RATE12M; break;
1955 case MGN_18M: ret = DESC90_RATE18M; break;
1956 case MGN_24M: ret = DESC90_RATE24M; break;
1957 case MGN_36M: ret = DESC90_RATE36M; break;
1958 case MGN_48M: ret = DESC90_RATE48M; break;
1959 case MGN_54M: ret = DESC90_RATE54M; break;
1961 // HT rate since here
1962 case MGN_MCS0: ret = DESC90_RATEMCS0; break;
1963 case MGN_MCS1: ret = DESC90_RATEMCS1; break;
1964 case MGN_MCS2: ret = DESC90_RATEMCS2; break;
1965 case MGN_MCS3: ret = DESC90_RATEMCS3; break;
1966 case MGN_MCS4: ret = DESC90_RATEMCS4; break;
1967 case MGN_MCS5: ret = DESC90_RATEMCS5; break;
1968 case MGN_MCS6: ret = DESC90_RATEMCS6; break;
1969 case MGN_MCS7: ret = DESC90_RATEMCS7; break;
1970 case MGN_MCS8: ret = DESC90_RATEMCS8; break;
1971 case MGN_MCS9: ret = DESC90_RATEMCS9; break;
1972 case MGN_MCS10: ret = DESC90_RATEMCS10; break;
1973 case MGN_MCS11: ret = DESC90_RATEMCS11; break;
1974 case MGN_MCS12: ret = DESC90_RATEMCS12; break;
1975 case MGN_MCS13: ret = DESC90_RATEMCS13; break;
1976 case MGN_MCS14: ret = DESC90_RATEMCS14; break;
1977 case MGN_MCS15: ret = DESC90_RATEMCS15; break;
1978 case (0x80|0x20): ret = DESC90_RATEMCS32; break;
1986 u8 QueryIsShort(u8 TxHT, u8 TxRate, cb_desc *tcb_desc)
1990 tmp_Short = (TxHT==1)?((tcb_desc->bUseShortGI)?1:0):((tcb_desc->bUseShortPreamble)?1:0);
1992 if(TxHT==1 && TxRate != DESC90_RATEMCS15)
1998 static void tx_zero_isr(struct urb *tx_urb)
2004 * The tx procedure is just as following,
2005 * skb->cb will contain all the following information,
2006 * priority, morefrag, rate, &dev.
2008 short rtl8192_tx(struct net_device *dev, struct sk_buff* skb)
2010 struct r8192_priv *priv = ieee80211_priv(dev);
2011 cb_desc *tcb_desc = (cb_desc *)(skb->cb + MAX_DEV_ADDR_SIZE);
2012 tx_desc_819x_usb *tx_desc = (tx_desc_819x_usb *)skb->data;
2013 tx_fwinfo_819x_usb *tx_fwinfo = (tx_fwinfo_819x_usb *)(skb->data + USB_HWDESC_HEADER_LEN);
2014 struct usb_device *udev = priv->udev;
2017 struct urb *tx_urb = NULL, *tx_urb_zero = NULL;
2019 unsigned int idx_pipe;
2020 // RT_DEBUG_DATA(COMP_SEND, tcb_desc, sizeof(cb_desc));
2021 // printk("=============> %s\n", __FUNCTION__);
2022 pend = atomic_read(&priv->tx_pending[tcb_desc->queue_index]);
2023 /* we are locked here so the two atomic_read and inc are executed
2024 * without interleaves
2025 * !!! For debug purpose
2027 if( pend > MAX_TX_URB){
2028 printk("To discard skb packet!\n");
2029 dev_kfree_skb_any(skb);
2033 tx_urb = usb_alloc_urb(0,GFP_ATOMIC);
2035 dev_kfree_skb_any(skb);
2039 /* Fill Tx firmware info */
2040 memset(tx_fwinfo,0,sizeof(tx_fwinfo_819x_usb));
2042 tx_fwinfo->TxHT = (tcb_desc->data_rate&0x80)?1:0;
2043 tx_fwinfo->TxRate = MRateToHwRate8190Pci(tcb_desc->data_rate);
2044 tx_fwinfo->EnableCPUDur = tcb_desc->bTxEnableFwCalcDur;
2045 tx_fwinfo->Short = QueryIsShort(tx_fwinfo->TxHT, tx_fwinfo->TxRate, tcb_desc);
2046 if(tcb_desc->bAMPDUEnable) {//AMPDU enabled
2047 tx_fwinfo->AllowAggregation = 1;
2049 tx_fwinfo->RxMF = tcb_desc->ampdu_factor;
2050 tx_fwinfo->RxAMD = tcb_desc->ampdu_density&0x07;//ampdudensity
2052 tx_fwinfo->AllowAggregation = 0;
2054 tx_fwinfo->RxMF = 0;
2055 tx_fwinfo->RxAMD = 0;
2058 /* Protection mode related */
2059 tx_fwinfo->RtsEnable = (tcb_desc->bRTSEnable)?1:0;
2060 tx_fwinfo->CtsEnable = (tcb_desc->bCTSEnable)?1:0;
2061 tx_fwinfo->RtsSTBC = (tcb_desc->bRTSSTBC)?1:0;
2062 tx_fwinfo->RtsHT = (tcb_desc->rts_rate&0x80)?1:0;
2063 tx_fwinfo->RtsRate = MRateToHwRate8190Pci((u8)tcb_desc->rts_rate);
2064 tx_fwinfo->RtsSubcarrier = (tx_fwinfo->RtsHT==0)?(tcb_desc->RTSSC):0;
2065 tx_fwinfo->RtsBandwidth = (tx_fwinfo->RtsHT==1)?((tcb_desc->bRTSBW)?1:0):0;
2066 tx_fwinfo->RtsShort = (tx_fwinfo->RtsHT==0)?(tcb_desc->bRTSUseShortPreamble?1:0):\
2067 (tcb_desc->bRTSUseShortGI?1:0);
2069 /* Set Bandwidth and sub-channel settings. */
2070 if(priv->CurrentChannelBW == HT_CHANNEL_WIDTH_20_40)
2072 if(tcb_desc->bPacketBW) {
2073 tx_fwinfo->TxBandwidth = 1;
2074 tx_fwinfo->TxSubCarrier = 0; //By SD3's Jerry suggestion, use duplicated mode
2076 tx_fwinfo->TxBandwidth = 0;
2077 tx_fwinfo->TxSubCarrier = priv->nCur40MhzPrimeSC;
2080 tx_fwinfo->TxBandwidth = 0;
2081 tx_fwinfo->TxSubCarrier = 0;
2084 #ifdef USB_TX_DRIVER_AGGREGATION_ENABLE
2085 if (tcb_desc->drv_agg_enable)
2087 tx_fwinfo->Tx_INFO_RSVD = (tcb_desc->DrvAggrNum & 0x1f) << 1;
2090 /* Fill Tx descriptor */
2091 memset(tx_desc, 0, sizeof(tx_desc_819x_usb));
2094 tx_desc->CmdInit = 1;
2095 tx_desc->Offset = sizeof(tx_fwinfo_819x_usb) + 8;
2097 #ifdef USB_TX_DRIVER_AGGREGATION_ENABLE
2098 if (tcb_desc->drv_agg_enable) {
2099 tx_desc->PktSize = tcb_desc->pkt_size;
2103 tx_desc->PktSize = (skb->len - TX_PACKET_SHIFT_BYTES) & 0xffff;
2107 tx_desc->SecCAMID= 0;
2108 tx_desc->RATid = tcb_desc->RATRIndex;
2113 tx_desc->SecType = 0x0;
2114 if (tcb_desc->bHwSec)
2116 switch (priv->ieee80211->pairwise_key_type)
2118 case KEY_TYPE_WEP40:
2119 case KEY_TYPE_WEP104:
2120 tx_desc->SecType = 0x1;
2124 tx_desc->SecType = 0x2;
2128 tx_desc->SecType = 0x3;
2132 tx_desc->SecType = 0x0;
2138 tx_desc->QueueSelect = MapHwQueueToFirmwareQueue(tcb_desc->queue_index);
2139 tx_desc->TxFWInfoSize = sizeof(tx_fwinfo_819x_usb);
2141 tx_desc->DISFB = tcb_desc->bTxDisableRateFallBack;
2142 tx_desc->USERATE = tcb_desc->bTxUseDriverAssingedRate;
2144 /* Fill fields that are required to be initialized in all of the descriptors */
2146 tx_desc->FirstSeg = 1;
2147 tx_desc->LastSeg = 1;
2150 #ifdef USB_TX_DRIVER_AGGREGATION_ENABLE
2151 if (tcb_desc->drv_agg_enable) {
2152 tx_desc->TxBufferSize = tcb_desc->pkt_size + sizeof(tx_fwinfo_819x_usb);
2157 tx_desc->TxBufferSize = (u32)(skb->len - USB_HWDESC_HEADER_LEN);
2159 /* Get index to out pipe from specified QueueID */
2160 #ifndef USE_ONE_PIPE
2161 idx_pipe = txqueue2outpipe(priv,tcb_desc->queue_index);
2166 //RT_DEBUG_DATA(COMP_SEND,tx_fwinfo,sizeof(tx_fwinfo_819x_usb));
2167 //RT_DEBUG_DATA(COMP_SEND,tx_desc,sizeof(tx_desc_819x_usb));
2169 /* To submit bulk urb */
2170 usb_fill_bulk_urb(tx_urb,udev,
2171 usb_sndbulkpipe(udev,idx_pipe), skb->data,
2172 skb->len, rtl8192_tx_isr, skb);
2174 status = usb_submit_urb(tx_urb, GFP_ATOMIC);
2176 //we need to send 0 byte packet whenever 512N bytes/64N(HIGN SPEED/NORMAL SPEED) bytes packet has been transmitted. Otherwise, it will be halt to wait for another packet. WB. 2008.08.27
2177 bool bSend0Byte = false;
2179 if(udev->speed == USB_SPEED_HIGH)
2181 if (skb->len > 0 && skb->len % 512 == 0)
2186 if (skb->len > 0 && skb->len % 64 == 0)
2191 tx_urb_zero = usb_alloc_urb(0,GFP_ATOMIC);
2193 RT_TRACE(COMP_ERR, "can't alloc urb for zero byte\n");
2196 usb_fill_bulk_urb(tx_urb_zero,udev,
2197 usb_sndbulkpipe(udev,idx_pipe), &zero,
2198 0, tx_zero_isr, dev);
2199 status = usb_submit_urb(tx_urb_zero, GFP_ATOMIC);
2201 RT_TRACE(COMP_ERR, "Error TX URB for zero byte %d, error %d", atomic_read(&priv->tx_pending[tcb_desc->queue_index]), status);
2205 dev->trans_start = jiffies;
2206 atomic_inc(&priv->tx_pending[tcb_desc->queue_index]);
2209 RT_TRACE(COMP_ERR, "Error TX URB %d, error %d", atomic_read(&priv->tx_pending[tcb_desc->queue_index]),
2215 short rtl8192_usb_initendpoints(struct net_device *dev)
2217 struct r8192_priv *priv = ieee80211_priv(dev);
2219 priv->rx_urb = kmalloc(sizeof(struct urb *) * (MAX_RX_URB+1),
2222 #ifndef JACKSON_NEW_RX
2223 for(i=0;i<(MAX_RX_URB+1);i++){
2225 priv->rx_urb[i] = usb_alloc_urb(0,GFP_KERNEL);
2227 priv->rx_urb[i]->transfer_buffer = kmalloc(RX_URB_SIZE, GFP_KERNEL);
2229 priv->rx_urb[i]->transfer_buffer_length = RX_URB_SIZE;
2233 #ifdef THOMAS_BEACON
2236 void *oldaddr, *newaddr;
2238 priv->rx_urb[16] = usb_alloc_urb(0, GFP_KERNEL);
2239 priv->oldaddr = kmalloc(16, GFP_KERNEL);
2240 oldaddr = priv->oldaddr;
2241 align = ((long)oldaddr) & 3;
2243 newaddr = oldaddr + 4 - align;
2244 priv->rx_urb[16]->transfer_buffer_length = 16 - 4 + align;
2247 priv->rx_urb[16]->transfer_buffer_length = 16;
2249 priv->rx_urb[16]->transfer_buffer = newaddr;
2253 memset(priv->rx_urb, 0, sizeof(struct urb*) * MAX_RX_URB);
2254 priv->pp_rxskb = kcalloc(MAX_RX_URB, sizeof(struct sk_buff *),
2256 if (priv->pp_rxskb == NULL)
2263 if (priv->pp_rxskb) {
2264 kfree(priv->pp_rxskb);
2267 kfree(priv->rx_urb);
2270 priv->pp_rxskb = NULL;
2271 priv->rx_urb = NULL;
2273 DMESGE("Endpoint Alloc Failure");
2279 printk("End of initendpoints\n");
2283 #ifdef THOMAS_BEACON
2284 void rtl8192_usb_deleteendpoints(struct net_device *dev)
2287 struct r8192_priv *priv = ieee80211_priv(dev);
2290 for(i=0;i<(MAX_RX_URB+1);i++){
2291 usb_kill_urb(priv->rx_urb[i]);
2292 usb_free_urb(priv->rx_urb[i]);
2294 kfree(priv->rx_urb);
2295 priv->rx_urb = NULL;
2298 kfree(priv->oldaddr);
2299 priv->oldaddr = NULL;
2301 if (priv->pp_rxskb) {
2302 kfree(priv->pp_rxskb);
2307 void rtl8192_usb_deleteendpoints(struct net_device *dev)
2310 struct r8192_priv *priv = ieee80211_priv(dev);
2312 #ifndef JACKSON_NEW_RX
2315 for(i=0;i<(MAX_RX_URB+1);i++){
2316 usb_kill_urb(priv->rx_urb[i]);
2317 kfree(priv->rx_urb[i]->transfer_buffer);
2318 usb_free_urb(priv->rx_urb[i]);
2320 kfree(priv->rx_urb);
2321 priv->rx_urb = NULL;
2326 kfree(priv->rx_urb);
2327 priv->rx_urb = NULL;
2330 kfree(priv->oldaddr);
2331 priv->oldaddr = NULL;
2333 if (priv->pp_rxskb) {
2334 kfree(priv->pp_rxskb);
2343 extern void rtl8192_update_ratr_table(struct net_device* dev);
2344 void rtl8192_link_change(struct net_device *dev)
2348 struct r8192_priv *priv = ieee80211_priv(dev);
2349 struct ieee80211_device* ieee = priv->ieee80211;
2350 //write_nic_word(dev, BCN_INTR_ITV, net->beacon_interval);
2351 if (ieee->state == IEEE80211_LINKED)
2353 rtl8192_net_update(dev);
2354 rtl8192_update_ratr_table(dev);
2355 //add this as in pure N mode, wep encryption will use software way, but there is no chance to set this as wep will not set group key in wext. WB.2008.07.08
2356 if ((KEY_TYPE_WEP40 == ieee->pairwise_key_type) || (KEY_TYPE_WEP104 == ieee->pairwise_key_type))
2357 EnableHWSecurityConfig8192(dev);
2359 /*update timing params*/
2360 // RT_TRACE(COMP_CH, "========>%s(), chan:%d\n", __FUNCTION__, priv->chan);
2361 // rtl8192_set_chan(dev, priv->chan);
2362 if (ieee->iw_mode == IW_MODE_INFRA || ieee->iw_mode == IW_MODE_ADHOC)
2365 reg = read_nic_dword(dev, RCR);
2366 if (priv->ieee80211->state == IEEE80211_LINKED)
2367 priv->ReceiveConfig = reg |= RCR_CBSSID;
2369 priv->ReceiveConfig = reg &= ~RCR_CBSSID;
2370 write_nic_dword(dev, RCR, reg);
2373 // rtl8192_set_rxconf(dev);
2376 static struct ieee80211_qos_parameters def_qos_parameters = {
2377 {3,3,3,3},/* cw_min */
2378 {7,7,7,7},/* cw_max */
2379 {2,2,2,2},/* aifs */
2380 {0,0,0,0},/* flags */
2381 {0,0,0,0} /* tx_op_limit */
2385 void rtl8192_update_beacon(struct work_struct * work)
2387 struct r8192_priv *priv = container_of(work, struct r8192_priv, update_beacon_wq.work);
2388 struct net_device *dev = priv->ieee80211->dev;
2389 struct ieee80211_device* ieee = priv->ieee80211;
2390 struct ieee80211_network* net = &ieee->current_network;
2392 if (ieee->pHTInfo->bCurrentHTSupport)
2393 HTUpdateSelfAndPeerSetting(ieee, net);
2394 ieee->pHTInfo->bCurrentRT2RTLongSlotTime = net->bssht.bdRT2RTLongSlotTime;
2395 rtl8192_update_cap(dev, net->capability);
2398 * background support to run QoS activate functionality
2400 int WDCAPARA_ADD[] = {EDCAPARA_BE,EDCAPARA_BK,EDCAPARA_VI,EDCAPARA_VO};
2401 void rtl8192_qos_activate(struct work_struct * work)
2403 struct r8192_priv *priv = container_of(work, struct r8192_priv, qos_activate);
2404 struct net_device *dev = priv->ieee80211->dev;
2405 struct ieee80211_qos_parameters *qos_parameters = &priv->ieee80211->current_network.qos_data.parameters;
2406 u8 mode = priv->ieee80211->current_network.mode;
2407 //u32 size = sizeof(struct ieee80211_qos_parameters);
2415 mutex_lock(&priv->mutex);
2416 if(priv->ieee80211->state != IEEE80211_LINKED)
2418 RT_TRACE(COMP_QOS,"qos active process with associate response received\n");
2419 /* It better set slot time at first */
2420 /* For we just support b/g mode at present, let the slot time at 9/20 selection */
2421 /* update the ac parameter to related registers */
2422 for(i = 0; i < QOS_QUEUE_NUM; i++) {
2423 //Mode G/A: slotTimeTimer = 9; Mode B: 20
2424 u1bAIFS = qos_parameters->aifs[i] * ((mode&(IEEE_G|IEEE_N_24G)) ?9:20) + aSifsTime;
2425 u4bAcParam = ((((u32)(qos_parameters->tx_op_limit[i]))<< AC_PARAM_TXOP_LIMIT_OFFSET)|
2426 (((u32)(qos_parameters->cw_max[i]))<< AC_PARAM_ECW_MAX_OFFSET)|
2427 (((u32)(qos_parameters->cw_min[i]))<< AC_PARAM_ECW_MIN_OFFSET)|
2428 ((u32)u1bAIFS << AC_PARAM_AIFS_OFFSET));
2430 write_nic_dword(dev, WDCAPARA_ADD[i], u4bAcParam);
2431 //write_nic_dword(dev, WDCAPARA_ADD[i], 0x005e4332);
2435 mutex_unlock(&priv->mutex);
2438 static int rtl8192_qos_handle_probe_response(struct r8192_priv *priv,
2440 struct ieee80211_network *network)
2443 u32 size = sizeof(struct ieee80211_qos_parameters);
2445 if(priv->ieee80211->state !=IEEE80211_LINKED)
2448 if ((priv->ieee80211->iw_mode != IW_MODE_INFRA))
2451 if (network->flags & NETWORK_HAS_QOS_MASK) {
2452 if (active_network &&
2453 (network->flags & NETWORK_HAS_QOS_PARAMETERS))
2454 network->qos_data.active = network->qos_data.supported;
2456 if ((network->qos_data.active == 1) && (active_network == 1) &&
2457 (network->flags & NETWORK_HAS_QOS_PARAMETERS) &&
2458 (network->qos_data.old_param_count !=
2459 network->qos_data.param_count)) {
2460 network->qos_data.old_param_count =
2461 network->qos_data.param_count;
2462 queue_work(priv->priv_wq, &priv->qos_activate);
2463 RT_TRACE (COMP_QOS, "QoS parameters change call "
2467 memcpy(&priv->ieee80211->current_network.qos_data.parameters,\
2468 &def_qos_parameters, size);
2470 if ((network->qos_data.active == 1) && (active_network == 1)) {
2471 queue_work(priv->priv_wq, &priv->qos_activate);
2472 RT_TRACE(COMP_QOS, "QoS was disabled call qos_activate \n");
2474 network->qos_data.active = 0;
2475 network->qos_data.supported = 0;
2481 /* handle manage frame frame beacon and probe response */
2482 static int rtl8192_handle_beacon(struct net_device * dev,
2483 struct ieee80211_beacon * beacon,
2484 struct ieee80211_network * network)
2486 struct r8192_priv *priv = ieee80211_priv(dev);
2488 rtl8192_qos_handle_probe_response(priv,1,network);
2489 queue_delayed_work(priv->priv_wq, &priv->update_beacon_wq, 0);
2495 * handling the beaconing responses. if we get different QoS setting
2496 * off the network from the associated setting, adjust the QoS
2499 static int rtl8192_qos_association_resp(struct r8192_priv *priv,
2500 struct ieee80211_network *network)
2503 unsigned long flags;
2504 u32 size = sizeof(struct ieee80211_qos_parameters);
2505 int set_qos_param = 0;
2507 if ((priv == NULL) || (network == NULL))
2510 if(priv->ieee80211->state !=IEEE80211_LINKED)
2513 if ((priv->ieee80211->iw_mode != IW_MODE_INFRA))
2516 spin_lock_irqsave(&priv->ieee80211->lock, flags);
2517 if(network->flags & NETWORK_HAS_QOS_PARAMETERS) {
2518 memcpy(&priv->ieee80211->current_network.qos_data.parameters,\
2519 &network->qos_data.parameters,\
2520 sizeof(struct ieee80211_qos_parameters));
2521 priv->ieee80211->current_network.qos_data.active = 1;
2524 /* update qos parameter for current network */
2525 priv->ieee80211->current_network.qos_data.old_param_count = \
2526 priv->ieee80211->current_network.qos_data.param_count;
2527 priv->ieee80211->current_network.qos_data.param_count = \
2528 network->qos_data.param_count;
2531 memcpy(&priv->ieee80211->current_network.qos_data.parameters,\
2532 &def_qos_parameters, size);
2533 priv->ieee80211->current_network.qos_data.active = 0;
2534 priv->ieee80211->current_network.qos_data.supported = 0;
2538 spin_unlock_irqrestore(&priv->ieee80211->lock, flags);
2540 RT_TRACE(COMP_QOS, "%s: network->flags = %d,%d\n",__FUNCTION__,network->flags ,priv->ieee80211->current_network.qos_data.active);
2541 if (set_qos_param == 1)
2542 queue_work(priv->priv_wq, &priv->qos_activate);
2549 static int rtl8192_handle_assoc_response(struct net_device *dev,
2550 struct ieee80211_assoc_response_frame *resp,
2551 struct ieee80211_network *network)
2553 struct r8192_priv *priv = ieee80211_priv(dev);
2554 rtl8192_qos_association_resp(priv, network);
2559 void rtl8192_update_ratr_table(struct net_device* dev)
2560 // POCTET_STRING posLegacyRate,
2562 // PRT_WLAN_STA pEntry)
2564 struct r8192_priv* priv = ieee80211_priv(dev);
2565 struct ieee80211_device* ieee = priv->ieee80211;
2566 u8* pMcsRate = ieee->dot11HTOperationalRateSet;
2567 //struct ieee80211_network *net = &ieee->current_network;
2570 rtl8192_config_rate(dev, (u16*)(&ratr_value));
2571 ratr_value |= (*(u16*)(pMcsRate)) << 12;
2572 // switch (net->mode)
2576 ratr_value &= 0x00000FF0;
2579 ratr_value &= 0x0000000F;
2582 ratr_value &= 0x00000FF7;
2586 if (ieee->pHTInfo->PeerMimoPs == 0) //MIMO_PS_STATIC
2587 ratr_value &= 0x0007F007;
2589 if (priv->rf_type == RF_1T2R)
2590 ratr_value &= 0x000FF007;
2592 ratr_value &= 0x0F81F007;
2598 ratr_value &= 0x0FFFFFFF;
2599 if(ieee->pHTInfo->bCurTxBW40MHz && ieee->pHTInfo->bCurShortGI40MHz){
2600 ratr_value |= 0x80000000;
2601 }else if(!ieee->pHTInfo->bCurTxBW40MHz && ieee->pHTInfo->bCurShortGI20MHz){
2602 ratr_value |= 0x80000000;
2604 write_nic_dword(dev, RATR0+rate_index*4, ratr_value);
2605 write_nic_byte(dev, UFWP, 1);
2608 static u8 ccmp_ie[4] = {0x00,0x50,0xf2,0x04};
2609 static u8 ccmp_rsn_ie[4] = {0x00, 0x0f, 0xac, 0x04};
2610 bool GetNmodeSupportBySecCfg8192(struct net_device*dev)
2612 struct r8192_priv* priv = ieee80211_priv(dev);
2613 struct ieee80211_device* ieee = priv->ieee80211;
2614 struct ieee80211_network * network = &ieee->current_network;
2615 int wpa_ie_len= ieee->wpa_ie_len;
2616 struct ieee80211_crypt_data* crypt;
2619 crypt = ieee->crypt[ieee->tx_keyidx];
2620 //we use connecting AP's capability instead of only security config on our driver to distinguish whether it should use N mode or G mode
2621 encrypt = (network->capability & WLAN_CAPABILITY_PRIVACY) || (ieee->host_encrypt && crypt && crypt->ops && (0 == strcmp(crypt->ops->name,"WEP")));
2624 if(encrypt && (wpa_ie_len == 0)) {
2625 /* wep encryption, no N mode setting */
2627 // } else if((wpa_ie_len != 0)&&(memcmp(&(ieee->wpa_ie[14]),ccmp_ie,4))) {
2628 } else if((wpa_ie_len != 0)) {
2629 /* parse pairwise key type */
2630 //if((pairwisekey = WEP40)||(pairwisekey = WEP104)||(pairwisekey = TKIP))
2631 if (((ieee->wpa_ie[0] == 0xdd) && (!memcmp(&(ieee->wpa_ie[14]),ccmp_ie,4))) || ((ieee->wpa_ie[0] == 0x30) && (!memcmp(&ieee->wpa_ie[10],ccmp_rsn_ie, 4))))
2642 bool GetHalfNmodeSupportByAPs819xUsb(struct net_device* dev)
2645 struct r8192_priv* priv = ieee80211_priv(dev);
2646 struct ieee80211_device* ieee = priv->ieee80211;
2648 if(ieee->bHalfWirelessN24GMode == true)
2656 void rtl8192_refresh_supportrate(struct r8192_priv* priv)
2658 struct ieee80211_device* ieee = priv->ieee80211;
2659 //we donot consider set support rate for ABG mode, only HT MCS rate is set here.
2660 if (ieee->mode == WIRELESS_MODE_N_24G || ieee->mode == WIRELESS_MODE_N_5G)
2662 memcpy(ieee->Regdot11HTOperationalRateSet, ieee->RegHTSuppRateSet, 16);
2663 //RT_DEBUG_DATA(COMP_INIT, ieee->RegHTSuppRateSet, 16);
2664 //RT_DEBUG_DATA(COMP_INIT, ieee->Regdot11HTOperationalRateSet, 16);
2667 memset(ieee->Regdot11HTOperationalRateSet, 0, 16);
2671 u8 rtl8192_getSupportedWireleeMode(struct net_device*dev)
2673 struct r8192_priv *priv = ieee80211_priv(dev);
2675 switch(priv->rf_chip)
2680 ret = (WIRELESS_MODE_N_24G|WIRELESS_MODE_G|WIRELESS_MODE_B);
2683 ret = (WIRELESS_MODE_A|WIRELESS_MODE_N_5G);
2686 ret = WIRELESS_MODE_B;
2691 void rtl8192_SetWirelessMode(struct net_device* dev, u8 wireless_mode)
2693 struct r8192_priv *priv = ieee80211_priv(dev);
2694 u8 bSupportMode = rtl8192_getSupportedWireleeMode(dev);
2696 if ((wireless_mode == WIRELESS_MODE_AUTO) || ((wireless_mode&bSupportMode)==0))
2698 if(bSupportMode & WIRELESS_MODE_N_24G)
2700 wireless_mode = WIRELESS_MODE_N_24G;
2702 else if(bSupportMode & WIRELESS_MODE_N_5G)
2704 wireless_mode = WIRELESS_MODE_N_5G;
2706 else if((bSupportMode & WIRELESS_MODE_A))
2708 wireless_mode = WIRELESS_MODE_A;
2710 else if((bSupportMode & WIRELESS_MODE_G))
2712 wireless_mode = WIRELESS_MODE_G;
2714 else if((bSupportMode & WIRELESS_MODE_B))
2716 wireless_mode = WIRELESS_MODE_B;
2719 RT_TRACE(COMP_ERR, "%s(), No valid wireless mode supported, SupportedWirelessMode(%x)!!!\n", __FUNCTION__,bSupportMode);
2720 wireless_mode = WIRELESS_MODE_B;
2723 #ifdef TO_DO_LIST //// TODO: this function doesn't work well at this time, we should wait for FPGA
2724 ActUpdateChannelAccessSetting( pAdapter, pHalData->CurrentWirelessMode, &pAdapter->MgntInfo.Info8185.ChannelAccessSetting );
2726 priv->ieee80211->mode = wireless_mode;
2728 if ((wireless_mode == WIRELESS_MODE_N_24G) || (wireless_mode == WIRELESS_MODE_N_5G))
2729 priv->ieee80211->pHTInfo->bEnableHT = 1;
2731 priv->ieee80211->pHTInfo->bEnableHT = 0;
2732 RT_TRACE(COMP_INIT, "Current Wireless Mode is %x\n", wireless_mode);
2733 rtl8192_refresh_supportrate(priv);
2736 //init priv variables here. only non_zero value should be initialized here.
2737 static void rtl8192_init_priv_variable(struct net_device* dev)
2739 struct r8192_priv *priv = ieee80211_priv(dev);
2741 priv->card_8192 = NIC_8192U;
2742 priv->chan = 1; //set to channel 1
2743 priv->ieee80211->mode = WIRELESS_MODE_AUTO; //SET AUTO
2744 priv->ieee80211->iw_mode = IW_MODE_INFRA;
2745 priv->ieee80211->ieee_up=0;
2746 priv->retry_rts = DEFAULT_RETRY_RTS;
2747 priv->retry_data = DEFAULT_RETRY_DATA;
2748 priv->ieee80211->rts = DEFAULT_RTS_THRESHOLD;
2749 priv->ieee80211->rate = 110; //11 mbps
2750 priv->ieee80211->short_slot = 1;
2751 priv->promisc = (dev->flags & IFF_PROMISC) ? 1:0;
2754 priv->IrpPendingCount = 1;
2755 priv->ResetProgress = RESET_TYPE_NORESET;
2756 priv->bForcedSilentReset = 0;
2757 priv->bDisableNormalResetCheck = false;
2758 priv->force_reset = false;
2760 priv->ieee80211->FwRWRF = 0; //we don't use FW read/write RF until stable firmware is available.
2761 priv->ieee80211->current_network.beacon_interval = DEFAULT_BEACONINTERVAL;
2762 priv->ieee80211->iw_mode = IW_MODE_INFRA;
2763 priv->ieee80211->softmac_features = IEEE_SOFTMAC_SCAN |
2764 IEEE_SOFTMAC_ASSOCIATE | IEEE_SOFTMAC_PROBERQ |
2765 IEEE_SOFTMAC_PROBERS | IEEE_SOFTMAC_TX_QUEUE |
2766 IEEE_SOFTMAC_BEACONS;//added by amy 080604 //| //IEEE_SOFTMAC_SINGLE_QUEUE;
2768 priv->ieee80211->active_scan = 1;
2769 priv->ieee80211->modulation = IEEE80211_CCK_MODULATION | IEEE80211_OFDM_MODULATION;
2770 priv->ieee80211->host_encrypt = 1;
2771 priv->ieee80211->host_decrypt = 1;
2772 priv->ieee80211->start_send_beacons = NULL;//rtl819xusb_beacon_tx;//-by amy 080604
2773 priv->ieee80211->stop_send_beacons = NULL;//rtl8192_beacon_stop;//-by amy 080604
2774 priv->ieee80211->softmac_hard_start_xmit = rtl8192_hard_start_xmit;
2775 priv->ieee80211->set_chan = rtl8192_set_chan;
2776 priv->ieee80211->link_change = rtl8192_link_change;
2777 priv->ieee80211->softmac_data_hard_start_xmit = rtl8192_hard_data_xmit;
2778 priv->ieee80211->data_hard_stop = rtl8192_data_hard_stop;
2779 priv->ieee80211->data_hard_resume = rtl8192_data_hard_resume;
2780 priv->ieee80211->init_wmmparam_flag = 0;
2781 priv->ieee80211->fts = DEFAULT_FRAG_THRESHOLD;
2782 priv->ieee80211->check_nic_enough_desc = check_nic_enough_desc;
2783 priv->ieee80211->tx_headroom = TX_PACKET_SHIFT_BYTES;
2784 priv->ieee80211->qos_support = 1;
2787 // priv->ieee80211->SwChnlByTimerHandler = rtl8192_phy_SwChnl;
2788 priv->ieee80211->SetBWModeHandler = rtl8192_SetBWMode;
2789 priv->ieee80211->handle_assoc_response = rtl8192_handle_assoc_response;
2790 priv->ieee80211->handle_beacon = rtl8192_handle_beacon;
2792 priv->ieee80211->GetNmodeSupportBySecCfg = GetNmodeSupportBySecCfg8192;
2793 priv->ieee80211->GetHalfNmodeSupportByAPsHandler = GetHalfNmodeSupportByAPs819xUsb;
2794 priv->ieee80211->SetWirelessMode = rtl8192_SetWirelessMode;
2796 priv->ieee80211->InitialGainHandler = InitialGain819xUsb;
2797 priv->card_type = USB;
2799 if(Adapter->bInHctTest)
2801 pHalData->ShortRetryLimit = 7;
2802 pHalData->LongRetryLimit = 7;
2806 priv->ShortRetryLimit = 0x30;
2807 priv->LongRetryLimit = 0x30;
2809 priv->EarlyRxThreshold = 7;
2810 priv->enable_gpio0 = 0;
2811 priv->TransmitConfig =
2812 // TCR_DurProcMode | //for RTL8185B, duration setting by HW
2813 //? TCR_DISReqQsize |
2814 (TCR_MXDMA_2048<<TCR_MXDMA_OFFSET)| // Max DMA Burst Size per Tx DMA Burst, 7: reservied.
2815 (priv->ShortRetryLimit<<TCR_SRL_OFFSET)| // Short retry limit
2816 (priv->LongRetryLimit<<TCR_LRL_OFFSET) | // Long retry limit
2817 (false ? TCR_SAT: 0); // FALSE: HW provies PLCP length and LENGEXT, TURE: SW proiveds them
2819 if(Adapter->bInHctTest)
2820 pHalData->ReceiveConfig = pHalData->CSMethod |
2821 RCR_AMF | RCR_ADF | //RCR_AAP | //accept management/data
2823 RCR_ACF | //accept control frame for SW AP needs PS-poll, 2005.07.07, by rcnjko.
2824 RCR_AB | RCR_AM | RCR_APM | //accept BC/MC/UC
2825 RCR_AICV | RCR_ACRC32 | //accept ICV/CRC error packet
2826 ((u32)7<<RCR_MXDMA_OFFSET) | // Max DMA Burst Size per Rx DMA Burst, 7: unlimited.
2827 (pHalData->EarlyRxThreshold<<RCR_FIFO_OFFSET) | // Rx FIFO Threshold, 7: No Rx threshold.
2828 (pHalData->EarlyRxThreshold == 7 ? RCR_OnlyErlPkt:0);
2832 priv->ReceiveConfig =
2833 RCR_AMF | RCR_ADF | //accept management/data
2834 RCR_ACF | //accept control frame for SW AP needs PS-poll, 2005.07.07, by rcnjko.
2835 RCR_AB | RCR_AM | RCR_APM | //accept BC/MC/UC
2836 //RCR_AICV | RCR_ACRC32 | //accept ICV/CRC error packet
2837 ((u32)7<<RCR_MXDMA_OFFSET)| // Max DMA Burst Size per Rx DMA Burst, 7: unlimited.
2838 (priv->EarlyRxThreshold<<RX_FIFO_THRESHOLD_SHIFT) | // Rx FIFO Threshold, 7: No Rx threshold.
2839 (priv->EarlyRxThreshold == 7 ? RCR_ONLYERLPKT:0);
2841 priv->AcmControl = 0;
2842 priv->pFirmware = kmalloc(sizeof(rt_firmware), GFP_KERNEL);
2843 if (priv->pFirmware)
2844 memset(priv->pFirmware, 0, sizeof(rt_firmware));
2846 /* rx related queue */
2847 skb_queue_head_init(&priv->rx_queue);
2848 skb_queue_head_init(&priv->skb_queue);
2850 /* Tx related queue */
2851 for(i = 0; i < MAX_QUEUE_SIZE; i++) {
2852 skb_queue_head_init(&priv->ieee80211->skb_waitQ [i]);
2854 for(i = 0; i < MAX_QUEUE_SIZE; i++) {
2855 skb_queue_head_init(&priv->ieee80211->skb_aggQ [i]);
2857 for(i = 0; i < MAX_QUEUE_SIZE; i++) {
2858 skb_queue_head_init(&priv->ieee80211->skb_drv_aggQ [i]);
2860 priv->rf_set_chan = rtl8192_phy_SwChnl;
2864 static void rtl8192_init_priv_lock(struct r8192_priv* priv)
2866 spin_lock_init(&priv->tx_lock);
2867 spin_lock_init(&priv->irq_lock);//added by thomas
2868 //spin_lock_init(&priv->rf_lock);
2869 sema_init(&priv->wx_sem,1);
2870 sema_init(&priv->rf_sem,1);
2871 mutex_init(&priv->mutex);
2874 extern void rtl819x_watchdog_wqcallback(struct work_struct *work);
2876 void rtl8192_irq_rx_tasklet(struct r8192_priv *priv);
2877 //init tasklet and wait_queue here. only 2.6 above kernel is considered
2878 #define DRV_NAME "wlan0"
2879 static void rtl8192_init_priv_task(struct net_device* dev)
2881 struct r8192_priv *priv = ieee80211_priv(dev);
2883 #ifdef PF_SYNCTHREAD
2884 priv->priv_wq = create_workqueue(DRV_NAME,0);
2886 priv->priv_wq = create_workqueue(DRV_NAME);
2889 INIT_WORK(&priv->reset_wq, rtl8192_restart);
2891 //INIT_DELAYED_WORK(&priv->watch_dog_wq, hal_dm_watchdog);
2892 INIT_DELAYED_WORK(&priv->watch_dog_wq, rtl819x_watchdog_wqcallback);
2893 INIT_DELAYED_WORK(&priv->txpower_tracking_wq, dm_txpower_trackingcallback);
2894 // INIT_DELAYED_WORK(&priv->gpio_change_rf_wq, dm_gpio_change_rf_callback);
2895 INIT_DELAYED_WORK(&priv->rfpath_check_wq, dm_rf_pathcheck_workitemcallback);
2896 INIT_DELAYED_WORK(&priv->update_beacon_wq, rtl8192_update_beacon);
2897 INIT_DELAYED_WORK(&priv->initialgain_operate_wq, InitialGainOperateWorkItemCallBack);
2898 //INIT_WORK(&priv->SwChnlWorkItem, rtl8192_SwChnl_WorkItem);
2899 //INIT_WORK(&priv->SetBWModeWorkItem, rtl8192_SetBWModeWorkItem);
2900 INIT_WORK(&priv->qos_activate, rtl8192_qos_activate);
2902 tasklet_init(&priv->irq_rx_tasklet,
2903 (void(*)(unsigned long))rtl8192_irq_rx_tasklet,
2904 (unsigned long)priv);
2907 static void rtl8192_get_eeprom_size(struct net_device* dev)
2910 struct r8192_priv *priv = ieee80211_priv(dev);
2911 RT_TRACE(COMP_EPROM, "===========>%s()\n", __FUNCTION__);
2912 curCR = read_nic_word_E(dev,EPROM_CMD);
2913 RT_TRACE(COMP_EPROM, "read from Reg EPROM_CMD(%x):%x\n", EPROM_CMD, curCR);
2914 //whether need I consider BIT5?
2915 priv->epromtype = (curCR & Cmd9346CR_9356SEL) ? EPROM_93c56 : EPROM_93c46;
2916 RT_TRACE(COMP_EPROM, "<===========%s(), epromtype:%d\n", __FUNCTION__, priv->epromtype);
2919 //used to swap endian. as ntohl & htonl are not neccessary to swap endian, so use this instead.
2920 static inline u16 endian_swap(u16* data)
2923 *data = (tmp >> 8) | (tmp << 8);
2926 static void rtl8192_read_eeprom_info(struct net_device* dev)
2929 u8 bMac_Tmp_Addr[6] = {0x00, 0xe0, 0x4c, 0x00, 0x00, 0x02};
2930 u8 bLoad_From_EEPOM = false;
2931 struct r8192_priv *priv = ieee80211_priv(dev);
2933 RT_TRACE(COMP_EPROM, "===========>%s()\n", __FUNCTION__);
2934 wEPROM_ID = eprom_read(dev, 0); //first read EEPROM ID out;
2935 RT_TRACE(COMP_EPROM, "EEPROM ID is 0x%x\n", wEPROM_ID);
2937 if (wEPROM_ID != RTL8190_EEPROM_ID)
2939 RT_TRACE(COMP_ERR, "EEPROM ID is invalid(is 0x%x(should be 0x%x)\n", wEPROM_ID, RTL8190_EEPROM_ID);
2942 bLoad_From_EEPOM = true;
2944 if (bLoad_From_EEPOM)
2946 tmpValue = eprom_read(dev, (EEPROM_VID>>1));
2947 priv->eeprom_vid = endian_swap(&tmpValue);
2948 priv->eeprom_pid = eprom_read(dev, (EEPROM_PID>>1));
2949 tmpValue = eprom_read(dev, (EEPROM_ChannelPlan>>1));
2950 priv->eeprom_ChannelPlan =((tmpValue&0xff00)>>8);
2951 priv->btxpowerdata_readfromEEPORM = true;
2952 priv->eeprom_CustomerID = eprom_read(dev, (EEPROM_Customer_ID>>1)) >>8;
2956 priv->eeprom_vid = 0;
2957 priv->eeprom_pid = 0;
2958 priv->card_8192_version = VERSION_819xU_B;
2959 priv->eeprom_ChannelPlan = 0;
2960 priv->eeprom_CustomerID = 0;
2962 RT_TRACE(COMP_EPROM, "vid:0x%4x, pid:0x%4x, CustomID:0x%2x, ChanPlan:0x%x\n", priv->eeprom_vid, priv->eeprom_pid, priv->eeprom_CustomerID, priv->eeprom_ChannelPlan);
2963 //set channelplan from eeprom
2964 priv->ChannelPlan = priv->eeprom_ChannelPlan;
2965 if (bLoad_From_EEPOM)
2968 for (i=0; i<6; i+=2)
2971 tmp = eprom_read(dev, (u16)((EEPROM_NODE_ADDRESS_BYTE_0 + i)>>1));
2972 *(u16*)(&dev->dev_addr[i]) = tmp;
2977 memcpy(dev->dev_addr, bMac_Tmp_Addr, 6);
2978 //should I set IDR0 here?
2980 RT_TRACE(COMP_EPROM, "MAC addr:%pM\n", dev->dev_addr);
2981 priv->rf_type = RTL819X_DEFAULT_RF_TYPE; //default 1T2R
2982 priv->rf_chip = RF_8256;
2984 if (priv->card_8192_version == (u8)VERSION_819xU_A)
2986 //read Tx power gain offset of legacy OFDM to HT rate
2987 if (bLoad_From_EEPOM)
2988 priv->EEPROMTxPowerDiff = (eprom_read(dev, (EEPROM_TxPowerDiff>>1))&0xff00) >> 8;
2990 priv->EEPROMTxPowerDiff = EEPROM_Default_TxPower;
2991 RT_TRACE(COMP_EPROM, "TxPowerDiff:%d\n", priv->EEPROMTxPowerDiff);
2992 //read ThermalMeter from EEPROM
2993 if (bLoad_From_EEPOM)
2994 priv->EEPROMThermalMeter = (u8)(eprom_read(dev, (EEPROM_ThermalMeter>>1))&0x00ff);
2996 priv->EEPROMThermalMeter = EEPROM_Default_ThermalMeter;
2997 RT_TRACE(COMP_EPROM, "ThermalMeter:%d\n", priv->EEPROMThermalMeter);
2998 //vivi, for tx power track
2999 priv->TSSI_13dBm = priv->EEPROMThermalMeter *100;
3000 //read antenna tx power offset of B/C/D to A from EEPROM
3001 if (bLoad_From_EEPOM)
3002 priv->EEPROMPwDiff = (eprom_read(dev, (EEPROM_PwDiff>>1))&0x0f00)>>8;
3004 priv->EEPROMPwDiff = EEPROM_Default_PwDiff;
3005 RT_TRACE(COMP_EPROM, "TxPwDiff:%d\n", priv->EEPROMPwDiff);
3006 // Read CrystalCap from EEPROM
3007 if (bLoad_From_EEPOM)
3008 priv->EEPROMCrystalCap = (eprom_read(dev, (EEPROM_CrystalCap>>1))&0x0f);
3010 priv->EEPROMCrystalCap = EEPROM_Default_CrystalCap;
3011 RT_TRACE(COMP_EPROM, "CrystalCap = %d\n", priv->EEPROMCrystalCap);
3012 //get per-channel Tx power level
3013 if (bLoad_From_EEPOM)
3014 priv->EEPROM_Def_Ver = (eprom_read(dev, (EEPROM_TxPwIndex_Ver>>1))&0xff00)>>8;
3016 priv->EEPROM_Def_Ver = 1;
3017 RT_TRACE(COMP_EPROM, "EEPROM_DEF_VER:%d\n", priv->EEPROM_Def_Ver);
3018 if (priv->EEPROM_Def_Ver == 0) //old eeprom definition
3021 if (bLoad_From_EEPOM)
3022 priv->EEPROMTxPowerLevelCCK = (eprom_read(dev, (EEPROM_TxPwIndex_CCK>>1))&0xff) >> 8;
3024 priv->EEPROMTxPowerLevelCCK = 0x10;
3025 RT_TRACE(COMP_EPROM, "CCK Tx Power Levl: 0x%02x\n", priv->EEPROMTxPowerLevelCCK);
3028 if (bLoad_From_EEPOM)
3030 tmpValue = eprom_read(dev, (EEPROM_TxPwIndex_OFDM_24G+i)>>1);
3031 if (((EEPROM_TxPwIndex_OFDM_24G+i) % 2) == 0)
3032 tmpValue = tmpValue & 0x00ff;
3034 tmpValue = (tmpValue & 0xff00) >> 8;
3038 priv->EEPROMTxPowerLevelOFDM24G[i] = (u8) tmpValue;
3039 RT_TRACE(COMP_EPROM, "OFDM 2.4G Tx Power Level, Index %d = 0x%02x\n", i, priv->EEPROMTxPowerLevelCCK);
3041 }//end if EEPROM_DEF_VER == 0
3042 else if (priv->EEPROM_Def_Ver == 1)
3044 if (bLoad_From_EEPOM)
3046 tmpValue = eprom_read(dev, (EEPROM_TxPwIndex_CCK_V1>>1));
3047 tmpValue = (tmpValue & 0xff00) >> 8;
3051 priv->EEPROMTxPowerLevelCCK_V1[0] = (u8)tmpValue;
3053 if (bLoad_From_EEPOM)
3054 tmpValue = eprom_read(dev, (EEPROM_TxPwIndex_CCK_V1 + 2)>>1);
3057 *((u16*)(&priv->EEPROMTxPowerLevelCCK_V1[1])) = tmpValue;
3058 if (bLoad_From_EEPOM)
3059 tmpValue = eprom_read(dev, (EEPROM_TxPwIndex_OFDM_24G_V1>>1));
3062 *((u16*)(&priv->EEPROMTxPowerLevelOFDM24G[0])) = tmpValue;
3063 if (bLoad_From_EEPOM)
3064 tmpValue = eprom_read(dev, (EEPROM_TxPwIndex_OFDM_24G_V1+2)>>1);
3067 priv->EEPROMTxPowerLevelOFDM24G[2] = (u8)tmpValue;
3068 }//endif EEPROM_Def_Ver == 1
3070 //update HAL variables
3074 for (i=0; i<14; i++)
3077 priv->TxPowerLevelOFDM24G[i] = priv->EEPROMTxPowerLevelOFDM24G[0];
3078 else if (i>=4 && i<=9)
3079 priv->TxPowerLevelOFDM24G[i] = priv->EEPROMTxPowerLevelOFDM24G[1];
3081 priv->TxPowerLevelOFDM24G[i] = priv->EEPROMTxPowerLevelOFDM24G[2];
3084 for (i=0; i<14; i++)
3086 if (priv->EEPROM_Def_Ver == 0)
3089 priv->TxPowerLevelCCK[i] = priv->EEPROMTxPowerLevelOFDM24G[0] + (priv->EEPROMTxPowerLevelCCK - priv->EEPROMTxPowerLevelOFDM24G[1]);
3090 else if (i>=4 && i<=9)
3091 priv->TxPowerLevelCCK[i] = priv->EEPROMTxPowerLevelCCK;
3093 priv->TxPowerLevelCCK[i] = priv->EEPROMTxPowerLevelOFDM24G[2] + (priv->EEPROMTxPowerLevelCCK - priv->EEPROMTxPowerLevelOFDM24G[1]);
3095 else if (priv->EEPROM_Def_Ver == 1)
3098 priv->TxPowerLevelCCK[i] = priv->EEPROMTxPowerLevelCCK_V1[0];
3099 else if (i>=4 && i<=9)
3100 priv->TxPowerLevelCCK[i] = priv->EEPROMTxPowerLevelCCK_V1[1];
3102 priv->TxPowerLevelCCK[i] = priv->EEPROMTxPowerLevelCCK_V1[2];
3105 }//end update HAL variables
3106 priv->TxPowerDiff = priv->EEPROMPwDiff;
3107 // Antenna B gain offset to antenna A, bit0~3
3108 priv->AntennaTxPwDiff[0] = (priv->EEPROMTxPowerDiff & 0xf);
3109 // Antenna C gain offset to antenna A, bit4~7
3110 priv->AntennaTxPwDiff[1] = ((priv->EEPROMTxPowerDiff & 0xf0)>>4);
3111 // CrystalCap, bit12~15
3112 priv->CrystalCap = priv->EEPROMCrystalCap;
3113 // ThermalMeter, bit0~3 for RFIC1, bit4~7 for RFIC2
3114 // 92U does not enable TX power tracking.
3115 priv->ThermalMeter[0] = priv->EEPROMThermalMeter;
3116 }//end if VersionID == VERSION_819xU_A
3118 //added by vivi, for dlink led, 20080416
3119 switch(priv->eeprom_CustomerID)
3121 case EEPROM_CID_RUNTOP:
3122 priv->CustomerID = RT_CID_819x_RUNTOP;
3125 case EEPROM_CID_DLINK:
3126 priv->CustomerID = RT_CID_DLINK;
3130 priv->CustomerID = RT_CID_DEFAULT;
3135 switch(priv->CustomerID)
3137 case RT_CID_819x_RUNTOP:
3138 priv->LedStrategy = SW_LED_MODE2;
3142 priv->LedStrategy = SW_LED_MODE4;
3146 priv->LedStrategy = SW_LED_MODE0;
3152 if(priv->rf_type == RF_1T2R)
3154 RT_TRACE(COMP_EPROM, "\n1T2R config\n");
3158 RT_TRACE(COMP_EPROM, "\n2T4R config\n");
3161 // 2008/01/16 MH We can only know RF type in the function. So we have to init
3162 // DIG RATR table again.
3163 init_rate_adaptive(dev);
3164 //we need init DIG RATR table here again.
3166 RT_TRACE(COMP_EPROM, "<===========%s()\n", __FUNCTION__);
3170 short rtl8192_get_channel_map(struct net_device * dev)
3172 struct r8192_priv *priv = ieee80211_priv(dev);
3173 #ifdef ENABLE_DOT11D
3174 if(priv->ChannelPlan > COUNTRY_CODE_GLOBAL_DOMAIN){
3175 printk("rtl8180_init:Error channel plan! Set to default.\n");
3176 priv->ChannelPlan= 0;
3178 RT_TRACE(COMP_INIT, "Channel plan is %d\n",priv->ChannelPlan);
3180 rtl819x_set_channel_map(priv->ChannelPlan, priv);
3183 //Set Default Channel Plan
3185 DMESG("No channels, aborting");
3189 priv->ChannelPlan= 0;//hikaru
3190 // set channels 1..14 allowed in given locale
3191 for (i=1; i<=14; i++) {
3192 (priv->ieee80211->channel_map)[i] = (u8)(ch & 0x01);
3199 short rtl8192_init(struct net_device *dev)
3202 struct r8192_priv *priv = ieee80211_priv(dev);
3204 memset(&(priv->stats),0,sizeof(struct Stats));
3205 memset(priv->txqueue_to_outpipemap,0,9);
3209 u8 queuetopipe[]={3,2,1,0,4,8,7,6,5};
3210 memcpy(priv->txqueue_to_outpipemap,queuetopipe,9);
3212 printk("%d ",priv->txqueue_to_outpipemap[i]);
3217 u8 queuetopipe[]={3,2,1,0,4,4,0,4,4};
3218 memcpy(priv->txqueue_to_outpipemap,queuetopipe,9);
3220 printk("%d ",priv->txqueue_to_outpipemap[i]);
3224 rtl8192_init_priv_variable(dev);
3225 rtl8192_init_priv_lock(priv);
3226 rtl8192_init_priv_task(dev);
3227 rtl8192_get_eeprom_size(dev);
3228 rtl8192_read_eeprom_info(dev);
3229 rtl8192_get_channel_map(dev);
3231 init_timer(&priv->watch_dog_timer);
3232 priv->watch_dog_timer.data = (unsigned long)dev;
3233 priv->watch_dog_timer.function = watch_dog_timer_callback;
3234 if(rtl8192_usb_initendpoints(dev)!=0){
3235 DMESG("Endopoints initialization failed");
3239 //rtl8192_adapter_start(dev);
3246 /******************************************************************************
3247 *function: This function actually only set RRSR, RATR and BW_OPMODE registers
3248 * not to do all the hw config as its name says
3249 * input: net_device dev
3252 * notice: This part need to modified according to the rate set we filtered
3253 * ****************************************************************************/
3254 void rtl8192_hwconfig(struct net_device* dev)
3256 u32 regRATR = 0, regRRSR = 0;
3257 u8 regBwOpMode = 0, regTmp = 0;
3258 struct r8192_priv *priv = ieee80211_priv(dev);
3260 // Set RRSR, RATR, and BW_OPMODE registers
3262 switch(priv->ieee80211->mode)
3264 case WIRELESS_MODE_B:
3265 regBwOpMode = BW_OPMODE_20MHZ;
3266 regRATR = RATE_ALL_CCK;
3267 regRRSR = RATE_ALL_CCK;
3269 case WIRELESS_MODE_A:
3270 regBwOpMode = BW_OPMODE_5G |BW_OPMODE_20MHZ;
3271 regRATR = RATE_ALL_OFDM_AG;
3272 regRRSR = RATE_ALL_OFDM_AG;
3274 case WIRELESS_MODE_G:
3275 regBwOpMode = BW_OPMODE_20MHZ;
3276 regRATR = RATE_ALL_CCK | RATE_ALL_OFDM_AG;
3277 regRRSR = RATE_ALL_CCK | RATE_ALL_OFDM_AG;
3279 case WIRELESS_MODE_AUTO:
3281 if (Adapter->bInHctTest)
3283 regBwOpMode = BW_OPMODE_20MHZ;
3284 regRATR = RATE_ALL_CCK | RATE_ALL_OFDM_AG;
3285 regRRSR = RATE_ALL_CCK | RATE_ALL_OFDM_AG;
3290 regBwOpMode = BW_OPMODE_20MHZ;
3291 regRATR = RATE_ALL_CCK | RATE_ALL_OFDM_AG | RATE_ALL_OFDM_1SS | RATE_ALL_OFDM_2SS;
3292 regRRSR = RATE_ALL_CCK | RATE_ALL_OFDM_AG;
3295 case WIRELESS_MODE_N_24G:
3296 // It support CCK rate by default.
3297 // CCK rate will be filtered out only when associated AP does not support it.
3298 regBwOpMode = BW_OPMODE_20MHZ;
3299 regRATR = RATE_ALL_CCK | RATE_ALL_OFDM_AG | RATE_ALL_OFDM_1SS | RATE_ALL_OFDM_2SS;
3300 regRRSR = RATE_ALL_CCK | RATE_ALL_OFDM_AG;
3302 case WIRELESS_MODE_N_5G:
3303 regBwOpMode = BW_OPMODE_5G;
3304 regRATR = RATE_ALL_OFDM_AG | RATE_ALL_OFDM_1SS | RATE_ALL_OFDM_2SS;
3305 regRRSR = RATE_ALL_OFDM_AG;
3309 write_nic_byte(dev, BW_OPMODE, regBwOpMode);
3312 ratr_value = regRATR;
3313 if (priv->rf_type == RF_1T2R)
3315 ratr_value &= ~(RATE_ALL_OFDM_2SS);
3317 write_nic_dword(dev, RATR0, ratr_value);
3318 write_nic_byte(dev, UFWP, 1);
3320 regTmp = read_nic_byte(dev, 0x313);
3321 regRRSR = ((regTmp) << 24) | (regRRSR & 0x00ffffff);
3322 write_nic_dword(dev, RRSR, regRRSR);
3325 // Set Retry Limit here
3327 write_nic_word(dev, RETRY_LIMIT,
3328 priv->ShortRetryLimit << RETRY_LIMIT_SHORT_SHIFT | \
3329 priv->LongRetryLimit << RETRY_LIMIT_LONG_SHIFT);
3330 // Set Contention Window here
3334 // Set Tx Antenna including Feedback control
3336 // Set Auto Rate fallback control
3342 //InitializeAdapter and PhyCfg
3343 bool rtl8192_adapter_start(struct net_device *dev)
3345 struct r8192_priv *priv = ieee80211_priv(dev);
3347 bool init_status = true;
3348 RT_TRACE(COMP_INIT, "====>%s()\n", __FUNCTION__);
3349 priv->Rf_Mode = RF_OP_By_SW_3wire;
3350 //for ASIC power on sequence
3351 write_nic_byte_E(dev, 0x5f, 0x80);
3353 write_nic_byte_E(dev, 0x5f, 0xf0);
3354 write_nic_byte_E(dev, 0x5d, 0x00);
3355 write_nic_byte_E(dev, 0x5e, 0x80);
3356 write_nic_byte(dev, 0x17, 0x37);
3359 priv->pFirmware->firmware_status = FW_STATUS_0_INIT;
3360 //config CPUReset Register
3361 //Firmware Reset or not?
3362 dwRegRead = read_nic_dword(dev, CPU_GEN);
3363 if (priv->pFirmware->firmware_status == FW_STATUS_0_INIT)
3364 dwRegRead |= CPU_GEN_SYSTEM_RESET; //do nothing here?
3365 else if (priv->pFirmware->firmware_status == FW_STATUS_5_READY)
3366 dwRegRead |= CPU_GEN_FIRMWARE_RESET;
3368 RT_TRACE(COMP_ERR, "ERROR in %s(): undefined firmware state(%d)\n", __FUNCTION__, priv->pFirmware->firmware_status);
3370 write_nic_dword(dev, CPU_GEN, dwRegRead);
3373 rtl8192_BBConfig(dev);
3375 //Loopback mode or not
3376 priv->LoopbackMode = RTL819xU_NO_LOOPBACK;
3377 // priv->LoopbackMode = RTL819xU_MAC_LOOPBACK;
3379 dwRegRead = read_nic_dword(dev, CPU_GEN);
3380 if (priv->LoopbackMode == RTL819xU_NO_LOOPBACK)
3381 dwRegRead = ((dwRegRead & CPU_GEN_NO_LOOPBACK_MSK) | CPU_GEN_NO_LOOPBACK_SET);
3382 else if (priv->LoopbackMode == RTL819xU_MAC_LOOPBACK)
3383 dwRegRead |= CPU_CCK_LOOPBACK;
3385 RT_TRACE(COMP_ERR, "Serious error in %s(): wrong loopback mode setting(%d)\n", __FUNCTION__, priv->LoopbackMode);
3387 write_nic_dword(dev, CPU_GEN, dwRegRead);
3389 //after reset cpu, we need wait for a seconds to write in register.
3392 //xiong add for new bitfile:usb suspend reset pin set to 1. //do we need?
3393 write_nic_byte_E(dev, 0x5f, (read_nic_byte_E(dev, 0x5f)|0x20));
3396 rtl8192_hwconfig(dev);
3399 write_nic_byte(dev, CMDR, CR_RE|CR_TE);
3402 write_nic_dword(dev, MAC0, ((u32*)dev->dev_addr)[0]);
3403 write_nic_word(dev, MAC4, ((u16*)(dev->dev_addr + 4))[0]);
3406 write_nic_dword(dev, RCR, priv->ReceiveConfig);
3408 //Initialize Number of Reserved Pages in Firmware Queue
3409 write_nic_dword(dev, RQPN1, NUM_OF_PAGE_IN_FW_QUEUE_BK << RSVD_FW_QUEUE_PAGE_BK_SHIFT |\
3410 NUM_OF_PAGE_IN_FW_QUEUE_BE << RSVD_FW_QUEUE_PAGE_BE_SHIFT | \
3411 NUM_OF_PAGE_IN_FW_QUEUE_VI << RSVD_FW_QUEUE_PAGE_VI_SHIFT | \
3412 NUM_OF_PAGE_IN_FW_QUEUE_VO <<RSVD_FW_QUEUE_PAGE_VO_SHIFT);
3413 write_nic_dword(dev, RQPN2, NUM_OF_PAGE_IN_FW_QUEUE_MGNT << RSVD_FW_QUEUE_PAGE_MGNT_SHIFT |\
3414 NUM_OF_PAGE_IN_FW_QUEUE_CMD << RSVD_FW_QUEUE_PAGE_CMD_SHIFT);
3415 write_nic_dword(dev, RQPN3, APPLIED_RESERVED_QUEUE_IN_FW| \
3416 NUM_OF_PAGE_IN_FW_QUEUE_BCN<<RSVD_FW_QUEUE_PAGE_BCN_SHIFT
3417 // | NUM_OF_PAGE_IN_FW_QUEUE_PUB<<RSVD_FW_QUEUE_PAGE_PUB_SHIFT
3419 write_nic_dword(dev, RATR0+4*7, (RATE_ALL_OFDM_AG | RATE_ALL_CCK));
3422 // TODO: (it value is only for FPGA version). need to be changed!!2006.12.18, by Emily
3423 write_nic_byte(dev, ACK_TIMEOUT, 0x30);
3425 // RT_TRACE(COMP_INIT, "%s():priv->ResetProgress is %d\n", __FUNCTION__,priv->ResetProgress);
3426 if(priv->ResetProgress == RESET_TYPE_NORESET)
3427 rtl8192_SetWirelessMode(dev, priv->ieee80211->mode);
3428 if(priv->ResetProgress == RESET_TYPE_NORESET){
3429 CamResetAllEntry(dev);
3431 u8 SECR_value = 0x0;
3432 SECR_value |= SCR_TxEncEnable;
3433 SECR_value |= SCR_RxDecEnable;
3434 SECR_value |= SCR_NoSKMC;
3435 write_nic_byte(dev, SECR, SECR_value);
3440 write_nic_word(dev, ATIMWND, 2);
3441 write_nic_word(dev, BCN_INTERVAL, 100);
3444 #define DEFAULT_EDCA 0x005e4332
3446 for (i=0; i<QOS_QUEUE_NUM; i++)
3447 write_nic_dword(dev, WDCAPARA_ADD[i], DEFAULT_EDCA);
3449 #ifdef USB_RX_AGGREGATION_SUPPORT
3450 //3 For usb rx firmware aggregation control
3451 if(priv->ResetProgress == RESET_TYPE_NORESET)
3454 PRT_HIGH_THROUGHPUT pHTInfo = priv->ieee80211->pHTInfo;
3455 ulValue = (pHTInfo->UsbRxFwAggrEn<<24) | (pHTInfo->UsbRxFwAggrPageNum<<16) |
3456 (pHTInfo->UsbRxFwAggrPacketNum<<8) | (pHTInfo->UsbRxFwAggrTimeout);
3458 * If usb rx firmware aggregation is enabled,
3459 * when anyone of three threshold conditions above is reached,
3460 * firmware will send aggregated packet to driver.
3462 write_nic_dword(dev, 0x1a8, ulValue);
3463 priv->bCurrentRxAggrEnable = true;
3467 rtl8192_phy_configmac(dev);
3469 if (priv->card_8192_version == (u8) VERSION_819xU_A)
3471 rtl8192_phy_getTxPower(dev);
3472 rtl8192_phy_setTxPower(dev, priv->chan);
3476 init_status = init_firmware(dev);
3479 RT_TRACE(COMP_ERR,"ERR!!! %s(): Firmware download is failed\n", __FUNCTION__);
3482 RT_TRACE(COMP_INIT, "%s():after firmware download\n", __FUNCTION__);
3485 if(Adapter->ResetProgress == RESET_TYPE_NORESET)
3487 if(pMgntInfo->RegRfOff == TRUE)
3488 { // User disable RF via registry.
3489 RT_TRACE((COMP_INIT|COMP_RF), DBG_LOUD, ("InitializeAdapter819xUsb(): Turn off RF for RegRfOff ----------\n"));
3490 MgntActSet_RF_State(Adapter, eRfOff, RF_CHANGE_BY_SW);
3491 // Those action will be discard in MgntActSet_RF_State because off the same state
3492 for(eRFPath = 0; eRFPath <pHalData->NumTotalRFPath; eRFPath++)
3493 PHY_SetRFReg(Adapter, (RF90_RADIO_PATH_E)eRFPath, 0x4, 0xC00, 0x0);
3495 else if(pMgntInfo->RfOffReason > RF_CHANGE_BY_PS)
3496 { // H/W or S/W RF OFF before sleep.
3497 RT_TRACE((COMP_INIT|COMP_RF), DBG_LOUD, ("InitializeAdapter819xUsb(): Turn off RF for RfOffReason(%d) ----------\n", pMgntInfo->RfOffReason));
3498 MgntActSet_RF_State(Adapter, eRfOff, pMgntInfo->RfOffReason);
3502 pHalData->eRFPowerState = eRfOn;
3503 pMgntInfo->RfOffReason = 0;
3504 RT_TRACE((COMP_INIT|COMP_RF), DBG_LOUD, ("InitializeAdapter819xUsb(): RF is on ----------\n"));
3509 if(pHalData->eRFPowerState == eRfOff)
3511 MgntActSet_RF_State(Adapter, eRfOff, pMgntInfo->RfOffReason);
3512 // Those action will be discard in MgntActSet_RF_State because off the same state
3513 for(eRFPath = 0; eRFPath <pHalData->NumTotalRFPath; eRFPath++)
3514 PHY_SetRFReg(Adapter, (RF90_RADIO_PATH_E)eRFPath, 0x4, 0xC00, 0x0);
3519 if(priv->ResetProgress == RESET_TYPE_NORESET){
3520 rtl8192_phy_RFConfig(dev);
3521 RT_TRACE(COMP_INIT, "%s():after phy RF config\n", __FUNCTION__);
3525 if(priv->ieee80211->FwRWRF)
3526 // We can force firmware to do RF-R/W
3527 priv->Rf_Mode = RF_OP_By_FW;
3529 priv->Rf_Mode = RF_OP_By_SW_3wire;
3532 rtl8192_phy_updateInitGain(dev);
3533 /*--set CCK and OFDM Block "ON"--*/
3534 rtl8192_setBBreg(dev, rFPGA0_RFMOD, bCCKEn, 0x1);
3535 rtl8192_setBBreg(dev, rFPGA0_RFMOD, bOFDMEn, 0x1);
3537 if(priv->ResetProgress == RESET_TYPE_NORESET)
3540 u8 tmpvalue = read_nic_byte(dev, 0x301);
3544 RT_TRACE(COMP_POWER_TRACKING, "D-cut\n");
3548 priv->bDcut = FALSE;
3549 RT_TRACE(COMP_POWER_TRACKING, "C-cut\n");
3551 dm_initialize_txpower_tracking(dev);
3553 if(priv->bDcut == TRUE)
3556 u32 tmpRegA= rtl8192_QueryBBReg(dev,rOFDM0_XATxIQImbalance,bMaskDWord);
3557 // u32 tmpRegC= rtl8192_QueryBBReg(dev,rOFDM0_XCTxIQImbalance,bMaskDWord);
3558 for(i = 0; i<TxBBGainTableLength; i++)
3560 if(tmpRegA == priv->txbbgain_table[i].txbbgain_value)
3562 priv->rfa_txpowertrackingindex= (u8)i;
3563 priv->rfa_txpowertrackingindex_real= (u8)i;
3564 priv->rfa_txpowertracking_default= priv->rfa_txpowertrackingindex;
3569 TempCCk = rtl8192_QueryBBReg(dev, rCCK0_TxFilter1, bMaskByte2);
3571 for(i=0 ; i<CCKTxBBGainTableLength ; i++)
3574 if(TempCCk == priv->cck_txbbgain_table[i].ccktxbb_valuearray[0])
3576 priv->cck_present_attentuation_20Mdefault=(u8) i;
3580 priv->cck_present_attentuation_40Mdefault= 0;
3581 priv->cck_present_attentuation_difference= 0;
3582 priv->cck_present_attentuation = priv->cck_present_attentuation_20Mdefault;
3584 // pMgntInfo->bTXPowerTracking = FALSE;//TEMPLY DISABLE
3587 write_nic_byte(dev, 0x87, 0x0);
3593 /* this configures registers for beacon tx and enables it via
3594 * rtl8192_beacon_tx_enable(). rtl8192_beacon_tx_disable() might
3595 * be used to stop beacon transmission
3597 /***************************************************************************
3598 -------------------------------NET STUFF---------------------------
3599 ***************************************************************************/
3601 static struct net_device_stats *rtl8192_stats(struct net_device *dev)
3603 struct r8192_priv *priv = ieee80211_priv(dev);
3605 return &priv->ieee80211->stats;
3609 HalTxCheckStuck819xUsb(
3610 struct net_device *dev
3613 struct r8192_priv *priv = ieee80211_priv(dev);
3614 u16 RegTxCounter = read_nic_word(dev, 0x128);
3615 bool bStuck = FALSE;
3616 RT_TRACE(COMP_RESET,"%s():RegTxCounter is %d,TxCounter is %d\n",__FUNCTION__,RegTxCounter,priv->TxCounter);
3617 if(priv->TxCounter==RegTxCounter)
3620 priv->TxCounter = RegTxCounter;
3626 * <Assumption: RT_TX_SPINLOCK is acquired.>
3627 * First added: 2006.11.19 by emily
3630 TxCheckStuck(struct net_device *dev)
3632 struct r8192_priv *priv = ieee80211_priv(dev);
3635 // u8 ResetThreshold;
3636 bool bCheckFwTxCnt = false;
3637 //unsigned long flags;
3640 // Decide Stuch threshold according to current power save mode
3643 // RT_TRACE(COMP_RESET, " ==> TxCheckStuck()\n");
3644 // PlatformAcquireSpinLock(Adapter, RT_TX_SPINLOCK);
3645 // spin_lock_irqsave(&priv->ieee80211->lock,flags);
3646 for (QueueID = 0; QueueID<=BEACON_QUEUE;QueueID ++)
3648 if(QueueID == TXCMD_QUEUE)
3650 #ifdef USB_TX_DRIVER_AGGREGATION_ENABLE
3651 if((skb_queue_len(&priv->ieee80211->skb_waitQ[QueueID]) == 0) && (skb_queue_len(&priv->ieee80211->skb_aggQ[QueueID]) == 0) && (skb_queue_len(&priv->ieee80211->skb_drv_aggQ[QueueID]) == 0))
3653 if((skb_queue_len(&priv->ieee80211->skb_waitQ[QueueID]) == 0) && (skb_queue_len(&priv->ieee80211->skb_aggQ[QueueID]) == 0))
3657 bCheckFwTxCnt = true;
3659 // PlatformReleaseSpinLock(Adapter, RT_TX_SPINLOCK);
3660 // spin_unlock_irqrestore(&priv->ieee80211->lock,flags);
3661 // RT_TRACE(COMP_RESET,"bCheckFwTxCnt is %d\n",bCheckFwTxCnt);
3664 if(HalTxCheckStuck819xUsb(dev))
3666 RT_TRACE(COMP_RESET, "TxCheckStuck(): Fw indicates no Tx condition! \n");
3667 return RESET_TYPE_SILENT;
3670 return RESET_TYPE_NORESET;
3674 HalRxCheckStuck819xUsb(struct net_device *dev)
3676 u16 RegRxCounter = read_nic_word(dev, 0x130);
3677 struct r8192_priv *priv = ieee80211_priv(dev);
3678 bool bStuck = FALSE;
3679 static u8 rx_chk_cnt = 0;
3680 RT_TRACE(COMP_RESET,"%s(): RegRxCounter is %d,RxCounter is %d\n",__FUNCTION__,RegRxCounter,priv->RxCounter);
3681 // If rssi is small, we should check rx for long time because of bad rx.
3682 // or maybe it will continuous silent reset every 2 seconds.
3684 if(priv->undecorated_smoothed_pwdb >= (RateAdaptiveTH_High+5))
3686 rx_chk_cnt = 0; //high rssi, check rx stuck right now.
3688 else if(priv->undecorated_smoothed_pwdb < (RateAdaptiveTH_High+5) &&
3689 ((priv->CurrentChannelBW!=HT_CHANNEL_WIDTH_20&&priv->undecorated_smoothed_pwdb>=RateAdaptiveTH_Low_40M) ||
3690 (priv->CurrentChannelBW==HT_CHANNEL_WIDTH_20&&priv->undecorated_smoothed_pwdb>=RateAdaptiveTH_Low_20M)) )
3701 else if(((priv->CurrentChannelBW!=HT_CHANNEL_WIDTH_20&&priv->undecorated_smoothed_pwdb<RateAdaptiveTH_Low_40M) ||
3702 (priv->CurrentChannelBW==HT_CHANNEL_WIDTH_20&&priv->undecorated_smoothed_pwdb<RateAdaptiveTH_Low_20M)) &&
3703 priv->undecorated_smoothed_pwdb >= VeryLowRSSI)
3707 //DbgPrint("RSSI < %d && RSSI >= %d, no check this time \n", RateAdaptiveTH_Low, VeryLowRSSI);
3713 //DbgPrint("RSSI < %d && RSSI >= %d, check this time \n", RateAdaptiveTH_Low, VeryLowRSSI);
3720 //DbgPrint("RSSI <= %d, no check this time \n", VeryLowRSSI);
3726 //DbgPrint("RSSI <= %d, check this time \n", VeryLowRSSI);
3730 if(priv->RxCounter==RegRxCounter)
3733 priv->RxCounter = RegRxCounter;
3739 RxCheckStuck(struct net_device *dev)
3741 struct r8192_priv *priv = ieee80211_priv(dev);
3743 bool bRxCheck = FALSE;
3745 // RT_TRACE(COMP_RESET," ==> RxCheckStuck()\n");
3746 //PlatformAcquireSpinLock(Adapter, RT_RX_SPINLOCK);
3748 if(priv->IrpPendingCount > 1)
3750 //PlatformReleaseSpinLock(Adapter, RT_RX_SPINLOCK);
3752 // RT_TRACE(COMP_RESET,"bRxCheck is %d \n",bRxCheck);
3755 if(HalRxCheckStuck819xUsb(dev))
3757 RT_TRACE(COMP_RESET, "RxStuck Condition\n");
3758 return RESET_TYPE_SILENT;
3761 return RESET_TYPE_NORESET;
3766 * This function is called by Checkforhang to check whether we should ask OS to reset driver
3768 * \param pAdapter The adapter context for this miniport
3770 * Note:NIC with USB interface sholud not call this function because we cannot scan descriptor
3771 * to judge whether there is tx stuck.
3772 * Note: This function may be required to be rewrite for Vista OS.
3773 * <<<Assumption: Tx spinlock has been acquired >>>
3775 * 8185 and 8185b does not implement this function. This is added by Emily at 2006.11.24
3778 rtl819x_ifcheck_resetornot(struct net_device *dev)
3780 struct r8192_priv *priv = ieee80211_priv(dev);
3781 RESET_TYPE TxResetType = RESET_TYPE_NORESET;
3782 RESET_TYPE RxResetType = RESET_TYPE_NORESET;
3783 RT_RF_POWER_STATE rfState;
3785 rfState = priv->ieee80211->eRFPowerState;
3787 TxResetType = TxCheckStuck(dev);
3788 if( rfState != eRfOff ||
3789 /*ADAPTER_TEST_STATUS_FLAG(Adapter, ADAPTER_STATUS_FW_DOWNLOAD_FAILURE)) &&*/
3790 (priv->ieee80211->iw_mode != IW_MODE_ADHOC))
3792 // If driver is in the status of firmware download failure , driver skips RF initialization and RF is
3793 // in turned off state. Driver should check whether Rx stuck and do silent reset. And
3794 // if driver is in firmware download failure status, driver should initialize RF in the following
3795 // silent reset procedure Emily, 2008.01.21
3797 // Driver should not check RX stuck in IBSS mode because it is required to
3798 // set Check BSSID in order to send beacon, however, if check BSSID is
3799 // set, STA cannot hear any packet a all. Emily, 2008.04.12
3800 RxResetType = RxCheckStuck(dev);
3802 if(TxResetType==RESET_TYPE_NORMAL || RxResetType==RESET_TYPE_NORMAL)
3803 return RESET_TYPE_NORMAL;
3804 else if(TxResetType==RESET_TYPE_SILENT || RxResetType==RESET_TYPE_SILENT){
3805 RT_TRACE(COMP_RESET,"%s():silent reset\n",__FUNCTION__);
3806 return RESET_TYPE_SILENT;
3809 return RESET_TYPE_NORESET;
3813 void rtl8192_cancel_deferred_work(struct r8192_priv* priv);
3814 int _rtl8192_up(struct net_device *dev);
3815 int rtl8192_close(struct net_device *dev);
3820 CamRestoreAllEntry( struct net_device *dev)
3823 struct r8192_priv *priv = ieee80211_priv(dev);
3824 u8* MacAddr = priv->ieee80211->current_network.bssid;
3826 static u8 CAM_CONST_ADDR[4][6] = {
3827 {0x00, 0x00, 0x00, 0x00, 0x00, 0x00},
3828 {0x00, 0x00, 0x00, 0x00, 0x00, 0x01},
3829 {0x00, 0x00, 0x00, 0x00, 0x00, 0x02},
3830 {0x00, 0x00, 0x00, 0x00, 0x00, 0x03}};
3831 static u8 CAM_CONST_BROAD[] =
3832 {0xff, 0xff, 0xff, 0xff, 0xff, 0xff};
3834 RT_TRACE(COMP_SEC, "CamRestoreAllEntry: \n");
3837 if ((priv->ieee80211->pairwise_key_type == KEY_TYPE_WEP40)||
3838 (priv->ieee80211->pairwise_key_type == KEY_TYPE_WEP104))
3841 for(EntryId=0; EntryId<4; EntryId++)
3844 MacAddr = CAM_CONST_ADDR[EntryId];
3848 priv->ieee80211->pairwise_key_type,
3856 else if(priv->ieee80211->pairwise_key_type == KEY_TYPE_TKIP)
3860 if(priv->ieee80211->iw_mode == IW_MODE_ADHOC)
3864 priv->ieee80211->pairwise_key_type,
3872 priv->ieee80211->pairwise_key_type,
3878 else if(priv->ieee80211->pairwise_key_type == KEY_TYPE_CCMP)
3882 if(priv->ieee80211->iw_mode == IW_MODE_ADHOC)
3886 priv->ieee80211->pairwise_key_type,
3894 priv->ieee80211->pairwise_key_type,
3903 if(priv->ieee80211->group_key_type == KEY_TYPE_TKIP)
3905 MacAddr = CAM_CONST_BROAD;
3906 for(EntryId=1 ; EntryId<4 ; EntryId++)
3912 priv->ieee80211->group_key_type,
3918 if(priv->ieee80211->iw_mode == IW_MODE_ADHOC)
3922 priv->ieee80211->group_key_type,
3927 else if(priv->ieee80211->group_key_type == KEY_TYPE_CCMP)
3929 MacAddr = CAM_CONST_BROAD;
3930 for(EntryId=1; EntryId<4 ; EntryId++)
3936 priv->ieee80211->group_key_type,
3943 if(priv->ieee80211->iw_mode == IW_MODE_ADHOC)
3947 priv->ieee80211->group_key_type,
3953 //////////////////////////////////////////////////////////////
3954 // This function is used to fix Tx/Rx stop bug temporarily.
3955 // This function will do "system reset" to NIC when Tx or Rx is stuck.
3956 // The method checking Tx/Rx stuck of this function is supported by FW,
3957 // which reports Tx and Rx counter to register 0x128 and 0x130.
3958 //////////////////////////////////////////////////////////////
3960 rtl819x_ifsilentreset(struct net_device *dev)
3962 //OCTET_STRING asocpdu;
3963 struct r8192_priv *priv = ieee80211_priv(dev);
3965 int reset_status = 0;
3966 struct ieee80211_device *ieee = priv->ieee80211;
3969 // 2007.07.20. If we need to check CCK stop, please uncomment this line.
3970 //bStuck = Adapter->HalFunc.CheckHWStopHandler(Adapter);
3972 if(priv->ResetProgress==RESET_TYPE_NORESET)
3976 RT_TRACE(COMP_RESET,"=========>Reset progress!! \n");
3978 // Set the variable for reset.
3979 priv->ResetProgress = RESET_TYPE_SILENT;
3980 // rtl8192_close(dev);
3981 down(&priv->wx_sem);
3984 RT_TRACE(COMP_ERR,"%s():the driver is not up! return\n",__FUNCTION__);
3989 RT_TRACE(COMP_RESET,"%s():======>start to down the driver\n",__FUNCTION__);
3990 // if(!netif_queue_stopped(dev))
3991 // netif_stop_queue(dev);
3993 rtl8192_rtx_disable(dev);
3994 rtl8192_cancel_deferred_work(priv);
3996 del_timer_sync(&priv->watch_dog_timer);
3998 ieee->sync_scan_hurryup = 1;
3999 if(ieee->state == IEEE80211_LINKED)
4001 down(&ieee->wx_sem);
4002 printk("ieee->state is IEEE80211_LINKED\n");
4003 ieee80211_stop_send_beacons(priv->ieee80211);
4004 del_timer_sync(&ieee->associate_timer);
4005 cancel_delayed_work(&ieee->associate_retry_wq);
4006 ieee80211_stop_scan(ieee);
4007 netif_carrier_off(dev);
4011 printk("ieee->state is NOT LINKED\n");
4012 ieee80211_softmac_stop_protocol(priv->ieee80211); }
4014 RT_TRACE(COMP_RESET,"%s():<==========down process is finished\n",__FUNCTION__);
4015 //rtl8192_irq_disable(dev);
4016 RT_TRACE(COMP_RESET,"%s():===========>start to up the driver\n",__FUNCTION__);
4017 reset_status = _rtl8192_up(dev);
4019 RT_TRACE(COMP_RESET,"%s():<===========up process is finished\n",__FUNCTION__);
4020 if(reset_status == -EAGAIN)
4029 RT_TRACE(COMP_ERR," ERR!!! %s(): Reset Failed!!\n", __FUNCTION__);
4032 ieee->is_silent_reset = 1;
4033 EnableHWSecurityConfig8192(dev);
4034 if(ieee->state == IEEE80211_LINKED && ieee->iw_mode == IW_MODE_INFRA)
4036 ieee->set_chan(ieee->dev, ieee->current_network.channel);
4038 queue_work(ieee->wq, &ieee->associate_complete_wq);
4041 else if(ieee->state == IEEE80211_LINKED && ieee->iw_mode == IW_MODE_ADHOC)
4043 ieee->set_chan(ieee->dev, ieee->current_network.channel);
4044 ieee->link_change(ieee->dev);
4046 // notify_wx_assoc_event(ieee);
4048 ieee80211_start_send_beacons(ieee);
4050 if (ieee->data_hard_resume)
4051 ieee->data_hard_resume(ieee->dev);
4052 netif_carrier_on(ieee->dev);
4055 CamRestoreAllEntry(dev);
4057 priv->ResetProgress = RESET_TYPE_NORESET;
4058 priv->reset_count++;
4060 priv->bForcedSilentReset =false;
4061 priv->bResetInProgress = false;
4063 // For test --> force write UFWP.
4064 write_nic_byte(dev, UFWP, 1);
4065 RT_TRACE(COMP_RESET, "Reset finished!! ====>[%d]\n", priv->reset_count);
4069 void CAM_read_entry(
4070 struct net_device *dev,
4074 u32 target_command=0;
4075 u32 target_content=0;
4079 // printk("=======>start read CAM\n");
4080 for(entry_i=0;entry_i<CAM_CONTENT_COUNT;entry_i++)
4082 // polling bit, and No Write enable, and address
4083 target_command= entry_i+CAM_CONTENT_COUNT*iIndex;
4084 target_command= target_command | BIT31;
4086 //Check polling bit is clear
4090 ulStatus = read_nic_dword(dev, RWCAM);
4091 if(ulStatus & BIT31){
4098 write_nic_dword(dev, RWCAM, target_command);
4099 RT_TRACE(COMP_SEC,"CAM_read_entry(): WRITE A0: %x \n",target_command);
4100 // printk("CAM_read_entry(): WRITE A0: %lx \n",target_command);
4101 target_content = read_nic_dword(dev, RCAMO);
4102 RT_TRACE(COMP_SEC, "CAM_read_entry(): WRITE A8: %x \n",target_content);
4103 // printk("CAM_read_entry(): WRITE A8: %lx \n",target_content);
4108 void rtl819x_update_rxcounts(
4109 struct r8192_priv *priv,
4118 *TotalRxDataNum = 0;
4120 SlotIndex = (priv->ieee80211->LinkDetectInfo.SlotIndex++)%(priv->ieee80211->LinkDetectInfo.SlotNum);
4121 priv->ieee80211->LinkDetectInfo.RxBcnNum[SlotIndex] = priv->ieee80211->LinkDetectInfo.NumRecvBcnInPeriod;
4122 priv->ieee80211->LinkDetectInfo.RxDataNum[SlotIndex] = priv->ieee80211->LinkDetectInfo.NumRecvDataInPeriod;
4123 for( i=0; i<priv->ieee80211->LinkDetectInfo.SlotNum; i++ ){
4124 *TotalRxBcnNum += priv->ieee80211->LinkDetectInfo.RxBcnNum[i];
4125 *TotalRxDataNum += priv->ieee80211->LinkDetectInfo.RxDataNum[i];
4130 extern void rtl819x_watchdog_wqcallback(struct work_struct *work)
4132 struct delayed_work *dwork = container_of(work,struct delayed_work,work);
4133 struct r8192_priv *priv = container_of(dwork,struct r8192_priv,watch_dog_wq);
4134 struct net_device *dev = priv->ieee80211->dev;
4135 struct ieee80211_device* ieee = priv->ieee80211;
4136 RESET_TYPE ResetType = RESET_TYPE_NORESET;
4137 static u8 check_reset_cnt=0;
4138 bool bBusyTraffic = false;
4142 hal_dm_watchdog(dev);
4144 {//to get busy traffic condition
4145 if(ieee->state == IEEE80211_LINKED)
4147 if( ieee->LinkDetectInfo.NumRxOkInPeriod> 666 ||
4148 ieee->LinkDetectInfo.NumTxOkInPeriod> 666 ) {
4149 bBusyTraffic = true;
4151 ieee->LinkDetectInfo.NumRxOkInPeriod = 0;
4152 ieee->LinkDetectInfo.NumTxOkInPeriod = 0;
4153 ieee->LinkDetectInfo.bBusyTraffic = bBusyTraffic;
4156 //added by amy for AP roaming
4158 if(priv->ieee80211->state == IEEE80211_LINKED && priv->ieee80211->iw_mode == IW_MODE_INFRA)
4160 u32 TotalRxBcnNum = 0;
4161 u32 TotalRxDataNum = 0;
4163 rtl819x_update_rxcounts(priv, &TotalRxBcnNum, &TotalRxDataNum);
4164 if((TotalRxBcnNum+TotalRxDataNum) == 0)
4167 if(rfState == eRfOff)
4168 RT_TRACE(COMP_ERR,"========>%s()\n",__FUNCTION__);
4170 printk("===>%s(): AP is power off,connect another one\n",__FUNCTION__);
4171 // Dot11d_Reset(dev);
4172 priv->ieee80211->state = IEEE80211_ASSOCIATING;
4173 notify_wx_assoc_event(priv->ieee80211);
4174 RemovePeerTS(priv->ieee80211,priv->ieee80211->current_network.bssid);
4175 priv->ieee80211->link_change(dev);
4176 queue_work(priv->ieee80211->wq, &priv->ieee80211->associate_procedure_wq);
4180 priv->ieee80211->LinkDetectInfo.NumRecvBcnInPeriod=0;
4181 priv->ieee80211->LinkDetectInfo.NumRecvDataInPeriod=0;
4183 // CAM_read_entry(dev,4);
4184 //check if reset the driver
4185 if(check_reset_cnt++ >= 3)
4187 ResetType = rtl819x_ifcheck_resetornot(dev);
4188 check_reset_cnt = 3;
4189 //DbgPrint("Start to check silent reset\n");
4191 // RT_TRACE(COMP_RESET,"%s():priv->force_reset is %d,priv->ResetProgress is %d, priv->bForcedSilentReset is %d,priv->bDisableNormalResetCheck is %d,ResetType is %d\n",__FUNCTION__,priv->force_reset,priv->ResetProgress,priv->bForcedSilentReset,priv->bDisableNormalResetCheck,ResetType);
4192 if( (priv->force_reset) || (priv->ResetProgress==RESET_TYPE_NORESET &&
4193 (priv->bForcedSilentReset ||
4194 (!priv->bDisableNormalResetCheck && ResetType==RESET_TYPE_SILENT)))) // This is control by OID set in Pomelo
4196 RT_TRACE(COMP_RESET,"%s():priv->force_reset is %d,priv->ResetProgress is %d, priv->bForcedSilentReset is %d,priv->bDisableNormalResetCheck is %d,ResetType is %d\n",__FUNCTION__,priv->force_reset,priv->ResetProgress,priv->bForcedSilentReset,priv->bDisableNormalResetCheck,ResetType);
4197 rtl819x_ifsilentreset(dev);
4199 priv->force_reset = false;
4200 priv->bForcedSilentReset = false;
4201 priv->bResetInProgress = false;
4202 RT_TRACE(COMP_TRACE, " <==RtUsbCheckForHangWorkItemCallback()\n");
4206 void watch_dog_timer_callback(unsigned long data)
4208 struct r8192_priv *priv = ieee80211_priv((struct net_device *) data);
4209 //printk("===============>watch_dog timer\n");
4210 queue_delayed_work(priv->priv_wq,&priv->watch_dog_wq, 0);
4211 mod_timer(&priv->watch_dog_timer, jiffies + MSECS(IEEE80211_WATCH_DOG_TIME));
4213 int _rtl8192_up(struct net_device *dev)
4215 struct r8192_priv *priv = ieee80211_priv(dev);
4217 int init_status = 0;
4219 priv->ieee80211->ieee_up=1;
4220 RT_TRACE(COMP_INIT, "Bringing up iface");
4221 init_status = rtl8192_adapter_start(dev);
4224 RT_TRACE(COMP_ERR,"ERR!!! %s(): initialization is failed!\n", __FUNCTION__);
4225 priv->up=priv->ieee80211->ieee_up = 0;
4228 RT_TRACE(COMP_INIT, "start adapter finished\n");
4229 rtl8192_rx_enable(dev);
4230 // rtl8192_tx_enable(dev);
4231 if(priv->ieee80211->state != IEEE80211_LINKED)
4232 ieee80211_softmac_start_protocol(priv->ieee80211);
4233 ieee80211_reset_queue(priv->ieee80211);
4234 watch_dog_timer_callback((unsigned long) dev);
4235 if(!netif_queue_stopped(dev))
4236 netif_start_queue(dev);
4238 netif_wake_queue(dev);
4244 int rtl8192_open(struct net_device *dev)
4246 struct r8192_priv *priv = ieee80211_priv(dev);
4248 down(&priv->wx_sem);
4249 ret = rtl8192_up(dev);
4256 int rtl8192_up(struct net_device *dev)
4258 struct r8192_priv *priv = ieee80211_priv(dev);
4260 if (priv->up == 1) return -1;
4262 return _rtl8192_up(dev);
4266 int rtl8192_close(struct net_device *dev)
4268 struct r8192_priv *priv = ieee80211_priv(dev);
4271 down(&priv->wx_sem);
4273 ret = rtl8192_down(dev);
4281 int rtl8192_down(struct net_device *dev)
4283 struct r8192_priv *priv = ieee80211_priv(dev);
4286 if (priv->up == 0) return -1;
4289 priv->ieee80211->ieee_up = 0;
4290 RT_TRACE(COMP_DOWN, "==========>%s()\n", __FUNCTION__);
4292 if (!netif_queue_stopped(dev))
4293 netif_stop_queue(dev);
4295 rtl8192_rtx_disable(dev);
4296 //rtl8192_irq_disable(dev);
4298 /* Tx related queue release */
4299 for(i = 0; i < MAX_QUEUE_SIZE; i++) {
4300 skb_queue_purge(&priv->ieee80211->skb_waitQ [i]);
4302 for(i = 0; i < MAX_QUEUE_SIZE; i++) {
4303 skb_queue_purge(&priv->ieee80211->skb_aggQ [i]);
4306 for(i = 0; i < MAX_QUEUE_SIZE; i++) {
4307 skb_queue_purge(&priv->ieee80211->skb_drv_aggQ [i]);
4310 //as cancel_delayed_work will del work->timer, so if work is not definedas struct delayed_work, it will corrupt
4311 // flush_scheduled_work();
4312 rtl8192_cancel_deferred_work(priv);
4314 del_timer_sync(&priv->watch_dog_timer);
4317 ieee80211_softmac_stop_protocol(priv->ieee80211);
4318 memset(&priv->ieee80211->current_network, 0 , offsetof(struct ieee80211_network, list));
4319 RT_TRACE(COMP_DOWN, "<==========%s()\n", __FUNCTION__);
4325 void rtl8192_commit(struct net_device *dev)
4327 struct r8192_priv *priv = ieee80211_priv(dev);
4328 int reset_status = 0;
4329 //u8 reset_times = 0;
4330 if (priv->up == 0) return ;
4333 rtl8192_cancel_deferred_work(priv);
4334 del_timer_sync(&priv->watch_dog_timer);
4335 //cancel_delayed_work(&priv->SwChnlWorkItem);
4337 ieee80211_softmac_stop_protocol(priv->ieee80211);
4339 //rtl8192_irq_disable(dev);
4340 rtl8192_rtx_disable(dev);
4341 reset_status = _rtl8192_up(dev);
4346 void rtl8192_restart(struct net_device *dev)
4348 struct r8192_priv *priv = ieee80211_priv(dev);
4350 void rtl8192_restart(struct work_struct *work)
4352 struct r8192_priv *priv = container_of(work, struct r8192_priv, reset_wq);
4353 struct net_device *dev = priv->ieee80211->dev;
4355 down(&priv->wx_sem);
4357 rtl8192_commit(dev);
4362 static void r8192_set_multicast(struct net_device *dev)
4364 struct r8192_priv *priv = ieee80211_priv(dev);
4367 //down(&priv->wx_sem);
4371 promisc = (dev->flags & IFF_PROMISC) ? 1:0;
4373 if (promisc != priv->promisc)
4374 // rtl8192_commit(dev);
4376 priv->promisc = promisc;
4378 //schedule_work(&priv->reset_wq);
4379 //up(&priv->wx_sem);
4383 int r8192_set_mac_adr(struct net_device *dev, void *mac)
4385 struct r8192_priv *priv = ieee80211_priv(dev);
4386 struct sockaddr *addr = mac;
4388 down(&priv->wx_sem);
4390 memcpy(dev->dev_addr, addr->sa_data, ETH_ALEN);
4392 schedule_work(&priv->reset_wq);
4398 /* based on ipw2200 driver */
4399 int rtl8192_ioctl(struct net_device *dev, struct ifreq *rq, int cmd)
4401 struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
4402 struct iwreq *wrq = (struct iwreq *)rq;
4404 struct ieee80211_device *ieee = priv->ieee80211;
4406 u8 broadcast_addr[6] = {0xff,0xff,0xff,0xff,0xff,0xff};
4407 struct iw_point *p = &wrq->u.data;
4408 struct ieee_param *ipw = NULL;//(struct ieee_param *)wrq->u.data.pointer;
4410 down(&priv->wx_sem);
4413 if (p->length < sizeof(struct ieee_param) || !p->pointer){
4418 ipw = kmalloc(p->length, GFP_KERNEL);
4423 if (copy_from_user(ipw, p->pointer, p->length)) {
4430 case RTL_IOCTL_WPA_SUPPLICANT:
4431 //parse here for HW security
4432 if (ipw->cmd == IEEE_CMD_SET_ENCRYPTION)
4434 if (ipw->u.crypt.set_tx)
4436 if (strcmp(ipw->u.crypt.alg, "CCMP") == 0)
4437 ieee->pairwise_key_type = KEY_TYPE_CCMP;
4438 else if (strcmp(ipw->u.crypt.alg, "TKIP") == 0)
4439 ieee->pairwise_key_type = KEY_TYPE_TKIP;
4440 else if (strcmp(ipw->u.crypt.alg, "WEP") == 0)
4442 if (ipw->u.crypt.key_len == 13)
4443 ieee->pairwise_key_type = KEY_TYPE_WEP104;
4444 else if (ipw->u.crypt.key_len == 5)
4445 ieee->pairwise_key_type = KEY_TYPE_WEP40;
4448 ieee->pairwise_key_type = KEY_TYPE_NA;
4450 if (ieee->pairwise_key_type)
4452 memcpy((u8*)key, ipw->u.crypt.key, 16);
4453 EnableHWSecurityConfig8192(dev);
4454 //we fill both index entry and 4th entry for pairwise key as in IPW interface, adhoc will only get here, so we need index entry for its default key serching!
4456 setKey(dev, 4, ipw->u.crypt.idx, ieee->pairwise_key_type, (u8*)ieee->ap_mac_addr, 0, key);
4457 if (ieee->auth_mode != 2)
4458 setKey(dev, ipw->u.crypt.idx, ipw->u.crypt.idx, ieee->pairwise_key_type, (u8*)ieee->ap_mac_addr, 0, key);
4461 else //if (ipw->u.crypt.idx) //group key use idx > 0
4463 memcpy((u8*)key, ipw->u.crypt.key, 16);
4464 if (strcmp(ipw->u.crypt.alg, "CCMP") == 0)
4465 ieee->group_key_type= KEY_TYPE_CCMP;
4466 else if (strcmp(ipw->u.crypt.alg, "TKIP") == 0)
4467 ieee->group_key_type = KEY_TYPE_TKIP;
4468 else if (strcmp(ipw->u.crypt.alg, "WEP") == 0)
4470 if (ipw->u.crypt.key_len == 13)
4471 ieee->group_key_type = KEY_TYPE_WEP104;
4472 else if (ipw->u.crypt.key_len == 5)
4473 ieee->group_key_type = KEY_TYPE_WEP40;
4476 ieee->group_key_type = KEY_TYPE_NA;
4478 if (ieee->group_key_type)
4482 ipw->u.crypt.idx, //KeyIndex
4483 ieee->group_key_type, //KeyType
4484 broadcast_addr, //MacAddr
4490 #ifdef JOHN_HWSEC_DEBUG
4492 printk("@@ wrq->u pointer = ");
4493 for(i=0;i<wrq->u.data.length;i++){
4494 if(i%10==0) printk("\n");
4495 printk( "%8x|", ((u32*)wrq->u.data.pointer)[i] );
4498 #endif /*JOHN_HWSEC_DEBUG*/
4499 ret = ieee80211_wpa_supplicant_ioctl(priv->ieee80211, &wrq->u.data);
4513 u8 HwRateToMRate90(bool bIsHT, u8 rate)
4519 case DESC90_RATE1M: ret_rate = MGN_1M; break;
4520 case DESC90_RATE2M: ret_rate = MGN_2M; break;
4521 case DESC90_RATE5_5M: ret_rate = MGN_5_5M; break;
4522 case DESC90_RATE11M: ret_rate = MGN_11M; break;
4523 case DESC90_RATE6M: ret_rate = MGN_6M; break;
4524 case DESC90_RATE9M: ret_rate = MGN_9M; break;
4525 case DESC90_RATE12M: ret_rate = MGN_12M; break;
4526 case DESC90_RATE18M: ret_rate = MGN_18M; break;
4527 case DESC90_RATE24M: ret_rate = MGN_24M; break;
4528 case DESC90_RATE36M: ret_rate = MGN_36M; break;
4529 case DESC90_RATE48M: ret_rate = MGN_48M; break;
4530 case DESC90_RATE54M: ret_rate = MGN_54M; break;
4534 RT_TRACE(COMP_RECV, "HwRateToMRate90(): Non supported Rate [%x], bIsHT = %d!!!\n", rate, bIsHT);
4540 case DESC90_RATEMCS0: ret_rate = MGN_MCS0; break;
4541 case DESC90_RATEMCS1: ret_rate = MGN_MCS1; break;
4542 case DESC90_RATEMCS2: ret_rate = MGN_MCS2; break;
4543 case DESC90_RATEMCS3: ret_rate = MGN_MCS3; break;
4544 case DESC90_RATEMCS4: ret_rate = MGN_MCS4; break;
4545 case DESC90_RATEMCS5: ret_rate = MGN_MCS5; break;
4546 case DESC90_RATEMCS6: ret_rate = MGN_MCS6; break;
4547 case DESC90_RATEMCS7: ret_rate = MGN_MCS7; break;
4548 case DESC90_RATEMCS8: ret_rate = MGN_MCS8; break;
4549 case DESC90_RATEMCS9: ret_rate = MGN_MCS9; break;
4550 case DESC90_RATEMCS10: ret_rate = MGN_MCS10; break;
4551 case DESC90_RATEMCS11: ret_rate = MGN_MCS11; break;
4552 case DESC90_RATEMCS12: ret_rate = MGN_MCS12; break;
4553 case DESC90_RATEMCS13: ret_rate = MGN_MCS13; break;
4554 case DESC90_RATEMCS14: ret_rate = MGN_MCS14; break;
4555 case DESC90_RATEMCS15: ret_rate = MGN_MCS15; break;
4556 case DESC90_RATEMCS32: ret_rate = (0x80|0x20); break;
4560 RT_TRACE(COMP_RECV, "HwRateToMRate90(): Non supported Rate [%x], bIsHT = %d!!!\n",rate, bIsHT);
4569 * Function: UpdateRxPktTimeStamp
4570 * Overview: Recored down the TSF time stamp when receiving a packet
4578 * (pRfd->Status.TimeStampHigh is updated)
4579 * (pRfd->Status.TimeStampLow is updated)
4583 void UpdateRxPktTimeStamp8190 (struct net_device *dev, struct ieee80211_rx_stats *stats)
4585 struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
4587 if(stats->bIsAMPDU && !stats->bFirstMPDU) {
4588 stats->mac_time[0] = priv->LastRxDescTSFLow;
4589 stats->mac_time[1] = priv->LastRxDescTSFHigh;
4591 priv->LastRxDescTSFLow = stats->mac_time[0];
4592 priv->LastRxDescTSFHigh = stats->mac_time[1];
4598 long rtl819x_translate_todbm(u8 signal_strength_index )// 0-100 index.
4600 long signal_power; // in dBm.
4602 // Translate to dBm (x=0.5y-95).
4603 signal_power = (long)((signal_strength_index + 1) >> 1);
4606 return signal_power;
4610 /* 2008/01/22 MH We can not delcare RSSI/EVM total value of sliding window to
4611 be a local static. Otherwise, it may increase when we return from S3/S4. The
4612 value will be kept in memory or disk. We must delcare the value in adapter
4613 and it will be reinitialized when return from S3/S4. */
4614 void rtl8192_process_phyinfo(struct r8192_priv * priv,u8* buffer, struct ieee80211_rx_stats * pprevious_stats, struct ieee80211_rx_stats * pcurrent_stats)
4616 bool bcheck = false;
4618 u32 nspatial_stream, tmp_val;
4620 static u32 slide_rssi_index=0, slide_rssi_statistics=0;
4621 static u32 slide_evm_index=0, slide_evm_statistics=0;
4622 static u32 last_rssi=0, last_evm=0;
4624 static u32 slide_beacon_adc_pwdb_index=0, slide_beacon_adc_pwdb_statistics=0;
4625 static u32 last_beacon_adc_pwdb=0;
4627 struct ieee80211_hdr_3addr *hdr;
4629 unsigned int frag,seq;
4630 hdr = (struct ieee80211_hdr_3addr *)buffer;
4631 sc = le16_to_cpu(hdr->seq_ctl);
4632 frag = WLAN_GET_SEQ_FRAG(sc);
4633 seq = WLAN_GET_SEQ_SEQ(sc);
4634 //cosa add 04292008 to record the sequence number
4635 pcurrent_stats->Seq_Num = seq;
4637 // Check whether we should take the previous packet into accounting
4639 if(!pprevious_stats->bIsAMPDU)
4641 // if previous packet is not aggregated packet
4648 if(slide_rssi_statistics++ >= PHY_RSSI_SLID_WIN_MAX)
4650 slide_rssi_statistics = PHY_RSSI_SLID_WIN_MAX;
4651 last_rssi = priv->stats.slide_signal_strength[slide_rssi_index];
4652 priv->stats.slide_rssi_total -= last_rssi;
4654 priv->stats.slide_rssi_total += pprevious_stats->SignalStrength;
4656 priv->stats.slide_signal_strength[slide_rssi_index++] = pprevious_stats->SignalStrength;
4657 if(slide_rssi_index >= PHY_RSSI_SLID_WIN_MAX)
4658 slide_rssi_index = 0;
4660 // <1> Showed on UI for user, in dbm
4661 tmp_val = priv->stats.slide_rssi_total/slide_rssi_statistics;
4662 priv->stats.signal_strength = rtl819x_translate_todbm((u8)tmp_val);
4663 pcurrent_stats->rssi = priv->stats.signal_strength;
4665 // If the previous packet does not match the criteria, neglect it
4667 if(!pprevious_stats->bPacketMatchBSSID)
4669 if(!pprevious_stats->bToSelfBA)
4677 //rtl8190_process_cck_rxpathsel(priv,pprevious_stats);//only rtl8190 supported
4682 priv->stats.num_process_phyinfo++;
4684 /* record the general signal strength to the sliding window. */
4687 // <2> Showed on UI for engineering
4688 // hardware does not provide rssi information for each rf path in CCK
4689 if(!pprevious_stats->bIsCCK && (pprevious_stats->bPacketToSelf || pprevious_stats->bToSelfBA))
4691 for (rfpath = RF90_PATH_A; rfpath < priv->NumTotalRFPath; rfpath++)
4693 if (!rtl8192_phy_CheckIsLegalRFPath(priv->ieee80211->dev, rfpath))
4696 //Fixed by Jacken 2008-03-20
4697 if(priv->stats.rx_rssi_percentage[rfpath] == 0)
4699 priv->stats.rx_rssi_percentage[rfpath] = pprevious_stats->RxMIMOSignalStrength[rfpath];
4700 //DbgPrint("MIMO RSSI initialize \n");
4702 if(pprevious_stats->RxMIMOSignalStrength[rfpath] > priv->stats.rx_rssi_percentage[rfpath])
4704 priv->stats.rx_rssi_percentage[rfpath] =
4705 ( (priv->stats.rx_rssi_percentage[rfpath]*(Rx_Smooth_Factor-1)) +
4706 (pprevious_stats->RxMIMOSignalStrength[rfpath])) /(Rx_Smooth_Factor);
4707 priv->stats.rx_rssi_percentage[rfpath] = priv->stats.rx_rssi_percentage[rfpath] + 1;
4711 priv->stats.rx_rssi_percentage[rfpath] =
4712 ( (priv->stats.rx_rssi_percentage[rfpath]*(Rx_Smooth_Factor-1)) +
4713 (pprevious_stats->RxMIMOSignalStrength[rfpath])) /(Rx_Smooth_Factor);
4715 RT_TRACE(COMP_DBG,"priv->stats.rx_rssi_percentage[rfPath] = %d \n" ,priv->stats.rx_rssi_percentage[rfpath] );
4723 RT_TRACE(COMP_RXDESC, "Smooth %s PWDB = %d\n",
4724 pprevious_stats->bIsCCK? "CCK": "OFDM",
4725 pprevious_stats->RxPWDBAll);
4727 if(pprevious_stats->bPacketBeacon)
4729 /* record the beacon pwdb to the sliding window. */
4730 if(slide_beacon_adc_pwdb_statistics++ >= PHY_Beacon_RSSI_SLID_WIN_MAX)
4732 slide_beacon_adc_pwdb_statistics = PHY_Beacon_RSSI_SLID_WIN_MAX;
4733 last_beacon_adc_pwdb = priv->stats.Slide_Beacon_pwdb[slide_beacon_adc_pwdb_index];
4734 priv->stats.Slide_Beacon_Total -= last_beacon_adc_pwdb;
4735 //DbgPrint("slide_beacon_adc_pwdb_index = %d, last_beacon_adc_pwdb = %d, Adapter->RxStats.Slide_Beacon_Total = %d\n",
4736 // slide_beacon_adc_pwdb_index, last_beacon_adc_pwdb, Adapter->RxStats.Slide_Beacon_Total);
4738 priv->stats.Slide_Beacon_Total += pprevious_stats->RxPWDBAll;
4739 priv->stats.Slide_Beacon_pwdb[slide_beacon_adc_pwdb_index] = pprevious_stats->RxPWDBAll;
4740 //DbgPrint("slide_beacon_adc_pwdb_index = %d, pPreviousRfd->Status.RxPWDBAll = %d\n", slide_beacon_adc_pwdb_index, pPreviousRfd->Status.RxPWDBAll);
4741 slide_beacon_adc_pwdb_index++;
4742 if(slide_beacon_adc_pwdb_index >= PHY_Beacon_RSSI_SLID_WIN_MAX)
4743 slide_beacon_adc_pwdb_index = 0;
4744 pprevious_stats->RxPWDBAll = priv->stats.Slide_Beacon_Total/slide_beacon_adc_pwdb_statistics;
4745 if(pprevious_stats->RxPWDBAll >= 3)
4746 pprevious_stats->RxPWDBAll -= 3;
4749 RT_TRACE(COMP_RXDESC, "Smooth %s PWDB = %d\n",
4750 pprevious_stats->bIsCCK? "CCK": "OFDM",
4751 pprevious_stats->RxPWDBAll);
4754 if(pprevious_stats->bPacketToSelf || pprevious_stats->bPacketBeacon || pprevious_stats->bToSelfBA)
4756 if(priv->undecorated_smoothed_pwdb < 0) // initialize
4758 priv->undecorated_smoothed_pwdb = pprevious_stats->RxPWDBAll;
4759 //DbgPrint("First pwdb initialize \n");
4761 if(pprevious_stats->RxPWDBAll > (u32)priv->undecorated_smoothed_pwdb)
4763 priv->undecorated_smoothed_pwdb =
4764 ( ((priv->undecorated_smoothed_pwdb)*(Rx_Smooth_Factor-1)) +
4765 (pprevious_stats->RxPWDBAll)) /(Rx_Smooth_Factor);
4766 priv->undecorated_smoothed_pwdb = priv->undecorated_smoothed_pwdb + 1;
4770 priv->undecorated_smoothed_pwdb =
4771 ( ((priv->undecorated_smoothed_pwdb)*(Rx_Smooth_Factor-1)) +
4772 (pprevious_stats->RxPWDBAll)) /(Rx_Smooth_Factor);
4780 /* record the general EVM to the sliding window. */
4781 if(pprevious_stats->SignalQuality == 0)
4786 if(pprevious_stats->bPacketToSelf || pprevious_stats->bPacketBeacon || pprevious_stats->bToSelfBA){
4787 if(slide_evm_statistics++ >= PHY_RSSI_SLID_WIN_MAX){
4788 slide_evm_statistics = PHY_RSSI_SLID_WIN_MAX;
4789 last_evm = priv->stats.slide_evm[slide_evm_index];
4790 priv->stats.slide_evm_total -= last_evm;
4793 priv->stats.slide_evm_total += pprevious_stats->SignalQuality;
4795 priv->stats.slide_evm[slide_evm_index++] = pprevious_stats->SignalQuality;
4796 if(slide_evm_index >= PHY_RSSI_SLID_WIN_MAX)
4797 slide_evm_index = 0;
4799 // <1> Showed on UI for user, in percentage.
4800 tmp_val = priv->stats.slide_evm_total/slide_evm_statistics;
4801 priv->stats.signal_quality = tmp_val;
4802 //cosa add 10/11/2007, Showed on UI for user in Windows Vista, for Link quality.
4803 priv->stats.last_signal_strength_inpercent = tmp_val;
4806 // <2> Showed on UI for engineering
4807 if(pprevious_stats->bPacketToSelf || pprevious_stats->bPacketBeacon || pprevious_stats->bToSelfBA)
4809 for(nspatial_stream = 0; nspatial_stream<2 ; nspatial_stream++) // 2 spatial stream
4811 if(pprevious_stats->RxMIMOSignalQuality[nspatial_stream] != -1)
4813 if(priv->stats.rx_evm_percentage[nspatial_stream] == 0) // initialize
4815 priv->stats.rx_evm_percentage[nspatial_stream] = pprevious_stats->RxMIMOSignalQuality[nspatial_stream];
4817 priv->stats.rx_evm_percentage[nspatial_stream] =
4818 ( (priv->stats.rx_evm_percentage[nspatial_stream]* (Rx_Smooth_Factor-1)) +
4819 (pprevious_stats->RxMIMOSignalQuality[nspatial_stream]* 1)) / (Rx_Smooth_Factor);
4828 /*-----------------------------------------------------------------------------
4829 * Function: rtl819x_query_rxpwrpercentage()
4833 * Input: char antpower
4837 * Return: 0-100 percentage
4841 * 05/26/2008 amy Create Version 0 porting from windows code.
4843 *---------------------------------------------------------------------------*/
4844 static u8 rtl819x_query_rxpwrpercentage(
4848 if ((antpower <= -100) || (antpower >= 20))
4852 else if (antpower >= 0)
4858 return (100+antpower);
4861 } /* QueryRxPwrPercentage */
4864 rtl819x_evm_dbtopercentage(
4876 ret_val = 0 - ret_val;
4884 // We want good-looking for signal strength/quality
4885 // 2007/7/19 01:09, by cosa.
4888 rtl819x_signal_scale_mapping(
4894 // Step 1. Scale mapping.
4895 if(currsig >= 61 && currsig <= 100)
4897 retsig = 90 + ((currsig - 60) / 4);
4899 else if(currsig >= 41 && currsig <= 60)
4901 retsig = 78 + ((currsig - 40) / 2);
4903 else if(currsig >= 31 && currsig <= 40)
4905 retsig = 66 + (currsig - 30);
4907 else if(currsig >= 21 && currsig <= 30)
4909 retsig = 54 + (currsig - 20);
4911 else if(currsig >= 5 && currsig <= 20)
4913 retsig = 42 + (((currsig - 5) * 2) / 3);
4915 else if(currsig == 4)
4919 else if(currsig == 3)
4923 else if(currsig == 2)
4927 else if(currsig == 1)
4939 static void rtl8192_query_rxphystatus(
4940 struct r8192_priv * priv,
4941 struct ieee80211_rx_stats * pstats,
4942 rx_drvinfo_819x_usb * pdrvinfo,
4943 struct ieee80211_rx_stats * precord_stats,
4944 bool bpacket_match_bssid,
4945 bool bpacket_toself,
4950 //PRT_RFD_STATUS pRtRfdStatus = &(pRfd->Status);
4951 phy_sts_ofdm_819xusb_t* pofdm_buf;
4952 phy_sts_cck_819xusb_t * pcck_buf;
4953 phy_ofdm_rx_status_rxsc_sgien_exintfflag* prxsc;
4955 u8 i, max_spatial_stream, tmp_rxsnr, tmp_rxevm, rxsc_sgien_exflg;
4956 char rx_pwr[4], rx_pwr_all=0;
4957 //long rx_avg_pwr = 0;
4958 char rx_snrX, rx_evmX;
4960 u32 RSSI, total_rssi=0;//, total_evm=0;
4961 // long signal_strength_index = 0;
4966 priv->stats.numqry_phystatus++;
4968 is_cck_rate = rx_hal_is_cck_rate(pdrvinfo);
4970 // Record it for next packet processing
4971 memset(precord_stats, 0, sizeof(struct ieee80211_rx_stats));
4972 pstats->bPacketMatchBSSID = precord_stats->bPacketMatchBSSID = bpacket_match_bssid;
4973 pstats->bPacketToSelf = precord_stats->bPacketToSelf = bpacket_toself;
4974 pstats->bIsCCK = precord_stats->bIsCCK = is_cck_rate;//RX_HAL_IS_CCK_RATE(pDrvInfo);
4975 pstats->bPacketBeacon = precord_stats->bPacketBeacon = bPacketBeacon;
4976 pstats->bToSelfBA = precord_stats->bToSelfBA = bToSelfBA;
4978 prxpkt = (u8*)pdrvinfo;
4980 /* Move pointer to the 16th bytes. Phy status start address. */
4981 prxpkt += sizeof(rx_drvinfo_819x_usb);
4983 /* Initial the cck and ofdm buffer pointer */
4984 pcck_buf = (phy_sts_cck_819xusb_t *)prxpkt;
4985 pofdm_buf = (phy_sts_ofdm_819xusb_t *)prxpkt;
4987 pstats->RxMIMOSignalQuality[0] = -1;
4988 pstats->RxMIMOSignalQuality[1] = -1;
4989 precord_stats->RxMIMOSignalQuality[0] = -1;
4990 precord_stats->RxMIMOSignalQuality[1] = -1;
4995 // (1)Hardware does not provide RSSI for CCK
4999 // (2)PWDB, Average PWDB cacluated by hardware (for rate adaptive)
5001 u8 report;//, cck_agc_rpt;
5003 priv->stats.numqry_phystatusCCK++;
5005 if(!priv->bCckHighPower)
5007 report = pcck_buf->cck_agc_rpt & 0xc0;
5011 //Fixed by Jacken from Bryant 2008-03-20
5012 //Original value is -38 , -26 , -14 , -2
5013 //Fixed value is -35 , -23 , -11 , 6
5015 rx_pwr_all = -35 - (pcck_buf->cck_agc_rpt & 0x3e);
5018 rx_pwr_all = -23 - (pcck_buf->cck_agc_rpt & 0x3e);
5021 rx_pwr_all = -11 - (pcck_buf->cck_agc_rpt & 0x3e);
5024 rx_pwr_all = 6 - (pcck_buf->cck_agc_rpt & 0x3e);
5030 report = pcck_buf->cck_agc_rpt & 0x60;
5035 rx_pwr_all = -35 - ((pcck_buf->cck_agc_rpt & 0x1f)<<1) ;
5038 rx_pwr_all = -23 - ((pcck_buf->cck_agc_rpt & 0x1f)<<1);
5041 rx_pwr_all = -11 - ((pcck_buf->cck_agc_rpt & 0x1f)<<1) ;
5044 rx_pwr_all = 6 - ((pcck_buf->cck_agc_rpt & 0x1f)<<1) ;
5049 pwdb_all = rtl819x_query_rxpwrpercentage(rx_pwr_all);
5050 pstats->RxPWDBAll = precord_stats->RxPWDBAll = pwdb_all;
5051 pstats->RecvSignalPower = pwdb_all;
5054 // (3) Get Signal Quality (EVM)
5056 //if(bpacket_match_bssid)
5060 if(pstats->RxPWDBAll > 40)
5065 sq = pcck_buf->sq_rpt;
5067 if(pcck_buf->sq_rpt > 64)
5069 else if (pcck_buf->sq_rpt < 20)
5072 sq = ((64-sq) * 100) / 44;
5074 pstats->SignalQuality = precord_stats->SignalQuality = sq;
5075 pstats->RxMIMOSignalQuality[0] = precord_stats->RxMIMOSignalQuality[0] = sq;
5076 pstats->RxMIMOSignalQuality[1] = precord_stats->RxMIMOSignalQuality[1] = -1;
5081 priv->stats.numqry_phystatusHT++;
5083 // (1)Get RSSI for HT rate
5085 for(i=RF90_PATH_A; i<priv->NumTotalRFPath; i++)
5087 // 2008/01/30 MH we will judge RF RX path now.
5088 if (priv->brfpath_rxenable[i])
5093 if (!rtl8192_phy_CheckIsLegalRFPath(priv->ieee80211->dev, i))
5096 //Fixed by Jacken from Bryant 2008-03-20
5097 //Original value is 106
5098 rx_pwr[i] = ((pofdm_buf->trsw_gain_X[i]&0x3F)*2) - 106;
5100 //Get Rx snr value in DB
5101 tmp_rxsnr = pofdm_buf->rxsnr_X[i];
5102 rx_snrX = (char)(tmp_rxsnr);
5105 priv->stats.rxSNRdB[i] = (long)rx_snrX;
5107 /* Translate DBM to percentage. */
5108 RSSI = rtl819x_query_rxpwrpercentage(rx_pwr[i]);
5111 /* Record Signal Strength for next packet */
5112 //if(bpacket_match_bssid)
5114 pstats->RxMIMOSignalStrength[i] =(u8) RSSI;
5115 precord_stats->RxMIMOSignalStrength[i] =(u8) RSSI;
5121 // (2)PWDB, Average PWDB cacluated by hardware (for rate adaptive)
5123 //Fixed by Jacken from Bryant 2008-03-20
5124 //Original value is 106
5125 rx_pwr_all = (((pofdm_buf->pwdb_all ) >> 1 )& 0x7f) -106;
5126 pwdb_all = rtl819x_query_rxpwrpercentage(rx_pwr_all);
5128 pstats->RxPWDBAll = precord_stats->RxPWDBAll = pwdb_all;
5129 pstats->RxPower = precord_stats->RxPower = rx_pwr_all;
5132 // (3)EVM of HT rate
5134 if(pdrvinfo->RxHT && pdrvinfo->RxRate>=DESC90_RATEMCS8 &&
5135 pdrvinfo->RxRate<=DESC90_RATEMCS15)
5136 max_spatial_stream = 2; //both spatial stream make sense
5138 max_spatial_stream = 1; //only spatial stream 1 makes sense
5140 for(i=0; i<max_spatial_stream; i++)
5142 tmp_rxevm = pofdm_buf->rxevm_X[i];
5143 rx_evmX = (char)(tmp_rxevm);
5145 // Do not use shift operation like "rx_evmX >>= 1" because the compilor of free build environment
5146 // fill most significant bit to "zero" when doing shifting operation which may change a negative
5147 // value to positive one, then the dbm value (which is supposed to be negative) is not correct anymore.
5150 evm = rtl819x_evm_dbtopercentage(rx_evmX);
5151 //if(bpacket_match_bssid)
5153 if(i==0) // Fill value in RFD, Get the first spatial stream only
5154 pstats->SignalQuality = precord_stats->SignalQuality = (u8)(evm & 0xff);
5155 pstats->RxMIMOSignalQuality[i] = precord_stats->RxMIMOSignalQuality[i] = (u8)(evm & 0xff);
5160 /* record rx statistics for debug */
5161 rxsc_sgien_exflg = pofdm_buf->rxsc_sgien_exflg;
5162 prxsc = (phy_ofdm_rx_status_rxsc_sgien_exintfflag *)&rxsc_sgien_exflg;
5163 if(pdrvinfo->BW) //40M channel
5164 priv->stats.received_bwtype[1+prxsc->rxsc]++;
5166 priv->stats.received_bwtype[0]++;
5169 //UI BSS List signal strength(in percentage), make it good looking, from 0~100.
5170 //It is assigned to the BSS List in GetValueFromBeaconOrProbeRsp().
5173 pstats->SignalStrength = precord_stats->SignalStrength = (u8)(rtl819x_signal_scale_mapping((long)pwdb_all));//PWDB_ALL;
5178 //pRfd->Status.SignalStrength = pRecordRfd->Status.SignalStrength = (u8)(SignalScaleMapping(total_rssi/=RF90_PATH_MAX));//(u8)(total_rssi/=RF90_PATH_MAX);
5179 // We can judge RX path number now.
5181 pstats->SignalStrength = precord_stats->SignalStrength = (u8)(rtl819x_signal_scale_mapping((long)(total_rssi/=rf_rx_num)));
5183 } /* QueryRxPhyStatus8190Pci */
5186 rtl8192_record_rxdesc_forlateruse(
5187 struct ieee80211_rx_stats * psrc_stats,
5188 struct ieee80211_rx_stats * ptarget_stats
5191 ptarget_stats->bIsAMPDU = psrc_stats->bIsAMPDU;
5192 ptarget_stats->bFirstMPDU = psrc_stats->bFirstMPDU;
5193 ptarget_stats->Seq_Num = psrc_stats->Seq_Num;
5197 void TranslateRxSignalStuff819xUsb(struct sk_buff *skb,
5198 struct ieee80211_rx_stats * pstats,
5199 rx_drvinfo_819x_usb *pdrvinfo)
5201 // TODO: We must only check packet for current MAC address. Not finish
5202 rtl8192_rx_info *info = (struct rtl8192_rx_info *)skb->cb;
5203 struct net_device *dev=info->dev;
5204 struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
5205 bool bpacket_match_bssid, bpacket_toself;
5206 bool bPacketBeacon=FALSE, bToSelfBA=FALSE;
5207 static struct ieee80211_rx_stats previous_stats;
5208 struct ieee80211_hdr_3addr *hdr;//by amy
5211 // Get Signal Quality for only RX data queue (but not command queue)
5214 //u16 tmp_buf_len = 0;
5217 /* Get MAC frame start address. */
5218 tmp_buf = (u8*)skb->data;// + get_rxpacket_shiftbytes_819xusb(pstats);
5220 hdr = (struct ieee80211_hdr_3addr *)tmp_buf;
5221 fc = le16_to_cpu(hdr->frame_ctl);
5222 type = WLAN_FC_GET_TYPE(fc);
5223 praddr = hdr->addr1;
5225 /* Check if the received packet is acceptabe. */
5226 bpacket_match_bssid = ((IEEE80211_FTYPE_CTL != type) &&
5227 (eqMacAddr(priv->ieee80211->current_network.bssid, (fc & IEEE80211_FCTL_TODS)? hdr->addr1 : (fc & IEEE80211_FCTL_FROMDS )? hdr->addr2 : hdr->addr3))
5228 && (!pstats->bHwError) && (!pstats->bCRC)&& (!pstats->bICV));
5229 bpacket_toself = bpacket_match_bssid & (eqMacAddr(praddr, priv->ieee80211->dev->dev_addr));
5231 if(WLAN_FC_GET_FRAMETYPE(fc)== IEEE80211_STYPE_BEACON)
5233 bPacketBeacon = true;
5234 //DbgPrint("Beacon 2, MatchBSSID = %d, ToSelf = %d \n", bPacketMatchBSSID, bPacketToSelf);
5236 if(WLAN_FC_GET_FRAMETYPE(fc) == IEEE80211_STYPE_BLOCKACK)
5238 if((eqMacAddr(praddr,dev->dev_addr)))
5240 //DbgPrint("BlockAck, MatchBSSID = %d, ToSelf = %d \n", bPacketMatchBSSID, bPacketToSelf);
5245 if(bpacket_match_bssid)
5247 priv->stats.numpacket_matchbssid++;
5250 priv->stats.numpacket_toself++;
5253 // Process PHY information for previous packet (RSSI/PWDB/EVM)
5255 // Because phy information is contained in the last packet of AMPDU only, so driver
5256 // should process phy information of previous packet
5257 rtl8192_process_phyinfo(priv, tmp_buf, &previous_stats, pstats);
5258 rtl8192_query_rxphystatus(priv, pstats, pdrvinfo, &previous_stats, bpacket_match_bssid,bpacket_toself,bPacketBeacon,bToSelfBA);
5259 rtl8192_record_rxdesc_forlateruse(pstats, &previous_stats);
5264 * Function: UpdateReceivedRateHistogramStatistics
5265 * Overview: Recored down the received data rate
5268 * struct net_device *dev
5269 * struct ieee80211_rx_stats *stats
5273 * (priv->stats.ReceivedRateHistogram[] is updated)
5278 UpdateReceivedRateHistogramStatistics8190(
5279 struct net_device *dev,
5280 struct ieee80211_rx_stats *stats
5283 struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
5284 u32 rcvType=1; //0: Total, 1:OK, 2:CRC, 3:ICV
5286 u32 preamble_guardinterval; //1: short preamble/GI, 0: long preamble/GI
5291 else if(stats->bICV)
5294 if(stats->bShortPreamble)
5295 preamble_guardinterval = 1;// short
5297 preamble_guardinterval = 0;// long
5304 case MGN_1M: rateIndex = 0; break;
5305 case MGN_2M: rateIndex = 1; break;
5306 case MGN_5_5M: rateIndex = 2; break;
5307 case MGN_11M: rateIndex = 3; break;
5311 case MGN_6M: rateIndex = 4; break;
5312 case MGN_9M: rateIndex = 5; break;
5313 case MGN_12M: rateIndex = 6; break;
5314 case MGN_18M: rateIndex = 7; break;
5315 case MGN_24M: rateIndex = 8; break;
5316 case MGN_36M: rateIndex = 9; break;
5317 case MGN_48M: rateIndex = 10; break;
5318 case MGN_54M: rateIndex = 11; break;
5320 // 11n High throughput rate
5322 case MGN_MCS0: rateIndex = 12; break;
5323 case MGN_MCS1: rateIndex = 13; break;
5324 case MGN_MCS2: rateIndex = 14; break;
5325 case MGN_MCS3: rateIndex = 15; break;
5326 case MGN_MCS4: rateIndex = 16; break;
5327 case MGN_MCS5: rateIndex = 17; break;
5328 case MGN_MCS6: rateIndex = 18; break;
5329 case MGN_MCS7: rateIndex = 19; break;
5330 case MGN_MCS8: rateIndex = 20; break;
5331 case MGN_MCS9: rateIndex = 21; break;
5332 case MGN_MCS10: rateIndex = 22; break;
5333 case MGN_MCS11: rateIndex = 23; break;
5334 case MGN_MCS12: rateIndex = 24; break;
5335 case MGN_MCS13: rateIndex = 25; break;
5336 case MGN_MCS14: rateIndex = 26; break;
5337 case MGN_MCS15: rateIndex = 27; break;
5338 default: rateIndex = 28; break;
5340 priv->stats.received_preamble_GI[preamble_guardinterval][rateIndex]++;
5341 priv->stats.received_rate_histogram[0][rateIndex]++; //total
5342 priv->stats.received_rate_histogram[rcvType][rateIndex]++;
5346 void query_rxdesc_status(struct sk_buff *skb, struct ieee80211_rx_stats *stats, bool bIsRxAggrSubframe)
5348 rtl8192_rx_info *info = (struct rtl8192_rx_info *)skb->cb;
5349 struct net_device *dev=info->dev;
5350 struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
5351 //rx_desc_819x_usb *desc = (rx_desc_819x_usb *)skb->data;
5352 rx_drvinfo_819x_usb *driver_info = NULL;
5355 //Get Rx Descriptor Information
5357 #ifdef USB_RX_AGGREGATION_SUPPORT
5358 if (bIsRxAggrSubframe)
5360 rx_desc_819x_usb_aggr_subframe *desc = (rx_desc_819x_usb_aggr_subframe *)skb->data;
5361 stats->Length = desc->Length ;
5362 stats->RxDrvInfoSize = desc->RxDrvInfoSize;
5363 stats->RxBufShift = 0; //RxBufShift = 2 in RxDesc, but usb didn't shift bytes in fact.
5364 stats->bICV = desc->ICV;
5365 stats->bCRC = desc->CRC32;
5366 stats->bHwError = stats->bCRC|stats->bICV;
5367 stats->Decrypted = !desc->SWDec;//RTL8190 set this bit to indicate that Hw does not decrypt packet
5371 rx_desc_819x_usb *desc = (rx_desc_819x_usb *)skb->data;
5373 stats->Length = desc->Length;
5374 stats->RxDrvInfoSize = desc->RxDrvInfoSize;
5375 stats->RxBufShift = 0;//desc->Shift&0x03;
5376 stats->bICV = desc->ICV;
5377 stats->bCRC = desc->CRC32;
5378 stats->bHwError = stats->bCRC|stats->bICV;
5379 //RTL8190 set this bit to indicate that Hw does not decrypt packet
5380 stats->Decrypted = !desc->SWDec;
5383 if((priv->ieee80211->pHTInfo->bCurrentHTSupport == true) && (priv->ieee80211->pairwise_key_type == KEY_TYPE_CCMP))
5385 stats->bHwError = false;
5389 stats->bHwError = stats->bCRC|stats->bICV;
5392 if(stats->Length < 24 || stats->Length > MAX_8192U_RX_SIZE)
5393 stats->bHwError |= 1;
5397 // TODO: Need to verify it on FGPA platform
5398 //Driver info are written to the RxBuffer following rx desc
5399 if (stats->RxDrvInfoSize != 0) {
5400 driver_info = (rx_drvinfo_819x_usb *)(skb->data + sizeof(rx_desc_819x_usb) + \
5404 if(!stats->bHwError){
5406 ret_rate = HwRateToMRate90(driver_info->RxHT, driver_info->RxRate);
5407 if(ret_rate == 0xff)
5409 // Abnormal Case: Receive CRC OK packet with Rx descriptor indicating non supported rate.
5410 // Special Error Handling here, 2008.05.16, by Emily
5412 stats->bHwError = 1;
5413 stats->rate = MGN_1M; //Set 1M rate by default
5416 stats->rate = ret_rate;
5422 stats->bShortPreamble = driver_info->SPLCP;
5425 UpdateReceivedRateHistogramStatistics8190(dev, stats);
5427 stats->bIsAMPDU = (driver_info->PartAggr==1);
5428 stats->bFirstMPDU = (driver_info->PartAggr==1) && (driver_info->FirstAGGR==1);
5429 stats->TimeStampLow = driver_info->TSFL;
5430 // xiong mask it, 070514
5431 //pRfd->Status.TimeStampHigh = PlatformEFIORead4Byte(Adapter, TSFR+4);
5432 // stats->TimeStampHigh = read_nic_dword(dev, TSFR+4);
5434 UpdateRxPktTimeStamp8190(dev, stats);
5439 if(driver_info->FirstAGGR==1 || driver_info->PartAggr == 1)
5440 RT_TRACE(COMP_RXDESC, "driver_info->FirstAGGR = %d, driver_info->PartAggr = %d\n",
5441 driver_info->FirstAGGR, driver_info->PartAggr);
5445 skb_pull(skb,sizeof(rx_desc_819x_usb));
5447 // Get Total offset of MPDU Frame Body
5449 if((stats->RxBufShift + stats->RxDrvInfoSize) > 0) {
5451 skb_pull(skb,stats->RxBufShift + stats->RxDrvInfoSize);
5454 #ifdef USB_RX_AGGREGATION_SUPPORT
5455 /* for the rx aggregated sub frame, the redundant space truelly contained in the packet */
5456 if(bIsRxAggrSubframe) {
5460 /* for debug 2008.5.29 */
5462 //added by vivi, for MP, 20080108
5463 stats->RxIs40MHzPacket = driver_info->BW;
5464 if(stats->RxDrvInfoSize != 0)
5465 TranslateRxSignalStuff819xUsb(skb, stats, driver_info);
5469 u32 GetRxPacketShiftBytes819xUsb(struct ieee80211_rx_stats *Status, bool bIsRxAggrSubframe)
5471 #ifdef USB_RX_AGGREGATION_SUPPORT
5472 if (bIsRxAggrSubframe)
5473 return (sizeof(rx_desc_819x_usb) + Status->RxDrvInfoSize
5474 + Status->RxBufShift + 8);
5477 return (sizeof(rx_desc_819x_usb) + Status->RxDrvInfoSize
5478 + Status->RxBufShift);
5481 void rtl8192_rx_nomal(struct sk_buff* skb)
5483 rtl8192_rx_info *info = (struct rtl8192_rx_info *)skb->cb;
5484 struct net_device *dev=info->dev;
5485 struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
5486 struct ieee80211_rx_stats stats = {
5490 // .mac_time = jiffies,
5491 .freq = IEEE80211_24GHZ_BAND,
5494 struct ieee80211_hdr_1addr *ieee80211_hdr = NULL;
5495 bool unicast_packet = false;
5496 #ifdef USB_RX_AGGREGATION_SUPPORT
5497 struct sk_buff *agg_skb = NULL;
5498 u32 TotalLength = 0;
5500 u32 PacketLength = 0;
5501 u32 PacketOccupiedLendth = 0;
5503 u32 PacketShiftBytes = 0;
5504 rx_desc_819x_usb_aggr_subframe *RxDescr = NULL;
5505 u8 PaddingBytes = 0;
5506 //add just for testing
5511 /* 20 is for ps-poll */
5512 if((skb->len >=(20 + sizeof(rx_desc_819x_usb))) && (skb->len < RX_URB_SIZE)) {
5513 #ifdef USB_RX_AGGREGATION_SUPPORT
5514 TempByte = *(skb->data + sizeof(rx_desc_819x_usb));
5516 /* first packet should not contain Rx aggregation header */
5517 query_rxdesc_status(skb, &stats, false);
5519 /* hardware related info */
5520 #ifdef USB_RX_AGGREGATION_SUPPORT
5521 if (TempByte & BIT0) {
5523 //TotalLength = agg_skb->len - 4; /*sCrcLng*/
5524 TotalLength = stats.Length - 4; /*sCrcLng*/
5525 //RT_TRACE(COMP_RECV, "%s:first aggregated packet!Length=%d\n",__FUNCTION__,TotalLength);
5526 /* though the head pointer has passed this position */
5527 TempDWord = *(u32 *)(agg_skb->data - 4);
5528 PacketLength = (u16)(TempDWord & 0x3FFF); /*sCrcLng*/
5529 skb = dev_alloc_skb(PacketLength);
5530 memcpy(skb_put(skb,PacketLength),agg_skb->data,PacketLength);
5531 PacketShiftBytes = GetRxPacketShiftBytes819xUsb(&stats, false);
5534 /* Process the MPDU recevied */
5535 skb_trim(skb, skb->len - 4/*sCrcLng*/);
5537 rx_pkt_len = skb->len;
5538 ieee80211_hdr = (struct ieee80211_hdr_1addr *)skb->data;
5539 unicast_packet = false;
5540 if(is_broadcast_ether_addr(ieee80211_hdr->addr1)) {
5542 }else if(is_multicast_ether_addr(ieee80211_hdr->addr1)){
5545 /* unicast packet */
5546 unicast_packet = true;
5549 if(!ieee80211_rx(priv->ieee80211,skb, &stats)) {
5550 dev_kfree_skb_any(skb);
5552 priv->stats.rxoktotal++;
5553 if(unicast_packet) {
5554 priv->stats.rxbytesunicast += rx_pkt_len;
5557 #ifdef USB_RX_AGGREGATION_SUPPORT
5559 // (PipeIndex == 0) && (TempByte & BIT0) => TotalLength > 0.
5560 if (TotalLength > 0) {
5561 PacketOccupiedLendth = PacketLength + (PacketShiftBytes + 8);
5562 if ((PacketOccupiedLendth & 0xFF) != 0)
5563 PacketOccupiedLendth = (PacketOccupiedLendth & 0xFFFFFF00) + 256;
5564 PacketOccupiedLendth -= 8;
5565 TempDWord = PacketOccupiedLendth - PacketShiftBytes; /*- PacketLength */
5566 if (agg_skb->len > TempDWord)
5567 skb_pull(agg_skb, TempDWord);
5571 while (agg_skb->len>=GetRxPacketShiftBytes819xUsb(&stats, true)) {
5572 u8 tmpCRC = 0, tmpICV = 0;
5573 //RT_TRACE(COMP_RECV,"%s:aggred pkt,total_len = %d\n",__FUNCTION__,agg_skb->len);
5574 RxDescr = (rx_desc_819x_usb_aggr_subframe *)(agg_skb->data);
5575 tmpCRC = RxDescr->CRC32;
5576 tmpICV = RxDescr->ICV;
5577 memcpy(agg_skb->data, &agg_skb->data[44], 2);
5578 RxDescr->CRC32 = tmpCRC;
5579 RxDescr->ICV = tmpICV;
5581 memset(&stats, 0, sizeof(struct ieee80211_rx_stats));
5585 stats.freq = IEEE80211_24GHZ_BAND;
5586 query_rxdesc_status(agg_skb, &stats, true);
5587 PacketLength = stats.Length;
5589 if(PacketLength > agg_skb->len) {
5592 /* Process the MPDU recevied */
5593 skb = dev_alloc_skb(PacketLength);
5594 memcpy(skb_put(skb,PacketLength),agg_skb->data, PacketLength);
5595 skb_trim(skb, skb->len - 4/*sCrcLng*/);
5597 rx_pkt_len = skb->len;
5598 ieee80211_hdr = (struct ieee80211_hdr_1addr *)skb->data;
5599 unicast_packet = false;
5600 if(is_broadcast_ether_addr(ieee80211_hdr->addr1)) {
5602 }else if(is_multicast_ether_addr(ieee80211_hdr->addr1)){
5605 /* unicast packet */
5606 unicast_packet = true;
5608 if(!ieee80211_rx(priv->ieee80211,skb, &stats)) {
5609 dev_kfree_skb_any(skb);
5611 priv->stats.rxoktotal++;
5612 if(unicast_packet) {
5613 priv->stats.rxbytesunicast += rx_pkt_len;
5616 /* should trim the packet which has been copied to target skb */
5617 skb_pull(agg_skb, PacketLength);
5618 PacketShiftBytes = GetRxPacketShiftBytes819xUsb(&stats, true);
5619 PacketOccupiedLendth = PacketLength + PacketShiftBytes;
5620 if ((PacketOccupiedLendth & 0xFF) != 0) {
5621 PaddingBytes = 256 - (PacketOccupiedLendth & 0xFF);
5622 if (agg_skb->len > PaddingBytes)
5623 skb_pull(agg_skb, PaddingBytes);
5628 dev_kfree_skb(agg_skb);
5632 priv->stats.rxurberr++;
5633 printk("actual_length:%d\n", skb->len);
5634 dev_kfree_skb_any(skb);
5640 rtl819xusb_process_received_packet(
5641 struct net_device *dev,
5642 struct ieee80211_rx_stats *pstats
5645 // bool bfreerfd=false, bqueued=false;
5648 struct r8192_priv *priv = ieee80211_priv(dev);
5652 //PRX_TS_RECORD pts = NULL;
5654 // Get shifted bytes of Starting address of 802.11 header. 2006.09.28, by Emily
5655 //porting by amy 080508
5656 pstats->virtual_address += get_rxpacket_shiftbytes_819xusb(pstats);
5657 frame = pstats->virtual_address;
5658 frame_len = pstats->packetlength;
5659 #ifdef TODO // by amy about HCT
5660 if(!Adapter->bInHctTest)
5661 CountRxErrStatistics(Adapter, pRfd);
5664 #ifdef ENABLE_PS //by amy for adding ps function in future
5665 RT_RF_POWER_STATE rtState;
5666 // When RF is off, we should not count the packet for hw/sw synchronize
5667 // reason, ie. there may be a duration while sw switch is changed and hw
5668 // switch is being changed. 2006.12.04, by shien chang.
5669 Adapter->HalFunc.GetHwRegHandler(Adapter, HW_VAR_RF_STATE, (u8* )(&rtState));
5670 if (rtState == eRfOff)
5675 priv->stats.rxframgment++;
5679 RmMonitorSignalStrength(Adapter, pRfd);
5681 /* 2007/01/16 MH Add RX command packet handle here. */
5682 /* 2007/03/01 MH We have to release RFD and return if rx pkt is cmd pkt. */
5683 if (rtl819xusb_rx_command_packet(dev, pstats))
5695 void query_rx_cmdpkt_desc_status(struct sk_buff *skb, struct ieee80211_rx_stats *stats)
5697 // rtl8192_rx_info *info = (struct rtl8192_rx_info *)skb->cb;
5698 // struct net_device *dev=info->dev;
5699 // struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
5700 rx_desc_819x_usb *desc = (rx_desc_819x_usb *)skb->data;
5701 // rx_drvinfo_819x_usb *driver_info;
5704 //Get Rx Descriptor Information
5706 stats->virtual_address = (u8*)skb->data;
5707 stats->Length = desc->Length;
5708 stats->RxDrvInfoSize = 0;
5709 stats->RxBufShift = 0;
5710 stats->packetlength = stats->Length-scrclng;
5711 stats->fraglength = stats->packetlength;
5712 stats->fragoffset = 0;
5713 stats->ntotalfrag = 1;
5717 void rtl8192_rx_cmd(struct sk_buff *skb)
5719 struct rtl8192_rx_info *info = (struct rtl8192_rx_info *)skb->cb;
5720 struct net_device *dev = info->dev;
5722 // struct urb *rx_urb = info->urb;
5724 struct ieee80211_rx_stats stats = {
5728 // .mac_time = jiffies,
5729 .freq = IEEE80211_24GHZ_BAND,
5732 if((skb->len >=(20 + sizeof(rx_desc_819x_usb))) && (skb->len < RX_URB_SIZE))
5735 query_rx_cmdpkt_desc_status(skb,&stats);
5736 // this is to be done by amy 080508 prfd->queue_id = 1;
5740 // Process the command packet received.
5743 rtl819xusb_process_received_packet(dev,&stats);
5745 dev_kfree_skb_any(skb);
5753 void rtl8192_irq_rx_tasklet(struct r8192_priv *priv)
5755 struct sk_buff *skb;
5756 struct rtl8192_rx_info *info;
5758 while (NULL != (skb = skb_dequeue(&priv->skb_queue))) {
5759 info = (struct rtl8192_rx_info *)skb->cb;
5760 switch (info->out_pipe) {
5761 /* Nomal packet pipe */
5763 //RT_TRACE(COMP_RECV, "normal in-pipe index(%d)\n",info->out_pipe);
5764 priv->IrpPendingCount--;
5765 rtl8192_rx_nomal(skb);
5768 /* Command packet pipe */
5770 RT_TRACE(COMP_RECV, "command in-pipe index(%d)\n",\
5773 rtl8192_rx_cmd(skb);
5776 default: /* should never get here! */
5777 RT_TRACE(COMP_ERR, "Unknown in-pipe index(%d)\n",\
5786 static const struct net_device_ops rtl8192_netdev_ops = {
5787 .ndo_open = rtl8192_open,
5788 .ndo_stop = rtl8192_close,
5789 .ndo_get_stats = rtl8192_stats,
5790 .ndo_tx_timeout = tx_timeout,
5791 .ndo_do_ioctl = rtl8192_ioctl,
5792 .ndo_set_multicast_list = r8192_set_multicast,
5793 .ndo_set_mac_address = r8192_set_mac_adr,
5794 .ndo_validate_addr = eth_validate_addr,
5795 .ndo_change_mtu = eth_change_mtu,
5796 .ndo_start_xmit = ieee80211_xmit,
5800 /****************************************************************************
5801 ---------------------------- USB_STUFF---------------------------
5802 *****************************************************************************/
5804 static int __devinit rtl8192_usb_probe(struct usb_interface *intf,
5805 const struct usb_device_id *id)
5807 // unsigned long ioaddr = 0;
5808 struct net_device *dev = NULL;
5809 struct r8192_priv *priv= NULL;
5810 struct usb_device *udev = interface_to_usbdev(intf);
5811 RT_TRACE(COMP_INIT, "Oops: i'm coming\n");
5813 dev = alloc_ieee80211(sizeof(struct r8192_priv));
5816 usb_set_intfdata(intf, dev);
5817 SET_NETDEV_DEV(dev, &intf->dev);
5818 priv = ieee80211_priv(dev);
5819 priv->ieee80211 = netdev_priv(dev);
5822 dev->netdev_ops = &rtl8192_netdev_ops;
5824 //DMESG("Oops: i'm coming\n");
5825 #if WIRELESS_EXT >= 12
5826 #if WIRELESS_EXT < 17
5827 dev->get_wireless_stats = r8192_get_wireless_stats;
5829 dev->wireless_handlers = (struct iw_handler_def *) &r8192_wx_handlers_def;
5831 dev->type=ARPHRD_ETHER;
5833 dev->watchdog_timeo = HZ*3; //modified by john, 0805
5835 if (dev_alloc_name(dev, ifname) < 0){
5836 RT_TRACE(COMP_INIT, "Oops: devname already taken! Trying wlan%%d...\n");
5838 dev_alloc_name(dev, ifname);
5841 RT_TRACE(COMP_INIT, "Driver probe completed1\n");
5842 if(rtl8192_init(dev)!=0){
5843 RT_TRACE(COMP_ERR, "Initialization failed");
5846 netif_carrier_off(dev);
5847 netif_stop_queue(dev);
5849 register_netdev(dev);
5850 RT_TRACE(COMP_INIT, "dev name=======> %s\n",dev->name);
5851 rtl8192_proc_init_one(dev);
5854 RT_TRACE(COMP_INIT, "Driver probe completed\n");
5859 free_ieee80211(dev);
5861 RT_TRACE(COMP_ERR, "wlan driver load failed\n");
5866 //detach all the work and timer structure declared or inititialize in r8192U_init function.
5867 void rtl8192_cancel_deferred_work(struct r8192_priv* priv)
5870 cancel_work_sync(&priv->reset_wq);
5871 cancel_delayed_work(&priv->watch_dog_wq);
5872 cancel_delayed_work(&priv->update_beacon_wq);
5873 cancel_work_sync(&priv->qos_activate);
5874 //cancel_work_sync(&priv->SetBWModeWorkItem);
5875 //cancel_work_sync(&priv->SwChnlWorkItem);
5880 static void __devexit rtl8192_usb_disconnect(struct usb_interface *intf)
5882 struct net_device *dev = usb_get_intfdata(intf);
5884 struct r8192_priv *priv = ieee80211_priv(dev);
5887 unregister_netdev(dev);
5889 RT_TRACE(COMP_DOWN, "=============>wlan driver to be removed\n");
5890 rtl8192_proc_remove_one(dev);
5893 if (priv->pFirmware)
5895 kfree(priv->pFirmware);
5896 priv->pFirmware = NULL;
5898 // priv->rf_close(dev);
5899 // rtl8192_SetRFPowerState(dev, eRfOff);
5900 rtl8192_usb_deleteendpoints(dev);
5901 destroy_workqueue(priv->priv_wq);
5902 //rtl8192_irq_disable(dev);
5903 //rtl8192_reset(dev);
5907 free_ieee80211(dev);
5908 RT_TRACE(COMP_DOWN, "wlan driver removed\n");
5911 /* fun with the built-in ieee80211 stack... */
5912 extern int ieee80211_debug_init(void);
5913 extern void ieee80211_debug_exit(void);
5914 extern int ieee80211_crypto_init(void);
5915 extern void ieee80211_crypto_deinit(void);
5916 extern int ieee80211_crypto_tkip_init(void);
5917 extern void ieee80211_crypto_tkip_exit(void);
5918 extern int ieee80211_crypto_ccmp_init(void);
5919 extern void ieee80211_crypto_ccmp_exit(void);
5920 extern int ieee80211_crypto_wep_init(void);
5921 extern void ieee80211_crypto_wep_exit(void);
5923 static int __init rtl8192_usb_module_init(void)
5927 #ifdef CONFIG_IEEE80211_DEBUG
5928 ret = ieee80211_debug_init();
5930 printk(KERN_ERR "ieee80211_debug_init() failed %d\n", ret);
5934 ret = ieee80211_crypto_init();
5936 printk(KERN_ERR "ieee80211_crypto_init() failed %d\n", ret);
5940 ret = ieee80211_crypto_tkip_init();
5942 printk(KERN_ERR "ieee80211_crypto_tkip_init() failed %d\n",
5947 ret = ieee80211_crypto_ccmp_init();
5949 printk(KERN_ERR "ieee80211_crypto_ccmp_init() failed %d\n",
5954 ret = ieee80211_crypto_wep_init();
5956 printk(KERN_ERR "ieee80211_crypto_wep_init() failed %d\n", ret);
5960 printk(KERN_INFO "\nLinux kernel driver for RTL8192 based WLAN cards\n");
5961 printk(KERN_INFO "Copyright (c) 2007-2008, Realsil Wlan\n");
5962 RT_TRACE(COMP_INIT, "Initializing module");
5963 RT_TRACE(COMP_INIT, "Wireless extensions version %d", WIRELESS_EXT);
5964 rtl8192_proc_module_init();
5965 return usb_register(&rtl8192_usb_driver);
5969 static void __exit rtl8192_usb_module_exit(void)
5971 usb_deregister(&rtl8192_usb_driver);
5973 RT_TRACE(COMP_DOWN, "Exiting");
5974 // rtl8192_proc_module_remove();
5978 void rtl8192_try_wake_queue(struct net_device *dev, int pri)
5980 unsigned long flags;
5982 struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
5984 spin_lock_irqsave(&priv->tx_lock,flags);
5985 enough_desc = check_nic_enough_desc(dev,pri);
5986 spin_unlock_irqrestore(&priv->tx_lock,flags);
5989 ieee80211_wake_queue(priv->ieee80211);
5992 void EnableHWSecurityConfig8192(struct net_device *dev)
5994 u8 SECR_value = 0x0;
5995 struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
5996 struct ieee80211_device* ieee = priv->ieee80211;
5997 SECR_value = SCR_TxEncEnable | SCR_RxDecEnable;
5998 if (((KEY_TYPE_WEP40 == ieee->pairwise_key_type) || (KEY_TYPE_WEP104 == ieee->pairwise_key_type)) && (priv->ieee80211->auth_mode != 2))
6000 SECR_value |= SCR_RxUseDK;
6001 SECR_value |= SCR_TxUseDK;
6003 else if ((ieee->iw_mode == IW_MODE_ADHOC) && (ieee->pairwise_key_type & (KEY_TYPE_CCMP | KEY_TYPE_TKIP)))
6005 SECR_value |= SCR_RxUseDK;
6006 SECR_value |= SCR_TxUseDK;
6008 //add HWSec active enable here.
6009 //default using hwsec. when peer AP is in N mode only and pairwise_key_type is none_aes(which HT_IOT_ACT_PURE_N_MODE indicates it), use software security. when peer AP is in b,g,n mode mixed and pairwise_key_type is none_aes, use g mode hw security. WB on 2008.7.4
6011 ieee->hwsec_active = 1;
6013 if ((ieee->pHTInfo->IOTAction&HT_IOT_ACT_PURE_N_MODE) || !hwwep)//!ieee->hwsec_support) //add hwsec_support flag to totol control hw_sec on/off
6015 ieee->hwsec_active = 0;
6016 SECR_value &= ~SCR_RxDecEnable;
6018 RT_TRACE(COMP_SEC,"%s:, hwsec:%d, pairwise_key:%d, SECR_value:%x\n", __FUNCTION__, \
6019 ieee->hwsec_active, ieee->pairwise_key_type, SECR_value);
6021 write_nic_byte(dev, SECR, SECR_value);//SECR_value | SCR_UseDK );
6026 void setKey( struct net_device *dev,
6034 u32 TargetCommand = 0;
6035 u32 TargetContent = 0;
6038 if (EntryNo >= TOTAL_CAM_ENTRY)
6039 RT_TRACE(COMP_ERR, "cam entry exceeds in setKey()\n");
6041 RT_TRACE(COMP_SEC, "====>to setKey(), dev:%p, EntryNo:%d, KeyIndex:%d, KeyType:%d, MacAddr%pM\n", dev,EntryNo, KeyIndex, KeyType, MacAddr);
6044 usConfig |= BIT15 | (KeyType<<2);
6046 usConfig |= BIT15 | (KeyType<<2) | KeyIndex;
6047 // usConfig |= BIT15 | (KeyType<<2) | (DefaultKey<<5) | KeyIndex;
6050 for(i=0 ; i<CAM_CONTENT_COUNT; i++){
6051 TargetCommand = i+CAM_CONTENT_COUNT*EntryNo;
6052 TargetCommand |= BIT31|BIT16;
6054 if(i==0){//MAC|Config
6055 TargetContent = (u32)(*(MacAddr+0)) << 16|
6056 (u32)(*(MacAddr+1)) << 24|
6059 write_nic_dword(dev, WCAMI, TargetContent);
6060 write_nic_dword(dev, RWCAM, TargetCommand);
6061 // printk("setkey cam =%8x\n", read_cam(dev, i+6*EntryNo));
6064 TargetContent = (u32)(*(MacAddr+2)) |
6065 (u32)(*(MacAddr+3)) << 8|
6066 (u32)(*(MacAddr+4)) << 16|
6067 (u32)(*(MacAddr+5)) << 24;
6068 write_nic_dword(dev, WCAMI, TargetContent);
6069 write_nic_dword(dev, RWCAM, TargetCommand);
6073 if(KeyContent !=NULL){
6074 write_nic_dword(dev, WCAMI, (u32)(*(KeyContent+i-2)) );
6075 write_nic_dword(dev, RWCAM, TargetCommand);
6082 /***************************************************************************
6083 ------------------- module init / exit stubs ----------------
6084 ****************************************************************************/
6085 module_init(rtl8192_usb_module_init);
6086 module_exit(rtl8192_usb_module_exit);