E2AP code changes
[o-du/l2.git] / src / ric_stub / ric_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
19 /* This file contains E2AP message handler functions */
20
21 #include "ric_stub_sctp.h"
22 #include "ric_e2ap_msg_hdl.h"
23 #include "GlobalE2node-gNB-ID.h"
24
25 char encBuf[ENC_BUF_MAX_LEN];
26 Bool ricSubsStatus;
27 S16 SendE2APMsg(Region , Pool );
28
29 /*******************************************************************
30  *
31  * @brief Writes the encoded chunks into a buffer
32  *
33  * @details
34  *
35  *    Function : PrepFinalEncBuf
36  *
37  *    Functionality:Fills the encoded buffer
38  *
39  * @params[in] void *buffer,initial encoded data
40  * @params[in] size_t size,size of buffer
41  * @params[in] void *encodedBuf,final buffer
42  * @return ROK     - success
43  *         RFAILED - failure
44  *
45  * ****************************************************************/
46 static int PrepFinalEncBuf(const void *buffer, size_t size, void *encodedBuf)
47 {
48    memcpy(encodedBuf + encBufSize, buffer, size);
49    encBufSize += size;
50    return 0;
51 } /* PrepFinalEncBuf */
52
53 /*******************************************************************
54 *
55 * @brief Sends E2 msg over SCTP
56 *
57 * @details
58 *
59 *    Function : SendE2APMsg
60 *
61 *    Functionality: Sends E2 msg over SCTP
62 *
63 * @params[in] Region region
64 *             Pool pool
65 * @return ROK     - success
66 *         RFAILED - failure
67 *
68 * ****************************************************************/
69
70 S16 SendE2APMsg(Region region, Pool pool)
71 {
72    Buffer *mBuf;
73
74    if(SGetMsg(region, pool, &mBuf) == ROK)
75    {
76       if(SAddPstMsgMult((Data *)encBuf, encBufSize, mBuf) == ROK)
77       {
78          SPrntMsg(mBuf, 0,0);
79  
80          if(sctpSend(mBuf) != ROK)
81          {
82             DU_LOG("\nF1AP : SCTP Send for E2  failed");
83             SPutMsg(mBuf);
84             RETVALUE(RFAILED);
85          }
86       }
87       else
88       {
89          DU_LOG("\nF1AP : SAddPstMsgMult failed");
90          SPutMsg(mBuf);
91          RETVALUE(RFAILED);
92       }
93       SPutMsg(mBuf);
94    }
95    else
96    {
97       DU_LOG("\nF1AP : Failed to allocate memory");
98       RETVALUE(RFAILED);
99    }
100  
101    RETVALUE(ROK);
102 } /* SendE2APMsg */
103
104 /*******************************************************************
105  *
106  * @brief Builds PLMN ID 
107  *
108  * @details
109  *
110  *    Function : plmnBuildRic
111  *
112  *    Functionality: Building the PLMN ID
113  *
114  * @params[in] PLMNID plmn
115  *             OCTET_STRING_t *octe
116  * @return ROK     - success
117  *         RFAILED - failure
118  *
119  * ****************************************************************/
120
121 void plmnBuildRic(Plmn plmn, OCTET_STRING_t *octe)
122 {
123    U8 mncCnt;
124    octe->size = 3;
125    RIC_ALLOC(octe->buf,  octe->size * sizeof(U8));
126    if(octe->buf == NULLP)
127    {
128       RETVALUE(RFAILED);
129    }
130    mncCnt = 2;
131    octe->buf[0] = ((plmn.mcc[1] << 4) | (plmn.mcc[0]));
132    if(mncCnt == 2)
133    {
134       octe->buf[1]  = ((0xf0) | (plmn.mcc[2]));
135       octe->buf[2] = ((plmn.mnc[1] << 4) | (plmn.mnc[0]));
136    }
137    else
138    {
139       octe->buf[1] = ((plmn.mnc[0] << 4) | (plmn.mcc[2]));
140       octe->buf[2] = ((plmn.mnc[2] << 4) | (plmn.mnc[1]));
141    }
142 }
143
144 /*******************************************************************
145  *
146  * @brief Fills the RicId
147  *
148  * @details
149  *
150  *    Function : FillRicId
151  *
152  *    Functionality: Fills the RicId
153  *
154  * @params[in] BIT_STRING_t *nbid,
155  *             U8 unusedBits
156  *             U8 byteSize
157  *             U8 val
158  *
159  * @return ROK     - success
160  *         RFAILED - failure
161  *
162  * ****************************************************************/
163
164 S16 FillRicId(BIT_STRING_t *id, U8 unusedBits, U8 byteSize, U8 val)
165 {
166    U8 tmp;
167    id->size = byteSize;
168    RIC_ALLOC(id->buf, id->size * sizeof(U8));
169    if(id->buf == NULLP)
170    {
171       RETVALUE(RFAILED);
172    }
173
174    for (tmp = 0 ; tmp < (byteSize-1); tmp++)
175    {
176       id->buf[tmp] = tmp;
177    }
178    id->buf[byteSize-1]   = val;  //change this 
179    id->bits_unused = unusedBits;
180    RETVALUE(ROK);
181 }
182
183 /*******************************************************************
184  *
185  * @brief Builds Global RIC Id Params
186  *
187  * @details
188  *
189  *    Function : BuildGlobalRicId
190  *
191  *    Functionality: Building the Plmn and ric id
192  *
193  * @params[in] GlobalRIC_ID_t *ricId
194  * @return ROK     - success
195  *         RFAILED - failure
196  *
197  * ****************************************************************/
198
199 S16 BuildGlobalRicId(GlobalRIC_ID_t *ricId)
200 {
201    U8 unused = 4;
202    U8 byteSize = 3;
203    U8 val = 1;
204    if(ricId != NULLP)
205    {
206       plmnBuildRic(cuCfgParams.plmn , &ricId->pLMN_Identity);
207       /* fill ric Id */
208       FillRicId(&ricId->ric_ID, unused, byteSize, val);
209    }
210    RETVALUE(ROK);   
211 }
212 #if 0
213 RANfunctionID_ItemIEs_t* FillRanFuncItems(RANfunctionID_ItemIEs_t *items)
214 {
215   if(items != NULLP)
216   {
217      items->id = ProtocolIE_IDE2_id_RANfunction_Item;
218      items->criticality = CriticalityE2_reject;
219      items->value.present = RANfunctionID_ItemIEs__value_PR_RANfunctionID_Item; 
220      items->value.choice.RANfunctionID_Item.ranFunctionID = 1;
221      items->value.choice.RANfunctionID_Item.ranFunctionRevision = 4;
222   }
223   RETVALUE(items);
224 }
225
226 S16 BuildRANfuncIdList(RANfunctionsID_List_t *funcIdList)
227 {
228    U8 elementCnt;
229    RANfunctionID_ItemIEs_t *funcIdItems;
230
231    elementCnt = 1; 
232    funcIdList->list.count = elementCnt;
233    funcIdList->list.size  = elementCnt * sizeof(RANfunctionID_ItemIEs_t);
234    RIC_ALLOC(funcIdList->list.array, funcIdList->list.size);
235    if(funcIdList->list.array == NULLP)
236    {
237       DU_LOG("\nE2AP : Memory allocation for RAN Function List failed");
238       RETVALUE(RFAILED);
239    }
240    RIC_ALLOC(funcIdList->list.array[0], sizeof(RANfunctionID_ItemIEs_t));
241    FillRanFuncItems(funcIdList->list.array[0]);
242    RETVALUE(ROK);
243 }
244 #endif
245
246 /*******************************************************************
247  *
248  * @brief Builds and sends the E2SetupResponse
249  *
250  * @details
251  *
252  *    Function : BuildAndSendE2SetupRsp
253  *
254  *    Functionality: Constructs the F1SetupResponse message and sends
255  *                   it back to the DU through SCTP.
256  *
257  * @params[in] void **buf,Buffer to which encoded pattern is written into
258  * @params[in] int *size,size of buffer
259  *
260  * @return ROK     - success
261  *         RFAILED - failure
262  *
263  * ****************************************************************/
264 S16 BuildAndSendE2SetupRsp()
265 {
266    E2AP_PDU_t         *e2apMsg = NULL;
267    E2setupResponse_t  *e2SetupRsp;
268    asn_enc_rval_t     encRetVal; 
269    U8 idx;
270    U8 elementCnt;
271
272  
273    DU_LOG("\nE2AP : Building E2 Setup Response\n");
274
275    RIC_ALLOC(e2apMsg, sizeof(E2AP_PDU_t)); 
276    if(e2apMsg == NULLP)
277    {
278       DU_LOG("\nE2AP : Memory allocation for E2AP-PDU failed");
279       RETVALUE(RFAILED);
280    }
281    e2apMsg->present =  E2AP_PDU_PR_successfulOutcome;
282    RIC_ALLOC(e2apMsg->choice.successfulOutcome, sizeof(SuccessfulOutcomeE2_t));
283    if(e2apMsg->choice.successfulOutcome == NULLP)
284    {
285       DU_LOG("\nE2AP : Memory allocation for E2AP-PDU failed");
286       RIC_FREE(e2apMsg, sizeof(E2AP_PDU_t));
287       RETVALUE(RFAILED);  
288    }
289
290    e2apMsg->choice.successfulOutcome->procedureCode = ProcedureCodeE2_id_E2setup;
291    e2apMsg->choice.successfulOutcome->criticality = CriticalityE2_reject;
292    e2apMsg->choice.successfulOutcome->value.present = \
293          SuccessfulOutcomeE2__value_PR_E2setupResponse;
294    e2SetupRsp = &e2apMsg->choice.successfulOutcome->value.choice.E2setupResponse;
295
296    elementCnt = 1;
297    e2SetupRsp->protocolIEs.list.count = elementCnt;
298    e2SetupRsp->protocolIEs.list.size  = elementCnt * sizeof(E2setupResponseIEs_t);
299
300    RIC_ALLOC(e2SetupRsp->protocolIEs.list.array, \
301               e2SetupRsp->protocolIEs.list.size);
302    if(e2SetupRsp->protocolIEs.list.array == NULLP)
303    {
304       DU_LOG("\nE2AP : Memory allocation for E2ResponseIEs failed");
305       RIC_FREE(e2apMsg->choice.successfulOutcome, sizeof(SuccessfulOutcomeE2_t));
306       RIC_FREE(e2apMsg, sizeof(E2AP_PDU_t));
307       RETVALUE(RFAILED);
308    }
309
310    for(idx=0; idx<elementCnt; idx++)
311    {
312       RIC_ALLOC(e2SetupRsp->protocolIEs.list.array[idx], \
313             sizeof(E2setupResponseIEs_t)); 
314       if(e2SetupRsp->protocolIEs.list.array[idx] == NULLP)
315       {  
316          RIC_FREE(e2SetupRsp->protocolIEs.list.array,\
317                    e2SetupRsp->protocolIEs.list.size);
318          RIC_FREE(e2apMsg->choice.successfulOutcome, \
319                sizeof(SuccessfulOutcomeE2_t));
320          RIC_FREE(e2apMsg, sizeof(E2AP_PDU_t));
321          RETVALUE(RFAILED);
322       }    
323    }
324    /* Global RIC ID */
325    idx = 0;
326    e2SetupRsp->protocolIEs.list.array[idx]->id = ProtocolIE_IDE2_id_GlobalRIC_ID;
327    e2SetupRsp->protocolIEs.list.array[idx]->criticality = CriticalityE2_reject;
328    e2SetupRsp->protocolIEs.list.array[idx]->value.present = \
329                                      E2setupResponseIEs__value_PR_GlobalRIC_ID;
330
331    BuildGlobalRicId(&(e2SetupRsp->protocolIEs.list.array[idx]->value.choice.GlobalRIC_ID));
332
333    xer_fprint(stdout, &asn_DEF_E2AP_PDU, e2apMsg);
334    cmMemset((U8 *)encBuf, 0, ENC_BUF_MAX_LEN);
335    encBufSize = 0;
336    encRetVal = aper_encode(&asn_DEF_E2AP_PDU, 0, e2apMsg, PrepFinalEncBuf, encBuf);
337
338    /* Check encode results */
339    if(encRetVal.encoded == ENCODE_FAIL)
340    {
341            DU_LOG("\nE2AP : Could not encode E2SetupResponse structure (at %s)\n",\
342                            encRetVal.failed_type ? encRetVal.failed_type->name : "unknown");
343            RETVALUE(RFAILED);   
344    } 
345    else 
346    {
347            DU_LOG("\nE2AP : Created APER encoded buffer for E2SetupResponse\n");
348            for(int i=0; i< encBufSize; i++)
349            {
350                    printf("%x",encBuf[i]);
351            } 
352    }
353
354
355    if(SendE2APMsg(RIC_APP_MEM_REG, RIC_POOL) != ROK)
356    {
357       DU_LOG("\nF1AP : Sending E2 Setup Response failed");      
358       RETVALUE(RFAILED);
359    }
360
361    RETVALUE(ROK);
362 }
363
364 /*******************************************************************
365  *
366  * @brief Builds Ric Request Id
367  *
368  * @details
369  *
370  *    Function : BuildRicRequestId
371  *
372  *    Functionality: Building the Ric Request Id
373  *
374  * @params[in] RICrequestID_t *ricReqId
375  * @return ROK     - success
376  *         RFAILED - failure
377  *
378  * ****************************************************************/
379
380 S16 BuildRicRequestId(RICrequestID_t *ricReqId)
381 {
382
383    if(ricReqId != NULLP)
384    {
385       ricReqId->ricRequestorID = 1;
386       ricReqId->ricInstanceID  = 1;
387    }
388    RETVALUE(ROK);
389 }
390
391 /*******************************************************************
392  *
393  * @brief Fills Ric Action To be Setup Item
394  *
395  * @details
396  *
397  *    Function : fillSetupItems
398  *
399  *    Functionality: Filling ricAction Id, RicActionType
400  *
401  * @params[in] RICaction_ToBeSetup_Item_t *setupItems
402  * @return pointer of type RICaction_ToBeSetup_Item_t
403  *
404  * ****************************************************************/
405
406 RICaction_ToBeSetup_Item_t* fillSetupItems(RICaction_ToBeSetup_Item_t *setupItems)
407 {
408    if(setupItems != NULLP)
409    {
410       setupItems->ricActionID = 0;
411       setupItems->ricActionType = RICactionType_report;
412    }
413
414    RETVALUE(setupItems);
415 }
416
417 /*******************************************************************
418  *
419  * @brief Fills RIC Subscription Details Item List
420  *
421  * @details
422  *
423  *    Function : fillSubsDetails
424  *
425  *    Functionality: Fill the RIC Subscription Details Items List
426  *
427  * @params[in] RICaction_ToBeSetup_ItemIEs_t *items
428  * @return ROK     - success
429  *         RFAILED - failure
430  *
431  * ****************************************************************/
432
433 S16 fillSubsDetails(RICaction_ToBeSetup_ItemIEs_t *items)
434 {
435    if(items != NULLP)
436    {
437       items->id = ProtocolIE_IDE2_id_RICaction_ToBeSetup_Item;
438       items->criticality   =  CriticalityE2_ignore;
439       items->value.present =  RICaction_ToBeSetup_ItemIEs__value_PR_RICaction_ToBeSetup_Item;
440       fillSetupItems(&(items->value.choice.RICaction_ToBeSetup_Item));
441    }
442    RETVALUE(ROK);
443 }
444
445 /*******************************************************************
446  *
447  * @brief builds RIC Subscription Details
448  *
449  * @details
450  *
451  *    Function : BuildsRicSubsDetails
452  *
453  *    Functionality: Builds the RIC Subscription Details
454  *
455  * @params[in] RICsubscriptionDetails_t *subsDetails
456  * @return ROK     - success
457  *         RFAILED - failure
458  *
459  * ****************************************************************/
460
461 S16 BuildRicSubsDetails(RICsubscriptionDetails_t *subsDetails)
462 {
463
464    U8 elementCnt;
465
466    if(subsDetails != NULLP)
467    {
468       /* Plmn is not called */
469       plmnBuildRic(cuCfgParams.plmn, &subsDetails->ricEventTriggerDefinition);
470       elementCnt = 1;
471       subsDetails->ricAction_ToBeSetup_List.list.count = elementCnt;
472       subsDetails->ricAction_ToBeSetup_List.list.size = \
473                       elementCnt * sizeof(RICaction_ToBeSetup_ItemIEs_t);
474       RIC_ALLOC(subsDetails->ricAction_ToBeSetup_List.list.array, \
475                 subsDetails->ricAction_ToBeSetup_List.list.size);
476       if(subsDetails->ricAction_ToBeSetup_List.list.array  == NULLP)
477       {
478          DU_LOG("\nE2AP : Memory allocation for RICactionToBeSetup Items failed");
479          RETVALUE(RFAILED);
480       } 
481       RIC_ALLOC(subsDetails->ricAction_ToBeSetup_List.list.array[0],\
482                    sizeof(RICaction_ToBeSetup_ItemIEs_t));
483       fillSubsDetails(subsDetails->ricAction_ToBeSetup_List.list.array[0]);
484    }
485    RETVALUE(ROK);
486 }
487
488 /*******************************************************************
489  *
490  * @brief Builds and Send the RicSubscriptionReq
491  *
492  * @details
493  *
494  *    Function : BuildAndSendRicSubscriptionReq
495  *
496  * Functionality:Fills the RicSubscriptionReq
497  *
498  * @return ROK     - success
499  *         RFAILED - failure
500  *
501  ******************************************************************/
502
503 S16 BuildAndSendRicSubscriptionReq()
504 {
505
506    E2AP_PDU_t   *e2apRicMsg = NULL;
507    RICsubscriptionRequest_t   *ricSubscriptionReq;
508    U8   elementCnt;
509    U8   idx;
510    U8   ieId;
511    S16  ret; 
512    asn_enc_rval_t             encRetVal;        /* Encoder return value */
513    ricSubsStatus = TRUE;
514
515    DU_LOG("\nE2AP : Building RIC Subscription Request\n");
516
517    RIC_ALLOC(e2apRicMsg, sizeof(E2AP_PDU_t));
518    if(e2apRicMsg == NULLP)
519    {
520       DU_LOG("\nE2AP : Memory allocation for E2AP-PDU failed");
521       RETVALUE(RFAILED);
522    }
523
524    e2apRicMsg->present = E2AP_PDU_PR_initiatingMessage;
525    RIC_ALLOC(e2apRicMsg->choice.initiatingMessage, sizeof(InitiatingMessageE2_t));
526    if(e2apRicMsg->choice.initiatingMessage == NULLP)
527    {
528       DU_LOG("\nE2AP : Memory allocation for E2AP-PDU failed");
529       RIC_FREE(e2apRicMsg, sizeof(E2AP_PDU_t));
530       RETVALUE(RFAILED);
531    }
532    e2apRicMsg->choice.initiatingMessage->procedureCode = ProcedureCodeE2_id_RICsubscription;
533    e2apRicMsg->choice.initiatingMessage->criticality = CriticalityE2_reject;
534    e2apRicMsg->choice.initiatingMessage->value.present = InitiatingMessageE2__value_PR_RICsubscriptionRequest;
535    
536    RIC_ALLOC(ricSubscriptionReq, sizeof(RICsubscriptionRequest_t));
537    ricSubscriptionReq = &e2apRicMsg->choice.initiatingMessage->value.choice.RICsubscriptionRequest;
538    
539    elementCnt = 3;
540    ricSubscriptionReq->protocolIEs.list.count = elementCnt;
541    ricSubscriptionReq->protocolIEs.list.size  = elementCnt * sizeof(RICsubscriptionRequest_IEs_t);
542
543    /* Initialize the subscription members */
544    RIC_ALLOC(ricSubscriptionReq->protocolIEs.list.array, \
545               ricSubscriptionReq->protocolIEs.list.size);
546    if(ricSubscriptionReq->protocolIEs.list.array == NULLP)
547    {
548       DU_LOG("\nE2AP : Memory allocation for RICSubscriptionRequestIEs failed");
549       RIC_FREE(e2apRicMsg->choice.initiatingMessage, sizeof(InitiatingMessageE2_t));
550       RIC_FREE(e2apRicMsg, (Size)sizeof(E2AP_PDU_t));
551       RETVALUE(RFAILED);
552    }
553    
554    for(idx=0; idx<elementCnt; idx++)
555    {
556       RIC_ALLOC(ricSubscriptionReq->protocolIEs.list.array[idx],\
557             sizeof(RICsubscriptionRequest_IEs_t));
558       if(ricSubscriptionReq->protocolIEs.list.array[idx] == NULLP)
559       {
560          for(ieId=0; ieId<idx; ieId++)
561          {
562             RIC_FREE(ricSubscriptionReq->protocolIEs.list.array[ieId],\
563                   sizeof(RICsubscriptionRequest_IEs_t));
564          }
565          RIC_FREE(ricSubscriptionReq->protocolIEs.list.array,\
566                   ricSubscriptionReq->protocolIEs.list.size);
567          RIC_FREE(e2apRicMsg->choice.initiatingMessage, \
568                sizeof(InitiatingMessageE2_t));
569          RIC_FREE(e2apRicMsg, sizeof(E2AP_PDU_t));
570          RETVALUE(RFAILED);
571       }
572    }
573
574    /* Filling RIC Request Id */
575    idx = 0;
576    ricSubscriptionReq->protocolIEs.list.array[idx]->id = ProtocolIE_IDE2_id_RICrequestID;
577    ricSubscriptionReq->protocolIEs.list.array[idx]->criticality = CriticalityE2_reject;
578    ricSubscriptionReq->protocolIEs.list.array[idx]->value.present =\
579                                     RICsubscriptionRequest_IEs__value_PR_RICrequestID;
580  
581    BuildRicRequestId(&ricSubscriptionReq->protocolIEs.list.array[idx]->value.choice.RICrequestID);
582
583
584    /* Filling RAN Function Id */
585    idx++;
586    ricSubscriptionReq->protocolIEs.list.array[idx]->id = ProtocolIE_IDE2_id_RANfunctionID;
587    ricSubscriptionReq->protocolIEs.list.array[idx]->criticality = CriticalityE2_reject;
588    ricSubscriptionReq->protocolIEs.list.array[idx]->value.present =\
589                                     RICsubscriptionRequest_IEs__value_PR_RANfunctionID;
590    ricSubscriptionReq->protocolIEs.list.array[idx]->value.choice.RANfunctionID = 1;
591
592
593    /* Filling RIC Subscription Details */
594    idx++;
595    ricSubscriptionReq->protocolIEs.list.array[idx]->id = ProtocolIE_IDE2_id_RICsubscriptionDetails;
596    ricSubscriptionReq->protocolIEs.list.array[idx]->criticality = CriticalityE2_reject;
597    ricSubscriptionReq->protocolIEs.list.array[idx]->value.present =\
598                                     RICsubscriptionRequest_IEs__value_PR_RICsubscriptionDetails;
599
600    BuildRicSubsDetails(&(ricSubscriptionReq->protocolIEs.list.array[idx]->value.choice.RICsubscriptionDetails));
601
602
603    /* Prints the Msg formed */
604    xer_fprint(stdout, &asn_DEF_E2AP_PDU, e2apRicMsg);
605
606    cmMemset((U8 *)encBuf, 0, ENC_BUF_MAX_LEN);
607    encBufSize = 0;
608    encRetVal = aper_encode(&asn_DEF_E2AP_PDU, 0, e2apRicMsg, PrepFinalEncBuf,\
609                encBuf);
610    if(encRetVal.encoded == ENCODE_FAIL)
611    {
612       DU_LOG("\nE2AP : Could not encode RicSubscriptionRequest structure (at %s)\n",\
613       encRetVal.failed_type ? encRetVal.failed_type->name : "unknown");
614       RETVALUE(RFAILED);
615    }
616    else
617    {
618       DU_LOG("\nE2AP : Created APER encoded buffer for RicSubscriptionRequest\n");
619       for(int i=0; i< encBufSize; i++)
620       {
621           printf("%x",encBuf[i]);
622       } 
623    }
624
625
626    /* Sending msg */
627    if(SendE2APMsg(RIC_APP_MEM_REG, RIC_POOL) != ROK)
628    {
629       DU_LOG("\nE2AP : Sending RIC subscription Request failed");
630       RETVALUE(RFAILED);
631    }
632
633    RETVALUE(ROK);
634 }
635
636  
637 /*******************************************************************
638 *
639 * @brief Handles received E2AP message and sends back response  
640 *
641 * @details
642 *
643 *    Function : E2APMsgHdlr
644 *
645 *    Functionality:
646 *         - Decodes received E2AP control message
647 *         - Prepares response message, encodes and sends to SCTP
648 *
649 * @params[in] 
650 * @return ROK     - success
651 *         RFAILED - failure
652 *
653 * ****************************************************************/
654 void E2APMsgHdlr(Buffer *mBuf)
655 {
656    int i;
657    char *recvBuf;
658    MsgLen copyCnt;
659    MsgLen recvBufLen;
660    E2AP_PDU_t *e2apMsg;
661    asn_dec_rval_t rval; /* Decoder return value */
662    E2AP_PDU_t e2apasnmsg ;
663  
664    DU_LOG("\nE2AP : Received E2AP message buffer");
665    SPrntMsg(mBuf, 0,0);
666  
667    /* Copy mBuf into char array to decode it */
668    SFndLenMsg(mBuf, &recvBufLen);
669    if(SGetSBuf(DFLT_REGION, DFLT_POOL, (Data **)&recvBuf, (Size)recvBufLen) != ROK)
670    {
671       DU_LOG("\nE2AP : Memory allocation failed");
672       return;
673    }
674    if(SCpyMsgFix(mBuf, 0, recvBufLen, (Data *)recvBuf, &copyCnt) != ROK)
675    {
676       DU_LOG("\nE2AP : Failed while copying %d", copyCnt);
677       return;
678    }
679
680    printf("\nE2AP : Received flat buffer to be decoded : ");
681    for(i=0; i< recvBufLen; i++)
682    {
683         printf("%x",recvBuf[i]);
684    }
685
686    /* Decoding flat buffer into F1AP messsage */
687    e2apMsg = &e2apasnmsg;
688    memset(e2apMsg, 0, sizeof(E2AP_PDU_t));
689
690    rval = aper_decode(0, &asn_DEF_E2AP_PDU, (void **)&e2apMsg, recvBuf, recvBufLen, 0, 0);
691    SPutSBuf(DFLT_REGION, DFLT_POOL, (Data *)recvBuf, (Size)recvBufLen);
692    if(rval.code == RC_FAIL || rval.code == RC_WMORE)
693    {
694       DU_LOG("\nE2AP : ASN decode failed");
695       return;
696    }
697    printf("\n");
698    xer_fprint(stdout, &asn_DEF_E2AP_PDU, e2apMsg);
699
700    switch(e2apMsg->present)
701    {
702       case E2AP_PDU_PR_initiatingMessage:
703       {
704          switch(e2apMsg->choice.initiatingMessage->value.present)
705          {
706             case InitiatingMessageE2__value_PR_E2setupRequest:
707             {
708                DU_LOG("\nE2AP : E2 setup request received");
709                BuildAndSendE2SetupRsp();
710                break;
711             }
712             case InitiatingMessageE2__value_PR_RICindication:
713             {
714                DU_LOG("\nE2AP : RIC Indication Acknowledged");
715                break;
716             }
717             default:
718             {
719                DU_LOG("\nE2AP : Invalid type of intiating message [%d]",e2apMsg->choice.initiatingMessage->value.present);
720                return;
721             }
722          }/* End of switch(initiatingMessage) */
723          break;
724       }
725       case E2AP_PDU_PR_successfulOutcome: 
726       {
727          switch(e2apMsg->choice.successfulOutcome->value.present)
728          {
729             case SuccessfulOutcomeE2__value_PR_RICsubscriptionResponse:  
730             {
731                DU_LOG("\nE2AP : RICsubscriptionResponse Msg Acknowledged");
732                break;
733             }
734             default:
735             {
736                DU_LOG("\nE2AP : Invalid type of successfulOutcome message [%d]",e2apMsg->choice.successfulOutcome->value.present);
737                return;
738             }
739             break;
740          }
741          break; 
742       }
743       default:
744       {
745          DU_LOG("\nE2AP : Invalid type message type ");
746          return;
747       }
748  
749     }/* End of switch(e2apMsg->present) */
750
751     if(!ricSubsStatus)
752       BuildAndSendRicSubscriptionReq(); 
753        
754 } /* End of E2APMsgHdlr */
755
756
757 /**********************************************************************
758   End of file
759  **********************************************************************/