2 *************************************************************************
4 * 5F., No.36, Taiyuan St., Jhubei City,
8 * (c) Copyright 2002-2007, Ralink Technology, Inc.
10 * This program is free software; you can redistribute it and/or modify *
11 * it under the terms of the GNU General Public License as published by *
12 * the Free Software Foundation; either version 2 of the License, or *
13 * (at your option) any later version. *
15 * This program is distributed in the hope that it will be useful, *
16 * but WITHOUT ANY WARRANTY; without even the implied warranty of *
17 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
18 * GNU General Public License for more details. *
20 * You should have received a copy of the GNU General Public License *
21 * along with this program; if not, write to the *
22 * Free Software Foundation, Inc., *
23 * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
25 *************************************************************************
31 Miniport generic portion header file
35 -------- ---------- ----------------------------------------------
37 #include "../rt_config.h"
39 UCHAR BIT8[] = { 0x01, 0x02, 0x04, 0x08, 0x10, 0x20, 0x40, 0x80 };
41 { "none", "wep64", "wep128", "TKIP", "AES", "CKIP64", "CKIP128" };
44 // BBP register initialization set
46 REG_PAIR BBPRegTable[] = {
47 {BBP_R65, 0x2C}, // fix rssi issue
48 {BBP_R66, 0x38}, // Also set this default value to pAd->BbpTuning.R66CurrentValue at initial
50 {BBP_R70, 0xa}, // BBP_R70 will change to 0x8 in ApStartUp and LinkUp for rt2860C, otherwise value is 0xa
55 {BBP_R84, 0x99}, // 0x19 is for rt2860E and after. This is for extension channel overlapping IOT. 0x99 is for rt2860D and before
56 {BBP_R86, 0x00}, // middle range issue, Rory @2008-01-28
57 {BBP_R91, 0x04}, // middle range issue, Rory @2008-01-28
58 {BBP_R92, 0x00}, // middle range issue, Rory @2008-01-28
59 {BBP_R103, 0x00}, // near range high-power issue, requested from Gary @2008-0528
60 {BBP_R105, 0x05}, // 0x05 is for rt2860E to turn on FEQ control. It is safe for rt2860D and before, because Bit 7:2 are reserved in rt2860D and before.
61 {BBP_R106, 0x35}, // for ShortGI throughput
64 #define NUM_BBP_REG_PARMS (sizeof(BBPRegTable) / sizeof(REG_PAIR))
67 // ASIC register initialization sets
70 RTMP_REG_PAIR MACRegTable[] = {
71 #if defined(HW_BEACON_OFFSET) && (HW_BEACON_OFFSET == 0x200)
72 {BCN_OFFSET0, 0xf8f0e8e0}, /* 0x3800(e0), 0x3A00(e8), 0x3C00(f0), 0x3E00(f8), 512B for each beacon */
73 {BCN_OFFSET1, 0x6f77d0c8}, /* 0x3200(c8), 0x3400(d0), 0x1DC0(77), 0x1BC0(6f), 512B for each beacon */
74 #elif defined(HW_BEACON_OFFSET) && (HW_BEACON_OFFSET == 0x100)
75 {BCN_OFFSET0, 0xece8e4e0}, /* 0x3800, 0x3A00, 0x3C00, 0x3E00, 512B for each beacon */
76 {BCN_OFFSET1, 0xfcf8f4f0}, /* 0x3800, 0x3A00, 0x3C00, 0x3E00, 512B for each beacon */
78 #error You must re-calculate new value for BCN_OFFSET0 & BCN_OFFSET1 in MACRegTable[]!!!
79 #endif // HW_BEACON_OFFSET //
81 {LEGACY_BASIC_RATE, 0x0000013f}, // Basic rate set bitmap
82 {HT_BASIC_RATE, 0x00008003}, // Basic HT rate set , 20M, MCS=3, MM. Format is the same as in TXWI.
83 {MAC_SYS_CTRL, 0x00}, // 0x1004, , default Disable RX
84 {RX_FILTR_CFG, 0x17f97}, //0x1400 , RX filter control,
85 {BKOFF_SLOT_CFG, 0x209}, // default set short slot time, CC_DELAY_TIME should be 2
86 //{TX_SW_CFG0, 0x40a06}, // Gary,2006-08-23
87 {TX_SW_CFG0, 0x0}, // Gary,2008-05-21 for CWC test
88 {TX_SW_CFG1, 0x80606}, // Gary,2006-08-23
89 {TX_LINK_CFG, 0x1020}, // Gary,2006-08-23
90 //{TX_TIMEOUT_CFG, 0x00182090}, // CCK has some problem. So increase timieout value. 2006-10-09// MArvek RT
91 {TX_TIMEOUT_CFG, 0x000a2090}, // CCK has some problem. So increase timieout value. 2006-10-09// MArvek RT , Modify for 2860E ,2007-08-01
92 {MAX_LEN_CFG, MAX_AGGREGATION_SIZE | 0x00001000}, // 0x3018, MAX frame length. Max PSDU = 16kbytes.
93 {LED_CFG, 0x7f031e46}, // Gary, 2006-08-23
95 {PBF_MAX_PCNT, 0x1F3FBF9F}, //0x1F3f7f9f}, //Jan, 2006/04/20
97 {TX_RTY_CFG, 0x47d01f0f}, // Jan, 2006/11/16, Set TxWI->ACK =0 in Probe Rsp Modify for 2860E ,2007-08-03
99 {AUTO_RSP_CFG, 0x00000013}, // Initial Auto_Responder, because QA will turn off Auto-Responder
100 {CCK_PROT_CFG, 0x05740003 /*0x01740003 */ }, // Initial Auto_Responder, because QA will turn off Auto-Responder. And RTS threshold is enabled.
101 {OFDM_PROT_CFG, 0x05740003 /*0x01740003 */ }, // Initial Auto_Responder, because QA will turn off Auto-Responder. And RTS threshold is enabled.
103 {PBF_CFG, 0xf40006}, // Only enable Queue 2
104 {MM40_PROT_CFG, 0x3F44084}, // Initial Auto_Responder, because QA will turn off Auto-Responder
105 {WPDMA_GLO_CFG, 0x00000030},
106 #endif // RTMP_MAC_USB //
107 {GF20_PROT_CFG, 0x01744004}, // set 19:18 --> Short NAV for MIMO PS
108 {GF40_PROT_CFG, 0x03F44084},
109 {MM20_PROT_CFG, 0x01744004},
111 {MM40_PROT_CFG, 0x03F54084},
112 #endif // RTMP_MAC_PCI //
113 {TXOP_CTRL_CFG, 0x0000583f, /*0x0000243f *//*0x000024bf */ }, //Extension channel backoff.
114 {TX_RTS_CFG, 0x00092b20},
115 {EXP_ACK_TIME, 0x002400ca}, // default value
117 {TXOP_HLDR_ET, 0x00000002},
119 /* Jerry comments 2008/01/16: we use SIFS = 10us in CCK defaultly, but it seems that 10us
120 is too small for INTEL 2200bg card, so in MBSS mode, the delta time between beacon0
121 and beacon1 is SIFS (10us), so if INTEL 2200bg card connects to BSS0, the ping
122 will always lost. So we change the SIFS of CCK from 10us to 16us. */
123 {XIFS_TIME_CFG, 0x33a41010},
124 {PWR_PIN_CFG, 0x00000003}, // patch for 2880-E
127 RTMP_REG_PAIR STAMACRegTable[] = {
128 {WMM_AIFSN_CFG, 0x00002273},
129 {WMM_CWMIN_CFG, 0x00002344},
130 {WMM_CWMAX_CFG, 0x000034aa},
133 #define NUM_MAC_REG_PARMS (sizeof(MACRegTable) / sizeof(RTMP_REG_PAIR))
134 #define NUM_STA_MAC_REG_PARMS (sizeof(STAMACRegTable) / sizeof(RTMP_REG_PAIR))
137 ========================================================================
140 Allocate RTMP_ADAPTER data block and do some initialization
143 Adapter Pointer to our adapter
153 ========================================================================
155 NDIS_STATUS RTMPAllocAdapterBlock(IN PVOID handle,
156 OUT PRTMP_ADAPTER * ppAdapter)
161 UCHAR *pBeaconBuf = NULL;
163 DBGPRINT(RT_DEBUG_TRACE, ("--> RTMPAllocAdapterBlock\n"));
168 // Allocate RTMP_ADAPTER memory block
169 pBeaconBuf = kmalloc(MAX_BEACON_SIZE, MEM_ALLOC_FLAG);
170 if (pBeaconBuf == NULL) {
171 Status = NDIS_STATUS_FAILURE;
172 DBGPRINT_ERR(("Failed to allocate memory - BeaconBuf!\n"));
175 NdisZeroMemory(pBeaconBuf, MAX_BEACON_SIZE);
177 Status = AdapterBlockAllocateMemory(handle, (PVOID *) & pAd);
178 if (Status != NDIS_STATUS_SUCCESS) {
179 DBGPRINT_ERR(("Failed to allocate memory - ADAPTER\n"));
182 pAd->BeaconBuf = pBeaconBuf;
183 DBGPRINT(RT_DEBUG_OFF,
184 ("\n\n=== pAd = %p, size = %d ===\n\n", pAd,
185 (UINT32) sizeof(RTMP_ADAPTER)));
188 NdisAllocateSpinLock(&pAd->MgmtRingLock);
190 NdisAllocateSpinLock(&pAd->RxRingLock);
192 NdisAllocateSpinLock(&pAd->McuCmdLock);
194 #endif // RTMP_MAC_PCI //
196 for (index = 0; index < NUM_OF_TX_RING; index++) {
197 NdisAllocateSpinLock(&pAd->TxSwQueueLock[index]);
198 NdisAllocateSpinLock(&pAd->DeQueueLock[index]);
199 pAd->DeQueueRunning[index] = FALSE;
202 NdisAllocateSpinLock(&pAd->irq_lock);
206 if ((Status != NDIS_STATUS_SUCCESS) && (pBeaconBuf))
211 DBGPRINT_S(Status, ("<-- RTMPAllocAdapterBlock, Status=%x\n", Status));
216 ========================================================================
219 Read initial Tx power per MCS and BW from EEPROM
222 Adapter Pointer to our adapter
231 ========================================================================
233 VOID RTMPReadTxPwrPerRate(IN PRTMP_ADAPTER pAd)
235 ULONG data, Adata, Gdata;
236 USHORT i, value, value2;
237 INT Apwrdelta, Gpwrdelta;
238 UCHAR t1, t2, t3, t4;
239 BOOLEAN bApwrdeltaMinus = TRUE, bGpwrdeltaMinus = TRUE;
242 // Get power delta for 20MHz and 40MHz.
244 DBGPRINT(RT_DEBUG_TRACE, ("Txpower per Rate\n"));
245 RT28xx_EEPROM_READ16(pAd, EEPROM_TXPOWER_DELTA, value2);
249 if ((value2 & 0xff) != 0xff) {
251 Gpwrdelta = (value2 & 0xf);
254 bGpwrdeltaMinus = FALSE;
256 bGpwrdeltaMinus = TRUE;
258 if ((value2 & 0xff00) != 0xff00) {
259 if ((value2 & 0x8000))
260 Apwrdelta = ((value2 & 0xf00) >> 8);
262 if ((value2 & 0x4000))
263 bApwrdeltaMinus = FALSE;
265 bApwrdeltaMinus = TRUE;
267 DBGPRINT(RT_DEBUG_TRACE,
268 ("Gpwrdelta = %x, Apwrdelta = %x .\n", Gpwrdelta, Apwrdelta));
271 // Get Txpower per MCS for 20MHz in 2.4G.
273 for (i = 0; i < 5; i++) {
274 RT28xx_EEPROM_READ16(pAd,
275 EEPROM_TXPOWER_BYRATE_20MHZ_2_4G + i * 4,
278 if (bApwrdeltaMinus == FALSE) {
279 t1 = (value & 0xf) + (Apwrdelta);
282 t2 = ((value & 0xf0) >> 4) + (Apwrdelta);
285 t3 = ((value & 0xf00) >> 8) + (Apwrdelta);
288 t4 = ((value & 0xf000) >> 12) + (Apwrdelta);
292 if ((value & 0xf) > Apwrdelta)
293 t1 = (value & 0xf) - (Apwrdelta);
296 if (((value & 0xf0) >> 4) > Apwrdelta)
297 t2 = ((value & 0xf0) >> 4) - (Apwrdelta);
300 if (((value & 0xf00) >> 8) > Apwrdelta)
301 t3 = ((value & 0xf00) >> 8) - (Apwrdelta);
304 if (((value & 0xf000) >> 12) > Apwrdelta)
305 t4 = ((value & 0xf000) >> 12) - (Apwrdelta);
309 Adata = t1 + (t2 << 4) + (t3 << 8) + (t4 << 12);
310 if (bGpwrdeltaMinus == FALSE) {
311 t1 = (value & 0xf) + (Gpwrdelta);
314 t2 = ((value & 0xf0) >> 4) + (Gpwrdelta);
317 t3 = ((value & 0xf00) >> 8) + (Gpwrdelta);
320 t4 = ((value & 0xf000) >> 12) + (Gpwrdelta);
324 if ((value & 0xf) > Gpwrdelta)
325 t1 = (value & 0xf) - (Gpwrdelta);
328 if (((value & 0xf0) >> 4) > Gpwrdelta)
329 t2 = ((value & 0xf0) >> 4) - (Gpwrdelta);
332 if (((value & 0xf00) >> 8) > Gpwrdelta)
333 t3 = ((value & 0xf00) >> 8) - (Gpwrdelta);
336 if (((value & 0xf000) >> 12) > Gpwrdelta)
337 t4 = ((value & 0xf000) >> 12) - (Gpwrdelta);
341 Gdata = t1 + (t2 << 4) + (t3 << 8) + (t4 << 12);
343 RT28xx_EEPROM_READ16(pAd,
344 EEPROM_TXPOWER_BYRATE_20MHZ_2_4G + i * 4 +
346 if (bApwrdeltaMinus == FALSE) {
347 t1 = (value & 0xf) + (Apwrdelta);
350 t2 = ((value & 0xf0) >> 4) + (Apwrdelta);
353 t3 = ((value & 0xf00) >> 8) + (Apwrdelta);
356 t4 = ((value & 0xf000) >> 12) + (Apwrdelta);
360 if ((value & 0xf) > Apwrdelta)
361 t1 = (value & 0xf) - (Apwrdelta);
364 if (((value & 0xf0) >> 4) > Apwrdelta)
365 t2 = ((value & 0xf0) >> 4) - (Apwrdelta);
368 if (((value & 0xf00) >> 8) > Apwrdelta)
369 t3 = ((value & 0xf00) >> 8) - (Apwrdelta);
372 if (((value & 0xf000) >> 12) > Apwrdelta)
373 t4 = ((value & 0xf000) >> 12) - (Apwrdelta);
377 Adata |= ((t1 << 16) + (t2 << 20) + (t3 << 24) + (t4 << 28));
378 if (bGpwrdeltaMinus == FALSE) {
379 t1 = (value & 0xf) + (Gpwrdelta);
382 t2 = ((value & 0xf0) >> 4) + (Gpwrdelta);
385 t3 = ((value & 0xf00) >> 8) + (Gpwrdelta);
388 t4 = ((value & 0xf000) >> 12) + (Gpwrdelta);
392 if ((value & 0xf) > Gpwrdelta)
393 t1 = (value & 0xf) - (Gpwrdelta);
396 if (((value & 0xf0) >> 4) > Gpwrdelta)
397 t2 = ((value & 0xf0) >> 4) - (Gpwrdelta);
400 if (((value & 0xf00) >> 8) > Gpwrdelta)
401 t3 = ((value & 0xf00) >> 8) - (Gpwrdelta);
404 if (((value & 0xf000) >> 12) > Gpwrdelta)
405 t4 = ((value & 0xf000) >> 12) - (Gpwrdelta);
409 Gdata |= ((t1 << 16) + (t2 << 20) + (t3 << 24) + (t4 << 28));
410 data |= (value << 16);
412 /* For 20M/40M Power Delta issue */
413 pAd->Tx20MPwrCfgABand[i] = data;
414 pAd->Tx20MPwrCfgGBand[i] = data;
415 pAd->Tx40MPwrCfgABand[i] = Adata;
416 pAd->Tx40MPwrCfgGBand[i] = Gdata;
418 if (data != 0xffffffff)
419 RTMP_IO_WRITE32(pAd, TX_PWR_CFG_0 + i * 4, data);
420 DBGPRINT_RAW(RT_DEBUG_TRACE,
421 ("20MHz BW, 2.4G band-%lx, Adata = %lx, Gdata = %lx \n",
422 data, Adata, Gdata));
427 ========================================================================
430 Read initial channel power parameters from EEPROM
433 Adapter Pointer to our adapter
442 ========================================================================
444 VOID RTMPReadChannelPwr(IN PRTMP_ADAPTER pAd)
447 EEPROM_TX_PWR_STRUC Power;
448 EEPROM_TX_PWR_STRUC Power2;
450 // Read Tx power value for all channels
451 // Value from 1 - 0x7f. Default value is 24.
452 // Power value : 2.4G 0x00 (0) ~ 0x1F (31)
453 // : 5.5G 0xF9 (-7) ~ 0x0F (15)
455 // 0. 11b/g, ch1 - ch 14
456 for (i = 0; i < 7; i++) {
457 RT28xx_EEPROM_READ16(pAd, EEPROM_G_TX_PWR_OFFSET + i * 2,
459 RT28xx_EEPROM_READ16(pAd, EEPROM_G_TX2_PWR_OFFSET + i * 2,
461 pAd->TxPower[i * 2].Channel = i * 2 + 1;
462 pAd->TxPower[i * 2 + 1].Channel = i * 2 + 2;
464 if ((Power.field.Byte0 > 31) || (Power.field.Byte0 < 0))
465 pAd->TxPower[i * 2].Power = DEFAULT_RF_TX_POWER;
467 pAd->TxPower[i * 2].Power = Power.field.Byte0;
469 if ((Power.field.Byte1 > 31) || (Power.field.Byte1 < 0))
470 pAd->TxPower[i * 2 + 1].Power = DEFAULT_RF_TX_POWER;
472 pAd->TxPower[i * 2 + 1].Power = Power.field.Byte1;
474 if ((Power2.field.Byte0 > 31) || (Power2.field.Byte0 < 0))
475 pAd->TxPower[i * 2].Power2 = DEFAULT_RF_TX_POWER;
477 pAd->TxPower[i * 2].Power2 = Power2.field.Byte0;
479 if ((Power2.field.Byte1 > 31) || (Power2.field.Byte1 < 0))
480 pAd->TxPower[i * 2 + 1].Power2 = DEFAULT_RF_TX_POWER;
482 pAd->TxPower[i * 2 + 1].Power2 = Power2.field.Byte1;
485 // 1. U-NII lower/middle band: 36, 38, 40; 44, 46, 48; 52, 54, 56; 60, 62, 64 (including central frequency in BW 40MHz)
486 // 1.1 Fill up channel
488 for (i = 0; i < 4; i++) {
489 pAd->TxPower[3 * i + choffset + 0].Channel = 36 + i * 8 + 0;
490 pAd->TxPower[3 * i + choffset + 0].Power = DEFAULT_RF_TX_POWER;
491 pAd->TxPower[3 * i + choffset + 0].Power2 = DEFAULT_RF_TX_POWER;
493 pAd->TxPower[3 * i + choffset + 1].Channel = 36 + i * 8 + 2;
494 pAd->TxPower[3 * i + choffset + 1].Power = DEFAULT_RF_TX_POWER;
495 pAd->TxPower[3 * i + choffset + 1].Power2 = DEFAULT_RF_TX_POWER;
497 pAd->TxPower[3 * i + choffset + 2].Channel = 36 + i * 8 + 4;
498 pAd->TxPower[3 * i + choffset + 2].Power = DEFAULT_RF_TX_POWER;
499 pAd->TxPower[3 * i + choffset + 2].Power2 = DEFAULT_RF_TX_POWER;
503 for (i = 0; i < 6; i++) {
504 RT28xx_EEPROM_READ16(pAd, EEPROM_A_TX_PWR_OFFSET + i * 2,
506 RT28xx_EEPROM_READ16(pAd, EEPROM_A_TX2_PWR_OFFSET + i * 2,
509 if ((Power.field.Byte0 < 16) && (Power.field.Byte0 >= -7))
510 pAd->TxPower[i * 2 + choffset + 0].Power =
513 if ((Power.field.Byte1 < 16) && (Power.field.Byte1 >= -7))
514 pAd->TxPower[i * 2 + choffset + 1].Power =
517 if ((Power2.field.Byte0 < 16) && (Power2.field.Byte0 >= -7))
518 pAd->TxPower[i * 2 + choffset + 0].Power2 =
521 if ((Power2.field.Byte1 < 16) && (Power2.field.Byte1 >= -7))
522 pAd->TxPower[i * 2 + choffset + 1].Power2 =
526 // 2. HipperLAN 2 100, 102 ,104; 108, 110, 112; 116, 118, 120; 124, 126, 128; 132, 134, 136; 140 (including central frequency in BW 40MHz)
527 // 2.1 Fill up channel
529 for (i = 0; i < 5; i++) {
530 pAd->TxPower[3 * i + choffset + 0].Channel = 100 + i * 8 + 0;
531 pAd->TxPower[3 * i + choffset + 0].Power = DEFAULT_RF_TX_POWER;
532 pAd->TxPower[3 * i + choffset + 0].Power2 = DEFAULT_RF_TX_POWER;
534 pAd->TxPower[3 * i + choffset + 1].Channel = 100 + i * 8 + 2;
535 pAd->TxPower[3 * i + choffset + 1].Power = DEFAULT_RF_TX_POWER;
536 pAd->TxPower[3 * i + choffset + 1].Power2 = DEFAULT_RF_TX_POWER;
538 pAd->TxPower[3 * i + choffset + 2].Channel = 100 + i * 8 + 4;
539 pAd->TxPower[3 * i + choffset + 2].Power = DEFAULT_RF_TX_POWER;
540 pAd->TxPower[3 * i + choffset + 2].Power2 = DEFAULT_RF_TX_POWER;
542 pAd->TxPower[3 * 5 + choffset + 0].Channel = 140;
543 pAd->TxPower[3 * 5 + choffset + 0].Power = DEFAULT_RF_TX_POWER;
544 pAd->TxPower[3 * 5 + choffset + 0].Power2 = DEFAULT_RF_TX_POWER;
547 for (i = 0; i < 8; i++) {
548 RT28xx_EEPROM_READ16(pAd,
549 EEPROM_A_TX_PWR_OFFSET + (choffset - 14) +
551 RT28xx_EEPROM_READ16(pAd,
552 EEPROM_A_TX2_PWR_OFFSET + (choffset - 14) +
555 if ((Power.field.Byte0 < 16) && (Power.field.Byte0 >= -7))
556 pAd->TxPower[i * 2 + choffset + 0].Power =
559 if ((Power.field.Byte1 < 16) && (Power.field.Byte1 >= -7))
560 pAd->TxPower[i * 2 + choffset + 1].Power =
563 if ((Power2.field.Byte0 < 16) && (Power2.field.Byte0 >= -7))
564 pAd->TxPower[i * 2 + choffset + 0].Power2 =
567 if ((Power2.field.Byte1 < 16) && (Power2.field.Byte1 >= -7))
568 pAd->TxPower[i * 2 + choffset + 1].Power2 =
572 // 3. U-NII upper band: 149, 151, 153; 157, 159, 161; 165, 167, 169; 171, 173 (including central frequency in BW 40MHz)
573 // 3.1 Fill up channel
574 choffset = 14 + 12 + 16;
575 /*for (i = 0; i < 2; i++) */
576 for (i = 0; i < 3; i++) {
577 pAd->TxPower[3 * i + choffset + 0].Channel = 149 + i * 8 + 0;
578 pAd->TxPower[3 * i + choffset + 0].Power = DEFAULT_RF_TX_POWER;
579 pAd->TxPower[3 * i + choffset + 0].Power2 = DEFAULT_RF_TX_POWER;
581 pAd->TxPower[3 * i + choffset + 1].Channel = 149 + i * 8 + 2;
582 pAd->TxPower[3 * i + choffset + 1].Power = DEFAULT_RF_TX_POWER;
583 pAd->TxPower[3 * i + choffset + 1].Power2 = DEFAULT_RF_TX_POWER;
585 pAd->TxPower[3 * i + choffset + 2].Channel = 149 + i * 8 + 4;
586 pAd->TxPower[3 * i + choffset + 2].Power = DEFAULT_RF_TX_POWER;
587 pAd->TxPower[3 * i + choffset + 2].Power2 = DEFAULT_RF_TX_POWER;
589 pAd->TxPower[3 * 3 + choffset + 0].Channel = 171;
590 pAd->TxPower[3 * 3 + choffset + 0].Power = DEFAULT_RF_TX_POWER;
591 pAd->TxPower[3 * 3 + choffset + 0].Power2 = DEFAULT_RF_TX_POWER;
593 pAd->TxPower[3 * 3 + choffset + 1].Channel = 173;
594 pAd->TxPower[3 * 3 + choffset + 1].Power = DEFAULT_RF_TX_POWER;
595 pAd->TxPower[3 * 3 + choffset + 1].Power2 = DEFAULT_RF_TX_POWER;
598 /*for (i = 0; i < 4; i++) */
599 for (i = 0; i < 6; i++) {
600 RT28xx_EEPROM_READ16(pAd,
601 EEPROM_A_TX_PWR_OFFSET + (choffset - 14) +
603 RT28xx_EEPROM_READ16(pAd,
604 EEPROM_A_TX2_PWR_OFFSET + (choffset - 14) +
607 if ((Power.field.Byte0 < 16) && (Power.field.Byte0 >= -7))
608 pAd->TxPower[i * 2 + choffset + 0].Power =
611 if ((Power.field.Byte1 < 16) && (Power.field.Byte1 >= -7))
612 pAd->TxPower[i * 2 + choffset + 1].Power =
615 if ((Power2.field.Byte0 < 16) && (Power2.field.Byte0 >= -7))
616 pAd->TxPower[i * 2 + choffset + 0].Power2 =
619 if ((Power2.field.Byte1 < 16) && (Power2.field.Byte1 >= -7))
620 pAd->TxPower[i * 2 + choffset + 1].Power2 =
624 // 4. Print and Debug
625 /*choffset = 14 + 12 + 16 + 7; */
626 choffset = 14 + 12 + 16 + 11;
631 ========================================================================
634 Read the following from the registry
635 1. All the parameters
639 Adapter Pointer to our adapter
640 WrapperConfigurationContext For use by NdisOpenConfiguration
645 NDIS_STATUS_RESOURCES
651 ========================================================================
653 NDIS_STATUS NICReadRegParameters(IN PRTMP_ADAPTER pAd,
654 IN NDIS_HANDLE WrapperConfigurationContext)
656 NDIS_STATUS Status = NDIS_STATUS_SUCCESS;
657 DBGPRINT_S(Status, ("<-- NICReadRegParameters, Status=%x\n", Status));
662 ========================================================================
665 Read initial parameters from EEPROM
668 Adapter Pointer to our adapter
677 ========================================================================
679 VOID NICReadEEPROMParameters(IN PRTMP_ADAPTER pAd, IN PUCHAR mac_addr)
682 USHORT i, value, value2;
684 EEPROM_TX_PWR_STRUC Power;
685 EEPROM_VERSION_STRUC Version;
686 EEPROM_ANTENNA_STRUC Antenna;
687 EEPROM_NIC_CONFIG2_STRUC NicConfig2;
689 DBGPRINT(RT_DEBUG_TRACE, ("--> NICReadEEPROMParameters\n"));
691 if (pAd->chipOps.eeinit)
692 pAd->chipOps.eeinit(pAd);
694 // Init EEPROM Address Number, before access EEPROM; if 93c46, EEPROMAddressNum=6, else if 93c66, EEPROMAddressNum=8
695 RTMP_IO_READ32(pAd, E2PROM_CSR, &data);
696 DBGPRINT(RT_DEBUG_TRACE, ("--> E2PROM_CSR = 0x%x\n", data));
698 if ((data & 0x30) == 0)
699 pAd->EEPROMAddressNum = 6; // 93C46
700 else if ((data & 0x30) == 0x10)
701 pAd->EEPROMAddressNum = 8; // 93C66
703 pAd->EEPROMAddressNum = 8; // 93C86
704 DBGPRINT(RT_DEBUG_TRACE,
705 ("--> EEPROMAddressNum = %d\n", pAd->EEPROMAddressNum));
707 // RT2860 MAC no longer auto load MAC address from E2PROM. Driver has to intialize
708 // MAC address registers according to E2PROM setting
709 if (mac_addr == NULL ||
710 strlen((PSTRING) mac_addr) != 17 ||
711 mac_addr[2] != ':' || mac_addr[5] != ':' || mac_addr[8] != ':' ||
712 mac_addr[11] != ':' || mac_addr[14] != ':') {
713 USHORT Addr01, Addr23, Addr45;
715 RT28xx_EEPROM_READ16(pAd, 0x04, Addr01);
716 RT28xx_EEPROM_READ16(pAd, 0x06, Addr23);
717 RT28xx_EEPROM_READ16(pAd, 0x08, Addr45);
719 pAd->PermanentAddress[0] = (UCHAR) (Addr01 & 0xff);
720 pAd->PermanentAddress[1] = (UCHAR) (Addr01 >> 8);
721 pAd->PermanentAddress[2] = (UCHAR) (Addr23 & 0xff);
722 pAd->PermanentAddress[3] = (UCHAR) (Addr23 >> 8);
723 pAd->PermanentAddress[4] = (UCHAR) (Addr45 & 0xff);
724 pAd->PermanentAddress[5] = (UCHAR) (Addr45 >> 8);
726 DBGPRINT(RT_DEBUG_TRACE,
727 ("Initialize MAC Address from E2PROM \n"));
732 macptr = (PSTRING) mac_addr;
734 for (j = 0; j < MAC_ADDR_LEN; j++) {
735 AtoH(macptr, &pAd->PermanentAddress[j], 1);
739 DBGPRINT(RT_DEBUG_TRACE,
740 ("Initialize MAC Address from module parameter \n"));
744 //more conveninet to test mbssid, so ap's bssid &0xf1
745 if (pAd->PermanentAddress[0] == 0xff)
746 pAd->PermanentAddress[0] = RandomByte(pAd) & 0xf8;
748 //if (pAd->PermanentAddress[5] == 0xff)
749 // pAd->PermanentAddress[5] = RandomByte(pAd)&0xf8;
751 DBGPRINT_RAW(RT_DEBUG_TRACE,
752 ("E2PROM MAC: =%02x:%02x:%02x:%02x:%02x:%02x\n",
753 pAd->PermanentAddress[0],
754 pAd->PermanentAddress[1],
755 pAd->PermanentAddress[2],
756 pAd->PermanentAddress[3],
757 pAd->PermanentAddress[4],
758 pAd->PermanentAddress[5]));
759 if (pAd->bLocalAdminMAC == FALSE) {
762 COPY_MAC_ADDR(pAd->CurrentAddress,
763 pAd->PermanentAddress);
764 csr2.field.Byte0 = pAd->CurrentAddress[0];
765 csr2.field.Byte1 = pAd->CurrentAddress[1];
766 csr2.field.Byte2 = pAd->CurrentAddress[2];
767 csr2.field.Byte3 = pAd->CurrentAddress[3];
768 RTMP_IO_WRITE32(pAd, MAC_ADDR_DW0, csr2.word);
770 csr3.field.Byte4 = pAd->CurrentAddress[4];
771 csr3.field.Byte5 = pAd->CurrentAddress[5];
772 csr3.field.U2MeMask = 0xff;
773 RTMP_IO_WRITE32(pAd, MAC_ADDR_DW1, csr3.word);
774 DBGPRINT_RAW(RT_DEBUG_TRACE,
775 ("E2PROM MAC: =%02x:%02x:%02x:%02x:%02x:%02x\n",
776 PRINT_MAC(pAd->PermanentAddress)));
780 // if not return early. cause fail at emulation.
781 // Init the channel number for TX channel power
782 RTMPReadChannelPwr(pAd);
784 // if E2PROM version mismatch with driver's expectation, then skip
785 // all subsequent E2RPOM retieval and set a system error bit to notify GUI
786 RT28xx_EEPROM_READ16(pAd, EEPROM_VERSION_OFFSET, Version.word);
788 Version.field.Version + Version.field.FaeReleaseNumber * 256;
789 DBGPRINT(RT_DEBUG_TRACE,
790 ("E2PROM: Version = %d, FAE release #%d\n",
791 Version.field.Version, Version.field.FaeReleaseNumber));
793 if (Version.field.Version > VALID_EEPROM_VERSION) {
794 DBGPRINT_ERR(("E2PROM: WRONG VERSION 0x%x, should be %d\n",
795 Version.field.Version, VALID_EEPROM_VERSION));
796 /*pAd->SystemErrorBitmap |= 0x00000001;
798 // hard-code default value when no proper E2PROM installed
799 pAd->bAutoTxAgcA = FALSE;
800 pAd->bAutoTxAgcG = FALSE;
802 // Default the channel power
803 for (i = 0; i < MAX_NUM_OF_CHANNELS; i++)
804 pAd->TxPower[i].Power = DEFAULT_RF_TX_POWER;
806 // Default the channel power
807 for (i = 0; i < MAX_NUM_OF_11JCHANNELS; i++)
808 pAd->TxPower11J[i].Power = DEFAULT_RF_TX_POWER;
810 for(i = 0; i < NUM_EEPROM_BBP_PARMS; i++)
811 pAd->EEPROMDefaultValue[i] = 0xffff;
814 // Read BBP default value from EEPROM and store to array(EEPROMDefaultValue) in pAd
815 RT28xx_EEPROM_READ16(pAd, EEPROM_NIC1_OFFSET, value);
816 pAd->EEPROMDefaultValue[0] = value;
818 RT28xx_EEPROM_READ16(pAd, EEPROM_NIC2_OFFSET, value);
819 pAd->EEPROMDefaultValue[1] = value;
821 RT28xx_EEPROM_READ16(pAd, 0x38, value); // Country Region
822 pAd->EEPROMDefaultValue[2] = value;
824 for (i = 0; i < 8; i++) {
825 RT28xx_EEPROM_READ16(pAd, EEPROM_BBP_BASE_OFFSET + i * 2,
827 pAd->EEPROMDefaultValue[i + 3] = value;
830 // We have to parse NIC configuration 0 at here.
831 // If TSSI did not have preloaded value, it should reset the TxAutoAgc to false
832 // Therefore, we have to read TxAutoAgc control beforehand.
833 // Read Tx AGC control bit
834 Antenna.word = pAd->EEPROMDefaultValue[0];
835 if (Antenna.word == 0xFFFF) {
837 if (IS_RT3090(pAd) || IS_RT3390(pAd)) {
839 Antenna.field.RfIcType = RFIC_3020;
840 Antenna.field.TxPath = 1;
841 Antenna.field.RxPath = 1;
847 Antenna.field.RfIcType = RFIC_2820;
848 Antenna.field.TxPath = 1;
849 Antenna.field.RxPath = 2;
850 DBGPRINT(RT_DEBUG_WARN,
851 ("E2PROM error, hard code as 0x%04x\n",
855 // Choose the desired Tx&Rx stream.
856 if ((pAd->CommonCfg.TxStream == 0)
857 || (pAd->CommonCfg.TxStream > Antenna.field.TxPath))
858 pAd->CommonCfg.TxStream = Antenna.field.TxPath;
860 if ((pAd->CommonCfg.RxStream == 0)
861 || (pAd->CommonCfg.RxStream > Antenna.field.RxPath)) {
862 pAd->CommonCfg.RxStream = Antenna.field.RxPath;
864 if ((pAd->MACVersion < RALINK_2883_VERSION) &&
865 (pAd->CommonCfg.RxStream > 2)) {
866 // only 2 Rx streams for RT2860 series
867 pAd->CommonCfg.RxStream = 2;
871 // read value from EEPROM and set them to CSR174 ~ 177 in chain0 ~ chain2
873 for (i = 0; i < 3; i++) {
876 NicConfig2.word = pAd->EEPROMDefaultValue[1];
879 if ((NicConfig2.word & 0x00ff) == 0xff) {
880 NicConfig2.word &= 0xff00;
883 if ((NicConfig2.word >> 8) == 0xff) {
884 NicConfig2.word &= 0x00ff;
888 if (NicConfig2.field.DynamicTxAgcControl == 1)
889 pAd->bAutoTxAgcA = pAd->bAutoTxAgcG = TRUE;
891 pAd->bAutoTxAgcA = pAd->bAutoTxAgcG = FALSE;
893 DBGPRINT_RAW(RT_DEBUG_TRACE,
894 ("NICReadEEPROMParameters: RxPath = %d, TxPath = %d\n",
895 Antenna.field.RxPath, Antenna.field.TxPath));
897 // Save the antenna for future use
898 pAd->Antenna.word = Antenna.word;
900 // Set the RfICType here, then we can initialize RFIC related operation callbacks
901 pAd->Mlme.RealRxPath = (UCHAR) Antenna.field.RxPath;
902 pAd->RfIcType = (UCHAR) Antenna.field.RfIcType;
904 #ifdef RTMP_RF_RW_SUPPORT
905 RtmpChipOpsRFHook(pAd);
906 #endif // RTMP_RF_RW_SUPPORT //
909 sprintf((PSTRING) pAd->nickname, "RT2860STA");
910 #endif // RTMP_MAC_PCI //
913 // Reset PhyMode if we don't support 802.11a
914 // Only RFIC_2850 & RFIC_2750 support 802.11a
916 if ((Antenna.field.RfIcType != RFIC_2850)
917 && (Antenna.field.RfIcType != RFIC_2750)
918 && (Antenna.field.RfIcType != RFIC_3052)) {
919 if ((pAd->CommonCfg.PhyMode == PHY_11ABG_MIXED) ||
920 (pAd->CommonCfg.PhyMode == PHY_11A))
921 pAd->CommonCfg.PhyMode = PHY_11BG_MIXED;
922 else if ((pAd->CommonCfg.PhyMode == PHY_11ABGN_MIXED) ||
923 (pAd->CommonCfg.PhyMode == PHY_11AN_MIXED) ||
924 (pAd->CommonCfg.PhyMode == PHY_11AGN_MIXED) ||
925 (pAd->CommonCfg.PhyMode == PHY_11N_5G))
926 pAd->CommonCfg.PhyMode = PHY_11BGN_MIXED;
928 // Read TSSI reference and TSSI boundary for temperature compensation. This is ugly
931 /* these are tempature reference value (0x00 ~ 0xFE)
932 ex: 0x00 0x15 0x25 0x45 0x88 0xA0 0xB5 0xD0 0xF0
933 TssiPlusBoundaryG [4] [3] [2] [1] [0] (smaller) +
934 TssiMinusBoundaryG[0] [1] [2] [3] [4] (larger) */
935 RT28xx_EEPROM_READ16(pAd, 0x6E, Power.word);
936 pAd->TssiMinusBoundaryG[4] = Power.field.Byte0;
937 pAd->TssiMinusBoundaryG[3] = Power.field.Byte1;
938 RT28xx_EEPROM_READ16(pAd, 0x70, Power.word);
939 pAd->TssiMinusBoundaryG[2] = Power.field.Byte0;
940 pAd->TssiMinusBoundaryG[1] = Power.field.Byte1;
941 RT28xx_EEPROM_READ16(pAd, 0x72, Power.word);
942 pAd->TssiRefG = Power.field.Byte0; /* reference value [0] */
943 pAd->TssiPlusBoundaryG[1] = Power.field.Byte1;
944 RT28xx_EEPROM_READ16(pAd, 0x74, Power.word);
945 pAd->TssiPlusBoundaryG[2] = Power.field.Byte0;
946 pAd->TssiPlusBoundaryG[3] = Power.field.Byte1;
947 RT28xx_EEPROM_READ16(pAd, 0x76, Power.word);
948 pAd->TssiPlusBoundaryG[4] = Power.field.Byte0;
949 pAd->TxAgcStepG = Power.field.Byte1;
950 pAd->TxAgcCompensateG = 0;
951 pAd->TssiMinusBoundaryG[0] = pAd->TssiRefG;
952 pAd->TssiPlusBoundaryG[0] = pAd->TssiRefG;
954 // Disable TxAgc if the based value is not right
955 if (pAd->TssiRefG == 0xff)
956 pAd->bAutoTxAgcG = FALSE;
958 DBGPRINT(RT_DEBUG_TRACE,
959 ("E2PROM: G Tssi[-4 .. +4] = %d %d %d %d - %d -%d %d %d %d, step=%d, tuning=%d\n",
960 pAd->TssiMinusBoundaryG[4],
961 pAd->TssiMinusBoundaryG[3],
962 pAd->TssiMinusBoundaryG[2],
963 pAd->TssiMinusBoundaryG[1], pAd->TssiRefG,
964 pAd->TssiPlusBoundaryG[1], pAd->TssiPlusBoundaryG[2],
965 pAd->TssiPlusBoundaryG[3], pAd->TssiPlusBoundaryG[4],
966 pAd->TxAgcStepG, pAd->bAutoTxAgcG));
970 RT28xx_EEPROM_READ16(pAd, 0xD4, Power.word);
971 pAd->TssiMinusBoundaryA[4] = Power.field.Byte0;
972 pAd->TssiMinusBoundaryA[3] = Power.field.Byte1;
973 RT28xx_EEPROM_READ16(pAd, 0xD6, Power.word);
974 pAd->TssiMinusBoundaryA[2] = Power.field.Byte0;
975 pAd->TssiMinusBoundaryA[1] = Power.field.Byte1;
976 RT28xx_EEPROM_READ16(pAd, 0xD8, Power.word);
977 pAd->TssiRefA = Power.field.Byte0;
978 pAd->TssiPlusBoundaryA[1] = Power.field.Byte1;
979 RT28xx_EEPROM_READ16(pAd, 0xDA, Power.word);
980 pAd->TssiPlusBoundaryA[2] = Power.field.Byte0;
981 pAd->TssiPlusBoundaryA[3] = Power.field.Byte1;
982 RT28xx_EEPROM_READ16(pAd, 0xDC, Power.word);
983 pAd->TssiPlusBoundaryA[4] = Power.field.Byte0;
984 pAd->TxAgcStepA = Power.field.Byte1;
985 pAd->TxAgcCompensateA = 0;
986 pAd->TssiMinusBoundaryA[0] = pAd->TssiRefA;
987 pAd->TssiPlusBoundaryA[0] = pAd->TssiRefA;
989 // Disable TxAgc if the based value is not right
990 if (pAd->TssiRefA == 0xff)
991 pAd->bAutoTxAgcA = FALSE;
993 DBGPRINT(RT_DEBUG_TRACE,
994 ("E2PROM: A Tssi[-4 .. +4] = %d %d %d %d - %d -%d %d %d %d, step=%d, tuning=%d\n",
995 pAd->TssiMinusBoundaryA[4],
996 pAd->TssiMinusBoundaryA[3],
997 pAd->TssiMinusBoundaryA[2],
998 pAd->TssiMinusBoundaryA[1], pAd->TssiRefA,
999 pAd->TssiPlusBoundaryA[1], pAd->TssiPlusBoundaryA[2],
1000 pAd->TssiPlusBoundaryA[3], pAd->TssiPlusBoundaryA[4],
1001 pAd->TxAgcStepA, pAd->bAutoTxAgcA));
1003 pAd->BbpRssiToDbmDelta = 0x0;
1005 // Read frequency offset setting for RF
1006 RT28xx_EEPROM_READ16(pAd, EEPROM_FREQ_OFFSET, value);
1007 if ((value & 0x00FF) != 0x00FF)
1008 pAd->RfFreqOffset = (ULONG) (value & 0x00FF);
1010 pAd->RfFreqOffset = 0;
1011 DBGPRINT(RT_DEBUG_TRACE,
1012 ("E2PROM: RF FreqOffset=0x%lx \n", pAd->RfFreqOffset));
1014 //CountryRegion byte offset (38h)
1015 value = pAd->EEPROMDefaultValue[2] >> 8; // 2.4G band
1016 value2 = pAd->EEPROMDefaultValue[2] & 0x00FF; // 5G band
1018 if ((value <= REGION_MAXIMUM_BG_BAND)
1019 && (value2 <= REGION_MAXIMUM_A_BAND)) {
1020 pAd->CommonCfg.CountryRegion = ((UCHAR) value) | 0x80;
1021 pAd->CommonCfg.CountryRegionForABand = ((UCHAR) value2) | 0x80;
1022 TmpPhy = pAd->CommonCfg.PhyMode;
1023 pAd->CommonCfg.PhyMode = 0xff;
1024 RTMPSetPhyMode(pAd, TmpPhy);
1028 // Get RSSI Offset on EEPROM 0x9Ah & 0x9Ch.
1029 // The valid value are (-10 ~ 10)
1031 RT28xx_EEPROM_READ16(pAd, EEPROM_RSSI_BG_OFFSET, value);
1032 pAd->BGRssiOffset0 = value & 0x00ff;
1033 pAd->BGRssiOffset1 = (value >> 8);
1034 RT28xx_EEPROM_READ16(pAd, EEPROM_RSSI_BG_OFFSET + 2, value);
1035 pAd->BGRssiOffset2 = value & 0x00ff;
1036 pAd->ALNAGain1 = (value >> 8);
1037 RT28xx_EEPROM_READ16(pAd, EEPROM_LNA_OFFSET, value);
1038 pAd->BLNAGain = value & 0x00ff;
1039 pAd->ALNAGain0 = (value >> 8);
1041 // Validate 11b/g RSSI_0 offset.
1042 if ((pAd->BGRssiOffset0 < -10) || (pAd->BGRssiOffset0 > 10))
1043 pAd->BGRssiOffset0 = 0;
1045 // Validate 11b/g RSSI_1 offset.
1046 if ((pAd->BGRssiOffset1 < -10) || (pAd->BGRssiOffset1 > 10))
1047 pAd->BGRssiOffset1 = 0;
1049 // Validate 11b/g RSSI_2 offset.
1050 if ((pAd->BGRssiOffset2 < -10) || (pAd->BGRssiOffset2 > 10))
1051 pAd->BGRssiOffset2 = 0;
1053 RT28xx_EEPROM_READ16(pAd, EEPROM_RSSI_A_OFFSET, value);
1054 pAd->ARssiOffset0 = value & 0x00ff;
1055 pAd->ARssiOffset1 = (value >> 8);
1056 RT28xx_EEPROM_READ16(pAd, (EEPROM_RSSI_A_OFFSET + 2), value);
1057 pAd->ARssiOffset2 = value & 0x00ff;
1058 pAd->ALNAGain2 = (value >> 8);
1060 if (((UCHAR) pAd->ALNAGain1 == 0xFF) || (pAd->ALNAGain1 == 0x00))
1061 pAd->ALNAGain1 = pAd->ALNAGain0;
1062 if (((UCHAR) pAd->ALNAGain2 == 0xFF) || (pAd->ALNAGain2 == 0x00))
1063 pAd->ALNAGain2 = pAd->ALNAGain0;
1065 // Validate 11a RSSI_0 offset.
1066 if ((pAd->ARssiOffset0 < -10) || (pAd->ARssiOffset0 > 10))
1067 pAd->ARssiOffset0 = 0;
1069 // Validate 11a RSSI_1 offset.
1070 if ((pAd->ARssiOffset1 < -10) || (pAd->ARssiOffset1 > 10))
1071 pAd->ARssiOffset1 = 0;
1073 //Validate 11a RSSI_2 offset.
1074 if ((pAd->ARssiOffset2 < -10) || (pAd->ARssiOffset2 > 10))
1075 pAd->ARssiOffset2 = 0;
1079 // Get TX mixer gain setting
1080 // 0xff are invalid value
1081 // Note: RT30xX default value is 0x00 and will program to RF_R17 only when this value is not zero.
1082 // RT359X default value is 0x02
1084 if (IS_RT30xx(pAd) || IS_RT3572(pAd)) {
1085 RT28xx_EEPROM_READ16(pAd, EEPROM_TXMIXER_GAIN_2_4G, value);
1086 pAd->TxMixerGain24G = 0;
1088 if (value != 0xff) {
1090 pAd->TxMixerGain24G = (UCHAR) value;
1098 RT28xx_EEPROM_READ16(pAd, 0x3a, value);
1099 pAd->LedCntl.word = (value >> 8);
1100 RT28xx_EEPROM_READ16(pAd, EEPROM_LED1_OFFSET, value);
1102 RT28xx_EEPROM_READ16(pAd, EEPROM_LED2_OFFSET, value);
1104 RT28xx_EEPROM_READ16(pAd, EEPROM_LED3_OFFSET, value);
1107 RTMPReadTxPwrPerRate(pAd);
1110 #ifdef RTMP_EFUSE_SUPPORT
1111 RtmpEfuseSupportCheck(pAd);
1112 #endif // RTMP_EFUSE_SUPPORT //
1115 DBGPRINT(RT_DEBUG_TRACE, ("<-- NICReadEEPROMParameters\n"));
1119 ========================================================================
1121 Routine Description:
1122 Set default value from EEPROM
1125 Adapter Pointer to our adapter
1130 IRQL = PASSIVE_LEVEL
1134 ========================================================================
1136 VOID NICInitAsicFromEEPROM(IN PRTMP_ADAPTER pAd)
1141 // EEPROM_ANTENNA_STRUC Antenna;
1142 EEPROM_NIC_CONFIG2_STRUC NicConfig2;
1145 DBGPRINT(RT_DEBUG_TRACE, ("--> NICInitAsicFromEEPROM\n"));
1146 for (i = 3; i < NUM_EEPROM_BBP_PARMS; i++) {
1147 UCHAR BbpRegIdx, BbpValue;
1149 if ((pAd->EEPROMDefaultValue[i] != 0xFFFF)
1150 && (pAd->EEPROMDefaultValue[i] != 0)) {
1151 BbpRegIdx = (UCHAR) (pAd->EEPROMDefaultValue[i] >> 8);
1152 BbpValue = (UCHAR) (pAd->EEPROMDefaultValue[i] & 0xff);
1153 RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BbpRegIdx, BbpValue);
1157 NicConfig2.word = pAd->EEPROMDefaultValue[1];
1160 if ((NicConfig2.word & 0x00ff) == 0xff) {
1161 NicConfig2.word &= 0xff00;
1164 if ((NicConfig2.word >> 8) == 0xff) {
1165 NicConfig2.word &= 0x00ff;
1169 // Save the antenna for future use
1170 pAd->NicConfig2.word = NicConfig2.word;
1173 // set default antenna as main
1174 if (pAd->RfIcType == RFIC_3020)
1175 AsicSetRxAnt(pAd, pAd->RxAnt.Pair1PrimaryRxAnt);
1179 // Send LED Setting to MCU.
1181 if (pAd->LedCntl.word == 0xFF) {
1182 pAd->LedCntl.word = 0x01;
1188 #endif // RTMP_MAC_PCI //
1191 #endif // RTMP_MAC_USB //
1194 AsicSendCommandToMcu(pAd, 0x52, 0xff, (UCHAR) pAd->Led1,
1195 (UCHAR) (pAd->Led1 >> 8));
1196 AsicSendCommandToMcu(pAd, 0x53, 0xff, (UCHAR) pAd->Led2,
1197 (UCHAR) (pAd->Led2 >> 8));
1198 AsicSendCommandToMcu(pAd, 0x54, 0xff, (UCHAR) pAd->Led3,
1199 (UCHAR) (pAd->Led3 >> 8));
1200 AsicSendCommandToMcu(pAd, 0x51, 0xff, 0, pAd->LedCntl.field.Polarity);
1202 pAd->LedIndicatorStrength = 0xFF;
1203 RTMPSetSignalLED(pAd, -100); // Force signal strength Led to be turned off, before link up
1206 // Read Hardware controlled Radio state enable bit
1207 if (NicConfig2.field.HardwareRadioControl == 1) {
1208 pAd->StaCfg.bHardwareRadio = TRUE;
1210 // Read GPIO pin2 as Hardware controlled radio state
1211 RTMP_IO_READ32(pAd, GPIO_CTRL_CFG, &data);
1212 if ((data & 0x04) == 0) {
1213 pAd->StaCfg.bHwRadio = FALSE;
1214 pAd->StaCfg.bRadio = FALSE;
1215 // RTMP_IO_WRITE32(pAd, PWR_PIN_CFG, 0x00001818);
1216 RTMP_SET_FLAG(pAd, fRTMP_ADAPTER_RADIO_OFF);
1219 pAd->StaCfg.bHardwareRadio = FALSE;
1221 if (pAd->StaCfg.bRadio == FALSE) {
1222 RTMPSetLED(pAd, LED_RADIO_OFF);
1224 RTMPSetLED(pAd, LED_RADIO_ON);
1227 AsicSendCommandToMcu(pAd, 0x30, PowerRadioOffCID, 0xff,
1229 AsicCheckCommanOk(pAd, PowerRadioOffCID);
1232 AsicSendCommandToMcu(pAd, 0x30, 0xff, 0xff, 0x02);
1234 AsicSendCommandToMcu(pAd, 0x31, PowerWakeCID, 0x00,
1236 // 2-1. wait command ok.
1237 AsicCheckCommanOk(pAd, PowerWakeCID);
1238 #endif // RTMP_MAC_PCI //
1244 if (IS_RT3090(pAd) || IS_RT3572(pAd) || IS_RT3390(pAd)) {
1245 RTMP_CHIP_OP *pChipOps = &pAd->chipOps;
1246 if (pChipOps->AsicReverseRfFromSleepMode)
1247 pChipOps->AsicReverseRfFromSleepMode(pAd);
1249 // 3090 MCU Wakeup command needs more time to be stable.
1250 // Before stable, don't issue other MCU command to prevent from firmware error.
1252 if ((IS_RT3090(pAd) || IS_RT3572(pAd) || IS_RT3390(pAd))
1253 && IS_VERSION_AFTER_F(pAd)
1254 && (pAd->StaCfg.PSControl.field.rt30xxPowerMode == 3)
1255 && (pAd->StaCfg.PSControl.field.EnableNewPS == TRUE)) {
1256 DBGPRINT(RT_DEBUG_TRACE, ("%s, release Mcu Lock\n", __func__));
1257 RTMP_SEM_LOCK(&pAd->McuCmdLock);
1258 pAd->brt30xxBanMcuCmd = FALSE;
1259 RTMP_SEM_UNLOCK(&pAd->McuCmdLock);
1262 #endif // RTMP_MAC_PCI //
1264 // Turn off patching for cardbus controller
1265 if (NicConfig2.field.CardbusAcceleration == 1) {
1266 // pAd->bTest1 = TRUE;
1269 if (NicConfig2.field.DynamicTxAgcControl == 1)
1270 pAd->bAutoTxAgcA = pAd->bAutoTxAgcG = TRUE;
1272 pAd->bAutoTxAgcA = pAd->bAutoTxAgcG = FALSE;
1274 // Since BBP has been progamed, to make sure BBP setting will be
1275 // upate inside of AsicAntennaSelect, so reset to UNKNOWN_BAND!!
1277 pAd->CommonCfg.BandState = UNKNOWN_BAND;
1279 RTMP_BBP_IO_READ8_BY_REG_ID(pAd, BBP_R3, &BBPR3);
1281 if (pAd->Antenna.field.RxPath == 3) {
1283 } else if (pAd->Antenna.field.RxPath == 2) {
1285 } else if (pAd->Antenna.field.RxPath == 1) {
1288 RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R3, BBPR3);
1291 // Handle the difference when 1T
1292 RTMP_BBP_IO_READ8_BY_REG_ID(pAd, BBP_R1, &BBPR1);
1293 if (pAd->Antenna.field.TxPath == 1) {
1296 RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R1, BBPR1);
1298 DBGPRINT(RT_DEBUG_TRACE,
1299 ("Use Hw Radio Control Pin=%d; if used Pin=%d;\n",
1300 pAd->CommonCfg.bHardwareRadio,
1301 pAd->CommonCfg.bHardwareRadio));
1306 // update registers from EEPROM for RT3071 or later(3572/3592).
1308 if (IS_RT3090(pAd) || IS_RT3572(pAd) || IS_RT3390(pAd)) {
1309 UCHAR RegIdx, RegValue;
1312 // after RT3071, write BBP from EEPROM 0xF0 to 0x102
1313 for (i = 0xF0; i <= 0x102; i = i + 2) {
1315 RT28xx_EEPROM_READ16(pAd, i, value);
1316 if ((value != 0xFFFF) && (value != 0)) {
1317 RegIdx = (UCHAR) (value >> 8);
1318 RegValue = (UCHAR) (value & 0xff);
1319 RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, RegIdx,
1321 DBGPRINT(RT_DEBUG_TRACE,
1322 ("Update BBP Registers from EEPROM(0x%0x), BBP(0x%x) = 0x%x\n",
1323 i, RegIdx, RegValue));
1327 // after RT3071, write RF from EEPROM 0x104 to 0x116
1328 for (i = 0x104; i <= 0x116; i = i + 2) {
1330 RT28xx_EEPROM_READ16(pAd, i, value);
1331 if ((value != 0xFFFF) && (value != 0)) {
1332 RegIdx = (UCHAR) (value >> 8);
1333 RegValue = (UCHAR) (value & 0xff);
1334 RT30xxWriteRFRegister(pAd, RegIdx, RegValue);
1335 DBGPRINT(RT_DEBUG_TRACE,
1336 ("Update RF Registers from EEPROM0x%x), BBP(0x%x) = 0x%x\n",
1337 i, RegIdx, RegValue));
1342 #endif // RTMP_MAC_USB //
1344 DBGPRINT(RT_DEBUG_TRACE,
1345 ("TxPath = %d, RxPath = %d, RFIC=%d, Polar+LED mode=%x\n",
1346 pAd->Antenna.field.TxPath, pAd->Antenna.field.RxPath,
1347 pAd->RfIcType, pAd->LedCntl.word));
1348 DBGPRINT(RT_DEBUG_TRACE, ("<-- NICInitAsicFromEEPROM\n"));
1352 ========================================================================
1354 Routine Description:
1355 Initialize NIC hardware
1358 Adapter Pointer to our adapter
1363 IRQL = PASSIVE_LEVEL
1367 ========================================================================
1369 NDIS_STATUS NICInitializeAdapter(IN PRTMP_ADAPTER pAd, IN BOOLEAN bHardReset)
1371 NDIS_STATUS Status = NDIS_STATUS_SUCCESS;
1372 WPDMA_GLO_CFG_STRUC GloCfg;
1375 DELAY_INT_CFG_STRUC IntCfg;
1376 #endif // RTMP_MAC_PCI //
1377 // INT_MASK_CSR_STRUC IntMask;
1379 AC_TXOP_CSR0_STRUC csr0;
1381 DBGPRINT(RT_DEBUG_TRACE, ("--> NICInitializeAdapter\n"));
1383 // 3. Set DMA global configuration except TX_DMA_EN and RX_DMA_EN bits:
1387 RTMP_IO_READ32(pAd, WPDMA_GLO_CFG, &GloCfg.word);
1388 if ((GloCfg.field.TxDMABusy == 0)
1389 && (GloCfg.field.RxDMABusy == 0))
1392 RTMPusecDelay(1000);
1395 DBGPRINT(RT_DEBUG_TRACE,
1396 ("<== DMA offset 0x208 = 0x%x\n", GloCfg.word));
1397 GloCfg.word &= 0xff0;
1398 GloCfg.field.EnTXWriteBackDDONE = 1;
1399 RTMP_IO_WRITE32(pAd, WPDMA_GLO_CFG, GloCfg.word);
1401 // Record HW Beacon offset
1402 pAd->BeaconOffset[0] = HW_BEACON_BASE0;
1403 pAd->BeaconOffset[1] = HW_BEACON_BASE1;
1404 pAd->BeaconOffset[2] = HW_BEACON_BASE2;
1405 pAd->BeaconOffset[3] = HW_BEACON_BASE3;
1406 pAd->BeaconOffset[4] = HW_BEACON_BASE4;
1407 pAd->BeaconOffset[5] = HW_BEACON_BASE5;
1408 pAd->BeaconOffset[6] = HW_BEACON_BASE6;
1409 pAd->BeaconOffset[7] = HW_BEACON_BASE7;
1412 // write all shared Ring's base address into ASIC
1415 // asic simulation sequence put this ahead before loading firmware.
1416 // pbf hardware reset
1418 RTMP_IO_WRITE32(pAd, WPDMA_RST_IDX, 0x1003f); // 0x10000 for reset rx, 0x3f resets all 6 tx rings.
1419 RTMP_IO_WRITE32(pAd, PBF_SYS_CTRL, 0xe1f);
1420 RTMP_IO_WRITE32(pAd, PBF_SYS_CTRL, 0xe00);
1421 #endif // RTMP_MAC_PCI //
1423 // Initialze ASIC for TX & Rx operation
1424 if (NICInitializeAsic(pAd, bHardReset) != NDIS_STATUS_SUCCESS) {
1426 NICLoadFirmware(pAd);
1429 return NDIS_STATUS_FAILURE;
1433 // Write AC_BK base address register
1435 RTMP_GetPhysicalAddressLow(pAd->TxRing[QID_AC_BK].Cell[0].AllocPa);
1436 RTMP_IO_WRITE32(pAd, TX_BASE_PTR1, Value);
1437 DBGPRINT(RT_DEBUG_TRACE, ("--> TX_BASE_PTR1 : 0x%x\n", Value));
1439 // Write AC_BE base address register
1441 RTMP_GetPhysicalAddressLow(pAd->TxRing[QID_AC_BE].Cell[0].AllocPa);
1442 RTMP_IO_WRITE32(pAd, TX_BASE_PTR0, Value);
1443 DBGPRINT(RT_DEBUG_TRACE, ("--> TX_BASE_PTR0 : 0x%x\n", Value));
1445 // Write AC_VI base address register
1447 RTMP_GetPhysicalAddressLow(pAd->TxRing[QID_AC_VI].Cell[0].AllocPa);
1448 RTMP_IO_WRITE32(pAd, TX_BASE_PTR2, Value);
1449 DBGPRINT(RT_DEBUG_TRACE, ("--> TX_BASE_PTR2 : 0x%x\n", Value));
1451 // Write AC_VO base address register
1453 RTMP_GetPhysicalAddressLow(pAd->TxRing[QID_AC_VO].Cell[0].AllocPa);
1454 RTMP_IO_WRITE32(pAd, TX_BASE_PTR3, Value);
1455 DBGPRINT(RT_DEBUG_TRACE, ("--> TX_BASE_PTR3 : 0x%x\n", Value));
1457 // Write MGMT_BASE_CSR register
1458 Value = RTMP_GetPhysicalAddressLow(pAd->MgmtRing.Cell[0].AllocPa);
1459 RTMP_IO_WRITE32(pAd, TX_BASE_PTR5, Value);
1460 DBGPRINT(RT_DEBUG_TRACE, ("--> TX_BASE_PTR5 : 0x%x\n", Value));
1462 // Write RX_BASE_CSR register
1463 Value = RTMP_GetPhysicalAddressLow(pAd->RxRing.Cell[0].AllocPa);
1464 RTMP_IO_WRITE32(pAd, RX_BASE_PTR, Value);
1465 DBGPRINT(RT_DEBUG_TRACE, ("--> RX_BASE_PTR : 0x%x\n", Value));
1467 // Init RX Ring index pointer
1468 pAd->RxRing.RxSwReadIdx = 0;
1469 pAd->RxRing.RxCpuIdx = RX_RING_SIZE - 1;
1470 RTMP_IO_WRITE32(pAd, RX_CRX_IDX, pAd->RxRing.RxCpuIdx);
1472 // Init TX rings index pointer
1474 for (i = 0; i < NUM_OF_TX_RING; i++) {
1475 pAd->TxRing[i].TxSwFreeIdx = 0;
1476 pAd->TxRing[i].TxCpuIdx = 0;
1477 RTMP_IO_WRITE32(pAd, (TX_CTX_IDX0 + i * 0x10),
1478 pAd->TxRing[i].TxCpuIdx);
1482 // init MGMT ring index pointer
1483 pAd->MgmtRing.TxSwFreeIdx = 0;
1484 pAd->MgmtRing.TxCpuIdx = 0;
1485 RTMP_IO_WRITE32(pAd, TX_MGMTCTX_IDX, pAd->MgmtRing.TxCpuIdx);
1488 // set each Ring's SIZE into ASIC. Descriptor Size is fixed by design.
1491 // Write TX_RING_CSR0 register
1492 Value = TX_RING_SIZE;
1493 RTMP_IO_WRITE32(pAd, TX_MAX_CNT0, Value);
1494 RTMP_IO_WRITE32(pAd, TX_MAX_CNT1, Value);
1495 RTMP_IO_WRITE32(pAd, TX_MAX_CNT2, Value);
1496 RTMP_IO_WRITE32(pAd, TX_MAX_CNT3, Value);
1497 RTMP_IO_WRITE32(pAd, TX_MAX_CNT4, Value);
1498 Value = MGMT_RING_SIZE;
1499 RTMP_IO_WRITE32(pAd, TX_MGMTMAX_CNT, Value);
1501 // Write RX_RING_CSR register
1502 Value = RX_RING_SIZE;
1503 RTMP_IO_WRITE32(pAd, RX_MAX_CNT, Value);
1504 #endif // RTMP_MAC_PCI //
1508 RTMP_IO_WRITE32(pAd, WMM_TXOP0_CFG, csr0.word);
1509 if (pAd->CommonCfg.PhyMode == PHY_11B) {
1510 csr0.field.Ac0Txop = 192; // AC_VI: 192*32us ~= 6ms
1511 csr0.field.Ac1Txop = 96; // AC_VO: 96*32us ~= 3ms
1513 csr0.field.Ac0Txop = 96; // AC_VI: 96*32us ~= 3ms
1514 csr0.field.Ac1Txop = 48; // AC_VO: 48*32us ~= 1.5ms
1516 RTMP_IO_WRITE32(pAd, WMM_TXOP1_CFG, csr0.word);
1519 // 3. Set DMA global configuration except TX_DMA_EN and RX_DMA_EN bits:
1522 RTMP_IO_READ32(pAd, WPDMA_GLO_CFG, &GloCfg.word);
1523 if ((GloCfg.field.TxDMABusy == 0)
1524 && (GloCfg.field.RxDMABusy == 0))
1527 RTMPusecDelay(1000);
1531 GloCfg.word &= 0xff0;
1532 GloCfg.field.EnTXWriteBackDDONE = 1;
1533 RTMP_IO_WRITE32(pAd, WPDMA_GLO_CFG, GloCfg.word);
1536 RTMP_IO_WRITE32(pAd, DELAY_INT_CFG, IntCfg.word);
1537 #endif // RTMP_MAC_PCI //
1541 // Status = NICLoadFirmware(pAd);
1543 DBGPRINT(RT_DEBUG_TRACE, ("<-- NICInitializeAdapter\n"));
1548 ========================================================================
1550 Routine Description:
1554 Adapter Pointer to our adapter
1559 IRQL = PASSIVE_LEVEL
1563 ========================================================================
1565 NDIS_STATUS NICInitializeAsic(IN PRTMP_ADAPTER pAd, IN BOOLEAN bHardReset)
1569 UINT32 MacCsr12 = 0, Counter = 0;
1574 #endif // RTMP_MAC_USB //
1582 DBGPRINT(RT_DEBUG_TRACE, ("--> NICInitializeAsic\n"));
1585 RTMP_IO_WRITE32(pAd, PWR_PIN_CFG, 0x3); // To fix driver disable/enable hang issue when radio off
1586 if (bHardReset == TRUE) {
1587 RTMP_IO_WRITE32(pAd, MAC_SYS_CTRL, 0x3);
1589 RTMP_IO_WRITE32(pAd, MAC_SYS_CTRL, 0x1);
1591 RTMP_IO_WRITE32(pAd, MAC_SYS_CTRL, 0x0);
1592 // Initialize MAC register to default value
1593 for (Index = 0; Index < NUM_MAC_REG_PARMS; Index++) {
1594 RTMP_IO_WRITE32(pAd, MACRegTable[Index].Register,
1595 MACRegTable[Index].Value);
1599 for (Index = 0; Index < NUM_STA_MAC_REG_PARMS; Index++) {
1600 RTMP_IO_WRITE32(pAd, STAMACRegTable[Index].Register,
1601 STAMACRegTable[Index].Value);
1604 #endif // RTMP_MAC_PCI //
1607 // Make sure MAC gets ready after NICLoadFirmware().
1611 //To avoid hang-on issue when interface up in kernel 2.4,
1612 //we use a local variable "MacCsr0" instead of using "pAd->MACVersion" directly.
1614 RTMP_IO_READ32(pAd, MAC_CSR0, &MacCsr0);
1616 if ((MacCsr0 != 0x00) && (MacCsr0 != 0xFFFFFFFF))
1620 } while (Index++ < 100);
1622 pAd->MACVersion = MacCsr0;
1623 DBGPRINT(RT_DEBUG_TRACE,
1624 ("MAC_CSR0 [ Ver:Rev=0x%08x]\n", pAd->MACVersion));
1625 // turn on bit13 (set to zero) after rt2860D. This is to solve high-current issue.
1626 RTMP_IO_READ32(pAd, PBF_SYS_CTRL, &MacCsr12);
1627 MacCsr12 &= (~0x2000);
1628 RTMP_IO_WRITE32(pAd, PBF_SYS_CTRL, MacCsr12);
1630 RTMP_IO_WRITE32(pAd, MAC_SYS_CTRL, 0x3);
1631 RTMP_IO_WRITE32(pAd, USB_DMA_CFG, 0x0);
1632 Status = RTUSBVenderReset(pAd);
1634 RTMP_IO_WRITE32(pAd, MAC_SYS_CTRL, 0x0);
1636 // Initialize MAC register to default value
1637 for (Index = 0; Index < NUM_MAC_REG_PARMS; Index++) {
1639 if ((MACRegTable[Index].Register == TX_SW_CFG0)
1640 && (IS_RT3070(pAd) || IS_RT3071(pAd) || IS_RT3572(pAd)
1641 || IS_RT3090(pAd) || IS_RT3390(pAd))) {
1642 MACRegTable[Index].Value = 0x00000400;
1645 RTMP_IO_WRITE32(pAd, (USHORT) MACRegTable[Index].Register,
1646 MACRegTable[Index].Value);
1650 for (Index = 0; Index < NUM_STA_MAC_REG_PARMS; Index++) {
1651 RTMP_IO_WRITE32(pAd,
1652 (USHORT) STAMACRegTable[Index].Register,
1653 STAMACRegTable[Index].Value);
1656 #endif // RTMP_MAC_USB //
1659 // Initialize RT3070 serial MAC registers which is different from RT2870 serial
1660 if (IS_RT3090(pAd) || IS_RT3572(pAd) || IS_RT3390(pAd)) {
1661 RTMP_IO_WRITE32(pAd, TX_SW_CFG1, 0);
1663 // RT3071 version E has fixed this issue
1664 if ((pAd->MACVersion & 0xffff) < 0x0211) {
1665 if (pAd->NicConfig2.field.DACTestBit == 1) {
1666 RTMP_IO_WRITE32(pAd, TX_SW_CFG2, 0x2C); // To fix throughput drop drastically
1668 RTMP_IO_WRITE32(pAd, TX_SW_CFG2, 0x0F); // To fix throughput drop drastically
1671 RTMP_IO_WRITE32(pAd, TX_SW_CFG2, 0x0);
1673 } else if (IS_RT3070(pAd)) {
1674 if (((pAd->MACVersion & 0xffff) < 0x0201)) {
1675 RTMP_IO_WRITE32(pAd, TX_SW_CFG1, 0);
1676 RTMP_IO_WRITE32(pAd, TX_SW_CFG2, 0x2C); // To fix throughput drop drastically
1678 RTMP_IO_WRITE32(pAd, TX_SW_CFG2, 0);
1684 // Before program BBP, we need to wait BBP/RF get wake up.
1688 RTMP_IO_READ32(pAd, MAC_STATUS_CFG, &MacCsr12);
1690 if ((MacCsr12 & 0x03) == 0) // if BB.RF is stable
1693 DBGPRINT(RT_DEBUG_TRACE,
1694 ("Check MAC_STATUS_CFG = Busy = %x\n", MacCsr12));
1695 RTMPusecDelay(1000);
1696 } while (Index++ < 100);
1698 // The commands to firmware should be after these commands, these commands will init firmware
1699 // PCI and USB are not the same because PCI driver needs to wait for PCI bus ready
1700 RTMP_IO_WRITE32(pAd, H2M_BBP_AGENT, 0); // initialize BBP R/W access agent
1701 RTMP_IO_WRITE32(pAd, H2M_MAILBOX_CSR, 0);
1703 //2008/11/28:KH add to fix the dead rf frequency offset bug<--
1704 AsicSendCommandToMcu(pAd, 0x72, 0, 0, 0);
1705 //2008/11/28:KH add to fix the dead rf frequency offset bug-->
1707 RTMPusecDelay(1000);
1709 // Read BBP register, make sure BBP is up and running before write new data
1712 RTMP_BBP_IO_READ8_BY_REG_ID(pAd, BBP_R0, &R0);
1713 DBGPRINT(RT_DEBUG_TRACE, ("BBP version = %x\n", R0));
1714 } while ((++Index < 20) && ((R0 == 0xff) || (R0 == 0x00)));
1715 //ASSERT(Index < 20); //this will cause BSOD on Check-build driver
1717 if ((R0 == 0xff) || (R0 == 0x00))
1718 return NDIS_STATUS_FAILURE;
1720 // Initialize BBP register to default value
1721 for (Index = 0; Index < NUM_BBP_REG_PARMS; Index++) {
1722 RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBPRegTable[Index].Register,
1723 BBPRegTable[Index].Value);
1727 // TODO: shiang, check MACVersion, currently, rbus-based chip use this.
1728 if (pAd->MACVersion == 0x28720200) {
1732 //disable MLD by Bruce 20080704
1733 //BBP_IO_READ8_BY_REG_ID(pAd, BBP_R105, &value);
1734 //BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R105, value | 4);
1736 //Maximum PSDU length from 16K to 32K bytes
1737 RTMP_IO_READ32(pAd, MAX_LEN_CFG, &value2);
1738 value2 &= ~(0x3 << 12);
1739 value2 |= (0x2 << 12);
1740 RTMP_IO_WRITE32(pAd, MAX_LEN_CFG, value2);
1742 #endif // RTMP_MAC_PCI //
1744 // for rt2860E and after, init BBP_R84 with 0x19. This is for extension channel overlapping IOT.
1745 // RT3090 should not program BBP R84 to 0x19, otherwise TX will block.
1746 //3070/71/72,3090,3090A( are included in RT30xx),3572,3390
1747 if (((pAd->MACVersion & 0xffff) != 0x0101)
1748 && !(IS_RT30xx(pAd) || IS_RT3572(pAd) || IS_RT3390(pAd)))
1749 RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R84, 0x19);
1752 // add by johnli, RF power sequence setup
1753 if (IS_RT30xx(pAd) || IS_RT3572(pAd) || IS_RT3390(pAd)) { //update for RT3070/71/72/90/91/92,3572,3390.
1754 RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R79, 0x13);
1755 RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R80, 0x05);
1756 RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R81, 0x33);
1759 if (IS_RT3090(pAd) || IS_RT3390(pAd)) // RT309x, RT3071/72
1762 if ((pAd->MACVersion & 0xffff) >= 0x0211) {
1763 RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R103, 0xc0);
1765 // improve power consumption
1766 RTMP_BBP_IO_READ8_BY_REG_ID(pAd, BBP_R138, &bbpreg);
1767 if (pAd->Antenna.field.TxPath == 1) {
1768 // turn off tx DAC_1
1769 bbpreg = (bbpreg | 0x20);
1772 if (pAd->Antenna.field.RxPath == 1) {
1773 // turn off tx ADC_1
1776 RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R138, bbpreg);
1778 // improve power consumption in RT3071 Ver.E
1779 if ((pAd->MACVersion & 0xffff) >= 0x0211) {
1780 RTMP_BBP_IO_READ8_BY_REG_ID(pAd, BBP_R31, &bbpreg);
1782 RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R31, bbpreg);
1784 } else if (IS_RT3070(pAd)) {
1785 if ((pAd->MACVersion & 0xffff) >= 0x0201) {
1787 RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R103, 0xc0);
1789 // improve power consumption in RT3070 Ver.F
1790 RTMP_BBP_IO_READ8_BY_REG_ID(pAd, BBP_R31, &bbpreg);
1792 RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R31, bbpreg);
1794 // TX_LO1_en, RF R17 register Bit 3 to 0
1795 RT30xxReadRFRegister(pAd, RF_R17, &RFValue);
1797 // to fix rx long range issue
1798 if (pAd->NicConfig2.field.ExternalLNAForG == 0) {
1801 // set RF_R17_bit[2:0] equal to EEPROM setting at 0x48h
1802 if (pAd->TxMixerGain24G >= 1) {
1803 RFValue &= (~0x7); // clean bit [2:0]
1804 RFValue |= pAd->TxMixerGain24G;
1806 RT30xxWriteRFRegister(pAd, RF_R17, RFValue);
1811 if (pAd->MACVersion == 0x28600100) {
1812 RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R69, 0x16);
1813 RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R73, 0x12);
1816 if (pAd->MACVersion >= RALINK_2880E_VERSION && pAd->MACVersion < RALINK_3070_VERSION) // 3*3
1818 // enlarge MAX_LEN_CFG
1820 RTMP_IO_READ32(pAd, MAX_LEN_CFG, &csr);
1823 RTMP_IO_WRITE32(pAd, MAX_LEN_CFG, csr);
1828 { 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0, 0 };
1830 //Initialize WCID table
1832 for (Index = 0; Index < 254; Index++) {
1833 RTUSBMultiWrite(pAd,
1834 (USHORT) (MAC_WCID_BASE + Index * 8),
1838 #endif // RTMP_MAC_USB //
1840 // Add radio off control
1842 if (pAd->StaCfg.bRadio == FALSE) {
1843 // RTMP_IO_WRITE32(pAd, PWR_PIN_CFG, 0x00001818);
1844 RTMP_SET_FLAG(pAd, fRTMP_ADAPTER_RADIO_OFF);
1845 DBGPRINT(RT_DEBUG_TRACE, ("Set Radio Off\n"));
1849 // Clear raw counters
1850 RTMP_IO_READ32(pAd, RX_STA_CNT0, &Counter);
1851 RTMP_IO_READ32(pAd, RX_STA_CNT1, &Counter);
1852 RTMP_IO_READ32(pAd, RX_STA_CNT2, &Counter);
1853 RTMP_IO_READ32(pAd, TX_STA_CNT0, &Counter);
1854 RTMP_IO_READ32(pAd, TX_STA_CNT1, &Counter);
1855 RTMP_IO_READ32(pAd, TX_STA_CNT2, &Counter);
1857 // ASIC will keep garbage value after boot
1858 // Clear all shared key table when initial
1859 // This routine can be ignored in radio-ON/OFF operation.
1861 for (KeyIdx = 0; KeyIdx < 4; KeyIdx++) {
1862 RTMP_IO_WRITE32(pAd, SHARED_KEY_MODE_BASE + 4 * KeyIdx,
1866 // Clear all pairwise key table when initial
1867 for (KeyIdx = 0; KeyIdx < 256; KeyIdx++) {
1868 RTMP_IO_WRITE32(pAd,
1869 MAC_WCID_ATTRIBUTE_BASE +
1870 (KeyIdx * HW_WCID_ATTRI_SIZE), 1);
1873 // assert HOST ready bit
1874 // RTMP_IO_WRITE32(pAd, MAC_CSR1, 0x0); // 2004-09-14 asked by Mark
1875 // RTMP_IO_WRITE32(pAd, MAC_CSR1, 0x4);
1877 // It isn't necessary to clear this space when not hard reset.
1878 if (bHardReset == TRUE) {
1879 // clear all on-chip BEACON frame space
1880 for (apidx = 0; apidx < HW_BEACON_MAX_COUNT; apidx++) {
1881 for (i = 0; i < HW_BEACON_OFFSET >> 2; i += 4)
1882 RTMP_IO_WRITE32(pAd,
1883 pAd->BeaconOffset[apidx] + i,
1888 AsicDisableSync(pAd);
1889 // Clear raw counters
1890 RTMP_IO_READ32(pAd, RX_STA_CNT0, &Counter);
1891 RTMP_IO_READ32(pAd, RX_STA_CNT1, &Counter);
1892 RTMP_IO_READ32(pAd, RX_STA_CNT2, &Counter);
1893 RTMP_IO_READ32(pAd, TX_STA_CNT0, &Counter);
1894 RTMP_IO_READ32(pAd, TX_STA_CNT1, &Counter);
1895 RTMP_IO_READ32(pAd, TX_STA_CNT2, &Counter);
1896 // Default PCI clock cycle per ms is different as default setting, which is based on PCI.
1897 RTMP_IO_READ32(pAd, USB_CYC_CFG, &Counter);
1898 Counter &= 0xffffff00;
1899 Counter |= 0x000001e;
1900 RTMP_IO_WRITE32(pAd, USB_CYC_CFG, Counter);
1901 #endif // RTMP_MAC_USB //
1904 // for rt2860E and after, init TXOP_CTRL_CFG with 0x583f. This is for extension channel overlapping IOT.
1905 if ((pAd->MACVersion & 0xffff) != 0x0101)
1906 RTMP_IO_WRITE32(pAd, TXOP_CTRL_CFG, 0x583f);
1909 DBGPRINT(RT_DEBUG_TRACE, ("<-- NICInitializeAsic\n"));
1910 return NDIS_STATUS_SUCCESS;
1914 ========================================================================
1916 Routine Description:
1920 Adapter Pointer to our adapter
1925 IRQL = PASSIVE_LEVEL
1928 Reset NIC to initial state AS IS system boot up time.
1930 ========================================================================
1932 VOID NICIssueReset(IN PRTMP_ADAPTER pAd)
1935 DBGPRINT(RT_DEBUG_TRACE, ("--> NICIssueReset\n"));
1937 // Abort Tx, prevent ASIC from writing to Host memory
1938 //RTMP_IO_WRITE32(pAd, TX_CNTL_CSR, 0x001f0000);
1940 // Disable Rx, register value supposed will remain after reset
1941 RTMP_IO_READ32(pAd, MAC_SYS_CTRL, &Value);
1942 Value &= (0xfffffff3);
1943 RTMP_IO_WRITE32(pAd, MAC_SYS_CTRL, Value);
1945 // Issue reset and clear from reset state
1946 RTMP_IO_WRITE32(pAd, MAC_SYS_CTRL, 0x03); // 2004-09-17 change from 0x01
1947 RTMP_IO_WRITE32(pAd, MAC_SYS_CTRL, 0x00);
1949 DBGPRINT(RT_DEBUG_TRACE, ("<-- NICIssueReset\n"));
1953 ========================================================================
1955 Routine Description:
1956 Check ASIC registers and find any reason the system might hang
1959 Adapter Pointer to our adapter
1964 IRQL = DISPATCH_LEVEL
1966 ========================================================================
1968 BOOLEAN NICCheckForHang(IN PRTMP_ADAPTER pAd)
1973 VOID NICUpdateFifoStaCounters(IN PRTMP_ADAPTER pAd)
1975 TX_STA_FIFO_STRUC StaFifo;
1976 MAC_TABLE_ENTRY *pEntry;
1978 UCHAR pid = 0, wcid = 0;
1983 RTMP_IO_READ32(pAd, TX_STA_FIFO, &StaFifo.word);
1985 if (StaFifo.field.bValid == 0)
1988 wcid = (UCHAR) StaFifo.field.wcid;
1990 /* ignore NoACK and MGMT frame use 0xFF as WCID */
1991 if ((StaFifo.field.TxAckRequired == 0)
1992 || (wcid >= MAX_LEN_OF_MAC_TABLE)) {
1997 /* PID store Tx MCS Rate */
1998 pid = (UCHAR) StaFifo.field.PidType;
2000 pEntry = &pAd->MacTab.Content[wcid];
2002 pEntry->DebugFIFOCount++;
2004 if (StaFifo.field.TxBF) // 3*3
2005 pEntry->TxBFCount++;
2007 if (!StaFifo.field.TxSuccess) {
2008 pEntry->FIFOCount++;
2009 pEntry->OneSecTxFailCount++;
2011 if (pEntry->FIFOCount >= 1) {
2012 DBGPRINT(RT_DEBUG_TRACE, ("#"));
2013 pEntry->NoBADataCountDown = 64;
2015 if (pEntry->PsMode == PWR_ACTIVE) {
2017 for (tid = 0; tid < NUM_OF_TID; tid++) {
2018 BAOriSessionTearDown(pAd,
2025 // Update the continuous transmission counter except PS mode
2026 pEntry->ContinueTxFailCnt++;
2028 // Clear the FIFOCount when sta in Power Save mode. Basically we assume
2029 // this tx error happened due to sta just go to sleep.
2030 pEntry->FIFOCount = 0;
2031 pEntry->ContinueTxFailCnt = 0;
2033 //pEntry->FIFOCount = 0;
2035 //pEntry->bSendBAR = TRUE;
2037 if ((pEntry->PsMode != PWR_SAVE)
2038 && (pEntry->NoBADataCountDown > 0)) {
2039 pEntry->NoBADataCountDown--;
2040 if (pEntry->NoBADataCountDown == 0) {
2041 DBGPRINT(RT_DEBUG_TRACE, ("@\n"));
2045 pEntry->FIFOCount = 0;
2046 pEntry->OneSecTxNoRetryOkCount++;
2047 // update NoDataIdleCount when sucessful send packet to STA.
2048 pEntry->NoDataIdleCount = 0;
2049 pEntry->ContinueTxFailCnt = 0;
2052 succMCS = StaFifo.field.SuccessRate & 0x7F;
2054 reTry = pid - succMCS;
2056 if (StaFifo.field.TxSuccess) {
2057 pEntry->TXMCSExpected[pid]++;
2058 if (pid == succMCS) {
2059 pEntry->TXMCSSuccessful[pid]++;
2061 pEntry->TXMCSAutoFallBack[pid][succMCS]++;
2064 pEntry->TXMCSFailed[pid]++;
2068 if ((pid >= 12) && succMCS <= 7) {
2071 pEntry->OneSecTxRetryOkCount += reTry;
2075 // ASIC store 16 stack
2076 } while (i < (2 * TX_RING_SIZE));
2081 ========================================================================
2083 Routine Description:
2084 Read statistical counters from hardware registers and record them
2085 in software variables for later on query
2088 pAd Pointer to our adapter
2093 IRQL = DISPATCH_LEVEL
2095 ========================================================================
2097 VOID NICUpdateRawCounters(IN PRTMP_ADAPTER pAd)
2099 UINT32 OldValue; //, Value2;
2100 //ULONG PageSum, OneSecTransmitCount;
2101 //ULONG TxErrorRatio, Retry, Fail;
2102 RX_STA_CNT0_STRUC RxStaCnt0;
2103 RX_STA_CNT1_STRUC RxStaCnt1;
2104 RX_STA_CNT2_STRUC RxStaCnt2;
2105 TX_STA_CNT0_STRUC TxStaCnt0;
2106 TX_STA_CNT1_STRUC StaTx1;
2107 TX_STA_CNT2_STRUC StaTx2;
2108 TX_AGG_CNT_STRUC TxAggCnt;
2109 TX_AGG_CNT0_STRUC TxAggCnt0;
2110 TX_AGG_CNT1_STRUC TxAggCnt1;
2111 TX_AGG_CNT2_STRUC TxAggCnt2;
2112 TX_AGG_CNT3_STRUC TxAggCnt3;
2113 TX_AGG_CNT4_STRUC TxAggCnt4;
2114 TX_AGG_CNT5_STRUC TxAggCnt5;
2115 TX_AGG_CNT6_STRUC TxAggCnt6;
2116 TX_AGG_CNT7_STRUC TxAggCnt7;
2117 COUNTER_RALINK *pRalinkCounters;
2119 pRalinkCounters = &pAd->RalinkCounters;
2121 RTMP_IO_READ32(pAd, RX_STA_CNT0, &RxStaCnt0.word);
2122 RTMP_IO_READ32(pAd, RX_STA_CNT2, &RxStaCnt2.word);
2125 RTMP_IO_READ32(pAd, RX_STA_CNT1, &RxStaCnt1.word);
2126 // Update RX PLCP error counter
2127 pAd->PrivateInfo.PhyRxErrCnt += RxStaCnt1.field.PlcpErr;
2128 // Update False CCA counter
2129 pAd->RalinkCounters.OneSecFalseCCACnt +=
2130 RxStaCnt1.field.FalseCca;
2133 // Update FCS counters
2134 OldValue = pAd->WlanCounters.FCSErrorCount.u.LowPart;
2135 pAd->WlanCounters.FCSErrorCount.u.LowPart += (RxStaCnt0.field.CrcErr); // >> 7);
2136 if (pAd->WlanCounters.FCSErrorCount.u.LowPart < OldValue)
2137 pAd->WlanCounters.FCSErrorCount.u.HighPart++;
2139 // Add FCS error count to private counters
2140 pRalinkCounters->OneSecRxFcsErrCnt += RxStaCnt0.field.CrcErr;
2141 OldValue = pRalinkCounters->RealFcsErrCount.u.LowPart;
2142 pRalinkCounters->RealFcsErrCount.u.LowPart += RxStaCnt0.field.CrcErr;
2143 if (pRalinkCounters->RealFcsErrCount.u.LowPart < OldValue)
2144 pRalinkCounters->RealFcsErrCount.u.HighPart++;
2146 // Update Duplicate Rcv check
2147 pRalinkCounters->DuplicateRcv += RxStaCnt2.field.RxDupliCount;
2148 pAd->WlanCounters.FrameDuplicateCount.u.LowPart +=
2149 RxStaCnt2.field.RxDupliCount;
2150 // Update RX Overflow counter
2151 pAd->Counters8023.RxNoBuffer += (RxStaCnt2.field.RxFifoOverflowCount);
2153 //pAd->RalinkCounters.RxCount = 0;
2155 if (pRalinkCounters->RxCount != pAd->watchDogRxCnt) {
2156 pAd->watchDogRxCnt = pRalinkCounters->RxCount;
2157 pAd->watchDogRxOverFlowCnt = 0;
2159 if (RxStaCnt2.field.RxFifoOverflowCount)
2160 pAd->watchDogRxOverFlowCnt++;
2162 pAd->watchDogRxOverFlowCnt = 0;
2164 #endif // RTMP_MAC_USB //
2166 //if (!OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_TX_RATE_SWITCH_ENABLED) ||
2167 // (OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_TX_RATE_SWITCH_ENABLED) && (pAd->MacTab.Size != 1)))
2168 if (!pAd->bUpdateBcnCntDone) {
2169 // Update BEACON sent count
2170 RTMP_IO_READ32(pAd, TX_STA_CNT0, &TxStaCnt0.word);
2171 RTMP_IO_READ32(pAd, TX_STA_CNT1, &StaTx1.word);
2172 RTMP_IO_READ32(pAd, TX_STA_CNT2, &StaTx2.word);
2173 pRalinkCounters->OneSecBeaconSentCnt +=
2174 TxStaCnt0.field.TxBeaconCount;
2175 pRalinkCounters->OneSecTxRetryOkCount +=
2176 StaTx1.field.TxRetransmit;
2177 pRalinkCounters->OneSecTxNoRetryOkCount +=
2178 StaTx1.field.TxSuccess;
2179 pRalinkCounters->OneSecTxFailCount +=
2180 TxStaCnt0.field.TxFailCount;
2181 pAd->WlanCounters.TransmittedFragmentCount.u.LowPart +=
2182 StaTx1.field.TxSuccess;
2183 pAd->WlanCounters.RetryCount.u.LowPart +=
2184 StaTx1.field.TxRetransmit;
2185 pAd->WlanCounters.FailedCount.u.LowPart +=
2186 TxStaCnt0.field.TxFailCount;
2189 //if (pAd->bStaFifoTest == TRUE)
2191 RTMP_IO_READ32(pAd, TX_AGG_CNT, &TxAggCnt.word);
2192 RTMP_IO_READ32(pAd, TX_AGG_CNT0, &TxAggCnt0.word);
2193 RTMP_IO_READ32(pAd, TX_AGG_CNT1, &TxAggCnt1.word);
2194 RTMP_IO_READ32(pAd, TX_AGG_CNT2, &TxAggCnt2.word);
2195 RTMP_IO_READ32(pAd, TX_AGG_CNT3, &TxAggCnt3.word);
2196 RTMP_IO_READ32(pAd, TX_AGG_CNT4, &TxAggCnt4.word);
2197 RTMP_IO_READ32(pAd, TX_AGG_CNT5, &TxAggCnt5.word);
2198 RTMP_IO_READ32(pAd, TX_AGG_CNT6, &TxAggCnt6.word);
2199 RTMP_IO_READ32(pAd, TX_AGG_CNT7, &TxAggCnt7.word);
2200 pRalinkCounters->TxAggCount += TxAggCnt.field.AggTxCount;
2201 pRalinkCounters->TxNonAggCount += TxAggCnt.field.NonAggTxCount;
2202 pRalinkCounters->TxAgg1MPDUCount +=
2203 TxAggCnt0.field.AggSize1Count;
2204 pRalinkCounters->TxAgg2MPDUCount +=
2205 TxAggCnt0.field.AggSize2Count;
2207 pRalinkCounters->TxAgg3MPDUCount +=
2208 TxAggCnt1.field.AggSize3Count;
2209 pRalinkCounters->TxAgg4MPDUCount +=
2210 TxAggCnt1.field.AggSize4Count;
2211 pRalinkCounters->TxAgg5MPDUCount +=
2212 TxAggCnt2.field.AggSize5Count;
2213 pRalinkCounters->TxAgg6MPDUCount +=
2214 TxAggCnt2.field.AggSize6Count;
2216 pRalinkCounters->TxAgg7MPDUCount +=
2217 TxAggCnt3.field.AggSize7Count;
2218 pRalinkCounters->TxAgg8MPDUCount +=
2219 TxAggCnt3.field.AggSize8Count;
2220 pRalinkCounters->TxAgg9MPDUCount +=
2221 TxAggCnt4.field.AggSize9Count;
2222 pRalinkCounters->TxAgg10MPDUCount +=
2223 TxAggCnt4.field.AggSize10Count;
2225 pRalinkCounters->TxAgg11MPDUCount +=
2226 TxAggCnt5.field.AggSize11Count;
2227 pRalinkCounters->TxAgg12MPDUCount +=
2228 TxAggCnt5.field.AggSize12Count;
2229 pRalinkCounters->TxAgg13MPDUCount +=
2230 TxAggCnt6.field.AggSize13Count;
2231 pRalinkCounters->TxAgg14MPDUCount +=
2232 TxAggCnt6.field.AggSize14Count;
2234 pRalinkCounters->TxAgg15MPDUCount +=
2235 TxAggCnt7.field.AggSize15Count;
2236 pRalinkCounters->TxAgg16MPDUCount +=
2237 TxAggCnt7.field.AggSize16Count;
2239 // Calculate the transmitted A-MPDU count
2240 pRalinkCounters->TransmittedAMPDUCount.u.LowPart +=
2241 TxAggCnt0.field.AggSize1Count;
2242 pRalinkCounters->TransmittedAMPDUCount.u.LowPart +=
2243 (TxAggCnt0.field.AggSize2Count / 2);
2245 pRalinkCounters->TransmittedAMPDUCount.u.LowPart +=
2246 (TxAggCnt1.field.AggSize3Count / 3);
2247 pRalinkCounters->TransmittedAMPDUCount.u.LowPart +=
2248 (TxAggCnt1.field.AggSize4Count / 4);
2250 pRalinkCounters->TransmittedAMPDUCount.u.LowPart +=
2251 (TxAggCnt2.field.AggSize5Count / 5);
2252 pRalinkCounters->TransmittedAMPDUCount.u.LowPart +=
2253 (TxAggCnt2.field.AggSize6Count / 6);
2255 pRalinkCounters->TransmittedAMPDUCount.u.LowPart +=
2256 (TxAggCnt3.field.AggSize7Count / 7);
2257 pRalinkCounters->TransmittedAMPDUCount.u.LowPart +=
2258 (TxAggCnt3.field.AggSize8Count / 8);
2260 pRalinkCounters->TransmittedAMPDUCount.u.LowPart +=
2261 (TxAggCnt4.field.AggSize9Count / 9);
2262 pRalinkCounters->TransmittedAMPDUCount.u.LowPart +=
2263 (TxAggCnt4.field.AggSize10Count / 10);
2265 pRalinkCounters->TransmittedAMPDUCount.u.LowPart +=
2266 (TxAggCnt5.field.AggSize11Count / 11);
2267 pRalinkCounters->TransmittedAMPDUCount.u.LowPart +=
2268 (TxAggCnt5.field.AggSize12Count / 12);
2270 pRalinkCounters->TransmittedAMPDUCount.u.LowPart +=
2271 (TxAggCnt6.field.AggSize13Count / 13);
2272 pRalinkCounters->TransmittedAMPDUCount.u.LowPart +=
2273 (TxAggCnt6.field.AggSize14Count / 14);
2275 pRalinkCounters->TransmittedAMPDUCount.u.LowPart +=
2276 (TxAggCnt7.field.AggSize15Count / 15);
2277 pRalinkCounters->TransmittedAMPDUCount.u.LowPart +=
2278 (TxAggCnt7.field.AggSize16Count / 16);
2284 ========================================================================
2286 Routine Description:
2287 Reset NIC from error
2290 Adapter Pointer to our adapter
2295 IRQL = PASSIVE_LEVEL
2298 Reset NIC from error state
2300 ========================================================================
2302 VOID NICResetFromError(IN PRTMP_ADAPTER pAd)
2304 // Reset BBP (according to alex, reset ASIC will force reset BBP
2305 // Therefore, skip the reset BBP
2306 // RTMP_IO_WRITE32(pAd, MAC_CSR1, 0x2);
2308 RTMP_IO_WRITE32(pAd, MAC_SYS_CTRL, 0x1);
2309 // Remove ASIC from reset state
2310 RTMP_IO_WRITE32(pAd, MAC_SYS_CTRL, 0x0);
2312 NICInitializeAdapter(pAd, FALSE);
2313 NICInitAsicFromEEPROM(pAd);
2315 // Switch to current channel, since during reset process, the connection should remains on.
2316 AsicSwitchChannel(pAd, pAd->CommonCfg.CentralChannel, FALSE);
2317 AsicLockChannel(pAd, pAd->CommonCfg.CentralChannel);
2320 NDIS_STATUS NICLoadFirmware(IN PRTMP_ADAPTER pAd)
2322 NDIS_STATUS status = NDIS_STATUS_SUCCESS;
2323 if (pAd->chipOps.loadFirmware)
2324 status = pAd->chipOps.loadFirmware(pAd);
2330 ========================================================================
2332 Routine Description:
2333 erase 8051 firmware image in MAC ASIC
2336 Adapter Pointer to our adapter
2338 IRQL = PASSIVE_LEVEL
2340 ========================================================================
2342 VOID NICEraseFirmware(IN PRTMP_ADAPTER pAd)
2344 if (pAd->chipOps.eraseFirmware)
2345 pAd->chipOps.eraseFirmware(pAd);
2347 } /* End of NICEraseFirmware */
2350 ========================================================================
2352 Routine Description:
2353 Load Tx rate switching parameters
2356 Adapter Pointer to our adapter
2359 NDIS_STATUS_SUCCESS firmware image load ok
2360 NDIS_STATUS_FAILURE image not found
2362 IRQL = PASSIVE_LEVEL
2365 1. (B0: Valid Item number) (B1:Initial item from zero)
2366 2. Item Number(Dec) Mode(Hex) Current MCS(Dec) TrainUp(Dec) TrainDown(Dec)
2368 ========================================================================
2370 NDIS_STATUS NICLoadRateSwitchingParams(IN PRTMP_ADAPTER pAd)
2372 return NDIS_STATUS_SUCCESS;
2376 ========================================================================
2378 Routine Description:
2379 Compare two memory block
2382 pSrc1 Pointer to first memory address
2383 pSrc2 Pointer to second memory address
2387 1: pSrc1 memory is larger
2388 2: pSrc2 memory is larger
2390 IRQL = DISPATCH_LEVEL
2394 ========================================================================
2396 ULONG RTMPCompareMemory(IN PVOID pSrc1, IN PVOID pSrc2, IN ULONG Length)
2402 pMem1 = (PUCHAR) pSrc1;
2403 pMem2 = (PUCHAR) pSrc2;
2405 for (Index = 0; Index < Length; Index++) {
2406 if (pMem1[Index] > pMem2[Index])
2408 else if (pMem1[Index] < pMem2[Index])
2417 ========================================================================
2419 Routine Description:
2420 Zero out memory block
2423 pSrc1 Pointer to memory address
2429 IRQL = PASSIVE_LEVEL
2430 IRQL = DISPATCH_LEVEL
2434 ========================================================================
2436 VOID RTMPZeroMemory(IN PVOID pSrc, IN ULONG Length)
2441 pMem = (PUCHAR) pSrc;
2443 for (Index = 0; Index < Length; Index++) {
2449 ========================================================================
2451 Routine Description:
2452 Copy data from memory block 1 to memory block 2
2455 pDest Pointer to destination memory address
2456 pSrc Pointer to source memory address
2462 IRQL = PASSIVE_LEVEL
2463 IRQL = DISPATCH_LEVEL
2467 ========================================================================
2469 VOID RTMPMoveMemory(OUT PVOID pDest, IN PVOID pSrc, IN ULONG Length)
2475 ASSERT((Length == 0) || (pDest && pSrc));
2477 pMem1 = (PUCHAR) pDest;
2478 pMem2 = (PUCHAR) pSrc;
2480 for (Index = 0; Index < Length; Index++) {
2481 pMem1[Index] = pMem2[Index];
2486 ========================================================================
2488 Routine Description:
2489 Initialize port configuration structure
2492 Adapter Pointer to our adapter
2497 IRQL = PASSIVE_LEVEL
2501 ========================================================================
2503 VOID UserCfgInit(IN PRTMP_ADAPTER pAd)
2505 UINT key_index, bss_index;
2507 DBGPRINT(RT_DEBUG_TRACE, ("--> UserCfgInit\n"));
2510 // part I. intialize common configuration
2513 pAd->BulkOutReq = 0;
2515 pAd->BulkOutComplete = 0;
2516 pAd->BulkOutCompleteOther = 0;
2517 pAd->BulkOutCompleteCancel = 0;
2519 pAd->BulkInComplete = 0;
2520 pAd->BulkInCompleteFail = 0;
2522 //pAd->QuickTimerP = 100;
2523 //pAd->TurnAggrBulkInCount = 0;
2524 pAd->bUsbTxBulkAggre = 0;
2526 // init as unsed value to ensure driver will set to MCU once.
2527 pAd->LedIndicatorStrength = 0xFF;
2529 pAd->CommonCfg.MaxPktOneTxBulk = 2;
2530 pAd->CommonCfg.TxBulkFactor = 1;
2531 pAd->CommonCfg.RxBulkFactor = 1;
2533 pAd->CommonCfg.TxPower = 100; //mW
2535 NdisZeroMemory(&pAd->CommonCfg.IOTestParm,
2536 sizeof(pAd->CommonCfg.IOTestParm));
2537 #endif // RTMP_MAC_USB //
2539 for (key_index = 0; key_index < SHARE_KEY_NUM; key_index++) {
2540 for (bss_index = 0; bss_index < MAX_MBSSID_NUM; bss_index++) {
2541 pAd->SharedKey[bss_index][key_index].KeyLen = 0;
2542 pAd->SharedKey[bss_index][key_index].CipherAlg =
2547 pAd->EepromAccess = FALSE;
2549 pAd->Antenna.word = 0;
2550 pAd->CommonCfg.BBPCurrentBW = BW_20;
2552 pAd->LedCntl.word = 0;
2554 pAd->LedIndicatorStrength = 0;
2555 pAd->RLnkCtrlOffset = 0;
2556 pAd->HostLnkCtrlOffset = 0;
2557 pAd->StaCfg.PSControl.field.EnableNewPS = TRUE;
2558 pAd->CheckDmaBusyCount = 0;
2559 #endif // RTMP_MAC_PCI //
2561 pAd->bAutoTxAgcA = FALSE; // Default is OFF
2562 pAd->bAutoTxAgcG = FALSE; // Default is OFF
2563 pAd->RfIcType = RFIC_2820;
2565 // Init timer for reset complete event
2566 pAd->CommonCfg.CentralChannel = 1;
2567 pAd->bForcePrintTX = FALSE;
2568 pAd->bForcePrintRX = FALSE;
2569 pAd->bStaFifoTest = FALSE;
2570 pAd->bProtectionTest = FALSE;
2571 pAd->CommonCfg.Dsifs = 10; // in units of usec
2572 pAd->CommonCfg.TxPower = 100; //mW
2573 pAd->CommonCfg.TxPowerPercentage = 0xffffffff; // AUTO
2574 pAd->CommonCfg.TxPowerDefault = 0xffffffff; // AUTO
2575 pAd->CommonCfg.TxPreamble = Rt802_11PreambleAuto; // use Long preamble on TX by defaut
2576 pAd->CommonCfg.bUseZeroToDisableFragment = FALSE;
2577 pAd->CommonCfg.RtsThreshold = 2347;
2578 pAd->CommonCfg.FragmentThreshold = 2346;
2579 pAd->CommonCfg.UseBGProtection = 0; // 0: AUTO
2580 pAd->CommonCfg.bEnableTxBurst = TRUE; //0;
2581 pAd->CommonCfg.PhyMode = 0xff; // unknown
2582 pAd->CommonCfg.BandState = UNKNOWN_BAND;
2583 pAd->CommonCfg.RadarDetect.CSPeriod = 10;
2584 pAd->CommonCfg.RadarDetect.CSCount = 0;
2585 pAd->CommonCfg.RadarDetect.RDMode = RD_NORMAL_MODE;
2587 pAd->CommonCfg.RadarDetect.ChMovingTime = 65;
2588 pAd->CommonCfg.RadarDetect.LongPulseRadarTh = 3;
2589 pAd->CommonCfg.bAPSDCapable = FALSE;
2590 pAd->CommonCfg.bNeedSendTriggerFrame = FALSE;
2591 pAd->CommonCfg.TriggerTimerCount = 0;
2592 pAd->CommonCfg.bAPSDForcePowerSave = FALSE;
2593 pAd->CommonCfg.bCountryFlag = FALSE;
2594 pAd->CommonCfg.TxStream = 0;
2595 pAd->CommonCfg.RxStream = 0;
2597 NdisZeroMemory(&pAd->BeaconTxWI, sizeof(pAd->BeaconTxWI));
2599 NdisZeroMemory(&pAd->CommonCfg.HtCapability,
2600 sizeof(pAd->CommonCfg.HtCapability));
2601 pAd->HTCEnable = FALSE;
2602 pAd->bBroadComHT = FALSE;
2603 pAd->CommonCfg.bRdg = FALSE;
2605 NdisZeroMemory(&pAd->CommonCfg.AddHTInfo,
2606 sizeof(pAd->CommonCfg.AddHTInfo));
2607 pAd->CommonCfg.BACapability.field.MMPSmode = MMPS_ENABLE;
2608 pAd->CommonCfg.BACapability.field.MpduDensity = 0;
2609 pAd->CommonCfg.BACapability.field.Policy = IMMED_BA;
2610 pAd->CommonCfg.BACapability.field.RxBAWinLimit = 64; //32;
2611 pAd->CommonCfg.BACapability.field.TxBAWinLimit = 64; //32;
2612 DBGPRINT(RT_DEBUG_TRACE,
2613 ("--> UserCfgInit. BACapability = 0x%x\n",
2614 pAd->CommonCfg.BACapability.word));
2616 pAd->CommonCfg.BACapability.field.AutoBA = FALSE;
2617 BATableInit(pAd, &pAd->BATable);
2619 pAd->CommonCfg.bExtChannelSwitchAnnouncement = 1;
2620 pAd->CommonCfg.bHTProtect = 1;
2621 pAd->CommonCfg.bMIMOPSEnable = TRUE;
2622 //2008/11/05:KH add to support Antenna power-saving of AP<--
2623 pAd->CommonCfg.bGreenAPEnable = FALSE;
2624 //2008/11/05:KH add to support Antenna power-saving of AP-->
2625 pAd->CommonCfg.bBADecline = FALSE;
2626 pAd->CommonCfg.bDisableReordering = FALSE;
2628 if (pAd->MACVersion == 0x28720200) {
2629 pAd->CommonCfg.TxBASize = 13; //by Jerry recommend
2631 pAd->CommonCfg.TxBASize = 7;
2634 pAd->CommonCfg.REGBACapability.word = pAd->CommonCfg.BACapability.word;
2636 //pAd->CommonCfg.HTPhyMode.field.BW = BW_20;
2637 //pAd->CommonCfg.HTPhyMode.field.MCS = MCS_AUTO;
2638 //pAd->CommonCfg.HTPhyMode.field.ShortGI = GI_800;
2639 //pAd->CommonCfg.HTPhyMode.field.STBC = STBC_NONE;
2640 pAd->CommonCfg.TxRate = RATE_6;
2642 pAd->CommonCfg.MlmeTransmit.field.MCS = MCS_RATE_6;
2643 pAd->CommonCfg.MlmeTransmit.field.BW = BW_20;
2644 pAd->CommonCfg.MlmeTransmit.field.MODE = MODE_OFDM;
2646 pAd->CommonCfg.BeaconPeriod = 100; // in mSec
2649 // part II. intialize STA specific configuration
2652 RX_FILTER_SET_FLAG(pAd, fRX_FILTER_ACCEPT_DIRECT);
2653 RX_FILTER_CLEAR_FLAG(pAd, fRX_FILTER_ACCEPT_MULTICAST);
2654 RX_FILTER_SET_FLAG(pAd, fRX_FILTER_ACCEPT_BROADCAST);
2655 RX_FILTER_SET_FLAG(pAd, fRX_FILTER_ACCEPT_ALL_MULTICAST);
2657 pAd->StaCfg.Psm = PWR_ACTIVE;
2659 pAd->StaCfg.OrigWepStatus = Ndis802_11EncryptionDisabled;
2660 pAd->StaCfg.PairCipher = Ndis802_11EncryptionDisabled;
2661 pAd->StaCfg.GroupCipher = Ndis802_11EncryptionDisabled;
2662 pAd->StaCfg.bMixCipher = FALSE;
2663 pAd->StaCfg.DefaultKeyId = 0;
2665 // 802.1x port control
2666 pAd->StaCfg.PrivacyFilter = Ndis802_11PrivFilter8021xWEP;
2667 pAd->StaCfg.PortSecured = WPA_802_1X_PORT_NOT_SECURED;
2668 pAd->StaCfg.LastMicErrorTime = 0;
2669 pAd->StaCfg.MicErrCnt = 0;
2670 pAd->StaCfg.bBlockAssoc = FALSE;
2671 pAd->StaCfg.WpaState = SS_NOTUSE;
2673 pAd->CommonCfg.NdisRadioStateOff = FALSE; // New to support microsoft disable radio with OID command
2675 pAd->StaCfg.RssiTrigger = 0;
2676 NdisZeroMemory(&pAd->StaCfg.RssiSample, sizeof(RSSI_SAMPLE));
2677 pAd->StaCfg.RssiTriggerMode =
2678 RSSI_TRIGGERED_UPON_BELOW_THRESHOLD;
2679 pAd->StaCfg.AtimWin = 0;
2680 pAd->StaCfg.DefaultListenCount = 3; //default listen count;
2681 pAd->StaCfg.BssType = BSS_INFRA; // BSS_INFRA or BSS_ADHOC or BSS_MONITOR
2682 pAd->StaCfg.bScanReqIsFromWebUI = FALSE;
2683 OPSTATUS_CLEAR_FLAG(pAd, fOP_STATUS_DOZE);
2684 OPSTATUS_CLEAR_FLAG(pAd, fOP_STATUS_WAKEUP_NOW);
2686 pAd->StaCfg.bAutoTxRateSwitch = TRUE;
2687 pAd->StaCfg.DesiredTransmitSetting.field.MCS = MCS_AUTO;
2690 #ifdef PCIE_PS_SUPPORT
2691 pAd->brt30xxBanMcuCmd = FALSE;
2692 pAd->b3090ESpecialChip = FALSE;
2693 //KH Debug:the following must be removed
2694 pAd->StaCfg.PSControl.field.rt30xxPowerMode = 3;
2695 pAd->StaCfg.PSControl.field.rt30xxForceASPMTest = 0;
2696 pAd->StaCfg.PSControl.field.rt30xxFollowHostASPM = 1;
2697 #endif // PCIE_PS_SUPPORT //
2699 // global variables mXXXX used in MAC protocol state machines
2700 OPSTATUS_SET_FLAG(pAd, fOP_STATUS_RECEIVE_DTIM);
2701 OPSTATUS_CLEAR_FLAG(pAd, fOP_STATUS_ADHOC_ON);
2702 OPSTATUS_CLEAR_FLAG(pAd, fOP_STATUS_INFRA_ON);
2704 // PHY specification
2705 pAd->CommonCfg.PhyMode = PHY_11BG_MIXED; // default PHY mode
2706 OPSTATUS_CLEAR_FLAG(pAd, fOP_STATUS_SHORT_PREAMBLE_INUSED); // CCK use LONG preamble
2709 // user desired power mode
2710 pAd->StaCfg.WindowsPowerMode = Ndis802_11PowerModeCAM;
2711 pAd->StaCfg.WindowsBatteryPowerMode = Ndis802_11PowerModeCAM;
2712 pAd->StaCfg.bWindowsACCAMEnable = FALSE;
2714 RTMPInitTimer(pAd, &pAd->StaCfg.StaQuickResponeForRateUpTimer,
2715 GET_TIMER_FUNCTION(StaQuickResponeForRateUpExec),
2717 pAd->StaCfg.StaQuickResponeForRateUpTimerRunning = FALSE;
2720 pAd->StaCfg.ScanCnt = 0;
2722 pAd->StaCfg.bHwRadio = TRUE; // Default Hardware Radio status is On
2723 pAd->StaCfg.bSwRadio = TRUE; // Default Software Radio status is On
2724 pAd->StaCfg.bRadio = TRUE; // bHwRadio && bSwRadio
2725 pAd->StaCfg.bHardwareRadio = FALSE; // Default is OFF
2726 pAd->StaCfg.bShowHiddenSSID = FALSE; // Default no show
2728 // Nitro mode control
2729 pAd->StaCfg.bAutoReconnect = TRUE;
2731 // Save the init time as last scan time, the system should do scan after 2 seconds.
2732 // This patch is for driver wake up from standby mode, system will do scan right away.
2733 NdisGetSystemUpTime(&pAd->StaCfg.LastScanTime);
2734 if (pAd->StaCfg.LastScanTime > 10 * OS_HZ)
2735 pAd->StaCfg.LastScanTime -= (10 * OS_HZ);
2737 NdisZeroMemory(pAd->nickname, IW_ESSID_MAX_SIZE + 1);
2739 sprintf((PSTRING) pAd->nickname, "RT2860STA");
2740 #endif // RTMP_MAC_PCI //
2742 sprintf((PSTRING) pAd->nickname, "RT2870STA");
2743 #endif // RTMP_MAC_USB //
2744 RTMPInitTimer(pAd, &pAd->StaCfg.WpaDisassocAndBlockAssocTimer,
2745 GET_TIMER_FUNCTION(WpaDisassocApAndBlockAssoc),
2747 pAd->StaCfg.IEEE8021X = FALSE;
2748 pAd->StaCfg.IEEE8021x_required_keys = FALSE;
2749 pAd->StaCfg.WpaSupplicantUP = WPA_SUPPLICANT_DISABLE;
2750 pAd->StaCfg.bRSN_IE_FromWpaSupplicant = FALSE;
2751 pAd->StaCfg.WpaSupplicantUP = WPA_SUPPLICANT_ENABLE;
2753 NdisZeroMemory(pAd->StaCfg.ReplayCounter, 8);
2755 pAd->StaCfg.bAutoConnectByBssid = FALSE;
2756 pAd->StaCfg.BeaconLostTime = BEACON_LOST_TIME;
2757 NdisZeroMemory(pAd->StaCfg.WpaPassPhrase, 64);
2758 pAd->StaCfg.WpaPassPhraseLen = 0;
2759 pAd->StaCfg.bAutoRoaming = FALSE;
2760 pAd->StaCfg.bForceTxBurst = FALSE;
2763 // Default for extra information is not valid
2764 pAd->ExtraInfo = EXTRA_INFO_CLEAR;
2766 // Default Config change flag
2767 pAd->bConfigChanged = FALSE;
2770 // part III. AP configurations
2776 // dynamic BBP R66:sensibity tuning to overcome background noise
2777 pAd->BbpTuning.bEnable = TRUE;
2778 pAd->BbpTuning.FalseCcaLowerThreshold = 100;
2779 pAd->BbpTuning.FalseCcaUpperThreshold = 512;
2780 pAd->BbpTuning.R66Delta = 4;
2781 pAd->Mlme.bEnableAutoAntennaCheck = TRUE;
2784 // Also initial R66CurrentValue, RTUSBResumeMsduTransmission might use this value.
2785 // if not initial this value, the default value will be 0.
2787 pAd->BbpTuning.R66CurrentValue = 0x38;
2789 pAd->Bbp94 = BBPR94_DEFAULT;
2790 pAd->BbpForCCK = FALSE;
2792 // Default is FALSE for test bit 1
2793 //pAd->bTest1 = FALSE;
2795 // initialize MAC table and allocate spin lock
2796 NdisZeroMemory(&pAd->MacTab, sizeof(MAC_TABLE));
2797 InitializeQueueHeader(&pAd->MacTab.McastPsQueue);
2798 NdisAllocateSpinLock(&pAd->MacTabLock);
2800 //RTMPInitTimer(pAd, &pAd->RECBATimer, RECBATimerTimeout, pAd, TRUE);
2801 //RTMPSetTimer(&pAd->RECBATimer, REORDER_EXEC_INTV);
2803 pAd->CommonCfg.bWiFiTest = FALSE;
2805 pAd->bPCIclkOff = FALSE;
2806 #endif // RTMP_MAC_PCI //
2808 RTMP_SET_PSFLAG(pAd, fRTMP_PS_CAN_GO_SLEEP);
2809 DBGPRINT(RT_DEBUG_TRACE, ("<-- UserCfgInit\n"));
2812 // IRQL = PASSIVE_LEVEL
2813 UCHAR BtoH(STRING ch)
2815 if (ch >= '0' && ch <= '9')
2816 return (ch - '0'); // Handle numerals
2817 if (ch >= 'A' && ch <= 'F')
2818 return (ch - 'A' + 0xA); // Handle capitol hex digits
2819 if (ch >= 'a' && ch <= 'f')
2820 return (ch - 'a' + 0xA); // Handle small hex digits
2825 // FUNCTION: AtoH(char *, UCHAR *, int)
2827 // PURPOSE: Converts ascii string to network order hex
2830 // src - pointer to input ascii string
2831 // dest - pointer to output hex
2832 // destlen - size of dest
2836 // 2 ascii bytes make a hex byte so must put 1st ascii byte of pair
2837 // into upper nibble and 2nd ascii byte of pair into lower nibble.
2839 // IRQL = PASSIVE_LEVEL
2841 void AtoH(PSTRING src, PUCHAR dest, int destlen)
2847 destTemp = (PUCHAR) dest;
2850 *destTemp = BtoH(*srcptr++) << 4; // Put 1st ascii byte in upper nibble.
2851 *destTemp += BtoH(*srcptr++); // Add 2nd ascii byte to above.
2856 //+++Mark by shiang, not use now, need to remove after confirm
2857 //---Mark by shiang, not use now, need to remove after confirm
2860 ========================================================================
2862 Routine Description:
2866 pAd Pointer to our adapter
2867 pTimer Timer structure
2868 pTimerFunc Function to execute when timer expired
2869 Repeat Ture for period timer
2876 ========================================================================
2878 VOID RTMPInitTimer(IN PRTMP_ADAPTER pAd,
2879 IN PRALINK_TIMER_STRUCT pTimer,
2880 IN PVOID pTimerFunc, IN PVOID pData, IN BOOLEAN Repeat)
2883 // Set Valid to TRUE for later used.
2884 // It will crash if we cancel a timer or set a timer
2885 // that we haven't initialize before.
2887 pTimer->Valid = TRUE;
2889 pTimer->PeriodicType = Repeat;
2890 pTimer->State = FALSE;
2891 pTimer->cookie = (ULONG) pData;
2893 #ifdef RTMP_TIMER_TASK_SUPPORT
2895 #endif // RTMP_TIMER_TASK_SUPPORT //
2897 RTMP_OS_Init_Timer(pAd, &pTimer->TimerObj, pTimerFunc, (PVOID) pTimer);
2901 ========================================================================
2903 Routine Description:
2907 pTimer Timer structure
2908 Value Timer value in milliseconds
2914 To use this routine, must call RTMPInitTimer before.
2916 ========================================================================
2918 VOID RTMPSetTimer(IN PRALINK_TIMER_STRUCT pTimer, IN ULONG Value)
2920 if (pTimer->Valid) {
2921 pTimer->TimerValue = Value;
2922 pTimer->State = FALSE;
2923 if (pTimer->PeriodicType == TRUE) {
2924 pTimer->Repeat = TRUE;
2925 RTMP_SetPeriodicTimer(&pTimer->TimerObj, Value);
2927 pTimer->Repeat = FALSE;
2928 RTMP_OS_Add_Timer(&pTimer->TimerObj, Value);
2931 DBGPRINT_ERR(("RTMPSetTimer failed, Timer hasn't been initialize!\n"));
2936 ========================================================================
2938 Routine Description:
2942 pTimer Timer structure
2943 Value Timer value in milliseconds
2949 To use this routine, must call RTMPInitTimer before.
2951 ========================================================================
2953 VOID RTMPModTimer(IN PRALINK_TIMER_STRUCT pTimer, IN ULONG Value)
2957 if (pTimer->Valid) {
2958 pTimer->TimerValue = Value;
2959 pTimer->State = FALSE;
2960 if (pTimer->PeriodicType == TRUE) {
2961 RTMPCancelTimer(pTimer, &Cancel);
2962 RTMPSetTimer(pTimer, Value);
2964 RTMP_OS_Mod_Timer(&pTimer->TimerObj, Value);
2967 DBGPRINT_ERR(("RTMPModTimer failed, Timer hasn't been initialize!\n"));
2972 ========================================================================
2974 Routine Description:
2975 Cancel timer objects
2978 Adapter Pointer to our adapter
2983 IRQL = PASSIVE_LEVEL
2984 IRQL = DISPATCH_LEVEL
2987 1.) To use this routine, must call RTMPInitTimer before.
2988 2.) Reset NIC to initial state AS IS system boot up time.
2990 ========================================================================
2992 VOID RTMPCancelTimer(IN PRALINK_TIMER_STRUCT pTimer, OUT BOOLEAN * pCancelled)
2994 if (pTimer->Valid) {
2995 if (pTimer->State == FALSE)
2996 pTimer->Repeat = FALSE;
2998 RTMP_OS_Del_Timer(&pTimer->TimerObj, pCancelled);
3000 if (*pCancelled == TRUE)
3001 pTimer->State = TRUE;
3003 #ifdef RTMP_TIMER_TASK_SUPPORT
3004 // We need to go-through the TimerQ to findout this timer handler and remove it if
3005 // it's still waiting for execution.
3006 RtmpTimerQRemove(pTimer->pAd, pTimer);
3007 #endif // RTMP_TIMER_TASK_SUPPORT //
3009 DBGPRINT_ERR(("RTMPCancelTimer failed, Timer hasn't been initialize!\n"));
3014 ========================================================================
3016 Routine Description:
3020 pAd Pointer to our adapter
3026 IRQL = PASSIVE_LEVEL
3027 IRQL = DISPATCH_LEVEL
3031 ========================================================================
3033 VOID RTMPSetLED(IN PRTMP_ADAPTER pAd, IN UCHAR Status)
3039 LowByte = pAd->LedCntl.field.LedMode & 0x7f;
3043 AsicSendCommandToMcu(pAd, 0x50, 0xff, LowByte, HighByte);
3044 pAd->LedIndicatorStrength = 0;
3047 if (pAd->CommonCfg.Channel > 14)
3051 AsicSendCommandToMcu(pAd, 0x50, 0xff, LowByte, HighByte);
3055 AsicSendCommandToMcu(pAd, 0x50, 0xff, LowByte, HighByte);
3058 LowByte = 0; // Driver sets MAC register and MAC controls LED
3061 AsicSendCommandToMcu(pAd, 0x50, 0xff, LowByte, HighByte);
3065 AsicSendCommandToMcu(pAd, 0x50, 0xff, LowByte, HighByte);
3067 case LED_ON_SITE_SURVEY:
3069 AsicSendCommandToMcu(pAd, 0x50, 0xff, LowByte, HighByte);
3073 AsicSendCommandToMcu(pAd, 0x50, 0xff, LowByte, HighByte);
3076 DBGPRINT(RT_DEBUG_WARN,
3077 ("RTMPSetLED::Unknown Status %d\n", Status));
3082 // Keep LED status for LED SiteSurvey mode.
3083 // After SiteSurvey, we will set the LED mode to previous status.
3085 if ((Status != LED_ON_SITE_SURVEY) && (Status != LED_POWER_UP))
3086 pAd->LedStatus = Status;
3088 DBGPRINT(RT_DEBUG_TRACE,
3089 ("RTMPSetLED::Mode=%d,HighByte=0x%02x,LowByte=0x%02x\n",
3090 pAd->LedCntl.field.LedMode, HighByte, LowByte));
3094 ========================================================================
3096 Routine Description:
3097 Set LED Signal Stregth
3100 pAd Pointer to our adapter
3106 IRQL = PASSIVE_LEVEL
3109 Can be run on any IRQL level.
3111 According to Microsoft Zero Config Wireless Signal Stregth definition as belows.
3118 ========================================================================
3120 VOID RTMPSetSignalLED(IN PRTMP_ADAPTER pAd, IN NDIS_802_11_RSSI Dbm)
3124 if (pAd->LedCntl.field.LedMode == LED_MODE_SIGNAL_STREGTH) {
3127 else if (Dbm <= -81)
3129 else if (Dbm <= -71)
3131 else if (Dbm <= -67)
3133 else if (Dbm <= -57)
3139 // Update Signal Stregth to firmware if changed.
3141 if (pAd->LedIndicatorStrength != nLed) {
3142 AsicSendCommandToMcu(pAd, 0x51, 0xff, nLed,
3143 pAd->LedCntl.field.Polarity);
3144 pAd->LedIndicatorStrength = nLed;
3150 ========================================================================
3152 Routine Description:
3156 pAd Pointer to our adapter
3161 IRQL <= DISPATCH_LEVEL
3164 Before Enable RX, make sure you have enabled Interrupt.
3165 ========================================================================
3167 VOID RTMPEnableRxTx(IN PRTMP_ADAPTER pAd)
3169 // WPDMA_GLO_CFG_STRUC GloCfg;
3171 UINT32 rx_filter_flag;
3173 DBGPRINT(RT_DEBUG_TRACE, ("==> RTMPEnableRxTx\n"));
3176 RT28XXDMAEnable(pAd);
3178 // enable RX of MAC block
3179 if (pAd->OpMode == OPMODE_AP) {
3180 rx_filter_flag = APNORMAL;
3182 RTMP_IO_WRITE32(pAd, RX_FILTR_CFG, rx_filter_flag); // enable RX of DMA block
3184 if (pAd->CommonCfg.PSPXlink)
3185 rx_filter_flag = PSPXLINK;
3187 rx_filter_flag = STANORMAL; // Staion not drop control frame will fail WiFi Certification.
3188 RTMP_IO_WRITE32(pAd, RX_FILTR_CFG, rx_filter_flag);
3191 RTMP_IO_WRITE32(pAd, MAC_SYS_CTRL, 0xc);
3192 DBGPRINT(RT_DEBUG_TRACE, ("<== RTMPEnableRxTx\n"));
3195 //+++Add by shiang, move from os/linux/rt_main_dev.c
3196 void CfgInitHook(PRTMP_ADAPTER pAd)
3198 pAd->bBroadComHT = TRUE;
3201 int rt28xx_init(IN PRTMP_ADAPTER pAd,
3202 IN PSTRING pDefaultMac, IN PSTRING pHostName)
3211 // If dirver doesn't wake up firmware here,
3212 // NICLoadFirmware will hang forever when interface is up again.
3214 if (OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_DOZE) &&
3215 OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_PCIE_DEVICE)) {
3216 AUTO_WAKEUP_STRUC AutoWakeupCfg;
3217 AsicForceWakeup(pAd, TRUE);
3218 AutoWakeupCfg.word = 0;
3219 RTMP_IO_WRITE32(pAd, AUTO_WAKEUP_CFG,
3220 AutoWakeupCfg.word);
3221 OPSTATUS_CLEAR_FLAG(pAd, fOP_STATUS_DOZE);
3224 #endif // RTMP_MAC_PCI //
3226 // reset Adapter flags
3227 RTMP_CLEAR_FLAGS(pAd);
3229 // Init BssTab & ChannelInfo tabbles for auto channel select.
3231 // Allocate BA Reordering memory
3232 ba_reordering_resource_init(pAd, MAX_REORDERING_MPDU_NUM);
3234 // Make sure MAC gets ready.
3237 RTMP_IO_READ32(pAd, MAC_CSR0, &MacCsr0);
3238 pAd->MACVersion = MacCsr0;
3240 if ((pAd->MACVersion != 0x00)
3241 && (pAd->MACVersion != 0xFFFFFFFF))
3245 } while (index++ < 100);
3246 DBGPRINT(RT_DEBUG_TRACE,
3247 ("MAC_CSR0 [ Ver:Rev=0x%08x]\n", pAd->MACVersion));
3250 #ifdef PCIE_PS_SUPPORT
3251 /*Iverson patch PCIE L1 issue to make sure that driver can be read,write ,BBP and RF register at pcie L.1 level */
3252 if ((IS_RT3090(pAd) || IS_RT3572(pAd) || IS_RT3390(pAd))
3253 && OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_PCIE_DEVICE)) {
3254 RTMP_IO_READ32(pAd, AUX_CTRL, &MacCsr0);
3256 RTMP_IO_WRITE32(pAd, AUX_CTRL, MacCsr0);
3257 DBGPRINT(RT_DEBUG_TRACE, ("AUX_CTRL = 0x%x\n", MacCsr0));
3259 #endif // PCIE_PS_SUPPORT //
3261 // To fix driver disable/enable hang issue when radio off
3262 RTMP_IO_WRITE32(pAd, PWR_PIN_CFG, 0x2);
3263 #endif // RTMP_MAC_PCI //
3266 RT28XXDMADisable(pAd);
3268 // Load 8051 firmware
3269 Status = NICLoadFirmware(pAd);
3270 if (Status != NDIS_STATUS_SUCCESS) {
3271 DBGPRINT_ERR(("NICLoadFirmware failed, Status[=0x%08x]\n",
3276 NICLoadRateSwitchingParams(pAd);
3278 // Disable interrupts here which is as soon as possible
3279 // This statement should never be true. We might consider to remove it later
3281 if (RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_INTERRUPT_ACTIVE)) {
3282 RTMP_ASIC_INTERRUPT_DISABLE(pAd);
3284 #endif // RTMP_MAC_PCI //
3286 Status = RTMPAllocTxRxRingMemory(pAd);
3287 if (Status != NDIS_STATUS_SUCCESS) {
3288 DBGPRINT_ERR(("RTMPAllocDMAMemory failed, Status[=0x%08x]\n",
3293 RTMP_SET_FLAG(pAd, fRTMP_ADAPTER_INTERRUPT_IN_USE);
3298 Status = RtmpMgmtTaskInit(pAd);
3299 if (Status != NDIS_STATUS_SUCCESS)
3302 Status = MlmeInit(pAd);
3303 if (Status != NDIS_STATUS_SUCCESS) {
3304 DBGPRINT_ERR(("MlmeInit failed, Status[=0x%08x]\n", Status));
3307 // Initialize pAd->StaCfg, pAd->ApCfg, pAd->CommonCfg to manufacture default
3310 Status = RtmpNetTaskInit(pAd);
3311 if (Status != NDIS_STATUS_SUCCESS)
3314 // COPY_MAC_ADDR(pAd->ApCfg.MBSSID[apidx].Bssid, netif->hwaddr);
3315 // pAd->bForcePrintTX = TRUE;
3319 NdisAllocateSpinLock(&pAd->MacTabLock);
3321 MeasureReqTabInit(pAd);
3325 // Init the hardware, we need to init asic before read registry, otherwise mac register will be reset
3327 Status = NICInitializeAdapter(pAd, TRUE);
3328 if (Status != NDIS_STATUS_SUCCESS) {
3329 DBGPRINT_ERR(("NICInitializeAdapter failed, Status[=0x%08x]\n",
3331 if (Status != NDIS_STATUS_SUCCESS)
3335 DBGPRINT(RT_DEBUG_OFF, ("1. Phy Mode = %d\n", pAd->CommonCfg.PhyMode));
3338 pAd->CommonCfg.bMultipleIRP = FALSE;
3340 if (pAd->CommonCfg.bMultipleIRP)
3341 pAd->CommonCfg.NumOfBulkInIRP = RX_RING_SIZE;
3343 pAd->CommonCfg.NumOfBulkInIRP = 1;
3344 #endif // RTMP_MAC_USB //
3346 //Init Ba Capability parameters.
3347 // RT28XX_BA_INIT(pAd);
3348 pAd->CommonCfg.DesiredHtPhy.MpduDensity =
3349 (UCHAR) pAd->CommonCfg.BACapability.field.MpduDensity;
3350 pAd->CommonCfg.DesiredHtPhy.AmsduEnable =
3351 (USHORT) pAd->CommonCfg.BACapability.field.AmsduEnable;
3352 pAd->CommonCfg.DesiredHtPhy.AmsduSize =
3353 (USHORT) pAd->CommonCfg.BACapability.field.AmsduSize;
3354 pAd->CommonCfg.DesiredHtPhy.MimoPs =
3355 (USHORT) pAd->CommonCfg.BACapability.field.MMPSmode;
3357 pAd->CommonCfg.HtCapability.HtCapInfo.MimoPs =
3358 (USHORT) pAd->CommonCfg.BACapability.field.MMPSmode;
3359 pAd->CommonCfg.HtCapability.HtCapInfo.AMsduSize =
3360 (USHORT) pAd->CommonCfg.BACapability.field.AmsduSize;
3361 pAd->CommonCfg.HtCapability.HtCapParm.MpduDensity =
3362 (UCHAR) pAd->CommonCfg.BACapability.field.MpduDensity;
3364 // after reading Registry, we now know if in AP mode or STA mode
3366 // Load 8051 firmware; crash when FW image not existent
3367 // Status = NICLoadFirmware(pAd);
3368 // if (Status != NDIS_STATUS_SUCCESS)
3371 DBGPRINT(RT_DEBUG_OFF, ("2. Phy Mode = %d\n", pAd->CommonCfg.PhyMode));
3373 // We should read EEPROM for all cases. rt2860b
3374 NICReadEEPROMParameters(pAd, (PUCHAR) pDefaultMac);
3376 DBGPRINT(RT_DEBUG_OFF, ("3. Phy Mode = %d\n", pAd->CommonCfg.PhyMode));
3378 NICInitAsicFromEEPROM(pAd); //rt2860b
3380 // Set PHY to appropriate mode
3381 TmpPhy = pAd->CommonCfg.PhyMode;
3382 pAd->CommonCfg.PhyMode = 0xff;
3383 RTMPSetPhyMode(pAd, TmpPhy);
3386 // No valid channels.
3387 if (pAd->ChannelListNum == 0) {
3388 DBGPRINT(RT_DEBUG_ERROR,
3389 ("Wrong configuration. No valid channel found. Check \"ContryCode\" and \"ChannelGeography\" setting.\n"));
3393 DBGPRINT(RT_DEBUG_OFF,
3394 ("MCS Set = %02x %02x %02x %02x %02x\n",
3395 pAd->CommonCfg.HtCapability.MCSSet[0],
3396 pAd->CommonCfg.HtCapability.MCSSet[1],
3397 pAd->CommonCfg.HtCapability.MCSSet[2],
3398 pAd->CommonCfg.HtCapability.MCSSet[3],
3399 pAd->CommonCfg.HtCapability.MCSSet[4]));
3401 #ifdef RTMP_RF_RW_SUPPORT
3402 //Init RT30xx RFRegisters after read RFIC type from EEPROM
3403 NICInitRFRegisters(pAd);
3404 #endif // RTMP_RF_RW_SUPPORT //
3406 // APInitialize(pAd);
3409 // Initialize RF register to default value
3411 AsicSwitchChannel(pAd, pAd->CommonCfg.Channel, FALSE);
3412 AsicLockChannel(pAd, pAd->CommonCfg.Channel);
3414 // 8051 firmware require the signal during booting time.
3415 //2008/11/28:KH marked the following codes to patch Frequency offset bug
3416 //AsicSendCommandToMcu(pAd, 0x72, 0xFF, 0x00, 0x00);
3418 if (pAd && (Status != NDIS_STATUS_SUCCESS)) {
3420 // Undo everything if it failed
3422 if (RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_INTERRUPT_IN_USE)) {
3423 // NdisMDeregisterInterrupt(&pAd->Interrupt);
3424 RTMP_CLEAR_FLAG(pAd, fRTMP_ADAPTER_INTERRUPT_IN_USE);
3426 // RTMPFreeAdapter(pAd); // we will free it in disconnect()
3428 // Microsoft HCT require driver send a disconnect event after driver initialization.
3429 OPSTATUS_CLEAR_FLAG(pAd, fOP_STATUS_MEDIA_STATE_CONNECTED);
3430 // pAd->IndicateMediaState = NdisMediaStateDisconnected;
3431 RTMP_SET_FLAG(pAd, fRTMP_ADAPTER_MEDIA_STATE_CHANGE);
3433 DBGPRINT(RT_DEBUG_TRACE,
3434 ("NDIS_STATUS_MEDIA_DISCONNECT Event B!\n"));
3437 RTMP_CLEAR_FLAG(pAd, fRTMP_ADAPTER_RESET_IN_PROGRESS);
3438 RTMP_CLEAR_FLAG(pAd, fRTMP_ADAPTER_REMOVE_IN_PROGRESS);
3441 // Support multiple BulkIn IRP,
3442 // the value on pAd->CommonCfg.NumOfBulkInIRP may be large than 1.
3444 for (index = 0; index < pAd->CommonCfg.NumOfBulkInIRP; index++) {
3445 RTUSBBulkReceive(pAd);
3446 DBGPRINT(RT_DEBUG_TRACE, ("RTUSBBulkReceive!\n"));
3448 #endif // RTMP_MAC_USB //
3451 // Set up the Mac address
3452 RtmpOSNetDevAddrSet(pAd->net_dev, &pAd->CurrentAddress[0]);
3454 DBGPRINT_S(Status, ("<==== rt28xx_init, Status=%x\n", Status));
3462 RTMPFreeTxRxRingMemory(pAd);
3465 os_free_mem(pAd, pAd->mpdu_blk_pool.mem); // free BA pool
3467 // shall not set priv to NULL here because the priv didn't been free yet.
3468 //net_dev->ml_priv = 0;
3473 DBGPRINT(RT_DEBUG_ERROR, ("!!! rt28xx Initialized fail !!!\n"));
3477 //---Add by shiang, move from os/linux/rt_main_dev.c
3479 static INT RtmpChipOpsRegister(IN RTMP_ADAPTER * pAd, IN INT infType)
3481 RTMP_CHIP_OP *pChipOps = &pAd->chipOps;
3484 memset(pChipOps, 0, sizeof(RTMP_CHIP_OP));
3486 /* set eeprom related hook functions */
3487 status = RtmpChipOpsEepromHook(pAd, infType);
3489 /* set mcu related hook functions */
3491 #ifdef RTMP_PCI_SUPPORT
3492 case RTMP_DEV_INF_PCI:
3493 pChipOps->loadFirmware = RtmpAsicLoadFirmware;
3494 pChipOps->eraseFirmware = RtmpAsicEraseFirmware;
3495 pChipOps->sendCommandToMcu = RtmpAsicSendCommandToMcu;
3497 #endif // RTMP_PCI_SUPPORT //
3498 #ifdef RTMP_USB_SUPPORT
3499 case RTMP_DEV_INF_USB:
3500 pChipOps->loadFirmware = RtmpAsicLoadFirmware;
3501 pChipOps->sendCommandToMcu = RtmpAsicSendCommandToMcu;
3503 #endif // RTMP_USB_SUPPORT //
3511 INT RtmpRaDevCtrlInit(IN RTMP_ADAPTER * pAd, IN RTMP_INF_TYPE infType)
3515 // Assign the interface type. We need use it when do register/EEPROM access.
3516 pAd->infType = infType;
3518 pAd->OpMode = OPMODE_STA;
3519 DBGPRINT(RT_DEBUG_TRACE,
3520 ("STA Driver version-%s\n", STA_DRIVER_VERSION));
3523 init_MUTEX(&(pAd->UsbVendorReq_semaphore));
3524 os_alloc_mem(pAd, (PUCHAR *) & pAd->UsbVendorReqBuf,
3525 MAX_PARAM_BUFFER_SIZE - 1);
3526 if (pAd->UsbVendorReqBuf == NULL) {
3527 DBGPRINT(RT_DEBUG_ERROR,
3528 ("Allocate vendor request temp buffer failed!\n"));
3531 #endif // RTMP_MAC_USB //
3533 RtmpChipOpsRegister(pAd, infType);
3538 BOOLEAN RtmpRaDevCtrlExit(IN RTMP_ADAPTER * pAd)
3541 RTMPFreeAdapter(pAd);
3546 // not yet support MBSS
3547 PNET_DEV get_netdev_from_bssid(IN PRTMP_ADAPTER pAd, IN UCHAR FromWhichBSSID)
3549 PNET_DEV dev_p = NULL;
3552 dev_p = pAd->net_dev;
3556 return dev_p; /* return one of MBSS */