• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /****************************************************************************
2 **+-----------------------------------------------------------------------+**
3 **|                                                                       |**
4 **| Copyright(c) 1998 - 2008 Texas Instruments. All rights reserved.      |**
5 **| All rights reserved.                                                  |**
6 **|                                                                       |**
7 **| Redistribution and use in source and binary forms, with or without    |**
8 **| modification, are permitted provided that the following conditions    |**
9 **| are met:                                                              |**
10 **|                                                                       |**
11 **|  * Redistributions of source code must retain the above copyright     |**
12 **|    notice, this list of conditions and the following disclaimer.      |**
13 **|  * Redistributions in binary form must reproduce the above copyright  |**
14 **|    notice, this list of conditions and the following disclaimer in    |**
15 **|    the documentation and/or other materials provided with the         |**
16 **|    distribution.                                                      |**
17 **|  * Neither the name Texas Instruments nor the names of its            |**
18 **|    contributors may be used to endorse or promote products derived    |**
19 **|    from this software without specific prior written permission.      |**
20 **|                                                                       |**
21 **| THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS   |**
22 **| "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT     |**
23 **| LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR |**
24 **| A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT  |**
25 **| OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, |**
26 **| SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT      |**
27 **| LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, |**
28 **| DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY |**
29 **| THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT   |**
30 **| (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE |**
31 **| OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.  |**
32 **|                                                                       |**
33 **+-----------------------------------------------------------------------+**
34 ****************************************************************************/
35 /**************************************************************************/
36 /*                                                                        */
37 /*   MODULE:  Rate Adaptation.c                                           */
38 /*                                                                        */
39 /**************************************************************************/
40 #include "RateAdaptation.h"
41 #include "DataCtrl_Api.h"
42 #include "802_11Defs.h"
43 #include "osApi.h"
44 #include "report.h"
45 #include "utils.h"
46 #include "EvHandler.h"
47 #include "apConn.h"
48 
49 
50 static TI_STATUS rateAdaptationa_rateToIndexInRateMapTable(rateAdaptation_t* pRateAdaptation,
51 														   rate_e rate, UINT8* Index);
52 
53 static modulationType_e setModulationForRate(rateAdaptation_t	*pRateAdaptation,
54    											 rate_e				rate,
55   											 modulationType_e	modulation,
56 											 bssType_e			bssType);
57 
58 BOOL rateAdaptation_isRateInTable(ctrlData_rateAdapt_t *currTable,
59 								rate_e			rate);
60 
61 void rateAdaptation_getFallBackStepUp(ctrlData_rateAdapt_t *currTable,
62 										rate_e			rate,UINT8* FB,UINT8* SU);
63 
64 static void rateAdaptation_rxTimeOut(TI_HANDLE hRateAdaptation);
65 
66 static BOOL set4xEnableForRate(rateAdaptation_t*	pRateAdaptation,
67 							   rate_e				rate,
68 							   BOOL					enable4x,
69 							   bssType_e			bssType);
70 
71 /*************************************************************************
72 *                        ctrlData_create
73 **************************************************************************
74 * DESCRIPTION:	This function create the rateAdaptation module.
75 *
76 * INPUT:		hOs - handle to Os Abstraction Layer
77 *
78 * OUTPUT:
79 *
80 * RETURN:		Handle to the allocated rateAdaptation block
81 ************************************************************************/
82 
rateAdaptation_create(TI_HANDLE hOs)83 rateAdaptation_t* rateAdaptation_create(TI_HANDLE hOs)
84 {
85 	rateAdaptation_t* pRateAdaptation;
86 	void			*pTimer;
87 
88 	if( hOs == NULL )
89 	{
90 	    WLAN_OS_REPORT(("FATAL ERROR: rateAdaptation_create(): OS handle Error - Aborting\n"));
91 		return NULL;
92 	}
93 
94 	/* alocate RateAdaptation block */
95 	pRateAdaptation = os_memoryAlloc(hOs, (sizeof(rateAdaptation_t)));
96 	if(!pRateAdaptation)
97 		return NULL;
98 
99 	/* alocate Timer to use in PowerSave algorithm */
100 	pTimer = os_timerCreate(hOs, rateAdaptation_rxTimeOut, pRateAdaptation);
101 
102 	if (!pTimer)
103 	{
104 		utils_nullMemoryFree(hOs, pRateAdaptation, sizeof(rateAdaptation_t));
105 	    WLAN_OS_REPORT(("FATAL ERROR: rateAdaptation_create(): Error Creating rateAdaptation Module - Aborting\n"));
106 		return NULL;
107 	}
108 
109 
110 	/* reset RateAdaptation module block */
111 	os_memoryZero(hOs, pRateAdaptation, (sizeof(rateAdaptation_t)));
112 
113 	pRateAdaptation->pTimer = pTimer;
114 
115 	pRateAdaptation->hOs = hOs;
116 
117 	return(pRateAdaptation);
118 
119 }
120 
121 /***************************************************************************
122 *						rateAdaptation_config
123 ****************************************************************************
124 * DESCRIPTION:	This function initialize the Rate Adaptation algorithm
125 *
126 * INPUTS:		pRateAdaptation - the object
127 *				hOs - Handle to the Os Abstraction Layer
128 *				hReport - Handle to the Report object
129 *				rateAdaptationInitParam - pointer to Rate Adaptation
130 *										  module init parameters
131 *
132 * OUTPUT:
133 *
134 * RETURNS:		void
135 ***************************************************************************/
rateAdaptation_config(rateAdaptation_t * pRateAdaptation,TI_HANDLE hOs,TI_HANDLE hReport,TI_HANDLE hCtrlData,TI_HANDLE hEvHandler,TI_HANDLE hAPConnection,rateAdaptationInitParam_t * rateAdaptationInitParam)136 TI_STATUS rateAdaptation_config(rateAdaptation_t*			pRateAdaptation,
137 	   							TI_HANDLE					hOs,
138 								TI_HANDLE					hReport,
139 								TI_HANDLE					hCtrlData,
140                                 TI_HANDLE					hEvHandler,
141 								TI_HANDLE					hAPConnection,
142 								rateAdaptationInitParam_t*	rateAdaptationInitParam)
143 {
144 
145 	UINT32 i;
146 
147 	if( (pRateAdaptation == NULL)  || (hOs == NULL) ||
148 		(hReport == NULL) ||  (rateAdaptationInitParam == NULL) )
149 	{
150 	    WLAN_OS_REPORT(("FATAL ERROR: rateAdaptation_config(): Parameters Error - Aborting\n"));
151 		return NOK;
152 	}
153 
154 	pRateAdaptation->hOs = hOs;
155 	pRateAdaptation->hReport = hReport;
156 	pRateAdaptation->hCtrlData = hCtrlData;
157     pRateAdaptation->hEvHandler = hEvHandler;
158 	pRateAdaptation->hAPConnection = hAPConnection;
159 
160 	pRateAdaptation->contTxPacketsThreshold = rateAdaptationInitParam->contTxPacketsThreshold;
161 	pRateAdaptation->stepUpTxPacketsThreshold = rateAdaptationInitParam->stepUpTxPacketsThreshold;
162 	pRateAdaptation->ctrlDataFBShortInterval = rateAdaptationInitParam->ctrlDataFBShortInterval;
163 	pRateAdaptation->ctrlDataFBLongInterval = rateAdaptationInitParam->ctrlDataFBLongInterval;
164 	pRateAdaptation->lowRateThreshold = DEF_LOW_RATE_THRESHOLD;
165 
166 	pRateAdaptation->rateAdapt_timeout = 1000*rateAdaptationInitParam->rateAdapt_timeout;
167 
168 	pRateAdaptation->txCount = 0;
169 	pRateAdaptation->txSkipCount = 0;
170 	pRateAdaptation->txFailCount = 0;
171     pRateAdaptation->txRateFallBackCount = 0;
172 
173 	pRateAdaptation->stepUpFlag = FALSE;
174 
175 	/* resset Tspecs Rate Parameters */
176 	for(i = 0 ; i < MAX_NUM_OF_AC ; i++)
177 	{
178 		pRateAdaptation->tspecsRateParameters[i].enableEvent = FALSE;
179 		if(rateAdaptationInitParam->tspecsRateParameters[i].highRateThreshold < rateAdaptationInitParam->tspecsRateParameters[i].lowRateThreshold)
180 		{
181 			WLAN_REPORT_ERROR(pRateAdaptation->hReport, RATE_ADAPTATION_MODULE_LOG,
182 					(" rateAdaptation_config() ERROR: highRateThreshold < lowRateThreshold,  ac = %d\n",i));
183 
184 			pRateAdaptation->tspecsRateParameters[i].highRateThreshold = 0;
185 			pRateAdaptation->tspecsRateParameters[i].lowRateThreshold = 0;
186 
187 		}
188 		/* if either one of the threshold is zero all threshold should be with zero default value */
189 		else if( (rateAdaptationInitParam->tspecsRateParameters[i].highRateThreshold == 0) ||
190 				 (rateAdaptationInitParam->tspecsRateParameters[i].lowRateThreshold == 0))
191 		{
192 			pRateAdaptation->tspecsRateParameters[i].highRateThreshold = 0;
193 			pRateAdaptation->tspecsRateParameters[i].lowRateThreshold = 0;
194 		}
195 		else
196 		{
197 			pRateAdaptation->tspecsRateParameters[i].highRateThreshold = rateAdaptationInitParam->tspecsRateParameters[i].highRateThreshold;
198 			pRateAdaptation->tspecsRateParameters[i].lowRateThreshold = rateAdaptationInitParam->tspecsRateParameters[i].lowRateThreshold;
199 		}
200 	}
201 
202 	WLAN_REPORT_INFORMATION(pRateAdaptation->hReport, RATE_ADAPTATION_MODULE_LOG,
203 			(" Rate Adaptation initialize success\n"));
204 
205 	return OK;
206 
207 }
208 
209 /***************************************************************************
210 *							rateAdaptation_destroy
211 ****************************************************************************
212 * DESCRIPTION:	This function destroy the rateAdaptation object.
213 *
214 * INPUTS:		rateAdaptation - the object
215 *
216 * RETURNS:		OK - Unload succesfull
217 *				NOK - Unload unsuccesfull
218 ***************************************************************************/
219 
rateAdaptation_destroy(rateAdaptation_t * pRateAdaptation)220 TI_STATUS rateAdaptation_destroy(rateAdaptation_t* pRateAdaptation)
221 {
222 
223 	/* check parameters validity */
224 	if( pRateAdaptation == NULL )
225 	{
226 		WLAN_REPORT_ERROR(pRateAdaptation->hReport, RATE_ADAPTATION_MODULE_LOG,
227 			(" rateAdaptation_destroy() : parametrs value error \n"));
228 		return NOK;
229 	}
230 
231 	/* free timer */
232 	os_timerStop(pRateAdaptation->hOs, pRateAdaptation->pTimer);
233 	utils_nullTimerDestroy(pRateAdaptation->hOs, pRateAdaptation->pTimer);
234 
235 
236 	/* free rateAdaptation block */
237 	os_memoryFree(pRateAdaptation->hOs, pRateAdaptation, sizeof(rateAdaptation_t));
238 
239 	return OK;
240 }
241 
242 /***************************************************************************
243 *							rateAdaptation_rxTimeOut
244 ****************************************************************************
245 * DESCRIPTION:
246 ****************************************************************************/
247 
rateAdaptation_rxTimeOut(TI_HANDLE hRateAdaptation)248 static void rateAdaptation_rxTimeOut(TI_HANDLE hRateAdaptation)
249 {
250    rateAdaptation_t* pRateAdaptation = (rateAdaptation_t *) hRateAdaptation;
251    	UINT8		prevIndex = pRateAdaptation->currRateIndex,i;
252 	OS_802_11_THRESHOLD_CROSS_INDICATION_PARAMS	tspecRateCross;
253 
254 	os_timerStop(pRateAdaptation->hOs, pRateAdaptation->pTimer);
255 	os_timerStart(pRateAdaptation->hOs, pRateAdaptation->pTimer,pRateAdaptation->rateAdapt_timeout,FALSE);
256 
257 	pRateAdaptation->txCount = 0;
258 	pRateAdaptation->txSkipCount = 0;
259 	pRateAdaptation->txFailCount = 0;
260     pRateAdaptation->txRateFallBackCount = 0;
261 	pRateAdaptation->currRateIndex = pRateAdaptation->maxRateIndex;
262 
263 
264    	/* update OS with the current rate */
265 	if(prevIndex != pRateAdaptation->currRateIndex)
266 	{
267 		UINT32					statusData;
268 		paramInfo_t				param;
269 
270 	    pRateAdaptation->expirTimeTick = os_timeStampMs(pRateAdaptation->hOs) + pRateAdaptation->ctrlDataFBShortInterval;
271 	    pRateAdaptation->stepUpFlag = TRUE;
272 
273         WLAN_REPORT_WARNING(pRateAdaptation->hReport, RATE_ADAPTATION_MODULE_LOG,
274 			(" RateAdapt() : Time: %d, (60sec) OldRate(Index,Rate): %d,%d, NewRate(Index,Rate): %d,%d\n",
275             os_timeStampMs(pRateAdaptation->hOs),
276 			prevIndex,pRateAdaptation->RatesMap[prevIndex].rateNumber,
277 			pRateAdaptation->currRateIndex, pRateAdaptation->RatesMap[pRateAdaptation->currRateIndex].rateNumber ));
278 
279         /* update OS with the current rate */
280 		param.paramType = CTRL_DATA_FOUR_X_CURRRENT_STATUS_PARAM;
281 		param.content.ctrlDataCerruentFourXstate = pRateAdaptation->RatesMap[pRateAdaptation->currRateIndex].fourXEnable;
282 		ctrlData_setParam(pRateAdaptation->hCtrlData, &param);
283 
284     	/* update OS with the current rate */
285 
286 		statusData = hostToUtilityRate(pRateAdaptation->RatesMap[pRateAdaptation->currRateIndex].rate);
287 
288         EvHandlerSendEvent(pRateAdaptation->hEvHandler, IPC_EVENT_LINK_SPEED, (UINT8 *)&statusData,sizeof(UINT32));
289 
290 		/* send Tspecs Rate Event */
291 		for(i = 0 ; i < MAX_NUM_OF_AC ; i++)
292 		{
293 			if(pRateAdaptation->tspecsRateParameters[i].enableEvent == FALSE)
294 			{
295 				continue;
296 			}
297 			else
298 			{
299 				if( ((pRateAdaptation->RatesMap[prevIndex].rateNumber) < (pRateAdaptation->tspecsRateParameters[i].highRateThreshold)) &&
300 					(pRateAdaptation->RatesMap[pRateAdaptation->currRateIndex].rateNumber >= (pRateAdaptation->tspecsRateParameters[i].highRateThreshold)) )
301 				{
302 					tspecRateCross.uAC = i;
303 					tspecRateCross.uHighOrLowThresholdFlag = HIGH_THRESHOLD_CROSS;
304                     tspecRateCross.uAboveOrBelowFlag = CROSS_ABOVE;
305 					EvHandlerSendEvent(pRateAdaptation->hEvHandler, IPC_EVENT_TSPEC_RATE_STATUS, (UINT8 *)&tspecRateCross,sizeof(tspecRateCross));
306 				}
307                 else
308                 if( ((pRateAdaptation->RatesMap[prevIndex].rateNumber) < (pRateAdaptation->tspecsRateParameters[i].lowRateThreshold)) &&
309 						(hostRateToNumber((rate_e)pRateAdaptation->RatesMap[pRateAdaptation->currRateIndex].rateNumber) >= (pRateAdaptation->tspecsRateParameters[i].lowRateThreshold)) )
310 					{
311 						tspecRateCross.uAC = i;
312 						tspecRateCross.uHighOrLowThresholdFlag = LOW_THRESHOLD_CROSS;
313                         tspecRateCross.uAboveOrBelowFlag = CROSS_ABOVE;
314 						EvHandlerSendEvent(pRateAdaptation->hEvHandler, IPC_EVENT_TSPEC_RATE_STATUS, (UINT8 *)&tspecRateCross,sizeof(OS_802_11_THRESHOLD_CROSS_INDICATION_PARAMS));
315 					}
316 
317 			}
318 		}
319 	}
320     else {
321         /* no change */
322         pRateAdaptation->expirTimeTick = os_timeStampMs(pRateAdaptation->hOs) + pRateAdaptation->ctrlDataFBLongInterval;
323 	    pRateAdaptation->stepUpFlag = FALSE;
324     }
325 
326 }
327 /***************************************************************************
328 *							rateAdaptation_getCurrent
329 ****************************************************************************
330 * DESCRIPTION:	get current state - Rate and Modulation
331 *               Note: since a pointer to the rates map is returned,
332 *               Its content should be treated as READ ONLY!!!
333 ****************************************************************************/
rateAdaptation_getCurrent(rateAdaptation_t * pRateAdaptation)334 rateModulation4x_table_t* rateAdaptation_getCurrent(rateAdaptation_t* pRateAdaptation)
335 {
336     return &(pRateAdaptation->RatesMap[pRateAdaptation->currRateIndex]);
337 }
338 
339 /***************************************************************************
340 *						rateAdaptation_getCurrentRate
341 ****************************************************************************
342 * DESCRIPTION:	get current Rate
343 ****************************************************************************/
rateAdaptation_getCurrentRate(rateAdaptation_t * pRateAdaptation)344 rate_e rateAdaptation_getCurrentRate(rateAdaptation_t* pRateAdaptation)
345 {
346 	return pRateAdaptation->RatesMap[pRateAdaptation->currRateIndex].rate;
347 }
348 
349 /***************************************************************************
350 *					rateAdaptation_getCurrentModulation		               *
351 ****************************************************************************
352 * DESCRIPTION:	get current Modulation
353 ****************************************************************************/
rateAdaptation_getCurrentModulation(rateAdaptation_t * pRateAdaptation)354 modulationType_e rateAdaptation_getCurrentModulation(rateAdaptation_t* pRateAdaptation)
355 {
356 	return pRateAdaptation->RatesMap[pRateAdaptation->currRateIndex].modulation;
357 }
358 
359 /***************************************************************************
360 *					rateAdaptation_getCurrentFourXEnable	               *
361 ****************************************************************************
362 * DESCRIPTION:	get current fourx status
363 ****************************************************************************/
rateAdaptation_getCurrentFourXEnable(rateAdaptation_t * pRateAdaptation)364 BOOL rateAdaptation_getCurrentFourXEnable(rateAdaptation_t* pRateAdaptation)
365 {
366 	return pRateAdaptation->RatesMap[pRateAdaptation->currRateIndex].fourXEnable;
367 }
368 
369 /***************************************************************************
370 *					rateAdaptation_buildRateMapTable		               *
371 ****************************************************************************
372 * DESCRIPTION:	build the rate map table
373 ****************************************************************************/
rateAdaptation_buildRateMapTable(rateAdaptation_t * pRateAdaptation,ctrlData_rateAdapt_t * currTable,UINT32 supportedBitMap,UINT32 clientBitMap,modulationType_e modulation,BOOL enable4x,bssType_e bssType)374 TI_STATUS rateAdaptation_buildRateMapTable(rateAdaptation_t		*pRateAdaptation,
375 												   ctrlData_rateAdapt_t *currTable,
376 												   UINT32				supportedBitMap,
377 												   UINT32				clientBitMap,
378 												   modulationType_e		modulation,
379 												   BOOL					enable4x,
380 												   bssType_e			bssType)
381 {
382 	UINT8 i = 0;
383 	UINT8 index = 0;
384 	UINT32					statusData;
385 	UINT8 fallBack,stepUp;
386 
387 	/*
388 	Note : allRates[] is changed due to the fact that rate_e was set in the
389 	wrong order : 6,9 were in higher numeric value then 5.5 and 11 !!!
390 	 */
391 	rate_e	allRates[] =   {DRV_RATE_1M,
392 							DRV_RATE_2M,
393 							DRV_RATE_5_5M,
394 							DRV_RATE_6M,
395 							DRV_RATE_9M,
396 							DRV_RATE_11M,
397 							DRV_RATE_12M,
398 							DRV_RATE_18M,
399 							DRV_RATE_22M,
400 							DRV_RATE_24M,
401 							DRV_RATE_36M,
402 							DRV_RATE_48M,
403 							DRV_RATE_54M
404 	};
405 
406 	while(i < DRV_RATE_MAX)
407 	{
408 		if(rateAdaptation_Utils_IsRateInBitmap(pRateAdaptation,
409 											  supportedBitMap,
410 											  allRates[i]) == OK)
411 		{
412 			/* update rates parameters */
413 			pRateAdaptation->RatesMap[index].rate = allRates[i];
414 			pRateAdaptation->RatesMap[index].rateNumber = hostRateToNumber(allRates[i]);
415 
416 			if((rateAdaptation_isRateInTable(currTable,pRateAdaptation->RatesMap[index].rate)) &&
417 				(rateAdaptation_Utils_IsRateInBitmap(pRateAdaptation,
418 													clientBitMap,
419 													allRates[i]) == OK))
420 			{
421 				pRateAdaptation->RatesMap[index].valid = TRUE;
422 				rateAdaptation_getFallBackStepUp(currTable,pRateAdaptation->RatesMap[index].rate,&fallBack,&stepUp);
423 				pRateAdaptation->RatesMap[index].rateAdaptFallBack = fallBack;
424 				pRateAdaptation->RatesMap[index].rateAdaptStepUp = stepUp;
425 
426 				/* update modulation parameter */
427 				pRateAdaptation->RatesMap[index].modulation = setModulationForRate(pRateAdaptation,
428 																				   pRateAdaptation->RatesMap[index].rate,
429 																				   modulation,bssType);
430 
431 				/* update 4x enable parameter */
432 				pRateAdaptation->RatesMap[index].fourXEnable = set4xEnableForRate(pRateAdaptation,
433 					 															  pRateAdaptation->RatesMap[index].rate,
434 																				  enable4x, bssType);
435 
436 				pRateAdaptation->maxRateIndex = index;
437 				pRateAdaptation->currRateIndex = index;
438 			}
439 			else
440 			{
441 				pRateAdaptation->RatesMap[index].valid = FALSE;
442 				pRateAdaptation->RatesMap[index].modulation = setModulationForRate(pRateAdaptation,
443 																				   pRateAdaptation->RatesMap[index].rate,
444 																				   modulation,bssType);
445 			}
446 
447 			index++;
448 		}
449 
450 		i++;
451 	}
452 
453 	/* report the current rate to OS */
454 	statusData = hostToUtilityRate(pRateAdaptation->RatesMap[pRateAdaptation->currRateIndex].rate);
455 
456     EvHandlerSendEvent(pRateAdaptation->hEvHandler, IPC_EVENT_LINK_SPEED, (UINT8 *)&statusData,sizeof(UINT32));
457 
458 	return OK;
459 }
460 
461 /***************************************************************************
462 *							buildRateBitMap					               *
463 ****************************************************************************
464 * DESCRIPTION:
465 ****************************************************************************/
466 
rateAdaptation_Utils_buildRateBitMap(rateAdaptation_t * pRateAdaptation,ctrlData_rateAdapt_t * currTable,rate_e rate,UINT32 supportedBitMap,UINT32 clientBitMap)467 UINT32 rateAdaptation_Utils_buildRateBitMap(rateAdaptation_t	*pRateAdaptation,
468 											ctrlData_rateAdapt_t *currTable,
469 											rate_e			rate,
470 											UINT32			supportedBitMap,
471 											UINT32			clientBitMap)
472 {
473 	UINT32 buildRateBitMap = 0;
474 	UINT8 rateNumber = hostRateToNumber(rate);
475 
476 	if( (rateNumber >= hostRateToNumber(DRV_RATE_1M)) && (rateAdaptation_isRateInTable(currTable, DRV_RATE_1M) ) ) buildRateBitMap |= (clientBitMap & supportedBitMap & DRV_RATE_MASK_1_BARKER);
477 	if( (rateNumber >= hostRateToNumber(DRV_RATE_2M)) && (rateAdaptation_isRateInTable(currTable, DRV_RATE_2M) ) )  buildRateBitMap |= (clientBitMap & supportedBitMap & DRV_RATE_MASK_2_BARKER);
478 	if( (rateNumber >= hostRateToNumber(DRV_RATE_5_5M)) && (rateAdaptation_isRateInTable(currTable, DRV_RATE_5_5M) ) ) buildRateBitMap |= (clientBitMap & supportedBitMap & DRV_RATE_MASK_5_5_CCK);
479 	if( (rateNumber >= hostRateToNumber(DRV_RATE_11M)) && (rateAdaptation_isRateInTable(currTable, DRV_RATE_11M) ) ) buildRateBitMap |= (clientBitMap & supportedBitMap & DRV_RATE_MASK_11_CCK);
480 	if( (rateNumber >= hostRateToNumber(DRV_RATE_22M)) && (rateAdaptation_isRateInTable(currTable, DRV_RATE_22M) ) ) buildRateBitMap |= (clientBitMap & supportedBitMap & DRV_RATE_MASK_22_PBCC);
481 	if( (rateNumber >= hostRateToNumber(DRV_RATE_6M)) && (rateAdaptation_isRateInTable(currTable, DRV_RATE_6M) ) )  buildRateBitMap |= (clientBitMap & supportedBitMap & DRV_RATE_MASK_6_OFDM);
482 	if( (rateNumber >= hostRateToNumber(DRV_RATE_9M)) && (rateAdaptation_isRateInTable(currTable, DRV_RATE_9M) ) )  buildRateBitMap |= (clientBitMap & supportedBitMap & DRV_RATE_MASK_9_OFDM);
483 	if( (rateNumber >= hostRateToNumber(DRV_RATE_12M)) && (rateAdaptation_isRateInTable(currTable, DRV_RATE_12M) ) ) buildRateBitMap |= (clientBitMap & supportedBitMap & DRV_RATE_MASK_12_OFDM);
484 	if( (rateNumber >= hostRateToNumber(DRV_RATE_18M)) && (rateAdaptation_isRateInTable(currTable, DRV_RATE_18M) ) ) buildRateBitMap |= (clientBitMap & supportedBitMap & DRV_RATE_MASK_18_OFDM);
485 	if( (rateNumber >= hostRateToNumber(DRV_RATE_24M)) && (rateAdaptation_isRateInTable(currTable, DRV_RATE_24M) ) ) buildRateBitMap |= (clientBitMap & supportedBitMap & DRV_RATE_MASK_24_OFDM);
486 	if( (rateNumber >= hostRateToNumber(DRV_RATE_36M)) && (rateAdaptation_isRateInTable(currTable, DRV_RATE_36M) ) ) buildRateBitMap |= (clientBitMap & supportedBitMap & DRV_RATE_MASK_36_OFDM);
487 	if( (rateNumber >= hostRateToNumber(DRV_RATE_48M)) && (rateAdaptation_isRateInTable(currTable, DRV_RATE_48M) ) ) buildRateBitMap |= (clientBitMap & supportedBitMap & DRV_RATE_MASK_48_OFDM);
488 	if( (rateNumber >= hostRateToNumber(DRV_RATE_54M)) && (rateAdaptation_isRateInTable(currTable, DRV_RATE_54M) ) ) buildRateBitMap |= (clientBitMap & supportedBitMap & DRV_RATE_MASK_54_OFDM);
489 
490 	return buildRateBitMap;
491 }
492 
493 /***************************************************************************
494 *							rateAdaptation_isRateInTable					               *
495 ****************************************************************************
496 * DESCRIPTION:	check if a specific rate is in a rates table
497 ****************************************************************************/
498 
rateAdaptation_isRateInTable(ctrlData_rateAdapt_t * currTable,rate_e rate)499 BOOL rateAdaptation_isRateInTable(ctrlData_rateAdapt_t *currTable,
500 										rate_e			rate)
501 {
502 	UINT8 i = 0;
503 
504 	while(i <= currTable->len)
505 	{
506 		if(currTable->rateAdaptRatesTable[i++] == rate)
507 			return TRUE;
508 	}
509 	return FALSE;
510 }
511 
512 /***************************************************************************
513 *							rateAdaptation_getFallBackStepUp					               *
514 ****************************************************************************
515 * DESCRIPTION:	return Fall Back & Step UP values of a certain rate
516 ****************************************************************************/
517 
rateAdaptation_getFallBackStepUp(ctrlData_rateAdapt_t * currTable,rate_e rate,UINT8 * FB,UINT8 * SU)518 void rateAdaptation_getFallBackStepUp(ctrlData_rateAdapt_t *currTable,
519 										rate_e			rate,UINT8* FB,UINT8* SU)
520 {
521 	UINT8 i = 0;
522 
523 	while(i <= currTable->len)
524 	{
525 		if(currTable->rateAdaptRatesTable[i++] == rate)
526 		{
527 			*FB = currTable->rateAdaptFBTable[--i];
528 			*SU = currTable->rateAdaptSUTable[i];
529 			return;
530 		}
531 	}
532 
533 	*FB = 0;
534 	*SU = 0;
535 }
536 
537 
538 /***************************************************************************
539 *							IsRateInBitmap					               *
540 ****************************************************************************
541 * DESCRIPTION:	check if a specific rate is in a rates bitmap
542 ****************************************************************************/
rateAdaptation_Utils_IsRateInBitmap(rateAdaptation_t * pRateAdaptation,UINT32 ratesBitMap,rate_e rate)543 TI_STATUS rateAdaptation_Utils_IsRateInBitmap(rateAdaptation_t	*pRateAdaptation,
544 											UINT32				ratesBitMap,
545 											rate_e				rate)
546 {
547 	if( ( (rate == DRV_RATE_1M) && (ratesBitMap & DRV_RATE_MASK_1_BARKER) )||
548 		( (rate == DRV_RATE_2M) && (ratesBitMap & DRV_RATE_MASK_2_BARKER) ) ||
549 		( (rate == DRV_RATE_5_5M) && (ratesBitMap & DRV_RATE_MASK_5_5_CCK) ) ||
550 		( (rate == DRV_RATE_11M) && (ratesBitMap & DRV_RATE_MASK_11_CCK) ) ||
551 		( (rate == DRV_RATE_22M) && (ratesBitMap & DRV_RATE_MASK_22_PBCC) ) ||
552 		( (rate == DRV_RATE_6M) && (ratesBitMap & DRV_RATE_MASK_6_OFDM) ) ||
553 		( (rate == DRV_RATE_9M) && (ratesBitMap & DRV_RATE_MASK_9_OFDM) ) ||
554 		( (rate == DRV_RATE_12M) && (ratesBitMap & DRV_RATE_MASK_12_OFDM) ) ||
555 		( (rate == DRV_RATE_18M) && (ratesBitMap & DRV_RATE_MASK_18_OFDM) ) ||
556 		( (rate == DRV_RATE_24M) && (ratesBitMap & DRV_RATE_MASK_24_OFDM) ) ||
557 		( (rate == DRV_RATE_36M) && (ratesBitMap & DRV_RATE_MASK_36_OFDM) ) ||
558 		( (rate == DRV_RATE_48M) && (ratesBitMap & DRV_RATE_MASK_48_OFDM) ) ||
559 		( (rate == DRV_RATE_54M) && (ratesBitMap & DRV_RATE_MASK_54_OFDM) ) )
560 	{
561 		return OK;
562 	}
563 
564 	return NOK;
565 }
566 /***************************************************************************
567 *							setModulationForRate			               *
568 ****************************************************************************
569 * DESCRIPTION:	set modulation for the rate map table
570 ****************************************************************************/
571 
setModulationForRate(rateAdaptation_t * pRateAdaptation,rate_e rate,modulationType_e modulation,bssType_e bssType)572 static modulationType_e setModulationForRate(rateAdaptation_t	*pRateAdaptation,
573    											 rate_e				rate,
574   											 modulationType_e	modulation,
575 											 bssType_e			bssType)
576 {
577 	switch(rate)
578 	{
579 		case DRV_RATE_1M:
580 			return DRV_MODULATION_QPSK;
581 
582 		case DRV_RATE_2M:
583 			return DRV_MODULATION_QPSK;
584 
585 		case DRV_RATE_5_5M:
586 			if( (modulation == DRV_MODULATION_PBCC) &&
587 				(bssType == BSS_INFRASTRUCTURE) )
588 				return DRV_MODULATION_PBCC;
589 			else
590 				return DRV_MODULATION_CCK;
591 
592 		case DRV_RATE_11M:
593 			if( (modulation == DRV_MODULATION_PBCC) &&
594 				(bssType == BSS_INFRASTRUCTURE) )
595 				return DRV_MODULATION_PBCC;
596 			else
597 				return DRV_MODULATION_CCK;
598 
599 		case DRV_RATE_22M:
600 			return DRV_MODULATION_PBCC;
601 
602 		case DRV_RATE_6M:
603 			return DRV_MODULATION_OFDM;
604 
605 		case DRV_RATE_9M:
606 			return DRV_MODULATION_OFDM;
607 
608 		case DRV_RATE_18M:
609 			return DRV_MODULATION_OFDM;
610 
611 		case DRV_RATE_12M:
612 			return DRV_MODULATION_OFDM;
613 
614 		case DRV_RATE_24M:
615 			return DRV_MODULATION_OFDM;
616 
617 		case DRV_RATE_36M:
618 			return DRV_MODULATION_OFDM;
619 
620 		case DRV_RATE_48M:
621 			return DRV_MODULATION_OFDM;
622 
623 		case DRV_RATE_54M:
624 			return DRV_MODULATION_OFDM;
625 
626 		default:
627 			WLAN_REPORT_ERROR(pRateAdaptation->hReport, RATE_ADAPTATION_MODULE_LOG,
628 						(" setModulationForRate(): unKnown rate !!! \n"));
629 			return DRV_MODULATION_NONE;
630 
631 	}
632 }
633 
set4xEnableForRate(rateAdaptation_t * pRateAdaptation,rate_e rate,BOOL enable4x,bssType_e bssType)634 static BOOL set4xEnableForRate(rateAdaptation_t*	pRateAdaptation,
635 							   rate_e				rate,
636    							   BOOL					enable4x,
637 							   bssType_e			bssType)
638 {
639 	if(bssType == BSS_INDEPENDENT)
640 		return FALSE;
641 
642 	switch(rate)
643 	{
644 		case DRV_RATE_1M:
645 			return FALSE;
646 
647 		case DRV_RATE_2M:
648 			return FALSE;
649 
650 		case DRV_RATE_5_5M:
651 			return FALSE;
652 
653 		case DRV_RATE_11M:
654 			return enable4x;
655 
656 		case DRV_RATE_22M:
657 			return enable4x;
658 
659 		case DRV_RATE_6M:
660 			return FALSE;
661 
662 		case DRV_RATE_9M:
663 			return FALSE;
664 
665 		case DRV_RATE_18M:
666 			return enable4x;
667 
668 		case DRV_RATE_12M:
669 			return enable4x;
670 
671 		case DRV_RATE_24M:
672 			return enable4x;
673 
674 		case DRV_RATE_36M:
675 			return enable4x;
676 
677 		case DRV_RATE_48M:
678 			return enable4x;
679 
680 		case DRV_RATE_54M:
681 			return enable4x;
682 
683 		default:
684 			WLAN_REPORT_ERROR(pRateAdaptation->hReport, RATE_ADAPTATION_MODULE_LOG,
685 						(" set4xEnableForRate(): unKnown rate !!! \n"));
686 			return DRV_MODULATION_NONE;
687 
688 	}
689 
690 
691 }
692 /***************************************************************************
693 *					rateAdaptation_setMaxActivRate
694 ****************************************************************************
695 * DESCRIPTION:	set current rate
696 ****************************************************************************/
rateAdaptation_setMaxActivRate(rateAdaptation_t * pRateAdaptation,rate_e rate)697 TI_STATUS rateAdaptation_setMaxActivRate(rateAdaptation_t* pRateAdaptation, rate_e rate)
698 {
699 	UINT8  index;
700 	UINT32 status;
701 
702 	status = rateAdaptationa_rateToIndexInRateMapTable(pRateAdaptation, rate, &index);
703 
704 	if(status != OK)
705 		return NOK;
706 
707 	pRateAdaptation->maxRateIndex = index;
708 
709 	return OK;
710 }
711 
712 /***************************************************************************
713 *					rateAdaptation_configLowRateThrsh
714 ****************************************************************************
715 * DESCRIPTION:	set low rate threshold
716 ****************************************************************************/
rateAdaptation_configLowRateThrsh(rateAdaptation_t * pRateAdaptation,UINT8 rate)717 TI_STATUS rateAdaptation_configLowRateThrsh(rateAdaptation_t *pRateAdaptation, UINT8 rate)
718 {
719 	pRateAdaptation->lowRateThreshold = rate;
720 
721 	WLAN_REPORT_INFORMATION(pRateAdaptation->hReport, RATE_ADAPTATION_MODULE_LOG,
722 			(" \nrateAdaptation_configLowRateThrsh:rate  %d, translated to %d \n", rate, pRateAdaptation->lowRateThreshold));
723 
724 	return OK;
725 }
726 
727 /***************************************************************************
728 *					rateAdaptation_updateModulation
729 ****************************************************************************
730 * DESCRIPTION:	set current rate
731 ****************************************************************************/
rateAdaptation_updateModulation(rateAdaptation_t * pRateAdaptation,modulationType_e modulation,bssType_e bssType)732 void rateAdaptation_updateModulation(rateAdaptation_t* pRateAdaptation,
733 									 modulationType_e modulation,
734 									 bssType_e bssType)
735 {
736 	UINT8 index = 0;
737 
738 	for(index = 0 ; index < pRateAdaptation->maxRateIndex ; index++)
739 	{
740 		pRateAdaptation->RatesMap[index].modulation = setModulationForRate(pRateAdaptation,
741    																			pRateAdaptation->RatesMap[index].rate,
742   																			modulation,
743 																			bssType);
744 	}
745 }
746 /***************************************************************************
747 *					rateAdaptation_updateModulation
748 ****************************************************************************
749 * DESCRIPTION:	set current rate
750 ****************************************************************************/
rateAdaptation_update4xEnable(rateAdaptation_t * pRateAdaptation,BOOL enable4x,bssType_e bssType)751 void rateAdaptation_update4xEnable(rateAdaptation_t* pRateAdaptation,
752 								   BOOL				 enable4x,
753 								   bssType_e		 bssType)
754 {
755 	UINT8 index = 0;
756 
757 	for(index = 0 ; index < pRateAdaptation->maxRateIndex ; index++)
758 	{
759 		pRateAdaptation->RatesMap[index].fourXEnable = set4xEnableForRate(pRateAdaptation,
760 																		  pRateAdaptation->RatesMap[index].rate,
761 																		  enable4x, bssType);
762 
763 	}
764 }
765 /***************************************************************************
766 *						ctrlData_rateAdaptationStart
767 ****************************************************************************
768 * DESCRIPTION:	This function start the Rate Adaptation algorithm
769 ***************************************************************************/
rateAdaptation_start(rateAdaptation_t * pRateAdaptation)770 TI_STATUS rateAdaptation_start(rateAdaptation_t* pRateAdaptation)
771 {
772 	UINT32					statusData;
773 
774 	pRateAdaptation->txCount = 0;
775 	pRateAdaptation->txSkipCount = 0;
776 	pRateAdaptation->txFailCount = 0;
777     pRateAdaptation->txRateFallBackCount = 0;
778 
779 	pRateAdaptation->stepUpFlag = FALSE;
780 
781 	os_timerStart(pRateAdaptation->hOs, pRateAdaptation->pTimer,pRateAdaptation->rateAdapt_timeout,FALSE);
782 
783 	pRateAdaptation->expirTimeTick = os_timeStampMs(pRateAdaptation->hOs) + pRateAdaptation->ctrlDataFBLongInterval;
784 
785    	/* update OS with the current rate */
786 	statusData = hostToUtilityRate(pRateAdaptation->RatesMap[pRateAdaptation->currRateIndex].rate);
787 
788     EvHandlerSendEvent(pRateAdaptation->hEvHandler, IPC_EVENT_LINK_SPEED, (UINT8 *)&statusData,sizeof(UINT32));
789 
790 	return OK;
791 }
792 
793 /***************************************************************************
794 *						ctrlData_rateAdaptationStop
795 ****************************************************************************
796 * DESCRIPTION:	This function stop the rate adaptation algorithm
797 ***************************************************************************/
rateAdaptation_stop(rateAdaptation_t * pRateAdaptation)798 TI_STATUS rateAdaptation_stop(rateAdaptation_t* pRateAdaptation)
799 {
800 	os_timerStop(pRateAdaptation->hOs, pRateAdaptation->pTimer);
801 
802 	pRateAdaptation->txCount = 0;
803 	pRateAdaptation->txSkipCount = 0;
804 	pRateAdaptation->txFailCount = 0;
805     pRateAdaptation->txRateFallBackCount = 0;
806 	pRateAdaptation->stepUpFlag = FALSE;
807 	pRateAdaptation->expirTimeTick = 0;
808 
809 	pRateAdaptation->currRateIndex = pRateAdaptation->maxRateIndex;
810 
811 
812 	return OK;
813 }
814 
815 /***************************************************************************
816 *						rateAdaptation_stopTimer
817 ****************************************************************************
818 * DESCRIPTION:	This function stop the rate adaptation timer
819 ***************************************************************************/
rateAdaptation_stopTimer(rateAdaptation_t * pRateAdaptation)820 TI_STATUS rateAdaptation_stopTimer(rateAdaptation_t* pRateAdaptation)
821 {
822 	os_timerStop(pRateAdaptation->hOs, pRateAdaptation->pTimer);
823 
824 	return OK;
825 }
826 
827 
828 /***************************************************************************
829 *					rateAdaptation_setCurrentRate
830 ****************************************************************************
831 * DESCRIPTION:	set current rate
832 ****************************************************************************/
rateAdaptation_setCurrentRate(rateAdaptation_t * pRateAdaptation,rate_e rate)833 TI_STATUS rateAdaptation_setCurrentRate(rateAdaptation_t* pRateAdaptation,rate_e rate)
834 {
835 	UINT8					index;
836 	UINT32					statusData;
837 
838 	if(rateAdaptationa_rateToIndexInRateMapTable(pRateAdaptation, rate, &index) == OK)
839 		pRateAdaptation->currRateIndex = index;
840 	else
841 		pRateAdaptation->currRateIndex = pRateAdaptation->maxRateIndex;
842 
843 	/* report the current rate to OS */
844 
845 	statusData = hostToUtilityRate(pRateAdaptation->RatesMap[pRateAdaptation->currRateIndex].rate);
846 
847     EvHandlerSendEvent(pRateAdaptation->hEvHandler, IPC_EVENT_LINK_SPEED, (UINT8 *)&statusData,sizeof(UINT32));
848 
849 	return OK;
850 }
851 
852 /***************************************************************************
853 *					ctrlData_rateToIndexInRateMapTable
854 ****************************************************************************
855 * DESCRIPTION:	This function convert a specific rate to index in the
856 *				Rate Adaptation algorithm ratemap table
857 *
858 * INPUTS:		pRateAdaptation - the object
859 *				rate - the rate to convert
860 *
861 * OUTPUT:		Index - the index of the rate in the table.
862 *
863 * RETURNS:		If the rate is not in the table - return NOK otherwise OK
864 ***************************************************************************/
rateAdaptationa_rateToIndexInRateMapTable(rateAdaptation_t * pRateAdaptation,rate_e rate,UINT8 * Index)865 static TI_STATUS rateAdaptationa_rateToIndexInRateMapTable(rateAdaptation_t* pRateAdaptation,
866 														   rate_e rate, UINT8* Index)
867 {
868 	UINT8 i;
869 
870 	for(i = 0 ; i <= pRateAdaptation->maxRateIndex ; i++)
871 	{
872 		if(pRateAdaptation->RatesMap[i].rate == rate)
873 		{
874 			*Index = i;
875 			return OK;
876 		}
877 	}
878 
879 	return NOK;
880 }
881 
882 /***************************************************************************
883 *					getPrevRate
884 ****************************************************************************
885 * DESCRIPTION:
886 *
887 * INPUTS:		pRateAdaptation - the object
888 *
889 * RETURNS:		new rate
890 ****************************************************************************/
getPrevRate(rateAdaptation_t * pRateAdaptation)891 UINT8 getPrevRate(rateAdaptation_t *pRateAdaptation)
892 {
893     INT16 i;
894     if(pRateAdaptation->currRateIndex != 0)
895     {
896         for(i = pRateAdaptation->currRateIndex - 1; i > 0; i--)
897         {
898             if(pRateAdaptation->RatesMap[i].valid)
899                 return (UINT8)i;
900         }
901     }
902     return pRateAdaptation->currRateIndex;
903 }
904 
905 
906 
907 /***************************************************************************
908 *					getNextRate
909 ****************************************************************************
910 * DESCRIPTION:
911 *
912 * INPUTS:		pRateAdaptation - the object
913 *
914 * RETURNS:		new rate
915 ****************************************************************************/
getNextRate(rateAdaptation_t * pRateAdaptation)916 UINT8 getNextRate(rateAdaptation_t *pRateAdaptation)
917 {
918 	UINT32 i;
919 
920 	for(i = pRateAdaptation->currRateIndex + 1; i <= pRateAdaptation->maxRateIndex; i++)
921 	{
922 		if(pRateAdaptation->RatesMap[i].valid)
923 			return i;
924 	}
925 
926 	return pRateAdaptation->currRateIndex;
927 }
928 
929 /***************************************************************************
930 *					rateAdaptation_updateRateAdaptation
931 ****************************************************************************
932 * DESCRIPTION:	This function perform the Rate Adaptation algorithm. It
933 *				called for every tx complete.
934 *
935 * INPUTS:		pRateAdaptation - the object
936 *				actualTxRate - the actual tx rate
937 *				requestTxRate - the request tx rate
938 *				TxStatus - the tx status
939 *               txNumWaiting - the number of descriptors in the HW with previous rate
940 *
941 * RETURNS:		OK/NOK
942 ****************************************************************************/
rateAdaptation_updateRateAdaptation(rateAdaptation_t * pRateAdaptation,rate_e actualTxRate,rate_e requestTxRate,UINT32 TxStatus,int txNumWaiting)943 TI_STATUS rateAdaptation_updateRateAdaptation(rateAdaptation_t* pRateAdaptation,
944 											  rate_e			actualTxRate,
945 											  rate_e			requestTxRate,
946 											  UINT32			TxStatus,
947                                               int               txNumWaiting)
948 {
949 
950 	UINT32		txFailPercent;
951 	UINT32		timeStamp;
952 	UINT8		actualTxRateNumber = hostRateToNumber(actualTxRate);
953 	UINT8		requestTxRateNumber = hostRateToNumber(requestTxRate);
954 	OS_802_11_THRESHOLD_CROSS_INDICATION_PARAMS	tspecRateCross;
955 	UINT8		i,prevIndex = pRateAdaptation->currRateIndex;
956 
957     /* Check if need to skip some packets due to rate update */
958     if (pRateAdaptation->txSkipCount > 0) {
959         pRateAdaptation->txSkipCount--;
960         return OK;
961     }
962 
963     timeStamp = os_timeStampMs(pRateAdaptation->hOs);
964 
965 	pRateAdaptation->txCount++;
966 
967     /* if the TxStatus wasn't SUCCESS or the rate was falling back - we will update the mechanism, unless */
968 	/* the TxStatus is LIFETIME_EXCEEDED and there were no retries - we won't update the mechanism        */
969 	if(((TxStatus != SEND_COMPLETE_SUCCESS) && (TxStatus != SEND_COMPLETE_LIFETIME_EXCEEDED))
970         || (actualTxRateNumber < requestTxRateNumber))
971 	{
972 		pRateAdaptation->txFailCount++;
973         if (actualTxRateNumber < requestTxRateNumber)
974            pRateAdaptation->txRateFallBackCount++;
975 	}
976 
977 	/* Verify if the checking time has come. */
978 	if( TS_EXCEEDS(timeStamp, pRateAdaptation->expirTimeTick) )
979 	{
980 		/* If step up has just done wait for 10 packets only. */
981 		if((pRateAdaptation->stepUpFlag == TRUE) &&
982 			(pRateAdaptation->txCount > pRateAdaptation->stepUpTxPacketsThreshold ))
983 		{
984 			/* Calculate the packet fail percent. */
985 			txFailPercent = (pRateAdaptation->txFailCount * 100) / pRateAdaptation->txCount;
986 
987 			pRateAdaptation->stepUpFlag = FALSE; /* Flag is off for next time. */
988 
989 			if( (txFailPercent > pRateAdaptation->RatesMap[pRateAdaptation->currRateIndex].rateAdaptFallBack) &&
990 				(pRateAdaptation->currRateIndex > 0) )
991 			{
992 				pRateAdaptation->currRateIndex = getPrevRate(pRateAdaptation);
993 			}
994 		}
995 		else if (pRateAdaptation->txCount > pRateAdaptation->contTxPacketsThreshold )
996 		{
997 			/* Calculate the packet fail percents. */
998 			txFailPercent = (pRateAdaptation->txFailCount * 100) / pRateAdaptation->txCount;
999 
1000 			if ( (txFailPercent > pRateAdaptation->RatesMap[pRateAdaptation->currRateIndex].rateAdaptFallBack) &&
1001 				(pRateAdaptation->currRateIndex > 0) )
1002 			{
1003                 pRateAdaptation->currRateIndex = getPrevRate(pRateAdaptation);
1004 			}
1005 			else if ((txFailPercent < pRateAdaptation->RatesMap[pRateAdaptation->currRateIndex].rateAdaptStepUp) &&
1006 				(pRateAdaptation->currRateIndex < pRateAdaptation->maxRateIndex))
1007 			{
1008 				pRateAdaptation->currRateIndex = getNextRate(pRateAdaptation);
1009 				pRateAdaptation->stepUpFlag = TRUE; /* Flag is on for next time. */
1010 			}
1011 		}
1012 		else
1013 		{
1014 			return OK;
1015 		}
1016 
1017 		/* update OS with the current rate */
1018 		if(prevIndex != pRateAdaptation->currRateIndex)
1019 		{
1020 			UINT32			statusData;
1021 			paramInfo_t		param;
1022 			rate_e			currentRate = pRateAdaptation->RatesMap[pRateAdaptation->currRateIndex].rate;
1023 			UINT8			currentRateNumber = pRateAdaptation->RatesMap[pRateAdaptation->currRateIndex].rateNumber;
1024 
1025 		    WLAN_REPORT_WARNING(pRateAdaptation->hReport, RATE_ADAPTATION_MODULE_LOG,
1026 			    (" RateAdapt() : Time: %d, Fail: %d, Count: %d,Skip: %d\n",
1027                 timeStamp,pRateAdaptation->txFailCount,pRateAdaptation->txCount,txNumWaiting));
1028 
1029 			WLAN_REPORT_WARNING(pRateAdaptation->hReport, RATE_ADAPTATION_MODULE_LOG,
1030 			    (" OldRate(Index,Rate): %d,%d\n ",prevIndex,pRateAdaptation->RatesMap[prevIndex].rateNumber));
1031 			WLAN_REPORT_WARNING(pRateAdaptation->hReport, RATE_ADAPTATION_MODULE_LOG,
1032 				(" NewRate(Index,Rate): %d,%d\n ",pRateAdaptation->currRateIndex,currentRateNumber));
1033 
1034 			/* If the current rate is lower or equal to the roaming threshold, issue roaming trigger. */
1035 			if (currentRateNumber <= pRateAdaptation->lowRateThreshold)
1036 			{
1037 				roamingEventData_u RoamingEventData;
1038 
1039 				RoamingEventData.rate = currentRate;
1040 				apConn_reportRoamingEvent(pRateAdaptation->hAPConnection, ROAMING_TRIGGER_LOW_TX_RATE, &RoamingEventData);
1041 			}
1042 
1043 			/* Rate update - initialize the skip counter for packets that are already in the queue with old rates */
1044             if ((txNumWaiting >= 0) && (txNumWaiting <= 100)) {
1045                 /* In reasonable range */
1046                 pRateAdaptation->txSkipCount = (UINT32)txNumWaiting;
1047             } else {
1048                 pRateAdaptation->txSkipCount = 30; /* something happened, at least skip 30 packets */
1049             }
1050 
1051     		/* update OS with the current rate */
1052 			param.paramType = CTRL_DATA_FOUR_X_CURRRENT_STATUS_PARAM;
1053 			param.content.ctrlDataCerruentFourXstate = pRateAdaptation->RatesMap[pRateAdaptation->currRateIndex].fourXEnable;
1054 			ctrlData_setParam(pRateAdaptation->hCtrlData, &param);
1055 
1056     		/* update OS with the current rate */
1057 
1058 			statusData = hostToUtilityRate(currentRate);
1059 
1060             EvHandlerSendEvent(pRateAdaptation->hEvHandler, IPC_EVENT_LINK_SPEED, (UINT8 *)&statusData,sizeof(UINT32));
1061 
1062 			/* send Tspecs Rate Event */
1063 			for(i = 0 ; i < MAX_NUM_OF_AC ; i++)
1064 			{
1065 				if(pRateAdaptation->tspecsRateParameters[i].enableEvent == FALSE)
1066 				{
1067 					continue;
1068 				}
1069 				else
1070 				{
1071 					if ( (pRateAdaptation->RatesMap[prevIndex].rateNumber < pRateAdaptation->tspecsRateParameters[i].highRateThreshold) &&
1072 						(currentRateNumber >= pRateAdaptation->tspecsRateParameters[i].highRateThreshold) )
1073 					{
1074 						tspecRateCross.uAC = i;
1075 						tspecRateCross.uHighOrLowThresholdFlag = HIGH_THRESHOLD_CROSS;
1076                         tspecRateCross.uAboveOrBelowFlag = CROSS_ABOVE;
1077 						EvHandlerSendEvent(pRateAdaptation->hEvHandler, IPC_EVENT_TSPEC_RATE_STATUS, (UINT8 *)&tspecRateCross,sizeof(OS_802_11_THRESHOLD_CROSS_INDICATION_PARAMS));
1078 					}
1079 					else
1080 					if( (pRateAdaptation->RatesMap[prevIndex].rateNumber >= pRateAdaptation->tspecsRateParameters[i].highRateThreshold) &&
1081 						(currentRateNumber < pRateAdaptation->tspecsRateParameters[i].highRateThreshold) )
1082 					{
1083 						tspecRateCross.uAC = i;
1084 						tspecRateCross.uHighOrLowThresholdFlag = HIGH_THRESHOLD_CROSS;
1085                         tspecRateCross.uAboveOrBelowFlag = CROSS_BELOW;
1086 						EvHandlerSendEvent(pRateAdaptation->hEvHandler, IPC_EVENT_TSPEC_RATE_STATUS, (UINT8 *)&tspecRateCross,sizeof(OS_802_11_THRESHOLD_CROSS_INDICATION_PARAMS));
1087 					}
1088                     else
1089 					if( (pRateAdaptation->RatesMap[prevIndex].rateNumber >= pRateAdaptation->tspecsRateParameters[i].lowRateThreshold) &&
1090 						(currentRateNumber < pRateAdaptation->tspecsRateParameters[i].lowRateThreshold) )
1091 					{
1092 						tspecRateCross.uAC = i;
1093 						tspecRateCross.uHighOrLowThresholdFlag = LOW_THRESHOLD_CROSS;
1094                         tspecRateCross.uAboveOrBelowFlag = CROSS_BELOW;
1095 						EvHandlerSendEvent(pRateAdaptation->hEvHandler, IPC_EVENT_TSPEC_RATE_STATUS, (UINT8 *)&tspecRateCross,sizeof(OS_802_11_THRESHOLD_CROSS_INDICATION_PARAMS));
1096 					}
1097                     else
1098 					if( (pRateAdaptation->RatesMap[prevIndex].rateNumber < pRateAdaptation->tspecsRateParameters[i].lowRateThreshold) &&
1099 						(currentRateNumber >= pRateAdaptation->tspecsRateParameters[i].lowRateThreshold) )
1100 					{
1101 						tspecRateCross.uAC = i;
1102 						tspecRateCross.uHighOrLowThresholdFlag = LOW_THRESHOLD_CROSS;
1103                         tspecRateCross.uAboveOrBelowFlag = CROSS_ABOVE;
1104 						EvHandlerSendEvent(pRateAdaptation->hEvHandler, IPC_EVENT_TSPEC_RATE_STATUS, (UINT8 *)&tspecRateCross,sizeof(OS_802_11_THRESHOLD_CROSS_INDICATION_PARAMS));
1105 					}
1106 
1107 				}
1108 			}
1109 
1110 		}
1111 
1112 		pRateAdaptation->txCount = 0;
1113 		pRateAdaptation->txFailCount = 0;
1114         pRateAdaptation->txRateFallBackCount = 0;
1115 		TS_ADVANCE( timeStamp, pRateAdaptation->expirTimeTick,
1116 			(pRateAdaptation->stepUpFlag ? pRateAdaptation->ctrlDataFBShortInterval : pRateAdaptation->ctrlDataFBLongInterval));
1117 
1118 	}
1119 
1120 	return OK;
1121 }
1122 
1123 /***************************************************************************
1124 *					rateAdaptation_setTspecsRateParams
1125 ****************************************************************************
1126 * DESCRIPTION:
1127 *
1128 * INPUTS:		pRateAdaptation - the object
1129 **
1130 * RETURNS:		OK/NOK
1131 ****************************************************************************/
1132 
rateAdaptation_setTspecsRateEvent(rateAdaptation_t * pRateAdaptation,UINT8 acID,BOOL enableEvent)1133 void rateAdaptation_setTspecsRateEvent(rateAdaptation_t* pRateAdaptation,
1134 											 UINT8			acID,
1135 											BOOL			enableEvent)
1136 {
1137 
1138    /* Prevent ENABLE_EVENTS if one of the threshold of that AC is ZERO */
1139   if (((pRateAdaptation->tspecsRateParameters[acID].highRateThreshold == 0) ||
1140 	 (pRateAdaptation->tspecsRateParameters[acID].lowRateThreshold == 0)) && (enableEvent == TRUE))
1141    return;
1142 
1143 	pRateAdaptation->tspecsRateParameters[acID].enableEvent = enableEvent;
1144 }
1145 
1146 /***************************************************************************
1147 *					rateAdaptation_setTspecsRateThresholds
1148 ****************************************************************************
1149 * DESCRIPTION:
1150 *
1151 * INPUTS:		pRateAdaptation - the object
1152 **
1153 * RETURNS:		OK/NOK
1154 ****************************************************************************/
1155 
rateAdaptation_setTspecsRateThresholds(rateAdaptation_t * pRateAdaptation,UINT8 acID,UINT8 highRateThreshold,UINT8 lowRateThreshold)1156 void rateAdaptation_setTspecsRateThresholds(rateAdaptation_t* pRateAdaptation,
1157 											 UINT8			acID,
1158 											 UINT8			highRateThreshold,
1159 											 UINT8			lowRateThreshold)
1160 {
1161 		if(highRateThreshold < lowRateThreshold)
1162 		{
1163 			WLAN_REPORT_ERROR(pRateAdaptation->hReport, RATE_ADAPTATION_MODULE_LOG,
1164 					(" rateAdaptation_setTspecsRateThresholds() ERROR: highRateThreshold < lowRateThreshold,  ac = %d\n",acID));
1165 
1166 			pRateAdaptation->tspecsRateParameters[acID].highRateThreshold = 0;
1167 			pRateAdaptation->tspecsRateParameters[acID].lowRateThreshold = 0;
1168 
1169 		}
1170 		else
1171 		{
1172 			pRateAdaptation->tspecsRateParameters[acID].highRateThreshold = highRateThreshold;
1173 			pRateAdaptation->tspecsRateParameters[acID].lowRateThreshold = lowRateThreshold;
1174 		}
1175 }
1176 
1177 
1178 /*************************************************************************
1179  *																		 *
1180  *							DEBUG FUNCTIONS								 *
1181  *																		 *
1182  *************************************************************************/
rateAdaptation_print(rateAdaptation_t * pRateAdaptation)1183 void rateAdaptation_print(rateAdaptation_t *pRateAdaptation)
1184 {
1185 	UINT32 count;
1186 
1187 	WLAN_OS_REPORT(("     Rate Adaptation Parameters    \n"));
1188 	WLAN_OS_REPORT(("-----------------------------------\n"));
1189 	WLAN_OS_REPORT(("txCount                   = %d\n",pRateAdaptation->txCount));
1190 	WLAN_OS_REPORT(("txFailCount               = %d\n",pRateAdaptation->txFailCount));
1191     WLAN_OS_REPORT(("txRateFallBackCount       = %d\n",pRateAdaptation->txRateFallBackCount));
1192 	WLAN_OS_REPORT(("txSkipCount               = %d\n",pRateAdaptation->txSkipCount));
1193 	WLAN_OS_REPORT(("currRateIndex             = %d\n",pRateAdaptation->currRateIndex));
1194 	WLAN_OS_REPORT(("currRate Number           = %d\n",pRateAdaptation->RatesMap[pRateAdaptation->currRateIndex].rateNumber));
1195 	WLAN_OS_REPORT(("maxRateIndex              = %d\n",pRateAdaptation->maxRateIndex));
1196 	WLAN_OS_REPORT(("maxRate Number            = %d\n",pRateAdaptation->RatesMap[pRateAdaptation->maxRateIndex].rateNumber));
1197 	WLAN_OS_REPORT(("stepUpFlag                = %d\n",pRateAdaptation->stepUpFlag));
1198 	WLAN_OS_REPORT(("expirTimeTick             = %d\n",pRateAdaptation->expirTimeTick));
1199 	WLAN_OS_REPORT(("stepUpTxPacketsThreshold  = %d\n",pRateAdaptation->stepUpTxPacketsThreshold));
1200 	WLAN_OS_REPORT(("contTxPacketsThreshold    = %d\n",pRateAdaptation->contTxPacketsThreshold));
1201 	WLAN_OS_REPORT(("ctrlDataFBShortInterval   = %d\n",pRateAdaptation->ctrlDataFBShortInterval));
1202 	WLAN_OS_REPORT(("ctrlDataFBLongInterval    = %d\n",pRateAdaptation->ctrlDataFBLongInterval));
1203 
1204 	WLAN_OS_REPORT(("    Rate Adaptation Table    \n"));
1205 	WLAN_OS_REPORT(("-----------------------------\n"));
1206 	for(count = 0 ; count <  MAX_SUPPORTED_RATES ; count++)
1207 	{
1208 		WLAN_OS_REPORT(("Index = %d ,RateNumber = %d,StepUp = %d ,FallBack = %d , Modulation = %d 4X = %d valid = %d,\n",
1209 									count,
1210 										  pRateAdaptation->RatesMap[count].rateNumber,
1211 										  pRateAdaptation->RatesMap[count].rateAdaptStepUp,
1212 										  pRateAdaptation->RatesMap[count].rateAdaptFallBack,
1213 										  pRateAdaptation->RatesMap[count].modulation,
1214 										  pRateAdaptation->RatesMap[count].fourXEnable,
1215 										  pRateAdaptation->RatesMap[count].valid));
1216 	}
1217 
1218 	WLAN_OS_REPORT(("Tspecs Rate Parameters AC = %d  \n",count));
1219 	WLAN_OS_REPORT(("-----------------------------\n"));
1220 	for(count = 0 ; count < MAX_NUM_OF_AC ; count++)
1221 	{
1222 		WLAN_OS_REPORT(("AC = %d  \n",count));
1223 		WLAN_OS_REPORT(("---------\n"));
1224 		WLAN_OS_REPORT(("enableEvent = %d  \n",pRateAdaptation->tspecsRateParameters[count].enableEvent));
1225 		WLAN_OS_REPORT(("highRateThreshold = %d  \n",pRateAdaptation->tspecsRateParameters[count].highRateThreshold));
1226 		WLAN_OS_REPORT(("lowRateThreshold = %d  \n",pRateAdaptation->tspecsRateParameters[count].lowRateThreshold));
1227 	}
1228 
1229 
1230 }
1231 
1232