Version:  2.0.40 2.2.26 2.4.37 2.6.39 3.0 3.1 3.2 3.3 3.4 3.5 3.6 3.7 3.8 3.9 3.10 3.11 3.12 3.13 3.14 3.15

Linux/drivers/staging/rtl8192u/r8192U_core.c

  1 /******************************************************************************
  2  * Copyright(c) 2008 - 2010 Realtek Corporation. All rights reserved.
  3  * Linux device driver for RTL8192U
  4  *
  5  * Based on the r8187 driver, which is:
  6  * Copyright 2004-2005 Andrea Merello <andrea.merello@gmail.com>, 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.
 10  *
 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
 14  * more details.
 15  *
 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
 19  *
 20  * The full GNU General Public License is included in this distribution in the
 21  * file called LICENSE.
 22  *
 23  * Contact Information:
 24  * Jerry chuang <wlanfae@realtek.com>
 25  */
 26 
 27 #ifndef CONFIG_FORCE_HARD_FLOAT
 28 double __floatsidf(int i)
 29 {
 30         return i;
 31 }
 32 
 33 unsigned int __fixunsdfsi(double d)
 34 {
 35         return d;
 36 }
 37 
 38 double __adddf3(double a, double b)
 39 {
 40         return a+b;
 41 }
 42 
 43 double __addsf3(float a, float b)
 44 {
 45         return a+b;
 46 }
 47 
 48 double __subdf3(double a, double b)
 49 {
 50         return a-b;
 51 }
 52 
 53 double __extendsfdf2(float a)
 54 {
 55         return a;
 56 }
 57 #endif
 58 
 59 #undef LOOP_TEST
 60 #undef DUMP_RX
 61 #undef DUMP_TX
 62 #undef DEBUG_TX_DESC2
 63 #undef RX_DONT_PASS_UL
 64 #undef DEBUG_EPROM
 65 #undef DEBUG_RX_VERBOSE
 66 #undef DUMMY_RX
 67 #undef DEBUG_ZERO_RX
 68 #undef DEBUG_RX_SKB
 69 #undef DEBUG_TX_FRAG
 70 #undef DEBUG_RX_FRAG
 71 #undef DEBUG_TX_FILLDESC
 72 #undef DEBUG_TX
 73 #undef DEBUG_IRQ
 74 #undef DEBUG_RX
 75 #undef DEBUG_RXALLOC
 76 #undef DEBUG_REGISTERS
 77 #undef DEBUG_RING
 78 #undef DEBUG_IRQ_TASKLET
 79 #undef DEBUG_TX_ALLOC
 80 #undef DEBUG_TX_DESC
 81 
 82 #define CONFIG_RTL8192_IO_MAP
 83 
 84 #include <asm/uaccess.h>
 85 #include "r8192U_hw.h"
 86 #include "r8192U.h"
 87 #include "r8190_rtl8256.h" /* RTL8225 Radio frontend */
 88 #include "r8180_93cx6.h"   /* Card EEPROM */
 89 #include "r8192U_wx.h"
 90 #include "r819xU_phy.h" //added by WB 4.30.2008
 91 #include "r819xU_phyreg.h"
 92 #include "r819xU_cmdpkt.h"
 93 #include "r8192U_dm.h"
 94 #include <linux/usb.h>
 95 #include <linux/slab.h>
 96 #include <linux/proc_fs.h>
 97 #include <linux/seq_file.h>
 98 // FIXME: check if 2.6.7 is ok
 99 
