Merge "RAR and MSG3 scheduling in TDD [Issue-ID: ODUHIGH-342]"
authorHarshita Lal <harshita.lal@radisys.com>
Tue, 28 Sep 2021 08:39:00 +0000 (08:39 +0000)
committerGerrit Code Review <gerrit@o-ran-sc.org>
Tue, 28 Sep 2021 08:39:00 +0000 (08:39 +0000)
1  2 
src/5gnrsch/sch_common.c
src/5gnrsch/sch_slot_ind.c
src/cm/common_def.h
src/du_app/du_cfg.c
src/du_app/du_cfg.h

diff --combined src/5gnrsch/sch_common.c
@@@ -47,6 -47,7 +47,7 @@@ SchCb schCb[SCH_MAX_INST]
  uint16_t prachCfgIdxTable[MAX_PRACH_CONFIG_IDX][8];
  uint16_t numRbForPrachTable[MAX_RACH_NUM_RB_IDX][5];
  uint8_t pucchResourceSet[MAX_PUCCH_RES_SET_IDX][4];
+ uint8_t puschDeltaTable[MAX_MU_PUSCH];
  
  SchMacUlSchInfoFunc schMacUlSchInfoOpts[] =
  {
@@@ -863,15 -864,10 +864,15 @@@ uint8_t schDlRsrcAllocDlMsg(DlMsgAlloc 
  void BuildK0K1TableForFdd(SchCellCb *cell, SchK0K1TimingInfoTbl *k0K1InfoTbl, bool pdschCfgCmnPres,SchPdschCfgCmn pdschCmnCfg,\
  SchPdschConfig pdschDedCfg, uint8_t ulAckListCount, uint8_t *UlAckTbl)
  {
 -   uint8_t k0TmpVal = 0, k1TmpVal =0, cfgIdx=0;
 +   
 +   uint8_t k1TmpVal =0, cfgIdx=0;
     uint8_t slotIdx=0, k0Index=0, k1Index=0, numK0=0, numK1=0, numTimeDomAlloc=0;
 -   SchPdschCfgCmnTimeDomRsrcAlloc cmnTimeDomRsrcAllocList[MAX_NUM_DL_ALLOC];
 -   SchPdschTimeDomRsrcAlloc dedTimeDomRsrcAllocList[MAX_NUM_DL_ALLOC];
 +   
 +   /* TODO Commented these below lines for resolving warnings. Presently these variable are not 
 +    * required but this will require for harq processing */
 +   // uint8_t k0TmpVal = 0; 
 +   // SchPdschCfgCmnTimeDomRsrcAlloc cmnTimeDomRsrcAllocList[MAX_NUM_DL_ALLOC];
 +   // SchPdschTimeDomRsrcAlloc dedTimeDomRsrcAllocList[MAX_NUM_DL_ALLOC];
  
     /* Initialization the structure and storing the total slot values. */
     memset(k0K1InfoTbl, 0, sizeof(SchK0K1TimingInfoTbl));
        numTimeDomAlloc = pdschCmnCfg.numTimeDomAlloc;
        for(cfgIdx = 0; cfgIdx<numTimeDomAlloc; cfgIdx++)
        {
 -         cmnTimeDomRsrcAllocList[cfgIdx] = pdschCmnCfg.timeDomRsrcAllocList[cfgIdx];
 +         /*TODO uncomment this line during harq processing */
 +         //cmnTimeDomRsrcAllocList[cfgIdx] = pdschCmnCfg.timeDomRsrcAllocList[cfgIdx];
        }
     }
     else
        numTimeDomAlloc = pdschDedCfg.numTimeDomRsrcAlloc;
        for(cfgIdx = 0; cfgIdx<numTimeDomAlloc; cfgIdx++)
        {
 -         dedTimeDomRsrcAllocList[cfgIdx] = pdschDedCfg.timeDomRsrcAllociList[cfgIdx];
 +         /*TODO uncomment this line during harq processing */
 +         //dedTimeDomRsrcAllocList[cfgIdx] = pdschDedCfg.timeDomRsrcAllociList[cfgIdx];
        }
     }
     
         * As per 38.331 PDSCH-TimeDomainResourceAllocation field descriptions. */
        for(k0Index = 0; ((k0Index < numTimeDomAlloc) && (k0Index < MAX_NUM_K0_IDX));  k0Index++)
        {
 +         /* TODO These if 0 we will remove during harq processing */
 +#if 0
           if(pdschCfgCmnPres == true)
           {
              k0TmpVal = cmnTimeDomRsrcAllocList[k0Index].k0;
                 k0TmpVal = DEFAULT_K0_VALUE;
              }
           }
 -         
 +#endif         
           /* Checking all the Ul Alloc values. If value is less than MIN_NUM_K1_IDX
            * then skip else continue storing the values. */
           numK1 = 0;
@@@ -1145,13 -1137,15 +1146,15 @@@ SchPdschConfig pdschDedCfg, uint8_t ulA
  *
  * ****************************************************************/
  void BuildK2InfoTableForFdd(SchCellCb *cell, SchPuschTimeDomRsrcAlloc timeDomRsrcAllocList[], uint16_t puschSymTblSize,\
- SchK2TimingInfoTbl *k2InfoTbl)
+ SchK2TimingInfoTbl *msg3K2InfoTbl, SchK2TimingInfoTbl *k2InfoTbl)
  {
-    uint16_t slotIdx=0, k2Index=0, k2TmpVal=0;
+    uint16_t slotIdx=0, k2Index=0, k2TmpIdx=0, msg3K2TmpIdx=0;
  
     /* Initialization the structure and storing the total slot values. */
     memset(k2InfoTbl, 0, sizeof(SchK2TimingInfoTbl));
     k2InfoTbl->tblSize = cell->numSlots;
+    if(msg3K2InfoTbl)
+       msg3K2InfoTbl->tblSize = cell->numSlots;
     
     /* Checking all possible indexes for K2. */
     for(slotIdx = 0; slotIdx < cell->numSlots; slotIdx++)
        /* Storing K2 values. */
        for(k2Index = 0; ((k2Index < puschSymTblSize) && (k2Index < MAX_NUM_K2_IDX)); k2Index++)
        {
-          k2TmpVal= k2InfoTbl->k2TimingInfo[slotIdx].numK2;
-          k2InfoTbl->k2TimingInfo[slotIdx].k2Indexes[k2TmpVal] = k2Index;
+          k2TmpIdx= k2InfoTbl->k2TimingInfo[slotIdx].numK2;
+          k2InfoTbl->k2TimingInfo[slotIdx].k2Indexes[k2TmpIdx] = k2Index;
           k2InfoTbl->k2TimingInfo[slotIdx].numK2++;
+          /* Updating K2 values for MSG3 */
+          if(msg3K2InfoTbl)
+          {
+             msg3K2TmpIdx = msg3K2InfoTbl->k2TimingInfo[slotIdx].numK2;
+             msg3K2InfoTbl->k2TimingInfo[slotIdx].k2Indexes[msg3K2TmpIdx] = k2Index;
+             msg3K2InfoTbl->k2TimingInfo[slotIdx].numK2++;
+          }
        }
     }
  }
   *
   * ****************************************************************/
  void BuildK2InfoTable(SchCellCb *cell, SchPuschTimeDomRsrcAlloc timeDomRsrcAllocList[], uint16_t puschSymTblSize,\
- SchK2TimingInfoTbl *k2InfoTbl)
+ SchK2TimingInfoTbl *msg3K2InfoTbl, SchK2TimingInfoTbl *k2InfoTbl)
  {
  
  #ifdef NR_TDD
     bool dlSymbolPresent = false;
-    uint8_t slotIdx=0, k2Index=0, k2TmpVal=0, numK2 =0, currentSymbol =0;
+    uint8_t slotIdx=0, k2Index=0, k2Val=0, k2TmpVal=0, msg3K2TmpVal=0, msg3Delta=0, numK2 =0, currentSymbol =0;
     uint8_t startSymbol =0, endSymbol =0, checkSymbol=0, totalCfgSlot=0, slotCfg=0;
     SlotConfig currentSlot;
  #endif
  
     if(cell->cellCfg.dupMode == DUPLEX_MODE_FDD)
     {
-       BuildK2InfoTableForFdd(cell, timeDomRsrcAllocList, puschSymTblSize, k2InfoTbl);
+       BuildK2InfoTableForFdd(cell, timeDomRsrcAllocList, puschSymTblSize, msg3K2InfoTbl, k2InfoTbl);
     }
     else
     {
        /* Initialization the structure and storing the total slot values. */
        memset(k2InfoTbl, 0, sizeof(SchK2TimingInfoTbl));
        k2InfoTbl->tblSize = cell->numSlots;
+       if(msg3K2InfoTbl)
+          msg3K2InfoTbl->tblSize = cell->numSlots;
        totalCfgSlot = calculateSlotPatternLength(cell->cellCfg.ssbSchCfg.scsCommon, cell->cellCfg.tddCfg.tddPeriod);
  
        /* Checking all possible indexes for K2. */
-       for(slotIdx = 0; slotIdx < k2InfoTbl->tblSize; slotIdx++)
+       for(slotIdx = 0; slotIdx < cell->numSlots; slotIdx++)
        {
           currentSlot = schGetSlotSymbFrmt(slotIdx % totalCfgSlot, cell->slotFrmtBitMap);
           
                 /* Storing k2, startSymbol, endSymbol information for further processing.
                  * If k2 is absent then fill the default values given in spec 38.331
                  * PUSCH-TimeDomainResourceAllocationList field descriptions */
-                k2TmpVal = timeDomRsrcAllocList[k2Index].k2;
-                if(!k2TmpVal)
+                k2Val = timeDomRsrcAllocList[k2Index].k2;
+                if(!k2Val)
                 {
                    switch(cell->cellCfg.ssbSchCfg.scsCommon)
                    {
                       case SCS_15KHZ:
-                         k2TmpVal = DEFAULT_K2_VALUE_FOR_SCS15;
+                         k2Val = DEFAULT_K2_VALUE_FOR_SCS15;
                          break;
                       case SCS_30KHZ:
-                         k2TmpVal = DEFAULT_K2_VALUE_FOR_SCS30;
+                         k2Val = DEFAULT_K2_VALUE_FOR_SCS30;
                          break;
                       case SCS_60KHZ:
-                         k2TmpVal = DEFAULT_K2_VALUE_FOR_SCS60;
+                         k2Val = DEFAULT_K2_VALUE_FOR_SCS60;
                          break;
                       case SCS_120KHZ:
-                         k2TmpVal = DEFAULT_K2_VALUE_FOR_SCS120;
+                         k2Val = DEFAULT_K2_VALUE_FOR_SCS120;
                          break;
                    }
                 }
                 /* Current slot + k2 should be either UL or FLEXI slot.
                  * If slot is FLEXI then check all the symbols of that slot,
                  * it should not contain any DL or FLEXI slot */
-                k2TmpVal = (slotIdx + k2TmpVal) % totalCfgSlot;
+                k2TmpVal = (slotIdx + k2Val) % totalCfgSlot;
                 slotCfg = schGetSlotSymbFrmt(k2TmpVal, cell->slotFrmtBitMap);
-                if(slotCfg == DL_SLOT)
-                {
-                   continue;
-                }
-                if(slotCfg == FLEXI_SLOT)
+                if(slotCfg != DL_SLOT)
                 {
-                   startSymbol =  timeDomRsrcAllocList[k2Index].startSymbol;
-                   endSymbol   =  startSymbol+ timeDomRsrcAllocList[k2Index].symbolLength;
-                   dlSymbolPresent = false;
-                   for(checkSymbol= startSymbol; checkSymbol<endSymbol; checkSymbol++)
+                   if(slotCfg == FLEXI_SLOT)
                    {
-                      currentSymbol = cell->cellCfg.tddCfg.slotCfg[k2TmpVal][checkSymbol];
-                      if(currentSymbol == DL_SLOT || currentSymbol == FLEXI_SLOT)
+                      startSymbol =  timeDomRsrcAllocList[k2Index].startSymbol;
+                      endSymbol   =  startSymbol+ timeDomRsrcAllocList[k2Index].symbolLength;
+                      dlSymbolPresent = false;
+                      for(checkSymbol= startSymbol; checkSymbol<endSymbol; checkSymbol++)
                       {
-                         dlSymbolPresent = true;
-                         break;
+                         currentSymbol = cell->cellCfg.tddCfg.slotCfg[k2TmpVal][checkSymbol];
+                         if(currentSymbol == DL_SLOT || currentSymbol == FLEXI_SLOT)
+                         {
+                            dlSymbolPresent = true;
+                            break;
+                         }
                       }
                    }
+                   /* Store all the values if all condition satisfies. */
+                   if(dlSymbolPresent != true || slotCfg == UL_SLOT)
+                   {
+                      numK2 = k2InfoTbl->k2TimingInfo[slotIdx].numK2;
+                      k2InfoTbl->k2TimingInfo[slotIdx].k2Indexes[numK2] = k2Index;
+                      k2InfoTbl->k2TimingInfo[slotIdx].numK2++;
+                   }
                 }
-                /* Store all the values if all condition satisfies. */
-                if(dlSymbolPresent != true || slotCfg == UL_SLOT)
+                if(msg3K2InfoTbl)
                 {
-                   numK2 = k2InfoTbl->k2TimingInfo[slotIdx].numK2;
-                   k2InfoTbl->k2TimingInfo[slotIdx].k2Indexes[numK2] = k2Index;
-                   k2InfoTbl->k2TimingInfo[slotIdx].numK2++;
+                    msg3Delta = puschDeltaTable[cell->cellCfg.numerology];
+                   /* Check for K2 for MSG3 */
+                   /* Current slot + k2 should be either UL or FLEXI slot.
+                    * If slot is FLEXI then check all the symbols of that slot,
+                    * it should not contain any DL or FLEXI slot */
+                   msg3K2TmpVal = (slotIdx + k2Val + msg3Delta) % totalCfgSlot;
+                   slotCfg = schGetSlotSymbFrmt(msg3K2TmpVal, cell->slotFrmtBitMap);
+                   if(slotCfg != DL_SLOT)
+                   {
+                      if(slotCfg == FLEXI_SLOT)
+                      {
+                         startSymbol =  timeDomRsrcAllocList[k2Index].startSymbol;
+                         endSymbol   =  startSymbol+ timeDomRsrcAllocList[k2Index].symbolLength;
+                         dlSymbolPresent = false;
+                         for(checkSymbol= startSymbol; checkSymbol<endSymbol; checkSymbol++)
+                         {
+                            currentSymbol = cell->cellCfg.tddCfg.slotCfg[msg3K2TmpVal][checkSymbol];
+                            if(currentSymbol == DL_SLOT || currentSymbol == FLEXI_SLOT)
+                            {
+                               dlSymbolPresent = true;
+                               break;
+                            }
+                         }
+                      }
+                      /* Store all the values if all condition satisfies. */
+                      if(dlSymbolPresent != true || slotCfg == UL_SLOT)
+                      {
+                         numK2 = msg3K2InfoTbl->k2TimingInfo[slotIdx].numK2;
+                         msg3K2InfoTbl->k2TimingInfo[slotIdx].k2Indexes[numK2] = k2Index;
+                         msg3K2InfoTbl->k2TimingInfo[slotIdx].numK2++;
+                      }
+                   }
                 }
              }
           }
@@@ -79,7 -79,6 +79,6 @@@ uint8_t sendDlAllocToMac(DlSchedInfo *d
  
  }
  
  /*******************************************************************
   *
   * @brief Handles slot indication at SCH 
@@@ -117,6 -116,79 +116,79 @@@ void schCalcSlotValues(SlotTimingInfo s
     ADD_DELTA_TO_TIME(slotInd, schSlotValue->dlMsgTime, PHY_DELTA_DL + SCHED_DELTA);
  }
  
+ /*******************************************************************
+  *
+  * @brief Checks if a slot is to be scheduled for SSB transmission
+  *
+  * @details
+  *
+  *    Function : schCheckSsbOcc 
+  *
+  *    Functionality:
+  *       Checks if a slot is to be scheduled for SSB transmission
+  *
+  * @params[in] SlotTimingInfo slotTime
+  *             SchCellCb *cell 
+  * @return  Pdu transmission 
+  *
+  * ****************************************************************/
+ PduTxOccsaion schCheckSsbOcc(SlotTimingInfo slotTime, SchCellCb *cell)
+ {
+    uint8_t  ssb_rep;
+    ssb_rep = cell->cellCfg.ssbSchCfg.ssbPeriod;
+    /* Identify SSB ocassion*/
+    if ((slotTime.sfn % SCH_MIB_TRANS == 0) && (slotTime.slot ==0))
+    {
+       return NEW_TRANSMISSION;
+    }
+    else if(cell->firstSsbTransmitted) 
+    {
+       if((ssb_rep == 5) && ((slotTime.slot == 0 || slotTime.slot == 10)))
+          return REPEATITION;
+       else if((slotTime.sfn % (ssb_rep/10) == 0) && slotTime.slot == 0)
+          return REPEATITION;
+    }
+    /* not SSB occassion */
+    return NO_TRANSMISSION;
+ }
+ /*******************************************************************
+  *
+  * @brief Checks if a slot is to be scheduled for SIB1 transmission
+  *
+  * @details
+  *
+  *    Function : schCheckSib1Occ
+  *
+  *    Functionality:
+  *       Checks if a slot is to be scheduled for SIB1 transmission
+  *
+  * @params[in] SlotTimingInfo slotTime
+  *             SchCellCb *cell
+  * @return  Pdu transmission
+  *
+  * ****************************************************************/
+ PduTxOccsaion schCheckSib1Occ(SlotTimingInfo slotTime, SchCellCb *cell)
+ {
+    /* Identify SIB1 occasions */
+    if((slotTime.sfn % SCH_SIB1_TRANS == 0) && (slotTime.slot ==0))
+    {
+       return NEW_TRANSMISSION;
+    }
+    else if(cell->firstSib1Transmitted) 
+    {
+       if((slotTime.sfn % (cell->cellCfg.sib1SchCfg.sib1RepetitionPeriod/10) == 0) &&
+             (slotTime.slot == 0))
+       {
+          return REPEATITION;
+       }
+    }
+    /* not SIB1 occassion */
+    return NO_TRANSMISSION;
+ }
  /*******************************************************************
   *
   * @brief 
@@@ -183,10 -255,7 +255,10 @@@ uint8_t schFillBoGrantDlSchedInfo(SchCe
        
        if (!dlMsgAlloc->numLc)
        {
 -         DU_LOG("\nDEBUG  -->  SCH : No bo for any lcid\n");
 +         DU_LOG("\nDEBUG  -->  SCH : No pending BO for any LC id\n");
 +         /* Free the dl ded msg info allocated in macSchDlRlcBoInfo */
 +         SCH_FREE(cell->schDlSlotInfo[dlSchedInfo->schSlotValue.dlMsgTime.slot]->dlMsgInfo, \
 +               sizeof(DlMsgInfo));
           return ROK;
        }
  
   * ****************************************************************/
  uint8_t schProcessSlotInd(SlotTimingInfo *slotInd, Inst schInst)
  {
-    uint8_t  ssb_rep, ueIdx, lcgIdx, ret = ROK;
+    uint8_t  ueIdx, lcgIdx, ret = ROK;
     uint16_t slot;
     DlSchedInfo dlSchedInfo;
     DlBrdcstAlloc *dlBrdcstAlloc = NULLP;
-    RarAlloc   *rarAlloc = NULLP;
     DlMsgAlloc  *msg4Alloc = NULLP;
     DlMsgAlloc *dlMsgAlloc = NULLP;
     SchCellCb  *cell = NULLP;
  
     memset(&dlSchedInfo,0,sizeof(DlSchedInfo));
     dlSchedInfo.dlMsgAlloc = NULLP;
     schCalcSlotValues(*slotInd, &dlSchedInfo.schSlotValue);
     dlBrdcstAlloc = &dlSchedInfo.brdcstAlloc;
-    dlBrdcstAlloc->ssbTrans = NO_SSB;
-    dlBrdcstAlloc->sib1Trans = NO_SIB1;
+    dlBrdcstAlloc->ssbTrans = NO_TRANSMISSION;
+    dlBrdcstAlloc->sib1Trans = NO_TRANSMISSION;
  
     cell = schCb[schInst].cells[schInst];
     if(cell == NULLP)
        DU_LOG("\nERROR  -->  SCH : Cell Does not exist");
        return RFAILED;
     }
