1 /*******************************************************************************
2 ################################################################################
3 # Copyright (c) [2017-2019] [Radisys] #
5 # Licensed under the Apache License, Version 2.0 (the "License"); #
6 # you may not use this file except in compliance with the License. #
7 # You may obtain a copy of the License at #
9 # http://www.apache.org/licenses/LICENSE-2.0 #
11 # Unless required by applicable law or agreed to in writing, software #
12 # distributed under the License is distributed on an "AS IS" BASIS, #
13 # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. #
14 # See the License for the specific language governing permissions and #
15 # limitations under the License. #
16 ################################################################################
17 *******************************************************************************/
19 /**********************************************************************
25 Desc: Defines required by LTE MAC
29 **********************************************************************/
30 static const char* RLOG_MODULE_NAME="UDX";
31 static int RLOG_MODULE_ID=262144;
32 static int RLOG_FILE_ID=203;
34 /* header include files (.h) */
35 #include "envopt.h" /* environment options */
36 #include "envdep.h" /* environment dependent */
37 #include "envind.h" /* environment independent */
39 #include "gen.h" /* general */
40 #include "ssi.h" /* system services */
41 #include "cm5.h" /* common timer defines */
42 #include "cm_tkns.h" /* common tokens defines */
43 #include "cm_mblk.h" /* common memory allocation library defines */
44 #include "cm_llist.h" /* common link list defines */
45 #include "cm_hash.h" /* common hash list defines */
46 #include "cm_lte.h" /* common LTE defines */
47 #include "lkw.h" /* LKW defines */
48 #include "ckw.h" /* CKW defines */
49 #include "kwu.h" /* KWU defines */
50 #include "rgu.h" /* RGU defines */
51 #include "kw_err.h" /* Err defines */
52 #include "kw_env.h" /* RLC environment options */
54 #include "kw.h" /* RLC defines */
58 /* extern (.x) include files */
59 #include "gen.x" /* general */
60 #include "ssi.x" /* system services */
62 #include "cm5.x" /* common timer library */
63 #include "cm_tkns.x" /* common tokens */
64 #include "cm_mblk.x" /* common memory allocation */
65 #include "cm_llist.x" /* common link list */
66 #include "cm_hash.x" /* common hash list */
67 #include "cm_lte.x" /* common LTE includes */
68 #include "cm_lib.x" /* common memory allocation library */
69 #include "lkw.x" /* LKW */
70 #include "ckw.x" /* CKW */
71 #include "kwu.x" /* KWU */
72 #include "rgu.x" /* RGU */
79 #define KW_MODULE KW_DBGMASK_UDX
82 EXTERN S16 kwDlmHndlStaRsp ARGS (( KwCb *gCb,KwDlRbCb *rbCb,
83 KwUdxStaPdu *pStaPdu, KwUdxBufLst *rlsPduLst));
96 * Handler to bind the DL with UL.
98 * @param[in] pst Post structure
99 * @param[in] suId Service user SAP ID
100 * @param[in] spId Service provider ID
107 PUBLIC S16 KwDlUdxBndReq
114 PUBLIC S16 KwDlUdxBndReq (pst, suId, spId)
120 KwUdxDlSapCb *udxSap; /* pointer to session SAP */
125 #if (ERRCLASS & ERRCLS_INT_PAR)
126 if (pst->dstInst >= KW_MAX_RLC_INSTANCES)
131 tKwCb = KW_GET_KWCB(pst->dstInst);
133 KWDBGP_BRIEF(tKwCb, "KwDlUdxBndReq(spId(%d), suId(%d))\n",
136 udxSap = (tKwCb->u.dlCb->udxDlSap + spId);
138 /* Verify CKW SAP State */
139 switch(udxSap->state)
141 /* SAP is configured but not bound */
145 /* copy bind configuration parameters in SSAP sap */
147 udxSap->pst.dstProcId = pst->srcProcId;
148 udxSap->pst.dstEnt = pst->srcEnt;
149 udxSap->pst.dstInst = pst->srcInst;
151 /* Update the State */
152 udxSap->state = KW_SAP_BND;
154 RLOG1(L_INFO, "UDX SAP state [%d]", udxSap->state);
157 /* SAP is already bound */
161 * Sap is already bound check source, destination Entity and
164 if (udxSap->pst.dstProcId != pst->srcProcId
165 || udxSap->pst.dstEnt != pst->srcEnt
166 || udxSap->pst.dstInst != pst->srcInst
167 || udxSap->suId != suId)
169 KW_SEND_SAPID_ALARM(tKwCb, spId,
170 LKW_EVENT_UDX_BND_REQ, LCM_CAUSE_INV_PAR_VAL);
172 RLOG0(L_ERROR, "UDX SAP already Bound");
173 KwDlUdxBndCfm(&(udxSap->pst), udxSap->suId, CM_BND_NOK);
180 #if (ERRCLASS & ERRCLS_INT_PAR)
181 KW_SEND_SAPID_ALARM(tKwCb,spId,
182 LKW_EVENT_CKW_BND_REQ, LCM_CAUSE_INV_STATE);
183 #endif /* ERRCLASS & ERRCLS_INT_PAR */
184 RLOG0(L_ERROR, "Invalid UDX SAP State in Bind Req");
185 KwDlUdxBndCfm(&(udxSap->pst), udxSap->suId, CM_BND_NOK);
189 KwDlUdxBndCfm(&(udxSap->pst), udxSap->suId, CM_BND_OK);
196 * Handler for unbinding the DL from UL.
198 * @param[in] pst Post structure
199 * @param[in] spId Service provider SAP ID
200 * @param[in] reason Reason for Unbinding
206 PUBLIC S16 KwDlUdxUbndReq
213 PUBLIC S16 KwDlUdxUbndReq(pst, spId, reason)
219 KwUdxDlSapCb *udxSap;
224 #if (ERRCLASS & ERRCLS_INT_PAR)
225 if (pst->dstInst >= KW_MAX_RLC_INSTANCES)
231 tKwCb = KW_GET_KWCB(pst->dstInst);
233 RLOG2(L_DEBUG,"Unbind Req for spId[%d], reason[%d]",
236 /* disable upper sap (CKW) */
237 udxSap = (tKwCb->u.dlCb->udxDlSap + spId);
239 #if (ERRCLASS & ERRCLS_INT_PAR)
240 KW_GET_AND_VALIDATE_UDXSAP(tKwCb,udxSap, EKW208, "KwUiDlUdxndReq");
241 #endif /* ERRCLASS & ERRCLS_INT_PAR */
242 udxSap->state = KW_SAP_CFG;
249 * Handler for configuring RLC entities.
252 * This function is used by RRC to configure(add/delete/modify)
253 * one or more RLC entities.
254 * - CKW_CFG_ADD => kwCfgAddRb
255 * - CKW_CFG_MODIFY => kwCfgReCfgRb
256 * - CKW_CFG_DELETE => kwCfgDelRb
257 * - CKW_CFG_REESTABLISH => kwCfgReEstRb
258 * - CKW_CFG_DELETE_UE => kwCfgDelUe
260 * @param[in] pst - Post structure
261 * @param[in] spId - Serive Provider ID
262 * @param[in] cfg - Configuration information for one or more RLC entities.
269 PUBLIC S16 KwDlUdxCfgReq
276 PUBLIC S16 KwDlUdxCfgReq(pst, spId, cfg)
282 CkwCfgCfmInfo *cfgCfm;
290 #if (ERRCLASS & ERRCLS_INT_PAR)
291 if (pst->dstInst >= KW_MAX_RLC_INSTANCES)
297 tKwCb = KW_GET_KWCB(pst->dstInst);
299 pstUdxCfm = &(tKwCb->u.dlCb->udxDlSap[spId].pst);
300 KWDBGP_BRIEF(tKwCb,"spId(%d)\n", spId);
301 /* Allocate memory and memset to 0 for cfmInfo */
302 KW_ALLOC_SHRABL_BUF_WC(pstUdxCfm->region,
305 sizeof(CkwCfgCfmInfo));
307 #if (ERRCLASS & ERRCLS_ADD_RES)
310 RLOG0(L_FATAL,"Memory Allocation Failed.");
311 /* kw002.201 Freeing from proper region */
312 /* KW_PST_FREE(pst->region, pst->pool, cfg, sizeof(CkwCfgInfo)); */
315 #endif /* ERRCLASS & ERRCLS_ADD_RES */
317 /* For every entity configuration process by cfgType */
318 for (idx = 0; idx < cfg->numEnt; idx++)
320 CkwEntCfgCfmInfo *entCfgCfm;
321 CkwEntCfgInfo *entCfg;
323 entCfg = (CkwEntCfgInfo *)&(cfg->entCfg[idx]);
324 entCfgCfm = (CkwEntCfgCfmInfo *)&(cfgCfm->entCfgCfm[idx]);
326 switch (entCfg->cfgType)
330 if (entCfg->dir & KW_DIR_DL)
332 /* Add a new RB entity configuration */
333 if (kwCfgAddDlRb(tKwCb,cfg->ueId, cfg->cellId,\
334 entCfg, entCfgCfm) != ROK)
336 RLOG_ARG1(L_ERROR,DBG_RBID,cfg->entCfg[idx].rbId,"Addition Failed due to[%d]",
337 entCfgCfm->status.reason);
344 if (entCfg->dir & KW_DIR_DL)
346 /* Re-configure the existing RB entity configuration */
347 if (kwCfgReCfgDlRb(tKwCb,cfg->ueId, cfg->cellId,\
348 entCfg, entCfgCfm) != ROK)
350 RLOG_ARG1(L_ERROR,DBG_RBID,cfg->entCfg[idx].rbId,"ReCfg Failed due to[%d]",
351 entCfgCfm->status.reason);
359 if (entCfg->dir & KW_DIR_DL)
361 /* Delete the existing RB entity configuration */
362 if (kwCfgDelDlRb(tKwCb,cfg->ueId, cfg->cellId,\
363 entCfg, entCfgCfm) != ROK)
365 RLOG_ARG1(L_ERROR,DBG_RBID,cfg->entCfg[idx].rbId,"Deletion Failed due to[%d]",
366 entCfgCfm->status.reason);
372 case CKW_CFG_REESTABLISH:
374 if (entCfg->dir & KW_DIR_DL)
376 /*if direction is both then, re-establishment end indication
377 * should be sent only from the UL instance, only if DIR is
378 * DL only then DL instance will send indication.*/
379 Bool sndReEst = TRUE;
380 if (entCfg->dir & KW_DIR_UL)
384 /* Re-establish the existing RB entity configuration */
385 if (kwCfgReEstDlRb(tKwCb,cfg->ueId, cfg->cellId,
386 sndReEst,entCfg, entCfgCfm) != ROK)
388 RLOG_ARG1(L_ERROR,DBG_RBID,cfg->entCfg[idx].rbId,"Reest Failed due to[%d]",
389 entCfgCfm->status.reason);
395 case CKW_CFG_DELETE_UE:
397 /* Delete all RB entity configuration under UE */
398 if (kwCfgDelDlUe(tKwCb,cfg->ueId, cfg->cellId,
399 entCfg, entCfgCfm) != ROK)
401 RLOG_ARG1(L_ERROR,DBG_UEID,cfg->ueId,"deletion Failed due to[%d]",
402 entCfgCfm->status.reason);
406 case CKW_CFG_DELETE_CELL:
408 if (kwCfgDelDlCell(tKwCb,cfg->cellId,entCfg,entCfgCfm)
411 RLOG_ARG1(L_ERROR,DBG_CELLID,cfg->cellId,"deletion Failed due to[%d]",
412 entCfgCfm->status.reason);
419 KW_CFG_FILL_CFG_CFM(entCfgCfm, entCfg->rbId, entCfg->rbType,\
420 CKW_CFG_CFM_NOK, CKW_CFG_REAS_INVALID_CFG);
421 RLOG0(L_ERROR, "Invalid CfgType");
426 /* Assign number of entity configuraitons and suId */
427 cfgCfm->transId = cfg->transId;
428 cfgCfm->ueId = cfg->ueId;
429 cfgCfm->cellId = cfg->cellId;
430 cfgCfm->numEnt = cfg->numEnt;
432 /* kw002.201 Freeing from proper region */
433 /* KW_PST_FREE(pst->region, pst->pool, cfg, sizeof(CkwCfgInfo)); */
434 /* Send Configuration confirm primitive */
435 KwDlUdxCfgCfm(&(tKwCb->u.dlCb->udxDlSap[spId].pst),
436 tKwCb->u.dlCb->udxDlSap[spId].suId,
444 * This primitive is used by RRC to change the UeId for the existing UE
447 * @param pst - Pointer to the pst structure
448 * @param spId - The ID of the service provider SAP in the RLC layer
449 * @param transId - Transaction ID. This field uniquily identifies
450 * transaction between RRC and RLC
451 * @param ueInfo - Old UE Id Info for which the change request has come
452 * @param newUeInfo - New UE Id Info for existing UE context
459 PUBLIC S16 KwDlUdxUeIdChgReq
468 PUBLIC S16 KwDlUdxUeIdChgReq(pst,spId,transId,ueInfo,newUeInfo)
473 CkwUeInfo *newUeInfo;
479 TRC3(KwDlUdxUeIdChgReq)
481 #if (ERRCLASS & ERRCLS_INT_PAR)
482 if (pst->dstInst >= KW_MAX_RLC_INSTANCES)
488 tKwCb = KW_GET_KWCB(pst->dstInst);
490 KWDBGP_BRIEF(tKwCb, "(spId(%d), transId(%ld))\n",
493 KWDBGP_BRIEF(tKwCb, "(spId(%d), transId(%d))\n",
497 status.reason = CKW_CFG_REAS_NONE;
498 status.status = CKW_CFG_CFM_OK;
500 if (kwCfgDlUeIdChng(tKwCb, ueInfo, newUeInfo, &status) != ROK)
502 RLOG_ARG1(L_ERROR,DBG_CELLID,newUeInfo->cellId,"Failure due to[%d]",
505 KwDlUdxUeIdChgCfm(&(tKwCb->u.dlCb->udxDlSap[spId].pst),
506 tKwCb->u.dlCb->udxDlSap[spId].suId,
515 * Request for status PDU from ULM to DLM.
517 * @param[in] pst - Post Structure
518 * @param[in] spId - Service Provider Id
519 * @param[in] rlcId - Rlc Information Id
520 * @param[in] pStaPdu - Status PDU
527 PUBLIC S16 KwDlUdxStaPduReq
532 KwUdxDlStaPdu *pStaPdu
535 PUBLIC S16 KwDlUdxStaPduReq(pst, spId, rlcId, pStaPdu)
539 KwUdxDlStaPdu *pStaPdu;
545 tKwCb = KW_GET_KWCB (pst->dstInst);
547 kwDbmFetchDlRbCbByRbId(tKwCb, rlcId, &rbCb); /* Fetch DBM RbCb */
550 RLOG_ARG2(L_ERROR, DBG_UEID,rlcId->ueId, "CellId [%u]:RbId[%d] not found",
551 rlcId->cellId,rlcId->rbId);
552 KW_FREE_SHRABL_BUF(pst->region,
555 sizeof(KwUdxDlStaPdu));
559 AMDL.cntrlBo = pStaPdu->controlBo;
560 /* If there already exists a STAUS PDU, free it and take the new one
564 KW_FREE_SHRABL_BUF(pst->region,
567 sizeof(KwUdxDlStaPdu));
570 AMDL.pStaPdu = pStaPdu;
571 kwAmmSendDStaRsp(tKwCb, rbCb, &AMDL);
578 * It handles the status update recieved from ULM.
580 * @param[in] pst - Post Structure
581 * @param[in] spId - Service Provider Id
582 * @param[in] rlcId - Rlc Information Id
583 * @param[in] pStaPdu - Status PDU
590 PUBLIC S16 KwDlUdxStaUpdReq
598 PUBLIC S16 KwDlUdxStaUpdReq(pst, spId, rlcId,pStaPdu)
602 KwUdxStaPdu *pStaPdu;
608 tKwCb = KW_GET_KWCB(pst->dstInst);
610 kwDbmFetchDlRbCbByRbId(tKwCb, rlcId, &rbCb);
613 RLOG_ARG2(L_ERROR, DBG_UEID,rlcId->ueId, "CellId [%u]:RbId[%d] not found",
614 rlcId->cellId,rlcId->rbId);
618 kwAmmDlHndlStatusPdu(tKwCb, rbCb, pStaPdu);
620 KW_FREE_SHRABL_BUF(pst->region,
623 sizeof(KwUdxStaPdu));
632 PUBLIC S16 KwDlUdxL2MeasReq
635 KwL2MeasReqEvt *measReqEvt
638 PUBLIC S16 KwDlUdxL2MeasReq (pst, measReqEvt)
640 KwL2MeasReqEvt *measReqEvt;
645 VOLATILE U32 startTime = 0;
648 TRC3(KwDlUdxL2MeasReq);
651 SStartTask(&startTime, PID_RLC_MEAS_START);
653 tKwCb = KW_GET_KWCB(pst->dstInst);
655 /* Initialize measCfmEvt */
657 /* validate the received measReqEvt */
658 /*LTE_L2_MEAS_PHASE2*/
660 measType = measReqEvt->measReq.measType;
662 if(measType & LKW_L2MEAS_DL_IP)
664 /* if measurement is for DL IP enable for all QCI */
665 for(cntr = 0; cntr < LKW_MAX_QCI; cntr++)
667 tKwCb->u.dlCb->kwL2Cb.measOn[cntr] |= LKW_L2MEAS_DL_IP;
672 /* for nonIpThroughput meas, enable only for the sent QCIs */
674 for(i = 0; i < LKW_MAX_QCI; i++)
676 tKwCb->u.dlCb->kwL2Cb.measOn[i] |= measType;
680 /* We need to copy the transId for sending back confirms later */
681 for(cntr = 0; cntr < LKW_MAX_L2MEAS; cntr++)
683 KwL2MeasEvtCb* measEvtCb = &(tKwCb->u.dlCb->kwL2Cb.kwL2EvtCb[cntr]);
684 if(measEvtCb->measCb.measType & measType)
686 measEvtCb->transId= measReqEvt->transId;
691 SStopTask(startTime, PID_RLC_MEAS_START);
693 } /* KwDlUdxMeasReq */
697 This function processes L2 Measurement stop request received from the layer manager.
698 After receving this request, RLC stops L2 Measurement
699 * @param[in] pst post structure
700 * @param[in] measType meas Type
703 * -# Failure : RFAILED
707 PUBLIC S16 KwDlUdxL2MeasStopReq
713 PUBLIC S16 KwDlUdxL2MeasStopReq (pst, measType)
719 KwL2MeasEvtCb *measEvtCb = NULLP;
722 /* KwL2MeasCfmEvt measCfmEvt; */
723 VOLATILE U32 startTime = 0;
725 TRC3(KwDlUdxMeasStopReq);
728 SStartTask(&startTime, PID_RLC_MEAS_STOP);
730 tKwCb = KW_GET_KWCB(pst->dstInst);
731 /* cmMemset((U8*)&measCfmEvt, 0, sizeof(KwL2MeasCfmEvt)); */
732 /* reset the counters for the measurement type passed */
733 for(cntr = 0; cntr < LKW_MAX_L2MEAS; cntr++)
735 measEvtCb = &(tKwCb->u.dlCb->kwL2Cb.kwL2EvtCb[cntr]);
736 if(measEvtCb->measCb.measType & measType)
738 kwUtlResetDlL2MeasInKwRb(tKwCb, &measEvtCb->measCb, measType);
743 /* switch off the measurements for the type passed */
744 for(cntr = 0; cntr < LKW_MAX_QCI; cntr++)
746 tKwCb->u.dlCb->kwL2Cb.measOn[cntr] &= ~measType;
749 status = LCM_PRIM_OK;
750 /* Stop confirm is removed as UL thread is already sending it */
753 SStopTask(startTime, PID_RLC_MEAS_STOP);
759 This function processes L2 Measurement Send request received from the layer manager.
760 After receving this request, RLC sends L2 Measurement
761 * @param[in] pst post structure
762 * @param[in] measType meas Type
765 * -# Failure : RFAILED
769 PUBLIC S16 KwDlUdxL2MeasSendReq
775 PUBLIC S16 KwDlUdxL2MeasSendReq (pst, measType)
780 KwL2MeasEvtCb *measEvtCb;
783 VOLATILE U32 startTime = 0;
785 TRC3(KwDlUdxMeasSendReq);
787 tKwCb = KW_GET_KWCB(pst->dstInst);
788 for(cntr = 0; cntr < LKW_MAX_L2MEAS; cntr++)
790 measEvtCb = &(tKwCb->u.dlCb->kwL2Cb.kwL2EvtCb[cntr]);
791 if(measEvtCb->measCb.measType & measType)
794 SStartTask(&startTime, PID_RLC_MEAS_REPORT);
796 kwUtlSndDlL2MeasCfm(tKwCb, measEvtCb);
799 SStopTask(startTime, PID_RLC_MEAS_REPORT);
805 #endif /* LTE_L2_MEAS */
809 #endif /* __cplusplus */
812 /**********************************************************************
814 **********************************************************************/