diff --git a/CMakeLists.txt b/CMakeLists.txt
index d0b9f17a02..b8a1b3a082 100644
--- a/CMakeLists.txt
+++ b/CMakeLists.txt
@@ -19,7 +19,7 @@
# * contact@openairinterface.org
# */
-cmake_minimum_required (VERSION 3.16)
+cmake_minimum_required (VERSION 3.19)
project (OpenAirInterface LANGUAGES C CXX)
set(CMAKE_CXX_STANDARD 17)
set(OAI_VERSION 2.4.0)
@@ -441,6 +441,7 @@ add_library(ngap
${NGAP_DIR}/ngap_gNB_overload.c
${NGAP_DIR}/ngap_gNB_trace.c
${NGAP_DIR}/ngap_gNB_ue_context.c
+ ${NGAP_DIR}/ngap_gNB_NRPPa_transport_procedures.c
)
target_link_libraries(ngap PUBLIC asn1_ngap)
target_link_libraries(ngap PRIVATE asn1_lte_rrc_hdrs asn1_nr_rrc_hdrs)
@@ -1308,6 +1309,8 @@ set (GNB_APP_SRC
${OPENAIR2_DIR}/GNB_APP/gnb_app.c
${OPENAIR2_DIR}/E1AP/e1ap_setup.c
${OPENAIR2_DIR}/GNB_APP/gnb_config.c
+ ${OPENAIR2_DIR}/GNB_APP/gnb_config_common.c
+ ${OPENAIR2_DIR}/GNB_APP/gnb_config_ng.c
)
set (MCE_APP_SRC
@@ -2012,11 +2015,9 @@ target_link_libraries(nr_pbchsim PRIVATE asn1_nr_rrc_hdrs asn1_lte_rrc_hdrs)
add_executable(nr_psbchsim
${OPENAIR1_DIR}/SIMULATION/NR_PHY/psbchsim.c
${NFAPI_USER_DIR}/nfapi.c
- ${NFAPI_USER_DIR}/gnb_ind_vars.c
- ${PHY_INTERFACE_DIR}/queue_t.c
)
target_link_libraries(nr_psbchsim PRIVATE
- -Wl,--start-group UTIL SIMU PHY_COMMON PHY_NR_COMMON PHY_NR PHY_NR_UE SCHED_NR_LIB SCHED_NR_UE_LIB MAC_UE_NR MAC_NR_COMMON CONFIG_LIB L2_NR -Wl,--end-group
+ -Wl,--start-group UTIL SIMU PHY_COMMON PHY_NR_COMMON PHY_NR PHY_NR_UE SCHED_NR_LIB SCHED_NR_UE_LIB MAC_UE_NR MAC_NR_COMMON CONFIG_LIB -Wl,--end-group
m pthread ${T_LIB} ITTI dl physim_common softmodem_common
)
target_link_libraries(nr_psbchsim PRIVATE asn1_nr_rrc_hdrs asn1_lte_rrc_hdrs)
@@ -2035,7 +2036,7 @@ add_executable(nr_dlsim
${PHY_INTERFACE_DIR}/queue_t.c
)
target_link_libraries(nr_dlsim PRIVATE
- -Wl,--start-group UTIL SIMU PHY_COMMON PHY_NR_COMMON PHY_NR PHY_NR_UE SCHED_NR_LIB SCHED_NR_UE_LIB MAC_UE_NR MAC_NR_COMMON nr_rrc CONFIG_LIB L2_NR x2ap SECURITY ngap -Wl,--end-group
+ -Wl,--start-group UTIL SIMU PHY_COMMON PHY_NR_COMMON PHY_NR PHY_NR_UE SCHED_NR_LIB SCHED_NR_UE_LIB MAC_UE_NR MAC_NR_COMMON CONFIG_LIB L2_NR -Wl,--end-group
m pthread ${T_LIB} ITTI dl nr_ue_phy_meas physim_common
softmodem_common
)
@@ -2049,7 +2050,6 @@ target_link_libraries(nr_prachsim PRIVATE asn1_nr_rrc_hdrs asn1_lte_rrc_hdrs)
add_executable(nr_ulschsim
${OPENAIR1_DIR}/SIMULATION/NR_PHY/ulschsim.c
- ${PHY_INTERFACE_DIR}/queue_t.c
)
target_link_libraries(nr_ulschsim PRIVATE
-Wl,--start-group UTIL SIMU PHY_COMMON PHY_NR_COMMON PHY_NR PHY_NR_UE SCHED_NR_LIB CONFIG_LIB MAC_NR_COMMON -Wl,--end-group
@@ -2065,7 +2065,7 @@ add_executable(nr_ulsim
)
target_link_libraries(nr_ulsim PRIVATE
- -Wl,--start-group UTIL SIMU PHY_COMMON PHY_NR_COMMON PHY_NR PHY_NR_UE SCHED_NR_LIB SCHED_NR_UE_LIB MAC_UE_NR MAC_NR_COMMON nr_rrc CONFIG_LIB L2_NR x2ap SECURITY ngap -Wl,--end-group
+ -Wl,--start-group UTIL SIMU PHY_COMMON PHY_NR_COMMON PHY_NR PHY_NR_UE SCHED_NR_LIB SCHED_NR_UE_LIB MAC_UE_NR MAC_NR_COMMON CONFIG_LIB L2_NR -Wl,--end-group
m pthread ${T_LIB} ITTI dl nr_ue_phy_meas physim_common softmodem_common
)
target_link_libraries(nr_ulsim PRIVATE asn1_nr_rrc_hdrs asn1_lte_rrc_hdrs)
@@ -2073,8 +2073,6 @@ target_link_libraries(nr_ulsim PRIVATE asn1_nr_rrc_hdrs asn1_lte_rrc_hdrs)
add_executable(nr_srssim
${OPENAIR1_DIR}/SIMULATION/NR_PHY/srssim.c
${NFAPI_USER_DIR}/nfapi.c
- ${NFAPI_USER_DIR}/gnb_ind_vars.c
- ${PHY_INTERFACE_DIR}/queue_t.c
)
target_link_libraries(nr_srssim PRIVATE
diff --git a/README.md b/README.md
index 17e275f240..aba30a855b 100644
--- a/README.md
+++ b/README.md
@@ -7,7 +7,7 @@
-
+
diff --git a/ci-scripts/Jenkinsfile-GitLab-Container b/ci-scripts/Jenkinsfile-GitLab-Container
index e94f386e2e..85b6f18c18 100644
--- a/ci-scripts/Jenkinsfile-GitLab-Container
+++ b/ci-scripts/Jenkinsfile-GitLab-Container
@@ -795,6 +795,29 @@ pipeline {
}
}
}
+ stage ("SA-AERIAL-OAIUE-CN5G") {
+ when { expression {do5Gtest || do5GUeTest} }
+ steps {
+ script {
+ triggerSlaveJob ('RAN-SA-AERIAL-OAIUE-CN5G', 'SA-AERIAL-OAIUE-CN5G')
+ }
+ }
+ post {
+ always {
+ script {
+ // Using a unique variable name for each test stage to avoid overwriting on a global variable
+ // due to parallel-time concurrency
+ saAERIALOAIUEStatus = finalizeSlaveJob('RAN-SA-AERIAL-OAIUE-CN5G')
+ }
+ }
+ failure {
+ script {
+ currentBuild.result = 'FAILURE'
+ failingStages += saAERIALOAIUEStatus
+ }
+ }
+ }
+ }
stage ("SA-OAIUE-CN5G") {
when { expression {do5Gtest || do5GUeTest} }
steps {
diff --git a/ci-scripts/ci_infra.yaml b/ci-scripts/ci_infra.yaml
index 837f1edb82..00da44ed77 100644
--- a/ci-scripts/ci_infra.yaml
+++ b/ci-scripts/ci_infra.yaml
@@ -101,6 +101,14 @@ oc-cn5g-20897-aerial:
Undeploy: "! scripts/oc-cn5g-undeploy.sh /opt/oai-cn5g-fed-develop-2025-jan oaicicd-core-for-nvidia-aerial"
LogCollect: "! scripts/oc-cn5g-logcollect.sh /opt/oai-cn5g-fed-develop-2025-jan oaicicd-core-for-nvidia-aerial %%log_dir%%"
+oc-cn5g-00104:
+ Host: gracehopper1-oai
+ NetworkScript: echo "inet 172.21.6.105"
+ RunIperf3Server: False
+ Deploy: "! scripts/oc-cn5g-deploy.sh /opt/oai-cn5g-fed-develop-00104 oaicicd-core-for-nvidia-aerial"
+ Undeploy: "! scripts/oc-cn5g-undeploy.sh /opt/oai-cn5g-fed-develop-00104 oaicicd-core-for-nvidia-aerial"
+ LogCollect: "! scripts/oc-cn5g-logcollect.sh /opt/oai-cn5g-fed-develop-00104 oaicicd-core-for-nvidia-aerial %%log_dir%%"
+
matix-cn5g:
Host: matix
NetworkScript: docker exec prod-trf-gen ip a show dev eth0
@@ -300,6 +308,14 @@ oai_ue_caracal:
IF: oaitun_ue1
MTU: 1500
+oai_ue_jetson2:
+ Host: jetson2-oai
+ AttachScript: 'docker start oai-nr-ue'
+ DetachScript: 'docker stop oai-nr-ue'
+ NetworkScript: ip a show dev oaitun_ue1
+ IF: oaitun_ue1
+ MTU: 1500
+
lte_oai_ue_carabe:
Host: carabe
NetworkScript: docker exec lte-b200-ue-fdd-10Mhz-tm1 ip a show dev oaitun_ue1
diff --git a/ci-scripts/conf_files/gnb-vnf.sa.band78.78prb.aerial.conf b/ci-scripts/conf_files/gnb-vnf.sa.band78.78prb.aerial.conf
new file mode 100644
index 0000000000..12c0aba35c
--- /dev/null
+++ b/ci-scripts/conf_files/gnb-vnf.sa.band78.78prb.aerial.conf
@@ -0,0 +1,226 @@
+Active_gNBs = ( "gNB-OAI");
+# Asn1_verbosity, choice in: none, info, annoying
+Asn1_verbosity = "none";
+
+nfapi = "AERIAL";
+
+gNBs =
+(
+ {
+ ////////// Identification parameters:
+ gNB_ID = 0xe00;
+ gNB_name = "gNB-OAI";
+
+ // Tracking area code, 0x0000 and 0xfffe are reserved values
+ tracking_area_code = 1;
+ plmn_list = ({mcc = 001; mnc = 04; mnc_length = 2; snssaiList = ({sst = 1;});});
+
+ nr_cellid = 12345678L;
+
+ ////////// Physical parameters:
+
+ pdsch_AntennaPorts_XP = 2;
+ pdsch_AntennaPorts_N1 = 2;
+ pusch_AntennaPorts = 2;
+ do_CSIRS = 0;
+ do_SRS = 0;
+ min_rxtxtime = 6;
+
+ servingCellConfigCommon = (
+ {
+ #spCellConfigCommon
+
+ physCellId = 0;
+
+# downlinkConfigCommon
+ #frequencyInfoDL
+ # center frequency = 3350.01 MHz
+ # selected SSB frequency = 3349.92 MHz
+ absoluteFrequencySSB = 623328;
+ dl_frequencyBand = 78;
+ # frequency point A = 3300.87 MHz
+ dl_absoluteFrequencyPointA = 622398;
+ #scs-SpecificCarrierList
+ dl_offstToCarrier = 0;
+# subcarrierSpacing
+# 0=kHz15, 1=kHz30, 2=kHz60, 3=kHz120
+ dl_subcarrierSpacing = 1;
+ dl_carrierBandwidth = 78;
+ #initialDownlinkBWP
+ #genericParameters
+ # this is RBstart=0,L=162 (275*(275-L+1))+(274-RBstart))
+ initialDLBWPlocationAndBandwidth = 21175;
+ #
+# subcarrierSpacing
+# 0=kHz15, 1=kHz30, 2=kHz60, 3=kHz120
+ initialDLBWPsubcarrierSpacing = 1;
+ #pdcch-ConfigCommon
+ initialDLBWPcontrolResourceSetZero = 12;
+ initialDLBWPsearchSpaceZero = 0;
+
+ #uplinkConfigCommon
+ #frequencyInfoUL
+ ul_frequencyBand = 78;
+ #scs-SpecificCarrierList
+ ul_offstToCarrier = 0;
+# subcarrierSpacing
+# 0=kHz15, 1=kHz30, 2=kHz60, 3=kHz120
+ ul_subcarrierSpacing = 1;
+ ul_carrierBandwidth = 78;
+ pMax = 20;
+ #initialUplinkBWP
+ #genericParameters
+ initialULBWPlocationAndBandwidth = 21175;
+# subcarrierSpacing
+# 0=kHz15, 1=kHz30, 2=kHz60, 3=kHz120
+ initialULBWPsubcarrierSpacing = 1;
+ #rach-ConfigCommon
+ #rach-ConfigGeneric
+ prach_ConfigurationIndex = 148;# testMAC 158; OAI gNB 98
+#prach_msg1_FDM
+#0 = one, 1=two, 2=four, 3=eight
+ prach_msg1_FDM = 0;
+ prach_msg1_FrequencyStart = 0;
+ zeroCorrelationZoneConfig = 12;
+ preambleReceivedTargetPower = -96;
+#preamblTransMax (0...10) = (3,4,5,6,7,8,10,20,50,100,200)
+ preambleTransMax = 6;
+#powerRampingStep
+# 0=dB0,1=dB2,2=dB4,3=dB6
+ powerRampingStep = 1;
+#ssb_perRACH_OccasionAndCB_PreamblesPerSSB_PR
+#1=oneeighth,2=onefourth,3=half,4=one,5=two,6=four,7=eight,8=sixteen
+ ssb_perRACH_OccasionAndCB_PreamblesPerSSB_PR = 4;
+#one (0..15) 4,8,12,16,...60,64
+ ssb_perRACH_OccasionAndCB_PreamblesPerSSB = 15;
+#ra_ContentionResolutionTimer
+#(0..7) 8,16,24,32,40,48,56,64
+ ra_ContentionResolutionTimer = 7;
+ rsrp_ThresholdSSB = 19;
+#prach-RootSequenceIndex_PR
+#1 = 839, 2 = 139
+ prach_RootSequenceIndex_PR = 2;
+ prach_RootSequenceIndex = 1;
+ # SCS for msg1, can only be 15 for 30 kHz < 6 GHz, takes precendence over the one derived from prach-ConfigIndex
+ #
+ msg1_SubcarrierSpacing = 1,
+# restrictedSetConfig
+# 0=unrestricted, 1=restricted type A, 2=restricted type B
+ restrictedSetConfig = 0,
+
+ msg3_DeltaPreamble = 1;
+ p0_NominalWithGrant = -90;
+
+# pucch-ConfigCommon setup :
+# pucchGroupHopping
+# 0 = neither, 1= group hopping, 2=sequence hopping
+ pucchGroupHopping = 0;
+ hoppingId = 40;
+ p0_nominal = -90;
+
+ ssb_PositionsInBurst_Bitmap = 1;
+
+# ssb_periodicityServingCell
+# 0 = ms5, 1=ms10, 2=ms20, 3=ms40, 4=ms80, 5=ms160, 6=spare2, 7=spare1
+ ssb_periodicityServingCell = 2;
+
+# dmrs_TypeA_position
+# 0 = pos2, 1 = pos3
+ dmrs_TypeA_Position = 0;
+
+# subcarrierSpacing
+# 0=kHz15, 1=kHz30, 2=kHz60, 3=kHz120
+ subcarrierSpacing = 1;
+
+
+ #tdd-UL-DL-ConfigurationCommon
+# subcarrierSpacing
+# 0=kHz15, 1=kHz30, 2=kHz60, 3=kHz120
+ referenceSubcarrierSpacing = 1;
+ # pattern1
+ # dl_UL_TransmissionPeriodicity
+ # 0=ms0p5, 1=ms0p625, 2=ms1, 3=ms1p25, 4=ms2, 5=ms2p5, 6=ms5, 7=ms10
+ dl_UL_TransmissionPeriodicity = 6; #5;
+ nrofDownlinkSlots = 6; #3;
+ nrofDownlinkSymbols = 10; #6;
+ nrofUplinkSlots = 3; #1;
+ nrofUplinkSymbols = 0;
+
+ ssPBCH_BlockPower = -25;
+ }
+
+ );
+
+
+ # ------- SCTP definitions
+ SCTP :
+ {
+ # Number of streams to use in input/output
+ SCTP_INSTREAMS = 2;
+ SCTP_OUTSTREAMS = 2;
+ };
+
+
+ ////////// AMF parameters:
+ amf_ip_address = ({ ipv4 = "172.21.6.103"; });
+
+
+ NETWORK_INTERFACES :
+ {
+ GNB_IPV4_ADDRESS_FOR_NG_AMF = "172.21.16.53";
+ GNB_IPV4_ADDRESS_FOR_NGU = "172.21.16.53";
+ GNB_PORT_FOR_S1U = 2152; # Spec 2152
+ };
+
+ }
+);
+
+MACRLCs = (
+{
+ num_cc = 1;
+ remote_s_address = "127.0.0.1"; // pnf addr [!]
+ local_s_address = "127.0.0.2"; // vnf addr
+ local_s_portc = 50001; // vnf p5 port
+ remote_s_portc = 50000; // pnf p5 port [!]
+ local_s_portd = 50011; // vnf p7 port [!]
+ remote_s_portd = 50010; // pnf p7 port [!]
+ tr_s_preference = "aerial";
+ tr_n_preference = "local_RRC";
+ pusch_TargetSNRx10 = 180; # 150;
+ pucch_TargetSNRx10 = 180; #200;
+ ulsch_max_frame_inactivity = 10;
+ dl_max_mcs = 28;
+ ul_max_mcs = 28;
+}
+);
+
+
+security = {
+ # preferred ciphering algorithms
+ # the first one of the list that an UE supports in chosen
+ # valid values: nea0, nea1, nea2, nea3
+ ciphering_algorithms = ( "nea0" );
+
+ # preferred integrity algorithms
+ # the first one of the list that an UE supports in chosen
+ # valid values: nia0, nia1, nia2, nia3
+ integrity_algorithms = ( "nia2", "nia0" );
+
+ # setting 'drb_ciphering' to "no" disables ciphering for DRBs, no matter
+ # what 'ciphering_algorithms' configures; same thing for 'drb_integrity'
+ drb_ciphering = "yes";
+ drb_integrity = "no";
+};
+
+log_config :
+{
+ global_log_level ="info";
+ hw_log_level ="info";
+ phy_log_level ="info";
+ mac_log_level ="info";
+ rlc_log_level ="info";
+ pdcp_log_level ="info";
+ rrc_log_level ="info";
+ ngap_log_level ="debug";
+ f1ap_log_level ="debug";
+}
diff --git a/ci-scripts/scripts/set-wnc-bandwidth.sh b/ci-scripts/scripts/set-wnc-bandwidth.sh
new file mode 100644
index 0000000000..c52f30e388
--- /dev/null
+++ b/ci-scripts/scripts/set-wnc-bandwidth.sh
@@ -0,0 +1,93 @@
+#!/bin/bash
+
+if [ -z "$1" ]; then
+ echo "Usage: $0 [reboot]"
+ exit 1
+fi
+
+BANDWIDTH="$1"
+DO_REBOOT="$2"
+RU_IP="10.10.0.115"
+HOST="root@$RU_IP"
+LOGFILE="/tmp/radio_config_$(date +%Y%m%d_%H%M%S).log"
+
+echo "=== Starting at $(date) ===" | tee "$LOGFILE"
+echo "Target bandwidth: $BANDWIDTH" | tee -a "$LOGFILE"
+echo "Reboot before configuration: ${DO_REBOOT:-no}" | tee -a "$LOGFILE"
+
+if [ "$DO_REBOOT" == "reboot" ]; then
+ echo "=== Rebooting RU ($RU_IP) ... ===" | tee -a "$LOGFILE"
+
+ expect < /dev/null 2>&1
+set timeout 10
+spawn ssh -tt $HOST
+
+expect "#"
+send "reboot\r"
+expect "Continue?"
+send "Y\r"
+# We expect disconnect now
+expect eof
+EOF
+
+ echo "→ Waiting for $RU_IP SSH to go down..." | tee -a "$LOGFILE"
+ sleep 10
+
+ echo "→ Waiting for $RU_IP SSH port 22 to be open..." | tee -a "$LOGFILE"
+ while ! nc -zv $RU_IP 22 >/dev/null 2>&1; do
+ echo "SSH port 22 not open, waiting 5 seconds..." | tee -a "$LOGFILE"
+ sleep 5
+ done
+ echo "✓ SSH port 22 is open on $RU_IP" | tee -a "$LOGFILE"
+fi
+
+echo "=== Applying bandwidth configuration ===" | tee -a "$LOGFILE"
+
+expect < /dev/null 2>&1
+set timeout 10
+spawn ssh -tt $HOST
+
+expect "#"
+send "radio disable\r"
+
+expect "#"
+send "config\r"
+
+expect "(config)#"
+send "radio 1\r"
+
+expect "(conf-rf 1)#"
+send "bandwidth ${BANDWIDTH}\r"
+
+expect "(conf-rf 1)#"
+send "exit\r"
+
+expect "(config)#"
+send "exit\r"
+
+expect "#"
+send "radio enable\r"
+
+expect "#"
+send "show running-config\r"
+
+expect "#"
+send "exit\r"
+EOF
+
+echo "=== Checking bandwidth in running-config ===" | tee -a "$LOGFILE"
+
+FOUND_BW=$(grep -E "bandwidth[[:space:]]+[0-9]+" "$LOGFILE" \
+ | tail -n 1 \
+ | awk '{print $2}' \
+ | tr -d '\r[:space:]')
+
+if [ "$FOUND_BW" -eq "$BANDWIDTH" ]; then
+ echo "✓ SUCCESS: Bandwidth correctly set to $FOUND_BW" | tee -a "$LOGFILE"
+ rm "$LOGFILE"
+ exit 0
+else
+ echo "✖ ERROR: Expected bandwidth $BANDWIDTH but found: $FOUND_BW" | tee -a "$LOGFILE"
+ exit 1
+fi
+
diff --git a/ci-scripts/xml_files/container_sa_aerial_quectel.xml b/ci-scripts/xml_files/container_sa_aerial_quectel.xml
index b5de982e5a..e7e5ebd2dd 100644
--- a/ci-scripts/xml_files/container_sa_aerial_quectel.xml
+++ b/ci-scripts/xml_files/container_sa_aerial_quectel.xml
@@ -33,6 +33,15 @@
arm_
+
+ Custom_Script
+ true
+ Configure 100 MHz bandwidth on WNC RU
+ gracehopper1-oai
+
+ 100
+
+
Detach_UE
true
diff --git a/ci-scripts/xml_files/container_sa_aerial_quectel_ul_heavy.xml b/ci-scripts/xml_files/container_sa_aerial_quectel_ul_heavy.xml
index 9d826d2261..65a34c3e4e 100644
--- a/ci-scripts/xml_files/container_sa_aerial_quectel_ul_heavy.xml
+++ b/ci-scripts/xml_files/container_sa_aerial_quectel_ul_heavy.xml
@@ -33,6 +33,15 @@
arm_
+
+ Custom_Script
+ true
+ Configure 100 MHz bandwidth on WNC RU
+ gracehopper1-oai
+
+ 100
+
+
Detach_UE
true
diff --git a/ci-scripts/xml_files/container_sa_b200_nrue_jetson.xml b/ci-scripts/xml_files/container_sa_b200_nrue_jetson.xml
new file mode 100644
index 0000000000..610aa306d5
--- /dev/null
+++ b/ci-scripts/xml_files/container_sa_b200_nrue_jetson.xml
@@ -0,0 +1,212 @@
+
+
+ JETSON-5G-NRUE
+ 30 MHz TDD SA JETSON
+ tasks
+
+ DeployCoreNetwork
+ Initialize 5G Core
+ oc-cn5g-00104
+
+
+
+ Pull_Local_Registry
+ Pull Images from Local Registry
+ jetson2-oai
+ oai-nr-ue
+ armv8_
+
+
+
+ Pull_Local_Registry
+ Pull Images from Local Registry
+ gracehopper1-oai
+ oai-gnb-aerial
+ arm_
+
+
+
+ Create_Workspace
+ Create new Workspace
+ jetson2-oai
+
+
+
+ Create_Workspace
+ Create new Workspace
+ gracehopper1-oai
+
+
+
+ Custom_Script
+ Configure 30 MHz bandwidth on WNC RU
+ gracehopper1-oai
+
+ 30
+
+
+
+ Deploy_Object
+ Deploy PNF/Nvidia CUBB in a container
+ gracehopper1-oai
+ ci-scripts/yaml_files/sa_gnb_aerial_30MHz
+ nv-cubb
+
+
+
+ Deploy_Object
+ Deploy VNF in a container
+ gracehopper1-oai
+ ci-scripts/yaml_files/sa_gnb_aerial_30MHz
+ oai-gnb-aerial
+
+
+
+ Deploy_Object
+ Deploy nrUE (TDD/Band78/40MHz/N310) in a container
+ ci-scripts/yaml_files/sa_b200_jetson_nrue
+ jetson2-oai
+ 3
+
+
+
+ Attach_UE
+ Attach OAIUE
+ oai_ue_jetson2
+
+
+
+ Custom_Command
+ Configure IP route
+ jetson2-oai
+ sudo ip route add 172.21.6.105 via 13.1.1.100 dev oaitun_ue1
+
+
+
+ Ping
+ Ping: 20pings in 20sec
+ oai_ue_jetson2
+ oc-cn5g-00104
+ -c 20
+ 1
+ 25
+
+
+
+ Iperf
+ iperf (UL/10Mbps/UDP)(30 sec)
+ -u -b 10M -t 30 -i 1
+ oai_ue_jetson2
+ oc-cn5g-00104
+ 25
+ 80
+
+
+
+ Iperf
+ iperf (DL/10Mbps/UDP)(30 sec)
+ -u -b 10M -t 30 -i 1 -R
+ oai_ue_jetson2
+ oc-cn5g-00104
+ 25
+ 80
+
+
+
+ Iperf
+ iperf (UL/30Mbps/UDP)(30 sec)
+ true
+ -u -b 30M -t 30 -i 1
+ oai_ue_jetson2
+ oc-cn5g-00104
+ 25
+ 80
+
+
+
+ Iperf
+ iperf (DL/30Mbps/UDP)(30 sec)
+ true
+ -u -b 30M -t 30 -i 1 -R
+ oai_ue_jetson2
+ oc-cn5g-00104
+ 25
+ 80
+
+
+
+ Undeploy_Object
+ true
+ Undeploy nr UE
+ jetson2-oai
+ ci-scripts/yaml_files/sa_b200_jetson_nrue
+
+ oai-nr-ue
+
+
+
+
+ Undeploy_Object
+ true
+ Undeploy gNB
+ gracehopper1-oai
+ ci-scripts/yaml_files/sa_gnb_aerial_30MHz
+
+ oai-gnb-aerial=RetxCheck=20,100,100,100 oai-gnb-aerial=EndsWithBye
+
+
+
+
+ Custom_Script
+ true
+ Configure 100 MHz bandwidth on WNC RU
+ gracehopper1-oai
+
+ 100
+
+
+
+ Clean_Test_Server_Images
+ true
+ Clean Test Images on Test Server
+ gracehopper1-oai
+ oai-gnb-aerial
+
+
+
+ Clean_Test_Server_Images
+ true
+ Clean Test Images on Test Server
+ jetson2-oai
+ oai-nr-ue
+
+
+
+ UndeployCoreNetwork
+ true
+ Terminate 5G Core
+ oc-cn5g-00104
+
+
+
diff --git a/ci-scripts/yaml_files/sa_b200_jetson_nrue/docker-compose.yml b/ci-scripts/yaml_files/sa_b200_jetson_nrue/docker-compose.yml
new file mode 100644
index 0000000000..0a35a3caaa
--- /dev/null
+++ b/ci-scripts/yaml_files/sa_b200_jetson_nrue/docker-compose.yml
@@ -0,0 +1,27 @@
+services:
+ oai-nr-ue:
+ image: ${REGISTRY-oaisoftwarealliance/}${NRUE_IMG:-oai-nr-ue}:${TAG:-develop}
+ network_mode: host
+ container_name: oai-nr-ue
+ cap_drop:
+ - ALL
+ cap_add:
+ - NET_ADMIN # for interface bringup
+ - NET_RAW # for ping
+ - SYS_NICE # for performance
+ - IPC_LOCK # for memory locking
+ devices:
+ - /dev/net/tun:/dev/net/tun
+ - /dev/bus/usb/:/dev/bus/usb/
+ environment:
+ TZ: Europe/Paris
+ USE_B2XX: 'yes'
+ USE_ADDITIONAL_OPTIONS: --usrp-args type=b200 -C 3350010000 -r 78 --numerology 1 --band 78 --ssb 345 --ue-fo-compensation --uicc0.imsi 001040000000001 --uicc0.pdu_sessions.[0].dnn oai.ipv4 -A 60 --thread-pool 5,6,7,8,9 --ue-txgain 15 --ue-rxgain 90
+ cpuset: "3-11"
+ volumes:
+ - ../../conf_files/ue.sa.conf:/opt/oai-nr-ue/etc/nr-ue.conf
+ healthcheck:
+ test: /bin/bash -c "pgrep nr-uesoftmodem"
+ interval: 10s
+ timeout: 5s
+ retries: 5
diff --git a/ci-scripts/yaml_files/sa_gnb_aerial/docker-compose-ue.yaml b/ci-scripts/yaml_files/sa_gnb_aerial/docker-compose-ue.yaml
new file mode 100644
index 0000000000..15f2f177f4
--- /dev/null
+++ b/ci-scripts/yaml_files/sa_gnb_aerial/docker-compose-ue.yaml
@@ -0,0 +1,61 @@
+services:
+ oai-nr-ue:
+ image: ${REGISTRY-oaisoftwarealliance/}${NRUE_IMG:-oai-nr-ue}:${UE_TAG:-${TAG:-develop}}
+ logging:
+ options:
+ max-file: "1"
+ network_mode: host
+ container_name: oai-nr-ue
+ privileged: true
+ cpuset: 4,6,8,10,12,14,16,18,20,22,24,26,28
+ cap_drop:
+ - ALL
+ cap_add:
+ - NET_ADMIN # for interface bringup
+ - NET_RAW # for ping
+ - SYS_NICE # for performance
+ - IPC_LOCK # for memory locking
+ - SYS_PTRACE # for debugging
+ devices:
+ - /dev/net/tun:/dev/net/tun
+ ulimits:
+ core: -1 # for core dumps
+ #entrypoint: /bin/bash -c "sleep infinity"
+ environment:
+ TZ: UTC
+ #DISPLAY: $DISPLAY #Uncomment for GUI
+ USE_ADDITIONAL_OPTIONS: |
+ --thread-pool 4,6,8,10,12,14,16,18,20,22,24,26
+ --usrp-args type=x4xx,addr=192.168.10.2,clock_source=external,time_source=external
+ --ssb 1478 -r 273 --numerology 1 --band 78 -C 3750000000
+ --num-dl-actors 20
+ --ue-nb-ant-tx 1
+ --ue-nb-ant-rx 1
+ --ue-rxgain 25
+ --ue-txgain 13
+ --uicc0.imsi 001010000000003
+ --ue-fo-compensation -A 90
+ --usrp-tx-thread-config 1
+ --log_config.global_log_options level,nocolor,utc_time
+ # Unused options:
+ # --T_stdout 2
+ # --imscope
+ # --ssb 1478 -r 273 --numerology 1 --band 78 -C 3750000000
+ # --usrp-tx-thread-config 1
+ # --log_config.mac_log_level debug
+ # --log_config.nr_mac_log_level debug
+ # --usrp-tx-thread-config 1 -d
+ # --ssb 194 -r 51 --numerology 1 --band 78 -C 3750000000 #20MHz
+ # --ssb 236 -r 106 --numerology 1 --band 78 -C 3750000000 #40MHz
+ volumes:
+ - ../../conf_files/ue.sa.conf:/opt/oai-nr-ue/etc/nr-ue.conf
+ # UL throughput is worse with 256-qam table
+ - ../../../targets/PROJECTS/GENERIC-NR-5GC/CONF/uecap_ports1.xml:/opt/oai-nr-ue/uecap_ports1.xml
+ #For GUI
+ - ${HOME}/.Xauthority:/root/.Xauthority:rw
+ - /tmp/.X11-unix:/tmp/.X11-unix
+ healthcheck:
+ test: /bin/bash -c "pgrep nr-uesoftmodem"
+ interval: 10s
+ timeout: 5s
+ retries: 5
diff --git a/ci-scripts/yaml_files/sa_gnb_aerial_30MHz/aerial_l1_entrypoint.sh b/ci-scripts/yaml_files/sa_gnb_aerial_30MHz/aerial_l1_entrypoint.sh
new file mode 100755
index 0000000000..c8bac9eb3e
--- /dev/null
+++ b/ci-scripts/yaml_files/sa_gnb_aerial_30MHz/aerial_l1_entrypoint.sh
@@ -0,0 +1,32 @@
+#!/bin/bash
+
+# Check if cuBB_SDK is defined, if not, use default path
+cuBB_Path="${cuBB_SDK:-/opt/nvidia/cuBB}"
+
+cd "$cuBB_Path" || exit 1
+
+# Restart MPS
+# Export variables
+export CUDA_DEVICE_MAX_CONNECTIONS=8
+export CUDA_MPS_PIPE_DIRECTORY=/var
+export CUDA_MPS_LOG_DIRECTORY=/var
+
+# Stop existing MPS
+echo quit | sudo -E nvidia-cuda-mps-control
+
+# Start MPS
+sudo -E nvidia-cuda-mps-control -d
+sudo -E echo start_server -uid 0 | sudo -E nvidia-cuda-mps-control
+
+# Start cuphycontroller_scf
+# Check if an argument is provided
+if [ $# -eq 0 ]; then
+ # No argument provided, use default value
+ argument="P5G_WNC_GH"
+else
+ # Argument provided, use it
+ argument="$1"
+fi
+
+sudo -E "$cuBB_Path"/build.$(uname -m)/cuPHY-CP/cuphycontroller/examples/cuphycontroller_scf "$argument"
+sudo -E ./build.$(uname -m)/cuPHY-CP/gt_common_libs/nvIPC/tests/pcap/pcap_collect
diff --git a/ci-scripts/yaml_files/sa_gnb_aerial_30MHz/cuphycontroller_P5G_WNC_GH.yaml b/ci-scripts/yaml_files/sa_gnb_aerial_30MHz/cuphycontroller_P5G_WNC_GH.yaml
new file mode 100644
index 0000000000..d43e2b17ad
--- /dev/null
+++ b/ci-scripts/yaml_files/sa_gnb_aerial_30MHz/cuphycontroller_P5G_WNC_GH.yaml
@@ -0,0 +1,243 @@
+# SPDX-FileCopyrightText: Copyright (c) 2025 NVIDIA CORPORATION & AFFILIATES. All rights reserved.
+# SPDX-License-Identifier: Apache-2.0
+#
+# Licensed under the Apache License, Version 2.0 (the "License");
+# you may not use this file except in compliance with the License.
+# You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing, software
+# distributed under the License is distributed on an "AS IS" BASIS,
+# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+# See the License for the specific language governing permissions and
+# limitations under the License.
+
+aerial_sdk_version: 25-3-cubb
+l2adapter_filename: l2_adapter_config_P5G_GH.yaml
+aerial_metrics_backend_address: 127.0.0.1:8081
+
+# CPU core shared by all low-priority threads
+low_priority_core: 10
+enable_ptp_svc_monitoring: 0
+ptp_rms_threshold: 20 #ns
+nic_tput_alert_threshold_mbps: 85000
+
+cuphydriver_config:
+ standalone: 0
+ validation: 0
+ num_slots: 8
+ log_level: DBG
+ profiler_sec: 0
+ dpdk_thread: 10
+ dpdk_verbose_logs: 0
+ accu_tx_sched_res_ns: 500
+ accu_tx_sched_disable: 0 #Flag applicable only for CX6-DX : BF3/CX7 HW and beyond support accurate send scheduling directly on timestamp, for CX6-DX this is implemented via software emulation
+ fh_stats_dump_cpu_core: -1
+ pdump_client_thread: -1
+ use_green_contexts: 0
+ use_batched_memcpy: 0 # Experimental feature; requires >= CUDA 12.8
+ mps_sm_pusch: 100
+ mps_sm_pucch: 2
+ mps_sm_prach: 2
+ mps_sm_ul_order: 20
+ mps_sm_pdsch: 102
+ mps_sm_pdcch: 10
+ mps_sm_pbch: 2
+ mps_sm_gpu_comms: 16
+ mps_sm_srs: 16
+ pdsch_fallback: 0
+ dpdk_file_prefix: cuphycontroller
+ nics:
+ - nic: '0000:01:00.0'
+ mtu: 9216
+ cpu_mbufs: 196608
+ uplane_tx_handles: 64
+ txq_size: 8192
+ rxq_size: 16384
+ gpu: 0
+ cus_port_failover: 0
+ gpus:
+ - 0
+ # Set GPUID to the GPU sharing the PCIe switch as NIC
+ # run nvidia-smi topo -m to find out which GPU
+ workers_ul: [4,5]
+ workers_dl: [6,7,8]
+ debug_worker: -1
+ workers_sched_priority: 95
+ prometheus_thread: -1
+ start_section_id_srs: 3072
+ start_section_id_prach: 2048
+ enable_ul_cuphy_graphs: 1
+ enable_dl_cuphy_graphs: 1
+ ul_order_kernel_mode: 0 # 0: Ping-Pong, 1: dual CTA
+ ul_order_timeout_cpu_ns: 8000000
+ ul_order_timeout_log_interval_ns: 1000000000
+ ul_order_timeout_gpu_ns: 3000000
+ ul_order_timeout_gpu_srs_ns: 5200000
+ ul_srs_aggr3_task_launch_offset_ns: 500000
+ ul_order_timeout_gpu_log_enable: 0
+ ul_order_max_rx_pkts: 512
+ ul_order_rx_pkts_timeout_ns: 100000
+ cplane_disable: 0
+ gpu_init_comms_dl: 1
+ cell_group: 1
+ cell_group_num: 1
+ fix_beta_dl: 0
+ bfw_beta_prescaler: 16384
+ pusch_workCancelMode: 2 # set cuphyPuschStatPrms_t workCancelMode field to PUSCH_DEVICE_GRAPHS; this only sets the mode and does not cancel work;
+ # work cancellation (i.e., not launching some of the device graphs) can only occur after an explicit internal
+ # memory write is timely observed by a PUSCH graph.
+ pusch_sinr: 2
+ pusch_rssi: 1
+ pusch_tdi: 1
+ pusch_cfo: 1
+ pusch_dftsofdm: 0
+ pusch_to: 1
+ pusch_select_eqcoeffalgo: 3
+ pusch_select_chestalgo: 1
+ pusch_enable_perprgchest: 0
+ pusch_tbsizecheck: 1
+ pusch_deviceGraphLaunchEn: 1
+ pusch_waitTimeOutPreEarlyHarqUs: 3000
+ pusch_waitTimeOutPostEarlyHarqUs: 3000
+ puxch_polarDcdrListSz: 8
+ enable_cpu_task_tracing: 0
+ enable_prepare_tracing: 0
+ disable_empw: 0 #1=>Disables Multi packet WQE feature
+ cqe_tracer_config:
+ enable_dl_cqe_tracing: 0
+ cqe_trace_cell_mask: 1 #[64 bit mask: Bit0->Cell0, Bit1->Cell1...]
+ cqe_trace_slot_mask: 196800 #[20 bit mask: Bit0->Slot0, Bit1->Slot1...] 196800=>All *6,*7 DL Slots
+ ul_rx_pkt_tracing_level: 0
+ ul_rx_pkt_tracing_level_srs: 0
+ pmu_metrics: 0 #Enable and select PMU metrics, 0=disabled, 1=General Counters (platform agnostic), 2=Topdown Metrics (Grace only), 3=Cache Metrics (Grace only)
+ enable_h2d_copy_thread: 1
+ h2d_copy_thread_cpu_affinity : 11
+ h2d_copy_thread_sched_priority : 95 #0->SCHED_OTHER, >0->Actual
+ split_ul_cuda_streams: 0 # 1=Put UL slot 4 and slot 5 on different streams for DDDSUUDDDD pattern
+ serialize_pucch_pusch: 0 # 1=Force serialization of PUSCH/PUCCH
+ # Note: for Early Harq (EH) order is PUSCH EH -> PUCCH -> PUSCH non EH
+ # for non-Early Harq order is PUCCH -> all PUSCH processing
+ aggr_obj_non_avail_th: 5 # Threshold for consecutive non-availability of Aggregated objects(UL/DL) or DL/UL buffers
+ dl_wait_th_ns:
+ - 500000 #H2D copy wait threshold
+ - 4000000 #cuPHY DL channel wait threshold
+ sendCPlane_timing_error_th_ns : 0
+ sendCPlane_ulbfw_backoff_th_ns: 300000 # ULBFW must be completed by cplane send time - this is the backoff time
+ sendCPlane_dlbfw_backoff_th_ns: 300000 # DLBFW must be completed by cplane send time - this is the backoff time
+ pusch_forcedNumCsi2Bits: 0
+ mMIMO_enable: 0
+ enable_srs: 1
+ ue_mode: 0
+ mCh_segment_proc_enable: 0
+ pusch_aggr_per_ctx: 3
+ prach_aggr_per_ctx: 2
+ pucch_aggr_per_ctx: 4
+ srs_aggr_per_ctx: 3
+ ul_input_buffer_per_cell: 10
+ ul_input_buffer_per_cell_srs: 6
+ max_harq_pools: 384
+ max_harq_tx_count_bundled: 10
+ max_harq_tx_count_non_bundled: 4
+ ok_testbench_config:
+ enable_ok_tb: 0
+ num_ok_tb_slot: 0 #Presently not used
+ max_ru_unhealthy_ul_slots: 100
+ srs_chest_algo_type: 0
+ srs_chest_tol2_normalization_algo_type: 1
+ srs_chest_tol2_constant_scaler: 32768.0
+ bfw_power_normalization_alg_selector: 1
+ total_num_srs_chest_buffers: 6144
+ send_static_bfw_wt_all_cplane: 1
+ ul_pcap_capture_enable: 0
+ ul_pcap_capture_thread_cpu_affinity: 10
+ ul_pcap_capture_thread_sched_priority: 95
+ pcap_logger_ul_cplane_enable: 0
+ pcap_logger_dl_cplane_enable: 0
+ pcap_logger_thread_cpu_affinity: 10
+ pcap_logger_thread_sched_prio: 95
+ pcap_logger_file_save_dir: ./
+ dlc_bfw_enable_divide_per_cell: 0 # Enable/disable dividing DL BFW C-Plane transmission window among multiple cells in a slot
+ ulc_bfw_enable_divide_per_cell: 0 # Enable/disable dividing UL BFW C-Plane transmission window among multiple cells in a slot
+ dlc_alloc_cplane_bfw_txq: 0 # Allocates a second separate queue for BFW DL C-Plane transmission
+ ulc_alloc_cplane_bfw_txq: 1 # Allocates a second separate queue for BFW UL C-Plane transmission
+ #static beam id range
+ static_beam_id_start: 1
+ static_beam_id_end: 16527
+ #dynamic beam id range
+ dynamic_beam_id_start: 16528 #Dynamic beam ID start should be after static beam ID end
+ dynamic_beam_id_end: 32767 #15bit max value
+ bfw_c_plane_chaining_mode: 0 # 0: Default memcpy of BFW weights, 1: CPU mbuf chaining of BFW weights, 2: GPU mbuf chaining
+ enable_l1_param_sanity_check: 0
+ pusch_nMaxLdpcHetConfigs: 32
+ notify_ul_harq_buffer_release: 0
+
+ # data_config:
+ # datalake_core: 12 # This must be set for Data Lake and/or E3 Agent to be used
+ # datalake_db_write_enable: 1 # Enable/disable ClickHouse writes based on datalake_data_types
+ # datalake_samples: 1000000
+ # datalake_address: localhost
+ # datalake_engine: "MergeTree() PRIMARY KEY (TsTaiNs)"
+ # # datalake_drop_tables: 0 # Set to 1 to drop Clickhouse tables at startup
+ # datalake_data_types: [fh, pusch, hest] # Data types to write to ClickHouse DB (all types always collected in memory for E3 Agent):
+ # fh = Fronthaul IQ samples,pusch = PUSCH/FAPI data, hest = channel estimates
+ # datalake_store_failed_pdu: 0 # Set to 1 to store PDU data even when CRC fails
+ # e3_agent_enable: 0 # Enable/disable E3 Agent and dApp capabilities
+ # num_rows_fh: 120
+ # num_rows_pusch: 200
+ # num_rows_hest: 140
+ # e3_pub_port: 5555 # E3 publisher port for indication messages
+ # e3_rep_port: 5556 # E3 reply port for E3AP requests
+ # e3_sub_port: 5560 # E3 subscriber port for Manager messages
+
+ cells:
+ - name: O-RU 0
+ cell_id: 1
+ ru_type: 1
+ # set to 00:00:00:00:00:00 to use the MAC address of the NIC port to use
+ src_mac_addr: 00:00:00:00:00:00
+ dst_mac_addr: e8:c7:cf:ad:12:0b #WNC n78
+ nic: '0000:01:00.0'
+ vlan: 500
+ pcp: 7
+ txq_count_uplane: 1
+ eAxC_id_ssb_pbch: [0, 1, 2, 3]
+ eAxC_id_pdcch: [0, 1, 2, 3]
+ eAxC_id_pdsch: [0, 1, 2, 3]
+ eAxC_id_csirs: [0, 1, 2, 3]
+ eAxC_id_pusch: [0, 1, 2, 3]
+ eAxC_id_pucch: [0, 1, 2, 3]
+ eAxC_id_srs: [8, 9, 10, 11]
+ eAxC_id_prach: [4, 5, 6, 7]
+ dl_iq_data_fmt: {comp_meth: 1, bit_width: 9}
+ ul_iq_data_fmt: {comp_meth: 1, bit_width: 9}
+ section_3_time_offset: 484
+ fs_offset_dl: 10
+ exponent_dl: 4
+ ref_dl: 0
+ fs_offset_ul: -5
+ exponent_ul: 4
+ max_amp_ul: 65504
+ mu: 1
+ T1a_max_up_ns: 280000
+ T1a_max_cp_ul_ns: 405000
+ Ta4_min_ns: 50000
+ Ta4_max_ns: 331000
+ Tcp_adv_dl_ns: 125000
+ ul_u_plane_tx_offset_ns: 280000
+ fh_len_range: 0
+ pusch_prb_stride: 273
+ prach_prb_stride: 12
+ srs_prb_stride: 273
+ pusch_ldpc_max_num_itr_algo_type: 1
+ pusch_fixed_max_num_ldpc_itrs: 10
+ pusch_ldpc_early_termination: 0
+ pusch_ldpc_algo_index: 0
+ pusch_ldpc_flags: 2
+ pusch_ldpc_use_half: 1
+ pusch_nMaxPrb: 273
+ pusch_nMaxRx: 4
+ ul_gain_calibration: 78.68
+ lower_guard_bw: 845
+ tv_pusch: cuPhyChEstCoeffs.h5
diff --git a/ci-scripts/yaml_files/sa_gnb_aerial_30MHz/docker-compose.yaml b/ci-scripts/yaml_files/sa_gnb_aerial_30MHz/docker-compose.yaml
new file mode 100644
index 0000000000..7842077ab3
--- /dev/null
+++ b/ci-scripts/yaml_files/sa_gnb_aerial_30MHz/docker-compose.yaml
@@ -0,0 +1,67 @@
+services:
+ nv-cubb:
+ container_name: nv-cubb
+ deploy:
+ resources:
+ reservations:
+ devices:
+ - driver: nvidia
+ count: all
+ capabilities:
+ - gpu
+ network_mode: host
+ shm_size: 4096m
+ privileged: true
+ stdin_open: true
+ tty: true
+ volumes:
+ - /lib/modules:/lib/modules
+ - /dev/hugepages:/dev/hugepages
+ - /usr/src:/usr/src
+ - ./cuphycontroller_P5G_WNC_GH.yaml:/opt/nvidia/cuBB/cuPHY-CP/cuphycontroller/config/cuphycontroller_P5G_WNC_GH.yaml
+ - ./aerial_l1_entrypoint.sh:/opt/nvidia/cuBB/aerial_l1_entrypoint.sh
+ - /var/log/aerial:/var/log/aerial
+ - ../../../cmake_targets/share:/opt/cuBB/share
+ userns_mode: host
+ ipc: "shareable"
+ image: cubb-build:25-3
+ environment:
+ - cuBB_SDK=/opt/nvidia/cuBB
+ command: bash -c "sudo rm -rf /tmp/phy.log && sudo chmod +x /opt/nvidia/cuBB/aerial_l1_entrypoint.sh && /opt/nvidia/cuBB/aerial_l1_entrypoint.sh"
+ healthcheck:
+ test: ["CMD-SHELL",'grep -q "L1 is ready!" /tmp/phy.log && echo 0 || echo 1']
+ interval: 20s
+ timeout: 5s
+ retries: 5
+ oai-gnb-aerial:
+ cpuset: "13-16"
+ image: ${REGISTRY-oaisoftwarealliance/}${GNB_IMG:-oai-gnb-aerial}:${TAG:-develop}
+ depends_on:
+ nv-cubb:
+ condition: service_healthy
+ cap_drop:
+ - ALL
+ cap_add:
+ - SYS_NICE
+ - IPC_LOCK
+ ipc: "container:nv-cubb"
+ environment:
+ USE_ADDITIONAL_OPTIONS: --log_config.global_log_options level,nocolor,utc_time
+ deploy:
+ resources:
+ reservations:
+ devices:
+ - driver: nvidia
+ count: all
+ capabilities:
+ - gpu
+ network_mode: host
+ shm_size: 4096m
+ volumes:
+ - ../../conf_files/gnb-vnf.sa.band78.78prb.aerial.conf:/opt/oai-gnb/etc/gnb.conf
+ container_name: oai-gnb-aerial
+ healthcheck:
+ test: /bin/bash -c "ps aux | grep -v grep | grep -c softmodem"
+ interval: 10s
+ timeout: 5s
+ retries: 5
diff --git a/cmake_targets/tools/build_helper b/cmake_targets/tools/build_helper
index 64c171276c..2652b29634 100755
--- a/cmake_targets/tools/build_helper
+++ b/cmake_targets/tools/build_helper
@@ -105,19 +105,9 @@ check_supported_distribution() {
case "$distribution" in
"ubuntu24.04") return 0 ;;
"ubuntu22.04") return 0 ;;
- "ubuntu20.04") return 0 ;;
"debian11") return 0 ;;
"debian12") return 0 ;;
- "fedora41") return 0 ;;
- "fedora40") return 0 ;;
- "rhel8.2") return 0 ;;
- "rhel8.3") return 0 ;;
- "rhel8.4") return 0 ;;
- "rhel8.5") return 0 ;;
- "rhel8.6") return 0 ;;
- "rhel8.7") return 0 ;;
- "rhel8.8") return 0 ;;
- "rhel8.9") return 0 ;;
+ "fedora43") return 0 ;;
"rhel9.0") return 0 ;;
"rhel9.1") return 0 ;;
"rhel9.2") return 0 ;;
@@ -127,9 +117,6 @@ check_supported_distribution() {
"rhel9.6") return 0 ;;
"rhel9.7") return 0 ;;
"centos9") return 0 ;; # CentOS stream
- "rocky8.7") return 0 ;;
- "rocky8.8") return 0 ;;
- "rocky8.9") return 0 ;;
"rocky9.1") return 0 ;;
"rocky9.2") return 0 ;;
"rocky9.3") return 0 ;;
@@ -281,7 +268,7 @@ check_install_usrp_uhd_driver(){
$SUDO apt-get update
$SUDO apt-get -y install python3-tk $boost_libs_ubuntu libusb-1.0-0-dev
case "$(get_distribution_release)" in
- "ubuntu20.04" | "ubuntu22.04")
+ "ubuntu22.04")
$SUDO apt-get -y install libuhd-dev libuhd4.5.0 uhd-host
;;
esac
@@ -441,7 +428,7 @@ check_install_additional_tools (){
local optional_packages=""
if [[ "$OS_BASEDISTRO" == "debian" ]]; then
case "$(get_distribution_release)" in
- "ubuntu20.04" | "ubuntu22.04" | "debian11" | "debian12" )
+ "ubuntu22.04" | "debian11" | "debian12" )
optional_packages="python3 python3-pip python3-dev python3-scipy python3-matplotlib python3-pyroute2 universal-ctags"
;;
esac
diff --git a/common/utils/LOG/log.h b/common/utils/LOG/log.h
index a9db2e9c5c..837c6897a6 100644
--- a/common/utils/LOG/log.h
+++ b/common/utils/LOG/log.h
@@ -165,6 +165,7 @@ static const char *const flag_name[] = {FOREACH_FLAG(FLAG_TEXT) ""};
COMP_DEF(M2AP, ) \
COMP_DEF(M3AP, ) \
COMP_DEF(NGAP, ) \
+ COMP_DEF(NRPPA, ) \
COMP_DEF(GNB_APP, log) \
COMP_DEF(NR_RRC, log) \
COMP_DEF(NR_MAC, log) \
diff --git a/common/utils/T/T_messages.txt b/common/utils/T/T_messages.txt
index d2405f9033..818b30b7d0 100644
--- a/common/utils/T/T_messages.txt
+++ b/common/utils/T/T_messages.txt
@@ -586,6 +586,27 @@ ID = LEGACY_NGAP_TRACE
GROUP = ALL:LEGACY_NGAP:LEGACY_GROUP_TRACE:LEGACY
FORMAT = string,log
+ID = LEGACY_NRPPA_INFO
+ DESC = NRPPA legacy logs - info level
+ GROUP = ALL:LEGACY_NRPPA:LEGACY_GROUP_INFO:LEGACY
+ FORMAT = string,log
+ID = LEGACY_NRPPA_ERROR
+ DESC = NRPPA legacy logs - error level
+ GROUP = ALL:LEGACY_NRPPA:LEGACY_GROUP_ERROR:LEGACY
+ FORMAT = string,log
+ID = LEGACY_NRPPA_WARNING
+ DESC = NRPPA legacy logs - warning level
+ GROUP = ALL:LEGACY_NRPPA:LEGACY_GROUP_WARNING:LEGACY
+ FORMAT = string,log
+ID = LEGACY_NRPPA_DEBUG
+ DESC = NRPPA legacy logs - debug level
+ GROUP = ALL:LEGACY_NRPPA:LEGACY_GROUP_DEBUG:LEGACY
+ FORMAT = string,log
+ID = LEGACY_NRPPA_TRACE
+ DESC = NRPPA legacy logs - trace level
+ GROUP = ALL:LEGACY_NRPPA:LEGACY_GROUP_TRACE:LEGACY
+ FORMAT = string,log
+
ID = LEGACY_X2AP_INFO
DESC = X2AP legacy logs - info level
GROUP = ALL:LEGACY_X2AP:LEGACY_GROUP_INFO:LEGACY
@@ -1404,7 +1425,7 @@ ID = UE_PHY_PDCCH_ENERGY
ID = UE_PHY_PDSCH_IQ
DESC = UE PDSCH received IQ data
GROUP = ALL:PHY:GRAPHIC:HEAVY:UE
- FORMAT = int,eNB_ID : int,frame : int,subframe : int,nb_rb : int,N_RB_UL : int,symbols_per_tti : buffer,pusch_comp
+ FORMAT = int,eNB_ID : int,frame : int,subframe : int,nb_rb : int,N_RB_UL : int,symbols_per_tti : buffer,pdsch_comp
ID = UE_PHY_PDSCH_ENERGY
DESC = UE PDSCH 1 energy and threshold
GROUP = ALL:PHY:GRAPHIC:HEAVY:UE
diff --git a/common/utils/T/tracer/CMakeLists.txt b/common/utils/T/tracer/CMakeLists.txt
index e347552d31..d64ea840a9 100644
--- a/common/utils/T/tracer/CMakeLists.txt
+++ b/common/utils/T/tracer/CMakeLists.txt
@@ -37,11 +37,65 @@ add_subdirectory(filter)
add_subdirectory(logger)
add_subdirectory(view)
+# Option to enable record_db tracer tool with ClickHouse database support
+add_boolean_option(T_RECORD_DB OFF "Compile record_db tracer tool with ClickHouse support" OFF)
+
+if(T_RECORD_DB)
+ # Save current BUILD_SHARED_LIBS setting
+ set(SAVED_BUILD_SHARED_LIBS ${BUILD_SHARED_LIBS})
+
+ # Configure options for clickhouse-cpp
+ set(BUILD_SHARED_LIBS ON CACHE BOOL "" FORCE)
+
+ # Save current compiler flags and disable -Werror for zstd
+ set(SAVED_CMAKE_C_FLAGS "${CMAKE_C_FLAGS}")
+
+ # Check if system zstd library is available
+ find_library(ZSTD_LIBRARY NAMES zstd)
+ if(ZSTD_LIBRARY)
+ # Use system zstd library to avoid building legacy zstd code with warnings
+ set(WITH_SYSTEM_ZSTD ON CACHE BOOL "" FORCE)
+ else()
+ # Fall back to bundled zstd and suppress warnings from legacy code
+ # https://github.com/ClickHouse/clickhouse-cpp/blob/master/contrib/zstd/zstd/legacy/zstd_v01.c#L1935
+ set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -Wno-maybe-uninitialized -Wno-uninitialized")
+ endif()
+
+ CPMAddPackage(
+ NAME clickhouse-cpp
+ GITHUB_REPOSITORY ClickHouse/clickhouse-cpp
+ GIT_TAG master
+ )
+
+ # Restore original compiler flags and BUILD_SHARED_LIBS
+ set(CMAKE_C_FLAGS "${SAVED_CMAKE_C_FLAGS}")
+ set(BUILD_SHARED_LIBS ${SAVED_BUILD_SHARED_LIBS} CACHE BOOL "" FORCE)
+
+ CPMAddPackage(
+ NAME fmtlog
+ GITHUB_REPOSITORY MengRao/fmtlog
+ GIT_TAG main
+ GIT_SHALLOW FALSE
+ )
+
+ add_executable(record_db record_db.cpp)
+
+ target_include_directories(record_db PRIVATE ${fmtlog_SOURCE_DIR} ${fmtlog_SOURCE_DIR}/fmt/include)
+ target_link_libraries(record_db PRIVATE tracer_utils clickhouse-cpp-lib fmtlog-shared fmt)
+
+endif() # T_RECORD_DB
+
add_custom_target(T_tools)
add_dependencies(T_tools
record replay extract_config extract_input_subframe
extract_output_subframe extract macpdu2wireshark multi
textlog csv)
+
+# Add record_db to T_tools if it was built
+if(TARGET record_db)
+ add_dependencies(T_tools record_db)
+endif()
+
add_dependencies(nr-softmodem T_tools)
add_dependencies(nr-uesoftmodem T_tools)
add_dependencies(lte-softmodem T_tools)
diff --git a/common/utils/T/tracer/Makefile b/common/utils/T/tracer/Makefile
index cedf8fdbcf..5d0aed4029 100644
--- a/common/utils/T/tracer/Makefile
+++ b/common/utils/T/tracer/Makefile
@@ -1,18 +1,23 @@
CC=gcc
+CXX=g++
CFLAGS=-Wall -g -pthread -DT_TRACER -I. -I../incgen
+CXXFLAGS=-Wall -g -pthread -DT_TRACER -I. -I../incgen -std=c++11
#CFLAGS += -O3 -ffast-math -fomit-frame-pointer
LIBS=-lm
XLIBS=-lX11 -lpng -lXft
-all: record replay extract_config textlog enb ue vcd macpdu2wireshark \
+all: record record_db replay extract_config textlog enb ue vcd macpdu2wireshark \
extract_input_subframe extract_output_subframe to_vcd extract multi \
gnb t_tracer_app_gnb t_tracer_app_ue gnb_mac csv
record: utils.o record.o database.o configuration.o
$(CC) $(CFLAGS) -o record $^ $(LIBS)
+record_db: utils.o record_db.o database.o configuration.o
+ $(CXX) $(CXXFLAGS) -o record_db $^ $(LIBS) -lclickhouse-cpp-lib $(FMTLOG_LIBS)
+
replay: utils.o replay.o
$(CC) $(CFLAGS) -o replay $^ $(LIBS)
@@ -102,8 +107,11 @@ filter/filter.a:
%.o: %.c
$(CC) $(CFLAGS) -c -o $@ $<
+%.o: %.cpp
+ $(CXX) $(CXXFLAGS) -c -o $@ $<
+
clean:
- rm -f *.o core tracer_remote textlog enb ue vcd record replay
+ rm -f *.o core tracer_remote textlog enb ue vcd record record_db replay
rm -f extract_config macpdu2wireshark extract_input_subframe
rm -f extract_output_subframe to_vcd extract multi gnb
rm -f t_tracer_app_gnb t_tracer_app_ue gnb_mac csv
diff --git a/common/utils/T/tracer/record_db.cpp b/common/utils/T/tracer/record_db.cpp
new file mode 100644
index 0000000000..b450f617db
--- /dev/null
+++ b/common/utils/T/tracer/record_db.cpp
@@ -0,0 +1,1324 @@
+/*
+ * Licensed to the OpenAirInterface (OAI) Software Alliance under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The OpenAirInterface Software Alliance licenses this file to You under
+ * the OAI Public License, Version 1.1 (the "License"); you may not use this file
+ * except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.openairinterface.org/?page_id=698
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *-------------------------------------------------------------------------------
+ * For more information about the OpenAirInterface (OAI) Software Alliance:
+ * contact@openairinterface.org
+ */
+
+#include
+#include
+#include
+#include
+#include
+#include
+#include
+#include
+#include
+#include "fmtlog.h"
+
+namespace ch = clickhouse;
+
+extern "C" { // For connect_to(), socket_send(), parse_database(), etc.
+#include
+#include
+#include
+#include
+#include
+#include "database.h"
+#include "utils.h"
+#include "../T_defs.h"
+#include "configuration.h"
+}
+
+const int MAX_QUERY_SIZE = 65536;
+const char *DEFAULT_CLICKHOUSE_HOST = "localhost";
+const int DEFAULT_CLICKHOUSE_PORT = 9000;
+const char *DEFAULT_CLICKHOUSE_DB = "oai";
+
+// Buffer multiple rows per event type and insert when:
+// 1. Buffer reaches BATCH_SIZE rows, OR
+// 2. INSERT_INTERVAL_MS milliseconds have elapsed since last insert
+// This reduces insertion time from ~30ms/event to <1ms/event amortized
+const size_t BATCH_SIZE = 500; // Number of rows to buffer before inserting
+const uint64_t INSERT_INTERVAL_MS = 500; // Insert every 500ms
+const size_t BUFFER_SIZE = 10 * 1024 * 1024; // 10MB
+const size_t BUFFER_MARGIN = 183'456; // UE_PHY_PDSCH_IQ size
+
+// 5G NR timing constants
+const uint64_t NS_PER_SEC = 1000000000ULL;
+const uint64_t FRAME_PERIOD_NS = 10000000ULL; // 10ms per frame
+const int SFN_MAX = 1024;
+// Duration of one full SFN cycle (1024 frames = 10.24 seconds)
+const uint64_t SFN_CYCLE_NS = FRAME_PERIOD_NS * SFN_MAX;
+
+// TAI to UTC offset in seconds (37 leap seconds as of 2017)
+// This may need to be updated when new leap seconds are added
+const int TAI_UTC_OFFSET_SEC = 37;
+
+// GPS epoch is January 6, 1980 00:00:00 UTC
+// Unix epoch is January 1, 1970 00:00:00 UTC
+// Offset = 315964800 seconds
+const uint64_t UNIX_TO_GPS_OFFSET_SEC = 315964800ULL;
+const uint64_t UNIX_TO_GPS_OFFSET_NS = UNIX_TO_GPS_OFFSET_SEC * NS_PER_SEC;
+const uint8_t UTC_TO_GPS_OFFSET_SEC = 18; // As of 2017, GPS time is 18 seconds ahead of UTC time.
+const uint64_t UTC_TO_GPS_OFFSET_NS = UTC_TO_GPS_OFFSET_SEC * NS_PER_SEC;
+
+/**
+ * Calculate duration between two timestamps in nanoseconds
+ * Works with both std::chrono::high_resolution_clock::time_point and uint64_t nanosecond timestamps
+ */
+#define DURATION_NS(start, end) (std::chrono::duration_cast((end) - (start)).count())
+#define DURATION_US(start, end) (std::chrono::duration_cast((end) - (start)).count())
+#define DURATION_MS(start, end) (std::chrono::duration_cast((end) - (start)).count())
+
+/**
+ * Calculate duration between two uint64_t nanosecond timestamps
+ */
+#define DURATION_NS_U64(end_ns, start_ns) ((int64_t)(end_ns) - (int64_t)(start_ns))
+/**
+ * Get slot duration in nanoseconds for a given numerology
+ * mu=0 (15kHz): 1ms, mu=1 (30kHz): 0.5ms, mu=2 (60kHz): 0.25ms, etc.
+ */
+inline uint64_t get_slot_duration_ns(int mu)
+{
+ static const uint64_t slot_durations_ns[] = {
+ 1000000, // mu=0: 1ms
+ 500000, // mu=1: 0.5ms
+ 250000, // mu=2: 0.25ms
+ 125000, // mu=3: 0.125ms
+ 62500 // mu=4: 0.0625ms
+ };
+ if (mu < 0 || mu > 4) {
+ loge("Invalid numerology mu={}, using mu=0", mu);
+ return slot_durations_ns[0];
+ }
+ return slot_durations_ns[mu];
+}
+
+/**
+ * Get number of slots per frame for a given numerology
+ */
+inline int get_slots_per_frame(int mu)
+{
+ static const int slots_per_frame[] = {10, 20, 40, 80, 160};
+ if (mu < 0 || mu > 4) {
+ loge("Invalid numerology mu={}, using mu=0", mu);
+ return slots_per_frame[0];
+ }
+ return slots_per_frame[mu];
+}
+
+/**
+ * Convert Unix/Linux time to GPS time
+ *
+ * @param unix_time_ns Unix time in nanoseconds since Unix epoch (Jan 1, 1970)
+ * @return GPS time in nanoseconds since GPS epoch (Jan 6, 1980)
+ */
+inline uint64_t unix_to_gps_ns(uint64_t unix_time_ns)
+{
+ return unix_time_ns - UNIX_TO_GPS_OFFSET_NS + UTC_TO_GPS_OFFSET_NS;
+}
+
+/**
+ * Convert GPS time to Unix/Linux time
+ *
+ * @param gps_time_ns GPS time in nanoseconds since GPS epoch
+ * @return GPS time in nanoseconds since Unix epoch
+ */
+inline uint64_t gps_to_posix_ns(uint64_t gps_time_ns)
+{
+ return gps_time_ns + UNIX_TO_GPS_OFFSET_NS;
+}
+
+/**
+ * Convert GPS time to Unix/Linux time
+ *
+ * @param gps_time_ns GPS time in nanoseconds since GPS epoch
+ * @return UTC time in nanoseconds since Unix epoch
+ */
+inline uint64_t gps_to_utc_ns(uint64_t gps_time_ns)
+{
+ return gps_to_posix_ns(gps_time_ns) - UTC_TO_GPS_OFFSET_NS;
+}
+
+/**
+ * Calculate the absolute GPS timestamp for a given SFN and slot, given a close time reference in Unix time.
+ *
+ * @param sfn System Frame Number (0-1023)
+ * @param slot Slot number within the frame (depends on numerology)
+ * @param mu Numerology (0-4): 0=15kHz, 1=30kHz, 2=60kHz, 3=120kHz, 4=240kHz
+ * @param reference_utc_ns Reference UTC time in nanoseconds since Unix epoch
+ * @return UTC timestamp in nanoseconds when the SFN/slot was transmitted
+ */
+uint64_t calculate_sfn_slot_gps_time(int sfn, int slot, int mu, uint64_t reference_unix_ns)
+{
+ // Validate inputs
+ if (sfn < 0 || sfn >= SFN_MAX) {
+ loge("Invalid SFN={} (must be 0-1023)", sfn);
+ sfn = sfn % SFN_MAX;
+ return 0;
+ }
+
+ int slots_per_frame = get_slots_per_frame(mu);
+ if (slot < 0 || slot >= slots_per_frame) {
+ loge("Invalid slot={} for mu={} (must be 0-{})", slot, mu, slots_per_frame - 1);
+ slot = slot % slots_per_frame;
+ }
+ // Nanoseconds since GPS epoch start, should be slightly larger than actual transmit time.
+ uint64_t reference_gps_ns = unix_to_gps_ns(reference_unix_ns);
+
+ // Calculate the offset within one SFN cycle for the given SFN/slot
+ uint64_t slot_duration_ns = get_slot_duration_ns(mu);
+ uint64_t offset_in_cycle_ns = (sfn * FRAME_PERIOD_NS) + (slot * slot_duration_ns);
+
+ // Find the number of complete SFN cycles since GPS epoch
+ // We'll use the reference time to determine which SFN cycle we're in
+ uint64_t cycles_since_epoch = reference_gps_ns / SFN_CYCLE_NS;
+
+ // Calculate the base time for the current SFN cycle
+ uint64_t current_cycle_base_ns = cycles_since_epoch * SFN_CYCLE_NS;
+
+ // Calculate the target time within this cycle
+ uint64_t gps_time_ns = current_cycle_base_ns + offset_in_cycle_ns;
+
+ // Check if the GPS time is too far in the future (more than 1 second)
+ // If so, it probably occurred in the previous cycle
+ if (gps_time_ns > reference_gps_ns + NS_PER_SEC) {
+ gps_time_ns -= SFN_CYCLE_NS;
+ }
+ // Check if the target is too far in the past (more than 9.24 seconds)
+ // If so, it probably occurs in the next cycle
+ if (gps_time_ns < reference_gps_ns - (SFN_CYCLE_NS - NS_PER_SEC)) {
+ gps_time_ns += SFN_CYCLE_NS;
+ }
+ return gps_time_ns;
+}
+
+void calculate_sfn_slot_from_gps(uint64_t gps_time_ns, int mu, int *sfn, int *slot)
+{
+ uint64_t phase_ns = gps_time_ns % SFN_CYCLE_NS;
+
+ *sfn = phase_ns / FRAME_PERIOD_NS; // Truncate to integer
+ uint64_t position_in_frame_ns = phase_ns % FRAME_PERIOD_NS; // Remainder
+
+ uint64_t slot_duration_ns = get_slot_duration_ns(mu);
+ *slot = position_in_frame_ns / slot_duration_ns;
+
+ if (*sfn >= SFN_MAX)
+ *sfn = SFN_MAX - 1;
+ int max_slot = get_slots_per_frame(mu) - 1;
+ if (*slot > max_slot)
+ *slot = max_slot;
+}
+
+void calculate_sfn_slot_from_unix(uint64_t unix_time_ns, int mu, int *sfn, int *slot)
+{
+ uint64_t gps_time_ns = unix_to_gps_ns(unix_time_ns);
+ calculate_sfn_slot_from_gps(gps_time_ns, mu, sfn, slot);
+}
+
+void usage(void)
+{
+ printf(
+ "options:\n"
+ " -d this option is mandatory\n"
+ " -on turn log ON for given GROUP or ID\n"
+ " -off turn log OFF for given GROUP or ID\n"
+ " -ON turn all logs ON\n"
+ " -OFF turn all logs OFF\n"
+ " note: you may pass several -on/-off/-ON/-OFF,\n"
+ " they will be processed in order\n"
+ " by default, all is off\n"
+ " -ip connect to given IP address (default %s)\n"
+ " -p connect to given port (default %d)\n"
+ " -ch-host ClickHouse host (default %s)\n"
+ " -ch-port ClickHouse native port (default %d)\n"
+ " -ch-db ClickHouse database name (default %s)\n"
+ " -ch-user ClickHouse user (optional)\n"
+ " -ch-pass ClickHouse password (optional)\n"
+ " -ch-droptables drop the ClickHouse database before run\n"
+ " -debug enable debug logging\n",
+ DEFAULT_REMOTE_IP,
+ DEFAULT_REMOTE_PORT,
+ DEFAULT_CLICKHOUSE_HOST,
+ DEFAULT_CLICKHOUSE_PORT,
+ DEFAULT_CLICKHOUSE_DB);
+ exit(1);
+}
+
+volatile int run = 1;
+
+static int socket_fd = -1;
+
+void force_stop(int x)
+{
+ logi("gently quit...");
+ close(socket_fd);
+ socket_fd = -1;
+ run = 0;
+}
+
+struct clickhouse_config_t {
+ std::string host;
+ int port;
+ std::string database;
+ std::string user;
+ std::string password;
+ std::unique_ptr client;
+ int drop_tables;
+};
+
+// Buffer management structures
+struct DataBuffer {
+ uint8_t *buffer; // Large preallocated buffer
+ size_t buffer_size; // Total size of buffer
+ size_t current_offset; // Current write position in buffer
+ std::shared_ptr inner_col; // Reusable inner column for ClickHouse
+ std::shared_ptr offsets_col; // Reusable offsets column for ClickHouse (cumulative end offsets)
+ bool insert_now;
+
+ DataBuffer(size_t size) : buffer_size(size - BUFFER_MARGIN), current_offset(0), insert_now(false)
+ {
+ buffer = (uint8_t *)malloc(size);
+ if (!buffer) {
+ throw std::bad_alloc();
+ }
+
+ // Create and reserve ClickHouse columns for reuse
+ inner_col = std::make_shared();
+ auto &inner_data = inner_col->GetWritableData();
+ inner_data.reserve(size);
+
+ offsets_col = std::make_shared();
+ offsets_col->Reserve(BATCH_SIZE);
+ }
+
+ ~DataBuffer()
+ {
+ if (buffer) {
+ free(buffer);
+ buffer = nullptr;
+ }
+ }
+
+ // Disable copy constructor and assignment operator
+ DataBuffer(const DataBuffer &) = delete;
+ DataBuffer &operator=(const DataBuffer &) = delete;
+
+ // Copy data into buffer and return offset
+ size_t append(const void *data, size_t length)
+ {
+ if (current_offset + length > buffer_size) {
+ insert_now = true; // If this puts the buffer into the margin, insert it immediately
+ if (length > BUFFER_MARGIN) {
+ loge("DataBuffer full: current_offset={} length={} buffer_size={}", current_offset, length, buffer_size);
+ return (size_t)-1;
+ } // Else we have margin
+ }
+
+ size_t offset = current_offset;
+ memcpy(buffer + current_offset, data, length);
+ current_offset += length;
+
+ offsets_col->Append(current_offset);
+
+ return offset;
+ }
+
+ // Get pointer to data at a specific offset
+ const uint8_t *get_data(size_t offset) const
+ {
+ if (offset >= current_offset) {
+ return nullptr;
+ }
+ return buffer + offset;
+ }
+
+ // Clear buffer for reuse
+ void clear()
+ {
+ current_offset = 0;
+ insert_now = false;
+ inner_col->Clear();
+ offsets_col->Clear();
+ }
+
+ // Get number of entries
+ size_t entry_count() const
+ {
+ return offsets_col->Size();
+ }
+
+ // Get current usage
+ size_t usage() const
+ {
+ return current_offset;
+ }
+};
+
+struct EventBuffer {
+ std::vector columns; // Ordered list of columns
+ std::vector column_names; // Column names in same order
+ std::string event_table_name;
+ size_t row_count;
+ bool insert_now;
+ std::chrono::steady_clock::time_point last_insert_time;
+ database_event_format format;
+ std::string event_name;
+ bool has_frame_slot;
+ std::unordered_map> data_buffers;
+
+ // Cached typed column pointers to avoid expensive As<> casts on every insert
+ std::shared_ptr ts_sw_col;
+ std::shared_ptr ts_tx_col;
+ std::vector> int_cols;
+ std::vector> ulong_cols;
+ std::vector> string_cols;
+ std::unordered_map field_idx_to_typed_col_idx; // Maps format field index to typed column index
+
+ // Performance metrics
+ uint64_t last_column_build_duration_ns;
+ uint64_t last_block_append_duration_ns;
+ uint64_t last_insertion_duration_ns;
+
+ // Statistics tracking
+ uint64_t total_rows; // Total rows inserted since start
+ uint64_t rows_since_print; // Rows since last print
+
+ EventBuffer()
+ : row_count(0),
+ insert_now(false),
+ last_insert_time(std::chrono::steady_clock::now()),
+ has_frame_slot(false),
+ last_column_build_duration_ns(0),
+ last_block_append_duration_ns(0),
+ last_insertion_duration_ns(0),
+ total_rows(0),
+ rows_since_print(0)
+ {
+ }
+};
+
+// Global buffer map: event_id -> EventBuffer
+std::unordered_map g_event_buffers;
+
+/* Convert T format type to ClickHouse type */
+const char *get_clickhouse_type(const char *t_type)
+{
+ if (strcmp(t_type, "int") == 0)
+ return "Int32";
+ if (strcmp(t_type, "ulong") == 0)
+ return "UInt64";
+ if (strcmp(t_type, "string") == 0)
+ return "String";
+ if (strcmp(t_type, "buffer") == 0)
+ return "Array(UInt8)"; // Store as byte array
+ if (strncmp(t_type, "int", 3) == 0)
+ return "Int32";
+ return "String"; // default
+}
+
+/* Execute ClickHouse query */
+int clickhouse_execute(clickhouse_config_t *ch, const char *query)
+{
+ try {
+ ch->client->Execute(query);
+ return 0;
+ } catch (const std::exception &e) {
+ loge("ClickHouse query failed: {}", e.what());
+ return -1;
+ }
+}
+
+/* Initialize ClickHouse connection and create database */
+int clickhouse_init(clickhouse_config_t *ch)
+{
+ char query[1024];
+
+ try {
+ // Set connection options
+ ch::ClientOptions options;
+ options.SetHost(ch->host);
+ options.SetPort(ch->port);
+
+ if (!ch->user.empty()) {
+ options.SetUser(ch->user);
+ }
+ if (!ch->password.empty()) {
+ options.SetPassword(ch->password);
+ }
+
+ // Create client
+ ch->client = std::make_unique(options);
+ /* Handle drop database option */
+ if (ch->drop_tables) {
+ logi("Dropping database: {}", ch->database.c_str());
+ snprintf(query, sizeof(query), "DROP DATABASE IF EXISTS %s", ch->database.c_str());
+
+ if (clickhouse_execute(ch, query) != 0) {
+ loge("Failed to drop database {}", ch->database);
+ exit(1);
+ }
+ }
+
+ // Create database if not exists
+ snprintf(query, sizeof(query), "CREATE DATABASE IF NOT EXISTS %s", ch->database.c_str());
+ if (clickhouse_execute(ch, query) != 0) {
+ loge("Failed to create database");
+ return -1;
+ }
+
+ logi("ClickHouse connection initialized");
+ return 0;
+ } catch (const std::exception &e) {
+ loge("Failed to create ClickHouse client: {}", e.what());
+ return -1;
+ }
+}
+
+/* Create table schema from database format */
+char *create_table_schema(char *schema_buf, const char *event_name, database_event_format format, const char *database)
+{
+ char *p = schema_buf;
+ bool has_frame = false;
+ bool has_slot = false;
+ int i;
+
+ // Start CREATE TABLE statement
+ p += snprintf(p,
+ MAX_QUERY_SIZE - (p - schema_buf),
+ "CREATE TABLE IF NOT EXISTS %s.%s (\n TsSwNs DateTime64(9) DEFAULT now64(9)",
+ database,
+ event_name);
+
+ for (i = 0; i < format.count; i++) {
+ if (strcmp(format.name[i], "frame") == 0)
+ has_frame = true;
+ if (strcmp(format.name[i], "slot") == 0)
+ has_slot = true;
+ if (strcmp(format.name[i], "subframe") == 0)
+ has_slot = true;
+ }
+ if (has_frame && has_slot) {
+ p += snprintf(p, MAX_QUERY_SIZE - (p - schema_buf), ",\n TsTxUtcNs DateTime64(9)");
+ uint64_t timestamp_ns = std::chrono::system_clock::now().time_since_epoch().count() / NS_PER_SEC;
+ if (timestamp_ns > 1861920000) {
+ // 1861920000 -> 2029-01-01 00:00:00
+ logw("WARNING: Linux time {} is greater than 2029-01-01 00:00:00.", timestamp_ns);
+ logw(" Check if a negative leap second has been announced and change UTC_TO_GPS_OFFSET_NS accordingly.",
+ timestamp_ns);
+ }
+ }
+
+ // Add columns from format
+ for (i = 0; i < format.count; i++) {
+ const char *ch_type = get_clickhouse_type(format.type[i]);
+ p += snprintf(p, MAX_QUERY_SIZE - (p - schema_buf), ",\n %s %s", format.name[i], ch_type);
+ }
+
+ p += snprintf(p, MAX_QUERY_SIZE - (p - schema_buf), "\n) ENGINE = Memory();");
+
+#ifdef DB_DEBUG
+ logd("schema: {}", schema_buf);
+#endif
+ return schema_buf;
+}
+
+/* Initialize buffer for an event */
+void init_event_buffer(int event_id, void *database, const char *database_name)
+{
+ char *event_name = event_name_from_id(database, event_id);
+ database_event_format format = get_format(database, event_id);
+
+ if (!event_name)
+ return;
+
+ EventBuffer &buf = g_event_buffers[event_id];
+ buf.event_name = std::string(event_name);
+ buf.event_table_name = std::string(database_name) + "." + event_name;
+ buf.format = format;
+ buf.row_count = 0;
+ buf.last_insert_time = std::chrono::steady_clock::now();
+
+ // Check if this event has frame/slot fields
+ buf.has_frame_slot = false;
+ bool has_frame = false;
+ bool has_slot = false;
+ for (int i = 0; i < format.count; i++) {
+ if (strcmp(format.name[i], "frame") == 0)
+ has_frame = true;
+ if (strcmp(format.name[i], "slot") == 0 || strcmp(format.name[i], "subframe") == 0)
+ has_slot = true;
+ }
+ buf.has_frame_slot = has_frame && has_slot;
+
+ // Create TsSwNs column
+ auto ts_col = std::make_shared(9);
+ ts_col->Reserve(BATCH_SIZE);
+ buf.columns.push_back(ts_col);
+ buf.column_names.push_back("TsSwNs");
+ buf.ts_sw_col = ts_col; // Cache typed pointer
+
+ // Add data columns
+ for (int i = 0; i < format.count; i++) {
+ if (strcmp(format.type[i], "int") == 0) {
+ auto col = std::make_shared();
+ col->Reserve(BATCH_SIZE);
+ buf.columns.push_back(col);
+ buf.column_names.push_back(format.name[i]);
+ buf.field_idx_to_typed_col_idx[i] = buf.int_cols.size();
+ buf.int_cols.push_back(col);
+ } else if (strcmp(format.type[i], "ulong") == 0) {
+ auto col = std::make_shared();
+ col->Reserve(BATCH_SIZE);
+ buf.columns.push_back(col);
+ buf.column_names.push_back(format.name[i]);
+ buf.field_idx_to_typed_col_idx[i] = buf.ulong_cols.size();
+ buf.ulong_cols.push_back(col);
+ } else if (strcmp(format.type[i], "buffer") == 0) {
+ buf.data_buffers[i] = std::make_unique(BUFFER_SIZE);
+
+ // Placeholder - array column will be created from DataBuffer at flush time
+ buf.columns.push_back(nullptr);
+ buf.column_names.push_back(format.name[i]);
+
+ } else if (strcmp(format.type[i], "string") == 0) {
+ auto col = std::make_shared();
+ col->Reserve(BATCH_SIZE);
+ buf.columns.push_back(col);
+ buf.column_names.push_back(format.name[i]);
+ buf.field_idx_to_typed_col_idx[i] = buf.string_cols.size();
+ buf.string_cols.push_back(col);
+ } else {
+ // Default: treat as int
+ auto col = std::make_shared();
+ col->Reserve(BATCH_SIZE);
+ buf.columns.push_back(col);
+ buf.column_names.push_back(format.name[i]);
+ buf.field_idx_to_typed_col_idx[i] = buf.int_cols.size();
+ buf.int_cols.push_back(col);
+ }
+ }
+
+ // Add TsTxUtcNs column if event has frame/slot
+ if (buf.has_frame_slot) {
+ auto gps_col = std::make_shared(9);
+ gps_col->Reserve(BATCH_SIZE);
+ buf.columns.push_back(gps_col);
+ buf.column_names.push_back("TsTxUtcNs");
+ buf.ts_tx_col = gps_col; // Cache typed pointer
+ }
+
+ logi("Initialized buffer for event_id:{:<4} name:{:<31} has_frame_slot:{} columns:{}",
+ event_id,
+ event_name,
+ buf.has_frame_slot,
+ buf.columns.size());
+
+ // Print sizes of buffer fields
+ for (int i = 0; i < format.count; i++) {
+ if (strcmp(format.type[i], "buffer") == 0) {
+ logd(" Buffer field '{}' size={} MB", format.name[i], BUFFER_SIZE / (1024 * 1024));
+ }
+ }
+}
+
+/* Create tables for enabled events */
+int create_tables(clickhouse_config_t *ch, void *database, int *is_on, int number_of_events)
+{
+ int i;
+ size_t longest_table_name = 0;
+
+ for (i = 0; i < number_of_events; i++) {
+ if (!is_on[i])
+ continue;
+
+ char *event_name = event_name_from_id(database, i);
+ database_event_format format = get_format(database, i);
+ if (strlen(event_name) > longest_table_name)
+ longest_table_name = strlen(event_name);
+
+ if (!event_name)
+ continue;
+
+ logd("Creating table for event: {:<31}", event_name);
+
+ char schema[MAX_QUERY_SIZE];
+ create_table_schema(schema, event_name, format, ch->database.c_str());
+
+ if (clickhouse_execute(ch, schema) != 0) {
+ loge("Failed to create table {}", event_name);
+ return -1;
+ }
+
+ // Initialize buffer for this event
+ init_event_buffer(i, database, ch->database.c_str());
+ }
+
+ return (int)longest_table_name;
+}
+
+int insert_buffer(clickhouse_config_t *ch, int event_id)
+{
+ auto it = g_event_buffers.find(event_id);
+ if (it == g_event_buffers.end() || it->second.row_count == 0) {
+ return 0; // Nothing to flush
+ }
+
+ EventBuffer &buf = it->second;
+ buf.insert_now = false;
+
+ auto t_reconstruct_start = std::chrono::high_resolution_clock::now();
+ size_t total_data_size = 0;
+ for (auto &dbuf_pair : buf.data_buffers) {
+ int field_idx = dbuf_pair.first;
+ DataBuffer *dbuf = dbuf_pair.second.get();
+ int col_idx = field_idx + 1; // +1 because TsSwNs is at index 0
+
+ // Build the array column from the DataBuffer
+ size_t num_entries = dbuf->offsets_col->Size();
+
+ if (num_entries != buf.row_count) {
+ loge("DataBuffer entry count mismatch for field '{}': {} entries vs {} rows",
+ buf.format.name[field_idx],
+ num_entries,
+ buf.row_count);
+ }
+
+ // Copy all data to the DataBuffer's inner column (space already reserved in constructor)
+ if (dbuf->current_offset > 0) {
+ auto &inner_data = dbuf->inner_col->GetWritableData();
+ inner_data.resize(dbuf->current_offset); // Set size (doesn't reallocate since already reserved)
+ memcpy(inner_data.data(), dbuf->buffer, dbuf->current_offset);
+ }
+
+ // Create the array column from DataBuffer's columns and store it
+ auto array_col = std::make_shared>(dbuf->inner_col, dbuf->offsets_col);
+ buf.columns[col_idx] = array_col;
+
+ total_data_size += dbuf->current_offset;
+ }
+ auto t_reconstruct_end = std::chrono::high_resolution_clock::now();
+
+ ch::Block block;
+ for (size_t i = 0; i < buf.columns.size(); i++) {
+ if (buf.columns[i]) {
+ block.AppendColumn(buf.column_names[i], buf.columns[i]);
+ } else {
+ loge("Column '{}' at index {} is null when creating block", buf.column_names[i], i);
+ exit(1);
+ }
+ }
+ try {
+ auto t_insert_start = std::chrono::high_resolution_clock::now();
+ ch->client->Insert(buf.event_table_name.c_str(), block);
+ auto t_insert_end = std::chrono::high_resolution_clock::now();
+
+ buf.last_column_build_duration_ns = DURATION_NS(t_reconstruct_start, t_reconstruct_end);
+ buf.last_block_append_duration_ns = DURATION_NS(t_reconstruct_end, t_insert_start);
+ buf.last_insertion_duration_ns = DURATION_NS(t_insert_start, t_insert_end);
+
+ // Clear all columns and re-reserve (skip buffer-type columns which are rebuilt each time)
+ for (size_t i = 0; i < buf.columns.size(); i++) {
+ if (buf.columns[i]) { // Skip nullptr placeholders for buffer-type columns
+ auto col = std::const_pointer_cast(buf.columns[i]);
+ col->Clear();
+ col->Reserve(BATCH_SIZE);
+ }
+ }
+
+ // Reset buffer-type columns back to nullptr
+ for (auto &dbuf_pair : buf.data_buffers) {
+ int field_idx = dbuf_pair.first;
+ int col_idx = field_idx + 1;
+ buf.columns[col_idx] = nullptr;
+ }
+
+ // Clear all DataBuffers
+ for (auto &pair : buf.data_buffers) {
+ pair.second->clear();
+ }
+
+ int rows = buf.row_count;
+ buf.row_count = 0;
+ buf.last_insert_time = std::chrono::steady_clock::now();
+
+ // Update statistics
+ buf.total_rows += rows;
+ buf.rows_since_print += rows;
+
+ return rows;
+ } catch (const std::exception &e) {
+ loge("Failed to insert buffer for event {}: {}", buf.event_name, e.what());
+ return -1;
+ }
+}
+
+/* Flush all buffers to ClickHouse */
+int insert_all_buffers(clickhouse_config_t *ch)
+{
+ int errors = 0;
+ for (auto &pair : g_event_buffers) {
+ if (insert_buffer(ch, pair.first) <= 0) {
+ errors++;
+ }
+ }
+ return errors > 0 ? -1 : 0;
+}
+
+/* Check if buffer should be inserted based on size or time */
+uint8_t should_insert(EventBuffer &buf)
+{
+ if (buf.row_count == 0) {
+ return 0;
+ }
+
+ if (buf.row_count >= BATCH_SIZE) {
+ return 1;
+ }
+
+ if (static_cast(DURATION_MS(buf.last_insert_time, std::chrono::steady_clock::now())) >= INSERT_INTERVAL_MS) {
+ return 2;
+ }
+
+ if (buf.insert_now) {
+ return 3;
+ }
+
+ return 0;
+}
+
+int insert_event(clickhouse_config_t *ch,
+ void *database,
+ int event_id,
+ const char *event_data,
+ int data_length,
+ std::chrono::high_resolution_clock::time_point t_start)
+{
+ auto t_fn_start = std::chrono::high_resolution_clock::now();
+
+ // Get buffer for this event
+ auto it = g_event_buffers.find(event_id);
+ if (it == g_event_buffers.end()) {
+ loge("Buffer not found for event_id {}", event_id);
+ return -1;
+ }
+
+ EventBuffer &buf = it->second;
+ database_event_format format = buf.format;
+ const char *event_name = buf.event_name.c_str();
+ auto t_names_done = std::chrono::high_resolution_clock::now();
+
+ int16_t frame = -1;
+ int16_t slot = -1;
+
+ try {
+ const char *data_ptr = event_data;
+ int remaining = data_length;
+ int buf_len = 0;
+ int i;
+
+ auto t_append_start = std::chrono::high_resolution_clock::now();
+
+ // Append to TsSwNs column using cached pointer
+ buf.ts_sw_col->Append(std::chrono::system_clock::now().time_since_epoch().count());
+
+ // Process data columns
+ for (i = 0; i < format.count && remaining > 0; i++) {
+ if (strcmp(format.type[i], "int") == 0) {
+ int val = 0;
+ if (remaining >= 4) {
+ memcpy(&val, data_ptr, 4);
+ if (strcmp(format.name[i], "frame") == 0)
+ frame = val;
+ else if (strcmp(format.name[i], "slot") == 0)
+ slot = val;
+ else if (strcmp(format.name[i], "subframe") == 0)
+ slot = val;
+ data_ptr += 4;
+ remaining -= 4;
+ }
+
+ int typed_col_idx = buf.field_idx_to_typed_col_idx[i];
+ buf.int_cols[typed_col_idx]->Append(val);
+
+ } else if (strcmp(format.type[i], "ulong") == 0) {
+ uint64_t val = 0;
+ if (remaining >= 8) {
+ memcpy(&val, data_ptr, 8);
+ data_ptr += 8;
+ remaining -= 8;
+ }
+
+ int typed_col_idx = buf.field_idx_to_typed_col_idx[i];
+ buf.ulong_cols[typed_col_idx]->Append(val);
+
+ } else if (strcmp(format.type[i], "buffer") == 0) {
+ buf_len = 0;
+ const char *buf_data = nullptr;
+
+ if (remaining >= 4) {
+ memcpy(&buf_len, data_ptr, 4);
+ data_ptr += 4;
+ remaining -= 4;
+
+ if (buf_len > remaining)
+ buf_len = remaining;
+ if (buf_len > 0)
+ buf_data = data_ptr;
+
+ data_ptr += buf_len;
+ remaining -= buf_len;
+ }
+
+ auto it_dbuf = buf.data_buffers.find(i);
+ if (it_dbuf != buf.data_buffers.end()) {
+ size_t offset = it_dbuf->second->append(buf_data, buf_len);
+
+ buf.insert_now |= it_dbuf->second->insert_now;
+
+ if (offset == (size_t)-1) {
+ loge("DataBuffer full for field '{}', cannot append {} bytes", format.name[i], buf_len);
+ // Handle dropping tail for other columns and insert
+ }
+ }
+ } else if (strcmp(format.type[i], "string") == 0) {
+ std::string str_val;
+ if (remaining >= 4) {
+ int str_len;
+ memcpy(&str_len, data_ptr, 4);
+ data_ptr += 4;
+ remaining -= 4;
+
+ if (str_len > remaining)
+ str_len = remaining;
+ if (str_len > 0)
+ str_val = std::string(data_ptr, str_len);
+
+ data_ptr += str_len;
+ remaining -= str_len;
+ }
+
+ int typed_col_idx = buf.field_idx_to_typed_col_idx[i];
+ buf.string_cols[typed_col_idx]->Append(str_val);
+
+ } else {
+ // Default: treat as int
+ int val = 0;
+ if (remaining >= 4) {
+ memcpy(&val, data_ptr, 4);
+ data_ptr += 4;
+ remaining -= 4;
+ }
+
+ int typed_col_idx = buf.field_idx_to_typed_col_idx[i];
+ buf.int_cols[typed_col_idx]->Append(val);
+ }
+ }
+ auto t_append_data_end = std::chrono::high_resolution_clock::now();
+
+ // Add TsTxUtcNs column if event has frame/slot
+ if (buf.has_frame_slot) {
+ uint64_t timestamp_ns = std::chrono::system_clock::now().time_since_epoch().count();
+ uint64_t gps_elapsed_ns;
+ uint64_t transmit_time_in_utc_ns;
+ auto t_time_calc_start = std::chrono::high_resolution_clock::now();
+
+ if (frame == -1 || slot == -1) { // nr_ue_decode_BCCH_DL_SCH sets frame and slot to -1
+ transmit_time_in_utc_ns = timestamp_ns;
+ } else {
+ gps_elapsed_ns = calculate_sfn_slot_gps_time(frame, slot, 1, timestamp_ns);
+ transmit_time_in_utc_ns = gps_to_utc_ns(gps_elapsed_ns);
+
+ if (0) {
+ int check_frame, check_slot;
+ calculate_sfn_slot_from_unix(transmit_time_in_utc_ns, 1, &check_frame, &check_slot);
+ if (check_frame != frame || check_slot != slot) {
+ loge("ERROR1: sfn/slot check failed: {} {} {} {}", event_name, frame, slot, check_frame, check_slot);
+ }
+ }
+
+ auto t_time_calc_end = std::chrono::high_resolution_clock::now();
+
+ int64_t ref_to_t0_offset_ns = (int64_t)timestamp_ns - (int64_t)transmit_time_in_utc_ns;
+ // Handle sign separately to properly display negative fractional seconds
+ const char *sign = (ref_to_t0_offset_ns < 0) ? "-" : " ";
+ int64_t abs_offset = (ref_to_t0_offset_ns < 0) ? -ref_to_t0_offset_ns : ref_to_t0_offset_ns;
+ int64_t offset_sec = abs_offset / NS_PER_SEC;
+ int64_t offset_ns = abs_offset % NS_PER_SEC;
+
+ if (abs_offset > 50'000'000) { // 50ms
+ logi("{:<31} {:4d}.{:2d} TsSwNs={}.{:09} TsTxUtcNs={}.{:09} delta={}{}.{:09d}, {}",
+ event_name,
+ frame,
+ slot,
+ timestamp_ns / NS_PER_SEC,
+ timestamp_ns % NS_PER_SEC,
+ transmit_time_in_utc_ns / NS_PER_SEC,
+ transmit_time_in_utc_ns % NS_PER_SEC,
+ sign,
+ offset_sec,
+ offset_ns,
+ DURATION_NS(t_time_calc_start, t_time_calc_end));
+ }
+ }
+
+ // Append to TsTxUtcNs column using cached pointer
+ buf.ts_tx_col->Append(transmit_time_in_utc_ns);
+ }
+ auto t_append_ts_end = std::chrono::high_resolution_clock::now();
+
+ // Increment row count
+ buf.row_count++;
+
+ // Check if we should insert this buffer
+ int rows = 0;
+ auto t_insert_start = std::chrono::high_resolution_clock::now();
+ uint8_t insert = should_insert(buf);
+ auto t_insert_should_insert_end = std::chrono::high_resolution_clock::now();
+ if (insert) {
+ rows = insert_buffer(ch, event_id);
+ }
+ auto t_insert_end = std::chrono::high_resolution_clock::now();
+
+ if (insert) {
+ if (DURATION_MS(t_insert_start, t_insert_end) > 5) {
+ logi("Slow Insert: {:<31} {:4d}.{:2d}: {:3d} {:3d} {:5d} {:4d} {:5d} {:4d} {:8d} (ns) {:3d} (ms) rows:{:3d} reason: {}",
+ event_name,
+ frame,
+ slot,
+ DURATION_NS(t_fn_start, t_names_done),
+ DURATION_NS(t_names_done, t_append_start),
+ DURATION_NS(t_append_start, t_append_data_end),
+ DURATION_NS(t_append_data_end, t_append_ts_end),
+ buf.last_column_build_duration_ns,
+ buf.last_block_append_duration_ns,
+ buf.last_insertion_duration_ns,
+ DURATION_MS(t_insert_start, t_insert_end),
+ rows,
+ insert);
+ }
+ } else if (DURATION_US(t_fn_start, t_insert_end) > 50) {
+ logd("Slow saving data: {:<31} {:4d}.{:2d}: {:3d} {:3d} {:5d} {:4d} {:5d} {:4d} {:8d} (ns) buf_len:{:3d} rows:{:3d} ---",
+ event_name,
+ frame,
+ slot,
+ DURATION_NS(t_fn_start, t_names_done),
+ DURATION_NS(t_names_done, t_append_start),
+ DURATION_NS(t_append_start, t_append_data_end),
+ DURATION_NS(t_append_data_end, t_append_ts_end),
+ DURATION_NS(t_append_ts_end, t_insert_start),
+ DURATION_NS(t_insert_start, t_insert_should_insert_end),
+ DURATION_NS(t_insert_should_insert_end, t_insert_end),
+ buf_len,
+ buf.row_count);
+ }
+
+ return 0;
+ } catch (const std::exception &e) {
+ loge("Failed to insert event {}: {}", event_name, e.what());
+ return -1;
+ }
+}
+
+int main(int n, char **v)
+{
+ const char *default_database_filename = "T_messages.txt";
+ char *database_filename = NULL;
+ void *database;
+ const char *ip = DEFAULT_REMOTE_IP;
+ int port = DEFAULT_REMOTE_PORT;
+ char **on_off_name;
+ int *on_off_action;
+ int on_off_n = 0;
+ int *is_on;
+ int number_of_events;
+ int i;
+ char mt;
+ int debug_mode = 0;
+
+ clickhouse_config_t ch_config;
+ ch_config.drop_tables = 0;
+ ch_config.host = DEFAULT_CLICKHOUSE_HOST;
+ ch_config.port = DEFAULT_CLICKHOUSE_PORT;
+ ch_config.database = DEFAULT_CLICKHOUSE_DB;
+
+ /* write on a socket fails if the other end is closed and we get SIGPIPE */
+ if (signal(SIGPIPE, SIG_IGN) == SIG_ERR)
+ abort();
+
+ on_off_name = (char **)malloc(n * sizeof(char *));
+ if (on_off_name == NULL)
+ abort();
+ on_off_action = (int *)malloc(n * sizeof(int));
+ if (on_off_action == NULL)
+ abort();
+
+ for (i = 1; i < n; i++) {
+ if (!strcmp(v[i], "-h") || !strcmp(v[i], "--help"))
+ usage();
+ if (!strcmp(v[i], "-d")) {
+ if (i > n - 2)
+ usage();
+ database_filename = v[++i];
+ continue;
+ }
+ if (!strcmp(v[i], "-ip")) {
+ if (i > n - 2)
+ usage();
+ ip = v[++i];
+ continue;
+ }
+ if (!strcmp(v[i], "-p")) {
+ if (i > n - 2)
+ usage();
+ port = atoi(v[++i]);
+ continue;
+ }
+ if (!strcmp(v[i], "-ch-host")) {
+ if (i > n - 2)
+ usage();
+ ch_config.host = v[++i];
+ continue;
+ }
+ if (!strcmp(v[i], "-ch-port")) {
+ if (i > n - 2)
+ usage();
+ ch_config.port = atoi(v[++i]);
+ continue;
+ }
+ if (!strcmp(v[i], "-ch-db")) {
+ if (i > n - 2)
+ usage();
+ ch_config.database = v[++i];
+ continue;
+ }
+ if (!strcmp(v[i], "-ch-user")) {
+ if (i > n - 2)
+ usage();
+ ch_config.user = v[++i];
+ continue;
+ }
+ if (!strcmp(v[i], "-ch-pass")) {
+ if (i > n - 2)
+ usage();
+ ch_config.password = v[++i];
+ continue;
+ }
+ if (!strcmp(v[i], "-ch-droptables")) {
+ ch_config.drop_tables = 1;
+ continue;
+ }
+ if (!strcmp(v[i], "-debug")) {
+ debug_mode = 1;
+ continue;
+ }
+ if (!strcmp(v[i], "-on")) {
+ if (i > n - 2)
+ usage();
+ on_off_name[on_off_n] = v[++i];
+ on_off_action[on_off_n++] = 1;
+ logi("on: item: {}, on_off_name: {}, on_off_action: {}", v[i], on_off_name[on_off_n - 1], on_off_action[on_off_n - 1]);
+ continue;
+ }
+ if (!strcmp(v[i], "-off")) {
+ if (i > n - 2)
+ usage();
+ on_off_name[on_off_n] = v[++i];
+ on_off_action[on_off_n++] = 0;
+ continue;
+ }
+ if (!strcmp(v[i], "-ON")) {
+ on_off_name[on_off_n] = NULL;
+ on_off_action[on_off_n++] = 1;
+ continue;
+ }
+ if (!strcmp(v[i], "-OFF")) {
+ on_off_name[on_off_n] = NULL;
+ on_off_action[on_off_n++] = 0;
+ continue;
+ }
+ usage();
+ }
+
+ if (database_filename == NULL) {
+ logi("No database file provided, using default: {}", default_database_filename);
+ database_filename = strdup(default_database_filename);
+ }
+
+ database = parse_database(database_filename);
+
+ load_config_file(database_filename);
+
+ number_of_events = number_of_ids(database);
+ logi("Number of events: {}", number_of_events);
+ is_on = (int *)calloc(number_of_events, sizeof(int));
+ if (is_on == NULL) {
+ loge("aborting");
+ abort();
+ }
+
+ for (i = 0; i < on_off_n; i++) {
+ on_off(database, on_off_name[i], is_on, on_off_action[i]);
+ }
+
+ /* Initialize fmtlog for benchmarking */
+ fmtlog::setLogLevel(debug_mode ? fmtlog::DBG : fmtlog::INF);
+ fmtlog::setThreadName("main");
+
+ /* Initialize ClickHouse */
+ if (clickhouse_init(&ch_config) != 0) {
+ loge("Failed to initialize ClickHouse connection");
+ exit(1);
+ }
+
+ /* Create tables for enabled events */
+ int longest_table_name = create_tables(&ch_config, database, is_on, number_of_events);
+ if (longest_table_name < 0) {
+ loge("Failed to create tables");
+ exit(1);
+ }
+
+ socket_fd = connect_to(const_cast(ip), port);
+
+ /* activate selected traces */
+ mt = 1;
+ if (socket_send(socket_fd, &mt, 1) == -1 || socket_send(socket_fd, &number_of_events, sizeof(int)) == -1
+ || socket_send(socket_fd, is_on, number_of_events * sizeof(int)) == -1)
+ abort();
+
+ /* exit on ctrl+c and ctrl+z */
+ if (signal(SIGQUIT, force_stop) == SIG_ERR)
+ abort();
+ if (signal(SIGINT, force_stop) == SIG_ERR)
+ abort();
+ if (signal(SIGTSTP, force_stop) == SIG_ERR)
+ abort();
+
+ OBUF ebuf = {.osize = 0, .omaxsize = 0, .obuf = NULL};
+
+ /* read messages */
+ logi("Tables created, waiting for messages...");
+ int poll_count = 0;
+ auto last_periodic_insert = std::chrono::steady_clock::now();
+ auto last_stats_print = std::chrono::steady_clock::now();
+ const uint64_t STATS_PRINT_INTERVAL_MS = 5000; // Print stats every 5 seconds
+
+ while (run) {
+ int type;
+ int32_t length;
+ char *v;
+ int vpos = 0;
+
+ // Poll fmtlog periodically to insert buffered logs
+ if (++poll_count % 10 == 0) {
+ fmtlog::poll();
+ }
+
+ // Periodic insert check (every 10 messages)
+ if (poll_count % 10 == 0) {
+ auto now = std::chrono::steady_clock::now();
+ auto elapsed_ms =
+ static_cast(std::chrono::duration_cast(now - last_periodic_insert).count());
+
+ if (elapsed_ms >= INSERT_INTERVAL_MS) {
+ for (auto &pair : g_event_buffers) {
+ if (should_insert(pair.second)) {
+ insert_buffer(&ch_config, pair.first);
+ }
+ }
+ last_periodic_insert = now;
+ }
+ if (static_cast(DURATION_MS(last_stats_print, now)) >= STATS_PRINT_INTERVAL_MS) {
+ for (auto &pair : g_event_buffers) {
+ EventBuffer &buf = pair.second;
+ if (buf.rows_since_print > 0)
+ logi(" {:<31} rows: {:8d} total: {:10d}", buf.event_name, buf.rows_since_print, buf.total_rows);
+ buf.rows_since_print = 0;
+ }
+ last_stats_print = now;
+ logi("");
+ }
+ }
+
+ if (fullread(socket_fd, &length, 4) == -1)
+ goto read_error;
+ if (ebuf.omaxsize < length + 4) {
+ ebuf.omaxsize = (length + 4 + 65535) & ~65535;
+ ebuf.obuf = (char *)realloc(ebuf.obuf, ebuf.omaxsize);
+ if (ebuf.obuf == NULL) {
+ loge("out of memory");
+ exit(1);
+ }
+ }
+ v = ebuf.obuf;
+ memcpy(v + vpos, &length, 4);
+ vpos += 4;
+#ifdef T_SEND_TIME
+ if (length < (int32_t)sizeof(struct timespec))
+ goto read_error;
+ if (fullread(socket_fd, v + vpos, sizeof(struct timespec)) == -1)
+ goto read_error;
+ // memcpy(v+vpos, &ts, sizeof(struct timespec));
+ vpos += sizeof(struct timespec);
+ length -= sizeof(struct timespec);
+#endif
+ if (length < (int32_t)sizeof(int))
+ goto read_error;
+ if (fullread(socket_fd, &type, sizeof(int)) == -1)
+ goto read_error;
+ memcpy(v + vpos, &type, sizeof(int));
+ vpos += sizeof(int);
+ length -= sizeof(int);
+ if (fullread(socket_fd, v + vpos, length) == -1)
+ goto read_error;
+
+ auto t_start = std::chrono::high_resolution_clock::now();
+
+ if (type == -1) {
+ append_received_config_chunk(v + vpos, length);
+ } else if (type == -2) {
+ verify_config();
+ } else if (type >= 0 && type < number_of_events && is_on[type]) {
+ if (insert_event(&ch_config, database, type, v + vpos, length, t_start) != 0) {
+ loge("Failed to insert event type {}", type);
+ }
+ }
+ }
+
+read_error:
+ // Flush all remaining buffers before exit
+ logi("Inserting all buffers before exit...");
+ insert_all_buffers(&ch_config);
+
+ // Print final statistics
+ size_t total_rows = 0;
+ for (const auto& pair : g_event_buffers) {
+ total_rows += pair.second.row_count;
+ }
+ logi("Final buffer state: {} events with {} uninserted rows",
+ g_event_buffers.size(), total_rows);
+
+ // Client cleanup is automatic via std::unique_ptr
+ logi("Exiting...");
+
+ // Flush and close fmtlog
+ fmtlog::poll();
+ fmtlog::closeLogFile();
+
+ return 0;
+}
diff --git a/common/utils/actor/actor.h b/common/utils/actor/actor.h
index 023533d2d7..8993916d39 100644
--- a/common/utils/actor/actor.h
+++ b/common/utils/actor/actor.h
@@ -29,7 +29,7 @@
#define SHUTDOWN_ACTOR(ptr) shutdown_actor((Actor_t *)ptr);
-typedef struct Actor_t {
+typedef struct {
notifiedFIFO_t fifo;
bool terminate;
pthread_t thread;
diff --git a/common/utils/actor/tests/test_actor.cpp b/common/utils/actor/tests/test_actor.cpp
index 5f613846a2..a38046e5f8 100644
--- a/common/utils/actor/tests/test_actor.cpp
+++ b/common/utils/actor/tests/test_actor.cpp
@@ -93,7 +93,7 @@ TEST(DISABLED_actor, thread_safety_with_core_affinity)
// Thread safety can be ensured through data separation, here using C inheritance-like
// model
-typedef struct TestActor_t {
+typedef struct {
Actor_t actor;
int count;
} TestActor_t;
diff --git a/common/utils/barrier/barrier.h b/common/utils/barrier/barrier.h
index e27b56e766..78fc36264d 100644
--- a/common/utils/barrier/barrier.h
+++ b/common/utils/barrier/barrier.h
@@ -27,7 +27,7 @@
typedef void (*callback_t)(void*);
/// @brief This thread barrier allows modifying the maximum joins after it is initialized
-typedef struct dynamic_barrier_t {
+typedef struct {
pthread_mutex_t barrier_lock;
int completed_jobs;
int max_joins;
diff --git a/common/utils/ocp_itti/all_msg.h b/common/utils/ocp_itti/all_msg.h
index 377bfc4343..8b74409a3c 100644
--- a/common/utils/ocp_itti/all_msg.h
+++ b/common/utils/ocp_itti/all_msg.h
@@ -14,4 +14,4 @@
#include "openair2/COMMON/f1ap_messages_def.h"
#include "openair2/COMMON/e1ap_messages_def.h"
#include "openair2/COMMON/ngap_messages_def.h"
-
+#include "openair2/COMMON/nrppa_messages_def.h"
diff --git a/common/utils/ocp_itti/intertask_interface.h b/common/utils/ocp_itti/intertask_interface.h
index d23e62365d..353a0bae5a 100644
--- a/common/utils/ocp_itti/intertask_interface.h
+++ b/common/utils/ocp_itti/intertask_interface.h
@@ -230,6 +230,7 @@ typedef struct IttiMsgText_s {
#include
#include
#include
+#include
#include
#include
#include
@@ -294,6 +295,7 @@ typedef struct {
TASK_DEF(TASK_RAL_ENB, 200) \
TASK_DEF(TASK_S1AP, 200) \
TASK_DEF(TASK_NGAP, 200) \
+ TASK_DEF(TASK_NRPPA, 200) \
TASK_DEF(TASK_X2AP, 200) \
TASK_DEF(TASK_M2AP_ENB, 200) \
TASK_DEF(TASK_M2AP_MCE, 200) \
diff --git a/doc/README.md b/doc/README.md
index 8fc53eea24..13a9669f76 100644
--- a/doc/README.md
+++ b/doc/README.md
@@ -121,8 +121,9 @@ The other SDRs (AW2S, LimeSDR, ...) have no READMEs.
## Testing
- [UnitTests.md](./UnitTests.md) explains the unit testing setup
-- Component tests are under `tests/`. Currently, there is a simple CU-UP
- tester, see the corresponding [README.md](../tests/nr-cuup/README.md).
+- Component tests are under `tests/`. Currently, the following component tests are supported
+ - A simple CU-UP tester, see the corresponding [README.md](../tests/nr-cuup/README.md).
+ - A CU-NRPPA tester, see the corresponding [README.md](../tests/nr-cu-nrppa/README.md).
- [TESTBenches.md](./TESTBenches.md) lists the CI setup and links to pipelines
- The CI setup uses a [custom framework](../ci-scripts/README.md) to run
end-to-end tests.
diff --git a/doc/TESTBenches.md b/doc/TESTBenches.md
index f91321012c..c48cdfe5d3 100644
--- a/doc/TESTBenches.md
+++ b/doc/TESTBenches.md
@@ -27,6 +27,7 @@
| groot | Groot | gNB (n77) | B210 (30AD30F) |
| rocket | Rocket | gNB (n77) | B210 (31F8010) |
| raspix | Raspix | COTS UE | Quectel RM520N |
+| jetson1-oai | Jetson1-oai | nrUE | USRP B210 |
> **Note:** The available resources, and their current usage, is indicated here:
> - [Lockable resources of jenkins-oai](https://jenkins-oai.eurecom.fr/lockable-resources/):
@@ -238,6 +239,10 @@ information on how the images are built.
~5G-NR
- gracehopper1-oai
- run channel simulation on CPU and GPU using test_channel_scalability
+- [RAN-SA-AERIAL-OAIUE-CN5G](https://jenkins-oai.eurecom.fr/job/RAN-SA-AERIAL-OAIUE-CN5G/)
+ ~5G-NR ~nrUE
+ - 5G-NR SA test setup: OAI VNF + PNF/NVIDIA CUBB on gracehopper1-oai + WNC RU, OAIUE on jetson1-oai + B210, OAI CN5G
+ - OpenShift cluster for CN deployment and container images for gNB and UE deployment
### RAN-CI-NSA-Trigger
diff --git a/doc/tutorial_resources/oai-cn5g/conf/config.yaml b/doc/tutorial_resources/oai-cn5g/conf/config.yaml
index f18c965ed1..6e55c95bb3 100644
--- a/doc/tutorial_resources/oai-cn5g/conf/config.yaml
+++ b/doc/tutorial_resources/oai-cn5g/conf/config.yaml
@@ -100,6 +100,12 @@ nfs:
port: 8080
api_version: v1
interface_name: eth0
+ lmf:
+ host: oai-lmf
+ sbi:
+ port: 8080
+ api_version: v1
+ interface_name: eth0
#### Common for UDR and AMF
database:
@@ -220,6 +226,20 @@ upf:
- dnn: "ims"
- dnn: "default"
+lmf:
+ http_threads_count: 8
+ gnb_id_bits_count: 28
+ num_gnb: 1
+ trp_info_wait_ms: 500
+ positioning_wait_ms: 500
+ measurement_wait_ms: 500
+ support_features:
+ request_trp_info: no
+ determine_num_gnb: yes
+ use_http2: yes
+ use_fqdn_dns: no
+ register_nrf: yes
+
## DNN configuration
dnns:
- dnn: "oai"
diff --git a/doc/tutorial_resources/oai-cn5g/docker-compose-positioning.yaml b/doc/tutorial_resources/oai-cn5g/docker-compose-positioning.yaml
new file mode 100644
index 0000000000..6b75c22b6b
--- /dev/null
+++ b/doc/tutorial_resources/oai-cn5g/docker-compose-positioning.yaml
@@ -0,0 +1,195 @@
+services:
+ mysql:
+ container_name: "mysql"
+ image: mysql:8.0
+ volumes:
+ - ./database/oai_db.sql:/docker-entrypoint-initdb.d/oai_db.sql
+ - ./healthscripts/mysql-healthcheck.sh:/tmp/mysql-healthcheck.sh
+ environment:
+ - TZ=Europe/Paris
+ - MYSQL_DATABASE=oai_db
+ - MYSQL_USER=test
+ - MYSQL_PASSWORD=test
+ - MYSQL_ROOT_PASSWORD=linux
+ healthcheck:
+ test: /bin/bash -c "/tmp/mysql-healthcheck.sh"
+ interval: 5s
+ timeout: 2s
+ retries: 10
+ networks:
+ public_net:
+ ipv4_address: 192.168.70.131
+
+ ims:
+ container_name: "ims"
+ image: oaisoftwarealliance/ims:latest
+ volumes:
+ - ./conf/sip.conf:/etc/asterisk/sip.conf
+ - ./conf/users.conf:/etc/asterisk/users.conf
+ healthcheck:
+ test: /bin/bash -c "pgrep asterisk"
+ interval: 5s
+ timeout: 2s
+ retries: 10
+ networks:
+ public_net:
+ ipv4_address: 192.168.70.139
+ oai-udr:
+ container_name: "oai-udr"
+ image: oaisoftwarealliance/oai-udr:develop
+ expose:
+ - 80/tcp
+ - 8080/tcp
+ volumes:
+ - ./conf/config.yaml:/openair-udr/etc/config.yaml
+ environment:
+ - TZ=Europe/Paris
+ depends_on:
+ - mysql
+ - oai-nrf
+ networks:
+ public_net:
+ ipv4_address: 192.168.70.136
+ oai-udm:
+ container_name: "oai-udm"
+ image: oaisoftwarealliance/oai-udm:develop
+ expose:
+ - 80/tcp
+ - 8080/tcp
+ volumes:
+ - ./conf/config.yaml:/openair-udm/etc/config.yaml
+ environment:
+ - TZ=Europe/Paris
+ depends_on:
+ - oai-udr
+ networks:
+ public_net:
+ ipv4_address: 192.168.70.137
+ oai-ausf:
+ container_name: "oai-ausf"
+ image: oaisoftwarealliance/oai-ausf:develop
+ expose:
+ - 80/tcp
+ - 8080/tcp
+ volumes:
+ - ./conf/config.yaml:/openair-ausf/etc/config.yaml
+ environment:
+ - TZ=Europe/Paris
+ depends_on:
+ - oai-udm
+ networks:
+ public_net:
+ ipv4_address: 192.168.70.138
+ oai-nrf:
+ container_name: "oai-nrf"
+ image: oaisoftwarealliance/oai-nrf:develop
+ expose:
+ - 80/tcp
+ - 8080/tcp
+ volumes:
+ - ./conf/config.yaml:/openair-nrf/etc/config.yaml
+ environment:
+ - TZ=Europe/Paris
+ networks:
+ public_net:
+ ipv4_address: 192.168.70.130
+ oai-amf:
+ container_name: "oai-amf"
+ image: oaisoftwarealliance/oai-amf:develop
+ expose:
+ - 80/tcp
+ - 8080/tcp
+ - 38412/sctp
+ volumes:
+ - ./conf/config.yaml:/openair-amf/etc/config.yaml
+ environment:
+ - TZ=Europe/Paris
+ depends_on:
+ - mysql
+ - oai-nrf
+ - oai-ausf
+ networks:
+ public_net:
+ ipv4_address: 192.168.70.132
+ oai-lmf:
+ container_name: "oai-lmf"
+ image: oaisoftwarealliance/oai-lmf:develop
+ #image: oai-lmf:psoElementwiseTdoAmeanVarTDoAfilter
+ expose:
+ - 80/tcp
+ - 8080/tcp
+ volumes:
+ - ./conf/config.yaml:/openair-lmf/etc/config.yaml
+ environment:
+ - TZ=Europe/Paris
+ depends_on:
+ - mysql
+ - oai-nrf
+ - oai-amf
+ networks:
+ public_net:
+ ipv4_address: 192.168.70.141
+ oai-smf:
+ container_name: "oai-smf"
+ image: oaisoftwarealliance/oai-smf:develop
+ expose:
+ - 80/tcp
+ - 8080/tcp
+ - 8805/udp
+ volumes:
+ - ./conf/config.yaml:/openair-smf/etc/config.yaml
+ environment:
+ - TZ=Europe/Paris
+ depends_on:
+ - oai-nrf
+ - oai-amf
+ networks:
+ public_net:
+ ipv4_address: 192.168.70.133
+ oai-upf:
+ container_name: "oai-upf"
+ image: oaisoftwarealliance/oai-upf:develop
+ expose:
+ - 2152/udp
+ - 8805/udp
+ volumes:
+ - ./conf/config.yaml:/openair-upf/etc/config.yaml
+ environment:
+ - TZ=Europe/Paris
+ depends_on:
+ - oai-nrf
+ - oai-smf
+ cap_add:
+ - NET_ADMIN
+ - SYS_ADMIN
+ cap_drop:
+ - ALL
+ privileged: true
+ networks:
+ public_net:
+ ipv4_address: 192.168.70.134
+ oai-ext-dn:
+ privileged: true
+ init: true
+ container_name: oai-ext-dn
+ image: oaisoftwarealliance/trf-gen-cn5g:jammy
+ entrypoint: /bin/bash -c \
+ "ip route add 10.0.0.0/16 via 192.168.70.134 dev eth0; ip route; sleep infinity"
+ command: ["/bin/bash", "-c", "trap : SIGTERM SIGINT; sleep infinity & wait"]
+ healthcheck:
+ test: /bin/bash -c "ip r | grep 10.0.0"
+ interval: 5s
+ timeout: 2s
+ retries: 10
+ networks:
+ public_net:
+ ipv4_address: 192.168.70.135
+networks:
+ public_net:
+ driver: bridge
+ name: oai-cn5g-public-net
+ ipam:
+ config:
+ - subnet: 192.168.70.128/26
+ driver_opts:
+ com.docker.network.bridge.name: "oai-cn5g"
diff --git a/doc/tutorial_resources/positioning/InputData.json b/doc/tutorial_resources/positioning/InputData.json
new file mode 100644
index 0000000000..0caebbabba
--- /dev/null
+++ b/doc/tutorial_resources/positioning/InputData.json
@@ -0,0 +1,43 @@
+{
+ "externalClientType": "VALUE_ADDED_SERVICES",
+ "amfId": "128:1:1",
+ "locationQoS": {
+ "hAccuracy": 1.5,
+ "vAccuracy": 1.5,
+ "verticalRequested": true,
+ "responseTime": "LOW_DELAY",
+ "lcsQosClass": "BEST_EFFORT"
+ },
+ "supportedGADShapes": [
+ "POINT",
+ "POINT_UNCERTAINTY_CIRCLE"
+ ],
+ "supi": "imsi-001010000000001",
+ "ncgi": {
+ "plmnId": {
+ "mcc": "001",
+ "mnc": "01"
+ },
+ "nrCellId": "14680064",
+ "nid": "0"
+ },
+ "priority": "HIGHEST_PRIORITY",
+ "velocityRequested": "VELOCITY_IS_NOT_REQUESTED",
+ "lcsServiceType": 127,
+ "ldrType": "UE_AVAILABLE",
+ "hgmlcCallBackURI": "198.168.70.129",
+ "ldrReference": "11",
+ "lirReference": "1",
+ "periodicEventInfo": {
+ "reportingAmount": 10,
+ "reportingInterval": 60
+ },
+ "reportingAccessTypes": [
+ "NR",
+ "NON_3GPP_CONNECTED_TO_5GC"
+ ],
+ "ueConnectivityStates": {
+ "accessType": "3GPP_ACCESS",
+ "connectivitystate": "IDLE"
+ }
+}
diff --git a/docker/Dockerfile.base.ubuntu b/docker/Dockerfile.base.ubuntu
index e13170d303..a51d99bcc5 100644
--- a/docker/Dockerfile.base.ubuntu
+++ b/docker/Dockerfile.base.ubuntu
@@ -51,6 +51,8 @@ RUN apt-get update && \
bison \
flex \
m4 \
+ # libzstd-dev for ClickHouse C++ library
+ libzstd-dev \
# python3-pip for conf template generation
python3-pip \
wget \
diff --git a/docker/Dockerfile.build.ubuntu b/docker/Dockerfile.build.ubuntu
index 2fb391c9cf..b919a1aefc 100644
--- a/docker/Dockerfile.build.ubuntu
+++ b/docker/Dockerfile.build.ubuntu
@@ -52,6 +52,7 @@ RUN \
--cmake-opt -DOAI_VRTSIM_TAPS_CLIENT=ON \
--noavx512 \
--build-tool-opt -k10 \
+ --cmake-opt -DT_RECORD_DB=ON \
--cmake-opt -DCMAKE_C_FLAGS="-Werror" --cmake-opt -DCMAKE_CXX_FLAGS="-Werror" $BUILD_OPTION && \
# Mainly to see if the sanitize option was perfectly executed
echo "---- ldd on executables ----" && \
diff --git a/docker/Dockerfile.gNB.aerial.ubuntu b/docker/Dockerfile.gNB.aerial.ubuntu
index 1e2b41a71d..ac59370b4d 100644
--- a/docker/Dockerfile.gNB.aerial.ubuntu
+++ b/docker/Dockerfile.gNB.aerial.ubuntu
@@ -56,13 +56,15 @@ RUN /bin/sh oaienv && \
cd cmake_targets && \
mkdir -p log && \
./build_oai -c -w AERIAL --gNB --ninja --build-tool-opt -k10 \
- --cmake-opt -DCMAKE_C_FLAGS="-Werror" --cmake-opt -DCMAKE_CXX_FLAGS="-Werror"
+ --cmake-opt -DCMAKE_C_FLAGS="-Werror" --cmake-opt -DCMAKE_CXX_FLAGS="-Werror" \
+ --cmake-opt -DT_RECORD_DB=ON
#start from scratch for target executable
FROM ${UBUNTU_IMAGE} AS oai-gnb-aerial
ENV DEBIAN_FRONTEND=noninteractive
ENV TZ=Europe
+ENV PATH="/opt/oai-gnb/bin:$PATH"
RUN apt-get update && \
apt-get upgrade --yes && \
@@ -85,17 +87,20 @@ RUN apt-get update && \
WORKDIR /opt/oai-gnb/bin
COPY --from=ran-build \
- /oai-ran/cmake_targets/ran_build/build/nr-softmodem ./
+ /oai-ran/cmake_targets/ran_build/build/nr-softmodem \
+ /oai-ran/cmake_targets/ran_build/build/common/utils/T/tracer/record* \
+ ./
+
COPY ./docker/scripts/gnb_entrypoint.sh ./entrypoint.sh
COPY --from=ran-build \
/oai-ran/cmake_targets/ran_build/build/libparams_libconfig.so \
/oai-ran/cmake_targets/ran_build/build/libparams_yaml.so \
+ /oai-ran/cmake_targets/ran_build/build/_deps*/fmtlog-build*/libfmtlog-shared*.so \
+ /oai-ran/cmake_targets/ran_build/build/_deps*/clickhouse-cpp-build*/clickhouse/libclickhouse*.so \
/usr/local/lib/
-#copy files from nvIPC
COPY --from=ran-build \
- /usr/local/lib/libfmtlog-shared.so \
/usr/local/lib/libnvlog.so \
/usr/local/lib/libnvipc.so \
/usr/local/lib/
@@ -113,5 +118,6 @@ WORKDIR /opt/oai-gnb
COPY --from=ran-build /usr/local/bin/yq /usr/local/bin/yq
COPY --from=ran-build /tini /tini
+COPY --from=ran-build /oai-ran/common/utils/T/T_messages.txt ./
ENTRYPOINT ["/tini", "-v", "--", "/opt/oai-gnb/bin/entrypoint.sh"]
CMD ["/opt/oai-gnb/bin/nr-softmodem"]
diff --git a/docker/Dockerfile.nrORU.fhi72.ubuntu b/docker/Dockerfile.nrORU.fhi72.ubuntu
index 67d2fc2da9..637dd941c1 100644
--- a/docker/Dockerfile.nrORU.fhi72.ubuntu
+++ b/docker/Dockerfile.nrORU.fhi72.ubuntu
@@ -25,7 +25,6 @@ FROM ran-build-fhi72:latest AS ran-build
#start from scratch for target executable
FROM ${UBUNTU_IMAGE} AS oai-nr-oru
-ARG BUILD_OPTION
ENV DEBIAN_FRONTEND=noninteractive
ENV TZ=Europe
diff --git a/docker/Dockerfile.nrUE.ubuntu b/docker/Dockerfile.nrUE.ubuntu
index 08c83899b7..c75acf3b41 100644
--- a/docker/Dockerfile.nrUE.ubuntu
+++ b/docker/Dockerfile.nrUE.ubuntu
@@ -36,6 +36,7 @@ FROM ${UBUNTU_IMAGE} AS oai-nr-ue
ARG BUILD_OPTION
ENV DEBIAN_FRONTEND=noninteractive
ENV TZ=Europe/Paris
+ENV PATH="/opt/oai-nr-ue/bin:$PATH"
RUN apt-get update && \
apt-get upgrade --yes && \
@@ -66,6 +67,7 @@ RUN apt-get update && \
iperf3 \
iperf \
libyaml-cpp-dev \
+ libzstd1 \
libnanomsg5 && \
# if the --sanitize option was used to build, additional packages are required
/bin/bash -c 'if [[ "$BUILD_OPTION" = "--sanitize" ]]; then DEBIAN_FRONTEND=noninteractive apt-get install --yes \
@@ -77,6 +79,7 @@ RUN apt-get update && \
WORKDIR /opt/oai-nr-ue/bin
COPY --from=nr-ue-build \
/oai-ran/cmake_targets/ran_build/build/nr-uesoftmodem \
+ /oai-ran/cmake_targets/ran_build/build/common/utils/T/tracer/record* \
./
COPY ./docker/scripts/nr_ue_entrypoint.sh ./entrypoint.sh
@@ -93,10 +96,17 @@ COPY --from=nr-ue-build \
/oai-ran/cmake_targets/ran_build/build/libtelnetsrv.so \
/oai-ran/cmake_targets/ran_build/build/libtelnetsrv_ciUE.so \
/oai-ran/cmake_targets/ran_build/build/libtelnetsrv_5Gue.so \
+ /oai-ran/cmake_targets/ran_build/build/libnrscope.so \
+ /oai-ran/cmake_targets/ran_build/build/libtelnetsrv.so \
/oai-ran/cmake_targets/ran_build/build/libparams_yaml.so \
/oai-ran/cmake_targets/ran_build/build/libvrtsim.so \
+ # Wildcards so it doesn't fail if not present
+ /oai-ran/cmake_targets/ran_build/build/_deps*/fmtlog-build*/libfmtlog-shared*.so \
+ /oai-ran/cmake_targets/ran_build/build/_deps*/clickhouse-cpp-build*/clickhouse/libclickhouse*.so \
/usr/local/lib/
+# /oai-ran/cmake_targets/ran_build/build/libimscope.so \
+
# Now we are copying from builder-image the UHD files.
COPY --from=nr-ue-base /usr/local/bin/uhd_find_devices /usr/local/bin
COPY --from=nr-ue-base /usr/local/lib/libuhd.so.4.8.0 /usr/local/lib
@@ -123,5 +133,6 @@ WORKDIR /opt/oai-nr-ue
COPY --from=nr-ue-base /usr/local/bin/yq /usr/local/bin/yq
COPY --from=nr-ue-base /tini /tini
+COPY --from=nr-ue-build /oai-ran/common/utils/T/T_messages.txt ./
CMD ["/opt/oai-nr-ue/bin/nr-uesoftmodem"]
ENTRYPOINT ["/tini", "-v", "--", "/opt/oai-nr-ue/bin/entrypoint.sh"]
diff --git a/executables/nr-gnb.c b/executables/nr-gnb.c
index c5c1dee427..5413108209 100644
--- a/executables/nr-gnb.c
+++ b/executables/nr-gnb.c
@@ -120,13 +120,7 @@ static void tx_func(processingData_L1tx_t *info)
if (tx_slot_type == NR_DOWNLINK_SLOT || tx_slot_type == NR_MIXED_SLOT || get_softmodem_params()->continuous_tx
|| IS_SOFTMODEM_RFSIM || cfg->analog_beamforming_ve.analog_bf_vendor_ext.value) {
start_meas(&info->gNB->phy_proc_tx);
- phy_procedures_gNB_TX(info->gNB,
- &sched_response.DL_req,
- &sched_response.TX_req,
- &sched_response.UL_dci_req,
- frame_tx,
- slot_tx,
- 1);
+ phy_procedures_gNB_TX(info->gNB, &sched_response.DL_req, &sched_response.TX_req, &sched_response.UL_dci_req, frame_tx,slot_tx);
PHY_VARS_gNB *gNB = info->gNB;
processingData_RU_t syncMsgRU;
diff --git a/executables/nr-ue.c b/executables/nr-ue.c
index 88a8ff84c8..75814596d3 100644
--- a/executables/nr-ue.c
+++ b/executables/nr-ue.c
@@ -225,7 +225,7 @@ static void UE_synch(void *arg) {
ret = sl_nr_slss_search(UE, &syncD->proc, SL_NR_SSB_REPETITION_IN_FRAMES);
} else {
nr_get_carrier_frequencies(UE, &dl_carrier, &ul_carrier);
- ret = nr_initial_sync(&syncD->proc, UE, 2, IS_SA_MODE(get_softmodem_params()), syncD->gscnInfo, syncD->numGscn);
+ ret = nr_initial_sync(&syncD->proc, UE, 2, syncD->gscnInfo, syncD->numGscn);
}
if (ret.cell_detected) {
@@ -486,12 +486,13 @@ static int handle_sync_req_from_mac(PHY_VARS_NR_UE *UE)
UE->UE_scan_carrier = false;
UE->target_Nid_cell = UE->synch_request.synch_req.target_Nid_cell;
- const fapi_nr_ue_carrier_config_t *cfg = &UE->nrUE_config.carrier_config;
+ const fapi_nr_config_request_t *config = &UE->nrUE_config;
+ const fapi_nr_ue_carrier_config_t *cfg = &config->carrier_config;
uint64_t dl_CarrierFreq = get_carrier_frequency(fp->N_RB_DL, fp->numerology_index, cfg->dl_frequency);
uint64_t ul_CarrierFreq = get_carrier_frequency(fp->N_RB_UL, fp->numerology_index, cfg->uplink_frequency);
if (dl_CarrierFreq != fp->dl_CarrierFreq || ul_CarrierFreq != fp->ul_CarrierFreq) {
LOG_I(NR_PHY,
- "[UE %d] RF frequency change: dl %lu->%lu Hz, ul %lu->%lu Hz (from dl_frequency=%u kHz, target_Nid_cell=%d)\n",
+ "[UE %d] SYNC REQ: RF frequency change: dl %lu->%lu Hz, ul %lu->%lu Hz (from dl_frequency=%u kHz, target_Nid_cell=%d)\n",
UE->Mod_id,
fp->dl_CarrierFreq,
dl_CarrierFreq,
@@ -505,6 +506,16 @@ static int handle_sync_req_from_mac(PHY_VARS_NR_UE *UE)
init_symbol_rotation(fp);
}
+ int ssb_start_subcarrier = nr_get_ssb_start_sc(fp->numerology_index,
+ config->ssb_table.ssb_offset_point_a,
+ config->ssb_table.ssb_subcarrier_offset,
+ fp->freq_range);
+ // SSB location can change during for ex: handover on the target cell
+ if (ssb_start_subcarrier != fp->ssb_start_subcarrier) {
+ fp->ssb_start_subcarrier = ssb_start_subcarrier;
+ LOG_I(NR_PHY, "SYNC REQ: SSB location changed:%d\n", fp->ssb_start_subcarrier);
+ }
+
// Apply Doppler based on NTN-Config for target cell
if (UE->nrUE_config.ntn_config.is_targetcell)
apply_ntn_timing_advance_and_doppler(UE, fp, -1);
@@ -726,7 +737,6 @@ void *UE_thread(void *arg)
PHY_VARS_NR_UE *UE = (PHY_VARS_NR_UE *)arg;
const NR_DL_FRAME_PARMS *fp = &UE->frame_parms;
// int tx_enabled = 0;
- c16_t *rxp[fp->nb_antennas_rx];
enum stream_status_e stream_status = STREAM_STATUS_UNSYNC;
fapi_nr_config_request_t *cfg = &UE->nrUE_config;
sl_nr_phy_config_request_t *sl_cfg = NULL;
@@ -780,6 +790,7 @@ void *UE_thread(void *arg)
readFrame(UE, &tmp, duration_rx_to_tx, true);
}
+ c16_t *rxp[fp->nb_antennas_rx];
while (!oai_exit) {
if (syncRunning) {
notifiedFIFO_elt_t *res = pollNotifiedFIFO(&nf);
diff --git a/executables/nr-uesoftmodem.c b/executables/nr-uesoftmodem.c
index 1631332e5e..df4088a87d 100644
--- a/executables/nr-uesoftmodem.c
+++ b/executables/nr-uesoftmodem.c
@@ -240,6 +240,13 @@ static void trigger_deregistration(int sig)
}
}
+void *nrue_ru_start_thread(void *arg)
+{
+ (void)arg;
+ nrue_ru_start();
+ return NULL;
+}
+
int NB_UE_INST = 1;
configmodule_interface_t *uniqCfg = NULL;
nrLDPC_coding_interface_t nrLDPC_coding_interface = {0};
@@ -450,7 +457,11 @@ int main(int argc, char **argv)
load_module_shlib("imscope_record", NULL, 0, PHY_vars_UE_g[0][0]);
}
- nrue_ru_start();
+ // Launch a temporary high-priority thread to start the UE RU, ensuring radio library threads inherit this priority
+ pthread_t ru_start_thread;
+ threadCreate(&ru_start_thread, nrue_ru_start_thread, NULL, "ru_start_thread", -1, OAI_PRIORITY_RT_MAX);
+ int ret = pthread_join(ru_start_thread, NULL);
+ AssertFatal(ret == 0, "pthread_join error %d, errno %d (%s)\n", ret, errno, strerror(errno));
for (int inst = 0; inst < NB_UE_INST; inst++) {
LOG_I(PHY,"Intializing UE Threads for instance %d ...\n", inst);
diff --git a/nfapi/open-nFAPI/pnf/inc/pnf.h b/nfapi/open-nFAPI/pnf/inc/pnf.h
index 2dc2ce9de6..380890e07d 100644
--- a/nfapi/open-nFAPI/pnf/inc/pnf.h
+++ b/nfapi/open-nFAPI/pnf/inc/pnf.h
@@ -20,20 +20,17 @@
#include "nfapi_pnf_interface.h"
+typedef struct pnf_s {
+ nfapi_pnf_config_t _public;
-struct pnf_t {
-
- nfapi_pnf_config_t _public;
-
- int p5_sock;
+ int p5_sock;
uint8_t tx_message_buffer[NFAPI_MAX_PACKED_MESSAGE_SIZE];
uint8_t sctp;
uint8_t terminate;
-};
-
+} pnf_t;
int pnf_connect(pnf_t *pnf);
int pnf_message_pump(pnf_t *pnf);
diff --git a/nfapi/open-nFAPI/pnf/inc/pnf_p7.h b/nfapi/open-nFAPI/pnf/inc/pnf_p7.h
index 3040d9de09..3f6678fc65 100644
--- a/nfapi/open-nFAPI/pnf/inc/pnf_p7.h
+++ b/nfapi/open-nFAPI/pnf/inc/pnf_p7.h
@@ -80,12 +80,10 @@ typedef struct {
} pnf_p7_rx_reassembly_queue_t;
+typedef struct pnf_p7_s {
+ nfapi_pnf_p7_config_t _public;
-struct pnf_p7_t {
-
- nfapi_pnf_p7_config_t _public;
-
- //private data
+ //private data
int p7_sock;
uint8_t terminate;
@@ -138,7 +136,7 @@ struct pnf_p7_t {
pnf_p7_stats_t stats;
pnf_p7_nr_stats_t nr_stats;
-};
+} pnf_p7_t;
int pnf_p7_message_pump(pnf_p7_t* pnf_p7);
int pnf_nr_p7_message_pump(pnf_p7_t* pnf_p7);
diff --git a/nfapi/open-nFAPI/pnf/public_inc/nfapi_pnf_interface.h b/nfapi/open-nFAPI/pnf/public_inc/nfapi_pnf_interface.h
index 306216a1d5..e4f863d7e2 100644
--- a/nfapi/open-nFAPI/pnf/public_inc/nfapi_pnf_interface.h
+++ b/nfapi/open-nFAPI/pnf/public_inc/nfapi_pnf_interface.h
@@ -31,8 +31,8 @@ extern "C" {
#include
#include "openair1/PHY/defs_gNB.h"
-typedef struct pnf_t pnf_t;
-typedef struct pnf_p7_t pnf_p7_t;
+typedef struct pnf_s pnf_t;
+typedef struct pnf_p7_s pnf_p7_t;
/*! This enum is used to describe the states of the pnf
*/
diff --git a/nfapi/open-nFAPI/vnf/inc/vnf.h b/nfapi/open-nFAPI/vnf/inc/vnf.h
index 39769314f4..98dd9df84d 100644
--- a/nfapi/open-nFAPI/vnf/inc/vnf.h
+++ b/nfapi/open-nFAPI/vnf/inc/vnf.h
@@ -20,19 +20,16 @@
#include "nfapi_vnf_interface.h"
-struct vnf_t
-{
+typedef struct vnf_s {
+ nfapi_vnf_config_t _public;
- nfapi_vnf_config_t _public;
-
- uint8_t terminate;
+ uint8_t terminate;
uint8_t sctp;
uint8_t tx_message_buffer[NFAPI_MAX_PACKED_MESSAGE_SIZE];
- uint16_t next_phy_id;
-
-};
+ uint16_t next_phy_id;
+} vnf_t;
int vnf_pack_and_send_p5_message(vnf_t* vnf, uint16_t p5_idx, nfapi_p4_p5_message_header_t* msg, uint16_t msg_len);
diff --git a/nfapi/open-nFAPI/vnf/inc/vnf_p7.h b/nfapi/open-nFAPI/vnf/inc/vnf_p7.h
index 7e04d69b49..47fa6053f1 100644
--- a/nfapi/open-nFAPI/vnf/inc/vnf_p7.h
+++ b/nfapi/open-nFAPI/vnf/inc/vnf_p7.h
@@ -107,11 +107,10 @@ typedef struct nfapi_vnf_p7_connection_info {
} nfapi_vnf_p7_connection_info_t;
-struct vnf_p7_t{
+typedef struct vnf_p7_s {
+ nfapi_vnf_p7_config_t _public;
- nfapi_vnf_p7_config_t _public;
-
- // private data
+ // private data
uint8_t terminate;
nfapi_vnf_p7_connection_info_t* p7_connections;
int socket;
@@ -119,8 +118,8 @@ struct vnf_p7_t{
uint32_t slot_start_time_hr;
uint8_t* rx_message_buffer; // would this be better put in the p7 conenction info?
uint16_t rx_message_buffer_size;
-
-};
+
+} vnf_p7_t;
uint32_t vnf_get_current_time_hr(void);
diff --git a/nfapi/open-nFAPI/vnf/public_inc/nfapi_vnf_interface.h b/nfapi/open-nFAPI/vnf/public_inc/nfapi_vnf_interface.h
index 3f326e841c..7ddc19010d 100644
--- a/nfapi/open-nFAPI/vnf/public_inc/nfapi_vnf_interface.h
+++ b/nfapi/open-nFAPI/vnf/public_inc/nfapi_vnf_interface.h
@@ -30,9 +30,8 @@
extern "C" {
#endif
-typedef struct vnf_t vnf_t;
-typedef struct vnf_p7_t vnf_p7_t;
-
+typedef struct vnf_s vnf_t;
+typedef struct vnf_p7_s vnf_p7_t;
/*! The nfapi VNF phy configuration information
*/
diff --git a/openair1/PHY/CODING/nr_segmentation.c b/openair1/PHY/CODING/nr_segmentation.c
index 57c21a5980..8312471b34 100644
--- a/openair1/PHY/CODING/nr_segmentation.c
+++ b/openair1/PHY/CODING/nr_segmentation.c
@@ -24,9 +24,9 @@
author: Hongzhi WANG (TCL)
date: 12.09.2017
*/
-#include "PHY/defs_nr_UE.h"
-//#include "SCHED/extern.h"
+#include "common/utils/LOG/log.h"
+#include "openair1/PHY/CODING/coding_defs.h"
//#define DEBUG_SEGMENTATION
int32_t nr_segmentation(unsigned char *input_buffer,
@@ -174,8 +174,6 @@ else
return Kb;
}
-
-
#ifdef MAIN
main()
{
diff --git a/openair1/PHY/INIT/nr_init_ue.c b/openair1/PHY/INIT/nr_init_ue.c
index e137bf5b4c..19977b01e3 100644
--- a/openair1/PHY/INIT/nr_init_ue.c
+++ b/openair1/PHY/INIT/nr_init_ue.c
@@ -291,7 +291,7 @@ static void sl_ue_free(PHY_VARS_NR_UE *UE)
}
}
-void term_nr_ue_signal(PHY_VARS_NR_UE *ue, int nb_connected_gNB)
+void term_nr_ue_signal(PHY_VARS_NR_UE *ue)
{
const NR_DL_FRAME_PARMS* fp = &ue->frame_parms;
phy_term_nr_top();
diff --git a/openair1/PHY/INIT/nr_parms.c b/openair1/PHY/INIT/nr_parms.c
index 66f766571d..0e39e19d9e 100644
--- a/openair1/PHY/INIT/nr_parms.c
+++ b/openair1/PHY/INIT/nr_parms.c
@@ -24,6 +24,7 @@
#include "common/utils/LOG/log.h"
#include "executables/softmodem-common.h"
#include "PHY/MODULATION/nr_modulation.h"
+#include "PHY/nr_phy_common/inc/nr_phy_common.h"
/// Subcarrier spacings in Hz indexed by numerology index
static const uint32_t nr_subcarrier_spacing[MAX_NUM_SUBCARRIER_SPACING] = {15e3, 30e3, 60e3, 120e3, 240e3};
@@ -421,16 +422,11 @@ int nr_init_frame_parms_ue(NR_DL_FRAME_PARMS *fp, fapi_nr_config_request_t* conf
fp->samples_per_frame = 10 * fp->samples_per_subframe;
fp->freq_range = get_freq_range_from_freq(fp->dl_CarrierFreq);
- uint8_t sco = 0;
- if (((fp->freq_range == FR1) && (config->ssb_table.ssb_subcarrier_offset < 24)) ||
- ((fp->freq_range == FR2) && (config->ssb_table.ssb_subcarrier_offset < 12))) {
- if (fp->freq_range == FR1)
- sco = config->ssb_table.ssb_subcarrier_offset>>config->ssb_config.scs_common;
- else
- sco = config->ssb_table.ssb_subcarrier_offset;
- }
+ fp->ssb_start_subcarrier = nr_get_ssb_start_sc(config->ssb_config.scs_common,
+ config->ssb_table.ssb_offset_point_a,
+ config->ssb_table.ssb_subcarrier_offset,
+ fp->freq_range);
- fp->ssb_start_subcarrier = (12 * config->ssb_table.ssb_offset_point_a + sco);
set_Lmax(fp);
fp->L_ssb = (((uint64_t) config->ssb_table.ssb_mask_list[0].ssb_mask)<<32) | config->ssb_table.ssb_mask_list[1].ssb_mask;
diff --git a/openair1/PHY/INIT/nr_phy_init.h b/openair1/PHY/INIT/nr_phy_init.h
index ec4a8de71b..ee3122e6e3 100644
--- a/openair1/PHY/INIT/nr_phy_init.h
+++ b/openair1/PHY/INIT/nr_phy_init.h
@@ -34,7 +34,7 @@ int nr_init_frame_parms_ue_sl(NR_DL_FRAME_PARMS *fp,
int threequarter_fs,
uint32_t ofdm_offset_divisor);
int init_nr_ue_signal(PHY_VARS_NR_UE *ue,int nb_connected_eNB);
-void term_nr_ue_signal(PHY_VARS_NR_UE *ue, int nb_connected_gNB);
+void term_nr_ue_signal(PHY_VARS_NR_UE *ue);
void init_nr_ue_transport(PHY_VARS_NR_UE *ue);
void nr_dump_frame_parms(NR_DL_FRAME_PARMS *frame_parms);
void phy_init_nr_gNB(PHY_VARS_gNB *gNB);
diff --git a/openair1/PHY/LTE_ESTIMATION/lte_eNB_measurements.c b/openair1/PHY/LTE_ESTIMATION/lte_eNB_measurements.c
index f1b26c8d4e..755c67435d 100644
--- a/openair1/PHY/LTE_ESTIMATION/lte_eNB_measurements.c
+++ b/openair1/PHY/LTE_ESTIMATION/lte_eNB_measurements.c
@@ -87,12 +87,12 @@ void lte_eNB_I0_measurements(PHY_VARS_eNB *eNB,
measurements->n0_power[aarx] = ((k1*signal_energy(&common_vars->rxdata[aarx][(frame_parms->samples_per_tti<<1) -frame_parms->ofdm_symbol_size],
frame_parms->ofdm_symbol_size)) + k2*measurements->n0_power[aarx])>>10;
//measurements->n0_power[aarx] = (measurements->n0_power[aarx]) * 12*frame_parms->N_RB_DL)/(frame_parms->ofdm_symbol_size);
- measurements->n0_power_dB[aarx] = (unsigned short) dB_fixed(measurements->n0_power[aarx]);
+ measurements->n0_power_dB[aarx] = dB_fixed(measurements->n0_power[aarx]);
measurements->n0_power_tot += measurements->n0_power[aarx];
}
- measurements->n0_power_tot_dB = (unsigned short) dB_fixed(measurements->n0_power_tot);
+ measurements->n0_power_tot_dB = dB_fixed(measurements->n0_power_tot);
measurements->n0_power_tot_dBm = measurements->n0_power_tot_dB - eNB->rx_total_gain_dB;
// printf("n0_power %d\n",measurements->n0_power_tot_dB);
@@ -183,14 +183,14 @@ void lte_eNB_srs_measurements(PHY_VARS_eNB *eNB,
measurements->rx_spatial_power[srs_id][0][aarx]<<=1; // because of noise only in odd samples
- measurements->rx_spatial_power_dB[srs_id][0][aarx] = (unsigned short) dB_fixed(measurements->rx_spatial_power[srs_id][0][aarx]);
+ measurements->rx_spatial_power_dB[srs_id][0][aarx] = dB_fixed(measurements->rx_spatial_power[srs_id][0][aarx]);
measurements->wideband_cqi[srs_id][aarx] = measurements->rx_spatial_power[srs_id][0][aarx];
// measurements->rx_power[UE_id][aarx]/=frame_parms->nb_antennas_tx;
- measurements->wideband_cqi_dB[srs_id][aarx] = (unsigned short) dB_fixed(measurements->wideband_cqi[srs_id][aarx]);
+ measurements->wideband_cqi_dB[srs_id][aarx] = dB_fixed(measurements->wideband_cqi[srs_id][aarx]);
rx_power += measurements->wideband_cqi[srs_id][aarx];
// measurements->rx_avg_power_dB[UE_id] += measurements->rx_power_dB[UE_id][aarx];
}
@@ -206,7 +206,7 @@ void lte_eNB_srs_measurements(PHY_VARS_eNB *eNB,
measurements->wideband_cqi_tot[srs_id] = dB_fixed2(rx_power,2*measurements->n0_power_tot);
// times 2 since we have noise only in the odd carriers of the srs comb
- measurements->rx_rssi_dBm[srs_id] = (int32_t)dB_fixed(rx_power_avg_eNB[srs_id])-eNB->rx_total_gain_dB;
+ measurements->rx_rssi_dBm[srs_id] = dB_fixed(rx_power_avg_eNB[srs_id])-eNB->rx_total_gain_dB;
diff --git a/openair1/PHY/LTE_ESTIMATION/lte_ue_measurements.c b/openair1/PHY/LTE_ESTIMATION/lte_ue_measurements.c
index 86af5fb81c..9abaeb789c 100644
--- a/openair1/PHY/LTE_ESTIMATION/lte_ue_measurements.c
+++ b/openair1/PHY/LTE_ESTIMATION/lte_ue_measurements.c
@@ -254,13 +254,13 @@ void ue_rrc_measurements(PHY_VARS_UE *ue,
// ue->measurements.n0_power[aarx] += (((int32_t)rxF_pss[-64]*rxF_pss[-64])+((int32_t)rxF_pss[-63]*rxF_pss[-63]));
// printf("pssm32 %d\n",ue->measurements.n0_power[aarx]);
- ue->measurements.n0_power_dB[aarx] = (unsigned short) dB_fixed(ue->measurements.n0_power[aarx]/12);
+ ue->measurements.n0_power_dB[aarx] = dB_fixed(ue->measurements.n0_power[aarx]/12);
ue->measurements.n0_power_tot /*+=*/ = ue->measurements.n0_power[aarx];
}
//LOG_I(PHY,"Subframe %d RRC UE MEAS Noise Level %d \n", subframe, ue->measurements.n0_power_tot);
- ue->measurements.n0_power_tot_dB = (unsigned short) dB_fixed(ue->measurements.n0_power_tot/(12*aarx));
+ ue->measurements.n0_power_tot_dB = dB_fixed(ue->measurements.n0_power_tot/(12*aarx));
ue->measurements.n0_power_tot_dBm = ue->measurements.n0_power_tot_dB - ue->rx_total_gain_dB - dB_fixed(ue->frame_parms.ofdm_symbol_size);
} else {
LOG_E(PHY, "Not yet implemented: noise power calculation when prefix length == EXTENDED\n");
@@ -311,11 +311,11 @@ void ue_rrc_measurements(PHY_VARS_UE *ue,
ue->measurements.n0_power[aarx] += (((int32_t)rxF_pss[-66]*rxF_pss[-66])+((int32_t)rxF_pss[-65]*rxF_pss[-65]));
// ue->measurements.n0_power[aarx] += (((int32_t)rxF_pss[-64]*rxF_pss[-64])+((int32_t)rxF_pss[-63]*rxF_pss[-63]));
// printf("pssm32 %d\n",ue->measurements.n0_power[aarx]);
- ue->measurements.n0_power_dB[aarx] = (unsigned short) dB_fixed(ue->measurements.n0_power[aarx]/12);
+ ue->measurements.n0_power_dB[aarx] = dB_fixed(ue->measurements.n0_power[aarx]/12);
ue->measurements.n0_power_tot /*+=*/ = ue->measurements.n0_power[aarx];
}
- ue->measurements.n0_power_tot_dB = (unsigned short) dB_fixed(ue->measurements.n0_power_tot/(12*aarx));
+ ue->measurements.n0_power_tot_dB = dB_fixed(ue->measurements.n0_power_tot/(12*aarx));
ue->measurements.n0_power_tot_dBm = ue->measurements.n0_power_tot_dB - ue->rx_total_gain_dB - dB_fixed(ue->frame_parms.ofdm_symbol_size);
//LOG_I(PHY,"Subframe %d RRC UE MEAS Noise Level %d \n", subframe, ue->measurements.n0_power_tot);
@@ -1034,7 +1034,7 @@ void lte_ue_measurements(PHY_VARS_UE *ue,
if (ue->measurements.rx_spatial_power[eNB_id][aatx][aarx]<0)
ue->measurements.rx_spatial_power[eNB_id][aatx][aarx] = 0; //ue->measurements.n0_power[aarx];
- ue->measurements.rx_spatial_power_dB[eNB_id][aatx][aarx] = (unsigned short) dB_fixed(ue->measurements.rx_spatial_power[eNB_id][aatx][aarx]);
+ ue->measurements.rx_spatial_power_dB[eNB_id][aatx][aarx] = dB_fixed(ue->measurements.rx_spatial_power[eNB_id][aatx][aarx]);
if (aatx==0)
ue->measurements.rx_power[eNB_id][aarx] = ue->measurements.rx_spatial_power[eNB_id][aatx][aarx];
@@ -1042,7 +1042,7 @@ void lte_ue_measurements(PHY_VARS_UE *ue,
ue->measurements.rx_power[eNB_id][aarx] += ue->measurements.rx_spatial_power[eNB_id][aatx][aarx];
} //aatx
- ue->measurements.rx_power_dB[eNB_id][aarx] = (unsigned short) dB_fixed(ue->measurements.rx_power[eNB_id][aarx]);
+ ue->measurements.rx_power_dB[eNB_id][aarx] = dB_fixed(ue->measurements.rx_power[eNB_id][aarx]);
if (aarx==0)
ue->measurements.rx_power_tot[eNB_id] = ue->measurements.rx_power[eNB_id][aarx];
@@ -1050,7 +1050,7 @@ void lte_ue_measurements(PHY_VARS_UE *ue,
ue->measurements.rx_power_tot[eNB_id] += ue->measurements.rx_power[eNB_id][aarx];
} //aarx
- ue->measurements.rx_power_tot_dB[eNB_id] = (unsigned short) dB_fixed(ue->measurements.rx_power_tot[eNB_id]);
+ ue->measurements.rx_power_tot_dB[eNB_id] = dB_fixed(ue->measurements.rx_power_tot[eNB_id]);
} //eNB_id
diff --git a/openair1/PHY/LTE_TRANSPORT/prach.c b/openair1/PHY/LTE_TRANSPORT/prach.c
index 6cb2de68d2..e357825ac6 100644
--- a/openair1/PHY/LTE_TRANSPORT/prach.c
+++ b/openair1/PHY/LTE_TRANSPORT/prach.c
@@ -48,7 +48,7 @@ void rx_prach0(PHY_VARS_eNB *eNB,
uint16_t *max_preamble,
uint16_t *max_preamble_energy,
uint16_t *max_preamble_delay,
- uint16_t *avg_preamble_energy,
+ int16_t *avg_preamble_energy,
uint16_t Nf,
uint8_t tdd_mapindex,
uint8_t br_flag,
@@ -639,7 +639,7 @@ void rx_prach(PHY_VARS_eNB *eNB,
uint16_t *max_preamble,
uint16_t *max_preamble_energy,
uint16_t *max_preamble_delay,
- uint16_t *avg_preamble_energy,
+ int16_t *avg_preamble_energy,
uint16_t Nf,
uint8_t tdd_mapindex,
uint8_t br_flag) {
diff --git a/openair1/PHY/LTE_TRANSPORT/transport_proto.h b/openair1/PHY/LTE_TRANSPORT/transport_proto.h
index 9cf09d7b52..7fad5aa5db 100644
--- a/openair1/PHY/LTE_TRANSPORT/transport_proto.h
+++ b/openair1/PHY/LTE_TRANSPORT/transport_proto.h
@@ -593,7 +593,7 @@ void rx_prach(PHY_VARS_eNB *phy_vars_eNB,RU_t *ru,
uint16_t *max_preamble,
uint16_t *max_preamble_energy,
uint16_t *max_preamble_delay,
- uint16_t *avg_preamble_energy,
+ int16_t *avg_preamble_energy,
uint16_t Nf, uint8_t tdd_mapindex,
uint8_t br_flag
);
diff --git a/openair1/PHY/MODULATION/slot_fep_nr.c b/openair1/PHY/MODULATION/slot_fep_nr.c
index c534ed7eea..99cbf1c652 100644
--- a/openair1/PHY/MODULATION/slot_fep_nr.c
+++ b/openair1/PHY/MODULATION/slot_fep_nr.c
@@ -19,12 +19,10 @@
* contact@openairinterface.org
*/
-#include "PHY/defs_nr_UE.h"
#include "PHY/defs_gNB.h"
#include "PHY/defs_nr_common.h"
#include "modulation_UE.h"
#include "nr_modulation.h"
-#include "PHY/LTE_ESTIMATION/lte_estimation.h"
#include "PHY/NR_UE_ESTIMATION/nr_estimation.h"
#include "PHY/nr_phy_common/inc/nr_phy_common.h"
#include
diff --git a/openair1/PHY/NR_ESTIMATION/nr_ul_channel_estimation.c b/openair1/PHY/NR_ESTIMATION/nr_ul_channel_estimation.c
index b078d2be1c..45fe87e040 100644
--- a/openair1/PHY/NR_ESTIMATION/nr_ul_channel_estimation.c
+++ b/openair1/PHY/NR_ESTIMATION/nr_ul_channel_estimation.c
@@ -500,7 +500,6 @@ int nr_pusch_channel_estimation(PHY_VARS_gNB *gNB,
float beta_dmrs_pusch = get_beta_dmrs(pusch_pdu->num_dmrs_cdm_grps_no_data, pusch_pdu->dmrs_config_type == pusch_dmrs_type2);
int16_t dmrs_scaling = (1 / beta_dmrs_pusch) * (1 << 14);
nr_pusch_dmrs_rx(fp->Ncp,
- Ns,
gold,
pilot,
(1000 + p),
@@ -520,7 +519,7 @@ int nr_pusch_channel_estimation(PHY_VARS_gNB *gNB,
"Num RBs not configured according to 3GPP 38.211 section 6.3.1.4. For PUSCH with transform precoding, num RBs "
"cannot be multiple of any other primenumber other than 2,3,5\n");
AssertFatal(dmrs_seq != NULL, "DMRS low PAPR seq not found, check if DMRS sequences are generated");
- nr_pusch_lowpaprtype1_dmrs_rx(fp->Ncp, Ns, dmrs_seq, pilot, 1000, 0, nb_rb_pusch, 0, pusch_pdu->dmrs_config_type);
+ nr_pusch_lowpaprtype1_dmrs_rx(fp->Ncp, dmrs_seq, pilot, 1000, 0, nb_rb_pusch, 0, pusch_pdu->dmrs_config_type);
#ifdef DEBUG_PUSCH
printf("NR_UL_CHANNEL_EST: index %d, u %d,v %d\n", index, u, v);
LOG_M("gNb_DMRS_SEQ.m", "gNb_DMRS_SEQ", dmrs_seq, 6 * nb_rb_pusch, 1, 1);
@@ -725,8 +724,6 @@ void nr_pusch_ptrs_processing(PHY_VARS_gNB *gNB,
*ptrsReOffset,
*nb_rb,
rel15_ul->rnti,
- nr_tti_rx,
- symbol,
frame_parms->ofdm_symbol_size,
(int16_t *)&pusch_vars->rxdataF_comp[aarx][(symbol * nb_re_pusch)],
gold,
diff --git a/openair1/PHY/NR_REFSIG/dmrs_nr.h b/openair1/PHY/NR_REFSIG/dmrs_nr.h
index 5f17478874..8e275568e3 100644
--- a/openair1/PHY/NR_REFSIG/dmrs_nr.h
+++ b/openair1/PHY/NR_REFSIG/dmrs_nr.h
@@ -33,24 +33,11 @@
#ifndef DMRS_NR_H
#define DMRS_NR_H
-#include "PHY/defs_nr_UE.h"
#include "PHY/types.h"
#include "PHY/NR_REFSIG/ss_pbch_nr.h"
#include "PHY/NR_REFSIG/pss_nr.h"
#include "PHY/NR_REFSIG/sss_nr.h"
-/************** CODE GENERATION ***********************************/
-
-/************** DEFINE ********************************************/
-
-
-/************* STRUCTURES *****************************************/
-
-
-/************** VARIABLES *****************************************/
-
-/************** FUNCTION ******************************************/
-
int pseudo_random_sequence(int M_PN, uint32_t *c, uint32_t cinit);
void lte_gold_new(LTE_DL_FRAME_PARMS *frame_parms, uint32_t lte_gold_table[20][2][14], uint16_t Nid_cell);
uint16_t get_dmrs_freq_idx_ul(uint16_t n, uint8_t k_prime, uint8_t delta, uint8_t dmrs_type);
diff --git a/openair1/PHY/NR_REFSIG/nr_dmrs_rx.c b/openair1/PHY/NR_REFSIG/nr_dmrs_rx.c
index d06ce6d917..bb81bd5ad5 100644
--- a/openair1/PHY/NR_REFSIG/nr_dmrs_rx.c
+++ b/openair1/PHY/NR_REFSIG/nr_dmrs_rx.c
@@ -64,7 +64,6 @@ static inline c16_t get_modulated(const uint32_t *gold_sequence, const int idx_g
}
int nr_pusch_dmrs_rx(nr_prefix_type_t Ncp,
- unsigned int Ns,
const uint32_t *nr_gold_pusch,
c16_t *output,
unsigned short p,
@@ -108,7 +107,6 @@ int nr_pusch_dmrs_rx(nr_prefix_type_t Ncp,
}
int nr_pdsch_dmrs_rx(nr_prefix_type_t Ncp,
- unsigned int Ns,
const unsigned int *nr_gold_pdsch,
c16_t *output,
unsigned short p,
@@ -213,7 +211,6 @@ void nr_gen_ref_conj_symbols(const uint32_t *in, uint32_t length, c16_t *output,
}
int nr_pusch_lowpaprtype1_dmrs_rx(nr_prefix_type_t Ncp,
- unsigned int Ns,
c16_t *dmrs_seq,
c16_t *output,
unsigned short p,
diff --git a/openair1/PHY/NR_REFSIG/nr_refsig.h b/openair1/PHY/NR_REFSIG/nr_refsig.h
index e5a5e73229..87f12adc5a 100644
--- a/openair1/PHY/NR_REFSIG/nr_refsig.h
+++ b/openair1/PHY/NR_REFSIG/nr_refsig.h
@@ -36,7 +36,6 @@ uint32_t *nr_gold_csi_rs(int N_RB_DL, int symbols_per_slot, int slot, int symb,
uint32_t *nr_gold_prs(int nid, int slot, int symbol);
int nr_pdsch_dmrs_rx(nr_prefix_type_t Ncp,
- unsigned int Ns,
const unsigned int *nr_gold_pdsch,
c16_t *output,
unsigned short p,
@@ -56,7 +55,6 @@ void nr_pbch_dmrs_rx(int dmrss, const unsigned int *nr_gold_pbch, c16_t *output,
void nr_pdcch_dmrs_ref(const unsigned int *nr_gold_pdcch, c16_t *output, unsigned short nb_rb_corset);
int nr_pusch_dmrs_rx(nr_prefix_type_t Ncp,
- unsigned int Ns,
const uint32_t *nr_gold_pusch,
c16_t *output,
unsigned short p,
@@ -71,7 +69,6 @@ void nr_generate_modulation_table(void);
extern simde__m128i byte2m128i[256];
int nr_pusch_lowpaprtype1_dmrs_rx(nr_prefix_type_t Ncp,
- unsigned int Ns,
c16_t *dmrs_seq,
c16_t *output,
unsigned short p,
diff --git a/openair1/PHY/NR_REFSIG/pss_nr.h b/openair1/PHY/NR_REFSIG/pss_nr.h
index 07ab520e90..15ae316d74 100644
--- a/openair1/PHY/NR_REFSIG/pss_nr.h
+++ b/openair1/PHY/NR_REFSIG/pss_nr.h
@@ -32,9 +32,8 @@
#ifndef PSS_NR_H
#define PSS_NR_H
-#include "PHY/defs_nr_UE.h"
+#include "PHY/defs_nr_common.h"
#include "PHY/types.h"
-
#include "PHY/NR_REFSIG/ss_pbch_nr.h"
/************** CODE GENERATION ***********************************/
diff --git a/openair1/PHY/NR_REFSIG/ptrs_nr.c b/openair1/PHY/NR_REFSIG/ptrs_nr.c
index f73a01a2d6..53cc36cb26 100644
--- a/openair1/PHY/NR_REFSIG/ptrs_nr.c
+++ b/openair1/PHY/NR_REFSIG/ptrs_nr.c
@@ -194,8 +194,6 @@ void nr_ptrs_cpe_estimation(uint8_t K_ptrs,
uint8_t ptrsReOffset,
uint16_t nb_rb,
uint16_t rnti,
- unsigned char Ns,
- unsigned char symbol,
uint16_t ofdm_symbol_size,
int16_t *rxF_comp,
const uint32_t *gold_seq,
diff --git a/openair1/PHY/NR_REFSIG/ptrs_nr.h b/openair1/PHY/NR_REFSIG/ptrs_nr.h
index 75f526dad5..68e5f503b7 100644
--- a/openair1/PHY/NR_REFSIG/ptrs_nr.h
+++ b/openair1/PHY/NR_REFSIG/ptrs_nr.h
@@ -33,20 +33,6 @@
#ifndef PTRS_NR_H
#define PTRS_NR_H
-#include "PHY/defs_nr_UE.h"
-
-/************** CODE GENERATION ***********************************/
-
-/************** DEFINE ********************************************/
-
-
-/************* STRUCTURES *****************************************/
-
-
-/************** VARIABLES *****************************************/
-
-/************** FUNCTION ******************************************/
-
void set_ptrs_symb_idx(uint16_t *ptrs_symbols,
uint8_t duration_in_symbols,
uint8_t start_symbol,
@@ -86,15 +72,13 @@ int8_t nr_ptrs_process_slot(uint16_t dmrsSymbPos,
uint16_t ptrsSymbPos,
int16_t *estPerSymb,
uint16_t startSymbIdx,
- uint16_t noSymb
- );
+ uint16_t noSymb);
+
/* general function to estimate common phase error based upon PTRS */
void nr_ptrs_cpe_estimation(uint8_t K_ptrs,
uint8_t ptrsReOffset,
uint16_t nb_rb,
uint16_t rnti,
- unsigned char Ns,
- unsigned char symbol,
uint16_t ofdm_symbol_size,
int16_t *rxF_comp,
const uint32_t *gold_seq,
diff --git a/openair1/PHY/NR_REFSIG/sss_nr.h b/openair1/PHY/NR_REFSIG/sss_nr.h
index 8175869205..5bb55ebe2f 100644
--- a/openair1/PHY/NR_REFSIG/sss_nr.h
+++ b/openair1/PHY/NR_REFSIG/sss_nr.h
@@ -33,9 +33,7 @@
#define SSS_NR_H
#include "limits.h"
-#include "PHY/defs_nr_UE.h"
#include "PHY/types.h"
-
#include "pss_nr.h"
/************** DEFINE ********************************************/
diff --git a/openair1/PHY/NR_REFSIG/ul_ref_seq_nr.h b/openair1/PHY/NR_REFSIG/ul_ref_seq_nr.h
index 9ed101f247..845a2cd830 100644
--- a/openair1/PHY/NR_REFSIG/ul_ref_seq_nr.h
+++ b/openair1/PHY/NR_REFSIG/ul_ref_seq_nr.h
@@ -33,11 +33,8 @@
#ifndef LOWPAPR_SEQUENCES_NR_H
#define LOWPAPR_SEQUENCES_NR_H
-#include "PHY/defs_nr_UE.h"
#include "PHY/types.h"
-
#include "PHY/NR_REFSIG/ss_pbch_nr.h"
-
#include "PHY/defs_nr_common.h"
#include "PHY/defs_gNB.h"
diff --git a/openair1/PHY/NR_TRANSPORT/nr_dlsch.c b/openair1/PHY/NR_TRANSPORT/nr_dlsch.c
index 9018aabfde..24cf6b72b6 100644
--- a/openair1/PHY/NR_TRANSPORT/nr_dlsch.c
+++ b/openair1/PHY/NR_TRANSPORT/nr_dlsch.c
@@ -37,6 +37,7 @@
#include "PHY/NR_REFSIG/dmrs_nr.h"
#include "PHY/NR_REFSIG/ptrs_nr.h"
#include "common/utils/nr/nr_common.h"
+#include "PHY/NR_TRANSPORT/nr_transport_common_proto.h"
#include "executables/softmodem-common.h"
#include "SCHED_NR/sched_nr.h"
@@ -261,7 +262,6 @@ static inline int dmrs_case00(c16_t *output,
const int amp,
int sz,
int start_sc,
- int remaining_re,
int dmrs_port,
const int dmrs_Type,
int symbol_sz,
@@ -438,7 +438,6 @@ static inline int do_onelayer(NR_DL_FRAME_PARMS *frame_parms,
amp,
sz,
start_sc,
- remaining_re,
dmrs_port,
dmrs_Type,
symbol_sz,
@@ -772,7 +771,6 @@ static int do_one_dlsch(unsigned char *input_ptr, PHY_VARS_gNB *gNB, NR_gNB_DLSC
void nr_generate_pdsch(PHY_VARS_gNB *gNB, int n_dlsch, NR_gNB_DLSCH_t *dlsch_array, int frame, int slot)
{
- NR_DL_FRAME_PARMS *frame_parms = &gNB->frame_parms;
time_stats_t *dlsch_encoding_stats = &gNB->dlsch_encoding_stats;
time_stats_t *tinput = &gNB->tinput;
time_stats_t *tprep = &gNB->tprep;
@@ -831,7 +829,6 @@ void nr_generate_pdsch(PHY_VARS_gNB *gNB, int n_dlsch, NR_gNB_DLSCH_t *dlsch_arr
dlsch_array,
frame,
slot,
- frame_parms,
output,
tinput,
tprep,
diff --git a/openair1/PHY/NR_TRANSPORT/nr_dlsch.h b/openair1/PHY/NR_TRANSPORT/nr_dlsch.h
index 0a82b2c47f..09de55da74 100644
--- a/openair1/PHY/NR_TRANSPORT/nr_dlsch.h
+++ b/openair1/PHY/NR_TRANSPORT/nr_dlsch.h
@@ -42,7 +42,6 @@ int nr_dlsch_encoding(PHY_VARS_gNB *gNB,
NR_gNB_DLSCH_t *dlsch_array,
int frame,
uint8_t slot,
- NR_DL_FRAME_PARMS *frame_parms,
unsigned char *output,
time_stats_t *tinput,
time_stats_t *tprep,
diff --git a/openair1/PHY/NR_TRANSPORT/nr_dlsch_coding.c b/openair1/PHY/NR_TRANSPORT/nr_dlsch_coding.c
index 8a73d7754a..b2e7772a36 100644
--- a/openair1/PHY/NR_TRANSPORT/nr_dlsch_coding.c
+++ b/openair1/PHY/NR_TRANSPORT/nr_dlsch_coding.c
@@ -106,7 +106,6 @@ int nr_dlsch_encoding(PHY_VARS_gNB *gNB,
NR_gNB_DLSCH_t *dlsch_array,
int frame,
uint8_t slot,
- NR_DL_FRAME_PARMS *frame_parms,
unsigned char *output,
time_stats_t *tinput,
time_stats_t *tprep,
diff --git a/openair1/PHY/NR_TRANSPORT/nr_prs.c b/openair1/PHY/NR_TRANSPORT/nr_prs.c
index be1bd8adb8..207a94447d 100644
--- a/openair1/PHY/NR_TRANSPORT/nr_prs.c
+++ b/openair1/PHY/NR_TRANSPORT/nr_prs.c
@@ -27,12 +27,7 @@
//#define DEBUG_PRS_MOD
//#define DEBUG_PRS_MAP
-int nr_generate_prs(int slot,
- c16_t *txdataF,
- int16_t amp,
- prs_config_t *prs_cfg,
- nfapi_nr_config_request_scf_t *config,
- const NR_DL_FRAME_PARMS *frame_parms)
+int nr_generate_prs(int slot, c16_t *txdataF, int16_t amp, prs_config_t *prs_cfg, const NR_DL_FRAME_PARMS *frame_parms)
{
int k_prime = 0, k = 0, idx;
diff --git a/openair1/PHY/NR_TRANSPORT/nr_transport_proto.h b/openair1/PHY/NR_TRANSPORT/nr_transport_proto.h
index 29ae5bb612..a38bf9b6bb 100644
--- a/openair1/PHY/NR_TRANSPORT/nr_transport_proto.h
+++ b/openair1/PHY/NR_TRANSPORT/nr_transport_proto.h
@@ -40,12 +40,7 @@
NR_gNB_PHY_STATS_t *get_phy_stats(PHY_VARS_gNB *gNB, uint16_t rnti);
-int nr_generate_prs(int slot,
- c16_t *txdataF,
- int16_t amp,
- prs_config_t *prs_cfg,
- nfapi_nr_config_request_scf_t *config,
- const NR_DL_FRAME_PARMS *frame_parms);
+int nr_generate_prs(int slot, c16_t *txdataF, int16_t amp, prs_config_t *prs_cfg, const NR_DL_FRAME_PARMS *frame_parms);
/*!
\fn int nr_generate_pss
@@ -224,7 +219,6 @@ void nr_fill_srs(PHY_VARS_gNB *gNB,
int nr_get_srs_signal(PHY_VARS_gNB *gNB,
c16_t **rxdataF,
- frame_t frame,
slot_t slot,
nfapi_nr_srs_pdu_t *srs_pdu,
nr_srs_info_t *nr_srs_info,
diff --git a/openair1/PHY/NR_TRANSPORT/pucch_rx.c b/openair1/PHY/NR_TRANSPORT/pucch_rx.c
index 61bdce06b2..aa3a6e5907 100644
--- a/openair1/PHY/NR_TRANSPORT/pucch_rx.c
+++ b/openair1/PHY/NR_TRANSPORT/pucch_rx.c
@@ -1177,7 +1177,7 @@ void nr_decode_pucch2(PHY_VARS_gNB *gNB,
uint64_t decodedPayload[nb_symbols];
memset(decodedPayload,0,sizeof(decodedPayload));
- uint8_t corr_dB;
+ int8_t corr_dB;
int decoderState = 2;
if (pucch2_levdB < gNB->measurements.n0_subband_power_avg_dB + (gNB->pucch0_thres / 10))
decoderState = 1; // assuming missed detection, only attempt to decode for polar case (with CRC)
@@ -1372,67 +1372,3 @@ void nr_decode_pucch2(PHY_VARS_gNB *gNB,
uci_pdu->pduBitmap|=8;
}
}
-
-void nr_dump_uci_stats(FILE *fd,PHY_VARS_gNB *gNB,int frame) {
- int strpos = 0;
- char output[16384];
-
- for (int i = 0; i < MAX_MOBILES_PER_GNB; i++) {
- NR_gNB_PHY_STATS_t *stats = &gNB->phy_stats[i];
- if (!stats->active)
- return;
- NR_gNB_UCI_STATS_t *uci_stats = &stats->uci_stats;
- if (uci_stats->pucch0_sr_trials > 0)
- strpos += sprintf(output + strpos,
- "UCI %d RNTI %x: pucch0_sr_trials %d, pucch0_n00 %d dB, pucch0_n01 %d dB, pucch0_sr_thres %d dB, current "
- "pucch1_stat0 %d dB, current pucch1_stat1 %d dB, positive SR count %d\n",
- i,
- stats->rnti,
- uci_stats->pucch0_sr_trials,
- uci_stats->pucch0_n00,
- uci_stats->pucch0_n01,
- uci_stats->pucch0_sr_thres,
- dB_fixed(uci_stats->current_pucch0_sr_stat0),
- dB_fixed(uci_stats->current_pucch0_sr_stat1),
- uci_stats->pucch0_positive_SR);
- if (uci_stats->pucch01_trials > 0)
- strpos += sprintf(output + strpos,
- "UCI %d RNTI %x: pucch01_trials %d, pucch0_n00 %d dB, pucch0_n01 %d dB, pucch0_thres %d dB, current "
- "pucch0_stat0 %d dB, current pucch1_stat1 %d dB, pucch01_DTX %d\n",
- i,
- stats->rnti,
- uci_stats->pucch01_trials,
- uci_stats->pucch0_n01,
- uci_stats->pucch0_n01,
- uci_stats->pucch0_thres,
- dB_fixed(uci_stats->current_pucch0_stat0),
- dB_fixed(uci_stats->current_pucch0_stat1),
- uci_stats->pucch01_DTX);
-
- if (uci_stats->pucch02_trials > 0)
- strpos += sprintf(output + strpos,
- "UCI %d RNTI %x: pucch01_trials %d, pucch0_n00 %d dB, pucch0_n01 %d dB, pucch0_thres %d dB, current "
- "pucch0_stat0 %d dB, current pucch0_stat1 %d dB, pucch01_DTX %d\n",
- i,
- stats->rnti,
- uci_stats->pucch02_trials,
- uci_stats->pucch0_n00,
- uci_stats->pucch0_n01,
- uci_stats->pucch0_thres,
- dB_fixed(uci_stats->current_pucch0_stat0),
- dB_fixed(uci_stats->current_pucch0_stat1),
- uci_stats->pucch02_DTX);
-
- if (uci_stats->pucch2_trials > 0)
- strpos += sprintf(output + strpos,
- "UCI %d RNTI %x: pucch2_trials %d, pucch2_DTX %d\n",
- i,
- stats->rnti,
- uci_stats->pucch2_trials,
- uci_stats->pucch2_DTX);
- }
- if (fd)
- fprintf(fd, "%s", output);
- else
- printf("%s", output);
-}
diff --git a/openair1/PHY/NR_TRANSPORT/srs_rx.c b/openair1/PHY/NR_TRANSPORT/srs_rx.c
index 5d84c11c99..0637a8abce 100644
--- a/openair1/PHY/NR_TRANSPORT/srs_rx.c
+++ b/openair1/PHY/NR_TRANSPORT/srs_rx.c
@@ -75,7 +75,6 @@ void nr_fill_srs(PHY_VARS_gNB *gNB, frame_t frame, slot_t slot, nfapi_nr_srs_pdu
int nr_get_srs_signal(PHY_VARS_gNB *gNB,
c16_t **rxdataF,
- frame_t frame,
slot_t slot,
nfapi_nr_srs_pdu_t *srs_pdu,
nr_srs_info_t *nr_srs_info,
diff --git a/openair1/PHY/NR_UE_ESTIMATION/nr_adjust_synch_ue.c b/openair1/PHY/NR_UE_ESTIMATION/nr_adjust_synch_ue.c
index a407282c1b..1568c9e68e 100644
--- a/openair1/PHY/NR_UE_ESTIMATION/nr_adjust_synch_ue.c
+++ b/openair1/PHY/NR_UE_ESTIMATION/nr_adjust_synch_ue.c
@@ -34,7 +34,6 @@
int nr_adjust_synch_ue(NR_DL_FRAME_PARMS *frame_parms,
PHY_VARS_NR_UE *ue,
- module_id_t gNB_id,
const int estimateSz,
struct complex16 dl_ch_estimates_time[][estimateSz],
uint8_t frame,
diff --git a/openair1/PHY/NR_UE_ESTIMATION/nr_dl_channel_estimation.c b/openair1/PHY/NR_UE_ESTIMATION/nr_dl_channel_estimation.c
index 8978527095..f0e53a1c04 100644
--- a/openair1/PHY/NR_UE_ESTIMATION/nr_dl_channel_estimation.c
+++ b/openair1/PHY/NR_UE_ESTIMATION/nr_dl_channel_estimation.c
@@ -1295,7 +1295,7 @@ void nr_pdsch_channel_estimation(PHY_VARS_NR_UE *ue,
float beta_dmrs_pdsch = get_beta_dmrs(dlsch->n_dmrs_cdm_groups, config_type == NFAPI_NR_DMRS_TYPE2);
int16_t dmrs_scaling = (int16_t)((1 / beta_dmrs_pdsch) * (1 << 14));
const uint32_t *gold = nr_gold_pdsch(fp->N_RB_DL, fp->symbols_per_slot, dlsch->dlDmrsScramblingId, dlsch->nscid, slot, symbol);
- nr_pdsch_dmrs_rx(fp->Ncp, slot, gold, pilot, 1000 + p, 0, nb_rb_pdsch + rb_offset, config_type, dmrs_scaling);
+ nr_pdsch_dmrs_rx(fp->Ncp, gold, pilot, 1000 + p, 0, nb_rb_pdsch + rb_offset, config_type, dmrs_scaling);
delay_t delay = {0};
@@ -1380,8 +1380,7 @@ void nr_pdsch_channel_estimation(PHY_VARS_NR_UE *ue,
* 2) Interpolate PTRS estimated value in TD after all PTRS symbols
* 3) Compensate signal with PTRS estimation for slot
*********************************************************************/
-void nr_pdsch_ptrs_processing(PHY_VARS_NR_UE *ue,
- int nbRx,
+void nr_pdsch_ptrs_processing(int nbRx,
c16_t ptrs_phase_per_slot[][14],
int32_t ptrs_re_per_slot[][14],
uint32_t rx_size_symbol,
@@ -1389,7 +1388,6 @@ void nr_pdsch_ptrs_processing(PHY_VARS_NR_UE *ue,
NR_DL_FRAME_PARMS *frame_parms,
NR_DL_UE_HARQ_t *dlsch0_harq,
NR_DL_UE_HARQ_t *dlsch1_harq,
- uint8_t gNB_id,
uint8_t nr_slot_rx,
unsigned char symbol,
uint16_t rnti,
@@ -1478,8 +1476,6 @@ void nr_pdsch_ptrs_processing(PHY_VARS_NR_UE *ue,
*ptrsReOffset,
*nb_rb,
rnti,
- nr_slot_rx,
- symbol,
frame_parms->ofdm_symbol_size,
(int16_t *)(rxdataF_comp[0][aarx] + symbol * rx_size_symbol),
gold,
diff --git a/openair1/PHY/NR_UE_ESTIMATION/nr_estimation.h b/openair1/PHY/NR_UE_ESTIMATION/nr_estimation.h
index 4a67f2956e..78657510d0 100644
--- a/openair1/PHY/NR_UE_ESTIMATION/nr_estimation.h
+++ b/openair1/PHY/NR_UE_ESTIMATION/nr_estimation.h
@@ -94,7 +94,6 @@ void nr_pdsch_channel_estimation(PHY_VARS_NR_UE *ue,
int nr_adjust_synch_ue(NR_DL_FRAME_PARMS *frame_parms,
PHY_VARS_NR_UE *ue,
- module_id_t gNB_id,
int estimateSz,
struct complex16 dl_ch_estimates_time[][estimateSz],
uint8_t frame,
@@ -108,7 +107,6 @@ void nr_ue_measurements(PHY_VARS_NR_UE *ue,
int32_t dl_ch_estimates[][pdsch_est_size]);
uint32_t nr_ue_calculate_ssb_rsrp(const NR_DL_FRAME_PARMS *fp,
- const UE_nr_rxtx_proc_t *proc,
const c16_t rxdataF[][fp->samples_per_slot_wCP],
int symbol_offset,
int ssb_start_subcarrier);
@@ -122,7 +120,7 @@ void nr_ue_ssb_rsrp_measurements(PHY_VARS_NR_UE *ue,
typedef struct {
UE_nr_rxtx_proc_t proc;
PHY_VARS_NR_UE *ue;
- c16_t *rxdata[NB_ANTENNAS_RX];
+ c16_t **rxdata;
uint32_t rxdata_size;
c16_t rxdata_ant[];
} nr_meas_task_args_t;
@@ -139,8 +137,7 @@ void phy_adjust_gain_nr(PHY_VARS_NR_UE *ue,
uint32_t rx_power_fil_dB,
uint8_t gNB_id);
-void nr_pdsch_ptrs_processing(PHY_VARS_NR_UE *ue,
- int nbRx,
+void nr_pdsch_ptrs_processing(int nbRx,
c16_t ptrs_phase_per_slot[][14],
int32_t ptrs_re_per_slot[][14],
uint32_t rx_size_symbol,
@@ -148,7 +145,6 @@ void nr_pdsch_ptrs_processing(PHY_VARS_NR_UE *ue,
NR_DL_FRAME_PARMS *frame_parms,
NR_DL_UE_HARQ_t *dlsch0_harq,
NR_DL_UE_HARQ_t *dlsch1_harq,
- uint8_t gNB_id,
uint8_t nr_slot_rx,
unsigned char symbol,
uint16_t rnti,
diff --git a/openair1/PHY/NR_UE_ESTIMATION/nr_ue_measurements.c b/openair1/PHY/NR_UE_ESTIMATION/nr_ue_measurements.c
index 8a59470cbf..5190bbf83d 100644
--- a/openair1/PHY/NR_UE_ESTIMATION/nr_ue_measurements.c
+++ b/openair1/PHY/NR_UE_ESTIMATION/nr_ue_measurements.c
@@ -73,7 +73,7 @@ void nr_ue_measurements(PHY_VARS_NR_UE *ue,
cmax(frame_parms->nb_antennas_rx, 1),
false);
allocCast3D(rx_spatial_power_dB,
- unsigned short,
+ short,
ue->measurements.rx_spatial_power_dB,
NUMBER_OF_CONNECTED_gNB_MAX,
cmax(frame_parms->nb_antenna_ports_gNB, 1),
@@ -81,32 +81,21 @@ void nr_ue_measurements(PHY_VARS_NR_UE *ue,
false);
// signal measurements
- for (gNB_id = 0; gNB_id < ue->n_connected_gNB; gNB_id++){
-
+ for (gNB_id = 0; gNB_id < ue->n_connected_gNB; gNB_id++) {
ue->measurements.rx_power_tot[gNB_id] = 0;
-
- for (aarx = 0; aarx < frame_parms->nb_antennas_rx; aarx++){
-
- ue->measurements.rx_power[gNB_id][aarx] = 0;
-
- for (aatx = 0; aatx < frame_parms->nb_antenna_ports_gNB; aatx++){
+ for (aarx = 0; aarx < frame_parms->nb_antennas_rx; aarx++) {
+ int rx_power = 0;
+ for (aatx = 0; aatx < frame_parms->nb_antenna_ports_gNB; aatx++) {
const int z = signal_energy_nodc((c16_t*)&dl_ch_estimates[gNB_id][ch_offset], number_rbs * NR_NB_SC_PER_RB);
rx_spatial_power[gNB_id][aatx][aarx] = z;
-
if (rx_spatial_power[gNB_id][aatx][aarx] < 0)
rx_spatial_power[gNB_id][aatx][aarx] = 0;
-
- rx_spatial_power_dB[gNB_id][aatx][aarx] = (unsigned short)dB_fixed(rx_spatial_power[gNB_id][aatx][aarx]);
- ue->measurements.rx_power[gNB_id][aarx] += rx_spatial_power[gNB_id][aatx][aarx];
+ rx_spatial_power_dB[gNB_id][aatx][aarx] = dB_fixed(rx_spatial_power[gNB_id][aatx][aarx]);
+ rx_power += rx_spatial_power[gNB_id][aatx][aarx];
}
-
- ue->measurements.rx_power_dB[gNB_id][aarx] = (unsigned short) dB_fixed(ue->measurements.rx_power[gNB_id][aarx]);
- ue->measurements.rx_power_tot[gNB_id] += ue->measurements.rx_power[gNB_id][aarx];
-
+ ue->measurements.rx_power_tot[gNB_id] += rx_power;
}
-
- ue->measurements.rx_power_tot_dB[gNB_id] = (unsigned short) dB_fixed(ue->measurements.rx_power_tot[gNB_id]);
-
+ ue->measurements.rx_power_tot_dB[gNB_id] = dB_fixed(ue->measurements.rx_power_tot[gNB_id]);
}
// filter to remove jitter
@@ -154,7 +143,6 @@ void nr_ue_measurements(PHY_VARS_NR_UE *ue,
// This function calculates:
// - SS reference signal received digital power in dB/RE
uint32_t nr_ue_calculate_ssb_rsrp(const NR_DL_FRAME_PARMS *fp,
- const UE_nr_rxtx_proc_t *proc,
const c16_t rxdataF[][fp->samples_per_slot_wCP],
int symbol_offset,
int ssb_start_subcarrier)
@@ -242,7 +230,7 @@ void nr_ue_ssb_rsrp_measurements(PHY_VARS_NR_UE *ue,
if (fp->half_frame_bit)
symbol_offset += (fp->slots_per_frame >> 1) * fp->symbols_per_slot;
- uint32_t rsrp_avg = nr_ue_calculate_ssb_rsrp(fp, proc, rxdataF, symbol_offset, fp->ssb_start_subcarrier);
+ uint32_t rsrp_avg = nr_ue_calculate_ssb_rsrp(fp, rxdataF, symbol_offset, fp->ssb_start_subcarrier);
float rsrp_db_per_re = 10 * log10(rsrp_avg);
openair0_config_t *cfg0 = &openair0_cfg[ue->rf_map.card];
@@ -489,7 +477,7 @@ void do_neighboring_cell_measurements(UE_nr_rxtx_proc_t *proc, PHY_VARS_NR_UE *u
}
// RSRP measurements
- neighboring_cell_info->ssb_rsrp = nr_ue_calculate_ssb_rsrp(frame_parms, proc, rxdataF, 0, frame_parms->ssb_start_subcarrier);
+ neighboring_cell_info->ssb_rsrp = nr_ue_calculate_ssb_rsrp(frame_parms, rxdataF, 0, frame_parms->ssb_start_subcarrier);
neighboring_cell_info->ssb_rsrp_dBm =
10 * log10(neighboring_cell_info->ssb_rsrp) + 30 - SQ15_SQUARED_NORM_FACTOR_DB
@@ -533,9 +521,9 @@ void nr_ue_rrc_measurements(PHY_VARS_NR_UE *ue,
LOG_D(PHY, "In %s doing measurements for ssb_offset %d l_sss %d \n", __FUNCTION__, ssb_offset, l_sss);
- for (aarx = 0; aarxframe_parms.nb_antennas_rx; aarx++) {
+ for (aarx = 0; aarx < ue->frame_parms.nb_antennas_rx; aarx++) {
- ue->measurements.n0_power[aarx] = 0;
+ uint32_t n0_power = 0;
rxF_sss = (int16_t *)&rxdataF[aarx][l_sss*ue->frame_parms.ofdm_symbol_size];
//-ve spectrum from SSS
@@ -547,8 +535,7 @@ void nr_ue_rrc_measurements(PHY_VARS_NR_UE *ue,
LOG_I(PHY, "In %s -rxF_sss %d %d\n", __FUNCTION__, rxF_sss[re*2], rxF_sss[re*2 + 1]);
#endif
- ue->measurements.n0_power[aarx] += (((int32_t)rxF_sss[re*2]*rxF_sss[re*2]) + ((int32_t)rxF_sss[re*2 + 1]*rxF_sss[re*2 + 1]));
-
+ n0_power += (((int32_t)rxF_sss[re * 2] * rxF_sss[re * 2]) + ((int32_t)rxF_sss[re * 2 + 1] * rxF_sss[re * 2 + 1]));
}
//+ve spectrum from SSS
@@ -560,17 +547,14 @@ void nr_ue_rrc_measurements(PHY_VARS_NR_UE *ue,
LOG_I(PHY, "In %s +rxF_sss %d %d\n", __FUNCTION__, rxF_sss[re*2], rxF_sss[re*2 + 1]);
#endif
- ue->measurements.n0_power[aarx] += (((int32_t)rxF_sss[re*2]*rxF_sss[re*2]) + ((int32_t)rxF_sss[re*2 + 1]*rxF_sss[re*2 + 1]));
-
+ n0_power += (((int32_t)rxF_sss[re * 2]*rxF_sss[re * 2]) + ((int32_t)rxF_sss[re * 2 + 1] * rxF_sss[re * 2 + 1]));
}
- ue->measurements.n0_power[aarx] /= 2*k_length;
- ue->measurements.n0_power_dB[aarx] = (unsigned short) dB_fixed(ue->measurements.n0_power[aarx]);
- ue->measurements.n0_power_tot += ue->measurements.n0_power[aarx];
-
+ n0_power /= 2 * k_length;
+ ue->measurements.n0_power_tot += n0_power;
}
- ue->measurements.n0_power_tot_dB = (unsigned short) dB_fixed(ue->measurements.n0_power_tot);
+ ue->measurements.n0_power_tot_dB = dB_fixed(ue->measurements.n0_power_tot);
#ifdef DEBUG_MEAS_RRC
const int psd_awgn = -174;
diff --git a/openair1/PHY/NR_UE_TRANSPORT/csi_rx.c b/openair1/PHY/NR_UE_TRANSPORT/csi_rx.c
index d8604d4570..3004728091 100644
--- a/openair1/PHY/NR_UE_TRANSPORT/csi_rx.c
+++ b/openair1/PHY/NR_UE_TRANSPORT/csi_rx.c
@@ -581,7 +581,7 @@ int nr_csi_rs_pmi_estimation(const PHY_VARS_NR_UE *ue,
const int16_t log2_re,
uint8_t *i1,
uint8_t *i2,
- uint32_t *precoded_sinr_dB)
+ int32_t *precoded_sinr_dB)
{
const NR_DL_FRAME_PARMS *frame_parms = &ue->frame_parms;
@@ -730,7 +730,6 @@ int nr_csi_rs_cqi_estimation(const uint32_t precoded_sinr,
}
static void nr_csi_im_power_estimation(const PHY_VARS_NR_UE *ue,
- const UE_nr_rxtx_proc_t *proc,
const fapi_nr_dl_config_csiim_pdu_rel15_t *csiim_config_pdu,
uint32_t *interference_plus_noise_power,
const c16_t rxdataF[][ue->frame_parms.samples_per_slot_wCP])
@@ -822,7 +821,7 @@ void nr_ue_csi_im_procedures(PHY_VARS_NR_UE *ue,
LOG_I(NR_PHY, "csiim_config_pdu->l_csiim = %i.%i.%i.%i\n", csiim_config_pdu->l_csiim[0], csiim_config_pdu->l_csiim[1], csiim_config_pdu->l_csiim[2], csiim_config_pdu->l_csiim[3]);
#endif
- nr_csi_im_power_estimation(ue, proc, csiim_config_pdu, &ue->nr_csi_info->interference_plus_noise_power, rxdataF);
+ nr_csi_im_power_estimation(ue, csiim_config_pdu, &ue->nr_csi_info->interference_plus_noise_power, rxdataF);
ue->nr_csi_info->csi_im_meas_computed = true;
}
@@ -948,7 +947,7 @@ void nr_ue_csi_rs_procedures(PHY_VARS_NR_UE *ue,
uint8_t i1[3] = {0};
uint8_t i2[1] = {0};
uint8_t cqi = 0;
- uint32_t precoded_sinr_dB = 0;
+ int32_t precoded_sinr_dB = 0;
// bit 3 in bitmap to indicate RI measurment
if (csirs_config_pdu->measurement_bitmap & 8) {
nr_csi_rs_pmi_estimation(ue,
diff --git a/openair1/PHY/NR_UE_TRANSPORT/dci_nr.c b/openair1/PHY/NR_UE_TRANSPORT/dci_nr.c
index b5f26266e5..65a0247046 100644
--- a/openair1/PHY/NR_UE_TRANSPORT/dci_nr.c
+++ b/openair1/PHY/NR_UE_TRANSPORT/dci_nr.c
@@ -324,7 +324,6 @@ static void nr_pdcch_detection_mrc(int nb_ant, int sz, c16_t rxdataF_comp[][sz])
static void nr_rx_pdcch_symbol(PHY_VARS_NR_UE *ue,
const UE_nr_rxtx_proc_t *proc,
int symbol,
- int rel_symb_monOcc,
int ss_idx,
nr_phy_data_t *phy_data,
int llr_size_symbol,
@@ -430,12 +429,6 @@ int get_max_pdcch_monOcc(const NR_UE_PDCCH_CONFIG *phy_pdcch_config)
return monOcc;
}
-static void nr_dci_decoding_procedure(PHY_VARS_NR_UE *ue,
- const UE_nr_rxtx_proc_t *proc,
- c16_t *pdcch_e_rx,
- fapi_nr_dl_config_dci_dl_pdu_rel15_t *rel15,
- fapi_nr_dci_indication_t *dci_ind);
-
void set_first_last_pdcch_symb(const NR_UE_PDCCH_CONFIG *phy_pdcch_config, int *first_symb, int *last_symb)
{
*first_symb = NR_SYMBOLS_PER_SLOT; // max first pdcch symbol
@@ -478,7 +471,6 @@ void nr_pdcch_generate_llr(PHY_VARS_NR_UE *ue,
nr_rx_pdcch_symbol(ue,
proc,
symbol,
- rel_symb_monOcc,
ss_idx,
phy_data,
llr_size_symbol,
@@ -489,64 +481,6 @@ void nr_pdcch_generate_llr(PHY_VARS_NR_UE *ue,
}
}
-/* Decode DCI from LLRs for each Search-Space and send to MAC */
-void nr_pdcch_dci_indication(const UE_nr_rxtx_proc_t *proc,
- int llr_size,
- int max_monOcc,
- PHY_VARS_NR_UE *ue,
- nr_phy_data_t *phy_data,
- c16_t llr[phy_data->phy_pdcch_config.nb_search_space][max_monOcc][llr_size])
-{
- NR_UE_PDCCH_CONFIG *phy_pdcch_config = &phy_data->phy_pdcch_config;
-
- nr_downlink_indication_t dl_indication;
- fapi_nr_dci_indication_t dci_ind = {.SFN = proc->frame_rx, .slot = proc->nr_slot_rx};
-
- for (int ss_idx = 0; ss_idx < phy_pdcch_config->nb_search_space; ss_idx++) {
- fapi_nr_dl_config_dci_dl_pdu_rel15_t *rel15 = &phy_pdcch_config->pdcch_config[ss_idx];
- uint8_t unused_start_symb[NR_SYMBOLS_PER_SLOT] = {0};
- const int num_monitoring_occ = get_pdcch_mon_occasions_slot(rel15, unused_start_symb);
- const int llr_stride = llr_size / rel15->coreset.duration;
- int n_rb, cset_start;
- get_coreset_rballoc(rel15->coreset.frequency_domain_resource, &n_rb, &cset_start);
-
- for (int m = 0; m < num_monitoring_occ; m++) {
- /// PDCCH/DCI e-sequence (input to rate matching).
- c16_t pdcch_e_rx[NR_MAX_PDCCH_SIZE];
-
- nr_pdcch_demapping_deinterleaving(n_rb,
- llr[ss_idx][m],
- pdcch_e_rx,
- rel15->coreset.duration,
- rel15->coreset.RegBundleSize,
- rel15->coreset.InterleaverSize,
- rel15->coreset.ShiftIndex,
- rel15->number_of_candidates,
- rel15->CCE,
- rel15->L,
- llr_stride);
-
- nr_dci_decoding_procedure(ue, proc, pdcch_e_rx, rel15, &dci_ind);
- }
- }
-
- for (int i = 0; i < dci_ind.number_of_dcis; i++) {
- LOG_D(PHY,
- "Frame.slot: %d.%d: DCI %i of %d total DCIs found --> rnti %x : format %d\n",
- proc->frame_rx,
- proc->nr_slot_rx,
- i + 1,
- dci_ind.number_of_dcis,
- dci_ind.dci_list[i].rnti,
- dci_ind.dci_list[i].dci_format);
- }
-
- /* Send to MAC */
- nr_fill_dl_indication(&dl_indication, &dci_ind, NULL, proc, ue, phy_data);
- ue->if_inst->dl_indication(&dl_indication);
- phy_pdcch_config->nb_search_space = 0;
-}
-
static void nr_pdcch_unscrambling(c16_t *e_rx,
uint16_t scrambling_RNTI,
uint32_t length,
@@ -566,8 +500,7 @@ static void nr_pdcch_unscrambling(c16_t *e_rx,
}
}
-static void nr_dci_decoding_procedure(PHY_VARS_NR_UE *ue,
- const UE_nr_rxtx_proc_t *proc,
+static void nr_dci_decoding_procedure(const UE_nr_rxtx_proc_t *proc,
c16_t *pdcch_e_rx,
fapi_nr_dl_config_dci_dl_pdu_rel15_t *rel15,
fapi_nr_dci_indication_t *dci_ind)
@@ -659,3 +592,61 @@ static void nr_dci_decoding_procedure(PHY_VARS_NR_UE *ue,
e_rx_cand_idx += RE_PER_RB_OUT_DMRS * L * 6; // e_rx index for next candidate (L CCEs, 6 REGs per CCE and 9 REs per REG )
}
}
+
+/* Decode DCI from LLRs for each Search-Space and send to MAC */
+void nr_pdcch_dci_indication(const UE_nr_rxtx_proc_t *proc,
+ int llr_size,
+ int max_monOcc,
+ PHY_VARS_NR_UE *ue,
+ nr_phy_data_t *phy_data,
+ c16_t llr[phy_data->phy_pdcch_config.nb_search_space][max_monOcc][llr_size])
+{
+ NR_UE_PDCCH_CONFIG *phy_pdcch_config = &phy_data->phy_pdcch_config;
+
+ nr_downlink_indication_t dl_indication;
+ fapi_nr_dci_indication_t dci_ind = {.SFN = proc->frame_rx, .slot = proc->nr_slot_rx};
+
+ for (int ss_idx = 0; ss_idx < phy_pdcch_config->nb_search_space; ss_idx++) {
+ fapi_nr_dl_config_dci_dl_pdu_rel15_t *rel15 = &phy_pdcch_config->pdcch_config[ss_idx];
+ uint8_t unused_start_symb[NR_SYMBOLS_PER_SLOT] = {0};
+ const int num_monitoring_occ = get_pdcch_mon_occasions_slot(rel15, unused_start_symb);
+ const int llr_stride = llr_size / rel15->coreset.duration;
+ int n_rb, cset_start;
+ get_coreset_rballoc(rel15->coreset.frequency_domain_resource, &n_rb, &cset_start);
+
+ for (int m = 0; m < num_monitoring_occ; m++) {
+ /// PDCCH/DCI e-sequence (input to rate matching).
+ c16_t pdcch_e_rx[NR_MAX_PDCCH_SIZE];
+
+ nr_pdcch_demapping_deinterleaving(n_rb,
+ llr[ss_idx][m],
+ pdcch_e_rx,
+ rel15->coreset.duration,
+ rel15->coreset.RegBundleSize,
+ rel15->coreset.InterleaverSize,
+ rel15->coreset.ShiftIndex,
+ rel15->number_of_candidates,
+ rel15->CCE,
+ rel15->L,
+ llr_stride);
+
+ nr_dci_decoding_procedure(proc, pdcch_e_rx, rel15, &dci_ind);
+ }
+ }
+
+ for (int i = 0; i < dci_ind.number_of_dcis; i++) {
+ LOG_D(PHY,
+ "Frame.slot: %d.%d: DCI %i of %d total DCIs found --> rnti %x : format %d\n",
+ proc->frame_rx,
+ proc->nr_slot_rx,
+ i + 1,
+ dci_ind.number_of_dcis,
+ dci_ind.dci_list[i].rnti,
+ dci_ind.dci_list[i].dci_format);
+ }
+
+ /* Send to MAC */
+ nr_fill_dl_indication(&dl_indication, &dci_ind, NULL, proc, ue, phy_data);
+ ue->if_inst->dl_indication(&dl_indication);
+ phy_pdcch_config->nb_search_space = 0;
+}
diff --git a/openair1/PHY/NR_UE_TRANSPORT/nr_dlsch_demodulation.c b/openair1/PHY/NR_UE_TRANSPORT/nr_dlsch_demodulation.c
index 73bcbfab46..b46d89943c 100644
--- a/openair1/PHY/NR_UE_TRANSPORT/nr_dlsch_demodulation.c
+++ b/openair1/PHY/NR_UE_TRANSPORT/nr_dlsch_demodulation.c
@@ -60,7 +60,6 @@ static void nr_dlsch_mmse(uint32_t rx_size_symbol,
c16_t dl_ch_magb[][n_rx][rx_size_symbol],
c16_t dl_ch_magr[][n_rx][rx_size_symbol],
int32_t dl_ch_estimates_ext[][rx_size_symbol],
- unsigned short nb_rb,
unsigned char mod_order,
int shift,
unsigned char symbol,
@@ -86,7 +85,6 @@ static void nr_dlsch_llr(uint32_t rx_size_symbol,
c16_t dl_ch_mag[rx_size_symbol],
c16_t dl_ch_magb[rx_size_symbol],
c16_t dl_ch_magr[rx_size_symbol],
- NR_DL_UE_HARQ_t *dlsch0_harq,
NR_DL_UE_HARQ_t *dlsch1_harq,
unsigned char symbol,
uint32_t len,
@@ -141,7 +139,6 @@ static void nr_dlsch_channel_level_median(uint32_t rx_size_symbol,
@param rho Cross-correlation between two spatial channels on each RX antenna
@param frame_parms Pointer to frame descriptor
@param symbol Symbol on which to operate
- @param first_symbol_flag set to 1 on first DLSCH symbol
@param mod_order Modulation order of allocation
@param nb_rb Number of RBs in allocation
@param output_shift Rescaling for compensated output (should be energy-normalizing)
@@ -161,7 +158,6 @@ static void nr_dlsch_channel_compensation(uint32_t rx_size_symbol,
uint8_t n_layers,
unsigned char symbol,
int length,
- bool first_symbol_flag,
unsigned char mod_order,
unsigned short nb_rb,
unsigned char output_shift,
@@ -555,7 +551,6 @@ int nr_rx_pdsch(PHY_VARS_NR_UE *ue,
nl,
symbol,
nb_re_pdsch,
- first_symbol_flag,
dlsch_config->qamModOrder,
nb_rb_pdsch,
*log2_maxh,
@@ -614,7 +609,6 @@ int nr_rx_pdsch(PHY_VARS_NR_UE *ue,
dl_ch_magb,
dl_ch_magr,
dl_ch_estimates_ext,
- nb_rb_pdsch,
dlsch_config->qamModOrder,
*log2_maxh,
symbol,
@@ -649,8 +643,7 @@ int nr_rx_pdsch(PHY_VARS_NR_UE *ue,
/* Check for PTRS bitmap and process it respectively */
if((pduBitmap & 0x1) && (dlsch[0].rnti_type == TYPE_C_RNTI_)) {
- nr_pdsch_ptrs_processing(ue,
- nbRx,
+ nr_pdsch_ptrs_processing(nbRx,
ptrs_phase_per_slot,
ptrs_re_per_slot,
rx_size_symbol,
@@ -658,7 +651,6 @@ int nr_rx_pdsch(PHY_VARS_NR_UE *ue,
fp,
dlsch0_harq,
dlsch1_harq,
- gNB_id,
nr_slot_rx,
symbol,
dlsch[0].rnti,
@@ -674,7 +666,6 @@ int nr_rx_pdsch(PHY_VARS_NR_UE *ue,
dl_ch_mag[0][0],
dl_ch_magb[0][0],
dl_ch_magr[0][0],
- dlsch0_harq,
dlsch1_harq,
symbol,
dl_valid_re[symbol],
@@ -769,7 +760,6 @@ static void nr_dlsch_channel_compensation(uint32_t rx_size_symbol,
uint8_t n_layers,
unsigned char symbol,
int length,
- bool first_symbol_flag,
unsigned char mod_order,
unsigned short nb_rb,
unsigned char output_shift,
@@ -868,24 +858,11 @@ static void nr_dlsch_channel_compensation(uint32_t rx_size_symbol,
for (int aarx = 0; aarx < frame_parms->nb_antennas_rx; aarx++) {
for (int l = 0; l < n_layers; l++) {
for (int atx = 0; atx < n_layers; atx++) {
- rho128 = (simde__m128i *)&rho[aarx][l * n_layers + atx][symbol * nb_rb * 12];
- dl_ch128 = (simde__m128i *)dl_ch_estimates_ext[l * frame_parms->nb_antennas_rx + aarx];
- dl_ch128_2 = (simde__m128i *)dl_ch_estimates_ext[atx * frame_parms->nb_antennas_rx + aarx];
-
- // multiply by conjugated channel
- mult_cpx_conj_vector((c16_t *)dl_ch128, (c16_t *)dl_ch128_2, (c16_t *)rho128, 12 * nb_rb_0, output_shift);
-
- if (first_symbol_flag) {
- // rho_nm = H_arx_n.conj(H_arx_m)
- // rho_rx_corr[arx][nm] = |H_arx_n|^2.|H_arx_m|^2 &rho[aarx][l*n_layers+atx][symbol*nb_rb*12]
- measurements->rx_correlation[0][aarx][l * n_layers + atx] =
- signal_energy(&rho[aarx][l * n_layers + atx][symbol * nb_rb * 12], length);
- // avg_rho_re[aarx][l*n_layers+atx] = 16*avg_rho_re[aarx][l*n_layers+atx]/length;
- // avg_rho_im[aarx][l*n_layers+atx] = 16*avg_rho_im[aarx][l*n_layers+atx]/length;
- // printf("rho[rx]%d tx%d tx%d = Re: %d Im: %d\n",aarx, l,atx, avg_rho_re[aarx][l*n_layers+atx],
- // avg_rho_im[aarx][l*n_layers+atx]); printf("rho_corr[rx]%d tx%d tx%d = %d ...\n",aarx, l,atx,
- // measurements->rx_correlation[0][aarx][l*n_layers+atx]);
- }
+ rho128 = (simde__m128i *)&rho[aarx][l * n_layers + atx][symbol * nb_rb * 12];
+ dl_ch128 = (simde__m128i *)dl_ch_estimates_ext[l * frame_parms->nb_antennas_rx + aarx];
+ dl_ch128_2 = (simde__m128i *)dl_ch_estimates_ext[atx * frame_parms->nb_antennas_rx + aarx];
+ // multiply by conjugated channel
+ mult_cpx_conj_vector((c16_t *)dl_ch128, (c16_t *)dl_ch128_2, (c16_t *)rho128, 12 * nb_rb_0, output_shift);
}
}
}
@@ -1364,7 +1341,6 @@ static void nr_dlsch_mmse(uint32_t rx_size_symbol,
c16_t dl_ch_magb[][n_rx][rx_size_symbol],
c16_t dl_ch_magr[][n_rx][rx_size_symbol],
int32_t dl_ch_estimates_ext[][rx_size_symbol],
- unsigned short nb_rb,
unsigned char mod_order,
int shift,
unsigned char symbol,
@@ -1556,7 +1532,6 @@ static void nr_dlsch_llr(uint32_t rx_size_symbol,
c16_t dl_ch_mag[rx_size_symbol],
c16_t dl_ch_magb[rx_size_symbol],
c16_t dl_ch_magr[rx_size_symbol],
- NR_DL_UE_HARQ_t *dlsch0_harq,
NR_DL_UE_HARQ_t *dlsch1_harq,
unsigned char symbol,
uint32_t len,
diff --git a/openair1/PHY/NR_UE_TRANSPORT/nr_initial_sync.c b/openair1/PHY/NR_UE_TRANSPORT/nr_initial_sync.c
index 9d2db73e66..31566fd3fd 100644
--- a/openair1/PHY/NR_UE_TRANSPORT/nr_initial_sync.c
+++ b/openair1/PHY/NR_UE_TRANSPORT/nr_initial_sync.c
@@ -374,7 +374,7 @@ void nr_scan_ssb(void *arg)
&ssbInfo->pbchResult,
rxdataF); // start pbch detection at first symbol after pss
if (ssbInfo->syncRes.cell_detected) {
- uint32_t rsrp_avg = nr_ue_calculate_ssb_rsrp(ssbInfo->fp, ssbInfo->proc, rxdataF, 0, ssbInfo->gscnInfo.ssbFirstSC);
+ uint32_t rsrp_avg = nr_ue_calculate_ssb_rsrp(ssbInfo->fp, rxdataF, 0, ssbInfo->gscnInfo.ssbFirstSC);
int rsrp_db_per_re = 10 * log10(rsrp_avg);
ssbInfo->adjust_rxgain = TARGET_RX_POWER - rsrp_db_per_re;
LOG_I(PHY, "pbch rx ok. rsrp:%d dB/RE, adjust_rxgain:%d dB\n", rsrp_db_per_re, ssbInfo->adjust_rxgain);
@@ -388,7 +388,6 @@ void nr_scan_ssb(void *arg)
nr_initial_sync_t nr_initial_sync(UE_nr_rxtx_proc_t *proc,
PHY_VARS_NR_UE *ue,
int n_frames,
- int sa,
nr_gscn_info_t gscnInfo[MAX_GSCN_BAND],
int numGscn)
{
diff --git a/openair1/PHY/NR_UE_TRANSPORT/nr_initial_sync_sl.c b/openair1/PHY/NR_UE_TRANSPORT/nr_initial_sync_sl.c
index 321281fcda..e407459bc8 100644
--- a/openair1/PHY/NR_UE_TRANSPORT/nr_initial_sync_sl.c
+++ b/openair1/PHY/NR_UE_TRANSPORT/nr_initial_sync_sl.c
@@ -151,7 +151,6 @@ static int sl_nr_pss_correlation(PHY_VARS_NR_UE *UE, int frame_index)
}
static void sl_nr_extract_sss(PHY_VARS_NR_UE *ue,
- UE_nr_rxtx_proc_t *proc,
int32_t *tot_metric,
uint8_t *phase_max,
c16_t rxdataF[][ue->SL_UE_PHY_PARAMS.sl_frame_params.samples_per_slot_wCP])
@@ -440,7 +439,7 @@ nr_initial_sync_t sl_nr_slss_search(PHY_VARS_NR_UE *UE, UE_nr_rxtx_proc_t *proc,
UE->common_vars.rxdata);
}
- sl_nr_extract_sss(UE, NULL, &metric_tdd_ncp, &phase_tdd_ncp, rxdataF);
+ sl_nr_extract_sss(UE, &metric_tdd_ncp, &phase_tdd_ncp, rxdataF);
// save detected cell id to psbch
rx_slss_id = UE->SL_UE_PHY_PARAMS.sync_params.N_sl_id;
@@ -510,7 +509,7 @@ nr_initial_sync_t sl_nr_slss_search(PHY_VARS_NR_UE *UE, UE_nr_rxtx_proc_t *proc,
sl_nr_rx_indication_t rx_ind = {0};
uint16_t number_pdus = 1;
nr_fill_sl_indication(&sl_indication, &rx_ind, NULL, proc, UE, NULL);
- nr_fill_sl_rx_indication(&rx_ind, SL_NR_RX_PDU_TYPE_SSB, UE, number_pdus, proc, (void *)decoded_output, rx_slss_id);
+ nr_fill_sl_rx_indication(&rx_ind, SL_NR_RX_PDU_TYPE_SSB, UE, number_pdus, (void *)decoded_output, rx_slss_id);
LOG_D(PHY, "Sidelink SLSS SEARCH PSBCH RX OK. Send SL-SSB TO MAC\n");
diff --git a/openair1/PHY/NR_UE_TRANSPORT/nr_transport_proto_ue.h b/openair1/PHY/NR_UE_TRANSPORT/nr_transport_proto_ue.h
index 3daaaf0eee..6872306dfe 100644
--- a/openair1/PHY/NR_UE_TRANSPORT/nr_transport_proto_ue.h
+++ b/openair1/PHY/NR_UE_TRANSPORT/nr_transport_proto_ue.h
@@ -126,8 +126,7 @@ int nr_ulsch_encoding(PHY_VARS_NR_UE *ue,
const uint8_t slot,
unsigned int *G,
int nb_ulsch,
- uint8_t *ULSCH_ids,
- uint16_t number_dmrs_symbols);
+ uint8_t *ULSCH_ids);
/*! \brief Perform PUSCH scrambling. TS 38.211 V15.4.0 subclause 6.3.1.1
@param[in] in Pointer to input bits
@@ -242,7 +241,6 @@ double nr_ue_pbch_freq_offset(const NR_DL_FRAME_PARMS *frame_parms,
nr_initial_sync_t nr_initial_sync(UE_nr_rxtx_proc_t *proc,
PHY_VARS_NR_UE *phy_vars_ue,
int n_frames,
- int sa,
nr_gscn_info_t gscnInfo[MAX_GSCN_BAND],
int numGscn);
diff --git a/openair1/PHY/NR_UE_TRANSPORT/nr_ulsch_coding.c b/openair1/PHY/NR_UE_TRANSPORT/nr_ulsch_coding.c
index 852e87c071..4b769a8668 100644
--- a/openair1/PHY/NR_UE_TRANSPORT/nr_ulsch_coding.c
+++ b/openair1/PHY/NR_UE_TRANSPORT/nr_ulsch_coding.c
@@ -159,8 +159,7 @@ int nr_ulsch_encoding(PHY_VARS_NR_UE *ue,
const uint8_t slot,
unsigned int *G,
int nb_ulsch,
- uint8_t *ULSCH_ids,
- uint16_t number_dmrs_symbols)
+ uint8_t *ULSCH_ids)
{
start_meas_nr_ue_phy(ue, ULSCH_ENCODING_STATS);
diff --git a/openair1/PHY/NR_UE_TRANSPORT/nr_ulsch_ue.c b/openair1/PHY/NR_UE_TRANSPORT/nr_ulsch_ue.c
index 94ee8022a8..881ce016bc 100644
--- a/openair1/PHY/NR_UE_TRANSPORT/nr_ulsch_ue.c
+++ b/openair1/PHY/NR_UE_TRANSPORT/nr_ulsch_ue.c
@@ -435,8 +435,7 @@ static void map_current_symbol(const nr_phy_pxsch_params_t p,
/*
TS 38.211 table 6.4.1.1.3-1 and 2
*/
-static void dmrs_amp_mult(const uint32_t dmrs_port,
- const int Wt,
+static void dmrs_amp_mult(const int Wt,
const int Wf[2],
const c16_t *mod_dmrs,
c16_t *mod_dmrs_out,
@@ -493,9 +492,9 @@ static void map_symbols(const nr_phy_pxsch_params_t p,
c16_t mod_dmrs[ALNARS_16_4(n_dmrs)] __attribute((aligned(16)));
if (p.transform_precoding == transformPrecoder_disabled) {
nr_modulation(gold, n_dmrs * 2, DMRS_MOD_ORDER, (int16_t *)mod_dmrs);
- dmrs_amp_mult(p.dmrs_port, p.Wt, p.Wf, mod_dmrs, mod_dmrs_amp, n_dmrs, p.dmrs_type, p.num_cdm_no_data);
+ dmrs_amp_mult(p.Wt, p.Wf, mod_dmrs, mod_dmrs_amp, n_dmrs, p.dmrs_type, p.num_cdm_no_data);
} else {
- dmrs_amp_mult(p.dmrs_port, p.Wt, p.Wf, dmrs_seq, mod_dmrs_amp, n_dmrs, p.dmrs_type, p.num_cdm_no_data);
+ dmrs_amp_mult(p.Wt, p.Wf, dmrs_seq, mod_dmrs_amp, n_dmrs, p.dmrs_type, p.num_cdm_no_data);
}
} else if ((p.pdu_bit_map & PUSCH_PDU_BITMAP_PUSCH_PTRS) && ptrs_symbol) {
AssertFatal(p.transform_precoding == transformPrecoder_disabled, "PTRS NOT SUPPORTED IF TRANSFORM PRECODING IS ENABLED\n");
@@ -1190,7 +1189,7 @@ void nr_ue_ulsch_procedures(PHY_VARS_NR_UE *UE,
rm_info = calc_rate_match_info_uci(pusch_pdu, harq_process_ul_ue, nl_qm, &G[pusch_id]);
}
- if (nr_ulsch_encoding(UE, &phy_data->ulsch, frame, slot, G, 1, ULSCH_ids, number_dmrs_symbols) == -1) {
+ if (nr_ulsch_encoding(UE, &phy_data->ulsch, frame, slot, G, 1, ULSCH_ids) == -1) {
stop_meas_nr_ue_phy(UE, PUSCH_PROC_STATS);
return;
}
diff --git a/openair1/PHY/NR_UE_TRANSPORT/pucch_nr.c b/openair1/PHY/NR_UE_TRANSPORT/pucch_nr.c
index 51285edd0b..5f54b916b1 100644
--- a/openair1/PHY/NR_UE_TRANSPORT/pucch_nr.c
+++ b/openair1/PHY/NR_UE_TRANSPORT/pucch_nr.c
@@ -52,8 +52,7 @@
//#define ONE_OVER_SQRT2 23170 // 32767/sqrt(2) = 23170 (ONE_OVER_SQRT2)
//#define POLAR_CODING_DEBUG
-void nr_generate_pucch0(const PHY_VARS_NR_UE *ue,
- c16_t **txdataF,
+void nr_generate_pucch0(c16_t **txdataF,
const NR_DL_FRAME_PARMS *frame_parms,
const int16_t amp16,
const int nr_slot_tx,
@@ -156,8 +155,7 @@ void nr_generate_pucch0(const PHY_VARS_NR_UE *ue,
}
}
-void nr_generate_pucch1(const PHY_VARS_NR_UE *ue,
- c16_t **txdataF,
+void nr_generate_pucch1(c16_t **txdataF,
const NR_DL_FRAME_PARMS *frame_parms,
const int16_t amp16,
const int nr_slot_tx,
@@ -752,8 +750,7 @@ void nr_uci_encoding(uint64_t payload, uint8_t nr_bit, uint8_t nrofPRB, bool uci
}
}
//#if 0
-void nr_generate_pucch2(const PHY_VARS_NR_UE *ue,
- c16_t **txdataF,
+void nr_generate_pucch2(c16_t **txdataF,
const NR_DL_FRAME_PARMS *frame_parms,
const int16_t amp16,
const int nr_slot_tx,
@@ -937,8 +934,7 @@ void nr_generate_pucch2(const PHY_VARS_NR_UE *ue,
}
}
//#if 0
-void nr_generate_pucch3_4(const PHY_VARS_NR_UE *ue,
- c16_t **txdataF,
+void nr_generate_pucch3_4(c16_t **txdataF,
const NR_DL_FRAME_PARMS *frame_parms,
const int16_t amp16,
const int nr_slot_tx,
diff --git a/openair1/PHY/NR_UE_TRANSPORT/pucch_nr.h b/openair1/PHY/NR_UE_TRANSPORT/pucch_nr.h
index 7f769872de..47b86c31c0 100644
--- a/openair1/PHY/NR_UE_TRANSPORT/pucch_nr.h
+++ b/openair1/PHY/NR_UE_TRANSPORT/pucch_nr.h
@@ -42,29 +42,25 @@
#include "T.h"
#define ONE_OVER_SQRT2 23170 // 32767/sqrt(2) = 23170 (ONE_OVER_SQRT2)
-void nr_generate_pucch0(const PHY_VARS_NR_UE *ue,
- c16_t **txdataF,
+void nr_generate_pucch0(c16_t **txdataF,
const NR_DL_FRAME_PARMS *frame_parms,
const int16_t amp,
const int nr_slot_tx,
const fapi_nr_ul_config_pucch_pdu *pucch_pdu);
-void nr_generate_pucch1(const PHY_VARS_NR_UE *ue,
- c16_t **txdataF,
+void nr_generate_pucch1(c16_t **txdataF,
const NR_DL_FRAME_PARMS *frame_parms,
const int16_t amp,
const int nr_slot_tx,
const fapi_nr_ul_config_pucch_pdu *pucch_pdu);
-void nr_generate_pucch2(const PHY_VARS_NR_UE *ue,
- c16_t **txdataF,
+void nr_generate_pucch2(c16_t **txdataF,
const NR_DL_FRAME_PARMS *frame_parms,
const int16_t amp,
const int nr_slot_tx,
const fapi_nr_ul_config_pucch_pdu *pucch_pdu);
-void nr_generate_pucch3_4(const PHY_VARS_NR_UE *ue,
- c16_t **txdataF,
+void nr_generate_pucch3_4(c16_t **txdataF,
const NR_DL_FRAME_PARMS *frame_parms,
const int16_t amp,
const int nr_slot_tx,
diff --git a/openair1/PHY/NR_UE_TRANSPORT/sss_nr.c b/openair1/PHY/NR_UE_TRANSPORT/sss_nr.c
index da27ca8603..34751c1742 100644
--- a/openair1/PHY/NR_UE_TRANSPORT/sss_nr.c
+++ b/openair1/PHY/NR_UE_TRANSPORT/sss_nr.c
@@ -189,8 +189,8 @@ void insert_sss_nr(int16_t *sss_time,
static int pss_ch_est_nr(const NR_DL_FRAME_PARMS *frame_parms,
int nid2,
- c16_t pss_ext[NB_ANTENNAS_RX][LENGTH_PSS_NR],
- c16_t sss_ext[NB_ANTENNAS_RX][LENGTH_SSS_NR])
+ c16_t pss_ext[frame_parms->nb_antennas_rx][LENGTH_PSS_NR],
+ c16_t sss_ext[frame_parms->nb_antennas_rx][LENGTH_SSS_NR])
{
int16_t *pss = get_primary_synchro_nr2(nid2);
@@ -250,15 +250,13 @@ static int pss_ch_est_nr(const NR_DL_FRAME_PARMS *frame_parms,
*
*********************************************************************/
-static int do_pss_sss_extract_nr(
- const NR_DL_FRAME_PARMS *frame_parms,
- c16_t pss_ext[NB_ANTENNAS_RX][LENGTH_PSS_NR],
- c16_t sss_ext[NB_ANTENNAS_RX][LENGTH_SSS_NR],
- uint8_t doPss,
- uint8_t doSss,
- uint8_t subframe,
- int ssb_start_subcarrier,
- c16_t rxdataF[][frame_parms->samples_per_slot_wCP]) // add flag to indicate extracting only PSS, only SSS, or both
+static int do_pss_sss_extract_nr(const NR_DL_FRAME_PARMS *frame_parms,
+ c16_t pss_ext[frame_parms->nb_antennas_rx][LENGTH_PSS_NR],
+ c16_t sss_ext[frame_parms->nb_antennas_rx][LENGTH_SSS_NR],
+ uint8_t doPss,
+ uint8_t doSss,
+ int ssb_start_subcarrier,
+ c16_t rxdataF[][frame_parms->samples_per_slot_wCP]) // add flag to indicate extracting only PSS, only SSS, or both
{
AssertFatal(frame_parms->nb_antennas_rx > 0, "UB as sss_ext is not set to any value\n");
@@ -331,9 +329,8 @@ static int do_pss_sss_extract_nr(
*********************************************************************/
static int pss_sss_extract_nr(const NR_DL_FRAME_PARMS *frame_parms,
- c16_t pss_ext[NB_ANTENNAS_RX][LENGTH_PSS_NR],
- c16_t sss_ext[NB_ANTENNAS_RX][LENGTH_SSS_NR],
- uint8_t subframe,
+ c16_t pss_ext[frame_parms->nb_antennas_rx][LENGTH_PSS_NR],
+ c16_t sss_ext[frame_parms->nb_antennas_rx][LENGTH_SSS_NR],
int ssb_start_subcarrier,
c16_t rxdataF[][frame_parms->samples_per_slot_wCP])
{
@@ -342,7 +339,6 @@ static int pss_sss_extract_nr(const NR_DL_FRAME_PARMS *frame_parms,
sss_ext,
1 /* doPss */,
1 /* doSss */,
- subframe,
ssb_start_subcarrier,
rxdataF);
}
@@ -371,8 +367,8 @@ bool rx_sss_nr(const NR_DL_FRAME_PARMS *frame_parms,
c16_t rxdataF[][frame_parms->samples_per_slot_wCP])
{
uint8_t i;
- c16_t pss_ext[NB_ANTENNAS_RX][LENGTH_PSS_NR] = {0};
- c16_t sss_ext[NB_ANTENNAS_RX][LENGTH_SSS_NR] = {0};
+ c16_t pss_ext[frame_parms->nb_antennas_rx][LENGTH_PSS_NR];
+ c16_t sss_ext[frame_parms->nb_antennas_rx][LENGTH_SSS_NR];
uint8_t Nid2 = GET_NID2(nid2);
uint16_t Nid1;
uint8_t phase;
@@ -381,7 +377,7 @@ bool rx_sss_nr(const NR_DL_FRAME_PARMS *frame_parms,
// pss sss extraction
- pss_sss_extract_nr(frame_parms, pss_ext, sss_ext, 0, ssb_start_subcarrier, rxdataF); /* subframe */
+ pss_sss_extract_nr(frame_parms, pss_ext, sss_ext, ssb_start_subcarrier, rxdataF); /* subframe */
#ifdef DEBUG_PLOT_SSS
diff --git a/openair1/PHY/TOOLS/dB_routines.c b/openair1/PHY/TOOLS/dB_routines.c
index 6d56e6d124..13172da86b 100644
--- a/openair1/PHY/TOOLS/dB_routines.c
+++ b/openair1/PHY/TOOLS/dB_routines.c
@@ -21,7 +21,7 @@
#include "tools_defs.h"
-// Approximate 10*log10(x) in fixed point : x = 0...(2^32)-1
+// Approximate 10*log10(x) in fixed point : x = 0...(2^32)-1, where the output is truncated to 10*log10(2^30) = 90 dB
static const int8_t dB_table[256] = {
0, 3, 5, 6, 7, 8, 8, 9, 10, 10, 10, 11, 11, 11, 12, 12, 12, 13, 13, 13, 13, 13, 14, 14, 14, 14, 14, 14, 15, 15, 15, 15,
@@ -131,60 +131,60 @@ int16_t dB_fixed_x10(uint32_t x) {
int16_t dB_fixed_times10(uint32_t x)
{
- int16_t dB_power=0;
+ int16_t dB_power = 0;
- if (x==0) {
- dB_power = 0;
- } else if ( (x&0xff000000) != 0 ) {
- dB_power = dB_table_times10[((x>>24)&255)-1];
- dB_power += 3*dB_table_times10[255];
- } else if ( (x&0x00ff0000) != 0 ) {
- dB_power = dB_table_times10[((x>>16)&255)-1];
- dB_power += 2*dB_table_times10[255];
- } else if ( (x&0x0000ff00) != 0 ) {
- dB_power = dB_table_times10[((x>>8)&255)-1];
+ if (x == 0) {
+ dB_power = -900; // 0 in dB is -INF, but since we're dealing with integer variables, we'll put 10*log10(2^-30) x 10 in the output
+ } else if ((x & 0xff000000) != 0) {
+ dB_power = dB_table_times10[((x >> 24) & 255) - 1];
+ dB_power += 3 * dB_table_times10[255];
+ } else if ((x & 0x00ff0000) != 0) {
+ dB_power = dB_table_times10[((x >> 16) & 255) - 1];
+ dB_power += 2 * dB_table_times10[255];
+ } else if ((x & 0x0000ff00) != 0) {
+ dB_power = dB_table_times10[((x >> 8) & 255) - 1];
dB_power += dB_table_times10[255];
} else {
- dB_power = dB_table_times10[(x&255)-1];
+ dB_power = dB_table_times10[(x & 255) - 1];
}
if (dB_power > 900)
- return(900);
+ return (900);
return dB_power;
}
-
int8_t dB_fixed(uint32_t x)
{
- int8_t dB_power=0;
+ int8_t dB_power = 0;
- if (x==0) {
- dB_power = 0;
- } else if ( (x&0xff000000) != 0 ) {
- dB_power = dB_table[((x>>24)&255)-1];
- dB_power += 3*dB_table[255];
- } else if ( (x&0x00ff0000) != 0 ) {
- dB_power = dB_table[((x>>16)&255)-1];
- dB_power += 2*dB_table[255];
- } else if ( (x&0x0000ff00) != 0 ) {
- dB_power = dB_table[((x>>8)&255)-1];
+ if (x == 0) {
+ dB_power = -90; // 0 in dB is -INF, but since we're dealing with integer variables, we'll put 10*log10(2^-30) in the output
+ } else if ((x & 0xff000000) != 0) {
+ dB_power = dB_table[((x >> 24) & 255) - 1];
+ dB_power += 3 * dB_table[255];
+ } else if ((x & 0x00ff0000) != 0) {
+ dB_power = dB_table[((x >> 16) & 255) - 1];
+ dB_power += 2 * dB_table[255];
+ } else if ((x & 0x0000ff00) != 0) {
+ dB_power = dB_table[((x >> 8) & 255) - 1];
dB_power += dB_table[255];
} else {
- dB_power = dB_table[(x&255)-1];
+ dB_power = dB_table[(x & 255) - 1];
}
if (dB_power > 90)
- return(90);
+ return (90);
return dB_power;
}
-
-uint8_t dB_fixed64(uint64_t x)
+int8_t dB_fixed64(uint64_t x)
{
- if ((x<(((uint64_t)1)<<32))) return(dB_fixed((uint32_t)x));
- else return(4*dB_table[255]+dB_fixed((uint32_t)(x>>32)));
+ if ((x < (((uint64_t)1) << 32)))
+ return (dB_fixed((uint32_t)x));
+ else
+ return (4 * dB_table[255] + dB_fixed((uint32_t)(x >> 32)));
}
diff --git a/openair1/PHY/TOOLS/tools_defs.h b/openair1/PHY/TOOLS/tools_defs.h
index 40f6ca46f6..abe2ded220 100644
--- a/openair1/PHY/TOOLS/tools_defs.h
+++ b/openair1/PHY/TOOLS/tools_defs.h
@@ -961,7 +961,7 @@ uint32_t angle(struct complex16 perrror);
unsigned char factor2(unsigned int x);
int8_t dB_fixed(uint32_t x);
-uint8_t dB_fixed64(uint64_t x);
+int8_t dB_fixed64(uint64_t x);
int8_t dB_fixed2(uint32_t x,uint32_t y);
int16_t dB_fixed_times10(uint32_t x);
int16_t dB_fixed_x10(uint32_t x);
diff --git a/openair1/PHY/defs_RU.h b/openair1/PHY/defs_RU.h
index 851d417804..0873340445 100644
--- a/openair1/PHY/defs_RU.h
+++ b/openair1/PHY/defs_RU.h
@@ -45,7 +45,7 @@
#define MAX_BANDS_PER_RRU 4
#define MAX_RRU_CONFIG_SIZE 1024
-
+typedef struct NR_DL_FRAME_PARMS_s NR_DL_FRAME_PARMS;
typedef enum {
normal_txrx=0,
@@ -176,7 +176,7 @@ typedef struct {
int slot;
const c16_t *rxdata;
c16_t *rxdataF;
- const struct NR_DL_FRAME_PARMS *fp;
+ const NR_DL_FRAME_PARMS *fp;
int32_t sample_offet;
task_ans_t *ans;
} feprx_cmd_t;
@@ -491,8 +491,8 @@ typedef struct RU_t_s {
/// FAPI confiuration
nfapi_nr_config_request_scf_t config;
/// Frame parameters
- struct LTE_DL_FRAME_PARMS *frame_parms;
- struct NR_DL_FRAME_PARMS *nr_frame_parms;
+ struct LTE_DL_FRAME_PARMS_s *frame_parms;
+ struct NR_DL_FRAME_PARMS_s *nr_frame_parms;
///timing offset used in TDD
int N_TA_offset;
/// SF extension used in TDD (unit: number of samples at 30.72MHz) (this is an expert option)
diff --git a/openair1/PHY/defs_UE.h b/openair1/PHY/defs_UE.h
index 82cc747581..c6521e0c74 100644
--- a/openair1/PHY/defs_UE.h
+++ b/openair1/PHY/defs_UE.h
@@ -206,15 +206,15 @@ typedef struct {
//! estimated noise power (linear)
unsigned int n0_power[NB_ANTENNAS_RX];
//! estimated noise power (dB)
- unsigned short n0_power_dB[NB_ANTENNAS_RX];
+ short n0_power_dB[NB_ANTENNAS_RX];
//! total estimated noise power (linear)
unsigned int n0_power_tot;
//! total estimated noise power (dB)
- unsigned short n0_power_tot_dB;
+ short n0_power_tot_dB;
//! average estimated noise power (linear)
unsigned int n0_power_avg;
//! average estimated noise power (dB)
- unsigned short n0_power_avg_dB;
+ short n0_power_avg_dB;
//! total estimated noise power (dBm)
short n0_power_tot_dBm;
@@ -222,24 +222,24 @@ typedef struct {
//! estimated received spatial signal power (linear)
int rx_spatial_power[NUMBER_OF_CONNECTED_eNB_MAX][2][2];
//! estimated received spatial signal power (dB)
- unsigned short rx_spatial_power_dB[NUMBER_OF_CONNECTED_eNB_MAX][2][2];
+ short rx_spatial_power_dB[NUMBER_OF_CONNECTED_eNB_MAX][2][2];
/// estimated received signal power (sum over all TX antennas)
//int wideband_cqi[NUMBER_OF_CONNECTED_eNB_MAX][NB_ANTENNAS_RX];
int rx_power[NUMBER_OF_CONNECTED_eNB_MAX][NB_ANTENNAS_RX];
/// estimated received signal power (sum over all TX antennas)
//int wideband_cqi_dB[NUMBER_OF_CONNECTED_eNB_MAX][NB_ANTENNAS_RX];
- unsigned short rx_power_dB[NUMBER_OF_CONNECTED_eNB_MAX][NB_ANTENNAS_RX];
+ short rx_power_dB[NUMBER_OF_CONNECTED_eNB_MAX][NB_ANTENNAS_RX];
/// estimated received signal power (sum over all TX/RX antennas)
int rx_power_tot[NUMBER_OF_CONNECTED_eNB_MAX]; //NEW
/// estimated received signal power (sum over all TX/RX antennas)
- unsigned short rx_power_tot_dB[NUMBER_OF_CONNECTED_eNB_MAX]; //NEW
+ short rx_power_tot_dB[NUMBER_OF_CONNECTED_eNB_MAX]; //NEW
//! estimated received signal power (sum of all TX/RX antennas, time average)
int rx_power_avg[NUMBER_OF_CONNECTED_eNB_MAX];
//! estimated received signal power (sum of all TX/RX antennas, time average, in dB)
- unsigned short rx_power_avg_dB[NUMBER_OF_CONNECTED_eNB_MAX];
+ short rx_power_avg_dB[NUMBER_OF_CONNECTED_eNB_MAX];
/// SINR (sum of all TX/RX antennas, in dB)
int wideband_cqi_tot[NUMBER_OF_CONNECTED_eNB_MAX];
diff --git a/openair1/PHY/defs_common.h b/openair1/PHY/defs_common.h
index 04d99108a1..b728fe89f0 100644
--- a/openair1/PHY/defs_common.h
+++ b/openair1/PHY/defs_common.h
@@ -598,8 +598,7 @@ typedef struct {
int non_mbsfn_SubframeConfig;
} NonMBSFN_config_t;
-
-typedef struct LTE_DL_FRAME_PARMS {
+typedef struct LTE_DL_FRAME_PARMS_s {
/// Number of resource blocks (RB) in DL
uint8_t N_RB_DL;
/// Number of resource blocks (RB) in UL
diff --git a/openair1/PHY/defs_eNB.h b/openair1/PHY/defs_eNB.h
index 441c7b8f96..ebb7013cc0 100644
--- a/openair1/PHY/defs_eNB.h
+++ b/openair1/PHY/defs_eNB.h
@@ -419,17 +419,17 @@ typedef struct {
//! estimated noise power (linear)
unsigned int n0_power[MAX_NUM_RU_PER_eNB];
//! estimated noise power (dB)
- unsigned short n0_power_dB[MAX_NUM_RU_PER_eNB];
+ short n0_power_dB[MAX_NUM_RU_PER_eNB];
//! total estimated noise power (linear)
unsigned int n0_power_tot;
//! estimated avg noise power (dB)
- unsigned short n0_power_tot_dB;
+ short n0_power_tot_dB;
//! estimated avg noise power (dB)
short n0_power_tot_dBm;
//! estimated avg noise power per RB per RX ant (lin)
unsigned short n0_subband_power[MAX_NUM_RU_PER_eNB][100];
//! estimated avg noise power per RB per RX ant (dB)
- unsigned short n0_subband_power_dB[MAX_NUM_RU_PER_eNB][100];
+ short n0_subband_power_dB[MAX_NUM_RU_PER_eNB][100];
//! estimated avg noise power per RB (dB)
short n0_subband_power_tot_dB[100];
//! estimated avg noise power per RB (dBm)
@@ -440,7 +440,7 @@ typedef struct {
//! estimated received spatial signal power (linear)
unsigned int rx_spatial_power[NUMBER_OF_SRS_MAX][2][2];
//! estimated received spatial signal power (dB)
- unsigned short rx_spatial_power_dB[NUMBER_OF_SRS_MAX][2][2];
+ short rx_spatial_power_dB[NUMBER_OF_SRS_MAX][2][2];
//! estimated rssi (dBm)
short rx_rssi_dBm[NUMBER_OF_SRS_MAX];
//! estimated correlation (wideband linear) between spatial channels (computed in dlsch_demodulation)
@@ -453,7 +453,7 @@ typedef struct {
/// Wideband CQI in dB (= SINR dB)
int wideband_cqi_dB[NUMBER_OF_SRS_MAX][MAX_NUM_RU_PER_eNB];
/// Wideband CQI (sum of all RX antennas, in dB)
- char wideband_cqi_tot[NUMBER_OF_SRS_MAX];
+ int wideband_cqi_tot[NUMBER_OF_SRS_MAX];
/// Subband CQI per RX antenna and RB (= SINR)
int subband_cqi[NUMBER_OF_SRS_MAX][MAX_NUM_RU_PER_eNB][100];
/// Total Subband CQI and RB (= SINR)
diff --git a/openair1/PHY/defs_gNB.h b/openair1/PHY/defs_gNB.h
index b1113517c6..92523d94ee 100644
--- a/openair1/PHY/defs_gNB.h
+++ b/openair1/PHY/defs_gNB.h
@@ -319,17 +319,17 @@ typedef struct {
//! estimated noise power (linear)
unsigned int n0_power[MAX_NUM_RU_PER_gNB];
//! estimated noise power (dB)
- unsigned int n0_power_dB[MAX_NUM_RU_PER_gNB];
+ int n0_power_dB[MAX_NUM_RU_PER_gNB];
//! total estimated noise power (linear)
unsigned int n0_power_tot;
//! estimated avg noise power (dB)
- unsigned int n0_power_tot_dB;
+ int n0_power_tot_dB;
//! estimated avg noise power per RB per RX ant (lin)
fourDimArray_t *n0_subband_power;
//! estimated avg subband noise power (dB)
- unsigned int n0_subband_power_avg_dB;
+ int n0_subband_power_avg_dB;
//! estimated avg subband noise power per antenna (dB)
- unsigned int n0_subband_power_avg_perANT_dB[MAX_ANT];
+ int n0_subband_power_avg_perANT_dB[MAX_ANT];
//! estimated avg noise power per RB (dB)
int n0_subband_power_tot_dB[275];
/// PRACH background noise level
diff --git a/openair1/PHY/defs_nr_UE.h b/openair1/PHY/defs_nr_UE.h
index c14751a050..eb0403a2ba 100644
--- a/openair1/PHY/defs_nr_UE.h
+++ b/openair1/PHY/defs_nr_UE.h
@@ -104,18 +104,11 @@
/// Context data structure for gNB subframe processing
typedef struct {
/// Component Carrier index
- uint8_t CC_id;
+ uint8_t CC_id;
/// Last RX timestamp
openair0_timestamp_t timestamp_rx;
} UE_nr_proc_t;
-typedef enum {
- NR_PBCH_EST=0,
- NR_PDCCH_EST,
- NR_PDSCH_EST,
- NR_SSS_EST,
-} NR_CHANNEL_EST_t;
-
#define debug_msg if (((mac_xface->frame%100) == 0) || (mac_xface->frame < 50)) msg
#define NEIGHBOR_CELL_MAX_CONSECUTIVE_FAILURES 10
@@ -144,18 +137,14 @@ typedef struct {
int ssb_rsrp_dBm[64];
float ssb_sinr_dB[64];
// common measurements
- //! estimated noise power (linear)
- unsigned int n0_power[NB_ANTENNAS_RX];
- //! estimated noise power (dB)
- unsigned short n0_power_dB[NB_ANTENNAS_RX];
//! total estimated noise power (linear)
unsigned int n0_power_tot;
//! total estimated noise power (dB)
- unsigned short n0_power_tot_dB;
+ short n0_power_tot_dB;
//! average estimated noise power (linear)
unsigned int n0_power_avg;
//! average estimated noise power (dB)
- unsigned short n0_power_avg_dB;
+ short n0_power_avg_dB;
//! total estimated noise power (dBm)
short n0_power_tot_dBm;
@@ -165,59 +154,27 @@ typedef struct {
//! estimated received spatial signal power (dB)
fourDimArray_t *rx_spatial_power_dB;
- /// estimated received signal power (sum over all TX antennas)
- int rx_power[NUMBER_OF_CONNECTED_gNB_MAX][NB_ANTENNAS_RX];
- /// estimated received signal power (sum over all TX antennas)
- unsigned short rx_power_dB[NUMBER_OF_CONNECTED_gNB_MAX][NB_ANTENNAS_RX];
-
/// estimated received signal power (sum over all TX/RX antennas)
- int rx_power_tot[NUMBER_OF_CONNECTED_gNB_MAX]; //NEW
+ int rx_power_tot[NUMBER_OF_CONNECTED_gNB_MAX]; //NEW
/// estimated received signal power (sum over all TX/RX antennas)
- unsigned short rx_power_tot_dB[NUMBER_OF_CONNECTED_gNB_MAX]; //NEW
+ short rx_power_tot_dB[NUMBER_OF_CONNECTED_gNB_MAX]; //NEW
//! estimated received signal power (sum of all TX/RX antennas, time average)
- int rx_power_avg[NUMBER_OF_CONNECTED_gNB_MAX];
+ int rx_power_avg[NUMBER_OF_CONNECTED_gNB_MAX];
//! estimated received signal power (sum of all TX/RX antennas, time average, in dB)
- unsigned short rx_power_avg_dB[NUMBER_OF_CONNECTED_gNB_MAX];
+ short rx_power_avg_dB[NUMBER_OF_CONNECTED_gNB_MAX];
/// SINR (sum of all TX/RX antennas, in dB)
- int wideband_cqi_tot[NUMBER_OF_CONNECTED_gNB_MAX];
+ int wideband_cqi_tot[NUMBER_OF_CONNECTED_gNB_MAX];
/// SINR (sum of all TX/RX antennas, time average, in dB)
- int wideband_cqi_avg[NUMBER_OF_CONNECTED_gNB_MAX];
+ int wideband_cqi_avg[NUMBER_OF_CONNECTED_gNB_MAX];
//! estimated rssi (dBm)
- short rx_rssi_dBm[NUMBER_OF_CONNECTED_gNB_MAX];
- //! estimated correlation (wideband linear) between spatial channels (computed in dlsch_demodulation)
- int rx_correlation[NUMBER_OF_CONNECTED_gNB_MAX][NB_ANTENNAS_RX][NR_MAX_NB_LAYERS*NR_MAX_NB_LAYERS];//
- //! estimated correlation (wideband dB) between spatial channels (computed in dlsch_demodulation)
- int rx_correlation_dB[NUMBER_OF_CONNECTED_gNB_MAX][2];
+ short rx_rssi_dBm[NUMBER_OF_CONNECTED_gNB_MAX];
- /// Wideband CQI (sum of all RX antennas, in dB, for precoded transmission modes (3,4,5,6), up to 4 spatial streams)
- int precoded_cqi_dB[NUMBER_OF_CONNECTED_gNB_MAX+1][4];
- /// Subband CQI per RX antenna (= SINR)
- int subband_cqi[NUMBER_OF_CONNECTED_gNB_MAX][NB_ANTENNAS_RX][NUMBER_OF_SUBBANDS_MAX];
- /// Total Subband CQI (= SINR)
- int subband_cqi_tot[NUMBER_OF_CONNECTED_gNB_MAX][NUMBER_OF_SUBBANDS_MAX];
- /// Subband CQI in dB (= SINR dB)
- int subband_cqi_dB[NUMBER_OF_CONNECTED_gNB_MAX][NB_ANTENNAS_RX][NUMBER_OF_SUBBANDS_MAX];
- /// Total Subband CQI
- int subband_cqi_tot_dB[NUMBER_OF_CONNECTED_gNB_MAX][NUMBER_OF_SUBBANDS_MAX];
- /// Wideband PMI for each RX antenna
- int wideband_pmi_re[NUMBER_OF_CONNECTED_gNB_MAX][NB_ANTENNAS_RX];
- /// Wideband PMI for each RX antenna
- int wideband_pmi_im[NUMBER_OF_CONNECTED_gNB_MAX][NB_ANTENNAS_RX];
- ///Subband PMI for each RX antenna
- int subband_pmi_re[NUMBER_OF_CONNECTED_gNB_MAX][NUMBER_OF_SUBBANDS_MAX][NB_ANTENNAS_RX];
- ///Subband PMI for each RX antenna
- int subband_pmi_im[NUMBER_OF_CONNECTED_gNB_MAX][NUMBER_OF_SUBBANDS_MAX][NB_ANTENNAS_RX];
- /// chosen RX antennas (1=Rx antenna 1, 2=Rx antenna 2, 3=both Rx antennas)
- unsigned char selected_rx_antennas[NUMBER_OF_CONNECTED_gNB_MAX][NUMBER_OF_SUBBANDS_MAX];
- /// Wideband Rank indication
- unsigned char rank[NUMBER_OF_CONNECTED_gNB_MAX];
/// Number of RX Antennas
unsigned char nb_antennas_rx;
- /// DLSCH error counter
- // short dlsch_errors;
+
/// Info about neighboring cells to perform the measurements
neighboring_cell_info_t neighboring_cell_info[NUMBER_OF_NEIGHBORING_CELLS_MAX];
bool meas_request_pending;
@@ -263,17 +220,6 @@ typedef struct {
#define MAX_NR_DCI_DECODED_SLOT 10 // This value is not specified
-typedef enum {
- _format_0_0_found = 0,
- _format_0_1_found = 1,
- _format_1_0_found = 2,
- _format_1_1_found = 3,
- _format_2_0_found = 4,
- _format_2_1_found = 5,
- _format_2_2_found = 6,
- _format_2_3_found = 7
-} format_found_t;
-
#endif
typedef struct {
int nb_search_space;
@@ -282,18 +228,6 @@ typedef struct {
#define NR_PSBCH_DMRS_LENGTH 297 // in mod symbols
#define NR_PSBCH_DMRS_LENGTH_DWORD 20 // ceil(2(QPSK)*NR_PBCH_DMRS_LENGTH/32)
-
-/* NR Sidelink PSBCH payload fields
- TODO: This will be removed in the future and
- filled in by the upper layers once developed. */
-typedef struct {
- uint32_t coverageIndicator : 1;
- uint32_t tddConfig : 12;
- uint32_t DFN : 10;
- uint32_t slotIndex : 7;
- uint32_t reserved : 2;
-} PSBCH_payload;
-
#define PBCH_A 24
typedef struct {
@@ -426,15 +360,11 @@ typedef struct PHY_VARS_NR_UE_s {
fapi_nr_config_request_t nrUE_config;
nr_synch_request_t synch_request;
- NR_UE_PRACH *prach_vars[NUMBER_OF_CONNECTED_gNB_MAX];
- NR_UE_PRS *prs_vars[NR_MAX_PRS_COMB_SIZE];
- uint8_t prs_active_gNBs;
+ NR_UE_PRACH *prach_vars[NUMBER_OF_CONNECTED_gNB_MAX];
+ NR_UE_PRS *prs_vars[NR_MAX_PRS_COMB_SIZE];
+ uint8_t prs_active_gNBs;
NR_DL_UE_HARQ_t dl_harq_processes[2][NR_MAX_DLSCH_HARQ_PROCESSES];
NR_UL_UE_HARQ_t ul_harq_processes[NR_MAX_ULSCH_HARQ_PROCESSES];
- //Paging parameters
- uint32_t IMSImod1024;
- uint32_t PF;
- uint32_t PO;
// Scrambling IDs used in PUSCH DMRS
c16_t X_u[64][839];
@@ -463,21 +393,6 @@ typedef struct PHY_VARS_NR_UE_s {
int dlsch_received[NUMBER_OF_CONNECTED_gNB_MAX];
int dlsch_received_last[NUMBER_OF_CONNECTED_gNB_MAX];
int dlsch_fer[NUMBER_OF_CONNECTED_gNB_MAX];
- int dlsch_SI_received[NUMBER_OF_CONNECTED_gNB_MAX];
- int dlsch_SI_errors[NUMBER_OF_CONNECTED_gNB_MAX];
- int dlsch_ra_received[NUMBER_OF_CONNECTED_gNB_MAX];
- int dlsch_ra_errors[NUMBER_OF_CONNECTED_gNB_MAX];
- int dlsch_p_received[NUMBER_OF_CONNECTED_gNB_MAX];
- int dlsch_p_errors[NUMBER_OF_CONNECTED_gNB_MAX];
- int dlsch_mch_received[NUMBER_OF_CONNECTED_gNB_MAX];
- int current_dlsch_cqi[NUMBER_OF_CONNECTED_gNB_MAX];
- int dlsch_mch_received_sf[MAX_MBSFN_AREA][NUMBER_OF_CONNECTED_gNB_MAX];
- int dlsch_mcch_received[MAX_MBSFN_AREA][NUMBER_OF_CONNECTED_gNB_MAX];
- int dlsch_mtch_received[MAX_MBSFN_AREA][NUMBER_OF_CONNECTED_gNB_MAX];
- int dlsch_mcch_errors[MAX_MBSFN_AREA][NUMBER_OF_CONNECTED_gNB_MAX];
- int dlsch_mtch_errors[MAX_MBSFN_AREA][NUMBER_OF_CONNECTED_gNB_MAX];
- int dlsch_mcch_trials[MAX_MBSFN_AREA][NUMBER_OF_CONNECTED_gNB_MAX];
- int dlsch_mtch_trials[MAX_MBSFN_AREA][NUMBER_OF_CONNECTED_gNB_MAX];
uint8_t init_sync_frame;
/// temporary offset during cell search prior to MIB decoding
int ssb_offset;
diff --git a/openair1/PHY/defs_nr_common.h b/openair1/PHY/defs_nr_common.h
index 199877d738..20fc744f57 100644
--- a/openair1/PHY/defs_nr_common.h
+++ b/openair1/PHY/defs_nr_common.h
@@ -156,9 +156,7 @@ typedef struct {
} prach_list_t;
void init_prach_list(prach_list_t *);
-typedef struct NR_DL_FRAME_PARMS NR_DL_FRAME_PARMS;
-
-struct NR_DL_FRAME_PARMS {
+typedef struct NR_DL_FRAME_PARMS_s {
/// frequency range
frequency_range_t freq_range;
// /// Placeholder to replace overlapping fields below
@@ -269,7 +267,7 @@ struct NR_DL_FRAME_PARMS {
uint16_t tdd_slot_config;
uint8_t tdd_period;
bool print_ue_help_cmdline_log;
-};
+} NR_DL_FRAME_PARMS;
// PRS config structures
typedef struct {
@@ -305,6 +303,29 @@ typedef struct {
int32_t reserved;
} prs_meas_t;
+// Configuration parameters required for 5G Positioning
+// TRP Cartesian Coordinate information
+typedef struct trp_s {
+ // TRP id
+ uint32_t id;
+ // TRP x-axis value
+ uint32_t x_axis;
+ // TRP y-axis value
+ uint32_t y_axis;
+ // TRP z-axis value
+ uint32_t z_axis;
+ // 0 = mm, 1 = cm, 2 = dm
+ uint8_t unit;
+} trp_t;
+
+#define MAX_NUM_TRPs 8
+typedef struct {
+ trp_t trps[MAX_NUM_TRPs];
+ uint8_t num_trp;
+ // Serving gNB indicator
+ bool is_serving_gNB;
+} positioning_config_t;
+
// rel16 prs k_prime table as per ts138.211 sec.7.4.1.7.2
#define K_PRIME_TABLE_ROW_SIZE 4
#define K_PRIME_TABLE_COL_SIZE 12
diff --git a/openair1/PHY/impl_defs_top_NB_IoT.h b/openair1/PHY/impl_defs_top_NB_IoT.h
index 8d05e9a05e..4179a865b8 100644
--- a/openair1/PHY/impl_defs_top_NB_IoT.h
+++ b/openair1/PHY/impl_defs_top_NB_IoT.h
@@ -55,15 +55,15 @@ typedef struct {
//! estimated noise power (linear)
unsigned int n0_power[NB_ANTENNAS_RX];
//! estimated noise power (dB)
- unsigned short n0_power_dB[NB_ANTENNAS_RX];
+ short n0_power_dB[NB_ANTENNAS_RX];
//! total estimated noise power (linear)
unsigned int n0_power_tot;
//! total estimated noise power (dB)
- unsigned short n0_power_tot_dB;
+ short n0_power_tot_dB;
//! average estimated noise power (linear)
unsigned int n0_power_avg;
//! average estimated noise power (dB)
- unsigned short n0_power_avg_dB;
+ short n0_power_avg_dB;
//! total estimated noise power (dBm)
short n0_power_tot_dBm;
@@ -71,24 +71,24 @@ typedef struct {
//! estimated received spatial signal power (linear)
int rx_spatial_power[NUMBER_OF_CONNECTED_eNB_MAX][2][2];
//! estimated received spatial signal power (dB)
- unsigned short rx_spatial_power_dB[NUMBER_OF_CONNECTED_eNB_MAX][2][2];
+ short rx_spatial_power_dB[NUMBER_OF_CONNECTED_eNB_MAX][2][2];
/// estimated received signal power (sum over all TX antennas)
//int wideband_cqi[NUMBER_OF_CONNECTED_eNB_MAX][NB_ANTENNAS_RX];
int rx_power[NUMBER_OF_CONNECTED_eNB_MAX][NB_ANTENNAS_RX];
/// estimated received signal power (sum over all TX antennas)
//int wideband_cqi_dB[NUMBER_OF_CONNECTED_eNB_MAX][NB_ANTENNAS_RX];
- unsigned short rx_power_dB[NUMBER_OF_CONNECTED_eNB_MAX][NB_ANTENNAS_RX];
+ short rx_power_dB[NUMBER_OF_CONNECTED_eNB_MAX][NB_ANTENNAS_RX];
/// estimated received signal power (sum over all TX/RX antennas)
int rx_power_tot[NUMBER_OF_CONNECTED_eNB_MAX]; //NEW
/// estimated received signal power (sum over all TX/RX antennas)
- unsigned short rx_power_tot_dB[NUMBER_OF_CONNECTED_eNB_MAX]; //NEW
+ short rx_power_tot_dB[NUMBER_OF_CONNECTED_eNB_MAX]; //NEW
//! estimated received signal power (sum of all TX/RX antennas, time average)
int rx_power_avg[NUMBER_OF_CONNECTED_eNB_MAX];
//! estimated received signal power (sum of all TX/RX antennas, time average, in dB)
- unsigned short rx_power_avg_dB[NUMBER_OF_CONNECTED_eNB_MAX];
+ short rx_power_avg_dB[NUMBER_OF_CONNECTED_eNB_MAX];
/// SINR (sum of all TX/RX antennas, in dB)
int wideband_cqi_tot[NUMBER_OF_CONNECTED_eNB_MAX];
@@ -141,17 +141,17 @@ typedef struct {
//! estimated noise power (linear)
unsigned int n0_power[NB_ANTENNAS_RX];
//! estimated noise power (dB)
- unsigned short n0_power_dB[NB_ANTENNAS_RX];
+ short n0_power_dB[NB_ANTENNAS_RX];
//! total estimated noise power (linear)
unsigned int n0_power_tot;
//! estimated avg noise power (dB)
- unsigned short n0_power_tot_dB;
+ short n0_power_tot_dB;
//! estimated avg noise power (dB)
short n0_power_tot_dBm;
//! estimated avg noise power per RB per RX ant (lin)
unsigned short n0_subband_power[NB_ANTENNAS_RX][100];
//! estimated avg noise power per RB per RX ant (dB)
- unsigned short n0_subband_power_dB[NB_ANTENNAS_RX][100];
+ short n0_subband_power_dB[NB_ANTENNAS_RX][100];
//! estimated avg noise power per RB (dB)
short n0_subband_power_tot_dB[100];
//! estimated avg noise power per RB (dBm)
@@ -160,7 +160,7 @@ typedef struct {
//! estimated received spatial signal power (linear)
unsigned int rx_spatial_power[NUMBER_OF_UE_MAX][2][2];
//! estimated received spatial signal power (dB)
- unsigned short rx_spatial_power_dB[NUMBER_OF_UE_MAX][2][2];
+ short rx_spatial_power_dB[NUMBER_OF_UE_MAX][2][2];
//! estimated rssi (dBm)
short rx_rssi_dBm[NUMBER_OF_UE_MAX];
//! estimated correlation (wideband linear) between spatial channels (computed in dlsch_demodulation)
@@ -173,7 +173,7 @@ typedef struct {
/// Wideband CQI in dB (= SINR dB)
int wideband_cqi_dB[NUMBER_OF_UE_MAX][NB_ANTENNAS_RX];
/// Wideband CQI (sum of all RX antennas, in dB)
- char wideband_cqi_tot[NUMBER_OF_UE_MAX];
+ int wideband_cqi_tot[NUMBER_OF_UE_MAX];
/// Subband CQI per RX antenna and RB (= SINR)
int subband_cqi[NUMBER_OF_UE_MAX][NB_ANTENNAS_RX][100];
/// Total Subband CQI and RB (= SINR)
diff --git a/openair1/PHY/nr_phy_common/inc/nr_phy_common.h b/openair1/PHY/nr_phy_common/inc/nr_phy_common.h
index b4c0e1239c..67bed6eef4 100644
--- a/openair1/PHY/nr_phy_common/inc/nr_phy_common.h
+++ b/openair1/PHY/nr_phy_common/inc/nr_phy_common.h
@@ -389,4 +389,9 @@ void nr_generate_csi_rs(const NR_DL_FRAME_PARMS *frame_parms,
const uint8_t cdm_type,
c16_t **dataF);
+int nr_get_ssb_start_sc(int scs,
+ int ssb_offset_point_a,
+ int ssb_sco,
+ frequency_range_t freq_range);
+
#endif
diff --git a/openair1/PHY/nr_phy_common/src/nr_phy_common.c b/openair1/PHY/nr_phy_common/src/nr_phy_common.c
index a723780f94..c29a3a4936 100644
--- a/openair1/PHY/nr_phy_common/src/nr_phy_common.c
+++ b/openair1/PHY/nr_phy_common/src/nr_phy_common.c
@@ -481,3 +481,26 @@ void nr_fo_compensation(double fo_Hz, int samples_per_ms, int sample_offset, con
mult_complex_vectors(rxdata_in, rot, rxdata_out, size, 14);
#endif
}
+
+/*!
+* Setting the first subcarrier
+* 3GPP TS 38.211 sections 7.4.3.1 and 4.4.4.2
+* for FR1 offsetToPointA and k_SSB are expressed in terms of 15 kHz SCS
+* for FR2 offsetToPointA is expressed in terms of 60 kHz SCS and k_SSB expressed in terms of the SCS provided
+* by the higher-layer parameter subCarrierSpacingCommon
+*/
+int nr_get_ssb_start_sc(int scs, int ssb_offset_point_a, int ssb_sco, frequency_range_t freq_range)
+{
+ const int prb_offset =
+ (freq_range == FR1) ? ssb_offset_point_a >> scs : ssb_offset_point_a >> (scs - 2);
+ const int sc_offset =
+ (freq_range == FR1) ? ssb_sco >> scs : ssb_sco;
+
+ int ssb_start_subcarrier = (12 * prb_offset + sc_offset);
+
+ LOG_D(NR_PHY, "prb_offset:%d, ssb_subcarrier_offset:%d,scs :%d, Fr:%d, ssb_start_subcarrier:%d\n",
+ prb_offset, ssb_sco, scs, freq_range, ssb_start_subcarrier);
+
+ return ssb_start_subcarrier;
+
+}
diff --git a/openair1/SCHED/nfapi_lte_dummy.c b/openair1/SCHED/nfapi_lte_dummy.c
index 5ddf2d3485..82a8a77309 100644
--- a/openair1/SCHED/nfapi_lte_dummy.c
+++ b/openair1/SCHED/nfapi_lte_dummy.c
@@ -4,11 +4,8 @@
#include "nfapi/open-nFAPI/nfapi/public_inc/nfapi_nr_interface_scf.h"
#include "openair2/NR_PHY_INTERFACE/NR_IF_Module.h"
#include "openair1/PHY/LTE_TRANSPORT/transport_common.h"
-typedef struct pnf_t pnf_t;
-typedef struct pnf_p7_t pnf_p7_t;
-typedef struct vnf_t vnf_t;
-typedef struct vnf_p7_t vnf_p7_t;
-
+#include "nfapi/open-nFAPI/vnf/inc/vnf.h"
+#include "nfapi/open-nFAPI/pnf/inc/pnf.h"
int l1_north_init_gNB(void){return 0;}
int slot_ahead = 6;
diff --git a/openair1/SCHED/prach_procedures.c b/openair1/SCHED/prach_procedures.c
index 968a94eeb0..3c8dbe8d6e 100644
--- a/openair1/SCHED/prach_procedures.c
+++ b/openair1/SCHED/prach_procedures.c
@@ -47,11 +47,12 @@
extern int oai_nfapi_rach_ind(nfapi_rach_indication_t *rach_ind);
-void prach_procedures(PHY_VARS_eNB *eNB,
- int br_flag ) {
- uint16_t max_preamble[4]={0},max_preamble_energy[4]={0},max_preamble_delay[4]={0},avg_preamble_energy[4]={0};
+void prach_procedures(PHY_VARS_eNB *eNB, int br_flag)
+{
+ uint16_t max_preamble[4] = {0}, max_preamble_energy[4] = {0}, max_preamble_delay[4] = {0};
+ int16_t avg_preamble_energy[4] = {0};
uint16_t i;
- int frame,subframe;
+ int frame, subframe;
if (br_flag==1) {
subframe = eNB->proc.subframe_prach_br;
diff --git a/openair1/SCHED_NR/nr_ru_procedures.c b/openair1/SCHED_NR/nr_ru_procedures.c
index eb2c83c10a..ca712bbaf9 100644
--- a/openair1/SCHED_NR/nr_ru_procedures.c
+++ b/openair1/SCHED_NR/nr_ru_procedures.c
@@ -35,7 +35,7 @@
#include "sched_nr.h"
#include "PHY/MODULATION/modulation_common.h"
#include "PHY/MODULATION/nr_modulation.h"
-
+#include "openair1/PHY/defs_nr_common.h"
#include "common/utils/LOG/log.h"
#include "common/utils/system.h"
diff --git a/openair1/SCHED_NR/phy_procedures_nr_gNB.c b/openair1/SCHED_NR/phy_procedures_nr_gNB.c
index e304fe3dc9..4e69f8fa69 100644
--- a/openair1/SCHED_NR/phy_procedures_nr_gNB.c
+++ b/openair1/SCHED_NR/phy_procedures_nr_gNB.c
@@ -118,9 +118,10 @@ void nr_common_signal_procedures(PHY_VARS_gNB *gNB, int frame, int slot, const n
// by the higher-layer parameter subCarrierSpacingCommon
nfapi_nr_config_request_scf_t *cfg = &gNB->gNB_config;
const int scs = cfg->ssb_config.scs_common.value;
- const int prb_offset = (fp->freq_range == FR1) ? pdu->ssbOffsetPointA >> scs : pdu->ssbOffsetPointA >> (scs - 2);
- const int sc_offset = (fp->freq_range == FR1) ? pdu->SsbSubcarrierOffset >> scs : pdu->SsbSubcarrierOffset;
- fp->ssb_start_subcarrier = (12 * prb_offset + sc_offset);
+ fp->ssb_start_subcarrier = nr_get_ssb_start_sc(scs,
+ pdu->ssbOffsetPointA,
+ pdu->SsbSubcarrierOffset,
+ fp->freq_range);
if (fp->print_ue_help_cmdline_log && IS_SA_MODE(get_softmodem_params())) {
fp->print_ue_help_cmdline_log = false;
@@ -142,15 +143,6 @@ void nr_common_signal_procedures(PHY_VARS_gNB *gNB, int frame, int slot, const n
fp->ssb_start_subcarrier,
fp->threequarter_fs ? "-E" : "");
}
- LOG_D(PHY,
- "ssbOffsetPointA %d SSB SsbSubcarrierOffset %d prb_offset %d sc_offset %d scs %d ssb_start_subcarrier %d\n",
- pdu->ssbOffsetPointA,
- pdu->SsbSubcarrierOffset,
- prb_offset,
- sc_offset,
- scs,
- fp->ssb_start_subcarrier);
-
LOG_D(PHY,"SS TX: frame %d, slot %d, start_symbol %d\n", frame, slot, ssb_start_symbol);
const nfapi_nr_tx_precoding_and_beamforming_t *pb = &pdu->precoding_and_beamforming;
c16_t ***txdataF = gNB->common_vars.txdataF;
@@ -209,10 +201,7 @@ void clear_slot_beamid(PHY_VARS_gNB *gNB, int slot)
}
}
-static void nr_generate_csi_rs_gNB(PHY_VARS_gNB *gNB,
- int slot,
- const nfapi_nr_config_request_scf_t *cfg,
- const nfapi_nr_dl_tti_csi_rs_pdu *csi_rs_pdu)
+static void nr_generate_csi_rs_gNB(PHY_VARS_gNB *gNB, int slot, const nfapi_nr_dl_tti_csi_rs_pdu *csi_rs_pdu)
{
const nfapi_nr_dl_tti_csi_rs_pdu_rel15_t *csi_params = &csi_rs_pdu->csi_rs_pdu_rel15;
if (csi_params->csi_type == 2) // ZP-CSI
@@ -253,8 +242,7 @@ void phy_procedures_gNB_TX(PHY_VARS_gNB *gNB,
const nfapi_nr_tx_data_request_t *TX_req,
const nfapi_nr_ul_dci_request_t *UL_dci_req,
int frame,
- int slot,
- int do_meas)
+ int slot)
{
const NR_DL_FRAME_PARMS *fp = &gNB->frame_parms;
nfapi_nr_config_request_scf_t *cfg = &gNB->gNB_config;
@@ -280,7 +268,7 @@ void phy_procedures_gNB_TX(PHY_VARS_gNB *gNB,
{
int slot_prs = (slot - i * prs_config->PRSResourceTimeGap + fp->slots_per_frame) % fp->slots_per_frame;
LOG_D(PHY,"gNB_TX: frame %d, slot %d, slot_prs %d, PRS Resource ID %d\n",frame, slot, slot_prs, rsc_id);
- nr_generate_prs(slot_prs, &gNB->common_vars.txdataF[0][0][txdataF_offset], AMP, prs_config, cfg, fp);
+ nr_generate_prs(slot_prs, &gNB->common_vars.txdataF[0][0][txdataF_offset], AMP, prs_config, fp);
}
}
}
@@ -299,7 +287,7 @@ void phy_procedures_gNB_TX(PHY_VARS_gNB *gNB,
nr_generate_dci(gNB, &dl_tti_pdu->pdcch_pdu.pdcch_pdu_rel15, txdataF_offset, &gNB->frame_parms, slot);
break;
case NFAPI_NR_DL_TTI_CSI_RS_PDU_TYPE:
- nr_generate_csi_rs_gNB(gNB, slot, cfg, &dl_tti_pdu->csi_rs_pdu);
+ nr_generate_csi_rs_gNB(gNB, slot, &dl_tti_pdu->csi_rs_pdu);
break;
case NFAPI_NR_DL_TTI_PDSCH_PDU_TYPE: {
int tx_data_idx = dl_tti_pdu->pdsch_pdu.pdsch_pdu_rel15.pduIndex;
@@ -721,7 +709,6 @@ static void fill_ul_rb_mask(PHY_VARS_gNB *gNB,
static int fill_srs_reported_symbol(nfapi_nr_srs_reported_symbol_t *reported_symbol,
const nfapi_nr_srs_pdu_t *srs_pdu,
- const int N_RB_UL,
const int16_t *snr_per_rb,
const int srs_est)
{
@@ -890,7 +877,7 @@ void nr_srs_rx_procedures(PHY_VARS_gNB *gNB,
stop_meas(&gNB->generate_srs_stats);
c16_t **rxdataF = gNB->common_vars.rxdataF[srs->beam_nb];
start_meas(&gNB->get_srs_signal_stats);
- *srs_est = nr_get_srs_signal(gNB, rxdataF, frame_rx, slot_rx, srs_pdu, nr_srs_info, srs_received_signal, srs_received_noise);
+ *srs_est = nr_get_srs_signal(gNB, rxdataF, slot_rx, srs_pdu, nr_srs_info, srs_received_signal, srs_received_noise);
stop_meas(&gNB->get_srs_signal_stats);
uint32_t signal_power_avg = 0;
@@ -1275,7 +1262,7 @@ int phy_procedures_gNB_uespec_RX(PHY_VARS_gNB *gNB, int frame_rx, int slot_rx, N
AssertFatal(nr_srs_bf_report.num_reported_symbols == 1,
"nr_srs_bf_report.num_reported_symbols %i not handled yet!\n",
nr_srs_bf_report.num_reported_symbols);
- fill_srs_reported_symbol(&nr_srs_bf_report.reported_symbol_list[0], srs_pdu, frame_parms->N_RB_UL, snr_per_rb, srs_est);
+ fill_srs_reported_symbol(&nr_srs_bf_report.reported_symbol_list[0], srs_pdu, snr_per_rb, srs_est);
#ifdef SRS_IND_DEBUG
LOG_I(NR_PHY, "nr_srs_bf_report.prg_size = %i\n", nr_srs_bf_report.prg_size);
diff --git a/openair1/SCHED_NR/sched_nr.h b/openair1/SCHED_NR/sched_nr.h
index 84691e9584..fbfb665ed1 100644
--- a/openair1/SCHED_NR/sched_nr.h
+++ b/openair1/SCHED_NR/sched_nr.h
@@ -38,8 +38,7 @@ void phy_procedures_gNB_TX(PHY_VARS_gNB *gNB,
const nfapi_nr_tx_data_request_t *TX_req,
const nfapi_nr_ul_dci_request_t *UL_dci_req,
int frame,
- int slot,
- int do_meas);
+ int slot);
void nr_save_ul_tti_req(PHY_VARS_gNB *gNB, nfapi_nr_ul_tti_request_t *UL_tti_req);
int phy_procedures_gNB_uespec_RX(PHY_VARS_gNB *gNB, int frame_rx, int slot_rx, NR_UL_IND_t *UL_INFO);
void L1_nr_prach_procedures(PHY_VARS_gNB *gNB, int frame, int slot, nfapi_nr_rach_indication_t *rach_ind);
diff --git a/openair1/SCHED_NR_UE/defs.h b/openair1/SCHED_NR_UE/defs.h
index 5fe6e0c1bb..394b5592f5 100644
--- a/openair1/SCHED_NR_UE/defs.h
+++ b/openair1/SCHED_NR_UE/defs.h
@@ -172,7 +172,6 @@ void nr_fill_sl_rx_indication(sl_nr_rx_indication_t *rx_ind,
uint8_t pdu_type,
PHY_VARS_NR_UE *ue,
uint16_t n_pdus,
- const UE_nr_rxtx_proc_t *proc,
void *typeSpecific,
uint16_t rx_slss_id);
diff --git a/openair1/SCHED_NR_UE/phy_procedures_nr_ue.c b/openair1/SCHED_NR_UE/phy_procedures_nr_ue.c
index 2da33ce205..cc6a2ee23b 100644
--- a/openair1/SCHED_NR_UE/phy_procedures_nr_ue.c
+++ b/openair1/SCHED_NR_UE/phy_procedures_nr_ue.c
@@ -1066,7 +1066,6 @@ int pbch_processing(PHY_VARS_NR_UE *ue, const UE_nr_rxtx_proc_t *proc, nr_phy_da
TracyCZone(ctx, true);
int frame_rx = proc->frame_rx;
int nr_slot_rx = proc->nr_slot_rx;
- int gNB_id = proc->gNB_id;
NR_DL_FRAME_PARMS *fp = &ue->frame_parms;
int sampleShift = INT_MAX;
nr_ue_dlsch_init(phy_data->dlsch, NR_MAX_NB_LAYERS>4 ? 2:1, ue->max_ldpc_iterations);
@@ -1152,7 +1151,7 @@ int pbch_processing(PHY_VARS_NR_UE *ue, const UE_nr_rxtx_proc_t *proc, nr_phy_da
if (ue->no_timing_correction == 0 && pbchSuccess == 0) {
LOG_D(PHY,"start adjust sync slot = %d no timing %d\n", nr_slot_rx, ue->no_timing_correction);
sampleShift =
- nr_adjust_synch_ue(fp, ue, gNB_id, fp->ofdm_symbol_size, dl_ch_estimates_time, frame_rx, nr_slot_rx, 16384);
+ nr_adjust_synch_ue(fp, ue, fp->ofdm_symbol_size, dl_ch_estimates_time, frame_rx, nr_slot_rx, 16384);
}
if (get_nrUE_params()->cont_fo_comp && pbchSuccess == 0) {
diff --git a/openair1/SCHED_NR_UE/phy_procedures_nr_ue_sl.c b/openair1/SCHED_NR_UE/phy_procedures_nr_ue_sl.c
index 1e2151d1d3..9b17546f61 100644
--- a/openair1/SCHED_NR_UE/phy_procedures_nr_ue_sl.c
+++ b/openair1/SCHED_NR_UE/phy_procedures_nr_ue_sl.c
@@ -66,7 +66,6 @@ void nr_fill_sl_rx_indication(sl_nr_rx_indication_t *rx_ind,
uint8_t pdu_type,
PHY_VARS_NR_UE *ue,
uint16_t n_pdus,
- const UE_nr_rxtx_proc_t *proc,
void *typeSpecific,
uint16_t rx_slss_id)
{
@@ -157,7 +156,7 @@ static int nr_ue_psbch_procedures(PHY_VARS_NR_UE *ue,
}
nr_fill_sl_indication(&sl_indication, &rx_ind, NULL, proc, ue, phy_data);
- nr_fill_sl_rx_indication(&rx_ind, SL_NR_RX_PDU_TYPE_SSB, ue, number_pdus, proc, (void *)result, rx_slss_id);
+ nr_fill_sl_rx_indication(&rx_ind, SL_NR_RX_PDU_TYPE_SSB, ue, number_pdus, (void *)result, rx_slss_id);
if (ue->if_inst && ue->if_inst->sl_indication)
ue->if_inst->sl_indication(&sl_indication);
@@ -232,7 +231,7 @@ int psbch_pscch_processing(PHY_VARS_NR_UE *ue, const UE_nr_rxtx_proc_t *proc, nr
if (ue->no_timing_correction == 0 && psbchSuccess == 0) {
LOG_D(NR_PHY, "start adjust sync slot = %d no timing %d\n", nr_slot_rx, ue->no_timing_correction);
sampleShift =
- nr_adjust_synch_ue(fp, ue, proc->gNB_id, fp->ofdm_symbol_size, dl_ch_estimates_time, frame_rx, nr_slot_rx, 16384);
+ nr_adjust_synch_ue(fp, ue, fp->ofdm_symbol_size, dl_ch_estimates_time, frame_rx, nr_slot_rx, 16384);
}
LOG_D(NR_PHY, "Doing N0 measurements in %s\n", __FUNCTION__);
diff --git a/openair1/SCHED_NR_UE/pucch_uci_ue_nr.c b/openair1/SCHED_NR_UE/pucch_uci_ue_nr.c
index 03c14af9b9..be1187f574 100644
--- a/openair1/SCHED_NR_UE/pucch_uci_ue_nr.c
+++ b/openair1/SCHED_NR_UE/pucch_uci_ue_nr.c
@@ -176,17 +176,17 @@ void pucch_procedures_ue_nr(PHY_VARS_NR_UE *ue,
switch(pucch_pdu->format_type) {
case 0:
- nr_generate_pucch0(ue, txdataF, &ue->frame_parms, tx_amp, nr_slot_tx, pucch_pdu);
+ nr_generate_pucch0(txdataF, &ue->frame_parms, tx_amp, nr_slot_tx, pucch_pdu);
break;
case 1:
- nr_generate_pucch1(ue, txdataF, &ue->frame_parms, tx_amp, nr_slot_tx, pucch_pdu);
+ nr_generate_pucch1(txdataF, &ue->frame_parms, tx_amp, nr_slot_tx, pucch_pdu);
break;
case 2:
- nr_generate_pucch2(ue, txdataF, &ue->frame_parms, tx_amp, nr_slot_tx, pucch_pdu);
+ nr_generate_pucch2(txdataF, &ue->frame_parms, tx_amp, nr_slot_tx, pucch_pdu);
break;
case 3:
case 4:
- nr_generate_pucch3_4(ue, txdataF, &ue->frame_parms, tx_amp, nr_slot_tx, pucch_pdu);
+ nr_generate_pucch3_4(txdataF, &ue->frame_parms, tx_amp, nr_slot_tx, pucch_pdu);
break;
}
}
diff --git a/openair1/SIMULATION/LTE_PHY/dlsim.c b/openair1/SIMULATION/LTE_PHY/dlsim.c
index a09b3558cb..9e334cb154 100644
--- a/openair1/SIMULATION/LTE_PHY/dlsim.c
+++ b/openair1/SIMULATION/LTE_PHY/dlsim.c
@@ -520,7 +520,8 @@ int main(int argc, char **argv) {
DCI_ALLOC_t da;
DCI_ALLOC_t *dci_alloc = &da;
unsigned int coded_bits_per_codeword=0,nsymb; //,tbs=0;
- unsigned int tx_lev=0,tx_lev_dB=0,trials;
+ unsigned int tx_lev = 0, trials;
+ int tx_lev_dB = 0;
unsigned int errs[4],errs2[4],round_trials[4],dci_errors[4];//,num_layers;
memset(errs,0,4*sizeof(unsigned int));
memset(errs2,0,4*sizeof(unsigned int));
@@ -1494,7 +1495,7 @@ int main(int argc, char **argv) {
eNB->frame_parms.samples_per_tti);
}
- tx_lev_dB = (unsigned int) dB_fixed(tx_lev);
+ tx_lev_dB = dB_fixed(tx_lev);
if (n_frames==1) {
printf("tx_lev = %u (%u dB)\n",tx_lev,tx_lev_dB);
diff --git a/openair1/SIMULATION/LTE_PHY/prachsim.c b/openair1/SIMULATION/LTE_PHY/prachsim.c
index 1b7f9e80e4..c1128f76a1 100644
--- a/openair1/SIMULATION/LTE_PHY/prachsim.c
+++ b/openair1/SIMULATION/LTE_PHY/prachsim.c
@@ -393,7 +393,7 @@ int main(int argc, char **argv) {
subframe,
0); //Nf
/* tx_lev_dB not used later, no need to set */
- //tx_lev_dB = (unsigned int) dB_fixed(tx_lev);
+ //tx_lev_dB = dB_fixed(tx_lev);
LOG_M("txsig0_new.m","txs0", &txdata[0][subframe*frame_parms->samples_per_tti],frame_parms->samples_per_tti,1,1);
//LOG_M("txsig1.m","txs1", txdata[1],FRAME_LENGTH_COMPLEX_SAMPLES,1,1);
// multipath channel
diff --git a/openair1/SIMULATION/LTE_PHY/ulsim.c b/openair1/SIMULATION/LTE_PHY/ulsim.c
index 92b9d58f48..c85e07c99c 100644
--- a/openair1/SIMULATION/LTE_PHY/ulsim.c
+++ b/openair1/SIMULATION/LTE_PHY/ulsim.c
@@ -343,7 +343,8 @@ int main(int argc, char **argv) {
unsigned short input_buffer_length;
unsigned int ret;
unsigned int coded_bits_per_codeword,nsymb;
- unsigned int tx_lev = 0, tx_lev_dB = 0, trials, errs[6] = {0}, round_trials[4] = {0};
+ unsigned int tx_lev = 0, trials, errs[6] = {0}, round_trials[4] = {0};
+ int tx_lev_dB = 0;
FILE *bler_fd=NULL;
char bler_fname[512];
FILE *time_meas_fd=NULL;
@@ -894,7 +895,7 @@ int main(int argc, char **argv) {
// LOG_M("txsig1.m","txs1", txdata[1],FRAME_LENGTH_COMPLEX_SAMPLES,1,1);
tx_lev = signal_energy(&txdata[0][0],
OFDM_SYMBOL_SIZE_COMPLEX_SAMPLES);
- tx_lev_dB = (unsigned int) dB_fixed(tx_lev);
+ tx_lev_dB = dB_fixed(tx_lev);
}
iter_trials=0;
diff --git a/openair1/SIMULATION/NR_PHY/dlschsim.c b/openair1/SIMULATION/NR_PHY/dlschsim.c
index 076f05db48..6f4282f130 100644
--- a/openair1/SIMULATION/NR_PHY/dlschsim.c
+++ b/openair1/SIMULATION/NR_PHY/dlschsim.c
@@ -506,7 +506,7 @@ int main(int argc, char **argv)
unsigned char output[nb_rb * NR_SYMBOLS_PER_SLOT * NR_NB_SC_PER_RB * NR_MAX_NB_LAYERS] __attribute__((aligned(64)));
bzero(output, sizeof(output));
if (input_fd == NULL) {
- nr_dlsch_encoding(gNB, 1, dlsch, frame, slot, frame_parms, output, NULL, NULL, NULL, NULL, NULL, NULL, NULL);
+ nr_dlsch_encoding(gNB, 1, dlsch, frame, slot, output, NULL, NULL, NULL, NULL, NULL, NULL, NULL);
}
for (SNR = snr0; SNR < snr1 && !stop; SNR += snr_step) {
@@ -620,7 +620,7 @@ int main(int argc, char **argv)
free(RC.gNB);
free_nr_ue_dl_harq(UE->dl_harq_processes, 8, nb_rb);
- term_nr_ue_signal(UE, 1);
+ term_nr_ue_signal(UE);
free(UE);
for (i = 0; i < 2; i++) {
diff --git a/openair1/SIMULATION/NR_PHY/dlsim.c b/openair1/SIMULATION/NR_PHY/dlsim.c
index bcce053231..b068936739 100644
--- a/openair1/SIMULATION/NR_PHY/dlsim.c
+++ b/openair1/SIMULATION/NR_PHY/dlsim.c
@@ -1120,7 +1120,7 @@ int main(int argc, char **argv)
}
start_meas(&gNB->phy_proc_tx);
- phy_procedures_gNB_TX(gNB, &Sched_INFO->DL_req, &Sched_INFO->TX_req, &Sched_INFO->UL_dci_req, frame, slot, 1);
+ phy_procedures_gNB_TX(gNB, &Sched_INFO->DL_req, &Sched_INFO->TX_req, &Sched_INFO->UL_dci_req, frame, slot);
stop_meas(&gNB->phy_proc_tx);
int txdataF_offset = slot * frame_parms->samples_per_slot_wCP;
diff --git a/openair1/SIMULATION/NR_PHY/pbchsim.c b/openair1/SIMULATION/NR_PHY/pbchsim.c
index 087b17ab06..5702be2cf9 100644
--- a/openair1/SIMULATION/NR_PHY/pbchsim.c
+++ b/openair1/SIMULATION/NR_PHY/pbchsim.c
@@ -654,7 +654,7 @@ int main(int argc, char **argv)
nr_gscn_info_t gscnInfo[MAX_GSCN_BAND] = {0};
const int numGscn = 1;
gscnInfo[0].ssbFirstSC = frame_parms->ssb_start_subcarrier;
- nr_initial_sync_t ret = nr_initial_sync(&proc, UE, 1, 0, gscnInfo, numGscn);
+ nr_initial_sync_t ret = nr_initial_sync(&proc, UE, 1, gscnInfo, numGscn);
printf("nr_initial_sync1 returns %s\n", ret.cell_detected ? "cell detected" : "cell not detected");
if (!ret.cell_detected)
n_errors++;
@@ -761,7 +761,7 @@ int main(int argc, char **argv)
free(RC.gNB[0]);
free(RC.gNB);
- term_nr_ue_signal(UE, 1);
+ term_nr_ue_signal(UE);
free(UE);
for (i=0; i<2; i++) {
diff --git a/openair1/SIMULATION/NR_PHY/prachsim.c b/openair1/SIMULATION/NR_PHY/prachsim.c
index 4da1accfe8..7966c74375 100644
--- a/openair1/SIMULATION/NR_PHY/prachsim.c
+++ b/openair1/SIMULATION/NR_PHY/prachsim.c
@@ -667,7 +667,7 @@ int main(int argc, char **argv){
generate_nr_prach(UE, 0, frame, slot, tx);
/* tx_lev_dB not used later, no need to set */
- //tx_lev_dB = (unsigned int) dB_fixed(tx_lev);
+ //tx_lev_dB = dB_fixed(tx_lev);
#ifdef NR_PRACH_DEBUG
LOG_M("txsig0.m", "txs0", &txdata[0][subframe*frame_parms->samples_per_subframe], frame_parms->samples_per_subframe, 1, 1);
@@ -844,7 +844,7 @@ int main(int argc, char **argv){
free(RC.gNB[0]);
free(RC.gNB);
- term_nr_ue_signal(UE, 1);
+ term_nr_ue_signal(UE);
free(UE->nrUE_config.prach_config.num_prach_fd_occasions_list);
free(UE);
free(PHY_vars_UE_g[0]);
diff --git a/openair1/SIMULATION/NR_PHY/psbchsim.c b/openair1/SIMULATION/NR_PHY/psbchsim.c
index 49d07616c4..cb78915cbb 100644
--- a/openair1/SIMULATION/NR_PHY/psbchsim.c
+++ b/openair1/SIMULATION/NR_PHY/psbchsim.c
@@ -673,8 +673,8 @@ int main(int argc, char **argv)
free(r_re);
free(r_im);
- term_nr_ue_signal(UE_TX, 1);
- term_nr_ue_signal(UE_RX, 1);
+ term_nr_ue_signal(UE_TX);
+ term_nr_ue_signal(UE_RX);
free(UE_TX);
free(UE_RX);
diff --git a/openair1/SIMULATION/NR_PHY/pucchsim.c b/openair1/SIMULATION/NR_PHY/pucchsim.c
index 980beac6b3..bfa294a55f 100644
--- a/openair1/SIMULATION/NR_PHY/pucchsim.c
+++ b/openair1/SIMULATION/NR_PHY/pucchsim.c
@@ -551,11 +551,11 @@ int main(int argc, char **argv)
for (int aatx=0;aatx<1;aatx++)
bzero(txdataF[aatx],frame_parms->ofdm_symbol_size*sizeof(int));
if(format==0 && do_DTX==0){
- nr_generate_pucch0(UE, txdataF, frame_parms, amp, nr_slot_tx, &pucch_tx_pdu);
+ nr_generate_pucch0(txdataF, frame_parms, amp, nr_slot_tx, &pucch_tx_pdu);
} else if (format == 1 && do_DTX==0){
- nr_generate_pucch1(UE, txdataF, frame_parms, amp, nr_slot_tx, &pucch_tx_pdu);
+ nr_generate_pucch1(txdataF, frame_parms, amp, nr_slot_tx, &pucch_tx_pdu);
} else if (do_DTX == 0){
- nr_generate_pucch2(UE, txdataF, frame_parms, amp, nr_slot_tx, &pucch_tx_pdu);
+ nr_generate_pucch2(txdataF, frame_parms, amp, nr_slot_tx, &pucch_tx_pdu);
}
// SNR Computation
@@ -784,7 +784,7 @@ int main(int argc, char **argv)
free(RC.gNB[0]);
free(RC.gNB);
- term_nr_ue_signal(UE, 1);
+ term_nr_ue_signal(UE);
free(UE);
for (int aatx=0; aatxgNB_config.tdd_table.max_tdd_periodicity_list[i].max_num_of_symbol_per_slot_list);
free(gNB->gNB_config.tdd_table.max_tdd_periodicity_list);
- term_nr_ue_signal(UE, 1);
+ term_nr_ue_signal(UE);
free(UE);
abortTpool(&gNB->threadPool);
diff --git a/openair2/COMMON/e1ap_messages_types.h b/openair2/COMMON/e1ap_messages_types.h
index 48cfef98f3..4d1c9bbe9d 100644
--- a/openair2/COMMON/e1ap_messages_types.h
+++ b/openair2/COMMON/e1ap_messages_types.h
@@ -199,7 +199,7 @@ typedef struct {
typedef nssai_t e1ap_nssai_t;
-typedef struct e1ap_net_config_t {
+typedef struct {
net_ip_address_t CUUP_e1_ip_address;
net_ip_address_t CUCP_e1_ip_address;
uint16_t remotePortF1U;
@@ -230,7 +230,7 @@ typedef struct e1ap_cucp_setup_req_s {
uint64_t transac_id;
} e1ap_cucp_setup_req_t;
-typedef struct e1ap_register_req_t {
+typedef struct {
e1ap_setup_req_t setup_req;
e1ap_net_config_t net_config;
uint32_t gnb_id; // unused in CU-UP, but might be necessary for some functionality, e.g., E2 agent
@@ -658,7 +658,7 @@ typedef struct e1ap_bearer_modif_resp_s {
} e1ap_bearer_modif_resp_t;
/* E1AP Connection Loss indication */
-typedef struct e1ap_lost_connection_t {
+typedef struct {
int dummy;
} e1ap_lost_connection_t;
diff --git a/openair2/COMMON/f1ap_messages_types.h b/openair2/COMMON/f1ap_messages_types.h
index 5f430d0e39..3354388596 100644
--- a/openair2/COMMON/f1ap_messages_types.h
+++ b/openair2/COMMON/f1ap_messages_types.h
@@ -84,7 +84,7 @@
/* 9.3.1.42 of 3GPP TS 38.473 - gNB-CU System Information */
#define F1AP_MAX_NO_SIB_TYPES 32
-typedef struct f1ap_net_config_t {
+typedef struct f1ap_net_config_s {
char *CU_f1_ip_address;
char *DU_f1c_ip_address;
char *DU_f1u_ip_address;
@@ -97,31 +97,31 @@ typedef struct f1ap_cp_tnl_s {
uint16_t port;
} f1ap_cp_tnl_t;
-typedef enum f1ap_mode_t { F1AP_MODE_TDD = 0, F1AP_MODE_FDD = 1 } f1ap_mode_t;
+typedef enum f1ap_mode_e { F1AP_MODE_TDD = 0, F1AP_MODE_FDD = 1 } f1ap_mode_t;
-typedef struct f1ap_nr_frequency_info_t {
+typedef struct f1ap_nr_frequency_info_s {
uint32_t arfcn;
int band;
} f1ap_nr_frequency_info_t;
-typedef struct f1ap_transmission_bandwidth_t {
+typedef struct f1ap_transmission_bandwidth_s {
uint8_t scs;
uint16_t nrb;
} f1ap_transmission_bandwidth_t;
-typedef struct f1ap_fdd_info_t {
+typedef struct f1ap_fdd_info_s {
f1ap_nr_frequency_info_t ul_freqinfo;
f1ap_nr_frequency_info_t dl_freqinfo;
f1ap_transmission_bandwidth_t ul_tbw;
f1ap_transmission_bandwidth_t dl_tbw;
} f1ap_fdd_info_t;
-typedef struct f1ap_tdd_info_t {
+typedef struct f1ap_tdd_info_s {
f1ap_nr_frequency_info_t freqinfo;
f1ap_transmission_bandwidth_t tbw;
} f1ap_tdd_info_t;
-typedef struct f1ap_served_cell_info_t {
+typedef struct f1ap_served_cell_info_s {
// NR CGI (Mandatory)
plmn_id_t plmn;
uint64_t nr_cellid; // NR Global Cell Id
@@ -143,7 +143,7 @@ typedef struct f1ap_served_cell_info_t {
int measurement_timing_config_len;
} f1ap_served_cell_info_t;
-typedef struct f1ap_gnb_du_system_info_t {
+typedef struct f1ap_gnb_du_system_info_s {
// MIB message (Mandatory)
uint8_t *mib;
int mib_length;
@@ -171,12 +171,12 @@ typedef struct f1ap_setup_req_s {
} *cell;
} f1ap_setup_req_t;
-typedef struct f1ap_du_register_req_t {
+typedef struct f1ap_du_register_req_s {
f1ap_setup_req_t setup_req;
f1ap_net_config_t net_config;
} f1ap_du_register_req_t;
-typedef struct f1ap_sib_msg_t {
+typedef struct f1ap_sib_msg_s {
/// RRC container with system information owned by gNB-CU
uint8_t *SI_container;
int SI_container_length;
@@ -260,7 +260,7 @@ typedef struct f1ap_gnb_cu_configuration_update_failure_s {
uint16_t criticality_diagnostics;
} f1ap_gnb_cu_configuration_update_failure_t;
-typedef struct f1ap_cell_status_t {
+typedef struct f1ap_cell_status_s {
// NR CGI
plmn_id_t plmn;
uint64_t nr_cellid; // NR Global Cell Id
@@ -372,7 +372,7 @@ typedef enum preemption_vulnerability_e {
PREEMPTABLE,
} preemption_vulnerability_t;
-typedef enum f1ap_rlc_mode_t { F1AP_RLC_MODE_AM, F1AP_RLC_MODE_UM_BIDIR, F1AP_RLC_UM_UNI_UL, F1AP_RLC_UM_UNI_DL } f1ap_rlc_mode_t;
+typedef enum f1ap_rlc_mode_e { F1AP_RLC_MODE_AM, F1AP_RLC_MODE_UM_BIDIR, F1AP_RLC_UM_UNI_UL, F1AP_RLC_UM_UNI_DL } f1ap_rlc_mode_t;
typedef struct f1ap_cu_to_du_rrc_info_s {
byte_array_t *cg_configinfo;
@@ -382,7 +382,7 @@ typedef struct f1ap_cu_to_du_rrc_info_s {
byte_array_t *ho_prep_info;
} f1ap_cu_to_du_rrc_info_t;
-typedef struct f1ap_du_to_cu_rrc_info_t {
+typedef struct f1ap_du_to_cu_rrc_info_s {
byte_array_t cell_group_config;
byte_array_t *meas_gap_config;
} f1ap_du_to_cu_rrc_info_t;
@@ -412,28 +412,28 @@ typedef enum lower_layer_status_e {
LOWER_LAYERS_RESUME,
} lower_layer_status_t;
-typedef struct f1ap_srb_to_setup_t {
+typedef struct f1ap_srb_to_setup_s {
int id;
} f1ap_srb_to_setup_t;
-typedef struct f1ap_srb_setup_t {
+typedef struct f1ap_srb_setup_s {
int id;
int lcid;
} f1ap_srb_setup_t;
/// 9.3.1.52 Packet Error Rate
-typedef struct f1ap_per_t {
+typedef struct f1ap_per_s {
uint8_t scalar;
uint8_t exponent;
} f1ap_per_t;
// 9.3.1.49 Non-Dynamic 5QI Descriptor
-typedef struct f1ap_nondynamic_5qi_t {
+typedef struct f1ap_nondynamic_5qi_s {
int fiveQI;
} f1ap_nondynamic_5qi_t;
// 9.3.1.47 Dynamic 5QI Descriptor
-typedef struct f1ap_dynamic_5qi_t {
+typedef struct f1ap_dynamic_5qi_s {
int prio; /// QoS Priority Level
int pdb; /// Packet Delay Budget
f1ap_per_t per; /// Packet Error Rate
@@ -441,14 +441,14 @@ typedef struct f1ap_dynamic_5qi_t {
int *avg_win; /// Averaging Window
} f1ap_dynamic_5qi_t;
-typedef struct f1ap_arp_t {
+typedef struct f1ap_arp_s {
uint16_t prio;
preemption_capability_t preempt_cap;
preemption_vulnerability_t preempt_vuln;
} f1ap_arp_t;
// 9.3.1.45 QoS Flow Level QoS Parameters
-typedef struct f1ap_qos_flow_param_t {
+typedef struct f1ap_qos_flow_param_s {
fiveQI_t qos_type;
union {
f1ap_nondynamic_5qi_t nondyn;
@@ -458,13 +458,13 @@ typedef struct f1ap_qos_flow_param_t {
} f1ap_qos_flow_param_t;
// in 9.2.2.1 Flows Mapped to DRB Item
-typedef struct f1ap_drb_flows_mapped_t {
+typedef struct f1ap_drb_flows_mapped_s {
int qfi;
f1ap_qos_flow_param_t param;
} f1ap_drb_flows_mapped_t;
/// in 9.2.2.1 DRB Info in UE Context Setup Request
-typedef struct f1ap_drb_info_nr_t {
+typedef struct f1ap_drb_info_nr_s {
f1ap_qos_flow_param_t drb_qos;
nssai_t nssai;
int flows_len;
@@ -473,7 +473,7 @@ typedef struct f1ap_drb_info_nr_t {
typedef enum { F1AP_PDCP_SN_12B, F1AP_PDCP_SN_18B } f1ap_pdcp_sn_len_t;
/// in 9.2.2.1 DRB to Be Setup Item IEs
-typedef struct f1ap_drb_to_setup_t {
+typedef struct f1ap_drb_to_setup_s {
int id;
enum { F1AP_QOS_CHOICE_EUTRAN, F1AP_QOS_CHOICE_NR } qos_choice;
union {
@@ -487,14 +487,14 @@ typedef struct f1ap_drb_to_setup_t {
f1ap_pdcp_sn_len_t *ul_pdcp_sn_len;
} f1ap_drb_to_setup_t;
-typedef struct f1ap_drb_setup_t {
+typedef struct f1ap_drb_setup_s {
int id;
int *lcid;
int up_dl_tnl_len;
f1ap_up_tnl_t up_dl_tnl[2];
} f1ap_drb_setup_t;
-typedef struct f1ap_drb_to_release_t {
+typedef struct f1ap_drb_to_release_s {
int id;
} f1ap_drb_to_release_t;
@@ -534,7 +534,7 @@ typedef struct f1ap_ue_context_setup_resp_s {
f1ap_srb_setup_t *srbs;
} f1ap_ue_context_setup_resp_t;
-typedef struct f1ap_ue_context_mod_req_t {
+typedef struct f1ap_ue_context_mod_req_s {
uint32_t gNB_CU_ue_id;
uint32_t gNB_DU_ue_id;
@@ -565,7 +565,7 @@ typedef struct f1ap_ue_context_mod_req_t {
lower_layer_status_t *status;
} f1ap_ue_context_mod_req_t;
-typedef struct f1ap_ue_context_mod_resp {
+typedef struct f1ap_ue_context_mod_resp_s {
uint32_t gNB_CU_ue_id;
uint32_t gNB_DU_ue_id;
@@ -586,7 +586,7 @@ typedef enum F1ap_Cause_e {
F1AP_CAUSE_MISC,
} f1ap_Cause_t;
-typedef struct f1ap_ue_context_modif_required_t {
+typedef struct f1ap_ue_context_modif_required_s {
uint32_t gNB_CU_ue_id;
uint32_t gNB_DU_ue_id;
du_to_cu_rrc_information_t *du_to_cu_rrc_information;
@@ -594,28 +594,28 @@ typedef struct f1ap_ue_context_modif_required_t {
long cause_value;
} f1ap_ue_context_modif_required_t;
-typedef struct f1ap_ue_context_modif_confirm_t {
+typedef struct f1ap_ue_context_modif_confirm_s {
uint32_t gNB_CU_ue_id;
uint32_t gNB_DU_ue_id;
uint8_t *rrc_container;
int rrc_container_length;
} f1ap_ue_context_modif_confirm_t;
-typedef struct f1ap_ue_context_modif_refuse_t {
+typedef struct f1ap_ue_context_modif_refuse_s {
uint32_t gNB_CU_ue_id;
uint32_t gNB_DU_ue_id;
f1ap_Cause_t cause;
long cause_value;
} f1ap_ue_context_modif_refuse_t;
-typedef struct f1ap_ue_context_rel_req_t {
+typedef struct f1ap_ue_context_rel_req_s {
uint32_t gNB_CU_ue_id;
uint32_t gNB_DU_ue_id;
f1ap_Cause_t cause;
long cause_value;
} f1ap_ue_context_rel_req_t;
-typedef struct f1ap_ue_context_rel_cmd_t {
+typedef struct f1ap_ue_context_rel_cmd_s {
uint32_t gNB_CU_ue_id;
uint32_t gNB_DU_ue_id;
f1ap_Cause_t cause;
@@ -627,7 +627,7 @@ typedef struct f1ap_ue_context_rel_cmd_t {
uint32_t *old_gNB_DU_ue_id; // if after reestablishment request
} f1ap_ue_context_rel_cmd_t;
-typedef struct f1ap_ue_context_rel_cplt_t {
+typedef struct f1ap_ue_context_rel_cplt_s {
uint32_t gNB_CU_ue_id;
uint32_t gNB_DU_ue_id;
} f1ap_ue_context_rel_cplt_t;
@@ -694,7 +694,7 @@ typedef struct {
f1ap_paging_cell_item_t *cells;
} f1ap_paging_t;
-typedef struct f1ap_lost_connection_t {
+typedef struct f1ap_lost_connection_s {
int dummy;
} f1ap_lost_connection_t;
@@ -703,12 +703,12 @@ typedef enum F1AP_ResetType_e {
F1AP_RESET_PART_OF_F1_INTERFACE
} f1ap_ResetType_t;
-typedef struct f1ap_ue_to_reset_t {
+typedef struct f1ap_ue_to_reset_s {
uint32_t *gNB_CU_ue_id;
uint32_t *gNB_DU_ue_id;
} f1ap_ue_to_reset_t;
-typedef struct f1ap_reset_t {
+typedef struct f1ap_reset_s {
uint64_t transaction_id;
f1ap_Cause_t cause;
long cause_value;
@@ -717,7 +717,7 @@ typedef struct f1ap_reset_t {
f1ap_ue_to_reset_t *ue_to_reset; // array of num_ue_to_reset elements
} f1ap_reset_t;
-typedef struct f1ap_reset_ack_t {
+typedef struct f1ap_reset_ack_s {
uint64_t transaction_id;
int num_ue_to_reset;
f1ap_ue_to_reset_t *ue_to_reset; // array of num_ue_to_reset elements
diff --git a/openair2/COMMON/ngap_messages_def.h b/openair2/COMMON/ngap_messages_def.h
index 09e893f874..b1ffe77bc1 100644
--- a/openair2/COMMON/ngap_messages_def.h
+++ b/openair2/COMMON/ngap_messages_def.h
@@ -73,6 +73,7 @@ MESSAGE_DEF(NGAP_HANDOVER_NOTIFY, MESSAGE_PRIORITY_MED, ngap_handover_notify_t,
MESSAGE_DEF(NGAP_HANDOVER_CANCEL, MESSAGE_PRIORITY_MED, ngap_handover_cancel_t, ngap_handover_cancel)
MESSAGE_DEF(NGAP_UL_RAN_STATUS_TRANSFER, MESSAGE_PRIORITY_MED, ngap_ran_status_transfer_t, ngap_ul_ran_status_transfer)
MESSAGE_DEF(NGAP_DL_RAN_STATUS_TRANSFER, MESSAGE_PRIORITY_MED, ngap_ran_status_transfer_t, ngap_dl_ran_status_transfer)
+MESSAGE_DEF(NGAP_RECONNECT_TIMER, MESSAGE_PRIORITY_MED, IttiMsgText, ngap_gNB_amf_data)
/* NGAP -> RRC messages */
MESSAGE_DEF(NGAP_DOWNLINK_NAS , MESSAGE_PRIORITY_MED, ngap_downlink_nas_t , ngap_downlink_nas )
@@ -88,3 +89,18 @@ MESSAGE_DEF(NGAP_HANDOVER_CANCEL_ACK, MESSAGE_PRIORITY_MED, ngap_handover_cancel
/* NGAP <-> RRC messages (can be initiated either by MME or gNB) */
MESSAGE_DEF(NGAP_UE_CONTEXT_RELEASE_REQ , MESSAGE_PRIORITY_MED, ngap_ue_release_req_t , ngap_ue_release_req)
+
+/* NGAP -> NRPPA messages*/
+MESSAGE_DEF(NGAP_DOWNLINKUEASSOCIATEDNRPPA,
+ MESSAGE_PRIORITY_MED,
+ ngap_downlink_ue_associated_nrppa_t,
+ ngap_downlink_ue_associated_nrppa)
+MESSAGE_DEF(NGAP_DOWNLINKNONUEASSOCIATEDNRPPA,
+ MESSAGE_PRIORITY_MED,
+ ngap_downlink_non_ue_associated_nrppa_t,
+ ngap_downlink_non_ue_associated_nrppa)
+MESSAGE_DEF(NGAP_UPLINKUEASSOCIATEDNRPPA, MESSAGE_PRIORITY_MED, ngap_uplink_ue_associated_nrppa_t, ngap_uplink_ue_associated_nrppa)
+MESSAGE_DEF(NGAP_UPLINKNONUEASSOCIATEDNRPPA,
+ MESSAGE_PRIORITY_MED,
+ ngap_uplink_non_ue_associated_nrppa_t,
+ ngap_uplink_non_ue_associated_nrppa)
diff --git a/openair2/COMMON/ngap_messages_types.h b/openair2/COMMON/ngap_messages_types.h
index 02069d056e..85d61bba39 100644
--- a/openair2/COMMON/ngap_messages_types.h
+++ b/openair2/COMMON/ngap_messages_types.h
@@ -79,6 +79,11 @@
#define NGAP_UL_RAN_STATUS_TRANSFER(mSGpTR) (mSGpTR)->ittiMsg.ngap_ul_ran_status_transfer
#define NGAP_DL_RAN_STATUS_TRANSFER(mSGpTR) (mSGpTR)->ittiMsg.ngap_dl_ran_status_transfer
+#define NGAP_DOWNLINKUEASSOCIATEDNRPPA(mSGpTR) (mSGpTR)->ittiMsg.ngap_downlink_ue_associated_nrppa
+#define NGAP_DOWNLINKNONUEASSOCIATEDNRPPA(mSGpTR) (mSGpTR)->ittiMsg.ngap_downlink_non_ue_associated_nrppa
+
+#define NGAP_UPLINKUEASSOCIATEDNRPPA(mSGpTR) (mSGpTR)->ittiMsg.ngap_uplink_ue_associated_nrppa
+#define NGAP_UPLINKNONUEASSOCIATEDNRPPA(mSGpTR) (mSGpTR)->ittiMsg.ngap_uplink_non_ue_associated_nrppa
//-------------------------------------------------------------------------------------------//
/* Length of the transport layer address string
@@ -1007,4 +1012,44 @@ typedef struct {
ngap_ran_status_container_t ran_status;
} ngap_ran_status_transfer_t;
+// Uplink UE Associated NRPPA Transport message (9.2.9.2 3GPP 38.413 v16.0.0)
+typedef struct {
+ // AMF UE NGAP ID (Mandatory)
+ uint64_t amf_ue_ngap_id;
+ // RAN UE NGAP ID (Mandatory)
+ uint32_t gNB_ue_ngap_id;
+ // Routing ID (Mandatory)
+ byte_array_t routing_id;
+ // NRPPa pdu (Mandatory)
+ byte_array_t nrppa_pdu;
+} ngap_uplink_ue_associated_nrppa_t;
+
+// Uplink NON UE Associated NRPPA Transport message (9.2.9.4 3GPP 38.413 v16.0.0)
+typedef struct {
+ // Routing ID (Mandatory)
+ byte_array_t routing_id;
+ // NRPPa pdu (Mandatory)
+ byte_array_t nrppa_pdu;
+} ngap_uplink_non_ue_associated_nrppa_t;
+
+// Downlink UE Associated NRPPA Transport message (9.2.9.1 3GPP 38.413 v16.0.0)
+typedef struct {
+ // AMF UE NGAP ID (Mandatory)
+ uint64_t amf_ue_ngap_id;
+ // RAN UE NGAP ID (Mandatory)
+ uint32_t gNB_ue_ngap_id;
+ // Routing ID (Mandatory)
+ byte_array_t routing_id;
+ // NRPPa pdu (Mandatory)
+ byte_array_t nrppa_pdu;
+} ngap_downlink_ue_associated_nrppa_t;
+
+// Downlink NON UE Associated NRPPA Transport message (9.2.9.3 3GPP 38.413 v16.0.0)
+typedef struct {
+ // Routing ID (Mandatory)
+ byte_array_t routing_id;
+ // NRPPa pdu (Mandatory)
+ byte_array_t nrppa_pdu;
+} ngap_downlink_non_ue_associated_nrppa_t;
+
#endif /* NGAP_MESSAGES_TYPES_H_ */
diff --git a/openair2/COMMON/nrppa_messages_def.h b/openair2/COMMON/nrppa_messages_def.h
new file mode 100644
index 0000000000..aa40adce44
--- /dev/null
+++ b/openair2/COMMON/nrppa_messages_def.h
@@ -0,0 +1,44 @@
+/*
+ * Licensed to the OpenAirInterface (OAI) Software Alliance under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The OpenAirInterface Software Alliance licenses this file to You under
+ * the OAI Public License, Version 1.1 (the "License"); you may not use this file
+ * except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.openairinterface.org/?page_id=698
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *-------------------------------------------------------------------------------
+ * For more information about the OpenAirInterface (OAI) Software Alliance:
+ * contact@openairinterface.org
+ */
+
+#include "openair2/COMMON/nrppa_messages_types.h"
+
+// LMF -> CU
+MESSAGE_DEF(NRPPA_TRP_INFORMATION_REQ, MESSAGE_PRIORITY_MED, nrppa_trp_information_req_t, nrppa_trp_information_req)
+MESSAGE_DEF(NRPPA_TRP_INFORMATION_RESP, MESSAGE_PRIORITY_MED, nrppa_trp_information_resp_t, nrppa_trp_information_resp)
+MESSAGE_DEF(NRPPA_POSITIONING_INFORMATION_REQ,
+ MESSAGE_PRIORITY_MED,
+ nrppa_positioning_information_req_t,
+ nrppa_positioning_information_req)
+MESSAGE_DEF(NRPPA_POSITIONING_INFORMATION_RESP,
+ MESSAGE_PRIORITY_MED,
+ nrppa_positioning_information_resp_t,
+ nrppa_positioning_information_resp)
+MESSAGE_DEF(NRPPA_POSITIONING_ACTIVATION_REQ,
+ MESSAGE_PRIORITY_MED,
+ nrppa_positioning_activation_req_t,
+ nrppa_positioning_activation_req)
+MESSAGE_DEF(NRPPA_POSITIONING_ACTIVATION_RESP,
+ MESSAGE_PRIORITY_MED,
+ nrppa_positioning_activation_resp_t,
+ nrppa_positioning_activation_resp)
+MESSAGE_DEF(NRPPA_MEASUREMENT_REQ, MESSAGE_PRIORITY_MED, nrppa_measurement_req_t, nrppa_measurement_req)
+MESSAGE_DEF(NRPPA_MEASUREMENT_RESP, MESSAGE_PRIORITY_MED, nrppa_measurement_resp_t, nrppa_measurement_resp)
diff --git a/openair2/COMMON/nrppa_messages_types.h b/openair2/COMMON/nrppa_messages_types.h
new file mode 100644
index 0000000000..881362231d
--- /dev/null
+++ b/openair2/COMMON/nrppa_messages_types.h
@@ -0,0 +1,824 @@
+/*
+ * Licensed to the OpenAirInterface (OAI) Software Alliance under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The OpenAirInterface Software Alliance licenses this file to You under
+ * the OAI Public License, Version 1.1 (the "License"); you may not use this file
+ * except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.openairinterface.org/?page_id=698
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *-------------------------------------------------------------------------------
+ * For more information about the OpenAirInterface (OAI) Software Alliance:
+ * contact@openairinterface.org
+ */
+
+#ifndef NRPPA_MESSAGES_TYPES_H_
+#define NRPPA_MESSAGES_TYPES_H_
+
+// Defines to access message fields.
+
+#define NRPPA_TRP_INFORMATION_REQ(mSGpTR) (mSGpTR)->ittiMsg.nrppa_trp_information_req
+#define NRPPA_TRP_INFORMATION_RESP(mSGpTR) (mSGpTR)->ittiMsg.nrppa_trp_information_resp
+#define NRPPA_POSITIONING_INFORMATION_REQ(mSGpTR) (mSGpTR)->ittiMsg.nrppa_positioning_information_req
+#define NRPPA_POSITIONING_INFORMATION_RESP(mSGpTR) (mSGpTR)->ittiMsg.nrppa_positioning_information_resp
+#define NRPPA_POSITIONING_ACTIVATION_REQ(mSGpTR) (mSGpTR)->ittiMsg.nrppa_positioning_activation_req
+#define NRPPA_POSITIONING_ACTIVATION_RESP(mSGpTR) (mSGpTR)->ittiMsg.nrppa_positioning_activation_resp
+#define NRPPA_MEASUREMENT_REQ(mSGpTR) (mSGpTR)->ittiMsg.nrppa_measurement_req
+#define NRPPA_MEASUREMENT_RESP(mSGpTR) (mSGpTR)->ittiMsg.nrppa_measurement_resp
+
+/* Structure of Positioning related NRPPA messages */
+/* IE structures for Positioning related messages as per TS 38.455 V16.7.1*/
+
+typedef enum nrppa_trp_information_type_item_e {
+ NRPPA_TRP_INFORMATION_TYPE_ITEM_NR_PCI,
+ NRPPA_TRP_INFORMATION_TYPE_ITEM_NG_RAN_CGI,
+ NRPPA_TRP_INFORMATION_TYPE_ITEM_NR_ARFCN,
+ NRPPA_TRP_INFORMATION_TYPE_ITEM_PRS_CONFIG,
+ NRPPA_TRP_INFORMATION_TYPE_ITEM_SSB_CONFIG,
+ NRPPA_TRP_INFORMATION_TYPE_ITEM_SFN_INIT_TIME,
+ NRPPA_TRP_INFORMATION_TYPE_ITEM_SPATIAL_DIRECTION_INFO,
+ NRPPA_TRP_INFORMATION_TYPE_ITEM_GEO_COORDINATES
+} nrppa_trp_information_type_item_pr;
+
+typedef struct nrppa_trp_information_type_list_s {
+ nrppa_trp_information_type_item_pr *trp_information_type_item;
+ uint8_t trp_information_type_list_length;
+} nrppa_trp_information_type_list_t;
+
+typedef struct nrppa_trp_list_item_s {
+ uint32_t trp_id;
+} nrppa_trp_list_item_t;
+
+typedef struct nrppa_trp_list_s {
+ nrppa_trp_list_item_t *trp_list_item;
+ uint32_t trp_list_length;
+} nrppa_trp_list_t;
+
+typedef struct nrppa_access_point_position_s {
+ long latitude_sign;
+ long latitude;
+ long longitude;
+ long direction_of_altitude;
+ long altitude;
+ long uncertainty_semi_major;
+ long uncertainty_semi_minor;
+ long orientation_of_major_axis;
+ long uncertainty_altitude;
+ long confidence;
+} nrppa_access_point_position_t;
+
+typedef struct nrppa_ngran_high_accuracy_access_point_position_s {
+ long latitude;
+ long longitude;
+ long altitude;
+ long uncertainty_semi_major;
+ long uncertainty_semi_minor;
+ long orientation_of_major_axis;
+ long horizontal_confidence;
+ long uncertainty_altitude;
+ long vertical_confidence;
+} nrppa_ngran_high_accuracy_access_point_position_t;
+
+typedef union nrppa_trp_position_direct_accuracy_c {
+ nrppa_access_point_position_t trp_position;
+ nrppa_ngran_high_accuracy_access_point_position_t trp_HAposition;
+} nrppa_trp_position_direct_accuracy_u;
+
+typedef enum nrppa_trp_position_direct_accuracy_e {
+ NRPPA_TRP_POSITION_DIRECT_ACCURACY_PR_NOTHING,
+ NRPPA_TRP_POSITION_DIRECT_ACCURACY_PR_TRPPOSITION,
+ NRPPA_TRP_POSITION_DIRECT_ACCURACY_PR_TRPHAPOSITION
+} nrppa_trp_position_direct_accuracy_pr;
+
+typedef struct nrppa_trp_position_direct_accuracy_s {
+ nrppa_trp_position_direct_accuracy_pr present;
+ nrppa_trp_position_direct_accuracy_u choice;
+} nrppa_trp_position_direct_accuracy_t;
+
+typedef struct nrppa_trp_position_direct_s {
+ nrppa_trp_position_direct_accuracy_t accuracy;
+} nrppa_trp_position_direct_t;
+
+typedef enum nrppa_reference_point_e {
+ NRPPA_REFERENCE_POINT_PR_NOTHING,
+ NRPPA_REFERENCE_POINT_PR_COORDINATEID,
+ NRPPA_REFERENCE_POINT_PR_REFERENCEPOINTCOORDINATE,
+ NRPPA_REFERENCE_POINT_PR_REFERENCEPOINTCOORDINATEHA
+} nrppa_reference_point_pr;
+
+typedef union nrppa_reference_point_c {
+ long coordinate_id;
+ nrppa_access_point_position_t reference_point_coordinate;
+ nrppa_ngran_high_accuracy_access_point_position_t reference_point_coordinateHA;
+} nrppa_reference_point_u;
+
+typedef struct nrppa_reference_point_s {
+ nrppa_reference_point_pr present;
+ nrppa_reference_point_u choice;
+} nrppa_reference_point_t;
+
+typedef struct nrppa_location_uncertainty_s {
+ long horizontal_uncertainty;
+ long horizontal_confidence;
+ long vertical_uncertainty;
+ long vertical_confidence;
+} nrppa_location_uncertainty_t;
+
+typedef struct nrppa_relative_geodetic_location_s {
+ long milli_arc_second_units;
+ long height_units;
+ long delta_latitude;
+ long delta_longitude;
+ long delta_height;
+ nrppa_location_uncertainty_t location_uncertainty;
+} nrppa_relative_geodetic_location_t;
+
+typedef struct nrppa_relative_cartesian_location_s {
+ long xyz_unit;
+ long xvalue;
+ long yvalue;
+ long zvalue;
+ nrppa_location_uncertainty_t location_uncertainty;
+} nrppa_relative_cartesian_location_t;
+
+typedef union nrppa_trp_reference_point_type_c {
+ nrppa_relative_geodetic_location_t trp_position_relative_geodetic;
+ nrppa_relative_cartesian_location_t trp_position_relative_cartesian;
+} nrppa_trp_reference_point_type_u;
+
+typedef enum nrppa_trp_reference_point_type_e {
+ NRPPA_TRP_REFERENCE_POINT_TYPE_PR_NOTHING,
+ NRPPA_TRP_REFERENCE_POINT_TYPE_PR_TRPPOSITION_RELATIVE_GEODETIC,
+ NRPPA_TRP_REFERENCE_POINT_TYPE_PR_TRPPOSITION_RELATIVE_CARTESIAN
+} nrppa_trp_reference_point_type_pr;
+
+typedef struct nrppa_trp_reference_point_type_t {
+ nrppa_trp_reference_point_type_pr present;
+ nrppa_trp_reference_point_type_u choice;
+} nrppa_trp_reference_point_type_t;
+
+typedef struct nrppa_trp_position_referenced_t {
+ nrppa_reference_point_t reference_point;
+ nrppa_trp_reference_point_type_t reference_point_type;
+} nrppa_trp_position_referenced_t;
+
+typedef union nrppa_trp_position_definition_type_c {
+ nrppa_trp_position_direct_t direct;
+ nrppa_trp_position_referenced_t referenced;
+} nrppa_trp_position_definition_type_u;
+
+typedef enum nrppa_trp_position_definition_type_e {
+ NRPPA_TRP_POSITION_DEFINITION_TYPE_PR_NOTHING,
+ NRPPA_TRP_POSITION_DEFINITION_TYPE_PR_DIRECT,
+ NRPPA_TRP_POSITION_DEFINITION_TYPE_PR_REFERENCED
+} nrppa_trp_position_definition_type_pr;
+
+typedef struct nrppa_trp_position_definition_type_s {
+ nrppa_trp_position_definition_type_u choice;
+ nrppa_trp_position_definition_type_pr present;
+} nrppa_trp_position_definition_type_t;
+
+typedef struct nrppa_geographical_coordinates_s {
+ nrppa_trp_position_definition_type_t trp_position_definition_type;
+} nrppa_geographical_coordinates_t;
+
+typedef struct nrppa_ng_ran_cgi_s {
+ plmn_id_t plmn;
+ uint64_t nr_cellid;
+} nrppa_ng_ran_cgi_t;
+
+typedef union nrppa_trp_information_type_response_item_c {
+ uint16_t pci_nr;
+ nrppa_ng_ran_cgi_t ng_ran_cgi;
+ uint32_t nr_arfcn;
+ nrppa_geographical_coordinates_t geographical_coordinates;
+} nrppa_trp_information_type_response_item_u;
+
+typedef enum nrppa_trp_information_type_response_item_e {
+ NRPPA_TRP_INFORMATION_TYPE_RESPONSE_ITEM_PR_NOTHING,
+ NRPPA_TRP_INFORMATION_TYPE_RESPONSE_ITEM_PR_PCI_NR,
+ NRPPA_TRP_INFORMATION_TYPE_RESPONSE_ITEM_PR_NG_RAN_CGI,
+ NRPPA_TRP_INFORMATION_TYPE_RESPONSE_ITEM_PR_NRARFCN,
+ NRPPA_TRP_INFORMATION_TYPE_RESPONSE_ITEM_PR_PRSCONFIGURATION,
+ NRPPA_TRP_INFORMATION_TYPE_RESPONSE_ITEM_PR_SSBINFORMATION,
+ NRPPA_TRP_INFORMATION_TYPE_RESPONSE_ITEM_PR_SFNINITIALISATIONTIME,
+ NRPPA_TRP_INFORMATION_TYPE_RESPONSE_ITEM_PR_SPATIALDIRECTIONINFORMATION,
+ NRPPA_TRP_INFORMATION_TYPE_RESPONSE_ITEM_PR_GEOGRAPHICALCOORDINATES
+} nrppa_trp_information_type_response_item_pr;
+
+typedef struct nrppa_trp_information_type_response_item_s {
+ nrppa_trp_information_type_response_item_pr present;
+ nrppa_trp_information_type_response_item_u choice;
+} nrppa_trp_information_type_response_item_t;
+
+typedef struct nrppa_trp_information_type_response_list_s {
+ nrppa_trp_information_type_response_item_t *trp_information_type_response_item;
+ uint8_t trp_information_type_response_item_length;
+} nrppa_trp_information_type_response_list_t;
+
+typedef struct nrppa_trp_information_s {
+ uint32_t trp_id;
+ nrppa_trp_information_type_response_list_t trp_information_type_response_list;
+} nrppa_trp_information_t;
+
+typedef enum nrppa_subcarrier_spacing_e {
+ NRPPA_SUBCARRIER_SPACING_15KHZ,
+ NRPPA_SUBCARRIER_SPACING_30KHZ,
+ NRPPA_SUBCARRIER_SPACING_60KHZ,
+ NRPPA_SUBCARRIER_SPACING_120KHZ
+} nrppa_subcarrier_spacing_pr;
+
+typedef struct nrppa_scs_specific_carrier_s {
+ uint32_t offset_to_carrier;
+ nrppa_subcarrier_spacing_pr subcarrier_spacing;
+ uint16_t carrier_bandwidth;
+} nrppa_scs_specific_carrier_t;
+
+typedef struct nrppa_uplink_channel_bw_per_scs_list_s {
+ nrppa_scs_specific_carrier_t *scs_specific_carrier;
+ uint32_t scs_specific_carrier_list_length;
+} nrppa_uplink_channel_bw_per_scs_list_t;
+
+typedef enum nrppa_transmission_comb_e {
+ NRPPA_TRANSMISSION_COMB_PR_NOTHING,
+ NRPPA_TRANSMISSION_COMB_PR_N2,
+ NRPPA_TRANSMISSION_COMB_PR_N4
+} nrppa_transmission_comb_pr;
+
+typedef struct nrppa_transmission_comb_n2_s {
+ uint8_t comb_offset_n2;
+ uint8_t cyclic_shift_n2;
+} nrppa_transmission_comb_n2_t, nrppa_transmission_comb_pos_n2_t;
+
+typedef struct nrppa_transmission_comb_n4_s {
+ uint8_t comb_offset_n4;
+ uint8_t cyclic_shift_n4;
+} nrppa_transmission_comb_n4_t, nrppa_transmission_comb_pos_n4_t;
+
+typedef union nrppa_transmission_comb_c {
+ nrppa_transmission_comb_n2_t n2;
+ nrppa_transmission_comb_n4_t n4;
+} nrppa_transmission_comb_u;
+
+typedef struct nrppa_transmission_comb_s {
+ nrppa_transmission_comb_pr present;
+ nrppa_transmission_comb_u choice;
+} nrppa_transmission_comb_t;
+
+typedef enum nrppa_srs_resource_type_periodicity_e {
+ NRPPA_SRS_RESOURCE_TYPE_PERIODICITY_SLOT1 = 0,
+ NRPPA_SRS_RESOURCE_TYPE_PERIODICITY_SLOT2,
+ NRPPA_SRS_RESOURCE_TYPE_PERIODICITY_SLOT4,
+ NRPPA_SRS_RESOURCE_TYPE_PERIODICITY_SLOT5,
+ NRPPA_SRS_RESOURCE_TYPE_PERIODICITY_SLOT8,
+ NRPPA_SRS_RESOURCE_TYPE_PERIODICITY_SLOT10,
+ NRPPA_SRS_RESOURCE_TYPE_PERIODICITY_SLOT16,
+ NRPPA_SRS_RESOURCE_TYPE_PERIODICITY_SLOT20,
+ NRPPA_SRS_RESOURCE_TYPE_PERIODICITY_SLOT32,
+ NRPPA_SRS_RESOURCE_TYPE_PERIODICITY_SLOT40,
+ NRPPA_SRS_RESOURCE_TYPE_PERIODICITY_SLOT64,
+ NRPPA_SRS_RESOURCE_TYPE_PERIODICITY_SLOT80,
+ NRPPA_SRS_RESOURCE_TYPE_PERIODICITY_SLOT160,
+ NRPPA_SRS_RESOURCE_TYPE_PERIODICITY_SLOT320,
+ NRPPA_SRS_RESOURCE_TYPE_PERIODICITY_SLOT640,
+ NRPPA_SRS_RESOURCE_TYPE_PERIODICITY_SLOT1280,
+ NRPPA_SRS_RESOURCE_TYPE_PERIODICITY_SLOT2560
+} nrppa_srs_resource_type_periodicity_pr;
+
+typedef struct nrppa_resource_type_periodic_s {
+ nrppa_srs_resource_type_periodicity_pr periodicity;
+ uint16_t offset;
+} nrppa_resource_type_periodic_t, nrppa_resource_type_semi_persistent_t;
+
+typedef union nrppa_resource_type_c {
+ nrppa_resource_type_periodic_t periodic;
+ nrppa_resource_type_semi_persistent_t semi_persistent;
+ bool aperiodic;
+} nrppa_resource_type_u;
+
+typedef enum nrppa_resource_type_e {
+ NRPPA_RESOURCE_TYPE_PR_NOTHING,
+ NRPPA_RESOURCE_TYPE_PR_PERIODIC,
+ NRPPA_RESOURCE_TYPE_PR_SEMI_PERSISTENT,
+ NRPPA_RESOURCE_TYPE_PR_APERIODIC
+} nrppa_resource_type_pr;
+
+typedef struct nrppa_resource_type_s {
+ nrppa_resource_type_pr present;
+ nrppa_resource_type_u choice;
+} nrppa_resource_type_t;
+
+typedef struct nrppa_transmission_comb_n8_s {
+ uint8_t comb_offset_n8;
+ uint8_t cyclic_shift_n8;
+} nrppa_transmission_comb_pos_n8_t;
+
+typedef union nrppa_transmission_comb_pos_c {
+ nrppa_transmission_comb_pos_n2_t n2;
+ nrppa_transmission_comb_pos_n4_t n4;
+ nrppa_transmission_comb_pos_n8_t n8;
+} nrppa_transmission_comb_pos_u;
+
+typedef enum nrppa_transmission_comb_pos_e {
+ NRPPA_TRANSMISSION_COMB_POS_PR_NOTHING,
+ NRPPA_TRANSMISSION_COMB_POS_PR_N2,
+ NRPPA_TRANSMISSION_COMB_POS_PR_N4,
+ NRPPA_TRANSMISSION_COMB_POS_PR_N8
+} nrppa_transmission_comb_pos_pr;
+
+typedef struct nrppa_transmission_comb_pos_s {
+ nrppa_transmission_comb_pos_pr present;
+ nrppa_transmission_comb_pos_u choice;
+} nrppa_transmission_comb_pos_t;
+
+typedef enum nrppa_srs_resource_type_pos_periodicity_e {
+ NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT1 = 0,
+ NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT2,
+ NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT4,
+ NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT5,
+ NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT8,
+ NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT10,
+ NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT16,
+ NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT20,
+ NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT32,
+ NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT40,
+ NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT64,
+ NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT80,
+ NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT160,
+ NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT320,
+ NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT640,
+ NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT1280,
+ NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT2560,
+ NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT5120,
+ NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT10240,
+ NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT20480,
+ NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT40960,
+ NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT81920
+} nrppa_srs_resource_type_pos_periodicity_pr;
+
+typedef struct nrppa_resource_type_periodic_pos_s {
+ nrppa_srs_resource_type_pos_periodicity_pr periodicity;
+ uint16_t offset;
+} nrppa_resource_type_periodic_pos_t, nrppa_resource_type_semi_persistent_pos_t;
+
+typedef struct nrppa_resource_type_aperiodic_pos_s {
+ uint8_t slot_offset;
+} nrppa_resource_type_aperiodic_pos_t;
+
+typedef union nrppa_resource_type_pos_c {
+ nrppa_resource_type_periodic_pos_t periodic;
+ nrppa_resource_type_semi_persistent_pos_t semi_persistent;
+ nrppa_resource_type_aperiodic_pos_t aperiodic;
+} nrppa_resource_type_pos_u;
+
+typedef enum nrppa_resource_type_pos_e {
+ NRPPA_RESOURCE_TYPE_POS_PR_NOTHING,
+ NRPPA_RESOURCE_TYPE_POS_PR_PERIODIC,
+ NRPPA_RESOURCE_TYPE_POS_PR_SEMI_PERSISTENT,
+ NRPPA_RESOURCE_TYPE_POS_PR_APERIODIC
+} nrppa_resource_type_pos_pr;
+
+typedef struct nrppa_resource_type_pos_s {
+ nrppa_resource_type_pos_pr present;
+ nrppa_resource_type_pos_u choice;
+} nrppa_resource_type_pos_t;
+
+typedef struct nrppa_srs_resource_id_list_s {
+ long *srs_resource_id;
+ uint8_t srs_resource_id_list_length;
+} nrppa_srs_resource_id_list_t;
+
+typedef struct nrppa_resource_set_type_aperiodic_s {
+ uint8_t srs_resource_trigger;
+ long slot_offset;
+} nrppa_resource_set_type_aperiodic_t;
+
+typedef union nrppa_resource_set_type_c {
+ bool periodic;
+ bool semi_persistent;
+ nrppa_resource_set_type_aperiodic_t aperiodic;
+} nrppa_resource_set_type_u;
+
+typedef enum nrppa_resource_set_type_e {
+ NRPPA_RESOURCE_SET_TYPE_PR_NOTHING,
+ NRPPA_RESOURCE_SET_TYPE_PR_PERIODIC,
+ NRPPA_RESOURCE_SET_TYPE_PR_SEMI_PERSISTENT,
+ NRPPA_RESOURCE_SET_TYPE_PR_APERIODIC
+} nrppa_resource_set_type_pr;
+
+typedef struct nrppa_resource_set_type_s {
+ nrppa_resource_set_type_pr present;
+ nrppa_resource_set_type_u choice;
+} nrppa_resource_set_type_t;
+
+typedef struct nrppa_pos_srs_resource_id_list_s {
+ long *srs_pos_resource_id;
+ uint32_t pos_srs_resource_id_list_length;
+} nrppa_pos_srs_resource_id_list_t;
+
+typedef union nrppa_pos_resource_set_type_c {
+ bool periodic;
+ bool semi_persistent;
+ uint8_t srs_resource;
+} nrppa_pos_resource_set_type_u;
+
+typedef enum nrppa_pos_resource_set_type_e {
+ NRPPA_POS_RESOURCE_SET_TYPE_PR_NOTHING,
+ NRPPA_POS_RESOURCE_SET_TYPE_PR_PERIODIC,
+ NRPPA_POS_RESOURCE_SET_TYPE_PR_SEMI_PERSISTENT,
+ NRPPA_POS_RESOURCE_SET_TYPE_PR_APERIODIC
+} nrppa_pos_resource_set_type_pr;
+
+typedef struct nrppa_pos_resource_set_type_s {
+ nrppa_pos_resource_set_type_pr present;
+ nrppa_pos_resource_set_type_u choice;
+} nrppa_pos_resource_set_type_t;
+
+typedef enum nrppa_srs_resource_number_of_ports_e {
+ NRPPA_SRS_NUMBER_OF_PORTS_N1,
+ NRPPA_SRS_NUMBER_OF_PORTS_N2,
+ NRPPA_SRS_NUMBER_OF_PORTS_N4
+} nrppa_srs_resource_number_of_ports_pr;
+
+typedef enum nrppa_srs_resource_number_of_symbols_e {
+ NRPPA_SRS_NUMBER_OF_SYMBOLS_N1,
+ NRPPA_SRS_NUMBER_OF_SYMBOLS_N2,
+ NRPPA_SRS_NUMBER_OF_SYMBOLS_N4
+} nrppa_srs_resource_number_of_symbols_pr;
+
+typedef enum nrppa_srs_repetition_factor_e {
+ NRPPA_SRS_REPETITION_FACTOR_RF1,
+ NRPPA_SRS_REPETITION_FACTOR_RF2,
+ NRPPA_SRS_REPETITION_FACTOR_RF4
+} nrppa_srs_repetition_factor_pr;
+
+typedef enum nrppa_srs_group_or_sequencehopping_e {
+ NRPPA_GROUPORSEQUENCEHOPPING_NOTHING,
+ NRPPA_GROUPORSEQUENCEHOPPING_GROUPHOPPING,
+ NRPPA_GROUPORSEQUENCEHOPPING_SEQUENCEHOPPING
+} nrppa_srs_group_or_sequencehopping_pr;
+
+typedef struct nrppa_srs_resource_s {
+ uint32_t srs_resource_id;
+ nrppa_srs_resource_number_of_ports_pr nr_of_srs_ports;
+ nrppa_transmission_comb_t transmission_comb;
+ uint8_t start_position;
+ nrppa_srs_resource_number_of_symbols_pr nr_of_symbols;
+ nrppa_srs_repetition_factor_pr repetition_factor;
+ uint8_t freq_domain_position;
+ uint16_t freq_domain_shift;
+ uint8_t c_srs;
+ uint8_t b_srs;
+ uint8_t b_hop;
+ nrppa_srs_group_or_sequencehopping_pr group_or_sequence_hopping;
+ nrppa_resource_type_t resource_type;
+ uint16_t sequence_id;
+} nrppa_srs_resource_t;
+
+typedef enum nrppa_srs_resource_item_number_of_symbols_e {
+ NRPPA_SRS_RESOURCE_ITEM_NUMBER_OF_SYMBOLS_N1,
+ NRPPA_SRS_RESOURCE_ITEM_NUMBER_OF_SYMBOLS_N2,
+ NRPPA_SRS_RESOURCE_ITEM_NUMBER_OF_SYMBOLS_N4,
+ NRPPA_SRS_RESOURCE_ITEM_NUMBER_OF_SYMBOLS_N8,
+ NRPPA_SRS_RESOURCE_ITEM_NUMBER_OF_SYMBOLS_N12
+} nrppa_srs_resource_item_number_of_symbols_pr;
+
+typedef struct nrppa_pos_srs_resource_item_s {
+ uint32_t srs_pos_resource_id;
+ nrppa_transmission_comb_pos_t transmission_comb_pos;
+ uint8_t start_position;
+ nrppa_srs_resource_item_number_of_symbols_pr nr_of_symbols;
+ uint16_t freq_domain_shift;
+ uint8_t c_srs;
+ nrppa_srs_group_or_sequencehopping_pr group_or_sequence_hopping;
+ nrppa_resource_type_pos_t resource_type_pos;
+ uint32_t sequence_id;
+} nrppa_pos_srs_resource_item_t;
+
+typedef struct nrppa_srs_resource_set_s {
+ uint8_t srs_resource_set_id;
+ nrppa_srs_resource_id_list_t srs_resource_id_list;
+ nrppa_resource_set_type_t resource_set_type;
+} nrppa_srs_resource_set_t;
+
+typedef struct nrppa_pos_srs_resource_set_item_s {
+ uint8_t pos_srs_resource_set_id;
+ nrppa_pos_srs_resource_id_list_t pos_srs_resource_id_list;
+ nrppa_pos_resource_set_type_t pos_resource_set_type;
+} nrppa_pos_srs_resource_set_item_t;
+
+typedef struct nrppa_srs_resource_list_s {
+ nrppa_srs_resource_t *srs_resource;
+ uint32_t srs_resource_list_length;
+} nrppa_srs_resource_list_t;
+
+typedef struct nrppa_pos_srs_resource_list_s {
+ nrppa_pos_srs_resource_item_t *pos_srs_resource_item;
+ uint32_t pos_srs_resource_list_length;
+} nrppa_pos_srs_resource_list_t;
+
+typedef struct nrppa_srs_resource_set_list_s {
+ nrppa_srs_resource_set_t *srs_resource_set;
+ uint32_t srs_resource_set_list_length;
+} nrppa_srs_resource_set_list_t;
+
+typedef struct nrppa_pos_srs_resource_set_list_s {
+ nrppa_pos_srs_resource_set_item_t *pos_srs_resource_set_item;
+ uint32_t pos_srs_resource_set_list_length;
+} nrppa_pos_srs_resource_set_list_t;
+
+typedef struct nrppa_srs_config_s {
+ nrppa_srs_resource_list_t *srs_resource_list;
+ nrppa_pos_srs_resource_list_t *pos_srs_resource_list;
+ nrppa_srs_resource_set_list_t *srs_resource_set_list;
+ nrppa_pos_srs_resource_set_list_t *pos_srs_resource_set_list;
+} nrppa_srs_config_t;
+
+typedef enum nrppa_cp_type_e { NRPPA_CP_TYPE_NORMAL, NRPPA_CP_TYPE_EXTENDED } nrppa_cp_type_pr;
+
+typedef struct nrppa_active_ul_bwp_s {
+ uint32_t location_and_bandwidth;
+ nrppa_subcarrier_spacing_pr subcarrier_spacing;
+ nrppa_cp_type_pr cyclic_prefix;
+ uint32_t tx_direct_current_location;
+ uint8_t shift_7_dot_5kHz;
+ nrppa_srs_config_t srs_config;
+} nrppa_active_ul_bwp_t;
+
+typedef struct nrppa_srs_carrier_list_item_s {
+ uint32_t pointA;
+ nrppa_uplink_channel_bw_per_scs_list_t uplink_channel_bw_per_scs_list;
+ nrppa_active_ul_bwp_t active_ul_bwp;
+ uint16_t pci;
+} nrppa_srs_carrier_list_item_t;
+
+typedef struct nrppa_srs_carrier_list_s {
+ nrppa_srs_carrier_list_item_t *srs_carrier_list_item;
+ uint32_t srs_carrier_list_length;
+} nrppa_srs_carrier_list_t;
+
+typedef struct nrppa_srs_configuration_s {
+ nrppa_srs_carrier_list_t srs_carrier_list;
+} nrppa_srs_configuration_t;
+
+// IE 9.3.1.176 (TS 38.473 V16.21.0)
+typedef struct nrppa_trp_information_list_s {
+ nrppa_trp_information_t *trp_information_item;
+ uint32_t trp_information_item_length;
+} nrppa_trp_information_list_t;
+
+typedef union nrppa_srs_type_c {
+ uint8_t *srs_resource_set_id;
+ bool *aperiodic;
+} nrppa_srs_type_u;
+
+typedef enum nrppa_srs_type_e {
+ NRPPA_SRS_TYPE_PR_NOTHING,
+ NRPPA_SRS_TYPE_PR_SEMIPERSISTENTSRS,
+ NRPPA_SRS_TYPE_PR_APERIODICSRS
+} nrppa_srs_type_pr;
+
+typedef struct nrppa_srs_type_s {
+ nrppa_srs_type_pr present;
+ nrppa_srs_type_u choice;
+} nrppa_srs_type_t;
+
+typedef struct nrppa_trp_measurement_request_item_s {
+ uint32_t trp_id;
+} nrppa_trp_measurement_request_item_t;
+
+typedef struct nrppa_trp_measurement_request_list_s {
+ nrppa_trp_measurement_request_item_t *trp_measurement_request_item;
+ uint32_t trp_measurement_request_list_length;
+} nrppa_trp_measurement_request_list_t;
+
+typedef enum nrppa_pos_report_characteristics_e {
+ NRPPA_POSREPORTCHARACTERISTICS_ONDEMAND = 0,
+ NRPPA_POSREPORTCHARACTERISTICS_PERIODIC = 1
+} nrppa_report_characteristics_pr;
+
+typedef enum nrppa_pos_measurement_periodicity_e {
+ NRPPA_POSMEASUREMENTPERIODICITY_MS120 = 0,
+ NRPPA_POSMEASUREMENTPERIODICITY_MS240 = 1,
+ NRPPA_POSMEASUREMENTPERIODICITY_MS480 = 2,
+ NRPPA_POSMEASUREMENTPERIODICITY_MS640 = 3,
+ NRPPA_POSMEASUREMENTPERIODICITY_MS1024 = 4,
+ NRPPA_POSMEASUREMENTPERIODICITY_MS2048 = 5,
+ NRPPA_POSMEASUREMENTPERIODICITY_MS5120 = 6,
+ NRPPA_POSMEASUREMENTPERIODICITY_MS10240 = 7,
+ NRPPA_POSMEASUREMENTPERIODICITY_MIN1 = 8,
+ NRPPA_POSMEASUREMENTPERIODICITY_MIN6 = 9,
+ NRPPA_POSMEASUREMENTPERIODICITY_MIN12 = 10,
+ NRPPA_POSMEASUREMENTPERIODICITY_MIN30 = 11,
+ NRPPA_POSMEASUREMENTPERIODICITY_MIN60 = 12
+} nrppa_measurement_periodicity_pr;
+
+typedef enum nrppa_pos_measurement_type_e {
+ NRPPA_POSMEASUREMENTTYPE_GNB_RX_TX = 0,
+ NRPPA_POSMEASUREMENTTYPE_UL_SRS_RSRP = 1,
+ NRPPA_POSMEASUREMENTTYPE_UL_AOA = 2,
+ NRPPA_POSMEASUREMENTTYPE_UL_RTOA = 3
+} nrppa_measurement_type_pr;
+
+typedef struct nrppa_pos_measurement_quantities_item_s {
+ nrppa_measurement_type_pr measurement_type;
+} nrppa_measurement_quantities_item_t;
+
+typedef struct nrppa_pos_measurement_quantities_s {
+ nrppa_measurement_quantities_item_t *measurement_quantities_item;
+ uint32_t measurement_quantities_length;
+} nrppa_measurement_quantities_t;
+
+typedef struct nrppa_lcs_to_gcs_translationaoa_c {
+ uint16_t alpha;
+ uint16_t beta;
+ uint16_t gamma;
+} nrppa_lcs_to_gcs_translationaoa_t;
+
+typedef struct nrppa_ul_aoa_s {
+ uint16_t azimuth_aoa;
+ uint16_t *zenith_aoa;
+ nrppa_lcs_to_gcs_translationaoa_t *lcs_to_gcs_translation_aoa;
+} nrppa_ul_aoa_t;
+
+typedef union nrppa_relative_path_delay_c {
+ uint32_t k0;
+ uint32_t k1;
+ uint32_t k2;
+ uint32_t k3;
+ uint32_t k4;
+ uint32_t k5;
+} nrppa_relative_path_delay_u, nrppa_ul_rtoa_measurement_u, nrppa_gnb_rx_tx_time_diff_u;
+
+typedef enum nrppa_gnb_rx_tx_time_diff_meas_e {
+ NRPPA_GNBRXTXTIMEDIFFMEAS_PR_NOTHING,
+ NRPPA_GNBRXTXTIMEDIFFMEAS_PR_K0,
+ NRPPA_GNBRXTXTIMEDIFFMEAS_PR_K1,
+ NRPPA_GNBRXTXTIMEDIFFMEAS_PR_K2,
+ NRPPA_GNBRXTXTIMEDIFFMEAS_PR_K3,
+ NRPPA_GNBRXTXTIMEDIFFMEAS_PR_K4,
+ NRPPA_GNBRXTXTIMEDIFFMEAS_PR_K5
+} nrppa_gnb_rx_tx_time_diff_pr;
+
+typedef struct nrppa_gnb_rx_tx_time_diff_s {
+ nrppa_gnb_rx_tx_time_diff_pr present;
+ nrppa_gnb_rx_tx_time_diff_u choice;
+} nrppa_gnb_rx_tx_time_diff_t;
+
+typedef enum nrppa_ul_rtoa_measurement_e {
+ NRPPA_ULRTOAMEAS_PR_NOTHING,
+ NRPPA_ULRTOAMEAS_PR_K0,
+ NRPPA_ULRTOAMEAS_PR_K1,
+ NRPPA_ULRTOAMEAS_PR_K2,
+ NRPPA_ULRTOAMEAS_PR_K3,
+ NRPPA_ULRTOAMEAS_PR_K4,
+ NRPPA_ULRTOAMEAS_PR_K5
+} nrppa_ul_rtoa_measurement_pr;
+
+typedef struct nrppa_ul_rtoa_measurement_s {
+ nrppa_ul_rtoa_measurement_pr present;
+ nrppa_ul_rtoa_measurement_u choice;
+} nrppa_ul_rtoa_measurement_t;
+
+typedef union nrppa_measured_results_value_c {
+ nrppa_ul_aoa_t ul_angle_of_arrival;
+ uint8_t ul_srs_rsrp;
+ nrppa_ul_rtoa_measurement_t ul_rtoa;
+ nrppa_gnb_rx_tx_time_diff_t gnb_rx_tx_time_diff;
+} nrppa_measured_results_value_u;
+
+typedef enum nrppa_measured_results_value_e {
+ NRPPA_MEASURED_RESULTS_VALUE_PR_NOTHING,
+ NRPPA_MEASURED_RESULTS_VALUE_PR_UL_ANGLEOFARRIVAL,
+ NRPPA_MEASURED_RESULTS_VALUE_PR_UL_SRS_RSRP,
+ NRPPA_MEASURED_RESULTS_VALUE_PR_UL_RTOA,
+ NRPPA_MEASURED_RESULTS_VALUE_PR_GNB_RXTXTIMEDIFF
+} nrppa_measured_results_value_pr;
+
+typedef struct nrppa_measured_results_value_s {
+ nrppa_measured_results_value_pr present;
+ nrppa_measured_results_value_u choice;
+} nrppa_measured_results_value_t;
+
+typedef union nrppa_time_stamp_slot_index_c {
+ uint8_t scs_15;
+ uint8_t scs_30;
+ uint8_t scs_60;
+ uint8_t scs_120;
+} nrppa_time_stamp_slot_index_u;
+
+typedef enum nrppa_time_stamp_slot_index_e {
+ NRPPA_TIME_STAMP_SLOT_INDEX_PR_NOTHING,
+ NRPPA_TIME_STAMP_SLOT_INDEX_PR_SCS_15,
+ NRPPA_TIME_STAMP_SLOT_INDEX_PR_SCS_30,
+ NRPPA_TIME_STAMP_SLOT_INDEX_PR_SCS_60,
+ NRPPA_TIME_STAMP_SLOT_INDEX_PR_SCS_120
+} nrppa_time_stamp_slot_index_pr;
+
+typedef struct nrppa_time_stamp_slot_index_s {
+ nrppa_time_stamp_slot_index_pr present;
+ nrppa_time_stamp_slot_index_u choice;
+} nrppa_time_stamp_slot_index_t;
+
+typedef struct nrppa_time_stamp_s {
+ uint16_t system_frame_number;
+ nrppa_time_stamp_slot_index_t slot_index;
+} nrppa_time_stamp_t;
+
+typedef struct nrppa_measurement_result_item_s {
+ nrppa_measured_results_value_t measured_results_value;
+ nrppa_time_stamp_t time_stamp;
+} nrppa_measurement_result_item_t;
+
+typedef struct nrppa_measurement_result_s {
+ nrppa_measurement_result_item_t *measurement_result_item;
+ uint32_t measurement_result_item_length;
+} nrppa_measurement_result_t;
+
+typedef struct nrppa_measurement_response_item_s {
+ nrppa_measurement_result_t measurement_result;
+ uint32_t trp_id;
+} nrppa_measurement_response_item_t;
+
+typedef struct nrppa_measurement_response_list_s {
+ nrppa_measurement_response_item_t *measurement_response_item;
+ uint32_t measurement_response_list_length;
+} nrppa_measurement_response_list_t;
+
+typedef struct nrppa_trp_information_req_s {
+ // IE 9.2.4 (mandatory)
+ uint16_t transaction_id;
+ bool has_trp_list;
+ // mandatory
+ nrppa_trp_list_t trp_list;
+ // mandatory
+ nrppa_trp_information_type_list_t trp_information_type_list;
+} nrppa_trp_information_req_t;
+
+typedef struct nrppa_trp_information_resp_s {
+ // IE 9.2.4 (mandatory)
+ uint16_t transaction_id;
+ // mandatory
+ nrppa_trp_information_list_t trp_information_list;
+} nrppa_trp_information_resp_t;
+
+typedef struct nrppa_positioning_information_req_s {
+ // IE 9.2.4 (mandatory)
+ uint16_t transaction_id;
+} nrppa_positioning_information_req_t;
+
+typedef struct nrppa_positioning_information_resp_s {
+ // IE 9.2.4 (mandatory)
+ uint16_t transaction_id;
+ // IE 9.2.28 (optional)
+ nrppa_srs_configuration_t *srs_configuration;
+} nrppa_positioning_information_resp_t;
+
+typedef struct nrppa_positioning_activation_req_s {
+ // IE 9.2.4 (mandatory)
+ uint16_t transaction_id;
+ // (mandatory)
+ nrppa_srs_type_t srs_type;
+} nrppa_positioning_activation_req_t;
+
+typedef struct nrppa_positioning_activation_resp_s {
+ // IE 9.2.4 (mandatory)
+ uint16_t transaction_id;
+} nrppa_positioning_activation_resp_t;
+
+typedef struct nrppa_measurement_req_s {
+ // IE 9.2.4 (mandatory)
+ uint16_t transaction_id;
+ // (mandatory)
+ uint32_t lmf_measurement_id;
+ // (mandatory)
+ nrppa_trp_measurement_request_list_t trp_measurement_request_list;
+ // (mandatory) ondemand = 0, periodic = 1
+ nrppa_report_characteristics_pr report_characteristics;
+ // if report characteristics periodic
+ nrppa_measurement_periodicity_pr measurement_periodicity;
+ // (mandatory)
+ nrppa_measurement_quantities_t measurement_quantities;
+ // IE 9.2.28 (optional)
+ nrppa_srs_configuration_t *srs_configuration;
+} nrppa_measurement_req_t;
+
+typedef struct nrppa_measurement_resp_s {
+ // IE 9.2.4 (mandatory)
+ uint16_t transaction_id;
+ // (mandatory)
+ uint32_t lmf_measurement_id;
+ // (mandatory)
+ uint32_t ran_measurement_id;
+ // (optional)
+ nrppa_measurement_response_list_t *measurement_response_list;
+} nrppa_measurement_resp_t;
+
+#endif // NRPPA_MESSAGES_TYPES_H_
diff --git a/openair2/COMMON/positioning_nr_paramdef.h b/openair2/COMMON/positioning_nr_paramdef.h
new file mode 100644
index 0000000000..6861db6778
--- /dev/null
+++ b/openair2/COMMON/positioning_nr_paramdef.h
@@ -0,0 +1,62 @@
+/*
+ * Licensed to the OpenAirInterface (OAI) Software Alliance under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The OpenAirInterface Software Alliance licenses this file to You under
+ * the OAI Public License, Version 1.1 (the "License"); you may not use this file
+ * except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.openairinterface.org/?page_id=698
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *-------------------------------------------------------------------------------
+ * For more information about the OpenAirInterface (OAI) Software Alliance:
+ * contact@openairinterface.org
+ */
+
+#ifndef __POSITIONING_NR_PARAMDEF__H__
+#define __POSITIONING_NR_PARAMDEF__H__
+
+/* Positioning configuration section names */
+#define CONFIG_STRING_POSITIONING_CONFIG "positioning_config"
+
+/* Global parameters */
+
+/* TRP configuration parameters names */
+#define CONFIG_STRING_POSITIONING_NUM_TRPS "NumTRPs"
+#define CONFIG_STRING_POSITIONING_TRP_IDS_LIST "TRPIDs"
+#define CONFIG_STRING_POSITIONING_TRP_X_AXIS_LIST "TRPxAxis"
+#define CONFIG_STRING_POSITIONING_TRP_Y_AXIS_LIST "TRPyAxis"
+#define CONFIG_STRING_POSITIONING_TRP_Z_AXIS_LIST "TRPzAxis"
+#define CONFIG_STRING_POSITIONING_TRP_UNIT_LIST "Units"
+
+/* Help string for Positioning parameters */
+#define HELP_STRING_POSITIONING_NUM_TRPS "Number of TRPs connected with gNB(max 4)\n"
+#define HELP_STRING_POSITIONING_TRP_IDS_LIST "User defined IDs for each TRP \n"
+#define HELP_STRING_POSITIONING_TRP_X_AXIS_LIST "x-axis value of each TRP \n"
+#define HELP_STRING_POSITIONING_TRP_Y_AXIS_LIST "y-axis value of each TRP \n"
+#define HELP_STRING_POSITIONING_TRP_Z_AXIS_LIST "z-axis value of each TRP \n"
+#define HELP_STRING_POSITIONING_TRP_UNIT_LIST "XYZ unit value of each TRP \n"
+
+/*----------------------------------------------------------------------------------------------------------------------------------------------------------------*/
+/* TRP configuration parameters */
+/* optname helpstr paramflags XXXptr defXXXval type
+ * numelt */
+/*----------------------------------------------------------------------------------------------------------------------------------------------------------------*/
+// clang-format off
+#define POSITIONING_PARAMS_DESC { \
+ {CONFIG_STRING_POSITIONING_NUM_TRPS, HELP_STRING_POSITIONING_NUM_TRPS, 0, .uptr=NULL, .defuintval=0, TYPE_UINT, 0}, \
+ {CONFIG_STRING_POSITIONING_TRP_IDS_LIST, HELP_STRING_POSITIONING_TRP_IDS_LIST, 0, .uptr=NULL, .defintarrayval=0, TYPE_UINTARRAY, 0}, \
+ {CONFIG_STRING_POSITIONING_TRP_X_AXIS_LIST, HELP_STRING_POSITIONING_TRP_X_AXIS_LIST, 0, .uptr=NULL, .defintarrayval=0, TYPE_UINTARRAY, 0}, \
+ {CONFIG_STRING_POSITIONING_TRP_Y_AXIS_LIST, HELP_STRING_POSITIONING_TRP_Y_AXIS_LIST, 0, .uptr=NULL, .defintarrayval=0, TYPE_UINTARRAY, 0}, \
+ {CONFIG_STRING_POSITIONING_TRP_Z_AXIS_LIST, HELP_STRING_POSITIONING_TRP_Z_AXIS_LIST, 0, .uptr=NULL, .defintarrayval=0, TYPE_UINTARRAY, 0}, \
+ {CONFIG_STRING_POSITIONING_TRP_UNIT_LIST, HELP_STRING_POSITIONING_TRP_UNIT_LIST, 0, .uptr=NULL, .defintarrayval=0, TYPE_UINTARRAY, 0}, \
+}
+// clang-format on
+
+#endif
diff --git a/openair2/F1AP/f1ap_du_task.h b/openair2/F1AP/f1ap_du_task.h
index 8ce8aacab6..8546ca6cb3 100644
--- a/openair2/F1AP/f1ap_du_task.h
+++ b/openair2/F1AP/f1ap_du_task.h
@@ -21,9 +21,9 @@
#ifndef F1AP_DU_TASK_H_
#define F1AP_DU_TASK_H_
+#include "openair2/COMMON/f1ap_messages_types.h"
-struct f1ap_net_config_t;
-void du_task_send_sctp_association_req(instance_t instance, struct f1ap_net_config_t *du_inst);
+void du_task_send_sctp_association_req(instance_t instance, f1ap_net_config_t *du_inst);
void du_task_handle_sctp_association_resp(instance_t instance, sctp_new_association_resp_t *sctp_new_association_resp);
void du_task_handle_sctp_data_ind(instance_t instance, sctp_data_ind_t *sctp_data_ind);
void *F1AP_DU_task(void *arg);
diff --git a/openair2/F1AP/lib/f1ap_lib_common.h b/openair2/F1AP/lib/f1ap_lib_common.h
index 94e0ee22c3..419ee278b1 100644
--- a/openair2/F1AP/lib/f1ap_lib_common.h
+++ b/openair2/F1AP/lib/f1ap_lib_common.h
@@ -83,14 +83,10 @@
} while (0)
bool eq_f1ap_plmn(const plmn_id_t *a, const plmn_id_t *b);
-struct f1ap_served_cell_info_t;
-bool eq_f1ap_cell_info(const struct f1ap_served_cell_info_t *a, const struct f1ap_served_cell_info_t *b);
-struct f1ap_gnb_du_system_info_t;
-bool eq_f1ap_sys_info(const struct f1ap_gnb_du_system_info_t *a, const struct f1ap_gnb_du_system_info_t *b);
-struct f1ap_nr_frequency_info_t;
-bool eq_f1ap_freq_info(const struct f1ap_nr_frequency_info_t *a, const struct f1ap_nr_frequency_info_t *b);
-struct f1ap_transmission_bandwidth_t;
-bool eq_f1ap_tx_bandwidth(const struct f1ap_transmission_bandwidth_t *a, const struct f1ap_transmission_bandwidth_t *b);
+bool eq_f1ap_cell_info(const f1ap_served_cell_info_t *a, const f1ap_served_cell_info_t *b);
+bool eq_f1ap_sys_info(const f1ap_gnb_du_system_info_t *a, const f1ap_gnb_du_system_info_t *b);
+bool eq_f1ap_freq_info(const f1ap_nr_frequency_info_t *a, const f1ap_nr_frequency_info_t *b);
+bool eq_f1ap_tx_bandwidth(const f1ap_transmission_bandwidth_t *a, const f1ap_transmission_bandwidth_t *b);
struct OCTET_STRING;
uint8_t *cp_octet_string(const struct OCTET_STRING *os, int *len);
diff --git a/openair2/GNB_APP/gnb_app.c b/openair2/GNB_APP/gnb_app.c
index 98546413a0..9597f61430 100644
--- a/openair2/GNB_APP/gnb_app.c
+++ b/openair2/GNB_APP/gnb_app.c
@@ -53,6 +53,7 @@
#include "openair2/E1AP/e1ap.h"
#include "gnb_config.h"
#include "openair2/LAYER2/NR_MAC_gNB/mac_proto.h"
+#include "openair2/GNB_APP/gnb_config_ng.h"
extern RAN_CONTEXT_t RC;
/*------------------------------------------------------------------------------*/
diff --git a/openair2/GNB_APP/gnb_config.c b/openair2/GNB_APP/gnb_config.c
index 667ab25093..d3618bdaaf 100644
--- a/openair2/GNB_APP/gnb_config.c
+++ b/openair2/GNB_APP/gnb_config.c
@@ -79,7 +79,8 @@
#include "uper_encoder.h"
#include "utils.h"
#include "x2ap_messages_types.h"
-
+#include "gnb_config_common.h"
+#include "positioning_nr_paramdef.h"
static int DEFBANDS[] = {7};
static int DEFENBS[] = {0};
@@ -96,45 +97,6 @@ static int DEFRUTPCORES[] = {-1,-1,-1,-1};
(element)->choice.setup = CALLOC(1, sizeof(*((element)->choice.setup))); \
} while (0)
-static uint16_t set_snssai_config(nssai_t *nssai, const int max_num_ssi, uint8_t k, uint8_t l)
-{
- char snssaistr[MAX_OPTNAME_SIZE * 2 + 8];
- snprintf(snssaistr, sizeof(snssaistr), "%s.[%i].%s.[%i]", GNB_CONFIG_STRING_GNB_LIST, k, GNB_CONFIG_STRING_PLMN_LIST, l);
- GET_PARAMS_LIST(SNSSAIParamList,
- SNSSAIParams,
- GNBSNSSAIPARAMS_DESC,
- GNB_CONFIG_STRING_SNSSAI_LIST,
- snssaistr,
- SNSSAIPARAMS_CHECK);
- uint16_t num_ssi = SNSSAIParamList.numelt;
- AssertFatal(num_ssi < max_num_ssi, "S-NSSAI size %d exceeds the max array size %d", num_ssi, max_num_ssi);
- for (int s = 0; s < num_ssi; ++s) {
- nssai[s].sst = *SNSSAIParamList.paramarray[s][GNB_SLICE_SERVICE_TYPE_IDX].uptr;
- // SD is optional
- // 0xffffff is "no SD", see 23.003 Sec 28.4.2
- nssai[s].sd = *SNSSAIParamList.paramarray[s][GNB_SLICE_DIFFERENTIATOR_IDX].uptr;
- AssertFatal(nssai[s].sd <= 0xffffff, "SD cannot be bigger than 0xffffff, but is %d\n", nssai[s].sd);
- }
- return num_ssi;
-}
-
-static uint8_t set_plmn_config(plmn_id_t *p, uint8_t idx)
-{
- char gnbpath[MAX_OPTNAME_SIZE * 2 + 8];
- snprintf(gnbpath, sizeof(gnbpath), "%s.[%i]", GNB_CONFIG_STRING_GNB_LIST, idx);
- GET_PARAMS_LIST(PLMNParamList, PLMNParams, GNBPLMNPARAMS_DESC, GNB_CONFIG_STRING_PLMN_LIST, gnbpath, PLMNPARAMS_CHECK);
- uint8_t num_plmn = PLMNParamList.numelt;
- AssertFatal(num_plmn >= 1 && num_plmn <= 6, "The number of PLMN IDs must be in [1,6], but is %d\n", num_plmn);
- for (int l = 0; l < num_plmn; ++l) {
- plmn_id_t *plmn = &p[l];
- plmn->mcc = *PLMNParamList.paramarray[l][GNB_MOBILE_COUNTRY_CODE_IDX].uptr;
- plmn->mnc = *PLMNParamList.paramarray[l][GNB_MOBILE_NETWORK_CODE_IDX].uptr;
- plmn->mnc_digit_length = *PLMNParamList.paramarray[l][GNB_MNC_DIGIT_LENGTH].u8ptr;
- AssertFatal((plmn->mnc_digit_length == 2) || (plmn->mnc_digit_length == 3), "BAD MNC DIGIT LENGTH %d", plmn->mnc_digit_length);
- }
- return num_plmn;
-}
-
/**
* Allocate memory and initialize ServingCellConfigCommon struct members
*/
@@ -816,7 +778,7 @@ void RCconfig_nr_prs(void)
/**
* @brief Get number or blacklisted UL PRBs and their mapping from gNB config
*/
-static int get_prb_blacklist(uint8_t instance, uint16_t *prbbl)
+static int get_prb_blacklist(uint16_t *prbbl)
{
paramdef_t GNBSParams[] = GNBSPARAMS_DESC;
paramlist_def_t GNBParamList = {GNB_CONFIG_STRING_GNB_LIST, NULL, 0};
@@ -870,7 +832,7 @@ void RCconfig_NR_L1(void)
// PRB Blacklist
uint16_t prbbl[MAX_BWP_SIZE] = {0};
- int num_ulprbbl = get_prb_blacklist(j, prbbl);
+ int num_ulprbbl = get_prb_blacklist(prbbl);
if (num_ulprbbl != -1) {
RC.gNB[j]->num_ulprbbl = num_ulprbbl;
LOG_D(NR_PHY, "Copying %d blacklisted PRB to L1 context\n", RC.gNB[j]->num_ulprbbl);
@@ -943,7 +905,7 @@ bool is_pattern2_config(paramdef_t *param)
return true;
}
-static NR_ServingCellConfigCommon_t *get_scc_config(configmodule_interface_t *cfg, int minRXTXTIME, int do_SRS)
+static NR_ServingCellConfigCommon_t *get_scc_config(int minRXTXTIME, int do_SRS)
{
NR_ServingCellConfigCommon_t *scc = calloc_or_fail(1, sizeof(*scc));
uint64_t ssb_bitmap=0xff;
@@ -1039,8 +1001,7 @@ static NR_ServingCellConfigCommon_t *get_scc_config(configmodule_interface_t *cf
return scc;
}
-static int read_du_cell_info(configmodule_interface_t *cfg,
- bool separate_du,
+static int read_du_cell_info(bool separate_du,
uint32_t *gnb_id,
uint64_t *gnb_du_id,
char **name,
@@ -1211,7 +1172,7 @@ static f1ap_setup_req_t *RC_read_F1Setup(uint64_t id,
return req;
}
-static nr_ptrs_config_t *get_ptrs_config(int gnb_idx)
+static nr_ptrs_config_t *get_ptrs_config()
{
char aprefix[MAX_OPTNAME_SIZE * 2 + 8];
snprintf(aprefix, sizeof(aprefix), "%s.[%i]", GNB_CONFIG_STRING_GNB_LIST, 0);
@@ -1471,7 +1432,7 @@ void RCconfig_nr_macrlc(configmodule_interface_t *cfg)
AssertFatal(config.maxMIMO_layers != 0 && config.maxMIMO_layers <= tot_ant, "Invalid maxMIMO_layers %d\n", config.maxMIMO_layers);
config.redcap = get_redcap_config(0);
- config.ptrs = get_ptrs_config(0);
+ config.ptrs = get_ptrs_config();
char aprefix[MAX_OPTNAME_SIZE * 2 + 8];
snprintf(aprefix, sizeof(aprefix), "%s.[%d].%s", GNB_CONFIG_STRING_GNB_LIST, 0, GNB_CONFIG_STRING_TIMERS_CONFIG);
@@ -1523,7 +1484,7 @@ void RCconfig_nr_macrlc(configmodule_interface_t *cfg)
config.num_agg_level_candidates[PDCCH_AGG_LEVEL8],
config.num_agg_level_candidates[PDCCH_AGG_LEVEL16]);
- NR_ServingCellConfigCommon_t *scc = get_scc_config(cfg, config.minRXTXTIME, config.do_SRS);
+ NR_ServingCellConfigCommon_t *scc = get_scc_config(config.minRXTXTIME, config.do_SRS);
// BWP
get_bwp_config(&config, scc);
AssertFatal(config.num_additional_bwps <= 4, "Impossible to configure more than 4 additional BWPs\n");
@@ -1622,7 +1583,7 @@ void RCconfig_nr_macrlc(configmodule_interface_t *cfg)
RC.nrmac[j]->identity_pm = *(MacRLC_ParamList.paramarray[j][MACRLC_IDENTITY_PM_IDX].u8ptr);
// PRB Blacklist
uint16_t prbbl[MAX_BWP_SIZE] = {0};
- int num_ulprbbl = get_prb_blacklist(j, prbbl);
+ int num_ulprbbl = get_prb_blacklist(prbbl);
if (num_ulprbbl != -1) {
LOG_I(NR_PHY, "Copying %d blacklisted PRB to L1 context\n", num_ulprbbl);
memcpy(RC.nrmac[j]->ulprbbl, prbbl, MAX_BWP_SIZE * sizeof(prbbl[0]));
@@ -1667,7 +1628,7 @@ void RCconfig_nr_macrlc(configmodule_interface_t *cfg)
uint32_t gnb_id = 0;
char *name = NULL;
f1ap_served_cell_info_t info;
- read_du_cell_info(cfg, NODE_IS_DU(node_type), &gnb_id, &gnb_du_id, &name, &info, 1);
+ read_du_cell_info(NODE_IS_DU(node_type), &gnb_id, &gnb_du_id, &name, &info, 1);
NR_COMMON_channels_t *cc = &RC.nrmac[0]->common_channels[0];
cc->du_SIBs = fill_du_sibs(GNBParamList.paramarray[0]);
@@ -2131,130 +2092,6 @@ gNB_RRC_INST *RCconfig_NRRRC()
return rrc;
}
-int RCconfig_NR_NG(MessageDef *msg_p, uint32_t i)
-{
- int j,k = 0;
- int gnb_id;
-
- char* gnb_ipv4_address_for_NGU = NULL;
- uint32_t gnb_port_for_NGU = 0;
- char* gnb_ipv4_address_for_S1U = NULL;
- uint32_t gnb_port_for_S1U = 0;
-
- GET_PARAMS(GNBSParams, GNBSPARAMS_DESC, NULL);
- AssertFatal (i0) {
- // Output a list of all gNBs.
- GET_PARAMS_LIST(GNBParamList, GNBParams, GNBPARAMS_DESC, GNB_CONFIG_STRING_GNB_LIST, NULL);
- if (GNBParamList.numelt > 0) {
- for (k = 0; k < GNBParamList.numelt; k++) {
- if (GNBParamList.paramarray[k][GNB_GNB_ID_IDX].uptr == NULL) {
- // Calculate a default gNB ID
- if (IS_SA_MODE(get_softmodem_params())) {
- uint32_t hash;
-
- hash = ngap_generate_gNB_id ();
- gnb_id = k + (hash & 0xFFFFFF8);
- } else {
- gnb_id = k;
- }
- } else {
- gnb_id = *(GNBParamList.paramarray[k][GNB_GNB_ID_IDX].uptr);
- }
-
-
- // search if in active list
- for (j=0; j < GNBSParams[GNB_ACTIVE_GNBS_IDX].numelt; j++) {
- if (strcmp(GNBSParams[GNB_ACTIVE_GNBS_IDX].strlistptr[j], *(GNBParamList.paramarray[k][GNB_GNB_NAME_IDX].strptr)) == 0) {
-
- char aprefix[MAX_OPTNAME_SIZE*2 + 8];
- NGAP_REGISTER_GNB_REQ (msg_p).gNB_id = gnb_id;
-
- if (strcmp(*(GNBParamList.paramarray[k][GNB_CELL_TYPE_IDX].strptr), "CELL_MACRO_GNB") == 0) {
- NGAP_REGISTER_GNB_REQ (msg_p).cell_type = CELL_MACRO_GNB;
- } else if (strcmp(*(GNBParamList.paramarray[k][GNB_CELL_TYPE_IDX].strptr), "CELL_HOME_GNB") == 0) {
- NGAP_REGISTER_GNB_REQ (msg_p).cell_type = CELL_HOME_ENB;
- } else {
- AssertFatal (0,
- "Failed to parse gNB configuration file %s, gnb %u unknown value \"%s\" for cell_type choice: CELL_MACRO_GNB or CELL_HOME_GNB !\n",
- RC.config_file_name, i, *(GNBParamList.paramarray[k][GNB_CELL_TYPE_IDX].strptr));
- }
-
- NGAP_REGISTER_GNB_REQ (msg_p).gNB_name = strdup(*(GNBParamList.paramarray[k][GNB_GNB_NAME_IDX].strptr));
- NGAP_REGISTER_GNB_REQ (msg_p).tac = *GNBParamList.paramarray[k][GNB_TRACKING_AREA_CODE_IDX].uptr;
- AssertFatal(!GNBParamList.paramarray[k][GNB_MOBILE_COUNTRY_CODE_IDX_OLD].strptr
- && !GNBParamList.paramarray[k][GNB_MOBILE_NETWORK_CODE_IDX_OLD].strptr,
- "It seems that you use an old configuration file. Please change the existing\n"
- " tracking_area_code = \"1\";\n"
- " mobile_country_code = \"208\";\n"
- " mobile_network_code = \"93\";\n"
- "to\n"
- " tracking_area_code = 1; // no string!!\n"
- " plmn_list = ( { mcc = 208; mnc = 93; mnc_length = 2; } )\n");
- // PLMN
- plmn_id_t p[PLMN_LIST_MAX_SIZE] = {0};
- NGAP_REGISTER_GNB_REQ(msg_p).num_plmn = set_plmn_config(p, 0);
- for (int l = 0; l < NGAP_REGISTER_GNB_REQ(msg_p).num_plmn; ++l) {
- NGAP_REGISTER_GNB_REQ(msg_p).plmn[l].plmn = p[l];
- // SNSSAI
- NGAP_REGISTER_GNB_REQ(msg_p).plmn[l].num_nssai = set_snssai_config(NGAP_REGISTER_GNB_REQ(msg_p).plmn[l].s_nssai, 8, k, l);
- }
- NGAP_REGISTER_GNB_REQ(msg_p).default_drx = 0;
- // NG
- snprintf(aprefix, sizeof(aprefix), "%s.[%i]", GNB_CONFIG_STRING_GNB_LIST, k);
- GET_PARAMS_LIST(NGParamList, NGParams, GNBNGPARAMS_DESC, GNB_CONFIG_STRING_AMF_IP_ADDRESS, aprefix);
- NGAP_REGISTER_GNB_REQ (msg_p).nb_amf = 0;
-
- for (int l = 0; l < NGParamList.numelt; l++) {
- NGAP_REGISTER_GNB_REQ (msg_p).nb_amf += 1;
- strcpy(NGAP_REGISTER_GNB_REQ (msg_p).amf_ip_address[l].ipv4_address,*(NGParamList.paramarray[l][GNB_AMF_IPV4_ADDRESS_IDX].strptr));
- NGAP_REGISTER_GNB_REQ (msg_p).amf_ip_address[j].ipv4 = 1;
- NGAP_REGISTER_GNB_REQ (msg_p).amf_ip_address[j].ipv6 = 0;
- /* if no broadcasst_plmn array is defined, fill default values */
- if (NGAP_REGISTER_GNB_REQ(msg_p).broadcast_plmn_num[l] == 0) {
- NGAP_REGISTER_GNB_REQ(msg_p).broadcast_plmn_num[l] = NGAP_REGISTER_GNB_REQ(msg_p).num_plmn;
- for (int el = 0; el < NGAP_REGISTER_GNB_REQ(msg_p).num_plmn; ++el)
- NGAP_REGISTER_GNB_REQ(msg_p).broadcast_plmn_index[l][el] = el;
- }
- }
-
- // SCTP SETTING
- NGAP_REGISTER_GNB_REQ (msg_p).sctp_out_streams = SCTP_OUT_STREAMS;
- NGAP_REGISTER_GNB_REQ (msg_p).sctp_in_streams = SCTP_IN_STREAMS;
- if (IS_SA_MODE(get_softmodem_params())) {
- snprintf(aprefix, sizeof(aprefix), "%s.[%d].%s", GNB_CONFIG_STRING_GNB_LIST, k, GNB_CONFIG_STRING_SCTP_CONFIG);
- GET_PARAMS(SCTPParams, GNBSCTPPARAMS_DESC, aprefix);
- NGAP_REGISTER_GNB_REQ (msg_p).sctp_in_streams = (uint16_t)*(SCTPParams[GNB_SCTP_INSTREAMS_IDX].uptr);
- NGAP_REGISTER_GNB_REQ (msg_p).sctp_out_streams = (uint16_t)*(SCTPParams[GNB_SCTP_OUTSTREAMS_IDX].uptr);
- }
-
- // NETWORK_INTERFACES
- snprintf(aprefix, sizeof(aprefix), "%s.[%d].%s", GNB_CONFIG_STRING_GNB_LIST, k, GNB_CONFIG_STRING_NETWORK_INTERFACES_CONFIG);
- GET_PARAMS(NETParams, GNBNETPARAMS_DESC, aprefix);
- if (NETParams[GNB_IPV4_ADDRESS_FOR_NG_AMF_IDX].strptr != NULL) {
- char *cidr = *(NETParams[GNB_IPV4_ADDRESS_FOR_NG_AMF_IDX].strptr);
- char *save = NULL;
- char *address = strtok_r(cidr, "/", &save);
- strcpy(NGAP_REGISTER_GNB_REQ (msg_p).gnb_ip_address.ipv4_address, address);
- LOG_I(GNB_APP, "Parsed IPv4 address for NG AMF: %s\n", address);
- }
-
- NGAP_REGISTER_GNB_REQ (msg_p).gnb_ip_address.ipv6 = 0;
- NGAP_REGISTER_GNB_REQ (msg_p).gnb_ip_address.ipv4 = 1;
-
- break;
- }
- }
- }
- }
- }
- return 0;
-}
-
static pthread_mutex_t rc_mutex = PTHREAD_MUTEX_INITIALIZER;
static bool rc_done = false;
diff --git a/openair2/GNB_APP/gnb_config.h b/openair2/GNB_APP/gnb_config.h
index c33c6964dc..1f48358e67 100644
--- a/openair2/GNB_APP/gnb_config.h
+++ b/openair2/GNB_APP/gnb_config.h
@@ -44,7 +44,6 @@ void RCconfig_nr_macrlc(configmodule_interface_t *cfg);
void NRRCConfig(void);
gNB_RRC_INST *RCconfig_NRRRC();
-int RCconfig_NR_NG(MessageDef *msg_p, uint32_t i);
int RCconfig_NR_X2(MessageDef *msg_p, uint32_t i);
void wait_f1_setup_response(void);
f1ap_tdd_info_t read_tdd_config(const NR_ServingCellConfigCommon_t *scc);
diff --git a/openair2/GNB_APP/gnb_config_common.c b/openair2/GNB_APP/gnb_config_common.c
new file mode 100644
index 0000000000..ac5e840851
--- /dev/null
+++ b/openair2/GNB_APP/gnb_config_common.c
@@ -0,0 +1,66 @@
+/*
+ * Licensed to the OpenAirInterface (OAI) Software Alliance under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The OpenAirInterface Software Alliance licenses this file to You under
+ * the OAI Public License, Version 1.1 (the "License"); you may not use this file
+ * except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.openairinterface.org/?page_id=698
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *-------------------------------------------------------------------------------
+ * For more information about the OpenAirInterface (OAI) Software Alliance:
+ * contact@openairinterface.org
+ */
+
+#include "openair2/GNB_APP/gnb_config_common.h"
+#include "common/config/config_paramdesc.h"
+#include "common/config/config_userapi.h"
+#include "RRC_nr_paramsvalues.h"
+#include "gnb_paramdef.h"
+#include "sctp_default_values.h"
+
+uint16_t set_snssai_config(nssai_t *nssai, const int max_num_ssi, uint8_t k, uint8_t l)
+{
+ char snssaistr[MAX_OPTNAME_SIZE * 2 + 8];
+ snprintf(snssaistr, sizeof(snssaistr), "%s.[%i].%s.[%i]", GNB_CONFIG_STRING_GNB_LIST, k, GNB_CONFIG_STRING_PLMN_LIST, l);
+ GET_PARAMS_LIST(SNSSAIParamList,
+ SNSSAIParams,
+ GNBSNSSAIPARAMS_DESC,
+ GNB_CONFIG_STRING_SNSSAI_LIST,
+ snssaistr,
+ SNSSAIPARAMS_CHECK);
+ uint16_t num_ssi = SNSSAIParamList.numelt;
+ AssertFatal(num_ssi < max_num_ssi, "S-NSSAI size %d exceeds the max array size %d", num_ssi, max_num_ssi);
+ for (int s = 0; s < num_ssi; ++s) {
+ nssai[s].sst = *SNSSAIParamList.paramarray[s][GNB_SLICE_SERVICE_TYPE_IDX].uptr;
+ // SD is optional
+ // 0xffffff is "no SD", see 23.003 Sec 28.4.2
+ nssai[s].sd = *SNSSAIParamList.paramarray[s][GNB_SLICE_DIFFERENTIATOR_IDX].uptr;
+ AssertFatal(nssai[s].sd <= 0xffffff, "SD cannot be bigger than 0xffffff, but is %d\n", nssai[s].sd);
+ }
+ return num_ssi;
+}
+
+uint8_t set_plmn_config(plmn_id_t *p, uint8_t idx)
+{
+ char gnbpath[MAX_OPTNAME_SIZE * 2 + 8];
+ snprintf(gnbpath, sizeof(gnbpath), "%s.[%i]", GNB_CONFIG_STRING_GNB_LIST, idx);
+ GET_PARAMS_LIST(PLMNParamList, PLMNParams, GNBPLMNPARAMS_DESC, GNB_CONFIG_STRING_PLMN_LIST, gnbpath, PLMNPARAMS_CHECK);
+ uint8_t num_plmn = PLMNParamList.numelt;
+ AssertFatal(num_plmn >= 1 && num_plmn <= 6, "The number of PLMN IDs must be in [1,6], but is %d\n", num_plmn);
+ for (int l = 0; l < num_plmn; ++l) {
+ plmn_id_t *plmn = &p[l];
+ plmn->mcc = *PLMNParamList.paramarray[l][GNB_MOBILE_COUNTRY_CODE_IDX].uptr;
+ plmn->mnc = *PLMNParamList.paramarray[l][GNB_MOBILE_NETWORK_CODE_IDX].uptr;
+ plmn->mnc_digit_length = *PLMNParamList.paramarray[l][GNB_MNC_DIGIT_LENGTH].u8ptr;
+ AssertFatal((plmn->mnc_digit_length == 2) || (plmn->mnc_digit_length == 3), "BAD MNC DIGIT LENGTH %d", plmn->mnc_digit_length);
+ }
+ return num_plmn;
+}
diff --git a/openair2/GNB_APP/gnb_config_common.h b/openair2/GNB_APP/gnb_config_common.h
new file mode 100644
index 0000000000..8317709a78
--- /dev/null
+++ b/openair2/GNB_APP/gnb_config_common.h
@@ -0,0 +1,26 @@
+/*
+ * Licensed to the OpenAirInterface (OAI) Software Alliance under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The OpenAirInterface Software Alliance licenses this file to You under
+ * the OAI Public License, Version 1.1 (the "License"); you may not use this file
+ * except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.openairinterface.org/?page_id=698
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *-------------------------------------------------------------------------------
+ * For more information about the OpenAirInterface (OAI) Software Alliance:
+ * contact@openairinterface.org
+ */
+
+#include
+#include "common/5g_platform_types.h"
+
+uint16_t set_snssai_config(nssai_t *nssai, const int max_num_ssi, uint8_t k, uint8_t l);
+uint8_t set_plmn_config(plmn_id_t *p, uint8_t idx);
diff --git a/openair2/GNB_APP/gnb_config_ng.c b/openair2/GNB_APP/gnb_config_ng.c
new file mode 100644
index 0000000000..632c670def
--- /dev/null
+++ b/openair2/GNB_APP/gnb_config_ng.c
@@ -0,0 +1,162 @@
+/*
+ * Licensed to the OpenAirInterface (OAI) Software Alliance under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The OpenAirInterface Software Alliance licenses this file to You under
+ * the OAI Public License, Version 1.1 (the "License"); you may not use this file
+ * except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.openairinterface.org/?page_id=698
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *-------------------------------------------------------------------------------
+ * For more information about the OpenAirInterface (OAI) Software Alliance:
+ * contact@openairinterface.org
+ */
+
+#include "gnb_config_ng.h"
+#include
+#include "assertions.h"
+#include "common/ran_context.h"
+#include "openair2/GNB_APP/gnb_config_common.h"
+#include "common/config/config_paramdesc.h"
+#include "sctp_default_values.h"
+#include "gnb_paramdef.h"
+
+int RCconfig_NR_NG(MessageDef *msg_p, uint32_t i)
+{
+ int j, k = 0;
+ int gnb_id;
+
+ char *gnb_ipv4_address_for_NGU = NULL;
+ uint32_t gnb_port_for_NGU = 0;
+ char *gnb_ipv4_address_for_S1U = NULL;
+ uint32_t gnb_port_for_S1U = 0;
+
+ GET_PARAMS(GNBSParams, GNBSPARAMS_DESC, NULL);
+ AssertFatal(i < GNBSParams[GNB_ACTIVE_GNBS_IDX].numelt,
+ "Failed to parse config file %s, %uth attribute %s \n",
+ RC.config_file_name,
+ i,
+ GNB_CONFIG_STRING_ACTIVE_GNBS);
+
+ if (GNBSParams[GNB_ACTIVE_GNBS_IDX].numelt > 0) {
+ // Output a list of all gNBs.
+ GET_PARAMS_LIST(GNBParamList, GNBParams, GNBPARAMS_DESC, GNB_CONFIG_STRING_GNB_LIST, NULL);
+ if (GNBParamList.numelt > 0) {
+ for (k = 0; k < GNBParamList.numelt; k++) {
+ if (GNBParamList.paramarray[k][GNB_GNB_ID_IDX].uptr == NULL) {
+ // Calculate a default gNB ID
+ if (IS_SA_MODE(get_softmodem_params())) {
+ uint32_t hash;
+
+ hash = ngap_generate_gNB_id();
+ gnb_id = k + (hash & 0xFFFFFF8);
+ } else {
+ gnb_id = k;
+ }
+ } else {
+ gnb_id = *(GNBParamList.paramarray[k][GNB_GNB_ID_IDX].uptr);
+ }
+
+ // search if in active list
+ for (j = 0; j < GNBSParams[GNB_ACTIVE_GNBS_IDX].numelt; j++) {
+ if (strcmp(GNBSParams[GNB_ACTIVE_GNBS_IDX].strlistptr[j], *(GNBParamList.paramarray[k][GNB_GNB_NAME_IDX].strptr)) == 0) {
+ char aprefix[MAX_OPTNAME_SIZE * 2 + 8];
+ NGAP_REGISTER_GNB_REQ(msg_p).gNB_id = gnb_id;
+
+ if (strcmp(*(GNBParamList.paramarray[k][GNB_CELL_TYPE_IDX].strptr), "CELL_MACRO_GNB") == 0) {
+ NGAP_REGISTER_GNB_REQ(msg_p).cell_type = CELL_MACRO_GNB;
+ } else if (strcmp(*(GNBParamList.paramarray[k][GNB_CELL_TYPE_IDX].strptr), "CELL_HOME_GNB") == 0) {
+ NGAP_REGISTER_GNB_REQ(msg_p).cell_type = CELL_HOME_ENB;
+ } else {
+ AssertFatal(0,
+ "Failed to parse gNB configuration file %s, gnb %u unknown value \"%s\" for cell_type choice: "
+ "CELL_MACRO_GNB or CELL_HOME_GNB !\n",
+ RC.config_file_name,
+ i,
+ *(GNBParamList.paramarray[k][GNB_CELL_TYPE_IDX].strptr));
+ }
+
+ NGAP_REGISTER_GNB_REQ(msg_p).gNB_name = strdup(*(GNBParamList.paramarray[k][GNB_GNB_NAME_IDX].strptr));
+ NGAP_REGISTER_GNB_REQ(msg_p).tac = *GNBParamList.paramarray[k][GNB_TRACKING_AREA_CODE_IDX].uptr;
+ AssertFatal(!GNBParamList.paramarray[k][GNB_MOBILE_COUNTRY_CODE_IDX_OLD].strptr
+ && !GNBParamList.paramarray[k][GNB_MOBILE_NETWORK_CODE_IDX_OLD].strptr,
+ "It seems that you use an old configuration file. Please change the existing\n"
+ " tracking_area_code = \"1\";\n"
+ " mobile_country_code = \"208\";\n"
+ " mobile_network_code = \"93\";\n"
+ "to\n"
+ " tracking_area_code = 1; // no string!!\n"
+ " plmn_list = ( { mcc = 208; mnc = 93; mnc_length = 2; } )\n");
+ // PLMN
+ plmn_id_t p[PLMN_LIST_MAX_SIZE] = {0};
+ NGAP_REGISTER_GNB_REQ(msg_p).num_plmn = set_plmn_config(p, 0);
+ for (int l = 0; l < NGAP_REGISTER_GNB_REQ(msg_p).num_plmn; ++l) {
+ NGAP_REGISTER_GNB_REQ(msg_p).plmn[l].plmn = p[l];
+ // SNSSAI
+ NGAP_REGISTER_GNB_REQ(msg_p).plmn[l].num_nssai =
+ set_snssai_config(NGAP_REGISTER_GNB_REQ(msg_p).plmn[l].s_nssai, 8, k, l);
+ }
+ NGAP_REGISTER_GNB_REQ(msg_p).default_drx = 0;
+ // NG
+ snprintf(aprefix, sizeof(aprefix), "%s.[%i]", GNB_CONFIG_STRING_GNB_LIST, k);
+ GET_PARAMS_LIST(NGParamList, NGParams, GNBNGPARAMS_DESC, GNB_CONFIG_STRING_AMF_IP_ADDRESS, aprefix);
+ NGAP_REGISTER_GNB_REQ(msg_p).nb_amf = 0;
+
+ for (int l = 0; l < NGParamList.numelt; l++) {
+ NGAP_REGISTER_GNB_REQ(msg_p).nb_amf += 1;
+ strcpy(NGAP_REGISTER_GNB_REQ(msg_p).amf_ip_address[l].ipv4_address,
+ *(NGParamList.paramarray[l][GNB_AMF_IPV4_ADDRESS_IDX].strptr));
+ NGAP_REGISTER_GNB_REQ(msg_p).amf_ip_address[l].ipv4 = 1;
+ NGAP_REGISTER_GNB_REQ(msg_p).amf_ip_address[l].ipv6 = 0;
+ /* if no broadcasst_plmn array is defined, fill default values */
+ if (NGAP_REGISTER_GNB_REQ(msg_p).broadcast_plmn_num[l] == 0) {
+ NGAP_REGISTER_GNB_REQ(msg_p).broadcast_plmn_num[l] = NGAP_REGISTER_GNB_REQ(msg_p).num_plmn;
+ for (int el = 0; el < NGAP_REGISTER_GNB_REQ(msg_p).num_plmn; ++el)
+ NGAP_REGISTER_GNB_REQ(msg_p).broadcast_plmn_index[l][el] = el;
+ }
+ }
+
+ // SCTP SETTING
+ NGAP_REGISTER_GNB_REQ(msg_p).sctp_out_streams = SCTP_OUT_STREAMS;
+ NGAP_REGISTER_GNB_REQ(msg_p).sctp_in_streams = SCTP_IN_STREAMS;
+ if (IS_SA_MODE(get_softmodem_params())) {
+ snprintf(aprefix, sizeof(aprefix), "%s.[%d].%s", GNB_CONFIG_STRING_GNB_LIST, k, GNB_CONFIG_STRING_SCTP_CONFIG);
+ GET_PARAMS(SCTPParams, GNBSCTPPARAMS_DESC, aprefix);
+ NGAP_REGISTER_GNB_REQ(msg_p).sctp_in_streams = (uint16_t) * (SCTPParams[GNB_SCTP_INSTREAMS_IDX].uptr);
+ NGAP_REGISTER_GNB_REQ(msg_p).sctp_out_streams = (uint16_t) * (SCTPParams[GNB_SCTP_OUTSTREAMS_IDX].uptr);
+ }
+
+ // NETWORK_INTERFACES
+ snprintf(aprefix,
+ sizeof(aprefix),
+ "%s.[%d].%s",
+ GNB_CONFIG_STRING_GNB_LIST,
+ k,
+ GNB_CONFIG_STRING_NETWORK_INTERFACES_CONFIG);
+ GET_PARAMS(NETParams, GNBNETPARAMS_DESC, aprefix);
+ if (NETParams[GNB_IPV4_ADDRESS_FOR_NG_AMF_IDX].strptr != NULL) {
+ char *cidr = *(NETParams[GNB_IPV4_ADDRESS_FOR_NG_AMF_IDX].strptr);
+ char *save = NULL;
+ char *address = strtok_r(cidr, "/", &save);
+ strcpy(NGAP_REGISTER_GNB_REQ(msg_p).gnb_ip_address.ipv4_address, address);
+ LOG_I(GNB_APP, "Parsed IPv4 address for NG AMF: %s\n", address);
+ }
+
+ NGAP_REGISTER_GNB_REQ(msg_p).gnb_ip_address.ipv6 = 0;
+ NGAP_REGISTER_GNB_REQ(msg_p).gnb_ip_address.ipv4 = 1;
+
+ break;
+ }
+ }
+ }
+ }
+ }
+ return 0;
+}
diff --git a/openair2/GNB_APP/gnb_config_ng.h b/openair2/GNB_APP/gnb_config_ng.h
new file mode 100644
index 0000000000..792f55e940
--- /dev/null
+++ b/openair2/GNB_APP/gnb_config_ng.h
@@ -0,0 +1,29 @@
+/*
+ * Licensed to the OpenAirInterface (OAI) Software Alliance under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The OpenAirInterface Software Alliance licenses this file to You under
+ * the OAI Public License, Version 1.1 (the "License"); you may not use this file
+ * except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.openairinterface.org/?page_id=698
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *-------------------------------------------------------------------------------
+ * For more information about the OpenAirInterface (OAI) Software Alliance:
+ * contact@openairinterface.org
+ */
+
+#ifndef NGAP_GNB_CONFIG_H_
+#define NGAP_GNB_CONFIG_H_
+#include
+#include "intertask_interface.h"
+
+int RCconfig_NR_NG(MessageDef *msg_p, uint32_t i);
+
+#endif /* NGAP_GNB_CONFIG_H_ */
diff --git a/openair2/LAYER2/NR_MAC_UE/config_ue.c b/openair2/LAYER2/NR_MAC_UE/config_ue.c
index 2a5c8e041d..c42406149e 100644
--- a/openair2/LAYER2/NR_MAC_UE/config_ue.c
+++ b/openair2/LAYER2/NR_MAC_UE/config_ue.c
@@ -537,16 +537,15 @@ static void config_common_ue(NR_UE_MAC_INST_t *mac, NR_ServingCellConfigCommon_t
// SSB Table config
if (frequencyInfoDL && frequencyInfoDL->absoluteFrequencySSB) {
- int scs_scaling = 1 << (cfg->ssb_config.scs_common);
- if (frequencyInfoDL->absoluteFrequencyPointA < 600000)
- scs_scaling = scs_scaling * 3;
- if (frequencyInfoDL->absoluteFrequencyPointA > 2016666)
- scs_scaling = scs_scaling >> 2;
- uint32_t absolute_diff = (*frequencyInfoDL->absoluteFrequencySSB - frequencyInfoDL->absoluteFrequencyPointA);
- cfg->ssb_table.ssb_offset_point_a = absolute_diff / (12 * scs_scaling) - 10;
+ cfg->ssb_table.ssb_offset_point_a = get_ssb_offset_to_pointA(*frequencyInfoDL->absoluteFrequencySSB,
+ frequencyInfoDL->absoluteFrequencyPointA,
+ cfg->ssb_config.scs_common,
+ mac->frequency_range);
cfg->ssb_table.ssb_period = *scc->ssb_periodicityServingCell;
// NSA -> take ssb offset from SCS
- cfg->ssb_table.ssb_subcarrier_offset = absolute_diff % (12 * scs_scaling);
+ cfg->ssb_table.ssb_subcarrier_offset = get_ssb_subcarrier_offset(*frequencyInfoDL->absoluteFrequencySSB,
+ frequencyInfoDL->absoluteFrequencyPointA,
+ cfg->ssb_config.scs_common);
cfg->ssb_table.ssb_case = set_ssb_case(*scc->ssbSubcarrierSpacing, mac->nr_band);
}
@@ -717,9 +716,7 @@ static void update_ss(void *ue_ss_in, void *nw_ss_in)
}
}
-static void configure_common_ss_coreset(const NR_UE_MAC_INST_t *mac,
- NR_BWP_PDCCH_t *pdcch,
- NR_PDCCH_ConfigCommon_t *pdcch_ConfigCommon)
+static void configure_common_ss_coreset(NR_BWP_PDCCH_t *pdcch, NR_PDCCH_ConfigCommon_t *pdcch_ConfigCommon)
{
if (!pdcch_ConfigCommon)
return;
@@ -1778,7 +1775,7 @@ static void configure_common_BWP_dl(NR_UE_MAC_INST_t *mac, int bwp_id, NR_BWP_Do
NR_BWP_PDCCH_t *pdcch = &mac->config_BWP_PDCCH[bwp_id];
if (dl_common->pdcch_ConfigCommon) {
if (dl_common->pdcch_ConfigCommon->present == NR_SetupRelease_PDCCH_ConfigCommon_PR_setup)
- configure_common_ss_coreset(mac, pdcch, dl_common->pdcch_ConfigCommon->choice.setup);
+ configure_common_ss_coreset(pdcch, dl_common->pdcch_ConfigCommon->choice.setup);
if (dl_common->pdcch_ConfigCommon->present == NR_SetupRelease_PDCCH_ConfigCommon_PR_release)
release_common_ss_cset(pdcch);
}
@@ -2107,18 +2104,24 @@ static void handle_reconfiguration_with_sync(NR_UE_MAC_INST_t *mac,
configure_common_BWP_dl(mac, bwp_id, scc->downlinkConfigCommon->initialDownlinkBWP);
if (scc->uplinkConfigCommon)
configure_common_BWP_ul(mac, bwp_id, scc->uplinkConfigCommon->initialUplinkBWP);
+
+ // Update PDCCH config as MAC configuration has changed
+ if (IS_SA_MODE(get_softmodem_params()))
+ update_pdcch_config(mac);
}
mac->state = UE_NOT_SYNC_RECONF;
ra->ra_state = nrRA_UE_IDLE;
nr_ue_mac_default_configs(mac);
+ // PHY CONFIG request should be sent, ahead of SYNC request
+ // As SYNC request processes the new config
+ mac->if_module->phy_config_request(&mac->phy_config);
+ mac->phy_config.config_req.ntn_config.params_changed = false;
mac->synch_request.Mod_id = mac->ue_id;
mac->synch_request.CC_id = cc_idP;
mac->synch_request.synch_req.target_Nid_cell = mac->physCellId;
mac->if_module->synch_request(&mac->synch_request);
- mac->if_module->phy_config_request(&mac->phy_config);
- mac->phy_config.config_req.ntn_config.params_changed = false;
}
static void configure_physicalcellgroup(NR_UE_MAC_INST_t *mac,
diff --git a/openair2/LAYER2/NR_MAC_UE/config_ue_sl.c b/openair2/LAYER2/NR_MAC_UE/config_ue_sl.c
index e6d872da81..809ce054f4 100644
--- a/openair2/LAYER2/NR_MAC_UE/config_ue_sl.c
+++ b/openair2/LAYER2/NR_MAC_UE/config_ue_sl.c
@@ -394,8 +394,7 @@ int nr_rrc_mac_config_req_sl_preconfig(module_id_t module_id,
//Copies the values of SSB time allocation from ASN format to MAC context
-static void sl_mac_config_ssb_time_alloc(uint8_t module_id,
- NR_SL_SSB_TimeAllocation_r16_t *sl_SSB_TimeAllocation_r16,
+static void sl_mac_config_ssb_time_alloc(NR_SL_SSB_TimeAllocation_r16_t *sl_SSB_TimeAllocation_r16,
sl_ssb_timealloc_t *ssb_time_alloc)
{
@@ -432,9 +431,7 @@ void nr_rrc_mac_transmit_slss_req(module_id_t module_id,
sl_mac->tx_sl_bch.num_ssb = 0;
sl_mac->tx_sl_bch.ssb_slot = 0;
- sl_mac_config_ssb_time_alloc(module_id,
- ssb_ta,
- &sl_mac->tx_sl_bch.ssb_time_alloc);
+ sl_mac_config_ssb_time_alloc(ssb_ta, &sl_mac->tx_sl_bch.ssb_time_alloc);
LOG_I(NR_MAC,"[UE%d]SL RRC->MAC: TX SLSS REQ SLSS-id:%d, SL-MIB:%x, numssb:%d, offset:%d, interval:%d\n",
module_id, sl_mac->tx_sl_bch.slss_id,
@@ -489,9 +486,7 @@ void nr_rrc_mac_config_req_sl_mib(module_id_t module_id,
sl_mac->rx_sl_bch.num_ssb = 0;
sl_mac->rx_sl_bch.ssb_slot = 0;
- sl_mac_config_ssb_time_alloc(module_id,
- ssb_ta,
- &sl_mac->rx_sl_bch.ssb_time_alloc);
+ sl_mac_config_ssb_time_alloc(ssb_ta, &sl_mac->rx_sl_bch.ssb_time_alloc);
LOG_I(NR_MAC,"[UE%d]SL RRC->MAC: RX SLSS REQ SLSS-id:%d, SL-MIB:%x, numssb:%d, offset:%d, interval:%d\n",
module_id, sl_mac->rx_sl_bch.slss_id,
diff --git a/openair2/LAYER2/NR_MAC_UE/mac_proto.h b/openair2/LAYER2/NR_MAC_UE/mac_proto.h
index 9ee1bfab28..91783894b3 100644
--- a/openair2/LAYER2/NR_MAC_UE/mac_proto.h
+++ b/openair2/LAYER2/NR_MAC_UE/mac_proto.h
@@ -166,11 +166,7 @@ typedef struct {
enum { b_none, b_long, b_short, b_short_trunc, b_long_trunc } type_bsr;
} type_bsr_t;
-int nr_write_ce_ulsch_pdu(uint8_t *mac_ce,
- NR_UE_MAC_INST_t *mac,
- NR_SINGLE_ENTRY_PHR_MAC_CE *power_headroom,
- const type_bsr_t *bsr,
- uint8_t *mac_ce_end);
+int nr_write_ce_ulsch_pdu(uint8_t *mac_ce, NR_SINGLE_ENTRY_PHR_MAC_CE *power_headroom, const type_bsr_t *bsr, uint8_t *mac_ce_end);
void ue_dci_configuration(NR_UE_MAC_INST_t *mac, fapi_nr_dl_config_request_t *dl_config, const frame_t frame, const int slot);
void set_precoding_information_parameters(nfapi_nr_ue_pusch_pdu_t *pusch_config_pdu,
@@ -241,10 +237,9 @@ int get_sum_delta_pucch(NR_UE_MAC_INST_t *mac, int slot, frame_t frame);
void ul_ports_config(NR_UE_MAC_INST_t *mac,
int *n_front_load_symb,
nfapi_nr_ue_pusch_pdu_t *pusch_config_pdu,
- dci_pdu_rel15_t *dci,
- nr_dci_format_t dci_format);
+ dci_pdu_rel15_t *dci);
-bool init_RA(NR_UE_MAC_INST_t *mac, int frame);
+bool init_RA(NR_UE_MAC_INST_t *mac);
/* Random Access */
/* \brief This function schedules the PRACH according to prach_ConfigurationIndex and TS 38.211 tables 6.3.3.2.x
@@ -262,7 +257,7 @@ void configure_csi_resource_mapping(fapi_nr_dl_config_csirs_pdu_rel15_t *csirs_c
bool is_lcid_suspended(NR_UE_MAC_INST_t *mac, int lcid);
void nr_ra_contention_resolution_failed(NR_UE_MAC_INST_t *mac);
-void nr_ra_succeeded(NR_UE_MAC_INST_t *mac, const uint8_t gNB_index, const frame_t frame, const int slot);
+void nr_ra_succeeded(NR_UE_MAC_INST_t *mac, const frame_t frame, const int slot);
void nr_ra_backoff_setting(RA_config_t *ra);
void nr_get_RA_window(NR_UE_MAC_INST_t *mac);
void prepare_msg4_msgb_feedback(NR_UE_MAC_INST_t *mac, int pid, int ack_nack);
@@ -283,7 +278,7 @@ int16_t get_prach_tx_power(NR_UE_MAC_INST_t *mac);
void schedule_RA_after_SR_failure(NR_UE_MAC_INST_t *mac);
void nr_rar_not_successful(NR_UE_MAC_INST_t *mac);
void ra_resource_selection(NR_UE_MAC_INST_t *mac);
-void nr_Msg3_transmitted(NR_UE_MAC_INST_t *mac, uint8_t CC_id, frame_t frameP, slot_t slotP, uint8_t gNB_id);
+void nr_Msg3_transmitted(NR_UE_MAC_INST_t *mac);
void trigger_MAC_UE_RA(NR_UE_MAC_INST_t *mac, dci_pdu_rel15_t *pdcch_order);
void nr_get_Msg3_MsgA_PUSCH_payload(NR_UE_MAC_INST_t *mac, uint8_t *buf, int TBS_max);
void handle_time_alignment_timer_expired(NR_UE_MAC_INST_t *mac);
@@ -377,4 +372,5 @@ void nr_ue_sidelink_scheduler(nr_sidelink_indication_t *sl_ind, NR_UE_MAC_INST_t
NR_SearchSpace_t *get_common_search_space(const NR_UE_MAC_INST_t *mac, const NR_SearchSpaceId_t ss_id);
ssb_ro_preambles_t get_ssb_ro_preambles_4step(struct NR_RACH_ConfigCommon__ssb_perRACH_OccasionAndCB_PreamblesPerSSB *config);
+void update_pdcch_config(NR_UE_MAC_INST_t *mac);
#endif
diff --git a/openair2/LAYER2/NR_MAC_UE/mac_tables.c b/openair2/LAYER2/NR_MAC_UE/mac_tables.c
index a313600609..90cdc26fe4 100644
--- a/openair2/LAYER2/NR_MAC_UE/mac_tables.c
+++ b/openair2/LAYER2/NR_MAC_UE/mac_tables.c
@@ -470,8 +470,7 @@ void set_antenna_port_parameters(fapi_nr_dl_config_dlsch_pdu_rel15_t *dlsch_pdu,
void ul_ports_config(NR_UE_MAC_INST_t *mac,
int *n_front_load_symb,
nfapi_nr_ue_pusch_pdu_t *pusch_config_pdu,
- dci_pdu_rel15_t *dci,
- nr_dci_format_t dci_format)
+ dci_pdu_rel15_t *dci)
{
uint8_t rank = pusch_config_pdu->nrOfLayers;
NR_PUSCH_Config_t *pusch_Config = mac->current_UL_BWP->pusch_Config;
diff --git a/openair2/LAYER2/NR_MAC_UE/nr_ra_procedures.c b/openair2/LAYER2/NR_MAC_UE/nr_ra_procedures.c
index 47277f8a66..a93ad9f8d2 100644
--- a/openair2/LAYER2/NR_MAC_UE/nr_ra_procedures.c
+++ b/openair2/LAYER2/NR_MAC_UE/nr_ra_procedures.c
@@ -819,7 +819,7 @@ static void setup_ra_response_window(NR_UE_MAC_INST_t *mac,
// Random Access procedure initialization as per 5.1.1 and initialization of variables specific
// to Random Access type as specified in clause 5.1.1a (3GPP TS 38.321 version 16.2.1 Release 16)
-bool init_RA(NR_UE_MAC_INST_t *mac, int frame)
+bool init_RA(NR_UE_MAC_INST_t *mac)
{
RA_config_t *ra = &mac->ra;
LOG_D(NR_MAC, "Initialization of RA\n");
@@ -1023,7 +1023,7 @@ bool init_RA(NR_UE_MAC_INST_t *mac, int frame)
return true;
}
-void nr_Msg3_transmitted(NR_UE_MAC_INST_t *mac, uint8_t CC_id, frame_t frameP, slot_t slotP, uint8_t gNB_id)
+void nr_Msg3_transmitted(NR_UE_MAC_INST_t *mac)
{
RA_config_t *ra = &mac->ra;
NR_RACH_ConfigCommon_t *nr_rach_ConfigCommon = mac->current_UL_BWP->rach_ConfigCommon;
@@ -1109,7 +1109,7 @@ void nr_get_Msg3_MsgA_PUSCH_payload(NR_UE_MAC_INST_t *mac, uint8_t *buf, int TBS
// according to section 5 of 3GPP TS 38.321 version 16.2.1 Release 16
// todo:
// - complete handling of received contention-based RA preamble
-void nr_ra_succeeded(NR_UE_MAC_INST_t *mac, const uint8_t gNB_index, const frame_t frame, const int slot)
+void nr_ra_succeeded(NR_UE_MAC_INST_t *mac, const frame_t frame, const int slot)
{
RA_config_t *ra = &mac->ra;
diff --git a/openair2/LAYER2/NR_MAC_UE/nr_ue_dci_configuration.c b/openair2/LAYER2/NR_MAC_UE/nr_ue_dci_configuration.c
index 8dbce0032c..43aab362f3 100644
--- a/openair2/LAYER2/NR_MAC_UE/nr_ue_dci_configuration.c
+++ b/openair2/LAYER2/NR_MAC_UE/nr_ue_dci_configuration.c
@@ -422,6 +422,38 @@ static bool monitor_dci_for_other_SI(NR_UE_MAC_INST_t *mac,
return false;
}
+void update_pdcch_config(NR_UE_MAC_INST_t *mac)
+{
+ int scs = mac->current_DL_BWP ? mac->current_DL_BWP->scs : mac->numerology;
+ const int slots_per_frame = get_slots_per_frame_from_scs(scs);
+ int ssb_sc_offset_norm;
+ if (mac->ssb_subcarrier_offset < 24 && mac->frequency_range == FR1)
+ ssb_sc_offset_norm = mac->ssb_subcarrier_offset >> scs;
+ else
+ ssb_sc_offset_norm = mac->ssb_subcarrier_offset;
+ uint16_t ssb_offset_point_a = (mac->ssb_start_subcarrier - ssb_sc_offset_norm) / 12;
+ int ssb_start_symbol = get_ssb_start_symbol(mac->nr_band, scs, mac->mib_ssb);
+ get_type0_PDCCH_CSS_config_parameters(&mac->type0_PDCCH_CSS_config,
+ mac->mib_frame,
+ mac->mib,
+ slots_per_frame,
+ ssb_sc_offset_norm,
+ ssb_start_symbol,
+ scs,
+ mac->frequency_range,
+ mac->nr_band,
+ 273, // at this point UE in principle doesn't know the grid size (we assume the largest)
+ mac->mib_ssb,
+ 1, // If the UE is not configured with a periodicity, the UE assumes a periodicity of a half frame
+ ssb_offset_point_a);
+ if (mac->search_space_zero == NULL)
+ mac->search_space_zero = calloc(1, sizeof(*mac->search_space_zero));
+ if (mac->coreset0 == NULL)
+ mac->coreset0 = calloc(1, sizeof(*mac->coreset0));
+ fill_coresetZero(mac->coreset0, &mac->type0_PDCCH_CSS_config);
+ fill_searchSpaceZero(mac->search_space_zero, slots_per_frame, &mac->type0_PDCCH_CSS_config);
+}
+
void ue_dci_configuration(NR_UE_MAC_INST_t *mac, fapi_nr_dl_config_request_t *dl_config, const frame_t frame, const int slot)
{
const NR_UE_DL_BWP_t *current_DL_BWP = mac->current_DL_BWP;
@@ -430,37 +462,14 @@ void ue_dci_configuration(NR_UE_MAC_INST_t *mac, fapi_nr_dl_config_request_t *dl
int scs = current_DL_BWP ? current_DL_BWP->scs : mac->numerology;
const int slots_per_frame = get_slots_per_frame_from_scs(scs);
if (mac->get_sib1) {
- int ssb_sc_offset_norm;
- if (mac->ssb_subcarrier_offset < 24 && mac->frequency_range == FR1)
- ssb_sc_offset_norm = mac->ssb_subcarrier_offset >> scs;
- else
- ssb_sc_offset_norm = mac->ssb_subcarrier_offset;
- uint16_t ssb_offset_point_a = (mac->ssb_start_subcarrier - ssb_sc_offset_norm) / 12;
- int ssb_start_symbol = get_ssb_start_symbol(mac->nr_band, scs, mac->mib_ssb);
- get_type0_PDCCH_CSS_config_parameters(&mac->type0_PDCCH_CSS_config,
- mac->mib_frame,
- mac->mib,
- slots_per_frame,
- ssb_sc_offset_norm,
- ssb_start_symbol,
- scs,
- mac->frequency_range,
- mac->nr_band,
- 273, // at this point UE in principle doesn't know the grid size (we assume the largest)
- mac->mib_ssb,
- 1, // If the UE is not configured with a periodicity, the UE assumes a periodicity of a half frame
- ssb_offset_point_a);
- if (mac->search_space_zero == NULL)
- mac->search_space_zero = calloc(1, sizeof(*mac->search_space_zero));
- if (mac->coreset0 == NULL)
- mac->coreset0 = calloc(1, sizeof(*mac->coreset0));
- fill_coresetZero(mac->coreset0, &mac->type0_PDCCH_CSS_config);
- fill_searchSpaceZero(mac->search_space_zero, slots_per_frame, &mac->type0_PDCCH_CSS_config);
- if (is_ss_monitor_occasion(frame, slot, slots_per_frame, mac->search_space_zero)) {
+ update_pdcch_config(mac);
+ bool is_occasion = is_ss_monitor_occasion(frame, slot, slots_per_frame, mac->search_space_zero);
+ if (is_occasion) {
LOG_D(NR_MAC_DCI, "Monitoring DCI for SIB1 in frame %d slot %d\n", frame, slot);
config_dci_pdu(mac, dl_config, TYPE_SI_RNTI_, slot, mac->search_space_zero);
}
}
+
for (int i = 0; i < MAX_SI_GROUPS; i++) {
if (!mac->get_otherSI[i])
continue;
diff --git a/openair2/LAYER2/NR_MAC_UE/nr_ue_power_procedures.c b/openair2/LAYER2/NR_MAC_UE/nr_ue_power_procedures.c
index a409cbe653..668efba2f5 100644
--- a/openair2/LAYER2/NR_MAC_UE/nr_ue_power_procedures.c
+++ b/openair2/LAYER2/NR_MAC_UE/nr_ue_power_procedures.c
@@ -59,7 +59,7 @@ static const int nb_symbols_excluding_dmrs[11][2][2]
};
// ∆MPR according to Table 6.2.2-3 38.101-1
-static float get_delta_mpr(uint16_t nr_band, frame_type_t frame_type, int scs, int channel_bandwidth, int n_prbs, int start_prb, int power_class)
+static float get_delta_mpr(uint16_t nr_band, frame_type_t frame_type, int scs, int channel_bandwidth, int power_class)
{
if (compare_relative_ul_channel_bw(nr_band, scs, channel_bandwidth, frame_type)) {
if (power_class == 3) {
@@ -191,7 +191,7 @@ float nr_get_Pcmax(int p_Max,
int delta_TC = 0;
float MPR = get_mpr(Qm, N_RB_UL, is_transform_precoding, n_prbs, start_prb, power_class);
- float delta_MPR = get_delta_mpr(nr_band, frame_type, scs, channel_bandwidth, n_prbs, start_prb, power_class);
+ float delta_MPR = get_delta_mpr(nr_band, frame_type, scs, channel_bandwidth, power_class);
int A_MPR = 0; // TODO too complicated to implement for now (see 6.2.3 in 38.101-1)
int delta_rx_SRS = 0; // TODO for SRS
int P_MPR = 0; // to ensure compliance with applicable electromagnetic energy absorption requirements
diff --git a/openair2/LAYER2/NR_MAC_UE/nr_ue_procedures.c b/openair2/LAYER2/NR_MAC_UE/nr_ue_procedures.c
index 52ed7580c6..2c3ee539fc 100644
--- a/openair2/LAYER2/NR_MAC_UE/nr_ue_procedures.c
+++ b/openair2/LAYER2/NR_MAC_UE/nr_ue_procedures.c
@@ -3296,7 +3296,7 @@ static void nr_ue_process_rar(NR_UE_MAC_INST_t *mac, nr_downlink_indication_t *d
rar = (NR_MAC_RAR *) (dlsch_buffer + n_subheaders + (n_subPDUs - 1) * sizeof(NR_MAC_RAR));
handle_rar_reception(mac, rar, frame, slot);
if (ra->cfra)
- nr_ra_succeeded(mac, dl_info->gNB_index, frame, slot);
+ nr_ra_succeeded(mac, frame, slot);
break;
}
if (rarh->E == 0) {
@@ -3818,12 +3818,7 @@ static bool check_ra_contention_resolution(const uint8_t *pdu, const uint8_t *co
return true;
}
-static int nr_ue_validate_successrar(uint8_t *pduP,
- int32_t pdu_len,
- NR_UE_MAC_INST_t *mac,
- uint8_t gNB_index,
- frame_t frameP,
- int slot)
+static int nr_ue_validate_successrar(uint8_t *pduP, int32_t pdu_len, NR_UE_MAC_INST_t *mac, frame_t frameP, int slot)
{
// TS 38.321 - Figure 6.1.5a-1: BI MAC subheader
// TS 38.321 - Figure 6.1.5a-3: SuccessRAR MAC subheader
@@ -3885,7 +3880,7 @@ static int nr_ue_validate_successrar(uint8_t *pduP,
if (ra->RA_active && ra_success) {
nr_timer_stop(&ra->response_window_timer);
- nr_ra_succeeded(mac, gNB_index, frameP, slot);
+ nr_ra_succeeded(mac, frameP, slot);
} else if (!ra_success) {
nr_ra_backoff_setting(ra);
}
@@ -3943,7 +3938,6 @@ static void nr_ue_process_mac_pdu(NR_UE_MAC_INST_t *mac, nr_downlink_indication_
fapi_nr_pdsch_pdu_t *pdsch_pdu = &(dl_info->rx_ind->rx_indication_body + pdu_id)->pdsch_pdu;
uint8_t *pduP = pdsch_pdu->pdu;
int32_t pdu_len = (int32_t)pdsch_pdu->pdu_length;
- uint8_t gNB_index = dl_info->gNB_index;
uint8_t CC_id = dl_info->cc_id;
uint8_t done = 0;
RA_config_t *ra = &mac->ra;
@@ -3963,7 +3957,7 @@ static void nr_ue_process_mac_pdu(NR_UE_MAC_INST_t *mac, nr_downlink_indication_
dl_info->rx_ind->number_pdus);
if (ra->ra_type == RA_2_STEP && ra->ra_state == nrRA_WAIT_MSGB) {
- int n = nr_ue_validate_successrar(pduP, pdu_len, mac, gNB_index, frameP, slot);
+ int n = nr_ue_validate_successrar(pduP, pdu_len, mac, frameP, slot);
pduP += n;
pdu_len -= n;
}
@@ -4095,7 +4089,7 @@ static void nr_ue_process_mac_pdu(NR_UE_MAC_INST_t *mac, nr_downlink_indication_
bool ra_success = check_ra_contention_resolution(&pduP[1], ra->cont_res_id);
if (ra->RA_active && ra_success) {
- nr_ra_succeeded(mac, gNB_index, frameP, slot);
+ nr_ra_succeeded(mac, frameP, slot);
} else if (!ra_success) {
// consider this Contention Resolution not successful and discard the successfully decoded MAC PDU
nr_ra_contention_resolution_failed(mac);
@@ -4135,14 +4129,9 @@ static void nr_ue_process_mac_pdu(NR_UE_MAC_INST_t *mac, nr_downlink_indication_
* Function: generating MAC CEs (MAC CE and subheader) for the ULSCH PDU
* Parameters:
* @mac_ce pointer to the MAC sub-PDUs including the MAC CEs
- * @mac pointer to the MAC instance
* Return: number of written bytes
*/
-int nr_write_ce_ulsch_pdu(uint8_t *mac_ce,
- NR_UE_MAC_INST_t *mac,
- NR_SINGLE_ENTRY_PHR_MAC_CE *power_headroom,
- const type_bsr_t *bsr,
- uint8_t *mac_ce_end)
+int nr_write_ce_ulsch_pdu(uint8_t *mac_ce, NR_SINGLE_ENTRY_PHR_MAC_CE *power_headroom, const type_bsr_t *bsr, uint8_t *mac_ce_end)
{
uint8_t *pdu = mac_ce;
if (power_headroom) {
diff --git a/openair2/LAYER2/NR_MAC_UE/nr_ue_scheduler.c b/openair2/LAYER2/NR_MAC_UE/nr_ue_scheduler.c
index d06c8302a6..cc933b50e4 100644
--- a/openair2/LAYER2/NR_MAC_UE/nr_ue_scheduler.c
+++ b/openair2/LAYER2/NR_MAC_UE/nr_ue_scheduler.c
@@ -324,7 +324,7 @@ fapi_nr_dl_config_request_t *get_dl_config_request(NR_UE_MAC_INST_t *mac, int sl
return &mac->dl_config_request[slot];
}
-void ul_layers_config(NR_UE_MAC_INST_t *mac, nfapi_nr_ue_pusch_pdu_t *pusch_config_pdu, dci_pdu_rel15_t *dci, nr_dci_format_t dci_format)
+static void ul_layers_config(NR_UE_MAC_INST_t *mac, nfapi_nr_ue_pusch_pdu_t *pusch_config_pdu, dci_pdu_rel15_t *dci)
{
NR_UE_UL_BWP_t *current_UL_BWP = mac->current_UL_BWP;
NR_SRS_Config_t *srs_config = current_UL_BWP->srs_Config;
@@ -583,8 +583,8 @@ int nr_config_pusch_pdu(NR_UE_MAC_INST_t *mac,
else
pusch_config_pdu->num_dmrs_cdm_grps_no_data = 2;
} else if (dci_format == NR_UL_DCI_FORMAT_0_1) {
- ul_layers_config(mac, pusch_config_pdu, dci, dci_format);
- ul_ports_config(mac, &dmrslength, pusch_config_pdu, dci, dci_format);
+ ul_layers_config(mac, pusch_config_pdu, dci);
+ ul_ports_config(mac, &dmrslength, pusch_config_pdu, dci);
} else {
LOG_E(NR_MAC, "UL grant from DCI format %d is not handled...\n", dci_format);
mac->stats.bad_dci++;
@@ -1459,7 +1459,7 @@ static void nr_update_sr(NR_UE_MAC_INST_t *mac, bool BSRsent)
}
}
-static void nr_update_rlc_buffers_status(NR_UE_MAC_INST_t *mac, frame_t frameP, slot_t slotP, uint8_t gNB_index)
+static void nr_update_rlc_buffers_status(NR_UE_MAC_INST_t *mac, frame_t frameP, slot_t slotP)
{
for (int i = 0; i < mac->lc_ordered_list.count; i++) {
nr_lcordered_info_t *lc_info = mac->lc_ordered_list.array[i];
@@ -1987,10 +1987,8 @@ static uint8_t nr_locate_BsrIndexByBufferSize(int size, int value)
}
static void nr_ue_get_sdu_mac_ce_pre(NR_UE_MAC_INST_t *mac,
- int CC_id,
frame_t frame,
slot_t slot,
- uint8_t gNB_index,
uint8_t *ulsch_buffer,
uint32_t buflen,
uint32_t *LCG_bytes,
@@ -2172,8 +2170,7 @@ static void nr_ue_get_sdu_mac_ce_post(NR_UE_MAC_INST_t *mac,
}
}
- int size =
- nr_write_ce_ulsch_pdu(mac_ce_p->cur_ptr, mac, mac_ce_p->phr_len ? &mac_ce_p->phr : NULL, &mac_ce_p->bsr, mac_ce_p->pdu_end);
+ int size = nr_write_ce_ulsch_pdu(mac_ce_p->cur_ptr, mac_ce_p->phr_len ? &mac_ce_p->phr : NULL, &mac_ce_p->bsr, mac_ce_p->pdu_end);
LOG_D(NR_MAC, "Added %d bytes of BSR\n", size);
mac_ce_p->cur_ptr += size;
}
@@ -2272,7 +2269,6 @@ static uint select_logical_channels(NR_UE_MAC_INST_t *mac, nr_lcordered_info_t *
static bool fill_mac_sdu(NR_UE_MAC_INST_t *mac,
frame_t frame,
slot_t slot,
- uint8_t gNB_index,
int lcid,
uint count_same_priority_lcids,
uint32_t buflen_ep,
@@ -2406,18 +2402,14 @@ static bool fill_mac_sdu(NR_UE_MAC_INST_t *mac,
to generate the complete MAC PDU with sub-headers and MAC CEs according to ULSCH MAC PDU generation (6.1.2 TS 38.321)
the selected sub-header for the payload sub-PDUs is NR_MAC_SUBHEADER_LONG
* @module_idP Module ID
- * @CC_id Component Carrier index
* @frame current UL frame
* @slot current UL slot
- * @gNB_index gNB index
* @ulsch_buffer Pointer to ULSCH PDU
* @buflen TBS
*/
static uint8_t nr_ue_get_sdu(NR_UE_MAC_INST_t *mac,
- int CC_id,
frame_t frame,
slot_t slot,
- uint8_t gNB_index,
uint8_t *ulsch_buffer,
const uint32_t buflen,
int tx_power,
@@ -2436,7 +2428,7 @@ static uint8_t nr_ue_get_sdu(NR_UE_MAC_INST_t *mac,
uint32_t LCG_bytes[NR_MAX_NUM_LCGID] = {0};
nr_update_bsr(mac, LCG_bytes);
- nr_ue_get_sdu_mac_ce_pre(mac, CC_id, frame, slot, gNB_index, ulsch_buffer, buflen, LCG_bytes, &mac_ce_info, tx_power, P_CMAX);
+ nr_ue_get_sdu_mac_ce_pre(mac, frame, slot, ulsch_buffer, buflen, LCG_bytes, &mac_ce_info, tx_power, P_CMAX);
LOG_D(NR_MAC,
"[UE %d] [%d.%d] process UL transport block with size TBS = %d bytes, number of existing LCids %d \n",
@@ -2510,7 +2502,6 @@ static uint8_t nr_ue_get_sdu(NR_UE_MAC_INST_t *mac,
if (!fill_mac_sdu(mac,
frame,
slot,
- gNB_index,
lcid,
count_same_priority_lcids,
buflen_ep,
@@ -2563,12 +2554,10 @@ void nr_ue_ul_scheduler(NR_UE_MAC_INST_t *mac, nr_uplink_indication_t *ul_info)
int cc_id = ul_info->cc_id;
frame_t frame_tx = ul_info->frame;
slot_t slot_tx = ul_info->slot;
- uint32_t gNB_index = ul_info->gNB_index;
-
RA_config_t *ra = &mac->ra;
if (mac->state == UE_PERFORMING_RA && ra->ra_state == nrRA_UE_IDLE) {
- init_RA(mac, frame_tx);
+ init_RA(mac);
// perform the Random Access Resource selection procedure (see clause 5.1.2 and .2a)
ra_resource_selection(mac);
}
@@ -2579,7 +2568,7 @@ void nr_ue_ul_scheduler(NR_UE_MAC_INST_t *mac, nr_uplink_indication_t *ul_info)
bool BSRsent = false;
if (mac->state == UE_CONNECTED) {
nr_ue_periodic_srs_scheduling(mac, frame_tx, slot_tx);
- nr_update_rlc_buffers_status(mac, frame_tx, slot_tx, gNB_index);
+ nr_update_rlc_buffers_status(mac, frame_tx, slot_tx);
}
// Schedule ULSCH only if the current frame and slot match those in ul_config_req
@@ -2637,7 +2626,7 @@ void nr_ue_ul_scheduler(NR_UE_MAC_INST_t *mac, nr_uplink_indication_t *ul_info)
pdu->rb_size,
pdu->rb_start);
- nr_ue_get_sdu(mac, cc_id, frame_tx, slot_tx, gNB_index, ulsch_input_buffer, TBS_bytes, tx_power, P_CMAX, &BSRsent);
+ nr_ue_get_sdu(mac, frame_tx, slot_tx, ulsch_input_buffer, TBS_bytes, tx_power, P_CMAX, &BSRsent);
pdu->tx_request_body.fapiTxPdu = ulsch_input_buffer;
pdu->tx_request_body.pdu_length = TBS_bytes;
number_of_pdus++;
@@ -2654,11 +2643,11 @@ void nr_ue_ul_scheduler(NR_UE_MAC_INST_t *mac, nr_uplink_indication_t *ul_info)
LOG_I(NR_MAC, "[RAPROC][%d.%d] RA-Msg3 retransmitted\n", frame_tx, slot_tx);
// 38.321 restart the ra-ContentionResolutionTimer at each HARQ retransmission in the first symbol after the end of the Msg3
// transmission
- nr_Msg3_transmitted(mac, cc_id, frame_tx, slot_tx, gNB_index);
+ nr_Msg3_transmitted(mac);
}
if (ra->ra_state == nrRA_WAIT_RAR && !ra->cfra) {
LOG_A(NR_MAC, "[RAPROC][%d.%d] RA-Msg3 transmitted\n", frame_tx, slot_tx);
- nr_Msg3_transmitted(mac, cc_id, frame_tx, slot_tx, gNB_index);
+ nr_Msg3_transmitted(mac);
}
if (ra->ra_state == nrRA_WAIT_MSGB && !ra->cfra) {
LOG_A(NR_MAC, "[RAPROC][%d.%d] RA-MsgA-PUSCH transmitted\n", frame_tx, slot_tx);
diff --git a/openair2/LAYER2/NR_MAC_UE/tests/test_nr_ue_ra_procedures.cpp b/openair2/LAYER2/NR_MAC_UE/tests/test_nr_ue_ra_procedures.cpp
index f7fc520d06..cdbb3e9e3e 100644
--- a/openair2/LAYER2/NR_MAC_UE/tests/test_nr_ue_ra_procedures.cpp
+++ b/openair2/LAYER2/NR_MAC_UE/tests/test_nr_ue_ra_procedures.cpp
@@ -101,9 +101,8 @@ TEST(test_init_ra, four_step_cbra)
mac.frame_structure.frame_type = TDD;
mac.frame_structure.numb_slots_frame = 20;
mac.frequency_range = FR1;
- int frame = 151;
- init_RA(&mac, frame);
+ init_RA(&mac);
EXPECT_EQ(mac.ra.ra_type, RA_4_STEP);
EXPECT_EQ(mac.state, UE_PERFORMING_RA);
@@ -135,14 +134,13 @@ TEST(test_init_ra, four_step_cfra)
mac.frame_structure.frame_type = TDD;
mac.frame_structure.numb_slots_frame = 20;
mac.frequency_range = FR1;
- int frame = 151;
NR_RACH_ConfigDedicated_t rach_ConfigDedicated = {0};
NR_CFRA_t cfra;
rach_ConfigDedicated.cfra = &cfra;
ra->rach_ConfigDedicated = &rach_ConfigDedicated;
- init_RA(&mac, frame);
+ init_RA(&mac);
EXPECT_EQ(mac.ra.ra_type, RA_4_STEP);
EXPECT_EQ(mac.state, UE_PERFORMING_RA);
diff --git a/openair2/LAYER2/NR_MAC_gNB/nr_mac_gNB.h b/openair2/LAYER2/NR_MAC_gNB/nr_mac_gNB.h
index 40ed4c6a50..adbba9c772 100644
--- a/openair2/LAYER2/NR_MAC_gNB/nr_mac_gNB.h
+++ b/openair2/LAYER2/NR_MAC_gNB/nr_mac_gNB.h
@@ -184,7 +184,7 @@ typedef enum {
SSB_SINR,
} nr_config_report_type_t;
-typedef struct nr_mac_config_t {
+typedef struct nr_mac_config_s {
nr_pdsch_AntennaPorts_t pdsch_AntennaPorts;
int pusch_AntennaPorts;
int minRXTXTIME;
@@ -855,7 +855,7 @@ typedef struct gNB_MAC_INST_s gNB_MAC_INST;
typedef void (*nr_pp_impl_dl)(gNB_MAC_INST *nr_mac, post_process_pdsch_t *pp_pdsch);
typedef void (*nr_pp_impl_ul)(gNB_MAC_INST *nr_mac, post_process_pusch_t *pp_pusch);
-typedef struct f1_config_t {
+typedef struct {
f1ap_setup_req_t *setup_req;
f1ap_setup_resp_t *setup_resp;
uint32_t gnb_id; // associated gNB's ID, not used in DU itself
diff --git a/openair2/LAYER2/NR_MAC_gNB/nr_radio_config.h b/openair2/LAYER2/NR_MAC_gNB/nr_radio_config.h
index edf53f24f7..dc10904425 100644
--- a/openair2/LAYER2/NR_MAC_gNB/nr_radio_config.h
+++ b/openair2/LAYER2/NR_MAC_gNB/nr_radio_config.h
@@ -38,13 +38,8 @@ struct NR_MeasurementTimingConfiguration;
struct NR_PDSCH_TimeDomainResourceAllocationList;
// forward declaration of MAC configuration parameters, definition is included in C file
-struct nr_mac_config_t;
-typedef struct nr_mac_config_t nr_mac_config_t;
-
-struct nr_mac_timers;
+typedef struct nr_mac_config_s nr_mac_config_t;
typedef struct nr_mac_timers nr_mac_timers_t;
-
-struct measgap_config;
typedef struct measgap_config measgap_config_t;
void nr_rrc_config_dl_tda(struct NR_PDSCH_TimeDomainResourceAllocationList *pdsch_TimeDomainAllocationList,
diff --git a/openair2/LAYER2/nr_pdcp/nr_pdcp_entity.c b/openair2/LAYER2/nr_pdcp/nr_pdcp_entity.c
index 25081891d3..42e09308f2 100644
--- a/openair2/LAYER2/nr_pdcp/nr_pdcp_entity.c
+++ b/openair2/LAYER2/nr_pdcp/nr_pdcp_entity.c
@@ -303,7 +303,7 @@ static int nr_pdcp_entity_process_sdu(nr_pdcp_entity_t *entity,
return header_size + size + integrity_size;
}
-static bool nr_pdcp_entity_check_integrity(struct nr_pdcp_entity_t *entity,
+static bool nr_pdcp_entity_check_integrity(nr_pdcp_entity_t *entity,
const uint8_t *buffer,
int buffer_size,
const nr_pdcp_integrity_data_t *msg_integrity)
@@ -329,8 +329,7 @@ static bool nr_pdcp_entity_check_integrity(struct nr_pdcp_entity_t *entity,
}
/* may be called several times, take care to clean previous settings */
-static void nr_pdcp_entity_set_security(struct nr_pdcp_entity_t *entity,
- const nr_pdcp_entity_security_keys_and_algos_t *parameters)
+static void nr_pdcp_entity_set_security(nr_pdcp_entity_t *entity, const nr_pdcp_entity_security_keys_and_algos_t *parameters)
{
if (parameters->integrity_algorithm != -1) {
entity->security_keys_and_algos.integrity_algorithm = parameters->integrity_algorithm;
@@ -453,7 +452,7 @@ static void check_t_reordering(nr_pdcp_entity_t *entity)
}
}
-static void nr_pdcp_entity_set_time(struct nr_pdcp_entity_t *entity, uint64_t now)
+static void nr_pdcp_entity_set_time(nr_pdcp_entity_t *entity, uint64_t now)
{
entity->t_current = now;
@@ -697,12 +696,13 @@ nr_pdcp_entity_t *new_nr_pdcp_entity(
int pdusession_id,
bool has_sdap_rx,
bool has_sdap_tx,
- void (*deliver_sdu)(void *deliver_sdu_data, struct nr_pdcp_entity_t *entity,
- char *buf, int size,
+ void (*deliver_sdu)(void *deliver_sdu_data,
+ nr_pdcp_entity_t *entity,
+ char *buf,
+ int size,
const nr_pdcp_integrity_data_t *msg_integrity),
void *deliver_sdu_data,
- void (*deliver_pdu)(void *deliver_pdu_data, ue_id_t ue_id, int rb_id,
- char *buf, int size, int sdu_id),
+ void (*deliver_pdu)(void *deliver_pdu_data, ue_id_t ue_id, int rb_id, char *buf, int size, int sdu_id),
void *deliver_pdu_data,
int sn_size,
int t_reordering,
diff --git a/openair2/LAYER2/nr_pdcp/nr_pdcp_entity.h b/openair2/LAYER2/nr_pdcp/nr_pdcp_entity.h
index 84ecce8997..338279aec9 100644
--- a/openair2/LAYER2/nr_pdcp/nr_pdcp_entity.h
+++ b/openair2/LAYER2/nr_pdcp/nr_pdcp_entity.h
@@ -92,36 +92,36 @@ typedef struct {
uint8_t mode; /* 0: PDCP AM, 1: PDCP UM, 2: PDCP TM */
} nr_pdcp_statistics_t;
-typedef struct nr_pdcp_entity_t {
+typedef struct nr_pdcp_entity_s {
nr_pdcp_entity_type_t type;
/* functions provided by the PDCP module */
- void (*recv_pdu)(struct nr_pdcp_entity_t *entity, char *buffer, int size);
- int (*process_sdu)(struct nr_pdcp_entity_t *entity, char *buffer, int size,
- int sdu_id, char *pdu_buffer, int pdu_max_size);
- void (*delete_entity)(struct nr_pdcp_entity_t *entity);
- void (*release_entity)(struct nr_pdcp_entity_t *entity);
- void (*suspend_entity)(struct nr_pdcp_entity_t *entity);
- void (*reestablish_entity)(struct nr_pdcp_entity_t *entity,
- const nr_pdcp_entity_security_keys_and_algos_t *parameters);
- void (*get_stats)(struct nr_pdcp_entity_t *entity, nr_pdcp_statistics_t *out);
+ void (*recv_pdu)(struct nr_pdcp_entity_s *entity, char *buffer, int size);
+ int (*process_sdu)(struct nr_pdcp_entity_s *entity, char *buffer, int size, int sdu_id, char *pdu_buffer, int pdu_max_size);
+ void (*delete_entity)(struct nr_pdcp_entity_s *entity);
+ void (*release_entity)(struct nr_pdcp_entity_s *entity);
+ void (*suspend_entity)(struct nr_pdcp_entity_s *entity);
+ void (*reestablish_entity)(struct nr_pdcp_entity_s *entity, const nr_pdcp_entity_security_keys_and_algos_t *parameters);
+ void (*get_stats)(struct nr_pdcp_entity_s *entity, nr_pdcp_statistics_t *out);
/* set_security: pass -1 to parameters->integrity_algorithm / parameters->ciphering_algorithm
* to keep the corresponding current algorithm and key
*/
- void (*set_security)(struct nr_pdcp_entity_t *entity,
- const nr_pdcp_entity_security_keys_and_algos_t *parameters);
+ void (*set_security)(struct nr_pdcp_entity_s *entity, const nr_pdcp_entity_security_keys_and_algos_t *parameters);
/* check_integrity is used by RRC */
- bool (*check_integrity)(struct nr_pdcp_entity_t *entity,
- const uint8_t *buffer, int buffer_length,
+ bool (*check_integrity)(struct nr_pdcp_entity_s *entity,
+ const uint8_t *buffer,
+ int buffer_length,
const nr_pdcp_integrity_data_t *msg_integrity);
- void (*set_time)(struct nr_pdcp_entity_t *entity, uint64_t now);
+ void (*set_time)(struct nr_pdcp_entity_s *entity, uint64_t now);
/* callbacks provided to the PDCP module */
- void (*deliver_sdu)(void *deliver_sdu_data, struct nr_pdcp_entity_t *entity,
- char *buf, int size,
+ void (*deliver_sdu)(void *deliver_sdu_data,
+ struct nr_pdcp_entity_s *entity,
+ char *buf,
+ int size,
const nr_pdcp_integrity_data_t *msg_integrity);
void *deliver_sdu_data;
void (*deliver_pdu)(void *deliver_pdu_data, ue_id_t ue_id, int rb_id,
@@ -186,10 +186,10 @@ typedef struct nr_pdcp_entity_t {
bool entity_suspended;
/* PDCP Count API */
- nr_pdcp_count_t (*get_pdcp_count_dl)(struct nr_pdcp_entity_t *entity);
- nr_pdcp_count_t (*get_pdcp_count_ul)(struct nr_pdcp_entity_t *entity);
- void (*set_pdcp_count_dl)(struct nr_pdcp_entity_t *entity, nr_pdcp_count_t count, int sn_size);
- void (*set_pdcp_count_ul)(struct nr_pdcp_entity_t *entity, nr_pdcp_count_t count, int sn_size);
+ nr_pdcp_count_t (*get_pdcp_count_dl)(struct nr_pdcp_entity_s *entity);
+ nr_pdcp_count_t (*get_pdcp_count_ul)(struct nr_pdcp_entity_s *entity);
+ void (*set_pdcp_count_dl)(struct nr_pdcp_entity_s *entity, nr_pdcp_count_t count, int sn_size);
+ void (*set_pdcp_count_ul)(struct nr_pdcp_entity_s *entity, nr_pdcp_count_t count, int sn_size);
} nr_pdcp_entity_t;
@@ -200,12 +200,13 @@ nr_pdcp_entity_t *new_nr_pdcp_entity(
int pdusession_id,
bool has_sdap_rx,
bool has_sdap_tx,
- void (*deliver_sdu)(void *deliver_sdu_data, struct nr_pdcp_entity_t *entity,
- char *buf, int size,
+ void (*deliver_sdu)(void *deliver_sdu_data,
+ struct nr_pdcp_entity_s *entity,
+ char *buf,
+ int size,
const nr_pdcp_integrity_data_t *msg_integrity),
void *deliver_sdu_data,
- void (*deliver_pdu)(void *deliver_pdu_data, ue_id_t ue_id, int rb_id,
- char *buf, int size, int sdu_id),
+ void (*deliver_pdu)(void *deliver_pdu_data, ue_id_t ue_id, int rb_id, char *buf, int size, int sdu_id),
void *deliver_pdu_data,
int sn_size,
int t_reordering,
diff --git a/openair2/LAYER2/nr_rlc/nr_rlc_entity.c b/openair2/LAYER2/nr_rlc/nr_rlc_entity.c
index e452981357..2bb407ad01 100644
--- a/openair2/LAYER2/nr_rlc/nr_rlc_entity.c
+++ b/openair2/LAYER2/nr_rlc/nr_rlc_entity.c
@@ -71,26 +71,23 @@ static void nr_rlc_entity_get_stats(
out->txsdu_avg_time_to_tx = 0;
}
-nr_rlc_entity_t *new_nr_rlc_entity_am(
- int rx_maxsize,
- int tx_maxsize,
- void (*deliver_sdu)(void *deliver_sdu_data, struct nr_rlc_entity_t *entity,
- char *buf, int size),
- void *deliver_sdu_data,
- void (*sdu_successful_delivery)(void *sdu_successful_delivery_data,
- struct nr_rlc_entity_t *entity,
- int sdu_id),
- void *sdu_successful_delivery_data,
- void (*max_retx_reached)(void *max_retx_reached_data,
- struct nr_rlc_entity_t *entity),
- void *max_retx_reached_data,
- int t_poll_retransmit,
- int t_reassembly,
- int t_status_prohibit,
- int poll_pdu,
- int poll_byte,
- int max_retx_threshold,
- int sn_field_length)
+nr_rlc_entity_t *new_nr_rlc_entity_am(int rx_maxsize,
+ int tx_maxsize,
+ void (*deliver_sdu)(void *deliver_sdu_data, nr_rlc_entity_t *entity, char *buf, int size),
+ void *deliver_sdu_data,
+ void (*sdu_successful_delivery)(void *sdu_successful_delivery_data,
+ nr_rlc_entity_t *entity,
+ int sdu_id),
+ void *sdu_successful_delivery_data,
+ void (*max_retx_reached)(void *max_retx_reached_data, nr_rlc_entity_t *entity),
+ void *max_retx_reached_data,
+ int t_poll_retransmit,
+ int t_reassembly,
+ int t_status_prohibit,
+ int poll_pdu,
+ int poll_byte,
+ int max_retx_threshold,
+ int sn_field_length)
{
nr_rlc_entity_am_t *ret;
@@ -150,14 +147,12 @@ nr_rlc_entity_t *new_nr_rlc_entity_am(
return (nr_rlc_entity_t *)ret;
}
-nr_rlc_entity_t *new_nr_rlc_entity_um(
- int rx_maxsize,
- int tx_maxsize,
- void (*deliver_sdu)(void *deliver_sdu_data, struct nr_rlc_entity_t *entity,
- char *buf, int size),
- void *deliver_sdu_data,
- int t_reassembly,
- int sn_field_length)
+nr_rlc_entity_t *new_nr_rlc_entity_um(int rx_maxsize,
+ int tx_maxsize,
+ void (*deliver_sdu)(void *deliver_sdu_data, nr_rlc_entity_t *entity, char *buf, int size),
+ void *deliver_sdu_data,
+ int t_reassembly,
+ int sn_field_length)
{
nr_rlc_entity_um_t *ret;
@@ -203,11 +198,9 @@ nr_rlc_entity_t *new_nr_rlc_entity_um(
return (nr_rlc_entity_t *)ret;
}
-nr_rlc_entity_t *new_nr_rlc_entity_tm(
- int tx_maxsize,
- void (*deliver_sdu)(void *deliver_sdu_data, struct nr_rlc_entity_t *entity,
- char *buf, int size),
- void *deliver_sdu_data)
+nr_rlc_entity_t *new_nr_rlc_entity_tm(int tx_maxsize,
+ void (*deliver_sdu)(void *deliver_sdu_data, nr_rlc_entity_t *entity, char *buf, int size),
+ void *deliver_sdu_data)
{
nr_rlc_entity_tm_t *ret;
diff --git a/openair2/LAYER2/nr_rlc/nr_rlc_entity.h b/openair2/LAYER2/nr_rlc/nr_rlc_entity.h
index 459e9f59a5..a16e3b7186 100644
--- a/openair2/LAYER2/nr_rlc/nr_rlc_entity.h
+++ b/openair2/LAYER2/nr_rlc/nr_rlc_entity.h
@@ -97,41 +97,35 @@ typedef struct {
int retx_size;
} nr_rlc_entity_buffer_status_t;
-typedef struct nr_rlc_entity_t {
+typedef struct nr_rlc_entity_s {
/* functions provided by the RLC module */
- void (*recv_pdu)(struct nr_rlc_entity_t *entity, char *buffer, int size);
- nr_rlc_entity_buffer_status_t (*buffer_status)(
- struct nr_rlc_entity_t *entity, int maxsize);
- int (*generate_pdu)(struct nr_rlc_entity_t *entity, char *buffer, int size);
+ void (*recv_pdu)(struct nr_rlc_entity_s *entity, char *buffer, int size);
+ nr_rlc_entity_buffer_status_t (*buffer_status)(struct nr_rlc_entity_s *entity, int maxsize);
+ int (*generate_pdu)(struct nr_rlc_entity_s *entity, char *buffer, int size);
- void (*recv_sdu)(struct nr_rlc_entity_t *entity, char *buffer, int size,
- int sdu_id);
+ void (*recv_sdu)(struct nr_rlc_entity_s *entity, char *buffer, int size, int sdu_id);
- void (*set_time)(struct nr_rlc_entity_t *entity, uint64_t now);
+ void (*set_time)(struct nr_rlc_entity_s *entity, uint64_t now);
- void (*discard_sdu)(struct nr_rlc_entity_t *entity, int sdu_id);
+ void (*discard_sdu)(struct nr_rlc_entity_s *entity, int sdu_id);
- void (*reestablishment)(struct nr_rlc_entity_t *entity);
+ void (*reestablishment)(struct nr_rlc_entity_s *entity);
- void (*delete_entity)(struct nr_rlc_entity_t *entity);
+ void (*delete_entity)(struct nr_rlc_entity_s *entity);
- int (*available_tx_space)(struct nr_rlc_entity_t *entity);
- int (*tx_list_occupancy)(struct nr_rlc_entity_t *entity);
+ int (*available_tx_space)(struct nr_rlc_entity_s *entity);
+ int (*tx_list_occupancy)(struct nr_rlc_entity_s *entity);
- void (*get_stats)(struct nr_rlc_entity_t *entity, nr_rlc_statistics_t *out);
+ void (*get_stats)(struct nr_rlc_entity_s *entity, nr_rlc_statistics_t *out);
/* callbacks provided to the RLC module */
- void (*deliver_sdu)(void *deliver_sdu_data, struct nr_rlc_entity_t *entity,
- char *buf, int size);
+ void (*deliver_sdu)(void *deliver_sdu_data, struct nr_rlc_entity_s *entity, char *buf, int size);
void *deliver_sdu_data;
- void (*sdu_successful_delivery)(void *sdu_successful_delivery_data,
- struct nr_rlc_entity_t *entity,
- int sdu_id);
+ void (*sdu_successful_delivery)(void *sdu_successful_delivery_data, struct nr_rlc_entity_s *entity, int sdu_id);
void *sdu_successful_delivery_data;
- void (*max_retx_reached)(void *max_retx_reached_data,
- struct nr_rlc_entity_t *entity);
+ void (*max_retx_reached)(void *max_retx_reached_data, struct nr_rlc_entity_s *entity);
void *max_retx_reached_data;
/* buffer status computation */
nr_rlc_entity_buffer_status_t bstatus;
@@ -141,41 +135,34 @@ typedef struct nr_rlc_entity_t {
int avg_time_is_on;
} nr_rlc_entity_t;
-nr_rlc_entity_t *new_nr_rlc_entity_am(
- int rx_maxsize,
- int tx_maxsize,
- void (*deliver_sdu)(void *deliver_sdu_data, struct nr_rlc_entity_t *entity,
- char *buf, int size),
- void *deliver_sdu_data,
- void (*sdu_successful_delivery)(void *sdu_successful_delivery_data,
- struct nr_rlc_entity_t *entity,
- int sdu_id),
- void *sdu_successful_delivery_data,
- void (*max_retx_reached)(void *max_retx_reached_data,
- struct nr_rlc_entity_t *entity),
- void *max_retx_reached_data,
- int t_poll_retransmit,
- int t_reassembly,
- int t_status_prohibit,
- int poll_pdu,
- int poll_byte,
- int max_retx_threshold,
- int sn_field_length);
+nr_rlc_entity_t *new_nr_rlc_entity_am(int rx_maxsize,
+ int tx_maxsize,
+ void (*deliver_sdu)(void *deliver_sdu_data, nr_rlc_entity_t *entity, char *buf, int size),
+ void *deliver_sdu_data,
+ void (*sdu_successful_delivery)(void *sdu_successful_delivery_data,
+ nr_rlc_entity_t *entity,
+ int sdu_id),
+ void *sdu_successful_delivery_data,
+ void (*max_retx_reached)(void *max_retx_reached_data, nr_rlc_entity_t *entity),
+ void *max_retx_reached_data,
+ int t_poll_retransmit,
+ int t_reassembly,
+ int t_status_prohibit,
+ int poll_pdu,
+ int poll_byte,
+ int max_retx_threshold,
+ int sn_field_length);
-nr_rlc_entity_t *new_nr_rlc_entity_um(
- int rx_maxsize,
- int tx_maxsize,
- void (*deliver_sdu)(void *deliver_sdu_data, struct nr_rlc_entity_t *entity,
- char *buf, int size),
- void *deliver_sdu_data,
- int t_reassembly,
- int sn_field_length);
+nr_rlc_entity_t *new_nr_rlc_entity_um(int rx_maxsize,
+ int tx_maxsize,
+ void (*deliver_sdu)(void *deliver_sdu_data, nr_rlc_entity_t *entity, char *buf, int size),
+ void *deliver_sdu_data,
+ int t_reassembly,
+ int sn_field_length);
-nr_rlc_entity_t *new_nr_rlc_entity_tm(
- int tx_maxsize,
- void (*deliver_sdu)(void *deliver_sdu_data, struct nr_rlc_entity_t *entity,
- char *buf, int size),
- void *deliver_sdu_data);
+nr_rlc_entity_t *new_nr_rlc_entity_tm(int tx_maxsize,
+ void (*deliver_sdu)(void *deliver_sdu_data, nr_rlc_entity_t *entity, char *buf, int size),
+ void *deliver_sdu_data);
void nr_rlc_entity_um_reconfigure(nr_rlc_entity_t *_entity, int t_reassembly, int *sn_field_length);
diff --git a/openair2/LAYER2/nr_rlc/nr_rlc_oai_api.c b/openair2/LAYER2/nr_rlc/nr_rlc_oai_api.c
index 126f9fb51c..133aea8d15 100644
--- a/openair2/LAYER2/nr_rlc/nr_rlc_oai_api.c
+++ b/openair2/LAYER2/nr_rlc/nr_rlc_oai_api.c
@@ -875,8 +875,7 @@ struct srb0_data {
void (*send_initial_ul_rrc_message)(int ue_id, const uint8_t *sdu, sdu_size_t sdu_len, void *data);
};
-void deliver_sdu_srb0(void *deliver_sdu_data, struct nr_rlc_entity_t *entity,
- char *buf, int size)
+void deliver_sdu_srb0(void *deliver_sdu_data, nr_rlc_entity_t *entity, char *buf, int size)
{
struct srb0_data *s0 = (struct srb0_data *)deliver_sdu_data;
s0->send_initial_ul_rrc_message(s0->ue_id, (unsigned char *)buf, size, s0->data);
diff --git a/openair2/LAYER2/nr_rlc/tests/benchmark_nr_rlc_am_entity.cpp b/openair2/LAYER2/nr_rlc/tests/benchmark_nr_rlc_am_entity.cpp
index ac36b79211..fe51273e61 100644
--- a/openair2/LAYER2/nr_rlc/tests/benchmark_nr_rlc_am_entity.cpp
+++ b/openair2/LAYER2/nr_rlc/tests/benchmark_nr_rlc_am_entity.cpp
@@ -28,13 +28,13 @@ extern configmodule_interface_t *uniqCfg;
}
#include
-void deliver_sdu(void *deliver_sdu_data, struct nr_rlc_entity_t *entity, char *buf, int size)
+void deliver_sdu(void *deliver_sdu_data, nr_rlc_entity_t *entity, char *buf, int size)
{
}
-void sdu_successful_delivery(void *sdu_successful_delivery_data, struct nr_rlc_entity_t *entity, int sdu_id)
+void sdu_successful_delivery(void *sdu_successful_delivery_data, nr_rlc_entity_t *entity, int sdu_id)
{
}
-void max_retx_reached(void *max_retx_reached_data, struct nr_rlc_entity_t *entity)
+void max_retx_reached(void *max_retx_reached_data, nr_rlc_entity_t *entity)
{
}
diff --git a/openair2/LAYER2/nr_rlc/tests/test.c b/openair2/LAYER2/nr_rlc/tests/test.c
index 04e49c460a..6af48b474b 100644
--- a/openair2/LAYER2/nr_rlc/tests/test.c
+++ b/openair2/LAYER2/nr_rlc/tests/test.c
@@ -107,9 +107,7 @@ int test[] = {
#include TEST
};
-void deliver_sdu_gnb_am(void *deliver_sdu_data,
- struct nr_rlc_entity_t *_entity,
- char *buf, int size)
+void deliver_sdu_gnb_am(void *deliver_sdu_data, nr_rlc_entity_t *_entity, char *buf, int size)
{
nr_rlc_entity_am_t *entity = (nr_rlc_entity_am_t *)_entity;
printf("TEST: GNB: %"PRIu64": deliver SDU size %d [",
@@ -118,9 +116,7 @@ void deliver_sdu_gnb_am(void *deliver_sdu_data,
printf("]\n");
}
-void deliver_sdu_gnb_um(void *deliver_sdu_data,
- struct nr_rlc_entity_t *_entity,
- char *buf, int size)
+void deliver_sdu_gnb_um(void *deliver_sdu_data, nr_rlc_entity_t *_entity, char *buf, int size)
{
nr_rlc_entity_um_t *entity = (nr_rlc_entity_um_t *)_entity;
printf("TEST: GNB: %"PRIu64": deliver SDU size %d [",
@@ -129,9 +125,7 @@ void deliver_sdu_gnb_um(void *deliver_sdu_data,
printf("]\n");
}
-void deliver_sdu_gnb_tm(void *deliver_sdu_data,
- struct nr_rlc_entity_t *_entity,
- char *buf, int size)
+void deliver_sdu_gnb_tm(void *deliver_sdu_data, nr_rlc_entity_t *_entity, char *buf, int size)
{
nr_rlc_entity_tm_t *entity = (nr_rlc_entity_tm_t *)_entity;
printf("TEST: GNB: %"PRIu64": deliver SDU size %d [",
@@ -157,9 +151,7 @@ void max_retx_reached_gnb(void *max_retx_reached_data,
exit(1);
}
-void deliver_sdu_ue_am(void *deliver_sdu_data,
- struct nr_rlc_entity_t *_entity,
- char *buf, int size)
+void deliver_sdu_ue_am(void *deliver_sdu_data, nr_rlc_entity_t *_entity, char *buf, int size)
{
nr_rlc_entity_am_t *entity = (nr_rlc_entity_am_t *)_entity;
printf("TEST: UE: %"PRIu64": deliver SDU size %d [",
@@ -168,9 +160,7 @@ void deliver_sdu_ue_am(void *deliver_sdu_data,
printf("]\n");
}
-void deliver_sdu_ue_um(void *deliver_sdu_data,
- struct nr_rlc_entity_t *_entity,
- char *buf, int size)
+void deliver_sdu_ue_um(void *deliver_sdu_data, nr_rlc_entity_t *_entity, char *buf, int size)
{
nr_rlc_entity_um_t *entity = (nr_rlc_entity_um_t *)_entity;
printf("TEST: UE: %"PRIu64": deliver SDU size %d [",
@@ -179,9 +169,7 @@ void deliver_sdu_ue_um(void *deliver_sdu_data,
printf("]\n");
}
-void deliver_sdu_ue_tm(void *deliver_sdu_data,
- struct nr_rlc_entity_t *_entity,
- char *buf, int size)
+void deliver_sdu_ue_tm(void *deliver_sdu_data, nr_rlc_entity_t *_entity, char *buf, int size)
{
nr_rlc_entity_tm_t *entity = (nr_rlc_entity_tm_t *)_entity;
printf("TEST: UE: %"PRIu64": deliver SDU size %d [",
diff --git a/openair2/LAYER2/nr_rlc/tests/test_nr_rlc_am_entity.cpp b/openair2/LAYER2/nr_rlc/tests/test_nr_rlc_am_entity.cpp
index 5407f7b2ae..5f07b9243e 100644
--- a/openair2/LAYER2/nr_rlc/tests/test_nr_rlc_am_entity.cpp
+++ b/openair2/LAYER2/nr_rlc/tests/test_nr_rlc_am_entity.cpp
@@ -31,7 +31,7 @@ extern configmodule_interface_t *uniqCfg;
int sdu_delivered_count = 0;
int sdu_acked_count = 0;
-void deliver_sdu(void *deliver_sdu_data, struct nr_rlc_entity_t *entity, char *buf, int size)
+void deliver_sdu(void *deliver_sdu_data, nr_rlc_entity_t *entity, char *buf, int size)
{
sdu_delivered_count++;
char payload[300];
@@ -40,13 +40,13 @@ void deliver_sdu(void *deliver_sdu_data, struct nr_rlc_entity_t *entity, char *b
std::cout << "Delivered sdu: " << payload << std::endl;
}
-void sdu_successful_delivery(void *sdu_successful_delivery_data, struct nr_rlc_entity_t *entity, int sdu_id)
+void sdu_successful_delivery(void *sdu_successful_delivery_data, nr_rlc_entity_t *entity, int sdu_id)
{
sdu_acked_count++;
std::cout << "SDU " << sdu_id << " acked" << std::endl;
}
-void max_retx_reached(void *max_retx_reached_data, struct nr_rlc_entity_t *entity)
+void max_retx_reached(void *max_retx_reached_data, nr_rlc_entity_t *entity)
{
}
diff --git a/openair2/LAYER2/rlc_v2/rlc_entity.c b/openair2/LAYER2/rlc_v2/rlc_entity.c
index d774e2b7e1..26af68e58b 100644
--- a/openair2/LAYER2/rlc_v2/rlc_entity.c
+++ b/openair2/LAYER2/rlc_v2/rlc_entity.c
@@ -28,25 +28,22 @@
#include "LOG/log.h"
-rlc_entity_t *new_rlc_entity_am(
- int rx_maxsize,
- int tx_maxsize,
- void (*deliver_sdu)(void *deliver_sdu_data, struct rlc_entity_t *entity,
- char *buf, int size),
- void *deliver_sdu_data,
- void (*sdu_successful_delivery)(void *sdu_successful_delivery_data,
- struct rlc_entity_t *entity,
- int sdu_id),
- void *sdu_successful_delivery_data,
- void (*max_retx_reached)(void *max_retx_reached_data,
- struct rlc_entity_t *entity),
- void *max_retx_reached_data,
- int t_reordering,
- int t_status_prohibit,
- int t_poll_retransmit,
- int poll_pdu,
- int poll_byte,
- int max_retx_threshold)
+rlc_entity_t *new_rlc_entity_am(int rx_maxsize,
+ int tx_maxsize,
+ void (*deliver_sdu)(void *deliver_sdu_data, rlc_entity_t *entity, char *buf, int size),
+ void *deliver_sdu_data,
+ void (*sdu_successful_delivery)(void *sdu_successful_delivery_data,
+ rlc_entity_t *entity,
+ int sdu_id),
+ void *sdu_successful_delivery_data,
+ void (*max_retx_reached)(void *max_retx_reached_data, rlc_entity_t *entity),
+ void *max_retx_reached_data,
+ int t_reordering,
+ int t_status_prohibit,
+ int t_poll_retransmit,
+ int poll_pdu,
+ int poll_byte,
+ int max_retx_threshold)
{
rlc_entity_am_t *ret;
@@ -91,14 +88,12 @@ rlc_entity_t *new_rlc_entity_am(
return (rlc_entity_t *)ret;
}
-rlc_entity_t *new_rlc_entity_um(
- int rx_maxsize,
- int tx_maxsize,
- void (*deliver_sdu)(void *deliver_sdu_data, struct rlc_entity_t *entity,
- char *buf, int size),
- void *deliver_sdu_data,
- int t_reordering,
- int sn_field_length)
+rlc_entity_t *new_rlc_entity_um(int rx_maxsize,
+ int tx_maxsize,
+ void (*deliver_sdu)(void *deliver_sdu_data, rlc_entity_t *entity, char *buf, int size),
+ void *deliver_sdu_data,
+ int t_reordering,
+ int sn_field_length)
{
rlc_entity_um_t *ret;
diff --git a/openair2/LAYER2/rlc_v2/rlc_entity.h b/openair2/LAYER2/rlc_v2/rlc_entity.h
index c9b35204f0..d0be4d87e7 100644
--- a/openair2/LAYER2/rlc_v2/rlc_entity.h
+++ b/openair2/LAYER2/rlc_v2/rlc_entity.h
@@ -32,66 +32,55 @@ typedef struct {
int retx_size;
} rlc_entity_buffer_status_t;
-typedef struct rlc_entity_t {
+typedef struct rlc_entity_s {
/* functions provided by the RLC module */
- void (*recv_pdu)(struct rlc_entity_t *entity, char *buffer, int size);
- rlc_entity_buffer_status_t (*buffer_status)(
- struct rlc_entity_t *entity, int maxsize);
- int (*generate_pdu)(struct rlc_entity_t *entity, char *buffer, int size);
+ void (*recv_pdu)(struct rlc_entity_s *entity, char *buffer, int size);
+ rlc_entity_buffer_status_t (*buffer_status)(struct rlc_entity_s *entity, int maxsize);
+ int (*generate_pdu)(struct rlc_entity_s *entity, char *buffer, int size);
- void (*recv_sdu)(struct rlc_entity_t *entity, char *buffer, int size,
- int sdu_id);
+ void (*recv_sdu)(struct rlc_entity_s *entity, char *buffer, int size, int sdu_id);
- void (*set_time)(struct rlc_entity_t *entity, uint64_t now);
+ void (*set_time)(struct rlc_entity_s *entity, uint64_t now);
- void (*discard_sdu)(struct rlc_entity_t *entity, int sdu_id);
+ void (*discard_sdu)(struct rlc_entity_s *entity, int sdu_id);
- void (*reestablishment)(struct rlc_entity_t *entity);
+ void (*reestablishment)(struct rlc_entity_s *entity);
- void (*delete)(struct rlc_entity_t *entity);
+ void (*delete)(struct rlc_entity_s *entity);
/* callbacks provided to the RLC module */
- void (*deliver_sdu)(void *deliver_sdu_data, struct rlc_entity_t *entity,
- char *buf, int size);
+ void (*deliver_sdu)(void *deliver_sdu_data, struct rlc_entity_s *entity, char *buf, int size);
void *deliver_sdu_data;
- void (*sdu_successful_delivery)(void *sdu_successful_delivery_data,
- struct rlc_entity_t *entity,
- int sdu_id);
+ void (*sdu_successful_delivery)(void *sdu_successful_delivery_data, struct rlc_entity_s *entity, int sdu_id);
void *sdu_successful_delivery_data;
- void (*max_retx_reached)(void *max_retx_reached_data,
- struct rlc_entity_t *entity);
+ void (*max_retx_reached)(void *max_retx_reached_data, struct rlc_entity_s *entity);
void *max_retx_reached_data;
} rlc_entity_t;
-rlc_entity_t *new_rlc_entity_am(
- int rx_maxsize,
- int tx_maxsize,
- void (*deliver_sdu)(void *deliver_sdu_data, struct rlc_entity_t *entity,
- char *buf, int size),
- void *deliver_sdu_data,
- void (*sdu_successful_delivery)(void *sdu_successful_delivery_data,
- struct rlc_entity_t *entity,
- int sdu_id),
- void *sdu_successful_delivery_data,
- void (*max_retx_reached)(void *max_retx_reached_data,
- struct rlc_entity_t *entity),
- void *max_retx_reached_data,
- int t_reordering,
- int t_status_prohibit,
- int t_poll_retransmit,
- int poll_pdu,
- int poll_byte,
- int max_retx_threshold);
+rlc_entity_t *new_rlc_entity_am(int rx_maxsize,
+ int tx_maxsize,
+ void (*deliver_sdu)(void *deliver_sdu_data, rlc_entity_t *entity, char *buf, int size),
+ void *deliver_sdu_data,
+ void (*sdu_successful_delivery)(void *sdu_successful_delivery_data,
+ rlc_entity_t *entity,
+ int sdu_id),
+ void *sdu_successful_delivery_data,
+ void (*max_retx_reached)(void *max_retx_reached_data, rlc_entity_t *entity),
+ void *max_retx_reached_data,
+ int t_reordering,
+ int t_status_prohibit,
+ int t_poll_retransmit,
+ int poll_pdu,
+ int poll_byte,
+ int max_retx_threshold);
-rlc_entity_t *new_rlc_entity_um(
- int rx_maxsize,
- int tx_maxsize,
- void (*deliver_sdu)(void *deliver_sdu_data, struct rlc_entity_t *entity,
- char *buf, int size),
- void *deliver_sdu_data,
- int t_reordering,
- int sn_field_length);
+rlc_entity_t *new_rlc_entity_um(int rx_maxsize,
+ int tx_maxsize,
+ void (*deliver_sdu)(void *deliver_sdu_data, rlc_entity_t *entity, char *buf, int size),
+ void *deliver_sdu_data,
+ int t_reordering,
+ int sn_field_length);
#endif /* _RLC_ENTITY_H_ */
diff --git a/openair2/NR_UE_PHY_INTERFACE/NR_IF_Module.c b/openair2/NR_UE_PHY_INTERFACE/NR_IF_Module.c
index 73845551af..5fb8ad78dd 100644
--- a/openair2/NR_UE_PHY_INTERFACE/NR_IF_Module.c
+++ b/openair2/NR_UE_PHY_INTERFACE/NR_IF_Module.c
@@ -106,7 +106,6 @@ void print_ue_mac_stats(const module_id_t mod, const int frame_rx, const int slo
static int handle_bcch_bch(NR_UE_MAC_INST_t *mac,
int cc_id,
unsigned int gNB_index,
- void *phy_data,
uint8_t *pduP,
unsigned int additional_bits,
uint32_t ssb_index_mod8,
@@ -149,17 +148,13 @@ static int handle_bcch_dlsch(NR_UE_MAC_INST_t *mac,
}
// L2 Abstraction Layer
-static nr_dci_format_t handle_dci(NR_UE_MAC_INST_t *mac,
- unsigned int gNB_index,
- frame_t frame,
- int slot,
- fapi_nr_dci_indication_pdu_t *dci)
+static nr_dci_format_t handle_dci(NR_UE_MAC_INST_t *mac, frame_t frame, int slot, fapi_nr_dci_indication_pdu_t *dci)
{
// if notification of a reception of a PDCCH transmission of the SpCell is received from lower layers
// if the C-RNTI MAC CE was included in Msg3
// consider this Contention Resolution successful
if (mac->msg3_C_RNTI && mac->ra.ra_state == nrRA_WAIT_CONTENTION_RESOLUTION)
- nr_ra_succeeded(mac, gNB_index, frame, slot);
+ nr_ra_succeeded(mac, frame, slot);
// suspend RAR response window timer
// (in RFsim running multiple slot in parallel it might expire while decoding MSG2)
@@ -245,11 +240,7 @@ static uint32_t nr_ue_dl_processing(NR_UE_MAC_INST_t *mac, nr_downlink_indicatio
LOG_T(MAC, "[L2][IF MODULE][DL INDICATION][DCI_IND]\n");
for (int i = 0; i < dl_info->dci_ind->number_of_dcis; i++) {
LOG_T(MAC, ">>>NR_IF_Module i=%d, dl_info->dci_ind->number_of_dcis=%d\n", i, dl_info->dci_ind->number_of_dcis);
- nr_dci_format_t dci_format = handle_dci(mac,
- dl_info->gNB_index,
- dl_info->frame,
- dl_info->slot,
- dl_info->dci_ind->dci_list + i);
+ nr_dci_format_t dci_format = handle_dci(mac, dl_info->frame, dl_info->slot, dl_info->dci_ind->dci_list + i);
/* The check below filters out UL_DCIs which are being processed as DL_DCIs. */
if (dci_format != NR_DL_DCI_FORMAT_1_0 && dci_format != NR_DL_DCI_FORMAT_1_1) {
@@ -291,7 +282,6 @@ static uint32_t nr_ue_dl_processing(NR_UE_MAC_INST_t *mac, nr_downlink_indicatio
ret_mask |= (handle_bcch_bch(mac,
dl_info->cc_id,
dl_info->gNB_index,
- dl_info->phy_data,
rx_indication_body.ssb_pdu.pdu,
rx_indication_body.ssb_pdu.additional_bits,
rx_indication_body.ssb_pdu.ssb_index,
diff --git a/openair2/NR_UE_PHY_INTERFACE/NR_Packet_Drop.c b/openair2/NR_UE_PHY_INTERFACE/NR_Packet_Drop.c
index 97c5a4e130..439371c013 100644
--- a/openair2/NR_UE_PHY_INTERFACE/NR_Packet_Drop.c
+++ b/openair2/NR_UE_PHY_INTERFACE/NR_Packet_Drop.c
@@ -25,7 +25,7 @@
nr_bler_struct nr_bler_data[NR_NUM_MCS];
-slot_rnti_mcs_s slot_rnti_mcs[NUM_NFAPI_SLOT];
+slot_rnti_mcs_t slot_rnti_mcs[NUM_NFAPI_SLOT];
void read_channel_param(const nfapi_nr_dl_tti_pdsch_pdu_rel15_t * pdu, int slot, int index)
{
if (pdu == NULL)
diff --git a/openair2/NR_UE_PHY_INTERFACE/NR_Packet_Drop.h b/openair2/NR_UE_PHY_INTERFACE/NR_Packet_Drop.h
index dcc5710724..4db7f64a4f 100644
--- a/openair2/NR_UE_PHY_INTERFACE/NR_Packet_Drop.h
+++ b/openair2/NR_UE_PHY_INTERFACE/NR_Packet_Drop.h
@@ -44,13 +44,6 @@ typedef struct {
uint8_t area_code;
} nr_channel_status;
-typedef struct nr_phy_channel_params_t {
- uint16_t sfn_slot;
- uint16_t message_id;
- uint16_t nb_of_csi;
- nr_channel_status csi[NR_NUM_LAYER];
-} nr_phy_channel_params_t;
-
typedef struct {
uint8_t slot;
uint16_t rnti[MAX_NR_CHAN_PARAMS];
@@ -61,7 +54,7 @@ typedef struct {
bool drop_flag[MAX_NR_CHAN_PARAMS];
bool latest;
uint8_t area_code;
-} slot_rnti_mcs_s;
+} slot_rnti_mcs_t;
typedef struct {
uint16_t length;
diff --git a/openair2/RRC/LTE/rrc_UE.c b/openair2/RRC/LTE/rrc_UE.c
index 6b327d92bc..87481ec316 100644
--- a/openair2/RRC/LTE/rrc_UE.c
+++ b/openair2/RRC/LTE/rrc_UE.c
@@ -130,9 +130,8 @@ static int decode_SIB1( const protocol_ctxt_t *const ctxt_pP, const uint8_t eNB_
static int decode_SIB1_MBMS( const protocol_ctxt_t *const ctxt_pP, const uint8_t eNB_index, const uint8_t rsrq, const uint8_t rsrp );
-typedef struct rrc_dcch_data_copy_t
-{
- LTE_DL_DCCH_Message_t *dl_dcch_msg;
+typedef struct {
+ LTE_DL_DCCH_Message_t *dl_dcch_msg;
} rrc_dcch_data_copy_t;
static void rrc_ue_process_ueCapabilityEnquiry(const protocol_ctxt_t *const ctxt_pP,
diff --git a/openair2/RRC/NR/rrc_gNB.c b/openair2/RRC/NR/rrc_gNB.c
index 936f333124..7fea00e5dc 100644
--- a/openair2/RRC/NR/rrc_gNB.c
+++ b/openair2/RRC/NR/rrc_gNB.c
@@ -207,7 +207,7 @@ static bool rrc_delay_transaction(instance_t instance, MessageDef *msg_p)
return false; /* not delayed */
}
-typedef struct deliver_ue_ctxt_release_data_t {
+typedef struct {
gNB_RRC_INST *rrc;
f1ap_ue_context_rel_cmd_t *release_cmd;
sctp_assoc_t assoc_id;
diff --git a/openair2/RRC/NR/rrc_gNB_du.c b/openair2/RRC/NR/rrc_gNB_du.c
index 76f1ab1741..70fec34a83 100644
--- a/openair2/RRC/NR/rrc_gNB_du.c
+++ b/openair2/RRC/NR/rrc_gNB_du.c
@@ -53,12 +53,12 @@
#include "utils.h"
#include "xer_encoder.h"
-static int get_dl_band(const struct f1ap_served_cell_info_t *cell_info)
+static int get_dl_band(const f1ap_served_cell_info_t *cell_info)
{
return cell_info->mode == F1AP_MODE_TDD ? cell_info->tdd.freqinfo.band : cell_info->fdd.dl_freqinfo.band;
}
-static int get_ssb_scs(const struct f1ap_served_cell_info_t *cell_info)
+static int get_ssb_scs(const f1ap_served_cell_info_t *cell_info)
{
return cell_info->mode == F1AP_MODE_TDD ? cell_info->tdd.tbw.scs : cell_info->fdd.dl_tbw.scs;
}
diff --git a/openair2/RRC/NR/rrc_gNB_du.h b/openair2/RRC/NR/rrc_gNB_du.h
index 343ab5d189..e746b9af96 100644
--- a/openair2/RRC/NR/rrc_gNB_du.h
+++ b/openair2/RRC/NR/rrc_gNB_du.h
@@ -37,8 +37,8 @@ struct f1ap_served_cell_info_t;
#include "f1ap_messages_types.h"
#include "ngap_messages_types.h"
-void rrc_gNB_process_f1_setup_req(struct f1ap_setup_req_s *req, sctp_assoc_t assoc_id);
-void rrc_CU_process_f1_lost_connection(struct gNB_RRC_INST_s *rrc, struct f1ap_lost_connection_t *lc, sctp_assoc_t assoc_id);
+void rrc_gNB_process_f1_setup_req(f1ap_setup_req_t *req, sctp_assoc_t assoc_id);
+void rrc_CU_process_f1_lost_connection(struct gNB_RRC_INST_s *rrc, f1ap_lost_connection_t *lc, sctp_assoc_t assoc_id);
void rrc_gNB_process_f1_du_configuration_update(struct f1ap_gnb_du_configuration_update_s *conf_up, sctp_assoc_t assoc_id);
struct nr_rrc_du_container_t *get_du_for_ue(struct gNB_RRC_INST_s *rrc, uint32_t ue_id);
diff --git a/openair2/RRC/NR/rrc_gNB_mobility.c b/openair2/RRC/NR/rrc_gNB_mobility.c
index 4d2785d9a0..3c59cdfc16 100644
--- a/openair2/RRC/NR/rrc_gNB_mobility.c
+++ b/openair2/RRC/NR/rrc_gNB_mobility.c
@@ -163,7 +163,7 @@ static void nr_initiate_handover(const gNB_RRC_INST *rrc,
rrc_f1_ue_context_setup_for_target_du(rrc, ue, target_cell, ho_prep_info);
}
-typedef struct deliver_ue_ctxt_modification_data_t {
+typedef struct {
gNB_RRC_INST *rrc;
f1ap_ue_context_mod_req_t *modification_req;
sctp_assoc_t assoc_id;
diff --git a/openair2/RRC/NR/rrc_gNB_mobility.h b/openair2/RRC/NR/rrc_gNB_mobility.h
index d4a51efeb9..6eb65b51e5 100644
--- a/openair2/RRC/NR/rrc_gNB_mobility.h
+++ b/openair2/RRC/NR/rrc_gNB_mobility.h
@@ -28,7 +28,6 @@
/* forward declarations */
typedef struct gNB_RRC_INST_s gNB_RRC_INST;
typedef struct gNB_RRC_UE_s gNB_RRC_UE_t;
-typedef struct nr_rrc_cell_container_t nr_rrc_cell_container_t;
typedef struct NR_CellGroupConfig NR_CellGroupConfig_t;
diff --git a/openair3/NGAP/ngap_gNB.c b/openair3/NGAP/ngap_gNB.c
index 257ca25f1a..995de828bb 100644
--- a/openair3/NGAP/ngap_gNB.c
+++ b/openair3/NGAP/ngap_gNB.c
@@ -58,6 +58,7 @@
#include "ngap_gNB_mobility_management.h"
#include "ngap_gNB_ue_context.h"
#include "ngap_gNB_pdu_session_management.h"
+#include "ngap_gNB_NRPPa_transport_procedures.h"
#include "oai_asn1.h"
#include "openair3/SECU/kdf.h"
#include "queue.h"
@@ -93,6 +94,38 @@ uint32_t ngap_generate_gNB_id(void)
return gNB_id;
}
+static void ngap_gNB_redial_amf(ngap_gNB_amf_data_t *amf_desc_p)
+{
+ NGAP_INFO("AMF cnx_id = %u\n", amf_desc_p->cnx_id);
+ NGAP_INFO("AMF state = %d\n", amf_desc_p->state);
+ /*reconnect with the amf */
+ MessageDef *message_p = itti_alloc_new_message(TASK_NGAP, 0, SCTP_NEW_ASSOCIATION_REQ);
+ sctp_new_association_req_t *req = &message_p->ittiMsg.sctp_new_association_req;
+
+ /*amf descriptor */
+ req->port = NGAP_PORT_NUMBER;
+ req->ppid = NGAP_SCTP_PPID;
+ req->in_streams = amf_desc_p->in_streams;
+ req->out_streams = amf_desc_p->out_streams;
+ req->ulp_cnx_id = amf_desc_p->cnx_id;
+
+ ngap_gNB_instance_t *inst = amf_desc_p->ngap_gNB_instance;
+
+ memcpy(&req->remote_address, &amf_desc_p->amf_s1_ip, sizeof(req->remote_address));
+ memcpy(&req->local_address, &inst->gNB_ng_ip, sizeof(req->local_address));
+
+ NGAP_INFO("[gNB %ld] Re-dial AMF cnx_id=%u (streams in=%u out=%u)\n",
+ inst->instance,
+ amf_desc_p->cnx_id,
+ req->in_streams,
+ req->out_streams);
+
+ inst->ngap_amf_nb++;
+ inst->ngap_amf_pending_nb++;
+
+ itti_send_msg_to_task(TASK_SCTP, inst->instance, message_p);
+}
+
static void ngap_gNB_register_amf(ngap_gNB_instance_t *instance_p,
net_ip_address_t *amf_ip_address,
net_ip_address_t *local_ip_addr,
@@ -550,6 +583,15 @@ void *ngap_gNB_process_itti_msg(void *notUsed) {
ngap_gNB_handle_sctp_association_resp(instance, &received_msg->ittiMsg.sctp_new_association_resp);
break;
+ case TIMER_HAS_EXPIRED: {
+ timer_has_expired_t *th = &received_msg->ittiMsg.timer_has_expired;
+ ngap_gNB_amf_data_t *amf_desc_p = (ngap_gNB_amf_data_t *)th->arg;
+ if (amf_desc_p) {
+ ngap_gNB_redial_amf(amf_desc_p);
+ }
+ break;
+ }
+
case SCTP_DATA_IND:
ngap_gNB_handle_sctp_data_ind(&received_msg->ittiMsg.sctp_data_ind);
break;
@@ -626,6 +668,14 @@ void *ngap_gNB_process_itti_msg(void *notUsed) {
ngap_gNB_handle_ul_ran_status_transfer(instance, &NGAP_UL_RAN_STATUS_TRANSFER(received_msg));
break;
+ case NGAP_UPLINKUEASSOCIATEDNRPPA:
+ ngap_gNB_uplink_ue_associated_nrppa_transport(instance, &NGAP_UPLINKUEASSOCIATEDNRPPA(received_msg));
+ break;
+
+ case NGAP_UPLINKNONUEASSOCIATEDNRPPA:
+ ngap_gNB_uplink_non_ue_associated_nrppa_transport(instance, &NGAP_UPLINKNONUEASSOCIATEDNRPPA(received_msg));
+ break;
+
default:
NGAP_ERROR("Received unhandled message: %d:%s\n", ITTI_MSG_ID(received_msg), ITTI_MSG_NAME(received_msg));
break;
diff --git a/openair3/NGAP/ngap_gNB_NRPPa_transport_procedures.c b/openair3/NGAP/ngap_gNB_NRPPa_transport_procedures.c
new file mode 100644
index 0000000000..37b5e3b344
--- /dev/null
+++ b/openair3/NGAP/ngap_gNB_NRPPa_transport_procedures.c
@@ -0,0 +1,314 @@
+/*
+ * Licensed to the OpenAirInterface (OAI) Software Alliance under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The OpenAirInterface Software Alliance licenses this file to You under
+ * the OAI Public License, Version 1.1 (the "License"); you may not use this file
+ * except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.openairinterface.org/?page_id=698
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *-------------------------------------------------------------------------------
+ * For more information about the OpenAirInterface (OAI) Software Alliance:
+ * contact@openairinterface.org
+ */
+
+#include
+#include
+#include
+
+#include "assertions.h"
+#include "conversions.h"
+
+#include "intertask_interface.h"
+
+#include "ngap_common.h"
+#include "ngap_gNB_defs.h"
+#include "ngap_gNB_itti_messaging.h"
+#include "ngap_gNB_encoder.h"
+#include "ngap_gNB_nnsf.h"
+#include "ngap_gNB_ue_context.h"
+#include "ngap_gNB_management_procedures.h"
+
+#include "ngap_gNB_NRPPa_transport_procedures.h"
+
+// UPLINK UE ASSOCIATED NRPPA TRANSPORT (9.2.9.2 of TS 38.413 Version 16.0.0)
+int ngap_gNB_uplink_ue_associated_nrppa_transport(instance_t instance, const ngap_uplink_ue_associated_nrppa_t *msg)
+{
+ LOG_I(NGAP, "Initiating ngap_gNB_uplink_ue_associated_nrppa_transport \n");
+ DevAssert(msg != NULL);
+ DevAssert(msg->routing_id.buf);
+ DevAssert(msg->routing_id.len);
+ DevAssert(msg->nrppa_pdu.buf);
+ DevAssert(msg->nrppa_pdu.len);
+ struct ngap_gNB_ue_context_s *ue_context_p = NULL;
+ ngap_gNB_instance_t *ngap_gNB_instance_p = NULL;
+
+ // Retrieve the NGAP gNB instance associated with Mod_id
+ ngap_gNB_instance_p = ngap_gNB_get_instance(instance);
+ DevAssert(ngap_gNB_instance_p != NULL);
+
+ if ((ue_context_p = ngap_get_ue_context(msg->gNB_ue_ngap_id)) == NULL) {
+ // The context for this gNB ue ngap id doesn't exist in the map of gNB UEs
+ LOG_E(NGAP, "Failed to find ue context associated with gNB ue ngap id: %08x\n", msg->gNB_ue_ngap_id);
+ return -1;
+ }
+ /* Prepare the NGAP message to encode */
+ NGAP_NGAP_PDU_t pdu = {0};
+
+ // IE: 9.3.1.1 Message Type UplinkUEAssociatedNRPPaTransport
+ pdu.present = NGAP_NGAP_PDU_PR_initiatingMessage;
+ asn1cCalloc(pdu.choice.initiatingMessage, head);
+ head->procedureCode = NGAP_ProcedureCode_id_UplinkUEAssociatedNRPPaTransport;
+ head->criticality = NGAP_Criticality_ignore;
+ head->value.present = NGAP_InitiatingMessage__value_PR_UplinkUEAssociatedNRPPaTransport;
+ NGAP_UplinkUEAssociatedNRPPaTransport_t *out = &head->value.choice.UplinkUEAssociatedNRPPaTransport;
+
+ // IE: 9.3.3.1 AMF UE NGAP ID (mandatory)
+ {
+ asn1cSequenceAdd(out->protocolIEs.list, NGAP_UplinkUEAssociatedNRPPaTransportIEs_t, ie);
+ ie->id = NGAP_ProtocolIE_ID_id_AMF_UE_NGAP_ID;
+ ie->criticality = NGAP_Criticality_reject;
+ ie->value.present = NGAP_UplinkUEAssociatedNRPPaTransportIEs__value_PR_AMF_UE_NGAP_ID;
+ asn_uint642INTEGER(&ie->value.choice.AMF_UE_NGAP_ID, msg->amf_ue_ngap_id);
+ }
+
+ // IE: 9.3.3.2 RAN UE NGAP ID (mandatory)
+ {
+ asn1cSequenceAdd(out->protocolIEs.list, NGAP_UplinkUEAssociatedNRPPaTransportIEs_t, ie);
+ ie->id = NGAP_ProtocolIE_ID_id_RAN_UE_NGAP_ID;
+ ie->criticality = NGAP_Criticality_reject;
+ ie->value.present = NGAP_UplinkUEAssociatedNRPPaTransportIEs__value_PR_RAN_UE_NGAP_ID;
+ ie->value.choice.RAN_UE_NGAP_ID = msg->gNB_ue_ngap_id;
+ }
+
+ // IE: 9.3.3.13 Routing ID (mandatory)
+ {
+ asn1cSequenceAdd(out->protocolIEs.list, NGAP_UplinkUEAssociatedNRPPaTransportIEs_t, ie);
+ ie->id = NGAP_ProtocolIE_ID_id_RoutingID;
+ ie->criticality = NGAP_Criticality_reject;
+ ie->value.present = NGAP_UplinkUEAssociatedNRPPaTransportIEs__value_PR_RoutingID;
+ ie->value.choice.RoutingID.buf = msg->routing_id.buf;
+ ie->value.choice.RoutingID.size = msg->routing_id.len;
+ }
+
+ // IE: 9.3.3.14 NRPPa-PDU (mandatory)
+ {
+ asn1cSequenceAdd(out->protocolIEs.list, NGAP_UplinkUEAssociatedNRPPaTransportIEs_t, ie);
+ ie->id = NGAP_ProtocolIE_ID_id_NRPPa_PDU;
+ ie->criticality = NGAP_Criticality_reject;
+ ie->value.present = NGAP_UplinkUEAssociatedNRPPaTransportIEs__value_PR_NRPPa_PDU;
+ ie->value.choice.NRPPa_PDU.buf = msg->nrppa_pdu.buf;
+ ie->value.choice.NRPPa_PDU.size = msg->nrppa_pdu.len;
+ }
+
+ // Encode NGAP message
+ uint8_t *buffer = NULL;
+ uint32_t length = 0;
+ if (ngap_gNB_encode_pdu(&pdu, &buffer, &length) < 0) {
+ LOG_E(NGAP, "Failed to encode Uplink UE Associated NRPPa Transport\n");
+ ASN_STRUCT_FREE_CONTENTS_ONLY(asn_DEF_NGAP_NGAP_PDU, &pdu);
+ return -1;
+ }
+ LOG_I(NGAP, "Sending ngap_gNB_uplink_ue_associated_nrppa_transport over SCTP\n");
+
+ // UE associated signalling -> use the allocated stream
+ ngap_gNB_itti_send_sctp_data_req(ngap_gNB_instance_p->instance,
+ ue_context_p->amf_ref->assoc_id,
+ buffer,
+ length,
+ ue_context_p->tx_stream);
+ ASN_STRUCT_FREE_CONTENTS_ONLY(asn_DEF_NGAP_NGAP_PDU, &pdu);
+ return 0;
+}
+
+// UPLINK NON UE ASSOCIATED NRPPA TRANSPORT (9.2.9.4 of TS 38.413 Version 16.0.0)
+int ngap_gNB_uplink_non_ue_associated_nrppa_transport(instance_t instance, const ngap_uplink_non_ue_associated_nrppa_t *msg)
+{
+ LOG_I(NGAP, "ngap_gNB_uplink_non_ue_associated_nrppa_transport\n");
+ DevAssert(msg != NULL);
+ DevAssert(msg->routing_id.buf);
+ DevAssert(msg->routing_id.len);
+ DevAssert(msg->nrppa_pdu.buf);
+ DevAssert(msg->nrppa_pdu.len);
+
+ // Retrieve the NGAP gNB instance associated with Mod_id
+ ngap_gNB_instance_t *ngap_gNB_instance_p = NULL;
+ ngap_gNB_instance_p = ngap_gNB_get_instance(instance);
+ DevAssert(ngap_gNB_instance_p != NULL);
+
+ // Retrieve the NGAP gNB amf data
+ ngap_gNB_amf_data_t *amf_desc_p = NULL;
+ amf_desc_p = ngap_gNB_get_AMF_from_instance(ngap_gNB_instance_p);
+ DevAssert(amf_desc_p != NULL);
+
+ // Prepare the NGAP message to encode
+ NGAP_NGAP_PDU_t pdu = {0};
+
+ // IE: 9.3.1.1 Message Type UplinkNonUEAssociatedNRPPaTransport
+ pdu.present = NGAP_NGAP_PDU_PR_initiatingMessage;
+ asn1cCalloc(pdu.choice.initiatingMessage, head);
+ head->procedureCode = NGAP_ProcedureCode_id_UplinkNonUEAssociatedNRPPaTransport;
+ head->criticality = NGAP_Criticality_ignore;
+ head->value.present = NGAP_InitiatingMessage__value_PR_UplinkNonUEAssociatedNRPPaTransport;
+ NGAP_UplinkNonUEAssociatedNRPPaTransport_t *out = &head->value.choice.UplinkNonUEAssociatedNRPPaTransport;
+
+ // IE: 9.3.3.13 Routing ID (mandatory)
+ {
+ asn1cSequenceAdd(out->protocolIEs.list, NGAP_UplinkNonUEAssociatedNRPPaTransportIEs_t, ie);
+ ie->id = NGAP_ProtocolIE_ID_id_RoutingID;
+ ie->criticality = NGAP_Criticality_reject;
+ ie->value.present = NGAP_UplinkNonUEAssociatedNRPPaTransportIEs__value_PR_RoutingID;
+ ie->value.choice.RoutingID.buf = msg->routing_id.buf;
+ ie->value.choice.RoutingID.size = msg->routing_id.len;
+ }
+
+ // IE: 9.3.3.14 NRPPa-PDU (mandatory)
+ {
+ asn1cSequenceAdd(out->protocolIEs.list, NGAP_UplinkNonUEAssociatedNRPPaTransportIEs_t, ie);
+ ie->id = NGAP_ProtocolIE_ID_id_NRPPa_PDU;
+ ie->criticality = NGAP_Criticality_reject;
+ ie->value.present = NGAP_UplinkNonUEAssociatedNRPPaTransportIEs__value_PR_NRPPa_PDU;
+ ie->value.choice.NRPPa_PDU.buf = msg->nrppa_pdu.buf;
+ ie->value.choice.NRPPa_PDU.size = msg->nrppa_pdu.len;
+ }
+
+ // Encode NGAP message
+ uint8_t *buffer = NULL;
+ uint32_t length = 0;
+ if (ngap_gNB_encode_pdu(&pdu, &buffer, &length) < 0) {
+ LOG_E(NGAP, "Failed to encode Uplink Non UE Associated NRPPa Transport\n");
+ ASN_STRUCT_FREE_CONTENTS_ONLY(asn_DEF_NGAP_NGAP_PDU, &pdu);
+ return -1;
+ }
+
+ // Non UE-Associated signalling -> stream = 0
+ LOG_I(NGAP, "Sending ngap_gNB_uplink_non_ue_associated_nrppa_transport over SCTP (assoc_id %d)\n", amf_desc_p->assoc_id);
+ ngap_gNB_itti_send_sctp_data_req(ngap_gNB_instance_p->instance, amf_desc_p->assoc_id, buffer, length, 0);
+ ASN_STRUCT_FREE_CONTENTS_ONLY(asn_DEF_NGAP_NGAP_PDU, &pdu);
+ return 0;
+}
+
+// handle DOWNLINK UE ASSOCIATED NRPPA TRANSPORT (9.2.9.1 of TS 38.413 Version 16.0.0)
+int ngap_gNB_handle_downlink_ue_associated_nrppa_transport(sctp_assoc_t assoc_id, uint32_t stream, NGAP_NGAP_PDU_t *pdu)
+{
+ DevAssert(pdu != NULL);
+ ngap_gNB_amf_data_t *amf_desc_p = NULL;
+
+ if ((amf_desc_p = ngap_gNB_get_AMF(NULL, assoc_id, 0)) == NULL) {
+ NGAP_ERROR("[SCTP %d] Received NRPPa downlink message for non existing AMF context\n", assoc_id);
+ return -1;
+ }
+
+ ngap_gNB_instance_t *ngap_gNB_instance = NULL;
+ ngap_gNB_instance = amf_desc_p->ngap_gNB_instance;
+
+ // Prepare the NGAP message for NRPPA
+ NGAP_DownlinkUEAssociatedNRPPaTransport_t *container = NULL;
+ NGAP_DownlinkUEAssociatedNRPPaTransportIEs_t *ie = NULL;
+
+ // IE: 9.3.1.1 Message Type
+ container = &pdu->choice.initiatingMessage->value.choice.DownlinkUEAssociatedNRPPaTransport;
+
+ // IE: 9.3.3.1 AMF UE NGAP ID
+ uint64_t amf_ue_ngap_id;
+ NGAP_FIND_PROTOCOLIE_BY_ID(NGAP_DownlinkUEAssociatedNRPPaTransportIEs_t,
+ ie,
+ container,
+ NGAP_ProtocolIE_ID_id_AMF_UE_NGAP_ID,
+ true);
+ asn_INTEGER2ulong(&(ie->value.choice.AMF_UE_NGAP_ID), &amf_ue_ngap_id);
+
+ // IE: 9.3.3.2 RAN UE NGAP ID
+ NGAP_RAN_UE_NGAP_ID_t gnb_ue_ngap_id;
+ NGAP_FIND_PROTOCOLIE_BY_ID(NGAP_DownlinkUEAssociatedNRPPaTransportIEs_t,
+ ie,
+ container,
+ NGAP_ProtocolIE_ID_id_RAN_UE_NGAP_ID,
+ true);
+ gnb_ue_ngap_id = ie->value.choice.RAN_UE_NGAP_ID;
+
+ ngap_gNB_ue_context_t *ue_desc_p = NULL;
+ if ((ue_desc_p = ngap_get_ue_context(gnb_ue_ngap_id)) == NULL) {
+ NGAP_ERROR("[SCTP %d] Received NRPPa downlink message for non existing UE context gNB_UE_NGAP_ID: 0x%lx\n",
+ assoc_id,
+ gnb_ue_ngap_id);
+ return -1;
+ }
+
+ // Is it the first outcome of the AMF for this UE ? If so store the amf UE ngap id
+ if (ue_desc_p->amf_ue_ngap_id == 0) {
+ ue_desc_p->amf_ue_ngap_id = amf_ue_ngap_id;
+ } else {
+ // We already have a amf ue ngap id check the received is the same
+ if (ue_desc_p->amf_ue_ngap_id != amf_ue_ngap_id) {
+ NGAP_ERROR("[SCTP %d] Mismatch in AMF UE NGAP ID (0x%lx != 0x%" PRIx64 "\n",
+ assoc_id,
+ amf_ue_ngap_id,
+ (uint64_t)ue_desc_p->amf_ue_ngap_id);
+ return -1;
+ }
+ }
+
+ MessageDef *msg = itti_alloc_new_message(TASK_NGAP, 0, NGAP_DOWNLINKUEASSOCIATEDNRPPA);
+ ngap_downlink_ue_associated_nrppa_t *dl_ue_assoc_nrppa = &NGAP_DOWNLINKUEASSOCIATEDNRPPA(msg);
+
+ dl_ue_assoc_nrppa->amf_ue_ngap_id = amf_ue_ngap_id;
+ dl_ue_assoc_nrppa->gNB_ue_ngap_id = gnb_ue_ngap_id;
+
+ // IE: 9.3.3.13 Routing ID
+ NGAP_FIND_PROTOCOLIE_BY_ID(NGAP_DownlinkUEAssociatedNRPPaTransportIEs_t, ie, container, NGAP_ProtocolIE_ID_id_RoutingID, true);
+ dl_ue_assoc_nrppa->routing_id = create_byte_array(ie->value.choice.RoutingID.size, ie->value.choice.RoutingID.buf);
+
+ // IE: 9.3.3.14 NRPPa-PDU
+ NGAP_FIND_PROTOCOLIE_BY_ID(NGAP_DownlinkUEAssociatedNRPPaTransportIEs_t, ie, container, NGAP_ProtocolIE_ID_id_NRPPa_PDU, true);
+ dl_ue_assoc_nrppa->nrppa_pdu = create_byte_array(ie->value.choice.NRPPa_PDU.size, ie->value.choice.NRPPa_PDU.buf);
+
+ // Forward the NRPPA PDU to NRPPA
+ itti_send_msg_to_task(TASK_NRPPA, ngap_gNB_instance->instance, msg);
+
+ return 0;
+}
+
+// handle DOWNLINK NON UE ASSOCIATED NRPPA TRANSPORT (9.2.9.3 of TS 38.413 Version 16.0.0)
+int ngap_gNB_handle_downlink_non_ue_associated_nrppa_transport(sctp_assoc_t assoc_id, uint32_t stream, NGAP_NGAP_PDU_t *pdu)
+{
+ DevAssert(pdu != NULL);
+ ngap_gNB_amf_data_t *amf_desc_p = NULL;
+
+ if ((amf_desc_p = ngap_gNB_get_AMF(NULL, assoc_id, 0)) == NULL) {
+ NGAP_ERROR("[SCTP %d] Received NRPPa downlink message for non existing AMF context\n", assoc_id);
+ return -1;
+ }
+
+ ngap_gNB_instance_t *ngap_gNB_instance = NULL;
+ ngap_gNB_instance = amf_desc_p->ngap_gNB_instance;
+
+ MessageDef *msg = itti_alloc_new_message(TASK_NGAP, 0, NGAP_DOWNLINKNONUEASSOCIATEDNRPPA);
+ ngap_downlink_non_ue_associated_nrppa_t *dl_non_ue_assoc_nrppa = &NGAP_DOWNLINKNONUEASSOCIATEDNRPPA(msg);
+
+ // Prepare the NGAP message to forward to NRPPA
+ NGAP_DownlinkNonUEAssociatedNRPPaTransport_t *container;
+ NGAP_DownlinkNonUEAssociatedNRPPaTransportIEs_t *ie;
+
+ // IE: 9.3.1.1 Message Type
+ container = &pdu->choice.initiatingMessage->value.choice.DownlinkNonUEAssociatedNRPPaTransport;
+
+ // IE: 9.3.3.13 Routing ID
+ NGAP_FIND_PROTOCOLIE_BY_ID(NGAP_DownlinkNonUEAssociatedNRPPaTransportIEs_t, ie, container, NGAP_ProtocolIE_ID_id_RoutingID, true);
+ dl_non_ue_assoc_nrppa->routing_id = create_byte_array(ie->value.choice.RoutingID.size, ie->value.choice.RoutingID.buf);
+
+ // IE: 9.3.3.14 NRPPa-PDU
+ NGAP_FIND_PROTOCOLIE_BY_ID(NGAP_DownlinkNonUEAssociatedNRPPaTransportIEs_t, ie, container, NGAP_ProtocolIE_ID_id_NRPPa_PDU, true);
+ dl_non_ue_assoc_nrppa->nrppa_pdu = create_byte_array(ie->value.choice.NRPPa_PDU.size, ie->value.choice.NRPPa_PDU.buf);
+
+ itti_send_msg_to_task(TASK_NRPPA, ngap_gNB_instance->instance, msg);
+
+ return 0;
+}
diff --git a/openair3/NGAP/ngap_gNB_NRPPa_transport_procedures.h b/openair3/NGAP/ngap_gNB_NRPPa_transport_procedures.h
new file mode 100644
index 0000000000..a180888029
--- /dev/null
+++ b/openair3/NGAP/ngap_gNB_NRPPa_transport_procedures.h
@@ -0,0 +1,37 @@
+/*
+ * Licensed to the OpenAirInterface (OAI) Software Alliance under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The OpenAirInterface Software Alliance licenses this file to You under
+ * the OAI Public License, Version 1.1 (the "License"); you may not use this file
+ * except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.openairinterface.org/?page_id=698
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *-------------------------------------------------------------------------------
+ * For more information about the OpenAirInterface (OAI) Software Alliance:
+ * contact@openairinterface.org
+ */
+
+#ifndef NGAP_GNB_NRPPA_PROCEDURES_H_
+#define NGAP_GNB_NRPPA_PROCEDURES_H_
+
+// UPLINK UE ASSOCIATED NRPPA TRANSPORT (9.2.9.2 of TS 38.413 Version 16.0.0)
+int ngap_gNB_uplink_ue_associated_nrppa_transport(instance_t instance, const ngap_uplink_ue_associated_nrppa_t *msg);
+
+// UPLINK NON UE ASSOCIATED NRPPA TRANSPORT (9.2.9.4 of TS 38.413 Version 16.0.0)
+int ngap_gNB_uplink_non_ue_associated_nrppa_transport(instance_t instance, const ngap_uplink_non_ue_associated_nrppa_t *msg);
+
+// DOWNLINK UE ASSOCIATED NRPPA TRANSPORT (9.2.9.1 of TS 38.413 Version 16.0.0)
+int ngap_gNB_handle_downlink_ue_associated_nrppa_transport(sctp_assoc_t assoc_id, uint32_t stream, NGAP_NGAP_PDU_t *pdu);
+
+// DOWNLINK UE ASSOCIATED NRPPA TRANSPORT (9.2.9.3 of TS 38.413 Version 16.0.0)
+int ngap_gNB_handle_downlink_non_ue_associated_nrppa_transport(sctp_assoc_t assoc_id, uint32_t stream, NGAP_NGAP_PDU_t *pdu);
+
+#endif /* NGAP_GNB_NRPPA_PROCEDURES_H_ */
diff --git a/openair3/NGAP/ngap_gNB_decoder.c b/openair3/NGAP/ngap_gNB_decoder.c
index 43110e9037..3993f8aa72 100644
--- a/openair3/NGAP/ngap_gNB_decoder.c
+++ b/openair3/NGAP/ngap_gNB_decoder.c
@@ -112,6 +112,18 @@ static int ngap_gNB_decode_initiating_message(NGAP_NGAP_PDU_t *pdu) {
NGAP_INFO("DL RAN Status Transfer initiating message\n");
break;
+ case NGAP_ProcedureCode_id_DownlinkUEAssociatedNRPPaTransport:
+ res = asn_encode_to_new_buffer(NULL, ATS_CANONICAL_XER, &asn_DEF_NGAP_NGAP_PDU, pdu);
+ free(res.buffer);
+ NGAP_INFO("DL UE Associated NRPPA Transport initiating message\n");
+ break;
+
+ case NGAP_ProcedureCode_id_DownlinkNonUEAssociatedNRPPaTransport:
+ res = asn_encode_to_new_buffer(NULL, ATS_CANONICAL_XER, &asn_DEF_NGAP_NGAP_PDU, pdu);
+ free(res.buffer);
+ NGAP_INFO("DL NON UE Associated NRPPA Transport initiating message\n");
+ break;
+
default:
NGAP_ERROR("Unknown procedure ID (%d) for initiating message\n",
(int)pdu->choice.initiatingMessage->procedureCode);
diff --git a/openair3/NGAP/ngap_gNB_defs.h b/openair3/NGAP/ngap_gNB_defs.h
index 1a1e5768ff..b7c5dc3f64 100644
--- a/openair3/NGAP/ngap_gNB_defs.h
+++ b/openair3/NGAP/ngap_gNB_defs.h
@@ -161,6 +161,8 @@ struct ngap_gNB_instance_s;
/* This structure describes association of a gNB to a AMF */
typedef struct ngap_gNB_amf_data_s {
+ long t_reconnect; // ITTI timer id (or equivalent)
+
/* AMF descriptors tree, ordered by sctp assoc id */
RB_ENTRY(ngap_gNB_amf_data_s) entry;
diff --git a/openair3/NGAP/ngap_gNB_encoder.c b/openair3/NGAP/ngap_gNB_encoder.c
index ff318ed184..801ce95d42 100644
--- a/openair3/NGAP/ngap_gNB_encoder.c
+++ b/openair3/NGAP/ngap_gNB_encoder.c
@@ -56,7 +56,9 @@ static inline int ngap_gNB_encode_initiating(NGAP_NGAP_PDU_t *pdu, uint8_t **buf
NGAP_ProcedureCode_id_UplinkRANStatusTransfer,
NGAP_ProcedureCode_id_HandoverPreparation,
NGAP_ProcedureCode_id_HandoverCancel,
- NGAP_ProcedureCode_id_HandoverNotification};
+ NGAP_ProcedureCode_id_HandoverNotification,
+ NGAP_ProcedureCode_id_UplinkUEAssociatedNRPPaTransport,
+ NGAP_ProcedureCode_id_UplinkNonUEAssociatedNRPPaTransport};
int i;
for (i = 0; i < sizeofArray(tmp); i++)
if (pdu->choice.initiatingMessage->procedureCode == tmp[i])
diff --git a/openair3/NGAP/ngap_gNB_handlers.c b/openair3/NGAP/ngap_gNB_handlers.c
index 9113f850ca..ddd39b2535 100644
--- a/openair3/NGAP/ngap_gNB_handlers.c
+++ b/openair3/NGAP/ngap_gNB_handlers.c
@@ -50,6 +50,7 @@
#include "ngap_gNB_pdu_session_management.h"
#include "ngap_gNB_nas_procedures.h"
#include "ngap_gNB_paging.h"
+#include "ngap_gNB_NRPPa_transport_procedures.h"
#include "ngap_gNB_trace.h"
#include "ngap_gNB_ue_context.h"
#include "ngap_messages_types.h"
@@ -77,6 +78,8 @@ void ngap_handle_ng_setup_message(ngap_gNB_amf_data_t *amf_desc_p, int sctp_shut
/* Decrease associated AMF number */
amf_desc_p->ngap_gNB_instance->ngap_amf_associated_nb --;
}
+ /* Release UE context and start reconnection process*/
+ ngap_release_ues_for_amf(amf_desc_p);
/* If there are no more associated AMF, inform gNB app */
if (amf_desc_p->ngap_gNB_instance->ngap_amf_associated_nb == 0) {
@@ -1499,10 +1502,10 @@ const ngap_message_decoded_callback ngap_messages_callback[][3] = {
{0, 0, 0}, /* CellTrafficTrace */
{ngap_gNB_handle_deactivate_trace, 0, 0}, /* DeactivateTrace */
{ngap_gNB_handle_nas_downlink, 0, 0}, /* DownlinkNASTransport */
- {0, 0, 0}, /* DownlinkNonUEAssociatedNRPPaTransport */
+ {ngap_gNB_handle_downlink_non_ue_associated_nrppa_transport, 0, 0}, /* DownlinkNonUEAssociatedNRPPaTransport */
{0, 0, 0}, /* DownlinkRANConfigurationTransfer */
{ngap_gNB_handle_dl_ran_status_transfer, 0, 0}, /* DownlinkRANStatusTransfer */
- {0, 0, 0}, /* DownlinkUEAssociatedNRPPaTransport */
+ {ngap_gNB_handle_downlink_ue_associated_nrppa_transport, 0, 0}, /* DownlinkUEAssociatedNRPPaTransport */
{ngap_gNB_handle_error_indication, 0, 0}, /* ErrorIndication */
{0, ngap_gNB_handle_handover_cancel_ack, 0}, /* HandoverCancel */
{0, 0, 0}, /* HandoverNotification */
diff --git a/openair3/NGAP/ngap_gNB_nas_procedures.c b/openair3/NGAP/ngap_gNB_nas_procedures.c
index 2d4bd3eefa..9e341494c6 100644
--- a/openair3/NGAP/ngap_gNB_nas_procedures.c
+++ b/openair3/NGAP/ngap_gNB_nas_procedures.c
@@ -59,7 +59,7 @@
#include "s1ap_messages_types.h"
#include "xer_encoder.h"
#include "ds/byte_array.h"
-
+#include "intertask_interface.h"
/** @brief Selects the AMF instance for a given UE based on identity information.
* It attempts to select an AMF using the following prioritized criteria:
* 1. GUAMI, if provided and valid (via Region ID, Set ID, Pointer).
diff --git a/openair3/NGAP/ngap_gNB_ue_context.c b/openair3/NGAP/ngap_gNB_ue_context.c
index 994271d822..e50726380f 100644
--- a/openair3/NGAP/ngap_gNB_ue_context.c
+++ b/openair3/NGAP/ngap_gNB_ue_context.c
@@ -34,6 +34,8 @@
#include "common/utils/T/T.h"
#include "ngap_common.h"
#include "tree.h"
+#include "intertask_interface.h"
+#define SCTP_LOOKUP_TIMER_TIMEOUT_SEC 30
/* Tree of UE ordered by gNB_ue_ngap_id's
* NO INSTANCE, the 32 bits id is large enough to handle all UEs, regardless the cell, gNB, ...
@@ -92,3 +94,31 @@ struct ngap_gNB_ue_context_s *ngap_detach_ue_context(uint32_t gNB_ue_ngap_id)
RB_REMOVE(ngap_ue_map, &ngap_ue_head, tmp);
return tmp;
}
+
+void ngap_release_ues_for_amf(ngap_gNB_amf_data_t *amf_desc_p)
+{
+ /* Release all UE contexts for this AMF */
+ ngap_gNB_ue_context_t *ue = NULL;
+ ngap_gNB_ue_context_t *next = NULL;
+ RB_FOREACH_SAFE(ue, ngap_ue_map, &ngap_ue_head, next) {
+ if (ue->amf_ref == amf_desc_p) {
+ LOG_I(NGAP, "Releasing UE context: gNB UE NGAP ID: %u | AMF UE NGAP ID: %lu\n", ue->gNB_ue_ngap_id, ue->amf_ue_ngap_id);
+ MessageDef *msg_p = itti_alloc_new_message(TASK_NGAP, 0, NGAP_UE_CONTEXT_RELEASE_COMMAND);
+ NGAP_UE_CONTEXT_RELEASE_COMMAND(msg_p).gNB_ue_ngap_id = ue->gNB_ue_ngap_id;
+ itti_send_msg_to_task(TASK_RRC_GNB, amf_desc_p->ngap_gNB_instance->instance, msg_p);
+ }
+ }
+ /* Reset AMF connection and set reconnect timer */
+ /* SCTP lookup timer */
+ long tid;
+ int rc = timer_setup(SCTP_LOOKUP_TIMER_TIMEOUT_SEC,
+ 0,
+ TASK_NGAP,
+ amf_desc_p->ngap_gNB_instance->instance,
+ TIMER_ONE_SHOT,
+ amf_desc_p,
+ &tid);
+ if (rc == 0) {
+ amf_desc_p->t_reconnect = tid;
+ }
+}
diff --git a/openair3/NGAP/ngap_gNB_ue_context.h b/openair3/NGAP/ngap_gNB_ue_context.h
index 8053e8f8c6..1ca458968f 100644
--- a/openair3/NGAP/ngap_gNB_ue_context.h
+++ b/openair3/NGAP/ngap_gNB_ue_context.h
@@ -74,6 +74,7 @@ typedef struct ngap_gNB_ue_context_s {
} ngap_gNB_ue_context_t;
void ngap_store_ue_context(const ngap_gNB_ue_context_t *ue_desc_p);
+void ngap_release_ues_for_amf(ngap_gNB_amf_data_t *amf_desc_p);
ngap_gNB_ue_context_t *ngap_get_ue_context(uint32_t gNB_ue_ngap_id);
ngap_gNB_ue_context_t *ngap_get_ue_context_from_amf_ue_ngap_id(uint32_t amf_ue_ngap_id);
diff --git a/openair3/NRPPA/CMakeLists.txt b/openair3/NRPPA/CMakeLists.txt
index 613cbfc3ce..45f0964667 100644
--- a/openair3/NRPPA/CMakeLists.txt
+++ b/openair3/NRPPA/CMakeLists.txt
@@ -1,5 +1,15 @@
add_subdirectory(MESSAGES)
-add_executable(test_nrppa ${OPENAIR3_DIR}/NRPPA/test_nrppa.c )
-target_link_libraries(test_nrppa asn1_nrppa)
-
+add_library(nrppa
+ nrppa_gNB.c
+ nrppa_gNB_config.c
+ nrppa_gNB_handlers.c
+ nrppa_gNB_decoder.c
+ nrppa_gNB_ue_context.c
+ nrppa_gNB_location_information_transfer.c
+ nrppa_gNB_encoder.c
+ nrppa_gNB_measurement_information_transfer.c
+ )
+
+target_link_libraries(nrppa PUBLIC asn1_nrppa)
+target_link_libraries(nrppa PRIVATE asn1_lte_rrc_hdrs asn1_nr_rrc_hdrs)
diff --git a/openair3/NRPPA/nrppa_common.h b/openair3/NRPPA/nrppa_common.h
new file mode 100644
index 0000000000..b7c613e77a
--- /dev/null
+++ b/openair3/NRPPA/nrppa_common.h
@@ -0,0 +1,62 @@
+/*
+ * Licensed to the OpenAirInterface (OAI) Software Alliance under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The OpenAirInterface Software Alliance licenses this file to You under
+ * the OAI Public License, Version 1.1 (the "License"); you may not use this file
+ * except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.openairinterface.org/?page_id=698
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *-------------------------------------------------------------------------------
+ * For more information about the OpenAirInterface (OAI) Software Alliance:
+ * contact@openairinterface.org
+ */
+
+#ifndef NRPPA_COMMON_H_
+#define NRPPA_COMMON_H_
+
+#include "oai_asn1.h"
+#include "common/utils/LOG/log.h"
+#include "ds/byte_array.h"
+#include "nrppa_includes.h"
+
+#define NRPPA_FIND_PROTOCOLIE_BY_ID(IE_TYPE, ie, container, IE_ID, mandatory) \
+ do { \
+ IE_TYPE **ptr; \
+ ie = NULL; \
+ for (ptr = container->protocolIEs.list.array; ptr < &container->protocolIEs.list.array[container->protocolIEs.list.count]; \
+ ptr++) { \
+ if ((*ptr)->id == IE_ID) { \
+ ie = *ptr; \
+ break; \
+ } \
+ } \
+ if (ie == NULL) { \
+ if (mandatory) { \
+ AssertFatal(false, "NRPPA_FIND_PROTOCOLIE_BY_ID ie is NULL (searching for ie: %ld)\n", IE_ID); \
+ } else { \
+ LOG_I(NRPPA, "NRPPA_FIND_PROTOCOLIE_BY_ID ie is NULL (searching for ie: %ld)\n", IE_ID); \
+ } \
+ } \
+ } while (0); \
+ if (mandatory && !ie) \
+ return -1
+
+// gnb and ue related info in NRPPA message
+typedef struct nrppa_gnb_ue_info_s {
+ instance_t instance;
+ int32_t gNB_ue_ngap_id;
+ int64_t amf_ue_ngap_id;
+ byte_array_t routing_id;
+} nrppa_gnb_ue_info_t;
+
+typedef int (*nrppa_message_decoded_callback)(nrppa_gnb_ue_info_t *nrppa_msg_info, const NRPPA_NRPPA_PDU_t *pdu);
+
+#endif /* NRPPA_COMMON_H_ */
diff --git a/openair3/NRPPA/nrppa_gNB.c b/openair3/NRPPA/nrppa_gNB.c
new file mode 100644
index 0000000000..a561c026fd
--- /dev/null
+++ b/openair3/NRPPA/nrppa_gNB.c
@@ -0,0 +1,92 @@
+/*
+ * Licensed to the OpenAirInterface (OAI) Software Alliance under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The OpenAirInterface Software Alliance licenses this file to You under
+ * the OAI Public License, Version 1.1 (the "License"); you may not use this file
+ * except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.openairinterface.org/?page_id=698
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *-------------------------------------------------------------------------------
+ * For more information about the OpenAirInterface (OAI) Software Alliance:
+ * contact@openairinterface.org
+ */
+
+#include "tree.h"
+#include "queue.h"
+
+#include "intertask_interface.h"
+
+#include "assertions.h"
+#include "conversions.h"
+
+#include "nrppa_gNB.h"
+#include "nrppa_common.h"
+#include "nrppa_gNB_handlers.h"
+#include "nrppa_gNB_location_information_transfer.h"
+#include "nrppa_gNB_measurement_information_transfer.h"
+
+void nrppa_gNB_init(void)
+{
+ LOG_I(NRPPA, "Starting NRPPA layer\n");
+ itti_mark_task_ready(TASK_NRPPA);
+}
+
+void *nrppa_gNB_process_itti_msg(void *notUsed)
+{
+ MessageDef *received_msg = NULL;
+ int result;
+ itti_receive_msg(TASK_NRPPA, &received_msg);
+ if (received_msg) {
+ instance_t instance = ITTI_MSG_DESTINATION_INSTANCE(received_msg);
+ LOG_I(NRPPA, "Received message %s\n", ITTI_MSG_NAME(received_msg));
+ switch (ITTI_MSG_ID(received_msg)) {
+ case TERMINATE_MESSAGE:
+ LOG_W(NRPPA, " *** Exiting NRPPA thread\n");
+ itti_exit_task();
+ break;
+ case NGAP_DOWNLINKUEASSOCIATEDNRPPA:
+ nrppa_handle_downlink_ue_associated_nrppa_transport(instance, &NGAP_DOWNLINKUEASSOCIATEDNRPPA(received_msg));
+ break;
+ case NGAP_DOWNLINKNONUEASSOCIATEDNRPPA:
+ nrppa_handle_downlink_non_ue_associated_nrppa_transport(instance, &NGAP_DOWNLINKNONUEASSOCIATEDNRPPA(received_msg));
+ break;
+ case NRPPA_TRP_INFORMATION_RESP:
+ nrppa_gNB_trp_information_response(instance, received_msg);
+ break;
+ case NRPPA_POSITIONING_INFORMATION_RESP:
+ nrppa_gNB_positioning_information_response(instance, received_msg);
+ break;
+ case NRPPA_POSITIONING_ACTIVATION_RESP:
+ nrppa_gNB_positioning_activation_response(instance, received_msg);
+ break;
+ case NRPPA_MEASUREMENT_RESP:
+ nrppa_gNB_measurement_response(instance, received_msg);
+ break;
+ default:
+ LOG_E(NRPPA, "Received unhandled message: %d:%s\n", ITTI_MSG_ID(received_msg), ITTI_MSG_NAME(received_msg));
+ break;
+ }
+ result = itti_free(ITTI_MSG_ORIGIN_ID(received_msg), received_msg);
+ AssertFatal(result == EXIT_SUCCESS, "Failed to free memory (%d)!\n", result);
+ }
+ return NULL;
+}
+
+void *nrppa_gNB_task(void *arg)
+{
+ nrppa_gNB_init();
+
+ while (1) {
+ (void)nrppa_gNB_process_itti_msg(NULL);
+ }
+
+ return NULL;
+}
diff --git a/openair3/NRPPA/nrppa_gNB.h b/openair3/NRPPA/nrppa_gNB.h
new file mode 100644
index 0000000000..628cfc4587
--- /dev/null
+++ b/openair3/NRPPA/nrppa_gNB.h
@@ -0,0 +1,32 @@
+/*
+ * Licensed to the OpenAirInterface (OAI) Software Alliance under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The OpenAirInterface Software Alliance licenses this file to You under
+ * the OAI Public License, Version 1.1 (the "License"); you may not use this file
+ * except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.openairinterface.org/?page_id=698
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *-------------------------------------------------------------------------------
+ * For more information about the OpenAirInterface (OAI) Software Alliance:
+ * contact@openairinterface.org
+ */
+
+#include
+#include
+
+#ifndef NRPPA_GNB_H_
+#define NRPPA_GNB_H_
+
+void nrppa_gNB_init(void);
+void *nrppa_gNB_process_itti_msg(void *notUsed);
+void *nrppa_gNB_task(void *arg);
+
+#endif /* NRPPA_GNB_H_ */
diff --git a/openair3/NRPPA/nrppa_gNB_config.c b/openair3/NRPPA/nrppa_gNB_config.c
new file mode 100644
index 0000000000..dc0590f603
--- /dev/null
+++ b/openair3/NRPPA/nrppa_gNB_config.c
@@ -0,0 +1,84 @@
+/*
+ * Licensed to the OpenAirInterface (OAI) Software Alliance under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The OpenAirInterface Software Alliance licenses this file to You under
+ * the OAI Public License, Version 1.1 (the "License"); you may not use this file
+ * except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.openairinterface.org/?page_id=698
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *-------------------------------------------------------------------------------
+ * For more information about the OpenAirInterface (OAI) Software Alliance:
+ * contact@openairinterface.org
+ */
+
+#include "nrppa_gNB_config.h"
+#include "assertions.h"
+#include "openair1/PHY/defs_nr_common.h"
+#include "openair1/PHY/defs_gNB.h"
+#include "common/ran_context.h"
+#include "positioning_nr_paramdef.h"
+
+positioning_config_t RCconfig_nr_positioning(void)
+{
+ positioning_config_t positioning_config = {0};
+ paramdef_t positioning_params_desc[] = POSITIONING_PARAMS_DESC;
+ int num_params = sizeofArray(positioning_params_desc);
+ GET_PARAMS_LIST(POSITIONING_ParamList, POSITIONING_Params, POSITIONING_PARAMS_DESC, CONFIG_STRING_POSITIONING_CONFIG, NULL);
+
+ if (POSITIONING_ParamList.numelt > 0) {
+ paramdef_t *params = POSITIONING_ParamList.paramarray[0];
+
+ uint8_t num_trp = *gpd(params, num_params, CONFIG_STRING_POSITIONING_NUM_TRPS)->uptr;
+ if (num_trp == 0) {
+ LOG_E(NR_PHY, "No TRP configuration found..!!!\n");
+ return positioning_config;
+ } else if (num_trp > MAX_NUM_TRPs) {
+ AssertFatal(false, "Exceeded MAX number of TRPs\n");
+ }
+
+ uint8_t num_ids = gpd(params, num_params, CONFIG_STRING_POSITIONING_TRP_IDS_LIST)->numelt;
+ uint8_t num_x = gpd(params, num_params, CONFIG_STRING_POSITIONING_TRP_X_AXIS_LIST)->numelt;
+ uint8_t num_y = gpd(params, num_params, CONFIG_STRING_POSITIONING_TRP_Y_AXIS_LIST)->numelt;
+ uint8_t num_z = gpd(params, num_params, CONFIG_STRING_POSITIONING_TRP_Z_AXIS_LIST)->numelt;
+ uint8_t num_unit = gpd(params, num_params, CONFIG_STRING_POSITIONING_TRP_UNIT_LIST)->numelt;
+
+ if (num_trp != num_ids || num_trp != num_x || num_trp != num_y || num_trp != num_z || num_trp != num_unit) {
+ AssertFatal(false, "Mismatch in the number of TRPs with the number of ids, x-axis, y-axis, z-axis, units\n");
+ }
+
+ positioning_config.num_trp = num_trp;
+ for (int l = 0; l < num_trp; l++) {
+ positioning_config.trps[l].id = gpd(params, num_params, CONFIG_STRING_POSITIONING_TRP_IDS_LIST)->uptr[l];
+ positioning_config.trps[l].x_axis = gpd(params, num_params, CONFIG_STRING_POSITIONING_TRP_X_AXIS_LIST)->uptr[l];
+ positioning_config.trps[l].y_axis = gpd(params, num_params, CONFIG_STRING_POSITIONING_TRP_Y_AXIS_LIST)->uptr[l];
+ positioning_config.trps[l].z_axis = gpd(params, num_params, CONFIG_STRING_POSITIONING_TRP_Z_AXIS_LIST)->uptr[l];
+ positioning_config.trps[l].unit = gpd(params, num_params, CONFIG_STRING_POSITIONING_TRP_UNIT_LIST)->uptr[l];
+ }
+ } else {
+ LOG_I(NR_PHY, "No " CONFIG_STRING_POSITIONING_CONFIG " configuration found..!!\n");
+ }
+ return positioning_config;
+}
+
+void dump_positioning_config(const positioning_config_t *positioning_config)
+{
+ uint8_t num_trp = positioning_config->num_trp;
+ LOG_I(NR_PHY, "-----------------------------------------\n");
+ LOG_I(NR_PHY, "Positioning Config\n");
+ LOG_I(NR_PHY, "-----------------------------------------\n");
+ LOG_I(NR_PHY, "Number of TRPs \t\t%d\n", num_trp);
+ for (int i = 0; i < num_trp; i++) {
+ LOG_I(NR_PHY, "X-axis of TRP ID %d \t\t%d\n", positioning_config->trps[i].id, positioning_config->trps[i].x_axis);
+ LOG_I(NR_PHY, "Y-axis of TRP ID %d \t\t%d\n", positioning_config->trps[i].id, positioning_config->trps[i].y_axis);
+ LOG_I(NR_PHY, "Z-axis of TRP ID %d \t\t%d\n", positioning_config->trps[i].id, positioning_config->trps[i].z_axis);
+ }
+ LOG_I(NR_PHY, "-----------------------------------------\n");
+}
diff --git a/openair3/NRPPA/nrppa_gNB_config.h b/openair3/NRPPA/nrppa_gNB_config.h
new file mode 100644
index 0000000000..3ae710a62c
--- /dev/null
+++ b/openair3/NRPPA/nrppa_gNB_config.h
@@ -0,0 +1,30 @@
+/*
+ * Licensed to the OpenAirInterface (OAI) Software Alliance under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The OpenAirInterface Software Alliance licenses this file to You under
+ * the OAI Public License, Version 1.1 (the "License"); you may not use this file
+ * except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.openairinterface.org/?page_id=698
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *-------------------------------------------------------------------------------
+ * For more information about the OpenAirInterface (OAI) Software Alliance:
+ * contact@openairinterface.org
+ */
+
+#ifndef GNB_CONFIG_POSITIONING_H_
+#define GNB_CONFIG_POSITIONING_H_
+
+#include "openair1/PHY/defs_nr_common.h"
+
+positioning_config_t RCconfig_nr_positioning(void);
+void dump_positioning_config(const positioning_config_t *positioning_config);
+
+#endif /* GNB_CONFIG_POSITIONING_H_ */
diff --git a/openair3/NRPPA/nrppa_gNB_decoder.c b/openair3/NRPPA/nrppa_gNB_decoder.c
new file mode 100644
index 0000000000..756871bc59
--- /dev/null
+++ b/openair3/NRPPA/nrppa_gNB_decoder.c
@@ -0,0 +1,130 @@
+/*
+ * Licensed to the OpenAirInterface (OAI) Software Alliance under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The OpenAirInterface Software Alliance licenses this file to You under
+ * the OAI Public License, Version 1.1 (the "License"); you may not use this file
+ * except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.openairinterface.org/?page_id=698
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *-------------------------------------------------------------------------------
+ * For more information about the OpenAirInterface (OAI) Software Alliance:
+ * contact@openairinterface.org
+ */
+
+#include "assertions.h"
+#include "intertask_interface.h"
+#include "nrppa_common.h"
+#include "nrppa_gNB_decoder.h"
+
+static int nrppa_gNB_decode_initiating_message(NRPPA_NRPPA_PDU_t *pdu)
+{
+ asn_encode_to_new_buffer_result_t res = {NULL, {0, NULL, NULL}};
+ DevAssert(pdu != NULL);
+
+ switch (pdu->choice.initiatingMessage->procedureCode) {
+ case NRPPA_ProcedureCode_id_tRPInformationExchange: // TRPInformationRequest
+ res = asn_encode_to_new_buffer(NULL, ATS_CANONICAL_XER, &asn_DEF_NRPPA_NRPPA_PDU, pdu);
+ LOG_I(NRPPA, "TRP Information Request initiating message\n");
+ free(res.buffer);
+ break;
+ case NRPPA_ProcedureCode_id_positioningInformationExchange: // PositioningInformationRequest
+ res = asn_encode_to_new_buffer(NULL, ATS_CANONICAL_XER, &asn_DEF_NRPPA_NRPPA_PDU, pdu);
+ LOG_I(NRPPA, "Positioning Information Request initiating message\n");
+ free(res.buffer);
+ break;
+ case NRPPA_ProcedureCode_id_positioningActivation:
+ res = asn_encode_to_new_buffer(NULL, ATS_CANONICAL_XER, &asn_DEF_NRPPA_NRPPA_PDU, pdu);
+ LOG_I(NRPPA, "Positioning Activation initiating message\n");
+ free(res.buffer);
+ break;
+ case NRPPA_ProcedureCode_id_Measurement:
+ res = asn_encode_to_new_buffer(NULL, ATS_CANONICAL_XER, &asn_DEF_NRPPA_NRPPA_PDU, pdu);
+ LOG_I(NRPPA, "Positioning Measurement initiating message\n");
+ free(res.buffer);
+ break;
+ default:
+ AssertFatal(false, "Unknown procedure ID (%d) for initiating message\n", (int)pdu->choice.initiatingMessage->procedureCode);
+ return -1;
+ }
+ return 0;
+}
+
+static int nrppa_gNB_decode_successful_outcome(NRPPA_NRPPA_PDU_t *pdu)
+{
+ asn_encode_to_new_buffer_result_t res = {NULL, {0, NULL, NULL}};
+ DevAssert(pdu != NULL);
+
+ switch (pdu->choice.successfulOutcome->procedureCode) {
+ case NRPPA_ProcedureCode_id_tRPInformationExchange:
+ res = asn_encode_to_new_buffer(NULL, ATS_CANONICAL_XER, &asn_DEF_NRPPA_NRPPA_PDU, pdu);
+ LOG_I(NRPPA, "TRP Information Response successfull outcome message\n");
+ free(res.buffer);
+ break;
+
+ default:
+ AssertFatal(false,
+ "Unknown procedure ID (%d) for successfull outcome message\n",
+ (int)pdu->choice.initiatingMessage->procedureCode);
+ return -1;
+ }
+ return 0;
+}
+
+static int nrppa_gNB_decode_unsuccessful_outcome(NRPPA_NRPPA_PDU_t *pdu)
+{
+ asn_encode_to_new_buffer_result_t res = {NULL, {0, NULL, NULL}};
+ DevAssert(pdu != NULL);
+
+ switch (pdu->choice.unsuccessfulOutcome->procedureCode) {
+ case NRPPA_ProcedureCode_id_tRPInformationExchange:
+ res = asn_encode_to_new_buffer(NULL, ATS_CANONICAL_XER, &asn_DEF_NRPPA_NRPPA_PDU, pdu);
+ LOG_I(NRPPA, "TRP Information Failure unsuccessfull outcome message\n");
+ free(res.buffer);
+ break;
+
+ default:
+ AssertFatal(false,
+ "Unknown procedure ID (%d) for unsuccessfull outcome message\n",
+ (int)pdu->choice.initiatingMessage->procedureCode);
+ return -1;
+ }
+ return 0;
+}
+
+int nrppa_gNB_decode_pdu(NRPPA_NRPPA_PDU_t *pdu, const uint8_t *const buffer, const uint32_t length)
+{
+ asn_dec_rval_t dec_ret;
+ DevAssert(pdu != NULL);
+ DevAssert(buffer != NULL);
+ asn_codec_ctx_t st = {.max_stack_size = 100 * 1000}; // if we enable asn1c debug the stack size become large
+ dec_ret = aper_decode(&st, &asn_DEF_NRPPA_NRPPA_PDU, (void **)&pdu, buffer, length, 0, 0);
+ if (dec_ret.code != RC_OK) {
+ LOG_E(NRPPA, "Failed to decode pdu\n");
+ return -1;
+ }
+
+ switch (pdu->present) {
+ case NRPPA_NRPPA_PDU_PR_initiatingMessage:
+ return nrppa_gNB_decode_initiating_message(pdu);
+
+ case NRPPA_NRPPA_PDU_PR_successfulOutcome:
+ return nrppa_gNB_decode_successful_outcome(pdu);
+
+ case NRPPA_NRPPA_PDU_PR_unsuccessfulOutcome:
+ return nrppa_gNB_decode_unsuccessful_outcome(pdu);
+
+ default:
+ LOG_I(NRPPA, "Unknown presence (%d) or not implemented\n", (int)pdu->present);
+ break;
+ }
+
+ return -1;
+}
diff --git a/openair3/NRPPA/nrppa_gNB_decoder.h b/openair3/NRPPA/nrppa_gNB_decoder.h
new file mode 100644
index 0000000000..668208b8a5
--- /dev/null
+++ b/openair3/NRPPA/nrppa_gNB_decoder.h
@@ -0,0 +1,30 @@
+/*
+ * Licensed to the OpenAirInterface (OAI) Software Alliance under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The OpenAirInterface Software Alliance licenses this file to You under
+ * the OAI Public License, Version 1.1 (the "License"); you may not use this file
+ * except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.openairinterface.org/?page_id=698
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *-------------------------------------------------------------------------------
+ * For more information about the OpenAirInterface (OAI) Software Alliance:
+ * contact@openairinterface.org
+ */
+
+#include "nrppa_common.h"
+
+#ifndef NRPPA_GNB_DECODER_H_
+#define NRPPA_GNB_DECODER_H_
+
+int nrppa_gNB_decode_pdu(NRPPA_NRPPA_PDU_t *pdu, const uint8_t *const buffer, const uint32_t length)
+ __attribute__((warn_unused_result));
+
+#endif /* NRPPA_GNB_DECODER_H_ */
diff --git a/openair3/NRPPA/nrppa_gNB_encoder.c b/openair3/NRPPA/nrppa_gNB_encoder.c
new file mode 100644
index 0000000000..9ac0c4ecb0
--- /dev/null
+++ b/openair3/NRPPA/nrppa_gNB_encoder.c
@@ -0,0 +1,135 @@
+/*
+ * Licensed to the OpenAirInterface (OAI) Software Alliance under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The OpenAirInterface Software Alliance licenses this file to You under
+ * the OAI Public License, Version 1.1 (the "License"); you may not use this file
+ * except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.openairinterface.org/?page_id=698
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *-------------------------------------------------------------------------------
+ * For more information about the OpenAirInterface (OAI) Software Alliance:
+ * contact@openairinterface.org
+ */
+
+#include
+#include
+#include
+#include "nrppa_common.h"
+#include "nrppa_gNB_encoder.h"
+
+static inline int nrppa_gNB_encode_initiating(NRPPA_NRPPA_PDU_t *pdu, uint8_t **buffer, uint32_t *len)
+{
+ DevAssert(pdu != NULL);
+
+ const NRPPA_ProcedureCode_t tmp[] = {NRPPA_ProcedureCode_id_positioningInformationExchange,
+ NRPPA_ProcedureCode_id_positioningActivation,
+ NRPPA_ProcedureCode_id_positioningInformationUpdate,
+ NRPPA_ProcedureCode_id_positioningDeactivation,
+ NRPPA_ProcedureCode_id_tRPInformationExchange,
+ NRPPA_ProcedureCode_id_Measurement,
+ NRPPA_ProcedureCode_id_MeasurementReport,
+ NRPPA_ProcedureCode_id_MeasurementFailureIndication,
+ NRPPA_ProcedureCode_id_MeasurementAbort,
+ NRPPA_ProcedureCode_id_MeasurementUpdate};
+
+ int i;
+ for (i = 0; i < sizeofArray(tmp); i++)
+ if (pdu->choice.initiatingMessage->procedureCode == tmp[i])
+ break;
+ if (i == sizeofArray(tmp)) {
+ LOG_E(NRPPA, "Unknown procedure ID (%d) for initiating message\n", (int)pdu->choice.initiatingMessage->procedureCode);
+ return -1;
+ }
+
+ asn_encode_to_new_buffer_result_t res = asn_encode_to_new_buffer(NULL, ATS_ALIGNED_CANONICAL_PER, &asn_DEF_NRPPA_NRPPA_PDU, pdu);
+ AssertFatal(res.result.encoded > 0, "failed to encode NRPPA msg\n");
+ *buffer = res.buffer;
+ *len = res.result.encoded;
+ return 0;
+}
+
+static inline int nrppa_gNB_encode_successfull_outcome(NRPPA_NRPPA_PDU_t *pdu, uint8_t **buffer, uint32_t *len)
+{
+ DevAssert(pdu != NULL);
+ const NRPPA_ProcedureCode_t tmp[] = {NRPPA_ProcedureCode_id_positioningInformationExchange,
+ NRPPA_ProcedureCode_id_positioningActivation,
+ NRPPA_ProcedureCode_id_tRPInformationExchange,
+ NRPPA_ProcedureCode_id_Measurement};
+ int i;
+ for (i = 0; i < sizeofArray(tmp); i++)
+ if (pdu->choice.successfulOutcome->procedureCode == tmp[i])
+ break;
+ if (i == sizeofArray(tmp)) {
+ LOG_E(NRPPA, "Unknown procedure ID (%ld) for successfull outcome message\n", pdu->choice.successfulOutcome->procedureCode);
+ return -1;
+ }
+ // xer_fprint(stdout, &asn_DEF_NRPPA_NRPPA_PDU, pdu);
+ asn_encode_to_new_buffer_result_t res = asn_encode_to_new_buffer(NULL, ATS_ALIGNED_CANONICAL_PER, &asn_DEF_NRPPA_NRPPA_PDU, pdu);
+ AssertFatal(res.result.encoded > 0, "failed to encode NRPPA msg\n");
+ *buffer = res.buffer;
+ *len = res.result.encoded;
+ return 0;
+}
+
+static inline int nrppa_gNB_encode_unsuccessfull_outcome(NRPPA_NRPPA_PDU_t *pdu, uint8_t **buffer, uint32_t *len)
+{
+ DevAssert(pdu != NULL);
+
+ const NRPPA_ProcedureCode_t tmp[] = {NRPPA_ProcedureCode_id_positioningInformationExchange,
+ NRPPA_ProcedureCode_id_positioningActivation,
+ NRPPA_ProcedureCode_id_tRPInformationExchange,
+ NRPPA_ProcedureCode_id_Measurement};
+
+ int i;
+ for (i = 0; i < sizeofArray(tmp); i++)
+ if (pdu->choice.unsuccessfulOutcome->procedureCode == tmp[i])
+ break;
+ if (i == sizeofArray(tmp)) {
+ LOG_W(NRPPA, "Unknown procedure ID (%ld) for unsuccessfull outcome message\n", pdu->choice.unsuccessfulOutcome->procedureCode);
+ return -1;
+ }
+
+ asn_encode_to_new_buffer_result_t res = asn_encode_to_new_buffer(NULL, ATS_ALIGNED_CANONICAL_PER, &asn_DEF_NRPPA_NRPPA_PDU, pdu);
+ AssertFatal(res.result.encoded > 0, "failed to encode NRPPA msg\n");
+ *buffer = res.buffer;
+ *len = res.result.encoded;
+ return 0;
+}
+
+int nrppa_gNB_encode_pdu(NRPPA_NRPPA_PDU_t *pdu, uint8_t **buffer, uint32_t *len)
+{
+ int ret = -1;
+ DevAssert(pdu != NULL);
+ DevAssert(buffer != NULL);
+ DevAssert(len != NULL);
+
+ // xer_fprint(stdout, &asn_DEF_NRPPA_NRPPA_PDU, (void *)pdu);
+
+ switch (pdu->present) {
+ case NRPPA_NRPPA_PDU_PR_initiatingMessage:
+ ret = nrppa_gNB_encode_initiating(pdu, buffer, len);
+ break;
+
+ case NRPPA_NRPPA_PDU_PR_successfulOutcome:
+ ret = nrppa_gNB_encode_successfull_outcome(pdu, buffer, len);
+ break;
+
+ case NRPPA_NRPPA_PDU_PR_unsuccessfulOutcome:
+ ret = nrppa_gNB_encode_unsuccessfull_outcome(pdu, buffer, len);
+ break;
+
+ default:
+ LOG_E(NRPPA, "Unknown message outcome (%d) or not implemented", (int)pdu->present);
+ return -1;
+ }
+ ASN_STRUCT_FREE_CONTENTS_ONLY(asn_DEF_NRPPA_NRPPA_PDU, pdu);
+ return ret;
+}
diff --git a/openair3/NRPPA/nrppa_gNB_encoder.h b/openair3/NRPPA/nrppa_gNB_encoder.h
new file mode 100644
index 0000000000..dee34a2060
--- /dev/null
+++ b/openair3/NRPPA/nrppa_gNB_encoder.h
@@ -0,0 +1,27 @@
+/*
+ * Licensed to the OpenAirInterface (OAI) Software Alliance under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The OpenAirInterface Software Alliance licenses this file to You under
+ * the OAI Public License, Version 1.1 (the "License"); you may not use this file
+ * except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.openairinterface.org/?page_id=698
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *-------------------------------------------------------------------------------
+ * For more information about the OpenAirInterface (OAI) Software Alliance:
+ * contact@openairinterface.org
+ */
+
+#ifndef NRPPA_GNB_ENCODER_H_
+#define NRPPA_GNB_ENCODER_H_
+
+int nrppa_gNB_encode_pdu(NRPPA_NRPPA_PDU_t *pdu, uint8_t **buffer, uint32_t *len) __attribute__((warn_unused_result));
+
+#endif /* NRPPA_GNB_ENCODER_H_ */
diff --git a/openair3/NRPPA/nrppa_gNB_handlers.c b/openair3/NRPPA/nrppa_gNB_handlers.c
new file mode 100644
index 0000000000..476729cd36
--- /dev/null
+++ b/openair3/NRPPA/nrppa_gNB_handlers.c
@@ -0,0 +1,184 @@
+/*
+ * Licensed to the OpenAirInterface (OAI) Software Alliance under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The OpenAirInterface Software Alliance licenses this file to You under
+ * the OAI Public License, Version 1.1 (the "License"); you may not use this file
+ * except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.openairinterface.org/?page_id=698
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *-------------------------------------------------------------------------------
+ * For more information about the OpenAirInterface (OAI) Software Alliance:
+ * contact@openairinterface.org
+ */
+
+#include "intertask_interface.h"
+#include "nrppa_gNB_handlers.h"
+#include "nrppa_gNB_decoder.h"
+#include "nrppa_common.h"
+#include "nrppa_gNB_location_information_transfer.h"
+#include "nrppa_gNB_measurement_information_transfer.h"
+
+char *nrppa_direction2String(int nrppa_dir)
+{
+ static char *nrppa_direction_String[] = {
+ "", /* Nothing */
+ "Originating message", /* originating message */
+ "Successfull outcome", /* successfull outcome */
+ "UnSuccessfull outcome", /* successfull outcome */
+ };
+ return (nrppa_direction_String[nrppa_dir]);
+}
+
+/* Handlers matrix. Only gNB related procedure present here */
+nrppa_message_decoded_callback nrppa_messages_callback[][3] = {
+ {0, 0, 0}, // NRPPA_ProcedureCode_id_errorIndication ((NRPPA_ProcedureCode_t)0)
+ {0, 0, 0}, // NRPPA_ProcedureCode_id_privateMessage ((NRPPA_ProcedureCode_t)1)
+ {0, 0, 0}, // NRPPA_ProcedureCode_id_e_CIDMeasurementInitiation ((NRPPA_ProcedureCode_t)2)
+ {0, 0, 0}, // NRPPA_ProcedureCode_id_e_CIDMeasurementFailureIndication ((NRPPA_ProcedureCode_t)3)
+ {0, 0, 0}, // NRPPA_ProcedureCode_id_e_CIDMeasurementReport ((NRPPA_ProcedureCode_t)4)
+ {0, 0, 0}, // NRPPA_ProcedureCode_id_e_CIDMeasurementTermination ((NRPPA_ProcedureCode_t)5)
+ {0, 0, 0}, // NRPPA_ProcedureCode_id_oTDOAInformationExchange ((NRPPA_ProcedureCode_t)6)
+ {0, 0, 0}, // NRPPA_ProcedureCode_id_assistanceInformationControl ((NRPPA_ProcedureCode_t)7)
+ {0, 0, 0}, // NRPPA_ProcedureCode_id_assistanceInformationFeedback ((NRPPA_ProcedureCode_t)8)
+ {nrppa_gNB_handle_positioning_information_request,
+ 0,
+ 0}, // NRPPA_ProcedureCode_id_positioningInformationExchange ((NRPPA_ProcedureCode_t)9)
+ {0, 0, 0}, // NRPPA_ProcedureCode_id_positioningInformationUpdate ((NRPPA_ProcedureCode_t)10)
+ {nrppa_gNB_handle_measurement_request, 0, 0}, // NRPPA_ProcedureCode_id_Measurement ((NRPPA_ProcedureCode_t)11)
+ {0, 0, 0}, // NRPPA_ProcedureCode_id_MeasurementReport ((NRPPA_ProcedureCode_t)12)
+ {0, 0, 0}, // NRPPA_ProcedureCode_id_MeasurementUpdate ((NRPPA_ProcedureCode_t)13)
+ {0, 0, 0}, // NRPPA_ProcedureCode_id_MeasurementAbort ((NRPPA_ProcedureCode_t)14)
+ {0, 0, 0}, // NRPPA_ProcedureCode_id_MeasurementFailureIndication ((NRPPA_ProcedureCode_t)15)
+ {nrppa_gNB_handle_trp_information_request, 0, 0}, // NRPPA_ProcedureCode_id_tRPInformationExchange ((NRPPA_ProcedureCode_t)16)
+ {nrppa_gNB_handle_positioning_activation_request,
+ 0,
+ 0}, // NRPPA_ProcedureCode_id_positioningActivation ((NRPPA_ProcedureCode_t)17)
+ {0, 0, 0}, // NRPPA_ProcedureCode_id_positioningDeactivation ((NRPPA_ProcedureCode_t)18)
+};
+
+// Processing DOWNLINK UE ASSOCIATED NRPPA TRANSPORT (9.2.9.1 of TS 38.413 Version 16.0.0)
+int nrppa_handle_downlink_ue_associated_nrppa_transport(instance_t instance, const ngap_downlink_ue_associated_nrppa_t *msg)
+{
+ LOG_I(NRPPA, "Handling DOWNLINKUEASSOCIATEDNRPPA TRANSPORT\n");
+ uint8_t *const data = msg->nrppa_pdu.buf;
+ const uint32_t data_length = msg->nrppa_pdu.len;
+ NRPPA_NRPPA_PDU_t pdu;
+ int ret;
+ DevAssert(data != NULL);
+ memset(&pdu, 0, sizeof(pdu));
+
+ if (nrppa_gNB_decode_pdu(&pdu, data, data_length) < 0) {
+ LOG_E(NRPPA, "Failed to decode PDU\n");
+ ASN_STRUCT_FREE_CONTENTS_ONLY(asn_DEF_NRPPA_NRPPA_PDU, &pdu);
+ return -1;
+ }
+ /* Checking procedure Code and direction of message*/
+ if (pdu.choice.initiatingMessage->procedureCode >= sizeof(nrppa_messages_callback) / (3 * sizeof(nrppa_message_decoded_callback))
+ || (pdu.present > NRPPA_NRPPA_PDU_PR_unsuccessfulOutcome)) {
+ LOG_E(NRPPA,
+ "Either procedureCode %ld or direction %d exceed expected\n",
+ pdu.choice.initiatingMessage->procedureCode,
+ pdu.present);
+ ASN_STRUCT_FREE_CONTENTS_ONLY(asn_DEF_NRPPA_NRPPA_PDU, &pdu);
+ return -1;
+ }
+
+ /* No handler present.
+ * This can mean not implemented or no procedure for gNB (wrong direction).*/
+ if (nrppa_messages_callback[pdu.choice.initiatingMessage->procedureCode][pdu.present - 1] == NULL) {
+ LOG_E(NRPPA,
+ "No handler for procedureCode %ld in %s\n",
+ pdu.choice.initiatingMessage->procedureCode,
+ nrppa_direction2String(pdu.present - 1));
+ ASN_STRUCT_FREE_CONTENTS_ONLY(asn_DEF_NRPPA_NRPPA_PDU, &pdu);
+ return -1;
+ }
+
+ /* Calling the right handler*/
+ nrppa_gnb_ue_info_t nrppa_msg_info;
+ nrppa_msg_info.instance = instance;
+ nrppa_msg_info.gNB_ue_ngap_id = msg->gNB_ue_ngap_id;
+ nrppa_msg_info.amf_ue_ngap_id = msg->amf_ue_ngap_id;
+ nrppa_msg_info.routing_id.buf = msg->routing_id.buf;
+ nrppa_msg_info.routing_id.len = msg->routing_id.len;
+ ret = (*nrppa_messages_callback[pdu.choice.initiatingMessage->procedureCode][pdu.present - 1])(&nrppa_msg_info, &pdu);
+
+ if (msg->routing_id.buf) {
+ free(msg->routing_id.buf);
+ }
+
+ if (msg->nrppa_pdu.buf) {
+ free(msg->nrppa_pdu.buf);
+ }
+
+ ASN_STRUCT_FREE_CONTENTS_ONLY(asn_DEF_NRPPA_NRPPA_PDU, &pdu);
+ return ret;
+}
+
+// Processing DOWNLINK NON UE ASSOCIATED NRPPA TRANSPORT (9.2.9.3 of TS 38.413 Version 16.0.0)
+int nrppa_handle_downlink_non_ue_associated_nrppa_transport(instance_t instance, const ngap_downlink_non_ue_associated_nrppa_t *msg)
+{
+ LOG_I(NRPPA, "Handling DOWNLINKNONUEASSOCIATEDNRPPA TRANSPORT\n");
+ uint8_t *const data = msg->nrppa_pdu.buf;
+ const uint32_t data_length = msg->nrppa_pdu.len;
+ NRPPA_NRPPA_PDU_t pdu;
+ int ret;
+ DevAssert(data != NULL);
+ memset(&pdu, 0, sizeof(pdu));
+
+ if (nrppa_gNB_decode_pdu(&pdu, data, data_length) < 0) {
+ LOG_E(NRPPA, "Failed to decode Downlink Non UE Associated NRPPa PDU\n");
+ ASN_STRUCT_FREE_CONTENTS_ONLY(asn_DEF_NRPPA_NRPPA_PDU, &pdu);
+ return -1;
+ }
+
+ /* Checking procedure Code and direction of message*/
+ if (pdu.choice.initiatingMessage->procedureCode >= sizeof(nrppa_messages_callback) / (3 * sizeof(nrppa_message_decoded_callback))
+ || (pdu.present > NRPPA_NRPPA_PDU_PR_unsuccessfulOutcome)) {
+ LOG_E(NRPPA,
+ "Either procedureCode %ld or direction %d exceed expected\n",
+ pdu.choice.initiatingMessage->procedureCode,
+ pdu.present);
+ ASN_STRUCT_FREE_CONTENTS_ONLY(asn_DEF_NRPPA_NRPPA_PDU, &pdu);
+ return -1;
+ }
+
+ /* No handler present.
+ * This can mean not implemented or no procedure for gNB (wrong direction).*/
+ if (nrppa_messages_callback[pdu.choice.initiatingMessage->procedureCode][pdu.present - 1] == NULL) {
+ LOG_E(NRPPA,
+ "No handler for procedureCode %ld in %s\n",
+ pdu.choice.initiatingMessage->procedureCode,
+ nrppa_direction2String(pdu.present - 1));
+ ASN_STRUCT_FREE_CONTENTS_ONLY(asn_DEF_NRPPA_NRPPA_PDU, &pdu);
+ return -1;
+ }
+
+ /* Calling the right handler*/
+ nrppa_gnb_ue_info_t nrppa_msg_info;
+ nrppa_msg_info.instance = instance;
+ nrppa_msg_info.gNB_ue_ngap_id = 0; // non-ue associated
+ nrppa_msg_info.amf_ue_ngap_id = 0; // non-ue associated
+ nrppa_msg_info.routing_id.buf = msg->routing_id.buf;
+ nrppa_msg_info.routing_id.len = msg->routing_id.len;
+ ret = (*nrppa_messages_callback[pdu.choice.initiatingMessage->procedureCode][pdu.present - 1])(&nrppa_msg_info, &pdu);
+
+ if (msg->routing_id.buf) {
+ free(msg->routing_id.buf);
+ }
+
+ if (msg->nrppa_pdu.buf) {
+ free(msg->nrppa_pdu.buf);
+ }
+
+ ASN_STRUCT_FREE_CONTENTS_ONLY(asn_DEF_NRPPA_NRPPA_PDU, &pdu);
+ return ret;
+}
diff --git a/openair3/NRPPA/nrppa_gNB_handlers.h b/openair3/NRPPA/nrppa_gNB_handlers.h
new file mode 100644
index 0000000000..ecee41caa1
--- /dev/null
+++ b/openair3/NRPPA/nrppa_gNB_handlers.h
@@ -0,0 +1,28 @@
+/*
+ * Licensed to the OpenAirInterface (OAI) Software Alliance under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The OpenAirInterface Software Alliance licenses this file to You under
+ * the OAI Public License, Version 1.1 (the "License"); you may not use this file
+ * except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.openairinterface.org/?page_id=698
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *-------------------------------------------------------------------------------
+ * For more information about the OpenAirInterface (OAI) Software Alliance:
+ * contact@openairinterface.org
+ */
+
+#ifndef NRPPA_GNB_HANDLERS_H_
+#define NRPPA_GNB_HANDLERS_H_
+
+int nrppa_handle_downlink_ue_associated_nrppa_transport(instance_t instance, const ngap_downlink_ue_associated_nrppa_t *msg);
+int nrppa_handle_downlink_non_ue_associated_nrppa_transport(instance_t instance,
+ const ngap_downlink_non_ue_associated_nrppa_t *msg);
+#endif /* NRPPA_GNB_HANDLERS_H_ */
diff --git a/openair3/NRPPA/nrppa_gNB_location_information_transfer.c b/openair3/NRPPA/nrppa_gNB_location_information_transfer.c
new file mode 100644
index 0000000000..bb3bc9f8bd
--- /dev/null
+++ b/openair3/NRPPA/nrppa_gNB_location_information_transfer.c
@@ -0,0 +1,1379 @@
+/*
+ * Licensed to the OpenAirInterface (OAI) Software Alliance under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The OpenAirInterface Software Alliance licenses this file to You under
+ * the OAI Public License, Version 1.1 (the "License"); you may not use this file
+ * except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.openairinterface.org/?page_id=698
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *-------------------------------------------------------------------------------
+ * For more information about the OpenAirInterface (OAI) Software Alliance:
+ * contact@openairinterface.org
+ */
+
+#include "intertask_interface.h"
+#include "nrppa_common.h"
+#include "nrppa_gNB_location_information_transfer.h"
+#include "nrppa_gNB_ue_context.h"
+#include "nrppa_messages_types.h"
+#include "nrppa_gNB_encoder.h"
+#include "openair3/UTILS/conversions.h"
+
+void free_trp_information_request(nrppa_trp_information_req_t *msg)
+{
+ if (msg->trp_information_type_list.trp_information_type_item) {
+ free(msg->trp_information_type_list.trp_information_type_item);
+ }
+}
+
+static NRPPA_TRPPositionDirect_t encode_trp_position_direct(nrppa_trp_position_direct_t *in)
+{
+ NRPPA_TRPPositionDirect_t out = {0};
+
+ switch (in->accuracy.present) {
+ case NRPPA_TRP_POSITION_DIRECT_ACCURACY_PR_NOTHING:
+ out.accuracy.present = NRPPA_TRPPositionDirectAccuracy_PR_NOTHING;
+ break;
+ case NRPPA_TRP_POSITION_DIRECT_ACCURACY_PR_TRPPOSITION:
+ out.accuracy.present = NRPPA_TRPPositionDirectAccuracy_PR_tRPPosition;
+ asn1cCalloc(out.accuracy.choice.tRPPosition, out_pos);
+ nrppa_access_point_position_t *in_pos = &in->accuracy.choice.trp_position;
+
+ out_pos->latitudeSign = in_pos->latitude_sign;
+ out_pos->latitude = in_pos->latitude;
+ out_pos->longitude = in_pos->longitude;
+ out_pos->directionOfAltitude = in_pos->direction_of_altitude;
+ out_pos->altitude = in_pos->altitude;
+ out_pos->uncertaintySemi_major = in_pos->uncertainty_semi_major;
+ out_pos->uncertaintySemi_minor = in_pos->uncertainty_semi_minor;
+ out_pos->orientationOfMajorAxis = in_pos->orientation_of_major_axis;
+ out_pos->uncertaintyAltitude = in_pos->uncertainty_altitude;
+ out_pos->confidence = in_pos->confidence;
+ break;
+ case NRPPA_TRP_POSITION_DIRECT_ACCURACY_PR_TRPHAPOSITION:
+ out.accuracy.present = NRPPA_TRPPositionDirectAccuracy_PR_tRPHAposition;
+ asn1cCalloc(out.accuracy.choice.tRPHAposition, out_ha_pos);
+ nrppa_ngran_high_accuracy_access_point_position_t *in_ha_pos = &in->accuracy.choice.trp_HAposition;
+ out_ha_pos->latitude = in_ha_pos->latitude;
+ out_ha_pos->longitude = in_ha_pos->longitude;
+ out_ha_pos->altitude = in_ha_pos->altitude;
+ out_ha_pos->uncertaintySemi_major = in_ha_pos->uncertainty_semi_major;
+ out_ha_pos->uncertaintySemi_minor = in_ha_pos->uncertainty_semi_minor;
+ out_ha_pos->orientationOfMajorAxis = in_ha_pos->orientation_of_major_axis;
+ out_ha_pos->horizontalConfidence = in_ha_pos->horizontal_confidence;
+ out_ha_pos->uncertaintyAltitude = in_ha_pos->uncertainty_altitude;
+ out_ha_pos->verticalConfidence = in_ha_pos->vertical_confidence;
+ break;
+ default:
+ AssertFatal(false, "illegal direct accuracy entry\n");
+ break;
+ }
+ return out;
+}
+
+static NRPPA_TRPPositionReferenced_t encode_trp_position_referenced(nrppa_trp_position_referenced_t *in)
+{
+ NRPPA_TRPPositionReferenced_t out = {0};
+ NRPPA_ReferencePoint_t *out_ref_point = &out.referencePoint;
+ nrppa_reference_point_t *in_ref_point = &in->reference_point;
+ switch (in_ref_point->present) {
+ case NRPPA_REFERENCE_POINT_PR_NOTHING:
+ out_ref_point->present = NRPPA_ReferencePoint_PR_NOTHING;
+ break;
+ case NRPPA_REFERENCE_POINT_PR_COORDINATEID:
+ out_ref_point->present = NRPPA_ReferencePoint_PR_relativeCoordinateID;
+ out_ref_point->choice.relativeCoordinateID = in_ref_point->choice.coordinate_id;
+ break;
+ case NRPPA_REFERENCE_POINT_PR_REFERENCEPOINTCOORDINATE:
+ out_ref_point->present = NRPPA_ReferencePoint_PR_referencePointCoordinate;
+ asn1cCalloc(out_ref_point->choice.referencePointCoordinate, out_ref_coord);
+ nrppa_access_point_position_t *in_ref_coord = &in_ref_point->choice.reference_point_coordinate;
+ out_ref_coord->latitudeSign = in_ref_coord->latitude_sign;
+ out_ref_coord->latitude = in_ref_coord->latitude;
+ out_ref_coord->longitude = in_ref_coord->longitude;
+ out_ref_coord->directionOfAltitude = in_ref_coord->direction_of_altitude;
+ out_ref_coord->altitude = in_ref_coord->altitude;
+ out_ref_coord->uncertaintySemi_major = in_ref_coord->uncertainty_semi_major;
+ out_ref_coord->uncertaintySemi_minor = in_ref_coord->uncertainty_semi_minor;
+ out_ref_coord->orientationOfMajorAxis = in_ref_coord->orientation_of_major_axis;
+ out_ref_coord->uncertaintyAltitude = in_ref_coord->uncertainty_altitude;
+ out_ref_coord->confidence = in_ref_coord->confidence;
+ break;
+ case NRPPA_REFERENCE_POINT_PR_REFERENCEPOINTCOORDINATEHA:
+ out_ref_point->present = NRPPA_ReferencePoint_PR_referencePointCoordinateHA;
+ asn1cCalloc(out_ref_point->choice.referencePointCoordinateHA, out_ref_coord_ha);
+ nrppa_ngran_high_accuracy_access_point_position_t *in_ref_coord_ha = &in_ref_point->choice.reference_point_coordinateHA;
+ out_ref_coord_ha->latitude = in_ref_coord_ha->latitude;
+ out_ref_coord_ha->longitude = in_ref_coord_ha->longitude;
+ out_ref_coord_ha->altitude = in_ref_coord_ha->altitude;
+ out_ref_coord_ha->uncertaintySemi_major = in_ref_coord_ha->uncertainty_semi_major;
+ out_ref_coord_ha->uncertaintySemi_minor = in_ref_coord_ha->uncertainty_semi_minor;
+ out_ref_coord_ha->orientationOfMajorAxis = in_ref_coord_ha->orientation_of_major_axis;
+ out_ref_coord_ha->horizontalConfidence = in_ref_coord_ha->horizontal_confidence;
+ out_ref_coord_ha->uncertaintyAltitude = in_ref_coord_ha->uncertainty_altitude;
+ out_ref_coord_ha->verticalConfidence = in_ref_coord_ha->vertical_confidence;
+ break;
+ default:
+ AssertFatal(false, "illegal reference point entry\n");
+ break;
+ }
+
+ NRPPA_TRPReferencePointType_t *out_ref_point_type = &out.referencePointType;
+ nrppa_trp_reference_point_type_t *in_ref_point_type = &in->reference_point_type;
+ switch (in_ref_point_type->present) {
+ case NRPPA_TRP_REFERENCE_POINT_TYPE_PR_NOTHING:
+ out_ref_point_type->present = NRPPA_TRPReferencePointType_PR_NOTHING;
+ break;
+ case NRPPA_TRP_REFERENCE_POINT_TYPE_PR_TRPPOSITION_RELATIVE_GEODETIC:
+ out_ref_point_type->present = NRPPA_TRPReferencePointType_PR_tRPPositionRelativeGeodetic;
+ asn1cCalloc(out_ref_point_type->choice.tRPPositionRelativeGeodetic, out_geodetic);
+ nrppa_relative_geodetic_location_t *in_geodetic = &in_ref_point_type->choice.trp_position_relative_geodetic;
+ out_geodetic->milli_Arc_SecondUnits = in_geodetic->milli_arc_second_units;
+ out_geodetic->heightUnits = in_geodetic->height_units;
+ out_geodetic->deltaLatitude = in_geodetic->delta_latitude;
+ out_geodetic->deltaLongitude = in_geodetic->delta_longitude;
+ out_geodetic->deltaHeight = in_geodetic->delta_height;
+ NRPPA_LocationUncertainty_t *out_loc_uncertainty_g = &out_geodetic->locationUncertainty;
+ nrppa_location_uncertainty_t *in_loc_uncertainty_g = &in_geodetic->location_uncertainty;
+ out_loc_uncertainty_g->horizontalUncertainty = in_loc_uncertainty_g->horizontal_uncertainty;
+ out_loc_uncertainty_g->horizontalConfidence = in_loc_uncertainty_g->horizontal_confidence;
+ out_loc_uncertainty_g->verticalUncertainty = in_loc_uncertainty_g->vertical_uncertainty;
+ out_loc_uncertainty_g->verticalConfidence = in_loc_uncertainty_g->vertical_confidence;
+ break;
+ case NRPPA_TRP_REFERENCE_POINT_TYPE_PR_TRPPOSITION_RELATIVE_CARTESIAN:
+ out_ref_point_type->present = NRPPA_TRPReferencePointType_PR_tRPPositionRelativeCartesian;
+ asn1cCalloc(out_ref_point_type->choice.tRPPositionRelativeCartesian, out_cartesian);
+ nrppa_relative_cartesian_location_t *in_cartesian = &in_ref_point_type->choice.trp_position_relative_cartesian;
+
+ out_cartesian->xYZunit = in_cartesian->xyz_unit;
+ out_cartesian->xvalue = in_cartesian->xvalue;
+ out_cartesian->yvalue = in_cartesian->yvalue;
+ out_cartesian->zvalue = in_cartesian->zvalue;
+ NRPPA_LocationUncertainty_t *out_loc_uncertainty_c = &out_cartesian->locationUncertainty;
+ nrppa_location_uncertainty_t *in_loc_uncertainty_c = &in_cartesian->location_uncertainty;
+ out_loc_uncertainty_c->horizontalUncertainty = in_loc_uncertainty_c->horizontal_uncertainty;
+ out_loc_uncertainty_c->horizontalConfidence = in_loc_uncertainty_c->horizontal_confidence;
+ out_loc_uncertainty_c->verticalUncertainty = in_loc_uncertainty_c->vertical_uncertainty;
+ out_loc_uncertainty_c->verticalConfidence = in_loc_uncertainty_c->vertical_confidence;
+ break;
+ default:
+ AssertFatal(false, "illegal trp reference point type entry\n");
+ break;
+ }
+ return out;
+}
+
+static NRPPA_GeographicalCoordinates_t encode_geographical_coordinates_nrppa(nrppa_geographical_coordinates_t *in)
+{
+ NRPPA_GeographicalCoordinates_t out = {0};
+ NRPPA_TRPPositionDefinitionType_t *out_type = &out.tRPPositionDefinitionType;
+ nrppa_trp_position_definition_type_t *in_type = &in->trp_position_definition_type;
+ switch (in_type->present) {
+ case NRPPA_TRP_POSITION_DEFINITION_TYPE_PR_NOTHING:
+ out_type->present = NRPPA_TRPPositionDefinitionType_PR_NOTHING;
+ break;
+ case NRPPA_TRP_POSITION_DEFINITION_TYPE_PR_DIRECT:
+ out_type->present = NRPPA_TRPPositionDefinitionType_PR_direct;
+ asn1cCalloc(out_type->choice.direct, direct);
+ *direct = encode_trp_position_direct(&in_type->choice.direct);
+ break;
+ case NRPPA_TRP_POSITION_DEFINITION_TYPE_PR_REFERENCED:
+ out_type->present = NRPPA_TRPPositionDefinitionType_PR_referenced;
+ asn1cCalloc(out_type->choice.referenced, referenced);
+ *referenced = encode_trp_position_referenced(&in_type->choice.referenced);
+ break;
+ default:
+ AssertFatal(false, "illegal Geographical Coordinates entry\n");
+ break;
+ }
+ return out;
+}
+
+NRPPA_TRPInformationItem_t encode_trp_info_type_response_item_nrppa(nrppa_trp_information_type_response_item_t *in)
+{
+ NRPPA_TRPInformationItem_t out = {0};
+ switch (in->present) {
+ case NRPPA_TRP_INFORMATION_TYPE_RESPONSE_ITEM_PR_NOTHING:
+ out.present = NRPPA_TRPInformationItem_PR_NOTHING;
+ break;
+ case NRPPA_TRP_INFORMATION_TYPE_RESPONSE_ITEM_PR_PCI_NR:
+ out.present = NRPPA_TRPInformationItem_PR_pCI_NR;
+ out.choice.pCI_NR = in->choice.pci_nr;
+ break;
+ case NRPPA_TRP_INFORMATION_TYPE_RESPONSE_ITEM_PR_NG_RAN_CGI:
+ out.present = NRPPA_TRPInformationItem_PR_nG_RAN_CGI;
+ asn1cCalloc(out.choice.nG_RAN_CGI, nG_RAN_CGI);
+ MCC_MNC_TO_PLMNID(in->choice.ng_ran_cgi.plmn.mcc,
+ in->choice.ng_ran_cgi.plmn.mnc,
+ in->choice.ng_ran_cgi.plmn.mnc_digit_length,
+ &(nG_RAN_CGI->pLMN_Identity));
+ nG_RAN_CGI->nG_RANcell.present = NRPPA_NG_RANCell_PR_nR_CellID;
+ NR_CELL_ID_TO_BIT_STRING(in->choice.ng_ran_cgi.nr_cellid, &(nG_RAN_CGI->nG_RANcell.choice.nR_CellID));
+ break;
+ case NRPPA_TRP_INFORMATION_TYPE_RESPONSE_ITEM_PR_NRARFCN:
+ out.present = NRPPA_TRPInformationItem_PR_aRFCN;
+ out.choice.aRFCN = in->choice.nr_arfcn;
+ break;
+ case NRPPA_TRP_INFORMATION_TYPE_RESPONSE_ITEM_PR_PRSCONFIGURATION:
+ out.present = NRPPA_TRPInformationItem_PR_pRSConfiguration;
+ AssertFatal(false, "TRP information type response item PRS configuration unsupported\n");
+ break;
+ case NRPPA_TRP_INFORMATION_TYPE_RESPONSE_ITEM_PR_SSBINFORMATION:
+ out.present = NRPPA_TRPInformationItem_PR_sSBinformation;
+ AssertFatal(false, "TRP information type response item SSB Information unsupported\n");
+ break;
+ case NRPPA_TRP_INFORMATION_TYPE_RESPONSE_ITEM_PR_SFNINITIALISATIONTIME:
+ out.present = NRPPA_TRPInformationItem_PR_sFNInitialisationTime;
+ AssertFatal(false, "TRP information type response item SFN Initialization Time unsupported\n");
+ break;
+ case NRPPA_TRP_INFORMATION_TYPE_RESPONSE_ITEM_PR_SPATIALDIRECTIONINFORMATION:
+ out.present = NRPPA_TRPInformationItem_PR_spatialDirectionInformation;
+ AssertFatal(false, "TRP information type response item Spatial Direction Information unsupported\n");
+ break;
+ case NRPPA_TRP_INFORMATION_TYPE_RESPONSE_ITEM_PR_GEOGRAPHICALCOORDINATES:
+ out.present = NRPPA_TRPInformationItem_PR_geographicalCoordinates;
+ asn1cCalloc(out.choice.geographicalCoordinates, nrppa_geo_coord);
+ nrppa_geographical_coordinates_t *geo_coord = &in->choice.geographical_coordinates;
+ *nrppa_geo_coord = encode_geographical_coordinates_nrppa(geo_coord);
+ break;
+ default:
+ AssertFatal(false, "received illegal trp information type response item %d\n", in->present);
+ break;
+ }
+ return out;
+}
+
+void free_trp_information_response(nrppa_trp_information_resp_t *msg)
+{
+ nrppa_trp_information_list_t *trp_information_list = &msg->trp_information_list;
+ uint32_t trp_info_item_length = trp_information_list->trp_information_item_length;
+ for (int i = 0; i < trp_info_item_length; i++) {
+ nrppa_trp_information_t *trp_information_item = &trp_information_list->trp_information_item[i];
+ nrppa_trp_information_type_response_list_t *trp_info_type_resp_list = &trp_information_item->trp_information_type_response_list;
+ free(trp_info_type_resp_list->trp_information_type_response_item);
+ }
+ free(msg->trp_information_list.trp_information_item);
+}
+
+static NRPPA_SRSConfig_t encode_srs_config(const nrppa_srs_config_t *in_config)
+{
+ NRPPA_SRSConfig_t out_config = {0};
+ // optional: srs_resource_list
+ if (in_config->srs_resource_list) {
+ nrppa_srs_resource_list_t *srs_resource_list = in_config->srs_resource_list;
+ uint32_t srs_resource_list_length = srs_resource_list->srs_resource_list_length;
+ asn1cCalloc(out_config.sRSResource_List, nrppa_sRSResource_List);
+ for (int i = 0; i < srs_resource_list_length; i++) {
+ asn1cSequenceAdd(nrppa_sRSResource_List->list, NRPPA_SRSResource_t, nrppa_srs_resource);
+ nrppa_srs_resource_t *srs_resource = &srs_resource_list->srs_resource[i];
+ nrppa_srs_resource->sRSResourceID = srs_resource->srs_resource_id;
+
+ switch (srs_resource->nr_of_srs_ports) {
+ case NRPPA_SRS_NUMBER_OF_PORTS_N1:
+ nrppa_srs_resource->nrofSRS_Ports = NRPPA_SRSResource__nrofSRS_Ports_port1;
+ break;
+ case NRPPA_SRS_NUMBER_OF_PORTS_N2:
+ nrppa_srs_resource->nrofSRS_Ports = NRPPA_SRSResource__nrofSRS_Ports_ports2;
+ break;
+ case NRPPA_SRS_NUMBER_OF_PORTS_N4:
+ nrppa_srs_resource->nrofSRS_Ports = NRPPA_SRSResource__nrofSRS_Ports_ports4;
+ break;
+ default:
+ AssertFatal(false, "illegal number of srs ports %d\n", srs_resource->nr_of_srs_ports);
+ break;
+ }
+
+ nrppa_transmission_comb_t *srs_res_tx_comb = &srs_resource->transmission_comb;
+ switch (srs_res_tx_comb->present) {
+ case NRPPA_TRANSMISSION_COMB_PR_NOTHING:
+ nrppa_srs_resource->transmissionComb.present = NRPPA_TransmissionComb_PR_NOTHING;
+ break;
+ case NRPPA_TRANSMISSION_COMB_PR_N2:
+ nrppa_srs_resource->transmissionComb.present = NRPPA_TransmissionComb_PR_n2;
+ asn1cCalloc(nrppa_srs_resource->transmissionComb.choice.n2, nrppa_n2);
+ nrppa_n2->combOffset_n2 = srs_res_tx_comb->choice.n2.comb_offset_n2;
+ nrppa_n2->cyclicShift_n2 = srs_res_tx_comb->choice.n2.cyclic_shift_n2;
+ break;
+ case NRPPA_TRANSMISSION_COMB_PR_N4:
+ nrppa_srs_resource->transmissionComb.present = NRPPA_TransmissionComb_PR_n4;
+ asn1cCalloc(nrppa_srs_resource->transmissionComb.choice.n4, nrppa_n4);
+ nrppa_n4->combOffset_n4 = srs_res_tx_comb->choice.n4.comb_offset_n4;
+ nrppa_n4->cyclicShift_n4 = srs_res_tx_comb->choice.n4.cyclic_shift_n4;
+ break;
+ default:
+ AssertFatal(false, "illegal transmissionComb %d\n", srs_res_tx_comb->present);
+ break;
+ }
+
+ nrppa_srs_resource->startPosition = srs_resource->start_position;
+
+ switch (srs_resource->nr_of_symbols) {
+ case NRPPA_SRS_NUMBER_OF_SYMBOLS_N1:
+ nrppa_srs_resource->nrofSymbols = NRPPA_SRSResource__nrofSymbols_n1;
+ break;
+ case NRPPA_SRS_NUMBER_OF_SYMBOLS_N2:
+ nrppa_srs_resource->nrofSymbols = NRPPA_SRSResource__nrofSymbols_n2;
+ break;
+ case NRPPA_SRS_NUMBER_OF_SYMBOLS_N4:
+ nrppa_srs_resource->nrofSymbols = NRPPA_SRSResource__nrofSymbols_n4;
+ break;
+ default:
+ AssertFatal(false, "illegal number of symbols %d\n", srs_resource->nr_of_symbols);
+ break;
+ }
+
+ switch (srs_resource->repetition_factor) {
+ case NRPPA_SRS_REPETITION_FACTOR_RF1:
+ nrppa_srs_resource->repetitionFactor = NRPPA_SRSResource__repetitionFactor_n1;
+ break;
+ case NRPPA_SRS_REPETITION_FACTOR_RF2:
+ nrppa_srs_resource->repetitionFactor = NRPPA_SRSResource__repetitionFactor_n2;
+ break;
+ case NRPPA_SRS_REPETITION_FACTOR_RF4:
+ nrppa_srs_resource->repetitionFactor = NRPPA_SRSResource__repetitionFactor_n4;
+ break;
+ default:
+ AssertFatal(false, "illegal repetition factor %d\n", srs_resource->repetition_factor);
+ break;
+ }
+
+ nrppa_srs_resource->freqDomainPosition = srs_resource->freq_domain_position;
+ nrppa_srs_resource->freqDomainShift = srs_resource->freq_domain_shift;
+ nrppa_srs_resource->c_SRS = srs_resource->c_srs;
+ nrppa_srs_resource->b_SRS = srs_resource->b_srs;
+ nrppa_srs_resource->b_hop = srs_resource->b_hop;
+
+ switch (srs_resource->group_or_sequence_hopping) {
+ case NRPPA_GROUPORSEQUENCEHOPPING_NOTHING:
+ nrppa_srs_resource->groupOrSequenceHopping = NRPPA_SRSResource__groupOrSequenceHopping_neither;
+ break;
+ case NRPPA_GROUPORSEQUENCEHOPPING_GROUPHOPPING:
+ nrppa_srs_resource->groupOrSequenceHopping = NRPPA_SRSResource__groupOrSequenceHopping_groupHopping;
+ break;
+ case NRPPA_GROUPORSEQUENCEHOPPING_SEQUENCEHOPPING:
+ nrppa_srs_resource->groupOrSequenceHopping = NRPPA_SRSResource__groupOrSequenceHopping_sequenceHopping;
+ break;
+ default:
+ AssertFatal(false, "illegal groupOrSequenceHopping %d\n", srs_resource->group_or_sequence_hopping);
+ break;
+ }
+
+ NRPPA_ResourceType_t *nrppa_resourceType = &nrppa_srs_resource->resourceType;
+ nrppa_resource_type_t *resource_type = &srs_resource->resource_type;
+ if (resource_type->present == NRPPA_RESOURCE_TYPE_PR_NOTHING) {
+ nrppa_resourceType->present = NRPPA_ResourceType_PR_NOTHING;
+ } else if (resource_type->present == NRPPA_RESOURCE_TYPE_PR_PERIODIC) {
+ nrppa_resourceType->present = NRPPA_ResourceType_PR_periodic;
+ asn1cCalloc(nrppa_resourceType->choice.periodic, nrppa_periodic);
+ switch (resource_type->choice.periodic.periodicity) {
+ case NRPPA_SRS_RESOURCE_TYPE_PERIODICITY_SLOT1:
+ nrppa_periodic->periodicity = NRPPA_ResourceTypePeriodic__periodicity_slot1;
+ break;
+ case NRPPA_SRS_RESOURCE_TYPE_PERIODICITY_SLOT2:
+ nrppa_periodic->periodicity = NRPPA_ResourceTypePeriodic__periodicity_slot2;
+ break;
+ case NRPPA_SRS_RESOURCE_TYPE_PERIODICITY_SLOT4:
+ nrppa_periodic->periodicity = NRPPA_ResourceTypePeriodic__periodicity_slot4;
+ break;
+ case NRPPA_SRS_RESOURCE_TYPE_PERIODICITY_SLOT5:
+ nrppa_periodic->periodicity = NRPPA_ResourceTypePeriodic__periodicity_slot5;
+ break;
+ case NRPPA_SRS_RESOURCE_TYPE_PERIODICITY_SLOT8:
+ nrppa_periodic->periodicity = NRPPA_ResourceTypePeriodic__periodicity_slot8;
+ break;
+ case NRPPA_SRS_RESOURCE_TYPE_PERIODICITY_SLOT10:
+ nrppa_periodic->periodicity = NRPPA_ResourceTypePeriodic__periodicity_slot10;
+ break;
+ case NRPPA_SRS_RESOURCE_TYPE_PERIODICITY_SLOT16:
+ nrppa_periodic->periodicity = NRPPA_ResourceTypePeriodic__periodicity_slot16;
+ break;
+ case NRPPA_SRS_RESOURCE_TYPE_PERIODICITY_SLOT20:
+ nrppa_periodic->periodicity = NRPPA_ResourceTypePeriodic__periodicity_slot20;
+ break;
+ case NRPPA_SRS_RESOURCE_TYPE_PERIODICITY_SLOT32:
+ nrppa_periodic->periodicity = NRPPA_ResourceTypePeriodic__periodicity_slot32;
+ break;
+ case NRPPA_SRS_RESOURCE_TYPE_PERIODICITY_SLOT40:
+ nrppa_periodic->periodicity = NRPPA_ResourceTypePeriodic__periodicity_slot40;
+ break;
+ case NRPPA_SRS_RESOURCE_TYPE_PERIODICITY_SLOT64:
+ nrppa_periodic->periodicity = NRPPA_ResourceTypePeriodic__periodicity_slot64;
+ break;
+ case NRPPA_SRS_RESOURCE_TYPE_PERIODICITY_SLOT80:
+ nrppa_periodic->periodicity = NRPPA_ResourceTypePeriodic__periodicity_slot80;
+ break;
+ case NRPPA_SRS_RESOURCE_TYPE_PERIODICITY_SLOT160:
+ nrppa_periodic->periodicity = NRPPA_ResourceTypePeriodic__periodicity_slot160;
+ break;
+ case NRPPA_SRS_RESOURCE_TYPE_PERIODICITY_SLOT320:
+ nrppa_periodic->periodicity = NRPPA_ResourceTypePeriodic__periodicity_slot320;
+ break;
+ case NRPPA_SRS_RESOURCE_TYPE_PERIODICITY_SLOT640:
+ nrppa_periodic->periodicity = NRPPA_ResourceTypePeriodic__periodicity_slot640;
+ break;
+ case NRPPA_SRS_RESOURCE_TYPE_PERIODICITY_SLOT1280:
+ nrppa_periodic->periodicity = NRPPA_ResourceTypePeriodic__periodicity_slot1280;
+ break;
+ case NRPPA_SRS_RESOURCE_TYPE_PERIODICITY_SLOT2560:
+ nrppa_periodic->periodicity = NRPPA_ResourceTypePeriodic__periodicity_slot2560;
+ break;
+ default:
+ AssertFatal(false, "illegal periodicity %d\n", resource_type->choice.periodic.periodicity);
+ break;
+ }
+ nrppa_periodic->offset = resource_type->choice.periodic.offset;
+ } else if (resource_type->present == NRPPA_RESOURCE_TYPE_PR_SEMI_PERSISTENT) {
+ nrppa_resourceType->present = NRPPA_ResourceType_PR_semi_persistent;
+ asn1cCalloc(nrppa_resourceType->choice.semi_persistent, nrppa_semi_persistent);
+ switch (resource_type->choice.semi_persistent.periodicity) {
+ case NRPPA_SRS_RESOURCE_TYPE_PERIODICITY_SLOT1:
+ nrppa_semi_persistent->periodicity = NRPPA_ResourceTypeSemi_persistent__periodicity_slot1;
+ break;
+ case NRPPA_SRS_RESOURCE_TYPE_PERIODICITY_SLOT2:
+ nrppa_semi_persistent->periodicity = NRPPA_ResourceTypeSemi_persistent__periodicity_slot2;
+ break;
+ case NRPPA_SRS_RESOURCE_TYPE_PERIODICITY_SLOT4:
+ nrppa_semi_persistent->periodicity = NRPPA_ResourceTypeSemi_persistent__periodicity_slot4;
+ break;
+ case NRPPA_SRS_RESOURCE_TYPE_PERIODICITY_SLOT5:
+ nrppa_semi_persistent->periodicity = NRPPA_ResourceTypeSemi_persistent__periodicity_slot5;
+ break;
+ case NRPPA_SRS_RESOURCE_TYPE_PERIODICITY_SLOT8:
+ nrppa_semi_persistent->periodicity = NRPPA_ResourceTypeSemi_persistent__periodicity_slot8;
+ break;
+ case NRPPA_SRS_RESOURCE_TYPE_PERIODICITY_SLOT10:
+ nrppa_semi_persistent->periodicity = NRPPA_ResourceTypeSemi_persistent__periodicity_slot10;
+ break;
+ case NRPPA_SRS_RESOURCE_TYPE_PERIODICITY_SLOT16:
+ nrppa_semi_persistent->periodicity = NRPPA_ResourceTypeSemi_persistent__periodicity_slot16;
+ break;
+ case NRPPA_SRS_RESOURCE_TYPE_PERIODICITY_SLOT20:
+ nrppa_semi_persistent->periodicity = NRPPA_ResourceTypeSemi_persistent__periodicity_slot20;
+ break;
+ case NRPPA_SRS_RESOURCE_TYPE_PERIODICITY_SLOT32:
+ nrppa_semi_persistent->periodicity = NRPPA_ResourceTypeSemi_persistent__periodicity_slot32;
+ break;
+ case NRPPA_SRS_RESOURCE_TYPE_PERIODICITY_SLOT40:
+ nrppa_semi_persistent->periodicity = NRPPA_ResourceTypeSemi_persistent__periodicity_slot40;
+ break;
+ case NRPPA_SRS_RESOURCE_TYPE_PERIODICITY_SLOT64:
+ nrppa_semi_persistent->periodicity = NRPPA_ResourceTypeSemi_persistent__periodicity_slot64;
+ break;
+ case NRPPA_SRS_RESOURCE_TYPE_PERIODICITY_SLOT80:
+ nrppa_semi_persistent->periodicity = NRPPA_ResourceTypeSemi_persistent__periodicity_slot80;
+ break;
+ case NRPPA_SRS_RESOURCE_TYPE_PERIODICITY_SLOT160:
+ nrppa_semi_persistent->periodicity = NRPPA_ResourceTypeSemi_persistent__periodicity_slot160;
+ break;
+ case NRPPA_SRS_RESOURCE_TYPE_PERIODICITY_SLOT320:
+ nrppa_semi_persistent->periodicity = NRPPA_ResourceTypeSemi_persistent__periodicity_slot320;
+ break;
+ case NRPPA_SRS_RESOURCE_TYPE_PERIODICITY_SLOT640:
+ nrppa_semi_persistent->periodicity = NRPPA_ResourceTypeSemi_persistent__periodicity_slot640;
+ break;
+ case NRPPA_SRS_RESOURCE_TYPE_PERIODICITY_SLOT1280:
+ nrppa_semi_persistent->periodicity = NRPPA_ResourceTypeSemi_persistent__periodicity_slot1280;
+ break;
+ case NRPPA_SRS_RESOURCE_TYPE_PERIODICITY_SLOT2560:
+ nrppa_semi_persistent->periodicity = NRPPA_ResourceTypeSemi_persistent__periodicity_slot2560;
+ break;
+ default:
+ AssertFatal(false, "illegal periodicity %d\n", resource_type->choice.semi_persistent.periodicity);
+ break;
+ }
+ nrppa_semi_persistent->offset = resource_type->choice.semi_persistent.offset;
+ } else if (resource_type->present == NRPPA_RESOURCE_TYPE_PR_APERIODIC) {
+ nrppa_resourceType->present = NRPPA_ResourceType_PR_aperiodic;
+ asn1cCalloc(nrppa_resourceType->choice.aperiodic, nrppa_aperiodic);
+ nrppa_aperiodic->aperiodicResourceType = resource_type->choice.aperiodic;
+ } else {
+ AssertFatal(false, "illegal resourceType %d\n", resource_type->present);
+ }
+
+ nrppa_srs_resource->sequenceId = srs_resource->sequence_id;
+ }
+ }
+
+ // optional: pos_srs_resource_list
+ if (in_config->pos_srs_resource_list) {
+ nrppa_pos_srs_resource_list_t *pos_srs_resource_list = in_config->pos_srs_resource_list;
+ uint32_t pos_srs_resource_list_length = pos_srs_resource_list->pos_srs_resource_list_length;
+ asn1cCalloc(out_config.posSRSResource_List, nrppa_posSRSResource_List);
+ for (int i = 0; i < pos_srs_resource_list_length; i++) {
+ asn1cSequenceAdd(nrppa_posSRSResource_List->list, NRPPA_PosSRSResource_Item_t, nrppa_pos_srs_resource);
+ nrppa_pos_srs_resource_item_t *pos_srs_resource = &pos_srs_resource_list->pos_srs_resource_item[i];
+ nrppa_pos_srs_resource->srs_PosResourceId = pos_srs_resource->srs_pos_resource_id;
+
+ nrppa_transmission_comb_pos_t *pos_srs_res_tx_comb = &pos_srs_resource->transmission_comb_pos;
+ switch (pos_srs_res_tx_comb->present) {
+ case NRPPA_TRANSMISSION_COMB_POS_PR_NOTHING:
+ nrppa_pos_srs_resource->transmissionCombPos.present = NRPPA_TransmissionCombPos_PR_NOTHING;
+ break;
+ case NRPPA_TRANSMISSION_COMB_POS_PR_N2:
+ nrppa_pos_srs_resource->transmissionCombPos.present = NRPPA_TransmissionCombPos_PR_n2;
+ asn1cCalloc(nrppa_pos_srs_resource->transmissionCombPos.choice.n2, nrppa_pos_srs_resource_n2);
+ nrppa_transmission_comb_pos_n2_t *pos_srs_resource_n2 = &pos_srs_res_tx_comb->choice.n2;
+ nrppa_pos_srs_resource_n2->combOffset_n2 = pos_srs_resource_n2->comb_offset_n2;
+ nrppa_pos_srs_resource_n2->cyclicShift_n2 = pos_srs_resource_n2->cyclic_shift_n2;
+ break;
+ case NRPPA_TRANSMISSION_COMB_POS_PR_N4:
+ nrppa_pos_srs_resource->transmissionCombPos.present = NRPPA_TransmissionCombPos_PR_n4;
+ asn1cCalloc(nrppa_pos_srs_resource->transmissionCombPos.choice.n4, nrppa_pos_srs_resource_n4);
+ nrppa_transmission_comb_pos_n4_t *pos_srs_resource_n4 = &pos_srs_res_tx_comb->choice.n4;
+ nrppa_pos_srs_resource_n4->combOffset_n4 = pos_srs_resource_n4->comb_offset_n4;
+ nrppa_pos_srs_resource_n4->cyclicShift_n4 = pos_srs_resource_n4->cyclic_shift_n4;
+ break;
+ case NRPPA_TRANSMISSION_COMB_POS_PR_N8:
+ nrppa_pos_srs_resource->transmissionCombPos.present = NRPPA_TransmissionCombPos_PR_n8;
+ asn1cCalloc(nrppa_pos_srs_resource->transmissionCombPos.choice.n8, nrppa_pos_srs_resource_n8);
+ nrppa_transmission_comb_pos_n8_t *pos_srs_resource_n8 = &pos_srs_res_tx_comb->choice.n8;
+ nrppa_pos_srs_resource_n8->combOffset_n8 = pos_srs_resource_n8->comb_offset_n8;
+ nrppa_pos_srs_resource_n8->cyclicShift_n8 = pos_srs_resource_n8->cyclic_shift_n8;
+ break;
+ default:
+ AssertFatal(false, "illegal transmissionComb %d\n", pos_srs_res_tx_comb->present);
+ break;
+ }
+
+ nrppa_pos_srs_resource->startPosition = pos_srs_resource->start_position;
+
+ switch (pos_srs_resource->nr_of_symbols) {
+ case NRPPA_SRS_RESOURCE_ITEM_NUMBER_OF_SYMBOLS_N1:
+ nrppa_pos_srs_resource->nrofSymbols = NRPPA_PosSRSResource_Item__nrofSymbols_n1;
+ break;
+ case NRPPA_SRS_RESOURCE_ITEM_NUMBER_OF_SYMBOLS_N2:
+ nrppa_pos_srs_resource->nrofSymbols = NRPPA_PosSRSResource_Item__nrofSymbols_n2;
+ break;
+ case NRPPA_SRS_RESOURCE_ITEM_NUMBER_OF_SYMBOLS_N4:
+ nrppa_pos_srs_resource->nrofSymbols = NRPPA_PosSRSResource_Item__nrofSymbols_n4;
+ break;
+ case NRPPA_SRS_RESOURCE_ITEM_NUMBER_OF_SYMBOLS_N8:
+ nrppa_pos_srs_resource->nrofSymbols = NRPPA_PosSRSResource_Item__nrofSymbols_n8;
+ break;
+ case NRPPA_SRS_RESOURCE_ITEM_NUMBER_OF_SYMBOLS_N12:
+ nrppa_pos_srs_resource->nrofSymbols = NRPPA_PosSRSResource_Item__nrofSymbols_n12;
+ break;
+ default:
+ AssertFatal(false, "illegal number of symbols %d\n", pos_srs_resource->nr_of_symbols);
+ break;
+ }
+
+ nrppa_pos_srs_resource->freqDomainShift = pos_srs_resource->freq_domain_shift;
+ nrppa_pos_srs_resource->c_SRS = pos_srs_resource->c_srs;
+
+ switch (pos_srs_resource->group_or_sequence_hopping) {
+ case NRPPA_GROUPORSEQUENCEHOPPING_NOTHING:
+ nrppa_pos_srs_resource->groupOrSequenceHopping = NRPPA_PosSRSResource_Item__groupOrSequenceHopping_neither;
+ break;
+ case NRPPA_GROUPORSEQUENCEHOPPING_GROUPHOPPING:
+ nrppa_pos_srs_resource->groupOrSequenceHopping = NRPPA_PosSRSResource_Item__groupOrSequenceHopping_groupHopping;
+ break;
+ case NRPPA_GROUPORSEQUENCEHOPPING_SEQUENCEHOPPING:
+ nrppa_pos_srs_resource->groupOrSequenceHopping = NRPPA_PosSRSResource_Item__groupOrSequenceHopping_sequenceHopping;
+ break;
+ default:
+ AssertFatal(false, "illegal groupOrSequenceHopping %d\n", pos_srs_resource->group_or_sequence_hopping);
+ break;
+ }
+
+ nrppa_resource_type_pos_t *resource_type_pos = &pos_srs_resource->resource_type_pos;
+ NRPPA_ResourceTypePos_t *nrppa_resourceTypePos = &nrppa_pos_srs_resource->resourceTypePos;
+ if (resource_type_pos->present == NRPPA_RESOURCE_TYPE_POS_PR_NOTHING) {
+ nrppa_resourceTypePos->present = NRPPA_ResourceTypePos_PR_NOTHING;
+ } else if (resource_type_pos->present == NRPPA_RESOURCE_TYPE_POS_PR_PERIODIC) {
+ nrppa_resourceTypePos->present = NRPPA_ResourceTypePos_PR_periodic;
+ asn1cCalloc(nrppa_resourceTypePos->choice.periodic, nrppa_pos_periodic);
+ switch (resource_type_pos->choice.periodic.periodicity) {
+ case NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT1:
+ nrppa_pos_periodic->periodicity = NRPPA_ResourceTypePeriodicPos__periodicity_slot1;
+ break;
+ case NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT2:
+ nrppa_pos_periodic->periodicity = NRPPA_ResourceTypePeriodicPos__periodicity_slot2;
+ break;
+ case NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT4:
+ nrppa_pos_periodic->periodicity = NRPPA_ResourceTypePeriodicPos__periodicity_slot4;
+ break;
+ case NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT5:
+ nrppa_pos_periodic->periodicity = NRPPA_ResourceTypePeriodicPos__periodicity_slot5;
+ break;
+ case NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT8:
+ nrppa_pos_periodic->periodicity = NRPPA_ResourceTypePeriodicPos__periodicity_slot8;
+ break;
+ case NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT10:
+ nrppa_pos_periodic->periodicity = NRPPA_ResourceTypePeriodicPos__periodicity_slot10;
+ break;
+ case NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT16:
+ nrppa_pos_periodic->periodicity = NRPPA_ResourceTypePeriodicPos__periodicity_slot16;
+ break;
+ case NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT20:
+ nrppa_pos_periodic->periodicity = NRPPA_ResourceTypePeriodicPos__periodicity_slot20;
+ break;
+ case NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT32:
+ nrppa_pos_periodic->periodicity = NRPPA_ResourceTypePeriodicPos__periodicity_slot32;
+ break;
+ case NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT40:
+ nrppa_pos_periodic->periodicity = NRPPA_ResourceTypePeriodicPos__periodicity_slot40;
+ break;
+ case NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT64:
+ nrppa_pos_periodic->periodicity = NRPPA_ResourceTypePeriodicPos__periodicity_slot64;
+ break;
+ case NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT80:
+ nrppa_pos_periodic->periodicity = NRPPA_ResourceTypePeriodicPos__periodicity_slot80;
+ break;
+ case NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT160:
+ nrppa_pos_periodic->periodicity = NRPPA_ResourceTypePeriodicPos__periodicity_slot160;
+ break;
+ case NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT320:
+ nrppa_pos_periodic->periodicity = NRPPA_ResourceTypePeriodicPos__periodicity_slot320;
+ break;
+ case NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT640:
+ nrppa_pos_periodic->periodicity = NRPPA_ResourceTypePeriodicPos__periodicity_slot640;
+ break;
+ case NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT1280:
+ nrppa_pos_periodic->periodicity = NRPPA_ResourceTypePeriodicPos__periodicity_slot1280;
+ break;
+ case NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT2560:
+ nrppa_pos_periodic->periodicity = NRPPA_ResourceTypePeriodicPos__periodicity_slot2560;
+ break;
+ case NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT5120:
+ nrppa_pos_periodic->periodicity = NRPPA_ResourceTypePeriodicPos__periodicity_slot5120;
+ break;
+ case NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT10240:
+ nrppa_pos_periodic->periodicity = NRPPA_ResourceTypePeriodicPos__periodicity_slot10240;
+ break;
+ case NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT20480:
+ nrppa_pos_periodic->periodicity = NRPPA_ResourceTypePeriodicPos__periodicity_slot20480;
+ break;
+ case NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT40960:
+ nrppa_pos_periodic->periodicity = NRPPA_ResourceTypePeriodicPos__periodicity_slot40960;
+ break;
+ case NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT81920:
+ nrppa_pos_periodic->periodicity = NRPPA_ResourceTypePeriodicPos__periodicity_slot81920;
+ break;
+ default:
+ AssertFatal(false, "illegal periodicity %d\n", resource_type_pos->choice.periodic.periodicity);
+ break;
+ }
+
+ nrppa_pos_periodic->offset = resource_type_pos->choice.periodic.offset;
+ } else if (resource_type_pos->present == NRPPA_RESOURCE_TYPE_POS_PR_SEMI_PERSISTENT) {
+ nrppa_resourceTypePos->present = NRPPA_ResourceTypePos_PR_semi_persistent;
+ asn1cCalloc(nrppa_resourceTypePos->choice.semi_persistent, nrppa_pos_semi_persistent);
+ switch (resource_type_pos->choice.semi_persistent.periodicity) {
+ case NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT1:
+ nrppa_pos_semi_persistent->periodicity = NRPPA_ResourceTypeSemi_persistentPos__periodicity_slot1;
+ break;
+ case NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT2:
+ nrppa_pos_semi_persistent->periodicity = NRPPA_ResourceTypeSemi_persistentPos__periodicity_slot2;
+ break;
+ case NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT4:
+ nrppa_pos_semi_persistent->periodicity = NRPPA_ResourceTypeSemi_persistentPos__periodicity_slot4;
+ break;
+ case NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT5:
+ nrppa_pos_semi_persistent->periodicity = NRPPA_ResourceTypeSemi_persistentPos__periodicity_slot5;
+ break;
+ case NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT8:
+ nrppa_pos_semi_persistent->periodicity = NRPPA_ResourceTypeSemi_persistentPos__periodicity_slot8;
+ break;
+ case NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT10:
+ nrppa_pos_semi_persistent->periodicity = NRPPA_ResourceTypeSemi_persistentPos__periodicity_slot10;
+ break;
+ case NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT16:
+ nrppa_pos_semi_persistent->periodicity = NRPPA_ResourceTypeSemi_persistentPos__periodicity_slot16;
+ break;
+ case NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT20:
+ nrppa_pos_semi_persistent->periodicity = NRPPA_ResourceTypeSemi_persistentPos__periodicity_slot20;
+ break;
+ case NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT32:
+ nrppa_pos_semi_persistent->periodicity = NRPPA_ResourceTypeSemi_persistentPos__periodicity_slot32;
+ break;
+ case NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT40:
+ nrppa_pos_semi_persistent->periodicity = NRPPA_ResourceTypeSemi_persistentPos__periodicity_slot40;
+ break;
+ case NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT64:
+ nrppa_pos_semi_persistent->periodicity = NRPPA_ResourceTypeSemi_persistentPos__periodicity_slot64;
+ break;
+ case NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT80:
+ nrppa_pos_semi_persistent->periodicity = NRPPA_ResourceTypeSemi_persistentPos__periodicity_slot80;
+ break;
+ case NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT160:
+ nrppa_pos_semi_persistent->periodicity = NRPPA_ResourceTypeSemi_persistentPos__periodicity_slot160;
+ break;
+ case NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT320:
+ nrppa_pos_semi_persistent->periodicity = NRPPA_ResourceTypeSemi_persistentPos__periodicity_slot320;
+ break;
+ case NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT640:
+ nrppa_pos_semi_persistent->periodicity = NRPPA_ResourceTypeSemi_persistentPos__periodicity_slot640;
+ break;
+ case NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT1280:
+ nrppa_pos_semi_persistent->periodicity = NRPPA_ResourceTypeSemi_persistentPos__periodicity_slot1280;
+ break;
+ case NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT2560:
+ nrppa_pos_semi_persistent->periodicity = NRPPA_ResourceTypeSemi_persistentPos__periodicity_slot2560;
+ break;
+ case NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT5120:
+ nrppa_pos_semi_persistent->periodicity = NRPPA_ResourceTypeSemi_persistentPos__periodicity_slot5120;
+ break;
+ case NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT10240:
+ nrppa_pos_semi_persistent->periodicity = NRPPA_ResourceTypeSemi_persistentPos__periodicity_slot10240;
+ break;
+ case NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT20480:
+ nrppa_pos_semi_persistent->periodicity = NRPPA_ResourceTypeSemi_persistentPos__periodicity_slot20480;
+ break;
+ case NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT40960:
+ nrppa_pos_semi_persistent->periodicity = NRPPA_ResourceTypeSemi_persistentPos__periodicity_slot40960;
+ break;
+ case NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT81920:
+ nrppa_pos_semi_persistent->periodicity = NRPPA_ResourceTypeSemi_persistentPos__periodicity_slot81920;
+ break;
+ default:
+ AssertFatal(false, "illegal periodicity %d\n", resource_type_pos->choice.semi_persistent.periodicity);
+ break;
+ }
+ nrppa_pos_semi_persistent->offset = resource_type_pos->choice.semi_persistent.offset;
+ } else if (resource_type_pos->present == NRPPA_RESOURCE_TYPE_POS_PR_APERIODIC) {
+ nrppa_resourceTypePos->present = NRPPA_ResourceTypePos_PR_aperiodic;
+ asn1cCalloc(nrppa_resourceTypePos->choice.aperiodic, nrppa_pos_aperiodic);
+ nrppa_pos_aperiodic->slotOffset = resource_type_pos->choice.aperiodic.slot_offset;
+ } else {
+ AssertFatal(false, "illegal resourceType %d\n", resource_type_pos->present);
+ }
+
+ nrppa_pos_srs_resource->sequenceId = pos_srs_resource->sequence_id;
+ }
+ }
+
+ // optional: srs_resource_set_list
+ if (in_config->srs_resource_set_list) {
+ nrppa_srs_resource_set_list_t *srs_resource_set_list = in_config->srs_resource_set_list;
+ uint32_t srs_resource_set_list_length = srs_resource_set_list->srs_resource_set_list_length;
+ asn1cCalloc(out_config.sRSResourceSet_List, nrppa_sRSResourceSet_List);
+ for (int i = 0; i < srs_resource_set_list_length; i++) {
+ asn1cSequenceAdd(nrppa_sRSResourceSet_List->list, NRPPA_SRSResourceSet_t, nrppa_srs_resource_set);
+ nrppa_srs_resource_set_t *srs_resource_set = &srs_resource_set_list->srs_resource_set[i];
+ nrppa_srs_resource_set->sRSResourceSetID = srs_resource_set->srs_resource_set_id;
+ uint8_t srs_resource_id_list_length = srs_resource_set->srs_resource_id_list.srs_resource_id_list_length;
+ for (int j = 0; j < srs_resource_id_list_length; j++) {
+ asn1cSequenceAdd(nrppa_srs_resource_set->sRSResourceID_List.list, NRPPA_SRSResourceID_t, nrppa_srs_resource_id);
+ *nrppa_srs_resource_id = srs_resource_set->srs_resource_id_list.srs_resource_id[j];
+ }
+
+ NRPPA_ResourceSetType_t *nrppa_resourceSetType = &nrppa_srs_resource_set->resourceSetType;
+ nrppa_resource_set_type_t *resource_set_type = &srs_resource_set->resource_set_type;
+ switch (resource_set_type->present) {
+ case NRPPA_RESOURCE_SET_TYPE_PR_NOTHING:
+ nrppa_resourceSetType->present = NRPPA_ResourceSetType_PR_NOTHING;
+ break;
+ case NRPPA_RESOURCE_SET_TYPE_PR_PERIODIC:
+ nrppa_resourceSetType->present = NRPPA_ResourceSetType_PR_periodic;
+ asn1cCalloc(nrppa_resourceSetType->choice.periodic, nrppa_periodic_set_type);
+ nrppa_periodic_set_type->periodicSet = resource_set_type->choice.periodic;
+ break;
+ case NRPPA_RESOURCE_SET_TYPE_PR_SEMI_PERSISTENT:
+ nrppa_resourceSetType->present = NRPPA_ResourceSetType_PR_semi_persistent;
+ asn1cCalloc(nrppa_resourceSetType->choice.semi_persistent, nrppa_semi_persistent_set_type);
+ nrppa_semi_persistent_set_type->semi_persistentSet = resource_set_type->choice.semi_persistent;
+ break;
+ case NRPPA_RESOURCE_SET_TYPE_PR_APERIODIC:
+ nrppa_resourceSetType->present = NRPPA_ResourceSetType_PR_aperiodic;
+ asn1cCalloc(nrppa_resourceSetType->choice.aperiodic, nrppa_aperiodic_set_type);
+ nrppa_aperiodic_set_type->sRSResourceTrigger = resource_set_type->choice.aperiodic.srs_resource_trigger;
+ nrppa_aperiodic_set_type->slotoffset = resource_set_type->choice.aperiodic.slot_offset;
+ break;
+ default:
+ AssertFatal(false, "illegal resource set type %d\n", resource_set_type->present);
+ break;
+ }
+ }
+ }
+
+ // optional: pos_srs_resource_set_list
+ if (in_config->pos_srs_resource_set_list) {
+ nrppa_pos_srs_resource_set_list_t *pos_srs_resource_set_list = in_config->pos_srs_resource_set_list;
+ uint32_t pos_srs_resource_set_list_length = pos_srs_resource_set_list->pos_srs_resource_set_list_length;
+ asn1cCalloc(out_config.posSRSResourceSet_List, nrppa_posSRSResourceSet_List);
+ for (int i = 0; i < pos_srs_resource_set_list_length; i++) {
+ asn1cSequenceAdd(nrppa_posSRSResourceSet_List->list, NRPPA_PosSRSResourceSet_Item_t, nrppa_pos_srs_resource_set);
+ nrppa_pos_srs_resource_set_item_t *pos_srs_resource_set = &pos_srs_resource_set_list->pos_srs_resource_set_item[i];
+ nrppa_pos_srs_resource_set->possrsResourceSetID = pos_srs_resource_set->pos_srs_resource_set_id;
+ uint8_t pos_srs_resource_id_list_length = pos_srs_resource_set->pos_srs_resource_id_list.pos_srs_resource_id_list_length;
+ for (int j = 0; j < pos_srs_resource_id_list_length; j++) {
+ asn1cSequenceAdd(nrppa_pos_srs_resource_set->possRSResourceID_List.list,
+ NRPPA_SRSPosResourceID_t,
+ nrppa_pos_srs_resource_id);
+ *nrppa_pos_srs_resource_id = pos_srs_resource_set->pos_srs_resource_id_list.srs_pos_resource_id[j];
+ }
+
+ NRPPA_PosResourceSetType_t *nrppa_posresourceSetType = &nrppa_pos_srs_resource_set->posresourceSetType;
+ nrppa_pos_resource_set_type_t *pos_resource_set_type = &pos_srs_resource_set->pos_resource_set_type;
+ switch (pos_resource_set_type->present) {
+ case NRPPA_POS_RESOURCE_SET_TYPE_PR_NOTHING:
+ nrppa_posresourceSetType->present = NRPPA_PosResourceSetType_PR_NOTHING;
+ break;
+ case NRPPA_POS_RESOURCE_SET_TYPE_PR_PERIODIC:
+ nrppa_posresourceSetType->present = NRPPA_PosResourceSetType_PR_periodic;
+ asn1cCalloc(nrppa_posresourceSetType->choice.periodic, nrppa_pos_periodic_set_type);
+ nrppa_pos_periodic_set_type->posperiodicSet = pos_resource_set_type->choice.periodic;
+ break;
+ case NRPPA_POS_RESOURCE_SET_TYPE_PR_SEMI_PERSISTENT:
+ nrppa_posresourceSetType->present = NRPPA_PosResourceSetType_PR_semi_persistent;
+ asn1cCalloc(nrppa_posresourceSetType->choice.semi_persistent, nrppa_pos_semi_persistent_set_type);
+ nrppa_pos_semi_persistent_set_type->possemi_persistentSet = pos_resource_set_type->choice.semi_persistent;
+ break;
+ case NRPPA_POS_RESOURCE_SET_TYPE_PR_APERIODIC:
+ nrppa_posresourceSetType->present = NRPPA_PosResourceSetType_PR_aperiodic;
+ asn1cCalloc(nrppa_posresourceSetType->choice.aperiodic, nrppa_pos_aperiodic_set_type);
+ nrppa_pos_aperiodic_set_type->sRSResourceTrigger = pos_resource_set_type->choice.srs_resource;
+ break;
+ default:
+ AssertFatal(false, "illegal resource set type pos %d\n", pos_resource_set_type->present);
+ break;
+ }
+ }
+ }
+ return out_config;
+}
+
+static NRPPA_SRSCarrier_List_Item_t encode_srs_carrier_list_item(const nrppa_srs_carrier_list_item_t *in_item)
+{
+ NRPPA_SRSCarrier_List_Item_t out_item = {0};
+ // pointA
+ out_item.pointA = in_item->pointA;
+
+ // Uplink Channel BW-PerSCS-List
+ const nrppa_uplink_channel_bw_per_scs_list_t *uplink_channel_bw_per_scs_list = &in_item->uplink_channel_bw_per_scs_list;
+ NRPPA_UplinkChannelBW_PerSCS_List_t *nrppa_uplink_channel_bw_per_scs_list = &out_item.uplinkChannelBW_PerSCS_List;
+
+ uint32_t scs_specific_carrier_list_length = uplink_channel_bw_per_scs_list->scs_specific_carrier_list_length;
+ for (int i = 0; i < scs_specific_carrier_list_length; i++) {
+ asn1cSequenceAdd(nrppa_uplink_channel_bw_per_scs_list->list, NRPPA_SCS_SpecificCarrier_t, nrppa_scs_specific_carrier);
+ nrppa_scs_specific_carrier_t *scs_specific_carrier = &uplink_channel_bw_per_scs_list->scs_specific_carrier[i];
+ // offset to carrier
+ nrppa_scs_specific_carrier->offsetToCarrier = scs_specific_carrier->offset_to_carrier;
+ // subcarrier spacing
+ switch (scs_specific_carrier->subcarrier_spacing) {
+ case NRPPA_SUBCARRIER_SPACING_15KHZ:
+ nrppa_scs_specific_carrier->subcarrierSpacing = NRPPA_SCS_SpecificCarrier__subcarrierSpacing_kHz15;
+ break;
+ case NRPPA_SUBCARRIER_SPACING_30KHZ:
+ nrppa_scs_specific_carrier->subcarrierSpacing = NRPPA_SCS_SpecificCarrier__subcarrierSpacing_kHz30;
+ break;
+ case NRPPA_SUBCARRIER_SPACING_60KHZ:
+ nrppa_scs_specific_carrier->subcarrierSpacing = NRPPA_SCS_SpecificCarrier__subcarrierSpacing_kHz60;
+ break;
+ case NRPPA_SUBCARRIER_SPACING_120KHZ:
+ nrppa_scs_specific_carrier->subcarrierSpacing = NRPPA_SCS_SpecificCarrier__subcarrierSpacing_kHz120;
+ break;
+ default:
+ AssertFatal(false, "illegal subcarrier spacing %d\n", scs_specific_carrier->subcarrier_spacing);
+ break;
+ }
+ // carrier bandwidth
+ nrppa_scs_specific_carrier->carrierBandwidth = scs_specific_carrier->carrier_bandwidth;
+ }
+
+ // Active UL BWP
+ NRPPA_ActiveULBWP_t *nrppa_active_ul_bwp = &out_item.activeULBWP;
+ const nrppa_active_ul_bwp_t *active_ul_bwp = &in_item->active_ul_bwp;
+
+ // location and bandwidth
+ nrppa_active_ul_bwp->locationAndBandwidth = active_ul_bwp->location_and_bandwidth;
+ // subcarrier spacing
+ switch (active_ul_bwp->subcarrier_spacing) {
+ case NRPPA_SUBCARRIER_SPACING_15KHZ:
+ nrppa_active_ul_bwp->subcarrierSpacing = NRPPA_ActiveULBWP__subcarrierSpacing_kHz15;
+ break;
+ case NRPPA_SUBCARRIER_SPACING_30KHZ:
+ nrppa_active_ul_bwp->subcarrierSpacing = NRPPA_ActiveULBWP__subcarrierSpacing_kHz30;
+ break;
+ case NRPPA_SUBCARRIER_SPACING_60KHZ:
+ nrppa_active_ul_bwp->subcarrierSpacing = NRPPA_ActiveULBWP__subcarrierSpacing_kHz60;
+ break;
+ case NRPPA_SUBCARRIER_SPACING_120KHZ:
+ nrppa_active_ul_bwp->subcarrierSpacing = NRPPA_ActiveULBWP__subcarrierSpacing_kHz120;
+ break;
+ default:
+ AssertFatal(false, "illegal subcarrier spacing %d\n", active_ul_bwp->subcarrier_spacing);
+ break;
+ }
+
+ // cyclic prefix
+ if (active_ul_bwp->cyclic_prefix == NRPPA_CP_TYPE_NORMAL)
+ nrppa_active_ul_bwp->cyclicPrefix = NRPPA_ActiveULBWP__cyclicPrefix_normal;
+ else
+ nrppa_active_ul_bwp->cyclicPrefix = NRPPA_ActiveULBWP__cyclicPrefix_extended;
+
+ // Tx Direct Current Location
+ nrppa_active_ul_bwp->txDirectCurrentLocation = active_ul_bwp->tx_direct_current_location;
+
+ // SRS Config
+ const nrppa_srs_config_t *sRSConfig = &active_ul_bwp->srs_config;
+ nrppa_active_ul_bwp->sRSConfig = encode_srs_config(sRSConfig);
+ return out_item;
+}
+
+NRPPA_SRSCarrier_List_t encode_srs_carrier_list_nrppa(const nrppa_srs_carrier_list_t *in_list)
+{
+ NRPPA_SRSCarrier_List_t out_list = {0};
+ uint32_t list_len = in_list->srs_carrier_list_length;
+ for (int i = 0; i < list_len; i++) {
+ asn1cSequenceAdd(out_list.list, NRPPA_SRSCarrier_List_Item_t, out_item);
+ nrppa_srs_carrier_list_item_t *in_item = &in_list->srs_carrier_list_item[i];
+ *out_item = encode_srs_carrier_list_item(in_item);
+ }
+ return out_list;
+}
+
+void free_srs_carrier_list(nrppa_srs_carrier_list_t *srs_carrier_list)
+{
+ uint32_t srs_carrier_list_len = srs_carrier_list->srs_carrier_list_length;
+ for (int i = 0; i < srs_carrier_list_len; i++) {
+ nrppa_srs_carrier_list_item_t *srs_carrier_list_item = &srs_carrier_list->srs_carrier_list_item[i];
+ free(srs_carrier_list_item->uplink_channel_bw_per_scs_list.scs_specific_carrier);
+
+ nrppa_active_ul_bwp_t *active_ul_bwp = &srs_carrier_list_item->active_ul_bwp;
+ nrppa_srs_config_t *sRSConfig = &active_ul_bwp->srs_config;
+ if (sRSConfig->srs_resource_list) {
+ nrppa_srs_resource_list_t *srs_resource_list = sRSConfig->srs_resource_list;
+ free(srs_resource_list->srs_resource);
+ free(sRSConfig->srs_resource_list);
+ }
+ if (sRSConfig->pos_srs_resource_list) {
+ nrppa_pos_srs_resource_list_t *pos_srs_resource_list = sRSConfig->pos_srs_resource_list;
+ free(pos_srs_resource_list->pos_srs_resource_item);
+ free(sRSConfig->pos_srs_resource_list);
+ }
+ if (sRSConfig->srs_resource_set_list) {
+ nrppa_srs_resource_set_list_t *srs_resource_set_list = sRSConfig->srs_resource_set_list;
+ uint32_t srs_resource_set_list_length = srs_resource_set_list->srs_resource_set_list_length;
+ for (int j = 0; j < srs_resource_set_list_length; j++) {
+ nrppa_srs_resource_set_t *srs_resource_set = &srs_resource_set_list->srs_resource_set[j];
+ free(srs_resource_set->srs_resource_id_list.srs_resource_id);
+ }
+ free(srs_resource_set_list->srs_resource_set);
+ free(sRSConfig->srs_resource_set_list);
+ }
+ if (sRSConfig->pos_srs_resource_set_list) {
+ nrppa_pos_srs_resource_set_list_t *pos_srs_resource_set_list = sRSConfig->pos_srs_resource_set_list;
+ uint32_t pos_srs_resource_set_list_length = pos_srs_resource_set_list->pos_srs_resource_set_list_length;
+ for (int j = 0; j < pos_srs_resource_set_list_length; j++) {
+ nrppa_pos_srs_resource_set_item_t *pos_srs_resource_set = &pos_srs_resource_set_list->pos_srs_resource_set_item[j];
+ free(pos_srs_resource_set->pos_srs_resource_id_list.srs_pos_resource_id);
+ }
+ free(pos_srs_resource_set_list->pos_srs_resource_set_item);
+ free(sRSConfig->pos_srs_resource_set_list);
+ }
+ }
+ free(srs_carrier_list->srs_carrier_list_item);
+}
+
+void free_positioning_information_response(nrppa_positioning_information_resp_t *msg)
+{
+ /* SRS Configuration (O) */
+ if (msg->srs_configuration) {
+ nrppa_srs_carrier_list_t *srs_carrier_list = &msg->srs_configuration->srs_carrier_list;
+ free_srs_carrier_list(srs_carrier_list);
+ free(msg->srs_configuration);
+ }
+}
+
+void decode_nrppa_srstype(NRPPA_SRSType_t *srs_type, nrppa_srs_type_t *out)
+{
+ switch (srs_type->present) {
+ case NRPPA_SRSType_PR_NOTHING:
+ out->present = NRPPA_SRS_TYPE_PR_NOTHING;
+ break;
+ case NRPPA_SRSType_PR_semipersistentSRS:
+ out->present = NRPPA_SRS_TYPE_PR_SEMIPERSISTENTSRS;
+ out->choice.srs_resource_set_id = calloc_or_fail(1, sizeof(*out->choice.srs_resource_set_id));
+ *out->choice.srs_resource_set_id = srs_type->choice.semipersistentSRS->sRSResourceSetID;
+ break;
+ case NRPPA_SRSType_PR_aperiodicSRS:
+ out->present = NRPPA_SRS_TYPE_PR_APERIODICSRS;
+ out->choice.aperiodic = calloc_or_fail(1, sizeof(*out->choice.aperiodic));
+ *out->choice.aperiodic = srs_type->choice.aperiodicSRS->aperiodic;
+ break;
+ default:
+ AssertFatal(false, "received illegal SRS type\n");
+ break;
+ }
+}
+
+void free_positioning_activation_request(nrppa_positioning_activation_req_t *msg)
+{
+ if (msg->srs_type.present == NRPPA_SRS_TYPE_PR_SEMIPERSISTENTSRS) {
+ free(msg->srs_type.choice.srs_resource_set_id);
+ } else if (msg->srs_type.present == NRPPA_SRS_TYPE_PR_APERIODICSRS) {
+ free(msg->srs_type.choice.aperiodic);
+ }
+}
+
+int nrppa_gNB_handle_trp_information_request(nrppa_gnb_ue_info_t *nrppa_msg_info, const NRPPA_NRPPA_PDU_t *pdu)
+{
+ LOG_I(NRPPA, "Processing Received TRP Information Request \n");
+ DevAssert(pdu != NULL);
+ DevAssert(nrppa_msg_info != NULL);
+
+ if (LOG_DEBUGFLAG(DEBUG_ASN1)) {
+ xer_fprint(stdout, &asn_DEF_NRPPA_NRPPA_PDU, pdu);
+ }
+
+ // Forward request to RRC
+ MessageDef *msg = itti_alloc_new_message(TASK_RRC_GNB, 0, NRPPA_TRP_INFORMATION_REQ);
+ nrppa_trp_information_req_t *req = &NRPPA_TRP_INFORMATION_REQ(msg);
+
+ // Processing Received TRPInformationRequest
+ NRPPA_TRPInformationRequest_t *container = NULL;
+ NRPPA_TRPInformationRequest_IEs_t *ie = NULL;
+
+ // IE 9.2.3 Message type : mandatory
+ container = &pdu->choice.initiatingMessage->value.choice.TRPInformationRequest;
+
+ // IE 9.2.4 nrppatransactionID : mandatory
+ req->transaction_id = pdu->choice.initiatingMessage->nrppatransactionID;
+
+ // IE TRP List : optional
+ NRPPA_FIND_PROTOCOLIE_BY_ID(NRPPA_TRPInformationRequest_IEs_t, ie, container, NRPPA_ProtocolIE_ID_id_TRPList, false);
+
+ if (ie == NULL) {
+ req->has_trp_list = false;
+ } else {
+ LOG_W(NRPPA, "TRPInformationRequest IE TRP List : not handled\n");
+ }
+
+ // IE TRP Information Type List: mandatory
+ // not implemented in oai-lmf
+ NRPPA_FIND_PROTOCOLIE_BY_ID(NRPPA_TRPInformationRequest_IEs_t,
+ ie,
+ container,
+ NRPPA_ProtocolIE_ID_id_TRPInformationTypeList,
+ false);
+
+ if (ie == NULL) {
+ LOG_W(NRPPA, "TRPInformationRequest IE TRP Information Type List is mandatory but not handled\n");
+ } else {
+ uint8_t trp_info_list_len = ie->value.choice.TRPInformationTypeList.list.count;
+ AssertError(trp_info_list_len > 0, return false, "at least 1 TRP Information Type must be present");
+ nrppa_trp_information_type_list_t *trp_info_list = &req->trp_information_type_list;
+ trp_info_list->trp_information_type_list_length = trp_info_list_len;
+ trp_info_list->trp_information_type_item = calloc_or_fail(trp_info_list_len, sizeof(*trp_info_list->trp_information_type_item));
+ for (int i = 0; i < trp_info_list_len; i++) {
+ trp_info_list->trp_information_type_item[i] = *ie->value.choice.TRPInformationTypeList.list.array[i];
+ }
+ }
+
+ nrppa_store_ue_context(nrppa_msg_info, req->transaction_id);
+
+ LOG_I(NRPPA, "Forwarding to RRC TRPInformationRequest transaction_id=%d\n", req->transaction_id);
+ itti_send_msg_to_task(TASK_RRC_GNB, 0, msg);
+ ASN_STRUCT_FREE_CONTENTS_ONLY(asn_DEF_NRPPA_NRPPA_PDU, &pdu);
+ return 0;
+}
+
+int nrppa_gNB_trp_information_response(instance_t instance, MessageDef *msg_p)
+{
+ DevAssert(msg_p);
+ nrppa_trp_information_resp_t *resp = &NRPPA_TRP_INFORMATION_RESP(msg_p);
+ nrppa_gNB_ue_context_t *ue_info = nrppa_detach_ue_context(resp->transaction_id);
+
+ if (ue_info->gNB_ue_ngap_id != 0 && ue_info->amf_ue_ngap_id != 0) {
+ LOG_E(NRPPA, "Illegal gNB_ue_ngap_id %d and amf_ue_ngap_id %ld\n", ue_info->gNB_ue_ngap_id, ue_info->amf_ue_ngap_id);
+ free_trp_information_response(resp);
+ nrppa_free_ue_context(ue_info);
+ return -1;
+ }
+
+ LOG_I(NRPPA, "Received TRP Information Response info from RRC with transaction_id = %u\n", ue_info->transaction_id);
+
+ // Prepare NRPPA TRP Information transfer Response
+ NRPPA_NRPPA_PDU_t pdu = {0};
+
+ // IE: 9.2.3 Message Type : mandatory
+ pdu.present = NRPPA_NRPPA_PDU_PR_successfulOutcome;
+ asn1cCalloc(pdu.choice.successfulOutcome, head);
+ head->procedureCode = NRPPA_ProcedureCode_id_tRPInformationExchange;
+ head->criticality = NRPPA_Criticality_reject;
+ head->value.present = NRPPA_SuccessfulOutcome__value_PR_TRPInformationResponse;
+
+ // IE 9.2.4 nrppatransactionID : mandatory
+ head->nrppatransactionID = resp->transaction_id;
+ NRPPA_TRPInformationResponse_t *out = &head->value.choice.TRPInformationResponse;
+
+ // IE TRP Information List : mandatory
+ {
+ asn1cSequenceAdd(out->protocolIEs.list, NRPPA_TRPInformationResponse_IEs_t, ie);
+ ie->id = NRPPA_ProtocolIE_ID_id_TRPInformationList;
+ ie->criticality = NRPPA_Criticality_ignore;
+ ie->value.present = NRPPA_TRPInformationResponse_IEs__value_PR_TRPInformationList;
+
+ uint32_t trp_info_item_len = resp->trp_information_list.trp_information_item_length;
+ for (int i = 0; i < trp_info_item_len; i++) {
+ // TRPInformationItem (M)
+ asn1cSequenceAdd(ie->value.choice.TRPInformationList.list, TRPInformationList__Member, trpinfolist_member);
+ nrppa_trp_information_t *nrppa_tRPInformation = &resp->trp_information_list.trp_information_item[i];
+
+ trpinfolist_member->tRP_ID = nrppa_tRPInformation->trp_id;
+
+ NRPPA_TRPInformation_t *trp_info = &trpinfolist_member->tRPInformation;
+
+ nrppa_trp_information_type_response_list_t *nrppa_tRPInformationTypeResponseList =
+ &nrppa_tRPInformation->trp_information_type_response_list;
+ uint8_t trp_info_type_resp_item_len = nrppa_tRPInformationTypeResponseList->trp_information_type_response_item_length;
+
+ for (int j = 0; j < trp_info_type_resp_item_len; j++) {
+ asn1cSequenceAdd(trp_info->list, NRPPA_TRPInformationItem_t, trp_info_item);
+ nrppa_trp_information_type_response_item_t *resp_item =
+ &nrppa_tRPInformationTypeResponseList->trp_information_type_response_item[j];
+ *trp_info_item = encode_trp_info_type_response_item_nrppa(resp_item);
+ }
+ }
+ }
+
+ free_trp_information_response(resp);
+
+ if (LOG_DEBUGFLAG(DEBUG_ASN1)) {
+ xer_fprint(stdout, &asn_DEF_NRPPA_NRPPA_PDU, &pdu);
+ }
+
+ // Encode NRPPA message
+ uint8_t *buffer = NULL;
+ uint32_t length = 0;
+ if (nrppa_gNB_encode_pdu(&pdu, &buffer, &length) < 0) {
+ LOG_E(NRPPA, "Failed to encode Uplink NRPPa TRP Information Response\n");
+ ASN_STRUCT_FREE_CONTENTS_ONLY(asn_DEF_NRPPA_NRPPA_PDU, &pdu);
+ return -1;
+ }
+
+ MessageDef *msg = itti_alloc_new_message(TASK_NRPPA, 0, NGAP_UPLINKNONUEASSOCIATEDNRPPA);
+ ngap_uplink_non_ue_associated_nrppa_t *ULNRPPA = &NGAP_UPLINKNONUEASSOCIATEDNRPPA(msg);
+
+ // Routing ID
+ ULNRPPA->routing_id = create_byte_array(ue_info->routing_id.len, ue_info->routing_id.buf);
+
+ // NRPPa PDU
+ ULNRPPA->nrppa_pdu = create_byte_array(length, buffer);
+
+ // Forward the NRPPA PDU to NGAP
+ itti_send_msg_to_task(TASK_NGAP, instance, msg);
+ nrppa_free_ue_context(ue_info);
+ free(buffer);
+
+ return length;
+}
+
+int nrppa_gNB_handle_positioning_information_request(nrppa_gnb_ue_info_t *nrppa_msg_info, const NRPPA_NRPPA_PDU_t *pdu)
+{
+ DevAssert(pdu != NULL);
+ DevAssert(nrppa_msg_info != NULL);
+
+ if (LOG_DEBUGFLAG(DEBUG_ASN1)) {
+ xer_fprint(stdout, &asn_DEF_NRPPA_NRPPA_PDU, pdu);
+ }
+
+ LOG_I(NRPPA, "Processing Received Positioning Information Request\n");
+
+ // Preparing positioning information request for RRC
+ MessageDef *msg = itti_alloc_new_message(TASK_RRC_GNB, 0, NRPPA_POSITIONING_INFORMATION_REQ);
+ nrppa_positioning_information_req_t *req = &NRPPA_POSITIONING_INFORMATION_REQ(msg);
+
+ // IE 9.2.4 nrppatransactionID : mandatory
+ req->transaction_id = pdu->choice.initiatingMessage->nrppatransactionID;
+
+ nrppa_store_ue_context(nrppa_msg_info, req->transaction_id);
+
+ LOG_I(NRPPA, "Forwarding to RRC Positioning Information Request transaction id=%d\n", req->transaction_id);
+
+ itti_send_msg_to_task(TASK_RRC_GNB, 0, msg);
+ ASN_STRUCT_FREE_CONTENTS_ONLY(asn_DEF_NRPPA_NRPPA_PDU, &pdu);
+ return 0;
+}
+
+int nrppa_gNB_positioning_information_response(instance_t instance, MessageDef *msg_p)
+{
+ DevAssert(msg_p);
+ nrppa_positioning_information_resp_t *resp = &NRPPA_POSITIONING_INFORMATION_RESP(msg_p);
+ nrppa_gNB_ue_context_t *ue_info = nrppa_detach_ue_context(resp->transaction_id);
+
+ if (ue_info->gNB_ue_ngap_id <= 0 && ue_info->amf_ue_ngap_id <= 0) {
+ LOG_E(NRPPA, "Illegal gNB_ue_ngap_id %d and amf_ue_ngap_id %ld\n", ue_info->gNB_ue_ngap_id, ue_info->amf_ue_ngap_id);
+ free_positioning_information_response(resp);
+ nrppa_free_ue_context(ue_info);
+ return -1;
+ }
+
+ LOG_I(NRPPA,
+ "Received Positioning Information Response info from RRC with transaction_id = %u and gNB_ue_ngap_id %u\n",
+ ue_info->transaction_id,
+ ue_info->gNB_ue_ngap_id);
+
+ // Prepare NRPPA TRP Information transfer Response
+ NRPPA_NRPPA_PDU_t pdu = {0};
+
+ // IE: 9.2.3 Message Type : mandatory
+ pdu.present = NRPPA_NRPPA_PDU_PR_successfulOutcome;
+ asn1cCalloc(pdu.choice.successfulOutcome, head);
+ head->procedureCode = NRPPA_ProcedureCode_id_positioningInformationExchange;
+ head->criticality = NRPPA_Criticality_reject;
+ head->value.present = NRPPA_SuccessfulOutcome__value_PR_PositioningInformationResponse;
+
+ // IE 9.2.4 nrppatransactionID : mandatory
+ head->nrppatransactionID = resp->transaction_id;
+ NRPPA_PositioningInformationResponse_t *out = &head->value.choice.PositioningInformationResponse;
+
+ // IE SRS Configuration : optional
+ {
+ if (resp->srs_configuration) {
+ asn1cSequenceAdd(out->protocolIEs.list, NRPPA_PositioningInformationResponse_IEs_t, ie);
+ ie->id = NRPPA_ProtocolIE_ID_id_SRSConfiguration;
+ ie->criticality = NRPPA_Criticality_ignore;
+ ie->value.present = NRPPA_PositioningInformationResponse_IEs__value_PR_SRSConfiguration;
+ nrppa_srs_carrier_list_t *srs_carrier_list = &resp->srs_configuration->srs_carrier_list;
+ ie->value.choice.SRSConfiguration.sRSCarrier_List = encode_srs_carrier_list_nrppa(srs_carrier_list);
+ }
+ }
+
+ free_positioning_information_response(resp);
+
+ LOG_I(NRPPA, "Calling encoder for Positioning Information Response \n");
+
+ if (LOG_DEBUGFLAG(DEBUG_ASN1)) {
+ xer_fprint(stdout, &asn_DEF_NRPPA_NRPPA_PDU, &pdu);
+ }
+
+ // Encode NRPPA message
+ uint8_t *buffer = NULL;
+ uint32_t length = 0;
+ if (nrppa_gNB_encode_pdu(&pdu, &buffer, &length) < 0) {
+ LOG_E(NRPPA, "Failed to encode Uplink NRPPa PositioningInformationResponse\n");
+ ASN_STRUCT_FREE_CONTENTS_ONLY(asn_DEF_NRPPA_NRPPA_PDU, &pdu);
+ return -1;
+ }
+
+ MessageDef *msg = itti_alloc_new_message(TASK_NRPPA, 0, NGAP_UPLINKUEASSOCIATEDNRPPA);
+ ngap_uplink_ue_associated_nrppa_t *ULNRPPA = &NGAP_UPLINKUEASSOCIATEDNRPPA(msg);
+
+ ULNRPPA->gNB_ue_ngap_id = ue_info->gNB_ue_ngap_id;
+ ULNRPPA->amf_ue_ngap_id = ue_info->amf_ue_ngap_id;
+
+ // Routing ID
+ ULNRPPA->routing_id = create_byte_array(ue_info->routing_id.len, ue_info->routing_id.buf);
+
+ // NRPPA PDU
+ ULNRPPA->nrppa_pdu = create_byte_array(length, buffer);
+
+ // Forward the NRPPA PDU to NGAP
+ itti_send_msg_to_task(TASK_NGAP, instance, msg);
+ nrppa_free_ue_context(ue_info);
+ free(buffer);
+ return length;
+}
+
+int nrppa_gNB_handle_positioning_activation_request(nrppa_gnb_ue_info_t *nrppa_msg_info, const NRPPA_NRPPA_PDU_t *pdu)
+{
+ LOG_I(NRPPA, "Processing Received Positioning Activation Request \n");
+ DevAssert(pdu != NULL);
+ DevAssert(nrppa_msg_info != NULL);
+
+ if (LOG_DEBUGFLAG(DEBUG_ASN1)) {
+ xer_fprint(stdout, &asn_DEF_NRPPA_NRPPA_PDU, pdu);
+ }
+
+ // Preparing positioning information request for RRC
+ MessageDef *msg = itti_alloc_new_message(TASK_RRC_GNB, 0, NRPPA_POSITIONING_ACTIVATION_REQ);
+ nrppa_positioning_activation_req_t *req = &NRPPA_POSITIONING_ACTIVATION_REQ(msg);
+
+ // Processing Received PositioningActivationRequest
+ NRPPA_PositioningActivationRequest_t *container = NULL;
+ NRPPA_PositioningActivationRequestIEs_t *ie = NULL;
+
+ // IE 9.2.3 Message type : mandatory
+ container = &pdu->choice.initiatingMessage->value.choice.PositioningActivationRequest;
+
+ // IE 9.2.4 nrppatransactionID : mandatory
+ req->transaction_id = pdu->choice.initiatingMessage->nrppatransactionID;
+
+ // IE SRSType : mandatory
+ NRPPA_FIND_PROTOCOLIE_BY_ID(NRPPA_PositioningActivationRequestIEs_t, ie, container, NRPPA_ProtocolIE_ID_id_SRSType, true);
+ decode_nrppa_srstype(&ie->value.choice.SRSType, &req->srs_type);
+
+ nrppa_store_ue_context(nrppa_msg_info, req->transaction_id);
+
+ LOG_I(NRPPA, "Forwarding to RRC Positioning Activation Request transaction id = %d\n", req->transaction_id);
+
+ itti_send_msg_to_task(TASK_RRC_GNB, 0, msg);
+ ASN_STRUCT_FREE_CONTENTS_ONLY(asn_DEF_NRPPA_NRPPA_PDU, &pdu);
+ return 0;
+}
+
+int nrppa_gNB_positioning_activation_response(instance_t instance, MessageDef *msg_p)
+{
+ DevAssert(msg_p);
+ nrppa_positioning_activation_resp_t *resp = &NRPPA_POSITIONING_ACTIVATION_RESP(msg_p);
+ nrppa_gNB_ue_context_t *ue_info = nrppa_detach_ue_context(resp->transaction_id);
+
+ if (ue_info->gNB_ue_ngap_id <= 0 && ue_info->amf_ue_ngap_id <= 0) {
+ LOG_E(NRPPA, "Illegal gNB_ue_ngap_id %d and amf_ue_ngap_id %ld\n", ue_info->gNB_ue_ngap_id, ue_info->amf_ue_ngap_id);
+ nrppa_free_ue_context(ue_info);
+ return -1;
+ }
+
+ LOG_I(NRPPA,
+ "Received PositioningInformationResponse info from RRC with transaction_id=%u and gNB_ue_ngap_id %u\n",
+ ue_info->transaction_id,
+ ue_info->gNB_ue_ngap_id);
+
+ // Prepare NRPPA TRP Information transfer Response
+ NRPPA_NRPPA_PDU_t pdu = {0};
+
+ // IE: 9.2.3 Message Type : mandatory
+ pdu.present = NRPPA_NRPPA_PDU_PR_successfulOutcome;
+ asn1cCalloc(pdu.choice.successfulOutcome, head);
+ head->procedureCode = NRPPA_ProcedureCode_id_positioningActivation;
+ head->criticality = NRPPA_Criticality_reject;
+ head->value.present = NRPPA_SuccessfulOutcome__value_PR_PositioningActivationResponse;
+
+ // IE 9.2.4 nrppatransactionID : mandatory
+ head->nrppatransactionID = resp->transaction_id;
+
+ LOG_I(NRPPA, "Calling encoder for PositioningActivationResponse \n");
+
+ if (LOG_DEBUGFLAG(DEBUG_ASN1)) {
+ xer_fprint(stdout, &asn_DEF_NRPPA_NRPPA_PDU, &pdu);
+ }
+
+ // Encode NRPPA message
+ uint8_t *buffer = NULL;
+ uint32_t length = 0;
+ if (nrppa_gNB_encode_pdu(&pdu, &buffer, &length) < 0) {
+ LOG_E(NRPPA, "Failed to encode Uplink NRPPa PositioningActivationResponse\n");
+ nrppa_free_ue_context(ue_info);
+ ASN_STRUCT_FREE_CONTENTS_ONLY(asn_DEF_NRPPA_NRPPA_PDU, &pdu);
+ return -1;
+ }
+
+ MessageDef *msg = itti_alloc_new_message(TASK_NRPPA, 0, NGAP_UPLINKUEASSOCIATEDNRPPA);
+ ngap_uplink_ue_associated_nrppa_t *ULNRPPA = &NGAP_UPLINKUEASSOCIATEDNRPPA(msg);
+
+ ULNRPPA->gNB_ue_ngap_id = ue_info->gNB_ue_ngap_id;
+ ULNRPPA->amf_ue_ngap_id = ue_info->amf_ue_ngap_id;
+
+ // Routing ID
+ ULNRPPA->routing_id = create_byte_array(ue_info->routing_id.len, ue_info->routing_id.buf);
+
+ // NRPPA PDU
+ ULNRPPA->nrppa_pdu = create_byte_array(length, buffer);
+
+ // Forward the NRPPA PDU to NGAP
+ itti_send_msg_to_task(TASK_NGAP, instance, msg);
+ nrppa_free_ue_context(ue_info);
+ free(buffer);
+ return length;
+}
diff --git a/openair3/NRPPA/nrppa_gNB_location_information_transfer.h b/openair3/NRPPA/nrppa_gNB_location_information_transfer.h
new file mode 100644
index 0000000000..29d73c0059
--- /dev/null
+++ b/openair3/NRPPA/nrppa_gNB_location_information_transfer.h
@@ -0,0 +1,41 @@
+/*
+ * Licensed to the OpenAirInterface (OAI) Software Alliance under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The OpenAirInterface Software Alliance licenses this file to You under
+ * the OAI Public License, Version 1.1 (the "License"); you may not use this file
+ * except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.openairinterface.org/?page_id=698
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *-------------------------------------------------------------------------------
+ * For more information about the OpenAirInterface (OAI) Software Alliance:
+ * contact@openairinterface.org
+ */
+
+#ifndef NRPPA_GNB_POSITIONING_PROCEDURES_H_
+#define NRPPA_GNB_POSITIONING_PROCEDURES_H_
+
+int nrppa_gNB_handle_trp_information_request(nrppa_gnb_ue_info_t *nrppa_msg_info, const NRPPA_NRPPA_PDU_t *pdu);
+void free_trp_information_request(nrppa_trp_information_req_t *msg);
+int nrppa_gNB_trp_information_response(instance_t instance, MessageDef *msg_p);
+void free_trp_information_request(nrppa_trp_information_req_t *msg);
+NRPPA_TRPInformationItem_t encode_trp_info_type_response_item_nrppa(nrppa_trp_information_type_response_item_t *in);
+void free_trp_information_response(nrppa_trp_information_resp_t *msg);
+int nrppa_gNB_handle_positioning_information_request(nrppa_gnb_ue_info_t *nrppa_msg_info, const NRPPA_NRPPA_PDU_t *pdu);
+int nrppa_gNB_positioning_information_response(instance_t instance, MessageDef *msg_p);
+NRPPA_SRSCarrier_List_t encode_srs_carrier_list_nrppa(const nrppa_srs_carrier_list_t *in_list);
+void free_srs_carrier_list(nrppa_srs_carrier_list_t *srs_carrier_list);
+void free_positioning_information_response(nrppa_positioning_information_resp_t *msg);
+int nrppa_gNB_handle_positioning_activation_request(nrppa_gnb_ue_info_t *nrppa_msg_info, const NRPPA_NRPPA_PDU_t *pdu);
+void decode_nrppa_srstype(NRPPA_SRSType_t *srs_type, nrppa_srs_type_t *out);
+void free_positioning_activation_request(nrppa_positioning_activation_req_t *msg);
+int nrppa_gNB_positioning_activation_response(instance_t instance, MessageDef *msg_p);
+
+#endif /* NRPPA_GNB_POSITIONING_PROCEDURES_H_ */
diff --git a/openair3/NRPPA/nrppa_gNB_measurement_information_transfer.c b/openair3/NRPPA/nrppa_gNB_measurement_information_transfer.c
new file mode 100644
index 0000000000..afeacae4c7
--- /dev/null
+++ b/openair3/NRPPA/nrppa_gNB_measurement_information_transfer.c
@@ -0,0 +1,1143 @@
+/*
+ * Licensed to the OpenAirInterface (OAI) Software Alliance under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The OpenAirInterface Software Alliance licenses this file to You under
+ * the OAI Public License, Version 1.1 (the "License"); you may not use this file
+ * except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.openairinterface.org/?page_id=698
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *-------------------------------------------------------------------------------
+ * For more information about the OpenAirInterface (OAI) Software Alliance:
+ * contact@openairinterface.org
+ */
+
+#include "intertask_interface.h"
+#include "nrppa_common.h"
+#include "nrppa_gNB_ue_context.h"
+#include "nrppa_messages_types.h"
+#include "nrppa_gNB_encoder.h"
+#include "openair3/UTILS/conversions.h"
+#include "nrppa_gNB_measurement_information_transfer.h"
+#include "nrppa_gNB_location_information_transfer.h"
+
+static void decode_srs_config(const NRPPA_SRSConfig_t *in_config, nrppa_srs_config_t *out_config)
+{
+ // optional: sRSResource_List
+ if (in_config->sRSResource_List) {
+ out_config->srs_resource_list = calloc_or_fail(1, sizeof(*out_config->srs_resource_list));
+ nrppa_srs_resource_list_t *srs_resource_list = out_config->srs_resource_list;
+ uint32_t srs_resource_list_length = in_config->sRSResource_List->list.count;
+ srs_resource_list->srs_resource_list_length = srs_resource_list_length;
+ srs_resource_list->srs_resource = calloc_or_fail(srs_resource_list_length, sizeof(*srs_resource_list->srs_resource));
+ for (int i = 0; i < srs_resource_list_length; i++) {
+ nrppa_srs_resource_t *srs_resource = &srs_resource_list->srs_resource[i];
+ NRPPA_SRSResource_t *nrppa_srs_resource = in_config->sRSResource_List->list.array[i];
+ srs_resource->srs_resource_id = nrppa_srs_resource->sRSResourceID;
+ switch (nrppa_srs_resource->nrofSRS_Ports) {
+ case NRPPA_SRSResource__nrofSRS_Ports_port1:
+ srs_resource->nr_of_srs_ports = NRPPA_SRS_NUMBER_OF_PORTS_N1;
+ break;
+ case NRPPA_SRSResource__nrofSRS_Ports_ports2:
+ srs_resource->nr_of_srs_ports = NRPPA_SRS_NUMBER_OF_PORTS_N2;
+ break;
+ case NRPPA_SRSResource__nrofSRS_Ports_ports4:
+ srs_resource->nr_of_srs_ports = NRPPA_SRS_NUMBER_OF_PORTS_N4;
+ break;
+ default:
+ AssertFatal(false, "illegal number of srs ports %ld\n", nrppa_srs_resource->nrofSRS_Ports);
+ break;
+ }
+
+ nrppa_transmission_comb_t *srs_tx_comb = &srs_resource->transmission_comb;
+ NRPPA_TransmissionComb_t *nrppa_srs_tx_comb = &nrppa_srs_resource->transmissionComb;
+ switch (nrppa_srs_tx_comb->present) {
+ case NRPPA_TransmissionComb_PR_NOTHING:
+ srs_tx_comb->present = NRPPA_TRANSMISSION_COMB_PR_NOTHING;
+ break;
+ case NRPPA_TransmissionComb_PR_n2:
+ srs_tx_comb->present = NRPPA_TRANSMISSION_COMB_PR_N2;
+ srs_tx_comb->choice.n2.comb_offset_n2 = nrppa_srs_tx_comb->choice.n2->combOffset_n2;
+ srs_tx_comb->choice.n2.cyclic_shift_n2 = nrppa_srs_tx_comb->choice.n2->cyclicShift_n2;
+ break;
+ case NRPPA_TransmissionComb_PR_n4:
+ srs_tx_comb->present = NRPPA_TRANSMISSION_COMB_PR_N4;
+ srs_tx_comb->choice.n4.comb_offset_n4 = nrppa_srs_tx_comb->choice.n4->combOffset_n4;
+ srs_tx_comb->choice.n4.cyclic_shift_n4 = nrppa_srs_tx_comb->choice.n4->cyclicShift_n4;
+ break;
+ default:
+ AssertFatal(false, "illegal transmissionComb %d\n", nrppa_srs_tx_comb->present);
+ break;
+ }
+
+ srs_resource->start_position = nrppa_srs_resource->startPosition;
+
+ switch (nrppa_srs_resource->nrofSymbols) {
+ case NRPPA_SRSResource__nrofSymbols_n1:
+ srs_resource->nr_of_symbols = NRPPA_SRS_NUMBER_OF_SYMBOLS_N1;
+ break;
+ case NRPPA_SRSResource__nrofSymbols_n2:
+ srs_resource->nr_of_symbols = NRPPA_SRS_NUMBER_OF_SYMBOLS_N2;
+ break;
+ case NRPPA_SRSResource__nrofSymbols_n4:
+ srs_resource->nr_of_symbols = NRPPA_SRS_NUMBER_OF_SYMBOLS_N4;
+ break;
+ default:
+ AssertFatal(false, "illegal number of symbols %ld\n", nrppa_srs_resource->nrofSymbols);
+ break;
+ }
+
+ switch (nrppa_srs_resource->repetitionFactor) {
+ case NRPPA_SRSResource__repetitionFactor_n1:
+ srs_resource->repetition_factor = NRPPA_SRS_REPETITION_FACTOR_RF1;
+ break;
+ case NRPPA_SRSResource__repetitionFactor_n2:
+ srs_resource->repetition_factor = NRPPA_SRS_REPETITION_FACTOR_RF2;
+ break;
+ case NRPPA_SRSResource__repetitionFactor_n4:
+ srs_resource->repetition_factor = NRPPA_SRS_REPETITION_FACTOR_RF4;
+ break;
+ default:
+ AssertFatal(false, "illegal repetition factor %ld\n", nrppa_srs_resource->repetitionFactor);
+ break;
+ }
+
+ srs_resource->freq_domain_position = nrppa_srs_resource->freqDomainPosition;
+ srs_resource->freq_domain_shift = nrppa_srs_resource->freqDomainShift;
+ srs_resource->c_srs = nrppa_srs_resource->c_SRS;
+ srs_resource->b_srs = nrppa_srs_resource->b_SRS;
+ srs_resource->b_hop = nrppa_srs_resource->b_hop;
+
+ switch (nrppa_srs_resource->groupOrSequenceHopping) {
+ case NRPPA_SRSResource__groupOrSequenceHopping_neither:
+ srs_resource->group_or_sequence_hopping = NRPPA_GROUPORSEQUENCEHOPPING_NOTHING;
+ break;
+ case NRPPA_SRSResource__groupOrSequenceHopping_groupHopping:
+ srs_resource->group_or_sequence_hopping = NRPPA_GROUPORSEQUENCEHOPPING_GROUPHOPPING;
+ break;
+ case NRPPA_SRSResource__groupOrSequenceHopping_sequenceHopping:
+ srs_resource->group_or_sequence_hopping = NRPPA_GROUPORSEQUENCEHOPPING_SEQUENCEHOPPING;
+ break;
+ default:
+ AssertFatal(false, "illegal groupOrSequenceHopping %ld\n", nrppa_srs_resource->groupOrSequenceHopping);
+ break;
+ }
+
+ NRPPA_ResourceType_t *nrppa_resourceType = &nrppa_srs_resource->resourceType;
+ nrppa_resource_type_t *resource_type = &srs_resource->resource_type;
+ if (nrppa_resourceType->present == NRPPA_ResourceType_PR_NOTHING) {
+ resource_type->present = NRPPA_RESOURCE_TYPE_PR_NOTHING;
+ } else if (nrppa_resourceType->present == NRPPA_ResourceType_PR_periodic) {
+ resource_type->present = NRPPA_RESOURCE_TYPE_PR_PERIODIC;
+ nrppa_resource_type_periodic_t *periodic = &resource_type->choice.periodic;
+ switch (nrppa_resourceType->choice.periodic->periodicity) {
+ case NRPPA_ResourceTypePeriodic__periodicity_slot1:
+ periodic->periodicity = NRPPA_SRS_RESOURCE_TYPE_PERIODICITY_SLOT1;
+ break;
+ case NRPPA_ResourceTypePeriodic__periodicity_slot2:
+ periodic->periodicity = NRPPA_SRS_RESOURCE_TYPE_PERIODICITY_SLOT2;
+ break;
+ case NRPPA_ResourceTypePeriodic__periodicity_slot4:
+ periodic->periodicity = NRPPA_SRS_RESOURCE_TYPE_PERIODICITY_SLOT4;
+ break;
+ case NRPPA_ResourceTypePeriodic__periodicity_slot5:
+ periodic->periodicity = NRPPA_SRS_RESOURCE_TYPE_PERIODICITY_SLOT5;
+ break;
+ case NRPPA_ResourceTypePeriodic__periodicity_slot8:
+ periodic->periodicity = NRPPA_SRS_RESOURCE_TYPE_PERIODICITY_SLOT8;
+ break;
+ case NRPPA_ResourceTypePeriodic__periodicity_slot10:
+ periodic->periodicity = NRPPA_SRS_RESOURCE_TYPE_PERIODICITY_SLOT10;
+ break;
+ case NRPPA_ResourceTypePeriodic__periodicity_slot16:
+ periodic->periodicity = NRPPA_SRS_RESOURCE_TYPE_PERIODICITY_SLOT16;
+ break;
+ case NRPPA_ResourceTypePeriodic__periodicity_slot20:
+ periodic->periodicity = NRPPA_SRS_RESOURCE_TYPE_PERIODICITY_SLOT20;
+ break;
+ case NRPPA_ResourceTypePeriodic__periodicity_slot32:
+ periodic->periodicity = NRPPA_SRS_RESOURCE_TYPE_PERIODICITY_SLOT32;
+ break;
+ case NRPPA_ResourceTypePeriodic__periodicity_slot40:
+ periodic->periodicity = NRPPA_SRS_RESOURCE_TYPE_PERIODICITY_SLOT40;
+ break;
+ case NRPPA_ResourceTypePeriodic__periodicity_slot64:
+ periodic->periodicity = NRPPA_SRS_RESOURCE_TYPE_PERIODICITY_SLOT64;
+ break;
+ case NRPPA_ResourceTypePeriodic__periodicity_slot80:
+ periodic->periodicity = NRPPA_SRS_RESOURCE_TYPE_PERIODICITY_SLOT80;
+ break;
+ case NRPPA_ResourceTypePeriodic__periodicity_slot160:
+ periodic->periodicity = NRPPA_SRS_RESOURCE_TYPE_PERIODICITY_SLOT160;
+ break;
+ case NRPPA_ResourceTypePeriodic__periodicity_slot320:
+ periodic->periodicity = NRPPA_SRS_RESOURCE_TYPE_PERIODICITY_SLOT320;
+ break;
+ case NRPPA_ResourceTypePeriodic__periodicity_slot640:
+ periodic->periodicity = NRPPA_SRS_RESOURCE_TYPE_PERIODICITY_SLOT640;
+ break;
+ case NRPPA_ResourceTypePeriodic__periodicity_slot1280:
+ periodic->periodicity = NRPPA_SRS_RESOURCE_TYPE_PERIODICITY_SLOT1280;
+ break;
+ case NRPPA_ResourceTypePeriodic__periodicity_slot2560:
+ periodic->periodicity = NRPPA_SRS_RESOURCE_TYPE_PERIODICITY_SLOT2560;
+ break;
+ default:
+ AssertFatal(false, "illegal periodicity %ld\n", nrppa_resourceType->choice.periodic->periodicity);
+ break;
+ }
+ periodic->offset = nrppa_resourceType->choice.periodic->offset;
+ } else if (nrppa_resourceType->present == NRPPA_ResourceType_PR_semi_persistent) {
+ resource_type->present = NRPPA_RESOURCE_TYPE_PR_SEMI_PERSISTENT;
+ nrppa_resource_type_semi_persistent_t *semi_persistent = &resource_type->choice.semi_persistent;
+ switch (nrppa_resourceType->choice.semi_persistent->periodicity) {
+ case NRPPA_ResourceTypeSemi_persistent__periodicity_slot1:
+ semi_persistent->periodicity = NRPPA_SRS_RESOURCE_TYPE_PERIODICITY_SLOT1;
+ break;
+ case NRPPA_ResourceTypeSemi_persistent__periodicity_slot2:
+ semi_persistent->periodicity = NRPPA_SRS_RESOURCE_TYPE_PERIODICITY_SLOT2;
+ break;
+ case NRPPA_ResourceTypeSemi_persistent__periodicity_slot4:
+ semi_persistent->periodicity = NRPPA_SRS_RESOURCE_TYPE_PERIODICITY_SLOT4;
+ break;
+ case NRPPA_ResourceTypeSemi_persistent__periodicity_slot5:
+ semi_persistent->periodicity = NRPPA_SRS_RESOURCE_TYPE_PERIODICITY_SLOT5;
+ break;
+ case NRPPA_ResourceTypeSemi_persistent__periodicity_slot8:
+ semi_persistent->periodicity = NRPPA_SRS_RESOURCE_TYPE_PERIODICITY_SLOT8;
+ break;
+ case NRPPA_ResourceTypeSemi_persistent__periodicity_slot10:
+ semi_persistent->periodicity = NRPPA_SRS_RESOURCE_TYPE_PERIODICITY_SLOT10;
+ break;
+ case NRPPA_ResourceTypeSemi_persistent__periodicity_slot16:
+ semi_persistent->periodicity = NRPPA_SRS_RESOURCE_TYPE_PERIODICITY_SLOT16;
+ break;
+ case NRPPA_ResourceTypeSemi_persistent__periodicity_slot20:
+ semi_persistent->periodicity = NRPPA_SRS_RESOURCE_TYPE_PERIODICITY_SLOT20;
+ break;
+ case NRPPA_ResourceTypeSemi_persistent__periodicity_slot32:
+ semi_persistent->periodicity = NRPPA_SRS_RESOURCE_TYPE_PERIODICITY_SLOT32;
+ break;
+ case NRPPA_ResourceTypeSemi_persistent__periodicity_slot40:
+ semi_persistent->periodicity = NRPPA_SRS_RESOURCE_TYPE_PERIODICITY_SLOT40;
+ break;
+ case NRPPA_ResourceTypeSemi_persistent__periodicity_slot64:
+ semi_persistent->periodicity = NRPPA_SRS_RESOURCE_TYPE_PERIODICITY_SLOT64;
+ break;
+ case NRPPA_ResourceTypeSemi_persistent__periodicity_slot80:
+ semi_persistent->periodicity = NRPPA_SRS_RESOURCE_TYPE_PERIODICITY_SLOT80;
+ break;
+ case NRPPA_ResourceTypeSemi_persistent__periodicity_slot160:
+ semi_persistent->periodicity = NRPPA_SRS_RESOURCE_TYPE_PERIODICITY_SLOT160;
+ break;
+ case NRPPA_ResourceTypeSemi_persistent__periodicity_slot320:
+ semi_persistent->periodicity = NRPPA_SRS_RESOURCE_TYPE_PERIODICITY_SLOT320;
+ break;
+ case NRPPA_ResourceTypeSemi_persistent__periodicity_slot640:
+ semi_persistent->periodicity = NRPPA_SRS_RESOURCE_TYPE_PERIODICITY_SLOT640;
+ break;
+ case NRPPA_ResourceTypeSemi_persistent__periodicity_slot1280:
+ semi_persistent->periodicity = NRPPA_SRS_RESOURCE_TYPE_PERIODICITY_SLOT1280;
+ break;
+ case NRPPA_ResourceTypeSemi_persistent__periodicity_slot2560:
+ semi_persistent->periodicity = NRPPA_SRS_RESOURCE_TYPE_PERIODICITY_SLOT2560;
+ break;
+ default:
+ AssertFatal(false, "illegal periodicity %ld\n", nrppa_resourceType->choice.semi_persistent->periodicity);
+ break;
+ }
+ semi_persistent->offset = nrppa_resourceType->choice.semi_persistent->offset;
+ } else if (nrppa_resourceType->present == NRPPA_ResourceType_PR_aperiodic) {
+ resource_type->present = NRPPA_RESOURCE_TYPE_PR_APERIODIC;
+ resource_type->choice.aperiodic = nrppa_resourceType->choice.aperiodic->aperiodicResourceType;
+ } else {
+ AssertFatal(false, "illegal resourceType %d\n", nrppa_resourceType->present);
+ }
+
+ srs_resource->sequence_id = nrppa_srs_resource->sequenceId;
+ }
+ }
+
+ // optional: posSRSResource_List
+ if (in_config->posSRSResource_List) {
+ out_config->pos_srs_resource_list = calloc_or_fail(1, sizeof(*out_config->pos_srs_resource_list));
+ nrppa_pos_srs_resource_list_t *pos_srs_resource_list = out_config->pos_srs_resource_list;
+ uint32_t pos_srs_resource_list_length = in_config->posSRSResource_List->list.count;
+ pos_srs_resource_list->pos_srs_resource_list_length = pos_srs_resource_list_length;
+ pos_srs_resource_list->pos_srs_resource_item =
+ calloc_or_fail(pos_srs_resource_list_length, sizeof(*pos_srs_resource_list->pos_srs_resource_item));
+ for (int i = 0; i < pos_srs_resource_list_length; i++) {
+ NRPPA_PosSRSResource_Item_t *nrppa_pos_srs_resource = in_config->posSRSResource_List->list.array[i];
+ nrppa_pos_srs_resource_item_t *pos_srs_resource = &pos_srs_resource_list->pos_srs_resource_item[i];
+ pos_srs_resource->srs_pos_resource_id = nrppa_pos_srs_resource->srs_PosResourceId;
+
+ NRPPA_TransmissionCombPos_t *nrppa_tx_comb_pos = &nrppa_pos_srs_resource->transmissionCombPos;
+ nrppa_transmission_comb_pos_t *tx_comb_pos = &pos_srs_resource->transmission_comb_pos;
+ switch (nrppa_tx_comb_pos->present) {
+ case NRPPA_TransmissionCombPos_PR_NOTHING:
+ tx_comb_pos->present = NRPPA_TRANSMISSION_COMB_POS_PR_NOTHING;
+ break;
+ case NRPPA_TransmissionCombPos_PR_n2:
+ tx_comb_pos->present = NRPPA_TRANSMISSION_COMB_POS_PR_N2;
+ tx_comb_pos->choice.n2.comb_offset_n2 = nrppa_tx_comb_pos->choice.n2->combOffset_n2;
+ tx_comb_pos->choice.n2.cyclic_shift_n2 = nrppa_tx_comb_pos->choice.n2->cyclicShift_n2;
+ break;
+ case NRPPA_TransmissionCombPos_PR_n4:
+ tx_comb_pos->present = NRPPA_TRANSMISSION_COMB_POS_PR_N4;
+ tx_comb_pos->choice.n4.comb_offset_n4 = nrppa_tx_comb_pos->choice.n4->combOffset_n4;
+ tx_comb_pos->choice.n4.cyclic_shift_n4 = nrppa_tx_comb_pos->choice.n4->cyclicShift_n4;
+ break;
+ case NRPPA_TransmissionCombPos_PR_n8:
+ tx_comb_pos->present = NRPPA_TRANSMISSION_COMB_POS_PR_N8;
+ tx_comb_pos->choice.n8.comb_offset_n8 = nrppa_tx_comb_pos->choice.n8->combOffset_n8;
+ tx_comb_pos->choice.n8.cyclic_shift_n8 = nrppa_tx_comb_pos->choice.n8->cyclicShift_n8;
+ break;
+ default:
+ AssertFatal(false, "illegal transmissionComb %d\n", nrppa_tx_comb_pos->present);
+ break;
+ }
+
+ pos_srs_resource->start_position = nrppa_pos_srs_resource->startPosition;
+
+ switch (nrppa_pos_srs_resource->nrofSymbols) {
+ case NRPPA_PosSRSResource_Item__nrofSymbols_n1:
+ pos_srs_resource->nr_of_symbols = NRPPA_SRS_RESOURCE_ITEM_NUMBER_OF_SYMBOLS_N1;
+ break;
+ case NRPPA_PosSRSResource_Item__nrofSymbols_n2:
+ pos_srs_resource->nr_of_symbols = NRPPA_SRS_RESOURCE_ITEM_NUMBER_OF_SYMBOLS_N2;
+ break;
+ case NRPPA_PosSRSResource_Item__nrofSymbols_n4:
+ pos_srs_resource->nr_of_symbols = NRPPA_SRS_RESOURCE_ITEM_NUMBER_OF_SYMBOLS_N4;
+ break;
+ case NRPPA_PosSRSResource_Item__nrofSymbols_n8:
+ pos_srs_resource->nr_of_symbols = NRPPA_SRS_RESOURCE_ITEM_NUMBER_OF_SYMBOLS_N8;
+ break;
+ case NRPPA_PosSRSResource_Item__nrofSymbols_n12:
+ pos_srs_resource->nr_of_symbols = NRPPA_SRS_RESOURCE_ITEM_NUMBER_OF_SYMBOLS_N12;
+ break;
+ default:
+ AssertFatal(false, "illegal number of symbols %ld\n", nrppa_pos_srs_resource->nrofSymbols);
+ break;
+ }
+
+ pos_srs_resource->freq_domain_shift = nrppa_pos_srs_resource->freqDomainShift;
+ pos_srs_resource->c_srs = nrppa_pos_srs_resource->c_SRS;
+
+ switch (nrppa_pos_srs_resource->groupOrSequenceHopping) {
+ case NRPPA_PosSRSResource_Item__groupOrSequenceHopping_neither:
+ pos_srs_resource->group_or_sequence_hopping = NRPPA_GROUPORSEQUENCEHOPPING_NOTHING;
+ break;
+ case NRPPA_PosSRSResource_Item__groupOrSequenceHopping_groupHopping:
+ pos_srs_resource->group_or_sequence_hopping = NRPPA_GROUPORSEQUENCEHOPPING_GROUPHOPPING;
+ break;
+ case NRPPA_PosSRSResource_Item__groupOrSequenceHopping_sequenceHopping:
+ pos_srs_resource->group_or_sequence_hopping = NRPPA_GROUPORSEQUENCEHOPPING_SEQUENCEHOPPING;
+ break;
+ default:
+ AssertFatal(false, "illegal groupOrSequenceHopping %ld\n", nrppa_pos_srs_resource->groupOrSequenceHopping);
+ break;
+ }
+
+ NRPPA_ResourceTypePos_t *nrppa_res_type_pos = &nrppa_pos_srs_resource->resourceTypePos;
+ nrppa_resource_type_pos_t *res_type_pos = &pos_srs_resource->resource_type_pos;
+ if (nrppa_res_type_pos->present == NRPPA_ResourceTypePos_PR_NOTHING) {
+ res_type_pos->present = NRPPA_RESOURCE_TYPE_POS_PR_NOTHING;
+ } else if (nrppa_res_type_pos->present == NRPPA_ResourceTypePos_PR_periodic) {
+ res_type_pos->present = NRPPA_RESOURCE_TYPE_POS_PR_PERIODIC;
+ nrppa_resource_type_periodic_pos_t *pos_periodic = &res_type_pos->choice.periodic;
+ switch (nrppa_res_type_pos->choice.periodic->periodicity) {
+ case NRPPA_ResourceTypePeriodicPos__periodicity_slot1:
+ pos_periodic->periodicity = NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT1;
+ break;
+ case NRPPA_ResourceTypePeriodicPos__periodicity_slot2:
+ pos_periodic->periodicity = NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT2;
+ break;
+ case NRPPA_ResourceTypePeriodicPos__periodicity_slot4:
+ pos_periodic->periodicity = NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT4;
+ break;
+ case NRPPA_ResourceTypePeriodicPos__periodicity_slot5:
+ pos_periodic->periodicity = NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT5;
+ break;
+ case NRPPA_ResourceTypePeriodicPos__periodicity_slot8:
+ pos_periodic->periodicity = NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT8;
+ break;
+ case NRPPA_ResourceTypePeriodicPos__periodicity_slot10:
+ pos_periodic->periodicity = NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT10;
+ break;
+ case NRPPA_ResourceTypePeriodicPos__periodicity_slot16:
+ pos_periodic->periodicity = NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT16;
+ break;
+ case NRPPA_ResourceTypePeriodicPos__periodicity_slot20:
+ pos_periodic->periodicity = NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT20;
+ break;
+ case NRPPA_ResourceTypePeriodicPos__periodicity_slot32:
+ pos_periodic->periodicity = NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT32;
+ break;
+ case NRPPA_ResourceTypePeriodicPos__periodicity_slot40:
+ pos_periodic->periodicity = NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT40;
+ break;
+ case NRPPA_ResourceTypePeriodicPos__periodicity_slot64:
+ pos_periodic->periodicity = NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT64;
+ break;
+ case NRPPA_ResourceTypePeriodicPos__periodicity_slot80:
+ pos_periodic->periodicity = NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT80;
+ break;
+ case NRPPA_ResourceTypePeriodicPos__periodicity_slot160:
+ pos_periodic->periodicity = NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT160;
+ break;
+ case NRPPA_ResourceTypePeriodicPos__periodicity_slot320:
+ pos_periodic->periodicity = NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT320;
+ break;
+ case NRPPA_ResourceTypePeriodicPos__periodicity_slot640:
+ pos_periodic->periodicity = NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT640;
+ break;
+ case NRPPA_ResourceTypePeriodicPos__periodicity_slot1280:
+ pos_periodic->periodicity = NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT1280;
+ break;
+ case NRPPA_ResourceTypePeriodicPos__periodicity_slot2560:
+ pos_periodic->periodicity = NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT2560;
+ break;
+ case NRPPA_ResourceTypePeriodicPos__periodicity_slot5120:
+ pos_periodic->periodicity = NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT5120;
+ break;
+ case NRPPA_ResourceTypePeriodicPos__periodicity_slot10240:
+ pos_periodic->periodicity = NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT10240;
+ break;
+ case NRPPA_ResourceTypePeriodicPos__periodicity_slot20480:
+ pos_periodic->periodicity = NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT20480;
+ break;
+ case NRPPA_ResourceTypePeriodicPos__periodicity_slot40960:
+ pos_periodic->periodicity = NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT40960;
+ break;
+ case NRPPA_ResourceTypePeriodicPos__periodicity_slot81920:
+ pos_periodic->periodicity = NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT81920;
+ break;
+ default:
+ AssertFatal(false, "illegal periodicity %ld\n", nrppa_res_type_pos->choice.periodic->periodicity);
+ break;
+ }
+ pos_periodic->offset = nrppa_res_type_pos->choice.periodic->offset;
+ } else if (nrppa_res_type_pos->present == NRPPA_ResourceTypePos_PR_semi_persistent) {
+ res_type_pos->present = NRPPA_RESOURCE_TYPE_POS_PR_SEMI_PERSISTENT;
+ nrppa_resource_type_semi_persistent_pos_t *pos_semi_persistent = &res_type_pos->choice.semi_persistent;
+ switch (nrppa_res_type_pos->choice.semi_persistent->periodicity) {
+ case NRPPA_ResourceTypeSemi_persistentPos__periodicity_slot1:
+ pos_semi_persistent->periodicity = NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT1;
+ break;
+ case NRPPA_ResourceTypeSemi_persistentPos__periodicity_slot2:
+ pos_semi_persistent->periodicity = NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT2;
+ break;
+ case NRPPA_ResourceTypeSemi_persistentPos__periodicity_slot4:
+ pos_semi_persistent->periodicity = NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT4;
+ break;
+ case NRPPA_ResourceTypeSemi_persistentPos__periodicity_slot5:
+ pos_semi_persistent->periodicity = NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT5;
+ break;
+ case NRPPA_ResourceTypeSemi_persistentPos__periodicity_slot8:
+ pos_semi_persistent->periodicity = NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT8;
+ break;
+ case NRPPA_ResourceTypeSemi_persistentPos__periodicity_slot10:
+ pos_semi_persistent->periodicity = NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT10;
+ break;
+ case NRPPA_ResourceTypeSemi_persistentPos__periodicity_slot16:
+ pos_semi_persistent->periodicity = NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT16;
+ break;
+ case NRPPA_ResourceTypeSemi_persistentPos__periodicity_slot20:
+ pos_semi_persistent->periodicity = NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT20;
+ break;
+ case NRPPA_ResourceTypeSemi_persistentPos__periodicity_slot32:
+ pos_semi_persistent->periodicity = NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT32;
+ break;
+ case NRPPA_ResourceTypeSemi_persistentPos__periodicity_slot40:
+ pos_semi_persistent->periodicity = NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT40;
+ break;
+ case NRPPA_ResourceTypeSemi_persistentPos__periodicity_slot64:
+ pos_semi_persistent->periodicity = NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT64;
+ break;
+ case NRPPA_ResourceTypeSemi_persistentPos__periodicity_slot80:
+ pos_semi_persistent->periodicity = NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT80;
+ break;
+ case NRPPA_ResourceTypeSemi_persistentPos__periodicity_slot160:
+ pos_semi_persistent->periodicity = NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT160;
+ break;
+ case NRPPA_ResourceTypeSemi_persistentPos__periodicity_slot320:
+ pos_semi_persistent->periodicity = NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT320;
+ break;
+ case NRPPA_ResourceTypeSemi_persistentPos__periodicity_slot640:
+ pos_semi_persistent->periodicity = NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT640;
+ break;
+ case NRPPA_ResourceTypeSemi_persistentPos__periodicity_slot1280:
+ pos_semi_persistent->periodicity = NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT1280;
+ break;
+ case NRPPA_ResourceTypeSemi_persistentPos__periodicity_slot2560:
+ pos_semi_persistent->periodicity = NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT2560;
+ break;
+ case NRPPA_ResourceTypeSemi_persistentPos__periodicity_slot5120:
+ pos_semi_persistent->periodicity = NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT5120;
+ break;
+ case NRPPA_ResourceTypeSemi_persistentPos__periodicity_slot10240:
+ pos_semi_persistent->periodicity = NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT10240;
+ break;
+ case NRPPA_ResourceTypeSemi_persistentPos__periodicity_slot20480:
+ pos_semi_persistent->periodicity = NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT20480;
+ break;
+ case NRPPA_ResourceTypeSemi_persistentPos__periodicity_slot40960:
+ pos_semi_persistent->periodicity = NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT40960;
+ break;
+ case NRPPA_ResourceTypeSemi_persistentPos__periodicity_slot81920:
+ pos_semi_persistent->periodicity = NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT81920;
+ break;
+ default:
+ AssertFatal(false, "illegal periodicity %ld\n", nrppa_res_type_pos->choice.semi_persistent->periodicity);
+ break;
+ }
+ pos_semi_persistent->offset = nrppa_res_type_pos->choice.semi_persistent->offset;
+ } else if (nrppa_res_type_pos->present == NRPPA_ResourceTypePos_PR_aperiodic) {
+ res_type_pos->present = NRPPA_RESOURCE_TYPE_POS_PR_APERIODIC;
+ res_type_pos->choice.aperiodic.slot_offset = nrppa_res_type_pos->choice.aperiodic->slotOffset;
+ } else {
+ AssertFatal(false, "illegal resourceType %d\n", nrppa_res_type_pos->present);
+ }
+
+ pos_srs_resource->sequence_id = nrppa_pos_srs_resource->sequenceId;
+ }
+ }
+
+ // optional: sRSResourceSet_List
+ if (in_config->sRSResourceSet_List) {
+ out_config->srs_resource_set_list = calloc_or_fail(1, sizeof(*out_config->srs_resource_set_list));
+ nrppa_srs_resource_set_list_t *srs_resource_set_list = out_config->srs_resource_set_list;
+ uint32_t srs_resource_set_list_length = in_config->sRSResourceSet_List->list.count;
+ srs_resource_set_list->srs_resource_set_list_length = srs_resource_set_list_length;
+ srs_resource_set_list->srs_resource_set =
+ calloc_or_fail(srs_resource_set_list_length, sizeof(*srs_resource_set_list->srs_resource_set));
+ for (int i = 0; i < srs_resource_set_list_length; i++) {
+ NRPPA_SRSResourceSet_t *nrppa_srs_resource_set = in_config->sRSResourceSet_List->list.array[i];
+ nrppa_srs_resource_set_t *srs_resource_set = &srs_resource_set_list->srs_resource_set[i];
+ srs_resource_set->srs_resource_set_id = nrppa_srs_resource_set->sRSResourceSetID;
+ uint8_t srs_resource_id_list_length = nrppa_srs_resource_set->sRSResourceID_List.list.count;
+ srs_resource_set->srs_resource_id_list.srs_resource_id_list_length = srs_resource_id_list_length;
+ srs_resource_set->srs_resource_id_list.srs_resource_id =
+ calloc_or_fail(srs_resource_id_list_length, sizeof(*srs_resource_set->srs_resource_id_list.srs_resource_id));
+ for (int j = 0; j < srs_resource_id_list_length; j++) {
+ NRPPA_SRSResourceID_t *nrppa_srs_resource_id = nrppa_srs_resource_set->sRSResourceID_List.list.array[j];
+ srs_resource_set->srs_resource_id_list.srs_resource_id[j] = *nrppa_srs_resource_id;
+ }
+
+ NRPPA_ResourceSetType_t *nrppa_res_set_type = &nrppa_srs_resource_set->resourceSetType;
+ nrppa_resource_set_type_t *res_set_type = &srs_resource_set->resource_set_type;
+ switch (nrppa_res_set_type->present) {
+ case NRPPA_ResourceSetType_PR_NOTHING:
+ res_set_type->present = NRPPA_RESOURCE_SET_TYPE_PR_NOTHING;
+ break;
+ case NRPPA_ResourceSetType_PR_periodic:
+ res_set_type->present = NRPPA_RESOURCE_SET_TYPE_PR_PERIODIC;
+ res_set_type->choice.periodic = nrppa_res_set_type->choice.periodic->periodicSet;
+ break;
+ case NRPPA_ResourceSetType_PR_semi_persistent:
+ res_set_type->present = NRPPA_RESOURCE_SET_TYPE_PR_SEMI_PERSISTENT;
+ res_set_type->choice.semi_persistent = nrppa_res_set_type->choice.semi_persistent->semi_persistentSet;
+ break;
+ case NRPPA_ResourceSetType_PR_aperiodic:
+ res_set_type->present = NRPPA_RESOURCE_SET_TYPE_PR_APERIODIC;
+ res_set_type->choice.aperiodic.srs_resource_trigger = nrppa_res_set_type->choice.aperiodic->sRSResourceTrigger;
+ res_set_type->choice.aperiodic.slot_offset = nrppa_res_set_type->choice.aperiodic->slotoffset;
+ break;
+ default:
+ AssertFatal(false, "illegal resource set type %d\n", nrppa_res_set_type->present);
+ break;
+ }
+ }
+ }
+
+ // optional: posSRSResourceSet_List
+ if (in_config->posSRSResourceSet_List) {
+ out_config->pos_srs_resource_set_list = calloc_or_fail(1, sizeof(*out_config->pos_srs_resource_set_list));
+ nrppa_pos_srs_resource_set_list_t *pos_srs_resource_set_list = out_config->pos_srs_resource_set_list;
+ uint32_t pos_srs_resource_set_list_length = in_config->posSRSResourceSet_List->list.count;
+ pos_srs_resource_set_list->pos_srs_resource_set_list_length = pos_srs_resource_set_list_length;
+ pos_srs_resource_set_list->pos_srs_resource_set_item =
+ calloc_or_fail(pos_srs_resource_set_list_length, sizeof(*pos_srs_resource_set_list->pos_srs_resource_set_item));
+ for (int i = 0; i < pos_srs_resource_set_list_length; i++) {
+ NRPPA_PosSRSResourceSet_Item_t *nrppa_pos_srs_resource_set = in_config->posSRSResourceSet_List->list.array[i];
+ nrppa_pos_srs_resource_set_item_t *pos_srs_resource_set = &pos_srs_resource_set_list->pos_srs_resource_set_item[i];
+ pos_srs_resource_set->pos_srs_resource_set_id = nrppa_pos_srs_resource_set->possrsResourceSetID;
+ uint8_t pos_srs_resource_id_list_length = nrppa_pos_srs_resource_set->possRSResourceID_List.list.count;
+ pos_srs_resource_set->pos_srs_resource_id_list.pos_srs_resource_id_list_length = pos_srs_resource_id_list_length;
+ pos_srs_resource_set->pos_srs_resource_id_list.srs_pos_resource_id =
+ calloc_or_fail(pos_srs_resource_id_list_length,
+ sizeof(*pos_srs_resource_set->pos_srs_resource_id_list.srs_pos_resource_id));
+ for (int j = 0; j < pos_srs_resource_id_list_length; j++) {
+ NRPPA_SRSPosResourceID_t *nrppa_pos_srs_resource_id = nrppa_pos_srs_resource_set->possRSResourceID_List.list.array[j];
+ pos_srs_resource_set->pos_srs_resource_id_list.srs_pos_resource_id[j] = *nrppa_pos_srs_resource_id;
+ }
+
+ NRPPA_PosResourceSetType_t *nrppa_pos_res_set_type = &nrppa_pos_srs_resource_set->posresourceSetType;
+ nrppa_pos_resource_set_type_t *pos_res_set_type = &pos_srs_resource_set->pos_resource_set_type;
+ switch (nrppa_pos_res_set_type->present) {
+ case NRPPA_PosResourceSetType_PR_NOTHING:
+ pos_res_set_type->present = NRPPA_POS_RESOURCE_SET_TYPE_PR_NOTHING;
+ break;
+ case NRPPA_PosResourceSetType_PR_periodic:
+ pos_res_set_type->present = NRPPA_POS_RESOURCE_SET_TYPE_PR_PERIODIC;
+ pos_res_set_type->choice.periodic = nrppa_pos_res_set_type->choice.periodic->posperiodicSet;
+ break;
+ case NRPPA_PosResourceSetType_PR_semi_persistent:
+ pos_res_set_type->present = NRPPA_POS_RESOURCE_SET_TYPE_PR_SEMI_PERSISTENT;
+ pos_res_set_type->choice.semi_persistent = nrppa_pos_res_set_type->choice.semi_persistent->possemi_persistentSet;
+ break;
+ case NRPPA_PosResourceSetType_PR_aperiodic:
+ pos_res_set_type->present = NRPPA_POS_RESOURCE_SET_TYPE_PR_APERIODIC;
+ pos_res_set_type->choice.srs_resource = nrppa_pos_res_set_type->choice.aperiodic->sRSResourceTrigger;
+ break;
+ default:
+ AssertFatal(false, "illegal resource set type pos %d\n", nrppa_pos_res_set_type->present);
+ break;
+ }
+ }
+ }
+}
+
+static void decode_srs_carrier_list_item(const NRPPA_SRSCarrier_List_Item_t *in_item, nrppa_srs_carrier_list_item_t *out_item)
+{
+ // pointA
+ out_item->pointA = in_item->pointA;
+
+ // Uplink Channel BW-PerSCS-List
+ nrppa_uplink_channel_bw_per_scs_list_t *uplink_channel_bw_per_scs_list = &out_item->uplink_channel_bw_per_scs_list;
+ const NRPPA_UplinkChannelBW_PerSCS_List_t *nrppa_uplink_channel_bw_per_scs_list = &in_item->uplinkChannelBW_PerSCS_List;
+
+ uint32_t scs_specific_carrier_list_length = nrppa_uplink_channel_bw_per_scs_list->list.count;
+ AssertFatal(scs_specific_carrier_list_length > 0, "Atleast 1 uplink channel bw per scs list should be present\n");
+ uplink_channel_bw_per_scs_list->scs_specific_carrier_list_length = scs_specific_carrier_list_length;
+ uplink_channel_bw_per_scs_list->scs_specific_carrier =
+ calloc_or_fail(scs_specific_carrier_list_length, sizeof(*uplink_channel_bw_per_scs_list->scs_specific_carrier));
+ for (int i = 0; i < scs_specific_carrier_list_length; i++) {
+ NRPPA_SCS_SpecificCarrier_t *nrppa_scs_specific_carrier = nrppa_uplink_channel_bw_per_scs_list->list.array[i];
+ nrppa_scs_specific_carrier_t *scs_specific_carrier = &uplink_channel_bw_per_scs_list->scs_specific_carrier[i];
+ // offset to carrier
+ scs_specific_carrier->offset_to_carrier = nrppa_scs_specific_carrier->offsetToCarrier;
+ // subcarrier spacing
+ switch (nrppa_scs_specific_carrier->subcarrierSpacing) {
+ case NRPPA_SCS_SpecificCarrier__subcarrierSpacing_kHz15:
+ scs_specific_carrier->subcarrier_spacing = NRPPA_SUBCARRIER_SPACING_15KHZ;
+ break;
+ case NRPPA_SCS_SpecificCarrier__subcarrierSpacing_kHz30:
+ scs_specific_carrier->subcarrier_spacing = NRPPA_SUBCARRIER_SPACING_30KHZ;
+ break;
+ case NRPPA_SCS_SpecificCarrier__subcarrierSpacing_kHz60:
+ scs_specific_carrier->subcarrier_spacing = NRPPA_SUBCARRIER_SPACING_60KHZ;
+ break;
+ case NRPPA_SCS_SpecificCarrier__subcarrierSpacing_kHz120:
+ scs_specific_carrier->subcarrier_spacing = NRPPA_SUBCARRIER_SPACING_120KHZ;
+ break;
+ default:
+ AssertFatal(false, "illegal subcarrier spacing %ld\n", nrppa_scs_specific_carrier->subcarrierSpacing);
+ break;
+ }
+ // carrier bandwidth
+ scs_specific_carrier->carrier_bandwidth = nrppa_scs_specific_carrier->carrierBandwidth;
+ }
+
+ // Active UL BWP
+ const NRPPA_ActiveULBWP_t *nrppa_active_ul_bwp = &in_item->activeULBWP;
+ nrppa_active_ul_bwp_t *active_ul_bwp = &out_item->active_ul_bwp;
+
+ // location and bandwidth
+ active_ul_bwp->location_and_bandwidth = nrppa_active_ul_bwp->locationAndBandwidth;
+ // subcarrier spacing
+ switch (nrppa_active_ul_bwp->subcarrierSpacing) {
+ case NRPPA_ActiveULBWP__subcarrierSpacing_kHz15:
+ active_ul_bwp->subcarrier_spacing = NRPPA_SUBCARRIER_SPACING_15KHZ;
+ break;
+ case NRPPA_ActiveULBWP__subcarrierSpacing_kHz30:
+ active_ul_bwp->subcarrier_spacing = NRPPA_SUBCARRIER_SPACING_30KHZ;
+ break;
+ case NRPPA_ActiveULBWP__subcarrierSpacing_kHz60:
+ active_ul_bwp->subcarrier_spacing = NRPPA_SUBCARRIER_SPACING_60KHZ;
+ break;
+ case NRPPA_ActiveULBWP__subcarrierSpacing_kHz120:
+ active_ul_bwp->subcarrier_spacing = NRPPA_SUBCARRIER_SPACING_120KHZ;
+ break;
+ default:
+ AssertFatal(false, "illegal subcarrier spacing %ld\n", nrppa_active_ul_bwp->subcarrierSpacing);
+ break;
+ }
+
+ // cyclic prefix
+ if (nrppa_active_ul_bwp->cyclicPrefix == NRPPA_ActiveULBWP__cyclicPrefix_normal)
+ active_ul_bwp->cyclic_prefix = NRPPA_CP_TYPE_NORMAL;
+ else
+ active_ul_bwp->cyclic_prefix = NRPPA_CP_TYPE_EXTENDED;
+
+ // Tx Direct Current Location
+ active_ul_bwp->tx_direct_current_location = nrppa_active_ul_bwp->txDirectCurrentLocation;
+
+ // SRS Config
+ const NRPPA_SRSConfig_t *nrppa_sRSConfig = &nrppa_active_ul_bwp->sRSConfig;
+ nrppa_srs_config_t *sRSConfig = &active_ul_bwp->srs_config;
+ decode_srs_config(nrppa_sRSConfig, sRSConfig);
+}
+
+void decode_srs_carrier_list(nrppa_srs_carrier_list_t *out_list, const NRPPA_SRSCarrier_List_t *in_list)
+{
+ uint32_t list_len = in_list->list.count;
+ AssertFatal(list_len > 0, "atleast 1 SRS carrier list must be present");
+ out_list->srs_carrier_list_length = list_len;
+ out_list->srs_carrier_list_item = calloc_or_fail(list_len, sizeof(*out_list->srs_carrier_list_item));
+ for (int i = 0; i < list_len; i++) {
+ NRPPA_SRSCarrier_List_Item_t *in_item = in_list->list.array[i];
+ nrppa_srs_carrier_list_item_t *out_item = &out_list->srs_carrier_list_item[i];
+ decode_srs_carrier_list_item(in_item, out_item);
+ }
+}
+
+void free_measurement_request(nrppa_measurement_req_t *msg)
+{
+ free(msg->trp_measurement_request_list.trp_measurement_request_item);
+ if (msg->measurement_quantities.measurement_quantities_item) {
+ free(msg->measurement_quantities.measurement_quantities_item);
+ }
+
+ /* SRS Configuration (O) */
+ if (msg->srs_configuration) {
+ nrppa_srs_carrier_list_t *srs_carrier_list = &msg->srs_configuration->srs_carrier_list;
+ free_srs_carrier_list(srs_carrier_list);
+ free(msg->srs_configuration);
+ }
+}
+
+static NRPPA_TrpMeasurementResult_t encode_measurement_results(nrppa_measurement_result_t *in_result)
+{
+ NRPPA_TrpMeasurementResult_t out_result = {0};
+ for (int i = 0; i < in_result->measurement_result_item_length; i++) {
+ asn1cSequenceAdd(out_result.list, NRPPA_TrpMeasurementResultItem_t, out_item);
+ nrppa_measurement_result_item_t *in_item = &in_result->measurement_result_item[i];
+ NRPPA_TrpMeasuredResultsValue_t *out_meas_res_val = &out_item->measuredResultsValue;
+ nrppa_measured_results_value_t *in_meas_res_val = &in_item->measured_results_value;
+ switch (in_meas_res_val->present) {
+ case NRPPA_MEASURED_RESULTS_VALUE_PR_NOTHING:
+ out_meas_res_val->present = NRPPA_TrpMeasuredResultsValue_PR_NOTHING;
+ break;
+ case NRPPA_MEASURED_RESULTS_VALUE_PR_UL_ANGLEOFARRIVAL:
+ out_meas_res_val->present = NRPPA_TrpMeasuredResultsValue_PR_uL_AngleOfArrival;
+ asn1cCalloc(out_meas_res_val->choice.uL_AngleOfArrival, out_ul_aoa);
+ nrppa_ul_aoa_t *in_ul_aoa = &in_meas_res_val->choice.ul_angle_of_arrival;
+ out_ul_aoa->azimuthAoA = in_ul_aoa->azimuth_aoa;
+ if (in_ul_aoa->zenith_aoa) {
+ asn1cCalloc(out_ul_aoa->zenithAoA, out_z_aoa);
+ *out_z_aoa = *in_ul_aoa->zenith_aoa;
+ }
+ break;
+ case NRPPA_MEASURED_RESULTS_VALUE_PR_UL_SRS_RSRP:
+ out_meas_res_val->present = NRPPA_TrpMeasuredResultsValue_PR_uL_SRS_RSRP;
+ out_meas_res_val->choice.uL_SRS_RSRP = in_meas_res_val->choice.ul_srs_rsrp;
+ break;
+ case NRPPA_MEASURED_RESULTS_VALUE_PR_UL_RTOA:
+ out_meas_res_val->present = NRPPA_TrpMeasuredResultsValue_PR_uL_RTOA;
+ asn1cCalloc(out_meas_res_val->choice.uL_RTOA, out_ul_rtoa);
+ nrppa_ul_rtoa_measurement_t *in_ul_rtoa = &in_meas_res_val->choice.ul_rtoa;
+ switch (in_ul_rtoa->present) {
+ case NRPPA_ULRTOAMEAS_PR_NOTHING:
+ out_ul_rtoa->uLRTOAmeas.present = NRPPA_ULRTOAMeas_PR_NOTHING;
+ break;
+ case NRPPA_ULRTOAMEAS_PR_K0:
+ out_ul_rtoa->uLRTOAmeas.present = NRPPA_ULRTOAMeas_PR_k0;
+ out_ul_rtoa->uLRTOAmeas.choice.k0 = in_ul_rtoa->choice.k0;
+ break;
+ case NRPPA_ULRTOAMEAS_PR_K1:
+ out_ul_rtoa->uLRTOAmeas.present = NRPPA_ULRTOAMeas_PR_k1;
+ out_ul_rtoa->uLRTOAmeas.choice.k1 = in_ul_rtoa->choice.k1;
+ break;
+ case NRPPA_ULRTOAMEAS_PR_K2:
+ out_ul_rtoa->uLRTOAmeas.present = NRPPA_ULRTOAMeas_PR_k2;
+ out_ul_rtoa->uLRTOAmeas.choice.k2 = in_ul_rtoa->choice.k2;
+ break;
+ case NRPPA_ULRTOAMEAS_PR_K3:
+ out_ul_rtoa->uLRTOAmeas.present = NRPPA_ULRTOAMeas_PR_k3;
+ out_ul_rtoa->uLRTOAmeas.choice.k3 = in_ul_rtoa->choice.k3;
+ break;
+ case NRPPA_ULRTOAMEAS_PR_K4:
+ out_ul_rtoa->uLRTOAmeas.present = NRPPA_ULRTOAMeas_PR_k4;
+ out_ul_rtoa->uLRTOAmeas.choice.k4 = in_ul_rtoa->choice.k4;
+ break;
+ case NRPPA_ULRTOAMEAS_PR_K5:
+ out_ul_rtoa->uLRTOAmeas.present = NRPPA_ULRTOAMeas_PR_k5;
+ out_ul_rtoa->uLRTOAmeas.choice.k5 = in_ul_rtoa->choice.k5;
+ break;
+ default:
+ AssertFatal(false, "illegal ul rtoa measure type\n");
+ break;
+ }
+ break;
+ case NRPPA_MEASURED_RESULTS_VALUE_PR_GNB_RXTXTIMEDIFF:
+ out_meas_res_val->present = NRPPA_TrpMeasuredResultsValue_PR_gNB_RxTxTimeDiff;
+ asn1cCalloc(out_meas_res_val->choice.gNB_RxTxTimeDiff, out_rxtx_time_diff);
+ nrppa_gnb_rx_tx_time_diff_t *in_rxtx_time_diff = &in_meas_res_val->choice.gnb_rx_tx_time_diff;
+ switch (in_rxtx_time_diff->present) {
+ case NRPPA_GNBRXTXTIMEDIFFMEAS_PR_NOTHING:
+ out_rxtx_time_diff->rxTxTimeDiff.present = NRPPA_GNBRxTxTimeDiffMeas_PR_NOTHING;
+ break;
+ case NRPPA_GNBRXTXTIMEDIFFMEAS_PR_K0:
+ out_rxtx_time_diff->rxTxTimeDiff.present = NRPPA_GNBRxTxTimeDiffMeas_PR_k0;
+ out_rxtx_time_diff->rxTxTimeDiff.choice.k0 = in_rxtx_time_diff->choice.k0;
+ break;
+ case NRPPA_GNBRXTXTIMEDIFFMEAS_PR_K1:
+ out_rxtx_time_diff->rxTxTimeDiff.present = NRPPA_GNBRxTxTimeDiffMeas_PR_k1;
+ out_rxtx_time_diff->rxTxTimeDiff.choice.k1 = in_rxtx_time_diff->choice.k1;
+ break;
+ case NRPPA_GNBRXTXTIMEDIFFMEAS_PR_K2:
+ out_rxtx_time_diff->rxTxTimeDiff.present = NRPPA_GNBRxTxTimeDiffMeas_PR_k2;
+ out_rxtx_time_diff->rxTxTimeDiff.choice.k2 = in_rxtx_time_diff->choice.k2;
+ break;
+ case NRPPA_GNBRXTXTIMEDIFFMEAS_PR_K3:
+ out_rxtx_time_diff->rxTxTimeDiff.present = NRPPA_GNBRxTxTimeDiffMeas_PR_k3;
+ out_rxtx_time_diff->rxTxTimeDiff.choice.k3 = in_rxtx_time_diff->choice.k3;
+ break;
+ case NRPPA_GNBRXTXTIMEDIFFMEAS_PR_K4:
+ out_rxtx_time_diff->rxTxTimeDiff.present = NRPPA_GNBRxTxTimeDiffMeas_PR_k4;
+ out_rxtx_time_diff->rxTxTimeDiff.choice.k4 = in_rxtx_time_diff->choice.k4;
+ break;
+ case NRPPA_GNBRXTXTIMEDIFFMEAS_PR_K5:
+ out_rxtx_time_diff->rxTxTimeDiff.present = NRPPA_GNBRxTxTimeDiffMeas_PR_k5;
+ out_rxtx_time_diff->rxTxTimeDiff.choice.k5 = in_rxtx_time_diff->choice.k5;
+ break;
+ default:
+ AssertFatal(false, "illegal ul rtoa measure type\n");
+ break;
+ }
+ break;
+ default:
+ AssertFatal(false, "illegal measured results type\n");
+ break;
+ }
+
+ NRPPA_TimeStamp_t *out_time_stamp = &out_item->timeStamp;
+ nrppa_time_stamp_t *in_time_stamp = &in_item->time_stamp;
+ out_time_stamp->systemFrameNumber = in_time_stamp->system_frame_number;
+ switch (in_time_stamp->slot_index.present) {
+ case NRPPA_TIME_STAMP_SLOT_INDEX_PR_NOTHING:
+ out_time_stamp->slotIndex.present = NRPPA_TimeStampSlotIndex_PR_NOTHING;
+ break;
+ case NRPPA_TIME_STAMP_SLOT_INDEX_PR_SCS_15:
+ out_time_stamp->slotIndex.present = NRPPA_TimeStampSlotIndex_PR_sCS_15;
+ out_time_stamp->slotIndex.choice.sCS_15 = in_time_stamp->slot_index.choice.scs_15;
+ break;
+ case NRPPA_TIME_STAMP_SLOT_INDEX_PR_SCS_30:
+ out_time_stamp->slotIndex.present = NRPPA_TimeStampSlotIndex_PR_sCS_30;
+ out_time_stamp->slotIndex.choice.sCS_30 = in_time_stamp->slot_index.choice.scs_30;
+ break;
+ case NRPPA_TIME_STAMP_SLOT_INDEX_PR_SCS_60:
+ out_time_stamp->slotIndex.present = NRPPA_TimeStampSlotIndex_PR_sCS_60;
+ out_time_stamp->slotIndex.choice.sCS_60 = in_time_stamp->slot_index.choice.scs_60;
+ break;
+ case NRPPA_TIME_STAMP_SLOT_INDEX_PR_SCS_120:
+ out_time_stamp->slotIndex.present = NRPPA_TimeStampSlotIndex_PR_sCS_120;
+ out_time_stamp->slotIndex.choice.sCS_120 = in_time_stamp->slot_index.choice.scs_120;
+ break;
+ default:
+ AssertFatal(false, "illegal slot index\n");
+ break;
+ }
+ }
+ return out_result;
+}
+
+NRPPA_TRP_MeasurementResponseList_t encode_trp_measurement_reponse_list(nrppa_measurement_response_list_t *in_list)
+{
+ NRPPA_TRP_MeasurementResponseList_t out_list = {0};
+ for (int i = 0; i < in_list->measurement_response_list_length; i++) {
+ asn1cSequenceAdd(out_list.list, NRPPA_TRP_MeasurementResponseItem_t, out_item);
+ nrppa_measurement_response_item_t *in_item = &in_list->measurement_response_item[i];
+ out_item->tRP_ID = in_item->trp_id;
+ out_item->measurementResult = encode_measurement_results(&in_item->measurement_result);
+ }
+
+ return out_list;
+}
+
+void free_measurement_resp(nrppa_measurement_resp_t *msg)
+{
+ if (msg->measurement_response_list) {
+ nrppa_measurement_response_list_t *list = msg->measurement_response_list;
+ uint32_t meas_resp_list_len = list->measurement_response_list_length;
+ for (int i = 0; i < meas_resp_list_len; i++) {
+ nrppa_measurement_response_item_t *meas_response_item = &list->measurement_response_item[i];
+ nrppa_measurement_result_t *MeasurementResult = &meas_response_item->measurement_result;
+ uint32_t meas_result_length = MeasurementResult->measurement_result_item_length;
+ for (int j = 0; j < meas_result_length; j++) {
+ nrppa_measurement_result_item_t *item = &MeasurementResult->measurement_result_item[j];
+ nrppa_measured_results_value_t *measuredResultsValue = &item->measured_results_value;
+ if (measuredResultsValue->present == NRPPA_MEASURED_RESULTS_VALUE_PR_UL_ANGLEOFARRIVAL) {
+ if (measuredResultsValue->choice.ul_angle_of_arrival.zenith_aoa) {
+ free(measuredResultsValue->choice.ul_angle_of_arrival.zenith_aoa);
+ }
+ }
+ }
+ free(MeasurementResult->measurement_result_item);
+ }
+ free(msg->measurement_response_list->measurement_response_item);
+ free(msg->measurement_response_list);
+ }
+}
+
+int nrppa_gNB_handle_measurement_request(nrppa_gnb_ue_info_t *nrppa_msg_info, const NRPPA_NRPPA_PDU_t *pdu)
+{
+ DevAssert(pdu != NULL);
+ DevAssert(nrppa_msg_info != NULL);
+
+ LOG_I(NRPPA, "Processing Received Measurement Request \n");
+ if (LOG_DEBUGFLAG(DEBUG_ASN1)) {
+ xer_fprint(stdout, &asn_DEF_NRPPA_NRPPA_PDU, pdu);
+ }
+
+ // Forward request to RRC
+ MessageDef *msg = itti_alloc_new_message(TASK_RRC_GNB, 0, NRPPA_MEASUREMENT_REQ);
+ nrppa_measurement_req_t *req = &NRPPA_MEASUREMENT_REQ(msg);
+
+ // Processing Received TRPInformationRequest
+ NRPPA_MeasurementRequest_t *container = NULL;
+ NRPPA_MeasurementRequest_IEs_t *ie = NULL;
+
+ // IE 9.2.3 Message type : mandatory
+ container = &pdu->choice.initiatingMessage->value.choice.MeasurementRequest;
+
+ // IE 9.2.4 nrppatransactionID : mandatory
+ req->transaction_id = pdu->choice.initiatingMessage->nrppatransactionID;
+
+ NRPPA_FIND_PROTOCOLIE_BY_ID(NRPPA_MeasurementRequest_IEs_t, ie, container, NRPPA_ProtocolIE_ID_id_LMF_Measurement_ID, true);
+
+ // LMF Measurement ID : mandatory
+ req->lmf_measurement_id = ie->value.choice.Measurement_ID;
+
+ // IE TRP Measurement Request List : mandatory
+ NRPPA_FIND_PROTOCOLIE_BY_ID(NRPPA_MeasurementRequest_IEs_t,
+ ie,
+ container,
+ NRPPA_ProtocolIE_ID_id_TRP_MeasurementRequestList,
+ true);
+ NRPPA_TRP_MeasurementRequestList_t *nrppa_trp_meas_list = &ie->value.choice.TRP_MeasurementRequestList;
+ uint8_t meas_req_item_len = nrppa_trp_meas_list->list.count;
+ AssertError(meas_req_item_len > 0, return false, "at least 1 TRP Measurement Request Item must be present");
+ nrppa_trp_measurement_request_list_t *trp_meas_list = &req->trp_measurement_request_list;
+ trp_meas_list->trp_measurement_request_list_length = meas_req_item_len;
+ trp_meas_list->trp_measurement_request_item =
+ calloc_or_fail(meas_req_item_len, sizeof(*trp_meas_list->trp_measurement_request_item));
+ for (int i = 0; i < meas_req_item_len; i++) {
+ trp_meas_list->trp_measurement_request_item[i].trp_id = nrppa_trp_meas_list->list.array[i]->tRP_ID;
+ }
+
+ // IE Report Characteristics : mandatory
+ NRPPA_FIND_PROTOCOLIE_BY_ID(NRPPA_MeasurementRequest_IEs_t, ie, container, NRPPA_ProtocolIE_ID_id_ReportCharacteristics, true);
+ switch (ie->value.choice.ReportCharacteristics) {
+ case NRPPA_ReportCharacteristics_onDemand:
+ req->report_characteristics = NRPPA_POSREPORTCHARACTERISTICS_ONDEMAND;
+ break;
+ case NRPPA_ReportCharacteristics_periodic:
+ req->report_characteristics = NRPPA_POSREPORTCHARACTERISTICS_PERIODIC;
+ break;
+ default:
+ AssertError(false, return false, "illegal report characteristics\n");
+ break;
+ }
+
+ // IE Measurement Periodicity : C-if Report Charateristics periodic
+ if (req->report_characteristics == NRPPA_POSREPORTCHARACTERISTICS_PERIODIC) {
+ NRPPA_FIND_PROTOCOLIE_BY_ID(NRPPA_MeasurementRequest_IEs_t, ie, container, NRPPA_ProtocolIE_ID_id_MeasurementPeriodicity, true);
+ switch (ie->value.choice.MeasurementPeriodicity) {
+ case NRPPA_MeasurementPeriodicity_ms120:
+ req->measurement_periodicity = NRPPA_POSMEASUREMENTPERIODICITY_MS120;
+ break;
+ case NRPPA_MeasurementPeriodicity_ms240:
+ req->measurement_periodicity = NRPPA_POSMEASUREMENTPERIODICITY_MS240;
+ break;
+ case NRPPA_MeasurementPeriodicity_ms480:
+ req->measurement_periodicity = NRPPA_POSMEASUREMENTPERIODICITY_MS480;
+ break;
+ case NRPPA_MeasurementPeriodicity_ms640:
+ req->measurement_periodicity = NRPPA_POSMEASUREMENTPERIODICITY_MS640;
+ break;
+ case NRPPA_MeasurementPeriodicity_ms1024:
+ req->measurement_periodicity = NRPPA_POSMEASUREMENTPERIODICITY_MS1024;
+ break;
+ case NRPPA_MeasurementPeriodicity_ms2048:
+ req->measurement_periodicity = NRPPA_POSMEASUREMENTPERIODICITY_MS2048;
+ break;
+ case NRPPA_MeasurementPeriodicity_ms5120:
+ req->measurement_periodicity = NRPPA_POSMEASUREMENTPERIODICITY_MS5120;
+ break;
+ case NRPPA_MeasurementPeriodicity_ms10240:
+ req->measurement_periodicity = NRPPA_POSMEASUREMENTPERIODICITY_MS10240;
+ break;
+ case NRPPA_MeasurementPeriodicity_min1:
+ req->measurement_periodicity = NRPPA_POSMEASUREMENTPERIODICITY_MIN1;
+ break;
+ case NRPPA_MeasurementPeriodicity_min6:
+ req->measurement_periodicity = NRPPA_POSMEASUREMENTPERIODICITY_MIN6;
+ break;
+ case NRPPA_MeasurementPeriodicity_min12:
+ req->measurement_periodicity = NRPPA_POSMEASUREMENTPERIODICITY_MIN12;
+ break;
+ case NRPPA_MeasurementPeriodicity_min30:
+ req->measurement_periodicity = NRPPA_POSMEASUREMENTPERIODICITY_MIN30;
+ break;
+ case NRPPA_MeasurementPeriodicity_min60:
+ req->measurement_periodicity = NRPPA_POSMEASUREMENTPERIODICITY_MIN60;
+ break;
+ default:
+ AssertError(false, return false, "illegal measurement periodicity\n");
+ break;
+ }
+ }
+
+ // IE Measurement Quantity : mandatory (but not handled in OAI-LMF)
+ NRPPA_FIND_PROTOCOLIE_BY_ID(NRPPA_MeasurementRequest_IEs_t, ie, container, NRPPA_ProtocolIE_ID_id_MeasurementQuantities, false);
+ if (ie == NULL) {
+ LOG_W(NRPPA, "MeasurementQuantities is madatory but not handled in OAI LMF\n");
+ } else {
+ NRPPA_TRPMeasurementQuantities_t *nrppa_meas_q = &ie->value.choice.TRPMeasurementQuantities;
+ uint32_t q_len = nrppa_meas_q->list.count;
+ AssertError(q_len > 0, return false, "at least 1 TRP Measurement Quantity must be present");
+ nrppa_measurement_quantities_t *meas_q = &req->measurement_quantities;
+ meas_q->measurement_quantities_length = q_len;
+ meas_q->measurement_quantities_item = calloc_or_fail(q_len, sizeof(*meas_q->measurement_quantities_item));
+ nrppa_measurement_quantities_item_t *q_item = meas_q->measurement_quantities_item;
+ for (int i = 0; i < meas_req_item_len; i++) {
+ switch (nrppa_meas_q->list.array[i]->tRPMeasurementQuantities_Item) {
+ case NRPPA_TRPMeasurementQuantities_Item_gNB_RxTxTimeDiff:
+ q_item[i].measurement_type = NRPPA_POSMEASUREMENTTYPE_GNB_RX_TX;
+ break;
+ case NRPPA_TRPMeasurementQuantities_Item_uL_SRS_RSRP:
+ q_item[i].measurement_type = NRPPA_POSMEASUREMENTTYPE_UL_SRS_RSRP;
+ break;
+ case NRPPA_TRPMeasurementQuantities_Item_uL_AoA:
+ q_item[i].measurement_type = NRPPA_POSMEASUREMENTTYPE_UL_AOA;
+ break;
+ case NRPPA_TRPMeasurementQuantities_Item_uL_RTOA:
+ q_item[i].measurement_type = NRPPA_POSMEASUREMENTTYPE_UL_RTOA;
+ break;
+ default:
+ AssertError(false, return false, "illegal measurement quantity\n");
+ break;
+ }
+ }
+ }
+
+ // IE SRS Configuration : optional
+ NRPPA_FIND_PROTOCOLIE_BY_ID(NRPPA_MeasurementRequest_IEs_t, ie, container, NRPPA_ProtocolIE_ID_id_SRSConfiguration, false);
+ if (ie != NULL) {
+ NRPPA_SRSCarrier_List_t *nrppa_srs_carrier_list = &ie->value.choice.SRSConfiguration.sRSCarrier_List;
+ req->srs_configuration = calloc_or_fail(1, sizeof(*req->srs_configuration));
+ nrppa_srs_carrier_list_t *srs_carrier_list = &req->srs_configuration->srs_carrier_list;
+ decode_srs_carrier_list(srs_carrier_list, nrppa_srs_carrier_list);
+ }
+
+ nrppa_store_ue_context(nrppa_msg_info, req->transaction_id);
+
+ LOG_I(NRPPA, "Forwarding to RRC Measurement Request transaction_id %d\n", req->transaction_id);
+ itti_send_msg_to_task(TASK_RRC_GNB, 0, msg);
+ ASN_STRUCT_FREE_CONTENTS_ONLY(asn_DEF_NRPPA_NRPPA_PDU, &pdu);
+ return 0;
+}
+
+int nrppa_gNB_measurement_response(instance_t instance, MessageDef *msg_p)
+{
+ DevAssert(msg_p);
+ nrppa_measurement_resp_t *resp = &NRPPA_MEASUREMENT_RESP(msg_p);
+ nrppa_gNB_ue_context_t *ue_info = nrppa_detach_ue_context(resp->transaction_id);
+
+ if (ue_info->gNB_ue_ngap_id != 0 && ue_info->amf_ue_ngap_id != 0) {
+ LOG_E(NRPPA, "Illegal gNB_ue_ngap_id %d and amf_ue_ngap_id %ld\n", ue_info->gNB_ue_ngap_id, ue_info->amf_ue_ngap_id);
+ free_measurement_resp(resp);
+ nrppa_free_ue_context(ue_info);
+ return -1;
+ }
+
+ LOG_I(NRPPA,
+ "Received measurement response info from RRC with transaction_id %u and gNB_ue_ngap_id %u\n",
+ ue_info->transaction_id,
+ ue_info->gNB_ue_ngap_id);
+
+ // Prepare NRPPA TRP Information transfer Response
+ NRPPA_NRPPA_PDU_t pdu = {0};
+
+ // IE: 9.2.3 Message Type : mandatory
+ pdu.present = NRPPA_NRPPA_PDU_PR_successfulOutcome;
+ asn1cCalloc(pdu.choice.successfulOutcome, head);
+ head->procedureCode = NRPPA_ProcedureCode_id_Measurement;
+ head->criticality = NRPPA_Criticality_reject;
+ head->value.present = NRPPA_SuccessfulOutcome__value_PR_MeasurementResponse;
+
+ // IE 9.2.4 nrppatransactionID : mandatory
+ head->nrppatransactionID = resp->transaction_id;
+ NRPPA_MeasurementResponse_t *out = &head->value.choice.MeasurementResponse;
+
+ // IE LMF Measurement ID : mandatory
+ {
+ asn1cSequenceAdd(out->protocolIEs.list, NRPPA_MeasurementResponse_IEs_t, ie);
+ ie->id = NRPPA_ProtocolIE_ID_id_LMF_Measurement_ID;
+ ie->criticality = NRPPA_Criticality_reject;
+ ie->value.present = NRPPA_MeasurementResponse_IEs__value_PR_Measurement_ID;
+ ie->value.choice.Measurement_ID = resp->lmf_measurement_id;
+ }
+
+ // IE RAN Measurement ID : mandatory
+ {
+ asn1cSequenceAdd(out->protocolIEs.list, NRPPA_MeasurementResponse_IEs_t, ie);
+ ie->id = NRPPA_ProtocolIE_ID_id_RAN_Measurement_ID;
+ ie->criticality = NRPPA_Criticality_reject;
+ ie->value.present = NRPPA_MeasurementResponse_IEs__value_PR_Measurement_ID_1;
+ ie->value.choice.Measurement_ID_1 = resp->ran_measurement_id;
+ }
+
+ // IE TRP Measurement Response List : mandatory
+ {
+ if (resp->measurement_response_list) {
+ asn1cSequenceAdd(out->protocolIEs.list, NRPPA_MeasurementResponse_IEs_t, ie);
+ ie->id = NRPPA_ProtocolIE_ID_id_TRP_MeasurementResponseList;
+ ie->criticality = NRPPA_Criticality_reject;
+ ie->value.present = NRPPA_MeasurementResponse_IEs__value_PR_TRP_MeasurementResponseList;
+ ie->value.choice.TRP_MeasurementResponseList = encode_trp_measurement_reponse_list(resp->measurement_response_list);
+ }
+ }
+
+ free_measurement_resp(resp);
+
+ LOG_I(NRPPA, "Calling encoder for Measurement Response \n");
+
+ if (LOG_DEBUGFLAG(DEBUG_ASN1)) {
+ xer_fprint(stdout, &asn_DEF_NRPPA_NRPPA_PDU, &pdu);
+ }
+
+ // Encode NRPPA message
+ uint8_t *buffer = NULL;
+ uint32_t length = 0;
+ if (nrppa_gNB_encode_pdu(&pdu, &buffer, &length) < 0) {
+ LOG_E(NRPPA, "Failed to encode Uplink NRPPa Measurement Response\n");
+ nrppa_free_ue_context(ue_info);
+ ASN_STRUCT_FREE_CONTENTS_ONLY(asn_DEF_NRPPA_NRPPA_PDU, &pdu);
+ return -1;
+ }
+
+ MessageDef *msg = itti_alloc_new_message(TASK_NRPPA, 0, NGAP_UPLINKNONUEASSOCIATEDNRPPA);
+ ngap_uplink_non_ue_associated_nrppa_t *ULNRPPA = &NGAP_UPLINKNONUEASSOCIATEDNRPPA(msg);
+
+ // Routing ID
+ ULNRPPA->routing_id = create_byte_array(ue_info->routing_id.len, ue_info->routing_id.buf);
+
+ // NRPPa PDU
+ ULNRPPA->nrppa_pdu = create_byte_array(length, buffer);
+
+ // Forward the NRPPA PDU to NGAP
+ itti_send_msg_to_task(TASK_NGAP, instance, msg);
+ nrppa_free_ue_context(ue_info);
+ free(buffer);
+ return length;
+}
diff --git a/openair3/NRPPA/nrppa_gNB_measurement_information_transfer.h b/openair3/NRPPA/nrppa_gNB_measurement_information_transfer.h
new file mode 100644
index 0000000000..da03403f4d
--- /dev/null
+++ b/openair3/NRPPA/nrppa_gNB_measurement_information_transfer.h
@@ -0,0 +1,32 @@
+/*
+ * Licensed to the OpenAirInterface (OAI) Software Alliance under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The OpenAirInterface Software Alliance licenses this file to You under
+ * the OAI Public License, Version 1.1 (the "License"); you may not use this file
+ * except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.openairinterface.org/?page_id=698
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *-------------------------------------------------------------------------------
+ * For more information about the OpenAirInterface (OAI) Software Alliance:
+ * contact@openairinterface.org
+ */
+
+#ifndef NRPPA_GNB_MEASUREMENT_INFORMATION_TRANSFER_H_
+#define NRPPA_GNB_MEASUREMENT_INFORMATION_TRANSFER_H_
+
+int nrppa_gNB_handle_measurement_request(nrppa_gnb_ue_info_t *nrppa_msg_info, const NRPPA_NRPPA_PDU_t *pdu);
+void decode_srs_carrier_list(nrppa_srs_carrier_list_t *out_list, const NRPPA_SRSCarrier_List_t *in_list);
+void free_measurement_request(nrppa_measurement_req_t *msg);
+int nrppa_gNB_measurement_response(instance_t instance, MessageDef *msg_p);
+NRPPA_TRP_MeasurementResponseList_t encode_trp_measurement_reponse_list(nrppa_measurement_response_list_t *in_list);
+void free_measurement_resp(nrppa_measurement_resp_t *msg);
+
+#endif /* NRPPA_GNB_MEASUREMENT_INFORMATION_TRANSFER_H_ */
diff --git a/openair3/NRPPA/nrppa_gNB_ue_context.c b/openair3/NRPPA/nrppa_gNB_ue_context.c
new file mode 100644
index 0000000000..b5da194205
--- /dev/null
+++ b/openair3/NRPPA/nrppa_gNB_ue_context.c
@@ -0,0 +1,96 @@
+/*
+ * Licensed to the OpenAirInterface (OAI) Software Alliance under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The OpenAirInterface Software Alliance licenses this file to You under
+ * the OAI Public License, Version 1.1 (the "License"); you may not use this file
+ * except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.openairinterface.org/?page_id=698
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *-------------------------------------------------------------------------------
+ * For more information about the OpenAirInterface (OAI) Software Alliance:
+ * contact@openairinterface.org
+ */
+
+#include "nrppa_gNB_ue_context.h"
+#include "tree.h"
+#include "T.h"
+#include "common/utils/T/T.h"
+#include "common/utils/utils.h"
+#include "common/utils/LOG/log.h"
+
+static RB_HEAD(nrppa_ue_map, nrppa_gNB_ue_context_s) nrppa_ue_head = RB_INITIALIZER(&nrppa_ue_head);
+
+/* Generate the tree management functions prototypes */
+RB_PROTOTYPE(nrppa_ue_map, nrppa_gNB_ue_context_s, entries, nrppa_gNB_compare_transaction_id);
+
+static int nrppa_gNB_compare_transaction_id(struct nrppa_gNB_ue_context_s *p1, struct nrppa_gNB_ue_context_s *p2)
+{
+ if (p1->transaction_id > p2->transaction_id) {
+ return 1;
+ }
+
+ if (p1->transaction_id < p2->transaction_id) {
+ return -1;
+ }
+
+ return 0;
+}
+
+/* Generate the tree management functions */
+RB_GENERATE(nrppa_ue_map, nrppa_gNB_ue_context_s, entries, nrppa_gNB_compare_transaction_id);
+
+void nrppa_store_ue_context(const nrppa_gnb_ue_info_t *info, const uint16_t transaction_id)
+{
+ LOG_I(NRPPA, "Create NRPPa UE context (gNB UE ID %u) for transaction ID : %u\n", info->gNB_ue_ngap_id, transaction_id);
+ nrppa_gNB_ue_context_t *ue_info_p = calloc_or_fail(1, sizeof(*ue_info_p));
+ ue_info_p->transaction_id = transaction_id;
+ ue_info_p->gNB_ue_ngap_id = info->gNB_ue_ngap_id;
+ ue_info_p->amf_ue_ngap_id = info->amf_ue_ngap_id;
+ if (info->routing_id.len > 0 && info->routing_id.buf != NULL) {
+ ue_info_p->routing_id.len = info->routing_id.len;
+ ue_info_p->routing_id.buf = calloc_or_fail(1, info->routing_id.len);
+ memcpy(ue_info_p->routing_id.buf, info->routing_id.buf, info->routing_id.len);
+ } else {
+ ue_info_p->routing_id.len = 0;
+ ue_info_p->routing_id.buf = NULL;
+ }
+ if (RB_INSERT(nrppa_ue_map, &nrppa_ue_head, ue_info_p))
+ LOG_E(NRPPA, "Bug in UE uniq number allocation %u, we try to add a existing UE\n", ue_info_p->gNB_ue_ngap_id);
+ return;
+}
+
+struct nrppa_gNB_ue_context_s *nrppa_get_ue_context(uint16_t transaction_id)
+{
+ nrppa_gNB_ue_context_t temp = {.transaction_id = transaction_id};
+ return RB_FIND(nrppa_ue_map, &nrppa_ue_head, &temp);
+}
+
+struct nrppa_gNB_ue_context_s *nrppa_detach_ue_context(uint16_t transaction_id)
+{
+ struct nrppa_gNB_ue_context_s *tmp = nrppa_get_ue_context(transaction_id);
+ if (tmp == NULL) {
+ LOG_E(NRPPA, "Trying to free a NULL UE context, %u\n", transaction_id);
+ return NULL;
+ }
+ RB_REMOVE(nrppa_ue_map, &nrppa_ue_head, tmp);
+ return tmp;
+}
+
+void nrppa_free_ue_context(nrppa_gNB_ue_context_t *ue_info)
+{
+ if (!ue_info)
+ return;
+
+ if (ue_info->routing_id.buf) {
+ free(ue_info->routing_id.buf);
+ }
+ free(ue_info);
+}
diff --git a/openair3/NRPPA/nrppa_gNB_ue_context.h b/openair3/NRPPA/nrppa_gNB_ue_context.h
new file mode 100644
index 0000000000..fc976c611d
--- /dev/null
+++ b/openair3/NRPPA/nrppa_gNB_ue_context.h
@@ -0,0 +1,44 @@
+/*
+ * Licensed to the OpenAirInterface (OAI) Software Alliance under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The OpenAirInterface Software Alliance licenses this file to You under
+ * the OAI Public License, Version 1.1 (the "License"); you may not use this file
+ * except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.openairinterface.org/?page_id=698
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *-------------------------------------------------------------------------------
+ * For more information about the OpenAirInterface (OAI) Software Alliance:
+ * contact@openairinterface.org
+ */
+
+#include
+#include "tree.h"
+#include "ds/byte_array.h"
+#include "nrppa_common.h"
+
+#ifndef NRPPA_GNB_UE_CONTEXT_H_
+#define NRPPA_GNB_UE_CONTEXT_H_
+
+typedef struct nrppa_gNB_ue_context_s {
+ /* Tree related data */
+ RB_ENTRY(nrppa_gNB_ue_context_s) entries;
+ uint16_t transaction_id;
+ uint32_t gNB_ue_ngap_id;
+ uint64_t amf_ue_ngap_id;
+ byte_array_t routing_id;
+} nrppa_gNB_ue_context_t;
+
+void nrppa_store_ue_context(const nrppa_gnb_ue_info_t *info, const uint16_t transaction_id);
+nrppa_gNB_ue_context_t *nrppa_get_ue_context(uint16_t transaction_id);
+nrppa_gNB_ue_context_t *nrppa_detach_ue_context(uint16_t transaction_id);
+void nrppa_free_ue_context(nrppa_gNB_ue_context_t *ue_info);
+
+#endif /* NRPPA_GNB_UE_CONTEXT_H_ */
diff --git a/openair3/NRPPA/nrppa_includes.h b/openair3/NRPPA/nrppa_includes.h
new file mode 100644
index 0000000000..98e447d379
--- /dev/null
+++ b/openair3/NRPPA/nrppa_includes.h
@@ -0,0 +1,83 @@
+/*
+ * Licensed to the OpenAirInterface (OAI) Software Alliance under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The OpenAirInterface Software Alliance licenses this file to You under
+ * the OAI Public License, Version 1.1 (the "License"); you may not use this file
+ * except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.openairinterface.org/?page_id=698
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *-------------------------------------------------------------------------------
+ * For more information about the OpenAirInterface (OAI) Software Alliance:
+ * contact@openairinterface.org
+ */
+
+#ifndef NRPPA_INCLUDE_H_
+#define NRPPA_INCLUDE_H_
+
+#include "NRPPA_NRPPA-PDU.h"
+#include "NRPPA_InitiatingMessage.h"
+#include "NRPPA_SuccessfulOutcome.h"
+#include "NRPPA_UnsuccessfulOutcome.h"
+#include "NRPPA_ProtocolIE-ID.h"
+#include "NRPPA_ProtocolIE-Field.h"
+#include "NRPPA_ProtocolIE-Container.h"
+#include "NRPPA_ProtocolExtensionField.h"
+#include "NRPPA_ProtocolIE-ContainerList.h"
+#include "NRPPA_ProtocolExtensionContainer.h"
+#include "NRPPA_ProtocolIE-Single-Container.h"
+#include "NRPPA_asn_constant.h"
+#include "NRPPA_TRPInformationRequest.h"
+#include "NRPPA_TRPInformationItem.h"
+#include "NRPPA_TRPPositionDirect.h"
+#include "NRPPA_NG-RANAccessPointPosition.h"
+#include "NRPPA_NGRANHighAccuracyAccessPointPosition.h"
+#include "NRPPA_TRPPositionReferenced.h"
+#include "NRPPA_RelativeGeodeticLocation.h"
+#include "NRPPA_RelativeCartesianLocation.h"
+#include "NRPPA_SRSCarrier-List-Item.h"
+#include "NRPPA_SCS-SpecificCarrier.h"
+#include "NRPPA_SRSConfig.h"
+#include "NRPPA_SRSResource-List.h"
+#include "NRPPA_SRSResource.h"
+#include "NRPPA_ResourceType.h"
+#include "NRPPA_ResourceTypePeriodic.h"
+#include "NRPPA_ResourceTypeSemi-persistent.h"
+#include "NRPPA_ResourceTypeAperiodic.h"
+#include "NRPPA_PosSRSResource-List.h"
+#include "NRPPA_ResourceTypePos.h"
+#include "NRPPA_ResourceTypePeriodicPos.h"
+#include "NRPPA_ResourceTypeSemi-persistentPos.h"
+#include "NRPPA_ResourceTypeAperiodicPos.h"
+#include "NRPPA_SRSResourceSet-List.h"
+#include "NRPPA_SRSResourceSet.h"
+#include "NRPPA_PosSRSResource-List.h"
+#include "NRPPA_PosSRSResourceSet-Item.h"
+#include "NRPPA_PosSRSResource-List.h"
+#include "NRPPA_PosSRSResource-Item.h"
+#include "NRPPA_ResourceSetTypePeriodic.h"
+#include "NRPPA_ResourceSetTypeSemi-persistent.h"
+#include "NRPPA_ResourceSetTypeAperiodic.h"
+#include "NRPPA_PosSRSResourceSet-List.h"
+#include "NRPPA_PosResourceSetTypePeriodic.h"
+#include "NRPPA_PosResourceSetTypeSemi-persistent.h"
+#include "NRPPA_PosResourceSetTypeAperiodic.h"
+#include "NRPPA_SemipersistentSRS.h"
+#include "NRPPA_AperiodicSRS.h"
+#include "NRPPA_TRP-MeasurementRequestItem.h"
+#include "NRPPA_TRPMeasurementQuantities-Item.h"
+#include "NRPPA_TRPMeasurementQuantitiesList-Item.h"
+#include "NRPPA_TRP-MeasurementResponseList.h"
+#include "NRPPA_TRP-MeasurementResponseItem.h"
+#include "NRPPA_TrpMeasurementResultItem.h"
+#include "NRPPA_UL-RTOAMeasurement.h"
+#include "NRPPA_GNB-RxTxTimeDiff.h"
+
+#endif /* NRPPA_INCLUDE_H_ */
diff --git a/tests/CMakeLists.txt b/tests/CMakeLists.txt
index cefa52d456..63d036a83c 100644
--- a/tests/CMakeLists.txt
+++ b/tests/CMakeLists.txt
@@ -1 +1,2 @@
add_subdirectory(nr-cuup)
+add_subdirectory(nr-cu-nrppa)
diff --git a/tests/nr-cu-nrppa/CMakeLists.txt b/tests/nr-cu-nrppa/CMakeLists.txt
new file mode 100644
index 0000000000..b61b0dd920
--- /dev/null
+++ b/tests/nr-cu-nrppa/CMakeLists.txt
@@ -0,0 +1,11 @@
+add_executable(nr-cu-nrppa-test nr-cu-nrppa.c
+ ${OPENAIR2_DIR}/GNB_APP/gnb_config_common.c
+ ${OPENAIR2_DIR}/GNB_APP/gnb_config_ng.c)
+
+target_link_libraries(nr-cu-nrppa-test PRIVATE nr_nas nr_common lib_uicc usim_lib)
+target_link_libraries(nr-cu-nrppa-test PRIVATE
+ CONFIG_LIB ITTI SCTP_CLIENT
+ f1ap ngap SECURITY
+ UTIL softmodem_common nrppa)
+target_link_libraries(nr-cu-nrppa-test PRIVATE asn1_lte_rrc_hdrs asn1_nr_rrc_hdrs)
+add_dependencies(nr-cu-nrppa-test params_libconfig)
diff --git a/tests/nr-cu-nrppa/README.md b/tests/nr-cu-nrppa/README.md
new file mode 100644
index 0000000000..4ea780a20e
--- /dev/null
+++ b/tests/nr-cu-nrppa/README.md
@@ -0,0 +1,81 @@
+This is a simple standalone tester for NRPPA and NGAP positioning messages. It connects to the AMF to perform NGAP and NRPPA encoding/decoding and validates the exchange of positioning data.
+
+[[_TOC_]]
+
+# Overview
+From a schematic point of view, the tester and Core Network interaction looks like this:
+```
+ +-------+ +-------+
+ | LMF |<--- HTTP POST---| User |
+ +-------+ +-------+
+ |
+ | Nlmf
+ |
+ +-------+
+ | AMF |
+ +-------+
+ |
+ NGAP/NRPPA |
+ |
+ +-------+
+ |tester | (nr-cu-nrppa-test)
+ +-------+
+```
+The tester is designed to validate the integration of NRPPA and NGAP messages required for 5G positioning (*3GPP 38.413 V16.0.0* and *3GPP 38.455 V16.7.1*). It acts as a simulated RAN node (like a CU) connecting to the 5G Core Network's AMF.
+
+The following messages are integrated and tested:
+* **NGAP:** Uplink/Downlink UE Associated NRPPA Transport, Uplink/Downlink Non-UE Associated NRPPA Transport.
+* **NRPPA:** TRP Information Request/Response, Positioning Information Request/Response, Positioning Activation Request/Response, Measurement Request/Response.
+
+A test scenario is fixed to these steps:
+1. The 5G Core Network, specifically including the Location Management Function (LMF), is deployed via Docker.
+2. The tester connects to the AMF and establishes the NGAP connection.
+3. The user initiates a positioning procedure via a API call to the LMF.
+4. The AMF and the tester exchange the required NGAP and NRPPA messages to determine location.
+
+# Usage
+To run this test, you need to set up the Core Network and build the tester.
+
+**1. Core Network Deployment**
+
+Pull the required Docker images for the OAI 5G Core:
+
+ docker pull oaisoftwarealliance/ims:latest
+ docker pull oaisoftwarealliance/oai-amf:develop
+ docker pull oaisoftwarealliance/oai-nrf:develop
+ docker pull oaisoftwarealliance/oai-smf:develop
+ docker pull oaisoftwarealliance/oai-udr:develop
+ docker pull oaisoftwarealliance/oai-upf:develop
+ docker pull oaisoftwarealliance/oai-udm:develop
+ docker pull oaisoftwarealliance/oai-ausf:develop
+ docker pull oaisoftwarealliance/oai-lmf:develop
+
+Deploy the network using the positioning compose file:
+
+ cd doc/tutorial_resources/oai-cn5g
+ docker compose -f docker-compose-positioning.yaml up -d
+
+*(To undeploy later, run `docker compose -f docker-compose-positioning.yaml down -t 0`)*
+
+**2. Building the Tester**
+
+You can build the NRPPA tester like so:
+
+ cd ~/openairinterface5g
+ mkdir build && cd build && cmake .. -GNinja && ninja nr-cu-nrppa-test
+
+**3. Running the Tester**
+
+Start the tester with the dedicated configuration file:
+
+ LD_LIBRARY_PATH=. ./tests/nr-cu-nrppa/nr-cu-nrppa-test -O ../tests/nr-cu-nrppa/nr-nrppa-test.conf
+
+**4. Initiating the Procedure**
+
+Trigger the location determination by sending an HTTP POST request to the LMF:
+
+ cd ~/openairinterface5g/doc/tutorial_resources/positioning/
+ curl --http2-prior-knowledge -H "Content-Type: application/json" -d "@InputData.json" -X POST http://192.168.70.141:8080/nlmf-loc/v1/determine-location
+
+# Limitations
+- The tester is a standalone validation tool (`nr-cu-nrppa-test`) and does not represent a fully integrated, end-to-end gNB positioning setup.
diff --git a/tests/nr-cu-nrppa/nr-cu-nrppa.c b/tests/nr-cu-nrppa/nr-cu-nrppa.c
new file mode 100644
index 0000000000..de784a3a16
--- /dev/null
+++ b/tests/nr-cu-nrppa/nr-cu-nrppa.c
@@ -0,0 +1,733 @@
+/*
+ * Licensed to the OpenAirInterface (OAI) Software Alliance under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The OpenAirInterface Software Alliance licenses this file to You under
+ * the OAI Public License, Version 1.1 (the "License"); you may not use this file
+ * except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.openairinterface.org/?page_id=698
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *-------------------------------------------------------------------------------
+ * For more information about the OpenAirInterface (OAI) Software Alliance:
+ * contact@openairinterface.org
+ */
+
+#include "executables/softmodem-common.h"
+#include "common/utils/ocp_itti/intertask_interface.h"
+#include "common/ran_context.h"
+#include "nfapi/oai_integration/vendor_ext.h"
+#include "openair2/GNB_APP/gnb_config_common.h"
+#include "openair2/GNB_APP/gnb_config_ng.h"
+#include "openair2/GNB_APP/gnb_paramdef.h"
+#include "openair3/SCTP/sctp_default_values.h"
+#include "openair3/NRPPA/nrppa_gNB_config.h"
+#include "openair3/NRPPA/nrppa_gNB.h"
+#include "openair3/NAS/NR_UE/nr_nas_msg.h"
+#include "executables/nr-uesoftmodem.h"
+#include "openair3/NRPPA/nrppa_gNB_location_information_transfer.c"
+#include "openair3/NRPPA/nrppa_gNB_measurement_information_transfer.h"
+
+RAN_CONTEXT_t RC;
+THREAD_STRUCT thread_struct;
+uint64_t downlink_frequency[MAX_NUM_CCs][4];
+int32_t uplink_frequency_offset[MAX_NUM_CCs][4];
+int oai_exit = 0;
+int gnb_id;
+int NB_UE_INST = 1;
+
+void exit_function(const char *file, const char *function, const int line, const char *s, const int assert)
+{
+ if (assert) {
+ abort();
+ } else {
+ sleep(1); // allow other threads to exit first
+ exit(EXIT_SUCCESS);
+ }
+}
+
+nfapi_mode_t nfapi_mod = -1;
+void nfapi_setmode(nfapi_mode_t nfapi_mode)
+{
+ nfapi_mod = nfapi_mode;
+}
+nfapi_mode_t nfapi_getmode(void)
+{
+ return nfapi_mod;
+}
+
+ngran_node_t get_node_type()
+{
+ return ngran_gNB_CUUP;
+}
+
+nrUE_params_t *get_nrUE_params(void)
+{
+ static nrUE_params_t params = {0};
+ params.extra_pdu_id = -1;
+ return ¶ms;
+}
+
+void create_ue_ip_if(void)
+{
+}
+
+void create_ue_eth_if(void)
+{
+}
+
+void set_qfi(void)
+{
+}
+
+configmodule_interface_t *uniqCfg = NULL;
+
+static nrppa_trp_information_resp_t fill_trp_resp(uint8_t transaction_id)
+{
+ positioning_config_t positioning_config = RCconfig_nr_positioning();
+ dump_positioning_config(&positioning_config);
+ nrppa_trp_information_resp_t resp = {0};
+ resp.transaction_id = transaction_id;
+
+ nrppa_trp_information_list_t *list = &resp.trp_information_list;
+ uint32_t trp_info_item_len = positioning_config.num_trp;
+ list->trp_information_item_length = trp_info_item_len;
+ list->trp_information_item = calloc_or_fail(trp_info_item_len, sizeof(*list->trp_information_item));
+
+ uint8_t resp_item_len = 3;
+ for (int i = 0; i < trp_info_item_len; i++) {
+ nrppa_trp_information_t *tRPInformation = &list->trp_information_item[i];
+ tRPInformation->trp_id = positioning_config.trps[i].id;
+ nrppa_trp_information_type_response_list_t *resp_list = &tRPInformation->trp_information_type_response_list;
+ resp_list->trp_information_type_response_item_length = resp_item_len;
+ nrppa_trp_information_type_response_item_t *resp_item = calloc_or_fail(resp_item_len, sizeof(*resp_item));
+ resp_list->trp_information_type_response_item = resp_item;
+
+ // nrPCI
+ resp_item[0].present = NRPPA_TRP_INFORMATION_TYPE_RESPONSE_ITEM_PR_PCI_NR;
+ resp_item[0].choice.pci_nr = 123 + i;
+
+ // nG_RAN_CGI
+ resp_item[1].present = NRPPA_TRP_INFORMATION_TYPE_RESPONSE_ITEM_PR_NG_RAN_CGI;
+ resp_item[1].choice.ng_ran_cgi.plmn.mcc = 001;
+ resp_item[1].choice.ng_ran_cgi.plmn.mnc = 01;
+ resp_item[1].choice.ng_ran_cgi.plmn.mnc_digit_length = 2;
+ resp_item[1].choice.ng_ran_cgi.nr_cellid = gnb_id << 8; // HACK: Made to work with lmf
+
+ // geographicalCoordinates
+ resp_item[2].present = NRPPA_TRP_INFORMATION_TYPE_RESPONSE_ITEM_PR_GEOGRAPHICALCOORDINATES;
+ nrppa_geographical_coordinates_t *geographicalCoordinates = &resp_item[2].choice.geographical_coordinates;
+ nrppa_trp_position_definition_type_t *tRPPositionDefinitionType = &geographicalCoordinates->trp_position_definition_type;
+ // referenced
+ tRPPositionDefinitionType->present = NRPPA_TRP_POSITION_DEFINITION_TYPE_PR_REFERENCED;
+ nrppa_trp_position_referenced_t *referenced = &tRPPositionDefinitionType->choice.referenced;
+ // coordinate ID
+ referenced->reference_point.present = NRPPA_REFERENCE_POINT_PR_COORDINATEID;
+ referenced->reference_point.choice.coordinate_id = 2;
+ nrppa_trp_reference_point_type_t *referencePointType = &referenced->reference_point_type;
+ // relative cartesian
+ referencePointType->present = NRPPA_TRP_REFERENCE_POINT_TYPE_PR_TRPPOSITION_RELATIVE_CARTESIAN;
+ nrppa_relative_cartesian_location_t *trp_pos_cart = &referencePointType->choice.trp_position_relative_cartesian;
+ // 0 = millimeter
+ trp_pos_cart->xyz_unit = positioning_config.trps[i].unit;
+
+ // random reference cartesian coordinates in millimeter
+ trp_pos_cart->xvalue = positioning_config.trps[i].x_axis;
+ trp_pos_cart->yvalue = positioning_config.trps[i].y_axis;
+ trp_pos_cart->zvalue = positioning_config.trps[i].z_axis;
+ // testing random values for uncertainity and confidence
+ trp_pos_cart->location_uncertainty.horizontal_uncertainty = i + 1;
+ trp_pos_cart->location_uncertainty.horizontal_confidence = i + 2;
+ trp_pos_cart->location_uncertainty.vertical_uncertainty = i + 3;
+ trp_pos_cart->location_uncertainty.vertical_confidence = i + 4;
+ }
+ return resp;
+}
+
+static nrppa_positioning_information_resp_t fill_position_information_resp(uint16_t transaction_id)
+{
+ nrppa_positioning_information_resp_t resp = {0};
+ resp.transaction_id = transaction_id;
+ resp.srs_configuration = calloc_or_fail(1, sizeof(*resp.srs_configuration));
+ nrppa_srs_carrier_list_t *srs_carrier_list = &resp.srs_configuration->srs_carrier_list;
+ uint32_t srs_carrier_list_len = 2;
+ srs_carrier_list->srs_carrier_list_length = srs_carrier_list_len;
+ srs_carrier_list->srs_carrier_list_item = calloc_or_fail(srs_carrier_list_len, sizeof(*srs_carrier_list->srs_carrier_list_item));
+ for (int i = 0; i < srs_carrier_list_len; i++) {
+ nrppa_srs_carrier_list_item_t *srs_carrier_list_item = &srs_carrier_list->srs_carrier_list_item[i];
+ // pointA
+ srs_carrier_list_item->pointA = 87641 + i;
+
+ // Uplink Channel BW-PerSCS-List
+ nrppa_uplink_channel_bw_per_scs_list_t *uplink_channel_bw_per_scs_list = &srs_carrier_list_item->uplink_channel_bw_per_scs_list;
+
+ uint32_t scs_specific_carrier_list_length = 3;
+ uplink_channel_bw_per_scs_list->scs_specific_carrier_list_length = scs_specific_carrier_list_length;
+ uplink_channel_bw_per_scs_list->scs_specific_carrier =
+ calloc_or_fail(scs_specific_carrier_list_length, sizeof(*uplink_channel_bw_per_scs_list->scs_specific_carrier));
+ for (int j = 0; j < scs_specific_carrier_list_length; j++) {
+ nrppa_scs_specific_carrier_t *scs_specific_carrier = &uplink_channel_bw_per_scs_list->scs_specific_carrier[j];
+ // offset to carrier
+ scs_specific_carrier->offset_to_carrier = 100 + i + j;
+ // subcarrier spacing
+ scs_specific_carrier->subcarrier_spacing = NRPPA_SUBCARRIER_SPACING_30KHZ;
+ // carrier bandwidth
+ scs_specific_carrier->carrier_bandwidth = 106 + i + j;
+ }
+
+ // Active UL BWP
+ nrppa_active_ul_bwp_t *active_ul_bwp = &srs_carrier_list_item->active_ul_bwp;
+
+ // location and bandwidth
+ active_ul_bwp->location_and_bandwidth = 2775 + i;
+ // subcarrier spacing
+ active_ul_bwp->subcarrier_spacing = NRPPA_SUBCARRIER_SPACING_30KHZ;
+ // cyclic prefix
+ active_ul_bwp->cyclic_prefix = NRPPA_CP_TYPE_NORMAL;
+ // Tx Direct Current Location
+ active_ul_bwp->tx_direct_current_location = 10 + i;
+
+ // SRS Config
+ nrppa_srs_config_t *sRSConfig = &active_ul_bwp->srs_config;
+
+ // srs_resource_list
+ sRSConfig->srs_resource_list = calloc_or_fail(1, sizeof(*sRSConfig->srs_resource_list));
+ nrppa_srs_resource_list_t *srs_resource_list = sRSConfig->srs_resource_list;
+ uint32_t srs_resource_list_length = 3;
+ srs_resource_list->srs_resource_list_length = srs_resource_list_length;
+ srs_resource_list->srs_resource = calloc_or_fail(srs_resource_list_length, sizeof(*srs_resource_list->srs_resource));
+
+ // SRS resource config 1 : periodic
+ nrppa_srs_resource_t *srs_resource = &srs_resource_list->srs_resource[0];
+ srs_resource->srs_resource_id = 22;
+ srs_resource->nr_of_srs_ports = NRPPA_SRS_NUMBER_OF_PORTS_N2;
+ srs_resource->transmission_comb.present = NRPPA_TRANSMISSION_COMB_PR_N2;
+ srs_resource->transmission_comb.choice.n2.comb_offset_n2 = 1;
+ srs_resource->transmission_comb.choice.n2.cyclic_shift_n2 = 3;
+ srs_resource->start_position = 8;
+ srs_resource->nr_of_symbols = NRPPA_SRS_NUMBER_OF_SYMBOLS_N4;
+ srs_resource->repetition_factor = NRPPA_SRS_REPETITION_FACTOR_RF2;
+ srs_resource->freq_domain_position = 32;
+ srs_resource->freq_domain_shift = 108;
+ srs_resource->c_srs = 31;
+ srs_resource->b_srs = 1;
+ srs_resource->b_hop = 3;
+ srs_resource->group_or_sequence_hopping = NRPPA_GROUPORSEQUENCEHOPPING_GROUPHOPPING;
+ srs_resource->resource_type.present = NRPPA_RESOURCE_TYPE_PR_PERIODIC;
+
+ nrppa_resource_type_periodic_t *periodic = &srs_resource->resource_type.choice.periodic;
+ periodic->periodicity = NRPPA_SRS_RESOURCE_TYPE_PERIODICITY_SLOT16;
+ periodic->offset = 1000;
+ srs_resource->sequence_id = 18;
+
+ // SRS resource config 2 : semi-persistent
+ srs_resource = &srs_resource_list->srs_resource[1];
+ srs_resource->srs_resource_id = 24;
+ srs_resource->nr_of_srs_ports = NRPPA_SRS_NUMBER_OF_PORTS_N4;
+ srs_resource->transmission_comb.present = NRPPA_TRANSMISSION_COMB_PR_N4;
+ srs_resource->transmission_comb.choice.n2.comb_offset_n2 = 3;
+ srs_resource->transmission_comb.choice.n2.cyclic_shift_n2 = 5;
+ srs_resource->start_position = 8;
+ srs_resource->nr_of_symbols = NRPPA_SRS_NUMBER_OF_SYMBOLS_N2;
+ srs_resource->repetition_factor = NRPPA_SRS_REPETITION_FACTOR_RF2;
+ srs_resource->freq_domain_position = 32;
+ srs_resource->freq_domain_shift = 108;
+ srs_resource->c_srs = 31;
+ srs_resource->b_srs = 1;
+ srs_resource->b_hop = 3;
+ srs_resource->group_or_sequence_hopping = NRPPA_GROUPORSEQUENCEHOPPING_GROUPHOPPING;
+ srs_resource->resource_type.present = NRPPA_RESOURCE_TYPE_PR_SEMI_PERSISTENT;
+
+ srs_resource->resource_type.present = NRPPA_RESOURCE_TYPE_PR_SEMI_PERSISTENT;
+ nrppa_resource_type_semi_persistent_t *semi_persistent = &srs_resource->resource_type.choice.semi_persistent;
+ semi_persistent->periodicity = NRPPA_SRS_RESOURCE_TYPE_PERIODICITY_SLOT40;
+ semi_persistent->offset = 1000;
+ srs_resource->sequence_id = 12;
+
+ // SRS resource config 2 : aperiodic
+ srs_resource = &srs_resource_list->srs_resource[2];
+ srs_resource->srs_resource_id = 26;
+ srs_resource->nr_of_srs_ports = NRPPA_SRS_NUMBER_OF_PORTS_N2;
+ srs_resource->transmission_comb.present = NRPPA_TRANSMISSION_COMB_PR_N2;
+ srs_resource->transmission_comb.choice.n2.comb_offset_n2 = 1;
+ srs_resource->transmission_comb.choice.n2.cyclic_shift_n2 = 3;
+ srs_resource->start_position = 8;
+ srs_resource->nr_of_symbols = NRPPA_SRS_NUMBER_OF_SYMBOLS_N4;
+ srs_resource->repetition_factor = NRPPA_SRS_REPETITION_FACTOR_RF2;
+ srs_resource->freq_domain_position = 32;
+ srs_resource->freq_domain_shift = 108;
+ srs_resource->c_srs = 31;
+ srs_resource->b_srs = 1;
+ srs_resource->b_hop = 3;
+ srs_resource->group_or_sequence_hopping = NRPPA_GROUPORSEQUENCEHOPPING_SEQUENCEHOPPING;
+ srs_resource->resource_type.present = NRPPA_RESOURCE_TYPE_PR_APERIODIC;
+ // set aperiodic = 0 to enable
+ srs_resource->resource_type.choice.aperiodic = 0;
+ srs_resource->sequence_id = 10;
+
+ // optional: pos_srs_resource_list
+ sRSConfig->pos_srs_resource_list = calloc_or_fail(1, sizeof(*sRSConfig->pos_srs_resource_list));
+ nrppa_pos_srs_resource_list_t *pos_srs_resource_list = sRSConfig->pos_srs_resource_list;
+ uint32_t pos_srs_resource_list_length = 3;
+ pos_srs_resource_list->pos_srs_resource_list_length = pos_srs_resource_list_length;
+ pos_srs_resource_list->pos_srs_resource_item =
+ calloc_or_fail(pos_srs_resource_list_length, sizeof(*pos_srs_resource_list->pos_srs_resource_item));
+
+ // periodic
+ nrppa_pos_srs_resource_item_t *pos_srs_resource = &pos_srs_resource_list->pos_srs_resource_item[0];
+ pos_srs_resource->srs_pos_resource_id = 12;
+ pos_srs_resource->transmission_comb_pos.present = NRPPA_TRANSMISSION_COMB_POS_PR_N2;
+ pos_srs_resource->transmission_comb_pos.choice.n2.comb_offset_n2 = 1;
+ pos_srs_resource->transmission_comb_pos.choice.n2.cyclic_shift_n2 = 4;
+ pos_srs_resource->start_position = 9;
+ pos_srs_resource->nr_of_symbols = NRPPA_SRS_RESOURCE_ITEM_NUMBER_OF_SYMBOLS_N8;
+ pos_srs_resource->freq_domain_shift = 100;
+ pos_srs_resource->c_srs = 20;
+ pos_srs_resource->group_or_sequence_hopping = NRPPA_GROUPORSEQUENCEHOPPING_GROUPHOPPING;
+ pos_srs_resource->resource_type_pos.present = NRPPA_RESOURCE_TYPE_POS_PR_PERIODIC;
+ pos_srs_resource->resource_type_pos.choice.periodic.periodicity = NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT5;
+ pos_srs_resource->resource_type_pos.choice.periodic.offset = 10;
+ pos_srs_resource->sequence_id = 1;
+
+ // semi-persistent
+ pos_srs_resource = &pos_srs_resource_list->pos_srs_resource_item[1];
+ pos_srs_resource->srs_pos_resource_id = 13;
+ pos_srs_resource->transmission_comb_pos.present = NRPPA_TRANSMISSION_COMB_POS_PR_N4;
+ pos_srs_resource->transmission_comb_pos.choice.n4.comb_offset_n4 = 3;
+ pos_srs_resource->transmission_comb_pos.choice.n4.cyclic_shift_n4 = 5;
+ pos_srs_resource->start_position = 12;
+ pos_srs_resource->nr_of_symbols = NRPPA_SRS_RESOURCE_ITEM_NUMBER_OF_SYMBOLS_N12;
+ pos_srs_resource->freq_domain_shift = 100;
+ pos_srs_resource->c_srs = 20;
+ pos_srs_resource->group_or_sequence_hopping = NRPPA_GROUPORSEQUENCEHOPPING_GROUPHOPPING;
+ pos_srs_resource->resource_type_pos.present = NRPPA_RESOURCE_TYPE_POS_PR_SEMI_PERSISTENT;
+ pos_srs_resource->resource_type_pos.choice.semi_persistent.periodicity = NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT32;
+ pos_srs_resource->resource_type_pos.choice.semi_persistent.offset = 5;
+ pos_srs_resource->sequence_id = 2;
+
+ // aperiodic
+ pos_srs_resource = &pos_srs_resource_list->pos_srs_resource_item[2];
+ pos_srs_resource->srs_pos_resource_id = 14;
+ pos_srs_resource->transmission_comb_pos.present = NRPPA_TRANSMISSION_COMB_POS_PR_N8;
+ pos_srs_resource->transmission_comb_pos.choice.n8.comb_offset_n8 = 5;
+ pos_srs_resource->transmission_comb_pos.choice.n8.cyclic_shift_n8 = 2;
+ pos_srs_resource->start_position = 9;
+ pos_srs_resource->nr_of_symbols = NRPPA_SRS_RESOURCE_ITEM_NUMBER_OF_SYMBOLS_N4;
+ pos_srs_resource->freq_domain_shift = 100;
+ pos_srs_resource->c_srs = 20;
+ pos_srs_resource->group_or_sequence_hopping = NRPPA_GROUPORSEQUENCEHOPPING_SEQUENCEHOPPING;
+ pos_srs_resource->resource_type_pos.present = NRPPA_RESOURCE_TYPE_POS_PR_APERIODIC;
+ pos_srs_resource->resource_type_pos.choice.periodic.periodicity = NRPPA_SRS_RESOURCE_TYPE_POS_PERIODICITY_SLOT5;
+ pos_srs_resource->resource_type_pos.choice.aperiodic.slot_offset = 31;
+ pos_srs_resource->sequence_id = 3;
+
+ // optional: srs_resource_set_list
+ sRSConfig->srs_resource_set_list = calloc_or_fail(1, sizeof(*sRSConfig->srs_resource_set_list));
+ nrppa_srs_resource_set_list_t *srs_resource_set_list = sRSConfig->srs_resource_set_list;
+ uint32_t srs_resource_set_list_length = 3;
+ srs_resource_set_list->srs_resource_set_list_length = srs_resource_set_list_length;
+ srs_resource_set_list->srs_resource_set =
+ calloc_or_fail(srs_resource_set_list_length, sizeof(*srs_resource_set_list->srs_resource_set));
+
+ // periodic
+ nrppa_srs_resource_set_t *srs_resource_set = &srs_resource_set_list->srs_resource_set[0];
+ srs_resource_set->srs_resource_set_id = 0;
+ uint8_t srs_resource_id_list_length = 5;
+ srs_resource_set->srs_resource_id_list.srs_resource_id_list_length = srs_resource_id_list_length;
+ srs_resource_set->srs_resource_id_list.srs_resource_id =
+ calloc_or_fail(srs_resource_id_list_length, sizeof(*srs_resource_set->srs_resource_id_list.srs_resource_id));
+ for (int k = 0; k < srs_resource_id_list_length; k++) {
+ srs_resource_set->srs_resource_id_list.srs_resource_id[k] = k;
+ }
+ srs_resource_set->resource_set_type.present = NRPPA_RESOURCE_SET_TYPE_PR_PERIODIC;
+ // set periodic = 0 to enable
+ srs_resource_set->resource_set_type.choice.periodic = 0;
+
+ // semi-persistent
+ srs_resource_set = &srs_resource_set_list->srs_resource_set[1];
+ srs_resource_set->srs_resource_set_id = 1;
+ srs_resource_id_list_length = 5;
+ srs_resource_set->srs_resource_id_list.srs_resource_id_list_length = srs_resource_id_list_length;
+ srs_resource_set->srs_resource_id_list.srs_resource_id =
+ calloc_or_fail(srs_resource_id_list_length, sizeof(srs_resource_set->srs_resource_id_list.srs_resource_id));
+ for (int k = 0; k < srs_resource_id_list_length; k++) {
+ srs_resource_set->srs_resource_id_list.srs_resource_id[k] = k;
+ }
+ srs_resource_set->resource_set_type.present = NRPPA_RESOURCE_SET_TYPE_PR_SEMI_PERSISTENT;
+ // set semi_persistent = 0 to enable
+ srs_resource_set->resource_set_type.choice.semi_persistent = 0;
+
+ // aperiodic
+ srs_resource_set = &srs_resource_set_list->srs_resource_set[2];
+ srs_resource_set->srs_resource_set_id = 2;
+ srs_resource_id_list_length = 5;
+ srs_resource_set->srs_resource_id_list.srs_resource_id_list_length = srs_resource_id_list_length;
+ srs_resource_set->srs_resource_id_list.srs_resource_id =
+ calloc_or_fail(srs_resource_id_list_length, sizeof(*srs_resource_set->srs_resource_id_list.srs_resource_id));
+ for (int k = 0; k < srs_resource_id_list_length; k++) {
+ srs_resource_set->srs_resource_id_list.srs_resource_id[k] = k;
+ }
+
+ srs_resource_set->resource_set_type.present = NRPPA_RESOURCE_SET_TYPE_PR_APERIODIC;
+ srs_resource_set->resource_set_type.choice.aperiodic.srs_resource_trigger = 2;
+ srs_resource_set->resource_set_type.choice.aperiodic.slot_offset = 20;
+
+ // optional: pos_srs_resource_set_list
+ sRSConfig->pos_srs_resource_set_list = calloc_or_fail(1, sizeof(*sRSConfig->pos_srs_resource_set_list));
+ nrppa_pos_srs_resource_set_list_t *pos_srs_resource_set_list = sRSConfig->pos_srs_resource_set_list;
+ uint32_t pos_srs_resource_set_list_length = 3;
+ pos_srs_resource_set_list->pos_srs_resource_set_list_length = pos_srs_resource_set_list_length;
+ pos_srs_resource_set_list->pos_srs_resource_set_item =
+ calloc_or_fail(pos_srs_resource_set_list_length, sizeof(*pos_srs_resource_set_list->pos_srs_resource_set_item));
+
+ // periodic
+ nrppa_pos_srs_resource_set_item_t *pos_srs_resource_set = &pos_srs_resource_set_list->pos_srs_resource_set_item[0];
+ pos_srs_resource_set->pos_srs_resource_set_id = 0;
+ uint8_t pos_srs_resource_id_list_length = 5;
+ pos_srs_resource_set->pos_srs_resource_id_list.pos_srs_resource_id_list_length = pos_srs_resource_id_list_length;
+ pos_srs_resource_set->pos_srs_resource_id_list.srs_pos_resource_id =
+ calloc_or_fail(pos_srs_resource_id_list_length,
+ sizeof(*pos_srs_resource_set->pos_srs_resource_id_list.srs_pos_resource_id));
+ for (int k = 0; k < pos_srs_resource_id_list_length; k++) {
+ pos_srs_resource_set->pos_srs_resource_id_list.srs_pos_resource_id[k] = k;
+ }
+ pos_srs_resource_set->pos_resource_set_type.present = NRPPA_POS_RESOURCE_SET_TYPE_PR_PERIODIC;
+ // set periodic = 0 to enable
+ pos_srs_resource_set->pos_resource_set_type.choice.periodic = 0;
+
+ // semi-persistent
+ pos_srs_resource_set = &pos_srs_resource_set_list->pos_srs_resource_set_item[1];
+ pos_srs_resource_set->pos_srs_resource_set_id = 1;
+ pos_srs_resource_id_list_length = 5;
+ pos_srs_resource_set->pos_srs_resource_id_list.pos_srs_resource_id_list_length = pos_srs_resource_id_list_length;
+ pos_srs_resource_set->pos_srs_resource_id_list.srs_pos_resource_id =
+ calloc_or_fail(pos_srs_resource_id_list_length,
+ sizeof(*pos_srs_resource_set->pos_srs_resource_id_list.srs_pos_resource_id));
+ for (int k = 0; k < pos_srs_resource_id_list_length; k++) {
+ pos_srs_resource_set->pos_srs_resource_id_list.srs_pos_resource_id[k] = k;
+ }
+ pos_srs_resource_set->pos_resource_set_type.present = NRPPA_POS_RESOURCE_SET_TYPE_PR_SEMI_PERSISTENT;
+ // set semi_persistent = 0 to enable
+ pos_srs_resource_set->pos_resource_set_type.choice.semi_persistent = 0;
+
+ // aperiodic
+ pos_srs_resource_set = &pos_srs_resource_set_list->pos_srs_resource_set_item[2];
+ pos_srs_resource_set->pos_srs_resource_set_id = 2;
+ pos_srs_resource_id_list_length = 5;
+ pos_srs_resource_set->pos_srs_resource_id_list.pos_srs_resource_id_list_length = pos_srs_resource_id_list_length;
+ pos_srs_resource_set->pos_srs_resource_id_list.srs_pos_resource_id =
+ calloc_or_fail(pos_srs_resource_id_list_length,
+ sizeof(*pos_srs_resource_set->pos_srs_resource_id_list.srs_pos_resource_id));
+ for (int k = 0; k < pos_srs_resource_id_list_length; k++) {
+ pos_srs_resource_set->pos_srs_resource_id_list.srs_pos_resource_id[k] = k;
+ }
+ pos_srs_resource_set->pos_resource_set_type.present = NRPPA_POS_RESOURCE_SET_TYPE_PR_APERIODIC;
+ pos_srs_resource_set->pos_resource_set_type.choice.srs_resource = 3;
+ }
+ return resp;
+}
+
+static nrppa_measurement_resp_t fill_measurement_response(uint16_t transaction_id, uint32_t lmf_measurement_id)
+{
+ positioning_config_t positioning_config = RCconfig_nr_positioning();
+ nrppa_measurement_resp_t resp = {0};
+ resp.transaction_id = transaction_id;
+ resp.lmf_measurement_id = lmf_measurement_id;
+ resp.ran_measurement_id = 1;
+ resp.measurement_response_list = calloc_or_fail(1, sizeof(*resp.measurement_response_list));
+ uint32_t meas_response_list_len = positioning_config.num_trp;
+ resp.measurement_response_list->measurement_response_list_length = meas_response_list_len;
+ resp.measurement_response_list->measurement_response_item =
+ calloc_or_fail(meas_response_list_len, sizeof(*resp.measurement_response_list->measurement_response_item));
+ for (int i = 0; i < meas_response_list_len; i++) {
+ nrppa_measurement_response_item_t *meas_response_item = &resp.measurement_response_list->measurement_response_item[i];
+ meas_response_item->trp_id = positioning_config.trps[i].id;
+
+ nrppa_measurement_result_t *MeasurementResult = &meas_response_item->measurement_result;
+ uint32_t meas_result_length = 4;
+ MeasurementResult->measurement_result_item_length = meas_result_length;
+ MeasurementResult->measurement_result_item =
+ calloc_or_fail(meas_result_length, sizeof(*MeasurementResult->measurement_result_item));
+
+ // Angle of arrival
+ nrppa_measurement_result_item_t *measurement_result_item = &MeasurementResult->measurement_result_item[0];
+ nrppa_measured_results_value_t *measuredResultsValue = &measurement_result_item->measured_results_value;
+ measuredResultsValue->present = NRPPA_MEASURED_RESULTS_VALUE_PR_UL_ANGLEOFARRIVAL;
+ nrppa_ul_aoa_t *uL_AngleOfArrival = &measuredResultsValue->choice.ul_angle_of_arrival;
+ uL_AngleOfArrival->azimuth_aoa = 700 + i;
+ uL_AngleOfArrival->zenith_aoa = calloc_or_fail(1, sizeof(*uL_AngleOfArrival->zenith_aoa));
+ *uL_AngleOfArrival->zenith_aoa = 450 + i;
+
+ nrppa_time_stamp_t *timeStamp = &measurement_result_item->time_stamp;
+ timeStamp->system_frame_number = 100;
+ timeStamp->slot_index.present = NRPPA_TIME_STAMP_SLOT_INDEX_PR_SCS_30;
+ timeStamp->slot_index.choice.scs_30 = 15;
+
+ // UL SRS RSRP
+ measurement_result_item = &MeasurementResult->measurement_result_item[1];
+ measuredResultsValue = &measurement_result_item->measured_results_value;
+ measuredResultsValue->present = NRPPA_MEASURED_RESULTS_VALUE_PR_UL_SRS_RSRP;
+ measuredResultsValue->choice.ul_srs_rsrp = 100 + i;
+
+ timeStamp = &measurement_result_item->time_stamp;
+ timeStamp->system_frame_number = 101;
+ timeStamp->slot_index.present = NRPPA_TIME_STAMP_SLOT_INDEX_PR_SCS_15;
+ timeStamp->slot_index.choice.scs_15 = 8;
+
+ // UL RToA
+ measurement_result_item = &MeasurementResult->measurement_result_item[2];
+ measuredResultsValue = &measurement_result_item->measured_results_value;
+ measuredResultsValue->present = NRPPA_MEASURED_RESULTS_VALUE_PR_UL_RTOA;
+ nrppa_ul_rtoa_measurement_t *uL_RTOA = &measuredResultsValue->choice.ul_rtoa;
+ uL_RTOA->present = NRPPA_ULRTOAMEAS_PR_K1;
+ uL_RTOA->choice.k1 = 98500 + i;
+
+ timeStamp = &measurement_result_item->time_stamp;
+ timeStamp->system_frame_number = 102;
+ timeStamp->slot_index.present = NRPPA_TIME_STAMP_SLOT_INDEX_PR_SCS_60;
+ timeStamp->slot_index.choice.scs_60 = 31;
+
+ // gNB RX-TX Time Diff
+ measurement_result_item = &MeasurementResult->measurement_result_item[3];
+ measuredResultsValue = &measurement_result_item->measured_results_value;
+ measuredResultsValue->present = NRPPA_MEASURED_RESULTS_VALUE_PR_GNB_RXTXTIMEDIFF;
+ nrppa_gnb_rx_tx_time_diff_t *gNB_RxTxTimeDiff = &measuredResultsValue->choice.gnb_rx_tx_time_diff;
+ gNB_RxTxTimeDiff->present = NRPPA_GNBRXTXTIMEDIFFMEAS_PR_K3;
+ gNB_RxTxTimeDiff->choice.k3 = 98412 + i;
+
+ timeStamp = &measurement_result_item->time_stamp;
+ timeStamp->system_frame_number = 103;
+ timeStamp->slot_index.present = NRPPA_TIME_STAMP_SLOT_INDEX_PR_SCS_120;
+ timeStamp->slot_index.choice.scs_120 = 70;
+ }
+ return resp;
+}
+
+// Initializing UE NAS Context with simulated SIM data
+nr_ue_nas_t *simulated_ue_nas = NULL;
+void init_ue_nas_context(void)
+{
+ simulated_ue_nas = calloc_or_fail(1, sizeof(nr_ue_nas_t));
+ simulated_ue_nas->UE_id = 1;
+ simulated_ue_nas->security_container = calloc_or_fail(1, sizeof(stream_security_container_t));
+ // Allocation and simulation of UICC data
+ simulated_ue_nas->uicc = calloc_or_fail(1, sizeof(uicc_t));
+ // IMSI : 001010000000001
+ simulated_ue_nas->uicc->imsiStr = calloc_or_fail(1, 16 * sizeof(char));
+ strcpy(simulated_ue_nas->uicc->imsiStr, "001010000000001");
+ simulated_ue_nas->uicc->nmc_size = 2;
+ // DNN : oai
+ simulated_ue_nas->uicc->dnnStr = calloc_or_fail(1, 32 * sizeof(char));
+ strcpy(simulated_ue_nas->uicc->dnnStr, "oai");
+ // IMEISV : 6754567890123413
+ simulated_ue_nas->uicc->imeisvStr = calloc_or_fail(1, 17 * sizeof(char));
+ strcpy(simulated_ue_nas->uicc->imeisvStr, "6754567890123413");
+ // NSSAI: sst = 1, sd = 0xffffff
+ simulated_ue_nas->uicc->nssai_sst = 1;
+ simulated_ue_nas->uicc->nssai_sd = 0xffffff;
+ // Ki: fec86ba6eb707ed08905757b1bb44b8f
+ static const uint8_t TEST_K[16] =
+ {0xfe, 0xc8, 0x6b, 0xa6, 0xeb, 0x70, 0x7e, 0xd0, 0x89, 0x05, 0x75, 0x7b, 0x1b, 0xb4, 0x4b, 0x8f};
+ memcpy(simulated_ue_nas->uicc->key, TEST_K, 16);
+ // OPc: c42449363bbad02b66d16bc975d77cc1
+ static const uint8_t TEST_OPC[16] =
+ {0xc4, 0x24, 0x49, 0x36, 0x3b, 0xba, 0xd0, 0x2b, 0x66, 0xd1, 0x6b, 0xc9, 0x75, 0xd7, 0x7c, 0xc1};
+ memcpy(simulated_ue_nas->uicc->opc, TEST_OPC, 16);
+ simulated_ue_nas->security.nas_count_ul = 0;
+ simulated_ue_nas->security.nas_count_dl = 0;
+ simulated_ue_nas->fiveGMM_state = FGS_DEREGISTERED;
+}
+
+// Emulate registration request to register UE in the AMF (required for positioning)
+void send_initial_ue_message(instance_t instance)
+{
+ MessageDef *msg_p = itti_alloc_new_message(TASK_RRC_GNB, 0, NGAP_NAS_FIRST_REQ);
+
+ NGAP_NAS_FIRST_REQ(msg_p).gNB_ue_ngap_id = 1; // Simulated UE ID
+
+ NGAP_NAS_FIRST_REQ(msg_p).plmn.mcc = 1;
+ NGAP_NAS_FIRST_REQ(msg_p).plmn.mnc = 1;
+ NGAP_NAS_FIRST_REQ(msg_p).plmn.mnc_digit_length = 2;
+
+ NGAP_NAS_FIRST_REQ(msg_p).nr_cell_id = gnb_id;
+
+ NGAP_NAS_FIRST_REQ(msg_p).establishment_cause = NGAP_RRC_CAUSE_MO_SIGNALLING;
+
+ as_nas_info_t initialNasMsg = {0};
+ generateRegistrationRequest(&initialNasMsg, simulated_ue_nas, false);
+
+ NGAP_NAS_FIRST_REQ(msg_p).nas_pdu.buf = initialNasMsg.nas_data;
+ NGAP_NAS_FIRST_REQ(msg_p).nas_pdu.len = initialNasMsg.length;
+
+ NGAP_NAS_FIRST_REQ(msg_p).ue_identity.presenceMask = 0;
+
+ itti_send_msg_to_task(TASK_NGAP, instance, msg_p);
+}
+
+void *gNB_app_task(void *args_p)
+{
+ MessageDef *msg_p = NULL;
+ const char *msg_name = NULL;
+ instance_t instance;
+ int result;
+ /* for no gcc warnings */
+ (void)instance;
+
+ itti_mark_task_ready(TASK_GNB_APP);
+ do {
+ // Wait for a message
+ itti_receive_msg(TASK_GNB_APP, &msg_p);
+
+ msg_name = ITTI_MSG_NAME(msg_p);
+ instance = ITTI_MSG_DESTINATION_INSTANCE(msg_p);
+
+ switch (ITTI_MSG_ID(msg_p)) {
+ case TERMINATE_MESSAGE:
+ LOG_W(GNB_APP, " *** Exiting GNB_APP thread\n");
+ itti_exit_task();
+ break;
+
+ case NGAP_REGISTER_GNB_CNF:
+ LOG_I(GNB_APP, "[gNB %ld] Received %s: associated AMF %d\n", instance, msg_name, NGAP_REGISTER_GNB_CNF(msg_p).nb_amf);
+ send_initial_ue_message(instance);
+ break;
+
+ default:
+ LOG_E(GNB_APP, "Received unexpected message %s\n", msg_name);
+ break;
+ }
+ result = itti_free(ITTI_MSG_ORIGIN_ID(msg_p), msg_p);
+ AssertFatal(result == EXIT_SUCCESS, "Failed to free memory (%d)!\n", result);
+ } while (1);
+
+ return NULL;
+}
+
+void *rrc_gnb_task(void *args_p)
+{
+ MessageDef *msg_p;
+ MessageDef *msg_p_resp;
+ instance_t instance;
+ int result;
+
+ itti_mark_task_ready(TASK_RRC_GNB);
+ LOG_I(NR_RRC, "Entering main loop of NR_RRC message task\n");
+
+ while (1) {
+ // Wait for a message
+ itti_receive_msg(TASK_RRC_GNB, &msg_p);
+ const char *msg_name_p = ITTI_MSG_NAME(msg_p);
+ instance = ITTI_MSG_DESTINATION_INSTANCE(msg_p);
+ LOG_D(NR_RRC,
+ "RRC GNB Task Received %s for instance %ld from task %s\n",
+ ITTI_MSG_NAME(msg_p),
+ ITTI_MSG_DESTINATION_INSTANCE(msg_p),
+ ITTI_MSG_ORIGIN_NAME(msg_p));
+ switch (ITTI_MSG_ID(msg_p)) {
+ case TERMINATE_MESSAGE:
+ LOG_W(NR_RRC, " *** Exiting NR_RRC thread\n");
+ itti_exit_task();
+ break;
+ case NGAP_DOWNLINK_NAS:
+ LOG_I(NR_RRC, "Ignore NGAP_DOWNLINK_NAS: dont have to handle");
+ ngap_downlink_nas_t *nas = &NGAP_DOWNLINK_NAS(msg_p);
+ if (nas->nas_pdu.buf) {
+ free(nas->nas_pdu.buf);
+ }
+ break;
+ case NRPPA_TRP_INFORMATION_REQ:
+ nrppa_trp_information_req_t *trp_req = &NRPPA_TRP_INFORMATION_REQ(msg_p);
+ LOG_I(NR_RRC, "Received NRPPA_TRP_INFORMATION_REQ transaction_id %d\n", trp_req->transaction_id);
+ msg_p_resp = itti_alloc_new_message(TASK_RRC_GNB, 0, NRPPA_TRP_INFORMATION_RESP);
+ NRPPA_TRP_INFORMATION_RESP(msg_p_resp) = fill_trp_resp(trp_req->transaction_id);
+ LOG_I(NR_RRC, "Sending NRPPA_TRP_INFORMATION_RESP to TASK_NRPPA\n");
+ itti_send_msg_to_task(TASK_NRPPA, 0, msg_p_resp);
+ break;
+ case NRPPA_POSITIONING_INFORMATION_REQ:
+ nrppa_positioning_information_req_t *pos_req = &NRPPA_POSITIONING_INFORMATION_REQ(msg_p);
+ LOG_I(NR_RRC, "Received NRPPA_POSITIONING_INFORMATION_REQ transaction_id %d\n", pos_req->transaction_id);
+ msg_p_resp = itti_alloc_new_message(TASK_RRC_GNB, 0, NRPPA_POSITIONING_INFORMATION_RESP);
+ NRPPA_POSITIONING_INFORMATION_RESP(msg_p_resp) = fill_position_information_resp(pos_req->transaction_id);
+ LOG_I(NR_RRC, "Sending NRPPA_POSITIONING_INFORMATION_RESP to TASK_NRPPA\n");
+ itti_send_msg_to_task(TASK_NRPPA, 0, msg_p_resp);
+ break;
+ case NRPPA_POSITIONING_ACTIVATION_REQ:
+ nrppa_positioning_activation_req_t *req = &NRPPA_POSITIONING_ACTIVATION_REQ(msg_p);
+ LOG_I(NR_RRC, "Received NRPPA_POSITIONING_ACTIVATION_REQ transaction_id %d\n", req->transaction_id);
+ msg_p_resp = itti_alloc_new_message(TASK_RRC_GNB, 0, NRPPA_POSITIONING_ACTIVATION_RESP);
+ NRPPA_POSITIONING_ACTIVATION_RESP(msg_p_resp).transaction_id = req->transaction_id;
+ LOG_I(NR_RRC, "Sending NRPPA_POSITIONING_ACTIVATION_RESP to TASK_NRPPA\n");
+ itti_send_msg_to_task(TASK_NRPPA, 0, msg_p_resp);
+ free_positioning_activation_request(req);
+ break;
+ case NRPPA_MEASUREMENT_REQ:
+ nrppa_measurement_req_t *m_req = &NRPPA_MEASUREMENT_REQ(msg_p);
+ LOG_I(NR_RRC, "Received NRPPA_MEASUREMENT_REQ transaction_id %d\n", m_req->transaction_id);
+ msg_p_resp = itti_alloc_new_message(TASK_RRC_GNB, 0, NRPPA_MEASUREMENT_RESP);
+ NRPPA_MEASUREMENT_RESP(msg_p_resp) = fill_measurement_response(m_req->transaction_id, m_req->lmf_measurement_id);
+ LOG_I(NR_RRC, "Sending NRPPA_MEASUREMENT_RESP to TASK_NRPPA\n");
+ itti_send_msg_to_task(TASK_NRPPA, 0, msg_p_resp);
+ free_measurement_request(m_req);
+ break;
+ default:
+ LOG_E(NR_RRC, "[gNB %ld] Received unexpected message %s\n", instance, msg_name_p);
+ break;
+ }
+ result = itti_free(ITTI_MSG_ORIGIN_ID(msg_p), msg_p);
+ AssertFatal(result == EXIT_SUCCESS, "Failed to free memory (%d)!\n", result);
+ msg_p = NULL;
+ }
+}
+
+int main(int argc, char **argv)
+{
+ // load the config file
+ if ((uniqCfg = load_configmodule(argc, argv, CONFIG_ENABLECMDLINEONLY)) == NULL) {
+ exit_fun("[SOFTMODEM] Error, configuration module init failed\n");
+ }
+ logInit();
+
+ init_ue_nas_context();
+
+ set_softmodem_sighandler();
+
+ // Initialize ITTI tasks
+ itti_init(TASK_MAX, tasks_info);
+
+ int rc;
+ rc = itti_create_task(TASK_SCTP, sctp_eNB_task, NULL);
+ AssertFatal(rc >= 0, "Create task for SCTP failed\n");
+
+ rc = itti_create_task(TASK_NGAP, ngap_gNB_task, NULL);
+ AssertFatal(rc >= 0, "Create task for NGAP failed\n");
+
+ rc = itti_create_task(TASK_NRPPA, nrppa_gNB_task, NULL);
+ AssertFatal(rc >= 0, "Create task for NRPPA failed\n");
+
+ rc = itti_create_task(TASK_RRC_GNB, rrc_gnb_task, NULL);
+ AssertFatal(rc >= 0, "Create task for RRC failed\n");
+
+ rc = itti_create_task(TASK_GNB_APP, gNB_app_task, NULL);
+ AssertFatal(rc >= 0, "Create task for RRC failed\n");
+
+ MessageDef *msg_p;
+ msg_p = itti_alloc_new_message(TASK_GNB_APP, 0, NGAP_REGISTER_GNB_REQ);
+ RCconfig_NR_NG(msg_p, 0);
+ gnb_id = NGAP_REGISTER_GNB_REQ(msg_p).gNB_id;
+
+ LOG_I(GNB_APP, "Sending NGAP_REGISTER_GNB_REQ to TASK_NGAP\n");
+ itti_send_msg_to_task(TASK_NGAP, 0, msg_p);
+
+ printf("TYPE TO TERMINATE\n");
+ itti_wait_tasks_end(NULL);
+
+ logClean();
+ printf("Bye.\n");
+ return 0;
+}
diff --git a/tests/nr-cu-nrppa/nr-nrppa-test.conf b/tests/nr-cu-nrppa/nr-nrppa-test.conf
new file mode 100644
index 0000000000..aaaa45f176
--- /dev/null
+++ b/tests/nr-cu-nrppa/nr-nrppa-test.conf
@@ -0,0 +1,73 @@
+Active_gNBs = ( "gNB-OAI");
+# Asn1_verbosity, choice in: none, info, annoying
+Asn1_verbosity = "none";
+
+gNBs =
+(
+ {
+ ////////// Identification parameters:
+ gNB_ID = 0xe00;
+ gNB_name = "gNB-OAI";
+
+ // Tracking area code, 0x0000 and 0xfffe are reserved values
+ tracking_area_code = 1;
+ plmn_list = ({ mcc = 001; mnc = 01; mnc_length = 2; snssaiList = ({ sst = 1; }) });
+
+ nr_cellid = 12345678L;
+
+ # ------- SCTP definitions
+ SCTP :
+ {
+ # Number of streams to use in input/output
+ SCTP_INSTREAMS = 2;
+ SCTP_OUTSTREAMS = 2;
+ };
+
+
+ ////////// AMF parameters:
+ amf_ip_address = ({ ipv4 = "192.168.70.132"; });
+
+
+ NETWORK_INTERFACES :
+ {
+ GNB_IPV4_ADDRESS_FOR_NG_AMF = "192.168.70.129/24";
+ GNB_IPV4_ADDRESS_FOR_NGU = "192.168.70.129/24";
+ GNB_PORT_FOR_S1U = 2152; # Spec 2152
+ };
+
+ }
+);
+
+positioning_config = (
+ {
+ NumTRPs = 4; # number of TRPs
+ TRPIDs = [1,2,3,4]; # userdefined distinct IDs
+ TRPxAxis = [71,21,10,45]; # X-axis value of each TRP
+ TRPyAxis = [11,22,62,14]; # Y-axis value of each TRP
+ TRPzAxis = [41,22,33,42]; # Z-axis value of each TRP
+ Units = [0, 0, 0, 0]; # 0 = mm, 1 = cm, 2 = dm
+ }
+);
+
+L1s = (
+ {
+ num_cc = 1;
+ tr_n_preference = "local_mac";
+ prach_dtx_threshold = 120;
+ pucch0_dtx_threshold = 150;
+ ofdm_offset_divisor = 8; #set this to UINT_MAX for offset 0
+ }
+);
+
+log_config :
+{
+ global_log_level ="info";
+ hw_log_level ="info";
+ phy_log_level ="info";
+ mac_log_level ="info";
+ rlc_log_level ="info";
+ pdcp_log_level ="info";
+ rrc_log_level ="info";
+ ngap_log_level ="debug";
+ f1ap_log_level ="debug";
+};