Merge "O-DU High Architecture updated"
[o-du/l2.git] / src / 5gnrsch / rg_sch_utl.c
1 /*******************************************************************************
2 ################################################################################
3 #   Copyright (c) [2017-2019] [Radisys]                                        #
4 #                                                                              #
5 #   Licensed under the Apache License, Version 2.0 (the "License");            #
6 #   you may not use this file except in compliance with the License.           #
7 #   You may obtain a copy of the License at                                    #
8 #                                                                              #
9 #       http://www.apache.org/licenses/LICENSE-2.0                             #
10 #                                                                              #
11 #   Unless required by applicable law or agreed to in writing, software        #
12 #   distributed under the License is distributed on an "AS IS" BASIS,          #
13 #   WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.   #
14 #   See the License for the specific language governing permissions and        #
15 #   limitations under the License.                                             #
16 ################################################################################
17 *******************************************************************************/
18
19 /************************************************************************
20
21      Name:     LTE-MAC layer
22
23      Type:     C source file
24
25      Desc:     C source code for Entry point fucntions
26
27      File:     rg_sch_utl.c
28
29 **********************************************************************/
30
31 /** @file rg_sch_utl.c
32 @brief This file implements the schedulers main access to MAC layer code.
33 */
34
35 static const char* RLOG_MODULE_NAME="MAC";
36 static int RLOG_MODULE_ID=4096;
37 static int RLOG_FILE_ID=177;
38
39 /* header include files -- defines (.h) */
40 #include "common_def.h"
41 #include "lrg.h"
42 #include "rgr.h"
43 #include "tfu.h"
44 #include "rg_env.h"
45 #include "rg_sch_err.h"
46 #include "rg_sch_inf.h"
47 #include "rg_sch.h"
48 #include "rg_sch_cmn.h"
49 #include "rgm.h"
50 #include "rl_interface.h"
51 #include "rl_common.h"
52
53 /* header/extern include files (.x) */
54 #include "tfu.x"           /* TFU types */
55 #include "lrg.x"           /* layer management typedefs for MAC */
56 #include "rgr.x"           /* layer management typedefs for MAC */
57 #include "rgm.x"
58 #include "rg_sch_inf.x"         /* typedefs for Scheduler */
59 #include "rg_sch.x"        /* typedefs for Scheduler */
60 #include "rg_sch_cmn.x"        /* typedefs for Scheduler */
61 #ifdef EMTC_ENABLE
62 #include "rg_sch_emtc_ext.x"
63 #endif
64
65
66 /* SR_RACH_STATS */
67 uint32_t rgNumPrachRecvd =0;       /* Num of Rach Req received including dedicated preambles */
68 uint32_t rgNumRarSched =0;         /* Num of RARs sent */
69 uint32_t rgNumBI =0;               /* Num of BackOff Ind sent */
70 uint32_t rgNumMsg3CrcPassed =0;    /* Num of CRC success for Msg3 */
71 uint32_t rgNumMsg3CrcFailed =0;    /* Num of CRC fail for Msg 3 */
72 uint32_t rgNumMsg3FailMaxRetx =0;  /* Num of Msg3 fail after Max Retx attempts */
73 uint32_t rgNumMsg4Ack =0;          /* Num of Acks for Msg4 Tx */
74 uint32_t rgNumMsg4Nack =0; 
75        /* Num of Nacks for Msg4 Tx */
76 uint32_t rgNumMsg4FailMaxRetx =0;  /* Num of Msg4 Tx failed after Max Retx attempts */
77 uint32_t rgNumSrRecvd =0;          /* Num of Sched Req received */
78 uint32_t rgNumSrGrant =0;          /* Num of Sched Req Grants sent */
79 uint32_t rgNumMsg3CrntiCE =0;      /* Num of Msg 3 CRNTI CE received */
80 uint32_t rgNumDedPream =0;         /* Num of Dedicated Preambles recvd */
81 uint32_t rgNumMsg3CCCHSdu =0;      /* Num of Msg 3 CCCH Sdus recvd */
82 uint32_t rgNumCCCHSduCrntiNotFound =0;  /*UE Ctx not found for CCCH SDU Msg 3 */
83 uint32_t rgNumCrntiCeCrntiNotFound =0;  /*UE Ctx not found for CRNTI CE Msg 3 */
84 uint32_t rgNumMsg4WithCCCHSdu =0;       /* Num of Msg4 with CCCH Sdu */
85 uint32_t rgNumMsg4WoCCCHSdu =0;         /* Num of Msg4 without CCCH Sdu */
86 uint32_t rgNumMsg4Dtx =0;               /* Num of DTX received for Msg 4 */
87 uint32_t rgNumMsg3AckSent =0;           /* Num of PHICH Ack sent for Msg 3 */
88 uint32_t rgNumMsg3NackSent =0;          /* Num of PHICH Nack sent for Msg 3 */
89 uint32_t rgNumMsg4PdcchWithCrnti =0;    /* Num of PDCCH for CRNTI based contention resolution */
90 uint32_t rgNumRarFailDuetoRntiExhaustion =0; /* Num of RACH Failures due to RNTI pool exhaution */
91 uint32_t rgNumTAModified =0;            /* Num of times TA received is different from prev value */
92 uint32_t rgNumTASent =0;               /* Num of TA Command sent */
93 uint32_t rgNumMsg4ToBeTx =0;           /* Num of times MSG4 that should be sent */
94 uint32_t rgNumMsg4Txed =0;             /* Num of MSG4 actually sent *//* ysNumMsg4ToBeTx -ysNumMsg4Txed == Failed MSG4 TX */
95 uint32_t rgNumMsg3DtxRcvd  =0;         /* CRC Fail with SINR < 0 */
96
97 uint32_t rgNumDedPreamUECtxtFound =0;         /* Num of Dedicated Preambles recvd */
98
99 static uint8_t rgSchDciAmbigSizeTbl[61] = {0,0,0,0,0,0,0,0,0,0,0,
100                          0,1,0,1,0,1,0,0,0,1,
101                          0,0,0,1,0,1,0,0,0,0,
102                          0,1,0,0,0,0,0,0,0,1,
103                          0,0,0,1,0,0,0,0,0,0,
104                          0,0,0,0,0,1,0,0,0,0};
105
106 /* local defines */
107
108 uint32_t rgSchCmnBetaCqiOffstTbl[16];
109 uint32_t rgSchCmnBetaRiOffstTbl[16]; 
110 RgSchdApis rgSchCmnApis;
111 S16 RgUiRgmSendPrbRprtInd ARGS((
112 Pst* pst, 
113 SuId suId, 
114 RgmPrbRprtInd *prbRprtInd
115 ));
116
117 S16 RgUiRgmSendTmModeChangeInd ARGS((
118 Pst* pst, 
119 SuId suId, 
120 RgmTransModeInd *txModeChngInd
121 ));
122 #ifdef EMTC_ENABLE
123 S16 rgSCHEmtcUtlGetSfAlloc ARGS((
124 RgSchCellCb *cell
125 ));
126 S16 rgSCHEmtcUtlPutSfAlloc ARGS((
127 RgSchCellCb *cell
128 ));
129 Void rgSCHEmtcUtlUpdUeDciSize ARGS((
130 RgSchCellCb *cell,
131 RgSchUeCb *ueCb
132 ));
133 Void rgSCHEmtcGetDciFrmt61ASize ARGS((
134 RgSchCellCb *cell
135 ));
136 Void rgSCHEmtcGetDciFrmt60ASize ARGS((
137 RgSchCellCb *cell
138 ));
139 S16 rgSCHEmtcUtlFillPdschDciInfo ARGS((
140 TfuPdschDciInfo *pdsch,
141 TfuDciInfo      *pdcchDci
142 ));
143 Void rgSCHEmtcUtlRlsRnti ARGS((
144 RgSchCellCb *cell,
145 RgSchRntiLnk   *rntiLnk,
146 uint8_t             *isLegacy
147 ));
148 S16 rgSCHEmtcPdcchAlloc ARGS((
149 RgSchCellCb *cell,
150 RgSchPdcch  *pdcch
151 ));
152 Void rgSCHEmtcPdcchFree ARGS((
153 RgSchCellCb *cell,
154 RgSchPdcch  *pdcch
155 ));
156 #endif
157 /* Functions specific to TM1/TM2/TM6/TM7 for PRB calculation*/
158 Void rgSchUtlDlCalc1CwPrb ARGS(( RgSchCellCb    *cell,
159                                         RgSchUeCb      *ue,
160                                         uint32_t             bo,
161                                         uint32_t            *prbReqrd));
162
163 /* Functions specific to TM3/TM4 for PRB calculation*/
164 Void rgSchUtlDlCalc2CwPrb ARGS(( RgSchCellCb    *cell,
165                                         RgSchUeCb      *ue,
166                                         uint32_t             bo,
167                                         uint32_t            *prbReqrd));
168
169 #ifdef LTE_ADV
170 RgSchCellCb* rgSchUtlGetCellCb ARGS(( Inst       inst,
171                                              uint16_t        cellId
172 ));
173 #endif
174
175 typedef Void (*RgSchUtlDlCalcPrbFunc) ARGS((RgSchCellCb *cell, RgSchUeCb *ue,
176                                             uint32_t bo, uint32_t *prbRequrd));
177 #ifndef LTE_ADV
178 /* Functions specific to each transmission mode for PRB calculation*/
179 RgSchUtlDlCalcPrbFunc  dlCalcPrbFunc[7] = {rgSchUtlDlCalc1CwPrb,
180 rgSchUtlDlCalc1CwPrb, rgSchUtlDlCalc2CwPrb, rgSchUtlDlCalc2CwPrb,
181 NULLP, rgSchUtlDlCalc1CwPrb, rgSchUtlDlCalc1CwPrb};
182
183 #else
184 /* Functions specific to each transmission mode for PRB calculation*/
185 RgSchUtlDlCalcPrbFunc  dlCalcPrbFunc[9] = {rgSchUtlDlCalc1CwPrb,
186 rgSchUtlDlCalc1CwPrb, rgSchUtlDlCalc2CwPrb, rgSchUtlDlCalc2CwPrb,
187 NULLP, rgSchUtlDlCalc1CwPrb, rgSchUtlDlCalc1CwPrb, NULLP, NULLP};
188
189 #endif
190
191 #ifdef LTE_TDD
192 /* The below table will be used to map the UL SF number in a TDD Cfg 0 
193    frame to the ul Sf array maintained in cellCb */
194 static uint8_t  rgSchTddCfg0UlSfTbl[] = {2, 3, 4, 7, 8, 9};
195 #endif
196
197 static S16 rgSCHUtlUlAllocDbInit ARGS((
198          RgSchCellCb    *cell,
199          RgSchUlAllocDb *db,
200          uint8_t maxAllocs
201          ));
202 static Void rgSCHUtlUlAllocDbDeinit ARGS((
203          RgSchCellCb    *cell,
204          RgSchUlAllocDb *db
205          ));
206 static S16 rgSCHUtlUlHoleDbInit ARGS((
207          RgSchCellCb    *cell,
208          RgSchUlHoleDb *db,
209          uint8_t maxHoles,
210          uint8_t start,
211          uint8_t num
212          ));
213 static Void rgSCHUtlUlHoleDbDeinit ARGS((
214          RgSchCellCb   *cell,
215          RgSchUlHoleDb *db
216          ));
217
218 static S16 rgSCHChkBoUpdate ARGS((
219          RgSchCellCb    *cell,
220          RgInfCmnBoRpt  *boUpdt
221          ));
222 #ifdef UNUSE_FUN
223 #ifdef TFU_UPGRADE
224 static uint8_t rgSCHUtlFetchPcqiBitSz ARGS((
225  RgSchCellCb    *cell,
226  RgSchUeCb      *ueCb, 
227  uint8_t        numTxAnt
228  ));
229 #endif
230 #endif
231 /* sorted in ascending order of tbSz */
232 const struct rgSchUtlBcchPcchTbSz
233 {
234    uint8_t   rbIndex;    /* RB index {2,3} */
235    uint16_t  tbSz;       /* one of the Transport block size in bits of
236                      * rbIndex 2 or 3 */
237    /* Corrected allocation for common channels */
238    uint8_t   mcs;        /* imcs */
239 } rgSchUtlBcchPcchTbSzTbl[44] = {
240    { 2,   32,  0 }, { 2,   56,  1 }, { 2,   72,  2 }, { 3,   88,  1 },
241    { 2,  104,  3 }, { 2,  120,  4 }, { 2,  144,  5 }, { 2,  176,  6 },
242    { 3,  208,  4 }, { 2,  224,  7 }, { 2,  256,  8 }, { 2,  296,  9 },
243    { 2,  328, 10 }, { 2,  376, 11 }, { 3,  392,  8 }, { 2,  440, 12 },
244    { 3,  456,  9 }, { 2,  488, 13 }, { 3,  504, 10 }, { 2,  552, 14 },
245    { 3,  584, 11 }, { 2,  600, 15 }, { 2,  632, 16 }, { 3,  680, 12 },
246    { 2,  696, 17 }, { 3,  744, 13 }, { 2,  776, 18 }, { 2,  840, 19 },
247    { 2,  904, 20 }, { 3,  968, 16 }, { 2, 1000, 21 }, { 2, 1064, 22 },
248    { 2, 1128, 23 }, { 3, 1160, 18 }, { 2, 1192, 24 }, { 2, 1256, 25 },
249    { 3, 1288, 19 }, { 3, 1384, 20 }, { 2, 1480, 26 }, { 3, 1608, 22 },
250    { 3, 1736, 23 }, { 3, 1800, 24 }, { 3, 1864, 25 }, { 3, 2216, 26 }
251 };
252
253 /* local typedefs */
254
255 /* local externs */
256
257 /* forward references */
258 #ifdef LTE_TDD
259 static Void rgSCHUtlUpdPrachOcc ARGS((
260 RgSchCellCb *cell,
261 RgrTddPrachInfo *cellCfg));
262 #endif
263
264 #define RGSCH_NUM_PCFICH_REG 4
265 #define RGSCH_NUM_REG_PER_CCE 9
266 #define RGSCH_NUM_REG_PER_PHICH_GRP 3
267
268 #ifdef LTE_TDD
269 #define RGSCH_INITPHICH(_phich, _hqFeedBack, _nDmrs, _rbStart, _iPhich) {\
270    (_phich)->hqFeedBack = _hqFeedBack; \
271    (_phich)->rbStart = _rbStart; \
272    (_phich)->nDmrs = _nDmrs; \
273    (_phich)->iPhich = _iPhich; \
274    (_phich)->lnk.next = NULLP; \
275    (_phich)->lnk.prev = NULLP; \
276    (_phich)->lnk.node = (PTR)(_phich); \
277 }
278 #else
279 #define RGSCH_INITPHICH(_phich, _hqFeedBack, _nDmrs, _rbStart, _isForMsg3) {\
280    (_phich)->hqFeedBack = _hqFeedBack; \
281    (_phich)->rbStart = _rbStart; \
282    (_phich)->nDmrs = _nDmrs; \
283    (_phich)->isForMsg3 = _isForMsg3; \
284    (_phich)->lnk.next = NULLP; \
285    (_phich)->lnk.prev = NULLP; \
286    (_phich)->lnk.node = (PTR)(_phich); \
287 }
288 #endif
289
290 #define RGSCH_PHICH_ALLOC(_inst,_dataPtr, _size, _ret) {\
291    _ret = rgSCHUtlAllocSBuf(_inst, (Data **)&_dataPtr, _size); \
292 }
293
294 /* ccpu00117052 - MOD - Passing double pointer
295 for proper NULLP assignment*/
296 #define RGSCH_PHICH_FREE(_inst, _dataPtr, _size) {\
297       rgSCHUtlFreeSBuf(_inst, (Data **)(&(_dataPtr)), _size); \
298 }
299
300 #ifdef TFU_UPGRADE
301 #define RGSCH_GETBIT(a, b)     ((((uint8_t*)a)[(b)>>3] >> ((7-((b)&7)))) & 1)
302
303 /*
304 *
305 *       Fun:   rgSCHUtlPower
306 *
307 *       Desc:  This function finds of the Power of x raised to n
308 *
309 *       Ret:   value of x raised to n
310 *
311 *       Notes: None
312 *
313 *       File:  rg_sch_utl.c
314 *
315 */
316 #ifdef ANSI
317 F64 rgSCHUtlPower
318 (
319 F64    x,
320 F64    n
321 )
322 #else
323 F64 rgSCHUtlPower(x, n)
324 F64    x;
325 F64    n;
326 #endif
327 {
328  if( n==0 )
329  {
330    return ( 1 );
331  }
332  else if ( n>0 )
333  {
334    return ( x * rgSCHUtlPower( x, n-1 ) );
335  }
336  else
337  {
338    return ( (1/x) * rgSCHUtlPower( x, n+1 ) );
339  }
340 } /* end of rgSCHUtlPower*/
341
342 /*
343 *
344 *       Fun:   rgSCHUtlParse
345 *
346 *       Desc:  This function parses bits x to y of an array and
347 *                  returns the integer value  out of it.
348 *
349 *       Ret:   integer value of z bits
350 *
351 *       Notes: None
352 *
353 *       File:  rg_sch_utl.c
354 *
355 */
356 #ifdef ANSI
357 uint32_t rgSCHUtlParse
358 (
359 uint8_t     *buff,
360 uint8_t     startPos,
361 uint8_t     endPos,
362 uint8_t     buffSize
363 )
364 #else
365 uint32_t rgSCHUtlParse(buff, startPos, endPos, buffSize)
366 uint8_t     *buff;
367 uint8_t     startPos;
368 uint8_t     endPos;
369 uint8_t     buffSize;
370 #endif
371 {
372  uint8_t pointToChar,pointToEnd, loop;
373  uint8_t size =  endPos - startPos;
374  F64 result = 0;
375  pointToEnd = (startPos)%8;
376    for ( loop=0; loop<size; loop++)
377    {
378       pointToChar = (((startPos)+loop)/8);
379       if (RGSCH_GETBIT(buff+pointToChar,pointToEnd%8)==1)
380       {
381          result=result+(rgSCHUtlPower(2,(size-loop-1)));
382       }
383       pointToEnd++;
384    }
385    return ((uint32_t)result);
386 } /* end of rgSCHUtlParse*/
387
388 /*
389 *
390 *       Fun:   rgSCHUtlFindDist
391 *
392 *       Desc:  This function calculates the iterations need to cover
393 *                  before the valid Index can be used for next possible Reception
394 *
395 *       Ret:   integer value of z bits
396 *
397 *       Notes: None
398 *
399 *       File:  rg_sch_utl.c
400 *
401 */
402 #ifdef ANSI
403 uint8_t rgSCHUtlFindDist
404 (
405 uint16_t    crntTime,
406 uint16_t    tempIdx
407 )
408 #else
409 uint8_t rgSCHUtlFindDist(crntTime, tempIdx)
410 uint16_t    crntTime;
411 uint16_t    tempIdx;
412 #endif
413 {
414  uint8_t  dist =0;
415  /* ccpu00137113- Distance is not estimated properly if the periodicity is 
416   * equal to RG_SCH_PCQI_SRS_SR_TRINS_SIZE.
417   */
418  while(crntTime<=tempIdx)
419  {
420     crntTime += RG_SCH_PCQI_SRS_SR_TRINS_SIZE;
421     dist+=1;
422  }
423  return (dist-1);
424 } /* end of rgSCHUtlFindDist*/
425 #endif
426
427 \f
428 /**
429  * @brief This function checks availability of a PDCCH
430  *
431  * @details
432  *
433  *     Function: rgSCHUtlPdcchAvail
434  *     Purpose:  This function checks if a particular PDCCH is in use.
435  *               map field of PDCCH is used to track the CCEs arleady
436  *               allocated. Each bit of map represents one CCE and the
437  *               LSBit of first byte represents CCE 0.
438  *               steps:
439  *               1. Locate the set of bits that represent the PDCCH for
440  *               the provided location.
441  *               2.  If the value of the bits is non-zero one or many CCEs
442  *               for the PDCCH are in use and hence the PDCCH is not available.
443  *               3. If pdcch is available, assign it to [out]pdcch.
444  *               4.  Set all of the bits to one. There is no check performed
445  *               to see if the PDCCH is available.
446  *
447  *     Invoked by: scheduler
448  *
449  *  @param[in]  RgSchCellCb*     cell
450  *  @param[in]  RgSchPdcchInfo*  pdcchInfo
451  *  @param[in]  uint8_t            loc
452  *  @param[in]  uint8_t            aggrLvl
453  *  @param[out] RgSchPdcch**     pdcch
454  *  @return  Boolean
455  *         -#   TRUE  if available
456  *         -#   FALSE otherwise
457  *
458  **/
459 #ifdef ANSI
460 Bool rgSCHUtlPdcchAvail
461 (
462 RgSchCellCb             *cell,
463 RgSchPdcchInfo          *pdcchInfo,
464 CmLteAggrLvl            aggrLvl,
465 RgSchPdcch              **pdcch
466 )
467 #else
468 Bool rgSCHUtlPdcchAvail(cell, pdcchInfo, aggrLvl, pdcch)
469 RgSchCellCb             *cell;
470 RgSchPdcchInfo          *pdcchInfo;
471 CmLteAggrLvl            aggrLvl;
472 RgSchPdcch              **pdcch;
473 #endif
474 {
475    uint8_t             *byte;
476    uint16_t             offset;
477    uint16_t             initMask;
478    uint16_t             currMask;
479    Inst                 inst = cell->instIdx;
480    S16                  ret;
481    uint16_t             offsetStepMask;
482
483    /* V5G_213 : 10.1 */
484         offset = 0;
485         byte = &pdcchInfo->map[0];
486         initMask = (0xffff >> (16 - aggrLvl));
487         currMask = initMask;
488         /* if N(symbol, xPDCCH) =2, then xPDCCH will be candidates in 
489           * search space of index {0,1,2,3} and {8,9,..14}
490           */
491         if ((cell->cell5gtfCb.cfi == 2) && (aggrLvl == CM_LTE_AGGR_LVL2))
492         {
493                 offsetStepMask = 0xc;
494         }
495         else
496         {
497                 offsetStepMask = 0xc0;
498         }
499
500         /* Loop till the number of bytes available in the CCE map */
501         while (offset < ((pdcchInfo->nCce+ 7) >> 3))
502         {
503            byte = &pdcchInfo->map[offset];
504                 /* Checking for available CCE */
505                 if ((*byte & currMask) == 0)
506            {
507               break;
508            }
509                 /* if the number of CCEs required are not available, move to next offset */
510                 if (currMask & offsetStepMask)
511                 {
512                         offset++;
513                         currMask = initMask;
514                 }
515                 else
516                 {
517                    /* Move to the next available CCE index in the current byte(cce map) */
518                         currMask = currMask << aggrLvl;
519                 }
520         }
521
522         if ((offset >= ((pdcchInfo->nCce + 7) >> 3)) || 
523                   ((aggrLvl == CM_LTE_AGGR_LVL16) && (offset > 0)))
524         {
525                 return (FALSE);
526         }
527
528         byte = &pdcchInfo->map[offset];
529    
530    if (cell->pdcchLst.first != NULLP)
531    {
532       *pdcch = (RgSchPdcch *)(cell->pdcchLst.first->node);
533       cmLListDelFrm(&cell->pdcchLst, cell->pdcchLst.first);
534    }
535    else
536    {
537       ret = rgSCHUtlAllocSBuf(inst, (Data **)pdcch, sizeof(RgSchPdcch));
538       if(ROK != ret)
539       {
540          return (FALSE);
541       }
542    }
543
544    if (*pdcch)
545    {
546       (*byte) |= currMask;
547                 /* ALL CCEs will be used in case of level 16 */
548                 if (aggrLvl == CM_LTE_AGGR_LVL16)
549                 {
550                         *(byte+1) |= currMask;
551                 }
552       (*pdcch)->aggrLvl = aggrLvl;
553       cmLListAdd2Tail(&pdcchInfo->pdcchs, &((*pdcch)->lnk));
554       (*pdcch)->lnk.node = (PTR)*pdcch;
555       (*pdcch)->nCce = aggrLvl;
556       (*pdcch)->ue = NULLP;
557    }
558    return (TRUE);
559 }
560
561
562 \f
563 /**
564  * @brief This function releases a PDCCH
565  *
566  * @details
567  *
568  *     Function: rgSCHUtlPdcchPut
569  *     Purpose:  This function releases a PDCCH.
570  *               steps:
571  *               1. Locate the set of bits that represent the PDCCH for
572  *               the provided location.
573  *               2. Set all of the bits to zero.
574  *               3. Release the memory of PDCCH to the cell free Q
575  *
576  *     Invoked by: scheduler
577  *
578  *  @param[in]  RgSchPdcchInfo*  pdcchInfo
579  *  @param[in]  uint8_t            loc
580  *  @param[in]  uint8_t            aggrLvl
581  *  @return     Void
582  *
583  **/
584 #ifdef ANSI
585 Void rgSCHUtlPdcchPut
586 (
587 RgSchCellCb                *cell,
588 RgSchPdcchInfo             *pdcchInfo,
589 RgSchPdcch                 *pdcch
590 )
591 #else
592 Void rgSCHUtlPdcchPut(cell, pdcchInfo, pdcch)
593 RgSchCellCb                *cell;
594 RgSchPdcchInfo             *pdcchInfo;
595 RgSchPdcch                 *pdcch;
596 #endif
597 {
598    uint8_t              *byte;
599    uint8_t              offset;
600    uint16_t             mask;
601
602    switch(pdcch->aggrLvl)
603    {
604       case CM_LTE_AGGR_LVL2:
605          offset = (pdcch->nCce >> 1) & 3;
606          mask = 0x3 << (offset * 2); /*ccpu00128826 - Offset Correction */
607          break;
608       case CM_LTE_AGGR_LVL4:
609          offset = (pdcch->nCce >> 2) & 1;
610          mask = 0xf << (offset * 4);/*ccpu00128826 - Offset Correction */
611          break;
612       case CM_LTE_AGGR_LVL8:
613          mask = 0xff;
614          break;
615                 case CM_LTE_AGGR_LVL16:
616          mask = 0xffff;
617          break;
618       default:
619          return;
620    }
621    /* Placing common computation of byte from all the cases above here
622       for optimization */
623    byte = &pdcchInfo->map[pdcch->nCce >> 3];
624
625    cmLListDelFrm(&pdcchInfo->pdcchs, &pdcch->lnk);
626    cmLListAdd2Tail(&cell->pdcchLst, &pdcch->lnk);
627    pdcch->lnk.node = (PTR)pdcch;
628    pdcch->ue = NULLP;
629    (*byte) &= ~mask;
630
631   return;
632 }
633
634 \f
635 /**
636  * @brief This function initializes PDCCH information for frame
637  *
638  * @details
639  *
640  *     Function: rgSCHUtlPdcchInit
641  *     Purpose:  This function initializes PDCCH information for
642  *               a slot. It removes the list of PDCCHs allocated
643  *               in the prior use of this slot structure.
644  *
645  *     Invoked by: rgSCHUtlSubFrmPut
646  *
647  *  @param[in]  RgSchCellCb*     cell
648  *  @param[in]  RgSubFrm*     subFrm
649  *  @return  Void
650  *
651  **/
652 #ifdef ANSI
653 Void rgSCHUtlPdcchInit
654 (
655 RgSchCellCb             *cell,
656 RgSchDlSf               *subFrm,
657 uint16_t                nCce
658 )
659 #else
660 Void rgSCHUtlPdcchInit(cell, subFrm, nCce)
661 RgSchCellCb             *cell;
662 RgSchDlSf               *subFrm;
663 uint16_t                nCce;
664 #endif
665 {
666    RgSchPdcchInfo       *pdcchInfo;
667    RgSchPdcch           *pdcch;
668    Inst                 inst = cell->instIdx;
669    uint8_t              extraBits;
670    uint32_t             cceMapSz;
671
672    pdcchInfo = &subFrm->pdcchInfo;
673    while(pdcchInfo->pdcchs.first != NULLP)
674    {
675       pdcch = (RgSchPdcch *)pdcchInfo->pdcchs.first->node;
676       cmLListDelFrm(&pdcchInfo->pdcchs, pdcchInfo->pdcchs.first);
677       cmLListAdd2Tail(&cell->pdcchLst, &pdcch->lnk);
678       pdcch->ue = NULLP;
679    }
680    cmLListInit(&pdcchInfo->pdcchs);
681    
682 #ifdef LTEMAC_SPS
683    subFrm->relPdcch = NULLP;
684 #endif
685    
686    cceMapSz = ((pdcchInfo->nCce + 7) >> 3);
687
688         /* The bitMap array size is the number of ceiling(CCEs/8) */
689         /* If nCce received is not the same as the one stored in    
690         * pdcchInfo, free the pdcchInfo map                      */
691
692    if(pdcchInfo->nCce != nCce)
693    {
694       if(pdcchInfo->nCce)
695       {
696         rgSCHUtlFreeSBuf(inst, (Data **)(&(pdcchInfo->map)), cceMapSz);
697       }
698       pdcchInfo->nCce = nCce;
699       cceMapSz = ((pdcchInfo->nCce + 7) >> 3);
700       rgSCHUtlAllocSBuf(inst, (Data **)&pdcchInfo->map,  
701       cceMapSz);
702       if (pdcchInfo->map == NULLP)
703       {
704          /* Generate log error here */
705          return;
706       }    
707    }
708
709    memset(subFrm->pdcchInfo.map, 0, cceMapSz);
710    /*   If nCce is not exactly same as the bitMap size(no of bits allocated
711         * to represent the Cce's, then mark the extra bits as unavailable
712         extra bits = (((pdcchInfo->nCce + 7) >> 3)*8) - pdcchInfo->nCce
713         The last byte of bit map = subFrm->pdcchInfo.map[((pdcchInfo->nCce + 7) >> 3) - 1]
714          NOTE : extra bits are most significant of the last byte eg.  */
715    extraBits = (cceMapSz)*8 - pdcchInfo->nCce;
716    subFrm->pdcchInfo.map[cceMapSz - 1] |=
717      ((1 << extraBits) - 1) << (8 - extraBits);
718    return;
719 }
720
721 /* LTE_ADV_FLAG_REMOVED_START */
722 /**
723  * @brief This function frees Pool
724  * @details
725  *
726  *     Function: rgSchSFRTotalPoolFree
727  *
728  *     Invoked by: rgSchSFRTotalPoolInit
729  *
730  *  @param[in]  RgSchCellCb*     cell
731  *  @param[in]  RgSubFrm*     subFrm
732  *  @return  Void
733  *
734  **/
735 #ifdef ANSI
736 Void rgSchSFRTotalPoolFree
737 (
738  RgSchSFRTotalPoolInfo  *sfrTotalPoolInfo,
739  RgSchCellCb             *cell
740  )
741 #else
742 Void rgSchSFRTotalPoolFree(sfrTotalPoolInfo, cell)
743    RgSchSFRTotalPoolInfo  *sfrTotalPoolInfo;
744    RgSchCellCb             *cell;
745 #endif
746 {
747    CmLListCp   *l;
748    CmLList     *n;
749
750    /*Deinitialise if  these cc pools and ce pools are already existent*/
751    l = &sfrTotalPoolInfo->ccPool;
752    n = cmLListFirst(l);
753    while (n != NULL)
754    {
755       /*REMOVING Cell Centred POOLS IF ANY*/
756       n = cmLListDelFrm(l, n);
757
758       /* Deallocate buffer */
759       rgSCHUtlFreeSBuf(cell->instIdx, (Data **)(&(n->node)), sizeof(RgSchSFRPoolInfo));
760
761       /* Deallocate buffer */
762       rgSCHUtlFreeSBuf(cell->instIdx, (Data **)(&(n)), sizeof(CmLList));   
763       n = cmLListNext(l);
764    }
765
766    /*REMOVING Cell Edged POOLS IF ANY*/
767    l = &sfrTotalPoolInfo->cePool;
768    n = cmLListFirst(l);
769    while (n != NULL)
770    {
771       n = cmLListDelFrm(l, n);
772
773       /* Deallocate buffer */
774       rgSCHUtlFreeSBuf(cell->instIdx, (Data **)(&(n->node)), sizeof(RgSchSFRPoolInfo));
775
776       /* Deallocate buffer */
777       rgSCHUtlFreeSBuf(cell->instIdx, (Data **)(&(n)), sizeof(CmLList));   
778       n = cmLListNext(l);
779    } 
780
781 }
782
783 /**
784  * @brief This function resets temporary variables in Pool
785  * @details
786  *
787  *     Function: rgSchSFRResetPoolVariables
788  *
789  *     Invoked by: rgSCHSFRUtlTotalPoolInit
790  *
791  *  @param[in]  RgSchCellCb*     cell
792  *  @param[in]  RgSubFrm*     subFrm
793  *  @return  Void
794  *
795  **/
796 #ifdef ANSI
797 S16 rgSchSFRTotalPoolInit
798 (
799  RgSchCellCb             *cell,
800  RgSchDlSf               *sf
801  )
802 #else
803 static Void rgSchSFRTotalPoolInit(cell, sf)
804    RgSchCellCb             *cell;
805    RgSchDlSf               *sf;
806 #endif
807 {      
808    /*  Initialise the variables */
809    RgSchSFRPoolInfo *sfrCCPool;
810    RgSchSFRPoolInfo *sfrCEPool;
811    CmLListCp   *l;
812    CmLList     *n;
813    CmLList *temp = NULLP;
814    S16 ret = 0;
815
816    rgSchSFRTotalPoolFree(&sf->sfrTotalPoolInfo, cell);  
817    sf->sfrTotalPoolInfo.CCPool1BwAvlbl          = 0;
818    sf->sfrTotalPoolInfo.CCPool2BwAvlbl          = 0;
819    sf->sfrTotalPoolInfo.CEPoolBwAvlbl           = 0;
820    sf->sfrTotalPoolInfo.CC1                     = FALSE;
821    sf->sfrTotalPoolInfo.CC2                     = FALSE;
822    /*Initialise the CE Pools*/
823    cmLListInit (&(sf->sfrTotalPoolInfo.cePool));
824
825    ret = rgSCHUtlAllocSBuf(cell->instIdx, (Data **)&temp, sizeof(CmLList));
826    if (ret != ROK)
827    {
828       RLOG_ARG0(L_ERROR,DBG_CELLID,cell->cellId,
829                       "CE Pool memory allocation FAILED for cell");       
830       rgSchSFRTotalPoolFree(&sf->sfrTotalPoolInfo, cell);
831       return RFAILED;
832    }
833
834    ret = rgSCHUtlAllocSBuf(cell->instIdx, (Data **)&temp->node, sizeof(RgSchSFRPoolInfo));
835    if (ret != ROK)
836    {
837       RLOG_ARG0(L_ERROR,DBG_CELLID,cell->cellId,
838                       "CE Pool memory allocation FAILED for cell ");       
839       rgSchSFRTotalPoolFree(&sf->sfrTotalPoolInfo,cell);
840       return RFAILED;
841    }
842
843    l = &sf->sfrTotalPoolInfo.cePool;
844    cmLListAdd2Tail(l, temp);
845
846    /*Initialise Bandwidth and startRB and endRB for each pool*/
847    n = cmLListFirst(l);
848
849    /* Initialise the CE Pools */
850    sfrCEPool = (RgSchSFRPoolInfo*)n->node;
851
852    sfrCEPool->poolstartRB             = cell->lteAdvCb.sfrCfg.cellEdgeRbRange.startRb;
853    sfrCEPool->poolendRB               = cell->lteAdvCb.sfrCfg.cellEdgeRbRange.endRb;
854    sfrCEPool->bw                      = sfrCEPool->poolendRB - sfrCEPool->poolstartRB + 1;
855    sf->sfrTotalPoolInfo.CEPoolBwAvlbl = sfrCEPool->bw;
856
857    sfrCEPool->bwAlloced               = 0;
858    sfrCEPool->type2Start              = sfrCEPool->poolstartRB;
859    sfrCEPool->type2End                = RGSCH_CEIL(sfrCEPool->poolstartRB, cell->rbgSize);   
860    sfrCEPool->type0End                = ((sfrCEPool->poolendRB + 1) / cell->rbgSize) - 1;
861    sfrCEPool->pwrHiCCRange.startRb    = 0;
862    sfrCEPool->pwrHiCCRange.endRb      = 0;
863
864    /*Initialise CC Pool*/
865    cmLListInit (&(sf->sfrTotalPoolInfo.ccPool));
866
867    /*Add memory and Update CCPool*/
868    ret = rgSCHUtlAllocSBuf(cell->instIdx, (Data **)&temp, sizeof(CmLList));
869    if (ret != ROK)
870    {
871       RLOG_ARG0(L_ERROR,DBG_CELLID,cell->cellId,
872                       "CC Pool memory allocation FAILED for cell ");       
873       rgSchSFRTotalPoolFree(&sf->sfrTotalPoolInfo,cell);
874       return RFAILED;
875    }
876
877    ret = rgSCHUtlAllocSBuf(cell->instIdx, (Data **)&temp->node, sizeof(RgSchSFRPoolInfo));
878    if (ret != ROK)
879    {
880       RLOG_ARG0(L_ERROR,DBG_CELLID,cell->cellId,
881                       "CC Pool memory allocation FAILED for cell ");       
882       rgSchSFRTotalPoolFree(&sf->sfrTotalPoolInfo,cell);
883       return RFAILED;
884    }
885
886    l = &sf->sfrTotalPoolInfo.ccPool;
887    cmLListAdd2Tail(l, temp);
888
889    /*Initialise Bandwidth and startRB and endRB for each pool*/
890    if(sfrCEPool->poolstartRB)
891    {
892       n = cmLListFirst(l);
893       sfrCCPool = (RgSchSFRPoolInfo*)n->node;
894
895       sfrCCPool->poolstartRB              = 0;
896       sfrCCPool->poolendRB                = sfrCEPool->poolstartRB - 1;
897       sfrCCPool->bw                       = sfrCCPool->poolendRB - sfrCCPool->poolstartRB + 1;
898       sf->sfrTotalPoolInfo.CCPool1BwAvlbl = sfrCCPool->bw;
899       sfrCCPool->bwAlloced                = 0;
900       sfrCCPool->type2Start               = 0;
901       sfrCCPool->type2End                 = 0;
902       sfrCCPool->type0End                 = ((sfrCCPool->poolendRB + 1) / cell->rbgSize) - 1;
903       sf->sfrTotalPoolInfo.CC1            = TRUE;
904       sfrCCPool->pwrHiCCRange.startRb     = 0;
905       sfrCCPool->pwrHiCCRange.endRb       = 0;
906    }
907    else
908    {
909       n = cmLListFirst(l);
910       sfrCCPool = (RgSchSFRPoolInfo*)n->node;
911
912       sfrCCPool->poolstartRB              = sfrCEPool->poolendRB + 1;
913       sfrCCPool->poolendRB                = sf->bw - 1;
914       sfrCCPool->bw                       = sfrCCPool->poolendRB - sfrCCPool->poolstartRB + 1;
915       sf->sfrTotalPoolInfo.CCPool2BwAvlbl = sfrCCPool->bw;
916       sfrCCPool->CCPool2Exists            = TRUE;
917       sfrCCPool->bwAlloced                = 0;
918       sfrCCPool->type2Start               = sfrCCPool->poolstartRB;
919       sfrCCPool->type2End                 = RGSCH_CEIL(sfrCCPool->poolstartRB, cell->rbgSize);
920       sfrCCPool->type0End                 = ((sfrCCPool->poolendRB + 1) / cell->rbgSize) - 1;
921       sf->sfrTotalPoolInfo.CC2            = TRUE;
922       sfrCEPool->adjCCPool                = sfrCCPool; /* SFR_FIX */
923       sfrCCPool->pwrHiCCRange.startRb     = 0;
924       sfrCCPool->pwrHiCCRange.endRb       = 0;
925    }
926
927    if((sfrCEPool->poolendRB != sf->bw - 1) && (!sfrCCPool->poolstartRB))
928    {    
929       /*Add memory and Update CCPool*/
930       ret = rgSCHUtlAllocSBuf(cell->instIdx, (Data **)&temp, sizeof(CmLList));
931       if (ret != ROK)
932       {
933          RLOG_ARG0(L_ERROR,DBG_CELLID,cell->cellId,
934                          "CC Pool memory allocation FAILED for cell ");       
935          rgSchSFRTotalPoolFree(&sf->sfrTotalPoolInfo,cell);
936          return RFAILED;
937       }
938
939       ret = rgSCHUtlAllocSBuf(cell->instIdx, (Data **)&temp->node, sizeof(RgSchSFRPoolInfo));
940       if (ret != ROK)
941       {
942          RLOG_ARG0(L_ERROR,DBG_CELLID,cell->cellId,
943                          "CC Pool memory allocation FAILED for cell ");       
944          rgSchSFRTotalPoolFree(&sf->sfrTotalPoolInfo,cell);
945          return RFAILED;
946       }
947
948       cmLListAdd2Tail(l, temp);
949
950       n = cmLListCrnt(l);
951       sfrCCPool = (RgSchSFRPoolInfo*)n->node;
952
953       sfrCCPool->poolstartRB              = sfrCEPool->poolendRB + 1;
954       sfrCCPool->poolendRB                = sf->bw - 1;
955       sfrCCPool->bw                       = sfrCCPool->poolendRB - sfrCCPool->poolstartRB + 1;
956       sf->sfrTotalPoolInfo.CCPool2BwAvlbl = sfrCCPool->bw;
957       sfrCCPool->CCPool2Exists            = TRUE;
958       sfrCCPool->bwAlloced                = 0;
959       sfrCCPool->type2Start               = sfrCCPool->poolstartRB;      
960       sfrCCPool->type2End                 = RGSCH_CEIL(sfrCCPool->poolstartRB, cell->rbgSize);
961       sfrCCPool->type0End                 = ((sfrCCPool->poolendRB + 1) / cell->rbgSize) - 1;
962       sf->sfrTotalPoolInfo.CC2            = TRUE;
963       sfrCEPool->adjCCPool                = sfrCCPool; /* SFR_FIX */
964       sfrCCPool->pwrHiCCRange.startRb     = 0;
965       sfrCCPool->pwrHiCCRange.endRb       = 0;
966    }   
967
968    sf->sfrTotalPoolInfo.CCRetx            = FALSE;
969    sf->sfrTotalPoolInfo.CERetx            = FALSE;
970
971    sf->sfrTotalPoolInfo.ccBwFull          = FALSE;
972    sf->sfrTotalPoolInfo.ceBwFull          = FALSE;
973    sf->sfrTotalPoolInfo.isUeCellEdge      = FALSE;
974    return ROK;
975 }
976 /**
977  * @brief This function resets temporary variables in RNTP Prepration
978  * @details
979  *
980  *     Function:   rgSchDSFRRntpInfoInit 
981  *
982  *     Invoked by: rgSCHSFRUtlTotalPoolInit
983  *
984  *  @param[in]  TknStrOSXL*     rntpPtr
985  *  @param[in]  RgSubFrm*        subFrm
986  *  @return  S16
987  *
988  **/
989 #ifdef ANSI
990 S16   rgSchDSFRRntpInfoInit 
991 (
992  TknStrOSXL              *rntpPtr,
993  RgSchCellCb             *cell,
994  uint16_t                bw
995  )
996 #else
997 static Void rgSchDSFRRntpInfoInit(rntpPtr, cell, bw)
998    TknStrOSXL              *rntpPtr;
999    RgSchCellCb             *cell;
1000    uint16_t                bw;
1001 #endif
1002 {   
1003    Inst inst = cell->instIdx;
1004    uint16_t len;
1005
1006    rntpPtr->pres = PRSNT_NODEF;
1007
1008    len = (bw % 8 == 0) ? (bw/8) : (bw/8 + 1);
1009
1010    rntpPtr->len  = len;   
1011
1012    /* Allocate memory for "scheduled UE" Info */
1013    if((rgSCHUtlAllocSBuf(inst, (Data**)&(rntpPtr->val),
1014                (len * sizeof(uint8_t)))) != ROK)
1015    {
1016       RLOG_ARG0(L_ERROR,DBG_CELLID,cell->cellId,"Memory allocation FAILED for RNTP Alloc");
1017       return RFAILED;
1018    }
1019
1020    return ROK;
1021 }
1022
1023 /**
1024  * @brief This function release RNTP pattern from slot and Cell 
1025  * @details
1026  *
1027  *     Function:   rgSchDSFRRntpInfoFree 
1028  *
1029  *     Invoked by: rgSCHSFRUtlTotalPoolInit
1030  *
1031  *  @param[in]  TknStrOSXL*     rntpPtr
1032  *  @param[in]  RgSubFrm*        subFrm
1033  *  @return  S16
1034  *
1035  **/
1036 #ifdef ANSI
1037 S16   rgSchDSFRRntpInfoFree 
1038 (
1039  TknStrOSXL              *rntpPtr,
1040  RgSchCellCb             *cell,
1041  uint16_t                bw
1042  )
1043 #else
1044 static Void rgSchDSFRRntpInfoFree(rntpPtr, cell, bw)
1045    TknStrOSXL              *rntpPtr;
1046    RgSchCellCb             *cell;
1047    uint16_t                bw;
1048 #endif
1049 {   
1050    Inst inst = cell->instIdx;
1051    uint16_t len;
1052
1053    len = (bw % 8 == 0) ? (bw/8) : (bw/8 + 1);
1054
1055    if(rntpPtr->pres == PRSNT_NODEF)
1056    {   
1057       rgSCHUtlFreeSBuf(inst, (Data **)(&(rntpPtr->val)),(len * sizeof(uint8_t)));
1058       rntpPtr->pres = NOTPRSNT;
1059       rntpPtr->len  = 0;   
1060    }
1061
1062    return ROK;
1063 }
1064
1065 /**
1066  * @brief This function resets temporary variables in Pool
1067  * @details
1068  *
1069  *     Function: rgSchSFRResetPoolVariables
1070  *     Purpose:  Initialise the dynamic variables in each pool.
1071  *                    Reset bwAlloced, bwAssigned, type2End, type0End, type2Start
1072  *     Invoked by: rgSCHSFRUtlTotalPoolReset
1073  *
1074  *  @param[in]  RgSchCellCb*     cell
1075  *  @param[in]  RgSchSFRPoolInfo *pool
1076  *  @return  Void
1077  *
1078  **/
1079 #ifdef ANSI
1080 static Void rgSchSFRResetPoolVariables
1081 (
1082  RgSchCellCb             *cell,
1083  RgSchSFRPoolInfo        *pool
1084  )
1085 #else
1086 static Void rgSchSFRResetPoolVariables(cell, pool)
1087    RgSchCellCb             *cell;
1088    RgSchSFRPoolInfo *pool;
1089 #endif
1090 {
1091
1092    pool->bwAlloced  = 0;
1093
1094    /*type0end will be the last RBG in pool with all available RBs*/
1095    pool->type0End = (((pool->poolendRB + 1)/cell->rbgSize) - 1);
1096
1097    /*type2end will be the first RBG in pool with all available RBs*/
1098    pool->type2End = RGSCH_CEIL(pool->poolstartRB, cell->rbgSize);
1099    pool->type2Start = pool->poolstartRB;
1100    pool->bw = pool->poolendRB - pool->poolstartRB + 1;
1101
1102       return;
1103 }
1104 /**
1105  * @brief This function resets SFR Pool information for frame
1106  *
1107  * @details
1108  *
1109  *     Function: rgSCHSFRUtlTotalPooReset
1110  *     Purpose:  Update the dynamic variables in each pool as they will be modified in each slot.
1111  *                    Dont modify the static variables like startRB, endRB, BW
1112  *     Invoked by: rgSCHUtlSubFrmPut
1113  *
1114  *  @param[in]  RgSchCellCb*     cell
1115  *  @param[in]  RgSchDlSf*     subFrm
1116  *  @return  Void
1117  *
1118  **/
1119 #ifdef ANSI
1120 static Void rgSCHSFRUtlTotalPoolReset
1121 (
1122  RgSchCellCb             *cell,
1123  RgSchDlSf               *subFrm
1124  )
1125 #else
1126 static Void rgSCHSFRUtlTotalPoolReset(cell, subFrm)
1127    RgSchCellCb             *cell;
1128    RgSchDlSf               *subFrm;
1129 #endif
1130 {
1131    RgSchSFRTotalPoolInfo *totalPoolInfo = &subFrm->sfrTotalPoolInfo;
1132    CmLListCp    *ccPool = &totalPoolInfo->ccPool;
1133    CmLListCp    *cePool = &totalPoolInfo->cePool;
1134    CmLList *node = NULLP;
1135    RgSchSFRPoolInfo *tempPool = NULLP;
1136
1137    totalPoolInfo->ccBwFull          = FALSE;
1138    totalPoolInfo->ceBwFull          = FALSE;
1139    totalPoolInfo->isUeCellEdge      = FALSE;
1140    totalPoolInfo->CCPool1BwAvlbl    = 0;
1141    totalPoolInfo->CCPool2BwAvlbl    = 0;
1142    totalPoolInfo->CEPoolBwAvlbl     = 0;
1143    totalPoolInfo->CCRetx            = FALSE;
1144    totalPoolInfo->CERetx            = FALSE;
1145
1146    node = ccPool->first;
1147    while(node)
1148    {
1149       tempPool = (RgSchSFRPoolInfo *)(node->node);
1150       node = node->next;
1151       rgSchSFRResetPoolVariables(cell, tempPool);
1152       if(tempPool->poolstartRB == 0)
1153          totalPoolInfo->CCPool1BwAvlbl = tempPool->bw;
1154       else
1155          totalPoolInfo->CCPool2BwAvlbl = tempPool->bw;
1156    }
1157
1158    node = cePool->first;
1159    while(node)
1160    {
1161       tempPool = (RgSchSFRPoolInfo *)(node->node);
1162       node = node->next;
1163       rgSchSFRResetPoolVariables(cell, tempPool);
1164       totalPoolInfo->CEPoolBwAvlbl = tempPool->bw;    
1165    }
1166
1167    return;
1168 }
1169 /* LTE_ADV_FLAG_REMOVED_END */
1170 /**
1171  * @brief This function appends PHICH information for frame
1172  *
1173  * @details
1174  *
1175  *     Function: rgSCHUtlAddPhich
1176  *     Purpose:  This function appends PHICH information for
1177  *               a slot.
1178  *
1179  *     Invoked by: TOM
1180  *
1181  *  @param[in]  RgSchCellCb*     cell
1182  *  @param[in]  RgSubFrm*     subFrm
1183  *  @param[in]  uint8_t            hqFeedBack
1184  *  @param[in]  uint8_t            nDmrs
1185  *  @param[in]  uint8_t            rbStart
1186  *  @return  S16
1187  *      -# ROK
1188  *      -# RFAILED
1189  **/
1190 #ifdef LTE_TDD
1191 #ifdef ANSI
1192 S16 rgSCHUtlAddPhich
1193 (
1194 RgSchCellCb             *cell,
1195 CmLteTimingInfo         frm,
1196 uint8_t                      hqFeedBack,
1197 uint8_t                      nDmrs,
1198 uint8_t                      rbStart,
1199 uint8_t                      iPhich
1200 )
1201 #else
1202 S16 rgSCHUtlAddPhich(cell, frm, hqFeedBack, nDmrs, rbStart, iPhich)
1203 RgSchCellCb             *cell;
1204 CmLteTimingInfo         frm;
1205 uint8_t                      hqFeedBack;
1206 uint8_t                      nDmrs;
1207 uint8_t                      rbStart;
1208 uint8_t                      iPhich;
1209 #endif
1210 #else
1211 #ifdef ANSI
1212 S16 rgSCHUtlAddPhich
1213 (
1214 RgSchCellCb             *cell,
1215 CmLteTimingInfo         frm,
1216 uint8_t                 hqFeedBack,
1217 uint8_t                 nDmrs,
1218 uint8_t                 rbStart,
1219 Bool                    isForMsg3
1220 )
1221 #else
1222 S16 rgSCHUtlAddPhich(cell, frm, hqFeedBack, nDmrs, rbStart, isForMsg3)
1223 RgSchCellCb             *cell;
1224 CmLteTimingInfo         frm;
1225 uint8_t                 hqFeedBack;
1226 uint8_t                 nDmrs;
1227 uint8_t                 rbStart;
1228 Bool                    isForMsg3;
1229 #endif
1230 #endif
1231 {
1232    S16                ret;
1233    RgSchPhich         *phich;
1234    RgSchDlSf          *dlSf;
1235    Inst               inst = cell->instIdx;
1236
1237    dlSf = rgSCHUtlSubFrmGet(cell, frm);
1238    RGSCH_PHICH_ALLOC(inst, phich,sizeof(RgSchPhich), ret);
1239
1240    if(ret != ROK)
1241    {
1242       RLOG_ARG0(L_ERROR,DBG_CELLID,cell->cellId, " rgSCHUtlAddPhich(): "
1243                "Allocation of RgSchPhich failed");
1244       return RFAILED;
1245    }
1246 #ifdef LTE_TDD
1247    RGSCH_INITPHICH(phich, hqFeedBack, nDmrs, rbStart, iPhich);
1248 #else
1249    RGSCH_INITPHICH(phich, hqFeedBack, nDmrs, rbStart, isForMsg3); /*SR_RACH_STATS */
1250 #endif
1251    cmLListAdd2Tail(&dlSf->phichInfo.phichs, &phich->lnk);
1252    return ROK;
1253 } /* rgSCHUtlAddPhich */
1254
1255 /**
1256  * @brief This function resets PHICH information for frame
1257  *
1258  * @details
1259  *
1260  *     Function: rgSCHUtlPhichReset
1261  *     Purpose:  This function initializes PHICH information for
1262  *               a slot. It removes the list of PHICHs allocated
1263  *               in the prior use of this slot structure.
1264  *
1265  *     Invoked by: rgSCHUtlSubFrmPut
1266  *
1267  *  @param[in]  RgSchCellCb*     cell
1268  *  @param[in]  RgSubFrm*     subFrm
1269  *  @return  Void
1270  *
1271  **/
1272 #ifdef ANSI
1273 static Void rgSCHUtlPhichReset
1274 (
1275 RgSchCellCb                *cell,
1276 RgSchDlSf                  *subFrm
1277 )
1278 #else
1279 static Void rgSCHUtlPhichReset(cell, subFrm)
1280 RgSchCellCb                *cell;
1281 RgSchDlSf                  *subFrm;
1282 #endif
1283 {
1284    RgSchPhichInfo          *phichInfo;
1285    RgSchPhich              *phich;
1286
1287    UNUSED(cell);
1288
1289    phichInfo = &subFrm->phichInfo;
1290    while(phichInfo->phichs.first != NULLP)
1291    {
1292       phich = (RgSchPhich *)phichInfo->phichs.first->node;
1293       cmLListDelFrm(&phichInfo->phichs, phichInfo->phichs.first);
1294       RGSCH_PHICH_FREE(cell->instIdx, phich, sizeof(RgSchPhich));
1295    }
1296    cmLListInit(&phichInfo->phichs);
1297    return;
1298 } /* rgSCHUtlPhichReset */
1299
1300 \f
1301 /**
1302  * @brief This function returns slot data structure for a cell
1303  *
1304  * @details
1305  *
1306  *     Function: rgSCHUtlSubFrmGet
1307  *     Purpose:  This function resets the slot data structure
1308  *               when the slot is released
1309  *
1310  *     Invoked by: scheduler
1311  *
1312  *  @param[in]  RgSubFrm  subFrm
1313  *  @return  Void
1314  *
1315  **/
1316 #ifdef ANSI
1317 RgSchDlSf* rgSCHUtlSubFrmGet
1318 (
1319 RgSchCellCb            *cell,
1320 CmLteTimingInfo        frm
1321 )
1322 #else
1323 RgSchDlSf* rgSCHUtlSubFrmGet(cell, frm)
1324 RgSchCellCb            *cell;
1325 CmLteTimingInfo        frm;
1326 #endif
1327 {
1328    RgSchDlSf            *sf;
1329    uint8_t               dlIdx;
1330
1331 #ifdef LTE_TDD
1332    dlIdx = rgSCHUtlGetDlSfIdx(cell, &frm);
1333    //RGSCH_ARRAY_BOUND_CHECK(cell->instIdx, cell->subFrms, dlIdx);
1334    sf = cell->subFrms[dlIdx];
1335 #else
1336    /* Changing the idexing
1337       so that proper slot is selected */
1338    dlIdx = (((frm.sfn & 1) * RGSCH_NUM_SUB_FRAMES) + (frm.slot % RGSCH_NUM_SUB_FRAMES));
1339    RGSCH_ARRAY_BOUND_CHECK(cell->instIdx, cell->subFrms, dlIdx);
1340    sf = cell->subFrms[dlIdx];
1341 #endif
1342   /* CA dev Start */
1343    sf->dlIdx    = dlIdx;
1344   /* CA dev End */
1345    return (sf);
1346 }
1347
1348 \f
1349 /**
1350  * @brief This function returns slot data structure for a cell
1351  *
1352  * @details
1353  *
1354  *     Function: rgSCHUtlSubFrmPut
1355  *     Purpose:  This function resets the slot data structure
1356  *               when the slot is released
1357  *
1358  *     Invoked by: scheduler
1359  *
1360  *  @param[in]  RgSubFrm  subFrm
1361  *  @return  Void
1362  *
1363  **/
1364 #ifdef ANSI
1365 Void rgSCHUtlSubFrmPut
1366 (
1367 RgSchCellCb            *cell,
1368 RgSchDlSf              *sf
1369 )
1370 #else
1371 Void rgSCHUtlSubFrmPut(cell, sf)
1372 RgSchCellCb            *cell;
1373 RgSchDlSf              *sf;
1374 #endif
1375 {
1376    uint8_t                  i;
1377    uint8_t                  noRaRsps;
1378
1379 #ifdef LTE_TDD
1380    /* Release all the held PDCCH information */
1381    rgSCHUtlPdcchInit(cell, sf, sf->nCce);
1382 #else
1383    /* Release all the held PDCCH information */
1384    rgSCHUtlPdcchInit(cell, sf, cell->nCce);
1385 #endif
1386    rgSCHUtlPhichReset(cell, sf);
1387
1388    /* Reset the bw allocated. */
1389    sf->bwAssigned = 0;
1390 #ifdef LTEMAC_SPS
1391    /* Setting allocated bandwidth to SPS bandwidth for non-SPS RB allocator */
1392    sf->bwAlloced = ((cell->spsCellCfg.maxSpsDlBw +
1393       cell->rbgSize - 1)/cell->rbgSize) * cell->rbgSize;
1394    if (sf->bwAlloced > sf->bw)
1395    {
1396       sf->bwAlloced = sf->bw;
1397    }
1398    sf->spsAllocdBw = 0;
1399    sf->type2Start = sf->bwAlloced;
1400    memset( &sf->dlSfAllocInfo, 0, sizeof(RgSchDlSfAllocInfo));
1401 #else
1402    sf->bwAlloced = 0;
1403    /* Fix for ccpu00123918*/
1404    sf->type2Start = 0;
1405    /* LTE_ADV_FLAG_REMOVED_START */
1406    /* dsfr_pal_fixes ** 21-March-2013 ** SKS */
1407    if (cell->lteAdvCb.dsfrCfg.status == RGR_ENABLE)
1408    {
1409       memset(sf->rntpInfo.val, 0, sf->rntpInfo.len);
1410    }
1411    /* LTE_ADV_FLAG_REMOVED_END */
1412 #endif
1413    sf->txDone = FALSE;
1414    /*[ccpu00138609]-ADD-Reset the CCCH UE counter */
1415    sf->schdCcchUe = 0;
1416
1417    /* Non DLFS scheduling using Type0 RA requires the following
1418     * parameter's tracking */
1419    /* Type 2 localized allocations start from 0th RBG and onwards */
1420    /* Type 0 allocations start from last RBG and backwards*/
1421 #ifndef LTEMAC_SPS
1422    sf->type2End   = 0;
1423 #else
1424    sf->type2End   = RGSCH_CEIL(sf->bwAlloced,cell->rbgSize);
1425 #endif
1426    sf->type0End   = cell->noOfRbgs - 1;
1427    /* If last RBG is of incomplete size then special handling */
1428    (sf->bw % cell->rbgSize == 0)? (sf->lstRbgDfct = 0) :
1429       (sf->lstRbgDfct = cell->rbgSize - (sf->bw % cell->rbgSize));
1430    /* This resets the allocation for BCCH and PDCCH */
1431 #ifdef EMTC_ENABLE
1432    /* TODO we need to move this reset for emtc functions */
1433    if(!(cell->emtcEnable))
1434    {
1435       sf->bch.tb     = NULLP;
1436       sf->bch.tbSize = 0;
1437    }
1438 #else
1439    sf->bch.tb     = NULLP;
1440    sf->bch.tbSize = 0;
1441 #endif
1442    sf->bcch.pdcch = NULLP;
1443    sf->pcch.pdcch = NULLP;
1444 #ifdef LTE_TDD
1445    noRaRsps = RGSCH_MAX_TDD_RA_RSP_ALLOC;
1446 #else
1447    noRaRsps = RGSCH_MAX_RA_RSP_ALLOC;
1448 #endif
1449    for (i = 0; i < noRaRsps; i++)
1450    {
1451       sf->raRsp[i].pdcch = NULLP;
1452       cmLListInit(&(sf->raRsp[i].raRspLst));
1453    }
1454    /* LTE_ADV_FLAG_REMOVED_START */
1455    if (cell->lteAdvCb.sfrCfg.status == RGR_ENABLE)
1456    {
1457       rgSCHSFRUtlTotalPoolReset(cell, sf);
1458    }
1459    /* LTE_ADV_FLAG_REMOVED_END */
1460 #ifdef LTE_ADV
1461    cmLListInit(&sf->n1PucchResLst);
1462 #endif
1463
1464    sf->cceCnt = 0;
1465    sf->isCceFailure = FALSE;
1466    sf->dlUlBothCmplt = 0;
1467    return;
1468 }
1469
1470 \f
1471 /**
1472  * @brief This function computes log N (32 bit Unsigned) to the base 2
1473  *
1474  * @details
1475  *
1476  *     Function: rgSCHUtlLog32bitNbase2
1477  *     Purpose:  This function computes log N (32 bit Unsigned) to the base 2.
1478  *               For n= 0,1 ret = 0.
1479  *
1480  *     Invoked by: Scheduler
1481  *
1482  *  @param[in]  uint32_t       n
1483  *  @return  uint8_t
1484  *
1485  **/
1486 #ifdef ANSI
1487 uint8_t rgSCHUtlLog32bitNbase2
1488 (
1489 uint32_t               n
1490 )
1491 #else
1492 uint8_t rgSCHUtlLog32bitNbase2(n)
1493 uint32_t               n;
1494 #endif
1495 {
1496    uint32_t            b[] = {0x2, 0xc, 0xf0, 0xff00, 0xffff0000};
1497    uint32_t            s[] = {1, 2, 4, 8, 16};
1498    S16                 i;
1499    uint8_t             ret = 0;
1500
1501    for (i=4; i >= 0; i--)
1502    {
1503       if (n & b[i])
1504       {
1505          n >>= s[i];
1506          ret |= s[i];
1507       }
1508    }
1509    return (ret);
1510 }
1511
1512 #ifdef LTEMAC_SPS
1513
1514 /**
1515  * @brief This function is a wrapper to call scheduler specific API.
1516  *
1517  * @details
1518  *
1519  *     Function: rgSCHUtlDlRelPdcchFbk
1520  *     Purpose:  Calls scheduler's handler for SPS release PDCCH feedback
1521  *     information.
1522  *
1523  *     Invoked by: DHM
1524  *
1525  *  @param[in]   RgSchCellCb     *cell
1526  *  @param[in]   RgSchUeCb       *ue
1527  *  @param[in]   uint8_t            isAck
1528  *  @return  Void
1529  *
1530  **/
1531 #ifdef ANSI
1532 Void rgSCHUtlDlRelPdcchFbk
1533 (
1534 RgSchCellCb        *cell,
1535 RgSchUeCb          *ue,
1536 uint8_t               isAck
1537 )
1538 #else
1539 Void rgSCHUtlDlRelPdcchFbk(cell, ue, isAck)
1540 RgSchCellCb        *cell;
1541 RgSchUeCb          *ue;
1542 uint8_t               isAck;
1543 #endif
1544 {
1545    cell->sc.apis->rgSCHDlRelPdcchFbk(cell, ue, isAck);
1546    return;
1547 }
1548
1549
1550
1551 /**
1552  * @brief This function is a wrapper to call scheduler specific API.
1553  *
1554  * @details
1555  *
1556  *     Function: rgSCHUtlDlProcAck
1557  *     Purpose:  Calls scheduler's handler to process Ack
1558  *     information.
1559  *
1560  *     Invoked by: DHM
1561  *
1562  *  @param[in]   RgSchCellCb     *cell
1563  *  @param[in]   RgSchDlHqProcCb *hqP
1564  *  @return  Void
1565  *
1566  **/
1567 #ifdef ANSI
1568 Void rgSCHUtlDlProcAck
1569 (
1570 RgSchCellCb        *cell,
1571 RgSchDlHqProcCb    *hqP
1572 )
1573 #else
1574 Void rgSCHUtlDlProcAck(cell, hqP)
1575 RgSchCellCb        *cell;
1576 RgSchDlHqProcCb    *hqP;
1577 #endif
1578 {
1579    cell->sc.apis->rgSCHDlProcAck(cell, hqP);
1580    return;
1581 }
1582
1583 /**
1584  * @brief CRNTI CE Handler
1585  *
1586  * @details
1587  *
1588  *     Function : rgSCHUtlHdlCrntiCE
1589  *
1590  *     - Call scheduler common API
1591  *
1592  *
1593  *  @param[in]  RgSchCellCb   *cell
1594  *  @param[in]  RgSchUeCb     *ue
1595  *  @param[out] RgSchErrInfo  *err
1596  *  @return  Void
1597  **/
1598 #ifdef ANSI
1599 Void rgSCHUtlHdlCrntiCE
1600 (
1601 RgSchCellCb  *cell,
1602 RgSchUeCb    *ue
1603 )
1604 #else
1605 Void rgSCHUtlHdlCrntiCE(cell, ue)
1606 RgSchCellCb  *cell;
1607 RgSchUeCb    *ue;
1608 #endif
1609 {
1610
1611    cell->sc.apis->rgSCHHdlCrntiCE(cell, ue);
1612    return;
1613 }  /* rgSCHUtlHdlCrntiCE */
1614 #endif /* LTEMAC_SPS */
1615
1616 /***********************************************************
1617  *
1618  *     Func : rgSCHUtlCalcTotalRegs
1619  *
1620  *     Desc : Calculate total REGs, given a bandwidth, CFI
1621  *            and number of antennas.
1622  *
1623  *     Ret  : Total REGs (uint16_t)
1624  *
1625  *     Notes: Could optimise if bw values are limited
1626  *            (taken from RRC spec) by indexing values from
1627  *            a table.
1628  *            Input values are not validated. CFI is assumed
1629  *            to be 1/2/3/4.
1630  *
1631  *     File :
1632  *
1633  **********************************************************/
1634 #ifdef ANSI
1635 static uint16_t rgSCHUtlCalcTotalRegs
1636 (
1637 uint8_t    bw,
1638 uint8_t    cfi,
1639 uint8_t    numAntna,
1640 Bool  isEcp
1641 )
1642 #else
1643 static uint16_t rgSCHUtlCalcTotalRegs(bw, cfi, numAntna, isEcp)
1644 uint8_t    bw;
1645 uint8_t    cfi;
1646 uint8_t    numAntna;
1647 Bool  isEcp;
1648 #endif
1649 {
1650    uint16_t regs = 0;
1651
1652    /*ccpu00116757-  removed check for (ERRCLASS & ERRCLS_DEBUG)*/
1653
1654    if (bw <= 10)
1655       ++cfi;
1656    switch (cfi)
1657    {
1658       /* Refer 36.211 section 6.10.1.2
1659        * For symbols 2 and 4, the REGs per RB will be based on cyclic prefix
1660        *  and number of antenna ports.
1661        * For symbol 1, there are 2 REGs per RB always. Similarly symbol 3
1662        * will have 3 REGS.
1663        */
1664       case 4:
1665          /*CR changes [ccpu00124416] - MOD*/
1666          if(isEcp)
1667          {
1668             regs =  bw * RGSCH_NUM_REGS_4TH_SYM_EXT_CP;
1669          }
1670          else
1671          {
1672             regs =  bw * RGSCH_NUM_REGS_4TH_SYM_NOR_CP;
1673          }
1674       case 3:
1675          regs += bw * RGSCH_NUM_REGS_3RD_SYM;
1676       case 2:
1677             /*CR changes [ccpu00124416] - MOD using number of antenna ports*/
1678          regs += (numAntna == RGSCH_NUM_ANT_PORT_FOUR) ? \
1679             (bw * RGSCH_NUM_REGS_2ND_SYM_FOUR_ANT_PORT) : \
1680             (bw * RGSCH_NUM_REGS_2ND_SYM_1OR2_ANT_PORT);
1681       default: /* case 1 */
1682          regs += bw * RGSCH_NUM_REGS_1ST_SYM;
1683    }
1684    return (regs);
1685 }
1686
1687 /***********************************************************
1688  *
1689  *     Func : rgSCHUtlCalcPhichRegs
1690  *
1691  *     Desc : Calculates number of PHICH REGs
1692  *
1693  *     Ret  : Number of PHICH REGs (uint8_t)
1694  *
1695  *     Notes: ng6 is Ng multiplied by 6
1696  *
1697  *     File :
1698  *
1699  **********************************************************/
1700 #ifdef ANSI
1701 static uint16_t rgSCHUtlCalcPhichRegs
1702 (
1703 uint8_t bw,
1704 uint8_t ng6
1705 )
1706 #else
1707 static uint16_t rgSCHUtlCalcPhichRegs(bw, ng6)
1708 uint8_t bw;
1709 uint8_t ng6;
1710 #endif
1711 {
1712    /* ccpu00115330: Corrected the calculation for number of PHICH groups*/
1713    return (RGSCH_CEIL((bw * ng6) ,(8 * 6)) * RGSCH_NUM_REG_PER_PHICH_GRP);
1714 }
1715
1716 #ifdef LTE_TDD
1717 /**
1718  * @brief Calculates total CCEs (N_cce)
1719  *
1720  * @details
1721  *
1722  *     Function: rgSCHUtlCalcNCce
1723  *     Purpose:  This function calculates and returns total CCEs for a
1724  *               cell, given the following: bandwidth, Ng configuration
1725  *               (multiplied by six), cfi (actual number of control
1726  *               symbols), m factor for PHICH  and number of antennas.
1727  *
1728  *     Invoked by: Scheduler
1729  *
1730  *  @param[in]  uint8_t      bw
1731  *  @param[in]  uint8_t      ng6
1732  *  @param[in]  uint8_t      cfi
1733  *  @param[in]  uint8_t      mPhich
1734  *  @param[in]  uint8_t      numAntna
1735  *  @param[in]  Bool    isEcp
1736  *  @return     N_cce (uint8_t)
1737  *
1738  **/
1739 #ifdef ANSI
1740 uint8_t rgSCHUtlCalcNCce
1741 (
1742 uint8_t            bw,
1743 RgrPhichNg    ng,
1744 uint8_t            cfi,
1745 uint8_t            mPhich,
1746 uint8_t            numAntna,
1747 Bool          isEcp
1748 )
1749 #else
1750 uint8_t rgSCHUtlCalcNCce(bw, ng, cfi, mPhich, numAntna, isEcp)
1751 uint8_t             bw;
1752 RgrPhichNg     ng;
1753 uint8_t             cfi;
1754 uint8_t             mPhich;
1755 uint8_t             numAntna;
1756 Bool           isEcp;
1757 #endif
1758 {
1759    uint16_t         totalRegs;
1760    uint16_t         phichRegs;
1761    uint16_t         cceRegs;
1762    uint8_t          ng6;
1763
1764    /*ccpu00116757-  removed check for (ERRCLASS & ERRCLS_DEBUG)*/
1765
1766    switch (ng)
1767    {
1768       case RGR_NG_ONESIXTH:
1769          ng6 = 1;
1770          break;
1771       case RGR_NG_HALF:
1772          ng6 = 3;
1773          break;
1774       case RGR_NG_ONE:
1775          ng6 = 6;
1776          break;
1777       case RGR_NG_TWO:
1778       default:
1779          ng6 = 12;
1780          break;
1781    }
1782
1783    totalRegs = rgSCHUtlCalcTotalRegs(bw, cfi, numAntna, isEcp);
1784    phichRegs = rgSCHUtlCalcPhichRegs(bw, ng6);
1785    cceRegs   = totalRegs - mPhich*phichRegs - RGSCH_NUM_PCFICH_REG;
1786
1787    return ((uint8_t)(cceRegs/RGSCH_NUM_REG_PER_CCE));
1788 }
1789
1790 #else
1791 /**
1792  * @brief Calculates total CCEs (N_cce)
1793  *
1794  * @details
1795  *
1796  *     Function: rgSCHUtlCalcNCce
1797  *     Purpose:  This function calculates and returns total CCEs for a
1798  *               cell, given the following: bandwidth, Ng configuration
1799  *               (multiplied by six), cfi (actual number of control
1800  *               symbols) and number of antennas.
1801  *
1802  *     Invoked by: Scheduler
1803  *
1804  *  @param[in]  uint8_t      bw
1805  *  @param[in]  uint8_t      ng6
1806  *  @param[in]  uint8_t      cfi
1807  *  @param[in]  uint8_t      numAntna
1808  *  @return     N_cce (uint8_t)
1809  *
1810  **/
1811 #ifdef ANSI
1812 uint8_t rgSCHUtlCalcNCce
1813 (
1814 uint8_t       bw,
1815 RgrPhichNg    ng,
1816 uint8_t       cfi,
1817 uint8_t       numAntna,
1818 Bool          isEcp
1819 )
1820 #else
1821 uint8_t rgSCHUtlCalcNCce(bw, ng, cfi, numAntna, isEcp)
1822 uint8_t        bw;
1823 RgrPhichNg     ng;
1824 uint8_t        cfi;
1825 uint8_t        numAntna;
1826 Bool           isEcp;
1827 #endif
1828 {
1829    uint16_t         totalRegs;
1830    uint16_t         phichRegs;
1831    uint16_t         cceRegs;
1832    uint8_t          ng6;
1833
1834    /*ccpu00116757-  removed check for (ERRCLASS & ERRCLS_DEBUG)*/
1835
1836    switch (ng)
1837    {
1838       case RGR_NG_ONESIXTH:
1839          ng6 = 1;
1840          break;
1841       case RGR_NG_HALF:
1842          ng6 = 3;
1843          break;
1844       case RGR_NG_ONE:
1845          ng6 = 6;
1846          break;
1847       case RGR_NG_TWO:
1848       default:
1849          ng6 = 12;
1850          break;
1851    }
1852
1853    totalRegs = rgSCHUtlCalcTotalRegs(bw, cfi, numAntna, isEcp);
1854    phichRegs = rgSCHUtlCalcPhichRegs(bw, ng6);
1855    cceRegs   = totalRegs - phichRegs - RGSCH_NUM_PCFICH_REG;
1856
1857    return ((uint8_t)(cceRegs/RGSCH_NUM_REG_PER_CCE));
1858 }
1859 #endif
1860
1861 /**
1862  * @brief Returns PHICH info associated with an uplink
1863  *        HARQ process allocation
1864  *
1865  * @details
1866  *
1867  *     Function: rgSCHUtlGetPhichInfo
1868  *     Purpose:  This function returns PHICH info associated with
1869  *               an uplink HARQ process allocation. PHICH info
1870  *               comprises RB start and N_dmrs.
1871  *
1872  *  @param[in]  RgSchUlHqProcCb   *hqProc
1873  *  @param[out] uint8_t             *rbStartRef
1874  *  @param[out] uint8_t             *nDmrsRef
1875  *  @return  S16
1876  **/
1877 #ifdef LTE_TDD
1878 #ifdef ANSI
1879 S16 rgSCHUtlGetPhichInfo
1880 (
1881 RgSchUlHqProcCb   *hqProc,
1882 uint8_t           *rbStartRef,
1883 uint8_t           *nDmrsRef,
1884 uint8_t           *iPhich
1885 )
1886 #else
1887 S16 rgSCHUtlGetPhichInfo(hqProc, rbStartRef, nDmrsRef, iPhich)
1888 RgSchUlHqProcCb   *hqProc;
1889 uint8_t           *rbStartRef;
1890 uint8_t           *nDmrsRef;
1891 uint8_t           *iPhich;
1892 #endif
1893 #else
1894 #ifdef ANSI
1895 S16 rgSCHUtlGetPhichInfo
1896 (
1897 RgSchUlHqProcCb   *hqProc,
1898 uint8_t           *rbStartRef,
1899 uint8_t           *nDmrsRef
1900 )
1901 #else
1902 S16 rgSCHUtlGetPhichInfo(hqProc, rbStartRef, nDmrsRef)
1903 RgSchUlHqProcCb   *hqProc;
1904 uint8_t           *rbStartRef;
1905 uint8_t           *nDmrsRef;
1906 #endif
1907 #endif
1908 {
1909 /* ACC-TDD */
1910         S16 ret = RFAILED;
1911
1912         if ((hqProc != NULLP) && (hqProc->alloc != NULLP))
1913     {
1914        *rbStartRef = hqProc->alloc->grnt.rbStart;
1915        *nDmrsRef   = hqProc->alloc->grnt.nDmrs;
1916 #ifdef LTE_TDD
1917    *iPhich     = hqProc->iPhich;
1918 #endif
1919        ret = ROK;
1920     }
1921     return (ret);
1922 }
1923 #ifndef TFU_UPGRADE
1924 /**
1925  * @brief Returns uplink grant information required to permit
1926  *        PHY to receive data
1927  *
1928  * @details
1929  *
1930  *     Function: rgSCHUtlAllocRcptInfo
1931  *     Purpose:  Given an uplink allocation, this function returns
1932  *               uplink grant information which is needed by PHY to
1933  *               decode data sent from UE. This information includes:
1934  *               - RB start
1935  *               - Number of RBs
1936  *               - RV
1937  *
1938  *  @param[in]  RgSchUlAlloc   *alloc
1939  *  @param[out] uint8_t             *rbStartRef
1940  *  @param[out] uint8_t             *numRbRef
1941  *  @param[out] uint8_t             *rvRef
1942  *  @param[out] uint16_t            *size
1943  *  @param[out] TfuModScheme   *modType
1944  *  @param[out] Bool           *isRtx
1945  *  @param[out] uint8_t             *nDmrs
1946  *  @param[out] Bool           *ndi
1947  *  @param[out] uint8_t             *hqPId
1948  *  @return  S16
1949  **/
1950 #ifdef ANSI
1951 S16 rgSCHUtlAllocRcptInfo
1952 (
1953 RgSchUlAlloc   *alloc,
1954 CmLteRnti      *rnti,
1955 uint8_t        *iMcsRef,
1956 uint8_t        *rbStartRef,
1957 uint8_t        *numRbRef,
1958 uint8_t        *rvRef,
1959 uint16_t       *size,
1960 TfuModScheme   *modType,
1961 Bool           *isRtx,
1962 uint8_t        *nDmrs,
1963 Bool           *ndi,
1964 uint8_t        *hqPId
1965 )
1966 #else
1967 S16 rgSCHUtlAllocRcptInfo(alloc, rnti, iMcsRef, rbStartRef, numRbRef,
1968                                  rvRef, size, modType, isRtx, nDmrs, ndi,
1969                                  hqPId)
1970 RgSchUlAlloc   *alloc;
1971 CmLteRnti      *rnti;
1972 uint8_t        *iMcsRef;
1973 uint8_t        *rbStartRef;
1974 uint8_t        *numRbRef;
1975 uint8_t        *rvRef;
1976 uint16_t       *size;
1977 TfuModScheme   *modType;
1978 Bool           *isRtx;
1979 uint8_t        *nDmrs;
1980 Bool           *ndi;
1981 uint8_t        *hqPId;
1982 #endif
1983 {
1984    /* Modulation order for 16qam UEs would be
1985     * min(4,modulation order in grant). Please refer to 36.213-8.6.1*/
1986    CmLteUeCategory ueCtgy;
1987
1988 #if (ERRCLASS & ERRCLS_DEBUG)
1989    if ((alloc == NULLP) || (alloc->hqProc == NULLP))
1990    {
1991       return RFAILED;
1992    }
1993 #endif
1994
1995    if ( !alloc->forMsg3 )
1996    {
1997       if ( ((alloc->ue) == NULLP) ||  (RG_SCH_CMN_GET_UE(alloc->ue, alloc->ue->cell) == NULLP))
1998       {
1999          RLOG_ARG2(L_ERROR,DBG_CELLID,alloc->ue->cell->cellId,
2000                      "Failed: ue->sch is null RNTI:%d,isRetx=%d",
2001                      alloc->rnti, alloc->grnt.isRtx);
2002          return RFAILED; 
2003       }
2004      ueCtgy =  (RG_SCH_CMN_GET_UE_CTGY(alloc->ue));
2005    }
2006
2007    *iMcsRef    = alloc->grnt.iMcs;
2008    *rbStartRef = alloc->grnt.rbStart;
2009    *numRbRef   = alloc->grnt.numRb;
2010    *rvRef      = rgRvTable[alloc->hqProc->rvIdx];
2011    *rnti       = alloc->rnti;
2012    *size       = alloc->grnt.datSz;
2013    *modType    = (alloc->forMsg3)? alloc->grnt.modOdr:
2014                          ((ueCtgy == CM_LTE_UE_CAT_5)?
2015                          alloc->grnt.modOdr:
2016                          (RGSCH_MIN(RGSCH_QM_QPSK,alloc->grnt.modOdr)));
2017    *isRtx      = alloc->grnt.isRtx;
2018    *nDmrs      = alloc->grnt.nDmrs;
2019    *ndi        = alloc->hqProc->ndi;
2020    *hqPId      = alloc->hqProc->procId;
2021
2022    return ROK;
2023 }
2024 #else
2025 /**
2026  * @brief Returns uplink grant information required to permit
2027  *        PHY to receive data
2028  *
2029  * @details
2030  *
2031  *     Function: rgSCHUtlAllocRcptInfo
2032  *     Purpose:  Given an uplink allocation, this function returns
2033  *               uplink grant information which is needed by PHY to
2034  *               decode data sent from UE. This information includes:
2035  *               - RB start
2036  *               - Number of RBs
2037  *               - RV
2038  *
2039  *  @param[in]  RgSchUlAlloc   *alloc
2040  *  @param[out] uint8_t             *rbStartRef
2041  *  @param[out] uint8_t             *numRbRef
2042  *  @param[out] uint8_t             *rvRef
2043  *  @param[out] uint16_t            *size
2044  *  @param[out] TfuModScheme   *modType
2045  *  @return  S16
2046  **/
2047 #ifdef ANSI
2048 S16 rgSCHUtlAllocRcptInfo
2049 (
2050 RgSchCellCb             *cell,
2051 RgSchUlAlloc            *alloc,
2052 CmLteTimingInfo         *timeInfo,
2053 TfuUeUlSchRecpInfo      *recpReq
2054 )
2055 #else
2056 S16 rgSCHUtlAllocRcptInfo(cell, alloc, timeInfo, recpReq)
2057 RgSchCellCb             *cell;
2058 RgSchUlAlloc            *alloc;
2059 CmLteTimingInfo         *timeInfo;
2060 TfuUeUlSchRecpInfo      *recpReq;
2061 #endif
2062 {
2063 #if (ERRCLASS & ERRCLS_DEBUG)
2064    if ((alloc == NULLP) || (alloc->hqProc == NULLP))
2065    {
2066       return RFAILED;
2067    }
2068 #endif
2069    recpReq->size           = alloc->grnt.datSz;
2070    recpReq->rbStart        = alloc->grnt.rbStart;
2071    recpReq->numRb          = alloc->grnt.numRb;
2072    /* Modulation order min(4,mod in grant) for 16 qam UEs.
2073     * Please refer to 36.213-8.6.1*/
2074 #ifdef FOUR_TX_ANTENNA
2075    recpReq->modType        = (TfuModScheme)((alloc->forMsg3)?alloc->grnt.modOdr:
2076          (/*(alloc->ue->ueCatEnum == CM_LTE_UE_CAT_5)?
2077             alloc->grnt.modOdr:    *//* Chandra:TmpFx-TM500 Cat5 with Only16QAM */
2078           (RGSCH_MIN(RGSCH_QM_QPSK,alloc->grnt.modOdr))));
2079 #else
2080    recpReq->modType        = (TfuModScheme)((alloc->forMsg3)?alloc->grnt.modOdr:
2081                              ((alloc->ue->ueCatEnum == CM_LTE_UE_CAT_5)?
2082                               alloc->grnt.modOdr:
2083                              (RGSCH_MIN(RGSCH_QM_QPSK,alloc->grnt.modOdr))));
2084 #endif
2085    recpReq->nDmrs          = alloc->grnt.nDmrs;
2086    recpReq->hoppingEnbld   = FALSE;
2087    recpReq->hoppingBits    = 0;
2088    recpReq->isRtx          = alloc->grnt.isRtx;
2089    recpReq->ndi            = alloc->hqProc->ndi;   
2090    recpReq->rv             = rgRvTable[alloc->hqProc->rvIdx];
2091 #ifndef LTE_TDD
2092    recpReq->harqProcId = alloc->hqProc->procId;
2093 #else
2094    recpReq->harqProcId = rgSCHCmnGetUlHqProcIdx(timeInfo, cell);
2095 #endif
2096    /* Transmission mode is SISO till Uplink MIMO is implemented. */
2097    recpReq->txMode   = 0;
2098    /* This value needs to filled in in the case of frequency hopping. */
2099    recpReq->crntTxNb = 0;
2100
2101    recpReq->mcs = alloc->grnt.iMcs;
2102 #ifdef RG_5GTF
2103    recpReq->rbgStart = alloc->grnt.vrbgStart;
2104    recpReq->numRbg = alloc->grnt.numVrbg;
2105    recpReq->xPUSCHRange = alloc->grnt.xPUSCHRange;
2106    //TODO_SID Need to check
2107    recpReq->nAntPortLayer = 0;
2108    recpReq->SCID = alloc->grnt.SCID;
2109    recpReq->PMI = alloc->grnt.PMI;
2110    recpReq->uciWoTBFlag = alloc->grnt.uciOnxPUSCH;
2111    if(alloc->ue)
2112    {
2113       recpReq->beamIndex = alloc->ue->ue5gtfCb.BeamId;
2114    }
2115 #endif
2116
2117 #ifdef TENB_STATS
2118    if (!alloc->forMsg3)
2119    {
2120       if (alloc->grnt.isRtx)
2121       {
2122          alloc->ue->tenbStats->stats.nonPersistent.sch[RG_SCH_CELLINDEX(alloc->ue->cell)].ulRetxOccns++;
2123       }
2124       else
2125       {
2126          alloc->ue->tenbStats->stats.nonPersistent.sch[RG_SCH_CELLINDEX(alloc->ue->cell)].ulTxOccns++;
2127          alloc->ue->tenbStats->stats.nonPersistent.sch[RG_SCH_CELLINDEX(alloc->ue->cell)].ulSumiTbs += \
2128             rgSCHCmnUlGetITbsFrmIMcs(alloc->grnt.iMcs);
2129          alloc->ue->tenbStats->stats.nonPersistent.sch[RG_SCH_CELLINDEX(alloc->ue->cell)].ulNumiTbs ++;
2130          cell->tenbStats->sch.ulSumiTbs += \
2131             rgSCHCmnUlGetITbsFrmIMcs(alloc->grnt.iMcs);
2132          cell->tenbStats->sch.ulNumiTbs ++;
2133       }
2134       alloc->ue->tenbStats->stats.nonPersistent.sch[RG_SCH_CELLINDEX(alloc->ue->cell)].ulPrbUsg += alloc->grnt.numRb;
2135       cell->tenbStats->sch.ulPrbUsage[0] += alloc->grnt.numRb;
2136    }
2137 #endif
2138   /* ccpu00117050 - DEL - nSrs setting at rgSCHUtlAllocRcptInfo */
2139    return ROK;
2140 }
2141 #endif
2142
2143 #ifdef LTE_TDD
2144 /**
2145  * @brief This function initialises the PRACH slot occasions
2146  *
2147  * @details
2148  *
2149  *     Function: rgSCHUtlUpdPrachOcc
2150  *     Purpose:  This function updates the PRACH slots based on
2151  *               RGR configuration.
2152  *
2153  *     Invoked by: Scheduler
2154  *
2155  *  @param[in]  RgSchCellCb      *cell
2156  *  @param[in]  RgrTddPrachInfo  *cellCfg
2157  *  @return     Void
2158  *
2159  **/
2160 #ifdef ANSI
2161 static Void rgSCHUtlUpdPrachOcc
2162 (
2163 RgSchCellCb       *cell,
2164 RgrTddPrachInfo   *cellCfg
2165 )
2166 #else
2167 static Void rgSCHUtlUpdPrachOcc(cell, cellCfg)
2168 RgSchCellCb       *cell;
2169 RgrTddPrachInfo   *cellCfg;
2170 #endif
2171 {
2172    uint8_t    idx;
2173    uint8_t    count = 0;
2174    uint8_t    size;
2175    uint8_t    startIdx;
2176    uint8_t    endIdx;
2177
2178    /* In the 1st half frame */
2179    if(cellCfg->halfFrm == 0)
2180    {
2181       startIdx = 2;
2182       endIdx = 6;
2183    }
2184    /* In the 2nd half frame */
2185    else
2186    {
2187       startIdx = 6;
2188       endIdx = 10;
2189    }
2190    for(idx = startIdx; idx < endIdx; idx++)
2191    {
2192       if(rgSchTddUlDlSubfrmTbl[cell->ulDlCfgIdx][idx]
2193             == RG_SCH_TDD_UL_slot)
2194       {
2195          if(cellCfg->ulStartSfIdx == count)
2196          {
2197             size = cell->rachCfg.raOccasion.size;
2198             cell->rachCfg.raOccasion.slotNum[size] = idx;
2199             cell->rachCfg.raOccasion.size++;
2200             break;
2201          }
2202          count ++;
2203       }
2204    }
2205    return;
2206 }
2207
2208 /**
2209  * @brief This function initialises the PRACH occasions
2210  *
2211  * @details
2212  *
2213  *     Function: rgSCHUtlPrachCfgInit
2214  *     Purpose:  This function initialises the PRACH occasions based on
2215  *               RGR configuration.
2216  *
2217  *     Invoked by: Scheduler
2218  *
2219  *  @param[in]  RgSchCellCb       *cell
2220  *  @param[in]  RgrCellCfg        *cellCfg
2221  *  @return     Void
2222  *
2223  **/
2224 #ifdef ANSI
2225 Void rgSCHUtlPrachCfgInit
2226 (
2227 RgSchCellCb       *cell,
2228 RgrCellCfg        *cellCfg
2229 )
2230 #else
2231 Void rgSCHUtlPrachCfgInit(cell, cellCfg)
2232 RgSchCellCb       *cell;
2233 RgrCellCfg        *cellCfg;
2234 #endif
2235 {
2236    uint8_t idx;
2237    uint8_t subfrmIdx;
2238    uint8_t splFrm;
2239
2240    if(cellCfg->prachRscInfo.numRsc <= 0)
2241    {
2242       RLOG_ARG0(L_ERROR,DBG_CELLID,cell->cellId, "Invalid"
2243                   "PRACH resources Configuration ");
2244       return;
2245    }
2246
2247    /* Update SFN occasions */
2248    cell->rachCfg.raOccasion.sfnEnum =
2249                      cellCfg->prachRscInfo.prachInfo[0].sfn;
2250
2251    cell->rachCfg.raOccasion.size = 0;
2252
2253    /* Update slot occasions */
2254    for(idx = 0; idx < cellCfg->prachRscInfo.numRsc; idx++)
2255    {
2256       if(cellCfg->prachRscInfo.prachInfo[idx].freqIdx == 0)
2257       {
2258          if(cellCfg->prachRscInfo.prachInfo[idx].halfFrm == 0)
2259          {
2260             splFrm = 1;
2261          }
2262          else
2263          {
2264             splFrm = 6;
2265          }
2266          if(cellCfg->prachRscInfo.prachInfo[idx].ulStartSfIdx ==
2267                                                 RGR_TDD_SPL_UL_IDX)
2268          {
2269             subfrmIdx = cell->rachCfg.raOccasion.size;
2270             cell->rachCfg.raOccasion.slotNum[subfrmIdx] = splFrm;
2271             cell->rachCfg.raOccasion.size++;
2272          }
2273          else
2274          {
2275             rgSCHUtlUpdPrachOcc(cell,
2276                   &cellCfg->prachRscInfo.prachInfo[idx]);
2277          }
2278       }
2279    }
2280    return;
2281 }
2282
2283 /**
2284  * @brief This function performs RGR cell initialization
2285  *
2286  * @details
2287  *
2288  *     Function: rgSCHUtlRgrCellCfg
2289  *     Purpose:  This function initialises the cell with RGR configuration
2290  *               and slot related initialization.
2291  *
2292  *     Invoked by: Scheduler
2293  *
2294  *  @param[in]  RgSchCellCb       *cell
2295  *  @param[in]  RgrCellCfg        *cellCfg
2296  *  @param[in]  RgSchErrInfo      *errInfo
2297  *  @return     Void
2298  *
2299  **/
2300 #ifdef ANSI
2301 S16 rgSCHUtlRgrCellCfg
2302 (
2303 RgSchCellCb       *cell,
2304 RgrCellCfg        *cellCfg,
2305 RgSchErrInfo      *errInfo
2306 )
2307 #else
2308 S16 rgSCHUtlRgrCellCfg(cell, cellCfg, errInfo)
2309 RgSchCellCb       *cell;
2310 RgrCellCfg        *cellCfg;
2311 RgSchErrInfo      *errInfo;
2312 #endif
2313 {
2314    uint8_t         i;
2315    uint8_t         sfn=0;
2316    uint8_t         sfNum = 0;
2317    RgSchDlSf       *sf;
2318    CmLteTimingInfo frm;
2319    uint8_t         ulDlCfgIdx = cellCfg->ulDlCfgIdx;
2320    uint8_t         maxslots ;
2321    uint8_t         maxDlslots;
2322    S16             ret = ROK;
2323    uint16_t        bw;         /*!< Number of RBs in the cell */
2324    
2325    memset(&frm,0,sizeof(CmLteTimingInfo));
2326
2327    /* ccpu00132657-MOD- Determining DLSF array size independent of DELTAS */
2328    maxDlslots = rgSchTddNumDlSubfrmTbl[ulDlCfgIdx][RGSCH_NUM_SUB_FRAMES-1];
2329    maxslots = 2 * maxDlslots;
2330    cell->numDlSubfrms = maxslots;
2331 /* ACC-TDD <ccpu00130639> */
2332    cell->tddHqSfnCycle = -1;
2333    cell->ulDlCfgIdx = ulDlCfgIdx;
2334
2335    /* PRACH Occasions Initialization */
2336    rgSCHUtlPrachCfgInit(cell, cellCfg);
2337
2338    /* ccpu00132658- Moved out of below for loop since the updating rbgSize and 
2339     * bw are independent of sfNum*/
2340    /* determine the RBG size and no of RBGs for the configured
2341     * DL BW */
2342    if (cell->bwCfg.dlTotalBw > 63)
2343    {
2344       cell->rbgSize  = 4;
2345    }
2346    else if (cell->bwCfg.dlTotalBw > 26)
2347    {
2348       cell->rbgSize  = 3;
2349    }
2350    else if (cell->bwCfg.dlTotalBw > 10)
2351    {
2352       cell->rbgSize  = 2;
2353    }
2354    else
2355    {
2356       cell->rbgSize  = 1;
2357    }
2358    cell->noOfRbgs = RGSCH_CEIL(cell->bwCfg.dlTotalBw, cell->rbgSize);
2359
2360    bw    = cell->bwCfg.dlTotalBw;
2361
2362    rgSCHUtlAllocSBuf(cell->instIdx,
2363                (Data **)&cell->subFrms, sizeof(RgSchDlSf *) * maxslots);
2364    if (cell->subFrms == NULLP)
2365    {
2366       return RFAILED;
2367    }
2368
2369    /* Create memory for each frame. */
2370    for(i = 0; i < maxslots; i++)
2371    {
2372       while(rgSchTddUlDlSubfrmTbl[ulDlCfgIdx][sfNum] ==
2373             RG_SCH_TDD_UL_slot)
2374       {
2375          sfNum = (sfNum+1) % RGSCH_NUM_SUB_FRAMES;
2376       }
2377
2378       rgSCHUtlAllocSBuf(cell->instIdx, (Data **)&sf, sizeof(RgSchDlSf));
2379       if (sf == NULLP)
2380       {
2381          break;
2382       }
2383       memset(sf, 0, sizeof(*sf));
2384
2385 #ifdef LTE_ADV
2386       if (ROK != rgSCHLaaInitDlSfCb(cell, sf))
2387       {
2388          break;
2389       }
2390 #endif
2391       sf->sfNum = sfNum;
2392       sf->bw    = bw;
2393 #ifdef LTEMAC_SPS
2394    /* Mark SPS bandwidth to be occupied */
2395    sf->bwAlloced = ((cellCfg->spsCfg.maxSpsDlBw +
2396       cell->rbgSize - 1)/cell->rbgSize) * cell->rbgSize;
2397    sf->spsAllocdBw = 0;
2398    sf->type2End = sf->bwAlloced/cell->rbgSize;
2399 #else
2400    sf->bwAlloced = 0;
2401    /* Fix for ccpu00123918*/
2402    sf->type2Start = 0;
2403 #endif /* LTEMAC_SPS */
2404       /* Initialize the ackNakRepQ here */
2405 #ifdef RG_MAC_MEASGAP
2406       cmLListInit (&(sf->ackNakRepQ));
2407 #endif
2408       cell->subFrms[i] = sf;
2409       sfNum = (sfNum+1) % RGSCH_NUM_SUB_FRAMES;
2410    }
2411    if (i != maxslots)
2412    {
2413       for (; i > 0; i--)
2414       {
2415          /* ccpu00117052 - MOD - Passing double pointer
2416          for proper NULLP assignment*/
2417          rgSCHUtlFreeSBuf(cell->instIdx,
2418                (Data **)(&(cell->subFrms[i-1])), sizeof(RgSchDlSf));
2419 #ifdef LTE_ADV
2420          rgSCHLaaDeInitDlSfCb(cell, sf);
2421 #endif
2422       }
2423       /* ccpu00117052 - MOD - Passing double pointer
2424       for proper NULLP assignment*/
2425       rgSCHUtlFreeSBuf(cell->instIdx,
2426             (Data **)(&(cell->subFrms)), sizeof(RgSchDlSf *) * maxslots);
2427
2428       return RFAILED;
2429    }
2430
2431    if (cell->sc.apis == NULLP)
2432    {
2433       cell->sc.apis = &rgSchCmnApis;
2434    }
2435    ret = cell->sc.apis->rgSCHRgrCellCfg(cell, cellCfg, errInfo);
2436
2437    if (ret != ROK)
2438    {
2439       /* ccpu00132286- Removed deletion of sf nodes as the deletion will be 
2440        * happening during CellDelete. Added return handling to provide negative
2441        * confirm*/
2442       return (ret);
2443    }
2444
2445    /* Release the slots and thereby perform the initialization */
2446    for (i = 0; i < maxslots; i++)
2447    {
2448      if((i > 0) && (i%maxDlslots == 0))
2449      {
2450       sfn++;
2451      }
2452      frm.sfn = sfn;
2453      frm.slot = cell->subFrms[i]->sfNum;
2454      rgSCHUtlDlRlsSubFrm(cell, frm);
2455    }
2456
2457    return (ret);
2458 }
2459
2460 #else
2461 \f
2462 /**
2463  * @brief This function performs scheduler related cell creation
2464  *
2465  * @details
2466  *
2467  *     Function: rgSCHUtlRgrCellCfg
2468  *     Purpose:  This function creates the slots needed for the
2469  *               cell. It then peforms init of the scheduler by calling
2470  *               scheduler specific cell init function.
2471  *
2472  *     Invoked by: Scheduler
2473  *
2474  *  @param[in]  RgSchCellCb          *cell
2475  *  @param[in]  RgrCellCfg        *cellCfg
2476  *  @param[in]  RgSchErrInfo         *errInfo
2477  *  @return     Void
2478  *
2479  **/
2480 #ifdef ANSI
2481 S16 rgSCHUtlRgrCellCfg
2482 (
2483 RgSchCellCb       *cell,
2484 RgrCellCfg        *cellCfg,
2485 RgSchErrInfo      *errInfo
2486 )
2487 #else
2488 S16 rgSCHUtlRgrCellCfg(cell, cellCfg, errInfo)
2489 RgSchCellCb       *cell;
2490 RgrCellCfg        *cellCfg;
2491 RgSchErrInfo      *errInfo;
2492 #endif
2493 {
2494    uint8_t         i;
2495    RgSchDlSf       *sf;
2496    CmLteTimingInfo frm;
2497    S16             ret;
2498    Inst            inst = cell->instIdx;
2499    /* LTE_ADV_FLAG_REMOVED_START */
2500    uint16_t        len;
2501    len = (uint16_t)((cell->bwCfg.dlTotalBw % 8 == 0) ? (cell->bwCfg.dlTotalBw/8) : (cell->bwCfg.dlTotalBw/8 + 1)); /*KW fix for LTE_ADV */
2502    /* LTE_ADV_FLAG_REMOVED_END */
2503
2504    memset(&frm,0,sizeof(CmLteTimingInfo));
2505
2506    /* determine the RBG size and no of RBGs for the configured
2507     * DL BW */
2508    if (cell->bwCfg.dlTotalBw > 63)
2509    {
2510       cell->rbgSize  = 4;
2511    }
2512    else if (cell->bwCfg.dlTotalBw > 26)
2513    {
2514       cell->rbgSize  = 3;
2515    }
2516    else if (cell->bwCfg.dlTotalBw > 10)
2517    {
2518       cell->rbgSize  = 2;
2519    }
2520    else
2521    {
2522       cell->rbgSize  = 1;
2523    }
2524    cell->noOfRbgs = RGSCH_CEIL(cell->bwCfg.dlTotalBw, cell->rbgSize);
2525    /* Create memory for each frame. */
2526    /* Changing loop limit from
2527       RGSCH_NUM_SUB_FRAMES to RGSCH_NUM_DL_slotS */
2528    for(i = 0; i < RGSCH_NUM_DL_slotS; i++)
2529    {
2530       rgSCHUtlAllocSBuf(inst, (Data **)&sf, sizeof(RgSchDlSf));
2531       if (sf == NULLP)
2532       {
2533          break;
2534       }
2535       memset(sf, 0, sizeof(*sf));
2536
2537 #ifdef LTE_ADV
2538       if (ROK != rgSCHLaaInitDlSfCb(cell, sf))
2539       {
2540          break;
2541       }
2542 #endif
2543       /* Doing MOD operation before assigning value of i */
2544       sf->sfNum = i % RGSCH_NUM_SUB_FRAMES;
2545       sf->bw    = cell->bwCfg.dlTotalBw;
2546       /* Initialize the ackNakRepQ here */
2547 #ifdef RG_MAC_MEASGAP
2548       cmLListInit (&(sf->ackNakRepQ));
2549 #endif
2550       cell->subFrms[i] = sf;
2551       /* LTE_ADV_FLAG_REMOVED_START */
2552       if (cell->lteAdvCb.dsfrCfg.status == RGR_ENABLE)
2553       {
2554          /*initialize the RNTP Buffer*/
2555          if(rgSchDSFRRntpInfoInit(&sf->rntpInfo, cell, sf->bw))
2556          {
2557             return RFAILED; 
2558          }
2559       }
2560
2561       if (cell->lteAdvCb.sfrCfg.status == RGR_ENABLE)
2562       {
2563          /*initialise the pools of CC and CE*/
2564          if(rgSchSFRTotalPoolInit(cell, sf))
2565          {
2566             return RFAILED; 
2567          }
2568       }
2569       /* LTE_ADV_FLAG_REMOVED_END */
2570    }
2571
2572    /* LTE_ADV_FLAG_REMOVED_START */
2573    /* Allocate memory for "scheduled UE" Info */
2574    if (cell->lteAdvCb.dsfrCfg.status == RGR_ENABLE)
2575    {    
2576       if((rgSCHUtlAllocSBuf(inst, (Data**)&(cell->rntpAggrInfo.val),
2577                   (len * sizeof(uint8_t)))) != ROK)
2578       {
2579          RLOG_ARG0(L_ERROR,DBG_CELLID,cell->cellId,"Memory allocation FAILED for RNTP Alloc");
2580          return RFAILED;
2581       }
2582       cell->rntpAggrInfo.pres = PRSNT_NODEF;
2583       cell->rntpAggrInfo.len  = len;
2584    }     
2585    /* LTE_ADV_FLAG_REMOVED_END */
2586
2587    /* Changing loop limit from
2588       RGSCH_NUM_SUB_FRAMES to RGSCH_NUM_DL_slotS */
2589    if (i != RGSCH_NUM_DL_slotS)
2590    {
2591       for (; i > 0; i--)
2592       {
2593          /* ccpu00117052 - MOD - Passing double pointer
2594          for proper NULLP assignment*/
2595          rgSCHUtlFreeSBuf(inst, (Data **)(&(cell->subFrms[i-1])),
2596                sizeof(RgSchDlSf));
2597 #ifdef LTE_ADV
2598          rgSCHLaaDeInitDlSfCb(cell, sf);
2599 #endif
2600       }
2601       return RFAILED;
2602    }
2603
2604    if (cell->sc.apis == NULLP)
2605    {
2606       cell->sc.apis = &rgSchCmnApis;
2607    }
2608
2609    /* Release the slots and thereby perform the initialization */
2610    for (i = 0; i < RGSCH_NUM_DL_slotS; i++)
2611    {
2612       if (i >= RGSCH_NUM_SUB_FRAMES)
2613       {
2614          /* [ccpu00123828]-MOD-The below statement sfn += 1incorrectly modified
2615           * the value of sfn for i>=10 thru 19. Correct way is to assign
2616           it to one */
2617          frm.sfn = 1;
2618       }
2619       frm.slot = i % RGSCH_NUM_SUB_FRAMES;
2620       rgSCHUtlDlRlsSubFrm(cell, frm);
2621    }
2622
2623    ret = cell->sc.apis->rgSCHRgrCellCfg(cell, cellCfg, errInfo);
2624    if (ret != ROK)
2625    {
2626       errInfo->errCause = RGSCHERR_SCH_CFG;
2627       return RFAILED;
2628    }
2629 #ifdef EMTC_ENABLE
2630       if(cell->emtcEnable)
2631       {
2632          /* TODO: Repetition framework in RGR and APP */
2633          if (rgSCHUtlEmtcResMngmtInit(
2634                   cell, 
2635                   RGSCH_IOT_PDSCH_POOLSZ, RGSCH_IOT_PDSCH_DELTA, cellCfg->bwCfg.dlTotalBw,
2636                   RGSCH_IOT_PUSCH_POOLSZ, RGSCH_IOT_PUSCH_DELTA, RGSCH_IOT_PUSCH_MAXFREQSZ,
2637                   RGSCH_IOT_PUCCH_POOLSZ, RGSCH_IOT_PUCCH_DELTA, RGSCH_IOT_PUCCH_MAXFREQSZ) != ROK)
2638          {
2639             errInfo->errCause = RGSCHERR_SCH_CFG;
2640             return RFAILED;
2641          }
2642       }
2643 #endif
2644
2645    return (ret);
2646 }
2647 #endif
2648
2649 \f
2650 /**
2651  * @brief This function performs the cell reconfiguration at RGR interface
2652  *
2653  * @details
2654  *
2655  *     Function: rgSCHUtlRgrCellRecfg
2656  *     Purpose:  This function updates the reconfigurable parameters
2657  *               on the cell control block for the scheduler.
2658  *
2659  *     Invoked by: Scheduler
2660  *
2661  *  @param[in]  RgSchCellCb          *cell
2662  *  @param[in]  RgrCellCfg        *cellCfg
2663  *  @param[in]  RgSchErrInfo         *errInfo
2664  *  @return     Void
2665  *
2666  **/
2667 #ifdef ANSI
2668 S16 rgSCHUtlRgrCellRecfg
2669 (
2670 RgSchCellCb       *cell,
2671 RgrCellRecfg      *recfg,
2672 RgSchErrInfo      *err
2673 )
2674 #else
2675 S16 rgSCHUtlRgrCellRecfg(cell, recfg, err)
2676 RgSchCellCb       *cell;
2677 RgrCellRecfg      *recfg;
2678 RgSchErrInfo      *err;
2679 #endif
2680 {
2681    return (cell->sc.apis->rgSCHRgrCellRecfg(cell, recfg, err));
2682 }
2683
2684
2685 \f
2686 /**
2687  * @brief This function returns the Y value of UE for a sub frame
2688  *
2689  * @details
2690  *
2691  *     Function: rgSCHUtlFreeCell
2692  *     Purpose:  This function updates the value of Y stored in the
2693  *               UE control block. It uses the previously computed
2694  *               value for computing for this slot.
2695  *
2696  *     Invoked by: Scheduler
2697  *
2698  *  @param[in]  RgSchCellCb          *cell
2699  *  @return     Void
2700  *
2701  **/
2702 #ifdef ANSI
2703 S16 rgSCHUtlFreeCell
2704 (
2705 RgSchCellCb          *cell
2706 )
2707 #else
2708 S16 rgSCHUtlFreeCell(cell)
2709 RgSchCellCb          *cell;
2710 #endif
2711 {
2712    uint8_t          i;
2713    CmLListCp        *lst;
2714    RgSchPdcch       *pdcch;
2715    RgSchPdcchInfo   *pdcchInfo;
2716    RgSchPhichInfo   *phichInfo;
2717    RgSchPhich       *phich;
2718    Inst             inst = cell->instIdx;
2719    uint8_t          maxslots;
2720 #ifdef LTE_TDD
2721    RgSchRaReqInfo *raReqInfo;
2722    uint8_t         idx;
2723 #endif
2724
2725 #ifdef LTE_TDD
2726    maxslots = cell->numDlSubfrms;
2727 #else
2728    maxslots = RGSCH_NUM_DL_slotS;
2729 #endif
2730
2731
2732    /* Invoke the index for scheduler, cell deletion */
2733    cell->sc.apis->rgSCHFreeCell(cell);
2734
2735    /* Release the slots allocated               */
2736    for (i = 0; i < maxslots; i++)
2737    {
2738 #ifdef LTE_ADV
2739       rgSCHLaaDeInitDlSfCb(cell, cell->subFrms[i]);
2740 #endif
2741       pdcchInfo = &cell->subFrms[i]->pdcchInfo;
2742       /* ccpu00117052 - MOD - Passing double pointer
2743       for proper NULLP assignment*/
2744       rgSCHUtlFreeSBuf(inst, (Data **)(&(pdcchInfo->map)),
2745             (pdcchInfo->nCce + 7) >> 3);
2746       while (pdcchInfo->pdcchs.first != NULLP)
2747       {
2748          pdcch = (RgSchPdcch *)pdcchInfo->pdcchs.first->node;
2749          cmLListDelFrm(&pdcchInfo->pdcchs, pdcchInfo->pdcchs.first);
2750       /* ccpu00117052 - MOD - Passing double pointer
2751       for proper NULLP assignment*/
2752          rgSCHUtlFreeSBuf(inst, (Data **)&pdcch, sizeof(RgSchPdcch));
2753       }
2754
2755       phichInfo = &cell->subFrms[i]->phichInfo;
2756       while(phichInfo->phichs.first != NULLP)
2757       {
2758          phich = (RgSchPhich *)phichInfo->phichs.first->node;
2759          cmLListDelFrm(&phichInfo->phichs, phichInfo->phichs.first);
2760          RGSCH_PHICH_FREE(inst, phich, sizeof(RgSchPhich));
2761       }
2762
2763       /* LTE_ADV_FLAG_REMOVED_START */
2764       /*releasing SFR pool entries*/
2765       rgSchSFRTotalPoolFree(&cell->subFrms[i]->sfrTotalPoolInfo, cell);
2766
2767       /*releasing dsfr rntp pattern info*/
2768       rgSchDSFRRntpInfoFree(&cell->subFrms[i]->rntpInfo, cell, 
2769                                        cell->bwCfg.dlTotalBw);
2770       /* LTE_ADV_FLAG_REMOVED_END */
2771
2772       /* ccpu00117052 - MOD - Passing double pointer
2773       for proper NULLP assignment*/
2774       rgSCHUtlFreeSBuf(inst, (Data **)(&(cell->subFrms[i])), sizeof(RgSchDlSf));
2775    }
2776 #ifdef LTE_TDD
2777    /* Release the slot pointers */
2778    /* ccpu00117052 - MOD - Passing double pointer
2779    for proper NULLP assignment*/
2780    rgSCHUtlFreeSBuf(inst,
2781          (Data **) (&(cell->subFrms)), sizeof(RgSchDlSf *) * maxslots);
2782
2783    for(idx=0; idx < cell->raInfo.lstSize; idx++)
2784    {
2785       lst = &cell->raInfo.raReqLst[idx];
2786       while (lst->first != NULLP)
2787       {
2788          raReqInfo = (RgSchRaReqInfo *)lst->first->node;
2789          cmLListDelFrm(lst, &raReqInfo->raReqLstEnt);
2790          /* ccpu00117052 - MOD - Passing double pointer
2791          for proper NULLP assignment*/
2792          rgSCHUtlFreeSBuf(inst,(Data **)&raReqInfo, sizeof(RgSchRaReqInfo));
2793       }
2794    }
2795    /* ccpu00117052 - MOD - Passing double pointer
2796    for proper NULLP assignment*/
2797    rgSCHUtlFreeSBuf(inst,
2798          (Data **)(&(cell->raInfo.raReqLst)),
2799             sizeof(CmLListCp) * (cell->raInfo.lstSize));
2800 #endif
2801
2802    /* Release allocated pdcchs */
2803    lst = &cell->pdcchLst;
2804    while (lst->first != NULLP)
2805    {
2806       pdcch = (RgSchPdcch *)lst->first->node;
2807       cmLListDelFrm(lst, &pdcch->lnk);
2808 #ifdef EMTC_ENABLE
2809       if(cell->emtcEnable)
2810       {
2811          rgSCHEmtcPdcchFree(cell, pdcch);
2812          rgSCHUtlEmtcResMngmtDeinit(cell);
2813       }
2814 #endif
2815       /* ccpu00117052 - MOD - Passing double pointer
2816       for proper NULLP assignment*/
2817       rgSCHUtlFreeSBuf(inst,(Data **)&pdcch, sizeof(RgSchPdcch));
2818    }
2819 #ifdef LTE_ADV
2820    rgSCHLaaFreeLists(cell);
2821 #endif
2822
2823    /* LTE_ADV_FLAG_REMOVED_START */
2824    /* releasing RNTP Aggregation Info from CellCb*/
2825    rgSchDSFRRntpInfoFree(&cell->rntpAggrInfo, cell, cell->bwCfg.dlTotalBw);
2826    /* LTE_ADV_FLAG_REMOVED_END */
2827
2828    return ROK;
2829 }
2830
2831 \f
2832 /**
2833  * @brief This function adds the UE to scheduler
2834  *
2835  * @details
2836  *
2837  *     Function: rgSCHUtlRgrUeCfg
2838  *     Purpose:  This function performs addition of UE to scheduler
2839  *               1. First, it updates the Y table in the UE
2840  *               2. Then, it calls the scheduler's handler for UE addition
2841  *
2842  *     Invoked by: Scheduler
2843  *
2844  *  @param[in]  RgSchCellCb          *cell
2845  *  @param[in]  RgSchUeCb            *ue
2846  *  @param[in]  RgrUeCfg             *cfg
2847  *  @param[in]  RgSchErrInfo            *err
2848  *  @return     S16
2849  *
2850  **/
2851 #ifdef ANSI
2852 S16 rgSCHUtlRgrUeCfg
2853 (
2854 RgSchCellCb                *cell,
2855 RgSchUeCb                  *ue,
2856 RgrUeCfg                   *cfg,
2857 RgSchErrInfo               *err
2858 )
2859 #else
2860 S16 rgSCHUtlRgrUeCfg(cell, ue, cfg, err)
2861 RgSchCellCb                *cell;
2862 RgSchUeCb                  *ue;
2863 RgrUeCfg                   *cfg;
2864 RgSchErrInfo               *err;
2865 #endif
2866 {
2867
2868    /* Assign TM 1 as UE's default TM */
2869    ue->mimoInfo.txMode = RGR_UE_TM_1;
2870    ue->txModeTransCmplt = TRUE;
2871    cmInitTimers(&ue->txModeTransTmr, 1);
2872    if (cfg->txMode.pres == PRSNT_NODEF)
2873    {
2874       /* DL MU-MIMO not supported */
2875       if (cfg->txMode.txModeEnum == RGR_UE_TM_5)
2876       {
2877          err->errCause = RGSCHERR_SCH_CFG;
2878          return RFAILED;
2879       }
2880       ue->mimoInfo.txMode = cfg->txMode.txModeEnum;
2881    }
2882    ue->ul.ulTxAntSel = cfg->ulTxAntSel;
2883    ue->mimoInfo.cdbkSbstRstrctn = cfg->ueCodeBookRstCfg;
2884 #ifdef TFU_UPGRADE
2885    ue->ueCatEnum = cfg->ueCatEnum;
2886    if ((cfg->puschDedCfg.bACKIdx > 15) ||
2887        (cfg->puschDedCfg.bCQIIdx > 15) ||
2888        (cfg->puschDedCfg.bRIIdx > 15))
2889    {
2890       err->errCause = RGSCHERR_SCH_CFG;
2891       return RFAILED;
2892    }
2893    ue->ul.betaHqOffst = cfg->puschDedCfg.bACKIdx;
2894    ue->ul.betaCqiOffst = cfg->puschDedCfg.bCQIIdx;
2895    ue->ul.betaRiOffst = cfg->puschDedCfg.bRIIdx;
2896 #endif
2897    ue->csgMmbrSta = cfg->csgMmbrSta;
2898 #ifdef RG_PFS_STATS
2899    memset(&ue->pfsStats, 0, sizeof(RgSchPfsStats));
2900 #endif
2901    /* Call the handler of the scheduler based on cell configuration */
2902    return (cell->sc.apis->rgSCHRgrUeCfg(cell, ue, cfg, err));
2903 }
2904 /* Start : LTEMAC_2.1_DEV_CFG */
2905 \f
2906 /**
2907  * @brief This function adds a service to scheduler
2908  *
2909  * @details
2910  *
2911  *     Function: rgSCHUtlRgrLcCfg
2912  *     Purpose:  This function performs addition of service to scheduler
2913  *               The addition is performed for each direction based
2914  *               the direction field of the configuration
2915  *
2916  *     Invoked by: Scheduler
2917  *
2918  *  @param[in]  RgSchCellCb          *cell
2919  *  @param[in]  RgSchUeCb            *ue
2920  *  @param[in]  RgSchDlLcCb          *dlLc
2921  *  @param[in]  RgrLchCfg            *cfg
2922  *  @param[in]  RgSchErrInfo         *err
2923  *  @return     S16
2924  *
2925  **/
2926 #ifdef ANSI
2927 S16 rgSCHUtlRgrLcCfg
2928 (
2929 RgSchCellCb                *cell,
2930 RgSchUeCb                  *ue,
2931 RgSchDlLcCb                *dlLc,
2932 RgrLchCfg               *cfg,
2933 RgSchErrInfo               *errInfo
2934 )
2935 #else
2936 S16 rgSCHUtlRgrLcCfg(cell, ue, dlLc, cfg, errInfo)
2937 RgSchCellCb                *cell;
2938 RgSchUeCb                  *ue;
2939 RgSchDlLcCb                *dlLc;
2940 RgrLchCfg               *cfg;
2941 RgSchErrInfo               *errInfo;
2942 #endif
2943 {
2944    return (cell->sc.apis->rgSCHRgrLchCfg(cell, ue, dlLc, cfg, errInfo));
2945 }
2946
2947 \f
2948 /**
2949  * @brief This function modifies a service to scheduler
2950  *
2951  * @details
2952  *
2953  *     Function: rgSCHUtlRgrLcRecfg
2954  *     Purpose:  This function performs modification of a service in
2955  *               scheduler. The modification is performed for each direction
2956  *               based the direction field of the configuration
2957  *
2958  *     Invoked by: Scheduler
2959  *
2960  *  @param[in]  RgSchCellCb          *cell
2961  *  @param[in]  RgSchUeCb            *ue
2962  *  @param[in]  RgSchDlLcCb          *dlLc
2963  *  @param[in]  RgrLchRecfg          *recfg
2964  *  @param[in]  RgSchErrInfo         *err
2965  *  @return     S16
2966  *
2967  **/
2968 #ifdef ANSI
2969 S16 rgSCHUtlRgrLcRecfg
2970 (
2971 RgSchCellCb                *cell,
2972 RgSchUeCb                  *ue,
2973 RgSchDlLcCb                *dlLc,
2974 RgrLchRecfg                *recfg,
2975 RgSchErrInfo               *err
2976 )
2977 #else
2978 S16 rgSCHUtlRgrLcRecfg(cell, ue, dlLc, recfg, err)
2979 RgSchCellCb                *cell;
2980 RgSchUeCb                  *ue;
2981 RgSchDlLcCb                *dlLc;
2982 RgrLchRecfg                *recfg;
2983 RgSchErrInfo               *err;
2984 #endif
2985 {
2986    return (cell->sc.apis->rgSCHRgrLchRecfg(cell, ue, dlLc, recfg, err));
2987 }
2988
2989 /**
2990  * @brief This function deletes a Lc in scheduler
2991  *
2992  * @details
2993  *
2994  *     Function: rgSCHUtlRgrLcDel
2995  *     Purpose:  This function performs deletion of Lc in scheduler
2996  *
2997  *     Invoked by: Scheduler
2998  *
2999  *  @param[in]  RgSchCellCb   *cell
3000  *  @param[in]  RgSchUeCb     *ue
3001  *  @param[in]  CmLteLcId     lcId
3002  *  @param[in]  uint8_t            lcgId
3003  *  @return     S16
3004  *
3005  **/
3006 #ifdef ANSI
3007 S16 rgSCHUtlRgrLcDel
3008 (
3009 RgSchCellCb                *cell,
3010 RgSchUeCb                  *ue,
3011 CmLteLcId                  lcId,
3012 uint8_t                    lcgId
3013 )
3014 #else
3015 S16 rgSCHUtlRgrLcDel(cell, ue, lcId, lcgId)
3016 RgSchCellCb                *cell;
3017 RgSchUeCb                  *ue;
3018 CmLteLcId                  lcId;
3019 uint8_t                    lcgId;
3020 #endif
3021 {
3022    cell->sc.apis->rgSCHRgrLchDel(cell, ue, lcId, lcgId);
3023
3024    return  (ROK);
3025 } /* rgSCHUtlRgrLcDel */
3026
3027 /**
3028  * @brief This function adds a service to scheduler
3029  *
3030  * @details
3031  *
3032  *     Function: rgSCHUtlRgrLcgCfg
3033  *     Purpose:  This function performs addition of service to scheduler
3034  *               The addition is performed for each direction based
3035  *               the direction field of the configuration
3036  *
3037  *     Invoked by: Scheduler
3038  *
3039  *  @param[in]  RgSchCellCb          *cell
3040  *  @param[in]  RgSchUeCb            *ue
3041  *  @param[in]  RgrLchCfg            *cfg
3042  *  @param[in]  RgSchErrInfo         *err
3043  *  @return     S16
3044  *
3045  **/
3046 #ifdef ANSI
3047 S16 rgSCHUtlRgrLcgCfg
3048 (
3049 RgSchCellCb                *cell,
3050 RgSchUeCb                  *ue,
3051 RgrLcgCfg               *cfg,
3052 RgSchErrInfo               *errInfo
3053 )
3054 #else
3055 S16 rgSCHUtlRgrLcgCfg(cell, ue, cfg, errInfo)
3056 RgSchCellCb                *cell;
3057 RgSchUeCb                  *ue;
3058 RgrLcgCfg               *cfg;
3059 RgSchErrInfo               *errInfo;
3060 #endif
3061 {
3062    return (cell->sc.apis->rgSCHRgrLcgCfg(cell, ue, &(ue->ul.lcgArr[cfg->ulInfo.lcgId]), cfg, errInfo));
3063 }
3064
3065 \f
3066 /**
3067  * @brief This function modifies a service to scheduler
3068  *
3069  * @details
3070  *
3071  *     Function: rgSCHUtlRgrLcgRecfg
3072  *     Purpose:  This function performs modification of a service in
3073  *               scheduler. The modification is performed for each direction
3074  *               based the direction field of the configuration
3075  *
3076  *     Invoked by: Scheduler
3077  *
3078  *  @param[in]  RgSchCellCb          *cell
3079  *  @param[in]  RgSchUeCb            *ue
3080  *  @param[in]  RgrLcgRecfg          *recfg
3081  *  @param[in]  RgSchErrInfo         *err
3082  *  @return     S16
3083  *
3084  **/
3085 #ifdef ANSI
3086 S16 rgSCHUtlRgrLcgRecfg
3087 (
3088 RgSchCellCb                *cell,
3089 RgSchUeCb                  *ue,
3090 RgrLcgRecfg                *recfg,
3091 RgSchErrInfo               *err
3092 )
3093 #else
3094 S16 rgSCHUtlRgrLcgRecfg(cell, ue, recfg, err)
3095 RgSchCellCb                *cell;
3096 RgSchUeCb                  *ue;
3097 RgrLcgRecfg                *recfg;
3098 RgSchErrInfo               *err;
3099 #endif
3100 {
3101    return (cell->sc.apis->rgSCHRgrLcgRecfg(cell, ue, &(ue->ul.lcgArr[recfg->ulRecfg.lcgId]), recfg, err));
3102 } /* rgSCHUtlRgrLcRecfg */
3103
3104 /**
3105  * @brief This function modifies a service to scheduler
3106  *
3107  * @details
3108  *
3109  *     Function: rgSCHUtlRgrLcgDel
3110  *     Purpose:  This function performs modification of a service in
3111  *               scheduler. The modification is performed for each direction
3112  *               based the direction field of the configuration
3113  *
3114  *     Invoked by: Scheduler
3115  *
3116  *  @param[in]  RgSchCellCb   *cell
3117  *  @param[in]  RgSchUeCb     *ue
3118  *  @param[in]  RgrDel        *lcDelInfo
3119  *  @return     S16
3120  *
3121  **/
3122 #ifdef ANSI
3123 Void rgSCHUtlRgrLcgDel
3124 (
3125 RgSchCellCb                *cell,
3126 RgSchUeCb                  *ue,
3127 uint8_t                    lcgId
3128 )
3129 #else
3130 Void rgSCHUtlRgrLcgDel(cell, ue, lcgId)
3131 RgSchCellCb                *cell;
3132 RgSchUeCb                  *ue;
3133 uint8_t                    lcgId;
3134 #endif
3135 {
3136    cell->sc.apis->rgSCHFreeLcg(cell, ue, &ue->ul.lcgArr[lcgId]);
3137
3138   /* Stack Crash problem for TRACE5 changes. added the return below . */
3139  return;
3140
3141 } /* rgSCHUtlRgrLcgDel */
3142
3143
3144 /* End: LTEMAC_2.1_DEV_CFG */
3145
3146 /**
3147  * @brief This function is a wrapper to call scheduler specific API.
3148  *
3149  * @details
3150  *
3151  *     Function: rgSCHUtlDoaInd
3152  *     Purpose:  Updates the DOA for the UE
3153  *
3154  *     Invoked by: TOM
3155  *
3156  *  @param[in]  RgSchCellCb        *cell
3157  *  @param[in]  RgSchUeCb          *ue
3158  *  @param[in]  TfuDoaRpt          *doaRpt
3159  *  @return  Void
3160  *
3161  **/
3162 #ifdef ANSI
3163 Void  rgSCHUtlDoaInd
3164 (
3165 RgSchCellCb        *cell,
3166 RgSchUeCb          *ue,
3167 TfuDoaRpt          *doaRpt
3168 )
3169 #else
3170 Void rgSCHUtlDoaInd(cell, ue, doaRpt)
3171 RgSchCellCb        *cell;
3172 RgSchUeCb          *ue;
3173 TfuDoaRpt          *doaRpt;
3174 #endif
3175 {
3176    ue->mimoInfo.doa.pres = PRSNT_NODEF;
3177    ue->mimoInfo.doa.val = doaRpt->doa;
3178    return;
3179 }
3180 \f
3181 /**
3182  * @brief This function is a wrapper to call scheduler specific API.
3183  *
3184  * @details
3185  *
3186  *     Function: rgSCHUtlDlCqiInd
3187  *     Purpose:  Updates the DL CQI for the UE
3188  *
3189  *     Invoked by: TOM
3190  *
3191  *  @param[in]  RgSchCellCb        *cell
3192  *  @param[in]  RgSchUeCb          *ue
3193  *  @param[in]  TfuDlCqiRpt        *dlCqiRpt
3194  *  @param[in]  CmLteTimingInfo    timingInfo
3195  *  @return  Void
3196  *
3197  **/
3198 #ifdef ANSI
3199 Void rgSCHUtlDlCqiInd
3200 (
3201 RgSchCellCb        *cell,
3202 RgSchUeCb          *ue,
3203 TfuDlCqiRpt        *dlCqiRpt,
3204 CmLteTimingInfo    timingInfo
3205 )
3206 #else
3207 Void rgSCHUtlDlCqiInd(cell, ue, dlCqiRpt, timingInfo)
3208 RgSchCellCb        *cell;
3209 RgSchUeCb          *ue;
3210 TfuDlCqiRpt        *dlCqiRpt;
3211 CmLteTimingInfo    timingInfo;
3212 #endif
3213 {
3214    RgSchCellCb        *sCellCb = NULLP;
3215    if (dlCqiRpt->isPucchInfo)
3216    {
3217       sCellCb = ue->cellInfo[dlCqiRpt->dlCqiInfo.pucchCqi.cellIdx]->cell;
3218       sCellCb->sc.apis->rgSCHDlCqiInd(sCellCb, ue, dlCqiRpt->isPucchInfo, \
3219             (Void *)&dlCqiRpt->dlCqiInfo.pucchCqi, timingInfo);
3220    }
3221    else
3222    {
3223       uint32_t idx;
3224       for (idx = 0; idx < dlCqiRpt->dlCqiInfo.pusch.numOfCells; idx++)
3225       {
3226          sCellCb = ue->cellInfo[dlCqiRpt->dlCqiInfo.pusch.puschCqi[idx].cellIdx]->cell;
3227          sCellCb->sc.apis->rgSCHDlCqiInd(sCellCb, ue, dlCqiRpt->isPucchInfo, \
3228                (Void *)&dlCqiRpt->dlCqiInfo.pusch.puschCqi[idx], timingInfo);
3229       }
3230    }
3231    return;
3232 }
3233
3234 \f
3235 #ifdef TFU_UPGRADE
3236 /**
3237  * @brief This function is a wrapper to call scheduler specific API.
3238  *
3239  * @details
3240  *
3241  *     Function: rgSCHUtlSrsInd
3242  *     Purpose:  Updates the UL SRS for the UE
3243  *
3244  *     Invoked by: TOM
3245  *
3246  *  @param[in]  RgSchCellCb        *cell
3247  *  @param[in]  RgSchUeCb          *ue
3248  *  @param[in]  TfuSrsRpt*     srsRpt
3249  *  @param[in]  CmLteTimingInfo    timingInfo
3250  *  @return  Void
3251  *
3252  **/
3253 #ifdef ANSI
3254 Void rgSCHUtlSrsInd
3255 (
3256 RgSchCellCb        *cell,
3257 RgSchUeCb          *ue,
3258 TfuSrsRpt          *srsRpt,
3259 CmLteTimingInfo    timingInfo
3260 )
3261 #else
3262 Void rgSCHUtlSrsInd(cell, ue, srsRpt, timingInfo)
3263 RgSchCellCb        *cell;
3264 RgSchUeCb          *ue;
3265 TfuSrsRpt        *srsRpt;
3266 CmLteTimingInfo    timingInfo;
3267 #endif
3268 {
3269    cell->sc.apis->rgSCHSrsInd(cell, ue, srsRpt, timingInfo);
3270    return;
3271 }
3272 #endif
3273
3274 /**
3275  * @brief This function is a wrapper to call scheduler specific API.
3276  *
3277  * @details
3278  *
3279  *     Function: rgSCHUtlDlTARpt
3280  *     Purpose:  Reports PHY TA for a UE.
3281  *
3282  *     Invoked by: TOM
3283  *
3284  *  @param[in]  RgSchCellCb        *cell
3285  *  @param[in]  RgSchUeCb          *ue
3286  *  @return  Void
3287  *
3288  **/
3289 #ifdef ANSI
3290 Void rgSCHUtlDlTARpt
3291 (
3292 RgSchCellCb        *cell,
3293 RgSchUeCb          *ue
3294 )
3295 #else
3296 Void rgSCHUtlDlTARpt(cell, ue)
3297 RgSchCellCb        *cell;
3298 RgSchUeCb          *ue;
3299 #endif
3300 {
3301    cell->sc.apis->rgSCHDlTARpt(cell, ue);
3302    return;
3303 }
3304
3305 \f
3306 /**
3307  * @brief This function is a wrapper to call scheduler specific API.
3308  *
3309  * @details
3310  *
3311  *     Function: rgSCHUtlDlRlsSubFrm
3312  *     Purpose:  Releases scheduler Information from DL SubFrm.
3313  *
3314  *     Invoked by: DHM
3315  *
3316  *  @param[in]   RgSchCellCb     *cell
3317  *  @param[out]  CmLteTimingInfo subFrm
3318  *  @return  Void
3319  *
3320  **/
3321 #ifdef ANSI
3322 Void rgSCHUtlDlRlsSubFrm
3323 (
3324 RgSchCellCb        *cell,
3325 CmLteTimingInfo    subFrm
3326 )
3327 #else
3328 Void rgSCHUtlDlRlsSubFrm(cell, subFrm)
3329 RgSchCellCb        *cell;
3330 CmLteTimingInfo    subFrm;
3331 #endif
3332 {
3333    cell->sc.apis->rgSCHDlRlsSubFrm(cell, subFrm);
3334    return;
3335 }
3336
3337 #ifdef TFU_UPGRADE
3338 /**
3339  * @brief This API is invoked to update the AperCQI trigger
3340  *        weight.
3341  *
3342  * @details
3343  *
3344  *     Function : rgSCHUtlUpdACqiTrigWt
3345  *              - If HqFdbk is ACK then add up weight corresponding
3346  *                to ACK to the AcqiTrigWt.
3347  *              - If HqFdbk is NACK then add up weight corresponding
3348  *                to NACK to the AcqiTrigWt.
3349  *              - If AcqiTrigWt crosses threshold then trigger
3350  *                grant req for APERCQI to SCH.
3351  *
3352  *  @param[in]  RgSchUeCb       *ue
3353  *  @param[in]  uint8_t              isAck 
3354  *
3355  *  @return Void
3356  **/
3357 #ifdef ANSI
3358 Void rgSCHUtlUpdACqiTrigWt
3359 (
3360 RgSchUeCb       *ue,
3361 RgSchUeCellInfo *cellInfo,
3362 uint8_t         isAck 
3363 )
3364 #else
3365 Void rgSCHUtlUpdACqiTrigWt(ue,cellInfo, isAck)
3366 RgSchUeCb       *ue;
3367 RgSchUeCellInfo *cellInfo;
3368 uint8_t          isAck; 
3369 #endif
3370 {
3371 #ifdef LTE_ADV
3372    uint8_t triggerSet  = 0;
3373    uint8_t sIdx        = 0;
3374 #endif
3375
3376    if (isAck == TFU_HQFDB_ACK)
3377    {
3378       cellInfo->acqiCb.aCqiTrigWt += RG_APER_CQI_ACK_WGT;
3379    }
3380    else
3381    {
3382       cellInfo->acqiCb.aCqiTrigWt += RG_APER_CQI_NACK_WGT;
3383    }
3384
3385    if (cellInfo->acqiCb.aCqiTrigWt > RG_APER_CQI_THRESHOLD_WGT)
3386    {
3387       RgSchCellCb  *cell = ue->cell;
3388       RgSchErrInfo unUsed;
3389
3390       if(ue->dl.reqForCqi)
3391       {
3392          /* Already one ACQI trigger procedure is going on
3393           * which is not yet satisfied. Delaying this request till
3394           * the previous is getting satisfied*/
3395          return;
3396       }
3397
3398      ue->dl.reqForCqi = TRUE;
3399 #ifdef LTE_ADV
3400       rgSchCmnSetCqiReqField(cellInfo,ue,&ue->dl.reqForCqi);
3401       //Reset aCqiTrigWt for all the serving cells for which we have triggered ACQI 
3402       rgSCHTomUtlGetTrigSet(cell, ue, ue->dl.reqForCqi, &triggerSet);
3403       for (sIdx = 0; sIdx < CM_LTE_MAX_CELLS; sIdx++)
3404       {
3405          /* The Aperiodic requested for SCell index sIdx */
3406          if ((triggerSet >> (7 - sIdx)) & 0x01)
3407          {
3408             /* The Aperiodic request for SCell index sIdx */
3409             ue->cellInfo[sIdx]->acqiCb.aCqiTrigWt = 0;
3410          }
3411       }
3412  
3413 #endif
3414       /* Force SCH to send UL grant by indicating fake SR.
3415        * If this UE already in UL SCH Qs this SR Ind will
3416        * be ignored */
3417       rgSCHUtlSrRcvd(cell, ue, cell->crntTime, &unUsed);
3418    }
3419
3420    return;
3421 }
3422 #endif
3423
3424 /**
3425  * @brief This API is invoked to indicate scheduler of a CRC indication.
3426  *
3427  * @details
3428  *
3429  *     Function : rgSCHUtlHdlUlTransInd
3430  *      This API is invoked to indicate scheduler of a CRC indication.
3431  *
3432  *  @param[in]  RgSchCellCb     *cell
3433  *  @param[in]  RgSchUeCb       *ue
3434  *  @param[in]  CmLteTimingInfo timingInfo
3435  *
3436  *  @return Void
3437  **/
3438 #ifdef ANSI
3439 Void rgSCHUtlHdlUlTransInd
3440 (
3441 RgSchCellCb     *cell,
3442 RgSchUeCb       *ue,
3443 CmLteTimingInfo timingInfo
3444 )
3445 #else
3446 Void rgSCHUtlHdlUlTransInd(cell, ue, timingInfo)
3447 RgSchCellCb     *cell;
3448 RgSchUeCb       *ue;
3449 CmLteTimingInfo timingInfo;
3450 #endif
3451 {
3452    cell->sc.apis->rgSCHHdlUlTransInd(cell, ue, timingInfo);
3453    return;
3454 }
3455 #ifdef LTEMAC_SPS
3456 /**
3457  * @brief This API is invoked to indicate scheduler of a CRC failure.
3458  *
3459  * @details
3460  *
3461  *     Function : rgSCHUtlHdlCrcInd
3462  *      This API is invoked to indicate CRC  to scheduler.
3463  *
3464  *  @param[in]  RgSchCellCb     *cell
3465  *  @param[in]  RgSchUeCb       *ue
3466  *  @param[in]  CmLteTimingInfo timingInfo
3467  *
3468  *  @return Void
3469  **/
3470 #ifdef ANSI
3471 Void rgSCHUtlHdlCrcInd
3472 (
3473 RgSchCellCb     *cell,
3474 RgSchUeCb       *ue,
3475 CmLteTimingInfo timingInfo
3476 )
3477 #else
3478 Void rgSCHUtlHdlCrcInd(cell, ue, timingInfo)
3479 RgSchCellCb     *cell;
3480 RgSchUeCb       *ue;
3481 CmLteTimingInfo timingInfo;
3482 #endif
3483 {
3484    cell->sc.apis->rgSCHUlCrcInd(cell, ue, timingInfo);
3485    return;
3486 } /* end of rgSCHUtlHdlCrcFailInd */
3487
3488 /**
3489  * @brief This API is invoked to indicate scheduler of a CRC failure.
3490  *
3491  * @details
3492  *
3493  *     Function : rgSCHUtlHdlCrcFailInd
3494  *      This API is invoked to indicate CRC failure to scheduler.
3495  *
3496  *  @param[in]  RgSchCellCb     *cell
3497  *  @param[in]  RgSchUeCb       *ue
3498  *  @param[in]  CmLteTimingInfo timingInfo
3499  *
3500  *  @return Void
3501  **/
3502 #ifdef ANSI
3503 Void rgSCHUtlHdlCrcFailInd
3504 (
3505 RgSchCellCb     *cell,
3506 RgSchUeCb       *ue,
3507 CmLteTimingInfo timingInfo
3508 )
3509 #else
3510 Void rgSCHUtlHdlCrcFailInd(cell, ue, timingInfo)
3511 RgSchCellCb     *cell;
3512 RgSchUeCb       *ue;
3513 CmLteTimingInfo timingInfo;
3514 #endif
3515 {
3516    cell->sc.apis->rgSCHUlCrcFailInd(cell, ue, timingInfo);
3517    return;
3518 } /* end of rgSCHUtlHdlCrcFailInd */
3519 #endif /* LTEMAC_SPS */
3520
3521 \f
3522 /**
3523  * @brief This function is a wrapper to call scheduler specific API.
3524  *
3525  * @details
3526  *
3527  *     Function: rgSCHUtlDlProcAddToRetx
3528  *     Purpose:  This function adds a HARQ process to retransmission
3529  *               queue. This may be performed when a HARQ ack is
3530  *               unsuccessful.
3531  *
3532  *     Invoked by: HARQ feedback processing
3533  *
3534  *  @param[in]  RgSchCellCb*     cell
3535  *  @param[in]  RgSchDlHqProc*   hqP
3536  *  @return  Void
3537  *
3538  **/
3539 #ifdef ANSI
3540 Void rgSCHUtlDlProcAddToRetx
3541 (
3542 RgSchCellCb                *cell,
3543 RgSchDlHqProcCb            *hqP
3544 )
3545 #else
3546 Void rgSCHUtlDlProcAddToRetx(cell, hqP)
3547 RgSchCellCb                *cell;
3548 RgSchDlHqProcCb            *hqP;
3549 #endif
3550 {
3551    cell->sc.apis->rgSCHDlProcAddToRetx(cell, hqP);
3552    return;
3553 }
3554
3555 \f
3556 /**
3557  * @brief This function adds a HARQ process TB to transmission
3558  *
3559  * @details
3560  *
3561  *     Function: rgSCHUtlDlHqPTbAddToTx
3562  *     Purpose:  This function a HarqProcess TB to the slot
3563  *               list.
3564  *
3565  *     Invoked by: Scheduler
3566  *
3567  *  @param[in]  RgSubFrm*     subFrm
3568  *  @param[in]  RgDlHqProc*   hqP
3569  *  @param[in]  uint8_t            tbIdx
3570  *  @return  Void
3571  *
3572  **/
3573 #ifdef ANSI
3574 Void rgSCHUtlDlHqPTbAddToTx
3575 (
3576 RgSchDlSf                  *subFrm,
3577 RgSchDlHqProcCb            *hqP,
3578 uint8_t                    tbIdx
3579 )
3580 #else
3581 Void rgSCHUtlDlHqPTbAddToTx(subFrm, hqP, tbIdx)
3582 RgSchDlSf                  *subFrm;
3583 RgSchDlHqProcCb            *hqP;
3584 uint8_t                    tbIdx;
3585 #endif
3586 {
3587    RgSchUeCb *ue = NULLP;
3588    RgSchCellCb *cell = hqP->hqE->cell;
3589    /* CA Dev Start */
3590    /* Addition of UE to dlSf->ueLst shall be done only to UE's PCell */
3591    /* ue->cell will always hold PCell information */
3592    if (NULLP == hqP->hqPSfLnk.node)
3593    {
3594       if (hqP->hqE->ue)
3595       {
3596          ue = hqP->hqE->ue;
3597          if(NULLP == ue->dl.dlSfHqInfo[cell->cellId][subFrm->dlIdx].dlSfUeLnk.node)
3598          {
3599             ue->dl.dlSfHqInfo[cell->cellId][subFrm->dlIdx].dlSfUeLnk.node = (PTR)ue;
3600             cmLListAdd2Tail(&cell->subFrms[subFrm->dlIdx]->ueLst, 
3601                   &ue->dl.dlSfHqInfo[cell->cellId][subFrm->dlIdx].dlSfUeLnk);
3602
3603             ue->dl.dlSfHqInfo[cell->cellId][subFrm->dlIdx].isPuschHarqRecpPres = FALSE;
3604
3605          }
3606
3607          /* Add Hq proc in particular dlIdx List for this UE 
3608             This list will be used while processing feedback*/
3609          hqP->hqPSfLnk.node = (PTR)hqP;
3610          cmLListAdd2Tail(&ue->dl.dlSfHqInfo[cell->cellId][subFrm->dlIdx].hqPLst,&hqP->hqPSfLnk); 
3611 #ifdef CA_DBG
3612          {
3613             uint32_t gSCellSchedCount,gPrimarySchedCount;
3614             if(RG_SCH_IS_CELL_SEC(hqP->hqE->ue,hqP->hqE->cell))
3615             {
3616                gSCellSchedCount++;
3617             }else
3618                gPrimarySchedCount++;
3619          }
3620 #endif
3621       }
3622       else if (hqP->hqE->msg4Proc == hqP)
3623       {
3624          /* Msg4 will be scheduled on PCELL only hence add directly to subFrm msg4HqpList */
3625          hqP->hqPSfLnk.node = (PTR)hqP;
3626          cmLListAdd2Tail(&subFrm->msg4HqPLst, &hqP->hqPSfLnk);
3627       }
3628    }
3629    else
3630    {
3631       ue = hqP->hqE->ue; 
3632    }
3633    if((ue) && (HQ_TB_WAITING == hqP->tbInfo[tbIdx].state))
3634          
3635    {   
3636       ue->dl.dlSfHqInfo[cell->cellId][subFrm->dlIdx].totalTbCnt++;
3637    }
3638    /*totalTbCnt will hold the total number of TBs across all harq Proc from all 
3639     * cells*/
3640
3641    hqP->subFrm = subFrm; 
3642
3643    /* CA Dev End */
3644    return;
3645 }
3646
3647
3648 \f
3649 /**
3650  * @brief This function removes a HARQ process TB from transmission
3651  *
3652  * @details
3653  *
3654  *     Function: rgSCHUtlDlHqPTbRmvFrmTx
3655  *     Purpose:  This function removes a HarqProcess TB to the slot
3656  *               list.
3657  *
3658  *     Invoked by: Scheduler
3659  *
3660  *  @param[in]  RgSubFrm*     subFrm
3661  *  @param[in]  RgDlHqProc*   hqP
3662  *  @param[in]  uint8_t            tbIdx
3663  *  @param[in]  Bool          isRepeting
3664  *  @return  Void
3665  *
3666  **/
3667 #ifdef ANSI
3668 Void rgSCHUtlDlHqPTbRmvFrmTx
3669 (
3670 RgSchDlSf                  *subFrm,
3671 RgSchDlHqProcCb            *hqP,
3672 uint8_t                    tbIdx,
3673 Bool                       isRepeting
3674 )
3675 #else
3676 Void rgSCHUtlDlHqPTbRmvFrmTx(subFrm, hqP, tbIdx, isRepeting)
3677 RgSchDlSf                  *subFrm;
3678 RgSchDlHqProcCb            *hqP;
3679 uint8_t                    tbIdx;
3680 Bool                       isRepeting;
3681 #endif
3682 {
3683    RgSchCellCb *cell = NULLP;
3684    /* Check with TDD */
3685    if ((isRepeting) &&
3686          (hqP->hqE->ue->ackNakRepCb.cfgRepCnt !=
3687           hqP->tbInfo[tbIdx].fbkRepCntr))
3688    {
3689       cmLListDelFrm(&subFrm->ackNakRepQ,
3690          &hqP->tbInfo[tbIdx].anRepLnk[hqP->tbInfo[tbIdx].fbkRepCntr]);
3691    }
3692    else
3693    {
3694       if (NULLP != hqP->hqPSfLnk.node)
3695       {
3696          /* CA dev Start */
3697          if (hqP->hqE->msg4Proc == hqP)
3698          {
3699             /* Msg4 will be scheduled on PCELL only hence delete directly from subFrm msg4HqpList */
3700             cmLListDelFrm(&subFrm->msg4HqPLst, &hqP->hqPSfLnk); 
3701          }
3702          else
3703          {
3704             cell = hqP->hqE->cell;
3705             /* Addition of UE to dlSf->ueLst shall be done only to UE's PCell */
3706             /* ue->cell will always hold PCell information */
3707             cmLListDelFrm(&hqP->hqE->ue->dl.dlSfHqInfo[cell->cellId][subFrm->dlIdx].hqPLst,&hqP->hqPSfLnk); 
3708             if (0 == hqP->hqE->ue->dl.dlSfHqInfo[cell->cellId][subFrm->dlIdx].hqPLst.count)
3709             {
3710
3711                cmLListDelFrm(&cell->subFrms[subFrm->dlIdx]->ueLst, 
3712                      &hqP->hqE->ue->dl.dlSfHqInfo[cell->cellId][subFrm->dlIdx].dlSfUeLnk);
3713                hqP->hqE->ue->dl.dlSfHqInfo[cell->cellId][subFrm->dlIdx].dlSfUeLnk.node = (PTR)NULLP;
3714                hqP->hqE->ue->dl.dlSfHqInfo[cell->cellId][subFrm->dlIdx].totalTbCnt = 0;
3715             }
3716          }
3717          hqP->hqPSfLnk.node = NULLP;
3718       }
3719       hqP->subFrm = NULLP;
3720    }
3721    return;
3722 }
3723
3724 #ifdef LTE_ADV
3725 /**
3726  * @brief Handler for accessing the existing SCellCb identified by the key
3727  * SCellId under the CellCb.
3728  *
3729  * @details
3730  *
3731  *     Function : rgSchUtlGetCellCb
3732  *     
3733  *           
3734  *  @param[in]  *cellCb
3735  *  @param[in]  ueId
3736  *  @return  RgSchUeCb*
3737  **/
3738 #ifdef ANSI
3739 RgSchCellCb* rgSchUtlGetCellCb
3740 (
3741  Inst         inst,
3742  uint16_t     cellId
3743 )
3744 #else
3745 RgSchCellCb* rgSchUtlGetCellCb(inst, cellId)
3746  Inst          inst;
3747  uint16_t      cellId;
3748 #endif
3749 {
3750    RgSchCellCb    *cellCb = NULLP; 
3751    uint8_t        strtCellId;
3752
3753    strtCellId = rgSchCb[inst].genCfg.startCellId;
3754    cellCb     = rgSchCb[inst].cells[cellId - strtCellId];
3755
3756    return (cellCb);
3757
3758 }  /* rgSchUtlGetCellCb */
3759
3760 /**
3761  * @brief Handler for deriving the servCellidx
3762  *
3763  * @details
3764  *
3765  *     Function : rgSchUtlGetServCellIdx
3766  *     
3767  *           
3768  *  @param[in]  *cellId
3769  *  @param[in]  RgSchUeCb *ue
3770  *  @return   uint8_t servCellIdx
3771  **/
3772 #ifdef ANSI
3773 uint8_t rgSchUtlGetServCellIdx
3774 (
3775  Inst         inst,
3776  uint16_t     cellId,
3777  RgSchUeCb    *ue
3778 )
3779 #else
3780 uint8_t rgSchUtlGetServCellIdx(inst,cellId,ue)
3781  Inst         inst;
3782  uint16_t     cellId;
3783  RgSchUeCb    *ue;
3784 #endif
3785 {
3786    uint8_t servCellIdx;
3787    uint16_t strtCellId;
3788
3789    strtCellId = rgSchCb[inst].genCfg.startCellId;
3790
3791    servCellIdx = ue->cellIdToCellIdxMap[cellId - strtCellId];
3792
3793    return (servCellIdx);
3794
3795 }  /* rgSchUtlGetCellCb */
3796
3797 /**
3798  * @brief Handler for validating the Cell Id received secondary Cell Addition
3799  *
3800  * @details
3801  *
3802  *     Function : rgSchUtlGetCellId
3803  *     
3804  *           
3805  *  @param[in]  *cellCb
3806  *  @param[in]  ueId
3807  *  @return  RgSchUeCb*
3808  **/
3809 #ifdef ANSI
3810 S16 rgSchUtlVldtCellId
3811 (
3812  Inst         inst,
3813  uint16_t          cellId
3814 )
3815 #else
3816 S16 rgSchUtlVldtCellId(inst, cellId)
3817  Inst          inst;
3818  uint16_t           cellId;
3819 #endif
3820 {
3821    uint8_t              strtCellId;
3822
3823    strtCellId = rgSchCb[inst].genCfg.startCellId;
3824    if((cellId >= strtCellId) && ((cellId - strtCellId) < CM_LTE_MAX_CELLS))
3825    {
3826       return ROK;
3827    }
3828    return RFAILED;
3829 }  /* rgSchUtlVldtCellId */
3830
3831 #endif /* LTE_ADV*/
3832 /**
3833  * @brief UE reconfiguration for scheduler
3834  *
3835  * @details
3836  *
3837  *     Function : rgSCHUtlRgrUeRecfg
3838  *
3839  *     This functions updates UE specific scheduler
3840  *     information upon UE reconfiguration
3841  *
3842  *  @param[in]  RgSchCellCb  *cell
3843  *  @param[in]  RgSchUeCb    *ue
3844  *  @param[int] RgrUeRecfg   *ueRecfg
3845  *  @param[out] RgSchErrInfo *err
3846  *  @return  S16
3847  *      -# ROK
3848  *      -# RFAILED
3849  **/
3850 #ifdef ANSI
3851 S16 rgSCHUtlRgrUeRecfg
3852 (
3853 RgSchCellCb  *cell,
3854 RgSchUeCb    *ue,
3855 RgrUeRecfg   *ueRecfg,
3856 RgSchErrInfo *err
3857 )
3858 #else
3859 S16 rgSCHUtlRgrUeRecfg(cell, ue, ueRecfg, err)
3860 RgSchCellCb  *cell;
3861 RgSchUeCb    *ue;
3862 RgrUeRecfg   *ueRecfg;
3863 RgSchErrInfo *err;
3864 #endif
3865 {
3866 /* Changes for UE Category Reconfiguration feature addition */
3867    RgSchCmnUe    *ueSch = RG_SCH_CMN_GET_UE(ue, cell);
3868
3869    /* Changes for UE Category Reconfiguration feature addition */
3870    if (ueRecfg->ueRecfgTypes & RGR_UE_UECAT_RECFG)
3871    {
3872       ueSch->cmn.ueCat = ueRecfg->ueCatEnum-1;
3873 #ifdef TFU_UPGRADE
3874       ue->ueCatEnum = ueRecfg->ueCatEnum;
3875 #endif
3876    } 
3877
3878    /* DL MU-MIMO not supported */
3879    if (ueRecfg->ueRecfgTypes & RGR_UE_TXMODE_RECFG)
3880    {
3881
3882       if (ueRecfg->txMode.pres == PRSNT_NODEF)
3883       {
3884          if (ueRecfg->txMode.txModeEnum == RGR_UE_TM_5)
3885          {
3886             err->errCause = RGSCHERR_SCH_CFG;
3887             return RFAILED;
3888          }
3889 #ifdef LTE_ADV
3890         if(ue->mimoInfo.txMode != ueRecfg->txMode.txModeEnum)
3891          {
3892             /* Decremnt the previos A value for this cell */
3893             ue->f1bCsAVal -= rgSCHUtlGetMaxTbSupp(ue->mimoInfo.txMode);
3894             /* Update A value with the new TM Mode */
3895             ue->f1bCsAVal += rgSCHUtlGetMaxTbSupp(ueRecfg->txMode.txModeEnum);
3896
3897
3898             RLOG1(L_INFO,"UeReCfg A valie is %d\n",ue->f1bCsAVal);
3899          }
3900 #endif
3901          ue->mimoInfo.txMode = ueRecfg->txMode.txModeEnum;
3902       }
3903    }
3904 #ifdef TFU_UPGRADE
3905    /* [ccpu00123958]-ADD- Check for PUSCH related Reconfig from the bit mask  */
3906     if(ueRecfg->ueRecfgTypes & RGR_UE_PUSCH_RECFG)
3907     {
3908        /* Fix: ccpu00124012 */
3909        /* TODO:: Need to check if this is 
3910           mandatory to be re-configured on UE category re-configuration */
3911        /* ue->ul.betaHqOffst = ueRecfg->puschDedCfg.bACKIdx;
3912           ue->ul.betaCqiOffst = ueRecfg->puschDedCfg.bCQIIdx;
3913           ue->ul.betaRiOffst = ueRecfg->puschDedCfg.bRIIdx;*/
3914     }
3915 #endif
3916    if (ueRecfg->ueRecfgTypes & RGR_UE_ULTXANTSEL_RECFG)
3917    {
3918       ue->ul.ulTxAntSel = ueRecfg->ulTxAntSel;
3919    }
3920    if (ueRecfg->ueRecfgTypes & RGR_UE_CDBKSBST_RECFG)
3921    {
3922       ue->mimoInfo.cdbkSbstRstrctn = ueRecfg->ueCodeBookRstRecfg;
3923    }
3924
3925    /* Commenting here to assign garbage value when it is not set in APP. */
3926    //ue->accessStratumRls = ueRecfg->accessStratumRls;
3927    return (cell->sc.apis->rgSCHRgrUeRecfg(cell, ue, ueRecfg, err));
3928 }  /* rgSCHUtlRgrUeRecfg */
3929
3930 /**
3931  * @brief This function deletes a service from scheduler
3932  *
3933  * @details
3934  *
3935  *     Function: rgSCHUtlFreeDlLc
3936  *     Purpose:  This function is made available through a FP for
3937  *               making scheduler aware of a service being deleted from UE
3938  *
3939  *     Invoked by: BO and Scheduler
3940  *
3941  *  @param[in]  RgSchCellCb*  cell
3942  *  @param[in]  RgSchUeCb*    ue
3943  *  @param[in]  RgSchDlLcCb*  svc
3944  *  @return  Void
3945  **/
3946 #ifdef ANSI
3947 Void rgSCHUtlFreeDlLc
3948 (
3949 RgSchCellCb                *cell,
3950 RgSchUeCb                  *ue,
3951 RgSchDlLcCb                *svc
3952 )
3953 #else
3954 Void rgSCHUtlFreeDlLc(cell, ue, svc)
3955 RgSchCellCb                *cell;
3956 RgSchUeCb                  *ue;
3957 RgSchDlLcCb                *svc;
3958 #endif
3959 {
3960    cell->sc.apis->rgSCHFreeDlLc(cell, ue, svc);
3961
3962   /* Stack Crash problem for TRACE5 changes. added the return below . */
3963  return;
3964
3965 }
3966
3967 /**
3968  * @brief UE deletion for scheduler
3969  *
3970  * @details
3971  *
3972  *     Function : rgSCHUtlFreeUe
3973  *
3974  *     This functions deletes all scheduler information
3975  *     pertaining to a UE
3976  *
3977  *  @param[in]  RgSchCellCb  *cell
3978  *  @param[in]  RgSchUeCb    *ue
3979  *  @return  Void
3980  **/
3981 #ifdef ANSI
3982 Void rgSCHUtlFreeUe
3983 (
3984 RgSchCellCb  *cell,
3985 RgSchUeCb    *ue
3986 )
3987 #else
3988 Void rgSCHUtlFreeUe(cell, ue)
3989 RgSchCellCb  *cell;
3990 RgSchUeCb    *ue;
3991 #endif
3992 {
3993 #ifdef LTE_TDD
3994    rgSCHUtlDelUeANFdbkInfo(ue,RGSCH_PCELL_INDEX);
3995 #endif
3996    cell->sc.apis->rgSCHFreeUe(cell, ue);
3997
3998   /* Stack Crash problem for TRACE5 changes. added the return below . */
3999  return;
4000
4001 }  /* rgSCHUtlFreeUe */
4002
4003 /**
4004  * @brief This function updates the scheduler with service for a UE
4005  *
4006  * @details
4007  *
4008  *     Function: rgSCHUtlDlDedBoUpd
4009  *     Purpose:  This function should be called whenever there is a
4010  *               change BO for a service.
4011  *
4012  *     Invoked by: BO and Scheduler
4013  *
4014  *  @param[in]  RgSchCellCb*  cell
4015  *  @param[in]  RgSchUeCb*    ue
4016  *  @param[in]  RgSchDlLcCb*  lc
4017  *  @return  Void
4018  **/
4019 #ifdef ANSI
4020 Void rgSCHUtlDlDedBoUpd
4021 (
4022 RgSchCellCb                *cell,
4023 RgSchUeCb                  *ue,
4024 RgSchDlLcCb                *lc
4025 )
4026 #else
4027 Void rgSCHUtlDlDedBoUpd(cell, ue, lc)
4028 RgSchCellCb                *cell;
4029 RgSchUeCb                  *ue;
4030 RgSchDlLcCb                *lc;
4031 #endif
4032 {
4033    cell->sc.apis->rgSCHDlDedBoUpd(cell, ue, lc);
4034    return;
4035 }
4036 /**
4037  * @brief Record MSG3 allocation into the UE
4038  *
4039  * @details
4040  *
4041  *     Function : rgSCHUtlRecMsg3Alloc
4042  *
4043  *     This function is invoked to update record msg3 allocation information
4044  *    in the UE when UE is detected for RaCb
4045  *
4046  *  @param[in]  RgSchCellCb     *cell
4047  *  @param[in]  RgSchUeCb       *ue
4048  *  @param[in] RgSchRaCb       *raCb
4049  *
4050  **/
4051 #ifdef ANSI
4052 Void rgSCHUtlRecMsg3Alloc
4053 (
4054 RgSchCellCb      *cell,
4055 RgSchUeCb        *ue,
4056 RgSchRaCb        *raCb
4057 )
4058 #else
4059 Void rgSCHUtlRecMsg3Alloc(cell, ue, raCb)
4060 RgSchCellCb      *cell;
4061 RgSchUeCb        *ue;
4062 RgSchRaCb        *raCb;
4063 #endif
4064 {
4065    cell->sc.apis->rgSCHUlRecMsg3Alloc(cell, ue, raCb);
4066    return;
4067
4068 }  /* rgSCHRecMsg3Alloc */
4069
4070 #ifdef RG_UNUSED
4071 /**
4072  * @brief Update harq process for allocation
4073  *
4074  * @details
4075  *
4076  *     Function : rgSCHUtlUpdUlHqProc
4077  *
4078  *     This function is invoked when harq process
4079  *     control block is now in a new memory location
4080  *     thus requiring a pointer/reference update.
4081  *
4082  *  @param[in] RgSchCellCb      *cell
4083  *  @param[in] RgSchUlHqProcCb  *curProc
4084  *  @param[in] RgSchUlHqProcCb  *oldProc
4085  *  @return  S16
4086  *      -# ROK
4087  *      -# RFAILED
4088  **/
4089 #ifdef ANSI
4090 S16 rgSCHUtlUpdUlHqProc
4091 (
4092 RgSchCellCb      *cell,
4093 RgSchUlHqProcCb  *curProc,
4094 RgSchUlHqProcCb  *oldProc
4095 )
4096 #else
4097 S16 rgSCHUtlUpdUlHqProc(cell, curProc, oldProc)
4098 RgSchCellCb      *cell;
4099 RgSchUlHqProcCb  *curProc;
4100 RgSchUlHqProcCb  *oldProc;
4101 #endif
4102 {
4103    return (cell->sc.apis->rgSCHUpdUlHqProc(cell, curProc, oldProc));
4104 }  /* rgSCHUtlUpdUlHqProc */
4105 #endif
4106 /**
4107  * @brief UL grant for contention resolution
4108  *
4109  * @details
4110  *
4111  *     Function : rgSCHUtlContResUlGrant
4112  *
4113  *     Add UE to another queue specifically for CRNTI based contention
4114  *     resolution
4115  *
4116  *  @param[in]  RgSchCellCb *cell
4117  *  @param[in]  RgSchUeCb  *ue
4118  *  @param[out] RgSchErrInfo *err
4119  *  @return  S16
4120  *      -# ROK
4121  *      -# RFAILED
4122  **/
4123 #ifdef ANSI
4124 S16 rgSCHUtlContResUlGrant
4125 (
4126 RgSchCellCb  *cell,
4127 RgSchUeCb    *ue,
4128 RgSchErrInfo *err
4129 )
4130 #else
4131 S16 rgSCHUtlContResUlGrant(cell, ue, err)
4132 RgSchCellCb  *cell;
4133 RgSchUeCb    *ue;
4134 RgSchErrInfo *err;
4135 #endif
4136 {
4137
4138    ue->isMsg4PdcchWithCrnti = TRUE; 
4139
4140    return (cell->sc.apis->rgSCHContResUlGrant(cell, ue, err));
4141 }  /* rgSCHUtlContResUlGrant */
4142
4143 /**
4144  * @brief SR reception handling
4145  *
4146  * @details
4147  *
4148  *     Function : rgSCHUtlSrRcvd
4149  *
4150  *     - Handles SR reception for UE
4151  *
4152  *  @param[in]  RgSchCellCb  *cell
4153  *  @param[in]  RgSchUeCb    *ue
4154  *  @param[out] RgSchErrInfo *err
4155  *  @return  S16
4156  *      -# ROK
4157  *      -# RFAILED
4158  **/
4159 #ifdef ANSI
4160 S16 rgSCHUtlSrRcvd
4161 (
4162 RgSchCellCb  *cell,
4163 RgSchUeCb    *ue,
4164 CmLteTimingInfo frm,
4165 RgSchErrInfo *err
4166 )
4167 #else
4168 S16 rgSCHUtlSrRcvd(cell, ue, frm, err)
4169 RgSchCellCb  *cell;
4170 RgSchUeCb    *ue;
4171 CmLteTimingInfo frm;
4172 RgSchErrInfo *err;
4173 #endif
4174 {
4175    return (cell->sc.apis->rgSCHSrRcvd(cell, ue, frm, err));
4176 }  /* rgSCHUtlSrRcvd */
4177
4178 /**
4179  * @brief Short BSR update
4180  *
4181  * @details
4182  *
4183  *     Function : rgSCHUtlUpdBsrShort
4184  *
4185  *     This functions does requisite updates to handle short BSR reporting
4186  *
4187  *  @param[in]  RgSchCellCb  *cell
4188  *  @param[in]  RgSchUeCb    *ue
4189  *  @param[in]  uint8_t           lcgId
4190  *  @param[in]  uint8_t           bsr
4191  *  @param[out] RgSchErrInfo *err
4192  *  @return  Void
4193  *      -# ROK
4194  *      -# RFAILED
4195  **/
4196 #ifdef ANSI
4197 Void rgSCHUtlUpdBsrShort
4198 (
4199 RgSchCellCb  *cell,
4200 RgSchUeCb    *ue,
4201 uint8_t           lcgId,
4202 uint8_t           bsr,
4203 RgSchErrInfo *err
4204 )
4205 #else
4206 Void rgSCHUtlUpdBsrShort(cell, ue, lcgId, bsr, err)
4207 RgSchCellCb  *cell;
4208 RgSchUeCb    *ue;
4209 uint8_t           lcgId;
4210 uint8_t           bsr;
4211 RgSchErrInfo *err;
4212 #endif
4213 {
4214    cell->sc.apis->rgSCHUpdBsrShort(cell, ue, &ue->ul.lcgArr[lcgId], bsr, err);
4215    return;
4216 }  /* rgSCHUtlUpdBsrShort */
4217
4218
4219 /**
4220  * @brief Truncated BSR update
4221  *
4222  * @details
4223  *
4224  *     Function : rgSCHUtlUpdBsrTrunc
4225  *
4226  *     This functions does required updates to handle truncated BSR report
4227  *
4228  *
4229  *  @param[in]  RgSchCellCb  *cell
4230  *  @param[in]  RgSchUeCb    *ue
4231  *  @param[in]  uint8_t           lcgId
4232  *  @param[in]  uint8_t           bsr
4233  *  @param[out] RgSchErrInfo *err
4234  *  @return  Void
4235  *      -# ROK
4236  *      -# RFAILED
4237  **/
4238 #ifdef ANSI
4239 Void rgSCHUtlUpdBsrTrunc
4240 (
4241 RgSchCellCb  *cell,
4242 RgSchUeCb    *ue,
4243 uint8_t           lcgId,
4244 uint8_t           bsr,
4245 RgSchErrInfo *err
4246 )
4247 #else
4248 Void rgSCHUtlUpdBsrTrunc(cell, ue, lcgId, bsr, err)
4249 RgSchCellCb   *cell;
4250 RgSchUeCb     *ue;
4251 uint8_t            lcgId;
4252 uint8_t            bsr;
4253 RgSchErrInfo *err;
4254 #endif
4255 {
4256    cell->sc.apis->rgSCHUpdBsrTrunc(cell, ue, &ue->ul.lcgArr[lcgId], bsr, err);
4257    return; 
4258 }  /* rgSCHUtlUpdBsrTrunc */
4259
4260
4261 /**
4262  * @brief Long BSR update
4263  *
4264  * @details
4265  *
4266  *     Function : rgSCHUtlUpdBsrLong
4267  *
4268  *     - Update BSRs for all configured LCGs
4269  *     - Update priority of LCGs if needed
4270  *     - Update UE's position within/across uplink scheduling queues
4271  *
4272  *
4273  *  @param[in]  RgSchCellCb   *cell
4274  *  @param[in]  RgSchUeCb     *ue
4275  *  @param[in]  uint8_t            bsr0
4276  *  @param[in]  uint8_t            bsr1
4277  *  @param[in]  uint8_t            bsr2
4278  *  @param[in]  uint8_t            bsr3
4279  *  @param[out] RgSchErrInfo  *err
4280  *  @return  Void
4281  *      -# ROK
4282  *      -# RFAILED
4283  **/
4284 #ifdef ANSI
4285 Void rgSCHUtlUpdBsrLong
4286 (
4287 RgSchCellCb  *cell,
4288 RgSchUeCb    *ue,
4289 uint8_t           bsr0,
4290 uint8_t           bsr1,
4291 uint8_t           bsr2,
4292 uint8_t           bsr3,
4293 RgSchErrInfo *err
4294 )
4295 #else
4296 Void rgSCHUtlUpdBsrLong(cell, ue, bsr0, bsr1, bsr2, bsr3, err)
4297 RgSchCellCb  *cell;
4298 RgSchUeCb    *ue;
4299 uint8_t           bsr0;
4300 uint8_t           bsr1;
4301 uint8_t           bsr2;
4302 uint8_t           bsr3;
4303 RgSchErrInfo *err;
4304 #endif
4305 {
4306    uint8_t bsArr[4];
4307
4308    bsArr[0] = bsr0;
4309    bsArr[1] = bsr1;
4310    bsArr[2] = bsr2;
4311    bsArr[3] = bsr3;
4312    cell->sc.apis->rgSCHUpdBsrLong(cell, ue, bsArr, err);
4313    return;
4314 }  /* rgSCHUtlUpdBsrLong */
4315
4316 /**
4317  * @brief EXT PHR update
4318  *
4319  * @details
4320  *
4321  *     Function : rgSCHUtlUpdExtPhr
4322  *
4323  *     Updates extended power headroom info for a UE
4324  *
4325  *  @param[in]  RgSchCellCb  *cell
4326  *  @param[in]  RgSchUeCb    *ue
4327  *  @param[in]  uint8_t           phr
4328  *  @param[out] RgSchErrInfo *err
4329  *  @return  S16
4330  *      -# ROK
4331  *      -# RFAILED
4332  **/
4333 #ifdef ANSI
4334 S16 rgSCHUtlUpdExtPhr
4335 (
4336 RgSchCellCb  *cell,
4337 RgSchUeCb    *ue,
4338 RgInfExtPhrCEInfo * extPhr,
4339 RgSchErrInfo *err
4340 )
4341 #else
4342 S16 rgSCHUtlUpdExtPhr(cell, ue, extPhr, err)
4343 RgSchCellCb  *cell;
4344 RgSchUeCb    *ue;
4345 RgInfExtPhrCEInfo * extPhr;
4346 RgSchErrInfo *err;
4347 #endif
4348 {
4349    return (cell->sc.apis->rgSCHUpdExtPhr(cell, ue, extPhr, err));
4350 }  /* rgSCHUtlUpdExtPhr */
4351
4352
4353
4354 /**
4355  * @brief PHR update
4356  *
4357  * @details
4358  *
4359  *     Function : rgSCHUtlUpdPhr
4360  *
4361  *     Updates power headroom info for a UE
4362  *
4363  *  @param[in]  RgSchCellCb  *cell
4364  *  @param[in]  RgSchUeCb    *ue
4365  *  @param[in]  uint8_t           phr
4366  *  @param[out] RgSchErrInfo *err
4367  *  @return  S16
4368  *      -# ROK
4369  *      -# RFAILED
4370  **/
4371 #ifdef ANSI
4372 S16 rgSCHUtlUpdPhr
4373 (
4374 RgSchCellCb  *cell,
4375 RgSchUeCb    *ue,
4376 uint8_t           phr,
4377 RgSchErrInfo *err
4378 )
4379 #else
4380 S16 rgSCHUtlUpdPhr(cell, ue, phr, err)
4381 RgSchCellCb  *cell;
4382 RgSchUeCb    *ue;
4383 uint8_t           phr;
4384 RgSchErrInfo *err;
4385 #endif
4386 {
4387    return (cell->sc.apis->rgSCHUpdPhr(cell, ue, phr, err));
4388 }  /* rgSCHUtlUpdPhr */
4389
4390
4391 /**
4392  * @brief Indication of UL CQI
4393  *
4394  * @details
4395  *
4396  *     Function : rgSCHUtlUlCqiInd
4397  *
4398  *     - Updates uplink CQI information for the UE. Computes and
4399  *       stores the lowest CQI of CQIs reported in all subbands
4400  *
4401  *  @param[in]  RgSchCellCb         *cell
4402  *  @param[in]  RgSchUeCb           *ue
4403  *  @param[in]  TfuUlCqiRpt         *ulCqiInfo
4404  *  @return  Void
4405  **/
4406 #ifdef ANSI
4407 Void rgSCHUtlUlCqiInd
4408 (
4409 RgSchCellCb          *cell,
4410 RgSchUeCb            *ue,
4411 TfuUlCqiRpt          *ulCqiInfo
4412 )
4413 #else
4414 Void rgSCHUtlUlCqiInd(cell, ue, ulCqiInfo)
4415 RgSchCellCb          *cell;
4416 RgSchUeCb            *ue;
4417 TfuUlCqiRpt          *ulCqiInfo;
4418 #endif
4419 {
4420    cell->sc.apis->rgSCHUlCqiInd(cell, ue, ulCqiInfo);
4421    return;
4422 }  /* rgSCHUtlUlCqiInd */
4423
4424 /**
4425  * @brief Indication of PUCCH power adjustment
4426  *
4427  * @details
4428  *
4429  *     Function : rgSCHUtlPucchDeltaPwrInd
4430  *
4431  *     - Updates uplink CQI information for the UE. Computes and
4432  *       stores the lowest CQI of CQIs reported in all subbands
4433  *
4434  *  @param[in]  RgSchCellCb         *cell
4435  *  @param[in]  RgSchUeCb           *ue
4436  *  @param[in]  uint8_t                  delta
4437  *  @return  Void
4438  **/
4439 #ifdef ANSI
4440 Void rgSCHUtlPucchDeltaPwrInd
4441 (
4442 RgSchCellCb          *cell,
4443 RgSchUeCb            *ue,
4444 S8                   delta
4445 )
4446 #else
4447 Void rgSCHUtlPucchDeltaPwrInd(cell, ue, delta)
4448 RgSchCellCb          *cell;
4449 RgSchUeCb            *ue;
4450 S8                   delta;
4451 #endif
4452 {
4453    cell->sc.apis->rgSCHPucchDeltaPwrInd(cell, ue, delta);
4454    return;
4455 }  /* rgSCHUtlPucchDeltaPwrInd */
4456
4457 /* Start: LTEMAC_2.1_DEV_CFG */
4458 /**
4459  * @brief Ue Reset Request
4460  *
4461  * @details
4462  *
4463  *     Function : rgSCHUtlUeReset
4464  *
4465  *
4466  *  @param[in]  RgSchCellCb         *cell
4467  *  @param[in]  RgSchUeCb           *ue
4468  *  @return  S16
4469  **/
4470 #ifdef ANSI
4471 Void rgSCHUtlUeReset
4472 (
4473 RgSchCellCb          *cell,
4474 RgSchUeCb            *ue
4475 )
4476 #else
4477 Void rgSCHUtlUeReset(cell, ue)
4478 RgSchCellCb          *cell;
4479 RgSchUeCb            *ue;
4480 #endif
4481 {
4482    ue->remBoCnt = 0;
4483    cell->sc.apis->rgSCHUeReset(cell, ue);
4484    return;
4485 }  /* rgSCHUtlUeReset */
4486 /* End: LTEMAC_2.1_DEV_CFG */
4487
4488 /**
4489  * @brief Returns HARQ proc for which data expected now
4490  *
4491  * @details
4492  *
4493  *     Function: rgSCHUtlUlHqProcForUe
4494  *     Purpose:  This function returns the harq process for
4495  *               which data is expected in the current slot.
4496  *               It does not validate if the HARQ process
4497  *               has an allocation.
4498  *
4499  *     Invoked by: TOM
4500  *
4501  *  @param[in]  RgSchCellCb         *cell
4502  *  @param[in]  CmLteTimingInfo     frm
4503  *  @param[in]  RgSchUeCb           *ue
4504  *  @param[out] RgSchUlHqProcCb     **procRef
4505  *  @return  Void
4506  **/
4507 #ifdef ANSI
4508 Void rgSCHUtlUlHqProcForUe
4509 (
4510 RgSchCellCb         *cell,
4511 CmLteTimingInfo     frm,
4512 RgSchUeCb           *ue,
4513 RgSchUlHqProcCb     **procRef
4514 )
4515 #else
4516 Void rgSCHUtlUlHqProcForUe(cell, frm, ue, procRef)
4517 RgSchCellCb         *cell;
4518 CmLteTimingInfo     frm;
4519 RgSchUeCb           *ue;
4520 RgSchUlHqProcCb     **procRef;
4521 #endif
4522 {
4523    cell->sc.apis->rgSCHUlHqProcForUe(cell, frm, ue, procRef);
4524
4525  /* Stack Crash problems for TRACE5 changes. added the return below */
4526  return;
4527
4528 }
4529
4530 /**
4531  * @brief Returns first uplink allocation to send reception
4532  *        request to PHY
4533  *
4534  * @details
4535  *
4536  *     Function: rgSCHUtlFirstRcptnReq(cell)
4537  *     Purpose:  This function returns the first uplink allocation
4538  *               (or NULLP if there is none) in the slot
4539  *               in which is expected to prepare and send reception
4540  *               request to PHY.
4541  *
4542  *     Invoked by: TOM
4543  *
4544  *  @param[in]  RgSchCellCb      *cell
4545  *  @return  RgSchUlAlloc*
4546  **/
4547 #ifdef ANSI
4548 RgSchUlAlloc *rgSCHUtlFirstRcptnReq
4549 (
4550 RgSchCellCb      *cell
4551 )
4552 #else
4553 RgSchUlAlloc *rgSCHUtlFirstRcptnReq(cell)
4554 RgSchCellCb      *cell;
4555 #endif
4556 {
4557    return (cell->sc.apis->rgSCHFirstRcptnReq(cell));
4558 }
4559
4560 /**
4561  * @brief Returns first uplink allocation to send reception
4562  *        request to PHY
4563  *
4564  * @details
4565  *
4566  *     Function: rgSCHUtlNextRcptnReq(cell)
4567  *     Purpose:  This function returns the next uplink allocation
4568  *               (or NULLP if there is none) in the slot
4569  *               in which is expected to prepare and send reception
4570  *               request to PHY.
4571  *
4572  *     Invoked by: TOM
4573  *
4574  *  @param[in]  RgSchCellCb      *cell
4575  *  @return  RgSchUlAlloc*
4576  **/
4577 #ifdef ANSI
4578 RgSchUlAlloc *rgSCHUtlNextRcptnReq
4579 (
4580 RgSchCellCb      *cell,
4581 RgSchUlAlloc     *alloc
4582 )
4583 #else
4584 RgSchUlAlloc *rgSCHUtlNextRcptnReq(cell, alloc)
4585 RgSchCellCb      *cell;
4586 RgSchUlAlloc     *alloc;
4587 #endif
4588 {
4589    return (cell->sc.apis->rgSCHNextRcptnReq(cell, alloc));
4590 }
4591
4592 /**
4593  * @brief Returns first uplink allocation to send HARQ feedback
4594  *        request to PHY
4595  *
4596  * @details
4597  *
4598  *     Function: rgSCHUtlFirstHqFdbkAlloc
4599  *     Purpose:  This function returns the first uplink allocation
4600  *               (or NULLP if there is none) in the slot
4601  *               in which it is expected to prepare and send HARQ
4602  *               feedback to PHY.
4603  *
4604  *     Invoked by: TOM
4605  *
4606  *  @param[in]  RgSchCellCb      *cell
4607  *  @param[in]  uint8_t                idx  
4608  *  @return  RgSchUlAlloc*
4609  **/
4610 #ifdef ANSI
4611 RgSchUlAlloc *rgSCHUtlFirstHqFdbkAlloc
4612 (
4613 RgSchCellCb      *cell,
4614 uint8_t               idx
4615 )
4616 #else
4617 RgSchUlAlloc *rgSCHUtlFirstHqFdbkAlloc(cell, idx)
4618 RgSchCellCb      *cell;
4619 uint8_t               idx;
4620 #endif
4621 {
4622    return (cell->sc.apis->rgSCHFirstHqFdbkAlloc(cell, idx));
4623 }
4624
4625 \f
4626 /**
4627  * @brief Returns next allocation to send HARQ feedback for
4628  *
4629  * @details
4630  *
4631  *     Function: rgSCHUtlNextHqFdbkAlloc(cell)
4632  *     Purpose:  This function returns the next uplink allocation
4633  *               (or NULLP if there is none) in the slot
4634  *               for which HARQ feedback needs to be sent.
4635  *
4636  *     Invoked by: TOM
4637  *
4638  *  @param[in]  RgSchCellCb      *cell
4639  *  @return  RgSchUlAlloc*
4640  **/
4641 #ifdef ANSI
4642 RgSchUlAlloc *rgSCHUtlNextHqFdbkAlloc
4643 (
4644 RgSchCellCb      *cell,
4645 RgSchUlAlloc     *alloc,
4646 uint8_t               idx 
4647 )
4648 #else
4649 RgSchUlAlloc *rgSCHUtlNextHqFdbkAlloc(cell, alloc, idx)
4650 RgSchCellCb      *cell;
4651 RgSchUlAlloc     *alloc;
4652 uint8_t               idx; 
4653 #endif
4654 {
4655    return (cell->sc.apis->rgSCHNextHqFdbkAlloc(cell, alloc, idx));
4656 }
4657
4658 /***********************************************************
4659  *
4660  *     Func : rgSCHUtlResetSfAlloc
4661  *
4662  *     Desc : Utility Function to Reset slot allocation information.
4663  *
4664  *
4665  *     Ret  : ROK
4666  *            RFAILED
4667  *
4668  *
4669  *     File : rg_utl.c
4670  *
4671  **********************************************************/
4672 #ifdef ANSI
4673 S16 rgSCHUtlResetSfAlloc
4674 (
4675 RgInfSfAlloc *sfAlloc,
4676 Bool         resetCmnLcInfo,
4677 Bool         restAlloc
4678 )
4679 #else
4680 S16 rgSCHUtlResetSfAlloc(sfAlloc,resetCmnLcInfo,restAlloc)
4681 RgInfSfAlloc *sfAlloc;
4682 Bool         resetCmnLcInfo;
4683 Bool         restAlloc;
4684 #endif
4685 {
4686    if(TRUE == restAlloc)
4687    {
4688       if(sfAlloc->ueInfo.numUes)
4689       {
4690          memset(sfAlloc->ueInfo.allocInfo,0x00,
4691                (sizeof(RgInfUeAlloc)*sfAlloc->ueInfo.numUes));
4692       }
4693       sfAlloc->ueInfo.numUes = 0;
4694       sfAlloc->rarInfo.numRaRntis = 0;
4695       sfAlloc->flowCntrlInfo.numUes = 0;
4696    }
4697    if(TRUE == resetCmnLcInfo)
4698    {
4699       sfAlloc->cmnLcInfo.bitMask = 0;
4700    }
4701    return ROK;
4702 }
4703
4704 /***********************************************************
4705  *
4706  *     Func : rgSCHUtlGetRlsHqAlloc
4707  *
4708  *     Desc : Utility Function to Allocate slot allocation information.
4709  *
4710  *
4711  *     Ret  : ROK
4712  *            RFAILED
4713  *
4714  *
4715  *     File : rg_utl.c
4716  *
4717  **********************************************************/
4718 #ifdef ANSI
4719 S16 rgSCHUtlGetRlsHqAlloc
4720 (
4721 RgSchCellCb *cell
4722 )
4723 #else
4724 S16 rgSCHUtlGetRlsHqAlloc(cell)
4725 RgSchCellCb *cell;
4726 #endif
4727 {
4728    uint8_t    idx = 0;
4729    Inst  inst = cell->instIdx;
4730    for(idx=0; idx < RGSCH_NUM_SUB_FRAMES; idx++)
4731    {
4732       cell->rlsHqArr[idx].cellId = cell->cellId;
4733
4734       /* Allocating with additional location, to accommodate
4735          TA scheduling along with maximum no of UEs per SF */
4736
4737       /* Allocate memory for "scheduled UE" Info */
4738       if((rgSCHUtlAllocSBuf(inst,
4739                      (Data**)&(cell->rlsHqArr[idx].ueHqInfo),
4740                       (sizeof(RgInfUeHqInfo)*RGSCH_MAX_UE_PER_DL_SF))) != ROK)
4741       {
4742          RLOG_ARG0(L_ERROR,DBG_CELLID,cell->cellId,"Memory allocation FAILED for "
4743             "UE Alloc");
4744          return RFAILED;
4745       }
4746    }
4747
4748    return ROK;
4749
4750 }
4751
4752 /***********************************************************
4753  *
4754  *     Func : rgSCHUtlPutRlsHqAlloc
4755  *
4756  *     Desc : Utility Function to deallocate slot allocation information.
4757  *
4758  *
4759  *     Ret  : ROK
4760  *            RFAILED
4761  *
4762  *
4763  *     File : rg_utl.c
4764  *
4765  **********************************************************/
4766 #ifdef ANSI
4767 S16 rgSCHUtlPutRlsHqAlloc
4768 (
4769 RgSchCellCb *cell
4770 )
4771 #else
4772 S16 rgSCHUtlPutRlsHqAlloc(cell)
4773 RgSchCellCb *cell;
4774 #endif
4775 {
4776    uint8_t    idx = 0;
4777    Inst  inst = cell->instIdx;
4778
4779    for(idx=0; idx < RGSCH_NUM_SUB_FRAMES; idx++)
4780    {
4781       /* Deallocate memory for "scheduled UE" Info */
4782       if (cell->rlsHqArr[idx].ueHqInfo != NULLP)
4783       {
4784          /* Freeing with additional location, to accommodate TA
4785             scheduling along with maximum no of UEs per SF */
4786          /* ccpu00117052 - MOD - Passing double pointer
4787             for proper NULLP assignment*/
4788          rgSCHUtlFreeSBuf(inst,
4789                (Data **)(&(cell->rlsHqArr[idx].ueHqInfo)),
4790              (sizeof(RgInfUeHqInfo)*RGSCH_MAX_UE_PER_DL_SF));
4791       }
4792    }
4793
4794    return ROK;
4795
4796 }
4797
4798
4799 /***********************************************************
4800  *
4801  *     Func : rgSCHUtlGetSfAlloc
4802  *
4803  *     Desc : Utility Function to Allocate slot allocation information.
4804  *
4805  *
4806  *     Ret  : ROK
4807  *            RFAILED
4808  *
4809  *
4810  *     File : rg_utl.c
4811  *
4812  **********************************************************/
4813 #ifdef ANSI
4814 S16 rgSCHUtlGetSfAlloc
4815 (
4816 RgSchCellCb *cell
4817 )
4818 #else
4819 S16 rgSCHUtlGetSfAlloc(cell)
4820 RgSchCellCb *cell;
4821 #endif
4822 {
4823    uint8_t    idx;
4824    uint8_t    indx;
4825    Inst  inst = cell->instIdx;
4826    RgSchCmnUlCell *cellUl      = RG_SCH_CMN_GET_UL_CELL(cell);
4827
4828 #ifdef LTE_TDD
4829    for(idx=0; idx < RGSCH_SF_ALLOC_SIZE; idx++)
4830 #else
4831    for(idx=0; idx < RGSCH_NUM_SUB_FRAMES; idx++)
4832 #endif
4833    {
4834       cell->sfAllocArr[idx].cellId = cell->cellId;
4835
4836       /* Allocating with additional location, to accommodate
4837          TA scheduling along with maximum no of UEs per SF */
4838
4839       /* Allocate memory for "scheduled UE" Info */
4840       if((rgSCHUtlAllocSBuf(inst,
4841                      (Data**)&(cell->sfAllocArr[idx].ueInfo.allocInfo),
4842                       (sizeof(RgInfUeAlloc)*RGSCH_MAX_UE_PER_DL_SF))) != ROK)
4843       {
4844          RLOG_ARG0(L_ERROR,DBG_CELLID,cell->cellId,"Memory allocation FAILED for "
4845             "UE Alloc");
4846          return RFAILED;
4847       }
4848
4849       /* Allocate memory for "scheduled RAR" Info */
4850       if((rgSCHUtlAllocSBuf(inst,
4851                      (Data**)&(cell->sfAllocArr[idx].rarInfo.raRntiInfo),
4852                       (sizeof(RgInfRaRntiInfo)*RGSCH_MAX_RARNTI_PER_DL_SF))) != ROK)
4853       {
4854          RLOG_ARG0(L_ERROR,DBG_CELLID,cell->cellId,"Memory allocation FAILED for "
4855             "RARNTI");
4856          return RFAILED;
4857       }
4858       for(indx = 0; indx < RGSCH_MAX_RARNTI_PER_DL_SF; indx++)
4859       {
4860          if((rgSCHUtlAllocSBuf(inst,
4861             (Data**)&(cell->sfAllocArr[idx].rarInfo.raRntiInfo[indx].crntiInfo),
4862                    (sizeof(RgInfCrntiInfo)* (cellUl->maxMsg3PerUlSf)))) != ROK)
4863          {
4864             RLOG_ARG0(L_ERROR,DBG_CELLID,cell->cellId,"Memory allocation FAILED for "
4865                "RNTI");
4866             return RFAILED;
4867          }
4868       }
4869
4870    }
4871
4872 #ifdef EMTC_ENABLE
4873    rgSCHEmtcUtlGetSfAlloc(cell);
4874 #endif
4875
4876    return ROK;
4877
4878 }
4879
4880 /***********************************************************
4881  *
4882  *     Func : rgSCHUtlPutSfAlloc
4883  *
4884  *     Desc : Utility Function to deallocate slot allocation information.
4885  *
4886  *
4887  *     Ret  : ROK
4888  *            RFAILED
4889  *
4890  *
4891  *     File : rg_utl.c
4892  *
4893  **********************************************************/
4894 #ifdef ANSI
4895 S16 rgSCHUtlPutSfAlloc
4896 (
4897 RgSchCellCb *cell
4898 )
4899 #else
4900 S16 rgSCHUtlPutSfAlloc(cell)
4901 RgSchCellCb *cell;
4902 #endif
4903 {
4904    uint8_t    idx;
4905    uint8_t    indx;
4906    Inst  inst = cell->instIdx;
4907    RgSchCmnUlCell *cellUl      = RG_SCH_CMN_GET_UL_CELL(cell);
4908
4909 #ifdef LTE_TDD
4910    for(idx=0; idx < RGSCH_SF_ALLOC_SIZE; idx++)
4911 #else
4912       for(idx=0; idx < RGSCH_NUM_SUB_FRAMES; idx++)
4913 #endif
4914       {
4915          if (cell->sfAllocArr[idx].rarInfo.raRntiInfo != NULLP)
4916          {
4917             for(indx = 0; indx < RGSCH_MAX_RARNTI_PER_DL_SF; indx++)
4918             {
4919                if (cell->sfAllocArr[idx].rarInfo.raRntiInfo[indx].crntiInfo != NULLP)
4920                   /* ccpu00117052 - MOD - Passing double pointer
4921                      for proper NULLP assignment*/
4922                   rgSCHUtlFreeSBuf(inst,
4923                         (Data**)(&(cell->sfAllocArr[idx].rarInfo.raRntiInfo[indx].\
4924                               crntiInfo)),
4925                         (sizeof(RgInfCrntiInfo)* (cellUl->maxMsg3PerUlSf)));
4926             }
4927             /* Deallocate memory for "scheduled RAR" Info */
4928             /* ccpu00117052 - MOD - Passing double pointer
4929                for proper NULLP assignment*/
4930             rgSCHUtlFreeSBuf(inst,
4931                   (Data**)(&(cell->sfAllocArr[idx].rarInfo.raRntiInfo)),
4932                   (sizeof(RgInfRaRntiInfo)*RGSCH_MAX_RARNTI_PER_DL_SF));
4933          }
4934          /* Deallocate memory for "scheduled UE" Info */
4935          if (cell->sfAllocArr[idx].ueInfo.allocInfo != NULLP)
4936          {
4937             /* Freeing with additional location, to accommodate TA
4938                scheduling along with maximum no of UEs per SF */
4939             /* ccpu00117052 - MOD - Passing double pointer
4940                for proper NULLP assignment*/
4941             rgSCHUtlFreeSBuf(inst,
4942                   (Data**)(&(cell->sfAllocArr[idx].ueInfo.allocInfo)),
4943                   (sizeof(RgInfUeAlloc)*RGSCH_MAX_UE_PER_DL_SF));
4944          }
4945       }
4946
4947 #ifdef EMTC_ENABLE
4948    rgSCHEmtcUtlPutSfAlloc(cell);
4949 #endif
4950    return ROK;
4951
4952 }
4953
4954 /***********************************************************
4955  *
4956  *     Func : rgSCHUtlAllocSBuf
4957  *
4958  *     Desc : Utility Function to Allocate static buffer.
4959  *            Memory allocated is assumed contiguous.
4960  *
4961  *
4962  *     Ret  : ROK
4963  *            RFAILED
4964  *
4965  *     Notes: Caller doesnt need to raise the alarm in case of memory
4966  *            allocation gets failed.
4967  *
4968  *     File : rg_utl.c
4969  *
4970  **********************************************************/
4971 #ifdef ANSI
4972 S16 rgSCHUtlAllocSBuf
4973 (
4974 Inst    inst,               /* Instance of the invoking scheduler */
4975 Data    **pData,            /* Pointer of the data to be returned */
4976 Size    size                /* size */
4977 )
4978 #else
4979 S16 rgSCHUtlAllocSBuf(inst, pData, size)
4980 Inst    inst;              /* Instance of the invoking scheduler */
4981 Data    **pData;            /* Pointer of the data to be returned */
4982 Size    size;               /* size */
4983 #endif
4984 {
4985    /* Moving alarm diagnostics to available scope */
4986
4987    /* Initialize the param to NULLP */
4988    *pData = NULLP;
4989
4990    /* May not be necessary for data performance path */
4991 #ifndef NO_ERRCLS
4992    if (size == 0)
4993    {
4994       return RFAILED;
4995    }
4996 #endif
4997
4998    /* allocate buffer */
4999 #ifdef MS_MBUF_CORRUPTION /* Should be enabled when debugging mbuf corruption */
5000    MS_BUF_ADD_ALLOC_CALLER();
5001 #endif /* */
5002    if (SGetSBuf(rgSchCb[inst].rgSchInit.region, rgSchCb[inst].rgSchInit.pool,
5003                       pData, size) != ROK)
5004    {
5005      RgUstaDgn dgn;      /* Alarm diagnostics structure */
5006      dgn.type = LRG_USTA_DGNVAL_MEM;
5007      dgn.u.mem.region = rgSchCb[inst].rgSchInit.region;
5008      dgn.u.mem.pool = rgSchCb[inst].rgSchInit.pool;
5009      /*  Send an alarm to Layer Manager */
5010      rgSCHLmmStaInd(inst, LCM_CATEGORY_RESOURCE, LCM_EVENT_SMEM_ALLOC_FAIL,
5011                                        LCM_CAUSE_MEM_ALLOC_FAIL, &dgn);
5012      RGSCHLOGERROR(inst, ERRCLS_DEBUG, ERG015, 0, "Unable to Allocate Buffer");
5013      RLOG_ARG0(L_ERROR,DBG_INSTID,inst, "Unable to Allocate the Buffer");
5014      return RFAILED;
5015    }
5016
5017
5018    /* zero out the allocated memory */
5019    memset(*pData, 0x00, size);
5020
5021    return ROK;
5022
5023 } /* end of rgSCHUtlAllocSBuf */
5024
5025 \f
5026 /*
5027 *
5028 *       Fun:   rgSCHUtlFreeSBuf
5029 *
5030 *       Desc:  The argument to rgSCHUtlFreeSBuf() is a pointer to a block
5031 *              previously allocated by rgSCHUtlAllocSBuf() and size. It
5032 *              deallocates the memory.
5033 *
5034 *       Ret:   void
5035 *
5036 *       Notes: None
5037 *       File:  rg_utl.c
5038 */
5039 #ifdef ANSI
5040 Void rgSCHUtlFreeSBuf
5041 (
5042 Inst inst,          /* Instance of the invoking scheduler */
5043 Data **data,         /* pointer to data */
5044 Size size           /* size */
5045 )
5046 #else
5047 Void rgSCHUtlFreeSBuf(inst, data, size)
5048 Inst inst;          /* Instance of the invoking scheduler */
5049 Data **data;         /* pointer to data */
5050 Size size;          /* size */
5051 #endif
5052 {
5053
5054    S16 ret;
5055
5056    if ((data == NULLP) || (*data == NULLP) || (size == 0))
5057    {
5058       return;
5059    }
5060
5061
5062 #ifdef MS_MBUF_CORRUPTION /* Should be enabled when debugging mbuf corruption */
5063    MS_BUF_ADD_CALLER();
5064 #endif /* */
5065    /* Deallocate buffer */
5066    ret = SPutSBuf(rgSchCb[inst].rgSchInit.region,
5067                   rgSchCb[inst].rgSchInit.pool, (*data), size);
5068
5069    if (ret != ROK)
5070    {
5071       RGSCHLOGERROR(inst, ERRCLS_DEBUG, ERG016, (ErrVal) 0,
5072                  "rgSCHUtlFreeSBuf failed.\n");
5073       RLOG_ARG0(L_ERROR,DBG_INSTID,inst, "rgSCHUtlFreeSBuf failed");
5074       return;
5075    }
5076
5077    /* ccpu00117052 - ADD - Assigning the pointer to NULLP */
5078    *data = NULLP;
5079
5080    return;
5081 } /* end of rgSCHUtlFreeSBuf */
5082
5083 \f
5084 #ifdef RGR_SI_SCH
5085 /*
5086 *
5087 *       Fun:   rgSCHUtlFreeWarningSiSeg
5088 *
5089 *       Desc:  This is used to deallocate Warning SI Seg.
5090 *
5091 *       Ret:   void
5092 *
5093 *       Notes: None
5094 *
5095 *       File:  rg_utl.c
5096 */
5097 #ifdef ANSI
5098 Void rgSCHUtlFreeWarningSiSeg
5099 (
5100 Region        reg,
5101 Pool          pool,
5102 CmLListCp     *siPduLst          
5103 )
5104 #else
5105 Void rgSCHUtlFreeWarningSiSeg(reg, pool, siPduLst)
5106 Region        reg;
5107 Pool          pool;
5108 CmLListCp     *siPduLst;          
5109 #endif
5110 {
5111    CmLList      *node;
5112    Buffer       *pdu;
5113
5114       while (siPduLst->first != NULLP)
5115       {
5116          node = siPduLst->first;
5117          pdu = (Buffer *)node->node;
5118          cmLListDelFrm(siPduLst, node);
5119          RGSCH_FREE_MSG(pdu);
5120          SPutSBuf(reg, pool, (Data *)node,sizeof(CmLList));
5121          node = NULLP;
5122       }
5123
5124    return;
5125 } /* end of rgSCHUtlFreeWarningSiSeg */         
5126
5127 \f
5128 /*
5129 *
5130 *       Fun:   rgSCHUtlFreeWarningSiPdu
5131 *
5132 *       Desc:  This is used to deallocate Warning SI PDU.
5133 *
5134 *       Ret:   void
5135 *
5136 *       Notes: None
5137 *
5138 *       File:  rg_utl.c
5139 */
5140 #ifdef ANSI
5141 Void rgSCHUtlFreeWarningSiPdu
5142 (
5143 RgSchCellCb       *cell
5144 )
5145 #else
5146 Void rgSCHUtlFreeWarningSiPdu(cell)
5147 RgSchCellCb       *cell;
5148 #endif
5149 {
5150    CmLList            *node;
5151    Buffer             *pdu;
5152    RgSchWarningSiInfo *warningSi;
5153    RgSchWarningSiPdu  *warningSiPdu; 
5154
5155    warningSi = (RgSchWarningSiInfo *) cell->siCb.\
5156                   siArray[cell->siCb.siCtx.siId-1].si; 
5157    /* ccpu00136659: CMAS ETWS design changes */
5158    CM_LLIST_FIRST_NODE(&warningSi->warningSiMsg.segLstCp, node);
5159    if (node == NULLP)
5160    {
5161       return;
5162    }
5163
5164    warningSiPdu = (RgSchWarningSiPdu *)node->node;
5165    pdu = warningSiPdu->pdu;
5166    /* ccpu00136659: CMAS ETWS design changes */
5167    cmLListDelFrm(&warningSi->warningSiMsg.segLstCp, node); 
5168    RGSCH_FREE_MSG(pdu);
5169    if(warningSi->warningSiMsg.segLstCp.count == 0)
5170    {
5171       /* ccpu00136659: CMAS ETWS design changes */
5172       cell->siCb.siArray[cell->siCb.siCtx.siId-1].si = NULLP;
5173       rgSCHUtlRgrWarningSiCfgCfm(cell->instIdx,
5174             rgSchCb[cell->instIdx].rgrSap->sapCfg.spId,
5175             cell->siCb.warningSi[warningSi->idx].siId,
5176             warningSi->warningSiMsg.transId, RGR_CFG_CFM_TX_COMPLETE);
5177    }                                                                                 
5178
5179    return;
5180
5181 } /* end of rgSCHUtlFreeWarningSiPdu */         
5182  
5183 \f
5184 /*
5185 *
5186 *       Fun:   rgSCHUtlGetWarningSiPdu
5187 *
5188 *       Desc:  This is used to get Warning SI PDU for Scheduling. 
5189 *
5190 *       Ret:   
5191 *
5192 *       Notes: None
5193 *
5194 *       File:  rg_utl.c
5195 */
5196 #ifdef ANSI
5197 Buffer *rgSCHUtlGetWarningSiPdu
5198 (
5199 RgSchCellCb             *cell
5200 )
5201 #else
5202 Buffer *rgSCHUtlGetWarningSiPdu(cell)
5203 RgSchCellCb             *cell;
5204 #endif
5205 {
5206    RgSchWarningSiInfo  *warningSi;
5207    RgSchWarningSiPdu  *warningSiPdu; 
5208    Buffer       *pdu;
5209    CmLList      *node;
5210
5211    warningSi = (RgSchWarningSiInfo *) cell->siCb.
5212    siArray[cell->siCb.siCtx.siId-1].si; 
5213    /* ccpu00136659: CMAS ETWS design changes */
5214    CM_LLIST_FIRST_NODE(&warningSi->warningSiMsg.segLstCp, node);
5215    if (node != NULLP)
5216    {
5217       warningSiPdu = (RgSchWarningSiPdu *)node->node;
5218       pdu = warningSiPdu->pdu;
5219       return (pdu);
5220    }
5221    else
5222    {
5223       return (NULLP);
5224    }                                                  
5225 } /* rgSCHUtlGetWarningSiPdu  */    
5226
5227 \f
5228 /*
5229 *
5230 *       Fun:   rgSCHUtlGetMcsAndNPrb
5231 *
5232 *       Desc:  This is used to get mcs and nPrb value. 
5233 *
5234 *       Ret:   
5235 *
5236 *       Notes: None
5237 *
5238 *       File:  rg_utl.c
5239 */
5240 #ifdef ANSI
5241 S16 rgSCHUtlGetMcsAndNPrb
5242 (
5243 RgSchCellCb         *cell,
5244 uint8_t                  *nPrb,
5245 uint8_t                  *mcs,
5246 MsgLen              *msgLen
5247 )
5248 #else
5249 S16 rgSCHUtlGetMcsAndNPrb(cell, nPrb, mcs, msgLen)
5250 RgSchCellCb         *cell;
5251 uint8_t                  *nPrb;
5252 uint8_t                  *mcs;
5253 MsgLen              *msgLen;
5254 #endif
5255 {
5256    RgSchWarningSiInfo  *warningSi;
5257    RgSchWarningSiPdu  *warningSiPdu; 
5258    CmLList      *node;
5259
5260    if(cell->siCb.siCtx.warningSiFlag == FALSE)
5261    {
5262       *mcs =  cell->siCb.crntSiInfo.siInfo[cell->siCb.siCtx.siId-1].mcs;
5263       *nPrb =  cell->siCb.crntSiInfo.siInfo[cell->siCb.siCtx.siId-1].nPrb;
5264       *msgLen = cell->siCb.crntSiInfo.siInfo[cell->siCb.siCtx.siId-1].msgLen;
5265    }
5266    else
5267    {
5268       warningSi = (RgSchWarningSiInfo *) cell->siCb.
5269             siArray[cell->siCb.siCtx.siId-1].si; 
5270       /* ccpu00136659: CMAS ETWS design changes */
5271       CM_LLIST_FIRST_NODE(&warningSi->warningSiMsg.segLstCp, node);
5272       if (node == NULLP)
5273       {
5274         return RFAILED;
5275       }
5276       
5277       warningSiPdu = (RgSchWarningSiPdu *)node->node;
5278       *mcs = warningSiPdu->mcs;
5279       *nPrb = warningSiPdu->nPrb;
5280       *msgLen = warningSiPdu->msgLen;
5281       return ROK;
5282             
5283    }
5284    return ROK;
5285 } /* rgSCHUtlGetMcsAndNPrb  */     
5286
5287 /*
5288 *
5289 *       Fun:   rgSCHUtlCalMacAndPrb
5290 *
5291 *       Desc:  This is used to Calculate mcs and nPrb value for SIB1 and SIs. 
5292 *
5293 *       Ret:   
5294 *
5295 *       Notes: None
5296 *
5297 *       File:  rg_utl.c
5298 */
5299 #ifdef ANSI
5300 S16 rgSCHUtlCalMcsAndNPrb
5301 (
5302 RgSchCellCb         *cell,
5303 uint8_t                  cfgType,
5304 MsgLen              msgLen,
5305 uint8_t                  siId
5306 )
5307 #else
5308 S16 rgSCHUtlCalMcsAndNPrb(cell, nPrb, mcs, msgLen)
5309 RgSchCellCb         *cell;
5310 uint8_t                  cfgType;
5311 MsgLen              msgLen;
5312 uint8_t                  siId;
5313 #endif
5314 {
5315    uint8_t mcs = 0;
5316    uint8_t nPrb = 0;
5317
5318       /*Get the nPrb and mcs parametr values */
5319    if (rgSCHUtlGetAllwdCchTbSz(msgLen*8, &nPrb, &mcs) != (msgLen*8))
5320       {
5321          RLOG_ARG0(L_ERROR,DBG_CELLID,cell->cellId, "msgLen does "
5322             "not match any valid TB Size");
5323          return RFAILED;
5324       }
5325
5326
5327    if(cfgType == RGR_SI_CFG_TYPE_SIB1 || cfgType == RGR_SI_CFG_TYPE_SIB1_PWS)
5328    {
5329
5330       if(cell->siCb.crntSiInfo.sib1Info.sib1 == NULLP)
5331       {
5332          cell->siCb.crntSiInfo.sib1Info.mcs = mcs;
5333          cell->siCb.crntSiInfo.sib1Info.nPrb = nPrb;
5334          cell->siCb.crntSiInfo.sib1Info.msgLen = msgLen;
5335       }
5336       else
5337       {
5338          cell->siCb.newSiInfo.sib1Info.mcs = mcs;
5339          cell->siCb.newSiInfo.sib1Info.nPrb= nPrb;
5340          cell->siCb.newSiInfo.sib1Info.msgLen = msgLen;
5341       }
5342    }
5343
5344     
5345    if(cfgType == RGR_SI_CFG_TYPE_SI)
5346    {
5347       if(cell->siCb.crntSiInfo.siInfo[siId-1].si == NULLP &&
5348          !(cell->siCb.siBitMask & RGSCH_SI_SICFG_UPD))
5349       {
5350          cell->siCb.crntSiInfo.siInfo[siId-1].mcs = mcs;
5351          cell->siCb.crntSiInfo.siInfo[siId-1].nPrb = nPrb;
5352          cell->siCb.crntSiInfo.siInfo[siId-1].msgLen = msgLen;
5353       }
5354       else
5355       {
5356          cell->siCb.newSiInfo.siInfo[siId-1].mcs = mcs;
5357          cell->siCb.newSiInfo.siInfo[siId-1].nPrb= nPrb;
5358          cell->siCb.newSiInfo.siInfo[siId-1].msgLen = msgLen;
5359       }
5360    }
5361
5362    if(cfgType == RGR_SI_CFG_TYPE_SIB8_CDMA)
5363    {
5364       cell->siCb.crntSiInfo.siInfo[siId-1].mcs = mcs;
5365       cell->siCb.crntSiInfo.siInfo[siId-1].nPrb = nPrb;
5366       cell->siCb.crntSiInfo.siInfo[siId-1].msgLen = msgLen;
5367    }
5368
5369     return ROK;
5370 }
5371 #endif
5372
5373 /***********************************************************
5374  *
5375  *     Func : rgSCHUtlFillDgnParams
5376  *
5377  *     Desc : Utility Function to Fill Diagonostic params.
5378  *
5379  *     Ret  : None.
5380  *
5381  *     Notes: None.
5382  *
5383  *     File : rg_utl.c
5384  *
5385  **********************************************************/
5386 #ifdef ANSI
5387 Void rgSCHUtlFillDgnParams
5388 (
5389 Inst        inst,
5390 RgUstaDgn   *dgn,
5391 uint8_t          dgnType
5392 )
5393 #else
5394 Void rgSCHUtlFillDgnParams(inst, dgn, dgnType)
5395 Inst        inst;
5396 RgUstaDgn   *dgn;
5397 uint8_t          dgnType;
5398 #endif
5399 {
5400
5401    switch(dgnType)
5402    {
5403       case LRG_USTA_DGNVAL_MEM:
5404          dgn->type = (uint8_t) LRG_USTA_DGNVAL_MEM;
5405          dgn->u.mem.region  = rgSchCb[inst].rgSchInit.region;
5406          dgn->u.mem.pool    = rgSchCb[inst].rgSchInit.pool;
5407       break;
5408
5409       default:
5410       break;
5411    }
5412
5413    return;
5414 } /* end of rgSCHUtlFillDgnParams */
5415
5416 /***********************************************************
5417  *
5418  *     Func : rgSCHUtlGetPstToLyr
5419  *
5420  *     Desc : Utility Function to get the pst structure to post a message to MAC
5421  *
5422  *
5423  *     Ret  : ROK
5424  *            RFAILED
5425  *
5426  *     Notes: This function should be called while sending a msg from
5427  *     scheduler instance to MAC
5428  *
5429  *     File : rg_utl.c
5430  *
5431  **********************************************************/
5432 #ifdef ANSI
5433 Void rgSCHUtlGetPstToLyr
5434 (
5435 Pst     *pst,
5436 RgSchCb *schCb,
5437 Inst    macInst
5438 )
5439 #else
5440 Void rgSCHUtlGetPstToLyr (pst, schCb, macInst)
5441 Pst     *pst;
5442 RgSchCb *schCb;
5443 Inst    macInst;
5444 #endif
5445 {
5446
5447    /* Only the needed params are filled */
5448    pst->region = schCb->rgSchInit.region;
5449    pst->pool = schCb->rgSchInit.pool;
5450    pst->srcInst = schCb->rgSchInit.inst+SCH_INST_START;
5451    pst->srcProcId = schCb->rgSchInit.procId;
5452    pst->dstProcId = schCb->rgSchInit.procId;
5453
5454    pst->dstInst = macInst;
5455    pst->dstEnt = ENTMAC;
5456    pst->srcEnt = ENTMAC;
5457    pst->selector = 0;
5458    pst->prior     = PRIOR0;
5459    pst->intfVer   = 0;
5460    pst->route   = RTESPEC;
5461
5462    return;
5463 } /* end of rgSCHUtlGetPstToLyr */
5464
5465 /** @brief This function fills in the common lc information to be sent to MAC
5466  *
5467  * @details
5468  *
5469  *     Function: rgSCHUtlFillRgInfCmnLcInfo
5470  *       @param  RgSchDlSf       *sf,
5471  *       @param  RgInfSfAlloc    *sfAlloc,
5472  *       @param  CmLteLcId       lcId,
5473  *       @param  Bool            sendInd
5474  *
5475  * @return  S16
5476  *      -# ROK
5477  *      -# RFAILED
5478  */
5479 #ifdef ANSI
5480 S16 rgSCHUtlFillRgInfCmnLcInfo
5481 (
5482 RgSchDlSf       *sf,
5483 RgInfSfAlloc    *sfAlloc,
5484 CmLteLcId       lcId,
5485 Bool            sendInd
5486 )
5487 #else
5488 S16 rgSCHUtlFillRgInfCmnLcInfo(sf, sfAlloc, lcId, sendInd)
5489 RgSchDlSf       *sf;
5490 RgInfSfAlloc    *sfAlloc;
5491 CmLteLcId       lcId;
5492 Bool            sendInd;
5493 #endif
5494 {
5495
5496    if((sf->bch.tbSize)&&
5497       !(sfAlloc->cmnLcInfo.bitMask & RGINF_BCH_INFO))
5498    {
5499 #ifndef RGR_SI_SCH
5500       sfAlloc->cmnLcInfo.bchInfo.lcId = lcId;
5501 #endif
5502       sfAlloc->cmnLcInfo.bitMask |= RGINF_BCH_INFO;
5503    }
5504    else if((sf->bcch.pdcch != NULLP)&&
5505       !(sfAlloc->cmnLcInfo.bitMask & RGINF_BCCH_INFO))
5506    {
5507       sfAlloc->cmnLcInfo.bcchInfo.rnti = RGSCH_SI_RNTI;
5508       rgSCHUtlFillPdschDciInfo(&(sfAlloc->cmnLcInfo.bcchInfo.dciInfo),
5509                                        &(sf->bcch.pdcch->dci));
5510 #ifndef RGR_SI_SCH
5511       sfAlloc->cmnLcInfo.bcchInfo.lcId = lcId;
5512       sfAlloc->cmnLcInfo.bcchInfo.sndStatInd = sendInd;
5513 #endif
5514       sfAlloc->cmnLcInfo.bitMask |= RGINF_BCCH_INFO;
5515    }
5516    else if((sf->pcch.pdcch != NULLP) &&
5517       !(sfAlloc->cmnLcInfo.bitMask & RGINF_PCCH_INFO))
5518    {
5519       sfAlloc->cmnLcInfo.pcchInfo.rnti = RGSCH_P_RNTI;
5520       rgSCHUtlFillPdschDciInfo(&(sfAlloc->cmnLcInfo.pcchInfo.dciInfo),
5521                                          &(sf->pcch.pdcch->dci));
5522       sfAlloc->cmnLcInfo.pcchInfo.lcId = lcId;
5523       sfAlloc->cmnLcInfo.bitMask |= RGINF_PCCH_INFO;
5524    }
5525    return ROK;
5526 }
5527
5528 /** @brief This function fills in the RAR information to be sent to MAC
5529  *
5530  * @details
5531  *
5532  *     Function: rgSCHUtlFillRgInfRarInfo
5533  *
5534  * @param  RgSchCellCb  *cell 
5535  * @param  RgSchDlSf    *sf 
5536  * @param  RgInfSfAlloc *sfAlloc
5537  * @return  S16
5538  *      -# ROK
5539  *      -# RFAILED
5540  */
5541 #ifdef ANSI
5542 S16 rgSCHUtlFillRgInfRarInfo
5543 (
5544 RgSchDlSf       *sf,
5545 RgInfSfAlloc    *sfAlloc,
5546 RgSchCellCb     *cell
5547 )
5548 #else
5549 S16 rgSCHUtlFillRgInfRarInfo(sf, sfAlloc, cell)
5550 RgSchDlSf       *sf;
5551 RgInfSfAlloc    *sfAlloc;
5552 RgSchCellCb     *cell;
5553 #endif 
5554 {
5555    uint8_t               idx;
5556    CmLListCp        *lnkLst;
5557    CmLList          *tmp;
5558    RgSchRaCb        *raCb;
5559    RgSchUeCb        *ue;
5560    RgInfRaRntiInfo  *raRntiAlloc;
5561    uint8_t               noRaRsps;
5562    RgSchCmnDlCell   *cellDl = RG_SCH_CMN_GET_DL_CELL(cell);
5563
5564 #ifdef LTE_TDD
5565    noRaRsps = RGSCH_MAX_TDD_RA_RSP_ALLOC;
5566 #else
5567    noRaRsps = RGSCH_MAX_RA_RSP_ALLOC;
5568 #endif
5569
5570    for(idx =0; idx < noRaRsps; idx++)
5571    {
5572       if (sf->raRsp[idx].pdcch == NULLP)
5573       {
5574          /* No further raResp Allocations. */
5575          break;
5576       }
5577       /* Added Dl TB count for RACH Response transmission*/
5578 #ifdef LTE_L2_MEAS
5579       cell->dlUlTbCnt.tbTransDlTotalCnt++;
5580 #endif      
5581       raRntiAlloc = &(sfAlloc->rarInfo.raRntiInfo[idx]);
5582       raRntiAlloc->raRnti = sf->raRsp[idx].raRnti;
5583       raRntiAlloc->schdTbSz = sf->raRsp[idx].tbSz;
5584       raRntiAlloc->numCrnti = 0;
5585       rgSCHUtlFillPdschDciInfo(&(raRntiAlloc->dciInfo),
5586                       &(sf->raRsp[idx].pdcch->dci));
5587       /* RACHO : fill backoff indicator information */
5588       raRntiAlloc->backOffInd = sf->raRsp[idx].backOffInd;
5589
5590       /* Fill for contention free UEs*/
5591       lnkLst = &(sf->raRsp[idx].contFreeUeLst);
5592       CM_LLIST_FIRST_NODE(lnkLst, tmp);
5593       while (tmp)
5594       {
5595          ue = (RgSchUeCb *)tmp->node;
5596          tmp = tmp->next;
5597          raRntiAlloc->crntiInfo[raRntiAlloc->numCrnti].tmpCrnti = ue->ueId;
5598          raRntiAlloc->crntiInfo[raRntiAlloc->numCrnti].isContFree = TRUE;
5599          raRntiAlloc->crntiInfo[raRntiAlloc->numCrnti].rapId = ue->ul.rarGrnt.rapId;
5600 #ifndef MAC_5GTF_UPDATE
5601          raRntiAlloc->crntiInfo[raRntiAlloc->numCrnti].grnt.hop =
5602                                                         ue->ul.rarGrnt.hop;
5603          raRntiAlloc->crntiInfo[raRntiAlloc->numCrnti].grnt.cqiBit =
5604                                                         ue->ul.rarGrnt.cqiReqBit;
5605 #endif
5606          /* SHASHAHNK ADD RIV CALC */
5607          raRntiAlloc->crntiInfo[raRntiAlloc->numCrnti].grnt.rbStart =
5608                                                         ue->ul.rarGrnt.rbStart;
5609          raRntiAlloc->crntiInfo[raRntiAlloc->numCrnti].grnt.numRb =
5610                                                         ue->ul.rarGrnt.numRb;
5611          raRntiAlloc->crntiInfo[raRntiAlloc->numCrnti].grnt.tpc =
5612                                                         ue->ul.rarGrnt.tpc;
5613          raRntiAlloc->crntiInfo[raRntiAlloc->numCrnti].grnt.iMcsCrnt =
5614                                                         ue->ul.rarGrnt.iMcsCrnt;
5615          raRntiAlloc->crntiInfo[raRntiAlloc->numCrnti].ta = ue->ul.rarGrnt.ta;
5616          raRntiAlloc->numCrnti++;
5617          cmLListDelFrm(lnkLst, &ue->ul.rarGrnt.raRspLnk);
5618          ue->ul.rarGrnt.raRspLnk.node = (PTR)NULLP;
5619       }
5620       /* Fill for contention based UEs*/
5621       lnkLst = &(sf->raRsp[idx].raRspLst);
5622
5623       CM_LLIST_FIRST_NODE(lnkLst, tmp);
5624
5625       while((NULLP != tmp) && ((RgSchRaCb *)tmp->node != NULLP))
5626       {
5627          raCb     = (RgSchRaCb *)tmp->node;
5628
5629          raRntiAlloc->crntiInfo[raRntiAlloc->numCrnti].tmpCrnti = raCb->tmpCrnti;
5630          raRntiAlloc->crntiInfo[raRntiAlloc->numCrnti].isContFree = FALSE;
5631          raRntiAlloc->crntiInfo[raRntiAlloc->numCrnti].rapId = raCb->rapId;
5632          raRntiAlloc->crntiInfo[raRntiAlloc->numCrnti].ta.pres = TRUE;
5633          raRntiAlloc->crntiInfo[raRntiAlloc->numCrnti].ta.val = raCb->ta.val;
5634 #ifndef MAC_5GTF_UPDATE
5635          raRntiAlloc->crntiInfo[raRntiAlloc->numCrnti].grnt.hop =
5636                                                         raCb->msg3Grnt.hop;
5637          raRntiAlloc->crntiInfo[raRntiAlloc->numCrnti].grnt.cqiBit = FALSE;
5638 #endif
5639          raRntiAlloc->crntiInfo[raRntiAlloc->numCrnti].grnt.rbStart =
5640                                                         raCb->msg3Grnt.rbStart;
5641          raRntiAlloc->crntiInfo[raRntiAlloc->numCrnti].grnt.numRb =
5642                                                         raCb->msg3Grnt.numRb;
5643          raRntiAlloc->crntiInfo[raRntiAlloc->numCrnti].grnt.tpc =
5644                                                         raCb->msg3Grnt.tpc;
5645          raRntiAlloc->crntiInfo[raRntiAlloc->numCrnti].grnt.iMcsCrnt =
5646                                                         raCb->msg3Grnt.iMcsCrnt;
5647          raRntiAlloc->crntiInfo[raRntiAlloc->numCrnti].grnt.delayBit =
5648                                                         raCb->msg3Grnt.delayBit;
5649          /* For initial attaching UEs Aperiodic CQI need not be triggered */
5650          raRntiAlloc->numCrnti++;
5651          /* Search the next node */
5652          CM_LLIST_NEXT_NODE(lnkLst, tmp);
5653       }
5654    }
5655    sfAlloc->rarInfo.numRaRntis = idx;
5656    /* ccpu00132314-ADD-Update the tx power allocation info  
5657       TODO-Need to add a check for max tx power per symbol */
5658    sfAlloc->rarInfo.txPwrOffset = cellDl->rarTxPwrOffset;
5659
5660    return ROK;
5661 } /* end of rgSCHUtlFillRgInfRarInfo */
5662
5663 /** @brief This function fills in the pdsch data related allocation Info
5664  *         from the pdcch DCI info.
5665  * slot
5666  *
5667  * @details
5668  *
5669  *     Function: rgSCHUtlFillPdschDciInfo
5670  *
5671  *         Processing steps:
5672  *         - Depending upon the DCI Format, fill the appropriate fields.
5673  *
5674  * @param  [out] TfuPdschDciInfo *pdschDci
5675  * @param  [in]  TfuDciInfo      *pdcchDci
5676  * @return  S16
5677  *      -# ROK
5678  *      -# RFAILED
5679  */
5680 #ifdef ANSI
5681 S16 rgSCHUtlFillPdschDciInfo
5682 (
5683 TfuPdschDciInfo *pdsch,
5684 TfuDciInfo      *pdcchDci
5685 )
5686 #else
5687 S16 rgSCHUtlFillPdschDciInfo(pdsch, pdcchDci)
5688 TfuPdschDciInfo *pdsch;
5689 TfuDciInfo      *pdcchDci;
5690 #endif
5691 {
5692
5693 #ifdef EMTC_ENABLE
5694   S16 ret = ROK; 
5695 #endif
5696    pdsch->format = pdcchDci->dciFormat;
5697    switch(pdcchDci->dciFormat)
5698    {
5699       case TFU_DCI_FORMAT_1:
5700          pdsch->u.format1AllocInfo = pdcchDci->u.format1Info.allocInfo;
5701          break;
5702       case TFU_DCI_FORMAT_1A:
5703          if (pdcchDci->u.format1aInfo.isPdcchOrder == FALSE)
5704          {
5705             pdsch->u.format1aAllocInfo = pdcchDci->u.format1aInfo.t.pdschInfo.allocInfo;
5706          }
5707          break;
5708       case TFU_DCI_FORMAT_1B:
5709          pdsch->u.format1bAllocInfo = pdcchDci->u.format1bInfo.allocInfo;
5710          break;
5711       case TFU_DCI_FORMAT_1C:
5712          pdsch->u.format1cAllocInfo = pdcchDci->u.format1cInfo;
5713          break;
5714       case TFU_DCI_FORMAT_1D:
5715          pdsch->u.format1dAllocInfo = pdcchDci->u.format1dInfo.allocInfo;
5716          break;
5717       case TFU_DCI_FORMAT_2:
5718          pdsch->u.format2AllocInfo = pdcchDci->u.format2Info.allocInfo;
5719          break;
5720       case TFU_DCI_FORMAT_2A:
5721          pdsch->u.format2AAllocInfo = pdcchDci->u.format2AInfo.allocInfo;
5722          break;
5723 #ifdef RG_5GTF
5724                 case TFU_DCI_FORMAT_B1:
5725          pdsch->u.formatB1Info = pdcchDci->u.formatB1Info;
5726          break;
5727       case TFU_DCI_FORMAT_B2:
5728          pdsch->u.formatB2Info = pdcchDci->u.formatB2Info;
5729          break;
5730 #endif
5731       default:
5732 #ifdef EMTC_ENABLE
5733  ret = rgSCHEmtcUtlFillPdschDciInfo(pdsch, pdcchDci);
5734  if(RFAILED == ret)
5735  {
5736       return RFAILED;
5737          }
5738 #else  
5739          return RFAILED;
5740 #endif
5741    }
5742    return ROK;
5743 }
5744
5745 /* LTE_ADV_FLAG_REMOVED_START */
5746 /**
5747  * @brief This function resets temporary variables in Pool
5748  * @details
5749  *
5750  *     Function: rgSchSFRResetPoolVariables
5751  *
5752  *     Invoked by: rgSCHSFRUtlTotalPoolInit
5753  *
5754  *  @param[in]  RgSchCellCb*     cell
5755  *  @param[in]  RgSubFrm*     subFrm
5756  *  @return  Void
5757  *
5758  **/
5759 #ifdef ANSI
5760 Void rgSchDSFRPwrCheck
5761 (
5762  RgSchDlSf               *sf,
5763  Bool                    *isAllUePwrHigh
5764  )
5765 #else
5766 static Void rgSchDSFRPwrCheck(sf, isAllUePwrHigh)
5767    RgSchDlSf               *sf;
5768    Bool                    *isAllUePwrHigh;
5769
5770 #endif
5771 {     
5772    RgSchSFRPoolInfo *sfrCCPool;
5773
5774    CmLListCp   *l;
5775    CmLList     *n;   
5776
5777    l = &sf->sfrTotalPoolInfo.ccPool;    
5778    n = cmLListFirst(l);
5779    while(n)
5780    {    
5781       sfrCCPool = (RgSchSFRPoolInfo*)n->node;
5782       if((sfrCCPool->poolstartRB == sfrCCPool->pwrHiCCRange.startRb) &&
5783             (sfrCCPool->poolendRB == sfrCCPool->pwrHiCCRange.endRb))
5784       {
5785          n = cmLListNext(l);
5786          if(n)
5787          {
5788             continue;
5789          }
5790          *isAllUePwrHigh = TRUE;
5791          break;
5792       }
5793       else
5794          break;   
5795    } 
5796 }
5797 /* LTE_ADV_FLAG_REMOVED_END */
5798 /***********************************************************
5799  *
5800  *     Func : rgSCHUtlFillRgInfTbInfo
5801  *
5802  *     Desc : Utility Function to fill the allocation info of each Tb
5803  *
5804  *
5805  *     Ret  :  void
5806  *
5807  *
5808  *     Notes: This function should be called while sending a msg from
5809  *     scheduler instance to MAC
5810  *
5811  *     File : rg_utl.c
5812  *
5813  **********************************************************/
5814 #ifdef ANSI
5815 static Void rgSCHUtlFillRgInfTbInfo
5816 (
5817 RgSchDlHqProcCb *hqP,
5818 RgInfUeAlloc    *allocInfo,
5819 RgSchCellCb     *cell
5820 )
5821 #else
5822 static Void rgSCHUtlFillRgInfTbInfo (hqP, allocInfo, cell)
5823 RgSchDlHqProcCb *hqP;
5824 RgInfUeAlloc    *allocInfo;
5825 RgSchCellCb     *cell;
5826 #endif
5827 {
5828    RgSchDlSf       *sf;
5829    uint8_t              idx;
5830    RgInfUeTbInfo   *tbInfo;
5831    uint8_t              tbCnt;
5832    /* LTE_ADV_FLAG_REMOVED_START */
5833 #ifdef TFU_UPGRADE
5834    static         uint32_t  tmpCnt = 0;
5835    Bool            isAllUePwrHigh = FALSE;
5836 #endif 
5837    /* LTE_ADV_FLAG_REMOVED_END */
5838    RgSchDlLcCb    *dlLcCb = NULLP;
5839    uint16_t             rlcHdrEstmt;
5840    uint8_t              lcId;
5841    /* RRM_RBC_X */
5842 #ifdef LTE_L2_MEAS
5843    uint8_t              prbUsed = 0;
5844 #endif
5845    /* RRM_RBC_Y */
5846
5847    CmLteTimingInfo        frm;
5848
5849    /* Get Downlink slot */
5850    frm   = cell->crntTime;
5851    RGSCH_INCR_SUB_FRAME(frm, RG_SCH_CMN_DL_DELTA);
5852    sf = rgSCHUtlSubFrmGet(cell, frm);
5853    /* Setting of fillCtrlPdu flag
5854       If both P-cell and S-cell are present,
5855       make TRUE for P-cell and FALSE for all s-cells
5856       For all other cases set TRUE */
5857 #ifdef LTE_ADV
5858    if ((rgSchCb[cell->instIdx].genCfg.forceCntrlSrbBoOnPCel) &&
5859          !RG_SCH_CMN_IS_PCELL_HQP(hqP))
5860    {
5861       allocInfo->fillCtrlPdu = FALSE;
5862    }
5863    else
5864    {
5865       allocInfo->fillCtrlPdu = TRUE;
5866    }
5867 #endif
5868
5869    allocInfo->tbStrtIdx = -1;
5870
5871
5872 #ifdef LTE_ADV
5873    allocInfo->tbReqInfo.sCellHqPId = 0xff;
5874    rgSCHLaaHndlFillRgInfTbInfo(cell, hqP, allocInfo);
5875 #endif
5876
5877    /*TODO:REEMA: Check and fill the isRetx */
5878    for(tbCnt = 0; tbCnt < 2; tbCnt++)
5879    {
5880       RgSchUeCb  *ue = NULLP;
5881       /*Changed as a result of CR timer*/
5882       if ((hqP->hqE->ue != NULLP)/* &&
5883       ((hqP->tbInfo[tbCnt].lchSchdData[0].lcId != 0) || \
5884        (hqP->tbInfo[tbCnt].schdTa.pres == PRSNT_NODEF))*/)
5885       {
5886          ue = hqP->hqE->ue;
5887          allocInfo->rnti = ue->ueId;
5888          allocInfo->doa = hqP->hqE->ue->mimoInfo.doa;
5889          allocInfo->txMode = (TfuTxMode)(hqP->hqE->ue->mimoInfo.txMode);
5890          allocInfo->puschRptUsd = hqP->hqE->ue->mimoInfo.puschFdbkVld;
5891          allocInfo->puschPmiInfo = hqP->hqE->ue->mimoInfo.puschPmiInfo;
5892          if(hqP->tbInfo[tbCnt].schdTa.pres == PRSNT_NODEF)
5893          {
5894             hqP->tbInfo[tbCnt].taSnt = TRUE;
5895          }
5896 #ifdef TFU_UPGRADE
5897          if (RG_SCH_IS_PAPRSNT(ue,hqP->hqE->cell))
5898          {
5899             /*update pA value */
5900             allocInfo->pa = (RG_SCH_CMN_GET_PA(ue,hqP->hqE->cell)).val;
5901          }
5902 #endif
5903
5904          /* LTE_ADV_FLAG_REMOVED_START */
5905          /* If ABS is enabled, calculate resource used */
5906          if((0 == tbCnt) && (RGR_ENABLE == ue->cell->lteAdvCb.absCfg.status))
5907          {
5908             /* For Macro count number resource used in Non-ABS SF */
5909             if(RGR_ABS_MUTE == ue->cell->lteAdvCb.absCfg.absPatternType)
5910             {
5911                if(RG_SCH_ABS_ENABLED_NONABS_SF == ue->cell->lteAdvCb.absDlSfInfo)
5912                {
5913                   ue->cell->lteAdvCb.absLoadInfo[ue->cell->lteAdvCb.absPatternDlIdx]+=
5914                      hqP->tbInfo[tbCnt].dlGrnt.numRb;
5915                }
5916             }
5917             /* For pico count number resource used in ABS SF for ABS UE */
5918             else if(RGR_ABS_TRANSMIT == ue->cell->lteAdvCb.absCfg.absPatternType)
5919             {
5920                if(RG_SCH_ABS_ENABLED_ABS_SF == ue->cell->lteAdvCb.absDlSfInfo)
5921                {
5922                   if(TRUE == ue->lteAdvUeCb.rgrLteAdvUeCfg.isAbsUe)
5923                   {
5924                      ue->cell->lteAdvCb.absLoadInfo[ue->cell->lteAdvCb.absPatternDlIdx]+=
5925                         hqP->tbInfo[tbCnt].dlGrnt.numRb;
5926                   }
5927                }
5928             }
5929          } 
5930
5931 #ifdef TFU_UPGRADE         
5932          /*if SFR is enabled*/
5933          allocInfo->isEnbSFR = (uint8_t)RG_SCH_CMN_IS_SFR_ENB(ue->cell); /* KW fix for LTE_ADV */
5934          if((ue->cell->lteAdvCb.dsfrCfg.status == RGR_ENABLE) && 
5935                (ue->lteAdvUeCb.rgrLteAdvUeCfg.isUeCellEdge == FALSE))
5936          {         
5937             rgSchDSFRPwrCheck(sf, &isAllUePwrHigh);          
5938          } 
5939          if(isAllUePwrHigh)
5940          {  
5941             allocInfo->pa = (uint8_t)ue->cell->lteAdvCb.sfrCfg.pwrThreshold.pHigh;  /* KW fix for LTE_ADV */  
5942             if(tmpCnt++ == 100000)
5943             {
5944                RLOG_ARG2(L_DEBUG,DBG_CELLID,ue->cell->cellId, 
5945                         "DSFR::ll UEs can go HIGH, PHigh(%d) for UE(%d)",allocInfo->pa, ue->ueId);
5946                tmpCnt = 0;
5947             }
5948          }    
5949          else
5950          {  
5951             if (allocInfo->isEnbSFR)
5952             {
5953                /*Update pA to Plow if it is cell-centred ,else pA will be pHigh*/
5954                if (ue->lteAdvUeCb.rgrLteAdvUeCfg.isUeCellEdge == TRUE)
5955                {  
5956                   allocInfo->pa = ue->cell->lteAdvCb.sfrCfg.pwrThreshold.pHigh;
5957                   if(tmpCnt++ == 100000)
5958                   {
5959                      RLOG_ARG2(L_DEBUG,DBG_CELLID,ue->cell->cellId, 
5960                               "SFR::UE is CELL EDGE, PHigh(%d) for UE(%d)",allocInfo->pa, ue->ueId);
5961                      tmpCnt = 0;
5962                   }
5963
5964                }  
5965                else
5966                {
5967                   if(TRUE == ue->lteAdvUeCb.isCCUePHigh)
5968                   {
5969                      allocInfo->pa = ue->cell->lteAdvCb.sfrCfg.pwrThreshold.pHigh;
5970                      ue->lteAdvUeCb.isCCUePHigh = FALSE;
5971                   }
5972                   else
5973                   {
5974                      allocInfo->pa = ue->cell->lteAdvCb.sfrCfg.pwrThreshold.pLow;
5975                      if(tmpCnt++ == 100000)
5976                      {
5977                         RLOG_ARG2(L_DEBUG,DBG_CELLID,ue->cell->cellId, 
5978                                  "SFR::UE is CELL CENTRE, PLow(%d) for UE(%d)\n",allocInfo->pa, ue->ueId);
5979                         tmpCnt = 0;
5980                      }
5981                   }
5982                }
5983             }
5984          }
5985          /* LTE_ADV_FLAG_REMOVED_END */
5986 #endif         
5987       }
5988       else
5989       {
5990          if (hqP->hqE->raCb)
5991          {
5992 #ifdef TFU_UPGRADE
5993             RgSchCmnDlCell   *cellDl = RG_SCH_CMN_GET_DL_CELL(cell);
5994 #endif 
5995 #ifdef LTEMAC_SPS
5996             allocInfo->pdcchRnti = hqP->hqE->raCb->tmpCrnti;
5997 #endif
5998             allocInfo->rnti  =  hqP->hqE->raCb->tmpCrnti;
5999 #ifdef TFU_UPGRADE
6000             /*ccpu00132314-ADD-Use a default pA value
6001               for msg4 */
6002             allocInfo->pa = cellDl->msg4pAVal; 
6003 #endif 
6004          }
6005       }
6006       /* If TB Is scheduled for this SF */
6007       if(hqP->tbInfo[tbCnt].state == HQ_TB_WAITING)
6008       {
6009          if (allocInfo->tbStrtIdx == -1){
6010             allocInfo->tbStrtIdx = tbCnt;
6011 #ifndef LTEMAC_SPS
6012             rgSCHUtlFillPdschDciInfo(&(allocInfo->dciInfo),
6013                                &(hqP->pdcch->dci));
6014 #else
6015             if (hqP->pdcch)
6016             {
6017                rgSCHUtlFillPdschDciInfo(&(allocInfo->dciInfo),
6018                      &(hqP->pdcch->dci));
6019             }
6020             else if ((ue) && (ue->dl.spsOccPdcch.rnti == ue->spsRnti))
6021             {
6022                rgSCHUtlFillPdschDciInfo(&(allocInfo->dciInfo),
6023                      &(ue->dl.spsOccPdcch.dci));
6024             }
6025 #endif /* ifndef LTEMAC_SPS */
6026          }
6027 #ifdef LTEMAC_SPS
6028             if (hqP->pdcch)
6029             {
6030                allocInfo->pdcchRnti = hqP->pdcch->rnti;
6031             }
6032             else if (ue)
6033             {
6034                allocInfo->pdcchRnti = ue->spsRnti;
6035             }
6036 #endif
6037          tbInfo = &(allocInfo->tbInfo[tbCnt]);
6038          allocInfo->nmbOfTBs++;
6039          allocInfo->hqProcId = hqP->procId;
6040          allocInfo->tbInfo[tbCnt].schdTbSz = hqP->tbInfo[tbCnt].tbSz;
6041
6042          tbInfo->disTb  = FALSE;
6043          if(!(hqP->tbInfo[tbCnt].txCntr))
6044          {
6045 #ifdef LTE_ADV
6046             if(!((rgSCHLaaCheckIfLAAProc(hqP)) && (TRUE ==
6047                         rgSCHLaaSCellEnabled(cell))))
6048 #endif
6049             {
6050                hqP->tbInfo[tbCnt].txCntr++;
6051             }
6052             for(idx = 0; idx < hqP->tbInfo[tbCnt].numLch; idx++)
6053             {
6054                tbInfo->schdDat[idx].lcId =\
6055                   hqP->tbInfo[tbCnt].lchSchdData[idx].lcId;
6056                tbInfo->schdDat[idx].numBytes =\
6057                   hqP->tbInfo[tbCnt].lchSchdData[idx].schdData;
6058                if(hqP->hqE->ue)
6059                {
6060                   lcId = hqP->tbInfo[tbCnt].lchSchdData[idx].lcId; 
6061                   if(lcId != 0)
6062                   {
6063                      dlLcCb = hqP->hqE->ue->dl.lcCb[lcId-1];
6064                      if(dlLcCb != NULLP)
6065                      {
6066                         RG_SCH_CMN_DL_GET_HDR_EST(dlLcCb, rlcHdrEstmt);
6067                         /* Update the totalBo with the scheduled bo */
6068                         (hqP->hqE->ue->totalBo <= tbInfo->schdDat[idx].numBytes - rlcHdrEstmt)?\
6069                                                   (hqP->hqE->ue->totalBo = 0):\
6070                                                   (hqP->hqE->ue->totalBo -= tbInfo->schdDat[idx].numBytes-rlcHdrEstmt);
6071
6072                         /* RRM_RBC_X */
6073 #ifdef LTE_L2_MEAS
6074                         prbUsed = ((hqP->tbInfo[tbCnt].\
6075                                  lchSchdData[idx].schdData  *
6076                                  hqP->tbInfo[tbCnt].dlGrnt.numRb) /
6077                               (hqP->tbInfo[0].tbSz + hqP->tbInfo[1].tbSz));
6078                         dlLcCb->qciCb->dlPrbCount += prbUsed;
6079                         if(dlLcCb->qciCb->qci > 0)
6080                         {
6081                            RG_SCH_CALC_GBR_UTILIZATION(cell, dlLcCb, prbUsed);
6082                         }
6083 #endif                        /* RRM_RBC_Y */
6084
6085 #ifdef RG_PFS_STATS
6086                         //if(!(hqP->hqE->ue->pfsStats.lcStats[lcId-1].isLcCntSet))
6087                         if(tbCnt == 0)
6088                         {
6089                            uint8_t idx = 0;
6090                            if (hqP->hqE->ue->cell == hqP->hqE->cell)
6091                            {
6092                               idx = RGSCH_PCELL_INDEX;
6093                            }
6094                            else
6095                            {
6096                               idx = RG_SCH_GET_SCELL_INDEX((hqP->hqE->ue), (hqP->hqE->cell));
6097                            }
6098                            hqP->hqE->ue->pfsStats.lcStats[lcId-1].ueSchdOcc[idx]++;
6099                            hqP->hqE->ue->pfsStats.lcStats[lcId-1].perRefresh[ue->pfsStats.lcStats[lcId-1].lastIdx].lcSchdOcc++;
6100                         }   
6101 #endif
6102                      }
6103                   }
6104                }
6105             }
6106             /* Added Dl TB count for SRB/DRB data transmission*/
6107 #ifdef LTE_L2_MEAS 
6108             cell->dlUlTbCnt.tbTransDlTotalCnt++;  
6109 #endif            
6110             tbInfo->ta.pres = hqP->tbInfo[tbCnt].schdTa.pres;
6111             tbInfo->ta.val =  hqP->tbInfo[tbCnt].schdTa.val;
6112 #ifdef LTE_ADV
6113             tbInfo->sCellActCe = hqP->tbInfo[tbCnt].schdSCellActCe;
6114 #endif
6115             tbInfo->numSchLch = hqP->tbInfo[tbCnt].numLch;
6116             if(!(hqP->tbInfo[tbCnt].numLch))
6117             {
6118                tbInfo->schdDat[tbInfo->numSchLch].numBytes= hqP->tbInfo[tbCnt].tbSz;
6119                /* Fix: If only TA is scheduled, use some dummy LCID */
6120                if (tbInfo->ta.pres)
6121                   tbInfo->schdDat[tbInfo->numSchLch].lcId = RG_TA_LCID;
6122             }
6123
6124             tbInfo->contResCe = hqP->tbInfo[tbCnt].contResCe;
6125             tbInfo->isReTx = FALSE;
6126          }
6127          else
6128          {
6129 #ifdef LTE_ADV
6130             if(!((rgSCHLaaCheckIfLAAProc(hqP)) && (TRUE ==
6131                         rgSCHLaaSCellEnabled(cell))))
6132 #endif
6133             {
6134                hqP->tbInfo[tbCnt].txCntr++;
6135             }
6136             tbInfo->isReTx = TRUE;
6137             /* RRM_RBC_X */
6138             /* As per 36.314, harq retransmission also considered for 
6139              * prb utilization calculation*/
6140             for(idx = 0; idx < hqP->tbInfo[tbCnt].numLch; idx++)
6141             {
6142 #ifdef LTE_L2_MEAS
6143                if(hqP->hqE->ue)
6144                {
6145                   lcId = hqP->tbInfo[tbCnt].lchSchdData[idx].lcId; 
6146                   if(lcId != 0)
6147                   {
6148                      dlLcCb = hqP->hqE->ue->dl.lcCb[lcId-1];
6149                      if(dlLcCb != NULLP)
6150                      {
6151                         prbUsed = ((hqP->tbInfo[tbCnt].\
6152                                lchSchdData[idx].schdData  *
6153                                hqP->tbInfo[tbCnt].dlGrnt.numRb) /
6154                                   (hqP->tbInfo[0].tbSz + hqP->tbInfo[1].tbSz));
6155                         if(dlLcCb->qciCb->qci > 0)
6156                         {
6157                            RG_SCH_CALC_GBR_UTILIZATION(cell, dlLcCb, prbUsed);
6158                         }
6159                      }
6160                   }
6161                }
6162 #endif
6163             }
6164             /* RRM_RBC_Y */
6165          }
6166       }
6167     }
6168 #ifdef LTE_ADV 
6169    rgSCHLaaResetDlHqProcCb(hqP);
6170 #endif
6171
6172    return;
6173 }
6174 /***********************************************************
6175  *
6176  *     Func : rgSCHUtlFillRgInfUeInfo
6177  *
6178  *     Desc : Utility Function to fill the allocation info of Ue
6179  *             : MIMO : Filling 2TB's of each UE
6180  *
6181  *     Ret  : ROK
6182  *            RFAILED
6183  *
6184  *     Notes: This function should be called while sending a msg from
6185  *     scheduler instance to MAC
6186  *
6187  *     File : rg_utl.c
6188  *
6189  **********************************************************/
6190   /* CA dev Start */
6191 #ifdef ANSI
6192 Void rgSCHUtlFillRgInfUeInfo
6193 (
6194 RgSchDlSf       *sf,
6195 RgSchCellCb     *cell,
6196 CmLListCp       *dlDrxInactvTmrLst,
6197 CmLListCp       *dlInActvLst,
6198 CmLListCp       *ulInActvLst
6199 )
6200 #else
6201 Void rgSCHUtlFillRgInfUeInfo (sf,cell, dlDrxInactvTmrLst, dlInActvLst, ulInActvLst)
6202 {
6203 RgSchDlSf       *sf;
6204 RgSchCellCb     *cell;
6205 CmLListCp       *dlDrxInactvTmrLst;
6206 CmLListCp       *dlInActvLst;
6207 CmLListCp       *ulInActvLst;
6208 #endif
6209 {
6210    RgInfSfAlloc    *sfAlloc;
6211    CmLListCp       *lnkLst;   /* lnkLst assignment */
6212    CmLList         *tmp;
6213    CmLList         *hqPNode;
6214    RgSchUeCb       *ue = NULLP;
6215    RgInfUeInfo     *ueInfo = NULLP;
6216    RgInfUeAlloc    *ueAlloc = NULLP;
6217    RgSchDlHqProcCb *hqCb = NULLP;
6218
6219    /* Since Msg4 is sched only on PCELL, use cell arg's sfAllocArr */
6220    sfAlloc = &(cell->sfAllocArr[cell->crntSfIdx]);
6221    ueInfo = &(sfAlloc->ueInfo);
6222    ueAlloc = sfAlloc->ueInfo.allocInfo;
6223
6224    lnkLst = &(sf->msg4HqPLst);
6225    CM_LLIST_FIRST_NODE(lnkLst, tmp);
6226    while(NULLP != tmp)
6227    {
6228       printf("5GTF_ERROR MSG4 Consolidation\n");
6229       hqCb = (RgSchDlHqProcCb *)(tmp->node);
6230       CM_LLIST_NEXT_NODE(lnkLst, tmp);
6231
6232       rgSCHUtlFillRgInfTbInfo(hqCb, &ueAlloc[ueInfo->numUes], cell);
6233
6234       ue = hqCb->hqE->ue;
6235
6236       if(ue != NULLP)
6237       {   
6238          if((!(ue->dl.dlInactvMask & RG_HQENT_INACTIVE)) && (ue->isDrxEnabled))
6239          {   
6240             rgSCHUtlGetDrxSchdUesInDl(cell, ue, hqCb, &ueAlloc[ueInfo->numUes], 
6241                   dlDrxInactvTmrLst, dlInActvLst, ulInActvLst);
6242          }
6243       }
6244       ueInfo->numUes++;
6245    }
6246  
6247    lnkLst = &(sf->ueLst);
6248    CM_LLIST_FIRST_NODE(lnkLst, tmp);
6249    while(NULLP != tmp)
6250    {
6251 #if defined (TENB_STATS) && defined (RG_5GTF)
6252       cell->tenbStats->sch.dl5gtfPdschCons++;
6253 #endif
6254       ue = (RgSchUeCb *)(tmp->node);
6255       CM_LLIST_NEXT_NODE(lnkLst, tmp);
6256
6257       hqPNode = ue->dl.dlSfHqInfo[cell->cellId][sf->dlIdx].hqPLst.first;
6258       while (hqPNode)
6259       {
6260          hqCb = (RgSchDlHqProcCb *)hqPNode->node;
6261          hqPNode = hqPNode->next;
6262
6263          sfAlloc = &(hqCb->hqE->cell->sfAllocArr[hqCb->hqE->cell->crntSfIdx]);
6264          ueInfo = &(sfAlloc->ueInfo);
6265          ueAlloc = sfAlloc->ueInfo.allocInfo;
6266
6267          rgSCHUtlFillRgInfTbInfo(hqCb, &ueAlloc[ueInfo->numUes], 
6268                hqCb->hqE->cell);
6269
6270          if(ue->isDrxEnabled)
6271          {   
6272             rgSCHUtlGetDrxSchdUesInDl(cell, ue, hqCb, &ueAlloc[ueInfo->numUes], 
6273                   dlDrxInactvTmrLst, dlInActvLst, ulInActvLst);
6274          }
6275          ueInfo->numUes++;
6276       }
6277 #ifdef LTE_ADV
6278       if (rgSchCb[cell->instIdx].genCfg.isSCellActDeactAlgoEnable == TRUE)
6279       {
6280          /*If remaining BO is left then increment the count*/
6281          if(ue->totalBo > 0)
6282          {
6283             ue->remBoCnt++;
6284             /* Check if trigger for Activation is met or not */
6285             if(rgSCHIsActvReqd(cell, ue))
6286             {
6287                ue->remBoCnt = 0;
6288                /*Passing primary cell*/
6289                rgSCHSCellSelectAndActDeAct(ue->cell, ue, RGR_SCELL_ACT);
6290             }
6291          }
6292          else
6293          {
6294             /*If remaining BO is 0 then reset the count*/
6295             ue->remBoCnt = 0;
6296          }
6297       }
6298 #endif
6299    }
6300   
6301    return;
6302 } /* end of rgSCHUtlFillRgInfUeInfo */
6303   /* CA dev End */
6304
6305
6306 /** @brief This function  shall update the scheduler with the CEs and data rcvd
6307  *
6308  * @details
6309  *
6310  *     Function: rgSCHUtlUpdSch
6311  *
6312  *         Processing steps:
6313  *         - Collate the information of all the SDUs received and inform the
6314  *         scheduler rgSCHDataRcvd
6315  *         - Send Data indication to the higher layer with the dedicated data
6316  *         (rgUIMSndDedDatInd)
6317  *         - Inform scheduler with any MAC CEs if present.
6318  *
6319  * @param  [in] RgCellCb   *cellCb
6320  * @param  [in] RgUeCb     *ueCb
6321  * @param  [in] RgMacPdu   *pdu
6322  * @param  [in] RgSchErrInfo  *err
6323  *  @return  S16
6324  *      -# ROK
6325  *      -# RFAILED
6326  */
6327 #ifdef ANSI
6328 S16 rgSCHUtlUpdSch
6329 (
6330 RgInfSfDatInd    *subfrmInfo,
6331 RgSchCellCb      *cellCb,
6332 RgSchUeCb        *ueCb,
6333 RgInfUeDatInd    *pdu,
6334 RgSchErrInfo     *err
6335 )
6336 #else
6337 S16 rgSCHUtlUpdSch (subfrmInfo, cellCb, ueCb, pdu, err)
6338 RgInfSfDatInd    *subfrmInfo;
6339 RgSchCellCb      *cellCb;
6340 RgSchUeCb        *ueCb;
6341 RgInfUeDatInd    *pdu;
6342 RgSchErrInfo     *err;
6343 #endif
6344 {
6345
6346    S16               ret;
6347
6348 #ifdef LTEMAC_SPS
6349    if (RGSCH_UL_SPS_ACT_PRSENT & pdu->ceInfo.bitMask)
6350    {
6351       /* SPS to be activated due to data on SPS LCG ID*/
6352       rgSCHUtlSpsActInd(cellCb, ueCb, pdu->ceInfo.spsSduSize);
6353    }
6354 #endif
6355    /* TODO : Temp Fix for crash due to UL SDU corruption*/
6356    if (RGSCH_PHR_CE_PRSNT & pdu->ceInfo.bitMask)
6357    {
6358       /* PHR present */
6359       RGSCHCPYTIMEINFO(subfrmInfo->timingInfo, ueCb->macCeRptTime);
6360       if ((ret = rgSCHUtlUpdPhr(cellCb, ueCb, pdu->ceInfo.ces.phr, err)) != ROK)
6361          return (ret);
6362    }
6363    /* Note: Order of indication to Sch now is
6364     *       1st Indicate the DataInd info for each LCG's
6365     *       2nd Update the BSR reports received along with data
6366     *       this is to make sure the effBsr is updated to the latest BSR 
6367     *       received.
6368     */
6369    cellCb->sc.apis->rgSCHUpdUeDataIndLcg(cellCb, ueCb, pdu);
6370
6371 #ifndef MAC_5GTF_UPDATE
6372    if (RGSCH_TRUNC_BSR_CE_PRSNT & pdu->ceInfo.bitMask)
6373    {
6374       RGSCHCPYTIMEINFO(subfrmInfo->timingInfo, ueCb->macCeRptTime);
6375       /*ccpu00129922 - MOD - Deleted return value
6376        * checking since it returns void*/
6377       rgSCHUtlUpdBsrTrunc (cellCb, ueCb,
6378                   (uint8_t)(pdu->ceInfo.ces.bsr.truncBsr >> 6),
6379                   (uint8_t)(pdu->ceInfo.ces.bsr.truncBsr & 0x3F), err); 
6380    }
6381    else
6382    {
6383       if (RGSCH_SHORT_BSR_CE_PRSNT & pdu->ceInfo.bitMask)
6384       {
6385          RGSCHCPYTIMEINFO(subfrmInfo->timingInfo, ueCb->macCeRptTime);
6386          /*ccpu00129922 - MOD - Deleted return value
6387           checking since it returns void*/
6388          rgSCHUtlUpdBsrShort (cellCb, ueCb,
6389                      (uint8_t)(pdu->ceInfo.ces.bsr.shortBsr >> 6),
6390                      (uint8_t)(pdu->ceInfo.ces.bsr.shortBsr & 0x3F), err);
6391       }
6392       else
6393       {
6394          if (RGSCH_LONG_BSR_CE_PRSNT & pdu->ceInfo.bitMask)
6395 #else
6396          if (RGSCH_BSR_CE_PRSNT & pdu->ceInfo.bitMask)
6397 #endif
6398          {
6399             RGSCHCPYTIMEINFO(subfrmInfo->timingInfo, ueCb->macCeRptTime);
6400             /*ccpu00129922 - MOD - Deleted return value
6401               checking since it returns void*/
6402             rgSCHUtlUpdBsrLong (cellCb, ueCb,
6403                         pdu->ceInfo.ces.bsr.longBsr.bs1,
6404                         pdu->ceInfo.ces.bsr.longBsr.bs2,
6405                         pdu->ceInfo.ces.bsr.longBsr.bs3,
6406                         pdu->ceInfo.ces.bsr.longBsr.bs4,
6407                         err);
6408          }
6409 #ifndef MAC_5GTF_UPDATE
6410       }
6411  
6412    }
6413 #endif
6414             
6415    return ROK;
6416 } /* end of rgSCHUtlUpdSch */
6417 #ifdef RGR_V1
6418 /**
6419  * @brief Handler for Updating Bo received in StaRsp
6420  *
6421  * @details
6422  *
6423  *     Function : rgSCHUtlAddUeToCcchSduLst
6424  *
6425  *     This function shall be invoked once it receives staRsp on CCCH
6426  *
6427  *  @param[in]     RgSchCellCb       *cell
6428  *  @param[in]     RgSchUeCb       *ueCb
6429  *  @return  S16
6430  *      -# ROK
6431  **/
6432 #ifdef ANSI
6433 S16 rgSCHUtlAddUeToCcchSduLst
6434 (
6435 RgSchCellCb       *cell,
6436 RgSchUeCb         *ueCb
6437 )
6438 #else
6439 S16 rgSCHUtlAddUeToCcchSduLst(cell, ueCb)
6440 RgSchCellCb       *cell;
6441 RgSchUeCb         *ueCb;
6442 #endif
6443 {
6444    RgSchCmnDlUe  *ueDl = RG_SCH_CMN_GET_DL_UE(ueCb, cell);
6445    RgSchDlHqProcCb *hqP  = (RgSchDlHqProcCb *)ueDl->proc;
6446
6447    /* Temp Guard: For back to back CCCH SDU BO 
6448     * twice. Hence an extra guard. If already added to scheduling
6449     * queue or if scheduled and waiting for HQ FDBK, ignore */
6450    if ((ueCb->ccchSduLnk.node) ||
6451        ((!(ueCb->dl.dlInactvMask & RG_HQENT_INACTIVE)) &&
6452        ((hqP != NULLP) && (hqP->hqE->ccchSduProc))))
6453    {
6454       RLOG_ARG1(L_ERROR,DBG_CELLID,cell->cellId,"RNTI:%d Unexpected CCCH SDU BO",
6455          ueCb->ueId);
6456       return ROK;
6457    }
6458
6459    ueCb->ccchSduLnk.node = (PTR)(ueCb);
6460    cmLListAdd2Tail(&(cell->ccchSduUeLst), &(ueCb->ccchSduLnk));
6461
6462    return ROK;
6463 }
6464 /**
6465  *
6466  * @details
6467  *
6468  *     Function : rgSCHUtlUpdtBo
6469  *
6470  *     This function shall be invoked once it receives staRsp on CCCH
6471  *
6472  *  @param[in]     RgSchCellCb       *cell
6473  *  @param[in]     RgRguCmnStaRsp *staRsp
6474  *  @return  S16
6475  *      -# ROK
6476  **/
6477 #ifdef ANSI
6478 S16 rgSCHUtlUpdtBo
6479 (
6480 RgSchCellCb       *cell,
6481 RgInfCmnBoRpt     *staRsp
6482 )
6483 #else
6484 S16 rgSCHUtlUpdtBo(cell, staRsp)
6485 RgSchCellCb       *cell;
6486 RgInfCmnBoRpt     *staRsp;
6487 #endif
6488 {
6489    RgSchUeCb *ueCb;
6490
6491    if ((ueCb = rgSCHDbmGetUeCb(cell, staRsp->u.rnti)) == NULLP)
6492    {
6493       /* Handle Ue fetch failure */
6494       RLOG_ARG1(L_ERROR,DBG_CELLID,cell->cellId,"Invalid UEID:%d",staRsp->u.rnti);
6495       return RFAILED;
6496    }
6497    /* Update Bo in ueCb */
6498    ueCb->dlCcchInfo.bo = (uint32_t)(staRsp->bo);
6499 #ifdef EMTC_ENABLE
6500      if(ueCb->isEmtcUe)
6501      {
6502         rgSCHUtlAddUeToEmtcCcchSduLst(cell,ueCb);
6503      }
6504      else
6505 #endif
6506     {
6507       rgSCHUtlAddUeToCcchSduLst(cell, ueCb);
6508     }
6509
6510    return ROK;
6511 } /* rgSCHUtlUpdtBo */
6512
6513 #endif
6514 /**
6515  *
6516  * @details
6517  *     Function : rgSCHUtlHndlCcchBoUpdt
6518  *
6519  *     This function shall fetch the raCb with the given rnti and ask RAM to
6520  *     update BO
6521  *
6522  *
6523  *  @param[in]  RgSchCellCb    *cell
6524  *  @param[in]  RgInfCmnBoRpt *boRpt
6525  *  @return  S16
6526  *      -# ROK
6527  *      -# RFAILED
6528  **/
6529 #ifdef ANSI
6530 S16 rgSCHUtlHndlCcchBoUpdt
6531 (
6532 RgSchCellCb    *cell,
6533 RgInfCmnBoRpt  *boRpt
6534 )
6535 #else
6536 S16 rgSCHUtlHndlCcchBoUpdt(cell, boRpt)
6537 RgSchCellCb    *cell;
6538 RgInfCmnBoRpt  *boRpt;
6539 #endif
6540 {
6541    RgSchRaCb       *raCb;
6542    RgSchUeCb *ueCb;
6543
6544    if ((raCb = rgSCHDbmGetRaCb(cell, boRpt->u.rnti)) == NULLP)
6545    {
6546 #ifdef RGR_V1
6547    /* CR timer implementation changes*/
6548       /*If no raCb, schedule ueCb, ueCb is extracted in rgSCHUtlUpdtBo*/
6549       return (rgSCHUtlUpdtBo(cell, boRpt));
6550 #else
6551       /* Handle RaCb fetch failure */
6552       RLOG_ARG1(L_ERROR,DBG_CELLID,cell->cellId,
6553                       "Invalid RNTI:%d to fetch raCb",boRpt->u.rnti);
6554       return RFAILED;
6555 #endif
6556    }
6557
6558 #ifdef RGR_V1
6559
6560       /*Fix: If RaCb exists, then MSG4 is not completed yet*/
6561       /*Check if guard timer has expired, if not CR CE + CCCH SDU will be scheduled*/
6562       if((raCb->contResTmrLnk.node != NULLP) && \
6563             (raCb->schdLnk.node == NULLP) && (raCb->dlHqE->msg4Proc == NULLP))
6564       {
6565 #ifdef EMTC_ENABLE
6566          /*if contention resolution timer left ,Stop the Contention Resolution Guard Timer ,
6567          add in toBeSchduled list and update the Bo */
6568          if(TRUE == raCb->isEmtcRaCb)
6569          {
6570             rgSCHRamEmtcUpdtBo(cell, raCb, boRpt);
6571          }
6572          else
6573 #endif
6574          {
6575             cmLListDelFrm(&cell->contResGrdTmrLst, &(raCb->contResTmrLnk));
6576             raCb->contResTmrLnk.node=NULLP;               
6577             rgSCHRamUpdtBo(cell, raCb, boRpt);
6578          }
6579        }
6580       else
6581       {
6582          /*Fix:Guard timer has expired */
6583          /*Update the BO in UE CB but dont add it to the scheduling list. 
6584           *Should be added to the list after MSG4 completion*/
6585          if ((ueCb = rgSCHDbmGetUeCb(cell, boRpt->u.rnti)) == NULLP)
6586          {
6587             /* Handle Ue fetch failure */
6588             RLOG_ARG1(L_ERROR,DBG_CELLID,cell->cellId,"Invalid RNTI:%d",boRpt->u.rnti);
6589             return RFAILED;
6590          }
6591          /* Update Bo in ueCb */
6592          ueCb->dlCcchInfo.bo = (uint32_t)(boRpt->bo);     
6593       }
6594
6595 #else
6596       rgSCHRamUpdtBo(cell, raCb, boRpt);
6597 #endif
6598
6599    return ROK;
6600 } /* rgSCHUtlHndlCcchBoUpdt */
6601
6602 /**
6603  * @brief Validates BO received for BCCH or PCCH.
6604  *
6605  * @details
6606  *
6607  *     Function : rgSCHUtlGetAllwdCchTbSz
6608  *
6609  *     This function shall return the tbSz equal to or
6610  *     the nearest greater value for a given bo.
6611  *     If no such value found return -1. The nPrb value is
6612  *     accordingly set.
6613  *
6614  *
6615  *  @param[in]  uint32_t            bo
6616  *  @param[out] uint8_t             *nPrb
6617  *  @return  S32
6618  *      -# ROK
6619  *      -# RFAILED
6620  **/
6621 #ifdef ANSI
6622 S32 rgSCHUtlGetAllwdCchTbSz
6623 (
6624 uint32_t bo,
6625 uint8_t  *nPrb,
6626 uint8_t  *mcs
6627 )
6628 #else
6629 S32 rgSCHUtlGetAllwdCchTbSz(bo, nPrb, mcs)
6630 uint32_t bo;
6631 uint8_t  *nPrb;
6632 uint8_t  *mcs;
6633 #endif
6634 {
6635    S32 lt;
6636    S32 cn;
6637    S32 rt;
6638
6639    for (lt = 0, rt = 43; lt <= rt;)
6640    {
6641       cn = (lt + rt)/2;
6642       if (rgSchUtlBcchPcchTbSzTbl[cn].tbSz == bo)
6643       {
6644          *nPrb = rgSchUtlBcchPcchTbSzTbl[cn].rbIndex;
6645          *mcs  = rgSchUtlBcchPcchTbSzTbl[cn].mcs;
6646          return (rgSchUtlBcchPcchTbSzTbl[cn].tbSz);
6647       }
6648       else if (rgSchUtlBcchPcchTbSzTbl[cn].tbSz < bo)
6649          lt = cn + 1;
6650       else
6651          rt = cn - 1;
6652    }
6653    if (lt == 44)
6654    {
6655       return RFAILED;
6656    }
6657    *nPrb = rgSchUtlBcchPcchTbSzTbl[lt].rbIndex;
6658    *mcs  = rgSchUtlBcchPcchTbSzTbl[lt].mcs;
6659    return (rgSchUtlBcchPcchTbSzTbl[lt].tbSz);
6660 }
6661
6662 /**
6663  * @brief Handler for BO Updt received for BCCH or PCCH.
6664  *
6665  * @details
6666  *
6667  *     Function : rgSCHUtlHndlBcchPcchBoUpdt
6668  *
6669  *     This function shall store the buffer and time to transmit in lcCb
6670  *
6671  *
6672  *  @param[in]  RgSchCellCb    *cell
6673  *  @param[in]  RgInfCmnBoRpt  *boRpt
6674  *  @return  S16
6675  *      -# ROK
6676  *      -# RFAILED
6677  **/
6678 #ifdef ANSI
6679 S16 rgSCHUtlHndlBcchPcchBoUpdt
6680 (
6681 RgSchCellCb    *cell,
6682 RgInfCmnBoRpt  *boUpdt
6683 )
6684 #else
6685 S16 rgSCHUtlHndlBcchPcchBoUpdt(cell, boUpdt)
6686 RgSchCellCb    *cell;
6687 RgInfCmnBoRpt  *boUpdt;
6688 #endif
6689 {
6690    RgSchClcDlLcCb *dlLc;
6691    RgSchClcBoRpt  *boRpt;
6692    Inst           inst = cell->instIdx;
6693    uint8_t             nPrb=0;
6694    uint8_t             mcs=0;
6695
6696    dlLc = rgSCHDbmGetBcchOnBch(cell);
6697    if (dlLc == NULLP)
6698    {
6699       RLOG_ARG2(L_ERROR,DBG_CELLID,cell->cellId,
6700       "No Logical Channel dlLc is NULLP for RNTI:%d LCID:%d",boUpdt->u.rnti,boUpdt->lcId);
6701       return RFAILED;
6702    }
6703    if (boUpdt->lcId != dlLc->lcId)
6704    {
6705       /* Added for dropping paging Message*/      
6706           /*suman*/
6707       if ((rgSCHChkBoUpdate(cell,boUpdt))== ROK)  /* Checking if received BO falls within the window of 5120 slots*/
6708       {
6709          if (rgSCHUtlGetAllwdCchTbSz(boUpdt->bo*8, &nPrb, &mcs) 
6710                != (boUpdt->bo*8))
6711          {
6712             RLOG_ARG3(L_ERROR,DBG_CELLID,cell->cellId,"[%ld]BO: does not match any "
6713                   "valid TB Size RNTI:%d LCID:%d", boUpdt->bo,boUpdt->u.rnti,boUpdt->lcId);
6714             return RFAILED;
6715          }
6716       }/*end of rgSCHChkBoUpdate*/
6717       else
6718       {
6719           return ROK;
6720       } 
6721    }
6722    if ((dlLc = rgSCHDbmGetCmnLcCb(cell, boUpdt->lcId)) == NULLP)
6723    {
6724       /* Handle lcCb fetch failure */
6725       RLOG_ARG2(L_ERROR,DBG_CELLID,cell->cellId,
6726                       "LCID:%d Invalid for RNTI:%d",boUpdt->lcId,boUpdt->u.rnti);
6727    }
6728
6729    if (((rgSCHUtlAllocSBuf(inst, (Data **)(&boRpt), sizeof(RgSchClcBoRpt))) ==RFAILED) ||
6730        (!boRpt))
6731    {
6732       RLOG_ARG3(L_ERROR,DBG_CELLID,cell->cellId, "Allocation of common bo %dreport "
6733          "failed  RNTI:%d LCID:%d", boUpdt->bo,boUpdt->u.rnti,boUpdt->lcId);
6734       return RFAILED;
6735    }
6736
6737    boRpt->bo = boUpdt->bo;
6738    boRpt->mcs = mcs;
6739    boRpt->timeToTx = boUpdt->u.timeToTx;
6740    boRpt->nPrb = nPrb;
6741 #ifdef EMTC_ENABLE
6742    if(cell->emtcEnable)
6743    {
6744       boRpt->emtcDIReason = boUpdt->emtcDIReason;
6745       boRpt->pnb = boUpdt->pnb;
6746    }
6747 #endif
6748    RG_SCH_ADD_TO_CRNT_TIME(boRpt->timeToTx, 
6749          boRpt->maxTimeToTx, cell->siCfg.siWinSize)
6750    if((NULLP != dlLc) && (dlLc->si))
6751    {
6752       boRpt->retxCnt = cell->siCfg.retxCnt;
6753    }
6754    else
6755    {
6756       boRpt->retxCnt = 0;
6757    }
6758    rgSCHDbmInsCmnLcBoRpt(dlLc, boRpt);
6759
6760    return ROK;
6761 } /* rgSCHUtlHndlBcchPcchBoUpdt */
6762
6763 /**
6764  * @brief API for sending bind confirm from Scheduler instance to RRM
6765  *
6766  * @details
6767  *
6768  *     Function: rgSCHUtlRgrBndCfm
6769  *
6770  *     This API is invoked to send bind confirm from Scheduler instance to RRM.
6771  *     This API fills in Pst structure and SAP Ids and invokes
6772  *     bind confirm API towards RRM.
6773  *
6774  *  @param[in]  SuId          suId
6775  *  @param[in]  uint8_t            status
6776  *  @return  S16
6777  *      -# ROK
6778  *      -# RFAILED
6779  **/
6780 #ifdef ANSI
6781 S16 rgSCHUtlRgrBndCfm
6782 (
6783 Inst          instId,
6784 SuId          suId,
6785 uint8_t            status
6786 )
6787 #else
6788 S16 rgSCHUtlRgrBndCfm(instId, suId, status)
6789 Inst          instId;
6790 SuId          suId;
6791 uint8_t            status;
6792 #endif
6793 {
6794    S16  ret = ROK;
6795
6796    ret = RgUiRgrBndCfm(&rgSchCb[instId].rgrSap[suId].sapCfg.sapPst, rgSchCb[instId].rgrSap[suId].sapCfg.suId, status);
6797    if (ret != ROK)
6798    {
6799       RLOG_ARG0(L_ERROR,DBG_INSTID,instId,"rgSCHUtlRgrBndCfm: RgUiRgrBndCfm Failed ");
6800       return (ret);
6801    }
6802    return (ret);
6803 }  /* rgSCHUtlRgrBndCfm*/
6804
6805 /**
6806  * @brief API for sending bind confirm from Scheduler instance to RRM via RGM
6807  *        interface
6808  *
6809  * @details
6810  *
6811  *     Function: rgSCHUtlRgmBndCfm
6812  *
6813  *     This API is invoked to send bind confirm from Scheduler instance to RRM.
6814  *     This API fills in Pst structure and SAP Ids and invokes
6815  *
6816  *  @param[in]  SuId          suId
6817  *  @param[in]  uint8_t            status
6818  *  @return  S16
6819  *      -# ROK
6820  *      -# RFAILED
6821  **/
6822 #ifdef ANSI
6823 S16 rgSCHUtlRgmBndCfm
6824 (
6825 Inst          instId,
6826 SuId          suId,
6827 uint8_t            status
6828 )
6829 #else
6830 S16 rgSCHUtlRgmBndCfm(instId, suId, status)
6831 Inst          instId;
6832 SuId          suId;
6833 uint8_t            status;
6834 #endif
6835 {
6836    S16  ret = ROK;
6837
6838    ret = RgUiRgmBndCfm(&rgSchCb[instId].rgmSap[suId].sapCfg.sapPst, rgSchCb[instId].rgmSap[suId].sapCfg.suId, status);
6839    if (ret != ROK)
6840    {
6841       RLOG_ARG0(L_ERROR,DBG_INSTID,instId,"rgSCHUtlRgmBndCfm: RgUiRgrBndCfm Failed ");
6842       return (ret);
6843    }
6844    return (ret);
6845 }  /* rgSCHUtlRgmBndCfm*/
6846
6847
6848
6849 /**
6850  * @brief API for sending configuration confirm from Scheduler to DU APP
6851  *
6852  * @details
6853  *
6854  *     Function: schSendCfgCfm 
6855  *
6856  *     This API is invoked to send configuration confirm from Scheduler to DU
6857  *     APP.
6858  *
6859  *  @param[in]  Pst           pst 
6860  *  @param[in]  RgrCfgTransId transId
6861  *  @param[in]  uint8_t            status
6862  *  @return  S16
6863  *      -# ROK
6864  *      -# RFAILED
6865  **/
6866 #ifdef ANSI
6867 S16 schSendCfgCfm
6868 (
6869 Region        reg,
6870 Pool          pool,
6871 RgrCfgTransId transId,
6872 uint8_t            status
6873 )
6874 #else
6875 S16 schSendCfgCfm(reg, pool, transId, status)
6876 Region        reg;
6877 Pool          pool;
6878 RgrCfgTransId transId;
6879 uint8_t            status;
6880 #endif
6881 {
6882    Pst cfmPst;
6883    Inst inst = 0;
6884
6885    memset((&cfmPst), 0, sizeof(Pst));
6886
6887    cfmPst.srcEnt    = (Ent)ENTDUAPP;
6888    cfmPst.srcInst   = (Inst) 0;
6889    cfmPst.srcProcId = SFndProcId();
6890    cfmPst.dstEnt    = (Ent)ENTMAC;
6891    cfmPst.dstInst   = (Inst) 0;
6892    cfmPst.dstProcId = SFndProcId();
6893    cfmPst.selector  = ODU_SELECTOR_LC;
6894    cfmPst.region    = reg;
6895    cfmPst.pool      = pool;
6896
6897    if(RgUiRgrCfgCfm(&cfmPst,transId, status) != ROK)
6898    {
6899       RLOG_ARG0(L_ERROR,DBG_INSTID,inst,"schSendCfgCfm: RgUiRgrCfgCfm Failed");
6900       printf("\nschSendCfgCfm: RgUiRgrCfgCfm Failed ");
6901       return RFAILED;
6902    }
6903    return ROK;
6904 }  /* schSendCfgCfm*/
6905 #ifdef RGR_RRM_TICK
6906 /**
6907  * @brief API for sending TTI indication from Scheduler to RRM.
6908  *
6909  * @details
6910  *
6911  *     Function: rgSCHUtlRgrTtiInd
6912  *
6913  *     This API is invoked to send TTI indication from Scheduler instance to RRM.
6914  *     This API fills in Pst structure and RgrTtiIndInfo
6915  *
6916  *  @param[in]  cell                   RgSchCellCb
6917  *  @param[in]  CmLteTimingInfo        status
6918  *  @return  S16
6919  *      -# ROK
6920  *      -# RFAILED
6921  **/
6922 #ifdef ANSI
6923 S16 rgSCHUtlRgrTtiInd
6924 (
6925 RgSchCellCb          *cell,
6926 RgrTtiIndInfo        *rgrTti
6927 )
6928 #else
6929 S16 rgSCHUtlRgrTtiInd(cell, rgrTti)
6930 RgSchCellCb          *cell;
6931 RgrTtiIndInfo        *rgrTti;
6932 #endif
6933 {
6934    S16           ret = ROK;
6935    RgSchUpSapCb  *rgrSap;                    /*!< RGR SAP Control Block */
6936 #ifdef L2_L3_SPLIT
6937    Bool g_usettitmr;
6938    Void mtTmrHdlrPublic(void);
6939 #endif
6940
6941    rgrSap = cell->rgrSap;
6942    if (rgrSap->sapSta.sapState != LRG_BND)
6943    {
6944       RLOG_ARG1(L_ERROR,DBG_CELLID,cell->cellId,
6945                "rgSCHUtlRgrTtiInd() Upper SAP not bound (%d) ",
6946                rgrSap->sapSta.sapState);
6947       return RFAILED;
6948    }
6949    RgUiRgrTtiInd(&(cell->rgrSap->sapCfg.sapPst),
6950          cell->rgrSap->sapCfg.suId, rgrTti);
6951 #ifdef L2_L3_SPLIT
6952    {
6953       g_usettitmr = TRUE;
6954       mtTmrHdlrPublic();
6955    }
6956 #endif
6957    return (ret);
6958 }  /* rgSCHUtlRgrTtiInd*/
6959 #endif
6960 /** @brief This function is called by rgMacSchSfRecpInd. This function invokes the
6961  * scheduler with the information of the received Data and any Control Elements
6962  * if present.
6963  *
6964  * @details
6965  *
6966  *     Function:
6967  *
6968  *         Processing steps:
6969  *         - Retrieves the RaCb with the rnti provided, if it doesnt exist
6970  *         return failure.
6971  *         - If UE exists then update the Schduler with any MAC CEs if present.
6972  *         - Invoke RAM module to do Msg3 related processing rgSCHRamProcMsg3
6973  *
6974  * @param  [in] RgSchCellCb   *cellCb
6975  * @param  [in] RgSchUeCb     *ueCb
6976  * @param  [in] CmLteRnti     rnti
6977  * @param  [in] RgMacPdu   *pdu
6978  * @param  [in] RgSchErrInfo  *err
6979  * @param
6980  *  @return  S16
6981  *      -# ROK
6982  *      -# RFAILED
6983  */
6984 #ifdef ANSI
6985 S16 rgSCHUtlProcMsg3
6986 (
6987 RgInfSfDatInd    *subfrmInfo,
6988 RgSchCellCb      *cellCb,
6989 RgSchUeCb        *ueCb,
6990 CmLteRnti        rnti,
6991 RgInfUeDatInd    *pdu,
6992 RgSchErrInfo     *err
6993  )
6994 #else
6995 S16 rgSCHUtlProcMsg3 (subfrmInfo, cellCb, ueCb, rnti, pdu, err)
6996 RgInfSfDatInd    *subfrmInfo;
6997 RgSchCellCb      *cellCb;
6998 RgSchUeCb        *ueCb;
6999 CmLteRnti        rnti;
7000 RgInfUeDatInd    *pdu;
7001 RgSchErrInfo     *err;
7002 #endif
7003 {
7004    S16               ret;
7005    RgSchRaCb         *raCb;
7006
7007    /* must have an raCb for this case */
7008    raCb = rgSCHDbmGetRaCb (cellCb, rnti);
7009    if (raCb == NULLP)
7010    {
7011       RLOG_ARG1(L_ERROR,DBG_CELLID,cellCb->cellId, "RNTI:%d Received MSG3, unable to "
7012          "find raCb",rnti);
7013       return RFAILED;
7014    }
7015
7016    /* ccpu00130982: Processing CRNTI MAC CE before Short BSR, if any, such that 
7017     * effBsr of current case only will be considered in scheduling of ContResLst*/
7018    ret = rgSCHRamProcMsg3 (cellCb, ueCb, raCb, pdu, err);
7019    if (ret != ROK)
7020    {
7021       RLOG_ARG1(L_ERROR,DBG_CELLID,cellCb->cellId,"Processing failed in the RAM "
7022          "RNTI:%d ",rnti);
7023       return (ret);
7024    }
7025    /* if ueCb is present */
7026    if (ueCb != NULLP)
7027    {
7028       rgSCHUtlUpdSch (subfrmInfo, cellCb, ueCb, pdu, err);
7029    }
7030
7031    return ROK;
7032 }
7033 #ifdef LTEMAC_SPS
7034 /** @brief This function is called by RgMacSchSpsRelInd. This function invokes the
7035  * scheduler with the information of the received Data.
7036  *
7037  * @details
7038  *
7039  *     Function: rgSCHUtlSpsRelInd
7040  *
7041  *         Processing steps:
7042  *         TODO
7043  *
7044  * @param  [in] RgSchCellCb        *cellCb
7045  * @param  [in] RgSchUeCb          *ueCb
7046  * @param  [in] Bool               *isExplRel
7047  * @param
7048  *  @return  S16
7049  *      -# ROK
7050  *      -# RFAILED
7051  */
7052 #ifdef ANSI
7053 S16 rgSCHUtlSpsRelInd
7054 (
7055 RgSchCellCb        *cellCb,
7056 RgSchUeCb          *ueCb,
7057 Bool               isExplRel
7058 )
7059 #else
7060 S16 rgSCHUtlSpsRelInd (cellCb, ueCb, isExplRel)
7061 RgSchCellCb        *cellCb;
7062 RgSchUeCb          *ueCb;
7063 Bool               isExplRel;
7064 #endif
7065 {
7066    cellCb->sc.apis->rgSCHUlSpsRelInd(cellCb, ueCb, isExplRel);
7067    return ROK;
7068 } /* end of rgSCHUtlSpsRelInd */
7069
7070
7071 /** @brief This function is called by RgMacSchSpsRelInd. This function invokes the
7072  * scheduler with the information of the received Data.
7073  *
7074  * @details
7075  *
7076  *     Function: rgSCHUtlSpsActInd
7077  *
7078  *         Processing steps:
7079  *         TODO
7080  *
7081  * @param  [in] RgSchCellCb        *cellCb
7082  * @param  [in] RgSchUeCb          *ueCb
7083  * @param  [in] uint16_t                spsSduSize
7084  * @param
7085  *  @return  S16
7086  *      -# ROK
7087  *      -# RFAILED
7088  */
7089 #ifdef ANSI
7090 S16 rgSCHUtlSpsActInd
7091 (
7092 RgSchCellCb        *cellCb,
7093 RgSchUeCb          *ueCb,
7094 uint16_t                spsSduSize
7095 )
7096 #else
7097 S16 rgSCHUtlSpsActInd (cellCb, ueCb, spsSduSize)
7098 RgSchCellCb        *cellCb;
7099 RgSchUeCb          *ueCb;
7100 uint16_t                spsSduSize;
7101 #endif
7102 {
7103    cellCb->sc.apis->rgSCHUlSpsActInd(cellCb, ueCb, spsSduSize);
7104    return ROK;
7105 } /* end of rgSCHUtlSpsActInd */
7106
7107
7108 #endif /* LTEMAC_SPS */
7109
7110 #ifdef RG_PHASE_2
7111 /**
7112  * @brief This API is invoked to send uplink group power control request to PHY.
7113  *
7114  * @details
7115  *
7116  *     Function : rgSCHUtlTfuGrpPwrCntrlReq
7117  *
7118  *      This API is invoked to send uplink group power control request to PHY.
7119  *      It fills in the Pst structure, spId value and invokes group power
7120  *      control request primitive at TFU.
7121  *
7122  *  @param[in]  TfuGrpPwrCntrlReqInfo *grpPwrCntrlReq
7123  *  @return  S16
7124  *      -# ROK
7125  *      -# RFAILED
7126  **/
7127 #ifdef ANSI
7128 S16 rgSCHUtlTfuGrpPwrCntrlReq
7129 (
7130 Inst                  inst,
7131 S16                   sapId,
7132 TfuGrpPwrCntrlReqInfo *grpPwrCntrlReq
7133 )
7134 #else
7135 S16 rgSCHUtlTfuGrpPwrCntrlReq(inst, sapId, grpPwrCntrlReq)
7136 Inst                  inst;
7137 S16                   sapId;
7138 TfuGrpPwrCntrlReqInfo *grpPwrCntrlReq;
7139 #endif
7140 {
7141    S16             ret;
7142    RgSchLowSapCb  *tfuSap;
7143    Pst             pst;
7144
7145
7146    /* Get the lower SAP control block from the layer control block. */
7147    tfuSap = &(rgSchCb[inst].tfuSap[sapId]);
7148    if (tfuSap->sapSta.sapState != LRG_BND)
7149    {
7150       RLOG_ARG1(L_ERROR,DBG_CELLID,grpPwrCntrlReq->cellId,
7151                       "rgSCHUtlTfuGrpPwrCntrlReq() Lower SAP not bound (%d) ",tfuSap->sapSta.sapState);
7152       return RFAILED;
7153    }
7154    memcpy (&pst, &(tfuSap->sapCfg.sapPst), sizeof(Pst));
7155    if((ret = RgLiTfuGrpPwrCntrlReq (&pst, tfuSap->sapCfg.spId, grpPwrCntrlReq)) != ROK)
7156    {
7157       RLOG_ARG0(L_ERROR,DBG_CELLID,grpPwrCntrlReq->cellId,
7158                       "rgSCHUtlTfuGrpPwrCntrlReq() Call to RgLiTfuGrpPwrCntrlReq() failed");
7159    }
7160    return (ret);
7161 }  /* rgSCHUtlTfuGrpPwrCntrlReq */
7162 #endif
7163
7164 /* FOR ACK NACK REP */
7165
7166 /**
7167  * @brief This API is invoked to tell the DL Scheduler to add the UE back into
7168  * its scheduling queues.
7169  *
7170  * @details
7171  *
7172  *     Function : rgSCHUtlDlActvtUe
7173  *
7174  *      This API is invoked from Measurement gap moduled.
7175  *
7176  *  @param[in]  RgSchCellCb    *cell
7177  *  @param[in]  RgSchUeCb        *ueCb
7178  *
7179  *  @return  S16
7180  *      -# ROK
7181  *      -# RFAILED
7182  **/
7183 #ifdef ANSI
7184 S16 rgSCHUtlDlActvtUe
7185 (
7186 RgSchCellCb *cell,
7187 RgSchUeCb   *ue
7188 )
7189 #else
7190 S16 rgSCHUtlDlActvtUe(cell, ue)
7191 RgSchCellCb *cell;
7192 RgSchUeCb   *ue;
7193 #endif
7194 {
7195    cell->sc.apis->rgSCHActvtDlUe(cell, ue);
7196    return ROK;
7197 }
7198
7199 /**
7200  * @brief This API is invoked to tell the UL Scheduler to add the UE back into
7201  * its scheduling queues.
7202  *
7203  * @details
7204  *
7205  *     Function : rgSCHUtlUlActvtUe
7206  *
7207  *      This API is invoked from Measurement gap moduled.
7208  *
7209  *  @param[in]  RgSchCellCb    *cell
7210  *  @param[in]  RgSchUeCb        *ueCb
7211  *
7212  *  @return  S16
7213  *      -# ROK
7214  *      -# RFAILED
7215  **/
7216 #ifdef ANSI
7217 S16 rgSCHUtlUlActvtUe
7218 (
7219 RgSchCellCb *cell,
7220 RgSchUeCb   *ue
7221 )
7222 #else
7223 S16 rgSCHUtlUlActvtUe(cell, ue)
7224 RgSchCellCb *cell;
7225 RgSchUeCb   *ue;
7226 #endif
7227 {
7228    cell->sc.apis->rgSCHActvtUlUe(cell, ue);
7229    return ROK;
7230 }
7231
7232  /** @brief This function Validates the SAP information received along with the
7233   * primitive from the lower layer.
7234   *
7235   * Function: rgSCHUtlValidateTfuSap
7236   *
7237   *                      Validates SAP information.
7238   * @param  suId The SAP Id
7239   * @return
7240   *   -# ROK
7241   *   -# RFAILED
7242   */
7243 #ifdef ANSI
7244 S16 rgSCHUtlValidateTfuSap
7245 (
7246 Inst  inst,
7247 SuId  suId
7248 )
7249 #else
7250 S16 rgSCHUtlValidateTfuSap(inst, suId)
7251 Inst  inst;
7252 SuId  suId;
7253 #endif
7254 {
7255    RgSchLowSapCb  *tfuSap;
7256
7257    if(suId >= rgSchCb[inst].numSaps)
7258    {
7259       RLOG_ARG0(L_ERROR,DBG_INSTID,inst, "Incorrect SuId");
7260       return RFAILED;
7261    }
7262    tfuSap = &(rgSchCb[inst].tfuSap[suId]);
7263
7264    /* First lets check the suId */
7265    if( suId != tfuSap->sapCfg.suId)
7266    {
7267       RLOG_ARG2(L_ERROR,DBG_INSTID,inst,"Incorrect SuId. Configured (%d) Recieved (%d)",
7268             tfuSap->sapCfg.suId, suId);
7269       return RFAILED;
7270    }
7271    if (tfuSap->sapSta.sapState != LRG_BND)
7272    {
7273       RLOG_ARG1(L_ERROR,DBG_INSTID,inst,"Lower SAP not enabled SuId (%d)",
7274             tfuSap->sapCfg.suId);
7275       return RFAILED;
7276    }
7277    return ROK;
7278 } /* end of rgSCHUtlValidateTfuSap */
7279
7280 /*
7281 *
7282 *       Fun:   rgSCHUtlAllocEventMem
7283 *
7284 *       Desc:  This function allocates event memory
7285 *
7286 *       Ret:   ROK      - on success
7287 *              RFAILED  - on failure
7288 *
7289 *       Notes: None
7290 *
7291 *       File:  rg_utl.c
7292 *
7293 */
7294 #ifdef ANSI
7295 S16 rgSCHUtlAllocEventMem
7296 (
7297 Inst      inst,
7298 Ptr       *memPtr,
7299 Size      memSize
7300 )
7301 #else
7302 S16 rgSCHUtlAllocEventMem(inst, memPtr, memSize)
7303 Inst      inst;
7304 Ptr       *memPtr;
7305 Size      memSize;
7306 #endif
7307 {
7308    Mem              sMem;
7309    volatile uint32_t     startTime=0;
7310
7311
7312    sMem.region = rgSchCb[inst].rgSchInit.region;
7313    sMem.pool = rgSchCb[inst].rgSchInit.pool;
7314
7315 #if (ERRCLASS & ERRCLS_DEBUG)
7316    if (memSize<= 0)
7317    {
7318       RGSCHLOGERROR(inst, ERRCLS_INT_PAR, ERG022, memSize,
7319                    "rgAllocEventMem(): memSize invalid\n");
7320       return  (RFAILED);
7321    }
7322 #endif /* ERRCLASS & ERRCLS_DEBUG */
7323    /*starting Task*/
7324    SStartTask(&startTime, PID_SCHUTL_CMALLCEVT);
7325
7326 #ifdef MS_MBUF_CORRUPTION /* Should be enabled when debugging mbuf corruption */
7327    MS_BUF_ADD_ALLOC_CALLER();
7328 #endif /* */
7329 #ifdef TFU_ALLOC_EVENT_NO_INIT
7330    if(ROK != cmAllocEvntNoInit(memSize, TFU_MAX_MEMBLK_SIZE, &sMem, memPtr))
7331 #else
7332    if(ROK != cmAllocEvnt(memSize, TFU_MAX_MEMBLK_SIZE, &sMem, memPtr))
7333 #endif /* */
7334    {
7335       RLOG_ARG0(L_ERROR,DBG_INSTID,inst,"cmAllocEvnt Failed.");
7336       return RFAILED;
7337    }
7338    /*stoping Task*/
7339    SStopTask(startTime, PID_SCHUTL_CMALLCEVT);
7340    return ROK;
7341 } /* end of rgSCHUtlAllocEventMem*/
7342
7343 /*
7344 *
7345 *       Fun:   rgGetEventMem
7346 *
7347 *       Desc:  This function allocates event memory
7348 *
7349 *       Ret:   ROK      - on success
7350 *              RFAILED  - on failure
7351 *
7352 *       Notes: None
7353 *
7354 *       File:  rg_utl.c
7355 *
7356 */
7357 #ifdef ANSI
7358 S16 rgSCHUtlGetEventMem
7359 (
7360 Ptr       *ptr,
7361 Size      len,
7362 Ptr       memCp
7363 )
7364 #else
7365 S16 rgSCHUtlGetEventMem(ptr, len, memCp)
7366 Ptr       *ptr;
7367 Size      len;
7368 Ptr       memCp;
7369 #endif
7370 {
7371    S16   ret;
7372
7373 #ifdef TFU_ALLOC_EVENT_NO_INIT
7374    ret = cmGetMemNoInit(memCp, len, (Ptr *)ptr);
7375 #else
7376    ret = cmGetMem(memCp, len, (Ptr *)ptr);
7377 #endif
7378    return (ret);
7379 } /* end of rgSCHUtlGetEventMem*/
7380
7381 #ifdef LTE_TDD
7382
7383
7384 /**
7385  * @brief Handler to allocate memory for ACK/NACk feedback information
7386  *
7387  * @details
7388  *
7389  *     Function : rgSCHUtlAllocUeANFdbkInfo
7390  *
7391  *   It allocates memory for the UE related ACK NACK information.
7392  *
7393  *  @param[in]  RgSchUeCb           *ue
7394  *  @return     S16
7395  **/
7396 #ifdef ANSI
7397 S16 rgSCHUtlAllocUeANFdbkInfo
7398 (
7399 RgSchUeCb            *ue,
7400 uint8_t                   servCellIdx
7401 )
7402 #else
7403 S16 rgSCHUtlAllocUeANFdbkInfo(ue,servCellIdx)
7404 RgSchUeCb            *ue;
7405 uint8_t                   servCellIdx;
7406 #endif
7407 {
7408    uint8_t idx;
7409
7410    if (rgSCHUtlAllocSBuf(ue->cell->instIdx,
7411                (Data **) &(ue->cellInfo[servCellIdx]->anInfo), sizeof(RgSchTddANInfo) * \
7412                ue->cell->ackNackFdbkArrSize) != ROK)
7413    {
7414       return RFAILED;
7415    }
7416
7417    for(idx=0; idx < ue->cell->ackNackFdbkArrSize; idx++)
7418    {
7419       rgSCHUtlInitUeANFdbkInfo(&ue->cellInfo[servCellIdx]->anInfo[idx]);
7420    }
7421
7422    /* Set it to the first index */
7423    ue->cellInfo[servCellIdx]->nextFreeANIdx = 0;
7424    return ROK;
7425 } /* rgSCHUtlAllocUeANFdbkInfo */
7426
7427 /**
7428  * @brief Handler to release memory for ACK/NACk feedback information
7429  *
7430  * @details
7431  *
7432  *     Function : rgSCHUtlDelUeANFdbkInfo
7433  *
7434  *   It releases memory for the UE related ACK NACK information.
7435  *
7436  *  @param[in]  RgSchUeCb           *ue
7437  *  @return     Void
7438  **/
7439 #ifdef ANSI
7440 Void rgSCHUtlDelUeANFdbkInfo
7441 (
7442 RgSchUeCb            *ue,
7443 uint8_t                   servCellIdx
7444 )
7445 #else
7446 Void rgSCHUtlDelUeANFdbkInfo(ue,servCellIdx)
7447 RgSchUeCb            *ue;
7448 uint8_t                   servCellIdx;
7449 #endif
7450 {
7451
7452    /* ccpu00117052 - MOD - Passing double pointer
7453    for proper NULLP assignment*/
7454    rgSCHUtlFreeSBuf(ue->cell->instIdx,
7455          (Data **)(&( ue->cellInfo[servCellIdx]->anInfo)), sizeof(RgSchTddANInfo) * \
7456                         ue->cell->ackNackFdbkArrSize);
7457
7458    return;
7459 } /* rgSCHUtlDelUeANFdbkInfo */
7460
7461 /**
7462  * @brief Handler to initialise UE ACK/NACk feedback information
7463  *
7464  * @details
7465  *
7466  *     Function : rgSCHUtlInitUeANFdbkInfo
7467  *
7468  *   It initialises UE related ACK NACK information.
7469  *
7470  *  @param[in]  RgSchTddANInfo   *anFdInfo
7471  *  @return     S16
7472  **/
7473 #ifdef ANSI
7474 S16 rgSCHUtlInitUeANFdbkInfo
7475 (
7476 RgSchTddANInfo       *anFdInfo
7477 )
7478 #else
7479 S16 rgSCHUtlInitUeANFdbkInfo(anFdInfo)
7480 RgSchTddANInfo       *anFdInfo;
7481 #endif
7482 {
7483
7484    anFdInfo->sfn = RGSCH_MAX_SFN+1; /* defensively setting invalid sfn */
7485    anFdInfo->slot = 0;
7486    anFdInfo->ulDai = RG_SCH_INVALID_DAI_VAL;
7487    anFdInfo->dlDai = RG_SCH_INVALID_DAI_VAL;
7488    anFdInfo->latestMIdx = RG_SCH_INVALID_M_VAL;
7489
7490    return ROK;
7491 } /* rgSCHUtlInitUeANFdbkInfo */
7492
7493 /**
7494  * @brief Handler to get UE related ACK NACK feedback information
7495  *
7496  * @details
7497  *
7498  *     Function : rgSCHUtlGetUeANFdbkInfo
7499  *
7500  *   It gets the UE related ACK NACK information based on
7501  *   SFN and slot number.
7502  *
7503  *  @param[in]  RgSchUeCb        *ueCb
7504  *  @param[in]  CmLteTimingInfo  *time
7505  *  @return     RgSchTddANInfo*
7506  **/
7507 #ifdef ANSI
7508 RgSchTddANInfo* rgSCHUtlGetUeANFdbkInfo
7509 (
7510 RgSchUeCb         *ueCb,
7511 CmLteTimingInfo   *timeInfo,
7512 uint8_t                servCellIdx
7513 )
7514 #else
7515 RgSchTddANInfo* rgSCHUtlGetUeANFdbkInfo(ueCb, timeInfo,servCellIdx)
7516 RgSchUeCb         *ueCb;
7517 CmLteTimingInfo   *timeInfo;
7518 uint8_t                servCellIdx;
7519 #endif
7520 {
7521    uint8_t idx;
7522
7523    for (idx = 0; idx < ueCb->cell->ackNackFdbkArrSize; ++idx)
7524    {
7525        if( (timeInfo->sfn == ueCb->cellInfo[servCellIdx]->anInfo[idx].sfn) &&
7526                (timeInfo->slot == ueCb->cellInfo[servCellIdx]->anInfo[idx].slot))
7527        {
7528             return (&ueCb->cellInfo[servCellIdx]->anInfo[idx]);
7529        }
7530    }
7531
7532    return (NULLP);
7533 } /* rgSCHUtlGetUeANFdbkInfo */
7534
7535 /**
7536  * @brief To get downlink slot index
7537  *
7538  * @details
7539  *
7540  *     Function: rgSCHUtlGetDlSfIdx
7541  *     Purpose:  Gets downlink slot index based on SFN and slot no
7542  *
7543  *  @param[in]  CmLteTimingInfo  *timeInfo
7544  *  @param[in]  RgSchCellCb         *cell
7545  *  @return uint8_t
7546  *
7547  **/
7548 #ifdef ANSI
7549 uint8_t  rgSCHUtlGetDlSfIdx
7550 (
7551 RgSchCellCb        *cell,
7552 CmLteTimingInfo *timeInfo
7553 )
7554 #else
7555 uint8_t  rgSCHUtlGetDlSfIdx(cell, timeInfo)
7556 RgSchCellCb        *cell;
7557 CmLteTimingInfo *timeInfo;
7558 #endif
7559 {
7560    uint16_t       idx = 0;
7561
7562    idx = RGSCH_NUM_SUB_FRAMES - \
7563          rgSchTddNumUlSubfrmTbl[cell->ulDlCfgIdx][RGSCH_NUM_SUB_FRAMES-1];
7564    idx = ((idx * timeInfo->sfn) + \
7565          rgSchTddNumDlSubfrmTbl[cell->ulDlCfgIdx][timeInfo->slot]) - 1;
7566    idx = idx % cell->numDlSubfrms;
7567
7568    return ((uint8_t)idx);
7569 }
7570
7571 /**
7572  * @brief To get the next downlink slot
7573  *
7574  * @details
7575  *
7576  *     Function: rgSCHUtlGetNxtDlSfInfo
7577  *     Purpose:  Gets next downlink slot based on current DL slot
7578  *
7579  *  @param[in]  CmLteTimingInfo  curDlTime
7580  *  @param[in]  RgSchCellCb      *cell
7581  *  @param[in]  RgSchDlSf        *dlSf
7582  *  @param[in]  RgSchDlSf        **nxtDlsf
7583  *  @param[in]  CmLteTimingInfo  *nxtDlTime
7584  *  @return uint8_t
7585  *
7586  **/
7587 #ifdef ANSI
7588 Void rgSCHUtlGetNxtDlSfInfo
7589 (
7590 CmLteTimingInfo   curDlTime,
7591 RgSchCellCb       *cell,
7592 RgSchDlSf         *dlSf,
7593 RgSchDlSf         **nxtDlsf,
7594 CmLteTimingInfo   *nxtDlTime
7595 )
7596 #else
7597 Void rgSCHUtlGetNxtDlSfInfo(curDlTime, cell, dlSf, nxtDlsf, nxtDlTime)
7598 CmLteTimingInfo   curDlTime;
7599 RgSchCellCb       *cell;
7600 RgSchDlSf         *dlSf;
7601 RgSchDlSf         **nxtDlsf;
7602 CmLteTimingInfo   *nxtDlTime;
7603 #endif
7604 {
7605    uint16_t  idx = curDlTime.slot;
7606    uint8_t   count = 0;
7607
7608    while(TRUE)
7609    {
7610       do
7611       {
7612          idx = (idx + 1) % RGSCH_NUM_SUB_FRAMES;
7613          count++;
7614       }while(rgSchTddUlDlSubfrmTbl[cell->ulDlCfgIdx][idx]
7615                                        != RG_SCH_TDD_DL_slot);
7616       RG_SCH_ADD_TO_CRNT_TIME(curDlTime, (*nxtDlTime), count);
7617       *nxtDlsf = rgSCHUtlSubFrmGet(cell, *nxtDlTime);
7618       if(dlSf->dlFdbkInfo.slot != (*nxtDlsf)->dlFdbkInfo.slot)
7619       {
7620          break;
7621       }
7622    }
7623    return;
7624 }
7625
7626 /**
7627  * @brief To get the previous downlink slot
7628  *
7629  * @details
7630  *
7631  *     Function: rgSCHUtlGetPrevDlSfInfo
7632  *     Purpose:  Gets previous downlink slot based on current DL slot
7633  *
7634  *  @param[in]  RgSchCellCb      *cell
7635  *  @param[in]  CmLteTimingInfo  curDlTime
7636  *  @param[in]  CmLteTimingInfo  *prevDlTime
7637  *  @param[in]  uint8_t               *numSubfrm
7638  *  @return uint8_t
7639  *
7640  **/
7641 #ifdef ANSI
7642 Void rgSCHUtlGetPrevDlSfInfo
7643 (
7644 RgSchCellCb       *cell,
7645 CmLteTimingInfo   curDlTime,
7646 CmLteTimingInfo   *prevDlTime,
7647 uint8_t                *numSubfrm
7648 )
7649 #else
7650 Void rgSCHUtlGetPrevDlSfInfo(cell, curDlTime, prevDlTime, numSubfrm)
7651 RgSchCellCb       *cell;
7652 CmLteTimingInfo   curDlTime;
7653 CmLteTimingInfo   *prevDlTime;
7654 uint8_t                *numSubfrm;
7655 #endif
7656 {
7657    S16 idx = curDlTime.slot;
7658    uint8_t  count = 0;
7659
7660    do
7661    {
7662       idx--;
7663       if(idx < 0)
7664       {
7665          idx = RGSCH_NUM_SUB_FRAMES-1;
7666       }
7667       count++;
7668    }while(rgSchTddUlDlSubfrmTbl[cell->ulDlCfgIdx][idx]
7669          !=  RG_SCH_TDD_DL_slot);
7670    *numSubfrm = count;
7671    RGSCHDECRFRMCRNTTIME(curDlTime, (*prevDlTime), count);
7672    return;
7673 }
7674
7675 #endif
7676 /* Added Holes Management functions for Adaptive Re transmission */
7677 /******* </AllocHolesMemMgmnt>: START *****/
7678 /***********************************************************
7679  *
7680  *     Func : rgSCHUtlUlSfInit
7681  *
7682  *     Desc : UL slot init.
7683  *
7684  *     Ret  : S16
7685  *
7686  *     Notes:
7687  *
7688  *     File :
7689  *
7690  **********************************************************/
7691 #ifdef ANSI
7692 S16 rgSCHUtlUlSfInit
7693 (
7694 RgSchCellCb  *cell,
7695 RgSchUlSf    *sf,
7696 uint8_t           idx,
7697 uint8_t           maxUePerSf
7698 )
7699 #else
7700 S16 rgSCHUtlUlSfInit(cell, sf, idx, maxUePerSf)
7701 RgSchCellCb  *cell;
7702 RgSchUlSf    *sf;
7703 uint8_t           idx;
7704 uint8_t           maxUePerSf;
7705 #endif
7706 {
7707    S16             ret=ROK;
7708
7709    sf->idx = idx;
7710 #ifdef RG_5GTF
7711    uint8_t index;
7712 #endif
7713
7714 #ifdef LTE_TDD   
7715    if(cell->ulDlCfgIdx == 0)
7716    {
7717       /* Store the Uplink slot number corresponding to the idx */
7718       sf->ulSfIdx = rgSchTddCfg0UlSfTbl[idx%6]; 
7719    }
7720 #endif   
7721    ret = rgSCHUtlAllocSBuf(cell->instIdx, (Data **)&sf->allocDb,
7722                            sizeof(RgSchUlAllocDb));
7723    if (ret != ROK)
7724    {
7725       return (ret);
7726    }
7727    ret = rgSCHUtlUlAllocDbInit(cell, sf->allocDb, maxUePerSf);
7728    if (ret != ROK)
7729    {
7730       /* ccpu00117052 - MOD - Passing double pointer
7731       for proper NULLP assignment*/
7732       rgSCHUtlFreeSBuf(cell->instIdx, (Data **)(&(sf->allocDb)),
7733                        sizeof(RgSchUlAllocDb));
7734       return (ret);
7735    }
7736    ret = rgSCHUtlAllocSBuf(cell->instIdx, (Data **)&sf->holeDb,
7737          sizeof(RgSchUlHoleDb));
7738    if (ret != ROK)
7739    {
7740       rgSCHUtlUlAllocDbDeinit(cell, sf->allocDb);
7741       /* ccpu00117052 - MOD - Passing double pointer
7742       for proper NULLP assignment*/
7743       rgSCHUtlFreeSBuf(cell->instIdx, (Data **)(&(sf->allocDb)),
7744                        sizeof(RgSchUlAllocDb));
7745       return (ret);
7746    }
7747    /* Initialize the hole with CFI 1 Pusch Bw Info */ 
7748    ret = rgSCHUtlUlHoleDbInit(cell, sf->holeDb, (uint8_t)(maxUePerSf + 2), \
7749                               0, cell->dynCfiCb.bwInfo[1].numSb);
7750
7751    if (ret != ROK)
7752    {
7753       rgSCHUtlUlAllocDbDeinit(cell, sf->allocDb);
7754       /* ccpu00117052 - MOD - Passing double pointer
7755       for proper NULLP assignment*/
7756       rgSCHUtlFreeSBuf(cell->instIdx, (Data **)(&(sf->allocDb)),
7757                        sizeof(RgSchUlAllocDb));
7758       rgSCHUtlFreeSBuf(cell->instIdx, (Data **)(&(sf->holeDb)),
7759                        sizeof(RgSchUlHoleDb));
7760       return (ret);
7761    }
7762    cmLListInit(&sf->reTxLst);
7763
7764    /* Fix ccpu00120610*/
7765    sf->allocCountRef = &sf->allocDb->count;
7766
7767    /* initialize UL available subbands for current sub-frame */
7768    sf->availSubbands = cell->dynCfiCb.bwInfo[1].numSb;
7769 #ifdef RG_5GTF
7770    sf->numGrpPerTti = cell->cell5gtfCb.ueGrpPerTti;
7771    sf->numUePerGrp = cell->cell5gtfCb.uePerGrpPerTti;
7772    for(index = 0; index < MAX_5GTF_BEAMS; index++)
7773    {
7774       sf->sfBeamInfo[index].totVrbgAllocated = 0;
7775       sf->sfBeamInfo[index].totVrbgRequired = 0;
7776       sf->sfBeamInfo[index].vrbgStart = 0;
7777    }
7778 #endif
7779
7780    return (ret);
7781 }
7782
7783
7784 /***********************************************************
7785  *
7786  *     Func : rgSCHUtlUlSfDeinit
7787  *
7788  *     Desc : Deinitialises a slot
7789  *
7790  *     Ret  : Void
7791  *
7792  *     Notes:
7793  *
7794  *     File :
7795  *
7796  **********************************************************/
7797 #ifdef ANSI
7798 Void rgSCHUtlUlSfDeinit
7799 (
7800 RgSchCellCb  *cell,
7801 RgSchUlSf    *sf
7802 )
7803 #else
7804 Void rgSCHUtlUlSfDeinit(cell, sf)
7805 RgSchCellCb  *cell;
7806 RgSchUlSf    *sf;
7807 #endif
7808 {
7809    if (sf->allocDb)
7810    {
7811       rgSCHUtlUlAllocDbDeinit(cell, sf->allocDb);
7812       /* ccpu00117052 - MOD - Passing double pointer
7813       for proper NULLP assignment*/
7814       /* ccpu00117052 - MOD - Passing double pointer
7815       for proper NULLP assignment*/
7816       rgSCHUtlFreeSBuf(cell->instIdx, (Data **)(&(sf->allocDb)),
7817                        sizeof(RgSchUlAllocDb));
7818    }
7819    if (sf->holeDb)
7820    {
7821       rgSCHUtlUlHoleDbDeinit(cell, sf->holeDb);
7822       /* ccpu00117052 - MOD - Passing double pointer
7823       for proper NULLP assignment*/
7824       rgSCHUtlFreeSBuf(cell->instIdx, (Data **)(&(sf->holeDb)),
7825                        sizeof(RgSchUlHoleDb));
7826    }
7827    return;
7828 }
7829
7830 /***********************************************************
7831  *
7832  *     Func : rgSCHUtlUlAllocDbInit
7833  *
7834  *     Desc : Initialise allocation DB
7835  *
7836  *     Ret  : S16 (ROK/RFAILED)
7837  *
7838  *     Notes:
7839  *
7840  *     File :
7841  *
7842  **********************************************************/
7843 #ifdef ANSI
7844 static S16 rgSCHUtlUlAllocDbInit
7845 (
7846 RgSchCellCb    *cell,
7847 RgSchUlAllocDb *allocDb,
7848 uint8_t             maxAllocs
7849 )
7850 #else
7851 static S16 rgSCHUtlUlAllocDbInit(cell, allocDb, maxAllocs)
7852 RgSchCellCb    *cell;
7853 RgSchUlAllocDb *allocDb;
7854 uint8_t             maxAllocs;
7855 #endif
7856 {
7857    S16 ret = rgSCHUtlUlAllocMemInit(cell, &allocDb->mem, maxAllocs);
7858    if (ret != ROK)
7859    {
7860       return (ret);
7861    }
7862    allocDb->count = 0;
7863    allocDb->first = NULLP;
7864    return ROK;
7865 }
7866
7867 /***********************************************************
7868  *
7869  *     Func : rgSCHUtlUlAllocDbDeinit
7870  *
7871  *     Desc : Deinitialises allocation DB
7872  *            sent to UE, for a UE with accumulation disabled
7873  *
7874  *     Ret  : Void
7875  *
7876  *     Notes:
7877  *
7878  *     File :
7879  *
7880  **********************************************************/
7881 #ifdef ANSI
7882 static Void rgSCHUtlUlAllocDbDeinit
7883 (
7884 RgSchCellCb     *cell,
7885 RgSchUlAllocDb *allocDb
7886 )
7887 #else
7888 static Void rgSCHUtlUlAllocDbDeinit(cell, allocDb)
7889 RgSchCellCb     *cell;
7890 RgSchUlAllocDb *allocDb;
7891 #endif
7892 {
7893    rgSCHUtlUlAllocMemDeinit(cell, &allocDb->mem);
7894    allocDb->count = 0;
7895    allocDb->first = NULLP;
7896    return;
7897 }
7898
7899 /***********************************************************
7900  *
7901  *     Func : rgSCHUtlUlHoleDbInit
7902  *
7903  *     Desc : Initialise hole DB
7904  *
7905  *     Ret  : S16 (ROK/RFAILED)
7906  *
7907  *     Notes:
7908  *
7909  *     File :
7910  *
7911  **********************************************************/
7912 #ifdef ANSI
7913 static S16 rgSCHUtlUlHoleDbInit
7914 (
7915 RgSchCellCb   *cell,
7916 RgSchUlHoleDb *holeDb,
7917 uint8_t            maxHoles,
7918 uint8_t            start,
7919 uint8_t            num
7920 )
7921 #else
7922 static S16 rgSCHUtlUlHoleDbInit(cell, holeDb, maxHoles, start, num)
7923 RgSchCellCb   *cell;
7924 RgSchUlHoleDb *holeDb;
7925 uint8_t            maxHoles;
7926 uint8_t            start;
7927 uint8_t            num;
7928 #endif
7929 {
7930    S16 ret;
7931    RgSchUlHole *hole = NULLP;
7932
7933    ret = rgSCHUtlUlHoleMemInit(cell, &holeDb->mem, maxHoles, &hole);
7934    if (ret != ROK)
7935    {
7936       return (ret);
7937    }
7938    holeDb->count = 1;
7939    holeDb->first = hole;
7940    hole->start = start;
7941    hole->num = num;
7942    hole->prv = hole->nxt = NULLP;
7943    return ROK;
7944 }
7945
7946 /***********************************************************
7947  *
7948  *     Func : rgSCHUtlUlHoleDbDeinit
7949  *
7950  *     Desc : Deinitialises hole DB
7951  *
7952  *     Ret  : Void
7953  *
7954  *     Notes:
7955  *
7956  *     File :
7957  *
7958  **********************************************************/
7959 #ifdef ANSI
7960 static Void rgSCHUtlUlHoleDbDeinit
7961 (
7962 RgSchCellCb   *cell,
7963 RgSchUlHoleDb *holeDb
7964 )
7965 #else
7966 static Void rgSCHUtlUlHoleDbDeinit(cell, holeDb)
7967 RgSchCellCb   *cell;
7968 RgSchUlHoleDb *holeDb;
7969 #endif
7970 {
7971    rgSCHUtlUlHoleMemDeinit(cell, &holeDb->mem);
7972    holeDb->count = 0;
7973    holeDb->first = NULLP;
7974    return;
7975 }
7976
7977
7978 /***********************************************************
7979  *
7980  *     Func : rgSCHUtlUlAllocGetHole
7981  *
7982  *     Desc : Get allocation from hole
7983  *
7984  *     Ret  : RgSchUlAlloc *
7985  *
7986  *     Notes:
7987  *
7988  *     File :
7989  *
7990  **********************************************************/
7991 #ifdef ANSI
7992 RgSchUlAlloc *rgSCHUtlUlAllocGetHole
7993 (
7994 RgSchUlSf   *sf,
7995 uint8_t       numSb,
7996 RgSchUlHole *hole
7997 )
7998 #else
7999 RgSchUlAlloc *rgSCHUtlUlAllocGetHole(sf, numSb, hole)
8000 RgSchUlSf   *sf;
8001 uint8_t       numSb;
8002 RgSchUlHole *hole;
8003 #endif
8004 {
8005    if (numSb < hole->num)
8006    {
8007       return (rgSCHUtlUlAllocGetPartHole(sf, numSb, hole));
8008    }
8009    else
8010    {
8011       return (rgSCHUtlUlAllocGetCompHole(sf, hole));
8012    }
8013 }
8014
8015
8016 /***********************************************************
8017  *
8018  *     Func : rgSCHUtlUlAllocGetCompHole
8019  *
8020  *     Desc : Get an allocation corresponding to an entire hole
8021  *
8022  *     Ret  : RgSchUlAlloc *
8023  *
8024  *     Notes:
8025  *
8026  *     File :
8027  *
8028  **********************************************************/
8029 #ifdef ANSI
8030 RgSchUlAlloc *rgSCHUtlUlAllocGetCompHole
8031 (
8032 RgSchUlSf   *sf,
8033 RgSchUlHole *hole
8034 )
8035 #else
8036 RgSchUlAlloc *rgSCHUtlUlAllocGetCompHole(sf, hole)
8037 RgSchUlSf   *sf;
8038 RgSchUlHole *hole;
8039 #endif
8040 {
8041    RgSchUlAlloc *alloc;
8042       /* alloc = rgSCHUtlUlAllocGetAndIns(sf->allocDb, hole->prvAlloc, hole->nxtAlloc); */
8043    /* Calling rgSchCmnUlAllocGetAndIns is ok, but prv alloc needs to have nxtHole
8044     * updated, causing another check for prv */
8045    RgSchUlAlloc *prv = hole->prvAlloc;
8046    RgSchUlAlloc *nxt = hole->nxtAlloc;
8047
8048    if (prv)
8049    {
8050       if (hole->start == prv->nxtHole->start)
8051       {
8052          prv->nxtHole = NULLP;
8053       }
8054       alloc = rgSCHUtlUlAllocGetAdjNxt(sf->allocDb, prv);
8055    }
8056    else
8057    {
8058       alloc = rgSCHUtlUlAllocGetFirst(sf->allocDb);
8059    }
8060
8061    RGSCH_NULL_CHECK( 0, alloc);
8062    alloc->prvHole = NULLP;
8063    alloc->nxtHole = NULLP;
8064
8065    alloc->sbStart = hole->start;
8066    alloc->numSb = hole->num;
8067
8068    if (nxt)
8069    {
8070       nxt->prvHole = NULLP;
8071    }
8072
8073    rgSCHUtlUlHoleRls(sf->holeDb, hole);
8074
8075    /* UL_ALLOC_CHANGES*/
8076    alloc->allocDbRef = (void*)sf->allocDb;
8077    alloc->holeDbRef  = (void*)sf->holeDb;
8078    return (alloc);
8079 }
8080
8081 /***********************************************************
8082  *
8083  *     Func : rgSCHUtlUlAllocGetPartHole
8084  *
8085  *     Desc : Get an allocation corresponding to a part of a hole.
8086  *            The initial 'numSb' part of the hole shall be taken
8087  *            away for this alloc.
8088  *
8089  *     Ret  : RgSchUlAlloc *
8090  *
8091  *     Notes:
8092  *
8093  *     File :
8094  *
8095  **********************************************************/
8096 #ifdef ANSI
8097 RgSchUlAlloc *rgSCHUtlUlAllocGetPartHole
8098 (
8099 RgSchUlSf   *sf,
8100 uint8_t       numSb,
8101 RgSchUlHole *hole
8102 )
8103 #else
8104 RgSchUlAlloc *rgSCHUtlUlAllocGetPartHole(sf, numSb, hole)
8105 RgSchUlSf   *sf;
8106 uint8_t       numSb;
8107 RgSchUlHole *hole;
8108 #endif
8109 {
8110    RgSchUlAlloc *alloc;
8111       /* alloc = rgSCHUtlUlAllocGetAndIns(sf->allocDb, hole->prvAlloc, hole->nxtAlloc); */
8112    /* Calling rgSchCmnUlAllocGetAndIns is ok, but prv alloc needs to have nxtHole
8113     * updated, causing another check for prv */
8114    RgSchUlAlloc *prv = hole->prvAlloc;
8115
8116    if (prv)
8117    {
8118       if (hole->start == prv->nxtHole->start)
8119       {
8120          prv->nxtHole = NULLP;
8121       }
8122       alloc = rgSCHUtlUlAllocGetAdjNxt(sf->allocDb, prv);
8123    }
8124    else
8125    {
8126       alloc = rgSCHUtlUlAllocGetFirst(sf->allocDb);
8127    }
8128
8129    RGSCH_NULL_CHECK( 0, alloc);
8130    alloc->prvHole = NULLP;
8131    alloc->nxtHole = hole;
8132    hole->prvAlloc = alloc;
8133
8134    alloc->sbStart = hole->start;
8135    alloc->numSb = numSb;
8136    hole->start += numSb;
8137    hole->num -= numSb;
8138
8139    rgSCHUtlUlHoleDecr(sf->holeDb, hole);
8140
8141    /* UL_ALLOC_CHANGES*/
8142    alloc->allocDbRef = (void*)sf->allocDb;
8143    alloc->holeDbRef  = (void*)sf->holeDb;
8144
8145    return (alloc);
8146 }
8147
8148 /***********************************************************
8149  *
8150  *     Func : rgSCHUtlUlAllocFirst
8151  *
8152  *     Desc : Get first alloc in slot
8153  *
8154  *     Ret  : RgSchUlAlloc *
8155  *
8156  *     Notes:
8157  *
8158  *     File :
8159  *
8160  **********************************************************/
8161 #ifdef ANSI
8162 RgSchUlAlloc *rgSCHUtlUlAllocFirst
8163 (
8164 RgSchUlSf *sf
8165 )
8166 #else
8167 RgSchUlAlloc *rgSCHUtlUlAllocFirst(sf)
8168 RgSchUlSf *sf;
8169 #endif
8170 {
8171    return (sf->allocDb->first);
8172 }
8173
8174 /***********************************************************
8175  *
8176  *     Func : rgSCHUtlUlAllocNxt
8177  *
8178  *     Desc : Get next alloc
8179  *
8180  *     Ret  : RgSchUlAlloc *
8181  *
8182  *     Notes:
8183  *
8184  *     File :
8185  *
8186  **********************************************************/
8187 #ifdef ANSI
8188 RgSchUlAlloc *rgSCHUtlUlAllocNxt
8189 (
8190 RgSchUlSf    *sf,
8191 RgSchUlAlloc *alloc
8192 )
8193 #else
8194 RgSchUlAlloc *rgSCHUtlUlAllocNxt(sf, alloc)
8195 RgSchUlSf    *sf;
8196 RgSchUlAlloc *alloc;
8197 #endif
8198 {
8199    UNUSED(sf);
8200    return (alloc->nxt);
8201 }
8202
8203 /***********************************************************
8204  *
8205  *     Func : rgSCHUtlUlAllocGetAdjNxt
8206  *
8207  *     Desc : Get alloc which is immediately after the passed one.
8208  *            1. Gets alloc from mem.
8209  *            2. Inserts alloc into list (between prv and
8210  *                prv->nxt, prv is not NULLP).
8211  *            3. Increments alloc count.
8212  *            Note 1: Holes are not dealt with here.
8213  *            Note 2: Assumes prv to be NULL.
8214  *
8215  *     Ret  : RgSchUlAlloc *
8216  *
8217  *     Notes:
8218  *
8219  *     File :
8220  *
8221  **********************************************************/
8222 #ifdef ANSI
8223 RgSchUlAlloc *rgSCHUtlUlAllocGetAdjNxt
8224 (
8225 RgSchUlAllocDb *db,
8226 RgSchUlAlloc   *prv
8227 )
8228 #else
8229 RgSchUlAlloc *rgSCHUtlUlAllocGetAdjNxt(db, prv)
8230 RgSchUlAllocDb *db;
8231 RgSchUlAlloc   *prv;
8232 #endif
8233 {
8234    RgSchUlAlloc *alloc = rgSCHUtlUlAllocMemGet(&db->mem);
8235    RgSchUlAlloc *nxt = prv->nxt;
8236
8237 #if (ERRCLASS & ERRCLS_DEBUG)
8238    if ( alloc == NULLP )
8239    {
8240        return  ( NULLP );
8241    }
8242 #endif
8243    alloc->prv = prv;
8244    alloc->nxt = nxt;
8245    prv->nxt = alloc;
8246    if (nxt)
8247    {
8248       nxt->prv = alloc;
8249    }
8250
8251    ++db->count;
8252
8253    return (alloc);
8254 }
8255
8256 /***********************************************************
8257  *
8258  *     Func : rgSCHUtlUlAllocGetFirst
8259  *
8260  *     Desc : Get alloc which is to be the first one in the alloc list
8261  *            1. Gets alloc from mem.
8262  *            2. Inserts alloc as first element into list.
8263  *            3. Increments alloc count.
8264  *            Note 1: Holes are not dealt with here.
8265  *            Note 2: prv to necessarily NULLP.
8266  *
8267  *     Ret  : RgSchUlAlloc *
8268  *
8269  *     Notes:
8270  *
8271  *     File :
8272  *
8273  **********************************************************/
8274 #ifdef ANSI
8275 RgSchUlAlloc *rgSCHUtlUlAllocGetFirst
8276 (
8277 RgSchUlAllocDb *db
8278 )
8279 #else
8280 RgSchUlAlloc *rgSCHUtlUlAllocGetFirst(db)
8281 RgSchUlAllocDb *db;
8282 #endif
8283 {
8284    RgSchUlAlloc *alloc = rgSCHUtlUlAllocMemGet(&db->mem);
8285    RgSchUlAlloc *nxt = db->first;
8286
8287 #if (ERRCLASS & ERRCLS_DEBUG)
8288     if ( alloc == NULLP )
8289     {
8290        return  ( NULLP );
8291     }
8292 #endif
8293
8294    alloc->prv = NULLP;
8295    alloc->nxt = nxt;
8296    if (nxt)
8297    {
8298       nxt->prv = alloc;
8299    }
8300    db->first = alloc;
8301
8302    ++db->count;
8303
8304    return (alloc);
8305 }
8306
8307 /* UL_ALLOC_ENHANCEMENT */
8308 /***********************************************************
8309  *
8310  *     Func : rgSCHUtlUlHoleAddAllocation
8311  *
8312  *     Desc : On freeing an alloc, add to hole
8313  *
8314  *     Ret  : Void
8315  *
8316  *     Notes:
8317  *
8318  *     File :
8319  *
8320  **********************************************************/
8321 #ifdef ANSI
8322 Void rgSCHUtlUlHoleAddAllocation
8323 (
8324 RgSchUlAlloc *alloc
8325 )
8326 #else
8327 Void rgSCHUtlUlHoleAddAllocation(alloc)
8328 RgSchUlAlloc *alloc;
8329 #endif
8330 {
8331    /* Note: rgSchCmnUlHoleUpdAllocLnks function that is used should not exist as
8332     * one, if such excessive branching is done (AllocNone, AllocNoPrv etc).
8333     * The excessive branching is meant to utilise the knowledge of whether prv
8334     * and nxt allocs exist or not. Hence for each kind (none, noprv, nonxt,
8335     * both), there should be a rgSchCmnUlHoleUpdAllocLnks... function (such as
8336     * rgSchCmnUlHoleUpdAllocLnksNone/NoPrv etc. */
8337    RgSchUlHoleDb *db = alloc->holeDbRef;
8338    RgSchUlHole *prv = alloc->prvHole;
8339    RgSchUlHole *nxt = alloc->nxtHole;
8340
8341    if (prv)
8342    {
8343       if (nxt)
8344       {
8345          rgSCHUtlUlHoleJoin(db, prv, nxt, alloc);
8346       }
8347       else
8348          rgSCHUtlUlHoleExtndRight(db, prv, alloc);
8349    }
8350    else
8351    {
8352       if (nxt)
8353       {
8354          rgSCHUtlUlHoleExtndLeft(db, nxt, alloc);
8355       }
8356       else
8357          rgSCHUtlUlHoleNew(db, alloc);
8358    }
8359    return;
8360 }
8361
8362
8363 /***********************************************************
8364  *
8365  *     Func : rgSCHUtlUlAllocRelease
8366  *
8367  *     Desc : Releases an uplink allocation, only take alloc ptr
8368  *
8369  *     Ret  : Void
8370  *
8371  *     Notes:
8372  *
8373  *     File :
8374  *
8375  **********************************************************/
8376 #ifdef ANSI
8377 Void rgSCHUtlUlAllocRelease
8378 (
8379 RgSchUlAlloc *alloc
8380 )
8381 #else
8382 Void rgSCHUtlUlAllocRelease(alloc)
8383 RgSchUlAlloc *alloc;
8384 #endif
8385 {
8386    RgSchUlAllocDb *allocDb = alloc->allocDbRef;
8387    RgSchUlAlloc   *prv = alloc->prv;
8388    RgSchUlAlloc   *nxt = alloc->nxt;
8389
8390    alloc->ue = NULLP;
8391    alloc->raCb = NULLP;
8392    alloc->isAdaptive = FALSE;
8393
8394    if (prv)
8395    {
8396       prv->nxt = nxt;
8397       if (nxt)           /* general case: this allocation lies btw two */
8398       {
8399          nxt->prv = prv;
8400       }
8401    }
8402    else
8403    {
8404       allocDb->first = nxt;
8405       if (nxt)
8406       {
8407          nxt->prv = NULLP;
8408       }
8409    }
8410    --allocDb->count;
8411    rgSCHUtlUlHoleAddAllocation(alloc);
8412    rgSCHUtlUlAllocMemRls(&allocDb->mem, alloc);
8413
8414    return;
8415 }
8416
8417
8418 /***********************************************************
8419  *
8420  *     Func : rgSCHUtlUlAllocRls
8421  *
8422  *     Desc : Releases an uplink allocation
8423  *
8424  *     Ret  : Void
8425  *
8426  *     Notes:
8427  *
8428  *     File :
8429  *
8430  **********************************************************/
8431 #ifdef ANSI
8432 Void rgSCHUtlUlAllocRls
8433 (
8434 RgSchUlSf    *sf,
8435 RgSchUlAlloc *alloc
8436 )
8437 #else
8438 Void rgSCHUtlUlAllocRls(sf, alloc)
8439 RgSchUlSf    *sf;
8440 RgSchUlAlloc *alloc;
8441 #endif
8442 {
8443    RgSchUlAllocDb *allocDb = sf->allocDb;
8444    RgSchUlAlloc   *prv = alloc->prv;
8445    RgSchUlAlloc   *nxt = alloc->nxt;
8446
8447    alloc->ue = NULLP;
8448    alloc->raCb = NULLP;
8449    alloc->isAdaptive = FALSE;
8450
8451    if(allocDb->count)
8452    {
8453       if (prv)
8454       {
8455          prv->nxt = nxt;
8456          if (nxt)           /* general case: this allocation lies btw two */
8457          {
8458             nxt->prv = prv;
8459          }
8460       }
8461       else
8462       {
8463          allocDb->first = nxt;
8464          if (nxt)
8465          {
8466             nxt->prv = NULLP;
8467          }
8468       }
8469       --allocDb->count;
8470       rgSCHUtlUlHoleAddAlloc(sf, alloc);
8471       rgSCHUtlUlAllocMemRls(&allocDb->mem, alloc);
8472    }
8473    else
8474    {
8475
8476       printf("\nError: allocDb->count is ZERO ====\n");
8477    }
8478
8479    //printf("\nallocDb->count:%u\n",allocDb->count);
8480
8481    return;
8482 }
8483
8484 /***********************************************************
8485  *
8486  *     Func : rgSCHUtlUlHoleFirst
8487  *
8488  *     Desc : Get first (largest) hole
8489  *
8490  *     Ret  : RgSchUlHole *
8491  *
8492  *     Notes:
8493  *
8494  *     File :
8495  *
8496  **********************************************************/
8497 #ifdef ANSI
8498 RgSchUlHole *rgSCHUtlUlHoleFirst
8499 (
8500 RgSchUlSf *sf
8501 )
8502 #else
8503 RgSchUlHole *rgSCHUtlUlHoleFirst(sf)
8504 RgSchUlSf *sf;
8505 #endif
8506 {
8507    return (sf->holeDb->first);
8508 }
8509
8510 /***********************************************************
8511  *
8512  *     Func : rgSCHUtlUlHoleNxt
8513  *
8514  *     Desc : Get next largest hole
8515  *
8516  *     Ret  : RgSchUlHole *
8517  *
8518  *     Notes:
8519  *
8520  *     File :
8521  *
8522  **********************************************************/
8523 #ifdef ANSI
8524 RgSchUlHole *rgSCHUtlUlHoleNxt
8525 (
8526 RgSchUlSf   *sf,
8527 RgSchUlHole *hole
8528 )
8529 #else
8530 RgSchUlHole *rgSCHUtlUlHoleNxt(sf, hole)
8531 RgSchUlSf   *sf;
8532 RgSchUlHole *hole;
8533 #endif
8534 {
8535    UNUSED(sf);
8536    return (hole->nxt);
8537 }
8538
8539 /***********************************************************
8540  *
8541  *     Func : rgSCHUtlUlHoleAddAlloc
8542  *
8543  *     Desc : On freeing an alloc, add to hole
8544  *
8545  *     Ret  : Void
8546  *
8547  *     Notes:
8548  *
8549  *     File :
8550  *
8551  **********************************************************/
8552 #ifdef ANSI
8553 Void rgSCHUtlUlHoleAddAlloc
8554 (
8555 RgSchUlSf    *sf,
8556 RgSchUlAlloc *alloc
8557 )
8558 #else
8559 Void rgSCHUtlUlHoleAddAlloc(sf, alloc)
8560 RgSchUlSf    *sf;
8561 RgSchUlAlloc *alloc;
8562 #endif
8563 {
8564    /* Note: rgSchCmnUlHoleUpdAllocLnks function that is used should not exist as
8565     * one, if such excessive branching is done (AllocNone, AllocNoPrv etc).
8566     * The excessive branching is meant to utilise the knowledge of whether prv
8567     * and nxt allocs exist or not. Hence for each kind (none, noprv, nonxt,
8568     * both), there should be a rgSchCmnUlHoleUpdAllocLnks... function (such as
8569     * rgSchCmnUlHoleUpdAllocLnksNone/NoPrv etc. */
8570    RgSchUlHoleDb *db = sf->holeDb;
8571    RgSchUlHole *prv = alloc->prvHole;
8572    RgSchUlHole *nxt = alloc->nxtHole;
8573
8574    if (prv)
8575    {
8576       if (nxt)
8577       {
8578          rgSCHUtlUlHoleJoin(db, prv, nxt, alloc);
8579       }
8580       else
8581          rgSCHUtlUlHoleExtndRight(db, prv, alloc);
8582    }
8583    else
8584    {
8585       if (nxt)
8586       {
8587          rgSCHUtlUlHoleExtndLeft(db, nxt, alloc);
8588       }
8589       else
8590          rgSCHUtlUlHoleNew(db, alloc);
8591    }
8592
8593    /* increment the number of subbands getting freed to total available list */
8594    sf->availSubbands += alloc->numSb;
8595
8596    return;
8597 }
8598
8599 /***********************************************************
8600  *
8601  *     Func : rgSCHUtlUlHoleJoin
8602  *
8603  *     Desc : Join two holes (due to alloc being deleted)
8604  *
8605  *     Ret  : Void
8606  *
8607  *     Notes:
8608  *
8609  *     File :
8610  *
8611  **********************************************************/
8612 #ifdef ANSI
8613 Void rgSCHUtlUlHoleJoin
8614 (
8615 RgSchUlHoleDb *db,
8616 RgSchUlHole   *prv,
8617 RgSchUlHole   *nxt,
8618 RgSchUlAlloc  *alloc
8619 )
8620 #else
8621 Void rgSCHUtlUlHoleJoin(db, prv, nxt, alloc)
8622 RgSchUlHoleDb *db;
8623 RgSchUlHole   *prv;
8624 RgSchUlHole   *nxt;
8625 RgSchUlAlloc  *alloc;
8626 #endif
8627 {
8628    prv->num += alloc->numSb + nxt->num;
8629    rgSCHUtlUlHoleRls(db, nxt);
8630    rgSCHUtlUlHoleIncr(db, prv);
8631    rgSCHUtlUlHoleUpdAllocLnks(prv, alloc->prv, alloc->nxt);
8632
8633    return;
8634 }
8635
8636 /***********************************************************
8637  *
8638  *     Func : rgSCHUtlUlHoleExtndRight
8639  *
8640  *     Desc : Extend hole due to alloc coming 'after' the hole
8641  *            being deleted
8642  *
8643  *     Ret  : Void
8644  *
8645  *     Notes:
8646  *
8647  *     File :
8648  *
8649  **********************************************************/
8650 #ifdef ANSI
8651 Void rgSCHUtlUlHoleExtndRight
8652 (
8653 RgSchUlHoleDb *db,
8654 RgSchUlHole   *prv,
8655 RgSchUlAlloc  *alloc
8656 )
8657 #else
8658 Void rgSCHUtlUlHoleExtndRight(db, prv, alloc)
8659 RgSchUlHoleDb *db;
8660 RgSchUlHole   *prv;
8661 RgSchUlAlloc  *alloc;
8662 #endif
8663 {
8664    prv->num += alloc->numSb;
8665    rgSCHUtlUlHoleIncr(db, prv);
8666    rgSCHUtlUlHoleUpdAllocLnks(prv, alloc->prv, alloc->nxt);
8667    return;
8668 }
8669
8670 /***********************************************************
8671  *
8672  *     Func : rgSCHUtlUlHoleExtndLeft
8673  *
8674  *     Desc : Extend hole due to alloc coming 'before' the hole
8675  *            being deleted
8676  *
8677  *     Ret  : Void
8678  *
8679  *     Notes:
8680  *
8681  *     File :
8682  *
8683  **********************************************************/
8684 #ifdef ANSI
8685 Void rgSCHUtlUlHoleExtndLeft
8686 (
8687 RgSchUlHoleDb *db,
8688 RgSchUlHole   *nxt,
8689 RgSchUlAlloc  *alloc
8690 )
8691 #else
8692 Void rgSCHUtlUlHoleExtndLeft(db, nxt, alloc)
8693 RgSchUlHoleDb *db;
8694 RgSchUlHole   *nxt;
8695 RgSchUlAlloc  *alloc;
8696 #endif
8697 {
8698    nxt->num += alloc->numSb;
8699    nxt->start = alloc->sbStart;
8700    rgSCHUtlUlHoleIncr(db, nxt);
8701    rgSCHUtlUlHoleUpdAllocLnks(nxt, alloc->prv, alloc->nxt);
8702    return;
8703 }
8704
8705 /***********************************************************
8706  *
8707  *     Func : rgSCHUtlUlHoleNew
8708  *
8709  *     Desc : Create new hole due to alloc being deleted
8710  *
8711  *     Ret  : Void
8712  *
8713  *     Notes:
8714  *
8715  *     File :
8716  *
8717  **********************************************************/
8718 #ifdef ANSI
8719 Void rgSCHUtlUlHoleNew
8720 (
8721 RgSchUlHoleDb *db,
8722 RgSchUlAlloc  *alloc
8723 )
8724 #else
8725 Void rgSCHUtlUlHoleNew(db, alloc)
8726 RgSchUlHoleDb *db;
8727 RgSchUlAlloc  *alloc;
8728 #endif
8729 {
8730    RgSchUlHole *hole = rgSCHUtlUlHoleMemGet(&db->mem);
8731 #if (ERRCLASS & ERRCLS_DEBUG)
8732    if ( hole == NULLP )
8733    {
8734       return;
8735    }
8736 #endif
8737    hole->start = alloc->sbStart;
8738    hole->num = alloc->numSb;
8739    ++db->count;
8740    rgSCHUtlUlHoleIns(db, hole);
8741    rgSCHUtlUlHoleUpdAllocLnks(hole, alloc->prv, alloc->nxt);
8742    return;
8743 }
8744
8745 /***********************************************************
8746  *
8747  *     Func : rgSCHUtlUlHoleUpdAllocLnks
8748  *
8749  *     Desc : Update alloc links in hole
8750  *
8751  *     Ret  : Void
8752  *
8753  *     Notes:
8754  *
8755  *     File :
8756  *
8757  **********************************************************/
8758 #ifdef ANSI
8759 Void rgSCHUtlUlHoleUpdAllocLnks
8760 (
8761 RgSchUlHole  *hole,
8762 RgSchUlAlloc *prvAlloc,
8763 RgSchUlAlloc *nxtAlloc
8764 )
8765 #else
8766 Void rgSCHUtlUlHoleUpdAllocLnks(hole, prvAlloc, nxtAlloc)
8767 RgSchUlHole  *hole;
8768 RgSchUlAlloc *prvAlloc;
8769 RgSchUlAlloc *nxtAlloc;
8770 #endif
8771 {
8772    if (prvAlloc)
8773    {
8774       prvAlloc->nxtHole = hole;
8775    }
8776    if (nxtAlloc)
8777    {
8778       nxtAlloc->prvHole = hole;
8779    }
8780    hole->prvAlloc = prvAlloc;
8781    hole->nxtAlloc = nxtAlloc;
8782    return;
8783 }
8784
8785
8786 /***********************************************************
8787  *
8788  *     Func : rgSCHUtlUlHoleIns
8789  *
8790  *     Desc : Insert (newly created) hole in sorted list of holes.
8791  *            Searches linearly, beginning with the largest hole.
8792  *
8793  *     Ret  : Void
8794  *
8795  *     Notes:
8796  *
8797  *     File :
8798  *
8799  **********************************************************/
8800 #ifdef ANSI
8801 Void rgSCHUtlUlHoleIns
8802 (
8803 RgSchUlHoleDb *db,
8804 RgSchUlHole   *hole
8805 )
8806 #else
8807 Void rgSCHUtlUlHoleIns(db, hole)
8808 RgSchUlHoleDb *db;
8809 RgSchUlHole   *hole;
8810 #endif
8811 {
8812    RgSchUlHole *cur;
8813
8814    if ((cur = db->first) != NULLP)
8815    {
8816       RgSchUlHole *nxt;
8817       if (cur->num < hole->num)
8818       {
8819          /* Add at front */
8820          hole->nxt = cur;
8821          cur->prv = hole;
8822          db->first = hole;
8823          hole->prv = NULLP;
8824          return;
8825       }
8826
8827       for (nxt = cur->nxt; nxt; cur = nxt, nxt = nxt->nxt)
8828       {
8829          if (nxt->num < hole->num)
8830          {
8831             /* Insert hole:  cur <-> hole <-> nxt */
8832             cur->nxt = hole;
8833             hole->prv = cur;
8834             hole->nxt = nxt;
8835             nxt->prv = hole;
8836             return;
8837          }
8838       }
8839
8840       /* Add at end */
8841       cur->nxt = hole;
8842       hole->prv = cur;
8843       hole->nxt = NULLP;
8844       return;
8845    }
8846
8847    /* This is the first hole */
8848    db->first = hole;
8849    hole->prv = NULLP; /* may not be needed */
8850    hole->nxt = NULLP;
8851    return;
8852 }
8853
8854
8855 /***********************************************************
8856  *
8857  *     Func : rgSCHUtlUlHoleIncr
8858  *
8859  *     Desc : hole->num has increeased, reposition in sorted
8860  *            list if needed
8861  *
8862  *     Ret  : Void
8863  *
8864  *     Notes:
8865  *
8866  *     File :
8867  *
8868  **********************************************************/
8869 #ifdef ANSI
8870 Void rgSCHUtlUlHoleIncr
8871 (
8872 RgSchUlHoleDb *db,
8873 RgSchUlHole   *hole
8874 )
8875 #else
8876 Void rgSCHUtlUlHoleIncr(db, hole)
8877 RgSchUlHoleDb *db;
8878 RgSchUlHole   *hole;
8879 #endif
8880 {
8881    RgSchUlHole *cur;
8882
8883    if ((cur = hole->prv) != NULLP)
8884    {
8885       RgSchUlHole *prv;
8886
8887       if (cur->num > hole->num)
8888       {
8889          return;
8890       }
8891
8892       /* Remove hole from current position */
8893       cur->nxt = hole->nxt;
8894       if (hole->nxt)
8895       {
8896          hole->nxt->prv = cur;
8897       }
8898
8899       for (prv = cur->prv; prv; cur = prv, prv = prv->prv)
8900       {
8901          if (prv->num > hole->num)
8902          {
8903             /* Insert hole:  prv <-> hole <-> cur */
8904             prv->nxt = hole;
8905             hole->prv = prv;
8906             hole->nxt = cur;
8907             cur->prv = hole;
8908             return;
8909          }
8910       }
8911
8912       /* Add at front */
8913       hole->nxt = cur;
8914       cur->prv = hole;
8915       db->first = hole;
8916       hole->prv = NULLP;
8917       return;
8918    }
8919    return;
8920 }
8921
8922 /***********************************************************
8923  *
8924  *     Func : rgSCHUtlUlHoleDecr
8925  *
8926  *     Desc : hole->num has decreeased, reposition in sorted
8927  *            list if needed
8928  *
8929  *     Ret  : Void
8930  *
8931  *     Notes:
8932  *
8933  *     File :
8934  *
8935  **********************************************************/
8936 #ifdef ANSI
8937 Void rgSCHUtlUlHoleDecr
8938 (
8939 RgSchUlHoleDb *db,
8940 RgSchUlHole   *hole
8941 )
8942 #else
8943 Void rgSCHUtlUlHoleDecr(db, hole)
8944 RgSchUlHoleDb *db;
8945 RgSchUlHole   *hole;
8946 #endif
8947 {
8948    RgSchUlHole *cur;
8949
8950    if ((cur = hole->nxt) != NULLP)
8951    {
8952       RgSchUlHole *nxt;
8953
8954       if (cur->num < hole->num)
8955       {
8956          return;
8957       }
8958
8959       /* Remove hole from current position */
8960       cur->prv = hole->prv;
8961       if (hole->prv)
8962       {
8963          hole->prv->nxt = cur;
8964       }
8965       else /* no prv, so cur to replace hole as first in list */
8966       {
8967          db->first = cur;
8968       }
8969
8970       for (nxt = cur->nxt; nxt; cur = nxt, nxt = nxt->nxt)
8971       {
8972          if (nxt->num < hole->num)
8973          {
8974             /* Insert hole:  cur <-> hole <-> nxt */
8975             cur->nxt = hole;
8976             hole->prv = cur;
8977             hole->nxt = nxt;
8978             nxt->prv = hole;
8979             return;
8980          }
8981       }
8982
8983       /* Add at end */
8984       cur->nxt = hole;
8985       hole->prv = cur;
8986       hole->nxt = NULLP;
8987       return;
8988    }
8989    return;
8990 }
8991
8992 /***********************************************************
8993  *
8994  *     Func : rgSCHUtlUlHoleRls
8995  *
8996  *     Desc : Releases hole.
8997  *            1. Decrements hole count.
8998  *            2. Deletes hole from list.
8999  *            3. Frees hole (hole memory release).
9000  *
9001  *     Ret  : Void
9002  *
9003  *     Notes:
9004  *
9005  *     File :
9006  *
9007  **********************************************************/
9008 #ifdef ANSI
9009 Void rgSCHUtlUlHoleRls
9010 (
9011 RgSchUlHoleDb *db,
9012 RgSchUlHole   *hole
9013 )
9014 #else
9015 Void rgSCHUtlUlHoleRls(db, hole)
9016 RgSchUlHoleDb *db;
9017 RgSchUlHole   *hole;
9018 #endif
9019 {
9020    RgSchUlHole *prv = hole->prv;
9021    RgSchUlHole *nxt = hole->nxt;
9022
9023    --db->count;
9024    if (prv)
9025    {
9026       prv->nxt = nxt;
9027       if (nxt)
9028       {
9029          nxt->prv = prv;
9030       }
9031    }
9032    else
9033    {
9034       db->first = nxt;
9035       if (nxt)
9036       {
9037          nxt->prv = NULLP;
9038       }
9039    }
9040
9041    rgSCHUtlUlHoleMemRls(&db->mem, hole);
9042    return;
9043 }
9044
9045
9046 /***********************************************************
9047  *
9048  *     Func : rgSCHUtlUlAllocMemInit
9049  *
9050  *     Desc : Initialises alloc free pool
9051  *
9052  *     Ret  : S16 (ROK/RFAILED)
9053  *
9054  *     Notes:
9055  *
9056  *     File :
9057  *
9058  **********************************************************/
9059 #ifdef ANSI
9060 S16 rgSCHUtlUlAllocMemInit
9061 (
9062 RgSchCellCb     *cell,
9063 RgSchUlAllocMem *mem,
9064 uint8_t           maxAllocs
9065 )
9066 #else
9067 S16 rgSCHUtlUlAllocMemInit(cell, mem, maxAllocs)
9068 RgSchCellCb     *cell;
9069 RgSchUlAllocMem *mem;
9070 uint8_t           maxAllocs;
9071 #endif
9072 {
9073    S16 ret;
9074    RgSchUlAlloc *allocs;
9075
9076    ret = rgSCHUtlAllocSBuf(cell->instIdx, (Data **)&allocs,
9077                            maxAllocs * sizeof(*allocs));
9078    if (ret != ROK)
9079    {
9080       return (ret);
9081    }
9082    mem->allocs = allocs;
9083    mem->maxAllocs = maxAllocs;
9084    if (mem->maxAllocs == 1)
9085    {
9086       allocs[0].prv = NULLP;
9087       allocs[0].nxt = NULLP;
9088    }
9089    else
9090    {
9091       uint8_t i;
9092       allocs[0].prv = NULLP;
9093       allocs[0].nxt = &allocs[1];
9094       for (i = 1; i < mem->maxAllocs - 1; ++i)
9095       {
9096          allocs[i].prv = &allocs[i-1];
9097          allocs[i].nxt = &allocs[i+1];
9098       }
9099       allocs[i].prv = &allocs[i-1];
9100       allocs[i].nxt = NULLP;
9101    }
9102    mem->firstFree = &allocs[0];
9103    return ROK;
9104 }
9105
9106 /***********************************************************
9107  *
9108  *     Func : rgSCHUtlUlAllocMemDeinit
9109  *
9110  *     Desc : Deinitialises alloc free pool
9111  *
9112  *     Ret  : Void
9113  *
9114  *     Notes:
9115  *
9116  *     File :
9117  *
9118  **********************************************************/
9119 #ifdef ANSI
9120 Void rgSCHUtlUlAllocMemDeinit
9121 (
9122 RgSchCellCb     *cell,
9123 RgSchUlAllocMem *mem
9124 )
9125 #else
9126 Void rgSCHUtlUlAllocMemDeinit(cell, mem)
9127 RgSchCellCb     *cell;
9128 RgSchUlAllocMem *mem;
9129 #endif
9130 {
9131    /* ccpu00117052 - MOD - Passing double pointer
9132    for proper NULLP assignment*/
9133    rgSCHUtlFreeSBuf(cell->instIdx, (Data **)(&(mem->allocs)),
9134                     mem->maxAllocs * sizeof(*mem->allocs));
9135    mem->maxAllocs = 0;
9136    mem->firstFree = NULLP;
9137    return;
9138 }
9139
9140 /***********************************************************
9141  *
9142  *     Func : rgSCHUtlUlHoleMemInit
9143  *
9144  *     Desc : Initialises hole free pool. Assumes maxHoles
9145  *            to be at least 2.
9146  *
9147  *     Ret  : S16 (ROK/RFAILED)
9148  *
9149  *     Notes:
9150  *
9151  *     File :
9152  *
9153  **********************************************************/
9154 #ifdef ANSI
9155 S16 rgSCHUtlUlHoleMemInit
9156 (
9157 RgSchCellCb    *cell,
9158 RgSchUlHoleMem *mem,
9159 uint8_t          maxHoles,
9160 RgSchUlHole    **holeRef
9161 )
9162 #else
9163 S16 rgSCHUtlUlHoleMemInit(cell, mem, maxHoles, holeRef)
9164 RgSchCellCb     *cell;
9165 RgSchUlHoleMem *mem;
9166 uint8_t          maxHoles;
9167 RgSchUlHole    **holeRef;
9168 #endif
9169 {
9170    S16 ret;
9171    RgSchUlHole *holes;
9172
9173    ret = rgSCHUtlAllocSBuf(cell->instIdx, (Data **)&holes,
9174                            maxHoles * sizeof(*holes));
9175    if (ret != ROK)
9176    {
9177       return (ret);
9178    }
9179
9180    mem->holes = holes;
9181    mem->maxHoles = maxHoles;
9182
9183    /* first hole is taken up */
9184    holes[0].prv = NULLP; /* not needed */
9185    holes[0].nxt = NULLP; /* not needed */
9186    *holeRef = &holes[0];
9187
9188    if (mem->maxHoles == 2)
9189    {
9190       holes[1].prv = NULLP; /* may not be needed */
9191       holes[1].nxt = NULLP; /* may not be needed */
9192    }
9193    else
9194    {
9195       uint8_t i;
9196       holes[1].prv = NULLP;
9197       holes[0].nxt = &holes[1];
9198       for (i = 1; i < mem->maxHoles - 1; ++i)
9199       {
9200          holes[i].prv = &holes[i-1];
9201          holes[i].nxt = &holes[i+1];
9202       }
9203       holes[i].prv = &holes[i-1];
9204       holes[i].nxt = NULLP;
9205    }
9206    mem->firstFree = &holes[1];
9207
9208    return ROK;
9209 }
9210
9211 /***********************************************************
9212  *
9213  *     Func : rgSCHUtlUlHoleMemDeinit
9214  *
9215  *     Desc : Deinitialises hole free pool
9216  *
9217  *     Ret  : Void
9218  *
9219  *     Notes:
9220  *
9221  *     File :
9222  *
9223  **********************************************************/
9224 #ifdef ANSI
9225 Void rgSCHUtlUlHoleMemDeinit
9226 (
9227 RgSchCellCb    *cell,
9228 RgSchUlHoleMem *mem
9229 )
9230 #else
9231 Void rgSCHUtlUlHoleMemDeinit(cell, mem)
9232 RgSchCellCb    *cell;
9233 RgSchUlHoleMem *mem;
9234 #endif
9235 {
9236    /* ccpu00117052 - MOD - Passing double pointer
9237    for proper NULLP assignment*/
9238    rgSCHUtlFreeSBuf(cell->instIdx, (Data **)(&(mem->holes)),
9239                     mem->maxHoles * sizeof(*mem->holes));
9240    mem->maxHoles = 0;
9241    mem->firstFree = NULLP;
9242    return;
9243 }
9244
9245 /***********************************************************
9246  *
9247  *     Func : rgSCHUtlUlAllocMemGet
9248  *
9249  *     Desc : Gets an 'alloc' from the free pool
9250  *
9251  *     Ret  : RgSchUlAlloc *
9252  *
9253  *     Notes:
9254  *
9255  *     File :
9256  *
9257  **********************************************************/
9258 #ifdef ANSI
9259 RgSchUlAlloc *rgSCHUtlUlAllocMemGet
9260 (
9261 RgSchUlAllocMem *mem
9262 )
9263 #else
9264 RgSchUlAlloc *rgSCHUtlUlAllocMemGet(mem)
9265 RgSchUlAllocMem *mem;
9266 #endif
9267 {
9268    RgSchUlAlloc *alloc;
9269
9270 #if (ERRCLASS & ERRCLS_DEBUG)
9271    if (mem->firstFree == NULLP)
9272    {
9273       return (NULLP);
9274    }
9275 #endif
9276
9277    alloc = mem->firstFree;
9278    mem->firstFree = alloc->nxt;
9279    alloc->nxt = NULLP; /* probably not needed */
9280    /* alloc->prv might already be NULLP, in case was needed to set it to NULLP */
9281
9282    return (alloc);
9283 }
9284
9285 /***********************************************************
9286  *
9287  *     Func : rgSCHUtlUlAllocMemRls
9288  *
9289  *     Desc : Returns an 'alloc' to the free pool
9290  *
9291  *     Ret  :
9292  *
9293  *     Notes:
9294  *
9295  *     File :
9296  *
9297  **********************************************************/
9298 #ifdef ANSI
9299 Void rgSCHUtlUlAllocMemRls
9300 (
9301 RgSchUlAllocMem *mem,
9302 RgSchUlAlloc    *alloc
9303 )
9304 #else
9305 Void rgSCHUtlUlAllocMemRls(mem, alloc)
9306 RgSchUlAllocMem *mem;
9307 RgSchUlAlloc    *alloc;
9308 #endif
9309 {
9310    alloc->prv = NULLP;
9311
9312    alloc->nxt = mem->firstFree;
9313    if (mem->firstFree != NULLP)
9314    {
9315       mem->firstFree->prv = alloc;
9316    }
9317    mem->firstFree = alloc;
9318    return;
9319 }
9320
9321 /***********************************************************
9322  *
9323  *     Func : rgSCHUtlUlHoleMemGet
9324  *
9325  *     Desc : Gets a 'hole' from the free pool
9326  *
9327  *     Ret  : RgSchUlHole *
9328  *
9329  *     Notes:
9330  *
9331  *     File :
9332  *
9333  **********************************************************/
9334 #ifdef ANSI
9335 RgSchUlHole *rgSCHUtlUlHoleMemGet
9336 (
9337 RgSchUlHoleMem *mem
9338 )
9339 #else
9340 RgSchUlHole *rgSCHUtlUlHoleMemGet(mem)
9341 RgSchUlHoleMem *mem;
9342 #endif
9343 {
9344    RgSchUlHole *hole;
9345
9346 #if (ERRCLASS & ERRCLS_DEBUG)
9347    if (mem->firstFree == NULLP)
9348    {
9349       return (NULLP);
9350    }
9351 #endif
9352
9353    hole = mem->firstFree;
9354    mem->firstFree = hole->nxt;
9355    mem->firstFree->prv = NULLP; /* may not be needed, under error class */
9356    hole->nxt = NULLP; /* probably not needed */
9357    /* hole->prv is might already be NULLP, in case was needed to set it to NULLP */
9358
9359    return (hole);
9360 }
9361
9362 /***********************************************************
9363  *
9364  *     Func : rgSCHUtlUlHoleMemRls
9365  *
9366  *     Desc : Returns a 'hole' to the free pool
9367  *
9368  *     Ret  : Void
9369  *
9370  *     Notes:
9371  *
9372  *     File :
9373  *
9374  **********************************************************/
9375 #ifdef ANSI
9376 Void rgSCHUtlUlHoleMemRls
9377 (
9378 RgSchUlHoleMem *mem,
9379 RgSchUlHole    *hole
9380 )
9381 #else
9382 Void rgSCHUtlUlHoleMemRls(mem, hole)
9383 RgSchUlHoleMem *mem;
9384 RgSchUlHole    *hole;
9385 #endif
9386 {
9387    hole->prv = NULLP;
9388
9389    hole->nxt = mem->firstFree;
9390    if (mem->firstFree != NULLP)
9391    {
9392       mem->firstFree->prv = hole;
9393    }
9394    mem->firstFree = hole;
9395    return;
9396 }
9397
9398 /**
9399  * @brief Get an alloc from the specified position in the BW.
9400  *
9401  * @details
9402  *
9403  *     Function : rgSCHUtlUlGetSpfcAlloc
9404  *
9405  *      - Return an alloc from the specified position in the BW.
9406  *        Note: This function assumes there is always a hole
9407  *              Existing which completely has the specified
9408  *              allocation. The reason for such an assumption is
9409  *              the function's usage as of now guarantees that there
9410  *              will always be such hole. And also for efficiency.
9411  *
9412  *  @param[in]  RgSchUlSf     *sf
9413  *  @param[in]  uint8_t            startSb
9414  *  @param[in]  uint8_t            numSb
9415  *  @return  RgSchUlAlloc*
9416  **/
9417 #ifdef ANSI
9418 RgSchUlAlloc *rgSCHUtlUlGetSpfcAlloc
9419 (
9420 RgSchUlSf       *sf,
9421 uint8_t              startSb,
9422 uint8_t              numSb
9423 )
9424 #else
9425 RgSchUlAlloc *rgSCHUtlUlGetSpfcAlloc(sf, startSb, numSb)
9426 RgSchUlSf       *sf;
9427 uint8_t              startSb;
9428 uint8_t              numSb;
9429 #endif
9430 {
9431    RgSchUlHole     *hole, *nxtHole;
9432    RgSchUlAlloc    *alloc = NULLP;
9433
9434    if ((hole = rgSCHUtlUlHoleFirst(sf)) == NULLP)
9435    {
9436       return (NULLP);
9437    }
9438    do
9439    {
9440       nxtHole = rgSCHUtlUlHoleNxt(sf, hole);
9441       if ((startSb >= hole->start) &&
9442           (startSb+numSb <= hole->start+hole->num))
9443       {
9444          if (startSb != hole->start)
9445          {
9446             /* Create a new hole to accomodate Subbands between
9447              * hole start and req alloc start */
9448             RgSchUlHole *newHole = rgSCHUtlUlHoleMemGet(&(sf->holeDb->mem));
9449
9450 #if (ERRCLASS & ERRCLS_DEBUG)
9451             if ( newHole == NULLP )
9452             {
9453                 return ( NULLP );
9454             }
9455 #endif
9456             newHole->start = hole->start;
9457             newHole->num = startSb - hole->start;
9458             hole->start = startSb;
9459             /* [ccpu00122847]-MOD- Correctly updating the hole->num */
9460             hole->num -= newHole->num;
9461             ++(sf->holeDb->count);
9462             rgSCHUtlUlHoleIns(sf->holeDb, newHole);
9463             newHole->prvAlloc = hole->prvAlloc;
9464             if (newHole->prvAlloc)
9465             {
9466                newHole->prvAlloc->nxtHole = newHole;
9467             }
9468             if (numSb == hole->num)
9469             {
9470                alloc = rgSCHUtlUlAllocGetCompHole(sf, hole);
9471             }
9472             else
9473             {
9474                alloc = rgSCHUtlUlAllocGetPartHole(sf, numSb, hole);
9475             }
9476             alloc->prvHole = newHole;
9477             newHole->nxtAlloc = alloc;
9478          }
9479          else /* Hole start and req alloc start are same */
9480          {
9481             if (numSb == hole->num)
9482             {
9483                alloc = rgSCHUtlUlAllocGetCompHole(sf, hole);
9484             }
9485             else
9486             {
9487                alloc = rgSCHUtlUlAllocGetPartHole(sf, numSb, hole);
9488             }
9489          }
9490          break;
9491       }
9492    } while ((hole = nxtHole) != NULLP);
9493    return (alloc);
9494 }
9495 #ifdef LTE_L2_MEAS
9496 /**
9497  * @brief  Validates the qci values
9498  *
9499  * @details
9500  *
9501  *     Function :rgSCHUtlValidateQci
9502  *
9503  *  @param[in]  RgSchCellCb     *cellCb
9504  *  @param[in]  uint8_t              numQci
9505  *  @param[out] uint8_t              *qci
9506  *  @return  S16
9507  *           ROK
9508  *           RFAILED
9509  **/
9510 #ifdef ANSI
9511 static S16 rgSCHUtlValidateQci
9512 (
9513 RgSchCellCb  *cellCb,
9514 uint8_t           numQci,
9515 uint8_t           *qci
9516 )
9517 #else
9518 static S16 rgSCHUtlValidateQci(cellCb, numQci, qci)
9519 RgSchCellCb  *cellCb;
9520 uint8_t           numQci;
9521 uint8_t           *qci;
9522 #endif
9523 {
9524    uint8_t        qciIdx;
9525    uint8_t        qciVal;
9526
9527
9528    for(qciIdx = 0; qciIdx < numQci; qciIdx++)
9529    {
9530       qciVal = qci[qciIdx];
9531       if(qciVal == 0 || qciVal > 9)
9532       {
9533          return RFAILED;
9534       }
9535       if(qciVal != cellCb->qciArray[qciVal].qci)
9536       {
9537          return RFAILED;
9538       }
9539    }
9540
9541    return ROK;
9542 }/* rgSCHUtlValidateQci */
9543 /**
9544  * @brief  Validates the measurement request parameters.
9545  *
9546  * @details
9547  *
9548  *     Function :rgSCHUtlValidateMeasReq
9549  *
9550  *  @param[in]  RgSchCellCb        *cellCb
9551  *  @param[in]  LrgSchMeasReqInfo  *schL2MeasInfo
9552  *  @param[out] RgSchErrInfo       *err
9553  *  @return  RgSchUlAlloc*
9554  **/
9555 #ifdef ANSI
9556 S16 rgSCHUtlValidateMeasReq
9557 (
9558 RgSchCellCb       *cellCb, 
9559 LrgSchMeasReqInfo *schL2MeasInfo,
9560 RgSchErrInfo      *err
9561 )
9562 #else
9563 S16 rgSCHUtlValidateMeasReq(cellCb, schL2MeasInfo, err)
9564 RgSchCellCb       *cellCb;
9565 LrgSchMeasReqInfo *schL2MeasInfo;
9566 RgSchErrInfo      *err;
9567 #endif
9568 {
9569    uint16_t    measType;
9570    S16   ret;
9571
9572
9573    measType = schL2MeasInfo->measType;
9574
9575    if((measType == 0) ||
9576        measType > 2047)
9577    {
9578       err->errType = RGSCHERR_SCH_INVALID_MEAS_TYPE;
9579       err->errCause = RGSCHERR_SCH_L2MEAS;
9580       return RFAILED;
9581    }
9582    if((schL2MeasInfo->timePrd !=0) &&
9583       (measType & LRG_L2MEAS_AVG_PRB_PER_QCI_DL) &&
9584       ((schL2MeasInfo->avgPrbQciDl.numQci > LRG_MAX_QCI_PER_REQ)||
9585        (schL2MeasInfo->avgPrbQciDl.numQci == 0)))
9586    {
9587       err->errType = RGSCHERR_SCH_INVALID_PARAM_RANGE;
9588       err->errCause = RGSCHERR_SCH_L2MEAS;
9589       return RFAILED;
9590    }
9591    if((schL2MeasInfo->timePrd !=0) &&
9592      (measType & LRG_L2MEAS_AVG_PRB_PER_QCI_UL) &&
9593       (schL2MeasInfo->avgPrbQciUl.numQci > LRG_MAX_QCI_PER_REQ)) 
9594    {
9595       err->errType = RGSCHERR_SCH_INVALID_PARAM_RANGE;
9596       err->errCause = RGSCHERR_SCH_L2MEAS;
9597       return RFAILED;
9598    }
9599    if((measType & LRG_L2MEAS_NMB_ACTV_UE_PER_QCI_DL) &&
9600          ((schL2MeasInfo->nmbActvUeQciDl.numQci > LRG_MAX_QCI_PER_REQ) ||
9601           (schL2MeasInfo->nmbActvUeQciDl.sampPrd == 0)||
9602           ((schL2MeasInfo->timePrd !=0)&&
9603            (schL2MeasInfo->timePrd < schL2MeasInfo->nmbActvUeQciDl.sampPrd)) ||
9604          (schL2MeasInfo->nmbActvUeQciDl.sampPrd > LRG_MAX_SAMP_PRD)))
9605    {
9606       err->errType = RGSCHERR_SCH_INVALID_PARAM_RANGE;
9607       err->errCause = RGSCHERR_SCH_L2MEAS;
9608       return RFAILED;
9609    }
9610    if((measType & LRG_L2MEAS_NMB_ACTV_UE_PER_QCI_UL) &&
9611       ((schL2MeasInfo->nmbActvUeQciUl.numQci > LRG_MAX_QCI_PER_REQ) ||
9612        (schL2MeasInfo->nmbActvUeQciUl.sampPrd == 0)||
9613        ((schL2MeasInfo->timePrd !=0) &&
9614         (schL2MeasInfo->timePrd < schL2MeasInfo->nmbActvUeQciUl.sampPrd)) ||
9615         (schL2MeasInfo->nmbActvUeQciUl.sampPrd > LRG_MAX_SAMP_PRD)))
9616    {
9617       err->errType = RGSCHERR_SCH_INVALID_PARAM_RANGE;
9618       err->errCause = RGSCHERR_SCH_L2MEAS;
9619       return RFAILED;
9620    }
9621    if((schL2MeasInfo->timePrd !=0) &&
9622        (measType & LRG_L2MEAS_AVG_PRB_PER_QCI_DL))
9623    {
9624       RGSCH_ARRAY_BOUND_CHECK(cellCb->instIdx, schL2MeasInfo->avgPrbQciDl.qci,  \
9625       (schL2MeasInfo->avgPrbQciDl.numQci));
9626       ret  = rgSCHUtlValidateQci(cellCb, schL2MeasInfo->avgPrbQciDl.numQci,
9627                                  schL2MeasInfo->avgPrbQciDl.qci);
9628       if(ret != ROK)
9629       {
9630           err->errType = RGSCHERR_SCH_INVALID_QCI_VAL;
9631           err->errCause = RGSCHERR_SCH_L2MEAS;
9632           return RFAILED;
9633       }
9634    }
9635    return ROK;
9636 }/* rgSCHUtlValidateMeasReq */
9637 #endif /* LTE_L2_MEAS */
9638 /******* </AllocHolesMemMgmnt>: END *****/
9639 #ifdef RGR_SI_SCH
9640 /**
9641  * @brief API for sending SI configuration confirm from Scheduler to RRM
9642  *
9643  * @details
9644  *
9645  *     Function: rgSCHUtlRgrSiCfgCfm
9646  *
9647  *     This API is invoked to send SI configuration confirm from Scheduler
9648  *     to RRM.
9649  *     This API fills in Pst structure and SAP Ids and invokes
9650  *     config confirm API towards RRM.
9651  *
9652  *  @param[in]  RgrCfgTransId transId
9653  *  @param[in]  uint8_t            status
9654  *  @return  S16
9655  *      -# ROK
9656  *      -# RFAILED
9657  **/
9658 #ifdef ANSI
9659 S16 rgSCHUtlRgrSiCfgCfm
9660 (
9661 Inst          instId,
9662 SpId          spId,
9663 RgrCfgTransId transId,
9664 uint8_t            status
9665 )
9666 #else
9667 S16 rgSCHUtlRgrSiCfgCfm(instId, spId, transId, status)
9668 Inst          instId;
9669 SpId          spId;
9670 RgrCfgTransId transId;
9671 uint8_t            status;
9672 #endif
9673 {
9674    uint8_t        prntTrans[RGR_CFG_TRANSID_SIZE+1];
9675
9676
9677    memcpy(prntTrans, transId.trans, RGR_CFG_TRANSID_SIZE);
9678    prntTrans[RGR_CFG_TRANSID_SIZE] = '\0';
9679
9680
9681    if(RgUiRgrSiCfgCfm(&rgSchCb[instId].rgrSap[spId].sapCfg.sapPst,
9682                     rgSchCb[instId].rgrSap[spId].sapCfg.suId,
9683                     transId, status) != ROK)
9684    {
9685       RLOG_ARG0(L_ERROR,DBG_INSTID,instId,"rgSCHUtlRgrSiCfgCfm: "
9686                 "RgUiRgrSiCfgCfm Failed ");
9687       return RFAILED;
9688    }
9689
9690    return ROK;
9691 }  /* rgSCHUtlRgrSiCfgCfm */
9692
9693 \f
9694 /**
9695  * @brief API for sending Warning SI configuration confirm from 
9696  * Scheduler to RRM
9697  *
9698  * @details
9699  *
9700  *
9701  *     This API is invoked to send Warning SI configuration confirm 
9702  *     from Scheduler to RRM.
9703  *     This API fills in Pst structure and SAP Ids and invokes
9704  *     config confirm API towards RRM.
9705  *
9706  *  @param[in]  RgrCfgTransId transId
9707  *  @param[in]  uint8_t            status
9708  *  @return  S16
9709  *      -# ROK
9710  *      -# RFAILED
9711  **/
9712 #ifdef ANSI
9713 S16 rgSCHUtlRgrWarningSiCfgCfm
9714 (
9715 Inst          instId,
9716 SpId          spId,
9717 uint8_t            siId,
9718 RgrCfgTransId transId,
9719 uint8_t            status
9720 )
9721 #else
9722 S16 rgSCHUtlRgrWarningSiCfgCfm(instId, spId, siId, transId, status)
9723 Inst          instId;
9724 SpId          spId;
9725 uint8_t            siId;
9726 RgrCfgTransId transId;
9727 uint8_t            status;
9728 #endif
9729 {
9730    uint8_t        prntTrans[RGR_CFG_TRANSID_SIZE+1];
9731
9732
9733    memcpy(prntTrans, transId.trans, RGR_CFG_TRANSID_SIZE);
9734    prntTrans[RGR_CFG_TRANSID_SIZE] = '\0';
9735
9736
9737    if(RgUiRgrWarningSiCfgCfm(&rgSchCb[instId].rgrSap[spId].sapCfg.sapPst,
9738                     rgSchCb[instId].rgrSap[spId].sapCfg.suId, 
9739                     transId, siId, status) != ROK)
9740    {
9741       RLOG_ARG0(L_ERROR,DBG_INSTID,instId,"rgSCHUtlRgrSiCfgCfm: "
9742                 "RgUiRgrSiCfgCfm Failed ");
9743       return RFAILED;
9744    }
9745
9746    return ROK;
9747 }  /* rgSCHUtlRgrWarningSiCfgCfm */
9748
9749 /***********************************************************
9750  *
9751  *     Func : rgSCHUtlPutSiInfo
9752  *
9753  *     Desc : Utility Function to deallocate SI information
9754  *
9755  *
9756  *            RFAILED
9757  *
9758  *
9759  *     File : rg_utl.c
9760  *
9761  **********************************************************/
9762 #ifdef ANSI
9763 Void rgSCHUtlPutSiInfo
9764 (
9765 RgSchCellCb *cell
9766 )
9767 #else
9768 Void rgSCHUtlPutSiInfo(cell)
9769 RgSchCellCb *cell;
9770 #endif
9771 {
9772    uint8_t    idx = 0;
9773    uint32_t   sizeOfSiInfo = 0;
9774    /*Free the buffers in crntSiInfo*/
9775    RGSCH_FREE_MSG(cell->siCb.crntSiInfo.mib)
9776    RGSCH_FREE_MSG(cell->siCb.crntSiInfo.sib1Info.sib1)
9777    
9778    sizeOfSiInfo = sizeof(cell->siCb.crntSiInfo.siInfo)/sizeof(cell->siCb.crntSiInfo.siInfo[0]);
9779    
9780    for(idx=0; idx < sizeOfSiInfo; idx++)
9781    {
9782       RGSCH_FREE_MSG(cell->siCb.crntSiInfo.siInfo[idx].si)
9783    }
9784
9785    /*Free the buffers in newSiInfo */
9786    RGSCH_FREE_MSG(cell->siCb.newSiInfo.mib)
9787    RGSCH_FREE_MSG(cell->siCb.newSiInfo.sib1Info.sib1)
9788
9789    sizeOfSiInfo = sizeof(cell->siCb.newSiInfo.siInfo)/sizeof(cell->siCb.newSiInfo.siInfo[0]);
9790
9791    for(idx=0; idx < sizeOfSiInfo; idx++)
9792    {
9793       RGSCH_FREE_MSG(cell->siCb.newSiInfo.siInfo[idx].si)
9794    }
9795
9796    return;
9797 }
9798 #endif /*RGR_SI_SCH */
9799
9800
9801
9802 /***********************************************************
9803  *
9804  *     Func : rgSCHUtlGetDrxSchdUesInDl
9805  *
9806  *     Desc : Utility Function to fill the get the list of
9807  *            scheduled UEs. On these UE's, drx-inactivity
9808  *            timer will be started/restarted.
9809  *
9810  *     Ret  : ROK
9811  *            RFAILED
9812  *
9813  *     Notes:
9814  *
9815  *     File : rg_utl.c
9816  *
9817  **********************************************************/
9818 #ifdef ANSI
9819 S16 rgSCHUtlGetDrxSchdUesInDl
9820 (
9821 RgSchCellCb     *cellCb,
9822 RgSchUeCb       *ueCb,
9823 RgSchDlHqProcCb *dlHq,
9824 RgInfUeAlloc    *allocInfo,
9825 CmLListCp       *dlDrxInactvTmrLst,
9826 CmLListCp       *dlInActvLst,
9827 CmLListCp       *ulInActvLst
9828 )
9829 #else
9830 S16 rgSCHUtlGetDrxSchdUesInDl(cellCb, ueCb, dlHq, allocInfo, dlDrxInactvTmrLst, dlInActvLst, ulInActvLst)
9831 RgSchCellCb     *cellCb;
9832 RgSchUeCb       *ueCb;
9833 RgSchDlHqProcCb *dlHq;
9834 RgInfUeAlloc    *allocInfo;
9835 CmLListCp       *dlDrxInactvTmrLst;
9836 CmLListCp       *dlInActvLst;
9837 CmLListCp       *ulInActvLst;
9838 #endif
9839 {
9840    Bool                  isNewTx = FALSE;
9841    uint8_t                    idx;
9842    RgSchDrxDlHqProcCb    *drxHq;
9843    RgSchDRXCellCb        *drxCell = cellCb->drxCb;
9844    RgSchDrxUeCb          *drxUe;
9845 #ifdef DEBUGP
9846    Inst                  inst = cellCb->instIdx;
9847 #endif
9848    uint8_t                    cellIdx = ueCb->cellIdToCellIdxMap[RG_SCH_CELLINDEX(dlHq->hqE->cell)];
9849    uint32_t                   dlInactvMask;
9850    uint32_t                   ulInactvMask;
9851
9852    for(idx = 0; idx < allocInfo->nmbOfTBs; idx++)
9853    {
9854       if(allocInfo->tbInfo[idx].isReTx == FALSE)
9855       {
9856          isNewTx = TRUE;
9857          /* Removing break here, since in 2 TB case if 2nd TB is proceeding with 
9858             retx then drxretx timer should be stopped.*/
9859       }
9860       else
9861       {
9862          /*Stop the DRX retransmission timer as UE scheduled for retx. Here
9863           * we stop the timer and inactivate the UE for both UL and DL.
9864           * This may result in loss of one slot for UL but this trade
9865           * off is taken to avoid the overhead of maintaining a list of UEs
9866           * to be inactivated in the next slot.*/
9867          drxHq = RG_SCH_DRX_GET_DL_HQ(dlHq);
9868          drxUe = RG_SCH_DRX_GET_UE(ueCb);
9869          if(drxHq->reTxIndx != DRX_INVALID)
9870          {  
9871             /* This condition should never occur */      
9872             if(drxHq->reTxIndx >= RG_SCH_MAX_DRXQ_SIZE)
9873             {
9874                RGSCHDBGERRNEW(inst,(rgSchPBuf(inst),"[%d]UE:DRXUE RETX IDX[%d]"
9875                         "is out of bound,dlInactvMask %d,procId %d\n", ueCb->ueId,
9876                         drxHq->reTxIndx,ueCb->dl.dlInactvMask, dlHq->procId));
9877             }
9878
9879             drxUe->drxDlInactvMaskPerCell[cellIdx]  |= (RG_SCH_DRX_DLHQ_BITMASK << dlHq->procId);
9880             drxUe->drxUlInactvMaskPerCell[cellIdx]  |= (RG_SCH_DRX_DLHQ_BITMASK << dlHq->procId);
9881
9882             dlInactvMask = RG_SCH_DRX_DLHQ_BITMASK << dlHq->procId;
9883             ulInactvMask = RG_SCH_DRX_DLHQ_BITMASK << dlHq->procId;
9884
9885             for(cellIdx = 0; cellIdx < CM_LTE_MAX_CELLS; cellIdx++)
9886             {
9887                dlInactvMask &= drxUe->drxDlInactvMaskPerCell[cellIdx];
9888                ulInactvMask &= drxUe->drxUlInactvMaskPerCell[cellIdx];
9889             }
9890
9891             drxUe->drxDlInactvMask |= dlInactvMask;
9892             drxUe->drxUlInactvMask |= ulInactvMask;
9893
9894             /* if no other condition is keeping ue active,
9895              * inactivate the Ue
9896              */
9897             if(!RG_SCH_DRX_DL_IS_UE_ACTIVE(drxUe))
9898             {
9899                /* BUG 2 : HARQ_RTT, changed for consistency */
9900                ueCb->dl.dlInactvMask |= (RG_DRX_INACTIVE);
9901
9902                /* Add to DL inactive list */
9903                cmLListAdd2Tail(dlInActvLst,&(ueCb->dlDrxInactvLnk));
9904                ueCb->dlDrxInactvLnk.node = (PTR)ueCb;
9905             }
9906
9907             if(!RG_SCH_DRX_UL_IS_UE_ACTIVE(drxUe))
9908             {
9909                /*BUG 2: HARQ_RTT changed for consistency */
9910                ueCb->ul.ulInactvMask |= (RG_DRX_INACTIVE);
9911
9912                cmLListAdd2Tail(ulInActvLst,&(ueCb->ulDrxInactvLnk));
9913                ueCb->ulDrxInactvLnk.node  = (PTR)ueCb;
9914             }
9915
9916             /* Deleting entry from HARQ RTT queue for the same HARQ proc, 
9917              * if exist. This is the special case which can happen iF UL 
9918              * scheduling is done later. */
9919             if(drxHq->rttIndx != DRX_INVALID)
9920             {
9921                cmLListDelFrm (&(cellCb->drxCb->drxQ[drxHq->rttIndx].harqRTTQ),
9922                      &(drxHq->harqRTTEnt));
9923
9924                drxHq->rttIndx = DRX_INVALID;
9925             }   
9926
9927             cmLListDelFrm (&(drxCell->drxQ[drxHq->reTxIndx].harqRetxQ),
9928                   &(drxHq->harqRetxEnt));
9929             drxHq->reTxIndx = DRX_INVALID;
9930          }
9931       }
9932    }
9933
9934    if(isNewTx == TRUE)
9935    {
9936       if(ueCb->drxCb->raRcvd == TRUE)
9937       {
9938          ueCb->drxCb->raRcvd = FALSE;
9939
9940          /* mark the ra bit */
9941          ueCb->drxCb->drxUlInactvMask |= RG_SCH_DRX_RA_BITMASK;
9942          ueCb->drxCb->drxDlInactvMask |= RG_SCH_DRX_RA_BITMASK;
9943
9944       }/*if(ra->rcvd) == TRUE */
9945
9946       if(ueCb->dlDrxInactvTmrLnk.node == NULLP)
9947       {   
9948          cmLListAdd2Tail(dlDrxInactvTmrLst,&(ueCb->dlDrxInactvTmrLnk));
9949          ueCb->dlDrxInactvTmrLnk.node = (PTR)ueCb;
9950       }
9951    }/*if(isNewTx == TRUE) */
9952
9953    return ROK;
9954 }/* rgSCHUtlGetSchdUes*/
9955 \f
9956 /* ccpu00117452 - MOD - Changed macro name from
9957    RGR_RRM_DLPWR_CNTRL to RGR_CQI_REPT */
9958 #ifdef RGR_CQI_REPT
9959 /**
9960  * @brief This function fills StaInd struct
9961  *
9962  * @details
9963  *
9964  *     Function: rgSCHUtlFillSndStaInd
9965  *     Purpose:  Fills StaInd struct and sends the
9966  *               StaInd to RRM
9967  *
9968  *  @param[in]  RgSchCellCb        *cell  pointer to Cell Control block
9969  *  @param[in]  RgSchUeCb          *ue  pointer to Ue Control block
9970  *  @param[in]  RgrStaIndInfo      *staInfo Sta Ind struct to be filled
9971  *  @param[in]  uint8_t                 numCqiRept NUmber of reports to be filled
9972  *  @return  Void
9973  *
9974  **/
9975 #ifdef ANSI
9976 S16 rgSCHUtlFillSndStaInd
9977 (
9978 RgSchCellCb        *cell,
9979 RgSchUeCb          *ue,
9980 RgrStaIndInfo      *staInfo,
9981 uint8_t                 numCqiRept
9982 )
9983 #else
9984 S16 rgSCHUtlFillSndStaInd(cell, ue, staInfo, numCqiRept)
9985 RgSchCellCb        *cell;
9986 RgSchUeCb          *ue;
9987 RgrStaIndInfo      *staInfo;
9988 uint8_t                 numCqiRept;
9989 #endif
9990 {
9991    uint8_t idxStart;
9992
9993    /* Fill StaInd for sending collated Latest N CQI rpeorts */
9994    /* Find index in the array from where Latest N
9995       reports needs to be fetched. Use this value to index in the array
9996       and copy the reports into staInfo */
9997
9998    /* Fill the Cell Id of PCC of the UE */
9999    staInfo->cellId = ue->cell->cellId;
10000    staInfo->crnti = ue->ueId;
10001
10002    idxStart = ue->schCqiInfo.cqiCount - numCqiRept;
10003
10004    memcpy (&(staInfo->ueCqiInfo.cqiRept),
10005             &(ue->schCqiInfo.cqiRept[idxStart]),
10006             numCqiRept * sizeof(RgrUeCqiRept));
10007
10008    staInfo->ueCqiInfo.numCqiRept = numCqiRept;
10009
10010    ue->schCqiInfo.cqiCount = 0;
10011
10012    /* Call utility function (rgSCHUtlRgrStaInd) to send rpts to RRM */
10013    if(rgSCHUtlRgrStaInd(cell, staInfo) != ROK)
10014    {
10015       RLOG_ARG1(L_ERROR,DBG_CELLID,cell->cellId,"Could not send "
10016          "CQI reports for RNTI:%d",ue->ueId);
10017       return RFAILED;
10018    }
10019
10020    return ROK;
10021
10022 }/* End of rgSCHUtlFillSndStaInd */
10023
10024
10025 \f
10026 /**
10027  * @brief API for sending STA indication from Scheduler to RRM.
10028  *
10029  * @details
10030  *
10031  *     Function: rgSCHUtlRgrStaInd
10032  *
10033  *     This API is invoked to send STA indication from Scheduler instance to RRM.
10034  *     This API fills in Pst structure and RgrStaIndInfo
10035  *     and calls the Sta primitive API towards RRM.
10036  *
10037  *  @param[in]  cell                   RgSchCellCb
10038  *  @param[in]  RgrStsIndInfo          *rgrSta
10039  *  @return  S16
10040  *      -# ROK
10041  *      -# RFAILED
10042  **/
10043 #ifdef ANSI
10044 S16 rgSCHUtlRgrStaInd
10045 (
10046 RgSchCellCb          *cell,
10047 RgrStaIndInfo        *rgrSta
10048 )
10049 #else
10050 S16 rgSCHUtlRgrStaInd(cell, rgrSta)
10051 RgSchCellCb          *cell;
10052 RgrStaIndInfo        *rgrSta;
10053 #endif
10054 {
10055    S16           ret = ROK;
10056    RgSchUpSapCb  *rgrSap;                    /*!< RGR SAP Control Block */
10057
10058
10059
10060    rgrSap = cell->rgrSap;
10061    if (rgrSap->sapSta.sapState != LRG_BND)
10062    {
10063       RLOG_ARG1(L_ERROR,DBG_CELLID,cell->cellId,
10064                "rgSCHUtlRgrStaInd() Upper SAP not bound (%d) ",
10065                rgrSap->sapSta.sapState);
10066       return RFAILED;
10067    }
10068    RgUiRgrStaInd(&(cell->rgrSap->sapCfg.sapPst),
10069          cell->rgrSap->sapCfg.suId, rgrSta);
10070    return (ret);
10071 }  /* rgSCHUtlRgrStaInd*/
10072 #endif /* End of RGR_CQI_REPT */
10073
10074 /* Fix : syed HO UE does not have a valid ue->rntiLnk */
10075 /**
10076  * @brief Indicates MAC to release any rnti context it has.
10077  *
10078  * @details
10079  *     Function : rgSCHUtlIndRntiRls2Mac 
10080  *       This function indicates MAC for this rnti release.
10081  *       In case of ueId change it will indicate MAC
10082  *       about the new rnti to be updated.
10083  *       It will post a release RNTI indication to MAC.
10084  *     
10085  *    
10086  *           
10087  *  @param[in]     RgSchCellCb    *cell
10088  *  @param[in]     CmLteRnti      rnti 
10089  *  @param[in]     Bool           ueIdChng
10090  *  @param[in]     CmLteRnti      newRnti
10091  *  @return  Void
10092  *      -# ROK 
10093  **/
10094 #ifdef ANSI
10095 Void rgSCHUtlIndRntiRls2Mac 
10096 (
10097 RgSchCellCb    *cell,
10098 CmLteRnti      rnti,
10099 Bool           ueIdChng,
10100 CmLteRnti      newRnti
10101 )
10102 #else
10103 Void rgSCHUtlIndRntiRls2Mac(cell, rnti, ueIdChng, newRnti)
10104 RgSchCellCb    *cell;
10105 CmLteRnti      rnti;
10106 Bool           ueIdChng;
10107 CmLteRnti      newRnti;
10108 #endif
10109 {
10110    Pst          pst;
10111    Inst         inst = cell->instIdx;
10112    RgInfRlsRnti rntiInfo;
10113
10114
10115    /* Copy the info to rntiInfo */
10116    rntiInfo.cellId = cell->cellId;
10117    rntiInfo.rnti   = rnti;
10118    /* Fix : syed ueId change as part of reestablishment.
10119     * Now SCH to trigger this. CRG ueRecfg for ueId change 
10120     * is dummy */          
10121    rntiInfo.ueIdChng = ueIdChng;
10122    rntiInfo.newRnti  = newRnti;
10123 #ifdef LTE_ADV
10124    rntiInfo.isUeSCellDel = FALSE;
10125 #endif
10126    /* Invoke MAC to release the rnti */
10127    rgSCHUtlGetPstToLyr(&pst, &rgSchCb[inst], cell->macInst);
10128    RgSchMacRlsRnti(&pst, &rntiInfo);
10129    return;
10130 }
10131
10132 /* LTE_ADV_FLAG_REMOVED_START */
10133 /**
10134  * @brief API for sending LOAD INF indication from Scheduler to RRM.
10135  * @details
10136  *
10137  *     Function: rgSCHUtlRgrLoadInfInd
10138  *
10139  *     This API is invoked to send LOAD INF indication from Scheduler instance to RRM.
10140  *     This API fills in Pst structure and RgrLoadInfIndInfo
10141  *     and calls the Sta primitive API towards RRM.
10142  *
10143  *  @param[in]  cell                    RgSchCellCb
10144  *  @param[in]  RgrLoadInfIndInfo       *rgrLoadInf
10145  *  @return  S16
10146  *      -# ROK
10147  *      -# RFAILED
10148  **/
10149 #ifdef ANSI
10150 S16 rgSCHUtlRgrLoadInfInd
10151 (
10152  RgSchCellCb           *cell,
10153  RgrLoadInfIndInfo     *rgrLoadInf
10154  )
10155 #else
10156 S16 rgSCHUtlRgrLoadInfInd(cell, rgrLoadInf)
10157    RgSchCellCb           *cell;
10158    RgrLoadInfIndInfo     *rgrLoadInf;
10159 #endif
10160 {
10161    S16           ret = ROK;
10162    RgSchUpSapCb  *rgrSap;                    /*!< RGR SAP Control Block */
10163
10164    rgrSap = cell->rgrSap;
10165    if (rgrSap->sapSta.sapState != LRG_BND)
10166    {
10167       RLOG_ARG1(L_ERROR,DBG_CELLID,cell->cellId,
10168                "rgSCHUtlRgrLoadInfInd() Upper SAP not bound (%d) ",
10169                rgrSap->sapSta.sapState);
10170       return RFAILED;
10171    }
10172    RgUiRgrLoadInfInd(&(cell->rgrSap->sapCfg.sapPst),
10173          cell->rgrSap->sapCfg.suId, rgrLoadInf);
10174    return (ret);
10175 }  /* rgSCHUtlRgrLoadInfInd*/
10176 /* LTE_ADV_FLAG_REMOVED_END */
10177
10178 /* MS_FIX : syed SCH to act as MASTER in maintaining
10179  * rnti related context. Trigger to rnti del/Chng at SCH
10180  * will result in a Indication to MAC to release its
10181  * RNTI context. MAC inturn indicates the context cleared
10182  * indication to SCH, upon which SCH would set this
10183 /**
10184  * @brief API for sending STA indication from Scheduler to RRM.
10185  *
10186  * @details
10187  *
10188  *     Function: rgSCHUtlRlsRnti
10189  *
10190  *     This API is invoked to indicate MAC to release rnti
10191  *
10192  *  @param[in]  RgSchCellCb    *cellCb                   
10193  *  @param[in]  RgSchRntiLnk   *rntiLnk,
10194  *  @param[in]  Bool           ueIdChngd,
10195  *  @param[in]  CmLteRnti      newRnti
10196  *  @return  Void
10197  **/
10198
10199 #ifdef ANSI
10200 Void rgSCHUtlRlsRnti
10201 (
10202 RgSchCellCb    *cell,
10203 RgSchRntiLnk   *rntiLnk,
10204 Bool           ueIdChngd,
10205 CmLteRnti      newRnti
10206 )
10207 #else
10208 Void rgSCHUtlRlsRnti(cell, rntiLnk, ueIdChngd, newRnti)
10209 RgSchCellCb    *cell;
10210 RgSchRntiLnk   *rntiLnk;
10211 Bool           ueIdChngd;
10212 CmLteRnti      newRnti;
10213 #endif
10214 {
10215
10216    uint8_t isLegacy = 0;
10217 #ifdef EMTC_ENABLE
10218    if(cell->emtcEnable)
10219    {
10220       rgSCHEmtcUtlRlsRnti(cell, rntiLnk, &isLegacy);
10221    }
10222 #endif
10223    if(!isLegacy)
10224    {
10225       /*Add to Guard Pool*/
10226       cmLListAdd2Tail(&cell->rntiDb.rntiGuardPool, &rntiLnk->rntiGrdPoolLnk);
10227       rntiLnk->rntiGrdPoolLnk.node = (PTR)rntiLnk;
10228    }
10229    /* Fix: syed Explicitly Inidcate MAC to release RNTI */
10230    rgSCHUtlIndRntiRls2Mac(cell, rntiLnk->rnti, ueIdChngd, newRnti);
10231
10232    return;
10233 }
10234
10235
10236 /**
10237  * @brief This function fills StaInd struct
10238  *
10239  * @details
10240  *
10241  *     Function: rgSCHUtlFillSndUeStaInd
10242  *     Purpose:  Fills StaInd struct and sends the
10243  *               StaInd to RRM
10244  *
10245  *  @param[in]  RgSchCellCb        *cell  pointer to Cell Control block
10246  *  @param[in]  RgSchUeCb          *ue  pointer to Ue Control block
10247  *  @param[in]  uint8_t                 numCqiRept NUmber of reports to be filled
10248  *  @return  Void
10249  *
10250  **/
10251 #ifdef ANSI
10252 S16 rgSCHUtlFillSndUeStaInd
10253 (
10254 RgSchCellCb          *cell,
10255 RgSchUeCb            *ue,
10256 RgrUeStaIndInfo      *ueStaInfo
10257 )
10258 #else
10259 S16 rgSCHUtlFillSndUeStaInd(cell, ue, ueStaInfo)
10260 RgSchCellCb          *cell;
10261 RgSchUeCb            *ue;
10262 RgrUeStaIndInfo      *ueStaInfo;
10263 #endif
10264 {
10265
10266    ueStaInfo->cellId = cell->cellId;
10267    ueStaInfo->crnti = ue->ueId;
10268
10269    /* Call utility function (rgSCHUtlRgrUeStaInd) to send rpts to RRM */
10270    if(rgSCHUtlRgrUeStaInd(cell, ueStaInfo) != ROK)
10271    {
10272       RLOG_ARG1(L_ERROR,DBG_CELLID,cell->cellId,"Could not send "
10273          "UE Sta reports CRNTI:%d",ue->ueId);
10274       return RFAILED;
10275    }
10276
10277    return ROK;
10278
10279 }/* End of rgSCHUtlFillSndStaInd */
10280
10281
10282 \f
10283 /**
10284  * @brief API for sending STA indication from Scheduler to RRM.
10285  *
10286  * @details
10287  *
10288  *     Function: rgSCHUtlRgrStaInd
10289  *
10290  *     This API is invoked to send STA indication from Scheduler instance to RRM.
10291  *     This API fills in Pst structure and RgrStaIndInfo
10292  *     and calls the Sta primitive API towards RRM.
10293  *
10294  *  @param[in]  cell                   RgSchCellCb
10295  *  @param[in]  RgrStsIndInfo          *rgrSta
10296  *  @return  S16
10297  *      -# ROK
10298  *      -# RFAILED
10299  **/
10300 #ifdef ANSI
10301 S16 rgSCHUtlRgrUeStaInd
10302 (
10303 RgSchCellCb          *cell,
10304 RgrUeStaIndInfo      *rgrUeSta
10305 )
10306 #else
10307 S16 rgSCHUtlRgrUeStaInd(cell, rgrUeSta)
10308 RgSchCellCb          *cell;
10309 RgrUeStaIndInfo      *rgrUeSta;
10310 #endif
10311 {
10312    S16           ret = ROK;
10313    RgSchUpSapCb  *rgrSap;                    /*!< RGR SAP Control Block */
10314
10315    rgrSap = cell->rgrSap;
10316    if (rgrSap->sapSta.sapState != LRG_BND)
10317    {
10318       RLOG_ARG1(L_ERROR,DBG_CELLID,cell->cellId,
10319                "rgSCHUtlRgrUeStaInd() Upper SAP not bound (%d) ",
10320                rgrSap->sapSta.sapState);
10321       return RFAILED;
10322    }
10323    RgUiRgrUeStaInd(&(cell->rgrSap->sapCfg.sapPst),
10324          cell->rgrSap->sapCfg.suId, rgrUeSta);
10325    return (ret);
10326 }  /* rgSCHUtlRgrStaInd*/
10327
10328 /* RRM_RBC_X */
10329 /**
10330  * @brief function to report DL and UL PRB usage to RRM.
10331  *
10332  *
10333  *     Function: rgSCHUtlUpdAvgPrbUsage
10334  *               This function sends the PRB usage report to 
10335  *               RRM with the interval configured by RRM.
10336  *
10337  *  @param[in]  cell       *RgSchCellCb
10338  *  @return  S16
10339  *      -# ROK
10340  *      -# RFAILED
10341  **/
10342 #ifdef ANSI
10343 S16 rgSCHUtlUpdAvgPrbUsage
10344 (
10345 RgSchCellCb          *cell
10346 )
10347 #else
10348 S16 rgSCHUtlUpdAvgPrbUsage(cell)
10349 RgSchCellCb       *cell;
10350 #endif
10351 {
10352    CmLteTimingInfo  frm;
10353    RgmPrbRprtInd    *prbRprtInd;
10354    S16              ret = ROK;
10355    uint32_t              idx;
10356 #ifdef DBG_MAC_RRM_PRB_PRINT
10357    static uint32_t       count = 0;
10358    const uint32_t reprotForEvery20Sec = 20000/cell->prbUsage.rprtPeriod;
10359
10360    count++;
10361 #endif
10362
10363    frm   = cell->crntTime;
10364    RGSCH_INCR_SUB_FRAME(frm, RG_SCH_CMN_DL_DELTA);
10365
10366    uint16_t numDlSf;
10367    uint16_t numUlSf;
10368 #ifdef LTE_TDD
10369   
10370    if(cell->prbUsage.rprtPeriod >= RGSCH_NUM_SUB_FRAMES)
10371    {
10372       /* Get the total number of DL and UL slots within the reporting period*/
10373       numDlSf = (cell->prbUsage.rprtPeriod * 
10374             rgSchTddNumDlSubfrmTbl[cell->ulDlCfgIdx][RGSCH_NUM_SUB_FRAMES-1])
10375          / RGSCH_NUM_SUB_FRAMES;
10376       numUlSf = (cell->prbUsage.rprtPeriod * 
10377             rgSchTddNumUlSubfrmTbl[cell->ulDlCfgIdx][RGSCH_NUM_SUB_FRAMES-1])
10378          / RGSCH_NUM_SUB_FRAMES;
10379    }
10380    else
10381    {
10382       /* Get the total number of DL and UL slots < 10 ms interval */
10383       numDlSf = rgSchTddNumDlSubfrmTbl[cell->ulDlCfgIdx][frm.slot];
10384       numUlSf = rgSchTddNumUlSubfrmTbl[cell->ulDlCfgIdx][frm.slot];
10385    }
10386 #else
10387      numDlSf = cell->prbUsage.rprtPeriod;
10388      numUlSf = cell->prbUsage.rprtPeriod;
10389 #endif
10390
10391    if(SGetSBuf(cell->rgmSap->sapCfg.sapPst.region, 
10392                cell->rgmSap->sapCfg.sapPst.pool, (Data**)&prbRprtInd, 
10393                sizeof(RgmPrbRprtInd)) != ROK)
10394    {
10395       return RFAILED;
10396    }
10397
10398    memset(&prbRprtInd->stQciPrbRpts[0],
10399             0,
10400             (RGM_MAX_QCI_REPORTS * sizeof(RgmPrbRptPerQci)));
10401
10402    prbRprtInd->bCellId            = cell->cellId;
10403
10404    if(numDlSf > 0)
10405    {
10406       prbRprtInd->bPrbUsageMask |= RGM_PRB_USAGE_DL; 
10407       for (idx = 0; idx < RGM_MAX_QCI_REPORTS; idx++ )
10408       {
10409          prbRprtInd->stQciPrbRpts[idx].bAvgPrbDlUsage  = 
10410            RGSCH_DIV_ROUND((cell->prbUsage.qciPrbRpts[idx].dlTotPrbUsed*100),
10411                            (numDlSf * cell->bwCfg.dlTotalBw));
10412          prbRprtInd->stQciPrbRpts[idx].bQci = cell->prbUsage.qciPrbRpts[idx].qci;
10413          cell->prbUsage.qciPrbRpts[idx].dlTotPrbUsed = 0;
10414       }
10415    }
10416
10417    if(numUlSf > 0)
10418    {
10419       prbRprtInd->bPrbUsageMask |= RGM_PRB_USAGE_UL; 
10420       for (idx = 0; idx < RGM_MAX_QCI_REPORTS; idx++ )
10421       {
10422          prbRprtInd->stQciPrbRpts[idx].bAvgPrbUlUsage  = 
10423            RGSCH_DIV_ROUND((cell->prbUsage.qciPrbRpts[idx].ulTotPrbUsed*100),
10424                            (numUlSf * cell->ulAvailBw));
10425          prbRprtInd->stQciPrbRpts[idx].bQci = cell->prbUsage.qciPrbRpts[idx].qci;
10426          cell->prbUsage.qciPrbRpts[idx].ulTotPrbUsed = 0;
10427       }
10428    }
10429
10430 #ifdef DBG_MAC_RRM_PRB_PRINT
10431    if((count % reprotForEvery20Sec) == 0 )
10432    {
10433       printf("\n====================================================================");
10434       printf("\nMAC:  QCI-1[DL:UL]  | QCI-2[DL:UL]  | QCI-3[DL:UL]  | QCI-4[DL:UL] \n");
10435       printf("======================================================================\n");
10436       printf(" [%d: %d]\t | [%d: %d]\t | [%d: %d]\t| [%d: %d]\t\n", 
10437                  prbRprtInd->stQciPrbRpts[0].bAvgPrbDlUsage,
10438                  prbRprtInd->stQciPrbRpts[0].bAvgPrbUlUsage,
10439                  prbRprtInd->stQciPrbRpts[1].bAvgPrbDlUsage,
10440                  prbRprtInd->stQciPrbRpts[1].bAvgPrbUlUsage,
10441                  prbRprtInd->stQciPrbRpts[2].bAvgPrbDlUsage,
10442                  prbRprtInd->stQciPrbRpts[2].bAvgPrbUlUsage,
10443                  prbRprtInd->stQciPrbRpts[3].bAvgPrbDlUsage,
10444                  prbRprtInd->stQciPrbRpts[3].bAvgPrbUlUsage);
10445    }
10446 #endif
10447    RgUiRgmSendPrbRprtInd(&(cell->rgmSap->sapCfg.sapPst), 
10448                     cell->rgmSap->sapCfg.suId, prbRprtInd);
10449
10450
10451    return (ret);
10452 }
10453 /* RRM_RBC_Y */
10454
10455 /**
10456  * @brief This function resends the Ta in case of 
10457  *        max retx failure or DTX for the Ta transmitted 
10458  *
10459  * @details
10460  *
10461  *     Function: rgSCHUtlReTxTa
10462  *     Purpose:  
10463  *                
10464  *  @param[in]  RgSchCellCb           *cell
10465  *  @param[in]  RgSchUeCb             *ue
10466  *  @return  Void 
10467  *
10468  **/
10469 #ifdef ANSI
10470 Void rgSCHUtlReTxTa 
10471 (
10472 RgSchCellCb       *cellCb,
10473 RgSchUeCb         *ueCb
10474 )
10475 #else
10476 Void rgSCHUtlReTxTa(cellCb, ueCb)
10477 RgSchCellCb       *cellCb;
10478 RgSchUeCb         *ueCb;
10479 #endif
10480 {
10481
10482    /* If TA Timer is running. Stop it */
10483    if (ueCb->taTmr.tmrEvnt != TMR_NONE)
10484    {
10485       rgSCHTmrStopTmr(cellCb, ueCb->taTmr.tmrEvnt, ueCb);
10486    }
10487    /*[ccpu00121813]-ADD-If maxretx is reached then 
10488     * use outstanding TA val for scheduling again */
10489    if(ueCb->dl.taCb.outStndngTa == TRUE)
10490    {
10491       ueCb->dl.taCb.ta = ueCb->dl.taCb.outStndngTaval;
10492       ueCb->dl.taCb.outStndngTaval = RGSCH_NO_TA_RQD;
10493       ueCb->dl.taCb.outStndngTa = FALSE;
10494
10495    }
10496    /* Fix : syed TA state updation missing */
10497    ueCb->dl.taCb.state = RGSCH_TA_TOBE_SCHEDULED;
10498    rgSCHUtlDlTARpt(cellCb, ueCb); 
10499
10500    return;
10501 }
10502
10503 /* Added function for dropping Paging Message*/
10504 /**
10505  * @brief Handler for BO Updt received for BCCH or PCCH.
10506  *
10507  * @details
10508  *
10509  *     Function : rgSCHChkBoUpdate
10510  *
10511  *     This function shall check for BO received falls within the scheduling window or not
10512  *
10513  *
10514  *  @param[in]  RgSchCellCb    *cell
10515  *  @return  S16
10516  *      -# ROK 
10517  *      -# RFAILED
10518  **/
10519 #ifdef ANSI
10520 static S16 rgSCHChkBoUpdate
10521 (
10522 RgSchCellCb    *cell,
10523 RgInfCmnBoRpt  *boUpdt
10524 )
10525 #else
10526 static S16 rgSCHChkBoUpdate (cell, boUpdt)
10527 RgSchCellCb    *cell;
10528 RgInfCmnBoRpt  *boUpdt;
10529 #endif
10530 {
10531
10532    uint32_t crntTimeInSubFrms = 0;
10533    uint32_t boUpdTimeInSubFrms = 0;
10534    uint32_t distance = 0;
10535
10536    crntTimeInSubFrms = (cell->crntTime.sfn * RGSCH_NUM_SUB_FRAMES_5G) +  cell->crntTime.slot +
10537            RG_SCH_CMN_DL_DELTA + 2;  /* As bo received will scheduled in next TTI
10538                                         so incrementing with +1 more */
10539    boUpdTimeInSubFrms = (boUpdt->u.timeToTx.sfn * RGSCH_NUM_SUB_FRAMES_5G)+ boUpdt->u.timeToTx.slot;
10540
10541
10542    distance = boUpdTimeInSubFrms > crntTimeInSubFrms ? \
10543               boUpdTimeInSubFrms - crntTimeInSubFrms : \
10544               (RGSCH_MAX_SUBFRM_5G - crntTimeInSubFrms + boUpdTimeInSubFrms);
10545
10546    if (distance > RGSCH_PCCHBCCH_WIN)
10547    {
10548            return RFAILED;
10549    }
10550    return ROK;
10551
10552 }/*rgSCHChkBoUpdate*/
10553
10554
10555 #ifdef LTE_TDD
10556 /**
10557  * @brief  Utility function to calculate the UL reTxIdx in TDD cfg0
10558  *
10559  * @details
10560  *
10561  *     Function : rgSchUtlCfg0ReTxIdx
10562  *
10563  *     Update the reTxIdx according to the rules mentioned
10564  *     in 3GPP TS 36.213 section 8 for TDD Cfg0
10565  *
10566  *  @param[in]  RgSchCellCb     *cell
10567  *  @param[in]  CmLteTimingInfo  phichTime 
10568  *  @param[in]  uint8_t               hqFdbkIdx
10569  *  @return     uint8_t
10570  **/
10571 #ifdef ANSI
10572 uint8_t rgSchUtlCfg0ReTxIdx
10573 (
10574 RgSchCellCb    *cell,
10575 CmLteTimingInfo phichTime,
10576 uint8_t              hqFdbkIdx
10577 )
10578 #else
10579 uint8_t rgSchUtlCfg0ReTxIdx (cell, phichTime, hqFdbkIdx)
10580 RgSchCellCb    *cell;
10581 CmLteTimingInfo phichTime;
10582 uint8_t              hqFdbkIdx;
10583 #endif
10584 {
10585    uint8_t reTxIdx = RGSCH_INVALID_INFO;
10586    uint8_t iPhich = 0; 
10587    RgSchCmnUlCell  *cellUl = RG_SCH_CMN_GET_UL_CELL(cell);
10588    RgSchUlSf       *ulSf;   
10589    uint8_t               ulSF; /* UL SF in the TDD frame */
10590          
10591    ulSf = &cellUl->ulSfArr[hqFdbkIdx];
10592    ulSF = ulSf->ulSfIdx;
10593     
10594    /* Check for the UL SF 4 or 9 */
10595    if(ulSF == 9 || ulSF == 4)
10596    {
10597      iPhich = 1;  
10598    }
10599    if(phichTime.slot == 0 || phichTime.slot == 5)
10600    {    
10601       if(iPhich == 0)
10602       {
10603          /* Retx will happen according to the Pusch k table */
10604          reTxIdx = cellUl->schdIdx;
10605       }
10606       if(iPhich == 1)
10607       {
10608          /* Retx will happen at n+7 */
10609          RGSCHCMNADDTOCRNTTIME(phichTime, phichTime, 7);
10610          /* Fetch the corresponding  UL slot Idx in UL sf array */ 
10611          reTxIdx = rgSCHCmnGetUlSfIdx(&phichTime, cell);
10612       }   
10613    }
10614    else if(phichTime.slot == 1 || phichTime.slot == 6) 
10615    { 
10616       /* Retx will happen at n+7 */
10617       RGSCHCMNADDTOCRNTTIME(phichTime, phichTime, 7);
10618       /* Fetch the corresponding  UL slot Idx in UL sf array */ 
10619       reTxIdx = rgSCHCmnGetUlSfIdx(&phichTime, cell);
10620    }
10621    return (reTxIdx);
10622 }
10623 #endif
10624
10625 /**
10626  * @brief  Utility function to calculate total num of PRBs required to
10627  *         satisfy DL BO for TM1/TM2/TM6/TM7
10628  *
10629  * @details
10630  *
10631  *     Function : rgSchUtlDlCalc1CwPrb
10632  *
10633  *    Calculate PRBs required for UE to satisfy BO in DL
10634  *   
10635  *    Note : Total calculated PRBs will be assigned to *prbReqrd
10636  *    
10637  *
10638  *  @param[in]  RgSchCellCb     *cell
10639  *  @param[in]  RgSchUeCb       *ue 
10640  *  @param[in]  uint32_t              bo 
10641  *  @param[out] uint32_t             *prbReqrd 
10642  *  @return Void
10643  **/
10644 #ifdef ANSI
10645 Void rgSchUtlDlCalc1CwPrb
10646 (
10647 RgSchCellCb    *cell,
10648 RgSchUeCb      *ue,
10649 uint32_t             bo,
10650 uint32_t            *prbReqrd
10651 )
10652 #else
10653 Void rgSchUtlDlCalc1CwPrb(cell, ue, bo, prbReqrd)
10654 RgSchCellCb   *cell;
10655 RgSchUeCb     *ue;
10656 uint32_t            bo;
10657 uint32_t           *prbReqrd;
10658 #endif
10659 {
10660    RgSchCmnDlCell *dlCell  = RG_SCH_CMN_GET_DL_CELL(cell); 
10661    RgSchCmnDlUe   *dlUe  = RG_SCH_CMN_GET_DL_UE(ue, cell); 
10662    uint32_t            eff;
10663    uint32_t            noRes;
10664    uint8_t             iTbs;
10665    uint8_t             cfi = dlCell->currCfi;               
10666
10667    iTbs  = dlUe->mimoInfo.cwInfo[0].iTbs[0];
10668    eff   = (*(RgSchCmnTbSzEff *)(dlCell->cqiToEffTbl[0][cfi]))[iTbs];
10669
10670    /* Optimization to convert totalBo (which is in-terms of bytes) to bits 
10671     * i.e, << 3 and multiply with 1024 i.e, << 10 */
10672    noRes = ((uint64_t)((bo << 3) << 10)) / (eff);
10673    /* Get the number of RBs needed for this transmission */
10674    /* Number of RBs = No of REs / No of REs per RB       */
10675    *prbReqrd = RGSCH_CEIL(noRes, dlCell->noResPerRb[cfi]);
10676
10677    return;
10678 } /* rgSchUtlDlCalc1CwPrb*/
10679
10680 /**
10681  * @brief  Utility function to calculate total num of PRBs required to
10682  *         satisfy DL BO(BO sum of all logical channels for that UE or an LC BO)
10683  *         for TM3/TM4
10684  *
10685  * @details
10686  *
10687  *     Function : rgSchUtlDlCalc2CwPrb
10688  *
10689  *    Calculate PRBs required for UE to satisfy BO in DL
10690  *   
10691  *    Note : Total calculated PRBs will be assigned to *prbReqrd
10692  *    
10693  *
10694  *  @param[in]  RgSchCellCb     *cell
10695  *  @param[in]  RgSchUeCb       *ue 
10696  *  @param[in]  uint32_t              bo 
10697  *  @param[out] uint32_t             *prbReqrd 
10698  *  @return Void
10699  **/
10700 #ifdef ANSI
10701 Void rgSchUtlDlCalc2CwPrb
10702 (
10703 RgSchCellCb    *cell,
10704 RgSchUeCb      *ue,
10705 uint32_t             bo,
10706 uint32_t            *prbReqrd
10707 )
10708 #else
10709 Void rgSchUtlDlCalc2CwPrb(cell, ue, bo, prbReqrd)
10710 RgSchCellCb   *cell;
10711 RgSchUeCb     *ue;
10712 uint32_t            bo;
10713 uint32_t           *prbReqrd;
10714 #endif
10715 {
10716    RgSchCmnDlCell *dlCell  = RG_SCH_CMN_GET_DL_CELL(cell); 
10717    RgSchCmnDlUe   *dlUe  = RG_SCH_CMN_GET_DL_UE(ue, cell); 
10718    uint32_t            eff1, eff2;
10719    uint32_t            noRes;
10720    uint8_t             noLyr1, noLyr2;
10721    uint8_t             iTbs1, iTbs2;
10722    uint8_t             cfi = dlCell->currCfi;               
10723
10724    if ((dlUe->mimoInfo.forceTD) ||/* Transmit Diversity (TD) */
10725        (dlUe->mimoInfo.ri < 2))/* 1 layer precoding */
10726    {
10727       iTbs1  = dlUe->mimoInfo.cwInfo[0].iTbs[0];
10728       eff1   = (*(RgSchCmnTbSzEff *)(dlCell->cqiToEffTbl[0][cfi]))[iTbs1];
10729
10730       /* Optimization to convert totalBo (which is in-terms of bytes) to bits 
10731        * i.e, << 3 and multiply with 1024 i.e, << 10 */
10732       noRes = ((uint64_t)((bo << 3) << 10)) / (eff1);
10733       /* Get the number of RBs needed for this transmission */
10734       /* Number of RBs = No of REs / No of REs per RB       */
10735       *prbReqrd = RGSCH_CEIL(noRes, dlCell->noResPerRb[cfi]);
10736    }
10737    else
10738    {
10739       noLyr1 = dlUe->mimoInfo.cwInfo[0].noLyr;
10740       noLyr2 = dlUe->mimoInfo.cwInfo[1].noLyr;
10741       iTbs1  = dlUe->mimoInfo.cwInfo[0].iTbs[noLyr1 - 1];
10742       iTbs2  = dlUe->mimoInfo.cwInfo[1].iTbs[noLyr2 - 1];
10743       eff1 = (*(RgSchCmnTbSzEff *)(dlCell->cqiToEffTbl[noLyr1 - 1][cfi]))[iTbs1];
10744       eff2 = (*(RgSchCmnTbSzEff *)(dlCell->cqiToEffTbl[noLyr2 - 1][cfi]))[iTbs2];
10745
10746       /* Optimization to convert totalBo (which is in-terms of bytes) to bits 
10747        * i.e, << 3 and multiply with 1024 i.e, << 10 */
10748       noRes = ((uint64_t)((bo << 3) << 10)) / (eff1 + eff2);
10749       /* Get the number of RBs needed for this transmission */
10750       /* Number of RBs = No of REs / No of REs per RB       */
10751       *prbReqrd = RGSCH_CEIL(noRes, dlCell->noResPerRb[cfi]);
10752    }
10753    return;
10754 } /* rgSchUtlDlCalc2CwPrb */
10755
10756 /**
10757  * @brief  Utility function to calculate total num of PRBs required to
10758  *         satisfy DL BO(BO sum of all logical channels for that UE or an LC BO)
10759  *
10760  * @details
10761  *
10762  *     Function : rgSchUtlCalcTotalPrbReq
10763  *
10764  *    This function calls TM specific routine to calculate PRB
10765  *   
10766  *
10767  *  @param[in]  RgSchCellCb     *cell
10768  *  @param[in]  RgSchUeCb       *ue 
10769  *  @param[in]  uint32_t              bo 
10770  *  @param[out] uint32_t             *prbReqrd 
10771  *  @return Void
10772  **/
10773 #ifdef ANSI
10774 Void rgSchUtlCalcTotalPrbReq
10775 (
10776 RgSchCellCb    *cell,
10777 RgSchUeCb      *ue,
10778 uint32_t             bo,
10779 uint32_t            *prbReqrd
10780 )
10781 #else
10782 Void rgSchUtlCalcTotalPrbReq(cell, ue, bo, prbReqrd)
10783 RgSchCellCb   *cell;
10784 RgSchUeCb     *ue;
10785 uint32_t            bo;
10786 uint32_t           *prbReqrd;
10787 #endif
10788 {
10789    /* Call TM specific Prb calculation routine */
10790    (dlCalcPrbFunc[ue->mimoInfo.txMode - 1])(cell, ue, bo, prbReqrd);
10791
10792    return;
10793 } /* rgSchUtlCalcTotalPrbReq */
10794 #ifdef UNUSE_FUN
10795 #ifdef TFU_UPGRADE
10796 /***********************************************************
10797  *
10798  *     Func : rgSCHUtlFetchPcqiBitSz
10799  *
10800  *
10801  *     Desc : Fetch the CQI/PMI bits for a UE based on the mode, periodicity.
10802  *
10803  *     Ret  : uint8_t
10804  *            ROK - Success
10805  *
10806  *     Notes:
10807  *
10808  *     File :
10809  *
10810  **********************************************************/
10811 #ifdef ANSI
10812 static uint8_t rgSCHUtlFetchPcqiBitSz
10813 (
10814  RgSchCellCb    *cell,
10815  RgSchUeCb    *ueCb, 
10816  uint8_t           numTxAnt
10817  )
10818 #else
10819 static uint8_t rgSCHUtlFetchPcqiBitSz (cell, ueCb, numTxAnt)
10820 RgSchCellCb   *cell;
10821 RgSchUeCb     *ueCb;
10822 uint8_t            numTxAnt;
10823 #endif
10824 {
10825    uint8_t   confRepMode;
10826    uint8_t   pcqiSz;
10827    uint8_t   ri;
10828    RgSchUePCqiCb *cqiCb = RG_SCH_GET_UE_CELL_CQI_CB(ueCb,cell);
10829
10830    confRepMode = cqiCb->cqiCfg.cqiSetup.prdModeEnum;
10831    if((ueCb->mimoInfo.txMode != RGR_UE_TM_3) && 
10832          (ueCb->mimoInfo.txMode != RGR_UE_TM_4))
10833    {
10834       ri =1;
10835    }
10836    else
10837    {
10838       ri = cqiCb->perRiVal;
10839    }
10840    switch(confRepMode)
10841    {
10842       case RGR_PRD_CQI_MOD10:
10843       {
10844          pcqiSz = 4;
10845       }
10846       break;
10847
10848       case RGR_PRD_CQI_MOD11:
10849       {
10850          if(numTxAnt == 2)
10851          {
10852             if (ri ==1)
10853             {
10854                pcqiSz = 6;
10855             }
10856             else
10857             {
10858                pcqiSz = 8;
10859             }
10860          }
10861          else if(numTxAnt == 4)
10862          {
10863             if (ri ==1)
10864             {
10865                pcqiSz = 8;
10866             }
10867             else
10868             {
10869                pcqiSz = 11;
10870             }
10871          }
10872          else
10873          {
10874             /* This is number of antenna case 1.
10875              * This is not applicable for Mode 1-1. 
10876              * So setting it to invalid value */
10877             pcqiSz = 0;
10878          }
10879       }
10880       break;
10881
10882       case RGR_PRD_CQI_MOD20:
10883       {
10884          if(cqiCb->isWb)
10885          {
10886             pcqiSz = 4;
10887          }
10888          else
10889          {
10890             pcqiSz = 4 + cqiCb->label;
10891          }
10892       }
10893       break;
10894
10895       case RGR_PRD_CQI_MOD21:
10896       {
10897          if(cqiCb->isWb)
10898          {
10899              if(numTxAnt == 2)
10900              {
10901                 if (ri ==1)
10902                 {
10903                     pcqiSz = 6;
10904                 }
10905                 else
10906                 {
10907                     pcqiSz = 8;
10908                 }
10909              }
10910              else if(numTxAnt == 4)
10911              {
10912                 if (ri ==1)
10913                 {
10914                     pcqiSz = 8;
10915                 }
10916                 else
10917                 {
10918                     pcqiSz = 11;
10919                 }
10920              }
10921              else
10922              {
10923                 /* This might be number of antenna case 1.
10924                  * For mode 2-1 wideband case only antenna port 2 or 4 is supported.
10925                  * So setting invalid value.*/
10926                 pcqiSz = 0;
10927              }
10928           }
10929           else
10930           {
10931              if (ri ==1)
10932              {
10933                  pcqiSz = 4 + cqiCb->label;
10934              }
10935              else
10936              {
10937                  pcqiSz = 7 + cqiCb->label;
10938              }
10939           }
10940       }
10941       break;
10942
10943       default:
10944          pcqiSz = 0;
10945       break;
10946    }
10947    
10948    return (pcqiSz);
10949 }
10950 #endif
10951 #endif
10952 /**
10953  * @brief  Utility function to returns the number of subbands based on the 
10954  *         requested bytes.
10955  *
10956  * @details
10957  *
10958  *     Function : rgSchUtlGetNumSbs
10959  *
10960  *     Calculate the number of PRBs
10961  *     Update the subbandRequired based on the nPrbs and subband size
10962  *
10963  *  @param[in]  RgSchCellCb  *cell
10964  *  @param[in]  RgSchUeCb    *ue
10965  *  @param[in]  uint32_t          *numSbs
10966  *  @return     uint8_t
10967  **/
10968 #ifdef ANSI
10969 uint8_t rgSchUtlGetNumSbs
10970 (
10971 RgSchCellCb                  *cell,
10972 RgSchUeCb                    *ue,
10973 uint32_t                     *numSbs
10974 )
10975 #else
10976 uint8_t rgSchUtlGetNumSbs (cell, ue, numSbs)
10977 RgSchCellCb                  *cell;
10978 RgSchUeCb                    *ue;
10979 uint32_t                     *numSbs;
10980 #endif
10981 {
10982    uint32_t                       nPrb;
10983    //Currently hardcoding MAX prb for each UE
10984    nPrb = ue->ue5gtfCb.maxPrb;
10985    (*numSbs) = RGSCH_CEIL(nPrb, MAX_5GTF_VRBG_SIZE);
10986    return ROK;
10987 }
10988
10989 /**
10990  * @brief  Utility function to insert the UE node into UE Lst based on the
10991  *         number of subbands allocated for the UE for the current TTI.
10992  *
10993  * @details
10994  *
10995  *     Function : rgSchUtlSortInsUeLst
10996  *
10997  *     If subbandRequired < Min, then insert at head
10998  *     Else If subbandRequired > Max, then insert at tail
10999  *     Else, traverse the list and place the node at the appropriate place
11000  *
11001  *  @param[in]  RgSchCellCb  *cell
11002  *  @param[in]  RgSchUeCb    *ue
11003  *  @return     uint8_t
11004  **/
11005 #ifdef ANSI
11006 uint8_t rgSchUtlSortInsUeLst
11007 (
11008 RgSchCellCb  *cell,
11009 CmLListCp    *ueLst,
11010 CmLList      *node,
11011 uint8_t      vrbgRequired
11012 )
11013 #else
11014 uint8_t rgSchUtlSortInsUeLst (cell, ueLst, node, vrbgRequired)
11015 RgSchCellCb  *cell;
11016 CmLListCp    *ueLst;
11017 CmLList      *node;
11018 uint8_t      vrbgRequired;
11019 #endif
11020 {
11021    CmLList      *ueInLst;
11022    CmLList      *firstUeInLst;
11023    CmLList      *lastUeInLst;
11024    RgSchUeCb    *tempUe;
11025    RgSchCmnUlUe *ueUl;
11026
11027    //firstUeInLst = cmLListFirst(ueLst);
11028    CM_LLIST_FIRST_NODE(ueLst,firstUeInLst);
11029    if(NULLP == firstUeInLst)
11030    {
11031       /* first node to be added to the list */
11032       cmLListAdd2Tail(ueLst, node);
11033    }
11034    else
11035    {
11036       /* Sb Required for the UE is less than the first node in the list */
11037       tempUe      = (RgSchUeCb *)(firstUeInLst->node);
11038       ueUl = RG_SCH_CMN_GET_UL_UE(tempUe, cell);
11039
11040       if(vrbgRequired <= ueUl->vrbgRequired)
11041       {
11042          cmLListInsCrnt(ueLst, (node));
11043       }
11044       else
11045       {
11046          /* Sb Required for this UE is higher than the UEs in the list */
11047          lastUeInLst = cmLListLast(ueLst);
11048          tempUe      = (RgSchUeCb *)(lastUeInLst->node);
11049          if(vrbgRequired >= ueUl->vrbgRequired)
11050          {
11051             cmLListAdd2Tail(ueLst, (node));
11052          }
11053          else
11054          {
11055             /* This UE needs to be in the middle. Search and insert the UE */
11056             ueInLst = cmLListFirst(ueLst);
11057             do
11058             {
11059                tempUe = (RgSchUeCb *)(ueInLst->node);
11060
11061                if(vrbgRequired <= ueUl->vrbgRequired)
11062                {
11063                   cmLListInsCrnt(ueLst, (node));
11064                   break;
11065                }
11066
11067                ueInLst = cmLListNext(ueLst);
11068
11069             } while(NULLP != ueInLst && ueInLst != firstUeInLst);
11070          }
11071       }
11072    }
11073
11074    return ROK;
11075 }
11076
11077 /**
11078  * @brief Function to Send LCG GBR register to MAC
11079  *
11080  * @details
11081  *
11082  *     Function: rgSCHUtlBuildNSendLcgReg
11083  *
11084  *     Handler for sending LCG GBR registration 
11085  *
11086  *     Invoked by: 
11087  *         SCHD
11088  *
11089  *     Processing Steps:
11090  *           
11091  *  @param[in] RgSchCellCb       *cell
11092  *  @param[in] CmLteRnti         crnti
11093  *  @param[in] uint8_t                lcgId
11094  *  @param[in] Bool              isGbr
11095  *  @return  S16
11096  *      -# ROK 
11097  **/
11098 #ifdef ANSI
11099 S16 rgSCHUtlBuildNSendLcgReg
11100 (
11101 RgSchCellCb    *cell,
11102 CmLteRnti      crnti,
11103 uint8_t        lcgId,
11104 Bool           isGbr
11105 )
11106 #else
11107 S16 rgSCHUtlBuildNSendLcgReg(cell, crnti, lcgId, isGbr)
11108 RgSchCellCb    *cell;
11109 CmLteRnti      crnti;
11110 uint8_t        lcgId;
11111 Bool           isGbr;
11112 #endif
11113 {
11114    Pst            pst;
11115    RgInfLcgRegReq lcgRegReq;
11116
11117    memset(&pst, 0, sizeof(Pst));
11118    lcgRegReq.isGbr  = isGbr;
11119    lcgRegReq.cellId = cell->cellId;
11120    lcgRegReq.crnti  = crnti;
11121    lcgRegReq.lcgId  = lcgId;
11122    rgSCHUtlGetPstToLyr(&pst, &rgSchCb[cell->instIdx], cell->macInst);
11123    /* code Coverage portion of the test case */ 
11124    RgSchMacLcgReg(&pst, &lcgRegReq);
11125
11126    return ROK;
11127 }
11128
11129 #ifdef TFU_UPGRADE
11130 #ifdef LTE_ADV
11131 #ifndef TFU_TDD
11132 /**
11133  * @brief Function to map RGR pucch type to TFU type
11134  *
11135  * @details
11136  *
11137  *     Function: rgSchUtlGetFdbkMode
11138  *
11139  *
11140  *     Invoked by: 
11141  *         SCHD
11142  *
11143  *     Processing Steps:
11144  *           
11145  *  @param[in] RgrSchFrmt1b3TypEnum
11146  *  @return  TfuAckNackMode
11147  *      -# ROK 
11148  **/
11149 #ifdef ANSI
11150 TfuAckNackMode rgSchUtlGetFdbkMode
11151 (
11152 RgrSchFrmt1b3TypEnum fdbkType
11153 )
11154 #else
11155 TfuAckNackMode rgSchUtlGetFdbkMode(fdbkType)
11156 RgrSchFrmt1b3TypEnum fdbkType;
11157 #endif
11158 {
11159
11160    TfuAckNackMode mode = TFU_UCI_FORMAT_1A_1B;
11161
11162    switch(fdbkType)
11163    {
11164      case RG_SCH_UCI_FORMAT_NON_CA:
11165      case RG_SCH_UCI_FORMAT1A_1B:
11166      {
11167         mode = TFU_UCI_FORMAT_1A_1B;
11168      }
11169      break;
11170      case RG_SCH_UCI_FORMAT1B_CS:
11171      {
11172         mode = TFU_UCI_FORMAT_1B_CS;
11173      }
11174      break;
11175      case RG_SCH_UCI_FORMAT3:
11176      {
11177         mode = TFU_UCI_FORMAT_3;
11178      }
11179      break;
11180    }
11181    return (mode);
11182 }
11183 #endif /* TFU_TDD */
11184 #endif /* LTE_ADV */
11185 #endif /*TFU_UPGRADE */
11186
11187 #ifdef LTE_ADV
11188 /**
11189  * @brief Send Ue SCell delete to SMAC.
11190  *
11191  * @details
11192  *
11193  *     Function : rgSCHUtlSndUeSCellDel2Mac 
11194  *       This function populates the struct RgInfRlsRnti and
11195  *       get the pst for SMac and mark field isUeSCellDel to TRUE which 
11196  *       indicates that it is a Ue SCell delete.
11197  *     
11198  *    
11199  *           
11200  *  @param[in]     RgSchCellCb    *cell
11201  *  @param[in]     CmLteRnti      rnti 
11202  *  @return  Void
11203  *      -# ROK 
11204  **/
11205 #ifdef ANSI
11206 Void rgSCHUtlSndUeSCellDel2Mac 
11207 (
11208 RgSchCellCb    *cell,
11209 CmLteRnti      rnti
11210 )
11211 #else
11212 Void rgSCHUtlSndUeSCellDel2Mac(cell, rnti)
11213 RgSchCellCb    *cell;
11214 CmLteRnti      rnti;
11215 #endif
11216 {
11217    Pst          pst;
11218    Inst         inst = cell->instIdx;
11219    RgInfRlsRnti rntiInfo;
11220
11221    RGSCHDBGINFONEW(inst,(rgSchPBuf(inst),"RNTI Release IND for UE(%d)\n", rnti));
11222    /* Copy the info to rntiInfo */
11223    rntiInfo.cellId = cell->cellId;
11224    rntiInfo.rnti   = rnti;
11225    /* Fix : syed ueId change as part of reestablishment.
11226     * Now SCH to trigger this. CRG ueRecfg for ueId change 
11227     * is dummy */          
11228    rntiInfo.ueIdChng = FALSE;
11229    rntiInfo.newRnti  = rnti;
11230    rntiInfo.isUeSCellDel = TRUE;
11231    /* Invoke MAC to release the rnti */
11232    rgSCHUtlGetPstToLyr(&pst, &rgSchCb[inst], cell->macInst);
11233    RgSchMacRlsRnti(&pst, &rntiInfo);
11234    return;
11235 }
11236
11237 /**
11238  * @brief Returns max TB supported by a given txMode
11239  *
11240  * @details
11241  *
11242  *     Function : rgSCHUtlGetMaxTbSupp
11243  *     Max TB supported for TM Modes (1,2,5,6 and 7) is 1
11244  *     and 2 for others
11245  *    
11246  *           
11247  *  @param[in]     RgrTxMode  txMode
11248  *  @return        uint8_t maxTbCount; 
11249  *      -# ROK 
11250  **/
11251 #ifdef ANSI
11252 uint8_t rgSCHUtlGetMaxTbSupp
11253 (
11254 RgrTxMode txMode
11255 )
11256 #else
11257 uint8_t rgSCHUtlGetMaxTbSupp(txMode)
11258 RgrTxMode txMode
11259 #endif
11260 {
11261    uint8_t maxTbCount;
11262
11263    /* Primary Cell */
11264
11265    switch(txMode)
11266    {
11267       case RGR_UE_TM_1:
11268       case RGR_UE_TM_2:
11269       case RGR_UE_TM_5:
11270       case RGR_UE_TM_6:
11271       case RGR_UE_TM_7:
11272          maxTbCount = 1;
11273          break;
11274       case RGR_UE_TM_3:
11275       case RGR_UE_TM_4:
11276       case RGR_UE_TM_8:
11277       case RGR_UE_TM_9:
11278          maxTbCount = 2;
11279          break;
11280       default:
11281          maxTbCount = 0;
11282          break;
11283    }
11284
11285    return (maxTbCount);
11286 }
11287
11288 /**
11289  * @brief Send Ue SCell delete to SMAC.
11290  *
11291  * @details
11292  *
11293  *     Function : rgSCHTomUtlGetTrigSet 
11294  *      This function gets the triggerset based on cqiReq 
11295  *     
11296  *  @param[in]     RgSchCellCb    *cell
11297  *  @param[in]     RgSchUeCb      ueCb 
11298  *  @param[in]     uint8_t             cqiReq,
11299  *  @param[out]    uint8_t             *triggerSet
11300  *
11301  *  @return  Void
11302  *      -# ROK 
11303  **/
11304 #ifdef ANSI
11305 Void rgSCHTomUtlGetTrigSet
11306 (
11307    RgSchCellCb       *cell,
11308    RgSchUeCb         *ueCb,
11309    uint8_t           cqiReq,
11310    uint8_t           *triggerSet
11311  )
11312 #else
11313 static S16 rgSCHTomUtlGetTrigSet(cell, ueCb, cqiReq, triggerSet)
11314    RgSchCellCb       *cell;
11315    RgSchUeCb         *ueCb;
11316    uint8_t           cqiReq;
11317    uint8_t           *triggerSet;
11318 #endif
11319 {
11320    RgSchUeCellInfo *pCellInfo = RG_SCH_CMN_GET_PCELL_INFO(ueCb);
11321    switch(cqiReq)
11322    {
11323       case RG_SCH_APCQI_SERVING_CC:
11324          {
11325             /* APeriodic CQI request for Current Carrier.*/
11326             uint8_t sCellIdx = ueCb->cellIdToCellIdxMap[RG_SCH_CELLINDEX(cell)];
11327             *triggerSet = 1 << (7 - sCellIdx);
11328             break;
11329          }
11330       case RG_SCH_APCQI_1ST_SERVING_CCS_SET:
11331          {
11332             *triggerSet = pCellInfo->acqiCb.aCqiCfg.triggerSet1;
11333             break;
11334          }
11335       case RG_SCH_APCQI_2ND_SERVING_CCS_SET:
11336          {
11337             *triggerSet = pCellInfo->acqiCb.aCqiCfg.triggerSet2;
11338             break;
11339          }
11340       default:
11341          {
11342             /* BUG */
11343             break;
11344          }
11345    }
11346    return;
11347 }
11348 #endif
11349 /**
11350  * @brief This function updates the value of UE specific DCI sizes
11351  *
11352  * @details
11353  *
11354  *     Function: rgSCHUtlUpdUeDciSize
11355  *     Purpose:  This function calculates and updates DCI Sizes in bits.
11356  *
11357  *     Invoked by: Scheduler
11358  *
11359  *  @param[in]  RgSchCellCb       *cell
11360  *  @param[in]  RgSchUeCb         *ueCb
11361  *  @param[in]  isCsi2Bit         *isCsi2Bit: is 1 bit or 2 bit CSI
11362  *  @return     Void
11363  *
11364  **/
11365 #ifdef ANSI
11366 Void rgSCHUtlUpdUeDciSize
11367 (
11368 RgSchCellCb      *cell,
11369 RgSchUeCb        *ueCb,
11370 Bool             isCsi2Bit
11371 )
11372 #else
11373 Void rgSCHUtlUpdUeDciSize(cell, ueCb, isCsi2Bit)
11374 RgSchCellCb      *cell;
11375 RgSchUeCb        *ueCb;
11376 Bool             isCsi2Bit;
11377 #endif
11378 {
11379    uint8_t dci01aCmnSize = cell->dciSize.baseSize[TFU_DCI_FORMAT_0];
11380    uint8_t dci01aDedSize = cell->dciSize.baseSize[TFU_DCI_FORMAT_0];
11381    if ((ueCb->accessStratumRls >= RGR_REL_10) && (cell->bwCfg.dlTotalBw >= cell->bwCfg.ulTotalBw))
11382    {
11383       dci01aCmnSize += 1; /* Resource Allocation Type DCI 0 */
11384       dci01aDedSize += 1; /* Resource Allocation Type DCI 0 */
11385    }
11386    if (isCsi2Bit == TRUE)
11387    {
11388       dci01aDedSize += 2; /* 2 bit CSI DCI 0 */
11389    }
11390    else
11391    {
11392       dci01aDedSize += 1; /* 1 bit CSI DCI 0 */
11393    }
11394    
11395    /* Common CSI is always 1 bit DCI 0 */
11396    dci01aCmnSize += 1; /* 1 bit CSI DCI 0 */
11397
11398    /* Compare the sizes of DCI 0 with DCI 1A and consider the greater */
11399    if (dci01aCmnSize < cell->dciSize.baseSize[TFU_DCI_FORMAT_1A])
11400    {
11401       dci01aCmnSize = cell->dciSize.baseSize[TFU_DCI_FORMAT_1A];
11402    }
11403    if (dci01aDedSize < cell->dciSize.baseSize[TFU_DCI_FORMAT_1A])
11404    {
11405       dci01aDedSize = cell->dciSize.baseSize[TFU_DCI_FORMAT_1A];
11406    }
11407
11408    /* Remove the Ambiguous Sizes as mentioned in table Table 5.3.3.1.2-1 Spec 36.212-a80 Sec 5.3.3.1.3 */
11409    dci01aCmnSize += rgSchDciAmbigSizeTbl[dci01aCmnSize];
11410    dci01aDedSize += rgSchDciAmbigSizeTbl[dci01aDedSize];
11411
11412    ueCb->dciSize.cmnSize[TFU_DCI_FORMAT_0]  = dci01aCmnSize;
11413    ueCb->dciSize.cmnSize[TFU_DCI_FORMAT_1A] = dci01aCmnSize;
11414    
11415    ueCb->dciSize.dedSize[TFU_DCI_FORMAT_0]  = dci01aDedSize;
11416    ueCb->dciSize.dedSize[TFU_DCI_FORMAT_1A] = dci01aDedSize;
11417
11418    ueCb->dciSize.dedSize[TFU_DCI_FORMAT_1] = cell->dciSize.baseSize[TFU_DCI_FORMAT_1];
11419    do {
11420       /* Spec 36.212-a80 Sec 5.3.3.1.2: If the UE is configured to decode PDCCH with CRC scrambled 
11421        * by the C-RNTI and the number of information bits in format 1 is equal to that for format 0/1A 
11422        * for scheduling the same serving cell and mapped onto the UE specific search space given by the 
11423        * C-RNTI as defined in [3], one bit of value zero shall be appended to format 1. */
11424       if (ueCb->dciSize.dedSize[TFU_DCI_FORMAT_1] == ueCb->dciSize.dedSize[TFU_DCI_FORMAT_1A])
11425       {
11426          ueCb->dciSize.dedSize[TFU_DCI_FORMAT_1] += 1;
11427       }
11428
11429       /* Spec 36.212-a80 Sec 5.3.3.1.2: If the number of information bits in format 1 belongs 
11430        * to one of the sizes in Table 5.3.3.1.2-1, one or more zero bit(s) shall be appended 
11431        * to format 1 until the payload size of format 1 does not belong to one of the sizes in 
11432        * Table 5.3.3.1.2-1 and is not equal to that of format 0/1A mapped onto the same search space. */
11433       ueCb->dciSize.dedSize[TFU_DCI_FORMAT_1] += rgSchDciAmbigSizeTbl[ueCb->dciSize.dedSize[TFU_DCI_FORMAT_1]];
11434    } while (ueCb->dciSize.dedSize[TFU_DCI_FORMAT_1] == ueCb->dciSize.dedSize[TFU_DCI_FORMAT_1A]);
11435
11436    /* Just copying the value of 2/2A to avoid multiple checks at PDCCH allocations. This values never change.*/
11437    ueCb->dciSize.dedSize[TFU_DCI_FORMAT_2]  = cell->dciSize.size[TFU_DCI_FORMAT_2];
11438    ueCb->dciSize.dedSize[TFU_DCI_FORMAT_2A] = cell->dciSize.size[TFU_DCI_FORMAT_2A];
11439    ueCb->dciSize.noUlCcSize[TFU_DCI_FORMAT_2]  = cell->dciSize.size[TFU_DCI_FORMAT_2];
11440    ueCb->dciSize.noUlCcSize[TFU_DCI_FORMAT_2A] = cell->dciSize.size[TFU_DCI_FORMAT_2A];
11441
11442    /* Spec 36.212-a80 Sec 5.3.3.1.3: except when format 1A assigns downlink resource 
11443     * on a secondary cell without an uplink configuration associated with the secondary cell */
11444    ueCb->dciSize.noUlCcSize[TFU_DCI_FORMAT_1A] = cell->dciSize.baseSize[TFU_DCI_FORMAT_1A];
11445    ueCb->dciSize.noUlCcSize[TFU_DCI_FORMAT_1A] += rgSchDciAmbigSizeTbl[ueCb->dciSize.noUlCcSize[TFU_DCI_FORMAT_1A]];
11446    ueCb->dciSize.noUlCcSize[TFU_DCI_FORMAT_1] = cell->dciSize.baseSize[TFU_DCI_FORMAT_1];
11447    do {
11448       /* Spec 36.212-a80 Sec 5.3.3.1.2: If the UE is configured to decode PDCCH with CRC scrambled 
11449        * by the C-RNTI and the number of information bits in format 1 is equal to that for format 0/1A 
11450        * for scheduling the same serving cell and mapped onto the UE specific search space given by the 
11451        * C-RNTI as defined in [3], one bit of value zero shall be appended to format 1. */
11452       if (ueCb->dciSize.noUlCcSize[TFU_DCI_FORMAT_1] == ueCb->dciSize.noUlCcSize[TFU_DCI_FORMAT_1A])
11453       {
11454          ueCb->dciSize.noUlCcSize[TFU_DCI_FORMAT_1] += 1;
11455       }
11456
11457       /* Spec 36.212-a80 Sec 5.3.3.1.2: If the number of information bits in format 1 belongs 
11458        * to one of the sizes in Table 5.3.3.1.2-1, one or more zero bit(s) shall be appended 
11459        * to format 1 until the payload size of format 1 does not belong to one of the sizes in 
11460        * Table 5.3.3.1.2-1 and is not equal to that of format 0/1A mapped onto the same search space. */
11461       ueCb->dciSize.noUlCcSize[TFU_DCI_FORMAT_1] += rgSchDciAmbigSizeTbl[ueCb->dciSize.noUlCcSize[TFU_DCI_FORMAT_1]];
11462    } while (ueCb->dciSize.noUlCcSize[TFU_DCI_FORMAT_1] == ueCb->dciSize.noUlCcSize[TFU_DCI_FORMAT_1A]);
11463 #ifdef EMTC_ENABLE
11464    rgSCHEmtcUtlUpdUeDciSize(cell, ueCb); 
11465 #endif      
11466 }
11467
11468 /**
11469  * @brief This function initialises the DCI Size table
11470  *
11471  * @details
11472  *
11473  *     Function: rgSCHUtlCalcDciSizes
11474  *     Purpose:  This function calculates and initialises DCI Sizes in bits.
11475  *
11476  *     Invoked by: Scheduler
11477  *
11478  *  @param[in]  RgSchCellCb       *cell
11479  *  @return     Void
11480  *
11481  **/
11482 #ifdef ANSI
11483 Void rgSCHUtlCalcDciSizes
11484 (
11485 RgSchCellCb       *cell
11486 )
11487 #else
11488 Void rgSCHUtlCalcDciSizes(cell)
11489 RgSchCellCb       *cell;
11490 #endif
11491 {
11492    uint8_t dciSize = 0;
11493    uint8_t dci01aSize = 0;
11494    uint32_t bits = 0, idx = 0;
11495
11496    switch(TFU_DCI_FORMAT_0) /* Switch case for the purpose of readability */
11497    {
11498       case TFU_DCI_FORMAT_0:
11499          {
11500             /* DCI 0: Spec 36.212 Section 5.3.3.1.1 */
11501             dciSize = 0;
11502             /*-- Calculate resource block assignment bits need to be set
11503               Which is ln(N(N+1)/2) 36.212 5.3.3.1 --*/
11504             bits = (cell->bwCfg.ulTotalBw * (cell->bwCfg.ulTotalBw + 1) / 2);
11505             while ((bits & 0x8000) == 0)
11506             {
11507                bits <<= 1;
11508                idx++;
11509             }
11510             bits = 16 - idx;
11511
11512             dciSize = 1 /* DCI 0 bit indicator */ + \
11513                       1 /* Frequency hoping enable bit field */ + \
11514                       (uint8_t)bits /* For frequency Hopping */ + \
11515                       5 /* MCS */ + \
11516                       1 /* NDI */ + \
11517                       2 /* TPC */ + \
11518                       3 /* DMRS */
11519 #ifdef TFU_TDD
11520                       + \
11521                       2 /* UL Index Config 0 or DAI Config 1-6 */
11522 #endif
11523                       ;
11524
11525             cell->dciSize.baseSize[TFU_DCI_FORMAT_0] = dciSize;
11526
11527             /* If hoping flag is enabled */
11528             if (cell->bwCfg.ulTotalBw <= 49) /* Spec 36.213 Table 8.4-1, N UL_hop, if hopping is enabled */
11529             {
11530                cell->dciSize.dci0HopSize = 1;
11531             }
11532             else
11533             {
11534                cell->dciSize.dci0HopSize = 2;
11535             }
11536
11537             /* Update common non-CRNTI scrambled DCI 0/1A flag */
11538             dci01aSize = cell->dciSize.baseSize[TFU_DCI_FORMAT_0] + 1; /* 1 bit CSI */
11539          }
11540       case TFU_DCI_FORMAT_1A:
11541          {
11542             /* DCI 1A: Spec 36.212 Section 5.3.3.1.3 */
11543             dciSize = 0;
11544             idx = 0;
11545             /* Calculate resource block assignment bits need to be set
11546               Which is ln(N(N+1)/2) */
11547             bits = (cell->bwCfg.dlTotalBw * (cell->bwCfg.dlTotalBw + 1) / 2);
11548             while ((bits & 0x8000) == 0)
11549             {
11550                bits <<= 1;
11551                idx++;
11552             }
11553             bits = 16 - idx;
11554
11555             dciSize += 1 /* Format 1A */ + \
11556                        1 /* Local or Distributed */ + \
11557                        (uint8_t)bits /* Resource block Assignment */ + \
11558                        5 /* MCS */ + 
11559 #ifdef TFU_TDD
11560                        4 /* HARQ Proc Id */ + 
11561 #else
11562                        3 /* HARQ Proc Id */ + 
11563 #endif
11564                        1 /* NDI */ + \
11565                        2 /* RV */ + \
11566                        2 /* TPC CMD */
11567 #ifdef TFU_TDD
11568                        + \
11569                        2 /* DAI */
11570 #endif
11571                        ;
11572             cell->dciSize.baseSize[TFU_DCI_FORMAT_1A] = dciSize;
11573
11574             /* If the UE is not configured to decode PDCCH with CRC scrambled by the C-RNTI, 
11575              * and the number of information bits in format 1A is less than that of format 0, 
11576              * zeros shall be appended to format 1A until the payload size equals that of format 0. */
11577             /* Compare the size with DCI 1A  and DCI 0 and consider the greater one */
11578             if (dci01aSize < cell->dciSize.baseSize[TFU_DCI_FORMAT_1A])
11579             {
11580                dci01aSize = cell->dciSize.baseSize[TFU_DCI_FORMAT_1A];
11581             }
11582             /* If the number of information bits in format 1A belongs to one of the sizes in 
11583              * Table 5.3.3.1.2-1, one zero bit shall be appended to format 1A. */
11584             dci01aSize += rgSchDciAmbigSizeTbl[dci01aSize];
11585             cell->dciSize.size[TFU_DCI_FORMAT_1A] = cell->dciSize.size[TFU_DCI_FORMAT_0] = dci01aSize;
11586          }
11587       case TFU_DCI_FORMAT_1:
11588          {
11589             /* DCI 1: Spec 36.212 Section 5.3.3.1.2 */
11590             dciSize = 0;
11591             if (cell->bwCfg.dlTotalBw > 10)
11592             {
11593                dciSize = 1; /* Resource Allocation header bit */
11594             }
11595             
11596             /* Resouce allocation bits Type 0 and Type 1 */
11597             bits = (cell->bwCfg.dlTotalBw/cell->rbgSize);
11598             if ((cell->bwCfg.dlTotalBw % cell->rbgSize) != 0)
11599             {
11600                bits++;
11601             }
11602
11603             dciSize += (uint8_t)bits /* Resource Allocation bits */ + \
11604                        5 /* MCS */ + 
11605 #ifdef TFU_TDD
11606                        4 /* HARQ TDD */ + 
11607 #else
11608                        3 /* HARQ FDD */ + 
11609 #endif
11610                        1 /* NDI */ + \
11611                        2 /* Redunancy Version */ + \
11612                        2 /* TPC Cmd */
11613 #ifdef TFU_TDD
11614                        + \
11615                        2 /* DAI */
11616 #endif
11617                        ;
11618
11619             
11620             cell->dciSize.baseSize[TFU_DCI_FORMAT_1] = dciSize;
11621
11622             cell->dciSize.size[TFU_DCI_FORMAT_1] = dciSize;
11623             
11624             do {
11625                /* If the UE is not configured to decode PDCCH with CRC 
11626                 * scrambled by the C-RNTI and the number of information bits in format 1 
11627                 * is equal to that for format 0/1A, one bit of value zero shall be appended 
11628                 * to format 1. */
11629                if (dci01aSize == cell->dciSize.size[TFU_DCI_FORMAT_1])
11630                {
11631                   cell->dciSize.size[TFU_DCI_FORMAT_1] += 1;
11632                }
11633
11634                /* If the number of information bits in format 1 belongs to one of the sizes in 
11635                 * Table 5.3.3.1.2-1, one or more zero bit(s) shall be appended to format 1 until 
11636                 * the payload size of format 1 does not belong to one of the sizes in Table 5.3.3.1.2-1 
11637                 * and is not equal to that of format 0/1A mapped onto the same search space. */
11638                cell->dciSize.size[TFU_DCI_FORMAT_1] += rgSchDciAmbigSizeTbl[cell->dciSize.size[TFU_DCI_FORMAT_1]];
11639             } while (cell->dciSize.size[TFU_DCI_FORMAT_1] == dci01aSize);
11640          }
11641       case TFU_DCI_FORMAT_2:
11642          {
11643             /* DCI 2: Spec 36.212 Section 5.3.3.1.5 */
11644             dciSize = 0;
11645             if (cell->bwCfg.dlTotalBw > 10)
11646             {
11647                dciSize = 1; /* Resource Allocation bit */
11648             }
11649
11650             dciSize += (uint8_t)bits /* Resource Allocation bits */ + \
11651                        2 /* TPC */ + 
11652 #ifdef TFU_TDD
11653                        2 /* DAI */ + \
11654                        4 /* HARQ */ + 
11655 #else
11656                        3 /* HARQ */ +
11657 #endif
11658                        1 /* CW Swap Flag */ + \
11659                        5 /* MCS for TB1 */+ \
11660                        1 /* NDI for TB1 */+ \
11661                        2 /* RV for TB1 */ + \
11662                        5 /* MCS for TB2 */+ \
11663                        1 /* NDI for TB2 */+ \
11664                        2 /* RV for TB2 */;
11665             if (cell->numTxAntPorts == 2)
11666             {
11667                dciSize += 3;
11668             }
11669             else if (cell->numTxAntPorts == 4)
11670             {
11671                dciSize += 6;
11672             }
11673             cell->dciSize.size[TFU_DCI_FORMAT_2] = dciSize;
11674             cell->dciSize.size[TFU_DCI_FORMAT_2] += rgSchDciAmbigSizeTbl[cell->dciSize.size[TFU_DCI_FORMAT_2]];
11675          }
11676       case TFU_DCI_FORMAT_2A:
11677          {
11678             /* DCI 2A: Spec 36.212 Section 5.3.3.1.5A */
11679             dciSize = 0;
11680             if (cell->bwCfg.dlTotalBw > 10)
11681             {
11682                dciSize = 1; /* Resource Allocation bit */
11683             }
11684
11685             dciSize += (uint8_t)bits /* Resource Allocation bits */ + \
11686                          2 /* TPC */ + 
11687 #ifdef TFU_TDD
11688                          2 /* DAI */ + \
11689                          4 /* HARQ */ + 
11690 #else
11691                          3 /* HARQ */ +
11692 #endif
11693                          1 /* CW Swap Flag */ + \
11694                          5 /* MCS for TB1 */+ \
11695                          1 /* NDI for TB1 */+ \
11696                          2 /* RV for TB1 */ + \
11697                          5 /* MCS for TB2 */+ \
11698                          1 /* NDI for TB2 */+ \
11699                          2 /* RV for TB2 */;
11700             if (cell->numTxAntPorts == 4)
11701             {
11702                dciSize += 2;
11703             }
11704             cell->dciSize.size[TFU_DCI_FORMAT_2A] = dciSize;
11705             cell->dciSize.size[TFU_DCI_FORMAT_2A] += \
11706                           rgSchDciAmbigSizeTbl[cell->dciSize.size[TFU_DCI_FORMAT_2A]]; /* Spec 39.212 Table 5.3.3.1.2-1 */
11707          }
11708       case TFU_DCI_FORMAT_3:
11709          {
11710             /* DCI 3: Spec 36.212 Section 5.3.3.1.6 */
11711             cell->dciSize.size[TFU_DCI_FORMAT_3] = cell->dciSize.size[TFU_DCI_FORMAT_1A] / 2;
11712             if (cell->dciSize.size[TFU_DCI_FORMAT_3] % 2)
11713             {
11714                cell->dciSize.size[TFU_DCI_FORMAT_3]++;
11715             }
11716          }
11717       case TFU_DCI_FORMAT_3A:
11718          {
11719             /* DCI 3A: Spec 36.212 Section 5.3.3.1.7 */
11720             cell->dciSize.size[TFU_DCI_FORMAT_3A] = cell->dciSize.size[TFU_DCI_FORMAT_1A];
11721          }
11722 #ifdef EMTC_ENABLE
11723       case TFU_DCI_FORMAT_6_0A:
11724          {
11725             rgSCHEmtcGetDciFrmt60ASize(cell);
11726          }
11727          case TFU_DCI_FORMAT_6_1A:
11728          {
11729             rgSCHEmtcGetDciFrmt61ASize(cell);
11730          }
11731 #endif                  
11732       default:
11733          {
11734             /* DCI format not supported */
11735             break;
11736          }
11737    }
11738 }
11739
11740 /**
11741  * @brief Handler for the CPU OvrLd related state adjustment.
11742  *
11743  * @details
11744  *
11745  *     Function : rgSCHUtlCpuOvrLdAdjItbsCap
11746  *
11747  *     Processing Steps:
11748  *      - Record dl/ulTpts 
11749  *      - Adjust maxItbs to acheive target throughputs
11750  *
11751  *  @param[in]  RgSchCellCb *cell
11752  *  @return  Void 
11753  **/
11754 #ifdef ANSI
11755 Void rgSCHUtlCpuOvrLdAdjItbsCap
11756 (
11757  RgSchCellCb *cell
11758 )
11759 #else
11760 Void rgSCHUtlCpuOvrLdAdjItbsCap(cell)
11761  RgSchCellCb *cell
11762 #endif
11763 {
11764    uint32_t tptDelta;
11765
11766    if ((cell->cpuOvrLdCntrl.cpuOvrLdIns) & (RGR_CPU_OVRLD_DL_TPT_UP | 
11767             RGR_CPU_OVRLD_DL_TPT_DOWN))
11768    {
11769       /* Regulate DL Tpt for CPU overload */
11770       if (cell->measurements.dlTpt > cell->cpuOvrLdCntrl.tgtDlTpt)
11771       {
11772          tptDelta = cell->measurements.dlTpt - cell->cpuOvrLdCntrl.tgtDlTpt;
11773          /* Upto 0.5% drift in measured vs target tpt is ignored */
11774          if (((tptDelta*1000)/cell->cpuOvrLdCntrl.tgtDlTpt) > 5)
11775          {
11776             cell->thresholds.maxDlItbs = RGSCH_MAX((cell->thresholds.maxDlItbs-1), 1);
11777          }
11778       }
11779       else
11780       {
11781          tptDelta = cell->cpuOvrLdCntrl.tgtDlTpt - cell->measurements.dlTpt;
11782          /* Upto 0.5% drift in measured vs target tpt is ignored */
11783          if (((tptDelta*1000)/cell->cpuOvrLdCntrl.tgtDlTpt) > 5)
11784          {
11785             cell->thresholds.maxDlItbs = RGSCH_MIN((cell->thresholds.maxDlItbs+1), RG_SCH_DL_MAX_ITBS);
11786          }
11787       }
11788 #ifdef CPU_OL_DBG_PRINTS
11789       printf("\n DL CPU OL ADJ = %lu, %lu, %d\n", cell->measurements.dlTpt, cell->cpuOvrLdCntrl.tgtDlTpt, 
11790             cell->thresholds.maxDlItbs);
11791 #endif
11792    }
11793
11794    if ((cell->cpuOvrLdCntrl.cpuOvrLdIns) & (RGR_CPU_OVRLD_UL_TPT_UP | 
11795             RGR_CPU_OVRLD_UL_TPT_DOWN))
11796    {
11797       /* Regualte DL Tpt for CPU overload */
11798       if (cell->measurements.ulTpt > cell->cpuOvrLdCntrl.tgtUlTpt)
11799       {
11800          tptDelta = cell->measurements.ulTpt - cell->cpuOvrLdCntrl.tgtUlTpt;
11801          /* Upto 1% drift in measured vs target tpt is ignored */
11802          if (((tptDelta*1000)/cell->cpuOvrLdCntrl.tgtUlTpt) > 10)
11803          {
11804             cell->thresholds.maxUlItbs = RGSCH_MAX((cell->thresholds.maxUlItbs-1), 1);
11805          }
11806       }
11807       else
11808       {
11809          tptDelta = cell->cpuOvrLdCntrl.tgtUlTpt - cell->measurements.ulTpt;
11810          /* Upto 1% drift in measured vs target tpt is ignored */
11811          if (((tptDelta*1000)/cell->cpuOvrLdCntrl.tgtUlTpt) > 10)
11812          {
11813             cell->thresholds.maxUlItbs = RGSCH_MIN((cell->thresholds.maxUlItbs+1), RG_SCH_UL_MAX_ITBS);
11814          }
11815       }
11816 #ifdef CPU_OL_DBG_PRINTS
11817       printf("\n UL CPU OL ADJ = %lu, %lu, %d\n", cell->measurements.ulTpt, cell->cpuOvrLdCntrl.tgtUlTpt, 
11818             cell->thresholds.maxUlItbs);
11819 #endif
11820    }
11821
11822    return;
11823 }
11824 /**
11825  * @brief Handler for the num UE per TTI based CPU OvrLd instr updating
11826  *
11827  * @details
11828  *
11829  *     Function : rgSCHUtlChkAndUpdNumUePerTtiCpuOvInstr
11830  *
11831  *     Processing Steps:
11832  *      - Validate the config params.
11833  *      - Update numUEperTTi CPU OL related information.
11834  *      - If successful, return ROK else RFAILED.
11835  *
11836  *  @param[in]  RgSchCellCb *cell
11837  *  @param[in]  uint8_t          cnrtCpuOvrLdIns 
11838  *  @return     Void
11839  **/
11840 #ifdef ANSI
11841 static Void rgSCHUtlChkAndUpdNumUePerTtiCpuOvInstr
11842 (
11843  RgSchCellCb *cell, 
11844  uint8_t      crntCpuOvrLdIns
11845 )
11846 #else
11847 static S16 rgSCHUtlChkAndUpdNumUePerTtiCpuOvInstr(cell, crntCpuOvrLdIns)
11848  RgSchCellCb *cell; 
11849  uint8_t     crntCpuOvrLdIns;
11850 #endif
11851 {
11852    RgSchCpuOvrLdCntrlCb    *cpuInstr = &(cell->cpuOvrLdCntrl);
11853    RgSchCmnCell            *cellSch;
11854    uint8_t                 maxUeNewDlTxPerTti;
11855    uint8_t                 maxUeNewUlTxPerTti;
11856    uint8_t                 tmpslot        = 0;
11857 #ifdef CPU_OL_DBG_PRINTS 
11858    uint8_t                 idx = 0;
11859 #endif
11860    uint8_t                 maxDlDecCnt;
11861    uint8_t                 maxUlDecCnt;
11862
11863    cellSch = RG_SCH_CMN_GET_CELL(cell);
11864
11865    maxUeNewDlTxPerTti = cellSch->dl.maxUeNewTxPerTti; 
11866    maxUeNewUlTxPerTti = cellSch->ul.maxUeNewTxPerTti;
11867   
11868    /* Calculate Maximum Decremen */
11869    maxDlDecCnt =  (10*(maxUeNewDlTxPerTti - 1))-(10-RGR_MAX_PERC_NUM_UE_PER_TTI_RED);
11870    maxUlDecCnt =  (10*(maxUeNewUlTxPerTti - 1))-(10-RGR_MAX_PERC_NUM_UE_PER_TTI_RED);
11871
11872    /* Check for DL CPU Commands */
11873    if ( crntCpuOvrLdIns &  RGR_CPU_OVRLD_DL_DEC_NUM_UE_PER_TTI ) 
11874    {
11875       /* Decrement till 90% of maxUeNewDlTxPerTti */
11876       if ( cpuInstr->dlNxtIndxDecNumUeTti < maxDlDecCnt )
11877       {
11878          tmpslot = (cpuInstr->dlNxtIndxDecNumUeTti) % 10;
11879          cpuInstr->dlNxtIndxDecNumUeTti++;
11880          if ( cpuInstr->maxUeNewTxPerTti[tmpslot] > 1 )
11881          {
11882             cpuInstr->maxUeNewTxPerTti[tmpslot]--;
11883          }
11884          else
11885          {
11886 #ifdef CPU_OL_DBG_PRINTS
11887             printf("CPU_OL_TTI__ERROR\n");
11888 #endif
11889             RLOG_ARG0(L_ERROR,DBG_CELLID,cell->cellId,"Invalid CPU OL");
11890          }
11891       }
11892 #ifdef CPU_OL_DBG_PRINTS
11893       printf("dlNxtIndxDecNumUeTti = %d\n", cpuInstr->dlNxtIndxDecNumUeTti);
11894 #endif
11895       RLOG_ARG1(L_DEBUG,DBG_CELLID,cell->cellId,"dlNxtIndxDecNumUeTti = %d",
11896          cpuInstr->dlNxtIndxDecNumUeTti);
11897    }
11898    else if ( crntCpuOvrLdIns &  RGR_CPU_OVRLD_DL_INC_NUM_UE_PER_TTI )
11899    {
11900       if ( cpuInstr->dlNxtIndxDecNumUeTti >  0) 
11901       {
11902          cpuInstr->dlNxtIndxDecNumUeTti--;
11903          tmpslot = (cpuInstr->dlNxtIndxDecNumUeTti) % 10;
11904          if ( cpuInstr->maxUeNewTxPerTti[tmpslot] < maxUeNewDlTxPerTti )
11905          {
11906             cpuInstr->maxUeNewTxPerTti[tmpslot]++;
11907          }
11908          else
11909          {
11910 #ifdef CPU_OL_DBG_PRINTS
11911             printf("CPU_OL_TTI__ERROR\n");
11912 #endif
11913             RLOG_ARG0(L_ERROR,DBG_CELLID,cell->cellId,"Invalid CPU OL");
11914          }
11915       }
11916 #ifdef CPU_OL_DBG_PRINTS
11917       printf("dlNxtIndxDecNumUeTti = %d\n", cpuInstr->dlNxtIndxDecNumUeTti);
11918 #endif
11919       RLOG_ARG1(L_DEBUG,DBG_CELLID,cell->cellId,"dlNxtIndxDecNumUeTti = %d",
11920          cpuInstr->dlNxtIndxDecNumUeTti);
11921    }
11922    /* Check for UL CPU commands */
11923    if ( crntCpuOvrLdIns &  RGR_CPU_OVRLD_UL_DEC_NUM_UE_PER_TTI )
11924    {
11925       /* Decrement till 90% of maxUeNewDlTxPerTti */
11926       if ( cpuInstr->ulNxtIndxDecNumUeTti < maxUlDecCnt )
11927       {
11928          tmpslot = (cpuInstr->ulNxtIndxDecNumUeTti) % 10;
11929          cpuInstr->ulNxtIndxDecNumUeTti++;
11930          if ( cpuInstr->maxUeNewRxPerTti[tmpslot] > 1 )
11931          {
11932             cpuInstr->maxUeNewRxPerTti[tmpslot]--;
11933          }
11934          else
11935          {
11936 #ifdef CPU_OL_DBG_PRINTS
11937             printf("CPU_OL_TTI__ERROR\n");
11938 #endif
11939             RLOG_ARG0(L_ERROR,DBG_CELLID,cell->cellId,"Invalid CPU OL");
11940          }
11941       }
11942 #ifdef CPU_OL_DBG_PRINTS
11943       printf("ulNxtIndxDecNumUeTti = %d\n", cpuInstr->ulNxtIndxDecNumUeTti);
11944 #endif
11945       RLOG_ARG1(L_DEBUG,DBG_CELLID,cell->cellId,"dlNxtIndxDecNumUeTti = %d",
11946          cpuInstr->dlNxtIndxDecNumUeTti);
11947    }
11948    else if ( crntCpuOvrLdIns &  RGR_CPU_OVRLD_UL_INC_NUM_UE_PER_TTI )
11949    {
11950       if ( cpuInstr->ulNxtIndxDecNumUeTti >  0) 
11951       {
11952          cpuInstr->ulNxtIndxDecNumUeTti--;
11953          tmpslot = (cpuInstr->ulNxtIndxDecNumUeTti) % 10;
11954          if ( cpuInstr->maxUeNewRxPerTti[tmpslot] < maxUeNewUlTxPerTti )
11955          {
11956             cpuInstr->maxUeNewRxPerTti[tmpslot]++;
11957          }
11958          else
11959          {
11960 #ifdef CPU_OL_DBG_PRINTS
11961             printf("CPU_OL_TTI__ERROR\n");
11962 #endif
11963             RLOG_ARG0(L_ERROR,DBG_CELLID,cell->cellId,"Invalid CPU OL");
11964          }
11965       }
11966 #ifdef CPU_OL_DBG_PRINTS
11967       printf("ulNxtIndxDecNumUeTti = %d\n", cpuInstr->ulNxtIndxDecNumUeTti);
11968 #endif
11969       RLOG_ARG1(L_DEBUG,DBG_CELLID,cell->cellId,"dlNxtIndxDecNumUeTti = %d",
11970          cpuInstr->dlNxtIndxDecNumUeTti);
11971    }
11972 #ifdef CPU_OL_DBG_PRINTS 
11973  /* TODO: Debug Information - Shall be moved under CPU_OL_DBG_PRINTS */
11974    printf("maxUeNewDlTxPerTti = %d, maxUeNewUlTxPerTti = %d\n", maxUeNewDlTxPerTti, maxUeNewUlTxPerTti);
11975    printf("DL Sf numUePerTti:");
11976    for ( idx = 0; idx < 10 ; idx ++ )
11977    {
11978       printf("  %d", cpuInstr->maxUeNewTxPerTti[idx]);  
11979    }
11980    printf("\nUL Sf numUePerTti:");
11981    for ( idx = 0; idx < 10 ; idx ++ )
11982    {
11983       printf("  %d", cpuInstr->maxUeNewRxPerTti[idx]);  
11984    }
11985    printf("\n");
11986 #endif
11987
11988    return;
11989 } /* rgSCHUtlChkAndUpdNumUePerTtiCpuOvInstr */
11990
11991 /**
11992  * @brief Handler for the CPU OvrLd related cell Recfg.
11993  *
11994  * @details
11995  *
11996  *     Function : rgSCHUtlResetCpuOvrLdState
11997  *
11998  *     Processing Steps:
11999  *      - Validate the config params.
12000  *      - Update CPU OL related state information.
12001  *      - If successful, return ROK else RFAILED.
12002  *
12003  *  @param[in]  RgSchCellCb *cell
12004  *  @param[in]  uint8_t          cnrtCpuOvrLdIns 
12005  *  @return  S16
12006  *      -# ROK
12007  *      -# RFAILED
12008  **/
12009 #ifdef ANSI
12010 S16 rgSCHUtlResetCpuOvrLdState
12011 (
12012  RgSchCellCb *cell, 
12013  uint8_t     crntCpuOvrLdIns
12014 )
12015 #else
12016 S16 rgSCHUtlResetCpuOvrLdState(cell, crntCpuOvrLdIns)
12017  RgSchCellCb *cell; 
12018  uint8_t     crntCpuOvrLdIns;
12019 #endif
12020 {
12021    uint8_t         crntDlCpuOL=0;
12022    uint8_t         crntUlCpuOL=0;
12023    RgSchCmnCell    *schCmnCell = (RgSchCmnCell *)(cell->sc.sch);
12024    uint8_t idx;
12025
12026 #ifdef CPU_OL_DBG_PRINTS
12027    printf("\n CPU OVR LD Ins Rcvd = %d\n", (int)crntCpuOvrLdIns);
12028 #endif
12029    RLOG_ARG0(L_INFO,DBG_CELLID,cell->cellId,"CPU OVR LD Ins Rcvd");
12030
12031    if ( RGR_CPU_OVRLD_RESET == crntCpuOvrLdIns )
12032    {
12033       /* The CPU OL instruction received with RESET (0), hence reset it */
12034 #ifdef CPU_OL_DBG_PRINTS
12035       printf("rgSCHUtlResetCpuOvrLdState: RESET CPU OL instr\n");
12036 #endif
12037       RLOG_ARG0(L_INFO,DBG_CELLID,cell->cellId,"RESET CPU OVR LD");
12038       cell->cpuOvrLdCntrl.cpuOvrLdIns = 0;
12039       /* Reset the max UL and DL itbs to 26 */
12040       cell->thresholds.maxUlItbs = RG_SCH_UL_MAX_ITBS;
12041       cell->thresholds.maxDlItbs = RG_SCH_DL_MAX_ITBS;
12042       /* Reset the num UE per TTI intructions */
12043       cell->cpuOvrLdCntrl.dlNxtIndxDecNumUeTti = 0;
12044       cell->cpuOvrLdCntrl.ulNxtIndxDecNumUeTti = 0;
12045       for ( idx = 0; idx < 10; idx++ )
12046       {
12047          cell->cpuOvrLdCntrl.maxUeNewTxPerTti[idx] = 
12048             schCmnCell->dl.maxUeNewTxPerTti;
12049          cell->cpuOvrLdCntrl.maxUeNewRxPerTti[idx] = 
12050             schCmnCell->ul.maxUeNewTxPerTti;
12051       }
12052
12053       return ROK;
12054    }
12055    /* Check and Update numUEPer TTI based CPU overload instruction before
12056     * going for TP based CPU OL  
12057     * TTI based intrcuctions shall be > 0xF */
12058    if ( crntCpuOvrLdIns >  0xF )  
12059    {
12060       rgSCHUtlChkAndUpdNumUePerTtiCpuOvInstr(cell, crntCpuOvrLdIns);
12061       /* If need to have both TP and numUePerTti instrcution together in
12062        * one command then dont return from here */
12063       return ROK;
12064    }
12065
12066    crntDlCpuOL = (crntCpuOvrLdIns & RGR_CPU_OVRLD_DL_TPT_UP) +\
12067                  (crntCpuOvrLdIns & RGR_CPU_OVRLD_DL_TPT_DOWN);
12068    if ((crntDlCpuOL) && (crntDlCpuOL != RGR_CPU_OVRLD_DL_TPT_UP) && 
12069        (crntDlCpuOL != RGR_CPU_OVRLD_DL_TPT_DOWN))
12070    {
12071       /* Cfg validation failed. Invalid Command. Either UP/DOWN is allowed */
12072       return RFAILED;
12073    }
12074    crntUlCpuOL = (crntCpuOvrLdIns & RGR_CPU_OVRLD_UL_TPT_UP) +\
12075                  (crntCpuOvrLdIns & RGR_CPU_OVRLD_UL_TPT_DOWN);
12076    if ((crntUlCpuOL) && (crntUlCpuOL != RGR_CPU_OVRLD_UL_TPT_UP) && 
12077        (crntUlCpuOL != RGR_CPU_OVRLD_UL_TPT_DOWN))
12078    {
12079       /* Cfg validation failed. Invalid Command. Either UP/DOWN is allowed */
12080       return RFAILED;
12081    }
12082    if ((crntDlCpuOL == 0) && (crntUlCpuOL == 0))
12083    {
12084       /* Cfg validation failed. Invalid Command. Either UP/DOWN is allowed */
12085       return RFAILED;
12086    }
12087
12088    cell->cpuOvrLdCntrl.cpuOvrLdIns = crntCpuOvrLdIns;
12089
12090    if (crntUlCpuOL)
12091    {
12092       if (crntUlCpuOL == RGR_CPU_OVRLD_UL_TPT_DOWN)
12093       {
12094          cell->cpuOvrLdCntrl.tgtUlTpt = cell->measurements.ulTpt - \
12095             (cell->measurements.ulTpt * 3 )/100;
12096       }
12097       else
12098       {
12099          cell->cpuOvrLdCntrl.tgtUlTpt = cell->measurements.ulTpt + \
12100             (cell->measurements.ulTpt * 2 )/100;
12101       }
12102       RLOG_ARG3(L_DEBUG,DBG_CELLID,cell->cellId,"CPU OVR LD UL Reset to "
12103             "%d, %lu, %lu", (int)crntUlCpuOL, cell->cpuOvrLdCntrl.tgtUlTpt,cell->measurements.ulTpt);
12104 #ifdef CPU_OL_DBG_PRINTS
12105       printf("\n CPU OVR LD UL Reset to= %d, %lu, %lu\n", (int)crntUlCpuOL, cell->cpuOvrLdCntrl.tgtUlTpt,
12106                               cell->measurements.ulTpt);
12107 #endif
12108    }
12109
12110    if (crntDlCpuOL)
12111    {
12112       if (crntDlCpuOL == RGR_CPU_OVRLD_DL_TPT_DOWN)
12113       {
12114          cell->cpuOvrLdCntrl.tgtDlTpt = cell->measurements.dlTpt - \
12115                                         (cell->measurements.dlTpt * 1 )/100;
12116       }
12117       else
12118       {
12119          cell->cpuOvrLdCntrl.tgtDlTpt = cell->measurements.dlTpt + \
12120             (cell->measurements.dlTpt * 1 )/100;
12121       }
12122       RLOG_ARG3(L_DEBUG,DBG_CELLID,cell->cellId,"CPU OVR LD DL Reset to "
12123             "%d, %lu, %lu", (int)crntDlCpuOL, cell->cpuOvrLdCntrl.tgtDlTpt,cell->measurements.dlTpt);
12124
12125 #ifdef CPU_OL_DBG_PRINTS
12126       printf("\n CPU OVR LD DL Reset to= %d, %lu, %lu\n", (int)crntDlCpuOL, cell->cpuOvrLdCntrl.tgtDlTpt,
12127                               cell->measurements.dlTpt);
12128 #endif
12129    }
12130    rgSCHUtlCpuOvrLdAdjItbsCap(cell);
12131    return ROK;
12132 }
12133 #ifdef EMTC_ENABLE
12134 S16 rgSCHUtlAddToResLst
12135 (
12136  CmLListCp   *cp,  
12137  RgSchIotRes *iotRes
12138  )
12139 {
12140    cmLListAdd2Tail(cp, &iotRes->resLnk);
12141    iotRes->resLnk.node = (PTR)iotRes;
12142    return ROK;
12143 }
12144 S16 rgSCHUtlDelFrmResLst
12145 (
12146 RgSchUeCb *ue,
12147 RgSchIotRes *iotRes
12148 )
12149 {
12150    CmLListCp  *cp = NULLP;
12151    RgSchEmtcUeInfo *emtcUe = NULLP;
12152    emtcUe = RG_GET_EMTC_UE_CB(ue);
12153    if(iotRes->resType == RG_SCH_EMTC_PUCCH_RES)
12154    {
12155       cp = &emtcUe->ulResLst;
12156    }else if(iotRes->resType == RG_SCH_EMTC_PDSCH_RES)
12157    {
12158       cp = &emtcUe->dlResLst;
12159    }else
12160    {
12161       RLOG0(L_INFO, "*****restype mismatch");
12162    }
12163    if(cp != NULLP )
12164    { 
12165       if(cp->count == 0)
12166       {
12167          RLOG0(L_INFO,"****error count*****\n");
12168          return ROK;
12169       }
12170    }
12171    cmLListDelFrm(cp, &iotRes->resLnk);
12172    iotRes->resLnk.node = NULLP;
12173    return ROK;
12174 }
12175 #endif
12176 /**********************************************************************
12177
12178          End of file
12179 **********************************************************************/