diff --git a/.gitignore b/.gitignore index 3a0d25c25c..c4a4022fba 100644 --- a/.gitignore +++ b/.gitignore @@ -25,3 +25,4 @@ tags nfapi_nr_interface_scf *.log *.out +CMakeUserPresets.json diff --git a/CMakeLists.txt b/CMakeLists.txt index 8d3834319f..0eb40de493 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -1001,7 +1001,7 @@ set(PHY_SRC_UE set(PHY_NR_SRC_COMMON ${OPENAIR1_DIR}/PHY/NR_TRANSPORT/nr_prach_common.c - ${OPENAIR1_DIR}/PHY/NR_TRANSPORT/nr_csi_rs.c + ${OPENAIR1_DIR}/PHY/nr_phy_common/src/nr_phy_common_csirs.c ${OPENAIR1_DIR}/PHY/NR_TRANSPORT/nr_scrambling.c ${OPENAIR1_DIR}/PHY/NR_REFSIG/scrambling_luts.c ${OPENAIR1_DIR}/PHY/NR_REFSIG/refsig.c @@ -1033,12 +1033,12 @@ set(PHY_SRC_UE ${OPENAIR1_DIR}/PHY/NR_REFSIG/nr_gen_mod_table.c ${OPENAIR1_DIR}/PHY/NR_REFSIG/dmrs_nr.c ${OPENAIR1_DIR}/PHY/NR_REFSIG/ptrs_nr.c + ${OPENAIR1_DIR}/PHY/NR_TRANSPORT/nr_csi_rs.c ${OPENAIR1_DIR}/PHY/NR_ESTIMATION/nr_ul_channel_estimation.c ${OPENAIR1_DIR}/PHY/NR_ESTIMATION/nr_freq_equalization.c ${OPENAIR1_DIR}/PHY/NR_ESTIMATION/nr_measurements_gNB.c ${OPENAIR1_DIR}/PHY/TOOLS/file_output.c ${OPENAIR1_DIR}/PHY/TOOLS/cadd_vv.c - #${OPENAIR1_DIR}/PHY/TOOLS/lte_dfts.c ${OPENAIR1_DIR}/PHY/TOOLS/log2_approx.c ${OPENAIR1_DIR}/PHY/TOOLS/cmult_sv.c ${OPENAIR1_DIR}/PHY/TOOLS/cmult_vv.c @@ -1093,7 +1093,6 @@ set(PHY_SRC_UE ${OPENAIR1_DIR}/PHY/NR_UE_ESTIMATION/nr_adjust_gain.c ${OPENAIR1_DIR}/PHY/TOOLS/file_output.c ${OPENAIR1_DIR}/PHY/TOOLS/cadd_vv.c - # ${OPENAIR1_DIR}/PHY/TOOLS/lte_dfts.c ${OPENAIR1_DIR}/PHY/TOOLS/log2_approx.c ${OPENAIR1_DIR}/PHY/TOOLS/cmult_sv.c ${OPENAIR1_DIR}/PHY/TOOLS/cmult_vv.c @@ -1104,7 +1103,6 @@ set(PHY_SRC_UE ${OPENAIR1_DIR}/PHY/TOOLS/lut.c ${OPENAIR1_DIR}/PHY/TOOLS/simde_operations.c ${OPENAIR1_DIR}/PHY/INIT/nr_init_ue.c - # ${OPENAIR1_DIR}/SIMULATION/NR_UE_PHY/unit_tests/src/pucch_uci_test.c ${PHY_POLARSRC} ${PHY_SMALLBLOCKSRC} ${PHY_NR_CODINGIF} diff --git a/CMakePresets.json b/CMakePresets.json new file mode 100644 index 0000000000..9e20a5b07a --- /dev/null +++ b/CMakePresets.json @@ -0,0 +1,64 @@ +{ + "version": 3, + "configurePresets": [ + { + "name": "default", + "displayName": "Default Config", + "description": "Default build using Ninja generator", + "generator": "Ninja", + "binaryDir": "${sourceDir}/cmake_targets/ran_build/build", + "cacheVariables": { + "CMAKE_BUILD_TYPE": "RelWithDebInfo" + } + }, + { + "name": "tests", + "displayName": "Default unit test config", + "inherits": "default", + "binaryDir": "${sourceDir}/cmake_targets/ran_build/build_test", + "cacheVariables": { + "ENABLE_TESTS": "ON", + "SANITIZE_ADDRESS": "ON", + "CMAKE_BUILD_TYPE": "RelWithDebInfo" + } + } + ], + "buildPresets": [ + { + "name": "5gdefault", + "configurePreset": "default", + "targets": [ + "nr-uesoftmodem", + "nr-softmodem", + "rfsimulator", + "dfts", + "ldpc", + "params_libconfig", + "params_yaml" + ] + }, + { + "name": "default", + "inherits": "5gdefault" + }, + { + "name": "4gdefault", + "configurePreset": "default", + "targets": [ + "lte-softmodem", + "lte-uesoftmodem", + "dfts", + "coding", + "rfsimulator", + "params_libconfig" + ] + }, + { + "name": "tests", + "configurePreset": "tests", + "targets": [ + "tests" + ] + } + ] +} diff --git a/README.md b/README.md index b5d3dc46c0..fc5dd23e62 100644 --- a/README.md +++ b/README.md @@ -76,7 +76,8 @@ openairinterface5g ├── openair3 : Layer 3 (3GPP LTE Rel-10 S1AP/GTP, NR Rel-15 NGAP/GTP) ├── openshift : OpenShift helm charts for some deployment options of OAI ├── radio : Drivers for various radios such as USRP, AW2S, RFsim, 7.2 FHI, ... -└── targets : Some configuration files; only historical relevance, and might be deleted in the future +├── targets : Some configuration files; only historical relevance, and might be deleted in the future +└── tools : Tools for use by the developers/ci machines: code analysis and formatting ``` # How to get support from the OAI Community # diff --git a/ci-scripts/conf_files/gnb-du.band78.106prb.rfsim.conf b/ci-scripts/conf_files/gnb-du.band78.106prb.rfsim.conf index ef7f3d9b1f..3ee42b4510 100644 --- a/ci-scripts/conf_files/gnb-du.band78.106prb.rfsim.conf +++ b/ci-scripts/conf_files/gnb-du.band78.106prb.rfsim.conf @@ -198,8 +198,6 @@ RUs = ( max_pdschReferenceSignalPower = -27; max_rxgain = 114; eNB_instances = [0]; - #beamforming 1x4 matrix: - bf_weights = [0x00007fff, 0x0000, 0x0000, 0x0000]; clock_src = "internal"; } ); diff --git a/ci-scripts/conf_files/gnb-du.sa.band1.52prb.usrpb210.conf b/ci-scripts/conf_files/gnb-du.sa.band1.52prb.usrpb210.conf index fb227fbaab..adf5b4ab14 100644 --- a/ci-scripts/conf_files/gnb-du.sa.band1.52prb.usrpb210.conf +++ b/ci-scripts/conf_files/gnb-du.sa.band1.52prb.usrpb210.conf @@ -195,8 +195,6 @@ RUs = ( max_pdschReferenceSignalPower = -27; max_rxgain = 108; eNB_instances = [0]; - #beamforming 1x4 matrix: - bf_weights = [0x00007fff, 0x0000, 0x0000, 0x0000]; clock_src = "internal"; } ); diff --git a/ci-scripts/conf_files/gnb-du.sa.band78.106prb.rfsim.conf b/ci-scripts/conf_files/gnb-du.sa.band78.106prb.rfsim.conf index 8bc6410912..679af4bc9e 100644 --- a/ci-scripts/conf_files/gnb-du.sa.band78.106prb.rfsim.conf +++ b/ci-scripts/conf_files/gnb-du.sa.band78.106prb.rfsim.conf @@ -198,8 +198,6 @@ RUs = ( max_pdschReferenceSignalPower = -27; max_rxgain = 114; eNB_instances = [0]; - #beamforming 1x4 matrix: - bf_weights = [0x00007fff, 0x0000, 0x0000, 0x0000]; clock_src = "internal"; } ); diff --git a/ci-scripts/conf_files/gnb-du.sa.band78.106prb.usrpb200.conf b/ci-scripts/conf_files/gnb-du.sa.band78.106prb.usrpb200.conf index e977edd5f3..b9823cd5b6 100644 --- a/ci-scripts/conf_files/gnb-du.sa.band78.106prb.usrpb200.conf +++ b/ci-scripts/conf_files/gnb-du.sa.band78.106prb.usrpb200.conf @@ -200,8 +200,6 @@ RUs = ( max_pdschReferenceSignalPower = -27; max_rxgain = 114; eNB_instances = [0]; - #beamforming 1x4 matrix: - bf_weights = [0x00007fff, 0x0000, 0x0000, 0x0000]; clock_src = "internal"; } ); diff --git a/ci-scripts/conf_files/gnb.band66.106prb.rfsim.phytest-dora.conf b/ci-scripts/conf_files/gnb.band66.106prb.rfsim.phytest-dora.conf index 31b10bce7c..24d3fc094f 100644 --- a/ci-scripts/conf_files/gnb.band66.106prb.rfsim.phytest-dora.conf +++ b/ci-scripts/conf_files/gnb.band66.106prb.rfsim.phytest-dora.conf @@ -187,15 +187,6 @@ RUs = ( max_pdschReferenceSignalPower = -27; max_rxgain = 75; eNB_instances = [0]; - ##beamforming 1x2 matrix: 1 layer x 2 antennas - bf_weights = [0x00007fff, 0x0000]; - ##beamforming 1x4 matrix: 1 layer x 4 antennas - #bf_weights = [0x00007fff, 0x0000,0x0000, 0x0000]; - ## beamforming 2x2 matrix: - # bf_weights = [0x00007fff, 0x00000000, 0x00000000, 0x00007fff]; - ## beamforming 4x4 matrix: - #bf_weights = [0x00007fff, 0x0000, 0x0000, 0x0000, 0x00000000, 0x00007fff, 0x0000, 0x0000, 0x0000, 0x0000, 0x00007fff, 0x0000, 0x0000, 0x0000, 0x0000, 0x00007fff]; - sdr_addrs = "addr=192.168.10.2,mgmt_addr=192.168.10.2,second_addr=192.168.20.2"; clock_src = "external"; # if_freq = 3700000000L; diff --git a/ci-scripts/conf_files/gnb.band78.106prb.rfsim.phytest-dora.conf b/ci-scripts/conf_files/gnb.band78.106prb.rfsim.phytest-dora.conf index d9f029babc..b3ed318aa7 100644 --- a/ci-scripts/conf_files/gnb.band78.106prb.rfsim.phytest-dora.conf +++ b/ci-scripts/conf_files/gnb.band78.106prb.rfsim.phytest-dora.conf @@ -198,15 +198,6 @@ RUs = ( max_pdschReferenceSignalPower = -27; max_rxgain = 50; eNB_instances = [0]; - ## beamforming 1x2 matrix: 1 layer x 2 antennas - bf_weights = [0x00007fff, 0x0000]; - ## beamforming 1x4 matrix: 1 layer x 4 antennas - #bf_weights = [0x00007fff, 0x0000,0x0000, 0x0000]; - ## beamforming 2x2 matrix: - #bf_weights = [0x00007fff, 0x00000000, 0x00000000, 0x00007fff]; - ## beamforming 4x4 matrix: - #bf_weights = [0x00007fff, 0x0000, 0x0000, 0x0000, 0x00000000, 0x00007fff, 0x0000, 0x0000, 0x0000, 0x0000, 0x00007fff, 0x0000, 0x0000, 0x0000, 0x0000, 0x00007fff]; - sdr_addrs = "addr=192.168.10.2,second_addr=192.168.20.2"; } ); diff --git a/ci-scripts/conf_files/gnb.band78.106prb.usrpn300.phytest-dora.conf b/ci-scripts/conf_files/gnb.band78.106prb.usrpn300.phytest-dora.conf index 2bc2f78f31..4693bc2970 100644 --- a/ci-scripts/conf_files/gnb.band78.106prb.usrpn300.phytest-dora.conf +++ b/ci-scripts/conf_files/gnb.band78.106prb.usrpn300.phytest-dora.conf @@ -198,15 +198,6 @@ RUs = ( max_pdschReferenceSignalPower = -27; max_rxgain = 50; eNB_instances = [0]; - ## beamforming 1x2 matrix: 1 layer x 2 antennas - bf_weights = [0x00007fff, 0x0000]; - ## beamforming 1x4 matrix: 1 layer x 4 antennas - #bf_weights = [0x00007fff, 0x0000,0x0000, 0x0000]; - ## beamforming 2x2 matrix: - #bf_weights = [0x00007fff, 0x00000000, 0x00000000, 0x00007fff]; - ## beamforming 4x4 matrix: - #bf_weights = [0x00007fff, 0x0000, 0x0000, 0x0000, 0x00000000, 0x00007fff, 0x0000, 0x0000, 0x0000, 0x0000, 0x00007fff, 0x0000, 0x0000, 0x0000, 0x0000, 0x00007fff]; - sdr_addrs = "addr=192.168.10.2,second_addr=192.168.20.2"; } ); diff --git a/ci-scripts/conf_files/gnb.band78.162prb.usrpn300.phytest-dora.conf b/ci-scripts/conf_files/gnb.band78.162prb.usrpn300.phytest-dora.conf index 9c00c9f5a9..b677f617eb 100644 --- a/ci-scripts/conf_files/gnb.band78.162prb.usrpn300.phytest-dora.conf +++ b/ci-scripts/conf_files/gnb.band78.162prb.usrpn300.phytest-dora.conf @@ -191,7 +191,6 @@ RUs = ({ max_pdschReferenceSignalPower = -27; max_rxgain = 50; eNB_instances = [0]; - bf_weights = [0x00007fff, 0x0000]; sdr_addrs = "addr=192.168.10.2,second_addr=192.168.20.2"; }); diff --git a/ci-scripts/conf_files/gnb.band78.273prb.usrpn300.phytest-dora.conf b/ci-scripts/conf_files/gnb.band78.273prb.usrpn300.phytest-dora.conf index 35eaf7977b..e8ccac378b 100644 --- a/ci-scripts/conf_files/gnb.band78.273prb.usrpn300.phytest-dora.conf +++ b/ci-scripts/conf_files/gnb.band78.273prb.usrpn300.phytest-dora.conf @@ -193,7 +193,6 @@ RUs = ({ max_pdschReferenceSignalPower = -27; max_rxgain = 50; eNB_instances = [0]; - bf_weights = [0x00007fff, 0x0000]; sdr_addrs = "addr=192.168.10.2,second_addr=192.168.20.2"; }); diff --git a/ci-scripts/conf_files/gnb.nsa.band78.106prb.usrpn310.2x2.conf b/ci-scripts/conf_files/gnb.nsa.band78.106prb.usrpn310.2x2.conf index 7a0a7d133e..8c7ae493aa 100644 --- a/ci-scripts/conf_files/gnb.nsa.band78.106prb.usrpn310.2x2.conf +++ b/ci-scripts/conf_files/gnb.nsa.band78.106prb.usrpn310.2x2.conf @@ -211,7 +211,6 @@ RUs = ( max_pdschReferenceSignalPower = -27; max_rxgain = 75; eNB_instances = [0]; - bf_weights = [0x00007fff, 0x00007fff]; #clock_src = "external"; sf_extension = 0 sdr_addrs = "mgmt_addr=172.21.19.14,addr=192.168.10.2,second_addr=192.168.20.2,clock_source=internal,time_source=internal" diff --git a/ci-scripts/conf_files/gnb.sa.band261.u3.32prb.rfsim.conf b/ci-scripts/conf_files/gnb.sa.band261.u3.32prb.rfsim.conf index 604171a06c..2e707d9765 100644 --- a/ci-scripts/conf_files/gnb.sa.band261.u3.32prb.rfsim.conf +++ b/ci-scripts/conf_files/gnb.sa.band261.u3.32prb.rfsim.conf @@ -23,7 +23,8 @@ gNBs = sib1_tda = 15; min_rxtxtime = 6; - + beam_weights = [0]; // single SSB -> one analog beam + servingCellConfigCommon = ( { #spCellConfigCommon @@ -177,6 +178,9 @@ MACRLCs = ({ tr_n_preference = "local_RRC"; pusch_TargetSNRx10 = 200; pucch_TargetSNRx10 = 200; + set_analog_beamforming = 1; + beam_duration = 1; + beams_per_period = 1; }); L1s = ( diff --git a/ci-scripts/conf_files/gnb.sa.band66.106prb.rfsim.conf b/ci-scripts/conf_files/gnb.sa.band66.106prb.rfsim.conf index 9cf879999a..fed2aea45f 100644 --- a/ci-scripts/conf_files/gnb.sa.band66.106prb.rfsim.conf +++ b/ci-scripts/conf_files/gnb.sa.band66.106prb.rfsim.conf @@ -203,8 +203,6 @@ RUs = ( max_pdschReferenceSignalPower = -27; max_rxgain = 75; eNB_instances = [0]; - #beamforming 1x4 matrix: - bf_weights = [0x00007fff, 0x0000, 0x0000, 0x0000]; clock_src = "internal"; } ); diff --git a/ci-scripts/conf_files/gnb.sa.band66.ntn.25prb.rfsim.conf b/ci-scripts/conf_files/gnb.sa.band66.ntn.25prb.rfsim.conf index 9ffbf14a37..8731d00eb0 100644 --- a/ci-scripts/conf_files/gnb.sa.band66.ntn.25prb.rfsim.conf +++ b/ci-scripts/conf_files/gnb.sa.band66.ntn.25prb.rfsim.conf @@ -216,14 +216,6 @@ RUs = ( max_rxgain = 114; sf_extension = 0; eNB_instances = [0]; - ##beamforming 1x2 matrix: 1 layer x 2 antennas - bf_weights = [0x00007fff, 0x0000]; - ##beamforming 1x4 matrix: 1 layer x 4 antennas - #bf_weights = [0x00007fff, 0x0000,0x0000, 0x0000]; - ## beamforming 2x2 matrix: - # bf_weights = [0x00007fff, 0x00000000, 0x00000000, 0x00007fff]; - ## beamforming 4x4 matrix: - #bf_weights = [0x00007fff, 0x0000, 0x0000, 0x0000, 0x00000000, 0x00007fff, 0x0000, 0x0000, 0x0000, 0x0000, 0x00007fff, 0x0000, 0x0000, 0x0000, 0x0000, 0x00007fff]; sdr_addrs = "type=x300"; clock_src = "internal"; # if_freq = 3700000000L; diff --git a/ci-scripts/conf_files/gnb.sa.band66.u0.25prb.rfsim.conf b/ci-scripts/conf_files/gnb.sa.band66.u0.25prb.rfsim.conf index db0e87a2d9..0b3f3d58aa 100644 --- a/ci-scripts/conf_files/gnb.sa.band66.u0.25prb.rfsim.conf +++ b/ci-scripts/conf_files/gnb.sa.band66.u0.25prb.rfsim.conf @@ -203,14 +203,6 @@ RUs = ( max_rxgain = 114; sf_extension = 0; eNB_instances = [0]; - ##beamforming 1x2 matrix: 1 layer x 2 antennas - bf_weights = [0x00007fff, 0x0000]; - ##beamforming 1x4 matrix: 1 layer x 4 antennas - #bf_weights = [0x00007fff, 0x0000,0x0000, 0x0000]; - ## beamforming 2x2 matrix: - # bf_weights = [0x00007fff, 0x00000000, 0x00000000, 0x00007fff]; - ## beamforming 4x4 matrix: - #bf_weights = [0x00007fff, 0x0000, 0x0000, 0x0000, 0x00000000, 0x00007fff, 0x0000, 0x0000, 0x0000, 0x0000, 0x00007fff, 0x0000, 0x0000, 0x0000, 0x0000, 0x00007fff]; sdr_addrs = "type=x300"; clock_src = "internal"; # if_freq = 3700000000L; diff --git a/ci-scripts/conf_files/gnb.sa.band77.162prb.usrpn310.2x2.conf b/ci-scripts/conf_files/gnb.sa.band77.162prb.usrpn310.2x2.conf index a28259bda2..1612b12ebd 100644 --- a/ci-scripts/conf_files/gnb.sa.band77.162prb.usrpn310.2x2.conf +++ b/ci-scripts/conf_files/gnb.sa.band77.162prb.usrpn310.2x2.conf @@ -212,8 +212,6 @@ RUs = ( max_pdschReferenceSignalPower = -27; max_rxgain = 75; eNB_instances = [0]; - ##beamforming 1x2 matrix: 1 layer x 2 antennas - bf_weights = [0x00007fff, 0x0000]; #clock_src = "internal"; sdr_addrs = "addr=192.168.80.53, clock_source=internal,time_source=internal" diff --git a/ci-scripts/conf_files/gnb.sa.band77.273prb.fhi72.4x4-vvdn.conf b/ci-scripts/conf_files/gnb.sa.band77.273prb.fhi72.4x4-vvdn.conf index e048df534f..8c7ed99bda 100644 --- a/ci-scripts/conf_files/gnb.sa.band77.273prb.fhi72.4x4-vvdn.conf +++ b/ci-scripts/conf_files/gnb.sa.band77.273prb.fhi72.4x4-vvdn.conf @@ -220,8 +220,6 @@ RUs = ( eNB_instances = [0]; ru_thread_core = 5; sl_ahead = 5; - ##beamforming 1x2 matrix: 1 layer x 2 antennas - bf_weights = [0x00007fff, 0x0000,0x00007fff, 0x0000]; clock_src = "internal"; tr_preference = "raw_if4p5"; # important: activate FHI7.2 do_precoding = 0; # needs to match O-RU configuration diff --git a/ci-scripts/conf_files/gnb.sa.band77.273prb.usrpn310.2x2.conf b/ci-scripts/conf_files/gnb.sa.band77.273prb.usrpn310.2x2.conf index a62e9a36e5..f993f225c9 100644 --- a/ci-scripts/conf_files/gnb.sa.band77.273prb.usrpn310.2x2.conf +++ b/ci-scripts/conf_files/gnb.sa.band77.273prb.usrpn310.2x2.conf @@ -23,7 +23,6 @@ gNBs = ( pusch_AntennaPorts = 2; do_CSIRS = 1; do_SRS = 1; - ul_prbblacklist = "135,136,137,138" servingCellConfigCommon = ( { @@ -177,8 +176,8 @@ MACRLCs = ( num_cc = 1; tr_s_preference = "local_L1"; tr_n_preference = "local_RRC"; - pusch_TargetSNRx10 = 200; - pucch_TargetSNRx10 = 200; + pusch_TargetSNRx10 = 270; + pucch_TargetSNRx10 = 270; pusch_FailureThres = 1000; ulsch_max_frame_inactivity = 0; ul_max_mcs = 25; @@ -200,14 +199,12 @@ RUs = ( local_rf = "yes" nb_tx = 2; nb_rx = 2; - att_tx = 12; + att_tx = 15; att_rx = 0; bands = [77]; max_pdschReferenceSignalPower = -27; - max_rxgain = 72; + max_rxgain = 71; eNB_instances = [0]; - ##beamforming 1x2 matrix: 1 layer x 2 antennas - bf_weights = [0x00007fff, 0x0000]; #clock_src = "internal"; sdr_addrs = "addr=192.168.80.53,clock_source=internal,time_source=internal" } diff --git a/ci-scripts/conf_files/gnb.sa.band78.106prb.n310.7ds2u.conf b/ci-scripts/conf_files/gnb.sa.band78.106prb.n310.7ds2u.conf index 94601ba42f..e1ca5abff0 100644 --- a/ci-scripts/conf_files/gnb.sa.band78.106prb.n310.7ds2u.conf +++ b/ci-scripts/conf_files/gnb.sa.band78.106prb.n310.7ds2u.conf @@ -211,8 +211,6 @@ RUs = ( max_pdschReferenceSignalPower = -27; max_rxgain = 65; eNB_instances = [0]; - ##beamforming 1x2 matrix: 1 layer x 2 antennas - bf_weights = [0x00007fff, 0x0000]; sf_extension = 0 sdr_addrs = "addr=192.168.80.52,clock_source=internal,time_source=internal" } diff --git a/ci-scripts/conf_files/gnb.sa.band78.106prb.rfsim.conf b/ci-scripts/conf_files/gnb.sa.band78.106prb.rfsim.conf index b2d74a4017..ceb40487de 100644 --- a/ci-scripts/conf_files/gnb.sa.band78.106prb.rfsim.conf +++ b/ci-scripts/conf_files/gnb.sa.band78.106prb.rfsim.conf @@ -205,14 +205,6 @@ RUs = ( max_pdschReferenceSignalPower = -27; max_rxgain = 75; eNB_instances = [0]; - ##beamforming 1x2 matrix: 1 layer x 2 antennas - bf_weights = [0x00007fff, 0x0000]; - ##beamforming 1x4 matrix: 1 layer x 4 antennas - #bf_weights = [0x00007fff, 0x0000,0x0000, 0x0000]; - ## beamforming 2x2 matrix: - # bf_weights = [0x00007fff, 0x00000000, 0x00000000, 0x00007fff]; - ## beamforming 4x4 matrix: - #bf_weights = [0x00007fff, 0x0000, 0x0000, 0x0000, 0x00000000, 0x00007fff, 0x0000, 0x0000, 0x0000, 0x0000, 0x00007fff, 0x0000, 0x0000, 0x0000, 0x0000, 0x00007fff]; sf_extension = 0 sdr_addrs = "serial=XXXXXXX" } diff --git a/ci-scripts/conf_files/gnb.sa.band78.106prb.rfsim.neighbour.conf b/ci-scripts/conf_files/gnb.sa.band78.106prb.rfsim.neighbour.conf index 83dd899d13..8894867701 100644 --- a/ci-scripts/conf_files/gnb.sa.band78.106prb.rfsim.neighbour.conf +++ b/ci-scripts/conf_files/gnb.sa.band78.106prb.rfsim.neighbour.conf @@ -266,8 +266,6 @@ RUs = ({ max_pdschReferenceSignalPower = -27; max_rxgain = 114; eNB_instances = [0]; - #beamforming 1x4 matrix: - bf_weights = [0x00007fff, 0x0000, 0x0000, 0x0000]; clock_src = "internal"; }); diff --git a/ci-scripts/conf_files/gnb.sa.band78.106prb.rfsim.yaml b/ci-scripts/conf_files/gnb.sa.band78.106prb.rfsim.yaml index acd9f271d3..c4189ec9a7 100644 --- a/ci-scripts/conf_files/gnb.sa.band78.106prb.rfsim.yaml +++ b/ci-scripts/conf_files/gnb.sa.band78.106prb.rfsim.yaml @@ -166,14 +166,6 @@ RUs: max_pdschReferenceSignalPower: -27 max_rxgain: 75 eNB_instances: [0] - ##beamforming 1x2 matrix: 1 layer x 2 antennas - bf_weights: [0x00007fff, 0x0000] - ##beamforming 1x4 matrix: 1 layer x 4 antennas - #bf_weights = [0x00007fff, 0x0000,0x0000, 0x0000]; - ## beamforming 2x2 matrix: - # bf_weights = [0x00007fff, 0x00000000, 0x00000000, 0x00007fff]; - ## beamforming 4x4 matrix: - #bf_weights = [0x00007fff, 0x0000, 0x0000, 0x0000, 0x00000000, 0x00007fff, 0x0000, 0x0000, 0x0000, 0x0000, 0x00007fff, 0x0000, 0x0000, 0x0000, 0x0000, 0x00007fff]; sf_extension: 0 sdr_addrs: serial=XXXXXXX diff --git a/ci-scripts/conf_files/gnb.sa.band78.106prb.usrp310.2x2.conf b/ci-scripts/conf_files/gnb.sa.band78.106prb.usrp310.2x2.conf index 956011a297..dd9add6550 100644 --- a/ci-scripts/conf_files/gnb.sa.band78.106prb.usrp310.2x2.conf +++ b/ci-scripts/conf_files/gnb.sa.band78.106prb.usrp310.2x2.conf @@ -204,14 +204,6 @@ RUs = ( max_pdschReferenceSignalPower = -27; max_rxgain = 68; eNB_instances = [0]; - ##beamforming 1x2 matrix: 1 layer x 2 antennas - bf_weights = [0x00007fff, 0x0000]; - ##beamforming 1x4 matrix: 1 layer x 4 antennas - #bf_weights = [0x00007fff, 0x0000,0x0000, 0x0000]; - ## beamforming 2x2 matrix: - # bf_weights = [0x00007fff, 0x00000000, 0x00000000, 0x00007fff]; - ## beamforming 4x4 matrix: - #bf_weights = [0x00007fff, 0x0000, 0x0000, 0x0000, 0x00000000, 0x00007fff, 0x0000, 0x0000, 0x0000, 0x0000, 0x00007fff, 0x0000, 0x0000, 0x0000, 0x0000, 0x00007fff]; sf_extension = 0 sdr_addrs = "mgmt_addr=172.21.19.14,addr=192.168.10.2,second_addr=192.168.20.2,clock_source=internal,time_source=internal" } diff --git a/ci-scripts/conf_files/gnb.sa.band78.106prb.usrpb200.sc-fdma.conf b/ci-scripts/conf_files/gnb.sa.band78.106prb.usrpb200.sc-fdma.conf index dc5c30fe50..fc21991b67 100644 --- a/ci-scripts/conf_files/gnb.sa.band78.106prb.usrpb200.sc-fdma.conf +++ b/ci-scripts/conf_files/gnb.sa.band78.106prb.usrpb200.sc-fdma.conf @@ -175,7 +175,6 @@ MACRLCs = ( pusch_TargetSNRx10 = 200; pucch_TargetSNRx10 = 200; ul_prbblack_SNR_threshold = 10; - ul_max_mcs = 9; } ); @@ -200,8 +199,6 @@ RUs = ( max_pdschReferenceSignalPower = -27; max_rxgain = 114; eNB_instances = [0]; - #beamforming 1x4 matrix: - bf_weights = [0x00007fff, 0x0000, 0x0000, 0x0000]; clock_src = "internal"; } ); diff --git a/ci-scripts/conf_files/gnb.sa.band78.106prb.usrpn310.ddsuu-2x2.conf b/ci-scripts/conf_files/gnb.sa.band78.106prb.usrpn310.ddsuu-2x2.conf index 9af68e5b74..b41ea46c42 100644 --- a/ci-scripts/conf_files/gnb.sa.band78.106prb.usrpn310.ddsuu-2x2.conf +++ b/ci-scripts/conf_files/gnb.sa.band78.106prb.usrpn310.ddsuu-2x2.conf @@ -217,14 +217,6 @@ RUs = ( max_pdschReferenceSignalPower = -27; max_rxgain = 68; eNB_instances = [0]; - ##beamforming 1x2 matrix: 1 layer x 2 antennas - bf_weights = [0x00007fff, 0x0000]; - ##beamforming 1x4 matrix: 1 layer x 4 antennas - #bf_weights = [0x00007fff, 0x0000,0x0000, 0x0000]; - ## beamforming 2x2 matrix: - # bf_weights = [0x00007fff, 0x00000000, 0x00000000, 0x00007fff]; - ## beamforming 4x4 matrix: - #bf_weights = [0x00007fff, 0x0000, 0x0000, 0x0000, 0x00000000, 0x00007fff, 0x0000, 0x0000, 0x0000, 0x0000, 0x00007fff, 0x0000, 0x0000, 0x0000, 0x0000, 0x00007fff]; sf_extension = 0 sdr_addrs = "mgmt_addr=172.21.19.14,addr=192.168.10.2,second_addr=192.168.20.2,clock_source=internal,time_source=internal" sl_ahead = 5; diff --git a/ci-scripts/conf_files/gnb.sa.band78.162prb.usrpn310.2x2.conf b/ci-scripts/conf_files/gnb.sa.band78.162prb.usrpn310.2x2.conf index 7faa52c37e..eda8b0dad6 100644 --- a/ci-scripts/conf_files/gnb.sa.band78.162prb.usrpn310.2x2.conf +++ b/ci-scripts/conf_files/gnb.sa.band78.162prb.usrpn310.2x2.conf @@ -218,14 +218,6 @@ RUs = ( max_pdschReferenceSignalPower = -27; max_rxgain = 75; eNB_instances = [0]; - ##beamforming 1x2 matrix: 1 layer x 2 antennas - bf_weights = [0x00007fff, 0x0000]; - ##beamforming 1x4 matrix: 1 layer x 4 antennas - #bf_weights = [0x00007fff, 0x0000,0x0000, 0x0000]; - ## beamforming 2x2 matrix: - # bf_weights = [0x00007fff, 0x00000000, 0x00000000, 0x00007fff]; - ## beamforming 4x4 matrix: - #bf_weights = [0x00007fff, 0x0000, 0x0000, 0x0000, 0x00000000, 0x00007fff, 0x0000, 0x0000, 0x0000, 0x0000, 0x00007fff, 0x0000, 0x0000, 0x0000, 0x0000, 0x00007fff]; sf_extension = 0 sdr_addrs = "mgmt_addr=172.21.19.14,addr=192.168.10.2,second_addr=192.168.20.2,clock_source=internal,time_source=internal" } diff --git a/ci-scripts/conf_files/gnb.sa.band78.24prb.rfsim.conf b/ci-scripts/conf_files/gnb.sa.band78.24prb.rfsim.conf index b70ce97a85..fa12bd78c2 100644 --- a/ci-scripts/conf_files/gnb.sa.band78.24prb.rfsim.conf +++ b/ci-scripts/conf_files/gnb.sa.band78.24prb.rfsim.conf @@ -203,8 +203,6 @@ RUs = ( max_rxgain = 114; sf_extension = 0; eNB_instances = [0]; - #beamforming 1x4 matrix: - bf_weights = [0x00007fff, 0x0000, 0x0000, 0x0000]; clock_src = "internal"; } ); diff --git a/ci-scripts/conf_files/gnb.sa.band78.273prb.fhi72.4x4-benetel550.conf b/ci-scripts/conf_files/gnb.sa.band78.273prb.fhi72.4x4-benetel550.conf index 44f9eb99a1..139923e65a 100644 --- a/ci-scripts/conf_files/gnb.sa.band78.273prb.fhi72.4x4-benetel550.conf +++ b/ci-scripts/conf_files/gnb.sa.band78.273prb.fhi72.4x4-benetel550.conf @@ -227,8 +227,6 @@ RUs = ( eNB_instances = [0]; ru_thread_core = 5; sl_ahead = 10; - ##beamforming 1x2 matrix: 1 layer x 2 antennas - bf_weights = [0x00007fff, 0x0000,0x00007fff, 0x0000]; tr_preference = "raw_if4p5"; # important: activate FHI7.2 do_precoding = 0; # needs to match O-RU configuration } diff --git a/ci-scripts/conf_files/gnb.sa.band78.273prb.rfsim.2x2.conf b/ci-scripts/conf_files/gnb.sa.band78.273prb.rfsim.2x2.conf index f188434625..a722ef02bf 100644 --- a/ci-scripts/conf_files/gnb.sa.band78.273prb.rfsim.2x2.conf +++ b/ci-scripts/conf_files/gnb.sa.band78.273prb.rfsim.2x2.conf @@ -199,8 +199,6 @@ RUs = ( max_pdschReferenceSignalPower = -27; max_rxgain = 75; eNB_instances = [0]; - ##beamforming 1x2 matrix: 1 layer x 2 antennas - bf_weights = [0x00007fff, 0x0000]; #clock_src = "internal"; sdr_addrs = "mgmt_addr=192.168.10.2,addr=192.168.10.2,clock_source=internal,time_source=internal" } diff --git a/ci-scripts/conf_files/gnb.sa.band78.51prb.aw2s.ddsuu.2x2.conf b/ci-scripts/conf_files/gnb.sa.band78.51prb.aw2s.ddsuu.2x2.conf index a32aec583a..1c89d257d9 100644 --- a/ci-scripts/conf_files/gnb.sa.band78.51prb.aw2s.ddsuu.2x2.conf +++ b/ci-scripts/conf_files/gnb.sa.band78.51prb.aw2s.ddsuu.2x2.conf @@ -219,14 +219,6 @@ RUs = ( eNB_instances = [0]; bands = [78]; sl_ahead = 5; - ##beamforming 1x2 matrix: 1 layer x 2 antennas - bf_weights = [0x00007fff, 0x0000]; - ##beamforming 1x4 matrix: 1 layer x 4 antennas - #bf_weights = [0x00007fff, 0x0000,0x0000, 0x0000]; - ## beamforming 2x2 matrix: - # bf_weights = [0x00007fff, 0x00000000, 0x00000000, 0x00007fff]; - ## beamforming 4x4 matrix: - #bf_weights = [0x00007fff, 0x0000, 0x0000, 0x0000, 0x00000000, 0x00007fff, 0x0000, 0x0000, 0x0000, 0x0000, 0x00007fff, 0x0000, 0x0000, 0x0000, 0x0000, 0x00007fff]; } ); diff --git a/ci-scripts/conf_files/gnb.sa.band78.51prb.aw2s.ddsuu.conf b/ci-scripts/conf_files/gnb.sa.band78.51prb.aw2s.ddsuu.conf index 9ee7787eed..16a9ecfb93 100644 --- a/ci-scripts/conf_files/gnb.sa.band78.51prb.aw2s.ddsuu.conf +++ b/ci-scripts/conf_files/gnb.sa.band78.51prb.aw2s.ddsuu.conf @@ -219,14 +219,6 @@ RUs = ( eNB_instances = [0]; bands = [78]; sl_ahead = 5; - ##beamforming 1x2 matrix: 1 layer x 2 antennas - bf_weights = [0x00007fff, 0x0000]; - ##beamforming 1x4 matrix: 1 layer x 4 antennas - #bf_weights = [0x00007fff, 0x0000,0x0000, 0x0000]; - ## beamforming 2x2 matrix: - # bf_weights = [0x00007fff, 0x00000000, 0x00000000, 0x00007fff]; - ## beamforming 4x4 matrix: - #bf_weights = [0x00007fff, 0x0000, 0x0000, 0x0000, 0x00000000, 0x00007fff, 0x0000, 0x0000, 0x0000, 0x0000, 0x00007fff, 0x0000, 0x0000, 0x0000, 0x0000, 0x00007fff]; } ); diff --git a/ci-scripts/conf_files/gnb.sa.band78.51prb.usrpb200.conf b/ci-scripts/conf_files/gnb.sa.band78.51prb.usrpb200.conf index 4774fa1fad..c2ac243178 100644 --- a/ci-scripts/conf_files/gnb.sa.band78.51prb.usrpb200.conf +++ b/ci-scripts/conf_files/gnb.sa.band78.51prb.usrpb200.conf @@ -199,8 +199,6 @@ RUs = ( max_pdschReferenceSignalPower = -27; max_rxgain = 114; eNB_instances = [0]; - #beamforming 1x4 matrix: - bf_weights = [0x00007fff, 0x0000, 0x0000, 0x0000]; clock_src = "internal"; } ); diff --git a/ci-scripts/conf_files/untested/gNB_SA_n78_106PRB.2x2_usrpn310.conf b/ci-scripts/conf_files/untested/gNB_SA_n78_106PRB.2x2_usrpn310.conf index e48defc96e..43e11c6c40 100644 --- a/ci-scripts/conf_files/untested/gNB_SA_n78_106PRB.2x2_usrpn310.conf +++ b/ci-scripts/conf_files/untested/gNB_SA_n78_106PRB.2x2_usrpn310.conf @@ -217,15 +217,6 @@ RUs = ( max_pdschReferenceSignalPower = -27; max_rxgain = 75; eNB_instances = [0]; - ##beamforming 1x2 matrix: 1 layer x 2 antennas - bf_weights = [0x00007fff, 0x0000]; - ##beamforming 1x4 matrix: 1 layer x 4 antennas - #bf_weights = [0x00007fff, 0x0000,0x0000, 0x0000]; - ## beamforming 2x2 matrix: - # bf_weights = [0x00007fff, 0x00000000, 0x00000000, 0x00007fff]; - ## beamforming 4x4 matrix: - #bf_weights = [0x00007fff, 0x0000, 0x0000, 0x0000, 0x00000000, 0x00007fff, 0x0000, 0x0000, 0x0000, 0x0000, 0x00007fff, 0x0000, 0x0000, 0x0000, 0x0000, 0x00007fff]; - sdr_addrs = "mgmt_addr=172.21.19.14,addr=192.168.10.2,second_addr=192.168.20.2,clock_source=internal,time_source=internal" } ); diff --git a/ci-scripts/conf_files/untested/gNB_SA_n78_133PRB.2x2_usrpn310.conf b/ci-scripts/conf_files/untested/gNB_SA_n78_133PRB.2x2_usrpn310.conf index b949244ecc..6fe39879de 100644 --- a/ci-scripts/conf_files/untested/gNB_SA_n78_133PRB.2x2_usrpn310.conf +++ b/ci-scripts/conf_files/untested/gNB_SA_n78_133PRB.2x2_usrpn310.conf @@ -213,15 +213,6 @@ RUs = ( max_pdschReferenceSignalPower = -27; max_rxgain = 75; eNB_instances = [0]; - ##beamforming 1x2 matrix: 1 layer x 2 antennas - bf_weights = [0x00007fff, 0x0000]; - ##beamforming 1x4 matrix: 1 layer x 4 antennas - #bf_weights = [0x00007fff, 0x0000,0x0000, 0x0000]; - ## beamforming 2x2 matrix: - # bf_weights = [0x00007fff, 0x00000000, 0x00000000, 0x00007fff]; - ## beamforming 4x4 matrix: - #bf_weights = [0x00007fff, 0x0000, 0x0000, 0x0000, 0x00000000, 0x00007fff, 0x0000, 0x0000, 0x0000, 0x0000, 0x00007fff, 0x0000, 0x0000, 0x0000, 0x0000, 0x00007fff]; - sdr_addrs = "mgmt_addr=172.21.19.14,addr=192.168.10.2,second_addr=192.168.20.2,clock_source=internal,time_source=internal" } ); diff --git a/ci-scripts/conf_files/untested/gnb.band78.sa.fr1.106PRB.usrpn310.conf b/ci-scripts/conf_files/untested/gnb.band78.sa.fr1.106PRB.usrpn310.conf index 934603451d..4ffcf8fa3a 100644 --- a/ci-scripts/conf_files/untested/gnb.band78.sa.fr1.106PRB.usrpn310.conf +++ b/ci-scripts/conf_files/untested/gnb.band78.sa.fr1.106PRB.usrpn310.conf @@ -221,14 +221,6 @@ RUs = ( max_pdschReferenceSignalPower = -27; max_rxgain = 75; eNB_instances = [0]; - ##beamforming 1x2 matrix: 1 layer x 2 antennas - bf_weights = [0x00007fff, 0x0000]; - ##beamforming 1x4 matrix: 1 layer x 4 antennas - #bf_weights = [0x00007fff, 0x0000,0x0000, 0x0000]; - ## beamforming 2x2 matrix: - # bf_weights = [0x00007fff, 0x00000000, 0x00000000, 0x00007fff]; - ## beamforming 4x4 matrix: - #bf_weights = [0x00007fff, 0x0000, 0x0000, 0x0000, 0x00000000, 0x00007fff, 0x0000, 0x0000, 0x0000, 0x0000, 0x00007fff, 0x0000, 0x0000, 0x0000, 0x0000, 0x00007fff]; sf_extension = 0 sdr_addrs = "mgmt_addr=172.21.19.14,addr=192.168.10.2,second_addr=192.168.20.2,clock_source=internal,time_source=internal" } diff --git a/ci-scripts/conf_files/untested/gnb.sa.band66.fr1.106PRB.usrpn300.conf b/ci-scripts/conf_files/untested/gnb.sa.band66.fr1.106PRB.usrpn300.conf index 29edb27846..29cc65e17b 100644 --- a/ci-scripts/conf_files/untested/gnb.sa.band66.fr1.106PRB.usrpn300.conf +++ b/ci-scripts/conf_files/untested/gnb.sa.band66.fr1.106PRB.usrpn300.conf @@ -203,8 +203,6 @@ RUs = ( max_pdschReferenceSignalPower = -27; max_rxgain = 75; eNB_instances = [0]; - #beamforming 1x4 matrix: - bf_weights = [0x00007fff, 0x0000, 0x0000, 0x0000]; clock_src = "internal"; } ); diff --git a/ci-scripts/conf_files/untested/gnb.sa.band78.fr1.51PRB.usrpb210.conf b/ci-scripts/conf_files/untested/gnb.sa.band78.fr1.51PRB.usrpb210.conf index 32773d31f1..85bc18fa17 100644 --- a/ci-scripts/conf_files/untested/gnb.sa.band78.fr1.51PRB.usrpb210.conf +++ b/ci-scripts/conf_files/untested/gnb.sa.band78.fr1.51PRB.usrpb210.conf @@ -201,8 +201,6 @@ RUs = ( max_pdschReferenceSignalPower = -27; max_rxgain = 114; eNB_instances = [0]; - #beamforming 1x4 matrix: - bf_weights = [0x00007fff, 0x0000, 0x0000, 0x0000]; clock_src = "internal"; } ); diff --git a/ci-scripts/xml_files/container_sa_n310_2X2_100MHz_quectel.xml b/ci-scripts/xml_files/container_sa_n310_2X2_100MHz_quectel.xml index 6b7c8a92ec..214991e117 100644 --- a/ci-scripts/xml_files/container_sa_n310_2X2_100MHz_quectel.xml +++ b/ci-scripts/xml_files/container_sa_n310_2X2_100MHz_quectel.xml @@ -114,8 +114,8 @@ Iperf - iperf (DL/600Mbps/UDP)(30 sec)(single-ue profile) - -u -b 600M -t 30 -R -O 10 -l 9000 + iperf (DL/650Mbps/UDP)(30 sec)(single-ue profile) + -u -b 650M -t 30 -R -O 10 -l 9000 matix-cn5g up2 25 @@ -124,12 +124,12 @@ Iperf - iperf (UL/40Mbps/UDP)(30 sec)(single-ue profile) - -u -b 40M -t 30 -O 10 + iperf (UL/130Mbps/UDP)(30 sec)(single-ue profile) + -u -b 130M -t 30 -O 10 matix-cn5g up2 - 10 - 80 + 25 + 70 diff --git a/ci-scripts/xml_files/container_sa_sc_b200_quectel.xml b/ci-scripts/xml_files/container_sa_sc_b200_quectel.xml index 54df2fa1a4..d2bfaa02d4 100644 --- a/ci-scripts/xml_files/container_sa_sc_b200_quectel.xml +++ b/ci-scripts/xml_files/container_sa_sc_b200_quectel.xml @@ -150,8 +150,8 @@ Iperf - iperf (UL/6Mbps/UDP)(30 sec)(single-ue profile) - -u -b 6M -t 30 + iperf (UL/18Mbps/UDP)(30 sec) + -u -b 18M -t 30 idefix sabox-nepes 1 diff --git a/cmake_targets/autotests/test_case_list.xml b/cmake_targets/autotests/test_case_list.xml index 8ea193b816..5afe683055 100755 --- a/cmake_targets/autotests/test_case_list.xml +++ b/cmake_targets/autotests/test_case_list.xml @@ -387,7 +387,8 @@ (Test10: PUSCH Type B, 3 DMRS, 2 PTRS, 3 Interpolated Symbols), (Test11: 25 PRBs, 15 kHz SCS), (Test12: MCS 0, low SNR performance) - (Test13: MCS 28, 106 PRBs, Time shift 8) + (Test13: MCS 28, 106 PRBs, Time shift 8) + (Test14: SRS, SNR 40 dB) nr_ulsim -n100 -m9 -r106 -s5 -n100 -m16 -s10 @@ -401,8 +402,9 @@ -n100 -s5 -a4 -b8 -T 1,2 -U 1,3,1,1 -n100 -u0 -m0 -R25 -r25 -i 1,0 -n100 -m0 -S -0.6 -i 1,0 - -n100 -m 28 -R106 -r106 -t90 -s24 -S24 -d 8 - test1 test2 test3 test4 test5 test6 test7 test8 test9 test10 test11 test12 test13 + -n100 -m 28 -R106 -r106 -t90 -s24 -S24 -d 8 + -n100 -s40 -E 1 + test1 test2 test3 test4 test5 test6 test7 test8 test9 test10 test11 test12 test13 test14 PUSCH test OK segmentation fault|assertion|exiting|fatal 3 diff --git a/common/utils/nr/nr_common.h b/common/utils/nr/nr_common.h index 9087f335c5..94102a858f 100644 --- a/common/utils/nr/nr_common.h +++ b/common/utils/nr/nr_common.h @@ -39,6 +39,7 @@ #include "PHY/defs_common.h" #define NR_MAX_PDSCH_TBS 3824 +#define MAX_NUM_BEAM_PERIODS 4 #define MAX_BWP_SIZE 275 #define NR_MAX_NUM_BWP 4 #define NR_MAX_HARQ_PROCESSES 32 @@ -53,6 +54,7 @@ R(TYPE_P_RNTI_) /* Paging RNTI */ \ R(TYPE_SI_RNTI_) /* System information RNTI */ \ R(TYPE_RA_RNTI_) /* Random Access RNTI */ \ + R(TYPE_MSGB_RNTI_) /* Random Access MsgB RNTI */ \ R(TYPE_SP_CSI_RNTI_) /* Semipersistent CSI reporting on PUSCH */ \ R(TYPE_SFI_RNTI_) /* Slot Format Indication on the given cell */ \ R(TYPE_INT_RNTI_) /* Indication pre-emption in DL */ \ diff --git a/common/utils/oai_asn1.h b/common/utils/oai_asn1.h index 600aea1392..0f202bf699 100644 --- a/common/utils/oai_asn1.h +++ b/common/utils/oai_asn1.h @@ -154,17 +154,10 @@ static inline uint16_t BIT_STRING_to_uint16(const BIT_STRING_t *asn) { DevCheck ((asn->size > 0) && (asn->size <= 2), asn->size, 0, 0); - switch (asn->size) { - case 2: - result |= asn->buf[index++] << (8 - asn->bits_unused); - - case 1: - result |= asn->buf[index] >> asn->bits_unused; - break; - - default: - break; + if (asn->size == 2) { + result |= asn->buf[index++] << (8 - asn->bits_unused); } + result |= asn->buf[index] >> asn->bits_unused; return result; } diff --git a/doc/BUILD.md b/doc/BUILD.md index dc5b1361f2..4d629007b0 100644 --- a/doc/BUILD.md +++ b/doc/BUILD.md @@ -217,6 +217,30 @@ cmake-gui ../../.. ``` You can of course use all standard cmake/ninja/make commands in this directory. +## cmake presets + +CMake presets are common project configure options. See https://cmake.org/cmake/help/latest/manual/cmake-presets.7.html + +Configure presets: + + - `default`: Configure compilation with default options + - `tests`: Same as above but ENABLE_TESTS and SANITIZE_ADDRESS is ON + +Build presets: + + - `5gdefault`: Build the software for NR rfsimulator test + - `default`: same as 5gdefault + - `4gdefault`: Build the software for LTE rfsimulator test + - `tests`: build all unit tests + +To configure using configuration preset: + + cmake --preset + +To build using a build preset: + + cmake --build --preset + # Cross Compile If you want to use cross-compiler on x86 platform for aarch64 version, please refer the [cross-compile.md](./cross-compile.md) for more information. diff --git a/doc/FEATURE_SET.md b/doc/FEATURE_SET.md index 5469687ade..eb1027bb3e 100644 --- a/doc/FEATURE_SET.md +++ b/doc/FEATURE_SET.md @@ -105,10 +105,18 @@ These modes of operation are supported: - MAC <-> PHY data interface using FAPI P7 interface for BCH PDU, DCI PDU, PDSCH PDU - Scheduler procedures for SIB1 - Scheduler procedures for RA - - Contention Free RA procedure - - Contention Based RA procedure - - Msg3 can transfer uplink CCCH, DTCH or DCCH messages - - CBRA can be performed using MAC CE or C-RNTI + - 4-Step RA + - Contention Free RA procedure + - Contention Based RA procedure + - Msg3 can transfer uplink CCCH, DTCH or DCCH messages + - CBRA can be performed using MAC CE for C-RNTI + - Is not possible to use 2-Step RA and 4-Step RA at the same time + - 2-Step RA + - Contention Based RA procedure + - MsgA can transfer uplink CCCH, DTCH or DCCH messages + - CBRA can be performed using MAC CE for C-RNTI + - Is not possible to use 2-Step RA and 4-Step RA at the same time + - Fallback not supported - Scheduler procedures for CSI-RS - MAC downlink scheduler - phy-test scheduler (fixed allocation and usable also without UE) @@ -310,9 +318,15 @@ These modes of operation are supported: * Random access procedure (needs improvement, there is still not a clear separation between MAC and PHY) - Mapping SSBs to multiple ROs - Scheduling of PRACH - - Processing of RAR - - Transmission and re-transmission of Msg3 - - Msg4 and contention resolution + - 4-Step RA + - Processing of RAR + - Transmission and re-transmission of Msg3 + - Msg4 and contention resolution + - 2-Step RA + - Transmission of MsgA-PUSCH + - Reception of MsgB + - Processing of SuccessRAR + - Fallback not supported * DCI processing - format 10 (RA-RNTI, C-RNTI, SI-RNTI, TC-RNTI) - format 00 (C-RNTI, TC-RNTI) diff --git a/doc/README.md b/doc/README.md index 7f57a24eb0..ba7e5fbd12 100644 --- a/doc/README.md +++ b/doc/README.md @@ -115,3 +115,8 @@ The other SDRs (AW2S, LimeSDR, ...) have no READMEs. - [UnitTests.md](./UnitTests.md) explains the unit testing setup - [TESTBenches.md](./TESTBenches.md) lists the CI setup and links to pipelines + +# Developer tools + +- [formatting](../tools/formatting/README.md) is a clang-format error detection tool +- [iwyu](../tools/iwyu/README.md) is a tool to detect `#include` errors diff --git a/docker/Dockerfile.gNB.aerial.ubuntu22 b/docker/Dockerfile.gNB.aerial.ubuntu22 index 7440dfc9e8..592421c2b3 100644 --- a/docker/Dockerfile.gNB.aerial.ubuntu22 +++ b/docker/Dockerfile.gNB.aerial.ubuntu22 @@ -54,7 +54,8 @@ RUN /bin/sh oaienv && \ RUN /bin/sh oaienv && \ cd cmake_targets && \ mkdir -p log && \ - ./build_oai -w AERIAL --gNB --ninja + ./build_oai -c -w AERIAL --gNB --ninja \ + --cmake-opt -DCMAKE_C_FLAGS="-Werror" --cmake-opt -DCMAKE_CXX_FLAGS="-Werror" #start from scratch for target executable diff --git a/executables/nr-gnb.c b/executables/nr-gnb.c index 0e9b85eed9..c1229a07e3 100644 --- a/executables/nr-gnb.c +++ b/executables/nr-gnb.c @@ -128,7 +128,7 @@ static void tx_func(processingData_L1tx_t *info) // At this point, MAC scheduler just ran, including scheduling // PRACH/PUCCH/PUSCH, so trigger RX chain processing - LOG_D(NR_PHY, "%s() trigger RX for %d.%d\n", __func__, frame_rx, slot_rx); + LOG_D(NR_PHY, "Trigger RX for %d.%d\n", frame_rx, slot_rx); notifiedFIFO_elt_t *res = newNotifiedFIFO_elt(sizeof(processingData_L1_t), 0, &gNB->resp_L1, NULL); processingData_L1_t *syncMsg = NotifiedFifoData(res); syncMsg->gNB = gNB; @@ -229,15 +229,17 @@ static void rx_func(processingData_L1_t *info) if (gNB->phase_comp) { //apply the rx signal rotation here int soffset = (slot_rx & 3) * gNB->frame_parms.symbols_per_slot * gNB->frame_parms.ofdm_symbol_size; - for (int aa = 0; aa < gNB->frame_parms.nb_antennas_rx; aa++) { - apply_nr_rotation_RX(&gNB->frame_parms, - gNB->common_vars.rxdataF[aa], - gNB->frame_parms.symbol_rotation[1], - slot_rx, - gNB->frame_parms.N_RB_UL, - soffset, - 0, - gNB->frame_parms.Ncp == EXTENDED ? 12 : 14); + for (int bb = 0; bb < gNB->common_vars.num_beams_period; bb++) { + for (int aa = 0; aa < gNB->frame_parms.nb_antennas_rx; aa++) { + apply_nr_rotation_RX(&gNB->frame_parms, + gNB->common_vars.rxdataF[bb][aa], + gNB->frame_parms.symbol_rotation[1], + slot_rx, + gNB->frame_parms.N_RB_UL, + soffset, + 0, + gNB->frame_parms.Ncp == EXTENDED ? 12 : 14); + } } } phy_procedures_gNB_uespec_RX(gNB, frame_rx, slot_rx); @@ -417,17 +419,14 @@ void init_eNB_afterRU(void) { LOG_I(PHY,"gNB->num_RU:%d\n", gNB->num_RU); for (ru_id=0,aa=0; ru_idnum_RU; ru_id++) { - AssertFatal(gNB->RU_list[ru_id]->common.rxdataF!=NULL, - "RU %d : common.rxdataF is NULL\n", - gNB->RU_list[ru_id]->idx); - AssertFatal(gNB->RU_list[ru_id]->prach_rxsigF!=NULL, - "RU %d : prach_rxsigF is NULL\n", - gNB->RU_list[ru_id]->idx); + AssertFatal(gNB->RU_list[ru_id]->common.rxdataF != NULL, "RU %d : common.rxdataF is NULL\n", gNB->RU_list[ru_id]->idx); + AssertFatal(gNB->RU_list[ru_id]->prach_rxsigF != NULL, "RU %d : prach_rxsigF is NULL\n", gNB->RU_list[ru_id]->idx); for (i=0; iRU_list[ru_id]->nb_rx; aa++,i++) { LOG_I(PHY,"Attaching RU %d antenna %d to gNB antenna %d\n",gNB->RU_list[ru_id]->idx,i,aa); - gNB->prach_vars.rxsigF[aa] = gNB->RU_list[ru_id]->prach_rxsigF[0][i]; - gNB->common_vars.rxdataF[aa] = (c16_t *)gNB->RU_list[ru_id]->common.rxdataF[i]; + gNB->prach_vars.rxsigF[aa] = gNB->RU_list[ru_id]->prach_rxsigF[0][i]; + // TODO hardcoded beam to 0, still need to understand how to handle this properly + gNB->common_vars.rxdataF[0][aa] = (c16_t *)gNB->RU_list[ru_id]->common.rxdataF[i]; } } diff --git a/executables/nr-ru.c b/executables/nr-ru.c index 45a1aa024b..0a7e28431f 100644 --- a/executables/nr-ru.c +++ b/executables/nr-ru.c @@ -58,8 +58,6 @@ static int DEFBANDS[] = {7}; static int DEFENBS[] = {0}; static int DEFBFW[] = {0x00007fff}; static int DEFRUTPCORES[] = {-1,-1,-1,-1}; -//static int DEFNRBANDS[] = {7}; -//static int DEFGNBS[] = {0}; #include "ENB_APP/enb_paramdef.h" #include "GNB_APP/gnb_paramdef.h" @@ -540,9 +538,11 @@ void fh_if4p5_north_asynch_in(RU_t *ru,int *frame,int *slot) { VCD_SIGNAL_DUMPER_DUMP_VARIABLE_BY_NAME( VCD_SIGNAL_DUMPER_VARIABLES_TTI_NUMBER_TX0_RU, slot_tx ); } - if (ru->feptx_ofdm) ru->feptx_ofdm(ru,frame_tx,slot_tx); + if (ru->feptx_ofdm) + ru->feptx_ofdm(ru, frame_tx, slot_tx); - if (ru->fh_south_out) ru->fh_south_out(ru,frame_tx,slot_tx,proc->timestamp_tx); + if (ru->fh_south_out) + ru->fh_south_out(ru, frame_tx, slot_tx, proc->timestamp_tx); } void fh_if5_north_out(RU_t *ru) { @@ -717,7 +717,7 @@ static radio_tx_gpio_flag_t get_gpio_flags(RU_t *ru, int slot) if (ru->common.beam_id) { int prev_slot = (slot - 1 + fp->slots_per_frame) % fp->slots_per_frame; - const uint8_t *beam_ids = ru->common.beam_id[0]; + const int *beam_ids = ru->common.beam_id[0]; int prev_beam = beam_ids[prev_slot * fp->symbols_per_slot]; int beam = beam_ids[slot * fp->symbols_per_slot]; if (prev_beam != beam) { @@ -748,12 +748,12 @@ static radio_tx_gpio_flag_t get_gpio_flags(RU_t *ru, int slot) return flags_gpio; } -void tx_rf(RU_t *ru,int frame,int slot, uint64_t timestamp) { +void tx_rf(RU_t *ru, int frame,int slot, uint64_t timestamp) +{ RU_proc_t *proc = &ru->proc; NR_DL_FRAME_PARMS *fp = ru->nr_frame_parms; nfapi_nr_config_request_scf_t *cfg = &ru->config; void *txp[ru->nb_tx]; - unsigned int txs; int i; T(T_ENB_PHY_OUTPUT_SIGNAL, T_INT(0), @@ -809,7 +809,7 @@ void tx_rf(RU_t *ru,int frame,int slot, uint64_t timestamp) { flags_burst = proc->first_tx == 1 ? TX_BURST_START : TX_BURST_MIDDLE; } - if (fp->freq_range == FR2) + if (ru->openair0_cfg.gpio_controller != RU_GPIO_CONTROL_NONE) flags_gpio = get_gpio_flags(ru, slot); const int flags = flags_burst | (flags_gpio << 4); @@ -827,8 +827,11 @@ void tx_rf(RU_t *ru,int frame,int slot, uint64_t timestamp) { VCD_SIGNAL_DUMPER_DUMP_VARIABLE_BY_NAME(VCD_SIGNAL_DUMPER_VARIABLES_TRX_TST, (timestamp + ru->ts_offset) & 0xffffffff); VCD_SIGNAL_DUMPER_DUMP_FUNCTION_BY_NAME(VCD_SIGNAL_DUMPER_FUNCTIONS_TRX_WRITE, 1); // prepare tx buffer pointers - txs = ru->rfdevice - .trx_write_func(&ru->rfdevice, timestamp + ru->ts_offset - sf_extension, txp, siglen + sf_extension, ru->nb_tx, flags); + uint32_t txs = ru->rfdevice.trx_write_func(&ru->rfdevice, + timestamp + ru->ts_offset - sf_extension, + txp, + siglen + sf_extension, + ru->nb_tx, flags); LOG_D(PHY, "[TXPATH] RU %d aa %d tx_rf, writing to TS %llu, %d.%d, unwrapped_frame %d, slot %d, flags %d, siglen+sf_extension %d, " "returned %d, E %f\n", @@ -1031,7 +1034,8 @@ void *ru_stats_thread(void *param) { return(NULL); } -void ru_tx_func(void *param) { +void ru_tx_func(void *param) +{ processingData_RU_t *info = (processingData_RU_t *) param; RU_t *ru = info->ru; NR_DL_FRAME_PARMS *fp = ru->nr_frame_parms; @@ -1039,7 +1043,7 @@ void ru_tx_func(void *param) { int slot_tx = info->slot_tx; int print_frame = 8; char filename[40]; - + int cumul_samples = fp->get_samples_per_slot(0, fp); int i = 1; for (; i < fp->slots_per_subframe / 2; i++) @@ -1050,10 +1054,12 @@ void ru_tx_func(void *param) { int rt_prof_idx = absslot_rx % RT_PROF_DEPTH; clock_gettime(CLOCK_MONOTONIC,&ru->rt_ru_profiling.start_RU_TX[rt_prof_idx]); // do TX front-end processing if needed (precoding and/or IDFTs) - if (ru->feptx_prec) ru->feptx_prec(ru,frame_tx,slot_tx); + if (ru->feptx_prec) + ru->feptx_prec(ru,frame_tx,slot_tx); // do OFDM with/without TX front-end processing if needed - if ((ru->fh_north_asynch_in == NULL) && (ru->feptx_ofdm)) ru->feptx_ofdm(ru,frame_tx,slot_tx); + if ((ru->fh_north_asynch_in == NULL) && (ru->feptx_ofdm)) + ru->feptx_ofdm(ru, frame_tx, slot_tx); if(!emulate_rf) { // do outgoing fronthaul (south) if needed @@ -1100,7 +1106,8 @@ void ru_tx_func(void *param) { LOG_D(PHY,"rt_prof_idx %d : RU_TX time %d\n",rt_prof_idx,(int)(1e9 * (t1->tv_sec - t0->tv_sec) + (t1->tv_nsec-t0->tv_nsec))); } -void *ru_thread( void *param ) { +void *ru_thread(void *param) +{ static int ru_thread_status; RU_t *ru = (RU_t *)param; RU_proc_t *proc = &ru->proc; @@ -1333,11 +1340,11 @@ void *ru_thread( void *param ) { // Do PRACH RU processing int prach_id = find_nr_prach_ru(ru, proc->frame_rx, proc->tti_rx, SEARCH_EXIST); - if (prach_id>=0) { + if (prach_id >= 0) { VCD_SIGNAL_DUMPER_DUMP_FUNCTION_BY_NAME( VCD_SIGNAL_DUMPER_FUNCTIONS_PHY_RU_PRACH_RX, 1 ); T(T_GNB_PHY_PRACH_INPUT_SIGNAL, T_INT(proc->frame_rx), T_INT(proc->tti_rx), T_INT(0), - T_BUFFER(&ru->common.rxdata[0][fp->get_samples_slot_timestamp(proc->tti_rx-1,fp,0)]/*-ru->N_TA_offset*/, fp->get_samples_per_slot(proc->tti_rx,fp)*4*2)); + T_BUFFER(&ru->common.rxdata[0][fp->get_samples_slot_timestamp(proc->tti_rx-1,fp,0)]/*-ru->N_TA_offset*/, fp->get_samples_per_slot(proc->tti_rx,fp)*4*2)); int N_dur = get_nr_prach_duration(ru->prach_list[prach_id].fmt); for (int prach_oc = 0; prach_ocprach_list[prach_id].num_prach_ocas; prach_oc++) { @@ -1348,11 +1355,12 @@ void *ru_thread( void *param ) { ru->prach_list[prach_id].numRA, prachStartSymbol, prach_oc, - proc->frame_rx,proc->tti_rx); + proc->frame_rx, + proc->tti_rx); } clock_gettime(CLOCK_MONOTONIC,&ru->rt_ru_profiling.return_RU_prachrx[rt_prof_idx]); free_nr_ru_prach_entry(ru,prach_id); - VCD_SIGNAL_DUMPER_DUMP_FUNCTION_BY_NAME( VCD_SIGNAL_DUMPER_FUNCTIONS_PHY_RU_PRACH_RX, 0 ); + VCD_SIGNAL_DUMPER_DUMP_FUNCTION_BY_NAME(VCD_SIGNAL_DUMPER_FUNCTIONS_PHY_RU_PRACH_RX, 0); } // end if (prach_id > 0) } // end if (ru->feprx) else { @@ -1602,38 +1610,8 @@ void configure_rru(void *ruu, void *arg) nr_phy_init_RU(ru); } -/* -void init_precoding_weights(PHY_VARS_gNB *gNB) { - - int layer,ru_id,aa,re,ue,tb; - LTE_DL_FRAME_PARMS *fp=&gNB->frame_parms; - RU_t *ru; - LTE_gNB_DLSCH_t *dlsch; - - // init precoding weigths - for (ue=0;uedlsch[ue][tb]; - for (layer=0; layer<4; layer++) { - int nb_tx=0; - for (ru_id=0;ru_idnb_tx; - } - dlsch->ue_spec_bf_weights[layer] = (int32_t**)malloc16(nb_tx*sizeof(int32_t*)); - - for (aa=0; aaue_spec_bf_weights[layer][aa] = (int32_t *)malloc16(fp->ofdm_symbol_size*sizeof(int32_t)); - for (re=0;reofdm_symbol_size; re++) { - dlsch->ue_spec_bf_weights[layer][aa][re] = 0x00007fff; - } - } - } - } - } -}*/ - -void set_function_spec_param(RU_t *ru) { +void set_function_spec_param(RU_t *ru) +{ switch (ru->if_south) { case LOCAL_RF: // this is an RU with integrated RF (RRU, gNB) reset_meas(&ru->rx_fhaul); @@ -1782,20 +1760,19 @@ void init_NR_RU(configmodule_interface_t *cfg, char *rf_config_file) } } - gNB_RC = RC.gNB[0]; - gNB0 = ru->gNB_list[0]; - fp = ru->nr_frame_parms; + gNB_RC = RC.gNB[0]; + gNB0 = ru->gNB_list[0]; + fp = ru->nr_frame_parms; LOG_D(PHY, "RU FUnction:%d ru->if_south:%d\n", ru->function, ru->if_south); if (gNB0) { if ((ru->function != NGFI_RRU_IF5) && (ru->function != NGFI_RRU_IF4p5)) - AssertFatal(gNB0!=NULL,"gNB0 is null!\n"); + AssertFatal(gNB0, "gNB0 is null!\n"); if (gNB0 && gNB_RC) { - LOG_I(PHY,"Copying frame parms from gNB in RC to gNB %d in ru %d and frame_parms in ru\n",gNB0->Mod_id,ru->idx); - memset((void *)fp, 0, sizeof(NR_DL_FRAME_PARMS)); - memcpy((void *)fp,&gNB_RC->frame_parms,sizeof(NR_DL_FRAME_PARMS)); - memcpy((void *)&gNB0->frame_parms,(void *)&gNB_RC->frame_parms,sizeof(NR_DL_FRAME_PARMS)); + LOG_I(PHY,"Copying frame parms from gNB in RC to gNB %d in ru %d and frame_parms in ru\n", gNB0->Mod_id, ru->idx); + memcpy((void *)fp, &gNB_RC->frame_parms, sizeof(NR_DL_FRAME_PARMS)); + memcpy((void *)&gNB0->frame_parms, (void *)&gNB_RC->frame_parms, sizeof(NR_DL_FRAME_PARMS)); // attach all RU to all gNBs in its list/ LOG_D(PHY,"ru->num_gNB:%d gNB0->num_RU:%d\n", ru->num_gNB, gNB0->num_RU); @@ -1851,39 +1828,26 @@ void stop_RU(int nb_ru) { static void NRRCconfig_RU(configmodule_interface_t *cfg) { paramdef_t RUParams[] = RUPARAMS_DESC; - paramlist_def_t RUParamList = {CONFIG_STRING_RU_LIST,NULL,0}; + paramlist_def_t RUParamList = {CONFIG_STRING_RU_LIST, NULL, 0}; config_getlist(cfg, &RUParamList, RUParams, sizeofArray(RUParams), NULL); - paramdef_t GNBSParams[] = GNBSPARAMS_DESC; - paramdef_t GNBParams[] = GNBPARAMS_DESC; - paramlist_def_t GNBParamList = {GNB_CONFIG_STRING_GNB_LIST, NULL, 0}; - config_get(cfg, GNBSParams, sizeofArray(GNBSParams), NULL); - int num_gnbs = GNBSParams[GNB_ACTIVE_GNBS_IDX].numelt; - AssertFatal(num_gnbs > 0, "Failed to parse config file no gnbs %s \n", GNB_CONFIG_STRING_ACTIVE_GNBS); - config_getlist(cfg, &GNBParamList, GNBParams, sizeofArray(GNBParams), NULL); - int N1 = *GNBParamList.paramarray[0][GNB_PDSCH_ANTENNAPORTS_N1_IDX].iptr; - int N2 = *GNBParamList.paramarray[0][GNB_PDSCH_ANTENNAPORTS_N2_IDX].iptr; - int XP = *GNBParamList.paramarray[0][GNB_PDSCH_ANTENNAPORTS_XP_IDX].iptr; - int num_logical_antennas = N1 * N2 * XP; - if (RUParamList.numelt > 0) { RC.ru = (RU_t **)malloc(RC.nb_RU*sizeof(RU_t *)); RC.ru_mask = (1 << NB_RU) - 1; printf("Set RU mask to %lx\n",RC.ru_mask); for (int j = 0; j < RC.nb_RU; j++) { - RC.ru[j] = (RU_t *)malloc(sizeof(RU_t)); - memset((void *)RC.ru[j],0,sizeof(RU_t)); - RC.ru[j]->idx = j; - RC.ru[j]->nr_frame_parms = (NR_DL_FRAME_PARMS *)malloc(sizeof(NR_DL_FRAME_PARMS)); - RC.ru[j]->frame_parms = (LTE_DL_FRAME_PARMS *)malloc(sizeof(LTE_DL_FRAME_PARMS)); + RC.ru[j] = calloc(1, sizeof(*RC.ru[j])); + RC.ru[j]->idx = j; + RC.ru[j]->nr_frame_parms = calloc(1, sizeof(*RC.ru[j]->nr_frame_parms)); + RC.ru[j]->frame_parms = calloc(1, sizeof(*RC.ru[j]->frame_parms)); printf("Creating RC.ru[%d]:%p\n", j, RC.ru[j]); - RC.ru[j]->if_timing = synch_to_ext_device; + RC.ru[j]->if_timing = synch_to_ext_device; if (RC.nb_nr_L1_inst > 0) - RC.ru[j]->num_gNB = RUParamList.paramarray[j][RU_ENB_LIST_IDX].numelt; + RC.ru[j]->num_gNB = RUParamList.paramarray[j][RU_ENB_LIST_IDX].numelt; else - RC.ru[j]->num_gNB = 0; + RC.ru[j]->num_gNB = 0; for (int i = 0; i < RC.ru[j]->num_gNB; i++) RC.ru[j]->gNB_list[i] = RC.gNB[RUParamList.paramarray[j][RU_ENB_LIST_IDX].iptr[i]]; @@ -1904,10 +1868,8 @@ static void NRRCconfig_RU(configmodule_interface_t *cfg) "bad GPIO controller in configuration file: '%s'\n", *(RUParamList.paramarray[j][RU_GPIO_CONTROL].strptr)); } - } else { - RC.ru[j]->openair0_cfg.gpio_controller = RU_GPIO_CONTROL_GENERIC; - LOG_I(PHY, "RU GPIO control set as 'generic'\n"); - } + } else + RC.ru[j]->openair0_cfg.gpio_controller = RU_GPIO_CONTROL_NONE; if (config_isparamset(RUParamList.paramarray[j], RU_TX_SUBDEV)) { RC.ru[j]->openair0_cfg.tx_subdev = strdup(*(RUParamList.paramarray[j][RU_TX_SUBDEV].strptr)); @@ -2032,14 +1994,11 @@ static void NRRCconfig_RU(configmodule_interface_t *cfg) } /* strcmp(local_rf, "yes") != 0 */ RC.ru[j]->nb_tx = *(RUParamList.paramarray[j][RU_NB_TX_IDX].uptr); - AssertFatal(RC.ru[j]->nb_tx >= num_logical_antennas, - "Number of logical antenna ports (set in config file with pdsch_AntennaPorts) cannot be larger than physical antennas (nb_tx)\n"); RC.ru[j]->nb_rx = *(RUParamList.paramarray[j][RU_NB_RX_IDX].uptr); RC.ru[j]->att_tx = *(RUParamList.paramarray[j][RU_ATT_TX_IDX].uptr); RC.ru[j]->att_rx = *(RUParamList.paramarray[j][RU_ATT_RX_IDX].uptr); RC.ru[j]->if_frequency = *(RUParamList.paramarray[j][RU_IF_FREQUENCY].u64ptr); RC.ru[j]->if_freq_offset = *(RUParamList.paramarray[j][RU_IF_FREQ_OFFSET].iptr); - RC.ru[j]->do_precoding = *(RUParamList.paramarray[j][RU_DO_PRECODING].iptr); RC.ru[j]->sl_ahead = *(RUParamList.paramarray[j][RU_SL_AHEAD].iptr); RC.ru[j]->num_bands = RUParamList.paramarray[j][RU_BAND_LIST_IDX].numelt; for (int i = 0; i < RC.ru[j]->num_bands; i++) @@ -2057,15 +2016,6 @@ static void NRRCconfig_RU(configmodule_interface_t *cfg) AssertFatal(RC.ru[j]->num_tpcores <= RUParamList.paramarray[j][RU_TP_CORES].numelt, "Number of TP cores should be <=16\n"); for (int i = 0; i < RC.ru[j]->num_tpcores; i++) RC.ru[j]->tpcores[i] = RUParamList.paramarray[j][RU_TP_CORES].iptr[i]; - if (config_isparamset(RUParamList.paramarray[j], RU_BF_WEIGHTS_LIST_IDX)) { - RC.ru[j]->nb_bfw = RUParamList.paramarray[j][RU_BF_WEIGHTS_LIST_IDX].numelt; - - for (int i = 0; i < RC.ru[j]->num_gNB; i++) { - RC.ru[j]->bw_list[i] = (int32_t *)malloc16_clear((RC.ru[j]->nb_bfw)*sizeof(int32_t)); - for (int b = 0; b < RC.ru[j]->nb_bfw; b++) - RC.ru[j]->bw_list[i][b] = RUParamList.paramarray[j][RU_BF_WEIGHTS_LIST_IDX].iptr[b]; - } - } }// j=0..num_rus } else { RC.nb_RU = 0; diff --git a/nfapi/oai_integration/aerial/CMakeLists.txt b/nfapi/oai_integration/aerial/CMakeLists.txt index 4c02ab01e9..80d4cd77c6 100644 --- a/nfapi/oai_integration/aerial/CMakeLists.txt +++ b/nfapi/oai_integration/aerial/CMakeLists.txt @@ -19,7 +19,7 @@ if (OAI_AERIAL) else () message(STATUS " nvlog library found in ${NVLOG_LIB}") endif () - target_compile_definitions(aerial_lib PUBLIC ENABLE_L2_SLT_RSP ENABLE_AERIAL) + target_compile_definitions(aerial_lib PUBLIC ENABLE_L2_SLT_RSP) target_link_libraries(aerial_lib PRIVATE asn1_lte_rrc_hdrs asn1_nr_rrc_hdrs) target_link_libraries(aerial_lib PRIVATE nr_fapi_p5) target_link_libraries(aerial_lib PRIVATE "${NVLOG_LIB}" "${NVIPC_LIB}") diff --git a/nfapi/oai_integration/aerial/fapi_nvIPC.c b/nfapi/oai_integration/aerial/fapi_nvIPC.c index 46a28c440e..ca8cd16381 100644 --- a/nfapi/oai_integration/aerial/fapi_nvIPC.c +++ b/nfapi/oai_integration/aerial/fapi_nvIPC.c @@ -29,7 +29,7 @@ * \note * \warning */ -#ifdef ENABLE_AERIAL + #define _GNU_SOURCE #include #include @@ -79,39 +79,8 @@ static int ipc_handle_rx_msg(nv_ipc_t *ipc, nv_ipc_msg_t *msg) return -1; } - char *p_cpu_data = NULL; - if (msg->data_buf != NULL) { - int gpu; - if (msg->data_pool == NV_IPC_MEMPOOL_CUDA_DATA) { - gpu = 1; - } else { - gpu = 0; - } - -#ifdef NVIPC_CUDA_ENABLE - // Test CUDA: call CUDA functions to change all string to lower case - test_cuda_to_lower_case(test_cuda_device_id, msg->data_buf, TEST_DATA_BUF_LEN, gpu); -#endif - - if (gpu) { - p_cpu_data = cpu_buf_recv; - memset(cpu_buf_recv, 0, RECV_BUF_LEN); - ipc->cuda_memcpy_to_host(ipc, p_cpu_data, msg->data_buf, RECV_BUF_LEN); - } else { - p_cpu_data = msg->data_buf; - } - } - - int messageBufLen = msg->msg_len; - int dataBufLen = msg->data_len; - uint8_t msgbuf[messageBufLen]; - uint8_t databuf[dataBufLen]; - memcpy(msgbuf, msg->msg_buf, messageBufLen); - memcpy(databuf, msg->data_buf, dataBufLen); - uint8_t *pReadPackedMessage = msgbuf; - uint8_t *pReadData = databuf; - uint8_t *end = msgbuf + messageBufLen; - uint8_t *data_end = databuf + dataBufLen; + uint8_t *pReadPackedMessage = msg->msg_buf; + uint8_t *end = msg->msg_buf + msg->msg_len; // unpack FAPI messages and handle them if (vnf_config != 0) { @@ -209,6 +178,9 @@ static int ipc_handle_rx_msg(nv_ipc_t *ipc, nv_ipc_msg_t *msg) } case NFAPI_NR_PHY_MSG_TYPE_RX_DATA_INDICATION: { + uint8_t *pReadData = msg->data_buf; + int dataBufLen = msg->data_len; + uint8_t *data_end = msg->data_buf + dataBufLen; nfapi_nr_rx_data_indication_t ind; ind.header.message_id = fapi_msg.message_id; ind.header.message_length = fapi_msg.message_length; @@ -652,11 +624,7 @@ int load_hard_code_config(nv_ipc_config_t *config, int module_type, nv_ipc_trans return -1; } -#ifdef NVIPC_CUDA_ENABLE - int test_cuda_device_id = get_cuda_device_id(); -#else int test_cuda_device_id = -1; -#endif LOG_D(NFAPI_VNF,"CUDA device ID configured : %d \n", test_cuda_device_id); config->transport_config.shm.cuda_device_id = test_cuda_device_id; if (test_cuda_device_id >= 0) { @@ -686,4 +654,3 @@ int nvIPC_Init(nvipc_params_t nvipc_params_s) aerial_pnf_nr_connection_indication_cb(vnf_config, 1); return 0; } -#endif diff --git a/nfapi/oai_integration/aerial/fapi_nvIPC.h b/nfapi/oai_integration/aerial/fapi_nvIPC.h index 6910370495..3d88937f60 100644 --- a/nfapi/oai_integration/aerial/fapi_nvIPC.h +++ b/nfapi/oai_integration/aerial/fapi_nvIPC.h @@ -29,7 +29,6 @@ * \note * \warning */ -#ifdef ENABLE_AERIAL #ifndef OPENAIRINTERFACE_FAPI_NVIPC_H #define OPENAIRINTERFACE_FAPI_NVIPC_H @@ -37,9 +36,10 @@ #include "nv_ipc_utils.h" #include "nvlog.h" #include "nfapi/open-nFAPI/vnf/public_inc/nfapi_vnf_interface.h" -#include "openair1/PHY/defs_gNB.h" #include "debug.h" +#include "openair2/LAYER2/NR_MAC_gNB/nr_mac_gNB.h" + typedef struct { uint8_t num_msg; uint8_t opaque_handle; @@ -55,7 +55,6 @@ int aerial_send_P7_msg_with_data(void *packedBuf, uint32_t dataLength, nfapi_p7_message_header_t *header); void set_config(nfapi_vnf_config_t *conf); -int nvIPC_Init(nvipc_params_t); +int nvIPC_Init(nvipc_params_t nvipc_params_s); #endif // OPENAIRINTERFACE_FAPI_NVIPC_H -#endif diff --git a/nfapi/oai_integration/aerial/fapi_vnf_p5.c b/nfapi/oai_integration/aerial/fapi_vnf_p5.c index 81d91c8265..951a734ddd 100644 --- a/nfapi/oai_integration/aerial/fapi_vnf_p5.c +++ b/nfapi/oai_integration/aerial/fapi_vnf_p5.c @@ -29,7 +29,7 @@ * \note * \warning */ -#ifdef ENABLE_AERIAL + #include "fapi_vnf_p5.h" #include "fapi_vnf_p7.h" #include "nfapi/open-nFAPI/vnf/inc/vnf_p7.h" @@ -53,19 +53,19 @@ void *aerial_vnf_nr_p7_config_init(void *ptr) init_queue(&gnb_slot_ind_queue); p7_vnf->config->port = p7_vnf->local_port; - p7_vnf->config->sync_indication = &aerial_phy_sync_indication; - p7_vnf->config->slot_indication = &aerial_phy_slot_indication; - p7_vnf->config->harq_indication = &aerial_phy_harq_indication; + p7_vnf->config->sync_indication = NULL; + p7_vnf->config->slot_indication = NULL; + p7_vnf->config->harq_indication = NULL; p7_vnf->config->nr_crc_indication = &aerial_phy_nr_crc_indication; p7_vnf->config->nr_rx_data_indication = &aerial_phy_nr_rx_data_indication; p7_vnf->config->nr_rach_indication = &aerial_phy_nr_rach_indication; p7_vnf->config->nr_uci_indication = &aerial_phy_nr_uci_indication; - p7_vnf->config->srs_indication = &aerial_phy_srs_indication; - p7_vnf->config->sr_indication = &aerial_phy_sr_indication; - p7_vnf->config->cqi_indication = &aerial_phy_cqi_indication; - p7_vnf->config->lbt_dl_indication = &aerial_phy_lbt_dl_indication; - p7_vnf->config->nb_harq_indication = &aerial_phy_nb_harq_indication; - p7_vnf->config->nrach_indication = &aerial_phy_nrach_indication; + p7_vnf->config->srs_indication = NULL; + p7_vnf->config->sr_indication = NULL; + p7_vnf->config->cqi_indication = NULL; + p7_vnf->config->lbt_dl_indication = NULL; + p7_vnf->config->nb_harq_indication = NULL; + p7_vnf->config->nrach_indication = NULL; p7_vnf->config->nr_slot_indication = &aerial_phy_nr_slot_indication; p7_vnf->config->nr_srs_indication = &aerial_phy_nr_srs_indication; p7_vnf->config->malloc = &aerial_vnf_allocate; @@ -283,7 +283,7 @@ int aerial_nr_send_config_request(nfapi_vnf_config_t *config, int p5_idx) pnf_info *pnf = vnf->pnfs; phy_info *phy = pnf->phys; - nfapi_nr_config_request_scf_t *req = &RC.nrmac[0]->config[0]; //&RC.gNB[0]->gNB_config; // check + nfapi_nr_config_request_scf_t *req = &RC.nrmac[0]->config[0]; NFAPI_TRACE(NFAPI_TRACE_INFO, "[VNF] %d.%d pnf p7 %s:%d timing %u %u %u %u\n", @@ -617,4 +617,3 @@ int oai_fapi_send_end_request(int cell, uint32_t frame, uint32_t slot){ } return retval; } -#endif diff --git a/nfapi/oai_integration/aerial/fapi_vnf_p5.h b/nfapi/oai_integration/aerial/fapi_vnf_p5.h index b67f959f8f..84fb3ec2f8 100644 --- a/nfapi/oai_integration/aerial/fapi_vnf_p5.h +++ b/nfapi/oai_integration/aerial/fapi_vnf_p5.h @@ -29,7 +29,7 @@ * \note * \warning */ -#ifdef ENABLE_AERIAL + #ifndef OPENAIRINTERFACE_FAPI_VNF_P5_H #define OPENAIRINTERFACE_FAPI_VNF_P5_H #define _GNU_SOURCE @@ -70,4 +70,3 @@ int oai_fapi_ul_dci_req(nfapi_nr_ul_dci_request_t *ul_dci_req); int oai_fapi_tx_data_req(nfapi_nr_tx_data_request_t *tx_data_req); int oai_fapi_dl_tti_req(nfapi_nr_dl_tti_request_t *dl_config_req); #endif //OPENAIRINTERFACE_FAPI_VNF_P5_H -#endif diff --git a/nfapi/oai_integration/aerial/fapi_vnf_p7.c b/nfapi/oai_integration/aerial/fapi_vnf_p7.c index 790df64f94..2f8d001d50 100644 --- a/nfapi/oai_integration/aerial/fapi_vnf_p7.c +++ b/nfapi/oai_integration/aerial/fapi_vnf_p7.c @@ -29,414 +29,148 @@ * \note * \warning */ -#ifdef ENABLE_AERIAL + #include "fapi_vnf_p7.h" #include "nr_nfapi_p7.h" -extern RAN_CONTEXT_t RC; -extern UL_RCC_IND_t UL_RCC_INFO; -extern uint16_t sf_ahead; - -int aerial_wake_gNB_rxtx(PHY_VARS_gNB *gNB, uint16_t sfn, uint16_t slot) -{ - struct timespec curr_t; - clock_gettime(CLOCK_MONOTONIC, &curr_t); - // NFAPI_TRACE(NFAPI_TRACE_INFO, "\n wake_gNB_rxtx before assignment sfn:%d slot:%d TIME - // %d.%d",sfn,slot,curr_t.tv_sec,curr_t.tv_nsec); - gNB_L1_proc_t *proc = &gNB->proc; - gNB_L1_rxtx_proc_t *L1_proc = (slot & 1) ? &proc->L1_proc : &proc->L1_proc_tx; - - NR_DL_FRAME_PARMS *fp = &gNB->frame_parms; - // NFAPI_TRACE(NFAPI_TRACE_INFO, "%s(eNB:%p, sfn:%d, sf:%d)\n", __FUNCTION__, eNB, sfn, sf); - // int i; - struct timespec wait; - clock_gettime(CLOCK_REALTIME, &wait); - wait.tv_sec = 0; - wait.tv_nsec += 5000L; - // wait.tv_nsec = 0; - // wake up TX for subframe n+sf_ahead - // lock the TX mutex and make sure the thread is ready - if (pthread_mutex_timedlock(&L1_proc->mutex, &wait) != 0) { - LOG_E(PHY, "[gNB] ERROR pthread_mutex_lock for gNB RXTX thread %d (IC %d)\n", L1_proc->slot_rx & 1, L1_proc->instance_cnt); - exit_fun("error locking mutex_rxtx"); - return (-1); - } - - { - static uint16_t old_slot = 0; - static uint16_t old_sfn = 0; - proc->slot_rx = old_slot; - proc->frame_rx = old_sfn; - // Try to be 1 frame back - old_slot = slot; - old_sfn = sfn; - // NFAPI_TRACE(NFAPI_TRACE_INFO, "\n wake_gNB_rxtx after assignment sfn:%d slot:%d",proc->frame_rx,proc->slot_rx); - if (old_slot == 0 && old_sfn % 100 == 0) - LOG_W(PHY, - "[gNB] sfn/slot:%d%d old_sfn/slot:%d%d proc[rx:%d%d]\n", - sfn, - slot, - old_sfn, - old_slot, - proc->frame_rx, - proc->slot_rx); - } - - ++L1_proc->instance_cnt; - // LOG_D( PHY,"[VNF-subframe_ind] sfn/sf:%d:%d proc[frame_rx:%d subframe_rx:%d] L1_proc->instance_cnt_rxtx:%d \n", sfn, sf, - // proc->frame_rx, proc->subframe_rx, L1_proc->instance_cnt_rxtx); - // We have just received and processed the common part of a subframe, say n. - // TS_rx is the last received timestamp (start of 1st slot), TS_tx is the desired - // transmitted timestamp of the next TX slot (first). - // The last (TS_rx mod samples_per_frame) was n*samples_per_tti, - // we want to generate subframe (n+N), so TS_tx = TX_rx+N*samples_per_tti, - // and proc->subframe_tx = proc->subframe_rx+sf_ahead - L1_proc->timestamp_tx = proc->timestamp_rx + (gNB->if_inst->sl_ahead * fp->samples_per_subframe); - L1_proc->frame_rx = proc->frame_rx; - L1_proc->slot_rx = proc->slot_rx; - L1_proc->frame_tx = (L1_proc->slot_rx > (19 - gNB->if_inst->sl_ahead)) ? (L1_proc->frame_rx + 1) & 1023 : L1_proc->frame_rx; - L1_proc->slot_tx = (L1_proc->slot_rx + gNB->if_inst->sl_ahead) % 20; - - // LOG_I(PHY, "sfn/sf:%d%d proc[rx:%d%d] rx:%d%d] About to wake rxtx thread\n\n", sfn, slot, proc->frame_rx, proc->slot_rx, - // L1_proc->frame_rx, L1_proc->slot_rx); NFAPI_TRACE(NFAPI_TRACE_INFO, "\nEntering wake_gNB_rxtx sfn %d slot - // %d\n",L1_proc->frame_rx,L1_proc->slot_rx); - // the thread can now be woken up - if (pthread_cond_signal(&L1_proc->cond) != 0) { - LOG_E(PHY, "[gNB] ERROR pthread_cond_signal for gNB RXn-TXnp4 thread\n"); - exit_fun("ERROR pthread_clond_signal"); - return (-1); - } - - // LOG_D(PHY,"%s() About to attempt pthread_mutex_unlock\n", __FUNCTION__); - pthread_mutex_unlock(&L1_proc->mutex); - // LOG_D(PHY,"%s() UNLOCKED pthread_mutex_unlock\n", __FUNCTION__); - return (0); -} - -int aerialwake_eNB_rxtx(PHY_VARS_eNB *eNB, uint16_t sfn, uint16_t sf) -{ - L1_proc_t *proc = &eNB->proc; - L1_rxtx_proc_t *L1_proc = (sf & 1) ? &proc->L1_proc : &proc->L1_proc_tx; - LTE_DL_FRAME_PARMS *fp = &eNB->frame_parms; - // NFAPI_TRACE(NFAPI_TRACE_INFO, "%s(eNB:%p, sfn:%d, sf:%d)\n", __FUNCTION__, eNB, sfn, sf); - // int i; - struct timespec wait; - wait.tv_sec = 0; - wait.tv_nsec = 5000000L; - - // wake up TX for subframe n+sf_ahead - // lock the TX mutex and make sure the thread is ready - // if (pthread_mutex_timedlock(&L1_proc->mutex,&wait) != 0) { - // LOG_E( PHY, "[eNB] ERROR pthread_mutex_lock for eNB RXTX thread %d (IC %d)\n", L1_proc->subframe_rx&1,L1_proc->instance_cnt ); - // exit_fun( "error locking mutex_rxtx" ); - // return(-1); - //} - - { - static uint16_t old_sf = 0; - static uint16_t old_sfn = 0; - proc->subframe_rx = old_sf; - proc->frame_rx = old_sfn; - // Try to be 1 frame back - old_sf = sf; - old_sfn = sfn; - - if (old_sf == 0 && old_sfn % 100 == 0) - LOG_D(PHY, "[eNB] sfn/sf:%d%d old_sfn/sf:%d%d proc[rx:%d%d]\n", sfn, sf, old_sfn, old_sf, proc->frame_rx, proc->subframe_rx); - } - // wake up TX for subframe n+sf_ahead - // lock the TX mutex and make sure the thread is ready - if (pthread_mutex_timedlock(&L1_proc->mutex, &wait) != 0) { - LOG_E(PHY, "[eNB] ERROR pthread_mutex_lock for eNB RXTX thread %d (IC %d)\n", L1_proc->subframe_rx & 1, L1_proc->instance_cnt); - // exit_fun( "error locking mutex_rxtx" ); - return (-1); - } - static int busy_log_cnt = 0; - if (L1_proc->instance_cnt < 0) { - ++L1_proc->instance_cnt; - if (busy_log_cnt != 0) { - LOG_E(MAC, - "RCC singal to rxtx frame %d subframe %d busy end %d (frame %d subframe %d)\n", - L1_proc->frame_rx, - L1_proc->subframe_rx, - busy_log_cnt, - proc->frame_rx, - proc->subframe_rx); - } - busy_log_cnt = 0; - } else { - if (busy_log_cnt == 0) { - LOG_E(MAC, - "RCC singal to rxtx frame %d subframe %d busy %d (frame %d subframe %d)\n", - L1_proc->frame_rx, - L1_proc->subframe_rx, - L1_proc->instance_cnt, - proc->frame_rx, - proc->subframe_rx); - } - pthread_mutex_unlock(&L1_proc->mutex); - busy_log_cnt++; - return (0); - } - - pthread_mutex_unlock(&L1_proc->mutex); - - // LOG_D( PHY,"[VNF-subframe_ind] sfn/sf:%d:%d proc[frame_rx:%d subframe_rx:%d] L1_proc->instance_cnt_rxtx:%d \n", sfn, sf, - // proc->frame_rx, proc->subframe_rx, L1_proc->instance_cnt_rxtx); - // We have just received and processed the common part of a subframe, say n. - // TS_rx is the last received timestamp (start of 1st slot), TS_tx is the desired - // transmitted timestamp of the next TX slot (first). - // The last (TS_rx mod samples_per_frame) was n*samples_per_tti, - // we want to generate subframe (n+N), so TS_tx = TX_rx+N*samples_per_tti, - // and proc->subframe_tx = proc->subframe_rx+sf_ahead - L1_proc->timestamp_tx = proc->timestamp_rx + (sf_ahead * fp->samples_per_tti); - L1_proc->frame_rx = proc->frame_rx; - L1_proc->subframe_rx = proc->subframe_rx; - L1_proc->frame_tx = (L1_proc->subframe_rx > (9 - sf_ahead)) ? (L1_proc->frame_rx + 1) & 1023 : L1_proc->frame_rx; - L1_proc->subframe_tx = (L1_proc->subframe_rx + sf_ahead) % 10; - - // LOG_D(PHY, "sfn/sf:%d%d proc[rx:%d%d] L1_proc[instance_cnt_rxtx:%d rx:%d%d] About to wake rxtx thread\n\n", sfn, sf, - // proc->frame_rx, proc->subframe_rx, L1_proc->instance_cnt_rxtx, L1_proc->frame_rx, L1_proc->subframe_rx); - - // the thread can now be woken up - if (pthread_cond_signal(&L1_proc->cond) != 0) { - LOG_E(PHY, "[eNB] ERROR pthread_cond_signal for eNB RXn-TXnp4 thread\n"); - exit_fun("ERROR pthread_cond_signal"); - return (-1); - } - - return (0); -} +#include "openair2/LAYER2/NR_MAC_gNB/mac_proto.h" // for handle_nr_srs_measurements() extern pthread_cond_t nfapi_sync_cond; extern pthread_mutex_t nfapi_sync_mutex; extern int nfapi_sync_var; -int aerial_phy_sync_indication(struct nfapi_vnf_p7_config *config, uint8_t sync) -{ - // NFAPI_TRACE(NFAPI_TRACE_INFO, "[VNF] SYNC %s\n", sync==1 ? "ACHIEVED" : "LOST"); - - if (sync == 1 && nfapi_sync_var != 0) { - NFAPI_TRACE(NFAPI_TRACE_INFO, "[VNF] Signal to OAI main code that it can go\n"); - pthread_mutex_lock(&nfapi_sync_mutex); - nfapi_sync_var = 0; - pthread_cond_broadcast(&nfapi_sync_cond); - pthread_mutex_unlock(&nfapi_sync_mutex); - } - - return (0); -} - -int aerial_phy_slot_indication(struct nfapi_vnf_p7_config *config, uint16_t phy_id, uint16_t sfn, uint16_t slot) -{ - static uint8_t first_time = 1; - - if (first_time) { - NFAPI_TRACE(NFAPI_TRACE_INFO, "[VNF] slot indication %d\n", NFAPI_SFNSLOT2DEC(sfn, slot)); - first_time = 0; - } - - if (RC.gNB && RC.gNB[0]->configured) { - // uint16_t sfn = NFAPI_SFNSF2SFN(sfn_sf); - // uint16_t sf = NFAPI_SFNSF2SF(sfn_sf); - LOG_D(PHY, "[VNF] slot indication sfn:%d slot:%d\n", sfn, slot); - aerial_wake_gNB_rxtx(RC.gNB[0], sfn, slot); // DONE: find NR equivalent - } else { - NFAPI_TRACE(NFAPI_TRACE_INFO, "[VNF] %s() RC.gNB:%p\n", __FUNCTION__, RC.gNB); - - if (RC.gNB) - NFAPI_TRACE(NFAPI_TRACE_INFO, "RC.gNB[0]->configured:%d\n", RC.gNB[0]->configured); - } - - return 0; -} - -int aerial_phy_harq_indication(struct nfapi_vnf_p7_config *config, nfapi_harq_indication_t *ind) -{ - struct PHY_VARS_eNB_s *eNB = RC.eNB[0][0]; - LOG_D(MAC, - "%s() NFAPI SFN/SF:%d number_of_harqs:%u\n", - __FUNCTION__, - NFAPI_SFNSF2DEC(ind->sfn_sf), - ind->harq_indication_body.number_of_harqs); - AssertFatal(pthread_mutex_lock(&eNB->UL_INFO_mutex) == 0, "Mutex lock failed"); - if (NFAPI_MODE == NFAPI_MODE_VNF) { - int8_t index = NFAPI_SFNSF2SF(ind->sfn_sf); - - UL_RCC_INFO.harq_ind[index] = *ind; - - assert(ind->harq_indication_body.number_of_harqs <= NFAPI_HARQ_IND_MAX_PDU); - if (ind->harq_indication_body.number_of_harqs > 0) { - UL_RCC_INFO.harq_ind[index].harq_indication_body.harq_pdu_list = - malloc(sizeof(nfapi_harq_indication_pdu_t) * NFAPI_HARQ_IND_MAX_PDU); - } - for (int i = 0; i < ind->harq_indication_body.number_of_harqs; i++) { - memcpy(&UL_RCC_INFO.harq_ind[index].harq_indication_body.harq_pdu_list[i], - &ind->harq_indication_body.harq_pdu_list[i], - sizeof(nfapi_harq_indication_pdu_t)); - } - } else { - eNB->UL_INFO.harq_ind = *ind; - eNB->UL_INFO.harq_ind.harq_indication_body.harq_pdu_list = eNB->harq_pdu_list; - - assert(ind->harq_indication_body.number_of_harqs <= NFAPI_HARQ_IND_MAX_PDU); - for (int i = 0; i < ind->harq_indication_body.number_of_harqs; i++) { - memcpy(&eNB->UL_INFO.harq_ind.harq_indication_body.harq_pdu_list[i], - &ind->harq_indication_body.harq_pdu_list[i], - sizeof(eNB->UL_INFO.harq_ind.harq_indication_body.harq_pdu_list[i])); - } - } - AssertFatal(pthread_mutex_unlock(&eNB->UL_INFO_mutex) == 0, "Mutex unlock failed"); - // vnf_p7_info* p7_vnf = (vnf_p7_info*)(config->user_data); - // mac_harq_ind(p7_vnf->mac, ind); - return 1; -} - int aerial_phy_nr_crc_indication(nfapi_nr_crc_indication_t *ind) { - if (NFAPI_MODE == NFAPI_MODE_AERIAL) { - nfapi_nr_crc_indication_t *crc_ind = CALLOC(1, sizeof(*crc_ind)); - crc_ind->header.message_id = ind->header.message_id; - crc_ind->number_crcs = ind->number_crcs; - crc_ind->sfn = ind->sfn; - crc_ind->slot = ind->slot; - if (ind->number_crcs > 0) { - crc_ind->crc_list = CALLOC(NFAPI_NR_CRC_IND_MAX_PDU, sizeof(nfapi_nr_crc_t)); - AssertFatal(crc_ind->crc_list != NULL, "Memory not allocated for crc_ind->crc_list in phy_nr_crc_indication."); + nfapi_nr_crc_indication_t *crc_ind = CALLOC(1, sizeof(*crc_ind)); + crc_ind->header.message_id = ind->header.message_id; + crc_ind->number_crcs = ind->number_crcs; + crc_ind->sfn = ind->sfn; + crc_ind->slot = ind->slot; + if (ind->number_crcs > 0) { + crc_ind->crc_list = CALLOC(NFAPI_NR_CRC_IND_MAX_PDU, sizeof(nfapi_nr_crc_t)); + AssertFatal(crc_ind->crc_list != NULL, "Memory not allocated for crc_ind->crc_list in phy_nr_crc_indication."); + } + for (int j = 0; j < ind->number_crcs; j++) { + crc_ind->crc_list[j].handle = ind->crc_list[j].handle; + crc_ind->crc_list[j].rnti = ind->crc_list[j].rnti; + crc_ind->crc_list[j].harq_id = ind->crc_list[j].harq_id; + crc_ind->crc_list[j].tb_crc_status = ind->crc_list[j].tb_crc_status; + crc_ind->crc_list[j].num_cb = ind->crc_list[j].num_cb; + crc_ind->crc_list[j].cb_crc_status = ind->crc_list[j].cb_crc_status; + crc_ind->crc_list[j].ul_cqi = ind->crc_list[j].ul_cqi; + crc_ind->crc_list[j].timing_advance = ind->crc_list[j].timing_advance; + crc_ind->crc_list[j].rssi = ind->crc_list[j].rssi; + if (crc_ind->crc_list[j].tb_crc_status != 0) { + LOG_D(NR_MAC, + "Received crc_ind.harq_id %d status %d for index %d SFN SLot %u %u with rnti %04x\n", + crc_ind->crc_list[j].harq_id, + crc_ind->crc_list[j].tb_crc_status, + j, + crc_ind->sfn, + crc_ind->slot, + crc_ind->crc_list[j].rnti); } - for (int j = 0; j < ind->number_crcs; j++) { - crc_ind->crc_list[j].handle = ind->crc_list[j].handle; - crc_ind->crc_list[j].rnti = ind->crc_list[j].rnti; - crc_ind->crc_list[j].harq_id = ind->crc_list[j].harq_id; - crc_ind->crc_list[j].tb_crc_status = ind->crc_list[j].tb_crc_status; - crc_ind->crc_list[j].num_cb = ind->crc_list[j].num_cb; - crc_ind->crc_list[j].cb_crc_status = ind->crc_list[j].cb_crc_status; - crc_ind->crc_list[j].ul_cqi = ind->crc_list[j].ul_cqi; - crc_ind->crc_list[j].timing_advance = ind->crc_list[j].timing_advance; - crc_ind->crc_list[j].rssi = ind->crc_list[j].rssi; - if (crc_ind->crc_list[j].tb_crc_status != 0) { - LOG_D(NR_MAC, - "Received crc_ind.harq_id %d status %d for index %d SFN SLot %u %u with rnti %04x\n", - crc_ind->crc_list[j].harq_id, - crc_ind->crc_list[j].tb_crc_status, - j, - crc_ind->sfn, - crc_ind->slot, - crc_ind->crc_list[j].rnti); - } - } - if (!put_queue(&gnb_crc_ind_queue, crc_ind)) { - LOG_E(NR_MAC, "Put_queue failed for crc_ind\n"); - free(crc_ind->crc_list); - free(crc_ind); - } - } else { - LOG_E(NR_MAC, "NFAPI_MODE = %d not NFAPI_MODE_AERIAL(3)\n", nfapi_getmode()); + } + if (!put_queue(&gnb_crc_ind_queue, crc_ind)) { + LOG_E(NR_MAC, "Put_queue failed for crc_ind\n"); + free(crc_ind->crc_list); + free(crc_ind); } return 1; } int aerial_phy_nr_rx_data_indication(nfapi_nr_rx_data_indication_t *ind) { - if (NFAPI_MODE == NFAPI_MODE_AERIAL) { - nfapi_nr_rx_data_indication_t *rx_ind = CALLOC(1, sizeof(*rx_ind)); - rx_ind->header.message_id = ind->header.message_id; - rx_ind->sfn = ind->sfn; - rx_ind->slot = ind->slot; - rx_ind->number_of_pdus = ind->number_of_pdus; + nfapi_nr_rx_data_indication_t *rx_ind = CALLOC(1, sizeof(*rx_ind)); + rx_ind->header.message_id = ind->header.message_id; + rx_ind->sfn = ind->sfn; + rx_ind->slot = ind->slot; + rx_ind->number_of_pdus = ind->number_of_pdus; - if (ind->number_of_pdus > 0) { - rx_ind->pdu_list = CALLOC(NFAPI_NR_RX_DATA_IND_MAX_PDU, sizeof(nfapi_nr_rx_data_pdu_t)); - AssertFatal(rx_ind->pdu_list != NULL, "Memory not allocated for rx_ind->pdu_list in phy_nr_rx_data_indication."); - } - for (int j = 0; j < ind->number_of_pdus; j++) { - rx_ind->pdu_list[j].handle = ind->pdu_list[j].handle; - rx_ind->pdu_list[j].rnti = ind->pdu_list[j].rnti; - rx_ind->pdu_list[j].harq_id = ind->pdu_list[j].harq_id; - rx_ind->pdu_list[j].pdu_length = ind->pdu_list[j].pdu_length; - rx_ind->pdu_list[j].ul_cqi = ind->pdu_list[j].ul_cqi; - rx_ind->pdu_list[j].timing_advance = ind->pdu_list[j].timing_advance; - rx_ind->pdu_list[j].rssi = ind->pdu_list[j].rssi; + if (ind->number_of_pdus > 0) { + rx_ind->pdu_list = CALLOC(NFAPI_NR_RX_DATA_IND_MAX_PDU, sizeof(nfapi_nr_rx_data_pdu_t)); + AssertFatal(rx_ind->pdu_list != NULL, "Memory not allocated for rx_ind->pdu_list in phy_nr_rx_data_indication."); + } + for (int j = 0; j < ind->number_of_pdus; j++) { + rx_ind->pdu_list[j].handle = ind->pdu_list[j].handle; + rx_ind->pdu_list[j].rnti = ind->pdu_list[j].rnti; + rx_ind->pdu_list[j].harq_id = ind->pdu_list[j].harq_id; + rx_ind->pdu_list[j].pdu_length = ind->pdu_list[j].pdu_length; + rx_ind->pdu_list[j].ul_cqi = ind->pdu_list[j].ul_cqi; + rx_ind->pdu_list[j].timing_advance = ind->pdu_list[j].timing_advance; + rx_ind->pdu_list[j].rssi = ind->pdu_list[j].rssi; + // Only copy PDU data if there's any to copy + if (rx_ind->pdu_list[j].pdu_length > 0) { rx_ind->pdu_list[j].pdu = calloc(rx_ind->pdu_list[j].pdu_length, sizeof(uint8_t)); - memcpy(rx_ind->pdu_list[j].pdu,ind->pdu_list[j].pdu,ind->pdu_list[j].pdu_length); - LOG_D(NR_MAC, - "(%d.%d) Handle %d for index %d, RNTI, %04x, HARQID %d\n", - ind->sfn, - ind->slot, - ind->pdu_list[j].handle, - j, - ind->pdu_list[j].rnti, - ind->pdu_list[j].harq_id); + memcpy(rx_ind->pdu_list[j].pdu, ind->pdu_list[j].pdu, ind->pdu_list[j].pdu_length); } - if (!put_queue(&gnb_rx_ind_queue, rx_ind)) { - LOG_E(NR_MAC, "Put_queue failed for rx_ind\n"); - free(rx_ind->pdu_list); - free(rx_ind); - } - } else { - LOG_E(NR_MAC, "NFAPI_MODE = %d not NFAPI_MODE_AERIAL(3)\n", nfapi_getmode()); + LOG_D(NR_MAC, + "(%d.%d) Handle %d for index %d, RNTI, %04x, HARQID %d\n", + ind->sfn, + ind->slot, + ind->pdu_list[j].handle, + j, + ind->pdu_list[j].rnti, + ind->pdu_list[j].harq_id); + } + if (!put_queue(&gnb_rx_ind_queue, rx_ind)) { + LOG_E(NR_MAC, "Put_queue failed for rx_ind\n"); + free(rx_ind->pdu_list); + free(rx_ind); } return 1; } int aerial_phy_nr_rach_indication(nfapi_nr_rach_indication_t *ind) { - if (NFAPI_MODE == NFAPI_MODE_AERIAL) { - nfapi_nr_rach_indication_t *rach_ind = CALLOC(1, sizeof(*rach_ind)); - rach_ind->header.message_id = ind->header.message_id; - rach_ind->sfn = ind->sfn; - rach_ind->slot = ind->slot; - rach_ind->number_of_pdus = ind->number_of_pdus; - rach_ind->pdu_list = CALLOC(rach_ind->number_of_pdus, sizeof(*rach_ind->pdu_list)); - AssertFatal(rach_ind->pdu_list != NULL, "Memory not allocated for rach_ind->pdu_list in phy_nr_rach_indication."); - for (int i = 0; i < ind->number_of_pdus; i++) { - rach_ind->pdu_list[i].phy_cell_id = ind->pdu_list[i].phy_cell_id; - rach_ind->pdu_list[i].symbol_index = ind->pdu_list[i].symbol_index; - rach_ind->pdu_list[i].slot_index = ind->pdu_list[i].slot_index; - rach_ind->pdu_list[i].freq_index = ind->pdu_list[i].freq_index; - rach_ind->pdu_list[i].avg_rssi = ind->pdu_list[i].avg_rssi; - rach_ind->pdu_list[i].avg_snr = ind->pdu_list[i].avg_snr; - rach_ind->pdu_list[i].num_preamble = ind->pdu_list[i].num_preamble; - for (int j = 0; j < ind->pdu_list[i].num_preamble; j++) { - rach_ind->pdu_list[i].preamble_list[j].preamble_index = ind->pdu_list[i].preamble_list[j].preamble_index; - rach_ind->pdu_list[i].preamble_list[j].timing_advance = ind->pdu_list[i].preamble_list[j].timing_advance; - rach_ind->pdu_list[i].preamble_list[j].preamble_pwr = ind->pdu_list[i].preamble_list[j].preamble_pwr; - } - } - if (!put_queue(&gnb_rach_ind_queue, rach_ind)) { - LOG_E(NR_MAC, "Put_queue failed for rach_ind\n"); - for (int i = 0; i < ind->number_of_pdus; i++) { - free(rach_ind->pdu_list[i].preamble_list); - } - free(rach_ind->pdu_list); - free(rach_ind); - } else { - LOG_I(NR_MAC, "RACH.indication put_queue successfull\n"); + nfapi_nr_rach_indication_t *rach_ind = CALLOC(1, sizeof(*rach_ind)); + rach_ind->header.message_id = ind->header.message_id; + rach_ind->sfn = ind->sfn; + rach_ind->slot = ind->slot; + rach_ind->number_of_pdus = ind->number_of_pdus; + rach_ind->pdu_list = CALLOC(rach_ind->number_of_pdus, sizeof(*rach_ind->pdu_list)); + AssertFatal(rach_ind->pdu_list != NULL, "Memory not allocated for rach_ind->pdu_list in phy_nr_rach_indication."); + for (int i = 0; i < ind->number_of_pdus; i++) { + rach_ind->pdu_list[i].phy_cell_id = ind->pdu_list[i].phy_cell_id; + rach_ind->pdu_list[i].symbol_index = ind->pdu_list[i].symbol_index; + rach_ind->pdu_list[i].slot_index = ind->pdu_list[i].slot_index; + rach_ind->pdu_list[i].freq_index = ind->pdu_list[i].freq_index; + rach_ind->pdu_list[i].avg_rssi = ind->pdu_list[i].avg_rssi; + rach_ind->pdu_list[i].avg_snr = ind->pdu_list[i].avg_snr; + rach_ind->pdu_list[i].num_preamble = ind->pdu_list[i].num_preamble; + for (int j = 0; j < ind->pdu_list[i].num_preamble; j++) { + rach_ind->pdu_list[i].preamble_list[j].preamble_index = ind->pdu_list[i].preamble_list[j].preamble_index; + rach_ind->pdu_list[i].preamble_list[j].timing_advance = ind->pdu_list[i].preamble_list[j].timing_advance; + rach_ind->pdu_list[i].preamble_list[j].preamble_pwr = ind->pdu_list[i].preamble_list[j].preamble_pwr; } + } + if (!put_queue(&gnb_rach_ind_queue, rach_ind)) { + LOG_E(NR_MAC, "Put_queue failed for rach_ind\n"); + free(rach_ind->pdu_list); + free(rach_ind); } else { - LOG_E(NR_MAC, "NFAPI_MODE = %d not NFAPI_MODE_AERIAL(3)\n", nfapi_getmode()); + LOG_I(NR_MAC, "RACH.indication put_queue successfull\n"); } return 1; } int aerial_phy_nr_uci_indication(nfapi_nr_uci_indication_t *ind) { - if (NFAPI_MODE == NFAPI_MODE_AERIAL) { - nfapi_nr_uci_indication_t *uci_ind = CALLOC(1, sizeof(*uci_ind)); - AssertFatal(uci_ind, "Memory not allocated for uci_ind in phy_nr_uci_indication."); - *uci_ind = *ind; + nfapi_nr_uci_indication_t *uci_ind = CALLOC(1, sizeof(*uci_ind)); + AssertFatal(uci_ind, "Memory not allocated for uci_ind in phy_nr_uci_indication."); + *uci_ind = *ind; - uci_ind->uci_list = CALLOC(NFAPI_NR_UCI_IND_MAX_PDU, sizeof(nfapi_nr_uci_t)); - AssertFatal(uci_ind->uci_list != NULL, "Memory not allocated for uci_ind->uci_list in phy_nr_uci_indication."); - for (int i = 0; i < ind->num_ucis; i++) { - uci_ind->uci_list[i] = ind->uci_list[i]; + uci_ind->uci_list = CALLOC(NFAPI_NR_UCI_IND_MAX_PDU, sizeof(nfapi_nr_uci_t)); + AssertFatal(uci_ind->uci_list != NULL, "Memory not allocated for uci_ind->uci_list in phy_nr_uci_indication."); + for (int i = 0; i < ind->num_ucis; i++) { + uci_ind->uci_list[i] = ind->uci_list[i]; - switch (uci_ind->uci_list[i].pdu_type) { - case NFAPI_NR_UCI_PUSCH_PDU_TYPE: - LOG_E(MAC, "%s(): unhandled NFAPI_NR_UCI_PUSCH_PDU_TYPE\n", __func__); - break; + switch (uci_ind->uci_list[i].pdu_type) { + case NFAPI_NR_UCI_PUSCH_PDU_TYPE: + LOG_E(MAC, "%s(): unhandled NFAPI_NR_UCI_PUSCH_PDU_TYPE\n", __func__); + break; - case NFAPI_NR_UCI_FORMAT_0_1_PDU_TYPE: { + case NFAPI_NR_UCI_FORMAT_0_1_PDU_TYPE: { // nfapi_nr_uci_pucch_pdu_format_0_1_t *uci_ind_pdu = &uci_ind->uci_list[i].pucch_pdu_format_0_1; // nfapi_nr_uci_pucch_pdu_format_0_1_t *ind_pdu = &ind->uci_list[i].pucch_pdu_format_0_1; // if (ind_pdu->sr) { @@ -455,49 +189,49 @@ int aerial_phy_nr_uci_indication(nfapi_nr_uci_indication_t *ind) // for (int j = 0; j < uci_ind_pdu->harq->num_harq; j++) // uci_ind_pdu->harq->harq_list[j].harq_value = ind_pdu->harq->harq_list[j].harq_value; // } - break; - } + break; + } - case NFAPI_NR_UCI_FORMAT_2_3_4_PDU_TYPE: { - nfapi_nr_uci_pucch_pdu_format_2_3_4_t *uci_ind_pdu = &uci_ind->uci_list[i].pucch_pdu_format_2_3_4; - nfapi_nr_uci_pucch_pdu_format_2_3_4_t *ind_pdu = &ind->uci_list[i].pucch_pdu_format_2_3_4; - *uci_ind_pdu = *ind_pdu; - if (ind_pdu->harq.harq_payload) { - uci_ind_pdu->harq.harq_payload = CALLOC(1, sizeof(*uci_ind_pdu->harq.harq_payload)); - AssertFatal(uci_ind_pdu->harq.harq_payload != NULL, - "Memory not allocated for uci_ind_pdu->harq.harq_payload in phy_nr_uci_indication."); - *uci_ind_pdu->harq.harq_payload = *ind_pdu->harq.harq_payload; - } - if (ind_pdu->sr.sr_payload) { - uci_ind_pdu->sr.sr_payload = CALLOC(1, sizeof(*uci_ind_pdu->sr.sr_payload)); - AssertFatal(uci_ind_pdu->sr.sr_payload != NULL, - "Memory not allocated for uci_ind_pdu->sr.sr_payload in phy_nr_uci_indication."); - //SCF222.10.02 sr_bit_len values from 1 to 8, payload always just one byte - uci_ind_pdu->sr.sr_payload[0] = ind_pdu->sr.sr_payload[0]; - } - if (ind_pdu->csi_part1.csi_part1_payload) { - uint8_t byte_len = (ind_pdu->csi_part1.csi_part1_bit_len / 8) + 1; - uci_ind_pdu->csi_part1.csi_part1_payload = calloc(byte_len, sizeof(uint8_t)); - AssertFatal(uci_ind_pdu->csi_part1.csi_part1_payload != NULL, - "Memory not allocated for uci_ind_pdu->csi_part1.csi_part1_payload in phy_nr_uci_indication."); - memcpy(uci_ind_pdu->csi_part1.csi_part1_payload,ind_pdu->csi_part1.csi_part1_payload,byte_len); - } - if (ind_pdu->csi_part2.csi_part2_payload) { - uint8_t byte_len = (ind_pdu->csi_part2.csi_part2_bit_len / 8) + 1; - uci_ind_pdu->csi_part2.csi_part2_payload = calloc(byte_len, sizeof(uint8_t)); - AssertFatal(uci_ind_pdu->csi_part2.csi_part2_payload != NULL, - "Memory not allocated for uci_ind_pdu->csi_part2.csi_part2_payload in phy_nr_uci_indication."); - memcpy(uci_ind_pdu->csi_part2.csi_part2_payload,ind_pdu->csi_part2.csi_part2_payload,byte_len); - } - break; + case NFAPI_NR_UCI_FORMAT_2_3_4_PDU_TYPE: { + nfapi_nr_uci_pucch_pdu_format_2_3_4_t *uci_ind_pdu = &uci_ind->uci_list[i].pucch_pdu_format_2_3_4; + nfapi_nr_uci_pucch_pdu_format_2_3_4_t *ind_pdu = &ind->uci_list[i].pucch_pdu_format_2_3_4; + *uci_ind_pdu = *ind_pdu; + if (ind_pdu->harq.harq_payload) { + uci_ind_pdu->harq.harq_payload = CALLOC(1, sizeof(*uci_ind_pdu->harq.harq_payload)); + AssertFatal(uci_ind_pdu->harq.harq_payload != NULL, + "Memory not allocated for uci_ind_pdu->harq.harq_payload in phy_nr_uci_indication."); + *uci_ind_pdu->harq.harq_payload = *ind_pdu->harq.harq_payload; } + if (ind_pdu->sr.sr_payload) { + uci_ind_pdu->sr.sr_payload = CALLOC(1, sizeof(*uci_ind_pdu->sr.sr_payload)); + AssertFatal(uci_ind_pdu->sr.sr_payload != NULL, + "Memory not allocated for uci_ind_pdu->sr.sr_payload in phy_nr_uci_indication."); + //SCF222.10.02 sr_bit_len values from 1 to 8, payload always just one byte + uci_ind_pdu->sr.sr_payload[0] = ind_pdu->sr.sr_payload[0]; + } + if (ind_pdu->csi_part1.csi_part1_payload) { + uint8_t byte_len = (ind_pdu->csi_part1.csi_part1_bit_len / 8) + 1; + uci_ind_pdu->csi_part1.csi_part1_payload = calloc(byte_len, sizeof(uint8_t)); + AssertFatal(uci_ind_pdu->csi_part1.csi_part1_payload != NULL, + "Memory not allocated for uci_ind_pdu->csi_part1.csi_part1_payload in phy_nr_uci_indication."); + memcpy(uci_ind_pdu->csi_part1.csi_part1_payload,ind_pdu->csi_part1.csi_part1_payload,byte_len); + } + if (ind_pdu->csi_part2.csi_part2_payload) { + uint8_t byte_len = (ind_pdu->csi_part2.csi_part2_bit_len / 8) + 1; + uci_ind_pdu->csi_part2.csi_part2_payload = calloc(byte_len, sizeof(uint8_t)); + AssertFatal(uci_ind_pdu->csi_part2.csi_part2_payload != NULL, + "Memory not allocated for uci_ind_pdu->csi_part2.csi_part2_payload in phy_nr_uci_indication."); + memcpy(uci_ind_pdu->csi_part2.csi_part2_payload,ind_pdu->csi_part2.csi_part2_payload,byte_len); + } + break; } } + } - if (!put_queue(&gnb_uci_ind_queue, uci_ind)) { - LOG_E(NR_MAC, "Put_queue failed for uci_ind\n"); - for (int i = 0; i < ind->num_ucis; i++) { - if (uci_ind->uci_list[i].pdu_type == NFAPI_NR_UCI_FORMAT_0_1_PDU_TYPE) { + if (!put_queue(&gnb_uci_ind_queue, uci_ind)) { + LOG_E(NR_MAC, "Put_queue failed for uci_ind\n"); + for (int i = 0; i < ind->num_ucis; i++) { + if (uci_ind->uci_list[i].pdu_type == NFAPI_NR_UCI_FORMAT_0_1_PDU_TYPE) { // if (uci_ind->uci_list[i].pucch_pdu_format_0_1.harq) { // free(uci_ind->uci_list[i].pucch_pdu_format_0_1.harq->harq_list); // uci_ind->uci_list[i].pucch_pdu_format_0_1.harq->harq_list = NULL; @@ -508,210 +242,21 @@ int aerial_phy_nr_uci_indication(nfapi_nr_uci_indication_t *ind) // free(uci_ind->uci_list[i].pucch_pdu_format_0_1.sr); // uci_ind->uci_list[i].pucch_pdu_format_0_1.sr = NULL; // } - } - if (uci_ind->uci_list[i].pdu_type == NFAPI_NR_UCI_FORMAT_2_3_4_PDU_TYPE) { - free(uci_ind->uci_list[i].pucch_pdu_format_2_3_4.harq.harq_payload); - free(uci_ind->uci_list[i].pucch_pdu_format_2_3_4.csi_part1.csi_part1_payload); - free(uci_ind->uci_list[i].pucch_pdu_format_2_3_4.csi_part2.csi_part2_payload); - } } - free(uci_ind->uci_list); - uci_ind->uci_list = NULL; - free(uci_ind); - uci_ind = NULL; - } - } else { - LOG_E(NR_MAC, "NFAPI_MODE = %d not NFAPI_MODE_AERIAL(3)\n", nfapi_getmode()); - } - return 1; -} - -int aerial_phy_srs_indication(struct nfapi_vnf_p7_config *config, nfapi_srs_indication_t *ind) -{ - // vnf_p7_info* p7_vnf = (vnf_p7_info*)(config->user_data); - // mac_srs_ind(p7_vnf->mac, ind); - return 1; -} - -int aerial_phy_sr_indication(struct nfapi_vnf_p7_config *config, nfapi_sr_indication_t *ind) -{ - struct PHY_VARS_eNB_s *eNB = RC.eNB[0][0]; - LOG_D(MAC, "%s() NFAPI SFN/SF:%d srs:%d\n", __FUNCTION__, NFAPI_SFNSF2DEC(ind->sfn_sf), ind->sr_indication_body.number_of_srs); - AssertFatal(pthread_mutex_lock(&eNB->UL_INFO_mutex) == 0, "Mutex lock failed"); - if (NFAPI_MODE == NFAPI_MODE_VNF) { - int8_t index = NFAPI_SFNSF2SF(ind->sfn_sf); - - UL_RCC_INFO.sr_ind[index] = *ind; - LOG_D(MAC, - "%s() UL_INFO[%d].sr_ind.sr_indication_body.number_of_srs:%d\n", - __FUNCTION__, - index, - eNB->UL_INFO.sr_ind.sr_indication_body.number_of_srs); - if (ind->sr_indication_body.number_of_srs > 0) { - assert(ind->sr_indication_body.number_of_srs <= NFAPI_SR_IND_MAX_PDU); - UL_RCC_INFO.sr_ind[index].sr_indication_body.sr_pdu_list = malloc(sizeof(nfapi_sr_indication_pdu_t) * NFAPI_SR_IND_MAX_PDU); - } - - assert(ind->sr_indication_body.number_of_srs <= NFAPI_SR_IND_MAX_PDU); - for (int i = 0; i < ind->sr_indication_body.number_of_srs; i++) { - nfapi_sr_indication_pdu_t *dest_pdu = &UL_RCC_INFO.sr_ind[index].sr_indication_body.sr_pdu_list[i]; - nfapi_sr_indication_pdu_t *src_pdu = &ind->sr_indication_body.sr_pdu_list[i]; - - LOG_D(MAC, - "SR_IND[PDU:%d %d][rnti:%x cqi:%d channel:%d]\n", - index, - i, - src_pdu->rx_ue_information.rnti, - src_pdu->ul_cqi_information.ul_cqi, - src_pdu->ul_cqi_information.channel); - - memcpy(dest_pdu, src_pdu, sizeof(*src_pdu)); - } - } else { - nfapi_sr_indication_t *dest_ind = &eNB->UL_INFO.sr_ind; - nfapi_sr_indication_pdu_t *dest_pdu_list = eNB->sr_pdu_list; - *dest_ind = *ind; - dest_ind->sr_indication_body.sr_pdu_list = dest_pdu_list; - LOG_D(MAC, - "%s() eNB->UL_INFO.sr_ind.sr_indication_body.number_of_srs:%d\n", - __FUNCTION__, - eNB->UL_INFO.sr_ind.sr_indication_body.number_of_srs); - - assert(eNB->UL_INFO.sr_ind.sr_indication_body.number_of_srs <= NFAPI_SR_IND_MAX_PDU); - for (int i = 0; i < eNB->UL_INFO.sr_ind.sr_indication_body.number_of_srs; i++) { - nfapi_sr_indication_pdu_t *dest_pdu = &dest_ind->sr_indication_body.sr_pdu_list[i]; - nfapi_sr_indication_pdu_t *src_pdu = &ind->sr_indication_body.sr_pdu_list[i]; - LOG_D(MAC, - "SR_IND[PDU:%d][rnti:%x cqi:%d channel:%d]\n", - i, - src_pdu->rx_ue_information.rnti, - src_pdu->ul_cqi_information.ul_cqi, - src_pdu->ul_cqi_information.channel); - memcpy(dest_pdu, src_pdu, sizeof(*src_pdu)); - } - } - AssertFatal(pthread_mutex_unlock(&eNB->UL_INFO_mutex) == 0, "Mutex unlock failed"); - // vnf_p7_info* p7_vnf = (vnf_p7_info*)(config->user_data); - // mac_sr_ind(p7_vnf->mac, ind); - return 1; -} - -static bool aerial_is_ue_same(uint16_t ue_id_1, uint16_t ue_id_2) -{ - return (ue_id_1 == ue_id_2); -} - -static void aerial_analyze_cqi_pdus_for_duplicates(nfapi_cqi_indication_t *ind) -{ - uint16_t num_cqis = ind->cqi_indication_body.number_of_cqis; - assert(num_cqis <= NFAPI_CQI_IND_MAX_PDU); - for (int i = 0; i < num_cqis; i++) { - nfapi_cqi_indication_pdu_t *src_pdu = &ind->cqi_indication_body.cqi_pdu_list[i]; - - LOG_I(MAC, - "CQI_IND[PDU:%d][rnti:%x cqi:%d channel:%d]\n", - i, - src_pdu->rx_ue_information.rnti, - src_pdu->ul_cqi_information.ul_cqi, - src_pdu->ul_cqi_information.channel); - - for (int j = i + 1; j < num_cqis; j++) { - uint16_t rnti_i = ind->cqi_indication_body.cqi_pdu_list[i].rx_ue_information.rnti; - uint16_t rnti_j = ind->cqi_indication_body.cqi_pdu_list[j].rx_ue_information.rnti; - if (aerial_is_ue_same(rnti_i, rnti_j)) { - LOG_E(MAC, "Problem, two cqis received from a single UE for rnti %x\n", rnti_i); - // abort(); This will be fixed in merge request which handles multiple CQIs. + if (uci_ind->uci_list[i].pdu_type == NFAPI_NR_UCI_FORMAT_2_3_4_PDU_TYPE) { + free(uci_ind->uci_list[i].pucch_pdu_format_2_3_4.harq.harq_payload); + free(uci_ind->uci_list[i].pucch_pdu_format_2_3_4.csi_part1.csi_part1_payload); + free(uci_ind->uci_list[i].pucch_pdu_format_2_3_4.csi_part2.csi_part2_payload); } } + free(uci_ind->uci_list); + uci_ind->uci_list = NULL; + free(uci_ind); + uci_ind = NULL; } -} - -int aerial_phy_cqi_indication(struct nfapi_vnf_p7_config *config, nfapi_cqi_indication_t *ind) -{ - // vnf_p7_info* p7_vnf = (vnf_p7_info*)(config->user_data); - // mac_cqi_ind(p7_vnf->mac, ind); - struct PHY_VARS_eNB_s *eNB = RC.eNB[0][0]; - LOG_D(MAC, - "%s() NFAPI SFN/SF:%d number_of_cqis:%u\n", - __FUNCTION__, - NFAPI_SFNSF2DEC(ind->sfn_sf), - ind->cqi_indication_body.number_of_cqis); - AssertFatal(pthread_mutex_lock(&eNB->UL_INFO_mutex) == 0, "Mutex lock failed"); - if (NFAPI_MODE == NFAPI_MODE_VNF) { - int8_t index = NFAPI_SFNSF2SF(ind->sfn_sf); - - UL_RCC_INFO.cqi_ind[index] = *ind; - assert(ind->cqi_indication_body.number_of_cqis <= NFAPI_CQI_IND_MAX_PDU); - if (ind->cqi_indication_body.number_of_cqis > 0) { - UL_RCC_INFO.cqi_ind[index].cqi_indication_body.cqi_pdu_list = - malloc(sizeof(nfapi_cqi_indication_pdu_t) * NFAPI_CQI_IND_MAX_PDU); - UL_RCC_INFO.cqi_ind[index].cqi_indication_body.cqi_raw_pdu_list = - malloc(sizeof(nfapi_cqi_indication_raw_pdu_t) * NFAPI_CQI_IND_MAX_PDU); - } - - aerial_analyze_cqi_pdus_for_duplicates(ind); - - assert(ind->cqi_indication_body.number_of_cqis <= NFAPI_CQI_IND_MAX_PDU); - for (int i = 0; i < ind->cqi_indication_body.number_of_cqis; i++) { - nfapi_cqi_indication_pdu_t *src_pdu = &ind->cqi_indication_body.cqi_pdu_list[i]; - LOG_D(MAC, - "SR_IND[PDU:%d][rnti:%x cqi:%d channel:%d]\n", - i, - src_pdu->rx_ue_information.rnti, - src_pdu->ul_cqi_information.ul_cqi, - src_pdu->ul_cqi_information.channel); - memcpy(&UL_RCC_INFO.cqi_ind[index].cqi_indication_body.cqi_pdu_list[i], src_pdu, sizeof(nfapi_cqi_indication_pdu_t)); - - memcpy(&UL_RCC_INFO.cqi_ind[index].cqi_indication_body.cqi_raw_pdu_list[i], - &ind->cqi_indication_body.cqi_raw_pdu_list[i], - sizeof(nfapi_cqi_indication_raw_pdu_t)); - } - } else { - nfapi_cqi_indication_t *dest_ind = &eNB->UL_INFO.cqi_ind; - *dest_ind = *ind; - dest_ind->cqi_indication_body.cqi_pdu_list = ind->cqi_indication_body.cqi_pdu_list; - dest_ind->cqi_indication_body.cqi_raw_pdu_list = ind->cqi_indication_body.cqi_raw_pdu_list; - assert(ind->cqi_indication_body.number_of_cqis <= NFAPI_CQI_IND_MAX_PDU); - for (int i = 0; i < ind->cqi_indication_body.number_of_cqis; i++) { - nfapi_cqi_indication_pdu_t *src_pdu = &ind->cqi_indication_body.cqi_pdu_list[i]; - LOG_D(MAC, - "CQI_IND[PDU:%d][rnti:%x cqi:%d channel:%d]\n", - i, - src_pdu->rx_ue_information.rnti, - src_pdu->ul_cqi_information.ul_cqi, - src_pdu->ul_cqi_information.channel); - memcpy(&dest_ind->cqi_indication_body.cqi_pdu_list[i], src_pdu, sizeof(nfapi_cqi_indication_pdu_t)); - memcpy(&dest_ind->cqi_indication_body.cqi_raw_pdu_list[i], - &ind->cqi_indication_body.cqi_raw_pdu_list[i], - sizeof(nfapi_cqi_indication_raw_pdu_t)); - } - } - AssertFatal(pthread_mutex_unlock(&eNB->UL_INFO_mutex) == 0, "Mutex unlock failed"); return 1; } -int aerial_phy_lbt_dl_indication(struct nfapi_vnf_p7_config *config, nfapi_lbt_dl_indication_t *ind) -{ - // vnf_p7_info* p7_vnf = (vnf_p7_info*)(config->user_data); - // mac_lbt_dl_ind(p7_vnf->mac, ind); - return 1; -} - -int aerial_phy_nb_harq_indication(struct nfapi_vnf_p7_config *config, nfapi_nb_harq_indication_t *ind) -{ - // vnf_p7_info* p7_vnf = (vnf_p7_info*)(config->user_data); - // mac_nb_harq_ind(p7_vnf->mac, ind); - return 1; -} - -int aerial_phy_nrach_indication(struct nfapi_vnf_p7_config *config, nfapi_nrach_indication_t *ind) -{ - // vnf_p7_info* p7_vnf = (vnf_p7_info*)(config->user_data); - // mac_nrach_ind(p7_vnf->mac, ind); - return 1; -} - - NR_Sched_Rsp_t g_sched_resp; void gNB_dlsch_ulsch_scheduler(module_id_t module_idP, frame_t frame, sub_frame_t slot, NR_Sched_Rsp_t* sched_info); int oai_fapi_dl_tti_req(nfapi_nr_dl_tti_request_t *dl_config_req); @@ -728,29 +273,26 @@ int trigger_scheduler(nfapi_nr_slot_indication_scf_t *slot_ind) // Call into the scheduler (this is hardcoded and should be init properly!) // memset(sched_resp, 0, sizeof(*sched_resp)); gNB_dlsch_ulsch_scheduler(0, slot_ind->sfn, slot_ind->slot, &g_sched_resp); - if (NFAPI_MODE == NFAPI_MODE_AERIAL) { -#ifdef ENABLE_AERIAL - bool send_slt_resp = false; - if (g_sched_resp.DL_req.dl_tti_request_body.nPDUs> 0) { - oai_fapi_dl_tti_req(&g_sched_resp.DL_req); - send_slt_resp = true; - } - if (g_sched_resp.UL_tti_req.n_pdus > 0) { - oai_fapi_ul_tti_req(&g_sched_resp.UL_tti_req); - send_slt_resp = true; - } - if (g_sched_resp.TX_req.Number_of_PDUs > 0) { - oai_fapi_tx_data_req(&g_sched_resp.TX_req); - send_slt_resp = true; - } - if (g_sched_resp.UL_dci_req.numPdus > 0) { - oai_fapi_ul_dci_req(&g_sched_resp.UL_dci_req); - send_slt_resp = true; - } - if (send_slt_resp) { - oai_fapi_send_end_request(0,slot_ind->sfn, slot_ind->slot); - } -#endif + + bool send_slt_resp = false; + if (g_sched_resp.DL_req.dl_tti_request_body.nPDUs> 0) { + oai_fapi_dl_tti_req(&g_sched_resp.DL_req); + send_slt_resp = true; + } + if (g_sched_resp.UL_tti_req.n_pdus > 0) { + oai_fapi_ul_tti_req(&g_sched_resp.UL_tti_req); + send_slt_resp = true; + } + if (g_sched_resp.TX_req.Number_of_PDUs > 0) { + oai_fapi_tx_data_req(&g_sched_resp.TX_req); + send_slt_resp = true; + } + if (g_sched_resp.UL_dci_req.numPdus > 0) { + oai_fapi_ul_dci_req(&g_sched_resp.UL_dci_req); + send_slt_resp = true; + } + if (send_slt_resp) { + oai_fapi_send_end_request(0,slot_ind->sfn, slot_ind->slot); } return 1; @@ -772,26 +314,10 @@ int aerial_phy_nr_slot_indication(nfapi_nr_slot_indication_scf_t *ind) int aerial_phy_nr_srs_indication(nfapi_nr_srs_indication_t *ind) { - struct PHY_VARS_gNB_s *gNB = RC.gNB[0]; - - gNB->UL_INFO.srs_ind = *ind; - - if (ind->number_of_pdus > 0) - gNB->UL_INFO.srs_ind.pdu_list = malloc(sizeof(nfapi_nr_srs_indication_pdu_t) * ind->number_of_pdus); - - for (int i = 0; i < ind->number_of_pdus; i++) { - memcpy(&gNB->UL_INFO.srs_ind.pdu_list[i], &ind->pdu_list[i], sizeof(ind->pdu_list[0])); - - LOG_D(MAC, - "%s() NFAPI SFN/Slot:%d.%d SRS_IND:number_of_pdus:%d UL_INFO:pdus:%d\n", - __FUNCTION__, - ind->sfn, - ind->slot, - ind->number_of_pdus, - gNB->UL_INFO.srs_ind.number_of_pdus); - } - - + // or queue to decouple, but I think it should be fast (in all likelihood, + // the VNF has nothing to do) + for (int i = 0; i < ind->number_of_pdus; ++i) + handle_nr_srs_measurements(0, ind->sfn, ind->slot, &ind->pdu_list[i]); return 1; } @@ -1314,4 +840,3 @@ int fapi_nr_pack_and_send_p7_message(vnf_p7_t *vnf_p7, nfapi_p7_message_header_t return aerial_send_P7_msg(FAPI_buffer, len_FAPI, header); } } -#endif diff --git a/nfapi/oai_integration/aerial/fapi_vnf_p7.h b/nfapi/oai_integration/aerial/fapi_vnf_p7.h index 7ea5e24569..404df347cc 100644 --- a/nfapi/oai_integration/aerial/fapi_vnf_p7.h +++ b/nfapi/oai_integration/aerial/fapi_vnf_p7.h @@ -30,7 +30,6 @@ * \warning */ -#ifdef ENABLE_AERIAL #ifndef OPENAIRINTERFACE_FAPI_VNF_P7_H #define OPENAIRINTERFACE_FAPI_VNF_P7_H @@ -180,21 +179,10 @@ typedef struct { } vnf_info; -int aerial_wake_gNB_rxtx(PHY_VARS_gNB *gNB, uint16_t sfn, uint16_t slot); -int aerial_wake_eNB_rxtx(PHY_VARS_eNB *eNB, uint16_t sfn, uint16_t sf); -int aerial_phy_sync_indication(struct nfapi_vnf_p7_config *config, uint8_t sync); -int aerial_phy_slot_indication(struct nfapi_vnf_p7_config *config, uint16_t phy_id, uint16_t sfn, uint16_t slot); -int aerial_phy_harq_indication(struct nfapi_vnf_p7_config *config, nfapi_harq_indication_t *ind); int aerial_phy_nr_crc_indication(nfapi_nr_crc_indication_t *ind); int aerial_phy_nr_rx_data_indication(nfapi_nr_rx_data_indication_t *ind); int aerial_phy_nr_rach_indication(nfapi_nr_rach_indication_t *ind); int aerial_phy_nr_uci_indication(nfapi_nr_uci_indication_t *ind); -int aerial_phy_srs_indication(struct nfapi_vnf_p7_config *config, nfapi_srs_indication_t *ind); -int aerial_phy_sr_indication(struct nfapi_vnf_p7_config *config, nfapi_sr_indication_t *ind); -int aerial_phy_cqi_indication(struct nfapi_vnf_p7_config *config, nfapi_cqi_indication_t *ind); -int aerial_phy_lbt_dl_indication(struct nfapi_vnf_p7_config *config, nfapi_lbt_dl_indication_t *ind); -int aerial_phy_nb_harq_indication(struct nfapi_vnf_p7_config *config, nfapi_nb_harq_indication_t *ind); -int aerial_phy_nrach_indication(struct nfapi_vnf_p7_config *config, nfapi_nrach_indication_t *ind); int aerial_phy_nr_slot_indication(nfapi_nr_slot_indication_scf_t *ind); int aerial_phy_nr_srs_indication(nfapi_nr_srs_indication_t *ind); void *aerial_vnf_allocate(size_t size); @@ -241,4 +229,3 @@ uint8_t aerial_unpack_nr_rach_indication(uint8_t **ppReadPackedMsg, // int fapi_nr_p7_message_pack(void *pMessageBuf, void *pPackedBuf, uint32_t packedBufLen, nfapi_p7_codec_config_t* config); int fapi_nr_pack_and_send_p7_message(vnf_p7_t *vnf_p7, nfapi_p7_message_header_t *header); #endif // OPENAIRINTERFACE_FAPI_VNF_P7_H -#endif diff --git a/nfapi/open-nFAPI/fapi/CMakeLists.txt b/nfapi/open-nFAPI/fapi/CMakeLists.txt index bd93d05447..1e2208172f 100644 --- a/nfapi/open-nFAPI/fapi/CMakeLists.txt +++ b/nfapi/open-nFAPI/fapi/CMakeLists.txt @@ -4,3 +4,6 @@ add_library(nr_fapi_p5 ) target_include_directories(nr_fapi_p5 PUBLIC inc) target_link_libraries(nr_fapi_p5 PUBLIC nfapi_common) +if(OAI_AERIAL) + target_compile_definitions(nr_fapi_p5 PRIVATE ENABLE_AERIAL) +endif() diff --git a/nfapi/open-nFAPI/fapi/src/nr_fapi_p5.c b/nfapi/open-nFAPI/fapi/src/nr_fapi_p5.c index 063f9589ef..295cca7a48 100644 --- a/nfapi/open-nFAPI/fapi/src/nr_fapi_p5.c +++ b/nfapi/open-nFAPI/fapi/src/nr_fapi_p5.c @@ -1227,6 +1227,29 @@ uint8_t pack_nr_config_request(void *msg, uint8_t **ppWritePackedMsg, uint8_t *e numTLVs++; } #endif + + AssertFatal(pNfapiMsg->analog_beamforming_ve.num_beams_period_vendor_ext.tl.tag == 0, "BF Vendor extension shouldn't be set!"); + // The call to pack the TLV would be the same as any other TLV, it is only packed if the tag is set, + // so, it's safe to add the call to pack_nr_tlv even if it is not always set + retval &= pack_nr_tlv(NFAPI_NR_FAPI_NUM_BEAMS_PERIOD_VENDOR_EXTENSION_TAG, + &(pNfapiMsg->analog_beamforming_ve.num_beams_period_vendor_ext), + ppWritePackedMsg, + end, + &pack_uint8_tlv_value); + // only increase if it was set + numTLVs += pNfapiMsg->analog_beamforming_ve.num_beams_period_vendor_ext.tl.tag == NFAPI_NR_FAPI_NUM_BEAMS_PERIOD_VENDOR_EXTENSION_TAG; + + AssertFatal(pNfapiMsg->analog_beamforming_ve.analog_bf_vendor_ext.tl.tag == 0, "BF Vendor extension shouldn't be set!"); + // The call to pack the TLV would be the same as any other TLV, it is only packed if the tag is set, + // so, it's safe to add the call to pack_nr_tlv even if it is not always set + retval &= pack_nr_tlv(NFAPI_NR_FAPI_ANALOG_BF_VENDOR_EXTENSION_TAG, + &(pNfapiMsg->analog_beamforming_ve.analog_bf_vendor_ext), + ppWritePackedMsg, + end, + &pack_uint8_tlv_value); + // only increase if it was set + numTLVs += pNfapiMsg->analog_beamforming_ve.analog_bf_vendor_ext.tl.tag == NFAPI_NR_FAPI_ANALOG_BF_VENDOR_EXTENSION_TAG; + pNfapiMsg->num_tlv = numTLVs; retval &= push8(pNfapiMsg->num_tlv, &pNumTLVFields, end); return retval; diff --git a/nfapi/open-nFAPI/nfapi/public_inc/nfapi_nr_interface.h b/nfapi/open-nFAPI/nfapi/public_inc/nfapi_nr_interface.h index a6ab614bde..4e9987b0cb 100644 --- a/nfapi/open-nFAPI/nfapi/public_inc/nfapi_nr_interface.h +++ b/nfapi/open-nFAPI/nfapi/public_inc/nfapi_nr_interface.h @@ -23,6 +23,8 @@ #define NFAPI_NR_NFAPI_TIMING_WINDOW_TAG 0x011E #define NFAPI_NR_NFAPI_TIMING_INFO_MODE_TAG 0x011F #define NFAPI_NR_NFAPI_TIMING_INFO_PERIOD_TAG 0x0120 +#define NFAPI_NR_FAPI_NUM_BEAMS_PERIOD_VENDOR_EXTENSION_TAG 0xA000 +#define NFAPI_NR_FAPI_ANALOG_BF_VENDOR_EXTENSION_TAG 0xA001 typedef enum { NFAPI_NR_CCE_REG_MAPPING_INTERLEAVED=1, diff --git a/nfapi/open-nFAPI/nfapi/public_inc/nfapi_nr_interface_scf.h b/nfapi/open-nFAPI/nfapi/public_inc/nfapi_nr_interface_scf.h index 08b7843ce4..dc2f8eef83 100644 --- a/nfapi/open-nFAPI/nfapi/public_inc/nfapi_nr_interface_scf.h +++ b/nfapi/open-nFAPI/nfapi/public_inc/nfapi_nr_interface_scf.h @@ -22,6 +22,8 @@ #define NFAPI_MAX_NUM_UCI_INDICATION 8 #define NFAPI_MAX_NUM_GROUPS 8 #define NFAPI_MAX_NUM_CB 8 +#define NFAPI_MAX_NUM_PRGS 1 +#define NFAPI_MAX_NUM_BG_IF 1 // Extension to the generic structures for single tlv values @@ -443,6 +445,27 @@ typedef struct } nfapi_nr_measurement_config_t; +//-----------------------// +//3.3.6 Storing Precoding and Beamforming Tables + +//table 3-32 + +typedef struct { + uint16_t dig_beam_weight_Re; + uint16_t dig_beam_weight_Im; +} nfapi_nr_txru_t; + +typedef struct { + uint16_t beam_idx; //0~65535 + nfapi_nr_txru_t *txru_list; +} nfapi_nr_dig_beam_t; + +typedef struct { + uint16_t num_dig_beams; //0~65535 + uint16_t num_txrus; //0~65535 + nfapi_nr_dig_beam_t *dig_beam_list; +} nfapi_nr_dbt_pdu_t; + // Table 3–62 Precoding matrix (PM) PDU (v.222.10.04) typedef struct { int16_t precoder_weight_Re; @@ -463,6 +486,11 @@ typedef struct { nfapi_nr_pm_pdu_t *pmi_pdu; } nfapi_nr_pm_list_t; +typedef struct { + nfapi_uint8_tlv_t num_beams_period_vendor_ext; + nfapi_uint8_tlv_t analog_bf_vendor_ext; +} nfapi_nr_analog_beamforming_ve_t; + // ERROR enums typedef enum { // Table 2-22 NFAPI_NR_PARAM_MSG_OK = 0, @@ -575,6 +603,8 @@ typedef struct { nfapi_nr_measurement_config_t measurement_config; nfapi_nr_nfapi_t nfapi_config; nfapi_nr_pm_list_t pmi_list; + nfapi_nr_dbt_pdu_t dbt_config; + nfapi_nr_analog_beamforming_ve_t analog_beamforming_ve; } nfapi_nr_config_request_scf_t; typedef enum { @@ -669,28 +699,6 @@ typedef struct { nfapi_nr_phy_notifications_errors_e error_code; } nfapi_nr_phy_notifications_error_indicate_t; -//-----------------------// -//3.3.6 Storing Precoding and Beamforming Tables - -//table 3-32 -//? -typedef struct { - uint16_t beam_idx; //0~65535 -} nfapi_nr_dig_beam_t; - -typedef struct { - uint16_t dig_beam_weight_Re; - uint16_t dig_beam_weight_Im; -} nfapi_nr_txru_t; - -typedef struct { - uint16_t num_dig_beams; //0~65535 - uint16_t num_txrus; //0~65535 - nfapi_nr_dig_beam_t* dig_beam_list; - nfapi_nr_txru_t* txru_list; -} nfapi_nr_dbt_pdu_t; - - // Section 3.4 // Section 3.4.1 slot indication @@ -719,7 +727,7 @@ typedef struct typedef struct { uint16_t pm_idx;//Index to precoding matrix (PM) pre-stored at cell configuration. Note: If precoding is not used this parameter should be set to 0. Value: 0->65535. - nfapi_nr_dig_bf_interface_t dig_bf_interface_list[1];//max dig_bf_interfaces + nfapi_nr_dig_bf_interface_t dig_bf_interface_list[NFAPI_MAX_NUM_BG_IF];//max dig_bf_interfaces }nfapi_nr_tx_precoding_and_beamforming_number_of_prgs_t; @@ -730,7 +738,7 @@ typedef struct uint16_t prg_size;//Size in RBs of a precoding resource block group (PRG) – to which same precoding and digital beamforming gets applied. Value: 1->275 //watchout: dig_bf_interfaces here, in table 3-53 it's dig_bf_interface uint8_t dig_bf_interfaces;//Number of STD ant ports (parallel streams) feeding into the digBF Value: 0->255 - nfapi_nr_tx_precoding_and_beamforming_number_of_prgs_t prgs_list[1];//max prg_size + nfapi_nr_tx_precoding_and_beamforming_number_of_prgs_t prgs_list[NFAPI_MAX_NUM_PRGS];//max prg_size }nfapi_nr_tx_precoding_and_beamforming_t; @@ -1135,7 +1143,7 @@ typedef struct { //for prach_pdu: typedef struct { - nfapi_nr_dig_bf_interface_t* dig_bf_interface_list; + nfapi_nr_dig_bf_interface_t dig_bf_interface_list[NFAPI_MAX_NUM_BG_IF]; } nfapi_nr_ul_beamforming_number_of_prgs_t; typedef struct @@ -1144,7 +1152,7 @@ typedef struct uint16_t num_prgs; // Number of PRGs spanning this allocation. Value : 1->275 uint16_t prg_size; // Size in RBs of a precoding resource block group (PRG) – to which the same digital beamforming gets applied. Value: 1->275 uint8_t dig_bf_interface; // Number of logical antenna ports (parallel streams) resulting from the Rx combining. Value: 0->255 - nfapi_nr_ul_beamforming_number_of_prgs_t *prgs_list; + nfapi_nr_ul_beamforming_number_of_prgs_t prgs_list[NFAPI_MAX_NUM_PRGS]; } nfapi_nr_ul_beamforming_t; typedef struct diff --git a/nfapi/open-nFAPI/nfapi/src/nfapi_p7.c b/nfapi/open-nFAPI/nfapi/src/nfapi_p7.c index 9622cd7f5e..bcaf7a524d 100644 --- a/nfapi/open-nFAPI/nfapi/src/nfapi_p7.c +++ b/nfapi/open-nFAPI/nfapi/src/nfapi_p7.c @@ -935,10 +935,6 @@ static uint8_t pack_ul_tti_request_prach_pdu(nfapi_nr_prach_pdu_t *prach_pdu, ui return 0; } - if (prach_pdu->beamforming.num_prgs > 0 || prach_pdu->beamforming.prg_size > 0 || prach_pdu->beamforming.dig_bf_interface > 0) { - AssertFatal(1 == 0, "PRACH PDU Beamforming not supported yet"); - } - // Pack RX Beamforming PDU if (!(push16(prach_pdu->beamforming.num_prgs, ppWritePackedMsg, end) && push16(prach_pdu->beamforming.prg_size, ppWritePackedMsg, end) @@ -4772,15 +4768,6 @@ static uint8_t unpack_ul_tti_request_prach_pdu(void *tlv, uint8_t **ppReadPacked && pull8(ppReadPackedMsg, &prach_pdu->beamforming.dig_bf_interface, end))) { return 0; } - if (prach_pdu->beamforming.num_prgs > 0) { - prach_pdu->beamforming.prgs_list = calloc(prach_pdu->beamforming.num_prgs, sizeof(*prach_pdu->beamforming.prgs_list)); - if (prach_pdu->beamforming.dig_bf_interface > 0) { - for(int prg_idx = 0; prg_idx < prach_pdu->beamforming.num_prgs;prg_idx++){ - prach_pdu->beamforming.prgs_list[prg_idx].dig_bf_interface_list = - calloc(prach_pdu->beamforming.dig_bf_interface, sizeof(*prach_pdu->beamforming.prgs_list[0].dig_bf_interface_list)); - } - } - } for (int prg = 0; prg < prach_pdu->beamforming.num_prgs; prg++) { for (int digBFInterface = 0; digBFInterface < prach_pdu->beamforming.dig_bf_interface; digBFInterface++) { if (!pull16(ppReadPackedMsg, &prach_pdu->beamforming.prgs_list[prg].dig_bf_interface_list[digBFInterface].beam_idx, end)) { diff --git a/openair1/PHY/INIT/nr_init.c b/openair1/PHY/INIT/nr_init.c index 68333c821c..57d9bbc8eb 100644 --- a/openair1/PHY/INIT/nr_init.c +++ b/openair1/PHY/INIT/nr_init.c @@ -41,7 +41,6 @@ #include "SCHED_NR/fapi_nr_l1.h" #include "PHY/NR_REFSIG/ul_ref_seq_nr.h" - int l1_north_init_gNB() { if (RC.nb_nr_L1_inst > 0 && RC.gNB != NULL) { @@ -104,7 +103,7 @@ void reset_active_stats(PHY_VARS_gNB *gNB, int frame) // A global var to reduce the changes size ldpc_interface_t ldpc_interface = {0}, ldpc_interface_offload = {0}; -int phy_init_nr_gNB(PHY_VARS_gNB *gNB) +void phy_init_nr_gNB(PHY_VARS_gNB *gNB) { // shortcuts NR_DL_FRAME_PARMS *const fp = &gNB->frame_parms; @@ -112,16 +111,24 @@ int phy_init_nr_gNB(PHY_VARS_gNB *gNB) NR_gNB_COMMON *const common_vars = &gNB->common_vars; NR_gNB_PRACH *const prach_vars = &gNB->prach_vars; - int i; - int Ptx=cfg->carrier_config.num_tx_ant.value; - int Prx=cfg->carrier_config.num_rx_ant.value; + common_vars->analog_bf = cfg->analog_beamforming_ve.analog_bf_vendor_ext.value; + LOG_I(PHY, "L1 configured with%s analog beamforming\n", common_vars->analog_bf ? "" : "out"); + if (common_vars->analog_bf) { + common_vars->num_beams_period = cfg->analog_beamforming_ve.num_beams_period_vendor_ext.value; + LOG_I(PHY, "Max number of concurrent beams: %d\n", common_vars->num_beams_period); + } else + common_vars->num_beams_period = 1; + + int Ptx = cfg->carrier_config.num_tx_ant.value; + int Prx = cfg->carrier_config.num_rx_ant.value; int max_ul_mimo_layers = 4; - AssertFatal(Ptx>0 && Ptx<9,"Ptx %d is not supported\n",Ptx); - AssertFatal(Prx>0 && Prx<9,"Prx %d is not supported\n",Prx); - LOG_I(PHY,"[gNB %d] %s() About to wait for gNB to be configured\n", gNB->Mod_id, __FUNCTION__); + AssertFatal(Ptx > 0 && Ptx < 9,"Ptx %d is not supported\n", Ptx); + AssertFatal(Prx > 0 && Prx < 9,"Prx %d is not supported\n", Prx); + LOG_I(PHY, "[gNB %d]About to wait for gNB to be configured\n", gNB->Mod_id); - while(gNB->configured == 0) usleep(10000); + while(gNB->configured == 0) + usleep(10000); load_dftslib(); @@ -150,10 +157,6 @@ int phy_init_nr_gNB(PHY_VARS_gNB *gNB) nr_generate_modulation_table(); nr_init_pbch_interleaver(gNB->nr_pbch_interleaver); - // CSI RS init - // ceil((NB_RB*8(max allocation per RB)*2(QPSK))/32) - gNB->nr_csi_info = (nr_csi_info_t *)malloc16_clear(sizeof(nr_csi_info_t)); - generate_ul_reference_signal_sequences(SHRT_MAX); /* Generate low PAPR type 1 sequences for PUSCH DMRS, these are used if transform precoding is enabled. */ @@ -172,19 +175,23 @@ int phy_init_nr_gNB(PHY_VARS_gNB *gNB) } } - common_vars->txdataF = (c16_t **)malloc16(Ptx*sizeof(c16_t*)); - common_vars->rxdataF = (c16_t **)malloc16(Prx*sizeof(c16_t*)); - /* Do NOT allocate per-antenna txdataF/rxdataF: the gNB gets a pointer to the + /* Do NOT allocate per-antenna rxdataF: the gNB gets a pointer to the * RU to copy/recover freq-domain memory from there */ - common_vars->beam_id = (uint8_t **)malloc16(Ptx*sizeof(uint8_t*)); + common_vars->rxdataF = (c16_t ***)malloc16(common_vars->num_beams_period * sizeof(c16_t**)); + for (int i = 0; i < common_vars->num_beams_period; i++) + common_vars->rxdataF[i] = (c16_t **)malloc16(Prx * sizeof(c16_t*)); - for (i=0;itxdataF[i] = (c16_t*)malloc16_clear(fp->samples_per_frame_wCP*sizeof(c16_t)); // [hna] samples_per_frame without CP - LOG_D(PHY,"[INIT] common_vars->txdataF[%d] = %p (%lu bytes)\n", - i,common_vars->txdataF[i], - fp->samples_per_frame_wCP*sizeof(c16_t)); - common_vars->beam_id[i] = (uint8_t*)malloc16_clear(fp->symbols_per_slot*fp->slots_per_frame*sizeof(uint8_t)); - memset(common_vars->beam_id[i],255,fp->symbols_per_slot*fp->slots_per_frame); + common_vars->num_beams = cfg->dbt_config.num_dig_beams; + if (common_vars->num_beams > 0) { + common_vars->beam_id = (int **)malloc16(common_vars->num_beams_period * sizeof(int*)); + for (int i = 0; i < common_vars->num_beams_period; i++) + common_vars->beam_id[i] = (int*)malloc16_clear(fp->symbols_per_slot * fp->slots_per_frame * sizeof(int)); + } + common_vars->txdataF = (c16_t ***)malloc16(common_vars->num_beams_period * sizeof(c16_t**)); + for (int i = 0; i < common_vars->num_beams_period; i++) { + common_vars->txdataF[i] = (c16_t**)malloc16_clear(Ptx * sizeof(c16_t*)); + for (int j = 0; j < Ptx; j++) + common_vars->txdataF[i][j] = (c16_t*)malloc16_clear(fp->samples_per_frame_wCP * sizeof(c16_t)); } common_vars->debugBuff = (int32_t*)malloc16_clear(fp->samples_per_frame*sizeof(int32_t)*100); common_vars->debugBuff_sample_offset = 0; @@ -209,14 +216,14 @@ int phy_init_nr_gNB(PHY_VARS_gNB *gNB) pusch->ul_ch_estimates_time = (int32_t **)malloc16(n_buf * sizeof(int32_t *)); pusch->rxdataF_comp = (int32_t **)malloc16(n_buf * sizeof(int32_t *)); pusch->llr_layers = (int16_t **)malloc16(max_ul_mimo_layers * sizeof(int32_t *)); - for (i = 0; i < n_buf; i++) { + for (int i = 0; i < n_buf; i++) { pusch->ul_ch_estimates[i] = (int32_t *)malloc16_clear(sizeof(int32_t) * fp->ofdm_symbol_size * fp->symbols_per_slot); pusch->ul_ch_estimates_time[i] = (int32_t *)malloc16_clear(sizeof(int32_t) * fp->ofdm_symbol_size); pusch->ptrs_phase_per_slot[i] = (int32_t *)malloc16_clear(sizeof(int32_t) * fp->symbols_per_slot); // symbols per slot pusch->rxdataF_comp[i] = (int32_t *)malloc16_clear(sizeof(int32_t) * nb_re_pusch2 * fp->symbols_per_slot); } - for (i=0; i< max_ul_mimo_layers; i++) { + for (int i = 0; i < max_ul_mimo_layers; i++) { pusch->llr_layers[i] = (int16_t *)malloc16_clear((8 * ((3 * 8 * 6144) + 12)) * sizeof(int16_t)); // [hna] 6144 is LTE and (8*((3*8*6144)+12)) is not clear } @@ -224,8 +231,6 @@ int phy_init_nr_gNB(PHY_VARS_gNB *gNB) * sizeof(int16_t)); // [hna] 6144 is LTE and (8*((3*8*6144)+12)) is not clear pusch->ul_valid_re_per_slot = (int16_t *)malloc16_clear(sizeof(int16_t) * fp->symbols_per_slot); } // ulsch_id - - return (0); } void phy_free_nr_gNB(PHY_VARS_gNB *gNB) @@ -241,8 +246,6 @@ void phy_free_nr_gNB(PHY_VARS_gNB *gNB) free_and_zero(meas->n0_subband_power); free_and_zero(meas->n0_subband_power_dB); - free_and_zero(gNB->nr_csi_info); - for (int id = 0; id < gNB->max_nb_srs; id++) { for(int i=0; inr_srs_info[id]->srs_generated_signal[i]); @@ -258,13 +261,19 @@ void phy_free_nr_gNB(PHY_VARS_gNB *gNB) reset_nr_transport(gNB); NR_gNB_COMMON * common_vars = &gNB->common_vars; - for (int i = 0; i < Ptx; i++) { - free_and_zero(common_vars->txdataF[i]); - free_and_zero(common_vars->beam_id[i]); + for (int j = 0; j < common_vars->num_beams_period; j++) { + if (common_vars->beam_id) + free_and_zero(common_vars->beam_id[j]); + for (int i = 0; i < Ptx; i++) { + free_and_zero(common_vars->txdataF[j][i]); + } + free_and_zero(common_vars->txdataF[j]); } /* Do NOT free per-antenna txdataF/rxdataF: the gNB gets a pointer to the * RU's txdataF/rxdataF, and the RU will free that */ + for (int j = 0; j < common_vars->num_beams_period; j++) + free_and_zero(common_vars->rxdataF[j]); free_and_zero(common_vars->txdataF); free_and_zero(common_vars->rxdataF); free_and_zero(common_vars->beam_id); @@ -495,7 +504,7 @@ void init_nr_transport(PHY_VARS_gNB *gNB) gNB->max_nb_pucch = buffer_ul_slots ? MAX_MOBILES_PER_GNB * buffer_ul_slots : 1; gNB->max_nb_pusch = buffer_ul_slots ? MAX_MOBILES_PER_GNB * buffer_ul_slots : 1; - gNB->max_nb_srs = buffer_ul_slots << 1; // assuming at most 2 SRS per slot + gNB->max_nb_srs = buffer_ul_slots ? buffer_ul_slots << 1 : 1; // assuming at most 2 SRS per slot gNB->pucch = (NR_gNB_PUCCH_t *)malloc16(gNB->max_nb_pucch * sizeof(NR_gNB_PUCCH_t)); for (int i = 0; i < gNB->max_nb_pucch; i++) { diff --git a/openair1/PHY/INIT/nr_init_ru.c b/openair1/PHY/INIT/nr_init_ru.c index a9f630198d..93b95b96eb 100644 --- a/openair1/PHY/INIT/nr_init_ru.c +++ b/openair1/PHY/INIT/nr_init_ru.c @@ -29,31 +29,35 @@ void init_prach_ru_list(RU_t *ru); -int nr_phy_init_RU(RU_t *ru) { - +int nr_phy_init_RU(RU_t *ru) +{ NR_DL_FRAME_PARMS *fp = ru->nr_frame_parms; - int i,j; - int p; - int re; LOG_I(PHY,"Initializing RU signal buffers (if_south %s) nb_tx %d, nb_rx %d\n",ru_if_types[ru->if_south],ru->nb_tx, ru->nb_rx); - nfapi_nr_config_request_scf_t *cfg; - ru->nb_log_antennas=0; - for (int n=0;nnum_gNB;n++) { - cfg = &ru->config; - if (cfg->carrier_config.num_tx_ant.value > ru->nb_log_antennas) ru->nb_log_antennas = cfg->carrier_config.num_tx_ant.value; + nfapi_nr_config_request_scf_t *cfg = &ru->config; + ru->nb_log_antennas = 0; + for (int n = 0; n < ru->num_gNB; n++) { + if (cfg->carrier_config.num_tx_ant.value > ru->nb_log_antennas) + ru->nb_log_antennas = cfg->carrier_config.num_tx_ant.value; } - // copy configuration from gNB[0] in to RU, assume that all gNB instances sharing RU use the same configuration (at least the parts that are needed by the RU, numerology and PRACH) + + // copy configuration from gNB[0] in to RU, assume that all gNB instances sharing RU use the same configuration + // (at least the parts that are needed by the RU, numerology and PRACH) AssertFatal(ru->nb_log_antennas > 0 && ru->nb_log_antennas < 13, "ru->nb_log_antennas %d ! \n",ru->nb_log_antennas); + + ru->common.beam_id = malloc16_clear(MAX_NUM_BEAM_PERIODS * sizeof(int*)); + for(int i = 0; i < MAX_NUM_BEAM_PERIODS; i++) + ru->common.beam_id[i] = malloc16_clear(fp->symbols_per_slot * fp->slots_per_frame * sizeof(int)); + if (ru->if_south <= REMOTE_IF5) { // this means REMOTE_IF5 or LOCAL_RF, so allocate memory for time-domain signals // Time-domain signals ru->common.txdata = (int32_t**)malloc16(ru->nb_tx*sizeof(int32_t*)); ru->common.rxdata = (int32_t**)malloc16(ru->nb_rx*sizeof(int32_t*) ); - for (i=0; inb_tx; i++) { + for (int i = 0; i < ru->nb_tx; i++) { // Allocate 10 subframes of I/Q TX signal data (time) if not ru->common.txdata[i] = (int32_t*)malloc16_clear((ru->sf_extension + fp->samples_per_frame)*sizeof(int32_t)); LOG_I(PHY,"[INIT] common.txdata[%d] = %p (%lu bytes,sf_extension %d)\n",i,ru->common.txdata[i], @@ -63,7 +67,7 @@ int nr_phy_init_RU(RU_t *ru) { LOG_I(PHY,"[INIT] common.txdata[%d] = %p \n",i,ru->common.txdata[i]); } - for (i=0;inb_rx;i++) { + for (int i = 0; i < ru->nb_rx; i++) { ru->common.rxdata[i] = (int32_t*)malloc16_clear( fp->samples_per_frame*sizeof(int32_t) ); } } // IF5 or local RF @@ -76,7 +80,7 @@ int nr_phy_init_RU(RU_t *ru) { if (ru->function != NGFI_RRU_IF5) { // we need to do RX/TX RU processing LOG_I(PHY,"nb_tx %d\n",ru->nb_tx); ru->common.rxdata_7_5kHz = (int32_t**)malloc16(ru->nb_rx*sizeof(int32_t*) ); - for (i=0;inb_rx;i++) { + for (int i = 0; i < ru->nb_rx; i++) { ru->common.rxdata_7_5kHz[i] = (int32_t*)malloc16_clear( 2*fp->samples_per_subframe*2*sizeof(int32_t) ); LOG_I(PHY,"rxdata_7_5kHz[%d] %p for RU %d\n",i,ru->common.rxdata_7_5kHz[i],ru->idx); } @@ -84,31 +88,33 @@ int nr_phy_init_RU(RU_t *ru) { // allocate precoding input buffers (TX) ru->common.txdataF = (int32_t **)malloc16(ru->nb_tx*sizeof(int32_t*)); - for(i=0; i< ru->nb_tx; ++i) ru->common.txdataF[i] = (int32_t*)malloc16_clear(fp->samples_per_frame_wCP*sizeof(int32_t)); // [hna] samples_per_frame without CP + // [hna] samples_per_frame without CP + for(int i = 0; i < ru->nb_tx; ++i) + ru->common.txdataF[i] = (int32_t*)malloc16_clear(fp->samples_per_frame_wCP * sizeof(int32_t)); // allocate IFFT input buffers (TX) ru->common.txdataF_BF = (int32_t **)malloc16(ru->nb_tx*sizeof(int32_t*)); - LOG_I(PHY,"[INIT] common.txdata_BF= %p (%lu bytes)\n",ru->common.txdataF_BF, - ru->nb_tx*sizeof(int32_t*)); - for (i=0; inb_tx; i++) { + LOG_I(PHY,"[INIT] common.txdata_BF= %p (%lu bytes)\n", ru->common.txdataF_BF, ru->nb_tx*sizeof(int32_t*)); + for (int i = 0; i < ru->nb_tx; i++) { ru->common.txdataF_BF[i] = (int32_t*)malloc16_clear(fp->samples_per_subframe_wCP*sizeof(int32_t) ); LOG_I(PHY,"txdataF_BF[%d] %p for RU %d\n",i,ru->common.txdataF_BF[i],ru->idx); } // allocate FFT output buffers (RX) ru->common.rxdataF = (int32_t**)malloc16(ru->nb_rx*sizeof(int32_t*) ); - for (i=0; inb_rx; i++) { + for (int i = 0; i < ru->nb_rx; i++) { // allocate 4 slots of I/Q signal data (frequency) - ru->common.rxdataF[i] = (int32_t*)malloc16_clear(sizeof(**ru->common.rxdataF)*(RU_RX_SLOT_DEPTH*fp->symbols_per_slot*fp->ofdm_symbol_size) ); + int size = RU_RX_SLOT_DEPTH * fp->symbols_per_slot * fp->ofdm_symbol_size; + ru->common.rxdataF[i] = (int32_t*)malloc16_clear(sizeof(**ru->common.rxdataF) * size); LOG_I(PHY,"rxdataF[%d] %p for RU %d\n",i,ru->common.rxdataF[i],ru->idx); } /* number of elements of an array X is computed as sizeof(X) / sizeof(X[0]) */ // AssertFatal(ru->nb_rx <= sizeof(ru->prach_rxsigF) / sizeof(ru->prach_rxsigF[0]), // "nb_antennas_rx too large"); - for (j=0;jprach_rxsigF[j] = (int16_t**)malloc(ru->nb_rx * sizeof(int16_t*)); - for (i=0; inb_rx; i++) { + for (int i = 0; i < ru->nb_rx; i++) { // largest size for PRACH FFT is 4x98304 (16*24576) ru->prach_rxsigF[j][i] = (int16_t*)malloc16_clear( 4*98304*2*sizeof(int16_t) ); LOG_D(PHY,"[INIT] prach_vars->rxsigF[%d] = %p\n",i,ru->prach_rxsigF[j][i]); @@ -120,44 +126,8 @@ int nr_phy_init_RU(RU_t *ru) { LOG_I(PHY,"[INIT] %s() ru->num_gNB:%d \n", __FUNCTION__, ru->num_gNB); - if (ru->do_precoding == 1) { - int beam_count = 0; - if (ru->nb_tx>1) { //Enable beamforming when nb_tx > 1 - - for (p=0;pnb_log_antennas;p++) { - //if ((fp->L_ssb >> (63-p)) & 0x01)//64 bit-map with the MSB @2⁶³ corresponds to SSB ssb_index 0 - beam_count++; - } - AssertFatal(ru->nb_bfw==(beam_count*ru->nb_tx),"Number of beam weights from config file is %d while the expected number is %d",ru->nb_bfw,(beam_count*ru->nb_tx)); - - for (i=0; inum_gNB; i++) { - int l_ind = 0; - for (p=0;pnb_log_antennas;p++) { - //if ((fp->L_ssb >> (63-p)) & 0x01) { - ru->beam_weights[i][p] = (int32_t **)malloc16_clear(ru->nb_tx*sizeof(int32_t*)); - for (j=0; jnb_tx; j++) { - ru->beam_weights[i][p][j] = (int32_t *)malloc16_clear(fp->ofdm_symbol_size*sizeof(int32_t)); - AssertFatal(ru->bw_list[i],"ru->bw_list[%d] is null\n",i); - for (re=0; reofdm_symbol_size; re++) - ru->beam_weights[i][p][j][re] = ru->bw_list[i][l_ind]; - //printf("Beam Weight %08x for beam %d and tx %d\n",ru->bw_list[i][l_ind],p,j); - l_ind++; - } // for j - //} - } // for p - } // for i - } - - ru->common.beam_id = (uint8_t**)malloc16_clear(ru->nb_tx*sizeof(uint8_t*)); - for(i=0; i< ru->nb_tx; ++i) { - ru->common.beam_id[i] = (uint8_t*)malloc16_clear(fp->symbols_per_slot*fp->slots_per_frame*sizeof(uint8_t)); - memset(ru->common.beam_id[i],255,fp->symbols_per_slot*fp->slots_per_frame); - } - } } // !=IF5 - ru->common.sync_corr = (uint32_t*)malloc16_clear( LTE_NUMBER_OF_SUBFRAMES_PER_FRAME*sizeof(uint32_t)*fp->samples_per_subframe_wCP ); - init_prach_ru_list(ru); return(0); @@ -165,56 +135,48 @@ int nr_phy_init_RU(RU_t *ru) { void nr_phy_free_RU(RU_t *ru) { - int i,j; - int p; - LOG_I(PHY, "Freeing RU signal buffers (if_south %s) nb_tx %d\n", ru_if_types[ru->if_south], ru->nb_tx); if (ru->if_south <= REMOTE_IF5) { // this means REMOTE_IF5 or LOCAL_RF, so free memory for time-domain signals // Hack: undo what is done at allocation - for (i = 0; i < ru->nb_tx; i++) { + for (int i = 0; i < ru->nb_tx; i++) { int32_t *p = &ru->common.txdata[i][-ru->sf_extension]; free_and_zero(p); } free_and_zero(ru->common.txdata); - for (i = 0; i < ru->nb_rx; i++) + for (int i = 0; i < ru->nb_rx; i++) free_and_zero(ru->common.rxdata[i]); free_and_zero(ru->common.rxdata); } // else: IF5 or local RF -> nothing to free() if (ru->function != NGFI_RRU_IF5) { // we need to do RX/TX RU processing - for (i = 0; i < ru->nb_rx; i++) free_and_zero(ru->common.rxdata_7_5kHz[i]); + for (int i = 0; i < ru->nb_rx; i++) + free_and_zero(ru->common.rxdata_7_5kHz[i]); free_and_zero(ru->common.rxdata_7_5kHz); // free beamforming input buffers (TX) - for (i = 0; i < ru->nb_tx; i++) free_and_zero(ru->common.txdataF[i]); + for (int i = 0; i < ru->nb_tx; i++) + free_and_zero(ru->common.txdataF[i]); free_and_zero(ru->common.txdataF); // free IFFT input buffers (TX) - for (i = 0; i < ru->nb_tx; i++) free_and_zero(ru->common.txdataF_BF[i]); + for (int i = 0; i < ru->nb_tx; i++) + free_and_zero(ru->common.txdataF_BF[i]); free_and_zero(ru->common.txdataF_BF); // free FFT output buffers (RX) - for (i = 0; i < ru->nb_rx; i++) free_and_zero(ru->common.rxdataF[i]); - free_and_zero(ru->common.rxdataF); + for (int i = 0; i < ru->nb_rx; i++) + free_and_zero(ru->common.rxdataF[i]); + free_and_zero(ru->common.rxdataF); - for (j=0;jnb_rx; i++) + for (int j = 0; j < NUMBER_OF_NR_RU_PRACH_OCCASIONS_MAX; j++) { + for (int i = 0; i < ru->nb_rx; i++) free_and_zero(ru->prach_rxsigF[j][i]); free_and_zero(ru->prach_rxsigF[j]); } - if (ru->do_precoding == 1) { - for (i = 0; i < ru->num_gNB; i++) { - for (p = 0; p < ru->nb_log_antennas; p++) { - for (j=0; jnb_tx; j++) free_and_zero(ru->beam_weights[i][p][j]); - free_and_zero(ru->beam_weights[i][p]); - } - } - for(i=0; i< ru->nb_tx; ++i) - free_and_zero(ru->common.beam_id[i]); - free_and_zero(ru->common.beam_id); - } + for(int i = 0; i < MAX_NUM_BEAM_PERIODS; ++i) + free_and_zero(ru->common.beam_id[i]); + free_and_zero(ru->common.beam_id); } - free_and_zero(ru->common.sync_corr); } diff --git a/openair1/PHY/INIT/nr_phy_init.h b/openair1/PHY/INIT/nr_phy_init.h index a6a7852d2c..d2c65e939f 100644 --- a/openair1/PHY/INIT/nr_phy_init.h +++ b/openair1/PHY/INIT/nr_phy_init.h @@ -38,7 +38,7 @@ void term_nr_ue_signal(PHY_VARS_NR_UE *ue, int nb_connected_gNB); void init_nr_ue_transport(PHY_VARS_NR_UE *ue); void init_N_TA_offset(PHY_VARS_NR_UE *ue); void nr_dump_frame_parms(NR_DL_FRAME_PARMS *frame_parms); -int phy_init_nr_gNB(PHY_VARS_gNB *gNB); +void phy_init_nr_gNB(PHY_VARS_gNB *gNB); int init_codebook_gNB(PHY_VARS_gNB *gNB); void nr_phy_config_request(NR_PHY_Config_t *gNB); void nr_phy_config_request_sim(PHY_VARS_gNB *gNB,int N_RB_DL,int N_RB_UL,int mu,int Nid_cell,uint64_t position_in_burst); diff --git a/openair1/PHY/MODULATION/beamforming.c b/openair1/PHY/MODULATION/beamforming.c index 12517d0a97..97bb9abb5b 100644 --- a/openair1/PHY/MODULATION/beamforming.c +++ b/openair1/PHY/MODULATION/beamforming.c @@ -137,32 +137,25 @@ int beam_precoding_one_eNB(int32_t **txdataF, } -int nr_beam_precoding(c16_t **txdataF, - c16_t **txdataF_BF, - NR_DL_FRAME_PARMS *frame_parms, - int32_t ***beam_weights, - int slot, - int symbol, - int aa, - int nb_antenna_ports, - int offset) +void nr_beam_precoding(c16_t **txdataF, + c16_t **txdataF_BF, + NR_DL_FRAME_PARMS *frame_parms, + int32_t ***beam_weights, + int slot, + int symbol, + int aa, + int nb_antenna_ports, + int offset) { - - - uint8_t p; - // clear txdata_BF[aa][re] for each call of ue_spec_beamforming memset(&txdataF_BF[aa][symbol*frame_parms->ofdm_symbol_size], 0, sizeof(c16_t) *(frame_parms->ofdm_symbol_size)); - for (p=0; pL_ssb >> (63-p)) & 0x01) { - multadd_cpx_vector((int16_t*)&txdataF[p][(symbol*frame_parms->ofdm_symbol_size)+offset], - (int16_t*)beam_weights[p][aa], - (int16_t*)&txdataF_BF[aa][symbol*frame_parms->ofdm_symbol_size], - 0, - frame_parms->ofdm_symbol_size, - 15); - //} + for (int p = 0; p < nb_antenna_ports; p++) { + multadd_cpx_vector((int16_t*)&txdataF[p][(symbol*frame_parms->ofdm_symbol_size)+offset], + (int16_t*)beam_weights[p][aa], + (int16_t*)&txdataF_BF[aa][symbol*frame_parms->ofdm_symbol_size], + 0, + frame_parms->ofdm_symbol_size, + 15); } - return 0; } diff --git a/openair1/PHY/MODULATION/nr_modulation.h b/openair1/PHY/MODULATION/nr_modulation.h index 0a43086733..f066a967b5 100644 --- a/openair1/PHY/MODULATION/nr_modulation.h +++ b/openair1/PHY/MODULATION/nr_modulation.h @@ -95,16 +95,15 @@ int nr_slot_fep_ul(NR_DL_FRAME_PARMS *frame_parms, */ void nr_dft(c16_t *z, c16_t *d, uint32_t Msc_PUSCH); -int nr_beam_precoding(c16_t **txdataF, - c16_t **txdataF_BF, - NR_DL_FRAME_PARMS *frame_parms, - int32_t ***beam_weights, - int slot, - int symbol, - int aa, - int nb_antenna_ports, - int offset -); +void nr_beam_precoding(c16_t **txdataF, + c16_t **txdataF_BF, + NR_DL_FRAME_PARMS *frame_parms, + int32_t ***beam_weights, + int slot, + int symbol, + int aa, + int nb_antenna_ports, + int offset); void apply_nr_rotation_TX(const NR_DL_FRAME_PARMS *fp, c16_t *txdataF, diff --git a/openair1/PHY/NR_ESTIMATION/nr_measurements_gNB.c b/openair1/PHY/NR_ESTIMATION/nr_measurements_gNB.c index e36471c25d..c55be480d7 100644 --- a/openair1/PHY/NR_ESTIMATION/nr_measurements_gNB.c +++ b/openair1/PHY/NR_ESTIMATION/nr_measurements_gNB.c @@ -119,7 +119,7 @@ void gNB_I0_measurements(PHY_VARS_gNB *gNB, int slot, int first_symb, int num_sy NR_DL_FRAME_PARMS *frame_parms = &gNB->frame_parms; NR_gNB_COMMON *common_vars = &gNB->common_vars; PHY_MEASUREMENTS_gNB *measurements = &gNB->measurements; - int rb, nb_symb[275]={0}; + int nb_symb[275]={0}; allocCast2D(n0_subband_power, unsigned int, @@ -135,20 +135,20 @@ void gNB_I0_measurements(PHY_VARS_gNB *gNB, int slot, int first_symb, int num_sy frame_parms->N_RB_UL, false); - for (int s=first_symb;s<(first_symb+num_symb);s++) { + // TODO modify the measurements to take into account concurrent beams + for (int s = first_symb; s < first_symb + num_symb; s++) { int offset0 = ((slot&3)*frame_parms->symbols_per_slot + s) * frame_parms->ofdm_symbol_size; - for (rb=0; rbN_RB_UL; rb++) { + for (int rb = 0; rb < frame_parms->N_RB_UL; rb++) { if ((rb_mask_ul[s][rb >> 5] & (1U << (rb & 31))) == 0 && // check that rb was not used in this subframe !(I0_SKIP_DC && rb == frame_parms->N_RB_UL >> 1)) { // skip middle PRB because of artificial noise possibly created by FFT int offset = offset0 + (frame_parms->first_carrier_offset + (rb*12))%frame_parms->ofdm_symbol_size; nb_symb[rb]++; - for (int aarx=0; aarxnb_antennas_rx; aarx++) { - c16_t *ul_ch = &common_vars->rxdataF[aarx][offset]; + for (int aarx = 0; aarx < frame_parms->nb_antennas_rx; aarx++) { + c16_t *ul_ch = &common_vars->rxdataF[0][aarx][offset]; int32_t signal_energy; - if (((frame_parms->N_RB_UL&1) == 1) && - (rb==(frame_parms->N_RB_UL>>1))) { + if (((frame_parms->N_RB_UL & 1) == 1) && (rb == (frame_parms->N_RB_UL >> 1))) { signal_energy = signal_energy_nodc(ul_ch, 6); - ul_ch = &common_vars->rxdataF[aarx][offset0]; + ul_ch = &common_vars->rxdataF[0][aarx][offset0]; signal_energy += signal_energy_nodc(ul_ch, 6); } else { signal_energy = signal_energy_nodc(ul_ch, 12); diff --git a/openair1/PHY/NR_ESTIMATION/nr_ul_channel_estimation.c b/openair1/PHY/NR_ESTIMATION/nr_ul_channel_estimation.c index 7a46cd1b20..b8b44eceb6 100644 --- a/openair1/PHY/NR_ESTIMATION/nr_ul_channel_estimation.c +++ b/openair1/PHY/NR_ESTIMATION/nr_ul_channel_estimation.c @@ -71,6 +71,7 @@ int nr_pusch_channel_estimation(PHY_VARS_gNB *gNB, unsigned short p, unsigned char symbol, int ul_id, + int beam_nb, unsigned short bwp_start_subcarrier, nfapi_nr_pusch_pdu_t *pusch_pdu, int *max_ch, @@ -153,7 +154,7 @@ int nr_pusch_channel_estimation(PHY_VARS_gNB *gNB, memset(delay, 0, sizeof(*delay)); for (int aarx=0; aarxframe_parms.nb_antennas_rx; aarx++) { - c16_t *rxdataF = (c16_t *)&gNB->common_vars.rxdataF[aarx][symbol_offset + slot_offset]; + c16_t *rxdataF = (c16_t *)&gNB->common_vars.rxdataF[beam_nb][aarx][symbol_offset + slot_offset]; c16_t *ul_ch = &ul_ch_estimates[nl * gNB->frame_parms.nb_antennas_rx + aarx][symbol_offset]; memset(ul_ch, 0, sizeof(*ul_ch) * symbolSize); @@ -596,17 +597,6 @@ void nr_pusch_ptrs_processing(PHY_VARS_gNB *gNB, } // Antenna loop } -uint32_t calc_power(const int16_t *x, const uint32_t size) { - int64_t sum_x = 0; - int64_t sum_x2 = 0; - for(int k = 0; knb_antennas_rx * N_ap * M_sc_b_SRS; - int16_t ch_real[arr_len]; - memset(ch_real, 0, arr_len * sizeof(int16_t)); - - int16_t ch_imag[arr_len]; - memset(ch_imag, 0, arr_len * sizeof(int16_t)); - - int16_t noise_real[arr_len]; - memset(noise_real, 0, arr_len * sizeof(int16_t)); - - int16_t noise_imag[arr_len]; - memset(noise_imag, 0, arr_len * sizeof(int16_t)); + c16_t ch[arr_len]; + memset(ch, 0, arr_len * sizeof(c16_t)); - int16_t ls_estimated[2]; + c16_t noise[arr_len]; + memset(noise, 0, arr_len * sizeof(c16_t)); uint8_t mem_offset = ((16 - ((long)&srs_estimated_channel_freq[0][0][subcarrier_offset + nr_srs_info->k_0_p[0][0]])) & 0xF) >> 2; // >> 2 <=> /sizeof(int32_t) // filt16_end is {4096,8192,8192,8192,12288,16384,16384,16384,0,0,0,0,0,0,0,0} // The End of OFDM symbol corresponds to the position of last 16384 in the filter - // The multadd_real_vector_complex_scalar applies the remaining 8 zeros of filter, therefore, to avoid a buffer overflow, + // The c16multaddVectRealComplex applies the remaining 8 zeros of filter, therefore, to avoid a buffer overflow, // we added 8 in the array size - int32_t srs_est[frame_parms->ofdm_symbol_size*(1<num_symbols) + mem_offset + 8] __attribute__ ((aligned(32))); + int32_t srs_est[frame_parms->ofdm_symbol_size * (1 << srs_pdu->num_symbols) + mem_offset + 8] __attribute__((aligned(32))); + c16_t ls_estimated = {0}; for (int ant = 0; ant < frame_parms->nb_antennas_rx; ant++) { @@ -681,14 +664,12 @@ int nr_srs_channel_estimation( subcarrier -= frame_parms->ofdm_symbol_size; } - int16_t *srs_estimated_channel16 = (int16_t *)&srs_est[subcarrier + mem_offset]; + c16_t *srs_estimated_channel16 = (c16_t *)&srs_est[subcarrier + mem_offset]; for (int k = 0; k < M_sc_b_SRS; k++) { if (k%fd_cdm==0) { - - ls_estimated[0] = 0; - ls_estimated[1] = 0; + ls_estimated = (c16_t){0, 0}; uint16_t subcarrier_cdm = subcarrier; for (int cdm_idx = 0; cdm_idx < fd_cdm; cdm_idx++) { @@ -700,8 +681,8 @@ int nr_srs_channel_estimation( // We know that nr_srs_info->srs_generated_signal_bits bits are enough to represent the generated_real and generated_imag. // So we only need a nr_srs_info->srs_generated_signal_bits shift to ensure that the result fits into 16 bits. - ls_estimated[0] += (int16_t)(((int32_t)generated_real*received_real + (int32_t)generated_imag*received_imag)>>nr_srs_info->srs_generated_signal_bits); - ls_estimated[1] += (int16_t)(((int32_t)generated_real*received_imag - (int32_t)generated_imag*received_real)>>nr_srs_info->srs_generated_signal_bits); + ls_estimated.r += (int16_t)(((int32_t)generated_real*received_real + (int32_t)generated_imag*received_imag)>>nr_srs_info->srs_generated_signal_bits); + ls_estimated.i += (int16_t)(((int32_t)generated_real*received_imag - (int32_t)generated_imag*received_real)>>nr_srs_info->srs_generated_signal_bits); // Subcarrier increment subcarrier_cdm += K_TC; @@ -711,8 +692,7 @@ int nr_srs_channel_estimation( } } - srs_ls_estimated_channel[subcarrier].r = ls_estimated[0]; - srs_ls_estimated_channel[subcarrier].i = ls_estimated[1]; + srs_ls_estimated_channel[subcarrier] = ls_estimated; #ifdef SRS_DEBUG int subcarrier_log = subcarrier-subcarrier_offset; @@ -727,48 +707,48 @@ int nr_srs_channel_estimation( subcarrier_log, ((c16_t*)srs_generated_signal[p_index])[subcarrier].r, ((c16_t*)srs_generated_signal[p_index])[subcarrier].i, ((c16_t*)srs_received_signal[ant])[subcarrier].r, ((c16_t*)srs_received_signal[ant])[subcarrier].i, - ls_estimated[0], ls_estimated[1]); + ls_estimated.r, ls_estimated.i); #endif const uint16_t sc_offset = subcarrier + mem_offset; // Channel interpolation - if(srs_pdu->comb_size == 0) { - if(k == 0) { // First subcarrier case + if (srs_pdu->comb_size == 0) { + if (k == 0) { // First subcarrier case // filt8_start is {12288,8192,4096,0,0,0,0,0} - multadd_real_vector_complex_scalar(filt8_start, ls_estimated, srs_estimated_channel16, 8); - } else if(subcarrier < K_TC) { // Start of OFDM symbol case + c16multaddVectRealComplex(filt8_start, &ls_estimated, srs_estimated_channel16, 8); + } else if (subcarrier < K_TC) { // Start of OFDM symbol case // filt8_start is {12288,8192,4096,0,0,0,0,0} - srs_estimated_channel16 = (int16_t *)&srs_est[subcarrier]; + srs_estimated_channel16 = (c16_t *)&srs_est[subcarrier]; const short *filter = mem_offset == 0 ? filt8_start : filt8_start_shift2; - multadd_real_vector_complex_scalar(filter, ls_estimated, srs_estimated_channel16, 8); - } else if((subcarrier+K_TC)>=frame_parms->ofdm_symbol_size || k == (M_sc_b_SRS-1)) { // End of OFDM symbol or last subcarrier cases + c16multaddVectRealComplex(filter, &ls_estimated, srs_estimated_channel16, 8); + } else if ((subcarrier + K_TC) >= frame_parms->ofdm_symbol_size || k == (M_sc_b_SRS - 1)) { // End of OFDM symbol or last subcarrier cases // filt8_end is {4096,8192,12288,16384,0,0,0,0} const short *filter = mem_offset == 0 || k == (M_sc_b_SRS - 1) ? filt8_end : filt8_end_shift2; - multadd_real_vector_complex_scalar(filter, ls_estimated, srs_estimated_channel16, 8); - } else if(k%2 == 1) { // 1st middle case + c16multaddVectRealComplex(filter, &ls_estimated, srs_estimated_channel16, 8); + } else if (k % 2 == 1) { // 1st middle case // filt8_middle2 is {4096,8192,8192,8192,4096,0,0,0} - multadd_real_vector_complex_scalar(filt8_middle2, ls_estimated, srs_estimated_channel16, 8); - } else if(k%2 == 0) { // 2nd middle case + c16multaddVectRealComplex(filt8_middle2, &ls_estimated, srs_estimated_channel16, 8); + } else if (k % 2 == 0) { // 2nd middle case // filt8_middle4 is {0,0,4096,8192,8192,8192,4096,0} - multadd_real_vector_complex_scalar(filt8_middle4, ls_estimated, srs_estimated_channel16, 8); - srs_estimated_channel16 = (int16_t *)&srs_est[sc_offset]; + c16multaddVectRealComplex(filt8_middle4, &ls_estimated, srs_estimated_channel16, 8); + srs_estimated_channel16 = (c16_t *)&srs_est[sc_offset]; } } else { - if(k == 0) { // First subcarrier case + if (k == 0) { // First subcarrier case // filt16_start is {12288,8192,8192,8192,4096,0,0,0,0,0,0,0,0,0,0,0} - multadd_real_vector_complex_scalar(filt16_start, ls_estimated, srs_estimated_channel16, 16); - } else if(subcarrier < K_TC) { // Start of OFDM symbol case - srs_estimated_channel16 = (int16_t *)&srs_est[sc_offset]; + c16multaddVectRealComplex(filt16_start, &ls_estimated, srs_estimated_channel16, 16); + } else if (subcarrier < K_TC) { // Start of OFDM symbol case + srs_estimated_channel16 = (c16_t *)&srs_est[sc_offset]; // filt16_start is {12288,8192,8192,8192,4096,0,0,0,0,0,0,0,0,0,0,0} - multadd_real_vector_complex_scalar(filt16_start, ls_estimated, srs_estimated_channel16, 16); - } else if((subcarrier+K_TC)>=frame_parms->ofdm_symbol_size || k == (M_sc_b_SRS-1)) { // End of OFDM symbol or last subcarrier cases + c16multaddVectRealComplex(filt16_start, &ls_estimated, srs_estimated_channel16, 16); + } else if ((subcarrier + K_TC) >= frame_parms->ofdm_symbol_size || k == (M_sc_b_SRS - 1)) { // End of OFDM symbol or last subcarrier cases // filt16_end is {4096,8192,8192,8192,12288,16384,16384,16384,0,0,0,0,0,0,0,0} - multadd_real_vector_complex_scalar(filt16_end, ls_estimated, srs_estimated_channel16, 16); + c16multaddVectRealComplex(filt16_end, &ls_estimated, srs_estimated_channel16, 16); } else { // Middle case // filt16_middle4 is {4096,8192,8192,8192,8192,8192,8192,8192,4096,0,0,0,0,0,0,0} - multadd_real_vector_complex_scalar(filt16_middle4, ls_estimated, srs_estimated_channel16, 16); - srs_estimated_channel16 = (int16_t *)&srs_est[sc_offset]; + c16multaddVectRealComplex(filt16_middle4, &ls_estimated, srs_estimated_channel16, 16); + srs_estimated_channel16 = (c16_t *)&srs_est[sc_offset]; } } @@ -789,15 +769,14 @@ int nr_srs_channel_estimation( if (subcarrier>frame_parms->ofdm_symbol_size) { subcarrier -= frame_parms->ofdm_symbol_size; } - uint16_t base_idx = ant*N_ap*M_sc_b_SRS + p_index*M_sc_b_SRS; + uint16_t base_idx = ant * N_ap * M_sc_b_SRS + p_index * M_sc_b_SRS; for (int k = 0; k < M_sc_b_SRS; k++) { - ch_real[base_idx+k] = ((c16_t*)srs_estimated_channel_freq[ant][p_index])[subcarrier].r; - ch_imag[base_idx+k] = ((c16_t*)srs_estimated_channel_freq[ant][p_index])[subcarrier].i; - noise_real[base_idx+k] = abs(srs_ls_estimated_channel[subcarrier].r - ch_real[base_idx+k]); - noise_imag[base_idx+k] = abs(srs_ls_estimated_channel[subcarrier].i - ch_imag[base_idx+k]); + ch[base_idx + k] = ((c16_t *)srs_estimated_channel_freq[ant][p_index])[subcarrier]; + noise[base_idx + k].r = abs(srs_ls_estimated_channel[subcarrier].r - ch[base_idx + k].r); + noise[base_idx + k].i = abs(srs_ls_estimated_channel[subcarrier].i - ch[base_idx + k].i); subcarrier += K_TC; if (subcarrier >= frame_parms->ofdm_symbol_size) { - subcarrier=subcarrier-frame_parms->ofdm_symbol_size; + subcarrier = subcarrier - frame_parms->ofdm_symbol_size; } } @@ -823,9 +802,10 @@ int nr_srs_channel_estimation( subcarrier_log, srs_ls_estimated_channel[subcarrier].r, srs_ls_estimated_channel[subcarrier].i, - ((c16_t*)srs_estimated_channel_freq[ant][p_index])[subcarrier].r, - ((c16_t*)srs_estimated_channel_freq[ant][p_index])[subcarrier].i, - noise_real[base_idx+(k/K_TC)], noise_imag[base_idx+(k/K_TC)]); + ((c16_t *)srs_estimated_channel_freq[ant][p_index])[subcarrier].r, + ((c16_t *)srs_estimated_channel_freq[ant][p_index])[subcarrier].i, + noise[base_idx + (k / K_TC)].r, + noise[base_idx + (k / K_TC)].i); // Subcarrier increment subcarrier++; @@ -852,7 +832,7 @@ int nr_srs_channel_estimation( } // for (int ant = 0; ant < frame_parms->nb_antennas_rx; ant++) // Compute signal power - uint32_t signal_power = calc_power(ch_real, arr_len) + calc_power(ch_imag, arr_len); + uint32_t signal_power = max(signal_energy_nodc(ch, arr_len), 1); #ifdef SRS_DEBUG LOG_I(NR_PHY,"signal_power = %u\n", signal_power); @@ -864,11 +844,6 @@ int nr_srs_channel_estimation( } // Compute noise power - - const uint8_t signal_power_bits = log2_approx(signal_power); - const uint8_t factor_bits = signal_power_bits < 32 ? 32 - signal_power_bits : 0; // 32 due to input of dB_fixed(uint32_t x) - const int32_t factor_dB = dB_fixed(1<comb_size == 0 ? 6 : 3; const uint8_t n_noise_est = frame_parms->nb_antennas_rx*N_ap*srs_symbols_per_rb; uint64_t sum_re = 0; @@ -885,19 +860,19 @@ int nr_srs_channel_estimation( for (int ant = 0; ant < frame_parms->nb_antennas_rx; ant++) { for (int p_index = 0; p_index < N_ap; p_index++) { - uint16_t base_idx = ant*N_ap*M_sc_b_SRS + p_index*M_sc_b_SRS + rb*srs_symbols_per_rb; + uint16_t base_idx = ant * N_ap * M_sc_b_SRS + p_index * M_sc_b_SRS + rb * srs_symbols_per_rb; for (int srs_symb = 0; srs_symb < srs_symbols_per_rb; srs_symb++) { - sum_re = sum_re + noise_real[base_idx+srs_symb]; - sum_re2 = sum_re2 + noise_real[base_idx+srs_symb]*noise_real[base_idx+srs_symb]; - sum_im = sum_im + noise_imag[base_idx+srs_symb]; - sum_im2 = sum_im2 + noise_imag[base_idx+srs_symb]*noise_imag[base_idx+srs_symb]; + sum_re = sum_re + noise[base_idx + srs_symb].r; + sum_re2 = sum_re2 + noise[base_idx + srs_symb].r * noise[base_idx + srs_symb].r; + sum_im = sum_im + noise[base_idx + srs_symb].i; + sum_im2 = sum_im2 + noise[base_idx + srs_symb].i * noise[base_idx + srs_symb].i; } // for (int srs_symb = 0; srs_symb < srs_symbols_per_rb; srs_symb++) } // for (int p_index = 0; p_index < N_ap; p_index++) } // for (int ant = 0; ant < frame_parms->nb_antennas_rx; ant++) noise_power_per_rb[rb] = max(sum_re2 / n_noise_est - (sum_re / n_noise_est) * (sum_re / n_noise_est) + sum_im2 / n_noise_est - (sum_im / n_noise_est) * (sum_im / n_noise_est), 1); - snr_per_rb[rb] = dB_fixed((int32_t)((signal_power<subcarrier_spacing = %i\n", csi_params->subcarrier_spacing); @@ -56,405 +48,34 @@ void nr_generate_csi_rs(const NR_DL_FRAME_PARMS *frame_parms, LOG_I(NR_PHY, "csi_params->power_control_offset_ss = %i\n", csi_params->power_control_offset_ss); #endif - int dataF_offset = slot * frame_parms->samples_per_slot_wCP; - //*8(max allocation per RB)*2(QPSK)) - int csi_rs_length = frame_parms->N_RB_DL << 4; - int16_t mod_csi[frame_parms->symbols_per_slot][csi_rs_length>>1] __attribute__((aligned(16))); - uint16_t b = csi_params->freq_domain; - uint32_t beta = amp; - nr_csi_info->csi_rs_generated_signal_bits = log2_approx(amp); - - AssertFatal(b != 0, "Invalid CSI frequency domain mapping: no bit selected in bitmap\n"); - int size, ports, kprime, lprime; - int j[16], k_n[6], koverline[16], loverline[16]; - int found = 0; - int fi = 0; - // implementation of table 7.4.1.5.3-1 of 38.211 - // lprime and kprime are the max value of l' and k' - switch (csi_params->row) { - case 1: - ports = 1; - kprime = 0; - lprime = 0; - size = 3; - while (found < 1) { - if ((b >> fi) & 0x01) { - k_n[found] = fi; - found++; - } - else - fi++; - } - for (int i = 0; i < size; i++) { - j[i] = 0; - loverline[i] = csi_params->symb_l0; - koverline[i] = k_n[0] + (i<<2); - } - break; - case 2: - ports = 1; - kprime = 0; - lprime = 0; - size = 1; - while (found < 1) { - if ((b >> fi) & 0x01) { - k_n[found] = fi; - found++; - } - else - fi++; - } - for (int i = 0; i < size; i++) { - j[i] = 0; - loverline[i] = csi_params->symb_l0; - koverline[i] = k_n[0]; - } - break; - case 3: - ports = 2; - kprime = 1; - lprime = 0; - size = 1; - while (found < 1) { - if ((b >> fi) & 0x01) { - k_n[found] = fi << 1; - found++; - } - else - fi++; - } - for (int i = 0; i < size; i++) { - j[i] = 0; - loverline[i] = csi_params->symb_l0; - koverline[i] = k_n[0]; - } - break; - case 4: - ports = 4; - kprime = 1; - lprime = 0; - size = 2; - while (found < 1) { - if ((b >> fi) & 0x01) { - k_n[found] = fi << 2; - found++; - } - else - fi++; - } - for (int i = 0; i < size; i++) { - j[i] = i; - loverline[i] = csi_params->symb_l0; - koverline[i] = k_n[0] + (i << 1); - } - break; - case 5: - ports = 4; - kprime = 1; - lprime = 0; - size = 2; - while (found < 1) { - if ((b >> fi) & 0x01) { - k_n[found] = fi << 1; - found++; - } - else - fi++; - } - for (int i = 0; i < size; i++) { - j[i] = i; - loverline[i] = csi_params->symb_l0 + i; - koverline[i] = k_n[0]; - } - break; - case 6: - ports = 8; - kprime = 1; - lprime = 0; - size = 4; - while (found < 4) { - if ((b >> fi) & 0x01) { - k_n[found] = fi << 1; - found++; - } - fi++; - } - for (int i = 0; i < size; i++) { - j[i] = i; - loverline[i] = csi_params->symb_l0; - koverline[i] = k_n[i]; - } - break; - case 7: - ports = 8; - kprime = 1; - lprime = 0; - size = 4; - while (found < 2) { - if ((b >> fi) & 0x01) { - k_n[found] = fi << 1; - found++; - } - fi++; - } - for (int i = 0; i < size; i++) { - j[i] = i; - loverline[i] = csi_params->symb_l0 + (i >> 1); - koverline[i] = k_n[i % 2]; - } - break; - case 8: - ports = 8; - kprime = 1; - lprime = 1; - size = 2; - while (found < 2) { - if ((b >> fi) & 0x01) { - k_n[found] = fi << 1; - found++; - } - fi++; - } - for (int i = 0; i < size; i++) { - j[i] = i; - loverline[i] = csi_params->symb_l0; - koverline[i] = k_n[i]; - } - break; - case 9: - ports = 12; - kprime = 1; - lprime = 0; - size = 6; - while (found < 6) { - if ((b >> fi) & 0x01) { - k_n[found] = fi << 1; - found++; - } - fi++; - } - for (int i = 0; i < size; i++) { - j[i] = i; - loverline[i] = csi_params->symb_l0; - koverline[i] = k_n[i]; - } - break; - case 10: - ports = 12; - kprime = 1; - lprime = 1; - size = 3; - while (found < 3) { - if ((b >> fi) & 0x01) { - k_n[found] = fi << 1; - found++; - } - fi++; - } - for (int i = 0; i < size; i++) { - j[i] = i; - loverline[i] = csi_params->symb_l0; - koverline[i] = k_n[i]; - } - break; - case 11: - ports = 16; - kprime = 1; - lprime = 0; - size = 8; - while (found < 4) { - if ((b >> fi) & 0x01) { - k_n[found] = fi << 1; - found++; - } - fi++; - } - for (int i = 0; i < size; i++) { - j[i] = i; - loverline[i] = csi_params->symb_l0 + (i >> 2); - koverline[i] = k_n[i % 4]; - } - break; - case 12: - ports = 16; - kprime = 1; - lprime = 1; - size = 4; - while (found < 4) { - if ((b >> fi) & 0x01) { - k_n[found] = fi << 1; - found++; - } - fi++; - } - for (int i = 0; i < size; i++) { - j[i] = i; - loverline[i] = csi_params->symb_l0; - koverline[i] = k_n[i]; - } - break; - case 13: - ports = 24; - kprime = 1; - lprime = 0; - size = 12; - while (found < 3) { - if ((b >> fi) & 0x01) { - k_n[found] = fi << 1; - found++; - } - fi++; - } - for (int i = 0; i < size; i++) { - j[i] = i; - if (i < 6) - loverline[i] = csi_params->symb_l0 + i / 3; - else - loverline[i] = csi_params->symb_l1 + i / 9; - koverline[i] = k_n[i % 3]; - } - break; - case 14: - ports = 24; - kprime = 1; - lprime = 1; - size = 6; - while (found < 3) { - if ((b >> fi) & 0x01) { - k_n[found] = fi << 1; - found++; - } - fi++; - } - for (int i = 0; i < size; i++) { - j[i] = i; - if (i < 3) - loverline[i] = csi_params->symb_l0; - else - loverline[i] = csi_params->symb_l1; - koverline[i] = k_n[i%3]; - } - break; - case 15: - ports = 24; - kprime = 1; - lprime = 3; - size = 3; - while (found < 3) { - if ((b >> fi) & 0x01) { - k_n[found] = fi << 1; - found++; - } - fi++; - } - for (int i = 0; i < size; i++) { - j[i] = i; - loverline[i] = csi_params->symb_l0; - koverline[i] = k_n[i]; - } - break; - case 16: - ports = 32; - kprime = 1; - lprime = 0; - size = 16; - while (found < 4) { - if ((b >> fi) & 0x01) { - k_n[found] = fi << 1; - found++; - } - fi++; - } - for (int i = 0; i < size; i++) { - j[i] = i; - if (i < 8) - loverline[i] = csi_params->symb_l0 + (i>>2); - else - loverline[i] = csi_params->symb_l1 + (i/12); - koverline[i] = k_n[i % 4]; - } - break; - case 17: - ports = 32; - kprime = 1; - lprime = 1; - size = 8; - while (found < 4) { - if ((b >> fi) & 0x01) { - k_n[found] = fi << 1; - found++; - } - fi++; - } - for (int i = 0; i < size; i++) { - j[i] = i; - if (i < 4) - loverline[i] = csi_params->symb_l0; - else - loverline[i] = csi_params->symb_l1; - koverline[i] = k_n[i % 4]; - } - break; - case 18: - ports = 32; - kprime = 1; - lprime = 3; - size = 4; - while (found < 4) { - if ((b >> fi) & 0x01) { - k_n[found] = fi << 1; - found++; - } - fi++; - } - for (int i = 0; i < size; i++) { - j[i] = i; - loverline[i] = csi_params->symb_l0; - koverline[i] = k_n[i]; - } - break; - default: - AssertFatal(false, "Row %d is not valid for CSI Table 7.4.1.5.3-1\n", csi_params->row); - } + // setting the frequency density from its index + double rho = get_csi_rho(csi_params->freq_density); + int csi_length = get_csi_modulation_length(rho, + csi_params->freq_density, + phy_csi_parms->kprime, + csi_params->start_rb, + csi_params->nr_of_rbs); #ifdef NR_CSIRS_DEBUG - printf(" row %d, n. of ports %d\n k' ",csi_params->row,ports); - for (int kp = 0; kp <= kprime; kp++) - printf("%d, ",kp); - printf("l' "); - for (int lp = 0; lp <= lprime; lp++) - printf("%d, ", lp); - printf("\n k overline "); - for (int i = 0; i < size; i++) - printf("%d, ",koverline[i]); - printf("\n l overline "); - for (int i = 0; i < size; i++) - printf("%d, ",loverline[i]); - printf("\n"); + printf(" start rb %d, nr of rbs %d, csi length %d\n", csi_params->start_rb, csi_params->nr_of_rbs, csi_length); #endif + //*8(max allocation per RB)*2(QPSK)) + int16_t mod_csi[frame_parms->symbols_per_slot][(frame_parms->N_RB_DL << 4) >> 1] __attribute__((aligned(16))); + get_modulated_csi_symbols(frame_parms->symbols_per_slot, + slot, + frame_parms->N_RB_DL, + csi_length, + mod_csi, + phy_csi_parms->lprime, + csi_params->symb_l0, + csi_params->symb_l1, + csi_params->row, + csi_params->scramb_id); - // setting the frequency density from its index - double rho = 0; - switch (csi_params->freq_density) { - case 0: - rho = 0.5; - break; - case 1: - rho = 0.5; - break; - case 2: - rho = 1; - break; - case 3: - rho = 3; - break; - default: - AssertFatal(false, "Invalid frequency density index for CSI\n"); - } - + uint32_t beta = get_csi_beta_amplitude(amp, csi_params->power_control_offset_ss); double alpha = 0; - if (ports == 1) + if (phy_csi_parms->ports == 1) alpha = rho; else alpha = 2 * rho; @@ -464,167 +85,22 @@ void nr_generate_csi_rs(const NR_DL_FRAME_PARMS *frame_parms, #endif // CDM group size from CDM type index - int gs = 0; - switch (csi_params->cdm_type) { - case 0: - gs = 1; - break; - case 1: - gs = 2; - break; - case 2: - gs = 4; - break; - case 3: - gs = 8; - break; - default: - AssertFatal(false, "Invalid cdm type index for CSI\n"); - } + int gs = get_cdm_group_size(csi_params->cdm_type); - int csi_length; - if (rho < 1) { - if (csi_params->freq_density == 0) { - csi_length = (((csi_params->start_rb + csi_params->nr_of_rbs) >> 1) << kprime) << 1; - } else { - csi_length = ((((csi_params->start_rb + csi_params->nr_of_rbs) >> 1) << kprime) + 1) << 1; - } - } else { - csi_length = (((uint16_t) rho * (csi_params->start_rb + csi_params->nr_of_rbs)) << kprime) << 1; - } + int dataF_offset = slot * frame_parms->samples_per_slot_wCP; -#ifdef NR_CSIRS_DEBUG - printf(" start rb %d, nr of rbs %d, csi length %d\n", csi_params->start_rb, csi_params->nr_of_rbs, csi_length); -#endif - - if (N_cdm_groups) - *N_cdm_groups = size; - if (CDM_group_size) - *CDM_group_size = gs; - if (k_prime) - *k_prime = kprime; - if (l_prime) - *l_prime = lprime; - if (N_ports) - *N_ports = ports; - if (j_cdm) - memcpy(j_cdm, j, 16 * sizeof(uint8_t)); - if (k_overline) - memcpy(k_overline, koverline, 16 * sizeof(uint8_t)); - if (l_overline) - memcpy(l_overline, loverline, 16 * sizeof(uint8_t)); - -#ifdef NR_CSIRS_DEBUG - if (N_ports) - LOG_I(NR_PHY, "nr_csi_info->N_ports = %d\n", *N_ports); - if (N_cdm_groups) - LOG_I(NR_PHY, "nr_csi_info->N_cdm_groups = %d\n", *N_cdm_groups); - if (CDM_group_size) - LOG_I(NR_PHY, "nr_csi_info->CDM_group_size = %d\n", *CDM_group_size); - if (k_prime) - LOG_I(NR_PHY, "nr_csi_info->kprime = %d\n", *k_prime); - if (l_prime) - LOG_I(NR_PHY, "nr_csi_info->lprime = %d\n", *l_prime); - if (N_cdm_groups) { - for(int ji = 0; ji < *N_cdm_groups; ji++) { - LOG_I(NR_PHY, "(CDM group %d) j = %d, koverline = %d, loverline = %d\n", ji, j[ji], koverline[ji], loverline[ji]); - } - } -#endif - - if (csi_params->csi_type == 2) // ZP-CSI - return; - - // assuming amp is the amplitude of SSB channels - switch (csi_params->power_control_offset_ss) { - case 0: - beta = (amp*ONE_OVER_SQRT2_Q15)>>15; - break; - case 1: - beta = amp; - break; - case 2: - beta = (amp*ONE_OVER_SQRT2_Q15)>>14; - break; - case 3: - beta = amp << 1; - break; - default: - AssertFatal(false, "Invalid SS power offset density index for CSI\n"); - } - - for (int lp = 0; lp <= lprime; lp++) { - int symb = csi_params->symb_l0; - const uint32_t *gold = - nr_gold_csi_rs(frame_parms->N_RB_DL, frame_parms->symbols_per_slot, slot, symb + lp, csi_params->scramb_id); - nr_modulation(gold, csi_length, DMRS_MOD_ORDER, mod_csi[symb + lp]); - uint8_t row = csi_params->row; - if ((row == 5) || (row == 7) || (row == 11) || (row == 13) || (row == 16)) { - const uint32_t *gold = - nr_gold_csi_rs(frame_parms->N_RB_DL, frame_parms->symbols_per_slot, slot, symb + 1, csi_params->scramb_id); - nr_modulation(gold, csi_length, DMRS_MOD_ORDER, mod_csi[symb + 1]); - } - if ((row == 14) || (row == 13) || (row == 16) || (row == 17)) { - symb = csi_params->symb_l1; - const uint32_t *gold = - nr_gold_csi_rs(frame_parms->N_RB_DL, frame_parms->symbols_per_slot, slot, symb + lp, csi_params->scramb_id); - nr_modulation(gold, csi_length, DMRS_MOD_ORDER, mod_csi[symb + lp]); - if ((row == 13) || (row == 16)) { - const uint32_t *gold = - nr_gold_csi_rs(frame_parms->N_RB_DL, frame_parms->symbols_per_slot, slot, symb + 1, csi_params->scramb_id); - nr_modulation(gold, csi_length, DMRS_MOD_ORDER, mod_csi[symb + 1]); - } - } - } - - uint16_t start_sc = frame_parms->first_carrier_offset; - - // resource mapping according to 38.211 7.4.1.5.3 - for (int n = csi_params->start_rb; n < (csi_params->start_rb + csi_params->nr_of_rbs); n++) { - if ((csi_params->freq_density > 1) || (csi_params->freq_density == (n % 2))) { // for freq density 0.5 checks if even or odd RB - for (int ji = 0; ji < size; ji++) { // loop over CDM groups - for (int s = 0 ; s < gs; s++) { // loop over each CDM group size - int p = s + j[ji] * gs; // port index - for (int kp = 0; kp <= kprime; kp++) { // loop over frequency resource elements within a group - // frequency index of current resource element - int k = (start_sc + (n * NR_NB_SC_PER_RB) + koverline[ji] + kp) % (frame_parms->ofdm_symbol_size); - // wf according to tables 7.4.5.3-2 to 7.4.5.3-5 - int wf = kp == 0 ? 1 : (-2 * (s % 2) + 1); - int na = n * alpha; - int kpn = (rho * koverline[ji]) / NR_NB_SC_PER_RB; - int mprime = na + kp + kpn; // sequence index - for (int lp = 0; lp <= lprime; lp++) { // loop over frequency resource elements within a group - int l = lp + loverline[ji]; - // wt according to tables 7.4.5.3-2 to 7.4.5.3-5 - int wt; - if (s < 2) - wt = 1; - else if (s < 4) - wt = -2*(lp % 2) + 1; - else if (s < 6) - wt = -2 * (lp / 2) + 1; - else { - if ((lp == 0) || (lp == 3)) - wt = 1; - else - wt = -1; - } - int index = ((l * frame_parms->ofdm_symbol_size + k) << 1) + (2 * dataF_offset); - ((int16_t*)dataF[p])[index] = (beta * wt * wf * mod_csi[l][mprime << 1]) >> 15; - ((int16_t*)dataF[p])[index + 1] = (beta * wt * wf * mod_csi[l][(mprime << 1) + 1]) >> 15; -#ifdef NR_CSIRS_DEBUG - printf("l,k (%d,%d) seq. index %d \t port %d \t (%d,%d)\n", - l, - k, - mprime, - p + 3000, - ((int16_t*)dataF[p])[index], - ((int16_t*)dataF[p])[index + 1]); -#endif - } - } - } - } - } - } + csi_rs_resource_mapping(dataF, + frame_parms->N_RB_DL << 4, + mod_csi, + frame_parms->ofdm_symbol_size, + dataF_offset, + frame_parms->first_carrier_offset, + phy_csi_parms, + csi_params->start_rb, + csi_params->nr_of_rbs, + alpha, + beta, + rho, + gs, + csi_params->freq_density); } diff --git a/openair1/PHY/NR_TRANSPORT/nr_dci.c b/openair1/PHY/NR_TRANSPORT/nr_dci.c index e3b3f3b42e..6cae31d465 100644 --- a/openair1/PHY/NR_TRANSPORT/nr_dci.c +++ b/openair1/PHY/NR_TRANSPORT/nr_dci.c @@ -36,6 +36,7 @@ #include "nr_sch_dmrs.h" #include "PHY/MODULATION/nr_modulation.h" #include "common/utils/nr/nr_common.h" +#include "SCHED_NR/sched_nr.h" //#define DEBUG_PDCCH_DMRS //#define DEBUG_DCI @@ -50,17 +51,12 @@ static void nr_pdcch_scrambling(uint32_t *in, uint32_t size, uint32_t Nid, uint3 out[i] = in[i] ^ seq[i]; } -void nr_generate_dci(PHY_VARS_gNB *gNB, - nfapi_nr_dl_tti_pdcch_pdu_rel15_t *pdcch_pdu_rel15, - int32_t *txdataF, - int16_t amp, - NR_DL_FRAME_PARMS *frame_parms, - int slot) { - - uint16_t cset_start_sc; - uint8_t cset_start_symb, cset_nsymb; - int k,l,k_prime,dci_idx, dmrs_idx; - +static void nr_generate_dci(PHY_VARS_gNB *gNB, + nfapi_nr_dl_tti_pdcch_pdu_rel15_t *pdcch_pdu_rel15, + int txdataF_offset, + NR_DL_FRAME_PARMS *frame_parms, + int slot) +{ // fill reg list per symbol int reg_list[MAX_DCI_CORESET][NR_MAX_PDCCH_AGG_LEVEL * NR_NB_REG_PER_CCE]; nr_fill_reg_list(reg_list, pdcch_pdu_rel15); @@ -68,20 +64,29 @@ void nr_generate_dci(PHY_VARS_gNB *gNB, int rb_offset; int n_rb; get_coreset_rballoc(pdcch_pdu_rel15->FreqDomainResource,&n_rb,&rb_offset); - cset_start_sc = frame_parms->first_carrier_offset + (pdcch_pdu_rel15->BWPStart + rb_offset) * NR_NB_SC_PER_RB; + uint16_t cset_start_sc = frame_parms->first_carrier_offset + (pdcch_pdu_rel15->BWPStart + rb_offset) * NR_NB_SC_PER_RB; + int idx1 = pdcch_pdu_rel15->StartSymbolIndex+pdcch_pdu_rel15->DurationSymbols; + int idx2 = (((n_rb + rb_offset + pdcch_pdu_rel15->BWPStart) * 6 + 15) >> 4) << 4; + int16_t mod_dmrs[idx1][idx2] __attribute__((aligned(16))); - int16_t mod_dmrs[pdcch_pdu_rel15->StartSymbolIndex+pdcch_pdu_rel15->DurationSymbols][(((n_rb+rb_offset+pdcch_pdu_rel15->BWPStart)*6+15)>>4)<<4] __attribute__((aligned(16))); // 3 for the max coreset duration - - for (int d=0;dnumDlDci;d++) { + for (int d = 0; d < pdcch_pdu_rel15->numDlDci; d++) { /*The coreset is initialised * in frequency: the first subcarrier is obtained by adding the first CRB overlapping the SSB and the rb_offset for coreset 0 * or the rb_offset for other coresets * in time: by its first slot and its first symbol*/ const nfapi_nr_dl_dci_pdu_t *dci_pdu = &pdcch_pdu_rel15->dci_pdu[d]; - cset_start_symb = pdcch_pdu_rel15->StartSymbolIndex; - cset_nsymb = pdcch_pdu_rel15->DurationSymbols; - dci_idx = 0; + uint32_t cset_start_symb = pdcch_pdu_rel15->StartSymbolIndex; + uint32_t cset_nsymb = pdcch_pdu_rel15->DurationSymbols; + int dci_idx = 0; + // multi-beam number (for concurrent beams) + int beam_nb = beam_index_allocation(dci_pdu->precodingAndBeamforming.prgs_list[0].dig_bf_interface_list[0].beam_idx, + &gNB->common_vars, + slot, + frame_parms->symbols_per_slot, + cset_start_symb, + pdcch_pdu_rel15->DurationSymbols); + LOG_D(NR_PHY_DCI, "pdcch: Coreset rb_offset %d, nb_rb %d BWP Start %d\n", rb_offset, n_rb, pdcch_pdu_rel15->BWPStart); LOG_D(NR_PHY_DCI, "pdcch: Coreset starting subcarrier %d on symbol %d (%d symbols)\n", @@ -107,16 +112,18 @@ void nr_generate_dci(PHY_VARS_gNB *gNB, dmrs_length += rb_offset*6; // To accommodate more DMRS symbols in case of rb offset /// DMRS QPSK modulation - for (int symb=cset_start_symb; symbDurationSymbols; symb++) { + for (int symb = cset_start_symb; symb < cset_start_symb + pdcch_pdu_rel15->DurationSymbols; symb++) { const uint32_t *gold = nr_gold_pdcch(frame_parms->N_RB_DL, frame_parms->symbols_per_slot, dci_pdu->ScramblingId, slot, symb); - nr_modulation(gold, dmrs_length, DMRS_MOD_ORDER, - mod_dmrs[symb]); // Qm = 2 as DMRS is QPSK modulated + nr_modulation(gold, dmrs_length, DMRS_MOD_ORDER, mod_dmrs[symb]); // Qm = 2 as DMRS is QPSK modulated #ifdef DEBUG_PDCCH_DMRS if(dci_pdu->RNTI!=0xFFFF) { for (int i=0; i>1; i++) - printf("symb %d i %d %p gold seq 0x%08x mod_dmrs %d %d\n", symb, i, - &gold_pdcch_dmrs[symb][i>>5],gold_pdcch_dmrs[symb][i>>5], mod_dmrs[symb][i<<1], mod_dmrs[symb][(i<<1)+1]); + printf("symb %d i %d %p gold seq 0x%08x mod_dmrs %d %d\n", + symb, + i, + &gold_pdcch_dmrs[symb][i>>5],gold_pdcch_dmrs[symb][i>>5], + mod_dmrs[symb][i<<1], mod_dmrs[symb][(i<<1)+1]); } #endif } @@ -163,7 +170,8 @@ void nr_generate_dci(PHY_VARS_gNB *gNB, #endif /// Resource mapping - + uint16_t amp = gNB->TX_AMP; + int32_t *txdataF = (int32_t *)&gNB->common_vars.txdataF[beam_nb][0][txdataF_offset]; if (cset_start_sc >= frame_parms->ofdm_symbol_size) cset_start_sc -= frame_parms->ofdm_symbol_size; @@ -172,20 +180,21 @@ void nr_generate_dci(PHY_VARS_gNB *gNB, for(int symbol_idx = 0; symbol_idx < pdcch_pdu_rel15->DurationSymbols; symbol_idx++) { // allocating rbs per symbol for (int reg_count = 0; reg_count < num_regs; reg_count++) { - k = cset_start_sc + reg_list[d][reg_count] * NR_NB_SC_PER_RB; + int k = cset_start_sc + reg_list[d][reg_count] * NR_NB_SC_PER_RB; LOG_D(NR_PHY_DCI, "REG %d k %d\n", reg_list[d][reg_count], k); if (k >= frame_parms->ofdm_symbol_size) k -= frame_parms->ofdm_symbol_size; - l = cset_start_symb + symbol_idx; + int l = cset_start_symb + symbol_idx; // dmrs index depends on reference point for k according to 38.211 7.4.1.3.2 + int dmrs_idx; if (pdcch_pdu_rel15->CoreSetType == NFAPI_NR_CSET_CONFIG_PDCCH_CONFIG) dmrs_idx = (reg_list[d][reg_count] + pdcch_pdu_rel15->BWPStart) * 3; else dmrs_idx = (reg_list[d][reg_count] + rb_offset) * 3; - k_prime = 0; + int k_prime = 0; for (int m = 0; m < NR_NB_SC_PER_RB; m++) { if (m == (k_prime << 2) + 1) { // DMRS if not already mapped @@ -235,16 +244,13 @@ void nr_generate_dci(PHY_VARS_gNB *gNB, } // for (int d=0;dnumDlDci;d++) } -void nr_generate_dci_top(processingData_L1tx_t *msgTx, - int slot, - int32_t *txdataF, - int16_t amp, - NR_DL_FRAME_PARMS *frame_parms) { - - for (int i=0; inum_ul_pdcch; i++) - nr_generate_dci(msgTx->gNB,&msgTx->ul_pdcch_pdu[i].pdcch_pdu.pdcch_pdu_rel15,txdataF,amp,frame_parms,slot); - for (int i=0; inum_dl_pdcch; i++) - nr_generate_dci(msgTx->gNB,&msgTx->pdcch_pdu[i].pdcch_pdu_rel15,txdataF,amp,frame_parms,slot); - +void nr_generate_dci_top(processingData_L1tx_t *msgTx, int slot, int txdataF_offset) +{ + PHY_VARS_gNB *gNB = msgTx->gNB; + NR_DL_FRAME_PARMS *frame_parms = &gNB->frame_parms; + for (int i = 0; i < msgTx->num_ul_pdcch; i++) + nr_generate_dci(msgTx->gNB, &msgTx->ul_pdcch_pdu[i].pdcch_pdu.pdcch_pdu_rel15, txdataF_offset, frame_parms, slot); + for (int i = 0; i < msgTx->num_dl_pdcch; i++) + nr_generate_dci(msgTx->gNB, &msgTx->pdcch_pdu[i].pdcch_pdu_rel15, txdataF_offset, frame_parms, slot); } diff --git a/openair1/PHY/NR_TRANSPORT/nr_dci.h b/openair1/PHY/NR_TRANSPORT/nr_dci.h index 3a61d0b4a0..e735069975 100644 --- a/openair1/PHY/NR_TRANSPORT/nr_dci.h +++ b/openair1/PHY/NR_TRANSPORT/nr_dci.h @@ -26,11 +26,7 @@ #include "PHY/NR_REFSIG/nr_refsig.h" #include "nfapi/open-nFAPI/nfapi/public_inc/nfapi_nr_interface.h" -void nr_generate_dci_top(processingData_L1tx_t *msgTx, - int slot, - int32_t *txdataF, - int16_t amp, - NR_DL_FRAME_PARMS *frame_parms); +void nr_generate_dci_top(processingData_L1tx_t *msgTx, int slot, int txdataF_offset); int16_t find_nr_pdcch(int frame,int slot, PHY_VARS_gNB *gNB,find_type_t type); diff --git a/openair1/PHY/NR_TRANSPORT/nr_dlsch.c b/openair1/PHY/NR_TRANSPORT/nr_dlsch.c index 41746a6ba2..a1b9b5b283 100644 --- a/openair1/PHY/NR_TRANSPORT/nr_dlsch.c +++ b/openair1/PHY/NR_TRANSPORT/nr_dlsch.c @@ -39,6 +39,7 @@ #include "common/utils/LOG/vcd_signal_dumper.h" #include "common/utils/nr/nr_common.h" #include "executables/softmodem-common.h" +#include "SCHED_NR/sched_nr.h" //#define DEBUG_DLSCH //#define DEBUG_DLSCH_MAPPING @@ -468,7 +469,16 @@ void nr_generate_pdsch(processingData_L1tx_t *msgTx, int frame, int slot) // The Precoding matrix: // The Codebook Type I start_meas(&gNB->dlsch_precoding_stats); - c16_t **txdataF = gNB->common_vars.txdataF; + nfapi_nr_tx_precoding_and_beamforming_t *pb = &rel15->precodingAndBeamforming; + // beam number in multi-beam scenario (concurrent beams) + int beam_nb = beam_index_allocation(pb->prgs_list[0].dig_bf_interface_list[0].beam_idx, + &gNB->common_vars, + slot, + frame_parms->symbols_per_slot, + rel15->StartSymbolIndex, + rel15->NrOfSymbols); + + c16_t **txdataF = gNB->common_vars.txdataF[beam_nb]; for (int ant = 0; ant < frame_parms->nb_antennas_tx; ant++) { for (int l_symbol = rel15->StartSymbolIndex; l_symbol < rel15->StartSymbolIndex + rel15->NrOfSymbols; l_symbol++) { @@ -477,10 +487,8 @@ void nr_generate_pdsch(processingData_L1tx_t *msgTx, int frame, int slot) int rb = 0; while(rb < rel15->rbSize) { //get pmi info - const int pmi = (rel15->precodingAndBeamforming.prg_size > 0) ? - (rel15->precodingAndBeamforming.prgs_list[(int)rb/rel15->precodingAndBeamforming.prg_size].pm_idx) : 0; - const int pmi2 = (rb < (rel15->rbSize - 1) && rel15->precodingAndBeamforming.prg_size > 0) ? - (rel15->precodingAndBeamforming.prgs_list[(int)(rb+1)/rel15->precodingAndBeamforming.prg_size].pm_idx) : -1; + const int pmi = (pb->prg_size > 0) ? (pb->prgs_list[(int)rb / pb->prg_size].pm_idx) : 0; + const int pmi2 = (rb < (rel15->rbSize - 1) && pb->prg_size > 0) ? (pb->prgs_list[(int)(rb+1)/pb->prg_size].pm_idx) : -1; // If pmi of next RB and pmi of current RB are the same, we do 2 RB in a row // if pmi differs, or current rb is the end (rel15->rbSize - 1), than we do 1 RB in a row @@ -576,21 +584,6 @@ void nr_generate_pdsch(processingData_L1tx_t *msgTx, int frame, int slot) stop_meas(&gNB->dlsch_precoding_stats); - // TODO: handle precoding - // this maps the layers onto antenna ports - - // handle beamforming ID - // each antenna port is assigned a beam_index - // since PHY can only handle BF on slot basis we set the whole slot - - // first check if this slot has not already been allocated to another beam - if (gNB->common_vars.beam_id[0][slot*frame_parms->symbols_per_slot]==255) { - for (int j=0;jsymbols_per_slot;j++) - gNB->common_vars.beam_id[0][slot*frame_parms->symbols_per_slot+j] = rel15->precodingAndBeamforming.prgs_list[0].dig_bf_interface_list[0].beam_idx; - } - else { - LOG_D(PHY,"beam index for PDSCH allocation already taken\n"); - } }// dlsch loop } diff --git a/openair1/PHY/NR_TRANSPORT/nr_dlsch_coding.c b/openair1/PHY/NR_TRANSPORT/nr_dlsch_coding.c index 6915701385..7a29c8163a 100644 --- a/openair1/PHY/NR_TRANSPORT/nr_dlsch_coding.c +++ b/openair1/PHY/NR_TRANSPORT/nr_dlsch_coding.c @@ -73,13 +73,6 @@ void free_gNB_dlsch(NR_gNB_DLSCH_t *dlsch, uint16_t N_RB, const NR_DL_FRAME_PARM } free(harq->c); free(harq->pdu); - - for (int layer = 0; layer < max_layers; layer++) { - for (int aa = 0; aa < 64; aa++) - free(dlsch->ue_spec_bf_weights[layer][aa]); - free(dlsch->ue_spec_bf_weights[layer]); - } - free(dlsch->ue_spec_bf_weights); } NR_gNB_DLSCH_t new_gNB_dlsch(NR_DL_FRAME_PARMS *frame_parms, uint16_t N_RB) @@ -96,19 +89,6 @@ NR_gNB_DLSCH_t new_gNB_dlsch(NR_DL_FRAME_PARMS *frame_parms, uint16_t N_RB) uint32_t dlsch_bytes = a_segments*1056; // allocated bytes per segment NR_gNB_DLSCH_t dlsch; - dlsch.ue_spec_bf_weights = (int32_t ***)malloc16(max_layers * sizeof(int32_t **)); - for (int layer=0; layerb = malloc16(dlsch_bytes); diff --git a/openair1/PHY/NR_TRANSPORT/nr_prach.c b/openair1/PHY/NR_TRANSPORT/nr_prach.c index 40c358477f..a043d93500 100644 --- a/openair1/PHY/NR_TRANSPORT/nr_prach.c +++ b/openair1/PHY/NR_TRANSPORT/nr_prach.c @@ -31,23 +31,26 @@ */ #include "PHY/defs_gNB.h" +#include "SCHED_NR/sched_nr.h" #include "PHY/NR_TRANSPORT/nr_transport_proto.h" #include "PHY/NR_TRANSPORT/nr_transport_common_proto.h" #include "openair1/PHY/NR_TRANSPORT/nr_prach.h" void init_prach_list(PHY_VARS_gNB *gNB) { - AssertFatal(gNB!=NULL,"gNB is null\n"); - for (int i=0; iprach_vars.list[i].frame = -1; - gNB->prach_vars.list[i].slot = -1; + gNB->prach_vars.list[i].slot = -1; + gNB->prach_vars.list[i].beam_nb = -1; } } void free_nr_prach_entry(PHY_VARS_gNB *gNB, int prach_id) { gNB->prach_vars.list[prach_id].frame = -1; - gNB->prach_vars.list[prach_id].slot = -1; + gNB->prach_vars.list[prach_id].slot = -1; + gNB->prach_vars.list[prach_id].beam_nb = -1; } int16_t find_nr_prach(PHY_VARS_gNB *gNB,int frame, int slot, find_type_t type) { @@ -70,47 +73,54 @@ int16_t find_nr_prach(PHY_VARS_gNB *gNB,int frame, int slot, find_type_t type) { return -1; } -void nr_fill_prach(PHY_VARS_gNB *gNB, - int SFN, - int Slot, - nfapi_nr_prach_pdu_t *prach_pdu) +void nr_fill_prach(PHY_VARS_gNB *gNB, int SFN, int Slot, nfapi_nr_prach_pdu_t *prach_pdu) { - int prach_id = find_nr_prach(gNB,SFN,Slot,SEARCH_EXIST_OR_FREE); + int prach_id = find_nr_prach(gNB, SFN, Slot, SEARCH_EXIST_OR_FREE); AssertFatal(((prach_id >= 0) && (prach_id < NUMBER_OF_NR_PRACH_MAX)), "illegal or no prach_id found!!! prach_id %d\n", prach_id); - - gNB->prach_vars.list[prach_id].frame=SFN; - gNB->prach_vars.list[prach_id].slot=Slot; - LOG_D(NR_PHY,"Copying prach pdu %d bytes to index %d\n",(int)sizeof(*prach_pdu),prach_id); - memcpy((void*)&gNB->prach_vars.list[prach_id].pdu,(void*)prach_pdu,sizeof(*prach_pdu)); - + gNB_PRACH_list_t *prach = &gNB->prach_vars.list[prach_id]; + prach->frame = SFN; + prach->slot = Slot; + prach->beam_nb = 0; + if (gNB->common_vars.beam_id) { + int fapi_beam_idx = prach_pdu->beamforming.prgs_list[0].dig_bf_interface_list[0].beam_idx; + // TODO no idea how to compute final prach symbol here so for now we go til the end of the slot + int temp_nb_symbols = NR_NUMBER_OF_SYMBOLS_PER_SLOT - prach_pdu->prach_start_symbol; + prach->beam_nb = beam_index_allocation(fapi_beam_idx, + &gNB->common_vars, + Slot, + NR_NUMBER_OF_SYMBOLS_PER_SLOT, + prach_pdu->prach_start_symbol, + temp_nb_symbols); + } + LOG_D(NR_PHY,"Copying prach pdu %d bytes to index %d\n", (int)sizeof(*prach_pdu), prach_id); + memcpy(&prach->pdu, prach_pdu, sizeof(*prach_pdu)); } -void init_prach_ru_list(RU_t *ru) { - - AssertFatal(ru!=NULL,"ruis null\n"); - for (int i=0; iprach_list[i].frame = -1; - ru->prach_list[i].slot = -1; - } - pthread_mutex_init(&ru->prach_list_mutex,NULL); +void init_prach_ru_list(RU_t *ru) +{ + AssertFatal(ru != NULL, "ru is null\n"); + for (int i = 0; i < NUMBER_OF_NR_RU_PRACH_MAX; i++) { + ru->prach_list[i].frame = -1; + ru->prach_list[i].slot = -1; + } + pthread_mutex_init(&ru->prach_list_mutex, NULL); } -int16_t find_nr_prach_ru(RU_t *ru,int frame,int slot, find_type_t type) { - - AssertFatal(ru!=NULL,"ru is null\n"); +int16_t find_nr_prach_ru(RU_t *ru,int frame,int slot, find_type_t type) +{ + AssertFatal(ru != NULL, "ru is null\n"); pthread_mutex_lock(&ru->prach_list_mutex); - for (uint16_t i=0; i %d.%d\n", frame,slot,i, + for (int i = 0; i < NUMBER_OF_NR_RU_PRACH_MAX; i++) { + LOG_D(PHY,"searching for PRACH in %d.%d : prach_index %d=> %d.%d\n", + frame, + slot, + i, ru->prach_list[i].frame,ru->prach_list[i].slot); - if((type == SEARCH_EXIST_OR_FREE) && - (ru->prach_list[i].frame == -1) && - (ru->prach_list[i].slot == -1)) { - pthread_mutex_unlock(&ru->prach_list_mutex); - return i; + if((type == SEARCH_EXIST_OR_FREE) && (ru->prach_list[i].frame == -1) && (ru->prach_list[i].slot == -1)) { + pthread_mutex_unlock(&ru->prach_list_mutex); + return i; } - else if ((type == SEARCH_EXIST) && - (ru->prach_list[i].frame == frame) && - (ru->prach_list[i].slot == slot)) { + else if ((type == SEARCH_EXIST) && (ru->prach_list[i].frame == frame) && (ru->prach_list[i].slot == slot)) { pthread_mutex_unlock(&ru->prach_list_mutex); return i; } @@ -119,55 +129,42 @@ int16_t find_nr_prach_ru(RU_t *ru,int frame,int slot, find_type_t type) { return -1; } -void nr_fill_prach_ru(RU_t *ru, - int SFN, - int Slot, - nfapi_nr_prach_pdu_t *prach_pdu) { - - int prach_id = find_nr_prach_ru(ru,SFN,Slot,SEARCH_EXIST_OR_FREE); - AssertFatal( ((prach_id>=0) && (prach_id= 0) && (prach_id < NUMBER_OF_NR_PRACH_MAX)) || (prach_id < 0), + "illegal or no prach_id found!!! prach_id %d\n", + prach_id); pthread_mutex_lock(&ru->prach_list_mutex); - ru->prach_list[prach_id].frame = SFN; - ru->prach_list[prach_id].slot = Slot; - ru->prach_list[prach_id].fmt = prach_pdu->prach_format; - ru->prach_list[prach_id].numRA = prach_pdu->num_ra; - ru->prach_list[prach_id].prachStartSymbol = prach_pdu->prach_start_symbol; - ru->prach_list[prach_id].num_prach_ocas = prach_pdu->num_prach_ocas; - pthread_mutex_unlock(&ru->prach_list_mutex); - + ru->prach_list[prach_id].frame = SFN; + ru->prach_list[prach_id].slot = Slot; + ru->prach_list[prach_id].fmt = prach_pdu->prach_format; + ru->prach_list[prach_id].numRA = prach_pdu->num_ra; + ru->prach_list[prach_id].prachStartSymbol = prach_pdu->prach_start_symbol; + ru->prach_list[prach_id].num_prach_ocas = prach_pdu->num_prach_ocas; + pthread_mutex_unlock(&ru->prach_list_mutex); } -void free_nr_ru_prach_entry(RU_t *ru, - int prach_id) { - +void free_nr_ru_prach_entry(RU_t *ru, int prach_id) +{ pthread_mutex_lock(&ru->prach_list_mutex); ru->prach_list[prach_id].frame = -1; - ru->prach_list[prach_id].slot = -1; + ru->prach_list[prach_id].slot = -1; pthread_mutex_unlock(&ru->prach_list_mutex); - } -void rx_nr_prach_ru(RU_t *ru, - int prachFormat, - int numRA, - int prachStartSymbol, - int prachOccasion, - int frame, - int slot) { - - AssertFatal(ru!=NULL,"ru is null\n"); - - int16_t **rxsigF=NULL; - NR_DL_FRAME_PARMS *fp=ru->nr_frame_parms; - int slot2=slot; +void rx_nr_prach_ru(RU_t *ru, int prachFormat, int numRA, int prachStartSymbol, int prachOccasion, int frame, int slot) +{ + AssertFatal(ru != NULL,"ru is null\n"); + int16_t **rxsigF = NULL; + NR_DL_FRAME_PARMS *fp = ru->nr_frame_parms; + int slot2 = slot; int16_t *prach[ru->nb_rx]; int prach_sequence_length = ru->config.prach_config.prach_sequence_length.value; - - int msg1_frequencystart = ru->config.prach_config.num_prach_fd_occasions_list[numRA].k1.value; + int msg1_frequencystart = ru->config.prach_config.num_prach_fd_occasions_list[numRA].k1.value; int sample_offset_slot; if (prachStartSymbol == 0) { @@ -184,16 +181,24 @@ void rx_nr_prach_ru(RU_t *ru, sample_offset_slot = (fp->ofdm_symbol_size + fp->nb_prefix_samples) * prachStartSymbol; } - LOG_D(PHY,"frame %d, slot %d: doing rx_nr_prach_ru for format %d, numRA %d, prachStartSymbol %d, prachOccasion %d\n",frame,slot,prachFormat,numRA,prachStartSymbol,prachOccasion); + LOG_D(PHY, + "frame %d, slot %d: doing rx_nr_prach_ru for format %d, numRA %d, prachStartSymbol %d, prachOccasion %d\n", + frame, + slot, + prachFormat, + numRA, + prachStartSymbol, + prachOccasion); - rxsigF = ru->prach_rxsigF[prachOccasion]; + rxsigF = ru->prach_rxsigF[prachOccasion]; AssertFatal(ru->if_south == LOCAL_RF || ru->if_south == REMOTE_IF5, "we shouldn't call this if if_south != LOCAL_RF or REMOTE_IF5\n"); for (int aa=0; aanb_rx; aa++){ - if (prach_sequence_length == 0) slot2=(slot/fp->slots_per_subframe)*fp->slots_per_subframe; - prach[aa] = (int16_t*)&ru->common.rxdata[aa][fp->get_samples_slot_timestamp(slot2,fp,0)+sample_offset_slot-ru->N_TA_offset]; + if (prach_sequence_length == 0) + slot2 = (slot / fp->slots_per_subframe) * fp->slots_per_subframe; + prach[aa] = (int16_t*)&ru->common.rxdata[aa][fp->get_samples_slot_timestamp(slot2, fp, 0) + sample_offset_slot - ru->N_TA_offset]; } int reps; @@ -202,8 +207,13 @@ void rx_nr_prach_ru(RU_t *ru, int mu = fp->numerology_index; if (prach_sequence_length == 0) { - LOG_D(PHY,"PRACH (ru %d) in %d.%d, format %d, msg1_frequencyStart %d\n", - ru->idx,frame,slot2,prachFormat,msg1_frequencystart); + LOG_D(PHY, + "PRACH (ru %d) in %d.%d, format %d, msg1_frequencyStart %d\n", + ru->idx, + frame, + slot2, + prachFormat, + msg1_frequencystart); switch (prachFormat) { case 0: reps = 1; @@ -235,8 +245,14 @@ void rx_nr_prach_ru(RU_t *ru, } } else { - LOG_D(PHY,"PRACH (ru %d) in %d.%d, format %s, msg1_frequencyStart %d,startSymbol %d\n", - ru->idx,frame,slot,prachfmt[prachFormat],msg1_frequencystart,prachStartSymbol); + LOG_D(PHY, + "PRACH (ru %d) in %d.%d, format %s, msg1_frequencyStart %d,startSymbol %d\n", + ru->idx, + frame, + slot, + prachfmt[prachFormat], + msg1_frequencystart, + prachStartSymbol); switch (prachFormat) { case 4: //A1 reps = 2; @@ -293,7 +309,9 @@ void rx_nr_prach_ru(RU_t *ru, dftlen = 2048 >> mu; } - //actually what we should be checking here is how often the current prach crosses a 0.5ms boundary. I am not quite sure for which paramter set this would be the case, so I will ignore it for now and just check if the prach starts on a 0.5ms boundary + //actually what we should be checking here is how often the current prach crosses a 0.5ms boundary. + //I am not quite sure for which paramter set this would be the case, + //so I will ignore it for now and just check if the prach starts on a 0.5ms boundary if(fp->numerology_index == 0) { if (prachStartSymbol == 0 || prachStartSymbol == 7) Ncp += 16; diff --git a/openair1/PHY/NR_TRANSPORT/nr_transport_proto.h b/openair1/PHY/NR_TRANSPORT/nr_transport_proto.h index a086c347ef..397c0adf98 100644 --- a/openair1/PHY/NR_TRANSPORT/nr_transport_proto.h +++ b/openair1/PHY/NR_TRANSPORT/nr_transport_proto.h @@ -127,7 +127,8 @@ int nr_rx_pusch_tp(PHY_VARS_gNB *gNB, uint8_t ulsch_id, uint32_t frame, uint8_t slot, - unsigned char harq_pid); + unsigned char harq_pid, + int beam_nb); /*! \brief This function implements the idft transform precoding in PUSCH @@ -297,6 +298,7 @@ void nr_fill_srs(PHY_VARS_gNB *gNB, nfapi_nr_srs_pdu_t *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, @@ -326,12 +328,14 @@ void nr_decode_pucch1(c16_t **rxdataF, uint8_t nr_bit); void nr_decode_pucch2(PHY_VARS_gNB *gNB, + c16_t **rxdataF, int frame, int slot, nfapi_nr_uci_pucch_pdu_format_2_3_4_t* uci_pdu, nfapi_nr_pucch_pdu_t* pucch_pdu); void nr_decode_pucch0(PHY_VARS_gNB *gNB, + c16_t **rxdataF, int frame, int slot, nfapi_nr_uci_pucch_pdu_format_0_1_t* uci_pdu, diff --git a/openair1/PHY/NR_TRANSPORT/nr_ulsch.c b/openair1/PHY/NR_TRANSPORT/nr_ulsch.c index 2d98662813..47a0afc625 100644 --- a/openair1/PHY/NR_TRANSPORT/nr_ulsch.c +++ b/openair1/PHY/NR_TRANSPORT/nr_ulsch.c @@ -33,6 +33,7 @@ #include #include "PHY/NR_TRANSPORT/nr_transport_common_proto.h" #include "PHY/NR_TRANSPORT/nr_ulsch.h" +#include "SCHED_NR/sched_nr.h" static NR_gNB_ULSCH_t *find_nr_ulsch(PHY_VARS_gNB *gNB, uint16_t rnti, int pid) { @@ -71,6 +72,16 @@ void nr_fill_ulsch(PHY_VARS_gNB *gNB, int frame, int slot, nfapi_nr_pusch_pdu_t ulsch->harq_pid = harq_pid; ulsch->handled = 0; ulsch->active = true; + ulsch->beam_nb = 0; + if (gNB->common_vars.beam_id) { + int fapi_beam_idx = ulsch_pdu->beamforming.prgs_list[0].dig_bf_interface_list[0].beam_idx; + ulsch->beam_nb = beam_index_allocation(fapi_beam_idx, + &gNB->common_vars, + slot, + NR_NUMBER_OF_SYMBOLS_PER_SLOT, + ulsch_pdu->start_symbol_index, + ulsch_pdu->nr_of_symbols); + } ulsch->frame = frame; ulsch->slot = slot; diff --git a/openair1/PHY/NR_TRANSPORT/nr_ulsch_demodulation.c b/openair1/PHY/NR_TRANSPORT/nr_ulsch_demodulation.c index af675e5d49..e29e3e7b51 100644 --- a/openair1/PHY/NR_TRANSPORT/nr_ulsch_demodulation.c +++ b/openair1/PHY/NR_TRANSPORT/nr_ulsch_demodulation.c @@ -1394,6 +1394,7 @@ typedef struct puschSymbolProc_s { int16_t **llr_layers; int16_t *scramblingSequence; uint32_t nvar; + int beam_nb; } puschSymbolProc_t; static void nr_pusch_symbol_processing(void *arg) @@ -1416,7 +1417,7 @@ static void nr_pusch_symbol_processing(void *arg) frame_parms, pusch_vars, rel15_ul, - gNB->common_vars.rxdataF, + gNB->common_vars.rxdataF[rdata->beam_nb], (c16_t**)gNB->pusch_vars[ulsch_id].ul_ch_estimates, rdata->llr_layers, soffset, @@ -1471,7 +1472,8 @@ int nr_rx_pusch_tp(PHY_VARS_gNB *gNB, uint8_t ulsch_id, uint32_t frame, uint8_t slot, - unsigned char harq_pid) + unsigned char harq_pid, + int beam_nb) { NR_DL_FRAME_PARMS *frame_parms = &gNB->frame_parms; nfapi_nr_pusch_pdu_t *rel15_ul = &gNB->ulsch[ulsch_id].harq_process->ulsch_pdu; @@ -1503,6 +1505,7 @@ int nr_rx_pusch_tp(PHY_VARS_gNB *gNB, get_dmrs_port(nl, rel15_ul->dmrs_ports), symbol, ulsch_id, + beam_nb, bwp_start_subcarrier, rel15_ul, &max_ch, @@ -1535,10 +1538,10 @@ int nr_rx_pusch_tp(PHY_VARS_gNB *gNB, for (int s = rel15_ul->start_symbol_index; s < (rel15_ul->start_symbol_index + rel15_ul->nr_of_symbols); s++) { int offset0 = ((slot & 3) * frame_parms->symbols_per_slot + s) * frame_parms->ofdm_symbol_size; int offset = offset0 + (frame_parms->first_carrier_offset + start_sc) % frame_parms->ofdm_symbol_size; - c16_t *ul_ch = &gNB->common_vars.rxdataF[aarx][offset]; + c16_t *ul_ch = &gNB->common_vars.rxdataF[beam_nb][aarx][offset]; if (end_sc < start_sc) { int64_t symb_energy_aux = signal_energy_nodc(ul_ch, middle_sc - start_sc) * (middle_sc - start_sc); - ul_ch = &gNB->common_vars.rxdataF[aarx][offset0]; + ul_ch = &gNB->common_vars.rxdataF[beam_nb][aarx][offset0]; symb_energy_aux += (signal_energy_nodc(ul_ch, end_sc + 1) * (end_sc + 1)); symb_energy += symb_energy_aux / (rel15_ul->rb_size * NR_NB_SC_PER_RB); } else { @@ -1644,7 +1647,7 @@ int nr_rx_pusch_tp(PHY_VARS_gNB *gNB, c16_t temp_rxFext[frame_parms->nb_antennas_rx][buffer_length] __attribute__((aligned(32))); for (int aarx = 0; aarx < frame_parms->nb_antennas_rx; aarx++) for (int nl = 0; nl < rel15_ul->nrOfLayers; nl++) - nr_ulsch_extract_rbs(gNB->common_vars.rxdataF[aarx], + nr_ulsch_extract_rbs(gNB->common_vars.rxdataF[beam_nb][aarx], (c16_t *)pusch_vars->ul_ch_estimates[nl * frame_parms->nb_antennas_rx + aarx], temp_rxFext[aarx], (c16_t*)&ul_ch_estimates_ext[nl * frame_parms->nb_antennas_rx + aarx][meas_symbol * nb_re_pusch], @@ -1723,6 +1726,7 @@ int nr_rx_pusch_tp(PHY_VARS_gNB *gNB, rdata->llr_layers = pusch_vars->llr_layers; rdata->scramblingSequence = scramblingSequence; rdata->nvar = nvar; + rdata->beam_nb = beam_nb; if (rel15_ul->pdu_bit_map & PUSCH_PDU_BITMAP_PUSCH_PTRS) { nr_pusch_symbol_processing(rdata); diff --git a/openair1/PHY/NR_TRANSPORT/pucch_rx.c b/openair1/PHY/NR_TRANSPORT/pucch_rx.c index d4cf436c76..cda49b83d8 100644 --- a/openair1/PHY/NR_TRANSPORT/pucch_rx.c +++ b/openair1/PHY/NR_TRANSPORT/pucch_rx.c @@ -42,7 +42,7 @@ #include "PHY/defs_gNB.h" #include "PHY/sse_intrin.h" #include "PHY/NR_UE_TRANSPORT/pucch_nr.h" -#include +#include "PHY/CODING/nrSmallBlock/nr_small_block_defs.h" #include "PHY/NR_TRANSPORT/nr_transport_common_proto.h" #include "PHY/NR_TRANSPORT/nr_transport_proto.h" #include "PHY/NR_REFSIG/nr_refsig.h" @@ -50,6 +50,7 @@ #include "common/utils/LOG/vcd_signal_dumper.h" #include "nfapi/oai_integration/vendor_ext.h" #include "nfapi/oai_integration/vendor_ext.h" +#include "SCHED_NR/sched_nr.h" #include "T.h" @@ -62,15 +63,25 @@ void nr_fill_pucch(PHY_VARS_gNB *gNB, { if (NFAPI_MODE == NFAPI_MODE_PNF) - gNB->pucch[0].active = 0; // check if ture in monolithic mode + gNB->pucch[0].active = false; // check if true in monolithic mode bool found = false; for (int i = 0; i < gNB->max_nb_pucch; i++) { NR_gNB_PUCCH_t *pucch = &gNB->pucch[i]; - if (pucch->active == 0) { + if (pucch->active == false) { pucch->frame = frame; pucch->slot = slot; - pucch->active = 1; + pucch->active = true; + pucch->beam_nb = 0; + if (gNB->common_vars.beam_id) { + int fapi_beam_idx = pucch_pdu->beamforming.prgs_list[0].dig_bf_interface_list[0].beam_idx; + pucch->beam_nb = beam_index_allocation(fapi_beam_idx, + &gNB->common_vars, + slot, + NR_NUMBER_OF_SYMBOLS_PER_SLOT, + pucch_pdu->start_symbol_index, + pucch_pdu->nr_of_symbols); + } memcpy((void *)&pucch->pucch_pdu, (void *)pucch_pdu, sizeof(nfapi_nr_pucch_pdu_t)); LOG_D(PHY, "Programming PUCCH[%d] for %d.%d, format %d, nb_harq %d, nb_sr %d, nb_csi %d\n", @@ -148,12 +159,12 @@ static const int16_t idft12_im[12][12] = { }; //************************************************************************// void nr_decode_pucch0(PHY_VARS_gNB *gNB, + c16_t **rxdataF, int frame, int slot, nfapi_nr_uci_pucch_pdu_format_0_1_t *uci_pdu, nfapi_nr_pucch_pdu_t *pucch_pdu) { - c16_t **rxdataF = gNB->common_vars.rxdataF; NR_DL_FRAME_PARMS *frame_parms = &gNB->frame_parms; int soffset = (slot & 3) * frame_parms->symbols_per_slot * frame_parms->ofdm_symbol_size; @@ -1012,13 +1023,12 @@ void init_pucch2_luts() { void nr_decode_pucch2(PHY_VARS_gNB *gNB, + c16_t **rxdataF, int frame, int slot, nfapi_nr_uci_pucch_pdu_format_2_3_4_t* uci_pdu, nfapi_nr_pucch_pdu_t* pucch_pdu) { - - c16_t **rxdataF = gNB->common_vars.rxdataF; NR_DL_FRAME_PARMS *frame_parms = &gNB->frame_parms; //pucch_GroupHopping_t pucch_GroupHopping = pucch_pdu->group_hop_flag + (pucch_pdu->sequence_hop_flag<<1); diff --git a/openair1/PHY/NR_TRANSPORT/srs_rx.c b/openair1/PHY/NR_TRANSPORT/srs_rx.c index 037528b407..931bfe21e7 100644 --- a/openair1/PHY/NR_TRANSPORT/srs_rx.c +++ b/openair1/PHY/NR_TRANSPORT/srs_rx.c @@ -38,7 +38,7 @@ #include "PHY/CODING/nrSmallBlock/nr_small_block_defs.h" #include "PHY/NR_UE_TRANSPORT/srs_modulation_nr.h" #include "common/utils/LOG/log.h" - +#include "SCHED_NR/sched_nr.h" #include "nfapi/oai_integration/vendor_ext.h" #include "T.h" @@ -50,11 +50,21 @@ void nr_fill_srs(PHY_VARS_gNB *gNB, frame_t frame, slot_t slot, nfapi_nr_srs_pdu bool found = false; for (int i = 0; i < gNB->max_nb_srs; i++) { NR_gNB_SRS_t *srs = &gNB->srs[i]; - if (srs->active == 0) { + if (srs->active == false) { found = true; srs->frame = frame; srs->slot = slot; - srs->active = 1; + srs->active = true; + srs->beam_nb = 0; + if (gNB->common_vars.beam_id) { + int fapi_beam_idx = srs_pdu->beamforming.prgs_list[0].dig_bf_interface_list[0].beam_idx; + srs->beam_nb = beam_index_allocation(fapi_beam_idx, + &gNB->common_vars, + slot, + NR_NUMBER_OF_SYMBOLS_PER_SLOT, + srs_pdu->time_start_position, + 1 << srs_pdu->num_symbols); + } memcpy((void *)&srs->srs_pdu, (void *)srs_pdu, sizeof(nfapi_nr_srs_pdu_t)); break; } @@ -63,13 +73,13 @@ 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, int32_t srs_received_signal[][gNB->frame_parms.ofdm_symbol_size * (1 << srs_pdu->num_symbols)]) { - c16_t **rxdataF = gNB->common_vars.rxdataF; const NR_DL_FRAME_PARMS *frame_parms = &gNB->frame_parms; const uint16_t n_symbols = (slot % RU_RX_SLOT_DEPTH) * frame_parms->symbols_per_slot; // number of symbols until this slot diff --git a/openair1/PHY/NR_UE_TRANSPORT/csi_rx.c b/openair1/PHY/NR_UE_TRANSPORT/csi_rx.c index e75f22cab7..eed7da6556 100644 --- a/openair1/PHY/NR_UE_TRANSPORT/csi_rx.c +++ b/openair1/PHY/NR_UE_TRANSPORT/csi_rx.c @@ -177,21 +177,16 @@ bool is_csi_rs_in_symbol(const fapi_nr_dl_config_csirs_pdu_rel15_t csirs_config_ return ret; } -int nr_get_csi_rs_signal(const PHY_VARS_NR_UE *ue, - const UE_nr_rxtx_proc_t *proc, - const fapi_nr_dl_config_csirs_pdu_rel15_t *csirs_config_pdu, - const nr_csi_info_t *nr_csi_info, - const uint8_t N_cdm_groups, - const uint8_t CDM_group_size, - const uint8_t k_prime, - const uint8_t l_prime, - const uint8_t *j_cdm, - const uint8_t *k_overline, - const uint8_t *l_overline, - int32_t csi_rs_received_signal[][ue->frame_parms.samples_per_slot_wCP], - uint32_t *rsrp, - int *rsrp_dBm, - c16_t rxdataF[][ue->frame_parms.samples_per_slot_wCP]) +static int nr_get_csi_rs_signal(const PHY_VARS_NR_UE *ue, + const UE_nr_rxtx_proc_t *proc, + const fapi_nr_dl_config_csirs_pdu_rel15_t *csirs_config_pdu, + const nr_csi_info_t *nr_csi_info, + const csi_mapping_parms_t *csi_mapping, + const int CDM_group_size, + int32_t csi_rs_received_signal[][ue->frame_parms.samples_per_slot_wCP], + uint32_t *rsrp, + int *rsrp_dBm, + c16_t rxdataF[][ue->frame_parms.samples_per_slot_wCP]) { const NR_DL_FRAME_PARMS *fp = &ue->frame_parms; uint16_t meas_count = 0; @@ -206,17 +201,17 @@ int nr_get_csi_rs_signal(const PHY_VARS_NR_UE *ue, continue; } - for (int cdm_id = 0; cdm_id < N_cdm_groups; cdm_id++) { + for (int cdm_id = 0; cdm_id < csi_mapping->size; cdm_id++) { for (int s = 0; s < CDM_group_size; s++) { // loop over frequency resource elements within a group - for (int kp = 0; kp <= k_prime; kp++) { + for (int kp = 0; kp <= csi_mapping->kprime; kp++) { - uint16_t k = (fp->first_carrier_offset + (rb * NR_NB_SC_PER_RB) + k_overline[cdm_id] + kp) % fp->ofdm_symbol_size; + uint16_t k = (fp->first_carrier_offset + (rb * NR_NB_SC_PER_RB) + csi_mapping->koverline[cdm_id] + kp) % fp->ofdm_symbol_size; // loop over time resource elements within a group - for (int lp = 0; lp <= l_prime; lp++) { - uint16_t symb = lp + l_overline[cdm_id]; + for (int lp = 0; lp <= csi_mapping->lprime; lp++) { + uint16_t symb = lp + csi_mapping->loverline[cdm_id]; uint64_t symbol_offset = symb * fp->ofdm_symbol_size; c16_t *rx_signal = &rxdataF[ant_rx][symbol_offset]; c16_t *rx_csi_rs_signal = (c16_t*)&csi_rs_received_signal[ant_rx][symbol_offset]; @@ -230,7 +225,7 @@ int nr_get_csi_rs_signal(const PHY_VARS_NR_UE *ue, #ifdef NR_CSIRS_DEBUG int dataF_offset = proc->nr_slot_rx * fp->samples_per_slot_wCP; - uint16_t port_tx = s+j_cdm[cdm_id]*CDM_group_size; + uint16_t port_tx = s + csi_mapping->j[cdm_id] * CDM_group_size; c16_t *tx_csi_rs_signal = (c16_t*)&nr_csi_info->csi_rs_generated_signal[port_tx][symbol_offset + dataF_offset]; LOG_I(NR_PHY, "l,k (%2d,%4d) |\tport_tx %d (%4d,%4d)\tant_rx %d (%4d,%4d)\n", @@ -278,39 +273,32 @@ uint32_t calc_power_csirs(const uint16_t *x, const fapi_nr_dl_config_csirs_pdu_r return sum_x2 / size - (sum_x / size) * (sum_x / size); } -int nr_csi_rs_channel_estimation(const PHY_VARS_NR_UE *ue, - const UE_nr_rxtx_proc_t *proc, - const fapi_nr_dl_config_csirs_pdu_rel15_t *csirs_config_pdu, - const nr_csi_info_t *nr_csi_info, - const int32_t **csi_rs_generated_signal, - const int32_t csi_rs_received_signal[][ue->frame_parms.samples_per_slot_wCP], - const uint8_t N_cdm_groups, - const uint8_t CDM_group_size, - const uint8_t k_prime, - const uint8_t l_prime, - const uint8_t N_ports, - const uint8_t *j_cdm, - const uint8_t *k_overline, - const uint8_t *l_overline, - uint8_t mem_offset, - int32_t csi_rs_ls_estimated_channel[][N_ports][ue->frame_parms.ofdm_symbol_size], - int32_t csi_rs_estimated_channel_freq[][N_ports][ue->frame_parms.ofdm_symbol_size + FILTER_MARGIN], - int16_t *log2_re, - int16_t *log2_maxh, - uint32_t *noise_power) { - - const NR_DL_FRAME_PARMS *frame_parms = &ue->frame_parms; - const int dataF_offset = proc->nr_slot_rx*ue->frame_parms.samples_per_slot_wCP; +static int nr_csi_rs_channel_estimation(const NR_DL_FRAME_PARMS *fp, + const UE_nr_rxtx_proc_t *proc, + const fapi_nr_dl_config_csirs_pdu_rel15_t *csirs_config_pdu, + const nr_csi_info_t *nr_csi_info, + const int32_t **csi_rs_generated_signal, + const int32_t csi_rs_received_signal[][fp->samples_per_slot_wCP], + const csi_mapping_parms_t *csi_mapping, + const int CDM_group_size, + uint8_t mem_offset, + int32_t csi_rs_ls_estimated_channel[][csi_mapping->ports][fp->ofdm_symbol_size], + int32_t csi_rs_estimated_channel_freq[][csi_mapping->ports][fp->ofdm_symbol_size + FILTER_MARGIN], + int16_t *log2_re, + int16_t *log2_maxh, + uint32_t *noise_power) +{ + const int dataF_offset = proc->nr_slot_rx * fp->samples_per_slot_wCP; *noise_power = 0; int maxh = 0; int count = 0; - for (int ant_rx = 0; ant_rx < frame_parms->nb_antennas_rx; ant_rx++) { + for (int ant_rx = 0; ant_rx < fp->nb_antennas_rx; ant_rx++) { /// LS channel estimation - for(uint16_t port_tx = 0; port_txofdm_symbol_size*sizeof(int32_t)); + for(uint16_t port_tx = 0; port_tx < csi_mapping->ports; port_tx++) { + memset(csi_rs_ls_estimated_channel[ant_rx][port_tx], 0, fp->ofdm_symbol_size*sizeof(int32_t)); } for (int rb = csirs_config_pdu->start_rb; rb < (csirs_config_pdu->start_rb+csirs_config_pdu->nr_of_rbs); rb++) { @@ -320,21 +308,21 @@ int nr_csi_rs_channel_estimation(const PHY_VARS_NR_UE *ue, continue; } - for (int cdm_id = 0; cdm_id < N_cdm_groups; cdm_id++) { + for (int cdm_id = 0; cdm_id < csi_mapping->size; cdm_id++) { for (int s = 0; s < CDM_group_size; s++) { - uint16_t port_tx = s+j_cdm[cdm_id]*CDM_group_size; + uint16_t port_tx = s + csi_mapping->j[cdm_id] * CDM_group_size; // loop over frequency resource elements within a group - for (int kp = 0; kp <= k_prime; kp++) { + for (int kp = 0; kp <= csi_mapping->kprime; kp++) { - uint16_t kinit = (frame_parms->first_carrier_offset + rb*NR_NB_SC_PER_RB) % frame_parms->ofdm_symbol_size; - uint16_t k = kinit + k_overline[cdm_id] + kp; + uint16_t kinit = (fp->first_carrier_offset + rb*NR_NB_SC_PER_RB) % fp->ofdm_symbol_size; + uint16_t k = kinit + csi_mapping->koverline[cdm_id] + kp; // loop over time resource elements within a group - for (int lp = 0; lp <= l_prime; lp++) { - uint16_t symb = lp + l_overline[cdm_id]; - uint64_t symbol_offset = symb*frame_parms->ofdm_symbol_size; + for (int lp = 0; lp <= csi_mapping->lprime; lp++) { + uint16_t symb = lp + csi_mapping->loverline[cdm_id]; + uint64_t symbol_offset = symb * fp->ofdm_symbol_size; c16_t *tx_csi_rs_signal = (c16_t*)&csi_rs_generated_signal[port_tx][symbol_offset+dataF_offset]; c16_t *rx_csi_rs_signal = (c16_t*)&csi_rs_received_signal[ant_rx][symbol_offset]; c16_t *csi_rs_ls_estimated_channel16 = (c16_t*)&csi_rs_ls_estimated_channel[ant_rx][port_tx][0]; @@ -357,10 +345,10 @@ int nr_csi_rs_channel_estimation(const PHY_VARS_NR_UE *ue, if(!is_csi_rs_in_symbol(*csirs_config_pdu,symb)) { continue; } - for(int k = 0; kofdm_symbol_size; k++) { + for(int k = 0; k < fp->ofdm_symbol_size; k++) { LOG_I(NR_PHY, "l,k (%2d,%4d) | ", symb, k); - for(uint16_t port_tx = 0; port_txofdm_symbol_size; + for(uint16_t port_tx = 0; port_tx < csi_mapping->ports; port_tx++) { + uint64_t symbol_offset = symb * fp->ofdm_symbol_size; c16_t *tx_csi_rs_signal = (c16_t*)&csi_rs_generated_signal[port_tx][symbol_offset+dataF_offset]; c16_t *rx_csi_rs_signal = (c16_t*)&csi_rs_received_signal[ant_rx][symbol_offset]; c16_t *csi_rs_ls_estimated_channel16 = (c16_t*)&csi_rs_ls_estimated_channel[ant_rx][port_tx][0]; @@ -377,8 +365,8 @@ int nr_csi_rs_channel_estimation(const PHY_VARS_NR_UE *ue, /// Channel interpolation - for(uint16_t port_tx = 0; port_txofdm_symbol_size + FILTER_MARGIN) * sizeof(int32_t)); + for(uint16_t port_tx = 0; port_tx < csi_mapping->ports; port_tx++) { + memset(csi_rs_estimated_channel_freq[ant_rx][port_tx], 0, (fp->ofdm_symbol_size + FILTER_MARGIN) * sizeof(int32_t)); } for (int rb = csirs_config_pdu->start_rb; rb < (csirs_config_pdu->start_rb+csirs_config_pdu->nr_of_rbs); rb++) { @@ -390,15 +378,15 @@ int nr_csi_rs_channel_estimation(const PHY_VARS_NR_UE *ue, count++; - uint16_t k = (frame_parms->first_carrier_offset + rb*NR_NB_SC_PER_RB) % frame_parms->ofdm_symbol_size; + uint16_t k = (fp->first_carrier_offset + rb * NR_NB_SC_PER_RB) % fp->ofdm_symbol_size; uint16_t k_offset = k + mem_offset; - for(uint16_t port_tx = 0; port_txports; port_tx++) { int16_t *csi_rs_ls_estimated_channel16 = (int16_t*)&csi_rs_ls_estimated_channel[ant_rx][port_tx][k]; int16_t *csi_rs_estimated_channel16 = (int16_t *)&csi_rs_estimated_channel_freq[ant_rx][port_tx][k_offset]; - if( (k == 0) || (k == frame_parms->first_carrier_offset) ) { // Start of OFDM symbol case or first occupied subcarrier case + if( (k == 0) || (k == fp->first_carrier_offset) ) { // Start of OFDM symbol case or first occupied subcarrier case multadd_real_vector_complex_scalar(filt24_start, csi_rs_ls_estimated_channel16, csi_rs_estimated_channel16, 24); - } else if( ( (k + NR_NB_SC_PER_RB) >= frame_parms->ofdm_symbol_size) || - (rb == (csirs_config_pdu->start_rb+csirs_config_pdu->nr_of_rbs-1)) ) { // End of OFDM symbol case or Last occupied subcarrier case + } else if(((k + NR_NB_SC_PER_RB) >= fp->ofdm_symbol_size) || + (rb == (csirs_config_pdu->start_rb+csirs_config_pdu->nr_of_rbs-1))) { // End of OFDM symbol case or Last occupied subcarrier case multadd_real_vector_complex_scalar(filt24_end, csi_rs_ls_estimated_channel16, csi_rs_estimated_channel16 - 3*sizeof(uint64_t), 24); } else { // Middle case multadd_real_vector_complex_scalar(filt24_middle, csi_rs_ls_estimated_channel16, csi_rs_estimated_channel16 - 3*sizeof(uint64_t), 24); @@ -408,15 +396,15 @@ int nr_csi_rs_channel_estimation(const PHY_VARS_NR_UE *ue, /// Power noise estimation AssertFatal(csirs_config_pdu->nr_of_rbs > 0, " nr_of_rbs needs to be greater than 0\n"); - uint16_t noise_real[frame_parms->nb_antennas_rx][N_ports][csirs_config_pdu->nr_of_rbs]; - uint16_t noise_imag[frame_parms->nb_antennas_rx][N_ports][csirs_config_pdu->nr_of_rbs]; + uint16_t noise_real[fp->nb_antennas_rx][csi_mapping->ports][csirs_config_pdu->nr_of_rbs]; + uint16_t noise_imag[fp->nb_antennas_rx][csi_mapping->ports][csirs_config_pdu->nr_of_rbs]; for (int rb = csirs_config_pdu->start_rb; rb < (csirs_config_pdu->start_rb+csirs_config_pdu->nr_of_rbs); rb++) { if (csirs_config_pdu->freq_density <= 1 && csirs_config_pdu->freq_density != (rb % 2)) { continue; } - uint16_t k = (frame_parms->first_carrier_offset + rb*NR_NB_SC_PER_RB) % frame_parms->ofdm_symbol_size; + uint16_t k = (fp->first_carrier_offset + rb*NR_NB_SC_PER_RB) % fp->ofdm_symbol_size; uint16_t k_offset = k + mem_offset; - for(uint16_t port_tx = 0; port_txports; port_tx++) { c16_t *csi_rs_ls_estimated_channel16 = (c16_t*)&csi_rs_ls_estimated_channel[ant_rx][port_tx][k]; c16_t *csi_rs_estimated_channel16 = (c16_t *)&csi_rs_estimated_channel_freq[ant_rx][port_tx][k_offset]; noise_real[ant_rx][port_tx][rb-csirs_config_pdu->start_rb] = abs(csi_rs_ls_estimated_channel16->r-csi_rs_estimated_channel16->r); @@ -424,17 +412,17 @@ int nr_csi_rs_channel_estimation(const PHY_VARS_NR_UE *ue, maxh = cmax3(maxh, abs(csi_rs_estimated_channel16->r), abs(csi_rs_estimated_channel16->i)); } } - for(uint16_t port_tx = 0; port_txports; port_tx++) { *noise_power += (calc_power_csirs(noise_real[ant_rx][port_tx], csirs_config_pdu) + calc_power_csirs(noise_imag[ant_rx][port_tx],csirs_config_pdu)); } #ifdef NR_CSIRS_DEBUG - for(int k = 0; kofdm_symbol_size; k++) { - int rb = k >= frame_parms->first_carrier_offset ? - (k - frame_parms->first_carrier_offset)/NR_NB_SC_PER_RB : - (k + frame_parms->ofdm_symbol_size - frame_parms->first_carrier_offset)/NR_NB_SC_PER_RB; + for(int k = 0; k < fp->ofdm_symbol_size; k++) { + int rb = k >= fp->first_carrier_offset ? + (k - fp->first_carrier_offset)/NR_NB_SC_PER_RB : + (k + fp->ofdm_symbol_size - fp->first_carrier_offset)/NR_NB_SC_PER_RB; LOG_I(NR_PHY, "(k = %4d) |\t", k); - for(uint16_t port_tx = 0; port_txports; port_tx++) { c16_t *csi_rs_ls_estimated_channel16 = (c16_t*)&csi_rs_ls_estimated_channel[ant_rx][port_tx][0]; c16_t *csi_rs_estimated_channel16 = (c16_t *)&csi_rs_estimated_channel_freq[ant_rx][port_tx][mem_offset]; printf("Channel port_tx %d --> ant_rx %d : ls (%4d,%4d), int (%4d,%4d), noise (%4d,%4d) | ", @@ -450,14 +438,13 @@ int nr_csi_rs_channel_estimation(const PHY_VARS_NR_UE *ue, } - *noise_power /= (frame_parms->nb_antennas_rx*N_ports); - *log2_maxh = log2_approx(maxh-1); - *log2_re = log2_approx(count-1); + *noise_power /= (fp->nb_antennas_rx * csi_mapping->ports); + *log2_maxh = log2_approx(maxh - 1); + *log2_re = log2_approx(count - 1); #ifdef NR_CSIRS_DEBUG LOG_I(NR_PHY, "Noise power estimation based on CSI-RS: %i\n", *noise_power); #endif - return 0; } @@ -828,24 +815,64 @@ void nr_ue_csi_im_procedures(PHY_VARS_NR_UE *ue, ue->nr_csi_info->csi_im_meas_computed = true; } -static nfapi_nr_dl_tti_csi_rs_pdu_rel15_t convert_csirs_pdu(const fapi_nr_dl_config_csirs_pdu_rel15_t *csirs_config_pdu) +static void nr_ue_generate_csi_rs(const fapi_nr_dl_config_csirs_pdu_rel15_t *csi_params, + const csi_mapping_parms_t *mapping_parms, + const NR_DL_FRAME_PARMS *frame_parms, + const int16_t amp, + const int slot, + int32_t **dataF) { - nfapi_nr_dl_tti_csi_rs_pdu_rel15_t dl_tti_csi_rs_pdu; - dl_tti_csi_rs_pdu.subcarrier_spacing = csirs_config_pdu->subcarrier_spacing; - dl_tti_csi_rs_pdu.cyclic_prefix = csirs_config_pdu->cyclic_prefix; - dl_tti_csi_rs_pdu.start_rb = csirs_config_pdu->start_rb; - dl_tti_csi_rs_pdu.nr_of_rbs = csirs_config_pdu->nr_of_rbs; - dl_tti_csi_rs_pdu.csi_type = csirs_config_pdu->csi_type; - dl_tti_csi_rs_pdu.row = csirs_config_pdu->row; - dl_tti_csi_rs_pdu.freq_domain = csirs_config_pdu->freq_domain; - dl_tti_csi_rs_pdu.symb_l0 = csirs_config_pdu->symb_l0; - dl_tti_csi_rs_pdu.symb_l1 = csirs_config_pdu->symb_l1; - dl_tti_csi_rs_pdu.cdm_type = csirs_config_pdu->cdm_type; - dl_tti_csi_rs_pdu.freq_density = csirs_config_pdu->freq_density; - dl_tti_csi_rs_pdu.scramb_id = csirs_config_pdu->scramb_id; - dl_tti_csi_rs_pdu.power_control_offset = csirs_config_pdu->power_control_offset; - dl_tti_csi_rs_pdu.power_control_offset_ss = csirs_config_pdu->power_control_offset_ss; - return dl_tti_csi_rs_pdu; + // setting the frequency density from its index + double rho = get_csi_rho(csi_params->freq_density); + int csi_length = get_csi_modulation_length(rho, + csi_params->freq_density, + mapping_parms->kprime, + csi_params->start_rb, + csi_params->nr_of_rbs); + + //*8(max allocation per RB)*2(QPSK)) + int16_t mod_csi[frame_parms->symbols_per_slot][(frame_parms->N_RB_DL << 4) >> 1] __attribute__((aligned(16))); + get_modulated_csi_symbols(frame_parms->symbols_per_slot, + slot, + frame_parms->N_RB_DL, + csi_length, + mod_csi, + mapping_parms->lprime, + csi_params->symb_l0, + csi_params->symb_l1, + csi_params->row, + csi_params->scramb_id); + + uint32_t beta = get_csi_beta_amplitude(amp, csi_params->power_control_offset_ss); + double alpha = 0; + if (mapping_parms->ports == 1) + alpha = rho; + else + alpha = 2 * rho; + +#ifdef NR_CSIRS_DEBUG + printf(" rho %f, alpha %f\n", rho, alpha); +#endif + + // CDM group size from CDM type index + int gs = get_cdm_group_size(csi_params->cdm_type); + + int dataF_offset = slot * frame_parms->samples_per_slot_wCP; + + csi_rs_resource_mapping(dataF, + frame_parms->N_RB_DL << 4, + mod_csi, + frame_parms->ofdm_symbol_size, + dataF_offset, + frame_parms->first_carrier_offset, + mapping_parms, + csi_params->start_rb, + csi_params->nr_of_rbs, + alpha, + beta, + rho, + gs, + csi_params->freq_density); } void nr_ue_csi_rs_procedures(PHY_VARS_NR_UE *ue, @@ -857,6 +884,7 @@ void nr_ue_csi_rs_procedures(PHY_VARS_NR_UE *ue, if(!ue->csirs_vars[gNB_id]->active) { return; } + ue->csirs_vars[gNB_id]->active = 0; const fapi_nr_dl_config_csirs_pdu_rel15_t *csirs_config_pdu = &ue->csirs_vars[gNB_id]->csirs_config_pdu; @@ -882,83 +910,63 @@ void nr_ue_csi_rs_procedures(PHY_VARS_NR_UE *ue, return; } + if(csirs_config_pdu->csi_type == 2) { + LOG_E(NR_PHY, "Handling of ZP CSI-RS not handled yet at PHY\n"); + return; + } + const NR_DL_FRAME_PARMS *frame_parms = &ue->frame_parms; - int32_t csi_rs_received_signal[frame_parms->nb_antennas_rx][frame_parms->samples_per_slot_wCP]; - uint8_t N_cdm_groups = 0; - uint8_t CDM_group_size = 0; - uint8_t k_prime = 0; - uint8_t l_prime = 0; - uint8_t N_ports = 0; - uint8_t j_cdm[16]; - uint8_t k_overline[16]; - uint8_t l_overline[16]; - int16_t log2_re = 0; - int16_t log2_maxh = 0; - uint32_t rsrp = 0; - int rsrp_dBm = 0; - uint32_t noise_power = 0; - uint8_t rank_indicator = 0; - uint32_t precoded_sinr_dB = 0; - uint8_t cqi = 0; - uint8_t i1[3] = {0}; - uint8_t i2[1] = {0}; - nfapi_nr_dl_tti_csi_rs_pdu_rel15_t csi_params = convert_csirs_pdu(csirs_config_pdu); - nr_generate_csi_rs(frame_parms, - ue->nr_csi_info->csi_rs_generated_signal, - AMP, - ue->nr_csi_info, - &csi_params, - proc->nr_slot_rx, - &N_cdm_groups, - &CDM_group_size, - &k_prime, - &l_prime, - &N_ports, - j_cdm, - k_overline, - l_overline); + csi_mapping_parms_t mapping_parms = get_csi_mapping_parms(csirs_config_pdu->row, + csirs_config_pdu->freq_domain, + csirs_config_pdu->symb_l0, + csirs_config_pdu->symb_l1); + nr_csi_info_t *csi_info = ue->nr_csi_info; + nr_ue_generate_csi_rs(csirs_config_pdu, + &mapping_parms, + frame_parms, + AMP, + proc->nr_slot_rx, + csi_info->csi_rs_generated_signal); - int32_t csi_rs_ls_estimated_channel[frame_parms->nb_antennas_rx][N_ports][frame_parms->ofdm_symbol_size]; - int32_t csi_rs_estimated_channel_freq[frame_parms->nb_antennas_rx][N_ports][frame_parms->ofdm_symbol_size + FILTER_MARGIN]; + csi_info->csi_rs_generated_signal_bits = log2_approx(AMP); - // (long)&csi_rs_estimated_channel_freq[0][0][frame_parms->first_carrier_offset] & 0x1F gives us the remainder of the integer division by 32 of the memory address + int32_t csi_rs_ls_estimated_channel[frame_parms->nb_antennas_rx][mapping_parms.ports][frame_parms->ofdm_symbol_size]; + int32_t csi_rs_estimated_channel_freq[frame_parms->nb_antennas_rx][mapping_parms.ports][frame_parms->ofdm_symbol_size + FILTER_MARGIN]; + + // (long)&csi_rs_estimated_channel_freq[0][0][frame_parms->first_carrier_offset] & 0x1F + // gives us the remainder of the integer division by 32 of the memory address // By subtracting the previous value of 32, we know how much is left to have a multiple of 32. // Doing >> 2 <=> /sizeof(int32_t), we know what is the index offset of the array. uint8_t mem_offset = (((32 - ((long)&csi_rs_estimated_channel_freq[0][0][frame_parms->first_carrier_offset])) & 0x1F) >> 2); - + int CDM_group_size = get_cdm_group_size(csirs_config_pdu->cdm_type); + int32_t csi_rs_received_signal[frame_parms->nb_antennas_rx][frame_parms->samples_per_slot_wCP]; + uint32_t rsrp = 0; + int rsrp_dBm = 0; nr_get_csi_rs_signal(ue, proc, csirs_config_pdu, - ue->nr_csi_info, - N_cdm_groups, + csi_info, + &mapping_parms, CDM_group_size, - k_prime, - l_prime, - j_cdm, - k_overline, - l_overline, csi_rs_received_signal, &rsrp, &rsrp_dBm, rxdataF); + uint32_t noise_power = 0; + int16_t log2_re = 0; + int16_t log2_maxh = 0; // if we need to measure only RSRP no need to do channel estimation if (csirs_config_pdu->measurement_bitmap > 1) - nr_csi_rs_channel_estimation(ue, + nr_csi_rs_channel_estimation(frame_parms, proc, csirs_config_pdu, - ue->nr_csi_info, - (const int32_t **) ue->nr_csi_info->csi_rs_generated_signal, + csi_info, + (const int32_t **) csi_info->csi_rs_generated_signal, csi_rs_received_signal, - N_cdm_groups, + &mapping_parms, CDM_group_size, - k_prime, - l_prime, - N_ports, - j_cdm, - k_overline, - l_overline, mem_offset, csi_rs_ls_estimated_channel, csi_rs_estimated_channel_freq, @@ -966,27 +974,32 @@ void nr_ue_csi_rs_procedures(PHY_VARS_NR_UE *ue, &log2_maxh, &noise_power); + uint8_t rank_indicator = 0; // bit 1 in bitmap to indicate RI measurment if (csirs_config_pdu->measurement_bitmap & 2) { nr_csi_rs_ri_estimation(ue, csirs_config_pdu, - ue->nr_csi_info, - N_ports, + csi_info, + mapping_parms.ports, mem_offset, csi_rs_estimated_channel_freq, log2_maxh, &rank_indicator); } + uint8_t i1[3] = {0}; + uint8_t i2[1] = {0}; + uint8_t cqi = 0; + uint32_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, csirs_config_pdu, - ue->nr_csi_info, - N_ports, + csi_info, + mapping_parms.ports, mem_offset, csi_rs_estimated_channel_freq, - ue->nr_csi_info->csi_im_meas_computed ? ue->nr_csi_info->interference_plus_noise_power : noise_power, + csi_info->csi_im_meas_computed ? csi_info->interference_plus_noise_power : noise_power, rank_indicator, log2_re, i1, @@ -1029,6 +1042,4 @@ void nr_ue_csi_rs_procedures(PHY_VARS_NR_UE *ue, nr_fill_rx_indication(&rx_ind, FAPI_NR_CSIRS_IND, ue, NULL, NULL, 1, proc, (void *)&csirs_measurements, NULL); if (ue->if_inst && ue->if_inst->dl_indication) ue->if_inst->dl_indication(&dl_indication); - - return; } diff --git a/openair1/PHY/NR_UE_TRANSPORT/nr_prach.c b/openair1/PHY/NR_UE_TRANSPORT/nr_prach.c index 471b2aee38..e2928b2df4 100644 --- a/openair1/PHY/NR_UE_TRANSPORT/nr_prach.c +++ b/openair1/PHY/NR_UE_TRANSPORT/nr_prach.c @@ -225,7 +225,9 @@ int32_t generate_nr_prach(PHY_VARS_NR_UE *ue, uint8_t gNB_id, int frame, uint8_t k += kbar; k *= 2; - LOG_I(PHY, "PRACH [UE %d] in frame.slot %d.%d, placing PRACH in position %d, msg1 frequency start %d (k1 %d), preamble_offset %d, first_nonzero_root_idx %d\n", + LOG_I(PHY, + "PRACH [UE %d] in frame.slot %d.%d, placing PRACH in position %d, Msg1/MsgA-Preamble frequency start %d (k1 %d), " + "preamble_offset %d, first_nonzero_root_idx %d\n", Mod_id, frame, slot, diff --git a/openair1/PHY/TOOLS/signal_energy.c b/openair1/PHY/TOOLS/signal_energy.c index b3289935b6..012677e8bb 100644 --- a/openair1/PHY/TOOLS/signal_energy.c +++ b/openair1/PHY/TOOLS/signal_energy.c @@ -111,7 +111,7 @@ int32_t signal_energy_amp_shift(int32_t *input,uint32_t length) return((temp>0)?temp:1); } -int32_t signal_energy_nodc(const c16_t *input, uint32_t length) +uint32_t signal_energy_nodc(const c16_t *input, uint32_t length) { // init simde__m128 mm0 = simde_mm_setzero_ps(); @@ -134,7 +134,7 @@ int32_t signal_energy_nodc(const c16_t *input, uint32_t length) // Ave float sums[4]; simde_mm_store_ps(sums, mm0); - return (int)((sums[0] + sums[1] + sums[2] + sums[3] + leftover_sum) / (float)length); + return (uint32_t)((sums[0] + sums[1] + sums[2] + sums[3] + leftover_sum) / (float)length); } double signal_energy_fp(double *s_re[2],double *s_im[2],uint32_t nb_antennas,uint32_t length,uint32_t offset) diff --git a/openair1/PHY/TOOLS/tests/test_signal_energy.cpp b/openair1/PHY/TOOLS/tests/test_signal_energy.cpp index 8767570664..a185a8435b 100644 --- a/openair1/PHY/TOOLS/tests/test_signal_energy.cpp +++ b/openair1/PHY/TOOLS/tests/test_signal_energy.cpp @@ -1,7 +1,7 @@ #include extern "C" { #include "openair1/PHY/TOOLS/tools_defs.h" -extern int32_t signal_energy_nodc(const c16_t *input, uint32_t length); +extern uint32_t signal_energy_nodc(const c16_t *input, uint32_t length); } #include #include diff --git a/openair1/PHY/TOOLS/tools_defs.h b/openair1/PHY/TOOLS/tools_defs.h index d219760586..d1ed050f6f 100644 --- a/openair1/PHY/TOOLS/tools_defs.h +++ b/openair1/PHY/TOOLS/tools_defs.h @@ -758,10 +758,10 @@ int32_t signal_energy_amp_shift(int32_t *input, uint32_t length); int32_t subcarrier_energy(int32_t *,uint32_t, int32_t *subcarrier_energy, uint16_t rx_power_correction); #endif -/*!\fn int32_t signal_energy_nodc(int32_t *,uint32_t); +/*!\fn uint32_t signal_energy_nodc(c16_t *,uint32_t); \brief Computes the signal energy per subcarrier, without DC removal */ -int32_t signal_energy_nodc(const c16_t *input, uint32_t length); +uint32_t signal_energy_nodc(const c16_t *input, uint32_t length); int32_t signal_power(int32_t *,uint32_t); int32_t interference_power(int32_t *,uint32_t); diff --git a/openair1/PHY/defs_RU.h b/openair1/PHY/defs_RU.h index 3b7b7f2ba0..e3e7df19f4 100644 --- a/openair1/PHY/defs_RU.h +++ b/openair1/PHY/defs_RU.h @@ -130,9 +130,9 @@ typedef struct { /// - third index: frequency [0..] int32_t **tdd_calib_coeffs; /// \brief Anaglogue beam ID for each OFDM symbol (used when beamforming not done in RU) - /// - first index: antenna port + /// - first index: concurrent beam /// - second index: beam_id [0.. symbols_per_frame[ - uint8_t **beam_id; + int **beam_id; } RU_COMMON; diff --git a/openair1/PHY/defs_gNB.h b/openair1/PHY/defs_gNB.h index 154f752392..da316de8aa 100644 --- a/openair1/PHY/defs_gNB.h +++ b/openair1/PHY/defs_gNB.h @@ -123,8 +123,6 @@ typedef struct { typedef struct { /// Pointers to variables related to DLSCH harq process NR_DL_gNB_HARQ_t harq_process; - /// beamforming weights for UE-spec transmission (antenna ports 5 or 7..14), for each codeword, maximum 4 layers? - int32_t ***ue_spec_bf_weights; /// Active flag for baseband transmitter processing uint8_t active; /// Number of soft channel bits @@ -139,6 +137,8 @@ typedef struct { typedef struct { int frame; int slot; + // identifier for concurrent beams + int beam_nb; nfapi_nr_prach_pdu_t pdu; } gNB_PRACH_list_t; @@ -223,6 +223,8 @@ typedef struct { typedef struct { uint32_t frame; uint32_t slot; + // identifier for concurrent beams + int beam_nb; uint32_t unav_res; /// Pointers to 16 HARQ processes for the ULSCH NR_UL_gNB_HARQ_t *harq_process; @@ -243,7 +245,9 @@ typedef struct { } NR_gNB_ULSCH_t; typedef struct { - uint8_t active; + bool active; + // identifier for concurrent beams + int beam_nb; /// Frame where current PUCCH pdu was sent uint32_t frame; /// Slot where current PUCCH pdu was sent @@ -253,11 +257,15 @@ typedef struct { } NR_gNB_PUCCH_t; typedef struct { - uint8_t active; + bool active; + // identifier for concurrent beams + int beam_nb; /// Frame where current SRS pdu was received uint32_t frame; /// Slot where current SRS pdu was received uint32_t slot; + /// Measured SNR + int8_t snr; /// ULSCH PDU nfapi_nr_srs_pdu_t srs_pdu; } NR_gNB_SRS_t; @@ -266,17 +274,20 @@ typedef struct { /// \brief Pointers (dynamic) to the received data in the frequency domain. /// - first index: rx antenna [0..nb_antennas_rx[ /// - second index: ? [0..2*ofdm_symbol_size*frame_parms->symbols_per_tti[ - c16_t **rxdataF; + c16_t ***rxdataF; /// \brief holds the transmit data in the frequency domain. /// For IFFT_FPGA this points to the same memory as PHY_vars->rx_vars[a].RX_DMA_BUFFER. //? - /// - first index: eNB id [0..2] (hard coded) + /// - first index: beam (for concurrent beams) /// - second index: tx antenna [0..14[ where 14 is the total supported antenna ports. /// - third index: sample [0..samples_per_frame_woCP] - c16_t **txdataF; + c16_t ***txdataF; /// \brief Anaglogue beam ID for each OFDM symbol (used when beamforming not done in RU) - /// - first index: antenna port + /// - first index: beam index (for concurrent beams) /// - second index: beam_id [0.. symbols_per_frame[ - uint8_t **beam_id; + int **beam_id; + int num_beams; + int num_beams_period; + bool analog_bf; int32_t *debugBuff; int32_t debugBuff_sample_offset; } NR_gNB_COMMON; @@ -464,9 +475,6 @@ typedef struct PHY_VARS_gNB_s { /// SRS variables nr_srs_info_t **nr_srs_info; - /// CSI variables - nr_csi_info_t *nr_csi_info; - // reference amplitude for TX int16_t TX_AMP; diff --git a/openair1/PHY/defs_nr_UE.h b/openair1/PHY/defs_nr_UE.h index 0d077dfd42..4def69049e 100644 --- a/openair1/PHY/defs_nr_UE.h +++ b/openair1/PHY/defs_nr_UE.h @@ -310,6 +310,13 @@ typedef struct { fapi_nr_dl_config_csirs_pdu_rel15_t csirs_config_pdu; } NR_UE_CSI_RS; +typedef struct { + uint8_t csi_rs_generated_signal_bits; + int32_t **csi_rs_generated_signal; + bool csi_im_meas_computed; + uint32_t interference_plus_noise_power; +} nr_csi_info_t; + typedef struct { bool active; fapi_nr_ul_config_srs_pdu srs_config_pdu; diff --git a/openair1/PHY/defs_nr_common.h b/openair1/PHY/defs_nr_common.h index 07eef7a90e..64f3ef303c 100644 --- a/openair1/PHY/defs_nr_common.h +++ b/openair1/PHY/defs_nr_common.h @@ -119,13 +119,6 @@ typedef struct { nfapi_nr_srs_pdu_t srs_pdu; } nr_srs_info_t; -typedef struct { - uint8_t csi_rs_generated_signal_bits; - int32_t **csi_rs_generated_signal; - bool csi_im_meas_computed; - uint32_t interference_plus_noise_power; -} nr_csi_info_t; - typedef struct NR_DL_FRAME_PARMS NR_DL_FRAME_PARMS; typedef uint32_t (*get_samples_per_slot_t)(int slot, const NR_DL_FRAME_PARMS *fp); 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 579102b677..e0bc2aaa15 100644 --- a/openair1/PHY/nr_phy_common/inc/nr_phy_common.h +++ b/openair1/PHY/nr_phy_common/inc/nr_phy_common.h @@ -23,7 +23,47 @@ #define __NR_PHY_COMMON__H__ #include "PHY/impl_defs_top.h" #include "PHY/TOOLS/tools_defs.h" +#include "PHY/NR_REFSIG/nr_refsig_common.h" +#include "PHY/MODULATION/nr_modulation.h" +typedef struct { + int size; + int ports; + int kprime; + int lprime; + int j[16]; + int koverline[16]; + int loverline[16]; +} csi_mapping_parms_t; +void get_modulated_csi_symbols(int symbols_per_slot, + int slot, + int N_RB_DL, + int mod_length, + int16_t mod_csi[][(N_RB_DL << 4) >> 1], + int lprime, + int l0, + int l1, + int row, + int scramb_id); +void csi_rs_resource_mapping(int32_t **dataF, + int csi_rs_length, + int16_t mod_csi[][csi_rs_length >> 1], + int ofdm_symbol_size, + int dataF_offset, + int start_sc, + const csi_mapping_parms_t *mapping_parms, + int start_rb, + int nb_rbs, + double alpha, + int beta, + double rho, + int gs, + int freq_density); +csi_mapping_parms_t get_csi_mapping_parms(int row, int b, int l0, int l1); +int get_cdm_group_size(int cdm_type); +double get_csi_rho(int freq_density); +uint32_t get_csi_beta_amplitude(const int16_t amp, int power_control_offset_ss); +int get_csi_modulation_length(double rho, int freq_density, int kprime, int start_rb, int nb_rbs); void nr_qpsk_llr(int32_t *rxdataF_comp, int16_t *llr, uint32_t nb_re); void nr_16qam_llr(int32_t *rxdataF_comp, int32_t *ch_mag_in, int16_t *llr, uint32_t nb_re); void nr_64qam_llr(int32_t *rxdataF_comp, int32_t *ch_mag, int32_t *ch_mag2, int16_t *llr, uint32_t nb_re); diff --git a/openair1/PHY/nr_phy_common/src/nr_phy_common_csirs.c b/openair1/PHY/nr_phy_common/src/nr_phy_common_csirs.c new file mode 100644 index 0000000000..bba93b35e6 --- /dev/null +++ b/openair1/PHY/nr_phy_common/src/nr_phy_common_csirs.c @@ -0,0 +1,563 @@ +/* + * 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 "PHY/nr_phy_common/inc/nr_phy_common.h" + +void csi_rs_resource_mapping(int32_t **dataF, + int csi_rs_length, + int16_t mod_csi[][csi_rs_length >> 1], + int ofdm_symbol_size, + int dataF_offset, + int start_sc, + const csi_mapping_parms_t *mapping_parms, + int start_rb, + int nb_rbs, + double alpha, + int beta, + double rho, + int gs, + int freq_density) +{ + // resource mapping according to 38.211 7.4.1.5.3 + for (int n = start_rb; n < (start_rb + nb_rbs); n++) { + if ((freq_density > 1) || (freq_density == (n % 2))) { // for freq density 0.5 checks if even or odd RB + for (int ji = 0; ji < mapping_parms->size; ji++) { // loop over CDM groups + for (int s = 0 ; s < gs; s++) { // loop over each CDM group size + int p = s + mapping_parms->j[ji] * gs; // port index + for (int kp = 0; kp <= mapping_parms->kprime; kp++) { // loop over frequency resource elements within a group + // frequency index of current resource element + int k = (start_sc + (n * NR_NB_SC_PER_RB) + mapping_parms->koverline[ji] + kp) % (ofdm_symbol_size); + // wf according to tables 7.4.5.3-2 to 7.4.5.3-5 + int wf = kp == 0 ? 1 : (-2 * (s % 2) + 1); + int na = n * alpha; + int kpn = (rho * mapping_parms->koverline[ji]) / NR_NB_SC_PER_RB; + int mprime = na + kp + kpn; // sequence index + for (int lp = 0; lp <= mapping_parms->lprime; lp++) { // loop over frequency resource elements within a group + int l = lp + mapping_parms->loverline[ji]; + // wt according to tables 7.4.5.3-2 to 7.4.5.3-5 + int wt; + if (s < 2) + wt = 1; + else if (s < 4) + wt = -2 * (lp % 2) + 1; + else if (s < 6) + wt = -2 * (lp / 2) + 1; + else { + if ((lp == 0) || (lp == 3)) + wt = 1; + else + wt = -1; + } + int index = ((l * ofdm_symbol_size + k) << 1) + (2 * dataF_offset); + ((int16_t*)dataF[p])[index] = (beta * wt * wf * mod_csi[l][mprime << 1]) >> 15; + ((int16_t*)dataF[p])[index + 1] = (beta * wt * wf * mod_csi[l][(mprime << 1) + 1]) >> 15; + LOG_D(PHY, + "l,k (%d,%d) seq. index %d \t port %d \t (%d,%d)\n", + l, + k, + mprime, + p + 3000, + ((int16_t*)dataF[p])[index], + ((int16_t*)dataF[p])[index + 1]); + } + } + } + } + } + } +} + +void get_modulated_csi_symbols(int symbols_per_slot, + int slot, + int N_RB_DL, + int mod_length, + int16_t mod_csi[][(N_RB_DL << 4) >> 1], + int lprime, + int l0, + int l1, + int row, + int scramb_id) +{ + for (int lp = 0; lp <= lprime; lp++) { + int symb = l0; + const uint32_t *gold = + nr_gold_csi_rs(N_RB_DL, symbols_per_slot, slot, symb + lp, scramb_id); + nr_modulation(gold, mod_length, DMRS_MOD_ORDER, mod_csi[symb + lp]); + if ((row == 5) || (row == 7) || (row == 11) || (row == 13) || (row == 16)) { + const uint32_t *gold = + nr_gold_csi_rs(N_RB_DL, symbols_per_slot, slot, symb + 1, scramb_id); + nr_modulation(gold, mod_length, DMRS_MOD_ORDER, mod_csi[symb + 1]); + } + if ((row == 14) || (row == 13) || (row == 16) || (row == 17)) { + symb = l1; + const uint32_t *gold = + nr_gold_csi_rs(N_RB_DL, symbols_per_slot, slot, symb + lp, scramb_id); + nr_modulation(gold, mod_length, DMRS_MOD_ORDER, mod_csi[symb + lp]); + if ((row == 13) || (row == 16)) { + const uint32_t *gold = + nr_gold_csi_rs(N_RB_DL, symbols_per_slot, slot, symb + 1, scramb_id); + nr_modulation(gold, mod_length, DMRS_MOD_ORDER, mod_csi[symb + 1]); + } + } + } +} + +uint32_t get_csi_beta_amplitude(const int16_t amp, int power_control_offset_ss) +{ + uint32_t beta = amp; + // assuming amp is the amplitude of SSB channels + switch (power_control_offset_ss) { + case 0: + beta = (amp * ONE_OVER_SQRT2_Q15) >> 15; + break; + case 1: + beta = amp; + break; + case 2: + beta = (amp * ONE_OVER_SQRT2_Q15) >> 14; + break; + case 3: + beta = amp << 1; + break; + default: + AssertFatal(false, "Invalid SS power offset density index for CSI\n"); + } + return beta; +} + +int get_csi_modulation_length(double rho, int freq_density, int kprime, int start_rb, int nr_rbs) +{ + int csi_length = 0; + if (rho < 1) { + if (freq_density == 0) { + csi_length = (((start_rb + nr_rbs) >> 1) << kprime) << 1; + } else { + csi_length = ((((start_rb + nr_rbs) >> 1) << kprime) + 1) << 1; + } + } else { + csi_length = (((uint16_t) rho * (start_rb + nr_rbs)) << kprime) << 1; + } + return csi_length; +} + +double get_csi_rho(int freq_density) +{ + // setting the frequency density from its index + double rho = 0; + switch (freq_density) { + case 0: + rho = 0.5; + break; + case 1: + rho = 0.5; + break; + case 2: + rho = 1; + break; + case 3: + rho = 3; + break; + default: + AssertFatal(false, "Invalid frequency density index for CSI\n"); + } + return rho; +} + +int get_cdm_group_size(int cdm_type) +{ + // CDM group size from CDM type index + int gs = 0; + switch (cdm_type) { + case 0: + gs = 1; + break; + case 1: + gs = 2; + break; + case 2: + gs = 4; + break; + case 3: + gs = 8; + break; + default: + AssertFatal(false, "Invalid cdm type index for CSI\n"); + } + return gs; +} + +csi_mapping_parms_t get_csi_mapping_parms(int row, int b, int l0, int l1) +{ + AssertFatal(b != 0, "Invalid CSI frequency domain mapping: no bit selected in bitmap\n"); + csi_mapping_parms_t csi_parms = {0}; + int found = 0; + int fi = 0; + int k_n[6]; + // implementation of table 7.4.1.5.3-1 of 38.211 + // lprime and kprime are the max value of l' and k' + switch (row) { + case 1: + csi_parms.ports = 1; + csi_parms.kprime = 0; + csi_parms.lprime = 0; + csi_parms.size = 3; + while (found < 1) { + if ((b >> fi) & 0x01) { + k_n[found] = fi; + found++; + } + else + fi++; + } + for (int i = 0; i < csi_parms.size; i++) { + csi_parms.j[i] = 0; + csi_parms.loverline[i] = l0; + csi_parms.koverline[i] = k_n[0] + (i << 2); + } + break; + case 2: + csi_parms.ports = 1; + csi_parms.kprime = 0; + csi_parms.lprime = 0; + csi_parms.size = 1; + while (found < 1) { + if ((b >> fi) & 0x01) { + k_n[found] = fi; + found++; + } + else + fi++; + } + for (int i = 0; i < csi_parms.size; i++) { + csi_parms.j[i] = 0; + csi_parms.loverline[i] = l0; + csi_parms.koverline[i] = k_n[0]; + } + break; + case 3: + csi_parms.ports = 2; + csi_parms.kprime = 1; + csi_parms.lprime = 0; + csi_parms.size = 1; + while (found < 1) { + if ((b >> fi) & 0x01) { + k_n[found] = fi << 1; + found++; + } + else + fi++; + } + for (int i = 0; i < csi_parms.size; i++) { + csi_parms.j[i] = 0; + csi_parms.loverline[i] = l0; + csi_parms.koverline[i] = k_n[0]; + } + break; + case 4: + csi_parms.ports = 4; + csi_parms.kprime = 1; + csi_parms.lprime = 0; + csi_parms.size = 2; + while (found < 1) { + if ((b >> fi) & 0x01) { + k_n[found] = fi << 2; + found++; + } + else + fi++; + } + for (int i = 0; i < csi_parms.size; i++) { + csi_parms.j[i] = i; + csi_parms.loverline[i] = l0; + csi_parms.koverline[i] = k_n[0] + (i << 1); + } + break; + case 5: + csi_parms.ports = 4; + csi_parms.kprime = 1; + csi_parms.lprime = 0; + csi_parms.size = 2; + while (found < 1) { + if ((b >> fi) & 0x01) { + k_n[found] = fi << 1; + found++; + } + else + fi++; + } + for (int i = 0; i < csi_parms.size; i++) { + csi_parms.j[i] = i; + csi_parms.loverline[i] = l0 + i; + csi_parms.koverline[i] = k_n[0]; + } + break; + case 6: + csi_parms.ports = 8; + csi_parms.kprime = 1; + csi_parms.lprime = 0; + csi_parms.size = 4; + while (found < 4) { + if ((b >> fi) & 0x01) { + k_n[found] = fi << 1; + found++; + } + fi++; + } + for (int i = 0; i < csi_parms.size; i++) { + csi_parms.j[i] = i; + csi_parms.loverline[i] = l0; + csi_parms.koverline[i] = k_n[i]; + } + break; + case 7: + csi_parms.ports = 8; + csi_parms.kprime = 1; + csi_parms.lprime = 0; + csi_parms.size = 4; + while (found < 2) { + if ((b >> fi) & 0x01) { + k_n[found] = fi << 1; + found++; + } + fi++; + } + for (int i = 0; i < csi_parms.size; i++) { + csi_parms.j[i] = i; + csi_parms.loverline[i] = l0 + (i >> 1); + csi_parms.koverline[i] = k_n[i % 2]; + } + break; + case 8: + csi_parms.ports = 8; + csi_parms.kprime = 1; + csi_parms.lprime = 1; + csi_parms.size = 2; + while (found < 2) { + if ((b >> fi) & 0x01) { + k_n[found] = fi << 1; + found++; + } + fi++; + } + for (int i = 0; i < csi_parms.size; i++) { + csi_parms.j[i] = i; + csi_parms.loverline[i] = l0; + csi_parms.koverline[i] = k_n[i]; + } + break; + case 9: + csi_parms.ports = 12; + csi_parms.kprime = 1; + csi_parms.lprime = 0; + csi_parms.size = 6; + while (found < 6) { + if ((b >> fi) & 0x01) { + k_n[found] = fi << 1; + found++; + } + fi++; + } + for (int i = 0; i < csi_parms.size; i++) { + csi_parms.j[i] = i; + csi_parms.loverline[i] = l0; + csi_parms.koverline[i] = k_n[i]; + } + break; + case 10: + csi_parms.ports = 12; + csi_parms.kprime = 1; + csi_parms.lprime = 1; + csi_parms.size = 3; + while (found < 3) { + if ((b >> fi) & 0x01) { + k_n[found] = fi << 1; + found++; + } + fi++; + } + for (int i = 0; i < csi_parms.size; i++) { + csi_parms.j[i] = i; + csi_parms.loverline[i] = l0; + csi_parms.koverline[i] = k_n[i]; + } + break; + case 11: + csi_parms.ports = 16; + csi_parms.kprime = 1; + csi_parms.lprime = 0; + csi_parms.size = 8; + while (found < 4) { + if ((b >> fi) & 0x01) { + k_n[found] = fi << 1; + found++; + } + fi++; + } + for (int i = 0; i < csi_parms.size; i++) { + csi_parms.j[i] = i; + csi_parms.loverline[i] = l0 + (i >> 2); + csi_parms.koverline[i] = k_n[i % 4]; + } + break; + case 12: + csi_parms.ports = 16; + csi_parms.kprime = 1; + csi_parms.lprime = 1; + csi_parms.size = 4; + while (found < 4) { + if ((b >> fi) & 0x01) { + k_n[found] = fi << 1; + found++; + } + fi++; + } + for (int i = 0; i < csi_parms.size; i++) { + csi_parms.j[i] = i; + csi_parms.loverline[i] = l0; + csi_parms.koverline[i] = k_n[i]; + } + break; + case 13: + csi_parms.ports = 24; + csi_parms.kprime = 1; + csi_parms.lprime = 0; + csi_parms.size = 12; + while (found < 3) { + if ((b >> fi) & 0x01) { + k_n[found] = fi << 1; + found++; + } + fi++; + } + for (int i = 0; i < csi_parms.size; i++) { + csi_parms.j[i] = i; + if (i < 6) + csi_parms.loverline[i] = l0 + i / 3; + else + csi_parms.loverline[i] = l1 + i / 9; + csi_parms.koverline[i] = k_n[i % 3]; + } + break; + case 14: + csi_parms.ports = 24; + csi_parms.kprime = 1; + csi_parms.lprime = 1; + csi_parms.size = 6; + while (found < 3) { + if ((b >> fi) & 0x01) { + k_n[found] = fi << 1; + found++; + } + fi++; + } + for (int i = 0; i < csi_parms.size; i++) { + csi_parms.j[i] = i; + if (i < 3) + csi_parms.loverline[i] = l0; + else + csi_parms.loverline[i] = l1; + csi_parms.koverline[i] = k_n[i % 3]; + } + break; + case 15: + csi_parms.ports = 24; + csi_parms.kprime = 1; + csi_parms.lprime = 3; + csi_parms.size = 3; + while (found < 3) { + if ((b >> fi) & 0x01) { + k_n[found] = fi << 1; + found++; + } + fi++; + } + for (int i = 0; i < csi_parms.size; i++) { + csi_parms.j[i] = i; + csi_parms.loverline[i] = l0; + csi_parms.koverline[i] = k_n[i]; + } + break; + case 16: + csi_parms.ports = 32; + csi_parms.kprime = 1; + csi_parms.lprime = 0; + csi_parms.size = 16; + while (found < 4) { + if ((b >> fi) & 0x01) { + k_n[found] = fi << 1; + found++; + } + fi++; + } + for (int i = 0; i < csi_parms.size; i++) { + csi_parms.j[i] = i; + if (i < 8) + csi_parms.loverline[i] = l0 + (i >> 2); + else + csi_parms.loverline[i] = l1 + (i / 12); + csi_parms.koverline[i] = k_n[i % 4]; + } + break; + case 17: + csi_parms.ports = 32; + csi_parms.kprime = 1; + csi_parms.lprime = 1; + csi_parms.size = 8; + while (found < 4) { + if ((b >> fi) & 0x01) { + k_n[found] = fi << 1; + found++; + } + fi++; + } + for (int i = 0; i < csi_parms.size; i++) { + csi_parms.j[i] = i; + if (i < 4) + csi_parms.loverline[i] = l0; + else + csi_parms.loverline[i] = l1; + csi_parms.koverline[i] = k_n[i % 4]; + } + break; + case 18: + csi_parms.ports = 32; + csi_parms.kprime = 1; + csi_parms.lprime = 3; + csi_parms.size = 4; + while (found < 4) { + if ((b >> fi) & 0x01) { + k_n[found] = fi << 1; + found++; + } + fi++; + } + for (int i = 0; i < csi_parms.size; i++) { + csi_parms.j[i] = i; + csi_parms.loverline[i] = l0; + csi_parms.koverline[i] = k_n[i]; + } + break; + default: + AssertFatal(false, "Row %d is not valid for CSI Table 7.4.1.5.3-1\n", row); + } + return csi_parms; +} + diff --git a/openair1/SCHED_NR/fapi_nr_l1.c b/openair1/SCHED_NR/fapi_nr_l1.c index f990d6c157..06747c9a2e 100644 --- a/openair1/SCHED_NR/fapi_nr_l1.c +++ b/openair1/SCHED_NR/fapi_nr_l1.c @@ -157,7 +157,9 @@ void nr_schedule_response(NR_Sched_Rsp_t *Sched_INFO) uint8_t number_ul_tti_pdu = (UL_tti_req==NULL) ? 0 : UL_tti_req->n_pdus; uint8_t number_tx_data_pdu = (TX_req == NULL) ? 0 : TX_req->Number_of_PDUs; - if (NFAPI_MODE == NFAPI_MONOLITHIC){ + clear_slot_beamid(gNB, slot); // reset beam_id information for the slot to be processed + + if (NFAPI_MODE == NFAPI_MONOLITHIC) { if (slot_type == NR_DOWNLINK_SLOT || slot_type == NR_MIXED_SLOT) { processingData_L1tx_t *msgTx = gNB->msgDataTx; msgTx->num_pdsch_slot = 0; @@ -227,8 +229,8 @@ void nr_schedule_response(NR_Sched_Rsp_t *Sched_INFO) LOG_D(NR_PHY,"frame %d, slot %d, Got NFAPI_NR_UL_TTI_PRACH_PDU_TYPE for %d.%d\n", frame, slot, UL_tti_req->SFN, UL_tti_req->Slot); nfapi_nr_prach_pdu_t *prach_pdu = &UL_tti_req->pdus_list[i].prach_pdu; nr_fill_prach(gNB, UL_tti_req->SFN, UL_tti_req->Slot, prach_pdu); - if (gNB->RU_list[0]->if_south == LOCAL_RF || - gNB->RU_list[0]->if_south == REMOTE_IF5) nr_fill_prach_ru(gNB->RU_list[0], UL_tti_req->SFN, UL_tti_req->Slot, prach_pdu); + if (gNB->RU_list[0]->if_south == LOCAL_RF || gNB->RU_list[0]->if_south == REMOTE_IF5) + nr_fill_prach_ru(gNB->RU_list[0], UL_tti_req->SFN, UL_tti_req->Slot, prach_pdu); break; case NFAPI_NR_UL_CONFIG_SRS_PDU_TYPE: LOG_D(NR_PHY,"frame %d, slot %d, Got NFAPI_NR_UL_CONFIG_SRS_PDU_TYPE for %d.%d\n", frame, slot, UL_tti_req->SFN, UL_tti_req->Slot); diff --git a/openair1/SCHED_NR/nr_ru_procedures.c b/openair1/SCHED_NR/nr_ru_procedures.c index 2b26848170..475bbed493 100644 --- a/openair1/SCHED_NR/nr_ru_procedures.c +++ b/openair1/SCHED_NR/nr_ru_procedures.c @@ -52,28 +52,37 @@ extern int oai_exit; // OFDM modulation core routine, generates a first_symbol to first_symbol+num_symbols on a particular slot and TX antenna port -void nr_feptx0(RU_t *ru,int tti_tx,int first_symbol, int num_symbols, int aa) { - +void nr_feptx0(RU_t *ru,int tti_tx,int first_symbol, int num_symbols, int aa) +{ NR_DL_FRAME_PARMS *fp = ru->nr_frame_parms; unsigned int slot_offset,slot_offsetF; int slot = tti_tx; - //VCD_SIGNAL_DUMPER_DUMP_FUNCTION_BY_NAME(VCD_SIGNAL_DUMPER_FUNCTIONS_PHY_PROCEDURES_RU_FEPTX_OFDM+(first_symbol!=0?1:0) , 1 ); - if (aa==0 && first_symbol == 0) start_meas(&ru->ofdm_mod_stats); - slot_offset = fp->get_samples_slot_timestamp(slot,fp,0); - slot_offsetF = first_symbol*fp->ofdm_symbol_size; + if (aa == 0 && first_symbol == 0) + start_meas(&ru->ofdm_mod_stats); + slot_offset = fp->get_samples_slot_timestamp(slot, fp, 0); + slot_offsetF = first_symbol * fp->ofdm_symbol_size; - int abs_first_symbol = slot*fp->symbols_per_slot; + int abs_first_symbol = slot * fp->symbols_per_slot; - for (uint16_t idx_sym=abs_first_symbol; idx_symnumerology_index)) ? fp->nb_prefix_samples : fp->nb_prefix_samples0; + for (int idx_sym = abs_first_symbol; idx_sym < abs_first_symbol + first_symbol; idx_sym++) + slot_offset += (idx_sym % (0x7 << fp->numerology_index)) ? fp->nb_prefix_samples : fp->nb_prefix_samples0; - slot_offset += fp->ofdm_symbol_size*first_symbol; + slot_offset += fp->ofdm_symbol_size * first_symbol; - LOG_D(PHY,"SFN/SF:RU:TX:%d/%d aa %d Generating slot %d (first_symbol %d num_symbols %d) slot_offset %d, slot_offsetF %d\n",ru->proc.frame_tx, ru->proc.tti_tx,aa,slot,first_symbol,num_symbols,slot_offset,slot_offsetF); + LOG_D(PHY, + "SFN/SF:RU:TX:%d/%d aa %d Generating slot %d (first_symbol %d num_symbols %d) slot_offset %d, slot_offsetF %d\n", + ru->proc.frame_tx, + ru->proc.tti_tx, + aa, + slot, + first_symbol, + num_symbols, + slot_offset, + slot_offsetF); if (fp->Ncp == 1) { PHY_ofdm_mod(&ru->common.txdataF_BF[aa][slot_offsetF], @@ -110,8 +119,8 @@ void nr_feptx0(RU_t *ru,int tti_tx,int first_symbol, int num_symbols, int aa) { } } // numerology_index!=0 else { //numerology_index == 0 - for (uint16_t idx_sym=abs_first_symbol; idx_symcommon.txdataF_BF[aa][slot_offsetF], (int*)&ru->common.txdata[aa][slot_offset], fp->ofdm_symbol_size, @@ -135,7 +144,8 @@ void nr_feptx0(RU_t *ru,int tti_tx,int first_symbol, int num_symbols, int aa) { } // numerology 0 } - if (aa==0 && first_symbol==0) stop_meas(&ru->ofdm_mod_stats); + if (aa == 0 && first_symbol == 0) + stop_meas(&ru->ofdm_mod_stats); //VCD_SIGNAL_DUMPER_DUMP_FUNCTION_BY_NAME(VCD_SIGNAL_DUMPER_FUNCTIONS_PHY_PROCEDURES_RU_FEPTX_OFDM+(first_symbol!=0?1:0), 0); } @@ -170,167 +180,165 @@ void nr_feptx_ofdm(RU_t *ru,int frame_tx,int tti_tx) { } -void nr_feptx_prec(RU_t *ru,int frame_tx,int tti_tx) { - - int l,aa; +void nr_feptx_prec(RU_t *ru, int frame_tx, int tti_tx) +{ PHY_VARS_gNB **gNB_list = ru->gNB_list,*gNB; NR_DL_FRAME_PARMS *fp = ru->nr_frame_parms; nfapi_nr_config_request_scf_t *cfg = &ru->gNB_list[0]->gNB_config; - int32_t ***bw; - int i=0; int slot_tx = tti_tx; int txdataF_offset = (tti_tx*fp->samples_per_slot_wCP); start_meas(&ru->precoding_stats); - AssertFatal(ru->nb_log_antennas > 0,"ru->nb_log_antennas is 0!\n"); - if (ru->num_gNB == 1){ + AssertFatal(ru->nb_log_antennas > 0, "ru->nb_log_antennas is 0!\n"); + + if (nr_slot_select(cfg,frame_tx,slot_tx) == NR_UPLINK_SLOT) + return; + + if (ru->num_gNB == 1) { gNB = gNB_list[0]; - if (nr_slot_select(cfg,frame_tx,slot_tx) == NR_UPLINK_SLOT) return; + if (ru->config.dbt_config.num_dig_beams != 0) { + for(int i = 0; i < gNB->common_vars.num_beams_period; ++i) { + memcpy((void*) &ru->common.beam_id[i][slot_tx * fp->symbols_per_slot], + (void*) &gNB->common_vars.beam_id[i][slot_tx * fp->symbols_per_slot], + (fp->symbols_per_slot) * sizeof(int)); + } + } - if (!ru->do_precoding || (ru->nb_tx == 1 && ru->nb_log_antennas == 1)) { - for (i = 0; i < ru->nb_log_antennas; ++i) { - //ru->common.txdataF_BF[i] = (int32_t *)&gNB->common_vars.txdataF[i][txdataF_offset]; - memcpy(ru->common.txdataF_BF[i], - &gNB->common_vars.txdataF[i][txdataF_offset], - fp->samples_per_slot_wCP*sizeof(int32_t)); + if (ru->config.dbt_config.num_dig_beams == 0 || gNB->common_vars.analog_bf) { + for (int i = 0; i < ru->nb_log_antennas; ++i) { + // TODO hardcoded beam to 0, still need to understand how to handle this properly + memcpy(ru->common.txdataF_BF[i], &gNB->common_vars.txdataF[0][i][txdataF_offset], fp->samples_per_slot_wCP * sizeof(int32_t)); } } else { - for(i=0; inb_log_antennas; ++i) { - memcpy((void*)ru->common.txdataF[i], - (void*)&gNB->common_vars.txdataF[i][txdataF_offset], - fp->samples_per_slot_wCP*sizeof(int32_t)); - memcpy((void*)&ru->common.beam_id[i][slot_tx*fp->symbols_per_slot], - (void*)&gNB->common_vars.beam_id[i][slot_tx*fp->symbols_per_slot], - fp->symbols_per_slot*sizeof(uint8_t)); + for(int i = 0; i < ru->nb_log_antennas; ++i) { + // TODO hardcoded beam to 0, still need to understand how to handle this properly + memcpy(ru->common.txdataF[i], &gNB->common_vars.txdataF[0][i][txdataF_offset], fp->samples_per_slot_wCP * sizeof(int32_t)); } - bw = ru->beam_weights[0]; - for (l=0;lsymbols_per_slot;l++) { - for (aa=0;aanb_tx;aa++) { + for (int l = 0; l < fp->symbols_per_slot; l++) { + for (int aa = 0; aa < ru->nb_tx; aa++) { + AssertFatal(false, "This needs to be fixed by using appropriate beams from config\n"); nr_beam_precoding((c16_t **)ru->common.txdataF, (c16_t **)ru->common.txdataF_BF, fp, - bw, + ru->beam_weights[0], tti_tx, l, aa, ru->nb_log_antennas, 0); - }// for (aa=0;aanb_tx;aa++) - }// for (l=0;lsymbols_per_slot;l++) - }// ru->do_precoding - }// if (ru->num_gNB == 1) + } + } + } + } stop_meas(&ru->precoding_stats); } // core routine for FEP TX, called from threads in RU TX thread-pool -void nr_feptx(void *arg) { - +void nr_feptx(void *arg) +{ feptx_cmd_t *feptx = (feptx_cmd_t *)arg; - RU_t *ru = feptx->ru; - int slot = feptx->slot; - int aa = feptx->aid; - int startSymbol = feptx->startSymbol; - NR_DL_FRAME_PARMS *fp = ru->nr_frame_parms; - int numSymbols = feptx->numSymbols; - int numSamples = feptx->numSymbols*fp->ofdm_symbol_size; - int txdataF_offset = (slot*fp->samples_per_slot_wCP) + startSymbol*fp->ofdm_symbol_size; - int txdataF_BF_offset = startSymbol*fp->ofdm_symbol_size; + RU_t *ru = feptx->ru; + int slot = feptx->slot; + int aa = feptx->aid; + int startSymbol = feptx->startSymbol; + NR_DL_FRAME_PARMS *fp = ru->nr_frame_parms; + int numSymbols = feptx->numSymbols; + int numSamples = feptx->numSymbols * fp->ofdm_symbol_size; + int txdataF_offset = (slot * fp->samples_per_slot_wCP) + startSymbol * fp->ofdm_symbol_size; + int txdataF_BF_offset = startSymbol * fp->ofdm_symbol_size; - ////////////precoding//////////// VCD_SIGNAL_DUMPER_DUMP_FUNCTION_BY_NAME(VCD_SIGNAL_DUMPER_FUNCTIONS_PHY_PROCEDURES_RU_FEPTX_PREC+feptx->aid , 1); - - if (aa==0) start_meas(&ru->precoding_stats); - if (ru->do_precoding == 1) { - for(int i=0; inb_log_antennas; ++i) { - memcpy((void*) &ru->common.beam_id[i][slot*fp->symbols_per_slot], - (void*) &ru->gNB_list[0]->common_vars.beam_id[i][slot*fp->symbols_per_slot], - (fp->symbols_per_slot)*sizeof(uint8_t)); + if (aa == 0) + start_meas(&ru->precoding_stats); + + if (ru->config.dbt_config.num_dig_beams != 0) { + for(int i = 0; i < ru->gNB_list[0]->common_vars.num_beams_period; i++) { + memcpy(&ru->common.beam_id[i][slot * fp->symbols_per_slot], + &ru->gNB_list[0]->common_vars.beam_id[i][slot * fp->symbols_per_slot], + (fp->symbols_per_slot) * sizeof(int)); } } - if (ru->nb_tx == 1 && ru->nb_log_antennas == 1) { - memcpy((void*)&ru->common.txdataF_BF[0][txdataF_BF_offset], - (void*)&ru->gNB_list[0]->common_vars.txdataF[0][txdataF_offset], - numSamples*sizeof(int32_t)); - } - else if (ru->do_precoding == 0) { - int gNB_tx = ru->gNB_list[0]->frame_parms.nb_antennas_tx; + // If there is no digital beamforming we just need to copy the data to RU + if (ru->config.dbt_config.num_dig_beams == 0 || ru->gNB_list[0]->common_vars.analog_bf) memcpy((void*)&ru->common.txdataF_BF[aa][txdataF_BF_offset], - (void*)&ru->gNB_list[0]->common_vars.txdataF[aa%gNB_tx][txdataF_offset], - numSamples*sizeof(int32_t)); - } + (void*)&ru->gNB_list[0]->common_vars.txdataF[0][aa][txdataF_offset], // TODO hardcoded beam to 0, still need to understand how to handle this properly + numSamples * sizeof(int32_t)); else { - AssertFatal(1==0,"This needs to be fixed, do not use beamforming.\n"); - int32_t ***bw = ru->beam_weights[0]; - for(int i=0; isymbols_per_slot; ++i){ + AssertFatal(false, "This needs to be fixed by using appropriate beams from config\n"); + for(int i = 0; i < fp->symbols_per_slot; ++i) { nr_beam_precoding((c16_t **)ru->gNB_list[0]->common_vars.txdataF, (c16_t **)ru->common.txdataF_BF, fp, - bw, + ru->beam_weights[0], slot, i, aa, ru->nb_log_antennas, - txdataF_offset);//here + txdataF_offset); } } - if (aa==0) stop_meas(&ru->precoding_stats); + + if (aa==0) + stop_meas(&ru->precoding_stats); VCD_SIGNAL_DUMPER_DUMP_FUNCTION_BY_NAME(VCD_SIGNAL_DUMPER_FUNCTIONS_PHY_PROCEDURES_RU_FEPTX_PREC+feptx->aid , 0); ////////////FEPTX//////////// - nr_feptx0(ru,slot,startSymbol,numSymbols,aa); + nr_feptx0(ru, slot, startSymbol, numSymbols, aa); } // RU FEP TX using thread-pool -void nr_feptx_tp(RU_t *ru, int frame_tx, int slot) { - +void nr_feptx_tp(RU_t *ru, int frame_tx, int slot) +{ nfapi_nr_config_request_scf_t *cfg = &ru->gNB_list[0]->gNB_config; - int nbfeptx=0; - if (nr_slot_select(cfg,frame_tx,slot) == NR_UPLINK_SLOT) return; -// for (int aa=0; aanb_tx; aa++) memset(ru->common.txdataF[aa],0,ru->nr_frame_parms->samples_per_slot_wCP*sizeof(int32_t)); - - if (ru->idx == 0) VCD_SIGNAL_DUMPER_DUMP_FUNCTION_BY_NAME( VCD_SIGNAL_DUMPER_FUNCTIONS_PHY_PROCEDURES_RU_FEPTX_OFDM, 1 ); + int nbfeptx = 0; + if (nr_slot_select(cfg, frame_tx, slot) == NR_UPLINK_SLOT) + return; + if (ru->idx == 0) + VCD_SIGNAL_DUMPER_DUMP_FUNCTION_BY_NAME( VCD_SIGNAL_DUMPER_FUNCTIONS_PHY_PROCEDURES_RU_FEPTX_OFDM, 1); start_meas(&ru->ofdm_total_stats); - for (int aid=0;aidnb_tx;aid++) { - notifiedFIFO_elt_t *req=newNotifiedFIFO_elt(sizeof(feptx_cmd_t), 2000 + aid,ru->respfeptx,nr_feptx); - feptx_cmd_t *feptx_cmd=(feptx_cmd_t*)NotifiedFifoData(req); - feptx_cmd->aid = aid; - feptx_cmd->ru = ru; - feptx_cmd->slot = slot; - feptx_cmd->startSymbol = 0; - feptx_cmd->numSymbols = (ru->half_slot_parallelization>0)?ru->nr_frame_parms->symbols_per_slot>>1:ru->nr_frame_parms->symbols_per_slot; - pushTpool(ru->threadPool,req); - nbfeptx++; - if (ru->half_slot_parallelization>0) { - notifiedFIFO_elt_t *req=newNotifiedFIFO_elt(sizeof(feptx_cmd_t), 2000 + aid + ru->nb_tx,ru->respfeptx,nr_feptx); - feptx_cmd_t *feptx_cmd=(feptx_cmd_t*)NotifiedFifoData(req); - feptx_cmd->aid = aid; - feptx_cmd->ru = ru; - feptx_cmd->slot = slot; - feptx_cmd->startSymbol = ru->nr_frame_parms->symbols_per_slot>>1; - feptx_cmd->numSymbols = ru->nr_frame_parms->symbols_per_slot>>1; - pushTpool(ru->threadPool,req); - nbfeptx++; - } + for (int aid = 0; aid < ru->nb_tx; aid++) { + notifiedFIFO_elt_t *req=newNotifiedFIFO_elt(sizeof(feptx_cmd_t), 2000 + aid, ru->respfeptx, nr_feptx); + feptx_cmd_t *feptx_cmd = (feptx_cmd_t*)NotifiedFifoData(req); + feptx_cmd->aid = aid; + feptx_cmd->ru = ru; + feptx_cmd->slot = slot; + feptx_cmd->startSymbol = 0; + feptx_cmd->numSymbols = (ru->half_slot_parallelization > 0) ? + ru->nr_frame_parms->symbols_per_slot >> 1 : + ru->nr_frame_parms->symbols_per_slot; + pushTpool(ru->threadPool, req); + nbfeptx++; + if (ru->half_slot_parallelization > 0) { + notifiedFIFO_elt_t *req=newNotifiedFIFO_elt(sizeof(feptx_cmd_t), 2000 + aid + ru->nb_tx, ru->respfeptx, nr_feptx); + feptx_cmd_t *feptx_cmd = (feptx_cmd_t*)NotifiedFifoData(req); + feptx_cmd->aid = aid; + feptx_cmd->ru = ru; + feptx_cmd->slot = slot; + feptx_cmd->startSymbol = ru->nr_frame_parms->symbols_per_slot >> 1; + feptx_cmd->numSymbols = ru->nr_frame_parms->symbols_per_slot >> 1; + pushTpool(ru->threadPool, req); + nbfeptx++; + } } - while (nbfeptx>0) { + while (nbfeptx > 0) { notifiedFIFO_elt_t *req=pullTpool(ru->respfeptx, ru->threadPool); delNotifiedFIFO_elt(req); nbfeptx--; } stop_meas(&ru->ofdm_total_stats); - if (ru->idx == 0) VCD_SIGNAL_DUMPER_DUMP_FUNCTION_BY_NAME( VCD_SIGNAL_DUMPER_FUNCTIONS_PHY_PROCEDURES_RU_FEPTX_OFDM, 0 ); + if (ru->idx == 0) + VCD_SIGNAL_DUMPER_DUMP_FUNCTION_BY_NAME( VCD_SIGNAL_DUMPER_FUNCTIONS_PHY_PROCEDURES_RU_FEPTX_OFDM, 0); } // core RX FEP routine, called by threads in RU thread-pool void nr_fep(void* arg) { feprx_cmd_t *feprx_cmd = (feprx_cmd_t *)arg; - RU_t *ru = feprx_cmd->ru; int aid = feprx_cmd->aid; int tti_rx = feprx_cmd->slot; @@ -338,7 +346,7 @@ void nr_fep(void* arg) int endSymbol = feprx_cmd->endSymbol; NR_DL_FRAME_PARMS *fp = ru->nr_frame_parms; - LOG_D(PHY,"In nr_fep for aid %d, slot = %d, startSymbol %d, endSymbol %d\n", aid, tti_rx,startSymbol,endSymbol); + LOG_D(PHY,"aid %d, frame %d slot %d, startSymbol %d, endSymbol %d\n", aid, ru->proc.frame_rx, tti_rx, startSymbol, endSymbol); VCD_SIGNAL_DUMPER_DUMP_FUNCTION_BY_NAME(VCD_SIGNAL_DUMPER_FUNCTIONS_PHY_PROCEDURES_RU_FEPRX+aid, 1); diff --git a/openair1/SCHED_NR/phy_procedures_nr_gNB.c b/openair1/SCHED_NR/phy_procedures_nr_gNB.c index 73f71fad25..7148b28fe7 100644 --- a/openair1/SCHED_NR/phy_procedures_nr_gNB.c +++ b/openair1/SCHED_NR/phy_procedures_nr_gNB.c @@ -43,23 +43,42 @@ //#define DEBUG_RXDATA //#define SRS_IND_DEBUG -extern uint8_t nfapi_mode; +int beam_index_allocation(int fapi_beam_index, + NR_gNB_COMMON *common_vars, + int slot, + int symbols_per_slot, + int start_symbol, + int nb_symbols) +{ + if (!common_vars->beam_id) + return 0; -void nr_common_signal_procedures(PHY_VARS_gNB *gNB, int frame,int slot, nfapi_nr_dl_tti_ssb_pdu ssb_pdu) + int idx = -1; + for (int j = 0; j < common_vars->num_beams_period; j++) { + for (int i = start_symbol; i < start_symbol + nb_symbols; i++) { + int current_beam = common_vars->beam_id[j][slot * symbols_per_slot + i]; + if (current_beam == -1 || current_beam == fapi_beam_index) + idx = j; + else { + idx = -1; + break; + } + } + if (idx != -1) + break; + } + AssertFatal(idx >= 0, "Couldn't allocate beam ID %d\n", fapi_beam_index); + for (int j = start_symbol; j < start_symbol + nb_symbols; j++) + common_vars->beam_id[idx][slot * symbols_per_slot + j] = fapi_beam_index; + LOG_D(PHY, "Allocating beam %d in slot %d\n", idx, slot); + return idx; +} + +void nr_common_signal_procedures(PHY_VARS_gNB *gNB, int frame, int slot, nfapi_nr_dl_tti_ssb_pdu ssb_pdu) { NR_DL_FRAME_PARMS *fp = &gNB->frame_parms; - nfapi_nr_config_request_scf_t *cfg = &gNB->gNB_config; - c16_t **txdataF = gNB->common_vars.txdataF; - uint8_t n_hf; - int txdataF_offset = slot*fp->samples_per_slot_wCP; - uint16_t slots_per_hf = (fp->slots_per_frame) >> 1; - - if (slotSsbBlockIndex; LOG_D(PHY,"common_signal_procedures: frame %d, slot %d ssb index %d\n", frame, slot, ssb_index); int ssb_start_symbol_abs = nr_get_ssb_start_symbol(fp, ssb_index); // computing the starting symbol for current ssb @@ -70,11 +89,10 @@ void nr_common_signal_procedures(PHY_VARS_gNB *gNB, int frame,int slot, nfapi_nr // 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 subcarrier spacing provided // 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) ? ssb_pdu.ssb_pdu_rel15.ssbOffsetPointA >> scs - : ssb_pdu.ssb_pdu_rel15.ssbOffsetPointA >> (scs - 2); - const int sc_offset = - (fp->freq_range == FR1) ? ssb_pdu.ssb_pdu_rel15.SsbSubcarrierOffset >> scs : ssb_pdu.ssb_pdu_rel15.SsbSubcarrierOffset; + 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); if (fp->print_ue_help_cmdline_log && get_softmodem_params()->sa) { @@ -99,20 +117,34 @@ void nr_common_signal_procedures(PHY_VARS_gNB *gNB, int frame,int slot, nfapi_nr } LOG_D(PHY, "ssbOffsetPointA %d SSB SsbSubcarrierOffset %d prb_offset %d sc_offset %d scs %d ssb_start_subcarrier %d\n", - ssb_pdu.ssb_pdu_rel15.ssbOffsetPointA, - ssb_pdu.ssb_pdu_rel15.SsbSubcarrierOffset, + 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); - nr_generate_pss(&txdataF[0][txdataF_offset], gNB->TX_AMP, ssb_start_symbol, cfg, fp); - nr_generate_sss(&txdataF[0][txdataF_offset], gNB->TX_AMP, ssb_start_symbol, cfg, fp); + LOG_D(PHY,"SS TX: frame %d, slot %d, start_symbol %d\n", frame, slot, ssb_start_symbol); + nfapi_nr_tx_precoding_and_beamforming_t *pb = &pdu->precoding_and_beamforming; + c16_t ***txdataF = gNB->common_vars.txdataF; + int txdataF_offset = slot * fp->samples_per_slot_wCP; + // beam number in a scenario with multiple concurrent beams + int beam_nb = beam_index_allocation(pb->prgs_list[0].dig_bf_interface_list[0].beam_idx, + &gNB->common_vars, + slot, + fp->symbols_per_slot, + ssb_start_symbol, + 4); // 4 ssb symbols + + nr_generate_pss(&txdataF[beam_nb][0][txdataF_offset], gNB->TX_AMP, ssb_start_symbol, cfg, fp); + nr_generate_sss(&txdataF[beam_nb][0][txdataF_offset], gNB->TX_AMP, ssb_start_symbol, cfg, fp); + + uint16_t slots_per_hf = (fp->slots_per_frame) >> 1; + int n_hf = slot < slots_per_hf ? 0 : 1; int hf = fp->Lmax == 4 ? n_hf : 0; nr_generate_pbch_dmrs(nr_gold_pbch(fp->Lmax, gNB->gNB_config.cell_config.phy_cell_id.value, hf, ssb_index & 7), - &txdataF[0][txdataF_offset], + &txdataF[beam_nb][0][txdataF_offset], gNB->TX_AMP, ssb_start_symbol, cfg, @@ -121,23 +153,16 @@ void nr_common_signal_procedures(PHY_VARS_gNB *gNB, int frame,int slot, nfapi_nr #if T_TRACER if (T_ACTIVE(T_GNB_PHY_MIB)) { unsigned char bch[3]; - bch[0] = ssb_pdu.ssb_pdu_rel15.bchPayload & 0xff; - bch[1] = (ssb_pdu.ssb_pdu_rel15.bchPayload >> 8) & 0xff; - bch[2] = (ssb_pdu.ssb_pdu_rel15.bchPayload >> 16) & 0xff; + bch[0] = pdu->bchPayload & 0xff; + bch[1] = (pdu->bchPayload >> 8) & 0xff; + bch[2] = (pdu->bchPayload >> 16) & 0xff; T(T_GNB_PHY_MIB, T_INT(0) /* module ID */, T_INT(frame), T_INT(slot), T_BUFFER(bch, 3)); } #endif - // Beam_id is currently used only for FR2 - if (fp->freq_range == FR2){ - LOG_D(PHY,"slot %d, ssb_index %d, beam %d\n",slot,ssb_index,cfg->ssb_table.ssb_beam_id_list[ssb_index].beam_id.value); - for (int j=0;jsymbols_per_slot;j++) - gNB->common_vars.beam_id[0][slot*fp->symbols_per_slot+j] = cfg->ssb_table.ssb_beam_id_list[ssb_index].beam_id.value; - } - nr_generate_pbch(gNB, &ssb_pdu, - &txdataF[0][txdataF_offset], + &txdataF[beam_nb][0][txdataF_offset], ssb_start_symbol, n_hf, frame, @@ -145,29 +170,39 @@ void nr_common_signal_procedures(PHY_VARS_gNB *gNB, int frame,int slot, nfapi_nr fp); } +// clearing beam information to be provided to RU for all slots (DL and UL) +void clear_slot_beamid(PHY_VARS_gNB *gNB, int slot) +{ + LOG_D(PHY, "Clearing beam_id structure for slot %d\n", slot); + NR_DL_FRAME_PARMS *fp = &gNB->frame_parms; + for (int i = 0; i < gNB->common_vars.num_beams_period; i++) { + if (gNB->common_vars.beam_id) + memset(&gNB->common_vars.beam_id[i][slot * fp->symbols_per_slot], -1, fp->symbols_per_slot * sizeof(int)); + } +} void phy_procedures_gNB_TX(processingData_L1tx_t *msgTx, int frame, int slot, - int do_meas) { - - int aa; + int do_meas) +{ PHY_VARS_gNB *gNB = msgTx->gNB; - NR_DL_FRAME_PARMS *fp=&gNB->frame_parms; + NR_DL_FRAME_PARMS *fp = &gNB->frame_parms; nfapi_nr_config_request_scf_t *cfg = &gNB->gNB_config; int slot_prs = 0; - int txdataF_offset = slot*fp->samples_per_slot_wCP; + int txdataF_offset = slot * fp->samples_per_slot_wCP; prs_config_t *prs_config = NULL; - if ((cfg->cell_config.frame_duplex_type.value == TDD) && - (nr_slot_select(cfg,frame,slot) == NR_UPLINK_SLOT)) return; + if ((cfg->cell_config.frame_duplex_type.value == TDD) && (nr_slot_select(cfg,frame,slot) == NR_UPLINK_SLOT)) + return; VCD_SIGNAL_DUMPER_DUMP_FUNCTION_BY_NAME(VCD_SIGNAL_DUMPER_FUNCTIONS_PHY_PROCEDURES_gNB_TX + gNB->CC_id, 1); // clear the transmit data array and beam index for the current slot - for (aa=0; aacarrier_config.num_tx_ant.value; aa++) { - memset(&gNB->common_vars.txdataF[aa][txdataF_offset],0,fp->samples_per_slot_wCP*sizeof(int32_t)); - memset(&gNB->common_vars.beam_id[aa][slot*fp->symbols_per_slot],255,fp->symbols_per_slot*sizeof(uint8_t)); + for (int i = 0; i < gNB->common_vars.num_beams_period; i++) { + for (int aa = 0; aa < cfg->carrier_config.num_tx_ant.value; aa++) { + memset(&gNB->common_vars.txdataF[i][aa][txdataF_offset], 0, fp->samples_per_slot_wCP * sizeof(int32_t)); + } } // Check for PRS slot - section 7.4.1.7.4 in 3GPP rel16 38.211 @@ -180,19 +215,19 @@ void phy_procedures_gNB_TX(processingData_L1tx_t *msgTx, { 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][txdataF_offset], AMP, prs_config, cfg, fp); + nr_generate_prs(slot_prs, &gNB->common_vars.txdataF[0][0][txdataF_offset], AMP, prs_config, cfg, fp); } } } VCD_SIGNAL_DUMPER_DUMP_FUNCTION_BY_NAME(VCD_SIGNAL_DUMPER_FUNCTIONS_PHY_PROCEDURES_gNB_COMMON_TX,1); - for (int i=0; iLmax; i++) { + for (int i = 0; i < fp->Lmax; i++) { if (msgTx->ssb[i].active) { - nr_common_signal_procedures(gNB,frame,slot,msgTx->ssb[i].ssb_pdu); + nr_common_signal_procedures(gNB, frame, slot, msgTx->ssb[i].ssb_pdu); msgTx->ssb[i].active = false; } } - + VCD_SIGNAL_DUMPER_DUMP_FUNCTION_BY_NAME(VCD_SIGNAL_DUMPER_FUNCTIONS_PHY_PROCEDURES_gNB_COMMON_TX,0); int num_pdcch_pdus = msgTx->num_ul_pdcch + msgTx->num_dl_pdcch; @@ -203,7 +238,7 @@ void phy_procedures_gNB_TX(processingData_L1tx_t *msgTx, VCD_SIGNAL_DUMPER_DUMP_FUNCTION_BY_NAME(VCD_SIGNAL_DUMPER_FUNCTIONS_PHY_gNB_PDCCH_TX,1); - nr_generate_dci_top(msgTx, slot, (int32_t *)&gNB->common_vars.txdataF[0][txdataF_offset], gNB->TX_AMP, fp); + nr_generate_dci_top(msgTx, slot, txdataF_offset); VCD_SIGNAL_DUMPER_DUMP_FUNCTION_BY_NAME(VCD_SIGNAL_DUMPER_FUNCTIONS_PHY_gNB_PDCCH_TX,0); } @@ -218,42 +253,42 @@ void phy_procedures_gNB_TX(processingData_L1tx_t *msgTx, for (int i = 0; i < NR_SYMBOLS_PER_SLOT; i++){ NR_gNB_CSIRS_t *csirs = &msgTx->csirs_pdu[i]; if (csirs->active == 1) { + AssertFatal(gNB->common_vars.beam_id == NULL, "Cannot handle CSI in the framework of beamforming yet\n"); LOG_D(PHY, "CSI-RS generation started in frame %d.%d\n",frame,slot); nfapi_nr_dl_tti_csi_rs_pdu_rel15_t *csi_params = &csirs->csirs_pdu.csi_rs_pdu_rel15; + if (csi_params->csi_type == 2) { // ZP-CSI + csirs->active = 0; + return; + } + csi_mapping_parms_t mapping_parms = get_csi_mapping_parms(csi_params->row, + csi_params->freq_domain, + csi_params->symb_l0, + csi_params->symb_l1); nr_generate_csi_rs(&gNB->frame_parms, - (int32_t **)gNB->common_vars.txdataF, + (int32_t **)gNB->common_vars.txdataF[0], gNB->TX_AMP, - gNB->nr_csi_info, csi_params, slot, - NULL, - NULL, - NULL, - NULL, - NULL, - NULL, - NULL, - NULL); + &mapping_parms); csirs->active = 0; } } -// if ((frame&127) == 0) dump_pdsch_stats(gNB); - //apply the OFDM symbol rotation here if (gNB->phase_comp) { - for (aa=0; aacarrier_config.num_tx_ant.value; aa++) { - apply_nr_rotation_TX(fp, - &gNB->common_vars.txdataF[aa][txdataF_offset], - fp->symbol_rotation[0], - slot, - fp->N_RB_DL, - 0, - fp->Ncp == EXTENDED ? 12 : 14); - - T(T_GNB_PHY_DL_OUTPUT_SIGNAL, T_INT(0), - T_INT(frame), T_INT(slot), - T_INT(aa), T_BUFFER(&gNB->common_vars.txdataF[aa][txdataF_offset], fp->samples_per_slot_wCP*sizeof(int32_t))); + for(int i = 0; i < gNB->common_vars.num_beams_period; ++i) { + for (int aa = 0; aa < cfg->carrier_config.num_tx_ant.value; aa++) { + apply_nr_rotation_TX(fp, + &gNB->common_vars.txdataF[i][aa][txdataF_offset], + fp->symbol_rotation[0], + slot, + fp->N_RB_DL, + 0, + fp->Ncp == EXTENDED ? 12 : 14); + T(T_GNB_PHY_DL_OUTPUT_SIGNAL, T_INT(0), + T_INT(frame), T_INT(slot), + T_INT(aa), T_BUFFER(&gNB->common_vars.txdataF[aa][txdataF_offset], fp->samples_per_slot_wCP*sizeof(int32_t))); + } } } @@ -339,7 +374,7 @@ static void nr_postDecode(PHY_VARS_gNB *gNB, notifiedFIFO_elt_t *req) if (ulsch_harq->ulsch_pdu.mcs_index == 0 && dumpsig==1) { int off = ((ulsch_harq->ulsch_pdu.rb_size&1) == 1)? 4:0; - LOG_M("rxsigF0.m","rxsF0",&gNB->common_vars.rxdataF[0][(ulsch_harq->slot%RU_RX_SLOT_DEPTH)*gNB->frame_parms.ofdm_symbol_size*gNB->frame_parms.symbols_per_slot],gNB->frame_parms.ofdm_symbol_size*gNB->frame_parms.symbols_per_slot,1,1); + LOG_M("rxsigF0.m","rxsF0",&gNB->common_vars.rxdataF[0][0][(ulsch_harq->slot%RU_RX_SLOT_DEPTH)*gNB->frame_parms.ofdm_symbol_size*gNB->frame_parms.symbols_per_slot],gNB->frame_parms.ofdm_symbol_size*gNB->frame_parms.symbols_per_slot,1,1); LOG_M("rxsigF0_ext.m","rxsF0_ext", &gNB->pusch_vars[0].rxdataF_ext[0][ulsch_harq->ulsch_pdu.start_symbol_index*NR_NB_SC_PER_RB * ulsch_harq->ulsch_pdu.rb_size],ulsch_harq->ulsch_pdu.nr_of_symbols*(off+(NR_NB_SC_PER_RB * @@ -728,13 +763,6 @@ int phy_procedures_gNB_uespec_RX(PHY_VARS_gNB *gNB, int frame_rx, int slot_rx) gNB_I0_measurements(gNB, slot_rx, first_symb, num_symb, rb_mask_ul); const int soffset = (slot_rx & 3) * gNB->frame_parms.symbols_per_slot * gNB->frame_parms.ofdm_symbol_size; - int offset = 10 * gNB->frame_parms.ofdm_symbol_size + gNB->frame_parms.first_carrier_offset; - LOG_D(PHY, - "frame %d, slot %d: UL signal energy %d\n", - frame_rx, - slot_rx, - signal_energy_nodc(&gNB->common_vars.rxdataF[0][soffset + offset + (47 * 12)], 12 * 18)); - start_meas(&gNB->phy_proc_rx); for (int i = 0; i < gNB->max_nb_pucch; i++) { @@ -742,13 +770,10 @@ int phy_procedures_gNB_uespec_RX(PHY_VARS_gNB *gNB, int frame_rx, int slot_rx) if (pucch) { if (NFAPI_MODE == NFAPI_MODE_PNF) pucch->frame = frame_rx; - if ((pucch->active == 1) && - (pucch->frame == frame_rx) && - (pucch->slot == slot_rx) ) { - + if (pucch->active && (pucch->frame == frame_rx) && (pucch->slot == slot_rx)) { + c16_t **rxdataF = gNB->common_vars.rxdataF[pucch->beam_nb]; pucch_decode_done = 1; - - nfapi_nr_pucch_pdu_t *pucch_pdu = &pucch->pucch_pdu; + nfapi_nr_pucch_pdu_t *pucch_pdu = &pucch->pucch_pdu; uint16_t num_ucis; switch (pucch_pdu->format_type) { case 0: @@ -760,21 +785,17 @@ int phy_procedures_gNB_uespec_RX(PHY_VARS_gNB *gNB, int frame_rx, int slot_rx) gNB->uci_pdu_list[num_ucis].pdu_size = sizeof(nfapi_nr_uci_pucch_pdu_format_0_1_t); nfapi_nr_uci_pucch_pdu_format_0_1_t *uci_pdu_format0 = &gNB->uci_pdu_list[num_ucis].pucch_pdu_format_0_1; - offset = pucch_pdu->start_symbol_index*gNB->frame_parms.ofdm_symbol_size + (gNB->frame_parms.first_carrier_offset+pucch_pdu->prb_start*12); - LOG_D(PHY, + int offset = pucch_pdu->start_symbol_index*gNB->frame_parms.ofdm_symbol_size + (gNB->frame_parms.first_carrier_offset+pucch_pdu->prb_start*12); + LOG_D(NR_PHY, "frame %d, slot %d: PUCCH signal energy %d\n", frame_rx, slot_rx, - signal_energy_nodc(&gNB->common_vars.rxdataF[0][soffset + offset], 12)); + signal_energy_nodc(&rxdataF[0][soffset + offset], 12)); - nr_decode_pucch0(gNB, - frame_rx, - slot_rx, - uci_pdu_format0, - pucch_pdu); + nr_decode_pucch0(gNB, rxdataF, frame_rx, slot_rx, uci_pdu_format0, pucch_pdu); gNB->UL_INFO.uci_ind.num_ucis += 1; - pucch->active = 0; + pucch->active = false; break; case 2: num_ucis = gNB->UL_INFO.uci_ind.num_ucis; @@ -786,14 +807,10 @@ int phy_procedures_gNB_uespec_RX(PHY_VARS_gNB *gNB, int frame_rx, int slot_rx) nfapi_nr_uci_pucch_pdu_format_2_3_4_t *uci_pdu_format2 = &gNB->uci_pdu_list[num_ucis].pucch_pdu_format_2_3_4; LOG_D(PHY, "%d.%d Calling nr_decode_pucch2\n", frame_rx, slot_rx); - nr_decode_pucch2(gNB, - frame_rx, - slot_rx, - uci_pdu_format2, - pucch_pdu); + nr_decode_pucch2(gNB, rxdataF, frame_rx, slot_rx, uci_pdu_format2, pucch_pdu); gNB->UL_INFO.uci_ind.num_ucis += 1; - pucch->active = 0; + pucch->active = false; break; default: AssertFatal(1 == 0, "Only PUCCH formats 0 and 2 are currently supported\n"); @@ -852,7 +869,7 @@ int phy_procedures_gNB_uespec_RX(PHY_VARS_gNB *gNB, int frame_rx, int slot_rx) VCD_SIGNAL_DUMPER_DUMP_FUNCTION_BY_NAME(VCD_SIGNAL_DUMPER_FUNCTIONS_NR_RX_PUSCH, 1); start_meas(&gNB->rx_pusch_stats); - nr_rx_pusch_tp(gNB, ULSCH_id, frame_rx, slot_rx, ulsch->harq_pid); + nr_rx_pusch_tp(gNB, ULSCH_id, frame_rx, slot_rx, ulsch->harq_pid, ulsch->beam_nb); NR_gNB_PUSCH *pusch_vars = &gNB->pusch_vars[ULSCH_id]; pusch_vars->ulsch_power_tot = 0; pusch_vars->ulsch_noise_power_tot = 0; @@ -923,7 +940,7 @@ int phy_procedures_gNB_uespec_RX(PHY_VARS_gNB *gNB, int frame_rx, int slot_rx) for (int i = 0; i < gNB->max_nb_srs; i++) { NR_gNB_SRS_t *srs = &gNB->srs[i]; if (srs) { - if ((srs->active == 1) && (srs->frame == frame_rx) && (srs->slot == slot_rx)) { + if ((srs->active == true) && (srs->frame == frame_rx) && (srs->slot == slot_rx)) { LOG_D(NR_PHY, "(%d.%d) gNB is waiting for SRS, id = %i\n", frame_rx, slot_rx, i); start_meas(&gNB->rx_srs_stats); @@ -936,16 +953,15 @@ int phy_procedures_gNB_uespec_RX(PHY_VARS_gNB *gNB, int frame_rx, int slot_rx) int32_t srs_estimated_channel_time[frame_parms->nb_antennas_rx][1 << srs_pdu->num_ant_ports][frame_parms->ofdm_symbol_size] __attribute__((aligned(32))); int32_t srs_estimated_channel_time_shifted[frame_parms->nb_antennas_rx][1 << srs_pdu->num_ant_ports][frame_parms->ofdm_symbol_size]; int8_t snr_per_rb[srs_pdu->bwp_size]; - int8_t snr = 0; start_meas(&gNB->generate_srs_stats); if (check_srs_pdu(srs_pdu, &gNB->nr_srs_info[i]->srs_pdu) == 0) { generate_srs_nr(srs_pdu, frame_parms, gNB->nr_srs_info[i]->srs_generated_signal, 0, gNB->nr_srs_info[i], AMP, frame_rx, slot_rx); } stop_meas(&gNB->generate_srs_stats); - + c16_t **rxdataF = gNB->common_vars.rxdataF[srs->beam_nb]; start_meas(&gNB->get_srs_signal_stats); - int srs_est = nr_get_srs_signal(gNB, frame_rx, slot_rx, srs_pdu, gNB->nr_srs_info[i], srs_received_signal); + int srs_est = nr_get_srs_signal(gNB, rxdataF, frame_rx, slot_rx, srs_pdu, gNB->nr_srs_info[i], srs_received_signal); stop_meas(&gNB->get_srs_signal_stats); if (srs_est >= 0) { @@ -961,11 +977,11 @@ int phy_procedures_gNB_uespec_RX(PHY_VARS_gNB *gNB, int frame_rx, int slot_rx) srs_estimated_channel_time, srs_estimated_channel_time_shifted, snr_per_rb, - &snr); + &gNB->srs->snr); stop_meas(&gNB->srs_channel_estimation_stats); } - if ((snr * 10) < gNB->srs_thres) { + if ((gNB->srs->snr * 10) < gNB->srs_thres) { srs_est = -1; } @@ -1038,7 +1054,7 @@ int phy_procedures_gNB_uespec_RX(PHY_VARS_gNB *gNB, int frame_rx, int slot_rx) nfapi_nr_srs_beamforming_report_t nr_srs_bf_report; nr_srs_bf_report.prg_size = srs_pdu->beamforming.prg_size; nr_srs_bf_report.num_symbols = 1 << srs_pdu->num_symbols; - nr_srs_bf_report.wide_band_snr = srs_est >= 0 ? (snr + 64) << 1 : 0xFF; // 0xFF will be set if this field is invalid + nr_srs_bf_report.wide_band_snr = srs_est >= 0 ? (gNB->srs->snr + 64) << 1 : 0xFF; // 0xFF will be set if this field is invalid nr_srs_bf_report.num_reported_symbols = 1 << srs_pdu->num_symbols; fill_srs_reported_symbol_list(&nr_srs_bf_report.prgs, srs_pdu, frame_parms->N_RB_UL, snr_per_rb, srs_est); @@ -1131,7 +1147,7 @@ int phy_procedures_gNB_uespec_RX(PHY_VARS_gNB *gNB, int frame_rx, int slot_rx) #endif gNB->UL_INFO.srs_ind.number_of_pdus += 1; - srs->active = 0; + srs->active = false; stop_meas(&gNB->rx_srs_stats); } @@ -1141,7 +1157,7 @@ int phy_procedures_gNB_uespec_RX(PHY_VARS_gNB *gNB, int frame_rx, int slot_rx) stop_meas(&gNB->phy_proc_rx); if (pucch_decode_done || pusch_decode_done) { - T(T_GNB_PHY_PUCCH_PUSCH_IQ, T_INT(frame_rx), T_INT(slot_rx), T_BUFFER(&gNB->common_vars.rxdataF[0][0], gNB->frame_parms.symbols_per_slot * gNB->frame_parms.ofdm_symbol_size * 4)); + T(T_GNB_PHY_PUCCH_PUSCH_IQ, T_INT(frame_rx), T_INT(slot_rx), T_BUFFER(&gNB->common_vars.rxdataF[0][0][0], gNB->frame_parms.symbols_per_slot * gNB->frame_parms.ofdm_symbol_size * 4)); } VCD_SIGNAL_DUMPER_DUMP_FUNCTION_BY_NAME(VCD_SIGNAL_DUMPER_FUNCTIONS_PHY_PROCEDURES_gNB_UESPEC_RX,0); diff --git a/openair1/SCHED_NR/sched_nr.h b/openair1/SCHED_NR/sched_nr.h index c31d3669a4..6cde0e8614 100644 --- a/openair1/SCHED_NR/sched_nr.h +++ b/openair1/SCHED_NR/sched_nr.h @@ -39,7 +39,6 @@ void L1_nr_prach_procedures(PHY_VARS_gNB *gNB,int frame,int slot); void nr_common_signal_procedures (PHY_VARS_gNB *gNB,int frame,int slot,nfapi_nr_dl_tti_ssb_pdu ssb_pdu); void nr_feptx_ofdm(RU_t *ru,int frame_tx,int tti_tx); void nr_feptx0(RU_t *ru,int tti_tx,int first_symbol, int num_symbols, int aa); - void nr_feptx_prec(RU_t *ru,int frame_tx,int tti_tx); void nr_feptx_prec_control(RU_t *ru,int frame,int tti_tx); void nr_fep_tp(RU_t *ru, int slot); @@ -47,5 +46,11 @@ void nr_feptx_tp(RU_t *ru, int frame_tx, int slot); void feptx_prec(RU_t *ru,int frame_tx,int tti_tx); int nr_phy_init_RU(RU_t *ru); void nr_phy_free_RU(RU_t *ru); - +void clear_slot_beamid(PHY_VARS_gNB *gNB, int slot); +int beam_index_allocation(int fapi_beam_index, + NR_gNB_COMMON *common_vars, + int slot, + int symbols_per_slot, + int start_symbol, + int nb_symbols); #endif diff --git a/openair1/SCHED_NR_UE/phy_procedures_nr_ue.c b/openair1/SCHED_NR_UE/phy_procedures_nr_ue.c index 33b39fd772..cf1ebf8319 100644 --- a/openair1/SCHED_NR_UE/phy_procedures_nr_ue.c +++ b/openair1/SCHED_NR_UE/phy_procedures_nr_ue.c @@ -1081,7 +1081,6 @@ void pdsch_processing(PHY_VARS_NR_UE *ue, const UE_nr_rxtx_proc_t *proc, nr_phy_ } } nr_ue_csi_rs_procedures(ue, proc, rxdataF); - ue->csirs_vars[gNB_id]->active = 0; } if (dlsch[0].active) { 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 256dab11f7..5a7e9dddac 100644 --- a/openair1/SCHED_NR_UE/phy_procedures_nr_ue_sl.c +++ b/openair1/SCHED_NR_UE/phy_procedures_nr_ue_sl.c @@ -82,7 +82,7 @@ void nr_fill_sl_rx_indication(sl_nr_rx_indication_t *rx_ind, sl_nr_ssb_pdu_t *ssb_pdu = &rx_ind->rx_indication_body[n_pdus - 1].ssb_pdu; if (typeSpecific) { uint8_t *psbch_decoded_output = (uint8_t *)typeSpecific; - memcpy(ssb_pdu->psbch_payload, psbch_decoded_output, sizeof(4)); // 4 bytes of PSBCH payload bytes + memcpy(ssb_pdu->psbch_payload, psbch_decoded_output, 4); // 4 bytes of PSBCH payload bytes ssb_pdu->rsrp_dbm = sl_phy_params->psbch.rsrp_dBm_per_RE; ssb_pdu->rx_slss_id = rx_slss_id; ssb_pdu->decode_status = true; diff --git a/openair1/SIMULATION/NR_PHY/dlsim.c b/openair1/SIMULATION/NR_PHY/dlsim.c index 47957be52e..9ab2de4215 100644 --- a/openair1/SIMULATION/NR_PHY/dlsim.c +++ b/openair1/SIMULATION/NR_PHY/dlsim.c @@ -663,6 +663,7 @@ int main(int argc, char **argv) RC.nb_nr_mac_CC[i] = 1; mac_top_init_gNB(ngran_gNB, scc, NULL, &conf); gNB_mac = RC.nrmac[0]; + nr_mac_config_scc(RC.nrmac[0], scc, &conf); gNB_mac->dl_bler.harq_round_max = num_rounds; @@ -1042,24 +1043,33 @@ int main(int argc, char **argv) int txdataF_offset = slot * frame_parms->samples_per_slot_wCP; if (n_trials==1) { - LOG_M("txsigF0.m","txsF0=", &gNB->common_vars.txdataF[0][txdataF_offset+2*frame_parms->ofdm_symbol_size],frame_parms->ofdm_symbol_size,1,1); + LOG_M("txsigF0.m","txsF0=", + &gNB->common_vars.txdataF[0][0][txdataF_offset +2 * frame_parms->ofdm_symbol_size], + frame_parms->ofdm_symbol_size, + 1, + 1); if (gNB->frame_parms.nb_antennas_tx>1) - LOG_M("txsigF1.m","txsF1=", &gNB->common_vars.txdataF[1][txdataF_offset+2*frame_parms->ofdm_symbol_size],frame_parms->ofdm_symbol_size,1,1); + LOG_M("txsigF1.m","txsF1=", + &gNB->common_vars.txdataF[0][1][txdataF_offset + 2 * frame_parms->ofdm_symbol_size], + frame_parms->ofdm_symbol_size, + 1, + 1); } - if (n_trials == 1) printf("slot_offset %d, txdataF_offset %d \n", slot_offset, txdataF_offset); + if (n_trials == 1) + printf("slot_offset %d, txdataF_offset %d \n", slot_offset, txdataF_offset); //TODO: loop over slots for (aa=0; aaframe_parms.nb_antennas_tx; aa++) { if (cyclic_prefix_type == 1) { - PHY_ofdm_mod((int *)&gNB->common_vars.txdataF[aa][txdataF_offset], + PHY_ofdm_mod((int *)&gNB->common_vars.txdataF[0][aa][txdataF_offset], (int *)&txdata[aa][slot_offset], frame_parms->ofdm_symbol_size, 12, frame_parms->nb_prefix_samples, CYCLIC_PREFIX); } else { - nr_normal_prefix_mod(&gNB->common_vars.txdataF[aa][txdataF_offset], + nr_normal_prefix_mod(&gNB->common_vars.txdataF[0][aa][txdataF_offset], &txdata[aa][slot_offset], 14, frame_parms, diff --git a/openair1/SIMULATION/NR_PHY/nr_unitary_defs.h b/openair1/SIMULATION/NR_PHY/nr_unitary_defs.h index e5ed3aaf00..504b6a8ed5 100644 --- a/openair1/SIMULATION/NR_PHY/nr_unitary_defs.h +++ b/openair1/SIMULATION/NR_PHY/nr_unitary_defs.h @@ -65,6 +65,7 @@ int oai_nfapi_ul_config_req(nfapi_ul_config_request_t *ul_config_req) { return(0 void fill_scc_sim(NR_ServingCellConfigCommon_t *scc,uint64_t *ssb_bitmap,int N_RB_DL,int N_RB_UL,int mu_dl,int mu_ul); void fix_scc(NR_ServingCellConfigCommon_t *scc,uint64_t ssbmap); void prepare_scc(NR_ServingCellConfigCommon_t *scc); +void prepare_msgA_scc(NR_ServingCellConfigCommon_t *scc); void prepare_scd(NR_ServingCellConfig_t *scd); uint32_t ngap_generate_gNB_id(void) {return 0;} diff --git a/openair1/SIMULATION/NR_PHY/pbchsim.c b/openair1/SIMULATION/NR_PHY/pbchsim.c index aea092152f..f9b39de894 100644 --- a/openair1/SIMULATION/NR_PHY/pbchsim.c +++ b/openair1/SIMULATION/NR_PHY/pbchsim.c @@ -640,49 +640,45 @@ int main(int argc, char **argv) int slot = start_symbol/14; for (aa=0; aaframe_parms.nb_antennas_tx; aa++) - memset(gNB->common_vars.txdataF[aa],0,frame_parms->samples_per_slot_wCP*sizeof(int32_t)); + memset(gNB->common_vars.txdataF[0][aa], 0, frame_parms->samples_per_slot_wCP * sizeof(int32_t)); nr_common_signal_procedures (gNB,frame,slot,msgDataTx.ssb[i].ssb_pdu); + int samp = frame_parms->get_samples_slot_timestamp(slot, frame_parms, 0); for (aa=0; aaframe_parms.nb_antennas_tx; aa++) { if (cyclic_prefix_type == 1) { apply_nr_rotation_TX(frame_parms, - gNB->common_vars.txdataF[aa], + gNB->common_vars.txdataF[0][aa], frame_parms->symbol_rotation[0], slot, frame_parms->N_RB_DL, 0, 12); - PHY_ofdm_mod((int *)gNB->common_vars.txdataF[aa], - (int *)&txdata[aa][frame_parms->get_samples_slot_timestamp(slot,frame_parms,0)], - frame_parms->ofdm_symbol_size, - 12, - frame_parms->nb_prefix_samples, - CYCLIC_PREFIX); + PHY_ofdm_mod((int *)gNB->common_vars.txdataF[0][aa], + (int *)&txdata[aa][samp], + frame_parms->ofdm_symbol_size, + 12, + frame_parms->nb_prefix_samples, + CYCLIC_PREFIX); } else { apply_nr_rotation_TX(frame_parms, - gNB->common_vars.txdataF[aa], + gNB->common_vars.txdataF[0][aa], frame_parms->symbol_rotation[0], slot, frame_parms->N_RB_DL, 0, 14); - /*nr_normal_prefix_mod(gNB->common_vars.txdataF[aa], - &txdata[aa][frame_parms->get_samples_slot_timestamp(slot,frame_parms,0)], - 14, - frame_parms);*/ - - PHY_ofdm_mod((int *)gNB->common_vars.txdataF[aa], - (int*)&txdata[aa][frame_parms->get_samples_slot_timestamp(slot,frame_parms,0)], + PHY_ofdm_mod((int *)gNB->common_vars.txdataF[0][aa], + (int*)&txdata[aa][samp], frame_parms->ofdm_symbol_size, 1, frame_parms->nb_prefix_samples0, CYCLIC_PREFIX); - PHY_ofdm_mod((int *)&gNB->common_vars.txdataF[aa][frame_parms->ofdm_symbol_size], - (int*)&txdata[aa][frame_parms->get_samples_slot_timestamp(slot,frame_parms,0)+frame_parms->nb_prefix_samples0+frame_parms->ofdm_symbol_size], + PHY_ofdm_mod((int *)&gNB->common_vars.txdataF[0][aa][frame_parms->ofdm_symbol_size], + (int*)&txdata[aa][samp + frame_parms->nb_prefix_samples0 + frame_parms->ofdm_symbol_size], frame_parms->ofdm_symbol_size, 13, frame_parms->nb_prefix_samples, @@ -691,9 +687,9 @@ int main(int argc, char **argv) } } } - LOG_M("txsigF0.m","txsF0", gNB->common_vars.txdataF[0],frame_length_complex_samples_no_prefix,1,1); + LOG_M("txsigF0.m","txsF0", gNB->common_vars.txdataF[0][0],frame_length_complex_samples_no_prefix, 1, 1); if (gNB->frame_parms.nb_antennas_tx>1) - LOG_M("txsigF1.m","txsF1", gNB->common_vars.txdataF[1],frame_length_complex_samples_no_prefix,1,1); + LOG_M("txsigF1.m","txsF1", gNB->common_vars.txdataF[0][1],frame_length_complex_samples_no_prefix, 1, 1); } else { printf("Reading %d samples from file to antenna buffer %d\n",frame_length_complex_samples,0); diff --git a/openair1/SIMULATION/NR_PHY/pucchsim.c b/openair1/SIMULATION/NR_PHY/pucchsim.c index 9dd9ef61a9..9817a0b2bb 100644 --- a/openair1/SIMULATION/NR_PHY/pucchsim.c +++ b/openair1/SIMULATION/NR_PHY/pucchsim.c @@ -436,7 +436,7 @@ int main(int argc, char **argv) /* RU handles rxdataF, and gNB just has a pointer. Here, we don't have an RU, * so we need to allocate that memory as well. */ for (i = 0; i < n_rx; i++) - gNB->common_vars.rxdataF[i] = malloc16_clear(gNB->frame_parms.samples_per_frame_wCP*sizeof(c16_t)); + gNB->common_vars.rxdataF[0][i] = malloc16_clear(gNB->frame_parms.samples_per_frame_wCP * sizeof(c16_t)); double fs,txbw,rxbw; uint32_t samples; @@ -463,7 +463,7 @@ int main(int argc, char **argv) s_im = malloc(n_tx*sizeof(double*)); r_re = malloc(n_rx*sizeof(double*)); r_im = malloc(n_rx*sizeof(double*)); - memcpy((void*)&gNB->frame_parms,(void*)frame_parms,sizeof(frame_parms)); + memcpy((void *)&gNB->frame_parms, (void *)frame_parms, sizeof(*frame_parms)); for (int aatx=0; aatxcommon_vars.rxdataF[0]; + for(SNR = snr0; SNR <= snr1; SNR += 1) { ack_nack_errors=0; - sr_errors=0; + sr_errors = 0; n_errors = 0; - c16_t **txdataF = gNB->common_vars.txdataF; + c16_t **txdataF = gNB->common_vars.txdataF[0]; for (trial=0; trialofdm_symbol_size*sizeof(int)); @@ -569,7 +570,6 @@ int main(int argc, char **argv) if (n_trials==1) printf("txlev %d (%f dB), offset %d, sigma2 %f ( %f dB)\n",txlev,10*log10(txlev),startingSymbolIndex*frame_parms->ofdm_symbol_size,sigma2,sigma2_dB); - c16_t **rxdataF = gNB->common_vars.rxdataF; for (int symb=0; symbframe_parms.symbols_per_slot;symb++) { if (symb= startingSymbolIndex+nrofSymbols) { int i0 = symb*gNB->frame_parms.ofdm_symbol_size; @@ -668,7 +668,7 @@ int main(int argc, char **argv) } else pucch_pdu.freq_hop_flag = 0; - nr_decode_pucch0(gNB, nr_frame_tx, nr_slot_tx,&uci_pdu,&pucch_pdu); + nr_decode_pucch0(gNB, rxdataF, nr_frame_tx, nr_slot_tx,&uci_pdu,&pucch_pdu); if(sr_flag==1){ if (uci_pdu.sr.sr_indication == 0 || uci_pdu.sr.sr_confidence_level == 1) sr_errors+=1; @@ -721,7 +721,7 @@ int main(int argc, char **argv) pucch_pdu.second_hop_prb = N_RB_DL-1; } else pucch_pdu.freq_hop_flag = 0; - nr_decode_pucch2(gNB,nr_frame_tx,nr_slot_tx,&uci_pdu,&pucch_pdu); + nr_decode_pucch2(gNB, rxdataF, nr_frame_tx, nr_slot_tx, &uci_pdu, &pucch_pdu); int csi_part1_bytes=pucch_pdu.bit_len_csi_part1>>3; if ((pucch_pdu.bit_len_csi_part1&7) > 0) csi_part1_bytes++; for (int i=0;igNB_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); - for (i = 0; i < n_rx; i++) - free(gNB->common_vars.rxdataF[i]); + for (int j = 0; j < gNB->common_vars.num_beams_period; j++) { + for (i = 0; i < n_rx; i++) + free(gNB->common_vars.rxdataF[j][i]); + } phy_free_nr_gNB(gNB); free(RC.gNB[0]); free(RC.gNB); diff --git a/openair1/SIMULATION/NR_PHY/ulsim.c b/openair1/SIMULATION/NR_PHY/ulsim.c index b4a44f4130..910d076e0f 100644 --- a/openair1/SIMULATION/NR_PHY/ulsim.c +++ b/openair1/SIMULATION/NR_PHY/ulsim.c @@ -625,6 +625,7 @@ int main(int argc, char *argv[]) for (i = 0; i < RC.nb_nr_macrlc_inst; i++) RC.nb_nr_mac_CC[i] = 1; mac_top_init_gNB(ngran_gNB, scc, NULL /* scd will be updated further below */, &conf); + nr_mac_config_scc(RC.nrmac[0], scc, &conf); NR_ServingCellConfig_t *scd = calloc(1,sizeof(NR_ServingCellConfig_t)); prepare_scd(scd); @@ -656,7 +657,7 @@ int main(int argc, char *argv[]) /* RU handles rxdataF, and gNB just has a pointer. Here, we don't have an RU, * so we need to allocate that memory as well. */ for (i = 0; i < n_rx; i++) - gNB->common_vars.rxdataF[i] = malloc16_clear(gNB->frame_parms.samples_per_frame_wCP*sizeof(int32_t)); + gNB->common_vars.rxdataF[0][i] = malloc16_clear(gNB->frame_parms.samples_per_frame_wCP*sizeof(int32_t)); N_RB_DL = gNB->frame_parms.N_RB_DL; /* no RU: need to have rxdata */ @@ -723,7 +724,7 @@ int main(int argc, char *argv[]) NR_gNB_ULSCH_t *ulsch_gNB = &gNB->ulsch[UE_id]; - NR_Sched_Rsp_t *Sched_INFO = malloc(sizeof(*Sched_INFO)); + NR_Sched_Rsp_t *Sched_INFO = malloc16_clear(sizeof(*Sched_INFO)); memset((void*)Sched_INFO,0,sizeof(*Sched_INFO)); nfapi_nr_ul_tti_request_t *UL_tti_req = &Sched_INFO->UL_tti_req; Sched_INFO->sched_response_id = -1; @@ -936,6 +937,7 @@ int main(int argc, char *argv[]) } //--------------- int ret = 1; + int srs_ret = do_SRS; for (SNR = snr0; SNR <= snr1; SNR += snr_step) { varArray_t *table_rx=initVarArray(1000,sizeof(double)); @@ -971,6 +973,9 @@ int main(int argc, char *argv[]) int max_pusch_delay = INT_MIN; int delay_pusch_est_count = 0; + int64_t sum_srs_snr = 0; + int srs_snr_count = 0; + for (trial = 0; trial < n_trials; trial++) { uint8_t round = 0; @@ -1070,6 +1075,7 @@ int main(int argc, char *argv[]) srs_pdu->subcarrier_spacing = frame_parms->subcarrier_spacing; srs_pdu->num_ant_ports = n_tx == 4 ? 2 : n_tx == 2 ? 1 : 0; srs_pdu->sequence_id = 40; + srs_pdu->time_start_position = frame_parms->symbols_per_slot - 1; srs_pdu->config_index = rrc_get_max_nr_csrs(srs_pdu->bwp_size, srs_pdu->bandwidth_index); srs_pdu->resource_type = NR_SRS_Resource__resourceType_PR_periodic; srs_pdu->t_srs = 1; @@ -1228,7 +1234,7 @@ int main(int argc, char *argv[]) for (int aa = 0; aa < gNB->frame_parms.nb_antennas_rx; aa++) nr_slot_fep_ul(&gNB->frame_parms, (int32_t *)rxdata[aa], - (int32_t *)gNB->common_vars.rxdataF[aa], + (int32_t *)gNB->common_vars.rxdataF[0][aa], symbol, slot, 0); @@ -1236,7 +1242,7 @@ int main(int argc, char *argv[]) int offset = (slot & 3) * gNB->frame_parms.symbols_per_slot * gNB->frame_parms.ofdm_symbol_size; for (int aa = 0; aa < gNB->frame_parms.nb_antennas_rx; aa++) { apply_nr_rotation_RX(&gNB->frame_parms, - gNB->common_vars.rxdataF[aa], + gNB->common_vars.rxdataF[0][aa], gNB->frame_parms.symbol_rotation[1], slot, gNB->frame_parms.N_RB_UL, @@ -1249,15 +1255,15 @@ int main(int argc, char *argv[]) if (n_trials == 1 && round == 0) { LOG_M("rxsig0.m", "rx0", &rxdata[0][slot_offset], slot_length, 1, 1); - LOG_M("rxsigF0.m", "rxsF0", gNB->common_vars.rxdataF[0], 14 * frame_parms->ofdm_symbol_size, 1, 1); + LOG_M("rxsigF0.m", "rxsF0", gNB->common_vars.rxdataF[0][0], 14 * frame_parms->ofdm_symbol_size, 1, 1); if (precod_nbr_layers > 1) { LOG_M("rxsig1.m", "rx1", &rxdata[1][slot_offset], slot_length, 1, 1); - LOG_M("rxsigF1.m", "rxsF1", gNB->common_vars.rxdataF[1], 14 * frame_parms->ofdm_symbol_size, 1, 1); + LOG_M("rxsigF1.m", "rxsF1", gNB->common_vars.rxdataF[0][1], 14 * frame_parms->ofdm_symbol_size, 1, 1); if (precod_nbr_layers == 4) { LOG_M("rxsig2.m", "rx2", &rxdata[2][slot_offset], slot_length, 1, 1); LOG_M("rxsig3.m", "rx3", &rxdata[3][slot_offset], slot_length, 1, 1); - LOG_M("rxsigF2.m", "rxsF2", gNB->common_vars.rxdataF[2], 14 * frame_parms->ofdm_symbol_size, 1, 1); - LOG_M("rxsigF3.m", "rxsF3", gNB->common_vars.rxdataF[3], 14 * frame_parms->ofdm_symbol_size, 1, 1); + LOG_M("rxsigF2.m", "rxsF2", gNB->common_vars.rxdataF[0][2], 14 * frame_parms->ofdm_symbol_size, 1, 1); + LOG_M("rxsigF3.m", "rxsF3", gNB->common_vars.rxdataF[0][3], 14 * frame_parms->ofdm_symbol_size, 1, 1); } } } @@ -1435,6 +1441,10 @@ int main(int argc, char *argv[]) max_pusch_delay = max(ulsch_gNB->delay.est_delay, max_pusch_delay); delay_pusch_est_count++; + if (do_SRS == 1) { + sum_srs_snr += gNB->srs->snr; + srs_snr_count++; + } } // trial loop roundStats/=((float)n_trials); @@ -1470,8 +1480,14 @@ int main(int argc, char *argv[]) printf(") Avg round %.2f, Eff Rate %.4f bits/slot, Eff Throughput %.2f, TBS %u bits/slot\n", roundStats,effRate,effTP,TBS); - printf("DMRS-PUSCH delay estimation: min %i, max %i, average %f\n", - min_pusch_delay >> 1, max_pusch_delay >> 1, (double)sum_pusch_delay / (2 * delay_pusch_est_count)); + double av_delay = (double)sum_pusch_delay / (2 * delay_pusch_est_count); + printf("DMRS-PUSCH delay estimation: min %i, max %i, average %2.1f\n", min_pusch_delay >> 1, max_pusch_delay >> 1, av_delay); + + if (do_SRS == 1) { + float srs_snr_av = (float)sum_srs_snr / srs_snr_count; + srs_ret = srs_snr_av >= 0.7 * SNR || srs_snr_av > 30 ? 0 : 1; + printf("SNR based on SRS: %2.1f dB\n", srs_snr_av); + } printf("*****************************************\n"); printf("\n"); @@ -1518,7 +1534,7 @@ int main(int argc, char *argv[]) if(n_trials==1) break; - if ((float)effTP >= eff_tp_check) { + if (srs_ret == 0 && (float)effTP >= eff_tp_check) { printf("*************\n"); printf("PUSCH test OK\n"); printf("*************\n"); diff --git a/openair2/E1AP/e1ap.c b/openair2/E1AP/e1ap.c index df359c9234..1e28ebd52a 100644 --- a/openair2/E1AP/e1ap.c +++ b/openair2/E1AP/e1ap.c @@ -1662,7 +1662,7 @@ void extract_BEARER_CONTEXT_RELEASE_COMMAND(const E1AP_E1AP_PDU_t *pdu, e1ap_bea if ((ie->value.choice.Cause.present != E1AP_Cause_PR_NOTHING) && (ie->value.choice.Cause.present != E1AP_Cause_PR_choice_extension)) bearerCxt->cause = ie->value.choice.Cause.choice.radioNetwork; - + break; default: LOG_E(E1AP, "Handle for this IE is not implemented (or) invalid IE detected\n"); diff --git a/openair2/ENB_APP/enb_paramdef.h b/openair2/ENB_APP/enb_paramdef.h index ff594608ac..5fd4cdce70 100644 --- a/openair2/ENB_APP/enb_paramdef.h +++ b/openair2/ENB_APP/enb_paramdef.h @@ -169,7 +169,7 @@ typedef enum { #define RU_NUM_INTERFACES 39 #define RU_HALF_SLOT_PARALLELIZATION 40 #define RU_RU_THREAD_CORE 41 -#define RU_GPIO_CONTROL 42 +#define RU_GPIO_CONTROL 42 /*-----------------------------------------------------------------------------------------------------------------------------------------*/ /* RU configuration parameters */ /* optname helpstr paramflags XXXptr defXXXval type numelt */ diff --git a/openair2/GNB_APP/L1_nr_paramdef.h b/openair2/GNB_APP/L1_nr_paramdef.h index 1c3d7e98ec..b6d2e87d9c 100644 --- a/openair2/GNB_APP/L1_nr_paramdef.h +++ b/openair2/GNB_APP/L1_nr_paramdef.h @@ -78,7 +78,7 @@ {CONFIG_STRING_L1_PUCCH0_DTX_THRESHOLD, NULL, 0, .uptr=NULL, .defintval=100, TYPE_UINT, 0}, \ {CONFIG_STRING_L1_PRACH_DTX_THRESHOLD, NULL, 0, .uptr=NULL, .defintval=150, TYPE_UINT, 0}, \ {CONFIG_STRING_L1_PUSCH_DTX_THRESHOLD, NULL, 0, .uptr=NULL, .defintval=50, TYPE_UINT, 0}, \ - {CONFIG_STRING_L1_SRS_DTX_THRESHOLD, NULL, 0, .uptr=NULL, .defintval=50, TYPE_UINT, 0}, \ + {CONFIG_STRING_L1_SRS_DTX_THRESHOLD, NULL, 0, .uptr=NULL, .defintval=30, TYPE_UINT, 0}, \ {CONFIG_STRING_L1_MAX_LDPC_ITERATIONS, NULL, 0, .uptr=NULL, .defintval=8, TYPE_UINT, 0}, \ {CONFIG_STRING_L1_RX_THREAD_CORE, NULL, 0, .uptr=NULL, .defintval=-1, TYPE_UINT, 0}, \ {CONFIG_STRING_L1_TX_THREAD_CORE, NULL, 0, .uptr=NULL, .defintval=-1, TYPE_UINT, 0}, \ diff --git a/openair2/GNB_APP/RRC_nr_paramsvalues.h b/openair2/GNB_APP/RRC_nr_paramsvalues.h index bfda253fbf..5b77da80b4 100644 --- a/openair2/GNB_APP/RRC_nr_paramsvalues.h +++ b/openair2/GNB_APP/RRC_nr_paramsvalues.h @@ -34,7 +34,6 @@ #define __NR_RRC_PARAMSVALUES__H__ #include "common/config/config_paramdesc.h" -#include "NR_ServingCellConfigCommon.h" /* cell configuration section name */ #define GNB_CONFIG_STRING_GNB_LIST "gNBs" @@ -91,6 +90,22 @@ #define GNB_CONFIG_STRING_P0NOMINAL "p0_nominal" #define GNB_CONFIG_STRING_PUCCHRES "pucch_ResourceCommon" +#define GNB_CONFIG_STRING_MSGBRESPONSEWINDOW_R16 "msgB_ResponseWindow_r16" +#define GNB_CONFIG_STRING_MSGARSRPTHRESHOLD_R16 "msgA_RSRP_Threshold_r16" +#define GNB_CONFIG_STRING_MSGACBPREAMBLESPERSHAREDRO_R16 "msgA_CB_PreamblesPerSSB_PerSharedRO_r16" +#define GNB_CONFIG_STRING_MSGAMCS_R16 "msgA_MCS_r16" +#define GNB_CONFIG_STRING_NROFSLOTSMSGAPUSCH_R16 "nrofSlotsMsgA_PUSCH_r16" +#define GNB_CONFIG_STRING_NROFMSGAPOPERSLOT_R16 "nrofMsgA_PO_PerSlot_r16" +#define GNB_CONFIG_STRING_MSGAPUSCHTIMEDOMAINOFFSET_R16 "msgA_PUSCH_TimeDomainOffset_r16" +#define GNB_CONFIG_STRING_STARTSYMBOLANDLENGTHMSGA_PO_R16 "startSymbolAndLengthMsgA_PO_r16" +#define GNB_CONFIG_STRING_MAPPINGTYPEMSGAPUSCH_R16 "mappingTypeMsgA_PUSCH_r16" +#define GNB_CONFIG_STRING_GUARDBANDMSGAPUSCH_R16 "guardBandMsgA_PUSCH_r16" +#define GNB_CONFIG_STRING_FREQUENCYSTARTMSGAPUSCH_R16 "frequencyStartMsgA_PUSCH_r16" +#define GNB_CONFIG_STRING_NROFPRBSPERMSGAPO_R16 "nrofPRBs_PerMsgA_PO_r16" +#define GNB_CONFIG_STRING_NROFMSGAPOFDM_R16 "nrofMsgA_PO_FDM_r16" +#define GNB_CONFIG_STRING_MSGAPUSCHNROFPORTS_R16 "msgA_PUSCH_NrofPorts_r16" +#define GNB_CONFIG_STRING_NROFDMRSSEQUENCES_R16 "nrofDMRS_Sequences_r16" +#define GNB_CONFIG_STRING_MSGATRANSFORMPRECODER_R16 "msgA_TransformPrecoder_r16" #define GNB_CONFIG_STRING_SSBPOSITIONSINBURST "ssb_PositionsInBurst_Bitmap" #define GNB_CONFIG_STRING_SSBPERIODICITYSERVINGCELL "ssb_periodicityServingCell" @@ -296,4 +311,25 @@ {GNB_CONFIG_STRING_LOCATIONANDBANDWIDTH_ULBWP4,NULL,0,.i64ptr=&scd->uplinkConfig->uplinkBWP_ToAddModList->list.array[3]->bwp_Common->genericParameters.locationAndBandwidth,.defint64val=0,TYPE_INT64,0}, \ {GNB_CONFIG_STRING_DEFAULTDLBWP_ID,NULL,0,.i64ptr=scd->defaultDownlinkBWP_Id,.defint64val=0,TYPE_INT64,0}} +/*-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------*/ +/* Serving Cell Config Common configuration parameters to apply in RA 2-Step */ +/*-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------*/ + +#define MSGASCCPARAMS_DESC(scc) { \ +{GNB_CONFIG_STRING_MSGBRESPONSEWINDOW_R16,NULL,0,.i64ptr=scc->uplinkConfigCommon->initialUplinkBWP->ext1->msgA_ConfigCommon_r16->choice.setup->rach_ConfigCommonTwoStepRA_r16.rach_ConfigGenericTwoStepRA_r16.msgB_ResponseWindow_r16,.defintval=-1,TYPE_INT64,0},\ +{GNB_CONFIG_STRING_MSGARSRPTHRESHOLD_R16,NULL,0,.i64ptr=scc->uplinkConfigCommon->initialUplinkBWP->ext1->msgA_ConfigCommon_r16->choice.setup->rach_ConfigCommonTwoStepRA_r16.msgA_RSRP_Threshold_r16,.defintval=19,TYPE_INT64,0},\ +{GNB_CONFIG_STRING_MSGAMCS_R16,NULL,0,.i64ptr=&scc->uplinkConfigCommon->initialUplinkBWP->ext1->msgA_ConfigCommon_r16->choice.setup->msgA_PUSCH_Config_r16->msgA_PUSCH_ResourceGroupA_r16->msgA_MCS_r16,.defintval=2,TYPE_INT64,0},\ +{GNB_CONFIG_STRING_NROFSLOTSMSGAPUSCH_R16,NULL,0,.i64ptr=&scc->uplinkConfigCommon->initialUplinkBWP->ext1->msgA_ConfigCommon_r16->choice.setup->msgA_PUSCH_Config_r16->msgA_PUSCH_ResourceGroupA_r16->nrofSlotsMsgA_PUSCH_r16,.defintval=1,TYPE_INT64,0},\ +{GNB_CONFIG_STRING_NROFMSGAPOPERSLOT_R16,NULL,0,.i64ptr=&scc->uplinkConfigCommon->initialUplinkBWP->ext1->msgA_ConfigCommon_r16->choice.setup->msgA_PUSCH_Config_r16->msgA_PUSCH_ResourceGroupA_r16->nrofMsgA_PO_PerSlot_r16,.defintval=NR_MsgA_PUSCH_Resource_r16__nrofMsgA_PO_PerSlot_r16_one,TYPE_INT64,0},\ +{GNB_CONFIG_STRING_MSGAPUSCHTIMEDOMAINOFFSET_R16,NULL,0,.i64ptr=&scc->uplinkConfigCommon->initialUplinkBWP->ext1->msgA_ConfigCommon_r16->choice.setup->msgA_PUSCH_Config_r16->msgA_PUSCH_ResourceGroupA_r16->msgA_PUSCH_TimeDomainOffset_r16,.defintval=0,TYPE_INT64,0},\ +{GNB_CONFIG_STRING_STARTSYMBOLANDLENGTHMSGA_PO_R16,NULL,0,.i64ptr=scc->uplinkConfigCommon->initialUplinkBWP->ext1->msgA_ConfigCommon_r16->choice.setup->msgA_PUSCH_Config_r16->msgA_PUSCH_ResourceGroupA_r16->startSymbolAndLengthMsgA_PO_r16,.defintval=38,TYPE_INT64,0},\ +{GNB_CONFIG_STRING_MAPPINGTYPEMSGAPUSCH_R16,NULL,0,.i64ptr=scc->uplinkConfigCommon->initialUplinkBWP->ext1->msgA_ConfigCommon_r16->choice.setup->msgA_PUSCH_Config_r16->msgA_PUSCH_ResourceGroupA_r16->mappingTypeMsgA_PUSCH_r16,.defintval=0,TYPE_INT64,0},\ +{GNB_CONFIG_STRING_GUARDBANDMSGAPUSCH_R16,NULL,0,.i64ptr=&scc->uplinkConfigCommon->initialUplinkBWP->ext1->msgA_ConfigCommon_r16->choice.setup->msgA_PUSCH_Config_r16->msgA_PUSCH_ResourceGroupA_r16->guardBandMsgA_PUSCH_r16,.defintval=0,TYPE_INT64,0}, \ +{GNB_CONFIG_STRING_FREQUENCYSTARTMSGAPUSCH_R16,NULL,0,.i64ptr=&scc->uplinkConfigCommon->initialUplinkBWP->ext1->msgA_ConfigCommon_r16->choice.setup->msgA_PUSCH_Config_r16->msgA_PUSCH_ResourceGroupA_r16->frequencyStartMsgA_PUSCH_r16,.defintval=0,TYPE_INT64,0}, \ +{GNB_CONFIG_STRING_NROFPRBSPERMSGAPO_R16,NULL,0,.i64ptr=&scc->uplinkConfigCommon->initialUplinkBWP->ext1->msgA_ConfigCommon_r16->choice.setup->msgA_PUSCH_Config_r16->msgA_PUSCH_ResourceGroupA_r16->nrofPRBs_PerMsgA_PO_r16,.defintval=8,TYPE_INT64,0}, \ +{GNB_CONFIG_STRING_NROFMSGAPOFDM_R16,NULL,0,.i64ptr=&scc->uplinkConfigCommon->initialUplinkBWP->ext1->msgA_ConfigCommon_r16->choice.setup->msgA_PUSCH_Config_r16->msgA_PUSCH_ResourceGroupA_r16->nrofMsgA_PO_FDM_r16,.defintval=NR_MsgA_PUSCH_Resource_r16__nrofMsgA_PO_FDM_r16_one,TYPE_INT64,0}, \ +{GNB_CONFIG_STRING_MSGAPUSCHNROFPORTS_R16,NULL,0,.i64ptr=scc->uplinkConfigCommon->initialUplinkBWP->ext1->msgA_ConfigCommon_r16->choice.setup->msgA_PUSCH_Config_r16->msgA_PUSCH_ResourceGroupA_r16->msgA_DMRS_Config_r16.msgA_PUSCH_NrofPorts_r16,.defintval=1,TYPE_INT64,0},\ +{GNB_CONFIG_STRING_NROFDMRSSEQUENCES_R16,NULL,0,.i64ptr=&scc->uplinkConfigCommon->initialUplinkBWP->ext1->msgA_ConfigCommon_r16->choice.setup->msgA_PUSCH_Config_r16->msgA_PUSCH_ResourceGroupA_r16->nrofDMRS_Sequences_r16,.defintval=1,TYPE_INT64,0},\ +{GNB_CONFIG_STRING_MSGATRANSFORMPRECODER_R16,NULL,0,.i64ptr=scc->uplinkConfigCommon->initialUplinkBWP->ext1->msgA_ConfigCommon_r16->choice.setup->msgA_PUSCH_Config_r16->msgA_TransformPrecoder_r16,.defintval=NR_MsgA_PUSCH_Config_r16__msgA_TransformPrecoder_r16_disabled,TYPE_INT64,0},\ +{GNB_CONFIG_STRING_MSGACBPREAMBLESPERSHAREDRO_R16,NULL,0,.i64ptr=scc->uplinkConfigCommon->initialUplinkBWP->ext1->msgA_ConfigCommon_r16->choice.setup->rach_ConfigCommonTwoStepRA_r16.msgA_CB_PreamblesPerSSB_PerSharedRO_r16,.defintval=1,TYPE_INT64,0}} #endif diff --git a/openair2/GNB_APP/gnb_config.c b/openair2/GNB_APP/gnb_config.c index a528835b03..73e0481a4b 100644 --- a/openair2/GNB_APP/gnb_config.c +++ b/openair2/GNB_APP/gnb_config.c @@ -49,6 +49,11 @@ #endif #include "lib/f1ap_interface_management.h" +static int DEFBANDS[] = {7}; +static int DEFENBS[] = {0}; +static int DEFBFW[] = {0x00007fff}; +static int DEFRUTPCORES[] = {-1,-1,-1,-1}; + /** * @brief Helper define to allocate and initialize SetupRelease structures */ @@ -145,6 +150,28 @@ void prepare_scc(NR_ServingCellConfigCommon_t *scc) scc->ext2->ntn_Config_r17->ephemerisInfo_r17->choice.positionVelocity_r17 = calloc_or_fail(1, sizeof(*scc->ext2->ntn_Config_r17->ephemerisInfo_r17->choice.positionVelocity_r17)); } +void prepare_msgA_scc(NR_ServingCellConfigCommon_t *scc) { + NR_BWP_UplinkCommon_t *initialUplinkBWP = scc->uplinkConfigCommon->initialUplinkBWP; + // Add the struct ext1 + initialUplinkBWP->ext1 = calloc(1, sizeof(*initialUplinkBWP->ext1)); + initialUplinkBWP->ext1->msgA_ConfigCommon_r16 = calloc(1, sizeof(*initialUplinkBWP->ext1->msgA_ConfigCommon_r16)); + initialUplinkBWP->ext1->msgA_ConfigCommon_r16->present = NR_SetupRelease_MsgA_ConfigCommon_r16_PR_setup; + initialUplinkBWP->ext1->msgA_ConfigCommon_r16->choice.setup = + calloc(1, sizeof(*initialUplinkBWP->ext1->msgA_ConfigCommon_r16->choice.setup)); + NR_MsgA_ConfigCommon_r16_t *NR_MsgA_ConfigCommon_r16 = initialUplinkBWP->ext1->msgA_ConfigCommon_r16->choice.setup; + NR_MsgA_ConfigCommon_r16->rach_ConfigCommonTwoStepRA_r16.rach_ConfigGenericTwoStepRA_r16.msgB_ResponseWindow_r16 = + calloc(1, sizeof(long)); + NR_MsgA_ConfigCommon_r16->rach_ConfigCommonTwoStepRA_r16.msgA_RSRP_Threshold_r16 = calloc(1, sizeof(NR_RSRP_Range_t)); + + NR_MsgA_ConfigCommon_r16->rach_ConfigCommonTwoStepRA_r16.msgA_CB_PreamblesPerSSB_PerSharedRO_r16 = calloc(1, sizeof(long)); + + NR_MsgA_ConfigCommon_r16->msgA_PUSCH_Config_r16 = calloc(1, sizeof(NR_MsgA_PUSCH_Config_r16_t)); + NR_MsgA_PUSCH_Config_r16_t *msgA_PUSCH_Config_r16 = NR_MsgA_ConfigCommon_r16->msgA_PUSCH_Config_r16; + msgA_PUSCH_Config_r16->msgA_PUSCH_ResourceGroupA_r16 = calloc(1, sizeof(NR_MsgA_PUSCH_Resource_r16_t)); + NR_MsgA_PUSCH_Resource_r16_t *msgA_PUSCH_Resource = msgA_PUSCH_Config_r16->msgA_PUSCH_ResourceGroupA_r16; + msgA_PUSCH_Resource->startSymbolAndLengthMsgA_PO_r16 = calloc(1, sizeof(long)); + msgA_PUSCH_Config_r16->msgA_TransformPrecoder_r16 = calloc(1, sizeof(long)); +} // Section 4.1 in 38.213 NR_ServingCellConfigCommon__ssb_PositionsInBurst_PR get_ssb_len(NR_ServingCellConfigCommon_t *scc) @@ -266,7 +293,7 @@ void fill_scc_sim(NR_ServingCellConfigCommon_t *scc, uint64_t *ssb_bitmap, int N rach_ConfigCommon->choice.setup->prach_RootSequenceIndex.present = NR_RACH_ConfigCommon__prach_RootSequenceIndex_PR_l139; rach_ConfigCommon->choice.setup->prach_RootSequenceIndex.choice.l139 = 0; rach_ConfigCommon->choice.setup->restrictedSetConfig = NR_RACH_ConfigCommon__restrictedSetConfig_unrestrictedSet; - *rach_ConfigCommon->choice.setup->msg1_SubcarrierSpacing = -1; + *rach_ConfigCommon->choice.setup->msg1_SubcarrierSpacing = mu_ul; struct NR_SetupRelease_PUSCH_ConfigCommon *pusch_ConfigCommon = initialUplinkBWP->pusch_ConfigCommon; asn1cSeqAdd(&pusch_ConfigCommon->choice.setup->pusch_TimeDomainAllocationList->list, add_PUSCH_TimeDomainResourceAllocation(55)); @@ -384,6 +411,14 @@ void fix_scc(NR_ServingCellConfigCommon_t *scc, uint64_t ssbmap) scc->uplinkConfigCommon->initialUplinkBWP->rach_ConfigCommon->choice.setup->msg1_SubcarrierSpacing=NULL; } + if (scc->uplinkConfigCommon->initialUplinkBWP->ext1 + && (int)scc->uplinkConfigCommon->initialUplinkBWP->ext1->msgA_ConfigCommon_r16->choice.setup->msgA_PUSCH_Config_r16 + ->msgA_PUSCH_ResourceGroupA_r16->msgA_PUSCH_TimeDomainOffset_r16 + == 0) { + free(scc->uplinkConfigCommon->initialUplinkBWP->ext1); + scc->uplinkConfigCommon->initialUplinkBWP->ext1 = NULL; + } + if ((int)*scc->n_TimingAdvanceOffset == -1) { free(scc->n_TimingAdvanceOffset); scc->n_TimingAdvanceOffset = NULL; @@ -935,14 +970,20 @@ static NR_ServingCellConfigCommon_t *get_scc_config(configmodule_interface_t *cf uint64_t ssb_bitmap=0xff; prepare_scc(scc); paramdef_t SCCsParams[] = SCCPARAMS_DESC(scc); + prepare_msgA_scc(scc); + paramdef_t MsgASCCsParams[] = MSGASCCPARAMS_DESC(scc); paramlist_def_t SCCsParamList = {GNB_CONFIG_STRING_SERVINGCELLCONFIGCOMMON, NULL, 0}; + paramlist_def_t MsgASCCsParamList = {GNB_CONFIG_STRING_SERVINGCELLCONFIGCOMMON, NULL, 0}; char aprefix[MAX_OPTNAME_SIZE*2 + 8]; sprintf(aprefix, "%s.[%i]", GNB_CONFIG_STRING_GNB_LIST, 0); config_getlist(cfg, &SCCsParamList, NULL, 0, aprefix); - if (SCCsParamList.numelt > 0) { + config_getlist(cfg, &MsgASCCsParamList, NULL, 0, aprefix); + + if (SCCsParamList.numelt > 0 || MsgASCCsParamList.numelt > 0) { sprintf(aprefix, "%s.[%i].%s.[%i]", GNB_CONFIG_STRING_GNB_LIST,0,GNB_CONFIG_STRING_SERVINGCELLCONFIGCOMMON, 0); config_get(cfg, SCCsParams, sizeofArray(SCCsParams), aprefix); + config_get(cfg, MsgASCCsParams, sizeofArray(MsgASCCsParams), aprefix); struct NR_FrequencyInfoDL *frequencyInfoDL = scc->downlinkConfigCommon->frequencyInfoDL; LOG_I(RRC, "Read in ServingCellConfigCommon (PhysCellId %d, ABSFREQSSB %d, DLBand %d, ABSFREQPOINTA %d, DLBW " @@ -1267,6 +1308,21 @@ void RCconfig_nr_macrlc(configmodule_interface_t *cfg) config.pdsch_AntennaPorts.XP, config.pusch_AntennaPorts); + paramdef_t RUParams[] = RUPARAMS_DESC; + paramlist_def_t RUParamList = {CONFIG_STRING_RU_LIST, NULL, 0}; + config_getlist(config_get_if(), &RUParamList, RUParams, sizeofArray(RUParams), NULL); + int num_tx = 0; + if (RUParamList.numelt > 0) { + for (int i = 0; i < RUParamList.numelt; i++) + num_tx += *(RUParamList.paramarray[i][RU_NB_TX_IDX].uptr); + AssertFatal(num_tx >= config.pdsch_AntennaPorts.XP * config.pdsch_AntennaPorts.N1 * config.pdsch_AntennaPorts.N2, + "Number of logical antenna ports (set in config file with pdsch_AntennaPorts) cannot be larger than physical antennas (nb_tx)\n"); + } + else { + // TODO temporary solution for 3rd party RU or nFAPI, in which case we don't have RU section present in the config file + num_tx = config.pdsch_AntennaPorts.XP * config.pdsch_AntennaPorts.N1 * config.pdsch_AntennaPorts.N2; + LOG_E(GNB_APP, "RU information not present in config file. Assuming physical antenna ports equal to logical antenna ports %d\n", num_tx); + } config.minRXTXTIME = *GNBParamList.paramarray[0][GNB_MINRXTXTIME_IDX].iptr; LOG_I(GNB_APP, "minTXRXTIME %d\n", config.minRXTXTIME); config.sib1_tda = *GNBParamList.paramarray[0][GNB_SIB1_TDA_IDX].iptr; @@ -1324,6 +1380,19 @@ void RCconfig_nr_macrlc(configmodule_interface_t *cfg) config.timer_config.n311, config.timer_config.t319); + if (config_isparamset(GNBParamList.paramarray[0], GNB_BEAMWEIGHTS_IDX)) { + int n = GNBParamList.paramarray[0][GNB_BEAMWEIGHTS_IDX].numelt; + AssertFatal(n % num_tx == 0, "Error! Number of beam input needs to be multiple of TX antennas\n"); + // each beam is described by a set of weights (one for each antenna) + // on the other hand in case of analog beamforming an index to the RU beam identifier is provided + config.nb_bfw[0] = num_tx; // number of tx antennas + config.nb_bfw[1] = n / num_tx; // number of beams + config.bw_list = malloc16_clear(n * sizeof(*config.bw_list)); + for (int b = 0; b < n; b++) { + config.bw_list[b] = GNBParamList.paramarray[0][GNB_BEAMWEIGHTS_IDX].iptr[b]; + } + } + NR_ServingCellConfigCommon_t *scc = get_scc_config(cfg, config.minRXTXTIME); //xer_fprint(stdout, &asn_DEF_NR_ServingCellConfigCommon, scc); NR_ServingCellConfig_t *scd = get_scd_config(cfg); @@ -1424,6 +1493,8 @@ void RCconfig_nr_macrlc(configmodule_interface_t *cfg) beam_info->beams_per_period = beams_per_period; beam_info->beam_allocation_size = -1; // to be initialized once we have information on frame configuration } + // triggers also PHY initialization in case we have L1 via FAPI + nr_mac_config_scc(RC.nrmac[j], scc, &config); } // for (j=0;j 0) { + if (MacRLC_ParamList.numelt > 0) { RC.nb_nr_macrlc_inst = MacRLC_ParamList.numelt; for (int j = 0; j < RC.nb_nr_macrlc_inst; j++) { if (strcmp(*(MacRLC_ParamList.paramarray[j][MACRLC_TRANSPORT_N_PREFERENCE_IDX].strptr), "f1") == 0) { diff --git a/openair2/GNB_APP/gnb_paramdef.h b/openair2/GNB_APP/gnb_paramdef.h index 253d94b44a..57153698f1 100644 --- a/openair2/GNB_APP/gnb_paramdef.h +++ b/openair2/GNB_APP/gnb_paramdef.h @@ -131,22 +131,23 @@ typedef enum { #define GNB_CONFIG_STRING_DRBS "drbs" #define GNB_CONFIG_STRING_USE_DELTA_MCS "use_deltaMCS" #define GNB_CONFIG_HLP_USE_DELTA_MCS "Use deltaMCS-based power headroom reporting in PUSCH-Config" -#define GNB_CONFIG_HLP_FORCEUL256QAMOFF "suppress activation of UL 256 QAM despite UE support" +#define GNB_CONFIG_HLP_FORCEUL256QAMOFF "suppress activation of UL 256 QAM despite UE support" #define GNB_CONFIG_STRING_FORCEUL256QAMOFF "force_UL256qam_off" -#define GNB_CONFIG_STRING_GNB_DU_ID "gNB_DU_ID" -#define GNB_CONFIG_STRING_GNB_CU_UP_ID "gNB_CU_UP_ID" -#define GNB_CONFIG_STRING_NUM_DL_HARQPROCESSES "num_dlharq" -#define GNB_CONFIG_STRING_NUM_UL_HARQPROCESSES "num_ulharq" +#define GNB_CONFIG_STRING_GNB_DU_ID "gNB_DU_ID" +#define GNB_CONFIG_STRING_GNB_CU_UP_ID "gNB_CU_UP_ID" +#define GNB_CONFIG_STRING_NUM_DL_HARQPROCESSES "num_dlharq" +#define GNB_CONFIG_STRING_NUM_UL_HARQPROCESSES "num_ulharq" +#define GNB_CONFIG_STRING_BEAM_WEIGHTS_LIST "beam_weights" #define GNB_CONFIG_HLP_STRING_ENABLE_SDAP "enable the SDAP layer\n" #define GNB_CONFIG_HLP_FORCE256QAMOFF "suppress activation of 256 QAM despite UE support" #define GNB_CONFIG_HLP_MAXMIMOLAYERS "limit on maxMIMO-layers for DL" #define GNB_CONFIG_HLP_DISABLE_HARQ "disable feedback for all HARQ processes (REL17 feature)" #define GNB_CONFIG_HLP_STRING_DRBS "Number of total DRBs to establish, including the mandatory for PDU SEssion (default=1)\n" -#define GNB_CONFIG_HLP_GNB_DU_ID "defines the gNB-DU ID (only applicable for DU)" -#define GNB_CONFIG_HLP_GNB_CU_UP_ID "defines the gNB-CU-UP ID (only applicable for CU-UP)" -#define GNB_CONFIG_HLP_NUM_DL_HARQ "Set Num DL harq processes. Valid values 2,4,6,8,10,12,16,32. Default 16" -#define GNB_CONFIG_HLP_NUM_UL_HARQ "Set Num UL harq processes. Valid values 16,32. Default 16" +#define GNB_CONFIG_HLP_GNB_DU_ID "defines the gNB-DU ID (only applicable for DU)" +#define GNB_CONFIG_HLP_GNB_CU_UP_ID "defines the gNB-CU-UP ID (only applicable for CU-UP)" +#define GNB_CONFIG_HLP_NUM_DL_HARQ "Set Num DL harq processes. Valid values 2,4,6,8,10,12,16,32. Default 16" +#define GNB_CONFIG_HLP_NUM_UL_HARQ "Set Num UL harq processes. Valid values 16,32. Default 16" /*-----------------------------------------------------------------------------------------------------------------------------------------*/ /* cell configuration parameters */ @@ -187,8 +188,9 @@ typedef enum { {GNB_CONFIG_STRING_FORCEUL256QAMOFF, GNB_CONFIG_HLP_FORCEUL256QAMOFF, 0,.iptr=NULL, .defintval=0, TYPE_INT, 0}, \ {GNB_CONFIG_STRING_MAXMIMOLAYERS, GNB_CONFIG_HLP_MAXMIMOLAYERS, 0, .iptr=NULL, .defintval=-1, TYPE_INT, 0}, \ {GNB_CONFIG_STRING_DISABLE_HARQ, GNB_CONFIG_HLP_DISABLE_HARQ, PARAMFLAG_BOOL, .iptr=NULL, .defintval=0, TYPE_INT, 0}, \ -{GNB_CONFIG_STRING_NUM_DL_HARQPROCESSES, GNB_CONFIG_HLP_NUM_DL_HARQ, 0, .iptr=NULL, .defintval=16, TYPE_INT, 0}, \ -{GNB_CONFIG_STRING_NUM_UL_HARQPROCESSES, GNB_CONFIG_HLP_NUM_UL_HARQ, 0, .iptr=NULL, .defintval=16, TYPE_INT, 0}, \ +{GNB_CONFIG_STRING_NUM_DL_HARQPROCESSES, GNB_CONFIG_HLP_NUM_DL_HARQ, 0, .iptr=NULL, .defintval=16, TYPE_INT, 0}, \ +{GNB_CONFIG_STRING_NUM_UL_HARQPROCESSES, GNB_CONFIG_HLP_NUM_UL_HARQ, 0, .iptr=NULL, .defintval=16, TYPE_INT, 0}, \ +{GNB_CONFIG_STRING_BEAM_WEIGHTS_LIST, NULL, 0, .iptr=NULL, .defintarrayval=0, TYPE_INTARRAY, 0}, \ } // clang-format on @@ -228,6 +230,7 @@ typedef enum { #define GNB_DISABLE_HARQ_IDX 32 #define GNB_NUM_DL_HARQ_IDX 33 #define GNB_NUM_UL_HARQ_IDX 34 +#define GNB_BEAMWEIGHTS_IDX 35 #define TRACKING_AREA_CODE_OKRANGE {0x0001,0xFFFD} #define NUM_DL_HARQ_OKVALUES {2,4,6,8,10,12,16,32} @@ -267,8 +270,9 @@ typedef enum { { .s5 = { NULL } }, \ { .s5 = { NULL } }, \ { .s5 = { NULL } }, \ - { .s1 = { config_check_intval, NUM_DL_HARQ_OKVALUES,8 } }, \ - { .s1 = { config_check_intval, NUM_UL_HARQ_OKVALUES,2 } }, \ + { .s1 = { config_check_intval, NUM_DL_HARQ_OKVALUES,8 } }, \ + { .s1 = { config_check_intval, NUM_UL_HARQ_OKVALUES,2 } }, \ + { .s5 = { NULL } }, \ } /*-------------------------------------------------------------------------------------------------------------------------------------------------*/ @@ -633,3 +637,4 @@ typedef enum { /*----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------*/ #endif + diff --git a/openair2/LAYER2/NR_MAC_COMMON/nr_mac.h b/openair2/LAYER2/NR_MAC_COMMON/nr_mac.h index 1dff70618e..b7e2da6f10 100644 --- a/openair2/LAYER2/NR_MAC_COMMON/nr_mac.h +++ b/openair2/LAYER2/NR_MAC_COMMON/nr_mac.h @@ -244,6 +244,12 @@ typedef struct { uint8_t E: 1; } __attribute__ ((__packed__)) NR_RA_HEADER_RAPID; +typedef struct { + uint8_t RAPID: 6; + uint8_t T1: 1; + uint8_t E: 1; +} __attribute__((__packed__)) NR_RA_HEADER_RAPID_MSGB; + /*!\brief RAR MAC subheader with Backoff Indicator */ typedef struct { uint8_t BI: 4; @@ -252,7 +258,23 @@ typedef struct { uint8_t E: 1; } __attribute__ ((__packed__)) NR_RA_HEADER_BI; -// TS 38.321 ch. 6.2.3 +typedef struct { + uint8_t BI: 4; + uint8_t R: 1; + uint8_t T2: 1; + uint8_t T1: 1; + uint8_t E: 1; +} __attribute__((__packed__)) NR_RA_HEADER_BI_MSGB; + +typedef struct { + uint8_t R: 4; + uint8_t S: 1; + uint8_t T2: 1; + uint8_t T1: 1; + uint8_t E: 1; +} __attribute__((__packed__)) NR_RA_HEADER_SUCCESS_RAR_MSGB; + +// TS 38.321 Sec. 6.2.3 typedef struct { uint8_t TA1: 7; // octet 1 [6:0] uint8_t R: 1; // octet 1 [7] @@ -265,6 +287,38 @@ typedef struct { uint8_t TCRNTI_2: 8; // octet 7 [7:0] } __attribute__ ((__packed__)) NR_MAC_RAR; +// TS 38.321 Sec. 6.2.3 +typedef struct { + uint8_t TA1: 7; // octet 1 [6:0] + uint8_t R: 1; // octet 1 [7] + uint8_t UL_GRANT_1: 3; // octet 2 [2:0] + uint8_t TA2: 5; // octet 2 [7:3] + uint8_t UL_GRANT_2: 8; // octet 3 [7:0] + uint8_t UL_GRANT_3: 8; // octet 4 [7:0] + uint8_t UL_GRANT_4: 8; // octet 5 [7:0] + uint8_t TCRNTI_1: 8; // octet 6 [7:0] + uint8_t TCRNTI_2: 8; // octet 7 [7:0] +} __attribute__((__packed__)) NR_MAC_RAR_MSGB; + +// TS 38.321 Sec. 6.2.3 +typedef struct { + uint8_t CONT_RES_1: 8; // octet 1 [7:0] + uint8_t CONT_RES_2: 8; // octet 2 [7:0] + uint8_t CONT_RES_3: 8; // octet 3 [7:0] + uint8_t CONT_RES_4: 8; // octet 4 [7:0] + uint8_t CONT_RES_5: 8; // octet 5 [7:0] + uint8_t CONT_RES_6: 8; // octet 6 [7:0] + uint8_t HARQ_FTI: 3; // octet 7 [2:0] + uint8_t TPC: 2; // octet 7 [4:3] + uint8_t CH_ACESS_CPEXT: 2; // octet 7 [6:5] + uint8_t R: 1; // octet 7 [7] + uint8_t TA1: 4; // octet 8 [3:0] + uint8_t PUCCH_RI: 4; // octet 8 [7:4] + uint8_t TA2: 8; // octet 9 [7:0] + uint8_t CRNTI_1: 8; // octet 10 [7:0] + uint8_t CRNTI_2: 8; // octet 11 [7:0] +} __attribute__((__packed__)) NR_MAC_SUCCESS_RAR; + // DCI pdu structures. Used by both gNB and UE. typedef struct { uint32_t val; @@ -474,7 +528,6 @@ typedef struct Type0_PDCCH_CSS_config_s { uint32_t first_symbol_index; uint32_t search_space_duration; uint32_t search_space_frame_period; // in slots - uint32_t ssb_length; uint32_t ssb_index; int32_t cset_start_rb; NR_SubcarrierSpacing_t scs_pdcch; @@ -560,6 +613,7 @@ typedef struct NR_UE_UL_BWP { uint16_t BWPSize; uint16_t BWPStart; NR_RACH_ConfigCommon_t *rach_ConfigCommon; + NR_MsgA_ConfigCommon_r16_t *msgA_ConfigCommon_r16; NR_PUSCH_TimeDomainResourceAllocationList_t *tdaList_Common; NR_ConfiguredGrantConfig_t *configuredGrantConfig; NR_PUSCH_Config_t *pusch_Config; @@ -630,5 +684,10 @@ typedef struct NR_tda_info { bool valid_tda; } NR_tda_info_t; +typedef enum { + RA_4_STEP = 0, + RA_2_STEP = 1, +} nr_ra_type_t; + #endif /*__LAYER2_MAC_H__ */ diff --git a/openair2/LAYER2/NR_MAC_COMMON/nr_mac_common.c b/openair2/LAYER2/NR_MAC_COMMON/nr_mac_common.c index 3f0db0e4da..28bf3bfc8e 100644 --- a/openair2/LAYER2/NR_MAC_COMMON/nr_mac_common.c +++ b/openair2/LAYER2/NR_MAC_COMMON/nr_mac_common.c @@ -655,6 +655,7 @@ NR_tda_info_t get_dl_tda_info(const NR_UE_DL_BWP_t *dl_BWP, case TYPE_CS_RNTI_: case TYPE_MCS_C_RNTI_: case TYPE_RA_RNTI_: + case TYPE_MSGB_RNTI_: case TYPE_TC_RNTI_: if(tdalist) tda_info = set_tda_info_from_list(tdalist, tda_index); @@ -2658,16 +2659,17 @@ long get_transformPrecoding(const NR_UE_UL_BWP_t *current_UL_BWP, nr_dci_format_ && current_UL_BWP->configuredGrantConfig->transformPrecoder) return *current_UL_BWP->configuredGrantConfig->transformPrecoder; - if (dci_format == NR_UL_DCI_FORMAT_0_1 + long msg3_tp = NR_PUSCH_Config__transformPrecoder_disabled; + if (current_UL_BWP && current_UL_BWP->rach_ConfigCommon && current_UL_BWP->rach_ConfigCommon->msg3_transformPrecoder) + msg3_tp = NR_PUSCH_Config__transformPrecoder_enabled; + + if (dci_format != NR_UL_DCI_FORMAT_0_0 && current_UL_BWP && current_UL_BWP->pusch_Config && current_UL_BWP->pusch_Config->transformPrecoder) return *current_UL_BWP->pusch_Config->transformPrecoder; - if (current_UL_BWP && current_UL_BWP->rach_ConfigCommon && current_UL_BWP->rach_ConfigCommon->msg3_transformPrecoder) - return NR_PUSCH_Config__transformPrecoder_enabled; - - return NR_PUSCH_Config__transformPrecoder_disabled; + return msg3_tp; } uint8_t get_pusch_nb_antenna_ports(NR_PUSCH_Config_t *pusch_Config, @@ -5312,6 +5314,15 @@ rnti_t nr_get_ra_rnti(uint8_t s_id, uint8_t t_id, uint8_t f_id, uint8_t ul_carri return ra_rnti; } +rnti_t nr_get_MsgB_rnti(uint8_t s_id, uint8_t t_id, uint8_t f_id, uint8_t ul_carrier_id) +{ + // 3GPP TS 38.321 Section 5.1.3a + rnti_t MsgB_rnti = 1 + s_id + 14 * t_id + 1120 * f_id + 8960 * ul_carrier_id + 17920; + LOG_D(MAC, "f_id %d t_id %d s_id %d ul_carrier_id %d Computed MsgB_RNTI is 0x%04X\n", f_id, t_id, s_id, ul_carrier_id, MsgB_rnti); + + return MsgB_rnti; +} + int get_FeedbackDisabled(NR_DownlinkHARQ_FeedbackDisabled_r17_t *downlinkHARQ_FeedbackDisabled_r17, int harq_pid) { if (downlinkHARQ_FeedbackDisabled_r17 == NULL) @@ -5322,3 +5333,20 @@ int get_FeedbackDisabled(NR_DownlinkHARQ_FeedbackDisabled_r17_t *downlinkHARQ_Fe return (downlinkHARQ_FeedbackDisabled_r17->buf[byte_index] >> (7 - bit_index)) & 1; } + +int nr_get_prach_mu(const NR_MsgA_ConfigCommon_r16_t *msgacc, const NR_RACH_ConfigCommon_t *rach_ConfigCommon) +{ + int mu; + + // if 2-Step configuration file exists + if (msgacc && msgacc->rach_ConfigCommonTwoStepRA_r16.msgA_SubcarrierSpacing_r16) { + // Choose Subcarrier Spacing of configuration file of 2-Step + mu = *msgacc->rach_ConfigCommonTwoStepRA_r16.msgA_SubcarrierSpacing_r16; + } else if (rach_ConfigCommon->msg1_SubcarrierSpacing) { + // Choose Subcarrier Spacing of configuration file of 4-Step + mu = *rach_ConfigCommon->msg1_SubcarrierSpacing; + } else + AssertFatal(false, "PRACH subcarrier spacing mandatory present for L139, not supported otherwise\n"); + + return mu; +} diff --git a/openair2/LAYER2/NR_MAC_COMMON/nr_mac_common.h b/openair2/LAYER2/NR_MAC_COMMON/nr_mac_common.h index 4ce1571390..a4930aec47 100644 --- a/openair2/LAYER2/NR_MAC_COMMON/nr_mac_common.h +++ b/openair2/LAYER2/NR_MAC_COMMON/nr_mac_common.h @@ -317,6 +317,8 @@ uint32_t compute_PDU_length(uint32_t num_TLV, uint32_t total_length); rnti_t nr_get_ra_rnti(uint8_t s_id, uint8_t t_id, uint8_t f_id, uint8_t ul_carrier_id); +rnti_t nr_get_MsgB_rnti(uint8_t s_id, uint8_t t_id, uint8_t f_id, uint8_t ul_carrier_id); + bool supported_bw_comparison(int bw_mhz, NR_SupportedBandwidth_t *supported_BW, long *support_90mhz); int get_FeedbackDisabled(NR_DownlinkHARQ_FeedbackDisabled_r17_t *downlinkHARQ_FeedbackDisabled_r17, int harq_pid); @@ -325,4 +327,6 @@ int get_nrofHARQ_ProcessesForPDSCH(const NR_UE_ServingCell_Info_t *sc_info); int get_nrofHARQ_ProcessesForPUSCH(const NR_UE_ServingCell_Info_t *sc_info); +int nr_get_prach_mu(const NR_MsgA_ConfigCommon_r16_t *msgacc, const NR_RACH_ConfigCommon_t *rach_ConfigCommon); + #endif diff --git a/openair2/LAYER2/NR_MAC_UE/config_ue.c b/openair2/LAYER2/NR_MAC_UE/config_ue.c index de8fa49d48..19a799dab6 100644 --- a/openair2/LAYER2/NR_MAC_UE/config_ue.c +++ b/openair2/LAYER2/NR_MAC_UE/config_ue.c @@ -1540,6 +1540,12 @@ static void configure_common_BWP_ul(NR_UE_MAC_INST_t *mac, int bwp_id, NR_BWP_Up NR_RACH_ConfigCommon_t, asn_DEF_NR_RACH_ConfigCommon); } + if (ul_common->ext1 && ul_common->ext1->msgA_ConfigCommon_r16) { + HANDLE_SETUPRELEASE_DIRECT(bwp->msgA_ConfigCommon_r16, + ul_common->ext1->msgA_ConfigCommon_r16, + NR_MsgA_ConfigCommon_r16_t, + asn_DEF_NR_MsgA_ConfigCommon_r16); + } if (ul_common->pucch_ConfigCommon) HANDLE_SETUPRELEASE_DIRECT(bwp->pucch_ConfigCommon, ul_common->pucch_ConfigCommon, @@ -1901,6 +1907,7 @@ static uint32_t nr_get_sf_periodicBSRTimer(long periodicBSR) break; case NR_BSR_Config__periodicBSR_Timer_infinity: timer = UINT_MAX; + break; default: AssertFatal(false, "Invalid periodicBSR_Timer %ld\n", periodicBSR); } diff --git a/openair2/LAYER2/NR_MAC_UE/mac_defs.h b/openair2/LAYER2/NR_MAC_UE/mac_defs.h index c913321f80..ffa09ccb25 100644 --- a/openair2/LAYER2/NR_MAC_UE/mac_defs.h +++ b/openair2/LAYER2/NR_MAC_UE/mac_defs.h @@ -191,11 +191,6 @@ typedef enum { RE_ESTABLISHMENT } NR_UE_MAC_reset_cause_t; -typedef enum { - RA_2STEP = 0, - RA_4STEP -} nr_ra_type_e; - typedef struct { // after multiplexing buffer remain for each lcid int32_t LCID_buffer_remain; @@ -268,16 +263,17 @@ typedef struct { } NR_UE_SCHEDULING_INFO; typedef enum { - nrRA_UE_IDLE = 0, - nrRA_GENERATE_PREAMBLE = 1, - nrRA_WAIT_RAR = 2, - nrRA_WAIT_CONTENTION_RESOLUTION = 3, - nrRA_SUCCEEDED = 4, - nrRA_FAILED = 5 + nrRA_UE_IDLE, + nrRA_GENERATE_PREAMBLE, + nrRA_WAIT_RAR, + nrRA_WAIT_MSGB, + nrRA_WAIT_CONTENTION_RESOLUTION, + nrRA_SUCCEEDED, + nrRA_FAILED, } nrRA_UE_state_t; static const char *const nrra_ue_text[] = - {"UE_IDLE", "GENERATE_PREAMBLE", "WAIT_RAR", "WAIT_CONTENTION_RESOLUTION", "RA_SUCCEEDED", "RA_FAILED"}; + {"UE_IDLE", "GENERATE_PREAMBLE", "WAIT_RAR", "WAIT_MSGB", "WAIT_CONTENTION_RESOLUTION", "RA_SUCCEEDED", "RA_FAILED"}; typedef struct { /// PRACH format retrieved from prach_ConfigIndex @@ -299,7 +295,7 @@ typedef struct { /// uint8_t RA_SCALING_FACTOR_BI; /// Indicating whether it is 2-step or 4-step RA - nr_ra_type_e RA_TYPE; + nr_ra_type_t RA_TYPE; /// UE configured maximum output power int RA_PCMAX; } NR_PRACH_RESOURCES_t; @@ -312,10 +308,21 @@ typedef struct { nrRA_UE_state_t ra_state; /// RA contention type uint8_t cfra; + /// RA type + nr_ra_type_t ra_type; /// RA rx frame offset: compensate RA rx offset introduced by OAI gNB. uint8_t RA_offset; + /// MsgB SuccessRAR MAC subheader + int8_t MsgB_R; + int8_t MsgB_CH_ACESS_CPEXT; + uint8_t MsgB_TPC; + int8_t MsgB_HARQ_FTI; + uint16_t timing_advance_command; + int8_t PUCCH_RI; /// RA-rnti uint16_t ra_rnti; + /// MsgB RNTI + uint16_t MsgB_rnti; /// Temporary CRNTI uint16_t t_crnti; /// number of attempt for rach diff --git a/openair2/LAYER2/NR_MAC_UE/mac_proto.h b/openair2/LAYER2/NR_MAC_UE/mac_proto.h index 1f53812dec..6feca8756e 100644 --- a/openair2/LAYER2/NR_MAC_UE/mac_proto.h +++ b/openair2/LAYER2/NR_MAC_UE/mac_proto.h @@ -304,6 +304,10 @@ void nr_ra_failed(NR_UE_MAC_INST_t *mac, uint8_t CC_id, NR_PRACH_RESOURCES_t *pr void nr_ra_succeeded(NR_UE_MAC_INST_t *mac, const uint8_t gNB_index, const frame_t frame, const int slot); +int16_t nr_get_RA_window_2Step(const NR_MsgA_ConfigCommon_r16_t *msgA_ConfigCommon_r16); + +int16_t nr_get_RA_window_4Step(const NR_RACH_ConfigCommon_t *rach_ConfigCommon); + void nr_get_RA_window(NR_UE_MAC_INST_t *mac); /* \brief Function called by PHY to retrieve information to be transmitted using the RA procedure. @@ -331,7 +335,7 @@ void nr_get_prach_resources(NR_UE_MAC_INST_t *mac, NR_PRACH_RESOURCES_t *prach_resources, NR_RACH_ConfigDedicated_t * rach_ConfigDedicated); -void prepare_msg4_feedback(NR_UE_MAC_INST_t *mac, int pid, int ack_nack); +void prepare_msg4_msgb_feedback(NR_UE_MAC_INST_t *mac, int pid, int ack_nack); void configure_initial_pucch(PUCCH_sched_t *pucch, int res_ind); void release_PUCCH_SRS(NR_UE_MAC_INST_t *mac); void nr_ue_reset_sync_state(NR_UE_MAC_INST_t *mac); @@ -356,7 +360,7 @@ void schedule_RA_after_SR_failure(NR_UE_MAC_INST_t *mac); void nr_Msg1_transmitted(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 trigger_MAC_UE_RA(NR_UE_MAC_INST_t *mac); -void nr_get_msg3_payload(NR_UE_MAC_INST_t *mac, uint8_t *buf, int TBS_max); +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); int8_t nr_ue_process_dci_freq_dom_resource_assignment(nfapi_nr_ue_pusch_pdu_t *pusch_config_pdu, fapi_nr_dl_config_dlsch_pdu_rel15_t *dlsch_config_pdu, @@ -410,7 +414,7 @@ int nr_config_pusch_pdu(NR_UE_MAC_INST_t *mac, dci_pdu_rel15_t *dci, csi_payload_t *csi_report, RAR_grant_t *rar_grant, - uint16_t rnti, + rnti_t rnti, int ss_type, const nr_dci_format_t dci_format); diff --git a/openair2/LAYER2/NR_MAC_UE/nr_ra_procedures.c b/openair2/LAYER2/NR_MAC_UE/nr_ra_procedures.c index 6272c4c33f..da183b3b14 100644 --- a/openair2/LAYER2/NR_MAC_UE/nr_ra_procedures.c +++ b/openair2/LAYER2/NR_MAC_UE/nr_ra_procedures.c @@ -104,15 +104,19 @@ void init_RA(NR_UE_MAC_INST_t *mac, prach_resources->POWER_OFFSET_2STEP_RA = 0; prach_resources->RA_SCALING_FACTOR_BI = 1; + + // Contention Free if (rach_ConfigDedicated) { if (rach_ConfigDedicated->cfra){ - LOG_I(NR_MAC, "Initialization of 2-step contention-free random access procedure\n"); - prach_resources->RA_TYPE = RA_2STEP; + LOG_I(MAC, "Initialization of 4-Step CFRA procedure\n"); + prach_resources->RA_TYPE = RA_4_STEP; + ra->ra_type = RA_4_STEP; ra->cfra = 1; } else if (rach_ConfigDedicated->ext1){ - if (rach_ConfigDedicated->ext1->cfra_TwoStep_r16){ - LOG_I(NR_MAC, "Setting RA type to 2-step...\n"); - prach_resources->RA_TYPE = RA_2STEP; + if (rach_ConfigDedicated->ext1->cfra_TwoStep_r16) { + LOG_I(MAC, "Initialization of 2-Step CFRA procedure\n"); + prach_resources->RA_TYPE = RA_2_STEP; + ra->ra_type = RA_2_STEP; ra->cfra = 1; } else { LOG_E(NR_MAC, "Config not handled\n"); @@ -120,10 +124,20 @@ void init_RA(NR_UE_MAC_INST_t *mac, } else { LOG_E(NR_MAC, "Config not handled\n"); } - } else { - LOG_I(NR_MAC, "Initialization of 4-step contention-based random access procedure\n"); - prach_resources->RA_TYPE = RA_4STEP; + // Contention Based + } else if (mac->current_UL_BWP->msgA_ConfigCommon_r16) { + LOG_I(MAC, "Initialization of 2-Step CBRA procedure\n"); + prach_resources->RA_TYPE = RA_2_STEP; + ra->ra_type = RA_2_STEP; ra->cfra = 0; + } else if (nr_rach_ConfigCommon) { + LOG_I(MAC, "Initialization of 4-Step CBRA procedure\n"); + prach_resources->RA_TYPE = RA_4_STEP; + ra->ra_type = RA_4_STEP; + ra->cfra = 0; + } else { + LOG_E(MAC, "Config not handled\n"); + AssertFatal(false, "In %s: config not handled\n", __FUNCTION__); } switch (rach_ConfigGeneric->powerRampingStep){ // in dB @@ -177,10 +191,28 @@ void init_RA(NR_UE_MAC_INST_t *mac, break; } - if (nr_rach_ConfigCommon->ext1) { - if (nr_rach_ConfigCommon->ext1->ra_PrioritizationForAccessIdentity_r16){ + if (ra->ra_type == RA_2_STEP) { + if (nr_rach_ConfigCommon->ext1 && nr_rach_ConfigCommon->ext1->ra_PrioritizationForAccessIdentity_r16) { LOG_D(MAC, "Missing implementation for Access Identity initialization procedures\n"); } + // Perform initialization of variables specific to Random Access type as specified in clause 5.1.1a of TS 38.321 + NR_RACH_ConfigGenericTwoStepRA_r16_t nr_ra_ConfigGenericTwoStepRA_r16 = + mac->current_UL_BWP->msgA_ConfigCommon_r16->rach_ConfigCommonTwoStepRA_r16.rach_ConfigGenericTwoStepRA_r16; + // Takes the value of 2-Step RA variable + if (nr_ra_ConfigGenericTwoStepRA_r16.msgA_PreamblePowerRampingStep_r16) { + prach_resources->RA_PREAMBLE_POWER_RAMPING_STEP = *nr_ra_ConfigGenericTwoStepRA_r16.msgA_PreamblePowerRampingStep_r16; + } else { + // If 2-Step variable does not exist, it takes the value of 4-Step RA variable + prach_resources->RA_PREAMBLE_POWER_RAMPING_STEP = nr_rach_ConfigCommon->rach_ConfigGeneric.powerRampingStep; + } + prach_resources->RA_SCALING_FACTOR_BI = 1; + // Takes the value of 2-Step RA variable + if (nr_ra_ConfigGenericTwoStepRA_r16.preambleTransMax_r16) { + ra->preambleTransMax = (int)*nr_ra_ConfigGenericTwoStepRA_r16.preambleTransMax_r16; + } else { + // If 2-Step variable does not exist, it takes the value of 4-Step RA variable + ra->preambleTransMax = (int)nr_rach_ConfigCommon->rach_ConfigGeneric.preambleTransMax; + } } } @@ -623,7 +655,7 @@ static uint8_t *fill_msg3_crnti_pdu(RA_config_t *ra, uint8_t *pdu, uint16_t crnt static uint8_t *fill_msg3_pdu_from_rlc(NR_UE_MAC_INST_t *mac, uint8_t *pdu, int TBS_max) { RA_config_t *ra = &mac->ra; - // regular MSG3 with PDU coming from higher layers + // regular Msg3/MsgA_PUSCH with PDU coming from higher layers *(NR_MAC_SUBHEADER_FIXED *)pdu = (NR_MAC_SUBHEADER_FIXED){.LCID = UL_SCH_LCID_CCCH}; pdu += sizeof(NR_MAC_SUBHEADER_FIXED); tbs_size_t len = mac_rlc_data_req(mac->ue_id, @@ -637,7 +669,7 @@ static uint8_t *fill_msg3_pdu_from_rlc(NR_UE_MAC_INST_t *mac, uint8_t *pdu, int (char *)pdu, 0, 0); - AssertFatal(len > 0, "no data for Msg.3\n"); + AssertFatal(len > 0, "no data for Msg3/MsgA_PUSCH\n"); // UE Contention Resolution Identity // Store the first 48 bits belonging to the uplink CCCH SDU within Msg3 to determine whether or not the // Random Access Procedure has been successful after reception of Msg4 @@ -647,7 +679,7 @@ static uint8_t *fill_msg3_pdu_from_rlc(NR_UE_MAC_INST_t *mac, uint8_t *pdu, int return pdu; } -void nr_get_msg3_payload(NR_UE_MAC_INST_t *mac, uint8_t *buf, int TBS_max) +void nr_get_Msg3_MsgA_PUSCH_payload(NR_UE_MAC_INST_t *mac, uint8_t *buf, int TBS_max) { RA_config_t *ra = &mac->ra; @@ -660,10 +692,10 @@ void nr_get_msg3_payload(NR_UE_MAC_INST_t *mac, uint8_t *buf, int TBS_max) uint8_t *pdu = buf; if (ra->msg3_C_RNTI) pdu = fill_msg3_crnti_pdu(ra, pdu, mac->crnti); - else + else pdu = fill_msg3_pdu_from_rlc(mac, pdu, TBS_max); - AssertFatal(TBS_max >= pdu - buf, "Allocated resources are not enough for Msg3!\n"); + AssertFatal(TBS_max >= pdu - buf, "Allocated resources are not enough for Msg3/MsgA_PUSCH!\n"); // Padding: fill remainder with 0 LOG_D(NR_MAC, "Remaining %ld bytes, filling with padding\n", pdu - buf); while (pdu < buf + TBS_max - sizeof(NR_MAC_SUBHEADER_FIXED)) { @@ -695,13 +727,24 @@ void nr_ue_get_rach(NR_UE_MAC_INST_t *mac, int CC_id, frame_t frame, uint8_t gNB // Delay init RA procedure to allow the convergence of the IIR filter on PRACH noise measurements at gNB side if (ra->ra_state == nrRA_UE_IDLE) { - if ((mac->first_sync_frame > -1 || get_softmodem_params()->do_ra || get_softmodem_params()->nsa) && - ((MAX_FRAME_NUMBER + frame - mac->first_sync_frame) % MAX_FRAME_NUMBER) > 150) { - ra->ra_state = nrRA_GENERATE_PREAMBLE; - } else { - LOG_D(NR_MAC,"PRACH Condition not met: ra state %d, frame %d, sync_frame %d\n", ra->ra_state, frame, mac->first_sync_frame); - return; - } + LOG_D(NR_MAC, + "ra->ra_state %d frame %d mac->first_sync_frame %d xxx %d", + ra->ra_state, + frame, + mac->first_sync_frame, + ((MAX_FRAME_NUMBER + frame - mac->first_sync_frame) % MAX_FRAME_NUMBER) > 10); + if ((mac->first_sync_frame > -1 || get_softmodem_params()->do_ra || get_softmodem_params()->nsa) + && ((MAX_FRAME_NUMBER + frame - mac->first_sync_frame) % MAX_FRAME_NUMBER) > 150) { + ra->ra_state = nrRA_GENERATE_PREAMBLE; + LOG_D(NR_MAC, "PRACH Condition met: ra state %d, frame %d, sync_frame %d\n", ra->ra_state, frame, mac->first_sync_frame); + } else { + LOG_D(NR_MAC, + "PRACH Condition not met: ra state %d, frame %d, sync_frame %d\n", + ra->ra_state, + frame, + mac->first_sync_frame); + return; + } } LOG_D(NR_MAC, "[UE %d][%d.%d]: ra_state %d, RA_active %d\n", mac->ue_id, frame, nr_slot_tx, ra->ra_state, ra->RA_active); @@ -762,8 +805,7 @@ void nr_ue_get_rach(NR_UE_MAC_INST_t *mac, int CC_id, frame_t frame, uint8_t gNB nr_ra_succeeded(mac, gNB_id, frame, nr_slot_tx); } - } else if (ra->RA_window_cnt == 0 && !ra->RA_RAPID_found) { - + } else if (ra->RA_window_cnt == 0 && !ra->RA_RAPID_found && ra->ra_state != nrRA_WAIT_MSGB) { LOG_W(MAC, "[UE %d][%d:%d] RAR reception failed \n", mac->ue_id, frame, nr_slot_tx); nr_ra_failed(mac, CC_id, prach_resources, frame, nr_slot_tx); @@ -795,49 +837,102 @@ void nr_ue_get_rach(NR_UE_MAC_INST_t *mac, int CC_id, frame_t frame, uint8_t gNB } } +int16_t nr_get_RA_window_2Step(const NR_MsgA_ConfigCommon_r16_t *msgA_ConfigCommon_r16) +{ + int16_t ra_ResponseWindow = *msgA_ConfigCommon_r16->rach_ConfigCommonTwoStepRA_r16 + .rach_ConfigGenericTwoStepRA_r16.msgB_ResponseWindow_r16; + + switch (ra_ResponseWindow) { + case NR_RACH_ConfigGenericTwoStepRA_r16__msgB_ResponseWindow_r16_sl1: + return 1; + break; + case NR_RACH_ConfigGenericTwoStepRA_r16__msgB_ResponseWindow_r16_sl2: + return 2; + break; + case NR_RACH_ConfigGenericTwoStepRA_r16__msgB_ResponseWindow_r16_sl4: + return 4; + break; + case NR_RACH_ConfigGenericTwoStepRA_r16__msgB_ResponseWindow_r16_sl8: + return 8; + break; + case NR_RACH_ConfigGenericTwoStepRA_r16__msgB_ResponseWindow_r16_sl10: + return 10; + break; + case NR_RACH_ConfigGenericTwoStepRA_r16__msgB_ResponseWindow_r16_sl20: + return 20; + break; + case NR_RACH_ConfigGenericTwoStepRA_r16__msgB_ResponseWindow_r16_sl40: + return 40; + break; + case NR_RACH_ConfigGenericTwoStepRA_r16__msgB_ResponseWindow_r16_sl80: + return 80; + break; + case NR_RACH_ConfigGenericTwoStepRA_r16__msgB_ResponseWindow_r16_sl160: + return 160; + break; + case NR_RACH_ConfigGenericTwoStepRA_r16__msgB_ResponseWindow_r16_sl320: + return 360; + break; + default: + AssertFatal(false, "illegal msgB_responseWindow value %d\n", ra_ResponseWindow); + break; + } + return 0; +} + +int16_t nr_get_RA_window_4Step(const NR_RACH_ConfigCommon_t *rach_ConfigCommon) +{ + int16_t ra_ResponseWindow = rach_ConfigCommon->rach_ConfigGeneric.ra_ResponseWindow; + + switch (ra_ResponseWindow) { + case NR_RACH_ConfigGeneric__ra_ResponseWindow_sl1: + return 1; + break; + case NR_RACH_ConfigGeneric__ra_ResponseWindow_sl2: + return 2; + break; + case NR_RACH_ConfigGeneric__ra_ResponseWindow_sl4: + return 4; + break; + case NR_RACH_ConfigGeneric__ra_ResponseWindow_sl8: + return 8; + break; + case NR_RACH_ConfigGeneric__ra_ResponseWindow_sl10: + return 10; + break; + case NR_RACH_ConfigGeneric__ra_ResponseWindow_sl20: + return 20; + break; + case NR_RACH_ConfigGeneric__ra_ResponseWindow_sl40: + return 40; + break; + case NR_RACH_ConfigGeneric__ra_ResponseWindow_sl80: + return 80; + break; + default: + AssertFatal(false, "illegal ra_ResponseWindow value %d\n", ra_ResponseWindow); + break; + } + return 0; +} + void nr_get_RA_window(NR_UE_MAC_INST_t *mac) { RA_config_t *ra = &mac->ra; + NR_RACH_ConfigCommon_t *setup = mac->current_UL_BWP->rach_ConfigCommon; AssertFatal(&setup->rach_ConfigGeneric != NULL, "In %s: FATAL! rach_ConfigGeneric is NULL...\n", __FUNCTION__); - NR_RACH_ConfigGeneric_t *rach_ConfigGeneric = &setup->rach_ConfigGeneric; const double ta_Common_ms = get_ta_Common_ms(mac->sc_info.ntn_Config_r17); const int mu = mac->current_DL_BWP->scs; const int slots_per_ms = nr_slots_per_frame[mu] / 10; - + const int ra_Offset_slots = ra->RA_offset * nr_slots_per_frame[mu]; const int ta_Common_slots = (int)ceil(ta_Common_ms * slots_per_ms); ra->RA_window_cnt = ra_Offset_slots + ta_Common_slots; // taking into account the 2 frames gap introduced by OAI gNB - int ra_ResponseWindow = rach_ConfigGeneric->ra_ResponseWindow; - - switch (ra_ResponseWindow) { - case NR_RACH_ConfigGeneric__ra_ResponseWindow_sl1: - ra->RA_window_cnt += 1; - break; - case NR_RACH_ConfigGeneric__ra_ResponseWindow_sl2: - ra->RA_window_cnt += 2; - break; - case NR_RACH_ConfigGeneric__ra_ResponseWindow_sl4: - ra->RA_window_cnt += 4; - break; - case NR_RACH_ConfigGeneric__ra_ResponseWindow_sl8: - ra->RA_window_cnt += 8; - break; - case NR_RACH_ConfigGeneric__ra_ResponseWindow_sl10: - ra->RA_window_cnt += 10; - break; - case NR_RACH_ConfigGeneric__ra_ResponseWindow_sl20: - ra->RA_window_cnt += 20; - break; - case NR_RACH_ConfigGeneric__ra_ResponseWindow_sl40: - ra->RA_window_cnt += 40; - break; - case NR_RACH_ConfigGeneric__ra_ResponseWindow_sl80: - ra->RA_window_cnt += 80; - break; - } + ra->RA_window_cnt += ra->ra_type == RA_2_STEP ? nr_get_RA_window_2Step(mac->current_UL_BWP->msgA_ConfigCommon_r16) + : nr_get_RA_window_4Step(mac->current_UL_BWP->rach_ConfigCommon); } //////////////////////////////////////////////////////////////////////////// @@ -855,7 +950,7 @@ void nr_ue_contention_resolution(NR_UE_MAC_INST_t *mac, int cc_id, frame_t frame ra->t_crnti = 0; nr_timer_stop(&ra->contention_resolution_timer); // Signal PHY to quit RA procedure - LOG_E(MAC, "[UE %d] CB-RA: Contention resolution timer has expired, RA procedure has failed...\n", mac->ue_id); + LOG_E(MAC, "[UE %d] 4-Step CBRA: Contention resolution timer has expired, RA procedure has failed...\n", mac->ue_id); nr_ra_failed(mac, cc_id, prach_resources, frame, slot); } } @@ -869,14 +964,27 @@ void nr_ra_succeeded(NR_UE_MAC_INST_t *mac, const uint8_t gNB_index, const frame RA_config_t *ra = &mac->ra; if (ra->cfra) { - LOG_I(MAC, "[UE %d][%d.%d][RAPROC] RA procedure succeeded. CF-RA: RAR successfully received.\n", mac->ue_id, frame, slot); + LOG_I(MAC, "[UE %d][%d.%d][RAPROC] RA procedure succeeded. CFRA: RAR successfully received.\n", mac->ue_id, frame, slot); ra->RA_window_cnt = -1; + } else if (ra->ra_type == RA_2_STEP) { + LOG_A(MAC, + "[UE %d][%d.%d][RAPROC] 2-Step RA procedure succeeded. CBRA: Contention Resolution is successful.\n", + mac->ue_id, + frame, + slot); + mac->crnti = ra->t_crnti; + ra->t_crnti = 0; + LOG_D(MAC, "[UE %d][%d.%d] CBRA: cleared response window timer...\n", mac->ue_id, frame, slot); } else { - LOG_A(MAC, "[UE %d][%d.%d][RAPROC] RA procedure succeeded. CB-RA: Contention Resolution is successful.\n", mac->ue_id, frame, slot); + LOG_A(MAC, + "[UE %d][%d.%d][RAPROC] 4-Step RA procedure succeeded. CBRA: Contention Resolution is successful.\n", + mac->ue_id, + frame, + slot); nr_timer_stop(&ra->contention_resolution_timer); mac->crnti = ra->t_crnti; ra->t_crnti = 0; - LOG_D(MAC, "[UE %d][%d.%d] CB-RA: cleared contention resolution timer...\n", mac->ue_id, frame, slot); + LOG_D(MAC, "[UE %d][%d.%d] CBRA: cleared contention resolution timer...\n", mac->ue_id, frame, slot); } LOG_D(MAC, "[UE %d] clearing RA_active flag...\n", mac->ue_id); @@ -931,7 +1039,6 @@ void nr_ra_failed(NR_UE_MAC_INST_t *mac, uint8_t CC_id, NR_PRACH_RESOURCES_t *pr prach_resources->ra_PREAMBLE_RECEIVED_TARGET_POWER = nr_get_Po_NOMINAL_PUSCH(mac, prach_resources, CC_id); } else { - // Resetting RA window nr_get_RA_window(mac); } } @@ -944,7 +1051,7 @@ void trigger_MAC_UE_RA(NR_UE_MAC_INST_t *mac) mac->ra.msg3_C_RNTI = true; } -void prepare_msg4_feedback(NR_UE_MAC_INST_t *mac, int pid, int ack_nack) +void prepare_msg4_msgb_feedback(NR_UE_MAC_INST_t *mac, int pid, int ack_nack) { NR_UE_HARQ_STATUS_t *current_harq = &mac->dl_harq_info[pid]; int sched_slot = current_harq->ul_slot; 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 550ae2b8da..1c01f84d4d 100644 --- a/openair2/LAYER2/NR_MAC_UE/nr_ue_dci_configuration.c +++ b/openair2/LAYER2/NR_MAC_UE/nr_ue_dci_configuration.c @@ -266,6 +266,14 @@ void config_dci_pdu(NR_UE_MAC_INST_t *mac, rel15->rnti = mac->ra.ra_rnti; rel15->SubcarrierSpacing = current_DL_BWP->scs; break; + case TYPE_MSGB_RNTI_: + // we use the initial DL BWP + sps = current_DL_BWP->cyclicprefix == NULL ? 14 : 12; + monitoringSymbolsWithinSlot = + (ss->monitoringSymbolsWithinSlot->buf[0] << (sps - 8)) | (ss->monitoringSymbolsWithinSlot->buf[1] >> (16 - sps)); + rel15->rnti = mac->ra.MsgB_rnti; + rel15->SubcarrierSpacing = current_DL_BWP->scs; + break; case TYPE_P_RNTI_: break; case TYPE_CS_RNTI_: @@ -571,7 +579,12 @@ void ue_dci_configuration(NR_UE_MAC_INST_t *mac, fapi_nr_dl_config_request_t *dl if (mac->state == UE_PERFORMING_RA && mac->ra.ra_state >= nrRA_WAIT_RAR) { // if RA is ongoing use RA search space if (is_ss_monitor_occasion(frame, slot, slots_per_frame, pdcch_config->ra_SS)) { - int rnti_type = mac->ra.ra_state == nrRA_WAIT_RAR ? TYPE_RA_RNTI_ : TYPE_TC_RNTI_; + nr_rnti_type_t rnti_type = 0; + if (mac->ra.ra_type == RA_4_STEP) { + rnti_type = mac->ra.ra_state == nrRA_WAIT_RAR ? TYPE_RA_RNTI_ : TYPE_TC_RNTI_; + } else { + rnti_type = TYPE_MSGB_RNTI_; + } config_dci_pdu(mac, dl_config, rnti_type, slot, pdcch_config->ra_SS); } } else if (mac->state == UE_CONNECTED) { diff --git a/openair2/LAYER2/NR_MAC_UE/nr_ue_procedures.c b/openair2/LAYER2/NR_MAC_UE/nr_ue_procedures.c index 7844b31132..6ba441bad1 100644 --- a/openair2/LAYER2/NR_MAC_UE/nr_ue_procedures.c +++ b/openair2/LAYER2/NR_MAC_UE/nr_ue_procedures.c @@ -161,6 +161,8 @@ int get_rnti_type(const NR_UE_MAC_INST_t *mac, const uint16_t rnti) if (rnti == ra->ra_rnti) { rnti_type = TYPE_RA_RNTI_; + } else if (rnti == ra->MsgB_rnti && (ra->ra_state == nrRA_WAIT_MSGB || ra->ra_state == nrRA_WAIT_CONTENTION_RESOLUTION)) { + rnti_type = TYPE_MSGB_RNTI_; } else if (rnti == ra->t_crnti && (ra->ra_state == nrRA_WAIT_RAR || ra->ra_state == nrRA_WAIT_CONTENTION_RESOLUTION)) { rnti_type = TYPE_TC_RNTI_; } else if (rnti == mac->crnti) { @@ -3347,6 +3349,7 @@ static nr_dci_format_t nr_extract_dci_00_10(NR_UE_MAC_INST_t *mac, dci_pdu_rel15->format_indicator = format_indicator; break; case TYPE_TC_RNTI_ : + case TYPE_MSGB_RNTI_: // Identifier for DCI formats EXTRACT_DCI_ITEM(format_indicator, 1); if (format_indicator == 1) { @@ -3434,6 +3437,101 @@ static void set_time_alignment(NR_UE_MAC_INST_t *mac, int ta, ta_type_t type, in nr_timer_start(&mac->time_alignment_timer); } +static bool check_ra_contention_resolution(const uint8_t *pdu, const uint8_t *cont_res) +{ + if (IS_SOFTMODEM_IQPLAYER) // Control is bypassed when replaying IQs (BMC) + return true; + for (int i = 0; i < 6; i++) { + if (pdu[i] != cont_res[i]) { + return false; + } + } + 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) +{ + // TS 38.321 - Figure 6.1.5a-1: BI MAC subheader + // TS 38.321 - Figure 6.1.5a-3: SuccessRAR MAC subheader + int n = 0; + uint8_t E = 1; + uint8_t cont_res_id[6]; + RA_config_t *ra = &mac->ra; + + while (n < pdu_len && E) { + E = (pduP[n] >> 7) & 0x1; + uint8_t SUCESS_RAR_header_T1 = (pduP[n] >> 6) & 0x1; + if (SUCESS_RAR_header_T1 == 0) { // T2 exist + int SUCESS_RAR_header_T2 = (pduP[n] >> 5) & 0x1; + if (SUCESS_RAR_header_T2 == 0) { // BI + ra->RA_backoff_indicator = pduP[n] & 0x0F; + n++; + } else { // S + n++; + // TS 38.321 - Figure 6.2.3a-2: successRAR + for (int i = 0; i < 6; ++i) + cont_res_id[i] = pduP[n + i]; + n += 6; + // Oct 7 + ra->MsgB_R = 0; + ra->MsgB_CH_ACESS_CPEXT = (pduP[n] >> 5) & 0x3; + ra->MsgB_TPC = (pduP[n] >> 3) & 3; + ra->MsgB_HARQ_FTI = (int8_t)pduP[n] & 0x7; + // Oct 8 + n++; + ra->PUCCH_RI = ((int8_t)pduP[n] >> 4) & 0x0F; + // Oct 8 and Oct 9 + ra->timing_advance_command = ((uint16_t)(pduP[n] & 0xf) << 8) | pduP[n + 1]; + n += 2; + // Oct 10 and Oct 11 + ra->t_crnti = ((uint16_t)pduP[n] << 8) | pduP[n + 1]; + n += 2; + + LOG_D(NR_MAC, + "successRAR: Contention Resolution ID 0x%02x%02x%02x%02x%02x%02x R 0x%01x CH_ACESS_CPEXT 0x%02x TPC 0x%02x " + "HARQ_FTI 0x%03x PUCCH_RI 0x%04x TA 0x%012x CRNTI 0x%04x\n", + cont_res_id[0], + cont_res_id[1], + cont_res_id[2], + cont_res_id[3], + cont_res_id[4], + cont_res_id[5], + ra->MsgB_R, + ra->MsgB_CH_ACESS_CPEXT, + ra->MsgB_TPC, + ra->MsgB_HARQ_FTI, + ra->PUCCH_RI, + ra->timing_advance_command, + ra->t_crnti); + + bool ra_success = check_ra_contention_resolution(cont_res_id, ra->cont_res_id); + + if (ra->RA_active && ra_success) { + nr_ra_succeeded(mac, gNB_index, frameP, slot); + } else if (!ra_success) { + // nr_ra_failed(mac, CC_id, &ra->prach_resources, frameP, slot); + ra->ra_state = nrRA_UE_IDLE; + ra->RA_active = 0; + } + } + } else { // RAPID + int RAPID = pduP[n] & 0x3F; + n++; + LOG_D(MAC, "RAPID %d\n", RAPID); + AssertFatal(false, "FallbackRAR not implemented yet!\n"); + } + } + const int ta = ((NR_MAC_CE_TA *)pduP)[1].TA_COMMAND; + + set_time_alignment(mac, ta, adjustment_ta, frameP, slot); + return n; +} + /////////////////////////////////// // brief: nr_ue_process_mac_pdu // function: parsing DL PDU header @@ -3457,9 +3555,12 @@ static void set_time_alignment(NR_UE_MAC_INST_t *mac, int ta, ta_type_t type, in // // |0|1|2|3|4|5|6|7| bit-wise // |R|R| LCID | -// LCID: The Logical Channel ID field identifies the logical channel instance of the corresponding MAC SDU or the type of the corresponding MAC CE or padding as described -// in Tables 6.2.1-1 and 6.2.1-2 for the DL-SCH and UL-SCH respectively. There is one LCID field per MAC subheader. The LCID field size is 6 bits; -// L: The Length field indicates the length of the corresponding MAC SDU or variable-sized MAC CE in bytes. There is one L field per MAC subheader except for subheaders +// LCID: The Logical Channel ID field identifies the logical channel instance of the corresponding MAC SDU or the type of the +// corresponding MAC CE or padding as described +// in Tables 6.2.1-1 and 6.2.1-2 for the DL-SCH and UL-SCH respectively. There is one LCID field per MAC subheader. The LCID +// field size is 6 bits; +// L: The Length field indicates the length of the corresponding MAC SDU or variable-sized MAC CE in bytes. There is one L field +// per MAC subheader except for subheaders // corresponding to fixed-sized MAC CEs and padding. The size of the L field is indicated by the F field; // F: lenght of L is 0:8 or 1:16 bits wide // R: Reserved bit, set to zero. @@ -3475,17 +3576,24 @@ void nr_ue_process_mac_pdu(NR_UE_MAC_INST_t *mac, nr_downlink_indication_t *dl_i uint8_t done = 0; RA_config_t *ra = &mac->ra; - if (!pduP){ + if (!pduP) { return; } - LOG_D(MAC, "[%d.%d]: processing PDU %d (with length %d) of %d total number of PDUs...\n", + LOG_D(MAC, + "[%d.%d]: processing PDU %d (with length %d) of %d total number of PDUs...\n", frameP, slot, pdu_id, pdu_len, 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); + pduP += n; + pdu_len -= n; + } + while (!done && pdu_len > 0){ uint16_t mac_len = 0x0000; uint16_t mac_subheader_len = 0x0001; // default to fixed-length subheader = 1-oct @@ -3618,15 +3726,7 @@ void nr_ue_process_mac_pdu(NR_UE_MAC_INST_t *mac, nr_downlink_indication_t *dl_i pduP[5], pduP[6]); - bool ra_success = true; - if (!IS_SOFTMODEM_IQPLAYER) { // Control is bypassed when replaying IQs (BMC) - for(int i = 0; i < mac_len; i++) { - if(ra->cont_res_id[i] != pduP[i + 1]) { - ra_success = false; - break; - } - } - } + 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); diff --git a/openair2/LAYER2/NR_MAC_UE/nr_ue_scheduler.c b/openair2/LAYER2/NR_MAC_UE/nr_ue_scheduler.c index a076829a8a..9003cc42d2 100644 --- a/openair2/LAYER2/NR_MAC_UE/nr_ue_scheduler.c +++ b/openair2/LAYER2/NR_MAC_UE/nr_ue_scheduler.c @@ -574,7 +574,7 @@ int nr_config_pusch_pdu(NR_UE_MAC_INST_t *mac, dci_pdu_rel15_t *dci, csi_payload_t *csi_report, RAR_grant_t *rar_grant, - uint16_t rnti, + rnti_t rnti, int ss_type, const nr_dci_format_t dci_format) { @@ -584,6 +584,7 @@ int nr_config_pusch_pdu(NR_UE_MAC_INST_t *mac, int rnti_type = get_rnti_type(mac, rnti); NR_UE_UL_BWP_t *current_UL_BWP = mac->current_UL_BWP; NR_UE_ServingCell_Info_t *sc_info = &mac->sc_info; + int scs = current_UL_BWP->scs; // Common configuration pusch_config_pdu->dmrs_config_type = pusch_dmrs_type1; @@ -596,8 +597,69 @@ int nr_config_pusch_pdu(NR_UE_MAC_INST_t *mac, int dmrslength = 1; NR_PUSCH_Config_t *pusch_Config = current_UL_BWP->pusch_Config; - if (rar_grant) { + AssertFatal(!((mac->ra.ra_state < nrRA_SUCCEEDED && mac->ra.ra_type == RA_2_STEP) && rar_grant), "logic error: Is not possible to have both msgA_pusch_resource and rar_grant\n"); + if (mac->ra.ra_state < nrRA_SUCCEEDED && mac->ra.ra_type == RA_2_STEP) { + NR_MsgA_PUSCH_Resource_r16_t *msgA_PUSCH_Resource = + current_UL_BWP->msgA_ConfigCommon_r16->msgA_PUSCH_Config_r16->msgA_PUSCH_ResourceGroupA_r16; + int S = 0; + int L = 0; + SLIV2SL(*msgA_PUSCH_Resource->startSymbolAndLengthMsgA_PO_r16, &S, &L); + tda_info->k2 = msgA_PUSCH_Resource->msgA_PUSCH_TimeDomainOffset_r16; + tda_info->startSymbolIndex = S; + tda_info->nrOfSymbols = L; + l_prime_mask = get_l_prime(tda_info->nrOfSymbols, + tda_info->mapping_type, + add_pos, + dmrslength, + tda_info->startSymbolIndex, + mac->dmrs_TypeA_Position); + LOG_I(NR_MAC, + "MSGA PUSCH start_sym:%d NR Symb:%d mappingtype:%d, DMRS_MASK:%x\n", + pusch_config_pdu->start_symbol_index, + pusch_config_pdu->nr_of_symbols, + tda_info->mapping_type, + l_prime_mask); + + LOG_D(NR_MAC, + "sc_info->initial_ul_BWPStart = %d sc_info->initial_ul_BWPSize = %d\n", + sc_info->initial_ul_BWPStart, + sc_info->initial_ul_BWPSize); + pusch_config_pdu->handle = 0; + pusch_config_pdu->rb_size = msgA_PUSCH_Resource->nrofPRBs_PerMsgA_PO_r16; + pusch_config_pdu->mcs_table = 0; + pusch_config_pdu->frequency_hopping = msgA_PUSCH_Resource->msgA_IntraSlotFrequencyHopping_r16 ? *msgA_PUSCH_Resource->msgA_IntraSlotFrequencyHopping_r16 : 0; + pusch_config_pdu->dmrs_ports = 1; // is in SIB1 nrofDMRS_Sequences_r16? + pusch_config_pdu->pusch_data.new_data_indicator = 1; // new data + pusch_config_pdu->num_dmrs_cdm_grps_no_data = 2; + pusch_config_pdu->ul_dmrs_symb_pos = get_l_prime(3, 0, pusch_dmrs_pos2, pusch_len1, 10, mac->dmrs_TypeA_Position); + pusch_config_pdu->transform_precoding = + *mac->current_UL_BWP->msgA_ConfigCommon_r16->msgA_PUSCH_Config_r16->msgA_TransformPrecoder_r16; + pusch_config_pdu->rb_bitmap[0] = 0; + pusch_config_pdu->rb_start = msgA_PUSCH_Resource->frequencyStartMsgA_PUSCH_r16; // rb_start depends on the RO + pusch_config_pdu->bwp_size = sc_info->initial_ul_BWPSize; + pusch_config_pdu->bwp_start = sc_info->initial_ul_BWPStart; + pusch_config_pdu->subcarrier_spacing = scs; + pusch_config_pdu->cyclic_prefix = 0; + pusch_config_pdu->uplink_frequency_shift_7p5khz = 0; + pusch_config_pdu->vrb_to_prb_mapping = 0; + pusch_config_pdu->dmrs_config_type = 0; + pusch_config_pdu->data_scrambling_id = mac->physCellId; + pusch_config_pdu->ul_dmrs_scrambling_id = mac->physCellId; + pusch_config_pdu->scid = 0; + pusch_config_pdu->resource_alloc = 1; + pusch_config_pdu->tx_direct_current_location = 0; + pusch_config_pdu->mcs_index = msgA_PUSCH_Resource->msgA_MCS_r16; + pusch_config_pdu->qam_mod_order = nr_get_Qm_dl(pusch_config_pdu->mcs_index, 0); + pusch_config_pdu->start_symbol_index = S; + pusch_config_pdu->nr_of_symbols = L; + pusch_config_pdu->pusch_data.rv_index = 0; // 8.3 in 38.213 + pusch_config_pdu->pusch_data.harq_process_id = 0; + pusch_config_pdu->pusch_data.num_cb = 0; + pusch_config_pdu->tbslbrm = 0; + pusch_config_pdu->target_code_rate = nr_get_code_rate_ul(pusch_config_pdu->mcs_index, 0); + + } else if (rar_grant) { // Note: for Msg3 or MsgA PUSCH transmission the N_PRB_oh is always set to 0 int ibwp_start = sc_info->initial_ul_BWPStart; int ibwp_size = sc_info->initial_ul_BWPSize; @@ -779,7 +841,7 @@ int nr_config_pusch_pdu(NR_UE_MAC_INST_t *mac, uint32_t n_RS_Id = 0; if (NR_DMRS_ulconfig->transformPrecodingEnabled && - NR_DMRS_ulconfig->transformPrecodingEnabled->nPUSCH_Identity != NULL) + NR_DMRS_ulconfig->transformPrecodingEnabled->nPUSCH_Identity) n_RS_Id = *NR_DMRS_ulconfig->transformPrecodingEnabled->nPUSCH_Identity; else n_RS_Id = mac->physCellId; @@ -1501,8 +1563,8 @@ void nr_ue_ul_scheduler(NR_UE_MAC_INST_t *mac, nr_uplink_indication_t *ul_info) TBS_bytes, ra->ra_state); ulcfg_pdu->pusch_config_pdu.tx_request_body.fapiTxPdu = NULL; - if (ra->ra_state == nrRA_WAIT_RAR && !ra->cfra) { - nr_get_msg3_payload(mac, ulsch_input_buffer, TBS_bytes); + if ((ra->ra_state == nrRA_WAIT_RAR || ra->ra_state == nrRA_WAIT_MSGB) && !ra->cfra) { + nr_get_Msg3_MsgA_PUSCH_payload(mac, ulsch_input_buffer, TBS_bytes); for (int k = 0; k < TBS_bytes; k++) { LOG_D(NR_MAC, "(%i): 0x%x\n", k, ulsch_input_buffer[k]); } @@ -1553,6 +1615,9 @@ void nr_ue_ul_scheduler(NR_UE_MAC_INST_t *mac, nr_uplink_indication_t *ul_info) 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); } + 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); + } } ulcfg_pdu++; } @@ -1739,13 +1804,6 @@ static void build_ro_list(NR_UE_MAC_INST_t *mac) NR_RACH_ConfigGeneric_t *rach_ConfigGeneric = &setup->rach_ConfigGeneric; config_index = rach_ConfigGeneric->prach_ConfigurationIndex; - - int mu; - if (setup->msg1_SubcarrierSpacing) - mu = *setup->msg1_SubcarrierSpacing; - else - mu = mac->current_UL_BWP->scs; - msg1_FDM = rach_ConfigGeneric->msg1_FDM; switch (msg1_FDM){ @@ -1765,6 +1823,7 @@ static void build_ro_list(NR_UE_MAC_INST_t *mac) int unpaired = mac->phy_config.config_req.cell_config.frame_duplex_type; const int64_t *prach_config_info_p = get_prach_config_info(mac->frequency_range, config_index, unpaired); + int mu = nr_get_prach_mu(mac->current_UL_BWP->msgA_ConfigCommon_r16, setup); // Identify the proper PRACH Configuration Index table according to the operating frequency LOG_D(NR_MAC,"mu = %u, PRACH config index = %u, unpaired = %u\n", mu, config_index, unpaired); @@ -2867,7 +2926,54 @@ static void nr_ue_prach_scheduler(NR_UE_MAC_INST_t *mac, frame_t frameP, sub_fra if(mac->if_module != NULL && mac->if_module->scheduled_response != NULL) mac->if_module->scheduled_response(&scheduled_response); - nr_Msg1_transmitted(mac); + if (ra->ra_type == RA_4_STEP) { + nr_Msg1_transmitted(mac); + } else if (ra->ra_type == RA_2_STEP) { + NR_MsgA_PUSCH_Resource_r16_t *msgA_PUSCH_Resource = + mac->current_UL_BWP->msgA_ConfigCommon_r16->msgA_PUSCH_Config_r16->msgA_PUSCH_ResourceGroupA_r16; + int mu = nr_get_prach_mu(mac->current_UL_BWP->msgA_ConfigCommon_r16, setup); + const int n_slots_frame = nr_slots_per_frame[mu]; + slot_t msgA_pusch_slot = (slotP + msgA_PUSCH_Resource->msgA_PUSCH_TimeDomainOffset_r16) % n_slots_frame; + frame_t msgA_pusch_frame = + (frameP + ((slotP + msgA_PUSCH_Resource->msgA_PUSCH_TimeDomainOffset_r16) / n_slots_frame)) % 1024; + + fapi_nr_ul_config_request_pdu_t *pdu = + lockGet_ul_config(mac, msgA_pusch_frame, msgA_pusch_slot, FAPI_NR_UL_CONFIG_TYPE_PUSCH); + if (!pdu) + return; + + // Config Msg3/MsgA-PUSCH PDU + NR_tda_info_t tda_info = {0}; + AssertFatal(msgA_PUSCH_Resource->startSymbolAndLengthMsgA_PO_r16, + "Only SLIV based on startSymbolAndLengthMsgA_PO_r16 implemented\n"); + + int ret = nr_config_pusch_pdu(mac, + &tda_info, + &pdu->pusch_config_pdu, + NULL, + NULL, + NULL, + mac->ra.ra_rnti, + NR_SearchSpace__searchSpaceType_PR_common, + NR_DCI_NONE); + + if (ret != 0) + remove_ul_config_last_item(pdu); + release_ul_config(pdu, false); + + // Compute MsgB RNTI + ra->MsgB_rnti = + nr_get_MsgB_rnti(prach_occasion_info_p->start_symbol, prach_occasion_info_p->slot, prach_occasion_info_p->fdm, 0); + LOG_D(NR_MAC, "ra->ra_state %s\n", nrra_ue_text[ra->ra_state]); + ra->ra_state = nrRA_WAIT_MSGB; + ra->t_crnti = 0; + mac->crnti = 0; + ra->ra_rnti = 0; + } else { + AssertFatal(false, "RA type %d not implemented!\n", ra->ra_type); + } + + // rnti = ra->t_crnti; } // is_nr_prach_slot } // if is_nr_UL_slot } diff --git a/openair2/LAYER2/NR_MAC_gNB/config.c b/openair2/LAYER2/NR_MAC_gNB/config.c index e4cd0d4ef0..39ee7fc238 100644 --- a/openair2/LAYER2/NR_MAC_gNB/config.c +++ b/openair2/LAYER2/NR_MAC_gNB/config.c @@ -272,7 +272,9 @@ nfapi_nr_pm_list_t init_DL_MIMO_codebook(gNB_MAC_INST *gNB, nr_pdsch_AntennaPort return mat; } -static void config_common(gNB_MAC_INST *nrmac, nr_pdsch_AntennaPorts_t pdsch_AntennaPorts, int pusch_AntennaPorts, NR_ServingCellConfigCommon_t *scc) +static void config_common(gNB_MAC_INST *nrmac, + const nr_mac_config_t *config, + NR_ServingCellConfigCommon_t *scc) { nfapi_nr_config_request_scf_t *cfg = &nrmac->config[0]; nrmac->common_channels[0].ServingCellConfigCommon = scc; @@ -527,6 +529,7 @@ static void config_common(gNB_MAC_INST *nrmac, nr_pdsch_AntennaPorts_t pdsch_Ant cfg->num_tlv += 2; // logical antenna ports + nr_pdsch_AntennaPorts_t pdsch_AntennaPorts = config->pdsch_AntennaPorts; int num_pdsch_antenna_ports = pdsch_AntennaPorts.N1 * pdsch_AntennaPorts.N2 * pdsch_AntennaPorts.XP; cfg->carrier_config.num_tx_ant.value = num_pdsch_antenna_ports; AssertFatal(num_pdsch_antenna_ports > 0 && num_pdsch_antenna_ports < 33, "pdsch_AntennaPorts in 1...32\n"); @@ -550,18 +553,19 @@ static void config_common(gNB_MAC_INST *nrmac, nr_pdsch_AntennaPorts_t pdsch_Ant cfg->num_tlv++; } + int pusch_AntennaPorts = config->pusch_AntennaPorts; cfg->carrier_config.num_rx_ant.value = pusch_AntennaPorts; AssertFatal(pusch_AntennaPorts > 0 && pusch_AntennaPorts < 13, "pusch_AntennaPorts in 1...12\n"); cfg->carrier_config.num_rx_ant.tl.tag = NFAPI_NR_CONFIG_NUM_RX_ANT_TAG; LOG_I(NR_MAC, - "Set RX antenna number to %d, Set TX antenna number to %d (num ssb %d: %x,%x)\n", + "Set TX antenna number to %d, Set RX antenna number to %d (num ssb %d: %x,%x)\n", cfg->carrier_config.num_tx_ant.value, cfg->carrier_config.num_rx_ant.value, num_ssb, cfg->ssb_table.ssb_mask_list[0].ssb_mask.value, cfg->ssb_table.ssb_mask_list[1].ssb_mask.value); AssertFatal(cfg->carrier_config.num_tx_ant.value > 0, - "carrier_config.num_tx_ant.value %d !\n", + "carrier_config.num_tx_ant.value %d!\n", cfg->carrier_config.num_tx_ant.value); cfg->num_tlv++; cfg->num_tlv++; @@ -589,13 +593,42 @@ static void config_common(gNB_MAC_INST *nrmac, nr_pdsch_AntennaPorts_t pdsch_Ant AssertFatal(periods_per_frame > 0, "TDD configuration cannot be configured\n"); } + int nb_tx = config->nb_bfw[0]; // number of tx antennas + int nb_beams = config->nb_bfw[1]; // number of beams // precoding matrix configuration (to be improved) cfg->pmi_list = init_DL_MIMO_codebook(nrmac, pdsch_AntennaPorts); + // beamforming matrix configuration + cfg->dbt_config.num_dig_beams = nb_beams; + if (nb_beams > 0) { + cfg->dbt_config.num_txrus = nb_tx; + cfg->dbt_config.dig_beam_list = malloc16(nb_beams * sizeof(*cfg->dbt_config.dig_beam_list)); + AssertFatal(cfg->dbt_config.dig_beam_list, "out of memory\n"); + for (int i = 0; i < nb_beams; i++) { + nfapi_nr_dig_beam_t *beam = &cfg->dbt_config.dig_beam_list[i]; + beam->beam_idx = i; + beam->txru_list = malloc16(nb_tx * sizeof(*beam->txru_list)); + for (int j = 0; j < nb_tx; j++) { + nfapi_nr_txru_t *txru = &beam->txru_list[j]; + txru->dig_beam_weight_Re = config->bw_list[j + i * nb_tx] & 0xffff; + txru->dig_beam_weight_Im = (config->bw_list[j + i * nb_tx] >> 16) & 0xffff; + LOG_D(NR_MAC, "Beam %d Tx %d Weight (%d, %d)\n", i, j, txru->dig_beam_weight_Re, txru->dig_beam_weight_Im); + } + } + } + + if (nrmac->beam_info.beam_allocation) { + cfg->analog_beamforming_ve.num_beams_period_vendor_ext.tl.tag = NFAPI_NR_FAPI_NUM_BEAMS_PERIOD_VENDOR_EXTENSION_TAG; + cfg->analog_beamforming_ve.num_beams_period_vendor_ext.value = nrmac->beam_info.beams_per_period; + cfg->num_tlv++; + cfg->analog_beamforming_ve.analog_bf_vendor_ext.tl.tag = NFAPI_NR_FAPI_ANALOG_BF_VENDOR_EXTENSION_TAG; + cfg->analog_beamforming_ve.analog_bf_vendor_ext.value = 1; // analog BF enabled + cfg->num_tlv++; + } } static void initialize_beam_information(NR_beam_info_t *beam_info, int mu, int slots_per_frame) { - if(!beam_info->beam_allocation) + if (!beam_info->beam_allocation) return; int size = mu == 0 ? slots_per_frame << 1 : slots_per_frame; @@ -644,7 +677,8 @@ void nr_mac_config_scc(gNB_MAC_INST *nrmac, NR_ServingCellConfigCommon_t *scc, c LOG_I(NR_MAC, "Configuring common parameters from NR ServingCellConfig\n"); - config_common(nrmac, config->pdsch_AntennaPorts, config->pusch_AntennaPorts, scc); + config_common(nrmac, config, scc); + fapi_beam_index_allocation(scc, nrmac); if (NFAPI_MODE == NFAPI_MONOLITHIC) { // nothing to be sent in the other cases diff --git a/openair2/LAYER2/NR_MAC_gNB/gNB_scheduler.c b/openair2/LAYER2/NR_MAC_gNB/gNB_scheduler.c index 7f364235ad..af07ecfb54 100644 --- a/openair2/LAYER2/NR_MAC_gNB/gNB_scheduler.c +++ b/openair2/LAYER2/NR_MAC_gNB/gNB_scheduler.c @@ -92,49 +92,6 @@ void clear_nr_nfapi_information(gNB_MAC_INST *gNB, LOG_D(NR_MAC, "%d.%d UL_tti_req_ahead SFN.slot = %d.%d for index %d \n", frameP, slotP, future_ul_tti_req->SFN, future_ul_tti_req->Slot, prev_slot % size); /* future_ul_tti_req->Slot is fixed! */ for (int i = 0; i < future_ul_tti_req->n_pdus; i++) { - switch(future_ul_tti_req->pdus_list[i].pdu_type){ - case NFAPI_NR_UL_CONFIG_PRACH_PDU_TYPE: - if(future_ul_tti_req->pdus_list[i].prach_pdu.beamforming.prgs_list){ - for (int j = 0; j < future_ul_tti_req->pdus_list[i].prach_pdu.beamforming.num_prgs; ++j) { - if(future_ul_tti_req->pdus_list[i].prach_pdu.beamforming.prgs_list[j].dig_bf_interface_list){ - free(future_ul_tti_req->pdus_list[i].prach_pdu.beamforming.prgs_list[j].dig_bf_interface_list); - } - } - free(future_ul_tti_req->pdus_list[i].prach_pdu.beamforming.prgs_list); - } - break; - case NFAPI_NR_UL_CONFIG_PUSCH_PDU_TYPE: - if(future_ul_tti_req->pdus_list[i].pusch_pdu.beamforming.prgs_list){ - for (int j = 0; j < future_ul_tti_req->pdus_list[i].pusch_pdu.beamforming.num_prgs; ++j) { - if(future_ul_tti_req->pdus_list[i].pusch_pdu.beamforming.prgs_list[j].dig_bf_interface_list){ - free(future_ul_tti_req->pdus_list[i].pusch_pdu.beamforming.prgs_list[j].dig_bf_interface_list); - } - } - free(future_ul_tti_req->pdus_list[i].pusch_pdu.beamforming.prgs_list); - } - break; - case NFAPI_NR_UL_CONFIG_PUCCH_PDU_TYPE: - if(future_ul_tti_req->pdus_list[i].pucch_pdu.beamforming.prgs_list){ - for (int j = 0; j < future_ul_tti_req->pdus_list[i].pucch_pdu.beamforming.num_prgs; ++j) { - if(future_ul_tti_req->pdus_list[i].pucch_pdu.beamforming.prgs_list[j].dig_bf_interface_list){ - free(future_ul_tti_req->pdus_list[i].pucch_pdu.beamforming.prgs_list[j].dig_bf_interface_list); - } - } - free(future_ul_tti_req->pdus_list[i].pucch_pdu.beamforming.prgs_list); - } - break; - case NFAPI_NR_UL_CONFIG_SRS_PDU_TYPE: - if(future_ul_tti_req->pdus_list[i].srs_pdu.beamforming.prgs_list){ - for (int j = 0; j < future_ul_tti_req->pdus_list[i].srs_pdu.beamforming.num_prgs; ++j) { - if(future_ul_tti_req->pdus_list[i].srs_pdu.beamforming.prgs_list[j].dig_bf_interface_list){ - free(future_ul_tti_req->pdus_list[i].srs_pdu.beamforming.prgs_list[j].dig_bf_interface_list); - } - } - free(future_ul_tti_req->pdus_list[i].srs_pdu.beamforming.prgs_list); - } - default: - break; - } future_ul_tti_req->pdus_list[i].pdu_type = 0; future_ul_tti_req->pdus_list[i].pdu_size = 0; } diff --git a/openair2/LAYER2/NR_MAC_gNB/gNB_scheduler_RA.c b/openair2/LAYER2/NR_MAC_gNB/gNB_scheduler_RA.c index ed32fe3669..b158942dd5 100644 --- a/openair2/LAYER2/NR_MAC_gNB/gNB_scheduler_RA.c +++ b/openair2/LAYER2/NR_MAC_gNB/gNB_scheduler_RA.c @@ -54,16 +54,13 @@ extern uint16_t sl_ahead; // forward declaration of functions used in this file static void fill_msg3_pusch_pdu(nfapi_nr_pusch_pdu_t *pusch_pdu, NR_ServingCellConfigCommon_t *scc, - int round, + const NR_RA_t *ra, int startSymbolAndLength, - rnti_t rnti, int scs, int bwp_size, int bwp_start, int mappingtype, - int fh, - int msg3_first_rb, - int msg3_nb_rb); + int fh); static void nr_fill_rar(uint8_t Mod_idP, NR_RA_t *ra, uint8_t *dlsch_buffer, nfapi_nr_pusch_pdu_t *pusch_pdu); static const uint8_t DELTA[4] = {2, 3, 4, 6}; @@ -91,16 +88,15 @@ static int16_t ssb_index_from_prach(module_id_t module_idP, float num_ssb_per_RO = ssb_per_rach_occasion[cfg->prach_config.ssb_per_rach.value]; uint16_t start_symbol_index = 0; - uint8_t mu,N_dur=0,N_t_slot=0,start_symbol = 0, temp_start_symbol = 0, N_RA_slot=0; + uint8_t N_dur=0,N_t_slot=0,start_symbol = 0, temp_start_symbol = 0, N_RA_slot=0; uint16_t format,RA_sfn_index = -1; uint8_t config_period = 1; uint16_t prach_occasion_id = -1; uint8_t num_active_ssb = cc->num_active_ssb; - - if (rach_ConfigCommon->msg1_SubcarrierSpacing) - mu = *rach_ConfigCommon->msg1_SubcarrierSpacing; - else - mu = scc->downlinkConfigCommon->frequencyInfoDL->scs_SpecificCarrierList.list.array[0]->subcarrierSpacing; + NR_MsgA_ConfigCommon_r16_t *msgacc = NULL; + if (scc->uplinkConfigCommon->initialUplinkBWP->ext1 && scc->uplinkConfigCommon->initialUplinkBWP->ext1->msgA_ConfigCommon_r16) + msgacc = scc->uplinkConfigCommon->initialUplinkBWP->ext1->msgA_ConfigCommon_r16->choice.setup; + int mu = nr_get_prach_mu(msgacc, rach_ConfigCommon); get_nr_prach_info_from_index(config_index, (int)frameP, @@ -167,7 +163,7 @@ void find_SSB_and_RO_available(gNB_MAC_INST *nrmac) nfapi_nr_config_request_scf_t *cfg = &nrmac->config[0]; NR_RACH_ConfigCommon_t *rach_ConfigCommon = scc->uplinkConfigCommon->initialUplinkBWP->rach_ConfigCommon->choice.setup; uint8_t config_index = rach_ConfigCommon->rach_ConfigGeneric.prach_ConfigurationIndex; - uint8_t mu,N_dur=0,N_t_slot=0,start_symbol=0,N_RA_slot = 0; + uint8_t N_dur=0,N_t_slot=0,start_symbol=0,N_RA_slot = 0; uint16_t format,N_RA_sfn = 0,unused_RA_occasion,repetition = 0; uint8_t num_active_ssb = 0; uint8_t max_association_period = 1; @@ -204,10 +200,10 @@ void find_SSB_and_RO_available(gNB_MAC_INST *nrmac) break; } - if (rach_ConfigCommon->msg1_SubcarrierSpacing) - mu = *rach_ConfigCommon->msg1_SubcarrierSpacing; - else - mu = scc->downlinkConfigCommon->frequencyInfoDL->scs_SpecificCarrierList.list.array[0]->subcarrierSpacing; + NR_MsgA_ConfigCommon_r16_t *msgacc = NULL; + if (scc->uplinkConfigCommon->initialUplinkBWP->ext1 && scc->uplinkConfigCommon->initialUplinkBWP->ext1->msgA_ConfigCommon_r16) + msgacc = scc->uplinkConfigCommon->initialUplinkBWP->ext1->msgA_ConfigCommon_r16->choice.setup; + int mu = nr_get_prach_mu(msgacc, rach_ConfigCommon); // prach is scheduled according to configuration index and tables 6.3.3.2.2 to 6.3.3.2.4 get_nr_prach_occasion_info_from_index(config_index, @@ -224,7 +220,7 @@ void find_SSB_and_RO_available(gNB_MAC_INST *nrmac) float num_ssb_per_RO = ssb_per_rach_occasion[cfg->prach_config.ssb_per_rach.value]; uint8_t fdm = cfg->prach_config.num_prach_fd_occasions.value; - uint64_t L_ssb = (((uint64_t) cfg->ssb_table.ssb_mask_list[0].ssb_mask.value)<<32) | cfg->ssb_table.ssb_mask_list[1].ssb_mask.value ; + uint64_t L_ssb = (((uint64_t) cfg->ssb_table.ssb_mask_list[0].ssb_mask.value) << 32) | cfg->ssb_table.ssb_mask_list[1].ssb_mask.value; uint32_t total_RA_occasions = N_RA_sfn * N_t_slot * N_RA_slot * fdm; for(int i = 0; i < 64; i++) { @@ -256,8 +252,115 @@ void find_SSB_and_RO_available(gNB_MAC_INST *nrmac) cc->max_association_period, N_RA_sfn, cc->total_prach_occasions_per_config_period); -} - +} + +static void schedule_nr_MsgA_pusch(NR_UplinkConfigCommon_t *uplinkConfigCommon, + gNB_MAC_INST *nr_mac, + module_id_t module_idP, + frame_t frameP, + sub_frame_t slotP, + nfapi_nr_prach_pdu_t *prach_pdu, + uint16_t dmrs_TypeA_Position, + NR_PhysCellId_t physCellId) +{ + NR_SCHED_ENSURE_LOCKED(&nr_mac->sched_lock); + + NR_MsgA_PUSCH_Resource_r16_t *msgA_PUSCH_Resource = uplinkConfigCommon->initialUplinkBWP->ext1->msgA_ConfigCommon_r16->choice + .setup->msgA_PUSCH_Config_r16->msgA_PUSCH_ResourceGroupA_r16; + + int mu = nr_get_prach_mu(uplinkConfigCommon->initialUplinkBWP->ext1->msgA_ConfigCommon_r16->choice.setup, + uplinkConfigCommon->initialUplinkBWP->rach_ConfigCommon->choice.setup); + + const int n_slots_frame = nr_slots_per_frame[mu]; + slot_t msgA_pusch_slot = (slotP + msgA_PUSCH_Resource->msgA_PUSCH_TimeDomainOffset_r16) % n_slots_frame; + frame_t msgA_pusch_frame = (frameP + ((slotP + msgA_PUSCH_Resource->msgA_PUSCH_TimeDomainOffset_r16) / n_slots_frame)) % 1024; + + int index = ul_buffer_index((int)msgA_pusch_frame, (int)msgA_pusch_slot, mu, nr_mac->UL_tti_req_ahead_size); + nfapi_nr_ul_tti_request_t *UL_tti_req = &nr_mac[module_idP].UL_tti_req_ahead[0][index]; + + UL_tti_req->SFN = msgA_pusch_frame; + UL_tti_req->Slot = msgA_pusch_slot; + AssertFatal(is_xlsch_in_slot(nr_mac->ulsch_slot_bitmap[msgA_pusch_slot / 64], msgA_pusch_slot), + "Slot %d is not an Uplink slot, invalid msgA_PUSCH_TimeDomainOffset_r16 %ld\n", + msgA_pusch_slot, + msgA_PUSCH_Resource->msgA_PUSCH_TimeDomainOffset_r16); + + UL_tti_req->pdus_list[UL_tti_req->n_pdus].pdu_type = NFAPI_NR_UL_CONFIG_PUSCH_PDU_TYPE; + UL_tti_req->pdus_list[UL_tti_req->n_pdus].pdu_size = sizeof(nfapi_nr_pusch_pdu_t); + nfapi_nr_pusch_pdu_t *pusch_pdu = &UL_tti_req->pdus_list[UL_tti_req->n_pdus].pusch_pdu; + memset(pusch_pdu, 0, sizeof(nfapi_nr_pusch_pdu_t)); + + rnti_t ra_rnti = nr_get_ra_rnti(prach_pdu->prach_start_symbol, slotP, prach_pdu->num_ra, 0); + + // Fill PUSCH PDU + pusch_pdu->pdu_bit_map = PUSCH_PDU_BITMAP_PUSCH_DATA; + pusch_pdu->rnti = ra_rnti; + pusch_pdu->handle = 0; + pusch_pdu->rb_size = msgA_PUSCH_Resource->nrofPRBs_PerMsgA_PO_r16; + pusch_pdu->mcs_table = 0; + pusch_pdu->frequency_hopping = + msgA_PUSCH_Resource->msgA_IntraSlotFrequencyHopping_r16 ? *msgA_PUSCH_Resource->msgA_IntraSlotFrequencyHopping_r16 : 0; + pusch_pdu->dmrs_ports = 1; // 6.2.2 in 38.214 only port 0 to be used + AssertFatal(msgA_PUSCH_Resource->startSymbolAndLengthMsgA_PO_r16, + "Only SLIV based on startSymbolAndLengthMsgA_PO_r16 implemented\n"); + int S = 0; + int L = 0; + SLIV2SL(*msgA_PUSCH_Resource->startSymbolAndLengthMsgA_PO_r16, &S, &L); + pusch_pdu->start_symbol_index = S; + pusch_pdu->nr_of_symbols = L; + pusch_pdu->pusch_data.new_data_indicator = 1; + pusch_pdu->nrOfLayers = 1; + pusch_pdu->num_dmrs_cdm_grps_no_data = 2; // no data in dmrs symbols as in 6.2.2 in 38.214 + pusch_pdu->ul_dmrs_symb_pos = get_l_prime(3, 0, pusch_dmrs_pos2, pusch_len1, 10, dmrs_TypeA_Position); + pusch_pdu->transform_precoding = *uplinkConfigCommon->initialUplinkBWP->ext1->msgA_ConfigCommon_r16->choice.setup->msgA_PUSCH_Config_r16->msgA_TransformPrecoder_r16; + pusch_pdu->rb_bitmap[0] = 0; + pusch_pdu->rb_start = msgA_PUSCH_Resource->frequencyStartMsgA_PUSCH_r16; // rb_start depends on the RO + int locationAndBandwidth = uplinkConfigCommon->initialUplinkBWP->genericParameters.locationAndBandwidth; + pusch_pdu->bwp_size = NRRIV2BW(locationAndBandwidth, MAX_BWP_SIZE); + pusch_pdu->bwp_start = NRRIV2PRBOFFSET(locationAndBandwidth, MAX_BWP_SIZE); + pusch_pdu->subcarrier_spacing = 0; + pusch_pdu->cyclic_prefix = 0; + pusch_pdu->uplink_frequency_shift_7p5khz = 0; + pusch_pdu->vrb_to_prb_mapping = 0; + pusch_pdu->dmrs_config_type = 0; + pusch_pdu->data_scrambling_id = 0; + if (msgA_PUSCH_Resource->msgA_DMRS_Config_r16.msgA_ScramblingID0_r16) { + pusch_pdu->ul_dmrs_scrambling_id = *msgA_PUSCH_Resource->msgA_DMRS_Config_r16.msgA_ScramblingID0_r16; + } else { + pusch_pdu->ul_dmrs_scrambling_id = physCellId; + } + pusch_pdu->scid = + 0; // DMRS sequence initialization [TS38.211, sec 6.4.1.1.1]. Should match what is sent in DCI 0_1, otherwise set to 0. + pusch_pdu->pusch_identity = 0; + pusch_pdu->resource_alloc = 1; // type 1 + pusch_pdu->tx_direct_current_location = 0; + pusch_pdu->mcs_index = msgA_PUSCH_Resource->msgA_MCS_r16; + pusch_pdu->qam_mod_order = nr_get_Qm_dl(pusch_pdu->mcs_index, pusch_pdu->mcs_table); + + int num_dmrs_symb = 0; + for (int i = 10; i < 10 + 3; i++) + num_dmrs_symb += (pusch_pdu->ul_dmrs_symb_pos >> i) & 1; + AssertFatal(pusch_pdu->mcs_index <= 28, "Exceeding MCS limit for MsgA PUSCH\n"); + int R = nr_get_code_rate_ul(pusch_pdu->mcs_index, pusch_pdu->mcs_table); + pusch_pdu->target_code_rate = R; + int TBS = nr_compute_tbs(pusch_pdu->qam_mod_order, + R, + pusch_pdu->rb_size, + pusch_pdu->nr_of_symbols, + num_dmrs_symb * 12, // nb dmrs set for no data in dmrs symbol + 0, // nb_rb_oh + 0, // to verify tb scaling + pusch_pdu->nrOfLayers) + >> 3; + + pusch_pdu->pusch_data.tb_size = TBS; + pusch_pdu->maintenance_parms_v3.ldpcBaseGraph = get_BG(TBS << 3, R); + + LOG_D(NR_MAC, "Scheduling MsgA PUSCH in %d.%d\n", msgA_pusch_frame, msgA_pusch_slot); + + UL_tti_req->n_pdus += 1; +} + void schedule_nr_prach(module_id_t module_idP, frame_t frameP, sub_frame_t slotP) { gNB_MAC_INST *gNB = RC.nrmac[module_idP]; @@ -267,11 +370,10 @@ void schedule_nr_prach(module_id_t module_idP, frame_t frameP, sub_frame_t slotP NR_COMMON_channels_t *cc = gNB->common_channels; NR_ServingCellConfigCommon_t *scc = cc->ServingCellConfigCommon; NR_RACH_ConfigCommon_t *rach_ConfigCommon = scc->uplinkConfigCommon->initialUplinkBWP->rach_ConfigCommon->choice.setup; - int mu; - if (rach_ConfigCommon->msg1_SubcarrierSpacing) - mu = *rach_ConfigCommon->msg1_SubcarrierSpacing; - else - mu = scc->downlinkConfigCommon->frequencyInfoDL->scs_SpecificCarrierList.list.array[0]->subcarrierSpacing; + NR_MsgA_ConfigCommon_r16_t *msgacc = NULL; + if (scc->uplinkConfigCommon->initialUplinkBWP->ext1 && scc->uplinkConfigCommon->initialUplinkBWP->ext1->msgA_ConfigCommon_r16) + msgacc = scc->uplinkConfigCommon->initialUplinkBWP->ext1->msgA_ConfigCommon_r16->choice.setup; + int mu = nr_get_prach_mu(msgacc, rach_ConfigCommon); int index = ul_buffer_index(frameP, slotP, mu, gNB->UL_tti_req_ahead_size); nfapi_nr_ul_tti_request_t *UL_tti_req = &RC.nrmac[module_idP]->UL_tti_req_ahead[0][index]; nfapi_nr_config_request_scf_t *cfg = &RC.nrmac[module_idP]->config[0]; @@ -330,15 +432,23 @@ void schedule_nr_prach(module_id_t module_idP, frame_t frameP, sub_frame_t slotP continue; float num_ssb_per_RO = ssb_per_rach_occasion[cfg->prach_config.ssb_per_rach.value]; + int beam_index = 0; if(num_ssb_per_RO <= 1) { - int ssb_index = (int) (prach_occasion_id / (int)(1 / num_ssb_per_RO)) % cc->num_active_ssb; - beam = beam_allocation_procedure(&gNB->beam_info, frameP, slotP, ssb_index, nr_slots_per_frame[mu]); - AssertFatal(beam.idx >= 0, "Cannot allocate PRACH corresponding to SSB %d in any available beam\n", ssb_index); + // ordered ssb number + int n_ssb = (int) (prach_occasion_id / (int)(1 / num_ssb_per_RO)) % cc->num_active_ssb; + // fapi beam index + beam_index = get_fapi_beamforming_index(gNB, cc->ssb_index[n_ssb]); + // multi-beam allocation structure + beam = beam_allocation_procedure(&gNB->beam_info, frameP, slotP, beam_index, nr_slots_per_frame[mu]); + AssertFatal(beam.idx >= 0, "Cannot allocate PRACH corresponding to %d SSB transmitted in any available beam\n", n_ssb + 1); } else { int first_ssb_index = (prach_occasion_id * (int)num_ssb_per_RO) % cc->num_active_ssb; for(int j = first_ssb_index; j < first_ssb_index + num_ssb_per_RO; j++) { - beam = beam_allocation_procedure(&gNB->beam_info, frameP, slotP, j, nr_slots_per_frame[mu]); + // fapi beam index + beam_index = get_fapi_beamforming_index(gNB, cc->ssb_index[j]); + // multi-beam allocation structure + beam = beam_allocation_procedure(&gNB->beam_info, frameP, slotP, beam_index, nr_slots_per_frame[mu]); AssertFatal(beam.idx >= 0, "Cannot allocate PRACH corresponding to SSB %d in any available beam\n", j); } } @@ -361,6 +471,11 @@ void schedule_nr_prach(module_id_t module_idP, frame_t frameP, sub_frame_t slotP format0, rach_ConfigCommon->restrictedSetConfig); + prach_pdu->beamforming.num_prgs = 0; + prach_pdu->beamforming.prg_size = 0; + prach_pdu->beamforming.dig_bf_interface = 1; + prach_pdu->beamforming.prgs_list[0].dig_bf_interface_list[0].beam_idx = beam_index; + LOG_D(NR_MAC, "Frame %d, Slot %d: Prach Occasion id = %u fdm index = %u start symbol = %u slot index = %u subframe index = %u \n", frameP, @@ -426,6 +541,18 @@ void schedule_nr_prach(module_id_t module_idP, frame_t frameP, sub_frame_t slotP AssertFatal(1==0,"Invalid PRACH format"); } } + if (scc->uplinkConfigCommon->initialUplinkBWP->ext1 + && scc->uplinkConfigCommon->initialUplinkBWP->ext1->msgA_ConfigCommon_r16) { + if (gNB->UE_info.list[0] == NULL) + schedule_nr_MsgA_pusch(scc->uplinkConfigCommon, + gNB, + module_idP, + frameP, + slotP, + prach_pdu, + scc->dmrs_TypeA_Position, + *scc->physCellId); + } } } } @@ -445,6 +572,76 @@ void schedule_nr_prach(module_id_t module_idP, frame_t frameP, sub_frame_t slotP } } +int nr_fill_successrar(const NR_UE_sched_ctrl_t *ue_sched_ctl, + rnti_t crnti, + const unsigned char *ue_cont_res_id, + uint8_t resource_indicator, + uint8_t timing_indicator, + unsigned char *mac_pdu, + int mac_pdu_length) +{ + LOG_D(NR_MAC, "mac_pdu_length = %d\n", mac_pdu_length); + int timing_advance_cmd = ue_sched_ctl->ta_update; + // TS 38.321 - Figure 6.1.5a-1: BI MAC subheader + NR_RA_HEADER_BI_MSGB *bi = (NR_RA_HEADER_BI_MSGB *)&mac_pdu[mac_pdu_length]; + mac_pdu_length += sizeof(NR_RA_HEADER_BI_MSGB); + + bi->E = 1; + bi->T1 = 0; + bi->T2 = 0; + bi->R = 0; + bi->BI = 0; // BI = 0, 5ms + + // TS 38.321 - Figure 6.1.5a-3: SuccessRAR MAC subheader + NR_RA_HEADER_SUCCESS_RAR_MSGB *SUCESS_RAR_header = (NR_RA_HEADER_SUCCESS_RAR_MSGB *)&mac_pdu[mac_pdu_length]; + mac_pdu_length += sizeof(NR_RA_HEADER_SUCCESS_RAR_MSGB); + + SUCESS_RAR_header->E = 0; + SUCESS_RAR_header->T1 = 0; + SUCESS_RAR_header->T2 = 1; + SUCESS_RAR_header->S = 0; + SUCESS_RAR_header->R = 0; + + // TS 38.321 - Figure 6.2.3a-2: successRAR + NR_MAC_SUCCESS_RAR *successRAR = (NR_MAC_SUCCESS_RAR *)&mac_pdu[mac_pdu_length]; + mac_pdu_length += sizeof(NR_MAC_SUCCESS_RAR); + + successRAR->CONT_RES_1 = ue_cont_res_id[0]; + successRAR->CONT_RES_2 = ue_cont_res_id[1]; + successRAR->CONT_RES_3 = ue_cont_res_id[2]; + successRAR->CONT_RES_4 = ue_cont_res_id[3]; + successRAR->CONT_RES_5 = ue_cont_res_id[4]; + successRAR->CONT_RES_6 = ue_cont_res_id[5]; + successRAR->R = 0; + successRAR->CH_ACESS_CPEXT = 1; + successRAR->TPC = ue_sched_ctl->tpc0; + successRAR->HARQ_FTI = timing_indicator; + successRAR->PUCCH_RI = resource_indicator; + successRAR->TA1 = (uint8_t)(timing_advance_cmd >> 8); // 4 MSBs of timing advance; + successRAR->TA2 = (uint8_t)(timing_advance_cmd & 0xff); // 8 LSBs of timing advance; + successRAR->CRNTI_1 = (uint8_t)(crnti >> 8); // 8 MSBs of rnti + successRAR->CRNTI_2 = (uint8_t)(crnti & 0xff); // 8 LSBs of rnti + + LOG_D(NR_MAC, + "successRAR: Contention Resolution ID 0x%02x%02x%02x%02x%02x%02x R 0x%01x CH_ACESS_CPEXT 0x%02x TPC 0x%02x HARQ_FTI 0x%03x " + "PUCCH_RI 0x%04x TA 0x%012x CRNTI 0x%04x\n", + successRAR->CONT_RES_1, + successRAR->CONT_RES_2, + successRAR->CONT_RES_3, + successRAR->CONT_RES_4, + successRAR->CONT_RES_5, + successRAR->CONT_RES_6, + successRAR->R, + successRAR->CH_ACESS_CPEXT, + successRAR->TPC, + successRAR->HARQ_FTI, + successRAR->PUCCH_RI, + timing_advance_cmd, + crnti); + LOG_D(NR_MAC, "mac_pdu_length = %d\n", mac_pdu_length); + return mac_pdu_length; +} + static bool ra_contains_preamble(const NR_RA_t *ra, uint16_t preamble_index) { for (int j = 0; j < ra->preambles.num_preambles; j++) { @@ -534,22 +731,32 @@ void nr_initiate_ra_proc(module_id_t module_idP, ra->rnti = trial; } - ra->ra_state = nrRA_Msg2; ra->preamble_frame = frameP; ra->preamble_slot = slotP; ra->preamble_index = preamble_index; ra->timing_offset = timing_offset; uint8_t ul_carrier_id = 0; // 0 for NUL 1 for SUL ra->RA_rnti = nr_get_ra_rnti(symbol, slotP, freq_index, ul_carrier_id); + + NR_ServingCellConfigCommon_t *scc = cc->ServingCellConfigCommon; + if (scc->uplinkConfigCommon->initialUplinkBWP->ext1 && scc->uplinkConfigCommon->initialUplinkBWP->ext1->msgA_ConfigCommon_r16) { + ra->ra_type = RA_2_STEP; + ra->ra_state = nrRA_WAIT_MsgA_PUSCH; + ra->MsgB_rnti = nr_get_MsgB_rnti(symbol, slotP, freq_index, ul_carrier_id); + } else { + ra->ra_type = RA_4_STEP; + ra->ra_state = nrRA_Msg2; + } + int index = ra - cc->ra; LOG_I(NR_MAC, "%d.%d UE RA-RNTI %04x TC-RNTI %04x: Activating RA process index %d\n", frameP, slotP, ra->RA_rnti, ra->rnti, index); // Configure RA BWP - NR_ServingCellConfigCommon_t *scc = cc->ServingCellConfigCommon; configure_UE_BWP(nr_mac, scc, NULL, ra, NULL, -1, -1); - uint8_t beam_index = ssb_index_from_prach(module_idP, frameP, slotP, preamble_index, freq_index, symbol); - ra->beam_id = cc->ssb_index[beam_index]; + // return current SSB order in the list of tranmitted SSBs + int n_ssb = ssb_index_from_prach(module_idP, frameP, slotP, preamble_index, freq_index, symbol); + ra->beam_id = get_fapi_beamforming_index(nr_mac, cc->ssb_index[n_ssb]); NR_SCHED_UNLOCK(&nr_mac->sched_lock); @@ -654,13 +861,7 @@ static void nr_generate_Msg3_retransmission(module_id_t module_idP, nfapi_nr_pusch_pdu_t *pusch_pdu = &future_ul_tti_req->pdus_list[future_ul_tti_req->n_pdus].pusch_pdu; memset(pusch_pdu, 0, sizeof(nfapi_nr_pusch_pdu_t)); - fill_msg3_pusch_pdu(pusch_pdu, scc, - ra->msg3_round, - startSymbolAndLength, - ra->rnti, mu, - BWPSize, BWPStart, - mappingtype, fh, - rbStart, ra->msg3_nb_rb); + fill_msg3_pusch_pdu(pusch_pdu, scc, ra, startSymbolAndLength, mu, BWPSize, BWPStart, mappingtype, fh); future_ul_tti_req->n_pdus += 1; // generation of DCI 0_0 to schedule msg3 retransmission @@ -706,6 +907,12 @@ static void nr_generate_Msg3_retransmission(module_id_t module_idP, dci_pdu->beta_PDCCH_1_0 = 0; dci_pdu->powerControlOffsetSS = 1; + dci_pdu->precodingAndBeamforming.num_prgs = 0; + dci_pdu->precodingAndBeamforming.prg_size = 0; + dci_pdu->precodingAndBeamforming.dig_bf_interfaces = 1; + dci_pdu->precodingAndBeamforming.prgs_list[0].pm_idx = 0; + dci_pdu->precodingAndBeamforming.prgs_list[0].dig_bf_interface_list[0].beam_idx = ra->beam_id; + dci_pdu_rel15_t uldci_payload={0}; config_uldci(sc_info, @@ -883,16 +1090,13 @@ static void nr_get_Msg3alloc(module_id_t module_id, static void fill_msg3_pusch_pdu(nfapi_nr_pusch_pdu_t *pusch_pdu, NR_ServingCellConfigCommon_t *scc, - int round, + const NR_RA_t *ra, int startSymbolAndLength, - rnti_t rnti, int scs, int bwp_size, int bwp_start, int mappingtype, - int fh, - int msg3_first_rb, - int msg3_nb_rb) + int fh) { int start_symbol_index,nr_of_symbols; @@ -900,7 +1104,7 @@ static void fill_msg3_pusch_pdu(nfapi_nr_pusch_pdu_t *pusch_pdu, int mcsindex = -1; // init value pusch_pdu->pdu_bit_map = PUSCH_PDU_BITMAP_PUSCH_DATA; - pusch_pdu->rnti = rnti; + pusch_pdu->rnti = ra->rnti; pusch_pdu->handle = 0; pusch_pdu->bwp_start = bwp_start; pusch_pdu->bwp_size = bwp_size; @@ -928,11 +1132,11 @@ static void fill_msg3_pusch_pdu(nfapi_nr_pusch_pdu_t *pusch_pdu, pusch_pdu->num_dmrs_cdm_grps_no_data = 2; // no data in dmrs symbols as in 6.2.2 in 38.214 pusch_pdu->resource_alloc = 1; //type 1 memset(pusch_pdu->rb_bitmap, 0, sizeof(pusch_pdu->rb_bitmap)); - pusch_pdu->rb_start = msg3_first_rb; - if (msg3_nb_rb > pusch_pdu->bwp_size) - AssertFatal(1==0,"MSG3 allocated number of RBs exceed the BWP size\n"); + pusch_pdu->rb_start = ra->msg3_first_rb; + if (ra->msg3_nb_rb > pusch_pdu->bwp_size) + AssertFatal(false, "MSG3 allocated number of RBs exceed the BWP size\n"); else - pusch_pdu->rb_size = msg3_nb_rb; + pusch_pdu->rb_size = ra->msg3_nb_rb; pusch_pdu->vrb_to_prb_mapping = 0; pusch_pdu->frequency_hopping = fh; @@ -945,27 +1149,17 @@ static void fill_msg3_pusch_pdu(nfapi_nr_pusch_pdu_t *pusch_pdu, pusch_pdu->start_symbol_index = start_symbol_index; pusch_pdu->nr_of_symbols = nr_of_symbols; //Optional Data only included if indicated in pduBitmap - pusch_pdu->pusch_data.rv_index = nr_rv_round_map[round%4]; + pusch_pdu->pusch_data.rv_index = nr_rv_round_map[ra->msg3_round % 4]; pusch_pdu->pusch_data.harq_process_id = 0; - pusch_pdu->pusch_data.new_data_indicator = (round == 0) ? 1 : 0;; + pusch_pdu->pusch_data.new_data_indicator = (ra->msg3_round == 0) ? 1 : 0;; pusch_pdu->pusch_data.num_cb = 0; // Beamforming pusch_pdu->beamforming.num_prgs = 0; pusch_pdu->beamforming.prg_size = 0; // bwp_size; - pusch_pdu->beamforming.dig_bf_interface = 0; - if (pusch_pdu->beamforming.num_prgs > 0) { - if (pusch_pdu->beamforming.prgs_list == NULL) { - pusch_pdu->beamforming.prgs_list = calloc(pusch_pdu->beamforming.num_prgs, sizeof(*pusch_pdu->beamforming.prgs_list)); - } - if (pusch_pdu->beamforming.dig_bf_interface > 0) { - if (pusch_pdu->beamforming.prgs_list[0].dig_bf_interface_list == NULL) { - pusch_pdu->beamforming.prgs_list[0].dig_bf_interface_list = - calloc(pusch_pdu->beamforming.dig_bf_interface, sizeof(*pusch_pdu->beamforming.prgs_list[0].dig_bf_interface_list)); - } - } - pusch_pdu->beamforming.prgs_list[0].dig_bf_interface_list[0].beam_idx = 0; - } + pusch_pdu->beamforming.dig_bf_interface = 1; + pusch_pdu->beamforming.prgs_list[0].dig_bf_interface_list[0].beam_idx = ra->beam_id; + int num_dmrs_symb = 0; for(int i = start_symbol_index; i < start_symbol_index+nr_of_symbols; i++) num_dmrs_symb += (pusch_pdu->ul_dmrs_symb_pos >> i) & 1; @@ -1048,13 +1242,7 @@ static void nr_add_msg3(module_id_t module_idP, int CC_id, frame_t frameP, sub_f ra->msg3_first_rb, ra->msg3_round); - fill_msg3_pusch_pdu(pusch_pdu,scc, - ra->msg3_round, - startSymbolAndLength, - ra->rnti, scs, - ibwp_size, ra->msg3_bwp_start, - mappingtype, fh, - ra->msg3_first_rb, ra->msg3_nb_rb); + fill_msg3_pusch_pdu(pusch_pdu, scc, ra, startSymbolAndLength, scs, ibwp_size, ra->msg3_bwp_start, mappingtype, fh); future_ul_tti_req->n_pdus += 1; // calling function to fill rar message @@ -1271,7 +1459,7 @@ static void nr_generate_Msg2(module_id_t module_idP, BWPStart = dl_bwp->BWPStart; BWPSize = sc_info->initial_dl_BWPSize; } else { - type0_PDCCH_CSS_config = &nr_mac->type0_PDCCH_CSS_config[ra->beam_id]; + type0_PDCCH_CSS_config = &nr_mac->type0_PDCCH_CSS_config[cc->ssb_index[ra->beam_id]]; BWPStart = type0_PDCCH_CSS_config->cset_start_rb; BWPSize = type0_PDCCH_CSS_config->num_rbs; } @@ -1354,7 +1542,7 @@ static void nr_generate_Msg2(module_id_t module_idP, pdsch_pdu_rel15->precodingAndBeamforming.prg_size = 0; pdsch_pdu_rel15->precodingAndBeamforming.dig_bf_interfaces = 0; pdsch_pdu_rel15->precodingAndBeamforming.prgs_list[0].pm_idx = 0; - pdsch_pdu_rel15->precodingAndBeamforming.prgs_list[0].dig_bf_interface_list[0].beam_idx = 0; + pdsch_pdu_rel15->precodingAndBeamforming.prgs_list[0].dig_bf_interface_list[0].beam_idx = ra->beam_id; LOG_A(NR_MAC, "UE %04x: %d.%d Generating RA-Msg2 DCI, RA RNTI 0x%x, state %d, CoreSetType %d, RAPID %d\n", @@ -1438,6 +1626,12 @@ static void nr_generate_Msg2(module_id_t module_idP, dci_pdu->beta_PDCCH_1_0 = 0; dci_pdu->powerControlOffsetSS = 1; + dci_pdu->precodingAndBeamforming.num_prgs = 0; + dci_pdu->precodingAndBeamforming.prg_size = 0; + dci_pdu->precodingAndBeamforming.dig_bf_interfaces = 1; + dci_pdu->precodingAndBeamforming.prgs_list[0].pm_idx = 0; + dci_pdu->precodingAndBeamforming.prgs_list[0].dig_bf_interface_list[0].beam_idx = ra->beam_id; + dci_pdu_rel15_t dci_payload; dci_payload.frequency_domain_assignment.val = PRBalloc_to_locationandbandwidth0(pdsch_pdu_rel15->rbSize, pdsch_pdu_rel15->rbStart, BWPSize); @@ -1603,7 +1797,7 @@ static void prepare_dl_pdus(gNB_MAC_INST *nr_mac, BWPStart = dl_bwp->BWPStart; BWPSize = dl_bwp->BWPSize; } else { - type0_PDCCH_CSS_config = &nr_mac->type0_PDCCH_CSS_config[ra->beam_id]; + type0_PDCCH_CSS_config = &nr_mac->type0_PDCCH_CSS_config[cc->ssb_index[ra->beam_id]]; BWPStart = type0_PDCCH_CSS_config->cset_start_rb; BWPSize = type0_PDCCH_CSS_config->num_rbs; } @@ -1665,6 +1859,12 @@ static void prepare_dl_pdus(gNB_MAC_INST *nr_mac, dci_pdu->beta_PDCCH_1_0 = 0; dci_pdu->powerControlOffsetSS = 1; + dci_pdu->precodingAndBeamforming.num_prgs = 0; + dci_pdu->precodingAndBeamforming.prg_size = 0; + dci_pdu->precodingAndBeamforming.dig_bf_interfaces = 1; + dci_pdu->precodingAndBeamforming.prgs_list[0].pm_idx = 0; + dci_pdu->precodingAndBeamforming.prgs_list[0].dig_bf_interface_list[0].beam_idx = ra->beam_id; + dci_pdu_rel15_t dci_payload; dci_payload.frequency_domain_assignment.val = PRBalloc_to_locationandbandwidth0(pdsch_pdu_rel15->rbSize, pdsch_pdu_rel15->rbStart, @@ -1737,32 +1937,31 @@ static void prepare_dl_pdus(gNB_MAC_INST *nr_mac, LOG_D(NR_MAC, "numDlDci: %i\n", pdcch_pdu_rel15->numDlDci); } -static void nr_generate_Msg4(module_id_t module_idP, - int CC_id, - frame_t frameP, - sub_frame_t slotP, - NR_RA_t *ra, - nfapi_nr_dl_tti_request_t *DL_req, - nfapi_nr_tx_data_request_t *TX_req) +static void nr_generate_Msg4_MsgB(module_id_t module_idP, + int CC_id, + frame_t frameP, + sub_frame_t slotP, + NR_RA_t *ra, + nfapi_nr_dl_tti_request_t *DL_req, + nfapi_nr_tx_data_request_t *TX_req) { gNB_MAC_INST *nr_mac = RC.nrmac[module_idP]; NR_COMMON_channels_t *cc = &nr_mac->common_channels[CC_id]; NR_UE_DL_BWP_t *dl_bwp = &ra->DL_BWP; - // if it is a DL slot, if the RA is in MSG4 state + // if it is a DL slot, if the RA is in MSG4 state if (is_xlsch_in_slot(nr_mac->dlsch_slot_bitmap[slotP / 64], slotP)) { - NR_ServingCellConfigCommon_t *scc = cc->ServingCellConfigCommon; NR_SearchSpace_t *ss = ra->ra_ss; - + const char *ra_type_str = ra->ra_type == RA_2_STEP ? "MsgB" : "Msg4"; NR_ControlResourceSet_t *coreset = ra->coreset; - AssertFatal(coreset!=NULL,"Coreset cannot be null for RA-Msg4\n"); + AssertFatal(coreset != NULL, "Coreset cannot be null for RA %s\n", ra_type_str); uint16_t mac_sdu_length = 0; NR_UE_info_t *UE = find_nr_UE(&nr_mac->UE_info, ra->rnti); if (!UE) { - LOG_E(NR_MAC, "want to generate Msg4, but rnti %04x not in the table\n", ra->rnti); + LOG_E(NR_MAC, "want to generate %s, but rnti %04x not in the table\n", ra_type_str, ra->rnti); return; } @@ -1799,7 +1998,7 @@ static void nr_generate_Msg4(module_id_t module_idP, BWPStart = dl_bwp->BWPStart; BWPSize = dl_bwp->BWPSize; } else { - type0_PDCCH_CSS_config = &nr_mac->type0_PDCCH_CSS_config[ra->beam_id]; + type0_PDCCH_CSS_config = &nr_mac->type0_PDCCH_CSS_config[cc->ssb_index[ra->beam_id]]; BWPStart = type0_PDCCH_CSS_config->cset_start_rb; BWPSize = type0_PDCCH_CSS_config->num_rbs; } @@ -1858,7 +2057,8 @@ static void nr_generate_Msg4(module_id_t module_idP, } else { uint8_t subheader_len = (mac_sdu_length < 256) ? sizeof(NR_MAC_SUBHEADER_SHORT) : sizeof(NR_MAC_SUBHEADER_LONG); - pdu_length = mac_sdu_length + subheader_len + 7; //7 is contetion resolution length + pdu_length = mac_sdu_length + subheader_len + 13; // 13 is contention resolution length of msgB. It is divided into 3 parts: + // BI MAC subheader (1 Oct) + SuccessRAR MAC subheader (1 Oct) + SuccessRAR (11 Oct) } // increase PRBs until we get to BWPSize or TBS is bigger than MAC PDU size @@ -1873,7 +2073,7 @@ static void nr_generate_Msg4(module_id_t module_idP, rbSize, msg4_tda.nrOfSymbols, dmrs_info.N_PRB_DMRS * dmrs_info.N_DMRS_SLOT, 0, tb_scaling,1) >> 3; } while (tb_size < pdu_length && mcsIndex<=28); - AssertFatal(tb_size >= pdu_length,"Cannot allocate Msg4\n"); + AssertFatal(tb_size >= pdu_length, "Cannot allocate %s\n", ra_type_str); int i = 0; uint16_t *vrb_map = cc[CC_id].vrb_map[beam.idx]; @@ -1936,9 +2136,22 @@ static void nr_generate_Msg4(module_id_t module_idP, uint8_t *buf = (uint8_t *) harq->transportBlock; // Bytes to be transmitted if (harq->round == 0) { - // UE Contention Resolution Identity MAC CE - uint16_t mac_pdu_length = nr_write_ce_dlsch_pdu(module_idP, nr_mac->sched_ctrlCommon, buf, 255, ra->cont_res_id); - LOG_D(NR_MAC,"Encoded contention resolution mac_pdu_length %d\n",mac_pdu_length); + uint16_t mac_pdu_length = 0; + if (ra->ra_type == RA_4_STEP) { + // UE Contention Resolution Identity MAC CE + mac_pdu_length = nr_write_ce_dlsch_pdu(module_idP, nr_mac->sched_ctrlCommon, buf, 255, ra->cont_res_id); + } else if (ra->ra_type == RA_2_STEP) { + mac_pdu_length = nr_fill_successrar(nr_mac->sched_ctrlCommon, + ra->rnti, + ra->cont_res_id, + pucch->resource_indicator, + pucch->timing_indicator, + buf, + mac_pdu_length); + } else { + AssertFatal(false, "RA type %d not implemented!\n", ra->ra_type); + } + uint8_t buffer[CCCH_SDU_SIZE]; uint8_t mac_subheader_len = sizeof(NR_MAC_SUBHEADER_SHORT); // Get RLC data on the SRB (RRCSetup, RRCReestablishment) @@ -1971,9 +2184,20 @@ static void nr_generate_Msg4(module_id_t module_idP, memcpy(&buf[mac_pdu_length + mac_subheader_len], buffer, mac_sdu_length); } + rnti_t rnti = ra->ra_type == RA_4_STEP ? ra->rnti : ra->MsgB_rnti; + const int pduindex = nr_mac->pdu_index[CC_id]++; prepare_dl_pdus(nr_mac, ra, dl_bwp, dl_req, pucch, dmrs_info, msg4_tda, aggregation_level, CCEIndex, tb_size, harq->ndi, sched_ctrl->tpc1, delta_PRI, - current_harq_pid, time_domain_assignment, CC_id, ra->rnti, harq->round, mcsIndex, tb_scaling, pduindex, rbStart, rbSize); + current_harq_pid, + time_domain_assignment, + CC_id, + rnti, + harq->round, + mcsIndex, + tb_scaling, + pduindex, + rbStart, + rbSize); // Add padding header and zero rest out if there is space left if (ra->mac_pdu_length < harq->tb_size) { @@ -2012,7 +2236,7 @@ static void nr_generate_Msg4(module_id_t module_idP, if (pucch == NULL) { LOG_A(NR_MAC, "(UE RNTI 0x%04x) Skipping Ack of RA-Msg4. CBRA procedure succeeded!\n", ra->rnti); - UE->Msg4_ACKed = true; + UE->Msg4_MsgB_ACKed = true; // Pause scheduling according to: // 3GPP TS 38.331 Section 12 Table 12.1-1: UE performance requirements for RRC procedures for UEs @@ -2023,17 +2247,18 @@ static void nr_generate_Msg4(module_id_t module_idP, nr_clear_ra_proc(ra); } else { - ra->ra_state = nrRA_WAIT_Msg4_ACK; + ra->ra_state = nrRA_WAIT_Msg4_MsgB_ACK; LOG_I(NR_MAC,"UE %04x Generate msg4: feedback at %4d.%2d, payload %d bytes, next state WAIT_Msg4_ACK\n", ra->rnti, pucch->frame, pucch->ul_slot, harq->tb_size); } } } -static void nr_check_Msg4_Ack(module_id_t module_id, int CC_id, frame_t frame, sub_frame_t slot, NR_RA_t *ra) +static void nr_check_Msg4_MsgB_Ack(module_id_t module_id, int CC_id, frame_t frame, sub_frame_t slot, NR_RA_t *ra) { + const char *ra_type_str = ra->ra_type == RA_2_STEP ? "MsgB" : "Msg4"; NR_UE_info_t *UE = find_nr_UE(&RC.nrmac[module_id]->UE_info, ra->rnti); if (!UE) { - LOG_E(NR_MAC, "Cannot check Msg4 ACK/NACK, rnti %04x not in the table\n", ra->rnti); + LOG_E(NR_MAC, "Cannot check %s ACK/NACK, rnti %04x not in the table\n", ra_type_str, ra->rnti); return; } const int current_harq_pid = ra->harq_pid; @@ -2045,10 +2270,14 @@ static void nr_check_Msg4_Ack(module_id_t module_id, int CC_id, frame_t frame, s if (harq->is_waiting == 0) { if (harq->round == 0) { - if (UE->Msg4_ACKed) { - LOG_A(NR_MAC, "(UE RNTI 0x%04x) Received Ack of RA-Msg4. CBRA procedure succeeded!\n", ra->rnti); + if (UE->Msg4_MsgB_ACKed) { + LOG_A(NR_MAC, + "%4d.%2d UE %04x: Received Ack of %s. CBRA procedure succeeded!\n", + frame, slot, ra->rnti, ra_type_str); } else { - LOG_I(NR_MAC, "%4d.%2d UE %04x: RA Procedure failed at Msg4!\n", frame, slot, ra->rnti); + LOG_I(NR_MAC, + "%4d.%2d UE %04x: RA Procedure failed at %s!\n", + frame, slot, ra->rnti, ra_type_str); nr_mac_trigger_ul_failure(sched_ctrl, UE->current_DL_BWP.scs); } @@ -2064,8 +2293,8 @@ static void nr_check_Msg4_Ack(module_id_t module_id, int CC_id, frame_t frame, s remove_nr_list(&sched_ctrl->retrans_dl_harq, current_harq_pid); } } else { - LOG_I(NR_MAC, "(UE %04x) Received Nack of RA-Msg4. Preparing retransmission!\n", ra->rnti); - ra->ra_state = nrRA_Msg4; + LOG_I(NR_MAC, "(UE %04x) Received Nack in %s, preparing retransmission!\n", ra->rnti, nrra_text[ra->ra_state]); + ra->ra_state = ra->ra_type == RA_4_STEP ? nrRA_Msg4 : nrRA_MsgB; } } } @@ -2218,7 +2447,7 @@ void nr_schedule_RA(module_id_t module_idP, LOG_D(NR_MAC, "RA[state:%d]\n", ra->ra_state); // Check RA Contention Resolution timer - if (ra->ra_state >= nrRA_WAIT_Msg3) { + if (ra->ra_type == RA_4_STEP && ra->ra_state >= nrRA_WAIT_Msg3) { ra->contention_resolution_timer--; if (ra->contention_resolution_timer < 0) { LOG_W(NR_MAC, "(%d.%d) RA Contention Resolution timer expired for UE 0x%04x, RA procedure failed...\n", frameP, slotP, ra->rnti); @@ -2237,10 +2466,11 @@ void nr_schedule_RA(module_id_t module_idP, nr_generate_Msg3_retransmission(module_idP, CC_id, frameP, slotP, ra, ul_dci_req); break; case nrRA_Msg4: - nr_generate_Msg4(module_idP, CC_id, frameP, slotP, ra, DL_req, TX_req); + case nrRA_MsgB: + nr_generate_Msg4_MsgB(module_idP, CC_id, frameP, slotP, ra, DL_req, TX_req); break; - case nrRA_WAIT_Msg4_ACK: - nr_check_Msg4_Ack(module_idP, CC_id, frameP, slotP, ra); + case nrRA_WAIT_Msg4_MsgB_ACK: + nr_check_Msg4_MsgB_Ack(module_idP, CC_id, frameP, slotP, ra); break; default: break; diff --git a/openair2/LAYER2/NR_MAC_gNB/gNB_scheduler_bch.c b/openair2/LAYER2/NR_MAC_gNB/gNB_scheduler_bch.c index 18ce58f2d4..60e3fb00a1 100644 --- a/openair2/LAYER2/NR_MAC_gNB/gNB_scheduler_bch.c +++ b/openair2/LAYER2/NR_MAC_gNB/gNB_scheduler_bch.c @@ -52,41 +52,43 @@ static void schedule_ssb(frame_t frame, NR_ServingCellConfigCommon_t *scc, nfapi_nr_dl_tti_request_body_t *dl_req, int i_ssb, + int beam_index, uint8_t scoffset, uint16_t offset_pointa, uint32_t payload) { - uint8_t beam_index = 0; - nfapi_nr_dl_tti_request_pdu_t *dl_config_pdu = &dl_req->dl_tti_pdu_list[dl_req->nPDUs]; - memset((void *) dl_config_pdu, 0,sizeof(nfapi_nr_dl_tti_request_pdu_t)); - dl_config_pdu->PDUType = NFAPI_NR_DL_TTI_SSB_PDU_TYPE; - dl_config_pdu->PDUSize =2 + sizeof(nfapi_nr_dl_tti_ssb_pdu_rel15_t); + nfapi_nr_dl_tti_request_pdu_t *dl_config_pdu = &dl_req->dl_tti_pdu_list[dl_req->nPDUs]; + memset((void *) dl_config_pdu, 0, sizeof(nfapi_nr_dl_tti_request_pdu_t)); + dl_config_pdu->PDUType = NFAPI_NR_DL_TTI_SSB_PDU_TYPE; + dl_config_pdu->PDUSize = 2 + sizeof(nfapi_nr_dl_tti_ssb_pdu_rel15_t); - AssertFatal(scc->physCellId!=NULL,"ServingCellConfigCommon->physCellId is null\n"); - AssertFatal(*scc->physCellId < 1008 && *scc->physCellId >=0, "5G physicall cell id out of range: %ld\n", *scc->physCellId); - dl_config_pdu->ssb_pdu.ssb_pdu_rel15.PhysCellId = *scc->physCellId; - dl_config_pdu->ssb_pdu.ssb_pdu_rel15.BetaPss = 0; - dl_config_pdu->ssb_pdu.ssb_pdu_rel15.SsbBlockIndex = i_ssb; - AssertFatal(scc->downlinkConfigCommon!=NULL,"scc->downlinkConfigCommonL is null\n"); - AssertFatal(scc->downlinkConfigCommon->frequencyInfoDL!=NULL,"scc->downlinkConfigCommon->frequencyInfoDL is null\n"); - AssertFatal(scc->downlinkConfigCommon->frequencyInfoDL->absoluteFrequencySSB!=NULL,"scc->downlinkConfigCommon->frequencyInfoDL->absoluteFrequencySSB is null\n"); - AssertFatal(scc->downlinkConfigCommon->frequencyInfoDL->frequencyBandList.list.count==1,"Frequency Band list does not have 1 element (%d)\n", + AssertFatal(scc->physCellId != NULL,"ServingCellConfigCommon->physCellId is null\n"); + AssertFatal(*scc->physCellId < 1008 && *scc->physCellId >=0, "5G physicall cell id out of range: %ld\n", *scc->physCellId); + dl_config_pdu->ssb_pdu.ssb_pdu_rel15.PhysCellId = *scc->physCellId; + dl_config_pdu->ssb_pdu.ssb_pdu_rel15.BetaPss = 0; + dl_config_pdu->ssb_pdu.ssb_pdu_rel15.SsbBlockIndex = i_ssb; + AssertFatal(scc->downlinkConfigCommon,"scc->downlinkConfigCommonL is null\n"); + AssertFatal(scc->downlinkConfigCommon->frequencyInfoDL,"scc->downlinkConfigCommon->frequencyInfoDL is null\n"); + AssertFatal(scc->downlinkConfigCommon->frequencyInfoDL->absoluteFrequencySSB, + "scc->downlinkConfigCommon->frequencyInfoDL->absoluteFrequencySSB is null\n"); + AssertFatal(scc->downlinkConfigCommon->frequencyInfoDL->frequencyBandList.list.count == 1, + "Frequency Band list does not have 1 element (%d)\n", scc->downlinkConfigCommon->frequencyInfoDL->frequencyBandList.list.count); AssertFatal(scc->ssbSubcarrierSpacing,"ssbSubcarrierSpacing is null\n"); - AssertFatal(scc->downlinkConfigCommon->frequencyInfoDL->frequencyBandList.list.array[0],"band is null\n"); + AssertFatal(scc->downlinkConfigCommon->frequencyInfoDL->frequencyBandList.list.array[0], "band is null\n"); dl_config_pdu->ssb_pdu.ssb_pdu_rel15.SsbSubcarrierOffset = scoffset; //kSSB - dl_config_pdu->ssb_pdu.ssb_pdu_rel15.ssbOffsetPointA = offset_pointa; - dl_config_pdu->ssb_pdu.ssb_pdu_rel15.bchPayloadFlag = 1; - dl_config_pdu->ssb_pdu.ssb_pdu_rel15.bchPayload = payload; - dl_config_pdu->ssb_pdu.ssb_pdu_rel15.precoding_and_beamforming.num_prgs=1; - dl_config_pdu->ssb_pdu.ssb_pdu_rel15.precoding_and_beamforming.prg_size=275; //1 PRG of max size for analogue beamforming - dl_config_pdu->ssb_pdu.ssb_pdu_rel15.precoding_and_beamforming.dig_bf_interfaces=1; + dl_config_pdu->ssb_pdu.ssb_pdu_rel15.ssbOffsetPointA = offset_pointa; + dl_config_pdu->ssb_pdu.ssb_pdu_rel15.bchPayloadFlag = 1; + dl_config_pdu->ssb_pdu.ssb_pdu_rel15.bchPayload = payload; + dl_config_pdu->ssb_pdu.ssb_pdu_rel15.precoding_and_beamforming.num_prgs = 1; + dl_config_pdu->ssb_pdu.ssb_pdu_rel15.precoding_and_beamforming.prg_size = 275; //1 PRG of max size for analogue beamforming + dl_config_pdu->ssb_pdu.ssb_pdu_rel15.precoding_and_beamforming.dig_bf_interfaces = 1; dl_config_pdu->ssb_pdu.ssb_pdu_rel15.precoding_and_beamforming.prgs_list[0].pm_idx = 0; dl_config_pdu->ssb_pdu.ssb_pdu_rel15.precoding_and_beamforming.prgs_list[0].dig_bf_interface_list[0].beam_idx = beam_index; dl_req->nPDUs++; - LOG_D(MAC,"Scheduling ssb %d at frame %d and slot %d\n",i_ssb,frame,slot); + LOG_D(MAC,"Scheduling ssb %d at frame %d and slot %d\n", i_ssb, frame, slot); } static void fill_ssb_vrb_map(NR_COMMON_channels_t *cc, @@ -152,13 +154,12 @@ void schedule_nr_mib(module_id_t module_idP, frame_t frameP, sub_frame_t slotP, if (ssb_period > 1) // 0 is every half frame ssb_frame_periodicity = 1 << (ssb_period -1); - if (!(frameP%ssb_frame_periodicity) && - ((slotP<(slots_per_frame>>1)) || (ssb_period == 0))) { + if (!(frameP % ssb_frame_periodicity) && ((slotP < (slots_per_frame >> 1)) || (ssb_period == 0))) { // schedule SSB only for given frames according to SSB periodicity // and in first half frame unless periodicity of 5ms int rel_slot; if (ssb_period == 0) // scheduling every half frame - rel_slot = slotP%(slots_per_frame>>1); + rel_slot = slotP % (slots_per_frame >> 1); else rel_slot = slotP; @@ -171,21 +172,20 @@ void schedule_nr_mib(module_id_t module_idP, frame_t frameP, sub_frame_t slotP, const BIT_STRING_t *mediumBitmap = &scc->ssb_PositionsInBurst->choice.mediumBitmap; const BIT_STRING_t *longBitmap = &scc->ssb_PositionsInBurst->choice.longBitmap; - uint16_t ssb_start_symbol; const int n_slots_frame = nr_slots_per_frame[scs]; - switch (scc->ssb_PositionsInBurst->present) { case 1: // short bitmap (<3GHz) max 4 SSBs for (int i_ssb = 0; i_ssb < 4; i_ssb++) { if ((shortBitmap->buf[0] >> (7 - i_ssb)) & 0x01) { - ssb_start_symbol = get_ssb_start_symbol(band, scs, i_ssb); + uint16_t ssb_start_symbol = get_ssb_start_symbol(band, scs, i_ssb); // if start symbol is in current slot, schedule current SSB, fill VRB map and call get_type0_PDCCH_CSS_config_parameters - if ((ssb_start_symbol / 14) == rel_slot){ - NR_beam_alloc_t beam = beam_allocation_procedure(&gNB->beam_info, frameP, slotP, i_ssb, n_slots_frame); + if ((ssb_start_symbol / 14) == rel_slot) { + int beam_index = get_fapi_beamforming_index(gNB, i_ssb); + NR_beam_alloc_t beam = beam_allocation_procedure(&gNB->beam_info, frameP, slotP, beam_index, n_slots_frame); AssertFatal(beam.idx >= 0, "Cannot allocate SSB %d in any available beam\n", i_ssb); const int prb_offset = offset_pointa >> scs; - schedule_ssb(frameP, slotP, scc, dl_req, i_ssb, ssbSubcarrierOffset, offset_pointa, mib_pdu); + schedule_ssb(frameP, slotP, scc, dl_req, i_ssb, beam_index, ssbSubcarrierOffset, offset_pointa, mib_pdu); fill_ssb_vrb_map(cc, prb_offset, ssbSubcarrierOffset, ssb_start_symbol, CC_id, beam.idx); if (get_softmodem_params()->sa == 1) { get_type0_PDCCH_CSS_config_parameters(&gNB->type0_PDCCH_CSS_config[i_ssb], @@ -210,13 +210,14 @@ void schedule_nr_mib(module_id_t module_idP, frame_t frameP, sub_frame_t slotP, // medium bitmap (<6GHz) max 8 SSBs for (int i_ssb = 0; i_ssb < 8; i_ssb++) { if ((mediumBitmap->buf[0] >> (7 - i_ssb)) & 0x01) { - ssb_start_symbol = get_ssb_start_symbol(band, scs, i_ssb); + uint16_t ssb_start_symbol = get_ssb_start_symbol(band, scs, i_ssb); // if start symbol is in current slot, schedule current SSB, fill VRB map and call get_type0_PDCCH_CSS_config_parameters - if ((ssb_start_symbol / 14) == rel_slot){ - NR_beam_alloc_t beam = beam_allocation_procedure(&gNB->beam_info, frameP, slotP, i_ssb, n_slots_frame); + if ((ssb_start_symbol / 14) == rel_slot) { + int beam_index = get_fapi_beamforming_index(gNB, i_ssb); + NR_beam_alloc_t beam = beam_allocation_procedure(&gNB->beam_info, frameP, slotP, beam_index, n_slots_frame); AssertFatal(beam.idx >= 0, "Cannot allocate SSB %d in any available beam\n", i_ssb); const int prb_offset = offset_pointa >> scs; - schedule_ssb(frameP, slotP, scc, dl_req, i_ssb, ssbSubcarrierOffset, offset_pointa, mib_pdu); + schedule_ssb(frameP, slotP, scc, dl_req, i_ssb, beam_index, ssbSubcarrierOffset, offset_pointa, mib_pdu); fill_ssb_vrb_map(cc, prb_offset, ssbSubcarrierOffset, ssb_start_symbol, CC_id, beam.idx); if (get_softmodem_params()->sa == 1) { get_type0_PDCCH_CSS_config_parameters(&gNB->type0_PDCCH_CSS_config[i_ssb], @@ -241,13 +242,14 @@ void schedule_nr_mib(module_id_t module_idP, frame_t frameP, sub_frame_t slotP, // long bitmap FR2 max 64 SSBs for (int i_ssb = 0; i_ssb < 64; i_ssb++) { if ((longBitmap->buf[i_ssb / 8] >> (7 - (i_ssb % 8))) & 0x01) { - ssb_start_symbol = get_ssb_start_symbol(band, scs, i_ssb); + uint16_t ssb_start_symbol = get_ssb_start_symbol(band, scs, i_ssb); // if start symbol is in current slot, schedule current SSB, fill VRB map and call get_type0_PDCCH_CSS_config_parameters - if ((ssb_start_symbol / 14) == rel_slot){ - NR_beam_alloc_t beam = beam_allocation_procedure(&gNB->beam_info, frameP, slotP, i_ssb, n_slots_frame); + if ((ssb_start_symbol / 14) == rel_slot) { + int beam_index = get_fapi_beamforming_index(gNB, i_ssb); + NR_beam_alloc_t beam = beam_allocation_procedure(&gNB->beam_info, frameP, slotP, beam_index, n_slots_frame); AssertFatal(beam.idx >= 0, "Cannot allocate SSB %d in any available beam\n", i_ssb); const int prb_offset = offset_pointa >> (scs-2); // reference 60kHz - schedule_ssb(frameP, slotP, scc, dl_req, i_ssb, ssbSubcarrierOffset, offset_pointa, mib_pdu); + schedule_ssb(frameP, slotP, scc, dl_req, i_ssb, beam_index, ssbSubcarrierOffset, offset_pointa, mib_pdu); fill_ssb_vrb_map(cc, prb_offset, ssbSubcarrierOffset >> (scs - 2), ssb_start_symbol, CC_id, beam.idx); if (get_softmodem_params()->sa == 1) { get_type0_PDCCH_CSS_config_parameters(&gNB->type0_PDCCH_CSS_config[i_ssb], @@ -386,7 +388,7 @@ static uint32_t schedule_control_sib1(module_id_t module_id, pdsch->mcs = 0; // starting from mcs 0 gNB_mac->sched_ctrlCommon->num_total_bytes = num_total_bytes; - uint8_t nr_of_candidates; + uint8_t nr_of_candidates = 0; for (int i=0; i<3; i++) { find_aggregation_candidates(&gNB_mac->sched_ctrlCommon->aggregation_level, &nr_of_candidates, gNB_mac->sched_ctrlCommon->search_space,4<sched_pdsch : &sched_osi->sched_pdsch); @@ -526,11 +529,11 @@ static void nr_fill_nfapi_dl_SIB_pdu(int Mod_idP, dl_req->nPDUs += 1; nfapi_nr_dl_tti_pdsch_pdu_rel15_t *pdsch_pdu_rel15 = &dl_tti_pdsch_pdu->pdsch_pdu.pdsch_pdu_rel15; - pdsch_pdu_rel15->precodingAndBeamforming.num_prgs=0; - pdsch_pdu_rel15->precodingAndBeamforming.prg_size=0; - pdsch_pdu_rel15->precodingAndBeamforming.dig_bf_interfaces=0; + pdsch_pdu_rel15->precodingAndBeamforming.num_prgs = 0; + pdsch_pdu_rel15->precodingAndBeamforming.prg_size = 0; + pdsch_pdu_rel15->precodingAndBeamforming.dig_bf_interfaces = 1; pdsch_pdu_rel15->precodingAndBeamforming.prgs_list[0].pm_idx = 0; - pdsch_pdu_rel15->precodingAndBeamforming.prgs_list[0].dig_bf_interface_list[0].beam_idx = 0; + pdsch_pdu_rel15->precodingAndBeamforming.prgs_list[0].dig_bf_interface_list[0].beam_idx = beam_index; pdcch_pdu_rel15->CoreSetType = NFAPI_NR_CSET_CONFIG_MIB_SIB1; @@ -538,7 +541,7 @@ static void nr_fill_nfapi_dl_SIB_pdu(int Mod_idP, pdsch_pdu_rel15->rnti = SI_RNTI; pdsch_pdu_rel15->pduIndex = pdu_index; - pdsch_pdu_rel15->BWPSize = type0_PDCCH_CSS_config->num_rbs; + pdsch_pdu_rel15->BWPSize = type0_PDCCH_CSS_config->num_rbs; pdsch_pdu_rel15->BWPStart = type0_PDCCH_CSS_config->cset_start_rb; pdsch_pdu_rel15->SubcarrierSpacing = type0_PDCCH_CSS_config->scs_pdcch; @@ -592,6 +595,12 @@ static void nr_fill_nfapi_dl_SIB_pdu(int Mod_idP, dci_pdu->beta_PDCCH_1_0 = 0; dci_pdu->powerControlOffsetSS = 1; + dci_pdu->precodingAndBeamforming.num_prgs = 0; + dci_pdu->precodingAndBeamforming.prg_size = 0; + dci_pdu->precodingAndBeamforming.dig_bf_interfaces = 1; + dci_pdu->precodingAndBeamforming.prgs_list[0].pm_idx = 0; + dci_pdu->precodingAndBeamforming.prgs_list[0].dig_bf_interface_list[0].beam_idx = beam_index; + /* DCI payload */ dci_pdu_rel15_t dci_payload; memset(&dci_payload, 0, sizeof(dci_pdu_rel15_t)); @@ -692,7 +701,8 @@ void schedule_nr_sib1(module_id_t module_idP, (type0_PDCCH_CSS_config->active == true)) { const int n_slots_frame = nr_slots_per_frame[*scc->ssbSubcarrierSpacing]; - NR_beam_alloc_t beam = beam_allocation_procedure(&gNB_mac->beam_info, frameP, slotP, i, n_slots_frame); + int beam_index = get_fapi_beamforming_index(gNB_mac, i); + NR_beam_alloc_t beam = beam_allocation_procedure(&gNB_mac->beam_info, frameP, slotP, beam_index, n_slots_frame); AssertFatal(beam.idx >= 0, "Cannot allocate SIB1 corresponding to SSB %d in any available beam\n", i); LOG_D(NR_MAC,"(%d.%d) SIB1 transmission: ssb_index %d\n", frameP, slotP, type0_PDCCH_CSS_config->ssb_index); @@ -729,7 +739,8 @@ void schedule_nr_sib1(module_id_t module_idP, type0_PDCCH_CSS_config, TBS, tda_info.startSymbolIndex, - tda_info.nrOfSymbols); + tda_info.nrOfSymbols, + beam_index); const int ntx_req = TX_req->Number_of_PDUs; nfapi_nr_pdu_t *tx_req = &TX_req->pdu_list[ntx_req]; @@ -829,7 +840,7 @@ void schedule_nr_sib19(module_id_t module_idP, } const int window_length = 10; - for (int i=0; itype0_PDCCH_CSS_config[i]; if(((frameP - 1) % frame == 0) && @@ -837,7 +848,8 @@ void schedule_nr_sib19(module_id_t module_idP, (type0_PDCCH_CSS_config->num_rbs > 0)) { const int n_slots_frame = nr_slots_per_frame[*scc->ssbSubcarrierSpacing]; - NR_beam_alloc_t beam = beam_allocation_procedure(&gNB_mac->beam_info, frameP, slotP, i, n_slots_frame); + int beam_index = get_fapi_beamforming_index(gNB_mac, i); + NR_beam_alloc_t beam = beam_allocation_procedure(&gNB_mac->beam_info, frameP, slotP, beam_index, n_slots_frame); AssertFatal(beam.idx >= 0, "Cannot allocate SIB19 corresponding to SSB %d in any available beam\n", i); LOG_D(NR_MAC,"(%d.%d) SIB19 transmission: ssb_index %d\n", frameP, slotP, type0_PDCCH_CSS_config->ssb_index); @@ -873,7 +885,8 @@ void schedule_nr_sib19(module_id_t module_idP, type0_PDCCH_CSS_config, TBS, tda_info.startSymbolIndex, - tda_info.nrOfSymbols); + tda_info.nrOfSymbols, + beam_index); const int ntx_req = TX_req->Number_of_PDUs; nfapi_nr_pdu_t *tx_req = &TX_req->pdu_list[ntx_req]; @@ -901,4 +914,4 @@ void schedule_nr_sib19(module_id_t module_idP, T_BUFFER(sib19_bcch_pdu, sib19_bcch_length)); } } -} \ No newline at end of file +} diff --git a/openair2/LAYER2/NR_MAC_gNB/gNB_scheduler_dlsch.c b/openair2/LAYER2/NR_MAC_gNB/gNB_scheduler_dlsch.c index 1307df70ac..adf3faf227 100644 --- a/openair2/LAYER2/NR_MAC_gNB/gNB_scheduler_dlsch.c +++ b/openair2/LAYER2/NR_MAC_gNB/gNB_scheduler_dlsch.c @@ -627,7 +627,7 @@ static void pf_dl(module_id_t module_id, /* Loop UE_info->list to check retransmission */ UE_iterator(UE_list, UE) { - if (UE->Msg4_ACKed != true) + if (!UE->Msg4_MsgB_ACKed) continue; NR_UE_sched_ctrl_t *sched_ctrl = &UE->UE_sched_ctrl; @@ -1136,7 +1136,7 @@ void nr_schedule_ue_spec(module_id_t module_id, pdsch_pdu->precodingAndBeamforming.prg_size = pdsch_pdu->rbSize; pdsch_pdu->precodingAndBeamforming.dig_bf_interfaces = 0; pdsch_pdu->precodingAndBeamforming.prgs_list[0].pm_idx = sched_pdsch->pm_index; - pdsch_pdu->precodingAndBeamforming.prgs_list[0].dig_bf_interface_list[0].beam_idx = 0; + pdsch_pdu->precodingAndBeamforming.prgs_list[0].dig_bf_interface_list[0].beam_idx = UE->UE_beam_index; // TBS_LBRM according to section 5.4.2.1 of 38.212 // TODO: verify the case where maxMIMO_Layers is NULL, in which case // in principle maxMIMO_layers should be given by the maximum number of layers @@ -1196,7 +1196,7 @@ void nr_schedule_ue_spec(module_id_t module_id, dci_pdu->precodingAndBeamforming.prg_size = 0; dci_pdu->precodingAndBeamforming.dig_bf_interfaces = 0; dci_pdu->precodingAndBeamforming.prgs_list[0].pm_idx = 0; - dci_pdu->precodingAndBeamforming.prgs_list[0].dig_bf_interface_list[0].beam_idx = 0; + dci_pdu->precodingAndBeamforming.prgs_list[0].dig_bf_interface_list[0].beam_idx = UE->UE_beam_index; /* DCI payload */ dci_pdu_rel15_t dci_payload; diff --git a/openair2/LAYER2/NR_MAC_gNB/gNB_scheduler_primitives.c b/openair2/LAYER2/NR_MAC_gNB/gNB_scheduler_primitives.c index 4cf6da7433..834e42d7a3 100644 --- a/openair2/LAYER2/NR_MAC_gNB/gNB_scheduler_primitives.c +++ b/openair2/LAYER2/NR_MAC_gNB/gNB_scheduler_primitives.c @@ -797,10 +797,12 @@ void config_uldci(const NR_UE_ServingCell_Info_t *sc_info, dci_pdu_rel15->rv = pusch_pdu->pusch_data.rv_index; dci_pdu_rel15->harq_pid.val = pusch_pdu->pusch_data.harq_process_id; dci_pdu_rel15->tpc = tpc; - NR_PUSCH_Config_t *pusch_Config = ul_bwp->pusch_Config; - if (pusch_Config) AssertFatal(pusch_Config->resourceAllocation == NR_PUSCH_Config__resourceAllocation_resourceAllocationType1, - "Only frequency resource allocation type 1 is currently supported\n"); + NR_PUSCH_Config_t *pusch_Config = ul_bwp->pusch_Config; + if (pusch_Config) + AssertFatal(pusch_Config->resourceAllocation == NR_PUSCH_Config__resourceAllocation_resourceAllocationType1, + "Only frequency resource allocation type 1 is currently supported\n"); + switch (dci_format) { case NR_UL_DCI_FORMAT_0_0: dci_pdu_rel15->format_indicator = 0; @@ -1126,18 +1128,7 @@ void nr_configure_pucch(nfapi_nr_pucch_pdu_t *pucch_pdu, pucch_pdu->beamforming.num_prgs = 0; pucch_pdu->beamforming.prg_size = 0; // pucch_pdu->prb_size; pucch_pdu->beamforming.dig_bf_interface = 0; - if (pucch_pdu->beamforming.num_prgs > 0) { - if (pucch_pdu->beamforming.prgs_list == NULL) { - pucch_pdu->beamforming.prgs_list = calloc(pucch_pdu->beamforming.num_prgs, sizeof(*pucch_pdu->beamforming.prgs_list)); - } - if (pucch_pdu->beamforming.dig_bf_interface > 0) { - if (pucch_pdu->beamforming.prgs_list[0].dig_bf_interface_list == NULL) { - pucch_pdu->beamforming.prgs_list[0].dig_bf_interface_list = - calloc(pucch_pdu->beamforming.dig_bf_interface, sizeof(*pucch_pdu->beamforming.prgs_list[0].dig_bf_interface_list)); - } - } - pucch_pdu->beamforming.prgs_list[0].dig_bf_interface_list[0].beam_idx = 0; - } + pucch_pdu->beamforming.prgs_list[0].dig_bf_interface_list[0].beam_idx = UE->UE_beam_index; } void set_r_pucch_parms(int rsetindex, @@ -2423,12 +2414,14 @@ void configure_UE_BWP(gNB_MAC_INST *nr_mac, AssertFatal(ra->ra_ss!=NULL,"SearchSpace cannot be null for RA\n"); ra->coreset = get_coreset(nr_mac, scc, dl_bwp, ra->ra_ss, NR_SearchSpace__searchSpaceType_PR_common); + NR_COMMON_channels_t *cc = &nr_mac->common_channels[0]; + int ssb_index = cc->ssb_index[ra->beam_id]; ra->sched_pdcch = set_pdcch_structure(nr_mac, ra->ra_ss, ra->coreset, scc, &dl_genericParameters, - &nr_mac->type0_PDCCH_CSS_config[ra->beam_id]); + &nr_mac->type0_PDCCH_CSS_config[ssb_index]); UL_BWP->dci_format = NR_UL_DCI_FORMAT_0_0; DL_BWP->dci_format = NR_DL_DCI_FORMAT_1_0; @@ -2476,10 +2469,7 @@ NR_UE_info_t *add_new_nr_ue(gNB_MAC_INST *nr_mac, rnti_t rntiP, NR_CellGroupConf UE->uid = uid_linear_allocator_new(&UE_info->uid_allocator); UE->CellGroup = CellGroup; - if (CellGroup) - UE->Msg4_ACKed = true; - else - UE->Msg4_ACKed = false; + UE->Msg4_MsgB_ACKed = CellGroup != NULL; NR_UE_sched_ctrl_t *sched_ctrl = &UE->UE_sched_ctrl; memset(sched_ctrl, 0, sizeof(*sched_ctrl)); @@ -3114,6 +3104,44 @@ void UL_tti_req_ahead_initialization(gNB_MAC_INST *gNB, int n, int CCid, frame_t } } +int get_fapi_beamforming_index(gNB_MAC_INST *mac, int ssb_idx) +{ + int beam_idx = mac->fapi_beam_index[ssb_idx]; + AssertFatal(beam_idx >= 0, "Invalid beamforming index %d\n", beam_idx); + return beam_idx; +} + +// TODO this is a placeholder for a possibly more complex function +// for now the fapi beam index is the number of SSBs transmitted before ssb_index i +void fapi_beam_index_allocation(NR_ServingCellConfigCommon_t *scc, gNB_MAC_INST *mac) +{ + int len = 0; + uint8_t* buf = NULL; + switch (scc->ssb_PositionsInBurst->present) { + case NR_ServingCellConfigCommon__ssb_PositionsInBurst_PR_shortBitmap: + len = 4; + buf = scc->ssb_PositionsInBurst->choice.shortBitmap.buf; + break; + case NR_ServingCellConfigCommon__ssb_PositionsInBurst_PR_mediumBitmap: + len = 8; + buf = scc->ssb_PositionsInBurst->choice.mediumBitmap.buf; + break; + case NR_ServingCellConfigCommon__ssb_PositionsInBurst_PR_longBitmap: + len = 64; + buf = scc->ssb_PositionsInBurst->choice.longBitmap.buf; + break; + default : + AssertFatal(false, "Invalid configuration\n"); + } + int fapi_index = 0; + for (int i = 0; i < len; ++i) { + if ((buf[i / 8] >> (7 - i % 8)) & 0x1) + mac->fapi_beam_index[i] = fapi_index++; + else + mac->fapi_beam_index[i] = -1; + } +} + static inline int get_beam_index(const NR_beam_info_t *beam_info, int frame, int slot, int beam_index, int slots_per_frame) { return ((frame * slots_per_frame + slot) / beam_info->beam_duration) % beam_info->beam_allocation_size; diff --git a/openair2/LAYER2/NR_MAC_gNB/gNB_scheduler_uci.c b/openair2/LAYER2/NR_MAC_gNB/gNB_scheduler_uci.c index bf33bfbac6..189f74a0ab 100644 --- a/openair2/LAYER2/NR_MAC_gNB/gNB_scheduler_uci.c +++ b/openair2/LAYER2/NR_MAC_gNB/gNB_scheduler_uci.c @@ -1041,8 +1041,8 @@ void handle_nr_uci_pucch_0_1(module_id_t mod_id, remove_front_nr_list(&sched_ctrl->feedback_dl_harq); LOG_D(NR_MAC,"%4d.%2d bit %d pid %d ack/nack %d\n",frame, slot, harq_bit,pid,harq_value); handle_dl_harq(UE, pid, harq_value == 0 && harq_confidence == 0, nrmac->dl_bler.harq_round_max); - if (!UE->Msg4_ACKed && harq_value == 0 && harq_confidence == 0) - UE->Msg4_ACKed = true; + if (!UE->Msg4_MsgB_ACKed && harq_value == 0 && harq_confidence == 0) + UE->Msg4_MsgB_ACKed = true; if (harq_confidence == 1) UE->mac_stats.pucch0_DTX++; } diff --git a/openair2/LAYER2/NR_MAC_gNB/gNB_scheduler_ulsch.c b/openair2/LAYER2/NR_MAC_gNB/gNB_scheduler_ulsch.c index cb233eae1b..319d8fec67 100644 --- a/openair2/LAYER2/NR_MAC_gNB/gNB_scheduler_ulsch.c +++ b/openair2/LAYER2/NR_MAC_gNB/gNB_scheduler_ulsch.c @@ -596,7 +596,7 @@ void handle_nr_ul_harq(const int CC_idP, } } NR_SCHED_UNLOCK(&nrmac->sched_lock); - LOG_E(NR_MAC, "no RA proc for RNTI 0x%04x in Msg3/PUSCH\n", crc_pdu->rnti); + LOG_D(NR_MAC, "no RA proc for RNTI 0x%04x in Msg3/MsgA-PUSCH\n", crc_pdu->rnti); return; } if (nrmac->radio_config.disable_harq) { @@ -819,7 +819,7 @@ static void _nr_rx_sdu(const module_id_t gnb_mod_idP, * it. */ for (int i = 0; i < NR_NB_RA_PROC_MAX; ++i) { NR_RA_t *ra = &gNB_mac->common_channels[CC_idP].ra[i]; - if (ra->ra_state != nrRA_WAIT_Msg3) + if (ra->ra_type == RA_4_STEP && ra->ra_state != nrRA_WAIT_Msg3) continue; if (no_sig) { @@ -827,22 +827,29 @@ static void _nr_rx_sdu(const module_id_t gnb_mod_idP, handle_msg3_failed_rx(ra, i, gNB_mac->ul_bler.harq_round_max); continue; } - - // random access pusch with TC-RNTI - if (ra->rnti != current_rnti) { - LOG_D(NR_MAC, "expected TC_RNTI %04x to match current RNTI %04x\n", ra->rnti, current_rnti); - - if ((frameP == ra->Msg3_frame) && (slotP == ra->Msg3_slot)) { - LOG_W(NR_MAC, - "Random Access %i failed at state %s (TC_RNTI %04x RNTI %04x)\n", - i, - nrra_text[ra->ra_state], - ra->rnti, - current_rnti); - nr_clear_ra_proc(ra); + if (ra->ra_type == RA_2_STEP) { + // random access pusch with RA-RNTI + if (ra->RA_rnti != current_rnti) { + LOG_E(NR_MAC, "expected TC_RNTI %04x to match current RNTI %04x\n", ra->RA_rnti, current_rnti); + continue; } + } else { + // random access pusch with TC-RNTI + if (ra->rnti != current_rnti) { + LOG_E(NR_MAC, "expected TC_RNTI %04x to match current RNTI %04x\n", ra->rnti, current_rnti); - continue; + if ((frameP == ra->Msg3_frame) && (slotP == ra->Msg3_slot)) { + LOG_W(NR_MAC, + "Random Access %i failed at state %s (TC_RNTI %04x RNTI %04x)\n", + i, + nrra_text[ra->ra_state], + ra->rnti, + current_rnti); + nr_clear_ra_proc(ra); + } + + continue; + } } UE = UE ? UE : add_new_nr_ue(gNB_mac, ra->rnti, ra->CellGroup); @@ -882,7 +889,7 @@ static void _nr_rx_sdu(const module_id_t gnb_mod_idP, process_addmod_bearers_cellGroupConfig(&UE->UE_sched_ctrl, ra->CellGroup->rlc_BearerToAddModList); nr_clear_ra_proc(ra); } else { - LOG_D(NR_MAC, "[RAPROC] Received Msg3:\n"); + LOG_D(NR_MAC, "[RAPROC] Received %s:\n", ra->ra_type == RA_2_STEP ? "MsgA-PUSCH" : "Msg3"); for (uint32_t k = 0; k < sdu_lenP; k++) { LOG_D(NR_MAC, "(%i): 0x%x\n", k, sduP[k]); } @@ -914,7 +921,7 @@ static void _nr_rx_sdu(const module_id_t gnb_mod_idP, // The UE identified by C-RNTI still exists at the gNB // Reset Msg4_ACKed to not schedule ULSCH and DLSCH before RRC Reconfiguration - UE->Msg4_ACKed = false; + UE->Msg4_MsgB_ACKed = false; nr_mac_reset_ul_failure(&UE->UE_sched_ctrl); // Reset HARQ processes reset_dl_harq_list(&UE->UE_sched_ctrl); @@ -949,8 +956,13 @@ static void _nr_rx_sdu(const module_id_t gnb_mod_idP, // the function is only called to decode the contention resolution sub-header nr_process_mac_pdu(gnb_mod_idP, UE, CC_idP, frameP, slotP, sduP, sdu_lenP, -1); - LOG_I(NR_MAC, "Activating scheduling RA-Msg4 for TC_RNTI 0x%04x (state %s)\n", ra->rnti, nrra_text[ra->ra_state]); - ra->ra_state = nrRA_Msg4; + LOG_I(NR_MAC, + "Activating scheduling %s for TC_RNTI 0x%04x (state %s)\n", + ra->ra_type == RA_2_STEP ? "MsgB" : "Msg4", + ra->rnti, + nrra_text[ra->ra_state]); + ra->ra_state = ra->ra_type == RA_2_STEP ? nrRA_MsgB : nrRA_Msg4; + LOG_D(NR_MAC, "TC_RNTI 0x%04x next RA state %s\n", ra->rnti, nrra_text[ra->ra_state]); return; } } @@ -1754,7 +1766,7 @@ static bool allocate_ul_retransmission(gNB_MAC_INST *nrmac, return true; } -uint32_t ul_pf_tbs[3][29]; // pre-computed, approximate TBS values for PF coefficient +uint32_t ul_pf_tbs[5][29]; // pre-computed, approximate TBS values for PF coefficient typedef struct UEsched_s { float coef; NR_UE_info_t * UE; @@ -1787,7 +1799,7 @@ static void pf_ul(module_id_t module_id, UE_iterator(UE_list, UE) { NR_UE_sched_ctrl_t *sched_ctrl = &UE->UE_sched_ctrl; - if (UE->Msg4_ACKed != true || sched_ctrl->ul_failure) + if (!UE->Msg4_MsgB_ACKed || sched_ctrl->ul_failure) continue; LOG_D(NR_MAC,"pf_ul: preparing UL scheduling for UE %04x\n",UE->rnti); @@ -2221,11 +2233,11 @@ nr_pp_impl_ul nr_init_fr1_ulsch_preprocessor(int CC_id) * which should approximately(!) give us the TBsize. In particular, the * number of symbols, the number of DMRS symbols, and the exact Qm and R, are * not correct*/ - for (int mcsTableIdx = 0; mcsTableIdx < 3; ++mcsTableIdx) { + for (int mcsTableIdx = 0; mcsTableIdx < 5; ++mcsTableIdx) { for (int mcs = 0; mcs < 29; ++mcs) { - if (mcs > 27 && mcsTableIdx == 1) + if (mcs > 27 && (mcsTableIdx == 1 || mcsTableIdx == 3 || mcsTableIdx == 4)) continue; - const uint8_t Qm = nr_get_Qm_dl(mcs, mcsTableIdx); + const uint8_t Qm = nr_get_Qm_ul(mcs, mcsTableIdx); const uint16_t R = nr_get_code_rate_ul(mcs, mcsTableIdx); /* note: we do not update R/Qm based on low MCS or pi2BPSK */ ul_pf_tbs[mcsTableIdx][mcs] = nr_compute_tbs(Qm, @@ -2483,6 +2495,12 @@ void nr_schedule_ulsch(module_id_t module_id, frame_t frame, sub_frame_t slot, n pusch_pdu->pusch_data.tb_size = sched_pusch->tb_size; pusch_pdu->pusch_data.num_cb = 0; //CBG not supported + // Beamforming + pusch_pdu->beamforming.num_prgs = 0; + pusch_pdu->beamforming.prg_size = 0; // bwp_size; + pusch_pdu->beamforming.dig_bf_interface = 1; + pusch_pdu->beamforming.prgs_list[0].dig_bf_interface_list[0].beam_idx = UE->UE_beam_index; + pusch_pdu->maintenance_parms_v3.ldpcBaseGraph = get_BG(sched_pusch->tb_size<<3,sched_pusch->R); // Calacualte the normalized tx_power for PHR @@ -2584,6 +2602,11 @@ void nr_schedule_ulsch(module_id_t module_id, frame_t frame, sub_frame_t slot, n dci_pdu->CceIndex = sched_ctrl->cce_index; dci_pdu->beta_PDCCH_1_0 = 0; dci_pdu->powerControlOffsetSS = 1; + dci_pdu->precodingAndBeamforming.num_prgs = 0; + dci_pdu->precodingAndBeamforming.prg_size = 0; + dci_pdu->precodingAndBeamforming.dig_bf_interfaces = 1; + dci_pdu->precodingAndBeamforming.prgs_list[0].pm_idx = 0; + dci_pdu->precodingAndBeamforming.prgs_list[0].dig_bf_interface_list[0].beam_idx = UE->UE_beam_index; dci_pdu_rel15_t uldci_payload; memset(&uldci_payload, 0, sizeof(uldci_payload)); diff --git a/openair2/LAYER2/NR_MAC_gNB/mac_proto.h b/openair2/LAYER2/NR_MAC_gNB/mac_proto.h index 756ddbb39e..da3b612561 100644 --- a/openair2/LAYER2/NR_MAC_gNB/mac_proto.h +++ b/openair2/LAYER2/NR_MAC_gNB/mac_proto.h @@ -439,6 +439,8 @@ int get_mcs_from_bler(const NR_bler_options_t *bler_options, int ul_buffer_index(int frame, int slot, int scs, int size); void UL_tti_req_ahead_initialization(gNB_MAC_INST *gNB, int n, int CCid, frame_t frameP, int slotP); +void fapi_beam_index_allocation(NR_ServingCellConfigCommon_t *scc, gNB_MAC_INST *mac); +int get_fapi_beamforming_index(gNB_MAC_INST *mac, int ssb_idx); NR_beam_alloc_t beam_allocation_procedure(NR_beam_info_t *beam_info, int frame, int slot, int beam_index, int slots_per_frame); void reset_beam_status(NR_beam_info_t *beam_info, int frame, int slot, int beam_index, int slots_per_frame, bool new_beam); diff --git a/openair2/LAYER2/NR_MAC_gNB/main.c b/openair2/LAYER2/NR_MAC_gNB/main.c index e8519a151a..1407a2cbb3 100644 --- a/openair2/LAYER2/NR_MAC_gNB/main.c +++ b/openair2/LAYER2/NR_MAC_gNB/main.c @@ -315,9 +315,6 @@ void mac_top_init_gNB(ngran_node_t node_type, du_init_f1_ue_data(); srand48(0); - - // triggers also PYH initialization in case we have L1 via FAPI - nr_mac_config_scc(RC.nrmac[0], scc, config); } void nr_mac_send_f1_setup_req(void) diff --git a/openair2/LAYER2/NR_MAC_gNB/nr_mac_gNB.h b/openair2/LAYER2/NR_MAC_gNB/nr_mac_gNB.h index 1306652033..aa07e8f474 100644 --- a/openair2/LAYER2/NR_MAC_gNB/nr_mac_gNB.h +++ b/openair2/LAYER2/NR_MAC_gNB/nr_mac_gNB.h @@ -100,7 +100,6 @@ #define MAX_NUM_OF_SSB 64 #define MAX_NUM_NR_PRACH_PREAMBLES 64 #define MIN_NUM_PRBS_TO_SCHEDULE 5 -#define MAX_NUM_BEAM_PERIODS 4 extern const uint8_t nr_rv_round_map[4]; @@ -114,16 +113,18 @@ typedef struct { } NR_list_t; typedef enum { - nrRA_gNB_IDLE = 0, - nrRA_Msg2 = 1, - nrRA_WAIT_Msg3 = 2, - nrRA_Msg3_retransmission = 3, - nrRA_Msg4 = 4, - nrRA_WAIT_Msg4_ACK = 5, + nrRA_gNB_IDLE, + nrRA_Msg2, + nrRA_WAIT_MsgA_PUSCH, + nrRA_WAIT_Msg3, + nrRA_Msg3_retransmission, + nrRA_Msg4, + nrRA_MsgB, + nrRA_WAIT_Msg4_MsgB_ACK, } RA_gNB_state_t; static const char *const nrra_text[] = - {"IDLE", "Msg2", "WAIT_Msg3", "Msg3_retransmission", "Msg3_dcch_dtch", "Msg4", "WAIT_Msg4_ACK"}; + {"IDLE", "Msg2", "WAIT_MsgA_PUSCH", "WAIT_Msg3", "Msg3_retransmission", "Msg3_dcch_dtch", "Msg4", "MsgB", "WAIT_Msg4_ACK"}; typedef struct { int idx; @@ -166,6 +167,9 @@ typedef struct nr_mac_config_t { nr_mac_timers_t timer_config; int num_dlharq; int num_ulharq; + /// beamforming weight matrix size + int nb_bfw[2]; + int32_t *bw_list; } nr_mac_config_t; typedef struct NR_preamble_ue { @@ -219,6 +223,8 @@ typedef struct { rnti_t rnti; /// RA RNTI allocated from received PRACH uint16_t RA_rnti; + /// MsgB RNTI allocated from received MsgA + uint16_t MsgB_rnti; /// Received UE Contention Resolution Identifier uint8_t cont_res_id[6]; /// Msg3 first RB @@ -247,6 +253,7 @@ typedef struct { /// Preambles for contention-free access NR_preamble_ue_t preambles; int contention_resolution_timer; + nr_ra_type_t ra_type; /// CFRA flag bool cfra; // BWP for RA @@ -753,7 +760,7 @@ typedef struct { NR_UE_NR_Capability_t *capability; // UE selected beam index uint8_t UE_beam_index; - bool Msg4_ACKed; + bool Msg4_MsgB_ACKed; float ul_thr_ue; float dl_thr_ue; long pdsch_HARQ_ACK_Codebook; @@ -792,6 +799,11 @@ typedef struct f1_config_t { uint32_t gnb_id; // associated gNB's ID, not used in DU itself } f1_config_t; +typedef struct { + char *nvipc_shm_prefix; + int8_t nvipc_poll_core; +} nvipc_params_t; + /*! \brief top level eNB MAC structure */ typedef struct gNB_MAC_INST_s { /// Ethernet parameters for northbound midhaul interface @@ -908,7 +920,7 @@ typedef struct gNB_MAC_INST_s { uint8_t min_grant_mcs; bool identity_pm; int precoding_matrix_size[NR_MAX_NB_LAYERS]; - + int fapi_beam_index[MAX_NUM_OF_SSB]; nr_mac_rrc_ul_if_t mac_rrc; f1_config_t f1_config; int16_t frame; diff --git a/openair2/LAYER2/PDCP_v10.1.0/pdcp_fifo.c b/openair2/LAYER2/PDCP_v10.1.0/pdcp_fifo.c index 5f54bf6f04..c86e44b607 100644 --- a/openair2/LAYER2/PDCP_v10.1.0/pdcp_fifo.c +++ b/openair2/LAYER2/PDCP_v10.1.0/pdcp_fifo.c @@ -776,7 +776,7 @@ void pdcp_fifo_read_input_sdus_frompc5s (const protocol_ctxt_t *const ctxt_pP) pc5s_header->destinationL2Id=destinationL2Id; } } /* end of !ctxt.enb_flag */ - + break; default: LOG_D(PDCP, "pc5s message type %d, unknown...\n", pc5s_header->traffic_type); break; diff --git a/openair2/M2AP/m2ap_MCE_interface_management.c b/openair2/M2AP/m2ap_MCE_interface_management.c index 9d45eac4a3..d6efcb105b 100644 --- a/openair2/M2AP/m2ap_MCE_interface_management.c +++ b/openair2/M2AP/m2ap_MCE_interface_management.c @@ -1376,7 +1376,7 @@ int MCE_handle_MBMS_SESSION_COUNTING_FAILURE(instance_t instance, module_id_t d /* mandatory */ /* c1. MCCH_Update_Time */ //long - ie=(M2AP_MbmsServiceCountingRequest_Ies_t *)calloc(1,sizeof(M2AP_MbmsSchedulingInformation_Ies_t)); + ie = calloc(1, sizeof(*ie)); ie->id = M2AP_ProtocolIE_ID_id_MCCH_Update_Time; ie->criticality = M2AP_Criticality_reject; ie->value.present = M2AP_MbmsServiceCountingRequest_Ies__value_PR_MCCH_Update_Time; @@ -1388,7 +1388,7 @@ int MCE_handle_MBMS_SESSION_COUNTING_FAILURE(instance_t instance, module_id_t d /* mandatory */ /* c1. MCE_MBMS_M2AP_ID (integer value) */ //long - ie = (M2AP_MbmsServiceCountingRequest_Ies_t *)calloc(1, sizeof(M2AP_MbmsServiceCountingRequest_Ies_t)); + ie = calloc(1, sizeof(*ie)); ie->id = M2AP_ProtocolIE_ID_id_MBSFN_Area_ID; ie->criticality = M2AP_Criticality_reject; ie->value.present = M2AP_MbmsServiceCountingRequest_Ies__value_PR_MBSFN_Area_ID; @@ -1397,7 +1397,7 @@ int MCE_handle_MBMS_SESSION_COUNTING_FAILURE(instance_t instance, module_id_t d /* mandatory */ /* c2. TMGI (integrer value) */ - ie = (M2AP_MbmsServiceCountingRequest_Ies_t *)calloc(1, sizeof(M2AP_MbmsServiceCountingRequest_Ies_t )); + ie = calloc(1, sizeof(*ie)); ie->id = M2AP_ProtocolIE_ID_id_MBMS_Counting_Request_Session; ie->criticality = M2AP_Criticality_reject; ie->value.present = M2AP_MbmsServiceCountingRequest_Ies__value_PR_MBMS_Counting_Request_Session; diff --git a/openair2/NR_PHY_INTERFACE/NR_IF_Module.c b/openair2/NR_PHY_INTERFACE/NR_IF_Module.c index 0cc456c322..2e4687a352 100644 --- a/openair2/NR_PHY_INTERFACE/NR_IF_Module.c +++ b/openair2/NR_PHY_INTERFACE/NR_IF_Module.c @@ -241,6 +241,8 @@ void handle_nr_srs(NR_UL_IND_t *UL_info) { const int num_srs = UL_info->srs_ind.number_of_pdus; nfapi_nr_srs_indication_pdu_t *srs_list = UL_info->srs_ind.pdu_list; + // from here + for (int i = 0; i < num_srs; i++) { nfapi_nr_srs_indication_pdu_t *srs_ind = &srs_list[i]; LOG_D(NR_PHY, "(%d.%d) UL_info->srs_ind.pdu_list[%d].rnti: 0x%04x\n", frame, slot, i, srs_ind->rnti); diff --git a/openair2/NR_UE_PHY_INTERFACE/NR_IF_Module.c b/openair2/NR_UE_PHY_INTERFACE/NR_IF_Module.c index 2da11f109c..c4faefa0fa 100644 --- a/openair2/NR_UE_PHY_INTERFACE/NR_IF_Module.c +++ b/openair2/NR_UE_PHY_INTERFACE/NR_IF_Module.c @@ -1127,7 +1127,7 @@ void update_harq_status(NR_UE_MAC_INST_t *mac, uint8_t harq_pid, uint8_t ack_nac LOG_D(PHY,"Updating harq_status for harq_id %d, ack/nak %d\n", harq_pid, current_harq->ack); // we can prepare feedback for MSG4 in advance if (mac->ra.ra_state == nrRA_WAIT_CONTENTION_RESOLUTION) - prepare_msg4_feedback(mac, harq_pid, ack_nack); + prepare_msg4_msgb_feedback(mac, harq_pid, ack_nack); else { current_harq->ack = ack_nack; current_harq->ack_received = true; diff --git a/openair2/NR_UE_PHY_INTERFACE/NR_IF_Module.h b/openair2/NR_UE_PHY_INTERFACE/NR_IF_Module.h index f82555f149..6654fc8bff 100644 --- a/openair2/NR_UE_PHY_INTERFACE/NR_IF_Module.h +++ b/openair2/NR_UE_PHY_INTERFACE/NR_IF_Module.h @@ -37,7 +37,6 @@ #include #include "fapi_nr_ue_interface.h" #include "openair2/PHY_INTERFACE/queue_t.h" -#include "nfapi_nr_interface_scf.h" #include "openair2/NR_PHY_INTERFACE/NR_IF_Module.h" #include "NR_Packet_Drop.h" #include "nfapi/open-nFAPI/nfapi/public_inc/sidelink_nr_ue_interface.h" diff --git a/openair2/NR_UE_PHY_INTERFACE/NR_Packet_Drop.h b/openair2/NR_UE_PHY_INTERFACE/NR_Packet_Drop.h index 02907f9940..dcc5710724 100644 --- a/openair2/NR_UE_PHY_INTERFACE/NR_Packet_Drop.h +++ b/openair2/NR_UE_PHY_INTERFACE/NR_Packet_Drop.h @@ -22,7 +22,6 @@ #define __NR_CHAN_MODEL_H__ #include "common/platform_types.h" -#include #include "openair2/NR_PHY_INTERFACE/NR_IF_Module.h" #define NR_NUM_MCS 29 diff --git a/openair2/RRC/NR/nr_rrc_config.c b/openair2/RRC/NR/nr_rrc_config.c index e3f310a4c9..201a0e84d4 100644 --- a/openair2/RRC/NR/nr_rrc_config.c +++ b/openair2/RRC/NR/nr_rrc_config.c @@ -71,6 +71,25 @@ static NR_SetupRelease_RACH_ConfigCommon_t *clone_rach_configcommon(const NR_Set return clone; } +static NR_SetupRelease_MsgA_ConfigCommon_r16_t *clone_msga_configcommon(const NR_SetupRelease_MsgA_ConfigCommon_r16_t *mcc) +{ + if (mcc == NULL || mcc->present == NR_SetupRelease_MsgA_ConfigCommon_r16_PR_NOTHING) + return NULL; + NR_SetupRelease_MsgA_ConfigCommon_r16_t *clone = calloc_or_fail(1, sizeof(*clone)); + clone->present = mcc->present; + if (clone->present == NR_SetupRelease_MsgA_ConfigCommon_r16_PR_release) + return clone; + uint8_t buf[1024]; + asn_enc_rval_t enc_rval = uper_encode_to_buffer(&asn_DEF_NR_MsgA_ConfigCommon_r16, NULL, mcc->choice.setup, buf, sizeof(buf)); + AssertFatal(enc_rval.encoded > 0 && enc_rval.encoded < sizeof(buf), + "could not clone NR_MsgA_ConfigCommon_r16: problem while encoding\n"); + asn_dec_rval_t dec_rval = + uper_decode(NULL, &asn_DEF_NR_MsgA_ConfigCommon_r16, (void **)&clone->choice.setup, buf, enc_rval.encoded, 0, 0); + AssertFatal(dec_rval.code == RC_OK && dec_rval.consumed == enc_rval.encoded, + "could not clone NR_MsgA_ConfigCommon_r16:: problem while decoding\n"); + return clone; +} + static NR_SetupRelease_PUSCH_ConfigCommon_t *clone_pusch_configcommon(const NR_SetupRelease_PUSCH_ConfigCommon_t *pcc) { if (pcc == NULL || pcc->present == NR_SetupRelease_PUSCH_ConfigCommon_PR_NOTHING) @@ -2351,6 +2370,17 @@ NR_BCCH_DL_SCH_Message_t *get_SIB1_NR(const NR_ServingCellConfigCommon_t *scc, UL->initialUplinkBWP.genericParameters = clone_generic_parameters(&scc->uplinkConfigCommon->initialUplinkBWP->genericParameters); UL->initialUplinkBWP.rach_ConfigCommon = clone_rach_configcommon(scc->uplinkConfigCommon->initialUplinkBWP->rach_ConfigCommon); + + if (scc->uplinkConfigCommon->initialUplinkBWP->ext1) { + NR_SetupRelease_MsgA_ConfigCommon_r16_t *msgA_configcommon = + clone_msga_configcommon(scc->uplinkConfigCommon->initialUplinkBWP->ext1->msgA_ConfigCommon_r16); + if (msgA_configcommon) { + // Add the struct ext1 + UL->initialUplinkBWP.ext1 = calloc(1, sizeof(*UL->initialUplinkBWP.ext1)); + UL->initialUplinkBWP.ext1->msgA_ConfigCommon_r16 = msgA_configcommon; + } + } + UL->initialUplinkBWP.pusch_ConfigCommon = clone_pusch_configcommon(scc->uplinkConfigCommon->initialUplinkBWP->pusch_ConfigCommon); free(UL->initialUplinkBWP.pusch_ConfigCommon->choice.setup->groupHoppingEnabledTransformPrecoding); UL->initialUplinkBWP.pusch_ConfigCommon->choice.setup->groupHoppingEnabledTransformPrecoding = NULL; diff --git a/openair2/RRC/NR_UE/rrc_sl_preconfig.c b/openair2/RRC/NR_UE/rrc_sl_preconfig.c index b5ae64b96e..212899f866 100644 --- a/openair2/RRC/NR_UE/rrc_sl_preconfig.c +++ b/openair2/RRC/NR_UE/rrc_sl_preconfig.c @@ -215,7 +215,7 @@ static void prepare_NR_SL_BWPConfigCommon(NR_SL_BWP_ConfigCommon_r16_t *sl_bwp, // Value can be between symbols 0 to 7 sl_bwp->sl_BWP_Generic_r16->sl_StartSymbol_r16 = calloc(1, sizeof(long)); - sl_bwp->sl_BWP_Generic_r16->sl_PSBCH_Config_r16 = calloc(1,sizeof(NR_SL_PSBCH_Config_r16_t)); + sl_bwp->sl_BWP_Generic_r16->sl_PSBCH_Config_r16 = calloc(1, sizeof(*sl_bwp->sl_BWP_Generic_r16->sl_PSBCH_Config_r16)); // PSBCH CONFIG contains PO and alpha for PSBCH powercontrol. sl_bwp->sl_BWP_Generic_r16->sl_PSBCH_Config_r16->present = NR_SetupRelease_SL_PSBCH_Config_r16_PR_release; diff --git a/radio/COMMON/common_lib.h b/radio/COMMON/common_lib.h index 80894c2a1d..272f376d50 100644 --- a/radio/COMMON/common_lib.h +++ b/radio/COMMON/common_lib.h @@ -174,6 +174,7 @@ typedef struct { } udp_ctx_t; typedef enum { + RU_GPIO_CONTROL_NONE, RU_GPIO_CONTROL_GENERIC, RU_GPIO_CONTROL_INTERDIGITAL, } gpio_control_t; @@ -336,11 +337,6 @@ typedef struct { uint8_t if_compress; } eth_params_t; -typedef struct { - char *nvipc_shm_prefix; - int8_t nvipc_poll_core; -} nvipc_params_t; - typedef struct { //! Tx buffer for if device, keep one per subframe now to allow multithreading void *tx[10]; diff --git a/radio/USRP/README.md b/radio/USRP/README.md index cd3f5f10ba..12fba9f9d5 100644 --- a/radio/USRP/README.md +++ b/radio/USRP/README.md @@ -84,8 +84,6 @@ RUs = ( max_pdschReferenceSignalPower = -27; max_rxgain = 75; eNB_instances = [0]; - ##beamforming 1x2 matrix: 1 layer x 2 antennas - bf_weights = [0x00007fff, 0x0000]; sdr_addrs = "addr0=192.168.10.2,addr1=192.168.20.2,clock_source=external,time_source=external" tx_subdev ="A:0 B:0" rx_subdev ="A:1 B:1" diff --git a/radio/USRP/usrp_lib.cpp b/radio/USRP/usrp_lib.cpp index 1c4efdacf8..34edcc9b8f 100644 --- a/radio/USRP/usrp_lib.cpp +++ b/radio/USRP/usrp_lib.cpp @@ -313,6 +313,8 @@ static int trx_usrp_start(openair0_device *device) { #endif switch (device->openair0_cfg->gpio_controller) { + case RU_GPIO_CONTROL_NONE: + break; case RU_GPIO_CONTROL_GENERIC: trx_usrp_start_generic_gpio(device, s); break; diff --git a/targets/PROJECTS/GENERIC-LTE-EPC/CONF/gnb.band66.tm1.106PRB.usrpn300.conf b/targets/PROJECTS/GENERIC-LTE-EPC/CONF/gnb.band66.tm1.106PRB.usrpn300.conf index 21fc46a549..32b0eb9658 100644 --- a/targets/PROJECTS/GENERIC-LTE-EPC/CONF/gnb.band66.tm1.106PRB.usrpn300.conf +++ b/targets/PROJECTS/GENERIC-LTE-EPC/CONF/gnb.band66.tm1.106PRB.usrpn300.conf @@ -200,14 +200,6 @@ RUs = ( max_pdschReferenceSignalPower = -27; max_rxgain = 75; eNB_instances = [0]; - ## beamforming 1x2 matrix: 1 layer x 2 antennas - bf_weights = [0x00007fff, 0x0000]; - ## beamforming 1x4 matrix: 1 layer x 4 antennas - #bf_weights = [0x00007fff, 0x0000,0x0000, 0x0000]; - ## beamforming 2x2 matrix: - #bf_weights = [0x00007fff, 0x00000000, 0x00000000, 0x00007fff]; - ## beamforming 4x4 matrix: - #bf_weights = [0x00007fff, 0x0000, 0x0000, 0x0000, 0x00000000, 0x00007fff, 0x0000, 0x0000, 0x0000, 0x0000, 0x00007fff, 0x0000, 0x0000, 0x0000, 0x0000, 0x00007fff]; sdr_addrs = "addr=192.168.10.2,mgmt_addr=192.168.10.2,second_addr=192.168.20.2"; clock_src = "external"; # if_freq = 3700000000L; diff --git a/targets/PROJECTS/GENERIC-LTE-EPC/CONF/gnb.band66.tm1.106PRB.usrpx300.conf b/targets/PROJECTS/GENERIC-LTE-EPC/CONF/gnb.band66.tm1.106PRB.usrpx300.conf index 9ed2e258ef..ff860ad7a1 100644 --- a/targets/PROJECTS/GENERIC-LTE-EPC/CONF/gnb.band66.tm1.106PRB.usrpx300.conf +++ b/targets/PROJECTS/GENERIC-LTE-EPC/CONF/gnb.band66.tm1.106PRB.usrpx300.conf @@ -187,14 +187,6 @@ RUs = ( max_pdschReferenceSignalPower = -27; max_rxgain = 114; eNB_instances = [0]; - ## beamforming 1x2 matrix: 1 layer x 2 antennas - bf_weights = [0x00007fff, 0x0000]; - ## beamforming 1x4 matrix: 1 layer x 4 antennas - #bf_weights = [0x00007fff, 0x0000,0x0000, 0x0000]; - ## beamforming 2x2 matrix: - #bf_weights = [0x00007fff, 0x00000000, 0x00000000, 0x00007fff]; - ## beamforming 4x4 matrix: - #bf_weights = [0x00007fff, 0x0000, 0x0000, 0x0000, 0x00000000, 0x00007fff, 0x0000, 0x0000, 0x0000, 0x0000, 0x00007fff, 0x0000, 0x0000, 0x0000, 0x0000, 0x00007fff]; sdr_addrs = "type=x300"; clock_src = "internal"; # if_freq = 3700000000L; diff --git a/targets/PROJECTS/GENERIC-LTE-EPC/CONF/gnb.band66.tm1.24PRB.usrpx300.conf b/targets/PROJECTS/GENERIC-LTE-EPC/CONF/gnb.band66.tm1.24PRB.usrpx300.conf index 4526aea13a..18cceef18b 100644 --- a/targets/PROJECTS/GENERIC-LTE-EPC/CONF/gnb.band66.tm1.24PRB.usrpx300.conf +++ b/targets/PROJECTS/GENERIC-LTE-EPC/CONF/gnb.band66.tm1.24PRB.usrpx300.conf @@ -187,14 +187,6 @@ RUs = ( max_pdschReferenceSignalPower = -27; max_rxgain = 114; eNB_instances = [0]; - ## beamforming 1x2 matrix: 1 layer x 2 antennas - bf_weights = [0x00007fff, 0x0000]; - ## beamforming 1x4 matrix: 1 layer x 4 antennas - #bf_weights = [0x00007fff, 0x0000,0x0000, 0x0000]; - ## beamforming 2x2 matrix: - #bf_weights = [0x00007fff, 0x00000000, 0x00000000, 0x00007fff]; - ## beamforming 4x4 matrix: - #bf_weights = [0x00007fff, 0x0000, 0x0000, 0x0000, 0x00000000, 0x00007fff, 0x0000, 0x0000, 0x0000, 0x0000, 0x00007fff, 0x0000, 0x0000, 0x0000, 0x0000, 0x00007fff]; sdr_addrs = "type=x300"; clock_src = "internal"; # if_freq = 3700000000L; diff --git a/targets/PROJECTS/GENERIC-LTE-EPC/CONF/gnb.band66.tm1.25PRB.usrpn300.conf b/targets/PROJECTS/GENERIC-LTE-EPC/CONF/gnb.band66.tm1.25PRB.usrpn300.conf index b60bd97b04..efdad8ef4f 100644 --- a/targets/PROJECTS/GENERIC-LTE-EPC/CONF/gnb.band66.tm1.25PRB.usrpn300.conf +++ b/targets/PROJECTS/GENERIC-LTE-EPC/CONF/gnb.band66.tm1.25PRB.usrpn300.conf @@ -185,14 +185,6 @@ RUs = ( max_pdschReferenceSignalPower = -27; max_rxgain = 50; eNB_instances = [0]; - ## beamforming 1x2 matrix: 1 layer x 2 antennas - bf_weights = [0x00007fff, 0x0000]; - ## beamforming 1x4 matrix: 1 layer x 4 antennas - #bf_weights = [0x00007fff, 0x0000,0x0000, 0x0000]; - ## beamforming 2x2 matrix: - #bf_weights = [0x00007fff, 0x00000000, 0x00000000, 0x00007fff]; - ## beamforming 4x4 matrix: - #bf_weights = [0x00007fff, 0x0000, 0x0000, 0x0000, 0x00000000, 0x00007fff, 0x0000, 0x0000, 0x0000, 0x0000, 0x00007fff, 0x0000, 0x0000, 0x0000, 0x0000, 0x00007fff]; sdr_addrs = "addr=192.168.10.2,mgmt_addr=192.168.10.2,second_addr=192.168.20.2"; clock_src = "external"; # if_freq = 3700000000L; diff --git a/targets/PROJECTS/GENERIC-LTE-EPC/CONF/gnb.band66.tm1.25PRB.usrpx300.conf b/targets/PROJECTS/GENERIC-LTE-EPC/CONF/gnb.band66.tm1.25PRB.usrpx300.conf index 8eac631208..886b213c19 100644 --- a/targets/PROJECTS/GENERIC-LTE-EPC/CONF/gnb.band66.tm1.25PRB.usrpx300.conf +++ b/targets/PROJECTS/GENERIC-LTE-EPC/CONF/gnb.band66.tm1.25PRB.usrpx300.conf @@ -185,14 +185,6 @@ RUs = ( max_pdschReferenceSignalPower = -27; max_rxgain = 114; eNB_instances = [0]; - ## beamforming 1x2 matrix: 1 layer x 2 antennas - bf_weights = [0x00007fff, 0x0000]; - ## beamforming 1x4 matrix: 1 layer x 4 antennas - #bf_weights = [0x00007fff, 0x0000,0x0000, 0x0000]; - ## beamforming 2x2 matrix: - #bf_weights = [0x00007fff, 0x00000000, 0x00000000, 0x00007fff]; - ## beamforming 4x4 matrix: - #bf_weights = [0x00007fff, 0x0000, 0x0000, 0x0000, 0x00000000, 0x00007fff, 0x0000, 0x0000, 0x0000, 0x0000, 0x00007fff, 0x0000, 0x0000, 0x0000, 0x0000, 0x00007fff]; sdr_addrs = "type=x300"; clock_src = "internal"; # if_freq = 3700000000L; diff --git a/targets/PROJECTS/GENERIC-LTE-EPC/CONF/gnb.band78.tm1.106PRB.PTRS.usrpx300.conf b/targets/PROJECTS/GENERIC-LTE-EPC/CONF/gnb.band78.tm1.106PRB.PTRS.usrpx300.conf index 777ce3b28a..142fb423a7 100644 --- a/targets/PROJECTS/GENERIC-LTE-EPC/CONF/gnb.band78.tm1.106PRB.PTRS.usrpx300.conf +++ b/targets/PROJECTS/GENERIC-LTE-EPC/CONF/gnb.band78.tm1.106PRB.PTRS.usrpx300.conf @@ -247,14 +247,6 @@ RUs = ( max_pdschReferenceSignalPower = -27; max_rxgain = 114; eNB_instances = [0]; - ## beamforming 1x2 matrix: 1 layer x 2 antennas - bf_weights = [0x00007fff, 0x0000]; - ## beamforming 1x4 matrix: 1 layer x 4 antennas - #bf_weights = [0x00007fff, 0x0000,0x0000, 0x0000]; - ## beamforming 2x2 matrix: - #bf_weights = [0x00007fff, 0x00000000, 0x00000000, 0x00007fff]; - ## beamforming 4x4 matrix: - #bf_weights = [0x00007fff, 0x0000, 0x0000, 0x0000, 0x00000000, 0x00007fff, 0x0000, 0x0000, 0x0000, 0x0000, 0x00007fff, 0x0000, 0x0000, 0x0000, 0x0000, 0x00007fff]; sdr_addrs = "type=x300"; clock_src = "external"; } diff --git a/targets/PROJECTS/GENERIC-LTE-EPC/CONF/gnb.band78.tm1.106PRB.usrpb210.conf b/targets/PROJECTS/GENERIC-LTE-EPC/CONF/gnb.band78.tm1.106PRB.usrpb210.conf index f6a32dce67..28130500d8 100644 --- a/targets/PROJECTS/GENERIC-LTE-EPC/CONF/gnb.band78.tm1.106PRB.usrpb210.conf +++ b/targets/PROJECTS/GENERIC-LTE-EPC/CONF/gnb.band78.tm1.106PRB.usrpb210.conf @@ -198,14 +198,6 @@ RUs = ( max_pdschReferenceSignalPower = -27; max_rxgain = 114; eNB_instances = [0]; - ## beamforming 1x2 matrix: 1 layer x 2 antennas - #bf_weights = [0x00007fff, 0x00007fff]; - ## beamforming 1x4 matrix: 1 layer x 4 antennas - #bf_weights = [0x00007fff, 0x0000,0x0000, 0x0000]; - ## beamforming 2x2 matrix: - #bf_weights = [0x00007fff, 0x00000000, 0x00000000, 0x00007fff]; - ## beamforming 4x4 matrix: - #bf_weights = [0x00007fff, 0x0000, 0x0000, 0x0000, 0x00000000, 0x00007fff, 0x0000, 0x0000, 0x0000, 0x0000, 0x00007fff, 0x0000, 0x0000, 0x0000, 0x0000, 0x00007fff]; sdr_addrs = "type=b200"; #clock_src = "external"; } diff --git a/targets/PROJECTS/GENERIC-LTE-EPC/CONF/gnb.band78.tm1.106PRB.usrpn300.conf b/targets/PROJECTS/GENERIC-LTE-EPC/CONF/gnb.band78.tm1.106PRB.usrpn300.conf index 4fe6b380ad..0de8ba8c09 100644 --- a/targets/PROJECTS/GENERIC-LTE-EPC/CONF/gnb.band78.tm1.106PRB.usrpn300.conf +++ b/targets/PROJECTS/GENERIC-LTE-EPC/CONF/gnb.band78.tm1.106PRB.usrpn300.conf @@ -197,16 +197,6 @@ RUs = ( max_pdschReferenceSignalPower = -27; max_rxgain = 50; eNB_instances = [0]; - ## beamforming 1x2 matrix: 1 layer x 2 antennas - #bf_weights = [0x00007fff, 0x00007fff]; - ## beamforming 1x4 matrix: 1 layer x 4 antennas - #bf_weights = [0x00007fff, 0x0000,0x0000, 0x0000]; - ## beamforming 2x2 matrix: - #bf_weights = [0x00007fff, 0x00000000, 0x00000000, 0x00007fff]; - ## beamforming 2x4 matrix: - #bf_weights = [0x00007fff, 0x0000, 0x0000, 0x0000, 0x0000, 0x00007fff, 0x0000, 0x0000]; - #beamforming 4x4 matrix: - bf_weights = [0x00007fff, 0x0000, 0x0000, 0x0000, 0x0000, 0x00007fff, 0x0000, 0x0000, 0x0000, 0x0000, 0x00007fff, 0x0000, 0x0000, 0x0000, 0x0000, 0x00007fff]; sdr_addrs = "addr=192.168.10.2,mgmt_addr=192.168.10.2,second_addr=192.168.20.2"; clock_src = "external"; } diff --git a/targets/PROJECTS/GENERIC-LTE-EPC/CONF/gnb.band78.tm1.106PRB.usrpx300.conf b/targets/PROJECTS/GENERIC-LTE-EPC/CONF/gnb.band78.tm1.106PRB.usrpx300.conf index fbf8ed8e3c..babe3f5d47 100644 --- a/targets/PROJECTS/GENERIC-LTE-EPC/CONF/gnb.band78.tm1.106PRB.usrpx300.conf +++ b/targets/PROJECTS/GENERIC-LTE-EPC/CONF/gnb.band78.tm1.106PRB.usrpx300.conf @@ -197,14 +197,6 @@ RUs = ( max_pdschReferenceSignalPower = -27; max_rxgain = 114; eNB_instances = [0]; - ##beamforming 1x2 matrix: 1 layer x 2 antennas - bf_weights = [0x00007fff, 0x0000]; - ##beamforming 1x4 matrix: 1 layer x 4 antennas - #bf_weights = [0x00007fff, 0x0000,0x0000, 0x0000]; - ## beamforming 2x2 matrix: - # bf_weights = [0x00007fff, 0x00000000, 0x00000000, 0x00007fff]; - ## beamforming 4x4 matrix: - #bf_weights = [0x00007fff, 0x0000, 0x0000, 0x0000, 0x00000000, 0x00007fff, 0x0000, 0x0000, 0x0000, 0x0000, 0x00007fff, 0x0000, 0x0000, 0x0000, 0x0000, 0x00007fff]; sdr_addrs = "type=x300"; clock_src = "external"; } diff --git a/targets/PROJECTS/GENERIC-LTE-EPC/CONF/gnb.band78.tm1.24PRB.usrpb210.conf b/targets/PROJECTS/GENERIC-LTE-EPC/CONF/gnb.band78.tm1.24PRB.usrpb210.conf index 025ae59c51..4aa5eb633c 100644 --- a/targets/PROJECTS/GENERIC-LTE-EPC/CONF/gnb.band78.tm1.24PRB.usrpb210.conf +++ b/targets/PROJECTS/GENERIC-LTE-EPC/CONF/gnb.band78.tm1.24PRB.usrpb210.conf @@ -198,14 +198,6 @@ RUs = ( max_pdschReferenceSignalPower = -27; max_rxgain = 75; eNB_instances = [0]; - ## beamforming 1x2 matrix: 1 layer x 2 antennas - bf_weights = [0x00007fff, 0x0000]; - ## beamforming 1x4 matrix: 1 layer x 4 antennas - #bf_weights = [0x00007fff, 0x0000,0x0000, 0x0000]; - ## beamforming 2x2 matrix: - #bf_weights = [0x00007fff, 0x00000000, 0x00000000, 0x00007fff]; - ## beamforming 4x4 matrix: - #bf_weights = [0x00007fff, 0x0000, 0x0000, 0x0000, 0x00000000, 0x00007fff, 0x0000, 0x0000, 0x0000, 0x0000, 0x00007fff, 0x0000, 0x0000, 0x0000, 0x0000, 0x00007fff]; sdr_addrs = "type=b200"; #"addr=192.168.18.207"; #"addr=192.168.10.2,mgmt_addr=192.168.10.2,second_addr=192.168.20.2"; diff --git a/targets/PROJECTS/GENERIC-LTE-EPC/CONF/gnb.band78.tm1.24PRB.usrpn300.conf b/targets/PROJECTS/GENERIC-LTE-EPC/CONF/gnb.band78.tm1.24PRB.usrpn300.conf index 9e350e9260..4dbaf377df 100644 --- a/targets/PROJECTS/GENERIC-LTE-EPC/CONF/gnb.band78.tm1.24PRB.usrpn300.conf +++ b/targets/PROJECTS/GENERIC-LTE-EPC/CONF/gnb.band78.tm1.24PRB.usrpn300.conf @@ -198,14 +198,6 @@ RUs = ( max_pdschReferenceSignalPower = -27; max_rxgain = 75; eNB_instances = [0]; - ## beamforming 1x2 matrix: 1 layer x 2 antennas - bf_weights = [0x00007fff, 0x0000]; - ## beamforming 1x4 matrix: 1 layer x 4 antennas - #bf_weights = [0x00007fff, 0x0000,0x0000, 0x0000]; - ## beamforming 2x2 matrix: - #bf_weights = [0x00007fff, 0x00000000, 0x00000000, 0x00007fff]; - ## beamforming 4x4 matrix: - #bf_weights = [0x00007fff, 0x0000, 0x0000, 0x0000, 0x00000000, 0x00007fff, 0x0000, 0x0000, 0x0000, 0x0000, 0x00007fff, 0x0000, 0x0000, 0x0000, 0x0000, 0x00007fff]; sdr_addrs = "addr=192.168.10.2,mgmt_addr=192.168.10.2,second_addr=192.168.20.2"; clock_src = "external"; } diff --git a/targets/PROJECTS/GENERIC-LTE-EPC/CONF/gnb.band78.tm1.24PRB.usrpx300.conf b/targets/PROJECTS/GENERIC-LTE-EPC/CONF/gnb.band78.tm1.24PRB.usrpx300.conf index 388a515d71..490b735f09 100644 --- a/targets/PROJECTS/GENERIC-LTE-EPC/CONF/gnb.band78.tm1.24PRB.usrpx300.conf +++ b/targets/PROJECTS/GENERIC-LTE-EPC/CONF/gnb.band78.tm1.24PRB.usrpx300.conf @@ -198,14 +198,6 @@ RUs = ( max_pdschReferenceSignalPower = -27; max_rxgain = 114; eNB_instances = [0]; - ## beamforming 1x2 matrix: 1 layer x 2 antennas - bf_weights = [0x00007fff, 0x0000]; - ## beamforming 1x4 matrix: 1 layer x 4 antennas - #bf_weights = [0x00007fff, 0x0000,0x0000, 0x0000]; - ## beamforming 2x2 matrix: - #bf_weights = [0x00007fff, 0x00000000, 0x00000000, 0x00007fff]; - ## beamforming 4x4 matrix: - #bf_weights = [0x00007fff, 0x0000, 0x0000, 0x0000, 0x00000000, 0x00007fff, 0x0000, 0x0000, 0x0000, 0x0000, 0x00007fff, 0x0000, 0x0000, 0x0000, 0x0000, 0x00007fff]; sdr_addrs = "type=x300"; clock_src = "external"; } diff --git a/targets/PROJECTS/GENERIC-LTE-EPC/CONF/testing_gnb_24PRB.conf b/targets/PROJECTS/GENERIC-LTE-EPC/CONF/testing_gnb_24PRB.conf index bbf21da8c2..53683cf3ba 100644 --- a/targets/PROJECTS/GENERIC-LTE-EPC/CONF/testing_gnb_24PRB.conf +++ b/targets/PROJECTS/GENERIC-LTE-EPC/CONF/testing_gnb_24PRB.conf @@ -211,14 +211,6 @@ RUs = ( max_pdschReferenceSignalPower = -27; max_rxgain = 114; eNB_instances = [0]; - ## beamforming 1x2 matrix: 1 layer x 2 antennas - bf_weights = [0x00007fff, 0x0000]; - ## beamforming 1x4 matrix: 1 layer x 4 antennas - #bf_weights = [0x00007fff, 0x0000,0x0000, 0x0000]; - ## beamforming 2x2 matrix: - #bf_weights = [0x00007fff, 0x00000000, 0x00000000, 0x00007fff]; - ## beamforming 4x4 matrix: - #bf_weights = [0x00007fff, 0x0000, 0x0000, 0x0000, 0x00000000, 0x00007fff, 0x0000, 0x0000, 0x0000, 0x0000, 0x00007fff, 0x0000, 0x0000, 0x0000, 0x0000, 0x00007fff]; clock_src = "external"; } ); diff --git a/targets/PROJECTS/GENERIC-NR-5GC/CONF/du_gnb.conf b/targets/PROJECTS/GENERIC-NR-5GC/CONF/du_gnb.conf index df1b63ae1f..b5fd259b9c 100644 --- a/targets/PROJECTS/GENERIC-NR-5GC/CONF/du_gnb.conf +++ b/targets/PROJECTS/GENERIC-NR-5GC/CONF/du_gnb.conf @@ -197,8 +197,6 @@ RUs = ( max_pdschReferenceSignalPower = -27; max_rxgain = 114; eNB_instances = [0]; - #beamforming 1x4 matrix: - bf_weights = [0x00007fff, 0x0000, 0x0000, 0x0000]; clock_src = "internal"; } ); diff --git a/targets/PROJECTS/GENERIC-NR-5GC/CONF/gNB_SA_40_2x2.conf b/targets/PROJECTS/GENERIC-NR-5GC/CONF/gNB_SA_40_2x2.conf index 1637250a17..7dc75f5873 100755 --- a/targets/PROJECTS/GENERIC-NR-5GC/CONF/gNB_SA_40_2x2.conf +++ b/targets/PROJECTS/GENERIC-NR-5GC/CONF/gNB_SA_40_2x2.conf @@ -251,15 +251,6 @@ RUs = ( max_pdschReferenceSignalPower = -27; max_rxgain = 75; eNB_instances = [0]; - ##beamforming 1x2 matrix: 1 layer x 2 antennas - bf_weights = [0x00007fff, 0x0000]; - ##beamforming 1x4 matrix: 1 layer x 4 antennas - #bf_weights = [0x00007fff, 0x0000,0x0000, 0x0000]; - ## beamforming 2x2 matrix: - # bf_weights = [0x00007fff, 0x00000000, 0x00000000, 0x00007fff]; - ## beamforming 4x4 matrix: - #bf_weights = [0x00007fff, 0x0000, 0x0000, 0x0000, 0x00000000, 0x00007fff, 0x0000, 0x0000, 0x0000, 0x0000, 0x00007fff, 0x0000, 0x0000, 0x0000, 0x0000, 0x00007fff]; - sdr_addrs = "addr=192.168.30.2,second_addr=192.168.50.2,clock_source=internal,time_source=internal" } ); diff --git a/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.band78.sa.fr1.106PRB.2x2.usrpn310.conf b/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.band78.sa.fr1.106PRB.2x2.usrpn310.conf index f1172c206b..66fca54e6c 100644 --- a/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.band78.sa.fr1.106PRB.2x2.usrpn310.conf +++ b/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.band78.sa.fr1.106PRB.2x2.usrpn310.conf @@ -233,15 +233,6 @@ RUs = ( max_pdschReferenceSignalPower = -27; max_rxgain = 75; eNB_instances = [0]; - ##beamforming 1x2 matrix: 1 layer x 2 antennas - bf_weights = [0x00007fff, 0x0000]; - ##beamforming 1x4 matrix: 1 layer x 4 antennas - #bf_weights = [0x00007fff, 0x0000,0x0000, 0x0000]; - ## beamforming 2x2 matrix: - # bf_weights = [0x00007fff, 0x00000000, 0x00000000, 0x00007fff]; - ## beamforming 4x4 matrix: - #bf_weights = [0x00007fff, 0x0000, 0x0000, 0x0000, 0x00000000, 0x00007fff, 0x0000, 0x0000, 0x0000, 0x0000, 0x00007fff, 0x0000, 0x0000, 0x0000, 0x0000, 0x00007fff]; - sf_extension = 0 sdr_addrs = "addr=192.168.82.52,second_addr=192.168.83.52,clock_source=internal,time_source=internal" } diff --git a/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.band78.sa.fr1.162PRB.2x2.usrpn310.conf b/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.band78.sa.fr1.162PRB.2x2.usrpn310.conf index dcefa5cb7e..a71fd9a896 100644 --- a/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.band78.sa.fr1.162PRB.2x2.usrpn310.conf +++ b/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.band78.sa.fr1.162PRB.2x2.usrpn310.conf @@ -237,14 +237,6 @@ RUs = ( max_pdschReferenceSignalPower = -27; max_rxgain = 75; eNB_instances = [0]; - ##beamforming 1x2 matrix: 1 layer x 2 antennas - bf_weights = [0x00007fff, 0x0000]; - ##beamforming 1x4 matrix: 1 layer x 4 antennas - #bf_weights = [0x00007fff, 0x0000,0x0000, 0x0000]; - ## beamforming 2x2 matrix: - # bf_weights = [0x00007fff, 0x00000000, 0x00000000, 0x00007fff]; - ## beamforming 4x4 matrix: - #bf_weights = [0x00007fff, 0x0000, 0x0000, 0x0000, 0x00000000, 0x00007fff, 0x0000, 0x0000, 0x0000, 0x0000, 0x00007fff, 0x0000, 0x0000, 0x0000, 0x0000, 0x00007fff]; sf_extension = 0 sdr_addrs = "addr=192.168.82.52,second_addr=192.168.83.52,clock_source=internal,time_source=internal" } diff --git a/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.band78.tm1.106PRB.usrpn300.gtp-itti.conf b/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.band78.tm1.106PRB.usrpn300.gtp-itti.conf index 897f30234e..7d95cf8a03 100644 --- a/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.band78.tm1.106PRB.usrpn300.gtp-itti.conf +++ b/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.band78.tm1.106PRB.usrpn300.gtp-itti.conf @@ -202,8 +202,6 @@ RUs = ( max_pdschReferenceSignalPower = -27; max_rxgain = 75; eNB_instances = [0]; - #beamforming 1x4 matrix: - bf_weights = [0x00007fff, 0x0000, 0x0000, 0x0000]; sdr_addrs = "addr=192.168.10.2,mgmt_addr=192.168.10.2,second_addr=192.168.20.2"; clock_src = "external"; } diff --git a/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band1.u0.52PRB.usrpb210.conf b/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band1.u0.52PRB.usrpb210.conf index 9e743e28a0..c5657670a8 100644 --- a/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band1.u0.52PRB.usrpb210.conf +++ b/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band1.u0.52PRB.usrpb210.conf @@ -198,8 +198,6 @@ RUs = ( max_pdschReferenceSignalPower = -27; max_rxgain = 114; eNB_instances = [0]; - #beamforming 1x4 matrix: - bf_weights = [0x00007fff, 0x0000, 0x0000, 0x0000]; clock_src = "internal"; } ); diff --git a/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band257.u3.32prb.usrpx410.conf b/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band257.u3.32prb.usrpx410.conf index e993aa1b8b..27f69605b2 100644 --- a/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band257.u3.32prb.usrpx410.conf +++ b/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band257.u3.32prb.usrpx410.conf @@ -207,8 +207,6 @@ RUs = ( max_rxgain = 60; eNB_instances = [0]; #if_freq = 2650000000L; - ##beamforming 1x2 matrix: 1 layer x 2 antennas - bf_weights = [0x00007fff, 0x0000]; #clock_src = "internal"; sdr_addrs = "mgmt_addr=192.168.10.2,addr=192.168.10.2,clock_source=internal,time_source=internal" } diff --git a/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band41.fr1.106PRB.usrpb210.conf b/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band41.fr1.106PRB.usrpb210.conf index 0bb51e8028..a8c6eca533 100644 --- a/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band41.fr1.106PRB.usrpb210.conf +++ b/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band41.fr1.106PRB.usrpb210.conf @@ -203,8 +203,6 @@ RUs = ( max_pdschReferenceSignalPower = -27; max_rxgain = 114; eNB_instances = [0]; - #beamforming 1x4 matrix: - bf_weights = [0x00007fff, 0x0000, 0x0000, 0x0000]; clock_src = "internal"; sl_ahead = 2; } diff --git a/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band41.fr1.52PRB.usrpb210.conf b/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band41.fr1.52PRB.usrpb210.conf index 5db8a178a3..9e6f84f37b 100644 --- a/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band41.fr1.52PRB.usrpb210.conf +++ b/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band41.fr1.52PRB.usrpb210.conf @@ -208,8 +208,6 @@ RUs = ( max_rxgain = 114; sf_extension = 0; eNB_instances = [0]; - #beamforming 1x4 matrix: - bf_weights = [0x00007fff, 0x0000, 0x0000, 0x0000]; clock_src = "internal"; } ); diff --git a/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band66.fr1.106PRB.usrpn300.conf b/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band66.fr1.106PRB.usrpn300.conf index 48c3f42af7..5690be2f0c 100644 --- a/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band66.fr1.106PRB.usrpn300.conf +++ b/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band66.fr1.106PRB.usrpn300.conf @@ -201,8 +201,6 @@ RUs = ( max_pdschReferenceSignalPower = -27; max_rxgain = 75; eNB_instances = [0]; - #beamforming 1x4 matrix: - bf_weights = [0x00007fff, 0x0000, 0x0000, 0x0000]; clock_src = "internal"; } ); diff --git a/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band66.fr1.106PRB.usrpx300.conf b/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band66.fr1.106PRB.usrpx300.conf index dc73b4bb00..af96da5b28 100644 --- a/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band66.fr1.106PRB.usrpx300.conf +++ b/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band66.fr1.106PRB.usrpx300.conf @@ -217,14 +217,6 @@ RUs = ( max_rxgain = 114; sf_extension = 0; eNB_instances = [0]; - ##beamforming 1x2 matrix: 1 layer x 2 antennas - bf_weights = [0x00007fff, 0x0000]; - ##beamforming 1x4 matrix: 1 layer x 4 antennas - #bf_weights = [0x00007fff, 0x0000,0x0000, 0x0000]; - ## beamforming 2x2 matrix: - # bf_weights = [0x00007fff, 0x00000000, 0x00000000, 0x00007fff]; - ## beamforming 4x4 matrix: - #bf_weights = [0x00007fff, 0x0000, 0x0000, 0x0000, 0x00000000, 0x00007fff, 0x0000, 0x0000, 0x0000, 0x0000, 0x00007fff, 0x0000, 0x0000, 0x0000, 0x0000, 0x00007fff]; sdr_addrs = "type=x300"; clock_src = "internal"; # if_freq = 3700000000L; diff --git a/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band66.fr1.24PRB.usrpx300.conf b/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band66.fr1.24PRB.usrpx300.conf index cb04c81ec7..8dd8985ca3 100644 --- a/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band66.fr1.24PRB.usrpx300.conf +++ b/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band66.fr1.24PRB.usrpx300.conf @@ -233,14 +233,6 @@ RUs = ( max_rxgain = 114; sf_extension = 0; eNB_instances = [0]; - ##beamforming 1x2 matrix: 1 layer x 2 antennas - bf_weights = [0x00007fff, 0x0000]; - ##beamforming 1x4 matrix: 1 layer x 4 antennas - #bf_weights = [0x00007fff, 0x0000,0x0000, 0x0000]; - ## beamforming 2x2 matrix: - # bf_weights = [0x00007fff, 0x00000000, 0x00000000, 0x00007fff]; - ## beamforming 4x4 matrix: - #bf_weights = [0x00007fff, 0x0000, 0x0000, 0x0000, 0x00000000, 0x00007fff, 0x0000, 0x0000, 0x0000, 0x0000, 0x00007fff, 0x0000, 0x0000, 0x0000, 0x0000, 0x00007fff]; sdr_addrs = "type=x300"; clock_src = "internal"; # if_freq = 3700000000L; diff --git a/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band66.fr1.25PRB.usrpx300.conf b/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band66.fr1.25PRB.usrpx300.conf index 4e3ddd7f4a..ebf9279bbd 100644 --- a/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band66.fr1.25PRB.usrpx300.conf +++ b/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band66.fr1.25PRB.usrpx300.conf @@ -240,14 +240,6 @@ RUs = ( max_rxgain = 114; sf_extension = 0; eNB_instances = [0]; - ##beamforming 1x2 matrix: 1 layer x 2 antennas - bf_weights = [0x00007fff, 0x0000]; - ##beamforming 1x4 matrix: 1 layer x 4 antennas - #bf_weights = [0x00007fff, 0x0000,0x0000, 0x0000]; - ## beamforming 2x2 matrix: - # bf_weights = [0x00007fff, 0x00000000, 0x00000000, 0x00007fff]; - ## beamforming 4x4 matrix: - #bf_weights = [0x00007fff, 0x0000, 0x0000, 0x0000, 0x00000000, 0x00007fff, 0x0000, 0x0000, 0x0000, 0x0000, 0x00007fff, 0x0000, 0x0000, 0x0000, 0x0000, 0x00007fff]; sdr_addrs = "type=x300"; clock_src = "internal"; # if_freq = 3700000000L; diff --git a/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band77.273prb.fhi72.4x4-vvdn.conf b/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band77.273prb.fhi72.4x4-vvdn.conf index 13101d561b..254f3cfe90 100644 --- a/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band77.273prb.fhi72.4x4-vvdn.conf +++ b/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band77.273prb.fhi72.4x4-vvdn.conf @@ -226,8 +226,6 @@ RUs = ( eNB_instances = [0]; ru_thread_core = 6; sl_ahead = 5; - ##beamforming 1x2 matrix: 1 layer x 2 antennas - bf_weights = [0x00007fff, 0x0000,0x00007fff, 0x0000]; clock_src = "internal"; tr_preference = "raw_if4p5"; # important: activate FHI7.2 do_precoding = 0; # needs to match O-RU configuration diff --git a/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band77.fr1.273PRB.2x2.usrpn300.conf b/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band77.fr1.273PRB.2x2.usrpn300.conf index 2aef056ca8..0cef16488b 100644 --- a/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band77.fr1.273PRB.2x2.usrpn300.conf +++ b/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band77.fr1.273PRB.2x2.usrpn300.conf @@ -200,8 +200,6 @@ RUs = ( max_pdschReferenceSignalPower = -27; max_rxgain = 75; eNB_instances = [0]; - ##beamforming 1x2 matrix: 1 layer x 2 antennas - bf_weights = [0x00007fff, 0x0000]; #clock_src = "internal"; sdr_addrs = "mgmt_addr=192.168.10.2,addr=192.168.10.2,clock_source=internal,time_source=internal" } diff --git a/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band77.fr1.273PRB.usrpx300.conf b/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band77.fr1.273PRB.usrpx300.conf index 74982cf3d0..f986b9ac44 100644 --- a/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band77.fr1.273PRB.usrpx300.conf +++ b/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band77.fr1.273PRB.usrpx300.conf @@ -200,8 +200,6 @@ RUs = ( max_pdschReferenceSignalPower = -27; max_rxgain = 75; eNB_instances = [0]; - ##beamforming 1x2 matrix: 1 layer x 2 antennas - bf_weights = [0x00007fff, 0x0000]; #clock_src = "internal"; sdr_addrs = "addr=192.168.30.2,second_addr=192.168.40.2,clock_source=internal,time_source=internal" } diff --git a/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band78.106PRB.usrpb210.RA_2-Step.conf b/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band78.106PRB.usrpb210.RA_2-Step.conf new file mode 100644 index 0000000000..45dbf2197f --- /dev/null +++ b/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band78.106PRB.usrpb210.RA_2-Step.conf @@ -0,0 +1,278 @@ +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; + + ////////// Physical parameters: + + do_CSIRS = 1; + do_SRS = 1; + + servingCellConfigCommon = ( + { + #spCellConfigCommon + + physCellId = 0; + +# downlinkConfigCommon + #frequencyInfoDL + # this is 3600 MHz + 43 PRBs@30kHz SCS (same as initial BWP) + absoluteFrequencySSB = 641280; + dl_frequencyBand = 78; + # this is 3600 MHz + dl_absoluteFrequencyPointA = 640008; + #scs-SpecificCarrierList + dl_offstToCarrier = 0; +# subcarrierSpacing +# 0=kHz15, 1=kHz30, 2=kHz60, 3=kHz120 + dl_subcarrierSpacing = 1; + dl_carrierBandwidth = 106; + #initialDownlinkBWP + #genericParameters + # this is RBstart=27,L=48 (275*(L-1))+RBstart + initialDLBWPlocationAndBandwidth = 28875; # 6366 12925 12956 28875 12952 +# 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 = 106; + pMax = 20; + #initialUplinkBWP + #genericParameters + initialULBWPlocationAndBandwidth = 28875; +# subcarrierSpacing +# 0=kHz15, 1=kHz30, 2=kHz60, 3=kHz120 + initialULBWPsubcarrierSpacing = 1; + #rach-ConfigCommon + #rach-ConfigGeneric + prach_ConfigurationIndex = 98; +#prach_msg1_FDM +#0 = one, 1=two, 2=four, 3=eight + prach_msg1_FDM = 0; + prach_msg1_FrequencyStart = 0; + zeroCorrelationZoneConfig = 13; + 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; +#ra_ReponseWindow +#1,2,4,8,10,20,40,80 + ra_ResponseWindow = 4; +#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; +#oneHalf (0..15) 4,8,12,16,...60,64 + ssb_perRACH_OccasionAndCB_PreamblesPerSSB = 14; +#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; + + # 0=sl1, 1=sl2, 2=sl4, 3=sl8, 4=sl10, 5=sl20, 6=sl40, 7=sl80, 8=sl160, 9=sl320 + msgB_ResponseWindow_r16 = 2; + msgA_RSRP_Threshold_r16 = 19; + + msgA_CB_PreamblesPerSSB_PerSharedRO_r16 = 1; + + msgA_MCS_r16 = 2; + nrofSlotsMsgA_PUSCH_r16 = 1; + # 0=one, 1=two, 2=three, 3=six + nrofMsgA_PO_PerSlot_r16 = 0; + msgA_PUSCH_TimeDomainOffset_r16 = 8; + startSymbolAndLengthMsgA_PO_r16 = 38; + mappingTypeMsgA_PUSCH_r16 = 0; + guardBandMsgA_PUSCH_r16 = 0; + frequencyStartMsgA_PUSCH_r16 = 0; + nrofPRBs_PerMsgA_PO_r16 = 8; + # 0=one, 1=two, 2=four, 3=eight + nrofMsgA_PO_FDM_r16 = 0; + msgA_PUSCH_NrofPorts_r16 = 1; + nrofDMRS_Sequences_r16 = 1; + # 0=enabled, 1=disabled + msgA_TransformPrecoder_r16 = 1; + +# pucch-ConfigCommon setup : +# pucchGroupHopping +# 0 = neither, 1= group hopping, 2=sequence hopping + pucchGroupHopping = 0; + hoppingId = 40; + p0_nominal = -90; +# ssb_PositionsInBurs_BitmapPR +# 1=short, 2=medium, 3=long + ssb_PositionsInBurst_PR = 2; + 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; + nrofDownlinkSlots = 7; + nrofDownlinkSymbols = 6; + nrofUplinkSlots = 2; + nrofUplinkSymbols = 4; + + 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 = "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 + }; + + } +); + +MACRLCs = ( +{ + num_cc = 1; + tr_s_preference = "local_L1"; + tr_n_preference = "local_RRC"; + pusch_TargetSNRx10 = 150; + pucch_TargetSNRx10 = 200; +} +); + +L1s = ( +{ + num_cc = 1; + tr_n_preference = "local_mac"; + prach_dtx_threshold = 120; + pucch0_dtx_threshold = 100; + ofdm_offset_divisor = 8; #set this to UINT_MAX for offset 0 +} +); + +RUs = ( +{ + local_rf = "yes" + nb_tx = 1 + nb_rx = 1 + att_tx = 12; + att_rx = 12; + bands = [78]; + max_pdschReferenceSignalPower = -27; + max_rxgain = 114; + eNB_instances = [0]; + #beamforming 1x4 matrix: + bf_weights = [0x00007fff, 0x0000, 0x0000, 0x0000]; + clock_src = "internal"; +} +); + +rfsimulator : +{ + serveraddr = "server"; + serverport = 4043; + options = (); #("saviq"); or/and "chanmod" + modelname = "AWGN"; + IQfile = "/tmp/rfsimulator.iqs"; +}; + +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"; +}; + +e2_agent = { + near_ric_ip_addr = "127.0.0.1"; + #sm_dir = "/path/where/the/SMs/are/located/" + sm_dir = "/usr/local/lib/flexric/" +}; diff --git a/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band78.273prb.fhi72.4x4-benetel550.conf b/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band78.273prb.fhi72.4x4-benetel550.conf index 07fae93c76..a8f072a199 100644 --- a/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band78.273prb.fhi72.4x4-benetel550.conf +++ b/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band78.273prb.fhi72.4x4-benetel550.conf @@ -227,8 +227,6 @@ RUs = ( eNB_instances = [0]; ru_thread_core = 9; sl_ahead = 10; - ##beamforming 1x2 matrix: 1 layer x 2 antennas - bf_weights = [0x00007fff, 0x0000,0x00007fff, 0x0000]; tr_preference = "raw_if4p5"; # important: activate FHI7.2 do_precoding = 0; # needs to match O-RU configuration } diff --git a/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band78.273prb.fhi72.4x4-benetel650.conf b/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band78.273prb.fhi72.4x4-benetel650.conf index 7a739526f0..767c551881 100644 --- a/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band78.273prb.fhi72.4x4-benetel650.conf +++ b/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band78.273prb.fhi72.4x4-benetel650.conf @@ -227,8 +227,6 @@ RUs = ( eNB_instances = [0]; ru_thread_core = 9; sl_ahead = 10; - ##beamforming 1x2 matrix: 1 layer x 2 antennas - bf_weights = [0x00007fff, 0x0000,0x00007fff, 0x0000]; tr_preference = "raw_if4p5"; # important: activate FHI7.2 do_precoding = 0; # needs to match O-RU configuration } diff --git a/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band78.273prb.fhi72.4x4-liteon.conf b/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band78.273prb.fhi72.4x4-liteon.conf index 0d0a931e8a..2cc2cbeee7 100644 --- a/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band78.273prb.fhi72.4x4-liteon.conf +++ b/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band78.273prb.fhi72.4x4-liteon.conf @@ -224,9 +224,6 @@ RUs = ( eNB_instances = [0]; # TODO is relevant? ru_thread_core = 6; sl_ahead = 5; - ##beamforming 1x2 matrix: 1 layer x 2 antennas - bf_weights = [0x00007fff, 0x0000,0x00007fff, 0x0000]; # necessary? - tr_preference = "raw_if4p5"; # important: activate FHI7.2 do_precoding = 0; # needs to match O-RU configuration diff --git a/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band78.fr1.106PRB.2x2.usrpn300.conf b/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band78.fr1.106PRB.2x2.usrpn300.conf index 336bd3aca0..1e1e00b6f2 100644 --- a/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band78.fr1.106PRB.2x2.usrpn300.conf +++ b/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band78.fr1.106PRB.2x2.usrpn300.conf @@ -201,8 +201,6 @@ RUs = ( max_pdschReferenceSignalPower = -27; max_rxgain = 75; eNB_instances = [0]; - ##beamforming 1x2 matrix: 1 layer x 2 antennas - bf_weights = [0x00007fff, 0x0000]; #clock_src = "internal"; sdr_addrs = "mgmt_addr=192.168.10.2,addr=192.168.10.2,clock_source=internal,time_source=internal" } diff --git a/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band78.fr1.106PRB.usrpb210.4layer.conf b/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band78.fr1.106PRB.usrpb210.4layer.conf index 02e9bde6e1..5270ff68d9 100644 --- a/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band78.fr1.106PRB.usrpb210.4layer.conf +++ b/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band78.fr1.106PRB.usrpb210.4layer.conf @@ -203,8 +203,6 @@ RUs = ( max_pdschReferenceSignalPower = -27; max_rxgain = 114; eNB_instances = [0]; - #beamforming 1x4 matrix: - bf_weights = [0x00007fff, 0x0000, 0x0000, 0x0000, 0x00000000, 0x00007fff, 0x0000, 0x0000, 0x0000, 0x0000, 0x00007fff, 0x0000, 0x0000, 0x0000, 0x0000, 0x00007fff]; clock_src = "internal"; } ); diff --git a/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band78.fr1.106PRB.usrpb210.conf b/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band78.fr1.106PRB.usrpb210.conf index 51cfbc5952..9d789b9c40 100644 --- a/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band78.fr1.106PRB.usrpb210.conf +++ b/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band78.fr1.106PRB.usrpb210.conf @@ -201,8 +201,6 @@ RUs = ( max_pdschReferenceSignalPower = -27; max_rxgain = 114; eNB_instances = [0]; - #beamforming 1x4 matrix: - bf_weights = [0x00007fff, 0x0000, 0x0000, 0x0000]; clock_src = "internal"; } ); diff --git a/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band78.fr1.106PRB.usrpb210.sabox.conf b/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band78.fr1.106PRB.usrpb210.sabox.conf index d2a5193ae1..813c864c33 100644 --- a/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band78.fr1.106PRB.usrpb210.sabox.conf +++ b/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band78.fr1.106PRB.usrpb210.sabox.conf @@ -207,8 +207,6 @@ RUs = ( max_pdschReferenceSignalPower = -27; max_rxgain = 114; eNB_instances = [0]; - #beamforming 1x4 matrix: - bf_weights = [0x00007fff, 0x0000, 0x0000, 0x0000]; clock_src = "internal"; } ); diff --git a/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band78.fr1.106PRB.usrpb210.yaml b/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band78.fr1.106PRB.usrpb210.yaml index a215c71304..54cefa608f 100644 --- a/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band78.fr1.106PRB.usrpb210.yaml +++ b/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band78.fr1.106PRB.usrpb210.yaml @@ -178,7 +178,6 @@ RUs: max_pdschReferenceSignalPower: -27 max_rxgain: 114 eNB_instances: [0] - bf_weights: [0x00007fff, 0x0000, 0x0000, 0x0000] clock_src: internal rfsimulator: diff --git a/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band78.fr1.162PRB.2x2.usrpn300.conf b/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band78.fr1.162PRB.2x2.usrpn300.conf index 45dc540a5e..1985789f5a 100644 --- a/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band78.fr1.162PRB.2x2.usrpn300.conf +++ b/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band78.fr1.162PRB.2x2.usrpn300.conf @@ -209,8 +209,6 @@ RUs = ( max_pdschReferenceSignalPower = -27; max_rxgain = 75; eNB_instances = [0]; - ##beamforming 1x2 matrix: 1 layer x 2 antennas - bf_weights = [0x00007fff, 0x0000]; #clock_src = "internal"; sdr_addrs = "mgmt_addr=192.168.10.2,addr=192.168.10.2,clock_source=internal,time_source=internal" } diff --git a/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band78.fr1.217PRB.2x2.usrpn300.conf b/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band78.fr1.217PRB.2x2.usrpn300.conf index 60194ed927..e995999f46 100644 --- a/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band78.fr1.217PRB.2x2.usrpn300.conf +++ b/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band78.fr1.217PRB.2x2.usrpn300.conf @@ -203,8 +203,6 @@ RUs = ( max_pdschReferenceSignalPower = -27; max_rxgain = 75; eNB_instances = [0]; - ##beamforming 1x2 matrix: 1 layer x 2 antennas - bf_weights = [0x00007fff, 0x0000]; #clock_src = "internal"; sdr_addrs = "mgmt_addr=192.168.10.2,addr=192.168.10.2,clock_source=internal,time_source=internal" } diff --git a/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band78.fr1.24PRB.usrpb210.conf b/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band78.fr1.24PRB.usrpb210.conf index 408677ecdb..d7cf316b1d 100644 --- a/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band78.fr1.24PRB.usrpb210.conf +++ b/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band78.fr1.24PRB.usrpb210.conf @@ -203,8 +203,6 @@ RUs = ( max_rxgain = 114; sf_extension = 0; eNB_instances = [0]; - #beamforming 1x4 matrix: - bf_weights = [0x00007fff, 0x0000, 0x0000, 0x0000]; clock_src = "internal"; } ); diff --git a/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb0.prs.band78.fr1.106PRB.usrpx310.conf b/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb0.prs.band78.fr1.106PRB.usrpx310.conf index 23b54c0755..4fc0b8a387 100644 --- a/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb0.prs.band78.fr1.106PRB.usrpx310.conf +++ b/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb0.prs.band78.fr1.106PRB.usrpx310.conf @@ -257,14 +257,6 @@ RUs = ( max_pdschReferenceSignalPower = -27; max_rxgain = 75; eNB_instances = [0]; - ##beamforming 1x2 matrix: 1 layer x 2 antennas - bf_weights = [0x00007fff, 0x0000]; - ##beamforming 1x4 matrix: 1 layer x 4 antennas - #bf_weights = [0x00007fff, 0x0000,0x0000, 0x0000]; - ## beamforming 2x2 matrix: - # bf_weights = [0x00007fff, 0x00000000, 0x00000000, 0x00007fff]; - ## beamforming 4x4 matrix: - #bf_weights = [0x00007fff, 0x0000, 0x0000, 0x0000, 0x00000000, 0x00007fff, 0x0000, 0x0000, 0x0000, 0x0000, 0x00007fff, 0x0000, 0x0000, 0x0000, 0x0000, 0x00007fff]; sf_extension = 0 sdr_addrs = "mgmt_addr=172.21.19.14,addr=192.168.10.2,second_addr=192.168.20.2,clock_source=internal,time_source=internal" } diff --git a/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb1.prs.band78.fr1.106PRB.usrpx310.conf b/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb1.prs.band78.fr1.106PRB.usrpx310.conf index 3ca332f7bc..28d880cf16 100644 --- a/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb1.prs.band78.fr1.106PRB.usrpx310.conf +++ b/targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb1.prs.band78.fr1.106PRB.usrpx310.conf @@ -256,14 +256,6 @@ RUs = ( max_pdschReferenceSignalPower = -27; max_rxgain = 75; eNB_instances = [0]; - ##beamforming 1x2 matrix: 1 layer x 2 antennas - bf_weights = [0x00007fff, 0x0000]; - ##beamforming 1x4 matrix: 1 layer x 4 antennas - #bf_weights = [0x00007fff, 0x0000,0x0000, 0x0000]; - ## beamforming 2x2 matrix: - # bf_weights = [0x00007fff, 0x00000000, 0x00000000, 0x00007fff]; - ## beamforming 4x4 matrix: - #bf_weights = [0x00007fff, 0x0000, 0x0000, 0x0000, 0x00000000, 0x00007fff, 0x0000, 0x0000, 0x0000, 0x0000, 0x00007fff, 0x0000, 0x0000, 0x0000, 0x0000, 0x00007fff]; sf_extension = 0 sdr_addrs = "mgmt_addr=172.21.19.14,addr=192.168.10.2,second_addr=192.168.20.2,clock_source=internal,time_source=internal" } diff --git a/tools/iwyu/README.md b/tools/iwyu/README.md new file mode 100644 index 0000000000..30b573747a --- /dev/null +++ b/tools/iwyu/README.md @@ -0,0 +1,23 @@ +# Overview + +IWYU - [include what you use](https://github.com/include-what-you-use/include-what-you-use) +is a tool that can detect and correct C/C++ include errors + +# Usage + +``` +TARGET= docker compose up +``` + +Automatically apply suggestions: + +``` +TARGET= docker compose run iwyu | tee suggestions +cat suggestions | python3 ~/include-what-you-use/fix_includes.py +``` + +Apply only removal suggestions + +``` +cat suggestions | grep "should add these line\|The full include-list\|should remove these lines\|^-" | python3 ~/include-what-you-use/fix_includes.py +``` diff --git a/tools/iwyu/docker-compose.yaml b/tools/iwyu/docker-compose.yaml new file mode 100644 index 0000000000..de8dab6b73 --- /dev/null +++ b/tools/iwyu/docker-compose.yaml @@ -0,0 +1,39 @@ +services: + iwyu: + image: iwyu + build: + dockerfile_inline: | + FROM ran-base + ENV DEBIAN_FRONTEND=noninteractive + RUN apt update && \ + apt install -y wget gnupg && \ + wget -O - https://apt.llvm.org/llvm-snapshot.gpg.key | apt-key add - && \ + echo "deb http://apt.llvm.org/focal/ llvm-toolchain-focal-14 main" > /etc/apt/sources.list.d/llvm.list && \ + apt update + RUN apt install -y \ + git \ + cmake \ + build-essential \ + clang-14 \ + libclang-14-dev \ + ninja-build \ + libyaml-cpp-dev + WORKDIR /iwyu/ + RUN git clone https://github.com/include-what-you-use/include-what-you-use.git + RUN cd /iwyu/include-what-you-use && \ + git checkout origin/clang_14 && \ + mkdir build && cd build && \ + cmake -DCMAKE_CXX_COMPILER=g++ -DCMAKE_C_COMPILER=gcc ../ -G "Unix Makefiles" && \ + make + RUN apt clean && rm -rf /var/lib/apt/lists/* + volumes: + - ../../:/code/ + command: + bash -c "git config --global --add safe.directory /code && \ + mkdir -p iwyu-bin && cd iwyu-bin && \ + cmake \ + -DCMAKE_C_INCLUDE_WHAT_YOU_USE=/iwyu/include-what-you-use/build/bin/include-what-you-use \ + -DCMAKE_CXX_INCLUDE_WHAT_YOU_USE=/iwyu/include-what-you-use/build/bin/include-what-you-use \ + /code/ \ + -GNinja && \ + cmake --build . --target $TARGET"