100 #ifdef CONFIG_RTL8192_PM
101 #include "r8192_pm.h"
102 #endif
103 
104 #include "dot11d.h"
105 //set here to open your trace code. //WB
106 u32 rt_global_debug_component = COMP_DOWN       |
107                                 COMP_SEC        |
108                                 COMP_ERR; //always open err flags on
109 
110 #define TOTAL_CAM_ENTRY 32
111 #define CAM_CONTENT_COUNT 8
112 
113 static const struct usb_device_id rtl8192_usb_id_tbl[] = {
114         /* Realtek */
115         {USB_DEVICE(0x0bda, 0x8709)},
116         /* Corega */
117         {USB_DEVICE(0x07aa, 0x0043)},
118         /* Belkin */
119         {USB_DEVICE(0x050d, 0x805E)},
120         /* Sitecom */
121         {USB_DEVICE(0x0df6, 0x0031)},
122         /* EnGenius */
123         {USB_DEVICE(0x1740, 0x9201)},
124         /* Dlink */
125         {USB_DEVICE(0x2001, 0x3301)},
126         /* Zinwell */
127         {USB_DEVICE(0x5a57, 0x0290)},
128         /* LG */
129         {USB_DEVICE(0x043e, 0x7a01)},
130         {}
131 };
132 
133 MODULE_LICENSE("GPL");
134 MODULE_VERSION("V 1.1");
135 MODULE_DEVICE_TABLE(usb, rtl8192_usb_id_tbl);
136 MODULE_DESCRIPTION("Linux driver for Realtek RTL8192 USB WiFi cards");
137 
138 static char *ifname = "wlan%d";
139 static int hwwep = 1;  //default use hw. set 0 to use software security
140 static int channels = 0x3fff;
141 
142 
143 
144 module_param(ifname, charp, S_IRUGO|S_IWUSR);
145 module_param(hwwep, int, S_IRUGO|S_IWUSR);
146 module_param(channels, int, S_IRUGO|S_IWUSR);
147 
148 MODULE_PARM_DESC(ifname, " Net interface name, wlan%d=default");
149 MODULE_PARM_DESC(hwwep, " Try to use hardware security support. ");
150 MODULE_PARM_DESC(channels, " Channel bitmask for specific locales. NYI");
151 
152 static int rtl8192_usb_probe(struct usb_interface *intf,
153                              const struct usb_device_id *id);
154 static void rtl8192_usb_disconnect(struct usb_interface *intf);
155 
156 
157 static struct usb_driver rtl8192_usb_driver = {
158         .name           = RTL819xU_MODULE_NAME,           /* Driver name   */
159         .id_table       = rtl8192_usb_id_tbl,             /* PCI_ID table  */
160         .probe          = rtl8192_usb_probe,              /* probe fn      */
161         .disconnect     = rtl8192_usb_disconnect,         /* remove fn     */
162 #ifdef CONFIG_RTL8192_PM
163         .suspend        = rtl8192_suspend,                /* PM suspend fn */
164         .resume         = rtl8192_resume,                 /* PM resume fn  */
165 #else
166         .suspend        = NULL,                           /* PM suspend fn */
167         .resume         = NULL,                           /* PM resume fn  */
168 #endif
169 };
170 
171 
172 typedef struct _CHANNEL_LIST {
173         u8      Channel[32];
174         u8      Len;
175 } CHANNEL_LIST, *PCHANNEL_LIST;
176 
177 static CHANNEL_LIST ChannelPlan[] = {
178         {{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
179         {{1,2,3,4,5,6,7,8,9,10,11},11},                                                 //IC
180         {{1,2,3,4,5,6,7,8,9,10,11,12,13,36,40,44,48,52,56,60,64},21},   //ETSI
181         {{1,2,3,4,5,6,7,8,9,10,11,12,13},13},    //Spain. Change to ETSI.
182         {{1,2,3,4,5,6,7,8,9,10,11,12,13},13},   //France. Change to ETSI.
183         {{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
184         {{1,2,3,4,5,6,7,8,9,10,11,12,13,14,36,40,44,48,52,56,60,64},22},//MKK1
185         {{1,2,3,4,5,6,7,8,9,10,11,12,13},13},   //Israel.
186         {{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
187         {{1,2,3,4,5,6,7,8,9,10,11,12,13,14,36,40,44,48,52,56,60,64}, 22},    //MIC
188         {{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 };
190 
191 static void rtl819x_set_channel_map(u8 channel_plan, struct r8192_priv *priv)
192 {
193         int i, max_chan = -1, min_chan = -1;
194         struct ieee80211_device *ieee = priv->ieee80211;
195         switch (channel_plan) {
196         case COUNTRY_CODE_FCC:
197         case COUNTRY_CODE_IC:
198         case COUNTRY_CODE_ETSI:
199         case COUNTRY_CODE_SPAIN:
200         case COUNTRY_CODE_FRANCE:
201         case COUNTRY_CODE_MKK:
202         case COUNTRY_CODE_MKK1:
203         case COUNTRY_CODE_ISRAEL:
204         case COUNTRY_CODE_TELEC:
205         case COUNTRY_CODE_MIC:
206                 Dot11d_Init(ieee);
207                 ieee->bGlobalDomain = false;
208                 //actually 8225 & 8256 rf chips only support B,G,24N mode
209                 if ((priv->rf_chip == RF_8225) || (priv->rf_chip == RF_8256)) {
210                         min_chan = 1;
211                         max_chan = 14;
212                 } else {
213                         RT_TRACE(COMP_ERR, "unknown rf chip, can't set channel map in function:%s()\n", __func__);
214                 }
215                 if (ChannelPlan[channel_plan].Len != 0) {
216                         // Clear old channel map
217                         memset(GET_DOT11D_INFO(ieee)->channel_map, 0, sizeof(GET_DOT11D_INFO(ieee)->channel_map));
218                         // Set new channel map
219                         for (i = 0; i < ChannelPlan[channel_plan].Len; i++) {
220                                 if (ChannelPlan[channel_plan].Channel[i] < min_chan || ChannelPlan[channel_plan].Channel[i] > max_chan)
221                                         break;
222                                 GET_DOT11D_INFO(ieee)->channel_map[ChannelPlan[channel_plan].Channel[i]] = 1;
223                         }
224                 }
225                 break;
226 
227         case COUNTRY_CODE_GLOBAL_DOMAIN:
228                 GET_DOT11D_INFO(ieee)->bEnabled = 0;//this flag enabled to follow 11d country IE setting, otherwise, it shall follow global domain settings.
229                 Dot11d_Reset(ieee);
230                 ieee->bGlobalDomain = true;
231                 break;
232 
233         default:
234                 break;
235         }
236 }
237 
238 
239 
240 
241 static void CamResetAllEntry(struct net_device *dev)
242 {
243         u32 ulcommand = 0;
244         //2004/02/11  In static WEP, OID_ADD_KEY or OID_ADD_WEP are set before STA associate to AP.
245         // However, ResetKey is called on OID_802_11_INFRASTRUCTURE_MODE and MlmeAssociateRequest
246         // In this condition, Cam can not be reset because upper layer will not set this static key again.
247         ulcommand |= BIT31|BIT30;
248         write_nic_dword(dev, RWCAM, ulcommand);
249 
250 }
251 
252 
253 void write_cam(struct net_device *dev, u8 addr, u32 data)
254 {
255         write_nic_dword(dev, WCAMI, data);
256         write_nic_dword(dev, RWCAM, BIT31|BIT16|(addr&0xff));
257 }
258 
259 u32 read_cam(struct net_device *dev, u8 addr)
260 {
261         u32 data;
262 
263         write_nic_dword(dev, RWCAM, 0x80000000|(addr&0xff));
264         read_nic_dword(dev, 0xa8, &data);
265         return data;
266 }
267 
268 void write_nic_byte_E(struct net_device *dev, int indx, u8 data)
269 {
270         int status;
271         struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
272         struct usb_device *udev = priv->udev;
273 
274         status = usb_control_msg(udev, usb_sndctrlpipe(udev, 0),
275                                  RTL8187_REQ_SET_REGS, RTL8187_REQT_WRITE,
276                                  indx|0xfe00, 0, &data, 1, HZ / 2);
277 
278         if (status < 0)
279                 netdev_err(dev, "write_nic_byte_E TimeOut! status: %d\n", status);
280 }
281 
282 int read_nic_byte_E(struct net_device *dev, int indx, u8 *data)
283 {
284         int status;
285         struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
286         struct usb_device *udev = priv->udev;
287 
288         status = usb_control_msg(udev, usb_rcvctrlpipe(udev, 0),
289                                  RTL8187_REQ_GET_REGS, RTL8187_REQT_READ,
290                                  indx|0xfe00, 0, data, 1, HZ / 2);
291 
292         if (status < 0) {
293                 netdev_err(dev, "%s failure status: %d\n", __func__, status);
294                 return status;
295         }
296 
297         return 0;
298 }
299 //as 92U has extend page from 4 to 16, so modify functions below.
300 void write_nic_byte(struct net_device *dev, int indx, u8 data)
301 {
302         int status;
303 
304         struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
305         struct usb_device *udev = priv->udev;
306 
307         status = usb_control_msg(udev, usb_sndctrlpipe(udev, 0),
308                                  RTL8187_REQ_SET_REGS, RTL8187_REQT_WRITE,
309                                  (indx&0xff)|0xff00, (indx>>8)&0x0f, &data, 1, HZ / 2);
310 
311         if (status < 0)
312                 netdev_err(dev, "write_nic_byte TimeOut! status: %d\n", status);
313 
314 
315 }
316 
317 
318 void write_nic_word(struct net_device *dev, int indx, u16 data)
319 {
320 
321         int status;
322 
323         struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
324         struct usb_device *udev = priv->udev;
325 
326         status = usb_control_msg(udev, usb_sndctrlpipe(udev, 0),
327                                  RTL8187_REQ_SET_REGS, RTL8187_REQT_WRITE,
328                                  (indx&0xff)|0xff00, (indx>>8)&0x0f, &data, 2, HZ / 2);
329 
330         if (status < 0)
331                 netdev_err(dev, "write_nic_word TimeOut! status: %d\n", status);
332 
333 }
334 
335 
336 void write_nic_dword(struct net_device *dev, int indx, u32 data)
337 {
338 
339         int status;
340 
341         struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
342         struct usb_device *udev = priv->udev;
343 
344         status = usb_control_msg(udev, usb_sndctrlpipe(udev, 0),
345                                  RTL8187_REQ_SET_REGS, RTL8187_REQT_WRITE,
346                                  (indx&0xff)|0xff00, (indx>>8)&0x0f, &data, 4, HZ / 2);
347 
348 
349         if (status < 0)
350                 netdev_err(dev, "write_nic_dword TimeOut! status: %d\n", status);
351 
352 }
353 
354 
355 
356 int read_nic_byte(struct net_device *dev, int indx, u8 *data)
357 {
358         int status;
359         struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
360         struct usb_device *udev = priv->udev;
361 
362         status = usb_control_msg(udev, usb_rcvctrlpipe(udev, 0),
363                                  RTL8187_REQ_GET_REGS, RTL8187_REQT_READ,
364                                  (indx&0xff)|0xff00, (indx>>8)&0x0f, data, 1, HZ / 2);
365 
366         if (status < 0) {
367                 netdev_err(dev, "%s failure status: %d\n", __func__, status);
368                 return status;
369         }
370 
371         return 0;
372 }
373 
374 
375 
376 int read_nic_word(struct net_device *dev, int indx, u16 *data)
377 {
378         int status;
379         struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
380         struct usb_device *udev = priv->udev;
381 
382         status = usb_control_msg(udev, usb_rcvctrlpipe(udev, 0),
383                                  RTL8187_REQ_GET_REGS, RTL8187_REQT_READ,
384                                  (indx&0xff)|0xff00, (indx>>8)&0x0f,
385                                  data, 2, HZ / 2);
386 
387         if (status < 0) {
388                 netdev_err(dev, "%s failure status: %d\n", __func__, status);
389                 return status;
390         }
391 
392         return 0;
393 }
394 
395 static int read_nic_word_E(struct net_device *dev, int indx, u16 *data)
396 {
397         int status;
398         struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
399         struct usb_device *udev = priv->udev;
400 
401         status = usb_control_msg(udev, usb_rcvctrlpipe(udev, 0),
402                                  RTL8187_REQ_GET_REGS, RTL8187_REQT_READ,
403                                  indx|0xfe00, 0, data, 2, HZ / 2);
404 
405         if (status < 0) {
406                 netdev_err(dev, "%s failure status: %d\n", __func__, status);
407                 return status;
408         }
409 
410         return 0;
411 }
412 
413 int read_nic_dword(struct net_device *dev, int indx, u32 *data)
414 {
415         int status;
416 
417         struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
418         struct usb_device *udev = priv->udev;
419 
420         status = usb_control_msg(udev, usb_rcvctrlpipe(udev, 0),
421                                  RTL8187_REQ_GET_REGS, RTL8187_REQT_READ,
422                                  (indx&0xff)|0xff00, (indx>>8)&0x0f,
423                                  data, 4, HZ / 2);
424 
425         if (status < 0) {
426                 netdev_err(dev, "%s failure status: %d\n", __func__, status);
427                 return status;
428         }
429 
430         return 0;
431 }
432 
433 /* u8 read_phy_cck(struct net_device *dev, u8 adr); */
434 /* u8 read_phy_ofdm(struct net_device *dev, u8 adr); */
435 /* this might still called in what was the PHY rtl8185/rtl8192 common code
436  * plans are to possibility turn it again in one common code...
437  */
438 inline void force_pci_posting(struct net_device *dev)
439 {
440 }
441 
442 static struct net_device_stats *rtl8192_stats(struct net_device *dev);
443 void rtl8192_commit(struct net_device *dev);
444 void rtl8192_restart(struct work_struct *work);
445 void watch_dog_timer_callback(unsigned long data);
446 
447 /****************************************************************************
448  *   -----------------------------PROCFS STUFF-------------------------
449 *****************************************************************************
450  */
451 
452 static struct proc_dir_entry *rtl8192_proc;
453 
454 static int proc_get_stats_ap(struct seq_file *m, void *v)
455 {
456         struct net_device *dev = m->private;
457         struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
458         struct ieee80211_device *ieee = priv->ieee80211;
459         struct ieee80211_network *target;
460 
461         list_for_each_entry(target, &ieee->network_list, list) {
462                 const char *wpa = "non_WPA";
463                 if (target->wpa_ie_len > 0 || target->rsn_ie_len > 0)
464                         wpa = "WPA";
465 
466                 seq_printf(m, "%s %s\n", target->ssid, wpa);
467         }
468 
469         return 0;
470 }
471 
472 static int proc_get_registers(struct seq_file *m, void *v)
473 {
474         struct net_device *dev = m->private;
475         int i, n, max = 0xff;
476         u8 byte_rd;
477 
478         seq_puts(m, "\n####################page 0##################\n ");
479 
480         for (n = 0; n <= max;) {
481                 seq_printf(m, "\nD:  %2x > ", n);
482 
483                 for (i = 0; i < 16 && n <= max; i++, n++) {
484                         read_nic_byte(dev, 0x000|n, &byte_rd);
485                         seq_printf(m, "%2x ", byte_rd);
486                 }
487         }
488 
489         seq_puts(m, "\n####################page 1##################\n ");
490         for (n = 0; n <= max;) {
491                 seq_printf(m, "\nD:  %2x > ", n);
492 
493                 for (i = 0; i < 16 && n <= max; i++, n++) {
494                         read_nic_byte(dev, 0x100|n, &byte_rd);
495                         seq_printf(m, "%2x ", byte_rd);
496                 }
497         }
498 
499         seq_puts(m, "\n####################page 3##################\n ");
500         for (n = 0; n <= max;) {
501                 seq_printf(m, "\nD:  %2x > ", n);
502 
503                 for (i = 0; i < 16 && n <= max; i++, n++) {
504                         read_nic_byte(dev, 0x300|n, &byte_rd);
505                         seq_printf(m, "%2x ", byte_rd);
506                 }
507         }
508 
509         seq_putc(m, '\n');
510         return 0;
511 }
512 
513 static int proc_get_stats_tx(struct seq_file *m, void *v)
514 {
515         struct net_device *dev = m->private;
516         struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
517 
518         seq_printf(m,
519                    "TX VI priority ok int: %lu\n"
520                    "TX VI priority error int: %lu\n"
521                    "TX VO priority ok int: %lu\n"
522                    "TX VO priority error int: %lu\n"
523                    "TX BE priority ok int: %lu\n"
524                    "TX BE priority error int: %lu\n"
525                    "TX BK priority ok int: %lu\n"
526                    "TX BK priority error int: %lu\n"
527                    "TX MANAGE priority ok int: %lu\n"
528                    "TX MANAGE priority error int: %lu\n"
529                    "TX BEACON priority ok int: %lu\n"
530                    "TX BEACON priority error int: %lu\n"
531                    "TX queue resume: %lu\n"
532                    "TX queue stopped?: %d\n"
533                    "TX fifo overflow: %lu\n"
534                    "TX VI queue: %d\n"
535                    "TX VO queue: %d\n"
536                    "TX BE queue: %d\n"
537                    "TX BK queue: %d\n"
538                    "TX VI dropped: %lu\n"
539                    "TX VO dropped: %lu\n"
540                    "TX BE dropped: %lu\n"
541                    "TX BK dropped: %lu\n"
542                    "TX total data packets %lu\n",
543                    priv->stats.txviokint,
544                    priv->stats.txvierr,
545                    priv->stats.txvookint,
546                    priv->stats.txvoerr,
547                    priv->stats.txbeokint,
548                    priv->stats.txbeerr,
549                    priv->stats.txbkokint,
550                    priv->stats.txbkerr,
551                    priv->stats.txmanageokint,
552                    priv->stats.txmanageerr,
553                    priv->stats.txbeaconokint,
554                    priv->stats.txbeaconerr,
555                    priv->stats.txresumed,
556                    netif_queue_stopped(dev),
557                    priv->stats.txoverflow,
558                    atomic_read(&(priv->tx_pending[VI_PRIORITY])),
559                    atomic_read(&(priv->tx_pending[VO_PRIORITY])),
560                    atomic_read(&(priv->tx_pending[BE_PRIORITY])),
561                    atomic_read(&(priv->tx_pending[BK_PRIORITY])),
562                    priv->stats.txvidrop,
563                    priv->stats.txvodrop,
564                    priv->stats.txbedrop,
565                    priv->stats.txbkdrop,
566                    priv->stats.txdatapkt
567                 );
568 
569         return 0;
570 }
571 
572 static int proc_get_stats_rx(struct seq_file *m, void *v)
573 {
574         struct net_device *dev = m->private;
575         struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
576 
577         seq_printf(m,
578                    "RX packets: %lu\n"
579                    "RX urb status error: %lu\n"
580                    "RX invalid urb error: %lu\n",
581                    priv->stats.rxoktotal,
582                    priv->stats.rxstaterr,
583                    priv->stats.rxurberr);
584 
585         return 0;
586 }
587 
588 static void rtl8192_proc_module_init(void)
589 {
590         RT_TRACE(COMP_INIT, "Initializing proc filesystem");
591         rtl8192_proc = proc_mkdir(RTL819xU_MODULE_NAME, init_net.proc_net);
592 }
593 
594 /*
595  * seq_file wrappers for procfile show routines.
596  */
597 static int rtl8192_proc_open(struct inode *inode, struct file *file)
598 {
599         struct net_device *dev = proc_get_parent_data(inode);
600         int (*show)(struct seq_file *, void *) = PDE_DATA(inode);
601 
602         return single_open(file, show, dev);
603 }
604 
605 static const struct file_operations rtl8192_proc_fops = {
606         .open           = rtl8192_proc_open,
607         .read           = seq_read,
608         .llseek         = seq_lseek,
609         .release        = single_release,
610 };
611 
612 /*
613  * Table of proc files we need to create.
614  */
615 struct rtl8192_proc_file {
616         char name[12];
617         int (*show)(struct seq_file *, void *);
618 };
619 
620 static const struct rtl8192_proc_file rtl8192_proc_files[] = {
621         { "stats-rx",   &proc_get_stats_rx },
622         { "stats-tx",   &proc_get_stats_tx },
623         { "stats-ap",   &proc_get_stats_ap },
624         { "registers",  &proc_get_registers },
625         { "" }
626 };
627 
628 static void rtl8192_proc_init_one(struct net_device *dev)
629 {
630         const struct rtl8192_proc_file *f;
631         struct proc_dir_entry *dir;
632 
633         if (rtl8192_proc) {
634                 dir = proc_mkdir_data(dev->name, 0, rtl8192_proc, dev);
635                 if (!dir) {
636                         RT_TRACE(COMP_ERR, "Unable to initialize /proc/net/rtl8192/%s\n",
637                                  dev->name);
638                         return;
639                 }
640 
641                 for (f = rtl8192_proc_files; f->name[0]; f++) {
642                         if (!proc_create_data(f->name, S_IFREG | S_IRUGO, dir,
643                                               &rtl8192_proc_fops, f->show)) {
644                                 RT_TRACE(COMP_ERR, "Unable to initialize "
645                                          "/proc/net/rtl8192/%s/%s\n",
646                                          dev->name, f->name);
647                                 return;
648                         }
649                 }
650         }
651 }
652 
653 static void rtl8192_proc_remove_one(struct net_device *dev)
654 {
655         remove_proc_subtree(dev->name, rtl8192_proc);
656 }
657 
658 /****************************************************************************
659    -----------------------------MISC STUFF-------------------------
660 *****************************************************************************/
661 
662 short check_nic_enough_desc(struct net_device *dev, int queue_index)
663 {
664         struct r8192_priv *priv = ieee80211_priv(dev);
665         int used = atomic_read(&priv->tx_pending[queue_index]);
666 
667         return (used < MAX_TX_URB);
668 }
669 
670 static void tx_timeout(struct net_device *dev)
671 {
672         struct r8192_priv *priv = ieee80211_priv(dev);
673 
674         schedule_work(&priv->reset_wq);
675 }
676 
677 
678 /* this is only for debug */
679 void dump_eprom(struct net_device *dev)
680 {
681         int i;
682         for (i = 0; i < 63; i++)
683                 RT_TRACE(COMP_EPROM, "EEPROM addr %x : %x", i, eprom_read(dev, i));
684 }
685 
686 void rtl8192_update_msr(struct net_device *dev)
687 {
688         struct r8192_priv *priv = ieee80211_priv(dev);
689         u8 msr;
690 
691         read_nic_byte(dev, MSR, &msr);
692         msr &= ~MSR_LINK_MASK;
693 
694         /* do not change in link_state != WLAN_LINK_ASSOCIATED.
695          * msr must be updated if the state is ASSOCIATING.
696          * this is intentional and make sense for ad-hoc and
697          * master (see the create BSS/IBSS func)
698          */
699         if (priv->ieee80211->state == IEEE80211_LINKED) {
700 
701                 if (priv->ieee80211->iw_mode == IW_MODE_INFRA)
702                         msr |= (MSR_LINK_MANAGED<<MSR_LINK_SHIFT);
703                 else if (priv->ieee80211->iw_mode == IW_MODE_ADHOC)
704                         msr |= (MSR_LINK_ADHOC<<MSR_LINK_SHIFT);
705                 else if (priv->ieee80211->iw_mode == IW_MODE_MASTER)
706                         msr |= (MSR_LINK_MASTER<<MSR_LINK_SHIFT);
707 
708         } else {
709                 msr |= (MSR_LINK_NONE<<MSR_LINK_SHIFT);
710         }
711 
712         write_nic_byte(dev, MSR, msr);
713 }
714 
715 void rtl8192_set_chan(struct net_device *dev, short ch)
716 {
717         struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
718         RT_TRACE(COMP_CH, "=====>%s()====ch:%d\n", __func__, ch);
719         priv->chan = ch;
720 
721         /* this hack should avoid frame TX during channel setting*/
722 
723 #ifndef LOOP_TEST
724         //need to implement rf set channel here WB
725 
726         if (priv->rf_set_chan)
727                 priv->rf_set_chan(dev, priv->chan);
728         mdelay(10);
729 #endif
730 }
731 
732 static void rtl8192_rx_isr(struct urb *urb);
733 
734 static u32 get_rxpacket_shiftbytes_819xusb(struct ieee80211_rx_stats *pstats)
735 {
736 
737 #ifdef USB_RX_AGGREGATION_SUPPORT
738         if (pstats->bisrxaggrsubframe)
739                 return (sizeof(rx_desc_819x_usb) + pstats->RxDrvInfoSize
740                         + pstats->RxBufShift + 8);
741         else
742 #endif
743                 return (sizeof(rx_desc_819x_usb) + pstats->RxDrvInfoSize
744                         + pstats->RxBufShift);
745 
746 }
747 static int rtl8192_rx_initiate(struct net_device *dev)
748 {
749         struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
750         struct urb *entry;
751         struct sk_buff *skb;
752         struct rtl8192_rx_info *info;
753 
754         /* nomal packet rx procedure */
755         while (skb_queue_len(&priv->rx_queue) < MAX_RX_URB) {
756                 skb = __dev_alloc_skb(RX_URB_SIZE, GFP_KERNEL);
757                 if (!skb)
758                         break;
759                 entry = usb_alloc_urb(0, GFP_KERNEL);
760                 if (!entry) {
761                         kfree_skb(skb);
762                         break;
763                 }
764                 usb_fill_bulk_urb(entry, priv->udev,
765                                   usb_rcvbulkpipe(priv->udev, 3), skb_tail_pointer(skb),
766                                   RX_URB_SIZE, rtl8192_rx_isr, skb);
767                 info = (struct rtl8192_rx_info *) skb->cb;
768                 info->urb = entry;
769                 info->dev = dev;
770                 info->out_pipe = 3; //denote rx normal packet queue
771                 skb_queue_tail(&priv->rx_queue, skb);
772                 usb_submit_urb(entry, GFP_KERNEL);
773         }
774 
775         /* command packet rx procedure */
776         while (skb_queue_len(&priv->rx_queue) < MAX_RX_URB + 3) {
777                 skb = __dev_alloc_skb(RX_URB_SIZE, GFP_KERNEL);
778                 if (!skb)
779                         break;
780                 entry = usb_alloc_urb(0, GFP_KERNEL);
781                 if (!entry) {
782                         kfree_skb(skb);
783                         break;
784                 }
785                 usb_fill_bulk_urb(entry, priv->udev,
786                                   usb_rcvbulkpipe(priv->udev, 9), skb_tail_pointer(skb),
787                                   RX_URB_SIZE, rtl8192_rx_isr, skb);
788                 info = (struct rtl8192_rx_info *) skb->cb;
789                 info->urb = entry;
790                 info->dev = dev;
791                 info->out_pipe = 9; //denote rx cmd packet queue
792                 skb_queue_tail(&priv->rx_queue, skb);
793                 usb_submit_urb(entry, GFP_KERNEL);
794         }
795 
796         return 0;
797 }
798 
799 void rtl8192_set_rxconf(struct net_device *dev)
800 {
801         struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
802         u32 rxconf;
803 
804         read_nic_dword(dev, RCR, &rxconf);
805         rxconf = rxconf & ~MAC_FILTER_MASK;
806         rxconf = rxconf | RCR_AMF;
807         rxconf = rxconf | RCR_ADF;
808         rxconf = rxconf | RCR_AB;
809         rxconf = rxconf | RCR_AM;
810 
811         if (dev->flags & IFF_PROMISC)
812                 DMESG("NIC in promisc mode");
813 
814         if (priv->ieee80211->iw_mode == IW_MODE_MONITOR ||
815             dev->flags & IFF_PROMISC) {
816                 rxconf = rxconf | RCR_AAP;
817         } else {
818                 rxconf = rxconf | RCR_APM;
819                 rxconf = rxconf | RCR_CBSSID;
820         }
821 
822 
823         if (priv->ieee80211->iw_mode == IW_MODE_MONITOR) {
824                 rxconf = rxconf | RCR_AICV;
825                 rxconf = rxconf | RCR_APWRMGT;
826         }
827 
828         if (priv->crcmon == 1 && priv->ieee80211->iw_mode == IW_MODE_MONITOR)
829                 rxconf = rxconf | RCR_ACRC32;
830 
831 
832         rxconf = rxconf & ~RX_FIFO_THRESHOLD_MASK;
833         rxconf = rxconf | (RX_FIFO_THRESHOLD_NONE<<RX_FIFO_THRESHOLD_SHIFT);
834         rxconf = rxconf & ~MAX_RX_DMA_MASK;
835         rxconf = rxconf | ((u32)7<<RCR_MXDMA_OFFSET);
836 
837         rxconf = rxconf | RCR_ONLYERLPKT;
838 
839         write_nic_dword(dev, RCR, rxconf);
840 }
841 //wait to be removed
842 void rtl8192_rx_enable(struct net_device *dev)
843 {
844         rtl8192_rx_initiate(dev);
845 }
846 
847 
848 void rtl8192_tx_enable(struct net_device *dev)
849 {
850 }
851 
852 
853 
854 void rtl8192_rtx_disable(struct net_device *dev)
855 {
856         u8 cmd;
857         struct r8192_priv *priv = ieee80211_priv(dev);
858         struct sk_buff *skb;
859         struct rtl8192_rx_info *info;
860 
861         read_nic_byte(dev, CMDR, &cmd);
862         write_nic_byte(dev, CMDR, cmd & ~(CR_TE|CR_RE));
863         force_pci_posting(dev);
864         mdelay(10);
865 
866         while ((skb = __skb_dequeue(&priv->rx_queue))) {
867                 info = (struct rtl8192_rx_info *) skb->cb;
868                 if (!info->urb)
869                         continue;
870 
871                 usb_kill_urb(info->urb);
872                 kfree_skb(skb);
873         }
874 
875         if (skb_queue_len(&priv->skb_queue))
876                 netdev_warn(dev, "skb_queue not empty\n");
877 
878         skb_queue_purge(&priv->skb_queue);
879         return;
880 }
881 
882 inline u16 ieeerate2rtlrate(int rate)
883 {
884         switch (rate) {
885         case 10:
886                 return 0;
887         case 20:
888                 return 1;
889         case 55:
890                 return 2;
891         case 110:
892                 return 3;
893         case 60:
894                 return 4;
895         case 90:
896                 return 5;
897         case 120:
898                 return 6;
899         case 180:
900                 return 7;
901         case 240:
902                 return 8;
903         case 360:
904                 return 9;
905         case 480:
906                 return 10;
907         case 540:
908                 return 11;
909         default:
910                 return 3;
911 
912         }
913 }
914 static u16 rtl_rate[] = {10, 20, 55, 110, 60, 90, 120, 180, 240, 360, 480, 540};
915 inline u16 rtl8192_rate2rate(short rate)
916 {
917         if (rate > 11) return 0;
918         return rtl_rate[rate];
919 }
920 
921 
922 /* The prototype of rx_isr has changed since one version of Linux Kernel */
923 static void rtl8192_rx_isr(struct urb *urb)
924 {
925         struct sk_buff *skb = (struct sk_buff *) urb->context;
926         struct rtl8192_rx_info *info = (struct rtl8192_rx_info *)skb->cb;
927         struct net_device *dev = info->dev;
928         struct r8192_priv *priv = ieee80211_priv(dev);
929         int out_pipe = info->out_pipe;
930         int err;
931         if (!priv->up)
932                 return;
933         if (unlikely(urb->status)) {
934                 info->urb = NULL;
935                 priv->stats.rxstaterr++;
936                 priv->ieee80211->stats.rx_errors++;
937                 usb_free_urb(urb);
938                 return;
939         }
940         skb_unlink(skb, &priv->rx_queue);
941         skb_put(skb, urb->actual_length);
942 
943         skb_queue_tail(&priv->skb_queue, skb);
944         tasklet_schedule(&priv->irq_rx_tasklet);
945 
946         skb = dev_alloc_skb(RX_URB_SIZE);
947         if (unlikely(!skb)) {
948                 usb_free_urb(urb);
949                 netdev_err(dev, "%s(): can't alloc skb\n", __func__);
950                 /* TODO check rx queue length and refill *somewhere* */
951                 return;
952         }
953 
954         usb_fill_bulk_urb(urb, priv->udev,
955                           usb_rcvbulkpipe(priv->udev, out_pipe), skb_tail_pointer(skb),
956                           RX_URB_SIZE, rtl8192_rx_isr, skb);
957 
958         info = (struct rtl8192_rx_info *) skb->cb;
959         info->urb = urb;
960         info->dev = dev;
961         info->out_pipe = out_pipe;
962 
963         urb->transfer_buffer = skb_tail_pointer(skb);
964         urb->context = skb;
965         skb_queue_tail(&priv->rx_queue, skb);
966         err = usb_submit_urb(urb, GFP_ATOMIC);
967         if (err && err != EPERM)
968                 netdev_err(dev, "can not submit rxurb, err is %x, URB status is %x\n", err, urb->status);
969 }
970 
971 static u32 rtl819xusb_rx_command_packet(struct net_device *dev,
972                                         struct ieee80211_rx_stats *pstats)
973 {
974         u32     status;
975 
976         status = cmpk_message_handle_rx(dev, pstats);
977         if (status)
978                 DMESG("rxcommandpackethandle819xusb: It is a command packet\n");
979 
980         return status;
981 }
982 
983 
984 static void rtl8192_data_hard_stop(struct net_device *dev)
985 {
986         //FIXME !!
987 }
988 
989 
990 static void rtl8192_data_hard_resume(struct net_device *dev)
991 {
992         // FIXME !!
993 }
994 
995 /* this function TX data frames when the ieee80211 stack requires this.
996  * It checks also if we need to stop the ieee tx queue, eventually do it
997  */
998 static void rtl8192_hard_data_xmit(struct sk_buff *skb, struct net_device *dev, int rate)
999 {
1000         struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
1001         int ret;
1002         unsigned long flags;
1003         cb_desc *tcb_desc = (cb_desc *)(skb->cb + MAX_DEV_ADDR_SIZE);
1004         u8 queue_index = tcb_desc->queue_index;
1005 
1006         /* shall not be referred by command packet */
1007         RTL8192U_ASSERT(queue_index != TXCMD_QUEUE);
1008 
1009         spin_lock_irqsave(&priv->tx_lock, flags);
1010 
1011         memcpy((unsigned char *)(skb->cb), &dev, sizeof(dev));
1012         tcb_desc->bTxEnableFwCalcDur = 1;
1013         skb_push(skb, priv->ieee80211->tx_headroom);
1014         ret = rtl8192_tx(dev, skb);
1015 
1016         spin_unlock_irqrestore(&priv->tx_lock, flags);
1017 
1018         return;
1019 }
1020 
1021 /* This is a rough attempt to TX a frame
1022  * This is called by the ieee 80211 stack to TX management frames.
1023  * If the ring is full packet are dropped (for data frame the queue
1024  * is stopped before this can happen).
1025  */
1026 static int rtl8192_hard_start_xmit(struct sk_buff *skb, struct net_device *dev)
1027 {
1028         struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
1029         int ret;
1030         unsigned long flags;
1031         cb_desc *tcb_desc = (cb_desc *)(skb->cb + MAX_DEV_ADDR_SIZE);
1032         u8 queue_index = tcb_desc->queue_index;
1033 
1034 
1035         spin_lock_irqsave(&priv->tx_lock, flags);
1036 
1037         memcpy((unsigned char *)(skb->cb), &dev, sizeof(dev));
1038         if (queue_index == TXCMD_QUEUE) {
1039                 skb_push(skb, USB_HWDESC_HEADER_LEN);
1040                 rtl819xU_tx_cmd(dev, skb);
1041                 ret = 1;
1042                 spin_unlock_irqrestore(&priv->tx_lock, flags);
1043                 return ret;
1044         } else {
1045                 skb_push(skb, priv->ieee80211->tx_headroom);
1046                 ret = rtl8192_tx(dev, skb);
1047         }
1048 
1049         spin_unlock_irqrestore(&priv->tx_lock, flags);
1050 
1051         return ret;
1052 }
1053 
1054 
1055 void rtl8192_try_wake_queue(struct net_device *dev, int pri);
1056 
1057 #ifdef USB_TX_DRIVER_AGGREGATION_ENABLE
1058 u16 DrvAggr_PaddingAdd(struct net_device *dev, struct sk_buff *skb)
1059 {
1060         u16     PaddingNum =  256 - ((skb->len + TX_PACKET_DRVAGGR_SUBFRAME_SHIFT_BYTES) % 256);
1061         return  PaddingNum & 0xff;
1062 }
1063 
1064 u8 MRateToHwRate8190Pci(u8 rate);
1065 u8 QueryIsShort(u8 TxHT, u8 TxRate, cb_desc *tcb_desc);
1066 u8 MapHwQueueToFirmwareQueue(u8 QueueID);
1067 struct sk_buff *DrvAggr_Aggregation(struct net_device *dev, struct ieee80211_drv_agg_txb *pSendList)
1068 {
1069         struct ieee80211_device *ieee = netdev_priv(dev);
1070         struct r8192_priv *priv = ieee80211_priv(dev);
1071         cb_desc         *tcb_desc = NULL;
1072         u8              i;
1073         u32             TotalLength;
1074         struct sk_buff  *skb;
1075         struct sk_buff  *agg_skb;
1076         tx_desc_819x_usb_aggr_subframe *tx_agg_desc = NULL;
1077         tx_fwinfo_819x_usb             *tx_fwinfo = NULL;
1078 
1079         //
1080         // Local variable initialization.
1081         //
1082         /* first skb initialization */
1083         skb = pSendList->tx_agg_frames[0];
1084         TotalLength = skb->len;
1085 
1086         /* Get the total aggregation length including the padding space and
1087          * sub frame header.
1088          */
1089         for (i = 1; i < pSendList->nr_drv_agg_frames; i++) {
1090                 TotalLength += DrvAggr_PaddingAdd(dev, skb);
1091                 skb = pSendList->tx_agg_frames[i];
1092                 TotalLength += (skb->len + TX_PACKET_DRVAGGR_SUBFRAME_SHIFT_BYTES);
1093         }
1094 
1095         /* allocate skb to contain the aggregated packets */
1096         agg_skb = dev_alloc_skb(TotalLength + ieee->tx_headroom);
1097         memset(agg_skb->data, 0, agg_skb->len);
1098         skb_reserve(agg_skb, ieee->tx_headroom);
1099 
1100         /* reserve info for first subframe Tx descriptor to be set in the tx function */
1101         skb = pSendList->tx_agg_frames[0];
1102         tcb_desc = (cb_desc *)(skb->cb + MAX_DEV_ADDR_SIZE);
1103         tcb_desc->drv_agg_enable = 1;
1104         tcb_desc->pkt_size = skb->len;
1105         tcb_desc->DrvAggrNum = pSendList->nr_drv_agg_frames;
1106         netdev_dbg(dev, "DrvAggNum = %d\n", tcb_desc->DrvAggrNum);
1107         memcpy(agg_skb->cb, skb->cb, sizeof(skb->cb));
1108         memcpy(skb_put(agg_skb, skb->len), skb->data, skb->len);
1109 
1110         for (i = 1; i < pSendList->nr_drv_agg_frames; i++) {
1111                 /* push the next sub frame to be 256 byte aline */
1112                 skb_put(agg_skb, DrvAggr_PaddingAdd(dev, skb));
1113 
1114                 /* Subframe drv Tx descriptor and firmware info setting */
1115                 skb = pSendList->tx_agg_frames[i];
1116                 tcb_desc = (cb_desc *)(skb->cb + MAX_DEV_ADDR_SIZE);
1117                 tx_agg_desc = (tx_desc_819x_usb_aggr_subframe *)skb_tail_pointer(agg_skb);
1118                 tx_fwinfo = (tx_fwinfo_819x_usb *)(skb_tail_pointer(agg_skb) + sizeof(tx_desc_819x_usb_aggr_subframe));
1119 
1120                 memset(tx_fwinfo, 0, sizeof(tx_fwinfo_819x_usb));
1121                 /* DWORD 0 */
1122                 tx_fwinfo->TxHT = (tcb_desc->data_rate&0x80) ? 1 : 0;
1123                 tx_fwinfo->TxRate = MRateToHwRate8190Pci(tcb_desc->data_rate);
1124                 tx_fwinfo->EnableCPUDur = tcb_desc->bTxEnableFwCalcDur;
1125                 tx_fwinfo->Short = QueryIsShort(tx_fwinfo->TxHT, tx_fwinfo->TxRate, tcb_desc);
1126                 if (tcb_desc->bAMPDUEnable) {//AMPDU enabled
1127                         tx_fwinfo->AllowAggregation = 1;
1128                         /* DWORD 1 */
1129                         tx_fwinfo->RxMF = tcb_desc->ampdu_factor;
1130                         tx_fwinfo->RxAMD = tcb_desc->ampdu_density&0x07;//ampdudensity
1131                 } else {
1132                         tx_fwinfo->AllowAggregation = 0;
1133                         /* DWORD 1 */
1134                         tx_fwinfo->RxMF = 0;
1135                         tx_fwinfo->RxAMD = 0;
1136                 }
1137 
1138                 /* Protection mode related */
1139                 tx_fwinfo->RtsEnable = (tcb_desc->bRTSEnable) ? 1 : 0;
1140                 tx_fwinfo->CtsEnable = (tcb_desc->bCTSEnable) ? 1 : 0;
1141                 tx_fwinfo->RtsSTBC = (tcb_desc->bRTSSTBC) ? 1 : 0;
1142                 tx_fwinfo->RtsHT = (tcb_desc->rts_rate&0x80) ? 1 : 0;
1143                 tx_fwinfo->RtsRate =  MRateToHwRate8190Pci((u8)tcb_desc->rts_rate);
1144                 tx_fwinfo->RtsSubcarrier = (tx_fwinfo->RtsHT == 0) ? (tcb_desc->RTSSC) : 0;
1145                 tx_fwinfo->RtsBandwidth = (tx_fwinfo->RtsHT == 1) ? ((tcb_desc->bRTSBW) ? 1 : 0) : 0;
1146                 tx_fwinfo->RtsShort = (tx_fwinfo->RtsHT == 0) ? (tcb_desc->bRTSUseShortPreamble ? 1 : 0) :
1147                                       (tcb_desc->bRTSUseShortGI ? 1 : 0);
1148 
1149                 /* Set Bandwidth and sub-channel settings. */
1150                 if (priv->CurrentChannelBW == HT_CHANNEL_WIDTH_20_40) {
1151                         if (tcb_desc->bPacketBW) {
1152                                 tx_fwinfo->TxBandwidth = 1;
1153                                 tx_fwinfo->TxSubCarrier = 0;    //By SD3's Jerry suggestion, use duplicated mode
1154                         } else {
1155                                 tx_fwinfo->TxBandwidth = 0;
1156                                 tx_fwinfo->TxSubCarrier = priv->nCur40MhzPrimeSC;
1157                         }
1158                 } else {
1159                         tx_fwinfo->TxBandwidth = 0;
1160                         tx_fwinfo->TxSubCarrier = 0;
1161                 }
1162 
1163                 /* Fill Tx descriptor */
1164                 memset(tx_agg_desc, 0, sizeof(tx_desc_819x_usb_aggr_subframe));
1165                 /* DWORD 0 */
1166                 tx_agg_desc->Offset =  sizeof(tx_fwinfo_819x_usb) + 8;
1167                 /* already raw data, need not to subtract header length */
1168                 tx_agg_desc->PktSize = skb->len & 0xffff;
1169 
1170                 /*DWORD 1*/
1171                 tx_agg_desc->SecCAMID = 0;
1172                 tx_agg_desc->RATid = tcb_desc->RATRIndex;
1173                 tx_agg_desc->NoEnc = 1;
1174                 tx_agg_desc->SecType = 0x0;
1175 
1176                 if (tcb_desc->bHwSec) {
1177                         switch (priv->ieee80211->pairwise_key_type) {
1178                         case KEY_TYPE_WEP40:
1179                         case KEY_TYPE_WEP104:
1180                                 tx_agg_desc->SecType = 0x1;
1181                                 tx_agg_desc->NoEnc = 0;
1182                                 break;
1183                         case KEY_TYPE_TKIP:
1184                                 tx_agg_desc->SecType = 0x2;
1185                                 tx_agg_desc->NoEnc = 0;
1186                                 break;
1187                         case KEY_TYPE_CCMP:
1188                                 tx_agg_desc->SecType = 0x3;
1189                                 tx_agg_desc->NoEnc = 0;
1190                                 break;
1191                         case KEY_TYPE_NA:
1192                                 tx_agg_desc->SecType = 0x0;
1193                                 tx_agg_desc->NoEnc = 1;
1194                                 break;
1195                         }
1196                 }
1197 
1198                 tx_agg_desc->QueueSelect = MapHwQueueToFirmwareQueue(tcb_desc->queue_index);
1199                 tx_agg_desc->TxFWInfoSize =  sizeof(tx_fwinfo_819x_usb);
1200 
1201                 tx_agg_desc->DISFB = tcb_desc->bTxDisableRateFallBack;
1202                 tx_agg_desc->USERATE = tcb_desc->bTxUseDriverAssingedRate;
1203 
1204                 tx_agg_desc->OWN = 1;
1205 
1206                 //DWORD 2
1207                 /* According windows driver, it seems that there no need to fill this field */
1208 
1209                 /* to fill next packet */
1210                 skb_put(agg_skb, TX_PACKET_DRVAGGR_SUBFRAME_SHIFT_BYTES);
1211                 memcpy(skb_put(agg_skb, skb->len), skb->data, skb->len);
1212         }
1213 
1214         for (i = 0; i < pSendList->nr_drv_agg_frames; i++)
1215                 dev_kfree_skb_any(pSendList->tx_agg_frames[i]);
1216 
1217         return agg_skb;
1218 }
1219 
1220 /* NOTE:
1221         This function return a list of PTCB which is proper to be aggregate with the input TCB.
1222         If no proper TCB is found to do aggregation, SendList will only contain the input TCB.
1223 */
1224 u8 DrvAggr_GetAggregatibleList(struct net_device *dev, struct sk_buff *skb,
1225                                struct ieee80211_drv_agg_txb *pSendList)
1226 {
1227         struct ieee80211_device *ieee = netdev_priv(dev);
1228         PRT_HIGH_THROUGHPUT     pHTInfo = ieee->pHTInfo;
1229         u16             nMaxAggrNum = pHTInfo->UsbTxAggrNum;
1230         cb_desc         *tcb_desc = (cb_desc *)(skb->cb + MAX_DEV_ADDR_SIZE);
1231         u8              QueueID = tcb_desc->queue_index;
1232 
1233         do {
1234                 pSendList->tx_agg_frames[pSendList->nr_drv_agg_frames++] = skb;
1235                 if (pSendList->nr_drv_agg_frames >= nMaxAggrNum)
1236                         break;
1237 
1238         } while ((skb = skb_dequeue(&ieee->skb_drv_aggQ[QueueID])));
1239 
1240         RT_TRACE(COMP_AMSDU, "DrvAggr_GetAggregatibleList, nAggrTcbNum = %d \n", pSendList->nr_drv_agg_frames);
1241         return pSendList->nr_drv_agg_frames;
1242 }
1243 #endif
1244 
1245 static void rtl8192_tx_isr(struct urb *tx_urb)
1246 {
1247         struct sk_buff *skb = (struct sk_buff *)tx_urb->context;
1248         struct net_device *dev = NULL;
1249         struct r8192_priv *priv = NULL;
1250         cb_desc *tcb_desc = (cb_desc *)(skb->cb + MAX_DEV_ADDR_SIZE);
1251         u8  queue_index = tcb_desc->queue_index;
1252 
1253         memcpy(&dev, (struct net_device *)(skb->cb), sizeof(struct net_device *));
1254         priv = ieee80211_priv(dev);
1255 
1256         if (tcb_desc->queue_index != TXCMD_QUEUE) {
1257                 if (tx_urb->status == 0) {
1258                         dev->trans_start = jiffies;
1259                         priv->stats.txoktotal++;
1260                         priv->ieee80211->LinkDetectInfo.NumTxOkInPeriod++;
1261                         priv->stats.txbytesunicast += (skb->len - priv->ieee80211->tx_headroom);
1262                 } else {
1263                         priv->ieee80211->stats.tx_errors++;
1264                         /* TODO */
1265                 }
1266         }
1267 
1268         /* free skb and tx_urb */
1269         if (skb != NULL) {
1270                 dev_kfree_skb_any(skb);
1271                 usb_free_urb(tx_urb);
1272                 atomic_dec(&priv->tx_pending[queue_index]);
1273         }
1274 
1275         //
1276         // Handle HW Beacon:
1277         // We had transfer our beacon frame to host controller at this moment.
1278         //
1279         //
1280         // Caution:
1281         // Handling the wait queue of command packets.
1282         // For Tx command packets, we must not do TCB fragment because it is not handled right now.
1283         // We must cut the packets to match the size of TX_CMD_PKT before we send it.
1284         //
1285 
1286         /* Handle MPDU in wait queue. */
1287         if (queue_index != BEACON_QUEUE) {
1288                 /* Don't send data frame during scanning.*/
1289                 if ((skb_queue_len(&priv->ieee80211->skb_waitQ[queue_index]) != 0) &&
1290                     (!(priv->ieee80211->queue_stop))) {
1291                         skb = skb_dequeue(&(priv->ieee80211->skb_waitQ[queue_index]));
1292                         if (skb)
1293                                 priv->ieee80211->softmac_hard_start_xmit(skb, dev);
1294 
1295                         return; //modified by david to avoid further processing AMSDU
1296                 }
1297 #ifdef USB_TX_DRIVER_AGGREGATION_ENABLE
1298                 else if ((skb_queue_len(&priv->ieee80211->skb_drv_aggQ[queue_index]) != 0) &&
1299                          (!(priv->ieee80211->queue_stop))) {
1300                         // Tx Driver Aggregation process
1301                         /* The driver will aggregation the packets according to the following stats
1302                          * 1. check whether there's tx irq available, for it's a completion return
1303                          *    function, it should contain enough tx irq;
1304                          * 2. check packet type;
1305                          * 3. initialize sendlist, check whether the to-be send packet no greater than 1
1306                          * 4. aggregates the packets, and fill firmware info and tx desc into it, etc.
1307                          * 5. check whether the packet could be sent, otherwise just insert into wait head
1308                          * */
1309                         skb = skb_dequeue(&priv->ieee80211->skb_drv_aggQ[queue_index]);
1310                         if (!check_nic_enough_desc(dev, queue_index)) {
1311                                 skb_queue_head(&(priv->ieee80211->skb_drv_aggQ[queue_index]), skb);
1312                                 return;
1313                         }
1314 
1315                         /*TODO*/
1316                         {
1317                                 struct ieee80211_drv_agg_txb SendList;
1318 
1319                                 memset(&SendList, 0, sizeof(struct ieee80211_drv_agg_txb));
1320                                 if (DrvAggr_GetAggregatibleList(dev, skb, &SendList) > 1) {
1321                                         skb = DrvAggr_Aggregation(dev, &SendList);
1322 
1323                                 }
1324                         }
1325                         priv->ieee80211->softmac_hard_start_xmit(skb, dev);
1326                 }
1327 #endif
1328         }
1329 
1330 }
1331 
1332 static void rtl8192_config_rate(struct net_device *dev, u16 *rate_config)
1333 {
1334         struct r8192_priv *priv = ieee80211_priv(dev);
1335         struct ieee80211_network *net;
1336         u8 i = 0, basic_rate = 0;
1337         net = &priv->ieee80211->current_network;
1338 
1339         for (i = 0; i < net->rates_len; i++) {
1340                 basic_rate = net->rates[i]&0x7f;
1341                 switch (basic_rate) {
1342                 case MGN_1M:    *rate_config |= RRSR_1M;        break;
1343                 case MGN_2M:    *rate_config |= RRSR_2M;        break;
1344                 case MGN_5_5M:  *rate_config |= RRSR_5_5M;      break;
1345                 case MGN_11M:   *rate_config |= RRSR_11M;       break;
1346                 case MGN_6M:    *rate_config |= RRSR_6M;        break;
1347                 case MGN_9M:    *rate_config |= RRSR_9M;        break;
1348                 case MGN_12M:   *rate_config |= RRSR_12M;       break;
1349                 case MGN_18M:   *rate_config |= RRSR_18M;       break;
1350                 case MGN_24M:   *rate_config |= RRSR_24M;       break;
1351                 case MGN_36M:   *rate_config |= RRSR_36M;       break;
1352                 case MGN_48M:   *rate_config |= RRSR_48M;       break;
1353                 case MGN_54M:   *rate_config |= RRSR_54M;       break;
1354                 }
1355         }
1356         for (i = 0; i < net->rates_ex_len; i++) {
1357                 basic_rate = net->rates_ex[i]&0x7f;
1358                 switch (basic_rate) {
1359                 case MGN_1M:    *rate_config |= RRSR_1M;        break;
1360                 case MGN_2M:    *rate_config |= RRSR_2M;        break;
1361                 case MGN_5_5M:  *rate_config |= RRSR_5_5M;      break;
1362                 case MGN_11M:   *rate_config |= RRSR_11M;       break;
1363                 case MGN_6M:    *rate_config |= RRSR_6M;        break;
1364                 case MGN_9M:    *rate_config |= RRSR_9M;        break;
1365                 case MGN_12M:   *rate_config |= RRSR_12M;       break;
1366                 case MGN_18M:   *rate_config |= RRSR_18M;       break;
1367                 case MGN_24M:   *rate_config |= RRSR_24M;       break;
1368                 case MGN_36M:   *rate_config |= RRSR_36M;       break;
1369                 case MGN_48M:   *rate_config |= RRSR_48M;       break;
1370                 case MGN_54M:   *rate_config |= RRSR_54M;       break;
1371                 }
1372         }
1373 }
1374 
1375 
1376 #define SHORT_SLOT_TIME 9
1377 #define NON_SHORT_SLOT_TIME 20
1378 
1379 static void rtl8192_update_cap(struct net_device *dev, u16 cap)
1380 {
1381         u32 tmp = 0;
1382         struct r8192_priv *priv = ieee80211_priv(dev);
1383         struct ieee80211_network *net = &priv->ieee80211->current_network;
1384         priv->short_preamble = cap & WLAN_CAPABILITY_SHORT_PREAMBLE;
1385         tmp = priv->basic_rate;
1386         if (priv->short_preamble)
1387                 tmp |= BRSR_AckShortPmb;
1388         write_nic_dword(dev, RRSR, tmp);
1389 
1390         if (net->mode & (IEEE_G|IEEE_N_24G)) {
1391                 u8 slot_time = 0;
1392                 if ((cap & WLAN_CAPABILITY_SHORT_SLOT) && (!priv->ieee80211->pHTInfo->bCurrentRT2RTLongSlotTime)) //short slot time
1393                         slot_time = SHORT_SLOT_TIME;
1394                 else //long slot time
1395                         slot_time = NON_SHORT_SLOT_TIME;
1396                 priv->slot_time = slot_time;
1397                 write_nic_byte(dev, SLOT_TIME, slot_time);
1398         }
1399 
1400 }
1401 static void rtl8192_net_update(struct net_device *dev)
1402 {
1403 
1404         struct r8192_priv *priv = ieee80211_priv(dev);
1405         struct ieee80211_network *net;
1406         u16 BcnTimeCfg = 0, BcnCW = 6, BcnIFS = 0xf;
1407         u16 rate_config = 0;
1408         net = &priv->ieee80211->current_network;
1409 
1410         rtl8192_config_rate(dev, &rate_config);
1411         priv->basic_rate = rate_config &= 0x15f;
1412 
1413         write_nic_dword(dev, BSSIDR, ((u32 *)net->bssid)[0]);
1414         write_nic_word(dev, BSSIDR+4, ((u16 *)net->bssid)[2]);
1415 
1416         rtl8192_update_msr(dev);
1417         if (priv->ieee80211->iw_mode == IW_MODE_ADHOC) {
1418                 write_nic_word(dev, ATIMWND, 2);
1419                 write_nic_word(dev, BCN_DMATIME, 1023);
1420                 write_nic_word(dev, BCN_INTERVAL, net->beacon_interval);
1421                 write_nic_word(dev, BCN_DRV_EARLY_INT, 1);
1422                 write_nic_byte(dev, BCN_ERR_THRESH, 100);
1423                 BcnTimeCfg |= (BcnCW<<BCN_TCFG_CW_SHIFT);
1424                 // TODO: BcnIFS may required to be changed on ASIC
1425                 BcnTimeCfg |= BcnIFS<<BCN_TCFG_IFS;
1426 
1427                 write_nic_word(dev, BCN_TCFG, BcnTimeCfg);
1428         }
1429 
1430 
1431 
1432 }
1433 
1434 //temporary hw beacon is not used any more.
1435 //open it when necessary
1436 void rtl819xusb_beacon_tx(struct net_device *dev, u16  tx_rate)
1437 {
1438 
1439 }
1440 inline u8 rtl8192_IsWirelessBMode(u16 rate)
1441 {
1442         if (((rate <= 110) && (rate != 60) && (rate != 90)) || (rate == 220))
1443                 return 1;
1444         else return 0;
1445 }
1446 
1447 u16 N_DBPSOfRate(u16 DataRate);
1448 
1449 u16 ComputeTxTime(u16 FrameLength, u16 DataRate, u8 bManagementFrame,
1450                   u8 bShortPreamble)
1451 {
1452         u16     FrameTime;
1453         u16     N_DBPS;
1454         u16     Ceiling;
1455 
1456         if (rtl8192_IsWirelessBMode(DataRate)) {
1457                 if (bManagementFrame || !bShortPreamble || DataRate == 10) // long preamble
1458                         FrameTime = (u16)(144+48+(FrameLength*8/(DataRate/10)));
1459                 else // Short preamble
1460                         FrameTime = (u16)(72+24+(FrameLength*8/(DataRate/10)));
1461                 if ((FrameLength*8 % (DataRate/10)) != 0) //Get the Ceilling
1462                         FrameTime++;
1463         } else {        //802.11g DSSS-OFDM PLCP length field calculation.
1464                 N_DBPS = N_DBPSOfRate(DataRate);
1465                 Ceiling = (16 + 8*FrameLength + 6) / N_DBPS
1466                         + (((16 + 8*FrameLength + 6) % N_DBPS) ? 1 : 0);
1467                 FrameTime = (u16)(16 + 4 + 4*Ceiling + 6);
1468         }
1469         return FrameTime;
1470 }
1471 
1472 u16 N_DBPSOfRate(u16 DataRate)
1473 {
1474         u16 N_DBPS = 24;
1475 
1476         switch (DataRate) {
1477         case 60:
1478                 N_DBPS = 24;
1479                 break;
1480 
1481         case 90:
1482                 N_DBPS = 36;
1483                 break;
1484 
1485         case 120:
1486                 N_DBPS = 48;
1487                 break;
1488 
1489         case 180:
1490                 N_DBPS = 72;
1491                 break;
1492 
1493         case 240:
1494                 N_DBPS = 96;
1495                 break;
1496 
1497         case 360:
1498                 N_DBPS = 144;
1499                 break;
1500 
1501         case 480:
1502                 N_DBPS = 192;
1503                 break;
1504 
1505         case 540:
1506                 N_DBPS = 216;
1507                 break;
1508 
1509         default:
1510                 break;
1511         }
1512 
1513         return N_DBPS;
1514 }
1515 
1516 unsigned int txqueue2outpipe(struct r8192_priv *priv, unsigned int tx_queue)
1517 {
1518         if (tx_queue >= 9) {
1519                 RT_TRACE(COMP_ERR, "%s():Unknown queue ID!!!\n", __func__);
1520                 return 0x04;
1521         }
1522         return priv->txqueue_to_outpipemap[tx_queue];
1523 }
1524 
1525 short rtl819xU_tx_cmd(struct net_device *dev, struct sk_buff *skb)
1526 {
1527         struct r8192_priv *priv = ieee80211_priv(dev);
1528         int                     status;
1529         struct urb              *tx_urb;
1530         unsigned int            idx_pipe;
1531         tx_desc_cmd_819x_usb *pdesc = (tx_desc_cmd_819x_usb *)skb->data;
1532         cb_desc *tcb_desc = (cb_desc *)(skb->cb + MAX_DEV_ADDR_SIZE);
1533         u8 queue_index = tcb_desc->queue_index;
1534 
1535         atomic_inc(&priv->tx_pending[queue_index]);
1536         tx_urb = usb_alloc_urb(0, GFP_ATOMIC);
1537         if (!tx_urb) {
1538                 dev_kfree_skb(skb);
1539                 return -ENOMEM;
1540         }
1541 
1542         memset(pdesc, 0, USB_HWDESC_HEADER_LEN);
1543         /* Tx descriptor ought to be set according to the skb->cb */
1544         pdesc->FirstSeg = 1;//bFirstSeg;
1545         pdesc->LastSeg = 1;//bLastSeg;
1546         pdesc->CmdInit = tcb_desc->bCmdOrInit;
1547         pdesc->TxBufferSize = tcb_desc->txbuf_size;
1548         pdesc->OWN = 1;
1549         pdesc->LINIP = tcb_desc->bLastIniPkt;
1550 
1551         //----------------------------------------------------------------------------
1552         // Fill up USB_OUT_CONTEXT.
1553         //----------------------------------------------------------------------------
1554         // Get index to out pipe from specified QueueID.
1555 #ifndef USE_ONE_PIPE
1556         idx_pipe = txqueue2outpipe(priv, queue_index);
1557 #else
1558         idx_pipe = 0x04;
1559 #endif
1560         usb_fill_bulk_urb(tx_urb, priv->udev, usb_sndbulkpipe(priv->udev, idx_pipe),
1561                           skb->data, skb->len, rtl8192_tx_isr, skb);
1562 
1563         status = usb_submit_urb(tx_urb, GFP_ATOMIC);
1564 
1565         if (!status) {
1566                 return 0;
1567         } else {
1568                 DMESGE("Error TX CMD URB, error %d", status);
1569                 return -1;
1570         }
1571 }
1572 
1573 /*
1574  * Mapping Software/Hardware descriptor queue id to "Queue Select Field"
1575  * in TxFwInfo data structure
1576  * 2006.10.30 by Emily
1577  *
1578  * \param QUEUEID       Software Queue
1579 */
1580 static u8 MapHwQueueToFirmwareQueue(u8 QueueID)
1581 {
1582         u8 QueueSelect = 0x0;       //defualt set to
1583 
1584         switch (QueueID) {
1585         case BE_QUEUE:
1586                 QueueSelect = QSLT_BE;
1587                 break;
1588 
1589         case BK_QUEUE:
1590                 QueueSelect = QSLT_BK;
1591                 break;
1592 
1593         case VO_QUEUE:
1594                 QueueSelect = QSLT_VO;
1595                 break;
1596 
1597         case VI_QUEUE:
1598                 QueueSelect = QSLT_VI;
1599                 break;
1600         case MGNT_QUEUE:
1601                 QueueSelect = QSLT_MGNT;
1602                 break;
1603 
1604         case BEACON_QUEUE:
1605                 QueueSelect = QSLT_BEACON;
1606                 break;
1607 
1608                 // TODO: 2006.10.30 mark other queue selection until we verify it is OK
1609                 // TODO: Remove Assertions
1610         case TXCMD_QUEUE:
1611                 QueueSelect = QSLT_CMD;
1612                 break;
1613         case HIGH_QUEUE:
1614                 QueueSelect = QSLT_HIGH;
1615                 break;
1616 
1617         default:
1618                 RT_TRACE(COMP_ERR, "TransmitTCB(): Impossible Queue Selection: %d \n", QueueID);
1619                 break;
1620         }
1621         return QueueSelect;
1622 }
1623 
1624 static u8 MRateToHwRate8190Pci(u8 rate)
1625 {
1626         u8  ret = DESC90_RATE1M;
1627 
1628         switch (rate) {
1629         case MGN_1M:    ret = DESC90_RATE1M;    break;
1630         case MGN_2M:    ret = DESC90_RATE2M;    break;
1631         case MGN_5_5M:  ret = DESC90_RATE5_5M;  break;
1632         case MGN_11M:   ret = DESC90_RATE11M;   break;
1633         case MGN_6M:    ret = DESC90_RATE6M;    break;
1634         case MGN_9M:    ret = DESC90_RATE9M;    break;
1635         case MGN_12M:   ret = DESC90_RATE12M;   break;
1636         case MGN_18M:   ret = DESC90_RATE18M;   break;
1637         case MGN_24M:   ret = DESC90_RATE24M;   break;
1638         case MGN_36M:   ret = DESC90_RATE36M;   break;
1639         case MGN_48M:   ret = DESC90_RATE48M;   break;
1640         case MGN_54M:   ret = DESC90_RATE54M;   break;
1641 
1642         // HT rate since here
1643         case MGN_MCS0:  ret = DESC90_RATEMCS0;  break;
1644         case MGN_MCS1:  ret = DESC90_RATEMCS1;  break;
1645         case MGN_MCS2:  ret = DESC90_RATEMCS2;  break;
1646         case MGN_MCS3:  ret = DESC90_RATEMCS3;  break;
1647         case MGN_MCS4:  ret = DESC90_RATEMCS4;  break;
1648         case MGN_MCS5:  ret = DESC90_RATEMCS5;  break;
1649         case MGN_MCS6:  ret = DESC90_RATEMCS6;  break;
1650         case MGN_MCS7:  ret = DESC90_RATEMCS7;  break;
1651         case MGN_MCS8:  ret = DESC90_RATEMCS8;  break;
1652         case MGN_MCS9:  ret = DESC90_RATEMCS9;  break;
1653         case MGN_MCS10: ret = DESC90_RATEMCS10; break;
1654         case MGN_MCS11: ret = DESC90_RATEMCS11; break;
1655         case MGN_MCS12: ret = DESC90_RATEMCS12; break;
1656         case MGN_MCS13: ret = DESC90_RATEMCS13; break;
1657         case MGN_MCS14: ret = DESC90_RATEMCS14; break;
1658         case MGN_MCS15: ret = DESC90_RATEMCS15; break;
1659         case (0x80|0x20): ret = DESC90_RATEMCS32; break;
1660 
1661         default:       break;
1662         }
1663         return ret;
1664 }
1665 
1666 
1667 static u8 QueryIsShort(u8 TxHT, u8 TxRate, cb_desc *tcb_desc)
1668 {
1669         u8   tmp_Short;
1670 
1671         tmp_Short = (TxHT == 1) ? ((tcb_desc->bUseShortGI) ? 1 : 0) : ((tcb_desc->bUseShortPreamble) ? 1 : 0);
1672 
1673         if (TxHT == 1 && TxRate != DESC90_RATEMCS15)
1674                 tmp_Short = 0;
1675 
1676         return tmp_Short;
1677 }
1678 
1679 static void tx_zero_isr(struct urb *tx_urb)
1680 {
1681         return;
1682 }
1683 
1684 /*
1685  * The tx procedure is just as following,
1686  * skb->cb will contain all the following information,
1687  * priority, morefrag, rate, &dev.
1688  * */
1689 short rtl8192_tx(struct net_device *dev, struct sk_buff *skb)
1690 {
1691         struct r8192_priv *priv = ieee80211_priv(dev);
1692         cb_desc *tcb_desc = (cb_desc *)(skb->cb + MAX_DEV_ADDR_SIZE);
1693         tx_desc_819x_usb *tx_desc = (tx_desc_819x_usb *)skb->data;
1694         tx_fwinfo_819x_usb *tx_fwinfo = (tx_fwinfo_819x_usb *)(skb->data + USB_HWDESC_HEADER_LEN);
1695         struct usb_device *udev = priv->udev;
1696         int pend;
1697         int status;
1698         struct urb *tx_urb = NULL, *tx_urb_zero = NULL;
1699         unsigned int idx_pipe;
1700         pend = atomic_read(&priv->tx_pending[tcb_desc->queue_index]);
1701         /* we are locked here so the two atomic_read and inc are executed
1702          * without interleaves
1703          * !!! For debug purpose
1704          */
1705         if (pend > MAX_TX_URB) {
1706                 netdev_dbg(dev, "To discard skb packet!\n");
1707                 dev_kfree_skb_any(skb);
1708                 return -1;
1709         }
1710 
1711         tx_urb = usb_alloc_urb(0, GFP_ATOMIC);
1712         if (!tx_urb) {
1713                 dev_kfree_skb_any(skb);
1714                 return -ENOMEM;
1715         }
1716 
1717         /* Fill Tx firmware info */
1718         memset(tx_fwinfo, 0, sizeof(tx_fwinfo_819x_usb));
1719         /* DWORD 0 */
1720         tx_fwinfo->TxHT = (tcb_desc->data_rate&0x80) ? 1 : 0;
1721         tx_fwinfo->TxRate = MRateToHwRate8190Pci(tcb_desc->data_rate);
1722         tx_fwinfo->EnableCPUDur = tcb_desc->bTxEnableFwCalcDur;
1723         tx_fwinfo->Short = QueryIsShort(tx_fwinfo->TxHT, tx_fwinfo->TxRate, tcb_desc);
1724         if (tcb_desc->bAMPDUEnable) {//AMPDU enabled
1725                 tx_fwinfo->AllowAggregation = 1;
1726                 /* DWORD 1 */
1727                 tx_fwinfo->RxMF = tcb_desc->ampdu_factor;
1728                 tx_fwinfo->RxAMD = tcb_desc->ampdu_density&0x07;//ampdudensity
1729         } else {
1730                 tx_fwinfo->AllowAggregation = 0;
1731                 /* DWORD 1 */
1732                 tx_fwinfo->RxMF = 0;
1733                 tx_fwinfo->RxAMD = 0;
1734         }
1735 
1736         /* Protection mode related */
1737         tx_fwinfo->RtsEnable = (tcb_desc->bRTSEnable) ? 1 : 0;
1738         tx_fwinfo->CtsEnable = (tcb_desc->bCTSEnable) ? 1 : 0;
1739         tx_fwinfo->RtsSTBC = (tcb_desc->bRTSSTBC) ? 1 : 0;
1740         tx_fwinfo->RtsHT = (tcb_desc->rts_rate&0x80) ? 1 : 0;
1741         tx_fwinfo->RtsRate =  MRateToHwRate8190Pci((u8)tcb_desc->rts_rate);
1742         tx_fwinfo->RtsSubcarrier = (tx_fwinfo->RtsHT == 0) ? (tcb_desc->RTSSC) : 0;
1743         tx_fwinfo->RtsBandwidth = (tx_fwinfo->RtsHT == 1) ? ((tcb_desc->bRTSBW) ? 1 : 0) : 0;
1744         tx_fwinfo->RtsShort = (tx_fwinfo->RtsHT == 0) ? (tcb_desc->bRTSUseShortPreamble ? 1 : 0) :
1745                               (tcb_desc->bRTSUseShortGI ? 1 : 0);
1746 
1747         /* Set Bandwidth and sub-channel settings. */
1748         if (priv->CurrentChannelBW == HT_CHANNEL_WIDTH_20_40) {
1749                 if (tcb_desc->bPacketBW) {
1750                         tx_fwinfo->TxBandwidth = 1;
1751                         tx_fwinfo->TxSubCarrier = 0;    //By SD3's Jerry suggestion, use duplicated mode
1752                 } else {
1753                         tx_fwinfo->TxBandwidth = 0;
1754                         tx_fwinfo->TxSubCarrier = priv->nCur40MhzPrimeSC;
1755                 }
1756         } else {
1757                 tx_fwinfo->TxBandwidth = 0;
1758                 tx_fwinfo->TxSubCarrier = 0;
1759         }
1760 
1761 #ifdef USB_TX_DRIVER_AGGREGATION_ENABLE
1762         if (tcb_desc->drv_agg_enable)
1763                 tx_fwinfo->Tx_INFO_RSVD = (tcb_desc->DrvAggrNum & 0x1f) << 1;
1764 #endif
1765         /* Fill Tx descriptor */
1766         memset(tx_desc, 0, sizeof(tx_desc_819x_usb));
1767         /* DWORD 0 */
1768         tx_desc->LINIP = 0;
1769         tx_desc->CmdInit = 1;
1770         tx_desc->Offset =  sizeof(tx_fwinfo_819x_usb) + 8;
1771 
1772 #ifdef USB_TX_DRIVER_AGGREGATION_ENABLE
1773         if (tcb_desc->drv_agg_enable)
1774                 tx_desc->PktSize = tcb_desc->pkt_size;
1775         else
1776 #endif
1777         {
1778                 tx_desc->PktSize = (skb->len - TX_PACKET_SHIFT_BYTES) & 0xffff;
1779         }
1780 
1781         /*DWORD 1*/
1782         tx_desc->SecCAMID = 0;
1783         tx_desc->RATid = tcb_desc->RATRIndex;
1784         tx_desc->NoEnc = 1;
1785         tx_desc->SecType = 0x0;
1786         if (tcb_desc->bHwSec) {
1787                 switch (priv->ieee80211->pairwise_key_type) {
1788                 case KEY_TYPE_WEP40:
1789                 case KEY_TYPE_WEP104:
1790                         tx_desc->SecType = 0x1;
1791                         tx_desc->NoEnc = 0;
1792                         break;
1793                 case KEY_TYPE_TKIP:
1794                         tx_desc->SecType = 0x2;
1795                         tx_desc->NoEnc = 0;
1796                         break;
1797                 case KEY_TYPE_CCMP:
1798                         tx_desc->SecType = 0x3;
1799                         tx_desc->NoEnc = 0;
1800                         break;
1801                 case KEY_TYPE_NA:
1802                         tx_desc->SecType = 0x0;
1803                         tx_desc->NoEnc = 1;
1804                         break;
1805                 }
1806         }
1807 
1808         tx_desc->QueueSelect = MapHwQueueToFirmwareQueue(tcb_desc->queue_index);
1809         tx_desc->TxFWInfoSize =  sizeof(tx_fwinfo_819x_usb);
1810 
1811         tx_desc->DISFB = tcb_desc->bTxDisableRateFallBack;
1812         tx_desc->USERATE = tcb_desc->bTxUseDriverAssingedRate;
1813 
1814         /* Fill fields that are required to be initialized in all of the descriptors */
1815         //DWORD 0
1816         tx_desc->FirstSeg = 1;
1817         tx_desc->LastSeg = 1;
1818         tx_desc->OWN = 1;
1819 
1820 #ifdef USB_TX_DRIVER_AGGREGATION_ENABLE
1821         if (tcb_desc->drv_agg_enable) {
1822                 tx_desc->TxBufferSize = tcb_desc->pkt_size + sizeof(tx_fwinfo_819x_usb);
1823         } else
1824 #endif
1825         {
1826                 //DWORD 2
1827                 tx_desc->TxBufferSize = (u32)(skb->len - USB_HWDESC_HEADER_LEN);
1828         }
1829         /* Get index to out pipe from specified QueueID */
1830 #ifndef USE_ONE_PIPE
1831         idx_pipe = txqueue2outpipe(priv, tcb_desc->queue_index);
1832 #else
1833         idx_pipe = 0x5;
1834 #endif
1835 
1836         /* To submit bulk urb */
1837         usb_fill_bulk_urb(tx_urb, udev,
1838                           usb_sndbulkpipe(udev, idx_pipe), skb->data,
1839                           skb->len, rtl8192_tx_isr, skb);
1840 
1841         status = usb_submit_urb(tx_urb, GFP_ATOMIC);
1842         if (!status) {
1843                 //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
1844                 bool bSend0Byte = false;
1845                 u8 zero = 0;
1846                 if (udev->speed == USB_SPEED_HIGH) {
1847                         if (skb->len > 0 && skb->len % 512 == 0)
1848                                 bSend0Byte = true;
1849                 } else {
1850                         if (skb->len > 0 && skb->len % 64 == 0)
1851                                 bSend0Byte = true;
1852                 }
1853                 if (bSend0Byte) {
1854                         tx_urb_zero = usb_alloc_urb(0, GFP_ATOMIC);
1855                         if (!tx_urb_zero) {
1856                                 RT_TRACE(COMP_ERR, "can't alloc urb for zero byte\n");
1857                                 return -ENOMEM;
1858                         }
1859                         usb_fill_bulk_urb(tx_urb_zero, udev,
1860                                           usb_sndbulkpipe(udev, idx_pipe), &zero,
1861                                           0, tx_zero_isr, dev);
1862                         status = usb_submit_urb(tx_urb_zero, GFP_ATOMIC);
1863                         if (status) {
1864                                 RT_TRACE(COMP_ERR, "Error TX URB for zero byte %d, error %d", atomic_read(&priv->tx_pending[tcb_desc->queue_index]), status);
1865                                 return -1;
1866                         }
1867                 }
1868                 dev->trans_start = jiffies;
1869                 atomic_inc(&priv->tx_pending[tcb_desc->queue_index]);
1870                 return 0;
1871         } else {
1872                 RT_TRACE(COMP_ERR, "Error TX URB %d, error %d", atomic_read(&priv->tx_pending[tcb_desc->queue_index]),
1873                          status);
1874                 return -1;
1875         }
1876 }
1877 
1878 static short rtl8192_usb_initendpoints(struct net_device *dev)
1879 {
1880         struct r8192_priv *priv = ieee80211_priv(dev);
1881 
1882         priv->rx_urb = kmalloc(sizeof(struct urb *) * (MAX_RX_URB+1),
1883                                GFP_KERNEL);
1884         if (priv->rx_urb == NULL)
1885                 return -ENOMEM;
1886 
1887 #ifndef JACKSON_NEW_RX
1888         for (i = 0; i < (MAX_RX_URB+1); i++) {
1889 
1890                 priv->rx_urb[i] = usb_alloc_urb(0, GFP_KERNEL);
1891 
1892                 priv->rx_urb[i]->transfer_buffer = kmalloc(RX_URB_SIZE, GFP_KERNEL);
1893 
1894                 priv->rx_urb[i]->transfer_buffer_length = RX_URB_SIZE;
1895         }
1896 #endif
1897 
1898 #ifdef THOMAS_BEACON
1899         {
1900                 long align = 0;
1901                 void *oldaddr, *newaddr;
1902 
1903                 priv->rx_urb[16] = usb_alloc_urb(0, GFP_KERNEL);
1904                 priv->oldaddr = kmalloc(16, GFP_KERNEL);
1905                 oldaddr = priv->oldaddr;
1906                 align = ((long)oldaddr) & 3;
1907                 if (align) {
1908                         newaddr = oldaddr + 4 - align;
1909                         priv->rx_urb[16]->transfer_buffer_length = 16 - 4 + align;
1910                 } else {
1911                         newaddr = oldaddr;
1912                         priv->rx_urb[16]->transfer_buffer_length = 16;
1913                 }
1914                 priv->rx_urb[16]->transfer_buffer = newaddr;
1915         }
1916 #endif
1917 
1918         memset(priv->rx_urb, 0, sizeof(struct urb *) * MAX_RX_URB);
1919         priv->pp_rxskb = kcalloc(MAX_RX_URB, sizeof(struct sk_buff *),
1920                                  GFP_KERNEL);
1921         if (!priv->pp_rxskb) {
1922                 kfree(priv->rx_urb);
1923 
1924                 priv->pp_rxskb = NULL;
1925                 priv->rx_urb = NULL;
1926 
1927                 DMESGE("Endpoint Alloc Failure");
1928                 return -ENOMEM;
1929         }
1930 
1931         netdev_dbg(dev, "End of initendpoints\n");
1932         return 0;
1933 
1934 }
1935 #ifdef THOMAS_BEACON
1936 static void rtl8192_usb_deleteendpoints(struct net_device *dev)
1937 {
1938         int i;
1939         struct r8192_priv *priv = ieee80211_priv(dev);
1940 
1941         if (priv->rx_urb) {
1942                 for (i = 0; i < (MAX_RX_URB+1); i++) {
1943                         usb_kill_urb(priv->rx_urb[i]);
1944                         usb_free_urb(priv->rx_urb[i]);
1945                 }
1946                 kfree(priv->rx_urb);
1947                 priv->rx_urb = NULL;
1948         }
1949         kfree(priv->oldaddr);
1950         priv->oldaddr = NULL;
1951         if (priv->pp_rxskb) {
1952                 kfree(priv->pp_rxskb);
1953                 priv->pp_rxskb = NULL;
1954         }
1955 }
1956 #else
1957 void rtl8192_usb_deleteendpoints(struct net_device *dev)
1958 {
1959         int i;
1960         struct r8192_priv *priv = ieee80211_priv(dev);
1961 
1962 #ifndef JACKSON_NEW_RX
1963 
1964         if (priv->rx_urb) {
1965                 for (i = 0; i < (MAX_RX_URB+1); i++) {
1966                         usb_kill_urb(priv->rx_urb[i]);
1967                         kfree(priv->rx_urb[i]->transfer_buffer);
1968                         usb_free_urb(priv->rx_urb[i]);
1969                 }
1970                 kfree(priv->rx_urb);
1971                 priv->rx_urb = NULL;
1972 
1973         }
1974 #else
1975         kfree(priv->rx_urb);
1976         priv->rx_urb = NULL;
1977         kfree(priv->oldaddr);
1978         priv->oldaddr = NULL;
1979         if (priv->pp_rxskb) {
1980                 kfree(priv->pp_rxskb);
1981                 priv->pp_rxskb = 0;
1982 
1983         }
1984 
1985 #endif
1986 }
1987 #endif
1988 
1989 extern void rtl8192_update_ratr_table(struct net_device *dev);
1990 static void rtl8192_link_change(struct net_device *dev)
1991 {
1992         struct r8192_priv *priv = ieee80211_priv(dev);
1993         struct ieee80211_device *ieee = priv->ieee80211;
1994         if (ieee->state == IEEE80211_LINKED) {
1995                 rtl8192_net_update(dev);
1996                 rtl8192_update_ratr_table(dev);
1997                 //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
1998                 if ((KEY_TYPE_WEP40 == ieee->pairwise_key_type) || (KEY_TYPE_WEP104 == ieee->pairwise_key_type))
1999                         EnableHWSecurityConfig8192(dev);
2000         }
2001         /*update timing params*/
2002         if (ieee->iw_mode == IW_MODE_INFRA || ieee->iw_mode == IW_MODE_ADHOC) {
2003                 u32 reg = 0;
2004                 read_nic_dword(dev, RCR, &reg);
2005                 if (priv->ieee80211->state == IEEE80211_LINKED)
2006                         priv->ReceiveConfig = reg |= RCR_CBSSID;
2007                 else
2008                         priv->ReceiveConfig = reg &= ~RCR_CBSSID;
2009                 write_nic_dword(dev, RCR, reg);
2010         }
2011 }
2012 
2013 static struct ieee80211_qos_parameters def_qos_parameters = {
2014         {3, 3, 3, 3},/* cw_min */
2015         {7, 7, 7, 7},/* cw_max */
2016         {2, 2, 2, 2},/* aifs */
2017         {0, 0, 0, 0},/* flags */
2018         {0, 0, 0, 0} /* tx_op_limit */
2019 };
2020 
2021 
2022 static void rtl8192_update_beacon(struct work_struct *work)
2023 {
2024         struct r8192_priv *priv = container_of(work, struct r8192_priv, update_beacon_wq.work);
2025         struct net_device *dev = priv->ieee80211->dev;
2026         struct ieee80211_device *ieee = priv->ieee80211;
2027         struct ieee80211_network *net = &ieee->current_network;
2028 
2029         if (ieee->pHTInfo->bCurrentHTSupport)
2030                 HTUpdateSelfAndPeerSetting(ieee, net);
2031         ieee->pHTInfo->bCurrentRT2RTLongSlotTime = net->bssht.bdRT2RTLongSlotTime;
2032         rtl8192_update_cap(dev, net->capability);
2033 }
2034 /*
2035 * background support to run QoS activate functionality
2036 */
2037 static int WDCAPARA_ADD[] = {EDCAPARA_BE, EDCAPARA_BK, EDCAPARA_VI, EDCAPARA_VO};
2038 static void rtl8192_qos_activate(struct work_struct *work)
2039 {
2040         struct r8192_priv *priv = container_of(work, struct r8192_priv, qos_activate);
2041         struct net_device *dev = priv->ieee80211->dev;
2042         struct ieee80211_qos_parameters *qos_parameters = &priv->ieee80211->current_network.qos_data.parameters;
2043         u8 mode = priv->ieee80211->current_network.mode;
2044         u8  u1bAIFS;
2045         u32 u4bAcParam;
2046         int i;
2047 
2048         if (priv == NULL)
2049                 return;
2050 
2051         mutex_lock(&priv->mutex);
2052         if (priv->ieee80211->state != IEEE80211_LINKED)
2053                 goto success;
2054         RT_TRACE(COMP_QOS, "qos active process with associate response received\n");
2055         /* It better set slot time at first */
2056         /* For we just support b/g mode at present, let the slot time at 9/20 selection */
2057         /* update the ac parameter to related registers */
2058         for (i = 0; i <  QOS_QUEUE_NUM; i++) {
2059                 //Mode G/A: slotTimeTimer = 9; Mode B: 20
2060                 u1bAIFS = qos_parameters->aifs[i] * ((mode&(IEEE_G|IEEE_N_24G)) ? 9 : 20) + aSifsTime;
2061                 u4bAcParam = ((((u32)(qos_parameters->tx_op_limit[i]))<< AC_PARAM_TXOP_LIMIT_OFFSET)|
2062                               (((u32)(qos_parameters->cw_max[i]))<< AC_PARAM_ECW_MAX_OFFSET)|
2063                               (((u32)(qos_parameters->cw_min[i]))<< AC_PARAM_ECW_MIN_OFFSET)|
2064                               ((u32)u1bAIFS << AC_PARAM_AIFS_OFFSET));
2065 
2066                 write_nic_dword(dev, WDCAPARA_ADD[i], u4bAcParam);
2067         }
2068 
2069 success:
2070         mutex_unlock(&priv->mutex);
2071 }
2072 
2073 static int rtl8192_qos_handle_probe_response(struct r8192_priv *priv,
2074                                              int active_network,
2075                                              struct ieee80211_network *network)
2076 {
2077         int ret = 0;
2078         u32 size = sizeof(struct ieee80211_qos_parameters);
2079 
2080         if (priv->ieee80211->state != IEEE80211_LINKED)
2081                 return ret;
2082 
2083         if ((priv->ieee80211->iw_mode != IW_MODE_INFRA))
2084                 return ret;
2085 
2086         if (network->flags & NETWORK_HAS_QOS_MASK) {
2087                 if (active_network &&
2088                     (network->flags & NETWORK_HAS_QOS_PARAMETERS))
2089                         network->qos_data.active = network->qos_data.supported;
2090 
2091                 if ((network->qos_data.active == 1) && (active_network == 1) &&
2092                     (network->flags & NETWORK_HAS_QOS_PARAMETERS) &&
2093                     (network->qos_data.old_param_count !=
2094                      network->qos_data.param_count)) {
2095                         network->qos_data.old_param_count =
2096                                 network->qos_data.param_count;
2097                         queue_work(priv->priv_wq, &priv->qos_activate);
2098                         RT_TRACE(COMP_QOS, "QoS parameters change call "
2099                                  "qos_activate\n");
2100                 }
2101         } else {
2102                 memcpy(&priv->ieee80211->current_network.qos_data.parameters,
2103                        &def_qos_parameters, size);
2104 
2105                 if ((network->qos_data.active == 1) && (active_network == 1)) {
2106                         queue_work(priv->priv_wq, &priv->qos_activate);
2107                         RT_TRACE(COMP_QOS, "QoS was disabled call qos_activate \n");
2108                 }
2109                 network->qos_data.active = 0;
2110                 network->qos_data.supported = 0;
2111         }
2112 
2113         return 0;
2114 }
2115 
2116 /* handle and manage frame from beacon and probe response */
2117 static int rtl8192_handle_beacon(struct net_device *dev,
2118                                  struct ieee80211_beacon *beacon,
2119                                  struct ieee80211_network *network)
2120 {
2121         struct r8192_priv *priv = ieee80211_priv(dev);
2122 
2123         rtl8192_qos_handle_probe_response(priv, 1, network);
2124         queue_delayed_work(priv->priv_wq, &priv->update_beacon_wq, 0);
2125         return 0;
2126 
2127 }
2128 
2129 /*
2130 * handling the beaconing responses. if we get different QoS setting
2131 * off the network from the associated setting, adjust the QoS
2132 * setting
2133 */
2134 static int rtl8192_qos_association_resp(struct r8192_priv *priv,
2135                                         struct ieee80211_network *network)
2136 {
2137         int ret = 0;
2138         unsigned long flags;
2139         u32 size = sizeof(struct ieee80211_qos_parameters);
2140         int set_qos_param = 0;
2141 
2142         if ((priv == NULL) || (network == NULL))
2143                 return ret;
2144 
2145         if (priv->ieee80211->state != IEEE80211_LINKED)
2146                 return ret;
2147 
2148         if ((priv->ieee80211->iw_mode != IW_MODE_INFRA))
2149                 return ret;
2150 
2151         spin_lock_irqsave(&priv->ieee80211->lock, flags);
2152         if (network->flags & NETWORK_HAS_QOS_PARAMETERS) {
2153                 memcpy(&priv->ieee80211->current_network.qos_data.parameters,
2154                        &network->qos_data.parameters,
2155                        sizeof(struct ieee80211_qos_parameters));
2156                 priv->ieee80211->current_network.qos_data.active = 1;
2157                 set_qos_param = 1;
2158                 /* update qos parameter for current network */
2159                 priv->ieee80211->current_network.qos_data.old_param_count =
2160                         priv->ieee80211->current_network.qos_data.param_count;
2161                 priv->ieee80211->current_network.qos_data.param_count =
2162                         network->qos_data.param_count;
2163         } else {
2164                 memcpy(&priv->ieee80211->current_network.qos_data.parameters,
2165                        &def_qos_parameters, size);
2166                 priv->ieee80211->current_network.qos_data.active = 0;
2167                 priv->ieee80211->current_network.qos_data.supported = 0;
2168                 set_qos_param = 1;
2169         }
2170 
2171         spin_unlock_irqrestore(&priv->ieee80211->lock, flags);
2172 
2173         RT_TRACE(COMP_QOS, "%s: network->flags = %d,%d\n", __func__, network->flags, priv->ieee80211->current_network.qos_data.active);
2174         if (set_qos_param == 1)
2175                 queue_work(priv->priv_wq, &priv->qos_activate);
2176 
2177 
2178         return ret;
2179 }
2180 
2181 
2182 static int rtl8192_handle_assoc_response(struct net_device *dev,
2183                                          struct ieee80211_assoc_response_frame *resp,
2184                                          struct ieee80211_network *network)
2185 {
2186         struct r8192_priv *priv = ieee80211_priv(dev);
2187         rtl8192_qos_association_resp(priv, network);
2188         return 0;
2189 }
2190 
2191 
2192 void rtl8192_update_ratr_table(struct net_device *dev)
2193 {
2194         struct r8192_priv *priv = ieee80211_priv(dev);
2195         struct ieee80211_device *ieee = priv->ieee80211;
2196         u8 *pMcsRate = ieee->dot11HTOperationalRateSet;
2197         u32 ratr_value = 0;
2198         u8 rate_index = 0;
2199         rtl8192_config_rate(dev, (u16 *)(&ratr_value));
2200         ratr_value |= (*(u16 *)(pMcsRate)) << 12;
2201         switch (ieee->mode) {
2202         case IEEE_A:
2203                 ratr_value &= 0x00000FF0;
2204                 break;
2205         case IEEE_B:
2206                 ratr_value &= 0x0000000F;
2207                 break;
2208         case IEEE_G:
2209                 ratr_value &= 0x00000FF7;
2210                 break;
2211         case IEEE_N_24G:
2212         case IEEE_N_5G:
2213                 if (ieee->pHTInfo->PeerMimoPs == 0) {//MIMO_PS_STATIC
2214                         ratr_value &= 0x0007F007;
2215                 } else {
2216                         if (priv->rf_type == RF_1T2R)
2217                                 ratr_value &= 0x000FF007;
2218                         else
2219                                 ratr_value &= 0x0F81F007;
2220                 }
2221                 break;
2222         default:
2223                 break;
2224         }
2225         ratr_value &= 0x0FFFFFFF;
2226         if (ieee->pHTInfo->bCurTxBW40MHz && ieee->pHTInfo->bCurShortGI40MHz)
2227                 ratr_value |= 0x80000000;
2228         else if (!ieee->pHTInfo->bCurTxBW40MHz && ieee->pHTInfo->bCurShortGI20MHz)
2229                 ratr_value |= 0x80000000;
2230         write_nic_dword(dev, RATR0+rate_index*4, ratr_value);
2231         write_nic_byte(dev, UFWP, 1);
2232 }
2233 
2234 static u8 ccmp_ie[4] = {0x00, 0x50, 0xf2, 0x04};
2235 static u8 ccmp_rsn_ie[4] = {0x00, 0x0f, 0xac, 0x04};
2236 static bool GetNmodeSupportBySecCfg8192(struct net_device *dev)
2237 {
2238         struct r8192_priv *priv = ieee80211_priv(dev);
2239         struct ieee80211_device *ieee = priv->ieee80211;
2240         struct ieee80211_network *network = &ieee->current_network;
2241         int wpa_ie_len = ieee->wpa_ie_len;
2242         struct ieee80211_crypt_data *crypt;
2243         int encrypt;
2244 
2245         crypt = ieee->crypt[ieee->tx_keyidx];
2246         //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
2247         encrypt = (network->capability & WLAN_CAPABILITY_PRIVACY) || (ieee->host_encrypt && crypt && crypt->ops && (0 == strcmp(crypt->ops->name, "WEP")));
2248 
2249         /* simply judge  */
2250         if (encrypt && (wpa_ie_len == 0)) {
2251                 /* wep encryption, no N mode setting */
2252                 return false;
2253         } else if ((wpa_ie_len != 0)) {
2254                 /* parse pairwise key type */
2255                 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))))
2256                         return true;
2257                 else
2258                         return false;
2259         } else {
2260                 return true;
2261         }
2262 
2263         return true;
2264 }
2265 
2266 static bool GetHalfNmodeSupportByAPs819xUsb(struct net_device *dev)
2267 {
2268         bool                    Reval;
2269         struct r8192_priv *priv = ieee80211_priv(dev);
2270         struct ieee80211_device *ieee = priv->ieee80211;
2271 
2272         if (ieee->bHalfWirelessN24GMode == true)
2273                 Reval = true;
2274         else
2275                 Reval =  false;
2276 
2277         return Reval;
2278 }
2279 
2280 static void rtl8192_refresh_supportrate(struct r8192_priv *priv)
2281 {
2282         struct ieee80211_device *ieee = priv->ieee80211;
2283         //we do not consider set support rate for ABG mode, only HT MCS rate is set here.
2284         if (ieee->mode == WIRELESS_MODE_N_24G || ieee->mode == WIRELESS_MODE_N_5G)
2285                 memcpy(ieee->Regdot11HTOperationalRateSet, ieee->RegHTSuppRateSet, 16);
2286         else
2287                 memset(ieee->Regdot11HTOperationalRateSet, 0, 16);
2288         return;
2289 }
2290 
2291 static u8 rtl8192_getSupportedWireleeMode(struct net_device *dev)
2292 {
2293         struct r8192_priv *priv = ieee80211_priv(dev);
2294         u8 ret = 0;
2295         switch (priv->rf_chip) {
2296         case RF_8225:
2297         case RF_8256:
2298         case RF_PSEUDO_11N:
2299                 ret = (WIRELESS_MODE_N_24G|WIRELESS_MODE_G|WIRELESS_MODE_B);
2300                 break;
2301         case RF_8258:
2302                 ret = (WIRELESS_MODE_A|WIRELESS_MODE_N_5G);
2303                 break;
2304         default:
2305                 ret = WIRELESS_MODE_B;
2306                 break;
2307         }
2308         return ret;
2309 }
2310 static void rtl8192_SetWirelessMode(struct net_device *dev, u8 wireless_mode)
2311 {
2312         struct r8192_priv *priv = ieee80211_priv(dev);
2313         u8 bSupportMode = rtl8192_getSupportedWireleeMode(dev);
2314 
2315         if ((wireless_mode == WIRELESS_MODE_AUTO) || ((wireless_mode&bSupportMode) == 0)) {
2316                 if (bSupportMode & WIRELESS_MODE_N_24G) {
2317                         wireless_mode = WIRELESS_MODE_N_24G;
2318                 } else if (bSupportMode & WIRELESS_MODE_N_5G) {
2319                         wireless_mode = WIRELESS_MODE_N_5G;
2320                 } else if ((bSupportMode & WIRELESS_MODE_A)) {
2321                         wireless_mode = WIRELESS_MODE_A;
2322                 } else if ((bSupportMode & WIRELESS_MODE_G)) {
2323                         wireless_mode = WIRELESS_MODE_G;
2324                 } else if ((bSupportMode & WIRELESS_MODE_B)) {
2325                         wireless_mode = WIRELESS_MODE_B;
2326                 } else {
2327                         RT_TRACE(COMP_ERR, "%s(), No valid wireless mode supported, SupportedWirelessMode(%x)!!!\n", __func__, bSupportMode);
2328                         wireless_mode = WIRELESS_MODE_B;
2329                 }
2330         }
2331 #ifdef TO_DO_LIST //// TODO: this function doesn't work well at this time, we should wait for FPGA
2332         ActUpdateChannelAccessSetting(pAdapter, pHalData->CurrentWirelessMode, &pAdapter->MgntInfo.Info8185.ChannelAccessSetting);
2333 #endif
2334         priv->ieee80211->mode = wireless_mode;
2335 
2336         if ((wireless_mode == WIRELESS_MODE_N_24G) ||  (wireless_mode == WIRELESS_MODE_N_5G))
2337                 priv->ieee80211->pHTInfo->bEnableHT = 1;
2338         else
2339                 priv->ieee80211->pHTInfo->bEnableHT = 0;
2340         RT_TRACE(COMP_INIT, "Current Wireless Mode is %x\n", wireless_mode);
2341         rtl8192_refresh_supportrate(priv);
2342 
2343 }
2344 //init priv variables here. only non_zero value should be initialized here.
2345 static void rtl8192_init_priv_variable(struct net_device *dev)
2346 {
2347         struct r8192_priv *priv = ieee80211_priv(dev);
2348         u8 i;
2349         priv->card_8192 = NIC_8192U;
2350         priv->chan = 1; //set to channel 1
2351         priv->ieee80211->mode = WIRELESS_MODE_AUTO; //SET AUTO
2352         priv->ieee80211->iw_mode = IW_MODE_INFRA;
2353         priv->ieee80211->ieee_up = 0;
2354         priv->retry_rts = DEFAULT_RETRY_RTS;
2355         priv->retry_data = DEFAULT_RETRY_DATA;
2356         priv->ieee80211->rts = DEFAULT_RTS_THRESHOLD;
2357         priv->ieee80211->rate = 110; //11 mbps
2358         priv->ieee80211->short_slot = 1;
2359         priv->promisc = (dev->flags & IFF_PROMISC) ? 1 : 0;
2360         priv->CckPwEnl = 6;
2361         //for silent reset
2362         priv->IrpPendingCount = 1;
2363         priv->ResetProgress = RESET_TYPE_NORESET;
2364         priv->bForcedSilentReset = 0;
2365         priv->bDisableNormalResetCheck = false;
2366         priv->force_reset = false;
2367 
2368         priv->ieee80211->FwRWRF = 0;    //we don't use FW read/write RF until stable firmware is available.
2369         priv->ieee80211->current_network.beacon_interval = DEFAULT_BEACONINTERVAL;
2370         priv->ieee80211->iw_mode = IW_MODE_INFRA;
2371         priv->ieee80211->softmac_features  = IEEE_SOFTMAC_SCAN |
2372                 IEEE_SOFTMAC_ASSOCIATE | IEEE_SOFTMAC_PROBERQ |
2373                 IEEE_SOFTMAC_PROBERS | IEEE_SOFTMAC_TX_QUEUE |
2374                 IEEE_SOFTMAC_BEACONS;//added by amy 080604
2375 
2376         priv->ieee80211->active_scan = 1;
2377         priv->ieee80211->modulation = IEEE80211_CCK_MODULATION | IEEE80211_OFDM_MODULATION;
2378         priv->ieee80211->host_encrypt = 1;
2379         priv->ieee80211->host_decrypt = 1;
2380         priv->ieee80211->start_send_beacons = NULL; //-by amy 080604
2381         priv->ieee80211->stop_send_beacons = NULL;  //-by amy 080604
2382         priv->ieee80211->softmac_hard_start_xmit = rtl8192_hard_start_xmit;
2383         priv->ieee80211->set_chan = rtl8192_set_chan;
2384         priv->ieee80211->link_change = rtl8192_link_change;
2385         priv->ieee80211->softmac_data_hard_start_xmit = rtl8192_hard_data_xmit;
2386         priv->ieee80211->data_hard_stop = rtl8192_data_hard_stop;
2387         priv->ieee80211->data_hard_resume = rtl8192_data_hard_resume;
2388         priv->ieee80211->init_wmmparam_flag = 0;
2389         priv->ieee80211->fts = DEFAULT_FRAG_THRESHOLD;
2390         priv->ieee80211->check_nic_enough_desc = check_nic_enough_desc;
2391         priv->ieee80211->tx_headroom = TX_PACKET_SHIFT_BYTES;
2392         priv->ieee80211->qos_support = 1;
2393 
2394         //added by WB
2395         priv->ieee80211->SetBWModeHandler = rtl8192_SetBWMode;
2396         priv->ieee80211->handle_assoc_response = rtl8192_handle_assoc_response;
2397         priv->ieee80211->handle_beacon = rtl8192_handle_beacon;
2398         //added by david
2399         priv->ieee80211->GetNmodeSupportBySecCfg = GetNmodeSupportBySecCfg8192;
2400         priv->ieee80211->GetHalfNmodeSupportByAPsHandler = GetHalfNmodeSupportByAPs819xUsb;
2401         priv->ieee80211->SetWirelessMode = rtl8192_SetWirelessMode;
2402         //added by amy
2403         priv->ieee80211->InitialGainHandler = InitialGain819xUsb;
2404         priv->card_type = USB;
2405 #ifdef TO_DO_LIST
2406         if (Adapter->bInHctTest) {
2407                 pHalData->ShortRetryLimit = 7;
2408                 pHalData->LongRetryLimit = 7;
2409         }
2410 #endif
2411         priv->ShortRetryLimit = 0x30;
2412         priv->LongRetryLimit = 0x30;
2413         priv->EarlyRxThreshold = 7;
2414         priv->enable_gpio0 = 0;
2415         priv->TransmitConfig =
2416                 (TCR_MXDMA_2048<<TCR_MXDMA_OFFSET)|  // Max DMA Burst Size per Tx DMA Burst, 7: reserved.
2417                 (priv->ShortRetryLimit<<TCR_SRL_OFFSET)|        // Short retry limit
2418                 (priv->LongRetryLimit<<TCR_LRL_OFFSET) |        // Long retry limit
2419                 (false ? TCR_SAT : 0);  // FALSE: HW provides PLCP length and LENGEXT, TRUE: SW provides them
2420 #ifdef TO_DO_LIST
2421         if (Adapter->bInHctTest)
2422                 pHalData->ReceiveConfig =       pHalData->CSMethod |
2423                                                 RCR_AMF | RCR_ADF |     //accept management/data
2424                                                 //guangan200710
2425                                                 RCR_ACF |       //accept control frame for SW AP needs PS-poll, 2005.07.07, by rcnjko.
2426                                                 RCR_AB | RCR_AM | RCR_APM |             //accept BC/MC/UC
2427                                                 RCR_AICV | RCR_ACRC32 |                 //accept ICV/CRC error packet
2428                                                 ((u32)7<<RCR_MXDMA_OFFSET) | // Max DMA Burst Size per Rx DMA Burst, 7: unlimited.
2429                                                 (pHalData->EarlyRxThreshold<<RCR_FIFO_OFFSET) | // Rx FIFO Threshold, 7: No Rx threshold.
2430                                                 (pHalData->EarlyRxThreshold == 7 ? RCR_OnlyErlPkt : 0);
2431         else
2432 
2433 #endif
2434         priv->ReceiveConfig     =
2435                 RCR_AMF | RCR_ADF |             //accept management/data
2436                 RCR_ACF |                       //accept control frame for SW AP needs PS-poll, 2005.07.07, by rcnjko.
2437                 RCR_AB | RCR_AM | RCR_APM |     //accept BC/MC/UC
2438                 ((u32)7<<RCR_MXDMA_OFFSET)| // Max DMA Burst Size per Rx DMA Burst, 7: unlimited.
2439                 (priv->EarlyRxThreshold<<RX_FIFO_THRESHOLD_SHIFT) | // Rx FIFO Threshold, 7: No Rx threshold.
2440                 (priv->EarlyRxThreshold == 7 ? RCR_ONLYERLPKT : 0);
2441 
2442         priv->AcmControl = 0;
2443         priv->pFirmware = kzalloc(sizeof(rt_firmware), GFP_KERNEL);
2444 
2445         /* rx related queue */
2446         skb_queue_head_init(&priv->rx_queue);
2447         skb_queue_head_init(&priv->skb_queue);
2448 
2449         /* Tx related queue */
2450         for (i = 0; i < MAX_QUEUE_SIZE; i++)
2451                 skb_queue_head_init(&priv->ieee80211->skb_waitQ[i]);
2452         for (i = 0; i < MAX_QUEUE_SIZE; i++)
2453                 skb_queue_head_init(&priv->ieee80211->skb_aggQ[i]);
2454         for (i = 0; i < MAX_QUEUE_SIZE; i++)
2455                 skb_queue_head_init(&priv->ieee80211->skb_drv_aggQ[i]);
2456         priv->rf_set_chan = rtl8192_phy_SwChnl;
2457 }
2458 
2459 //init lock here
2460 static void rtl8192_init_priv_lock(struct r8192_priv *priv)
2461 {
2462         spin_lock_init(&priv->tx_lock);
2463         spin_lock_init(&priv->irq_lock);//added by thomas
2464         sema_init(&priv->wx_sem, 1);
2465         sema_init(&priv->rf_sem, 1);
2466         mutex_init(&priv->mutex);
2467 }
2468 
2469 extern  void    rtl819x_watchdog_wqcallback(struct work_struct *work);
2470 
2471 void rtl8192_irq_rx_tasklet(struct r8192_priv *priv);
2472 //init tasklet and wait_queue here. only 2.6 above kernel is considered
2473 #define DRV_NAME "wlan0"
2474 static void rtl8192_init_priv_task(struct net_device *dev)
2475 {
2476         struct r8192_priv *priv = ieee80211_priv(dev);
2477 
2478         priv->priv_wq = create_workqueue(DRV_NAME);
2479 
2480         INIT_WORK(&priv->reset_wq, rtl8192_restart);
2481 
2482         INIT_DELAYED_WORK(&priv->watch_dog_wq, rtl819x_watchdog_wqcallback);
2483         INIT_DELAYED_WORK(&priv->txpower_tracking_wq,  dm_txpower_trackingcallback);
2484         INIT_DELAYED_WORK(&priv->rfpath_check_wq,  dm_rf_pathcheck_workitemcallback);
2485         INIT_DELAYED_WORK(&priv->update_beacon_wq, rtl8192_update_beacon);
2486         INIT_DELAYED_WORK(&priv->initialgain_operate_wq, InitialGainOperateWorkItemCallBack);
2487         INIT_WORK(&priv->qos_activate, rtl8192_qos_activate);
2488 
2489         tasklet_init(&priv->irq_rx_tasklet,
2490                      (void(*)(unsigned long))rtl8192_irq_rx_tasklet,
2491                      (unsigned long)priv);
2492 }
2493 
2494 static void rtl8192_get_eeprom_size(struct net_device *dev)
2495 {
2496         u16 curCR = 0;
2497         struct r8192_priv *priv = ieee80211_priv(dev);
2498         RT_TRACE(COMP_EPROM, "===========>%s()\n", __func__);
2499         read_nic_word_E(dev, EPROM_CMD, &curCR);
2500         RT_TRACE(COMP_EPROM, "read from Reg EPROM_CMD(%x):%x\n", EPROM_CMD, curCR);
2501         //whether need I consider BIT5?
2502         priv->epromtype = (curCR & Cmd9346CR_9356SEL) ? EPROM_93c56 : EPROM_93c46;
2503         RT_TRACE(COMP_EPROM, "<===========%s(), epromtype:%d\n", __func__, priv->epromtype);
2504 }
2505 
2506 //used to swap endian. as ntohl & htonl are not necessary to swap endian, so use this instead.
2507 static inline u16 endian_swap(u16 *data)
2508 {
2509         u16 tmp = *data;
2510         *data = (tmp >> 8) | (tmp << 8);
2511         return *data;
2512 }
2513 static void rtl8192_read_eeprom_info(struct net_device *dev)
2514 {
2515         u16 wEPROM_ID = 0;
2516         u8 bMac_Tmp_Addr[6] = {0x00, 0xe0, 0x4c, 0x00, 0x00, 0x02};
2517         u8 bLoad_From_EEPOM = false;
2518         struct r8192_priv *priv = ieee80211_priv(dev);
2519         u16 tmpValue = 0;
2520         int i;
2521         RT_TRACE(COMP_EPROM, "===========>%s()\n", __func__);
2522         wEPROM_ID = eprom_read(dev, 0); //first read EEPROM ID out;
2523         RT_TRACE(COMP_EPROM, "EEPROM ID is 0x%x\n", wEPROM_ID);
2524 
2525         if (wEPROM_ID != RTL8190_EEPROM_ID) {
2526                 RT_TRACE(COMP_ERR, "EEPROM ID is invalid(is 0x%x(should be 0x%x)\n", wEPROM_ID, RTL8190_EEPROM_ID);
2527         } else {
2528                 bLoad_From_EEPOM = true;
2529         }
2530 
2531         if (bLoad_From_EEPOM) {
2532                 tmpValue = eprom_read(dev, (EEPROM_VID>>1));
2533                 priv->eeprom_vid = endian_swap(&tmpValue);
2534                 priv->eeprom_pid = eprom_read(dev, (EEPROM_PID>>1));
2535                 tmpValue = eprom_read(dev, (EEPROM_ChannelPlan>>1));
2536                 priv->eeprom_ChannelPlan = ((tmpValue&0xff00)>>8);
2537                 priv->btxpowerdata_readfromEEPORM = true;
2538                 priv->eeprom_CustomerID = eprom_read(dev, (EEPROM_Customer_ID>>1)) >>8;
2539         } else {
2540                 priv->eeprom_vid = 0;
2541                 priv->eeprom_pid = 0;
2542                 priv->card_8192_version = VERSION_819xU_B;
2543                 priv->eeprom_ChannelPlan = 0;
2544                 priv->eeprom_CustomerID = 0;
2545         }
2546         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);
2547         //set channelplan from eeprom
2548         priv->ChannelPlan = priv->eeprom_ChannelPlan;
2549         if (bLoad_From_EEPOM) {
2550                 int i;
2551                 for (i = 0; i < 6; i += 2) {
2552                         u16 tmp = 0;
2553                         tmp = eprom_read(dev, (u16)((EEPROM_NODE_ADDRESS_BYTE_0 + i)>>1));
2554                         *(u16 *)(&dev->dev_addr[i]) = tmp;
2555                 }
2556         } else {
2557                 memcpy(dev->dev_addr, bMac_Tmp_Addr, 6);
2558                 //should I set IDR0 here?
2559         }
2560         RT_TRACE(COMP_EPROM, "MAC addr:%pM\n", dev->dev_addr);
2561         priv->rf_type = RTL819X_DEFAULT_RF_TYPE; //default 1T2R
2562         priv->rf_chip = RF_8256;
2563 
2564         if (priv->card_8192_version == (u8)VERSION_819xU_A) {
2565                 //read Tx power gain offset of legacy OFDM to HT rate
2566                 if (bLoad_From_EEPOM)
2567                         priv->EEPROMTxPowerDiff = (eprom_read(dev, (EEPROM_TxPowerDiff>>1))&0xff00) >> 8;
2568                 else
2569                         priv->EEPROMTxPowerDiff = EEPROM_Default_TxPower;
2570                 RT_TRACE(COMP_EPROM, "TxPowerDiff:%d\n", priv->EEPROMTxPowerDiff);
2571                 //read ThermalMeter from EEPROM
2572                 if (bLoad_From_EEPOM)
2573                         priv->EEPROMThermalMeter = (u8)(eprom_read(dev, (EEPROM_ThermalMeter>>1))&0x00ff);
2574                 else
2575                         priv->EEPROMThermalMeter = EEPROM_Default_ThermalMeter;
2576                 RT_TRACE(COMP_EPROM, "ThermalMeter:%d\n", priv->EEPROMThermalMeter);
2577                 //vivi, for tx power track
2578                 priv->TSSI_13dBm = priv->EEPROMThermalMeter *100;
2579                 //read antenna tx power offset of B/C/D to A from EEPROM
2580                 if (bLoad_From_EEPOM)
2581                         priv->EEPROMPwDiff = (eprom_read(dev, (EEPROM_PwDiff>>1))&0x0f00)>>8;
2582                 else
2583                         priv->EEPROMPwDiff = EEPROM_Default_PwDiff;
2584                 RT_TRACE(COMP_EPROM, "TxPwDiff:%d\n", priv->EEPROMPwDiff);
2585                 // Read CrystalCap from EEPROM
2586                 if (bLoad_From_EEPOM)
2587                         priv->EEPROMCrystalCap = (eprom_read(dev, (EEPROM_CrystalCap>>1))&0x0f);
2588                 else
2589                         priv->EEPROMCrystalCap = EEPROM_Default_CrystalCap;
2590                 RT_TRACE(COMP_EPROM, "CrystalCap = %d\n", priv->EEPROMCrystalCap);
2591                 //get per-channel Tx power level
2592                 if (bLoad_From_EEPOM)
2593                         priv->EEPROM_Def_Ver = (eprom_read(dev, (EEPROM_TxPwIndex_Ver>>1))&0xff00)>>8;
2594                 else
2595                         priv->EEPROM_Def_Ver = 1;
2596                 RT_TRACE(COMP_EPROM, "EEPROM_DEF_VER:%d\n", priv->EEPROM_Def_Ver);
2597                 if (priv->EEPROM_Def_Ver == 0) { //old eeprom definition
2598                         int i;
2599                         if (bLoad_From_EEPOM)
2600                                 priv->EEPROMTxPowerLevelCCK = (eprom_read(dev, (EEPROM_TxPwIndex_CCK>>1))&0xff) >> 8;
2601                         else
2602                                 priv->EEPROMTxPowerLevelCCK = 0x10;
2603                         RT_TRACE(COMP_EPROM, "CCK Tx Power Levl: 0x%02x\n", priv->EEPROMTxPowerLevelCCK);
2604                         for (i = 0; i < 3; i++) {
2605                                 if (bLoad_From_EEPOM) {
2606                                         tmpValue = eprom_read(dev, (EEPROM_TxPwIndex_OFDM_24G+i)>>1);
2607                                         if (((EEPROM_TxPwIndex_OFDM_24G+i) % 2) == 0)
2608                                                 tmpValue = tmpValue & 0x00ff;
2609                                         else
2610                                                 tmpValue = (tmpValue & 0xff00) >> 8;
2611                                 } else {
2612                                         tmpValue = 0x10;
2613                                 }
2614                                 priv->EEPROMTxPowerLevelOFDM24G[i] = (u8) tmpValue;
2615                                 RT_TRACE(COMP_EPROM, "OFDM 2.4G Tx Power Level, Index %d = 0x%02x\n", i, priv->EEPROMTxPowerLevelCCK);
2616                         }
2617                 } else if (priv->EEPROM_Def_Ver == 1) {
2618                         if (bLoad_From_EEPOM) {
2619                                 tmpValue = eprom_read(dev, (EEPROM_TxPwIndex_CCK_V1>>1));
2620                                 tmpValue = (tmpValue & 0xff00) >> 8;
2621                         } else {
2622                                 tmpValue = 0x10;
2623                         }
2624                         priv->EEPROMTxPowerLevelCCK_V1[0] = (u8)tmpValue;
2625 
2626                         if (bLoad_From_EEPOM)
2627                                 tmpValue = eprom_read(dev, (EEPROM_TxPwIndex_CCK_V1 + 2)>>1);
2628                         else
2629                                 tmpValue = 0x1010;
2630                         *((u16 *)(&priv->EEPROMTxPowerLevelCCK_V1[1])) = tmpValue;
2631                         if (bLoad_From_EEPOM)
2632                                 tmpValue = eprom_read(dev, (EEPROM_TxPwIndex_OFDM_24G_V1>>1));
2633                         else
2634                                 tmpValue = 0x1010;
2635                         *((u16 *)(&priv->EEPROMTxPowerLevelOFDM24G[0])) = tmpValue;
2636                         if (bLoad_From_EEPOM)
2637                                 tmpValue = eprom_read(dev, (EEPROM_TxPwIndex_OFDM_24G_V1+2)>>1);
2638                         else
2639                                 tmpValue = 0x10;
2640                         priv->EEPROMTxPowerLevelOFDM24G[2] = (u8)tmpValue;
2641                 }//endif EEPROM_Def_Ver == 1
2642 
2643                 //update HAL variables
2644                 //
2645                 for (i = 0; i < 14; i++) {
2646                         if (i <= 3)
2647                                 priv->TxPowerLevelOFDM24G[i] = priv->EEPROMTxPowerLevelOFDM24G[0];
2648                         else if (i >= 4 && i <= 9)
2649                                 priv->TxPowerLevelOFDM24G[i] = priv->EEPROMTxPowerLevelOFDM24G[1];
2650                         else
2651                                 priv->TxPowerLevelOFDM24G[i] = priv->EEPROMTxPowerLevelOFDM24G[2];
2652                 }
2653 
2654                 for (i = 0; i < 14; i++) {
2655                         if (priv->EEPROM_Def_Ver == 0) {
2656                                 if (i <= 3)
2657                                         priv->TxPowerLevelCCK[i] = priv->EEPROMTxPowerLevelOFDM24G[0] + (priv->EEPROMTxPowerLevelCCK - priv->EEPROMTxPowerLevelOFDM24G[1]);
2658                                 else if (i >= 4 && i <= 9)
2659                                         priv->TxPowerLevelCCK[i] = priv->EEPROMTxPowerLevelCCK;
2660                                 else
2661                                         priv->TxPowerLevelCCK[i] = priv->EEPROMTxPowerLevelOFDM24G[2] + (priv->EEPROMTxPowerLevelCCK - priv->EEPROMTxPowerLevelOFDM24G[1]);
2662                         } else if (priv->EEPROM_Def_Ver == 1) {
2663                                 if (i <= 3)
2664                                         priv->TxPowerLevelCCK[i] = priv->EEPROMTxPowerLevelCCK_V1[0];
2665                                 else if (i >= 4 && i <= 9)
2666                                         priv->TxPowerLevelCCK[i] = priv->EEPROMTxPowerLevelCCK_V1[1];
2667                                 else
2668                                         priv->TxPowerLevelCCK[i] = priv->EEPROMTxPowerLevelCCK_V1[2];
2669                         }
2670                 }
2671                 priv->TxPowerDiff = priv->EEPROMPwDiff;
2672                 // Antenna B gain offset to antenna A, bit0~3
2673                 priv->AntennaTxPwDiff[0] = (priv->EEPROMTxPowerDiff & 0xf);
2674                 // Antenna C gain offset to antenna A, bit4~7
2675                 priv->AntennaTxPwDiff[1] = ((priv->EEPROMTxPowerDiff & 0xf0)>>4);
2676                 // CrystalCap, bit12~15
2677                 priv->CrystalCap = priv->EEPROMCrystalCap;
2678                 // ThermalMeter, bit0~3 for RFIC1, bit4~7 for RFIC2
2679                 // 92U does not enable TX power tracking.
2680                 priv->ThermalMeter[0] = priv->EEPROMThermalMeter;
2681         }//end if VersionID == VERSION_819xU_A
2682 
2683         //added by vivi, for dlink led, 20080416
2684         switch (priv->eeprom_CustomerID) {
2685         case EEPROM_CID_RUNTOP:
2686                 priv->CustomerID = RT_CID_819x_RUNTOP;
2687                 break;
2688 
2689         case EEPROM_CID_DLINK:
2690                 priv->CustomerID = RT_CID_DLINK;
2691                 break;
2692 
2693         default:
2694                 priv->CustomerID = RT_CID_DEFAULT;
2695                 break;
2696 
2697         }
2698 
2699         switch (priv->CustomerID) {
2700         case RT_CID_819x_RUNTOP:
2701                 priv->LedStrategy = SW_LED_MODE2;
2702                 break;
2703 
2704         case RT_CID_DLINK:
2705                 priv->LedStrategy = SW_LED_MODE4;
2706                 break;
2707 
2708         default:
2709                 priv->LedStrategy = SW_LED_MODE0;
2710                 break;
2711 
2712         }
2713 
2714 
2715         if (priv->rf_type == RF_1T2R) {
2716                 RT_TRACE(COMP_EPROM, "\n1T2R config\n");
2717         } else {
2718                 RT_TRACE(COMP_EPROM, "\n2T4R config\n");
2719         }
2720 
2721         // 2008/01/16 MH We can only know RF type in the function. So we have to init
2722         // DIG RATR table again.
2723         init_rate_adaptive(dev);
2724         //we need init DIG RATR table here again.
2725 
2726         RT_TRACE(COMP_EPROM, "<===========%s()\n", __func__);
2727         return;
2728 }
2729 
2730 static short rtl8192_get_channel_map(struct net_device *dev)
2731 {
2732         struct r8192_priv *priv = ieee80211_priv(dev);
2733         if (priv->ChannelPlan > COUNTRY_CODE_GLOBAL_DOMAIN) {
2734                 netdev_err(dev, "rtl8180_init: Error channel plan! Set to default.\n");
2735                 priv->ChannelPlan = 0;
2736         }
2737         RT_TRACE(COMP_INIT, "Channel plan is %d\n", priv->ChannelPlan);
2738 
2739         rtl819x_set_channel_map(priv->ChannelPlan, priv);
2740         return 0;
2741 }
2742 
2743 static short rtl8192_init(struct net_device *dev)
2744 {
2745 
2746         struct r8192_priv *priv = ieee80211_priv(dev);
2747 
2748         memset(&(priv->stats), 0, sizeof(struct Stats));
2749         memset(priv->txqueue_to_outpipemap, 0, 9);
2750 #ifdef PIPE12
2751         {
2752                 int i = 0;
2753                 u8 queuetopipe[] = {3, 2, 1, 0, 4, 8, 7, 6, 5};
2754                 memcpy(priv->txqueue_to_outpipemap, queuetopipe, 9);
2755         }
2756 #else
2757         {
2758                 u8 queuetopipe[] = {3, 2, 1, 0, 4, 4, 0, 4, 4};
2759                 memcpy(priv->txqueue_to_outpipemap, queuetopipe, 9);
2760         }
2761 #endif
2762         rtl8192_init_priv_variable(dev);
2763         rtl8192_init_priv_lock(priv);
2764         rtl8192_init_priv_task(dev);
2765         rtl8192_get_eeprom_size(dev);
2766         rtl8192_read_eeprom_info(dev);
2767         rtl8192_get_channel_map(dev);
2768         init_hal_dm(dev);
2769         init_timer(&priv->watch_dog_timer);
2770         priv->watch_dog_timer.data = (unsigned long)dev;
2771         priv->watch_dog_timer.function = watch_dog_timer_callback;
2772         if (rtl8192_usb_initendpoints(dev) != 0) {
2773                 DMESG("Endopoints initialization failed");
2774                 return -ENOMEM;
2775         }
2776 
2777 #ifdef DEBUG_EPROM
2778         dump_eprom(dev);
2779 #endif
2780         return 0;
2781 }
2782 
2783 /******************************************************************************
2784  *function:  This function actually only set RRSR, RATR and BW_OPMODE registers
2785  *           not to do all the hw config as its name says
2786  *   input:  net_device dev
2787  *  output:  none
2788  *  return:  none
2789  *  notice:  This part need to modified according to the rate set we filtered
2790  * ****************************************************************************/
2791 static void rtl8192_hwconfig(struct net_device *dev)
2792 {
2793         u32 regRATR = 0, regRRSR = 0;
2794         u8 regBwOpMode = 0, regTmp = 0;
2795         struct r8192_priv *priv = ieee80211_priv(dev);
2796         u32 ratr_value = 0;
2797 
2798         // Set RRSR, RATR, and BW_OPMODE registers
2799         //
2800         switch (priv->ieee80211->mode) {
2801         case WIRELESS_MODE_B:
2802                 regBwOpMode = BW_OPMODE_20MHZ;
2803                 regRATR = RATE_ALL_CCK;
2804                 regRRSR = RATE_ALL_CCK;
2805                 break;
2806         case WIRELESS_MODE_A:
2807                 regBwOpMode = BW_OPMODE_5G |BW_OPMODE_20MHZ;
2808                 regRATR = RATE_ALL_OFDM_AG;
2809                 regRRSR = RATE_ALL_OFDM_AG;
2810                 break;
2811         case WIRELESS_MODE_G:
2812                 regBwOpMode = BW_OPMODE_20MHZ;
2813                 regRATR = RATE_ALL_CCK | RATE_ALL_OFDM_AG;
2814                 regRRSR = RATE_ALL_CCK | RATE_ALL_OFDM_AG;
2815                 break;
2816         case WIRELESS_MODE_AUTO:
2817 #ifdef TO_DO_LIST
2818                 if (Adapter->bInHctTest) {
2819                         regBwOpMode = BW_OPMODE_20MHZ;
2820                         regRATR = RATE_ALL_CCK | RATE_ALL_OFDM_AG;
2821                         regRRSR = RATE_ALL_CCK | RATE_ALL_OFDM_AG;
2822                 }
2823                 else
2824 #endif
2825                 {
2826                         regBwOpMode = BW_OPMODE_20MHZ;
2827                         regRATR = RATE_ALL_CCK | RATE_ALL_OFDM_AG | RATE_ALL_OFDM_1SS | RATE_ALL_OFDM_2SS;
2828                         regRRSR = RATE_ALL_CCK | RATE_ALL_OFDM_AG;
2829                 }
2830                 break;
2831         case WIRELESS_MODE_N_24G:
2832                 // It support CCK rate by default.
2833                 // CCK rate will be filtered out only when associated AP does not support it.
2834                 regBwOpMode = BW_OPMODE_20MHZ;
2835                 regRATR = RATE_ALL_CCK | RATE_ALL_OFDM_AG | RATE_ALL_OFDM_1SS | RATE_ALL_OFDM_2SS;
2836                 regRRSR = RATE_ALL_CCK | RATE_ALL_OFDM_AG;
2837                 break;
2838         case WIRELESS_MODE_N_5G:
2839                 regBwOpMode = BW_OPMODE_5G;
2840                 regRATR = RATE_ALL_OFDM_AG | RATE_ALL_OFDM_1SS | RATE_ALL_OFDM_2SS;
2841                 regRRSR = RATE_ALL_OFDM_AG;
2842                 break;
2843         }
2844 
2845         write_nic_byte(dev, BW_OPMODE, regBwOpMode);
2846         ratr_value = regRATR;
2847         if (priv->rf_type == RF_1T2R)
2848                 ratr_value &= ~(RATE_ALL_OFDM_2SS);
2849         write_nic_dword(dev, RATR0, ratr_value);
2850         write_nic_byte(dev, UFWP, 1);
2851         read_nic_byte(dev, 0x313, &regTmp);
2852         regRRSR = ((regTmp) << 24) | (regRRSR & 0x00ffffff);
2853         write_nic_dword(dev, RRSR, regRRSR);
2854 
2855         //
2856         // Set Retry Limit here
2857         //
2858         write_nic_word(dev, RETRY_LIMIT,
2859                        priv->ShortRetryLimit << RETRY_LIMIT_SHORT_SHIFT |
2860                        priv->LongRetryLimit << RETRY_LIMIT_LONG_SHIFT);
2861         // Set Contention Window here
2862 
2863         // Set Tx AGC
2864 
2865         // Set Tx Antenna including Feedback control
2866 
2867         // Set Auto Rate fallback control
2868 
2869 
2870 }
2871 
2872 
2873 //InitializeAdapter and PhyCfg
2874 static bool rtl8192_adapter_start(struct net_device *dev)
2875 {
2876         struct r8192_priv *priv = ieee80211_priv(dev);
2877         u32 dwRegRead = 0;
2878         bool init_status = true;
2879         u8 SECR_value = 0x0;
2880         u8 tmp;
2881         RT_TRACE(COMP_INIT, "====>%s()\n", __func__);
2882         priv->Rf_Mode = RF_OP_By_SW_3wire;
2883         //for ASIC power on sequence
2884         write_nic_byte_E(dev, 0x5f, 0x80);
2885         mdelay(50);
2886         write_nic_byte_E(dev, 0x5f, 0xf0);
2887         write_nic_byte_E(dev, 0x5d, 0x00);
2888         write_nic_byte_E(dev, 0x5e, 0x80);
2889         write_nic_byte(dev, 0x17, 0x37);
2890         mdelay(10);
2891         priv->pFirmware->firmware_status = FW_STATUS_0_INIT;
2892         //config CPUReset Register
2893         //Firmware Reset or not?
2894         read_nic_dword(dev, CPU_GEN, &dwRegRead);
2895         if (priv->pFirmware->firmware_status == FW_STATUS_0_INIT)
2896                 dwRegRead |= CPU_GEN_SYSTEM_RESET; //do nothing here?
2897         else if (priv->pFirmware->firmware_status == FW_STATUS_5_READY)
2898                 dwRegRead |= CPU_GEN_FIRMWARE_RESET;
2899         else
2900                 RT_TRACE(COMP_ERR, "ERROR in %s(): undefined firmware state(%d)\n", __func__,   priv->pFirmware->firmware_status);
2901 
2902         write_nic_dword(dev, CPU_GEN, dwRegRead);
2903         //config BB.
2904         rtl8192_BBConfig(dev);
2905 
2906         //Loopback mode or not
2907         priv->LoopbackMode = RTL819xU_NO_LOOPBACK;
2908 
2909         read_nic_dword(dev, CPU_GEN, &dwRegRead);
2910         if (priv->LoopbackMode == RTL819xU_NO_LOOPBACK)
2911                 dwRegRead = ((dwRegRead & CPU_GEN_NO_LOOPBACK_MSK) | CPU_GEN_NO_LOOPBACK_SET);
2912         else if (priv->LoopbackMode == RTL819xU_MAC_LOOPBACK)
2913                 dwRegRead |= CPU_CCK_LOOPBACK;
2914         else
2915                 RT_TRACE(COMP_ERR, "Serious error in %s(): wrong loopback mode setting(%d)\n", __func__,  priv->LoopbackMode);
2916 
2917         write_nic_dword(dev, CPU_GEN, dwRegRead);
2918 
2919         //after reset cpu, we need wait for a seconds to write in register.
2920         udelay(500);
2921 
2922         //xiong add for new bitfile:usb suspend reset pin set to 1. //do we need?
2923         read_nic_byte_E(dev, 0x5f, &tmp);
2924         write_nic_byte_E(dev, 0x5f, tmp|0x20);
2925 
2926         //Set Hardware
2927         rtl8192_hwconfig(dev);
2928 
2929         //turn on Tx/Rx
2930         write_nic_byte(dev, CMDR, CR_RE|CR_TE);
2931 
2932         //set IDR0 here
2933         write_nic_dword(dev, MAC0, ((u32 *)dev->dev_addr)[0]);
2934         write_nic_word(dev, MAC4, ((u16 *)(dev->dev_addr + 4))[0]);
2935 
2936         //set RCR
2937         write_nic_dword(dev, RCR, priv->ReceiveConfig);
2938 
2939         //Initialize Number of Reserved Pages in Firmware Queue
2940         write_nic_dword(dev, RQPN1,  NUM_OF_PAGE_IN_FW_QUEUE_BK << RSVD_FW_QUEUE_PAGE_BK_SHIFT |
2941                         NUM_OF_PAGE_IN_FW_QUEUE_BE << RSVD_FW_QUEUE_PAGE_BE_SHIFT |
2942                         NUM_OF_PAGE_IN_FW_QUEUE_VI << RSVD_FW_QUEUE_PAGE_VI_SHIFT |
2943                         NUM_OF_PAGE_IN_FW_QUEUE_VO <<RSVD_FW_QUEUE_PAGE_VO_SHIFT);
2944         write_nic_dword(dev, RQPN2, NUM_OF_PAGE_IN_FW_QUEUE_MGNT << RSVD_FW_QUEUE_PAGE_MGNT_SHIFT |
2945                         NUM_OF_PAGE_IN_FW_QUEUE_CMD << RSVD_FW_QUEUE_PAGE_CMD_SHIFT);
2946         write_nic_dword(dev, RQPN3, APPLIED_RESERVED_QUEUE_IN_FW|
2947                         NUM_OF_PAGE_IN_FW_QUEUE_BCN<<RSVD_FW_QUEUE_PAGE_BCN_SHIFT);
2948         write_nic_dword(dev, RATR0+4*7, (RATE_ALL_OFDM_AG | RATE_ALL_CCK));
2949 
2950         //Set AckTimeout
2951         // TODO: (it value is only for FPGA version). need to be changed!!2006.12.18, by Emily
2952         write_nic_byte(dev, ACK_TIMEOUT, 0x30);
2953 
2954         if (priv->ResetProgress == RESET_TYPE_NORESET)
2955                 rtl8192_SetWirelessMode(dev, priv->ieee80211->mode);
2956         if (priv->ResetProgress == RESET_TYPE_NORESET) {
2957                 CamResetAllEntry(dev);
2958                 SECR_value |= SCR_TxEncEnable;
2959                 SECR_value |= SCR_RxDecEnable;
2960                 SECR_value |= SCR_NoSKMC;
2961                 write_nic_byte(dev, SECR, SECR_value);
2962         }
2963 
2964         //Beacon related
2965         write_nic_word(dev, ATIMWND, 2);
2966         write_nic_word(dev, BCN_INTERVAL, 100);
2967 
2968 #define DEFAULT_EDCA 0x005e4332
2969         {
2970                 int i;
2971                 for (i = 0; i < QOS_QUEUE_NUM; i++)
2972                         write_nic_dword(dev, WDCAPARA_ADD[i], DEFAULT_EDCA);
2973         }
2974 #ifdef USB_RX_AGGREGATION_SUPPORT
2975         //3 For usb rx firmware aggregation control
2976         if (priv->ResetProgress == RESET_TYPE_NORESET) {
2977                 u32 ulValue;
2978                 PRT_HIGH_THROUGHPUT     pHTInfo = priv->ieee80211->pHTInfo;
2979                 ulValue = (pHTInfo->UsbRxFwAggrEn<<24) | (pHTInfo->UsbRxFwAggrPageNum<<16) |
2980                           (pHTInfo->UsbRxFwAggrPacketNum<<8) | (pHTInfo->UsbRxFwAggrTimeout);
2981                 /*
2982                  * If usb rx firmware aggregation is enabled,
2983                  * when anyone of three threshold conditions above is reached,
2984                  * firmware will send aggregated packet to driver.
2985                  */
2986                 write_nic_dword(dev, 0x1a8, ulValue);
2987                 priv->bCurrentRxAggrEnable = true;
2988         }
2989 #endif
2990 
2991         rtl8192_phy_configmac(dev);
2992 
2993         if (priv->card_8192_version == (u8) VERSION_819xU_A) {
2994                 rtl8192_phy_getTxPower(dev);
2995                 rtl8192_phy_setTxPower(dev, priv->chan);
2996         }
2997 
2998         //Firmware download
2999         init_status = init_firmware(dev);
3000         if (!init_status) {
3001                 RT_TRACE(COMP_ERR, "ERR!!! %s(): Firmware download is failed\n", __func__);
3002                 return init_status;
3003         }
3004         RT_TRACE(COMP_INIT, "%s():after firmware download\n", __func__);
3005         //
3006 #ifdef TO_DO_LIST
3007         if (Adapter->ResetProgress == RESET_TYPE_NORESET) {
3008                 if (pMgntInfo->RegRfOff == TRUE) { // User disable RF via registry.
3009                         RT_TRACE((COMP_INIT|COMP_RF), DBG_LOUD, ("InitializeAdapter819xUsb(): Turn off RF for RegRfOff ----------\n"));
3010                         MgntActSet_RF_State(Adapter, eRfOff, RF_CHANGE_BY_SW);
3011                         // Those actions will be discard in MgntActSet_RF_State because of the same state
3012                         for (eRFPath = 0; eRFPath < pHalData->NumTotalRFPath; eRFPath++)
3013                                 PHY_SetRFReg(Adapter, (RF90_RADIO_PATH_E)eRFPath, 0x4, 0xC00, 0x0);
3014                 } else if (pMgntInfo->RfOffReason > RF_CHANGE_BY_PS) { // H/W or S/W RF OFF before sleep.
3015                         RT_TRACE((COMP_INIT|COMP_RF), DBG_LOUD, ("InitializeAdapter819xUsb(): Turn off RF for RfOffReason(%d) ----------\n", pMgntInfo->RfOffReason));
3016                         MgntActSet_RF_State(Adapter, eRfOff, pMgntInfo->RfOffReason);
3017                 } else {
3018                         pHalData->eRFPowerState = eRfOn;
3019                         pMgntInfo->RfOffReason = 0;
3020                         RT_TRACE((COMP_INIT|COMP_RF), DBG_LOUD, ("InitializeAdapter819xUsb(): RF is on ----------\n"));
3021                 }
3022         } else {
3023                 if (pHalData->eRFPowerState == eRfOff) {
3024                         MgntActSet_RF_State(Adapter, eRfOff, pMgntInfo->RfOffReason);
3025                         // Those actions will be discard in MgntActSet_RF_State because of the same state
3026                         for (eRFPath = 0; eRFPath < pHalData->NumTotalRFPath; eRFPath++)
3027                                 PHY_SetRFReg(Adapter, (RF90_RADIO_PATH_E)eRFPath, 0x4, 0xC00, 0x0);
3028                 }
3029         }
3030 #endif
3031         //config RF.
3032         if (priv->ResetProgress == RESET_TYPE_NORESET) {
3033                 rtl8192_phy_RFConfig(dev);
3034                 RT_TRACE(COMP_INIT, "%s():after phy RF config\n", __func__);
3035         }
3036 
3037 
3038         if (priv->ieee80211->FwRWRF)
3039                 // We can force firmware to do RF-R/W
3040                 priv->Rf_Mode = RF_OP_By_FW;
3041         else
3042                 priv->Rf_Mode = RF_OP_By_SW_3wire;
3043 
3044 
3045         rtl8192_phy_updateInitGain(dev);
3046         /*--set CCK and OFDM Block "ON"--*/
3047         rtl8192_setBBreg(dev, rFPGA0_RFMOD, bCCKEn, 0x1);
3048         rtl8192_setBBreg(dev, rFPGA0_RFMOD, bOFDMEn, 0x1);
3049 
3050         if (priv->ResetProgress == RESET_TYPE_NORESET) {
3051                 //if D or C cut
3052                 u8 tmpvalue;
3053                 read_nic_byte(dev, 0x301, &tmpvalue);
3054                 if (tmpvalue == 0x03) {
3055                         priv->bDcut = TRUE;
3056                         RT_TRACE(COMP_POWER_TRACKING, "D-cut\n");
3057                 } else {
3058                         priv->bDcut = FALSE;
3059                         RT_TRACE(COMP_POWER_TRACKING, "C-cut\n");
3060                 }
3061                 dm_initialize_txpower_tracking(dev);
3062 
3063                 if (priv->bDcut == TRUE) {
3064                         u32 i, TempCCk;
3065                         u32 tmpRegA = rtl8192_QueryBBReg(dev, rOFDM0_XATxIQImbalance, bMaskDWord);
3066                         for (i = 0; i < TxBBGainTableLength; i++) {
3067                                 if (tmpRegA == priv->txbbgain_table[i].txbbgain_value) {
3068                                         priv->rfa_txpowertrackingindex = (u8)i;
3069                                         priv->rfa_txpowertrackingindex_real = (u8)i;
3070                                         priv->rfa_txpowertracking_default = priv->rfa_txpowertrackingindex;
3071                                         break;
3072                                 }
3073                         }
3074 
3075                         TempCCk = rtl8192_QueryBBReg(dev, rCCK0_TxFilter1, bMaskByte2);
3076 
3077                         for (i = 0; i < CCKTxBBGainTableLength; i++) {
3078 
3079                                 if (TempCCk == priv->cck_txbbgain_table[i].ccktxbb_valuearray[0]) {
3080                                         priv->cck_present_attentuation_20Mdefault = (u8) i;
3081                                         break;
3082                                 }
3083                         }
3084                         priv->cck_present_attentuation_40Mdefault = 0;
3085                         priv->cck_present_attentuation_difference = 0;
3086                         priv->cck_present_attentuation = priv->cck_present_attentuation_20Mdefault;
3087 
3088                 }
3089         }
3090         write_nic_byte(dev, 0x87, 0x0);
3091 
3092 
3093         return init_status;
3094 }
3095 
3096 /* this configures registers for beacon tx and enables it via
3097  * rtl8192_beacon_tx_enable(). rtl8192_beacon_tx_disable() might
3098  * be used to stop beacon transmission
3099  */
3100 /***************************************************************************
3101     -------------------------------NET STUFF---------------------------
3102 ***************************************************************************/
3103 
3104 static struct net_device_stats *rtl8192_stats(struct net_device *dev)
3105 {
3106         struct r8192_priv *priv = ieee80211_priv(dev);
3107 
3108         return &priv->ieee80211->stats;
3109 }
3110 
3111 static bool HalTxCheckStuck819xUsb(struct net_device *dev)
3112 {
3113         struct r8192_priv *priv = ieee80211_priv(dev);
3114         u16             RegTxCounter;
3115         bool            bStuck = FALSE;
3116         read_nic_word(dev, 0x128, &RegTxCounter);
3117         RT_TRACE(COMP_RESET, "%s():RegTxCounter is %d,TxCounter is %d\n", __func__, RegTxCounter, priv->TxCounter);
3118         if (priv->TxCounter == RegTxCounter)
3119                 bStuck = TRUE;
3120 
3121         priv->TxCounter = RegTxCounter;
3122 
3123         return bStuck;
3124 }
3125 
3126 /*
3127 *       <Assumption: RT_TX_SPINLOCK is acquired.>
3128 *       First added: 2006.11.19 by emily
3129 */
3130 static RESET_TYPE TxCheckStuck(struct net_device *dev)
3131 {
3132         struct r8192_priv *priv = ieee80211_priv(dev);
3133         u8                      QueueID;
3134         bool                    bCheckFwTxCnt = false;
3135 
3136         //
3137         // Decide such threshold according to current power save mode
3138         //
3139 
3140         for (QueueID = 0; QueueID <= BEACON_QUEUE; QueueID++) {
3141                 if (QueueID == TXCMD_QUEUE)
3142                         continue;
3143 #ifdef USB_TX_DRIVER_AGGREGATION_ENABLE
3144                 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))
3145 #else
3146                 if ((skb_queue_len(&priv->ieee80211->skb_waitQ[QueueID]) == 0)  && (skb_queue_len(&priv->ieee80211->skb_aggQ[QueueID]) == 0))
3147 #endif
3148                                 continue;
3149 
3150                 bCheckFwTxCnt = true;
3151         }
3152         if (bCheckFwTxCnt) {
3153                 if (HalTxCheckStuck819xUsb(dev)) {
3154                         RT_TRACE(COMP_RESET, "TxCheckStuck(): Fw indicates no Tx condition! \n");
3155                         return RESET_TYPE_SILENT;
3156                 }
3157         }
3158         return RESET_TYPE_NORESET;
3159 }
3160 
3161 static bool HalRxCheckStuck819xUsb(struct net_device *dev)
3162 {
3163         u16     RegRxCounter;
3164         struct r8192_priv *priv = ieee80211_priv(dev);
3165         bool bStuck = FALSE;
3166         static u8       rx_chk_cnt;
3167         read_nic_word(dev, 0x130, &RegRxCounter);
3168         RT_TRACE(COMP_RESET, "%s(): RegRxCounter is %d,RxCounter is %d\n", __func__, RegRxCounter, priv->RxCounter);
3169         // If rssi is small, we should check rx for long time because of bad rx.
3170         // or maybe it will continuous silent reset every 2 seconds.
3171         rx_chk_cnt++;
3172         if (priv->undecorated_smoothed_pwdb >= (RateAdaptiveTH_High+5)) {
3173                 rx_chk_cnt = 0; //high rssi, check rx stuck right now.
3174         } else if (priv->undecorated_smoothed_pwdb < (RateAdaptiveTH_High+5) &&
3175                    ((priv->CurrentChannelBW != HT_CHANNEL_WIDTH_20 && priv->undecorated_smoothed_pwdb >= RateAdaptiveTH_Low_40M) ||
3176                     (priv->CurrentChannelBW == HT_CHANNEL_WIDTH_20 && priv->undecorated_smoothed_pwdb >= RateAdaptiveTH_Low_20M))) {
3177                 if (rx_chk_cnt < 2)
3178                         return bStuck;
3179                 else
3180                         rx_chk_cnt = 0;
3181         } else if (((priv->CurrentChannelBW != HT_CHANNEL_WIDTH_20 && priv->undecorated_smoothed_pwdb < RateAdaptiveTH_Low_40M) ||
3182                     (priv->CurrentChannelBW == HT_CHANNEL_WIDTH_20 && priv->undecorated_smoothed_pwdb < RateAdaptiveTH_Low_20M)) &&
3183                      priv->undecorated_smoothed_pwdb >= VeryLowRSSI) {
3184                 if (rx_chk_cnt < 4)
3185                         return bStuck;
3186                 else
3187                         rx_chk_cnt = 0;
3188         } else {
3189                 if (rx_chk_cnt < 8)
3190                         return bStuck;
3191                 else
3192                         rx_chk_cnt = 0;
3193         }
3194 
3195         if (priv->RxCounter == RegRxCounter)
3196                 bStuck = TRUE;
3197 
3198         priv->RxCounter = RegRxCounter;
3199 
3200         return bStuck;
3201 }
3202 
3203 static RESET_TYPE RxCheckStuck(struct net_device *dev)
3204 {
3205         struct r8192_priv *priv = ieee80211_priv(dev);
3206         bool        bRxCheck = FALSE;
3207 
3208         if (priv->IrpPendingCount > 1)
3209                 bRxCheck = TRUE;
3210 
3211         if (bRxCheck) {
3212                 if (HalRxCheckStuck819xUsb(dev)) {
3213                         RT_TRACE(COMP_RESET, "RxStuck Condition\n");
3214                         return RESET_TYPE_SILENT;
3215                 }
3216         }
3217         return RESET_TYPE_NORESET;
3218 }
3219 
3220 
3221 /**
3222 *       This function is called by Checkforhang to check whether we should ask OS to reset driver
3223 *
3224 *       \param pAdapter The adapter context for this miniport
3225 *
3226 *       Note:NIC with USB interface sholud not call this function because we cannot scan descriptor
3227 *       to judge whether there is tx stuck.
3228 *       Note: This function may be required to be rewrite for Vista OS.
3229 *       <<<Assumption: Tx spinlock has been acquired >>>
3230 *
3231 *       8185 and 8185b does not implement this function. This is added by Emily at 2006.11.24
3232 */
3233 static RESET_TYPE rtl819x_ifcheck_resetornot(struct net_device *dev)
3234 {
3235         struct r8192_priv *priv = ieee80211_priv(dev);
3236         RESET_TYPE      TxResetType = RESET_TYPE_NORESET;
3237         RESET_TYPE      RxResetType = RESET_TYPE_NORESET;
3238         RT_RF_POWER_STATE       rfState;
3239 
3240         rfState = priv->ieee80211->eRFPowerState;
3241 
3242         TxResetType = TxCheckStuck(dev);
3243         if (rfState != eRfOff ||
3244             (priv->ieee80211->iw_mode != IW_MODE_ADHOC)) {
3245                 // If driver is in the status of firmware download failure , driver skips RF initialization and RF is
3246                 // in turned off state. Driver should check whether Rx stuck and do silent reset. And
3247                 // if driver is in firmware download failure status, driver should initialize RF in the following
3248                 // silent reset procedure Emily, 2008.01.21
3249 
3250                 // Driver should not check RX stuck in IBSS mode because it is required to
3251                 // set Check BSSID in order to send beacon, however, if check BSSID is
3252                 // set, STA cannot hear any packet at all. Emily, 2008.04.12
3253                 RxResetType = RxCheckStuck(dev);
3254         }
3255         if (TxResetType == RESET_TYPE_NORMAL || RxResetType == RESET_TYPE_NORMAL) {
3256                 return RESET_TYPE_NORMAL;
3257         } else if (TxResetType == RESET_TYPE_SILENT || RxResetType == RESET_TYPE_SILENT) {
3258                 RT_TRACE(COMP_RESET, "%s():silent reset\n", __func__);
3259                 return RESET_TYPE_SILENT;
3260         } else {
3261                 return RESET_TYPE_NORESET;
3262         }
3263 
3264 }
3265 
3266 void rtl8192_cancel_deferred_work(struct r8192_priv *priv);
3267 int _rtl8192_up(struct net_device *dev);
3268 int rtl8192_close(struct net_device *dev);
3269 
3270 
3271 
3272 static void CamRestoreAllEntry(struct net_device *dev)
3273 {
3274         u8 EntryId = 0;
3275         struct r8192_priv *priv = ieee80211_priv(dev);
3276         u8      *MacAddr = priv->ieee80211->current_network.bssid;
3277 
3278         static u8       CAM_CONST_ADDR[4][6] = {
3279                 {0x00, 0x00, 0x00, 0x00, 0x00, 0x00},
3280                 {0x00, 0x00, 0x00, 0x00, 0x00, 0x01},
3281                 {0x00, 0x00, 0x00, 0x00, 0x00, 0x02},
3282                 {0x00, 0x00, 0x00, 0x00, 0x00, 0x03} };
3283         static u8       CAM_CONST_BROAD[] = {
3284                 0xff, 0xff, 0xff, 0xff, 0xff, 0xff};
3285 
3286         RT_TRACE(COMP_SEC, "CamRestoreAllEntry: \n");
3287 
3288 
3289         if ((priv->ieee80211->pairwise_key_type == KEY_TYPE_WEP40) ||
3290             (priv->ieee80211->pairwise_key_type == KEY_TYPE_WEP104)) {
3291 
3292                 for (EntryId = 0; EntryId < 4; EntryId++) {
3293                         MacAddr = CAM_CONST_ADDR[EntryId];
3294                         setKey(dev, EntryId, EntryId,
3295                                priv->ieee80211->pairwise_key_type,
3296                                MacAddr, 0, NULL);
3297                 }
3298 
3299         } else if (priv->ieee80211->pairwise_key_type == KEY_TYPE_TKIP) {
3300 
3301                 if (priv->ieee80211->iw_mode == IW_MODE_ADHOC)
3302                         setKey(dev, 4, 0, priv->ieee80211->pairwise_key_type,
3303                                (u8 *)dev->dev_addr, 0, NULL);
3304                 else
3305                         setKey(dev, 4, 0, priv->ieee80211->pairwise_key_type,
3306                                MacAddr, 0, NULL);
3307         } else if (priv->ieee80211->pairwise_key_type == KEY_TYPE_CCMP) {
3308 
3309                 if (priv->ieee80211->iw_mode == IW_MODE_ADHOC)
3310                         setKey(dev, 4, 0, priv->ieee80211->pairwise_key_type,
3311                                (u8 *)dev->dev_addr, 0, NULL);
3312                 else
3313                         setKey(dev, 4, 0, priv->ieee80211->pairwise_key_type,
3314                                MacAddr, 0, NULL);
3315         }
3316 
3317 
3318 
3319         if (priv->ieee80211->group_key_type == KEY_TYPE_TKIP) {
3320                 MacAddr = CAM_CONST_BROAD;
3321                 for (EntryId = 1; EntryId < 4; EntryId++) {
3322                         setKey(dev, EntryId, EntryId,
3323                                priv->ieee80211->group_key_type,
3324                                MacAddr, 0, NULL);
3325                 }
3326                 if (priv->ieee80211->iw_mode == IW_MODE_ADHOC)
3327                         setKey(dev, 0, 0, priv->ieee80211->group_key_type,
3328                                CAM_CONST_ADDR[0], 0, NULL);
3329         } else if (priv->ieee80211->group_key_type == KEY_TYPE_CCMP) {
3330                 MacAddr = CAM_CONST_BROAD;
3331                 for (EntryId = 1; EntryId < 4; EntryId++) {
3332                         setKey(dev, EntryId, EntryId,
3333                                priv->ieee80211->group_key_type,
3334                                MacAddr, 0, NULL);
3335                 }
3336 
3337                 if (priv->ieee80211->iw_mode == IW_MODE_ADHOC)
3338                         setKey(dev, 0, 0, priv->ieee80211->group_key_type,
3339                                CAM_CONST_ADDR[0], 0, NULL);
3340         }
3341 }
3342 //////////////////////////////////////////////////////////////
3343 // This function is used to fix Tx/Rx stop bug temporarily.
3344 // This function will do "system reset" to NIC when Tx or Rx is stuck.
3345 // The method checking Tx/Rx stuck of this function is supported by FW,
3346 // which reports Tx and Rx counter to register 0x128 and 0x130.
3347 //////////////////////////////////////////////////////////////
3348 static void rtl819x_ifsilentreset(struct net_device *dev)
3349 {
3350         struct r8192_priv *priv = ieee80211_priv(dev);
3351         u8      reset_times = 0;
3352         int reset_status = 0;
3353         struct ieee80211_device *ieee = priv->ieee80211;
3354 
3355 
3356         // 2007.07.20. If we need to check CCK stop, please uncomment this line.
3357         //bStuck = Adapter->HalFunc.CheckHWStopHandler(Adapter);
3358 
3359         if (priv->ResetProgress == RESET_TYPE_NORESET) {
3360 RESET_START:
3361 
3362                 RT_TRACE(COMP_RESET, "=========>Reset progress!! \n");
3363 
3364                 // Set the variable for reset.
3365                 priv->ResetProgress = RESET_TYPE_SILENT;
3366                 down(&priv->wx_sem);
3367                 if (priv->up == 0) {
3368                         RT_TRACE(COMP_ERR, "%s():the driver is not up! return\n", __func__);
3369                         up(&priv->wx_sem);
3370                         return;
3371                 }
3372                 priv->up = 0;
3373                 RT_TRACE(COMP_RESET, "%s():======>start to down the driver\n", __func__);
3374 
3375                 rtl8192_rtx_disable(dev);
3376                 rtl8192_cancel_deferred_work(priv);
3377                 deinit_hal_dm(dev);
3378                 del_timer_sync(&priv->watch_dog_timer);
3379 
3380                 ieee->sync_scan_hurryup = 1;
3381                 if (ieee->state == IEEE80211_LINKED) {
3382                         down(&ieee->wx_sem);
3383                         netdev_dbg(dev, "ieee->state is IEEE80211_LINKED\n");
3384                         ieee80211_stop_send_beacons(priv->ieee80211);
3385                         del_timer_sync(&ieee->associate_timer);
3386                         cancel_delayed_work(&ieee->associate_retry_wq);
3387                         ieee80211_stop_scan(ieee);
3388                         netif_carrier_off(dev);
3389                         up(&ieee->wx_sem);
3390                 } else {
3391                         netdev_dbg(dev, "ieee->state is NOT LINKED\n");
3392                         ieee80211_softmac_stop_protocol(priv->ieee80211);
3393                 }
3394                 up(&priv->wx_sem);
3395                 RT_TRACE(COMP_RESET, "%s():<==========down process is finished\n", __func__);
3396                 RT_TRACE(COMP_RESET, "%s():===========>start up the driver\n", __func__);
3397                 reset_status = _rtl8192_up(dev);
3398 
3399                 RT_TRACE(COMP_RESET, "%s():<===========up process is finished\n", __func__);
3400                 if (reset_status == -EAGAIN) {
3401                         if (reset_times < 3) {
3402                                 reset_times++;
3403                                 goto RESET_START;
3404                         } else {
3405                                 RT_TRACE(COMP_ERR, " ERR!!! %s():  Reset Failed!!\n", __func__);
3406                         }
3407                 }
3408                 ieee->is_silent_reset = 1;
3409                 EnableHWSecurityConfig8192(dev);
3410                 if (ieee->state == IEEE80211_LINKED && ieee->iw_mode == IW_MODE_INFRA) {
3411                         ieee->set_chan(ieee->dev, ieee->current_network.channel);
3412 
3413                         queue_work(ieee->wq, &ieee->associate_complete_wq);
3414 
3415                 } else if (ieee->state == IEEE80211_LINKED && ieee->iw_mode == IW_MODE_ADHOC) {
3416                         ieee->set_chan(ieee->dev, ieee->current_network.channel);
3417                         ieee->link_change(ieee->dev);
3418 
3419                         ieee80211_start_send_beacons(ieee);
3420 
3421                         if (ieee->data_hard_resume)
3422                                 ieee->data_hard_resume(ieee->dev);
3423                         netif_carrier_on(ieee->dev);
3424                 }
3425 
3426                 CamRestoreAllEntry(dev);
3427 
3428                 priv->ResetProgress = RESET_TYPE_NORESET;
3429                 priv->reset_count++;
3430 
3431                 priv->bForcedSilentReset = false;
3432                 priv->bResetInProgress = false;
3433 
3434                 // For test --> force write UFWP.
3435                 write_nic_byte(dev, UFWP, 1);
3436                 RT_TRACE(COMP_RESET, "Reset finished!! ====>[%d]\n", priv->reset_count);
3437         }
3438 }
3439 
3440 void CAM_read_entry(struct net_device *dev, u32 iIndex)
3441 {
3442         u32 target_command = 0;
3443         u32 target_content = 0;
3444         u8 entry_i = 0;
3445         u32 ulStatus;
3446         s32 i = 100;
3447         for (entry_i = 0; entry_i < CAM_CONTENT_COUNT; entry_i++) {
3448                 // polling bit, and No Write enable, and address
3449                 target_command = entry_i+CAM_CONTENT_COUNT*iIndex;
3450                 target_command = target_command | BIT31;
3451 
3452                 //Check polling bit is clear
3453                 while ((i--) >= 0) {
3454                         read_nic_dword(dev, RWCAM, &ulStatus);
3455                         if (ulStatus & BIT31)
3456                                 continue;
3457                         else
3458                                 break;
3459                 }
3460                 write_nic_dword(dev, RWCAM, target_command);
3461                 RT_TRACE(COMP_SEC, "CAM_read_entry(): WRITE A0: %x \n", target_command);
3462                 read_nic_dword(dev, RCAMO, &target_content);
3463                 RT_TRACE(COMP_SEC, "CAM_read_entry(): WRITE A8: %x \n", target_content);
3464         }
3465         printk("\n");
3466 }
3467 
3468 static void rtl819x_update_rxcounts(struct r8192_priv *priv, u32 *TotalRxBcnNum,
3469                              u32 *TotalRxDataNum)
3470 {
3471         u16                     SlotIndex;
3472         u8                      i;
3473 
3474         *TotalRxBcnNum = 0;
3475         *TotalRxDataNum = 0;
3476 
3477         SlotIndex = (priv->ieee80211->LinkDetectInfo.SlotIndex++)%(priv->ieee80211->LinkDetectInfo.SlotNum);
3478         priv->ieee80211->LinkDetectInfo.RxBcnNum[SlotIndex] = priv->ieee80211->LinkDetectInfo.NumRecvBcnInPeriod;
3479         priv->ieee80211->LinkDetectInfo.RxDataNum[SlotIndex] = priv->ieee80211->LinkDetectInfo.NumRecvDataInPeriod;
3480         for (i = 0; i < priv->ieee80211->LinkDetectInfo.SlotNum; i++) {
3481                 *TotalRxBcnNum += priv->ieee80211->LinkDetectInfo.RxBcnNum[i];
3482                 *TotalRxDataNum += priv->ieee80211->LinkDetectInfo.RxDataNum[i];
3483         }
3484 }
3485 
3486 
3487 void rtl819x_watchdog_wqcallback(struct work_struct *work)
3488 {
3489         struct delayed_work *dwork = container_of(work, struct delayed_work, work);
3490         struct r8192_priv *priv = container_of(dwork, struct r8192_priv, watch_dog_wq);
3491         struct net_device *dev = priv->ieee80211->dev;
3492         struct ieee80211_device *ieee = priv->ieee80211;
3493         RESET_TYPE      ResetType = RESET_TYPE_NORESET;
3494         static u8       check_reset_cnt;
3495         bool bBusyTraffic = false;
3496         u32     TotalRxBcnNum = 0;
3497         u32     TotalRxDataNum = 0;
3498 
3499         if (!priv->up)
3500                 return;
3501         hal_dm_watchdog(dev);
3502 
3503         //to get busy traffic condition
3504         if (ieee->state == IEEE80211_LINKED) {
3505                 if (ieee->LinkDetectInfo.NumRxOkInPeriod > 666 ||
3506                     ieee->LinkDetectInfo.NumTxOkInPeriod > 666 ) {
3507                         bBusyTraffic = true;
3508                 }
3509                 ieee->LinkDetectInfo.NumRxOkInPeriod = 0;
3510                 ieee->LinkDetectInfo.NumTxOkInPeriod = 0;
3511                 ieee->LinkDetectInfo.bBusyTraffic = bBusyTraffic;
3512         }
3513         //added by amy for AP roaming
3514         if (priv->ieee80211->state == IEEE80211_LINKED && priv->ieee80211->iw_mode == IW_MODE_INFRA) {
3515 
3516                 rtl819x_update_rxcounts(priv, &TotalRxBcnNum, &TotalRxDataNum);
3517                 if ((TotalRxBcnNum+TotalRxDataNum) == 0) {
3518 #ifdef TODO
3519                         if (rfState == eRfOff)
3520                                 RT_TRACE(COMP_ERR, "========>%s()\n", __func__);
3521 #endif
3522                         netdev_dbg(dev, "===>%s(): AP is power off, connect another one\n", __func__);
3523                         priv->ieee80211->state = IEEE80211_ASSOCIATING;
3524                         notify_wx_assoc_event(priv->ieee80211);
3525                         RemovePeerTS(priv->ieee80211, priv->ieee80211->current_network.bssid);
3526                         priv->ieee80211->link_change(dev);
3527                         queue_work(priv->ieee80211->wq, &priv->ieee80211->associate_procedure_wq);
3528 
3529                 }
3530         }
3531         priv->ieee80211->LinkDetectInfo.NumRecvBcnInPeriod = 0;
3532         priv->ieee80211->LinkDetectInfo.NumRecvDataInPeriod = 0;
3533         //check if reset the driver
3534         if (check_reset_cnt++ >= 3) {
3535                 ResetType = rtl819x_ifcheck_resetornot(dev);
3536                 check_reset_cnt = 3;
3537         }
3538         if ((priv->force_reset) || (priv->ResetProgress == RESET_TYPE_NORESET &&
3539             (priv->bForcedSilentReset ||
3540             (!priv->bDisableNormalResetCheck && ResetType == RESET_TYPE_SILENT)))) { // This is control by OID set in Pomelo
3541                 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", __func__, priv->force_reset, priv->ResetProgress, priv->bForcedSilentReset, priv->bDisableNormalResetCheck, ResetType);
3542                 rtl819x_ifsilentreset(dev);
3543         }
3544         priv->force_reset = false;
3545         priv->bForcedSilentReset = false;
3546         priv->bResetInProgress = false;
3547         RT_TRACE(COMP_TRACE, " <==RtUsbCheckForHangWorkItemCallback()\n");
3548 
3549 }
3550 
3551 void watch_dog_timer_callback(unsigned long data)
3552 {
3553         struct r8192_priv *priv = ieee80211_priv((struct net_device *) data);
3554         queue_delayed_work(priv->priv_wq, &priv->watch_dog_wq, 0);
3555         mod_timer(&priv->watch_dog_timer, jiffies + MSECS(IEEE80211_WATCH_DOG_TIME));
3556 }
3557 int _rtl8192_up(struct net_device *dev)
3558 {
3559         struct r8192_priv *priv = ieee80211_priv(dev);
3560         int init_status = 0;
3561         priv->up = 1;
3562         priv->ieee80211->ieee_up = 1;
3563         RT_TRACE(COMP_INIT, "Bringing up iface");
3564         init_status = rtl8192_adapter_start(dev);
3565         if (!init_status) {
3566                 RT_TRACE(COMP_ERR, "ERR!!! %s(): initialization failed!\n", __func__);
3567                 priv->up = priv->ieee80211->ieee_up = 0;
3568                 return -EAGAIN;
3569         }
3570         RT_TRACE(COMP_INIT, "start adapter finished\n");
3571         rtl8192_rx_enable(dev);
3572         if (priv->ieee80211->state != IEEE80211_LINKED)
3573                 ieee80211_softmac_start_protocol(priv->ieee80211);
3574         ieee80211_reset_queue(priv->ieee80211);
3575         watch_dog_timer_callback((unsigned long) dev);
3576         if (!netif_queue_stopped(dev))
3577                 netif_start_queue(dev);
3578         else
3579                 netif_wake_queue(dev);
3580 
3581         return 0;
3582 }
3583 
3584 
3585 static int rtl8192_open(struct net_device *dev)
3586 {
3587         struct r8192_priv *priv = ieee80211_priv(dev);
3588         int ret;
3589         down(&priv->wx_sem);
3590         ret = rtl8192_up(dev);
3591         up(&priv->wx_sem);
3592         return ret;
3593 
3594 }
3595 
3596 
3597 int rtl8192_up(struct net_device *dev)
3598 {
3599         struct r8192_priv *priv = ieee80211_priv(dev);
3600 
3601         if (priv->up == 1) return -1;
3602 
3603         return _rtl8192_up(dev);
3604 }
3605 
3606 
3607 int rtl8192_close(struct net_device *dev)
3608 {
3609         struct r8192_priv *priv = ieee80211_priv(dev);
3610         int ret;
3611 
3612         down(&priv->wx_sem);
3613 
3614         ret = rtl8192_down(dev);
3615 
3616         up(&priv->wx_sem);
3617 
3618         return ret;
3619 
3620 }
3621 
3622 int rtl8192_down(struct net_device *dev)
3623 {
3624         struct r8192_priv *priv = ieee80211_priv(dev);
3625         int i;
3626 
3627         if (priv->up == 0) return -1;
3628 
3629         priv->up = 0;
3630         priv->ieee80211->ieee_up = 0;
3631         RT_TRACE(COMP_DOWN, "==========>%s()\n", __func__);
3632         /* FIXME */
3633         if (!netif_queue_stopped(dev))
3634                 netif_stop_queue(dev);
3635 
3636         rtl8192_rtx_disable(dev);
3637 
3638         /* Tx related queue release */
3639         for (i = 0; i < MAX_QUEUE_SIZE; i++)
3640                 skb_queue_purge(&priv->ieee80211->skb_waitQ[i]);
3641         for (i = 0; i < MAX_QUEUE_SIZE; i++)
3642                 skb_queue_purge(&priv->ieee80211->skb_aggQ[i]);
3643 
3644         for (i = 0; i < MAX_QUEUE_SIZE; i++)
3645                 skb_queue_purge(&priv->ieee80211->skb_drv_aggQ[i]);
3646 
3647         //as cancel_delayed_work will del work->timer, so if work is not defined as struct delayed_work, it will corrupt
3648         rtl8192_cancel_deferred_work(priv);
3649         deinit_hal_dm(dev);
3650         del_timer_sync(&priv->watch_dog_timer);
3651 
3652 
3653         ieee80211_softmac_stop_protocol(priv->ieee80211);
3654         memset(&priv->ieee80211->current_network, 0, offsetof(struct ieee80211_network, list));
3655         RT_TRACE(COMP_DOWN, "<==========%s()\n", __func__);
3656 
3657         return 0;
3658 }
3659 
3660 
3661 void rtl8192_commit(struct net_device *dev)
3662 {
3663         struct r8192_priv *priv = ieee80211_priv(dev);
3664         int reset_status = 0;
3665         if (priv->up == 0) return;
3666         priv->up = 0;
3667 
3668         rtl8192_cancel_deferred_work(priv);
3669         del_timer_sync(&priv->watch_dog_timer);
3670 
3671         ieee80211_softmac_stop_protocol(priv->ieee80211);
3672 
3673         rtl8192_rtx_disable(dev);
3674         reset_status = _rtl8192_up(dev);
3675 
3676 }
3677 
3678 void rtl8192_restart(struct work_struct *work)
3679 {
3680         struct r8192_priv *priv = container_of(work, struct r8192_priv, reset_wq);
3681         struct net_device *dev = priv->ieee80211->dev;
3682 
3683         down(&priv->wx_sem);
3684 
3685         rtl8192_commit(dev);
3686 
3687         up(&priv->wx_sem);
3688 }
3689 
3690 static void r8192_set_multicast(struct net_device *dev)
3691 {
3692         struct r8192_priv *priv = ieee80211_priv(dev);
3693         short promisc;
3694 
3695         /* FIXME FIXME */
3696 
3697         promisc = (dev->flags & IFF_PROMISC) ? 1 : 0;
3698 
3699         if (promisc != priv->promisc)
3700 
3701                 priv->promisc = promisc;
3702 }
3703 
3704 
3705 static int r8192_set_mac_adr(struct net_device *dev, void *mac)
3706 {
3707         struct r8192_priv *priv = ieee80211_priv(dev);
3708         struct sockaddr *addr = mac;
3709 
3710         down(&priv->wx_sem);
3711 
3712         memcpy(dev->dev_addr, addr->sa_data, ETH_ALEN);
3713 
3714         schedule_work(&priv->reset_wq);
3715         up(&priv->wx_sem);
3716 
3717         return 0;
3718 }
3719 
3720 /* based on ipw2200 driver */
3721 static int rtl8192_ioctl(struct net_device *dev, struct ifreq *rq, int cmd)
3722 {
3723         struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
3724         struct iwreq *wrq = (struct iwreq *)rq;
3725         int ret = -1;
3726         struct ieee80211_device *ieee = priv->ieee80211;
3727         u32 key[4];
3728         u8 broadcast_addr[6] = {0xff, 0xff, 0xff, 0xff, 0xff, 0xff};
3729         struct iw_point *p = &wrq->u.data;
3730         struct ieee_param *ipw = NULL;
3731 
3732         down(&priv->wx_sem);
3733 
3734 
3735         if (p->length < sizeof(struct ieee_param) || !p->pointer) {
3736                 ret = -EINVAL;
3737                 goto out;
3738         }
3739 
3740         ipw = memdup_user(p->pointer, p->length);
3741         if (IS_ERR(ipw)) {
3742                 ret = PTR_ERR(ipw);
3743                 goto out;
3744         }
3745 
3746         switch (cmd) {
3747         case RTL_IOCTL_WPA_SUPPLICANT:
3748                 //parse here for HW security
3749                 if (ipw->cmd == IEEE_CMD_SET_ENCRYPTION) {
3750                         if (ipw->u.crypt.set_tx) {
3751                                 if (strcmp(ipw->u.crypt.alg, "CCMP") == 0) {
3752                                         ieee->pairwise_key_type = KEY_TYPE_CCMP;
3753                                 } else if (strcmp(ipw->u.crypt.alg, "TKIP") == 0) {
3754                                         ieee->pairwise_key_type = KEY_TYPE_TKIP;
3755                                 } else if (strcmp(ipw->u.crypt.alg, "WEP") == 0) {
3756                                         if (ipw->u.crypt.key_len == 13)
3757                                                 ieee->pairwise_key_type = KEY_TYPE_WEP104;
3758                                         else if (ipw->u.crypt.key_len == 5)
3759                                                 ieee->pairwise_key_type = KEY_TYPE_WEP40;
3760                                 } else {
3761                                         ieee->pairwise_key_type = KEY_TYPE_NA;
3762                                 }
3763 
3764                                 if (ieee->pairwise_key_type) {
3765                                         memcpy((u8 *)key, ipw->u.crypt.key, 16);
3766                                         EnableHWSecurityConfig8192(dev);
3767                                         //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!
3768                                         //added by WB.
3769                                         setKey(dev, 4, ipw->u.crypt.idx, ieee->pairwise_key_type, (u8 *)ieee->ap_mac_addr, 0, key);
3770                                         if (ieee->auth_mode != 2)
3771                                                 setKey(dev, ipw->u.crypt.idx, ipw->u.crypt.idx, ieee->pairwise_key_type, (u8 *)ieee->ap_mac_addr, 0, key);
3772                                 }
3773                         } else {
3774                                 memcpy((u8 *)key, ipw->u.crypt.key, 16);
3775                                 if (strcmp(ipw->u.crypt.alg, "CCMP") == 0) {
3776                                         ieee->group_key_type = KEY_TYPE_CCMP;
3777                                 } else if (strcmp(ipw->u.crypt.alg, "TKIP") == 0) {
3778                                         ieee->group_key_type = KEY_TYPE_TKIP;
3779                                 } else if (strcmp(ipw->u.crypt.alg, "WEP") == 0) {
3780                                         if (ipw->u.crypt.key_len == 13)
3781                                                 ieee->group_key_type = KEY_TYPE_WEP104;
3782                                         else if (ipw->u.crypt.key_len == 5)
3783                                                 ieee->group_key_type = KEY_TYPE_WEP40;
3784                                 } else {
3785                                         ieee->group_key_type = KEY_TYPE_NA;
3786                                 }
3787 
3788                                 if (ieee->group_key_type) {
3789                                         setKey(dev, ipw->u.crypt.idx,
3790                                                ipw->u.crypt.idx,                //KeyIndex
3791                                                ieee->group_key_type,    //KeyType
3792                                                broadcast_addr,  //MacAddr
3793                                                0,               //DefaultKey
3794                                                key);            //KeyContent
3795                                 }
3796                         }
3797                 }
3798                 ret = ieee80211_wpa_supplicant_ioctl(priv->ieee80211, &wrq->u.data);
3799                 break;
3800 
3801         default:
3802                 ret = -EOPNOTSUPP;
3803                 break;
3804         }
3805         kfree(ipw);
3806         ipw = NULL;
3807 out:
3808         up(&priv->wx_sem);
3809         return ret;
3810 }
3811 
3812 static u8 HwRateToMRate90(bool bIsHT, u8 rate)
3813 {
3814         u8  ret_rate = 0xff;
3815 
3816         if (!bIsHT) {
3817                 switch (rate) {
3818                 case DESC90_RATE1M:   ret_rate = MGN_1M;         break;
3819                 case DESC90_RATE2M:   ret_rate = MGN_2M;         break;
3820                 case DESC90_RATE5_5M: ret_rate = MGN_5_5M;       break;
3821                 case DESC90_RATE11M:  ret_rate = MGN_11M;        break;
3822                 case DESC90_RATE6M:   ret_rate = MGN_6M;         break;
3823                 case DESC90_RATE9M:   ret_rate = MGN_9M;         break;
3824                 case DESC90_RATE12M:  ret_rate = MGN_12M;        break;
3825                 case DESC90_RATE18M:  ret_rate = MGN_18M;        break;
3826                 case DESC90_RATE24M:  ret_rate = MGN_24M;        break;
3827                 case DESC90_RATE36M:  ret_rate = MGN_36M;        break;
3828                 case DESC90_RATE48M:  ret_rate = MGN_48M;        break;
3829                 case DESC90_RATE54M:  ret_rate = MGN_54M;        break;
3830 
3831                 default:
3832                         ret_rate = 0xff;
3833                         RT_TRACE(COMP_RECV, "HwRateToMRate90(): Non supported Rate [%x], bIsHT = %d!!!\n", rate, bIsHT);
3834                         break;
3835                 }
3836 
3837         } else {
3838                 switch (rate) {
3839                 case DESC90_RATEMCS0:   ret_rate = MGN_MCS0;    break;
3840                 case DESC90_RATEMCS1:   ret_rate = MGN_MCS1;    break;
3841                 case DESC90_RATEMCS2:   ret_rate = MGN_MCS2;    break;
3842                 case DESC90_RATEMCS3:   ret_rate = MGN_MCS3;    break;
3843                 case DESC90_RATEMCS4:   ret_rate = MGN_MCS4;    break;
3844                 case DESC90_RATEMCS5:   ret_rate = MGN_MCS5;    break;
3845                 case DESC90_RATEMCS6:   ret_rate = MGN_MCS6;    break;
3846                 case DESC90_RATEMCS7:   ret_rate = MGN_MCS7;    break;
3847                 case DESC90_RATEMCS8:   ret_rate = MGN_MCS8;    break;
3848                 case DESC90_RATEMCS9:   ret_rate = MGN_MCS9;    break;
3849                 case DESC90_RATEMCS10:  ret_rate = MGN_MCS10;   break;
3850                 case DESC90_RATEMCS11:  ret_rate = MGN_MCS11;   break;
3851                 case DESC90_RATEMCS12:  ret_rate = MGN_MCS12;   break;
3852                 case DESC90_RATEMCS13:  ret_rate = MGN_MCS13;   break;
3853                 case DESC90_RATEMCS14:  ret_rate = MGN_MCS14;   break;
3854                 case DESC90_RATEMCS15:  ret_rate = MGN_MCS15;   break;
3855                 case DESC90_RATEMCS32:  ret_rate = (0x80|0x20); break;
3856 
3857                 default:
3858                         ret_rate = 0xff;
3859                         RT_TRACE(COMP_RECV, "HwRateToMRate90(): Non supported Rate [%x], bIsHT = %d!!!\n", rate, bIsHT);
3860                         break;
3861                 }
3862         }
3863 
3864         return ret_rate;
3865 }
3866 
3867 /**
3868  * Function:     UpdateRxPktTimeStamp
3869  * Overview:     Record the TSF time stamp when receiving a packet
3870  *
3871  * Input:
3872  *       PADAPTER        Adapter
3873  *       PRT_RFD         pRfd,
3874  *
3875  * Output:
3876  *       PRT_RFD         pRfd
3877  *                               (pRfd->Status.TimeStampHigh is updated)
3878  *                               (pRfd->Status.TimeStampLow is updated)
3879  * Return:
3880  *               None
3881  */
3882 static void UpdateRxPktTimeStamp8190(struct net_device *dev,
3883                                      struct ieee80211_rx_stats *stats)
3884 {
3885         struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
3886 
3887         if (stats->bIsAMPDU && !stats->bFirstMPDU) {
3888                 stats->mac_time[0] = priv->LastRxDescTSFLow;
3889                 stats->mac_time[1] = priv->LastRxDescTSFHigh;
3890         } else {
3891                 priv->LastRxDescTSFLow = stats->mac_time[0];
3892                 priv->LastRxDescTSFHigh = stats->mac_time[1];
3893         }
3894 }
3895 
3896 //by amy 080606
3897 
3898 static long rtl819x_translate_todbm(u8 signal_strength_index)// 0-100 index.
3899 {
3900         long    signal_power; // in dBm.
3901 
3902         // Translate to dBm (x=0.5y-95).
3903         signal_power = (long)((signal_strength_index + 1) >> 1);
3904         signal_power -= 95;
3905 
3906         return signal_power;
3907 }
3908 
3909 
3910 /* 2008/01/22 MH We can not declare RSSI/EVM total value of sliding window to
3911     be a local static. Otherwise, it may increase when we return from S3/S4. The
3912     value will be kept in memory or disk. Declare the value in the adaptor
3913     and it will be reinitialized when returned from S3/S4. */
3914 static void rtl8192_process_phyinfo(struct r8192_priv *priv, u8 *buffer,
3915                                     struct ieee80211_rx_stats *pprevious_stats,
3916                                     struct ieee80211_rx_stats *pcurrent_stats)
3917 {
3918         bool bcheck = false;
3919         u8      rfpath;
3920         u32     nspatial_stream, tmp_val;
3921         static u32 slide_rssi_index, slide_rssi_statistics;
3922         static u32 slide_evm_index, slide_evm_statistics;
3923         static u32 last_rssi, last_evm;
3924 
3925         static u32 slide_beacon_adc_pwdb_index, slide_beacon_adc_pwdb_statistics;
3926         static u32 last_beacon_adc_pwdb;
3927 
3928         struct ieee80211_hdr_3addr *hdr;
3929         u16 sc;
3930         unsigned int frag, seq;
3931         hdr = (struct ieee80211_hdr_3addr *)buffer;
3932         sc = le16_to_cpu(hdr->seq_ctl);
3933         frag = WLAN_GET_SEQ_FRAG(sc);
3934         seq = WLAN_GET_SEQ_SEQ(sc);
3935         //cosa add 04292008 to record the sequence number
3936         pcurrent_stats->Seq_Num = seq;
3937         //
3938         // Check whether we should take the previous packet into accounting
3939         //
3940         if (!pprevious_stats->bIsAMPDU) {
3941                 // if previous packet is not aggregated packet
3942                 bcheck = true;
3943         }
3944 
3945         if (slide_rssi_statistics++ >= PHY_RSSI_SLID_WIN_MAX) {
3946                 slide_rssi_statistics = PHY_RSSI_SLID_WIN_MAX;
3947                 last_rssi = priv->stats.slide_signal_strength[slide_rssi_index];
3948                 priv->stats.slide_rssi_total -= last_rssi;
3949         }
3950         priv->stats.slide_rssi_total += pprevious_stats->SignalStrength;
3951 
3952         priv->stats.slide_signal_strength[slide_rssi_index++] = pprevious_stats->SignalStrength;
3953         if (slide_rssi_index >= PHY_RSSI_SLID_WIN_MAX)
3954                 slide_rssi_index = 0;
3955 
3956         // <1> Showed on UI for user, in dbm
3957         tmp_val = priv->stats.slide_rssi_total/slide_rssi_statistics;
3958         priv->stats.signal_strength = rtl819x_translate_todbm((u8)tmp_val);
3959         pcurrent_stats->rssi = priv->stats.signal_strength;
3960         //
3961         // If the previous packet does not match the criteria, neglect it
3962         //
3963         if (!pprevious_stats->bPacketMatchBSSID) {
3964                 if (!pprevious_stats->bToSelfBA)
3965                         return;
3966         }
3967 
3968         if (!bcheck)
3969                 return;
3970 
3971 
3972         //rtl8190_process_cck_rxpathsel(priv,pprevious_stats);//only rtl8190 supported
3973 
3974         //
3975         // Check RSSI
3976         //
3977         priv->stats.num_process_phyinfo++;
3978 
3979         /* record the general signal strength to the sliding window. */
3980 
3981 
3982         // <2> Showed on UI for engineering
3983         // hardware does not provide rssi information for each rf path in CCK
3984         if (!pprevious_stats->bIsCCK && (pprevious_stats->bPacketToSelf || pprevious_stats->bToSelfBA)) {
3985                 for (rfpath = RF90_PATH_A; rfpath < priv->NumTotalRFPath; rfpath++) {
3986                         if (!rtl8192_phy_CheckIsLegalRFPath(priv->ieee80211->dev, rfpath))
3987                                 continue;
3988 
3989                         //Fixed by Jacken 2008-03-20
3990                         if (priv->stats.rx_rssi_percentage[rfpath] == 0)
3991                                 priv->stats.rx_rssi_percentage[rfpath] = pprevious_stats->RxMIMOSignalStrength[rfpath];
3992                         if (pprevious_stats->RxMIMOSignalStrength[rfpath]  > priv->stats.rx_rssi_percentage[rfpath]) {
3993                                 priv->stats.rx_rssi_percentage[rfpath] =
3994                                         ((priv->stats.rx_rssi_percentage[rfpath]*(Rx_Smooth_Factor-1)) +
3995                                          (pprevious_stats->RxMIMOSignalStrength[rfpath])) /(Rx_Smooth_Factor);
3996                                 priv->stats.rx_rssi_percentage[rfpath] = priv->stats.rx_rssi_percentage[rfpath]  + 1;
3997                         } else {
3998                                 priv->stats.rx_rssi_percentage[rfpath] =
3999                                         ((priv->stats.rx_rssi_percentage[rfpath]*(Rx_Smooth_Factor-1)) +
4000                                          (pprevious_stats->RxMIMOSignalStrength[rfpath])) /(Rx_Smooth_Factor);
4001                         }
4002                         RT_TRACE(COMP_DBG, "priv->stats.rx_rssi_percentage[rfPath]  = %d \n", priv->stats.rx_rssi_percentage[rfpath]);
4003                 }
4004         }
4005 
4006 
4007         //
4008         // Check PWDB.
4009         //
4010         RT_TRACE(COMP_RXDESC, "Smooth %s PWDB = %d\n",
4011                  pprevious_stats->bIsCCK ? "CCK" : "OFDM",
4012                  pprevious_stats->RxPWDBAll);
4013 
4014         if (pprevious_stats->bPacketBeacon) {
4015                 /* record the beacon pwdb to the sliding window. */
4016                 if (slide_beacon_adc_pwdb_statistics++ >= PHY_Beacon_RSSI_SLID_WIN_MAX) {
4017                         slide_beacon_adc_pwdb_statistics = PHY_Beacon_RSSI_SLID_WIN_MAX;
4018                         last_beacon_adc_pwdb = priv->stats.Slide_Beacon_pwdb[slide_beacon_adc_pwdb_index];
4019                         priv->stats.Slide_Beacon_Total -= last_beacon_adc_pwdb;
4020                 }
4021                 priv->stats.Slide_Beacon_Total += pprevious_stats->RxPWDBAll;
4022                 priv->stats.Slide_Beacon_pwdb[slide_beacon_adc_pwdb_index] = pprevious_stats->RxPWDBAll;
4023                 slide_beacon_adc_pwdb_index++;
4024                 if (slide_beacon_adc_pwdb_index >= PHY_Beacon_RSSI_SLID_WIN_MAX)
4025                         slide_beacon_adc_pwdb_index = 0;
4026                 pprevious_stats->RxPWDBAll = priv->stats.Slide_Beacon_Total/slide_beacon_adc_pwdb_statistics;
4027                 if (pprevious_stats->RxPWDBAll >= 3)
4028                         pprevious_stats->RxPWDBAll -= 3;
4029         }
4030 
4031         RT_TRACE(COMP_RXDESC, "Smooth %s PWDB = %d\n",
4032                  pprevious_stats->bIsCCK ? "CCK" : "OFDM",
4033                  pprevious_stats->RxPWDBAll);
4034 
4035 
4036         if (pprevious_stats->bPacketToSelf || pprevious_stats->bPacketBeacon || pprevious_stats->bToSelfBA) {
4037                 if (priv->undecorated_smoothed_pwdb < 0)        // initialize
4038                         priv->undecorated_smoothed_pwdb = pprevious_stats->RxPWDBAll;
4039                 if (pprevious_stats->RxPWDBAll > (u32)priv->undecorated_smoothed_pwdb) {
4040                         priv->undecorated_smoothed_pwdb =
4041                                 (((priv->undecorated_smoothed_pwdb)*(Rx_Smooth_Factor-1)) +
4042                                  (pprevious_stats->RxPWDBAll)) /(Rx_Smooth_Factor);
4043                         priv->undecorated_smoothed_pwdb = priv->undecorated_smoothed_pwdb + 1;
4044                 } else {
4045                         priv->undecorated_smoothed_pwdb =
4046                                 (((priv->undecorated_smoothed_pwdb)*(Rx_Smooth_Factor-1)) +
4047                                  (pprevious_stats->RxPWDBAll)) /(Rx_Smooth_Factor);
4048                 }
4049 
4050         }
4051 
4052         //
4053         // Check EVM
4054         //
4055         /* record the general EVM to the sliding window. */
4056         if (pprevious_stats->SignalQuality) {
4057                 if (pprevious_stats->bPacketToSelf || pprevious_stats->bPacketBeacon || pprevious_stats->bToSelfBA) {
4058                         if (slide_evm_statistics++ >= PHY_RSSI_SLID_WIN_MAX) {
4059                                 slide_evm_statistics = PHY_RSSI_SLID_WIN_MAX;
4060                                 last_evm = priv->stats.slide_evm[slide_evm_index];
4061                                 priv->stats.slide_evm_total -= last_evm;
4062                         }
4063 
4064                         priv->stats.slide_evm_total += pprevious_stats->SignalQuality;
4065 
4066                         priv->stats.slide_evm[slide_evm_index++] = pprevious_stats->SignalQuality;
4067                         if (slide_evm_index >= PHY_RSSI_SLID_WIN_MAX)
4068                                 slide_evm_index = 0;
4069 
4070                         // <1> Showed on UI for user, in percentage.
4071                         tmp_val = priv->stats.slide_evm_total/slide_evm_statistics;
4072                         priv->stats.signal_quality = tmp_val;
4073                         //cosa add 10/11/2007, Showed on UI for user in Windows Vista, for Link quality.
4074                         priv->stats.last_signal_strength_inpercent = tmp_val;
4075                 }
4076 
4077                 // <2> Showed on UI for engineering
4078                 if (pprevious_stats->bPacketToSelf || pprevious_stats->bPacketBeacon || pprevious_stats->bToSelfBA) {
4079                         for (nspatial_stream = 0; nspatial_stream < 2; nspatial_stream++) { // 2 spatial stream
4080                                 if (pprevious_stats->RxMIMOSignalQuality[nspatial_stream] != -1) {
4081                                         if (priv->stats.rx_evm_percentage[nspatial_stream] == 0) // initialize
4082                                                 priv->stats.rx_evm_percentage[nspatial_stream] = pprevious_stats->RxMIMOSignalQuality[nspatial_stream];
4083                                         priv->stats.rx_evm_percentage[nspatial_stream] =
4084                                                 ((priv->stats.rx_evm_percentage[nspatial_stream]* (Rx_Smooth_Factor-1)) +
4085                                                  (pprevious_stats->RxMIMOSignalQuality[nspatial_stream]* 1)) / (Rx_Smooth_Factor);
4086                                 }
4087                         }
4088                 }
4089         }
4090 
4091 
4092 }
4093 
4094 /*-----------------------------------------------------------------------------
4095  * Function:    rtl819x_query_rxpwrpercentage()
4096  *
4097  * Overview:
4098  *
4099  * Input:               char            antpower
4100  *
4101  * Output:              NONE
4102  *
4103  * Return:              0-100 percentage
4104  *
4105  * Revised History:
4106  *      When            Who             Remark
4107  *      05/26/2008      amy             Create Version 0 porting from windows code.
4108  *
4109  *---------------------------------------------------------------------------*/
4110 static u8 rtl819x_query_rxpwrpercentage(char antpower)
4111 {
4112         if ((antpower <= -100) || (antpower >= 20))
4113                 return  0;
4114         else if (antpower >= 0)
4115                 return  100;
4116         else
4117                 return  100 + antpower;
4118 
4119 }       /* QueryRxPwrPercentage */
4120 
4121 static u8 rtl819x_evm_dbtopercentage(char value)
4122 {
4123         char ret_val;
4124 
4125         ret_val = value;
4126 
4127         if (ret_val >= 0)
4128                 ret_val = 0;
4129         if (ret_val <= -33)
4130                 ret_val = -33;
4131         ret_val = 0 - ret_val;
4132         ret_val *= 3;
4133         if (ret_val == 99)
4134                 ret_val = 100;
4135         return ret_val;
4136 }
4137 //
4138 //      Description:
4139 //      We want good-looking for signal strength/quality
4140 //      2007/7/19 01:09, by cosa.
4141 //
4142 static long rtl819x_signal_scale_mapping(long currsig)
4143 {
4144         long retsig;
4145 
4146         // Step 1. Scale mapping.
4147         if (currsig >= 61 && currsig <= 100)
4148                 retsig = 90 + ((currsig - 60) / 4);
4149         else if (currsig >= 41 && currsig <= 60)
4150                 retsig = 78 + ((currsig - 40) / 2);
4151         else if (currsig >= 31 && currsig <= 40)
4152                 retsig = 66 + (currsig - 30);
4153         else if (currsig >= 21 && currsig <= 30)
4154                 retsig = 54 + (currsig - 20);
4155         else if (currsig >= 5 && currsig <= 20)
4156                 retsig = 42 + (((currsig - 5) * 2) / 3);
4157         else if (currsig == 4)
4158                 retsig = 36;
4159         else if (currsig == 3)
4160                 retsig = 27;
4161         else if (currsig == 2)
4162                 retsig = 18;
4163         else if (currsig == 1)
4164                 retsig = 9;
4165         else
4166                 retsig = currsig;
4167 
4168         return retsig;
4169 }
4170 
4171 static inline bool rx_hal_is_cck_rate(struct rx_drvinfo_819x_usb *pdrvinfo)
4172 {
4173         if (pdrvinfo->RxHT)
4174                 return false;
4175 
4176         switch (pdrvinfo->RxRate) {
4177         case DESC90_RATE1M:
4178         case DESC90_RATE2M:
4179         case DESC90_RATE5_5M:
4180         case DESC90_RATE11M:
4181                 return true;
4182         default:
4183                 return false;
4184         }
4185 }
4186 
4187 static void rtl8192_query_rxphystatus(struct r8192_priv *priv,
4188                                       struct ieee80211_rx_stats *pstats,
4189                                       rx_drvinfo_819x_usb  *pdrvinfo,
4190                                       struct ieee80211_rx_stats *precord_stats,
4191                                       bool bpacket_match_bssid,
4192                                       bool bpacket_toself,
4193                                       bool bPacketBeacon,
4194                                       bool bToSelfBA)
4195 {
4196         phy_sts_ofdm_819xusb_t *pofdm_buf;
4197         phy_sts_cck_819xusb_t   *pcck_buf;
4198         phy_ofdm_rx_status_rxsc_sgien_exintfflag *prxsc;
4199         u8                              *prxpkt;
4200         u8                              i, max_spatial_stream, tmp_rxsnr, tmp_rxevm, rxsc_sgien_exflg;
4201         char                            rx_pwr[4], rx_pwr_all = 0;
4202         char                            rx_snrX, rx_evmX;
4203         u8                              evm, pwdb_all;
4204         u32                             RSSI, total_rssi = 0;
4205         u8                              is_cck_rate = 0;
4206         u8                              rf_rx_num = 0;
4207         u8                              sq;
4208 
4209 
4210         priv->stats.numqry_phystatus++;
4211 
4212         is_cck_rate = rx_hal_is_cck_rate(pdrvinfo);
4213 
4214         // Record it for next packet processing
4215         memset(precord_stats, 0, sizeof(struct ieee80211_rx_stats));
4216         pstats->bPacketMatchBSSID = precord_stats->bPacketMatchBSSID = bpacket_match_bssid;
4217         pstats->bPacketToSelf = precord_stats->bPacketToSelf = bpacket_toself;
4218         pstats->bIsCCK = precord_stats->bIsCCK = is_cck_rate;
4219         pstats->bPacketBeacon = precord_stats->bPacketBeacon = bPacketBeacon;
4220         pstats->bToSelfBA = precord_stats->bToSelfBA = bToSelfBA;
4221 
4222         prxpkt = (u8 *)pdrvinfo;
4223 
4224         /* Move pointer to the 16th bytes. Phy status start address. */
4225         prxpkt += sizeof(rx_drvinfo_819x_usb);
4226 
4227         /* Initial the cck and ofdm buffer pointer */
4228         pcck_buf = (phy_sts_cck_819xusb_t *)prxpkt;
4229         pofdm_buf = (phy_sts_ofdm_819xusb_t *)prxpkt;
4230 
4231         pstats->RxMIMOSignalQuality[0] = -1;
4232         pstats->RxMIMOSignalQuality[1] = -1;
4233         precord_stats->RxMIMOSignalQuality[0] = -1;
4234         precord_stats->RxMIMOSignalQuality[1] = -1;
4235 
4236         if (is_cck_rate) {
4237                 //
4238                 // (1)Hardware does not provide RSSI for CCK
4239                 //
4240 
4241                 //
4242                 // (2)PWDB, Average PWDB cacluated by hardware (for rate adaptive)
4243                 //
4244                 u8 report;
4245 
4246                 priv->stats.numqry_phystatusCCK++;
4247 
4248                 if (!priv->bCckHighPower) {
4249                         report = pcck_buf->cck_agc_rpt & 0xc0;
4250                         report = report>>6;
4251                         switch (report) {
4252                                 //Fixed by Jacken from Bryant 2008-03-20
4253                                 //Original value is -38 , -26 , -14 , -2
4254                                 //Fixed value is -35 , -23 , -11 , 6
4255                         case 0x3:
4256                                 rx_pwr_all = -35 - (pcck_buf->cck_agc_rpt & 0x3e);
4257                                 break;
4258                         case 0x2:
4259                                 rx_pwr_all = -23 - (pcck_buf->cck_agc_rpt & 0x3e);
4260                                 break;
4261                         case 0x1:
4262                                 rx_pwr_all = -11 - (pcck_buf->cck_agc_rpt & 0x3e);
4263                                 break;
4264                         case 0x0:
4265                                 rx_pwr_all = 6 - (pcck_buf->cck_agc_rpt & 0x3e);
4266                                 break;
4267                         }
4268                 } else {
4269                         report = pcck_buf->cck_agc_rpt & 0x60;
4270                         report = report>>5;
4271                         switch (report) {
4272                         case 0x3:
4273                                 rx_pwr_all = -35 - ((pcck_buf->cck_agc_rpt & 0x1f)<<1);
4274                                 break;
4275                         case 0x2:
4276                                 rx_pwr_all = -23 - ((pcck_buf->cck_agc_rpt & 0x1f)<<1);
4277                                 break;
4278                         case 0x1:
4279                                 rx_pwr_all = -11 - ((pcck_buf->cck_agc_rpt & 0x1f)<<1);
4280                                 break;
4281                         case 0x0:
4282                                 rx_pwr_all = 6 - ((pcck_buf->cck_agc_rpt & 0x1f)<<1);
4283                                 break;
4284                         }
4285                 }
4286 
4287                 pwdb_all = rtl819x_query_rxpwrpercentage(rx_pwr_all);
4288                 pstats->RxPWDBAll = precord_stats->RxPWDBAll = pwdb_all;
4289                 pstats->RecvSignalPower = pwdb_all;
4290 
4291                 //
4292                 // (3) Get Signal Quality (EVM)
4293                 //
4294 
4295                 if (pstats->RxPWDBAll > 40) {
4296                         sq = 100;
4297                 } else {
4298                         sq = pcck_buf->sq_rpt;
4299 
4300                         if (pcck_buf->sq_rpt > 64)
4301                                 sq = 0;
4302                         else if (pcck_buf->sq_rpt < 20)
4303                                 sq = 100;
4304                         else
4305                                 sq = ((64-sq) * 100) / 44;
4306                 }
4307                 pstats->SignalQuality = precord_stats->SignalQuality = sq;
4308                 pstats->RxMIMOSignalQuality[0] = precord_stats->RxMIMOSignalQuality[0] = sq;
4309                 pstats->RxMIMOSignalQuality[1] = precord_stats->RxMIMOSignalQuality[1] = -1;
4310 
4311         } else {
4312                 priv->stats.numqry_phystatusHT++;
4313                 //
4314                 // (1)Get RSSI for HT rate
4315                 //
4316                 for (i = RF90_PATH_A; i < priv->NumTotalRFPath; i++) {
4317                         // 2008/01/30 MH we will judge RF RX path now.
4318                         if (priv->brfpath_rxenable[i])
4319                                 rf_rx_num++;
4320                         else
4321                                 continue;
4322 
4323                         if (!rtl8192_phy_CheckIsLegalRFPath(priv->ieee80211->dev, i))
4324                                 continue;
4325 
4326                         //Fixed by Jacken from Bryant 2008-03-20
4327                         //Original value is 106
4328                         rx_pwr[i] = ((pofdm_buf->trsw_gain_X[i]&0x3F)*2) - 106;
4329 
4330                         //Get Rx snr value in DB
4331                         tmp_rxsnr =     pofdm_buf->rxsnr_X[i];
4332                         rx_snrX = (char)(tmp_rxsnr);
4333                         rx_snrX /= 2;
4334                         priv->stats.rxSNRdB[i] = (long)rx_snrX;
4335 
4336                         /* Translate DBM to percentage. */
4337                         RSSI = rtl819x_query_rxpwrpercentage(rx_pwr[i]);
4338                         total_rssi += RSSI;
4339 
4340                         /* Record Signal Strength for next packet */
4341                         pstats->RxMIMOSignalStrength[i] = (u8) RSSI;
4342                         precord_stats->RxMIMOSignalStrength[i] = (u8) RSSI;
4343                 }
4344 
4345 
4346                 //
4347                 // (2)PWDB, Average PWDB cacluated by hardware (for rate adaptive)
4348                 //
4349                 //Fixed by Jacken from Bryant 2008-03-20
4350                 //Original value is 106
4351                 rx_pwr_all = (((pofdm_buf->pwdb_all) >> 1)& 0x7f) -106;
4352                 pwdb_all = rtl819x_query_rxpwrpercentage(rx_pwr_all);
4353 
4354                 pstats->RxPWDBAll = precord_stats->RxPWDBAll = pwdb_all;
4355                 pstats->RxPower = precord_stats->RxPower =  rx_pwr_all;
4356 
4357                 //
4358                 // (3)EVM of HT rate
4359                 //
4360                 if (pdrvinfo->RxHT && pdrvinfo->RxRate >= DESC90_RATEMCS8 &&
4361                     pdrvinfo->RxRate <= DESC90_RATEMCS15)
4362                         max_spatial_stream = 2; //both spatial stream make sense
4363                 else
4364                         max_spatial_stream = 1; //only spatial stream 1 makes sense
4365 
4366                 for (i = 0; i < max_spatial_stream; i++) {
4367                         tmp_rxevm =     pofdm_buf->rxevm_X[i];
4368                         rx_evmX = (char)(tmp_rxevm);
4369 
4370                         // Do not use shift operation like "rx_evmX >>= 1" because the compiler of free build environment
4371                         // will set the most significant bit to "zero" when doing shifting operation which may change a negative
4372                         // value to positive one, then the dbm value (which is supposed to be negative)  is not correct anymore.
4373                         rx_evmX /= 2;   //dbm
4374 
4375                         evm = rtl819x_evm_dbtopercentage(rx_evmX);
4376                         if (i == 0) // Fill value in RFD, Get the first spatial stream only
4377                                 pstats->SignalQuality = precord_stats->SignalQuality = (u8)(evm & 0xff);
4378                         pstats->RxMIMOSignalQuality[i] = precord_stats->RxMIMOSignalQuality[i] = (u8)(evm & 0xff);
4379                 }
4380 
4381 
4382                 /* record rx statistics for debug */
4383                 rxsc_sgien_exflg = pofdm_buf->rxsc_sgien_exflg;
4384                 prxsc = (phy_ofdm_rx_status_rxsc_sgien_exintfflag *)&rxsc_sgien_exflg;
4385                 if (pdrvinfo->BW)       //40M channel
4386                         priv->stats.received_bwtype[1+prxsc->rxsc]++;
4387                 else                            //20M channel
4388                         priv->stats.received_bwtype[0]++;
4389         }
4390 
4391         //UI BSS List signal strength(in percentage), make it good looking, from 0~100.
4392         //It is assigned to the BSS List in GetValueFromBeaconOrProbeRsp().
4393         if (is_cck_rate) {
4394                 pstats->SignalStrength = precord_stats->SignalStrength = (u8)(rtl819x_signal_scale_mapping((long)pwdb_all));
4395         } else {
4396                 // We can judge RX path number now.
4397                 if (rf_rx_num != 0)
4398                         pstats->SignalStrength = precord_stats->SignalStrength = (u8)(rtl819x_signal_scale_mapping((long)(total_rssi /= rf_rx_num)));
4399         }
4400 }       /* QueryRxPhyStatus8190Pci */
4401 
4402 static void rtl8192_record_rxdesc_forlateruse(struct ieee80211_rx_stats *psrc_stats,
4403                                               struct ieee80211_rx_stats *ptarget_stats)
4404 {
4405         ptarget_stats->bIsAMPDU = psrc_stats->bIsAMPDU;
4406         ptarget_stats->bFirstMPDU = psrc_stats->bFirstMPDU;
4407         ptarget_stats->Seq_Num = psrc_stats->Seq_Num;
4408 }
4409 
4410 
4411 static void TranslateRxSignalStuff819xUsb(struct sk_buff *skb,
4412                                           struct ieee80211_rx_stats *pstats,
4413                                           rx_drvinfo_819x_usb  *pdrvinfo)
4414 {
4415         // TODO: We must only check packet for current MAC address. Not finish
4416         rtl8192_rx_info *info = (struct rtl8192_rx_info *)skb->cb;
4417         struct net_device *dev = info->dev;
4418         struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
4419         bool bpacket_match_bssid, bpacket_toself;
4420         bool bPacketBeacon = FALSE, bToSelfBA = FALSE;
4421         static struct ieee80211_rx_stats  previous_stats;
4422         struct ieee80211_hdr_3addr *hdr;//by amy
4423         u16 fc, type;
4424 
4425         // Get Signal Quality for only RX data queue (but not command queue)
4426 
4427         u8 *tmp_buf;
4428         u8  *praddr;
4429 
4430         /* Get MAC frame start address. */
4431         tmp_buf = (u8 *)skb->data;
4432 
4433         hdr = (struct ieee80211_hdr_3addr *)tmp_buf;
4434         fc = le16_to_cpu(hdr->frame_ctl);
4435         type = WLAN_FC_GET_TYPE(fc);
4436         praddr = hdr->addr1;
4437 
4438         /* Check if the received packet is acceptable. */
4439         bpacket_match_bssid = ((IEEE80211_FTYPE_CTL != type) &&
4440                                (eqMacAddr(priv->ieee80211->current_network.bssid,  (fc & IEEE80211_FCTL_TODS) ? hdr->addr1 : (fc & IEEE80211_FCTL_FROMDS) ? hdr->addr2 : hdr->addr3))
4441                                && (!pstats->bHwError) && (!pstats->bCRC) && (!pstats->bICV));
4442         bpacket_toself =  bpacket_match_bssid & (eqMacAddr(praddr, priv->ieee80211->dev->dev_addr));
4443 
4444         if (WLAN_FC_GET_FRAMETYPE(fc) == IEEE80211_STYPE_BEACON)
4445                 bPacketBeacon = true;
4446         if (WLAN_FC_GET_FRAMETYPE(fc) == IEEE80211_STYPE_BLOCKACK) {
4447                 if ((eqMacAddr(praddr, dev->dev_addr)))
4448                         bToSelfBA = true;
4449         }
4450 
4451 
4452 
4453         if (bpacket_match_bssid)
4454                 priv->stats.numpacket_matchbssid++;
4455         if (bpacket_toself)
4456                 priv->stats.numpacket_toself++;
4457         //
4458         // Process PHY information for previous packet (RSSI/PWDB/EVM)
4459         //
4460         // Because phy information is contained in the last packet of AMPDU only, so driver
4461         // should process phy information of previous packet
4462         rtl8192_process_phyinfo(priv, tmp_buf, &previous_stats, pstats);
4463         rtl8192_query_rxphystatus(priv, pstats, pdrvinfo, &previous_stats, bpacket_match_bssid, bpacket_toself, bPacketBeacon, bToSelfBA);
4464         rtl8192_record_rxdesc_forlateruse(pstats, &previous_stats);
4465 
4466 }
4467 
4468 /**
4469 * Function:     UpdateReceivedRateHistogramStatistics
4470 * Overview:     Record the received data rate
4471 *
4472 * Input:
4473 *       struct net_device *dev
4474 *       struct ieee80211_rx_stats *stats
4475 *
4476 * Output:
4477 *
4478 *                       (priv->stats.ReceivedRateHistogram[] is updated)
4479 * Return:
4480 *               None
4481 */
4482 static void
4483 UpdateReceivedRateHistogramStatistics8190(struct net_device *dev,
4484                                           struct ieee80211_rx_stats *stats)
4485 {
4486         struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
4487         u32 rcvType = 1;   //0: Total, 1:OK, 2:CRC, 3:ICV
4488         u32 rateIndex;
4489         u32 preamble_guardinterval;  //1: short preamble/GI, 0: long preamble/GI
4490 
4491 
4492         if (stats->bCRC)
4493                 rcvType = 2;
4494         else if (stats->bICV)
4495                 rcvType = 3;
4496 
4497         if (stats->bShortPreamble)
4498                 preamble_guardinterval = 1;// short
4499         else
4500                 preamble_guardinterval = 0;// long
4501 
4502         switch (stats->rate) {
4503                 //
4504                 // CCK rate
4505                 //
4506         case MGN_1M:    rateIndex = 0;  break;
4507         case MGN_2M:    rateIndex = 1;  break;
4508         case MGN_5_5M:  rateIndex = 2;  break;
4509         case MGN_11M:   rateIndex = 3;  break;
4510                 //
4511                 // Legacy OFDM rate
4512                 //
4513         case MGN_6M:    rateIndex = 4;  break;
4514         case MGN_9M:    rateIndex = 5;  break;
4515         case MGN_12M:   rateIndex = 6;  break;
4516         case MGN_18M:   rateIndex = 7;  break;
4517         case MGN_24M:   rateIndex = 8;  break;
4518         case MGN_36M:   rateIndex = 9;  break;
4519         case MGN_48M:   rateIndex = 10; break;
4520         case MGN_54M:   rateIndex = 11; break;
4521                 //
4522                 // 11n High throughput rate
4523                 //
4524         case MGN_MCS0:  rateIndex = 12; break;
4525         case MGN_MCS1:  rateIndex = 13; break;
4526         case MGN_MCS2:  rateIndex = 14; break;
4527         case MGN_MCS3:  rateIndex = 15; break;
4528         case MGN_MCS4:  rateIndex = 16; break;
4529         case MGN_MCS5:  rateIndex = 17; break;
4530         case MGN_MCS6:  rateIndex = 18; break;
4531         case MGN_MCS7:  rateIndex = 19; break;
4532         case MGN_MCS8:  rateIndex = 20; break;
4533         case MGN_MCS9:  rateIndex = 21; break;
4534         case MGN_MCS10: rateIndex = 22; break;
4535         case MGN_MCS11: rateIndex = 23; break;
4536         case MGN_MCS12: rateIndex = 24; break;
4537         case MGN_MCS13: rateIndex = 25; break;
4538         case MGN_MCS14: rateIndex = 26; break;
4539         case MGN_MCS15: rateIndex = 27; break;
4540         default:        rateIndex = 28; break;
4541         }
4542         priv->stats.received_preamble_GI[preamble_guardinterval][rateIndex]++;
4543         priv->stats.received_rate_histogram[0][rateIndex]++; //total
4544         priv->stats.received_rate_histogram[rcvType][rateIndex]++;
4545 }
4546 
4547 
4548 static void query_rxdesc_status(struct sk_buff *skb,
4549                                 struct ieee80211_rx_stats *stats,
4550                                 bool bIsRxAggrSubframe)
4551 {
4552         rtl8192_rx_info *info = (struct rtl8192_rx_info *)skb->cb;
4553         struct net_device *dev = info->dev;
4554         struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
4555         rx_drvinfo_819x_usb  *driver_info = NULL;
4556 
4557         //
4558         //Get Rx Descriptor Information
4559         //
4560 #ifdef USB_RX_AGGREGATION_SUPPORT
4561         if (bIsRxAggrSubframe) {
4562                 rx_desc_819x_usb_aggr_subframe *desc = (rx_desc_819x_usb_aggr_subframe *)skb->data;
4563                 stats->Length = desc->Length;
4564                 stats->RxDrvInfoSize = desc->RxDrvInfoSize;
4565                 stats->RxBufShift = 0; //RxBufShift = 2 in RxDesc, but usb didn't shift bytes in fact.
4566                 stats->bICV = desc->ICV;
4567                 stats->bCRC = desc->CRC32;
4568                 stats->bHwError = stats->bCRC|stats->bICV;
4569                 stats->Decrypted = !desc->SWDec;//RTL8190 set this bit to indicate that Hw does not decrypt packet
4570         } else
4571 #endif
4572         {
4573                 rx_desc_819x_usb *desc = (rx_desc_819x_usb *)skb->data;
4574 
4575                 stats->Length = desc->Length;
4576                 stats->RxDrvInfoSize = desc->RxDrvInfoSize;
4577                 stats->RxBufShift = 0;
4578                 stats->bICV = desc->ICV;
4579                 stats->bCRC = desc->CRC32;
4580                 stats->bHwError = stats->bCRC|stats->bICV;
4581                 //RTL8190 set this bit to indicate that Hw does not decrypt packet
4582                 stats->Decrypted = !desc->SWDec;
4583         }
4584 
4585         if ((priv->ieee80211->pHTInfo->bCurrentHTSupport == true) && (priv->ieee80211->pairwise_key_type == KEY_TYPE_CCMP))
4586                 stats->bHwError = false;
4587         else
4588                 stats->bHwError = stats->bCRC|stats->bICV;
4589 
4590         if (stats->Length < 24 || stats->Length > MAX_8192U_RX_SIZE)
4591                 stats->bHwError |= 1;
4592         //
4593         //Get Driver Info
4594         //
4595         // TODO: Need to verify it on FGPA platform
4596         //Driver info are written to the RxBuffer following rx desc
4597         if (stats->RxDrvInfoSize != 0) {
4598                 driver_info = (rx_drvinfo_819x_usb *)(skb->data + sizeof(rx_desc_819x_usb) +
4599                                                       stats->RxBufShift);
4600                 /* unit: 0.5M */
4601                 /* TODO */
4602                 if (!stats->bHwError) {
4603                         u8      ret_rate;
4604                         ret_rate = HwRateToMRate90(driver_info->RxHT, driver_info->RxRate);
4605                         if (ret_rate == 0xff) {
4606                                 // Abnormal Case: Receive CRC OK packet with Rx descriptor indicating non supported rate.
4607                                 // Special Error Handling here, 2008.05.16, by Emily
4608 
4609                                 stats->bHwError = 1;
4610                                 stats->rate = MGN_1M;   //Set 1M rate by default
4611                         } else {
4612                                 stats->rate = ret_rate;
4613                         }
4614                 } else {
4615                         stats->rate = 0x02;
4616                 }
4617 
4618                 stats->bShortPreamble = driver_info->SPLCP;
4619 
4620 
4621                 UpdateReceivedRateHistogramStatistics8190(dev, stats);
4622 
4623                 stats->bIsAMPDU = (driver_info->PartAggr == 1);
4624                 stats->bFirstMPDU = (driver_info->PartAggr == 1) && (driver_info->FirstAGGR == 1);
4625                 stats->TimeStampLow = driver_info->TSFL;
4626                 // xiong mask it, 070514
4627 
4628                 UpdateRxPktTimeStamp8190(dev, stats);
4629 
4630                 //
4631                 // Rx A-MPDU
4632                 //
4633                 if (driver_info->FirstAGGR == 1 || driver_info->PartAggr == 1)
4634                         RT_TRACE(COMP_RXDESC, "driver_info->FirstAGGR = %d, driver_info->PartAggr = %d\n",
4635                                  driver_info->FirstAGGR, driver_info->PartAggr);
4636 
4637         }
4638 
4639         skb_pull(skb, sizeof(rx_desc_819x_usb));
4640         //
4641         // Get Total offset of MPDU Frame Body
4642         //
4643         if ((stats->RxBufShift + stats->RxDrvInfoSize) > 0) {
4644                 stats->bShift = 1;
4645                 skb_pull(skb, stats->RxBufShift + stats->RxDrvInfoSize);
4646         }
4647 
4648 #ifdef USB_RX_AGGREGATION_SUPPORT
4649         /* for the rx aggregated sub frame, the redundant space truly contained in the packet */
4650         if (bIsRxAggrSubframe)
4651                 skb_pull(skb, 8);
4652 #endif
4653         /* for debug 2008.5.29 */
4654 
4655         //added by vivi, for MP, 20080108
4656         stats->RxIs40MHzPacket = driver_info->BW;
4657         if (stats->RxDrvInfoSize != 0)
4658                 TranslateRxSignalStuff819xUsb(skb, stats, driver_info);
4659 
4660 }
4661 
4662 u32 GetRxPacketShiftBytes819xUsb(struct ieee80211_rx_stats  *Status, bool bIsRxAggrSubframe)
4663 {
4664 #ifdef USB_RX_AGGREGATION_SUPPORT
4665         if (bIsRxAggrSubframe)
4666                 return (sizeof(rx_desc_819x_usb) + Status->RxDrvInfoSize
4667                         + Status->RxBufShift + 8);
4668         else
4669 #endif
4670                 return (sizeof(rx_desc_819x_usb) + Status->RxDrvInfoSize
4671                         + Status->RxBufShift);
4672 }
4673 
4674 static void rtl8192_rx_nomal(struct sk_buff *skb)
4675 {
4676         rtl8192_rx_info *info = (struct rtl8192_rx_info *)skb->cb;
4677         struct net_device *dev = info->dev;
4678         struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
4679         struct ieee80211_rx_stats stats = {
4680                 .signal = 0,
4681                 .noise = -98,
4682                 .rate = 0,
4683                 .freq = IEEE80211_24GHZ_BAND,
4684         };
4685         u32 rx_pkt_len = 0;
4686         struct ieee80211_hdr_1addr *ieee80211_hdr = NULL;
4687         bool unicast_packet = false;
4688 #ifdef USB_RX_AGGREGATION_SUPPORT
4689         struct sk_buff *agg_skb = NULL;
4690         u32  TotalLength = 0;
4691         u32  TempDWord = 0;
4692         u32  PacketLength = 0;
4693         u32  PacketOccupiedLendth = 0;
4694         u8   TempByte = 0;
4695         u32  PacketShiftBytes = 0;
4696         rx_desc_819x_usb_aggr_subframe *RxDescr = NULL;
4697         u8  PaddingBytes = 0;
4698         //add just for testing
4699         u8   testing;
4700 
4701 #endif
4702 
4703         /* 20 is for ps-poll */
4704         if ((skb->len >= (20 + sizeof(rx_desc_819x_usb))) && (skb->len < RX_URB_SIZE)) {
4705 #ifdef USB_RX_AGGREGATION_SUPPORT
4706                 TempByte = *(skb->data + sizeof(rx_desc_819x_usb));
4707 #endif
4708                 /* first packet should not contain Rx aggregation header */
4709                 query_rxdesc_status(skb, &stats, false);
4710                 /* TODO */
4711                 /* hardware related info */
4712 #ifdef USB_RX_AGGREGATION_SUPPORT
4713                 if (TempByte & BIT0) {
4714                         agg_skb = skb;
4715                         TotalLength = stats.Length - 4; /*sCrcLng*/
4716                         /* though the head pointer has passed this position  */
4717                         TempDWord = *(u32 *)(agg_skb->data - 4);
4718                         PacketLength = (u16)(TempDWord & 0x3FFF); /*sCrcLng*/
4719                         skb = dev_alloc_skb(PacketLength);
4720                         memcpy(skb_put(skb, PacketLength), agg_skb->data, PacketLength);
4721                         PacketShiftBytes = GetRxPacketShiftBytes819xUsb(&stats, false);
4722                 }
4723 #endif
4724                 /* Process the MPDU received */
4725                 skb_trim(skb, skb->len - 4/*sCrcLng*/);
4726 
4727                 rx_pkt_len = skb->len;
4728                 ieee80211_hdr = (struct ieee80211_hdr_1addr *)skb->data;
4729                 unicast_packet = false;
4730                 if (is_broadcast_ether_addr(ieee80211_hdr->addr1)) {
4731                         //TODO
4732                 } else if (is_multicast_ether_addr(ieee80211_hdr->addr1)) {
4733                         //TODO
4734                 } else {
4735                         /* unicast packet */
4736                         unicast_packet = true;
4737                 }
4738 
4739                 if (!ieee80211_rx(priv->ieee80211, skb, &stats)) {
4740                         dev_kfree_skb_any(skb);
4741                 } else {
4742                         priv->stats.rxoktotal++;
4743                         if (unicast_packet)
4744                                 priv->stats.rxbytesunicast += rx_pkt_len;
4745                 }
4746 #ifdef USB_RX_AGGREGATION_SUPPORT
4747                 testing = 1;
4748                 if (TotalLength > 0) {
4749                         PacketOccupiedLendth = PacketLength + (PacketShiftBytes + 8);
4750                         if ((PacketOccupiedLendth & 0xFF) != 0)
4751                                 PacketOccupiedLendth = (PacketOccupiedLendth & 0xFFFFFF00) + 256;
4752                         PacketOccupiedLendth -= 8;
4753                         TempDWord = PacketOccupiedLendth - PacketShiftBytes; /*- PacketLength */
4754                         if (agg_skb->len > TempDWord)
4755                                 skb_pull(agg_skb, TempDWord);
4756                         else
4757                                 agg_skb->len = 0;
4758 
4759                         while (agg_skb->len >= GetRxPacketShiftBytes819xUsb(&stats, true)) {
4760                                 u8 tmpCRC = 0, tmpICV = 0;
4761                                 RxDescr = (rx_desc_819x_usb_aggr_subframe *)(agg_skb->data);
4762                                 tmpCRC = RxDescr->CRC32;
4763                                 tmpICV = RxDescr->ICV;
4764                                 memcpy(agg_skb->data, &agg_skb->data[44], 2);
4765                                 RxDescr->CRC32 = tmpCRC;
4766                                 RxDescr->ICV = tmpICV;
4767 
4768                                 memset(&stats, 0, sizeof(struct ieee80211_rx_stats));
4769                                 stats.signal = 0;
4770                                 stats.noise = -98;
4771                                 stats.rate = 0;
4772                                 stats.freq = IEEE80211_24GHZ_BAND;
4773                                 query_rxdesc_status(agg_skb, &stats, true);
4774                                 PacketLength = stats.Length;
4775 
4776                                 if (PacketLength > agg_skb->len)
4777                                         break;
4778                                 /* Process the MPDU received */
4779                                 skb = dev_alloc_skb(PacketLength);
4780                                 memcpy(skb_put(skb, PacketLength), agg_skb->data, PacketLength);
4781                                 skb_trim(skb, skb->len - 4/*sCrcLng*/);
4782 
4783                                 rx_pkt_len = skb->len;
4784                                 ieee80211_hdr = (struct ieee80211_hdr_1addr *)skb->data;
4785                                 unicast_packet = false;
4786                                 if (is_broadcast_ether_addr(ieee80211_hdr->addr1)) {
4787                                         //TODO
4788                                 } else if (is_multicast_ether_addr(ieee80211_hdr->addr1)) {
4789                                         //TODO
4790                                 } else {
4791                                         /* unicast packet */
4792                                         unicast_packet = true;
4793                                 }
4794                                 if (!ieee80211_rx(priv->ieee80211, skb, &stats)) {
4795                                         dev_kfree_skb_any(skb);
4796                                 } else {
4797                                         priv->stats.rxoktotal++;
4798                                         if (unicast_packet)
4799                                                 priv->stats.rxbytesunicast += rx_pkt_len;
4800                                 }
4801                                 /* should trim the packet which has been copied to target skb */
4802                                 skb_pull(agg_skb, PacketLength);
4803                                 PacketShiftBytes = GetRxPacketShiftBytes819xUsb(&stats, true);
4804                                 PacketOccupiedLendth = PacketLength + PacketShiftBytes;
4805                                 if ((PacketOccupiedLendth & 0xFF) != 0) {
4806                                         PaddingBytes = 256 - (PacketOccupiedLendth & 0xFF);
4807                                         if (agg_skb->len > PaddingBytes)
4808                                                 skb_pull(agg_skb, PaddingBytes);
4809                                         else
4810                                                 agg_skb->len = 0;
4811                                 }
4812                         }
4813                         dev_kfree_skb(agg_skb);
4814                 }
4815 #endif
4816         } else {
4817                 priv->stats.rxurberr++;
4818                 netdev_dbg(dev, "actual_length: %d\n", skb->len);
4819                 dev_kfree_skb_any(skb);
4820         }
4821 
4822 }
4823 
4824 static void rtl819xusb_process_received_packet(struct net_device *dev,
4825                                                struct ieee80211_rx_stats *pstats)
4826 {
4827         u8      *frame;
4828         u16     frame_len = 0;
4829         struct r8192_priv *priv = ieee80211_priv(dev);
4830 
4831         // Get shifted bytes of Starting address of 802.11 header. 2006.09.28, by Emily
4832         //porting by amy 080508
4833         pstats->virtual_address += get_rxpacket_shiftbytes_819xusb(pstats);
4834         frame = pstats->virtual_address;
4835         frame_len = pstats->packetlength;
4836 #ifdef TODO     // by amy about HCT
4837         if (!Adapter->bInHctTest)
4838                 CountRxErrStatistics(Adapter, pRfd);
4839 #endif
4840 #ifdef ENABLE_PS  //by amy for adding ps function in future
4841         RT_RF_POWER_STATE rtState;
4842         // When RF is off, we should not count the packet for hw/sw synchronize
4843         // reason, ie. there may be a duration while sw switch is changed and hw
4844         // switch is being changed. 2006.12.04, by shien chang.
4845         Adapter->HalFunc.GetHwRegHandler(Adapter, HW_VAR_RF_STATE, (u8 *)(&rtState));
4846         if (rtState == eRfOff)
4847                 return;
4848 #endif
4849         priv->stats.rxframgment++;
4850 
4851 #ifdef TODO
4852         RmMonitorSignalStrength(Adapter, pRfd);
4853 #endif
4854         /* 2007/01/16 MH Add RX command packet handle here. */
4855         /* 2007/03/01 MH We have to release RFD and return if rx pkt is cmd pkt. */
4856         if (rtl819xusb_rx_command_packet(dev, pstats))
4857                 return;
4858 
4859 #ifdef SW_CRC_CHECK
4860         SwCrcCheck();
4861 #endif
4862 
4863 
4864 }
4865 
4866 static void query_rx_cmdpkt_desc_status(struct sk_buff *skb,
4867                                         struct ieee80211_rx_stats *stats)
4868 {
4869         rx_desc_819x_usb *desc = (rx_desc_819x_usb *)skb->data;
4870 
4871         //
4872         //Get Rx Descriptor Information
4873         //
4874         stats->virtual_address = (u8 *)skb->data;
4875         stats->Length = desc->Length;
4876         stats->RxDrvInfoSize = 0;
4877         stats->RxBufShift = 0;
4878         stats->packetlength = stats->Length-scrclng;
4879         stats->fraglength = stats->packetlength;
4880         stats->fragoffset = 0;
4881         stats->ntotalfrag = 1;
4882 }
4883 
4884 
4885 static void rtl8192_rx_cmd(struct sk_buff *skb)
4886 {
4887         struct rtl8192_rx_info *info = (struct rtl8192_rx_info *)skb->cb;
4888         struct net_device *dev = info->dev;
4889         /* TODO */
4890         struct ieee80211_rx_stats stats = {
4891                 .signal = 0,
4892                 .noise = -98,
4893                 .rate = 0,
4894                 .freq = IEEE80211_24GHZ_BAND,
4895         };
4896 
4897         if ((skb->len >= (20 + sizeof(rx_desc_819x_usb))) && (skb->len < RX_URB_SIZE)) {
4898 
4899                 query_rx_cmdpkt_desc_status(skb, &stats);
4900                 // this is to be done by amy 080508     prfd->queue_id = 1;
4901 
4902 
4903                 //
4904                 //  Process the command packet received.
4905                 //
4906 
4907                 rtl819xusb_process_received_packet(dev, &stats);
4908 
4909                 dev_kfree_skb_any(skb);
4910         }
4911 }
4912 
4913 void rtl8192_irq_rx_tasklet(struct r8192_priv *priv)
4914 {
4915         struct sk_buff *skb;
4916         struct rtl8192_rx_info *info;
4917 
4918         while (NULL != (skb = skb_dequeue(&priv->skb_queue))) {
4919                 info = (struct rtl8192_rx_info *)skb->cb;
4920                 switch (info->out_pipe) {
4921                 /* Nomal packet pipe */
4922                 case 3:
4923                         priv->IrpPendingCount--;
4924                         rtl8192_rx_nomal(skb);
4925                         break;
4926 
4927                 /* Command packet pipe */
4928                 case 9:
4929                         RT_TRACE(COMP_RECV, "command in-pipe index(%d)\n",
4930                                  info->out_pipe);
4931 
4932                         rtl8192_rx_cmd(skb);
4933                         break;
4934 
4935                 default: /* should never get here! */
4936                         RT_TRACE(COMP_ERR, "Unknown in-pipe index(%d)\n",
4937                                  info->out_pipe);
4938                         dev_kfree_skb(skb);
4939                         break;
4940 
4941                 }
4942         }
4943 }
4944 
4945 static const struct net_device_ops rtl8192_netdev_ops = {
4946         .ndo_open               = rtl8192_open,
4947         .ndo_stop               = rtl8192_close,
4948         .ndo_get_stats          = rtl8192_stats,
4949         .ndo_tx_timeout         = tx_timeout,
4950         .ndo_do_ioctl           = rtl8192_ioctl,
4951         .ndo_set_rx_mode        = r8192_set_multicast,
4952         .ndo_set_mac_address    = r8192_set_mac_adr,
4953         .ndo_validate_addr      = eth_validate_addr,
4954         .ndo_change_mtu         = eth_change_mtu,
4955         .ndo_start_xmit         = ieee80211_xmit,
4956 };
4957 
4958 
4959 /****************************************************************************
4960      ---------------------------- USB_STUFF---------------------------
4961 *****************************************************************************/
4962 
4963 static int rtl8192_usb_probe(struct usb_interface *intf,
4964                              const struct usb_device_id *id)
4965 {
4966         struct net_device *dev = NULL;
4967         struct r8192_priv *priv = NULL;
4968         struct usb_device *udev = interface_to_usbdev(intf);
4969         int ret;
4970         RT_TRACE(COMP_INIT, "Oops: i'm coming\n");
4971 
4972         dev = alloc_ieee80211(sizeof(struct r8192_priv));
4973         if (dev == NULL)
4974                 return -ENOMEM;
4975 
4976         usb_set_intfdata(intf, dev);
4977         SET_NETDEV_DEV(dev, &intf->dev);
4978         priv = ieee80211_priv(dev);
4979         priv->ieee80211 = netdev_priv(dev);
4980         priv->udev = udev;
4981 
4982         dev->netdev_ops = &rtl8192_netdev_ops;
4983 
4984 #if WIRELESS_EXT >= 12
4985 #if WIRELESS_EXT < 17
4986         dev->get_wireless_stats = r8192_get_wireless_stats;
4987 #endif
4988         dev->wireless_handlers = (struct iw_handler_def *) &r8192_wx_handlers_def;
4989 #endif
4990         dev->type = ARPHRD_ETHER;
4991 
4992         dev->watchdog_timeo = HZ*3;     //modified by john, 0805
4993 
4994         if (dev_alloc_name(dev, ifname) < 0) {
4995                 RT_TRACE(COMP_INIT, "Oops: devname already taken! Trying wlan%%d...\n");
4996                 ifname = "wlan%d";
4997                 dev_alloc_name(dev, ifname);
4998         }
4999 
5000         RT_TRACE(COMP_INIT, "Driver probe completed1\n");
5001         if (rtl8192_init(dev) != 0) {
5002                 RT_TRACE(COMP_ERR, "Initialization failed");
5003                 ret = -ENODEV;
5004                 goto fail;
5005         }
5006         netif_carrier_off(dev);
5007         netif_stop_queue(dev);
5008 
5009         ret = register_netdev(dev);
5010         if (ret)
5011                 goto fail2;
5012 
5013         RT_TRACE(COMP_INIT, "dev name=======> %s\n", dev->name);
5014         rtl8192_proc_init_one(dev);
5015 
5016 
5017         RT_TRACE(COMP_INIT, "Driver probe completed\n");
5018         return 0;
5019 
5020 fail2:
5021         rtl8192_down(dev);
5022         kfree(priv->pFirmware);
5023         priv->pFirmware = NULL;
5024         rtl8192_usb_deleteendpoints(dev);
5025         destroy_workqueue(priv->priv_wq);
5026         mdelay(10);
5027 fail:
5028         free_ieee80211(dev);
5029 
5030         RT_TRACE(COMP_ERR, "wlan driver load failed\n");
5031         return ret;
5032 }
5033 
5034 //detach all the work and timer structure declared or inititialize in r8192U_init function.
5035 void rtl8192_cancel_deferred_work(struct r8192_priv *priv)
5036 {
5037 
5038         cancel_work_sync(&priv->reset_wq);
5039         cancel_delayed_work(&priv->watch_dog_wq);
5040         cancel_delayed_work(&priv->update_beacon_wq);
5041         cancel_work_sync(&priv->qos_activate);
5042 }
5043 
5044 
5045 static void rtl8192_usb_disconnect(struct usb_interface *intf)
5046 {
5047         struct net_device *dev = usb_get_intfdata(intf);
5048 
5049         struct r8192_priv *priv = ieee80211_priv(dev);
5050         if (dev) {
5051 
5052                 unregister_netdev(dev);
5053 
5054                 RT_TRACE(COMP_DOWN, "=============>wlan driver to be removed\n");
5055                 rtl8192_proc_remove_one(dev);
5056 
5057                 rtl8192_down(dev);
5058                 kfree(priv->pFirmware);
5059                 priv->pFirmware = NULL;
5060                 rtl8192_usb_deleteendpoints(dev);
5061                 destroy_workqueue(priv->priv_wq);
5062                 mdelay(10);
5063 
5064         }
5065         free_ieee80211(dev);
5066         RT_TRACE(COMP_DOWN, "wlan driver removed\n");
5067 }
5068 
5069 /* fun with the built-in ieee80211 stack... */
5070 extern int ieee80211_debug_init(void);
5071 extern void ieee80211_debug_exit(void);
5072 extern int ieee80211_crypto_init(void);
5073 extern void ieee80211_crypto_deinit(void);
5074 extern int ieee80211_crypto_tkip_init(void);
5075 extern void ieee80211_crypto_tkip_exit(void);
5076 extern int ieee80211_crypto_ccmp_init(void);
5077 extern void ieee80211_crypto_ccmp_exit(void);
5078 extern int ieee80211_crypto_wep_init(void);
5079 extern void ieee80211_crypto_wep_exit(void);
5080 
5081 static int __init rtl8192_usb_module_init(void)
5082 {
5083         int ret;
5084 
5085 #ifdef CONFIG_IEEE80211_DEBUG
5086         ret = ieee80211_debug_init();
5087         if (ret) {
5088                 pr_err("ieee80211_debug_init() failed %d\n", ret);
5089                 return ret;
5090         }
5091 #endif
5092         ret = ieee80211_crypto_init();
5093         if (ret) {
5094                 pr_err("ieee80211_crypto_init() failed %d\n", ret);
5095                 return ret;
5096         }
5097 
5098         ret = ieee80211_crypto_tkip_init();
5099         if (ret) {
5100                 pr_err("ieee80211_crypto_tkip_init() failed %d\n", ret);
5101                 return ret;
5102         }
5103 
5104         ret = ieee80211_crypto_ccmp_init();
5105         if (ret) {
5106                 pr_err("ieee80211_crypto_ccmp_init() failed %d\n", ret);
5107                 return ret;
5108         }
5109 
5110         ret = ieee80211_crypto_wep_init();
5111         if (ret) {
5112                 pr_err("ieee80211_crypto_wep_init() failed %d\n", ret);
5113                 return ret;
5114         }
5115 
5116         pr_info("\nLinux kernel driver for RTL8192 based WLAN cards\n");
5117         pr_info("Copyright (c) 2007-2008, Realsil Wlan\n");
5118         RT_TRACE(COMP_INIT, "Initializing module");
5119         RT_TRACE(COMP_INIT, "Wireless extensions version %d", WIRELESS_EXT);
5120         rtl8192_proc_module_init();
5121         return usb_register(&rtl8192_usb_driver);
5122 }
5123 
5124 
5125 static void __exit rtl8192_usb_module_exit(void)
5126 {
5127         usb_deregister(&rtl8192_usb_driver);
5128 
5129         RT_TRACE(COMP_DOWN, "Exiting");
5130 }
5131 
5132 
5133 void rtl8192_try_wake_queue(struct net_device *dev, int pri)
5134 {
5135         unsigned long flags;
5136         short enough_desc;
5137         struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
5138 
5139         spin_lock_irqsave(&priv->tx_lock, flags);
5140         enough_desc = check_nic_enough_desc(dev, pri);
5141         spin_unlock_irqrestore(&priv->tx_lock, flags);
5142 
5143         if (enough_desc)
5144                 ieee80211_wake_queue(priv->ieee80211);
5145 }
5146 
5147 void EnableHWSecurityConfig8192(struct net_device *dev)
5148 {
5149         u8 SECR_value = 0x0;
5150         struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
5151         struct ieee80211_device *ieee = priv->ieee80211;
5152         SECR_value = SCR_TxEncEnable | SCR_RxDecEnable;
5153         if (((KEY_TYPE_WEP40 == ieee->pairwise_key_type) || (KEY_TYPE_WEP104 == ieee->pairwise_key_type)) && (priv->ieee80211->auth_mode != 2)) {
5154                 SECR_value |= SCR_RxUseDK;
5155                 SECR_value |= SCR_TxUseDK;
5156         } else if ((ieee->iw_mode == IW_MODE_ADHOC) && (ieee->pairwise_key_type & (KEY_TYPE_CCMP | KEY_TYPE_TKIP))) {
5157                 SECR_value |= SCR_RxUseDK;
5158                 SECR_value |= SCR_TxUseDK;
5159         }
5160         //add HWSec active enable here.
5161         //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
5162 
5163         ieee->hwsec_active = 1;
5164 
5165         if ((ieee->pHTInfo->IOTAction&HT_IOT_ACT_PURE_N_MODE) || !hwwep) { //add hwsec_support flag to totol control hw_sec on/off
5166                 ieee->hwsec_active = 0;
5167                 SECR_value &= ~SCR_RxDecEnable;
5168         }
5169         RT_TRACE(COMP_SEC, "%s:, hwsec:%d, pairwise_key:%d, SECR_value:%x\n", __func__,
5170                  ieee->hwsec_active, ieee->pairwise_key_type, SECR_value);
5171         write_nic_byte(dev, SECR,  SECR_value);
5172 }
5173 
5174 
5175 void setKey(struct net_device *dev, u8 EntryNo, u8 KeyIndex, u16 KeyType,
5176             u8 *MacAddr, u8 DefaultKey, u32 *KeyContent)
5177 {
5178         u32 TargetCommand = 0;
5179         u32 TargetContent = 0;
5180         u16 usConfig = 0;
5181         u8 i;
5182         if (EntryNo >= TOTAL_CAM_ENTRY)
5183                 RT_TRACE(COMP_ERR, "cam entry exceeds in setKey()\n");
5184 
5185         RT_TRACE(COMP_SEC, "====>to setKey(), dev:%p, EntryNo:%d, KeyIndex:%d, KeyType:%d, MacAddr%pM\n", dev, EntryNo, KeyIndex, KeyType, MacAddr);
5186 
5187         if (DefaultKey)
5188                 usConfig |= BIT15 | (KeyType<<2);
5189         else
5190                 usConfig |= BIT15 | (KeyType<<2) | KeyIndex;
5191 
5192 
5193         for (i = 0; i < CAM_CONTENT_COUNT; i++) {
5194                 TargetCommand  = i+CAM_CONTENT_COUNT*EntryNo;
5195                 TargetCommand |= BIT31|BIT16;
5196 
5197                 if (i == 0) { //MAC|Config
5198                         TargetContent = (u32)(*(MacAddr+0)) << 16|
5199                                         (u32)(*(MacAddr+1)) << 24|
5200                                         (u32)usConfig;
5201 
5202                         write_nic_dword(dev, WCAMI, TargetContent);
5203                         write_nic_dword(dev, RWCAM, TargetCommand);
5204                 } else if (i == 1) { //MAC
5205                         TargetContent = (u32)(*(MacAddr+2))      |
5206                                         (u32)(*(MacAddr+3)) <<  8|
5207                                         (u32)(*(MacAddr+4)) << 16|
5208                                         (u32)(*(MacAddr+5)) << 24;
5209                         write_nic_dword(dev, WCAMI, TargetContent);
5210                         write_nic_dword(dev, RWCAM, TargetCommand);
5211                 } else {
5212                         //Key Material
5213                         if (KeyContent != NULL) {
5214                                 write_nic_dword(dev, WCAMI, (u32)(*(KeyContent+i-2)));
5215                                 write_nic_dword(dev, RWCAM, TargetCommand);
5216                         }
5217                 }
5218         }
5219 
5220 }
5221 
5222 /***************************************************************************
5223      ------------------- module init / exit stubs ----------------
5224 ****************************************************************************/
5225 module_init(rtl8192_usb_module_init);
5226 module_exit(rtl8192_usb_module_exit);
5227 

This page was automatically generated by LXR 0.3.1 (source).  •  Linux is a registered trademark of Linus Torvalds  •  Contact us