X-Git-Url: https://gerrit.o-ran-sc.org/r/gitweb?a=blobdiff_plain;f=src%2Fric_stub%2Fric_e2ap_msg_hdl.c;h=5eebc63ac412a558177e0817d29fb14f9ce0a74d;hb=47dcc6df526aaec243361a0296966cde738129cb;hp=7db9c3546e5d78c17e1470ae920aade26fa8807c;hpb=a50cee433ee06d6a8a4215c274432ab4ad8fdb26;p=o-du%2Fl2.git diff --git a/src/ric_stub/ric_e2ap_msg_hdl.c b/src/ric_stub/ric_e2ap_msg_hdl.c index 7db9c3546..5eebc63ac 100644 --- a/src/ric_stub/ric_e2ap_msg_hdl.c +++ b/src/ric_stub/ric_e2ap_msg_hdl.c @@ -28,10 +28,45 @@ #include "ProtocolIE-FieldE2.h" #include "InitiatingMessageE2.h" #include "SuccessfulOutcomeE2.h" +#include "UnsuccessfulOutcomeE2.h" #include "E2AP-PDU.h" #include "du_log.h" #include "E2nodeComponentInterfaceF1.h" +#include "E2SM-KPM-RANfunction-Description.h" +#include "RANfunction-Name.h" +#include "RIC-EventTriggerStyle-Item.h" +#include "RIC-ReportStyle-Item.h" +#include "MeasurementInfo-Action-Item.h" +/******************************************************************* + * + * @brief Assigns new transaction id to RIC initiated procedure + * + * @details + * + * Function : assignTransactionId + * + * Functionality: Assigns new transaction id to a RIC initiated + * procedure + * + * @params[in] Region region + * Pool pool + * @return ROK - success + * RFAILED - failure + * + * ****************************************************************/ + +uint8_t assignTransactionId(DuDb *duDb) +{ + uint8_t currTransId = duDb->ricTransIdCounter; + + /* Update to next valid value */ + duDb->ricTransIdCounter++; + if(duDb->ricTransIdCounter == MAX_NUM_TRANSACTION) + duDb->ricTransIdCounter = 0; + + return currTransId; +} /******************************************************************* * @@ -134,9 +169,13 @@ uint8_t BuildGlobalRicId(GlobalRIC_ID_t *ricId) * ****************************************************************/ void FreeE2SetupRsp(E2AP_PDU_t *e2apMsg) { - uint8_t arrIdx = 0; + uint8_t arrIdx = 0, e2NodeConfigIdx=0, ranFuncIdx=0; + RANfunctionsID_List_t *ranFuncAddedList; E2setupResponse_t *e2SetupRsp; - + E2nodeComponentConfigAdditionAck_ItemIEs_t *e2NodeAddAckItemIe; + E2nodeComponentConfigAdditionAck_List_t *e2NodeConfigAdditionAckList; + E2nodeComponentInterfaceF1_t *f1InterfaceInfo; + if(e2apMsg) { if(e2apMsg->choice.successfulOutcome) @@ -146,6 +185,48 @@ void FreeE2SetupRsp(E2AP_PDU_t *e2apMsg) { for(arrIdx=0; arrIdxprotocolIEs.list.count; arrIdx++) { + switch(e2SetupRsp->protocolIEs.list.array[arrIdx]->id) + { + case ProtocolIE_IDE2_id_RANfunctionsAccepted: + { + ranFuncAddedList= &e2SetupRsp->protocolIEs.list.array[arrIdx]->value.choice.RANfunctionsID_List; + if(ranFuncAddedList->list.array) + { + for(ranFuncIdx=0;ranFuncIdxlist.count; ranFuncIdx++) + { + if(ranFuncAddedList->list.array[ranFuncIdx]) + { + RIC_FREE(ranFuncAddedList->list.array[ranFuncIdx], sizeof(RANfunction_ItemIEs_t)); + } + } + RIC_FREE(ranFuncAddedList->list.array, ranFuncAddedList->list.size); + } + break; + } + case ProtocolIE_IDE2_id_E2nodeComponentConfigAdditionAck: + { + e2NodeConfigAdditionAckList =&e2SetupRsp->protocolIEs.list.array[arrIdx]->value.choice.E2nodeComponentConfigAdditionAck_List; + if(e2NodeConfigAdditionAckList->list.count) + { + for(e2NodeConfigIdx=0; e2NodeConfigIdxlist.count; e2NodeConfigIdx++) + { + e2NodeAddAckItemIe = (E2nodeComponentConfigAdditionAck_ItemIEs_t*) e2NodeConfigAdditionAckList->list.array[e2NodeConfigIdx]; + if(e2NodeAddAckItemIe) + { + f1InterfaceInfo = e2NodeAddAckItemIe->value.choice.E2nodeComponentConfigAdditionAck_Item.e2nodeComponentID.choice.e2nodeComponentInterfaceTypeF1; + if(f1InterfaceInfo) + { + RIC_FREE(f1InterfaceInfo->gNB_DU_ID.buf, f1InterfaceInfo->gNB_DU_ID.size); + RIC_FREE(f1InterfaceInfo, sizeof(E2nodeComponentInterfaceF1_t)); + } + RIC_FREE(e2NodeAddAckItemIe, sizeof(E2nodeComponentConfigAdditionAck_ItemIEs_t)); + } + } + RIC_FREE(e2NodeConfigAdditionAckList->list.array, e2NodeConfigAdditionAckList->list.size); + } + break; + } + } RIC_FREE(e2SetupRsp->protocolIEs.list.array[arrIdx], sizeof(E2setupResponseIEs_t)); } RIC_FREE(e2SetupRsp->protocolIEs.list.array, e2SetupRsp->protocolIEs.list.size); @@ -172,7 +253,8 @@ void FreeE2SetupRsp(E2AP_PDU_t *e2apMsg) * @return ROK - success * RFAILED - failure * ****************************************************************/ -uint8_t BuildE2nodeComponentConfigAdditionAck(E2nodeComponentConfigAdditionAck_List_t *e2NodeConfigAdditionAckList, uint8_t duId) + +uint8_t BuildE2nodeComponentConfigAdditionAck(E2nodeComponentConfigAdditionAck_List_t *e2NodeConfigAdditionAckList, DuDb *duDb) { uint8_t arrIdx = 0; E2nodeComponentConfigAdditionAck_ItemIEs_t *e2NodeAddAckItem; @@ -199,7 +281,7 @@ uint8_t BuildE2nodeComponentConfigAdditionAck(E2nodeComponentConfigAdditionAck_L e2NodeAddAckItem->id = ProtocolIE_IDE2_id_E2nodeComponentConfigAdditionAck_Item; e2NodeAddAckItem->criticality = CriticalityE2_reject; e2NodeAddAckItem->value.present = E2nodeComponentConfigAdditionAck_ItemIEs__value_PR_E2nodeComponentConfigAdditionAck_Item; - e2NodeAddAckItem->value.choice.E2nodeComponentConfigAdditionAck_Item.e2nodeComponentInterfaceType = E2nodeComponentInterfaceType_f1; + e2NodeAddAckItem->value.choice.E2nodeComponentConfigAdditionAck_Item.e2nodeComponentInterfaceType = duDb->e2NodeComponent.interfaceType; /* >E2 Node Component ID */ e2NodeAddAckItem->value.choice.E2nodeComponentConfigAdditionAck_Item.e2nodeComponentID.present = E2nodeComponentID_PR_e2nodeComponentInterfaceTypeF1; @@ -219,7 +301,7 @@ uint8_t BuildE2nodeComponentConfigAdditionAck(E2nodeComponentConfigAdditionAck_L DU_LOG("\nERROR -->list. E2AP: Memory allocation failed for BuildE2nodeComponentConfigAdditionAck %d",__LINE__); return RFAILED; } - e2NodeAddAckItem->value.choice.E2nodeComponentConfigAdditionAck_Item.e2nodeComponentID.choice.e2nodeComponentInterfaceTypeF1->gNB_DU_ID.buf[0] = duId; + e2NodeAddAckItem->value.choice.E2nodeComponentConfigAdditionAck_Item.e2nodeComponentID.choice.e2nodeComponentInterfaceTypeF1->gNB_DU_ID.buf[0] = duDb->e2NodeComponent.componentId; /* >E2 Node Component Configuration Acknowledge*/ e2NodeAddAckItem->value.choice.E2nodeComponentConfigAdditionAck_Item.e2nodeComponentConfigurationAck.updateOutcome = \ @@ -227,6 +309,86 @@ uint8_t BuildE2nodeComponentConfigAdditionAck(E2nodeComponentConfigAdditionAck_L return ROK; } + +/******************************************************************* + * + * @brief Build RAN function added list + * + * @details + * + * Function : BuildRanFunctionAddedList + * + * Functionality: Build RAN function added list + * ->For ProcedureCodeE2_id_E2setup or ProcedureCodeE2_id_RICserviceQuery + * we add all the RAN Function list which is present in RIC database. + * ->For any other procedures, we just fill the RAN functions whose ID + * is present in the recvList + * + * @params[in] + * Stored DU databse + * Count of ran functions to be added in the list + * Received list of RAN functions + * RAN Function list + * Procedure Code + * + * @return ROK - success + * RFAILED - failure + * ****************************************************************/ + +uint8_t BuildRanFunctionAddedList(DuDb *duDb, uint8_t count, RanFunction *ranFunToBeAdded, RANfunctionsID_List_t *ranFuncAddedList, uint8_t procedureCode) +{ + uint8_t ranFuncIdx = 0; + RANfunctionID_ItemIEs_t *ranFuncAddedItemIe; + + /* For ProcedureCodeE2_id_E2setup and ProcedureCodeE2_id_RICserviceQuery, + * the number of RAN function list items is equal to the number of + * ran function entries stored in the database. + * For any other procedure, the RAN function list count is equal + * to the count of ran functions obtained from the function's caller */ + + if((procedureCode == ProcedureCodeE2_id_RICserviceQuery)||(procedureCode == ProcedureCodeE2_id_E2setup)) + ranFuncAddedList->list.count = duDb->numOfRanFunction; + else + ranFuncAddedList->list.count = count; + + ranFuncAddedList->list.size = ranFuncAddedList->list.count*sizeof(RANfunctionID_ItemIEs_t*); + RIC_ALLOC(ranFuncAddedList->list.array, ranFuncAddedList->list.size); + if(ranFuncAddedList->list.array) + { + for(ranFuncIdx = 0; ranFuncIdx< ranFuncAddedList->list.count; ranFuncIdx++) + { + RIC_ALLOC(ranFuncAddedList->list.array[ranFuncIdx], sizeof(RANfunction_ItemIEs_t)); + if(ranFuncAddedList->list.array[ranFuncIdx] == NULLP) + { + DU_LOG("\nERROR --> E2AP : Memory allocation for RAN function added list array item"); + return RFAILED; + } + ranFuncAddedItemIe = (RANfunctionID_ItemIEs_t*)ranFuncAddedList->list.array[ranFuncIdx]; + ranFuncAddedItemIe->id = ProtocolIE_IDE2_id_RANfunctionID_Item; + ranFuncAddedItemIe->criticality= CriticalityE2_ignore; + ranFuncAddedItemIe->value.present = RANfunctionID_ItemIEs__value_PR_RANfunctionID_Item; + if((procedureCode == ProcedureCodeE2_id_RICserviceQuery)||(procedureCode == ProcedureCodeE2_id_E2setup)) + { + /* filling the RAN function information with the help of DuDb */ + ranFuncAddedItemIe->value.choice.RANfunctionID_Item.ranFunctionID = duDb->ranFunction[ranFuncIdx].id; + ranFuncAddedItemIe->value.choice.RANfunctionID_Item.ranFunctionRevision= duDb->ranFunction[ranFuncIdx].revisionCounter; + } + else + { + /* filling the the RAN function information with the help received list of RAN functions */ + ranFuncAddedItemIe->value.choice.RANfunctionID_Item.ranFunctionID = ranFunToBeAdded[ranFuncIdx].id; + ranFuncAddedItemIe->value.choice.RANfunctionID_Item.ranFunctionRevision= ranFunToBeAdded[ranFuncIdx].revisionCounter; + } + } + } + else + { + DU_LOG("\nERROR --> E2AP : Memory allocation for RAN function added list array"); + return RFAILED; + } + return ROK; +} + /******************************************************************* * * @brief Builds and sends the E2SetupResponse @@ -245,7 +407,8 @@ uint8_t BuildE2nodeComponentConfigAdditionAck(E2nodeComponentConfigAdditionAck_L * RFAILED - failure * * ****************************************************************/ -uint8_t BuildAndSendE2SetupRsp(uint32_t duId) + +uint8_t BuildAndSendE2SetupRsp(DuDb *duDb, uint8_t transId) { E2AP_PDU_t *e2apMsg = NULL; E2setupResponse_t *e2SetupRsp; @@ -278,8 +441,12 @@ uint8_t BuildAndSendE2SetupRsp(uint32_t duId) e2SetupRsp = &e2apMsg->choice.successfulOutcome->value.choice.E2setupResponse; elementCnt = 3; + /* Fill Accepted RAN function IE If Ran function information is stored in databse */ + if(duDb->numOfRanFunction) + elementCnt++; + e2SetupRsp->protocolIEs.list.count = elementCnt; - e2SetupRsp->protocolIEs.list.size = elementCnt * sizeof(E2setupResponseIEs_t); + e2SetupRsp->protocolIEs.list.size = elementCnt * sizeof(E2setupResponseIEs_t*); RIC_ALLOC(e2SetupRsp->protocolIEs.list.array, e2SetupRsp->protocolIEs.list.size); if(e2SetupRsp->protocolIEs.list.array == NULLP) @@ -309,7 +476,7 @@ uint8_t BuildAndSendE2SetupRsp(uint32_t duId) e2SetupRsp->protocolIEs.list.array[idx]->id = ProtocolIE_IDE2_id_TransactionID; e2SetupRsp->protocolIEs.list.array[idx]->criticality = CriticalityE2_reject; e2SetupRsp->protocolIEs.list.array[idx]->value.present = E2setupResponseIEs__value_PR_TransactionID; - e2SetupRsp->protocolIEs.list.array[idx]->value.choice.TransactionID = TRANS_ID; + e2SetupRsp->protocolIEs.list.array[idx]->value.choice.TransactionID = transId; /* Global RIC ID */ idx++; @@ -324,13 +491,27 @@ uint8_t BuildAndSendE2SetupRsp(uint32_t duId) break; } + if(duDb->numOfRanFunction) + { + /* Accepted RAN function Id */ + idx++; + e2SetupRsp->protocolIEs.list.array[idx]->id = ProtocolIE_IDE2_id_RANfunctionsAccepted; + e2SetupRsp->protocolIEs.list.array[idx]->criticality = CriticalityE2_reject; + e2SetupRsp->protocolIEs.list.array[idx]->value.present = E2setupResponseIEs__value_PR_RANfunctionsID_List; + if(BuildRanFunctionAddedList(duDb, 0, NULL, &e2SetupRsp->protocolIEs.list.array[idx]->value.choice.RANfunctionsID_List, ProcedureCodeE2_id_E2setup)!=ROK) + { + DU_LOG("\nERROR --> E2AP : Failed to build Ran function added list"); + break; + } + } + /* E2 Node Component Configuration Addition Acknowledge List*/ idx++; e2SetupRsp->protocolIEs.list.array[idx]->id = ProtocolIE_IDE2_id_E2nodeComponentConfigAdditionAck; e2SetupRsp->protocolIEs.list.array[idx]->criticality = CriticalityE2_reject; e2SetupRsp->protocolIEs.list.array[idx]->value.present = \ E2setupResponseIEs__value_PR_E2nodeComponentConfigAdditionAck_List; - if(BuildE2nodeComponentConfigAdditionAck(&e2SetupRsp->protocolIEs.list.array[idx]->value.choice.E2nodeComponentConfigAdditionAck_List, duId)!=ROK) + if(BuildE2nodeComponentConfigAdditionAck(&e2SetupRsp->protocolIEs.list.array[idx]->value.choice.E2nodeComponentConfigAdditionAck_List, duDb)!=ROK) { DU_LOG("\nERROR --> E2AP : Failed to build E2Node Component config addition ack list"); break; @@ -357,7 +538,7 @@ uint8_t BuildAndSendE2SetupRsp(uint32_t duId) } } - if(SendE2APMsg(RIC_APP_MEM_REG, RIC_POOL, duId) != ROK) + if(SendE2APMsg(RIC_APP_MEM_REG, RIC_POOL, duDb->duId) != ROK) { DU_LOG("\nERROR --> E2AP : Sending E2 Setup Response failed"); break; @@ -366,7 +547,7 @@ uint8_t BuildAndSendE2SetupRsp(uint32_t duId) } FreeE2SetupRsp(e2apMsg); - BuildAndSendRicSubscriptionReq(duId); + BuildAndSendRicSubscriptionReq(duDb->duId); return ROK; } @@ -671,6 +852,170 @@ void ProcRicSubscriptionResponse(uint32_t duId) duDb->ricSubscribedToDu = true; } +/******************************************************************* + * + * @brief deallocate the memory allocated in E2SetupFailure + * + * @details + * + * Function : FreeE2SetupFailure + * + * Functionality: deallocate the memory allocated in E2SetupFailure + * + * @params[in] E2AP_PDU_t *e2apMsg + * + * @return void + * ****************************************************************/ +void FreeE2SetupFailure(E2AP_PDU_t *e2apMsg) +{ + uint8_t arrIdx = 0; + E2setupFailure_t *e2SetupFail; + + if(e2apMsg) + { + if(e2apMsg->choice.unsuccessfulOutcome) + { + e2SetupFail = &e2apMsg->choice.unsuccessfulOutcome->value.choice.E2setupFailure; + if(e2SetupFail->protocolIEs.list.array) + { + for(arrIdx=0; arrIdxprotocolIEs.list.count; arrIdx++) + { + RIC_FREE(e2SetupFail->protocolIEs.list.array[arrIdx], sizeof(E2setupFailureIEs_t)); + } + RIC_FREE(e2SetupFail->protocolIEs.list.array, e2SetupFail->protocolIEs.list.size); + } + RIC_FREE(e2apMsg->choice.unsuccessfulOutcome, sizeof(UnsuccessfulOutcomeE2_t)); + } + RIC_FREE(e2apMsg, sizeof(E2AP_PDU_t)); + } +} + +/******************************************************************* + * + * @brief Buld and send the E2 Setup failure + * + * @details + * + * Function : BuildAndSendE2SetupFailure + * + * Functionality: + * - Buld and send the E2 Setup failure + * @return ROK - success + * RFAILED - failure + * + * ****************************************************************/ + +uint8_t BuildAndSendE2SetupFailure(uint32_t duId, uint8_t transId) +{ + E2AP_PDU_t *e2apMsg = NULL; + E2setupFailure_t *e2SetupFailure; + asn_enc_rval_t encRetVal; + uint8_t arrIdx; + uint8_t elementCnt; + bool memAllocFailed = false; + + DU_LOG("\nINFO --> E2AP : Building E2 Setup failure\n"); + while(true) + { + RIC_ALLOC(e2apMsg, sizeof(E2AP_PDU_t)); + if(e2apMsg == NULLP) + { + DU_LOG("\nERROR --> E2AP : Memory allocation for E2AP-PDU failed"); + break; + } + e2apMsg->present = E2AP_PDU_PR_unsuccessfulOutcome; + RIC_ALLOC(e2apMsg->choice.unsuccessfulOutcome , sizeof(struct UnsuccessfulOutcomeE2)); + if(e2apMsg->choice.unsuccessfulOutcome == NULLP) + { + DU_LOG("\nERROR --> E2AP : Memory allocation for E2AP-PDU failed"); + break; + } + + e2apMsg->choice.unsuccessfulOutcome->procedureCode = ProcedureCodeE2_id_E2setup; + e2apMsg->choice.unsuccessfulOutcome->criticality = CriticalityE2_reject; + e2apMsg->choice.unsuccessfulOutcome->value.present = UnsuccessfulOutcomeE2__value_PR_E2setupFailure; + e2SetupFailure = &e2apMsg->choice.unsuccessfulOutcome->value.choice.E2setupFailure; + + elementCnt = 3; + e2SetupFailure->protocolIEs.list.count = elementCnt; + e2SetupFailure->protocolIEs.list.size = elementCnt * sizeof(struct E2setupFailureIEs *); + + RIC_ALLOC(e2SetupFailure->protocolIEs.list.array, e2SetupFailure->protocolIEs.list.size); + if(e2SetupFailure->protocolIEs.list.array == NULLP) + { + DU_LOG("\nERROR --> E2AP : Memory allocation for E2FailureIEs failed"); + break; + } + + for(arrIdx=0; arrIdxprotocolIEs.list.array[arrIdx], sizeof(struct E2setupFailureIEs)); + if(e2SetupFailure->protocolIEs.list.array[arrIdx] == NULLP) + { + DU_LOG("\nERROR --> E2AP : Memory allocation for E2FailureIEs failed"); + memAllocFailed = true; + break; + } + } + + if(memAllocFailed == true) + { + DU_LOG("\nERROR --> E2AP : Memory allocation for E2FailureIEs failed"); + break; + } + + /* Trans Id */ + arrIdx = 0; + e2SetupFailure->protocolIEs.list.array[arrIdx]->id = ProtocolIE_IDE2_id_TransactionID; + e2SetupFailure->protocolIEs.list.array[arrIdx]->criticality = CriticalityE2_reject; + e2SetupFailure->protocolIEs.list.array[arrIdx]->value.present = E2setupFailureIEs__value_PR_TransactionID; + e2SetupFailure->protocolIEs.list.array[arrIdx]->value.choice.TransactionID = transId; + + arrIdx++; + e2SetupFailure->protocolIEs.list.array[arrIdx]->id = ProtocolIE_IDE2_id_CauseE2; + e2SetupFailure->protocolIEs.list.array[arrIdx]->criticality = CriticalityE2_reject; + e2SetupFailure->protocolIEs.list.array[arrIdx]->value.present = E2setupFailureIEs__value_PR_CauseE2; + e2SetupFailure->protocolIEs.list.array[arrIdx]->value.choice.CauseE2.present = CauseE2_PR_protocol; + e2SetupFailure->protocolIEs.list.array[arrIdx]->value.choice.CauseE2.choice.protocol = CauseE2Protocol_unspecified; + + arrIdx++; + e2SetupFailure->protocolIEs.list.array[arrIdx]->id = ProtocolIE_IDE2_id_TimeToWaitE2; + e2SetupFailure->protocolIEs.list.array[arrIdx]->criticality = CriticalityE2_ignore; + e2SetupFailure->protocolIEs.list.array[arrIdx]->value.present = E2setupFailureIEs__value_PR_TimeToWaitE2; + e2SetupFailure->protocolIEs.list.array[arrIdx]->value.choice.TimeToWaitE2 = TimeToWaitE2_v5s; + + xer_fprint(stdout, &asn_DEF_E2AP_PDU, e2apMsg); + memset(encBuf, 0, ENC_BUF_MAX_LEN); + encBufSize = 0; + encRetVal = aper_encode(&asn_DEF_E2AP_PDU, 0, e2apMsg, PrepFinalEncBuf, encBuf); + + /* Check encode results */ + if(encRetVal.encoded == ENCODE_FAIL) + { + DU_LOG("\nERROR --> E2AP : Could not encode E2 Setup failure structure (at %s)\n",\ + encRetVal.failed_type ? encRetVal.failed_type->name : "unknown"); + break; + } + else + { + DU_LOG("\nDEBUG --> E2AP : Created APER encoded buffer for E2 Setup Failure\n"); + for(int i=0; i< encBufSize; i++) + { + DU_LOG("%x",encBuf[i]); + } + } + + if(SendE2APMsg(RIC_APP_MEM_REG, RIC_POOL, duId) != ROK) + { + DU_LOG("\nERROR --> E2AP : Sending E2 Setup Failure failed"); + break; + } + break; + } + + FreeE2SetupFailure(e2apMsg); +} + /******************************************************************* * * @brief process the e2setup request @@ -688,21 +1033,64 @@ void ProcRicSubscriptionResponse(uint32_t duId) uint8_t ProcE2SetupReq(uint32_t *duId, E2setupRequest_t *e2SetupReq) { - uint8_t arrIdx = 0, e2NodeAddListIdx =0, duIdx = 0; + uint8_t arrIdx = 0, e2NodeAddListIdx =0, duIdx = 0, transId =0, ranFuncIdx; DuDb *duDb = NULLP; E2nodeComponentConfigAddition_List_t *e2NodeAddList; E2nodeComponentConfigAddition_ItemIEs_t *e2NodeAddItem; + RANfunction_ItemIEs_t *ranFuncItemIe; + RANfunction_Item_t *ranFunItem; + RANfunctions_List_t *ranFunctionsList; if(e2SetupReq) { - if(e2SetupReq->protocolIEs.list.array) - { - for(arrIdx=0; arrIdxprotocolIEs.list.count; arrIdx++) + if(e2SetupReq->protocolIEs.list.array) + { + for(arrIdx=0; arrIdxprotocolIEs.list.count; arrIdx++) + { + if(e2SetupReq->protocolIEs.list.array[arrIdx]) { - if(e2SetupReq->protocolIEs.list.array[arrIdx]) + switch(e2SetupReq->protocolIEs.list.array[arrIdx]->id) { - switch(e2SetupReq->protocolIEs.list.array[arrIdx]->id) - { + case ProtocolIE_IDE2_id_TransactionID: + { + transId = e2SetupReq->protocolIEs.list.array[arrIdx]->value.choice.TransactionID; + break; + } + case ProtocolIE_IDE2_id_GlobalE2node_ID: + { + if(e2SetupReq->protocolIEs.list.array[arrIdx]->value.choice.GlobalE2node_ID.choice.gNB->gNB_DU_ID) + { + *duId =e2SetupReq->protocolIEs.list.array[arrIdx]->value.choice.GlobalE2node_ID.choice.gNB->gNB_DU_ID->buf[0]; + + SEARCH_DU_DB(duIdx, *duId, duDb); + if(duDb == NULLP) + { + duDb = &ricCb.duInfo[ricCb.numDu]; + ricCb.numDu++; + } + memset(duDb, 0, sizeof(DuDb)); + duDb->duId = *duId; + } + break; + } + case ProtocolIE_IDE2_id_RANfunctionsAdded: + { + + ranFunctionsList = &e2SetupReq->protocolIEs.list.array[arrIdx]->value.choice.RANfunctions_List; + + if(ranFunctionsList->list.array) + { + for(ranFuncIdx=0;ranFuncIdxlist.count; ranFuncIdx++) + { + ranFuncItemIe = (RANfunction_ItemIEs_t *) ranFunctionsList->list.array[ranFuncIdx]; + ranFunItem = &ranFuncItemIe->value.choice.RANfunction_Item; + duDb->ranFunction[ranFunItem->ranFunctionID-1].id = ranFunItem->ranFunctionID; + duDb->ranFunction[ranFunItem->ranFunctionID-1].revisionCounter = ranFunItem->ranFunctionRevision; + duDb->numOfRanFunction++; + } + } + break; + } case ProtocolIE_IDE2_id_E2nodeComponentConfigAddition: { e2NodeAddList = &e2SetupReq->protocolIEs.list.array[arrIdx]->value.choice.E2nodeComponentConfigAddition_List; @@ -714,28 +1102,10 @@ uint8_t ProcE2SetupReq(uint32_t *duId, E2setupRequest_t *e2SetupReq) { e2NodeAddItem = (E2nodeComponentConfigAddition_ItemIEs_t *) e2NodeAddList->list.array[e2NodeAddListIdx]; if(e2NodeAddItem->value.choice.E2nodeComponentConfigAddition_Item.e2nodeComponentID.choice.\ - e2nodeComponentInterfaceTypeF1) + e2nodeComponentInterfaceTypeF1) { - if(e2NodeAddItem->value.choice.E2nodeComponentConfigAddition_Item.e2nodeComponentID.choice.\ - e2nodeComponentInterfaceTypeF1->gNB_DU_ID.buf) - { - *duId = e2NodeAddItem->value.choice.E2nodeComponentConfigAddition_Item.e2nodeComponentID.\ - choice.e2nodeComponentInterfaceTypeF1->gNB_DU_ID.buf[0]; - SEARCH_DU_DB(duIdx, duId, duDb); - if(duDb == NULLP) - { - duDb = &ricCb.duInfo[ricCb.numDu]; - ricCb.numDu++; - } - memset(duDb, 0, sizeof(DuDb)); - duDb->duId = *duId; - - if(BuildAndSendE2SetupRsp(*duId) !=ROK) - { - DU_LOG("\nERROR --> E2AP : Failed to build and send E2 setup response"); - return RFAILED; - } - } + duDb->e2NodeComponent.interfaceType = F1; + duDb->e2NodeComponent.componentId = e2NodeAddItem->value.choice.E2nodeComponentConfigAddition_Item.e2nodeComponentID.choice.e2nodeComponentInterfaceTypeF1->gNB_DU_ID.buf[0]; } } } @@ -749,6 +1119,12 @@ uint8_t ProcE2SetupReq(uint32_t *duId, E2setupRequest_t *e2SetupReq) } } } + + if(BuildAndSendE2SetupRsp(duDb, transId) !=ROK) + { + DU_LOG("\nERROR --> E2AP : Failed to build and send E2 setup response"); + return RFAILED; + } return ROK; } @@ -1126,6 +1502,203 @@ uint8_t ProcE2ResetReq(uint32_t duId, ResetRequestE2_t *resetReq) return ROK; } +/******************************************************************* + * + * @brief deallocate the memory allocated in building the + * Service Query message + * + * @details + * + * Function : FreeRicServiceQuery + * + * Functionality: deallocate the memory allocated in building + * Ric Service Query message + * + * @params[in] E2AP_PDU_t *e2apMsg + * + * @return void + * ****************************************************************/ + +void FreeRicServiceQuery(E2AP_PDU_t *e2apMsg) +{ + uint8_t arrIdx = 0, ranFuncIdx=0; + RANfunctionsID_List_t *ranFuncAddedList; + RICserviceQuery_t *ricServiceQuery; + + if(e2apMsg) + { + if(e2apMsg->choice.initiatingMessage) + { + ricServiceQuery = &e2apMsg->choice.initiatingMessage->value.choice.RICserviceQuery; + if(ricServiceQuery->protocolIEs.list.array) + { + for(arrIdx=0; arrIdxprotocolIEs.list.count; arrIdx++) + { + if(ricServiceQuery->protocolIEs.list.array[arrIdx]) + { + switch(ricServiceQuery->protocolIEs.list.array[arrIdx]->id) + { + case ProtocolIE_IDE2_id_RANfunctionsAccepted: + { + ranFuncAddedList= &ricServiceQuery->protocolIEs.list.array[arrIdx]->value.choice.RANfunctionsID_List; + if(ranFuncAddedList->list.array) + { + for(ranFuncIdx=0;ranFuncIdxlist.count; ranFuncIdx++) + { + RIC_FREE(ranFuncAddedList->list.array[ranFuncIdx], sizeof(RANfunction_ItemIEs_t)); + } + RIC_FREE(ranFuncAddedList->list.array, ranFuncAddedList->list.size); + } + break; + } + case RICserviceQuery_IEs__value_PR_TransactionID: + { + break; + } + } + RIC_FREE(ricServiceQuery->protocolIEs.list.array[arrIdx], sizeof(RICserviceQuery_IEs_t)); + } + } + RIC_FREE(ricServiceQuery->protocolIEs.list.array, ricServiceQuery->protocolIEs.list.size); + } + RIC_FREE(e2apMsg->choice.initiatingMessage, sizeof(InitiatingMessageE2_t)); + } + RIC_FREE(e2apMsg, sizeof(E2AP_PDU_t)); + } +} + +/******************************************************************* + * + * @brief build and send the ric service Query + * + * @details + * + * Function : BuildAndSendRicServiceQuery + * + * Functionality: build and send the ric service Query + * @return ROK - success + * RFAILED - Acknowledge + * + ******************************************************************/ + +uint8_t BuildAndSendRicServiceQuery(DuDb *duDb) +{ + uint8_t arrIdx; + uint8_t elementCnt; + uint8_t ret = RFAILED; + bool memAllocFailed = false; + E2AP_PDU_t *e2apMsg = NULL; + asn_enc_rval_t encRetVal; + RICserviceQuery_t *ricServiceQuery; + + DU_LOG("\nINFO --> E2AP : Building Ric service Query\n"); + while(true) + { + RIC_ALLOC(e2apMsg, sizeof(E2AP_PDU_t)); + if(e2apMsg == NULLP) + { + DU_LOG("\nERROR --> E2AP : Memory allocation for E2AP-PDU failed"); + break; + } + e2apMsg->present = E2AP_PDU_PR_initiatingMessage; + RIC_ALLOC(e2apMsg->choice.initiatingMessage , sizeof(struct InitiatingMessageE2)); + if(e2apMsg->choice.initiatingMessage == NULLP) + { + DU_LOG("\nERROR --> E2AP : Memory allocation for E2AP-PDU failed"); + break; + } + + e2apMsg->choice.initiatingMessage->procedureCode = ProcedureCodeE2_id_RICserviceQuery; + e2apMsg->choice.initiatingMessage->criticality = CriticalityE2_reject; + e2apMsg->choice.initiatingMessage->value.present = InitiatingMessageE2__value_PR_RICserviceQuery; + ricServiceQuery = &e2apMsg->choice.initiatingMessage->value.choice.RICserviceQuery; + + elementCnt = 1; + /* Fill Accepted RAN function IE If Ran function information is stored in databse */ + if(duDb->numOfRanFunction) + elementCnt++; + + ricServiceQuery->protocolIEs.list.count = elementCnt; + ricServiceQuery->protocolIEs.list.size = elementCnt * sizeof(RICserviceQuery_IEs_t*); + + RIC_ALLOC(ricServiceQuery->protocolIEs.list.array, ricServiceQuery->protocolIEs.list.size); + if(ricServiceQuery->protocolIEs.list.array == NULLP) + { + DU_LOG("\nERROR --> E2AP : Memory allocation for ricServiceQueryIEs failed"); + break; + } + + for(arrIdx=0; arrIdxprotocolIEs.list.array[arrIdx], sizeof(RICserviceQuery_IEs_t)); + if(ricServiceQuery->protocolIEs.list.array[arrIdx] == NULLP) + { + DU_LOG("\nERROR --> E2AP : Memory allocation for ricServiceQueryIEs failed"); + memAllocFailed = true; + break; + } + } + if(memAllocFailed == true) + { + DU_LOG("\nERROR --> E2AP : Memory allocation for ricServiceQueryIEs failed"); + break; + } + + /* Trans Id */ + arrIdx = 0; + ricServiceQuery->protocolIEs.list.array[arrIdx]->id = ProtocolIE_IDE2_id_TransactionID; + ricServiceQuery->protocolIEs.list.array[arrIdx]->criticality = CriticalityE2_reject; + ricServiceQuery->protocolIEs.list.array[arrIdx]->value.present = RICserviceQuery_IEs__value_PR_TransactionID; + ricServiceQuery->protocolIEs.list.array[arrIdx]->value.choice.TransactionID = assignTransactionId(duDb); + + if(duDb->numOfRanFunction) + { + /* Accepted RAN function Id */ + arrIdx++; + ricServiceQuery->protocolIEs.list.array[arrIdx]->id = ProtocolIE_IDE2_id_RANfunctionsAccepted; + ricServiceQuery->protocolIEs.list.array[arrIdx]->criticality = CriticalityE2_reject; + ricServiceQuery->protocolIEs.list.array[arrIdx]->value.present = RICserviceQuery_IEs__value_PR_RANfunctionsID_List; + if(BuildRanFunctionAddedList(duDb, 0, NULL, &ricServiceQuery->protocolIEs.list.array[arrIdx]->value.choice.RANfunctionsID_List, ProcedureCodeE2_id_RICserviceQuery)!=ROK) + { + DU_LOG("\nERROR --> E2AP : Failed to build Ran function added list"); + break; + } + } + + xer_fprint(stdout, &asn_DEF_E2AP_PDU, e2apMsg); + memset(encBuf, 0, ENC_BUF_MAX_LEN); + encBufSize = 0; + encRetVal = aper_encode(&asn_DEF_E2AP_PDU, 0, e2apMsg, PrepFinalEncBuf, encBuf); + + /* Check encode results */ + if(encRetVal.encoded == ENCODE_FAIL) + { + DU_LOG("\nERROR --> E2AP : Could not encode RIC service Query structure (at %s)\n",\ + encRetVal.failed_type ? encRetVal.failed_type->name : "unknown"); + break; + } + else + { + DU_LOG("\nDEBUG --> E2AP : Created APER encoded buffer for RIC service Query\n"); + for(int i=0; i< encBufSize; i++) + { + DU_LOG("%x",encBuf[i]); + } + } + + if(SendE2APMsg(RIC_APP_MEM_REG, RIC_POOL, duDb->duId) != ROK) + { + DU_LOG("\nERROR --> E2AP : Sending of RIC service Query failed"); + break; + } + + ret =ROK; + break; + } + FreeRicServiceQuery(e2apMsg); + return ret; +} + /******************************************************************* * * @brief Handles received E2AP message and sends back response @@ -1221,6 +1794,12 @@ void E2APMsgHdlr(uint32_t *duId, Buffer *mBuf) DU_LOG("\nINFO --> E2AP : RIC Indication Acknowledged"); break; } + case InitiatingMessageE2__value_PR_RICserviceUpdate: + { + DU_LOG("\nINFO --> E2AP : RIC Service update received"); + break; + } + default: { DU_LOG("\nERROR --> E2AP : Invalid type of intiating message [%d]",e2apMsg->choice.initiatingMessage->value.present);