Ue Config Changes aligned with AAD
[o-du/l2.git] / src / du_app / du_msg_hdl.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 /* This file contains message handling functionality for DU APP */
20 #include "common_def.h"
21 #include "lrg.h"
22 #include "legtp.h"
23 #include "lkw.h"
24 #include "kwu.h"
25 #include "lrg.x"
26 #include "lkw.x"
27 #include "kwu.x"
28 #include "du_app_mac_inf.h"
29 #include "du_app_rlc_inf.h"
30 #include "du_cfg.h"
31 #include "du_app_rlc_inf.h"
32 #include "du_mgr.h"
33 #include "du_sctp.h"
34 #include "F1AP-PDU.h"
35 #include "du_f1ap_msg_hdl.h"
36 #include "du_ue_mgr.h"
37 #include "lsctp.h"
38 #include "legtp.h"
39 #include "lphy_stub.h"
40 #include "du_utils.h"
41 #include "du_cell_mgr.h" 
42
43 #ifdef O1_ENABLE
44
45 #include "GlobalDefs.h"
46 #include "AlarmInterface.h"
47
48 #endif 
49
50 uint8_t rlcDlCfg = 0;
51 uint8_t numRlcDlSaps = 0;
52 uint8_t rlcUlCfg = 0;
53 uint8_t numRlcMacSaps = 0;
54 uint8_t macCfg = 0;
55 uint8_t macCfgInst = 0;
56
57 DuCfgParams duCfgParam;
58 uint8_t packRlcConfigReq(Pst *pst, RlcMngmt *cfg);
59 uint8_t cmPkLkwCntrlReq(Pst *pst, RlcMngmt *cfg);
60 uint8_t cmPkLrgCfgReq(Pst *pst, RgMngmt *cfg);
61 uint8_t BuildAndSendE2SetupReq();
62 uint8_t egtpHdlDatInd(EgtpMsg egtpMsg);
63 uint8_t BuildAndSendDUConfigUpdate();
64 uint16_t getTransId();
65 uint8_t cmPkLrgSchCfgReq(Pst * pst,RgMngmt * cfg);
66
67 packMacCellCfgReq packMacCellCfgOpts[] =
68 {
69    packMacCellCfg, /* packing for loosely coupled */
70    MacProcCellCfgReq, /* packing for tightly coupled */
71    packMacCellCfg, /* packing for light weight loosly coupled */
72 };
73
74 DuMacCellStartReq packMacCellStartReqOpts[] =
75 {
76    packMacCellStartReq,   /* Loose coupling */
77    MacProcCellStartReq,    /* TIght coupling */
78    packMacCellStartReq    /* Light weight-loose coupling */
79 };
80
81 DuMacCellStopReq packMacCellStopReqOpts[] =
82 {
83    packMacCellStopReq,   /* Loose coupling */
84    MacProcCellStopReq,    /* TIght coupling */
85    packMacCellStopReq    /* Light weight-loose coupling */
86 };
87
88 /**************************************************************************
89  * @brief Function to fill configs required by RLC
90  *
91  * @details
92  *
93  *      Function : duBuildRlcCfg 
94  * 
95  *      Functionality:
96  *           Initiates general Configs towards RLC 
97  *     
98  * @param[in] Inst  Specifies if RLC UL or RLC DL instance 
99  * @return ROK     - success
100  *         RFAILED - failure
101  *
102  ***************************************************************************/
103 uint8_t duBuildRlcCfg(Inst inst)
104 {
105    RlcMngmt   rlcMngmt;
106    RlcGenCfg  *genCfg = NULLP;
107    Pst pst;
108
109    DU_SET_ZERO(&rlcMngmt, sizeof(RlcMngmt));
110    DU_SET_ZERO(&pst, sizeof(Pst));
111
112    genCfg   = &(rlcMngmt.t.cfg.s.gen);
113
114    /*----------- Fill General Configuration Parameters ---------*/
115    genCfg->maxUe       = duCfgParam.maxUe;
116    genCfg->maxKwuSaps  = 2;
117    genCfg->maxUdxSaps  = 1; 
118    genCfg->rlcMode     = (inst == RLC_UL_INST) ?
119       LKW_RLC_MODE_UL : LKW_RLC_MODE_DL;
120    genCfg->timeRes     = 1; 
121    genCfg->maxRguSaps  = DEFAULT_CELLS;
122
123    /*----------- Fill lmPst
124     * Parameters ---------*/
125    genCfg->lmPst.dstProcId = DU_PROC;
126    genCfg->lmPst.srcProcId = DU_PROC;
127    genCfg->lmPst.dstEnt    = ENTDUAPP;
128    genCfg->lmPst.dstInst   = DU_INST;
129    genCfg->lmPst.srcEnt    = ENTRLC;
130    genCfg->lmPst.srcInst   = inst;
131    genCfg->lmPst.prior     = PRIOR0;
132    genCfg->lmPst.route     = RTESPEC;
133    genCfg->lmPst.region    = (inst == RLC_UL_INST) ?
134       RLC_UL_MEM_REGION:RLC_DL_MEM_REGION;
135    genCfg->lmPst.pool      = RLC_POOL;
136    genCfg->lmPst.selector  = ODU_SELECTOR_LC;
137
138    /* Fill Header */
139    rlcMngmt.hdr.msgType             = TCFG;
140    rlcMngmt.hdr.msgLen              = 0;
141    rlcMngmt.hdr.entId.ent           = ENTRLC;
142    rlcMngmt.hdr.entId.inst          = (Inst)0;
143    rlcMngmt.hdr.elmId.elmnt         = STGEN;
144    rlcMngmt.hdr.seqNmb              = 0;
145    rlcMngmt.hdr.version             = 0;
146    rlcMngmt.hdr.transId             = 0;
147    rlcMngmt.hdr.response.prior      = PRIOR0;
148    rlcMngmt.hdr.response.route      = RTESPEC;
149    rlcMngmt.hdr.response.mem.region = (inst == RLC_UL_INST) ?
150       RLC_UL_MEM_REGION:RLC_DL_MEM_REGION;
151    rlcMngmt.hdr.response.mem.pool   = DU_POOL;
152    rlcMngmt.hdr.response.selector   = ODU_SELECTOR_LC;
153
154    /* Fill Pst */
155    pst.selector  = ODU_SELECTOR_LC;
156    pst.srcEnt    = ENTDUAPP;
157    pst.dstEnt    = ENTRLC;
158    pst.dstInst   = inst;
159    pst.dstProcId = DU_PROC;
160    pst.srcProcId = DU_PROC;
161    pst.region    = duCb.init.region;
162
163    DU_LOG("\nDU_APP : RLC Gen Cfg Req sent for inst %d", inst);
164
165    /* Send the request to RLC */
166    packRlcConfigReq(&pst, &rlcMngmt);
167
168    return ROK;
169 }
170
171 /**************************************************************************
172  * @brief Function to fill configs required by RLC
173  *
174  * @details
175  *
176  *      Function : duBuildRlcLsapCfg 
177  * 
178  *      Functionality:
179  *           Initiates general Configs towards RLC 
180  *     
181  * @param[in] Inst  Specifies if RLC UL or RLC DL instance 
182  * @return ROK     - success
183  *         RFAILED - failure
184  *
185  ***************************************************************************/
186 uint8_t duBuildRlcLsapCfg(Ent ent, Inst inst, uint8_t lsapInst)
187 {
188
189    RlcMngmt   rlcMngmt;
190    RlcSapCfg  *lSap = NULLP;
191    Pst        pst;
192
193    DU_SET_ZERO(&rlcMngmt, sizeof(RlcMngmt));
194    DU_SET_ZERO(&pst, sizeof(Pst));
195
196    /* Fill Header */
197    rlcMngmt.hdr.msgType             = TCFG;
198    rlcMngmt.hdr.entId.ent           = ENTRLC;
199    rlcMngmt.hdr.response.mem.region = (inst == RLC_UL_INST) ?
200       RLC_UL_MEM_REGION:RLC_DL_MEM_REGION;
201
202    rlcMngmt.hdr.response.mem.pool   = RLC_POOL;
203
204    /* Fill Pst */
205    pst.selector  = ODU_SELECTOR_LC;
206    pst.srcEnt    = ENTDUAPP;
207    pst.dstEnt    = ENTRLC;
208    pst.dstProcId = DU_PROC;
209    pst.dstInst   = inst;
210    pst.srcProcId = DU_PROC;
211    pst.region    = duCb.init.region;
212    lSap   = &(rlcMngmt.t.cfg.s.sap);
213
214    lSap->mem.region = (inst == RLC_UL_INST) ?
215       RLC_UL_MEM_REGION:RLC_DL_MEM_REGION;
216    lSap->mem.pool    = RLC_POOL;
217    lSap->mem.spare   = 0;
218    lSap->bndTmrIntvl = 10;
219    lSap->priority    = PRIOR0;
220    lSap->route       = RTESPEC;
221    if (ent == ENTMAC)
222    {
223       lSap->procId      = DU_PROC;
224       lSap->ent         = ENTMAC;
225       lSap->inst        = lsapInst;
226       lSap->sapId       = lsapInst;      /* SapId will be stored as suId in MAC */
227       lSap->selector    = (inst == RLC_UL_INST) ? ODU_SELECTOR_LWLC : ODU_SELECTOR_TC;
228       rlcMngmt.hdr.elmId.elmnt  = STRGUSAP;
229       DU_LOG("\nDU_APP : RLC MAC Lower Sap Cfg Req sent for inst %d", inst);
230
231    }
232    else
233    {
234       lSap->procId    = DU_PROC;
235       lSap->ent       = ENTRLC;
236       lSap->inst      = (inst == RLC_UL_INST) ?
237          RLC_DL_INST : RLC_UL_INST;
238       lSap->sapId       = 0;
239       lSap->selector = ODU_SELECTOR_LC;
240       rlcMngmt.hdr.elmId.elmnt  = STUDXSAP;
241       DU_LOG("\nDU_APP : RLC DL/UL Lower Sap Cfg Req sent for inst %d", inst);
242    }
243
244    packRlcConfigReq(&pst, &rlcMngmt);
245    return ROK;
246 }
247
248 /**************************************************************************
249  * @brief Function to fill configs required by RLC
250  *
251  * @details
252  *
253  *      Function : duBuildRlcUsapCfg 
254  * 
255  *      Functionality:
256  *           Initiates general Configs towards RLC 
257  *     
258  * @param[in] Inst  Specifies if RLC UL or RLC DL instance 
259  * @return ROK     - success
260  *         RFAILED - failure
261  *
262  ***************************************************************************/
263 uint8_t duBuildRlcUsapCfg(uint8_t elemId, Ent ent, Inst inst)
264 {
265    RlcMngmt   rlcMngmt;
266    RlcSapCfg  *uSap = NULLP;
267    Pst        pst;
268
269    DU_SET_ZERO(&rlcMngmt, sizeof(RlcMngmt));
270    DU_SET_ZERO(&pst, sizeof(Pst));
271
272    uSap   = &(rlcMngmt.t.cfg.s.sap);
273
274    uSap->selector   = ODU_SELECTOR_LC;
275    uSap->mem.region = (inst == RLC_UL_INST) ?
276       RLC_UL_MEM_REGION:RLC_DL_MEM_REGION;
277    uSap->mem.pool = RLC_POOL;
278    uSap->mem.spare = 0;
279
280    uSap->procId = DU_PROC;
281    uSap->ent = ENTRLC;
282    uSap->sapId = 0;
283
284    uSap->inst = (inst == RLC_UL_INST) ?
285       RLC_DL_INST : RLC_UL_INST;
286    uSap->bndTmrIntvl = 1000;
287    uSap->priority = PRIOR0;
288    uSap->route = RTESPEC;
289
290    /* Fill Header */
291    rlcMngmt.hdr.msgType             = TCFG;
292    rlcMngmt.hdr.entId.ent           = ENTRLC;
293    rlcMngmt.hdr.elmId.elmnt         = STUDXSAP;
294    rlcMngmt.hdr.response.mem.region = (inst == RLC_UL_INST) ?
295       RLC_UL_MEM_REGION:RLC_DL_MEM_REGION;
296
297    rlcMngmt.hdr.response.mem.pool   = RLC_POOL;
298
299    /* Fill Pst */
300    pst.selector  = ODU_SELECTOR_LC;
301    pst.srcEnt    = ENTDUAPP;
302    pst.dstEnt    = ENTRLC;
303    pst.dstProcId = DU_PROC;
304    pst.dstInst = inst;
305    pst.srcProcId = DU_PROC;
306    pst.region = duCb.init.region;
307
308    DU_LOG("\nDU_APP : RLC Kwu Upper Sap Cfg Req sent for inst %d", inst);
309    packRlcConfigReq(&pst, &rlcMngmt);
310
311    return ROK;
312 }
313
314 /**************************************************************************
315  * @brief Function to populate internal DS of DU APP
316  *
317  * @details
318  *
319  *      Function : duProcCfgComplete
320  * 
321  *      Functionality:
322  *           Populates internal data structures of DU APP after 
323  *           receiving configurations.
324  *     
325  * @param[in]  void
326  * @return ROK     - success
327  *         RFAILED - failure
328  *
329  ***************************************************************************/
330 uint8_t duProcCfgComplete()
331 {
332    uint8_t         ret = ROK;
333    static uint16_t cellId = 0;
334    uint16_t        idx;
335    for(idx=0; idx< DEFAULT_CELLS; idx++)
336    {
337       DuCellCb *cell = NULLP;
338       DU_ALLOC(cell, sizeof(DuCellCb))
339       if(cell == NULLP)
340       {
341          DU_LOG("\nDU_APP : Memory Allocation failed in duProcCfgComplete");
342          ret = RFAILED;
343       }
344       else
345       {
346          uint8_t idx1; 
347          memset(cell, 0, sizeof(DuCellCb));
348          cell->cellId = ++cellId;
349          memset(&cell->cellInfo.nrEcgi.plmn, 0, sizeof(Plmn));
350          cell->cellInfo.nrEcgi.plmn.mcc[0] = PLMN_MCC0;
351          cell->cellInfo.nrEcgi.plmn.mcc[1] = PLMN_MCC1;
352          cell->cellInfo.nrEcgi.plmn.mcc[2] = PLMN_MCC2;
353          cell->cellInfo.nrEcgi.plmn.mnc[0] = PLMN_MNC0;
354          cell->cellInfo.nrEcgi.plmn.mnc[1] = PLMN_MNC1;
355          cell->cellInfo.nrEcgi.cellId = NR_CELL_ID;
356          cell->cellInfo.nrPci = NR_PCI; 
357          cell->cellInfo.fiveGsTac = DU_TAC;
358          memset(&cell->cellInfo.plmn[idx1], 0, sizeof(Plmn));
359          for(idx1=0; idx1<MAX_PLMN; idx1++)
360          {
361             cell->cellInfo.plmn[idx1].mcc[0] = PLMN_MCC0;
362             cell->cellInfo.plmn[idx1].mcc[1] = PLMN_MCC1;
363             cell->cellInfo.plmn[idx1].mcc[2] = PLMN_MCC2;
364             cell->cellInfo.plmn[idx1].mnc[0] = PLMN_MNC0;
365             cell->cellInfo.plmn[idx1].mnc[1] = PLMN_MNC1;
366          }
367          cell->cellInfo.maxUe = duCfgParam.maxUe;
368          cell->cellStatus = CELL_OUT_OF_SERVICE;
369
370          duCb.cfgCellLst[duCb.numCfgCells] = cell;
371          duCb.numCfgCells++;
372       }
373    }
374    if(ret != RFAILED)
375    {
376       //Start layer configs
377       ret = duSendRlcUlCfg();
378    }
379    return ret;
380 }
381 /**************************************************************************
382  * @brief Function to invoke DU Layer Configs
383  *
384  * @details
385  *
386  *      Function : duSendRlcUlCfg 
387  * 
388  *      Functionality:
389  *           Initiates Configs towards layers of DU
390  *     
391  * @param[in]  void
392  * @return ROK     - success
393  *         RFAILED - failure
394  *
395  ***************************************************************************/
396 uint8_t duSendRlcUlCfg()
397 {
398    uint8_t cellIdx; 
399
400    duBuildRlcCfg((Inst)RLC_UL_INST);
401    for(cellIdx = 0; cellIdx < DEFAULT_CELLS; cellIdx++)
402    {
403       duBuildRlcLsapCfg(ENTMAC, (Inst)RLC_UL_INST, cellIdx);
404    }
405    duBuildRlcLsapCfg(ENTRLC, (Inst)RLC_UL_INST, 0);
406
407    return ROK;
408 }
409
410 /**************************************************************************
411  * @brief Function to invoke DU Layer Configs
412  *
413  * @details
414  *
415  *      Function : duSendRlcDlCfg 
416  * 
417  *      Functionality:
418  *           Initiates Configs towards layers of DU
419  *     
420  * @param[in]  void
421  * @return ROK     - success
422  *         RFAILED - failure
423  *
424  ***************************************************************************/
425 uint8_t duSendRlcDlCfg()
426 {
427    uint8_t cellIdx; 
428
429    duBuildRlcCfg((Inst)RLC_DL_INST);
430    duBuildRlcUsapCfg(STUDXSAP, ENTRLC, (Inst)RLC_DL_INST);
431    for(cellIdx = 0; cellIdx < DEFAULT_CELLS; cellIdx++)
432    {
433       duBuildRlcLsapCfg(ENTMAC, (Inst)RLC_DL_INST, cellIdx);
434    }
435
436    return ROK;
437 }
438 /**************************************************************************
439  * @brief Function to handle Config Confirm from RLC
440  *
441  * @details
442  *
443  *      Function : DuHdlRlcCfgComplete 
444  * 
445  *      Functionality:
446  *           Handles Gen Config Confirm from RLC
447  *     
448  * @param[in]  Pst     *pst, Post structure of the primitive.     
449  * @param[in]  RlcMngmt *cfm, Unpacked primitive info received from RLC
450  * @return ROK     - success
451  *         RFAILED - failure
452  *
453  ***************************************************************************/
454 uint8_t DuHdlRlcCfgComplete(Pst *pst, RlcMngmt *cfm)
455 {
456    uint8_t ret = ROK;
457    if (pst->srcInst == RLC_UL_INST)
458    {
459       ret = duProcRlcUlCfgComplete(pst, cfm);
460    }
461    else
462    {
463       ret = duProcRlcDlCfgComplete(pst, cfm);
464    }
465    return ret;
466 }
467
468 /**************************************************************************
469  * @brief Function to handle Control Config Confirm from RLC
470  *
471  * @details
472  *
473  *      Function : duHdlRlcCntrlCfgComplete 
474  * 
475  *      Functionality:
476  *           Handles Control Config Confirm from RLC
477  *     
478  * @param[in]  Pst     *pst, Post structure of the primitive.     
479  * @param[in]  RlcMngmt *cfm, Unpacked primitive info received from RLC
480  * @return ROK     - success
481  *         RFAILED - failure
482  *
483  ***************************************************************************/
484 uint8_t duHdlRlcCntrlCfgComplete(Pst *pst, RlcMngmt *cntrl)
485 {
486    uint8_t ret = ROK;
487
488    if (cntrl->cfm.status == LCM_PRIM_OK)
489    {
490       switch (cntrl->hdr.elmId.elmnt)
491       {
492          case  STRGUSAP:
493             {
494                if (pst->srcInst == RLC_DL_INST)
495                {
496                   DU_LOG("\nDU_APP : BIND OF RLC DL TO MAC (RGU) SAP SUCCESSFUL");
497                   macCfgInst++;
498                   if(macCfgInst < DEFAULT_CELLS)
499                   {
500                      macCfgInst = 0;
501                      duBindUnbindRlcToMacSap((Inst) RLC_DL_INST, ABND);
502                   }
503                   else
504                   {
505                      duBindUnbindRlcToMacSap((Inst) RLC_UL_INST, ABND);
506                   }
507                }
508                else
509                {
510                   DU_LOG("\nDU_APP : BIND OF RLC UL TO MAC (RGU) SAP SUCCESSFUL");
511                   macCfgInst++;
512                   if(macCfgInst < DEFAULT_CELLS)
513                   {
514                      duBindUnbindRlcToMacSap((Inst) RLC_UL_INST, ABND);
515                   }
516                   else
517                   {
518                      duSendSchCfg();
519                   }
520                   break;
521                }
522             }
523
524       }
525    }
526    return ret;
527 }
528 /**************************************************************************
529  * @brief Function to handle Config Confirm from RLC UL
530  *
531  * @details
532  *
533  *      Function : duHdlRlcUlCfgComplete 
534  * 
535  *      Functionality:
536  *           Handles Config Confirm from RLC UL
537  *     
538  * @param[in]  Pst     *pst, Post structure of the primitive.     
539  * @param[in]  RlcMngmt *cfm, Unpacked primitive info received from RLC UL
540  * @return ROK     - success
541  *         RFAILED - failure
542  *
543  ***************************************************************************/
544 uint8_t duProcRlcUlCfgComplete(Pst *pst, RlcMngmt *cfm)
545 {
546    uint8_t ret;
547
548    DU_LOG("\nDU_APP : RLC UL Cfg Status %d", cfm->cfm.status);
549    if (cfm->cfm.status == LCM_PRIM_OK)
550    {
551       switch(cfm->hdr.elmId.elmnt)
552       {
553          case STGEN:
554             {
555                rlcUlCfg |= RLC_GEN_CFG;
556                break;
557             }
558          case STRGUSAP:
559             {
560                numRlcMacSaps++;
561                if(numRlcMacSaps == DEFAULT_CELLS)
562                {
563                   rlcUlCfg |= RLC_MAC_SAP_CFG;
564                   numRlcMacSaps = 0;
565                }
566                break;
567             }
568          case STUDXSAP:
569             {
570                rlcUlCfg |= RLC_UDX_SAP_CFG;
571                break;
572
573             }
574          default:
575             break;
576       }
577       DU_LOG("\nDU_APP : RLC UL Cfg Cfm received for the element %d ",cfm->hdr.elmId.elmnt);
578       if(rlcUlCfg == DU_RLC_UL_CONFIGURED)
579       {
580          rlcUlCfg = 0;
581          numRlcMacSaps = 0;
582          //Start configuration of RLC DL
583          duSendRlcDlCfg();
584
585       }
586    }
587    else
588    {
589       DU_LOG("\nDU_APP : Config confirm NOK from RLC UL");
590       ret = RFAILED;
591    }
592    return ret;
593 }
594
595 /**************************************************************************
596  * @brief Function to handle Config Confirm from RLC DL
597  *
598  * @details
599  *
600  *      Function : duHdlRlcDlCfgComplete 
601  * 
602  *      Functionality:
603  *           Handles Config Confirm from RLC DL
604  *     
605  * @param[in]  Pst     *pst, Post structure of the primitive.     
606  * @param[in]  RlcMngmt *cfm, Unpacked primitive info received from RLC DL
607  * @return ROK     - success
608  *         RFAILED - failure
609  *
610  ***************************************************************************/
611 uint8_t duProcRlcDlCfgComplete(Pst *pst, RlcMngmt *cfm)
612 {
613    DU_LOG("\nDU_APP : RLC DL Cfg Status %d", cfm->cfm.status);
614    if (cfm->cfm.status == LCM_PRIM_OK)
615    {
616       switch(cfm->hdr.elmId.elmnt)
617       {
618          case STGEN:
619             {
620                rlcDlCfg |= RLC_GEN_CFG;
621                break;
622             }
623          case STRGUSAP:
624             {
625                numRlcMacSaps++;
626                if(numRlcMacSaps == DEFAULT_CELLS)
627                {
628                   rlcDlCfg |= RLC_MAC_SAP_CFG;
629                   numRlcMacSaps = 0;
630                }
631                break;
632             }
633          case STUDXSAP:
634             {
635                rlcDlCfg |= RLC_UDX_SAP_CFG;
636                break;
637
638             }
639          default:
640             break;
641
642       }
643       DU_LOG("\nDU_APP : RLC DL Cfg Cfm received for the element %d ",cfm->hdr.elmId.elmnt);
644       if(rlcDlCfg == DU_RLC_DL_CONFIGURED)
645       {
646          rlcDlCfg = 0;
647          //Start configuration of MAC
648          duSendMacCfg();
649
650       }
651    }
652    else
653    {
654       DU_LOG("\nDU_APP : Config confirm NOK from RLC DL");
655    }
656    return ROK;
657 }
658
659 /**************************************************************************
660  * @brief Function to send configs to MAC
661  *
662  * @details
663  *
664  *      Function : duSendMacCfg 
665  * 
666  *      Functionality:
667  *           Initiates Configs towards MAC layer
668  *     
669  * @param[in]  void
670  * @return ROK     - success
671  *         RFAILED - failure
672  *
673  ***************************************************************************/
674 uint8_t duSendMacCfg()
675 {
676    duBuildMacGenCfg();
677    duBuildMacUsapCfg(RLC_UL_INST);
678    duBuildMacUsapCfg(RLC_DL_INST);
679
680    return ROK;
681 }
682
683 /**************************************************************************
684  * @brief Function to fill gen config required by MAC
685  *
686  * @details
687  *
688  *      Function : duBuildMacGenCfg 
689  * 
690  *      Functionality:
691  *           Initiates general Configs towards MAC
692  *     
693  * @param[in] void
694  * @return ROK     - success
695  *         RFAILED - failure
696  *
697  ***************************************************************************/
698 uint8_t duBuildMacGenCfg()
699 {
700    RgMngmt       rgMngmt;
701    RgGenCfg      *genCfg=NULLP;
702    Pst           pst;
703
704    DU_SET_ZERO(&pst, sizeof(Pst));
705    DU_SET_ZERO(&rgMngmt, sizeof(RgMngmt));
706
707    genCfg   = &(rgMngmt.t.cfg.s.genCfg);
708
709    /*----------- Fill General Configuration Parameters ---------*/
710    genCfg->mem.region = MAC_MEM_REGION;
711    genCfg->mem.pool   = MAC_POOL;
712    genCfg->tmrRes     = 10;
713    genCfg->numRguSaps = 2;
714
715    genCfg->lmPst.dstProcId = DU_PROC;
716    genCfg->lmPst.srcProcId = DU_PROC;
717    genCfg->lmPst.dstEnt    = ENTDUAPP;
718    genCfg->lmPst.dstInst   = 0;
719    genCfg->lmPst.srcEnt    = ENTMAC;
720    genCfg->lmPst.srcInst   = macCfgInst;
721    genCfg->lmPst.prior     = PRIOR0;
722    genCfg->lmPst.route     = RTESPEC;
723    genCfg->lmPst.region    = MAC_MEM_REGION;
724    genCfg->lmPst.pool      = MAC_POOL;
725    genCfg->lmPst.selector  = ODU_SELECTOR_LC;
726
727    /* Fill Header */
728    rgMngmt.hdr.msgType             = TCFG;
729    rgMngmt.hdr.msgLen              = 0;
730    rgMngmt.hdr.entId.ent           = ENTMAC;
731    rgMngmt.hdr.entId.inst          = (Inst)0;
732    rgMngmt.hdr.elmId.elmnt         = STGEN;
733    rgMngmt.hdr.seqNmb              = 0;
734    rgMngmt.hdr.version             = 0;
735    rgMngmt.hdr.transId             = 0;
736
737    rgMngmt.hdr.response.prior      = PRIOR0;
738    rgMngmt.hdr.response.route      = RTESPEC;
739    rgMngmt.hdr.response.mem.region = MAC_MEM_REGION;
740    rgMngmt.hdr.response.mem.pool   = MAC_POOL;
741    rgMngmt.hdr.response.selector   = ODU_SELECTOR_LC;
742
743    /* Fill Pst */
744    pst.selector  = ODU_SELECTOR_LC;
745    pst.srcEnt    = ENTDUAPP;
746    pst.dstEnt    = ENTMAC;
747    pst.dstInst   = macCfgInst;
748    pst.dstProcId = DU_PROC;
749    pst.srcProcId = DU_PROC;
750    pst.region = duCb.init.region;
751
752    DU_LOG("\nDU_APP : MAC Gen Cfg Req sent");
753
754    /* Send the request to MAC */
755    cmPkLrgCfgReq(&pst, &rgMngmt);
756
757    return ROK;
758 }
759
760 /**************************************************************************
761  * @brief Function to fill USAP config required by MAC
762  *
763  * @details
764  *
765  *      Function : duBuildMacUsapCfg 
766  * 
767  *      Functionality:
768  *           Initiates USAP Configs towards MAC
769  *     
770  * @param[in] SpId  Specifies if RLC UL or RLC DL instance 
771  * @return ROK     - success
772  *         RFAILED - failure
773  *
774  ***************************************************************************/
775 uint8_t duBuildMacUsapCfg(SpId sapId)
776 {
777    RgMngmt     rgMngmt;
778    RgUpSapCfg  *uSap = NULLP;
779    Pst         pst;
780
781    DU_SET_ZERO(&pst, sizeof(Pst));
782    DU_SET_ZERO(&rgMngmt, sizeof(RgMngmt));
783
784    uSap   = &(rgMngmt.t.cfg.s.rguSap);
785
786    uSap->mem.region = MAC_MEM_REGION;
787    uSap->mem.pool   = MAC_POOL;
788    uSap->suId       = 0;
789    uSap->spId       = sapId;
790    uSap->procId     = DU_PROC;
791    uSap->ent        = ENTRLC;
792    uSap->inst       = sapId;
793    uSap->prior      = PRIOR0;
794    uSap->route      = RTESPEC;
795    uSap->selector   = ODU_SELECTOR_LC ;
796
797    /* fill header */
798    rgMngmt.hdr.msgType             = TCFG;
799    rgMngmt.hdr.entId.ent           = ENTMAC;
800    rgMngmt.hdr.entId.inst          = (Inst)0;
801    rgMngmt.hdr.elmId.elmnt         = STRGUSAP;
802    rgMngmt.hdr.response.mem.region = MAC_MEM_REGION;
803    rgMngmt.hdr.response.mem.pool   = MAC_POOL;
804
805    /* fill pst */
806    pst.selector  = ODU_SELECTOR_LC;
807    pst.srcEnt    = ENTDUAPP;
808    pst.dstEnt    = ENTMAC;
809    pst.dstInst   = macCfgInst;
810    pst.dstProcId = DU_PROC;
811    pst.srcProcId = DU_PROC;
812    pst.region    = duCb.init.region;
813
814    DU_LOG("\nDU_APP : MAC Rgu USap Cfg Req sent");
815
816    /* Send the request to MAC */
817    cmPkLrgCfgReq(&pst, &rgMngmt);
818
819    return ROK;
820 }
821
822 /**************************************************************************
823  * @brief Function to handle Config Confirm from MAC
824  *
825  * @details
826  *
827  *      Function : duHdlMacCfgComplete 
828  * 
829  *      Functionality:
830  *           Handles Gen Config Confirm from MAC
831  *     
832  * @param[in]  Pst     *pst, Post structure of the primitive.     
833  * @param[in]  RgMngmt *cfm, Unpacked primitive info received from MAC
834  * @return ROK     - success
835  *         RFAILED - failure
836  *
837  ***************************************************************************/
838 uint8_t duHdlMacCfgComplete(Pst *pst, RgMngmt *cfm)
839 {
840    uint8_t ret = ROK;
841
842    if (cfm->cfm.status == LCM_PRIM_OK)
843    {
844       switch (cfm->hdr.elmId.elmnt)
845       {
846          case STGEN:
847             {
848                macCfg |= MAC_GEN_CFG;
849                break;
850             }
851          case STRGUSAP:
852             {
853                macCfg |= MAC_SAP_CFG;
854                numRlcMacSaps++;
855                break;
856             }
857          default:
858             break;
859       }
860       DU_LOG("\nDU_APP : MAC Cfg Cfm received for the element %d ",cfm->hdr.elmId.elmnt);
861       if(macCfg == MAC_CONFIGURED && numRlcMacSaps == MAX_MAC_SAP)
862       {
863          macCfg = 0;
864          DU_LOG("\nDU_APP : Completed sending Configs");
865          macCfgInst = 0;
866          duBindUnbindRlcToMacSap(RLC_DL_INST, ABND);
867       }
868
869    }
870    else
871    {
872       DU_LOG("\nDU_APP : Config confirm NOK from MAC");
873       ret = RFAILED;
874    }
875    return ret;
876 }
877
878 /**************************************************************************
879  * @brief Function to bind/unbind RLC to MAC SAP
880  *
881  * @details
882  *
883  *      Function : duBindUnbindRlcToMacSap 
884  * 
885  *      Functionality:
886  *           Initiates Bind/Unbind from RLC to MAC
887  *     
888  * @param[in] Inst   Specifies if RLC UL or RLC DL instance 
889  * @param[in] action Specifies if action is bind or unbind
890  * @return ROK     - success
891  *         RFAILED - failure
892  *
893  ***************************************************************************/
894 uint8_t duBindUnbindRlcToMacSap(uint8_t inst, uint8_t action)
895 {
896    RlcCntrl  *cntrl = NULLP;
897    RlcMngmt  rlcMngmt;
898    Pst      pst;
899
900
901    DU_SET_ZERO(&rlcMngmt, sizeof(RlcMngmt));
902    DU_SET_ZERO(&pst, sizeof(Pst));
903
904    if (action == ABND)
905    {
906       DU_LOG("\nDU_APP : Cntrl Req to RLC inst %d to bind MAC sap", inst);
907    }
908    else
909    {
910       DU_LOG("\nDU_APP : Cntrl Req to RLC inst %d to unbind MAC sap", inst);
911    }
912    cntrl = &(rlcMngmt.t.cntrl);
913
914    cntrl->action            =  action;
915    cntrl->subAction         =  DU_ZERO_VAL;
916    cntrl->s.sapCntrl.suId   =  macCfgInst;
917    cntrl->s.sapCntrl.spId   =  inst;
918
919    /* Fill header */
920    rlcMngmt.hdr.msgType             = TCNTRL;
921    rlcMngmt.hdr.entId.ent           = ENTRLC;
922    rlcMngmt.hdr.entId.inst          = inst;
923    rlcMngmt.hdr.elmId.elmnt         = 186; /* ambiguous defines in lkw.h and lrg.h so direct hardcoded*/
924    rlcMngmt.hdr.response.mem.region = (inst == RLC_UL_INST) ?
925       RLC_UL_MEM_REGION:RLC_DL_MEM_REGION;
926    rlcMngmt.hdr.response.mem.pool   = RLC_POOL;
927
928    /* Fill pst */
929    pst.selector  = ODU_SELECTOR_LC;
930    pst.srcEnt    = ENTDUAPP;
931    pst.dstEnt    = ENTRLC;
932    pst.dstProcId = DU_PROC;
933    pst.dstInst   = inst;
934    pst.srcProcId = DU_PROC;
935    pst.region    = duCb.init.region;
936
937    cmPkLkwCntrlReq(&pst, &rlcMngmt);
938
939    return ROK;
940 }
941 /*******************************************************************
942  *
943  * @brief Handles SCTP notifications
944  *
945  * @details
946  *
947  *    Function : duSctpNtfyHdl
948  *
949  *    Functionality:
950  *         Handles SCTP notification
951  *
952  * @params[in] Message Buffer
953  *             SCTP notification
954  *
955  * @return ROK     - success
956  *         RFAILED - failure
957  *
958  * ****************************************************************/
959
960 uint8_t duSctpNtfyHdl(Buffer *mBuf, CmInetSctpNotification *ntfy)
961 {
962    if(f1Params.assocId == ntfy->u.assocChange.assocId)
963    {
964       if(BuildAndSendF1SetupReq() != ROK)
965       {
966          return RFAILED;
967       }
968    }
969    else if(ricParams.assocId == ntfy->u.assocChange.assocId)
970    {
971       if(BuildAndSendE2SetupReq() != ROK)
972       {
973          return RFAILED;
974       }
975    }
976    else
977    {
978       DU_LOG("\nDU_APP : Invalid assocId %d received", ntfy->u.assocChange.assocId);
979       return RFAILED;
980    }
981    return ROK;
982 }
983
984 /*******************************************************************
985  *
986  * @brief  Fills Pst struct for ENTEGTP
987  *
988  * @details
989  *
990  *    Function : duFillEgtpPst
991  *
992  *    Functionality:
993  *       Fills Pst struct for ENTEGTP
994  *
995  * @params[in] 
996  * @return ROK     - success
997  *         RFAILED - failure
998  *
999  * ****************************************************************/
1000 uint8_t duFillEgtpPst(Pst *pst, Event event)
1001 {
1002    memset(pst, 0, sizeof(Pst));
1003    pst->srcEnt = (Ent)ENTDUAPP;
1004    pst->srcInst = (Inst)DU_INST;
1005    pst->srcProcId = DU_PROC;
1006    pst->dstEnt = (Ent)ENTEGTP;
1007    pst->dstInst = (Inst)EGTP_INST;
1008    pst->dstProcId = pst->srcProcId;
1009    pst->event = event;
1010    pst->selector = ODU_SELECTOR_LC;
1011    pst->pool= DU_POOL;
1012
1013    return ROK;
1014 }
1015
1016
1017 /*******************************************************************
1018  *
1019  * @brief  Function to configure EGTP
1020  *
1021  * @details
1022  *
1023  *    Function : duBuildEgtpCfgReq
1024  *
1025  *    Functionality:
1026  *       Function to configure EGTP
1027  *
1028  * @params[in] 
1029  * @return ROK     - success
1030  *         RFAILED - failure
1031  *
1032  * ****************************************************************/
1033
1034 uint8_t duBuildEgtpCfgReq()
1035 {
1036    Pst pst;
1037    EgtpConfig egtpCfg;
1038
1039    DU_LOG("\nDU_APP : Sending EGTP config request");
1040
1041    memset(&egtpCfg, 0, sizeof(EgtpConfig));
1042    memcpy(&egtpCfg, &duCfgParam.egtpParams, sizeof(EgtpConfig));
1043
1044    duFillEgtpPst(&pst, EVTCFGREQ);
1045    packEgtpCfgReq(&pst, egtpCfg);
1046
1047    return ROK;
1048 }
1049
1050 /*******************************************************************
1051  *
1052  * @brief  Function to configure EGTP
1053  *
1054  * @details
1055  *
1056  *    Function : duBuildEgtpCfgReq
1057  *
1058  *    Functionality:
1059  *       Function to configure EGTP
1060  *
1061  * @params[in] 
1062  * @return ROK     - success
1063  *         RFAILED - failure
1064  *
1065  * ****************************************************************/
1066 uint8_t duHdlEgtpCfgComplete(CmStatus cfm)
1067 {
1068    uint8_t ret = ROK;
1069
1070    if(cfm.status == LCM_PRIM_OK)
1071    {
1072       DU_LOG("\nDU_APP : EGTP configuraton complete");
1073 #ifdef EGTP_TEST
1074       duSendEgtpSrvOpenReq();
1075 #endif
1076    }
1077    else
1078    {
1079       DU_LOG("\nDU_APP : EGTP configuraton failed");
1080       ret = RFAILED;
1081    }
1082
1083    return (ret);
1084 }
1085
1086 /*******************************************************************
1087  *
1088  * @brief  Sends server open request to EGTP
1089  *
1090  * @details
1091  *
1092  *    Function : duSendEgtpSrvOpenReq
1093  *
1094  *    Functionality:
1095  *       Sends server open request to EGTP
1096  *
1097  * @params[in] 
1098  * @return ROK     - success
1099  *         RFAILED - failure
1100  *
1101  * ****************************************************************/
1102
1103 uint8_t duSendEgtpSrvOpenReq()
1104 {
1105    Pst pst;
1106
1107    DU_LOG("\nDU_APP : Sending EGTP server open request");
1108
1109    duFillEgtpPst(&pst, EVTSRVOPENREQ);
1110    packEgtpSrvOpenReq(&pst);
1111
1112    return ROK;
1113 }
1114
1115 /*******************************************************************
1116  *
1117  * @brief Handles server open confirmation
1118  *
1119  * @details
1120  *
1121  *    Function : duHdlEgtpSrvOpenComplete
1122  *
1123  *    Functionality:
1124  *        Handles server open confirmation
1125  *
1126  * @params[in] 
1127  * @return ROK     - success
1128  *         RFAILED - failure
1129  *
1130  *****************************************************************/
1131
1132 uint8_t duHdlEgtpSrvOpenComplete(CmStatus cfm)
1133 {
1134    uint8_t ret = ROK;
1135
1136    if(cfm.status == LCM_PRIM_OK)
1137    {
1138       DU_LOG("\nDU_APP : EGTP server opened successfully");
1139 #ifdef EGTP_TEST
1140       duSendEgtpTnlMgmtReq(EGTP_TNL_MGMT_ADD, EGTP_LCL_TEID, EGTP_REM_TEID);
1141 #endif
1142    }
1143    else
1144    {
1145       DU_LOG("\nDU_APP : EGTP server opening failed");
1146       ret = RFAILED;
1147    }
1148
1149    return (ret);
1150 }
1151
1152 /*******************************************************************
1153  *
1154  * @brief Sends tunnel management request
1155  *
1156  * @details
1157  *
1158  *    Function : duSendEgtpTnlMgmtReq 
1159  *
1160  *    Functionality:
1161  *        Builds and sends tunnel management request to EGTP
1162  *
1163  * @params[in] Action
1164  *             Local tunnel endpoint id
1165  *             Remote tunnel endpoint id 
1166  * @return ROK     - success
1167  *         RFAILED - failure
1168  *
1169  * ****************************************************************/
1170
1171 uint8_t duSendEgtpTnlMgmtReq(uint8_t action, uint32_t lclTeid, uint32_t remTeid)
1172 {
1173    Pst pst;
1174    EgtpTnlEvt tnlEvt;
1175
1176    tnlEvt.action = action;
1177    tnlEvt.lclTeid = lclTeid;
1178    tnlEvt.remTeid = remTeid;
1179
1180    DU_LOG("\nDU_APP : Sending EGTP tunnel management request");
1181
1182    duFillEgtpPst(&pst, EVTTNLMGMTREQ);
1183    packEgtpTnlMgmtReq(&pst, tnlEvt);
1184
1185    return ROK;
1186 }
1187
1188 /*******************************************************************
1189  *
1190  * @brief Handles Tunnel management confirm 
1191  *
1192  * @details
1193  *
1194  *    Function : duHdlEgtpTnlMgmtCfm
1195  *
1196  *    Functionality:
1197  *      Handles tunnel management confirm received from Egtp
1198  *
1199  * @params[in] Tunnel Event  
1200  * @return ROK     - success
1201  *         RFAILED - failure
1202  *
1203  * ****************************************************************/
1204 uint8_t duHdlEgtpTnlMgmtCfm(EgtpTnlEvt tnlEvtCfm)
1205 {
1206    uint8_t ret = ROK;
1207
1208    if(tnlEvtCfm.cfmStatus.status == LCM_PRIM_OK)
1209    {
1210       DU_LOG("\nDU_APP : Tunnel management confirm OK");
1211    }
1212    else
1213    {
1214       DU_LOG("\nDU_APP : Tunnel management failed");
1215       ret = RFAILED;
1216    }
1217
1218    return (ret);
1219 }
1220
1221 uint8_t duSendEgtpDatInd(Buffer *mBuf)
1222 {
1223    EgtpMsg  egtpMsg;
1224
1225    /* Fill EGTP header */
1226    egtpMsg.msgHdr.msgType = EGTPU_MSG_GPDU;
1227    egtpMsg.msgHdr.nPdu.pres = FALSE;
1228    egtpMsg.msgHdr.seqNum.pres = FALSE;
1229    egtpMsg.msgHdr.extHdr.udpPort.pres = FALSE;
1230    egtpMsg.msgHdr.extHdr.pdcpNmb.pres = FALSE;
1231    egtpMsg.msgHdr.teId = 1;
1232    egtpMsg.msg = mBuf;
1233
1234    egtpHdlDatInd(egtpMsg);
1235
1236    return ROK;
1237
1238 }
1239
1240 #ifdef EGTP_TEST
1241 /*******************************************************************
1242  *
1243  * @brief Simulate UL Data for intial test
1244  *
1245  * @details
1246  *
1247  *    Function : duSendEgtpTestData
1248  *
1249  *    Functionality:
1250  *      Simulate UL data for initial test
1251  *
1252  * @params[in] 
1253  * @return ROK     - success
1254  *         RFAILED - failure
1255  *
1256  * ****************************************************************/
1257 uint8_t duSendEgtpTestData()
1258 {
1259    char data[30] = "This is EGTP data from DU";
1260    int datSize = 30;
1261
1262    Buffer   *mBuf;
1263
1264    if(ODU_GET_MSG_BUF(DU_APP_MEM_REGION, DU_POOL, &mBuf) == ROK)
1265    {
1266       if(ODU_ADD_POST_MSG_MULT((Data *)data, datSize, mBuf) != ROK)
1267       {
1268          DU_LOG("\nDU_APP : ODU_ADD_POST_MSG_MULT failed");
1269          ODU_PUT_MSG_BUF(mBuf);
1270          return RFAILED;
1271       }
1272    }
1273    else
1274    {
1275       DU_LOG("\nDU_APP : Failed to allocate memory");
1276       return RFAILED;
1277    }
1278
1279    /* filling IPv4 header */ 
1280    CmIpv4Hdr ipv4Hdr;
1281    MsgLen    mLen;
1282
1283    mLen = 0;
1284    ODU_GET_MSG_LEN(mBuf, &mLen);
1285
1286    memset(&ipv4Hdr, 0, sizeof(CmIpv4Hdr));
1287    ipv4Hdr.length = CM_IPV4_HDRLEN + mLen;
1288    ipv4Hdr.hdrVer = 0x45;
1289    ipv4Hdr.proto = 1;
1290    ipv4Hdr.srcAddr = CM_INET_NTOH_UINT32(duCfgParam.egtpParams.localIp.ipV4Addr);
1291    ipv4Hdr.destAddr = CM_INET_NTOH_UINT32(duCfgParam.egtpParams.destIp.ipV4Addr);
1292
1293    /* Packing IPv4 header into buffer */
1294    uint8_t          ret, cnt, idx;
1295    Data         revPkArray[CM_IPV4_HDRLEN];
1296    Data         pkArray[CM_IPV4_HDRLEN];
1297
1298    /* initialize locals */
1299    cnt = 0;
1300    memset(revPkArray, 0, CM_IPV4_HDRLEN);
1301    memset(pkArray, 0, CM_IPV4_HDRLEN);
1302
1303    /* Pack Header Version */
1304    pkArray[cnt++] = ipv4Hdr.hdrVer;
1305
1306    /* Pack TOS */
1307    pkArray[cnt++] = ipv4Hdr.tos;
1308
1309    pkArray[cnt++] = (Data)GetHiByte(ipv4Hdr.length);
1310    pkArray[cnt++] = (Data)GetLoByte(ipv4Hdr.length);
1311
1312    /* Pack Id */
1313    pkArray[cnt++] = (Data) GetHiByte(ipv4Hdr.id);
1314    pkArray[cnt++] = (Data) GetLoByte(ipv4Hdr.id);
1315
1316    /* Pack Offset */
1317    pkArray[cnt++] = (Data)GetHiByte(ipv4Hdr.off);
1318    pkArray[cnt++] = (Data)GetLoByte(ipv4Hdr.off);
1319
1320    /* Pack TTL */
1321    pkArray[cnt++] = ipv4Hdr.ttl;
1322
1323    /* Pack Protocol */
1324    pkArray[cnt++] = ipv4Hdr.proto;
1325
1326    /* Pack Checksum */
1327    pkArray[cnt++] = (Data)GetHiByte(ipv4Hdr.chkSum);
1328    pkArray[cnt++] = (Data)GetLoByte(ipv4Hdr.chkSum);
1329
1330    /* Pack Source Address */
1331    pkArray[cnt++] = (Data)GetHiByte(GetHiWord(ipv4Hdr.srcAddr));
1332    pkArray[cnt++] = (Data)GetLoByte(GetHiWord(ipv4Hdr.srcAddr));
1333    pkArray[cnt++] = (Data)GetHiByte(GetLoWord(ipv4Hdr.srcAddr));
1334    pkArray[cnt++] = (Data)GetLoByte(GetLoWord(ipv4Hdr.srcAddr));
1335
1336    /* Pack Destination Address */
1337    pkArray[cnt++] = (Data)GetHiByte(GetHiWord(ipv4Hdr.destAddr));
1338    pkArray[cnt++] = (Data)GetLoByte(GetHiWord(ipv4Hdr.destAddr));
1339    pkArray[cnt++] = (Data)GetHiByte(GetLoWord(ipv4Hdr.destAddr));
1340    pkArray[cnt++] = (Data)GetLoByte(GetLoWord(ipv4Hdr.destAddr));
1341
1342    for (idx = 0;  idx < CM_IPV4_HDRLEN;  idx++)
1343       revPkArray[idx] = pkArray[CM_IPV4_HDRLEN - idx -1];
1344
1345    /* this function automatically reverses revPkArray */
1346    ret = ODU_ADD_PRE_MSG_MULT(revPkArray, (MsgLen)cnt, mBuf);
1347
1348    duSendEgtpDatInd(mBuf);
1349
1350    return ROK;
1351 }
1352 #endif /* EGTP_TEST */
1353
1354
1355 /**************************************************************************
1356  * @brief Function to send configs to SCH
1357  *
1358  * @details
1359  *
1360  *      Function : duSendSchCfg 
1361  * 
1362  *      Functionality:
1363  *           Sends general config to Scheduler via MAC layer
1364  *     
1365  * @param[in]  void
1366  * @return ROK     - success
1367  *         RFAILED - failure
1368  *
1369  ***************************************************************************/
1370 uint8_t duSendSchCfg()
1371 {
1372    RgMngmt       rgMngmt;
1373    RgSchInstCfg  *cfg = NULLP;
1374    Pst           pst;
1375
1376    DU_SET_ZERO(&pst, sizeof(Pst));
1377    DU_SET_ZERO(&rgMngmt, sizeof(RgMngmt));
1378
1379    cfg = &(rgMngmt.t.cfg.s.schInstCfg);
1380
1381    /* Filling of Instance Id */
1382    cfg->instId = DEFAULT_CELLS + 1;
1383    /* Filling of Gen config */
1384    cfg->genCfg.mem.region = MAC_MEM_REGION;
1385    cfg->genCfg.mem.pool = MAC_POOL;
1386    cfg->genCfg.tmrRes = 10;
1387
1388 #ifdef LTE_ADV
1389    cfg->genCfg.forceCntrlSrbBoOnPCel = FALSE;
1390    cfg->genCfg.isSCellActDeactAlgoEnable = TRUE;
1391 #endif/*LTE_ADV*/
1392    cfg->genCfg.startCellId     = 1;
1393    cfg->genCfg.lmPst.dstProcId = DU_PROC;
1394    cfg->genCfg.lmPst.srcProcId = DU_PROC;
1395    cfg->genCfg.lmPst.dstEnt    = ENTDUAPP;
1396    cfg->genCfg.lmPst.dstInst   = DU_INST;
1397    cfg->genCfg.lmPst.srcEnt    = ENTMAC;
1398    cfg->genCfg.lmPst.srcInst   = DEFAULT_CELLS + 1;
1399    cfg->genCfg.lmPst.prior     = PRIOR0;
1400    cfg->genCfg.lmPst.route     = RTESPEC;
1401    cfg->genCfg.lmPst.region    = MAC_MEM_REGION;
1402    cfg->genCfg.lmPst.pool      = MAC_POOL;
1403    cfg->genCfg.lmPst.selector  = ODU_SELECTOR_LC;
1404
1405    /* Fill Header */
1406    rgMngmt.hdr.msgType             = TCFG;
1407    rgMngmt.hdr.entId.ent           = ENTMAC;
1408    rgMngmt.hdr.entId.inst          = DU_INST;
1409    rgMngmt.hdr.elmId.elmnt         = STSCHINST;
1410    rgMngmt.hdr.response.mem.region = MAC_MEM_REGION;
1411    rgMngmt.hdr.response.mem.pool   = MAC_POOL;
1412
1413    /* Fill Pst */
1414    pst.selector  = ODU_SELECTOR_LC;
1415    pst.srcEnt    = ENTDUAPP;
1416    pst.dstEnt    = ENTMAC;
1417    pst.dstProcId = DU_PROC;
1418    pst.srcProcId = DU_PROC;
1419    pst.srcInst   = DU_INST;
1420    pst.dstInst   = 0;
1421    pst.region    = duCb.init.region;
1422    pst.event    = (Event) EVTMACSCHGENCFGREQ;
1423
1424    DU_LOG("\nDU_APP : MAC Sch Cfg sent");
1425
1426    /* Send the request to MAC */
1427    cmPkLrgSchCfgReq(&pst, &rgMngmt);
1428
1429    return ROK;
1430 }
1431
1432
1433 /**************************************************************************
1434  * @brief Function to configure SCTP params and 
1435  *  responsible for F1 and E2 interfaces
1436  *
1437  * @details
1438  *
1439  *      Function : duLayerConfigComplete
1440  * 
1441  *      Functionality:
1442  *           Configures SCTP Params and responsible for handling
1443  *           F1 and E2 interface.
1444  *     
1445  * @param[in]  void
1446  * @return ROK     - success
1447  *         RFAILED - failure
1448  *
1449  ***************************************************************************/
1450 uint8_t duLayerConfigComplete()
1451 {
1452    uint8_t ret = ROK;
1453
1454    DU_LOG("\nDU_APP : Configuring all Layer is complete");
1455
1456    if((ret = duSctpCfgReq(duCfgParam.sctpParams)) != ROK)
1457    {
1458       DU_LOG("\nDU_APP : Failed configuring Sctp Params");
1459       ret = RFAILED;
1460    }
1461    if((ret = duSctpAssocReq(F1_INTERFACE)) != ROK)
1462    {
1463       DU_LOG("\nDU_APP : Failed to send AssocReq F1");
1464       ret = RFAILED;
1465    }
1466    if((ret = duSctpAssocReq(E2_INTERFACE)) != ROK)
1467    {
1468       DU_LOG("\nDU_APP : Failed to send AssocReq E2");
1469       ret = RFAILED;
1470    }
1471
1472    return (ret); 
1473
1474
1475 /**************************************************************************
1476  * @brief Function to handle  SCH Config Confirm from MAC
1477  *
1478  * @details
1479  *
1480  *      Function : duHdlSchCfgComplete 
1481  * 
1482  *      Functionality:
1483  *           Handles Scheduler Gen Config Confirm from MAC
1484  *     
1485  * @param[in]  Pst     *pst, Post structure of the primitive.     
1486  * @param[in]  RgMngmt *cfm, Unpacked primitive info received from MAC
1487  * @return ROK     - success
1488  *         RFAILED - failure
1489  *
1490  ***************************************************************************/
1491 uint8_t duHdlSchCfgComplete(Pst *pst, RgMngmt *cfm)
1492 {
1493    if (cfm->cfm.status == LCM_PRIM_OK)
1494    {
1495       switch (cfm->hdr.elmId.elmnt)
1496       {
1497          case STSCHINST:
1498             {
1499                DU_LOG("\nDU_APP : Received SCH CFG CFM at DU APP");
1500                break;
1501             }
1502          default:
1503             break;
1504       }
1505    }
1506    duLayerConfigComplete();
1507    duBuildEgtpCfgReq();
1508    return ROK;
1509 }
1510
1511 /*******************************************************************
1512  *
1513  * @brief Sends Slot indication to EGTP
1514  *
1515  * @details
1516  *
1517  *    Function : duSendEgtpSlotInd
1518  *
1519  *    Functionality:
1520  *     Sends Slot indication to EGTP
1521  *
1522  * @params[in] 
1523  * @return ROK     - success
1524  *         RFAILED - failure
1525  *
1526  * ****************************************************************/
1527 uint8_t duSendEgtpSlotInd()
1528 {
1529    Pst pst;
1530
1531    duFillEgtpPst(&pst, EVTSLOTIND);
1532    packEgtpSlotInd(&pst);
1533
1534    return ROK;
1535
1536 }
1537
1538 /**************************************************************************
1539  * @brief Function to fill and send MacCellconfig
1540  *
1541  * @details
1542  *
1543  *      Function : duBuildAndSendMacCellCfg 
1544  * 
1545  *      Functionality:
1546  *           Initiates MAC Configs towards MAC
1547  *     
1548  * @param[in]cell id
1549  * @return ROK     - success
1550  *         RFAILED - failure
1551  *
1552  ***************************************************************************/
1553 uint8_t duBuildAndSendMacCellCfg(uint16_t cellId)
1554 {
1555    Pst pst;
1556    MacCellCfg *duMacCellCfg = NULLP;
1557
1558    DU_ALLOC_SHRABL_BUF(duMacCellCfg, sizeof(MacCellCfg));
1559    if(duMacCellCfg == NULLP)
1560    {
1561       return RFAILED;
1562    }
1563
1564    /* store the address in the duCellCb so that we can free on confirm msg */
1565    duCb.actvCellLst[cellId-1]->duMacCellCfg = duMacCellCfg;
1566
1567    /* copy the mac config structure from duCfgParams */
1568    memcpy(duMacCellCfg,&duCfgParam.macCellCfg,sizeof(MacCellCfg));
1569
1570    /* Fill Pst */
1571    FILL_PST_DUAPP_TO_MAC(pst, EVENT_MAC_CELL_CONFIG_REQ);
1572
1573    /* Send MAC cell config to MAC */
1574    return (*packMacCellCfgOpts[pst.selector])(&pst, duMacCellCfg);
1575 }
1576
1577 /**************************************************************************
1578  * @brief Function to Handle MAC cell config confirm
1579  *
1580  * @details
1581  *
1582  *      Function : duHandleMacCellCfgCfm 
1583  * 
1584  *      Functionality:
1585  *           Initiates general Configs towards MAC
1586  *     
1587  * @param[in] void
1588  * @return ROK     - success
1589  *         RFAILED - failure
1590  *
1591  ***************************************************************************/
1592 uint8_t  duHandleMacCellCfgCfm(Pst *pst, MacCellCfgCfm *macCellCfgCfm)
1593 {
1594    uint8_t  actvCellIdx  = 0;
1595    uint8_t  ret          = ROK;
1596
1597    for(actvCellIdx = 0; actvCellIdx < MAX_NUM_CELL; actvCellIdx++)
1598    {
1599       if(macCellCfgCfm->cellId == duCb.actvCellLst[actvCellIdx]->cellId)
1600       {
1601          duCb.actvCellLst[actvCellIdx]->duMacCellCfg = NULLP;
1602       }
1603    }
1604    if(macCellCfgCfm->rsp == ROK)
1605    {
1606       /* Build and send GNB-DU config update */
1607       ret = BuildAndSendDUConfigUpdate();
1608
1609       /* Build and Send Cell Start Req to MAC */
1610       ret = duBuildAndSendMacCellStartReq();
1611    }
1612    else
1613    {
1614       /* TODO : Action to be taken if cell configuration fails. 
1615        * Should CU be informed? */
1616
1617       DU_LOG("\nMac cell cfg failed");
1618       ret = RFAILED;
1619    }
1620    return ret;
1621 }
1622
1623 /*******************************************************************
1624  *
1625  * @brief Handles slot indication from MAC
1626  *
1627  * @details
1628  *
1629  *    Function : duHandleSlotInd
1630  *
1631  *    Functionality:
1632  *      Handles slot indication from MAC
1633  *
1634  * @params[in] Post structure pointer
1635  *             Slot Info pointer
1636  * @return ROK     - success
1637  *         RFAILED - failure
1638  *
1639  * ****************************************************************/
1640 uint8_t duHandleSlotInd(Pst *pst, SlotIndInfo *slotInfo)
1641 {
1642    DuCellCb *cellCb = NULLP;
1643
1644    if(slotInfo->cellId <=0 || slotInfo->cellId > MAX_NUM_CELL)
1645    {
1646       DU_LOG("\nDU APP : Invalid Cell Id %d in duHandleSlotInd()", slotInfo->cellId);
1647       return RFAILED;
1648    }
1649
1650    if(duGetCellCb(slotInfo->cellId, &cellCb) != ROK)
1651       return RFAILED;
1652
1653    if(!cellCb->firstSlotIndRcvd)
1654    {
1655       DU_LOG("\nDU APP : Slot Indication received");
1656       cellCb->firstSlotIndRcvd = true;
1657       if((cellCb != NULL) && (cellCb->cellStatus == ACTIVATION_IN_PROGRESS))
1658       {
1659          DU_LOG("\nDU APP : 5G-NR Cell %d is UP", slotInfo->cellId);
1660          cellCb->cellStatus = ACTIVATED;
1661
1662 #ifdef O1_ENABLE
1663     DU_LOG("\nDU APP : Raise cell UP alarm for cell id=%d", slotInfo->cellId);
1664     raiseCellAlrm(CELL_UP_ALARM_ID, slotInfo->cellId);
1665 #endif
1666       }
1667    }
1668
1669    /* TODO : Slot Indication to be moved out of EGTP_TEST when
1670     * data path is established */
1671 #ifdef EGTP_TEST
1672    duSendEgtpSlotInd();    
1673 #endif
1674
1675    if((pst->selector == ODU_SELECTOR_LWLC) || (pst->selector == ODU_SELECTOR_TC)) 
1676       DU_FREE_SHRABL_BUF(pst->region, pst->pool, slotInfo, sizeof(SlotIndInfo));
1677    return ROK;
1678 }
1679
1680 /*******************************************************************
1681  *
1682  * @brief Builds and sends cell start request to MAC
1683  *
1684  * @details
1685  *
1686  *    Function : duBuildAndSendMacCellStartReq
1687  *
1688  *    Functionality:
1689  *       Builds and sends cell start request to MAC
1690  *
1691  * @params[in] 
1692  * @return ROK     - success
1693  *         RFAILED - failure
1694  *
1695  * ****************************************************************/
1696 uint8_t duBuildAndSendMacCellStartReq()
1697 {
1698    Pst pst;
1699    MacCellStartInfo *cellStartInfo = NULL;
1700
1701    DU_LOG("\nDU APP : Building and Sending cell start request to MAC");
1702
1703    /* Send Cell Start Request to MAC */
1704    DU_ALLOC_SHRABL_BUF(cellStartInfo, sizeof(MacCellStartInfo));
1705    if(!cellStartInfo)
1706    {
1707       DU_LOG("\nDU APP : Memory alloc failed while building cell start request");
1708       return RFAILED;
1709    }
1710
1711    for(uint8_t id = 0; id < duCb.numActvCells; id++) 
1712    {
1713       if(duCb.actvCellLst[id])
1714       {
1715          duCb.actvCellLst[id]->firstSlotIndRcvd = FALSE;
1716          cellStartInfo->cellId = duCb.actvCellLst[id]->cellId;
1717
1718          /* Fill Pst */
1719          FILL_PST_DUAPP_TO_MAC(pst, EVENT_MAC_CELL_START_REQ);
1720
1721          return (*packMacCellStartReqOpts[pst.selector])(&pst, cellStartInfo);
1722       }
1723    }
1724    return ROK;
1725 }
1726
1727 /*******************************************************************
1728  *
1729  * @brief Builds and sends cell stop request to MAC
1730  *
1731  * @details
1732  *
1733  *    Function : duBuildAndSendMacCellStopReq 
1734  *
1735  *    Functionality:
1736  *       Builds and sends cell stop request to MAC
1737  *
1738  * @params[in] 
1739  * @return ROK     - success
1740  *         RFAILED - failure
1741  *
1742  * ****************************************************************/
1743 uint8_t duBuildAndSendMacCellStopReq()
1744 {
1745    Pst pst;
1746    MacCellStopInfo *cellStopInfo = NULL;
1747
1748    DU_LOG("\nDU APP : Building and Sending cell stop request to MAC");
1749
1750    /* Send Cell Stop Request to MAC */
1751    DU_ALLOC_SHRABL_BUF(cellStopInfo, sizeof(MacCellStopInfo));
1752    if(!cellStopInfo)
1753    {
1754       DU_LOG("\nDU APP : Memory alloc failed while building cell stop request");
1755       return RFAILED;
1756    }
1757    cellStopInfo->cellId = duCb.actvCellLst[0]->cellId;
1758
1759    /* Fill Pst */
1760    FILL_PST_DUAPP_TO_MAC(pst, EVENT_MAC_CELL_STOP_REQ);
1761
1762    return (*packMacCellStopReqOpts[pst.selector])(&pst, cellStopInfo);
1763 }
1764
1765 /*******************************************************************
1766  *
1767  * @brief Handles stop indication from MAC
1768  *
1769  * @details
1770  *
1771  *    Function : duHandleStopInd
1772  *
1773  *    Functionality:
1774  *      Handles stop indication from MAC
1775  *
1776  * @params[in] Post structure pointer
1777  * @return ROK     - success
1778  *         RFAILED - failure
1779  *
1780  * ****************************************************************/
1781 uint8_t duHandleStopInd(Pst *pst, MacCellStopInfo *cellStopId)
1782 {
1783    DuCellCb *cellCb = NULLP;
1784  
1785    if(cellStopId->cellId <=0 || cellStopId->cellId > MAX_NUM_CELL)
1786    {
1787       DU_LOG("\nDU APP : Invalid Cell Id %d in duHandleStopInd()", cellStopId->cellId);
1788    }
1789
1790    if(duGetCellCb(cellStopId->cellId, &cellCb) != ROK)
1791       return RFAILED;
1792
1793    if(cellCb->firstSlotIndRcvd)
1794    {
1795       cellCb->firstSlotIndRcvd = false;
1796       if((cellCb->cellStatus == ACTIVATED))
1797       {
1798          DU_LOG("\nDU APP : 5G-NR Cell %d is DOWN", cellStopId->cellId);
1799          cellCb->cellStatus = DELETION_IN_PROGRESS;
1800
1801 #ifdef O1_ENABLE
1802        DU_LOG("\nDU APP : Raise cell down alarm for cell id=%d", cellStopId->cellId);
1803        raiseCellAlrm(CELL_DOWN_ALARM_ID, cellStopId->cellId);
1804 #endif
1805       }
1806    }
1807    if((pst->selector == ODU_SELECTOR_LWLC) || (pst->selector == ODU_SELECTOR_TC))
1808       DU_FREE_SHRABL_BUF(MAC_MEM_REGION, pst->pool, cellStopId, sizeof(MacCellStopInfo));
1809
1810    cellCb->cellStatus = CELL_OUT_OF_SERVICE; //TODO: cell status must be set to OOS after all UE and cell cleanup which is not
1811                                              //supported now
1812
1813
1814    return ROK;
1815 }
1816
1817 /*******************************************************************
1818  *
1819  * @brief Handles slot indication from MAC
1820  *
1821  * @details
1822  *
1823  *    Function : duHandleUlCcchInd
1824  *
1825  *    Functionality:
1826  *      Handles UL CCCH indication from MAC
1827  *
1828  * @params[in] Post structure pointer
1829  *             UL CCCH Ind pointer
1830  * @return ROK     - success
1831  *         RFAILED - failure
1832  *
1833  * ****************************************************************/
1834 uint8_t duHandleUlCcchInd(Pst *pst, UlCcchIndInfo *ulCcchIndInfo)
1835 {
1836
1837    DU_LOG("\nDU APP : UL CCCH Indication received");
1838
1839    return (duProcUlCcchInd(ulCcchIndInfo));
1840 }
1841
1842 /*******************************************************************
1843  *
1844  * @brief Process UL RRC Message from RLC
1845  *
1846  * @details
1847  *
1848  *    Function : DuProcRlcUlRrcMsgTrans
1849  *
1850  *    Functionality: Process UL RRC Message from RLC
1851  *
1852  * @params[in] Post structure
1853  *             UL RRC Message Info
1854  * @return ROK     - success
1855  *         RFAILED - failure
1856  *
1857  * ****************************************************************/
1858 uint8_t DuProcRlcUlRrcMsgTrans(Pst *pst, RlcUlRrcMsgInfo *ulRrcMsgInfo)
1859 {
1860    DuCellCb *cellCb = NULLP;
1861    DuUeCb   ueCb;
1862   
1863    if(duGetCellCb(ulRrcMsgInfo->cellId, &cellCb) != ROK)
1864       return RFAILED;
1865    
1866    ueCb = cellCb->ueCb[ulRrcMsgInfo->ueIdx -1];
1867
1868
1869    BuildAndSendULRRCMessageTransfer(ueCb, ulRrcMsgInfo->lcId, ulRrcMsgInfo->msgLen, \
1870       ulRrcMsgInfo->rrcMsg);
1871
1872    DU_FREE_SHRABL_BUF(pst->region, pst->pool, ulRrcMsgInfo->rrcMsg, ulRrcMsgInfo->msgLen);
1873    DU_FREE_SHRABL_BUF(pst->region, pst->pool, ulRrcMsgInfo, sizeof(RlcUlRrcMsgInfo));
1874    return ROK;
1875 }
1876
1877 /*******************************************************************
1878 *
1879 * @brief Process RRC delivery report from RLC
1880 *
1881 * @details
1882 *
1883 *    Function : DuProcRlcRrcDeliveryReport
1884 *
1885 *    Functionality: Process RRC delivery Message from RLC
1886 *
1887 * @params[in] Post structure
1888 *             UL RRC Message Info
1889 * @return ROK     - success
1890 *         RFAILED - failure
1891 *
1892 * ****************************************************************/
1893 uint8_t DuProcRlcRrcDeliveryReport(Pst *pst, RrcDeliveryReport *rrcDeliveryReport)
1894 {
1895    DuCellCb *cellCb = NULLP;
1896    DuUeCb   ueCb;
1897    uint8_t  ret = RFAILED;
1898
1899    if(duGetCellCb(rrcDeliveryReport->cellId, &cellCb) != ROK)
1900       return RFAILED;
1901    
1902    ueCb = cellCb->ueCb[rrcDeliveryReport->ueIdx -1];
1903    ret = BuildAndSendRrcDeliveryReport(ueCb.gnbCuUeF1apId, ueCb.gnbDuUeF1apId,rrcDeliveryReport);
1904
1905    DU_FREE_SHRABL_BUF(pst->region, pst->pool, rrcDeliveryReport, sizeof(RrcDeliveryReport));
1906    return ret;
1907 }
1908
1909
1910 /**********************************************************************
1911   End of file
1912  **********************************************************************/