staging: rtl8192e: Clean up MlmeDisassociateRequest
[deliverable/linux.git] / drivers / staging / rtl8192e / r8192E_core.c
CommitLineData
ecdfa446
GKH
1/******************************************************************************
2 * Copyright(c) 2008 - 2010 Realtek Corporation. All rights reserved.
4803ef77 3 * Linux device driver for RTL8192E
ecdfa446
GKH
4 *
5 * Based on the r8180 driver, which is:
6 * Copyright 2004-2005 Andrea Merello <andreamrl@tiscali.it>, et al.
7 * This program is free software; you can redistribute it and/or modify it
8 * under the terms of version 2 of the GNU General Public License as
9 * published by the Free Software Foundation.
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
ecdfa446 27//#define CONFIG_RTL8192_IO_MAP
3d14b518 28#include <linux/vmalloc.h>
5a0e3ad6 29#include <linux/slab.h>
ecdfa446
GKH
30#include <asm/uaccess.h>
31#include "r8192E_hw.h"
32#include "r8192E.h"
33#include "r8190_rtl8256.h" /* RTL8225 Radio frontend */
34#include "r8180_93cx6.h" /* Card EEPROM */
35#include "r8192E_wx.h"
36#include "r819xE_phy.h" //added by WB 4.30.2008
37#include "r819xE_phyreg.h"
38#include "r819xE_cmdpkt.h"
39#include "r8192E_dm.h"
ecdfa446 40
bebdf809 41#ifdef CONFIG_PM
ecdfa446
GKH
42#include "r8192_pm.h"
43#endif
44
45#ifdef ENABLE_DOT11D
65a43784 46#include "ieee80211/dot11d.h"
ecdfa446
GKH
47#endif
48
49//set here to open your trace code. //WB
57be9583 50u32 rt_global_debug_component = COMP_ERR ; //always open err flags on
cf3d3d38 51
5eaa53de 52static DEFINE_PCI_DEVICE_TABLE(rtl8192_pci_id_tbl) = {
ecdfa446
GKH
53 /* Realtek */
54 { PCI_DEVICE(0x10ec, 0x8192) },
55
56 /* Corega */
57 { PCI_DEVICE(0x07aa, 0x0044) },
58 { PCI_DEVICE(0x07aa, 0x0047) },
ecdfa446
GKH
59 {}
60};
61
dca41306 62static char ifname[IFNAMSIZ] = "wlan%d";
ecdfa446
GKH
63static int hwwep = 1; //default use hw. set 0 to use software security
64static int channels = 0x3fff;
65
66MODULE_LICENSE("GPL");
ecdfa446 67MODULE_VERSION("V 1.1");
ecdfa446
GKH
68MODULE_DEVICE_TABLE(pci, rtl8192_pci_id_tbl);
69//MODULE_AUTHOR("Andrea Merello <andreamrl@tiscali.it>");
70MODULE_DESCRIPTION("Linux driver for Realtek RTL819x WiFi cards");
71
ecdfa446 72
dca41306 73module_param_string(ifname, ifname, sizeof(ifname), S_IRUGO|S_IWUSR);
ecdfa446
GKH
74module_param(hwwep,int, S_IRUGO|S_IWUSR);
75module_param(channels,int, S_IRUGO|S_IWUSR);
ecdfa446
GKH
76
77MODULE_PARM_DESC(ifname," Net interface name, wlan%d=default");
ecdfa446
GKH
78MODULE_PARM_DESC(hwwep," Try to use hardware WEP support. Still broken and not available on all cards");
79MODULE_PARM_DESC(channels," Channel bitmask for specific locales. NYI");
80
81static int __devinit rtl8192_pci_probe(struct pci_dev *pdev,
82 const struct pci_device_id *id);
83static void __devexit rtl8192_pci_disconnect(struct pci_dev *pdev);
84
85static struct pci_driver rtl8192_pci_driver = {
86 .name = RTL819xE_MODULE_NAME, /* Driver name */
87 .id_table = rtl8192_pci_id_tbl, /* PCI_ID table */
88 .probe = rtl8192_pci_probe, /* probe fn */
89 .remove = __devexit_p(rtl8192_pci_disconnect), /* remove fn */
bebdf809 90#ifdef CONFIG_PM
ecdfa446
GKH
91 .suspend = rtl8192E_suspend, /* PM suspend fn */
92 .resume = rtl8192E_resume, /* PM resume fn */
93#else
94 .suspend = NULL, /* PM suspend fn */
214985a6 95 .resume = NULL, /* PM resume fn */
ecdfa446 96#endif
ecdfa446
GKH
97};
98
559fba5e
MM
99static void rtl8192_start_beacon(struct net_device *dev);
100static void rtl8192_stop_beacon(struct net_device *dev);
101static void rtl819x_watchdog_wqcallback(struct work_struct *work);
80a4dead
MM
102static void rtl8192_irq_rx_tasklet(unsigned long arg);
103static void rtl8192_irq_tx_tasklet(unsigned long arg);
104static void rtl8192_prepare_beacon(unsigned long arg);
559fba5e 105static irqreturn_t rtl8192_interrupt(int irq, void *netdev);
881a975b 106static void rtl819xE_tx_cmd(struct net_device *dev, struct sk_buff *skb);
5b3b1a7b
MM
107static void rtl8192_update_ratr_table(struct net_device* dev);
108static void rtl8192_restart(struct work_struct *work);
109static void watch_dog_timer_callback(unsigned long data);
110static int _rtl8192_up(struct net_device *dev);
111static void rtl8192_cancel_deferred_work(struct r8192_priv* priv);
559fba5e 112
ecdfa446
GKH
113#ifdef ENABLE_DOT11D
114
115typedef struct _CHANNEL_LIST
116{
117 u8 Channel[32];
118 u8 Len;
119}CHANNEL_LIST, *PCHANNEL_LIST;
120
ab2161a0 121static const CHANNEL_LIST ChannelPlan[] = {
ecdfa446
GKH
122 {{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
123 {{1,2,3,4,5,6,7,8,9,10,11},11}, //IC
124 {{1,2,3,4,5,6,7,8,9,10,11,12,13,36,40,44,48,52,56,60,64},21}, //ETSI
125 {{1,2,3,4,5,6,7,8,9,10,11,12,13},13}, //Spain. Change to ETSI.
126 {{1,2,3,4,5,6,7,8,9,10,11,12,13},13}, //France. Change to ETSI.
127 {{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
128 {{1,2,3,4,5,6,7,8,9,10,11,12,13,14,36,40,44,48,52,56,60,64},22},//MKK1
129 {{1,2,3,4,5,6,7,8,9,10,11,12,13},13}, //Israel.
130 {{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
131 {{1,2,3,4,5,6,7,8,9,10,11,12,13,14,36,40,44,48,52,56,60,64}, 22}, //MIC
132 {{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
133};
134
135static void rtl819x_set_channel_map(u8 channel_plan, struct r8192_priv* priv)
136{
137 int i, max_chan=-1, min_chan=-1;
138 struct ieee80211_device* ieee = priv->ieee80211;
139 switch (channel_plan)
140 {
141 case COUNTRY_CODE_FCC:
142 case COUNTRY_CODE_IC:
143 case COUNTRY_CODE_ETSI:
144 case COUNTRY_CODE_SPAIN:
145 case COUNTRY_CODE_FRANCE:
146 case COUNTRY_CODE_MKK:
147 case COUNTRY_CODE_MKK1:
148 case COUNTRY_CODE_ISRAEL:
149 case COUNTRY_CODE_TELEC:
150 case COUNTRY_CODE_MIC:
151 {
152 Dot11d_Init(ieee);
153 ieee->bGlobalDomain = false;
154 //acturally 8225 & 8256 rf chip only support B,G,24N mode
6f304eb2
MM
155 min_chan = 1;
156 max_chan = 14;
157
ecdfa446
GKH
158 if (ChannelPlan[channel_plan].Len != 0){
159 // Clear old channel map
160 memset(GET_DOT11D_INFO(ieee)->channel_map, 0, sizeof(GET_DOT11D_INFO(ieee)->channel_map));
161 // Set new channel map
162 for (i=0;i<ChannelPlan[channel_plan].Len;i++)
163 {
164 if (ChannelPlan[channel_plan].Channel[i] < min_chan || ChannelPlan[channel_plan].Channel[i] > max_chan)
165 break;
166 GET_DOT11D_INFO(ieee)->channel_map[ChannelPlan[channel_plan].Channel[i]] = 1;
167 }
168 }
169 break;
170 }
171 case COUNTRY_CODE_GLOBAL_DOMAIN:
172 {
173 GET_DOT11D_INFO(ieee)->bEnabled = 0; //this flag enabled to follow 11d country IE setting, otherwise, it shall follow global domain setting
174 Dot11d_Reset(ieee);
175 ieee->bGlobalDomain = true;
176 break;
177 }
178 default:
179 break;
180 }
181}
182#endif
183
52cab756
MM
184static inline bool rx_hal_is_cck_rate(prx_fwinfo_819x_pci pdrvinfo)
185{
186 return (pdrvinfo->RxRate == DESC90_RATE1M ||
187 pdrvinfo->RxRate == DESC90_RATE2M ||
188 pdrvinfo->RxRate == DESC90_RATE5_5M ||
189 pdrvinfo->RxRate == DESC90_RATE11M) &&
190 !pdrvinfo->RxHT;
191}
ecdfa446
GKH
192
193void CamResetAllEntry(struct net_device *dev)
194{
3f9ab1ee
MM
195 struct r8192_priv* priv = ieee80211_priv(dev);
196 write_nic_dword(priv, RWCAM, BIT31|BIT30);
ecdfa446
GKH
197}
198
3f9ab1ee 199void write_cam(struct r8192_priv *priv, u8 addr, u32 data)
ecdfa446 200{
3f9ab1ee
MM
201 write_nic_dword(priv, WCAMI, data);
202 write_nic_dword(priv, RWCAM, BIT31|BIT16|(addr&0xff) );
ecdfa446 203}
3f9ab1ee
MM
204
205u32 read_cam(struct r8192_priv *priv, u8 addr)
ecdfa446 206{
3f9ab1ee
MM
207 write_nic_dword(priv, RWCAM, 0x80000000|(addr&0xff) );
208 return read_nic_dword(priv, 0xa8);
ecdfa446
GKH
209}
210
ecdfa446
GKH
211#ifdef CONFIG_RTL8180_IO_MAP
212
3f9ab1ee 213u8 read_nic_byte(struct r8192_priv *priv, int x)
ecdfa446 214{
3f9ab1ee 215 struct net_device *dev = priv->ieee80211->dev;
ecdfa446
GKH
216 return 0xff&inb(dev->base_addr +x);
217}
218
3f9ab1ee 219u32 read_nic_dword(struct r8192_priv *priv, int x)
ecdfa446 220{
3f9ab1ee 221 struct net_device *dev = priv->ieee80211->dev;
ecdfa446
GKH
222 return inl(dev->base_addr +x);
223}
224
3f9ab1ee 225u16 read_nic_word(struct r8192_priv *priv, int x)
ecdfa446 226{
3f9ab1ee 227 struct net_device *dev = priv->ieee80211->dev;
ecdfa446
GKH
228 return inw(dev->base_addr +x);
229}
230
3f9ab1ee 231void write_nic_byte(struct r8192_priv *priv, int x,u8 y)
ecdfa446 232{
3f9ab1ee 233 struct net_device *dev = priv->ieee80211->dev;
ecdfa446
GKH
234 outb(y&0xff,dev->base_addr +x);
235}
236
3f9ab1ee 237void write_nic_word(struct r8192_priv *priv, int x,u16 y)
ecdfa446 238{
3f9ab1ee 239 struct net_device *dev = priv->ieee80211->dev;
ecdfa446
GKH
240 outw(y,dev->base_addr +x);
241}
242
3f9ab1ee 243void write_nic_dword(struct r8192_priv *priv, int x,u32 y)
ecdfa446 244{
3f9ab1ee 245 struct net_device *dev = priv->ieee80211->dev;
ecdfa446
GKH
246 outl(y,dev->base_addr +x);
247}
248
249#else /* RTL_IO_MAP */
250
3f9ab1ee 251u8 read_nic_byte(struct r8192_priv *priv, int x)
ecdfa446 252{
3f9ab1ee 253 struct net_device *dev = priv->ieee80211->dev;
ecdfa446
GKH
254 return 0xff&readb((u8*)dev->mem_start +x);
255}
256
3f9ab1ee 257u32 read_nic_dword(struct r8192_priv *priv, int x)
ecdfa446 258{
3f9ab1ee 259 struct net_device *dev = priv->ieee80211->dev;
ecdfa446
GKH
260 return readl((u8*)dev->mem_start +x);
261}
262
3f9ab1ee 263u16 read_nic_word(struct r8192_priv *priv, int x)
ecdfa446 264{
3f9ab1ee 265 struct net_device *dev = priv->ieee80211->dev;
ecdfa446
GKH
266 return readw((u8*)dev->mem_start +x);
267}
268
3f9ab1ee 269void write_nic_byte(struct r8192_priv *priv, int x,u8 y)
ecdfa446 270{
3f9ab1ee 271 struct net_device *dev = priv->ieee80211->dev;
ecdfa446
GKH
272 writeb(y,(u8*)dev->mem_start +x);
273 udelay(20);
274}
275
3f9ab1ee 276void write_nic_dword(struct r8192_priv *priv, int x,u32 y)
ecdfa446 277{
3f9ab1ee 278 struct net_device *dev = priv->ieee80211->dev;
ecdfa446
GKH
279 writel(y,(u8*)dev->mem_start +x);
280 udelay(20);
281}
282
3f9ab1ee 283void write_nic_word(struct r8192_priv *priv, int x,u16 y)
ecdfa446 284{
3f9ab1ee 285 struct net_device *dev = priv->ieee80211->dev;
ecdfa446
GKH
286 writew(y,(u8*)dev->mem_start +x);
287 udelay(20);
288}
289
290#endif /* RTL_IO_MAP */
291
65a43784 292u8 rtl8192e_ap_sec_type(struct ieee80211_device *ieee)
293{
4a533365
MM
294 static const u8 ccmp_ie[4] = {0x00,0x50,0xf2,0x04};
295 static const u8 ccmp_rsn_ie[4] = {0x00, 0x0f, 0xac, 0x04};
65a43784 296 int wpa_ie_len= ieee->wpa_ie_len;
297 struct ieee80211_crypt_data* crypt;
298 int encrypt;
299
300 crypt = ieee->crypt[ieee->tx_keyidx];
301
207b58fb
MM
302 encrypt = (ieee->current_network.capability & WLAN_CAPABILITY_PRIVACY) ||
303 (ieee->host_encrypt && crypt && crypt->ops &&
65a43784 304 (0 == strcmp(crypt->ops->name,"WEP")));
305
306 /* simply judge */
307 if(encrypt && (wpa_ie_len == 0)) {
308 // wep encryption, no N mode setting */
309 return SEC_ALG_WEP;
310 } else if((wpa_ie_len != 0)) {
311 // parse pairwise key type */
312 if (((ieee->wpa_ie[0] == 0xdd) && (!memcmp(&(ieee->wpa_ie[14]),ccmp_ie,4))) ||
313 ((ieee->wpa_ie[0] == 0x30) && (!memcmp(&ieee->wpa_ie[10],ccmp_rsn_ie, 4))))
314 return SEC_ALG_CCMP;
315 else
316 return SEC_ALG_TKIP;
317 } else {
318 return SEC_ALG_NONE;
319 }
320}
321
322void
323rtl8192e_SetHwReg(struct net_device *dev,u8 variable,u8* val)
324{
325 struct r8192_priv* priv = ieee80211_priv(dev);
326
327 switch(variable)
328 {
329
330 case HW_VAR_BSSID:
3f9ab1ee
MM
331 write_nic_dword(priv, BSSIDR, ((u32*)(val))[0]);
332 write_nic_word(priv, BSSIDR+2, ((u16*)(val+2))[0]);
65a43784 333 break;
334
335 case HW_VAR_MEDIA_STATUS:
336 {
337 RT_OP_MODE OpMode = *((RT_OP_MODE *)(val));
3f9ab1ee 338 u8 btMsr = read_nic_byte(priv, MSR);
65a43784 339
340 btMsr &= 0xfc;
341
342 switch(OpMode)
343 {
344 case RT_OP_MODE_INFRASTRUCTURE:
345 btMsr |= MSR_INFRA;
65a43784 346 break;
347
348 case RT_OP_MODE_IBSS:
349 btMsr |= MSR_ADHOC;
65a43784 350 break;
351
352 case RT_OP_MODE_AP:
353 btMsr |= MSR_AP;
65a43784 354 break;
355
356 default:
357 btMsr |= MSR_NOLINK;
358 break;
359 }
360
3f9ab1ee 361 write_nic_byte(priv, MSR, btMsr);
65a43784 362 }
363 break;
364
951fc8ed 365 case HW_VAR_CHECK_BSSID:
65a43784 366 {
367 u32 RegRCR, Type;
368
369 Type = ((u8*)(val))[0];
3f9ab1ee 370 RegRCR = read_nic_dword(priv, RCR);
65a43784 371 priv->ReceiveConfig = RegRCR;
372
373 if (Type == true)
374 RegRCR |= (RCR_CBSSID);
375 else if (Type == false)
376 RegRCR &= (~RCR_CBSSID);
377
3f9ab1ee 378 write_nic_dword(priv, RCR,RegRCR);
65a43784 379 priv->ReceiveConfig = RegRCR;
380
381 }
382 break;
383
384 case HW_VAR_SLOT_TIME:
385 {
65a43784 386 priv->slot_time = val[0];
3f9ab1ee 387 write_nic_byte(priv, SLOT_TIME, val[0]);
65a43784 388
389 }
390 break;
391
392 case HW_VAR_ACK_PREAMBLE:
393 {
394 u32 regTmp = 0;
395 priv->short_preamble = (bool)(*(u8*)val );
396 regTmp = priv->basic_rate;
397 if (priv->short_preamble)
398 regTmp |= BRSR_AckShortPmb;
3f9ab1ee 399 write_nic_dword(priv, RRSR, regTmp);
65a43784 400 }
401 break;
402
403 case HW_VAR_CPU_RST:
3f9ab1ee 404 write_nic_dword(priv, CPU_GEN, ((u32*)(val))[0]);
65a43784 405 break;
406
407 default:
408 break;
409 }
410
411}
412
ecdfa446
GKH
413static struct proc_dir_entry *rtl8192_proc = NULL;
414
ecdfa446
GKH
415static int proc_get_stats_ap(char *page, char **start,
416 off_t offset, int count,
417 int *eof, void *data)
418{
419 struct net_device *dev = data;
420 struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
421 struct ieee80211_device *ieee = priv->ieee80211;
422 struct ieee80211_network *target;
ecdfa446
GKH
423 int len = 0;
424
425 list_for_each_entry(target, &ieee->network_list, list) {
426
427 len += snprintf(page + len, count - len,
428 "%s ", target->ssid);
429
430 if(target->wpa_ie_len>0 || target->rsn_ie_len>0){
431 len += snprintf(page + len, count - len,
432 "WPA\n");
433 }
434 else{
435 len += snprintf(page + len, count - len,
436 "non_WPA\n");
437 }
438
439 }
440
441 *eof = 1;
442 return len;
443}
444
445static int proc_get_registers(char *page, char **start,
446 off_t offset, int count,
447 int *eof, void *data)
448{
449 struct net_device *dev = data;
3f9ab1ee 450 struct r8192_priv *priv = ieee80211_priv(dev);
ecdfa446
GKH
451 int len = 0;
452 int i,n;
ecdfa446
GKH
453 int max=0xff;
454
455 /* This dump the current register page */
456 len += snprintf(page + len, count - len,
457 "\n####################page 0##################\n ");
458
459 for(n=0;n<=max;)
460 {
ecdfa446
GKH
461 len += snprintf(page + len, count - len,
462 "\nD: %2x > ",n);
463
464 for(i=0;i<16 && n<=max;i++,n++)
465 len += snprintf(page + len, count - len,
3f9ab1ee 466 "%2x ",read_nic_byte(priv,n));
ecdfa446
GKH
467 }
468 len += snprintf(page + len, count - len,"\n");
469 len += snprintf(page + len, count - len,
470 "\n####################page 1##################\n ");
471 for(n=0;n<=max;)
472 {
ecdfa446
GKH
473 len += snprintf(page + len, count - len,
474 "\nD: %2x > ",n);
475
476 for(i=0;i<16 && n<=max;i++,n++)
477 len += snprintf(page + len, count - len,
3f9ab1ee 478 "%2x ",read_nic_byte(priv,0x100|n));
ecdfa446
GKH
479 }
480
481 len += snprintf(page + len, count - len,
482 "\n####################page 3##################\n ");
483 for(n=0;n<=max;)
484 {
ecdfa446
GKH
485 len += snprintf(page + len, count - len,
486 "\nD: %2x > ",n);
487
488 for(i=0;i<16 && n<=max;i++,n++)
489 len += snprintf(page + len, count - len,
3f9ab1ee 490 "%2x ",read_nic_byte(priv,0x300|n));
ecdfa446
GKH
491 }
492
ecdfa446
GKH
493 *eof = 1;
494 return len;
495
496}
497
ecdfa446
GKH
498static int proc_get_stats_tx(char *page, char **start,
499 off_t offset, int count,
500 int *eof, void *data)
501{
502 struct net_device *dev = data;
503 struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
504
505 int len = 0;
506
507 len += snprintf(page + len, count - len,
508 "TX VI priority ok int: %lu\n"
ecdfa446 509 "TX VO priority ok int: %lu\n"
ecdfa446 510 "TX BE priority ok int: %lu\n"
ecdfa446 511 "TX BK priority ok int: %lu\n"
ecdfa446 512 "TX MANAGE priority ok int: %lu\n"
ecdfa446
GKH
513 "TX BEACON priority ok int: %lu\n"
514 "TX BEACON priority error int: %lu\n"
515 "TX CMDPKT priority ok int: %lu\n"
ecdfa446
GKH
516 "TX queue stopped?: %d\n"
517 "TX fifo overflow: %lu\n"
ecdfa446
GKH
518 "TX total data packets %lu\n"
519 "TX total data bytes :%lu\n",
ecdfa446 520 priv->stats.txviokint,
ecdfa446 521 priv->stats.txvookint,
ecdfa446 522 priv->stats.txbeokint,
ecdfa446 523 priv->stats.txbkokint,
ecdfa446 524 priv->stats.txmanageokint,
ecdfa446
GKH
525 priv->stats.txbeaconokint,
526 priv->stats.txbeaconerr,
527 priv->stats.txcmdpktokint,
ecdfa446
GKH
528 netif_queue_stopped(dev),
529 priv->stats.txoverflow,
ecdfa446 530 priv->ieee80211->stats.tx_packets,
3059f2de 531 priv->ieee80211->stats.tx_bytes);
ecdfa446
GKH
532
533 *eof = 1;
534 return len;
535}
536
537
538
539static int proc_get_stats_rx(char *page, char **start,
540 off_t offset, int count,
541 int *eof, void *data)
542{
543 struct net_device *dev = data;
544 struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
545
546 int len = 0;
547
548 len += snprintf(page + len, count - len,
549 "RX packets: %lu\n"
550 "RX desc err: %lu\n"
c282f2e3 551 "RX rx overflow error: %lu\n",
ecdfa446
GKH
552 priv->stats.rxint,
553 priv->stats.rxrdu,
c282f2e3 554 priv->stats.rxoverflow);
ecdfa446
GKH
555
556 *eof = 1;
557 return len;
558}
559
5e1ad18a 560static void rtl8192_proc_module_init(void)
ecdfa446
GKH
561{
562 RT_TRACE(COMP_INIT, "Initializing proc filesystem");
ecdfa446 563 rtl8192_proc=create_proc_entry(RTL819xE_MODULE_NAME, S_IFDIR, init_net.proc_net);
ecdfa446
GKH
564}
565
566
5e1ad18a 567static void rtl8192_proc_module_remove(void)
ecdfa446 568{
ecdfa446 569 remove_proc_entry(RTL819xE_MODULE_NAME, init_net.proc_net);
ecdfa446
GKH
570}
571
572
5e1ad18a 573static void rtl8192_proc_remove_one(struct net_device *dev)
ecdfa446
GKH
574{
575 struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
576
577 printk("dev name=======> %s\n",dev->name);
578
579 if (priv->dir_dev) {
580 // remove_proc_entry("stats-hw", priv->dir_dev);
581 remove_proc_entry("stats-tx", priv->dir_dev);
582 remove_proc_entry("stats-rx", priv->dir_dev);
583 // remove_proc_entry("stats-ieee", priv->dir_dev);
584 remove_proc_entry("stats-ap", priv->dir_dev);
585 remove_proc_entry("registers", priv->dir_dev);
586 // remove_proc_entry("cck-registers",priv->dir_dev);
587 // remove_proc_entry("ofdm-registers",priv->dir_dev);
588 //remove_proc_entry(dev->name, rtl8192_proc);
589 remove_proc_entry("wlan0", rtl8192_proc);
590 priv->dir_dev = NULL;
591 }
592}
593
594
5e1ad18a 595static void rtl8192_proc_init_one(struct net_device *dev)
ecdfa446
GKH
596{
597 struct proc_dir_entry *e;
598 struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
599 priv->dir_dev = create_proc_entry(dev->name,
600 S_IFDIR | S_IRUGO | S_IXUGO,
601 rtl8192_proc);
602 if (!priv->dir_dev) {
603 RT_TRACE(COMP_ERR, "Unable to initialize /proc/net/rtl8192/%s\n",
604 dev->name);
605 return;
606 }
ecdfa446
GKH
607 e = create_proc_read_entry("stats-rx", S_IFREG | S_IRUGO,
608 priv->dir_dev, proc_get_stats_rx, dev);
609
610 if (!e) {
611 RT_TRACE(COMP_ERR,"Unable to initialize "
612 "/proc/net/rtl8192/%s/stats-rx\n",
613 dev->name);
614 }
615
616
617 e = create_proc_read_entry("stats-tx", S_IFREG | S_IRUGO,
618 priv->dir_dev, proc_get_stats_tx, dev);
619
620 if (!e) {
621 RT_TRACE(COMP_ERR, "Unable to initialize "
622 "/proc/net/rtl8192/%s/stats-tx\n",
623 dev->name);
624 }
ecdfa446
GKH
625
626 e = create_proc_read_entry("stats-ap", S_IFREG | S_IRUGO,
627 priv->dir_dev, proc_get_stats_ap, dev);
628
629 if (!e) {
630 RT_TRACE(COMP_ERR, "Unable to initialize "
631 "/proc/net/rtl8192/%s/stats-ap\n",
632 dev->name);
633 }
634
635 e = create_proc_read_entry("registers", S_IFREG | S_IRUGO,
636 priv->dir_dev, proc_get_registers, dev);
637 if (!e) {
638 RT_TRACE(COMP_ERR, "Unable to initialize "
639 "/proc/net/rtl8192/%s/registers\n",
640 dev->name);
641 }
ecdfa446 642}
ecdfa446 643
ecdfa446
GKH
644short check_nic_enough_desc(struct net_device *dev, int prio)
645{
646 struct r8192_priv *priv = ieee80211_priv(dev);
647 struct rtl8192_tx_ring *ring = &priv->tx_ring[prio];
648
649 /* for now we reserve two free descriptor as a safety boundary
650 * between the tail and the head
651 */
285f660c 652 return (ring->entries - skb_queue_len(&ring->queue) >= 2);
ecdfa446
GKH
653}
654
5e1ad18a 655static void tx_timeout(struct net_device *dev)
ecdfa446
GKH
656{
657 struct r8192_priv *priv = ieee80211_priv(dev);
ecdfa446 658
ecdfa446 659 schedule_work(&priv->reset_wq);
ecdfa446
GKH
660 printk("TXTIMEOUT");
661}
662
5e1ad18a 663static void rtl8192_irq_enable(struct net_device *dev)
ecdfa446
GKH
664{
665 struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
666 priv->irq_enabled = 1;
3f9ab1ee 667 write_nic_dword(priv, INTA_MASK, priv->irq_mask);
ecdfa446
GKH
668}
669
65a43784 670void rtl8192_irq_disable(struct net_device *dev)
ecdfa446
GKH
671{
672 struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
673
3f9ab1ee 674 write_nic_dword(priv, INTA_MASK, 0);
ecdfa446
GKH
675 priv->irq_enabled = 0;
676}
677
ecdfa446
GKH
678void rtl8192_update_msr(struct net_device *dev)
679{
680 struct r8192_priv *priv = ieee80211_priv(dev);
681 u8 msr;
682
3f9ab1ee 683 msr = read_nic_byte(priv, MSR);
ecdfa446
GKH
684 msr &= ~ MSR_LINK_MASK;
685
686 /* do not change in link_state != WLAN_LINK_ASSOCIATED.
687 * msr must be updated if the state is ASSOCIATING.
688 * this is intentional and make sense for ad-hoc and
689 * master (see the create BSS/IBSS func)
690 */
691 if (priv->ieee80211->state == IEEE80211_LINKED){
692
693 if (priv->ieee80211->iw_mode == IW_MODE_INFRA)
694 msr |= (MSR_LINK_MANAGED<<MSR_LINK_SHIFT);
695 else if (priv->ieee80211->iw_mode == IW_MODE_ADHOC)
696 msr |= (MSR_LINK_ADHOC<<MSR_LINK_SHIFT);
697 else if (priv->ieee80211->iw_mode == IW_MODE_MASTER)
698 msr |= (MSR_LINK_MASTER<<MSR_LINK_SHIFT);
699
700 }else
701 msr |= (MSR_LINK_NONE<<MSR_LINK_SHIFT);
702
3f9ab1ee 703 write_nic_byte(priv, MSR, msr);
ecdfa446
GKH
704}
705
706void rtl8192_set_chan(struct net_device *dev,short ch)
707{
61d0e67a 708 struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
ecdfa446 709
61d0e67a 710 priv->chan = ch;
ecdfa446 711
61d0e67a 712 /* need to implement rf set channel here WB */
ecdfa446 713
61d0e67a
MM
714 if (priv->rf_set_chan)
715 priv->rf_set_chan(dev, priv->chan);
ecdfa446
GKH
716}
717
718void rtl8192_rx_enable(struct net_device *dev)
719{
7aed48d9
MM
720 struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
721
3f9ab1ee 722 write_nic_dword(priv, RDQDA,priv->rx_ring_dma);
ecdfa446
GKH
723}
724
725/* the TX_DESC_BASE setting is according to the following queue index
726 * BK_QUEUE ===> 0
727 * BE_QUEUE ===> 1
728 * VI_QUEUE ===> 2
729 * VO_QUEUE ===> 3
730 * HCCA_QUEUE ===> 4
731 * TXCMD_QUEUE ===> 5
732 * MGNT_QUEUE ===> 6
733 * HIGH_QUEUE ===> 7
734 * BEACON_QUEUE ===> 8
735 * */
881a975b 736static const u32 TX_DESC_BASE[] = {BKQDA, BEQDA, VIQDA, VOQDA, HCCAQDA, CQDA, MQDA, HQDA, BQDA};
ecdfa446
GKH
737void rtl8192_tx_enable(struct net_device *dev)
738{
7aed48d9
MM
739 struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
740 u32 i;
ecdfa446 741
7aed48d9 742 for (i = 0; i < MAX_TX_QUEUE_COUNT; i++)
3f9ab1ee 743 write_nic_dword(priv, TX_DESC_BASE[i], priv->tx_ring[i].dma);
7aed48d9
MM
744
745 ieee80211_reset_queue(priv->ieee80211);
ecdfa446
GKH
746}
747
ecdfa446
GKH
748
749static void rtl8192_free_rx_ring(struct net_device *dev)
750{
7aed48d9
MM
751 struct r8192_priv *priv = ieee80211_priv(dev);
752 int i;
ecdfa446 753
7aed48d9
MM
754 for (i = 0; i < priv->rxringcount; i++) {
755 struct sk_buff *skb = priv->rx_buf[i];
756 if (!skb)
757 continue;
ecdfa446 758
7aed48d9
MM
759 pci_unmap_single(priv->pdev,
760 *((dma_addr_t *)skb->cb),
761 priv->rxbuffersize, PCI_DMA_FROMDEVICE);
762 kfree_skb(skb);
763 }
ecdfa446 764
7aed48d9
MM
765 pci_free_consistent(priv->pdev, sizeof(*priv->rx_ring) * priv->rxringcount,
766 priv->rx_ring, priv->rx_ring_dma);
767 priv->rx_ring = NULL;
ecdfa446
GKH
768}
769
770static void rtl8192_free_tx_ring(struct net_device *dev, unsigned int prio)
771{
7aed48d9
MM
772 struct r8192_priv *priv = ieee80211_priv(dev);
773 struct rtl8192_tx_ring *ring = &priv->tx_ring[prio];
ecdfa446 774
7aed48d9
MM
775 while (skb_queue_len(&ring->queue)) {
776 tx_desc_819x_pci *entry = &ring->desc[ring->idx];
777 struct sk_buff *skb = __skb_dequeue(&ring->queue);
ecdfa446 778
7aed48d9
MM
779 pci_unmap_single(priv->pdev, le32_to_cpu(entry->TxBuffAddr),
780 skb->len, PCI_DMA_TODEVICE);
781 kfree_skb(skb);
782 ring->idx = (ring->idx + 1) % ring->entries;
783 }
ecdfa446 784
7aed48d9
MM
785 pci_free_consistent(priv->pdev, sizeof(*ring->desc)*ring->entries,
786 ring->desc, ring->dma);
787 ring->desc = NULL;
ecdfa446
GKH
788}
789
16d74da0 790void PHY_SetRtl8192eRfOff(struct net_device* dev)
ecdfa446 791{
3f9ab1ee
MM
792 struct r8192_priv *priv = ieee80211_priv(dev);
793
65a43784 794 //disable RF-Chip A/B
795 rtl8192_setBBreg(dev, rFPGA0_XA_RFInterfaceOE, BIT4, 0x0);
796 //analog to digital off, for power save
797 rtl8192_setBBreg(dev, rFPGA0_AnalogParameter4, 0x300, 0x0);
798 //digital to analog off, for power save
799 rtl8192_setBBreg(dev, rFPGA0_AnalogParameter1, 0x18, 0x0);
800 //rx antenna off
801 rtl8192_setBBreg(dev, rOFDM0_TRxPathEnable, 0xf, 0x0);
802 //rx antenna off
803 rtl8192_setBBreg(dev, rOFDM1_TRxPathEnable, 0xf, 0x0);
804 //analog to digital part2 off, for power save
805 rtl8192_setBBreg(dev, rFPGA0_AnalogParameter1, 0x60, 0x0);
806 rtl8192_setBBreg(dev, rFPGA0_AnalogParameter1, 0x4, 0x0);
807 // Analog parameter!!Change bias and Lbus control.
3f9ab1ee 808 write_nic_byte(priv, ANAPAR_FOR_8192PciE, 0x07);
65a43784 809
810}
ecdfa446 811
65a43784 812void rtl8192_halt_adapter(struct net_device *dev, bool reset)
ecdfa446 813{
ecdfa446 814 struct r8192_priv *priv = ieee80211_priv(dev);
65a43784 815 int i;
932f4b3a
MM
816 u8 OpMode;
817 u32 ulRegRead;
65a43784 818
819 OpMode = RT_OP_MODE_NO_LINK;
820 priv->ieee80211->SetHwRegHandler(dev, HW_VAR_MEDIA_STATUS, &OpMode);
ecdfa446 821
932f4b3a
MM
822 if (!priv->ieee80211->bSupportRemoteWakeUp) {
823 /*
824 * disable tx/rx. In 8185 we write 0x10 (Reset bit),
825 * but here we make reference to WMAC and wirte 0x0
826 */
3f9ab1ee 827 write_nic_byte(priv, CMDR, 0);
65a43784 828 }
ecdfa446 829
65a43784 830 mdelay(20);
ecdfa446 831
932f4b3a 832 if (!reset) {
65a43784 833 mdelay(150);
834
932f4b3a 835 priv->bHwRfOffAction = 2;
65a43784 836
932f4b3a
MM
837 /*
838 * Call MgntActSet_RF_State instead to
839 * prevent RF config race condition.
840 */
841 if (!priv->ieee80211->bSupportRemoteWakeUp) {
65a43784 842 PHY_SetRtl8192eRfOff(dev);
3f9ab1ee 843 ulRegRead = read_nic_dword(priv, CPU_GEN);
932f4b3a 844 ulRegRead |= CPU_GEN_SYSTEM_RESET;
3f9ab1ee 845 write_nic_dword(priv,CPU_GEN, ulRegRead);
932f4b3a
MM
846 } else {
847 /* for WOL */
3f9ab1ee
MM
848 write_nic_dword(priv, WFCRC0, 0xffffffff);
849 write_nic_dword(priv, WFCRC1, 0xffffffff);
850 write_nic_dword(priv, WFCRC2, 0xffffffff);
65a43784 851
932f4b3a 852 /* Write PMR register */
3f9ab1ee 853 write_nic_byte(priv, PMR, 0x5);
932f4b3a 854 /* Disable tx, enanble rx */
3f9ab1ee 855 write_nic_byte(priv, MacBlkCtrl, 0xa);
65a43784 856 }
857 }
858
859 for(i = 0; i < MAX_QUEUE_SIZE; i++) {
860 skb_queue_purge(&priv->ieee80211->skb_waitQ [i]);
861 }
862 for(i = 0; i < MAX_QUEUE_SIZE; i++) {
863 skb_queue_purge(&priv->ieee80211->skb_aggQ [i]);
864 }
ecdfa446
GKH
865
866 skb_queue_purge(&priv->skb_queue);
ecdfa446
GKH
867}
868
881a975b 869static const u16 rtl_rate[] = {10,20,55,110,60,90,120,180,240,360,480,540};
ecdfa446
GKH
870inline u16 rtl8192_rate2rate(short rate)
871{
872 if (rate >11) return 0;
873 return rtl_rate[rate];
874}
875
5e1ad18a 876static void rtl8192_data_hard_stop(struct net_device *dev)
ecdfa446 877{
ecdfa446
GKH
878}
879
5e1ad18a 880static void rtl8192_data_hard_resume(struct net_device *dev)
ecdfa446 881{
ecdfa446
GKH
882}
883
214985a6
MM
884/*
885 * this function TX data frames when the ieee80211 stack requires this.
ecdfa446
GKH
886 * It checks also if we need to stop the ieee tx queue, eventually do it
887 */
5e1ad18a 888static void rtl8192_hard_data_xmit(struct sk_buff *skb, struct net_device *dev, int rate)
ecdfa446
GKH
889{
890 struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
891 int ret;
ecdfa446
GKH
892 cb_desc *tcb_desc = (cb_desc *)(skb->cb + MAX_DEV_ADDR_SIZE);
893 u8 queue_index = tcb_desc->queue_index;
dcf663fb 894
ecdfa446 895 /* shall not be referred by command packet */
5d33549a 896 BUG_ON(queue_index == TXCMD_QUEUE);
ecdfa446 897
dcf663fb 898 if (priv->bHwRadioOff || (!priv->up))
65a43784 899 {
900 kfree_skb(skb);
901 return;
902 }
903
dcf663fb 904 memcpy(skb->cb, &dev, sizeof(dev));
ecdfa446 905
ecdfa446
GKH
906 skb_push(skb, priv->ieee80211->tx_headroom);
907 ret = rtl8192_tx(dev, skb);
dcf663fb 908 if (ret != 0) {
ecdfa446 909 kfree_skb(skb);
ecdfa446
GKH
910 }
911
dcf663fb
MM
912 if (queue_index != MGNT_QUEUE) {
913 priv->ieee80211->stats.tx_bytes += (skb->len - priv->ieee80211->tx_headroom);
914 priv->ieee80211->stats.tx_packets++;
915 }
ecdfa446
GKH
916}
917
214985a6
MM
918/*
919 * This is a rough attempt to TX a frame
ecdfa446
GKH
920 * This is called by the ieee 80211 stack to TX management frames.
921 * If the ring is full packet are dropped (for data frame the queue
922 * is stopped before this can happen).
923 */
5e1ad18a 924static int rtl8192_hard_start_xmit(struct sk_buff *skb,struct net_device *dev)
ecdfa446
GKH
925{
926 struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
ecdfa446 927 int ret;
ecdfa446
GKH
928 cb_desc *tcb_desc = (cb_desc *)(skb->cb + MAX_DEV_ADDR_SIZE);
929 u8 queue_index = tcb_desc->queue_index;
930
162f535f
MM
931 if (queue_index != TXCMD_QUEUE) {
932 if (priv->bHwRadioOff || (!priv->up))
65a43784 933 {
162f535f
MM
934 kfree_skb(skb);
935 return 0;
936 }
65a43784 937 }
ecdfa446 938
162f535f
MM
939 memcpy(skb->cb, &dev, sizeof(dev));
940 if (queue_index == TXCMD_QUEUE) {
ecdfa446
GKH
941 rtl819xE_tx_cmd(dev, skb);
942 ret = 0;
ecdfa446
GKH
943 return ret;
944 } else {
ecdfa446
GKH
945 tcb_desc->RATRIndex = 7;
946 tcb_desc->bTxDisableRateFallBack = 1;
947 tcb_desc->bTxUseDriverAssingedRate = 1;
948 tcb_desc->bTxEnableFwCalcDur = 1;
949 skb_push(skb, priv->ieee80211->tx_headroom);
950 ret = rtl8192_tx(dev, skb);
162f535f 951 if (ret != 0) {
ecdfa446 952 kfree_skb(skb);
162f535f 953 }
ecdfa446
GKH
954 }
955
ecdfa446 956 return ret;
ecdfa446
GKH
957}
958
959
5e1ad18a 960static void rtl8192_tx_isr(struct net_device *dev, int prio)
ecdfa446 961{
a922a4b7
MM
962 struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
963 struct rtl8192_tx_ring *ring = &priv->tx_ring[prio];
ecdfa446 964
a922a4b7
MM
965 while (skb_queue_len(&ring->queue)) {
966 tx_desc_819x_pci *entry = &ring->desc[ring->idx];
967 struct sk_buff *skb;
ecdfa446 968
a922a4b7
MM
969 /*
970 * beacon packet will only use the first descriptor defaultly,
971 * and the OWN may not be cleared by the hardware
972 */
973 if (prio != BEACON_QUEUE) {
974 if (entry->OWN)
975 return;
976 ring->idx = (ring->idx + 1) % ring->entries;
977 }
ecdfa446 978
a922a4b7
MM
979 skb = __skb_dequeue(&ring->queue);
980 pci_unmap_single(priv->pdev, le32_to_cpu(entry->TxBuffAddr),
981 skb->len, PCI_DMA_TODEVICE);
ecdfa446 982
a922a4b7
MM
983 kfree_skb(skb);
984 }
ecdfa446 985
a922a4b7
MM
986 if (prio != BEACON_QUEUE) {
987 /* try to deal with the pending packets */
988 tasklet_schedule(&priv->irq_tx_tasklet);
989 }
ecdfa446
GKH
990}
991
5e1ad18a 992static void rtl8192_stop_beacon(struct net_device *dev)
ecdfa446 993{
ecdfa446
GKH
994}
995
5e1ad18a 996static void rtl8192_config_rate(struct net_device* dev, u16* rate_config)
ecdfa446
GKH
997{
998 struct r8192_priv *priv = ieee80211_priv(dev);
999 struct ieee80211_network *net;
1000 u8 i=0, basic_rate = 0;
1001 net = & priv->ieee80211->current_network;
1002
1003 for (i=0; i<net->rates_len; i++)
1004 {
1005 basic_rate = net->rates[i]&0x7f;
1006 switch(basic_rate)
1007 {
1008 case MGN_1M: *rate_config |= RRSR_1M; break;
1009 case MGN_2M: *rate_config |= RRSR_2M; break;
1010 case MGN_5_5M: *rate_config |= RRSR_5_5M; break;
1011 case MGN_11M: *rate_config |= RRSR_11M; break;
1012 case MGN_6M: *rate_config |= RRSR_6M; break;
1013 case MGN_9M: *rate_config |= RRSR_9M; break;
1014 case MGN_12M: *rate_config |= RRSR_12M; break;
1015 case MGN_18M: *rate_config |= RRSR_18M; break;
1016 case MGN_24M: *rate_config |= RRSR_24M; break;
1017 case MGN_36M: *rate_config |= RRSR_36M; break;
1018 case MGN_48M: *rate_config |= RRSR_48M; break;
1019 case MGN_54M: *rate_config |= RRSR_54M; break;
1020 }
1021 }
1022 for (i=0; i<net->rates_ex_len; i++)
1023 {
1024 basic_rate = net->rates_ex[i]&0x7f;
1025 switch(basic_rate)
1026 {
1027 case MGN_1M: *rate_config |= RRSR_1M; break;
1028 case MGN_2M: *rate_config |= RRSR_2M; break;
1029 case MGN_5_5M: *rate_config |= RRSR_5_5M; break;
1030 case MGN_11M: *rate_config |= RRSR_11M; break;
1031 case MGN_6M: *rate_config |= RRSR_6M; break;
1032 case MGN_9M: *rate_config |= RRSR_9M; break;
1033 case MGN_12M: *rate_config |= RRSR_12M; break;
1034 case MGN_18M: *rate_config |= RRSR_18M; break;
1035 case MGN_24M: *rate_config |= RRSR_24M; break;
1036 case MGN_36M: *rate_config |= RRSR_36M; break;
1037 case MGN_48M: *rate_config |= RRSR_48M; break;
1038 case MGN_54M: *rate_config |= RRSR_54M; break;
1039 }
1040 }
1041}
1042
1043
1044#define SHORT_SLOT_TIME 9
1045#define NON_SHORT_SLOT_TIME 20
1046
5e1ad18a 1047static void rtl8192_update_cap(struct net_device* dev, u16 cap)
ecdfa446
GKH
1048{
1049 u32 tmp = 0;
1050 struct r8192_priv *priv = ieee80211_priv(dev);
1051 struct ieee80211_network *net = &priv->ieee80211->current_network;
1052 priv->short_preamble = cap & WLAN_CAPABILITY_SHORT_PREAMBLE;
1053 tmp = priv->basic_rate;
1054 if (priv->short_preamble)
1055 tmp |= BRSR_AckShortPmb;
3f9ab1ee 1056 write_nic_dword(priv, RRSR, tmp);
ecdfa446
GKH
1057
1058 if (net->mode & (IEEE_G|IEEE_N_24G))
1059 {
1060 u8 slot_time = 0;
1061 if ((cap & WLAN_CAPABILITY_SHORT_SLOT)&&(!priv->ieee80211->pHTInfo->bCurrentRT2RTLongSlotTime))
1062 {//short slot time
1063 slot_time = SHORT_SLOT_TIME;
1064 }
1065 else //long slot time
1066 slot_time = NON_SHORT_SLOT_TIME;
1067 priv->slot_time = slot_time;
3f9ab1ee 1068 write_nic_byte(priv, SLOT_TIME, slot_time);
ecdfa446
GKH
1069 }
1070
1071}
5e1ad18a
GKH
1072
1073static void rtl8192_net_update(struct net_device *dev)
ecdfa446 1074{
ecdfa446
GKH
1075 struct r8192_priv *priv = ieee80211_priv(dev);
1076 struct ieee80211_network *net;
1077 u16 BcnTimeCfg = 0, BcnCW = 6, BcnIFS = 0xf;
1078 u16 rate_config = 0;
1079 net = &priv->ieee80211->current_network;
eb40aeac
MM
1080
1081 /* update Basic rate: RR, BRSR */
ecdfa446 1082 rtl8192_config_rate(dev, &rate_config);
ecdfa446 1083
eb40aeac
MM
1084 /*
1085 * Select RRSR (in Legacy-OFDM and CCK)
1086 * For 8190, we select only 24M, 12M, 6M, 11M, 5.5M,
1087 * 2M, and 1M from the Basic rate.
1088 * We do not use other rates.
1089 */
1090 priv->basic_rate = rate_config &= 0x15f;
1091
1092 /* BSSID */
3f9ab1ee
MM
1093 write_nic_dword(priv, BSSIDR, ((u32 *)net->bssid)[0]);
1094 write_nic_word(priv, BSSIDR+4, ((u16 *)net->bssid)[2]);
ecdfa446 1095
ecdfa446
GKH
1096 if (priv->ieee80211->iw_mode == IW_MODE_ADHOC)
1097 {
3f9ab1ee
MM
1098 write_nic_word(priv, ATIMWND, 2);
1099 write_nic_word(priv, BCN_DMATIME, 256);
1100 write_nic_word(priv, BCN_INTERVAL, net->beacon_interval);
eb40aeac
MM
1101 /*
1102 * BIT15 of BCN_DRV_EARLY_INT will indicate
1103 * whether software beacon or hw beacon is applied.
1104 */
3f9ab1ee
MM
1105 write_nic_word(priv, BCN_DRV_EARLY_INT, 10);
1106 write_nic_byte(priv, BCN_ERR_THRESH, 100);
ecdfa446
GKH
1107
1108 BcnTimeCfg |= (BcnCW<<BCN_TCFG_CW_SHIFT);
eb40aeac
MM
1109 /* TODO: BcnIFS may required to be changed on ASIC */
1110 BcnTimeCfg |= BcnIFS<<BCN_TCFG_IFS;
3f9ab1ee 1111 write_nic_word(priv, BCN_TCFG, BcnTimeCfg);
ecdfa446 1112 }
ecdfa446
GKH
1113}
1114
ecdfa446
GKH
1115void rtl819xE_tx_cmd(struct net_device *dev, struct sk_buff *skb)
1116{
1117 struct r8192_priv *priv = ieee80211_priv(dev);
1118 struct rtl8192_tx_ring *ring;
1119 tx_desc_819x_pci *entry;
1120 unsigned int idx;
1121 dma_addr_t mapping;
1122 cb_desc *tcb_desc;
1123 unsigned long flags;
1124
1125 ring = &priv->tx_ring[TXCMD_QUEUE];
1126 mapping = pci_map_single(priv->pdev, skb->data, skb->len, PCI_DMA_TODEVICE);
1127
1128 spin_lock_irqsave(&priv->irq_th_lock,flags);
1129 idx = (ring->idx + skb_queue_len(&ring->queue)) % ring->entries;
1130 entry = &ring->desc[idx];
1131
1132 tcb_desc = (cb_desc *)(skb->cb + MAX_DEV_ADDR_SIZE);
1133 memset(entry,0,12);
1134 entry->LINIP = tcb_desc->bLastIniPkt;
1135 entry->FirstSeg = 1;//first segment
1136 entry->LastSeg = 1; //last segment
1137 if(tcb_desc->bCmdOrInit == DESC_PACKET_TYPE_INIT) {
1138 entry->CmdInit = DESC_PACKET_TYPE_INIT;
1139 } else {
1140 entry->CmdInit = DESC_PACKET_TYPE_NORMAL;
1141 entry->Offset = sizeof(TX_FWINFO_8190PCI) + 8;
1142 entry->PktSize = (u16)(tcb_desc->pkt_size + entry->Offset);
1143 entry->QueueSelect = QSLT_CMD;
1144 entry->TxFWInfoSize = 0x08;
1145 entry->RATid = (u8)DESC_PACKET_TYPE_INIT;
1146 }
1147 entry->TxBufferSize = skb->len;
1148 entry->TxBuffAddr = cpu_to_le32(mapping);
1149 entry->OWN = 1;
1150
ecdfa446
GKH
1151 __skb_queue_tail(&ring->queue, skb);
1152 spin_unlock_irqrestore(&priv->irq_th_lock,flags);
1153
3f9ab1ee 1154 write_nic_byte(priv, TPPoll, TPPoll_CQ);
ecdfa446
GKH
1155
1156 return;
1157}
1158
1159/*
1160 * Mapping Software/Hardware descriptor queue id to "Queue Select Field"
1161 * in TxFwInfo data structure
214985a6 1162 */
5e1ad18a 1163static u8 MapHwQueueToFirmwareQueue(u8 QueueID)
ecdfa446 1164{
f72b6a50 1165 u8 QueueSelect = 0;
ecdfa446 1166
f72b6a50
MM
1167 switch (QueueID) {
1168 case BE_QUEUE:
1169 QueueSelect = QSLT_BE;
1170 break;
ecdfa446 1171
f72b6a50
MM
1172 case BK_QUEUE:
1173 QueueSelect = QSLT_BK;
1174 break;
ecdfa446 1175
f72b6a50
MM
1176 case VO_QUEUE:
1177 QueueSelect = QSLT_VO;
1178 break;
ecdfa446 1179
f72b6a50
MM
1180 case VI_QUEUE:
1181 QueueSelect = QSLT_VI;
1182 break;
ecdfa446 1183
f72b6a50
MM
1184 case MGNT_QUEUE:
1185 QueueSelect = QSLT_MGNT;
1186 break;
ecdfa446 1187
f72b6a50
MM
1188 case BEACON_QUEUE:
1189 QueueSelect = QSLT_BEACON;
1190 break;
ecdfa446 1191
f72b6a50
MM
1192 case TXCMD_QUEUE:
1193 QueueSelect = QSLT_CMD;
1194 break;
1195
1196 case HIGH_QUEUE:
1197 default:
1198 RT_TRACE(COMP_ERR, "Impossible Queue Selection: %d\n", QueueID);
1199 break;
ecdfa446
GKH
1200 }
1201 return QueueSelect;
1202}
1203
5e1ad18a 1204static u8 MRateToHwRate8190Pci(u8 rate)
ecdfa446
GKH
1205{
1206 u8 ret = DESC90_RATE1M;
1207
1208 switch(rate) {
1209 case MGN_1M: ret = DESC90_RATE1M; break;
1210 case MGN_2M: ret = DESC90_RATE2M; break;
1211 case MGN_5_5M: ret = DESC90_RATE5_5M; break;
1212 case MGN_11M: ret = DESC90_RATE11M; break;
1213 case MGN_6M: ret = DESC90_RATE6M; break;
1214 case MGN_9M: ret = DESC90_RATE9M; break;
1215 case MGN_12M: ret = DESC90_RATE12M; break;
1216 case MGN_18M: ret = DESC90_RATE18M; break;
1217 case MGN_24M: ret = DESC90_RATE24M; break;
1218 case MGN_36M: ret = DESC90_RATE36M; break;
1219 case MGN_48M: ret = DESC90_RATE48M; break;
1220 case MGN_54M: ret = DESC90_RATE54M; break;
1221
1222 // HT rate since here
1223 case MGN_MCS0: ret = DESC90_RATEMCS0; break;
1224 case MGN_MCS1: ret = DESC90_RATEMCS1; break;
1225 case MGN_MCS2: ret = DESC90_RATEMCS2; break;
1226 case MGN_MCS3: ret = DESC90_RATEMCS3; break;
1227 case MGN_MCS4: ret = DESC90_RATEMCS4; break;
1228 case MGN_MCS5: ret = DESC90_RATEMCS5; break;
1229 case MGN_MCS6: ret = DESC90_RATEMCS6; break;
1230 case MGN_MCS7: ret = DESC90_RATEMCS7; break;
1231 case MGN_MCS8: ret = DESC90_RATEMCS8; break;
1232 case MGN_MCS9: ret = DESC90_RATEMCS9; break;
1233 case MGN_MCS10: ret = DESC90_RATEMCS10; break;
1234 case MGN_MCS11: ret = DESC90_RATEMCS11; break;
1235 case MGN_MCS12: ret = DESC90_RATEMCS12; break;
1236 case MGN_MCS13: ret = DESC90_RATEMCS13; break;
1237 case MGN_MCS14: ret = DESC90_RATEMCS14; break;
1238 case MGN_MCS15: ret = DESC90_RATEMCS15; break;
1239 case (0x80|0x20): ret = DESC90_RATEMCS32; break;
1240
1241 default: break;
1242 }
1243 return ret;
1244}
1245
1246
5e1ad18a 1247static u8 QueryIsShort(u8 TxHT, u8 TxRate, cb_desc *tcb_desc)
ecdfa446
GKH
1248{
1249 u8 tmp_Short;
1250
1251 tmp_Short = (TxHT==1)?((tcb_desc->bUseShortGI)?1:0):((tcb_desc->bUseShortPreamble)?1:0);
1252
1253 if(TxHT==1 && TxRate != DESC90_RATEMCS15)
1254 tmp_Short = 0;
1255
1256 return tmp_Short;
1257}
1258
1259/*
1260 * The tx procedure is just as following,
1261 * skb->cb will contain all the following information,
1262 * priority, morefrag, rate, &dev.
214985a6 1263 */
ecdfa446
GKH
1264short rtl8192_tx(struct net_device *dev, struct sk_buff* skb)
1265{
067ba6cf
MM
1266 struct r8192_priv *priv = ieee80211_priv(dev);
1267 struct rtl8192_tx_ring *ring;
1268 unsigned long flags;
1269 cb_desc *tcb_desc = (cb_desc *)(skb->cb + MAX_DEV_ADDR_SIZE);
1270 tx_desc_819x_pci *pdesc = NULL;
1271 TX_FWINFO_8190PCI *pTxFwInfo = NULL;
1272 dma_addr_t mapping;
1273 bool multi_addr = false, broad_addr = false, uni_addr = false;
1274 u8 *pda_addr = NULL;
1275 int idx;
1276
1277 if (priv->bdisable_nic) {
1278 RT_TRACE(COMP_ERR, "Nic is disabled! Can't tx packet len=%d qidx=%d!!!\n",
1279 skb->len, tcb_desc->queue_index);
65a43784 1280 return skb->len;
067ba6cf 1281 }
65a43784 1282
1283#ifdef ENABLE_LPS
1284 priv->ieee80211->bAwakePktSent = true;
1285#endif
1286
067ba6cf
MM
1287 mapping = pci_map_single(priv->pdev, skb->data, skb->len, PCI_DMA_TODEVICE);
1288
1289 /* collect the tx packets statitcs */
1290 pda_addr = ((u8 *)skb->data) + sizeof(TX_FWINFO_8190PCI);
1291 if (is_multicast_ether_addr(pda_addr))
1292 multi_addr = true;
1293 else if (is_broadcast_ether_addr(pda_addr))
1294 broad_addr = true;
1295 else
1296 uni_addr = true;
1297
1298 if (uni_addr)
1299 priv->stats.txbytesunicast += (u8)(skb->len) - sizeof(TX_FWINFO_8190PCI);
067ba6cf
MM
1300
1301 /* fill tx firmware */
1302 pTxFwInfo = (PTX_FWINFO_8190PCI)skb->data;
1303 memset(pTxFwInfo, 0, sizeof(TX_FWINFO_8190PCI));
1304 pTxFwInfo->TxHT = (tcb_desc->data_rate&0x80) ? 1 : 0;
1305 pTxFwInfo->TxRate = MRateToHwRate8190Pci((u8)tcb_desc->data_rate);
1306 pTxFwInfo->EnableCPUDur = tcb_desc->bTxEnableFwCalcDur;
1307 pTxFwInfo->Short = QueryIsShort(pTxFwInfo->TxHT, pTxFwInfo->TxRate, tcb_desc);
1308
1309 /* Aggregation related */
1310 if (tcb_desc->bAMPDUEnable) {
1311 pTxFwInfo->AllowAggregation = 1;
1312 pTxFwInfo->RxMF = tcb_desc->ampdu_factor;
1313 pTxFwInfo->RxAMD = tcb_desc->ampdu_density;
1314 } else {
1315 pTxFwInfo->AllowAggregation = 0;
1316 pTxFwInfo->RxMF = 0;
1317 pTxFwInfo->RxAMD = 0;
1318 }
ecdfa446 1319
067ba6cf
MM
1320 /* Protection mode related */
1321 pTxFwInfo->RtsEnable = (tcb_desc->bRTSEnable) ? 1 : 0;
1322 pTxFwInfo->CtsEnable = (tcb_desc->bCTSEnable) ? 1 : 0;
1323 pTxFwInfo->RtsSTBC = (tcb_desc->bRTSSTBC) ? 1 : 0;
1324 pTxFwInfo->RtsHT = (tcb_desc->rts_rate&0x80) ? 1 : 0;
1325 pTxFwInfo->RtsRate = MRateToHwRate8190Pci((u8)tcb_desc->rts_rate);
1326 pTxFwInfo->RtsBandwidth = 0;
1327 pTxFwInfo->RtsSubcarrier = tcb_desc->RTSSC;
1328 pTxFwInfo->RtsShort = (pTxFwInfo->RtsHT == 0) ? (tcb_desc->bRTSUseShortPreamble ? 1 : 0) : (tcb_desc->bRTSUseShortGI? 1 : 0);
1329
1330 /* Set Bandwidth and sub-channel settings. */
1331 if (priv->CurrentChannelBW == HT_CHANNEL_WIDTH_20_40) {
1332 if (tcb_desc->bPacketBW) {
1333 pTxFwInfo->TxBandwidth = 1;
067ba6cf
MM
1334 /* use duplicated mode */
1335 pTxFwInfo->TxSubCarrier = 0;
067ba6cf
MM
1336 } else {
1337 pTxFwInfo->TxBandwidth = 0;
1338 pTxFwInfo->TxSubCarrier = priv->nCur40MhzPrimeSC;
1339 }
1340 } else {
1341 pTxFwInfo->TxBandwidth = 0;
1342 pTxFwInfo->TxSubCarrier = 0;
1343 }
ecdfa446 1344
067ba6cf
MM
1345 spin_lock_irqsave(&priv->irq_th_lock, flags);
1346 ring = &priv->tx_ring[tcb_desc->queue_index];
1347 if (tcb_desc->queue_index != BEACON_QUEUE)
1348 idx = (ring->idx + skb_queue_len(&ring->queue)) % ring->entries;
1349 else
1350 idx = 0;
1351
1352 pdesc = &ring->desc[idx];
1353 if ((pdesc->OWN == 1) && (tcb_desc->queue_index != BEACON_QUEUE)) {
1354 RT_TRACE(COMP_ERR, "No more TX desc@%d, ring->idx = %d,idx = %d,%x",
1355 tcb_desc->queue_index, ring->idx, idx, skb->len);
1356 spin_unlock_irqrestore(&priv->irq_th_lock, flags);
1357 return skb->len;
1358 }
ecdfa446 1359
067ba6cf
MM
1360 /* fill tx descriptor */
1361 memset(pdesc, 0, 12);
1362
1363 /*DWORD 0*/
1364 pdesc->LINIP = 0;
1365 pdesc->CmdInit = 1;
1366 pdesc->Offset = sizeof(TX_FWINFO_8190PCI) + 8; /* We must add 8!! */
1367 pdesc->PktSize = (u16)skb->len-sizeof(TX_FWINFO_8190PCI);
1368
1369 /*DWORD 1*/
1370 pdesc->SecCAMID = 0;
1371 pdesc->RATid = tcb_desc->RATRIndex;
1372
1373 pdesc->NoEnc = 1;
1374 pdesc->SecType = 0x0;
1375 if (tcb_desc->bHwSec) {
1376 switch (priv->ieee80211->pairwise_key_type) {
1377 case KEY_TYPE_WEP40:
1378 case KEY_TYPE_WEP104:
1379 pdesc->SecType = 0x1;
1380 pdesc->NoEnc = 0;
1381 break;
1382 case KEY_TYPE_TKIP:
1383 pdesc->SecType = 0x2;
1384 pdesc->NoEnc = 0;
1385 break;
1386 case KEY_TYPE_CCMP:
1387 pdesc->SecType = 0x3;
1388 pdesc->NoEnc = 0;
1389 break;
1390 case KEY_TYPE_NA:
1391 pdesc->SecType = 0x0;
1392 pdesc->NoEnc = 1;
1393 break;
1394 }
1395 }
ecdfa446 1396
067ba6cf
MM
1397 /* Set Packet ID */
1398 pdesc->PktId = 0x0;
ecdfa446 1399
067ba6cf
MM
1400 pdesc->QueueSelect = MapHwQueueToFirmwareQueue(tcb_desc->queue_index);
1401 pdesc->TxFWInfoSize = sizeof(TX_FWINFO_8190PCI);
ecdfa446 1402
067ba6cf
MM
1403 pdesc->DISFB = tcb_desc->bTxDisableRateFallBack;
1404 pdesc->USERATE = tcb_desc->bTxUseDriverAssingedRate;
ecdfa446 1405
067ba6cf
MM
1406 pdesc->FirstSeg = 1;
1407 pdesc->LastSeg = 1;
1408 pdesc->TxBufferSize = skb->len;
ecdfa446 1409
067ba6cf
MM
1410 pdesc->TxBuffAddr = cpu_to_le32(mapping);
1411 __skb_queue_tail(&ring->queue, skb);
1412 pdesc->OWN = 1;
1413 spin_unlock_irqrestore(&priv->irq_th_lock, flags);
1414 dev->trans_start = jiffies;
3f9ab1ee 1415 write_nic_word(priv, TPPoll, 0x01<<tcb_desc->queue_index);
067ba6cf 1416 return 0;
ecdfa446
GKH
1417}
1418
5e1ad18a 1419static short rtl8192_alloc_rx_desc_ring(struct net_device *dev)
ecdfa446
GKH
1420{
1421 struct r8192_priv *priv = ieee80211_priv(dev);
1422 rx_desc_819x_pci *entry = NULL;
1423 int i;
1424
1425 priv->rx_ring = pci_alloc_consistent(priv->pdev,
1426 sizeof(*priv->rx_ring) * priv->rxringcount, &priv->rx_ring_dma);
1427
1428 if (!priv->rx_ring || (unsigned long)priv->rx_ring & 0xFF) {
1429 RT_TRACE(COMP_ERR,"Cannot allocate RX ring\n");
1430 return -ENOMEM;
1431 }
1432
1433 memset(priv->rx_ring, 0, sizeof(*priv->rx_ring) * priv->rxringcount);
1434 priv->rx_idx = 0;
1435
1436 for (i = 0; i < priv->rxringcount; i++) {
1437 struct sk_buff *skb = dev_alloc_skb(priv->rxbuffersize);
1438 dma_addr_t *mapping;
1439 entry = &priv->rx_ring[i];
1440 if (!skb)
1441 return 0;
1442 priv->rx_buf[i] = skb;
1443 mapping = (dma_addr_t *)skb->cb;
1c7ec2e8 1444 *mapping = pci_map_single(priv->pdev, skb_tail_pointer(skb),
ecdfa446
GKH
1445 priv->rxbuffersize, PCI_DMA_FROMDEVICE);
1446
1447 entry->BufferAddress = cpu_to_le32(*mapping);
1448
1449 entry->Length = priv->rxbuffersize;
1450 entry->OWN = 1;
1451 }
1452
1453 entry->EOR = 1;
1454 return 0;
1455}
1456
1457static int rtl8192_alloc_tx_desc_ring(struct net_device *dev,
1458 unsigned int prio, unsigned int entries)
1459{
1460 struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
1461 tx_desc_819x_pci *ring;
1462 dma_addr_t dma;
1463 int i;
1464
1465 ring = pci_alloc_consistent(priv->pdev, sizeof(*ring) * entries, &dma);
1466 if (!ring || (unsigned long)ring & 0xFF) {
1467 RT_TRACE(COMP_ERR, "Cannot allocate TX ring (prio = %d)\n", prio);
1468 return -ENOMEM;
1469 }
1470
1471 memset(ring, 0, sizeof(*ring)*entries);
1472 priv->tx_ring[prio].desc = ring;
1473 priv->tx_ring[prio].dma = dma;
1474 priv->tx_ring[prio].idx = 0;
1475 priv->tx_ring[prio].entries = entries;
1476 skb_queue_head_init(&priv->tx_ring[prio].queue);
1477
1478 for (i = 0; i < entries; i++)
1479 ring[i].NextDescAddress =
1480 cpu_to_le32((u32)dma + ((i + 1) % entries) * sizeof(*ring));
1481
1482 return 0;
1483}
1484
5e1ad18a 1485static short rtl8192_pci_initdescring(struct net_device *dev)
ecdfa446 1486{
1f1f19ff
MM
1487 u32 ret;
1488 int i;
1489 struct r8192_priv *priv = ieee80211_priv(dev);
ecdfa446 1490
1f1f19ff
MM
1491 ret = rtl8192_alloc_rx_desc_ring(dev);
1492 if (ret)
1493 return ret;
ecdfa446 1494
1f1f19ff
MM
1495 /* general process for other queue */
1496 for (i = 0; i < MAX_TX_QUEUE_COUNT; i++) {
1497 ret = rtl8192_alloc_tx_desc_ring(dev, i, priv->txringcount);
1498 if (ret)
1499 goto err_free_rings;
1500 }
ecdfa446 1501
1f1f19ff 1502 return 0;
ecdfa446
GKH
1503
1504err_free_rings:
1f1f19ff
MM
1505 rtl8192_free_rx_ring(dev);
1506 for (i = 0; i < MAX_TX_QUEUE_COUNT; i++)
1507 if (priv->tx_ring[i].desc)
1508 rtl8192_free_tx_ring(dev, i);
1509 return 1;
ecdfa446
GKH
1510}
1511
5e1ad18a 1512static void rtl8192_pci_resetdescring(struct net_device *dev)
ecdfa446
GKH
1513{
1514 struct r8192_priv *priv = ieee80211_priv(dev);
1515 int i;
1516
1517 /* force the rx_idx to the first one */
1518 if(priv->rx_ring) {
1519 rx_desc_819x_pci *entry = NULL;
1520 for (i = 0; i < priv->rxringcount; i++) {
1521 entry = &priv->rx_ring[i];
1522 entry->OWN = 1;
1523 }
1524 priv->rx_idx = 0;
1525 }
1526
1527 /* after reset, release previous pending packet, and force the
1528 * tx idx to the first one */
1529 for (i = 0; i < MAX_TX_QUEUE_COUNT; i++) {
1530 if (priv->tx_ring[i].desc) {
1531 struct rtl8192_tx_ring *ring = &priv->tx_ring[i];
1532
1533 while (skb_queue_len(&ring->queue)) {
1534 tx_desc_819x_pci *entry = &ring->desc[ring->idx];
1535 struct sk_buff *skb = __skb_dequeue(&ring->queue);
1536
1537 pci_unmap_single(priv->pdev, le32_to_cpu(entry->TxBuffAddr),
1538 skb->len, PCI_DMA_TODEVICE);
1539 kfree_skb(skb);
1540 ring->idx = (ring->idx + 1) % ring->entries;
1541 }
1542 ring->idx = 0;
1543 }
1544 }
1545}
1546
5e1ad18a 1547static void rtl8192_link_change(struct net_device *dev)
ecdfa446 1548{
ecdfa446
GKH
1549 struct r8192_priv *priv = ieee80211_priv(dev);
1550 struct ieee80211_device* ieee = priv->ieee80211;
3f9ab1ee 1551 //write_nic_word(priv, BCN_INTR_ITV, net->beacon_interval);
ecdfa446
GKH
1552 if (ieee->state == IEEE80211_LINKED)
1553 {
1554 rtl8192_net_update(dev);
1555 rtl8192_update_ratr_table(dev);
11aacc28 1556
ecdfa446
GKH
1557 //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
1558 if ((KEY_TYPE_WEP40 == ieee->pairwise_key_type) || (KEY_TYPE_WEP104 == ieee->pairwise_key_type))
1559 EnableHWSecurityConfig8192(dev);
ecdfa446
GKH
1560 }
1561 else
1562 {
3f9ab1ee 1563 write_nic_byte(priv, 0x173, 0);
ecdfa446
GKH
1564 }
1565 /*update timing params*/
1566 //rtl8192_set_chan(dev, priv->chan);
1567 //MSR
1568 rtl8192_update_msr(dev);
1569
1570 // 2007/10/16 MH MAC Will update TSF according to all received beacon, so we have
1571 // // To set CBSSID bit when link with any AP or STA.
1572 if (ieee->iw_mode == IW_MODE_INFRA || ieee->iw_mode == IW_MODE_ADHOC)
1573 {
1574 u32 reg = 0;
3f9ab1ee 1575 reg = read_nic_dword(priv, RCR);
ecdfa446
GKH
1576 if (priv->ieee80211->state == IEEE80211_LINKED)
1577 priv->ReceiveConfig = reg |= RCR_CBSSID;
1578 else
1579 priv->ReceiveConfig = reg &= ~RCR_CBSSID;
3f9ab1ee 1580 write_nic_dword(priv, RCR, reg);
ecdfa446
GKH
1581 }
1582}
ecdfa446
GKH
1583
1584
5b3b1a7b 1585static const struct ieee80211_qos_parameters def_qos_parameters = {
ecdfa446
GKH
1586 {3,3,3,3},/* cw_min */
1587 {7,7,7,7},/* cw_max */
1588 {2,2,2,2},/* aifs */
1589 {0,0,0,0},/* flags */
1590 {0,0,0,0} /* tx_op_limit */
1591};
1592
5e1ad18a 1593static void rtl8192_update_beacon(struct work_struct * work)
ecdfa446
GKH
1594{
1595 struct r8192_priv *priv = container_of(work, struct r8192_priv, update_beacon_wq.work);
1596 struct net_device *dev = priv->ieee80211->dev;
ecdfa446
GKH
1597 struct ieee80211_device* ieee = priv->ieee80211;
1598 struct ieee80211_network* net = &ieee->current_network;
1599
1600 if (ieee->pHTInfo->bCurrentHTSupport)
1601 HTUpdateSelfAndPeerSetting(ieee, net);
1602 ieee->pHTInfo->bCurrentRT2RTLongSlotTime = net->bssht.bdRT2RTLongSlotTime;
1603 rtl8192_update_cap(dev, net->capability);
1604}
214985a6 1605
ecdfa446
GKH
1606/*
1607* background support to run QoS activate functionality
1608*/
881a975b 1609static const int WDCAPARA_ADD[] = {EDCAPARA_BE,EDCAPARA_BK,EDCAPARA_VI,EDCAPARA_VO};
5e1ad18a 1610static void rtl8192_qos_activate(struct work_struct * work)
ecdfa446
GKH
1611{
1612 struct r8192_priv *priv = container_of(work, struct r8192_priv, qos_activate);
ecdfa446
GKH
1613 struct ieee80211_qos_parameters *qos_parameters = &priv->ieee80211->current_network.qos_data.parameters;
1614 u8 mode = priv->ieee80211->current_network.mode;
ecdfa446
GKH
1615 u8 u1bAIFS;
1616 u32 u4bAcParam;
1617 int i;
ecdfa446 1618
ecdfa446 1619 mutex_lock(&priv->mutex);
ecdfa446
GKH
1620 if(priv->ieee80211->state != IEEE80211_LINKED)
1621 goto success;
1622 RT_TRACE(COMP_QOS,"qos active process with associate response received\n");
1623 /* It better set slot time at first */
1624 /* For we just support b/g mode at present, let the slot time at 9/20 selection */
1625 /* update the ac parameter to related registers */
1626 for(i = 0; i < QOS_QUEUE_NUM; i++) {
1627 //Mode G/A: slotTimeTimer = 9; Mode B: 20
1628 u1bAIFS = qos_parameters->aifs[i] * ((mode&(IEEE_G|IEEE_N_24G)) ?9:20) + aSifsTime;
1629 u4bAcParam = ((((u32)(qos_parameters->tx_op_limit[i]))<< AC_PARAM_TXOP_LIMIT_OFFSET)|
1630 (((u32)(qos_parameters->cw_max[i]))<< AC_PARAM_ECW_MAX_OFFSET)|
1631 (((u32)(qos_parameters->cw_min[i]))<< AC_PARAM_ECW_MIN_OFFSET)|
1632 ((u32)u1bAIFS << AC_PARAM_AIFS_OFFSET));
3f9ab1ee
MM
1633 write_nic_dword(priv, WDCAPARA_ADD[i], u4bAcParam);
1634 //write_nic_dword(priv, WDCAPARA_ADD[i], 0x005e4332);
ecdfa446
GKH
1635 }
1636
1637success:
ecdfa446 1638 mutex_unlock(&priv->mutex);
ecdfa446
GKH
1639}
1640
1641static int rtl8192_qos_handle_probe_response(struct r8192_priv *priv,
1642 int active_network,
1643 struct ieee80211_network *network)
1644{
1645 int ret = 0;
1646 u32 size = sizeof(struct ieee80211_qos_parameters);
1647
1648 if(priv->ieee80211->state !=IEEE80211_LINKED)
1649 return ret;
1650
1651 if ((priv->ieee80211->iw_mode != IW_MODE_INFRA))
1652 return ret;
1653
1654 if (network->flags & NETWORK_HAS_QOS_MASK) {
1655 if (active_network &&
1656 (network->flags & NETWORK_HAS_QOS_PARAMETERS))
1657 network->qos_data.active = network->qos_data.supported;
1658
1659 if ((network->qos_data.active == 1) && (active_network == 1) &&
1660 (network->flags & NETWORK_HAS_QOS_PARAMETERS) &&
1661 (network->qos_data.old_param_count !=
1662 network->qos_data.param_count)) {
1663 network->qos_data.old_param_count =
1664 network->qos_data.param_count;
ecdfa446 1665 queue_work(priv->priv_wq, &priv->qos_activate);
ecdfa446
GKH
1666 RT_TRACE (COMP_QOS, "QoS parameters change call "
1667 "qos_activate\n");
1668 }
1669 } else {
207b58fb 1670 memcpy(&priv->ieee80211->current_network.qos_data.parameters,
ecdfa446
GKH
1671 &def_qos_parameters, size);
1672
1673 if ((network->qos_data.active == 1) && (active_network == 1)) {
ecdfa446 1674 queue_work(priv->priv_wq, &priv->qos_activate);
ecdfa446
GKH
1675 RT_TRACE(COMP_QOS, "QoS was disabled call qos_activate \n");
1676 }
1677 network->qos_data.active = 0;
1678 network->qos_data.supported = 0;
1679 }
1680
1681 return 0;
1682}
1683
1684/* handle manage frame frame beacon and probe response */
1685static int rtl8192_handle_beacon(struct net_device * dev,
1686 struct ieee80211_beacon * beacon,
1687 struct ieee80211_network * network)
1688{
1689 struct r8192_priv *priv = ieee80211_priv(dev);
1690
1691 rtl8192_qos_handle_probe_response(priv,1,network);
1692
ecdfa446 1693 queue_delayed_work(priv->priv_wq, &priv->update_beacon_wq, 0);
ecdfa446
GKH
1694 return 0;
1695
1696}
1697
1698/*
214985a6
MM
1699 * handling the beaconing responses. if we get different QoS setting
1700 * off the network from the associated setting, adjust the QoS setting
1701 */
ecdfa446
GKH
1702static int rtl8192_qos_association_resp(struct r8192_priv *priv,
1703 struct ieee80211_network *network)
1704{
b72cb94f
MM
1705 int ret = 0;
1706 unsigned long flags;
1707 u32 size = sizeof(struct ieee80211_qos_parameters);
1708 int set_qos_param = 0;
ecdfa446 1709
b72cb94f
MM
1710 if ((priv == NULL) || (network == NULL))
1711 return ret;
ecdfa446 1712
b72cb94f
MM
1713 if (priv->ieee80211->state != IEEE80211_LINKED)
1714 return ret;
ecdfa446 1715
b72cb94f
MM
1716 if ((priv->ieee80211->iw_mode != IW_MODE_INFRA))
1717 return ret;
ecdfa446 1718
b72cb94f
MM
1719 spin_lock_irqsave(&priv->ieee80211->lock, flags);
1720 if (network->flags & NETWORK_HAS_QOS_PARAMETERS) {
207b58fb
MM
1721 memcpy(&priv->ieee80211->current_network.qos_data.parameters,
1722 &network->qos_data.parameters,
ecdfa446
GKH
1723 sizeof(struct ieee80211_qos_parameters));
1724 priv->ieee80211->current_network.qos_data.active = 1;
b72cb94f
MM
1725 set_qos_param = 1;
1726 /* update qos parameter for current network */
1727 priv->ieee80211->current_network.qos_data.old_param_count =
1728 priv->ieee80211->current_network.qos_data.param_count;
1729 priv->ieee80211->current_network.qos_data.param_count =
1730 network->qos_data.param_count;
1731
1732 } else {
207b58fb 1733 memcpy(&priv->ieee80211->current_network.qos_data.parameters,
ecdfa446
GKH
1734 &def_qos_parameters, size);
1735 priv->ieee80211->current_network.qos_data.active = 0;
1736 priv->ieee80211->current_network.qos_data.supported = 0;
b72cb94f
MM
1737 set_qos_param = 1;
1738 }
ecdfa446 1739
b72cb94f 1740 spin_unlock_irqrestore(&priv->ieee80211->lock, flags);
ecdfa446 1741
b72cb94f
MM
1742 RT_TRACE(COMP_QOS, "%s: network->flags = %d,%d\n", __FUNCTION__,
1743 network->flags, priv->ieee80211->current_network.qos_data.active);
ecdfa446 1744 if (set_qos_param == 1)
ecdfa446 1745 queue_work(priv->priv_wq, &priv->qos_activate);
ecdfa446 1746
b72cb94f 1747 return ret;
ecdfa446
GKH
1748}
1749
1750
1751static int rtl8192_handle_assoc_response(struct net_device *dev,
1752 struct ieee80211_assoc_response_frame *resp,
1753 struct ieee80211_network *network)
1754{
1755 struct r8192_priv *priv = ieee80211_priv(dev);
1756 rtl8192_qos_association_resp(priv, network);
1757 return 0;
1758}
1759
1760
214985a6 1761/* updateRATRTabel for MCS only. Basic rate is not implemented. */
5b3b1a7b 1762static void rtl8192_update_ratr_table(struct net_device* dev)
ecdfa446
GKH
1763{
1764 struct r8192_priv* priv = ieee80211_priv(dev);
1765 struct ieee80211_device* ieee = priv->ieee80211;
1766 u8* pMcsRate = ieee->dot11HTOperationalRateSet;
ecdfa446
GKH
1767 u32 ratr_value = 0;
1768 u8 rate_index = 0;
1769
1770 rtl8192_config_rate(dev, (u16*)(&ratr_value));
1771 ratr_value |= (*(u16*)(pMcsRate)) << 12;
16d74da0 1772
ecdfa446
GKH
1773 switch (ieee->mode)
1774 {
1775 case IEEE_A:
1776 ratr_value &= 0x00000FF0;
1777 break;
1778 case IEEE_B:
1779 ratr_value &= 0x0000000F;
1780 break;
1781 case IEEE_G:
1782 ratr_value &= 0x00000FF7;
1783 break;
1784 case IEEE_N_24G:
1785 case IEEE_N_5G:
1786 if (ieee->pHTInfo->PeerMimoPs == 0) //MIMO_PS_STATIC
1787 ratr_value &= 0x0007F007;
1788 else{
1789 if (priv->rf_type == RF_1T2R)
1790 ratr_value &= 0x000FF007;
1791 else
1792 ratr_value &= 0x0F81F007;
1793 }
1794 break;
1795 default:
1796 break;
1797 }
1798 ratr_value &= 0x0FFFFFFF;
1799 if(ieee->pHTInfo->bCurTxBW40MHz && ieee->pHTInfo->bCurShortGI40MHz){
1800 ratr_value |= 0x80000000;
1801 }else if(!ieee->pHTInfo->bCurTxBW40MHz && ieee->pHTInfo->bCurShortGI20MHz){
1802 ratr_value |= 0x80000000;
1803 }
3f9ab1ee
MM
1804 write_nic_dword(priv, RATR0+rate_index*4, ratr_value);
1805 write_nic_byte(priv, UFWP, 1);
ecdfa446
GKH
1806}
1807
5e1ad18a 1808static bool GetNmodeSupportBySecCfg8190Pci(struct net_device*dev)
ecdfa446 1809{
65a43784 1810 struct r8192_priv *priv = ieee80211_priv(dev);
1811 struct ieee80211_device *ieee = priv->ieee80211;
ecdfa446 1812
f8acdc3d
MM
1813 return !(ieee->rtllib_ap_sec_type &&
1814 (ieee->rtllib_ap_sec_type(ieee)&(SEC_ALG_WEP|SEC_ALG_TKIP)));
ecdfa446
GKH
1815}
1816
5e1ad18a 1817static void rtl8192_refresh_supportrate(struct r8192_priv* priv)
ecdfa446
GKH
1818{
1819 struct ieee80211_device* ieee = priv->ieee80211;
1820 //we donot consider set support rate for ABG mode, only HT MCS rate is set here.
1821 if (ieee->mode == WIRELESS_MODE_N_24G || ieee->mode == WIRELESS_MODE_N_5G)
1822 {
1823 memcpy(ieee->Regdot11HTOperationalRateSet, ieee->RegHTSuppRateSet, 16);
ecdfa446
GKH
1824 }
1825 else
1826 memset(ieee->Regdot11HTOperationalRateSet, 0, 16);
ecdfa446
GKH
1827}
1828
6f304eb2 1829static u8 rtl8192_getSupportedWireleeMode(struct net_device *dev)
ecdfa446 1830{
6f304eb2 1831 return (WIRELESS_MODE_N_24G|WIRELESS_MODE_G|WIRELESS_MODE_B);
ecdfa446 1832}
5e1ad18a
GKH
1833
1834static void rtl8192_SetWirelessMode(struct net_device* dev, u8 wireless_mode)
ecdfa446
GKH
1835{
1836 struct r8192_priv *priv = ieee80211_priv(dev);
1837 u8 bSupportMode = rtl8192_getSupportedWireleeMode(dev);
1838
ecdfa446
GKH
1839 if ((wireless_mode == WIRELESS_MODE_AUTO) || ((wireless_mode&bSupportMode)==0))
1840 {
1841 if(bSupportMode & WIRELESS_MODE_N_24G)
1842 {
1843 wireless_mode = WIRELESS_MODE_N_24G;
1844 }
1845 else if(bSupportMode & WIRELESS_MODE_N_5G)
1846 {
1847 wireless_mode = WIRELESS_MODE_N_5G;
1848 }
1849 else if((bSupportMode & WIRELESS_MODE_A))
1850 {
1851 wireless_mode = WIRELESS_MODE_A;
1852 }
1853 else if((bSupportMode & WIRELESS_MODE_G))
1854 {
1855 wireless_mode = WIRELESS_MODE_G;
1856 }
1857 else if((bSupportMode & WIRELESS_MODE_B))
1858 {
1859 wireless_mode = WIRELESS_MODE_B;
1860 }
1861 else{
1862 RT_TRACE(COMP_ERR, "%s(), No valid wireless mode supported, SupportedWirelessMode(%x)!!!\n", __FUNCTION__,bSupportMode);
1863 wireless_mode = WIRELESS_MODE_B;
1864 }
1865 }
ecdfa446
GKH
1866 priv->ieee80211->mode = wireless_mode;
1867
1868 if ((wireless_mode == WIRELESS_MODE_N_24G) || (wireless_mode == WIRELESS_MODE_N_5G))
1869 priv->ieee80211->pHTInfo->bEnableHT = 1;
1870 else
1871 priv->ieee80211->pHTInfo->bEnableHT = 0;
1872 RT_TRACE(COMP_INIT, "Current Wireless Mode is %x\n", wireless_mode);
1873 rtl8192_refresh_supportrate(priv);
ecdfa446 1874}
ecdfa446 1875
5e1ad18a 1876static bool GetHalfNmodeSupportByAPs819xPci(struct net_device* dev)
ecdfa446 1877{
ecdfa446
GKH
1878 struct r8192_priv* priv = ieee80211_priv(dev);
1879 struct ieee80211_device* ieee = priv->ieee80211;
1880
285f660c 1881 return ieee->bHalfWirelessN24GMode;
ecdfa446
GKH
1882}
1883
1884short rtl8192_is_tx_queue_empty(struct net_device *dev)
1885{
1886 int i=0;
1887 struct r8192_priv *priv = ieee80211_priv(dev);
1888 for (i=0; i<=MGNT_QUEUE; i++)
1889 {
1890 if ((i== TXCMD_QUEUE) || (i == HCCA_QUEUE) )
1891 continue;
1892 if (skb_queue_len(&(&priv->tx_ring[i])->queue) > 0){
1893 printk("===>tx queue is not empty:%d, %d\n", i, skb_queue_len(&(&priv->tx_ring[i])->queue));
1894 return 0;
1895 }
1896 }
1897 return 1;
1898}
16d74da0 1899
5e1ad18a 1900static void rtl8192_hw_sleep_down(struct net_device *dev)
ecdfa446 1901{
65a43784 1902 struct r8192_priv *priv = ieee80211_priv(dev);
1903 unsigned long flags = 0;
1904
1905 spin_lock_irqsave(&priv->rf_ps_lock,flags);
1906 if (priv->RFChangeInProgress) {
1907 spin_unlock_irqrestore(&priv->rf_ps_lock,flags);
1908 RT_TRACE(COMP_RF, "rtl8192_hw_sleep_down(): RF Change in progress! \n");
1909 printk("rtl8192_hw_sleep_down(): RF Change in progress!\n");
1910 return;
1911 }
1912 spin_unlock_irqrestore(&priv->rf_ps_lock,flags);
65a43784 1913
ecdfa446
GKH
1914 MgntActSet_RF_State(dev, eRfSleep, RF_CHANGE_BY_PS);
1915}
16d74da0 1916
5e1ad18a 1917static void rtl8192_hw_sleep_wq (struct work_struct *work)
ecdfa446 1918{
ecdfa446
GKH
1919 struct delayed_work *dwork = container_of(work,struct delayed_work,work);
1920 struct ieee80211_device *ieee = container_of(dwork,struct ieee80211_device,hw_sleep_wq);
1921 struct net_device *dev = ieee->dev;
65a43784 1922
ecdfa446
GKH
1923 rtl8192_hw_sleep_down(dev);
1924}
65a43784 1925
5e1ad18a 1926static void rtl8192_hw_wakeup(struct net_device* dev)
ecdfa446 1927{
65a43784 1928 struct r8192_priv *priv = ieee80211_priv(dev);
1929 unsigned long flags = 0;
1930
1931 spin_lock_irqsave(&priv->rf_ps_lock,flags);
1932 if (priv->RFChangeInProgress) {
1933 spin_unlock_irqrestore(&priv->rf_ps_lock,flags);
1934 RT_TRACE(COMP_RF, "rtl8192_hw_wakeup(): RF Change in progress! \n");
1935 printk("rtl8192_hw_wakeup(): RF Change in progress! schedule wake up task again\n");
1936 queue_delayed_work(priv->ieee80211->wq,&priv->ieee80211->hw_wakeup_wq,MSECS(10));//PowerSave is not supported if kernel version is below 2.6.20
1937 return;
1938 }
1939 spin_unlock_irqrestore(&priv->rf_ps_lock,flags);
ecdfa446 1940
ecdfa446 1941 MgntActSet_RF_State(dev, eRfOn, RF_CHANGE_BY_PS);
ecdfa446 1942}
65a43784 1943
ecdfa446
GKH
1944void rtl8192_hw_wakeup_wq (struct work_struct *work)
1945{
ecdfa446
GKH
1946 struct delayed_work *dwork = container_of(work,struct delayed_work,work);
1947 struct ieee80211_device *ieee = container_of(dwork,struct ieee80211_device,hw_wakeup_wq);
1948 struct net_device *dev = ieee->dev;
ecdfa446
GKH
1949 rtl8192_hw_wakeup(dev);
1950
1951}
1952
1953#define MIN_SLEEP_TIME 50
1954#define MAX_SLEEP_TIME 10000
5e1ad18a 1955static void rtl8192_hw_to_sleep(struct net_device *dev, u32 th, u32 tl)
ecdfa446 1956{
ecdfa446 1957 struct r8192_priv *priv = ieee80211_priv(dev);
9236928f 1958 u32 tmp;
ecdfa446 1959 u32 rb = jiffies;
ecdfa446 1960
9236928f 1961 spin_lock(&priv->ps_lock);
ecdfa446 1962
65a43784 1963 // Writing HW register with 0 equals to disable
1964 // the timer, that is not really what we want
1965 //
1966 tl -= MSECS(8+16+7);
ecdfa446 1967
65a43784 1968 // If the interval in witch we are requested to sleep is too
1969 // short then give up and remain awake
1970 // when we sleep after send null frame, the timer will be too short to sleep.
1971 //
ecdfa446 1972 if(((tl>=rb)&& (tl-rb) <= MSECS(MIN_SLEEP_TIME))
65a43784 1973 ||((rb>tl)&& (rb-tl) < MSECS(MIN_SLEEP_TIME))) {
65a43784 1974 printk("too short to sleep::%x, %x, %lx\n",tl, rb, MSECS(MIN_SLEEP_TIME));
9236928f 1975 goto out_unlock;
ecdfa446
GKH
1976 }
1977
ecdfa446 1978 if(((tl > rb) && ((tl-rb) > MSECS(MAX_SLEEP_TIME)))||
65a43784 1979 ((tl < rb) && (tl>MSECS(69)) && ((rb-tl) > MSECS(MAX_SLEEP_TIME)))||
1980 ((tl<rb)&&(tl<MSECS(69))&&((tl+0xffffffff-rb)>MSECS(MAX_SLEEP_TIME)))) {
ecdfa446 1981 printk("========>too long to sleep:%x, %x, %lx\n", tl, rb, MSECS(MAX_SLEEP_TIME));
9236928f 1982 goto out_unlock;
65a43784 1983 }
9236928f
MM
1984
1985 tmp = (tl>rb)?(tl-rb):(rb-tl);
65a43784 1986 queue_delayed_work(priv->ieee80211->wq,
9236928f 1987 &priv->ieee80211->hw_wakeup_wq,tmp);
65a43784 1988
9236928f
MM
1989 queue_delayed_work(priv->ieee80211->wq,
1990 (void *)&priv->ieee80211->hw_sleep_wq,0);
1991out_unlock:
1992 spin_unlock(&priv->ps_lock);
ecdfa446 1993}
214985a6 1994
ecdfa446
GKH
1995static void rtl8192_init_priv_variable(struct net_device* dev)
1996{
1997 struct r8192_priv *priv = ieee80211_priv(dev);
1998 u8 i;
65a43784 1999 PRT_POWER_SAVE_CONTROL pPSC = (PRT_POWER_SAVE_CONTROL)(&(priv->ieee80211->PowerSaveControl));
2000
2001 // Default Halt the NIC if RF is OFF.
2002 pPSC->RegRfPsLevel |= RT_RF_OFF_LEVL_HALT_NIC;
2003 pPSC->RegRfPsLevel |= RT_RF_OFF_LEVL_CLK_REQ;
2004 pPSC->RegRfPsLevel |= RT_RF_OFF_LEVL_ASPM;
2005 pPSC->RegRfPsLevel |= RT_RF_LPS_LEVEL_ASPM;
2006 pPSC->bLeisurePs = true;
2007 pPSC->RegMaxLPSAwakeIntvl = 5;
2008 priv->bHwRadioOff = false;
2009
ecdfa446 2010 priv->being_init_adapter = false;
ecdfa446 2011 priv->txringcount = 64;//32;
ecdfa446
GKH
2012 priv->rxbuffersize = 9100;//2048;//1024;
2013 priv->rxringcount = MAX_RX_COUNT;//64;
2014 priv->irq_enabled=0;
ecdfa446
GKH
2015 priv->rx_skb_complete = 1;
2016 priv->chan = 1; //set to channel 1
2017 priv->RegWirelessMode = WIRELESS_MODE_AUTO;
2018 priv->RegChannelPlan = 0xf;
ecdfa446
GKH
2019 priv->ieee80211->mode = WIRELESS_MODE_AUTO; //SET AUTO
2020 priv->ieee80211->iw_mode = IW_MODE_INFRA;
2021 priv->ieee80211->ieee_up=0;
2022 priv->retry_rts = DEFAULT_RETRY_RTS;
2023 priv->retry_data = DEFAULT_RETRY_DATA;
2024 priv->ieee80211->rts = DEFAULT_RTS_THRESHOLD;
2025 priv->ieee80211->rate = 110; //11 mbps
2026 priv->ieee80211->short_slot = 1;
2027 priv->promisc = (dev->flags & IFF_PROMISC) ? 1:0;
2028 priv->bcck_in_ch14 = false;
ecdfa446
GKH
2029 priv->CCKPresentAttentuation = 0;
2030 priv->rfa_txpowertrackingindex = 0;
2031 priv->rfc_txpowertrackingindex = 0;
2032 priv->CckPwEnl = 6;
ecdfa446
GKH
2033 //added by amy for silent reset
2034 priv->ResetProgress = RESET_TYPE_NORESET;
2035 priv->bForcedSilentReset = 0;
2036 priv->bDisableNormalResetCheck = false;
2037 priv->force_reset = false;
2038 //added by amy for power save
ecdfa446
GKH
2039 priv->ieee80211->RfOffReason = 0;
2040 priv->RFChangeInProgress = false;
2041 priv->bHwRfOffAction = 0;
2042 priv->SetRFPowerStateInProgress = false;
2043 priv->ieee80211->PowerSaveControl.bInactivePs = true;
2044 priv->ieee80211->PowerSaveControl.bIPSModeBackup = false;
ecdfa446
GKH
2045
2046 priv->ieee80211->current_network.beacon_interval = DEFAULT_BEACONINTERVAL;
2047 priv->ieee80211->iw_mode = IW_MODE_INFRA;
2048 priv->ieee80211->softmac_features = IEEE_SOFTMAC_SCAN |
2049 IEEE_SOFTMAC_ASSOCIATE | IEEE_SOFTMAC_PROBERQ |
2050 IEEE_SOFTMAC_PROBERS | IEEE_SOFTMAC_TX_QUEUE;/* |
2051 IEEE_SOFTMAC_BEACONS;*///added by amy 080604 //| //IEEE_SOFTMAC_SINGLE_QUEUE;
2052
2053 priv->ieee80211->active_scan = 1;
2054 priv->ieee80211->modulation = IEEE80211_CCK_MODULATION | IEEE80211_OFDM_MODULATION;
2055 priv->ieee80211->host_encrypt = 1;
2056 priv->ieee80211->host_decrypt = 1;
2057 //priv->ieee80211->start_send_beacons = NULL;//rtl819xusb_beacon_tx;//-by amy 080604
2058 //priv->ieee80211->stop_send_beacons = NULL;//rtl8192_beacon_stop;//-by amy 080604
2059 priv->ieee80211->start_send_beacons = rtl8192_start_beacon;//+by david 081107
2060 priv->ieee80211->stop_send_beacons = rtl8192_stop_beacon;//+by david 081107
2061 priv->ieee80211->softmac_hard_start_xmit = rtl8192_hard_start_xmit;
2062 priv->ieee80211->set_chan = rtl8192_set_chan;
2063 priv->ieee80211->link_change = rtl8192_link_change;
2064 priv->ieee80211->softmac_data_hard_start_xmit = rtl8192_hard_data_xmit;
2065 priv->ieee80211->data_hard_stop = rtl8192_data_hard_stop;
2066 priv->ieee80211->data_hard_resume = rtl8192_data_hard_resume;
2067 priv->ieee80211->init_wmmparam_flag = 0;
2068 priv->ieee80211->fts = DEFAULT_FRAG_THRESHOLD;
2069 priv->ieee80211->check_nic_enough_desc = check_nic_enough_desc;
2070 priv->ieee80211->tx_headroom = sizeof(TX_FWINFO_8190PCI);
2071 priv->ieee80211->qos_support = 1;
2072 priv->ieee80211->dot11PowerSaveMode = 0;
2073 //added by WB
2074// priv->ieee80211->SwChnlByTimerHandler = rtl8192_phy_SwChnl;
2075 priv->ieee80211->SetBWModeHandler = rtl8192_SetBWMode;
2076 priv->ieee80211->handle_assoc_response = rtl8192_handle_assoc_response;
2077 priv->ieee80211->handle_beacon = rtl8192_handle_beacon;
2078
2079 priv->ieee80211->sta_wake_up = rtl8192_hw_wakeup;
2080// priv->ieee80211->ps_request_tx_ack = rtl8192_rq_tx_ack;
2081 priv->ieee80211->enter_sleep_state = rtl8192_hw_to_sleep;
2082 priv->ieee80211->ps_is_queue_empty = rtl8192_is_tx_queue_empty;
2083 //added by david
2084 priv->ieee80211->GetNmodeSupportBySecCfg = GetNmodeSupportBySecCfg8190Pci;
2085 priv->ieee80211->SetWirelessMode = rtl8192_SetWirelessMode;
2086 priv->ieee80211->GetHalfNmodeSupportByAPsHandler = GetHalfNmodeSupportByAPs819xPci;
2087
2088 //added by amy
2089 priv->ieee80211->InitialGainHandler = InitialGain819xPci;
2090
65a43784 2091#ifdef ENABLE_IPS
2092 priv->ieee80211->ieee80211_ips_leave_wq = ieee80211_ips_leave_wq;
2093 priv->ieee80211->ieee80211_ips_leave = ieee80211_ips_leave;
2094#endif
2095#ifdef ENABLE_LPS
2096 priv->ieee80211->LeisurePSLeave = LeisurePSLeave;
16d74da0 2097#endif
65a43784 2098
2099 priv->ieee80211->SetHwRegHandler = rtl8192e_SetHwReg;
2100 priv->ieee80211->rtllib_ap_sec_type = rtl8192e_ap_sec_type;
2101
395aa640
MM
2102 priv->ShortRetryLimit = 0x30;
2103 priv->LongRetryLimit = 0x30;
ecdfa446
GKH
2104
2105 priv->ReceiveConfig = RCR_ADD3 |
2106 RCR_AMF | RCR_ADF | //accept management/data
2107 RCR_AICV | //accept control frame for SW AP needs PS-poll, 2005.07.07, by rcnjko.
2108 RCR_AB | RCR_AM | RCR_APM | //accept BC/MC/UC
2109 RCR_AAP | ((u32)7<<RCR_MXDMA_OFFSET) |
2110 ((u32)7 << RCR_FIFO_OFFSET) | RCR_ONLYERLPKT;
2111
207b58fb
MM
2112 priv->irq_mask = (u32)(IMR_ROK | IMR_VODOK | IMR_VIDOK | IMR_BEDOK | IMR_BKDOK |
2113 IMR_HCCADOK | IMR_MGNTDOK | IMR_COMDOK | IMR_HIGHDOK |
2114 IMR_BDOK | IMR_RXCMDOK | IMR_TIMEOUT0 | IMR_RDU | IMR_RXFOVW |
ecdfa446
GKH
2115 IMR_TXFOVW | IMR_BcnInt | IMR_TBDOK | IMR_TBDER);
2116
5b84cc78 2117 priv->pFirmware = vzalloc(sizeof(rt_firmware));
ecdfa446
GKH
2118
2119 /* rx related queue */
ecdfa446
GKH
2120 skb_queue_head_init(&priv->skb_queue);
2121
2122 /* Tx related queue */
2123 for(i = 0; i < MAX_QUEUE_SIZE; i++) {
2124 skb_queue_head_init(&priv->ieee80211->skb_waitQ [i]);
2125 }
2126 for(i = 0; i < MAX_QUEUE_SIZE; i++) {
2127 skb_queue_head_init(&priv->ieee80211->skb_aggQ [i]);
2128 }
2129 priv->rf_set_chan = rtl8192_phy_SwChnl;
2130}
2131
ecdfa446
GKH
2132static void rtl8192_init_priv_lock(struct r8192_priv* priv)
2133{
2134 spin_lock_init(&priv->tx_lock);
ecdfa446
GKH
2135 spin_lock_init(&priv->irq_th_lock);
2136 spin_lock_init(&priv->rf_ps_lock);
2137 spin_lock_init(&priv->ps_lock);
ecdfa446
GKH
2138 sema_init(&priv->wx_sem,1);
2139 sema_init(&priv->rf_sem,1);
ecdfa446 2140 mutex_init(&priv->mutex);
ecdfa446
GKH
2141}
2142
214985a6 2143/* init tasklet and wait_queue here */
ecdfa446
GKH
2144#define DRV_NAME "wlan0"
2145static void rtl8192_init_priv_task(struct net_device* dev)
2146{
2147 struct r8192_priv *priv = ieee80211_priv(dev);
2148
ecdfa446 2149 priv->priv_wq = create_workqueue(DRV_NAME);
ecdfa446 2150
65a43784 2151#ifdef ENABLE_IPS
80a4dead 2152 INIT_WORK(&priv->ieee80211->ips_leave_wq, IPSLeave_wq);
65a43784 2153#endif
2154
ecdfa446
GKH
2155// INIT_WORK(&priv->reset_wq, (void(*)(void*)) rtl8192_restart);
2156 INIT_WORK(&priv->reset_wq, rtl8192_restart);
2157// INIT_DELAYED_WORK(&priv->watch_dog_wq, hal_dm_watchdog);
2158 INIT_DELAYED_WORK(&priv->watch_dog_wq, rtl819x_watchdog_wqcallback);
2159 INIT_DELAYED_WORK(&priv->txpower_tracking_wq, dm_txpower_trackingcallback);
2160 INIT_DELAYED_WORK(&priv->rfpath_check_wq, dm_rf_pathcheck_workitemcallback);
2161 INIT_DELAYED_WORK(&priv->update_beacon_wq, rtl8192_update_beacon);
2162 //INIT_WORK(&priv->SwChnlWorkItem, rtl8192_SwChnl_WorkItem);
2163 //INIT_WORK(&priv->SetBWModeWorkItem, rtl8192_SetBWModeWorkItem);
2164 INIT_WORK(&priv->qos_activate, rtl8192_qos_activate);
80a4dead
MM
2165 INIT_DELAYED_WORK(&priv->ieee80211->hw_wakeup_wq, rtl8192_hw_wakeup_wq);
2166 INIT_DELAYED_WORK(&priv->ieee80211->hw_sleep_wq, rtl8192_hw_sleep_wq);
ecdfa446 2167
80a4dead
MM
2168 tasklet_init(&priv->irq_rx_tasklet, rtl8192_irq_rx_tasklet,
2169 (unsigned long) priv);
2170 tasklet_init(&priv->irq_tx_tasklet, rtl8192_irq_tx_tasklet,
2171 (unsigned long) priv);
2172 tasklet_init(&priv->irq_prepare_beacon_tasklet, rtl8192_prepare_beacon,
2173 (unsigned long) priv);
ecdfa446
GKH
2174}
2175
2176static void rtl8192_get_eeprom_size(struct net_device* dev)
2177{
2178 u16 curCR = 0;
2179 struct r8192_priv *priv = ieee80211_priv(dev);
2180 RT_TRACE(COMP_INIT, "===========>%s()\n", __FUNCTION__);
3f9ab1ee 2181 curCR = read_nic_dword(priv, EPROM_CMD);
ecdfa446
GKH
2182 RT_TRACE(COMP_INIT, "read from Reg Cmd9346CR(%x):%x\n", EPROM_CMD, curCR);
2183 //whether need I consider BIT5?
2184 priv->epromtype = (curCR & EPROM_CMD_9356SEL) ? EPROM_93c56 : EPROM_93c46;
2185 RT_TRACE(COMP_INIT, "<===========%s(), epromtype:%d\n", __FUNCTION__, priv->epromtype);
2186}
2187
ecdfa446 2188/*
214985a6
MM
2189 * Adapter->EEPROMAddressSize should be set before this function call.
2190 * EEPROM address size can be got through GetEEPROMSize8185()
2191 */
3f9ab1ee 2192static void rtl8192_read_eeprom_info(struct r8192_priv *priv)
ecdfa446 2193{
3f9ab1ee 2194 struct net_device *dev = priv->ieee80211->dev;
ecdfa446 2195 u8 tempval;
ecdfa446 2196 u8 ICVer8192, ICVer8256;
ecdfa446
GKH
2197 u16 i,usValue, IC_Version;
2198 u16 EEPROMId;
ecdfa446
GKH
2199 u8 bMac_Tmp_Addr[6] = {0x00, 0xe0, 0x4c, 0x00, 0x00, 0x01};
2200 RT_TRACE(COMP_INIT, "====> rtl8192_read_eeprom_info\n");
2201
2202
2203 // TODO: I don't know if we need to apply EF function to EEPROM read function
2204
2205 //2 Read EEPROM ID to make sure autoload is success
2206 EEPROMId = eprom_read(dev, 0);
2207 if( EEPROMId != RTL8190_EEPROM_ID )
2208 {
2209 RT_TRACE(COMP_ERR, "EEPROM ID is invalid:%x, %x\n", EEPROMId, RTL8190_EEPROM_ID);
2210 priv->AutoloadFailFlag=true;
2211 }
2212 else
2213 {
2214 priv->AutoloadFailFlag=false;
2215 }
2216
2217 //
2218 // Assign Chip Version ID
2219 //
2220 // Read IC Version && Channel Plan
2221 if(!priv->AutoloadFailFlag)
2222 {
2223 // VID, PID
2224 priv->eeprom_vid = eprom_read(dev, (EEPROM_VID >> 1));
2225 priv->eeprom_did = eprom_read(dev, (EEPROM_DID >> 1));
2226
2227 usValue = eprom_read(dev, (u16)(EEPROM_Customer_ID>>1)) >> 8 ;
2228 priv->eeprom_CustomerID = (u8)( usValue & 0xff);
2229 usValue = eprom_read(dev, (EEPROM_ICVersion_ChannelPlan>>1));
2230 priv->eeprom_ChannelPlan = usValue&0xff;
2231 IC_Version = ((usValue&0xff00)>>8);
2232
ecdfa446
GKH
2233 ICVer8192 = (IC_Version&0xf); //bit0~3; 1:A cut, 2:B cut, 3:C cut...
2234 ICVer8256 = ((IC_Version&0xf0)>>4);//bit4~6, bit7 reserved for other RF chip; 1:A cut, 2:B cut, 3:C cut...
2235 RT_TRACE(COMP_INIT, "\nICVer8192 = 0x%x\n", ICVer8192);
2236 RT_TRACE(COMP_INIT, "\nICVer8256 = 0x%x\n", ICVer8256);
2237 if(ICVer8192 == 0x2) //B-cut
2238 {
2239 if(ICVer8256 == 0x5) //E-cut
2240 priv->card_8192_version= VERSION_8190_BE;
2241 }
4803ef77 2242
ecdfa446
GKH
2243 switch(priv->card_8192_version)
2244 {
2245 case VERSION_8190_BD:
2246 case VERSION_8190_BE:
2247 break;
2248 default:
2249 priv->card_8192_version = VERSION_8190_BD;
2250 break;
2251 }
2252 RT_TRACE(COMP_INIT, "\nIC Version = 0x%x\n", priv->card_8192_version);
2253 }
2254 else
2255 {
2256 priv->card_8192_version = VERSION_8190_BD;
2257 priv->eeprom_vid = 0;
2258 priv->eeprom_did = 0;
2259 priv->eeprom_CustomerID = 0;
2260 priv->eeprom_ChannelPlan = 0;
2261 RT_TRACE(COMP_INIT, "\nIC Version = 0x%x\n", 0xff);
2262 }
2263
2264 RT_TRACE(COMP_INIT, "EEPROM VID = 0x%4x\n", priv->eeprom_vid);
2265 RT_TRACE(COMP_INIT, "EEPROM DID = 0x%4x\n", priv->eeprom_did);
2266 RT_TRACE(COMP_INIT,"EEPROM Customer ID: 0x%2x\n", priv->eeprom_CustomerID);
2267
2268 //2 Read Permanent MAC address
2269 if(!priv->AutoloadFailFlag)
2270 {
2271 for(i = 0; i < 6; i += 2)
2272 {
2273 usValue = eprom_read(dev, (u16) ((EEPROM_NODE_ADDRESS_BYTE_0+i)>>1));
2274 *(u16*)(&dev->dev_addr[i]) = usValue;
2275 }
2276 } else {
2277 // when auto load failed, the last address byte set to be a random one.
2278 // added by david woo.2007/11/7
2279 memcpy(dev->dev_addr, bMac_Tmp_Addr, 6);
ecdfa446
GKH
2280 }
2281
820793c3 2282 RT_TRACE(COMP_INIT, "Permanent Address = %pM\n", dev->dev_addr);
ecdfa446
GKH
2283
2284 //2 TX Power Check EEPROM Fail or not
2285 if(priv->card_8192_version > VERSION_8190_BD) {
2286 priv->bTXPowerDataReadFromEEPORM = true;
2287 } else {
2288 priv->bTXPowerDataReadFromEEPORM = false;
2289 }
2290
bbc9a991 2291 // 2007/11/15 MH 8190PCI Default=2T4R, 8192PCIE default=1T2R
ecdfa446
GKH
2292 priv->rf_type = RTL819X_DEFAULT_RF_TYPE;
2293
2294 if(priv->card_8192_version > VERSION_8190_BD)
2295 {
2296 // Read RF-indication and Tx Power gain index diff of legacy to HT OFDM rate.
2297 if(!priv->AutoloadFailFlag)
2298 {
2299 tempval = (eprom_read(dev, (EEPROM_RFInd_PowerDiff>>1))) & 0xff;
2300 priv->EEPROMLegacyHTTxPowerDiff = tempval & 0xf; // bit[3:0]
2301
2302 if (tempval&0x80) //RF-indication, bit[7]
2303 priv->rf_type = RF_1T2R;
2304 else
2305 priv->rf_type = RF_2T4R;
2306 }
2307 else
2308 {
2309 priv->EEPROMLegacyHTTxPowerDiff = EEPROM_Default_LegacyHTTxPowerDiff;
2310 }
2311 RT_TRACE(COMP_INIT, "EEPROMLegacyHTTxPowerDiff = %d\n",
2312 priv->EEPROMLegacyHTTxPowerDiff);
2313
2314 // Read ThermalMeter from EEPROM
2315 if(!priv->AutoloadFailFlag)
2316 {
2317 priv->EEPROMThermalMeter = (u8)(((eprom_read(dev, (EEPROM_ThermalMeter>>1))) & 0xff00)>>8);
2318 }
2319 else
2320 {
2321 priv->EEPROMThermalMeter = EEPROM_Default_ThermalMeter;
2322 }
2323 RT_TRACE(COMP_INIT, "ThermalMeter = %d\n", priv->EEPROMThermalMeter);
2324 //vivi, for tx power track
2325 priv->TSSI_13dBm = priv->EEPROMThermalMeter *100;
2326
2327 if(priv->epromtype == EPROM_93c46)
2328 {
2329 // Read antenna tx power offset of B/C/D to A and CrystalCap from EEPROM
2330 if(!priv->AutoloadFailFlag)
2331 {
2332 usValue = eprom_read(dev, (EEPROM_TxPwDiff_CrystalCap>>1));
2333 priv->EEPROMAntPwDiff = (usValue&0x0fff);
2334 priv->EEPROMCrystalCap = (u8)((usValue&0xf000)>>12);
2335 }
2336 else
2337 {
2338 priv->EEPROMAntPwDiff = EEPROM_Default_AntTxPowerDiff;
2339 priv->EEPROMCrystalCap = EEPROM_Default_TxPwDiff_CrystalCap;
2340 }
2341 RT_TRACE(COMP_INIT, "EEPROMAntPwDiff = %d\n", priv->EEPROMAntPwDiff);
2342 RT_TRACE(COMP_INIT, "EEPROMCrystalCap = %d\n", priv->EEPROMCrystalCap);
2343
2344 //
2345 // Get per-channel Tx Power Level
2346 //
2347 for(i=0; i<14; i+=2)
2348 {
2349 if(!priv->AutoloadFailFlag)
2350 {
2351 usValue = eprom_read(dev, (u16) ((EEPROM_TxPwIndex_CCK+i)>>1) );
2352 }
2353 else
2354 {
2355 usValue = EEPROM_Default_TxPower;
2356 }
2357 *((u16*)(&priv->EEPROMTxPowerLevelCCK[i])) = usValue;
2358 RT_TRACE(COMP_INIT,"CCK Tx Power Level, Index %d = 0x%02x\n", i, priv->EEPROMTxPowerLevelCCK[i]);
2359 RT_TRACE(COMP_INIT, "CCK Tx Power Level, Index %d = 0x%02x\n", i+1, priv->EEPROMTxPowerLevelCCK[i+1]);
2360 }
2361 for(i=0; i<14; i+=2)
2362 {
2363 if(!priv->AutoloadFailFlag)
2364 {
2365 usValue = eprom_read(dev, (u16) ((EEPROM_TxPwIndex_OFDM_24G+i)>>1) );
2366 }
2367 else
2368 {
2369 usValue = EEPROM_Default_TxPower;
2370 }
2371 *((u16*)(&priv->EEPROMTxPowerLevelOFDM24G[i])) = usValue;
2372 RT_TRACE(COMP_INIT, "OFDM 2.4G Tx Power Level, Index %d = 0x%02x\n", i, priv->EEPROMTxPowerLevelOFDM24G[i]);
2373 RT_TRACE(COMP_INIT, "OFDM 2.4G Tx Power Level, Index %d = 0x%02x\n", i+1, priv->EEPROMTxPowerLevelOFDM24G[i+1]);
2374 }
2375 }
ecdfa446 2376
ecdfa446
GKH
2377 //
2378 // Update HAL variables.
2379 //
2380 if(priv->epromtype == EPROM_93c46)
2381 {
2382 for(i=0; i<14; i++)
2383 {
2384 priv->TxPowerLevelCCK[i] = priv->EEPROMTxPowerLevelCCK[i];
2385 priv->TxPowerLevelOFDM24G[i] = priv->EEPROMTxPowerLevelOFDM24G[i];
2386 }
2387 priv->LegacyHTTxPowerDiff = priv->EEPROMLegacyHTTxPowerDiff;
2388 // Antenna B gain offset to antenna A, bit0~3
2389 priv->AntennaTxPwDiff[0] = (priv->EEPROMAntPwDiff & 0xf);
2390 // Antenna C gain offset to antenna A, bit4~7
2391 priv->AntennaTxPwDiff[1] = ((priv->EEPROMAntPwDiff & 0xf0)>>4);
2392 // Antenna D gain offset to antenna A, bit8~11
2393 priv->AntennaTxPwDiff[2] = ((priv->EEPROMAntPwDiff & 0xf00)>>8);
2394 // CrystalCap, bit12~15
2395 priv->CrystalCap = priv->EEPROMCrystalCap;
2396 // ThermalMeter, bit0~3 for RFIC1, bit4~7 for RFIC2
2397 priv->ThermalMeter[0] = (priv->EEPROMThermalMeter & 0xf);
2398 priv->ThermalMeter[1] = ((priv->EEPROMThermalMeter & 0xf0)>>4);
2399 }
2400 else if(priv->epromtype == EPROM_93c56)
2401 {
2402 //char cck_pwr_diff_a=0, cck_pwr_diff_c=0;
2403
2404 //cck_pwr_diff_a = pHalData->EEPROMRfACCKChnl7TxPwLevel - pHalData->EEPROMRfAOfdmChnlTxPwLevel[1];
2405 //cck_pwr_diff_c = pHalData->EEPROMRfCCCKChnl7TxPwLevel - pHalData->EEPROMRfCOfdmChnlTxPwLevel[1];
2406 for(i=0; i<3; i++) // channel 1~3 use the same Tx Power Level.
2407 {
2408 priv->TxPowerLevelCCK_A[i] = priv->EEPROMRfACCKChnl1TxPwLevel[0];
2409 priv->TxPowerLevelOFDM24G_A[i] = priv->EEPROMRfAOfdmChnlTxPwLevel[0];
2410 priv->TxPowerLevelCCK_C[i] = priv->EEPROMRfCCCKChnl1TxPwLevel[0];
2411 priv->TxPowerLevelOFDM24G_C[i] = priv->EEPROMRfCOfdmChnlTxPwLevel[0];
2412 }
2413 for(i=3; i<9; i++) // channel 4~9 use the same Tx Power Level
2414 {
2415 priv->TxPowerLevelCCK_A[i] = priv->EEPROMRfACCKChnl1TxPwLevel[1];
2416 priv->TxPowerLevelOFDM24G_A[i] = priv->EEPROMRfAOfdmChnlTxPwLevel[1];
2417 priv->TxPowerLevelCCK_C[i] = priv->EEPROMRfCCCKChnl1TxPwLevel[1];
2418 priv->TxPowerLevelOFDM24G_C[i] = priv->EEPROMRfCOfdmChnlTxPwLevel[1];
2419 }
2420 for(i=9; i<14; i++) // channel 10~14 use the same Tx Power Level
2421 {
2422 priv->TxPowerLevelCCK_A[i] = priv->EEPROMRfACCKChnl1TxPwLevel[2];
2423 priv->TxPowerLevelOFDM24G_A[i] = priv->EEPROMRfAOfdmChnlTxPwLevel[2];
2424 priv->TxPowerLevelCCK_C[i] = priv->EEPROMRfCCCKChnl1TxPwLevel[2];
2425 priv->TxPowerLevelOFDM24G_C[i] = priv->EEPROMRfCOfdmChnlTxPwLevel[2];
2426 }
2427 for(i=0; i<14; i++)
2428 RT_TRACE(COMP_INIT, "priv->TxPowerLevelCCK_A[%d] = 0x%x\n", i, priv->TxPowerLevelCCK_A[i]);
2429 for(i=0; i<14; i++)
2430 RT_TRACE(COMP_INIT,"priv->TxPowerLevelOFDM24G_A[%d] = 0x%x\n", i, priv->TxPowerLevelOFDM24G_A[i]);
2431 for(i=0; i<14; i++)
2432 RT_TRACE(COMP_INIT, "priv->TxPowerLevelCCK_C[%d] = 0x%x\n", i, priv->TxPowerLevelCCK_C[i]);
2433 for(i=0; i<14; i++)
2434 RT_TRACE(COMP_INIT, "priv->TxPowerLevelOFDM24G_C[%d] = 0x%x\n", i, priv->TxPowerLevelOFDM24G_C[i]);
2435 priv->LegacyHTTxPowerDiff = priv->EEPROMLegacyHTTxPowerDiff;
2436 priv->AntennaTxPwDiff[0] = 0;
2437 priv->AntennaTxPwDiff[1] = 0;
2438 priv->AntennaTxPwDiff[2] = 0;
2439 priv->CrystalCap = priv->EEPROMCrystalCap;
2440 // ThermalMeter, bit0~3 for RFIC1, bit4~7 for RFIC2
2441 priv->ThermalMeter[0] = (priv->EEPROMThermalMeter & 0xf);
2442 priv->ThermalMeter[1] = ((priv->EEPROMThermalMeter & 0xf0)>>4);
2443 }
2444 }
2445
2446 if(priv->rf_type == RF_1T2R)
2447 {
2448 RT_TRACE(COMP_INIT, "\n1T2R config\n");
2449 }
2450 else if (priv->rf_type == RF_2T4R)
2451 {
2452 RT_TRACE(COMP_INIT, "\n2T4R config\n");
2453 }
2454
2455 // 2008/01/16 MH We can only know RF type in the function. So we have to init
2456 // DIG RATR table again.
2457 init_rate_adaptive(dev);
2458
2459 //1 Make a copy for following variables and we can change them if we want
2460
ecdfa446
GKH
2461 if(priv->RegChannelPlan == 0xf)
2462 {
2463 priv->ChannelPlan = priv->eeprom_ChannelPlan;
2464 }
2465 else
2466 {
2467 priv->ChannelPlan = priv->RegChannelPlan;
2468 }
2469
2470 //
2471 // Used PID and DID to Set CustomerID
2472 //
2473 if( priv->eeprom_vid == 0x1186 && priv->eeprom_did == 0x3304 )
2474 {
2475 priv->CustomerID = RT_CID_DLINK;
2476 }
2477
2478 switch(priv->eeprom_CustomerID)
2479 {
2480 case EEPROM_CID_DEFAULT:
2481 priv->CustomerID = RT_CID_DEFAULT;
2482 break;
2483 case EEPROM_CID_CAMEO:
2484 priv->CustomerID = RT_CID_819x_CAMEO;
2485 break;
2486 case EEPROM_CID_RUNTOP:
2487 priv->CustomerID = RT_CID_819x_RUNTOP;
2488 break;
2489 case EEPROM_CID_NetCore:
2490 priv->CustomerID = RT_CID_819x_Netcore;
2491 break;
2492 case EEPROM_CID_TOSHIBA: // Merge by Jacken, 2008/01/31
2493 priv->CustomerID = RT_CID_TOSHIBA;
2494 if(priv->eeprom_ChannelPlan&0x80)
2495 priv->ChannelPlan = priv->eeprom_ChannelPlan&0x7f;
2496 else
2497 priv->ChannelPlan = 0x0;
2498 RT_TRACE(COMP_INIT, "Toshiba ChannelPlan = 0x%x\n",
2499 priv->ChannelPlan);
2500 break;
2501 case EEPROM_CID_Nettronix:
ecdfa446
GKH
2502 priv->CustomerID = RT_CID_Nettronix;
2503 break;
2504 case EEPROM_CID_Pronet:
2505 priv->CustomerID = RT_CID_PRONET;
2506 break;
2507 case EEPROM_CID_DLINK:
2508 priv->CustomerID = RT_CID_DLINK;
2509 break;
2510
2511 case EEPROM_CID_WHQL:
2512 //Adapter->bInHctTest = TRUE;//do not supported
2513
2514 //priv->bSupportTurboMode = FALSE;
2515 //priv->bAutoTurboBy8186 = FALSE;
2516
2517 //pMgntInfo->PowerSaveControl.bInactivePs = FALSE;
2518 //pMgntInfo->PowerSaveControl.bIPSModeBackup = FALSE;
2519 //pMgntInfo->PowerSaveControl.bLeisurePs = FALSE;
2520
2521 break;
2522 default:
2523 // value from RegCustomerID
2524 break;
2525 }
2526
2527 //Avoid the channel plan array overflow, by Bruce, 2007-08-27.
2528 if(priv->ChannelPlan > CHANNEL_PLAN_LEN - 1)
2529 priv->ChannelPlan = 0; //FCC
2530
2531 switch(priv->CustomerID)
2532 {
2533 case RT_CID_DEFAULT:
ecdfa446 2534 priv->LedStrategy = SW_LED_MODE1;
ecdfa446
GKH
2535 break;
2536
2537 case RT_CID_819x_CAMEO:
2538 priv->LedStrategy = SW_LED_MODE2;
2539 break;
2540
2541 case RT_CID_819x_RUNTOP:
2542 priv->LedStrategy = SW_LED_MODE3;
2543 break;
2544
2545 case RT_CID_819x_Netcore:
2546 priv->LedStrategy = SW_LED_MODE4;
2547 break;
2548
2549 case RT_CID_Nettronix:
2550 priv->LedStrategy = SW_LED_MODE5;
2551 break;
2552
2553 case RT_CID_PRONET:
2554 priv->LedStrategy = SW_LED_MODE6;
2555 break;
2556
2557 case RT_CID_TOSHIBA: //Modify by Jacken 2008/01/31
2558 // Do nothing.
2559 //break;
2560
2561 default:
ecdfa446 2562 priv->LedStrategy = SW_LED_MODE1;
ecdfa446
GKH
2563 break;
2564 }
65a43784 2565
2566
ecdfa446 2567 if( priv->eeprom_vid == 0x1186 && priv->eeprom_did == 0x3304)
65a43784 2568 priv->ieee80211->bSupportRemoteWakeUp = true;
ecdfa446 2569 else
65a43784 2570 priv->ieee80211->bSupportRemoteWakeUp = false;
2571
2572
ecdfa446
GKH
2573 RT_TRACE(COMP_INIT, "RegChannelPlan(%d)\n", priv->RegChannelPlan);
2574 RT_TRACE(COMP_INIT, "ChannelPlan = %d \n", priv->ChannelPlan);
2575 RT_TRACE(COMP_INIT, "LedStrategy = %d \n", priv->LedStrategy);
2576 RT_TRACE(COMP_TRACE, "<==== ReadAdapterInfo\n");
2577
2578 return ;
2579}
2580
2581
5e1ad18a 2582static short rtl8192_get_channel_map(struct net_device * dev)
ecdfa446
GKH
2583{
2584 struct r8192_priv *priv = ieee80211_priv(dev);
2585#ifdef ENABLE_DOT11D
2586 if(priv->ChannelPlan> COUNTRY_CODE_GLOBAL_DOMAIN){
2587 printk("rtl8180_init:Error channel plan! Set to default.\n");
2588 priv->ChannelPlan= 0;
2589 }
2590 RT_TRACE(COMP_INIT, "Channel plan is %d\n",priv->ChannelPlan);
2591
2592 rtl819x_set_channel_map(priv->ChannelPlan, priv);
2593#else
2594 int ch,i;
2595 //Set Default Channel Plan
2596 if(!channels){
2597 DMESG("No channels, aborting");
2598 return -1;
2599 }
2600 ch=channels;
2601 priv->ChannelPlan= 0;//hikaru
2602 // set channels 1..14 allowed in given locale
2603 for (i=1; i<=14; i++) {
2604 (priv->ieee80211->channel_map)[i] = (u8)(ch & 0x01);
2605 ch >>= 1;
2606 }
2607#endif
2608 return 0;
2609}
5e1ad18a
GKH
2610
2611static short rtl8192_init(struct net_device *dev)
ecdfa446
GKH
2612{
2613 struct r8192_priv *priv = ieee80211_priv(dev);
2614 memset(&(priv->stats),0,sizeof(struct Stats));
2615 rtl8192_init_priv_variable(dev);
2616 rtl8192_init_priv_lock(priv);
2617 rtl8192_init_priv_task(dev);
2618 rtl8192_get_eeprom_size(dev);
3f9ab1ee 2619 rtl8192_read_eeprom_info(priv);
ecdfa446
GKH
2620 rtl8192_get_channel_map(dev);
2621 init_hal_dm(dev);
2622 init_timer(&priv->watch_dog_timer);
2623 priv->watch_dog_timer.data = (unsigned long)dev;
2624 priv->watch_dog_timer.function = watch_dog_timer_callback;
7bb5e823 2625 if (request_irq(dev->irq, rtl8192_interrupt, IRQF_SHARED, dev->name, dev)) {
ecdfa446
GKH
2626 printk("Error allocating IRQ %d",dev->irq);
2627 return -1;
2628 }else{
2629 priv->irq=dev->irq;
2630 printk("IRQ %d",dev->irq);
2631 }
2632 if(rtl8192_pci_initdescring(dev)!=0){
2633 printk("Endopoints initialization failed");
2634 return -1;
2635 }
2636
2637 //rtl8192_rx_enable(dev);
2638 //rtl8192_adapter_start(dev);
ecdfa446
GKH
2639 return 0;
2640}
2641
214985a6
MM
2642/*
2643 * Actually only set RRSR, RATR and BW_OPMODE registers
2644 * not to do all the hw config as its name says
2645 * This part need to modified according to the rate set we filtered
2646 */
5e1ad18a 2647static void rtl8192_hwconfig(struct net_device* dev)
ecdfa446
GKH
2648{
2649 u32 regRATR = 0, regRRSR = 0;
2650 u8 regBwOpMode = 0, regTmp = 0;
2651 struct r8192_priv *priv = ieee80211_priv(dev);
2652
2653// Set RRSR, RATR, and BW_OPMODE registers
2654 //
2655 switch(priv->ieee80211->mode)
2656 {
2657 case WIRELESS_MODE_B:
2658 regBwOpMode = BW_OPMODE_20MHZ;
2659 regRATR = RATE_ALL_CCK;
2660 regRRSR = RATE_ALL_CCK;
2661 break;
2662 case WIRELESS_MODE_A:
2663 regBwOpMode = BW_OPMODE_5G |BW_OPMODE_20MHZ;
2664 regRATR = RATE_ALL_OFDM_AG;
2665 regRRSR = RATE_ALL_OFDM_AG;
2666 break;
2667 case WIRELESS_MODE_G:
2668 regBwOpMode = BW_OPMODE_20MHZ;
2669 regRATR = RATE_ALL_CCK | RATE_ALL_OFDM_AG;
2670 regRRSR = RATE_ALL_CCK | RATE_ALL_OFDM_AG;
2671 break;
2672 case WIRELESS_MODE_AUTO:
2673 case WIRELESS_MODE_N_24G:
2674 // It support CCK rate by default.
2675 // CCK rate will be filtered out only when associated AP does not support it.
2676 regBwOpMode = BW_OPMODE_20MHZ;
2677 regRATR = RATE_ALL_CCK | RATE_ALL_OFDM_AG | RATE_ALL_OFDM_1SS | RATE_ALL_OFDM_2SS;
2678 regRRSR = RATE_ALL_CCK | RATE_ALL_OFDM_AG;
2679 break;
2680 case WIRELESS_MODE_N_5G:
2681 regBwOpMode = BW_OPMODE_5G;
2682 regRATR = RATE_ALL_OFDM_AG | RATE_ALL_OFDM_1SS | RATE_ALL_OFDM_2SS;
2683 regRRSR = RATE_ALL_OFDM_AG;
2684 break;
2685 }
2686
3f9ab1ee 2687 write_nic_byte(priv, BW_OPMODE, regBwOpMode);
ecdfa446
GKH
2688 {
2689 u32 ratr_value = 0;
2690 ratr_value = regRATR;
2691 if (priv->rf_type == RF_1T2R)
2692 {
2693 ratr_value &= ~(RATE_ALL_OFDM_2SS);
2694 }
3f9ab1ee
MM
2695 write_nic_dword(priv, RATR0, ratr_value);
2696 write_nic_byte(priv, UFWP, 1);
ecdfa446 2697 }
3f9ab1ee 2698 regTmp = read_nic_byte(priv, 0x313);
ecdfa446 2699 regRRSR = ((regTmp) << 24) | (regRRSR & 0x00ffffff);
3f9ab1ee 2700 write_nic_dword(priv, RRSR, regRRSR);
ecdfa446
GKH
2701
2702 //
2703 // Set Retry Limit here
2704 //
3f9ab1ee 2705 write_nic_word(priv, RETRY_LIMIT,
207b58fb 2706 priv->ShortRetryLimit << RETRY_LIMIT_SHORT_SHIFT |
ecdfa446
GKH
2707 priv->LongRetryLimit << RETRY_LIMIT_LONG_SHIFT);
2708 // Set Contention Window here
2709
2710 // Set Tx AGC
2711
2712 // Set Tx Antenna including Feedback control
2713
2714 // Set Auto Rate fallback control
2715
2716
2717}
2718
2719
5e1ad18a 2720static RT_STATUS rtl8192_adapter_start(struct net_device *dev)
ecdfa446
GKH
2721{
2722 struct r8192_priv *priv = ieee80211_priv(dev);
2723// struct ieee80211_device *ieee = priv->ieee80211;
2724 u32 ulRegRead;
2725 RT_STATUS rtStatus = RT_STATUS_SUCCESS;
ecdfa446
GKH
2726 //u8 eRFPath;
2727 u8 tmpvalue;
ecdfa446 2728 u8 ICVersion,SwitchingRegulatorOutput;
ecdfa446 2729 bool bfirmwareok = true;
ecdfa446
GKH
2730 u32 tmpRegA, tmpRegC, TempCCk;
2731 int i =0;
ecdfa446
GKH
2732
2733 RT_TRACE(COMP_INIT, "====>%s()\n", __FUNCTION__);
2734 priv->being_init_adapter = true;
2735 rtl8192_pci_resetdescring(dev);
2736 // 2007/11/02 MH Before initalizing RF. We can not use FW to do RF-R/W.
2737 priv->Rf_Mode = RF_OP_By_SW_3wire;
4803ef77 2738
ecdfa446
GKH
2739 //dPLL on
2740 if(priv->ResetProgress == RESET_TYPE_NORESET)
2741 {
3f9ab1ee 2742 write_nic_byte(priv, ANAPAR, 0x37);
ecdfa446
GKH
2743 // Accordign to designer's explain, LBUS active will never > 10ms. We delay 10ms
2744 // Joseph increae the time to prevent firmware download fail
2745 mdelay(500);
2746 }
4803ef77 2747
ecdfa446
GKH
2748 //PlatformSleepUs(10000);
2749 // For any kind of InitializeAdapter process, we shall use system now!!
2750 priv->pFirmware->firmware_status = FW_STATUS_0_INIT;
2751
ecdfa446
GKH
2752 //
2753 //3 //Config CPUReset Register
2754 //3//
2755 //3 Firmware Reset Or Not
3f9ab1ee 2756 ulRegRead = read_nic_dword(priv, CPU_GEN);
ecdfa446
GKH
2757 if(priv->pFirmware->firmware_status == FW_STATUS_0_INIT)
2758 { //called from MPInitialized. do nothing
2759 ulRegRead |= CPU_GEN_SYSTEM_RESET;
2760 }else if(priv->pFirmware->firmware_status == FW_STATUS_5_READY)
2761 ulRegRead |= CPU_GEN_FIRMWARE_RESET; // Called from MPReset
2762 else
2763 RT_TRACE(COMP_ERR, "ERROR in %s(): undefined firmware state(%d)\n", __FUNCTION__, priv->pFirmware->firmware_status);
2764
3f9ab1ee 2765 write_nic_dword(priv, CPU_GEN, ulRegRead);
ecdfa446
GKH
2766 //mdelay(100);
2767
ecdfa446
GKH
2768 //3//
2769 //3 //Fix the issue of E-cut high temperature issue
2770 //3//
2771 // TODO: E cut only
3f9ab1ee 2772 ICVersion = read_nic_byte(priv, IC_VERRSION);
ecdfa446
GKH
2773 if(ICVersion >= 0x4) //E-cut only
2774 {
2775 // HW SD suggest that we should not wirte this register too often, so driver
2776 // should readback this register. This register will be modified only when
2777 // power on reset
3f9ab1ee 2778 SwitchingRegulatorOutput = read_nic_byte(priv, SWREGULATOR);
ecdfa446
GKH
2779 if(SwitchingRegulatorOutput != 0xb8)
2780 {
3f9ab1ee 2781 write_nic_byte(priv, SWREGULATOR, 0xa8);
ecdfa446 2782 mdelay(1);
3f9ab1ee 2783 write_nic_byte(priv, SWREGULATOR, 0xb8);
ecdfa446
GKH
2784 }
2785 }
ecdfa446
GKH
2786
2787 //3//
2788 //3// Initialize BB before MAC
2789 //3//
ecdfa446
GKH
2790 RT_TRACE(COMP_INIT, "BB Config Start!\n");
2791 rtStatus = rtl8192_BBConfig(dev);
2792 if(rtStatus != RT_STATUS_SUCCESS)
2793 {
2794 RT_TRACE(COMP_ERR, "BB Config failed\n");
2795 return rtStatus;
2796 }
2797 RT_TRACE(COMP_INIT,"BB Config Finished!\n");
2798
ecdfa446
GKH
2799 //3//Set Loopback mode or Normal mode
2800 //3//
2801 //2006.12.13 by emily. Note!We should not merge these two CPU_GEN register writings
2802 // because setting of System_Reset bit reset MAC to default transmission mode.
2803 //Loopback mode or not
2804 priv->LoopbackMode = RTL819X_NO_LOOPBACK;
2805 //priv->LoopbackMode = RTL819X_MAC_LOOPBACK;
2806 if(priv->ResetProgress == RESET_TYPE_NORESET)
2807 {
3f9ab1ee 2808 ulRegRead = read_nic_dword(priv, CPU_GEN);
ecdfa446
GKH
2809 if(priv->LoopbackMode == RTL819X_NO_LOOPBACK)
2810 {
2811 ulRegRead = ((ulRegRead & CPU_GEN_NO_LOOPBACK_MSK) | CPU_GEN_NO_LOOPBACK_SET);
2812 }
2813 else if (priv->LoopbackMode == RTL819X_MAC_LOOPBACK )
2814 {
2815 ulRegRead |= CPU_CCK_LOOPBACK;
2816 }
2817 else
2818 {
2819 RT_TRACE(COMP_ERR,"Serious error: wrong loopback mode setting\n");
2820 }
2821
2822 //2008.06.03, for WOL
2823 //ulRegRead &= (~(CPU_GEN_GPIO_UART));
3f9ab1ee 2824 write_nic_dword(priv, CPU_GEN, ulRegRead);
ecdfa446
GKH
2825
2826 // 2006.11.29. After reset cpu, we sholud wait for a second, otherwise, it may fail to write registers. Emily
2827 udelay(500);
2828 }
2829 //3Set Hardware(Do nothing now)
2830 rtl8192_hwconfig(dev);
2831 //2=======================================================
2832 // Common Setting for all of the FPGA platform. (part 1)
2833 //2=======================================================
2834 // If there is changes, please make sure it applies to all of the FPGA version
2835 //3 Turn on Tx/Rx
3f9ab1ee 2836 write_nic_byte(priv, CMDR, CR_RE|CR_TE);
ecdfa446
GKH
2837
2838 //2Set Tx dma burst
3f9ab1ee 2839 write_nic_byte(priv, PCIF, ((MXDMA2_NoLimit<<MXDMA2_RX_SHIFT) |
ecdfa446 2840 (MXDMA2_NoLimit<<MXDMA2_TX_SHIFT) ));
4803ef77 2841
ecdfa446 2842 //set IDR0 here
3f9ab1ee
MM
2843 write_nic_dword(priv, MAC0, ((u32*)dev->dev_addr)[0]);
2844 write_nic_word(priv, MAC4, ((u16*)(dev->dev_addr + 4))[0]);
ecdfa446 2845 //set RCR
3f9ab1ee 2846 write_nic_dword(priv, RCR, priv->ReceiveConfig);
ecdfa446
GKH
2847
2848 //3 Initialize Number of Reserved Pages in Firmware Queue
2849 #ifdef TO_DO_LIST
2850 if(priv->bInHctTest)
2851 {
207b58fb
MM
2852 PlatformEFIOWrite4Byte(Adapter, RQPN1, NUM_OF_PAGE_IN_FW_QUEUE_BK_DTM << RSVD_FW_QUEUE_PAGE_BK_SHIFT |
2853 NUM_OF_PAGE_IN_FW_QUEUE_BE_DTM << RSVD_FW_QUEUE_PAGE_BE_SHIFT |
2854 NUM_OF_PAGE_IN_FW_QUEUE_VI_DTM << RSVD_FW_QUEUE_PAGE_VI_SHIFT |
ecdfa446
GKH
2855 NUM_OF_PAGE_IN_FW_QUEUE_VO_DTM <<RSVD_FW_QUEUE_PAGE_VO_SHIFT);
2856 PlatformEFIOWrite4Byte(Adapter, RQPN2, NUM_OF_PAGE_IN_FW_QUEUE_MGNT << RSVD_FW_QUEUE_PAGE_MGNT_SHIFT);
207b58fb
MM
2857 PlatformEFIOWrite4Byte(Adapter, RQPN3, APPLIED_RESERVED_QUEUE_IN_FW|
2858 NUM_OF_PAGE_IN_FW_QUEUE_BCN<<RSVD_FW_QUEUE_PAGE_BCN_SHIFT|
ecdfa446
GKH
2859 NUM_OF_PAGE_IN_FW_QUEUE_PUB_DTM<<RSVD_FW_QUEUE_PAGE_PUB_SHIFT);
2860 }
2861 else
2862 #endif
2863 {
3f9ab1ee 2864 write_nic_dword(priv, RQPN1, NUM_OF_PAGE_IN_FW_QUEUE_BK << RSVD_FW_QUEUE_PAGE_BK_SHIFT |
207b58fb
MM
2865 NUM_OF_PAGE_IN_FW_QUEUE_BE << RSVD_FW_QUEUE_PAGE_BE_SHIFT |
2866 NUM_OF_PAGE_IN_FW_QUEUE_VI << RSVD_FW_QUEUE_PAGE_VI_SHIFT |
ecdfa446 2867 NUM_OF_PAGE_IN_FW_QUEUE_VO <<RSVD_FW_QUEUE_PAGE_VO_SHIFT);
3f9ab1ee
MM
2868 write_nic_dword(priv, RQPN2, NUM_OF_PAGE_IN_FW_QUEUE_MGNT << RSVD_FW_QUEUE_PAGE_MGNT_SHIFT);
2869 write_nic_dword(priv, RQPN3, APPLIED_RESERVED_QUEUE_IN_FW|
207b58fb 2870 NUM_OF_PAGE_IN_FW_QUEUE_BCN<<RSVD_FW_QUEUE_PAGE_BCN_SHIFT|
ecdfa446
GKH
2871 NUM_OF_PAGE_IN_FW_QUEUE_PUB<<RSVD_FW_QUEUE_PAGE_PUB_SHIFT);
2872 }
2873
2874 rtl8192_tx_enable(dev);
2875 rtl8192_rx_enable(dev);
2876 //3Set Response Rate Setting Register
2877 // CCK rate is supported by default.
2878 // CCK rate will be filtered out only when associated AP does not support it.
3f9ab1ee
MM
2879 ulRegRead = (0xFFF00000 & read_nic_dword(priv, RRSR)) | RATE_ALL_OFDM_AG | RATE_ALL_CCK;
2880 write_nic_dword(priv, RRSR, ulRegRead);
2881 write_nic_dword(priv, RATR0+4*7, (RATE_ALL_OFDM_AG | RATE_ALL_CCK));
ecdfa446
GKH
2882
2883 //2Set AckTimeout
2884 // TODO: (it value is only for FPGA version). need to be changed!!2006.12.18, by Emily
3f9ab1ee 2885 write_nic_byte(priv, ACK_TIMEOUT, 0x30);
ecdfa446
GKH
2886
2887 //rtl8192_actset_wirelessmode(dev,priv->RegWirelessMode);
2888 if(priv->ResetProgress == RESET_TYPE_NORESET)
2889 rtl8192_SetWirelessMode(dev, priv->ieee80211->mode);
2890 //-----------------------------------------------------------------------------
2891 // Set up security related. 070106, by rcnjko:
2892 // 1. Clear all H/W keys.
2893 // 2. Enable H/W encryption/decryption.
2894 //-----------------------------------------------------------------------------
2895 CamResetAllEntry(dev);
2896 {
2897 u8 SECR_value = 0x0;
2898 SECR_value |= SCR_TxEncEnable;
2899 SECR_value |= SCR_RxDecEnable;
2900 SECR_value |= SCR_NoSKMC;
3f9ab1ee 2901 write_nic_byte(priv, SECR, SECR_value);
ecdfa446
GKH
2902 }
2903 //3Beacon related
3f9ab1ee
MM
2904 write_nic_word(priv, ATIMWND, 2);
2905 write_nic_word(priv, BCN_INTERVAL, 100);
5e1ad18a 2906 for (i=0; i<QOS_QUEUE_NUM; i++)
3f9ab1ee 2907 write_nic_dword(priv, WDCAPARA_ADD[i], 0x005e4332);
ecdfa446
GKH
2908 //
2909 // Switching regulator controller: This is set temporarily.
2910 // It's not sure if this can be removed in the future.
2911 // PJ advised to leave it by default.
2912 //
3f9ab1ee 2913 write_nic_byte(priv, 0xbe, 0xc0);
ecdfa446
GKH
2914
2915 //2=======================================================
2916 // Set PHY related configuration defined in MAC register bank
2917 //2=======================================================
2918 rtl8192_phy_configmac(dev);
2919
2920 if (priv->card_8192_version > (u8) VERSION_8190_BD) {
2921 rtl8192_phy_getTxPower(dev);
2922 rtl8192_phy_setTxPower(dev, priv->chan);
2923 }
2924
2925 //if D or C cut
3f9ab1ee 2926 tmpvalue = read_nic_byte(priv, IC_VERRSION);
ecdfa446
GKH
2927 priv->IC_Cut = tmpvalue;
2928 RT_TRACE(COMP_INIT, "priv->IC_Cut = 0x%x\n", priv->IC_Cut);
2929 if(priv->IC_Cut >= IC_VersionCut_D)
2930 {
2931 //pHalData->bDcut = TRUE;
2932 if(priv->IC_Cut == IC_VersionCut_D)
2933 RT_TRACE(COMP_INIT, "D-cut\n");
2934 if(priv->IC_Cut == IC_VersionCut_E)
2935 {
2936 RT_TRACE(COMP_INIT, "E-cut\n");
2937 // HW SD suggest that we should not wirte this register too often, so driver
2938 // should readback this register. This register will be modified only when
2939 // power on reset
2940 }
2941 }
2942 else
2943 {
2944 //pHalData->bDcut = FALSE;
2945 RT_TRACE(COMP_INIT, "Before C-cut\n");
2946 }
2947
ecdfa446
GKH
2948 //Firmware download
2949 RT_TRACE(COMP_INIT, "Load Firmware!\n");
2950 bfirmwareok = init_firmware(dev);
2951 if(bfirmwareok != true) {
2952 rtStatus = RT_STATUS_FAILURE;
2953 return rtStatus;
2954 }
2955 RT_TRACE(COMP_INIT, "Load Firmware finished!\n");
11aacc28 2956
ecdfa446
GKH
2957 //RF config
2958 if(priv->ResetProgress == RESET_TYPE_NORESET)
2959 {
2960 RT_TRACE(COMP_INIT, "RF Config Started!\n");
2961 rtStatus = rtl8192_phy_RFConfig(dev);
2962 if(rtStatus != RT_STATUS_SUCCESS)
2963 {
2964 RT_TRACE(COMP_ERR, "RF Config failed\n");
2965 return rtStatus;
2966 }
2967 RT_TRACE(COMP_INIT, "RF Config Finished!\n");
2968 }
2969 rtl8192_phy_updateInitGain(dev);
2970
2971 /*---- Set CCK and OFDM Block "ON"----*/
2972 rtl8192_setBBreg(dev, rFPGA0_RFMOD, bCCKEn, 0x1);
2973 rtl8192_setBBreg(dev, rFPGA0_RFMOD, bOFDMEn, 0x1);
2974
ecdfa446 2975 //Enable Led
3f9ab1ee 2976 write_nic_byte(priv, 0x87, 0x0);
ecdfa446
GKH
2977
2978 //2=======================================================
2979 // RF Power Save
2980 //2=======================================================
2981#ifdef ENABLE_IPS
2982
2983{
0157a2b9 2984 if(priv->ieee80211->RfOffReason > RF_CHANGE_BY_PS)
ecdfa446
GKH
2985 { // H/W or S/W RF OFF before sleep.
2986 RT_TRACE((COMP_INIT|COMP_RF|COMP_POWER), "%s(): Turn off RF for RfOffReason(%d) ----------\n", __FUNCTION__,priv->ieee80211->RfOffReason);
2987 MgntActSet_RF_State(dev, eRfOff, priv->ieee80211->RfOffReason);
2988 }
2989 else if(priv->ieee80211->RfOffReason >= RF_CHANGE_BY_IPS)
2990 { // H/W or S/W RF OFF before sleep.
2991 RT_TRACE((COMP_INIT|COMP_RF|COMP_POWER), "%s(): Turn off RF for RfOffReason(%d) ----------\n", __FUNCTION__,priv->ieee80211->RfOffReason);
2992 MgntActSet_RF_State(dev, eRfOff, priv->ieee80211->RfOffReason);
2993 }
2994 else
2995 {
2996 RT_TRACE((COMP_INIT|COMP_RF|COMP_POWER), "%s(): RF-ON \n",__FUNCTION__);
2997 priv->ieee80211->eRFPowerState = eRfOn;
2998 priv->ieee80211->RfOffReason = 0;
2999 //DrvIFIndicateCurrentPhyStatus(Adapter);
3000 // LED control
3001 //Adapter->HalFunc.LedControlHandler(Adapter, LED_CTL_POWER_ON);
3002
3003 //
3004 // If inactive power mode is enabled, disable rf while in disconnected state.
3005 // But we should still tell upper layer we are in rf on state.
3006 // 2007.07.16, by shien chang.
3007 //
3008 //if(!Adapter->bInHctTest)
3009 //IPSEnter(Adapter);
3010
3011 }
3012}
3013#endif
4803ef77
MM
3014 // We can force firmware to do RF-R/W
3015 if(priv->ieee80211->FwRWRF)
3016 priv->Rf_Mode = RF_OP_By_FW;
3017 else
3018 priv->Rf_Mode = RF_OP_By_SW_3wire;
ecdfa446 3019
ecdfa446
GKH
3020 if(priv->ResetProgress == RESET_TYPE_NORESET)
3021 {
3022 dm_initialize_txpower_tracking(dev);
3023
3024 if(priv->IC_Cut >= IC_VersionCut_D)
3025 {
3026 tmpRegA= rtl8192_QueryBBReg(dev,rOFDM0_XATxIQImbalance,bMaskDWord);
3027 tmpRegC= rtl8192_QueryBBReg(dev,rOFDM0_XCTxIQImbalance,bMaskDWord);
3028 for(i = 0; i<TxBBGainTableLength; i++)
3029 {
3030 if(tmpRegA == priv->txbbgain_table[i].txbbgain_value)
3031 {
3032 priv->rfa_txpowertrackingindex= (u8)i;
3033 priv->rfa_txpowertrackingindex_real= (u8)i;
3034 priv->rfa_txpowertracking_default = priv->rfa_txpowertrackingindex;
3035 break;
3036 }
3037 }
3038
3039 TempCCk = rtl8192_QueryBBReg(dev, rCCK0_TxFilter1, bMaskByte2);
3040
3041 for(i=0 ; i<CCKTxBBGainTableLength ; i++)
3042 {
3043 if(TempCCk == priv->cck_txbbgain_table[i].ccktxbb_valuearray[0])
3044 {
3045 priv->CCKPresentAttentuation_20Mdefault =(u8) i;
3046 break;
3047 }
3048 }
3049 priv->CCKPresentAttentuation_40Mdefault = 0;
3050 priv->CCKPresentAttentuation_difference = 0;
3051 priv->CCKPresentAttentuation = priv->CCKPresentAttentuation_20Mdefault;
3052 RT_TRACE(COMP_POWER_TRACKING, "priv->rfa_txpowertrackingindex_initial = %d\n", priv->rfa_txpowertrackingindex);
3053 RT_TRACE(COMP_POWER_TRACKING, "priv->rfa_txpowertrackingindex_real__initial = %d\n", priv->rfa_txpowertrackingindex_real);
3054 RT_TRACE(COMP_POWER_TRACKING, "priv->CCKPresentAttentuation_difference_initial = %d\n", priv->CCKPresentAttentuation_difference);
3055 RT_TRACE(COMP_POWER_TRACKING, "priv->CCKPresentAttentuation_initial = %d\n", priv->CCKPresentAttentuation);
3056 priv->btxpower_tracking = FALSE;//TEMPLY DISABLE
3057 }
3058 }
4803ef77 3059
ecdfa446
GKH
3060 rtl8192_irq_enable(dev);
3061 priv->being_init_adapter = false;
3062 return rtStatus;
3063
3064}
3065
80a4dead 3066static void rtl8192_prepare_beacon(unsigned long arg)
ecdfa446 3067{
80a4dead 3068 struct r8192_priv *priv = (struct r8192_priv*) arg;
ecdfa446
GKH
3069 struct sk_buff *skb;
3070 //unsigned long flags;
3071 cb_desc *tcb_desc;
3072
3073 skb = ieee80211_get_beacon(priv->ieee80211);
3074 tcb_desc = (cb_desc *)(skb->cb + 8);
ecdfa446
GKH
3075 //spin_lock_irqsave(&priv->tx_lock,flags);
3076 /* prepare misc info for the beacon xmit */
3077 tcb_desc->queue_index = BEACON_QUEUE;
bbc9a991 3078 /* IBSS does not support HT yet, use 1M defaultly */
ecdfa446
GKH
3079 tcb_desc->data_rate = 2;
3080 tcb_desc->RATRIndex = 7;
3081 tcb_desc->bTxDisableRateFallBack = 1;
3082 tcb_desc->bTxUseDriverAssingedRate = 1;
3083
3084 skb_push(skb, priv->ieee80211->tx_headroom);
3085 if(skb){
3086 rtl8192_tx(priv->ieee80211->dev,skb);
3087 }
3088 //spin_unlock_irqrestore (&priv->tx_lock, flags);
3089}
3090
ecdfa446 3091
214985a6
MM
3092/*
3093 * configure registers for beacon tx and enables it via
ecdfa446
GKH
3094 * rtl8192_beacon_tx_enable(). rtl8192_beacon_tx_disable() might
3095 * be used to stop beacon transmission
3096 */
559fba5e 3097static void rtl8192_start_beacon(struct net_device *dev)
ecdfa446
GKH
3098{
3099 struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
3100 struct ieee80211_network *net = &priv->ieee80211->current_network;
3101 u16 BcnTimeCfg = 0;
3102 u16 BcnCW = 6;
3103 u16 BcnIFS = 0xf;
3104
3105 DMESG("Enabling beacon TX");
ecdfa446
GKH
3106 rtl8192_irq_disable(dev);
3107 //rtl8192_beacon_tx_enable(dev);
3108
3109 /* ATIM window */
3f9ab1ee 3110 write_nic_word(priv, ATIMWND, 2);
ecdfa446
GKH
3111
3112 /* Beacon interval (in unit of TU) */
3f9ab1ee 3113 write_nic_word(priv, BCN_INTERVAL, net->beacon_interval);
ecdfa446
GKH
3114
3115 /*
3116 * DrvErlyInt (in unit of TU).
3117 * (Time to send interrupt to notify driver to c
3118 * hange beacon content)
3119 * */
3f9ab1ee 3120 write_nic_word(priv, BCN_DRV_EARLY_INT, 10);
ecdfa446
GKH
3121
3122 /*
3123 * BcnDMATIM(in unit of us).
3124 * Indicates the time before TBTT to perform beacon queue DMA
3125 * */
3f9ab1ee 3126 write_nic_word(priv, BCN_DMATIME, 256);
ecdfa446
GKH
3127
3128 /*
3129 * Force beacon frame transmission even after receiving
3130 * beacon frame from other ad hoc STA
3131 * */
3f9ab1ee 3132 write_nic_byte(priv, BCN_ERR_THRESH, 100);
ecdfa446
GKH
3133
3134 /* Set CW and IFS */
3135 BcnTimeCfg |= BcnCW<<BCN_TCFG_CW_SHIFT;
3136 BcnTimeCfg |= BcnIFS<<BCN_TCFG_IFS;
3f9ab1ee 3137 write_nic_word(priv, BCN_TCFG, BcnTimeCfg);
ecdfa446
GKH
3138
3139
3140 /* enable the interrupt for ad-hoc process */
3141 rtl8192_irq_enable(dev);
3142}
ecdfa446 3143
5e1ad18a 3144static bool HalTxCheckStuck8190Pci(struct net_device *dev)
ecdfa446 3145{
ecdfa446 3146 struct r8192_priv *priv = ieee80211_priv(dev);
3f9ab1ee 3147 u16 RegTxCounter = read_nic_word(priv, 0x128);
ecdfa446
GKH
3148 bool bStuck = FALSE;
3149 RT_TRACE(COMP_RESET,"%s():RegTxCounter is %d,TxCounter is %d\n",__FUNCTION__,RegTxCounter,priv->TxCounter);
3150 if(priv->TxCounter==RegTxCounter)
3151 bStuck = TRUE;
3152
3153 priv->TxCounter = RegTxCounter;
3154
3155 return bStuck;
3156}
3157
3158/*
214985a6
MM
3159 * Assumption: RT_TX_SPINLOCK is acquired.
3160 */
5e1ad18a 3161static RESET_TYPE
ecdfa446
GKH
3162TxCheckStuck(struct net_device *dev)
3163{
3164 struct r8192_priv *priv = ieee80211_priv(dev);
ecdfa446
GKH
3165 u8 ResetThreshold = NIC_SEND_HANG_THRESHOLD_POWERSAVE;
3166 bool bCheckFwTxCnt = false;
ecdfa446
GKH
3167
3168 //
3169 // Decide Stuch threshold according to current power save mode
3170 //
ecdfa446
GKH
3171 switch (priv->ieee80211->dot11PowerSaveMode)
3172 {
3173 // The threshold value may required to be adjusted .
3174 case eActive: // Active/Continuous access.
3175 ResetThreshold = NIC_SEND_HANG_THRESHOLD_NORMAL;
3176 break;
3177 case eMaxPs: // Max power save mode.
3178 ResetThreshold = NIC_SEND_HANG_THRESHOLD_POWERSAVE;
3179 break;
3180 case eFastPs: // Fast power save mode.
3181 ResetThreshold = NIC_SEND_HANG_THRESHOLD_POWERSAVE;
3182 break;
3183 }
3184
ecdfa446
GKH
3185 if(bCheckFwTxCnt)
3186 {
3187 if(HalTxCheckStuck8190Pci(dev))
3188 {
3189 RT_TRACE(COMP_RESET, "TxCheckStuck(): Fw indicates no Tx condition! \n");
3190 return RESET_TYPE_SILENT;
3191 }
3192 }
11aacc28 3193
ecdfa446
GKH
3194 return RESET_TYPE_NORESET;
3195}
3196
3197
5e1ad18a 3198static bool HalRxCheckStuck8190Pci(struct net_device *dev)
ecdfa446
GKH
3199{
3200 struct r8192_priv *priv = ieee80211_priv(dev);
3f9ab1ee 3201 u16 RegRxCounter = read_nic_word(priv, 0x130);
ecdfa446 3202 bool bStuck = FALSE;
935ce899 3203
ecdfa446
GKH
3204 RT_TRACE(COMP_RESET,"%s(): RegRxCounter is %d,RxCounter is %d\n",__FUNCTION__,RegRxCounter,priv->RxCounter);
3205 // If rssi is small, we should check rx for long time because of bad rx.
3206 // or maybe it will continuous silent reset every 2 seconds.
935ce899 3207 priv->rx_chk_cnt++;
ecdfa446
GKH
3208 if(priv->undecorated_smoothed_pwdb >= (RateAdaptiveTH_High+5))
3209 {
935ce899 3210 priv->rx_chk_cnt = 0; /* high rssi, check rx stuck right now. */
ecdfa446
GKH
3211 }
3212 else if(priv->undecorated_smoothed_pwdb < (RateAdaptiveTH_High+5) &&
3213 ((priv->CurrentChannelBW!=HT_CHANNEL_WIDTH_20&&priv->undecorated_smoothed_pwdb>=RateAdaptiveTH_Low_40M) ||
3214 (priv->CurrentChannelBW==HT_CHANNEL_WIDTH_20&&priv->undecorated_smoothed_pwdb>=RateAdaptiveTH_Low_20M)) )
3215
3216 {
935ce899 3217 if(priv->rx_chk_cnt < 2)
ecdfa446
GKH
3218 {
3219 return bStuck;
3220 }
3221 else
3222 {
935ce899 3223 priv->rx_chk_cnt = 0;
ecdfa446
GKH
3224 }
3225 }
3226 else if(((priv->CurrentChannelBW!=HT_CHANNEL_WIDTH_20&&priv->undecorated_smoothed_pwdb<RateAdaptiveTH_Low_40M) ||
3227 (priv->CurrentChannelBW==HT_CHANNEL_WIDTH_20&&priv->undecorated_smoothed_pwdb<RateAdaptiveTH_Low_20M)) &&
3228 priv->undecorated_smoothed_pwdb >= VeryLowRSSI)
3229 {
935ce899 3230 if(priv->rx_chk_cnt < 4)
ecdfa446 3231 {
ecdfa446
GKH
3232 return bStuck;
3233 }
3234 else
3235 {
935ce899 3236 priv->rx_chk_cnt = 0;
ecdfa446
GKH
3237 }
3238 }
3239 else
3240 {
935ce899 3241 if(priv->rx_chk_cnt < 8)
ecdfa446 3242 {
ecdfa446
GKH
3243 return bStuck;
3244 }
3245 else
3246 {
935ce899 3247 priv->rx_chk_cnt = 0;
ecdfa446
GKH
3248 }
3249 }
ecdfa446
GKH
3250 if(priv->RxCounter==RegRxCounter)
3251 bStuck = TRUE;
3252
3253 priv->RxCounter = RegRxCounter;
3254
3255 return bStuck;
3256}
3257
5e1ad18a 3258static RESET_TYPE RxCheckStuck(struct net_device *dev)
ecdfa446
GKH
3259{
3260
3261 if(HalRxCheckStuck8190Pci(dev))
3262 {
3263 RT_TRACE(COMP_RESET, "RxStuck Condition\n");
3264 return RESET_TYPE_SILENT;
3265 }
3266
3267 return RESET_TYPE_NORESET;
3268}
3269
5e1ad18a 3270static RESET_TYPE
ecdfa446
GKH
3271rtl819x_ifcheck_resetornot(struct net_device *dev)
3272{
3273 struct r8192_priv *priv = ieee80211_priv(dev);
3274 RESET_TYPE TxResetType = RESET_TYPE_NORESET;
3275 RESET_TYPE RxResetType = RESET_TYPE_NORESET;
3276 RT_RF_POWER_STATE rfState;
3277
3278 rfState = priv->ieee80211->eRFPowerState;
3279
3280 TxResetType = TxCheckStuck(dev);
11aacc28 3281
ecdfa446
GKH
3282 if( rfState != eRfOff &&
3283 /*ADAPTER_TEST_STATUS_FLAG(Adapter, ADAPTER_STATUS_FW_DOWNLOAD_FAILURE)) &&*/
3284 (priv->ieee80211->iw_mode != IW_MODE_ADHOC))
3285 {
3286 // If driver is in the status of firmware download failure , driver skips RF initialization and RF is
3287 // in turned off state. Driver should check whether Rx stuck and do silent reset. And
3288 // if driver is in firmware download failure status, driver should initialize RF in the following
3289 // silent reset procedure Emily, 2008.01.21
3290
3291 // Driver should not check RX stuck in IBSS mode because it is required to
3292 // set Check BSSID in order to send beacon, however, if check BSSID is
3293 // set, STA cannot hear any packet a all. Emily, 2008.04.12
3294 RxResetType = RxCheckStuck(dev);
3295 }
ecdfa446
GKH
3296
3297 RT_TRACE(COMP_RESET,"%s(): TxResetType is %d, RxResetType is %d\n",__FUNCTION__,TxResetType,RxResetType);
3298 if(TxResetType==RESET_TYPE_NORMAL || RxResetType==RESET_TYPE_NORMAL)
3299 return RESET_TYPE_NORMAL;
3300 else if(TxResetType==RESET_TYPE_SILENT || RxResetType==RESET_TYPE_SILENT)
3301 return RESET_TYPE_SILENT;
3302 else
3303 return RESET_TYPE_NORESET;
3304
3305}
3306
3307
5e1ad18a 3308static void CamRestoreAllEntry(struct net_device *dev)
ecdfa446
GKH
3309{
3310 u8 EntryId = 0;
3311 struct r8192_priv *priv = ieee80211_priv(dev);
881a975b 3312 const u8* MacAddr = priv->ieee80211->current_network.bssid;
ecdfa446 3313
881a975b 3314 static const u8 CAM_CONST_ADDR[4][6] = {
ecdfa446
GKH
3315 {0x00, 0x00, 0x00, 0x00, 0x00, 0x00},
3316 {0x00, 0x00, 0x00, 0x00, 0x00, 0x01},
3317 {0x00, 0x00, 0x00, 0x00, 0x00, 0x02},
3318 {0x00, 0x00, 0x00, 0x00, 0x00, 0x03}};
881a975b 3319 static const u8 CAM_CONST_BROAD[] =
ecdfa446
GKH
3320 {0xff, 0xff, 0xff, 0xff, 0xff, 0xff};
3321
3322 RT_TRACE(COMP_SEC, "CamRestoreAllEntry: \n");
3323
3324
3325 if ((priv->ieee80211->pairwise_key_type == KEY_TYPE_WEP40)||
3326 (priv->ieee80211->pairwise_key_type == KEY_TYPE_WEP104))
3327 {
3328
3329 for(EntryId=0; EntryId<4; EntryId++)
3330 {
3331 {
3332 MacAddr = CAM_CONST_ADDR[EntryId];
3333 setKey(dev,
3334 EntryId ,
3335 EntryId,
3336 priv->ieee80211->pairwise_key_type,
3337 MacAddr,
3338 0,
3339 NULL);
3340 }
3341 }
3342
3343 }
3344 else if(priv->ieee80211->pairwise_key_type == KEY_TYPE_TKIP)
3345 {
3346
3347 {
3348 if(priv->ieee80211->iw_mode == IW_MODE_ADHOC)
3349 setKey(dev,
3350 4,
3351 0,
3352 priv->ieee80211->pairwise_key_type,
3353 (u8*)dev->dev_addr,
3354 0,
3355 NULL);
3356 else
3357 setKey(dev,
3358 4,
3359 0,
3360 priv->ieee80211->pairwise_key_type,
3361 MacAddr,
3362 0,
3363 NULL);
3364 }
3365 }
3366 else if(priv->ieee80211->pairwise_key_type == KEY_TYPE_CCMP)
3367 {
3368
3369 {
3370 if(priv->ieee80211->iw_mode == IW_MODE_ADHOC)
3371 setKey(dev,
3372 4,
3373 0,
3374 priv->ieee80211->pairwise_key_type,
3375 (u8*)dev->dev_addr,
3376 0,
3377 NULL);
3378 else
3379 setKey(dev,
3380 4,
3381 0,
3382 priv->ieee80211->pairwise_key_type,
3383 MacAddr,
3384 0,
3385 NULL);
3386 }
3387 }
3388
3389
3390
3391 if(priv->ieee80211->group_key_type == KEY_TYPE_TKIP)
3392 {
3393 MacAddr = CAM_CONST_BROAD;
3394 for(EntryId=1 ; EntryId<4 ; EntryId++)
3395 {
3396 {
3397 setKey(dev,
3398 EntryId,
3399 EntryId,
3400 priv->ieee80211->group_key_type,
3401 MacAddr,
3402 0,
3403 NULL);
3404 }
3405 }
3406 if(priv->ieee80211->iw_mode == IW_MODE_ADHOC)
3407 setKey(dev,
3408 0,
3409 0,
3410 priv->ieee80211->group_key_type,
3411 CAM_CONST_ADDR[0],
3412 0,
3413 NULL);
3414 }
3415 else if(priv->ieee80211->group_key_type == KEY_TYPE_CCMP)
3416 {
3417 MacAddr = CAM_CONST_BROAD;
3418 for(EntryId=1; EntryId<4 ; EntryId++)
3419 {
3420 {
3421 setKey(dev,
3422 EntryId ,
3423 EntryId,
3424 priv->ieee80211->group_key_type,
3425 MacAddr,
3426 0,
3427 NULL);
3428 }
3429 }
3430
3431 if(priv->ieee80211->iw_mode == IW_MODE_ADHOC)
3432 setKey(dev,
3433 0 ,
3434 0,
3435 priv->ieee80211->group_key_type,
3436 CAM_CONST_ADDR[0],
3437 0,
3438 NULL);
3439 }
3440}
3441
ecdfa446
GKH
3442/*
3443 * This function is used to fix Tx/Rx stop bug temporarily.
3444 * This function will do "system reset" to NIC when Tx or Rx is stuck.
3445 * The method checking Tx/Rx stuck of this function is supported by FW,
3446 * which reports Tx and Rx counter to register 0x128 and 0x130.
214985a6 3447 */
5e1ad18a 3448static void rtl819x_ifsilentreset(struct net_device *dev)
ecdfa446
GKH
3449{
3450 struct r8192_priv *priv = ieee80211_priv(dev);
3451 u8 reset_times = 0;
3452 int reset_status = 0;
3453 struct ieee80211_device *ieee = priv->ieee80211;
3454
3455
65a43784 3456 return;
3457
ecdfa446
GKH
3458 // 2007.07.20. If we need to check CCK stop, please uncomment this line.
3459 //bStuck = Adapter->HalFunc.CheckHWStopHandler(Adapter);
3460
3461 if(priv->ResetProgress==RESET_TYPE_NORESET)
3462 {
3463RESET_START:
65a43784 3464#ifdef ENABLE_LPS
3465 //LZM for PS-Poll AID issue. 090429
3466 if(priv->ieee80211->state == IEEE80211_LINKED)
3467 LeisurePSLeave(dev);
3468#endif
ecdfa446
GKH
3469
3470 RT_TRACE(COMP_RESET,"=========>Reset progress!! \n");
3471
3472 // Set the variable for reset.
3473 priv->ResetProgress = RESET_TYPE_SILENT;
3474// rtl8192_close(dev);
11aacc28 3475
ecdfa446
GKH
3476 down(&priv->wx_sem);
3477 if(priv->up == 0)
3478 {
3479 RT_TRACE(COMP_ERR,"%s():the driver is not up! return\n",__FUNCTION__);
3480 up(&priv->wx_sem);
3481 return ;
3482 }
3483 priv->up = 0;
3484 RT_TRACE(COMP_RESET,"%s():======>start to down the driver\n",__FUNCTION__);
3485 if(!netif_queue_stopped(dev))
3486 netif_stop_queue(dev);
3487
3488 dm_backup_dynamic_mechanism_state(dev);
3489
3490 rtl8192_irq_disable(dev);
3491 rtl8192_cancel_deferred_work(priv);
3492 deinit_hal_dm(dev);
3493 del_timer_sync(&priv->watch_dog_timer);
3494 ieee->sync_scan_hurryup = 1;
3495 if(ieee->state == IEEE80211_LINKED)
3496 {
3497 down(&ieee->wx_sem);
3498 printk("ieee->state is IEEE80211_LINKED\n");
3499 ieee80211_stop_send_beacons(priv->ieee80211);
3500 del_timer_sync(&ieee->associate_timer);
ecdfa446 3501 cancel_delayed_work(&ieee->associate_retry_wq);
ecdfa446 3502 ieee80211_stop_scan(ieee);
ecdfa446
GKH
3503 up(&ieee->wx_sem);
3504 }
3505 else{
3506 printk("ieee->state is NOT LINKED\n");
65a43784 3507 ieee80211_softmac_stop_protocol(priv->ieee80211,true);
ecdfa446 3508 }
65a43784 3509 rtl8192_halt_adapter(dev, true);
ecdfa446
GKH
3510 up(&priv->wx_sem);
3511 RT_TRACE(COMP_RESET,"%s():<==========down process is finished\n",__FUNCTION__);
3512 RT_TRACE(COMP_RESET,"%s():===========>start to up the driver\n",__FUNCTION__);
3513 reset_status = _rtl8192_up(dev);
3514
3515 RT_TRACE(COMP_RESET,"%s():<===========up process is finished\n",__FUNCTION__);
3516 if(reset_status == -1)
3517 {
3518 if(reset_times < 3)
3519 {
3520 reset_times++;
3521 goto RESET_START;
3522 }
3523 else
3524 {
3525 RT_TRACE(COMP_ERR," ERR!!! %s(): Reset Failed!!\n",__FUNCTION__);
3526 }
3527 }
ecdfa446 3528 ieee->is_silent_reset = 1;
ecdfa446 3529 EnableHWSecurityConfig8192(dev);
ecdfa446
GKH
3530 if(ieee->state == IEEE80211_LINKED && ieee->iw_mode == IW_MODE_INFRA)
3531 {
3532 ieee->set_chan(ieee->dev, ieee->current_network.channel);
3533
ecdfa446 3534 queue_work(ieee->wq, &ieee->associate_complete_wq);
ecdfa446
GKH
3535
3536 }
3537 else if(ieee->state == IEEE80211_LINKED && ieee->iw_mode == IW_MODE_ADHOC)
3538 {
3539 ieee->set_chan(ieee->dev, ieee->current_network.channel);
3540 ieee->link_change(ieee->dev);
3541
3542 // notify_wx_assoc_event(ieee);
3543
3544 ieee80211_start_send_beacons(ieee);
3545
3546 if (ieee->data_hard_resume)
3547 ieee->data_hard_resume(ieee->dev);
3548 netif_carrier_on(ieee->dev);
3549 }
ecdfa446
GKH
3550
3551 CamRestoreAllEntry(dev);
3552
3553 // Restore the previous setting for all dynamic mechanism
3554 dm_restore_dynamic_mechanism_state(dev);
3555
3556 priv->ResetProgress = RESET_TYPE_NORESET;
3557 priv->reset_count++;
3558
3559 priv->bForcedSilentReset =false;
3560 priv->bResetInProgress = false;
3561
3562 // For test --> force write UFWP.
3f9ab1ee 3563 write_nic_byte(priv, UFWP, 1);
ecdfa446 3564 RT_TRACE(COMP_RESET, "Reset finished!! ====>[%d]\n", priv->reset_count);
ecdfa446
GKH
3565 }
3566}
3567
3568#ifdef ENABLE_IPS
3569void InactivePsWorkItemCallback(struct net_device *dev)
3570{
3571 struct r8192_priv *priv = ieee80211_priv(dev);
3572 PRT_POWER_SAVE_CONTROL pPSC = (PRT_POWER_SAVE_CONTROL)(&(priv->ieee80211->PowerSaveControl));
ecdfa446
GKH
3573
3574 RT_TRACE(COMP_POWER, "InactivePsWorkItemCallback() ---------> \n");
3575 //
3576 // This flag "bSwRfProcessing", indicates the status of IPS procedure, should be set if the IPS workitem
3577 // is really scheduled.
3578 // The old code, sets this flag before scheduling the IPS workitem and however, at the same time the
3579 // previous IPS workitem did not end yet, fails to schedule the current workitem. Thus, bSwRfProcessing
3580 // blocks the IPS procedure of switching RF.
3581 // By Bruce, 2007-12-25.
3582 //
3583 pPSC->bSwRfProcessing = TRUE;
3584
207b58fb 3585 RT_TRACE(COMP_RF, "InactivePsWorkItemCallback(): Set RF to %s.\n",
ecdfa446
GKH
3586 pPSC->eInactivePowerState == eRfOff?"OFF":"ON");
3587
3588
3589 MgntActSet_RF_State(dev, pPSC->eInactivePowerState, RF_CHANGE_BY_IPS);
3590
3591 //
3592 // To solve CAM values miss in RF OFF, rewrite CAM values after RF ON. By Bruce, 2007-09-20.
3593 //
ecdfa446
GKH
3594 pPSC->bSwRfProcessing = FALSE;
3595 RT_TRACE(COMP_POWER, "InactivePsWorkItemCallback() <--------- \n");
3596}
3597
65a43784 3598#ifdef ENABLE_LPS
214985a6 3599/* Change current and default preamble mode. */
65a43784 3600bool MgntActSet_802_11_PowerSaveMode(struct net_device *dev, u8 rtPsMode)
3601{
3602 struct r8192_priv *priv = ieee80211_priv(dev);
65a43784 3603
3604 // Currently, we do not change power save mode on IBSS mode.
3605 if(priv->ieee80211->iw_mode == IW_MODE_ADHOC)
3606 {
3607 return false;
3608 }
3609
3610 //
3611 // <RJ_NOTE> If we make HW to fill up the PwrMgt bit for us,
3612 // some AP will not response to our mgnt frames with PwrMgt bit set,
3613 // e.g. cannot associate the AP.
3614 // So I commented out it. 2005.02.16, by rcnjko.
3615 //
3616// // Change device's power save mode.
3617// Adapter->HalFunc.SetPSModeHandler( Adapter, rtPsMode );
3618
3619 // Update power save mode configured.
3620 //RT_TRACE(COMP_LPS,"%s(): set ieee->ps = %x\n",__FUNCTION__,rtPsMode);
3621 if(!priv->ps_force) {
3622 priv->ieee80211->ps = rtPsMode;
3623 }
3624
3625 // Awake immediately
3626 if(priv->ieee80211->sta_sleep != 0 && rtPsMode == IEEE80211_PS_DISABLED)
3627 {
3628 unsigned long flags;
3629
3630 //PlatformSetTimer(Adapter, &(pMgntInfo->AwakeTimer), 0);
3631 // Notify the AP we awke.
3632 rtl8192_hw_wakeup(dev);
3633 priv->ieee80211->sta_sleep = 0;
3634
3635 spin_lock_irqsave(&(priv->ieee80211->mgmt_tx_lock), flags);
3636 printk("LPS leave: notify AP we are awaked ++++++++++ SendNullFunctionData\n");
3637 ieee80211_sta_ps_send_null_frame(priv->ieee80211, 0);
3638 spin_unlock_irqrestore(&(priv->ieee80211->mgmt_tx_lock), flags);
3639 }
3640
3641 return true;
3642}
3643
214985a6 3644/* Enter the leisure power save mode. */
65a43784 3645void LeisurePSEnter(struct net_device *dev)
3646{
3647 struct r8192_priv *priv = ieee80211_priv(dev);
3648 PRT_POWER_SAVE_CONTROL pPSC = (PRT_POWER_SAVE_CONTROL)(&(priv->ieee80211->PowerSaveControl));
3649
3650 //RT_TRACE(COMP_PS, "LeisurePSEnter()...\n");
3651 //RT_TRACE(COMP_PS, "pPSC->bLeisurePs = %d, ieee->ps = %d,pPSC->LpsIdleCount is %d,RT_CHECK_FOR_HANG_PERIOD is %d\n",
3652 // pPSC->bLeisurePs, priv->ieee80211->ps,pPSC->LpsIdleCount,RT_CHECK_FOR_HANG_PERIOD);
3653
3654 if(!((priv->ieee80211->iw_mode == IW_MODE_INFRA) &&
3655 (priv->ieee80211->state == IEEE80211_LINKED)) ||
3656 (priv->ieee80211->iw_mode == IW_MODE_ADHOC) ||
3657 (priv->ieee80211->iw_mode == IW_MODE_MASTER))
3658 return;
3659
3660 if (pPSC->bLeisurePs)
3661 {
3662 // Idle for a while if we connect to AP a while ago.
3663 if(pPSC->LpsIdleCount >= RT_CHECK_FOR_HANG_PERIOD) // 4 Sec
3664 {
3665
3666 if(priv->ieee80211->ps == IEEE80211_PS_DISABLED)
3667 {
3668
3669 //RT_TRACE(COMP_LPS, "LeisurePSEnter(): Enter 802.11 power save mode...\n");
3670 MgntActSet_802_11_PowerSaveMode(dev, IEEE80211_PS_MBCAST|IEEE80211_PS_UNICAST);
3671
3672 }
3673 }
3674 else
3675 pPSC->LpsIdleCount++;
3676 }
3677}
3678
3679
214985a6 3680/* Leave leisure power save mode. */
65a43784 3681void LeisurePSLeave(struct net_device *dev)
3682{
3683 struct r8192_priv *priv = ieee80211_priv(dev);
3684 PRT_POWER_SAVE_CONTROL pPSC = (PRT_POWER_SAVE_CONTROL)(&(priv->ieee80211->PowerSaveControl));
3685
65a43784 3686 if (pPSC->bLeisurePs)
3687 {
3688 if(priv->ieee80211->ps != IEEE80211_PS_DISABLED)
3689 {
3690 // move to lps_wakecomplete()
3691 //RT_TRACE(COMP_LPS, "LeisurePSLeave(): Busy Traffic , Leave 802.11 power save..\n");
3692 MgntActSet_802_11_PowerSaveMode(dev, IEEE80211_PS_DISABLED);
3693
3694 }
3695 }
3696}
3697#endif
3698
3699
214985a6 3700/* Enter the inactive power save mode. RF will be off */
ecdfa446
GKH
3701void
3702IPSEnter(struct net_device *dev)
3703{
3704 struct r8192_priv *priv = ieee80211_priv(dev);
3705 PRT_POWER_SAVE_CONTROL pPSC = (PRT_POWER_SAVE_CONTROL)(&(priv->ieee80211->PowerSaveControl));
3706 RT_RF_POWER_STATE rtState;
3707
3708 if (pPSC->bInactivePs)
3709 {
3710 rtState = priv->ieee80211->eRFPowerState;
3711 //
3712 // Added by Bruce, 2007-12-25.
3713 // Do not enter IPS in the following conditions:
3714 // (1) RF is already OFF or Sleep
3715 // (2) bSwRfProcessing (indicates the IPS is still under going)
3716 // (3) Connectted (only disconnected can trigger IPS)
3717 // (4) IBSS (send Beacon)
3718 // (5) AP mode (send Beacon)
3719 //
3720 if (rtState == eRfOn && !pPSC->bSwRfProcessing
3721 && (priv->ieee80211->state != IEEE80211_LINKED) )
3722 {
3723 RT_TRACE(COMP_RF,"IPSEnter(): Turn off RF.\n");
3724 pPSC->eInactivePowerState = eRfOff;
3725// queue_work(priv->priv_wq,&(pPSC->InactivePsWorkItem));
3726 InactivePsWorkItemCallback(dev);
3727 }
3728 }
3729}
3730
3731//
3732// Description:
3733// Leave the inactive power save mode, RF will be on.
3734// 2007.08.17, by shien chang.
3735//
3736void
3737IPSLeave(struct net_device *dev)
3738{
3739 struct r8192_priv *priv = ieee80211_priv(dev);
3740 PRT_POWER_SAVE_CONTROL pPSC = (PRT_POWER_SAVE_CONTROL)(&(priv->ieee80211->PowerSaveControl));
3741 RT_RF_POWER_STATE rtState;
3742
3743 if (pPSC->bInactivePs)
3744 {
3745 rtState = priv->ieee80211->eRFPowerState;
3746 if (rtState != eRfOn && !pPSC->bSwRfProcessing && priv->ieee80211->RfOffReason <= RF_CHANGE_BY_IPS)
3747 {
3748 RT_TRACE(COMP_POWER, "IPSLeave(): Turn on RF.\n");
3749 pPSC->eInactivePowerState = eRfOn;
3750// queue_work(priv->priv_wq,&(pPSC->InactivePsWorkItem));
3751 InactivePsWorkItemCallback(dev);
3752 }
3753 }
3754}
65a43784 3755
80a4dead 3756void IPSLeave_wq(struct work_struct *work)
65a43784 3757{
80a4dead 3758 struct ieee80211_device *ieee = container_of(work, struct ieee80211_device, ips_leave_wq);
65a43784 3759 struct net_device *dev = ieee->dev;
3760
3761 struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
3762 down(&priv->ieee80211->ips_sem);
3763 IPSLeave(dev);
3764 up(&priv->ieee80211->ips_sem);
3765}
3766
3767void ieee80211_ips_leave_wq(struct net_device *dev)
3768{
3769 struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
3770 RT_RF_POWER_STATE rtState;
3771 rtState = priv->ieee80211->eRFPowerState;
3772
3773 if(priv->ieee80211->PowerSaveControl.bInactivePs){
3774 if(rtState == eRfOff){
3775 if(priv->ieee80211->RfOffReason > RF_CHANGE_BY_IPS)
3776 {
3777 RT_TRACE(COMP_ERR, "%s(): RF is OFF.\n",__FUNCTION__);
3778 return;
3779 }
3780 else{
3781 printk("=========>%s(): IPSLeave\n",__FUNCTION__);
3782 queue_work(priv->ieee80211->wq,&priv->ieee80211->ips_leave_wq);
3783 }
3784 }
3785 }
3786}
3787//added by amy 090331 end
3788void ieee80211_ips_leave(struct net_device *dev)
3789{
3790 struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
3791 down(&priv->ieee80211->ips_sem);
3792 IPSLeave(dev);
3793 up(&priv->ieee80211->ips_sem);
3794}
ecdfa446 3795#endif
ecdfa446 3796
5e1ad18a 3797static void rtl819x_update_rxcounts(
ecdfa446
GKH
3798 struct r8192_priv *priv,
3799 u32* TotalRxBcnNum,
3800 u32* TotalRxDataNum
3801)
3802{
3803 u16 SlotIndex;
3804 u8 i;
3805
3806 *TotalRxBcnNum = 0;
3807 *TotalRxDataNum = 0;
3808
3809 SlotIndex = (priv->ieee80211->LinkDetectInfo.SlotIndex++)%(priv->ieee80211->LinkDetectInfo.SlotNum);
3810 priv->ieee80211->LinkDetectInfo.RxBcnNum[SlotIndex] = priv->ieee80211->LinkDetectInfo.NumRecvBcnInPeriod;
3811 priv->ieee80211->LinkDetectInfo.RxDataNum[SlotIndex] = priv->ieee80211->LinkDetectInfo.NumRecvDataInPeriod;
3812 for( i=0; i<priv->ieee80211->LinkDetectInfo.SlotNum; i++ ){
3813 *TotalRxBcnNum += priv->ieee80211->LinkDetectInfo.RxBcnNum[i];
3814 *TotalRxDataNum += priv->ieee80211->LinkDetectInfo.RxDataNum[i];
3815 }
3816}
3817
3818
559fba5e 3819static void rtl819x_watchdog_wqcallback(struct work_struct *work)
ecdfa446
GKH
3820{
3821 struct delayed_work *dwork = container_of(work,struct delayed_work,work);
3822 struct r8192_priv *priv = container_of(dwork,struct r8192_priv,watch_dog_wq);
3823 struct net_device *dev = priv->ieee80211->dev;
ecdfa446
GKH
3824 struct ieee80211_device* ieee = priv->ieee80211;
3825 RESET_TYPE ResetType = RESET_TYPE_NORESET;
ecdfa446
GKH
3826 unsigned long flags;
3827 bool bBusyTraffic = false;
65a43784 3828 bool bEnterPS = false;
3829
f500e256 3830 if ((!priv->up) || priv->bHwRadioOff)
65a43784 3831 return;
3832
ecdfa446
GKH
3833 if(!priv->up)
3834 return;
3835 hal_dm_watchdog(dev);
3836#ifdef ENABLE_IPS
ecdfa446 3837 if(ieee->actscanning == false){
207b58fb
MM
3838 if((ieee->iw_mode == IW_MODE_INFRA) && (ieee->state == IEEE80211_NOLINK) &&
3839 (ieee->eRFPowerState == eRfOn)&&!ieee->is_set_key &&
65a43784 3840 (!ieee->proto_stoppping) && !ieee->wx_set_enc){
ecdfa446 3841 if(ieee->PowerSaveControl.ReturnPoint == IPS_CALLBACK_NONE){
ecdfa446
GKH
3842 IPSEnter(dev);
3843 //ieee80211_stop_scan(priv->ieee80211);
3844 }
3845 }
3846 }
3847#endif
3848 {//to get busy traffic condition
3849 if(ieee->state == IEEE80211_LINKED)
3850 {
65a43784 3851 if( ieee->LinkDetectInfo.NumRxOkInPeriod> 100 ||
3852 ieee->LinkDetectInfo.NumTxOkInPeriod> 100 ) {
ecdfa446
GKH
3853 bBusyTraffic = true;
3854 }
3855
65a43784 3856#ifdef ENABLE_LPS
3857 //added by amy for Leisure PS
3858 if( ((ieee->LinkDetectInfo.NumRxUnicastOkInPeriod + ieee->LinkDetectInfo.NumTxOkInPeriod) > 8 ) ||
3859 (ieee->LinkDetectInfo.NumRxUnicastOkInPeriod > 2) )
3860 {
65a43784 3861 bEnterPS= false;
3862 }
3863 else
3864 {
3865 bEnterPS= true;
3866 }
3867
65a43784 3868 // LeisurePS only work in infra mode.
3869 if(bEnterPS)
3870 {
3871 LeisurePSEnter(dev);
3872 }
3873 else
3874 {
3875 LeisurePSLeave(dev);
3876 }
3877#endif
3878
3879 }
3880 else
3881 {
3882#ifdef ENABLE_LPS
3883 //RT_TRACE(COMP_LPS,"====>no link LPS leave\n");
3884 LeisurePSLeave(dev);
3885#endif
ecdfa446 3886 }
65a43784 3887
ecdfa446
GKH
3888 ieee->LinkDetectInfo.NumRxOkInPeriod = 0;
3889 ieee->LinkDetectInfo.NumTxOkInPeriod = 0;
65a43784 3890 ieee->LinkDetectInfo.NumRxUnicastOkInPeriod = 0;
ecdfa446
GKH
3891 ieee->LinkDetectInfo.bBusyTraffic = bBusyTraffic;
3892 }
3893
3894
3895 //added by amy for AP roaming
3896 if (1)
3897 {
3898 if(ieee->state == IEEE80211_LINKED && ieee->iw_mode == IW_MODE_INFRA)
3899 {
3900 u32 TotalRxBcnNum = 0;
3901 u32 TotalRxDataNum = 0;
3902
3903 rtl819x_update_rxcounts(priv, &TotalRxBcnNum, &TotalRxDataNum);
3904 if((TotalRxBcnNum+TotalRxDataNum) == 0)
3905 {
3906 if( ieee->eRFPowerState == eRfOff)
3907 RT_TRACE(COMP_ERR,"========>%s()\n",__FUNCTION__);
3908 printk("===>%s(): AP is power off,connect another one\n",__FUNCTION__);
65a43784 3909 // Dot11d_Reset(dev);
ecdfa446
GKH
3910 ieee->state = IEEE80211_ASSOCIATING;
3911 notify_wx_assoc_event(priv->ieee80211);
65a43784 3912 RemovePeerTS(priv->ieee80211,priv->ieee80211->current_network.bssid);
ecdfa446
GKH
3913 ieee->is_roaming = true;
3914 ieee->is_set_key = false;
65a43784 3915 ieee->link_change(dev);
3916 queue_work(ieee->wq, &ieee->associate_procedure_wq);
ecdfa446
GKH
3917 }
3918 }
3919 ieee->LinkDetectInfo.NumRecvBcnInPeriod=0;
3920 ieee->LinkDetectInfo.NumRecvDataInPeriod=0;
3921
3922 }
ecdfa446
GKH
3923 //check if reset the driver
3924 spin_lock_irqsave(&priv->tx_lock,flags);
d5fdaa3a
MM
3925 if (priv->watchdog_check_reset_cnt++ >= 3 && !ieee->is_roaming &&
3926 priv->watchdog_last_time != 1)
ecdfa446
GKH
3927 {
3928 ResetType = rtl819x_ifcheck_resetornot(dev);
d5fdaa3a 3929 priv->watchdog_check_reset_cnt = 3;
ecdfa446
GKH
3930 }
3931 spin_unlock_irqrestore(&priv->tx_lock,flags);
3932 if(!priv->bDisableNormalResetCheck && ResetType == RESET_TYPE_NORMAL)
3933 {
3934 priv->ResetProgress = RESET_TYPE_NORMAL;
3935 RT_TRACE(COMP_RESET,"%s(): NOMAL RESET\n",__FUNCTION__);
3936 return;
3937 }
3938 /* disable silent reset temply 2008.9.11*/
11aacc28 3939
ecdfa446
GKH
3940 if( ((priv->force_reset) || (!priv->bDisableNormalResetCheck && ResetType==RESET_TYPE_SILENT))) // This is control by OID set in Pomelo
3941 {
d5fdaa3a 3942 priv->watchdog_last_time = 1;
ecdfa446
GKH
3943 rtl819x_ifsilentreset(dev);
3944 }
3945 else
d5fdaa3a 3946 priv->watchdog_last_time = 0;
11aacc28 3947
ecdfa446
GKH
3948 priv->force_reset = false;
3949 priv->bForcedSilentReset = false;
3950 priv->bResetInProgress = false;
3951 RT_TRACE(COMP_TRACE, " <==RtUsbCheckForHangWorkItemCallback()\n");
3952
3953}
3954
3955void watch_dog_timer_callback(unsigned long data)
3956{
3957 struct r8192_priv *priv = ieee80211_priv((struct net_device *) data);
ecdfa446 3958 queue_delayed_work(priv->priv_wq,&priv->watch_dog_wq,0);
ecdfa446
GKH
3959 mod_timer(&priv->watch_dog_timer, jiffies + MSECS(IEEE80211_WATCH_DOG_TIME));
3960
3961}
5b3b1a7b
MM
3962
3963static int _rtl8192_up(struct net_device *dev)
ecdfa446
GKH
3964{
3965 struct r8192_priv *priv = ieee80211_priv(dev);
3966 //int i;
3967 RT_STATUS init_status = RT_STATUS_SUCCESS;
3968 priv->up=1;
3969 priv->ieee80211->ieee_up=1;
65a43784 3970 priv->bdisable_nic = false; //YJ,add,091111
ecdfa446
GKH
3971 RT_TRACE(COMP_INIT, "Bringing up iface");
3972
3973 init_status = rtl8192_adapter_start(dev);
3974 if(init_status != RT_STATUS_SUCCESS)
3975 {
3976 RT_TRACE(COMP_ERR,"ERR!!! %s(): initialization is failed!\n",__FUNCTION__);
3977 return -1;
3978 }
3979 RT_TRACE(COMP_INIT, "start adapter finished\n");
4803ef77 3980
ecdfa446
GKH
3981 if(priv->ieee80211->eRFPowerState!=eRfOn)
3982 MgntActSet_RF_State(dev, eRfOn, priv->ieee80211->RfOffReason);
4803ef77 3983
ecdfa446
GKH
3984 if(priv->ieee80211->state != IEEE80211_LINKED)
3985 ieee80211_softmac_start_protocol(priv->ieee80211);
3986 ieee80211_reset_queue(priv->ieee80211);
3987 watch_dog_timer_callback((unsigned long) dev);
3988 if(!netif_queue_stopped(dev))
3989 netif_start_queue(dev);
3990 else
3991 netif_wake_queue(dev);
3992
3993 return 0;
3994}
3995
3996
5e1ad18a 3997static int rtl8192_open(struct net_device *dev)
ecdfa446
GKH
3998{
3999 struct r8192_priv *priv = ieee80211_priv(dev);
4000 int ret;
4001
4002 down(&priv->wx_sem);
4003 ret = rtl8192_up(dev);
4004 up(&priv->wx_sem);
4005 return ret;
4006
4007}
4008
4009
4010int rtl8192_up(struct net_device *dev)
4011{
4012 struct r8192_priv *priv = ieee80211_priv(dev);
4013
4014 if (priv->up == 1) return -1;
4015
4016 return _rtl8192_up(dev);
4017}
4018
4019
5e1ad18a 4020static int rtl8192_close(struct net_device *dev)
ecdfa446
GKH
4021{
4022 struct r8192_priv *priv = ieee80211_priv(dev);
4023 int ret;
4024
4025 down(&priv->wx_sem);
4026
4027 ret = rtl8192_down(dev);
4028
4029 up(&priv->wx_sem);
4030
4031 return ret;
4032
4033}
4034
4035int rtl8192_down(struct net_device *dev)
4036{
4037 struct r8192_priv *priv = ieee80211_priv(dev);
16d74da0 4038
ecdfa446
GKH
4039 if (priv->up == 0) return -1;
4040
65a43784 4041#ifdef ENABLE_LPS
4042 //LZM for PS-Poll AID issue. 090429
4043 if(priv->ieee80211->state == IEEE80211_LINKED)
4044 LeisurePSLeave(dev);
4045#endif
4046
ecdfa446
GKH
4047 priv->up=0;
4048 priv->ieee80211->ieee_up = 0;
4049 RT_TRACE(COMP_DOWN, "==========>%s()\n", __FUNCTION__);
4050/* FIXME */
4051 if (!netif_queue_stopped(dev))
4052 netif_stop_queue(dev);
4053
4054 rtl8192_irq_disable(dev);
ecdfa446
GKH
4055 rtl8192_cancel_deferred_work(priv);
4056 deinit_hal_dm(dev);
4057 del_timer_sync(&priv->watch_dog_timer);
4058
65a43784 4059 ieee80211_softmac_stop_protocol(priv->ieee80211,true);
4060
4061 rtl8192_halt_adapter(dev,false);
ecdfa446
GKH
4062 memset(&priv->ieee80211->current_network, 0 , offsetof(struct ieee80211_network, list));
4063
4064 RT_TRACE(COMP_DOWN, "<==========%s()\n", __FUNCTION__);
4065
16d74da0 4066 return 0;
ecdfa446
GKH
4067}
4068
4069
4070void rtl8192_commit(struct net_device *dev)
4071{
4072 struct r8192_priv *priv = ieee80211_priv(dev);
4073
4074 if (priv->up == 0) return ;
4075
4076
65a43784 4077 ieee80211_softmac_stop_protocol(priv->ieee80211,true);
ecdfa446
GKH
4078
4079 rtl8192_irq_disable(dev);
65a43784 4080 rtl8192_halt_adapter(dev,true);
ecdfa446
GKH
4081 _rtl8192_up(dev);
4082}
4083
5b3b1a7b 4084static void rtl8192_restart(struct work_struct *work)
ecdfa446
GKH
4085{
4086 struct r8192_priv *priv = container_of(work, struct r8192_priv, reset_wq);
4087 struct net_device *dev = priv->ieee80211->dev;
ecdfa446
GKH
4088
4089 down(&priv->wx_sem);
4090
4091 rtl8192_commit(dev);
4092
4093 up(&priv->wx_sem);
4094}
4095
4096static void r8192_set_multicast(struct net_device *dev)
4097{
4098 struct r8192_priv *priv = ieee80211_priv(dev);
ecdfa446 4099
109ded2b 4100 priv->promisc = (dev->flags & IFF_PROMISC) ? 1 : 0;
ecdfa446
GKH
4101}
4102
4103
5e1ad18a 4104static int r8192_set_mac_adr(struct net_device *dev, void *mac)
ecdfa446
GKH
4105{
4106 struct r8192_priv *priv = ieee80211_priv(dev);
4107 struct sockaddr *addr = mac;
4108
4109 down(&priv->wx_sem);
4110
4111 memcpy(dev->dev_addr, addr->sa_data, ETH_ALEN);
4112
ecdfa446 4113 schedule_work(&priv->reset_wq);
ecdfa446
GKH
4114 up(&priv->wx_sem);
4115
4116 return 0;
4117}
4118
4119/* based on ipw2200 driver */
5e1ad18a 4120static int rtl8192_ioctl(struct net_device *dev, struct ifreq *rq, int cmd)
ecdfa446
GKH
4121{
4122 struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
4123 struct iwreq *wrq = (struct iwreq *)rq;
4124 int ret=-1;
4125 struct ieee80211_device *ieee = priv->ieee80211;
4126 u32 key[4];
4127 u8 broadcast_addr[6] = {0xff,0xff,0xff,0xff,0xff,0xff};
4128 struct iw_point *p = &wrq->u.data;
4129 struct ieee_param *ipw = NULL;//(struct ieee_param *)wrq->u.data.pointer;
4130
4131 down(&priv->wx_sem);
4132
4133
4134 if (p->length < sizeof(struct ieee_param) || !p->pointer){
4135 ret = -EINVAL;
4136 goto out;
4137 }
4138
32414878 4139 ipw = kmalloc(p->length, GFP_KERNEL);
ecdfa446
GKH
4140 if (ipw == NULL){
4141 ret = -ENOMEM;
4142 goto out;
4143 }
4144 if (copy_from_user(ipw, p->pointer, p->length)) {
4145 kfree(ipw);
4146 ret = -EFAULT;
4147 goto out;
4148 }
4149
4150 switch (cmd) {
4151 case RTL_IOCTL_WPA_SUPPLICANT:
4152 //parse here for HW security
4153 if (ipw->cmd == IEEE_CMD_SET_ENCRYPTION)
4154 {
4155 if (ipw->u.crypt.set_tx)
4156 {
4157 if (strcmp(ipw->u.crypt.alg, "CCMP") == 0)
4158 ieee->pairwise_key_type = KEY_TYPE_CCMP;
4159 else if (strcmp(ipw->u.crypt.alg, "TKIP") == 0)
4160 ieee->pairwise_key_type = KEY_TYPE_TKIP;
4161 else if (strcmp(ipw->u.crypt.alg, "WEP") == 0)
4162 {
4163 if (ipw->u.crypt.key_len == 13)
4164 ieee->pairwise_key_type = KEY_TYPE_WEP104;
4165 else if (ipw->u.crypt.key_len == 5)
4166 ieee->pairwise_key_type = KEY_TYPE_WEP40;
4167 }
4168 else
4169 ieee->pairwise_key_type = KEY_TYPE_NA;
4170
4171 if (ieee->pairwise_key_type)
4172 {
4173 memcpy((u8*)key, ipw->u.crypt.key, 16);
4174 EnableHWSecurityConfig8192(dev);
4175 //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!
4176 //added by WB.
4177 setKey(dev, 4, ipw->u.crypt.idx, ieee->pairwise_key_type, (u8*)ieee->ap_mac_addr, 0, key);
4178 if (ieee->auth_mode != 2) //LEAP WEP will never set this.
4179 setKey(dev, ipw->u.crypt.idx, ipw->u.crypt.idx, ieee->pairwise_key_type, (u8*)ieee->ap_mac_addr, 0, key);
4180 }
4181 if ((ieee->pairwise_key_type == KEY_TYPE_CCMP) && ieee->pHTInfo->bCurrentHTSupport){
3f9ab1ee 4182 write_nic_byte(priv, 0x173, 1); //fix aes bug
ecdfa446
GKH
4183 }
4184
4185 }
4186 else //if (ipw->u.crypt.idx) //group key use idx > 0
4187 {
4188 memcpy((u8*)key, ipw->u.crypt.key, 16);
4189 if (strcmp(ipw->u.crypt.alg, "CCMP") == 0)
4190 ieee->group_key_type= KEY_TYPE_CCMP;
4191 else if (strcmp(ipw->u.crypt.alg, "TKIP") == 0)
4192 ieee->group_key_type = KEY_TYPE_TKIP;
4193 else if (strcmp(ipw->u.crypt.alg, "WEP") == 0)
4194 {
4195 if (ipw->u.crypt.key_len == 13)
4196 ieee->group_key_type = KEY_TYPE_WEP104;
4197 else if (ipw->u.crypt.key_len == 5)
4198 ieee->group_key_type = KEY_TYPE_WEP40;
4199 }
4200 else
4201 ieee->group_key_type = KEY_TYPE_NA;
4202
4203 if (ieee->group_key_type)
4204 {
4205 setKey( dev,
4206 ipw->u.crypt.idx,
4207 ipw->u.crypt.idx, //KeyIndex
4208 ieee->group_key_type, //KeyType
4209 broadcast_addr, //MacAddr
4210 0, //DefaultKey
4211 key); //KeyContent
4212 }
4213 }
4214 }
ecdfa446
GKH
4215 ret = ieee80211_wpa_supplicant_ioctl(priv->ieee80211, &wrq->u.data);
4216 break;
4217
4218 default:
4219 ret = -EOPNOTSUPP;
4220 break;
4221 }
4222
4223 kfree(ipw);
4224out:
4225 up(&priv->wx_sem);
4226
4227 return ret;
4228}
4229
5e1ad18a 4230static u8 HwRateToMRate90(bool bIsHT, u8 rate)
ecdfa446
GKH
4231{
4232 u8 ret_rate = 0x02;
4233
4234 if(!bIsHT) {
4235 switch(rate) {
4236 case DESC90_RATE1M: ret_rate = MGN_1M; break;
4237 case DESC90_RATE2M: ret_rate = MGN_2M; break;
4238 case DESC90_RATE5_5M: ret_rate = MGN_5_5M; break;
4239 case DESC90_RATE11M: ret_rate = MGN_11M; break;
4240 case DESC90_RATE6M: ret_rate = MGN_6M; break;
4241 case DESC90_RATE9M: ret_rate = MGN_9M; break;
4242 case DESC90_RATE12M: ret_rate = MGN_12M; break;
4243 case DESC90_RATE18M: ret_rate = MGN_18M; break;
4244 case DESC90_RATE24M: ret_rate = MGN_24M; break;
4245 case DESC90_RATE36M: ret_rate = MGN_36M; break;
4246 case DESC90_RATE48M: ret_rate = MGN_48M; break;
4247 case DESC90_RATE54M: ret_rate = MGN_54M; break;
4248
4249 default:
4250 RT_TRACE(COMP_RECV, "HwRateToMRate90(): Non supported Rate [%x], bIsHT = %d!!!\n", rate, bIsHT);
4251 break;
4252 }
4253
4254 } else {
4255 switch(rate) {
4256 case DESC90_RATEMCS0: ret_rate = MGN_MCS0; break;
4257 case DESC90_RATEMCS1: ret_rate = MGN_MCS1; break;
4258 case DESC90_RATEMCS2: ret_rate = MGN_MCS2; break;
4259 case DESC90_RATEMCS3: ret_rate = MGN_MCS3; break;
4260 case DESC90_RATEMCS4: ret_rate = MGN_MCS4; break;
4261 case DESC90_RATEMCS5: ret_rate = MGN_MCS5; break;
4262 case DESC90_RATEMCS6: ret_rate = MGN_MCS6; break;
4263 case DESC90_RATEMCS7: ret_rate = MGN_MCS7; break;
4264 case DESC90_RATEMCS8: ret_rate = MGN_MCS8; break;
4265 case DESC90_RATEMCS9: ret_rate = MGN_MCS9; break;
4266 case DESC90_RATEMCS10: ret_rate = MGN_MCS10; break;
4267 case DESC90_RATEMCS11: ret_rate = MGN_MCS11; break;
4268 case DESC90_RATEMCS12: ret_rate = MGN_MCS12; break;
4269 case DESC90_RATEMCS13: ret_rate = MGN_MCS13; break;
4270 case DESC90_RATEMCS14: ret_rate = MGN_MCS14; break;
4271 case DESC90_RATEMCS15: ret_rate = MGN_MCS15; break;
4272 case DESC90_RATEMCS32: ret_rate = (0x80|0x20); break;
4273
4274 default:
4275 RT_TRACE(COMP_RECV, "HwRateToMRate90(): Non supported Rate [%x], bIsHT = %d!!!\n",rate, bIsHT);
4276 break;
4277 }
4278 }
4279
4280 return ret_rate;
4281}
4282
214985a6 4283/* Record the TSF time stamp when receiving a packet */
5e1ad18a 4284static void UpdateRxPktTimeStamp8190 (struct net_device *dev, struct ieee80211_rx_stats *stats)
ecdfa446
GKH
4285{
4286 struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
4287
4288 if(stats->bIsAMPDU && !stats->bFirstMPDU) {
4289 stats->mac_time[0] = priv->LastRxDescTSFLow;
4290 stats->mac_time[1] = priv->LastRxDescTSFHigh;
4291 } else {
4292 priv->LastRxDescTSFLow = stats->mac_time[0];
4293 priv->LastRxDescTSFHigh = stats->mac_time[1];
4294 }
4295}
4296
5e1ad18a 4297static long rtl819x_translate_todbm(u8 signal_strength_index)// 0-100 index.
ecdfa446
GKH
4298{
4299 long signal_power; // in dBm.
4300
4301 // Translate to dBm (x=0.5y-95).
4302 signal_power = (long)((signal_strength_index + 1) >> 1);
4303 signal_power -= 95;
4304
4305 return signal_power;
4306}
4307
ecdfa446
GKH
4308/* 2008/01/22 MH We can not delcare RSSI/EVM total value of sliding window to
4309 be a local static. Otherwise, it may increase when we return from S3/S4. The
4310 value will be kept in memory or disk. We must delcare the value in adapter
4311 and it will be reinitialized when return from S3/S4. */
5e1ad18a 4312static void rtl8192_process_phyinfo(struct r8192_priv * priv, u8* buffer,struct ieee80211_rx_stats * pprevious_stats, struct ieee80211_rx_stats * pcurrent_stats)
ecdfa446
GKH
4313{
4314 bool bcheck = false;
4315 u8 rfpath;
4316 u32 nspatial_stream, tmp_val;
4317 //u8 i;
4318 static u32 slide_rssi_index=0, slide_rssi_statistics=0;
4319 static u32 slide_evm_index=0, slide_evm_statistics=0;
4320 static u32 last_rssi=0, last_evm=0;
4321 //cosa add for rx path selection
4322// static long slide_cck_adc_pwdb_index=0, slide_cck_adc_pwdb_statistics=0;
4323// static char last_cck_adc_pwdb[4]={0,0,0,0};
4324 //cosa add for beacon rssi smoothing
4325 static u32 slide_beacon_adc_pwdb_index=0, slide_beacon_adc_pwdb_statistics=0;
4326 static u32 last_beacon_adc_pwdb=0;
4327
4328 struct ieee80211_hdr_3addr *hdr;
4329 u16 sc ;
4330 unsigned int frag,seq;
4331 hdr = (struct ieee80211_hdr_3addr *)buffer;
4332 sc = le16_to_cpu(hdr->seq_ctl);
4333 frag = WLAN_GET_SEQ_FRAG(sc);
4334 seq = WLAN_GET_SEQ_SEQ(sc);
4335 //cosa add 04292008 to record the sequence number
4336 pcurrent_stats->Seq_Num = seq;
4337 //
4338 // Check whether we should take the previous packet into accounting
4339 //
4340 if(!pprevious_stats->bIsAMPDU)
4341 {
4342 // if previous packet is not aggregated packet
4343 bcheck = true;
ecdfa446
GKH
4344 }
4345
4346 if(slide_rssi_statistics++ >= PHY_RSSI_SLID_WIN_MAX)
4347 {
4348 slide_rssi_statistics = PHY_RSSI_SLID_WIN_MAX;
4349 last_rssi = priv->stats.slide_signal_strength[slide_rssi_index];
4350 priv->stats.slide_rssi_total -= last_rssi;
4351 }
4352 priv->stats.slide_rssi_total += pprevious_stats->SignalStrength;
4353
4354 priv->stats.slide_signal_strength[slide_rssi_index++] = pprevious_stats->SignalStrength;
4355 if(slide_rssi_index >= PHY_RSSI_SLID_WIN_MAX)
4356 slide_rssi_index = 0;
4357
4358 // <1> Showed on UI for user, in dbm
4359 tmp_val = priv->stats.slide_rssi_total/slide_rssi_statistics;
4360 priv->stats.signal_strength = rtl819x_translate_todbm((u8)tmp_val);
4361 pcurrent_stats->rssi = priv->stats.signal_strength;
4362 //
4363 // If the previous packet does not match the criteria, neglect it
4364 //
4365 if(!pprevious_stats->bPacketMatchBSSID)
4366 {
4367 if(!pprevious_stats->bToSelfBA)
4368 return;
4369 }
4370
4371 if(!bcheck)
4372 return;
4373
ecdfa446
GKH
4374 // <2> Showed on UI for engineering
4375 // hardware does not provide rssi information for each rf path in CCK
4376 if(!pprevious_stats->bIsCCK && pprevious_stats->bPacketToSelf)
4377 {
4378 for (rfpath = RF90_PATH_A; rfpath < RF90_PATH_C; rfpath++)
4379 {
4380 if (!rtl8192_phy_CheckIsLegalRFPath(priv->ieee80211->dev, rfpath))
4381 continue;
4382 RT_TRACE(COMP_DBG,"Jacken -> pPreviousstats->RxMIMOSignalStrength[rfpath] = %d \n" ,pprevious_stats->RxMIMOSignalStrength[rfpath] );
4383 //Fixed by Jacken 2008-03-20
4384 if(priv->stats.rx_rssi_percentage[rfpath] == 0)
4385 {
4386 priv->stats.rx_rssi_percentage[rfpath] = pprevious_stats->RxMIMOSignalStrength[rfpath];
ecdfa446
GKH
4387 }
4388 if(pprevious_stats->RxMIMOSignalStrength[rfpath] > priv->stats.rx_rssi_percentage[rfpath])
4389 {
4390 priv->stats.rx_rssi_percentage[rfpath] =
4391 ( (priv->stats.rx_rssi_percentage[rfpath]*(Rx_Smooth_Factor-1)) +
4392 (pprevious_stats->RxMIMOSignalStrength[rfpath])) /(Rx_Smooth_Factor);
4393 priv->stats.rx_rssi_percentage[rfpath] = priv->stats.rx_rssi_percentage[rfpath] + 1;
4394 }
4395 else
4396 {
4397 priv->stats.rx_rssi_percentage[rfpath] =
4398 ( (priv->stats.rx_rssi_percentage[rfpath]*(Rx_Smooth_Factor-1)) +
4399 (pprevious_stats->RxMIMOSignalStrength[rfpath])) /(Rx_Smooth_Factor);
4400 }
4401 RT_TRACE(COMP_DBG,"Jacken -> priv->RxStats.RxRSSIPercentage[rfPath] = %d \n" ,priv->stats.rx_rssi_percentage[rfpath] );
4402 }
4403 }
4404
4405
4406 //
4407 // Check PWDB.
4408 //
4409 //cosa add for beacon rssi smoothing by average.
4410 if(pprevious_stats->bPacketBeacon)
4411 {
4412 /* record the beacon pwdb to the sliding window. */
4413 if(slide_beacon_adc_pwdb_statistics++ >= PHY_Beacon_RSSI_SLID_WIN_MAX)
4414 {
4415 slide_beacon_adc_pwdb_statistics = PHY_Beacon_RSSI_SLID_WIN_MAX;
4416 last_beacon_adc_pwdb = priv->stats.Slide_Beacon_pwdb[slide_beacon_adc_pwdb_index];
4417 priv->stats.Slide_Beacon_Total -= last_beacon_adc_pwdb;
ecdfa446
GKH
4418 // slide_beacon_adc_pwdb_index, last_beacon_adc_pwdb, Adapter->RxStats.Slide_Beacon_Total);
4419 }
4420 priv->stats.Slide_Beacon_Total += pprevious_stats->RxPWDBAll;
4421 priv->stats.Slide_Beacon_pwdb[slide_beacon_adc_pwdb_index] = pprevious_stats->RxPWDBAll;
ecdfa446
GKH
4422 slide_beacon_adc_pwdb_index++;
4423 if(slide_beacon_adc_pwdb_index >= PHY_Beacon_RSSI_SLID_WIN_MAX)
4424 slide_beacon_adc_pwdb_index = 0;
4425 pprevious_stats->RxPWDBAll = priv->stats.Slide_Beacon_Total/slide_beacon_adc_pwdb_statistics;
4426 if(pprevious_stats->RxPWDBAll >= 3)
4427 pprevious_stats->RxPWDBAll -= 3;
4428 }
4429
4430 RT_TRACE(COMP_RXDESC, "Smooth %s PWDB = %d\n",
4431 pprevious_stats->bIsCCK? "CCK": "OFDM",
4432 pprevious_stats->RxPWDBAll);
4433
4434 if(pprevious_stats->bPacketToSelf || pprevious_stats->bPacketBeacon || pprevious_stats->bToSelfBA)
4435 {
4436 if(priv->undecorated_smoothed_pwdb < 0) // initialize
4437 {
4438 priv->undecorated_smoothed_pwdb = pprevious_stats->RxPWDBAll;
ecdfa446 4439 }
11aacc28 4440
ecdfa446
GKH
4441 if(pprevious_stats->RxPWDBAll > (u32)priv->undecorated_smoothed_pwdb)
4442 {
4443 priv->undecorated_smoothed_pwdb =
4444 ( ((priv->undecorated_smoothed_pwdb)*(Rx_Smooth_Factor-1)) +
4445 (pprevious_stats->RxPWDBAll)) /(Rx_Smooth_Factor);
4446 priv->undecorated_smoothed_pwdb = priv->undecorated_smoothed_pwdb + 1;
4447 }
4448 else
4449 {
4450 priv->undecorated_smoothed_pwdb =
4451 ( ((priv->undecorated_smoothed_pwdb)*(Rx_Smooth_Factor-1)) +
4452 (pprevious_stats->RxPWDBAll)) /(Rx_Smooth_Factor);
4453 }
ecdfa446
GKH
4454 }
4455
4456 //
4457 // Check EVM
4458 //
4459 /* record the general EVM to the sliding window. */
4460 if(pprevious_stats->SignalQuality == 0)
4461 {
4462 }
4463 else
4464 {
4465 if(pprevious_stats->bPacketToSelf || pprevious_stats->bPacketBeacon || pprevious_stats->bToSelfBA){
4466 if(slide_evm_statistics++ >= PHY_RSSI_SLID_WIN_MAX){
4467 slide_evm_statistics = PHY_RSSI_SLID_WIN_MAX;
4468 last_evm = priv->stats.slide_evm[slide_evm_index];
4469 priv->stats.slide_evm_total -= last_evm;
4470 }
4471
4472 priv->stats.slide_evm_total += pprevious_stats->SignalQuality;
4473
4474 priv->stats.slide_evm[slide_evm_index++] = pprevious_stats->SignalQuality;
4475 if(slide_evm_index >= PHY_RSSI_SLID_WIN_MAX)
4476 slide_evm_index = 0;
4477
4478 // <1> Showed on UI for user, in percentage.
4479 tmp_val = priv->stats.slide_evm_total/slide_evm_statistics;
ecdfa446 4480 //cosa add 10/11/2007, Showed on UI for user in Windows Vista, for Link quality.
ecdfa446
GKH
4481 }
4482
4483 // <2> Showed on UI for engineering
4484 if(pprevious_stats->bPacketToSelf || pprevious_stats->bPacketBeacon || pprevious_stats->bToSelfBA)
4485 {
4486 for(nspatial_stream = 0; nspatial_stream<2 ; nspatial_stream++) // 2 spatial stream
4487 {
4488 if(pprevious_stats->RxMIMOSignalQuality[nspatial_stream] != -1)
4489 {
4490 if(priv->stats.rx_evm_percentage[nspatial_stream] == 0) // initialize
4491 {
4492 priv->stats.rx_evm_percentage[nspatial_stream] = pprevious_stats->RxMIMOSignalQuality[nspatial_stream];
4493 }
4494 priv->stats.rx_evm_percentage[nspatial_stream] =
4495 ( (priv->stats.rx_evm_percentage[nspatial_stream]* (Rx_Smooth_Factor-1)) +
4496 (pprevious_stats->RxMIMOSignalQuality[nspatial_stream]* 1)) / (Rx_Smooth_Factor);
4497 }
4498 }
4499 }
4500 }
4501
4502}
4503
ecdfa446
GKH
4504static u8 rtl819x_query_rxpwrpercentage(
4505 char antpower
4506 )
4507{
4508 if ((antpower <= -100) || (antpower >= 20))
4509 {
4510 return 0;
4511 }
4512 else if (antpower >= 0)
4513 {
4514 return 100;
4515 }
4516 else
4517 {
4518 return (100+antpower);
4519 }
4520
d5abdf72 4521}
ecdfa446
GKH
4522
4523static u8
4524rtl819x_evm_dbtopercentage(
4525 char value
4526 )
4527{
4528 char ret_val;
4529
4530 ret_val = value;
4531
4532 if(ret_val >= 0)
4533 ret_val = 0;
4534 if(ret_val <= -33)
4535 ret_val = -33;
4536 ret_val = 0 - ret_val;
4537 ret_val*=3;
4538 if(ret_val == 99)
4539 ret_val = 100;
c6eae677 4540 return ret_val;
ecdfa446
GKH
4541}
4542
214985a6 4543/* We want good-looking for signal strength/quality */
5e1ad18a 4544static long rtl819x_signal_scale_mapping(long currsig)
ecdfa446
GKH
4545{
4546 long retsig;
4547
4548 // Step 1. Scale mapping.
4549 if(currsig >= 61 && currsig <= 100)
4550 {
4551 retsig = 90 + ((currsig - 60) / 4);
4552 }
4553 else if(currsig >= 41 && currsig <= 60)
4554 {
4555 retsig = 78 + ((currsig - 40) / 2);
4556 }
4557 else if(currsig >= 31 && currsig <= 40)
4558 {
4559 retsig = 66 + (currsig - 30);
4560 }
4561 else if(currsig >= 21 && currsig <= 30)
4562 {
4563 retsig = 54 + (currsig - 20);
4564 }
4565 else if(currsig >= 5 && currsig <= 20)
4566 {
4567 retsig = 42 + (((currsig - 5) * 2) / 3);
4568 }
4569 else if(currsig == 4)
4570 {
4571 retsig = 36;
4572 }
4573 else if(currsig == 3)
4574 {
4575 retsig = 27;
4576 }
4577 else if(currsig == 2)
4578 {
4579 retsig = 18;
4580 }
4581 else if(currsig == 1)
4582 {
4583 retsig = 9;
4584 }
4585 else
4586 {
4587 retsig = currsig;
4588 }
4589
4590 return retsig;
4591}
4592
4593static void rtl8192_query_rxphystatus(
4594 struct r8192_priv * priv,
4595 struct ieee80211_rx_stats * pstats,
4596 prx_desc_819x_pci pdesc,
4597 prx_fwinfo_819x_pci pdrvinfo,
4598 struct ieee80211_rx_stats * precord_stats,
4599 bool bpacket_match_bssid,
4600 bool bpacket_toself,
4601 bool bPacketBeacon,
4602 bool bToSelfBA
4603 )
4604{
4605 //PRT_RFD_STATUS pRtRfdStatus = &(pRfd->Status);
4606 phy_sts_ofdm_819xpci_t* pofdm_buf;
4607 phy_sts_cck_819xpci_t * pcck_buf;
4608 phy_ofdm_rx_status_rxsc_sgien_exintfflag* prxsc;
4609 u8 *prxpkt;
4610 u8 i,max_spatial_stream, tmp_rxsnr, tmp_rxevm, rxsc_sgien_exflg;
4611 char rx_pwr[4], rx_pwr_all=0;
4612 //long rx_avg_pwr = 0;
4613 char rx_snrX, rx_evmX;
4614 u8 evm, pwdb_all;
4615 u32 RSSI, total_rssi=0;//, total_evm=0;
4616// long signal_strength_index = 0;
4617 u8 is_cck_rate=0;
4618 u8 rf_rx_num = 0;
4619
ecdfa446
GKH
4620 is_cck_rate = rx_hal_is_cck_rate(pdrvinfo);
4621
4622 // Record it for next packet processing
4623 memset(precord_stats, 0, sizeof(struct ieee80211_rx_stats));
4624 pstats->bPacketMatchBSSID = precord_stats->bPacketMatchBSSID = bpacket_match_bssid;
4625 pstats->bPacketToSelf = precord_stats->bPacketToSelf = bpacket_toself;
4626 pstats->bIsCCK = precord_stats->bIsCCK = is_cck_rate;//RX_HAL_IS_CCK_RATE(pDrvInfo);
4627 pstats->bPacketBeacon = precord_stats->bPacketBeacon = bPacketBeacon;
4628 pstats->bToSelfBA = precord_stats->bToSelfBA = bToSelfBA;
4629 /*2007.08.30 requested by SD3 Jerry */
d163f324 4630 if (priv->phy_check_reg824 == 0)
ecdfa446 4631 {
d163f324
MM
4632 priv->phy_reg824_bit9 = rtl8192_QueryBBReg(priv->ieee80211->dev, rFPGA0_XA_HSSIParameter2, 0x200);
4633 priv->phy_check_reg824 = 1;
ecdfa446
GKH
4634 }
4635
4636
4637 prxpkt = (u8*)pdrvinfo;
4638
4639 /* Move pointer to the 16th bytes. Phy status start address. */
4640 prxpkt += sizeof(rx_fwinfo_819x_pci);
4641
4642 /* Initial the cck and ofdm buffer pointer */
4643 pcck_buf = (phy_sts_cck_819xpci_t *)prxpkt;
4644 pofdm_buf = (phy_sts_ofdm_819xpci_t *)prxpkt;
4645
4646 pstats->RxMIMOSignalQuality[0] = -1;
4647 pstats->RxMIMOSignalQuality[1] = -1;
4648 precord_stats->RxMIMOSignalQuality[0] = -1;
4649 precord_stats->RxMIMOSignalQuality[1] = -1;
4650
4651 if(is_cck_rate)
4652 {
4653 //
4654 // (1)Hardware does not provide RSSI for CCK
4655 //
4656
4657 //
4658 // (2)PWDB, Average PWDB cacluated by hardware (for rate adaptive)
4659 //
4660 u8 report;//, cck_agc_rpt;
ecdfa446 4661
d163f324 4662 if (!priv->phy_reg824_bit9)
ecdfa446
GKH
4663 {
4664 report = pcck_buf->cck_agc_rpt & 0xc0;
4665 report = report>>6;
4666 switch(report)
4667 {
4668 //Fixed by Jacken from Bryant 2008-03-20
4669 //Original value is -38 , -26 , -14 , -2
4670 //Fixed value is -35 , -23 , -11 , 6
4671 case 0x3:
4672 rx_pwr_all = -35 - (pcck_buf->cck_agc_rpt & 0x3e);
4673 break;
4674 case 0x2:
4675 rx_pwr_all = -23 - (pcck_buf->cck_agc_rpt & 0x3e);
4676 break;
4677 case 0x1:
4678 rx_pwr_all = -11 - (pcck_buf->cck_agc_rpt & 0x3e);
4679 break;
4680 case 0x0:
4681 rx_pwr_all = 8 - (pcck_buf->cck_agc_rpt & 0x3e);
4682 break;
4683 }
4684 }
4685 else
4686 {
4687 report = pcck_buf->cck_agc_rpt & 0x60;
4688 report = report>>5;
4689 switch(report)
4690 {
4691 case 0x3:
4692 rx_pwr_all = -35 - ((pcck_buf->cck_agc_rpt & 0x1f)<<1) ;
4693 break;
4694 case 0x2:
4695 rx_pwr_all = -23 - ((pcck_buf->cck_agc_rpt & 0x1f)<<1);
4696 break;
4697 case 0x1:
4698 rx_pwr_all = -11 - ((pcck_buf->cck_agc_rpt & 0x1f)<<1) ;
4699 break;
4700 case 0x0:
4701 rx_pwr_all = -8 - ((pcck_buf->cck_agc_rpt & 0x1f)<<1) ;
4702 break;
4703 }
4704 }
4705
4706 pwdb_all = rtl819x_query_rxpwrpercentage(rx_pwr_all);
4707 pstats->RxPWDBAll = precord_stats->RxPWDBAll = pwdb_all;
4708 pstats->RecvSignalPower = rx_pwr_all;
4709
4710 //
4711 // (3) Get Signal Quality (EVM)
4712 //
4713 if(bpacket_match_bssid)
4714 {
4715 u8 sq;
4716
4717 if(pstats->RxPWDBAll > 40)
4718 {
4719 sq = 100;
4720 }else
4721 {
4722 sq = pcck_buf->sq_rpt;
4723
4724 if(pcck_buf->sq_rpt > 64)
4725 sq = 0;
4726 else if (pcck_buf->sq_rpt < 20)
4727 sq = 100;
4728 else
4729 sq = ((64-sq) * 100) / 44;
4730 }
4731 pstats->SignalQuality = precord_stats->SignalQuality = sq;
4732 pstats->RxMIMOSignalQuality[0] = precord_stats->RxMIMOSignalQuality[0] = sq;
4733 pstats->RxMIMOSignalQuality[1] = precord_stats->RxMIMOSignalQuality[1] = -1;
4734 }
4735 }
4736 else
4737 {
ecdfa446
GKH
4738 //
4739 // (1)Get RSSI for HT rate
4740 //
4741 for(i=RF90_PATH_A; i<RF90_PATH_MAX; i++)
4742 {
4743 // 2008/01/30 MH we will judge RF RX path now.
4744 if (priv->brfpath_rxenable[i])
4745 rf_rx_num++;
4746 //else
4747 //continue;
4748
4749 //Fixed by Jacken from Bryant 2008-03-20
4750 //Original value is 106
ecdfa446 4751 rx_pwr[i] = ((pofdm_buf->trsw_gain_X[i]&0x3F)*2) - 110;
ecdfa446
GKH
4752
4753 //Get Rx snr value in DB
4754 tmp_rxsnr = pofdm_buf->rxsnr_X[i];
4755 rx_snrX = (char)(tmp_rxsnr);
4756 rx_snrX /= 2;
ecdfa446
GKH
4757
4758 /* Translate DBM to percentage. */
4759 RSSI = rtl819x_query_rxpwrpercentage(rx_pwr[i]);
4760 if (priv->brfpath_rxenable[i])
4761 total_rssi += RSSI;
4762
4763 /* Record Signal Strength for next packet */
4764 if(bpacket_match_bssid)
4765 {
4766 pstats->RxMIMOSignalStrength[i] =(u8) RSSI;
4767 precord_stats->RxMIMOSignalStrength[i] =(u8) RSSI;
4768 }
4769 }
4770
4771
4772 //
4773 // (2)PWDB, Average PWDB cacluated by hardware (for rate adaptive)
4774 //
4775 //Fixed by Jacken from Bryant 2008-03-20
4776 //Original value is 106
4777 rx_pwr_all = (((pofdm_buf->pwdb_all ) >> 1 )& 0x7f) -106;
4778 pwdb_all = rtl819x_query_rxpwrpercentage(rx_pwr_all);
4779
4780 pstats->RxPWDBAll = precord_stats->RxPWDBAll = pwdb_all;
4781 pstats->RxPower = precord_stats->RxPower = rx_pwr_all;
4782 pstats->RecvSignalPower = rx_pwr_all;
4783 //
4784 // (3)EVM of HT rate
4785 //
4786 if(pdrvinfo->RxHT && pdrvinfo->RxRate>=DESC90_RATEMCS8 &&
4787 pdrvinfo->RxRate<=DESC90_RATEMCS15)
4788 max_spatial_stream = 2; //both spatial stream make sense
4789 else
4790 max_spatial_stream = 1; //only spatial stream 1 makes sense
4791
4792 for(i=0; i<max_spatial_stream; i++)
4793 {
4794 tmp_rxevm = pofdm_buf->rxevm_X[i];
4795 rx_evmX = (char)(tmp_rxevm);
4796
4797 // Do not use shift operation like "rx_evmX >>= 1" because the compilor of free build environment
4798 // fill most significant bit to "zero" when doing shifting operation which may change a negative
4799 // value to positive one, then the dbm value (which is supposed to be negative) is not correct anymore.
4800 rx_evmX /= 2; //dbm
4801
4802 evm = rtl819x_evm_dbtopercentage(rx_evmX);
ecdfa446
GKH
4803 if(bpacket_match_bssid)
4804 {
4805 if(i==0) // Fill value in RFD, Get the first spatial stream only
4806 pstats->SignalQuality = precord_stats->SignalQuality = (u8)(evm & 0xff);
4807 pstats->RxMIMOSignalQuality[i] = precord_stats->RxMIMOSignalQuality[i] = (u8)(evm & 0xff);
4808 }
4809 }
4810
4811
4812 /* record rx statistics for debug */
4813 rxsc_sgien_exflg = pofdm_buf->rxsc_sgien_exflg;
4814 prxsc = (phy_ofdm_rx_status_rxsc_sgien_exintfflag *)&rxsc_sgien_exflg;
ecdfa446
GKH
4815 }
4816
4817 //UI BSS List signal strength(in percentage), make it good looking, from 0~100.
4818 //It is assigned to the BSS List in GetValueFromBeaconOrProbeRsp().
4819 if(is_cck_rate)
4820 {
4821 pstats->SignalStrength = precord_stats->SignalStrength = (u8)(rtl819x_signal_scale_mapping((long)pwdb_all));//PWDB_ALL;
4822
4823 }
4824 else
4825 {
4826 //pRfd->Status.SignalStrength = pRecordRfd->Status.SignalStrength = (u1Byte)(SignalScaleMapping(total_rssi/=RF90_PATH_MAX));//(u1Byte)(total_rssi/=RF90_PATH_MAX);
4827 // We can judge RX path number now.
4828 if (rf_rx_num != 0)
4829 pstats->SignalStrength = precord_stats->SignalStrength = (u8)(rtl819x_signal_scale_mapping((long)(total_rssi/=rf_rx_num)));
4830 }
d5abdf72 4831}
ecdfa446 4832
5e1ad18a 4833static void
ecdfa446
GKH
4834rtl8192_record_rxdesc_forlateruse(
4835 struct ieee80211_rx_stats * psrc_stats,
4836 struct ieee80211_rx_stats * ptarget_stats
4837)
4838{
4839 ptarget_stats->bIsAMPDU = psrc_stats->bIsAMPDU;
4840 ptarget_stats->bFirstMPDU = psrc_stats->bFirstMPDU;
4841 //ptarget_stats->Seq_Num = psrc_stats->Seq_Num;
4842}
4843
4844
4845
5e1ad18a 4846static void TranslateRxSignalStuff819xpci(struct net_device *dev,
ecdfa446
GKH
4847 struct sk_buff *skb,
4848 struct ieee80211_rx_stats * pstats,
4849 prx_desc_819x_pci pdesc,
4850 prx_fwinfo_819x_pci pdrvinfo)
4851{
4852 // TODO: We must only check packet for current MAC address. Not finish
4853 struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
4854 bool bpacket_match_bssid, bpacket_toself;
4855 bool bPacketBeacon=false, bToSelfBA=false;
ecdfa446
GKH
4856 struct ieee80211_hdr_3addr *hdr;
4857 u16 fc,type;
4858
4859 // Get Signal Quality for only RX data queue (but not command queue)
4860
4861 u8* tmp_buf;
4862 u8 *praddr;
4863
4864 /* Get MAC frame start address. */
4865 tmp_buf = skb->data;
4866
4867 hdr = (struct ieee80211_hdr_3addr *)tmp_buf;
4868 fc = le16_to_cpu(hdr->frame_ctl);
4869 type = WLAN_FC_GET_TYPE(fc);
4870 praddr = hdr->addr1;
4871
4872 /* Check if the received packet is acceptabe. */
4873 bpacket_match_bssid = ((IEEE80211_FTYPE_CTL != type) &&
03996954 4874 (!compare_ether_addr(priv->ieee80211->current_network.bssid, (fc & IEEE80211_FCTL_TODS)? hdr->addr1 : (fc & IEEE80211_FCTL_FROMDS )? hdr->addr2 : hdr->addr3))
ecdfa446 4875 && (!pstats->bHwError) && (!pstats->bCRC)&& (!pstats->bICV));
03996954 4876 bpacket_toself = bpacket_match_bssid & (!compare_ether_addr(praddr, priv->ieee80211->dev->dev_addr));
11aacc28 4877
ecdfa446
GKH
4878 if(WLAN_FC_GET_FRAMETYPE(fc)== IEEE80211_STYPE_BEACON)
4879 {
4880 bPacketBeacon = true;
ecdfa446
GKH
4881 }
4882 if(WLAN_FC_GET_FRAMETYPE(fc) == IEEE80211_STYPE_BLOCKACK)
4883 {
03996954 4884 if((!compare_ether_addr(praddr,dev->dev_addr)))
ecdfa446 4885 bToSelfBA = true;
ecdfa446
GKH
4886 }
4887
ecdfa446
GKH
4888 //
4889 // Process PHY information for previous packet (RSSI/PWDB/EVM)
4890 //
4891 // Because phy information is contained in the last packet of AMPDU only, so driver
4892 // should process phy information of previous packet
83184e69
MM
4893 rtl8192_process_phyinfo(priv, tmp_buf, &priv->previous_stats, pstats);
4894 rtl8192_query_rxphystatus(priv, pstats, pdesc, pdrvinfo, &priv->previous_stats, bpacket_match_bssid,
ecdfa446 4895 bpacket_toself ,bPacketBeacon, bToSelfBA);
83184e69 4896 rtl8192_record_rxdesc_forlateruse(pstats, &priv->previous_stats);
ecdfa446
GKH
4897
4898}
4899
4900
5e1ad18a 4901static void rtl8192_tx_resume(struct net_device *dev)
ecdfa446
GKH
4902{
4903 struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
4904 struct ieee80211_device *ieee = priv->ieee80211;
4905 struct sk_buff *skb;
4906 int queue_index;
4907
4908 for(queue_index = BK_QUEUE; queue_index < TXCMD_QUEUE;queue_index++) {
4909 while((!skb_queue_empty(&ieee->skb_waitQ[queue_index]))&&
4910 (priv->ieee80211->check_nic_enough_desc(dev,queue_index) > 0)) {
4911 /* 1. dequeue the packet from the wait queue */
4912 skb = skb_dequeue(&ieee->skb_waitQ[queue_index]);
4913 /* 2. tx the packet directly */
4914 ieee->softmac_data_hard_start_xmit(skb,dev,0/* rate useless now*/);
ecdfa446
GKH
4915 }
4916 }
4917}
4918
80a4dead 4919static void rtl8192_irq_tx_tasklet(unsigned long arg)
ecdfa446 4920{
80a4dead 4921 struct r8192_priv *priv = (struct r8192_priv*) arg;
1348dc08
MM
4922 struct rtl8192_tx_ring *mgnt_ring = &priv->tx_ring[MGNT_QUEUE];
4923 struct net_device *dev = priv->ieee80211->dev;
4924 unsigned long flags;
4925
4926 /* check if we need to report that the management queue is drained */
4927 spin_lock_irqsave(&priv->irq_th_lock, flags);
4928
4929 if (!skb_queue_len(&mgnt_ring->queue) &&
4930 priv->ieee80211->ack_tx_to_ieee &&
4931 rtl8192_is_tx_queue_empty(dev)) {
4932 priv->ieee80211->ack_tx_to_ieee = 0;
4933 ieee80211_ps_tx_ack(priv->ieee80211, 1);
4934 }
4935
4936 spin_unlock_irqrestore(&priv->irq_th_lock, flags);
4937
4938 rtl8192_tx_resume(dev);
ecdfa446
GKH
4939}
4940
214985a6 4941/* Record the received data rate */
5e1ad18a 4942static void UpdateReceivedRateHistogramStatistics8190(
ecdfa446
GKH
4943 struct net_device *dev,
4944 struct ieee80211_rx_stats* pstats
4945 )
4946{
4947 struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
4948 u32 rcvType=1; //0: Total, 1:OK, 2:CRC, 3:ICV
4949 u32 rateIndex;
4950 u32 preamble_guardinterval; //1: short preamble/GI, 0: long preamble/GI
4951
ecdfa446
GKH
4952 if(pstats->bCRC)
4953 rcvType = 2;
4954 else if(pstats->bICV)
4955 rcvType = 3;
4956
4957 if(pstats->bShortPreamble)
4958 preamble_guardinterval = 1;// short
4959 else
4960 preamble_guardinterval = 0;// long
4961
4962 switch(pstats->rate)
4963 {
4964 //
4965 // CCK rate
4966 //
4967 case MGN_1M: rateIndex = 0; break;
4968 case MGN_2M: rateIndex = 1; break;
4969 case MGN_5_5M: rateIndex = 2; break;
4970 case MGN_11M: rateIndex = 3; break;
4971 //
4972 // Legacy OFDM rate
4973 //
4974 case MGN_6M: rateIndex = 4; break;
4975 case MGN_9M: rateIndex = 5; break;
4976 case MGN_12M: rateIndex = 6; break;
4977 case MGN_18M: rateIndex = 7; break;
4978 case MGN_24M: rateIndex = 8; break;
4979 case MGN_36M: rateIndex = 9; break;
4980 case MGN_48M: rateIndex = 10; break;
4981 case MGN_54M: rateIndex = 11; break;
4982 //
4983 // 11n High throughput rate
4984 //
4985 case MGN_MCS0: rateIndex = 12; break;
4986 case MGN_MCS1: rateIndex = 13; break;
4987 case MGN_MCS2: rateIndex = 14; break;
4988 case MGN_MCS3: rateIndex = 15; break;
4989 case MGN_MCS4: rateIndex = 16; break;
4990 case MGN_MCS5: rateIndex = 17; break;
4991 case MGN_MCS6: rateIndex = 18; break;
4992 case MGN_MCS7: rateIndex = 19; break;
4993 case MGN_MCS8: rateIndex = 20; break;
4994 case MGN_MCS9: rateIndex = 21; break;
4995 case MGN_MCS10: rateIndex = 22; break;
4996 case MGN_MCS11: rateIndex = 23; break;
4997 case MGN_MCS12: rateIndex = 24; break;
4998 case MGN_MCS13: rateIndex = 25; break;
4999 case MGN_MCS14: rateIndex = 26; break;
5000 case MGN_MCS15: rateIndex = 27; break;
5001 default: rateIndex = 28; break;
5002 }
ecdfa446
GKH
5003 priv->stats.received_rate_histogram[0][rateIndex]++; //total
5004 priv->stats.received_rate_histogram[rcvType][rateIndex]++;
5005}
5006
5e1ad18a 5007static void rtl8192_rx(struct net_device *dev)
ecdfa446
GKH
5008{
5009 struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
5010 struct ieee80211_hdr_1addr *ieee80211_hdr = NULL;
5011 bool unicast_packet = false;
5012 struct ieee80211_rx_stats stats = {
5013 .signal = 0,
5014 .noise = -98,
5015 .rate = 0,
5016 .freq = IEEE80211_24GHZ_BAND,
5017 };
5018 unsigned int count = priv->rxringcount;
79b03af6
MM
5019 prx_fwinfo_819x_pci pDrvInfo = NULL;
5020 struct sk_buff *new_skb;
ecdfa446 5021
ecdfa446
GKH
5022 while (count--) {
5023 rx_desc_819x_pci *pdesc = &priv->rx_ring[priv->rx_idx];//rx descriptor
5024 struct sk_buff *skb = priv->rx_buf[priv->rx_idx];//rx pkt
5025
79b03af6 5026 if (pdesc->OWN)
ecdfa446
GKH
5027 /* wait data to be filled by hardware */
5028 return;
79b03af6 5029
ecdfa446
GKH
5030 stats.bICV = pdesc->ICV;
5031 stats.bCRC = pdesc->CRC32;
5032 stats.bHwError = pdesc->CRC32 | pdesc->ICV;
5033
5034 stats.Length = pdesc->Length;
5035 if(stats.Length < 24)
5036 stats.bHwError |= 1;
5037
5038 if(stats.bHwError) {
5039 stats.bShift = false;
ecdfa446 5040 goto done;
79b03af6
MM
5041 }
5042 pDrvInfo = NULL;
5043 new_skb = dev_alloc_skb(priv->rxbuffersize);
ecdfa446 5044
79b03af6 5045 if (unlikely(!new_skb))
ecdfa446 5046 goto done;
ecdfa446
GKH
5047
5048 stats.RxDrvInfoSize = pdesc->RxDrvInfoSize;
5049 stats.RxBufShift = ((pdesc->Shift)&0x03);
5050 stats.Decrypted = !pdesc->SWDec;
5051
ecdfa446 5052 pci_dma_sync_single_for_cpu(priv->pdev,
ecdfa446
GKH
5053 *((dma_addr_t *)skb->cb),
5054 priv->rxbuffersize,
5055 PCI_DMA_FROMDEVICE);
5056 skb_put(skb, pdesc->Length);
5057 pDrvInfo = (rx_fwinfo_819x_pci *)(skb->data + stats.RxBufShift);
5058 skb_reserve(skb, stats.RxDrvInfoSize + stats.RxBufShift);
5059
5060 stats.rate = HwRateToMRate90((bool)pDrvInfo->RxHT, (u8)pDrvInfo->RxRate);
5061 stats.bShortPreamble = pDrvInfo->SPLCP;
5062
5063 /* it is debug only. It should be disabled in released driver.
5064 * 2007.1.11 by Emily
5065 * */
5066 UpdateReceivedRateHistogramStatistics8190(dev, &stats);
5067
5068 stats.bIsAMPDU = (pDrvInfo->PartAggr==1);
5069 stats.bFirstMPDU = (pDrvInfo->PartAggr==1) && (pDrvInfo->FirstAGGR==1);
5070
5071 stats.TimeStampLow = pDrvInfo->TSFL;
3f9ab1ee 5072 stats.TimeStampHigh = read_nic_dword(priv, TSFR+4);
ecdfa446
GKH
5073
5074 UpdateRxPktTimeStamp8190(dev, &stats);
5075
5076 //
5077 // Get Total offset of MPDU Frame Body
5078 //
5079 if((stats.RxBufShift + stats.RxDrvInfoSize) > 0)
5080 stats.bShift = 1;
5081
5082 stats.RxIs40MHzPacket = pDrvInfo->BW;
5083
5084 /* ???? */
5085 TranslateRxSignalStuff819xpci(dev,skb, &stats, pdesc, pDrvInfo);
5086
5087 /* Rx A-MPDU */
5088 if(pDrvInfo->FirstAGGR==1 || pDrvInfo->PartAggr == 1)
5089 RT_TRACE(COMP_RXDESC, "pDrvInfo->FirstAGGR = %d, pDrvInfo->PartAggr = %d\n",
5090 pDrvInfo->FirstAGGR, pDrvInfo->PartAggr);
5091 skb_trim(skb, skb->len - 4/*sCrcLng*/);
5092 /* rx packets statistics */
5093 ieee80211_hdr = (struct ieee80211_hdr_1addr *)skb->data;
5094 unicast_packet = false;
5095
5096 if(is_broadcast_ether_addr(ieee80211_hdr->addr1)) {
5097 //TODO
5098 }else if(is_multicast_ether_addr(ieee80211_hdr->addr1)){
5099 //TODO
5100 }else {
5101 /* unicast packet */
5102 unicast_packet = true;
5103 }
5104
5105 stats.packetlength = stats.Length-4;
5106 stats.fraglength = stats.packetlength;
5107 stats.fragoffset = 0;
5108 stats.ntotalfrag = 1;
5109
fb5fe277 5110 if(!ieee80211_rtl_rx(priv->ieee80211, skb, &stats)){
ecdfa446
GKH
5111 dev_kfree_skb_any(skb);
5112 } else {
5113 priv->stats.rxok++;
5114 if(unicast_packet) {
5115 priv->stats.rxbytesunicast += skb->len;
5116 }
5117 }
5118
43f88d53
DL
5119 pci_unmap_single(priv->pdev, *((dma_addr_t *) skb->cb),
5120 priv->rxbuffersize, PCI_DMA_FROMDEVICE);
5121
ecdfa446
GKH
5122 skb = new_skb;
5123 priv->rx_buf[priv->rx_idx] = skb;
1c7ec2e8 5124 *((dma_addr_t *) skb->cb) = pci_map_single(priv->pdev, skb_tail_pointer(skb), priv->rxbuffersize, PCI_DMA_FROMDEVICE);
ecdfa446 5125
ecdfa446
GKH
5126done:
5127 pdesc->BufferAddress = cpu_to_le32(*((dma_addr_t *)skb->cb));
5128 pdesc->OWN = 1;
5129 pdesc->Length = priv->rxbuffersize;
5130 if (priv->rx_idx == priv->rxringcount-1)
5131 pdesc->EOR = 1;
5132 priv->rx_idx = (priv->rx_idx + 1) % priv->rxringcount;
5133 }
5134
5135}
5136
80a4dead 5137static void rtl8192_irq_rx_tasklet(unsigned long arg)
ecdfa446 5138{
80a4dead 5139 struct r8192_priv *priv = (struct r8192_priv*) arg;
ecdfa446
GKH
5140 rtl8192_rx(priv->ieee80211->dev);
5141 /* unmask RDU */
3f9ab1ee 5142 write_nic_dword(priv, INTA_MASK, read_nic_dword(priv, INTA_MASK) | IMR_RDU);
ecdfa446
GKH
5143}
5144
5145static const struct net_device_ops rtl8192_netdev_ops = {
5146 .ndo_open = rtl8192_open,
5147 .ndo_stop = rtl8192_close,
ecdfa446
GKH
5148 .ndo_tx_timeout = tx_timeout,
5149 .ndo_do_ioctl = rtl8192_ioctl,
5150 .ndo_set_multicast_list = r8192_set_multicast,
5151 .ndo_set_mac_address = r8192_set_mac_adr,
fb5fe277 5152 .ndo_start_xmit = ieee80211_rtl_xmit,
ecdfa446
GKH
5153};
5154
ecdfa446
GKH
5155static int __devinit rtl8192_pci_probe(struct pci_dev *pdev,
5156 const struct pci_device_id *id)
5157{
5158 unsigned long ioaddr = 0;
5159 struct net_device *dev = NULL;
5160 struct r8192_priv *priv= NULL;
5161 u8 unit = 0;
3a8f2d3c 5162 int ret = -ENODEV;
ecdfa446
GKH
5163
5164#ifdef CONFIG_RTL8192_IO_MAP
5165 unsigned long pio_start, pio_len, pio_flags;
5166#else
5167 unsigned long pmem_start, pmem_len, pmem_flags;
5168#endif //end #ifdef RTL_IO_MAP
5169
5170 RT_TRACE(COMP_INIT,"Configuring chip resources");
5171
5172 if( pci_enable_device (pdev) ){
5173 RT_TRACE(COMP_ERR,"Failed to enable PCI device");
5174 return -EIO;
5175 }
5176
5177 pci_set_master(pdev);
5178 //pci_set_wmi(pdev);
5179 pci_set_dma_mask(pdev, 0xffffff00ULL);
ecdfa446 5180 pci_set_consistent_dma_mask(pdev,0xffffff00ULL);
ecdfa446 5181 dev = alloc_ieee80211(sizeof(struct r8192_priv));
3a8f2d3c
KV
5182 if (!dev) {
5183 ret = -ENOMEM;
5184 goto fail_free;
5185 }
ecdfa446 5186
ecdfa446 5187 pci_set_drvdata(pdev, dev);
ecdfa446 5188 SET_NETDEV_DEV(dev, &pdev->dev);
ecdfa446 5189 priv = ieee80211_priv(dev);
ecdfa446 5190 priv->ieee80211 = netdev_priv(dev);
ecdfa446 5191 priv->pdev=pdev;
ecdfa446
GKH
5192 if((pdev->subsystem_vendor == PCI_VENDOR_ID_DLINK)&&(pdev->subsystem_device == 0x3304)){
5193 priv->ieee80211->bSupportRemoteWakeUp = 1;
5194 } else
ecdfa446
GKH
5195 {
5196 priv->ieee80211->bSupportRemoteWakeUp = 0;
5197 }
5198
5199#ifdef CONFIG_RTL8192_IO_MAP
5200
5201 pio_start = (unsigned long)pci_resource_start (pdev, 0);
5202 pio_len = (unsigned long)pci_resource_len (pdev, 0);
5203 pio_flags = (unsigned long)pci_resource_flags (pdev, 0);
5204
5205 if (!(pio_flags & IORESOURCE_IO)) {
5206 RT_TRACE(COMP_ERR,"region #0 not a PIO resource, aborting");
5207 goto fail;
5208 }
5209
5210 //DMESG("IO space @ 0x%08lx", pio_start );
5211 if( ! request_region( pio_start, pio_len, RTL819xE_MODULE_NAME ) ){
5212 RT_TRACE(COMP_ERR,"request_region failed!");
5213 goto fail;
5214 }
5215
5216 ioaddr = pio_start;
5217 dev->base_addr = ioaddr; // device I/O address
5218
5219#else
5220
5221 pmem_start = pci_resource_start(pdev, 1);
5222 pmem_len = pci_resource_len(pdev, 1);
5223 pmem_flags = pci_resource_flags (pdev, 1);
5224
5225 if (!(pmem_flags & IORESOURCE_MEM)) {
5226 RT_TRACE(COMP_ERR,"region #1 not a MMIO resource, aborting");
5227 goto fail;
5228 }
5229
5230 //DMESG("Memory mapped space @ 0x%08lx ", pmem_start);
5231 if( ! request_mem_region(pmem_start, pmem_len, RTL819xE_MODULE_NAME)) {
5232 RT_TRACE(COMP_ERR,"request_mem_region failed!");
5233 goto fail;
5234 }
5235
5236
5237 ioaddr = (unsigned long)ioremap_nocache( pmem_start, pmem_len);
5238 if( ioaddr == (unsigned long)NULL ){
5239 RT_TRACE(COMP_ERR,"ioremap failed!");
5240 // release_mem_region( pmem_start, pmem_len );
5241 goto fail1;
5242 }
5243
5244 dev->mem_start = ioaddr; // shared mem start
5245 dev->mem_end = ioaddr + pci_resource_len(pdev, 0); // shared mem end
5246
5247#endif //end #ifdef RTL_IO_MAP
5248
5249 /* We disable the RETRY_TIMEOUT register (0x41) to keep
5250 * PCI Tx retries from interfering with C3 CPU state */
5251 pci_write_config_byte(pdev, 0x41, 0x00);
5252
5253
5254 pci_read_config_byte(pdev, 0x05, &unit);
5255 pci_write_config_byte(pdev, 0x05, unit & (~0x04));
5256
5257 dev->irq = pdev->irq;
5258 priv->irq = 0;
5259
5260 dev->netdev_ops = &rtl8192_netdev_ops;
ecdfa446 5261
890a6850 5262 dev->wireless_handlers = &r8192_wx_handlers_def;
ecdfa446
GKH
5263 dev->type=ARPHRD_ETHER;
5264
890a6850 5265 dev->watchdog_timeo = HZ*3;
ecdfa446
GKH
5266
5267 if (dev_alloc_name(dev, ifname) < 0){
5268 RT_TRACE(COMP_INIT, "Oops: devname already taken! Trying wlan%%d...\n");
dca41306 5269 strcpy(ifname, "wlan%d");
ecdfa446
GKH
5270 dev_alloc_name(dev, ifname);
5271 }
5272
5273 RT_TRACE(COMP_INIT, "Driver probe completed1\n");
5274 if(rtl8192_init(dev)!=0){
5275 RT_TRACE(COMP_ERR, "Initialization failed");
5276 goto fail;
5277 }
5278
ecdfa446
GKH
5279 register_netdev(dev);
5280 RT_TRACE(COMP_INIT, "dev name=======> %s\n",dev->name);
5281 rtl8192_proc_init_one(dev);
5282
5283
5284 RT_TRACE(COMP_INIT, "Driver probe completed\n");
ecdfa446 5285 return 0;
ecdfa446
GKH
5286
5287fail1:
5288
5289#ifdef CONFIG_RTL8180_IO_MAP
5290
5291 if( dev->base_addr != 0 ){
5292
5293 release_region(dev->base_addr,
5294 pci_resource_len(pdev, 0) );
5295 }
5296#else
5297 if( dev->mem_start != (unsigned long)NULL ){
5298 iounmap( (void *)dev->mem_start );
5299 release_mem_region( pci_resource_start(pdev, 1),
5300 pci_resource_len(pdev, 1) );
5301 }
5302#endif //end #ifdef RTL_IO_MAP
5303
5304fail:
5305 if(dev){
5306
5307 if (priv->irq) {
5308 free_irq(dev->irq, dev);
5309 dev->irq=0;
5310 }
5311 free_ieee80211(dev);
5312 }
5313
3a8f2d3c 5314fail_free:
ecdfa446
GKH
5315 pci_disable_device(pdev);
5316
5317 DMESG("wlan driver load failed\n");
5318 pci_set_drvdata(pdev, NULL);
3a8f2d3c 5319 return ret;
ecdfa446
GKH
5320
5321}
5322
5323/* detach all the work and timer structure declared or inititialized
5324 * in r8192_init function.
5325 * */
5b3b1a7b 5326static void rtl8192_cancel_deferred_work(struct r8192_priv* priv)
ecdfa446
GKH
5327{
5328 /* call cancel_work_sync instead of cancel_delayed_work if and only if Linux_version_code
5329 * is or is newer than 2.6.20 and work structure is defined to be struct work_struct.
5330 * Otherwise call cancel_delayed_work is enough.
39cfb97b 5331 * FIXME (2.6.20 should 2.6.22, work_struct should not cancel)
ecdfa446 5332 * */
ecdfa446
GKH
5333 cancel_delayed_work(&priv->watch_dog_wq);
5334 cancel_delayed_work(&priv->update_beacon_wq);
5335 cancel_delayed_work(&priv->ieee80211->hw_wakeup_wq);
5336 cancel_delayed_work(&priv->ieee80211->hw_sleep_wq);
ecdfa446 5337 cancel_delayed_work(&priv->gpio_change_rf_wq);
ecdfa446
GKH
5338 cancel_work_sync(&priv->reset_wq);
5339 cancel_work_sync(&priv->qos_activate);
5340 //cancel_work_sync(&priv->SetBWModeWorkItem);
5341 //cancel_work_sync(&priv->SwChnlWorkItem);
ecdfa446
GKH
5342
5343}
5344
5345
5346static void __devexit rtl8192_pci_disconnect(struct pci_dev *pdev)
5347{
5348 struct net_device *dev = pci_get_drvdata(pdev);
5349 struct r8192_priv *priv ;
fb53c2b7 5350 u32 i;
ecdfa446 5351
fb53c2b7 5352 if (dev) {
ecdfa446
GKH
5353
5354 unregister_netdev(dev);
5355
fb53c2b7 5356 priv = ieee80211_priv(dev);
ecdfa446
GKH
5357
5358 rtl8192_proc_remove_one(dev);
5359
5360 rtl8192_down(dev);
5361 if (priv->pFirmware)
5362 {
5363 vfree(priv->pFirmware);
5364 priv->pFirmware = NULL;
5365 }
ecdfa446 5366 destroy_workqueue(priv->priv_wq);
ecdfa446 5367
fb53c2b7
MM
5368 /* free tx/rx rings */
5369 rtl8192_free_rx_ring(dev);
5370 for (i = 0; i < MAX_TX_QUEUE_COUNT; i++)
5371 rtl8192_free_tx_ring(dev, i);
5372
5373 if (priv->irq) {
ecdfa446
GKH
5374 printk("Freeing irq %d\n",dev->irq);
5375 free_irq(dev->irq, dev);
5376 priv->irq=0;
ecdfa446
GKH
5377 }
5378
ecdfa446
GKH
5379#ifdef CONFIG_RTL8180_IO_MAP
5380
5381 if( dev->base_addr != 0 ){
5382
5383 release_region(dev->base_addr,
5384 pci_resource_len(pdev, 0) );
5385 }
5386#else
5387 if( dev->mem_start != (unsigned long)NULL ){
5388 iounmap( (void *)dev->mem_start );
5389 release_mem_region( pci_resource_start(pdev, 1),
5390 pci_resource_len(pdev, 1) );
5391 }
5392#endif /*end #ifdef RTL_IO_MAP*/
5393 free_ieee80211(dev);
5394
5395 }
5396
5397 pci_disable_device(pdev);
5398 RT_TRACE(COMP_DOWN, "wlan driver removed\n");
5399}
5400
fb5fe277
GK
5401extern int ieee80211_rtl_init(void);
5402extern void ieee80211_rtl_exit(void);
ecdfa446
GKH
5403
5404static int __init rtl8192_pci_module_init(void)
5405{
5406 int retval;
5407
fb5fe277 5408 retval = ieee80211_rtl_init();
ecdfa446
GKH
5409 if (retval)
5410 return retval;
5411
5412 printk(KERN_INFO "\nLinux kernel driver for RTL8192 based WLAN cards\n");
5413 printk(KERN_INFO "Copyright (c) 2007-2008, Realsil Wlan\n");
5414 RT_TRACE(COMP_INIT, "Initializing module");
ecdfa446 5415 rtl8192_proc_module_init();
ecdfa446 5416 if(0!=pci_register_driver(&rtl8192_pci_driver))
ecdfa446
GKH
5417 {
5418 DMESG("No device found");
5419 /*pci_unregister_driver (&rtl8192_pci_driver);*/
5420 return -ENODEV;
5421 }
5422 return 0;
5423}
5424
5425
5426static void __exit rtl8192_pci_module_exit(void)
5427{
5428 pci_unregister_driver(&rtl8192_pci_driver);
5429
5430 RT_TRACE(COMP_DOWN, "Exiting");
5431 rtl8192_proc_module_remove();
fb5fe277 5432 ieee80211_rtl_exit();
ecdfa446
GKH
5433}
5434
559fba5e 5435static irqreturn_t rtl8192_interrupt(int irq, void *netdev)
ecdfa446 5436{
b2cf8d48
MM
5437 struct net_device *dev = (struct net_device *) netdev;
5438 struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
5439 unsigned long flags;
5440 u32 inta;
f8129a95
MM
5441 irqreturn_t ret = IRQ_HANDLED;
5442
5443 spin_lock_irqsave(&priv->irq_th_lock, flags);
ecdfa446 5444
b2cf8d48
MM
5445 /* We should return IRQ_NONE, but for now let me keep this */
5446 if (priv->irq_enabled == 0)
f8129a95 5447 goto out_unlock;
ecdfa446 5448
b2cf8d48 5449 /* ISR: 4bytes */
ecdfa446 5450
3f9ab1ee
MM
5451 inta = read_nic_dword(priv, ISR); /* & priv->IntrMask; */
5452 write_nic_dword(priv, ISR, inta); /* reset int situation */
ecdfa446 5453
b2cf8d48 5454 if (!inta) {
b2cf8d48
MM
5455 /*
5456 * most probably we can safely return IRQ_NONE,
5457 * but for now is better to avoid problems
5458 */
f8129a95 5459 goto out_unlock;
b2cf8d48 5460 }
ecdfa446 5461
b2cf8d48
MM
5462 if (inta == 0xffff) {
5463 /* HW disappared */
f8129a95 5464 goto out_unlock;
b2cf8d48
MM
5465 }
5466
f8129a95
MM
5467 if (!netif_running(dev))
5468 goto out_unlock;
ecdfa446 5469
b2cf8d48
MM
5470 if (inta & IMR_TBDOK) {
5471 RT_TRACE(COMP_INTR, "beacon ok interrupt!\n");
5472 rtl8192_tx_isr(dev, BEACON_QUEUE);
5473 priv->stats.txbeaconokint++;
5474 }
ecdfa446 5475
b2cf8d48
MM
5476 if (inta & IMR_TBDER) {
5477 RT_TRACE(COMP_INTR, "beacon ok interrupt!\n");
5478 rtl8192_tx_isr(dev, BEACON_QUEUE);
5479 priv->stats.txbeaconerr++;
5480 }
ecdfa446 5481
b2cf8d48
MM
5482 if (inta & IMR_MGNTDOK ) {
5483 RT_TRACE(COMP_INTR, "Manage ok interrupt!\n");
5484 priv->stats.txmanageokint++;
5485 rtl8192_tx_isr(dev,MGNT_QUEUE);
5486 }
ecdfa446 5487
b2cf8d48
MM
5488 if (inta & IMR_COMDOK)
5489 {
5490 priv->stats.txcmdpktokint++;
5491 rtl8192_tx_isr(dev, TXCMD_QUEUE);
5492 }
ecdfa446 5493
b2cf8d48 5494 if (inta & IMR_ROK) {
b2cf8d48
MM
5495 priv->stats.rxint++;
5496 tasklet_schedule(&priv->irq_rx_tasklet);
5497 }
ecdfa446 5498
b2cf8d48
MM
5499 if (inta & IMR_BcnInt) {
5500 RT_TRACE(COMP_INTR, "prepare beacon for interrupt!\n");
5501 tasklet_schedule(&priv->irq_prepare_beacon_tasklet);
5502 }
ecdfa446 5503
b2cf8d48
MM
5504 if (inta & IMR_RDU) {
5505 RT_TRACE(COMP_INTR, "rx descriptor unavailable!\n");
5506 priv->stats.rxrdu++;
5507 /* reset int situation */
3f9ab1ee 5508 write_nic_dword(priv, INTA_MASK, read_nic_dword(priv, INTA_MASK) & ~IMR_RDU);
b2cf8d48
MM
5509 tasklet_schedule(&priv->irq_rx_tasklet);
5510 }
ecdfa446 5511
b2cf8d48
MM
5512 if (inta & IMR_RXFOVW) {
5513 RT_TRACE(COMP_INTR, "rx overflow !\n");
5514 priv->stats.rxoverflow++;
5515 tasklet_schedule(&priv->irq_rx_tasklet);
5516 }
ecdfa446 5517
b2cf8d48
MM
5518 if (inta & IMR_TXFOVW)
5519 priv->stats.txoverflow++;
ecdfa446 5520
b2cf8d48
MM
5521 if (inta & IMR_BKDOK) {
5522 RT_TRACE(COMP_INTR, "BK Tx OK interrupt!\n");
5523 priv->stats.txbkokint++;
5524 priv->ieee80211->LinkDetectInfo.NumTxOkInPeriod++;
5525 rtl8192_tx_isr(dev, BK_QUEUE);
5526 }
ecdfa446 5527
b2cf8d48
MM
5528 if (inta & IMR_BEDOK) {
5529 RT_TRACE(COMP_INTR, "BE TX OK interrupt!\n");
5530 priv->stats.txbeokint++;
5531 priv->ieee80211->LinkDetectInfo.NumTxOkInPeriod++;
5532 rtl8192_tx_isr(dev, BE_QUEUE);
5533 }
ecdfa446 5534
b2cf8d48
MM
5535 if (inta & IMR_VIDOK) {
5536 RT_TRACE(COMP_INTR, "VI TX OK interrupt!\n");
5537 priv->stats.txviokint++;
5538 priv->ieee80211->LinkDetectInfo.NumTxOkInPeriod++;
5539 rtl8192_tx_isr(dev, VI_QUEUE);
5540 }
ecdfa446 5541
b2cf8d48
MM
5542 if (inta & IMR_VODOK) {
5543 priv->stats.txvookint++;
5544 priv->ieee80211->LinkDetectInfo.NumTxOkInPeriod++;
5545 rtl8192_tx_isr(dev, VO_QUEUE);
5546 }
ecdfa446 5547
f8129a95 5548out_unlock:
b2cf8d48 5549 spin_unlock_irqrestore(&priv->irq_th_lock, flags);
ecdfa446 5550
f8129a95 5551 return ret;
ecdfa446
GKH
5552}
5553
ecdfa446
GKH
5554void EnableHWSecurityConfig8192(struct net_device *dev)
5555{
5556 u8 SECR_value = 0x0;
ecdfa446 5557 struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
16d74da0
MM
5558 struct ieee80211_device* ieee = priv->ieee80211;
5559
ecdfa446 5560 SECR_value = SCR_TxEncEnable | SCR_RxDecEnable;
11aacc28 5561
ecdfa446
GKH
5562 if (((KEY_TYPE_WEP40 == ieee->pairwise_key_type) || (KEY_TYPE_WEP104 == ieee->pairwise_key_type)) && (priv->ieee80211->auth_mode != 2))
5563 {
5564 SECR_value |= SCR_RxUseDK;
5565 SECR_value |= SCR_TxUseDK;
5566 }
5567 else if ((ieee->iw_mode == IW_MODE_ADHOC) && (ieee->pairwise_key_type & (KEY_TYPE_CCMP | KEY_TYPE_TKIP)))
5568 {
5569 SECR_value |= SCR_RxUseDK;
5570 SECR_value |= SCR_TxUseDK;
5571 }
5572
ecdfa446
GKH
5573 //add HWSec active enable here.
5574//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
5575 ieee->hwsec_active = 1;
5576
5577 if ((ieee->pHTInfo->IOTAction&HT_IOT_ACT_PURE_N_MODE) || !hwwep)//!ieee->hwsec_support) //add hwsec_support flag to totol control hw_sec on/off
5578 {
5579 ieee->hwsec_active = 0;
5580 SECR_value &= ~SCR_RxDecEnable;
5581 }
5582
207b58fb 5583 RT_TRACE(COMP_SEC,"%s:, hwsec:%d, pairwise_key:%d, SECR_value:%x\n", __FUNCTION__,
ecdfa446
GKH
5584 ieee->hwsec_active, ieee->pairwise_key_type, SECR_value);
5585 {
3f9ab1ee 5586 write_nic_byte(priv, SECR, SECR_value);//SECR_value | SCR_UseDK );
ecdfa446
GKH
5587 }
5588
5589}
5590#define TOTAL_CAM_ENTRY 32
5591//#define CAM_CONTENT_COUNT 8
5592void setKey( struct net_device *dev,
5593 u8 EntryNo,
5594 u8 KeyIndex,
5595 u16 KeyType,
881a975b 5596 const u8 *MacAddr,
ecdfa446
GKH
5597 u8 DefaultKey,
5598 u32 *KeyContent )
5599{
5600 u32 TargetCommand = 0;
5601 u32 TargetContent = 0;
5602 u16 usConfig = 0;
5603 u8 i;
5604#ifdef ENABLE_IPS
5605 struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
5606 RT_RF_POWER_STATE rtState;
5607 rtState = priv->ieee80211->eRFPowerState;
5608 if(priv->ieee80211->PowerSaveControl.bInactivePs){
5609 if(rtState == eRfOff){
5610 if(priv->ieee80211->RfOffReason > RF_CHANGE_BY_IPS)
5611 {
5612 RT_TRACE(COMP_ERR, "%s(): RF is OFF.\n",__FUNCTION__);
65a43784 5613 //up(&priv->wx_sem);
ecdfa446
GKH
5614 return ;
5615 }
5616 else{
65a43784 5617 down(&priv->ieee80211->ips_sem);
ecdfa446 5618 IPSLeave(dev);
65a43784 5619 up(&priv->ieee80211->ips_sem);
ecdfa446
GKH
5620 }
5621 }
5622 }
5623 priv->ieee80211->is_set_key = true;
5624#endif
5625 if (EntryNo >= TOTAL_CAM_ENTRY)
5626 RT_TRACE(COMP_ERR, "cam entry exceeds in setKey()\n");
5627
0ee9f67c 5628 RT_TRACE(COMP_SEC, "====>to setKey(), dev:%p, EntryNo:%d, KeyIndex:%d, KeyType:%d, MacAddr%pM\n", dev,EntryNo, KeyIndex, KeyType, MacAddr);
ecdfa446
GKH
5629
5630 if (DefaultKey)
5631 usConfig |= BIT15 | (KeyType<<2);
5632 else
5633 usConfig |= BIT15 | (KeyType<<2) | KeyIndex;
5634// usConfig |= BIT15 | (KeyType<<2) | (DefaultKey<<5) | KeyIndex;
5635
5636
5637 for(i=0 ; i<CAM_CONTENT_COUNT; i++){
5638 TargetCommand = i+CAM_CONTENT_COUNT*EntryNo;
5639 TargetCommand |= BIT31|BIT16;
5640
5641 if(i==0){//MAC|Config
5642 TargetContent = (u32)(*(MacAddr+0)) << 16|
5643 (u32)(*(MacAddr+1)) << 24|
5644 (u32)usConfig;
5645
3f9ab1ee
MM
5646 write_nic_dword(priv, WCAMI, TargetContent);
5647 write_nic_dword(priv, RWCAM, TargetCommand);
ecdfa446
GKH
5648 }
5649 else if(i==1){//MAC
5650 TargetContent = (u32)(*(MacAddr+2)) |
5651 (u32)(*(MacAddr+3)) << 8|
5652 (u32)(*(MacAddr+4)) << 16|
5653 (u32)(*(MacAddr+5)) << 24;
3f9ab1ee
MM
5654 write_nic_dword(priv, WCAMI, TargetContent);
5655 write_nic_dword(priv, RWCAM, TargetCommand);
ecdfa446
GKH
5656 }
5657 else { //Key Material
5658 if(KeyContent != NULL)
5659 {
3f9ab1ee
MM
5660 write_nic_dword(priv, WCAMI, (u32)(*(KeyContent+i-2)) );
5661 write_nic_dword(priv, RWCAM, TargetCommand);
ecdfa446
GKH
5662 }
5663 }
5664 }
5665 RT_TRACE(COMP_SEC,"=========>after set key, usconfig:%x\n", usConfig);
ecdfa446 5666}
ecdfa446 5667
65a43784 5668bool NicIFEnableNIC(struct net_device* dev)
5669{
5670 RT_STATUS init_status = RT_STATUS_SUCCESS;
5671 struct r8192_priv* priv = ieee80211_priv(dev);
5672 PRT_POWER_SAVE_CONTROL pPSC = (PRT_POWER_SAVE_CONTROL)(&(priv->ieee80211->PowerSaveControl));
5673
5674 //YJ,add,091109
5675 if (priv->up == 0){
5676 RT_TRACE(COMP_ERR, "ERR!!! %s(): Driver is already down!\n",__FUNCTION__);
5677 priv->bdisable_nic = false; //YJ,add,091111
5678 return false;
5679 }
5680 // <1> Reset memory: descriptor, buffer,..
5681 //NicIFResetMemory(Adapter);
5682
5683 // <2> Enable Adapter
65a43784 5684 //priv->bfirst_init = true;
5685 init_status = rtl8192_adapter_start(dev);
5686 if (init_status != RT_STATUS_SUCCESS) {
5687 RT_TRACE(COMP_ERR,"ERR!!! %s(): initialization is failed!\n",__FUNCTION__);
5688 priv->bdisable_nic = false; //YJ,add,091111
5689 return -1;
5690 }
65a43784 5691 RT_CLEAR_PS_LEVEL(pPSC, RT_RF_OFF_LEVL_HALT_NIC);
5692 //priv->bfirst_init = false;
5693
5694 // <3> Enable Interrupt
5695 rtl8192_irq_enable(dev);
5696 priv->bdisable_nic = false;
16d74da0 5697
c6eae677 5698 return (init_status == RT_STATUS_SUCCESS);
65a43784 5699}
214985a6 5700
65a43784 5701bool NicIFDisableNIC(struct net_device* dev)
5702{
5703 bool status = true;
5704 struct r8192_priv* priv = ieee80211_priv(dev);
5705 u8 tmp_state = 0;
5706 // <1> Disable Interrupt
16d74da0 5707
65a43784 5708 priv->bdisable_nic = true; //YJ,move,091109
5709 tmp_state = priv->ieee80211->state;
5710
5711 ieee80211_softmac_stop_protocol(priv->ieee80211, false);
5712
5713 priv->ieee80211->state = tmp_state;
5714 rtl8192_cancel_deferred_work(priv);
5715 rtl8192_irq_disable(dev);
5716 // <2> Stop all timer
5717
5718 // <3> Disable Adapter
5719 rtl8192_halt_adapter(dev, false);
5720// priv->bdisable_nic = true;
65a43784 5721
5722 return status;
5723}
5724
ecdfa446
GKH
5725module_init(rtl8192_pci_module_init);
5726module_exit(rtl8192_pci_module_exit);
This page took 0.528948 seconds and 5 git commands to generate.