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 Ralink Wireless Chip PHY(BBP/RF) related definition & structures
35 -------- ---------- ----------------------------------------------
38 #ifndef __RTMP_PHY_H__
39 #define __RTMP_PHY_H__
77 /* value domain of pAd->RfIcType */
78 #define RFIC_2820 1 /* 2.4G 2T3R */
79 #define RFIC_2850 2 /* 2.4G/5G 2T3R */
80 #define RFIC_2720 3 /* 2.4G 1T2R */
81 #define RFIC_2750 4 /* 2.4G/5G 1T2R */
82 #define RFIC_3020 5 /* 2.4G 1T1R */
83 #define RFIC_2020 6 /* 2.4G B/G */
84 #define RFIC_3021 7 /* 2.4G 1T2R */
85 #define RFIC_3022 8 /* 2.4G 2T2R */
86 #define RFIC_3052 9 /* 2.4G/5G 2T2R */
91 #define BBP_R0 0 /* version */
92 #define BBP_R1 1 /* TSSI */
93 #define BBP_R2 2 /* TX configure */
98 #define BBP_R14 14 /* RX configure */
100 #define BBP_R17 17 /* RX sensibility */
109 #define BBP_R49 49 /*TSSI */
114 #define BBP_R62 62 /* Rx SQ0 Threshold HIGH */
122 #define BBP_R70 70 /* Rx AGC SQ CCK Xcorr threshold */
136 #define BBP_R94 94 /* Tx Gain Control */
152 #define BBP_R138 138 /* add by johnli, RF power sequence setup, ADC dynamic on/off control */
153 #endif /* RT30xx // */
155 #define BBPR94_DEFAULT 0x06 /* Add 1 value will gain 1db */
158 /* BBP & RF are using indirect access. Before write any value into it. */
159 /* We have to make sure there is no outstanding command pending via checking busy bit. */
161 #define MAX_BUSY_COUNT 100 /* Number of retry before failing access BBP & RF indirect register */
163 /*#define PHY_TR_SWITCH_TIME 5 // usec */
165 /*#define BBP_R17_LOW_SENSIBILITY 0x50 */
166 /*#define BBP_R17_MID_SENSIBILITY 0x41 */
167 /*#define BBP_R17_DYNAMIC_UP_BOUND 0x40 */
169 #define RSSI_FOR_VERY_LOW_SENSIBILITY -35
170 #define RSSI_FOR_LOW_SENSIBILITY -58
171 #define RSSI_FOR_MID_LOW_SENSIBILITY -80
172 #define RSSI_FOR_MID_SENSIBILITY -90
174 /*****************************************************************************
175 RF register Read/Write marco definition
176 *****************************************************************************/
178 #define RTMP_RF_IO_WRITE32(_A, _V) \
180 if ((_A)->bPCIclkOff == FALSE) \
182 PHY_CSR4_STRUC _value; \
183 unsigned long _busyCnt = 0; \
186 RTMP_IO_READ32((_A), RF_CSR_CFG0, &_value.word); \
187 if (_value.field.Busy == IDLE) \
190 }while (_busyCnt < MAX_BUSY_COUNT); \
191 if(_busyCnt < MAX_BUSY_COUNT) \
193 RTMP_IO_WRITE32((_A), RF_CSR_CFG0, (_V)); \
197 #endif /* RTMP_MAC_PCI // */
199 #define RTMP_RF_IO_WRITE32(_A, _V) RTUSBWriteRFRegister(_A, _V)
200 #endif /* RTMP_MAC_USB // */
203 #define RTMP_RF_IO_READ8_BY_REG_ID(_A, _I, _pV) RT30xxReadRFRegister(_A, _I, _pV)
204 #define RTMP_RF_IO_WRITE8_BY_REG_ID(_A, _I, _V) RT30xxWriteRFRegister(_A, _I, _V)
205 #endif /* RT30xx // */
207 /*****************************************************************************
208 BBP register Read/Write marco definitions.
209 we read/write the bbp value by register's ID.
210 Generate PER to test BA
211 *****************************************************************************/
214 basic marco for BBP read operation.
215 _pAd: the data structure pointer of struct rt_rtmp_adapter
216 _bbpID : the bbp register ID
217 _pV: data pointer used to save the value of queried bbp register.
218 _bViaMCU: if we need access the bbp via the MCU.
220 #define RTMP_BBP_IO_READ8(_pAd, _bbpID, _pV, _bViaMCU) \
222 BBP_CSR_CFG_STRUC BbpCsr; \
223 int _busyCnt, _secCnt, _regID; \
225 _regID = ((_bViaMCU) == TRUE ? H2M_BBP_AGENT : BBP_CSR_CFG); \
226 for (_busyCnt=0; _busyCnt<MAX_BUSY_COUNT; _busyCnt++) \
228 RTMP_IO_READ32(_pAd, _regID, &BbpCsr.word); \
229 if (BbpCsr.field.Busy == BUSY) \
232 BbpCsr.field.fRead = 1; \
233 BbpCsr.field.BBP_RW_MODE = 1; \
234 BbpCsr.field.Busy = 1; \
235 BbpCsr.field.RegNum = _bbpID; \
236 RTMP_IO_WRITE32(_pAd, _regID, BbpCsr.word); \
237 if ((_bViaMCU) == TRUE) \
239 AsicSendCommandToMcu(_pAd, 0x80, 0xff, 0x0, 0x0); \
240 RTMPusecDelay(1000); \
242 for (_secCnt=0; _secCnt<MAX_BUSY_COUNT; _secCnt++) \
244 RTMP_IO_READ32(_pAd, _regID, &BbpCsr.word); \
245 if (BbpCsr.field.Busy == IDLE) \
248 if ((BbpCsr.field.Busy == IDLE) && \
249 (BbpCsr.field.RegNum == _bbpID)) \
251 *(_pV) = (u8)BbpCsr.field.Value; \
255 if (BbpCsr.field.Busy == BUSY) \
257 DBGPRINT_ERR(("BBP(viaMCU=%d) read R%d fail\n", (_bViaMCU), _bbpID)); \
258 *(_pV) = (_pAd)->BbpWriteLatch[_bbpID]; \
259 if ((_bViaMCU) == TRUE) \
261 RTMP_IO_READ32(_pAd, _regID, &BbpCsr.word); \
262 BbpCsr.field.Busy = 0; \
263 RTMP_IO_WRITE32(_pAd, _regID, BbpCsr.word); \
269 This marco used for the BBP read operation which didn't need via MCU.
271 #define BBP_IO_READ8_BY_REG_ID(_A, _I, _pV) \
272 RTMP_BBP_IO_READ8((_A), (_I), (_pV), FALSE)
275 This marco used for the BBP read operation which need via MCU.
276 But for some chipset which didn't have mcu (e.g., RBUS based chipset), we
277 will use this function too and didn't access the bbp register via the MCU.
279 /* Read BBP register by register's ID. Generate PER to test BA */
280 #define RTMP_BBP_IO_READ8_BY_REG_ID(_A, _I, _pV) \
282 BBP_CSR_CFG_STRUC BbpCsr; \
285 BbpCsr.field.Busy = IDLE; \
286 if ((IS_RT3090((_A)) || IS_RT3572((_A)) || IS_RT3390((_A))) && ((_A)->StaCfg.PSControl.field.rt30xxPowerMode == 3) \
287 && ((_A)->StaCfg.PSControl.field.EnableNewPS == TRUE) \
288 && ((_A)->bPCIclkOff == FALSE) \
289 && ((_A)->brt30xxBanMcuCmd == FALSE)) \
291 for (i=0; i<MAX_BUSY_COUNT; i++) \
293 RTMP_IO_READ32(_A, H2M_BBP_AGENT, &BbpCsr.word); \
294 if (BbpCsr.field.Busy == BUSY) \
299 BbpCsr.field.fRead = 1; \
300 BbpCsr.field.BBP_RW_MODE = 1; \
301 BbpCsr.field.Busy = 1; \
302 BbpCsr.field.RegNum = _I; \
303 RTMP_IO_WRITE32(_A, H2M_BBP_AGENT, BbpCsr.word); \
304 brc = AsicSendCommandToMcu(_A, 0x80, 0xff, 0x0, 0x0); \
307 for (k=0; k<MAX_BUSY_COUNT; k++) \
309 RTMP_IO_READ32(_A, H2M_BBP_AGENT, &BbpCsr.word); \
310 if (BbpCsr.field.Busy == IDLE) \
313 if ((BbpCsr.field.Busy == IDLE) && \
314 (BbpCsr.field.RegNum == _I)) \
316 *(_pV) = (u8)BbpCsr.field.Value; \
322 BbpCsr.field.Busy = 0; \
323 RTMP_IO_WRITE32(_A, H2M_BBP_AGENT, BbpCsr.word); \
327 else if (!((IS_RT3090((_A)) || IS_RT3572((_A)) || IS_RT3390((_A))) && ((_A)->StaCfg.PSControl.field.rt30xxPowerMode == 3) \
328 && ((_A)->StaCfg.PSControl.field.EnableNewPS == TRUE)) \
329 && ((_A)->bPCIclkOff == FALSE)) \
331 for (i=0; i<MAX_BUSY_COUNT; i++) \
333 RTMP_IO_READ32(_A, H2M_BBP_AGENT, &BbpCsr.word); \
334 if (BbpCsr.field.Busy == BUSY) \
339 BbpCsr.field.fRead = 1; \
340 BbpCsr.field.BBP_RW_MODE = 1; \
341 BbpCsr.field.Busy = 1; \
342 BbpCsr.field.RegNum = _I; \
343 RTMP_IO_WRITE32(_A, H2M_BBP_AGENT, BbpCsr.word); \
344 AsicSendCommandToMcu(_A, 0x80, 0xff, 0x0, 0x0); \
345 for (k=0; k<MAX_BUSY_COUNT; k++) \
347 RTMP_IO_READ32(_A, H2M_BBP_AGENT, &BbpCsr.word); \
348 if (BbpCsr.field.Busy == IDLE) \
351 if ((BbpCsr.field.Busy == IDLE) && \
352 (BbpCsr.field.RegNum == _I)) \
354 *(_pV) = (u8)BbpCsr.field.Value; \
361 DBGPRINT_ERR((" , brt30xxBanMcuCmd = %d, Read BBP %d \n", (_A)->brt30xxBanMcuCmd, (_I))); \
362 *(_pV) = (_A)->BbpWriteLatch[_I]; \
364 if ((BbpCsr.field.Busy == BUSY) || ((_A)->bPCIclkOff == TRUE)) \
366 DBGPRINT_ERR(("BBP read R%d=0x%x fail\n", _I, BbpCsr.word)); \
367 *(_pV) = (_A)->BbpWriteLatch[_I]; \
372 basic marco for BBP write operation.
373 _pAd: the data structure pointer of struct rt_rtmp_adapter
374 _bbpID : the bbp register ID
375 _pV: data used to save the value of queried bbp register.
376 _bViaMCU: if we need access the bbp via the MCU.
378 #define RTMP_BBP_IO_WRITE8(_pAd, _bbpID, _pV, _bViaMCU) \
380 BBP_CSR_CFG_STRUC BbpCsr; \
381 int _busyCnt, _regID; \
383 _regID = ((_bViaMCU) == TRUE ? H2M_BBP_AGENT : BBP_CSR_CFG); \
384 for (_busyCnt=0; _busyCnt<MAX_BUSY_COUNT; _busyCnt++) \
386 RTMP_IO_READ32((_pAd), BBP_CSR_CFG, &BbpCsr.word); \
387 if (BbpCsr.field.Busy == BUSY) \
390 BbpCsr.field.fRead = 0; \
391 BbpCsr.field.BBP_RW_MODE = 1; \
392 BbpCsr.field.Busy = 1; \
393 BbpCsr.field.Value = _pV; \
394 BbpCsr.field.RegNum = _bbpID; \
395 RTMP_IO_WRITE32((_pAd), BBP_CSR_CFG, BbpCsr.word); \
396 if ((_bViaMCU) == TRUE) \
398 AsicSendCommandToMcu(_pAd, 0x80, 0xff, 0x0, 0x0); \
399 if ((_pAd)->OpMode == OPMODE_AP) \
400 RTMPusecDelay(1000); \
402 (_pAd)->BbpWriteLatch[_bbpID] = _pV; \
405 if (_busyCnt == MAX_BUSY_COUNT) \
407 DBGPRINT_ERR(("BBP write R%d fail\n", _bbpID)); \
408 if((_bViaMCU) == TRUE) \
410 RTMP_IO_READ32(_pAd, H2M_BBP_AGENT, &BbpCsr.word); \
411 BbpCsr.field.Busy = 0; \
412 RTMP_IO_WRITE32(_pAd, H2M_BBP_AGENT, BbpCsr.word); \
418 This marco used for the BBP write operation which didn't need via MCU.
420 #define BBP_IO_WRITE8_BY_REG_ID(_A, _I, _pV) \
421 RTMP_BBP_IO_WRITE8((_A), (_I), (_pV), FALSE)
424 This marco used for the BBP write operation which need via MCU.
425 But for some chipset which didn't have mcu (e.g., RBUS based chipset), we
426 will use this function too and didn't access the bbp register via the MCU.
428 /* Write BBP register by register's ID & value */
429 #define RTMP_BBP_IO_WRITE8_BY_REG_ID(_A, _I, _V) \
431 BBP_CSR_CFG_STRUC BbpCsr; \
434 if (_I < MAX_NUM_OF_BBP_LATCH) \
436 if ((IS_RT3090((_A)) || IS_RT3572((_A)) || IS_RT3390((_A))) && ((_A)->StaCfg.PSControl.field.rt30xxPowerMode == 3) \
437 && ((_A)->StaCfg.PSControl.field.EnableNewPS == TRUE) \
438 && ((_A)->bPCIclkOff == FALSE) \
439 && ((_A)->brt30xxBanMcuCmd == FALSE)) \
441 if (_A->AccessBBPFailCount > 20) \
443 AsicResetBBPAgent(_A); \
444 _A->AccessBBPFailCount = 0; \
446 for (BusyCnt=0; BusyCnt<MAX_BUSY_COUNT; BusyCnt++) \
448 RTMP_IO_READ32(_A, H2M_BBP_AGENT, &BbpCsr.word); \
449 if (BbpCsr.field.Busy == BUSY) \
452 BbpCsr.field.fRead = 0; \
453 BbpCsr.field.BBP_RW_MODE = 1; \
454 BbpCsr.field.Busy = 1; \
455 BbpCsr.field.Value = _V; \
456 BbpCsr.field.RegNum = _I; \
457 RTMP_IO_WRITE32(_A, H2M_BBP_AGENT, BbpCsr.word); \
458 brc = AsicSendCommandToMcu(_A, 0x80, 0xff, 0x0, 0x0); \
461 (_A)->BbpWriteLatch[_I] = _V; \
465 BbpCsr.field.Busy = 0; \
466 RTMP_IO_WRITE32(_A, H2M_BBP_AGENT, BbpCsr.word); \
471 else if (!((IS_RT3090((_A)) || IS_RT3572((_A)) || IS_RT3390((_A))) && ((_A)->StaCfg.PSControl.field.rt30xxPowerMode == 3) \
472 && ((_A)->StaCfg.PSControl.field.EnableNewPS == TRUE)) \
473 && ((_A)->bPCIclkOff == FALSE)) \
475 if (_A->AccessBBPFailCount > 20) \
477 AsicResetBBPAgent(_A); \
478 _A->AccessBBPFailCount = 0; \
480 for (BusyCnt=0; BusyCnt<MAX_BUSY_COUNT; BusyCnt++) \
482 RTMP_IO_READ32(_A, H2M_BBP_AGENT, &BbpCsr.word); \
483 if (BbpCsr.field.Busy == BUSY) \
486 BbpCsr.field.fRead = 0; \
487 BbpCsr.field.BBP_RW_MODE = 1; \
488 BbpCsr.field.Busy = 1; \
489 BbpCsr.field.Value = _V; \
490 BbpCsr.field.RegNum = _I; \
491 RTMP_IO_WRITE32(_A, H2M_BBP_AGENT, BbpCsr.word); \
492 AsicSendCommandToMcu(_A, 0x80, 0xff, 0x0, 0x0); \
493 (_A)->BbpWriteLatch[_I] = _V; \
499 DBGPRINT_ERR((" brt30xxBanMcuCmd = %d. Write BBP %d \n", (_A)->brt30xxBanMcuCmd, (_I))); \
501 if ((BusyCnt == MAX_BUSY_COUNT) || ((_A)->bPCIclkOff == TRUE)) \
503 if (BusyCnt == MAX_BUSY_COUNT) \
504 (_A)->AccessBBPFailCount++; \
505 DBGPRINT_ERR(("BBP write R%d=0x%x fail. BusyCnt= %d.bPCIclkOff = %d. \n", _I, BbpCsr.word, BusyCnt, (_A)->bPCIclkOff )); \
510 DBGPRINT_ERR(("****** BBP_Write_Latch Buffer exceeds max boundry ****** \n")); \
513 #endif /* RTMP_MAC_PCI // */
516 #define RTMP_BBP_IO_READ8_BY_REG_ID(_A, _I, _pV) RTUSBReadBBPRegister(_A, _I, _pV)
517 #define RTMP_BBP_IO_WRITE8_BY_REG_ID(_A, _I, _V) RTUSBWriteBBPRegister(_A, _I, _V)
519 #define BBP_IO_WRITE8_BY_REG_ID(_A, _I, _V) RTUSBWriteBBPRegister(_A, _I, _V)
520 #define BBP_IO_READ8_BY_REG_ID(_A, _I, _pV) RTUSBReadBBPRegister(_A, _I, _pV)
521 #endif /* RTMP_MAC_USB // */
524 #define RTMP_ASIC_MMPS_DISABLE(_pAd) \
528 /* disable MMPS BBP control register */ \
529 RTMP_BBP_IO_READ8_BY_REG_ID(_pAd, BBP_R3, &_bbpData); \
530 _bbpData &= ~(0x04); /*bit 2*/ \
531 RTMP_BBP_IO_WRITE8_BY_REG_ID(_pAd, BBP_R3, _bbpData); \
533 /* disable MMPS MAC control register */ \
534 RTMP_IO_READ32(_pAd, 0x1210, &_macData); \
535 _macData &= ~(0x09); /*bit 0, 3*/ \
536 RTMP_IO_WRITE32(_pAd, 0x1210, _macData); \
539 #define RTMP_ASIC_MMPS_ENABLE(_pAd) \
543 /* enable MMPS BBP control register */ \
544 RTMP_BBP_IO_READ8_BY_REG_ID(_pAd, BBP_R3, &_bbpData); \
545 _bbpData |= (0x04); /*bit 2*/ \
546 RTMP_BBP_IO_WRITE8_BY_REG_ID(_pAd, BBP_R3, _bbpData); \
548 /* enable MMPS MAC control register */ \
549 RTMP_IO_READ32(_pAd, 0x1210, &_macData); \
550 _macData |= (0x09); /*bit 0, 3*/ \
551 RTMP_IO_WRITE32(_pAd, 0x1210, _macData); \
554 #endif /* RT30xx // */
556 #endif /* __RTMP_PHY_H__ // */