]> git.proxmox.com Git - mirror_ubuntu-artful-kernel.git/blame - drivers/staging/rtl8723bs/hal/odm_DIG.c
Merge tag 'iio-for-4.13b' of git://git.kernel.org/pub/scm/linux/kernel/git/jic23...
[mirror_ubuntu-artful-kernel.git] / drivers / staging / rtl8723bs / hal / odm_DIG.c
CommitLineData
554c0a3a
HG
1/******************************************************************************
2 *
3 * Copyright(c) 2007 - 2011 Realtek Corporation. All rights reserved.
4 *
5 * This program is free software; you can redistribute it and/or modify it
6 * under the terms of version 2 of the GNU General Public License as
7 * published by the Free Software Foundation.
8 *
9 * This program is distributed in the hope that it will be useful, but WITHOUT
10 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
11 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
12 * more details.
13 *
14 ******************************************************************************/
15
16#include "odm_precomp.h"
17
18#define ADAPTIVITY_VERSION "5.0"
19
20void odm_NHMCounterStatisticsInit(void *pDM_VOID)
21{
22 PDM_ODM_T pDM_Odm = (PDM_ODM_T)pDM_VOID;
23
24 /* PHY parameters initialize for n series */
25 rtw_write16(pDM_Odm->Adapter, ODM_REG_NHM_TIMER_11N+2, 0x2710); /* 0x894[31:16]= 0x2710 Time duration for NHM unit: 4us, 0x2710 =40ms */
26 /* rtw_write16(pDM_Odm->Adapter, ODM_REG_NHM_TIMER_11N+2, 0x4e20); 0x894[31:16]= 0x4e20 Time duration for NHM unit: 4us, 0x4e20 =80ms */
27 rtw_write16(pDM_Odm->Adapter, ODM_REG_NHM_TH9_TH10_11N+2, 0xffff); /* 0x890[31:16]= 0xffff th_9, th_10 */
28 /* rtw_write32(pDM_Odm->Adapter, ODM_REG_NHM_TH3_TO_TH0_11N, 0xffffff5c); 0x898 = 0xffffff5c th_3, th_2, th_1, th_0 */
29 rtw_write32(pDM_Odm->Adapter, ODM_REG_NHM_TH3_TO_TH0_11N, 0xffffff52); /* 0x898 = 0xffffff52 th_3, th_2, th_1, th_0 */
30 rtw_write32(pDM_Odm->Adapter, ODM_REG_NHM_TH7_TO_TH4_11N, 0xffffffff); /* 0x89c = 0xffffffff th_7, th_6, th_5, th_4 */
31 PHY_SetBBReg(pDM_Odm->Adapter, ODM_REG_FPGA0_IQK_11N, bMaskByte0, 0xff); /* 0xe28[7:0]= 0xff th_8 */
32 PHY_SetBBReg(pDM_Odm->Adapter, ODM_REG_NHM_TH9_TH10_11N, BIT10|BIT9|BIT8, 0x7); /* 0x890[9:8]=3 enable CCX */
33 PHY_SetBBReg(pDM_Odm->Adapter, ODM_REG_OFDM_FA_RSTC_11N, BIT7, 0x1); /* 0xc0c[7]= 1 max power among all RX ants */
34}
35
36void odm_NHMCounterStatistics(void *pDM_VOID)
37{
38 PDM_ODM_T pDM_Odm = (PDM_ODM_T)pDM_VOID;
39
40 /* Get NHM report */
41 odm_GetNHMCounterStatistics(pDM_Odm);
42
43 /* Reset NHM counter */
44 odm_NHMCounterStatisticsReset(pDM_Odm);
45}
46
47void odm_GetNHMCounterStatistics(void *pDM_VOID)
48{
49 PDM_ODM_T pDM_Odm = (PDM_ODM_T)pDM_VOID;
50 u32 value32 = 0;
51
52 value32 = PHY_QueryBBReg(pDM_Odm->Adapter, ODM_REG_NHM_CNT_11N, bMaskDWord);
53
54 pDM_Odm->NHM_cnt_0 = (u8)(value32 & bMaskByte0);
55}
56
57void odm_NHMCounterStatisticsReset(void *pDM_VOID)
58{
59 PDM_ODM_T pDM_Odm = (PDM_ODM_T)pDM_VOID;
60
61 PHY_SetBBReg(pDM_Odm->Adapter, ODM_REG_NHM_TH9_TH10_11N, BIT1, 0);
62 PHY_SetBBReg(pDM_Odm->Adapter, ODM_REG_NHM_TH9_TH10_11N, BIT1, 1);
63}
64
65void odm_NHMBBInit(void *pDM_VOID)
66{
67 PDM_ODM_T pDM_Odm = (PDM_ODM_T)pDM_VOID;
68
69 pDM_Odm->adaptivity_flag = 0;
70 pDM_Odm->tolerance_cnt = 3;
71 pDM_Odm->NHMLastTxOkcnt = 0;
72 pDM_Odm->NHMLastRxOkcnt = 0;
73 pDM_Odm->NHMCurTxOkcnt = 0;
74 pDM_Odm->NHMCurRxOkcnt = 0;
75}
76
77/* */
78void odm_NHMBB(void *pDM_VOID)
79{
80 PDM_ODM_T pDM_Odm = (PDM_ODM_T)pDM_VOID;
81 /* u8 test_status; */
82 /* Pfalse_ALARM_STATISTICS pFalseAlmCnt = &(pDM_Odm->FalseAlmCnt); */
83
84 pDM_Odm->NHMCurTxOkcnt =
85 *(pDM_Odm->pNumTxBytesUnicast)-pDM_Odm->NHMLastTxOkcnt;
86 pDM_Odm->NHMCurRxOkcnt =
87 *(pDM_Odm->pNumRxBytesUnicast)-pDM_Odm->NHMLastRxOkcnt;
88 pDM_Odm->NHMLastTxOkcnt =
89 *(pDM_Odm->pNumTxBytesUnicast);
90 pDM_Odm->NHMLastRxOkcnt =
91 *(pDM_Odm->pNumRxBytesUnicast);
92 ODM_RT_TRACE(
93 pDM_Odm,
94 ODM_COMP_DIG,
95 ODM_DBG_LOUD,
96 (
97 "NHM_cnt_0 =%d, NHMCurTxOkcnt = %llu, NHMCurRxOkcnt = %llu\n",
98 pDM_Odm->NHM_cnt_0,
99 pDM_Odm->NHMCurTxOkcnt,
100 pDM_Odm->NHMCurRxOkcnt
101 )
102 );
103
104
105 if ((pDM_Odm->NHMCurTxOkcnt) + 1 > (u64)(pDM_Odm->NHMCurRxOkcnt<<2) + 1) { /* Tx > 4*Rx possible for adaptivity test */
106 if (pDM_Odm->NHM_cnt_0 >= 190 || pDM_Odm->adaptivity_flag == true) {
107 /* Enable EDCCA since it is possible running Adaptivity testing */
108 /* test_status = 1; */
109 pDM_Odm->adaptivity_flag = true;
110 pDM_Odm->tolerance_cnt = 0;
111 } else {
112 if (pDM_Odm->tolerance_cnt < 3)
113 pDM_Odm->tolerance_cnt = pDM_Odm->tolerance_cnt + 1;
114 else
115 pDM_Odm->tolerance_cnt = 4;
116 /* test_status = 5; */
117 if (pDM_Odm->tolerance_cnt > 3) {
118 /* test_status = 3; */
119 pDM_Odm->adaptivity_flag = false;
120 }
121 }
122 } else { /* TX<RX */
123 if (pDM_Odm->adaptivity_flag == true && pDM_Odm->NHM_cnt_0 <= 200) {
124 /* test_status = 2; */
125 pDM_Odm->tolerance_cnt = 0;
126 } else {
127 if (pDM_Odm->tolerance_cnt < 3)
128 pDM_Odm->tolerance_cnt = pDM_Odm->tolerance_cnt + 1;
129 else
130 pDM_Odm->tolerance_cnt = 4;
131 /* test_status = 5; */
132 if (pDM_Odm->tolerance_cnt > 3) {
133 /* test_status = 4; */
134 pDM_Odm->adaptivity_flag = false;
135 }
136 }
137 }
138
139 ODM_RT_TRACE(pDM_Odm, ODM_COMP_DIG, ODM_DBG_LOUD, ("adaptivity_flag = %d\n ", pDM_Odm->adaptivity_flag));
140}
141
142void odm_SearchPwdBLowerBound(void *pDM_VOID, u8 IGI_target)
143{
144 PDM_ODM_T pDM_Odm = (PDM_ODM_T)pDM_VOID;
145 u32 value32 = 0;
146 u8 cnt, IGI;
147 bool bAdjust = true;
148 s8 TH_L2H_dmc, TH_H2L_dmc;
149 s8 Diff;
150
151 IGI = 0x50; /* find H2L, L2H lower bound */
152 ODM_Write_DIG(pDM_Odm, IGI);
153
154
155 Diff = IGI_target-(s8)IGI;
156 TH_L2H_dmc = pDM_Odm->TH_L2H_ini + Diff;
157 if (TH_L2H_dmc > 10)
158 TH_L2H_dmc = 10;
159 TH_H2L_dmc = TH_L2H_dmc - pDM_Odm->TH_EDCCA_HL_diff;
160 PHY_SetBBReg(pDM_Odm->Adapter, rOFDM0_ECCAThreshold, bMaskByte0, (u8)TH_L2H_dmc);
161 PHY_SetBBReg(pDM_Odm->Adapter, rOFDM0_ECCAThreshold, bMaskByte2, (u8)TH_H2L_dmc);
162
163 mdelay(5);
164
165 while (bAdjust) {
166 for (cnt = 0; cnt < 20; cnt++) {
167 value32 = PHY_QueryBBReg(pDM_Odm->Adapter, ODM_REG_RPT_11N, bMaskDWord);
168
169 if (value32 & BIT30)
170 pDM_Odm->txEdcca1 = pDM_Odm->txEdcca1 + 1;
171 else if (value32 & BIT29)
172 pDM_Odm->txEdcca1 = pDM_Odm->txEdcca1 + 1;
173 else
174 pDM_Odm->txEdcca0 = pDM_Odm->txEdcca0 + 1;
175 }
176 /* DbgPrint("txEdcca1 = %d, txEdcca0 = %d\n", pDM_Odm->txEdcca1, pDM_Odm->txEdcca0); */
177
178 if (pDM_Odm->txEdcca1 > 5) {
179 IGI = IGI-1;
180 TH_L2H_dmc = TH_L2H_dmc + 1;
181 if (TH_L2H_dmc > 10)
182 TH_L2H_dmc = 10;
183 TH_H2L_dmc = TH_L2H_dmc - pDM_Odm->TH_EDCCA_HL_diff;
184 PHY_SetBBReg(pDM_Odm->Adapter, rOFDM0_ECCAThreshold, bMaskByte0, (u8)TH_L2H_dmc);
185 PHY_SetBBReg(pDM_Odm->Adapter, rOFDM0_ECCAThreshold, bMaskByte2, (u8)TH_H2L_dmc);
186
187 pDM_Odm->TxHangFlg = true;
188 pDM_Odm->txEdcca1 = 0;
189 pDM_Odm->txEdcca0 = 0;
190
191 if (TH_L2H_dmc == 10) {
192 bAdjust = false;
193 pDM_Odm->TxHangFlg = false;
194 pDM_Odm->txEdcca1 = 0;
195 pDM_Odm->txEdcca0 = 0;
196 pDM_Odm->H2L_lb = TH_H2L_dmc;
197 pDM_Odm->L2H_lb = TH_L2H_dmc;
198 pDM_Odm->Adaptivity_IGI_upper = IGI;
199 }
200 } else {
201 bAdjust = false;
202 pDM_Odm->TxHangFlg = false;
203 pDM_Odm->txEdcca1 = 0;
204 pDM_Odm->txEdcca0 = 0;
205 pDM_Odm->H2L_lb = TH_H2L_dmc;
206 pDM_Odm->L2H_lb = TH_L2H_dmc;
207 pDM_Odm->Adaptivity_IGI_upper = IGI;
208 }
209 }
210
211 ODM_RT_TRACE(pDM_Odm, ODM_COMP_DIG, ODM_DBG_LOUD, ("IGI = 0x%x, H2L_lb = 0x%x, L2H_lb = 0x%x\n", IGI, pDM_Odm->H2L_lb, pDM_Odm->L2H_lb));
212}
213
214void odm_AdaptivityInit(void *pDM_VOID)
215{
216 PDM_ODM_T pDM_Odm = (PDM_ODM_T)pDM_VOID;
217
218 if (pDM_Odm->Carrier_Sense_enable == false)
219 pDM_Odm->TH_L2H_ini = 0xf7; /* -7 */
220 else
221 pDM_Odm->TH_L2H_ini = 0xa;
222
223 pDM_Odm->AdapEn_RSSI = 20;
224 pDM_Odm->TH_EDCCA_HL_diff = 7;
225
226 pDM_Odm->IGI_Base = 0x32;
227 pDM_Odm->IGI_target = 0x1c;
228 pDM_Odm->ForceEDCCA = 0;
229 pDM_Odm->NHM_disable = false;
230 pDM_Odm->TxHangFlg = true;
231 pDM_Odm->txEdcca0 = 0;
232 pDM_Odm->txEdcca1 = 0;
233 pDM_Odm->H2L_lb = 0;
234 pDM_Odm->L2H_lb = 0;
235 pDM_Odm->Adaptivity_IGI_upper = 0;
236 odm_NHMBBInit(pDM_Odm);
237
238 PHY_SetBBReg(pDM_Odm->Adapter, REG_RD_CTRL, BIT11, 1); /* stop counting if EDCCA is asserted */
239}
240
241
242void odm_Adaptivity(void *pDM_VOID, u8 IGI)
243{
244 PDM_ODM_T pDM_Odm = (PDM_ODM_T)pDM_VOID;
245 s8 TH_L2H_dmc, TH_H2L_dmc;
246 s8 Diff, IGI_target;
247 bool EDCCA_State = false;
248
249 if (!(pDM_Odm->SupportAbility & ODM_BB_ADAPTIVITY)) {
250 ODM_RT_TRACE(pDM_Odm, ODM_COMP_DIG, ODM_DBG_LOUD, ("Go to odm_DynamicEDCCA()\n"));
251 return;
252 }
253 ODM_RT_TRACE(pDM_Odm, ODM_COMP_DIG, ODM_DBG_LOUD, ("odm_Adaptivity() =====>\n"));
254 ODM_RT_TRACE(pDM_Odm, ODM_COMP_DIG, ODM_DBG_LOUD, ("ForceEDCCA =%d, IGI_Base = 0x%x, TH_L2H_ini = %d, TH_EDCCA_HL_diff = %d, AdapEn_RSSI = %d\n",
255 pDM_Odm->ForceEDCCA, pDM_Odm->IGI_Base, pDM_Odm->TH_L2H_ini, pDM_Odm->TH_EDCCA_HL_diff, pDM_Odm->AdapEn_RSSI));
256
257 if (*pDM_Odm->pBandWidth == ODM_BW20M) /* CHANNEL_WIDTH_20 */
258 IGI_target = pDM_Odm->IGI_Base;
259 else if (*pDM_Odm->pBandWidth == ODM_BW40M)
260 IGI_target = pDM_Odm->IGI_Base + 2;
261 else if (*pDM_Odm->pBandWidth == ODM_BW80M)
262 IGI_target = pDM_Odm->IGI_Base + 2;
263 else
264 IGI_target = pDM_Odm->IGI_Base;
265 pDM_Odm->IGI_target = (u8) IGI_target;
266
267 /* Search pwdB lower bound */
268 if (pDM_Odm->TxHangFlg == true) {
269 PHY_SetBBReg(pDM_Odm->Adapter, ODM_REG_DBG_RPT_11N, bMaskDWord, 0x208);
270 odm_SearchPwdBLowerBound(pDM_Odm, pDM_Odm->IGI_target);
271 }
272
273 if ((!pDM_Odm->bLinked) || (*pDM_Odm->pChannel > 149)) { /* Band4 doesn't need adaptivity */
274 PHY_SetBBReg(pDM_Odm->Adapter, rOFDM0_ECCAThreshold, bMaskByte0, 0x7f);
275 PHY_SetBBReg(pDM_Odm->Adapter, rOFDM0_ECCAThreshold, bMaskByte2, 0x7f);
276 return;
277 }
278
279 if (!pDM_Odm->ForceEDCCA) {
280 if (pDM_Odm->RSSI_Min > pDM_Odm->AdapEn_RSSI)
7bb0dffd 281 EDCCA_State = true;
554c0a3a 282 else if (pDM_Odm->RSSI_Min < (pDM_Odm->AdapEn_RSSI - 5))
7bb0dffd 283 EDCCA_State = false;
554c0a3a 284 } else
7bb0dffd 285 EDCCA_State = true;
554c0a3a
HG
286
287 if (
288 pDM_Odm->bLinked &&
289 pDM_Odm->Carrier_Sense_enable == false &&
290 pDM_Odm->NHM_disable == false &&
291 pDM_Odm->TxHangFlg == false
292 )
293 odm_NHMBB(pDM_Odm);
294
295 ODM_RT_TRACE(
296 pDM_Odm,
297 ODM_COMP_DIG,
298 ODM_DBG_LOUD,
299 (
300 "BandWidth =%s, IGI_target = 0x%x, EDCCA_State =%d\n",
301 (*pDM_Odm->pBandWidth == ODM_BW80M) ? "80M" :
302 ((*pDM_Odm->pBandWidth == ODM_BW40M) ? "40M" : "20M"),
303 IGI_target,
304 EDCCA_State
305 )
306 );
307
7bb0dffd 308 if (EDCCA_State) {
554c0a3a
HG
309 Diff = IGI_target-(s8)IGI;
310 TH_L2H_dmc = pDM_Odm->TH_L2H_ini + Diff;
311 if (TH_L2H_dmc > 10)
312 TH_L2H_dmc = 10;
313
314 TH_H2L_dmc = TH_L2H_dmc - pDM_Odm->TH_EDCCA_HL_diff;
315
316 /* replace lower bound to prevent EDCCA always equal */
317 if (TH_H2L_dmc < pDM_Odm->H2L_lb)
318 TH_H2L_dmc = pDM_Odm->H2L_lb;
319 if (TH_L2H_dmc < pDM_Odm->L2H_lb)
320 TH_L2H_dmc = pDM_Odm->L2H_lb;
321 } else {
322 TH_L2H_dmc = 0x7f;
323 TH_H2L_dmc = 0x7f;
324 }
325 ODM_RT_TRACE(pDM_Odm, ODM_COMP_DIG, ODM_DBG_LOUD, ("IGI = 0x%x, TH_L2H_dmc = %d, TH_H2L_dmc = %d\n",
326 IGI, TH_L2H_dmc, TH_H2L_dmc));
327 PHY_SetBBReg(pDM_Odm->Adapter, rOFDM0_ECCAThreshold, bMaskByte0, (u8)TH_L2H_dmc);
328 PHY_SetBBReg(pDM_Odm->Adapter, rOFDM0_ECCAThreshold, bMaskByte2, (u8)TH_H2L_dmc);
329}
330
331void ODM_Write_DIG(void *pDM_VOID, u8 CurrentIGI)
332{
333 PDM_ODM_T pDM_Odm = (PDM_ODM_T)pDM_VOID;
334 pDIG_T pDM_DigTable = &pDM_Odm->DM_DigTable;
335
336 if (pDM_DigTable->bStopDIG) {
337 ODM_RT_TRACE(pDM_Odm, ODM_COMP_DIG, ODM_DBG_LOUD, ("Stop Writing IGI\n"));
338 return;
339 }
340
341 ODM_RT_TRACE(pDM_Odm, ODM_COMP_DIG, ODM_DBG_TRACE, ("ODM_REG(IGI_A, pDM_Odm) = 0x%x, ODM_BIT(IGI, pDM_Odm) = 0x%x\n",
342 ODM_REG(IGI_A, pDM_Odm), ODM_BIT(IGI, pDM_Odm)));
343
344 if (pDM_DigTable->CurIGValue != CurrentIGI) {
345 /* 1 Check initial gain by upper bound */
346 if (!pDM_DigTable->bPSDInProgress) {
347 if (CurrentIGI > pDM_DigTable->rx_gain_range_max) {
348 ODM_RT_TRACE(pDM_Odm, ODM_COMP_DIG, ODM_DBG_TRACE, ("CurrentIGI(0x%02x) is larger than upper bound !!\n", pDM_DigTable->rx_gain_range_max));
349 CurrentIGI = pDM_DigTable->rx_gain_range_max;
350 }
351
352 }
353
354 /* 1 Set IGI value */
355 PHY_SetBBReg(pDM_Odm->Adapter, ODM_REG(IGI_A, pDM_Odm), ODM_BIT(IGI, pDM_Odm), CurrentIGI);
356
357 if (pDM_Odm->RFType > ODM_1T1R)
358 PHY_SetBBReg(pDM_Odm->Adapter, ODM_REG(IGI_B, pDM_Odm), ODM_BIT(IGI, pDM_Odm), CurrentIGI);
359
360 pDM_DigTable->CurIGValue = CurrentIGI;
361 }
362
363 ODM_RT_TRACE(pDM_Odm, ODM_COMP_DIG, ODM_DBG_TRACE, ("CurrentIGI(0x%02x).\n", CurrentIGI));
364
365}
366
367void odm_PauseDIG(
368 void *pDM_VOID,
369 ODM_Pause_DIG_TYPE PauseType,
370 u8 IGIValue
371)
372{
373 PDM_ODM_T pDM_Odm = (PDM_ODM_T)pDM_VOID;
374 pDIG_T pDM_DigTable = &pDM_Odm->DM_DigTable;
318dda31 375 static bool bPaused;
554c0a3a
HG
376
377 ODM_RT_TRACE(pDM_Odm, ODM_COMP_DIG, ODM_DBG_LOUD, ("odm_PauseDIG() =========>\n"));
378
379 if (
380 (pDM_Odm->SupportAbility & ODM_BB_ADAPTIVITY) &&
381 pDM_Odm->TxHangFlg == true
382 ) {
383 ODM_RT_TRACE(
384 pDM_Odm,
385 ODM_COMP_DIG,
386 ODM_DBG_LOUD,
387 ("odm_PauseDIG(): Dynamic adjust threshold in progress !!\n")
388 );
389 return;
390 }
391
392 if (
393 !bPaused && (!(pDM_Odm->SupportAbility & ODM_BB_DIG) ||
394 !(pDM_Odm->SupportAbility & ODM_BB_FA_CNT))
395 ){
396 ODM_RT_TRACE(
397 pDM_Odm,
398 ODM_COMP_DIG,
399 ODM_DBG_LOUD,
400 ("odm_PauseDIG(): Return: SupportAbility ODM_BB_DIG or ODM_BB_FA_CNT is disabled\n")
401 );
402 return;
403 }
404
405 switch (PauseType) {
406 /* 1 Pause DIG */
407 case ODM_PAUSE_DIG:
408 /* 2 Disable DIG */
409 ODM_CmnInfoUpdate(pDM_Odm, ODM_CMNINFO_ABILITY, pDM_Odm->SupportAbility & (~ODM_BB_DIG));
410 ODM_RT_TRACE(pDM_Odm, ODM_COMP_DIG, ODM_DBG_LOUD, ("odm_PauseDIG(): Pause DIG !!\n"));
411
412 /* 2 Backup IGI value */
413 if (!bPaused) {
414 pDM_DigTable->IGIBackup = pDM_DigTable->CurIGValue;
415 bPaused = true;
416 }
417 ODM_RT_TRACE(pDM_Odm, ODM_COMP_DIG, ODM_DBG_LOUD, ("odm_PauseDIG(): Backup IGI = 0x%x\n", pDM_DigTable->IGIBackup));
418
419 /* 2 Write new IGI value */
420 ODM_Write_DIG(pDM_Odm, IGIValue);
421 ODM_RT_TRACE(pDM_Odm, ODM_COMP_DIG, ODM_DBG_LOUD, ("odm_PauseDIG(): Write new IGI = 0x%x\n", IGIValue));
422 break;
423
424 /* 1 Resume DIG */
425 case ODM_RESUME_DIG:
426 if (bPaused) {
427 /* 2 Write backup IGI value */
428 ODM_Write_DIG(pDM_Odm, pDM_DigTable->IGIBackup);
429 bPaused = false;
430 ODM_RT_TRACE(pDM_Odm, ODM_COMP_DIG, ODM_DBG_LOUD, ("odm_PauseDIG(): Write original IGI = 0x%x\n", pDM_DigTable->IGIBackup));
431
432 /* 2 Enable DIG */
433 ODM_CmnInfoUpdate(pDM_Odm, ODM_CMNINFO_ABILITY, pDM_Odm->SupportAbility | ODM_BB_DIG);
434 ODM_RT_TRACE(pDM_Odm, ODM_COMP_DIG, ODM_DBG_LOUD, ("odm_PauseDIG(): Resume DIG !!\n"));
435 }
436 break;
437
438 default:
439 ODM_RT_TRACE(pDM_Odm, ODM_COMP_DIG, ODM_DBG_LOUD, ("odm_PauseDIG(): Wrong type !!\n"));
440 break;
441 }
442}
443
444bool odm_DigAbort(void *pDM_VOID)
445{
446 PDM_ODM_T pDM_Odm = (PDM_ODM_T)pDM_VOID;
447
448 /* SupportAbility */
449 if (!(pDM_Odm->SupportAbility & ODM_BB_FA_CNT)) {
450 ODM_RT_TRACE(pDM_Odm, ODM_COMP_DIG, ODM_DBG_LOUD, ("odm_DIG(): Return: SupportAbility ODM_BB_FA_CNT is disabled\n"));
451 return true;
452 }
453
454 /* SupportAbility */
455 if (!(pDM_Odm->SupportAbility & ODM_BB_DIG)) {
456 ODM_RT_TRACE(pDM_Odm, ODM_COMP_DIG, ODM_DBG_LOUD, ("odm_DIG(): Return: SupportAbility ODM_BB_DIG is disabled\n"));
457 return true;
458 }
459
460 /* ScanInProcess */
461 if (*(pDM_Odm->pbScanInProcess)) {
462 ODM_RT_TRACE(pDM_Odm, ODM_COMP_DIG, ODM_DBG_LOUD, ("odm_DIG(): Return: In Scan Progress\n"));
463 return true;
464 }
465
466 /* add by Neil Chen to avoid PSD is processing */
467 if (pDM_Odm->bDMInitialGainEnable == false) {
468 ODM_RT_TRACE(pDM_Odm, ODM_COMP_DIG, ODM_DBG_LOUD, ("odm_DIG(): Return: PSD is Processing\n"));
469 return true;
470 }
471
472 return false;
473}
474
475void odm_DIGInit(void *pDM_VOID)
476{
477 PDM_ODM_T pDM_Odm = (PDM_ODM_T)pDM_VOID;
478 pDIG_T pDM_DigTable = &pDM_Odm->DM_DigTable;
479
480 pDM_DigTable->bStopDIG = false;
481 pDM_DigTable->bPSDInProgress = false;
482 pDM_DigTable->CurIGValue = (u8) PHY_QueryBBReg(pDM_Odm->Adapter, ODM_REG(IGI_A, pDM_Odm), ODM_BIT(IGI, pDM_Odm));
483 pDM_DigTable->RssiLowThresh = DM_DIG_THRESH_LOW;
484 pDM_DigTable->RssiHighThresh = DM_DIG_THRESH_HIGH;
485 pDM_DigTable->FALowThresh = DMfalseALARM_THRESH_LOW;
486 pDM_DigTable->FAHighThresh = DMfalseALARM_THRESH_HIGH;
487 pDM_DigTable->BackoffVal = DM_DIG_BACKOFF_DEFAULT;
488 pDM_DigTable->BackoffVal_range_max = DM_DIG_BACKOFF_MAX;
489 pDM_DigTable->BackoffVal_range_min = DM_DIG_BACKOFF_MIN;
490 pDM_DigTable->PreCCK_CCAThres = 0xFF;
491 pDM_DigTable->CurCCK_CCAThres = 0x83;
492 pDM_DigTable->ForbiddenIGI = DM_DIG_MIN_NIC;
493 pDM_DigTable->LargeFAHit = 0;
494 pDM_DigTable->Recover_cnt = 0;
495 pDM_DigTable->bMediaConnect_0 = false;
496 pDM_DigTable->bMediaConnect_1 = false;
497
498 /* To Initialize pDM_Odm->bDMInitialGainEnable == false to avoid DIG error */
499 pDM_Odm->bDMInitialGainEnable = true;
500
501 pDM_DigTable->DIG_Dynamic_MIN_0 = DM_DIG_MIN_NIC;
502 pDM_DigTable->DIG_Dynamic_MIN_1 = DM_DIG_MIN_NIC;
503
504 /* To Initi BT30 IGI */
505 pDM_DigTable->BT30_CurIGI = 0x32;
506
507 if (pDM_Odm->BoardType & (ODM_BOARD_EXT_PA|ODM_BOARD_EXT_LNA)) {
508 pDM_DigTable->rx_gain_range_max = DM_DIG_MAX_NIC;
509 pDM_DigTable->rx_gain_range_min = DM_DIG_MIN_NIC;
510 } else {
511 pDM_DigTable->rx_gain_range_max = DM_DIG_MAX_NIC;
512 pDM_DigTable->rx_gain_range_min = DM_DIG_MIN_NIC;
513 }
514
515}
516
517
518void odm_DIG(void *pDM_VOID)
519{
520 PDM_ODM_T pDM_Odm = (PDM_ODM_T)pDM_VOID;
521
522 /* Common parameters */
523 pDIG_T pDM_DigTable = &pDM_Odm->DM_DigTable;
524 Pfalse_ALARM_STATISTICS pFalseAlmCnt = &pDM_Odm->FalseAlmCnt;
525 bool FirstConnect, FirstDisConnect;
526 u8 DIG_MaxOfMin, DIG_Dynamic_MIN;
527 u8 dm_dig_max, dm_dig_min;
528 u8 CurrentIGI = pDM_DigTable->CurIGValue;
529 u8 offset;
530 u32 dm_FA_thres[3];
531 u8 Adap_IGI_Upper = 0;
532 u32 TxTp = 0, RxTp = 0;
533 bool bDFSBand = false;
534 bool bPerformance = true, bFirstTpTarget = false, bFirstCoverage = false;
535
536 if (odm_DigAbort(pDM_Odm) == true)
537 return;
538
539 ODM_RT_TRACE(pDM_Odm, ODM_COMP_DIG, ODM_DBG_LOUD, ("odm_DIG() ===========================>\n\n"));
540
541 if (pDM_Odm->adaptivity_flag == true)
542 Adap_IGI_Upper = pDM_Odm->Adaptivity_IGI_upper;
543
544
545 /* 1 Update status */
546 DIG_Dynamic_MIN = pDM_DigTable->DIG_Dynamic_MIN_0;
547 FirstConnect = (pDM_Odm->bLinked) && (pDM_DigTable->bMediaConnect_0 == false);
548 FirstDisConnect = (!pDM_Odm->bLinked) && (pDM_DigTable->bMediaConnect_0 == true);
549
550 /* 1 Boundary Decision */
551 /* 2 For WIN\CE */
552 dm_dig_max = 0x5A;
553 dm_dig_min = DM_DIG_MIN_NIC;
554 DIG_MaxOfMin = DM_DIG_MAX_AP;
555
556 ODM_RT_TRACE(pDM_Odm, ODM_COMP_DIG, ODM_DBG_LOUD, ("odm_DIG(): Absolutly upper bound = 0x%x, lower bound = 0x%x\n", dm_dig_max, dm_dig_min));
557
558 /* 1 Adjust boundary by RSSI */
559 if (pDM_Odm->bLinked && bPerformance) {
560 /* 2 Modify DIG upper bound */
561 /* 4 Modify DIG upper bound for 92E, 8723A\B, 8821 & 8812 BT */
562 if (pDM_Odm->bBtLimitedDig == 1) {
563 offset = 10;
564 ODM_RT_TRACE(pDM_Odm, ODM_COMP_DIG, ODM_DBG_LOUD, ("odm_DIG(): Coex. case: Force upper bound to RSSI + %d !!!!!!\n", offset));
565 } else
566 offset = 15;
567
568 if ((pDM_Odm->RSSI_Min + offset) > dm_dig_max)
569 pDM_DigTable->rx_gain_range_max = dm_dig_max;
570 else if ((pDM_Odm->RSSI_Min + offset) < dm_dig_min)
571 pDM_DigTable->rx_gain_range_max = dm_dig_min;
572 else
573 pDM_DigTable->rx_gain_range_max = pDM_Odm->RSSI_Min + offset;
574
575 /* 2 Modify DIG lower bound */
576 /* if (pDM_Odm->bOneEntryOnly) */
577 {
578 if (pDM_Odm->RSSI_Min < dm_dig_min)
579 DIG_Dynamic_MIN = dm_dig_min;
580 else if (pDM_Odm->RSSI_Min > DIG_MaxOfMin)
581 DIG_Dynamic_MIN = DIG_MaxOfMin;
582 else
583 DIG_Dynamic_MIN = pDM_Odm->RSSI_Min;
584 }
585 } else {
586 pDM_DigTable->rx_gain_range_max = dm_dig_max;
587 DIG_Dynamic_MIN = dm_dig_min;
588 }
589
590 /* 1 Force Lower Bound for AntDiv */
591 if (pDM_Odm->bLinked && !pDM_Odm->bOneEntryOnly) {
592 if (pDM_Odm->SupportAbility & ODM_BB_ANT_DIV) {
593 if (
594 pDM_Odm->AntDivType == CG_TRX_HW_ANTDIV ||
595 pDM_Odm->AntDivType == CG_TRX_SMART_ANTDIV ||
596 pDM_Odm->AntDivType == S0S1_SW_ANTDIV
597 ) {
598 if (pDM_DigTable->AntDiv_RSSI_max > DIG_MaxOfMin)
599 DIG_Dynamic_MIN = DIG_MaxOfMin;
600 else
601 DIG_Dynamic_MIN = (u8) pDM_DigTable->AntDiv_RSSI_max;
602 ODM_RT_TRACE(
603 pDM_Odm,
604 ODM_COMP_ANT_DIV,
605 ODM_DBG_LOUD,
606 (
607 "odm_DIG(): Antenna diversity case: Force lower bound to 0x%x !!!!!!\n",
608 DIG_Dynamic_MIN
609 )
610 );
611 ODM_RT_TRACE(
612 pDM_Odm,
613 ODM_COMP_ANT_DIV,
614 ODM_DBG_LOUD,
615 (
616 "odm_DIG(): Antenna diversity case: RSSI_max = 0x%x !!!!!!\n",
617 pDM_DigTable->AntDiv_RSSI_max
618 )
619 );
620 }
621 }
622 }
623 ODM_RT_TRACE(
624 pDM_Odm,
625 ODM_COMP_DIG,
626 ODM_DBG_LOUD,
627 (
628 "odm_DIG(): Adjust boundary by RSSI Upper bound = 0x%x, Lower bound = 0x%x\n",
629 pDM_DigTable->rx_gain_range_max,
630 DIG_Dynamic_MIN
631 )
632 );
633 ODM_RT_TRACE(
634 pDM_Odm,
635 ODM_COMP_DIG,
636 ODM_DBG_LOUD,
637 (
638 "odm_DIG(): Link status: bLinked = %d, RSSI = %d, bFirstConnect = %d, bFirsrDisConnect = %d\n\n",
639 pDM_Odm->bLinked,
640 pDM_Odm->RSSI_Min,
641 FirstConnect,
642 FirstDisConnect
643 )
644 );
645
646 /* 1 Modify DIG lower bound, deal with abnormal case */
647 /* 2 Abnormal false alarm case */
648 if (FirstDisConnect) {
649 pDM_DigTable->rx_gain_range_min = DIG_Dynamic_MIN;
650 pDM_DigTable->ForbiddenIGI = DIG_Dynamic_MIN;
651 } else
652 pDM_DigTable->rx_gain_range_min =
653 odm_ForbiddenIGICheck(pDM_Odm, DIG_Dynamic_MIN, CurrentIGI);
654
655 if (pDM_Odm->bLinked && !FirstConnect) {
656 if (
657 (pDM_Odm->PhyDbgInfo.NumQryBeaconPkt < 5) &&
658 pDM_Odm->bsta_state
659 ) {
660 pDM_DigTable->rx_gain_range_min = dm_dig_min;
661 ODM_RT_TRACE(
662 pDM_Odm,
663 ODM_COMP_DIG,
664 ODM_DBG_LOUD,
665 (
666 "odm_DIG(): Abnrormal #beacon (%d) case in STA mode: Force lower bound to 0x%x !!!!!!\n\n",
667 pDM_Odm->PhyDbgInfo.NumQryBeaconPkt,
668 pDM_DigTable->rx_gain_range_min
669 )
670 );
671 }
672 }
673
674 /* 2 Abnormal lower bound case */
675 if (pDM_DigTable->rx_gain_range_min > pDM_DigTable->rx_gain_range_max) {
676 pDM_DigTable->rx_gain_range_min = pDM_DigTable->rx_gain_range_max;
677 ODM_RT_TRACE(
678 pDM_Odm,
679 ODM_COMP_DIG,
680 ODM_DBG_LOUD,
681 (
682 "odm_DIG(): Abnrormal lower bound case: Force lower bound to 0x%x !!!!!!\n\n",
683 pDM_DigTable->rx_gain_range_min
684 )
685 );
686 }
687
688
689 /* 1 False alarm threshold decision */
690 odm_FAThresholdCheck(pDM_Odm, bDFSBand, bPerformance, RxTp, TxTp, dm_FA_thres);
691 ODM_RT_TRACE(pDM_Odm, ODM_COMP_DIG, ODM_DBG_LOUD, ("odm_DIG(): False alarm threshold = %d, %d, %d\n\n", dm_FA_thres[0], dm_FA_thres[1], dm_FA_thres[2]));
692
693 /* 1 Adjust initial gain by false alarm */
694 if (pDM_Odm->bLinked && bPerformance) {
695 /* 2 After link */
696 ODM_RT_TRACE(
697 pDM_Odm,
698 ODM_COMP_DIG,
699 ODM_DBG_LOUD,
700 ("odm_DIG(): Adjust IGI after link\n")
701 );
702
703 if (bFirstTpTarget || (FirstConnect && bPerformance)) {
704 pDM_DigTable->LargeFAHit = 0;
705
706 if (pDM_Odm->RSSI_Min < DIG_MaxOfMin) {
707 if (CurrentIGI < pDM_Odm->RSSI_Min)
708 CurrentIGI = pDM_Odm->RSSI_Min;
709 } else {
710 if (CurrentIGI < DIG_MaxOfMin)
711 CurrentIGI = DIG_MaxOfMin;
712 }
713
714 ODM_RT_TRACE(
715 pDM_Odm,
716 ODM_COMP_DIG,
717 ODM_DBG_LOUD,
718 (
719 "odm_DIG(): First connect case: IGI does on-shot to 0x%x\n",
720 CurrentIGI
721 )
722 );
723
724 } else {
725 if (pFalseAlmCnt->Cnt_all > dm_FA_thres[2])
726 CurrentIGI = CurrentIGI + 4;
727 else if (pFalseAlmCnt->Cnt_all > dm_FA_thres[1])
728 CurrentIGI = CurrentIGI + 2;
729 else if (pFalseAlmCnt->Cnt_all < dm_FA_thres[0])
730 CurrentIGI = CurrentIGI - 2;
731
732 if (
733 (pDM_Odm->PhyDbgInfo.NumQryBeaconPkt < 5) &&
734 (pFalseAlmCnt->Cnt_all < DM_DIG_FA_TH1) &&
735 (pDM_Odm->bsta_state)
736 ) {
737 CurrentIGI = pDM_DigTable->rx_gain_range_min;
738 ODM_RT_TRACE(
739 pDM_Odm,
740 ODM_COMP_DIG,
741 ODM_DBG_LOUD,
742 (
743 "odm_DIG(): Abnormal #beacon (%d) case: IGI does one-shot to 0x%x\n",
744 pDM_Odm->PhyDbgInfo.NumQryBeaconPkt,
745 CurrentIGI
746 )
747 );
748 }
749 }
750 } else {
751 /* 2 Before link */
752 ODM_RT_TRACE(
753 pDM_Odm,
754 ODM_COMP_DIG,
755 ODM_DBG_LOUD,
756 ("odm_DIG(): Adjust IGI before link\n")
757 );
758
759 if (FirstDisConnect || bFirstCoverage) {
760 CurrentIGI = dm_dig_min;
761 ODM_RT_TRACE(
762 pDM_Odm,
763 ODM_COMP_DIG,
764 ODM_DBG_LOUD,
765 ("odm_DIG(): First disconnect case: IGI does on-shot to lower bound\n")
766 );
767 } else {
768 if (pFalseAlmCnt->Cnt_all > dm_FA_thres[2])
769 CurrentIGI = CurrentIGI + 4;
770 else if (pFalseAlmCnt->Cnt_all > dm_FA_thres[1])
771 CurrentIGI = CurrentIGI + 2;
772 else if (pFalseAlmCnt->Cnt_all < dm_FA_thres[0])
773 CurrentIGI = CurrentIGI - 2;
774 }
775 }
776
777 /* 1 Check initial gain by upper/lower bound */
778 if (CurrentIGI < pDM_DigTable->rx_gain_range_min)
779 CurrentIGI = pDM_DigTable->rx_gain_range_min;
780
781 if (CurrentIGI > pDM_DigTable->rx_gain_range_max)
782 CurrentIGI = pDM_DigTable->rx_gain_range_max;
783
784 ODM_RT_TRACE(
785 pDM_Odm,
786 ODM_COMP_DIG,
787 ODM_DBG_LOUD,
788 (
789 "odm_DIG(): CurIGValue = 0x%x, TotalFA = %d\n\n",
790 CurrentIGI,
791 pFalseAlmCnt->Cnt_all
792 )
793 );
794
795 /* 1 Force upper bound and lower bound for adaptivity */
796 if (
797 pDM_Odm->SupportAbility & ODM_BB_ADAPTIVITY &&
798 pDM_Odm->adaptivity_flag == true
799 ) {
800 if (CurrentIGI > Adap_IGI_Upper)
801 CurrentIGI = Adap_IGI_Upper;
802
803 if (pDM_Odm->IGI_LowerBound != 0) {
804 if (CurrentIGI < pDM_Odm->IGI_LowerBound)
805 CurrentIGI = pDM_Odm->IGI_LowerBound;
806 }
807 ODM_RT_TRACE(pDM_Odm, ODM_COMP_DIG, ODM_DBG_LOUD, ("odm_DIG(): Adaptivity case: Force upper bound to 0x%x !!!!!!\n", Adap_IGI_Upper));
808 ODM_RT_TRACE(pDM_Odm, ODM_COMP_DIG, ODM_DBG_LOUD, ("odm_DIG(): Adaptivity case: Force lower bound to 0x%x !!!!!!\n\n", pDM_Odm->IGI_LowerBound));
809 }
810
811
812 /* 1 Update status */
813 if (pDM_Odm->bBtHsOperation) {
814 if (pDM_Odm->bLinked) {
815 if (pDM_DigTable->BT30_CurIGI > (CurrentIGI))
816 ODM_Write_DIG(pDM_Odm, CurrentIGI);
817 else
818 ODM_Write_DIG(pDM_Odm, pDM_DigTable->BT30_CurIGI);
819
820 pDM_DigTable->bMediaConnect_0 = pDM_Odm->bLinked;
821 pDM_DigTable->DIG_Dynamic_MIN_0 = DIG_Dynamic_MIN;
822 } else {
823 if (pDM_Odm->bLinkInProcess)
824 ODM_Write_DIG(pDM_Odm, 0x1c);
825 else if (pDM_Odm->bBtConnectProcess)
826 ODM_Write_DIG(pDM_Odm, 0x28);
827 else
828 ODM_Write_DIG(pDM_Odm, pDM_DigTable->BT30_CurIGI);/* ODM_Write_DIG(pDM_Odm, pDM_DigTable->CurIGValue); */
829 }
830 } else { /* BT is not using */
831 ODM_Write_DIG(pDM_Odm, CurrentIGI);/* ODM_Write_DIG(pDM_Odm, pDM_DigTable->CurIGValue); */
832 pDM_DigTable->bMediaConnect_0 = pDM_Odm->bLinked;
833 pDM_DigTable->DIG_Dynamic_MIN_0 = DIG_Dynamic_MIN;
834 }
835}
836
837void odm_DIGbyRSSI_LPS(void *pDM_VOID)
838{
839 PDM_ODM_T pDM_Odm = (PDM_ODM_T)pDM_VOID;
840 Pfalse_ALARM_STATISTICS pFalseAlmCnt = &pDM_Odm->FalseAlmCnt;
841
842 u8 RSSI_Lower = DM_DIG_MIN_NIC; /* 0x1E or 0x1C */
843 u8 CurrentIGI = pDM_Odm->RSSI_Min;
844
845 CurrentIGI = CurrentIGI+RSSI_OFFSET_DIG;
846
847 ODM_RT_TRACE(
848 pDM_Odm,
849 ODM_COMP_DIG,
850 ODM_DBG_LOUD,
851 ("odm_DIGbyRSSI_LPS() ==>\n")
852 );
853
854 /* Using FW PS mode to make IGI */
855 /* Adjust by FA in LPS MODE */
856 if (pFalseAlmCnt->Cnt_all > DM_DIG_FA_TH2_LPS)
857 CurrentIGI = CurrentIGI+4;
858 else if (pFalseAlmCnt->Cnt_all > DM_DIG_FA_TH1_LPS)
859 CurrentIGI = CurrentIGI+2;
860 else if (pFalseAlmCnt->Cnt_all < DM_DIG_FA_TH0_LPS)
861 CurrentIGI = CurrentIGI-2;
862
863
864 /* Lower bound checking */
865
866 /* RSSI Lower bound check */
867 if ((pDM_Odm->RSSI_Min-10) > DM_DIG_MIN_NIC)
868 RSSI_Lower = pDM_Odm->RSSI_Min-10;
869 else
870 RSSI_Lower = DM_DIG_MIN_NIC;
871
872 /* Upper and Lower Bound checking */
873 if (CurrentIGI > DM_DIG_MAX_NIC)
874 CurrentIGI = DM_DIG_MAX_NIC;
875 else if (CurrentIGI < RSSI_Lower)
876 CurrentIGI = RSSI_Lower;
877
878
879 ODM_RT_TRACE(
880 pDM_Odm,
881 ODM_COMP_DIG,
882 ODM_DBG_LOUD,
883 ("odm_DIGbyRSSI_LPS(): pFalseAlmCnt->Cnt_all = %d\n", pFalseAlmCnt->Cnt_all)
884 );
885 ODM_RT_TRACE(
886 pDM_Odm,
887 ODM_COMP_DIG,
888 ODM_DBG_LOUD,
889 ("odm_DIGbyRSSI_LPS(): pDM_Odm->RSSI_Min = %d\n", pDM_Odm->RSSI_Min)
890 );
891 ODM_RT_TRACE(
892 pDM_Odm,
893 ODM_COMP_DIG,
894 ODM_DBG_LOUD,
895 ("odm_DIGbyRSSI_LPS(): CurrentIGI = 0x%x\n", CurrentIGI)
896 );
897
898 ODM_Write_DIG(pDM_Odm, CurrentIGI);
899 /* ODM_Write_DIG(pDM_Odm, pDM_DigTable->CurIGValue); */
900}
901
902/* 3 ============================================================ */
903/* 3 FASLE ALARM CHECK */
904/* 3 ============================================================ */
905
906void odm_FalseAlarmCounterStatistics(void *pDM_VOID)
907{
908 PDM_ODM_T pDM_Odm = (PDM_ODM_T)pDM_VOID;
909 Pfalse_ALARM_STATISTICS FalseAlmCnt = &(pDM_Odm->FalseAlmCnt);
910 u32 ret_value;
911
912 if (!(pDM_Odm->SupportAbility & ODM_BB_FA_CNT))
913 return;
914
915 /* hold ofdm counter */
916 /* hold page C counter */
917 PHY_SetBBReg(pDM_Odm->Adapter, ODM_REG_OFDM_FA_HOLDC_11N, BIT31, 1);
918 /* hold page D counter */
919 PHY_SetBBReg(pDM_Odm->Adapter, ODM_REG_OFDM_FA_RSTD_11N, BIT31, 1);
920
921 ret_value = PHY_QueryBBReg(
922 pDM_Odm->Adapter, ODM_REG_OFDM_FA_TYPE1_11N, bMaskDWord
923 );
924 FalseAlmCnt->Cnt_Fast_Fsync = (ret_value&0xffff);
925 FalseAlmCnt->Cnt_SB_Search_fail = ((ret_value&0xffff0000)>>16);
926
927 ret_value = PHY_QueryBBReg(
928 pDM_Odm->Adapter, ODM_REG_OFDM_FA_TYPE2_11N, bMaskDWord
929 );
930 FalseAlmCnt->Cnt_OFDM_CCA = (ret_value&0xffff);
931 FalseAlmCnt->Cnt_Parity_Fail = ((ret_value&0xffff0000)>>16);
932
933 ret_value = PHY_QueryBBReg(
934 pDM_Odm->Adapter, ODM_REG_OFDM_FA_TYPE3_11N, bMaskDWord
935 );
936 FalseAlmCnt->Cnt_Rate_Illegal = (ret_value&0xffff);
937 FalseAlmCnt->Cnt_Crc8_fail = ((ret_value&0xffff0000)>>16);
938
939 ret_value = PHY_QueryBBReg(
940 pDM_Odm->Adapter, ODM_REG_OFDM_FA_TYPE4_11N, bMaskDWord
941 );
942 FalseAlmCnt->Cnt_Mcs_fail = (ret_value&0xffff);
943
944 FalseAlmCnt->Cnt_Ofdm_fail =
945 FalseAlmCnt->Cnt_Parity_Fail +
946 FalseAlmCnt->Cnt_Rate_Illegal +
947 FalseAlmCnt->Cnt_Crc8_fail +
948 FalseAlmCnt->Cnt_Mcs_fail +
949 FalseAlmCnt->Cnt_Fast_Fsync +
950 FalseAlmCnt->Cnt_SB_Search_fail;
951
952 {
953 /* hold cck counter */
954 PHY_SetBBReg(pDM_Odm->Adapter, ODM_REG_CCK_FA_RST_11N, BIT12, 1);
955 PHY_SetBBReg(pDM_Odm->Adapter, ODM_REG_CCK_FA_RST_11N, BIT14, 1);
956
957 ret_value = PHY_QueryBBReg(
958 pDM_Odm->Adapter, ODM_REG_CCK_FA_LSB_11N, bMaskByte0
959 );
960 FalseAlmCnt->Cnt_Cck_fail = ret_value;
961
962 ret_value = PHY_QueryBBReg(
963 pDM_Odm->Adapter, ODM_REG_CCK_FA_MSB_11N, bMaskByte3
964 );
965 FalseAlmCnt->Cnt_Cck_fail += (ret_value&0xff)<<8;
966
967 ret_value = PHY_QueryBBReg(
968 pDM_Odm->Adapter, ODM_REG_CCK_CCA_CNT_11N, bMaskDWord
969 );
970 FalseAlmCnt->Cnt_CCK_CCA =
971 ((ret_value&0xFF)<<8) | ((ret_value&0xFF00)>>8);
972 }
973
974 FalseAlmCnt->Cnt_all = (
975 FalseAlmCnt->Cnt_Fast_Fsync +
976 FalseAlmCnt->Cnt_SB_Search_fail +
977 FalseAlmCnt->Cnt_Parity_Fail +
978 FalseAlmCnt->Cnt_Rate_Illegal +
979 FalseAlmCnt->Cnt_Crc8_fail +
980 FalseAlmCnt->Cnt_Mcs_fail +
981 FalseAlmCnt->Cnt_Cck_fail
982 );
983
984 FalseAlmCnt->Cnt_CCA_all =
985 FalseAlmCnt->Cnt_OFDM_CCA + FalseAlmCnt->Cnt_CCK_CCA;
986
987 ODM_RT_TRACE(
988 pDM_Odm,
989 ODM_COMP_FA_CNT,
990 ODM_DBG_LOUD,
991 ("Enter odm_FalseAlarmCounterStatistics\n")
992 );
993 ODM_RT_TRACE(
994 pDM_Odm,
995 ODM_COMP_FA_CNT,
996 ODM_DBG_LOUD,
997 (
998 "Cnt_Fast_Fsync =%d, Cnt_SB_Search_fail =%d\n",
999 FalseAlmCnt->Cnt_Fast_Fsync,
1000 FalseAlmCnt->Cnt_SB_Search_fail
1001 )
1002 );
1003 ODM_RT_TRACE(
1004 pDM_Odm,
1005 ODM_COMP_FA_CNT,
1006 ODM_DBG_LOUD,
1007 (
1008 "Cnt_Parity_Fail =%d, Cnt_Rate_Illegal =%d\n",
1009 FalseAlmCnt->Cnt_Parity_Fail,
1010 FalseAlmCnt->Cnt_Rate_Illegal
1011 )
1012 );
1013 ODM_RT_TRACE(
1014 pDM_Odm,
1015 ODM_COMP_FA_CNT,
1016 ODM_DBG_LOUD,
1017 (
1018 "Cnt_Crc8_fail =%d, Cnt_Mcs_fail =%d\n",
1019 FalseAlmCnt->Cnt_Crc8_fail,
1020 FalseAlmCnt->Cnt_Mcs_fail
1021 )
1022 );
1023
1024 ODM_RT_TRACE(
1025 pDM_Odm,
1026 ODM_COMP_FA_CNT,
1027 ODM_DBG_LOUD,
1028 ("Cnt_OFDM_CCA =%d\n", FalseAlmCnt->Cnt_OFDM_CCA)
1029 );
1030 ODM_RT_TRACE(
1031 pDM_Odm,
1032 ODM_COMP_FA_CNT,
1033 ODM_DBG_LOUD,
1034 ("Cnt_CCK_CCA =%d\n", FalseAlmCnt->Cnt_CCK_CCA)
1035 );
1036 ODM_RT_TRACE(
1037 pDM_Odm,
1038 ODM_COMP_FA_CNT,
1039 ODM_DBG_LOUD,
1040 ("Cnt_CCA_all =%d\n", FalseAlmCnt->Cnt_CCA_all)
1041 );
1042 ODM_RT_TRACE(
1043 pDM_Odm,
1044 ODM_COMP_FA_CNT,
1045 ODM_DBG_LOUD,
1046 ("Cnt_Ofdm_fail =%d\n", FalseAlmCnt->Cnt_Ofdm_fail)
1047 );
1048 ODM_RT_TRACE(
1049 pDM_Odm,
1050 ODM_COMP_FA_CNT,
1051 ODM_DBG_LOUD,
1052 ("Cnt_Cck_fail =%d\n", FalseAlmCnt->Cnt_Cck_fail)
1053 );
1054 ODM_RT_TRACE(
1055 pDM_Odm,
1056 ODM_COMP_FA_CNT,
1057 ODM_DBG_LOUD,
1058 ("Cnt_Ofdm_fail =%d\n", FalseAlmCnt->Cnt_Ofdm_fail)
1059 );
1060 ODM_RT_TRACE(
1061 pDM_Odm,
1062 ODM_COMP_FA_CNT,
1063 ODM_DBG_LOUD,
1064 ("Total False Alarm =%d\n", FalseAlmCnt->Cnt_all)
1065 );
1066}
1067
1068
1069void odm_FAThresholdCheck(
1070 void *pDM_VOID,
1071 bool bDFSBand,
1072 bool bPerformance,
1073 u32 RxTp,
1074 u32 TxTp,
1075 u32 *dm_FA_thres
1076)
1077{
1078 PDM_ODM_T pDM_Odm = (PDM_ODM_T)pDM_VOID;
1079
1080 if (pDM_Odm->bLinked && (bPerformance || bDFSBand)) {
1081 /* For NIC */
1082 dm_FA_thres[0] = DM_DIG_FA_TH0;
1083 dm_FA_thres[1] = DM_DIG_FA_TH1;
1084 dm_FA_thres[2] = DM_DIG_FA_TH2;
1085 } else {
1086 dm_FA_thres[0] = 2000;
1087 dm_FA_thres[1] = 4000;
1088 dm_FA_thres[2] = 5000;
1089 }
1090 return;
1091}
1092
1093u8 odm_ForbiddenIGICheck(void *pDM_VOID, u8 DIG_Dynamic_MIN, u8 CurrentIGI)
1094{
1095 PDM_ODM_T pDM_Odm = (PDM_ODM_T)pDM_VOID;
1096 pDIG_T pDM_DigTable = &pDM_Odm->DM_DigTable;
1097 Pfalse_ALARM_STATISTICS pFalseAlmCnt = &(pDM_Odm->FalseAlmCnt);
1098 u8 rx_gain_range_min = pDM_DigTable->rx_gain_range_min;
1099
1100 if (pFalseAlmCnt->Cnt_all > 10000) {
1101 ODM_RT_TRACE(pDM_Odm, ODM_COMP_DIG, ODM_DBG_LOUD, ("odm_DIG(): Abnormally false alarm case.\n"));
1102
1103 if (pDM_DigTable->LargeFAHit != 3)
1104 pDM_DigTable->LargeFAHit++;
1105
1106 /* if (pDM_DigTable->ForbiddenIGI < pDM_DigTable->CurIGValue) */
1107 if (pDM_DigTable->ForbiddenIGI < CurrentIGI) {
1108 pDM_DigTable->ForbiddenIGI = CurrentIGI;
1109 /* pDM_DigTable->ForbiddenIGI = pDM_DigTable->CurIGValue; */
1110 pDM_DigTable->LargeFAHit = 1;
1111 }
1112
1113 if (pDM_DigTable->LargeFAHit >= 3) {
1114 if ((pDM_DigTable->ForbiddenIGI + 2) > pDM_DigTable->rx_gain_range_max)
1115 rx_gain_range_min = pDM_DigTable->rx_gain_range_max;
1116 else
1117 rx_gain_range_min = (pDM_DigTable->ForbiddenIGI + 2);
1118 pDM_DigTable->Recover_cnt = 1800;
1119 ODM_RT_TRACE(pDM_Odm, ODM_COMP_DIG, ODM_DBG_LOUD, ("odm_DIG(): Abnormally false alarm case: Recover_cnt = %d\n", pDM_DigTable->Recover_cnt));
1120 }
1121 } else {
1122 if (pDM_DigTable->Recover_cnt != 0) {
1123 pDM_DigTable->Recover_cnt--;
1124 ODM_RT_TRACE(pDM_Odm, ODM_COMP_DIG, ODM_DBG_LOUD, ("odm_DIG(): Normal Case: Recover_cnt = %d\n", pDM_DigTable->Recover_cnt));
1125 } else {
1126 if (pDM_DigTable->LargeFAHit < 3) {
1127 if ((pDM_DigTable->ForbiddenIGI - 2) < DIG_Dynamic_MIN) { /* DM_DIG_MIN) */
1128 pDM_DigTable->ForbiddenIGI = DIG_Dynamic_MIN; /* DM_DIG_MIN; */
1129 rx_gain_range_min = DIG_Dynamic_MIN; /* DM_DIG_MIN; */
1130 ODM_RT_TRACE(pDM_Odm, ODM_COMP_DIG, ODM_DBG_LOUD, ("odm_DIG(): Normal Case: At Lower Bound\n"));
1131 } else {
1132 pDM_DigTable->ForbiddenIGI -= 2;
1133 rx_gain_range_min = (pDM_DigTable->ForbiddenIGI + 2);
1134 ODM_RT_TRACE(pDM_Odm, ODM_COMP_DIG, ODM_DBG_LOUD, ("odm_DIG(): Normal Case: Approach Lower Bound\n"));
1135 }
1136 } else
1137 pDM_DigTable->LargeFAHit = 0;
1138 }
1139 }
1140
1141 return rx_gain_range_min;
1142
1143}
1144
1145/* 3 ============================================================ */
1146/* 3 CCK Packet Detect Threshold */
1147/* 3 ============================================================ */
1148
1149void odm_CCKPacketDetectionThresh(void *pDM_VOID)
1150{
1151 PDM_ODM_T pDM_Odm = (PDM_ODM_T)pDM_VOID;
1152 Pfalse_ALARM_STATISTICS FalseAlmCnt = &(pDM_Odm->FalseAlmCnt);
1153 u8 CurCCK_CCAThres;
1154
1155
1156 if (
1157 !(pDM_Odm->SupportAbility & ODM_BB_CCK_PD) ||
1158 !(pDM_Odm->SupportAbility & ODM_BB_FA_CNT)
1159 ) {
1160 ODM_RT_TRACE(
1161 pDM_Odm,
1162 ODM_COMP_CCK_PD,
1163 ODM_DBG_LOUD,
1164 ("odm_CCKPacketDetectionThresh() return ==========\n")
1165 );
1166 return;
1167 }
1168
1169 if (pDM_Odm->ExtLNA)
1170 return;
1171
1172 ODM_RT_TRACE(
1173 pDM_Odm,
1174 ODM_COMP_CCK_PD,
1175 ODM_DBG_LOUD,
1176 ("odm_CCKPacketDetectionThresh() ==========>\n")
1177 );
1178
1179 if (pDM_Odm->bLinked) {
1180 if (pDM_Odm->RSSI_Min > 25)
1181 CurCCK_CCAThres = 0xcd;
1182 else if ((pDM_Odm->RSSI_Min <= 25) && (pDM_Odm->RSSI_Min > 10))
1183 CurCCK_CCAThres = 0x83;
1184 else {
1185 if (FalseAlmCnt->Cnt_Cck_fail > 1000)
1186 CurCCK_CCAThres = 0x83;
1187 else
1188 CurCCK_CCAThres = 0x40;
1189 }
1190 } else {
1191 if (FalseAlmCnt->Cnt_Cck_fail > 1000)
1192 CurCCK_CCAThres = 0x83;
1193 else
1194 CurCCK_CCAThres = 0x40;
1195 }
1196
1197 ODM_Write_CCK_CCA_Thres(pDM_Odm, CurCCK_CCAThres);
1198
1199 ODM_RT_TRACE(
1200 pDM_Odm,
1201 ODM_COMP_CCK_PD,
1202 ODM_DBG_LOUD,
1203 (
1204 "odm_CCKPacketDetectionThresh() CurCCK_CCAThres = 0x%x\n",
1205 CurCCK_CCAThres
1206 )
1207 );
1208}
1209
1210void ODM_Write_CCK_CCA_Thres(void *pDM_VOID, u8 CurCCK_CCAThres)
1211{
1212 PDM_ODM_T pDM_Odm = (PDM_ODM_T)pDM_VOID;
1213 pDIG_T pDM_DigTable = &pDM_Odm->DM_DigTable;
1214
1215 /* modify by Guo.Mingzhi 2012-01-03 */
1216 if (pDM_DigTable->CurCCK_CCAThres != CurCCK_CCAThres)
1217 rtw_write8(pDM_Odm->Adapter, ODM_REG(CCK_CCA, pDM_Odm), CurCCK_CCAThres);
1218
1219 pDM_DigTable->PreCCK_CCAThres = pDM_DigTable->CurCCK_CCAThres;
1220 pDM_DigTable->CurCCK_CCAThres = CurCCK_CCAThres;
1221}