-    ssb_rep = cell->cellCfg.ssbSchCfg.ssbPeriod;
     memcpy(&cell->slotInfo, slotInd, sizeof(SlotTimingInfo));
-    dlBrdcstAlloc->ssbIdxSupported = 1;
+    dlBrdcstAlloc->ssbIdxSupported = SSB_IDX_SUPPORTED;
  
     slot = dlSchedInfo.schSlotValue.currentTime.slot;
  
     dlSchedInfo.cellId = cell->cellId;
  
-    /* Identify SSB ocassion*/
-    if ((dlSchedInfo.schSlotValue.broadcastTime.sfn % SCH_MIB_TRANS == 0) && (dlSchedInfo.schSlotValue.broadcastTime.slot ==0))
-    {
-       dlBrdcstAlloc->ssbTrans = SSB_TRANSMISSION;
-       if(!cell->firstSsbTransmitted)
-          cell->firstSsbTransmitted = true;
-    }
-    else if (cell->firstSsbTransmitted) 
-    {
-       if((ssb_rep == 5) && ((dlSchedInfo.schSlotValue.broadcastTime.slot == 0 || dlSchedInfo.schSlotValue.broadcastTime.slot == 10)))
-          dlBrdcstAlloc->ssbTrans = SSB_REPEAT;
-       else if((dlSchedInfo.schSlotValue.broadcastTime.sfn % (ssb_rep/10) == 0) && dlSchedInfo.schSlotValue.broadcastTime.slot == 0)
-          dlBrdcstAlloc->ssbTrans = SSB_REPEAT;
-    }
-    else
-    {
-       /* not SSB occassion */
-    }
-    /* Identify SIB1 occasions */
-    if((dlSchedInfo.schSlotValue.broadcastTime.sfn % SCH_SIB1_TRANS == 0) && (dlSchedInfo.schSlotValue.broadcastTime.slot ==0))
-    {
-       dlBrdcstAlloc->sib1Trans = SIB1_TRANSMISSION;
-       if(!cell->firstSib1Transmitted)
-          cell->firstSib1Transmitted = true;
-    }
-    else if (cell->firstSib1Transmitted) 
-    {
-       if((dlSchedInfo.schSlotValue.broadcastTime.sfn % (cell->cellCfg.sib1SchCfg.sib1RepetitionPeriod/10) == 0) &&
-             (dlSchedInfo.schSlotValue.broadcastTime.slot == 0))
-       {
-          dlBrdcstAlloc->sib1Trans = SIB1_REPITITION;
-       }
-    }
-    else
-    {
-       /* not SIB1 occassion */
-    }
+    /* Check if this slot is SSB occassion */
+    dlBrdcstAlloc->ssbTrans = schCheckSsbOcc(dlSchedInfo.schSlotValue.broadcastTime, cell); 
+    if((dlBrdcstAlloc->ssbTrans == NEW_TRANSMISSION) && (!cell->firstSsbTransmitted))
+       cell->firstSsbTransmitted = true;
  
