#0) More information on formula syntax:  http://doc.itk.ericsson.se/binder/current/html/ItkViewGuide/07_FormulaFiles.html
#1) Any text starting with a '#' is treated as a comment and discarded
#2) Each formula is split into the formula result variable name (part before the '=' sign) and the formula expression (the part after the '=' sign).
#3) Any reference in the formula expression to a counter name of other formula name is replaced by a perl variable reference
#4) The special names sum_<countername>, sum_time_<countername> and sum_mo_<countername> are replaced by a perl reference to variable containing counter aggregates
#5) Each formula expression is then evaluated using perl 'eval'. This means that the syntax of the expressions is the same as that of perl - you can use any perl operators & functions.
#6) The order in which the formulas are defined does not have any importance, a formula can refer to other formulas defined further down in the file
#7) The formula names should not start with "pm"

# Compliant to KPI Measurement Description 5/1550-CSH 103 704 PAC16 and N19Q2
# https://erilink.ericsson.se/eridoc/erl/objectId/09004cff877db904?docno=5/1550-CSH103704Uen&action=current&format=msw8

# Accessibility
Acc_CBRA_RandomAccessSuccRate = 100 * pmRadioRaCbSuccMsg3 / pmRadioRaCbAttMsg2
Acc_EndcSetupSuccessRate = ( pmEndcSetupUeSucc / pmEndcSetupUeAtt) * 100 
Acc_EndcSetupScgUeSuccessRate = ( pmEndcSetupScgUeSucc / pmEndcSetupScgUeAtt ) * 100
Acc_EndcNRDRBSetupSuccessRate =  ( pmEndcNrDrbSetupSucc / pmEndcNrDrbSetupAtt ) * 100

