[Epic-ID: ODUHIGH-516][Task-ID: 526] Implementation of ric service query
[o-du/l2.git] / src / du_app / du_e2ap_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 #include "common_def.h"
19 #include "du_tmr.h"
20 #include "lrg.h"
21 #include "lkw.x"
22 #include "lrg.x"
23 #include "legtp.h"
24 #include "du_app_mac_inf.h"
25 #include "du_app_rlc_inf.h"
26 #include "du_e2ap_mgr.h"
27 #include "du_e2ap_msg_hdl.h"
28 #include "du_cfg.h"
29 #include "du_mgr.h"
30 #include "du_mgr_main.h"
31 #include "du_utils.h"
32 #include "GlobalE2node-gNB-ID.h"
33 #include "ProtocolIE-FieldE2.h"
34 #include "E2setupRequest.h"
35 #include "InitiatingMessageE2.h"
36 #include "SuccessfulOutcomeE2.h"
37 #include "UnsuccessfulOutcomeE2.h"
38 #include "E2AP-PDU.h"
39 #include "odu_common_codec.h"
40 #include "E2nodeComponentInterfaceF1.h"
41 #include "E2setupRequest.h"
42 #include "du_e2_conversions.h"
43 #include "E2SM-KPM-RANfunction-Description.h"
44 #include "RANfunction-Name.h"
45 #include "RIC-EventTriggerStyle-Item.h"
46 #include "RIC-ReportStyle-Item.h"
47 #include "MeasurementInfo-Action-Item.h"
48
49 /*******************************************************************
50  *
51  * @brief Builds Global gNodeB Params
52  *
53  * @details
54  *
55  *    Function : BuildGlobalgNBId
56  *
57  *    Functionality: Building the Plmn and gNB id
58  *
59  * @params[in] GlobalE2node_gNB_ID_t *gNbId
60  * @return ROK     - success
61  *         RFAILED - failure
62  *
63  ******************************************************************/
64
65 uint8_t BuildGlobalgNBId(GlobalE2node_gNB_ID_t *gNbId)
66 {
67    uint8_t unused = 0;
68    uint8_t byteSize = 4;
69    uint8_t gnbId = duCb.gnbId;
70    uint8_t ret = ROK;
71
72    /* fill Global gNB ID Id */
73    gNbId->global_gNB_ID.plmn_id.size = 3 * sizeof(uint8_t);
74    gNbId->global_gNB_ID.plmn_id.buf = NULLP;
75    DU_ALLOC(gNbId->global_gNB_ID.plmn_id.buf , gNbId->global_gNB_ID.plmn_id.size);
76    if(gNbId->global_gNB_ID.plmn_id.buf == NULLP)
77    {
78       DU_LOG("\nERROR  -->  E2AP: Memory allocation failed for Plmn buffer");
79       ret = RFAILED;
80    }
81    else
82    {
83       buildPlmnId(duCfgParam.srvdCellLst[0].duCellInfo.cellInfo.nrCgi.plmn, \
84             gNbId->global_gNB_ID.plmn_id.buf);
85       gNbId->global_gNB_ID.gnb_id.present = GNB_ID_Choice_PR_gnb_ID;
86       /* Allocate Buffer size */
87       gNbId->global_gNB_ID.gnb_id.choice.gnb_ID.size = byteSize * sizeof(uint8_t);
88       gNbId->global_gNB_ID.gnb_id.choice.gnb_ID.buf = NULLP;
89       DU_ALLOC(gNbId->global_gNB_ID.gnb_id.choice.gnb_ID.buf, \
90             gNbId->global_gNB_ID.gnb_id.choice.gnb_ID.size);
91       if(gNbId->global_gNB_ID.gnb_id.choice.gnb_ID.buf == NULLP)
92       {
93          DU_LOG("\nERROR  -->  E2AP: Memory allocation failed for gnb buffer");
94          ret = RFAILED;
95       }
96       else
97       {
98          fillBitString(&gNbId->global_gNB_ID.gnb_id.choice.gnb_ID, unused, byteSize, gnbId);
99       }
100    }
101
102    /* fill gNB-DU ID */ 
103    DU_ALLOC( gNbId->gNB_DU_ID, sizeof(GNB_DU_ID_t));
104    if(gNbId->gNB_DU_ID == NULLP)
105    {
106       DU_LOG("\nERROR  -->  E2AP: Memory allocation failed for gNB_DU_ID ");
107       ret = RFAILED;
108    }
109    else
110    {
111       gNbId->gNB_DU_ID->size = sizeof(uint8_t);
112       DU_ALLOC( gNbId->gNB_DU_ID->buf, sizeof(uint8_t));
113       if(gNbId->gNB_DU_ID->buf)
114       {
115          gNbId->gNB_DU_ID->buf[0] =duCb.e2apDb.e2NodeId;
116       }
117       else
118       {
119          DU_LOG("\nERROR  -->  E2AP: Memory allocation failed for gNB_DU_ID buffer");
120          ret = RFAILED;
121       }
122    }
123
124    return ret;
125 }
126
127 /******************************************************************
128  *
129  * @brief Search E2 node component with the help of action type
130  *
131  * @details
132  *
133  *    Function : searchE2NodeComponentInfo 
134  *
135  *    Functionality: Search E2 node component with the help of action type 
136  *
137  * @params[in] uint8_t componentActionType
138  * @return CmLList
139  *
140  * ****************************************************************/
141
142 CmLList *searchE2NodeComponentInfo(InterfaceType interfaceType, uint8_t componentActionType)
143 {
144    E2NodeComponent *e2NodeComponentInfo;
145    CmLList         *node;
146
147    if(duCb.e2apDb.e2NodeComponentList.count)
148    {
149       CM_LLIST_FIRST_NODE(&duCb.e2apDb.e2NodeComponentList, node);
150       while(node)
151       {
152          e2NodeComponentInfo = (E2NodeComponent*)node->node;
153          if((e2NodeComponentInfo->interfaceType == interfaceType) && (e2NodeComponentInfo->componentActionType == componentActionType))
154             break;
155          else
156             node = node->next;
157       }
158    }
159    return node; 
160 }
161
162 /*******************************************************************
163  *
164  * @brief Builds E2 node config addition list 
165  *
166  * @details
167  *
168  *    Function : BuildE2NodeConfigAddList
169  *
170  *    Functionality: Building E2 node config addition list
171  *
172  * @params[in] E2nodeComponentConfigAddition_List_t *e2NodeAddList 
173  * @return ROK     - success
174  *         RFAILED - failure
175  *
176  ******************************************************************/
177
178 uint8_t BuildE2NodeConfigAddList(E2nodeComponentConfigAddition_List_t *e2NodeAddList)
179 {
180    uint8_t arrIdx = 0;
181    CmLList         *node;
182    E2NodeComponent *e2NodeComponentInfo;
183    E2nodeComponentConfigAddition_ItemIEs_t *e2NodeAddItemIe;
184    E2nodeComponentConfigAddition_Item_t *e2NodeAddItem;
185
186    e2NodeAddList->list.count = 1;
187    e2NodeAddList->list.size = e2NodeAddList->list.count * sizeof(E2nodeComponentConfigAddition_ItemIEs_t *);
188    DU_ALLOC(e2NodeAddList->list.array, e2NodeAddList->list.size);
189    if(e2NodeAddList->list.array == NULLP)
190    {
191        DU_LOG("\nERROR  --> E2AP: Memory allocation failed for BuildE2NodeConfigAddList %d",__LINE__);
192        return RFAILED;
193    }
194
195    for(arrIdx = 0; arrIdx< e2NodeAddList->list.count; arrIdx++)
196    {
197       DU_ALLOC(e2NodeAddList->list.array[arrIdx], sizeof(E2nodeComponentConfigAddition_ItemIEs_t));
198       if(e2NodeAddList->list.array[arrIdx] == NULLP)
199       {
200          DU_LOG("\nERROR  --> E2AP: Memory allocation failed for BuildE2NodeConfigAddList %d",__LINE__);
201          return RFAILED;
202       }
203    }
204    
205    node = searchE2NodeComponentInfo(F1, E2_NODE_COMPONENT_ADD);
206    if(!node)
207    {
208       DU_LOG("\nERROR  --> E2AP : Received e2NodeComponentInfo is null");
209       return RFAILED;
210    }
211    e2NodeComponentInfo = (E2NodeComponent*)node->node;
212    
213    arrIdx = 0;
214    e2NodeAddItemIe = (E2nodeComponentConfigAddition_ItemIEs_t *) e2NodeAddList->list.array[arrIdx];
215    e2NodeAddItemIe->id = ProtocolIE_IDE2_id_E2nodeComponentConfigAddition_Item;
216    e2NodeAddItemIe->criticality = CriticalityE2_reject;
217    e2NodeAddItemIe->value.present = E2nodeComponentConfigAddition_ItemIEs__value_PR_E2nodeComponentConfigAddition_Item;
218    e2NodeAddItem = &e2NodeAddItemIe->value.choice.E2nodeComponentConfigAddition_Item;
219    
220    /* E2nodeComponentInterfaceType */
221    e2NodeAddItem->e2nodeComponentInterfaceType = E2nodeComponentInterfaceType_f1;
222
223    /* E2 Node Component Request Part */
224    if(e2NodeComponentInfo->componentRequestPart)
225    {
226       e2NodeAddItem->e2nodeComponentConfiguration.e2nodeComponentRequestPart.size = e2NodeComponentInfo->reqBufSize ;
227       DU_ALLOC(e2NodeAddItem->e2nodeComponentConfiguration.e2nodeComponentRequestPart.buf,\
228             e2NodeAddItem->e2nodeComponentConfiguration.e2nodeComponentRequestPart.size);
229       if(e2NodeAddItem->e2nodeComponentConfiguration.e2nodeComponentRequestPart.buf == NULLP)
230       {
231          DU_LOG("\nERROR  --> E2AP: Memory allocation failed for BuildE2NodeConfigAddList %d",__LINE__);
232          return RFAILED;
233       }
234
235       memcpy(e2NodeAddItem->e2nodeComponentConfiguration.e2nodeComponentRequestPart.buf,\
236             e2NodeComponentInfo->componentRequestPart, e2NodeAddItem->e2nodeComponentConfiguration.\
237             e2nodeComponentRequestPart.size);
238    }
239    else
240    {
241       DU_LOG("\nERROR  --> E2AP: componentRequestPart is null ");
242       return RFAILED;
243    }
244
245
246    /* E2 Node Component Response Part */
247    if(e2NodeComponentInfo->componentResponsePart)
248    {
249       e2NodeAddItem->e2nodeComponentConfiguration.e2nodeComponentResponsePart.size = e2NodeComponentInfo->rspBufSize; 
250       DU_ALLOC(e2NodeAddItem->e2nodeComponentConfiguration.e2nodeComponentResponsePart.buf, \
251             e2NodeAddItem->e2nodeComponentConfiguration.e2nodeComponentResponsePart.size);
252       if(e2NodeAddItem->e2nodeComponentConfiguration.e2nodeComponentResponsePart.buf == NULLP)
253       {
254          DU_LOG("\nERROR  --> E2AP: Memory allocation failed for BuildE2NodeConfigAddList %d",__LINE__);
255          return RFAILED;
256       }
257       memcpy(e2NodeAddItem->e2nodeComponentConfiguration.e2nodeComponentResponsePart.buf, \
258             e2NodeComponentInfo->componentResponsePart, e2NodeAddItem->e2nodeComponentConfiguration.\
259             e2nodeComponentResponsePart.size);
260    }
261    else
262    {
263       DU_LOG("\nERROR  --> E2AP: componentResponsePart is null");
264       return RFAILED;
265    }
266    
267    /* E2 Node Component ID */
268    e2NodeAddItem->e2nodeComponentID.present = E2nodeComponentID_PR_e2nodeComponentInterfaceTypeF1;
269    DU_ALLOC(e2NodeAddItem->e2nodeComponentID.choice.e2nodeComponentInterfaceTypeF1,\
270    sizeof(E2nodeComponentInterfaceF1_t));
271    if(e2NodeAddItem->e2nodeComponentID.choice.e2nodeComponentInterfaceTypeF1 == NULLP)
272    {
273        DU_LOG("\nERROR  --> E2AP: Memory allocation failed for BuildE2NodeConfigAddList %d",__LINE__);
274        return RFAILED;
275    }
276    e2NodeAddItem->e2nodeComponentID.choice.e2nodeComponentInterfaceTypeF1->gNB_DU_ID.size = sizeof(uint8_t);
277    DU_ALLOC(e2NodeAddItem->e2nodeComponentID.choice.e2nodeComponentInterfaceTypeF1->gNB_DU_ID.buf,\
278    e2NodeAddItem->e2nodeComponentID.choice.e2nodeComponentInterfaceTypeF1->gNB_DU_ID.size);
279
280    if(e2NodeAddItem->e2nodeComponentID.choice.e2nodeComponentInterfaceTypeF1->gNB_DU_ID.buf == NULLP)
281    {
282       DU_LOG("\nERROR  -->list.  E2AP: Memory allocation failed for BuildE2NodeConfigAddList %d",__LINE__);
283       return RFAILED;
284    }
285    e2NodeAddItem->e2nodeComponentID.choice.e2nodeComponentInterfaceTypeF1->gNB_DU_ID.buf[arrIdx]  = e2NodeComponentInfo->componentId;
286    return ROK;
287
288 }
289
290 /*******************************************************************
291  *
292  * @brief deallocation of E2SM_KPM_RANfunction_Description_t
293  *
294  * @details
295  *
296  *    Function : freeE2smKpmRanFunctionDefinition
297  *
298  *    Functionality: deallocation of E2SM_KPM_RANfunction_Description_t
299  *
300  * @params[in]  E2SM_KPM_RANfunction_Description_t *ranFunctionDefinition
301  * @return void
302  *
303  ******************************************************************/
304
305 void freeE2smKpmRanFunctionDefinition(E2SM_KPM_RANfunction_Description_t *ranFunctionDefinition)
306 {
307    MeasurementInfo_Action_Item_t *measInfoList;
308    uint8_t eventTriggerIdx, reportStyleIdx, measInfoIdx;
309    RANfunction_Name_t *ranFuncName;
310    struct E2SM_KPM_RANfunction_Description__ric_ReportStyle_List *ricReportStyle;
311    struct E2SM_KPM_RANfunction_Description__ric_EventTriggerStyle_List *eventTriggerStyle;
312    if(ranFunctionDefinition)
313    {
314       ranFuncName = &ranFunctionDefinition->ranFunction_Name;
315       /* Free RAN function Name */     
316       DU_FREE(ranFuncName->ranFunction_ShortName.buf,  ranFuncName->ranFunction_ShortName.size);
317       DU_FREE(ranFuncName->ranFunction_E2SM_OID.buf, ranFuncName->ranFunction_E2SM_OID.size);
318       DU_FREE(ranFuncName->ranFunction_Description.buf, ranFuncName->ranFunction_Description.size);
319
320       /* Sequence of Event Trigger styles */
321       eventTriggerStyle = ranFunctionDefinition->ric_EventTriggerStyle_List;
322       if(eventTriggerStyle)
323       {
324          if(eventTriggerStyle->list.array)
325          {
326             for(eventTriggerIdx =0;eventTriggerIdx<eventTriggerStyle->list.count; eventTriggerIdx++)
327             {
328                if(eventTriggerStyle->list.array[eventTriggerIdx])
329                {
330                   DU_FREE(eventTriggerStyle->list.array[eventTriggerIdx]->ric_EventTriggerStyle_Name.buf,\
331                         eventTriggerStyle->list.array[eventTriggerIdx]->ric_EventTriggerStyle_Name.size);
332                   DU_FREE(eventTriggerStyle->list.array[eventTriggerIdx], sizeof(RIC_EventTriggerStyle_Item_t ));
333                }
334             }
335             DU_FREE(eventTriggerStyle->list.array, eventTriggerStyle->list.size)
336          }
337          DU_FREE(eventTriggerStyle, sizeof(struct E2SM_KPM_RANfunction_Description__ric_EventTriggerStyle_List));
338       }
339       
340       /* Sequence of Report styles */
341       ricReportStyle = ranFunctionDefinition->ric_ReportStyle_List;
342       if(ricReportStyle)
343       {
344          if(ricReportStyle->list.array)
345          {
346             for(reportStyleIdx =0;reportStyleIdx<ricReportStyle->list.count; reportStyleIdx++)
347             {
348                if(ricReportStyle->list.array[reportStyleIdx])
349                {
350                   if(ricReportStyle->list.array[reportStyleIdx]->ric_ReportStyle_Name.buf)
351                   {
352                      DU_FREE(ricReportStyle->list.array[reportStyleIdx]->ric_ReportStyle_Name.buf,\
353                            ricReportStyle->list.array[reportStyleIdx]->ric_ReportStyle_Name.size);
354                   }
355                   if(ricReportStyle->list.array[reportStyleIdx]->measInfo_Action_List.list.array)
356                   {
357                      for(measInfoIdx=0; measInfoIdx<ricReportStyle->list.array[reportStyleIdx]->measInfo_Action_List.list.count; \
358                            measInfoIdx++)
359                      {
360                         measInfoList = ricReportStyle->list.array[reportStyleIdx]->measInfo_Action_List.list.array[measInfoIdx];
361                         if(measInfoList)
362                         {
363                            DU_FREE(measInfoList->measID, sizeof(long));
364                            DU_FREE(measInfoList->measName.buf, measInfoList->measName.size);
365                            DU_FREE(measInfoList,sizeof(MeasurementInfo_Action_Item_t)); 
366                         }
367                      }
368                      DU_FREE(measInfoList,ricReportStyle->list.array[reportStyleIdx]->measInfo_Action_List.list.size);
369                   }
370                   DU_FREE(ricReportStyle->list.array[reportStyleIdx], sizeof(RIC_ReportStyle_Item_t));
371                }
372             }
373             DU_FREE(ricReportStyle->list.array, ricReportStyle->list.size);
374          }
375          DU_FREE(ricReportStyle, sizeof(struct E2SM_KPM_RANfunction_Description__ric_ReportStyle_List));
376       }
377       DU_FREE(ranFunctionDefinition, sizeof(E2SM_KPM_RANfunction_Description_t)); 
378    }
379 }
380
381 /*******************************************************************
382  *
383  * @brief fill the e2sm ric report style
384  *
385  * @details
386  *
387  *    Function : fillRicReportStyle
388  *
389  *    Functionality: fill the report style
390  *
391  * @params[in]   RanFunction *ranFuncDb, struct
392  * E2SM_KPM_RANfunction_Description__ric_ReportStyle_List *ricReportStyle
393  * @return ROK     - success
394  *         RFAILED - failure
395  *
396  ******************************************************************/
397 uint8_t fillRicReportStyle(RanFunction *ranFuncDb, struct E2SM_KPM_RANfunction_Description__ric_ReportStyle_List *ricReportStyle)
398 {
399    uint8_t styleIdx, measInfoIdx;
400    MeasurementInfo_Action_List_t *measInfo;
401    CmLList  *node;
402    
403    ricReportStyle->list.count = ranFuncDb->numOfReportStyleSupported;
404    ricReportStyle->list.size = ricReportStyle->list.count * sizeof(RIC_ReportStyle_Item_t*);
405    DU_ALLOC(ricReportStyle->list.array, ricReportStyle->list.size);
406    if(!ricReportStyle->list.array)
407    {
408       DU_LOG("\nERROR  --> E2AP: Memory allocation failed for ranFuncDefinition %d",__LINE__);
409       return RFAILED;
410    }
411
412    for(styleIdx =0;styleIdx<ricReportStyle->list.count; styleIdx++)
413    {
414       DU_ALLOC(ricReportStyle->list.array[styleIdx], sizeof(RIC_ReportStyle_Item_t));
415       if(!ricReportStyle->list.array[styleIdx])
416       {
417          DU_LOG("\nERROR  --> E2AP: Memory allocation failed in function %s at %d",__func__,__LINE__);
418          return RFAILED;
419       }
420       
421       /* RIC Report Style Type */
422       ricReportStyle->list.array[styleIdx]->ric_ReportStyle_Type = ranFuncDb->reportStyleList[styleIdx].reportStyle.styleType;
423       
424       /* RIC Report Style Format Type */
425       ricReportStyle->list.array[styleIdx]->ric_ActionFormat_Type = ranFuncDb->reportStyleList[styleIdx].reportStyle.formatType;
426       
427       /* RIC Report Style Name */
428       ricReportStyle->list.array[styleIdx]->ric_ReportStyle_Name.size = strlen(ranFuncDb->reportStyleList[styleIdx].reportStyle.name);
429       DU_ALLOC(ricReportStyle->list.array[styleIdx]->ric_ReportStyle_Name.buf,\
430             ricReportStyle->list.array[styleIdx]->ric_ReportStyle_Name.size);
431       if(!ricReportStyle->list.array[styleIdx]->ric_ReportStyle_Name.buf)
432       {
433          DU_LOG("\nERROR  --> E2AP: Memory allocation failed in function %s at %d",__func__,__LINE__);
434          return RFAILED;
435       }
436       memcpy(ricReportStyle->list.array[styleIdx]->ric_ReportStyle_Name.buf, ranFuncDb->reportStyleList[styleIdx].reportStyle.name,\
437             ricReportStyle->list.array[styleIdx]->ric_ReportStyle_Name.size);
438
439       /* RIC Indication Header Format Type*/
440       ricReportStyle->list.array[styleIdx]->ric_IndicationHeaderFormat_Type = ranFuncDb->ricIndicationHeaderFormat;
441
442       /* RIC Indication Message Format Type*/
443       ricReportStyle->list.array[styleIdx]->ric_IndicationMessageFormat_Type = ranFuncDb->ricIndicationMessageFormat;
444       
445       /* Measurement Info Action List */
446       CmLListCp measInfoList =ranFuncDb->reportStyleList[styleIdx].measurementInfoList;
447       if(!measInfoList.count)
448       {
449          continue;      
450       }
451
452       CM_LLIST_FIRST_NODE(&ranFuncDb->reportStyleList[styleIdx].measurementInfoList, node);
453       measInfo = &ricReportStyle->list.array[styleIdx]->measInfo_Action_List;
454
455       measInfo->list.count = measInfoList.count; 
456       measInfo->list.size =  measInfoList.count*sizeof(MeasurementInfo_Action_Item_t*);
457       DU_ALLOC(measInfo->list.array, measInfo->list.size);
458       if(!measInfo->list.array)
459       {
460          DU_LOG("\nERROR  --> E2AP: Memory allocation failed in function %s at %d",__func__,__LINE__);
461          return RFAILED;
462       }
463
464       for(measInfoIdx=0; measInfoIdx<measInfo->list.count; measInfoIdx++)
465       {
466          if(!node)
467          {
468             DU_LOG("\nERROR  --> E2AP: Measurement info node is null");
469             return RFAILED;
470          }
471
472          DU_ALLOC(measInfo->list.array[measInfoIdx],sizeof(MeasurementInfo_Action_Item_t));  
473          if(!measInfo->list.array[measInfoIdx])
474          {
475             DU_LOG("\nERROR  --> E2AP: Memory allocation failed in function %s at %d",__func__,__LINE__);
476             return RFAILED;
477          }
478          MeasurementInfoForAction *measInfoForAction= (MeasurementInfoForAction*)node->node;
479          DU_ALLOC(measInfo->list.array[measInfoIdx]->measID, sizeof(long));
480          if(!measInfo->list.array[measInfoIdx]->measID)
481          {
482             DU_LOG("\nERROR  --> E2AP: Memory allocation failed in function %s at %d",__func__,__LINE__);
483             return RFAILED;
484          }
485          
486          memcpy(measInfo->list.array[measInfoIdx]->measID, &measInfoForAction->measurementTypeId,sizeof(long));
487          measInfo->list.array[measInfoIdx]->measName.size= strlen(measInfoForAction->measurementTypeName);
488          DU_ALLOC(measInfo->list.array[measInfoIdx]->measName.buf, measInfo->list.array[measInfoIdx]->measName.size);
489          if(!measInfo->list.array[measInfoIdx]->measName.size)
490          {
491             DU_LOG("\nERROR  --> E2AP: Memory allocation failed in function %s at %d",__func__,__LINE__);
492             return RFAILED;
493          }
494
495          memcpy(measInfo->list.array[measInfoIdx]->measName.buf, \
496                measInfoForAction->measurementTypeName,\
497                measInfo->list.array[measInfoIdx]->measName.size);
498          node = node->next;
499       }
500
501    }
502    return ROK;
503 }
504 /*******************************************************************
505  *
506  * @brief fill the ric event trigger style
507  *
508  * @details
509  *
510  *    Function : fillRicEventTriggerStyle
511  *
512  *    Functionality: fill the ric event trigger style
513  *
514  * @params[in]   
515  * @return ROK     - success
516  *         RFAILED - failure
517  *
518  ******************************************************************/
519 uint8_t fillRicEventTriggerStyle(RanFunction *ranFuncDb, struct E2SM_KPM_RANfunction_Description__ric_EventTriggerStyle_List *ricEventTriggerStyle)
520 {
521    uint8_t styleIdx;
522
523    ricEventTriggerStyle->list.count = ranFuncDb->numOfEventTriggerStyleSupported;
524    ricEventTriggerStyle->list.size = ricEventTriggerStyle->list.count*  sizeof(RIC_EventTriggerStyle_Item_t *);
525    DU_ALLOC(ricEventTriggerStyle->list.array, ricEventTriggerStyle->list.size);
526    if(!ricEventTriggerStyle->list.array)
527    {
528       DU_LOG("\nERROR  --> E2AP: Memory allocation failed for ric_EventTriggerStyle_List %d",__LINE__);
529       return RFAILED;
530    }
531
532    for(styleIdx =0;styleIdx<ricEventTriggerStyle->list.count; styleIdx++)
533    {
534       DU_ALLOC(ricEventTriggerStyle->list.array[styleIdx], sizeof(RIC_EventTriggerStyle_Item_t ));
535       if(!ricEventTriggerStyle->list.array[styleIdx])
536       {
537          DU_LOG("\nERROR  --> E2AP: Memory allocation failed in function %s at %d",__func__,__LINE__);
538          return RFAILED;
539       }
540       ricEventTriggerStyle->list.array[styleIdx]->ric_EventTriggerStyle_Type = ranFuncDb->eventTriggerStyleList[styleIdx].styleType;
541
542       ricEventTriggerStyle->list.array[styleIdx]->ric_EventTriggerFormat_Type = ranFuncDb->eventTriggerStyleList[styleIdx].formatType;
543
544       ricEventTriggerStyle->list.array[styleIdx]->ric_EventTriggerStyle_Name.size = strlen(ranFuncDb->eventTriggerStyleList[styleIdx].name);
545       DU_ALLOC(ricEventTriggerStyle->list.array[styleIdx]->ric_EventTriggerStyle_Name.buf,\
546             ricEventTriggerStyle->list.array[styleIdx]->ric_EventTriggerStyle_Name.size);
547       if(!ricEventTriggerStyle->list.array[styleIdx]->ric_EventTriggerStyle_Name.buf)
548       {
549          DU_LOG("\nERROR  --> E2AP: Memory allocation failed in function %s at %d",__func__,__LINE__);
550          return RFAILED;
551       }
552       memcpy(ricEventTriggerStyle->list.array[styleIdx]->ric_EventTriggerStyle_Name.buf,ranFuncDb->eventTriggerStyleList[styleIdx].name,\
553             ricEventTriggerStyle->list.array[styleIdx]->ric_EventTriggerStyle_Name.size);
554    
555    }
556    return ROK;
557 }
558
559 /*******************************************************************
560  *
561  * @brief Builds Ran function item
562  *
563  * @details
564  *
565  *    Function : BuildRanFunctionItem  
566  *
567  *    Functionality: Building RAN function item
568  *
569  * @params[in] 
570  *             RAN function item that has to be filled 
571  *             Stored RAN Function information
572  * @return ROK     - success
573  *         RFAILED - failure
574  *
575  ******************************************************************/
576
577 uint8_t BuildRanFunctionItem(RANfunction_Item_t *ranFuncItem, RanFunction *ranFuncDb)
578 {
579    uint8_t ret =RFAILED;
580    RANfunctionDefinition_t  *ranFunctionDefinition;
581    RANfunction_Name_t *ranFuncName;
582    asn_enc_rval_t encRetVal;
583    E2SM_KPM_RANfunction_Description_t *ranFuncDefinition;
584    
585    while(true)
586    {
587       /* RAN function Id*/
588       ranFuncItem->ranFunctionID = ranFuncDb->id;
589
590       /* RAN Function Revision*/
591       ranFuncItem->ranFunctionRevision = ranFuncDb->revisionCounter;
592
593       /* RAN function OID*/
594       ranFuncItem->ranFunctionOID.size = strlen(ranFuncDb->name.serviceModelOID);
595       DU_ALLOC(ranFuncItem->ranFunctionOID.buf, ranFuncItem->ranFunctionOID.size);
596       if(!ranFuncItem->ranFunctionOID.buf)
597       {
598          DU_LOG("\nERROR  --> E2AP: Memory allocation failed in function %s at %d",__func__,__LINE__);
599          break;
600       }
601       memcpy(ranFuncItem->ranFunctionOID.buf, ranFuncDb->name.serviceModelOID, ranFuncItem->ranFunctionOID.size);
602
603       /* RAN function Definition */
604       DU_ALLOC(ranFuncDefinition, sizeof(E2SM_KPM_RANfunction_Description_t));
605       if(!ranFuncDefinition)
606       {
607          DU_LOG("\nERROR  --> E2AP: Memory allocation failed in function %s at %d",__func__,__LINE__);
608          break;
609       }
610
611       /* RAN function Name */
612       ranFuncName = &ranFuncDefinition->ranFunction_Name;
613
614       /* RAN function ShortName */
615       ranFuncName->ranFunction_ShortName.size = strlen(ranFuncDb->name.shortName); 
616       DU_ALLOC(ranFuncName->ranFunction_ShortName.buf,  ranFuncName->ranFunction_ShortName.size);
617       if(!ranFuncName->ranFunction_ShortName.buf)
618       {
619          DU_LOG("\nERROR  --> E2AP: Memory allocation failed in function %s at %d",__func__,__LINE__);
620          break;
621       }
622       memcpy(ranFuncName->ranFunction_ShortName.buf, ranFuncDb->name.shortName, strlen(ranFuncDb->name.shortName));
623
624       /* RAN function E2SM_OID */
625       ranFuncName->ranFunction_E2SM_OID.size = strlen(ranFuncDb->name.serviceModelOID);
626       DU_ALLOC(ranFuncName->ranFunction_E2SM_OID.buf, ranFuncName->ranFunction_E2SM_OID.size);
627       if(!ranFuncName->ranFunction_E2SM_OID.buf)
628       {
629          DU_LOG("\nERROR  --> E2AP: Memory allocation failed in function %s at %d",__func__,__LINE__);
630          break;
631       }
632       memcpy(ranFuncName->ranFunction_E2SM_OID.buf, ranFuncDb->name.serviceModelOID, ranFuncName->ranFunction_E2SM_OID.size);
633
634       /* RAN Function Name Description */
635       ranFuncName->ranFunction_Description.size = strlen(ranFuncDb->name.description);
636       DU_ALLOC(ranFuncName->ranFunction_Description.buf, ranFuncName->ranFunction_Description.size);
637       if(!ranFuncName->ranFunction_Description.buf)
638       {
639          DU_LOG("\nERROR  --> E2AP: Memory allocation failed in function %s at %d",__func__,__LINE__);
640          break;
641       }
642       memcpy(ranFuncName->ranFunction_Description.buf, ranFuncDb->name.description, ranFuncName->ranFunction_Description.size);
643
644       /* RIC Event Trigger Style List */
645       DU_ALLOC(ranFuncDefinition->ric_EventTriggerStyle_List, sizeof(struct E2SM_KPM_RANfunction_Description__ric_EventTriggerStyle_List));
646       if(!ranFuncDefinition->ric_EventTriggerStyle_List)
647       {
648          DU_LOG("\nERROR  --> E2AP: Memory allocation failed in function %s at %d",__func__,__LINE__);
649          break;
650       }
651
652       if(fillRicEventTriggerStyle(ranFuncDb, ranFuncDefinition->ric_EventTriggerStyle_List)!=ROK)
653       {
654          DU_LOG("\nERROR  --> E2AP: failed to fill ric event trigger style");
655          break;
656       }
657
658       /* RIC Report Style List */
659       DU_ALLOC(ranFuncDefinition->ric_ReportStyle_List, sizeof(struct E2SM_KPM_RANfunction_Description__ric_ReportStyle_List));
660       if(!ranFuncDefinition->ric_ReportStyle_List)
661       {
662          DU_LOG("\nERROR  --> E2AP: Memory allocation failed in function %s at %d",__func__,__LINE__);
663          break;
664       }
665       if(fillRicReportStyle(ranFuncDb, ranFuncDefinition->ric_ReportStyle_List) != ROK)
666       {
667          DU_LOG("\nERROR  --> E2AP: failed to fill ric report style");
668          break;
669       }
670
671       /* Encode the F1SetupRequest type as APER */
672       xer_fprint(stdout, &asn_DEF_E2SM_KPM_RANfunction_Description, ranFuncDefinition);
673
674       memset(encBuf, 0, ENC_BUF_MAX_LEN);
675       encBufSize = 0;
676       encRetVal = aper_encode(&asn_DEF_E2SM_KPM_RANfunction_Description, 0, ranFuncDefinition, PrepFinalEncBuf, encBuf);
677
678       /* Encode results */
679       if(encRetVal.encoded == ENCODE_FAIL)
680       {
681          DU_LOG("\nERROR  -->  F1AP : Could not encode RAN function definition  (at %s)\n",\
682                encRetVal.failed_type ? encRetVal.failed_type->name : "unknown");
683          break;
684       }
685       else
686       {
687          DU_LOG("\nDEBUG   -->  F1AP : Created APER encoded buffer for RAN function definition \n");
688          for(uint8_t measIeIdx=0; measIeIdx< encBufSize; measIeIdx++)
689          {
690             printf("%x",encBuf[measIeIdx]);
691          }
692          ranFunctionDefinition = &ranFuncItem->ranFunctionDefinition; 
693          ranFunctionDefinition->size = encBufSize;
694          DU_ALLOC(ranFunctionDefinition->buf, encBufSize);
695          if(ranFunctionDefinition->buf == NULLP)
696          {
697             DU_LOG("\nERROR  -->  F1AP : Memory allocation failed for RAN function definition buffer");
698             break;
699          }
700          memcpy(ranFunctionDefinition->buf, &encBuf, encBufSize);
701          ret = ROK;
702          break;
703       }
704    }
705    freeE2smKpmRanFunctionDefinition(ranFuncDefinition);
706    return ret;
707 }
708
709 /*******************************************************************
710  *
711  * @brief Builds Ran function add list based on the procedure code
712  *
713  * @details
714  *
715  *    Function : BuildRanFunctionAddList 
716  *
717  *    Functionality: Building RAN addition addition list
718  *       In case of ProcedureCodeE2_id_E2setup we add all the RAN Function list
719  *       which is present in E2 database.
720  *       In the case of other procedures, we just fill the RAN functions whose ID 
721  *       is contained in recvList
722  *
723  * @params[in] 
724  *       RAN Function list
725  *       Procedure code
726  *       Count of ran functions to be added in the list
727  *       Received list of RAN functions
728  *
729  * @return ROK     - success
730  *         RFAILED - failure
731  *
732  ******************************************************************/
733
734 uint8_t BuildRanFunctionAddList(RANfunctions_List_t *ranFunctionsList, uint8_t procedureCode, uint8_t count, uint8_t *recvList)
735 {
736    uint16_t id;
737    RanFunction *ranFuncDb;
738    uint8_t ranFuncIdx;
739    RANfunction_ItemIEs_t *ranFuncItemIe;
740    
741    /* For ProcedureCodeE2_id_E2setup, the number of RAN function list items is
742     * equal to the number of ran function entries stored in the database.
743     * For any other procedure, the RAN function list count is equal
744     * to the count of ran functions obtained from the function's caller */
745
746    if(procedureCode == ProcedureCodeE2_id_E2setup)
747       ranFunctionsList->list.count = duCb.e2apDb.numOfRanFunction;
748    else
749       ranFunctionsList->list.count = count;
750
751    ranFunctionsList->list.size = ranFunctionsList->list.count * sizeof(RANfunction_ItemIEs_t*);
752    DU_ALLOC(ranFunctionsList->list.array, ranFunctionsList->list.size);
753    if(ranFunctionsList->list.array == NULLP)
754    {
755       DU_LOG("\nERROR  --> E2AP: Memory allocation failed in %s at %d",__func__, __LINE__);
756       return RFAILED;
757    }
758
759    for(ranFuncIdx = 0; ranFuncIdx< ranFunctionsList->list.count; ranFuncIdx++)
760    {
761       DU_ALLOC(ranFunctionsList->list.array[ranFuncIdx], sizeof(RANfunction_ItemIEs_t));
762       if(ranFunctionsList->list.array[ranFuncIdx] == NULLP)
763       {
764          DU_LOG("\nERROR  --> E2AP: Memory allocation failed in %s at %d",__func__, __LINE__);
765          return RFAILED;
766       }
767       if(procedureCode == ProcedureCodeE2_id_E2setup) 
768       {
769          /* Getting all of the RAN function's information from DuCb one by one*/
770          ranFuncDb = &duCb.e2apDb.ranFunction[ranFuncIdx];
771       }
772       else
773       {
774          /* Getting only the RAN function information from DuCb whose Id is
775           * present in the received array */
776          id =recvList[ranFuncIdx];
777          ranFuncDb = &duCb.e2apDb.ranFunction[id-1];
778       }
779       ranFuncItemIe = (RANfunction_ItemIEs_t *) ranFunctionsList->list.array[ranFuncIdx];
780       ranFuncItemIe->id = ProtocolIE_IDE2_id_RANfunction_Item;
781       ranFuncItemIe->criticality = CriticalityE2_ignore;
782       ranFuncItemIe->value.present = RANfunction_ItemIEs__value_PR_RANfunction_Item;
783       BuildRanFunctionItem(&ranFuncItemIe->value.choice.RANfunction_Item, ranFuncDb);
784    }
785    return ROK;
786 }   
787
788 /*******************************************************************
789  *
790  * @brief De Allocate E2 Setup Request Message
791  *
792  * @details
793  *
794  *    Function : FreeE2SetupReq
795  *
796  *    Functionality: De-Allocating E2 Setup request Message
797  *
798  * @params[in] E2AP_PDU_t *e2apMsg
799  
800  * @return void
801  *
802  * ****************************************************************/
803
804 void FreeE2SetupReq(E2AP_PDU_t *e2apMsg)
805 {
806    uint8_t arrIdx = 0;
807    uint8_t e2NodeAddListIdx =0, ranFuncAddListIdx;
808    E2setupRequest_t *e2SetupReq;
809    E2nodeComponentConfigAddition_List_t *e2NodeAddList;
810    E2nodeComponentConfigAddition_ItemIEs_t *e2NodeAddItem;
811    RANfunctions_List_t *ranFunctionsList;
812    RANfunction_ItemIEs_t *ranFuncItemIe;
813    RANfunction_Item_t  *ranFunItem;
814
815    /* De-allocating Memory */
816    if(e2apMsg != NULLP)
817    {
818       if(e2apMsg->choice.initiatingMessage != NULLP)
819       {
820          e2SetupReq = &e2apMsg->choice.initiatingMessage->value.choice.E2setupRequest; 
821          if(e2SetupReq->protocolIEs.list.array != NULLP)
822          {
823             for(arrIdx = 0; arrIdx < e2SetupReq->protocolIEs.list.count; arrIdx++)
824             {
825                if(e2SetupReq->protocolIEs.list.array[arrIdx] != NULLP)
826                {
827                   switch(e2SetupReq->protocolIEs.list.array[arrIdx]->id)
828                   {
829                      case ProtocolIE_IDE2_id_TransactionID:
830                           break;
831                      case ProtocolIE_IDE2_id_GlobalE2node_ID:
832                         {
833                            if(e2SetupReq->protocolIEs.list.array[arrIdx]->\
834                                  value.choice.GlobalE2node_ID.choice.gNB != NULLP)
835                            {
836                               GlobalE2node_gNB_ID_t *gNbId = NULLP;
837                               gNbId = e2SetupReq->protocolIEs.list.array[arrIdx]->\
838                                       value.choice.GlobalE2node_ID.choice.gNB;
839                               if(gNbId->global_gNB_ID.plmn_id.buf != NULLP)
840                               {
841                                  DU_FREE(gNbId->global_gNB_ID.gnb_id.choice.gnb_ID.buf,\
842                                        gNbId->global_gNB_ID.gnb_id.choice.gnb_ID.size);
843                                  DU_FREE(gNbId->global_gNB_ID.plmn_id.buf,\
844                                        gNbId->global_gNB_ID.plmn_id.size);
845                               }
846
847                               if(gNbId->gNB_DU_ID != NULLP)
848                               {
849                                  DU_FREE( gNbId->gNB_DU_ID->buf, gNbId->gNB_DU_ID->size);
850                                  DU_FREE(gNbId->gNB_DU_ID, sizeof(GNB_DU_ID_t));
851                               }
852                               DU_FREE(e2SetupReq->protocolIEs.list.array[arrIdx]->value.\
853                                     choice.GlobalE2node_ID.choice.gNB, sizeof(GlobalE2node_gNB_ID_t));
854                            }
855                            break;
856                         }
857                      case ProtocolIE_IDE2_id_E2nodeComponentConfigAddition:
858                      {
859                          e2NodeAddList = &e2SetupReq->protocolIEs.list.array[arrIdx]->value.choice.E2nodeComponentConfigAddition_List;
860                          if(e2NodeAddList->list.array)
861                          {
862                              for(e2NodeAddListIdx = 0; e2NodeAddListIdx< e2NodeAddList->list.count; e2NodeAddListIdx++)
863                              {
864                                 e2NodeAddItem = (E2nodeComponentConfigAddition_ItemIEs_t *) e2NodeAddList->list.array[e2NodeAddListIdx];
865                                 
866                                 /* Free E2 Node Component Request Part */
867                                 DU_FREE(e2NodeAddItem->value.choice.E2nodeComponentConfigAddition_Item.e2nodeComponentConfiguration.e2nodeComponentRequestPart.buf,\
868                                       e2NodeAddItem->value.choice.E2nodeComponentConfigAddition_Item.e2nodeComponentConfiguration.e2nodeComponentRequestPart.size);
869                                 
870                                 /* Free E2 Node Component Response Part */
871                                 DU_FREE(e2NodeAddItem->value.choice.E2nodeComponentConfigAddition_Item.e2nodeComponentConfiguration.\
872                                       e2nodeComponentResponsePart.buf, \
873                                       e2NodeAddItem->value.choice.E2nodeComponentConfigAddition_Item.e2nodeComponentConfiguration.e2nodeComponentResponsePart.size);
874                                  
875                                  /* Free E2 Node Component ID */
876                                 if(e2NodeAddItem->value.choice.E2nodeComponentConfigAddition_Item.e2nodeComponentID.choice.e2nodeComponentInterfaceTypeF1)
877                                 {
878                                     DU_FREE(e2NodeAddItem->value.choice.E2nodeComponentConfigAddition_Item.e2nodeComponentID.choice.\
879                                     e2nodeComponentInterfaceTypeF1->gNB_DU_ID.buf,\
880                                     e2NodeAddItem->value.choice.E2nodeComponentConfigAddition_Item.e2nodeComponentID.choice.\
881                                     e2nodeComponentInterfaceTypeF1->gNB_DU_ID.size);
882                                     DU_FREE(e2NodeAddItem->value.choice.E2nodeComponentConfigAddition_Item.e2nodeComponentID.choice.e2nodeComponentInterfaceTypeF1,\
883                                     sizeof(E2nodeComponentInterfaceF1_t));
884                                 }
885                                 DU_FREE(e2NodeAddList->list.array[e2NodeAddListIdx], sizeof(E2nodeComponentConfigAddition_ItemIEs_t));
886                              }
887                              DU_FREE(e2NodeAddList->list.array, e2NodeAddList->list.size);
888                          }
889                          break;
890                      }
891                      case ProtocolIE_IDE2_id_RANfunctionsAdded:
892                      {
893                         ranFunctionsList = &(e2SetupReq->protocolIEs.list.array[arrIdx]->value.choice.RANfunctions_List);  
894                         if(ranFunctionsList->list.array)
895                         {  
896                            for(ranFuncAddListIdx= 0; ranFuncAddListIdx< ranFunctionsList->list.count; ranFuncAddListIdx++)
897                            {
898                               if(ranFunctionsList->list.array[ranFuncAddListIdx])
899                               {
900                                  ranFuncItemIe = (RANfunction_ItemIEs_t *) ranFunctionsList->list.array[ranFuncAddListIdx];
901                                  ranFunItem = &ranFuncItemIe->value.choice.RANfunction_Item;
902                                  DU_FREE(ranFunItem->ranFunctionOID.buf, ranFunItem->ranFunctionOID.size);
903                                  DU_FREE(ranFunItem->ranFunctionDefinition.buf, ranFunItem->ranFunctionDefinition.size);
904                                  DU_FREE(ranFunctionsList->list.array[ranFuncAddListIdx], sizeof(RANfunction_ItemIEs_t));
905                               }
906                            }
907                            DU_FREE(ranFunctionsList->list.array, ranFunctionsList->list.size);
908                         }
909                         break;
910                      }
911
912                      default:
913                         DU_LOG("\nERROR  --> E2AP: Invalid event at e2SetupRequet %ld ",\
914                               (e2SetupReq->protocolIEs.list.array[arrIdx]->id));
915                         break;
916                   }
917                   DU_FREE(e2SetupReq->protocolIEs.list.array[arrIdx], sizeof(E2setupRequestIEs_t));
918                }
919             }
920             DU_FREE(e2SetupReq->protocolIEs.list.array, e2SetupReq->protocolIEs.list.size);
921          }
922          DU_FREE(e2apMsg->choice.initiatingMessage, sizeof(InitiatingMessageE2_t));
923       }
924       DU_FREE(e2apMsg, sizeof(E2AP_PDU_t));
925    }
926 }
927
928 /*******************************************************************
929  *
930  * @brief Builds and Send the E2SetupRequest
931  *
932  * @details
933  *
934  *    Function : BuildAndSendE2SetupReq
935  *
936  * Functionality:Fills the E2SetupRequest
937  *
938  * @return ROK     - success
939  *         RFAILED - failure
940  *
941  ******************************************************************/
942
943 uint8_t BuildAndSendE2SetupReq()
944 {
945    uint8_t arrIdx = 0, elementCnt=0;
946    uint8_t transId = 0, ret = ROK;
947    bool memAllocFailed;
948    E2AP_PDU_t        *e2apMsg = NULLP;
949    E2setupRequest_t  *e2SetupReq = NULLP;
950    asn_enc_rval_t     encRetVal;       /* Encoder return value */
951
952    DU_LOG("\nINFO   -->  E2AP : Building E2 Setup Request\n");
953    do
954    {
955       DU_ALLOC(e2apMsg, sizeof(E2AP_PDU_t));
956       if(e2apMsg == NULLP)
957       {
958          DU_LOG("\nERROR  -->  E2AP : Memory allocation for E2AP-PDU failed");
959          break;
960       }
961       e2apMsg->present = E2AP_PDU_PR_initiatingMessage;
962       DU_ALLOC(e2apMsg->choice.initiatingMessage, sizeof(InitiatingMessageE2_t));
963       if(e2apMsg->choice.initiatingMessage == NULLP)
964       {
965          DU_LOG("\nERROR  -->  E2AP : Memory allocation for E2AP-PDU failed");
966          break;
967       }
968       e2apMsg->choice.initiatingMessage->criticality = CriticalityE2_reject;
969       e2apMsg->choice.initiatingMessage->procedureCode = ProcedureCodeE2_id_E2setup;
970       e2apMsg->choice.initiatingMessage->value.present = InitiatingMessageE2__value_PR_E2setupRequest;
971       e2SetupReq = &e2apMsg->choice.initiatingMessage->value.choice.E2setupRequest;
972
973       elementCnt = 4;
974       e2SetupReq->protocolIEs.list.count = elementCnt;
975       e2SetupReq->protocolIEs.list.size = elementCnt * sizeof(E2setupRequestIEs_t*);
976
977       /* Initialize the E2Setup members */
978       DU_ALLOC(e2SetupReq->protocolIEs.list.array, \
979             e2SetupReq->protocolIEs.list.size);
980       if(e2SetupReq->protocolIEs.list.array == NULLP)
981       {
982          DU_LOG("\nERROR  -->  E2AP : Memory allocation failed for array elements");
983          break;
984       }
985       for(arrIdx = 0; arrIdx < elementCnt; (arrIdx)++)
986       {
987          DU_ALLOC(e2SetupReq->protocolIEs.list.array[arrIdx],\
988                sizeof(E2setupRequestIEs_t));
989          if(e2SetupReq->protocolIEs.list.array[arrIdx] == NULLP)
990          {
991             memAllocFailed = true;
992             DU_LOG("\nERROR  -->  E2AP : Memory allocation failed for arrayarrIdx [%d]", arrIdx);
993             break;
994          }
995       }
996       if(memAllocFailed == true)
997          break;
998
999       arrIdx = 0;
1000
1001       /* TransactionID */
1002       e2SetupReq->protocolIEs.list.array[arrIdx]->id = ProtocolIE_IDE2_id_TransactionID;
1003       e2SetupReq->protocolIEs.list.array[arrIdx]->criticality = CriticalityE2_reject;
1004       e2SetupReq->protocolIEs.list.array[arrIdx]->value.present = E2setupRequestIEs__value_PR_TransactionID;
1005       transId = assignTransactionId();
1006       e2SetupReq->protocolIEs.list.array[arrIdx]->value.choice.TransactionID = transId;
1007
1008       arrIdx++;
1009       /* GlobalE2node_gNB_ID */
1010       e2SetupReq->protocolIEs.list.array[arrIdx]->id = ProtocolIE_IDE2_id_GlobalE2node_ID;
1011       e2SetupReq->protocolIEs.list.array[arrIdx]->criticality = CriticalityE2_reject;
1012       e2SetupReq->protocolIEs.list.array[arrIdx]->value.present = E2setupRequestIEs__value_PR_GlobalE2node_ID;
1013       e2SetupReq->protocolIEs.list.array[arrIdx]->value.choice.GlobalE2node_ID.present = GlobalE2node_ID_PR_gNB;
1014
1015       DU_ALLOC(e2SetupReq->protocolIEs.list.array[arrIdx]->value.choice.\
1016             GlobalE2node_ID.choice.gNB, sizeof(GlobalE2node_gNB_ID_t));
1017       if(e2SetupReq->protocolIEs.list.array[arrIdx]->value.choice.\
1018             GlobalE2node_ID.choice.gNB == NULLP)
1019       {
1020          DU_LOG("\nERROR  -->  E2AP : Memory allocation failed for gNbId");
1021          break;
1022       }
1023       else
1024       {
1025          ret = BuildGlobalgNBId(e2SetupReq->protocolIEs.list.array[arrIdx]->value.\
1026                choice.GlobalE2node_ID.choice.gNB);
1027          if(ret != ROK)
1028          {
1029              DU_LOG("\nERROR  -->  E2AP : Failed to build Global Gnb Id");
1030              break;
1031          }
1032       }
1033       
1034       /* RAN Functions Added List */
1035       arrIdx++;
1036       e2SetupReq->protocolIEs.list.array[arrIdx]->id = ProtocolIE_IDE2_id_RANfunctionsAdded;
1037       e2SetupReq->protocolIEs.list.array[arrIdx]->criticality = CriticalityE2_reject;
1038       e2SetupReq->protocolIEs.list.array[arrIdx]->value.present = E2setupRequestIEs__value_PR_RANfunctions_List;
1039       if(BuildRanFunctionAddList(&(e2SetupReq->protocolIEs.list.array[arrIdx]->value.choice.RANfunctions_List), ProcedureCodeE2_id_E2setup, 0, NULL)!=ROK)      
1040       {
1041          DU_LOG("\nERROR  -->  E2AP : Failed to create RAN Function");
1042          break;
1043       }
1044
1045       /* E2 Node Component Configuration Addition List */
1046       arrIdx++;
1047       e2SetupReq->protocolIEs.list.array[arrIdx]->id = ProtocolIE_IDE2_id_E2nodeComponentConfigAddition;
1048       e2SetupReq->protocolIEs.list.array[arrIdx]->criticality = CriticalityE2_reject;
1049       e2SetupReq->protocolIEs.list.array[arrIdx]->value.present = E2setupRequestIEs__value_PR_E2nodeComponentConfigAddition_List;
1050       if(BuildE2NodeConfigAddList(&(e2SetupReq->protocolIEs.list.array[arrIdx]->value.choice.E2nodeComponentConfigAddition_List))!=ROK)
1051       {
1052          DU_LOG("\nERROR  -->  E2AP : Failed to create E2 Node config list");
1053          break;
1054       }
1055
1056
1057
1058       /* Prints the Msg formed */
1059       xer_fprint(stdout, &asn_DEF_E2AP_PDU, e2apMsg);
1060
1061       memset(encBuf, 0, ENC_BUF_MAX_LEN);
1062       encBufSize = 0;
1063       encRetVal = aper_encode(&asn_DEF_E2AP_PDU, 0, e2apMsg, PrepFinalEncBuf,\
1064             encBuf);
1065       if(encRetVal.encoded == ENCODE_FAIL)
1066       {
1067          DU_LOG("\nERROR  -->  E2AP : Could not encode E2SetupRequest structure (at %s)\n",\
1068                encRetVal.failed_type ? encRetVal.failed_type->name : "unknown");
1069          break;
1070       }
1071       else
1072       {
1073          DU_LOG("\nDEBUG   -->  E2AP : Created APER encoded buffer for E2SetupRequest\n");
1074 #ifdef DEBUG_ASN_PRINT
1075          for(int i=0; i< encBufSize; i++)
1076          {
1077             printf("%x",encBuf[i]);
1078          }
1079 #endif
1080       }
1081       if(SendE2APMsg(DU_APP_MEM_REGION, DU_POOL, encBuf, encBufSize) != ROK)
1082       {
1083          DU_LOG("\nERROR  -->  E2AP : Sending E2 Setup request failed");
1084       }
1085       break;
1086    }while(true);
1087
1088    duCb.e2apDb.e2TransInfo.e2InitTransaction[transId].transactionId = transId;
1089    duCb.e2apDb.e2TransInfo.e2InitTransaction[transId].procedureCode = e2apMsg->choice.initiatingMessage->procedureCode;
1090    
1091    FreeE2SetupReq(e2apMsg);
1092    return ret;
1093 }/* End of BuildAndSendE2SetupReq */
1094
1095 /*******************************************************************
1096  *
1097  * @brief Builds Ric Request Id
1098  *
1099  * @details
1100  *
1101  *    Function : BuildRicRequestId
1102  *
1103  *    Functionality: Building the Ric Request Id
1104  *
1105  * @params[in] RICrequestID_t *ricReqId
1106  * @return ROK     - success
1107  *         RFAILED - failure
1108  *
1109  * ****************************************************************/
1110
1111 uint8_t BuildRicRequestId(RICrequestID_t *ricReqId)
1112 {
1113    if(ricReqId == NULLP)
1114    {
1115       return RFAILED;
1116    }
1117
1118    ricReqId->ricRequestorID = 1;
1119    ricReqId->ricInstanceID  = 1;
1120    return ROK;
1121 }
1122
1123 /*******************************************************************
1124  *
1125  * @brief Fills the mandatory RicAdmitted List Items
1126  *
1127  * @details
1128  *
1129  *    Function : fillRicAdmitList
1130  *
1131  *    Functionality: Fills the mandatory Ric Admitted List Items
1132  *
1133  * @params[in] RICaction_Admitted_ItemIEs_t *ricAdmitItems
1134  * @return ROK     - success
1135  *         RFAILED - failure
1136  *
1137  * ****************************************************************/
1138
1139 uint8_t fillRicAdmitList(RICaction_Admitted_ItemIEs_t *ricAdmitItems)
1140 {
1141
1142    if(ricAdmitItems != NULLP)
1143    {
1144       ricAdmitItems->id = ProtocolIE_IDE2_id_RICaction_Admitted_Item;
1145       ricAdmitItems->criticality = CriticalityE2_reject;
1146       ricAdmitItems->value.present = RICaction_Admitted_ItemIEs__value_PR_RICaction_Admitted_Item;
1147       ricAdmitItems->value.choice.RICaction_Admitted_Item.ricActionID = 1; 
1148    }
1149    else
1150    {
1151       return RFAILED;
1152    }
1153    return ROK;
1154 }
1155 /*******************************************************************
1156  *
1157  * @brief Builds the mandatory RicAdmitted List Params
1158  *
1159  * @details
1160  *
1161  *    Function : BuildRicAdmitList
1162  *
1163  *    Functionality: Builds the mandatory Ric Admitted List Params
1164  *
1165  * @params[in] RICaction_Admitted_List_t *admitListPtr
1166  * @return ROK     - success
1167  *         RFAILED - failure
1168  *
1169  * ****************************************************************/
1170
1171 uint8_t BuildRicAdmitList(RICaction_Admitted_List_t *admitListPtr)
1172 {
1173    uint8_t idx ;
1174    uint8_t elementCnt;  
1175    uint8_t ret= ROK;
1176    elementCnt = 1;
1177
1178    if(admitListPtr == NULLP)
1179    {
1180       DU_LOG("\nERROR  -->  E2AP : Memory allocation for RIC Admit List failed");
1181       ret = RFAILED;
1182    }
1183    else
1184    {
1185       admitListPtr->list.count = elementCnt;
1186       admitListPtr->list.size  = elementCnt * sizeof(RICaction_Admitted_ItemIEs_t);
1187       DU_ALLOC(admitListPtr->list.array, admitListPtr->list.size);
1188       if(admitListPtr->list.array == NULLP)
1189       {
1190          DU_LOG("\nERROR  -->  E2AP : Memory allocation for RIC Admit List failed");
1191          ret = RFAILED;
1192       }
1193       else
1194       {
1195          for(idx=0 ; idx<elementCnt ; idx++ )
1196          {
1197             DU_ALLOC(admitListPtr->list.array[idx], sizeof(RICaction_Admitted_ItemIEs_t));
1198             if(admitListPtr->list.array[idx] == NULLP)
1199             {
1200                ret = RFAILED;
1201             }
1202          }
1203          if(ret != RFAILED)
1204          {
1205             idx=0;
1206             fillRicAdmitList((RICaction_Admitted_ItemIEs_t *)admitListPtr->list.array[idx]);
1207          }
1208       }
1209    }    
1210    return ret;
1211 }
1212 /*******************************************************************
1213  *
1214  * @breif Deallocation of BuildAndSendRicSubscriptionRsp memory
1215  *
1216  * @details
1217  *
1218  *    Function : FreeRicSubscriptionRsp
1219  *
1220  * Functionality:Free the RicSubscriptionRsp
1221  *
1222  * @param[in] E2AP_PDU_t *e2apRicMsg
1223  *
1224  * @return void
1225  *      
1226  *
1227  ******************************************************************/
1228 void FreeRicSubscriptionRsp(E2AP_PDU_t  *e2apRicMsg)
1229 {
1230    RICsubscriptionResponse_t  *ricSubscriptionRsp= NULLP;
1231    uint8_t idx=0;
1232    uint8_t idx1=0;
1233    RICaction_Admitted_List_t *admitListPtr;
1234
1235    if(e2apRicMsg != NULLP)
1236    {
1237       if(e2apRicMsg->choice.successfulOutcome != NULLP)
1238       {
1239          ricSubscriptionRsp = &e2apRicMsg->choice.successfulOutcome->value.choice.RICsubscriptionResponse;
1240          if(ricSubscriptionRsp)
1241          {
1242             if(ricSubscriptionRsp->protocolIEs.list.array != NULLP)
1243             {
1244                for(idx=0; idx<ricSubscriptionRsp->protocolIEs.list.count; idx++)
1245                {
1246                   if(ricSubscriptionRsp->protocolIEs.list.array[idx] != NULLP)
1247                   {
1248                      switch(ricSubscriptionRsp->protocolIEs.list.array[idx]->id)
1249                      {
1250                         case ProtocolIE_IDE2_id_RICrequestID:
1251                            break;
1252
1253                         case ProtocolIE_IDE2_id_RANfunctionID:
1254                            break;
1255
1256                         case ProtocolIE_IDE2_id_RICactions_Admitted:
1257                            {
1258                               admitListPtr = &ricSubscriptionRsp->protocolIEs.list.\
1259                                              array[idx]->value.choice.RICaction_Admitted_List;
1260                               if(admitListPtr->list.array != NULLP)
1261                               {
1262                                  for(idx1=0 ; idx1<admitListPtr->list.count; idx1++ )
1263                                  {
1264                                     if(admitListPtr->list.array[idx1] != NULLP)
1265                                     {
1266                                        DU_FREE(admitListPtr->list.array[idx1],
1267                                              sizeof(RICaction_Admitted_ItemIEs_t));
1268                                     }
1269                                  }
1270                                  DU_FREE(admitListPtr->list.array, admitListPtr->list.size);     
1271                               }
1272                               break;
1273                            }
1274                         default:
1275                            break;
1276                      }
1277                      DU_FREE(ricSubscriptionRsp->protocolIEs.list.array[idx], \
1278                            sizeof(RICsubscriptionResponse_IEs_t));
1279                   }
1280                }
1281                DU_FREE(ricSubscriptionRsp->protocolIEs.list.array, \
1282                      ricSubscriptionRsp->protocolIEs.list.size);
1283             }
1284          }   
1285          DU_FREE(e2apRicMsg->choice.successfulOutcome, sizeof(SuccessfulOutcomeE2_t));
1286       }         
1287       DU_FREE(e2apRicMsg, sizeof(E2AP_PDU_t));        
1288    }
1289 }
1290 /*******************************************************************
1291  *
1292  * @brief Builds and Send the RicSubscriptionRsp
1293  *
1294  * @details
1295  *
1296  *    Function : BuildAndSendRicSubscriptionRsp
1297  *
1298  * functionality:Fills the RicSubscriptionRsp
1299  *
1300  * @return ROK     - success
1301  *         RFAILED - failure
1302  *
1303  ******************************************************************/
1304 uint8_t  FillRicSubscriptionRsp(RICsubscriptionResponse_t  *ricSubscriptionRsp )
1305 {
1306    uint8_t idx=0;
1307    uint8_t ret = ROK;
1308    uint8_t elementCnt = 0;
1309    uint8_t BuildRicRequestIdret=ROK;
1310    uint8_t BuildRicAdmitListret=ROK;
1311
1312    elementCnt=3;
1313    ricSubscriptionRsp->protocolIEs.list.count = elementCnt;
1314    ricSubscriptionRsp->protocolIEs.list.size  = elementCnt * sizeof(RICsubscriptionResponse_IEs_t);
1315    DU_ALLOC(ricSubscriptionRsp->protocolIEs.list.array, \
1316          ricSubscriptionRsp->protocolIEs.list.size);
1317    if(ricSubscriptionRsp->protocolIEs.list.array == NULLP)
1318    {
1319       DU_LOG("\nERROR  -->  E2AP : Memory allocation for FillRicSubscriptionRsp  failed");
1320       ret = RFAILED;
1321    }
1322    else
1323    {
1324       for(idx=0; idx<ricSubscriptionRsp->protocolIEs.list.count; idx++)
1325       {
1326          DU_ALLOC(ricSubscriptionRsp->protocolIEs.list.array[idx], \
1327                sizeof(RICsubscriptionResponse_IEs_t));
1328          if(ricSubscriptionRsp->protocolIEs.list.array[idx] == NULLP)
1329          {
1330             ret = RFAILED;
1331          }
1332       }
1333       if(ret != RFAILED)
1334       {
1335
1336          idx=0;
1337          ricSubscriptionRsp->protocolIEs.list.array[idx]->id = ProtocolIE_IDE2_id_RICrequestID;
1338          ricSubscriptionRsp->protocolIEs.list.array[idx]->criticality = CriticalityE2_reject;
1339          ricSubscriptionRsp->protocolIEs.list.array[idx]->value.present =\
1340                                                                          RICsubscriptionRequest_IEs__value_PR_RICrequestID;
1341          BuildRicRequestIdret =
1342             BuildRicRequestId(&ricSubscriptionRsp->protocolIEs.list.array[idx]->value.choice.RICrequestID);
1343          if(BuildRicRequestIdret != ROK)
1344          {
1345             ret = RFAILED;
1346          }
1347          else
1348          {
1349             idx++;
1350             ricSubscriptionRsp->protocolIEs.list.array[idx]->id = ProtocolIE_IDE2_id_RANfunctionID;
1351             ricSubscriptionRsp->protocolIEs.list.array[idx]->criticality = CriticalityE2_reject;
1352             ricSubscriptionRsp->protocolIEs.list.array[idx]->value.present =\
1353                                                                             RICsubscriptionRequest_IEs__value_PR_RANfunctionID;
1354             ricSubscriptionRsp->protocolIEs.list.array[idx]->value.choice.RANfunctionID = 1;
1355
1356             idx++;
1357             ricSubscriptionRsp->protocolIEs.list.array[idx]->id = ProtocolIE_IDE2_id_RICactions_Admitted;
1358             ricSubscriptionRsp->protocolIEs.list.array[idx]->criticality = CriticalityE2_reject;
1359             ricSubscriptionRsp->protocolIEs.list.array[idx]->value.present =\
1360                                                                             RICsubscriptionResponse_IEs__value_PR_RICaction_Admitted_List;
1361             BuildRicAdmitListret =
1362                BuildRicAdmitList(&ricSubscriptionRsp->protocolIEs.list.array[idx]->value.choice.RICaction_Admitted_List);
1363             if(BuildRicAdmitListret != ROK)
1364             {
1365                ret = RFAILED;
1366             }
1367          }
1368       }
1369    }    
1370    return ret;
1371 }
1372 /*******************************************************************
1373  *
1374  * @brief Builds and Send the RicSubscriptionRsp
1375  *
1376  * @details
1377  *
1378  *    Function : BuildAndSendRicSubscriptionRsp
1379  *
1380  * Functionality:Fills the RicSubscriptionRsp
1381  *
1382  * @return ROK     - success
1383  *         RFAILED - failure
1384  *
1385  ******************************************************************/
1386
1387 uint8_t BuildAndSendRicSubscriptionRsp()
1388 {
1389
1390    E2AP_PDU_t         *e2apRicMsg = NULLP;
1391    RICsubscriptionResponse_t  *ricSubscriptionRsp=NULLP;
1392    asn_enc_rval_t     encRetVal; 
1393    uint8_t ret = RFAILED;
1394    uint8_t FillRicricSubscriptionRspret;
1395
1396    while(true)
1397    {
1398       DU_LOG("\nINFO   -->  E2AP : Building RIC Subscription Response\n");
1399
1400       DU_ALLOC(e2apRicMsg, sizeof(E2AP_PDU_t)); 
1401       if(e2apRicMsg == NULLP)
1402       {
1403          DU_LOG("\nERROR  -->  E2AP : Memory allocation for E2AP-PDU failed");
1404          break;
1405       }
1406       e2apRicMsg->present =  E2AP_PDU_PR_successfulOutcome;
1407       DU_ALLOC(e2apRicMsg->choice.successfulOutcome, sizeof(SuccessfulOutcomeE2_t));
1408       if(e2apRicMsg->choice.successfulOutcome == NULLP)
1409       {
1410          DU_LOG("\nERROR  -->  E2AP : Memory allocation for RIC subscription Response failed");
1411          break;
1412       }
1413
1414       e2apRicMsg->choice.successfulOutcome->procedureCode = ProcedureCodeE2_id_RICsubscription;
1415       e2apRicMsg->choice.successfulOutcome->criticality = CriticalityE2_reject;
1416       e2apRicMsg->choice.successfulOutcome->value.present = \
1417                                                             SuccessfulOutcomeE2__value_PR_RICsubscriptionResponse;
1418       ricSubscriptionRsp = &e2apRicMsg->choice.successfulOutcome->value.choice.RICsubscriptionResponse;
1419
1420       FillRicricSubscriptionRspret = FillRicSubscriptionRsp(ricSubscriptionRsp);
1421       if(FillRicricSubscriptionRspret != ROK)
1422       {
1423          DU_LOG("\nERROR  -->  E2AP : Memory allocation for RICsubscriptionResponseIE failed");
1424          break;
1425       }
1426
1427       /* Prints the Msg formed */
1428       xer_fprint(stdout, &asn_DEF_E2AP_PDU, e2apRicMsg);
1429
1430       memset(encBuf, 0, ENC_BUF_MAX_LEN);
1431       encBufSize = 0;
1432       encRetVal = aper_encode(&asn_DEF_E2AP_PDU, 0, e2apRicMsg, PrepFinalEncBuf,\
1433             encBuf);
1434       if(encRetVal.encoded == ENCODE_FAIL)
1435       {
1436          DU_LOG("\nERROR  -->  E2AP : Could not encode RIC Subscription Response structure (at %s)\n",\
1437                encRetVal.failed_type ? encRetVal.failed_type->name : "unknown");
1438          break;
1439       }
1440       else
1441       {
1442          DU_LOG("\nDEBUG   -->  E2AP : Created APER encoded buffer for RIC subscription response \n");
1443 #ifdef DEBUG_ASN_PRINT
1444          for(int i=0; i< encBufSize; i++)
1445          {
1446             printf("%x",encBuf[i]);
1447          } 
1448 #endif
1449       } 
1450
1451       if(SendE2APMsg(DU_APP_MEM_REGION, DU_POOL, encBuf, encBufSize) != ROK)
1452       {
1453          DU_LOG("\nERROR  -->  E2AP : Sending RIC Subscription Response failed");      
1454          break;
1455       }
1456
1457       ret = ROK;
1458       break;
1459
1460    }
1461    FreeRicSubscriptionRsp(e2apRicMsg);
1462
1463    return ret;
1464 }
1465
1466 /******************************************************************
1467  *
1468  * @brief Deallocation of memory allocated bu aper decoder for e2 setup response
1469  *
1470  * @details
1471  *
1472  *    Function : freeAperDecodingOfE2SetupRsp
1473  *
1474  *    Functionality: Deallocation of memory allocated bu aper decoder for e2
1475  *    setup response
1476  *
1477  * @params[in] E2setupResponse_t *e2SetRspMsg;
1478  * @return void
1479  *
1480  * ****************************************************************/
1481 void freeAperDecodingOfE2SetupRsp(E2setupResponse_t *e2SetRspMsg)
1482 {
1483    uint8_t arrIdx, e2NodeConfigAddAckListIdx;
1484    E2nodeComponentConfigAdditionAck_ItemIEs_t *e2NodeAddAckItem;
1485    E2nodeComponentConfigAdditionAck_List_t *e2NodeConfigAddAckList;
1486
1487    if(e2SetRspMsg)
1488    {
1489       if(e2SetRspMsg->protocolIEs.list.array)
1490       {
1491          for(arrIdx=0; arrIdx<e2SetRspMsg->protocolIEs.list.count; arrIdx++)
1492          {
1493             if(e2SetRspMsg->protocolIEs.list.array[arrIdx])
1494             {
1495                switch(e2SetRspMsg->protocolIEs.list.array[arrIdx]->id)
1496                {
1497                   case ProtocolIE_IDE2_id_TransactionID:
1498                      break;
1499
1500                   case ProtocolIE_IDE2_id_GlobalRIC_ID:
1501                      {
1502                         free(e2SetRspMsg->protocolIEs.list.array[arrIdx]->value.choice.GlobalRIC_ID.pLMN_Identity.buf);
1503                         free(e2SetRspMsg->protocolIEs.list.array[arrIdx]->value.choice.GlobalRIC_ID.ric_ID.buf);
1504                         break;
1505                      }
1506
1507                   case ProtocolIE_IDE2_id_E2nodeComponentConfigAdditionAck:
1508                      {
1509                         e2NodeConfigAddAckList = &e2SetRspMsg->protocolIEs.list.array[arrIdx]->value.choice.E2nodeComponentConfigAdditionAck_List;
1510                         if(e2NodeConfigAddAckList->list.array )
1511                         {
1512                            for(e2NodeConfigAddAckListIdx = 0; e2NodeConfigAddAckListIdx< e2NodeConfigAddAckList->list.count; e2NodeConfigAddAckListIdx++)
1513                            {
1514                               if(e2NodeConfigAddAckList->list.array[e2NodeConfigAddAckListIdx])
1515                               {
1516                                  e2NodeAddAckItem = (E2nodeComponentConfigAdditionAck_ItemIEs_t*) e2NodeConfigAddAckList->list.array[e2NodeConfigAddAckListIdx];
1517                                  free(e2NodeAddAckItem->value.choice.E2nodeComponentConfigAdditionAck_Item.e2nodeComponentID.choice.\
1518                                        e2nodeComponentInterfaceTypeF1->gNB_DU_ID.buf);
1519                                  free(e2NodeAddAckItem->value.choice.E2nodeComponentConfigAdditionAck_Item.e2nodeComponentID.choice.\
1520                                        e2nodeComponentInterfaceTypeF1);
1521                                  free(e2NodeConfigAddAckList->list.array[e2NodeConfigAddAckListIdx]);
1522                               }
1523                            }
1524                            free(e2NodeConfigAddAckList->list.array);
1525                         }
1526                         break;
1527                      }
1528                }
1529                free(e2SetRspMsg->protocolIEs.list.array[arrIdx]);  
1530             }
1531          }
1532          free(e2SetRspMsg->protocolIEs.list.array);
1533       }
1534    }
1535 }
1536 /******************************************************************
1537  *
1538  * @brief Processes E2 Setup Response sent by RIC
1539  *
1540  * @details
1541  *
1542  *    Function : procE2SetupRsp
1543  *
1544  *    Functionality: Processes E2 Setup Response sent by RIC
1545  *
1546  * @params[in] E2AP_PDU_t ASN decoded E2AP message
1547  * @return ROK     - success
1548  *         RFAILED - failure
1549  *
1550  * ****************************************************************/
1551 uint8_t procE2SetupRsp(E2AP_PDU_t *e2apMsg)
1552 {
1553    uint8_t arrIdx =0, transId=0; 
1554    uint32_t recvBufLen;             
1555    E2setupResponse_t *e2SetRspMsg;
1556    CmLList         *node;
1557    E2NodeComponent *e2NodeComponentInfo;
1558
1559    DU_LOG("\nINFO   -->  E2AP : E2 Setup Response received"); 
1560    duCb.e2Status = TRUE; //Set E2 status as true
1561    e2SetRspMsg = &e2apMsg->choice.successfulOutcome->value.choice.E2setupResponse;
1562
1563    for(arrIdx=0; arrIdx<e2SetRspMsg->protocolIEs.list.count; arrIdx++)
1564    {
1565       switch(e2SetRspMsg->protocolIEs.list.array[arrIdx]->id)
1566       {
1567          case ProtocolIE_IDE2_id_TransactionID:
1568             {
1569                transId = e2SetRspMsg->protocolIEs.list.array[arrIdx]->value.choice.TransactionID;
1570                if((duCb.e2apDb.e2TransInfo.e2InitTransaction[transId].transactionId == transId) &&\
1571                      (duCb.e2apDb.e2TransInfo.e2InitTransaction[transId].procedureCode == e2apMsg->choice.successfulOutcome->procedureCode))
1572                {
1573                   memset(&duCb.e2apDb.e2TransInfo.e2InitTransaction[transId], 0, sizeof(E2TransInfo));
1574                }
1575                else
1576                {
1577                   DU_LOG("\nERROR  -->  E2AP : Invalid transaction id [%d]", transId);
1578                   return RFAILED;
1579                }
1580                break;
1581             }
1582
1583          case ProtocolIE_IDE2_id_GlobalRIC_ID:
1584             {
1585                /* To store the Ric Id Params */
1586                recvBufLen = sizeof(e2SetRspMsg->protocolIEs.list.array[arrIdx]->value\
1587                      .choice.GlobalRIC_ID.pLMN_Identity.size);
1588                   memcpy(&duCb.e2apDb.ricId.plmnId, e2SetRspMsg->protocolIEs.list.array[arrIdx]\
1589                         ->value.choice.GlobalRIC_ID.pLMN_Identity.buf, recvBufLen);
1590                bitStringToInt(&e2SetRspMsg->protocolIEs.list.array[arrIdx]->value.choice.GlobalRIC_ID.ric_ID, &duCb.e2apDb.ricId);
1591                /*TODO : duCb.e2apDb.ricId.plmnId memory to be deallocated after the usage */
1592                break;
1593             }
1594
1595          case ProtocolIE_IDE2_id_E2nodeComponentConfigAdditionAck:
1596             break;
1597
1598          default:
1599             DU_LOG("\nERROR  -->  E2AP : Invalid IE received in E2SetupRsp:%ld",
1600                   e2SetRspMsg->protocolIEs.list.array[arrIdx]->id);
1601             break;
1602       }
1603    }
1604    freeAperDecodingOfE2SetupRsp(e2SetRspMsg);
1605    
1606    node = searchE2NodeComponentInfo(F1, E2_NODE_COMPONENT_ADD);
1607    if(!node)
1608    {
1609       DU_LOG("\nERROR  --> E2AP : Received e2NodeComponentInfo is null");
1610       return RFAILED;
1611    }
1612    else
1613    {
1614       e2NodeComponentInfo = (E2NodeComponent*)node->node;
1615       cmLListDelFrm(&duCb.e2apDb.e2NodeComponentList, node);
1616       DU_FREE(e2NodeComponentInfo->componentRequestPart, e2NodeComponentInfo->reqBufSize);
1617       DU_FREE(e2NodeComponentInfo->componentResponsePart, e2NodeComponentInfo->rspBufSize);
1618       DU_FREE(e2NodeComponentInfo, sizeof(E2NodeComponent));
1619       DU_FREE(node, sizeof(CmLList));
1620    }
1621
1622    BuildAndSendE2NodeConfigUpdate();
1623    return ROK;
1624 }
1625
1626 /******************************************************************
1627  *
1628  * @brief Processes RIC Subscription Req sent by RIC
1629  *
1630  * @details
1631  *
1632  *    Function : procRicSubsReq
1633  *
1634  *    Functionality: Processes E2 Setup Response sent by CU
1635  *
1636  * @params[in] E2AP_PDU_t ASN decoded E2AP message
1637  * @return ROK     - success
1638  *         RFAILED - failure
1639  *
1640  * ****************************************************************/
1641
1642 uint8_t procRicSubsReq(E2AP_PDU_t *e2apMsg)
1643 {
1644    uint8_t idx; 
1645    uint8_t ied; 
1646    uint8_t ret = ROK;
1647    CmLList  *ricSubscriptionNode = NULLP;
1648    RICsubscriptionRequest_t *ricSubsReq;
1649    RicSubscription *ricSubscriptionInfo;
1650    RICaction_ToBeSetup_ItemIEs_t *actionItem;
1651
1652    DU_LOG("\nINFO   -->  E2AP : RIC Subscription request received"); 
1653    ricSubsReq = &e2apMsg->choice.initiatingMessage->value.choice.RICsubscriptionRequest;
1654
1655    for(idx=0; idx<ricSubsReq->protocolIEs.list.count; idx++)
1656    {
1657       if(ricSubsReq->protocolIEs.list.array[idx])
1658       {
1659          switch(ricSubsReq->protocolIEs.list.array[idx]->id)
1660          {
1661             case ProtocolIE_IDE2_id_RICrequestID:
1662                {
1663                   /* TODO :- ricSubscriptionInfo details will be stored based on
1664                    * RAN function id, so first we need to search RAN function and then add
1665                    * subscription details to that ran function */
1666                   DU_ALLOC(ricSubscriptionInfo, sizeof(RicSubscription));
1667                   if(!ricSubscriptionInfo)
1668                   {
1669                      DU_LOG("\nERROR  -->  E2AP : Memory allocation failed for ricSubscriptionInfo");
1670                      return RFAILED;
1671                   }
1672                   ricSubscriptionInfo->requestId.requestorId = ricSubsReq->protocolIEs.list.array[idx]->value.choice.RICrequestID.ricRequestorID;
1673                   ricSubscriptionInfo->requestId.instanceId = ricSubsReq->protocolIEs.list.array[idx]->value.choice.RICrequestID.ricInstanceID;
1674                   DU_ALLOC(ricSubscriptionNode, sizeof(CmLList));
1675                   if(ricSubscriptionNode)
1676                   {
1677                      ricSubscriptionNode->node = (PTR) ricSubscriptionInfo;
1678                      cmLListAdd2Tail(&duCb.e2apDb.ranFunction[0].subscriptionList,ricSubscriptionNode);
1679                   }
1680                   break;
1681                }
1682             case ProtocolIE_IDE2_id_RANfunctionID:
1683                {
1684                   duCb.e2apDb.ranFunction[0].id = ricSubsReq->protocolIEs.list.array[idx]-> \
1685                                           value.choice.RANfunctionID; 
1686                   break;
1687                }
1688             case ProtocolIE_IDE2_id_RICsubscriptionDetails:
1689                {
1690                   if(ricSubsReq->protocolIEs.list.array[idx]->value.choice.RICsubscriptionDetails.ricAction_ToBeSetup_List.\
1691                         list.array)
1692                   {
1693                      actionItem =(RICaction_ToBeSetup_ItemIEs_t *)ricSubsReq->protocolIEs.list\
1694                                  .array[idx]->value.choice.RICsubscriptionDetails.ricAction_ToBeSetup_List\
1695                                  .list.array[0];
1696
1697                      for(ied = 0; ied < ricSubsReq->protocolIEs.list.array[idx]->value.choice.\
1698                            RICsubscriptionDetails.ricAction_ToBeSetup_List.list.count; ied++)
1699                      {
1700                         switch(actionItem->id)
1701                         {
1702                            case ProtocolIE_IDE2_id_RICaction_ToBeSetup_Item:
1703                               {
1704                                  ricSubscriptionInfo->actionSequence[0].id  = actionItem->value.choice.RICaction_ToBeSetup_Item.ricActionID;
1705                                  ricSubscriptionInfo->actionSequence[0].type = actionItem->value.choice.RICaction_ToBeSetup_Item.ricActionType;
1706                                  break;
1707                               }
1708                            default:
1709                               DU_LOG("\nERROR  -->  E2AP : Invalid IE received in RicSetupLst:%ld",actionItem->id);
1710                               break;
1711                         }
1712                         free(actionItem);
1713                      }
1714                      free(ricSubsReq->protocolIEs.list.array[idx]->value.choice.RICsubscriptionDetails.ricAction_ToBeSetup_List.\
1715                            list.array);
1716
1717                      /* This is a dummy trigger for statistics request. It will
1718                       * be removed in next gerrit and actual statistics request
1719                       * will be sent when RIC subscription request is received
1720                       * from RIC */
1721                      ricSubscriptionInfo->actionSequence[0].definition.styleType = 1;
1722                      BuildAndSendStatsReq(ricSubscriptionInfo->actionSequence[0].definition);
1723                   }
1724                   break;
1725                }
1726
1727             default:
1728                DU_LOG("\nERROR  -->  E2AP : Invalid IE received in RIC SubsReq:%ld",
1729                      ricSubsReq->protocolIEs.list.array[idx]->id);
1730                break;
1731          }
1732          free(ricSubsReq->protocolIEs.list.array[idx]);
1733       }
1734    }
1735    free(ricSubsReq->protocolIEs.list.array);
1736    ret = BuildAndSendRicSubscriptionRsp();
1737    {
1738       BuildAndSendRicIndication(ricSubscriptionInfo);
1739    }
1740
1741    return ret;
1742 }
1743
1744 /*******************************************************************
1745  *
1746  * @brief Free the RicIndication Message
1747  *
1748  * @details
1749  *
1750  *    Function : FreeRicIndication
1751  *
1752  * Functionality: Free the RicIndication Message
1753  *
1754  * @return void
1755  *         
1756  *
1757  ******************************************************************/
1758 void FreeRicIndication(E2AP_PDU_t  *e2apMsg) 
1759 {
1760    uint8_t idx=0;
1761    RICindication_t *ricIndicationMsg= NULLP;
1762
1763
1764    if(e2apMsg != NULLP)
1765    {
1766       if(e2apMsg->choice.initiatingMessage != NULLP)
1767       {
1768          ricIndicationMsg = &e2apMsg->choice.initiatingMessage->value.choice.RICindication;
1769          if(ricIndicationMsg!= NULLP)
1770          {
1771             if(ricIndicationMsg->protocolIEs.list.array != NULLP)
1772             {
1773                for(idx=0; idx<ricIndicationMsg->protocolIEs.list.count; idx++)
1774                {
1775                   if(ricIndicationMsg->protocolIEs.list.array[idx] != NULLP)
1776                   {
1777                      switch(ricIndicationMsg->protocolIEs.list.array[idx]->id)
1778                      {
1779                         case ProtocolIE_IDE2_id_RICrequestID:
1780                            break;
1781
1782                         case ProtocolIE_IDE2_id_RANfunctionID:
1783                            break;
1784
1785                         case ProtocolIE_IDE2_id_RICactionID:
1786                            break;
1787
1788                         case ProtocolIE_IDE2_id_RICindicationType:
1789                            break;
1790
1791                         case ProtocolIE_IDE2_id_RICindicationHeader:
1792                            {
1793                               DU_FREE(ricIndicationMsg->protocolIEs.list.array[idx]->value.choice.RICindicationHeader.buf,\
1794                                     ricIndicationMsg->protocolIEs.list.array[idx]->value.choice.RICindicationHeader.size);
1795                               break;
1796                            }
1797                         case ProtocolIE_IDE2_id_RICindicationMessage:
1798                            {
1799                               DU_FREE(ricIndicationMsg->protocolIEs.list.array[idx]->value.choice.RICindicationMessage.buf,\
1800                                     ricIndicationMsg->protocolIEs.list.array[idx]->value.choice.RICindicationMessage.size);
1801                               break;
1802                            }
1803                         default:
1804                            break;
1805                      }
1806                      DU_FREE(ricIndicationMsg->protocolIEs.list.array[idx],sizeof(RICindication_IEs_t));
1807                   }
1808                }
1809                DU_FREE(ricIndicationMsg->protocolIEs.list.array,ricIndicationMsg->protocolIEs.list.size);
1810             }
1811          }
1812          DU_FREE(e2apMsg->choice.initiatingMessage, sizeof(InitiatingMessageE2_t));
1813       }
1814       DU_FREE(e2apMsg, sizeof(E2AP_PDU_t));
1815    }
1816 }
1817 /*******************************************************************
1818  *
1819  * brief Fill the RicIndication Message
1820  *
1821  * @details
1822  *
1823  *    Function : FillRicIndication
1824  *
1825  * Functionality:Fills the RicIndication Message
1826  *
1827  * @return ROK     - success
1828  *         RFAILED - failure
1829  *
1830  ******************************************************************/
1831 uint8_t FillRicIndication(RICindication_t *ricIndicationMsg, RicSubscription *ricSubscriptionInfo)
1832 {
1833    uint8_t elementCnt=0;
1834    uint8_t idx=0;
1835    uint8_t ret = ROK;
1836    elementCnt = 6;
1837
1838    ricIndicationMsg->protocolIEs.list.count = elementCnt;
1839    ricIndicationMsg->protocolIEs.list.size  = elementCnt * sizeof(RICindication_t);
1840    /* Initialize the Ric Indication members */
1841    DU_ALLOC(ricIndicationMsg->protocolIEs.list.array, \
1842          ricIndicationMsg->protocolIEs.list.size);
1843    if(ricIndicationMsg->protocolIEs.list.array == NULLP)
1844    {
1845       DU_LOG("\nERROR  -->  E2AP : Memory allocation for RICindicationIEs failed");
1846       ret = RFAILED;
1847    }
1848    else
1849    {
1850       for(idx=0; idx<elementCnt; idx++)
1851       {
1852          DU_ALLOC(ricIndicationMsg->protocolIEs.list.array[idx],\
1853                sizeof(RICindication_IEs_t));
1854          if(ricIndicationMsg->protocolIEs.list.array[idx] == NULLP)
1855          {
1856             DU_LOG("\nERROR  -->  E2AP : Memory allocation for RICindicationIEs failed");
1857             ret = RFAILED;
1858          }
1859       }
1860       if(ret != RFAILED)
1861       {
1862          idx = 0;
1863
1864          ricIndicationMsg->protocolIEs.list.array[idx]->id = ProtocolIE_IDE2_id_RICrequestID;
1865          ricIndicationMsg->protocolIEs.list.array[idx]->criticality = CriticalityE2_reject;
1866          ricIndicationMsg->protocolIEs.list.array[idx]->value.present = \
1867                                                                         RICindication_IEs__value_PR_RICrequestID;
1868          ricIndicationMsg->protocolIEs.list.array[idx]->value.choice.RICrequestID.ricRequestorID =ricSubscriptionInfo->requestId.requestorId;
1869          ricIndicationMsg->protocolIEs.list.array[idx]->value.choice.RICrequestID.ricInstanceID = ricSubscriptionInfo->requestId.instanceId;
1870
1871          idx++;
1872          ricIndicationMsg->protocolIEs.list.array[idx]->id = ProtocolIE_IDE2_id_RANfunctionID;
1873          ricIndicationMsg->protocolIEs.list.array[idx]->criticality = CriticalityE2_reject;
1874          ricIndicationMsg->protocolIEs.list.array[idx]->value.present = \
1875                                                                         RICindication_IEs__value_PR_RANfunctionID;
1876          ricIndicationMsg->protocolIEs.list.array[idx]->value.choice.RANfunctionID = duCb.e2apDb.ranFunction[0].id;
1877
1878          idx++;
1879          ricIndicationMsg->protocolIEs.list.array[idx]->id = ProtocolIE_IDE2_id_RICactionID;
1880          ricIndicationMsg->protocolIEs.list.array[idx]->criticality = CriticalityE2_reject;
1881          ricIndicationMsg->protocolIEs.list.array[idx]->value.present = \
1882                                                                         RICindication_IEs__value_PR_RICactionID;
1883          ricIndicationMsg->protocolIEs.list.array[idx]->value.choice.RICactionID = ricSubscriptionInfo->actionSequence[0].id;
1884
1885          idx++;
1886          ricIndicationMsg->protocolIEs.list.array[idx]->id = ProtocolIE_IDE2_id_RICindicationType;
1887          ricIndicationMsg->protocolIEs.list.array[idx]->criticality = CriticalityE2_reject;
1888          ricIndicationMsg->protocolIEs.list.array[idx]->value.present = \
1889                                                                         RICindication_IEs__value_PR_RICindicationType;
1890          ricIndicationMsg->protocolIEs.list.array[idx]->value.choice.RICindicationType = ricSubscriptionInfo->actionSequence[0].type;
1891
1892          idx++;
1893          ricIndicationMsg->protocolIEs.list.array[idx]->id = ProtocolIE_IDE2_id_RICindicationHeader;
1894          ricIndicationMsg->protocolIEs.list.array[idx]->criticality = CriticalityE2_reject;
1895          ricIndicationMsg->protocolIEs.list.array[idx]->value.present = \
1896                                                                         RICindication_IEs__value_PR_RICindicationHeader;
1897          ricIndicationMsg->protocolIEs.list.array[idx]->value.choice.RICindicationHeader.size = 3 *
1898             sizeof(uint8_t);
1899          DU_ALLOC(ricIndicationMsg->protocolIEs.list.array[idx]->value.choice.RICindicationHeader.buf ,\
1900                ricIndicationMsg->protocolIEs.list.array[idx]->value.choice.RICindicationHeader.size);
1901          if(ricIndicationMsg->protocolIEs.list.array[idx]->value.choice.RICindicationHeader.buf == NULLP)
1902          {
1903             DU_LOG("\nERROR  -->  E2AP : Memory allocation for RICindicationIEs failed");
1904             ret = RFAILED;
1905          }
1906          else
1907          {
1908             buildPlmnId(duCfgParam.srvdCellLst[0].duCellInfo.cellInfo.nrCgi.plmn, \
1909                   ricIndicationMsg->protocolIEs.list.array[idx]->value.choice.RICindicationHeader.buf);
1910             idx++;
1911             /* TO BE CHANGED: RIC INDICATION DATA */
1912             /* For now filling a dummy octect data, need to tested with PRBs*/
1913             ricIndicationMsg->protocolIEs.list.array[idx]->id = ProtocolIE_IDE2_id_RICindicationMessage;
1914             ricIndicationMsg->protocolIEs.list.array[idx]->criticality = CriticalityE2_reject;
1915             ricIndicationMsg->protocolIEs.list.array[idx]->value.present = \
1916                                                                            RICindication_IEs__value_PR_RICindicationMessage;
1917             ricIndicationMsg->protocolIEs.list.array[idx]->value.choice.RICindicationMessage.size = 3 *
1918                sizeof(uint8_t);
1919             DU_ALLOC(ricIndicationMsg->protocolIEs.list.array[idx]->value.choice.RICindicationMessage.buf ,\
1920                   ricIndicationMsg->protocolIEs.list.array[idx]->value.choice.RICindicationMessage.size);
1921             if(ricIndicationMsg->protocolIEs.list.array[idx]->value.choice.RICindicationMessage.buf == NULLP)
1922             {
1923                DU_LOG("\nERROR  -->  E2AP : Memory allocation for RICindicationIEs failed");
1924                ret = RFAILED;
1925             }
1926             else
1927             {
1928                buildPlmnId(duCfgParam.srvdCellLst[0].duCellInfo.cellInfo.nrCgi.plmn, \
1929                      ricIndicationMsg->protocolIEs.list.array[idx]->value.choice.RICindicationMessage.buf);
1930             }
1931          }
1932       }
1933    }
1934    return ret;
1935 }
1936
1937 /*******************************************************************
1938  *
1939  * @brief Builds and Send the RicIndication Message
1940  *
1941  * @details
1942  *
1943  *    Function : BuildAndSendRicIndication
1944  *
1945  * Functionality:Fills the RicIndication Message
1946  *
1947  * @return ROK     - success
1948  *         RFAILED - failure
1949  *
1950  ******************************************************************/
1951
1952 uint8_t BuildAndSendRicIndication(RicSubscription *ricSubscriptionInfo)
1953 {
1954    E2AP_PDU_t                 *e2apMsg = NULLP;
1955    RICindication_t            *ricIndicationMsg=NULLP;
1956    asn_enc_rval_t             encRetVal;        /* Encoder return value */
1957    uint8_t ret = RFAILED; 
1958    uint8_t FillRicIndicationret = ROK;
1959
1960    while(true)
1961    {
1962       DU_LOG("\nINFO   -->  E2AP : Building RIC Indication Message\n");
1963
1964       DU_ALLOC(e2apMsg, sizeof(E2AP_PDU_t));
1965       if(e2apMsg == NULLP)
1966       {
1967          DU_LOG("\nERROR  -->  E2AP : Memory allocation for E2AP-PDU failed");
1968          break;
1969       }
1970
1971       e2apMsg->present = E2AP_PDU_PR_initiatingMessage;
1972       DU_ALLOC(e2apMsg->choice.initiatingMessage, sizeof(InitiatingMessageE2_t));
1973       if(e2apMsg->choice.initiatingMessage == NULLP)
1974       {
1975          DU_LOG("\nERROR  -->  E2AP : Memory allocation for E2AP-PDU failed");
1976          break;
1977       }
1978       e2apMsg->choice.initiatingMessage->procedureCode = ProcedureCodeE2_id_RICindication;
1979       e2apMsg->choice.initiatingMessage->criticality = CriticalityE2_reject;
1980       e2apMsg->choice.initiatingMessage->value.present = InitiatingMessageE2__value_PR_RICindication;
1981
1982       ricIndicationMsg = &e2apMsg->choice.initiatingMessage->value.choice.RICindication;
1983
1984       FillRicIndicationret = FillRicIndication(ricIndicationMsg, ricSubscriptionInfo);
1985       if(FillRicIndicationret != ROK)
1986       {
1987          break;
1988       }
1989       /* Prints the Msg formed */
1990       xer_fprint(stdout, &asn_DEF_E2AP_PDU, e2apMsg);
1991       memset(encBuf, 0, ENC_BUF_MAX_LEN);
1992       encBufSize = 0;
1993       encRetVal = aper_encode(&asn_DEF_E2AP_PDU, 0, e2apMsg, PrepFinalEncBuf,\
1994             encBuf);
1995       if(encRetVal.encoded == ENCODE_FAIL)
1996       {
1997          DU_LOG("\nERROR  -->  E2AP : Could not encode RIC Indication Message (at %s)\n",\
1998                encRetVal.failed_type ? encRetVal.failed_type->name : "unknown");
1999          break;
2000       }
2001       else
2002       {
2003          DU_LOG("\nDEBUG  -->  E2AP : Created APER encoded buffer for RIC Indication Message \n");
2004 #ifdef DEBUG_ASN_PRINT
2005          for(int i=0; i< encBufSize; i++)
2006          {
2007             printf("%x",encBuf[i]);
2008          } 
2009 #endif
2010       }
2011
2012       if(SendE2APMsg(DU_APP_MEM_REGION, DU_POOL, encBuf, encBufSize) != ROK)
2013       {
2014          DU_LOG("\nINFO   -->  E2AP : Sending RIC Indication Message");      
2015
2016       }
2017       ret = ROK;
2018       break;
2019    }
2020    FreeRicIndication(e2apMsg);  
2021    return ret;
2022 }
2023
2024 /*******************************************************************
2025  *
2026  * @brief Deallocate the memory allocated for E2nodeConfigurationUpdate msg 
2027  *
2028  * @details
2029  *
2030  *    Function : FreeE2NodeConfigUpdate 
2031  *
2032  *    Functionality:
2033  *       - freeing the memory allocated for E2nodeConfigurationUpdate
2034  *
2035  * @params[in] E2AP_PDU_t *e2apMsg 
2036  * @return ROK     - success
2037  *         RFAILED - failure
2038  *
2039  * ****************************************************************/
2040 void FreeE2NodeConfigUpdate(E2AP_PDU_t *e2apMsg)
2041 {
2042    uint8_t arrIdx =0;
2043    E2nodeConfigurationUpdate_t *e2NodeConfigUpdate;
2044
2045    if(e2apMsg != NULLP)
2046    {
2047       if(e2apMsg->choice.initiatingMessage != NULLP)
2048       {
2049          e2NodeConfigUpdate = &e2apMsg->choice.initiatingMessage->value.choice.E2nodeConfigurationUpdate;
2050          if(e2NodeConfigUpdate->protocolIEs.list.array != NULLP)
2051          {
2052             for(arrIdx = 0; arrIdx < e2NodeConfigUpdate->protocolIEs.list.count; arrIdx++)
2053             {
2054                DU_FREE(e2NodeConfigUpdate->protocolIEs.list.array[arrIdx], sizeof(E2nodeConfigurationUpdate_IEs_t));
2055             }
2056             DU_FREE(e2NodeConfigUpdate->protocolIEs.list.array, e2NodeConfigUpdate->protocolIEs.list.size);
2057          }
2058          DU_FREE(e2apMsg->choice.initiatingMessage, sizeof(InitiatingMessageE2_t));
2059       }
2060       DU_FREE(e2apMsg, sizeof(E2AP_PDU_t));
2061    }
2062 }
2063
2064 /*******************************************************************
2065  *
2066  * @brief Buld and send the E2 node config update msg 
2067  *
2068  * @details
2069  *
2070  *    Function : BuildAndSendE2NodeConfigUpdate
2071  *
2072  *    Functionality:
2073  *         - Buld and send the E2 node config update msg
2074  *
2075  * @params[in] 
2076  * @return ROK     - success
2077  *         RFAILED - failure
2078  *
2079  * ****************************************************************/
2080
2081 uint8_t BuildAndSendE2NodeConfigUpdate()
2082 {
2083    uint8_t arrIdx = 0,elementCnt = 1;
2084    uint8_t ret = ROK;
2085    E2AP_PDU_t        *e2apMsg = NULLP;
2086    E2nodeConfigurationUpdate_t *e2NodeConfigUpdate = NULLP;
2087    asn_enc_rval_t     encRetVal;       /* Encoder return value */
2088
2089    DU_LOG("\nINFO   -->  E2AP : Building E2 Node config update\n");
2090    do
2091    {
2092       DU_ALLOC(e2apMsg, sizeof(E2AP_PDU_t));
2093       if(e2apMsg == NULLP)
2094       {
2095          DU_LOG("\nERROR  -->  E2AP : Memory allocation for E2AP-PDU failed");
2096          break;
2097       }
2098       e2apMsg->present = E2AP_PDU_PR_initiatingMessage;
2099       DU_ALLOC(e2apMsg->choice.initiatingMessage, sizeof(InitiatingMessageE2_t));
2100       if(e2apMsg->choice.initiatingMessage == NULLP)
2101       {
2102          DU_LOG("\nERROR  -->  E2AP : Memory allocation for E2AP-PDU failed");
2103          DU_FREE(e2apMsg, sizeof(E2AP_PDU_t));
2104          return RFAILED;
2105       }
2106       e2apMsg->choice.initiatingMessage->criticality = CriticalityE2_reject;
2107       e2apMsg->choice.initiatingMessage->procedureCode = ProcedureCodeE2_id_E2nodeConfigurationUpdate;
2108       e2apMsg->choice.initiatingMessage->value.present = \
2109       InitiatingMessageE2__value_PR_E2nodeConfigurationUpdate;
2110       e2NodeConfigUpdate = &e2apMsg->choice.initiatingMessage->value.choice.E2nodeConfigurationUpdate;
2111
2112       e2NodeConfigUpdate->protocolIEs.list.count = elementCnt;
2113       e2NodeConfigUpdate->protocolIEs.list.size  = elementCnt * sizeof(E2nodeConfigurationUpdate_IEs_t*);
2114       /* Initialize the Ric Indication members */
2115       DU_ALLOC(e2NodeConfigUpdate->protocolIEs.list.array, \
2116             e2NodeConfigUpdate->protocolIEs.list.size);
2117       if(e2NodeConfigUpdate->protocolIEs.list.array == NULLP)
2118       {
2119          DU_LOG("\nERROR  -->  E2AP : Memory allocation for e2NodeConfigUpdate failed");
2120          break;
2121       }
2122       
2123       for(arrIdx =0; arrIdx<elementCnt; arrIdx++)
2124       {
2125          DU_ALLOC(e2NodeConfigUpdate->protocolIEs.list.array[arrIdx], sizeof(E2nodeConfigurationUpdate_IEs_t));
2126          if(e2NodeConfigUpdate->protocolIEs.list.array[arrIdx] == NULLP)
2127          {
2128             
2129             DU_LOG("\nERROR  -->  E2AP : Memory allocation for e2NodeConfigUpdate failed");
2130             break;
2131          }
2132       }
2133
2134       arrIdx = 0;
2135       /* TransactionID */
2136       e2NodeConfigUpdate->protocolIEs.list.array[arrIdx]->id = ProtocolIE_IDE2_id_TransactionID;
2137       e2NodeConfigUpdate->protocolIEs.list.array[arrIdx]->criticality = CriticalityE2_reject;
2138       e2NodeConfigUpdate->protocolIEs.list.array[arrIdx]->value.present = E2nodeConfigurationUpdate_IEs__value_PR_TransactionID;
2139       e2NodeConfigUpdate->protocolIEs.list.array[arrIdx]->value.choice.TransactionID = TRANS_ID;
2140
2141
2142       /* Prints the Msg formed */
2143       xer_fprint(stdout, &asn_DEF_E2AP_PDU, e2apMsg);
2144
2145       memset(encBuf, 0, ENC_BUF_MAX_LEN);
2146       encBufSize = 0;
2147       encRetVal = aper_encode(&asn_DEF_E2AP_PDU, 0, e2apMsg, PrepFinalEncBuf,\
2148             encBuf);
2149       if(encRetVal.encoded == ENCODE_FAIL)
2150       {
2151          DU_LOG("\nERROR  -->  E2AP : Could not encode E2nodeConfigurationUpdate structure (at %s)\n",\
2152                encRetVal.failed_type ? encRetVal.failed_type->name : "unknown");
2153          break;
2154       }
2155       else
2156       {
2157          DU_LOG("\nDEBUG   -->  E2AP : Created APER encoded buffer for E2nodeConfigurationUpdate\n");
2158 #ifdef DEBUG_ASN_PRINT
2159          for(int i=0; i< encBufSize; i++)
2160          {
2161             printf("%x",encBuf[i]);
2162          }
2163 #endif
2164       }
2165       if(SendE2APMsg(DU_APP_MEM_REGION, DU_POOL, encBuf, encBufSize))
2166       {
2167          DU_LOG("\nERROR  -->  E2AP : Sending E2 node config update failed");
2168          return RFAILED;
2169       }
2170
2171       break;
2172    }while(true);
2173    
2174    FreeE2NodeConfigUpdate(e2apMsg);
2175    return ret;
2176 }
2177
2178 /*******************************************************************
2179  *
2180  * @brief Deallocate the memory allocated for E2ResetRequest msg
2181  *
2182  * @details
2183  *
2184  *    Function : FreeE2ResetRequest
2185  *
2186  *    Functionality:
2187  *       - freeing the memory allocated for E2ResetRequest
2188  *
2189  * @params[in] E2AP_PDU_t *e2apMsg
2190  * @return ROK     - success
2191  *         RFAILED - failure
2192  *
2193  * ****************************************************************/
2194 void FreeE2ResetRequest(E2AP_PDU_t *e2apMsg)
2195 {
2196    uint8_t ieIdx =0;
2197    ResetRequestE2_t  *resetReq = NULLP;
2198
2199    if(e2apMsg != NULLP)
2200    {
2201       if(e2apMsg->choice.initiatingMessage != NULLP)
2202       {
2203          resetReq = &e2apMsg->choice.initiatingMessage->value.choice.ResetRequestE2;
2204          if(resetReq->protocolIEs.list.array)
2205          {
2206             for(ieIdx = 0; ieIdx < resetReq->protocolIEs.list.count; ieIdx++)
2207             {
2208                DU_FREE(resetReq->protocolIEs.list.array[ieIdx], sizeof(ResetRequestIEs_t));
2209             }
2210             DU_FREE(resetReq->protocolIEs.list.array, resetReq->protocolIEs.list.size);
2211          }
2212          DU_FREE(e2apMsg->choice.initiatingMessage, sizeof(InitiatingMessageE2_t));
2213       }
2214       DU_FREE(e2apMsg, sizeof(E2AP_PDU_t));
2215    }
2216 }
2217
2218 /*******************************************************************
2219  *
2220  * @brief Build and send the E2 reset request msg
2221  *
2222  * @details
2223  *
2224  *    Function : BuildAndSendE2ResetRequest
2225  *
2226  *    Functionality:
2227  *         - Buld and send the E2 reset request msg to RIC
2228  *
2229  * @params[in]
2230  * @return ROK     - success
2231  *         RFAILED - failure
2232  *
2233  * ****************************************************************/
2234 uint8_t BuildAndSendE2ResetRequest(E2CauseType failureType, E2Cause failureCause)
2235 {
2236    uint8_t ieIdx = 0, elementCnt = 0, transId = 0;
2237    uint8_t ret = RFAILED;
2238    E2AP_PDU_t        *e2apMsg = NULLP;
2239    ResetRequestE2_t  *resetReq = NULLP;
2240    asn_enc_rval_t     encRetVal;       /* Encoder return value */
2241
2242    DU_LOG("\nINFO   -->  E2AP : Building E2 Reset Request\n");
2243
2244    do
2245    {
2246       DU_ALLOC(e2apMsg, sizeof(E2AP_PDU_t));
2247       if(e2apMsg == NULLP)
2248       {
2249          DU_LOG("\nERROR  -->  E2AP : BuildAndSendE2ResetRequest(): Memory allocation for E2AP-PDU failed");
2250          break;
2251       }
2252
2253       e2apMsg->present = E2AP_PDU_PR_initiatingMessage;
2254       DU_ALLOC(e2apMsg->choice.initiatingMessage, sizeof(InitiatingMessageE2_t));
2255       if(e2apMsg->choice.initiatingMessage == NULLP)
2256       {
2257          DU_LOG("\nERROR  -->  E2AP : BuildAndSendE2ResetRequest(): Memory allocation for initiatingMessage");
2258          break;
2259       }
2260
2261       e2apMsg->choice.initiatingMessage->procedureCode = ProcedureCodeE2_id_Reset;
2262       e2apMsg->choice.initiatingMessage->criticality = CriticalityE2_reject;
2263       e2apMsg->choice.initiatingMessage->value.present = InitiatingMessageE2__value_PR_ResetRequestE2;
2264       resetReq = &e2apMsg->choice.initiatingMessage->value.choice.ResetRequestE2;
2265
2266       elementCnt = 2;
2267       resetReq->protocolIEs.list.count = elementCnt;
2268       resetReq->protocolIEs.list.size = elementCnt * sizeof(ResetRequestIEs_t *);
2269
2270       DU_ALLOC(resetReq->protocolIEs.list.array, resetReq->protocolIEs.list.size);
2271       if(!resetReq->protocolIEs.list.array)
2272       {
2273          DU_LOG("\nERROR  -->  E2AP : BuildAndSendE2ResetRequest(): Memory allocation failed for \
2274             Reset Request IE array");
2275          break;
2276       }
2277
2278       for(ieIdx = 0; ieIdx < elementCnt; ieIdx++)
2279       {
2280          DU_ALLOC(resetReq->protocolIEs.list.array[ieIdx], sizeof(ResetRequestIEs_t));
2281          if(!resetReq->protocolIEs.list.array[ieIdx])
2282          {
2283             DU_LOG("\nERROR  -->  E2AP : BuildAndSendE2ResetRequest(): Memory allocation failed for \
2284             Reset Request IE array element");
2285             break;
2286          }
2287       }
2288
2289       /* In case of failure */
2290       if(ieIdx < elementCnt)
2291          break;
2292
2293       ieIdx = 0;
2294       resetReq->protocolIEs.list.array[ieIdx]->id = ProtocolIE_IDE2_id_TransactionID;
2295       resetReq->protocolIEs.list.array[ieIdx]->criticality = CriticalityE2_reject;
2296       resetReq->protocolIEs.list.array[ieIdx]->value.present = ResetRequestIEs__value_PR_TransactionID;
2297       transId = assignTransactionId();
2298       resetReq->protocolIEs.list.array[ieIdx]->value.choice.TransactionID = transId;
2299
2300       ieIdx++;
2301       resetReq->protocolIEs.list.array[ieIdx]->id = ProtocolIE_IDE2_id_CauseE2;
2302       resetReq->protocolIEs.list.array[ieIdx]->criticality = CriticalityE2_ignore;
2303       resetReq->protocolIEs.list.array[ieIdx]->value.present = ResetRequestIEs__value_PR_CauseE2;
2304       resetReq->protocolIEs.list.array[ieIdx]->value.choice.CauseE2.present = failureType;
2305       switch(resetReq->protocolIEs.list.array[ieIdx]->value.choice.CauseE2.present)
2306       {
2307          case CauseE2_PR_NOTHING:
2308             break;
2309          case CauseE2_PR_ricRequest:
2310             resetReq->protocolIEs.list.array[ieIdx]->value.choice.CauseE2.choice.ricRequest = failureCause;
2311             break;
2312          case CauseE2_PR_ricService:
2313             resetReq->protocolIEs.list.array[ieIdx]->value.choice.CauseE2.choice.ricService = failureCause;
2314             break;
2315          case CauseE2_PR_e2Node:
2316             resetReq->protocolIEs.list.array[ieIdx]->value.choice.CauseE2.choice.e2Node = failureCause;
2317             break;
2318          case CauseE2_PR_transport:
2319             resetReq->protocolIEs.list.array[ieIdx]->value.choice.CauseE2.choice.transport = failureCause;
2320             break;
2321          case CauseE2_PR_protocol:
2322             resetReq->protocolIEs.list.array[ieIdx]->value.choice.CauseE2.choice.protocol = failureCause;
2323             break;
2324          case CauseE2_PR_misc:
2325             resetReq->protocolIEs.list.array[ieIdx]->value.choice.CauseE2.choice.misc = failureCause;
2326             break;
2327       }
2328
2329       /* Prints the Msg formed */
2330       xer_fprint(stdout, &asn_DEF_E2AP_PDU, e2apMsg);
2331
2332       memset(encBuf, 0, ENC_BUF_MAX_LEN);
2333       encBufSize = 0;
2334       encRetVal = aper_encode(&asn_DEF_E2AP_PDU, 0, e2apMsg, PrepFinalEncBuf,\
2335             encBuf);
2336       if(encRetVal.encoded == ENCODE_FAIL)
2337       {
2338          DU_LOG("\nERROR  -->  E2AP : Could not encode E2SetupRequest structure (at %s)\n",\
2339                encRetVal.failed_type ? encRetVal.failed_type->name : "unknown");
2340          break;
2341       }
2342       else
2343       {
2344          DU_LOG("\nDEBUG   -->  E2AP : Created APER encoded buffer for E2SetupRequest\n");
2345 #ifdef DEBUG_ASN_PRINT
2346          for(int i=0; i< encBufSize; i++)
2347          {
2348             printf("%x",encBuf[i]);
2349          }
2350 #endif
2351       }
2352       if(SendE2APMsg(DU_APP_MEM_REGION, DU_POOL, encBuf, encBufSize) != ROK)
2353       {
2354          DU_LOG("\nERROR  -->  E2AP : Sending E2 Setup request failed");
2355          break;
2356       }
2357
2358       /* In case the message is sent successfully, store the transaction info to
2359        * be used when response is received */
2360       duCb.e2apDb.e2TransInfo.e2InitTransaction[transId].transactionId = transId;
2361       duCb.e2apDb.e2TransInfo.e2InitTransaction[transId].procedureCode = e2apMsg->choice.initiatingMessage->procedureCode;
2362
2363       ret = ROK;
2364       break;
2365    }while(true);
2366
2367    /* Free all memory */
2368    FreeE2ResetRequest(e2apMsg);
2369    return ret;
2370 }
2371
2372 /*******************************************************************
2373  *
2374  * @brief Deallocate the memory allocated for Reset Response msg
2375  *
2376  * @details
2377  *
2378  *    Function : freeAperDecodingOfE2ResetRsp
2379  *
2380  *    Functionality:
2381  *       - freeing the memory allocated for Reset response
2382  *
2383  * @params[in] ResetResponseE2_t *resetResponse
2384  * @return void
2385  *
2386  * ****************************************************************/
2387 void freeAperDecodingOfE2ResetRsp(ResetResponseE2_t *resetResponse)
2388 {
2389    uint8_t ieIdx;
2390
2391    if(resetResponse)
2392    {
2393       if(resetResponse->protocolIEs.list.array)
2394       {
2395          for(ieIdx=0; ieIdx < resetResponse->protocolIEs.list.count; ieIdx++)
2396          {
2397             if(resetResponse->protocolIEs.list.array[ieIdx])
2398             {
2399                switch(resetResponse->protocolIEs.list.array[ieIdx]->id)
2400                {
2401                   case ProtocolIE_IDE2_id_TransactionID:
2402                      break;
2403
2404                   case ProtocolIE_IDE2_id_CriticalityDiagnosticsE2:
2405                      break;
2406                }
2407                free(resetResponse->protocolIEs.list.array[ieIdx]);
2408             }
2409          }
2410          free(resetResponse->protocolIEs.list.array);
2411       }
2412    }
2413 }
2414
2415 /******************************************************************
2416  *
2417  * @brief Processes E2 Reset Response sent by RIC
2418  *
2419  * @details
2420  *
2421  *    Function : procResetResponse
2422  *
2423  *    Functionality: Processes E2 Reset Response sent by RIC
2424  *
2425  * @params[in] E2AP_PDU_t ASN decoded E2AP message
2426  * @return ROK     - success
2427  *         RFAILED - failure
2428  *
2429  * ****************************************************************/
2430 uint8_t procResetResponse(E2AP_PDU_t *e2apMsg)
2431 {
2432    uint8_t ieIdx =0, transId;
2433    ResetResponseE2_t *resetResponse;
2434
2435    DU_LOG("\nINFO   -->  E2AP : E2 Reset Response received");
2436    resetResponse = &e2apMsg->choice.successfulOutcome->value.choice.ResetResponseE2;;
2437
2438    for(ieIdx=0; ieIdx < resetResponse->protocolIEs.list.count; ieIdx++)
2439    {
2440       switch(resetResponse->protocolIEs.list.array[ieIdx]->id)
2441       {
2442          case ProtocolIE_IDE2_id_TransactionID:
2443             transId = resetResponse->protocolIEs.list.array[ieIdx]->value.choice.TransactionID;
2444             if((duCb.e2apDb.e2TransInfo.e2InitTransaction[transId].transactionId == transId) && \
2445                   (duCb.e2apDb.e2TransInfo.e2InitTransaction[transId].procedureCode == e2apMsg->choice.successfulOutcome->procedureCode))
2446             {
2447                memset(&duCb.e2apDb.e2TransInfo.e2InitTransaction[transId], 0, sizeof(E2TransInfo));
2448             }
2449             else
2450             {
2451                DU_LOG("\nERROR  -->  E2AP : Invalid transaction id [%d]", transId);
2452                return RFAILED;
2453             }
2454             break;
2455          case ProtocolIE_IDE2_id_CriticalityDiagnosticsE2:
2456             /* As per ORAN WG3 E2AP spec v3.0, section 9.2.2
2457                Criticality Diagnostics IE is sent by Near-RT RIC when parts of a received message i.e. 
2458                Reset Request in this case, have not been comprehended or were missing, or if the message 
2459                contained logical errors.
2460
2461                Processing of this ID should be implemented when negative call flows are to be supported.
2462              */
2463             break;
2464          default:
2465             DU_LOG("\nERROR  -->  E2AP : Invalid IE received in E2 Reset Response : %ld",
2466                   resetResponse->protocolIEs.list.array[ieIdx]->id);
2467             break;
2468       }
2469    }
2470
2471    freeAperDecodingOfE2ResetRsp(resetResponse);
2472    return ROK;
2473 }
2474
2475 /******************************************************************
2476  *
2477  * @brief Deallocation of memory allocated bu aper decoder for e2 setup Failure
2478  *
2479  * @details
2480  *
2481  *    Function : freeAperDecodingOfE2SetupFailure
2482  *
2483  *    Functionality: Deallocation of memory allocated bu aper decoder for e2
2484  *    setup Failure
2485  *
2486  * @params[in] E2setupFailure_t *e2SetupFailure;
2487  * @return void
2488  *
2489  * ****************************************************************/
2490 void freeAperDecodingOfE2SetupFailure(E2setupFailure_t *e2SetupFailure)
2491 {
2492    uint8_t arrIdx;
2493
2494    if(e2SetupFailure)
2495    {
2496       if(e2SetupFailure->protocolIEs.list.array)
2497       {
2498          for(arrIdx=0; arrIdx<e2SetupFailure->protocolIEs.list.count; arrIdx++)
2499          {
2500             if(e2SetupFailure->protocolIEs.list.array[arrIdx])
2501             {
2502                free(e2SetupFailure->protocolIEs.list.array[arrIdx]);  
2503             }
2504          }
2505          free(e2SetupFailure->protocolIEs.list.array);
2506       }
2507    }
2508 }
2509 /******************************************************************
2510  *
2511  * @brief Processes E2 Setup Failure sent by RIC
2512  *
2513  * @details
2514  *
2515  *    Function : procE2SetupFailure
2516  *
2517  *    Functionality: Processes E2 Setup failure sent by RIC
2518  *
2519  * @params[in] E2AP_PDU_t ASN decoded E2AP message
2520  * @return ROK     - success
2521  *         RFAILED - failure
2522  *
2523  * ****************************************************************/
2524 void procE2SetupFailure(E2AP_PDU_t *e2apMsg)
2525 {
2526    uint8_t arrIdx =0, transId =0, timerValue=0; 
2527    E2setupFailure_t *e2SetupFailure;
2528
2529    DU_LOG("\nINFO   -->  E2AP : E2 Setup failure received"); 
2530    e2SetupFailure = &e2apMsg->choice.unsuccessfulOutcome->value.choice.E2setupFailure;
2531
2532    for(arrIdx=0; arrIdx<e2SetupFailure->protocolIEs.list.count; arrIdx++)
2533    {
2534       switch(e2SetupFailure->protocolIEs.list.array[arrIdx]->id)
2535       {
2536          case ProtocolIE_IDE2_id_TransactionID:
2537          {
2538             transId = e2SetupFailure->protocolIEs.list.array[arrIdx]->value.choice.TransactionID;
2539             if((duCb.e2apDb.e2TransInfo.e2InitTransaction[transId].transactionId == transId) &&\
2540                   (duCb.e2apDb.e2TransInfo.e2InitTransaction[transId].procedureCode == e2apMsg->choice.unsuccessfulOutcome->procedureCode))
2541             {
2542                memset(&duCb.e2apDb.e2TransInfo.e2InitTransaction[transId], 0, sizeof(E2TransInfo));
2543             }
2544             else
2545             {
2546                DU_LOG("\nERROR  -->  E2AP : Invalid transaction id [%d]", transId);
2547                return ;
2548             }
2549             break;
2550          }
2551          case ProtocolIE_IDE2_id_TimeToWaitE2:
2552             {
2553                timerValue = covertE2WaitTimerEnumToValue(e2SetupFailure->protocolIEs.list.array[arrIdx]->value.choice.TimeToWaitE2);
2554                if((duChkTmr((PTR)&(duCb.e2apDb.e2TimersInfo.e2Timers.e2SetupTimer), EVENT_E2_SETUP_TMR)) == FALSE)
2555                {
2556                   duStartTmr((PTR)&(duCb.e2apDb.e2TimersInfo.e2Timers.e2SetupTimer), EVENT_E2_SETUP_TMR, timerValue);
2557                }
2558                else
2559                {
2560                   DU_LOG("\nERROR   -->  E2AP : EVENT_E2_SETUP_TMR timer is already running");
2561                   return;
2562                }
2563                break; 
2564             }
2565       }
2566    }
2567
2568    freeAperDecodingOfE2SetupFailure(e2SetupFailure);
2569 }
2570 /*******************************************************************
2571  *
2572  * @brief Handles received E2AP message and sends back response  
2573  *
2574  * @details
2575  *
2576  *    Function : E2APMsgHdlr
2577  *
2578  *    Functionality:
2579  *         - Decodes received E2AP control message
2580  *         - Prepares response message, encodes and sends to SCTP
2581  *
2582  * @params[in] 
2583  * @return ROK     - success
2584  *         RFAILED - failure
2585  *
2586  * ****************************************************************/
2587 void E2APMsgHdlr(Buffer *mBuf)
2588 {
2589    int i =0;
2590    char *recvBuf = NULLP;
2591    MsgLen copyCnt =0;
2592    MsgLen recvBufLen =0;
2593    E2AP_PDU_t *e2apMsg = NULLP;
2594    asn_dec_rval_t rval ={0}; /* Decoder return value */
2595    E2AP_PDU_t e2apasnmsg={0} ;
2596
2597    DU_LOG("\nDEBUG   -->  E2AP : Received E2AP message buffer");
2598    ODU_PRINT_MSG(mBuf, 0,0);
2599
2600    /* Copy mBuf into char array to decode it */
2601    ODU_GET_MSG_LEN(mBuf, &recvBufLen);
2602    DU_ALLOC(recvBuf, (Size)recvBufLen);
2603
2604    if(recvBuf == NULLP)
2605    {
2606       DU_LOG("\nERROR  -->  E2AP : Memory allocation failed");
2607       return;
2608    }
2609    if(ODU_COPY_MSG_TO_FIX_BUF(mBuf, 0, recvBufLen, (Data *)recvBuf, &copyCnt) != ROK)
2610    {
2611       DU_LOG("\nERROR  -->  E2AP : Failed while copying %d", copyCnt);
2612       return;
2613    }
2614
2615 #ifdef DEBUG_ASN_PRINT
2616    printf("\nDEBUG   -->  E2AP : Received flat buffer to be decoded : ");
2617    for(i=0; i< recvBufLen; i++)
2618    {
2619       printf("%x",recvBuf[i]);
2620    }
2621 #endif
2622
2623    /* Decoding flat buffer into E2AP messsage */
2624    e2apMsg = &e2apasnmsg;
2625    memset(e2apMsg, 0, sizeof(E2AP_PDU_t));
2626
2627    rval = aper_decode(0, &asn_DEF_E2AP_PDU, (void **)&e2apMsg, recvBuf, recvBufLen, 0, 0);
2628    DU_FREE(recvBuf, (Size)recvBufLen);
2629
2630    if(rval.code == RC_FAIL || rval.code == RC_WMORE)
2631    {
2632       DU_LOG("\nERROR  -->  E2AP : ASN decode failed");
2633       return;
2634    }
2635    printf("\n");
2636    xer_fprint(stdout, &asn_DEF_E2AP_PDU, e2apMsg);
2637
2638    switch(e2apMsg->present)
2639    {
2640       case E2AP_PDU_PR_unsuccessfulOutcome:
2641          {
2642             switch(e2apMsg->choice.unsuccessfulOutcome->value.present)
2643             {
2644                case UnsuccessfulOutcomeE2__value_PR_E2setupFailure:
2645                   {
2646                      procE2SetupFailure(e2apMsg);
2647                      break;
2648                   }
2649                default:
2650                   {
2651                      DU_LOG("\nERROR  -->  E2AP : Invalid type of E2AP_PDU_PR_unsuccessfulOutcome  [%d]",\
2652                            e2apMsg->choice.unsuccessfulOutcome->value.present);
2653                      return;
2654                   }
2655             }
2656             break;
2657          }
2658       case E2AP_PDU_PR_successfulOutcome:
2659          {
2660             switch(e2apMsg->choice.successfulOutcome->value.present)
2661             {
2662                case SuccessfulOutcomeE2__value_PR_E2setupResponse:
2663                   {
2664                      if(!duCb.e2Status)
2665                      {
2666                         procE2SetupRsp(e2apMsg);
2667                      }
2668                      break;
2669                   }
2670                case SuccessfulOutcomeE2__value_PR_E2nodeConfigurationUpdateAcknowledge:
2671                   {
2672                      DU_LOG("\nDEBUG   -->  E2AP : E2 node Config update ack message recevied");
2673                      break;
2674                   }
2675                case SuccessfulOutcomeE2__value_PR_ResetResponseE2:
2676                   {
2677                      procResetResponse(e2apMsg);
2678                      break;
2679                   }
2680                default:
2681                   {
2682                      DU_LOG("\nERROR  -->  E2AP : Invalid type of E2AP_PDU_PR_successfulOutcome  [%d]",\
2683                            e2apMsg->choice.successfulOutcome->value.present);
2684                      return;
2685                   }
2686             }/* End of switch(successfulOutcome) */
2687             free(e2apMsg->choice.successfulOutcome);
2688             break;
2689          }
2690
2691       case E2AP_PDU_PR_initiatingMessage:
2692          {
2693             switch(e2apMsg->choice.initiatingMessage->value.present)
2694             {
2695                case InitiatingMessageE2__value_PR_RICsubscriptionRequest: 
2696                   {
2697                      procRicSubsReq(e2apMsg);
2698                      break;
2699                   }
2700                default:
2701                   {
2702                      DU_LOG("\nERROR  -->  E2AP : Invalid type of E2AP_PDU_PR_initiatingMessage [%d]",\
2703                            e2apMsg->choice.initiatingMessage->value.present);
2704                      return;
2705                   }
2706             }/* End of switch(initiatingMessage) */
2707             free(e2apMsg->choice.initiatingMessage);
2708             break;
2709          }
2710       default:
2711          {
2712             DU_LOG("\nERROR  -->  E2AP : Invalid type of e2apMsg->present [%d]",e2apMsg->present);
2713             return;
2714          }
2715          free(e2apMsg);
2716
2717    }/* End of switch(e2apMsg->present) */
2718
2719 } /* End of E2APMsgHdlr */
2720
2721 /**********************************************************************
2722   End of file
2723  **********************************************************************/