[Epic-ID: ODUHIGH-516][Task-ID: 526] Handling of RIC Service Acknowledge and Failure 06/11806/4
authorpborla <pborla@radisys.com>
Thu, 21 Sep 2023 16:23:31 +0000 (21:53 +0530)
committerpborla <pborla@radisys.com>
Fri, 22 Sep 2023 09:53:02 +0000 (15:23 +0530)
Change-Id: I75f4f3423bfdf86b4a2a0e5227f13894e1595bbc
Signed-off-by: pborla <pborla@radisys.com>
src/du_app/du_e2ap_msg_hdl.c
src/du_app/du_e2ap_msg_hdl.h
src/du_app/du_tmr.c
src/ric_stub/ric_e2ap_msg_hdl.c

index f13282f..e952c5f 100644 (file)
@@ -50,6 +50,7 @@
 #include "E2SM-KPM-ActionDefinition.h"
 #include "E2SM-KPM-ActionDefinition-Format1.h"
 #include "MeasurementInfoItem.h"
+#include "RANfunctionsIDcause-List.h"
 
 /*******************************************************************
  *
@@ -3482,6 +3483,7 @@ uint8_t BuildAndSendRicServiceUpdate(RicServiceUpdate serviceUpdate)
       }
       duCb.e2apDb.e2TimersInfo.e2Timers.ricServiceUpdateTimer.ricService.dir = serviceUpdate.dir;
       duCb.e2apDb.e2TimersInfo.e2Timers.ricServiceUpdateTimer.ricService.transId =transId;
+      memcpy(&duCb.e2apDb.e2TimersInfo.e2Timers.ricServiceUpdateTimer.ricService.recvRanFuncList, &serviceUpdate.recvRanFuncList, sizeof(E2TmpRanFunList));
    }
    FreeRicServiceUpdate(e2apMsg);
    return ret;
@@ -3597,6 +3599,240 @@ void procRicServiceQuery(E2AP_PDU_t *e2apMsg)
    freeAperDecodingOfRicServiceQuery(ricServiceQuery);
 }
 
+/******************************************************************
+ *
+ * @brief Deallocation of memory allocated by aper decoder for 
+ *    RIC service update ack
+ *
+ * @details
+ *
+ *    Function : freeAperDecodingOfRicServiceUpdateAck
+ *
+ *    Functionality: Deallocation of memory allocated by aper decoder 
+ *    for RIC service update ack
+ *
+ * @params[in] RICserviceUpdateAck_t *ricServiceAck;
+ * @return void
+ *
+ * ****************************************************************/
+
+void freeAperDecodingOfRicServiceUpdateAck(RICserviceUpdateAcknowledge_t *ricServiceAck)
+{
+   uint8_t arrIdx=0,ranFuncIdx=0;
+   RANfunctionsID_List_t *ranFuncAddedList=NULL;
+
+   if(ricServiceAck)
+   {
+      if(ricServiceAck->protocolIEs.list.array)
+      {
+         for(arrIdx=0; arrIdx<ricServiceAck->protocolIEs.list.count; arrIdx++)
+         {
+            if(ricServiceAck->protocolIEs.list.array[arrIdx])
+            {
+               switch(ricServiceAck->protocolIEs.list.array[arrIdx]->id)
+               {
+                  case ProtocolIE_IDE2_id_RANfunctionsAccepted:
+                  {
+                     ranFuncAddedList= &ricServiceAck->protocolIEs.list.array[arrIdx]->value.choice.RANfunctionsID_List;
+                     if(ranFuncAddedList->list.array)
+                     {
+                        for(ranFuncIdx=0;ranFuncIdx<ranFuncAddedList->list.count; ranFuncIdx++)
+                        {
+                           free(ranFuncAddedList->list.array[ranFuncIdx]);
+                        }
+                        free(ranFuncAddedList->list.array);
+                     }
+                     break;
+                  }
+                  default:
+                     break;
+               }
+               free(ricServiceAck->protocolIEs.list.array[arrIdx]);  
+            }
+         }
+         free(ricServiceAck->protocolIEs.list.array);
+      }
+   }
+}
+
+/******************************************************************
+ *
+ * @brief Processes RIC service update ack sent by RIC
+ *
+ * @details
+ *
+ *    Function : procRicServiceUpdateAck
+ *
+ *    Functionality: Processes RIC service update ack sent by RIC
+ *
+ * @params[in] E2AP_PDU_t ASN decoded E2AP message
+ * @return ROK     - success
+ *         RFAILED - failure
+ *
+ * ****************************************************************/
+
+void procRicServiceUpdateAck(E2AP_PDU_t *e2apMsg)
+{
+   uint8_t arrIdx =0, transId =0; 
+   uint16_t id =0, tmpIdx=0, ranFuncIdx=0;
+   RicServiceUpdate serviceUpdate;
+   RANfunctionsIDcause_List_t *rejectedList=NULL;
+   RICserviceUpdateAcknowledge_t *ricServiceAck=NULL;
+   RANfunctionIDcause_ItemIEs_t *ranFuncRejectedItemIe=NULL;
+   
+   DU_LOG("\nINFO   -->  E2AP : RIC service update ack received"); 
+   memset(&serviceUpdate, 0, sizeof(RicServiceUpdate));
+   ricServiceAck = &e2apMsg->choice.successfulOutcome->value.choice.RICserviceUpdateAcknowledge;
+   
+   for(arrIdx=0; arrIdx<ricServiceAck->protocolIEs.list.count; arrIdx++)
+   {
+      switch(ricServiceAck->protocolIEs.list.array[arrIdx]->id)
+      {
+         case ProtocolIE_IDE2_id_TransactionID:
+         {
+            transId = ricServiceAck->protocolIEs.list.array[arrIdx]->value.choice.TransactionID;
+            if((duCb.e2apDb.e2TransInfo.e2InitTransaction[transId].transactionId == transId) &&\
+            (duCb.e2apDb.e2TransInfo.e2InitTransaction[transId].procedureCode == e2apMsg->choice.unsuccessfulOutcome->procedureCode))
+            {
+              memset(&duCb.e2apDb.e2TransInfo.e2InitTransaction[transId], 0, sizeof(E2TransInfo));
+            }
+            else if((duCb.e2apDb.e2TransInfo.ricInitTransaction[transId].transactionId == transId) &&\
+            (duCb.e2apDb.e2TransInfo.ricInitTransaction[transId].procedureCode == e2apMsg->choice.unsuccessfulOutcome->procedureCode))
+            {
+              memset(&duCb.e2apDb.e2TransInfo.ricInitTransaction[transId], 0, sizeof(E2TransInfo));
+            }
+            else
+            {
+               DU_LOG("\nERROR  -->  E2AP : Invalid transaction id [%d]", transId);
+               return ;
+            }
+            break;
+         }
+         
+         case ProtocolIE_IDE2_id_RANfunctionsAccepted:
+            break;
+
+         case ProtocolIE_IDE2_id_RANfunctionsRejected:
+         {
+            rejectedList= &ricServiceAck->protocolIEs.list.array[arrIdx]->value.choice.RANfunctionsIDcause_List;
+            if(rejectedList->list.array)
+            {
+               for(ranFuncIdx=0;ranFuncIdx<rejectedList->list.count; ranFuncIdx++)
+               {
+                  ranFuncRejectedItemIe =  (RANfunctionIDcause_ItemIEs_t*)rejectedList->list.array[ranFuncIdx];
+                  id = ranFuncRejectedItemIe->value.choice.RANfunctionIDcause_Item.ranFunctionID;
+                  tmpIdx= serviceUpdate.recvRanFuncList.numOfRanFunToBeAdded;
+                  serviceUpdate.recvRanFuncList.ranFunToBeAdded[tmpIdx].id = duCb.e2apDb.ranFunction[id-1].id;
+                  serviceUpdate.recvRanFuncList.ranFunToBeAdded[tmpIdx].revisionCounter = duCb.e2apDb.ranFunction[id-1].revisionCounter;
+                  serviceUpdate.recvRanFuncList.numOfRanFunToBeAdded++;
+               }
+            }
+            break;
+         }
+
+      }
+   }
+
+   if(serviceUpdate.recvRanFuncList.numOfRanFunToBeAdded)
+   {
+      serviceUpdate.dir = E2_NODE_INITIATED;
+      BuildAndSendRicServiceUpdate(serviceUpdate);
+   }
+   freeAperDecodingOfRicServiceUpdateAck(ricServiceAck);
+}
+
+/******************************************************************
+ *
+ * @brief Deallocation of memory allocated by aper decoder for 
+ *       RIC service update failure
+ *
+ * @details
+ *
+ *    Function : freeAperDecodingOfRicServiceUpdateFailure
+ *
+ *    Functionality: Deallocation of memory allocated by aper decoder 
+ *    for RIC service update failure
+ *
+ * @params[in] RICserviceUpdateFailure_t *ricServiceFailure;
+ * @return void
+ *
+ * ****************************************************************/
+
+void freeAperDecodingOfRicServiceUpdateFailure(RICserviceUpdateFailure_t *ricServiceFailure)
+{
+   uint8_t arrIdx=0;
+
+   if(ricServiceFailure)
+   {
+      if(ricServiceFailure->protocolIEs.list.array)
+      {
+         for(arrIdx=0; arrIdx<ricServiceFailure->protocolIEs.list.count; arrIdx++)
+         {
+            if(ricServiceFailure->protocolIEs.list.array[arrIdx])
+            {
+               free(ricServiceFailure->protocolIEs.list.array[arrIdx]);  
+            }
+         }
+         free(ricServiceFailure->protocolIEs.list.array);
+      }
+   }
+}
+
+/******************************************************************
+ *
+ * @brief Processes RIC service update failure sent by RIC
+ *
+ * @details
+ *
+ *    Function : procRicServiceUpdateFailure
+ *
+ *    Functionality: Processes RIC service update failure sent by RIC
+ *
+ * @params[in] E2AP_PDU_t ASN decoded E2AP message
+ * @return ROK     - success
+ *         RFAILED - failure
+ *
+ * ****************************************************************/
+
+void procRicServiceUpdateFailure(E2AP_PDU_t *e2apMsg)
+{
+   uint8_t arrIdx =0, timerValue=0; 
+   RICserviceUpdateFailure_t *ricServiceFailure=NULL;
+
+   DU_LOG("\nINFO   -->  E2AP : RIC service update failure received"); 
+   ricServiceFailure = &e2apMsg->choice.unsuccessfulOutcome->value.choice.RICserviceUpdateFailure;
+
+   for(arrIdx=0; arrIdx<ricServiceFailure->protocolIEs.list.count; arrIdx++)
+   {
+      switch(ricServiceFailure->protocolIEs.list.array[arrIdx]->id)
+      {
+         case ProtocolIE_IDE2_id_TransactionID:
+            {
+               break;
+            }
+         case ProtocolIE_IDE2_id_TimeToWaitE2:
+            {
+               timerValue = covertE2WaitTimerEnumToValue(ricServiceFailure->protocolIEs.list.array[arrIdx]->value.choice.TimeToWaitE2);
+               if((duChkTmr((PTR)&(duCb.e2apDb.e2TimersInfo.e2Timers.ricServiceUpdateTimer), EVENT_RIC_SERVICE_UPDATE_TMR)) == FALSE)
+               {
+                  duStartTmr((PTR)&(duCb.e2apDb.e2TimersInfo.e2Timers.ricServiceUpdateTimer), EVENT_RIC_SERVICE_UPDATE_TMR, timerValue);
+               }
+               else
+               {
+                  DU_LOG("\nERROR   -->  E2AP : EVENT_RIC_SERVICE_UPDATE_TMR  timer is already running");
+                  return;
+               }
+               break; 
+            }
+         case ProtocolIE_IDE2_id_CauseE2:
+            {
+               break;
+            }
+      }
+   }
+
+   freeAperDecodingOfRicServiceUpdateFailure(ricServiceFailure);
+}
 
 /*******************************************************************
  *
@@ -3677,6 +3913,11 @@ void E2APMsgHdlr(Buffer *mBuf)
                      procE2SetupFailure(e2apMsg);
                      break;
                   }
+               case UnsuccessfulOutcomeE2__value_PR_RICserviceUpdateFailure:
+                  {
+                     procRicServiceUpdateFailure(e2apMsg);
+                     break;
+                  }
                default:
                   {
                      DU_LOG("\nERROR  -->  E2AP : Invalid type of E2AP_PDU_PR_unsuccessfulOutcome  [%d]",\
@@ -3708,6 +3949,13 @@ void E2APMsgHdlr(Buffer *mBuf)
                      procResetResponse(e2apMsg);
                      break;
                   }
+               case SuccessfulOutcomeE2__value_PR_RICserviceUpdateAcknowledge:
+                  {
+                     procRicServiceUpdateAck(e2apMsg);
+                     break;
+                  }
+
+
                default:
                   {
                      DU_LOG("\nERROR  -->  E2AP : Invalid type of E2AP_PDU_PR_successfulOutcome  [%d]",\
index 47f1b7a..c5701c2 100644 (file)
@@ -25,7 +25,7 @@ uint8_t  BuildAndSendE2NodeConfigUpdate();
 uint8_t BuildAndSendE2ResetRequest(E2CauseType failureType, E2Cause failureCause);
 void     E2APMsgHdlr(Buffer *mBuf);
 uint8_t BuildAndSendRicIndication(RicSubscription *ricSubscriptionInfo);
-
+uint8_t BuildAndSendRicServiceUpdate(RicServiceUpdate serviceUpdate);
 uint8_t BuildAndSendStatsReq(uint16_t ranFuncId, RicSubscription *ricSubscriptionInfo);
 /**********************************************************************
   End of file
index 28663d8..838dd35 100644 (file)
@@ -53,7 +53,15 @@ bool duChkTmr(PTR cb, int16_t tmrEvnt)
              return TRUE;
          }
       }
-      
+      case EVENT_RIC_SERVICE_UPDATE_TMR:
+      {
+         if(((RicServiceUpdateTimer*)cb)->timer.tmrEvnt == EVENT_RIC_SERVICE_UPDATE_TMR)
+         {
+            DU_LOG("\nERROR  -->  DU_APP : duChkTmr: Timer already running for event [%d]", tmrEvnt);
+            return TRUE;
+         }
+         break;
+      }      
       default:
       {
          DU_LOG("\nERROR  -->  DU_APP : duChkTmr: Invalid tmr Evnt [%d]", tmrEvnt);
@@ -90,6 +98,16 @@ void duStartTmr(PTR cb, int16_t tmrEvnt, uint8_t timerValue)
          arg.max = MAX_E2_SETUP_TMR;
          break;
       }
+      case EVENT_RIC_SERVICE_UPDATE_TMR:
+      {
+         RicServiceUpdateTimer *ricServiceUpdateTimer;
+         ricServiceUpdateTimer= ((RicServiceUpdateTimer*)cb);
+         TMR_CALCUATE_WAIT(arg.wait, timerValue, duCb.duTimersInfo.tmrRes);
+
+         arg.timers = &ricServiceUpdateTimer->timer;
+         arg.max = MAX_RIC_SERVICE_UPDATE_TMR;
+         break;
+      }
       default:
       {
          DU_LOG("\nERROR  -->  DU : duStartTmr: Invalid tmr Evnt [%d]", tmrEvnt);
@@ -132,6 +150,14 @@ void duTmrExpiry(PTR cb,int16_t tmrEvnt)
          BuildAndSendE2SetupReq();
          break;
       }
+      case EVENT_RIC_SERVICE_UPDATE_TMR:
+      {
+         RicServiceUpdateTimer *ricServiceUpdateTimer;
+         
+         ricServiceUpdateTimer= ((RicServiceUpdateTimer*)cb);
+         BuildAndSendRicServiceUpdate(ricServiceUpdateTimer->ricService);
+         break;
+      }
       default:
       {
          DU_LOG("\nERROR  -->  DU : duStartTmr: Invalid tmr Evnt [%d]", tmrEvnt);
index 9b4ce41..c399f89 100644 (file)
@@ -2436,7 +2436,7 @@ uint8_t BuildRanFunctionRejectedList(uint8_t count, RanFunction *ranFunRejectedL
          return RFAILED;
       }
       ranFuncRejectedItemIe = (RANfunctionIDcause_ItemIEs_t*)ranFuncRejectedList->list.array[ranFuncIdx];
-      ranFuncRejectedItemIe->id = ProtocolIE_IDE2_id_RANfunctionID_Item;
+      ranFuncRejectedItemIe->id = ProtocolIE_IDE2_id_RANfunctionIEcause_Item;
       ranFuncRejectedItemIe->criticality= CriticalityE2_ignore;
       ranFuncRejectedItemIe->value.present = RANfunctionIDcause_ItemIEs__value_PR_RANfunctionIDcause_Item;
       ranFuncRejectedItemIe->value.choice.RANfunctionIDcause_Item.ranFunctionID = ranFunRejectedList[ranFuncIdx].id;
@@ -2738,16 +2738,7 @@ void ProcRicServiceUpdate(uint32_t duId, RICserviceUpdate_t *ricServiceUpdate)
                   {
                      delRanFuncItem  = (RANfunctionID_ItemIEs_t*) deleteList->list.array[ranFuncIdx];
                      ranFuncIdItem = &delRanFuncItem->value.choice.RANfunctionID_Item;
-                     if(duDb->ranFunction[ranFuncIdItem->ranFunctionID-1].id != ranFuncIdItem->ranFunctionID)
-                     {
-                        /* Calculating total number of ran fuctions which are not present */
-                        failedRanFuncCount++;
-
-                        /* Adding the ran function in temporary list */
-                        ricRanFuncList.ranFunRejectedList[ricRanFuncList.numOfRanFuneRejected].id =  ranFuncItem->ranFunctionID; 
-                        ricRanFuncList.numOfRanFuneRejected++;
-                     }
-                     else
+                     if(duDb->ranFunction[ranFuncIdItem->ranFunctionID-1].id == ranFuncIdItem->ranFunctionID)
                      {
                         memset(&duDb->ranFunction[ranFuncIdItem->ranFunctionID-1], 0, sizeof(RanFunction));
                         duDb->numOfRanFunction--;