Staging: rtl8192s_usb: Remove duplicate device ID
[linux-2.6/linux-acpi-2.6/ibm-acpi-2.6.git] / drivers / staging / rtl8192su / r8192U_core.c
blob1b6890611fb6dc822156e6ffbee719fb156712c3
1 /******************************************************************************
2 * Copyright(c) 2008 - 2010 Realtek Corporation. All rights reserved.
3 * Linux device driver for RTL8192U
5 * Based on the r8187 driver, which is:
6 * Copyright 2004-2005 Andrea Merello <andreamrl@tiscali.it>, et al.
7 * This program is free software; you can redistribute it and/or modify it
8 * under the terms of version 2 of the GNU General Public License as
9 * published by the Free Software Foundation.
11 * This program is distributed in the hope that it will be useful, but WITHOUT
12 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
13 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
14 * more details.
16 * You should have received a copy of the GNU General Public License along with
17 * this program; if not, write to the Free Software Foundation, Inc.,
18 * 51 Franklin Street, Fifth Floor, Boston, MA 02110, USA
20 * The full GNU General Public License is included in this distribution in the
21 * file called LICENSE.
23 * Contact Information:
24 * Jerry chuang <wlanfae@realtek.com>
27 #include <linux/vmalloc.h>
28 #include <linux/slab.h>
29 #include <linux/eeprom_93cx6.h>
31 #undef LOOP_TEST
32 #undef DUMP_RX
33 #undef DUMP_TX
34 #undef DEBUG_TX_DESC2
35 #undef RX_DONT_PASS_UL
36 #undef DEBUG_EPROM
37 #undef DEBUG_RX_VERBOSE
38 #undef DUMMY_RX
39 #undef DEBUG_ZERO_RX
40 #undef DEBUG_RX_SKB
41 #undef DEBUG_TX_FRAG
42 #undef DEBUG_RX_FRAG
43 #undef DEBUG_TX_FILLDESC
44 #undef DEBUG_TX
45 #undef DEBUG_IRQ
46 #undef DEBUG_RX
47 #undef DEBUG_RXALLOC
48 #undef DEBUG_REGISTERS
49 #undef DEBUG_RING
50 #undef DEBUG_IRQ_TASKLET
51 #undef DEBUG_TX_ALLOC
52 #undef DEBUG_TX_DESC
54 #define CONFIG_RTL8192_IO_MAP
56 #include <asm/uaccess.h>
57 #include "r8192U.h"
58 #include "r8192U_wx.h"
60 #include "r8192S_rtl8225.h"
61 #include "r8192S_hw.h"
62 #include "r8192S_phy.h"
63 #include "r8192S_phyreg.h"
64 #include "r8192S_Efuse.h"
66 #include "r819xU_cmdpkt.h"
67 #include "r8192U_dm.h"
68 //#include "r8192xU_phyreg.h"
69 #include <linux/usb.h>
71 #include "r8192U_pm.h"
73 #include "ieee80211/dot11d.h"
77 u32 rt_global_debug_component = \
78 // COMP_TRACE |
79 // COMP_DBG |
80 // COMP_INIT |
81 // COMP_RECV |
82 // COMP_SEND |
83 // COMP_IO |
84 COMP_POWER |
85 // COMP_EPROM |
86 COMP_SWBW |
87 COMP_POWER_TRACKING |
88 COMP_TURBO |
89 COMP_QOS |
90 // COMP_RATE |
91 // COMP_RM |
92 COMP_DIG |
93 // COMP_EFUSE |
94 // COMP_CH |
95 // COMP_TXAGC |
96 COMP_HIPWR |
97 // COMP_HALDM |
98 COMP_SEC |
99 COMP_LED |
100 // COMP_RF |
101 // COMP_RXDESC |
102 COMP_FIRMWARE |
103 COMP_HT |
104 COMP_AMSDU |
105 COMP_SCAN |
106 // COMP_CMD |
107 COMP_DOWN |
108 COMP_RESET |
109 COMP_ERR; //always open err flags on
111 #define TOTAL_CAM_ENTRY 32
112 #define CAM_CONTENT_COUNT 8
114 static const struct usb_device_id rtl8192_usb_id_tbl[] = {
115 {USB_DEVICE(0x0bda, 0x8171)}, /* Realtek */
116 {USB_DEVICE(0x0bda, 0x8172)},
117 {USB_DEVICE(0x0bda, 0x8173)},
118 {USB_DEVICE(0x0bda, 0x8174)},
119 {USB_DEVICE(0x0bda, 0x8712)},
120 {USB_DEVICE(0x0bda, 0x8713)},
121 {USB_DEVICE(0x07aa, 0x0047)},
122 {USB_DEVICE(0x07d1, 0x3303)},
123 {USB_DEVICE(0x07d1, 0x3302)},
124 {USB_DEVICE(0x07d1, 0x3300)},
125 {USB_DEVICE(0x1740, 0x9603)},
126 {USB_DEVICE(0x1740, 0x9605)},
127 {USB_DEVICE(0x050d, 0x815F)},
128 {USB_DEVICE(0x06f8, 0xe031)},
129 {USB_DEVICE(0x7392, 0x7611)},
130 {USB_DEVICE(0x7392, 0x7612)},
131 {USB_DEVICE(0x7392, 0x7622)},
132 {USB_DEVICE(0x0DF6, 0x0045)},
133 {USB_DEVICE(0x0E66, 0x0015)},
134 {USB_DEVICE(0x0E66, 0x0016)},
135 {USB_DEVICE(0x0b05, 0x1786)},
136 /* these are not in the official list */
137 {USB_DEVICE(0x0df6, 0x004b)}, /* WL-349 */
141 MODULE_LICENSE("GPL");
142 MODULE_VERSION("V 1.1");
143 MODULE_DEVICE_TABLE(usb, rtl8192_usb_id_tbl);
144 MODULE_DESCRIPTION("Linux driver for Realtek RTL8192 USB WiFi cards");
146 static char* ifname = "wlan%d";
147 static int hwwep = 1; //default use hw. set 0 to use software security
148 static int channels = 0x3fff;
152 module_param(ifname, charp, S_IRUGO|S_IWUSR );
153 //module_param(hwseqnum,int, S_IRUGO|S_IWUSR);
154 module_param(hwwep,int, S_IRUGO|S_IWUSR);
155 module_param(channels,int, S_IRUGO|S_IWUSR);
157 MODULE_PARM_DESC(ifname," Net interface name, wlan%d=default");
158 //MODULE_PARM_DESC(hwseqnum," Try to use hardware 802.11 header sequence numbers. Zero=default");
159 MODULE_PARM_DESC(hwwep," Try to use hardware security support. ");
160 MODULE_PARM_DESC(channels," Channel bitmask for specific locales. NYI");
162 static int __devinit rtl8192_usb_probe(struct usb_interface *intf,
163 const struct usb_device_id *id);
164 static void __devexit rtl8192_usb_disconnect(struct usb_interface *intf);
166 static struct usb_driver rtl8192_usb_driver = {
167 .name = RTL819xU_MODULE_NAME, /* Driver name */
168 .id_table = rtl8192_usb_id_tbl, /* PCI_ID table */
169 .probe = rtl8192_usb_probe, /* probe fn */
170 .disconnect = rtl8192_usb_disconnect, /* remove fn */
171 .suspend = rtl8192U_suspend, /* PM suspend fn */
172 .resume = rtl8192U_resume, /* PM resume fn */
173 .reset_resume = rtl8192U_resume, /* PM reset resume fn */
177 static void rtl8192SU_read_eeprom_info(struct net_device *dev);
178 short rtl8192SU_tx(struct net_device *dev, struct sk_buff* skb);
179 void rtl8192SU_rx_nomal(struct sk_buff* skb);
180 void rtl8192SU_rx_cmd(struct sk_buff *skb);
181 bool rtl8192SU_adapter_start(struct net_device *dev);
182 short rtl8192SU_tx_cmd(struct net_device *dev, struct sk_buff *skb);
183 void rtl8192SU_link_change(struct net_device *dev);
184 void InitialGain8192S(struct net_device *dev,u8 Operation);
185 void rtl8192SU_query_rxdesc_status(struct sk_buff *skb, struct ieee80211_rx_stats *stats, bool bIsRxAggrSubframe);
187 struct rtl819x_ops rtl8192su_ops = {
188 .nic_type = NIC_8192SU,
189 .rtl819x_read_eeprom_info = rtl8192SU_read_eeprom_info,
190 .rtl819x_tx = rtl8192SU_tx,
191 .rtl819x_tx_cmd = rtl8192SU_tx_cmd,
192 .rtl819x_rx_nomal = rtl8192SU_rx_nomal,
193 .rtl819x_rx_cmd = rtl8192SU_rx_cmd,
194 .rtl819x_adapter_start = rtl8192SU_adapter_start,
195 .rtl819x_link_change = rtl8192SU_link_change,
196 .rtl819x_initial_gain = InitialGain8192S,
197 .rtl819x_query_rxdesc_status = rtl8192SU_query_rxdesc_status,
201 typedef struct _CHANNEL_LIST
203 u8 Channel[32];
204 u8 Len;
205 }CHANNEL_LIST, *PCHANNEL_LIST;
207 static CHANNEL_LIST ChannelPlan[] = {
208 {{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
209 {{1,2,3,4,5,6,7,8,9,10,11},11}, //IC
210 {{1,2,3,4,5,6,7,8,9,10,11,12,13,36,40,44,48,52,56,60,64},21}, //ETSI
211 {{1,2,3,4,5,6,7,8,9,10,11,12,13},13}, //Spain. Change to ETSI.
212 {{1,2,3,4,5,6,7,8,9,10,11,12,13},13}, //France. Change to ETSI.
213 {{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
214 {{1,2,3,4,5,6,7,8,9,10,11,12,13,14,36,40,44,48,52,56,60,64},22},//MKK1
215 {{1,2,3,4,5,6,7,8,9,10,11,12,13},13}, //Israel.
216 {{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
217 {{1,2,3,4,5,6,7,8,9,10,11,12,13,14,36,40,44,48,52,56,60,64}, 22}, //MIC
218 {{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
221 static void rtl819x_eeprom_register_read(struct eeprom_93cx6 *eeprom)
223 struct net_device *dev = eeprom->data;
224 u8 reg = read_nic_byte(dev, EPROM_CMD);
226 eeprom->reg_data_in = reg & RTL819X_EEPROM_CMD_WRITE;
227 eeprom->reg_data_out = reg & RTL819X_EEPROM_CMD_READ;
228 eeprom->reg_data_clock = reg & RTL819X_EEPROM_CMD_CK;
229 eeprom->reg_chip_select = reg & RTL819X_EEPROM_CMD_CS;
232 static void rtl819x_eeprom_register_write(struct eeprom_93cx6 *eeprom)
234 struct net_device *dev = eeprom->data;
235 u8 reg = 2 << 6;
237 if (eeprom->reg_data_in)
238 reg |= RTL819X_EEPROM_CMD_WRITE;
239 if (eeprom->reg_data_out)
240 reg |= RTL819X_EEPROM_CMD_READ;
241 if (eeprom->reg_data_clock)
242 reg |= RTL819X_EEPROM_CMD_CK;
243 if (eeprom->reg_chip_select)
244 reg |= RTL819X_EEPROM_CMD_CS;
246 write_nic_byte(dev, EPROM_CMD, reg);
247 read_nic_byte(dev, EPROM_CMD);
248 udelay(10);
251 static void rtl819x_set_channel_map(u8 channel_plan, struct r8192_priv* priv)
253 int i, max_chan=-1, min_chan=-1;
254 struct ieee80211_device* ieee = priv->ieee80211;
255 switch (channel_plan)
257 case COUNTRY_CODE_FCC:
258 case COUNTRY_CODE_IC:
259 case COUNTRY_CODE_ETSI:
260 case COUNTRY_CODE_SPAIN:
261 case COUNTRY_CODE_FRANCE:
262 case COUNTRY_CODE_MKK:
263 case COUNTRY_CODE_MKK1:
264 case COUNTRY_CODE_ISRAEL:
265 case COUNTRY_CODE_TELEC:
266 case COUNTRY_CODE_MIC:
268 Dot11d_Init(ieee);
269 ieee->bGlobalDomain = false;
270 //acturally 8225 & 8256 rf chip only support B,G,24N mode
271 if ((priv->rf_chip == RF_8225) || (priv->rf_chip == RF_8256) || (priv->rf_chip == RF_6052))
273 min_chan = 1;
274 max_chan = 14;
276 else
278 RT_TRACE(COMP_ERR, "unknown rf chip, can't set channel map in function:%s()\n", __FUNCTION__);
280 if (ChannelPlan[channel_plan].Len != 0){
281 // Clear old channel map
282 memset(GET_DOT11D_INFO(ieee)->channel_map, 0, sizeof(GET_DOT11D_INFO(ieee)->channel_map));
283 // Set new channel map
284 for (i=0;i<ChannelPlan[channel_plan].Len;i++)
286 if (ChannelPlan[channel_plan].Channel[i] < min_chan || ChannelPlan[channel_plan].Channel[i] > max_chan)
287 break;
288 GET_DOT11D_INFO(ieee)->channel_map[ChannelPlan[channel_plan].Channel[i]] = 1;
291 break;
293 case COUNTRY_CODE_GLOBAL_DOMAIN:
295 GET_DOT11D_INFO(ieee)->bEnabled = 0;//this flag enabled to follow 11d country IE setting, otherwise, it shall follow global domain settings.
296 Dot11d_Reset(ieee);
297 ieee->bGlobalDomain = true;
298 break;
300 default:
301 break;
303 return;
306 #define eqMacAddr(a,b) ( ((a)[0]==(b)[0] && (a)[1]==(b)[1] && (a)[2]==(b)[2] && (a)[3]==(b)[3] && (a)[4]==(b)[4] && (a)[5]==(b)[5]) ? 1:0 )
308 #define rx_hal_is_cck_rate(_pDesc)\
309 ((_pDesc->RxMCS == DESC92S_RATE1M ||\
310 _pDesc->RxMCS == DESC92S_RATE2M ||\
311 _pDesc->RxMCS == DESC92S_RATE5_5M ||\
312 _pDesc->RxMCS == DESC92S_RATE11M) &&\
313 !_pDesc->RxHT)
315 #define tx_hal_is_cck_rate(_DataRate)\
316 ( _DataRate == MGN_1M ||\
317 _DataRate == MGN_2M ||\
318 _DataRate == MGN_5_5M ||\
319 _DataRate == MGN_11M )
324 void CamResetAllEntry(struct net_device *dev)
326 #if 1
327 u32 ulcommand = 0;
328 //2004/02/11 In static WEP, OID_ADD_KEY or OID_ADD_WEP are set before STA associate to AP.
329 // However, ResetKey is called on OID_802_11_INFRASTRUCTURE_MODE and MlmeAssociateRequest
330 // In this condition, Cam can not be reset because upper layer will not set this static key again.
331 //if(Adapter->EncAlgorithm == WEP_Encryption)
332 // return;
333 //debug
334 //DbgPrint("========================================\n");
335 //DbgPrint(" Call ResetAllEntry \n");
336 //DbgPrint("========================================\n\n");
337 ulcommand |= BIT31|BIT30;
338 write_nic_dword(dev, RWCAM, ulcommand);
339 #else
340 for(ucIndex=0;ucIndex<TOTAL_CAM_ENTRY;ucIndex++)
341 CAM_mark_invalid(dev, ucIndex);
342 for(ucIndex=0;ucIndex<TOTAL_CAM_ENTRY;ucIndex++)
343 CAM_empty_entry(dev, ucIndex);
344 #endif
349 void write_cam(struct net_device *dev, u8 addr, u32 data)
351 write_nic_dword(dev, WCAMI, data);
352 write_nic_dword(dev, RWCAM, BIT31|BIT16|(addr&0xff) );
355 u32 read_cam(struct net_device *dev, u8 addr)
357 write_nic_dword(dev, RWCAM, 0x80000000|(addr&0xff) );
358 return read_nic_dword(dev, 0xa8);
361 void write_nic_byte_E(struct net_device *dev, int indx, u8 data)
363 int status;
364 struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
365 struct usb_device *udev = priv->udev;
367 status = usb_control_msg(udev, usb_sndctrlpipe(udev, 0),
368 RTL8187_REQ_SET_REGS, RTL8187_REQT_WRITE,
369 indx|0xfe00, 0, &data, 1, HZ / 2);
371 if (status < 0)
373 printk("write_nic_byte_E TimeOut! status:%d\n", status);
377 u8 read_nic_byte_E(struct net_device *dev, int indx)
379 int status;
380 u8 data;
381 struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
382 struct usb_device *udev = priv->udev;
384 status = usb_control_msg(udev, usb_rcvctrlpipe(udev, 0),
385 RTL8187_REQ_GET_REGS, RTL8187_REQT_READ,
386 indx|0xfe00, 0, &data, 1, HZ / 2);
388 if (status < 0)
390 printk("read_nic_byte_E TimeOut! status:%d\n", status);
393 return data;
395 //as 92U has extend page from 4 to 16, so modify functions below.
396 void write_nic_byte(struct net_device *dev, int indx, u8 data)
398 int status;
400 struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
401 struct usb_device *udev = priv->udev;
403 status = usb_control_msg(udev, usb_sndctrlpipe(udev, 0),
404 RTL8187_REQ_SET_REGS, RTL8187_REQT_WRITE,
405 indx, 0, &data, 1, HZ / 2);
407 if (status < 0)
409 printk("write_nic_byte TimeOut! status:%d\n", status);
416 void write_nic_word(struct net_device *dev, int indx, u16 data)
419 int status;
421 struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
422 struct usb_device *udev = priv->udev;
424 status = usb_control_msg(udev, usb_sndctrlpipe(udev, 0),
425 RTL8187_REQ_SET_REGS, RTL8187_REQT_WRITE,
426 indx, 0, &data, 2, HZ / 2);
428 if (status < 0)
430 printk("write_nic_word TimeOut! status:%d\n", status);
436 void write_nic_dword(struct net_device *dev, int indx, u32 data)
439 int status;
441 struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
442 struct usb_device *udev = priv->udev;
444 status = usb_control_msg(udev, usb_sndctrlpipe(udev, 0),
445 RTL8187_REQ_SET_REGS, RTL8187_REQT_WRITE,
446 indx, 0, &data, 4, HZ / 2);
449 if (status < 0)
451 printk("write_nic_dword TimeOut! status:%d\n", status);
458 u8 read_nic_byte(struct net_device *dev, int indx)
460 u8 data;
461 int status;
462 struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
463 struct usb_device *udev = priv->udev;
465 status = usb_control_msg(udev, usb_rcvctrlpipe(udev, 0),
466 RTL8187_REQ_GET_REGS, RTL8187_REQT_READ,
467 indx, 0, &data, 1, HZ / 2);
469 if (status < 0)
471 printk("read_nic_byte TimeOut! status:%d\n", status);
474 return data;
479 u16 read_nic_word(struct net_device *dev, int indx)
481 u16 data;
482 int status;
483 struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
484 struct usb_device *udev = priv->udev;
486 status = usb_control_msg(udev, usb_rcvctrlpipe(udev, 0),
487 RTL8187_REQ_GET_REGS, RTL8187_REQT_READ,
488 indx, 0, &data, 2, HZ / 2);
490 if (status < 0)
492 printk("read_nic_word TimeOut! status:%d\n", status);
496 return data;
499 u16 read_nic_word_E(struct net_device *dev, int indx)
501 u16 data;
502 int status;
503 struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
504 struct usb_device *udev = priv->udev;
506 status = usb_control_msg(udev, usb_rcvctrlpipe(udev, 0),
507 RTL8187_REQ_GET_REGS, RTL8187_REQT_READ,
508 indx|0xfe00, 0, &data, 2, HZ / 2);
510 if (status < 0)
512 printk("read_nic_word TimeOut! status:%d\n", status);
516 return data;
519 u32 read_nic_dword(struct net_device *dev, int indx)
521 u32 data;
522 int status;
523 // int result;
525 struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
526 struct usb_device *udev = priv->udev;
528 status = usb_control_msg(udev, usb_rcvctrlpipe(udev, 0),
529 RTL8187_REQ_GET_REGS, RTL8187_REQT_READ,
530 indx, 0, &data, 4, HZ / 2);
531 // if(0 != result) {
532 // printk(KERN_WARNING "read size of data = %d\, date = %d\n", result, data);
533 // }
535 if (status < 0)
537 printk("read_nic_dword TimeOut! status:%d\n", status);
538 if(status == -ENODEV) {
539 priv->usb_error = true;
545 return data;
549 //u8 read_phy_cck(struct net_device *dev, u8 adr);
550 //u8 read_phy_ofdm(struct net_device *dev, u8 adr);
551 /* this might still called in what was the PHY rtl8185/rtl8192 common code
552 * plans are to possibilty turn it again in one common code...
554 inline void force_pci_posting(struct net_device *dev)
559 static struct net_device_stats *rtl8192_stats(struct net_device *dev);
560 void rtl8192_commit(struct net_device *dev);
561 //void rtl8192_restart(struct net_device *dev);
562 void rtl8192_restart(struct work_struct *work);
563 //void rtl8192_rq_tx_ack(struct work_struct *work);
565 void watch_dog_timer_callback(unsigned long data);
567 /****************************************************************************
568 -----------------------------PROCFS STUFF-------------------------
569 *****************************************************************************/
571 static struct proc_dir_entry *rtl8192_proc = NULL;
575 static int proc_get_stats_ap(char *page, char **start,
576 off_t offset, int count,
577 int *eof, void *data)
579 struct net_device *dev = data;
580 struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
581 struct ieee80211_device *ieee = priv->ieee80211;
582 struct ieee80211_network *target;
584 int len = 0;
586 list_for_each_entry(target, &ieee->network_list, list) {
588 len += snprintf(page + len, count - len,
589 "%s ", target->ssid);
591 if(target->wpa_ie_len>0 || target->rsn_ie_len>0){
592 len += snprintf(page + len, count - len,
593 "WPA\n");
595 else{
596 len += snprintf(page + len, count - len,
597 "non_WPA\n");
602 *eof = 1;
603 return len;
606 static int proc_get_registers(char *page, char **start,
607 off_t offset, int count,
608 int *eof, void *data)
610 struct net_device *dev = data;
611 // struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
613 int len = 0;
614 int i,n,page0,page1,page2;
616 int max=0xff;
617 page0 = 0x000;
618 page1 = 0x100;
619 page2 = 0x800;
621 /* This dump the current register page */
622 if(!IS_BB_REG_OFFSET_92S(page0)){
623 len += snprintf(page + len, count - len,
624 "\n####################page %x##################\n ", (page0>>8));
625 for(n=0;n<=max;)
627 len += snprintf(page + len, count - len,
628 "\nD: %2x > ",n);
629 for(i=0;i<16 && n<=max;i++,n++)
630 len += snprintf(page + len, count - len,
631 "%2.2x ",read_nic_byte(dev,(page0|n)));
633 }else{
634 len += snprintf(page + len, count - len,
635 "\n####################page %x##################\n ", (page0>>8));
636 for(n=0;n<=max;)
638 len += snprintf(page + len, count - len, "\nD: %2x > ",n);
639 for(i=0;i<4 && n<=max;n+=4,i++)
640 len += snprintf(page + len, count - len,
641 "%8.8x ",rtl8192_QueryBBReg(dev,(page0|n), bMaskDWord));
644 len += snprintf(page + len, count - len,"\n");
645 *eof = 1;
646 return len;
649 static int proc_get_registers_1(char *page, char **start,
650 off_t offset, int count,
651 int *eof, void *data)
653 struct net_device *dev = data;
654 // struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
656 int len = 0;
657 int i,n,page0;
659 int max=0xff;
660 page0 = 0x100;
662 /* This dump the current register page */
663 len += snprintf(page + len, count - len,
664 "\n####################page %x##################\n ", (page0>>8));
665 for(n=0;n<=max;)
667 len += snprintf(page + len, count - len,
668 "\nD: %2x > ",n);
669 for(i=0;i<16 && n<=max;i++,n++)
670 len += snprintf(page + len, count - len,
671 "%2.2x ",read_nic_byte(dev,(page0|n)));
673 len += snprintf(page + len, count - len,"\n");
674 *eof = 1;
675 return len;
678 static int proc_get_registers_2(char *page, char **start,
679 off_t offset, int count,
680 int *eof, void *data)
682 struct net_device *dev = data;
683 // struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
685 int len = 0;
686 int i,n,page0;
688 int max=0xff;
689 page0 = 0x200;
691 /* This dump the current register page */
692 len += snprintf(page + len, count - len,
693 "\n####################page %x##################\n ", (page0>>8));
694 for(n=0;n<=max;)
696 len += snprintf(page + len, count - len,
697 "\nD: %2x > ",n);
698 for(i=0;i<16 && n<=max;i++,n++)
699 len += snprintf(page + len, count - len,
700 "%2.2x ",read_nic_byte(dev,(page0|n)));
702 len += snprintf(page + len, count - len,"\n");
703 *eof = 1;
704 return len;
707 static int proc_get_registers_8(char *page, char **start,
708 off_t offset, int count,
709 int *eof, void *data)
711 struct net_device *dev = data;
713 int len = 0;
714 int i,n,page0;
716 int max=0xff;
717 page0 = 0x800;
719 /* This dump the current register page */
720 len += snprintf(page + len, count - len,
721 "\n####################page %x##################\n ", (page0>>8));
722 for(n=0;n<=max;)
724 len += snprintf(page + len, count - len, "\nD: %2x > ",n);
725 for(i=0;i<4 && n<=max;n+=4,i++)
726 len += snprintf(page + len, count - len,
727 "%8.8x ",rtl8192_QueryBBReg(dev,(page0|n), bMaskDWord));
729 len += snprintf(page + len, count - len,"\n");
730 *eof = 1;
731 return len;
734 static int proc_get_registers_9(char *page, char **start,
735 off_t offset, int count,
736 int *eof, void *data)
738 struct net_device *dev = data;
739 // struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
741 int len = 0;
742 int i,n,page0;
744 int max=0xff;
745 page0 = 0x900;
747 /* This dump the current register page */
748 len += snprintf(page + len, count - len,
749 "\n####################page %x##################\n ", (page0>>8));
750 for(n=0;n<=max;)
752 len += snprintf(page + len, count - len, "\nD: %2x > ",n);
753 for(i=0;i<4 && n<=max;n+=4,i++)
754 len += snprintf(page + len, count - len,
755 "%8.8x ",rtl8192_QueryBBReg(dev,(page0|n), bMaskDWord));
757 len += snprintf(page + len, count - len,"\n");
758 *eof = 1;
759 return len;
761 static int proc_get_registers_a(char *page, char **start,
762 off_t offset, int count,
763 int *eof, void *data)
765 struct net_device *dev = data;
766 // struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
768 int len = 0;
769 int i,n,page0;
771 int max=0xff;
772 page0 = 0xa00;
774 /* This dump the current register page */
775 len += snprintf(page + len, count - len,
776 "\n####################page %x##################\n ", (page0>>8));
777 for(n=0;n<=max;)
779 len += snprintf(page + len, count - len, "\nD: %2x > ",n);
780 for(i=0;i<4 && n<=max;n+=4,i++)
781 len += snprintf(page + len, count - len,
782 "%8.8x ",rtl8192_QueryBBReg(dev,(page0|n), bMaskDWord));
784 len += snprintf(page + len, count - len,"\n");
785 *eof = 1;
786 return len;
788 static int proc_get_registers_b(char *page, char **start,
789 off_t offset, int count,
790 int *eof, void *data)
792 struct net_device *dev = data;
793 // struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
795 int len = 0;
796 int i,n,page0;
798 int max=0xff;
799 page0 = 0xb00;
801 /* This dump the current register page */
802 len += snprintf(page + len, count - len,
803 "\n####################page %x##################\n ", (page0>>8));
804 for(n=0;n<=max;)
806 len += snprintf(page + len, count - len, "\nD: %2x > ",n);
807 for(i=0;i<4 && n<=max;n+=4,i++)
808 len += snprintf(page + len, count - len,
809 "%8.8x ",rtl8192_QueryBBReg(dev,(page0|n), bMaskDWord));
811 len += snprintf(page + len, count - len,"\n");
812 *eof = 1;
813 return len;
815 static int proc_get_registers_c(char *page, char **start,
816 off_t offset, int count,
817 int *eof, void *data)
819 struct net_device *dev = data;
820 // struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
822 int len = 0;
823 int i,n,page0;
825 int max=0xff;
826 page0 = 0xc00;
828 /* This dump the current register page */
829 len += snprintf(page + len, count - len,
830 "\n####################page %x##################\n ", (page0>>8));
831 for(n=0;n<=max;)
833 len += snprintf(page + len, count - len, "\nD: %2x > ",n);
834 for(i=0;i<4 && n<=max;n+=4,i++)
835 len += snprintf(page + len, count - len,
836 "%8.8x ",rtl8192_QueryBBReg(dev,(page0|n), bMaskDWord));
838 len += snprintf(page + len, count - len,"\n");
839 *eof = 1;
840 return len;
842 static int proc_get_registers_d(char *page, char **start,
843 off_t offset, int count,
844 int *eof, void *data)
846 struct net_device *dev = data;
847 // struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
849 int len = 0;
850 int i,n,page0;
852 int max=0xff;
853 page0 = 0xd00;
855 /* This dump the current register page */
856 len += snprintf(page + len, count - len,
857 "\n####################page %x##################\n ", (page0>>8));
858 for(n=0;n<=max;)
860 len += snprintf(page + len, count - len, "\nD: %2x > ",n);
861 for(i=0;i<4 && n<=max;n+=4,i++)
862 len += snprintf(page + len, count - len,
863 "%8.8x ",rtl8192_QueryBBReg(dev,(page0|n), bMaskDWord));
865 len += snprintf(page + len, count - len,"\n");
866 *eof = 1;
867 return len;
869 static int proc_get_registers_e(char *page, char **start,
870 off_t offset, int count,
871 int *eof, void *data)
873 struct net_device *dev = data;
874 // struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
876 int len = 0;
877 int i,n,page0;
879 int max=0xff;
880 page0 = 0xe00;
882 /* This dump the current register page */
883 len += snprintf(page + len, count - len,
884 "\n####################page %x##################\n ", (page0>>8));
885 for(n=0;n<=max;)
887 len += snprintf(page + len, count - len, "\nD: %2x > ",n);
888 for(i=0;i<4 && n<=max;n+=4,i++)
889 len += snprintf(page + len, count - len,
890 "%8.8x ",rtl8192_QueryBBReg(dev,(page0|n), bMaskDWord));
892 len += snprintf(page + len, count - len,"\n");
893 *eof = 1;
894 return len;
897 static int proc_get_stats_tx(char *page, char **start,
898 off_t offset, int count,
899 int *eof, void *data)
901 struct net_device *dev = data;
902 struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
904 int len = 0;
906 len += snprintf(page + len, count - len,
907 "TX VI priority ok int: %lu\n"
908 "TX VI priority error int: %lu\n"
909 "TX VO priority ok int: %lu\n"
910 "TX VO priority error int: %lu\n"
911 "TX BE priority ok int: %lu\n"
912 "TX BE priority error int: %lu\n"
913 "TX BK priority ok int: %lu\n"
914 "TX BK priority error int: %lu\n"
915 "TX MANAGE priority ok int: %lu\n"
916 "TX MANAGE priority error int: %lu\n"
917 "TX BEACON priority ok int: %lu\n"
918 "TX BEACON priority error int: %lu\n"
919 // "TX high priority ok int: %lu\n"
920 // "TX high priority failed error int: %lu\n"
921 "TX queue resume: %lu\n"
922 "TX queue stopped?: %d\n"
923 "TX fifo overflow: %lu\n"
924 // "TX beacon: %lu\n"
925 "TX VI queue: %d\n"
926 "TX VO queue: %d\n"
927 "TX BE queue: %d\n"
928 "TX BK queue: %d\n"
929 // "TX HW queue: %d\n"
930 "TX VI dropped: %lu\n"
931 "TX VO dropped: %lu\n"
932 "TX BE dropped: %lu\n"
933 "TX BK dropped: %lu\n"
934 "TX total data packets %lu\n",
935 // "TX beacon aborted: %lu\n",
936 priv->stats.txviokint,
937 priv->stats.txvierr,
938 priv->stats.txvookint,
939 priv->stats.txvoerr,
940 priv->stats.txbeokint,
941 priv->stats.txbeerr,
942 priv->stats.txbkokint,
943 priv->stats.txbkerr,
944 priv->stats.txmanageokint,
945 priv->stats.txmanageerr,
946 priv->stats.txbeaconokint,
947 priv->stats.txbeaconerr,
948 // priv->stats.txhpokint,
949 // priv->stats.txhperr,
950 priv->stats.txresumed,
951 netif_queue_stopped(dev),
952 priv->stats.txoverflow,
953 // priv->stats.txbeacon,
954 atomic_read(&(priv->tx_pending[VI_PRIORITY])),
955 atomic_read(&(priv->tx_pending[VO_PRIORITY])),
956 atomic_read(&(priv->tx_pending[BE_PRIORITY])),
957 atomic_read(&(priv->tx_pending[BK_PRIORITY])),
958 // read_nic_byte(dev, TXFIFOCOUNT),
959 priv->stats.txvidrop,
960 priv->stats.txvodrop,
961 priv->stats.txbedrop,
962 priv->stats.txbkdrop,
963 priv->stats.txdatapkt
964 // priv->stats.txbeaconerr
967 *eof = 1;
968 return len;
973 static int proc_get_stats_rx(char *page, char **start,
974 off_t offset, int count,
975 int *eof, void *data)
977 struct net_device *dev = data;
978 struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
980 int len = 0;
982 len += snprintf(page + len, count - len,
983 "RX packets: %lu\n"
984 "RX urb status error: %lu\n"
985 "RX invalid urb error: %lu\n",
986 priv->stats.rxoktotal,
987 priv->stats.rxstaterr,
988 priv->stats.rxurberr);
990 *eof = 1;
991 return len;
994 void rtl8192_proc_module_init(void)
996 RT_TRACE(COMP_INIT, "Initializing proc filesystem");
997 rtl8192_proc=create_proc_entry(RTL819xU_MODULE_NAME, S_IFDIR, init_net.proc_net);
1001 void rtl8192_proc_module_remove(void)
1003 remove_proc_entry(RTL819xU_MODULE_NAME, init_net.proc_net);
1007 void rtl8192_proc_remove_one(struct net_device *dev)
1009 struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
1012 if (priv->dir_dev) {
1013 // remove_proc_entry("stats-hw", priv->dir_dev);
1014 remove_proc_entry("stats-tx", priv->dir_dev);
1015 remove_proc_entry("stats-rx", priv->dir_dev);
1016 // remove_proc_entry("stats-ieee", priv->dir_dev);
1017 remove_proc_entry("stats-ap", priv->dir_dev);
1018 remove_proc_entry("registers", priv->dir_dev);
1019 remove_proc_entry("registers-1", priv->dir_dev);
1020 remove_proc_entry("registers-2", priv->dir_dev);
1021 remove_proc_entry("registers-8", priv->dir_dev);
1022 remove_proc_entry("registers-9", priv->dir_dev);
1023 remove_proc_entry("registers-a", priv->dir_dev);
1024 remove_proc_entry("registers-b", priv->dir_dev);
1025 remove_proc_entry("registers-c", priv->dir_dev);
1026 remove_proc_entry("registers-d", priv->dir_dev);
1027 remove_proc_entry("registers-e", priv->dir_dev);
1028 // remove_proc_entry("cck-registers",priv->dir_dev);
1029 // remove_proc_entry("ofdm-registers",priv->dir_dev);
1030 //remove_proc_entry(dev->name, rtl8192_proc);
1031 remove_proc_entry("wlan0", rtl8192_proc);
1032 priv->dir_dev = NULL;
1037 void rtl8192_proc_init_one(struct net_device *dev)
1039 struct proc_dir_entry *e;
1040 struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
1041 priv->dir_dev = create_proc_entry(dev->name,
1042 S_IFDIR | S_IRUGO | S_IXUGO,
1043 rtl8192_proc);
1044 if (!priv->dir_dev) {
1045 RT_TRACE(COMP_ERR, "Unable to initialize /proc/net/rtl8192/%s\n",
1046 dev->name);
1047 return;
1049 e = create_proc_read_entry("stats-rx", S_IFREG | S_IRUGO,
1050 priv->dir_dev, proc_get_stats_rx, dev);
1052 if (!e) {
1053 RT_TRACE(COMP_ERR,"Unable to initialize "
1054 "/proc/net/rtl8192/%s/stats-rx\n",
1055 dev->name);
1059 e = create_proc_read_entry("stats-tx", S_IFREG | S_IRUGO,
1060 priv->dir_dev, proc_get_stats_tx, dev);
1062 if (!e) {
1063 RT_TRACE(COMP_ERR, "Unable to initialize "
1064 "/proc/net/rtl8192/%s/stats-tx\n",
1065 dev->name);
1068 e = create_proc_read_entry("stats-ap", S_IFREG | S_IRUGO,
1069 priv->dir_dev, proc_get_stats_ap, dev);
1071 if (!e) {
1072 RT_TRACE(COMP_ERR, "Unable to initialize "
1073 "/proc/net/rtl8192/%s/stats-ap\n",
1074 dev->name);
1077 e = create_proc_read_entry("registers", S_IFREG | S_IRUGO,
1078 priv->dir_dev, proc_get_registers, dev);
1079 if (!e) {
1080 RT_TRACE(COMP_ERR, "Unable to initialize "
1081 "/proc/net/rtl8192/%s/registers\n",
1082 dev->name);
1084 e = create_proc_read_entry("registers-1", S_IFREG | S_IRUGO,
1085 priv->dir_dev, proc_get_registers_1, dev);
1086 if (!e) {
1087 RT_TRACE(COMP_ERR, "Unable to initialize "
1088 "/proc/net/rtl8192/%s/registers-1\n",
1089 dev->name);
1091 e = create_proc_read_entry("registers-2", S_IFREG | S_IRUGO,
1092 priv->dir_dev, proc_get_registers_2, dev);
1093 if (!e) {
1094 RT_TRACE(COMP_ERR, "Unable to initialize "
1095 "/proc/net/rtl8192/%s/registers-2\n",
1096 dev->name);
1098 e = create_proc_read_entry("registers-8", S_IFREG | S_IRUGO,
1099 priv->dir_dev, proc_get_registers_8, dev);
1100 if (!e) {
1101 RT_TRACE(COMP_ERR, "Unable to initialize "
1102 "/proc/net/rtl8192/%s/registers-8\n",
1103 dev->name);
1105 e = create_proc_read_entry("registers-9", S_IFREG | S_IRUGO,
1106 priv->dir_dev, proc_get_registers_9, dev);
1107 if (!e) {
1108 RT_TRACE(COMP_ERR, "Unable to initialize "
1109 "/proc/net/rtl8192/%s/registers-9\n",
1110 dev->name);
1112 e = create_proc_read_entry("registers-a", S_IFREG | S_IRUGO,
1113 priv->dir_dev, proc_get_registers_a, dev);
1114 if (!e) {
1115 RT_TRACE(COMP_ERR, "Unable to initialize "
1116 "/proc/net/rtl8192/%s/registers-a\n",
1117 dev->name);
1119 e = create_proc_read_entry("registers-b", S_IFREG | S_IRUGO,
1120 priv->dir_dev, proc_get_registers_b, dev);
1121 if (!e) {
1122 RT_TRACE(COMP_ERR, "Unable to initialize "
1123 "/proc/net/rtl8192/%s/registers-b\n",
1124 dev->name);
1126 e = create_proc_read_entry("registers-c", S_IFREG | S_IRUGO,
1127 priv->dir_dev, proc_get_registers_c, dev);
1128 if (!e) {
1129 RT_TRACE(COMP_ERR, "Unable to initialize "
1130 "/proc/net/rtl8192/%s/registers-c\n",
1131 dev->name);
1133 e = create_proc_read_entry("registers-d", S_IFREG | S_IRUGO,
1134 priv->dir_dev, proc_get_registers_d, dev);
1135 if (!e) {
1136 RT_TRACE(COMP_ERR, "Unable to initialize "
1137 "/proc/net/rtl8192/%s/registers-d\n",
1138 dev->name);
1140 e = create_proc_read_entry("registers-e", S_IFREG | S_IRUGO,
1141 priv->dir_dev, proc_get_registers_e, dev);
1142 if (!e) {
1143 RT_TRACE(COMP_ERR, "Unable to initialize "
1144 "/proc/net/rtl8192/%s/registers-e\n",
1145 dev->name);
1148 /****************************************************************************
1149 -----------------------------MISC STUFF-------------------------
1150 *****************************************************************************/
1152 /* this is only for debugging */
1153 void print_buffer(u32 *buffer, int len)
1155 int i;
1156 u8 *buf =(u8*)buffer;
1158 printk("ASCII BUFFER DUMP (len: %x):\n",len);
1160 for(i=0;i<len;i++)
1161 printk("%c",buf[i]);
1163 printk("\nBINARY BUFFER DUMP (len: %x):\n",len);
1165 for(i=0;i<len;i++)
1166 printk("%x",buf[i]);
1168 printk("\n");
1171 //short check_nic_enough_desc(struct net_device *dev, priority_t priority)
1172 short check_nic_enough_desc(struct net_device *dev,int queue_index)
1174 struct r8192_priv *priv = ieee80211_priv(dev);
1175 int used = atomic_read(&priv->tx_pending[queue_index]);
1177 return (used < MAX_TX_URB);
1180 void tx_timeout(struct net_device *dev)
1182 struct r8192_priv *priv = ieee80211_priv(dev);
1183 //rtl8192_commit(dev);
1185 schedule_work(&priv->reset_wq);
1186 //DMESG("TXTIMEOUT");
1189 /* this is only for debug */
1190 void rtl8192_dump_reg(struct net_device *dev)
1192 int i;
1193 int n;
1194 int max=0x1ff;
1196 RT_TRACE(COMP_PHY, "Dumping NIC register map");
1198 for(n=0;n<=max;)
1200 printk( "\nD: %2x> ", n);
1201 for(i=0;i<16 && n<=max;i++,n++)
1202 printk("%2x ",read_nic_byte(dev,n));
1204 printk("\n");
1207 /****************************************************************************
1208 ------------------------------HW STUFF---------------------------
1209 *****************************************************************************/
1211 void rtl8192_set_mode(struct net_device *dev,int mode)
1213 u8 ecmd;
1214 ecmd=read_nic_byte(dev, EPROM_CMD);
1215 ecmd=ecmd &~ EPROM_CMD_OPERATING_MODE_MASK;
1216 ecmd=ecmd | (mode<<EPROM_CMD_OPERATING_MODE_SHIFT);
1217 ecmd=ecmd &~ (1<<EPROM_CS_SHIFT);
1218 ecmd=ecmd &~ (1<<EPROM_CK_SHIFT);
1219 write_nic_byte(dev, EPROM_CMD, ecmd);
1223 void rtl8192_update_msr(struct net_device *dev)
1225 struct r8192_priv *priv = ieee80211_priv(dev);
1226 LED_CTL_MODE LedAction = LED_CTL_NO_LINK;
1227 u8 msr;
1229 msr = read_nic_byte(dev, MSR);
1230 msr &= ~ MSR_LINK_MASK;
1232 /* do not change in link_state != WLAN_LINK_ASSOCIATED.
1233 * msr must be updated if the state is ASSOCIATING.
1234 * this is intentional and make sense for ad-hoc and
1235 * master (see the create BSS/IBSS func)
1237 if (priv->ieee80211->state == IEEE80211_LINKED) {
1239 if (priv->ieee80211->iw_mode == IW_MODE_INFRA) {
1240 msr |= (MSR_LINK_MANAGED<<MSR_LINK_SHIFT);
1241 LedAction = LED_CTL_LINK;
1242 } else if (priv->ieee80211->iw_mode == IW_MODE_ADHOC)
1243 msr |= (MSR_LINK_ADHOC<<MSR_LINK_SHIFT);
1244 else if (priv->ieee80211->iw_mode == IW_MODE_MASTER)
1245 msr |= (MSR_LINK_MASTER<<MSR_LINK_SHIFT);
1247 } else
1248 msr |= (MSR_LINK_NONE<<MSR_LINK_SHIFT);
1250 write_nic_byte(dev, MSR, msr);
1252 if(priv->ieee80211->LedControlHandler != NULL)
1253 priv->ieee80211->LedControlHandler(dev, LedAction);
1256 void rtl8192_set_chan(struct net_device *dev,short ch)
1258 struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
1259 // u32 tx;
1260 RT_TRACE(COMP_CH, "=====>%s()====ch:%d\n", __FUNCTION__, ch);
1261 //printk("=====>%s()====ch:%d\n", __FUNCTION__, ch);
1262 priv->chan=ch;
1264 /* this hack should avoid frame TX during channel setting*/
1267 // tx = read_nic_dword(dev,TX_CONF);
1268 // tx &= ~TX_LOOPBACK_MASK;
1270 #ifndef LOOP_TEST
1271 // write_nic_dword(dev,TX_CONF, tx |( TX_LOOPBACK_MAC<<TX_LOOPBACK_SHIFT));
1273 //need to implement rf set channel here WB
1275 if (priv->rf_set_chan)
1276 priv->rf_set_chan(dev,priv->chan);
1277 mdelay(10);
1278 // write_nic_dword(dev,TX_CONF,tx | (TX_LOOPBACK_NONE<<TX_LOOPBACK_SHIFT));
1279 #endif
1282 static void rtl8192_rx_isr(struct urb *urb);
1284 u32 get_rxpacket_shiftbytes_819xusb(struct ieee80211_rx_stats *pstats)
1287 return (sizeof(rx_desc_819x_usb) + pstats->RxDrvInfoSize
1288 + pstats->RxBufShift);
1291 static int rtl8192_rx_initiate(struct net_device*dev)
1293 struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
1294 struct urb *entry;
1295 struct sk_buff *skb;
1296 struct rtl8192_rx_info *info;
1298 /* nomal packet rx procedure */
1299 while (skb_queue_len(&priv->rx_queue) < MAX_RX_URB) {
1300 skb = __dev_alloc_skb(RX_URB_SIZE, GFP_KERNEL);
1301 if (!skb)
1302 break;
1303 entry = usb_alloc_urb(0, GFP_KERNEL);
1304 if (!entry) {
1305 kfree_skb(skb);
1306 break;
1308 usb_fill_bulk_urb(entry, priv->udev,
1309 usb_rcvbulkpipe(priv->udev, 3), skb_tail_pointer(skb),
1310 RX_URB_SIZE, rtl8192_rx_isr, skb);
1311 info = (struct rtl8192_rx_info *) skb->cb;
1312 info->urb = entry;
1313 info->dev = dev;
1314 info->out_pipe = 3; //denote rx normal packet queue
1315 skb_queue_tail(&priv->rx_queue, skb);
1316 usb_submit_urb(entry, GFP_KERNEL);
1319 /* command packet rx procedure */
1320 while (skb_queue_len(&priv->rx_queue) < MAX_RX_URB + 3) {
1321 skb = __dev_alloc_skb(RX_URB_SIZE ,GFP_KERNEL);
1322 if (!skb)
1323 break;
1324 entry = usb_alloc_urb(0, GFP_KERNEL);
1325 if (!entry) {
1326 kfree_skb(skb);
1327 break;
1329 usb_fill_bulk_urb(entry, priv->udev,
1330 usb_rcvbulkpipe(priv->udev, 9), skb_tail_pointer(skb),
1331 RX_URB_SIZE, rtl8192_rx_isr, skb);
1332 info = (struct rtl8192_rx_info *) skb->cb;
1333 info->urb = entry;
1334 info->dev = dev;
1335 info->out_pipe = 9; //denote rx cmd packet queue
1336 skb_queue_tail(&priv->rx_queue, skb);
1337 usb_submit_urb(entry, GFP_KERNEL);
1340 return 0;
1343 void rtl8192_set_rxconf(struct net_device *dev)
1345 struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
1346 u32 rxconf;
1348 rxconf=read_nic_dword(dev,RCR);
1349 rxconf = rxconf &~ MAC_FILTER_MASK;
1350 rxconf = rxconf | RCR_AMF;
1351 rxconf = rxconf | RCR_ADF;
1352 rxconf = rxconf | RCR_AB;
1353 rxconf = rxconf | RCR_AM;
1354 //rxconf = rxconf | RCR_ACF;
1356 if (dev->flags & IFF_PROMISC) {DMESG ("NIC in promisc mode");}
1358 if(priv->ieee80211->iw_mode == IW_MODE_MONITOR || \
1359 dev->flags & IFF_PROMISC){
1360 rxconf = rxconf | RCR_AAP;
1361 } /*else if(priv->ieee80211->iw_mode == IW_MODE_MASTER){
1362 rxconf = rxconf | (1<<ACCEPT_ALLMAC_FRAME_SHIFT);
1363 rxconf = rxconf | (1<<RX_CHECK_BSSID_SHIFT);
1364 }*/else{
1365 rxconf = rxconf | RCR_APM;
1366 rxconf = rxconf | RCR_CBSSID;
1370 if(priv->ieee80211->iw_mode == IW_MODE_MONITOR){
1371 rxconf = rxconf | RCR_AICV;
1372 rxconf = rxconf | RCR_APWRMGT;
1375 if( priv->crcmon == 1 && priv->ieee80211->iw_mode == IW_MODE_MONITOR)
1376 rxconf = rxconf | RCR_ACRC32;
1379 rxconf = rxconf &~ RX_FIFO_THRESHOLD_MASK;
1380 rxconf = rxconf | (RX_FIFO_THRESHOLD_NONE<<RX_FIFO_THRESHOLD_SHIFT);
1381 rxconf = rxconf &~ MAX_RX_DMA_MASK;
1382 rxconf = rxconf | ((u32)7<<RCR_MXDMA_OFFSET);
1384 // rxconf = rxconf | (1<<RX_AUTORESETPHY_SHIFT);
1385 rxconf = rxconf | RCR_ONLYERLPKT;
1387 // rxconf = rxconf &~ RCR_CS_MASK;
1388 // rxconf = rxconf | (1<<RCR_CS_SHIFT);
1390 write_nic_dword(dev, RCR, rxconf);
1392 #ifdef DEBUG_RX
1393 DMESG("rxconf: %x %x",rxconf ,read_nic_dword(dev,RCR));
1394 #endif
1396 //wait to be removed
1397 void rtl8192_rx_enable(struct net_device *dev)
1399 //u8 cmd;
1401 //struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
1403 rtl8192_rx_initiate(dev);
1405 // rtl8192_set_rxconf(dev);
1409 void rtl8192_tx_enable(struct net_device *dev)
1413 void rtl8192_rtx_disable(struct net_device *dev)
1415 u8 cmd;
1416 struct r8192_priv *priv = ieee80211_priv(dev);
1417 struct sk_buff *skb;
1418 struct rtl8192_rx_info *info;
1420 cmd=read_nic_byte(dev,CMDR);
1421 write_nic_byte(dev, CMDR, cmd &~ \
1422 (CR_TE|CR_RE));
1423 force_pci_posting(dev);
1424 mdelay(10);
1426 while ((skb = __skb_dequeue(&priv->rx_queue))) {
1427 info = (struct rtl8192_rx_info *) skb->cb;
1428 if (!info->urb)
1429 continue;
1431 usb_kill_urb(info->urb);
1432 kfree_skb(skb);
1435 if (skb_queue_len(&priv->skb_queue)) {
1436 printk(KERN_WARNING "skb_queue not empty\n");
1439 skb_queue_purge(&priv->skb_queue);
1440 return;
1444 int alloc_tx_beacon_desc_ring(struct net_device *dev, int count)
1446 return 0;
1449 inline u16 ieeerate2rtlrate(int rate)
1451 switch(rate){
1452 case 10:
1453 return 0;
1454 case 20:
1455 return 1;
1456 case 55:
1457 return 2;
1458 case 110:
1459 return 3;
1460 case 60:
1461 return 4;
1462 case 90:
1463 return 5;
1464 case 120:
1465 return 6;
1466 case 180:
1467 return 7;
1468 case 240:
1469 return 8;
1470 case 360:
1471 return 9;
1472 case 480:
1473 return 10;
1474 case 540:
1475 return 11;
1476 default:
1477 return 3;
1481 static u16 rtl_rate[] = {10,20,55,110,60,90,120,180,240,360,480,540};
1482 inline u16 rtl8192_rate2rate(short rate)
1484 if (rate >11) return 0;
1485 return rtl_rate[rate];
1488 static void rtl8192_rx_isr(struct urb *urb)
1490 struct sk_buff *skb = (struct sk_buff *) urb->context;
1491 struct rtl8192_rx_info *info = (struct rtl8192_rx_info *)skb->cb;
1492 struct net_device *dev = info->dev;
1493 struct r8192_priv *priv = ieee80211_priv(dev);
1494 int out_pipe = info->out_pipe;
1495 int err;
1496 if(!priv->up)
1497 return;
1498 if (unlikely(urb->status)) {
1499 info->urb = NULL;
1500 priv->stats.rxstaterr++;
1501 priv->ieee80211->stats.rx_errors++;
1502 usb_free_urb(urb);
1503 // printk("%s():rx status err\n",__FUNCTION__);
1504 return;
1507 skb_unlink(skb, &priv->rx_queue);
1508 skb_put(skb, urb->actual_length);
1510 skb_queue_tail(&priv->skb_queue, skb);
1511 tasklet_schedule(&priv->irq_rx_tasklet);
1513 skb = dev_alloc_skb(RX_URB_SIZE);
1514 if (unlikely(!skb)) {
1515 usb_free_urb(urb);
1516 printk("%s():can,t alloc skb\n",__FUNCTION__);
1517 /* TODO check rx queue length and refill *somewhere* */
1518 return;
1521 usb_fill_bulk_urb(urb, priv->udev,
1522 usb_rcvbulkpipe(priv->udev, out_pipe),
1523 skb_tail_pointer(skb),
1524 RX_URB_SIZE, rtl8192_rx_isr, skb);
1526 info = (struct rtl8192_rx_info *) skb->cb;
1527 info->urb = urb;
1528 info->dev = dev;
1529 info->out_pipe = out_pipe;
1531 urb->transfer_buffer = skb_tail_pointer(skb);
1532 urb->context = skb;
1533 skb_queue_tail(&priv->rx_queue, skb);
1534 err = usb_submit_urb(urb, GFP_ATOMIC);
1535 if(err && err != -EPERM)
1536 printk("can not submit rxurb, err is %x,URB status is %x\n",err,urb->status);
1540 rtl819xusb_rx_command_packet(
1541 struct net_device *dev,
1542 struct ieee80211_rx_stats *pstats
1545 u32 status;
1547 //RT_TRACE(COMP_RECV, DBG_TRACE, ("---> RxCommandPacketHandle819xUsb()\n"));
1549 status = cmpk_message_handle_rx(dev, pstats);
1550 if (status)
1552 DMESG("rxcommandpackethandle819xusb: It is a command packet\n");
1554 else
1556 //RT_TRACE(COMP_RECV, DBG_TRACE, ("RxCommandPacketHandle819xUsb: It is not a command packet\n"));
1559 //RT_TRACE(COMP_RECV, DBG_TRACE, ("<--- RxCommandPacketHandle819xUsb()\n"));
1560 return status;
1563 void rtl8192_data_hard_stop(struct net_device *dev)
1565 //FIXME !!
1569 void rtl8192_data_hard_resume(struct net_device *dev)
1571 // FIXME !!
1574 /* this function TX data frames when the ieee80211 stack requires this.
1575 * It checks also if we need to stop the ieee tx queue, eventually do it
1577 void rtl8192_hard_data_xmit(struct sk_buff *skb, struct net_device *dev, int rate)
1579 struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
1580 int ret;
1581 unsigned long flags;
1582 cb_desc *tcb_desc = (cb_desc *)(skb->cb + MAX_DEV_ADDR_SIZE);
1583 u8 queue_index = tcb_desc->queue_index;
1585 /* shall not be referred by command packet */
1586 assert(queue_index != TXCMD_QUEUE);
1588 spin_lock_irqsave(&priv->tx_lock,flags);
1590 memcpy((unsigned char *)(skb->cb),&dev,sizeof(dev));
1591 // tcb_desc->RATRIndex = 7;
1592 // tcb_desc->bTxDisableRateFallBack = 1;
1593 // tcb_desc->bTxUseDriverAssingedRate = 1;
1594 tcb_desc->bTxEnableFwCalcDur = 1;
1595 skb_push(skb, priv->ieee80211->tx_headroom);
1596 ret = priv->ops->rtl819x_tx(dev, skb);
1598 //priv->ieee80211->stats.tx_bytes+=(skb->len - priv->ieee80211->tx_headroom);
1599 //priv->ieee80211->stats.tx_packets++;
1601 spin_unlock_irqrestore(&priv->tx_lock,flags);
1603 // return ret;
1604 return;
1607 /* This is a rough attempt to TX a frame
1608 * This is called by the ieee 80211 stack to TX management frames.
1609 * If the ring is full packet are dropped (for data frame the queue
1610 * is stopped before this can happen).
1612 int rtl8192_hard_start_xmit(struct sk_buff *skb,struct net_device *dev)
1614 struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
1615 int ret;
1616 unsigned long flags;
1617 cb_desc *tcb_desc = (cb_desc *)(skb->cb + MAX_DEV_ADDR_SIZE);
1618 u8 queue_index = tcb_desc->queue_index;
1621 spin_lock_irqsave(&priv->tx_lock,flags);
1623 memcpy((unsigned char *)(skb->cb),&dev,sizeof(dev));
1624 if(queue_index == TXCMD_QUEUE) {
1625 skb_push(skb, USB_HWDESC_HEADER_LEN);
1626 priv->ops->rtl819x_tx_cmd(dev, skb);
1627 ret = 1;
1628 spin_unlock_irqrestore(&priv->tx_lock,flags);
1629 return ret;
1630 } else {
1631 skb_push(skb, priv->ieee80211->tx_headroom);
1632 ret = priv->ops->rtl819x_tx(dev, skb);
1635 spin_unlock_irqrestore(&priv->tx_lock,flags);
1637 return ret;
1641 void rtl8192_try_wake_queue(struct net_device *dev, int pri);
1644 static void rtl8192_tx_isr(struct urb *tx_urb)
1646 struct sk_buff *skb = (struct sk_buff*)tx_urb->context;
1647 struct net_device *dev = NULL;
1648 struct r8192_priv *priv = NULL;
1649 cb_desc *tcb_desc = (cb_desc *)(skb->cb + MAX_DEV_ADDR_SIZE);
1650 u8 queue_index = tcb_desc->queue_index;
1651 // bool bToSend0Byte;
1652 // u16 BufLen = skb->len;
1654 memcpy(&dev,(struct net_device*)(skb->cb),sizeof(struct net_device*));
1655 priv = ieee80211_priv(dev);
1657 if(tcb_desc->queue_index != TXCMD_QUEUE) {
1658 if(tx_urb->status == 0) {
1659 // dev->trans_start = jiffies;
1660 // As act as station mode, destion shall be unicast address.
1661 //priv->ieee80211->stats.tx_bytes+=(skb->len - priv->ieee80211->tx_headroom);
1662 //priv->ieee80211->stats.tx_packets++;
1663 priv->stats.txoktotal++;
1664 priv->ieee80211->LinkDetectInfo.NumTxOkInPeriod++;
1665 priv->stats.txbytesunicast += (skb->len - priv->ieee80211->tx_headroom);
1666 } else {
1667 priv->ieee80211->stats.tx_errors++;
1668 //priv->stats.txmanageerr++;
1669 /* TODO */
1673 /* free skb and tx_urb */
1674 if(skb != NULL) {
1675 dev_kfree_skb_any(skb);
1676 usb_free_urb(tx_urb);
1677 atomic_dec(&priv->tx_pending[queue_index]);
1682 // Handle HW Beacon:
1683 // We had transfer our beacon frame to host controler at this moment.
1686 // Caution:
1687 // Handling the wait queue of command packets.
1688 // For Tx command packets, we must not do TCB fragment because it is not handled right now.
1689 // We must cut the packets to match the size of TX_CMD_PKT before we send it.
1691 if (queue_index == MGNT_QUEUE){
1692 if (priv->ieee80211->ack_tx_to_ieee){
1693 if (rtl8192_is_tx_queue_empty(dev)){
1694 priv->ieee80211->ack_tx_to_ieee = 0;
1695 ieee80211_ps_tx_ack(priv->ieee80211, 1);
1699 /* Handle MPDU in wait queue. */
1700 if(queue_index != BEACON_QUEUE) {
1701 /* Don't send data frame during scanning.*/
1702 if((skb_queue_len(&priv->ieee80211->skb_waitQ[queue_index]) != 0)&&\
1703 (!(priv->ieee80211->queue_stop))) {
1704 if(NULL != (skb = skb_dequeue(&(priv->ieee80211->skb_waitQ[queue_index]))))
1705 priv->ieee80211->softmac_hard_start_xmit(skb, dev);
1707 return; //modified by david to avoid further processing AMSDU
1713 void rtl8192_beacon_stop(struct net_device *dev)
1715 u8 msr, msrm, msr2;
1716 struct r8192_priv *priv = ieee80211_priv(dev);
1718 msr = read_nic_byte(dev, MSR);
1719 msrm = msr & MSR_LINK_MASK;
1720 msr2 = msr & ~MSR_LINK_MASK;
1722 if(NIC_8192U == priv->card_8192) {
1723 usb_kill_urb(priv->rx_urb[MAX_RX_URB]);
1725 if ((msrm == (MSR_LINK_ADHOC<<MSR_LINK_SHIFT) ||
1726 (msrm == (MSR_LINK_MASTER<<MSR_LINK_SHIFT)))){
1727 write_nic_byte(dev, MSR, msr2 | MSR_LINK_NONE);
1728 write_nic_byte(dev, MSR, msr);
1732 void rtl8192_config_rate(struct net_device* dev, u16* rate_config)
1734 struct r8192_priv *priv = ieee80211_priv(dev);
1735 struct ieee80211_network *net;
1736 u8 i=0, basic_rate = 0;
1737 net = & priv->ieee80211->current_network;
1739 for (i=0; i<net->rates_len; i++)
1741 basic_rate = net->rates[i]&0x7f;
1742 switch(basic_rate)
1744 case MGN_1M: *rate_config |= RRSR_1M; break;
1745 case MGN_2M: *rate_config |= RRSR_2M; break;
1746 case MGN_5_5M: *rate_config |= RRSR_5_5M; break;
1747 case MGN_11M: *rate_config |= RRSR_11M; break;
1748 case MGN_6M: *rate_config |= RRSR_6M; break;
1749 case MGN_9M: *rate_config |= RRSR_9M; break;
1750 case MGN_12M: *rate_config |= RRSR_12M; break;
1751 case MGN_18M: *rate_config |= RRSR_18M; break;
1752 case MGN_24M: *rate_config |= RRSR_24M; break;
1753 case MGN_36M: *rate_config |= RRSR_36M; break;
1754 case MGN_48M: *rate_config |= RRSR_48M; break;
1755 case MGN_54M: *rate_config |= RRSR_54M; break;
1758 for (i=0; i<net->rates_ex_len; i++)
1760 basic_rate = net->rates_ex[i]&0x7f;
1761 switch(basic_rate)
1763 case MGN_1M: *rate_config |= RRSR_1M; break;
1764 case MGN_2M: *rate_config |= RRSR_2M; break;
1765 case MGN_5_5M: *rate_config |= RRSR_5_5M; break;
1766 case MGN_11M: *rate_config |= RRSR_11M; break;
1767 case MGN_6M: *rate_config |= RRSR_6M; break;
1768 case MGN_9M: *rate_config |= RRSR_9M; break;
1769 case MGN_12M: *rate_config |= RRSR_12M; break;
1770 case MGN_18M: *rate_config |= RRSR_18M; break;
1771 case MGN_24M: *rate_config |= RRSR_24M; break;
1772 case MGN_36M: *rate_config |= RRSR_36M; break;
1773 case MGN_48M: *rate_config |= RRSR_48M; break;
1774 case MGN_54M: *rate_config |= RRSR_54M; break;
1780 #define SHORT_SLOT_TIME 9
1781 #define NON_SHORT_SLOT_TIME 20
1783 void rtl8192_update_cap(struct net_device* dev, u16 cap)
1785 //u32 tmp = 0;
1786 struct r8192_priv *priv = ieee80211_priv(dev);
1787 struct ieee80211_network *net = &priv->ieee80211->current_network;
1788 priv->short_preamble = cap & WLAN_CAPABILITY_SHORT_PREAMBLE;
1790 //LZM MOD 090303 HW_VAR_ACK_PREAMBLE
1791 if(0)
1793 u8 tmp = 0;
1794 tmp = ((priv->nCur40MhzPrimeSC) << 5);
1795 if (priv->short_preamble)
1796 tmp |= 0x80;
1797 write_nic_byte(dev, RRSR+2, tmp);
1800 if (net->mode & (IEEE_G|IEEE_N_24G))
1802 u8 slot_time = 0;
1803 if ((cap & WLAN_CAPABILITY_SHORT_SLOT)&&(!priv->ieee80211->pHTInfo->bCurrentRT2RTLongSlotTime))
1804 {//short slot time
1805 slot_time = SHORT_SLOT_TIME;
1807 else //long slot time
1808 slot_time = NON_SHORT_SLOT_TIME;
1809 priv->slot_time = slot_time;
1810 write_nic_byte(dev, SLOT_TIME, slot_time);
1814 void rtl8192_net_update(struct net_device *dev)
1817 struct r8192_priv *priv = ieee80211_priv(dev);
1818 struct ieee80211_network *net;
1819 u16 BcnTimeCfg = 0, BcnCW = 6, BcnIFS = 0xf;
1820 u16 rate_config = 0;
1821 net = & priv->ieee80211->current_network;
1823 rtl8192_config_rate(dev, &rate_config);
1824 priv->basic_rate = rate_config &= 0x15f;
1826 write_nic_dword(dev,BSSIDR,((u32*)net->bssid)[0]);
1827 write_nic_word(dev,BSSIDR+4,((u16*)net->bssid)[2]);
1828 //for(i=0;i<ETH_ALEN;i++)
1829 // write_nic_byte(dev,BSSID+i,net->bssid[i]);
1831 rtl8192_update_msr(dev);
1832 // rtl8192_update_cap(dev, net->capability);
1833 if (priv->ieee80211->iw_mode == IW_MODE_ADHOC)
1835 write_nic_word(dev, ATIMWND, 2);
1836 write_nic_word(dev, BCN_DMATIME, 1023);
1837 write_nic_word(dev, BCN_INTERVAL, net->beacon_interval);
1838 // write_nic_word(dev, BcnIntTime, 100);
1839 write_nic_word(dev, BCN_DRV_EARLY_INT, 1);
1840 write_nic_byte(dev, BCN_ERR_THRESH, 100);
1841 BcnTimeCfg |= (BcnCW<<BCN_TCFG_CW_SHIFT);
1842 // TODO: BcnIFS may required to be changed on ASIC
1843 BcnTimeCfg |= BcnIFS<<BCN_TCFG_IFS;
1845 write_nic_word(dev, BCN_TCFG, BcnTimeCfg);
1852 //temporary hw beacon is not used any more.
1853 //open it when necessary
1854 #if 1
1855 void rtl819xusb_beacon_tx(struct net_device *dev,u16 tx_rate)
1858 #endif
1859 inline u8 rtl8192_IsWirelessBMode(u16 rate)
1861 if( ((rate <= 110) && (rate != 60) && (rate != 90)) || (rate == 220) )
1862 return 1;
1863 else return 0;
1866 u16 N_DBPSOfRate(u16 DataRate);
1868 u16 ComputeTxTime(
1869 u16 FrameLength,
1870 u16 DataRate,
1871 u8 bManagementFrame,
1872 u8 bShortPreamble
1875 u16 FrameTime;
1876 u16 N_DBPS;
1877 u16 Ceiling;
1879 if( rtl8192_IsWirelessBMode(DataRate) )
1881 if( bManagementFrame || !bShortPreamble || DataRate == 10 )
1882 { // long preamble
1883 FrameTime = (u16)(144+48+(FrameLength*8/(DataRate/10)));
1885 else
1886 { // Short preamble
1887 FrameTime = (u16)(72+24+(FrameLength*8/(DataRate/10)));
1889 if( ( FrameLength*8 % (DataRate/10) ) != 0 ) //Get the Ceilling
1890 FrameTime ++;
1891 } else { //802.11g DSSS-OFDM PLCP length field calculation.
1892 N_DBPS = N_DBPSOfRate(DataRate);
1893 Ceiling = (16 + 8*FrameLength + 6) / N_DBPS
1894 + (((16 + 8*FrameLength + 6) % N_DBPS) ? 1 : 0);
1895 FrameTime = (u16)(16 + 4 + 4*Ceiling + 6);
1897 return FrameTime;
1900 u16 N_DBPSOfRate(u16 DataRate)
1902 u16 N_DBPS = 24;
1904 switch(DataRate)
1906 case 60:
1907 N_DBPS = 24;
1908 break;
1910 case 90:
1911 N_DBPS = 36;
1912 break;
1914 case 120:
1915 N_DBPS = 48;
1916 break;
1918 case 180:
1919 N_DBPS = 72;
1920 break;
1922 case 240:
1923 N_DBPS = 96;
1924 break;
1926 case 360:
1927 N_DBPS = 144;
1928 break;
1930 case 480:
1931 N_DBPS = 192;
1932 break;
1934 case 540:
1935 N_DBPS = 216;
1936 break;
1938 default:
1939 break;
1942 return N_DBPS;
1945 void rtl819xU_cmd_isr(struct urb *tx_cmd_urb, struct pt_regs *regs)
1947 usb_free_urb(tx_cmd_urb);
1950 unsigned int txqueue2outpipe(struct r8192_priv* priv,unsigned int tx_queue) {
1952 if(tx_queue >= 9)
1954 RT_TRACE(COMP_ERR,"%s():Unknown queue ID!!!\n",__FUNCTION__);
1955 return 0x04;
1957 return priv->txqueue_to_outpipemap[tx_queue];
1960 short rtl8192SU_tx_cmd(struct net_device *dev, struct sk_buff *skb)
1962 struct r8192_priv *priv = ieee80211_priv(dev);
1963 int status;
1964 struct urb *tx_urb;
1965 unsigned int idx_pipe;
1966 tx_desc_cmd_819x_usb *pdesc = (tx_desc_cmd_819x_usb *)skb->data;
1967 cb_desc *tcb_desc = (cb_desc *)(skb->cb + MAX_DEV_ADDR_SIZE);
1968 u8 queue_index = tcb_desc->queue_index;
1969 u32 PktSize = 0;
1971 //printk("\n %s::::::::::::::::::::::queue_index = %d\n",__FUNCTION__, queue_index);
1972 atomic_inc(&priv->tx_pending[queue_index]);
1974 tx_urb = usb_alloc_urb(0,GFP_ATOMIC);
1975 if(!tx_urb){
1976 dev_kfree_skb(skb);
1977 return -ENOMEM;
1980 memset(pdesc, 0, USB_HWDESC_HEADER_LEN);
1982 /* Tx descriptor ought to be set according to the skb->cb */
1983 pdesc->LINIP = tcb_desc->bLastIniPkt;
1984 PktSize = (u16)(skb->len - USB_HWDESC_HEADER_LEN);
1985 pdesc->PktSize = PktSize;
1986 //printk("PKTSize = %d %x\n",pdesc->PktSize,pdesc->PktSize);
1987 //----------------------------------------------------------------------------
1988 // Fill up USB_OUT_CONTEXT.
1989 //----------------------------------------------------------------------------
1990 // Get index to out pipe from specified QueueID.
1991 idx_pipe = txqueue2outpipe(priv,queue_index);
1992 //printk("=============>%s queue_index:%d, outpipe:%d\n", __func__,queue_index,priv->RtOutPipes[idx_pipe]);
1994 usb_fill_bulk_urb(tx_urb,
1995 priv->udev,
1996 usb_sndbulkpipe(priv->udev,priv->RtOutPipes[idx_pipe]),
1997 skb->data,
1998 skb->len,
1999 rtl8192_tx_isr,
2000 skb);
2002 status = usb_submit_urb(tx_urb, GFP_ATOMIC);
2003 if (!status){
2004 return 0;
2005 }else{
2006 printk("Error TX CMD URB, error %d",
2007 status);
2008 return -1;
2013 * Mapping Software/Hardware descriptor queue id to "Queue Select Field"
2014 * in TxFwInfo data structure
2015 * 2006.10.30 by Emily
2017 * \param QUEUEID Software Queue
2019 u8 MapHwQueueToFirmwareQueue(u8 QueueID)
2021 u8 QueueSelect = 0x0; //defualt set to
2023 switch(QueueID) {
2024 case BE_QUEUE:
2025 QueueSelect = QSLT_BE; //or QSelect = pTcb->priority;
2026 break;
2028 case BK_QUEUE:
2029 QueueSelect = QSLT_BK; //or QSelect = pTcb->priority;
2030 break;
2032 case VO_QUEUE:
2033 QueueSelect = QSLT_VO; //or QSelect = pTcb->priority;
2034 break;
2036 case VI_QUEUE:
2037 QueueSelect = QSLT_VI; //or QSelect = pTcb->priority;
2038 break;
2039 case MGNT_QUEUE:
2040 QueueSelect = QSLT_MGNT;
2041 break;
2043 case BEACON_QUEUE:
2044 QueueSelect = QSLT_BEACON;
2045 break;
2047 // TODO: 2006.10.30 mark other queue selection until we verify it is OK
2048 // TODO: Remove Assertions
2049 //#if (RTL819X_FPGA_VER & RTL819X_FPGA_GUANGAN_070502)
2050 case TXCMD_QUEUE:
2051 QueueSelect = QSLT_CMD;
2052 break;
2053 //#endif
2054 case HIGH_QUEUE:
2055 QueueSelect = QSLT_HIGH;
2056 break;
2058 default:
2059 RT_TRACE(COMP_ERR, "TransmitTCB(): Impossible Queue Selection: %d \n", QueueID);
2060 break;
2062 return QueueSelect;
2065 u8 MRateToHwRate8190Pci(u8 rate)
2067 u8 ret = DESC92S_RATE1M;
2069 switch(rate)
2071 // CCK and OFDM non-HT rates
2072 case MGN_1M: ret = DESC92S_RATE1M; break;
2073 case MGN_2M: ret = DESC92S_RATE2M; break;
2074 case MGN_5_5M: ret = DESC92S_RATE5_5M; break;
2075 case MGN_11M: ret = DESC92S_RATE11M; break;
2076 case MGN_6M: ret = DESC92S_RATE6M; break;
2077 case MGN_9M: ret = DESC92S_RATE9M; break;
2078 case MGN_12M: ret = DESC92S_RATE12M; break;
2079 case MGN_18M: ret = DESC92S_RATE18M; break;
2080 case MGN_24M: ret = DESC92S_RATE24M; break;
2081 case MGN_36M: ret = DESC92S_RATE36M; break;
2082 case MGN_48M: ret = DESC92S_RATE48M; break;
2083 case MGN_54M: ret = DESC92S_RATE54M; break;
2085 // HT rates since here
2086 case MGN_MCS0: ret = DESC92S_RATEMCS0; break;
2087 case MGN_MCS1: ret = DESC92S_RATEMCS1; break;
2088 case MGN_MCS2: ret = DESC92S_RATEMCS2; break;
2089 case MGN_MCS3: ret = DESC92S_RATEMCS3; break;
2090 case MGN_MCS4: ret = DESC92S_RATEMCS4; break;
2091 case MGN_MCS5: ret = DESC92S_RATEMCS5; break;
2092 case MGN_MCS6: ret = DESC92S_RATEMCS6; break;
2093 case MGN_MCS7: ret = DESC92S_RATEMCS7; break;
2094 case MGN_MCS8: ret = DESC92S_RATEMCS8; break;
2095 case MGN_MCS9: ret = DESC92S_RATEMCS9; break;
2096 case MGN_MCS10: ret = DESC92S_RATEMCS10; break;
2097 case MGN_MCS11: ret = DESC92S_RATEMCS11; break;
2098 case MGN_MCS12: ret = DESC92S_RATEMCS12; break;
2099 case MGN_MCS13: ret = DESC92S_RATEMCS13; break;
2100 case MGN_MCS14: ret = DESC92S_RATEMCS14; break;
2101 case MGN_MCS15: ret = DESC92S_RATEMCS15; break;
2103 // Set the highest SG rate
2104 case MGN_MCS0_SG:
2105 case MGN_MCS1_SG:
2106 case MGN_MCS2_SG:
2107 case MGN_MCS3_SG:
2108 case MGN_MCS4_SG:
2109 case MGN_MCS5_SG:
2110 case MGN_MCS6_SG:
2111 case MGN_MCS7_SG:
2112 case MGN_MCS8_SG:
2113 case MGN_MCS9_SG:
2114 case MGN_MCS10_SG:
2115 case MGN_MCS11_SG:
2116 case MGN_MCS12_SG:
2117 case MGN_MCS13_SG:
2118 case MGN_MCS14_SG:
2119 case MGN_MCS15_SG:
2121 ret = DESC92S_RATEMCS15_SG;
2122 break;
2125 default: break;
2127 return ret;
2130 u8 QueryIsShort(u8 TxHT, u8 TxRate, cb_desc *tcb_desc)
2132 u8 tmp_Short;
2134 tmp_Short = (TxHT==1)?((tcb_desc->bUseShortGI)?1:0):((tcb_desc->bUseShortPreamble)?1:0);
2136 if(TxHT==1 && TxRate != DESC90_RATEMCS15)
2137 tmp_Short = 0;
2139 return tmp_Short;
2142 static void tx_zero_isr(struct urb *tx_urb)
2144 return;
2149 * The tx procedure is just as following, skb->cb will contain all the following
2150 *information: * priority, morefrag, rate, &dev.
2151 * */
2152 // <Note> Buffer format for 8192S Usb bulk out:
2154 // --------------------------------------------------
2155 // | 8192S Usb Tx Desc | 802_11_MAC_header | data |
2156 // --------------------------------------------------
2157 // | 32 bytes | 24 bytes |0-2318 bytes|
2158 // --------------------------------------------------
2159 // |<------------ BufferLen ------------------------->|
2161 short rtl8192SU_tx(struct net_device *dev, struct sk_buff* skb)
2163 struct r8192_priv *priv = ieee80211_priv(dev);
2164 cb_desc *tcb_desc = (cb_desc *)(skb->cb + MAX_DEV_ADDR_SIZE);
2165 tx_desc_819x_usb *tx_desc = (tx_desc_819x_usb *)skb->data;
2166 struct usb_device *udev = priv->udev;
2167 int pend;
2168 int status;
2169 struct urb *tx_urb = NULL, *tx_urb_zero = NULL;
2170 unsigned int idx_pipe;
2171 u16 MPDUOverhead = 0;
2172 u16 type = 0;
2174 pend = atomic_read(&priv->tx_pending[tcb_desc->queue_index]);
2175 /* we are locked here so the two atomic_read and inc are executed
2176 * without interleaves * !!! For debug purpose */
2177 if( pend > MAX_TX_URB){
2178 switch (tcb_desc->queue_index) {
2179 case VO_PRIORITY:
2180 priv->stats.txvodrop++;
2181 break;
2182 case VI_PRIORITY:
2183 priv->stats.txvidrop++;
2184 break;
2185 case BE_PRIORITY:
2186 priv->stats.txbedrop++;
2187 break;
2188 default://BK_PRIORITY
2189 priv->stats.txbkdrop++;
2190 break;
2192 printk("To discard skb packet!\n");
2193 dev_kfree_skb_any(skb);
2194 return -1;
2197 tx_urb = usb_alloc_urb(0,GFP_ATOMIC);
2198 if(!tx_urb){
2199 dev_kfree_skb_any(skb);
2200 return -ENOMEM;
2203 memset(tx_desc, 0, sizeof(tx_desc_819x_usb));
2206 tx_desc->NonQos = (IsQoSDataFrame(skb->data)==TRUE)? 0:1;
2208 /* Fill Tx descriptor */
2209 //memset(tx_fwinfo,0,sizeof(tx_fwinfo_819x_usb));
2211 // This part can just fill to the first descriptor of the frame.
2212 /* DWORD 0 */
2213 tx_desc->TxHT = (tcb_desc->data_rate&0x80)?1:0;
2216 tx_desc->TxRate = MRateToHwRate8190Pci(tcb_desc->data_rate);
2217 //tx_desc->EnableCPUDur = tcb_desc->bTxEnableFwCalcDur;
2218 tx_desc->TxShort = QueryIsShort(tx_desc->TxHT, tx_desc->TxRate, tcb_desc);
2221 // Aggregation related
2222 if(tcb_desc->bAMPDUEnable) {//AMPDU enabled
2223 tx_desc->AllowAggregation = 1;
2224 /* DWORD 1 */
2225 //tx_fwinfo->RxMF = tcb_desc->ampdu_factor;
2226 //tx_fwinfo->RxAMD = tcb_desc->ampdu_density&0x07;//ampdudensity
2227 } else {
2228 tx_desc->AllowAggregation = 0;
2229 /* DWORD 1 */
2230 //tx_fwinfo->RxMF = 0;
2231 //tx_fwinfo->RxAMD = 0;
2235 // <Roger_Notes> For AMPDU case, we must insert SSN into TX_DESC,
2236 // FW according as this SSN to do necessary packet retry.
2237 // 2008.06.06.
2240 u8 *pSeq;
2241 u16 Temp;
2242 //pSeq = (u8 *)(VirtualAddress+USB_HWDESC_HEADER_LEN + FRAME_OFFSET_SEQUENCE);
2243 pSeq = (u8 *)(skb->data+USB_HWDESC_HEADER_LEN + 22);
2244 Temp = pSeq[0];
2245 Temp <<= 12;
2246 Temp |= (*(u16 *)pSeq)>>4;
2247 tx_desc->Seq = Temp;
2250 /* Protection mode related */
2251 tx_desc->RTSEn = (tcb_desc->bRTSEnable)?1:0;
2252 tx_desc->CTS2Self = (tcb_desc->bCTSEnable)?1:0;
2253 tx_desc->RTSSTBC = (tcb_desc->bRTSSTBC)?1:0;
2254 tx_desc->RTSHT = (tcb_desc->rts_rate&0x80)?1:0;
2255 tx_desc->RTSRate = MRateToHwRate8190Pci((u8)tcb_desc->rts_rate);
2256 tx_desc->RTSSubcarrier = (tx_desc->RTSHT==0)?(tcb_desc->RTSSC):0;
2257 tx_desc->RTSBW = (tx_desc->RTSHT==1)?((tcb_desc->bRTSBW)?1:0):0;
2258 tx_desc->RTSShort = (tx_desc->RTSHT==0)?(tcb_desc->bRTSUseShortPreamble?1:0):\
2259 (tcb_desc->bRTSUseShortGI?1:0);
2260 //LZM 090219
2261 tx_desc->DisRTSFB = 0;
2262 tx_desc->RTSRateFBLmt = 0xf;
2264 // <Roger_EXP> 2008.09.22. We disable RTS rate fallback temporarily.
2265 //tx_desc->DisRTSFB = 0x01;
2267 /* Set Bandwidth and sub-channel settings. */
2268 if(priv->CurrentChannelBW == HT_CHANNEL_WIDTH_20_40)
2270 if(tcb_desc->bPacketBW) {
2271 tx_desc->TxBandwidth = 1;
2272 tx_desc->TxSubCarrier = 0; //By SD3's Jerry suggestion, use duplicated mode
2273 } else {
2274 tx_desc->TxBandwidth = 0;
2275 tx_desc->TxSubCarrier = priv->nCur40MhzPrimeSC;
2277 } else {
2278 tx_desc->TxBandwidth = 0;
2279 tx_desc->TxSubCarrier = 0;
2283 //memset(tx_desc, 0, sizeof(tx_desc_819x_usb));
2284 /* DWORD 0 */
2285 tx_desc->LINIP = 0;
2286 //tx_desc->CmdInit = 1; //92su del
2287 tx_desc->Offset = USB_HWDESC_HEADER_LEN;
2290 tx_desc->PktSize = (skb->len - USB_HWDESC_HEADER_LEN) & 0xffff;
2293 /*DWORD 1*/
2294 //tx_desc->SecCAMID= 0;//92su del
2295 tx_desc->RaBRSRID= tcb_desc->RATRIndex;
2296 //#ifdef RTL8192S_PREPARE_FOR_NORMAL_RELEASE
2299 MPDUOverhead = 0;
2300 //tx_desc->NoEnc = 1;//92su del
2303 tx_desc->SecType = 0x0;
2305 if (tcb_desc->bHwSec)
2307 switch (priv->ieee80211->pairwise_key_type)
2309 case KEY_TYPE_WEP40:
2310 case KEY_TYPE_WEP104:
2311 tx_desc->SecType = 0x1;
2312 //tx_desc->NoEnc = 0;//92su del
2313 break;
2314 case KEY_TYPE_TKIP:
2315 tx_desc->SecType = 0x2;
2316 //tx_desc->NoEnc = 0;//92su del
2317 break;
2318 case KEY_TYPE_CCMP:
2319 tx_desc->SecType = 0x3;
2320 //tx_desc->NoEnc = 0;//92su del
2321 break;
2322 case KEY_TYPE_NA:
2323 tx_desc->SecType = 0x0;
2324 //tx_desc->NoEnc = 1;//92su del
2325 break;
2326 default:
2327 tx_desc->SecType = 0x0;
2328 //tx_desc->NoEnc = 1;//92su del
2329 break;
2333 //tx_desc->TxFWInfoSize = sizeof(tx_fwinfo_819x_usb);//92su del
2336 tx_desc->USERATE = tcb_desc->bTxUseDriverAssingedRate;
2337 tx_desc->DISFB = tcb_desc->bTxDisableRateFallBack;
2338 tx_desc->DataRateFBLmt = 0x1F;// Alwasy enable all rate fallback range
2340 tx_desc->QueueSelect = MapHwQueueToFirmwareQueue(tcb_desc->queue_index);
2343 /* Fill fields that are required to be initialized in all of the descriptors */
2344 //DWORD 0
2345 tx_desc->FirstSeg = 1;
2346 tx_desc->LastSeg = 1;
2347 tx_desc->OWN = 1;
2350 //DWORD 2
2351 //tx_desc->TxBufferSize = (u32)(skb->len - USB_HWDESC_HEADER_LEN);
2352 tx_desc->TxBufferSize = (u32)(skb->len);//92su mod FIXLZM
2355 /* Get index to out pipe from specified QueueID */
2356 idx_pipe = txqueue2outpipe(priv,tcb_desc->queue_index);
2357 //printk("=============>%s queue_index:%d, outpipe:%d\n", __func__,tcb_desc->queue_index,priv->RtOutPipes[idx_pipe]);
2359 //RT_DEBUG_DATA(COMP_SEND,tx_fwinfo,sizeof(tx_fwinfo_819x_usb));
2360 //RT_DEBUG_DATA(COMP_SEND,tx_desc,sizeof(tx_desc_819x_usb));
2362 /* To submit bulk urb */
2363 usb_fill_bulk_urb(tx_urb,
2364 udev,
2365 usb_sndbulkpipe(udev,priv->RtOutPipes[idx_pipe]),
2366 skb->data,
2367 skb->len, rtl8192_tx_isr, skb);
2369 if (type == IEEE80211_FTYPE_DATA) {
2370 if (priv->ieee80211->LedControlHandler != NULL)
2371 priv->ieee80211->LedControlHandler(dev, LED_CTL_TX);
2374 status = usb_submit_urb(tx_urb, GFP_ATOMIC);
2375 if (!status) {
2377 * we need to send 0 byte packet whenever 512N bytes/64N(HIGN SPEED/NORMAL SPEED) bytes packet has been transmitted.
2378 * Otherwise, it will be halt to wait for another packet. WB. 2008.08.27
2380 bool bSend0Byte = false;
2381 u8 zero = 0;
2382 if(udev->speed == USB_SPEED_HIGH) {
2383 if (skb->len > 0 && skb->len % 512 == 0)
2384 bSend0Byte = true;
2386 else {
2387 if (skb->len > 0 && skb->len % 64 == 0)
2388 bSend0Byte = true;
2390 if (bSend0Byte) {
2391 tx_urb_zero = usb_alloc_urb(0,GFP_ATOMIC);
2392 if(!tx_urb_zero) {
2393 RT_TRACE(COMP_ERR, "can't alloc urb for zero byte\n");
2394 return -ENOMEM;
2396 usb_fill_bulk_urb(tx_urb_zero,udev,
2397 usb_sndbulkpipe(udev,idx_pipe), &zero,
2398 0, tx_zero_isr, dev);
2399 status = usb_submit_urb(tx_urb_zero, GFP_ATOMIC);
2400 switch (status) {
2401 case 0:
2402 break;
2403 case -ECONNRESET:
2404 case -ENOENT:
2405 case -ESHUTDOWN:
2406 break;
2407 default:
2408 RT_TRACE(COMP_ERR, "Error TX URB for zero byte %d, error %d",
2409 atomic_read(&priv->tx_pending[tcb_desc->queue_index]), status);
2410 return -1;
2413 dev->trans_start = jiffies;
2414 atomic_inc(&priv->tx_pending[tcb_desc->queue_index]);
2415 return 0;
2416 } else {
2417 RT_TRACE(COMP_ERR, "Error TX URB %d, error %d", atomic_read(&priv->tx_pending[tcb_desc->queue_index]),
2418 status);
2419 return -1;
2423 void rtl8192SU_net_update(struct net_device *dev)
2426 struct r8192_priv *priv = ieee80211_priv(dev);
2427 struct ieee80211_device* ieee = priv->ieee80211;
2428 struct ieee80211_network *net = &priv->ieee80211->current_network;
2429 //u16 BcnTimeCfg = 0, BcnCW = 6, BcnIFS = 0xf;
2430 u16 rate_config = 0;
2431 u32 regTmp = 0;
2432 u8 rateIndex = 0;
2433 u8 retrylimit = 0x30;
2434 u16 cap = net->capability;
2436 priv->short_preamble = cap & WLAN_CAPABILITY_SHORT_PREAMBLE;
2438 //HW_VAR_BASIC_RATE
2439 //update Basic rate: RR, BRSR
2440 rtl8192_config_rate(dev, &rate_config); //HalSetBrateCfg
2442 priv->basic_rate = rate_config = rate_config & 0x15f;
2444 // Set RRSR rate table.
2445 write_nic_byte(dev, RRSR, rate_config&0xff);
2446 write_nic_byte(dev, RRSR+1, (rate_config>>8)&0xff);
2448 // Set RTS initial rate
2449 while(rate_config > 0x1)
2451 rate_config = (rate_config>> 1);
2452 rateIndex++;
2454 write_nic_byte(dev, INIRTSMCS_SEL, rateIndex);
2455 //HW_VAR_BASIC_RATE
2457 //set ack preample
2458 regTmp = (priv->nCur40MhzPrimeSC) << 5;
2459 if (priv->short_preamble)
2460 regTmp |= 0x80;
2461 write_nic_byte(dev, RRSR+2, regTmp);
2463 write_nic_dword(dev,BSSIDR,((u32*)net->bssid)[0]);
2464 write_nic_word(dev,BSSIDR+4,((u16*)net->bssid)[2]);
2466 write_nic_word(dev, BCN_INTERVAL, net->beacon_interval);
2467 //2008.10.24 added by tynli for beacon changed.
2468 PHY_SetBeaconHwReg( dev, net->beacon_interval);
2470 rtl8192_update_cap(dev, cap);
2472 if (ieee->iw_mode == IW_MODE_ADHOC){
2473 retrylimit = 7;
2474 //we should enable ibss interrupt here, but disable it temporarily
2475 if (0){
2476 priv->irq_mask |= (IMR_BcnInt | IMR_BcnInt | IMR_TBDOK | IMR_TBDER);
2477 //rtl8192_irq_disable(dev);
2478 //rtl8192_irq_enable(dev);
2481 else{
2482 if (0){
2483 priv->irq_mask &= ~(IMR_BcnInt | IMR_BcnInt | IMR_TBDOK | IMR_TBDER);
2484 //rtl8192_irq_disable(dev);
2485 //rtl8192_irq_enable(dev);
2489 priv->ShortRetryLimit = priv->LongRetryLimit = retrylimit;
2491 write_nic_word(dev, RETRY_LIMIT,
2492 retrylimit << RETRY_LIMIT_SHORT_SHIFT | \
2493 retrylimit << RETRY_LIMIT_LONG_SHIFT);
2496 void rtl8192SU_update_ratr_table(struct net_device* dev)
2498 struct r8192_priv* priv = ieee80211_priv(dev);
2499 struct ieee80211_device* ieee = priv->ieee80211;
2500 u8* pMcsRate = ieee->dot11HTOperationalRateSet;
2501 //struct ieee80211_network *net = &ieee->current_network;
2502 u32 ratr_value = 0;
2504 u8 rate_index = 0;
2505 int WirelessMode = ieee->mode;
2506 u8 MimoPs = ieee->pHTInfo->PeerMimoPs;
2508 u8 bNMode = 0;
2510 rtl8192_config_rate(dev, (u16*)(&ratr_value));
2511 ratr_value |= (*(u16*)(pMcsRate)) << 12;
2513 //switch (ieee->mode)
2514 switch (WirelessMode)
2516 case IEEE_A:
2517 ratr_value &= 0x00000FF0;
2518 break;
2519 case IEEE_B:
2520 ratr_value &= 0x0000000D;
2521 break;
2522 case IEEE_G:
2523 ratr_value &= 0x00000FF5;
2524 break;
2525 case IEEE_N_24G:
2526 case IEEE_N_5G:
2528 bNMode = 1;
2530 if (MimoPs == 0) //MIMO_PS_STATIC
2532 ratr_value &= 0x0007F005;
2534 else
2535 { // MCS rate only => for 11N mode.
2536 u32 ratr_mask;
2538 // 1T2R or 1T1R, Spatial Stream 2 should be disabled
2539 if ( priv->rf_type == RF_1T2R ||
2540 priv->rf_type == RF_1T1R ||
2541 (ieee->pHTInfo->IOTAction & HT_IOT_ACT_DISABLE_TX_2SS) )
2542 ratr_mask = 0x000ff005;
2543 else
2544 ratr_mask = 0x0f0ff005;
2546 if((ieee->pHTInfo->bCurTxBW40MHz) &&
2547 !(ieee->pHTInfo->IOTAction & HT_IOT_ACT_DISABLE_TX_40_MHZ))
2548 ratr_mask |= 0x00000010; // Set 6MBps
2550 // Select rates for rate adaptive mechanism.
2551 ratr_value &= ratr_mask;
2554 break;
2555 default:
2556 if(0)
2558 if(priv->rf_type == RF_1T2R) // 1T2R, Spatial Stream 2 should be disabled
2560 ratr_value &= 0x000ff0f5;
2562 else
2564 ratr_value &= 0x0f0ff0f5;
2567 //printk("====>%s(), mode is not correct:%x\n", __FUNCTION__, ieee->mode);
2568 break;
2571 ratr_value &= 0x0FFFFFFF;
2573 // Get MAX MCS available.
2574 if ( (bNMode && ((ieee->pHTInfo->IOTAction & HT_IOT_ACT_DISABLE_SHORT_GI)==0)) &&
2575 ((ieee->pHTInfo->bCurBW40MHz && ieee->pHTInfo->bCurShortGI40MHz) ||
2576 (!ieee->pHTInfo->bCurBW40MHz && ieee->pHTInfo->bCurShortGI20MHz)))
2578 u8 shortGI_rate = 0;
2579 u32 tmp_ratr_value = 0;
2580 ratr_value |= 0x10000000;//???
2581 tmp_ratr_value = (ratr_value>>12);
2582 for(shortGI_rate=15; shortGI_rate>0; shortGI_rate--)
2584 if((1<<shortGI_rate) & tmp_ratr_value)
2585 break;
2587 shortGI_rate = (shortGI_rate<<12)|(shortGI_rate<<8)|(shortGI_rate<<4)|(shortGI_rate);
2588 write_nic_byte(dev, SG_RATE, shortGI_rate);
2589 //printk("==>SG_RATE:%x\n", read_nic_byte(dev, SG_RATE));
2591 write_nic_dword(dev, ARFR0+rate_index*4, ratr_value);
2592 printk("=============>ARFR0+rate_index*4:%#x\n", ratr_value);
2594 //2 UFWP
2595 if (ratr_value & 0xfffff000){
2596 //printk("===>set to N mode\n");
2597 HalSetFwCmd8192S(dev, FW_CMD_RA_REFRESH_N);
2599 else {
2600 //printk("===>set to B/G mode\n");
2601 HalSetFwCmd8192S(dev, FW_CMD_RA_REFRESH_BG);
2605 void rtl8192SU_link_change(struct net_device *dev)
2607 struct r8192_priv *priv = ieee80211_priv(dev);
2608 struct ieee80211_device *ieee = priv->ieee80211;
2609 u32 reg = 0;
2611 reg = read_nic_dword(dev, RCR);
2612 if (ieee->state == IEEE80211_LINKED) {
2613 rtl8192SU_net_update(dev);
2614 rtl8192SU_update_ratr_table(dev);
2615 ieee->SetFwCmdHandler(dev, FW_CMD_HIGH_PWR_ENABLE);
2616 priv->ReceiveConfig = reg |= RCR_CBSSID;
2618 } else
2619 priv->ReceiveConfig = reg &= ~RCR_CBSSID;
2620 write_nic_dword(dev, RCR, reg);
2621 rtl8192_update_msr(dev);
2624 static struct ieee80211_qos_parameters def_qos_parameters = {
2625 {3,3,3,3},/* cw_min */
2626 {7,7,7,7},/* cw_max */
2627 {2,2,2,2},/* aifs */
2628 {0,0,0,0},/* flags */
2629 {0,0,0,0} /* tx_op_limit */
2633 void rtl8192_update_beacon(struct work_struct * work)
2635 struct r8192_priv *priv = container_of(work, struct r8192_priv, update_beacon_wq.work);
2636 struct net_device *dev = priv->ieee80211->dev;
2637 struct ieee80211_device* ieee = priv->ieee80211;
2638 struct ieee80211_network* net = &ieee->current_network;
2640 if (ieee->pHTInfo->bCurrentHTSupport)
2641 HTUpdateSelfAndPeerSetting(ieee, net);
2642 ieee->pHTInfo->bCurrentRT2RTLongSlotTime = net->bssht.bdRT2RTLongSlotTime;
2643 // Joseph test for turbo mode with AP
2644 ieee->pHTInfo->RT2RT_HT_Mode = net->bssht.RT2RT_HT_Mode;
2645 rtl8192_update_cap(dev, net->capability);
2648 * background support to run QoS activate functionality
2650 int WDCAPARA_ADD[] = {EDCAPARA_BE,EDCAPARA_BK,EDCAPARA_VI,EDCAPARA_VO};
2652 void rtl8192_qos_activate(struct work_struct * work)
2654 struct r8192_priv *priv = container_of(work, struct r8192_priv, qos_activate);
2655 struct net_device *dev = priv->ieee80211->dev;
2656 struct ieee80211_qos_parameters *qos_parameters = &priv->ieee80211->current_network.qos_data.parameters;
2657 u8 mode = priv->ieee80211->current_network.mode;
2658 //u32 size = sizeof(struct ieee80211_qos_parameters);
2659 u8 u1bAIFS;
2660 u32 u4bAcParam;
2661 int i;
2663 if (priv == NULL)
2664 return;
2666 mutex_lock(&priv->mutex);
2668 if(priv->ieee80211->state != IEEE80211_LINKED)
2669 goto success;
2670 RT_TRACE(COMP_QOS,"qos active process with associate response received\n");
2671 /* It better set slot time at first */
2672 /* For we just support b/g mode at present, let the slot time at 9/20 selection */
2673 /* update the ac parameter to related registers */
2674 for(i = 0; i < QOS_QUEUE_NUM; i++) {
2675 //Mode G/A: slotTimeTimer = 9; Mode B: 20
2676 u1bAIFS = qos_parameters->aifs[i] * ((mode&(IEEE_G|IEEE_N_24G)) ?9:20) + aSifsTime;
2677 u4bAcParam = ((((u32)(qos_parameters->tx_op_limit[i]))<< AC_PARAM_TXOP_LIMIT_OFFSET)|
2678 (((u32)(qos_parameters->cw_max[i]))<< AC_PARAM_ECW_MAX_OFFSET)|
2679 (((u32)(qos_parameters->cw_min[i]))<< AC_PARAM_ECW_MIN_OFFSET)|
2680 ((u32)u1bAIFS << AC_PARAM_AIFS_OFFSET));
2682 write_nic_dword(dev, WDCAPARA_ADD[i], u4bAcParam);
2683 //write_nic_dword(dev, WDCAPARA_ADD[i], 0x005e4322);
2686 success:
2687 mutex_unlock(&priv->mutex);
2690 static int rtl8192_qos_handle_probe_response(struct r8192_priv *priv,
2691 int active_network,
2692 struct ieee80211_network *network)
2694 int ret = 0;
2695 u32 size = sizeof(struct ieee80211_qos_parameters);
2697 if(priv->ieee80211->state !=IEEE80211_LINKED)
2698 return ret;
2700 if ((priv->ieee80211->iw_mode != IW_MODE_INFRA))
2701 return ret;
2703 if (network->flags & NETWORK_HAS_QOS_MASK) {
2704 if (active_network &&
2705 (network->flags & NETWORK_HAS_QOS_PARAMETERS))
2706 network->qos_data.active = network->qos_data.supported;
2708 if ((network->qos_data.active == 1) && (active_network == 1) &&
2709 (network->flags & NETWORK_HAS_QOS_PARAMETERS) &&
2710 (network->qos_data.old_param_count !=
2711 network->qos_data.param_count)) {
2712 network->qos_data.old_param_count =
2713 network->qos_data.param_count;
2714 queue_work(priv->priv_wq, &priv->qos_activate);
2715 RT_TRACE (COMP_QOS, "QoS parameters change call "
2716 "qos_activate\n");
2718 } else {
2719 memcpy(&priv->ieee80211->current_network.qos_data.parameters,\
2720 &def_qos_parameters, size);
2722 if ((network->qos_data.active == 1) && (active_network == 1)) {
2723 queue_work(priv->priv_wq, &priv->qos_activate);
2724 RT_TRACE(COMP_QOS, "QoS was disabled call qos_activate \n");
2726 network->qos_data.active = 0;
2727 network->qos_data.supported = 0;
2730 return 0;
2733 /* handle manage frame frame beacon and probe response */
2734 static int rtl8192_handle_beacon(struct net_device * dev,
2735 struct ieee80211_probe_response *beacon,
2736 struct ieee80211_network *network)
2738 struct r8192_priv *priv = ieee80211_priv(dev);
2740 rtl8192_qos_handle_probe_response(priv,1,network);
2741 queue_delayed_work(priv->priv_wq, &priv->update_beacon_wq, 0);
2743 return 0;
2748 * handling the beaconing responses. if we get different QoS setting
2749 * off the network from the associated setting, adjust the QoS
2750 * setting
2752 static int rtl8192_qos_association_resp(struct r8192_priv *priv,
2753 struct ieee80211_network *network)
2755 int ret = 0;
2756 unsigned long flags;
2757 u32 size = sizeof(struct ieee80211_qos_parameters);
2758 int set_qos_param = 0;
2760 if ((priv == NULL) || (network == NULL))
2761 return ret;
2763 if(priv->ieee80211->state !=IEEE80211_LINKED)
2764 return ret;
2766 if ((priv->ieee80211->iw_mode != IW_MODE_INFRA))
2767 return ret;
2769 spin_lock_irqsave(&priv->ieee80211->lock, flags);
2770 if(network->flags & NETWORK_HAS_QOS_PARAMETERS) {
2771 memcpy(&priv->ieee80211->current_network.qos_data.parameters,\
2772 &network->qos_data.parameters,\
2773 sizeof(struct ieee80211_qos_parameters));
2774 priv->ieee80211->current_network.qos_data.active = 1;
2776 set_qos_param = 1;
2777 /* update qos parameter for current network */
2778 priv->ieee80211->current_network.qos_data.old_param_count = \
2779 priv->ieee80211->current_network.qos_data.param_count;
2780 priv->ieee80211->current_network.qos_data.param_count = \
2781 network->qos_data.param_count;
2783 } else {
2784 memcpy(&priv->ieee80211->current_network.qos_data.parameters,\
2785 &def_qos_parameters, size);
2786 priv->ieee80211->current_network.qos_data.active = 0;
2787 priv->ieee80211->current_network.qos_data.supported = 0;
2788 set_qos_param = 1;
2791 spin_unlock_irqrestore(&priv->ieee80211->lock, flags);
2793 RT_TRACE(COMP_QOS, "%s: network->flags = %d,%d\n",__FUNCTION__,network->flags ,priv->ieee80211->current_network.qos_data.active);
2794 if (set_qos_param == 1)
2795 queue_work(priv->priv_wq, &priv->qos_activate);
2797 return ret;
2801 static int rtl8192_handle_assoc_response(struct net_device *dev,
2802 struct ieee80211_assoc_response_frame *resp,
2803 struct ieee80211_network *network)
2805 struct r8192_priv *priv = ieee80211_priv(dev);
2806 rtl8192_qos_association_resp(priv, network);
2807 return 0;
2811 void rtl8192_update_ratr_table(struct net_device* dev)
2812 // POCTET_STRING posLegacyRate,
2813 // u8* pMcsRate)
2814 // PRT_WLAN_STA pEntry)
2816 struct r8192_priv* priv = ieee80211_priv(dev);
2817 struct ieee80211_device* ieee = priv->ieee80211;
2818 u8* pMcsRate = ieee->dot11HTOperationalRateSet;
2819 //struct ieee80211_network *net = &ieee->current_network;
2820 u32 ratr_value = 0;
2821 u8 rate_index = 0;
2822 rtl8192_config_rate(dev, (u16*)(&ratr_value));
2823 ratr_value |= (*(u16*)(pMcsRate)) << 12;
2824 // switch (net->mode)
2825 switch (ieee->mode)
2827 case IEEE_A:
2828 ratr_value &= 0x00000FF0;
2829 break;
2830 case IEEE_B:
2831 ratr_value &= 0x0000000F;
2832 break;
2833 case IEEE_G:
2834 ratr_value &= 0x00000FF7;
2835 break;
2836 case IEEE_N_24G:
2837 case IEEE_N_5G:
2838 if (ieee->pHTInfo->PeerMimoPs == 0) //MIMO_PS_STATIC
2839 ratr_value &= 0x0007F007;
2840 else{
2841 if (priv->rf_type == RF_1T2R)
2842 ratr_value &= 0x000FF007;
2843 else
2844 ratr_value &= 0x0F81F007;
2846 break;
2847 default:
2848 break;
2850 ratr_value &= 0x0FFFFFFF;
2851 if(ieee->pHTInfo->bCurTxBW40MHz && ieee->pHTInfo->bCurShortGI40MHz){
2852 ratr_value |= 0x80000000;
2853 }else if(!ieee->pHTInfo->bCurTxBW40MHz && ieee->pHTInfo->bCurShortGI20MHz){
2854 ratr_value |= 0x80000000;
2856 write_nic_dword(dev, RATR0+rate_index*4, ratr_value);
2857 write_nic_byte(dev, UFWP, 1);
2860 static u8 ccmp_ie[4] = {0x00,0x50,0xf2,0x04};
2861 static u8 ccmp_rsn_ie[4] = {0x00, 0x0f, 0xac, 0x04};
2862 bool GetNmodeSupportBySecCfg8192(struct net_device*dev)
2864 #if 1
2865 struct r8192_priv* priv = ieee80211_priv(dev);
2866 struct ieee80211_device* ieee = priv->ieee80211;
2867 struct ieee80211_network * network = &ieee->current_network;
2868 int wpa_ie_len= ieee->wpa_ie_len;
2869 struct ieee80211_crypt_data* crypt;
2870 int encrypt;
2871 return TRUE;
2873 crypt = ieee->crypt[ieee->tx_keyidx];
2874 //we use connecting AP's capability instead of only security config on our driver to distinguish whether it should use N mode or G mode
2875 encrypt = (network->capability & WLAN_CAPABILITY_PRIVACY) || (ieee->host_encrypt && crypt && crypt->ops && (0 == strcmp(crypt->ops->name,"WEP")));
2877 /* simply judge */
2878 if(encrypt && (wpa_ie_len == 0)) {
2879 /* wep encryption, no N mode setting */
2880 return false;
2881 // } else if((wpa_ie_len != 0)&&(memcmp(&(ieee->wpa_ie[14]),ccmp_ie,4))) {
2882 } else if((wpa_ie_len != 0)) {
2883 /* parse pairwise key type */
2884 //if((pairwisekey = WEP40)||(pairwisekey = WEP104)||(pairwisekey = TKIP))
2885 if (((ieee->wpa_ie[0] == 0xdd) && (!memcmp(&(ieee->wpa_ie[14]),ccmp_ie,4))) || ((ieee->wpa_ie[0] == 0x30) && (!memcmp(&ieee->wpa_ie[10],ccmp_rsn_ie, 4))))
2886 return true;
2887 else
2888 return false;
2889 } else {
2890 return true;
2893 return true;
2894 #endif
2897 bool GetHalfNmodeSupportByAPs819xUsb(struct net_device* dev)
2899 bool Reval;
2900 struct r8192_priv* priv = ieee80211_priv(dev);
2901 struct ieee80211_device* ieee = priv->ieee80211;
2903 // Added by Roger, 2008.08.29.
2904 return false;
2906 if(ieee->bHalfWirelessN24GMode == true)
2907 Reval = true;
2908 else
2909 Reval = false;
2911 return Reval;
2914 void rtl8192_refresh_supportrate(struct r8192_priv* priv)
2916 struct ieee80211_device* ieee = priv->ieee80211;
2917 //we donot consider set support rate for ABG mode, only HT MCS rate is set here.
2918 if (ieee->mode == WIRELESS_MODE_N_24G || ieee->mode == WIRELESS_MODE_N_5G)
2920 memcpy(ieee->Regdot11HTOperationalRateSet, ieee->RegHTSuppRateSet, 16);
2921 //RT_DEBUG_DATA(COMP_INIT, ieee->RegHTSuppRateSet, 16);
2922 //RT_DEBUG_DATA(COMP_INIT, ieee->Regdot11HTOperationalRateSet, 16);
2924 else
2925 memset(ieee->Regdot11HTOperationalRateSet, 0, 16);
2926 return;
2929 u8 rtl8192_getSupportedWireleeMode(struct net_device*dev)
2931 struct r8192_priv *priv = ieee80211_priv(dev);
2932 u8 ret = 0;
2933 switch(priv->rf_chip)
2935 case RF_8225:
2936 case RF_8256:
2937 case RF_PSEUDO_11N:
2938 case RF_6052:
2939 ret = (WIRELESS_MODE_N_24G|WIRELESS_MODE_G|WIRELESS_MODE_B);
2940 break;
2941 case RF_8258:
2942 ret = (WIRELESS_MODE_A|WIRELESS_MODE_N_5G);
2943 break;
2944 default:
2945 ret = WIRELESS_MODE_B;
2946 break;
2948 return ret;
2950 void rtl8192_SetWirelessMode(struct net_device* dev, u8 wireless_mode)
2952 struct r8192_priv *priv = ieee80211_priv(dev);
2953 u8 bSupportMode = rtl8192_getSupportedWireleeMode(dev);
2955 #if 1
2956 if ((wireless_mode == WIRELESS_MODE_AUTO) || ((wireless_mode&bSupportMode)==0))
2958 if(bSupportMode & WIRELESS_MODE_N_24G)
2960 wireless_mode = WIRELESS_MODE_N_24G;
2962 else if(bSupportMode & WIRELESS_MODE_N_5G)
2964 wireless_mode = WIRELESS_MODE_N_5G;
2966 else if((bSupportMode & WIRELESS_MODE_A))
2968 wireless_mode = WIRELESS_MODE_A;
2970 else if((bSupportMode & WIRELESS_MODE_G))
2972 wireless_mode = WIRELESS_MODE_G;
2974 else if((bSupportMode & WIRELESS_MODE_B))
2976 wireless_mode = WIRELESS_MODE_B;
2978 else{
2979 RT_TRACE(COMP_ERR, "%s(), No valid wireless mode supported, SupportedWirelessMode(%x)!!!\n", __FUNCTION__,bSupportMode);
2980 wireless_mode = WIRELESS_MODE_B;
2983 #ifdef TO_DO_LIST //// TODO: this function doesn't work well at this time, we should wait for FPGA
2984 ActUpdateChannelAccessSetting( pAdapter, pHalData->CurrentWirelessMode, &pAdapter->MgntInfo.Info8185.ChannelAccessSetting );
2985 #endif
2986 //LZM 090306 usb crash here, mark it temp
2987 //write_nic_word(dev, SIFS_OFDM, 0x0e0e);
2988 priv->ieee80211->mode = wireless_mode;
2990 if ((wireless_mode == WIRELESS_MODE_N_24G) || (wireless_mode == WIRELESS_MODE_N_5G))
2991 priv->ieee80211->pHTInfo->bEnableHT = 1;
2992 else
2993 priv->ieee80211->pHTInfo->bEnableHT = 0;
2994 RT_TRACE(COMP_INIT, "Current Wireless Mode is %x\n", wireless_mode);
2995 rtl8192_refresh_supportrate(priv);
2996 #endif
3001 short rtl8192_is_tx_queue_empty(struct net_device *dev)
3003 int i=0;
3004 struct r8192_priv *priv = ieee80211_priv(dev);
3005 //struct ieee80211_device* ieee = priv->ieee80211;
3006 for (i=0; i<=MGNT_QUEUE; i++)
3008 if ((i== TXCMD_QUEUE) || (i == HCCA_QUEUE) )
3009 continue;
3010 if (atomic_read(&priv->tx_pending[i]))
3012 printk("===>tx queue is not empty:%d, %d\n", i, atomic_read(&priv->tx_pending[i]));
3013 return 0;
3016 return 1;
3019 void rtl8192_hw_sleep_down(struct net_device *dev)
3021 RT_TRACE(COMP_POWER, "%s()============>come to sleep down\n", __FUNCTION__);
3022 #ifdef TODO
3023 // MgntActSet_RF_State(dev, eRfSleep, RF_CHANGE_BY_PS);
3024 #endif
3027 void rtl8192_hw_sleep_wq (struct work_struct *work)
3029 // struct r8180_priv *priv = container_of(work, struct r8180_priv, watch_dog_wq);
3030 // struct ieee80211_device * ieee = (struct ieee80211_device*)
3031 // container_of(work, struct ieee80211_device, watch_dog_wq);
3032 struct delayed_work *dwork = container_of(work,struct delayed_work,work);
3033 struct ieee80211_device *ieee = container_of(dwork,struct ieee80211_device,hw_sleep_wq);
3034 struct net_device *dev = ieee->dev;
3036 //printk("=========>%s()\n", __FUNCTION__);
3037 rtl8192_hw_sleep_down(dev);
3039 // printk("dev is %d\n",dev);
3040 // printk("&*&(^*(&(&=========>%s()\n", __FUNCTION__);
3041 void rtl8192_hw_wakeup(struct net_device* dev)
3043 // u32 flags = 0;
3045 // spin_lock_irqsave(&priv->ps_lock,flags);
3046 RT_TRACE(COMP_POWER, "%s()============>come to wake up\n", __FUNCTION__);
3047 #ifdef TODO
3048 // MgntActSet_RF_State(dev, eRfSleep, RF_CHANGE_BY_PS);
3049 #endif
3050 //FIXME: will we send package stored while nic is sleep?
3051 // spin_unlock_irqrestore(&priv->ps_lock,flags);
3054 void rtl8192_hw_wakeup_wq (struct work_struct *work)
3056 // struct r8180_priv *priv = container_of(work, struct r8180_priv, watch_dog_wq);
3057 // struct ieee80211_device * ieee = (struct ieee80211_device*)
3058 // container_of(work, struct ieee80211_device, watch_dog_wq);
3059 struct delayed_work *dwork = container_of(work,struct delayed_work,work);
3060 struct ieee80211_device *ieee = container_of(dwork,struct ieee80211_device,hw_wakeup_wq);
3061 struct net_device *dev = ieee->dev;
3063 rtl8192_hw_wakeup(dev);
3066 #define MIN_SLEEP_TIME 50
3067 #define MAX_SLEEP_TIME 10000
3068 void rtl8192_hw_to_sleep(struct net_device *dev, u32 th, u32 tl)
3071 struct r8192_priv *priv = ieee80211_priv(dev);
3073 u32 rb = jiffies;
3074 unsigned long flags;
3076 spin_lock_irqsave(&priv->ps_lock,flags);
3078 /* Writing HW register with 0 equals to disable
3079 * the timer, that is not really what we want
3081 tl -= MSECS(4+16+7);
3083 //if(tl == 0) tl = 1;
3085 /* FIXME HACK FIXME HACK */
3086 // force_pci_posting(dev);
3087 //mdelay(1);
3089 // rb = read_nic_dword(dev, TSFTR);
3091 /* If the interval in witch we are requested to sleep is too
3092 * short then give up and remain awake
3094 if(((tl>=rb)&& (tl-rb) <= MSECS(MIN_SLEEP_TIME))
3095 ||((rb>tl)&& (rb-tl) < MSECS(MIN_SLEEP_TIME))) {
3096 spin_unlock_irqrestore(&priv->ps_lock,flags);
3097 printk("too short to sleep\n");
3098 return;
3101 // write_nic_dword(dev, TimerInt, tl);
3102 // rb = read_nic_dword(dev, TSFTR);
3104 u32 tmp = (tl>rb)?(tl-rb):(rb-tl);
3105 // if (tl<rb)
3107 queue_delayed_work(priv->ieee80211->wq, &priv->ieee80211->hw_wakeup_wq, tmp); //as tl may be less than rb
3109 /* if we suspect the TimerInt is gone beyond tl
3110 * while setting it, then give up
3112 #if 1
3113 if(((tl > rb) && ((tl-rb) > MSECS(MAX_SLEEP_TIME)))||
3114 ((tl < rb) && ((rb-tl) > MSECS(MAX_SLEEP_TIME)))) {
3115 printk("========>too long to sleep:%x, %x, %lx\n", tl, rb, MSECS(MAX_SLEEP_TIME));
3116 spin_unlock_irqrestore(&priv->ps_lock,flags);
3117 return;
3119 #endif
3120 // if(priv->rf_sleep)
3121 // priv->rf_sleep(dev);
3123 //printk("<=========%s()\n", __FUNCTION__);
3124 queue_delayed_work(priv->ieee80211->wq, (void *)&priv->ieee80211->hw_sleep_wq,0);
3126 spin_unlock_irqrestore(&priv->ps_lock,flags);
3128 //init priv variables here. only non_zero value should be initialized here.
3129 static void rtl8192_init_priv_variable(struct net_device* dev)
3131 struct r8192_priv *priv = ieee80211_priv(dev);
3132 u8 i;
3133 priv->card_8192 = NIC_8192U;
3134 priv->chan = 1; //set to channel 1
3135 priv->ieee80211->mode = WIRELESS_MODE_AUTO; //SET AUTO
3136 priv->ieee80211->iw_mode = IW_MODE_INFRA;
3137 priv->ieee80211->ieee_up=0;
3138 priv->retry_rts = DEFAULT_RETRY_RTS;
3139 priv->retry_data = DEFAULT_RETRY_DATA;
3140 priv->ieee80211->rts = DEFAULT_RTS_THRESHOLD;
3141 priv->ieee80211->rate = 110; //11 mbps
3142 priv->ieee80211->short_slot = 1;
3143 priv->promisc = (dev->flags & IFF_PROMISC) ? 1:0;
3144 priv->CckPwEnl = 6;
3145 //for silent reset
3146 priv->IrpPendingCount = 1;
3147 priv->ResetProgress = RESET_TYPE_NORESET;
3148 priv->bForcedSilentReset = 0;
3149 priv->bDisableNormalResetCheck = false;
3150 priv->force_reset = false;
3152 priv->ieee80211->FwRWRF = 0; //we don't use FW read/write RF until stable firmware is available.
3153 priv->ieee80211->current_network.beacon_interval = DEFAULT_BEACONINTERVAL;
3154 priv->ieee80211->iw_mode = IW_MODE_INFRA;
3155 priv->ieee80211->softmac_features = IEEE_SOFTMAC_SCAN |
3156 IEEE_SOFTMAC_ASSOCIATE | IEEE_SOFTMAC_PROBERQ |
3157 IEEE_SOFTMAC_PROBERS | IEEE_SOFTMAC_TX_QUEUE |
3158 IEEE_SOFTMAC_BEACONS;//added by amy 080604 //| //IEEE_SOFTMAC_SINGLE_QUEUE;
3160 priv->ieee80211->active_scan = 1;
3161 priv->ieee80211->modulation = IEEE80211_CCK_MODULATION | IEEE80211_OFDM_MODULATION;
3162 priv->ieee80211->host_encrypt = 1;
3163 priv->ieee80211->host_decrypt = 1;
3164 priv->ieee80211->start_send_beacons = NULL;//rtl819xusb_beacon_tx;//-by amy 080604
3165 priv->ieee80211->stop_send_beacons = NULL;//rtl8192_beacon_stop;//-by amy 080604
3166 priv->ieee80211->softmac_hard_start_xmit = rtl8192_hard_start_xmit;
3167 priv->ieee80211->set_chan = rtl8192_set_chan;
3168 priv->ieee80211->link_change = priv->ops->rtl819x_link_change;
3169 priv->ieee80211->softmac_data_hard_start_xmit = rtl8192_hard_data_xmit;
3170 priv->ieee80211->data_hard_stop = rtl8192_data_hard_stop;
3171 priv->ieee80211->data_hard_resume = rtl8192_data_hard_resume;
3172 priv->ieee80211->init_wmmparam_flag = 0;
3173 priv->ieee80211->fts = DEFAULT_FRAG_THRESHOLD;
3174 priv->ieee80211->check_nic_enough_desc = check_nic_enough_desc;
3175 priv->ieee80211->tx_headroom = TX_PACKET_SHIFT_BYTES;
3176 priv->ieee80211->qos_support = 1;
3178 //added by WB
3179 // priv->ieee80211->SwChnlByTimerHandler = rtl8192_phy_SwChnl;
3180 priv->ieee80211->SetBWModeHandler = rtl8192_SetBWMode;
3181 priv->ieee80211->handle_assoc_response = rtl8192_handle_assoc_response;
3182 priv->ieee80211->handle_beacon = rtl8192_handle_beacon;
3183 //for LPS
3184 priv->ieee80211->sta_wake_up = rtl8192_hw_wakeup;
3185 // priv->ieee80211->ps_request_tx_ack = rtl8192_rq_tx_ack;
3186 priv->ieee80211->enter_sleep_state = rtl8192_hw_to_sleep;
3187 priv->ieee80211->ps_is_queue_empty = rtl8192_is_tx_queue_empty;
3188 //added by david
3189 priv->ieee80211->GetNmodeSupportBySecCfg = GetNmodeSupportBySecCfg8192;
3190 priv->ieee80211->GetHalfNmodeSupportByAPsHandler = GetHalfNmodeSupportByAPs819xUsb;
3191 priv->ieee80211->SetWirelessMode = rtl8192_SetWirelessMode;
3192 //added by amy
3193 priv->ieee80211->InitialGainHandler = priv->ops->rtl819x_initial_gain;
3194 priv->card_type = USB;
3196 //1 RTL8192SU/
3197 priv->ieee80211->current_network.beacon_interval = DEFAULT_BEACONINTERVAL;
3198 priv->ieee80211->SetFwCmdHandler = HalSetFwCmd8192S;
3199 priv->bRFSiOrPi = 0;//o=si,1=pi;
3200 //lzm add
3201 priv->bInHctTest = false;
3203 priv->MidHighPwrTHR_L1 = 0x3B;
3204 priv->MidHighPwrTHR_L2 = 0x40;
3206 if(priv->bInHctTest)
3208 priv->ShortRetryLimit = HAL_RETRY_LIMIT_AP_ADHOC;
3209 priv->LongRetryLimit = HAL_RETRY_LIMIT_AP_ADHOC;
3211 else
3213 priv->ShortRetryLimit = HAL_RETRY_LIMIT_INFRA;
3214 priv->LongRetryLimit = HAL_RETRY_LIMIT_INFRA;
3217 priv->SetFwCmdInProgress = false; //is set FW CMD in Progress? 92S only
3218 priv->CurrentFwCmdIO = 0;
3220 priv->MinSpaceCfg = 0;
3222 priv->EarlyRxThreshold = 7;
3223 priv->enable_gpio0 = 0;
3224 priv->TransmitConfig =
3225 ((u32)TCR_MXDMA_2048<<TCR_MXDMA_OFFSET) | // Max DMA Burst Size per Tx DMA Burst, 7: reservied.
3226 (priv->ShortRetryLimit<<TCR_SRL_OFFSET) | // Short retry limit
3227 (priv->LongRetryLimit<<TCR_LRL_OFFSET) | // Long retry limit
3228 (false ? TCR_SAT : 0); // FALSE: HW provies PLCP length and LENGEXT, TURE: SW proiveds them
3229 if(priv->bInHctTest)
3230 priv->ReceiveConfig = //priv->CSMethod |
3231 RCR_AMF | RCR_ADF | //RCR_AAP | //accept management/data
3232 RCR_ACF |RCR_APPFCS| //accept control frame for SW AP needs PS-poll, 2005.07.07, by rcnjko.
3233 RCR_AB | RCR_AM | RCR_APM | //accept BC/MC/UC
3234 RCR_AICV | RCR_ACRC32 | //accept ICV/CRC error packet
3235 RCR_APP_PHYST_STAFF | RCR_APP_PHYST_RXFF | // Accept PHY status
3236 ((u32)7<<RCR_MXDMA_OFFSET) | // Max DMA Burst Size per Rx DMA Burst, 7: unlimited.
3237 (priv->EarlyRxThreshold<<RCR_FIFO_OFFSET) | // Rx FIFO Threshold, 7: No Rx threshold.
3238 (priv->EarlyRxThreshold == 7 ? RCR_OnlyErlPkt:0);
3239 else
3240 priv->ReceiveConfig = //priv->CSMethod |
3241 RCR_AMF | RCR_ADF | RCR_AB |
3242 RCR_AM | RCR_APM |RCR_AAP |RCR_ADD3|RCR_APP_ICV|
3243 RCR_APP_PHYST_STAFF | RCR_APP_PHYST_RXFF | // Accept PHY status
3244 RCR_APP_MIC | RCR_APPFCS;
3246 // <Roger_EXP> 2008.06.16.
3247 priv->IntrMask = (u16)(IMR_ROK | IMR_VODOK | IMR_VIDOK | IMR_BEDOK | IMR_BKDOK | \
3248 IMR_HCCADOK | IMR_MGNTDOK | IMR_COMDOK | IMR_HIGHDOK | \
3249 IMR_BDOK | IMR_RXCMDOK | /*IMR_TIMEOUT0 |*/ IMR_RDU | IMR_RXFOVW | \
3250 IMR_TXFOVW | IMR_BcnInt | IMR_TBDOK | IMR_TBDER);
3252 //1 End
3255 priv->AcmControl = 0;
3256 priv->pFirmware = (rt_firmware*)vmalloc(sizeof(rt_firmware));
3257 if (priv->pFirmware)
3258 memset(priv->pFirmware, 0, sizeof(rt_firmware));
3260 /* rx related queue */
3261 skb_queue_head_init(&priv->rx_queue);
3262 skb_queue_head_init(&priv->skb_queue);
3264 /* Tx related queue */
3265 for(i = 0; i < MAX_QUEUE_SIZE; i++) {
3266 skb_queue_head_init(&priv->ieee80211->skb_waitQ [i]);
3268 for(i = 0; i < MAX_QUEUE_SIZE; i++) {
3269 skb_queue_head_init(&priv->ieee80211->skb_aggQ [i]);
3271 for(i = 0; i < MAX_QUEUE_SIZE; i++) {
3272 skb_queue_head_init(&priv->ieee80211->skb_drv_aggQ [i]);
3274 priv->rf_set_chan = rtl8192_phy_SwChnl;
3277 //init lock here
3278 static void rtl8192_init_priv_lock(struct r8192_priv* priv)
3280 spin_lock_init(&priv->tx_lock);
3281 spin_lock_init(&priv->irq_lock);//added by thomas
3282 //spin_lock_init(&priv->rf_lock);//use rf_sem, or will crash in some OS.
3283 sema_init(&priv->wx_sem,1);
3284 sema_init(&priv->rf_sem,1);
3285 spin_lock_init(&priv->ps_lock);
3286 mutex_init(&priv->mutex);
3289 extern void rtl819x_watchdog_wqcallback(struct work_struct *work);
3291 void rtl8192_irq_rx_tasklet(struct r8192_priv *priv);
3292 //init tasklet and wait_queue here. only 2.6 above kernel is considered
3293 #define DRV_NAME "wlan0"
3294 static void rtl8192_init_priv_task(struct net_device* dev)
3296 struct r8192_priv *priv = ieee80211_priv(dev);
3298 #ifdef PF_SYNCTHREAD
3299 priv->priv_wq = create_workqueue(DRV_NAME,0);
3300 #else
3301 priv->priv_wq = create_workqueue(DRV_NAME);
3302 #endif
3304 INIT_WORK(&priv->reset_wq, rtl8192_restart);
3306 //INIT_DELAYED_WORK(&priv->watch_dog_wq, hal_dm_watchdog);
3307 INIT_DELAYED_WORK(&priv->watch_dog_wq, rtl819x_watchdog_wqcallback);
3308 INIT_DELAYED_WORK(&priv->txpower_tracking_wq, dm_txpower_trackingcallback);
3309 // INIT_DELAYED_WORK(&priv->gpio_change_rf_wq, dm_gpio_change_rf_callback);
3310 INIT_DELAYED_WORK(&priv->rfpath_check_wq, dm_rf_pathcheck_workitemcallback);
3311 INIT_DELAYED_WORK(&priv->update_beacon_wq, rtl8192_update_beacon);
3312 INIT_DELAYED_WORK(&priv->initialgain_operate_wq, InitialGainOperateWorkItemCallBack);
3313 //INIT_WORK(&priv->SwChnlWorkItem, rtl8192_SwChnl_WorkItem);
3314 //INIT_WORK(&priv->SetBWModeWorkItem, rtl8192_SetBWModeWorkItem);
3315 INIT_WORK(&priv->qos_activate, rtl8192_qos_activate);
3316 INIT_DELAYED_WORK(&priv->ieee80211->hw_wakeup_wq,(void*) rtl8192_hw_wakeup_wq);
3317 INIT_DELAYED_WORK(&priv->ieee80211->hw_sleep_wq,(void*) rtl8192_hw_sleep_wq);
3319 tasklet_init(&priv->irq_rx_tasklet,
3320 (void(*)(unsigned long))rtl8192_irq_rx_tasklet,
3321 (unsigned long)priv);
3324 //used to swap endian. as ntohl & htonl are not neccessary to swap endian, so use this instead.
3325 static inline u16 endian_swap(u16* data)
3327 u16 tmp = *data;
3328 *data = (tmp >> 8) | (tmp << 8);
3329 return *data;
3332 u8 rtl8192SU_UsbOptionToEndPointNumber(u8 UsbOption)
3334 u8 nEndPoint = 0;
3335 switch(UsbOption)
3337 case 0:
3338 nEndPoint = 6;
3339 break;
3340 case 1:
3341 nEndPoint = 11;
3342 break;
3343 case 2:
3344 nEndPoint = 4;
3345 break;
3346 default:
3347 RT_TRACE(COMP_INIT, "UsbOptionToEndPointNumber(): Invalid UsbOption(%#x)\n", UsbOption);
3348 break;
3350 return nEndPoint;
3353 u8 rtl8192SU_BoardTypeToRFtype(struct net_device* dev, u8 Boardtype)
3355 u8 RFtype = RF_1T2R;
3357 switch(Boardtype)
3359 case 0:
3360 RFtype = RF_1T1R;
3361 break;
3362 case 1:
3363 RFtype = RF_1T2R;
3364 break;
3365 case 2:
3366 RFtype = RF_2T2R;
3367 break;
3368 case 3:
3369 RFtype = RF_2T2R_GREEN;
3370 break;
3371 default:
3372 break;
3375 return RFtype;
3378 void update_hal_variables(struct r8192_priv *priv)
3380 int rf_path;
3381 int i;
3382 u8 index;
3384 for (rf_path = 0; rf_path < 2; rf_path++) {
3385 for (i = 0; i < 3; i++) {
3386 RT_TRACE((COMP_INIT), "CCK RF-%d CHan_Area-%d = 0x%x\n", rf_path, i, priv->RfCckChnlAreaTxPwr[rf_path][i]);
3387 RT_TRACE((COMP_INIT), "OFDM-1T RF-%d CHan_Area-%d = 0x%x\n", rf_path, i, priv->RfOfdmChnlAreaTxPwr1T[rf_path][i]);
3388 RT_TRACE((COMP_INIT), "OFDM-2T RF-%d CHan_Area-%d = 0x%x\n", rf_path, i, priv->RfOfdmChnlAreaTxPwr2T[rf_path][i]);
3390 /* Assign dedicated channel tx power */
3391 for(i = 0; i < 14; i++) {
3392 /* channel 1-3 use the same Tx Power Level. */
3393 if (i < 3) /* Channel 1-3 */
3394 index = 0;
3395 else if (i < 9) /* Channel 4-9 */
3396 index = 1;
3397 else /* Channel 10-14 */
3398 index = 2;
3399 /* Record A & B CCK /OFDM - 1T/2T Channel area tx power */
3400 priv->RfTxPwrLevelCck[rf_path][i] = priv->RfCckChnlAreaTxPwr[rf_path][index];
3401 priv->RfTxPwrLevelOfdm1T[rf_path][i] = priv->RfOfdmChnlAreaTxPwr1T[rf_path][index];
3402 priv->RfTxPwrLevelOfdm2T[rf_path][i] = priv->RfOfdmChnlAreaTxPwr2T[rf_path][index];
3403 if (rf_path == 0) {
3404 priv->TxPowerLevelOFDM24G[i] = priv->RfTxPwrLevelOfdm1T[rf_path][i] ;
3405 priv->TxPowerLevelCCK[i] = priv->RfTxPwrLevelCck[rf_path][i];
3408 for(i = 0; i < 14; i++) {
3409 RT_TRACE((COMP_INIT),
3410 "Rf-%d TxPwr CH-%d CCK OFDM_1T OFDM_2T= 0x%x/0x%x/0x%x\n",
3411 rf_path, i, priv->RfTxPwrLevelCck[rf_path][i],
3412 priv->RfTxPwrLevelOfdm1T[rf_path][i] ,
3413 priv->RfTxPwrLevelOfdm2T[rf_path][i] );
3419 * Description:
3420 * Config HW adapter information into initial value.
3422 * Assumption:
3423 * 1. After Auto load fail(i.e, check CR9346 fail)
3426 void rtl8192SU_ConfigAdapterInfo8192SForAutoLoadFail(struct net_device *dev)
3428 struct r8192_priv *priv = ieee80211_priv(dev);
3429 u8 rf_path; /* For EEPROM/EFUSE After V0.6_1117 */
3430 int i;
3432 RT_TRACE(COMP_INIT, "====> ConfigAdapterInfo8192SForAutoLoadFail\n");
3434 /* Isolation signals from Loader */
3435 write_nic_byte(dev, SYS_ISO_CTRL+1, 0xE8);
3436 mdelay(10);
3437 write_nic_byte(dev, PMC_FSM, 0x02); /* Enable Loader Data Keep */
3439 /* Initialize IC Version && Channel Plan */
3440 priv->eeprom_vid = 0;
3441 priv->eeprom_pid = 0;
3442 priv->card_8192_version = 0;
3443 priv->eeprom_ChannelPlan = 0;
3444 priv->eeprom_CustomerID = 0;
3445 priv->eeprom_SubCustomerID = 0;
3446 priv->bIgnoreDiffRateTxPowerOffset = false;
3448 RT_TRACE(COMP_INIT, "EEPROM VID = 0x%4x\n", priv->eeprom_vid);
3449 RT_TRACE(COMP_INIT, "EEPROM PID = 0x%4x\n", priv->eeprom_pid);
3450 RT_TRACE(COMP_INIT, "EEPROM Customer ID: 0x%2x\n",
3451 priv->eeprom_CustomerID);
3452 RT_TRACE(COMP_INIT, "EEPROM SubCustomer ID: 0x%2x\n",
3453 priv->eeprom_SubCustomerID);
3454 RT_TRACE(COMP_INIT, "EEPROM ChannelPlan = 0x%4x\n",
3455 priv->eeprom_ChannelPlan);
3456 RT_TRACE(COMP_INIT, "IgnoreDiffRateTxPowerOffset = %d\n",
3457 priv->bIgnoreDiffRateTxPowerOffset);
3459 priv->EEPROMUsbOption = EEPROM_USB_Default_OPTIONAL_FUNC;
3460 RT_TRACE(COMP_INIT, "USB Option = %#x\n", priv->EEPROMUsbOption);
3462 for(i=0; i<5; i++)
3463 priv->EEPROMUsbPhyParam[i] = EEPROM_USB_Default_PHY_PARAM;
3467 * In this case, we randomly assign a MAC address here.
3469 static u8 sMacAddr[6] = {0x00, 0xE0, 0x4C, 0x81, 0x92, 0x00};
3470 for(i = 0; i < 6; i++)
3471 dev->dev_addr[i] = sMacAddr[i];
3473 /* NicIFSetMacAddress(Adapter, Adapter->PermanentAddress); */
3474 write_nic_dword(dev, IDR0, ((u32*)dev->dev_addr)[0]);
3475 write_nic_word(dev, IDR4, ((u16*)(dev->dev_addr + 4))[0]);
3477 RT_TRACE(COMP_INIT,
3478 "ReadAdapterInfo8192SEFuse(), Permanent Address = %pM\n",
3479 dev->dev_addr);
3481 priv->EEPROMBoardType = EEPROM_Default_BoardType;
3482 priv->rf_type = RF_1T2R; /* RF_2T2R */
3483 priv->EEPROMTxPowerDiff = EEPROM_Default_PwDiff;
3484 priv->EEPROMThermalMeter = EEPROM_Default_ThermalMeter;
3485 priv->EEPROMCrystalCap = EEPROM_Default_CrystalCap;
3486 priv->EEPROMTxPwrBase = EEPROM_Default_TxPowerBase;
3487 priv->EEPROMTSSI_A = EEPROM_Default_TSSI;
3488 priv->EEPROMTSSI_B = EEPROM_Default_TSSI;
3489 priv->EEPROMTxPwrTkMode = EEPROM_Default_TxPwrTkMode;
3491 for (rf_path = 0; rf_path < 2; rf_path++)
3493 for (i = 0; i < 3; i++)
3495 /* Read CCK RF A & B Tx power */
3496 priv->RfCckChnlAreaTxPwr[rf_path][i] =
3497 priv->RfOfdmChnlAreaTxPwr1T[rf_path][i] =
3498 priv->RfOfdmChnlAreaTxPwr2T[rf_path][i] =
3499 (u8)(EEPROM_Default_TxPower & 0xff);
3503 update_hal_variables(priv);
3506 * Update remaining HAL variables.
3508 priv->TSSI_13dBm = priv->EEPROMThermalMeter *100;
3509 priv->LegacyHTTxPowerDiff = priv->EEPROMTxPowerDiff; /* new */
3510 priv->TxPowerDiff = priv->EEPROMTxPowerDiff;
3511 /* Antenna B gain offset to antenna A, bit0~3 */
3512 /* priv->AntennaTxPwDiff[0] = (priv->EEPROMTxPowerDiff & 0xf); */
3513 /* Antenna C gain offset to antenna A, bit4~7 */
3514 /* priv->AntennaTxPwDiff[1] = ((priv->EEPROMTxPowerDiff & 0xf0)>>4); */
3515 /* CrystalCap, bit12~15 */
3516 priv->CrystalCap = priv->EEPROMCrystalCap;
3517 /* ThermalMeter, bit0~3 for RFIC1, bit4~7 for RFIC2 */
3518 priv->ThermalMeter[0] = priv->EEPROMThermalMeter;
3519 priv->LedStrategy = SW_LED_MODE0;
3521 init_rate_adaptive(dev);
3523 RT_TRACE(COMP_INIT, "<==== ConfigAdapterInfo8192SForAutoLoadFail\n");
3527 * Description:
3528 * Read HW adapter information by E-Fuse
3529 * or EEPROM according CR9346 reported.
3531 * Assumption:
3532 * 1. CR9346 regiser has verified.
3533 * 2. PASSIVE_LEVEL (USB interface)
3535 void rtl8192SU_ReadAdapterInfo8192SUsb(struct net_device *dev)
3537 struct r8192_priv *priv = ieee80211_priv(dev);
3538 u16 i;
3539 u8 tmpU1b, tempval;
3540 u16 EEPROMId;
3541 u8 hwinfo[HWSET_MAX_SIZE_92S];
3542 u8 rf_path, index; /* For EEPROM/EFUSE After V0.6_1117 */
3543 struct eeprom_93cx6 eeprom;
3544 u16 eeprom_val;
3546 eeprom.data = dev;
3547 eeprom.register_read = rtl819x_eeprom_register_read;
3548 eeprom.register_write = rtl819x_eeprom_register_write;
3549 eeprom.width = PCI_EEPROM_WIDTH_93C46;
3552 * The following operation are prevent Efuse leakage by turn on 2.5V.
3554 tmpU1b = read_nic_byte(dev, EFUSE_TEST+3);
3555 write_nic_byte(dev, EFUSE_TEST+3, tmpU1b|0x80);
3556 mdelay(10);
3557 write_nic_byte(dev, EFUSE_TEST+3, (tmpU1b&(~BIT7)));
3559 /* Retrieve Chip version. */
3560 priv->card_8192_version = (VERSION_8192S)((read_nic_dword(dev, PMC_FSM)>>16)&0xF);
3561 RT_TRACE(COMP_INIT, "Chip Version ID: 0x%2x\n", priv->card_8192_version);
3563 switch (priv->card_8192_version) {
3564 case 0:
3565 RT_TRACE(COMP_INIT, "Chip Version ID: VERSION_8192S_ACUT.\n");
3566 break;
3567 case 1:
3568 RT_TRACE(COMP_INIT, "Chip Version ID: VERSION_8192S_BCUT.\n");
3569 break;
3570 case 2:
3571 RT_TRACE(COMP_INIT, "Chip Version ID: VERSION_8192S_CCUT.\n");
3572 break;
3573 default:
3574 RT_TRACE(COMP_INIT, "Unknown Chip Version!!\n");
3575 priv->card_8192_version = VERSION_8192S_BCUT;
3576 break;
3579 if (priv->EepromOrEfuse) { /* Read from EEPROM */
3580 /* Isolation signals from Loader */
3581 write_nic_byte(dev, SYS_ISO_CTRL+1, 0xE8);
3582 mdelay(10);
3583 /* Enable Loader Data Keep */
3584 write_nic_byte(dev, PMC_FSM, 0x02);
3585 /* Read all Content from EEPROM or EFUSE. */
3586 for (i = 0; i < HWSET_MAX_SIZE_92S; i += 2) {
3587 eeprom_93cx6_read(&eeprom, (u16) (i>>1), &eeprom_val);
3588 *((u16 *)(&hwinfo[i])) = eeprom_val;
3590 } else if (!(priv->EepromOrEfuse)) { /* Read from EFUSE */
3591 /* Read EFUSE real map to shadow. */
3592 EFUSE_ShadowMapUpdate(dev);
3593 memcpy(hwinfo, &priv->EfuseMap[EFUSE_INIT_MAP][0], HWSET_MAX_SIZE_92S);
3594 } else {
3595 RT_TRACE(COMP_INIT, "%s(): Invalid boot type", __func__);
3599 * Even though CR9346 regiser can verify whether Autoload
3600 * is success or not, but we still double check ID codes for 92S here
3601 * (e.g., due to HW GPIO polling fail issue)
3603 EEPROMId = *((u16 *)&hwinfo[0]);
3604 if (EEPROMId != RTL8190_EEPROM_ID) {
3605 RT_TRACE(COMP_INIT, "ID(%#x) is invalid!!\n", EEPROMId);
3606 priv->bTXPowerDataReadFromEEPORM = FALSE;
3607 priv->AutoloadFailFlag=TRUE;
3608 } else {
3609 priv->AutoloadFailFlag=FALSE;
3610 priv->bTXPowerDataReadFromEEPORM = TRUE;
3612 /* Read IC Version && Channel Plan */
3613 if (!priv->AutoloadFailFlag) {
3614 /* VID, PID */
3615 priv->eeprom_vid = *(u16 *)&hwinfo[EEPROM_VID];
3616 priv->eeprom_pid = *(u16 *)&hwinfo[EEPROM_PID];
3617 priv->bIgnoreDiffRateTxPowerOffset = false; //cosa for test
3620 /* EEPROM Version ID, Channel plan */
3621 priv->EEPROMVersion = *(u8 *)&hwinfo[EEPROM_Version];
3622 priv->eeprom_ChannelPlan = *(u8 *)&hwinfo[EEPROM_ChannelPlan];
3624 /* Customer ID, 0x00 and 0xff are reserved for Realtek. */
3625 priv->eeprom_CustomerID = *(u8 *)&hwinfo[EEPROM_CustomID];
3626 priv->eeprom_SubCustomerID = *(u8 *)&hwinfo[EEPROM_SubCustomID];
3627 } else {
3628 rtl8192SU_ConfigAdapterInfo8192SForAutoLoadFail(dev);
3629 return;
3632 RT_TRACE(COMP_INIT, "EEPROM Id = 0x%4x\n", EEPROMId);
3633 RT_TRACE(COMP_INIT, "EEPROM VID = 0x%4x\n", priv->eeprom_vid);
3634 RT_TRACE(COMP_INIT, "EEPROM PID = 0x%4x\n", priv->eeprom_pid);
3635 RT_TRACE(COMP_INIT, "EEPROM Version ID: 0x%2x\n", priv->EEPROMVersion);
3636 RT_TRACE(COMP_INIT, "EEPROM Customer ID: 0x%2x\n", priv->eeprom_CustomerID);
3637 RT_TRACE(COMP_INIT, "EEPROM SubCustomer ID: 0x%2x\n", priv->eeprom_SubCustomerID);
3638 RT_TRACE(COMP_INIT, "EEPROM ChannelPlan = 0x%4x\n", priv->eeprom_ChannelPlan);
3639 RT_TRACE(COMP_INIT, "bIgnoreDiffRateTxPowerOffset = %d\n", priv->bIgnoreDiffRateTxPowerOffset);
3641 /* Read USB optional function. */
3642 if (!priv->AutoloadFailFlag) {
3643 priv->EEPROMUsbOption = *(u8 *)&hwinfo[EEPROM_USB_OPTIONAL];
3644 } else {
3645 priv->EEPROMUsbOption = EEPROM_USB_Default_OPTIONAL_FUNC;
3648 priv->EEPROMUsbEndPointNumber = rtl8192SU_UsbOptionToEndPointNumber((priv->EEPROMUsbOption&EEPROM_EP_NUMBER)>>3);
3650 RT_TRACE(COMP_INIT, "USB Option = %#x\n", priv->EEPROMUsbOption);
3651 RT_TRACE(COMP_INIT, "EndPoint Number = %#x\n", priv->EEPROMUsbEndPointNumber);
3653 #ifdef TO_DO_LIST
3655 // Decide CustomerID according to VID/DID or EEPROM
3657 switch(pHalData->EEPROMCustomerID)
3659 case EEPROM_CID_ALPHA:
3660 pMgntInfo->CustomerID = RT_CID_819x_ALPHA;
3661 break;
3663 case EEPROM_CID_CAMEO:
3664 pMgntInfo->CustomerID = RT_CID_819x_CAMEO;
3665 break;
3667 case EEPROM_CID_SITECOM:
3668 pMgntInfo->CustomerID = RT_CID_819x_Sitecom;
3669 RT_TRACE(COMP_INIT, DBG_LOUD, ("CustomerID = 0x%4x\n", pMgntInfo->CustomerID));
3671 break;
3673 case EEPROM_CID_WHQL:
3674 Adapter->bInHctTest = TRUE;
3676 pMgntInfo->bSupportTurboMode = FALSE;
3677 pMgntInfo->bAutoTurboBy8186 = FALSE;
3679 pMgntInfo->PowerSaveControl.bInactivePs = FALSE;
3680 pMgntInfo->PowerSaveControl.bIPSModeBackup = FALSE;
3681 pMgntInfo->PowerSaveControl.bLeisurePs = FALSE;
3682 pMgntInfo->keepAliveLevel = 0;
3683 break;
3685 default:
3686 pMgntInfo->CustomerID = RT_CID_DEFAULT;
3687 break;
3692 // Led mode
3694 switch(pMgntInfo->CustomerID)
3696 case RT_CID_DEFAULT:
3697 case RT_CID_819x_ALPHA:
3698 pHalData->LedStrategy = SW_LED_MODE1;
3699 pHalData->bRegUseLed = TRUE;
3700 pHalData->SwLed1.bLedOn = TRUE;
3701 break;
3702 case RT_CID_819x_CAMEO:
3703 pHalData->LedStrategy = SW_LED_MODE1;
3704 pHalData->bRegUseLed = TRUE;
3705 break;
3707 case RT_CID_819x_Sitecom:
3708 pHalData->LedStrategy = SW_LED_MODE2;
3709 pHalData->bRegUseLed = TRUE;
3710 break;
3712 default:
3713 pHalData->LedStrategy = SW_LED_MODE0;
3714 break;
3716 #endif
3718 // Read USB PHY parameters.
3719 for(i=0; i<5; i++)
3720 priv->EEPROMUsbPhyParam[i] = *(u8 *)&hwinfo[EEPROM_USB_PHY_PARA1+i];
3722 //RT_PRINT_DATA(COMP_EFUSE, DBG_LOUD, ("USB PHY Param: \n"), pHalData->EEPROMUsbPhyParam, 5);
3725 //Read Permanent MAC address
3726 for(i=0; i<6; i++)
3727 dev->dev_addr[i] = *(u8 *)&hwinfo[EEPROM_NODE_ADDRESS_BYTE_0+i];
3729 //NicIFSetMacAddress(Adapter, Adapter->PermanentAddress);
3730 write_nic_dword(dev, IDR0, ((u32*)dev->dev_addr)[0]);
3731 write_nic_word(dev, IDR4, ((u16*)(dev->dev_addr + 4))[0]);
3733 RT_TRACE(COMP_INIT,
3734 "ReadAdapterInfo8192SEFuse(), Permanent Address = %pM\n",
3735 dev->dev_addr);
3738 // Get CustomerID(Boad Type)
3739 // i.e., 0x0: RTL8188SU, 0x1: RTL8191SU, 0x2: RTL8192SU, 0x3: RTL8191GU.
3740 // Others: Reserved. Default is 0x2: RTL8192SU.
3742 //if(!priv->AutoloadFailFlag)
3744 priv->EEPROMBoardType = *(u8 *)&hwinfo[EEPROM_BoardType];
3745 priv->rf_type = rtl8192SU_BoardTypeToRFtype(dev, priv->EEPROMBoardType);
3747 //else
3749 // priv->EEPROMBoardType = EEPROM_Default_BoardType;
3750 // priv->rf_type = RF_1T2R;
3753 priv->rf_chip = RF_6052;
3755 priv->rf_chip = RF_6052;//lzm test
3756 RT_TRACE(COMP_INIT, "BoardType = 0x%2x\n", priv->EEPROMBoardType);
3757 RT_TRACE(COMP_INIT, "RF_Type = 0x%2x\n", priv->rf_type);
3760 // Read antenna tx power offset of B/C/D to A from EEPROM
3761 // and read ThermalMeter from EEPROM
3763 //if(!priv->AutoloadFailFlag)
3765 priv->EEPROMTxPowerDiff = *(u8 *)&hwinfo[EEPROM_PwDiff];
3766 priv->EEPROMThermalMeter = *(u8 *)&hwinfo[EEPROM_ThermalMeter];
3768 //else
3770 // priv->EEPROMTxPowerDiff = EEPROM_Default_PwDiff;
3771 // priv->EEPROMThermalMeter = EEPROM_Default_ThermalMeter;
3774 RT_TRACE(COMP_INIT, "PwDiff = %#x\n", priv->EEPROMTxPowerDiff);
3775 RT_TRACE(COMP_INIT, "ThermalMeter = %#x\n", priv->EEPROMThermalMeter);
3778 // Read Tx Power gain offset of legacy OFDM to HT rate.
3779 // Read CrystalCap from EEPROM
3781 //if(!priv->AutoloadFailFlag)
3783 priv->EEPROMCrystalCap = *(u8 *)&hwinfo[EEPROM_CrystalCap];
3785 //else
3787 // priv->EEPROMCrystalCap = EEPROM_Default_CrystalCap;
3790 RT_TRACE(COMP_INIT, "CrystalCap = %#x\n", priv->EEPROMCrystalCap);
3793 // Get Tx Power Base.
3795 //if(!priv->AutoloadFailFlag)
3797 priv->EEPROMTxPwrBase = *(u8 *)&hwinfo[EEPROM_TxPowerBase];
3799 //else
3801 // priv->EEPROMTxPwrBase = EEPROM_Default_TxPowerBase;
3804 RT_TRACE(COMP_INIT, "TxPwrBase = %#x\n", priv->EEPROMTxPwrBase);
3808 // Get TSSI value for each path.
3810 //if(!priv->AutoloadFailFlag)
3812 priv->EEPROMTSSI_A = *(u8 *)&hwinfo[EEPROM_TSSI_A];
3813 priv->EEPROMTSSI_B = *(u8 *)&hwinfo[EEPROM_TSSI_B];
3815 //else
3816 //{ // Default setting for Empty EEPROM
3817 // priv->EEPROMTSSI_A = EEPROM_Default_TSSI;
3818 // priv->EEPROMTSSI_B = EEPROM_Default_TSSI;
3821 RT_TRACE(COMP_INIT, "TSSI_A = %#x, TSSI_B = %#x\n", priv->EEPROMTSSI_A, priv->EEPROMTSSI_B);
3824 // Get Tx Power tracking mode.
3826 //if(!priv->AutoloadFailFlag)
3828 priv->EEPROMTxPwrTkMode = *(u8 *)&hwinfo[EEPROM_TxPwTkMode];
3831 RT_TRACE(COMP_INIT, "TxPwrTkMod = %#x\n", priv->EEPROMTxPwrTkMode);
3836 // Buffer TxPwIdx(i.e., from offset 0x55~0x66, total 18Bytes)
3837 // Update CCK, OFDM (1T/2T)Tx Power Index from above buffer.
3841 // Get Tx Power Level by Channel
3843 //if(!priv->AutoloadFailFlag)
3845 // Read Tx power of Channel 1 ~ 14 from EFUSE.
3846 // 92S suupport RF A & B
3847 for (rf_path = 0; rf_path < 2; rf_path++)
3849 for (i = 0; i < 3; i++)
3851 // Read CCK RF A & B Tx power
3852 priv->RfCckChnlAreaTxPwr[rf_path][i] =
3853 hwinfo[EEPROM_TxPwIndex+rf_path*3+i];
3855 // Read OFDM RF A & B Tx power for 1T
3856 priv->RfOfdmChnlAreaTxPwr1T[rf_path][i] =
3857 hwinfo[EEPROM_TxPwIndex+6+rf_path*3+i];
3859 // Read OFDM RF A & B Tx power for 2T
3860 priv->RfOfdmChnlAreaTxPwr2T[rf_path][i] =
3861 hwinfo[EEPROM_TxPwIndex+12+rf_path*3+i];
3866 update_hal_variables(priv);
3870 // 2009/02/09 Cosa add for new EEPROM format
3872 for(i=0; i<14; i++) // channel 1~3 use the same Tx Power Level.
3874 // Read tx power difference between HT OFDM 20/40 MHZ
3875 if (i < 3) // Cjanel 1-3
3876 index = 0;
3877 else if (i < 9) // Channel 4-9
3878 index = 1;
3879 else // Channel 10-14
3880 index = 2;
3882 tempval = (*(u8 *)&hwinfo[EEPROM_TX_PWR_HT20_DIFF+index])&0xff;
3883 priv->TxPwrHt20Diff[RF90_PATH_A][i] = (tempval&0xF);
3884 priv->TxPwrHt20Diff[RF90_PATH_B][i] = ((tempval>>4)&0xF);
3886 // Read OFDM<->HT tx power diff
3887 if (i < 3) // Cjanel 1-3
3888 tempval = (*(u8 *)&hwinfo[EEPROM_TX_PWR_OFDM_DIFF])&0xff;
3889 else if (i < 9) // Channel 4-9
3890 tempval = (*(u8 *)&hwinfo[EEPROM_PwDiff])&0xff;
3891 else // Channel 10-14
3892 tempval = (*(u8 *)&hwinfo[EEPROM_TX_PWR_OFDM_DIFF+1])&0xff;
3894 //cosa tempval = (*(u1Byte *)&hwinfo[EEPROM_TX_PWR_OFDM_DIFF+index])&0xff;
3895 priv->TxPwrLegacyHtDiff[RF90_PATH_A][i] = (tempval&0xF);
3896 priv->TxPwrLegacyHtDiff[RF90_PATH_B][i] = ((tempval>>4)&0xF);
3899 // Read Band Edge tx power offset and check if user enable the ability
3901 // HT 40 band edge channel
3902 tempval = (*(u8 *)&hwinfo[EEPROM_TX_PWR_BAND_EDGE])&0xff;
3903 priv->TxPwrbandEdgeHt40[RF90_PATH_A][0] = (tempval&0xF); // Band edge low channel
3904 priv->TxPwrbandEdgeHt40[RF90_PATH_A][1] = ((tempval>>4)&0xF); // Band edge high channel
3905 tempval = (*(u8 *)&hwinfo[EEPROM_TX_PWR_BAND_EDGE+1])&0xff;
3906 priv->TxPwrbandEdgeHt40[RF90_PATH_B][0] = (tempval&0xF); // Band edge low channel
3907 priv->TxPwrbandEdgeHt40[RF90_PATH_B][1] = ((tempval>>4)&0xF); // Band edge high channel
3908 // HT 20 band edge channel
3909 tempval = (*(u8 *)&hwinfo[EEPROM_TX_PWR_BAND_EDGE+2])&0xff;
3910 priv->TxPwrbandEdgeHt20[RF90_PATH_A][0] = (tempval&0xF); // Band edge low channel
3911 priv->TxPwrbandEdgeHt20[RF90_PATH_A][1] = ((tempval>>4)&0xF); // Band edge high channel
3912 tempval = (*(u8 *)&hwinfo[EEPROM_TX_PWR_BAND_EDGE+3])&0xff;
3913 priv->TxPwrbandEdgeHt20[RF90_PATH_B][0] = (tempval&0xF); // Band edge low channel
3914 priv->TxPwrbandEdgeHt20[RF90_PATH_B][1] = ((tempval>>4)&0xF); // Band edge high channel
3915 // OFDM band edge channel
3916 tempval = (*(u8 *)&hwinfo[EEPROM_TX_PWR_BAND_EDGE+4])&0xff;
3917 priv->TxPwrbandEdgeLegacyOfdm[RF90_PATH_A][0] = (tempval&0xF); // Band edge low channel
3918 priv->TxPwrbandEdgeLegacyOfdm[RF90_PATH_A][1] = ((tempval>>4)&0xF); // Band edge high channel
3919 tempval = (*(u8 *)&hwinfo[EEPROM_TX_PWR_BAND_EDGE+5])&0xff;
3920 priv->TxPwrbandEdgeLegacyOfdm[RF90_PATH_B][0] = (tempval&0xF); // Band edge low channel
3921 priv->TxPwrbandEdgeLegacyOfdm[RF90_PATH_B][1] = ((tempval>>4)&0xF); // Band edge high channel
3923 priv->TxPwrbandEdgeFlag = (*(u8 *)&hwinfo[TX_PWR_BAND_EDGE_CHK]);
3926 for(i=0; i<14; i++)
3927 RT_TRACE(COMP_INIT, "RF-A Ht20 to HT40 Diff[%d] = 0x%x\n", i, priv->TxPwrHt20Diff[RF90_PATH_A][i]);
3928 for(i=0; i<14; i++)
3929 RT_TRACE(COMP_INIT, "RF-A Legacy to Ht40 Diff[%d] = 0x%x\n", i, priv->TxPwrLegacyHtDiff[RF90_PATH_A][i]);
3930 for(i=0; i<14; i++)
3931 RT_TRACE(COMP_INIT, "RF-B Ht20 to HT40 Diff[%d] = 0x%x\n", i, priv->TxPwrHt20Diff[RF90_PATH_B][i]);
3932 for(i=0; i<14; i++)
3933 RT_TRACE(COMP_INIT, "RF-B Legacy to HT40 Diff[%d] = 0x%x\n", i, priv->TxPwrLegacyHtDiff[RF90_PATH_B][i]);
3934 RT_TRACE(COMP_INIT, "RF-A HT40 band-edge low/high power diff = 0x%x/0x%x\n",
3935 priv->TxPwrbandEdgeHt40[RF90_PATH_A][0],
3936 priv->TxPwrbandEdgeHt40[RF90_PATH_A][1]);
3937 RT_TRACE((COMP_INIT&COMP_DBG), "RF-B HT40 band-edge low/high power diff = 0x%x/0x%x\n",
3938 priv->TxPwrbandEdgeHt40[RF90_PATH_B][0],
3939 priv->TxPwrbandEdgeHt40[RF90_PATH_B][1]);
3941 RT_TRACE((COMP_INIT&COMP_DBG), "RF-A HT20 band-edge low/high power diff = 0x%x/0x%x\n",
3942 priv->TxPwrbandEdgeHt20[RF90_PATH_A][0],
3943 priv->TxPwrbandEdgeHt20[RF90_PATH_A][1]);
3944 RT_TRACE((COMP_INIT&COMP_DBG), "RF-B HT20 band-edge low/high power diff = 0x%x/0x%x\n",
3945 priv->TxPwrbandEdgeHt20[RF90_PATH_B][0],
3946 priv->TxPwrbandEdgeHt20[RF90_PATH_B][1]);
3948 RT_TRACE((COMP_INIT&COMP_DBG), "RF-A OFDM band-edge low/high power diff = 0x%x/0x%x\n",
3949 priv->TxPwrbandEdgeLegacyOfdm[RF90_PATH_A][0],
3950 priv->TxPwrbandEdgeLegacyOfdm[RF90_PATH_A][1]);
3951 RT_TRACE((COMP_INIT&COMP_DBG), "RF-B OFDM band-edge low/high power diff = 0x%x/0x%x\n",
3952 priv->TxPwrbandEdgeLegacyOfdm[RF90_PATH_B][0],
3953 priv->TxPwrbandEdgeLegacyOfdm[RF90_PATH_B][1]);
3954 RT_TRACE((COMP_INIT&COMP_DBG), "Band-edge enable flag = %d\n", priv->TxPwrbandEdgeFlag);
3957 // Update remained HAL variables.
3959 priv->TSSI_13dBm = priv->EEPROMThermalMeter *100;
3960 priv->LegacyHTTxPowerDiff = priv->EEPROMTxPowerDiff;
3961 priv->TxPowerDiff = priv->EEPROMTxPowerDiff;
3962 //priv->AntennaTxPwDiff[0] = (priv->EEPROMTxPowerDiff & 0xf);// Antenna B gain offset to antenna A, bit[3:0]
3963 //priv->AntennaTxPwDiff[1] = ((priv->EEPROMTxPowerDiff & 0xf0)>>4);// Antenna C gain offset to antenna A, bit[7:4]
3964 priv->CrystalCap = priv->EEPROMCrystalCap; // CrystalCap, bit[15:12]
3965 priv->ThermalMeter[0] = (priv->EEPROMThermalMeter&0x1f);// ThermalMeter, bit0~3 for RFIC1, bit4~7 for RFIC2
3966 priv->LedStrategy = SW_LED_MODE0;
3968 init_rate_adaptive(dev);
3970 RT_TRACE(COMP_INIT, "<==== ReadAdapterInfo8192SUsb\n");
3972 //return RT_STATUS_SUCCESS;
3977 // Description:
3978 // Read HW adapter information by E-Fuse or EEPROM according CR9346 reported.
3980 // Assumption:
3981 // 1. CR9346 regiser has verified.
3982 // 2. PASSIVE_LEVEL (USB interface)
3984 // Created by Roger, 2008.10.21.
3986 static void rtl8192SU_read_eeprom_info(struct net_device *dev)
3988 struct r8192_priv *priv = ieee80211_priv(dev);
3989 u8 tmpU1b;
3991 RT_TRACE(COMP_INIT, "====> ReadAdapterInfo8192SUsb\n");
3993 // Retrieve Chip version.
3994 priv->card_8192_version = (VERSION_8192S)((read_nic_dword(dev, PMC_FSM)>>16)&0xF);
3995 RT_TRACE(COMP_INIT, "Chip Version ID: 0x%2x\n", priv->card_8192_version);
3997 tmpU1b = read_nic_byte(dev, EPROM_CMD);//CR9346
3999 // To check system boot selection.
4000 if (tmpU1b & CmdEERPOMSEL)
4002 RT_TRACE(COMP_INIT, "Boot from EEPROM\n");
4003 priv->EepromOrEfuse = TRUE;
4005 else
4007 RT_TRACE(COMP_INIT, "Boot from EFUSE\n");
4008 priv->EepromOrEfuse = FALSE;
4011 // To check autoload success or not.
4012 if (tmpU1b & CmdEEPROM_En)
4014 RT_TRACE(COMP_INIT, "Autoload OK!!\n");
4015 priv->AutoloadFailFlag=FALSE;
4016 rtl8192SU_ReadAdapterInfo8192SUsb(dev);//eeprom or e-fuse
4018 else
4019 { // Auto load fail.
4020 RT_TRACE(COMP_INIT, "AutoLoad Fail reported from CR9346!!\n");
4021 priv->AutoloadFailFlag=TRUE;
4022 rtl8192SU_ConfigAdapterInfo8192SForAutoLoadFail(dev);
4024 //if (IS_BOOT_FROM_EFUSE(Adapter))
4025 if(!priv->EepromOrEfuse)
4027 RT_TRACE(COMP_INIT, "Update shadow map for EFuse future use!!\n");
4028 EFUSE_ShadowMapUpdate(dev);
4031 #ifdef TO_DO_LIST
4032 if((priv->RegChannelPlan >= RT_CHANNEL_DOMAIN_MAX) || (pHalData->EEPROMChannelPlan & EEPROM_CHANNEL_PLAN_BY_HW_MASK))
4034 pMgntInfo->ChannelPlan = HalMapChannelPlan8192S(Adapter, (pHalData->EEPROMChannelPlan & (~(EEPROM_CHANNEL_PLAN_BY_HW_MASK))));
4035 pMgntInfo->bChnlPlanFromHW = (pHalData->EEPROMChannelPlan & EEPROM_CHANNEL_PLAN_BY_HW_MASK) ? TRUE : FALSE; // User cannot change channel plan.
4037 else
4039 pMgntInfo->ChannelPlan = (RT_CHANNEL_DOMAIN)pMgntInfo->RegChannelPlan;
4042 switch(pMgntInfo->ChannelPlan)
4044 case RT_CHANNEL_DOMAIN_GLOBAL_DOAMIN:
4046 PRT_DOT11D_INFO pDot11dInfo = GET_DOT11D_INFO(pMgntInfo);
4048 pDot11dInfo->bEnabled = TRUE;
4050 RT_TRACE(COMP_INIT, DBG_LOUD, ("ReadAdapterInfo8187(): Enable dot11d when RT_CHANNEL_DOMAIN_GLOBAL_DOAMIN!\n"));
4051 break;
4054 RT_TRACE(COMP_INIT, DBG_LOUD, ("RegChannelPlan(%d) EEPROMChannelPlan(%d)", pMgntInfo->RegChannelPlan, pHalData->EEPROMChannelPlan));
4055 RT_TRACE(COMP_INIT, DBG_LOUD, ("ChannelPlan = %d\n" , pMgntInfo->ChannelPlan));
4057 RT_TRACE(COMP_INIT, DBG_LOUD, ("<==== ReadAdapterInfo8192S\n"));
4058 #endif
4060 RT_TRACE(COMP_INIT, "<==== ReadAdapterInfo8192SUsb\n");
4062 //return RT_STATUS_SUCCESS;
4065 short rtl8192_get_channel_map(struct net_device * dev)
4067 struct r8192_priv *priv = ieee80211_priv(dev);
4068 if(priv->ChannelPlan > COUNTRY_CODE_GLOBAL_DOMAIN){
4069 printk("rtl8180_init:Error channel plan! Set to default.\n");
4070 priv->ChannelPlan= 0;
4072 RT_TRACE(COMP_INIT, "Channel plan is %d\n",priv->ChannelPlan);
4074 rtl819x_set_channel_map(priv->ChannelPlan, priv);
4075 return 0;
4078 short rtl8192_init(struct net_device *dev)
4081 struct r8192_priv *priv = ieee80211_priv(dev);
4083 rtl8192_init_priv_variable(dev);
4084 rtl8192_init_priv_lock(priv);
4085 rtl8192_init_priv_task(dev);
4086 priv->ops->rtl819x_read_eeprom_info(dev);
4087 rtl8192_get_channel_map(dev);
4088 init_hal_dm(dev);
4089 init_timer(&priv->watch_dog_timer);
4090 priv->watch_dog_timer.data = (unsigned long)dev;
4091 priv->watch_dog_timer.function = watch_dog_timer_callback;
4092 return 0;
4095 /******************************************************************************
4096 *function: This function actually only set RRSR, RATR and BW_OPMODE registers
4097 * not to do all the hw config as its name says
4098 * input: net_device dev
4099 * output: none
4100 * return: none
4101 * notice: This part need to modified according to the rate set we filtered
4102 * ****************************************************************************/
4103 void rtl8192_hwconfig(struct net_device* dev)
4105 u32 regRATR = 0, regRRSR = 0;
4106 u8 regBwOpMode = 0, regTmp = 0;
4107 struct r8192_priv *priv = ieee80211_priv(dev);
4109 // Set RRSR, RATR, and BW_OPMODE registers
4111 switch(priv->ieee80211->mode)
4113 case WIRELESS_MODE_B:
4114 regBwOpMode = BW_OPMODE_20MHZ;
4115 regRATR = RATE_ALL_CCK;
4116 regRRSR = RATE_ALL_CCK;
4117 break;
4118 case WIRELESS_MODE_A:
4119 regBwOpMode = BW_OPMODE_5G |BW_OPMODE_20MHZ;
4120 regRATR = RATE_ALL_OFDM_AG;
4121 regRRSR = RATE_ALL_OFDM_AG;
4122 break;
4123 case WIRELESS_MODE_G:
4124 regBwOpMode = BW_OPMODE_20MHZ;
4125 regRATR = RATE_ALL_CCK | RATE_ALL_OFDM_AG;
4126 regRRSR = RATE_ALL_CCK | RATE_ALL_OFDM_AG;
4127 break;
4128 case WIRELESS_MODE_AUTO:
4129 #ifdef TO_DO_LIST
4130 if (Adapter->bInHctTest)
4132 regBwOpMode = BW_OPMODE_20MHZ;
4133 regRATR = RATE_ALL_CCK | RATE_ALL_OFDM_AG;
4134 regRRSR = RATE_ALL_CCK | RATE_ALL_OFDM_AG;
4136 else
4137 #endif
4139 regBwOpMode = BW_OPMODE_20MHZ;
4140 regRATR = RATE_ALL_CCK | RATE_ALL_OFDM_AG | RATE_ALL_OFDM_1SS | RATE_ALL_OFDM_2SS;
4141 regRRSR = RATE_ALL_CCK | RATE_ALL_OFDM_AG;
4143 break;
4144 case WIRELESS_MODE_N_24G:
4145 // It support CCK rate by default.
4146 // CCK rate will be filtered out only when associated AP does not support it.
4147 regBwOpMode = BW_OPMODE_20MHZ;
4148 regRATR = RATE_ALL_CCK | RATE_ALL_OFDM_AG | RATE_ALL_OFDM_1SS | RATE_ALL_OFDM_2SS;
4149 regRRSR = RATE_ALL_CCK | RATE_ALL_OFDM_AG;
4150 break;
4151 case WIRELESS_MODE_N_5G:
4152 regBwOpMode = BW_OPMODE_5G;
4153 regRATR = RATE_ALL_OFDM_AG | RATE_ALL_OFDM_1SS | RATE_ALL_OFDM_2SS;
4154 regRRSR = RATE_ALL_OFDM_AG;
4155 break;
4158 write_nic_byte(dev, BW_OPMODE, regBwOpMode);
4160 u32 ratr_value = 0;
4161 ratr_value = regRATR;
4162 if (priv->rf_type == RF_1T2R)
4164 ratr_value &= ~(RATE_ALL_OFDM_2SS);
4166 write_nic_dword(dev, RATR0, ratr_value);
4167 write_nic_byte(dev, UFWP, 1);
4169 regTmp = read_nic_byte(dev, 0x313);
4170 regRRSR = ((regTmp) << 24) | (regRRSR & 0x00ffffff);
4171 write_nic_dword(dev, RRSR, regRRSR);
4174 // Set Retry Limit here
4176 write_nic_word(dev, RETRY_LIMIT,
4177 priv->ShortRetryLimit << RETRY_LIMIT_SHORT_SHIFT | \
4178 priv->LongRetryLimit << RETRY_LIMIT_LONG_SHIFT);
4179 // Set Contention Window here
4181 // Set Tx AGC
4183 // Set Tx Antenna including Feedback control
4185 // Set Auto Rate fallback control
4192 // Description:
4193 // Initial HW relted registers.
4195 // Assumption:
4196 // Config RTL8192S USB MAC, we should config MAC before download FW.
4198 // 2008.09.03, Added by Roger.
4200 static void rtl8192SU_MacConfigBeforeFwDownloadASIC(struct net_device *dev)
4202 u8 tmpU1b;// i;
4203 // u16 tmpU2b;
4204 // u32 tmpU4b;
4205 u8 PollingCnt = 20;
4207 RT_TRACE(COMP_INIT, "--->MacConfigBeforeFwDownloadASIC()\n");
4209 //2MAC Initialization for power on sequence, Revised by Roger. 2008.09.03.
4212 //<Roger_Notes> Set control path switch to HW control and reset Digital Core, CPU Core and
4213 // MAC I/O to solve FW download fail when system from resume sate.
4214 // 2008.11.04.
4216 tmpU1b = read_nic_byte(dev, SYS_CLKR+1);
4217 if(tmpU1b & 0x80)
4219 tmpU1b &= 0x3f;
4220 write_nic_byte(dev, SYS_CLKR+1, tmpU1b);
4222 // Clear FW RPWM for FW control LPS. by tynli. 2009.02.23
4223 write_nic_byte(dev, RPWM, 0x0);
4225 tmpU1b = read_nic_byte(dev, SYS_FUNC_EN+1);
4226 tmpU1b &= 0x73;
4227 write_nic_byte(dev, SYS_FUNC_EN+1, tmpU1b);
4228 udelay(1000);
4230 //Revised POS, suggested by SD1 Alex, 2008.09.27.
4231 write_nic_byte(dev, SPS0_CTRL+1, 0x53);
4232 write_nic_byte(dev, SPS0_CTRL, 0x57);
4234 //Enable AFE Macro Block's Bandgap adn Enable AFE Macro Block's Mbias
4235 tmpU1b = read_nic_byte(dev, AFE_MISC);
4236 write_nic_byte(dev, AFE_MISC, (tmpU1b|AFE_BGEN|AFE_MBEN));
4238 //Enable PLL Power (LDOA15V)
4239 tmpU1b = read_nic_byte(dev, LDOA15_CTRL);
4240 write_nic_byte(dev, LDOA15_CTRL, (tmpU1b|LDA15_EN));
4242 //Enable LDOV12D block
4243 tmpU1b = read_nic_byte(dev, LDOV12D_CTRL);
4244 write_nic_byte(dev, LDOV12D_CTRL, (tmpU1b|LDV12_EN));
4246 //mpU1b = read_nic_byte(Adapter, SPS1_CTRL);
4247 //write_nic_byte(dev, SPS1_CTRL, (tmpU1b|SPS1_LDEN));
4249 //PlatformSleepUs(2000);
4251 //Enable Switch Regulator Block
4252 //tmpU1b = read_nic_byte(Adapter, SPS1_CTRL);
4253 //write_nic_byte(dev, SPS1_CTRL, (tmpU1b|SPS1_SWEN));
4255 //write_nic_dword(Adapter, SPS1_CTRL, 0x00a7b267);
4257 tmpU1b = read_nic_byte(dev, SYS_ISO_CTRL+1);
4258 write_nic_byte(dev, SYS_ISO_CTRL+1, (tmpU1b|0x08));
4260 //Engineer Packet CP test Enable
4261 tmpU1b = read_nic_byte(dev, SYS_FUNC_EN+1);
4262 write_nic_byte(dev, SYS_FUNC_EN+1, (tmpU1b|0x20));
4264 //Support 64k IMEM, suggested by SD1 Alex.
4265 tmpU1b = read_nic_byte(dev, SYS_ISO_CTRL+1);
4266 write_nic_byte(dev, SYS_ISO_CTRL+1, (tmpU1b& 0x68));
4268 //Enable AFE clock
4269 tmpU1b = read_nic_byte(dev, AFE_XTAL_CTRL+1);
4270 write_nic_byte(dev, AFE_XTAL_CTRL+1, (tmpU1b& 0xfb));
4272 //Enable AFE PLL Macro Block
4273 tmpU1b = read_nic_byte(dev, AFE_PLL_CTRL);
4274 write_nic_byte(dev, AFE_PLL_CTRL, (tmpU1b|0x11));
4276 //Attatch AFE PLL to MACTOP/BB/PCIe Digital
4277 tmpU1b = read_nic_byte(dev, SYS_ISO_CTRL);
4278 write_nic_byte(dev, SYS_ISO_CTRL, (tmpU1b&0xEE));
4280 // Switch to 40M clock
4281 write_nic_byte(dev, SYS_CLKR, 0x00);
4283 //SSC Disable
4284 tmpU1b = read_nic_byte(dev, SYS_CLKR);
4285 //write_nic_byte(dev, SYS_CLKR, (tmpU1b&0x5f));
4286 write_nic_byte(dev, SYS_CLKR, (tmpU1b|0xa0));
4288 //Enable MAC clock
4289 tmpU1b = read_nic_byte(dev, SYS_CLKR+1);
4290 write_nic_byte(dev, SYS_CLKR+1, (tmpU1b|0x18));
4292 //Revised POS, suggested by SD1 Alex, 2008.09.27.
4293 write_nic_byte(dev, PMC_FSM, 0x02);
4295 //Enable Core digital and enable IOREG R/W
4296 tmpU1b = read_nic_byte(dev, SYS_FUNC_EN+1);
4297 write_nic_byte(dev, SYS_FUNC_EN+1, (tmpU1b|0x08));
4299 //Enable REG_EN
4300 tmpU1b = read_nic_byte(dev, SYS_FUNC_EN+1);
4301 write_nic_byte(dev, SYS_FUNC_EN+1, (tmpU1b|0x80));
4303 //Switch the control path to FW
4304 tmpU1b = read_nic_byte(dev, SYS_CLKR+1);
4305 write_nic_byte(dev, SYS_CLKR+1, (tmpU1b|0x80)& 0xBF);
4307 write_nic_byte(dev, CMDR, 0xFC);
4308 write_nic_byte(dev, CMDR+1, 0x37);
4310 //Fix the RX FIFO issue(usb error), 970410
4311 tmpU1b = read_nic_byte_E(dev, 0x5c);
4312 write_nic_byte_E(dev, 0x5c, (tmpU1b|BIT7));
4314 //For power save, used this in the bit file after 970621
4315 tmpU1b = read_nic_byte(dev, SYS_CLKR);
4316 write_nic_byte(dev, SYS_CLKR, tmpU1b&(~SYS_CPU_CLKSEL));
4318 // Revised for 8051 ROM code wrong operation. Added by Roger. 2008.10.16.
4319 write_nic_byte_E(dev, 0x1c, 0x80);
4322 // <Roger_EXP> To make sure that TxDMA can ready to download FW.
4323 // We should reset TxDMA if IMEM RPT was not ready.
4324 // Suggested by SD1 Alex. 2008.10.23.
4328 tmpU1b = read_nic_byte(dev, TCR);
4329 if((tmpU1b & TXDMA_INIT_VALUE) == TXDMA_INIT_VALUE)
4330 break;
4331 //PlatformStallExecution(5);
4332 udelay(5);
4333 }while(PollingCnt--); // Delay 1ms
4335 if(PollingCnt <= 0 )
4337 RT_TRACE(COMP_INIT, "MacConfigBeforeFwDownloadASIC(): Polling TXDMA_INIT_VALUE timeout!! Current TCR(%#x)\n", tmpU1b);
4338 tmpU1b = read_nic_byte(dev, CMDR);
4339 write_nic_byte(dev, CMDR, tmpU1b&(~TXDMA_EN));
4340 udelay(2);
4341 write_nic_byte(dev, CMDR, tmpU1b|TXDMA_EN);// Reset TxDMA
4345 RT_TRACE(COMP_INIT, "<---MacConfigBeforeFwDownloadASIC()\n");
4349 // Description:
4350 // Initial HW relted registers.
4352 // Assumption:
4353 // 1. This function is only invoked at driver intialization once.
4354 // 2. PASSIVE LEVEL.
4356 // 2008.06.10, Added by Roger.
4358 static void rtl8192SU_MacConfigAfterFwDownload(struct net_device *dev)
4360 struct r8192_priv *priv = ieee80211_priv((struct net_device *)dev);
4361 //PRT_HIGH_THROUGHPUT pHTInfo = priv->ieee80211->pHTInfo;
4362 //u8 tmpU1b, RxPageCfg, i;
4363 u16 tmpU2b;
4364 u8 tmpU1b;//, i;
4367 RT_TRACE(COMP_INIT, "--->MacConfigAfterFwDownload()\n");
4369 // Enable Tx/Rx
4370 tmpU2b = (BBRSTn|BB_GLB_RSTn|SCHEDULE_EN|MACRXEN|MACTXEN|DDMA_EN|
4371 FW2HW_EN|RXDMA_EN|TXDMA_EN|HCI_RXDMA_EN|HCI_TXDMA_EN); //3
4372 //Adapter->HalFunc.SetHwRegHandler( Adapter, HW_VAR_COMMAND, &tmpU1b );
4373 write_nic_word(dev, CMDR, tmpU2b); //LZM REGISTER COM 090305
4375 // Loopback mode or not
4376 priv->LoopbackMode = RTL8192SU_NO_LOOPBACK; // Set no loopback as default.
4377 if(priv->LoopbackMode == RTL8192SU_NO_LOOPBACK)
4378 tmpU1b = LBK_NORMAL;
4379 else if (priv->LoopbackMode == RTL8192SU_MAC_LOOPBACK )
4380 tmpU1b = LBK_MAC_DLB;
4381 else
4382 RT_TRACE(COMP_INIT, "Serious error: wrong loopback mode setting\n");
4384 //Adapter->HalFunc.SetHwRegHandler( Adapter, HW_VAR_LBK_MODE, &tmpU1b);
4385 write_nic_byte(dev, LBKMD_SEL, tmpU1b);
4387 // Set RCR
4388 write_nic_dword(dev, RCR, priv->ReceiveConfig);
4389 RT_TRACE(COMP_INIT, "MacConfigAfterFwDownload(): Current RCR settings(%#x)\n", priv->ReceiveConfig);
4392 // Set RQPN
4394 // <Roger_Notes> 2008.08.18.
4395 // 6 endpoints:
4396 // (1) Page number on CMDQ is 0x03.
4397 // (2) Page number on BCNQ, HQ and MGTQ is 0.
4398 // (3) Page number on BKQ, BEQ, VIQ and VOQ are 0x07.
4399 // (4) Page number on PUBQ is 0xdd
4401 // 11 endpoints:
4402 // (1) Page number on CMDQ is 0x00.
4403 // (2) Page number on BCNQ is 0x02, HQ and MGTQ are 0x03.
4404 // (3) Page number on BKQ, BEQ, VIQ and VOQ are 0x07.
4405 // (4) Page number on PUBQ is 0xd8
4407 //write_nic_dword(Adapter, 0xa0, 0x07070707); //BKQ, BEQ, VIQ and VOQ
4408 //write_nic_byte(dev, 0xa4, 0x00); // HCCAQ
4410 // Fix the RX FIFO issue(USB error), Rivesed by Roger, 2008-06-14
4411 tmpU1b = read_nic_byte_E(dev, 0x5C);
4412 write_nic_byte_E(dev, 0x5C, tmpU1b|BIT7);
4414 // For EFUSE init configuration.
4415 //if (IS_BOOT_FROM_EFUSE(Adapter)) // We may R/W EFUSE in EFUSE mode
4416 if (priv->bBootFromEfuse)
4418 u8 tempval;
4420 tempval = read_nic_byte(dev, SYS_ISO_CTRL+1);
4421 tempval &= 0xFE;
4422 write_nic_byte(dev, SYS_ISO_CTRL+1, tempval);
4424 // Enable LDO 2.5V for write action
4425 //tempval = read_nic_byte(Adapter, EFUSE_TEST+3);
4426 //write_nic_byte(Adapter, EFUSE_TEST+3, (tempval | 0x80));
4428 // Change Efuse Clock for write action
4429 //write_nic_byte(Adapter, EFUSE_CLK, 0x03);
4431 // Change Program timing
4432 write_nic_byte(dev, EFUSE_CTRL+3, 0x72);
4433 //printk("!!!!!!!!!!!!!!!!!!!!!%s: write 0x33 with 0x72\n",__FUNCTION__);
4434 RT_TRACE(COMP_INIT, "EFUSE CONFIG OK\n");
4438 RT_TRACE(COMP_INIT, "<---MacConfigAfterFwDownload()\n");
4441 void rtl8192SU_HwConfigureRTL8192SUsb(struct net_device *dev)
4444 struct r8192_priv *priv = ieee80211_priv(dev);
4445 u8 regBwOpMode = 0;
4446 u32 regRATR = 0, regRRSR = 0;
4447 u8 regTmp = 0;
4448 u32 i = 0;
4450 //1 This part need to modified according to the rate set we filtered!!
4452 // Set RRSR, RATR, and BW_OPMODE registers
4454 switch(priv->ieee80211->mode)
4456 case WIRELESS_MODE_B:
4457 regBwOpMode = BW_OPMODE_20MHZ;
4458 regRATR = RATE_ALL_CCK;
4459 regRRSR = RATE_ALL_CCK;
4460 break;
4461 case WIRELESS_MODE_A:
4462 regBwOpMode = BW_OPMODE_5G |BW_OPMODE_20MHZ;
4463 regRATR = RATE_ALL_OFDM_AG;
4464 regRRSR = RATE_ALL_OFDM_AG;
4465 break;
4466 case WIRELESS_MODE_G:
4467 regBwOpMode = BW_OPMODE_20MHZ;
4468 regRATR = RATE_ALL_CCK | RATE_ALL_OFDM_AG;
4469 regRRSR = RATE_ALL_CCK | RATE_ALL_OFDM_AG;
4470 break;
4471 case WIRELESS_MODE_AUTO:
4472 if (priv->bInHctTest)
4474 regBwOpMode = BW_OPMODE_20MHZ;
4475 regRATR = RATE_ALL_CCK | RATE_ALL_OFDM_AG;
4476 regRRSR = RATE_ALL_CCK | RATE_ALL_OFDM_AG;
4478 else
4480 regBwOpMode = BW_OPMODE_20MHZ;
4481 regRATR = RATE_ALL_CCK | RATE_ALL_OFDM_AG | RATE_ALL_OFDM_1SS | RATE_ALL_OFDM_2SS;
4482 regRRSR = RATE_ALL_CCK | RATE_ALL_OFDM_AG;
4484 break;
4485 case WIRELESS_MODE_N_24G:
4486 // It support CCK rate by default.
4487 // CCK rate will be filtered out only when associated AP does not support it.
4488 regBwOpMode = BW_OPMODE_20MHZ;
4489 regRATR = RATE_ALL_CCK | RATE_ALL_OFDM_AG | RATE_ALL_OFDM_1SS | RATE_ALL_OFDM_2SS;
4490 regRRSR = RATE_ALL_CCK | RATE_ALL_OFDM_AG;
4491 break;
4492 case WIRELESS_MODE_N_5G:
4493 regBwOpMode = BW_OPMODE_5G;
4494 regRATR = RATE_ALL_OFDM_AG | RATE_ALL_OFDM_1SS | RATE_ALL_OFDM_2SS;
4495 regRRSR = RATE_ALL_OFDM_AG;
4496 break;
4500 // <Roger_Notes> We disable CCK response rate until FIB CCK rate IC's back.
4501 // 2008.09.23.
4503 regTmp = read_nic_byte(dev, INIRTSMCS_SEL);
4504 regRRSR = ((regRRSR & 0x000fffff)<<8) | regTmp;
4507 // Update SIFS timing.
4509 //priv->SifsTime = 0x0e0e0a0a;
4510 //Adapter->HalFunc.SetHwRegHandler( Adapter, HW_VAR_SIFS, (pu1Byte)&pHalData->SifsTime);
4511 { u8 val[4] = {0x0e, 0x0e, 0x0a, 0x0a};
4512 // SIFS for CCK Data ACK
4513 write_nic_byte(dev, SIFS_CCK, val[0]);
4514 // SIFS for CCK consecutive tx like CTS data!
4515 write_nic_byte(dev, SIFS_CCK+1, val[1]);
4517 // SIFS for OFDM Data ACK
4518 write_nic_byte(dev, SIFS_OFDM, val[2]);
4519 // SIFS for OFDM consecutive tx like CTS data!
4520 write_nic_byte(dev, SIFS_OFDM+1, val[3]);
4523 write_nic_dword(dev, INIRTSMCS_SEL, regRRSR);
4524 write_nic_byte(dev, BW_OPMODE, regBwOpMode);
4527 // Suggested by SD1 Alex, 2008-06-14.
4529 //PlatformEFIOWrite1Byte(Adapter, TXOP_STALL_CTRL, 0x80);//NAV to protect all TXOP.
4532 // Set Data Auto Rate Fallback Retry Count register.
4534 write_nic_dword(dev, DARFRC, 0x02010000);
4535 write_nic_dword(dev, DARFRC+4, 0x06050403);
4536 write_nic_dword(dev, RARFRC, 0x02010000);
4537 write_nic_dword(dev, RARFRC+4, 0x06050403);
4539 // Set Data Auto Rate Fallback Reg. Added by Roger, 2008.09.22.
4540 for (i = 0; i < 8; i++)
4541 write_nic_dword(dev, ARFR0+i*4, 0x1f0ffff0);
4544 // Aggregation length limit. Revised by Roger. 2008.09.22.
4546 write_nic_byte(dev, AGGLEN_LMT_H, 0x0f); // Set AMPDU length to 12Kbytes for ShortGI case.
4547 write_nic_dword(dev, AGGLEN_LMT_L, 0xddd77442); // Long GI
4548 write_nic_dword(dev, AGGLEN_LMT_L+4, 0xfffdd772);
4550 // Set NAV protection length
4551 write_nic_word(dev, NAV_PROT_LEN, 0x0080);
4553 // Set TXOP stall control for several queue/HI/BCN/MGT/
4554 write_nic_byte(dev, TXOP_STALL_CTRL, 0x00); // NAV Protect next packet.
4556 // Set MSDU lifetime.
4557 write_nic_byte(dev, MLT, 0x8f);
4559 // Set CCK/OFDM SIFS
4560 write_nic_word(dev, SIFS_CCK, 0x0a0a); // CCK SIFS shall always be 10us.
4561 write_nic_word(dev, SIFS_OFDM, 0x0e0e);
4563 write_nic_byte(dev, ACK_TIMEOUT, 0x40);
4565 // CF-END Threshold
4566 write_nic_byte(dev, CFEND_TH, 0xFF);
4569 // For Min Spacing configuration.
4571 switch(priv->rf_type)
4573 case RF_1T2R:
4574 case RF_1T1R:
4575 RT_TRACE(COMP_INIT, "Initializeadapter: RF_Type%s\n", (priv->rf_type==RF_1T1R? "(1T1R)":"(1T2R)"));
4576 priv->MinSpaceCfg = (MAX_MSS_DENSITY_1T<<3);
4577 break;
4578 case RF_2T2R:
4579 case RF_2T2R_GREEN:
4580 RT_TRACE(COMP_INIT, "Initializeadapter:RF_Type(2T2R)\n");
4581 priv->MinSpaceCfg = (MAX_MSS_DENSITY_2T<<3);
4582 break;
4584 write_nic_byte(dev, AMPDU_MIN_SPACE, priv->MinSpaceCfg);
4586 //LZM 090219
4588 // For Min Spacing configuration.
4590 //priv->MinSpaceCfg = 0x00;
4591 //rtl8192SU_SetHwRegAmpduMinSpace(dev, priv->MinSpaceCfg);
4595 // Description: Initial HW relted registers.
4597 // Assumption: This function is only invoked at driver intialization once.
4599 // 2008.06.10, Added by Roger.
4600 bool rtl8192SU_adapter_start(struct net_device *dev)
4602 struct r8192_priv *priv = ieee80211_priv(dev);
4603 //u32 dwRegRead = 0;
4604 //bool init_status = true;
4605 //u32 ulRegRead;
4606 bool rtStatus = true;
4607 //u8 PipeIndex;
4608 //u8 eRFPath, tmpU1b;
4609 u8 fw_download_times = 1;
4612 RT_TRACE(COMP_INIT, "--->InitializeAdapter8192SUsb()\n");
4614 //pHalData->bGPIOChangeRF = FALSE;
4618 // <Roger_Notes> 2008.06.15.
4620 // Initialization Steps on RTL8192SU:
4621 // a. MAC initialization prior to sending down firmware code.
4622 // b. Download firmware code step by step(i.e., IMEM, EMEM, DMEM).
4623 // c. MAC configuration after firmware has been download successfully.
4624 // d. Initialize BB related configurations.
4625 // e. Initialize RF related configurations.
4626 // f. Start to BulkIn transfer.
4630 //a. MAC initialization prior to send down firmware code.
4632 start:
4633 rtl8192SU_MacConfigBeforeFwDownloadASIC(dev);
4636 //b. Download firmware code step by step(i.e., IMEM, EMEM, DMEM).
4638 rtStatus = FirmwareDownload92S(dev);
4639 if(rtStatus != true)
4641 if(fw_download_times == 1){
4642 RT_TRACE(COMP_INIT, "InitializeAdapter8192SUsb(): Download Firmware failed once, Download again!!\n");
4643 fw_download_times = fw_download_times + 1;
4644 goto start;
4645 }else{
4646 RT_TRACE(COMP_INIT, "InitializeAdapter8192SUsb(): Download Firmware failed twice, end!!\n");
4647 goto end;
4651 //c. MAC configuration after firmware has been download successfully.
4653 rtl8192SU_MacConfigAfterFwDownload(dev);
4655 //priv->bLbusEnable = TRUE;
4656 //if(priv->RegRfOff == TRUE)
4657 // priv->eRFPowerState = eRfOff;
4659 // Save target channel
4660 // <Roger_Notes> Current Channel will be updated again later.
4661 //priv->CurrentChannel = Channel;
4662 rtStatus = PHY_MACConfig8192S(dev);//===>ok
4663 if(rtStatus != true)
4665 RT_TRACE(COMP_INIT, "InitializeAdapter8192SUsb(): Fail to configure MAC!!\n");
4666 goto end;
4668 if (1){
4669 int i;
4670 for (i=0; i<4; i++)
4671 write_nic_dword(dev,WDCAPARA_ADD[i], 0x5e4322);
4672 write_nic_byte(dev,AcmHwCtrl, 0x01);
4677 //d. Initialize BB related configurations.
4680 rtStatus = PHY_BBConfig8192S(dev);//===>ok
4681 if(rtStatus != true)
4683 RT_TRACE(COMP_INIT, "InitializeAdapter8192SUsb(): Fail to configure BB!!\n");
4684 goto end;
4687 rtl8192_setBBreg(dev, rFPGA0_AnalogParameter2, 0xff, 0x58);//===>ok
4690 // e. Initialize RF related configurations.
4692 // 2007/11/02 MH Before initalizing RF. We can not use FW to do RF-R/W.
4693 priv->Rf_Mode = RF_OP_By_SW_3wire;
4695 // For RF test only from Scott's suggestion
4696 //write_nic_byte(dev, 0x27, 0xDB);
4697 //write_nic_byte(dev, 0x1B, 0x07);
4700 write_nic_byte(dev, AFE_XTAL_CTRL+1, 0xDB);
4702 // <Roger_Notes> The following IOs are configured for each RF modules.
4703 // Enable RF module and reset RF and SDM module. 2008.11.17.
4704 if(priv->card_8192_version == VERSION_8192S_ACUT)
4705 write_nic_byte(dev, SPS1_CTRL+3, (u8)(RF_EN|RF_RSTB|RF_SDMRSTB)); // Fix A-Cut bug.
4706 else
4707 write_nic_byte(dev, RF_CTRL, (u8)(RF_EN|RF_RSTB|RF_SDMRSTB));
4709 rtStatus = PHY_RFConfig8192S(dev);//===>ok
4710 if(rtStatus != true)
4712 RT_TRACE(COMP_INIT, "InitializeAdapter8192SUsb(): Fail to configure RF!!\n");
4713 goto end;
4717 // Set CCK and OFDM Block "ON"
4718 rtl8192_setBBreg(dev, rFPGA0_RFMOD, bCCKEn, 0x1);
4719 rtl8192_setBBreg(dev, rFPGA0_RFMOD, bOFDMEn, 0x1);
4722 // Turn off Radio B while RF type is 1T1R by SD3 Wilsion's request.
4723 // Revised by Roger, 2008.12.18.
4725 if(priv->rf_type == RF_1T1R)
4727 // This is needed for PHY_REG after 20081219
4728 rtl8192_setBBreg(dev, rFPGA0_RFMOD, 0xff000000, 0x03);
4729 // This is needed for PHY_REG before 20081219
4730 //PHY_SetBBReg(Adapter, rOFDM0_TRxPathEnable, bMaskByte0, 0x11);
4734 //LZM 090219
4735 // Set CCK and OFDM Block "ON"
4736 //rtl8192_setBBreg(dev, rFPGA0_RFMOD, bCCKEn, 0x1);
4737 //rtl8192_setBBreg(dev, rFPGA0_RFMOD, bOFDMEn, 0x1);
4740 //3//Get hardware version, do it in read eeprom?
4741 //GetHardwareVersion819xUsb(Adapter);
4743 //3//
4744 //3 //Set Hardware
4745 //3//
4746 rtl8192SU_HwConfigureRTL8192SUsb(dev);//==>ok
4749 // <Roger_Notes> We set MAC address here if autoload was failed before,
4750 // otherwise IDR0 will NOT contain any value.
4752 write_nic_dword(dev, IDR0, ((u32*)dev->dev_addr)[0]);
4753 write_nic_word(dev, IDR4, ((u16*)(dev->dev_addr + 4))[0]);
4754 if(!priv->bInHctTest)
4756 if(priv->ResetProgress == RESET_TYPE_NORESET)
4758 //RT_TRACE(COMP_MLME, DBG_LOUD, ("Initializeadapter8192SUsb():RegWirelessMode(%#x) \n", Adapter->RegWirelessMode));
4759 //Adapter->HalFunc.SetWirelessModeHandler(Adapter, Adapter->RegWirelessMode);
4760 rtl8192_SetWirelessMode(dev, priv->ieee80211->mode);//===>ok
4763 else
4765 priv->ieee80211->mode = WIRELESS_MODE_G;
4766 rtl8192_SetWirelessMode(dev, WIRELESS_MODE_G);
4769 //Security related.
4770 //-----------------------------------------------------------------------------
4771 // Set up security related. 070106, by rcnjko:
4772 // 1. Clear all H/W keys.
4773 // 2. Enable H/W encryption/decryption.
4774 //-----------------------------------------------------------------------------
4775 //CamResetAllEntry(Adapter);
4776 //Adapter->HalFunc.EnableHWSecCfgHandler(Adapter);
4778 //SecClearAllKeys(Adapter);
4779 CamResetAllEntry(dev);
4780 //SecInit(Adapter);
4782 u8 SECR_value = 0x0;
4783 SECR_value |= SCR_TxEncEnable;
4784 SECR_value |= SCR_RxDecEnable;
4785 SECR_value |= SCR_NoSKMC;
4786 write_nic_byte(dev, SECR, SECR_value);
4789 #ifdef TO_DO_LIST
4791 //PHY_UpdateInitialGain(dev);
4793 if(priv->RegRfOff == true)
4794 { // User disable RF via registry.
4795 u8 eRFPath = 0;
4797 RT_TRACE((COMP_INIT|COMP_RF), "InitializeAdapter8192SUsb(): Turn off RF for RegRfOff ----------\n");
4798 MgntActSet_RF_State(dev, eRfOff, RF_CHANGE_BY_SW);
4799 // Those action will be discard in MgntActSet_RF_State because off the same state
4800 for(eRFPath = 0; eRFPath <priv->NumTotalRFPath; eRFPath++)
4801 rtl8192_setBBreg(dev, (RF90_RADIO_PATH_E)eRFPath, 0x4, 0xC00, 0x0);
4803 else if(priv->RfOffReason > RF_CHANGE_BY_PS)
4804 { // H/W or S/W RF OFF before sleep.
4805 RT_TRACE((COMP_INIT|COMP_RF), "InitializeAdapter8192SUsb(): Turn off RF for RfOffReason(%d) ----------\n", priv->RfOffReason);
4806 MgntActSet_RF_State(dev, eRfOff, priv->RfOffReason);
4808 else
4810 priv->eRFPowerState = eRfOn;
4811 priv->RfOffReason = 0;
4812 RT_TRACE((COMP_INIT|COMP_RF), "InitializeAdapter8192SUsb(): RF is on ----------\n");
4815 #endif
4819 // f. Start to BulkIn transfer.
4821 #ifdef TO_DO_LIST
4823 #ifndef UNDER_VISTA
4825 u8 i;
4826 PlatformAcquireSpinLock(Adapter, RT_RX_SPINLOCK);
4828 for(PipeIndex=0; PipeIndex < MAX_RX_QUEUE; PipeIndex++)
4830 if (PipeIndex == 0)
4832 for(i=0; i<32; i++)
4833 HalUsbInMpdu(Adapter, PipeIndex);
4835 else
4837 //HalUsbInMpdu(Adapter, PipeIndex);
4838 //HalUsbInMpdu(Adapter, PipeIndex);
4839 //HalUsbInMpdu(Adapter, PipeIndex);
4842 PlatformReleaseSpinLock(Adapter, RT_RX_SPINLOCK);
4844 #else
4845 // Joseph add to 819X code base for Vista USB platform.
4846 // This part may need to be add to Hal819xU code base. too.
4847 PlatformUsbEnableInPipes(Adapter);
4848 #endif
4850 RT_TRACE(COMP_INIT, "HighestOperaRate = %x\n", Adapter->MgntInfo.HighestOperaRate);
4852 PlatformStartWorkItem( &(pHalData->RtUsbCheckForHangWorkItem) );
4855 // <Roger_EXP> The following configurations are for ASIC verification temporally.
4856 // 2008.07.10.
4859 #endif
4862 // Read EEPROM TX power index and PHY_REG_PG.txt to capture correct
4863 // TX power index for different rate set.
4865 //if(priv->card_8192_version >= VERSION_8192S_ACUT)
4867 // Get original hw reg values
4868 PHY_GetHWRegOriginalValue(dev);
4870 // Write correct tx power index//FIXLZM
4871 PHY_SetTxPowerLevel8192S(dev, priv->chan);
4875 u8 tmpU1b = 0;
4876 // EEPROM R/W workaround
4877 tmpU1b = read_nic_byte(dev, MAC_PINMUX_CFG);
4878 write_nic_byte(dev, MAC_PINMUX_CFG, tmpU1b&(~GPIOMUX_EN));
4882 //<Roger_Notes> 2008.08.19.
4883 // We return status here for temporal FPGA verification, 2008.08.19.
4885 #ifdef RTL8192SU_FW_IQK
4886 write_nic_dword(dev, WFM5, FW_IQK_ENABLE);
4887 ChkFwCmdIoDone(dev);
4888 #endif
4891 // <Roger_Notes> We enable high power mechanism after NIC initialized.
4892 // 2008.11.27.
4894 write_nic_dword(dev, WFM5, FW_RA_RESET);
4895 ChkFwCmdIoDone(dev);
4896 write_nic_dword(dev, WFM5, FW_RA_ACTIVE);
4897 ChkFwCmdIoDone(dev);
4898 write_nic_dword(dev, WFM5, FW_RA_REFRESH);
4899 ChkFwCmdIoDone(dev);
4900 write_nic_dword(dev, WFM5, FW_BB_RESET_ENABLE);
4902 // <Roger_Notes> We return status here for temporal FPGA verification. 2008.05.12.
4905 end:
4906 return rtStatus;
4909 /***************************************************************************
4910 -------------------------------NET STUFF---------------------------
4911 ***************************************************************************/
4913 static struct net_device_stats *rtl8192_stats(struct net_device *dev)
4915 struct r8192_priv *priv = ieee80211_priv(dev);
4917 return &priv->ieee80211->stats;
4920 bool
4921 HalTxCheckStuck819xUsb(
4922 struct net_device *dev
4925 struct r8192_priv *priv = ieee80211_priv(dev);
4926 u16 RegTxCounter = read_nic_word(dev, 0x128);
4927 bool bStuck = FALSE;
4928 RT_TRACE(COMP_RESET,"%s():RegTxCounter is %d,TxCounter is %d\n",__FUNCTION__,RegTxCounter,priv->TxCounter);
4929 if(priv->TxCounter==RegTxCounter)
4930 bStuck = TRUE;
4932 priv->TxCounter = RegTxCounter;
4934 return bStuck;
4938 * <Assumption: RT_TX_SPINLOCK is acquired.>
4939 * First added: 2006.11.19 by emily
4941 RESET_TYPE
4942 TxCheckStuck(struct net_device *dev)
4944 struct r8192_priv *priv = ieee80211_priv(dev);
4945 u8 QueueID;
4946 // PRT_TCB pTcb;
4947 // u8 ResetThreshold;
4948 bool bCheckFwTxCnt = false;
4949 //unsigned long flags;
4952 // Decide Stuch threshold according to current power save mode
4955 // RT_TRACE(COMP_RESET, " ==> TxCheckStuck()\n");
4956 // PlatformAcquireSpinLock(Adapter, RT_TX_SPINLOCK);
4957 // spin_lock_irqsave(&priv->ieee80211->lock,flags);
4958 for (QueueID = 0; QueueID<=BEACON_QUEUE;QueueID ++)
4960 if(QueueID == TXCMD_QUEUE)
4961 continue;
4962 #if 1
4963 if((skb_queue_len(&priv->ieee80211->skb_waitQ[QueueID]) == 0) && (skb_queue_len(&priv->ieee80211->skb_aggQ[QueueID]) == 0))
4964 continue;
4965 #endif
4967 bCheckFwTxCnt = true;
4969 // PlatformReleaseSpinLock(Adapter, RT_TX_SPINLOCK);
4970 // spin_unlock_irqrestore(&priv->ieee80211->lock,flags);
4971 // RT_TRACE(COMP_RESET,"bCheckFwTxCnt is %d\n",bCheckFwTxCnt);
4972 #if 1
4973 if(bCheckFwTxCnt)
4975 if(HalTxCheckStuck819xUsb(dev))
4977 RT_TRACE(COMP_RESET, "TxCheckStuck(): Fw indicates no Tx condition! \n");
4978 return RESET_TYPE_SILENT;
4981 #endif
4982 return RESET_TYPE_NORESET;
4985 bool
4986 HalRxCheckStuck819xUsb(struct net_device *dev)
4988 u16 RegRxCounter = read_nic_word(dev, 0x130);
4989 struct r8192_priv *priv = ieee80211_priv(dev);
4990 bool bStuck = FALSE;
4991 //#ifdef RTL8192SU
4993 //#else
4994 static u8 rx_chk_cnt = 0;
4995 RT_TRACE(COMP_RESET,"%s(): RegRxCounter is %d,RxCounter is %d\n",__FUNCTION__,RegRxCounter,priv->RxCounter);
4996 // If rssi is small, we should check rx for long time because of bad rx.
4997 // or maybe it will continuous silent reset every 2 seconds.
4998 rx_chk_cnt++;
4999 if(priv->undecorated_smoothed_pwdb >= (RateAdaptiveTH_High+5))
5001 rx_chk_cnt = 0; //high rssi, check rx stuck right now.
5003 else if(priv->undecorated_smoothed_pwdb < (RateAdaptiveTH_High+5) &&
5004 ((priv->CurrentChannelBW!=HT_CHANNEL_WIDTH_20&&priv->undecorated_smoothed_pwdb>=RateAdaptiveTH_Low_40M) ||
5005 (priv->CurrentChannelBW==HT_CHANNEL_WIDTH_20&&priv->undecorated_smoothed_pwdb>=RateAdaptiveTH_Low_20M)) )
5007 if(rx_chk_cnt < 2)
5009 return bStuck;
5011 else
5013 rx_chk_cnt = 0;
5016 else if(((priv->CurrentChannelBW!=HT_CHANNEL_WIDTH_20&&priv->undecorated_smoothed_pwdb<RateAdaptiveTH_Low_40M) ||
5017 (priv->CurrentChannelBW==HT_CHANNEL_WIDTH_20&&priv->undecorated_smoothed_pwdb<RateAdaptiveTH_Low_20M)) &&
5018 priv->undecorated_smoothed_pwdb >= VeryLowRSSI)
5020 if(rx_chk_cnt < 4)
5022 //DbgPrint("RSSI < %d && RSSI >= %d, no check this time \n", RateAdaptiveTH_Low, VeryLowRSSI);
5023 return bStuck;
5025 else
5027 rx_chk_cnt = 0;
5028 //DbgPrint("RSSI < %d && RSSI >= %d, check this time \n", RateAdaptiveTH_Low, VeryLowRSSI);
5031 else
5033 if(rx_chk_cnt < 8)
5035 //DbgPrint("RSSI <= %d, no check this time \n", VeryLowRSSI);
5036 return bStuck;
5038 else
5040 rx_chk_cnt = 0;
5041 //DbgPrint("RSSI <= %d, check this time \n", VeryLowRSSI);
5044 //#endif
5046 if(priv->RxCounter==RegRxCounter)
5047 bStuck = TRUE;
5049 priv->RxCounter = RegRxCounter;
5051 return bStuck;
5054 RESET_TYPE
5055 RxCheckStuck(struct net_device *dev)
5057 struct r8192_priv *priv = ieee80211_priv(dev);
5058 //int i;
5059 bool bRxCheck = FALSE;
5061 // RT_TRACE(COMP_RESET," ==> RxCheckStuck()\n");
5062 //PlatformAcquireSpinLock(Adapter, RT_RX_SPINLOCK);
5064 if(priv->IrpPendingCount > 1)
5065 bRxCheck = TRUE;
5066 //PlatformReleaseSpinLock(Adapter, RT_RX_SPINLOCK);
5068 // RT_TRACE(COMP_RESET,"bRxCheck is %d \n",bRxCheck);
5069 if(bRxCheck)
5071 if(HalRxCheckStuck819xUsb(dev))
5073 RT_TRACE(COMP_RESET, "RxStuck Condition\n");
5074 return RESET_TYPE_SILENT;
5077 return RESET_TYPE_NORESET;
5082 * This function is called by Checkforhang to check whether we should ask OS to reset driver
5084 * \param pAdapter The adapter context for this miniport
5086 * Note:NIC with USB interface sholud not call this function because we cannot scan descriptor
5087 * to judge whether there is tx stuck.
5088 * Note: This function may be required to be rewrite for Vista OS.
5089 * <<<Assumption: Tx spinlock has been acquired >>>
5091 * 8185 and 8185b does not implement this function. This is added by Emily at 2006.11.24
5093 RESET_TYPE
5094 rtl819x_ifcheck_resetornot(struct net_device *dev)
5096 struct r8192_priv *priv = ieee80211_priv(dev);
5097 RESET_TYPE TxResetType = RESET_TYPE_NORESET;
5098 RESET_TYPE RxResetType = RESET_TYPE_NORESET;
5099 RT_RF_POWER_STATE rfState;
5101 return RESET_TYPE_NORESET;
5103 rfState = priv->ieee80211->eRFPowerState;
5105 TxResetType = TxCheckStuck(dev);
5106 #if 1
5107 if( rfState != eRfOff ||
5108 /*ADAPTER_TEST_STATUS_FLAG(Adapter, ADAPTER_STATUS_FW_DOWNLOAD_FAILURE)) &&*/
5109 (priv->ieee80211->iw_mode != IW_MODE_ADHOC))
5111 // If driver is in the status of firmware download failure , driver skips RF initialization and RF is
5112 // in turned off state. Driver should check whether Rx stuck and do silent reset. And
5113 // if driver is in firmware download failure status, driver should initialize RF in the following
5114 // silent reset procedure Emily, 2008.01.21
5116 // Driver should not check RX stuck in IBSS mode because it is required to
5117 // set Check BSSID in order to send beacon, however, if check BSSID is
5118 // set, STA cannot hear any packet a all. Emily, 2008.04.12
5119 RxResetType = RxCheckStuck(dev);
5121 #endif
5122 if(TxResetType==RESET_TYPE_NORMAL || RxResetType==RESET_TYPE_NORMAL)
5123 return RESET_TYPE_NORMAL;
5124 else if(TxResetType==RESET_TYPE_SILENT || RxResetType==RESET_TYPE_SILENT){
5125 RT_TRACE(COMP_RESET,"%s():silent reset\n",__FUNCTION__);
5126 return RESET_TYPE_SILENT;
5128 else
5129 return RESET_TYPE_NORESET;
5133 void rtl8192_cancel_deferred_work(struct r8192_priv* priv);
5134 int _rtl8192_up(struct net_device *dev);
5135 int rtl8192_close(struct net_device *dev);
5139 void
5140 CamRestoreAllEntry( struct net_device *dev)
5142 u8 EntryId = 0;
5143 struct r8192_priv *priv = ieee80211_priv(dev);
5144 u8* MacAddr = priv->ieee80211->current_network.bssid;
5146 static u8 CAM_CONST_ADDR[4][6] = {
5147 {0x00, 0x00, 0x00, 0x00, 0x00, 0x00},
5148 {0x00, 0x00, 0x00, 0x00, 0x00, 0x01},
5149 {0x00, 0x00, 0x00, 0x00, 0x00, 0x02},
5150 {0x00, 0x00, 0x00, 0x00, 0x00, 0x03}};
5151 static u8 CAM_CONST_BROAD[] =
5152 {0xff, 0xff, 0xff, 0xff, 0xff, 0xff};
5154 RT_TRACE(COMP_SEC, "CamRestoreAllEntry: \n");
5157 if ((priv->ieee80211->pairwise_key_type == KEY_TYPE_WEP40)||
5158 (priv->ieee80211->pairwise_key_type == KEY_TYPE_WEP104))
5161 for(EntryId=0; EntryId<4; EntryId++)
5164 MacAddr = CAM_CONST_ADDR[EntryId];
5165 setKey(dev,
5166 EntryId ,
5167 EntryId,
5168 priv->ieee80211->pairwise_key_type,
5169 MacAddr,
5171 NULL);
5176 else if(priv->ieee80211->pairwise_key_type == KEY_TYPE_TKIP)
5180 if(priv->ieee80211->iw_mode == IW_MODE_ADHOC)
5181 setKey(dev,
5184 priv->ieee80211->pairwise_key_type,
5185 (u8*)dev->dev_addr,
5187 NULL);
5188 else
5189 setKey(dev,
5192 priv->ieee80211->pairwise_key_type,
5193 MacAddr,
5195 NULL);
5198 else if(priv->ieee80211->pairwise_key_type == KEY_TYPE_CCMP)
5202 if(priv->ieee80211->iw_mode == IW_MODE_ADHOC)
5203 setKey(dev,
5206 priv->ieee80211->pairwise_key_type,
5207 (u8*)dev->dev_addr,
5209 NULL);
5210 else
5211 setKey(dev,
5214 priv->ieee80211->pairwise_key_type,
5215 MacAddr,
5217 NULL);
5223 if(priv->ieee80211->group_key_type == KEY_TYPE_TKIP)
5225 MacAddr = CAM_CONST_BROAD;
5226 for(EntryId=1 ; EntryId<4 ; EntryId++)
5229 setKey(dev,
5230 EntryId,
5231 EntryId,
5232 priv->ieee80211->group_key_type,
5233 MacAddr,
5235 NULL);
5238 if(priv->ieee80211->iw_mode == IW_MODE_ADHOC)
5239 setKey(dev,
5242 priv->ieee80211->group_key_type,
5243 CAM_CONST_ADDR[0],
5245 NULL);
5247 else if(priv->ieee80211->group_key_type == KEY_TYPE_CCMP)
5249 MacAddr = CAM_CONST_BROAD;
5250 for(EntryId=1; EntryId<4 ; EntryId++)
5253 setKey(dev,
5254 EntryId ,
5255 EntryId,
5256 priv->ieee80211->group_key_type,
5257 MacAddr,
5259 NULL);
5263 if(priv->ieee80211->iw_mode == IW_MODE_ADHOC)
5264 setKey(dev,
5267 priv->ieee80211->group_key_type,
5268 CAM_CONST_ADDR[0],
5270 NULL);
5273 //////////////////////////////////////////////////////////////
5274 // This function is used to fix Tx/Rx stop bug temporarily.
5275 // This function will do "system reset" to NIC when Tx or Rx is stuck.
5276 // The method checking Tx/Rx stuck of this function is supported by FW,
5277 // which reports Tx and Rx counter to register 0x128 and 0x130.
5278 //////////////////////////////////////////////////////////////
5279 void
5280 rtl819x_ifsilentreset(struct net_device *dev)
5282 //OCTET_STRING asocpdu;
5283 struct r8192_priv *priv = ieee80211_priv(dev);
5284 u8 reset_times = 0;
5285 int reset_status = 0;
5286 struct ieee80211_device *ieee = priv->ieee80211;
5289 // 2007.07.20. If we need to check CCK stop, please uncomment this line.
5290 //bStuck = Adapter->HalFunc.CheckHWStopHandler(Adapter);
5292 if(priv->ResetProgress==RESET_TYPE_NORESET)
5294 RESET_START:
5296 RT_TRACE(COMP_RESET,"=========>Reset progress!! \n");
5298 // Set the variable for reset.
5299 priv->ResetProgress = RESET_TYPE_SILENT;
5300 // rtl8192_close(dev);
5301 #if 1
5302 down(&priv->wx_sem);
5303 if(priv->up == 0)
5305 RT_TRACE(COMP_ERR,"%s():the driver is not up! return\n",__FUNCTION__);
5306 up(&priv->wx_sem);
5307 return ;
5309 priv->up = 0;
5310 RT_TRACE(COMP_RESET,"%s():======>start to down the driver\n",__FUNCTION__);
5311 // if(!netif_queue_stopped(dev))
5312 // netif_stop_queue(dev);
5314 rtl8192_rtx_disable(dev);
5315 rtl8192_cancel_deferred_work(priv);
5316 deinit_hal_dm(dev);
5317 del_timer_sync(&priv->watch_dog_timer);
5319 ieee->sync_scan_hurryup = 1;
5320 if(ieee->state == IEEE80211_LINKED)
5322 down(&ieee->wx_sem);
5323 printk("ieee->state is IEEE80211_LINKED\n");
5324 ieee80211_stop_send_beacons(priv->ieee80211);
5325 del_timer_sync(&ieee->associate_timer);
5326 cancel_delayed_work(&ieee->associate_retry_wq);
5327 ieee80211_stop_scan(ieee);
5328 netif_carrier_off(dev);
5329 up(&ieee->wx_sem);
5331 else{
5332 printk("ieee->state is NOT LINKED\n");
5333 ieee80211_softmac_stop_protocol(priv->ieee80211); }
5334 up(&priv->wx_sem);
5335 RT_TRACE(COMP_RESET,"%s():<==========down process is finished\n",__FUNCTION__);
5336 //rtl8192_irq_disable(dev);
5337 RT_TRACE(COMP_RESET,"%s():===========>start to up the driver\n",__FUNCTION__);
5338 reset_status = _rtl8192_up(dev);
5340 RT_TRACE(COMP_RESET,"%s():<===========up process is finished\n",__FUNCTION__);
5341 if(reset_status == -EAGAIN)
5343 if(reset_times < 3)
5345 reset_times++;
5346 goto RESET_START;
5348 else
5350 RT_TRACE(COMP_ERR," ERR!!! %s(): Reset Failed!!\n", __FUNCTION__);
5353 #endif
5354 ieee->is_silent_reset = 1;
5355 #if 1
5356 EnableHWSecurityConfig8192(dev);
5357 #if 1
5358 if(ieee->state == IEEE80211_LINKED && ieee->iw_mode == IW_MODE_INFRA)
5360 ieee->set_chan(ieee->dev, ieee->current_network.channel);
5362 #if 1
5363 queue_work(ieee->wq, &ieee->associate_complete_wq);
5364 #endif
5367 else if(ieee->state == IEEE80211_LINKED && ieee->iw_mode == IW_MODE_ADHOC)
5369 ieee->set_chan(ieee->dev, ieee->current_network.channel);
5370 ieee->link_change(ieee->dev);
5372 // notify_wx_assoc_event(ieee);
5374 ieee80211_start_send_beacons(ieee);
5376 if (ieee->data_hard_resume)
5377 ieee->data_hard_resume(ieee->dev);
5378 netif_carrier_on(ieee->dev);
5380 #endif
5382 CamRestoreAllEntry(dev);
5384 priv->ResetProgress = RESET_TYPE_NORESET;
5385 priv->reset_count++;
5387 priv->bForcedSilentReset =false;
5388 priv->bResetInProgress = false;
5390 // For test --> force write UFWP.
5391 write_nic_byte(dev, UFWP, 1);
5392 RT_TRACE(COMP_RESET, "Reset finished!! ====>[%d]\n", priv->reset_count);
5393 #endif
5397 void CAM_read_entry(
5398 struct net_device *dev,
5399 u32 iIndex
5402 u32 target_command=0;
5403 u32 target_content=0;
5404 u8 entry_i=0;
5405 u32 ulStatus;
5406 s32 i=100;
5407 // printk("=======>start read CAM\n");
5408 for(entry_i=0;entry_i<CAM_CONTENT_COUNT;entry_i++)
5410 // polling bit, and No Write enable, and address
5411 target_command= entry_i+CAM_CONTENT_COUNT*iIndex;
5412 target_command= target_command | BIT31;
5414 //Check polling bit is clear
5415 // mdelay(1);
5416 #if 1
5417 while((i--)>=0)
5419 ulStatus = read_nic_dword(dev, RWCAM);
5420 if(ulStatus & BIT31){
5421 continue;
5423 else{
5424 break;
5427 #endif
5428 write_nic_dword(dev, RWCAM, target_command);
5429 RT_TRACE(COMP_SEC,"CAM_read_entry(): WRITE A0: %x \n",target_command);
5430 // printk("CAM_read_entry(): WRITE A0: %lx \n",target_command);
5431 target_content = read_nic_dword(dev, RCAMO);
5432 RT_TRACE(COMP_SEC, "CAM_read_entry(): WRITE A8: %x \n",target_content);
5433 // printk("CAM_read_entry(): WRITE A8: %lx \n",target_content);
5435 printk("\n");
5438 void rtl819x_update_rxcounts(
5439 struct r8192_priv *priv,
5440 u32* TotalRxBcnNum,
5441 u32* TotalRxDataNum
5444 u16 SlotIndex;
5445 u8 i;
5447 *TotalRxBcnNum = 0;
5448 *TotalRxDataNum = 0;
5450 SlotIndex = (priv->ieee80211->LinkDetectInfo.SlotIndex++)%(priv->ieee80211->LinkDetectInfo.SlotNum);
5451 priv->ieee80211->LinkDetectInfo.RxBcnNum[SlotIndex] = priv->ieee80211->LinkDetectInfo.NumRecvBcnInPeriod;
5452 priv->ieee80211->LinkDetectInfo.RxDataNum[SlotIndex] = priv->ieee80211->LinkDetectInfo.NumRecvDataInPeriod;
5453 for( i=0; i<priv->ieee80211->LinkDetectInfo.SlotNum; i++ ){
5454 *TotalRxBcnNum += priv->ieee80211->LinkDetectInfo.RxBcnNum[i];
5455 *TotalRxDataNum += priv->ieee80211->LinkDetectInfo.RxDataNum[i];
5459 void rtl819x_watchdog_wqcallback(struct work_struct *work)
5461 struct delayed_work *dwork = container_of(work,
5462 struct delayed_work,
5463 work);
5464 struct r8192_priv *priv = container_of(dwork,
5465 struct r8192_priv,
5466 watch_dog_wq);
5467 struct net_device *dev = priv->ieee80211->dev;
5468 struct ieee80211_device* ieee = priv->ieee80211;
5469 RESET_TYPE ResetType = RESET_TYPE_NORESET;
5470 static u8 check_reset_cnt;
5471 u32 TotalRxBcnNum = 0;
5472 u32 TotalRxDataNum = 0;
5473 bool bBusyTraffic = false;
5475 if(!priv->up)
5476 return;
5477 hal_dm_watchdog(dev);
5478 /* to get busy traffic condition */
5479 if (ieee->state == IEEE80211_LINKED) {
5480 if (ieee->LinkDetectInfo.NumRxOkInPeriod > 666 ||
5481 ieee->LinkDetectInfo.NumTxOkInPeriod > 666)
5482 bBusyTraffic = true;
5484 ieee->LinkDetectInfo.NumRxOkInPeriod = 0;
5485 ieee->LinkDetectInfo.NumTxOkInPeriod = 0;
5486 ieee->LinkDetectInfo.bBusyTraffic = bBusyTraffic;
5489 if (priv->ieee80211->state == IEEE80211_LINKED &&
5490 priv->ieee80211->iw_mode == IW_MODE_INFRA) {
5491 rtl819x_update_rxcounts(priv, &TotalRxBcnNum, &TotalRxDataNum);
5492 if ((TotalRxBcnNum + TotalRxDataNum) == 0) {
5493 RT_TRACE(COMP_ERR, "%s(): AP is powered off,"
5494 "connect another one\n", __func__);
5495 /* Dot11d_Reset(dev); */
5496 priv->ieee80211->state = IEEE80211_ASSOCIATING;
5497 notify_wx_assoc_event(priv->ieee80211);
5498 RemovePeerTS(priv->ieee80211,
5499 priv->ieee80211->current_network.bssid);
5500 ieee->is_roaming = true;
5501 priv->ieee80211->link_change(dev);
5502 if(ieee->LedControlHandler != NULL)
5503 ieee->LedControlHandler(ieee->dev,
5504 LED_CTL_START_TO_LINK);
5505 queue_work(priv->ieee80211->wq,
5506 &priv->ieee80211->associate_procedure_wq);
5509 priv->ieee80211->LinkDetectInfo.NumRecvBcnInPeriod = 0;
5510 priv->ieee80211->LinkDetectInfo.NumRecvDataInPeriod = 0;
5513 * CAM_read_entry(dev,4);
5514 * check if reset the driver
5516 if (check_reset_cnt++ >= 3 && !ieee->is_roaming) {
5517 ResetType = rtl819x_ifcheck_resetornot(dev);
5518 check_reset_cnt = 3;
5520 if ((priv->force_reset) || (priv->ResetProgress == RESET_TYPE_NORESET &&
5521 (priv->bForcedSilentReset ||
5522 (!priv->bDisableNormalResetCheck &&
5523 /* This is control by OID set in Pomelo */
5524 ResetType == RESET_TYPE_SILENT)))) {
5525 RT_TRACE(COMP_RESET, "%s(): priv->force_reset is %d,"
5526 "priv->ResetProgress is %d, "
5527 "priv->bForcedSilentReset is %d, "
5528 "priv->bDisableNormalResetCheck is %d, "
5529 "ResetType is %d",
5530 __func__,
5531 priv->force_reset,
5532 priv->ResetProgress,
5533 priv->bForcedSilentReset,
5534 priv->bDisableNormalResetCheck,
5535 ResetType);
5536 rtl819x_ifsilentreset(dev);
5538 priv->force_reset = false;
5539 priv->bForcedSilentReset = false;
5540 priv->bResetInProgress = false;
5543 void watch_dog_timer_callback(unsigned long data)
5545 struct r8192_priv *priv = ieee80211_priv((struct net_device *) data);
5546 //printk("===============>watch_dog timer\n");
5547 queue_delayed_work(priv->priv_wq,&priv->watch_dog_wq, 0);
5548 mod_timer(&priv->watch_dog_timer, jiffies + MSECS(IEEE80211_WATCH_DOG_TIME));
5550 int _rtl8192_up(struct net_device *dev)
5552 struct r8192_priv *priv = ieee80211_priv(dev);
5553 //int i;
5554 int init_status = 0;
5555 priv->up=1;
5556 priv->ieee80211->ieee_up=1;
5557 RT_TRACE(COMP_INIT, "Bringing up iface");
5558 init_status = priv->ops->rtl819x_adapter_start(dev);
5559 if(!init_status)
5561 RT_TRACE(COMP_ERR,"ERR!!! %s(): initialization is failed!\n", __FUNCTION__);
5562 priv->up=priv->ieee80211->ieee_up = 0;
5563 return -EAGAIN;
5565 RT_TRACE(COMP_INIT, "start adapter finished\n");
5566 rtl8192_rx_enable(dev);
5567 // rtl8192_tx_enable(dev);
5568 if(priv->ieee80211->state != IEEE80211_LINKED)
5569 ieee80211_softmac_start_protocol(priv->ieee80211);
5570 ieee80211_reset_queue(priv->ieee80211);
5571 watch_dog_timer_callback((unsigned long) dev);
5572 if(!netif_queue_stopped(dev))
5573 netif_start_queue(dev);
5574 else
5575 netif_wake_queue(dev);
5578 * Make sure that drop_unencrypted is initialized as "0"
5579 * No packets will be sent in non-security mode if we had set drop_unencrypted.
5580 * ex, After kill wpa_supplicant process, make the driver up again.
5581 * drop_unencrypted remains as "1", which is set by wpa_supplicant. 2008/12/04.john
5583 priv->ieee80211->drop_unencrypted = 0;
5585 return 0;
5589 int rtl8192_open(struct net_device *dev)
5591 struct r8192_priv *priv = ieee80211_priv(dev);
5592 int ret;
5593 down(&priv->wx_sem);
5594 ret = rtl8192_up(dev);
5595 up(&priv->wx_sem);
5596 return ret;
5601 int rtl8192_up(struct net_device *dev)
5603 struct r8192_priv *priv = ieee80211_priv(dev);
5605 if (priv->up == 1) return -1;
5607 return _rtl8192_up(dev);
5611 int rtl8192_close(struct net_device *dev)
5613 struct r8192_priv *priv = ieee80211_priv(dev);
5614 int ret;
5616 down(&priv->wx_sem);
5618 ret = rtl8192_down(dev);
5620 up(&priv->wx_sem);
5622 return ret;
5626 int rtl8192_down(struct net_device *dev)
5628 struct r8192_priv *priv = ieee80211_priv(dev);
5629 int i;
5631 if (priv->up == 0) return -1;
5633 priv->up=0;
5634 priv->ieee80211->ieee_up = 0;
5635 RT_TRACE(COMP_DOWN, "==========>%s()\n", __FUNCTION__);
5636 /* FIXME */
5637 if (!netif_queue_stopped(dev))
5638 netif_stop_queue(dev);
5640 rtl8192_rtx_disable(dev);
5641 //rtl8192_irq_disable(dev);
5643 /* Tx related queue release */
5644 for(i = 0; i < MAX_QUEUE_SIZE; i++) {
5645 skb_queue_purge(&priv->ieee80211->skb_waitQ [i]);
5647 for(i = 0; i < MAX_QUEUE_SIZE; i++) {
5648 skb_queue_purge(&priv->ieee80211->skb_aggQ [i]);
5651 for(i = 0; i < MAX_QUEUE_SIZE; i++) {
5652 skb_queue_purge(&priv->ieee80211->skb_drv_aggQ [i]);
5655 //as cancel_delayed_work will del work->timer, so if work is not definedas struct delayed_work, it will corrupt
5656 // flush_scheduled_work();
5657 rtl8192_cancel_deferred_work(priv);
5658 deinit_hal_dm(dev);
5659 del_timer_sync(&priv->watch_dog_timer);
5662 ieee80211_softmac_stop_protocol(priv->ieee80211);
5663 memset(&priv->ieee80211->current_network, 0 , offsetof(struct ieee80211_network, list));
5664 RT_TRACE(COMP_DOWN, "<==========%s()\n", __FUNCTION__);
5666 return 0;
5670 void rtl8192_commit(struct net_device *dev)
5672 struct r8192_priv *priv = ieee80211_priv(dev);
5673 int reset_status = 0;
5674 //u8 reset_times = 0;
5675 if (priv->up == 0) return ;
5676 priv->up = 0;
5678 rtl8192_cancel_deferred_work(priv);
5679 del_timer_sync(&priv->watch_dog_timer);
5680 //cancel_delayed_work(&priv->SwChnlWorkItem);
5682 ieee80211_softmac_stop_protocol(priv->ieee80211);
5684 //rtl8192_irq_disable(dev);
5685 rtl8192_rtx_disable(dev);
5686 reset_status = _rtl8192_up(dev);
5691 void rtl8192_restart(struct net_device *dev)
5693 struct r8192_priv *priv = ieee80211_priv(dev);
5695 void rtl8192_restart(struct work_struct *work)
5697 struct r8192_priv *priv = container_of(work, struct r8192_priv, reset_wq);
5698 struct net_device *dev = priv->ieee80211->dev;
5700 down(&priv->wx_sem);
5702 rtl8192_commit(dev);
5704 up(&priv->wx_sem);
5707 static void r8192_set_multicast(struct net_device *dev)
5709 struct r8192_priv *priv = ieee80211_priv(dev);
5710 short promisc;
5712 //down(&priv->wx_sem);
5714 /* FIXME FIXME */
5716 promisc = (dev->flags & IFF_PROMISC) ? 1:0;
5718 if (promisc != priv->promisc)
5719 // rtl8192_commit(dev);
5721 priv->promisc = promisc;
5723 //schedule_work(&priv->reset_wq);
5724 //up(&priv->wx_sem);
5728 int r8192_set_mac_adr(struct net_device *dev, void *mac)
5730 struct r8192_priv *priv = ieee80211_priv(dev);
5731 struct sockaddr *addr = mac;
5733 down(&priv->wx_sem);
5735 memcpy(dev->dev_addr, addr->sa_data, ETH_ALEN);
5737 schedule_work(&priv->reset_wq);
5739 up(&priv->wx_sem);
5741 return 0;
5744 /* based on ipw2200 driver */
5745 int rtl8192_ioctl(struct net_device *dev, struct ifreq *rq, int cmd)
5747 struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
5748 struct iwreq *wrq = (struct iwreq *)rq;
5749 int ret=-1;
5750 struct ieee80211_device *ieee = priv->ieee80211;
5751 u32 key[4];
5752 u8 broadcast_addr[6] = {0xff,0xff,0xff,0xff,0xff,0xff};
5753 u8 zero_addr[6] = {0};
5754 struct iw_point *p = &wrq->u.data;
5755 struct ieee_param *ipw = NULL;//(struct ieee_param *)wrq->u.data.pointer;
5757 down(&priv->wx_sem);
5760 if (p->length < sizeof(struct ieee_param) || !p->pointer){
5761 ret = -EINVAL;
5762 goto out;
5765 ipw = kmalloc(p->length, GFP_KERNEL);
5766 if (ipw == NULL){
5767 ret = -ENOMEM;
5768 goto out;
5770 if (copy_from_user(ipw, p->pointer, p->length)) {
5771 kfree(ipw);
5772 ret = -EFAULT;
5773 goto out;
5776 switch (cmd) {
5777 case RTL_IOCTL_WPA_SUPPLICANT:
5778 //parse here for HW security
5779 if (ipw->cmd == IEEE_CMD_SET_ENCRYPTION)
5781 if (ipw->u.crypt.set_tx)
5783 if (strcmp(ipw->u.crypt.alg, "CCMP") == 0)
5784 ieee->pairwise_key_type = KEY_TYPE_CCMP;
5785 else if (strcmp(ipw->u.crypt.alg, "TKIP") == 0)
5786 ieee->pairwise_key_type = KEY_TYPE_TKIP;
5787 else if (strcmp(ipw->u.crypt.alg, "WEP") == 0)
5789 if (ipw->u.crypt.key_len == 13)
5790 ieee->pairwise_key_type = KEY_TYPE_WEP104;
5791 else if (ipw->u.crypt.key_len == 5)
5792 ieee->pairwise_key_type = KEY_TYPE_WEP40;
5794 else
5795 ieee->pairwise_key_type = KEY_TYPE_NA;
5797 if (ieee->pairwise_key_type)
5799 // FIXME:these two lines below just to fix ipw interface bug, that is, it will never set mode down to driver. So treat it as ADHOC mode, if no association procedure. WB. 2009.02.04
5800 if (memcmp(ieee->ap_mac_addr, zero_addr, 6) == 0)
5801 ieee->iw_mode = IW_MODE_ADHOC;
5802 memcpy((u8*)key, ipw->u.crypt.key, 16);
5803 EnableHWSecurityConfig8192(dev);
5804 //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!
5805 //added by WB.
5806 setKey(dev, 4, ipw->u.crypt.idx, ieee->pairwise_key_type, (u8*)ieee->ap_mac_addr, 0, key);
5807 if (ieee->iw_mode == IW_MODE_ADHOC)
5808 setKey(dev, ipw->u.crypt.idx, ipw->u.crypt.idx, ieee->pairwise_key_type, (u8*)ieee->ap_mac_addr, 0, key);
5811 else //if (ipw->u.crypt.idx) //group key use idx > 0
5813 memcpy((u8*)key, ipw->u.crypt.key, 16);
5814 if (strcmp(ipw->u.crypt.alg, "CCMP") == 0)
5815 ieee->group_key_type= KEY_TYPE_CCMP;
5816 else if (strcmp(ipw->u.crypt.alg, "TKIP") == 0)
5817 ieee->group_key_type = KEY_TYPE_TKIP;
5818 else if (strcmp(ipw->u.crypt.alg, "WEP") == 0)
5820 if (ipw->u.crypt.key_len == 13)
5821 ieee->group_key_type = KEY_TYPE_WEP104;
5822 else if (ipw->u.crypt.key_len == 5)
5823 ieee->group_key_type = KEY_TYPE_WEP40;
5825 else
5826 ieee->group_key_type = KEY_TYPE_NA;
5828 if (ieee->group_key_type)
5830 setKey( dev,
5831 ipw->u.crypt.idx,
5832 ipw->u.crypt.idx, //KeyIndex
5833 ieee->group_key_type, //KeyType
5834 broadcast_addr, //MacAddr
5835 0, //DefaultKey
5836 key); //KeyContent
5840 #ifdef JOHN_HWSEC_DEBUG
5841 //john's test 0711
5842 printk("@@ wrq->u pointer = ");
5843 for(i=0;i<wrq->u.data.length;i++){
5844 if(i%10==0) printk("\n");
5845 printk( "%8x|", ((u32*)wrq->u.data.pointer)[i] );
5847 printk("\n");
5848 #endif /*JOHN_HWSEC_DEBUG*/
5849 ret = ieee80211_wpa_supplicant_ioctl(priv->ieee80211, &wrq->u.data);
5850 break;
5852 default:
5853 ret = -EOPNOTSUPP;
5854 break;
5856 kfree(ipw);
5857 ipw = NULL;
5858 out:
5859 up(&priv->wx_sem);
5860 return ret;
5863 u8 rtl8192SU_HwRateToMRate(bool bIsHT, u8 rate,bool bFirstAMPDU)
5866 u8 ret_rate = 0x02;
5868 if( bFirstAMPDU )
5870 if(!bIsHT)
5872 switch(rate)
5875 case DESC92S_RATE1M: ret_rate = MGN_1M; break;
5876 case DESC92S_RATE2M: ret_rate = MGN_2M; break;
5877 case DESC92S_RATE5_5M: ret_rate = MGN_5_5M; break;
5878 case DESC92S_RATE11M: ret_rate = MGN_11M; break;
5879 case DESC92S_RATE6M: ret_rate = MGN_6M; break;
5880 case DESC92S_RATE9M: ret_rate = MGN_9M; break;
5881 case DESC92S_RATE12M: ret_rate = MGN_12M; break;
5882 case DESC92S_RATE18M: ret_rate = MGN_18M; break;
5883 case DESC92S_RATE24M: ret_rate = MGN_24M; break;
5884 case DESC92S_RATE36M: ret_rate = MGN_36M; break;
5885 case DESC92S_RATE48M: ret_rate = MGN_48M; break;
5886 case DESC92S_RATE54M: ret_rate = MGN_54M; break;
5888 default:
5889 RT_TRACE(COMP_RECV, "HwRateToMRate90(): Non supported Rate [%x], bIsHT = %d!!!\n", rate, bIsHT);
5890 break;
5893 else
5895 switch(rate)
5898 case DESC92S_RATEMCS0: ret_rate = MGN_MCS0; break;
5899 case DESC92S_RATEMCS1: ret_rate = MGN_MCS1; break;
5900 case DESC92S_RATEMCS2: ret_rate = MGN_MCS2; break;
5901 case DESC92S_RATEMCS3: ret_rate = MGN_MCS3; break;
5902 case DESC92S_RATEMCS4: ret_rate = MGN_MCS4; break;
5903 case DESC92S_RATEMCS5: ret_rate = MGN_MCS5; break;
5904 case DESC92S_RATEMCS6: ret_rate = MGN_MCS6; break;
5905 case DESC92S_RATEMCS7: ret_rate = MGN_MCS7; break;
5906 case DESC92S_RATEMCS8: ret_rate = MGN_MCS8; break;
5907 case DESC92S_RATEMCS9: ret_rate = MGN_MCS9; break;
5908 case DESC92S_RATEMCS10: ret_rate = MGN_MCS10; break;
5909 case DESC92S_RATEMCS11: ret_rate = MGN_MCS11; break;
5910 case DESC92S_RATEMCS12: ret_rate = MGN_MCS12; break;
5911 case DESC92S_RATEMCS13: ret_rate = MGN_MCS13; break;
5912 case DESC92S_RATEMCS14: ret_rate = MGN_MCS14; break;
5913 case DESC92S_RATEMCS15: ret_rate = MGN_MCS15; break;
5914 case DESC92S_RATEMCS32: ret_rate = (0x80|0x20); break;
5916 default:
5917 RT_TRACE(COMP_RECV, "HwRateToMRate92S(): Non supported Rate [%x], bIsHT = %d!!!\n",rate, bIsHT );
5918 break;
5923 else
5925 switch(rate)
5928 case DESC92S_RATE1M: ret_rate = MGN_1M; break;
5929 case DESC92S_RATE2M: ret_rate = MGN_2M; break;
5930 case DESC92S_RATE5_5M: ret_rate = MGN_5_5M; break;
5931 case DESC92S_RATE11M: ret_rate = MGN_11M; break;
5932 case DESC92S_RATE6M: ret_rate = MGN_6M; break;
5933 case DESC92S_RATE9M: ret_rate = MGN_9M; break;
5934 case DESC92S_RATE12M: ret_rate = MGN_12M; break;
5935 case DESC92S_RATE18M: ret_rate = MGN_18M; break;
5936 case DESC92S_RATE24M: ret_rate = MGN_24M; break;
5937 case DESC92S_RATE36M: ret_rate = MGN_36M; break;
5938 case DESC92S_RATE48M: ret_rate = MGN_48M; break;
5939 case DESC92S_RATE54M: ret_rate = MGN_54M; break;
5940 case DESC92S_RATEMCS0: ret_rate = MGN_MCS0; break;
5941 case DESC92S_RATEMCS1: ret_rate = MGN_MCS1; break;
5942 case DESC92S_RATEMCS2: ret_rate = MGN_MCS2; break;
5943 case DESC92S_RATEMCS3: ret_rate = MGN_MCS3; break;
5944 case DESC92S_RATEMCS4: ret_rate = MGN_MCS4; break;
5945 case DESC92S_RATEMCS5: ret_rate = MGN_MCS5; break;
5946 case DESC92S_RATEMCS6: ret_rate = MGN_MCS6; break;
5947 case DESC92S_RATEMCS7: ret_rate = MGN_MCS7; break;
5948 case DESC92S_RATEMCS8: ret_rate = MGN_MCS8; break;
5949 case DESC92S_RATEMCS9: ret_rate = MGN_MCS9; break;
5950 case DESC92S_RATEMCS10: ret_rate = MGN_MCS10; break;
5951 case DESC92S_RATEMCS11: ret_rate = MGN_MCS11; break;
5952 case DESC92S_RATEMCS12: ret_rate = MGN_MCS12; break;
5953 case DESC92S_RATEMCS13: ret_rate = MGN_MCS13; break;
5954 case DESC92S_RATEMCS14: ret_rate = MGN_MCS14; break;
5955 case DESC92S_RATEMCS15: ret_rate = MGN_MCS15; break;
5956 case DESC92S_RATEMCS32: ret_rate = (0x80|0x20); break;
5958 default:
5959 RT_TRACE(COMP_RECV, "HwRateToMRate92S(): Non supported Rate [%x], bIsHT = %d!!!\n",rate, bIsHT );
5960 break;
5963 return ret_rate;
5966 u8 HwRateToMRate90(bool bIsHT, u8 rate)
5968 u8 ret_rate = 0xff;
5970 if(!bIsHT) {
5971 switch(rate) {
5972 case DESC90_RATE1M: ret_rate = MGN_1M; break;
5973 case DESC90_RATE2M: ret_rate = MGN_2M; break;
5974 case DESC90_RATE5_5M: ret_rate = MGN_5_5M; break;
5975 case DESC90_RATE11M: ret_rate = MGN_11M; break;
5976 case DESC90_RATE6M: ret_rate = MGN_6M; break;
5977 case DESC90_RATE9M: ret_rate = MGN_9M; break;
5978 case DESC90_RATE12M: ret_rate = MGN_12M; break;
5979 case DESC90_RATE18M: ret_rate = MGN_18M; break;
5980 case DESC90_RATE24M: ret_rate = MGN_24M; break;
5981 case DESC90_RATE36M: ret_rate = MGN_36M; break;
5982 case DESC90_RATE48M: ret_rate = MGN_48M; break;
5983 case DESC90_RATE54M: ret_rate = MGN_54M; break;
5985 default:
5986 ret_rate = 0xff;
5987 RT_TRACE(COMP_RECV, "HwRateToMRate90(): Non supported Rate [%x], bIsHT = %d!!!\n", rate, bIsHT);
5988 break;
5991 } else {
5992 switch(rate) {
5993 case DESC90_RATEMCS0: ret_rate = MGN_MCS0; break;
5994 case DESC90_RATEMCS1: ret_rate = MGN_MCS1; break;
5995 case DESC90_RATEMCS2: ret_rate = MGN_MCS2; break;
5996 case DESC90_RATEMCS3: ret_rate = MGN_MCS3; break;
5997 case DESC90_RATEMCS4: ret_rate = MGN_MCS4; break;
5998 case DESC90_RATEMCS5: ret_rate = MGN_MCS5; break;
5999 case DESC90_RATEMCS6: ret_rate = MGN_MCS6; break;
6000 case DESC90_RATEMCS7: ret_rate = MGN_MCS7; break;
6001 case DESC90_RATEMCS8: ret_rate = MGN_MCS8; break;
6002 case DESC90_RATEMCS9: ret_rate = MGN_MCS9; break;
6003 case DESC90_RATEMCS10: ret_rate = MGN_MCS10; break;
6004 case DESC90_RATEMCS11: ret_rate = MGN_MCS11; break;
6005 case DESC90_RATEMCS12: ret_rate = MGN_MCS12; break;
6006 case DESC90_RATEMCS13: ret_rate = MGN_MCS13; break;
6007 case DESC90_RATEMCS14: ret_rate = MGN_MCS14; break;
6008 case DESC90_RATEMCS15: ret_rate = MGN_MCS15; break;
6009 case DESC90_RATEMCS32: ret_rate = (0x80|0x20); break;
6011 default:
6012 ret_rate = 0xff;
6013 RT_TRACE(COMP_RECV, "HwRateToMRate90(): Non supported Rate [%x], bIsHT = %d!!!\n",rate, bIsHT);
6014 break;
6018 return ret_rate;
6022 * Function: UpdateRxPktTimeStamp
6023 * Overview: Recored down the TSF time stamp when receiving a packet
6025 * Input:
6026 * PADAPTER Adapter
6027 * PRT_RFD pRfd,
6029 * Output:
6030 * PRT_RFD pRfd
6031 * (pRfd->Status.TimeStampHigh is updated)
6032 * (pRfd->Status.TimeStampLow is updated)
6033 * Return:
6034 * None
6036 void UpdateRxPktTimeStamp8190 (struct net_device *dev, struct ieee80211_rx_stats *stats)
6038 struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
6040 if(stats->bIsAMPDU && !stats->bFirstMPDU) {
6041 stats->mac_time[0] = priv->LastRxDescTSFLow;
6042 stats->mac_time[1] = priv->LastRxDescTSFHigh;
6043 } else {
6044 priv->LastRxDescTSFLow = stats->mac_time[0];
6045 priv->LastRxDescTSFHigh = stats->mac_time[1];
6049 //by amy 080606
6051 long rtl819x_translate_todbm(u8 signal_strength_index )// 0-100 index.
6053 long signal_power; // in dBm.
6055 // Translate to dBm (x=0.5y-95).
6056 signal_power = (long)((signal_strength_index + 1) >> 1);
6057 signal_power -= 95;
6059 return signal_power;
6063 /* 2008/01/22 MH We can not delcare RSSI/EVM total value of sliding window to
6064 be a local static. Otherwise, it may increase when we return from S3/S4. The
6065 value will be kept in memory or disk. We must delcare the value in adapter
6066 and it will be reinitialized when return from S3/S4. */
6067 void rtl8192_process_phyinfo(struct r8192_priv * priv,u8* buffer, struct ieee80211_rx_stats * pprevious_stats, struct ieee80211_rx_stats * pcurrent_stats)
6069 bool bcheck = false;
6070 u8 rfpath;
6071 u32 nspatial_stream, tmp_val;
6072 //u8 i;
6073 static u32 slide_rssi_index=0, slide_rssi_statistics=0;
6074 static u32 slide_evm_index=0, slide_evm_statistics=0;
6075 static u32 last_rssi=0, last_evm=0;
6077 static u32 slide_beacon_adc_pwdb_index=0, slide_beacon_adc_pwdb_statistics=0;
6078 static u32 last_beacon_adc_pwdb=0;
6080 struct ieee80211_hdr_3addr *hdr;
6081 u16 sc ;
6082 unsigned int frag,seq;
6083 hdr = (struct ieee80211_hdr_3addr *)buffer;
6084 sc = le16_to_cpu(hdr->seq_ctrl);
6085 frag = WLAN_GET_SEQ_FRAG(sc);
6086 seq = WLAN_GET_SEQ_SEQ(sc);
6087 //cosa add 04292008 to record the sequence number
6088 pcurrent_stats->Seq_Num = seq;
6090 // Check whether we should take the previous packet into accounting
6092 if(!pprevious_stats->bIsAMPDU)
6094 // if previous packet is not aggregated packet
6095 bcheck = true;
6096 }else
6101 if(slide_rssi_statistics++ >= PHY_RSSI_SLID_WIN_MAX)
6103 slide_rssi_statistics = PHY_RSSI_SLID_WIN_MAX;
6104 last_rssi = priv->stats.slide_signal_strength[slide_rssi_index];
6105 priv->stats.slide_rssi_total -= last_rssi;
6107 priv->stats.slide_rssi_total += pprevious_stats->SignalStrength;
6109 priv->stats.slide_signal_strength[slide_rssi_index++] = pprevious_stats->SignalStrength;
6110 if(slide_rssi_index >= PHY_RSSI_SLID_WIN_MAX)
6111 slide_rssi_index = 0;
6113 // <1> Showed on UI for user, in dbm
6114 tmp_val = priv->stats.slide_rssi_total/slide_rssi_statistics;
6115 priv->stats.signal_strength = rtl819x_translate_todbm((u8)tmp_val);
6116 pcurrent_stats->rssi = priv->stats.signal_strength;
6118 // If the previous packet does not match the criteria, neglect it
6120 if(!pprevious_stats->bPacketMatchBSSID)
6122 if(!pprevious_stats->bToSelfBA)
6123 return;
6126 if(!bcheck)
6127 return;
6130 //rtl8190_process_cck_rxpathsel(priv,pprevious_stats);//only rtl8190 supported
6133 // Check RSSI
6135 priv->stats.num_process_phyinfo++;
6137 /* record the general signal strength to the sliding window. */
6140 // <2> Showed on UI for engineering
6141 // hardware does not provide rssi information for each rf path in CCK
6142 if(!pprevious_stats->bIsCCK && (pprevious_stats->bPacketToSelf || pprevious_stats->bToSelfBA))
6144 for (rfpath = RF90_PATH_A; rfpath < priv->NumTotalRFPath; rfpath++)
6146 if (!rtl8192_phy_CheckIsLegalRFPath(priv->ieee80211->dev, rfpath))
6147 continue;
6149 //Fixed by Jacken 2008-03-20
6150 if(priv->stats.rx_rssi_percentage[rfpath] == 0)
6152 priv->stats.rx_rssi_percentage[rfpath] = pprevious_stats->RxMIMOSignalStrength[rfpath];
6153 //DbgPrint("MIMO RSSI initialize \n");
6155 if(pprevious_stats->RxMIMOSignalStrength[rfpath] > priv->stats.rx_rssi_percentage[rfpath])
6157 priv->stats.rx_rssi_percentage[rfpath] =
6158 ( (priv->stats.rx_rssi_percentage[rfpath]*(Rx_Smooth_Factor-1)) +
6159 (pprevious_stats->RxMIMOSignalStrength[rfpath])) /(Rx_Smooth_Factor);
6160 priv->stats.rx_rssi_percentage[rfpath] = priv->stats.rx_rssi_percentage[rfpath] + 1;
6162 else
6164 priv->stats.rx_rssi_percentage[rfpath] =
6165 ( (priv->stats.rx_rssi_percentage[rfpath]*(Rx_Smooth_Factor-1)) +
6166 (pprevious_stats->RxMIMOSignalStrength[rfpath])) /(Rx_Smooth_Factor);
6168 RT_TRACE(COMP_DBG,"priv->stats.rx_rssi_percentage[rfPath] = %d \n" ,priv->stats.rx_rssi_percentage[rfpath] );
6174 // Check PWDB.
6176 RT_TRACE(COMP_RXDESC, "Smooth %s PWDB = %d\n",
6177 pprevious_stats->bIsCCK? "CCK": "OFDM",
6178 pprevious_stats->RxPWDBAll);
6180 if(pprevious_stats->bPacketBeacon)
6182 /* record the beacon pwdb to the sliding window. */
6183 if(slide_beacon_adc_pwdb_statistics++ >= PHY_Beacon_RSSI_SLID_WIN_MAX)
6185 slide_beacon_adc_pwdb_statistics = PHY_Beacon_RSSI_SLID_WIN_MAX;
6186 last_beacon_adc_pwdb = priv->stats.Slide_Beacon_pwdb[slide_beacon_adc_pwdb_index];
6187 priv->stats.Slide_Beacon_Total -= last_beacon_adc_pwdb;
6188 //DbgPrint("slide_beacon_adc_pwdb_index = %d, last_beacon_adc_pwdb = %d, Adapter->RxStats.Slide_Beacon_Total = %d\n",
6189 // slide_beacon_adc_pwdb_index, last_beacon_adc_pwdb, Adapter->RxStats.Slide_Beacon_Total);
6191 priv->stats.Slide_Beacon_Total += pprevious_stats->RxPWDBAll;
6192 priv->stats.Slide_Beacon_pwdb[slide_beacon_adc_pwdb_index] = pprevious_stats->RxPWDBAll;
6193 //DbgPrint("slide_beacon_adc_pwdb_index = %d, pPreviousRfd->Status.RxPWDBAll = %d\n", slide_beacon_adc_pwdb_index, pPreviousRfd->Status.RxPWDBAll);
6194 slide_beacon_adc_pwdb_index++;
6195 if(slide_beacon_adc_pwdb_index >= PHY_Beacon_RSSI_SLID_WIN_MAX)
6196 slide_beacon_adc_pwdb_index = 0;
6197 pprevious_stats->RxPWDBAll = priv->stats.Slide_Beacon_Total/slide_beacon_adc_pwdb_statistics;
6198 if(pprevious_stats->RxPWDBAll >= 3)
6199 pprevious_stats->RxPWDBAll -= 3;
6202 RT_TRACE(COMP_RXDESC, "Smooth %s PWDB = %d\n",
6203 pprevious_stats->bIsCCK? "CCK": "OFDM",
6204 pprevious_stats->RxPWDBAll);
6207 if(pprevious_stats->bPacketToSelf || pprevious_stats->bPacketBeacon || pprevious_stats->bToSelfBA)
6209 if(priv->undecorated_smoothed_pwdb < 0) // initialize
6211 priv->undecorated_smoothed_pwdb = pprevious_stats->RxPWDBAll;
6212 //DbgPrint("First pwdb initialize \n");
6214 #if 1
6215 if(pprevious_stats->RxPWDBAll > (u32)priv->undecorated_smoothed_pwdb)
6217 priv->undecorated_smoothed_pwdb =
6218 ( ((priv->undecorated_smoothed_pwdb)*(Rx_Smooth_Factor-1)) +
6219 (pprevious_stats->RxPWDBAll)) /(Rx_Smooth_Factor);
6220 priv->undecorated_smoothed_pwdb = priv->undecorated_smoothed_pwdb + 1;
6222 else
6224 priv->undecorated_smoothed_pwdb =
6225 ( ((priv->undecorated_smoothed_pwdb)*(Rx_Smooth_Factor-1)) +
6226 (pprevious_stats->RxPWDBAll)) /(Rx_Smooth_Factor);
6228 #else
6229 //Fixed by Jacken 2008-03-20
6230 if(pPreviousRfd->Status.RxPWDBAll > (u32)pHalData->UndecoratedSmoothedPWDB)
6232 pHalData->UndecoratedSmoothedPWDB =
6233 ( ((pHalData->UndecoratedSmoothedPWDB)* 5) + (pPreviousRfd->Status.RxPWDBAll)) / 6;
6234 pHalData->UndecoratedSmoothedPWDB = pHalData->UndecoratedSmoothedPWDB + 1;
6236 else
6238 pHalData->UndecoratedSmoothedPWDB =
6239 ( ((pHalData->UndecoratedSmoothedPWDB)* 5) + (pPreviousRfd->Status.RxPWDBAll)) / 6;
6241 #endif
6246 // Check EVM
6248 /* record the general EVM to the sliding window. */
6249 if(pprevious_stats->SignalQuality == 0)
6252 else
6254 if(pprevious_stats->bPacketToSelf || pprevious_stats->bPacketBeacon || pprevious_stats->bToSelfBA){
6255 if(slide_evm_statistics++ >= PHY_RSSI_SLID_WIN_MAX){
6256 slide_evm_statistics = PHY_RSSI_SLID_WIN_MAX;
6257 last_evm = priv->stats.slide_evm[slide_evm_index];
6258 priv->stats.slide_evm_total -= last_evm;
6261 priv->stats.slide_evm_total += pprevious_stats->SignalQuality;
6263 priv->stats.slide_evm[slide_evm_index++] = pprevious_stats->SignalQuality;
6264 if(slide_evm_index >= PHY_RSSI_SLID_WIN_MAX)
6265 slide_evm_index = 0;
6267 // <1> Showed on UI for user, in percentage.
6268 tmp_val = priv->stats.slide_evm_total/slide_evm_statistics;
6269 priv->stats.signal_quality = tmp_val;
6270 //cosa add 10/11/2007, Showed on UI for user in Windows Vista, for Link quality.
6271 priv->stats.last_signal_strength_inpercent = tmp_val;
6274 // <2> Showed on UI for engineering
6275 if(pprevious_stats->bPacketToSelf || pprevious_stats->bPacketBeacon || pprevious_stats->bToSelfBA)
6277 for(nspatial_stream = 0; nspatial_stream<2 ; nspatial_stream++) // 2 spatial stream
6279 if(pprevious_stats->RxMIMOSignalQuality[nspatial_stream] != -1)
6281 if(priv->stats.rx_evm_percentage[nspatial_stream] == 0) // initialize
6283 priv->stats.rx_evm_percentage[nspatial_stream] = pprevious_stats->RxMIMOSignalQuality[nspatial_stream];
6285 priv->stats.rx_evm_percentage[nspatial_stream] =
6286 ( (priv->stats.rx_evm_percentage[nspatial_stream]* (Rx_Smooth_Factor-1)) +
6287 (pprevious_stats->RxMIMOSignalQuality[nspatial_stream]* 1)) / (Rx_Smooth_Factor);
6296 /*-----------------------------------------------------------------------------
6297 * Function: rtl819x_query_rxpwrpercentage()
6299 * Overview:
6301 * Input: char antpower
6303 * Output: NONE
6305 * Return: 0-100 percentage
6307 * Revised History:
6308 * When Who Remark
6309 * 05/26/2008 amy Create Version 0 porting from windows code.
6311 *---------------------------------------------------------------------------*/
6312 static u8 rtl819x_query_rxpwrpercentage(
6313 char antpower
6316 if ((antpower <= -100) || (antpower >= 20))
6318 return 0;
6320 else if (antpower >= 0)
6322 return 100;
6324 else
6326 return (100+antpower);
6329 } /* QueryRxPwrPercentage */
6331 static u8
6332 rtl819x_evm_dbtopercentage(
6333 char value
6336 char ret_val;
6338 ret_val = value;
6340 if(ret_val >= 0)
6341 ret_val = 0;
6342 if(ret_val <= -33)
6343 ret_val = -33;
6344 ret_val = 0 - ret_val;
6345 ret_val*=3;
6346 if(ret_val == 99)
6347 ret_val = 100;
6348 return(ret_val);
6351 // Description:
6352 // We want good-looking for signal strength/quality
6353 // 2007/7/19 01:09, by cosa.
6355 long
6356 rtl819x_signal_scale_mapping(
6357 long currsig
6360 long retsig;
6362 // Step 1. Scale mapping.
6363 if(currsig >= 61 && currsig <= 100)
6365 retsig = 90 + ((currsig - 60) / 4);
6367 else if(currsig >= 41 && currsig <= 60)
6369 retsig = 78 + ((currsig - 40) / 2);
6371 else if(currsig >= 31 && currsig <= 40)
6373 retsig = 66 + (currsig - 30);
6375 else if(currsig >= 21 && currsig <= 30)
6377 retsig = 54 + (currsig - 20);
6379 else if(currsig >= 5 && currsig <= 20)
6381 retsig = 42 + (((currsig - 5) * 2) / 3);
6383 else if(currsig == 4)
6385 retsig = 36;
6387 else if(currsig == 3)
6389 retsig = 27;
6391 else if(currsig == 2)
6393 retsig = 18;
6395 else if(currsig == 1)
6397 retsig = 9;
6399 else
6401 retsig = currsig;
6404 return retsig;
6407 /*-----------------------------------------------------------------------------
6408 * Function: QueryRxPhyStatus8192S()
6410 * Overview:
6412 * Input: NONE
6414 * Output: NONE
6416 * Return: NONE
6418 * Revised History:
6419 * When Who Remark
6420 * 06/01/2007 MHC Create Version 0.
6421 * 06/05/2007 MHC Accordign to HW's new data sheet, we add CCK and OFDM
6422 * descriptor definition.
6423 * 07/04/2007 MHC According to Jerry and Bryant's document. We read
6424 * ir_isolation and ext_lna for RF's init value and use
6425 * to compensate RSSI after receiving packets.
6426 * 09/10/2008 MHC Modify name and PHY status field for 92SE.
6427 * 09/19/2008 MHC Add CCK/OFDM SS/SQ for 92S series.
6429 *---------------------------------------------------------------------------*/
6430 static void rtl8192SU_query_rxphystatus(
6431 struct r8192_priv * priv,
6432 struct ieee80211_rx_stats * pstats,
6433 rx_desc_819x_usb *pDesc,
6434 rx_drvinfo_819x_usb * pdrvinfo,
6435 struct ieee80211_rx_stats * precord_stats,
6436 bool bpacket_match_bssid,
6437 bool bpacket_toself,
6438 bool bPacketBeacon,
6439 bool bToSelfBA
6442 //PRT_RFD_STATUS pRtRfdStatus = &(pRfd->Status);
6443 //PHY_STS_CCK_8192S_T *pCck_buf;
6444 phy_sts_cck_819xusb_t * pcck_buf;
6445 phy_ofdm_rx_status_rxsc_sgien_exintfflag* prxsc;
6446 //u8 *prxpkt;
6447 //u8 i, max_spatial_stream, tmp_rxsnr, tmp_rxevm, rxsc_sgien_exflg;
6448 u8 i, max_spatial_stream, rxsc_sgien_exflg;
6449 char rx_pwr[4], rx_pwr_all=0;
6450 //long rx_avg_pwr = 0;
6451 //char rx_snrX, rx_evmX;
6452 u8 evm, pwdb_all;
6453 u32 RSSI, total_rssi=0;//, total_evm=0;
6454 // long signal_strength_index = 0;
6455 u8 is_cck_rate=0;
6456 u8 rf_rx_num = 0;
6460 priv->stats.numqry_phystatus++;
6462 is_cck_rate = rx_hal_is_cck_rate(pDesc);
6464 // Record it for next packet processing
6465 memset(precord_stats, 0, sizeof(struct ieee80211_rx_stats));
6466 pstats->bPacketMatchBSSID = precord_stats->bPacketMatchBSSID = bpacket_match_bssid;
6467 pstats->bPacketToSelf = precord_stats->bPacketToSelf = bpacket_toself;
6468 pstats->bIsCCK = precord_stats->bIsCCK = is_cck_rate;//RX_HAL_IS_CCK_RATE(pDrvInfo);
6469 pstats->bPacketBeacon = precord_stats->bPacketBeacon = bPacketBeacon;
6470 pstats->bToSelfBA = precord_stats->bToSelfBA = bToSelfBA;
6473 pstats->RxMIMOSignalQuality[0] = -1;
6474 pstats->RxMIMOSignalQuality[1] = -1;
6475 precord_stats->RxMIMOSignalQuality[0] = -1;
6476 precord_stats->RxMIMOSignalQuality[1] = -1;
6478 if(is_cck_rate)
6480 u8 report;//, tmp_pwdb;
6481 //char cck_adc_pwdb[4];
6483 // CCK Driver info Structure is not the same as OFDM packet.
6484 pcck_buf = (phy_sts_cck_819xusb_t *)pdrvinfo;
6487 // (1)Hardware does not provide RSSI for CCK
6491 // (2)PWDB, Average PWDB cacluated by hardware (for rate adaptive)
6494 priv->stats.numqry_phystatusCCK++;
6496 if(!priv->bCckHighPower)
6498 report = pcck_buf->cck_agc_rpt & 0xc0;
6499 report = report>>6;
6500 switch(report)
6502 //Fixed by Jacken from Bryant 2008-03-20
6503 //Original value is -38 , -26 , -14 , -2
6504 //Fixed value is -35 , -23 , -11 , 6
6505 case 0x3:
6506 rx_pwr_all = -35 - (pcck_buf->cck_agc_rpt & 0x3e);
6507 break;
6508 case 0x2:
6509 rx_pwr_all = -23 - (pcck_buf->cck_agc_rpt & 0x3e);
6510 break;
6511 case 0x1:
6512 rx_pwr_all = -11 - (pcck_buf->cck_agc_rpt & 0x3e);
6513 break;
6514 case 0x0:
6515 rx_pwr_all = 8 - (pcck_buf->cck_agc_rpt & 0x3e);//6->8
6516 break;
6519 else
6521 report = pdrvinfo->cfosho[0] & 0x60;
6522 report = report>>5;
6523 switch(report)
6525 case 0x3:
6526 rx_pwr_all = -35 - ((pcck_buf->cck_agc_rpt & 0x1f)<<1) ;
6527 break;
6528 case 0x2:
6529 rx_pwr_all = -23 - ((pcck_buf->cck_agc_rpt & 0x1f)<<1);
6530 break;
6531 case 0x1:
6532 rx_pwr_all = -11 - ((pcck_buf->cck_agc_rpt & 0x1f)<<1) ;
6533 break;
6534 case 0x0:
6535 rx_pwr_all = -8 - ((pcck_buf->cck_agc_rpt & 0x1f)<<1) ;//6->-8
6536 break;
6540 pwdb_all = rtl819x_query_rxpwrpercentage(rx_pwr_all);//check it
6541 pstats->RxPWDBAll = precord_stats->RxPWDBAll = pwdb_all;
6542 //pstats->RecvSignalPower = pwdb_all;
6543 pstats->RecvSignalPower = rx_pwr_all;
6546 // (3) Get Signal Quality (EVM)
6548 //if(bpacket_match_bssid)
6550 u8 sq;
6552 if(pstats->RxPWDBAll > 40)
6554 sq = 100;
6555 }else
6557 sq = pcck_buf->sq_rpt;
6559 if(pcck_buf->sq_rpt > 64)
6560 sq = 0;
6561 else if (pcck_buf->sq_rpt < 20)
6562 sq = 100;
6563 else
6564 sq = ((64-sq) * 100) / 44;
6566 pstats->SignalQuality = precord_stats->SignalQuality = sq;
6567 pstats->RxMIMOSignalQuality[0] = precord_stats->RxMIMOSignalQuality[0] = sq;
6568 pstats->RxMIMOSignalQuality[1] = precord_stats->RxMIMOSignalQuality[1] = -1;
6571 else
6573 priv->stats.numqry_phystatusHT++;
6575 // 2008/09/19 MH For 92S debug, RX RF path always enable!!
6576 priv->brfpath_rxenable[0] = priv->brfpath_rxenable[1] = TRUE;
6579 // (1)Get RSSI for HT rate
6581 //for(i=RF90_PATH_A; i<priv->NumTotalRFPath; i++)
6582 for(i=RF90_PATH_A; i<RF90_PATH_MAX; i++)
6584 // 2008/01/30 MH we will judge RF RX path now.
6585 if (priv->brfpath_rxenable[i])
6586 rf_rx_num++;
6587 //else
6588 // continue;
6590 //if (!rtl8192_phy_CheckIsLegalRFPath(priv->ieee80211->dev, i))
6591 // continue;
6593 //Fixed by Jacken from Bryant 2008-03-20
6594 //Original value is 106
6595 //rx_pwr[i] = ((pofdm_buf->trsw_gain_X[i]&0x3F)*2) - 106;
6596 rx_pwr[i] = ((pdrvinfo->gain_trsw[i]&0x3F)*2) - 110;
6598 /* Translate DBM to percentage. */
6599 RSSI = rtl819x_query_rxpwrpercentage(rx_pwr[i]); //check ok
6600 total_rssi += RSSI;
6601 RT_TRACE(COMP_RF, "RF-%d RXPWR=%x RSSI=%d\n", i, rx_pwr[i], RSSI);
6603 //Get Rx snr value in DB
6604 //tmp_rxsnr = pofdm_buf->rxsnr_X[i];
6605 //rx_snrX = (char)(tmp_rxsnr);
6606 //rx_snrX /= 2;
6607 //priv->stats.rxSNRdB[i] = (long)rx_snrX;
6608 priv->stats.rxSNRdB[i] = (long)(pdrvinfo->rxsnr[i]/2);
6610 /* Translate DBM to percentage. */
6611 //RSSI = rtl819x_query_rxpwrpercentage(rx_pwr[i]);
6612 //total_rssi += RSSI;
6614 /* Record Signal Strength for next packet */
6615 //if(bpacket_match_bssid)
6617 pstats->RxMIMOSignalStrength[i] =(u8) RSSI;
6618 precord_stats->RxMIMOSignalStrength[i] =(u8) RSSI;
6624 // (2)PWDB, Average PWDB cacluated by hardware (for rate adaptive)
6626 //Fixed by Jacken from Bryant 2008-03-20
6627 //Original value is 106
6628 //rx_pwr_all = (((pofdm_buf->pwdb_all ) >> 1 )& 0x7f) -106;
6629 rx_pwr_all = (((pdrvinfo->pwdb_all ) >> 1 )& 0x7f) -106;
6630 pwdb_all = rtl819x_query_rxpwrpercentage(rx_pwr_all);
6632 pstats->RxPWDBAll = precord_stats->RxPWDBAll = pwdb_all;
6633 pstats->RxPower = precord_stats->RxPower = rx_pwr_all;
6634 pstats->RecvSignalPower = rx_pwr_all;
6637 // (3)EVM of HT rate
6639 //if(pdrvinfo->RxHT && pdrvinfo->RxRate>=DESC90_RATEMCS8 &&
6640 // pdrvinfo->RxRate<=DESC90_RATEMCS15)
6641 if(pDesc->RxHT && pDesc->RxMCS>=DESC92S_RATEMCS8 &&
6642 pDesc->RxMCS<=DESC92S_RATEMCS15)
6643 max_spatial_stream = 2; //both spatial stream make sense
6644 else
6645 max_spatial_stream = 1; //only spatial stream 1 makes sense
6647 for(i=0; i<max_spatial_stream; i++)
6649 //tmp_rxevm = pofdm_buf->rxevm_X[i];
6650 //rx_evmX = (char)(tmp_rxevm);
6652 // Do not use shift operation like "rx_evmX >>= 1" because the compilor of free build environment
6653 // fill most significant bit to "zero" when doing shifting operation which may change a negative
6654 // value to positive one, then the dbm value (which is supposed to be negative) is not correct anymore.
6655 //rx_evmX /= 2; //dbm
6657 //evm = rtl819x_evm_dbtopercentage(rx_evmX);
6658 evm = rtl819x_evm_dbtopercentage( (pdrvinfo->rxevm[i] /*/ 2*/)); //dbm
6659 RT_TRACE(COMP_RF, "RXRATE=%x RXEVM=%x EVM=%s%d\n", pDesc->RxMCS, pdrvinfo->rxevm[i], "%", evm);
6661 //if(bpacket_match_bssid)
6663 if(i==0) // Fill value in RFD, Get the first spatial stream only
6664 pstats->SignalQuality = precord_stats->SignalQuality = (u8)(evm & 0xff);
6665 pstats->RxMIMOSignalQuality[i] = precord_stats->RxMIMOSignalQuality[i] = (u8)(evm & 0xff);
6670 /* record rx statistics for debug */
6671 //rxsc_sgien_exflg = pofdm_buf->rxsc_sgien_exflg;
6672 prxsc = (phy_ofdm_rx_status_rxsc_sgien_exintfflag *)&rxsc_sgien_exflg;
6673 //if(pdrvinfo->BW) //40M channel
6674 if(pDesc->BW) //40M channel
6675 priv->stats.received_bwtype[1+pdrvinfo->rxsc]++;
6676 else //20M channel
6677 priv->stats.received_bwtype[0]++;
6680 //UI BSS List signal strength(in percentage), make it good looking, from 0~100.
6681 //It is assigned to the BSS List in GetValueFromBeaconOrProbeRsp().
6682 if(is_cck_rate)
6684 pstats->SignalStrength = precord_stats->SignalStrength = (u8)(rtl819x_signal_scale_mapping((long)pwdb_all));//PWDB_ALL;//check ok
6687 else
6689 //pRfd->Status.SignalStrength = pRecordRfd->Status.SignalStrength = (u8)(SignalScaleMapping(total_rssi/=RF90_PATH_MAX));//(u8)(total_rssi/=RF90_PATH_MAX);
6690 // We can judge RX path number now.
6691 if (rf_rx_num != 0)
6692 pstats->SignalStrength = precord_stats->SignalStrength = (u8)(rtl819x_signal_scale_mapping((long)(total_rssi/=rf_rx_num)));
6694 }/* QueryRxPhyStatus8192S */
6696 void
6697 rtl8192_record_rxdesc_forlateruse(
6698 struct ieee80211_rx_stats * psrc_stats,
6699 struct ieee80211_rx_stats * ptarget_stats
6702 ptarget_stats->bIsAMPDU = psrc_stats->bIsAMPDU;
6703 ptarget_stats->bFirstMPDU = psrc_stats->bFirstMPDU;
6704 ptarget_stats->Seq_Num = psrc_stats->Seq_Num;
6707 static void rtl8192SU_query_rxphystatus(
6708 struct r8192_priv * priv,
6709 struct ieee80211_rx_stats * pstats,
6710 rx_desc_819x_usb *pDesc,
6711 rx_drvinfo_819x_usb * pdrvinfo,
6712 struct ieee80211_rx_stats * precord_stats,
6713 bool bpacket_match_bssid,
6714 bool bpacket_toself,
6715 bool bPacketBeacon,
6716 bool bToSelfBA
6718 void rtl8192SU_TranslateRxSignalStuff(struct sk_buff *skb,
6719 struct ieee80211_rx_stats * pstats,
6720 rx_desc_819x_usb *pDesc,
6721 rx_drvinfo_819x_usb *pdrvinfo)
6723 // TODO: We must only check packet for current MAC address. Not finish
6724 rtl8192_rx_info *info = (struct rtl8192_rx_info *)skb->cb;
6725 struct net_device *dev=info->dev;
6726 struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
6727 bool bpacket_match_bssid, bpacket_toself;
6728 bool bPacketBeacon=FALSE, bToSelfBA=FALSE;
6729 static struct ieee80211_rx_stats previous_stats;
6730 struct ieee80211_hdr_3addr *hdr;//by amy
6731 u16 fc,type;
6733 // Get Signal Quality for only RX data queue (but not command queue)
6735 u8* tmp_buf;
6736 //u16 tmp_buf_len = 0;
6737 u8 *praddr;
6739 /* Get MAC frame start address. */
6740 tmp_buf = (u8*)skb->data;// + get_rxpacket_shiftbytes_819xusb(pstats);
6742 hdr = (struct ieee80211_hdr_3addr *)tmp_buf;
6743 fc = le16_to_cpu(hdr->frame_control);
6744 type = WLAN_FC_GET_TYPE(fc);
6745 praddr = hdr->addr1;
6747 /* Check if the received packet is acceptabe. */
6748 bpacket_match_bssid = ((IEEE80211_FTYPE_CTL != type) &&
6749 (eqMacAddr(priv->ieee80211->current_network.bssid, (fc & IEEE80211_FCTL_TODS)? hdr->addr1 : (fc & IEEE80211_FCTL_FROMDS )? hdr->addr2 : hdr->addr3))
6750 && (!pstats->bHwError) && (!pstats->bCRC)&& (!pstats->bICV));
6751 bpacket_toself = bpacket_match_bssid & (eqMacAddr(praddr, priv->ieee80211->dev->dev_addr));
6753 #if 1//cosa
6754 if(WLAN_FC_GET_FRAMETYPE(fc)== IEEE80211_STYPE_BEACON)
6756 bPacketBeacon = true;
6757 //DbgPrint("Beacon 2, MatchBSSID = %d, ToSelf = %d \n", bPacketMatchBSSID, bPacketToSelf);
6759 if(WLAN_FC_GET_FRAMETYPE(fc) == IEEE80211_STYPE_BLOCKACK)
6761 if((eqMacAddr(praddr,dev->dev_addr)))
6762 bToSelfBA = true;
6763 //DbgPrint("BlockAck, MatchBSSID = %d, ToSelf = %d \n", bPacketMatchBSSID, bPacketToSelf);
6766 #endif
6769 if(bpacket_match_bssid)
6771 priv->stats.numpacket_matchbssid++;
6773 if(bpacket_toself){
6774 priv->stats.numpacket_toself++;
6777 // Process PHY information for previous packet (RSSI/PWDB/EVM)
6779 // Because phy information is contained in the last packet of AMPDU only, so driver
6780 // should process phy information of previous packet
6781 rtl8192_process_phyinfo(priv, tmp_buf, &previous_stats, pstats);
6782 rtl8192SU_query_rxphystatus(priv, pstats, pDesc, pdrvinfo, &previous_stats, bpacket_match_bssid,bpacket_toself,bPacketBeacon,bToSelfBA);
6783 rtl8192_record_rxdesc_forlateruse(pstats, &previous_stats);
6788 * Function: UpdateReceivedRateHistogramStatistics
6789 * Overview: Recored down the received data rate
6791 * Input:
6792 * struct net_device *dev
6793 * struct ieee80211_rx_stats *stats
6795 * Output:
6797 * (priv->stats.ReceivedRateHistogram[] is updated)
6798 * Return:
6799 * None
6801 void
6802 UpdateReceivedRateHistogramStatistics8190(
6803 struct net_device *dev,
6804 struct ieee80211_rx_stats *stats
6807 struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
6808 u32 rcvType=1; //0: Total, 1:OK, 2:CRC, 3:ICV
6809 u32 rateIndex;
6810 u32 preamble_guardinterval; //1: short preamble/GI, 0: long preamble/GI
6813 if(stats->bCRC)
6814 rcvType = 2;
6815 else if(stats->bICV)
6816 rcvType = 3;
6818 if(stats->bShortPreamble)
6819 preamble_guardinterval = 1;// short
6820 else
6821 preamble_guardinterval = 0;// long
6823 switch(stats->rate)
6826 // CCK rate
6828 case MGN_1M: rateIndex = 0; break;
6829 case MGN_2M: rateIndex = 1; break;
6830 case MGN_5_5M: rateIndex = 2; break;
6831 case MGN_11M: rateIndex = 3; break;
6833 // Legacy OFDM rate
6835 case MGN_6M: rateIndex = 4; break;
6836 case MGN_9M: rateIndex = 5; break;
6837 case MGN_12M: rateIndex = 6; break;
6838 case MGN_18M: rateIndex = 7; break;
6839 case MGN_24M: rateIndex = 8; break;
6840 case MGN_36M: rateIndex = 9; break;
6841 case MGN_48M: rateIndex = 10; break;
6842 case MGN_54M: rateIndex = 11; break;
6844 // 11n High throughput rate
6846 case MGN_MCS0: rateIndex = 12; break;
6847 case MGN_MCS1: rateIndex = 13; break;
6848 case MGN_MCS2: rateIndex = 14; break;
6849 case MGN_MCS3: rateIndex = 15; break;
6850 case MGN_MCS4: rateIndex = 16; break;
6851 case MGN_MCS5: rateIndex = 17; break;
6852 case MGN_MCS6: rateIndex = 18; break;
6853 case MGN_MCS7: rateIndex = 19; break;
6854 case MGN_MCS8: rateIndex = 20; break;
6855 case MGN_MCS9: rateIndex = 21; break;
6856 case MGN_MCS10: rateIndex = 22; break;
6857 case MGN_MCS11: rateIndex = 23; break;
6858 case MGN_MCS12: rateIndex = 24; break;
6859 case MGN_MCS13: rateIndex = 25; break;
6860 case MGN_MCS14: rateIndex = 26; break;
6861 case MGN_MCS15: rateIndex = 27; break;
6862 default: rateIndex = 28; break;
6864 priv->stats.received_preamble_GI[preamble_guardinterval][rateIndex]++;
6865 priv->stats.received_rate_histogram[0][rateIndex]++; //total
6866 priv->stats.received_rate_histogram[rcvType][rateIndex]++;
6869 void rtl8192SU_query_rxdesc_status(struct sk_buff *skb, struct ieee80211_rx_stats *stats, bool bIsRxAggrSubframe)
6871 rtl8192_rx_info *info = (struct rtl8192_rx_info *)skb->cb;
6872 struct net_device *dev=info->dev;
6873 struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
6874 //rx_desc_819x_usb *desc = (rx_desc_819x_usb *)skb->data;
6875 rx_drvinfo_819x_usb *driver_info = NULL;
6877 //PRT_RFD_STATUS pRtRfdStatus = &pRfd->Status;
6878 //PHAL_DATA_8192SUSB pHalData = GET_HAL_DATA(Adapter);
6879 //pu1Byte pDesc = (pu1Byte)pDescIn;
6880 //PRX_DRIVER_INFO_8192S pDrvInfo;
6882 rx_desc_819x_usb *desc = (rx_desc_819x_usb *)skb->data;
6884 if(0)
6886 int m = 0;
6887 printk("========================");
6888 for(m=0; m<skb->len; m++){
6889 if((m%32) == 0)
6890 printk("\n");
6891 printk("%2x ",((u8*)skb->data)[m]);
6893 printk("\n========================\n");
6899 //Get Rx Descriptor Raw Information
6901 stats->Length = desc->Length ;
6902 stats->RxDrvInfoSize = desc->RxDrvInfoSize*RX_DRV_INFO_SIZE_UNIT;
6903 stats->RxBufShift = (desc->Shift)&0x03;
6904 stats->bICV = desc->ICV;
6905 stats->bCRC = desc->CRC32;
6906 stats->bHwError = stats->bCRC|stats->bICV;
6907 stats->Decrypted = !desc->SWDec;//RTL8190 set this bit to indicate that Hw does not decrypt packet
6908 stats->bIsAMPDU = (desc->AMSDU==1);
6909 stats->bFirstMPDU = (desc->PAGGR==1) && (desc->FAGGR==1);
6910 stats->bShortPreamble = desc->SPLCP;
6911 stats->RxIs40MHzPacket = (desc->BW==1);
6912 stats->TimeStampLow = desc->TSFL;
6914 if((desc->FAGGR==1) || (desc->PAGGR==1))
6915 {// Rx A-MPDU
6916 RT_TRACE(COMP_RXDESC, "FirstAGGR = %d, PartAggr = %d\n", desc->FAGGR, desc->PAGGR);
6918 //YJ,test,090310
6919 if(stats->bHwError)
6921 if(stats->bICV)
6922 printk("%s: Receive ICV error!!!!!!!!!!!!!!!!!!!!!!\n", __FUNCTION__);
6923 if(stats->bCRC)
6924 printk("%s: Receive CRC error!!!!!!!!!!!!!!!!!!!!!!\n", __FUNCTION__);
6927 if(IS_UNDER_11N_AES_MODE(priv->ieee80211))
6929 // Always received ICV error packets in AES mode.
6930 // This fixed HW later MIC write bug.
6931 if(stats->bICV && !stats->bCRC)
6933 stats->bICV = FALSE;
6934 stats->bHwError = FALSE;
6938 // Transform HwRate to MRate
6939 if(!stats->bHwError)
6940 //stats->DataRate = HwRateToMRate(
6941 // (BOOLEAN)GET_RX_DESC_RXHT(pDesc),
6942 // (u1Byte)GET_RX_DESC_RXMCS(pDesc),
6943 // (BOOLEAN)GET_RX_DESC_PAGGR(pDesc));
6944 stats->rate = rtl8192SU_HwRateToMRate(desc->RxHT, desc->RxMCS, desc->PAGGR);
6945 else
6946 stats->rate = MGN_1M;
6949 // Collect Rx rate/AMPDU/TSFL
6951 //UpdateRxdRateHistogramStatistics8192S(Adapter, pRfd);
6952 //UpdateRxAMPDUHistogramStatistics8192S(Adapter, pRfd);
6953 //UpdateRxPktTimeStamp8192S(Adapter, pRfd);
6954 UpdateReceivedRateHistogramStatistics8190(dev, stats);
6955 //UpdateRxAMPDUHistogramStatistics8192S(dev, stats); //FIXLZM
6956 UpdateRxPktTimeStamp8190(dev, stats);
6959 // Get PHY Status and RSVD parts.
6960 // <Roger_Notes> It only appears on last aggregated packet.
6962 if (desc->PHYStatus)
6964 //driver_info = (rx_drvinfo_819x_usb *)(skb->data + RX_DESC_SIZE + stats->RxBufShift);
6965 driver_info = (rx_drvinfo_819x_usb *)(skb->data + sizeof(rx_desc_819x_usb) + \
6966 stats->RxBufShift);
6967 if(0)
6969 int m = 0;
6970 printk("========================\n");
6971 printk("RX_DESC_SIZE:%d, RxBufShift:%d, RxDrvInfoSize:%d\n",
6972 RX_DESC_SIZE, stats->RxBufShift, stats->RxDrvInfoSize);
6973 for(m=0; m<32; m++){
6974 printk("%2x ",((u8*)driver_info)[m]);
6976 printk("\n========================\n");
6982 //YJ,add,090107
6983 skb_pull(skb, sizeof(rx_desc_819x_usb));
6984 //YJ,add,090107,end
6987 // Get Total offset of MPDU Frame Body
6989 if((stats->RxBufShift + stats->RxDrvInfoSize) > 0)
6991 stats->bShift = 1;
6992 //YJ,add,090107
6993 skb_pull(skb, stats->RxBufShift + stats->RxDrvInfoSize);
6994 //YJ,add,090107,end
6998 // Get PHY Status and RSVD parts.
6999 // <Roger_Notes> It only appears on last aggregated packet.
7001 if (desc->PHYStatus)
7003 rtl8192SU_TranslateRxSignalStuff(skb, stats, desc, driver_info);
7008 // Description:
7009 // The strarting address of wireless lan header will shift 1 or 2 or 3 or "more" bytes for the following reason :
7010 // (1) QoS control : shift 2 bytes
7011 // (2) Mesh Network : shift 1 or 3 bytes
7012 // (3) RxDriverInfo occupies the front parts of Rx Packets buffer(shift units is in 8Bytes)
7014 // It is because Lextra CPU used by 8186 or 865x series assert exception if the statrting address
7015 // of IP header is not double word alignment.
7016 // This features is supported in 818xb and 8190 only, but not 818x.
7018 // parameter: PRT_RFD, Pointer of Reeceive frame descriptor which is initialized according to
7019 // Rx Descriptor
7020 // return value: unsigned int, number of total shifted bytes
7022 // Notes: 2008/06/28, created by Roger
7024 u32 GetRxPacketShiftBytes8192SU(struct ieee80211_rx_stats *Status, bool bIsRxAggrSubframe)
7026 //PRT_RFD_STATUS pRtRfdStatus = &pRfd->Status;
7028 return (sizeof(rx_desc_819x_usb) + Status->RxDrvInfoSize + Status->RxBufShift);
7031 void rtl8192SU_rx_nomal(struct sk_buff* skb)
7033 rtl8192_rx_info *info = (struct rtl8192_rx_info *)skb->cb;
7034 struct net_device *dev=info->dev;
7035 struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
7036 struct ieee80211_rx_stats stats = {
7037 .signal = 0,
7038 .noise = -98,
7039 .rate = 0,
7040 // .mac_time = jiffies,
7041 .freq = IEEE80211_24GHZ_BAND,
7043 u32 rx_pkt_len = 0;
7044 struct ieee80211_hdr_1addr *ieee80211_hdr = NULL;
7045 bool unicast_packet = false;
7047 //printk("**********skb->len = %d\n", skb->len);
7048 /* 20 is for ps-poll */
7049 if((skb->len >=(20 + sizeof(rx_desc_819x_usb))) && (skb->len < RX_URB_SIZE)) {
7051 /* first packet should not contain Rx aggregation header */
7052 rtl8192SU_query_rxdesc_status(skb, &stats, false);
7053 /* TODO */
7055 /* hardware related info */
7056 priv->stats.rxoktotal++; //YJ,test,090108
7058 /* Process the MPDU recevied */
7059 skb_trim(skb, skb->len - 4/*sCrcLng*/);//FIXLZM
7061 rx_pkt_len = skb->len;
7062 ieee80211_hdr = (struct ieee80211_hdr_1addr *)skb->data;
7063 unicast_packet = false;
7064 if(is_broadcast_ether_addr(ieee80211_hdr->addr1)) {
7065 //TODO
7066 }else if(is_multicast_ether_addr(ieee80211_hdr->addr1)){
7067 //TODO
7068 }else {
7069 /* unicast packet */
7070 unicast_packet = true;
7073 if(!ieee80211_rtl_rx(priv->ieee80211,skb, &stats)) {
7074 dev_kfree_skb_any(skb);
7075 } else {
7076 // priv->stats.rxoktotal++; //YJ,test,090108
7077 if(unicast_packet) {
7078 priv->stats.rxbytesunicast += rx_pkt_len;
7082 //up is firs pkt, follow is next and next
7084 else
7086 priv->stats.rxurberr++;
7087 printk("actual_length:%d\n", skb->len);
7088 dev_kfree_skb_any(skb);
7093 void
7094 rtl819xusb_process_received_packet(
7095 struct net_device *dev,
7096 struct ieee80211_rx_stats *pstats
7099 // bool bfreerfd=false, bqueued=false;
7100 u8* frame;
7101 u16 frame_len=0;
7102 struct r8192_priv *priv = ieee80211_priv(dev);
7103 // u8 index = 0;
7104 // u8 TID = 0;
7105 //u16 seqnum = 0;
7106 //PRX_TS_RECORD pts = NULL;
7108 // Get shifted bytes of Starting address of 802.11 header. 2006.09.28, by Emily
7109 //porting by amy 080508
7110 pstats->virtual_address += get_rxpacket_shiftbytes_819xusb(pstats);
7111 frame = pstats->virtual_address;
7112 frame_len = pstats->packetlength;
7113 #ifdef TODO // by amy about HCT
7114 if(!Adapter->bInHctTest)
7115 CountRxErrStatistics(Adapter, pRfd);
7116 #endif
7118 #ifdef ENABLE_PS //by amy for adding ps function in future
7119 RT_RF_POWER_STATE rtState;
7120 // When RF is off, we should not count the packet for hw/sw synchronize
7121 // reason, ie. there may be a duration while sw switch is changed and hw
7122 // switch is being changed. 2006.12.04, by shien chang.
7123 Adapter->HalFunc.GetHwRegHandler(Adapter, HW_VAR_RF_STATE, (u8* )(&rtState));
7124 if (rtState == eRfOff)
7126 return;
7128 #endif
7129 priv->stats.rxframgment++;
7132 #ifdef TODO
7133 RmMonitorSignalStrength(Adapter, pRfd);
7134 #endif
7135 /* 2007/01/16 MH Add RX command packet handle here. */
7136 /* 2007/03/01 MH We have to release RFD and return if rx pkt is cmd pkt. */
7137 if (rtl819xusb_rx_command_packet(dev, pstats))
7139 return;
7142 #ifdef SW_CRC_CHECK
7143 SwCrcCheck();
7144 #endif
7149 void query_rx_cmdpkt_desc_status(struct sk_buff *skb, struct ieee80211_rx_stats *stats)
7151 // rtl8192_rx_info *info = (struct rtl8192_rx_info *)skb->cb;
7152 // struct net_device *dev=info->dev;
7153 // struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
7154 rx_desc_819x_usb *desc = (rx_desc_819x_usb *)skb->data;
7155 // rx_drvinfo_819x_usb *driver_info;
7158 //Get Rx Descriptor Information
7160 stats->virtual_address = (u8*)skb->data;
7161 stats->Length = desc->Length;
7162 stats->RxDrvInfoSize = 0;
7163 stats->RxBufShift = 0;
7164 stats->packetlength = stats->Length-scrclng;
7165 stats->fraglength = stats->packetlength;
7166 stats->fragoffset = 0;
7167 stats->ntotalfrag = 1;
7170 void rtl8192SU_rx_cmd(struct sk_buff *skb)
7172 struct rtl8192_rx_info *info = (struct rtl8192_rx_info *)skb->cb;
7173 struct net_device *dev = info->dev;
7175 /* TODO */
7176 struct ieee80211_rx_stats stats = {
7177 .signal = 0,
7178 .noise = -98,
7179 .rate = 0,
7180 // .mac_time = jiffies,
7181 .freq = IEEE80211_24GHZ_BAND,
7185 // Check buffer length to determine if this is a valid MPDU.
7187 if( (skb->len >= sizeof(rx_desc_819x_usb)) && (skb->len <= RX_URB_SIZE) )//&&
7188 //(pHalData->SwChnlInProgress == FALSE))
7191 // Collection information in Rx descriptor.
7193 query_rx_cmdpkt_desc_status(skb,&stats);
7194 // this is to be done by amy 080508 prfd->queue_id = 1;
7197 // Process the MPDU recevied.
7199 rtl819xusb_process_received_packet(dev,&stats);
7201 dev_kfree_skb_any(skb);
7203 else
7205 //RTInsertTailListWithCnt(&pAdapter->RfdIdleQueue, &pRfd->List, &pAdapter->NumIdleRfd);
7206 //RT_ASSERT(pAdapter->NumIdleRfd <= pAdapter->NumRfd, ("HalUsbInCommandComplete8192SUsb(): Adapter->NumIdleRfd(%d)\n", pAdapter->NumIdleRfd));
7207 //RT_TRACE(COMP_RECV, DBG_LOUD, ("HalUsbInCommandComplete8192SUsb(): NOT enough Resources!! BufLenUsed(%d), NumIdleRfd(%d)\n",
7208 //pContext->BufLenUsed, pAdapter->NumIdleRfd));
7212 // Reuse USB_IN_CONTEXT since we had finished processing the
7213 // buffer in USB_IN_CONTEXT.
7215 //HalUsbReturnInContext(pAdapter, pContext);
7218 // Issue another bulk IN transfer.
7220 //HalUsbInMpdu(pAdapter, PipeIndex);
7222 RT_TRACE(COMP_RECV, "<--- HalUsbInCommandComplete8192SUsb()\n");
7226 void rtl8192_irq_rx_tasklet(struct r8192_priv *priv)
7228 struct sk_buff *skb;
7229 struct rtl8192_rx_info *info;
7231 while (NULL != (skb = skb_dequeue(&priv->skb_queue))) {
7232 info = (struct rtl8192_rx_info *)skb->cb;
7233 switch (info->out_pipe) {
7234 /* Nomal packet pipe */
7235 case 3:
7236 //RT_TRACE(COMP_RECV, "normal in-pipe index(%d)\n",info->out_pipe);
7237 priv->IrpPendingCount--;
7238 priv->ops->rtl819x_rx_nomal(skb);
7239 break;
7241 /* Command packet pipe */
7242 case 9:
7243 RT_TRACE(COMP_RECV, "command in-pipe index(%d)\n",\
7244 info->out_pipe);
7245 priv->ops->rtl819x_rx_cmd(skb);
7246 break;
7248 default: /* should never get here! */
7249 RT_TRACE(COMP_ERR, "Unknown in-pipe index(%d)\n",\
7250 info->out_pipe);
7251 dev_kfree_skb(skb);
7252 break;
7260 /****************************************************************************
7261 ---------------------------- USB_STUFF---------------------------
7262 *****************************************************************************/
7263 //LZM Merge from windows HalUsbSetQueuePipeMapping8192SUsb 090319
7264 static void HalUsbSetQueuePipeMapping8192SUsb(struct usb_interface *intf, struct net_device *dev)
7266 struct r8192_priv *priv = ieee80211_priv(dev);
7267 struct usb_host_interface *iface_desc;
7268 struct usb_endpoint_descriptor *endpoint;
7269 u8 i = 0;
7271 priv->ep_in_num = 0;
7272 priv->ep_out_num = 0;
7273 memset(priv->RtOutPipes,0,16);
7274 memset(priv->RtInPipes,0,16);
7276 iface_desc = intf->cur_altsetting;
7277 priv->ep_num = iface_desc->desc.bNumEndpoints;
7279 for (i = 0; i < priv->ep_num; ++i) {
7280 endpoint = &iface_desc->endpoint[i].desc;
7281 if (usb_endpoint_is_bulk_in(endpoint)) {
7282 priv->RtInPipes[priv->ep_in_num] = usb_endpoint_num(endpoint);
7283 priv->ep_in_num ++;
7284 //printk("in_endpoint_idx = %d\n", usb_endpoint_num(endpoint));
7285 } else if (usb_endpoint_is_bulk_out(endpoint)) {
7286 priv->RtOutPipes[priv->ep_out_num] = usb_endpoint_num(endpoint);
7287 priv->ep_out_num ++;
7288 //printk("out_endpoint_idx = %d\n", usb_endpoint_num(endpoint));
7292 memset(priv->txqueue_to_outpipemap,0,9);
7293 if (priv->ep_num == 6) {
7294 // BK, BE, VI, VO, HCCA, TXCMD, MGNT, HIGH, BEACON
7295 u8 queuetopipe[] = {3, 2, 1, 0, 4, 4, 4, 4, 4};
7297 memcpy(priv->txqueue_to_outpipemap,queuetopipe,9);
7298 } else if (priv->ep_num == 4) {
7299 // BK, BE, VI, VO, HCCA, TXCMD, MGNT, HIGH, BEACON
7300 u8 queuetopipe[] = {1, 1, 0, 0, 2, 2, 2, 2, 2};
7302 memcpy(priv->txqueue_to_outpipemap,queuetopipe,9);
7303 } else if (priv->ep_num > 9) {
7304 // BK, BE, VI, VO, HCCA, TXCMD, MGNT, HIGH, BEACON
7305 u8 queuetopipe[] = {3, 2, 1, 0, 4, 8, 7, 6, 5};
7307 memcpy(priv->txqueue_to_outpipemap,queuetopipe,9);
7308 } else {//use sigle pipe
7309 // BK, BE, VI, VO, HCCA, TXCMD, MGNT, HIGH, BEACON
7310 u8 queuetopipe[] = {0, 0, 0, 0, 0, 0, 0, 0, 0};
7311 memcpy(priv->txqueue_to_outpipemap,queuetopipe,9);
7314 printk("==>ep_num:%d, in_ep_num:%d, out_ep_num:%d\n", priv->ep_num, priv->ep_in_num, priv->ep_out_num);
7316 printk("==>RtInPipes:");
7317 for(i=0; i < priv->ep_in_num; i++)
7318 printk("%d ", priv->RtInPipes[i]);
7319 printk("\n");
7321 printk("==>RtOutPipes:");
7322 for(i=0; i < priv->ep_out_num; i++)
7323 printk("%d ", priv->RtOutPipes[i]);
7324 printk("\n");
7326 printk("==>txqueue_to_outpipemap for BK, BE, VI, VO, HCCA, TXCMD, MGNT, HIGH, BEACON:\n");
7327 for(i=0; i < 9; i++)
7328 printk("%d ", priv->txqueue_to_outpipemap[i]);
7329 printk("\n");
7331 return;
7334 static const struct net_device_ops rtl8192_netdev_ops = {
7335 .ndo_open = rtl8192_open,
7336 .ndo_stop = rtl8192_close,
7337 .ndo_get_stats = rtl8192_stats,
7338 .ndo_tx_timeout = tx_timeout,
7339 .ndo_do_ioctl = rtl8192_ioctl,
7340 .ndo_set_multicast_list = r8192_set_multicast,
7341 .ndo_set_mac_address = r8192_set_mac_adr,
7342 .ndo_validate_addr = eth_validate_addr,
7343 .ndo_change_mtu = eth_change_mtu,
7344 .ndo_start_xmit = rtl8192_ieee80211_rtl_xmit,
7347 static int __devinit rtl8192_usb_probe(struct usb_interface *intf,
7348 const struct usb_device_id *id)
7350 // unsigned long ioaddr = 0;
7351 struct net_device *dev = NULL;
7352 struct r8192_priv *priv= NULL;
7353 struct usb_device *udev = interface_to_usbdev(intf);
7355 RT_TRACE(COMP_INIT, "Oops: i'm coming\n");
7357 dev = alloc_ieee80211(sizeof(struct r8192_priv));
7359 usb_set_intfdata(intf, dev);
7360 SET_NETDEV_DEV(dev, &intf->dev);
7361 priv = ieee80211_priv(dev);
7362 priv->ieee80211 = netdev_priv(dev);
7363 priv->udev=udev;
7365 HalUsbSetQueuePipeMapping8192SUsb(intf, dev);
7367 //printk("===============>NIC 8192SU\n");
7368 priv->ops = &rtl8192su_ops;
7370 dev->netdev_ops = &rtl8192_netdev_ops;
7372 //DMESG("Oops: i'm coming\n");
7373 dev->wireless_handlers = (struct iw_handler_def *) &r8192_wx_handlers_def;
7375 dev->type=ARPHRD_ETHER;
7377 dev->watchdog_timeo = HZ*3; //modified by john, 0805
7379 if (dev_alloc_name(dev, ifname) < 0){
7380 RT_TRACE(COMP_INIT, "Oops: devname already taken! Trying wlan%%d...\n");
7381 ifname = "wlan%d";
7382 dev_alloc_name(dev, ifname);
7385 RT_TRACE(COMP_INIT, "Driver probe completed1\n");
7386 #if 1
7387 if(rtl8192_init(dev)!=0){
7388 RT_TRACE(COMP_ERR, "Initialization failed");
7389 goto fail;
7391 #endif
7392 netif_carrier_off(dev);
7393 netif_stop_queue(dev);
7395 register_netdev(dev);
7396 RT_TRACE(COMP_INIT, "dev name=======> %s\n",dev->name);
7397 rtl8192_proc_init_one(dev);
7400 RT_TRACE(COMP_INIT, "Driver probe completed\n");
7401 return 0;
7402 fail:
7403 free_ieee80211(dev);
7405 RT_TRACE(COMP_ERR, "wlan driver load failed\n");
7406 return -ENODEV;
7409 //detach all the work and timer structure declared or inititialize in r8192U_init function.
7410 void rtl8192_cancel_deferred_work(struct r8192_priv* priv)
7412 cancel_work_sync(&priv->reset_wq);
7413 cancel_work_sync(&priv->qos_activate);
7414 cancel_delayed_work(&priv->watch_dog_wq);
7415 cancel_delayed_work(&priv->update_beacon_wq);
7416 cancel_delayed_work(&priv->ieee80211->hw_wakeup_wq);
7417 cancel_delayed_work(&priv->ieee80211->hw_sleep_wq);
7418 //cancel_work_sync(&priv->SetBWModeWorkItem);
7419 //cancel_work_sync(&priv->SwChnlWorkItem);
7422 static void __devexit rtl8192_usb_disconnect(struct usb_interface *intf)
7424 struct net_device *dev = usb_get_intfdata(intf);
7425 struct r8192_priv *priv = ieee80211_priv(dev);
7426 if(dev){
7428 unregister_netdev(dev);
7430 RT_TRACE(COMP_DOWN, "=============>wlan driver to be removed\n");
7431 rtl8192_proc_remove_one(dev);
7433 rtl8192_down(dev);
7434 if (priv->pFirmware)
7436 vfree(priv->pFirmware);
7437 priv->pFirmware = NULL;
7439 // priv->rf_close(dev);
7440 // rtl8192_SetRFPowerState(dev, eRfOff);
7441 destroy_workqueue(priv->priv_wq);
7442 //rtl8192_irq_disable(dev);
7443 //rtl8192_reset(dev);
7444 mdelay(10);
7447 free_ieee80211(dev);
7448 RT_TRACE(COMP_DOWN, "wlan driver removed\n");
7451 /* fun with the built-in ieee80211 stack... */
7452 extern int ieee80211_debug_init(void);
7453 extern void ieee80211_debug_exit(void);
7454 extern int ieee80211_crypto_init(void);
7455 extern void ieee80211_crypto_deinit(void);
7456 extern int ieee80211_crypto_tkip_init(void);
7457 extern void ieee80211_crypto_tkip_exit(void);
7458 extern int ieee80211_crypto_ccmp_init(void);
7459 extern void ieee80211_crypto_ccmp_exit(void);
7460 extern int ieee80211_crypto_wep_init(void);
7461 extern void ieee80211_crypto_wep_exit(void);
7463 static int __init rtl8192_usb_module_init(void)
7465 int ret;
7467 #ifdef CONFIG_IEEE80211_DEBUG
7468 ret = ieee80211_debug_init();
7469 if (ret) {
7470 printk(KERN_ERR "ieee80211_debug_init() failed %d\n", ret);
7471 return ret;
7473 #endif
7474 ret = ieee80211_crypto_init();
7475 if (ret) {
7476 printk(KERN_ERR "ieee80211_crypto_init() failed %d\n", ret);
7477 return ret;
7480 ret = ieee80211_crypto_tkip_init();
7481 if (ret) {
7482 printk(KERN_ERR "ieee80211_crypto_tkip_init() failed %d\n",
7483 ret);
7484 return ret;
7487 ret = ieee80211_crypto_ccmp_init();
7488 if (ret) {
7489 printk(KERN_ERR "ieee80211_crypto_ccmp_init() failed %d\n",
7490 ret);
7491 return ret;
7494 ret = ieee80211_crypto_wep_init();
7495 if (ret) {
7496 printk(KERN_ERR "ieee80211_crypto_wep_init() failed %d\n", ret);
7497 return ret;
7500 printk(KERN_INFO "\nLinux kernel driver for RTL8192 based WLAN cards\n");
7501 printk(KERN_INFO "Copyright (c) 2007-2008, Realsil Wlan\n");
7502 RT_TRACE(COMP_INIT, "Initializing module");
7503 RT_TRACE(COMP_INIT, "Wireless extensions version %d", WIRELESS_EXT);
7504 rtl8192_proc_module_init();
7505 return usb_register(&rtl8192_usb_driver);
7509 static void __exit rtl8192_usb_module_exit(void)
7511 usb_deregister(&rtl8192_usb_driver);
7513 RT_TRACE(COMP_DOWN, "Exiting");
7514 rtl8192_proc_module_remove();
7516 ieee80211_crypto_tkip_exit();
7517 ieee80211_crypto_ccmp_exit();
7518 ieee80211_crypto_wep_exit();
7519 ieee80211_crypto_deinit();
7520 #ifdef CONFIG_IEEE80211_DEBUG
7521 ieee80211_debug_exit();
7522 #endif
7526 void rtl8192_try_wake_queue(struct net_device *dev, int pri)
7528 unsigned long flags;
7529 short enough_desc;
7530 struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
7532 spin_lock_irqsave(&priv->tx_lock,flags);
7533 enough_desc = check_nic_enough_desc(dev,pri);
7534 spin_unlock_irqrestore(&priv->tx_lock,flags);
7536 if(enough_desc)
7537 ieee80211_rtl_wake_queue(priv->ieee80211);
7540 void EnableHWSecurityConfig8192(struct net_device *dev)
7542 u8 SECR_value = 0x0;
7543 struct r8192_priv *priv = (struct r8192_priv *)ieee80211_priv(dev);
7544 struct ieee80211_device *ieee = priv->ieee80211;
7546 SECR_value = SCR_TxEncEnable | SCR_RxDecEnable;
7547 switch (ieee->pairwise_key_type) {
7548 case KEY_TYPE_WEP40:
7549 case KEY_TYPE_WEP104:
7550 if (priv->ieee80211->auth_mode != 2) {
7551 SECR_value |= SCR_RxUseDK;
7552 SECR_value |= SCR_TxUseDK;
7554 break;
7555 case KEY_TYPE_TKIP:
7556 case KEY_TYPE_CCMP:
7557 if (ieee->iw_mode == IW_MODE_ADHOC) {
7558 SECR_value |= SCR_RxUseDK;
7559 SECR_value |= SCR_TxUseDK;
7561 break;
7562 default:
7563 break;
7567 * add HWSec active enable here.
7568 * default using hwsec.
7569 * when peer AP is in N mode only and pairwise_key_type is none_aes
7570 * (which HT_IOT_ACT_PURE_N_MODE indicates it),
7571 * use software security.
7572 * when peer AP is in b,g,n mode mixed and pairwise_key_type is none_aes
7573 * use g mode hw security.
7575 ieee->hwsec_active = 1;
7577 /* add hwsec_support flag to totol control hw_sec on/off */
7578 if ((ieee->pHTInfo->IOTAction&HT_IOT_ACT_PURE_N_MODE) || !hwwep) {
7579 ieee->hwsec_active = 0;
7580 SECR_value &= ~SCR_RxDecEnable;
7583 RT_TRACE(COMP_SEC, "%s(): hwsec: %d, pairwise_key: %d, "
7584 "SECR_value: %x",
7585 __func__, ieee->hwsec_active,
7586 ieee->pairwise_key_type, SECR_value);
7588 write_nic_byte(dev, SECR, SECR_value); /* SECR_value | SCR_UseDK ); */
7592 void setKey(struct net_device *dev,
7593 u8 EntryNo,
7594 u8 KeyIndex,
7595 u16 KeyType,
7596 u8 *MacAddr,
7597 u8 DefaultKey,
7598 u32 *KeyContent)
7600 u32 TargetCommand = 0;
7601 u32 TargetContent = 0;
7602 u16 usConfig = 0;
7603 u8 i;
7605 if (EntryNo >= TOTAL_CAM_ENTRY)
7606 RT_TRACE(COMP_ERR, "%s(): cam entry exceeds TOTAL_CAM_ENTRY",
7607 __func__);
7609 RT_TRACE(COMP_SEC, "%s(): dev: %p, EntryNo: %d, "
7610 "KeyIndex: %d, KeyType: %d, MacAddr: %pM",
7611 __func__, dev, EntryNo,
7612 KeyIndex, KeyType, MacAddr);
7614 if (DefaultKey)
7615 usConfig |= BIT15 | (KeyType << 2);
7616 else
7617 usConfig |= BIT15 | (KeyType << 2) | KeyIndex;
7619 for (i = 0 ; i < CAM_CONTENT_COUNT; i++) {
7620 TargetCommand = i + CAM_CONTENT_COUNT * EntryNo;
7621 TargetCommand |= BIT31|BIT16;
7622 switch (i) {
7623 case 0: /* MAC|Config */
7624 TargetContent = (u32)(*(MacAddr + 0)) << 16|
7625 (u32)(*(MacAddr + 1)) << 24|
7626 (u32)usConfig;
7628 write_nic_dword(dev, WCAMI, TargetContent);
7629 write_nic_dword(dev, RWCAM, TargetCommand);
7630 continue;
7631 case 1: /* MAC */
7632 TargetContent = (u32)(*(MacAddr + 2))|
7633 (u32)(*(MacAddr + 3)) << 8|
7634 (u32)(*(MacAddr + 4)) << 16|
7635 (u32)(*(MacAddr + 5)) << 24;
7636 write_nic_dword(dev, WCAMI, TargetContent);
7637 write_nic_dword(dev, RWCAM, TargetCommand);
7638 continue;
7639 default: /* Key Material */
7640 if (KeyContent != NULL) {
7641 write_nic_dword(dev, WCAMI,
7642 (u32)(*(KeyContent+i-2)));
7643 write_nic_dword(dev, RWCAM,
7644 TargetCommand);
7646 continue;
7651 /***************************************************************************
7652 ------------------- module init / exit stubs ----------------
7653 ****************************************************************************/
7654 module_init(rtl8192_usb_module_init);
7655 module_exit(rtl8192_usb_module_exit);