+    /* Check if this slot is SIB1 occassion */
+    dlBrdcstAlloc->sib1Trans = schCheckSib1Occ(dlSchedInfo.schSlotValue.broadcastTime, cell);
+    if((dlBrdcstAlloc->sib1Trans == NEW_TRANSMISSION) && (!cell->firstSib1Transmitted))
+       cell->firstSib1Transmitted = true;
  
     if(dlBrdcstAlloc->ssbTrans || dlBrdcstAlloc->sib1Trans)
     {
     schProcessRaReq(*slotInd, cell);
  
     /* check for RAR */
-    if(cell->schDlSlotInfo[dlSchedInfo.schSlotValue.rarTime.slot]->rarInfo != NULLP)
+    if(cell->schDlSlotInfo[dlSchedInfo.schSlotValue.rarTime.slot]->rarAlloc != NULLP)
     {
        slot = dlSchedInfo.schSlotValue.rarTime.slot;
-       SCH_ALLOC(rarAlloc, sizeof(RarAlloc));
-       if(!rarAlloc)
-       {
-          DU_LOG("\nERROR  -->  SCH : Memory Allocation failed for RAR alloc");
-          return RFAILED;
-       }
-       dlSchedInfo.rarAlloc = rarAlloc;
-       /* RAR info is copied, this was earlier filled in schProcessRachInd */
-       memcpy(&rarAlloc->rarInfo,cell->schDlSlotInfo[slot]->rarInfo, sizeof(RarInfo));
-       /* pdcch and pdsch data is filled */
-       schFillRar(rarAlloc,
-           cell->schDlSlotInfo[slot]->rarInfo->raRnti,
-           cell->cellCfg.phyCellId,
-           cell->cellCfg.ssbSchCfg.ssbOffsetPointA,
-        dlBrdcstAlloc->ssbTrans,
-        dlBrdcstAlloc->sib1Trans);
-       SCH_FREE(cell->schDlSlotInfo[slot]->rarInfo,sizeof(RarInfo));
-       cell->schDlSlotInfo[slot]->rarInfo = NULLP;
+       dlSchedInfo.rarAlloc = cell->schDlSlotInfo[slot]->rarAlloc;
+       cell->schDlSlotInfo[slot]->rarAlloc = NULLP;
     }
  
     /* check for MSG4 */
        SCH_FREE(cell->schDlSlotInfo[dlSchedInfo.schSlotValue.dlMsgTime.slot]->dlMsgInfo, sizeof(DlMsgInfo));
        cell->schDlSlotInfo[dlSchedInfo.schSlotValue.dlMsgTime.slot]->dlMsgInfo = NULL;
     }
     /* check if UL grant must be sent in this slot for a SR/BSR that had been received */
     for(ueIdx=0; ueIdx<cell->numActvUe; ueIdx++)
     {
diff --combined src/cm/common_def.h
  #define RADIO_FRAME_DURATION 10 /* Time duration of a radio frame in ms */
  /* MAX values */
  #define MAX_NUM_CELL 1
+ #define MAX_NUM_MU   4
  #define MAX_NUM_UE   2
  #define MAX_NUM_UE_PER_TTI 1
 -#define MAX_NUM_LC   11
 +#define MAX_NUM_LC   32   /*Spec 38.331: Sec 6.4: maxLC-ID Keyword*/
  #define MAX_NUM_SRB  3    /* Max. no of Srbs */
  #define MAX_NUM_DRB  29   /* spec 38.331, maxDRB */
  
diff --combined src/du_app/du_cfg.c
@@@ -215,7 -215,10 +215,7 @@@ uint8_t readMacCfg(
     }
     else
     {
 -      for(uint8_t idx=0; idx<encBufSize; idx++)
 -      {
 -       duCfgParam.macCellCfg.ssbCfg.mibPdu[idx]=encBuf[idx];
 -      }
 +      memcpy(&duCfgParam.macCellCfg.ssbCfg.mibPdu, encBuf,encBufSize);
     }
     duCfgParam.macCellCfg.ssbCfg.multCarrBand = SSB_MULT_CARRIER_BAND;
     duCfgParam.macCellCfg.ssbCfg.multCellCarr = MULT_CELL_CARRIER;
        PDSCH_START_SYMBOL;
     duCfgParam.macCellCfg.initialDlBwp.pdschCommon.timeDomRsrcAllocList[idx].lengthSymbol =
        PDSCH_LENGTH_SYMBOL;
+  
     idx++;
     duCfgParam.macCellCfg.initialDlBwp.pdschCommon.timeDomRsrcAllocList[idx].k0 = PDSCH_K0_CFG2;
     duCfgParam.macCellCfg.initialDlBwp.pdschCommon.timeDomRsrcAllocList[idx].mappingType = 
@@@ -463,7 -467,6 +464,7 @@@ uint8_t fillServCellCfgCommSib(SrvCellC
     pdcchCfg.searchSpcId = PDCCH_SEARCH_SPACE_ID;
     pdcchCfg.ctrlRsrcSetId = PDCCH_CTRL_RSRC_SET_ID;
     pdcchCfg.monitorSlotPrdAndOffPresent = \
 +      
        SearchSpace__monitoringSlotPeriodicityAndOffset_PR_sl1;
     //pdcchCfg.monitorSlotPrdAndOff = \
     SearchSpace__monitoringSlotPeriodicityAndOffset_PR_sl1;
     pdschCfg.timeDomAlloc[0].mapType = \
        PDSCH_TimeDomainResourceAllocation__mappingType_typeA;
     pdschCfg.timeDomAlloc[0].sliv = calcSliv(PDSCH_START_SYMBOL,PDSCH_LENGTH_SYMBOL);
     pdschCfg.timeDomAlloc[1].k0 = PDSCH_K0_CFG2;
     pdschCfg.timeDomAlloc[1].mapType = \
        PDSCH_TimeDomainResourceAllocation__mappingType_typeA;
     rachCfg.preambleRcvdTgtPwr = PRACH_PREAMBLE_RCVD_TGT_PWR;
     rachCfg.preambleTransMax = RACH_ConfigGeneric__preambleTransMax_n200;
     rachCfg.pwrRampingStep = RACH_ConfigGeneric__powerRampingStep_dB2;
-    rachCfg.raRspWindow = RACH_ConfigGeneric__ra_ResponseWindow_sl20;
+    rachCfg.raRspWindow = RACH_ConfigGeneric__ra_ResponseWindow_sl10;
     rachCfg.numRaPreamble = NUM_RA_PREAMBLE;
     rachCfg.ssbPerRachOccPresent = \
        RACH_ConfigCommon__ssb_perRACH_OccasionAndCB_PreamblesPerSSB_PR_one;
  
  uint8_t readCfg()
  {
 -   uint8_t i,j,k;
 +   uint8_t srvdCellIdx, bandIdx, sliceIdx, plmnIdx;
 +   uint8_t brdcstPlmnIdx, freqBandIdx, srvdPlmnIdx;
     uint32_t ipv4_du, ipv4_cu, ipv4_ric;
     MibParams mib;
 -   Sib1Params sib1;   
 +   Sib1Params sib1;
 +   F1TaiSliceSuppLst *taiSliceSuppLst;
 +   RrmPolicy  *rrmPolicy;
 +
 +   /* TODO Added these below variable for local testing, once we will receive the
 +    * configuration from O1 we can remove these variable */
 +   F1Snsaai snsaai[NUM_OF_SUPPORTED_SLICE] = {{1,{2,3,4}},{5,{6,7,8}}};
 +   ResourceType rsrcType = PRB;
 +   RrmPolicyRatio policyRatio= {10,20,30};
 +   PolicyMemberList memberList;
 +   
 +   memset(&memberList, 0, sizeof(PolicyMemberList));
 +   memberList.snsaai =  snsaai[DEDICATED_SLICE_INDEX];
  
  #ifdef O1_ENABLE
     if( getStartupConfig(&g_cfg) != ROK )
     duCfgParam.egtpParams.destIp.ipV4Pres = TRUE;
     duCfgParam.egtpParams.destIp.ipV4Addr = ipv4_cu;
     duCfgParam.egtpParams.destPort = CU_EGTP_PORT;
 -   duCfgParam.egtpParams.minTunnelId = 0;
 -   duCfgParam.egtpParams.maxTunnelId = 10;
 +   duCfgParam.egtpParams.minTunnelId = MIN_TEID;
 +   duCfgParam.egtpParams.maxTunnelId = MAX_TEID;
  
     duCfgParam.maxUe = 32; //TODO: Check
     /* DU Info */      
     sib1.tac = DU_TAC;
     sib1.ranac = DU_RANAC;
     sib1.cellIdentity = CELL_IDENTITY;
 -   sib1.cellResvdForOpUse =\
 -      PLMN_IdentityInfo__cellReservedForOperatorUse_notReserved;
 +   sib1.cellResvdForOpUse = PLMN_IdentityInfo__cellReservedForOperatorUse_notReserved;
     sib1.connEstFailCnt = ConnEstFailureControl__connEstFailCount_n3;
 -   sib1.connEstFailOffValidity =\
 -      ConnEstFailureControl__connEstFailOffsetValidity_s120;
 +   sib1.connEstFailOffValidity = ConnEstFailureControl__connEstFailOffsetValidity_s120;
     sib1.siSchedInfo.winLen = SI_SchedulingInfo__si_WindowLength_s5;
 -   sib1.siSchedInfo.broadcastSta = \
 -      SchedulingInfo__si_BroadcastStatus_broadcasting;
 +   sib1.siSchedInfo.broadcastSta = SchedulingInfo__si_BroadcastStatus_broadcasting;
     sib1.siSchedInfo.preiodicity = SchedulingInfo__si_Periodicity_rf8;
     sib1.siSchedInfo.sibType = SIB_TypeInfo__type_sibType2;
     sib1.siSchedInfo.sibValTag = SIB1_VALUE_TAG;
  
     duCfgParam.sib1Params = sib1;
  
 -   for(i=0; i<DEFAULT_CELLS; i++)
 +   for(srvdCellIdx=0; srvdCellIdx<DEFAULT_CELLS; srvdCellIdx++)
     { 
 -      memset(&duCfgParam.srvdCellLst[i].duCellInfo.cellInfo.nrCgi.plmn, 0, sizeof(Plmn));
 -      duCfgParam.srvdCellLst[i].duCellInfo.cellInfo.nrCgi.plmn.mcc[0] = PLMN_MCC0;
 -      duCfgParam.srvdCellLst[i].duCellInfo.cellInfo.nrCgi.plmn.mcc[1] = PLMN_MCC1;
 -      duCfgParam.srvdCellLst[i].duCellInfo.cellInfo.nrCgi.plmn.mcc[2] = PLMN_MCC2;
 -      duCfgParam.srvdCellLst[i].duCellInfo.cellInfo.nrCgi.plmn.mnc[0] = PLMN_MNC0;
 -      duCfgParam.srvdCellLst[i].duCellInfo.cellInfo.nrCgi.plmn.mnc[1] = PLMN_MNC1;
 +      memset(&duCfgParam.srvdCellLst[srvdCellIdx].duCellInfo.cellInfo.nrCgi.plmn, 0, sizeof(Plmn));
 +      duCfgParam.srvdCellLst[srvdCellIdx].duCellInfo.cellInfo.nrCgi.plmn.mcc[0] = PLMN_MCC0;
 +      duCfgParam.srvdCellLst[srvdCellIdx].duCellInfo.cellInfo.nrCgi.plmn.mcc[1] = PLMN_MCC1;
 +      duCfgParam.srvdCellLst[srvdCellIdx].duCellInfo.cellInfo.nrCgi.plmn.mcc[2] = PLMN_MCC2;
 +      duCfgParam.srvdCellLst[srvdCellIdx].duCellInfo.cellInfo.nrCgi.plmn.mnc[0] = PLMN_MNC0;
 +      duCfgParam.srvdCellLst[srvdCellIdx].duCellInfo.cellInfo.nrCgi.plmn.mnc[1] = PLMN_MNC1;
  
        /*Cell ID */
 -      duCfgParam.srvdCellLst[i].duCellInfo.cellInfo.nrCgi.cellId = NR_CELL_ID;
 -      duCfgParam.srvdCellLst[i].duCellInfo.cellInfo.nrPci = NR_PCI;
 +      duCfgParam.srvdCellLst[srvdCellIdx].duCellInfo.cellInfo.nrCgi.cellId = NR_CELL_ID;
 +      duCfgParam.srvdCellLst[srvdCellIdx].duCellInfo.cellInfo.nrPci = NR_PCI;
  
        /* List of Available PLMN */
 -      for(j=0;j<MAX_PLMN;j++)
 +      for(srvdPlmnIdx=0; srvdPlmnIdx<MAX_PLMN; srvdPlmnIdx++)
        {
 -       memset(&duCfgParam.srvdCellLst[i].duCellInfo.cellInfo.plmn[j], 0, sizeof(Plmn));
 -       duCfgParam.srvdCellLst[i].duCellInfo.cellInfo.plmn[j].mcc[0] = PLMN_MCC0;
 -       duCfgParam.srvdCellLst[i].duCellInfo.cellInfo.plmn[j].mcc[1] = PLMN_MCC1;
 -       duCfgParam.srvdCellLst[i].duCellInfo.cellInfo.plmn[j].mcc[2] = PLMN_MCC2;
 -       duCfgParam.srvdCellLst[i].duCellInfo.cellInfo.plmn[j].mnc[0] = PLMN_MNC0;
 -       duCfgParam.srvdCellLst[i].duCellInfo.cellInfo.plmn[j].mnc[1] = PLMN_MNC1;
 +         /* As per spec 38.473, Plmn identity consists of 3 digit from mcc
 +          * followed by either 2 digit or 3 digits of mnc */ 
 +
 +         memset(&duCfgParam.srvdCellLst[srvdCellIdx].duCellInfo.cellInfo.srvdPlmn[srvdPlmnIdx].plmn, 0,\
 +         sizeof(Plmn));
 +         duCfgParam.srvdCellLst[srvdCellIdx].duCellInfo.cellInfo.srvdPlmn[srvdPlmnIdx].plmn.mcc[0] = PLMN_MCC0;
 +         duCfgParam.srvdCellLst[srvdCellIdx].duCellInfo.cellInfo.srvdPlmn[srvdPlmnIdx].plmn.mcc[1] = PLMN_MCC1;
 +         duCfgParam.srvdCellLst[srvdCellIdx].duCellInfo.cellInfo.srvdPlmn[srvdPlmnIdx].plmn.mcc[2] = PLMN_MCC2;
 +         duCfgParam.srvdCellLst[srvdCellIdx].duCellInfo.cellInfo.srvdPlmn[srvdPlmnIdx].plmn.mnc[0] = PLMN_MNC0;
 +         duCfgParam.srvdCellLst[srvdCellIdx].duCellInfo.cellInfo.srvdPlmn[srvdPlmnIdx].plmn.mnc[1] = PLMN_MNC1;
        }
        /* List of Extended PLMN */
 -      for(j=0;j<MAX_PLMN;j++)
 +      for(srvdPlmnIdx=0; srvdPlmnIdx<MAX_PLMN; srvdPlmnIdx++)
        {
 -       memset(&duCfgParam.srvdCellLst[i].duCellInfo.cellInfo.extPlmn[j], 0, sizeof(Plmn));
 -       duCfgParam.srvdCellLst[i].duCellInfo.cellInfo.extPlmn[j].mcc[0] = PLMN_MCC0;
 -       duCfgParam.srvdCellLst[i].duCellInfo.cellInfo.extPlmn[j].mcc[1] = PLMN_MCC1;
 -       duCfgParam.srvdCellLst[i].duCellInfo.cellInfo.extPlmn[j].mcc[2] = PLMN_MCC2;
 -       duCfgParam.srvdCellLst[i].duCellInfo.cellInfo.extPlmn[j].mnc[0] = PLMN_MNC0;
 -       duCfgParam.srvdCellLst[i].duCellInfo.cellInfo.extPlmn[j].mnc[1] = PLMN_MNC1;
 +         /* As per spec 38.473, Plmn identity consists of 3 digit from mcc
 +          * followed by either 2 digit or 3 digits of mnc */ 
 +
 +         memset(&duCfgParam.srvdCellLst[srvdCellIdx].duCellInfo.cellInfo.srvdPlmn[srvdPlmnIdx].extPlmn, 0, sizeof(Plmn));
 +         duCfgParam.srvdCellLst[srvdCellIdx].duCellInfo.cellInfo.srvdPlmn[srvdPlmnIdx].extPlmn.mcc[0] = PLMN_MCC0;
 +         duCfgParam.srvdCellLst[srvdCellIdx].duCellInfo.cellInfo.srvdPlmn[srvdPlmnIdx].extPlmn.mcc[1] = PLMN_MCC1;
 +         duCfgParam.srvdCellLst[srvdCellIdx].duCellInfo.cellInfo.srvdPlmn[srvdPlmnIdx].extPlmn.mcc[2] = PLMN_MCC2;
 +         duCfgParam.srvdCellLst[srvdCellIdx].duCellInfo.cellInfo.srvdPlmn[srvdPlmnIdx].extPlmn.mnc[0] = PLMN_MNC0;
 +         duCfgParam.srvdCellLst[srvdCellIdx].duCellInfo.cellInfo.srvdPlmn[srvdPlmnIdx].extPlmn.mnc[1] = PLMN_MNC1;
        } 
 -
 +      /* List of Supporting Slices */
 +      for(srvdPlmnIdx=0; srvdPlmnIdx<MAX_PLMN; srvdPlmnIdx++)
 +      {
 +         taiSliceSuppLst = &duCfgParam.srvdCellLst[srvdCellIdx].duCellInfo.cellInfo.srvdPlmn[srvdPlmnIdx].taiSliceSuppLst;
 +
 +         taiSliceSuppLst->pres = true;
 +         taiSliceSuppLst->numSupportedSlices = NUM_OF_SUPPORTED_SLICE;
 +
 +         memset(&taiSliceSuppLst->snssai, 0, sizeof(F1Snsaai));
 +         for(sliceIdx=0; sliceIdx<NUM_OF_SUPPORTED_SLICE; sliceIdx++)
 +         {
 +            DU_ALLOC(taiSliceSuppLst->snssai[sliceIdx], sizeof(F1Snsaai));
 +            if(taiSliceSuppLst->snssai[sliceIdx] == NULLP)
 +            {
 +               DU_LOG("\nERROR --> DU_APP: readCfg():Memory allocation failed");
 +               return RFAILED;
 +            }
 +            memcpy(taiSliceSuppLst->snssai[sliceIdx], &snsaai[sliceIdx], sizeof(F1Snsaai));
 +            
 +            /* Checking rrmPolicy Slice list available or not */
 +            if(!memcmp(&snsaai[sliceIdx], &memberList.snsaai, sizeof(F1Snsaai)))
 +            {
 +               rrmPolicy = &duCfgParam.srvdCellLst[srvdCellIdx].duCellInfo.cellInfo.srvdPlmn[srvdPlmnIdx].rrmPolicy;
 +               rrmPolicy->present = true;
 +               rrmPolicy->rsrcType = rsrcType; 
 +               rrmPolicy->memberList.snsaai = memberList.snsaai;
 +               rrmPolicy->rrmPolicyRatio = policyRatio;
 +            }
 +         }
 +      }
        /* TAC and EPSTAC */
 -      duCfgParam.srvdCellLst[i].duCellInfo.tac = DU_TAC;
 -      duCfgParam.srvdCellLst[i].duCellInfo.epsTac = DU_TAC; //to check and fill
 +      duCfgParam.srvdCellLst[srvdCellIdx].duCellInfo.tac = DU_TAC;
 +      duCfgParam.srvdCellLst[srvdCellIdx].duCellInfo.epsTac = DU_TAC; //to check and fill
        /* NR Mode info */
 -      duCfgParam.srvdCellLst[i].duCellInfo.f1Mode.mode.fdd.ulNrFreqInfo.nrArfcn = NR_UL_ARFCN;
 -      duCfgParam.srvdCellLst[i].duCellInfo.f1Mode.mode.fdd.ulNrFreqInfo.sulInfo.sulArfcn = SUL_ARFCN;
 -      duCfgParam.srvdCellLst[i].duCellInfo.f1Mode.mode.fdd.ulNrFreqInfo.sulInfo.sulTxBw.nrScs = SCS_15;
 -      duCfgParam.srvdCellLst[i].duCellInfo.f1Mode.mode.fdd.ulNrFreqInfo.sulInfo.sulTxBw.nrb = NRB_106;
 +      duCfgParam.srvdCellLst[srvdCellIdx].duCellInfo.f1Mode.mode.fdd.ulNrFreqInfo.nrArfcn = NR_UL_ARFCN;
 +      duCfgParam.srvdCellLst[srvdCellIdx].duCellInfo.f1Mode.mode.fdd.ulNrFreqInfo.sulInfo.sulArfcn = SUL_ARFCN;
 +      duCfgParam.srvdCellLst[srvdCellIdx].duCellInfo.f1Mode.mode.fdd.ulNrFreqInfo.sulInfo.sulTxBw.nrScs = SCS_15;
 +      duCfgParam.srvdCellLst[srvdCellIdx].duCellInfo.f1Mode.mode.fdd.ulNrFreqInfo.sulInfo.sulTxBw.nrb = NRB_106;
  
  #if 0
        /* NR Mode info */
 -      duCfgParam.srvdCellLst[i].duCellInfo.f1Mode.mode.tdd.nrFreqInfo.nrArfcn = NR_ARFCN;
 -      duCfgParam.srvdCellLst[i].duCellInfo.f1Mode.mode.tdd.nrFreqInfo.sulInfo.sulArfcn = SUL_ARFCN;
 -      duCfgParam.srvdCellLst[i].duCellInfo.f1Mode.mode.tdd.nrFreqInfo.sulInfo.sulTxBw.nrScs = SCS_15;                 
 -      duCfgParam.srvdCellLst[i].duCellInfo.f1Mode.mode.tdd.nrFreqInfo.sulInfo.sulTxBw.nrb = NRB_106;         
 +      duCfgParam.srvdCellLst[srvdCellIdx].duCellInfo.f1Mode.mode.tdd.nrFreqInfo.nrArfcn = NR_ARFCN;
 +      duCfgParam.srvdCellLst[srvdCellIdx].duCellInfo.f1Mode.mode.tdd.nrFreqInfo.sulInfo.sulArfcn = SUL_ARFCN;
 +      duCfgParam.srvdCellLst[srvdCellIdx].duCellInfo.f1Mode.mode.tdd.nrFreqInfo.sulInfo.sulTxBw.nrScs = SCS_15;               
 +      duCfgParam.srvdCellLst[srvdCellIdx].duCellInfo.f1Mode.mode.tdd.nrFreqInfo.sulInfo.sulTxBw.nrb = NRB_106;               
  
 -      for(j=0;j<MAXNRCELLBANDS;j++)
 +      for(freqBandIdx=0; freqBandIdx<MAX_NRCELL_BANDS; freqBandIdx++)
        {
 -       duCfgParam.srvdCellLst[i].duCellInfo.f1Mode.mode.tdd.nrFreqInfo.freqBand[j].nrFreqBand = NR_FREQ_BAND;
 -       for(k=0;k<MAXNRCELLBANDS;k++)
 -       {
 -          duCfgParam.srvdCellLst[i].duCellInfo.f1Mode.mode.tdd.nrFreqInfo.freqBand[j].sulBand[k] = SUL_BAND;  
 -       }
 +         duCfgParam.srvdCellLst[srvdCellIdx].duCellInfo.f1Mode.mode.tdd.nrFreqInfo.freqBand[freqBandIdx].nrFreqBand =\
 +         NR_FREQ_BAND;
 +         for(bandIdx=0; bandIdx<MAX_NRCELL_BANDS; bandIdx++)
 +         {
 +            duCfgParam.srvdCellLst[srvdCellIdx].duCellInfo.f1Mode.mode.tdd.nrFreqInfo.freqBand[freqBandIdx].sulBand[bandIdx]\
 +            = SUL_BAND;       
 +         }
        }
  #endif
 -      for(j=0;j<MAXNRCELLBANDS;j++)
 +      for(freqBandIdx=0; freqBandIdx<MAX_NRCELL_BANDS; freqBandIdx++)
        {
 -       duCfgParam.srvdCellLst[i].duCellInfo.f1Mode.mode.fdd.ulNrFreqInfo.freqBand[j].nrFreqBand = NR_FREQ_BAND;
 -       for(k=0;k<MAXNRCELLBANDS;k++)
 -       {
 -          duCfgParam.srvdCellLst[i].duCellInfo.f1Mode.mode.fdd.ulNrFreqInfo.freqBand[j].sulBand[k] = SUL_BAND;
 -       }
 +         duCfgParam.srvdCellLst[srvdCellIdx].duCellInfo.f1Mode.mode.fdd.ulNrFreqInfo.freqBand[freqBandIdx].\
 +         nrFreqBand = NR_FREQ_BAND;
 +         for(bandIdx=0; bandIdx<MAX_NRCELL_BANDS; bandIdx++)
 +         {
 +            duCfgParam.srvdCellLst[srvdCellIdx].duCellInfo.f1Mode.mode.fdd.ulNrFreqInfo.freqBand[freqBandIdx].\
 +            sulBand[bandIdx] = SUL_BAND;
 +         }
        }
 -      duCfgParam.srvdCellLst[i].duCellInfo.f1Mode.mode.fdd.dlNrFreqInfo.nrArfcn = NR_DL_ARFCN;
 -      duCfgParam.srvdCellLst[i].duCellInfo.f1Mode.mode.fdd.dlNrFreqInfo.sulInfo.sulArfcn = SUL_ARFCN;
 -      duCfgParam.srvdCellLst[i].duCellInfo.f1Mode.mode.fdd.dlNrFreqInfo.sulInfo.sulTxBw.nrScs = SCS_15;
 -      duCfgParam.srvdCellLst[i].duCellInfo.f1Mode.mode.fdd.dlNrFreqInfo.sulInfo.sulTxBw.nrb = NRB_106;
 -      for(j=0;j<MAXNRCELLBANDS;j++)
 +      duCfgParam.srvdCellLst[srvdCellIdx].duCellInfo.f1Mode.mode.fdd.dlNrFreqInfo.nrArfcn = NR_DL_ARFCN;
 +      duCfgParam.srvdCellLst[srvdCellIdx].duCellInfo.f1Mode.mode.fdd.dlNrFreqInfo.sulInfo.sulArfcn = SUL_ARFCN;
 +      duCfgParam.srvdCellLst[srvdCellIdx].duCellInfo.f1Mode.mode.fdd.dlNrFreqInfo.sulInfo.sulTxBw.nrScs = SCS_15;
 +      duCfgParam.srvdCellLst[srvdCellIdx].duCellInfo.f1Mode.mode.fdd.dlNrFreqInfo.sulInfo.sulTxBw.nrb = NRB_106;
 +      for(freqBandIdx=0; freqBandIdx<MAX_NRCELL_BANDS; freqBandIdx++)
        {
 -       duCfgParam.srvdCellLst[i].duCellInfo.f1Mode.mode.fdd.dlNrFreqInfo.freqBand[j].nrFreqBand = NR_FREQ_BAND;
 -       for(k=0;k<MAXNRCELLBANDS;k++)
 -       {
 -          duCfgParam.srvdCellLst[i].duCellInfo.f1Mode.mode.fdd.dlNrFreqInfo.freqBand[j].sulBand[k] = SUL_BAND;
 -       }
 +         duCfgParam.srvdCellLst[srvdCellIdx].duCellInfo.f1Mode.mode.fdd.dlNrFreqInfo.freqBand[freqBandIdx].\
 +         nrFreqBand = NR_FREQ_BAND;
 +         for(bandIdx=0; bandIdx<MAX_NRCELL_BANDS; bandIdx++)
 +         {
 +            duCfgParam.srvdCellLst[srvdCellIdx].duCellInfo.f1Mode.mode.fdd.dlNrFreqInfo.freqBand[freqBandIdx].\
 +            sulBand[bandIdx] = SUL_BAND;
 +         }
        }
  
 -      duCfgParam.srvdCellLst[i].duCellInfo.f1Mode.mode.fdd.ulTxBw.nrScs = SCS_15;
 -      duCfgParam.srvdCellLst[i].duCellInfo.f1Mode.mode.fdd.ulTxBw.nrb = NRB_106;
 +      duCfgParam.srvdCellLst[srvdCellIdx].duCellInfo.f1Mode.mode.fdd.ulTxBw.nrScs = SCS_15;
 +      duCfgParam.srvdCellLst[srvdCellIdx].duCellInfo.f1Mode.mode.fdd.ulTxBw.nrb = NRB_106;
  
 -      duCfgParam.srvdCellLst[i].duCellInfo.f1Mode.mode.fdd.dlTxBw.nrScs = SCS_15;
 -      duCfgParam.srvdCellLst[i].duCellInfo.f1Mode.mode.fdd.dlTxBw.nrb = NRB_106;
 +      duCfgParam.srvdCellLst[srvdCellIdx].duCellInfo.f1Mode.mode.fdd.dlTxBw.nrScs = SCS_15;
 +      duCfgParam.srvdCellLst[srvdCellIdx].duCellInfo.f1Mode.mode.fdd.dlTxBw.nrb = NRB_106;
  
 -#if 0
 -      duCfgParam.srvdCellLst[i].duCellInfo.f1Mode.mode.tdd.nrTxBw.nrScs = SCS_15;
 -      duCfgParam.srvdCellLst[i].duCellInfo.f1Mode.mode.tdd.nrTxBw.nrb = NRB_106;
 -#endif
        /*Measurement Config and Cell Config */ 
 -      duCfgParam.srvdCellLst[i].duCellInfo.measTimeCfg = TIME_CFG; 
 +      duCfgParam.srvdCellLst[srvdCellIdx].duCellInfo.measTimeCfg = TIME_CFG; 
  
 -      duCfgParam.srvdCellLst[i].duCellInfo.cellDir = DL_UL; 
 +      duCfgParam.srvdCellLst[srvdCellIdx].duCellInfo.cellDir = DL_UL; 
  
 -      duCfgParam.srvdCellLst[i].duCellInfo.cellType=CELL_TYPE;
 +      duCfgParam.srvdCellLst[srvdCellIdx].duCellInfo.cellType=CELL_TYPE;
  
        /* Broadcast PLMN Identity */
 -      for(j=0;j<MAXBPLMNNRMINUS1;j++)
 +      for(brdcstPlmnIdx=0; brdcstPlmnIdx<MAX_BPLMN_NRCELL_MINUS_1; brdcstPlmnIdx++)
        { 
 -       for(k=0;k<MAX_PLMN;k++)
 -       {
 -          memset(&duCfgParam.srvdCellLst[i].duCellInfo.brdcstPlmnInfo[j].plmn[k], 0, sizeof(Plmn));
 -          duCfgParam.srvdCellLst[i].duCellInfo.brdcstPlmnInfo[j].plmn[k].mcc[0] = PLMN_MCC0;
 -          duCfgParam.srvdCellLst[i].duCellInfo.brdcstPlmnInfo[j].plmn[k].mcc[1] = PLMN_MCC1;
 -          duCfgParam.srvdCellLst[i].duCellInfo.brdcstPlmnInfo[j].plmn[k].mcc[2] = PLMN_MCC2;
 -          duCfgParam.srvdCellLst[i].duCellInfo.brdcstPlmnInfo[j].plmn[k].mnc[0] = PLMN_MNC0;
 -          duCfgParam.srvdCellLst[i].duCellInfo.brdcstPlmnInfo[j].plmn[k].mnc[1] = PLMN_MNC1;                                         
 -       }
 -       /* Extended PLMN List */        
 -       for(k=0;k<MAX_PLMN;k++)
 -       {
 -          memset(&duCfgParam.srvdCellLst[i].duCellInfo.brdcstPlmnInfo[j].extPlmn[k], 0, sizeof(Plmn));
 -          duCfgParam.srvdCellLst[i].duCellInfo.brdcstPlmnInfo[j].extPlmn[k].mcc[0] = PLMN_MCC0;
 -          duCfgParam.srvdCellLst[i].duCellInfo.brdcstPlmnInfo[j].extPlmn[k].mcc[1] = PLMN_MCC1;
 -          duCfgParam.srvdCellLst[i].duCellInfo.brdcstPlmnInfo[j].extPlmn[k].mcc[2] = PLMN_MCC2;
 -          duCfgParam.srvdCellLst[i].duCellInfo.brdcstPlmnInfo[j].extPlmn[k].mnc[0] = PLMN_MNC0;
 -          duCfgParam.srvdCellLst[i].duCellInfo.brdcstPlmnInfo[j].extPlmn[k].mnc[1] = PLMN_MNC1;
 -       }
 -
 -       duCfgParam.srvdCellLst[i].duCellInfo.brdcstPlmnInfo[j].tac = DU_TAC;
 -       duCfgParam.srvdCellLst[i].duCellInfo.brdcstPlmnInfo[j].nrCellId = NR_CELL_ID;
 -       duCfgParam.srvdCellLst[i].duCellInfo.brdcstPlmnInfo[j].ranac = NR_RANAC;
 +         for(plmnIdx=0; plmnIdx<MAX_PLMN; plmnIdx++)
 +         {
 +            memset(&duCfgParam.srvdCellLst[srvdCellIdx].duCellInfo.brdcstPlmnInfo[brdcstPlmnIdx].plmn[plmnIdx],\
 +            0, sizeof(Plmn));
 +            duCfgParam.srvdCellLst[srvdCellIdx].duCellInfo.brdcstPlmnInfo[brdcstPlmnIdx].plmn[plmnIdx].mcc[0] =\
 +            PLMN_MCC0;
 +            duCfgParam.srvdCellLst[srvdCellIdx].duCellInfo.brdcstPlmnInfo[brdcstPlmnIdx].plmn[plmnIdx].mcc[1] =\
 +            PLMN_MCC1;
 +            duCfgParam.srvdCellLst[srvdCellIdx].duCellInfo.brdcstPlmnInfo[brdcstPlmnIdx].plmn[plmnIdx].mcc[2] =\
 +            PLMN_MCC2;
 +            duCfgParam.srvdCellLst[srvdCellIdx].duCellInfo.brdcstPlmnInfo[brdcstPlmnIdx].plmn[plmnIdx].mnc[0] =\
 +            PLMN_MNC0;
 +            duCfgParam.srvdCellLst[srvdCellIdx].duCellInfo.brdcstPlmnInfo[brdcstPlmnIdx].plmn[plmnIdx].mnc[1] =\
 +            PLMN_MNC1;
 +         }
 +         /* Extended PLMN List */      
 +         for(plmnIdx=0; plmnIdx<MAX_PLMN; plmnIdx++)
 +         {
 +            memset(&duCfgParam.srvdCellLst[srvdCellIdx].duCellInfo.brdcstPlmnInfo[brdcstPlmnIdx].\
 +            extPlmn[plmnIdx], 0, sizeof(Plmn));
 +            duCfgParam.srvdCellLst[srvdCellIdx].duCellInfo.brdcstPlmnInfo[brdcstPlmnIdx].\
 +            extPlmn[plmnIdx].mcc[0] = PLMN_MCC0;
 +            duCfgParam.srvdCellLst[srvdCellIdx].duCellInfo.brdcstPlmnInfo[brdcstPlmnIdx].\
 +            extPlmn[plmnIdx].mcc[1] = PLMN_MCC1;
 +            duCfgParam.srvdCellLst[srvdCellIdx].duCellInfo.brdcstPlmnInfo[brdcstPlmnIdx].\
 +            extPlmn[plmnIdx].mcc[2] = PLMN_MCC2;
 +            duCfgParam.srvdCellLst[srvdCellIdx].duCellInfo.brdcstPlmnInfo[brdcstPlmnIdx].\
 +            extPlmn[plmnIdx].mnc[0] = PLMN_MNC0;
 +            duCfgParam.srvdCellLst[srvdCellIdx].duCellInfo.brdcstPlmnInfo[brdcstPlmnIdx].\
 +            extPlmn[plmnIdx].mnc[1] = PLMN_MNC1;
 +         }
 +
 +         duCfgParam.srvdCellLst[srvdCellIdx].duCellInfo.brdcstPlmnInfo[brdcstPlmnIdx].tac = DU_TAC;
 +         duCfgParam.srvdCellLst[srvdCellIdx].duCellInfo.brdcstPlmnInfo[brdcstPlmnIdx].nrCellId = NR_CELL_ID;
 +         duCfgParam.srvdCellLst[srvdCellIdx].duCellInfo.brdcstPlmnInfo[brdcstPlmnIdx].ranac = NR_RANAC;
        }
  
        /*gnb DU System Info mib msg*/
        BuildMibMsg();
 -      DU_ALLOC(duCfgParam.srvdCellLst[i].duSysInfo.mibMsg, encBufSize);
 -      if(!(duCfgParam.srvdCellLst[i].duSysInfo.mibMsg))
 +      DU_ALLOC(duCfgParam.srvdCellLst[srvdCellIdx].duSysInfo.mibMsg, encBufSize);
 +      if(!(duCfgParam.srvdCellLst[srvdCellIdx].duSysInfo.mibMsg))
        {
 -       DU_LOG("\nERROR  -->  DU APP : Memory allocation failure at readCfg");
 -       return RFAILED;
 +         DU_LOG("\nERROR  -->  DU APP : Memory allocation failure at readCfg");
 +         return RFAILED;
        }
 -      memcpy(duCfgParam.srvdCellLst[i].duSysInfo.mibMsg, encBuf, encBufSize);
 -      duCfgParam.srvdCellLst[i].duSysInfo.mibLen = encBufSize;
 +      memcpy(duCfgParam.srvdCellLst[srvdCellIdx].duSysInfo.mibMsg, encBuf, encBufSize);
 +      duCfgParam.srvdCellLst[srvdCellIdx].duSysInfo.mibLen = encBufSize;
  
        /*gnb DU System Info mib msg*/
        BuildSib1Msg();
 -      DU_ALLOC(duCfgParam.srvdCellLst[i].duSysInfo.sib1Msg,\
 -          encBufSize);
 -      if(!(duCfgParam.srvdCellLst[i].duSysInfo.sib1Msg))
 +      DU_ALLOC(duCfgParam.srvdCellLst[srvdCellIdx].duSysInfo.sib1Msg,\
 +            encBufSize);
 +      if(!(duCfgParam.srvdCellLst[srvdCellIdx].duSysInfo.sib1Msg))
        {
 -       DU_LOG("\nERROR  -->  DU APP : Memory allocation failure at readCfg");
 -       return RFAILED;
 +         DU_LOG("\nERROR  -->  DU APP : Memory allocation failure at readCfg");
 +         return RFAILED;
        }
 -      memcpy(duCfgParam.srvdCellLst[i].duSysInfo.sib1Msg,\
 -          encBuf,encBufSize);
 -      duCfgParam.srvdCellLst[i].duSysInfo.sib1Len = encBufSize;
 +      memcpy(duCfgParam.srvdCellLst[srvdCellIdx].duSysInfo.sib1Msg,\
 +            encBuf,encBufSize);
 +      duCfgParam.srvdCellLst[srvdCellIdx].duSysInfo.sib1Len = encBufSize;
  
     }
  
@@@ -933,7 -877,6 +935,7 @@@ uint8_t duReadCfg(
     Buffer *mBuf;
  
     memset(&duCfgParam, 0, sizeof(DuCfgParams));
 +
     //Read configs into duCfgParams
     if(readCfg() != ROK)
     {
diff --combined src/du_app/du_cfg.h
  
  #define RSS_MEASUREMENT_UNIT DONT_REPORT_RSSI
  #define RA_CONT_RES_TIMER 64
- #define RA_RSP_WINDOW 180
+ #define RA_RSP_WINDOW 10
  #define PRACH_RESTRICTED_SET 0 /* Unrestricted */
  #define ROOT_SEQ_LEN 139
  
  #define MAX_F1_CONNECTIONS 65536    /* Max num of F1 connections */
  #define MAX_PLMN           1        /* Max num of broadcast PLMN ids */
  #define MAXNRARFCN         3279165  /* Maximum values of NRAFCN */
 -#define MAXNRCELLBANDS     2       /* Maximum number of frequency bands */
 +#define MAX_NRCELL_BANDS   2       /* Maximum number of frequency bands */
  #define MAX_NUM_OF_SLICE_ITEMS 1024     /* Maximum number of signalled slice support items */
 -#define MAXBPLMNNRMINUS1   1       /* Maximum number of PLMN Ids broadcast in an NR cell minus 1 */
 +#define MAX_BPLMN_NRCELL_MINUS_1   1       /* Maximum number of PLMN Ids broadcast in an NR cell minus 1 */
  #define MAXNUMOFSIBTYPES   32       /* Maximum number of SIB types */
  #define MAX_TNL_ASSOC      32       /* Max num of TNL Assoc between CU and DU */
  #define MAXCELLINENB       256      /* Max num of cells served by eNB */
  #define MAXNUMOFUACPERPLMN 64       /* Maximum number of signalled categories per PLMN */
  #define NR_RANAC           150      /* RANAC */
  #define DEFAULT_CELLS      1        /* Max num of broadcast PLMN ids */
 -
 +#define NUM_OF_SUPPORTED_SLICE  2
 +#define DEDICATED_SLICE_INDEX   1 
 +#define IE_EXTENSION_LIST_COUNT 1
  
  /* Macro definitions for MIB/SIB1 */
  #define SYS_FRAME_NUM 0
  #define PDSCH_MCS_INDEX 20  /* For 64QAM, valid mcs index: 17-28 in 38.214  - Table 5.1.3.1-1*/
  #define PUSCH_MCS_INDEX 10  /* For 16QAM, valid mcs index: 10-16 in 38.214  - Table 5.1.3.1-1*/
  
 +/*VALID Tunnel ID*/
 +#define MIN_TEID 1   /*[Spec 29.281,Sec 5.1]: All Zero TEIDs are never assigned for setting up GTP-U Tunnel*/
 +#define MAX_TEID 10 /*[Spec 29.281]: Max limit is not mentioned but as per GTP-U Header Format, TEID occupies 4 octets */
  typedef enum
  {
     GNBDU,
@@@ -496,12 -491,6 +496,12 @@@ typedef enu
     PUSCH_MAPPING_TYPE_B,
  }puschMappingType;
  
 +typedef enum
 +{
 +   PRB,
 +   DRB,
 +   RRC_CONNECTED_USERS
 +}ResourceType;
  
  typedef struct f1RrcVersion
  {
@@@ -606,14 -595,14 +606,14 @@@ typedef struct f1SulInf
  typedef struct f1FreqBand
  {
     uint16_t   nrFreqBand;
 -   uint16_t   sulBand[MAXNRCELLBANDS];
 +   uint16_t   sulBand[MAX_NRCELL_BANDS];
  }F1FreqBand;
  
  typedef struct f1NrFreqInfo
  {
     uint32_t        nrArfcn;
     F1SulInfo  sulInfo;
 -   F1FreqBand freqBand[MAXNRCELLBANDS];
 +   F1FreqBand freqBand[MAX_NRCELL_BANDS];
  }F1NrFreqInfo;
  
  typedef struct f1NrFddInfo
@@@ -662,7 -651,7 +662,7 @@@ typedef struct f1EutraModeInf
  typedef struct f1Snsaai
  {
     uint8_t   sst;
 -   uint32_t  sd;
 +   uint8_t   sd[SD_SIZE];
  }F1Snsaai;
  
  typedef struct epIpAddr
@@@ -676,40 -665,16 +676,40 @@@ typedef struct epIpAddrPor
     char   port[2];
  }EpIpAddrPort;
  
 +typedef struct policyMemberList
 +{
 +   Plmn   plmn;
 +   F1Snsaai snsaai;   
 +}PolicyMemberList;
 +
 +typedef struct rrmPolicyRatio
 +{
 +   uint8_t policyMaxRatio;
 +   uint8_t policyMinRatio;
 +   uint8_t policyDedicatedRatio;
 +}RrmPolicyRatio;
 +
 +typedef struct rrmPolicy
 +{
 +   bool present;
 +   ResourceType     rsrcType;
 +   PolicyMemberList memberList;
 +   RrmPolicyRatio   rrmPolicyRatio;
 +}RrmPolicy;
 +
  typedef struct f1TaiSliceSuppLst
  {
     bool       pres;
 -   F1Snsaai   snssai[MAX_NUM_OF_SLICE_ITEMS];   
 +   uint8_t    numSupportedSlices;
 +   F1Snsaai   *snssai[MAX_NUM_OF_SLICE_ITEMS];   
  }F1TaiSliceSuppLst;
  
  typedef struct f1SrvdPlmn
  {
 -   Plmn              plmn;
 -   F1TaiSliceSuppLst   taiSliceSuppLst;
 +   Plmn   plmn;
 +   Plmn   extPlmn;    /* Extended available PLMN list */
 +   F1TaiSliceSuppLst taiSliceSuppLst;
 +   RrmPolicy  rrmPolicy;
  }F1SrvdPlmn;
  
  typedef struct f1BrdcstPlmnInfo
@@@ -725,7 -690,8 +725,7 @@@ typedef struct f1CellInf
  {
     NrEcgi   nrCgi;                   /* Cell global Identity */
     uint32_t nrPci;                   /* Physical Cell Identity */
 -   Plmn   plmn[MAX_PLMN];     /* Available PLMN list */
 -   Plmn   extPlmn[MAX_PLMN];  /* Extended available PLMN list */
 +   F1SrvdPlmn srvdPlmn[MAX_PLMN];
  }F1CellInfo;
  
  typedef struct f1DuCellInfo
     uint8_t            measTimeCfg;  /* Measurement timing configuration */
     F1CellDir          cellDir;      /* Cell Direction */
     F1CellType         cellType;     /* Cell Type */
 -   F1BrdcstPlmnInfo   brdcstPlmnInfo[MAXBPLMNNRMINUS1]; /* Broadcast PLMN Identity Info List */
 +   F1BrdcstPlmnInfo   brdcstPlmnInfo[MAX_BPLMN_NRCELL_MINUS_1]; /* Broadcast PLMN Identity Info List */
  }F1DuCellInfo;
  
  typedef struct f1DuSysInfo