]> bbs.cooldavid.org Git - net-next-2.6.git/blame - drivers/staging/rt3090/chips/rt33xx.c
Staging: rt2860: add RT3090 chipset support
[net-next-2.6.git] / drivers / staging / rt3090 / chips / rt33xx.c
CommitLineData
36c7928c
BZ
1/*
2 *************************************************************************
3 * Ralink Tech Inc.
4 * 5F., No.36, Taiyuan St., Jhubei City,
5 * Hsinchu County 302,
6 * Taiwan, R.O.C.
7 *
8 * (c) Copyright 2002-2007, Ralink Technology, Inc.
9 *
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. *
14 * *
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. *
19 * *
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. *
24 * *
25 *************************************************************************
26
27 Module Name:
28 rt33xx.c
29
30 Abstract:
31 Specific funcitons and variables for RT30xx.
32
33 Revision History:
34 Who When What
35 -------- ---------- ----------------------------------------------
36*/
37
38
39#ifdef RT33xx
40
41
42#ifndef RTMP_RF_RW_SUPPORT
43#error "You Should Enable compile flag RTMP_RF_RW_SUPPORT for this chip"
44#endif // RTMP_RF_RW_SUPPORT //
45
46#include "../rt_config.h"
47
48
49//
50// RF register initialization set
51//
52REG_PAIR RFRegTableOverRT3390[] = {
53 {RF_R00, 0xA0},
54 {RF_R01, 0xE1},
55 {RF_R02, 0xF1},
56 {RF_R03, 0x62},
57 {RF_R04, 0x40},
58 {RF_R05, 0x8B},
59 {RF_R06, 0x42},
60 {RF_R07, 0x34},
61 {RF_R08, 0x00}, // Read only
62 {RF_R09, 0xC0},
63
64 {RF_R10, 0x61},
65 {RF_R11, 0x21},
66 {RF_R12, 0x3B},
67 {RF_R13, 0xE0},
68 {RF_R14, 0x90},
69 {RF_R15, 0x53},
70 {RF_R16, 0x0E},
71 {RF_R17, 0x94},
72 {RF_R18, 0x5C},
73 {RF_R19, 0x4A},
74
75 {RF_R20, 0xB2},
76 {RF_R21, 0xF6},
77 {RF_R22, 0x00},
78 {RF_R23, 0x14},
79 {RF_R24, 0x08},
80 {RF_R25, 0x3D},
81 {RF_R26, 0x85},
82 {RF_R27, 0x00},
83 {RF_R28, 0x41},
84 {RF_R29, 0x8F},
85 {RF_R30, 0x20},
86 {RF_R31, 0x0F},
87};
88
89UCHAR NUM_RF_REG_PARMS_OVER_RT3390=(sizeof(RFRegTableOverRT3390) / sizeof(REG_PAIR));
90
91
92
93// Antenna divesity use GPIO3 and EESK pin for control
94// Antenna and EEPROM access are both using EESK pin,
95// Therefor we should avoid accessing EESK at the same time
96// Then restore antenna after EEPROM access
97// The original name of this function is AsicSetRxAnt(), now change to
98//VOID AsicSetRxAnt(
99
100VOID RT33xxSetRxAnt(
101 IN PRTMP_ADAPTER pAd,
102 IN UCHAR Ant)
103{
104 UINT32 Value;
105 UINT32 x;
106
107 if ((pAd->EepromAccess) ||
108 (RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_RESET_IN_PROGRESS)) ||
109 (RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_HALT_IN_PROGRESS)) ||
110 (RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_RADIO_OFF)) ||
111 (RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_NIC_NOT_EXIST)))
112 {
113 return;
114 }
115
116 // the antenna selection is through firmware and MAC register(GPIO3)
117 if (Ant == 0)
118 {
119 // Main antenna
120 RTMP_IO_READ32(pAd, E2PROM_CSR, &x);
121 x |= (EESK);
122 RTMP_IO_WRITE32(pAd, E2PROM_CSR, x);
123
124 RTMP_IO_READ32(pAd, GPIO_CTRL_CFG, &Value);
125 Value &= ~(0x0808);
126 RTMP_IO_WRITE32(pAd, GPIO_CTRL_CFG, Value);
127 DBGPRINT_RAW(RT_DEBUG_TRACE, ("AsicSetRxAnt, switch to main antenna\n"));
128 }
129 else
130 {
131 // Aux antenna
132 RTMP_IO_READ32(pAd, E2PROM_CSR, &x);
133 x &= ~(EESK);
134 RTMP_IO_WRITE32(pAd, E2PROM_CSR, x);
135
136 RTMP_IO_READ32(pAd, GPIO_CTRL_CFG, &Value);
137 Value &= ~(0x0808);
138 Value |= 0x08;
139 RTMP_IO_WRITE32(pAd, GPIO_CTRL_CFG, Value);
140 DBGPRINT_RAW(RT_DEBUG_TRACE, ("AsicSetRxAnt, switch to aux antenna\n"));
141 }
142}
143
144
145/*
146 ========================================================================
147
148 Routine Description:
149 For RF filter calibration purpose
150
151 Arguments:
152 pAd Pointer to our adapter
153
154 Return Value:
155 None
156
157 IRQL = PASSIVE_LEVEL
158
159 ========================================================================
160*/
161VOID RTMPFilterCalibration(
162 IN PRTMP_ADAPTER pAd)
163{
164 UCHAR R55x = 0, value, FilterTarget = 0x1E, BBPValue=0;
165 UINT loop = 0, count = 0, loopcnt = 0, ReTry = 0;
166 UCHAR RF_R24_Value = 0;
167
168 // Give bbp filter initial value
169 pAd->Mlme.CaliBW20RfR24 = 0x1F;
170 pAd->Mlme.CaliBW40RfR24 = 0x2F; //Bit[5] must be 1 for BW 40
171
172 do
173 {
174 if (loop == 1) //BandWidth = 40 MHz
175 {
176 // Write 0x27 to RF_R24 to program filter
177 RF_R24_Value = 0x27;
178 RT30xxWriteRFRegister(pAd, RF_R24, RF_R24_Value);
179 if (IS_RT3090(pAd) || IS_RT3572(pAd)|| IS_RT3390(pAd))
180 FilterTarget = 0x15;
181 else
182 FilterTarget = 0x19;
183
184 // when calibrate BW40, BBP mask must set to BW40.
185 RTMP_BBP_IO_READ8_BY_REG_ID(pAd, BBP_R4, &BBPValue);
186 BBPValue&= (~0x18);
187 BBPValue|= (0x10);
188 RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R4, BBPValue);
189
190 // set to BW40
191 RT30xxReadRFRegister(pAd, RF_R31, &value);
192 value |= 0x20;
193 RT30xxWriteRFRegister(pAd, RF_R31, value);
194 }
195 else //BandWidth = 20 MHz
196 {
197 // Write 0x07 to RF_R24 to program filter
198 RF_R24_Value = 0x07;
199 RT30xxWriteRFRegister(pAd, RF_R24, RF_R24_Value);
200 if (IS_RT3090(pAd) || IS_RT3572(pAd)|| IS_RT3390(pAd))
201 FilterTarget = 0x13;
202 else
203 FilterTarget = 0x16;
204
205 // set to BW20
206 RT30xxReadRFRegister(pAd, RF_R31, &value);
207 value &= (~0x20);
208 RT30xxWriteRFRegister(pAd, RF_R31, value);
209 }
210
211 // Write 0x01 to RF_R22 to enable baseband loopback mode
212 RT30xxReadRFRegister(pAd, RF_R22, &value);
213 value |= 0x01;
214 RT30xxWriteRFRegister(pAd, RF_R22, value);
215
216 // Write 0x00 to BBP_R24 to set power & frequency of passband test tone
217 RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R24, 0);
218
219 do
220 {
221 // Write 0x90 to BBP_R25 to transmit test tone
222 RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R25, 0x90);
223
224 RTMPusecDelay(1000);
225 // Read BBP_R55[6:0] for received power, set R55x = BBP_R55[6:0]
226 RTMP_BBP_IO_READ8_BY_REG_ID(pAd, BBP_R55, &value);
227 R55x = value & 0xFF;
228
229 } while ((ReTry++ < 100) && (R55x == 0));
230
231 // Write 0x06 to BBP_R24 to set power & frequency of stopband test tone
232 RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R24, 0x06);
233
234 while(TRUE)
235 {
236 // Write 0x90 to BBP_R25 to transmit test tone
237 RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R25, 0x90);
238
239 //We need to wait for calibration
240 RTMPusecDelay(1000);
241 RTMP_BBP_IO_READ8_BY_REG_ID(pAd, BBP_R55, &value);
242 value &= 0xFF;
243 if ((R55x - value) < FilterTarget)
244 {
245 RF_R24_Value ++;
246 }
247 else if ((R55x - value) == FilterTarget)
248 {
249 RF_R24_Value ++;
250 count ++;
251 }
252 else
253 {
254 break;
255 }
256
257 // prevent infinite loop cause driver hang.
258 if (loopcnt++ > 100)
259 {
260 DBGPRINT(RT_DEBUG_ERROR, ("RTMPFilterCalibration - can't find a valid value, loopcnt=%d stop calibrating", loopcnt));
261 break;
262 }
263
264 // Write RF_R24 to program filter
265 RT30xxWriteRFRegister(pAd, RF_R24, RF_R24_Value);
266 }
267
268 if (count > 0)
269 {
270 RF_R24_Value = RF_R24_Value - ((count) ? (1) : (0));
271 }
272
273 // Store for future usage
274 if (loopcnt < 100)
275 {
276 if (loop++ == 0)
277 {
278 //BandWidth = 20 MHz
279 pAd->Mlme.CaliBW20RfR24 = (UCHAR)RF_R24_Value;
280 }
281 else
282 {
283 //BandWidth = 40 MHz
284 pAd->Mlme.CaliBW40RfR24 = (UCHAR)RF_R24_Value;
285 break;
286 }
287 }
288 else
289 break;
290
291 RT30xxWriteRFRegister(pAd, RF_R24, RF_R24_Value);
292
293 // reset count
294 count = 0;
295 } while(TRUE);
296
297 //
298 // Set back to initial state
299 //
300 RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R24, 0);
301
302 RT30xxReadRFRegister(pAd, RF_R22, &value);
303 value &= ~(0x01);
304 RT30xxWriteRFRegister(pAd, RF_R22, value);
305
306 // set BBP back to BW20
307 RTMP_BBP_IO_READ8_BY_REG_ID(pAd, BBP_R4, &BBPValue);
308 BBPValue&= (~0x18);
309 RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R4, BBPValue);
310
311 DBGPRINT(RT_DEBUG_TRACE, ("RTMPFilterCalibration - CaliBW20RfR24=0x%x, CaliBW40RfR24=0x%x\n", pAd->Mlme.CaliBW20RfR24, pAd->Mlme.CaliBW40RfR24));
312}
313
314
315// add by johnli, RF power sequence setup
316/*
317 ==========================================================================
318 Description:
319
320 Load RF normal operation-mode setup
321
322 ==========================================================================
323 */
324VOID RT33xxLoadRFNormalModeSetup(
325 IN PRTMP_ADAPTER pAd)
326{
327 UCHAR RFValue;
328
329 // RX0_PD & TX0_PD, RF R1 register Bit 2 & Bit 3 to 0 and RF_BLOCK_en,RX1_PD & TX1_PD, Bit0, Bit 4 & Bit5 to 1
330 RT30xxReadRFRegister(pAd, RF_R01, &RFValue);
331 RFValue = (RFValue & (~0x0C)) | 0x31;
332 RT30xxWriteRFRegister(pAd, RF_R01, RFValue);
333
334 // TX_LO2_en, RF R15 register Bit 3 to 0
335 RT30xxReadRFRegister(pAd, RF_R15, &RFValue);
336 RFValue &= (~0x08);
337 RT30xxWriteRFRegister(pAd, RF_R15, RFValue);
338
339 /* move to NICInitRT30xxRFRegisters
340 // TX_LO1_en, RF R17 register Bit 3 to 0
341 RT30xxReadRFRegister(pAd, RF_R17, &RFValue);
342 RFValue &= (~0x08);
343 // to fix rx long range issue
344 if (((pAd->MACVersion & 0xffff) >= 0x0211) && (pAd->NicConfig2.field.ExternalLNAForG == 0))
345 {
346 RFValue |= 0x20;
347 }
348 // set RF_R17_bit[2:0] equal to EEPROM setting at 0x48h
349 if (pAd->TxMixerGain24G >= 2)
350 {
351 RFValue &= (~0x7); // clean bit [2:0]
352 RFValue |= pAd->TxMixerGain24G;
353 }
354 RT30xxWriteRFRegister(pAd, RF_R17, RFValue);
355 */
356
357 // RX_LO1_en, RF R20 register Bit 3 to 0
358 RT30xxReadRFRegister(pAd, RF_R20, &RFValue);
359 RFValue &= (~0x08);
360 RT30xxWriteRFRegister(pAd, RF_R20, RFValue);
361
362 // RX_LO2_en, RF R21 register Bit 3 to 0
363 RT30xxReadRFRegister(pAd, RF_R21, &RFValue);
364 RFValue &= (~0x08);
365 RT30xxWriteRFRegister(pAd, RF_R21, RFValue);
366
367 /* add by johnli, reset RF_R27 when interface down & up to fix throughput problem*/
368 // LDORF_VC, RF R27 register Bit 2 to 0
369 RT30xxReadRFRegister(pAd, RF_R27, &RFValue);
370 // TX to RX IQ glitch(RF_R27) has been fixed in RT3070(F).
371 // Raising RF voltage is no longer needed for RT3070(F)
372 if (IS_RT3090(pAd)) // RT309x and RT3071/72
373 {
374 if ((pAd->MACVersion & 0xffff) < 0x0211)
375 RFValue = (RFValue & (~0x77)) | 0x3;
376 else
377 RFValue = (RFValue & (~0x77));
378 RT30xxWriteRFRegister(pAd, RF_R27, RFValue);
379 }
380 /* end johnli */
381}
382
383/*
384 ==========================================================================
385 Description:
386
387 Load RF sleep-mode setup
388
389 ==========================================================================
390 */
391VOID RT33xxLoadRFSleepModeSetup(
392 IN PRTMP_ADAPTER pAd)
393{
394 UCHAR RFValue;
395 UINT32 MACValue;
396
397
398 {
399 // RF_BLOCK_en. RF R1 register Bit 0 to 0
400 RT30xxReadRFRegister(pAd, RF_R01, &RFValue);
401 RFValue &= (~0x01);
402 RT30xxWriteRFRegister(pAd, RF_R01, RFValue);
403
404 // VCO_IC, RF R7 register Bit 4 & Bit 5 to 0
405 RT30xxReadRFRegister(pAd, RF_R07, &RFValue);
406 RFValue &= (~0x30);
407 RT30xxWriteRFRegister(pAd, RF_R07, RFValue);
408
409 // Idoh, RF R9 register Bit 1, Bit 2 & Bit 3 to 0
410 RT30xxReadRFRegister(pAd, RF_R09, &RFValue);
411 RFValue &= (~0x0E);
412 RT30xxWriteRFRegister(pAd, RF_R09, RFValue);
413
414 // RX_CTB_en, RF R21 register Bit 7 to 0
415 RT30xxReadRFRegister(pAd, RF_R21, &RFValue);
416 RFValue &= (~0x80);
417 RT30xxWriteRFRegister(pAd, RF_R21, RFValue);
418 }
419
420 if (IS_RT3090(pAd) || // IS_RT3090 including RT309x and RT3071/72
421 IS_RT3572(pAd) ||
422 IS_RT3390(pAd) ||
423 (IS_RT3070(pAd) && ((pAd->MACVersion & 0xffff) < 0x0201)))
424 {
425 {
426 RT30xxReadRFRegister(pAd, RF_R27, &RFValue);
427 RFValue |= 0x77;
428 RT30xxWriteRFRegister(pAd, RF_R27, RFValue);
429 }
430
431 RTMP_IO_READ32(pAd, LDO_CFG0, &MACValue);
432 MACValue |= 0x1D000000;
433 RTMP_IO_WRITE32(pAd, LDO_CFG0, MACValue);
434 }
435}
436
437/*
438 ==========================================================================
439 Description:
440
441 Reverse RF sleep-mode setup
442
443 ==========================================================================
444 */
445VOID RT33xxReverseRFSleepModeSetup(
446 IN PRTMP_ADAPTER pAd)
447{
448 UCHAR RFValue;
449 UINT32 MACValue;
450
451 {
452 // RF_BLOCK_en, RF R1 register Bit 0 to 1
453 RT30xxReadRFRegister(pAd, RF_R01, &RFValue);
454 RFValue |= 0x01;
455 RT30xxWriteRFRegister(pAd, RF_R01, RFValue);
456
457 // VCO_IC, RF R7 register Bit 4 & Bit 5 to 1
458 RT30xxReadRFRegister(pAd, RF_R07, &RFValue);
459 RFValue |= 0x30;
460 RT30xxWriteRFRegister(pAd, RF_R07, RFValue);
461
462 // Idoh, RF R9 register Bit 1, Bit 2 & Bit 3 to 1
463 RT30xxReadRFRegister(pAd, RF_R09, &RFValue);
464 RFValue |= 0x0E;
465 RT30xxWriteRFRegister(pAd, RF_R09, RFValue);
466
467 // RX_CTB_en, RF R21 register Bit 7 to 1
468 RT30xxReadRFRegister(pAd, RF_R21, &RFValue);
469 RFValue |= 0x80;
470 RT30xxWriteRFRegister(pAd, RF_R21, RFValue);
471 }
472
473 if (IS_RT3090(pAd) || // IS_RT3090 including RT309x and RT3071/72
474 IS_RT3572(pAd) ||
475 IS_RT3390(pAd) ||
476 (IS_RT3070(pAd) && ((pAd->MACVersion & 0xffff) < 0x0201)))
477 {
478 {
479 RT30xxReadRFRegister(pAd, RF_R27, &RFValue);
480 if ((pAd->MACVersion & 0xffff) < 0x0211)
481 RFValue = (RFValue & (~0x77)) | 0x3;
482 else
483 RFValue = (RFValue & (~0x77));
484 RT30xxWriteRFRegister(pAd, RF_R27, RFValue);
485 }
486
487 // RT3071 version E has fixed this issue
488 if ((pAd->NicConfig2.field.DACTestBit == 1) && ((pAd->MACVersion & 0xffff) < 0x0211))
489 {
490 // patch tx EVM issue temporarily
491 RTMP_IO_READ32(pAd, LDO_CFG0, &MACValue);
492 MACValue = ((MACValue & 0xE0FFFFFF) | 0x0D000000);
493 RTMP_IO_WRITE32(pAd, LDO_CFG0, MACValue);
494 }
495 else
496 {
497 RTMP_IO_READ32(pAd, LDO_CFG0, &MACValue);
498 MACValue = ((MACValue & 0xE0FFFFFF) | 0x01000000);
499 RTMP_IO_WRITE32(pAd, LDO_CFG0, MACValue);
500 }
501 }
502
503 if(IS_RT3572(pAd))
504 RT30xxWriteRFRegister(pAd, RF_R08, 0x80);
505}
506// end johnli
507
508VOID RT33xxHaltAction(
509 IN PRTMP_ADAPTER pAd)
510{
511 UINT32 TxPinCfg = 0x00050F0F;
512
513 //
514 // Turn off LNA_PE or TRSW_POL
515 //
516 if (IS_RT3070(pAd) || IS_RT3071(pAd) || IS_RT3390(pAd)||IS_RT3572(pAd))
517 {
518 //KH? Both support 3390 usb and PCI
519 if ((IS_RT3071(pAd) || IS_RT3572(pAd)||IS_RT3390(pAd))
520#ifdef RTMP_EFUSE_SUPPORT
521 && (pAd->bUseEfuse)
522#endif // RTMP_EFUSE_SUPPORT //
523 )
524 {
525 TxPinCfg &= 0xFFFBF0F0; // bit18 off
526 }
527 else
528 {
529 TxPinCfg &= 0xFFFFF0F0;
530 }
531
532 RTMP_IO_WRITE32(pAd, TX_PIN_CFG, TxPinCfg);
533 }
534}
535
536#endif // RT30xx //