import PULS_20160108
[GitHub/mt8127/android_kernel_alcatel_ttab.git] / drivers / misc / mediatek / connectivity / conn_soc / drv_wlan / mt_wifi / wlan / mgmt / rate.c
CommitLineData
6fa3eb70
S
1/*
2** $Id: //Department/DaVinci/BRANCHES/MT6620_WIFI_DRIVER_V2_3/mgmt/rate.c#1 $
3*/
4
5/*! \file "rate.c"
6 \brief This file contains the transmission rate handling routines.
7
8 This file contains the transmission rate handling routines for setting up
9 ACK/CTS Rate, Highest Tx Rate, Lowest Tx Rate, Initial Tx Rate and do
10 conversion between Rate Set and Data Rates.
11*/
12
13
14
15/*
16** $Log: rate.c $
17 *
18 * 07 08 2010 cp.wu
19 *
20 * [WPD00003833] [MT6620 and MT5931] Driver migration - move to new repository.
21 *
22 * 06 08 2010 cp.wu
23 * [WPD00003833][MT6620 and MT5931] Driver migration
24 * add rate.c.
25 *
26 * 03 16 2010 kevin.huang
27 * [BORA00000663][WIFISYS][New Feature] AdHoc Mode Support
28 * Add AdHoc Mode
29 *
30 * 12 18 2009 cm.chang
31 * [BORA00000018]Integrate WIFI part into BORA for the 1st time
32 * .
33 *
34 * Nov 23 2009 mtk01461
35 * [BORA00000018] Integrate WIFI part into BORA for the 1st time
36 * Update comments
37 *
38 * Nov 16 2009 mtk01461
39 * [BORA00000018] Integrate WIFI part into BORA for the 1st time
40 * Fix DBGLOG
41 *
42 * Nov 5 2009 mtk01461
43 * [BORA00000018] Integrate WIFI part into BORA for the 1st time
44 *
45** \main\maintrunk.MT5921\12 2008-12-19 17:19:32 GMT mtk01461
46** Fix the problem that do not ASSERT the length of Supported Rate IE == 8
47** \main\maintrunk.MT5921\11 2008-12-01 18:17:42 GMT mtk01088
48** fixed the lint "possible using null pointer" warning
49** \main\maintrunk.MT5921\10 2008-08-20 00:16:36 GMT mtk01461
50** Update for Driver Review
51** \main\maintrunk.MT5921\9 2008-04-13 21:17:13 GMT mtk01461
52** Revise GEN Link Speed OID
53** \main\maintrunk.MT5921\8 2008-03-28 10:40:13 GMT mtk01461
54** Add rateGetRateSetFromDataRates() for set desired rate OID
55** \main\maintrunk.MT5921\7 2008-03-26 09:16:20 GMT mtk01461
56** Add adopt operational rate as ACK rate if BasicRateSet was not found
57** Add comments
58** \main\maintrunk.MT5921\6 2008-02-21 15:01:39 GMT mtk01461
59** Add initial rate according rx signal quality support
60** \main\maintrunk.MT5921\5 2008-01-07 15:06:44 GMT mtk01461
61** Fix typo of rate adaptation of CtrlResp Frame
62** \main\maintrunk.MT5921\4 2007-10-25 18:05:12 GMT mtk01461
63** Add VOIP SCAN Support & Refine Roaming
64*/
65
66/*******************************************************************************
67* C O M P I L E R F L A G S
68********************************************************************************
69*/
70
71/*******************************************************************************
72* E X T E R N A L R E F E R E N C E S
73********************************************************************************
74*/
75#include "precomp.h"
76
77/*******************************************************************************
78* C O N S T A N T S
79********************************************************************************
80*/
81/* The list of valid data rates. */
82const UINT_8 aucDataRate[] = {
83 RATE_1M, /* RATE_1M_INDEX = 0 */
84 RATE_2M, /* RATE_2M_INDEX */
85 RATE_5_5M, /* RATE_5_5M_INDEX */
86 RATE_11M, /* RATE_11M_INDEX */
87 RATE_22M, /* RATE_22M_INDEX */
88 RATE_33M, /* RATE_33M_INDEX */
89 RATE_6M, /* RATE_6M_INDEX */
90 RATE_9M, /* RATE_9M_INDEX */
91 RATE_12M, /* RATE_12M_INDEX */
92 RATE_18M, /* RATE_18M_INDEX */
93 RATE_24M, /* RATE_24M_INDEX */
94 RATE_36M, /* RATE_36M_INDEX */
95 RATE_48M, /* RATE_48M_INDEX */
96 RATE_54M, /* RATE_54M_INDEX */
97 RATE_HT_PHY /* RATE_HT_PHY_INDEX */
98};
99
100static const UINT_8 aucDefaultAckCtsRateIndex[RATE_NUM] = {
101 RATE_1M_INDEX, /* RATE_1M_INDEX = 0 */
102 RATE_2M_INDEX, /* RATE_2M_INDEX */
103 RATE_5_5M_INDEX, /* RATE_5_5M_INDEX */
104 RATE_11M_INDEX, /* RATE_11M_INDEX */
105 RATE_1M_INDEX, /* RATE_22M_INDEX - Not supported */
106 RATE_1M_INDEX, /* RATE_33M_INDEX - Not supported */
107 RATE_6M_INDEX, /* RATE_6M_INDEX */
108 RATE_6M_INDEX, /* RATE_9M_INDEX */
109 RATE_12M_INDEX, /* RATE_12M_INDEX */
110 RATE_12M_INDEX, /* RATE_18M_INDEX */
111 RATE_24M_INDEX, /* RATE_24M_INDEX */
112 RATE_24M_INDEX, /* RATE_36M_INDEX */
113 RATE_24M_INDEX, /* RATE_48M_INDEX */
114 RATE_24M_INDEX /* RATE_54M_INDEX */
115};
116
117const BOOLEAN afgIsOFDMRate[RATE_NUM] = {
118 FALSE, /* RATE_1M_INDEX = 0 */
119 FALSE, /* RATE_2M_INDEX */
120 FALSE, /* RATE_5_5M_INDEX */
121 FALSE, /* RATE_11M_INDEX */
122 FALSE, /* RATE_22M_INDEX - Not supported */
123 FALSE, /* RATE_33M_INDEX - Not supported */
124 TRUE, /* RATE_6M_INDEX */
125 TRUE, /* RATE_9M_INDEX */
126 TRUE, /* RATE_12M_INDEX */
127 TRUE, /* RATE_18M_INDEX */
128 TRUE, /* RATE_24M_INDEX */
129 TRUE, /* RATE_36M_INDEX */
130 TRUE, /* RATE_48M_INDEX */
131 TRUE /* RATE_54M_INDEX */
132};
133
134/*******************************************************************************
135* D A T A T Y P E S
136********************************************************************************
137*/
138
139/*******************************************************************************
140* P U B L I C D A T A
141********************************************************************************
142*/
143
144/*******************************************************************************
145* P R I V A T E D A T A
146********************************************************************************
147*/
148
149/*******************************************************************************
150* M A C R O S
151********************************************************************************
152*/
153
154/*******************************************************************************
155* F U N C T I O N D E C L A R A T I O N S
156********************************************************************************
157*/
158
159/*******************************************************************************
160* F U N C T I O N S
161********************************************************************************
162*/
163/*----------------------------------------------------------------------------*/
164/*!
165* @brief Convert the given Supported Rate & Extended Supported Rate IE to the
166* Operational Rate Set and Basic Rate Set, and also check if any Basic
167* Rate Code is unknown by driver.
168*
169* @param[in] prIeSupportedRate Pointer to the Supported Rate IE
170* @param[in] prIeExtSupportedRate Pointer to the Ext Supported Rate IE
171* @param[out] pu2OperationalRateSet Pointer to the Operational Rate Set
172* @param[out] pu2BSSBasicRateSet Pointer to the Basic Rate Set
173* @param[out] pfgIsUnknownBSSBasicRate Pointer to a Flag to indicate that Basic
174* Rate Set has unknown Rate Code
175*
176* \return (none)
177*/
178/*----------------------------------------------------------------------------*/
179VOID
180rateGetRateSetFromIEs (
181 IN P_IE_SUPPORTED_RATE_T prIeSupportedRate,
182 IN P_IE_EXT_SUPPORTED_RATE_T prIeExtSupportedRate,
183 OUT PUINT_16 pu2OperationalRateSet,
184 OUT PUINT_16 pu2BSSBasicRateSet,
185 OUT PBOOLEAN pfgIsUnknownBSSBasicRate
186 )
187{
188 UINT_16 u2OperationalRateSet = 0;
189 UINT_16 u2BSSBasicRateSet = 0;
190 BOOLEAN fgIsUnknownBSSBasicRate = FALSE;
191 UINT_8 ucRate;
192 UINT_32 i, j;
193
194
195 ASSERT(pu2OperationalRateSet);
196 ASSERT(pu2BSSBasicRateSet);
197 ASSERT(pfgIsUnknownBSSBasicRate);
198
199 if (prIeSupportedRate) {
200 /* NOTE(Kevin): Buffalo WHR-G54S's supported rate set IE exceed 8.
201 * IE_LEN(pucIE) == 12, "1(B), 2(B), 5.5(B), 6(B), 9(B), 11(B),
202 * 12(B), 18(B), 24(B), 36(B), 48(B), 54(B)"
203 */
204 //ASSERT(prIeSupportedRate->ucLength <= ELEM_MAX_LEN_SUP_RATES);
205 ASSERT(prIeSupportedRate->ucLength <= RATE_NUM);
206
207 for (i = 0; i < prIeSupportedRate->ucLength; i++) {
208 ucRate = prIeSupportedRate->aucSupportedRates[i] & RATE_MASK;
209
210 /* Search all valid data rates */
211 for (j = 0; j < sizeof(aucDataRate)/sizeof(UINT_8); j++) {
212 if (ucRate == aucDataRate[j]) {
213 u2OperationalRateSet |= BIT(j);
214
215 if (prIeSupportedRate->aucSupportedRates[i] & RATE_BASIC_BIT) {
216 u2BSSBasicRateSet |= BIT(j);
217 }
218
219 break;
220 }
221 }
222
223 if ((j == sizeof(aucDataRate)/sizeof(UINT_8)) &&
224 (prIeSupportedRate->aucSupportedRates[i] & RATE_BASIC_BIT)) {
225 fgIsUnknownBSSBasicRate = TRUE; /* A data rate not list in the aucDataRate[] */
226 }
227 }
228 }
229
230
231 if (prIeExtSupportedRate) {
232 //ASSERT(prIeExtSupportedRate->ucLength <= ELEM_MAX_LEN_EXTENDED_SUP_RATES);
233
234 for (i = 0; i < prIeExtSupportedRate->ucLength; i++) {
235 ucRate = prIeExtSupportedRate->aucExtSupportedRates[i] & RATE_MASK;
236
237 /* Search all valid data rates */
238 for (j = 0; j < sizeof(aucDataRate)/sizeof(UINT_8); j++) {
239 if (ucRate == aucDataRate[j]) {
240 u2OperationalRateSet |= BIT(j);
241
242 if (prIeExtSupportedRate->aucExtSupportedRates[i] & RATE_BASIC_BIT) {
243 u2BSSBasicRateSet |= BIT(j);
244 }
245
246 break;
247 }
248 }
249
250 if ((j == sizeof(aucDataRate)/sizeof(UINT_8)) &&
251 (prIeExtSupportedRate->aucExtSupportedRates[i] & RATE_BASIC_BIT)) {
252 fgIsUnknownBSSBasicRate = TRUE; /* A data rate not list in the aucDataRate[] */
253 }
254 }
255 }
256
257 *pu2OperationalRateSet = u2OperationalRateSet;
258 *pu2BSSBasicRateSet = u2BSSBasicRateSet;
259 *pfgIsUnknownBSSBasicRate = fgIsUnknownBSSBasicRate;
260
261 return;
262
263} /* end of rateGetRateSetFromIEs() */
264
265
266/*----------------------------------------------------------------------------*/
267/*!
268* @brief Convert the given Operational Rate Set & Basic Rate Set to the Rate Code
269* Format for used in (Ext)Supportec Rate IE.
270*
271* @param[in] u2OperationalRateSet Operational Rate Set
272* @param[in] u2BSSBasicRateSet Basic Rate Set
273* @param[out] pucDataRates Pointer to the Data Rate Buffer
274* @param[out] pucDataRatesLen Pointer to the Data Rate Buffer Length
275*
276* @return (none)
277*/
278/*----------------------------------------------------------------------------*/
279VOID
280rateGetDataRatesFromRateSet (
281 IN UINT_16 u2OperationalRateSet,
282 IN UINT_16 u2BSSBasicRateSet,
283 OUT PUINT_8 pucDataRates,
284 OUT PUINT_8 pucDataRatesLen
285 )
286{
287 UINT_32 i, j;
288
289
290 ASSERT(pucDataRates);
291 ASSERT(pucDataRatesLen);
292
293 ASSERT(u2BSSBasicRateSet == (u2OperationalRateSet & u2BSSBasicRateSet));
294
295 for (i = RATE_1M_INDEX, j = 0; i < RATE_NUM; i++) {
296 if (u2OperationalRateSet & BIT(i)) {
297
298 *(pucDataRates + j) = aucDataRate[i];
299
300 if (u2BSSBasicRateSet & BIT(i)) {
301 *(pucDataRates + j) |= RATE_BASIC_BIT;
302 }
303
304 j++;
305 }
306 }
307
308 *pucDataRatesLen = (UINT_8)j;
309
310 return;
311
312} /* end of rateGetDataRatesFromRateSet() */
313
314
315/*----------------------------------------------------------------------------*/
316/*!
317* \brief Get the highest rate from given Rate Set.
318*
319* \param[in] u2RateSet Rate Set
320* \param[out] pucHighestRateIndex Pointer to buffer of the Highest Rate Index
321*
322* \retval TRUE Highest Rate Index was found
323* \retval FALSE Highest Rate Index was not found
324*/
325/*----------------------------------------------------------------------------*/
326BOOLEAN
327rateGetHighestRateIndexFromRateSet (
328 IN UINT_16 u2RateSet,
329 OUT PUINT_8 pucHighestRateIndex
330 )
331{
332 INT_32 i;
333
334
335 ASSERT(pucHighestRateIndex);
336
337 for (i = RATE_54M_INDEX; i >= RATE_1M_INDEX; i--) {
338 if (u2RateSet & BIT(i)) {
339 *pucHighestRateIndex = (UINT_8)i;
340 return TRUE;
341 }
342 }
343
344 return FALSE;
345
346} /* end of rateGetHighestRateIndexFromRateSet() */
347
348
349/*----------------------------------------------------------------------------*/
350/*!
351* \brief Get the lowest rate from given Rate Set.
352*
353* \param[in] u2RateSet Rate Set
354* \param[out] pucLowestRateIndex Pointer to buffer of the Lowest Rate Index
355*
356* \retval TRUE Lowest Rate Index was found
357* \retval FALSE Lowest Rate Index was not found
358*/
359/*----------------------------------------------------------------------------*/
360BOOLEAN
361rateGetLowestRateIndexFromRateSet (
362 IN UINT_16 u2RateSet,
363 OUT PUINT_8 pucLowestRateIndex
364 )
365{
366 UINT_32 i;
367
368 ASSERT(pucLowestRateIndex);
369
370 for (i = RATE_1M_INDEX; i <= RATE_54M_INDEX; i++) {
371 if (u2RateSet & BIT(i)) {
372 *pucLowestRateIndex = (UINT_8)i;
373 return TRUE;
374 }
375 }
376
377 return FALSE;
378
379} /* end of rateGetLowestRateIndexFromRateSet() */
380
381
382#if 0 // NOTE(Kevin): For reference
383/*----------------------------------------------------------------------------*/
384/*!
385* \brief Convert the given Data Rates to the Rate Set.
386*
387* \param[in] pucDataRates Pointer to the Data Rates
388* \param[in] ucDataRatesLen Length of given Data Rates
389* \param[out] pu2RateSet Pointer to the Rate Set
390*
391* \return (none)
392*/
393/*----------------------------------------------------------------------------*/
394VOID
395rateGetRateSetFromDataRates (
396 IN PUINT_8 pucDataRates,
397 IN UINT_8 ucDataRatesLen,
398 OUT PUINT_16 pu2RateSet
399 )
400{
401 UINT_16 u2RateSet = 0;
402 UINT_8 ucRate;
403 UINT_32 i, j;
404
405
406 ASSERT(pucDataRates);
407 ASSERT(pu2RateSet);
408
409 if (pucDataRates) {
410 for (i = 0; i < ucDataRatesLen; i++) {
411 ucRate = pucDataRates[i] & RATE_MASK;
412
413 /* Search all valid data rates */
414 for (j = 0; j < sizeof(aucDataRate)/sizeof(UINT_8); j++) {
415 if (ucRate == aucDataRate[j]) {
416 u2RateSet |= BIT(j);
417 break;
418 }
419 }
420 }
421 }
422
423 *pu2RateSet = u2RateSet;
424
425 return;
426
427} /* end of rateGetRateSetFromDataRates() */
428
429
430/*----------------------------------------------------------------------------*/
431/*!
432* \brief Parse the Operational Rate Set and Basic Rate Set to get the corresponding
433* ACK/CTS(Respnose) TX Rates.
434*
435* \param[in] u2OperationalRateSet Operational Rate Set
436* \param[in] u2BSSBasicRateSet Basic Rate Set
437* \param[out] aucAckCtsRateIndex Pointer to the Ack/Cts Data Rate Buffer
438*
439* \return (none)
440*/
441/*----------------------------------------------------------------------------*/
442VOID
443rateSetAckCtsDataRatesFromRateSet (
444 IN UINT_16 u2OperationalRateSet,
445 IN UINT_16 u2BSSBasicRateSet,
446 IN OUT UINT_8 aucAckCtsRateIndex[]
447 )
448{
449 INT_32 i,j;
450
451
452 ASSERT(aucAckCtsRateIndex);
453 ASSERT(u2BSSBasicRateSet == (u2OperationalRateSet & u2BSSBasicRateSet));
454
455 /* Setup default ACK/CTS response rate */
456 kalMemCopy(aucAckCtsRateIndex, (PVOID)aucDefaultAckCtsRateIndex, sizeof(aucDefaultAckCtsRateIndex));
457
458
459 for (i = RATE_54M_INDEX; i >= RATE_1M_INDEX; i--) {
460 if (u2OperationalRateSet & BIT(i)) {
461 for (j = i; j >= RATE_1M_INDEX; j--) {
462 if (u2BSSBasicRateSet & BIT(j)) {
463 if ((afgIsOFDMRate[i] && afgIsOFDMRate[j]) || (!afgIsOFDMRate[i] && !afgIsOFDMRate[j])) // Reply ACK Frame at the same Modulation Scheme.
464 aucAckCtsRateIndex[i] = (UINT_8)j;
465 break;
466 }
467 }
468
469 /* NOTE(Kevin 2008/03/25): Following code is used for those AP which has
470 * NULL BasicRateSet.
471 * e.g. If input Operational Rate Set = [18M 12M 9M], Basic Rate Set = NULL.
472 * Originally we'll get Ack Rate for [18M 12M 9M] is [12M 12M "6M"].
473 * Now we'll get Ack Rate for [18M 12M 9M] is [12M 12M 9M],
474 * The Ack Rate for Tx Rates which are not list in Operational Rate Set is still
475 * use highest mandatory rate as default.
476 */
477 if (j < RATE_1M_INDEX) { /* The ACK/CTS rate was not found in BasicRateSet */
478 if (!(BIT(aucAckCtsRateIndex[i]) & u2OperationalRateSet)) {
479 aucAckCtsRateIndex[i] = (UINT_8)i;
480 }
481 }
482 }
483 }
484
485 return;
486
487} /* end of rateSetAckCtsDataRatesFromRateSet() */
488
489
490/*----------------------------------------------------------------------------*/
491/*!
492* \brief Get the proper initial rate from Rate Set according to given RCPI value
493*
494* \param[in] u2RateSet Rate Set
495* \param[in] rRcpi RCPI value from AP or Peer STA
496* \param[out] pucInitialRateIndex Pointer to buffer of the initial Rate Index
497*
498* \retval TRUE Initial Rate Index was found
499* \retval FALSE Initial Rate Index was not found
500*/
501/*----------------------------------------------------------------------------*/
502BOOLEAN
503rateGetBestInitialRateIndex (
504 IN UINT_16 u2RateSet,
505 IN RCPI rRcpi,
506 OUT PUINT_8 pucInitialRateIndex
507 )
508{
509 UINT_16 u2InitRateSet;
510 INT_32 i;
511
512
513 ASSERT(pucInitialRateIndex);
514
515 DBGLOG(MGT, TRACE, ("rRcpi = %d\n", rRcpi));
516
517 if (rRcpi >= RCPI_100) { /* Best Signal */
518 u2InitRateSet = INITIAL_RATE_SET(RCPI_100);
519 }
520 else if (rRcpi >= RCPI_80) { /* Better Signal */
521 u2InitRateSet = INITIAL_RATE_SET(RCPI_80);
522 }
523 else if (rRcpi >= RCPI_60) { /* Good Signal */
524 u2InitRateSet = INITIAL_RATE_SET(RCPI_60);
525 }
526 else { /* Worse Signal */
527 /* NOTE(Kevin): If return FALSE, we should assign the BSS Basic Rate Index
528 * (prBssInfo->ucBasicRateIndex) to the initial rate. It was determined in
529 * function - bssUpdateTxRateForControlFrame().
530 */
531 return FALSE;
532 }
533
534 u2RateSet &= u2InitRateSet;
535
536 for (i = RATE_54M_INDEX; i >= RATE_1M_INDEX; i--) {
537 if (u2RateSet & BIT(i)) {
538 *pucInitialRateIndex = (UINT_8)i;
539 return TRUE;
540 }
541 }
542
543 return FALSE;
544
545} /* end of rateGetBestInitialRateIndex() */
546#endif
547