Merge "Added a new Flag ODU_LWR_MAC_DEBUG in the code"
[o-du/l2.git] / src / 5gnrsch / rg_sch_ram.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_ram.c
28   
29 **********************************************************************/
30
31 /** @file rg_sch_ram.c
32 @brief This file has APIs to handle the random access procedure functionality for the scheduler.
33 */
34
35 static const char* RLOG_MODULE_NAME="MAC";
36 static int RLOG_MODULE_ID=4096;
37 static int RLOG_FILE_ID=171;
38
39 /* header include files (.h) */
40 #include "common_def.h"
41
42 #include "rg_env.h"        /* MAC Environment Defines */
43 #include "rgr.h"           /* RGR Interface defines */
44 #include "rgm.h"           /* RGR Interface defines */
45 #include "tfu.h"           /* TFU Interface defines */
46 #include "lrg.h"           /* LRG Interface defines */
47 #include "rg_env.h"    /* Scheduler error defines */
48 #include "rg_sch_inf.h"        /* Scheduler defines */
49 #include "rg_sch_err.h"    /* Scheduler error defines */
50 #include "rg_sch.h"        /* Scheduler defines */
51 #include "rg_sch_cmn.h"
52 #include "rl_interface.h"
53 #include "rl_common.h"
54
55 /* header/extern include files (.x) */
56
57 #include "rgr.x"           /* RGR Interface includes */
58 #include "rgm.x"           /* RGR Interface includes */
59 #include "tfu.x"           /* TFU Interface includes */
60 #include "lrg.x"           /* LRG Interface includes */
61
62 #include "rg_sch_inf.x"         /* typedefs for Scheduler */
63 #include "rg_sch.x"        /* Scheduler includes */
64 #include "rg_sch_cmn.x"
65 #ifdef EMTC_ENABLE
66 EXTERN Bool rgSCHRamVldtRgrEmtcUeCfg  ARGS((
67 RgSchCellCb  *cell,
68 RgrUeCfg     *ueCfg
69 ));
70
71 EXTERN S16 rgSCHRamRmvAllFrmEmtcRaInfoSchdLst
72 (
73 RgSchCellCb       *cell
74 );
75 EXTERN Void rgSCHEmtcUtlUpdCmnNb 
76 (
77 RgSchRaCb      *raCb
78 );
79 EXTERN Void rgSCHEmtcHqPAlloc 
80 (
81 RgSchCellCb       *cell,
82 RgSchDlHqEnt      *hqEnt
83 );
84 #endif
85 /* local defines */
86 /* local typedefs */
87 PRIVATE Void rgSCHRamUlFreeAllocation ARGS((RgSchUlSf *sf,RgSchUlAlloc *alloc, 
88          RgSchCellCb     *cell,Bool isEmtc));
89
90 PRIVATE S16 rgSCHRamContResCrnti   ARGS((RgSchCellCb *cell, RgSchUeCb *ue, 
91                                       RgSchRaCb *raCb, RgSchErrInfo *err));
92 PRIVATE S16 rgSCHRamContResCcchsdu ARGS((RgSchCellCb *cell, RgSchRaCb *raCb));
93 #ifdef EMTC_ENABLE
94
95 EXTERN S16 rgSCHEmtcRamContResCcchsdu ARGS((RgSchCellCb *cell, RgSchRaCb *raCb));
96 EXTERN S16 rgSCHRamEmtcContResCcchsdu ARGS((RgSchCellCb *cell, RgSchRaCb *raCb));
97 EXTERN Void rgSCHChkEmtcContResGrdTmrExp ARGS((RgSchCellCb        *cell));
98 EXTERN Void rgSCHChkEmtcContResTmrExp ARGS((RgSchCellCb        *cell));
99 EXTERN Void rgSCHEmtcRaInfoFree ARGS((RgSchCellCb *cell, RgSchRaCb *raCb));
100 #endif
101 #ifdef RGR_V1
102 PRIVATE Void rgSCHChkContResGrdTmrExp ARGS((RgSchCellCb        *cell));
103 PRIVATE Void rgSCHChkContResTmrExp ARGS((RgSchCellCb        *cell));
104 PRIVATE Void rgSCHRamProcContResExp ARGS((RgSchCellCb *cell, 
105                                  RgSchRaCb  *raCb));
106 PRIVATE Void rgSCHRamProcContResGrdExp ARGS((RgSchCellCb *cell,
107                                       RgSchRaCb  *raCb));
108 #ifdef EMTC_ENABLE
109 EXTERN Void rgSCHChkEmtcContResGrdTmrExp ARGS((RgSchCellCb        *cell));
110 EXTERN Void rgSCHChkEmtcContResTmrExp ARGS((RgSchCellCb        *cell));
111 #endif
112 #endif
113 /* forward references */
114
115 /**
116  * @brief Check configured preamble id not colliding with non dedicated or PDCCH
117  * order preamble sets. When valid preamble id given check that C-RNTI given
118  * in configuration is not amongst the C-RNTI'smanaged by scheduler
119  *
120  * @details
121  *
122  *     Function : rgSCHRamVldtUeCfg 
123  *
124  *     Processing Steps: Check configured preamble id not colliding with non dedicated or PDCCH
125  *       order preamble sets. When valid preamble id given check that C-RNTI given
126  *       in configuration is not amongst the C-RNTI'smanaged by scheduler
127  *
128  *  @param[in]  RgSchCellCb  *cell
129  *  @param[in]  RgrUeCfg     *ueCfg
130  *  @return  S16
131  *      -# ROK
132  *      -# RFAILED
133  **/
134 #ifdef ANSI
135 S16 rgSCHRamVldtUeCfg 
136 (
137 RgSchCellCb  *cell,
138 RgrUeCfg     *ueCfg
139 )
140 #else
141 S16 rgSCHRamVldtUeCfg(cell, ueCfg)
142 RgSchCellCb  *cell;
143 RgrUeCfg     *ueCfg;
144 #endif
145 {
146    if (ueCfg->dedPreambleId.pres == PRSNT_NODEF)
147    {
148       if ((ueCfg->dedPreambleId.val < cell->rachCfg.numRaPreamble) ||
149           (ueCfg->dedPreambleId.val >= RGSCH_MAX_NUM_RA_PREAMBLE) ||
150           ((ueCfg->dedPreambleId.val >= cell->macPreambleSet.start) && 
151            (ueCfg->dedPreambleId.val <= cell->macPreambleSet.start +
152                                        cell->macPreambleSet.size - 1)) ||
153           ((ueCfg->crnti >= cell->rntiDb.rntiStart) && 
154            (ueCfg->crnti < cell->rntiDb.rntiStart + cell->rntiDb.maxRntis-1))
155 #ifdef EMTC_ENABLE
156           || (rgSCHRamVldtRgrEmtcUeCfg(cell,ueCfg))
157 #endif          
158           )
159       {
160          return RFAILED;
161       }
162    }
163    return ROK;
164 }
165
166 /**
167  * @brief Handler for Random Access Request
168  *
169  * @details
170  *
171  *     Function : rgSCHRamProcRaReq
172  *     
173  *     -# Create a node for each TfuRaReqInfo element received
174  *     -# Initialize the list with the above elements at the raRnti index 
175  *        in the cell. 
176  *     
177  *           
178  *  @param[in]  RgSchCellCb       *cell
179  *  @param[in]  CmLteRnti      raRnti
180  *  @param[in]  RgTfuRaReqInd *raReqInd
181  *  @param[out] RgSchErrInfo      *err
182  *  @return  S16
183  *      -# ROK 
184  *      -# RFAILED 
185  **/
186 #ifdef ANSI
187 S16 rgSCHRamProcRaReq
188 (
189 U8                raReqCnt,
190 RgSchCellCb       *cell,
191 CmLteRnti         raRnti,
192 TfuRachInfo       *raReqInd,
193 CmLteTimingInfo   timingInfo,
194 RgSchUeCb         *ue,
195 RgSchErrInfo      *err
196 )
197 #else
198 S16 rgSCHRamProcRaReq(raReqCnt, cell, raRnti, raReqInd, timingInfo, ue, err)
199 U8                raReqCnt;
200 RgSchCellCb       *cell;
201 CmLteRnti         raRnti;
202 TfuRachInfo       *raReqInd;
203 CmLteTimingInfo   timingInfo;
204 RgSchUeCb         *ue;
205 RgSchErrInfo      *err;
206 #endif
207 {
208    RgSchRaReqInfo *raReqInfo;
209    U16            raIndex;
210 #ifdef LTE_TDD
211    U8             fid;
212    U8             tid;
213 #endif
214
215
216
217       /* SR_RACH_STATS : RACH REQ */
218       rgNumPrachRecvd += raReqInd->numRaReqInfo;
219
220    /* ccpu00132523- Moved out this from for loop as updating of raIndex is 
221     * relates to only raRnti and all preambles having same raRnti*/
222 #ifdef LTE_TDD
223    /* UL subframes do not occupy all the subframes in a radio frame.
224     * So RA Rnti index to be calculated based on actual UL subframe index. */
225    /* Get the actual subframe number */
226    tid = (raRnti-1)%RGSCH_NUM_SUB_FRAMES;
227    /* Get the frequency index in the subframe */
228    fid = ((raRnti-1) / RGSCH_NUM_SUB_FRAMES)* RGSCH_NUM_SUB_FRAMES;
229    /* Get the index of RA RNTI in the array */
230    raIndex = ((timingInfo.sfn % cell->raInfo.maxRaSize) \
231                * RGSCH_MAX_RA_RNTI_PER_SUBFRM * RGSCH_NUM_SUB_FRAMES) + \
232                tid + fid;
233    /* Fixes for RACH handling in TDD: Removed deletion of queued RaReq */
234 #else
235    /* ccpu00132523- Placing the raReq into array based on RA SFN */
236    raIndex = (timingInfo.sfn & 1) * RGSCH_MAX_RA_RNTI + raRnti-1;
237 #endif
238
239    /* allocate new raReqInfos and enqueue them */
240    if (raReqInd->raReqInfoArr[raReqCnt].rapId >= RGSCH_MAX_NUM_RA_PREAMBLE)
241    {
242       RLOG_ARG1(L_ERROR,DBG_CELLID,cell->cellId,
243                "RARNTI:%d rgSCHTomRaReqInd(): RAM processing failed errType(%d) ",
244                raReqInd->raRnti);
245       return RFAILED;
246    }
247
248    /* SR_RACH_STATS : DED PREAMB*/
249    if (RGSCH_IS_DEDPRM(cell, raReqInd->raReqInfoArr[raReqCnt].rapId))
250    {
251       rgNumDedPream++;
252    }
253
254
255 #ifdef LTE_L2_MEAS
256    if (raReqInd->raReqInfoArr[raReqCnt].rapId < cell->rachCfg.sizeRaPreambleGrpA)
257    {
258       cell->raPrmbs.preamGrpA++;
259    }
260    else if (RGSCH_IS_DEDPRM(cell, raReqInd->raReqInfoArr[raReqCnt].rapId))
261    {
262       cell->raPrmbs.dedPream++;
263    }
264    else
265    {
266       cell->raPrmbs.preamGrpB++;
267    }
268 #endif
269
270    if((rgSCHUtlAllocSBuf(cell->instIdx, (Data **)(&raReqInfo), 
271                sizeof(RgSchRaReqInfo))) == RFAILED)
272    {
273       RLOG_ARG1(L_ERROR,DBG_CELLID,cell->cellId,"rgSCHRamProcRaReq(): Allocation"
274             " of RaReq failed RARNTI:%d",raRnti);
275       err->errCause = RGSCHERR_RAM_MEM_EXHAUST;
276       return RFAILED;
277    }
278
279    /* Insert the given raReqInfo */
280    /* RACHO */
281    raReqInfo->timingInfo = timingInfo;
282    raReqInfo->raReq = raReqInd->raReqInfoArr[raReqCnt]; 
283    raReqInfo->raReqLstEnt.next = NULLP;
284    raReqInfo->raReqLstEnt.prev = NULLP;
285    raReqInfo->raReqLstEnt.node = (PTR)raReqInfo;
286    /* ccpu00133504 */
287    raReqInfo->ue = ue;
288
289 #ifndef LTE_TDD
290    RGSCH_ARRAY_BOUND_CHECK(cell->instIdx, cell->raInfo.raReqLst, raIndex);
291 #endif
292    /* RACHO: If dedicated preamble, then give preference by appending at front */
293    if (RGSCH_IS_DEDPRM(cell, raReqInd->raReqInfoArr[raReqCnt].rapId))
294    {
295       cmLListFirst(&cell->raInfo.raReqLst[raIndex]);
296       cmLListInsCrnt(&cell->raInfo.raReqLst[raIndex], &raReqInfo->raReqLstEnt);
297    }
298    else
299    {
300       cmLListAdd2Tail(&cell->raInfo.raReqLst[raIndex], &raReqInfo->raReqLstEnt);
301    }
302
303    return ROK;
304 }  /* rgSCHRamProcRaReq */
305
306 /**
307  * @brief Handler for Random Access control block creation
308  *
309  * @details
310  *
311  *     Function : rgSCHRamCreateRaCb
312  *                Creates a raCb and gives the same to scheduler for its updation
313  *     
314  *
315  *  @param[in]       RgSchCellCb       *cell 
316  *  @param[in, out]  RgSchRaCb         **raCb 
317  *  @param[out]      RgSchErrInfo         *err
318  *  @return  S16
319  *      -# ROK 
320  *      -# RFAILED 
321  **/
322 #ifdef ANSI
323 S16 rgSCHRamCreateRaCb
324 (
325 RgSchCellCb       *cell,
326 RgSchRaCb         **raCb,
327 RgSchErrInfo      *err
328 )
329 #else
330 S16 rgSCHRamCreateRaCb(cell, raCb, err)
331 RgSchCellCb       *cell;
332 RgSchRaCb         **raCb;
333 RgSchErrInfo      *err;
334 #endif
335 {
336    RgSchRntiLnk *rntiLnk;
337    Inst         inst = cell->instIdx;
338
339
340    if((rgSCHUtlAllocSBuf(inst, (Data **)(raCb),
341                       sizeof(RgSchRaCb))) == RFAILED)
342    {
343       RLOG_ARG0(L_ERROR,DBG_CELLID,cell->cellId,"rgSCHRamCreateRaCb(): Allocation of "
344          "RaCb failed");
345       err->errCause = RGSCHERR_RAM_MEM_EXHAUST;
346       return RFAILED;
347    }
348
349    rntiLnk = rgSCHDbmGetRnti(cell);
350    if(rntiLnk != NULLP)
351    {
352       (*raCb)->rntiLnk = rntiLnk;
353       (*raCb)->tmpCrnti = rntiLnk->rnti;
354    }
355    else
356    {
357
358       /* SR_RACH_STATS: RNTI POOL Exhaution */
359       rgNumRarFailDuetoRntiExhaustion++;
360
361       /* No rnti available! */
362       RLOG_ARG0(L_ERROR,DBG_CELLID,cell->cellId,"rgSCHRamCreateRaCb(): Allocation of "
363          "temporary RNTI failed at MAC(CRNTI exhausted)");
364       /* ccpu00117052 - MOD - Passing double pointer
365       for proper NULLP assignment*/
366       rgSCHUtlFreeSBuf(inst, (Data **)(raCb), sizeof(RgSchRaCb));
367       err->errCause = RGSCHERR_RAM_RNTI_EXHAUST;
368       return RFAILED;
369    }
370
371    /* Allocate and initialize the DL HARQ portion of the RACB */
372    (*raCb)->dlHqE = rgSCHDhmHqEntInit(cell);
373    if ((*raCb)->dlHqE == NULLP)
374    {
375       /* No memory available! */
376       RLOG_ARG0(L_ERROR,DBG_CELLID,cell->cellId,"rgSCHRamCreateRaCb(): Creation of"
377          " DL HARQ failed");
378           /* ccpu00117052 - MOD - Passing double pointer
379       for proper NULLP assignment*/
380       rgSCHUtlFreeSBuf(inst, (Data **)(raCb), sizeof(RgSchRaCb));
381       err->errCause = RGSCHERR_RAM_MEM_EXHAUST;
382       return RFAILED;
383    }
384 #ifdef EMTC_ENABLE
385    (*raCb)->isEmtcRaCb = FALSE;
386    rgSCHEmtcHqPAlloc(cell, (*raCb)->dlHqE);
387 #endif
388    (*raCb)->dlHqE->raCb = (*raCb);
389    /* Initialize RaCb's contents */
390    (*raCb)->timingInfo = cell->crntTime;
391    (*raCb)->raState = RGSCH_RA_MSG3_PENDING;
392    (*raCb)->toDel = FALSE;
393    (*raCb)->phr.pres = FALSE;
394
395    /* Insert the created raCb into raCb list of cell */
396    (*raCb)->raCbLnk.node = (PTR)(*raCb);
397    cmLListAdd2Tail(&cell->raInfo.raCbLst, &(*raCb)->raCbLnk);
398    
399    return ROK;
400 }  /* rgSCHRamCreateRaCb */
401
402 /**
403  * @brief Handler for Ue Configuration Request
404  *
405  * @details
406  *
407  *     Function : rgSCHRamRgrUeCfg
408  *     
409  *     This function handles the UE config received based on the state of the
410  *     raCb.
411  *     -# If raCb is in RGSCH_RA_MSG4_PENDING state, it shall update the harq 
412  *        information to UeCb and update the references.
413  *     -# If raCb is in RGSCH_RA_MSG4_DONE, then it shall free the raCb
414  *     
415  *           
416  *  @param[in]     RgSchCellCb    *cell
417  *  @param[in,out] RgSchUeCb      *ue 
418  *  @param[in,out] RgSchRaCb      *raCb 
419  *  @param[out]    RgSchErrInfo   *err
420  *  @return  S16
421  *      -# ROK 
422  *      -# RFAILED 
423  **/
424 #ifdef ANSI
425 S16 rgSCHRamRgrUeCfg
426 (
427 RgSchCellCb    *cell,
428 RgSchUeCb      *ue,
429 RgSchRaCb      *raCb,
430 RgSchErrInfo   *err
431 )
432 #else
433 S16 rgSCHRamRgrUeCfg(cell, ue, raCb, err)
434 RgSchCellCb    *cell;
435 RgSchUeCb      *ue;
436 RgSchRaCb      *raCb;
437 RgSchErrInfo   *err;
438 #endif
439 {
440    /* Releasing HARQ processes of old UE when ue
441     *           reconfig with new crnti */
442   /* U32 cnt; */
443    RgSchDlHqEnt          **hqEnt = &(RG_SCH_CMN_GET_UE_HQE(ue, cell));
444    RgSchCmnUlUe *ueUl = RG_SCH_CMN_GET_UL_UE(ue, cell);
445
446
447    /* Fix : set UE inactive in DL until UE is reinitialization completed */
448    ue->dl.dlInactvMask |= RG_HQENT_INACTIVE;
449    ue->ul.ulInactvMask |= RG_HQENT_INACTIVE;
450
451    if(raCb->raState ==  RGSCH_RA_MSG4_PENDING)
452    {
453       raCb->ue = ue;
454       ue->rntiLnk = raCb->rntiLnk;
455       /* Update UL Harq process information */
456       /*ccpu00128820 - MOD - Msg3 alloc double delete issue*/
457       ueUl->hqEnt.hqProcCb[raCb->msg3HqProcId].ndi = raCb->msg3HqProc.ndi;    
458    }
459    else if(raCb->raState == RGSCH_RA_MSG4_DONE)
460    {
461       ue->rntiLnk = raCb->rntiLnk;
462       /* Update UL Harq process information */
463       /*ccpu00128820 - MOD - Msg3 alloc double delete issue*/
464       ueUl->hqEnt.hqProcCb[raCb->msg3HqProcId].ndi = raCb->msg3HqProc.ndi;      
465       /* Fix : syed Assign hqEnt to UE only if msg4 is done */
466       rgSCHDhmAssgnUeHqEntFrmRaCb(ue, raCb);
467    }
468    else
469    {
470       err->errCause = RGSCHERR_RAM_NO_MSG3_RCVD;
471       *hqEnt = NULLP;
472       raCb->dlHqE->ue = NULLP;
473       return RFAILED;
474    }
475
476    return ROK;
477 }  /* rgSCHRamRgrUeCfg */
478
479
480 /**
481  * @brief Handler for C-RNTI based contention resolution
482  *
483  * @details
484  *
485  *     Function : rgSCHRamContResCrnti
486  *     
487  *     This function shall be invoked once Msg3 indicates C-RNTI based
488  *     contention resolution.This shall indicate the scheduler regarding
489  *     C-RNTI based uplink grant.
490  *     
491  *           
492  *  @param[in,out] RgSchCellCb *cell 
493  *  @param[in,out] RgSchUeCb   *ue 
494  *  @param[in,out] RgSchRaCb   *raCb 
495  *  @return  S16
496  *      -# ROK 
497  **/
498 #ifdef ANSI
499 PRIVATE S16 rgSCHRamContResCrnti
500 (
501 RgSchCellCb  *cell,
502 RgSchUeCb    *ue,
503 RgSchRaCb    *raCb,
504 RgSchErrInfo *err
505 )
506 #else
507 PRIVATE S16 rgSCHRamContResCrnti(cell, ue, raCb, err)
508 RgSchCellCb  *cell;
509 RgSchUeCb    *ue;
510 RgSchRaCb    *raCb;
511 RgSchErrInfo *err;
512 #endif
513 {
514    TfuUlCqiRpt   ulCqiRpt;
515    RgSchCmnCell  *cellSch= (RgSchCmnCell *)(cell->sc.sch);
516
517
518    /* Fix: syed It is incorrect to copy over msg3HqProc to ueCb's 
519     * UL harq proc. In case of Crnti based RACH, ueCb has valid context which
520     * cannot be over written. It was leading to a crash. */ 
521
522    rgSCHUtlRecMsg3Alloc(cell, ue, raCb);
523
524    /* Fix for ccpu00123908: Reset the UL CQI to the cell default value here */
525    ulCqiRpt.isTxPort0 = TRUE;
526    ulCqiRpt.numSubband = 0;
527    /* Fix : syed HO UE does not have a valid ue->rntiLnk */        
528    ulCqiRpt.rnti = ue->ueId;
529    /* rg002.301:[ccpu00124018]-MOD- Avoiding hard coding of CQI and retriving from cell config*/
530    ulCqiRpt.wideCqi = cellSch->ul.dfltUlCqi;
531    rgSCHUtlUlCqiInd(cell, ue, &ulCqiRpt);
532
533    
534    /* Invoke scheduler to indicate UL grant req for contention resolution */
535    rgSCHUtlContResUlGrant(cell, ue, err);
536
537    if (raCb->phr.pres == TRUE)
538    {
539       rgSCHUtlUpdPhr(cell, ue, raCb->phr.val, err);
540    }
541    /* No need of raCb any more */
542    rgSCHRamDelRaCb(cell, raCb, TRUE);
543
544    return ROK;
545 }  /* rgSCHRamContResCrnti */
546
547
548 /**
549  * @brief Handler for CCCH SDU based contention resolution
550  *
551  * @details
552  *
553  *     Function : rgSCHRamContResCcchsdu
554  *     
555  *     This function shall be invoked once Msg3 indicates contention resolution
556  *     based on CCCH sdu. This shall update the raCb state to 
557  *     RGSCH_RA_MSG4_PENDING.
558  *     
559  *           
560  *  @param[in,out] RgSchRaCb *raCb 
561  *  @return  S16
562  *      -# ROK 
563  **/
564 #ifdef ANSI
565 PRIVATE S16 rgSCHRamContResCcchsdu
566 (
567 RgSchCellCb *cell,
568 RgSchRaCb *raCb
569 )
570 #else
571 PRIVATE S16 rgSCHRamContResCcchsdu(cell, raCb)
572 RgSchCellCb *cell;
573 RgSchRaCb *raCb;
574 #endif
575 {
576 #ifdef RGR_V1 
577    CmLteTimingInfo expTime = {0}; 
578    RgSchCmnCell  *cellSch  = RG_SCH_CMN_GET_CELL(cell);
579 #endif
580    if(raCb->raState != RGSCH_RA_MSG3_PENDING)
581    {
582       RLOG_ARG2(L_DEBUG,DBG_CELLID,cell->cellId,
583                "RNTI:%d RaCb in wrong State %d Drop Msg 3",
584                raCb->rntiLnk->rnti, 
585                raCb->raState);
586       return ROK;
587    }
588
589    raCb->raState = RGSCH_RA_MSG4_PENDING;
590
591 #ifdef RGR_V1 
592    if(cell->rachCfg.contResTmr - cellSch->dl.msg4TxDelay > 0)
593       {
594       /* Set the contension resolution guard timer = 
595          Cont Res Timer - Max msg4 Tx Delay */
596          RG_SCH_ADD_TO_CRNT_TIME(cell->crntTime, expTime,
597             (cell->rachCfg.contResTmr - cellSch->dl.msg4TxDelay));
598       }
599       else
600       {
601       /* Schedule the CRI CE in the next Sf itself */
602          RG_SCH_ADD_TO_CRNT_TIME(cell->crntTime, expTime, 1);
603       }
604       raCb->expiryTime = expTime;
605       raCb->contResTmrLnk.node = (PTR)(raCb);
606       cmLListAdd2Tail(&(cell->contResGrdTmrLst), &(raCb->contResTmrLnk));
607 #endif
608    return ROK;
609 }  /* rgSCHRamContResCcchsdu */
610
611
612 /**
613  * @brief Handler for Msg3
614  *
615  * @details
616  *
617  *     Function : rgSCHRamProcMsg3
618  *     
619  *     This function processes the received Msg3 and identifies the type of 
620  *     contention resolution and act accordingly. 
621  *     
622  *           
623  *  @param[in,out]  RgSchCellCb     *cell
624  *  @param[in,out]  RgSchUeCb       *ue
625  *  @param[in,out] RgSchRaCb        *raCb 
626  *  @return  S16
627  *      -# ROK 
628  **/
629 #ifdef ANSI
630 S16 rgSCHRamProcMsg3
631 (
632 RgSchCellCb     *cell,
633 RgSchUeCb       *ue,
634 RgSchRaCb       *raCb,
635 RgInfUeDatInd   *pdu,
636 RgSchErrInfo    *err
637 )
638 #else
639 S16 rgSCHRamProcMsg3(cell, ue, raCb, pdu, err)
640 RgSchCellCb     *cell;
641 RgSchUeCb       *ue;
642 RgSchRaCb       *raCb;
643 RgInfUeDatInd   *pdu;
644 RgSchErrInfo    *err;
645 #endif
646 {
647
648
649    /* Update raCb with PHR if received along with Msg3 */ 
650    if (pdu->ceInfo.bitMask & RGSCH_PHR_CE_PRSNT)
651    {
652       /* PHR present */
653       raCb->phr.pres = TRUE;
654       raCb->phr.val = pdu->ceInfo.ces.phr;
655    } 
656    if (ue)
657    {
658       rgSCHRamContResCrnti(cell, ue, raCb, err);
659    }
660    else
661    {
662 #ifdef EMTC_ENABLE
663       if(TRUE == raCb->isEmtcRaCb)
664       {
665          /* starting the emtc Contention resolution timer */
666          rgSCHRamEmtcContResCcchsdu(cell,raCb);
667       }
668       else
669 #endif
670       {
671          rgSCHRamContResCcchsdu(cell, raCb);
672       }
673    } 
674
675    return ROK;
676 }  /* rgSCHRamProcMsg3 */
677
678
679 /**
680  * @brief Handler for Updating Bo received in StaRsp
681  *
682  * @details
683  *
684  *     Function : rgSCHRamUpdtBo
685  *     
686  *     This function shall be invoked by RAM once it receives staRsp on CCCH
687  *  
688  *  @param[in]     RgSchCellCb       *cell         
689  *  @param[in,out] RgSchRaCb         *raCb 
690  *  @param[in]     RgRguCmnStaRsp *staRsp
691  *  @return  S16
692  *      -# ROK 
693  **/
694 #ifdef ANSI
695 S16 rgSCHRamUpdtBo
696 (
697 RgSchCellCb       *cell,
698 RgSchRaCb         *raCb,
699 RgInfCmnBoRpt     *staRsp
700 )
701 #else
702 S16 rgSCHRamUpdtBo(cell, raCb, staRsp)
703 RgSchCellCb       *cell;
704 RgSchRaCb         *raCb;
705 RgInfCmnBoRpt     *staRsp;
706 #endif
707 {
708
709    /* Update Bo in RaCb */
710    raCb->dlCcchInfo.bo = (U32)(staRsp->bo);
711    /* SR_RACH_STATS : MSG4 WITH CCCH SDU */
712    rgNumMsg4WithCCCHSdu++;
713
714    /* add this to the "tobeSchdLst" */
715    /* MSG4 Fix  Start */   
716    rgSCHRamAddToRaInfoSchdLst(cell, raCb);
717    /* MSG4 Fix  End */      
718    
719    return ROK;
720 } /* rgSCHRamUpdtBo */
721
722 /**
723  * @brief Handler for Msg3 Feedback indication
724  *
725  * @details
726  *
727  *     Function : rgSCHRamMsg3DatInd
728  *     
729  *     This function shall be invoked by TOM once the transmission of Msg4 is
730  *     ACKed/NACKed.
731  *     This shall invoke UHM to set ACK for Msg3 reception.
732  *           
733  *  @param[in,out] RgSchRaCb *raCb 
734  *  @return  S16
735  *      -# ROK 
736  **/
737 #ifdef ANSI
738 S16 rgSCHRamMsg3DatInd
739 (
740 RgSchRaCb      *raCb
741 )
742 #else
743 S16 rgSCHRamMsg3DatInd(raCb)
744 RgSchRaCb      *raCb;
745 #endif
746 {
747
748    /* SR_RACH_STATS : MSG3 ACK*/
749    rgNumMsg3CrcPassed++;
750    /*ccpu00128820 - MOD - Msg3 alloc double delete issue*/
751    rgSCHUhmProcMsg3DatInd(&(raCb->msg3HqProc));
752
753    return ROK;
754 }  /* rgSCHRamMsg3DatInd */
755
756 /**
757  * @brief Handler for Msg3 Feedback indication
758  *
759  * @details
760  *
761  *     Function : rgSCHRamMsg3FailureInd
762  *     
763  *     This function shall be invoked by TOM once the transmission of Msg4 is
764  *     ACKed/NACKed.
765  *     This shall invoke UHM to set ACK for Msg3 reception.
766  *           
767  *  @param[in,out] RgSchRaCb *raCb 
768  *  @return  S16
769  *      -# ROK 
770  **/
771 #ifdef ANSI
772 S16 rgSCHRamMsg3FailureInd
773 (
774 RgSchRaCb      *raCb
775 )
776 #else
777 S16 rgSCHRamMsg3FailureInd(raCb)
778 RgSchRaCb      *raCb;
779 #endif
780 {
781
782    /*ccpu00128820 - MOD - Msg3 alloc double delete issue*/
783    rgSCHUhmProcMsg3Failure(&(raCb->msg3HqProc));
784
785    return ROK;
786 }  /* rgSCHRamMsg3FailureInd */
787
788 /**
789  * @brief Handler for Msg4 Feedback indication
790  *
791  * @details
792  *
793  *     Function : rgSCHRamMsg4FdbkInd
794  *     
795  *     This function shall be invoked by TOM once the transmission of Msg4 is
796  *     ACKed/NACKed.
797  *     This shall invoke UHM to set ACK for Msg3 reception.
798  *           
799  *  @param[in,out] RgSchRaCb *raCb 
800  *  @return  S16
801  *      -# ROK 
802  **/
803 #ifdef ANSI
804 S16 rgSCHRamMsg4FdbkInd
805 (
806 RgSchRaCb      *raCb
807 )
808 #else
809 S16 rgSCHRamMsg4FdbkInd(raCb)
810 RgSchRaCb      *raCb;
811 #endif
812 {
813
814    return ROK;
815 }  /* rgSCHRamMsg4FdbkInd */
816
817
818 /**
819  * @brief Handler for Msg4 state updation
820  *
821  * @details
822  *
823  *     Function : rgSCHRamMsg4Done
824  *     
825  *     This function shall be invoked by DHM once the transmission of Msg4 is
826  *     done. This shall delete the raCb if there is a valid Ue or if this is to
827  *     be deleted. If not this shall update the state of the raCb.
828  *     
829  *           
830  *  @param[in]     RgSchCellCb    *cell
831  *  @param[in,out] RgSchRaCb      *raCb 
832  *  @return  S16
833  *      -# ROK 
834  **/
835 #ifdef ANSI
836 S16 rgSCHRamMsg4Done
837 (
838 RgSchCellCb    *cell,
839 RgSchRaCb      *raCb
840 )
841 #else
842 S16 rgSCHRamMsg4Done(cell, raCb)
843 RgSchCellCb    *cell;
844 RgSchRaCb      *raCb;
845 #endif
846 {
847
848    RLOG_ARG1(L_DEBUG,DBG_CELLID,cell->cellId,
849             "rgSCHRamMsg4Done(): tmpCRNTI = %u",
850             raCb->tmpCrnti);
851
852    if(raCb->ue != NULLP) 
853    {
854       /* Fix : syed Let this funtion decide on releasing
855        * hqP than the caller of this function otherwise sometimes it 
856        * might lead to incorrec NDI setting. */    
857       rgSCHDhmRlsHqpTb(raCb->dlHqE->msg4Proc, 0, TRUE);
858       /* Fix : syed Assign hqEnt to UE only if msg4 is done */
859       rgSCHDhmAssgnUeHqEntFrmRaCb(raCb->ue, raCb);
860 #ifdef EMTC_ENABLE
861       if(TRUE == raCb->isEmtcRaCb)
862       {
863          rgSCHEmtcUtlUpdCmnNb(raCb);
864       }
865 #endif
866       /* MS_FIX :Proceed to CCCH scheduling irrespective of
867        * MSG4 result */
868       if (raCb->ue->dlCcchInfo.bo)
869       {
870 #ifdef EMTC_ENABLE
871          /*if CR-ID Ack has been received ,Add emtc Ue to cchSduUeLst*/
872          if(TRUE == raCb->isEmtcRaCb)
873          {
874             rgSCHUtlAddUeToEmtcCcchSduLst(cell, raCb->ue);
875          }
876          else
877 #endif
878          {
879             rgSCHUtlAddUeToCcchSduLst(cell, raCb->ue);
880          }
881       }
882       /* Rnti shall not be released as Ue exists with this rnti */
883       rgSCHRamDelRaCb(cell, raCb, FALSE);
884    }
885    else if(raCb->toDel == TRUE)
886    {
887 #ifdef XEON_SPECIFIC_CHANGES
888       CM_LOG_DEBUG(CM_LOG_ID_SCH, "Deleting RacB:%d\n", raCb->tmpCrnti);
889 #endif
890       /* Delete RACB and release RNTI */
891       rgSCHRamDelRaCb(cell, raCb, TRUE);
892    }
893    else
894    {
895 #ifdef XEON_SPECIFIC_CHANGES
896       CM_LOG_DEBUG(CM_LOG_ID_SCH, "Releasing Harq of RacB:%d\n", raCb->tmpCrnti);
897 #endif
898       raCb->raState = RGSCH_RA_MSG4_DONE;
899       /* Release harq process as final feedback is received for Msg4. In other
900        * cases, delRaCb will take care of releasing the harq process */
901       printf("=======Harq process released \n"); 
902       RLOG_ARG0(L_DEBUG,DBG_CELLID,cell->cellId,
903                                          "Harq process released "); 
904       rgSCHDhmRlsHqpTb(raCb->dlHqE->msg4Proc, 0, TRUE);
905    }
906
907    return ROK;
908 }  /* rgSCHRamMsg4Done */
909
910
911 /**
912  * @brief Handler for deletion
913  *
914  * @details
915  *
916  *     Function : rgSCHRamDelRaCb
917  *     
918  *     This function shall be invoked whenever a raCb needs to be deleted. 
919  *    Invoked by both RAM and downlink scheduler 
920  *           
921  *  @param[in]     RgSchCellCb *cell 
922  *  @param[in,out] RgSchRaCb   *raCb
923  *  @param[in]     Bool        rlsRnti 
924  *  @return  S16
925  *      -# ROK 
926  *      -# RFAILED 
927  **/
928 #ifdef ANSI
929 S16 rgSCHRamDelRaCb
930 (
931 RgSchCellCb *cell,
932 RgSchRaCb   *raCb,
933 Bool        rlsRnti
934 )
935 #else
936 S16 rgSCHRamDelRaCb(cell, raCb, rlsRnti)
937 RgSchCellCb *cell;
938 RgSchRaCb   *raCb;
939 Bool        rlsRnti;
940 #endif
941 {
942    Inst         inst = cell->instIdx;
943    Bool         isEmtc = FALSE;
944  
945     /* Delete from all the lists it is enqueued */
946     cmLListDelFrm(&(cell->raInfo.raCbLst),&(raCb->raCbLnk));
947 #ifdef EMTC_ENABLE
948     /*ue Type is EMTC, then Delete the toBeSchedLst and stop the Guard Timer */
949    if(TRUE == raCb->isEmtcRaCb)
950    {
951       rgSCHRamEmtcDelRaCb(cell,raCb);
952       isEmtc = TRUE;
953    }
954     else
955 #endif
956     {
957       if (raCb->schdLnk.node == (PTR)raCb)
958       {
959          rgSCHRamRmvFrmRaInfoSchdLst(cell, raCb);
960       }
961 #ifdef RGR_V1
962       else if(raCb->contResTmrLnk.node != NULLP)
963       {
964          cmLListDelFrm(&cell->contResGrdTmrLst, &(raCb->contResTmrLnk));
965          raCb->contResTmrLnk.node = NULLP;
966       }
967 #endif
968     }
969
970    if(rlsRnti == TRUE)
971    {
972       rgSCHUtlRlsRnti(cell, raCb->rntiLnk, FALSE, 0);
973    }
974
975    /* Check if msg4 Hq Proc has been released. If not, release it */
976    if (raCb->dlHqE )
977    {
978       if (raCb->dlHqE->msg4Proc != NULLP)
979       {
980          /* Fix: syed Remove the msg4Proc if it waiting in sf->tbs list for
981           * harq feedback */          
982          if ((raCb->dlHqE->msg4Proc->subFrm != NULLP) &&
983              (raCb->dlHqE->msg4Proc->hqPSfLnk.node != NULLP))
984          {
985             RLOG_ARG1(L_ERROR,DBG_CELLID,cell->cellId,"TMP CRNTI:%d RACH FAILURE!! "
986                "msg4proc  removed from SF", raCb->tmpCrnti);
987             rgSCHUtlDlHqPTbRmvFrmTx(raCb->dlHqE->msg4Proc->subFrm, 
988                                     raCb->dlHqE->msg4Proc, 0, FALSE);
989          }            
990          /* Fix: syed Remove the msg4Proc from cell
991           * msg4Retx Queue. I have used CMN scheduler function
992           * directly. Please define a new API and call this
993           * function through that. */         
994          rgSCHCmnDlMsg4ProcRmvFrmRetx(cell, raCb->dlHqE->msg4Proc);           
995          rgSCHDhmRlsHqpTb(raCb->dlHqE->msg4Proc, 0, TRUE);
996       }
997
998       /* Mark the raCb pointer in dlHqE to NULLP */
999       raCb->dlHqE->raCb = NULLP;
1000
1001       rgSCHDhmDelHqEnt(cell, &raCb->dlHqE);
1002    }
1003    /* Fix: syed Adaptive Msg3 Retx crash. Remove the harqProc
1004     * from adaptive retx List. Free the alloc if it exists. */
1005    if (raCb->msg3HqProc.reTxLnk.node)
1006    {
1007       //TODO_SID: Need to take care of retxLst
1008       //cmLListDelFrm(raCb->msg3HqProc.reTxAlloc.reTxLst, &raCb->msg3HqProc.reTxLnk); 
1009       raCb->msg3HqProc.reTxLnk.node = (PTR)NULLP;
1010    }
1011
1012    if (raCb->msg3HqProc.alloc)
1013    {
1014       /* Fix: syed During GPR, please write an API instead of direct
1015        * call to cmn scheduler function */         
1016       RgSchCmnUlCell  *cellUl = RG_SCH_CMN_GET_UL_CELL(cell);
1017       /*ccpu00130356 - MOD- To avoid segmentation problem because of double
1018        free due to recursive calling of rgSCHRamDelRaCb*/
1019       rgSCHRamUlFreeAllocation(&cellUl->ulSfArr[raCb->msg3HqProc.ulSfIdx],
1020                                                    raCb->msg3HqProc.alloc,
1021                                                    cell,isEmtc);
1022    }
1023
1024 #ifdef EMTC_ENABLE
1025    if(TRUE == raCb->isEmtcRaCb)
1026    {
1027       rgSCHEmtcRaInfoFree(cell, raCb);
1028    }
1029 #endif
1030    rgSCHUtlFreeSBuf(inst, (Data **)&raCb, sizeof(RgSchRaCb));
1031
1032    return ROK;
1033 }  /* rgSCHRamDelRaCb */
1034
1035
1036 /**
1037  * @brief  TTI Handler for RAM module
1038  *
1039  * @details
1040  *
1041  *     Function : rgSCHRamTtiHndlr
1042  *     
1043  *     This function shall be invoked upon TtiInd by TOM
1044  *     This shall
1045  *         - remove RaReqs added to the queue for a raRnti for which PHY may
1046  *           give the requests in the next subframe
1047  *         - remove raCbs which are not yet processed once the 
1048  *           counter for raCb processing expires.
1049  *     
1050  *           
1051  *  @param[in,out] RgSchCellCb  *cell
1052  *  @return  S16
1053  *      -# ROK 
1054  **/
1055 #ifdef ANSI
1056 S16 rgSCHRamTtiHndlr
1057 (
1058 RgSchCellCb  *cell
1059 )
1060 #else
1061 S16 rgSCHRamTtiHndlr(cell)
1062 RgSchCellCb  *cell;
1063 #endif
1064 {
1065    RgSchRaCb   *raCb;
1066    U16         raSfn;
1067    U16         crntSfn;
1068    U16         dist;       /* Number of frames between raCb's creation and crnt
1069                               frame */
1070    U8          idx;
1071    U32         maxCnt;
1072 #ifndef LTE_TDD
1073    U8          winGap;        
1074    U8          raIdx;
1075    RgSchRaReqInfo *raReqInfo;
1076 #else
1077    CmLteTimingInfo      frm;
1078    U8                   raIdx;
1079 #endif
1080
1081
1082    crntSfn = cell->crntTime.sfn;
1083   
1084 #ifdef RGR_V1
1085    /*Check if Contention resolution guard timer expiring in the TTI*/
1086    rgSCHChkContResGrdTmrExp(cell);
1087    /*Check if Contention resolution timer expiring in the TTI*/
1088    rgSCHChkContResTmrExp(cell);
1089 #ifdef EMTC_ENABLE
1090       /*Check if EMTC Contention resolution guard timer expiring in the TTI*/
1091       rgSCHChkEmtcContResGrdTmrExp(cell);
1092       /*Check if EMTC Contention resolution timer expiring in the TTI*/
1093       rgSCHChkEmtcContResTmrExp(cell);
1094 #endif
1095 #endif
1096 #ifndef LTE_TDD
1097
1098    /* Delete the RA requests for which RAR window expired in this subframe 
1099     * And were not considered for RAR scheduling*/
1100    winGap = (rgRaPrmblToRaFrmTbl[cell->rachCfg.preambleFormat]-1)+ 
1101       (cell->rachCfg.raWinSize -1 ) + RGSCH_RARSP_WAIT_PERIOD;   
1102  
1103    raIdx = (((crntSfn & 1) * RGSCH_MAX_RA_RNTI+ cell->crntTime.slot 
1104             + RG_SCH_CMN_DL_DELTA - winGap)+ RGSCH_RAREQ_ARRAY_SIZE ) 
1105            % RGSCH_RAREQ_ARRAY_SIZE;
1106
1107    /* Flush the already existing raReqs against the given raRnti */
1108
1109    maxCnt = cell->raInfo.raReqLst[raIdx].count;
1110    for (idx = 0; idx < maxCnt; idx++)
1111    {
1112       raReqInfo = (RgSchRaReqInfo *)(cell->raInfo.raReqLst[raIdx].first->node);
1113       cmLListDelFrm(&(cell->raInfo.raReqLst[raIdx]),&(raReqInfo->raReqLstEnt));
1114       /* ccpu00117052 - MOD - Passing double pointer
1115       for proper NULLP assignment*/
1116       rgSCHUtlFreeSBuf(cell->instIdx, (Data **)&raReqInfo,
1117             sizeof(RgSchRaReqInfo));
1118    }
1119 #else
1120    /* Fixes for RACH handling: Added deletion of queued RaReq */
1121    frm   = cell->crntTime;
1122    RGSCH_INCR_SUB_FRAME(frm, RG_SCH_CMN_DL_DELTA);
1123    if(rgSchTddUlDlSubfrmTbl[cell->ulDlCfgIdx][frm.slot] !=
1124                      RG_SCH_TDD_UL_SUBFRAME)
1125    {
1126       raIdx = rgSchTddNumDlSubfrmTbl[cell->ulDlCfgIdx][frm.slot]-1;
1127       rgSCHRamDelRaReq(cell, cell->crntTime, raIdx);
1128    }
1129 #endif
1130    
1131    /* Remove the RACBs which are timed out */
1132    /* ccpu00132536:MOD- racb timeout will be verified in each SFN such that 
1133     * the RACB whose processing is not completed in RG_MAX_RA_PRC_FRM
1134     * will be deleted*/
1135    if (cell->crntTime.slot == 0)
1136    {
1137       maxCnt = cell->raInfo.raCbLst.count;
1138       for (idx = 0; idx < maxCnt; idx++)
1139       {
1140          raCb = (RgSchRaCb *)(cell->raInfo.raCbLst.first->node);
1141          /* Calculate number of frames between raCb's creation and crnt frame */
1142          raSfn = raCb->timingInfo.sfn;
1143          dist = (crntSfn + (RGSCH_MAX_SFN - raSfn)) % RGSCH_MAX_SFN;
1144          /* Delete RaCbs whose processing is not complete within 
1145           * "cell->t300TmrVal" frames */
1146           /* raCb not to be deleted if msg4 is not completed */
1147           /* raCb should not be deleted(RNTI should not be released) if UE is present
1148            * as it means the application still holds the RNTI. raCb will get deleted
1149            * as part of UE deletion. raCb will anyway get deleted without releasing RNTI on success/failure of MSG4*/
1150          
1151          if (dist >= cell->t300TmrVal) 
1152          {
1153             if ((raCb->dlHqE->msg4Proc == NULLP) && (raCb->dlHqE->ue == NULLP))
1154             {
1155                rgSCHRamDelRaCb(cell, raCb, TRUE);
1156             }
1157          }
1158          else
1159          {
1160             break;
1161          }
1162       }
1163    }
1164    
1165    return ROK; 
1166 }  /* rgSCHRamTtiHndlr */
1167
1168
1169 /**
1170  * @brief Function for handling cell delete
1171  *
1172  * @details
1173  *
1174  *     Function : rgSCHRamFreeCell
1175  *     
1176  *     This function shall be invoked whenever a cell needs to be deleted.
1177  *     This shall remove raCbs and raReqs stored in cell.
1178  *     
1179  *           
1180  *  @param[in,out] RgSchCellCb  *cell
1181  *  @return  S16
1182  *      -# ROK 
1183  **/
1184 #ifdef ANSI
1185 S16 rgSCHRamFreeCell
1186 (
1187 RgSchCellCb    *cell
1188 )
1189 #else
1190 S16 rgSCHRamFreeCell(cell)
1191 RgSchCellCb    *cell;
1192 #endif
1193 {
1194    RgSchRaReqInfo  *raReqInfo;
1195    RgSchRaCb       *raCb;
1196    U8              idx;
1197    U8              raCbCnt;
1198    Inst            inst = cell->instIdx;
1199    U8              lstSz;
1200 #ifdef LTE_TDD
1201    U8              maxUlSubframes;
1202    U8              maxDlSubframes;
1203 #endif
1204
1205
1206
1207
1208 #ifdef LTE_TDD
1209    maxUlSubframes =
1210       rgSchTddNumUlSubfrmTbl[cell->ulDlCfgIdx][RGSCH_NUM_SUB_FRAMES-1];
1211    maxDlSubframes =
1212       rgSchTddNumDlSubfrmTbl[cell->ulDlCfgIdx][RGSCH_NUM_SUB_FRAMES-1];
1213    lstSz = cell->raInfo.maxRaSize * RGSCH_MAX_RA_RNTI_PER_SUBFRM * \
1214                                                       maxUlSubframes;
1215 #else
1216    /* ccpu00133557- MEM LEAK FIX- Need to free all the nodes in RA Array list */
1217    lstSz = RGSCH_RAREQ_ARRAY_SIZE;
1218 #endif
1219
1220    for (idx = 0; idx < lstSz; idx++)
1221    {
1222       /* Delete and free raReqs stored */
1223       /* ccpu00133557- MEM LEAK FIX- Need to be freed till the count is non-zero */
1224       while(cell->raInfo.raReqLst[idx].count)
1225       {
1226          raReqInfo = (RgSchRaReqInfo *)(cell->raInfo.raReqLst[idx].first->node);
1227          cmLListDelFrm(&(cell->raInfo.raReqLst[idx]),&(raReqInfo->raReqLstEnt));
1228          /* ccpu00117052 - MOD - Passing double pointer
1229          for proper NULLP assignment*/
1230          rgSCHUtlFreeSBuf(inst, (Data **)&raReqInfo, sizeof(RgSchRaReqInfo));
1231       }
1232    }
1233
1234 #ifdef LTE_TDD
1235    /* Delete the RACH response list*/
1236       /* ccpu00117052 - MOD - Passing double pointer
1237       for proper NULLP assignment*/
1238    rgSCHUtlFreeSBuf(inst, 
1239          (Data **)(&(cell->rachRspLst)), sizeof(RgSchTddRachRspLst) * \
1240                                     maxDlSubframes);
1241 #endif
1242
1243    /* Delete raCbs in the "to be scheduled" list */
1244    /* ccpu00133557- MEM LEAK FIX- Need to be freed till the count is non-zero */
1245    while(cell->raInfo.toBeSchdLst.count)
1246    {
1247       raCb = (RgSchRaCb *)(cell->raInfo.toBeSchdLst.first->node);
1248       /* MSG4 Fix Start */
1249                   
1250       rgSCHRamRmvFrmRaInfoSchdLst(cell, raCb);
1251       /* MSG4 Fix End */          
1252    }
1253 #ifdef EMTC_ENABLE
1254    /* Delete raCbs in the "Emtc to be scheduled" list */
1255       if(cell->emtcEnable)
1256       {
1257           rgSCHRamRmvAllFrmEmtcRaInfoSchdLst(cell);
1258       }
1259 #endif
1260
1261    raCbCnt =  cell->raInfo.raCbLst.count;
1262
1263    /* Delete and free raCbs stored */ 
1264    for (idx = 0; idx < raCbCnt; idx++)
1265    {
1266       raCb = (RgSchRaCb *)(cell->raInfo.raCbLst.first->node);
1267       rgSCHRamDelRaCb(cell, raCb, TRUE);
1268    }
1269
1270    return ROK; 
1271 } /* rgSCHRamFreeCell */
1272 #ifdef RGR_V1
1273 #ifdef ANSI
1274 PRIVATE Void rgSCHRamProcContResExp
1275 (
1276 RgSchCellCb *cell,
1277 RgSchRaCb  *raCb
1278 )
1279 #else
1280 PRIVATE Void rgSCHRamProcContResExp (cell, raCb)
1281 RgSchCellCb *cell;
1282 RgSchRaCb  *raCb;
1283 #endif
1284 {
1285    raCb->expiryTime.sfn = RGSCH_CONTRES_EXP;
1286    /*MSG4 Fix*/
1287    if (raCb->ue)
1288    {
1289       /* UE exists and RNTI will be released as part of UE DEL */          
1290       rgSCHRamDelRaCb(cell, raCb, FALSE);
1291    }
1292    else
1293    {
1294       /* Calling Release RNTI, which would perform Racb deletion
1295        * RNTI removal and RNTI release indication to MAC. */       
1296       /* Delete RACB and release RNTI */
1297       rgSCHRamDelRaCb(cell, raCb, TRUE);
1298    }
1299    RETVOID;
1300 }
1301
1302 #ifdef ANSI
1303 PRIVATE Void rgSCHRamProcContResGrdExp
1304 (
1305 RgSchCellCb *cell,
1306 RgSchRaCb  *raCb
1307 )
1308 #else
1309 PRIVATE Void rgSCHRamProcContResGrdExp (cell, raCb)
1310 RgSchCellCb  *cell;
1311 RgSchRaCb  *raCb;
1312 #endif
1313 {
1314
1315
1316 /*Guard timer has expired, schedule only the contention REsolution CE with 
1317  * zero bo*/
1318    raCb->dlCcchInfo.bo = 0; 
1319    /* SR_RACH_STATS : MSG4 WO CCCH SDU */
1320    rgNumMsg4WoCCCHSdu++;
1321
1322    /* add this to the "tobeSchdLst" */
1323    raCb->schdLnk.node = (PTR)(raCb);
1324    
1325    cmLListDelFrm(&cell->contResGrdTmrLst, &(raCb->contResTmrLnk));
1326    raCb->contResTmrLnk.node = NULLP;
1327
1328    /* MSG4 Fix Start */
1329    RLOG_ARG1(L_DEBUG,DBG_CELLID,cell->cellId,
1330             "Con Res Grd Tmr exp RNTI:%d", 
1331             raCb->rntiLnk->rnti);   
1332    rgSCHRamAddToRaInfoSchdLst(cell, raCb);
1333    /* MSG4 Fix End */    
1334    RETVOID;
1335    
1336 }
1337 /**
1338  * @brief Check the Contention Resolution Guard Timer Expiry. 
1339  *
1340  * @details
1341  *
1342  *     Function: rgSCHChkContResTmrExp 
1343  *
1344  *
1345  *     Invoked by: Scheduler 
1346  *  @param[in] RgSchCellCb        *cell 
1347  *  @return  S16
1348  *      -# ROK 
1349  *      -# RFAILED 
1350  **/
1351 #ifdef ANSI
1352 PRIVATE Void rgSCHChkContResTmrExp
1353 (
1354 RgSchCellCb        *cell
1355 )
1356 #else
1357 PRIVATE Void rgSCHChkContResTmrExp(cell)
1358 RgSchCellCb        *cell;
1359 #endif
1360 {
1361    CmLList         *chkLnk    = NULLP;
1362    RgSchRaCb       *raCb = NULLP;
1363    
1364       
1365    chkLnk = cmLListFirst(&(cell->contResTmrLst));
1366    
1367    for (; chkLnk; chkLnk = chkLnk->next)
1368    {
1369       raCb = (RgSchRaCb *)(chkLnk->node);
1370       
1371       if(RGSCH_TIMEINFO_SAME(raCb->expiryTime, cell->crntTime))
1372       {
1373          /*If timer expired, call the handler function*/
1374          rgSCHRamProcContResExp(cell, raCb);
1375       }
1376           /*Fix: Need to traverse till end of list as the entries may not be in ascending order*/
1377    /*   else
1378       {
1379     break;
1380       }*/
1381    }
1382 }
1383 /**
1384  * @brief Check the Contention Resolution Guard Timer Expiry. 
1385  *
1386  * @details
1387  *
1388  *     Function: rgSCHChkContResGrdTmrExp 
1389  *
1390  *
1391  *     Invoked by: Scheduler 
1392  *  @param[in] RgSchCellCb        *cell 
1393  *  @return  S16
1394  *      -# ROK 
1395  *      -# RFAILED 
1396  **/
1397 #ifdef ANSI
1398 PRIVATE Void rgSCHChkContResGrdTmrExp
1399 (
1400 RgSchCellCb        *cell
1401 )
1402 #else
1403 PRIVATE Void rgSCHChkContResGrdTmrExp(cell)
1404 RgSchCellCb        *cell;
1405 #endif
1406 {
1407    CmLList         *chkLnk    = NULLP;
1408    RgSchRaCb       *raCb = NULLP;
1409    
1410       
1411    chkLnk = cmLListFirst(&(cell->contResGrdTmrLst));
1412    
1413    /*[ccpu00131941]-MOD-List traversal should be done using the listCp */
1414    for (; chkLnk; chkLnk = cmLListNext(&cell->contResGrdTmrLst))
1415    {
1416       raCb = (RgSchRaCb *)(chkLnk->node);
1417       
1418       if(RGSCH_TIMEINFO_SAME(raCb->expiryTime, cell->crntTime))
1419       {
1420     /*If timer expired, call the handler function*/
1421     rgSCHRamProcContResGrdExp(cell, raCb);
1422       }
1423       else
1424       {
1425     break;
1426       }
1427    }
1428 }
1429 #endif
1430 #ifdef LTE_TDD
1431 /**
1432  * @brief Function for handling RACH Request deletion
1433  *
1434  * @details
1435  *
1436  *     Function : rgSCHRamDelRaReq
1437  *
1438  *     This function shall be invoked to delete the RACH Requests
1439  *     that is not scheduled within the RA window size.
1440  *
1441  *
1442  *  @param[in,out] RgSchCellCb      *cell
1443  *  @param[in]     CmLteTimingInfo  timingInfo
1444  *  @param[in]     U8               raIdx
1445  *  @return  S16
1446  *      -# ROK
1447  **/
1448 #ifdef ANSI
1449 S16 rgSCHRamDelRaReq
1450 (
1451 RgSchCellCb          *cell,
1452 CmLteTimingInfo      timingInfo,
1453 U8                   raIdx
1454 )
1455 #else
1456 S16 rgSCHRamDelRaReq(cell, timingInfo, raIdx)
1457 RgSchCellCb          *cell;
1458 CmLteTimingInfo      timingInfo;
1459 U8                   raIdx;
1460 #endif
1461 {
1462    U8                   subfrmIdx;
1463    RgSchTddRachRspLst   *rachRsp;
1464    U16                   sfnIdx;
1465    S16                  calcSfn;
1466    U8                   subfrm;
1467    RgSchRaReqInfo       *raReqInfo;
1468    U8                   idx;
1469    U8                   i;
1470    U8                   raRntiIdx;
1471    CmLteRnti            raRnti;
1472
1473
1474
1475    rachRsp = &cell->rachRspLst[raIdx];
1476    /* Get the SFN Index to be deleted */
1477    calcSfn = timingInfo.sfn - rachRsp->delInfo.sfnOffset;
1478    if(calcSfn < 0)
1479    {
1480       sfnIdx = (calcSfn + RGSCH_MAX_SFN) % cell->raInfo.maxRaSize;
1481    }
1482    else
1483    {
1484       sfnIdx = calcSfn;
1485    }
1486
1487    /* Iterate through all the subframes to be delted in the SFN */
1488    for(subfrmIdx=0; subfrmIdx < rachRsp->delInfo.numSubfrms; subfrmIdx++)
1489    {
1490       subfrm = rachRsp->delInfo.subframe[subfrmIdx];
1491       /* Get the subframe Index to be deleted */
1492       /* Fixes for RACH handling in TDD: 
1493        * Corrected the computation of raRntiIdx
1494        * */
1495       raRntiIdx = ((sfnIdx % cell->raInfo.maxRaSize) * \
1496                      RGSCH_MAX_RA_RNTI_PER_SUBFRM * \
1497                      RGSCH_NUM_SUB_FRAMES) + subfrm;
1498
1499       /* Iterate through all the RNTIs in the subframe */
1500       for(i=0; i < RGSCH_MAX_RA_RNTI_PER_SUBFRM; i++)
1501       {
1502          raRnti = raRntiIdx + (i*RGSCH_NUM_SUB_FRAMES);
1503          for (idx = 0; idx < cell->raInfo.raReqLst[raRnti].count; idx++)
1504          {
1505             raReqInfo = 
1506                (RgSchRaReqInfo *)(cell->raInfo.raReqLst[raRnti].first->node);
1507             cmLListDelFrm(&(cell->raInfo.raReqLst[raRnti]),
1508                                     &(raReqInfo->raReqLstEnt));
1509             /* ccpu00117052 - MOD - Passing double pointer
1510             for proper NULLP assignment*/
1511             rgSCHUtlFreeSBuf(cell->instIdx,
1512                               (Data **)&raReqInfo, sizeof(RgSchRaReqInfo));
1513          }
1514       }
1515    }
1516
1517    return ROK;
1518 }
1519 #endif
1520
1521 /*MSG4 Fix Start */
1522 #ifdef ANSI
1523 S16 rgSCHRamAddToRaInfoSchdLst
1524 (
1525 RgSchCellCb       *cell,
1526 RgSchRaCb         *raCb
1527 )
1528 #else
1529 S16 rgSCHRamAddToRaInfoSchdLst(cell, raCb)
1530 RgSchCellCb       *cell;
1531 RgSchRaCb         *raCb;
1532 #endif
1533 {
1534    CmLteTimingInfo expTime ={0};
1535    RgSchCmnCell    *cellSch =  RG_SCH_CMN_GET_CELL(cell);
1536
1537
1538    /*Fix: This can be called even when guard timer is not expired. 
1539        * In this case CR timer expiry should be guard timer expiry time + Guard timer time*/
1540    RG_SCH_ADD_TO_CRNT_TIME(raCb->expiryTime, expTime, cellSch->dl.msg4TxDelay);
1541    raCb->expiryTime = expTime;
1542    raCb->schdLnk.node = (PTR)(raCb);
1543    cmLListAdd2Tail(&(cell->raInfo.toBeSchdLst), &(raCb->schdLnk));
1544    raCb->contResTmrLnk.node = (PTR)(raCb);
1545    cmLListAdd2Tail(&(cell->contResTmrLst), &(raCb->contResTmrLnk));
1546    return ROK;
1547 } /* rgSCHRamAddToRaInfoSchdLst */
1548
1549
1550
1551 #ifdef ANSI
1552 S16 rgSCHRamRmvFrmRaInfoSchdLst
1553 (
1554 RgSchCellCb       *cell,
1555 RgSchRaCb         *raCb
1556 )
1557 #else
1558 S16 rgSCHRamRmvFrmRaInfoSchdLst(cell, raCb)
1559 RgSchCellCb       *cell;
1560 RgSchRaCb         *raCb;
1561 #endif
1562 {
1563
1564    cmLListDelFrm(&(cell->raInfo.toBeSchdLst), &(raCb->schdLnk));
1565    raCb->schdLnk.node = NULLP;   
1566    cmLListDelFrm(&(cell->contResTmrLst), &(raCb->contResTmrLnk));
1567    raCb->contResTmrLnk.node = NULLP;
1568    return ROK;
1569 } /* rgSCHRamRmvFrmRaInfoSchdLst */
1570
1571 /*MSG4 Fix End*/
1572
1573 /***********************************************************
1574  *
1575  *     Func : rgSCHRamUlFreeAllocation
1576  *
1577  *     Desc : Free an allocation - invokes UHM and releases
1578  *            alloc
1579  *
1580  *     Ret  :
1581  *
1582  *     Notes:
1583  *
1584  *     File :
1585  *
1586  **********************************************************/
1587 #ifdef ANSI
1588 PRIVATE Void rgSCHRamUlFreeAllocation
1589 (
1590 RgSchUlSf       *sf,
1591 RgSchUlAlloc    *alloc,
1592 RgSchCellCb     *cell,
1593 Bool            isEmtc
1594
1595 )
1596 #else
1597 PRIVATE Void rgSCHRamUlFreeAllocation(sf, alloc, cell,isEmtc)
1598 RgSchUlSf       *sf;
1599 RgSchUlAlloc    *alloc;
1600 RgSchCellCb     *cell;
1601 Bool            isEmtc;
1602 #endif
1603 {
1604
1605    rgSCHUhmFreeProc(alloc->hqProc, cell);
1606    if(!isEmtc)
1607    {
1608       rgSCHUtlUlAllocRls(sf, alloc);
1609    }
1610    RETVOID;
1611 }
1612
1613 /**********************************************************************
1614  
1615          End of file
1616 **********************************************************************/