#Retainability
Ret_EndcUeRelAbnormal = pmEndcRelUeAbnormalMenb + pmEndcRelUeAbnormalSgnb
Ret_EndcUeRelAbnormalMeNBAb = pmEndcRelUeAbnormalMenb
Ret_EndcUeRelAbnormalMeNBAct = pmEndcRelUeAbnormalMenbAct 
Ret_EndcUeRelAbnormalPrimary = pmEndcRelUeAbnormalMenbAct + pmEndcRelUeAbnormalSgnbAct
Ret_EndcUeRelAbnormalSgNBAb = pmEndcRelUeAbnormalSgnb 
Ret_EndcUeRelTotal = pmEndcRelUeNormal + pmEndcRelUeAbnormalMenb + pmEndcRelUeAbnormalSgnb
Ret_EndcUeRelTotalPrimary = pmEndcRelUeNormal + pmEndcRelUeAbnormalMenb + pmEndcRelUeAbnormalSgnb
Ret_NrLegDrop = 100 * Ret_EndcUeRelAbnormal / Ret_EndcUeRelTotal
Ret_NrLegDropPrimary = 100 * Ret_EndcUeRelAbnormalPrimary / Ret_EndcUeRelTotalPrimary
Ret_NrLegRetainability = 100 * (1 - (Ret_EndcUeRelAbnormal / Ret_EndcUeRelTotal)
Ret_NrLegRetainabilityPrimary = 100 * (1 - (Ret_EndcUeRelAbnormalPrimary / Ret_EndcUeRelTotalPrimary)
Ret_NrlegDrop_MeNBTriggeredAbnormalActiveNRLegRelease = Ret_EndcUeRelAbnormalMeNBAct / Ret_EndcUeRelTotal
Ret_NrlegDrop_MeNBTriggeredAbnormalNRLegRelease = Ret_EndcUeRelAbnormalMeNBAb / Ret_EndcUeRelTotal
Ret_NrlegDrop_SgNBTriggeredAbnormalNRLegRelease = Ret_EndcUeRelAbnormalSgNBAb / Ret_EndcUeRelTotal

#Availability
Av_CellAvail = 100 * ( 900 - ( pmCellDowntimeAuto + pmCellDowntimeMan ) ) / (900)
Av_CellDownMan = 100 * pmCellDowntimeMan / 900
Av_CellDownAuto = 100 * pmCellDowntimeAuto / 900

#Integrity
Int_ActivUEsDl = pmActiveUeDlSum / pmActiveUeDlSamp
Int_ActivUEsUl = pmActiveUeUlSum / pmActiveUeUlSamp
Int_PacketsAcknowledgedToUeC5UInt = pmPdcpPktTransDlAckQos
Int_PacketsDiscardedByRlcAqmReportedByFcC5UInt  = pmPdcpPktTransDlDiscAqmQos
Int_PacketsDiscardedC5UInt = pmPdcpPktDisc 
Int_PacketsDiscardedDueToLateArrivalC5UInt = pmPdcpPktLossUlToDisc5qi
Int_PacketsDiscardedDueToPdcpAqmS1ULink = pmPdcpPktRecDlDiscAqm5qi
Int_PacketsDiscardedOrLostReportedByFcC5UInt = pmPdcpPktTransDlDiscQos
Int_PacketsDiscardedS1ULink = pmPdcpPktRecDlDisc5qi
Int_PacketsDiscardedWithInvalidGtpuHeaderC5UInt = pmPdcpPktDiscGtpu
Int_PacketsDiscardedWithMissingErabContextC5UInt = pmPdcpPktDiscNoCtxt 
Int_PacketsLostOrDiscardedC5UInt = pmPdcpPktLossUl5qi
Int_PacketsLostOrDiscardedDueToLateArrivalC5UInt  = pmPdcpPktLossUlToDisc5qi
Int_PacketsReceivedByUeC5UInt = pmPdcpPktRecUlQos 
Int_PacketsReceivedOooByUeC5UInt = pmPdcpPktRecUlOoo5qi
Int_PacketsReceivedS1ULink = pmPdcpPktRecDl5qi
Int_PacketsRetransmittedInDlC5UInt = pmPdcpPktTransDlRetrans5qi
Int_PacketsRetransmittedInDlQos = pmPdcpPktTransDlRetransQos
Int_PacketsTransmittedInDlC5UInt = pmPdcpPktTransDlQos
Int_PacketsTransmittedS1ULink = pmPdcpPktTransUl5qi 
Int_ReceivedVolumeUlC5UInt = pmPdcpVolRecUlQos
Int_RetransmittedVolumeC5UInt = pmPdcpVolTransDlRetrans5qi
Int_RetransmittedVolumeQos = pmPdcpVolTransDlRetransQos
Int_TransmittedVolumeDlC5UInt = pmPdcpVolTransDlQos
Int_VolumeTransmittedS1ULink = pmPdcpVolTransUl5qi
Int_AvgRadioRecInterferencePwr_fW = WeightedAverage(pmRadioRecInterferencePwrDistr, [0.79432,0.89716,1.12946,1.42191,1.79008,2.25357,2.83708,3.57167,4.49647,5.66072,11.07925,27.82982,69.90536,175.59432,441.07,630.95])
Int_AvgRadioRecInterferencePwr = 10*log10(Int_AvgRadioRecInterferencePwr_fW / 1000000000000)
Int_AvgRadioRecInterferencePower_fW = WeightedAverage(pmRadioRecInterferencePowerDistr, [0.1,0.129245,0.204840,0.324650,0.514535,0.79432,0.89716,1.12946,1.42191,1.79008,2.25357,2.83708,3.57167,4.49647,5.66072,11.07925,27.82982,69.90536,175.59432,441.07,630.95])
Int_AvgRadioRecInterferencePower = 10*log10(Int_AvgRadioRecInterferencePower_fW / 1000000000000)
Int_RadioSinrPucchDistrOld = WeightedAverage(pmRadioSinrPucchDistr,[-15,-13.5,-10.5,-7.5,-4.5,-1.5,1.5,3])
Int_RadioSinrPuschDistrOld = WeightedAverage(pmRadioSinrPuschDistr,[-5,-3.5,-0.5,2.5,5.5,8.5,11.5,14.5,17.5,20.5,23.5,25])
Int_RadioSinrPucchDistr = 10*log10(WeightedAverage(pmRadioSinrPucchDistr,[0.0158114,0.0473593,0.0944941,0.188541,0.376188,0.750594,1.49763,1.99526]))
Int_RadioSinrPuschDistr = 10*log10(WeightedAverage(pmRadioSinrPuschDistr,[0.158114,0.473592,0.944944,1.88541,3.76188,7.50594,14.9763,29.8817,59.6217,118.961,237.358,316.228])) 

Int_DLHarqBler    = 100 * (pmMacHarqDlNackQpsk)  / (pmMacHarqDlAckQpsk   + pmMacHarqDlNackQpsk)
Int_DLHarqBler16  = 100 * (pmMacHarqDlNack16Qam) / (pmMacHarqDlAck16Qam  + pmMacHarqDlNack16Qam)
Int_DLHarqBler64  = 100 * (pmMacHarqDlNack64Qam) / (pmMacHarqDlAck64Qam  + pmMacHarqDlNack64Qam)
Int_DLHarqBler256 = 100 * (pmMacHarqDlNack256Qam)/ (pmMacHarqDlAck256Qam + pmMacHarqDlNack256Qam)
Int_ULHarqBler    = 100 * (pmMacHarqUlNackQpsk)  / (pmMacHarqUlAckQpsk   + pmMacHarqUlNackQpsk)
Int_ULHarqBler16  = 100 * (pmMacHarqUlNack16Qam) / (pmMacHarqUlAck16Qam  + pmMacHarqUlNack16Qam)
Int_ULHarqBler64  = 100 * (pmMacHarqUlNack64Qam) / (pmMacHarqUlAck64Qam  + pmMacHarqUlNack64Qam)
Int_ULHarqBler256 = 100 * (pmMacHarqUlNack256Qam)/ (pmMacHarqUlAck256Qam + pmMacHarqUlNack256Qam)

Int_DLHarqDtxRate   = 100 * (pmMacHarqDlDtxQpsk)  / (pmMacHarqDlAckQpsk   +  pmMacHarqDlNackQpsk   + pmMacHarqDlDtxQpsk)
Int_DLHarqDtxRate16 = 100 * (pmMacHarqDlDtx16Qam) / (pmMacHarqDlAck16Qam  +  pmMacHarqDlNack16Qam  + pmMacHarqDlDtx16Qam)
Int_DLHarqDtxRate64 = 100 * (pmMacHarqDlDtx64Qam) / (pmMacHarqDlAck64Qam  +  pmMacHarqDlNack64Qam  + pmMacHarqDlDtx64Qam)
Int_DLHarqDtxRate256= 100 * (pmMacHarqDlDtx256Qam)/ (pmMacHarqDlAck256Qam +  pmMacHarqDlNack256Qam + pmMacHarqDlDtx256Qam)
Int_ULHarqDtxRate   = 100 * (pmMacHarqUlDtxQpsk)  / (pmMacHarqUlAckQpsk   +  pmMacHarqUlNackQpsk   + pmMacHarqUlDtxQpsk)
Int_ULHarqDtxRate16 = 100 * (pmMacHarqUlDtx16Qam) / (pmMacHarqUlAck16Qam  +  pmMacHarqUlNack16Qam  + pmMacHarqUlDtx16Qam)
Int_ULHarqDtxRate64 = 100 * (pmMacHarqUlDtx64Qam) / (pmMacHarqUlAck64Qam  +  pmMacHarqUlNack64Qam  + pmMacHarqUlDtx64Qam)
Int_ULHarqDtxRate256= 100 * (pmMacHarqUlDtx256Qam)/ (pmMacHarqUlAck256Qam +  pmMacHarqUlNack256Qam + pmMacHarqUlDtx256Qam)

Int_InitialDlHarqTransNackWith64Qam = pmMacHarqDlNack64QamInit

Int_DLInitHarqBler    = 100 * (pmMacHarqDlInitNackQpskInit)   / (pmMacHarqInitAckQpsk   +  pmMacHarqDlInitNackQpskInit) 
Int_DLInitHarqBler16  = 100 * (pmMacHarqDlInitNack16QamInit)  / (pmMacHarqInitAck16Qam  +  pmMacHarqDlInitNack16QamInit) 
Int_DLInitHarqBler64  = 100 * (pmMacHarqDlInitNack64QamInit)  / (pmMacHarqInitAck64Qam  +  pmMacHarqDlInitNack64QamInit)
Int_DLInitHarqBler256 = 100 * (pmMacHarqDlInitNack256QamInit) / (pmMacHarqInitAck256Qam +  pmMacHarqDlInitNack256QamInit)
Int_ULInitHarqBler    = 100 * (pmMacHarqUlInitNackQpskInit)   / (pmMacHarqInitAckQpsk   +  pmMacHarqUlInitNackQpskInit) 
Int_ULInitHarqBler16  = 100 * (pmMacHarqUlInitNack16QamInit)  / (pmMacHarqInitAck16Qam  +  pmMacHarqUlInitNack16QamInit) 
Int_ULInitHarqBler64  = 100 * (pmMacHarqUlInitNack64QamInit)  / (pmMacHarqInitAck64Qam  +  pmMacHarqUlInitNack64QamInit)
Int_ULInitHarqBler256 = 100 * (pmMacHarqUlInitNack256QamInit) / (pmMacHarqInitAck256Qam +  pmMacHarqUlInitNack256QamInit)

De_DrbEstabAtt5qi  = decompressArray(pmDrbEstabAtt5qi)
De_DrbEstabSucc5qi = decompressArray(pmDrbEstabSucc5qi)
Int_DrbEstabAtt5qi_1 = @{De_DrbEstabAtt5qi}[1]
Int_DrbEstabAtt5qi_2 = @{De_DrbEstabAtt5qi}[2]
Int_DrbEstabAtt5qi_3 = @{De_DrbEstabAtt5qi}[3]
Int_DrbEstabAtt5qi_4 = @{De_DrbEstabAtt5qi}[4]
Int_DrbEstabAtt5qi_5 = @{De_DrbEstabAtt5qi}[5]
Int_DrbEstabAtt5qi_6 = @{De_DrbEstabAtt5qi}[6]
Int_DrbEstabAtt5qi_7 = @{De_DrbEstabAtt5qi}[7]
Int_DrbEstabAtt5qi_8 = @{De_DrbEstabAtt5qi}[8]
Int_DrbEstabAtt5qi_9 = @{De_DrbEstabAtt5qi}[9]
Int_DrbEstabSuccRate5qi_1 = @{De_DrbEstabSucc5qi}[1] / @{De_DrbEstabAtt5qi}[1]
Int_DrbEstabSuccRate5qi_2 = @{De_DrbEstabSucc5qi}[2] / @{De_DrbEstabAtt5qi}[2]
Int_DrbEstabSuccRate5qi_3 = @{De_DrbEstabSucc5qi}[3] / @{De_DrbEstabAtt5qi}[3]
Int_DrbEstabSuccRate5qi_4 = @{De_DrbEstabSucc5qi}[4] / @{De_DrbEstabAtt5qi}[4]
Int_DrbEstabSuccRate5qi_5 = @{De_DrbEstabSucc5qi}[5] / @{De_DrbEstabAtt5qi}[5]
Int_DrbEstabSuccRate5qi_6 = @{De_DrbEstabSucc5qi}[6] / @{De_DrbEstabAtt5qi}[6]
Int_DrbEstabSuccRate5qi_7 = @{De_DrbEstabSucc5qi}[7] / @{De_DrbEstabAtt5qi}[7]
Int_DrbEstabSuccRate5qi_8 = @{De_DrbEstabSucc5qi}[8] / @{De_DrbEstabAtt5qi}[8]
Int_DrbEstabSuccRate5qi_9 = @{De_DrbEstabSucc5qi}[9] / @{De_DrbEstabAtt5qi}[9]

De_PdcpPktRecUlQos        = decompressArray(pmPdcpPktRecUlQos)
De_PdcpPktLossUlQos       = decompressArray(pmPdcpPktLossUlQos)
De_PdcpPktLossUlToQos     = decompressArray(pmPdcpPktLossUlToQos)
De_PdcpPktLossUlToDiscQos = decompressArray(pmPdcpPktLossUlToDiscQos)
#PdcpPktRecUlQos_6 = @{De_PdcpPktRecUlQos}[6]
#PdcpPktLossUlQos_6 = @{De_PdcpPktLossUlQos}[6]
#PdcpPktLossUlToQos_6 = @{De_PdcpPktLossUlToQos}[6]
#PdcpPktLossUlToDiscQos_6 = @{De_PdcpPktLossUlToDiscQos}[6] 
Int_PacketLossRateUl5qi_1 = 100 * @{De_PdcpPktLossUlQos}[1] / ( @{De_PdcpPktRecUlQos}[1] - @{De_PdcpPktLossUlToDiscQos}[1] + @{De_PdcpPktLossUlToQos}[1] )
Int_PacketLossRateUl5qi_2 = 100 * @{De_PdcpPktLossUlQos}[2] / ( @{De_PdcpPktRecUlQos}[2] - @{De_PdcpPktLossUlToDiscQos}[2] + @{De_PdcpPktLossUlToQos}[2] )
Int_PacketLossRateUl5qi_3 = 100 * @{De_PdcpPktLossUlQos}[3] / ( @{De_PdcpPktRecUlQos}[3] - @{De_PdcpPktLossUlToDiscQos}[3] + @{De_PdcpPktLossUlToQos}[3] )
Int_PacketLossRateUl5qi_4 = 100 * @{De_PdcpPktLossUlQos}[4] / ( @{De_PdcpPktRecUlQos}[4] - @{De_PdcpPktLossUlToDiscQos}[4] + @{De_PdcpPktLossUlToQos}[4] )
Int_PacketLossRateUl5qi_5 = 100 * @{De_PdcpPktLossUlQos}[5] / ( @{De_PdcpPktRecUlQos}[5] - @{De_PdcpPktLossUlToDiscQos}[5] + @{De_PdcpPktLossUlToQos}[5] )
Int_PacketLossRateUl5qi_6 = 100 * @{De_PdcpPktLossUlQos}[6] / ( @{De_PdcpPktRecUlQos}[6] - @{De_PdcpPktLossUlToDiscQos}[6] + @{De_PdcpPktLossUlToQos}[6] )
Int_PacketLossRateUl5qi_7 = 100 * @{De_PdcpPktLossUlQos}[7] / ( @{De_PdcpPktRecUlQos}[7] - @{De_PdcpPktLossUlToDiscQos}[7] + @{De_PdcpPktLossUlToQos}[7] )
Int_PacketLossRateUl5qi_8 = 100 * @{De_PdcpPktLossUlQos}[8] / ( @{De_PdcpPktRecUlQos}[8] - @{De_PdcpPktLossUlToDiscQos}[8] + @{De_PdcpPktLossUlToQos}[8] )
Int_PacketLossRateUl5qi_9 = 100 * @{De_PdcpPktLossUlQos}[9] / ( @{De_PdcpPktRecUlQos}[9] - @{De_PdcpPktLossUlToDiscQos}[9] + @{De_PdcpPktLossUlToQos}[9] )


#ESS
Int_Average_DL_MAC_Cell_THP_LTE = pmRadioThpVolDl / pmSchedActivityCellDl
Int_Average_DL_MAC_Cell_THP_NR = 64 * pmMacVolDl / pmPdschSchedActivity
Int_LTE_PRB_Util_Av = (pmPrbUsedDlBcch + pmPrbUsedDlDtch + pmPrbUsedDlPcch + pmPrbUsedDlSrb) / pmPrbAvailDl 
Int_LTE_UL_PRB_util_Av = pmPrbUsedUlDtch / pmPrbAvailUl 

#Throughput in Mbps. Note: some of these formulas may give incorrect result , problem under investigation
DL_Cell_Thp_Traffic_normalized = 64 * pmMacVolDl / (pmPdschSchedActivity * 1000)
DL_Cell_Thp_Resources_Normalized_TDD = 64 * pmMacVolDl / (pmPdschAvailTime * 1000)
DL_Cell_Thp_Fixed_Time_Normalization1 = 8 * pmMacVolDl / (900 * 1000000)
DL_Cell_Thp_Fixed_Time_Normalization2 = 64 * pmMacVolDlDrb / (1000 * pmMacTimeDlDrb)
UL_Cell_Thp_Traffic_Normalized = 64 * pmMacVolUl / (pmPuschSchedActivity * 1000)
UL_Cell_Thp_Resources_Normalized = 64 * pmMacVolUl / (pmPuschAvailTime * 1000)
UL_Cell_Thp_Fixed_Time_Normalization = 8 * pmMacVolUl / (900 * 1000000)
UL_UE_Thp_User_Thp = 64 * pmMacVolUlResUe / (pmMacTimeUlResUe * 1000)


##### NR-SA KPIs ##########

#PDU session setup success rate
Acc_NrSaPduSessionSetupSuccRate = 100 *  pmPduSessionEstabSucc / pmPduSessionEstabAtt
#NGAP signallimg setup success rate
Acc_NrSaNgSigEstabSuccRate = 100 *  pmNgSigConnEstabSucc / pmNgSigConnEstabAtt
#RRC connection setup succcess rate
Acc_NrSaRrcConnSetupSuccRate = 100 *  pmRrcConnEstabSucc  / (pmRrcConnEstabAtt -  pmRrcConnEstabAttReatt) 
#PDU session establishment success rate
Acc_NrSaPduSessionEstabSuccRate = Acc_NrSaRrcConnSetupSuccRate * Acc_NrSaNgSigEstabSuccRate * Acc_NrSaPduSessionSetupSuccRate  /  10000 
#Initial UE context establishment success rate
Acc_NrSaInitialUEContextEstabSuccRate = 100 * pmUeCtxtEstabSucc / pmUeCtxtEstabAtt

#Handover execution success rate
Mob_NrSaHoExecSuccRate = 100 * ( pmHoExeSuccOutIntraGnb + pmHoExeSuccOutInterGnb )  /  ( pmHoExeAttOutIntraGnb + pmHoExeAttOutInterGnb )
#Handover preparation success rate
Mob_NrSaHoPrepSuccRate = 100 * ( pmHoPrepSuccOutIntraGnb + pmHoPrepSuccOutInterGnb )  /  ( pmHoPrepAttOutIntraGnb + pmHoPrepAttOutInterGnb )
#Handover success rate
Mob_NrSaMobilitySuccRate = Mob_NrSaHoPrepSuccRate * Mob_NrSaHoExecSuccRate  /  100

#PDU connection abnormal release rate
Ret_NrSaPduSessionRetainabilityRate = 100* (  pmPduSessionRelAbnormalAmf +  pmPduSessionRelAbnormalGnb )  /   (  pmPduSessionRelAbnormalAmf +  pmPduSessionRelAbnormalGnb +  pmPduSessionRelNormal)  
#PDU connection abnormal release number
Ret_NrSaPduSessionRelAbnormal =  pmPduSessionRelAbnormalAmf +  pmPduSessionRelAbnormalGnb

############################