Commit f7d3b728 authored by Robert Schmidt's avatar Robert Schmidt

Merge branch 'integration_2025_w02' into 'develop'

Integration: `2025.w02`

Closes #866 and #887

See merge request oai/openairinterface5g!3197

* !3135 replace a set of #define by a C bit array, remove duplicated extern global variable declaration
* !3173 nrLDPC_coding: improvements
* !3181 Use UL actor for processSlotTx
* !3186 chore(ci): improved errors messages visibility
* !3101 NR gNB improvements for analog beam management
* !3130 NR gNB MSG3 TPC
* !3175 Improvements for PUSCH per symbol processing
* !3177 CI: change frequency for timing and B200-SABOX pipelines
* !3188 NR UE fix DCI mask size
* !3119 Config files improvements for PRACH
* !3196 Fix yaml example config file
* !3187 nrLDPC_coding: Fix naming, comments, superfluous variables and documentation typos in coding library interfaces
* !3076 move UL_INFO structure allocation local to a rx slot processing
* !3189 fhi_72: allow to provide dpdk_iova_mode to xran
* !3182 RSSI threshold for PUSCH & PUCCH power control
* !3103 Introduce ITTI queue in RRC-to-MAC direction
parents 7418a104 959bb59f
......@@ -772,10 +772,6 @@ set(PHY_TURBOIF
${OPENAIR1_DIR}/PHY/CODING/coding_load.c
)
set(PHY_NR_CODINGIF
${OPENAIR1_DIR}/PHY/CODING/nrLDPC_load.c
)
set(PHY_NRLDPC_CODINGIF
${OPENAIR1_DIR}/PHY/CODING/nrLDPC_coding/nrLDPC_coding_interface_load.c
)
......@@ -807,8 +803,6 @@ set(PHY_SRC_COMMON
${OPENAIR1_DIR}/PHY/LTE_REFSIG/lte_dl_mbsfn.c
${OPENAIR1_DIR}/PHY/LTE_REFSIG/lte_ul_ref.c
${OPENAIR1_DIR}/PHY/CODING/lte_segmentation.c
${OPENAIR1_DIR}/PHY/CODING/nr_segmentation.c
${OPENAIR1_DIR}/PHY/CODING/nr_rate_matching.c
${OPENAIR1_DIR}/PHY/CODING/ccoding_byte.c
${OPENAIR1_DIR}/PHY/CODING/ccoding_byte_lte.c
${OPENAIR1_DIR}/PHY/CODING/3gpplte_sse.c
......@@ -919,6 +913,8 @@ set(PHY_SRC_UE
)
set(PHY_NR_SRC_COMMON
${OPENAIR1_DIR}/PHY/CODING/nr_segmentation.c
${OPENAIR1_DIR}/PHY/NR_TRANSPORT/nr_tbs_tools.c
${OPENAIR1_DIR}/PHY/NR_TRANSPORT/nr_prach_common.c
${OPENAIR1_DIR}/PHY/nr_phy_common/src/nr_phy_common_csirs.c
${OPENAIR1_DIR}/PHY/NR_TRANSPORT/nr_scrambling.c
......@@ -942,7 +938,6 @@ set(PHY_SRC_UE
${OPENAIR1_DIR}/PHY/NR_TRANSPORT/nr_dlsch_coding.c
${OPENAIR1_DIR}/PHY/NR_TRANSPORT/nr_ulsch_decoding.c
${OPENAIR1_DIR}/PHY/NR_TRANSPORT/nr_ulsch.c
${OPENAIR1_DIR}/PHY/NR_TRANSPORT/nr_tbs_tools.c
${OPENAIR1_DIR}/PHY/NR_TRANSPORT/nr_sch_dmrs.c
${OPENAIR1_DIR}/PHY/NR_TRANSPORT/nr_prach.c
${OPENAIR1_DIR}/PHY/NR_TRANSPORT/nr_ulsch_llr_computation.c
......@@ -990,7 +985,6 @@ set(PHY_SRC_UE
${OPENAIR1_DIR}/PHY/NR_UE_TRANSPORT/nr_dlsch_demodulation.c
${OPENAIR1_DIR}/PHY/NR_UE_TRANSPORT/nr_ulsch_coding.c
${OPENAIR1_DIR}/PHY/NR_UE_TRANSPORT/nr_dlsch_decoding.c
${OPENAIR1_DIR}/PHY/NR_TRANSPORT/nr_tbs_tools.c
${OPENAIR1_DIR}/PHY/NR_TRANSPORT/nr_prach_common.c
${OPENAIR1_DIR}/PHY/NR_TRANSPORT/nr_sch_dmrs.c
${OPENAIR1_DIR}/PHY/NR_UE_TRANSPORT/
......@@ -2060,12 +2054,11 @@ target_link_libraries(smallblocktest PRIVATE
add_executable(ldpctest
${PHY_NR_CODINGIF}
${OPENAIR1_DIR}/PHY/CODING/TESTBENCH/ldpctest.c
)
target_link_libraries(ldpctest PRIVATE
-Wl,--start-group UTIL SIMU PHY_COMMON PHY_NR_COMMON -Wl,--end-group
m pthread dl shlib_loader ${T_LIB}
m pthread dl shlib_loader ${T_LIB} nr_coding_segment_utils
)
add_executable(nr_dlschsim
......
......@@ -91,8 +91,8 @@ gNBs =
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 = 3;
#oneHalf (0..15) 4,8,12,16,...60,64
ssb_perRACH_OccasionAndCB_PreamblesPerSSB_PR = 4;
#one (0..15) 4,8,12,16,...60,64
ssb_perRACH_OccasionAndCB_PreamblesPerSSB = 15;
#ra_ContentionResolutionTimer
#(0..7) 8,16,24,32,40,48,56,64
......
......@@ -90,7 +90,7 @@ gNBs =
#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
#one (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
......
......@@ -92,7 +92,7 @@ gNBs =
#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
#one (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
......
......@@ -35,13 +35,6 @@ gNBs =
do_SRS = 0;
min_rxtxtime = 2;
pdcch_ConfigSIB1 = (
{
controlResourceSetZero = 12;
searchSpaceZero = 0;
}
);
servingCellConfigCommon = (
{
#spCellConfigCommon
......@@ -116,8 +109,8 @@ gNBs =
ra_ResponseWindow = 5;
#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 = 3;
#oneHalf (0..15) 4,8,12,16,...60,64
ssb_perRACH_OccasionAndCB_PreamblesPerSSB_PR = 4;
#one (0..15) 4,8,12,16,...60,64
ssb_perRACH_OccasionAndCB_PreamblesPerSSB = 15;
#ra_ContentionResolutionTimer
#(0..7) 8,16,24,32,40,48,56,64
......
......@@ -90,7 +90,7 @@ gNBs =
#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
#one (0..15) 4,8,12,16,...60,64
ssb_perRACH_OccasionAndCB_PreamblesPerSSB = 15;
#ra_ContentionResolutionTimer
#(0..7) 8,16,24,32,40,48,56,64
......
......@@ -89,7 +89,7 @@ gNBs =
#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
#one (0..15) 4,8,12,16,...60,64
ssb_perRACH_OccasionAndCB_PreamblesPerSSB = 15;
#ra_ContentionResolutionTimer
#(0..7) 8,16,24,32,40,48,56,64
......
......@@ -31,11 +31,11 @@ gNBs =
# downlinkConfigCommon
#frequencyInfoDL
# this is 3600 MHz + 43 PRBs@30kHz SCS (same as initial BWP)
absoluteFrequencySSB = 641032;
# this is 3319.68 MHz
absoluteFrequencySSB = 621312;
dl_frequencyBand = 78;
# this is 3600 MHz
dl_absoluteFrequencyPointA = 640000;
# this is 3300.6 MHz
dl_absoluteFrequencyPointA = 620040;
#scs-SpecificCarrierList
dl_offstToCarrier = 0;
# subcarrierSpacing
......@@ -89,7 +89,7 @@ gNBs =
#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
#one (0..15) 4,8,12,16,...60,64
ssb_perRACH_OccasionAndCB_PreamblesPerSSB = 15;
#ra_ContentionResolutionTimer
#(0..7) 8,16,24,32,40,48,56,64
......
......@@ -89,7 +89,7 @@ gNBs =
#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
#one (0..15) 4,8,12,16,...60,64
ssb_perRACH_OccasionAndCB_PreamblesPerSSB = 15;
#ra_ContentionResolutionTimer
#(0..7) 8,16,24,32,40,48,56,64
......
......@@ -91,7 +91,7 @@ gNBs =
#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
#one (0..15) 4,8,12,16,...60,64
ssb_perRACH_OccasionAndCB_PreamblesPerSSB = 15;
#ra_ContentionResolutionTimer
#(0..7) 8,16,24,32,40,48,56,64
......
......@@ -84,8 +84,8 @@ gNBs =
#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; //15;
#one (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;
......
......@@ -89,8 +89,8 @@ gNBs =
#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; //15;
#one (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;
......
......@@ -88,8 +88,8 @@ gNBs =
ra_ResponseWindow = 5;
#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 = 3;
#oneHalf (0..15) 4,8,12,16,...60,64
ssb_perRACH_OccasionAndCB_PreamblesPerSSB_PR = 4;
#one (0..15) 4,8,12,16,...60,64
ssb_perRACH_OccasionAndCB_PreamblesPerSSB = 15;
#ra_ContentionResolutionTimer
#(0..7) 8,16,24,32,40,48,56,64
......
......@@ -87,7 +87,7 @@ gNBs =
#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
#one (0..15) 4,8,12,16,...60,64
ssb_perRACH_OccasionAndCB_PreamblesPerSSB = 15;
#ra_ContentionResolutionTimer
#(0..7) 8,16,24,32,40,48,56,64
......
......@@ -88,7 +88,7 @@ gNBs =
#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
#one (0..15) 4,8,12,16,...60,64
ssb_perRACH_OccasionAndCB_PreamblesPerSSB = 15;
#ra_ContentionResolutionTimer
#(0..7) 8,16,24,32,40,48,56,64
......
......@@ -88,7 +88,7 @@ gNBs =
#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
#one (0..15) 4,8,12,16,...60,64
ssb_perRACH_OccasionAndCB_PreamblesPerSSB = 15;
#ra_ContentionResolutionTimer
#(0..7) 8,16,24,32,40,48,56,64
......
......@@ -91,8 +91,8 @@ gNBs =
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 = 3;
#oneHalf (0..15) 4,8,12,16,...60,64
ssb_perRACH_OccasionAndCB_PreamblesPerSSB_PR = 4;
#one (0..15) 4,8,12,16,...60,64
ssb_perRACH_OccasionAndCB_PreamblesPerSSB = 15;
#ra_ContentionResolutionTimer
#(0..7) 8,16,24,32,40,48,56,64
......
......@@ -93,8 +93,8 @@ gNBs =
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 = 3;
#oneHalf (0..15) 4,8,12,16,...60,64
ssb_perRACH_OccasionAndCB_PreamblesPerSSB_PR = 4;
#one (0..15) 4,8,12,16,...60,64
ssb_perRACH_OccasionAndCB_PreamblesPerSSB = 15;
#ra_ContentionResolutionTimer
#(0..7) 8,16,24,32,40,48,56,64
......@@ -210,8 +210,6 @@ RUs = (
max_pdschReferenceSignalPower = -27;
max_rxgain = 75;
eNB_instances = [0];
##beamforming 1x2 matrix: 1 layer x 2 antennas
bf_weights = [0x00007fff, 0x0000, 0x00007fff, 0x0000];
#clock_src = "internal";
sdr_addrs = "addr=192.168.80.53, clock_source=internal,time_source=internal"
......
......@@ -24,13 +24,6 @@ gNBs =
do_CSIRS = 1;
do_SRS = 0;
pdcch_ConfigSIB1 = (
{
controlResourceSetZero = 11;
searchSpaceZero = 0;
}
);
servingCellConfigCommon = (
{
#spCellConfigCommon
......@@ -95,8 +88,8 @@ gNBs =
ra_ResponseWindow = 5;
#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 = 3;
#oneHalf (0..15) 4,8,12,16,...60,64
ssb_perRACH_OccasionAndCB_PreamblesPerSSB_PR = 4;
#one (0..15) 4,8,12,16,...60,64
ssb_perRACH_OccasionAndCB_PreamblesPerSSB = 15;
#ra_ContentionResolutionTimer
#(0..7) 8,16,24,32,40,48,56,64
......
......@@ -235,6 +235,7 @@ log_config :
fhi_72 = {
dpdk_devices = ("0000:c3:11.0", "0000:c3:11.1");
dpdk_iova_mode = "VA";
system_core = 0;
io_core = 1;
worker_cores = (2);
......
......@@ -91,8 +91,8 @@ gNBs = (
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 = 3;
# oneHalf (0..15) 4,8,12,16,...60,64
ssb_perRACH_OccasionAndCB_PreamblesPerSSB_PR = 4;
# one (0..15) 4,8,12,16,...60,64
ssb_perRACH_OccasionAndCB_PreamblesPerSSB = 15;
# ra_ContentionResolutionTimer
# (0..7) 8,16,24,32,40,48,56,64
......
......@@ -26,14 +26,6 @@ gNBs =
pdsch_AntennaPorts_XP = 1;
pusch_AntennaPorts = 1;
pdcch_ConfigSIB1 = (
{
controlResourceSetZero = 12;
searchSpaceZero = 0;
}
);
servingCellConfigCommon = (
{
#spCellConfigCommon
......@@ -97,8 +89,8 @@ gNBs =
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 = 3;
#oneHalf (0..15) 4,8,12,16,...60,64
ssb_perRACH_OccasionAndCB_PreamblesPerSSB_PR = 4;
#one (0..15) 4,8,12,16,...60,64
ssb_perRACH_OccasionAndCB_PreamblesPerSSB = 15;
#ra_ContentionResolutionTimer
#(0..7) 8,16,24,32,40,48,56,64
......
......@@ -91,8 +91,8 @@ gNBs =
ra_ResponseWindow = 5;
#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 = 3;
#oneHalf (0..15) 4,8,12,16,...60,64
ssb_perRACH_OccasionAndCB_PreamblesPerSSB_PR = 4;
#one (0..15) 4,8,12,16,...60,64
ssb_perRACH_OccasionAndCB_PreamblesPerSSB = 15;
#ra_ContentionResolutionTimer
#(0..7) 8,16,24,32,40,48,56,64
......
......@@ -85,8 +85,8 @@ gNBs =
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 = 3;
#oneHalf (0..15) 4,8,12,16,...60,64
ssb_perRACH_OccasionAndCB_PreamblesPerSSB_PR = 4;
#one (0..15) 4,8,12,16,...60,64
ssb_perRACH_OccasionAndCB_PreamblesPerSSB = 15;
#ra_ContentionResolutionTimer
#(0..7) 8,16,24,32,40,48,56,64
......
......@@ -21,12 +21,6 @@ gNBs =
do_CSIRS = 0;
do_SRS = 0;
min_rxtxtime = 6;
pdcch_ConfigSIB1 = (
{
controlResourceSetZero = 12;
searchSpaceZero = 0;
}
);
servingCellConfigCommon = (
{
......@@ -94,7 +88,7 @@ gNBs =
#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
#one (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
......
......@@ -77,8 +77,8 @@ gNBs:
ra_ResponseWindow: 5
#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: 3
#oneHalf (0..15) 4,8,12,16,...60,64
ssb_perRACH_OccasionAndCB_PreamblesPerSSB_PR: 4
#one (0..15) 4,8,12,16,...60,64
ssb_perRACH_OccasionAndCB_PreamblesPerSSB: 15
#ra_ContentionResolutionTimer
#(0..7) 8,16,24,32,40,48,56,64
......
......@@ -90,8 +90,8 @@ gNBs =
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 = 3;
#oneHalf (0..15) 4,8,12,16,...60,64
ssb_perRACH_OccasionAndCB_PreamblesPerSSB_PR = 4;
#one (0..15) 4,8,12,16,...60,64
ssb_perRACH_OccasionAndCB_PreamblesPerSSB = 15;
#ra_ContentionResolutionTimer
#(0..7) 8,16,24,32,40,48,56,64
......
......@@ -84,7 +84,7 @@ gNBs =
#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
#one (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
......
......@@ -103,8 +103,8 @@ gNBs =
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 = 3;
#oneHalf (0..15) 4,8,12,16,...60,64
ssb_perRACH_OccasionAndCB_PreamblesPerSSB_PR = 4;
#one (0..15) 4,8,12,16,...60,64
ssb_perRACH_OccasionAndCB_PreamblesPerSSB = 15;
#ra_ContentionResolutionTimer
#(0..7) 8,16,24,32,40,48,56,64
......
......@@ -104,8 +104,8 @@ gNBs =
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 = 3;
#oneHalf (0..15) 4,8,12,16,...60,64
ssb_perRACH_OccasionAndCB_PreamblesPerSSB_PR = 4;
#one (0..15) 4,8,12,16,...60,64
ssb_perRACH_OccasionAndCB_PreamblesPerSSB = 15;
#ra_ContentionResolutionTimer
#(0..7) 8,16,24,32,40,48,56,64
......
......@@ -86,7 +86,7 @@ gNBs =
#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
#one (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
......
......@@ -26,13 +26,6 @@ gNBs =
sib1_tda = 15;
# force_UL256qam_off = 1;
pdcch_ConfigSIB1 = (
{
controlResourceSetZero = 11;
searchSpaceZero = 0;
}
);
servingCellConfigCommon = (
{
#spCellConfigCommon
......@@ -82,7 +75,7 @@ gNBs =
initialULBWPsubcarrierSpacing = 1;
#rach-ConfigCommon
#rach-ConfigGeneric
prach_ConfigurationIndex = 151;
prach_ConfigurationIndex = 152;
#prach_msg1_FDM
#0 = one, 1=two, 2=four, 3=eight
prach_msg1_FDM = 0;
......@@ -99,8 +92,8 @@ gNBs =
ra_ResponseWindow = 5;
#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 = 3;
#oneHalf (0..15) 4,8,12,16,...60,64
ssb_perRACH_OccasionAndCB_PreamblesPerSSB_PR = 4;
#one (0..15) 4,8,12,16,...60,64
ssb_perRACH_OccasionAndCB_PreamblesPerSSB = 15;
#ra_ContentionResolutionTimer
#(0..7) 8,16,24,32,40,48,56,64
......
......@@ -88,8 +88,8 @@ gNBs =
ra_ResponseWindow = 5;
#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 = 3;
#oneHalf (0..15) 4,8,12,16,...60,64
ssb_perRACH_OccasionAndCB_PreamblesPerSSB_PR = 4;
#one (0..15) 4,8,12,16,...60,64
ssb_perRACH_OccasionAndCB_PreamblesPerSSB = 15;
#ra_ContentionResolutionTimer
#(0..7) 8,16,24,32,40,48,56,64
......
......@@ -75,7 +75,7 @@ gNBs =
initialULBWPsubcarrierSpacing = 1;
#rach-ConfigCommon
#rach-ConfigGeneric
prach_ConfigurationIndex = 100;
prach_ConfigurationIndex = 101;
#prach_msg1_FDM
#0 = one, 1=two, 2=four, 3=eight
prach_msg1_FDM = 0;
......@@ -92,8 +92,8 @@ gNBs =
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 = 3;
#oneHalf (0..15) 4,8,12,16,...60,64
ssb_perRACH_OccasionAndCB_PreamblesPerSSB_PR = 4;
#one (0..15) 4,8,12,16,...60,64
ssb_perRACH_OccasionAndCB_PreamblesPerSSB = 15;
#ra_ContentionResolutionTimer
#(0..7) 8,16,24,32,40,48,56,64
......
......@@ -75,7 +75,7 @@ gNBs =
initialULBWPsubcarrierSpacing = 1;
#rach-ConfigCommon
#rach-ConfigGeneric
prach_ConfigurationIndex = 100;
prach_ConfigurationIndex = 101;
#prach_msg1_FDM
#0 = one, 1=two, 2=four, 3=eight
prach_msg1_FDM = 0;
......@@ -92,8 +92,8 @@ gNBs =
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 = 3;
#oneHalf (0..15) 4,8,12,16,...60,64
ssb_perRACH_OccasionAndCB_PreamblesPerSSB_PR = 4;
#one (0..15) 4,8,12,16,...60,64
ssb_perRACH_OccasionAndCB_PreamblesPerSSB = 15;
#ra_ContentionResolutionTimer
#(0..7) 8,16,24,32,40,48,56,64
......
......@@ -26,11 +26,11 @@ gNBs =
# downlinkConfigCommon
#frequencyInfoDL
# this is 3300.30 MHz + (19 PRBs + 10 SCs)@30kHz SCS (GSCN: 7715)
absoluteFrequencySSB = 620736;
# this is 3610.56 MHz
absoluteFrequencySSB = 640704;
dl_frequencyBand = 78;
# this is 3300.30 MHz
dl_absoluteFrequencyPointA = 620020;
# this is 3599.94 MHz
dl_absoluteFrequencyPointA = 639996;
#scs-SpecificCarrierList
dl_offstToCarrier = 0;
# subcarrierSpacing
......@@ -84,7 +84,7 @@ gNBs =
#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
#one (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
......
......@@ -2,7 +2,6 @@ services:
oai-gnb:
image: ${REGISTRY:-oaisoftwarealliance}/oai-gnb-fhi72:${TAG:-develop}
cap_add:
- SYS_ADMIN
- IPC_LOCK
- SYS_NICE
cap_drop:
......
......@@ -226,7 +226,7 @@ compilations() {
ret=$?
} > $dlog/$logfile 2>&1
# Print the errors and warnings for CI purposes
grep -E -A3 "warning:|error:" $dlog/$logfile || true
grep -E -A5 -B5 "warning:|error:| Error " $dlog/$logfile || true
check_warnings "$dlog/$logfile"
if [[ $ret -eq 0 ]]; then
echo_success "$targets compiled"
......
......@@ -32,7 +32,9 @@
#ifndef __RAN_CONTEXT_H__
#define __RAN_CONTEXT_H__
#ifdef __cplusplus
extern "C" {
#endif
#include <pthread.h>
#include <stdint.h>
......@@ -111,6 +113,8 @@ typedef struct {
} RAN_CONTEXT_t;
extern RAN_CONTEXT_t RC;
#define NB_eNB_INST RC.nb_inst
#ifdef __cplusplus
}
#endif
#endif
......@@ -54,6 +54,7 @@
#include "common/utils/load_module_shlib.h"
#include "common/config/config_userapi.h"
#include "executables/softmodem-common.h"
#include "common/utils/threadPool/notified_fifo.h"
#include <readline/history.h>
#include "common/oai_version.h"
......@@ -657,7 +658,7 @@ void run_telnetsrv(void) {
fprintf(stderr,"[TELNETSRV] Error %s on listen call\n",strerror(errno));
using_history();
int plen=sprintf(prompt,"%s_%s> ",TELNET_PROMPT_PREFIX,get_softmodem_function(NULL));
int plen = sprintf(prompt, "%s_%s> ", TELNET_PROMPT_PREFIX, get_softmodem_function());
TELNET_LOG("\nInitializing telnet server...\n");
while( (telnetparams.new_socket = accept(sock, &cli_addr, &cli_len)) ) {
......@@ -746,7 +747,7 @@ void run_telnetclt(void) {
pthread_setname_np(pthread_self(), "telnetclt");
set_sched(pthread_self(),0,telnetparams.priority);
char prompt[sizeof(TELNET_PROMPT_PREFIX)+10];
sprintf(prompt,"%s_%s> ",TELNET_PROMPT_PREFIX,get_softmodem_function(NULL));
sprintf(prompt, "%s_%s> ", TELNET_PROMPT_PREFIX, get_softmodem_function());
name.sin_family = AF_INET;
struct in_addr addr;
inet_aton("127.0.0.1", &addr) ;
......@@ -883,7 +884,7 @@ int telnetsrv_autoinit(void) {
memset(&telnetparams,0,sizeof(telnetparams));
config_get(config_get_if(), telnetoptions, sizeofArray(telnetoptions), "telnetsrv");
/* possibly load a exec specific shared lib */
char *execfunc=get_softmodem_function(NULL);
char *execfunc = get_softmodem_function();
char libname[64];
sprintf(libname,"telnetsrv_%s",execfunc);
load_module_shlib(libname,NULL,0,NULL);
......
......@@ -31,8 +31,8 @@ void completed_task_ans(task_ans_t* task)
{
DevAssert(task != NULL);
if (atomic_load_explicit(&task->status, memory_order_acquire) != 0)
AssertFatal(0, "Task already finished?");
int status = atomic_load_explicit(&task->status, memory_order_acquire);
AssertFatal(status == 0, "Task not expected to be finished here. Status = %d\n", status);
atomic_store_explicit(&task->status, 1, memory_order_release);
}
......
......@@ -736,7 +736,7 @@ int websrv_callback_get_softmodemstatus(const struct _u_request *request, struct
inet_ntop(AF_INET, &(websrvparams.instance.bind_address->sin_addr), ipstr, INET_ADDRSTRLEN);
else
sprintf(ipstr, "%s", "0.0.0.0");
snprintf(srvinfo, sizeof(srvinfo) - 1, "%s:%hu %s", ipstr, websrvparams.instance.port, get_softmodem_function(NULL));
snprintf(srvinfo, sizeof(srvinfo) - 1, "%s:%hu %s", ipstr, websrvparams.instance.port, get_softmodem_function());
json_t *modemvars = json_array();
websrv_add_modeminfo(modemvars, "connected to", srvinfo, "string");
websrv_add_modeminfo(modemvars, "config_file", CONFIG_GETCONFFILE, "configfile");
......
......@@ -107,10 +107,10 @@ int websrv_scope_manager(uint64_t lcount, websrv_params_t *websrvparams)
websrv_websocket_send_scopemessage(SCOPEMSG_TYPE_TIME, strtime, websrvparams_ptr->wm);
}
if ((lcount % scope_params.refrate) == 0) {
if (IS_SOFTMODEM_GNB_BIT && (scope_params.statusmask & SCOPE_STATUSMASK_STARTED)) {
if (IS_SOFTMODEM_GNB && (scope_params.statusmask & SCOPE_STATUSMASK_STARTED)) {
phy_scope_gNB(scope_params.scopeform, scope_params.scopedata, scope_params.selectedTarget + 1 /* ue id, +1 as used in loop < limit */);
}
if (IS_SOFTMODEM_5GUE_BIT && (scope_params.statusmask & SCOPE_STATUSMASK_STARTED)) {
if (IS_SOFTMODEM_5GUE && (scope_params.statusmask & SCOPE_STATUSMASK_STARTED)) {
phy_scope_nrUE(((scopeData_t *)((PHY_VARS_NR_UE *)(scope_params.scopedata))->scopeData)->liveData,
scope_params.scopeform,
(PHY_VARS_NR_UE *)scope_params.scopedata,
......@@ -124,7 +124,7 @@ int websrv_scope_manager(uint64_t lcount, websrv_params_t *websrvparams)
/* free scope resources, as websrv scope interface can be stopped and started */
void websrv_scope_stop(void)
{
clear_softmodem_optmask(SOFTMODEM_DOSCOPE_BIT);
IS_SOFTMODEM_DOSCOPE = false;
scope_params.statusmask &= ~SCOPE_STATUSMASK_STARTED;
OAI_phy_scope_t *sp = (OAI_phy_scope_t *)scope_params.scopeform;
if (sp != NULL)
......@@ -138,7 +138,7 @@ void websrv_scope_stop(void)
char *websrv_scope_initdata(void)
{
scope_params.num_datamsg_max = 200;
if (IS_SOFTMODEM_GNB_BIT) {
if (IS_SOFTMODEM_GNB) {
scopeParms_t p;
p.ru = RC.ru[0];
p.gNB = RC.gNB[0];
......@@ -147,7 +147,7 @@ char *websrv_scope_initdata(void)
scope_params.scopeform = create_phy_scope_gnb();
scope_params.statusmask |= SCOPE_STATUSMASK_AVAILABLE;
return "gNB";
} else if (IS_SOFTMODEM_5GUE_BIT) {
} else if (IS_SOFTMODEM_5GUE) {
scope_params.scopedata = PHY_vars_UE_g[0][0];
nrUEinitScope(PHY_vars_UE_g[0][0]);
scope_params.scopeform = create_phy_scope_nrue(scope_params.selectedTarget);
......@@ -188,12 +188,12 @@ int websrv_scope_callback_set_params(const struct _u_request *request, struct _u
websrv_scope_initdata();
scope_params.statusmask |= SCOPE_STATUSMASK_STARTED;
scope_params.selectedTarget = 1; // 1 UE to be received from GUI (for xNB scope's
set_softmodem_optmask(SOFTMODEM_DOSCOPE_BIT); // to trigger data copy in scope buffers
IS_SOFTMODEM_DOSCOPE = true; // to trigger data copy in scope buffers
}
httpstatus = 200;
} else if (strcmp(vval, "stop") == 0) {
scope_params.statusmask &= ~SCOPE_STATUSMASK_STARTED;
clear_softmodem_optmask(SOFTMODEM_DOSCOPE_BIT);
IS_SOFTMODEM_DOSCOPE = false;
httpstatus = 200;
} else {
LOG_W(UTIL, "invalid startstop command value: %s\n", vval);
......@@ -232,11 +232,11 @@ int websrv_scope_callback_set_params(const struct _u_request *request, struct _u
httpstatus = 200;
} else if (strcmp(vname, "TargetSelect") == 0) {
scope_params.selectedTarget = strtol(vval, NULL, 10);
if (IS_SOFTMODEM_GNB_BIT && scope_params.selectedTarget > NUMBER_OF_UE_MAX) {
if (IS_SOFTMODEM_GNB && scope_params.selectedTarget > NUMBER_OF_UE_MAX) {
snprintf(errmsg, sizeof(errmsg) - 1, "max UE index is %d for this gNB", NUMBER_OF_UE_MAX);
httpstatus = 500;
scope_params.selectedTarget = 1;
} else if (IS_SOFTMODEM_5GUE_BIT && scope_params.selectedTarget > 0) {
} else if (IS_SOFTMODEM_5GUE && scope_params.selectedTarget > 0) {
snprintf(errmsg, sizeof(errmsg) - 1, "UE currently supports only one gNB");
httpstatus = 500;
scope_params.selectedTarget = 0;
......@@ -276,7 +276,7 @@ int websrv_scope_callback_get_desc(const struct _u_request *request, struct _u_r
char stitle[64];
websrv_scope_stop(); // in case it's not the first connection
if (IS_SOFTMODEM_DOSCOPE | IS_SOFTMODEM_ENB_BIT | IS_SOFTMODEM_4GUE_BIT) {
if (IS_SOFTMODEM_DOSCOPE | IS_SOFTMODEM_ENB | IS_SOFTMODEM_4GUE) {
strcpy(stitle, "none");
} else {
strcpy(stitle, websrv_scope_initdata());
......
......@@ -192,11 +192,16 @@ In the `MACRLCs` section of the gNB/DU configuration file:
* `identity_precoding_matrix` (default 0=false): flag to enable to use only
the identity precoding matrix in DL precoding
* `set_analog_beamforming` (default 0=false): flag to enable analog
beamforming
* `beam_duration`: duration/number of consecutive slots for a given set of
beamforming (for more information [`analog_beamforming.md`](../analog_beamforming.md))
* `beam_duration` (default 1): duration/number of consecutive slots for a given set of
beams, depending on hardware switching performance
* `beams_per_period`: set of beams that can be simultaneously allocated in a
* `beams_per_period` (default 1): set of beams that can be simultaneously allocated in a
period (`beam_duration`)
* `pusch_RSSI_Threshold`: Value between -1280 and 0 which maps to range
from -128.0 dBm/dBFS to 0.0 dBm/dBFS. This limits PUSCH TPC commands in
case RSSI reaches the threshold and prevents ADC railing. Unit depends on
RSSI reporting config.
* `pucch_RSSI_Threshold`: Same as above but for PUCCH
In the `gNBs` section of the gNB/DU configuration file: some of the parameters
affect RRC configuration (CellGroupConfig) of a UE, and are therefore listed
......
......@@ -917,6 +917,17 @@ Edit the sample OAI gNB configuration file and check following parameters:
cannot preallocate memory on NUMA nodes other than 0; in this case, set
this to 0 (no pre-allocation) and so that DPDK will allocate it on-demand
on the right NUMA node.
* `dpdk_iova_mode`: Specifies DPDK IO Virtual Address (IOVA) mode:
* `PA`: IOVA as Physical Address (PA) mode, where DPDK IOVA memory layout
corresponds directly to the physical memory layout.
* `VA`: IOVA as Virtual Address (VA) mode, where DPDK IOVA addresses do not
follow the physical memory layout. Uses IOMMU to remap physical memory.
Requires kernel support and IOMMU for address translation.
* If not specified, default value of "PA" is used (for backwards compabilibity;
it was hardcoded to PA in the past). However, we recommend using "VA" mode
as it offers several benefits. For a detailed explanation of DPDK IOVA,
including the advantages and disadvantages of each mode, refer to
[Memory in DPDK](https://www.dpdk.org/memory-in-dpdk-part-2-deep-dive-into-iova/)
* `owdm_enable`: used for eCPRI One-Way Delay Measurements; it depends if the RU supports it; if not set to 1 (enabled), default value is 0 (disabled)
* `fh_config`: parameters that need to match RU parameters
* timing parameters (starting with `T`) depend on the RU: `Tadv_cp_dl` is a
......
......@@ -84,6 +84,7 @@ Legacy unmaintained files:
- [L1 threads in NR-UE](./nr-ue-design.md)
- [Information on gNB MAC](./MAC/mac-usage.md)
- [Information on gNB RRC](./RRC/rrc-usage.md)
- [Information on analog beamforming implementation](./analog_beamforming.md)
Legacy unmaintained files:
- [`5Gnas.md`](./5Gnas.md)
......
......@@ -220,14 +220,10 @@ Calls nr_schedule_ulsch(): It is divided into the "preprocessor" and the
"postprocessor": the first makes the scheduling decisions, the second fills
nFAPI structures to indicate to the PHY what it is supposed to do. To signal
which users have how many resources, the preprocessor populates the
NR_sched_pusch_t (for values changing every TTI, e.g., frequency domain
allocation) and NR_sched_pusch_save_t (for values changing less frequently, at
least in FR1 [to my understanding], e.g., DMRS fields when the time domain
allocation stays between TTIs) structures. Furthermore, the preprocessor is an
NR_sched_pusch_t structures. Furthermore, the preprocessor is an
exchangeable module that schedules differently based on a particular
use-case/deployment type, e.g., one user for phytest [in
nr_ul_preprocessor_phytest()], multiple users in FR1
[nr_fr1_ulsch_preprocessor()], or maybe FR2 [does not exist yet]:
use-case/deployment type, e.g., one user for phytest in
[nr_ul_preprocessor_phytest()], multiple users in [nr_ulsch_preprocessor()]:
* calls preprocessor via pre_processor_ul(): the preprocessor is responsible
for allocating CCEs (using allocate_nr_CCEs()) and deciding on resource
allocation for the UEs including TB size. Note that we do not yet have
......@@ -258,8 +254,7 @@ NR_UE_sched_ctrl_t structure of affected users. In particular, the field rbSize
decides whether a user is to be allocated. Furthermore, the preprocessor is an
exchangeable module that schedules differently based on a particular
use-case/deployment type, e.g., one user for phytest [in
nr_preprocessor_phytest()], multiple users in FR1
[nr_fr1_dlsch_preprocessor()], or maybe FR2 [does not exist yet].
nr_preprocessor_phytest()], multiple users [nr_dlsch_preprocessor()].
* calls preprocessor via pre_processor_dl(): the preprocessor is responsible
for allocating CCEs and PUCCH (using allocate_nr_CCEs() and
nr_acknack_scheduling()) and deciding on the frequency/time domain
......
This document explains the implementation of analog beamforming in OAI codebase.
[[_TOC_]]
# Introduction to analog beamforming
Beamforming is a technique applied to antenna arrays to create a directional radiation pattern. This often consists in providing a different phase shift to each element of the array such that signals with a different angle of arrival/departure experience a change in radiation pattern because of constructive or destructive interference.
There are three main beamforming techinques: analog, digital and hybrid. The names refer to the phase shift application before or after the digital to analog conversion (or analog to digital in reception). When we speak about analog beamforming we generally refer to a techinique where the phase shifts that produce the beam stearing are applied by the radio unit (RU) choosing from a finite set of steering directions. The advantage of analog beamforming is a simplified analog circuitry and therefore reduced costs.
The presence of a limited number of predefined beams at RU poses constraints to the scheduler at gNB. As a matter of fact, the scheduler can serve only a limited number of beams, depending on the RU characteristics (possibly only 1), in a given time scale, that also depends on the RU characteristics (e.g. 1 slot or 1 symbol). This limitation doesn't exist for digital beamforming.
# Configuration file fields for analog beamforming
A set of parameters in configuration files controls the implementation of analog beamforming and instructs the scheduler on how to behave in such scenarios. Since most notably this technique in 5G is employed in FR2, the configuration file example currently available is a RFsim one for band 261. [Config file example](../ci-scripts/conf_files/gnb.sa.band261.u3.32prb.rfsim.conf)
In the `MACRLC` section of configuration files, there are three new parameters: `set_analog_beamforming`, `beam_duration` and `beams_per_period`. The explanation of these parameters is here provided:
- `set_analog_beamforming` can be set to 1 or 0 to activate or desactivate analog beamforming (default value is 0)
- `beam_duration` is the number of slots (currently minimum duration of a beam) the scheduler is tied to a beam (default value is 1)
- `beams_per_period` is the number of concurrent beams the RU can handle in the beam duration (default value is 1)
In the `gNBs` section of the configuration file, under the phyisical parameters, a vector field containing the set of beam indices to be provided by the OAI L1 to the RU is also required. This field is called `beam_weights`. In current implementation, the number of beam indices should be equal to the number of SSBs transmitted.
# Implementation in OAI scheduler
A new MAC structure `NR_beam_info_t` controls the behavior of the scheduler in presence of analog beamforming. Besides the already mentioned parameters `beam_duration` and `beams_per_period`, the structure also holds a matrix `beam_allocation[i][j]`, whose indices `i` and `j` stands respectively for the number of beams in the period and the slot index (the size of the latter depends on the frame characteristics).
This matrix contains the beams already allocated in a given slot, to flag the scheduler to use one of these to schedule a UE in one of these beams. If the matrix is full (all the beams in the given period, e.g. slot) are already allocated, the scheduler can't allocate a UE in a new beam.
To this goal, we extended the virtual resource block (VRB) map by one dimension to also contain information per allocated beam. As said, the scheduler can independently schedule users in a number of beams up to `beams_per_period` concurrently.
It is important to note that in current implementation, there are several periodical channels, e.g. PRACH or PUCCH for CSI et cetera, that have the precendence in being assigned a beam, that is because the scheduling is automatic, set in RRC configuration, and not up to the scheduler. For these instances, we assume the beam is available (if not there are assertions to stop the process). For data channels, the currently implemented PF scheduler is used. The only modification is that a UE can be served only if there is a free beam available or the one of the beams already in use correspond to that UE beam.
......@@ -13,7 +13,7 @@ The `UE_thread` function in `nr-ue.c` is the main top level thread that interact
The UE exits when at any point in operation it gets out of synchronization. When the command line option `--non-stop` is used, the UE goes to 'Initial Synchronization' mode when it loses synchronization with gNB. However, this feature is not fully implemented and it is a work in progress at the time of writing this documentation. This will be the default behavior (not a command line option) when the feature is fully implemented.
UE uses actors which are threads dedicated to particular activity. Sync Actor handles initial sync. DL Actors handle DLSCH PHY procedures. UL procedures are processed directly on the threadpool
UE uses actors which are threads dedicated to particular activity. Sync Actor handles initial sync. DL Actors handle DLSCH PHY procedures. UL procedures are are run on the UL Actor
![design](nr-ue-threads.svg)
......
This source diff could not be displayed because it is too large. You can view the blob instead.
......@@ -88,7 +88,7 @@ gNBs =
#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
#one (0..15) 4,8,12,16,...60,64
ssb_perRACH_OccasionAndCB_PreamblesPerSSB = 14; //15;
#ra_ContentionResolutionTimer
#(0..7) 8,16,24,32,40,48,56,64
......
......@@ -146,6 +146,9 @@ on DPDK:
- `IPC_LOCK` (becomes mandatory with DPDK)
- `SYS_RESOURCE`
- `NET_RAW`
- `SYS_ADMIN`: This is required by DPDK when using IOVA PA (Physical Address)
mode to read `/proc/self/pagemaps`. However, if DPDK EAL is configured to use
IOVA VA (Virtual Address) mode, this capability is no longer required.
## Capabilities with UHD
......
......@@ -71,7 +71,7 @@ RUN /bin/sh oaienv && \
--gNB \
--build-lib "telnetsrv enbscope uescope nrscope" \
-t oran_fhlib_5g --cmake-opt -Dxran_LOCATION=/opt/phy/fhi_lib/lib \
--build-e2 --cmake-opt -DXAPP_MULTILANGUAGE=OFF --cmake-opt -DKPM_VERSION=$KPM_VERSION --cmake-opt -DE2AP_VERSION=$E2AP_VERSION && \
--build-e2 --cmake-opt -DXAPP_MULTILANGUAGE=OFF --cmake-opt -DKPM_VERSION=$KPM_VERSION --cmake-opt -DE2AP_VERSION=$E2AP_VERSION \
$BUILD_OPTION && \
# Mainly to see if the sanitize option was perfectly executed
ldd ran_build/build/nr-softmodem && \
......
......@@ -44,28 +44,17 @@
#define _GNU_SOURCE
#include <pthread.h>
#undef MALLOC //there are two conflicting definitions, so we better make sure we don't use it at all
#include "assertions.h"
#include "PHY/types.h"
#include "PHY/INIT/phy_init.h"
#include "PHY/defs_eNB.h"
#include "SCHED/sched_eNB.h"
#include "PHY/LTE_TRANSPORT/transport_proto.h"
#include "nfapi/oai_integration/vendor_ext.h"
#undef MALLOC //there are two conflicting definitions, so we better make sure we don't use it at all
//#undef FRAME_LENGTH_COMPLEX_SAMPLES //there are two conflicting definitions, so we better make sure we don't use it at all
#include "radio/COMMON/common_lib.h"
//#undef FRAME_LENGTH_COMPLEX_SAMPLES //there are two conflicting definitions, so we better make sure we don't use it at all
#include "PHY/LTE_TRANSPORT/if4_tools.h"
#include "PHY/LTE_ESTIMATION/lte_estimation.h"
......@@ -102,8 +91,6 @@ struct timing_info_t {
// Fix per CC openair rf/if device update
extern int oai_exit;
extern int transmission_mode;
#include "executables/thread-common.h"
......@@ -927,7 +914,7 @@ void init_eNB_proc(int inst) {
if (cpu_meas_enabled)
threadCreate(&proc->process_stats_thread, process_stats_thread, (void *)eNB, "opp stats", -1, sched_get_priority_min(SCHED_OAI));
if (!IS_SOFTMODEM_NOSTATS_BIT)
if (!IS_SOFTMODEM_NOSTATS)
threadCreate(&proc->L1_stats_thread, L1_stats_thread, (void *)eNB, "L1 stats", -1, sched_get_priority_min(SCHED_OAI));
}
......
......@@ -45,8 +45,6 @@
#include <getopt.h>
#include <sys/sysinfo.h>
#undef MALLOC //there are two conflicting definitions, so we better make sure we don't use it at all
#include "assertions.h"
#include "PHY/defs_common.h"
#include "PHY/types.h"
......@@ -78,7 +76,6 @@ static int DEFRUTPCORES[] = {2,4,6,8};
#define MBMS_EXPERIMENTAL
extern int oai_exit;
extern clock_source_t clock_source;
#include "executables/thread-common.h"
//extern PARALLEL_CONF_t get_thread_parallel_conf(void);
......
......@@ -33,9 +33,6 @@
#define _GNU_SOURCE /* See feature_test_macros(7) */
#include <sched.h>
#undef MALLOC //there are two conflicting definitions, so we better make sure we don't use it at all
#include "assertions.h"
#include "common/oai_version.h"
......@@ -45,14 +42,9 @@
#include "common/ran_context.h"
#include "common/config/config_userapi.h"
#include "common/utils/load_module_shlib.h"
#undef MALLOC //there are two conflicting definitions, so we better make sure we don't use it at all
//#undef FRAME_LENGTH_COMPLEX_SAMPLES //there are two conflicting definitions, so we better make sure we don't use it at all
#include "radio/COMMON/common_lib.h"
#include "radio/ETHERNET/if_defs.h"
//#undef FRAME_LENGTH_COMPLEX_SAMPLES //there are two conflicting definitions, so we better make sure we don't use it at all
#include <openair1/PHY/phy_extern_ue.h>
#include "PHY/phy_vars.h"
......@@ -297,7 +289,8 @@ void exit_function(const char *file, const char *function, const int line, const
static void get_options(configmodule_interface_t *cfg)
{
CONFIG_SETRTFLAG(CONFIG_NOEXITONHELP);
get_common_options(cfg, SOFTMODEM_ENB_BIT);
IS_SOFTMODEM_ENB = true;
get_common_options(cfg);
CONFIG_CLEARRTFLAG(CONFIG_NOEXITONHELP);
if ( !(CONFIG_ISFLAGSET(CONFIG_ABORT)) ) {
......
......@@ -20,7 +20,6 @@
#include <sys/types.h>
#include <unistd.h>
#include "radio/COMMON/common_lib.h"
//#undef MALLOC
#include "assertions.h"
#include "PHY/types.h"
#include "PHY/defs_eNB.h"
......@@ -121,9 +120,6 @@ extern uint64_t downlink_frequency[MAX_NUM_CCs][4];
extern int32_t uplink_frequency_offset[MAX_NUM_CCs][4];
extern int rx_input_level_dBm;
extern int oai_exit;
extern openair0_config_t openair0_cfg[MAX_CARDS];
extern pthread_cond_t sync_cond;
extern pthread_mutex_t sync_mutex;
......
......@@ -41,9 +41,6 @@
#include "PHY/MODULATION/modulation_UE.h"
#include "PHY/LTE_ESTIMATION/lte_estimation.h"
#undef MALLOC //there are two conflicting definitions, so we better make sure we don't use it at all
//#undef FRAME_LENGTH_COMPLEX_SAMPLES //there are two conflicting definitions, so we better make sure we don't use it at all
#include "PHY/phy_extern_ue.h"
#include "LAYER2/MAC/mac_extern.h"
#include "LAYER2/MAC/mac_proto.h"
......@@ -82,7 +79,7 @@ void *UE_thread(void *arg);
int init_timer_thread(void);
int tx_req_num_elems;
extern uint16_t sf_ahead;
extern int sf_ahead;
//extern int tx_req_UE_MAC1();
void ue_stub_rx_handler(unsigned int, char *);
......
......@@ -33,9 +33,6 @@
#define _GNU_SOURCE /* See feature_test_macros(7) */
#include <sched.h>
#undef MALLOC //there are two conflicting definitions, so we better make sure we don't use it at all
#include "assertions.h"
#include "PHY/types.h"
......@@ -46,14 +43,9 @@
#include "common/ran_context.h"
#include "common/config/config_userapi.h"
#include "common/utils/load_module_shlib.h"
#undef MALLOC //there are two conflicting definitions, so we better make sure we don't use it at all
//#undef FRAME_LENGTH_COMPLEX_SAMPLES //there are two conflicting definitions, so we better make sure we don't use it at all
#include "radio/COMMON/common_lib.h"
#include "radio/ETHERNET/if_defs.h"
//#undef FRAME_LENGTH_COMPLEX_SAMPLES //there are two conflicting definitions, so we better make sure we don't use it at all
#include "PHY/phy_vars_ue.h"
#include "PHY/LTE_TRANSPORT/transport_vars.h"
......@@ -81,8 +73,7 @@ pthread_cond_t nfapi_sync_cond;
pthread_mutex_t nfapi_sync_mutex;
int nfapi_sync_var=-1; //!< protected by mutex \ref nfapi_sync_mutex
uint16_t sf_ahead=4;
int sf_ahead = 4;
int tddflag;
char *emul_iface;
......@@ -274,7 +265,8 @@ static void get_options(configmodule_interface_t *cfg)
CONFIG_SETRTFLAG(CONFIG_NOEXITONHELP);
/* unknown parameters on command line will be checked in main
after all init have been performed */
get_common_options(cfg, SOFTMODEM_4GUE_BIT);
IS_SOFTMODEM_4GUE = true;
get_common_options(cfg);
paramdef_t cmdline_uemodeparams[] =CMDLINE_UEMODEPARAMS_DESC;
paramdef_t cmdline_ueparams[] =CMDLINE_UEPARAMS_DESC;
config_process_cmdline(cfg, cmdline_uemodeparams, sizeofArray(cmdline_uemodeparams), NULL);
......
......@@ -75,7 +75,7 @@ int sync_var=-1; //!< protected by mutex \ref sync_mutex.
int config_sync_var=-1;
int oai_exit = 0;
uint16_t sf_ahead = 4;
int sf_ahead = 4;
RU_t ru_m;
......@@ -119,7 +119,8 @@ void exit_function(const char *file, const char *function, const int line, const
static void get_options(configmodule_interface_t *cfg)
{
CONFIG_SETRTFLAG(CONFIG_NOEXITONHELP);
get_common_options(cfg, SOFTMODEM_ENB_BIT);
IS_SOFTMODEM_ENB = true;
get_common_options(cfg);
CONFIG_CLEARRTFLAG(CONFIG_NOEXITONHELP);
// RCConfig();
......
......@@ -33,8 +33,6 @@
#define _GNU_SOURCE
#include <pthread.h>
#undef MALLOC //there are two conflicting definitions, so we better make sure we don't use it at all
#include "assertions.h"
#include <common/utils/LOG/log.h>
#include <common/utils/system.h>
......@@ -54,13 +52,7 @@
#include "LAYER2/NR_MAC_COMMON/nr_mac_extern.h"
#include "LAYER2/NR_MAC_gNB/mac_proto.h"
#undef MALLOC //there are two conflicting definitions, so we better make sure we don't use it at all
//#undef FRAME_LENGTH_COMPLEX_SAMPLES //there are two conflicting definitions, so we better make sure we don't use it at all
#include "radio/COMMON/common_lib.h"
//#undef FRAME_LENGTH_COMPLEX_SAMPLES //there are two conflicting definitions, so we better make sure we don't use it at all
#include "PHY/LTE_TRANSPORT/if4_tools.h"
#include "PHY/phy_extern.h"
......@@ -220,10 +212,10 @@ static void rx_func(processingData_L1_t *info)
LOG_D(NR_PHY, "%d.%d Starting RX processing\n", frame_rx, slot_rx);
// UE-specific RX processing for subframe n
// TODO: check if this is correct for PARALLEL_RU_L1_TRX_SPLIT
NR_UL_IND_t UL_INFO = {.frame = frame_rx, .slot = slot_rx, .module_id = gNB->Mod_id, .CC_id = gNB->CC_id};
// Do PRACH RU processing
L1_nr_prach_procedures(gNB,frame_rx,slot_rx);
UL_INFO.rach_ind.pdu_list = UL_INFO.prach_pdu_indication_list;
L1_nr_prach_procedures(gNB, frame_rx, slot_rx, &UL_INFO.rach_ind);
//WA: comment rotation in tx/rx
if (gNB->phase_comp) {
......@@ -242,15 +234,11 @@ static void rx_func(processingData_L1_t *info)
}
}
}
phy_procedures_gNB_uespec_RX(gNB, frame_rx, slot_rx);
phy_procedures_gNB_uespec_RX(gNB, frame_rx, slot_rx, &UL_INFO);
// Call the scheduler
start_meas(&gNB->ul_indication_stats);
gNB->UL_INFO.frame = frame_rx;
gNB->UL_INFO.slot = slot_rx;
gNB->UL_INFO.module_id = gNB->Mod_id;
gNB->UL_INFO.CC_id = gNB->CC_id;
gNB->if_inst->NR_UL_indication(&gNB->UL_INFO);
gNB->if_inst->NR_UL_indication(&UL_INFO);
stop_meas(&gNB->ul_indication_stats);
#ifndef OAI_FHI72
......@@ -376,9 +364,9 @@ void init_gNB_Tpool(int inst) {
// this will be removed when the msgDataTx is not necessary anymore
gNB->msgDataTx = msgDataTx;
if ((!get_softmodem_params()->emulate_l1) && (!IS_SOFTMODEM_NOSTATS_BIT) && (NFAPI_MODE!=NFAPI_MODE_VNF) && (NFAPI_MODE != NFAPI_MODE_AERIAL))
threadCreate(&proc->L1_stats_thread,nrL1_stats_thread,(void*)gNB,"L1_stats",-1,OAI_PRIORITY_RT_LOW);
if ((!get_softmodem_params()->emulate_l1) && (!IS_SOFTMODEM_NOSTATS) && (NFAPI_MODE != NFAPI_MODE_VNF)
&& (NFAPI_MODE != NFAPI_MODE_AERIAL))
threadCreate(&proc->L1_stats_thread, nrL1_stats_thread, (void *)gNB, "L1_stats", -1, OAI_PRIORITY_RT_LOW);
}
void term_gNB_Tpool(int inst) {
......@@ -462,17 +450,11 @@ void init_gNB()
// Register MAC interface module
AssertFatal((gNB->if_inst = NR_IF_Module_init(inst)) != NULL, "Cannot register interface");
LOG_I(NR_PHY, "Registered with MAC interface module (%p)\n", gNB->if_inst);
// Set function pointers in MAC IF module
LOG_I(NR_PHY, "Registered with MAC interface module (%p)\n", gNB->if_inst);
gNB->if_inst->NR_Schedule_response = nr_schedule_response;
gNB->if_inst->NR_PHY_config_req = nr_phy_config_request;
// Clear UL_INFO and set rx/crc indication lists
memset((void *)&gNB->UL_INFO, 0, sizeof(gNB->UL_INFO));
gNB->UL_INFO.rx_ind.pdu_list = gNB->rx_pdu_list;
gNB->UL_INFO.crc_ind.crc_list = gNB->crc_pdu_list;
gNB->prach_energy_counter = 0;
gNB->chest_time = get_softmodem_params()->chest_time;
gNB->chest_freq = get_softmodem_params()->chest_freq;
......
......@@ -29,8 +29,6 @@
#include <sys/sysinfo.h>
#include <math.h>
#undef MALLOC //there are two conflicting definitions, so we better make sure we don't use it at all
#include "common/utils/nr/nr_common.h"
#include "common/utils/assertions.h"
#include "common/utils/system.h"
......@@ -71,7 +69,7 @@ static int DEFRUTPCORES[] = {-1,-1,-1,-1};
#include <nfapi/oai_integration/vendor_ext.h>
#include "executables/nr-softmodem-common.h"
uint16_t sl_ahead;
int sl_ahead;
static void NRRCconfig_RU(configmodule_interface_t *cfg);
/*************************************************************/
......
......@@ -25,7 +25,6 @@
#include <sys/sysinfo.h>
#include "radio/COMMON/common_lib.h"
#undef MALLOC
#include "assertions.h"
#include "PHY/types.h"
......
......@@ -82,7 +82,6 @@ unsigned short config_frames[4] = {2,9,11,13};
#include "radio/COMMON/common_lib.h"
#include "s1ap_eNB.h"
#include "sctp_eNB_task.h"
#include "softmodem-bits.h"
#include "system.h"
#include "time_meas.h"
#include "utils.h"
......@@ -350,7 +349,8 @@ static void get_options(configmodule_interface_t *cfg)
{
paramdef_t cmdline_params[] = CMDLINE_PARAMS_DESC_GNB ;
CONFIG_SETRTFLAG(CONFIG_NOEXITONHELP);
get_common_options(cfg, SOFTMODEM_GNB_BIT);
IS_SOFTMODEM_GNB = true;
get_common_options(cfg);
config_process_cmdline(cfg, cmdline_params, sizeofArray(cmdline_params), NULL);
CONFIG_CLEARRTFLAG(CONFIG_NOEXITONHELP);
}
......
......@@ -103,10 +103,9 @@
static void *NRUE_phy_stub_standalone_pnf_task(void *arg);
static void start_process_slot_tx(void* arg) {
task_t task;
task.args = arg;
task.func = processSlotTX;
pushTpool(&(get_nrUE_params()->Tpool), task);
notifiedFIFO_elt_t *newTx = arg;
nr_rxtx_thread_data_t *curMsgTx = NotifiedFifoData(newTx);
pushNotifiedFIFO(&curMsgTx->UE->ul_actor.fifo, newTx);
}
static size_t dump_L1_UE_meas_stats(PHY_VARS_NR_UE *ue, char *output, size_t max_len)
......@@ -563,13 +562,7 @@ void processSlotTX(void *arg)
phy_procedures_nrUE_TX(UE, proc, &phy_data);
}
}
int slots_per_frame = (UE->sl_mode == 2) ? UE->SL_UE_PHY_PARAMS.sl_frame_params.slots_per_frame
: UE->frame_parms.slots_per_frame;
int next_slot_and_frame = proc->nr_slot_tx + 1 + proc->nr_slot_tx_offset + proc->frame_tx * slots_per_frame;
dynamic_barrier_join(&UE->process_slot_tx_barriers[next_slot_and_frame % NUM_PROCESS_SLOT_TX_BARRIERS]);
RU_write(rxtxD, sl_tx_action);
free(rxtxD);
TracyCZoneEnd(ctx);
}
......@@ -609,7 +602,7 @@ static int handle_sync_req_from_mac(PHY_VARS_NR_UE *UE)
for (int i = 0; i < NUM_DL_ACTORS; i++) {
flush_actor(UE->dl_actors + i);
}
/*TODO: Flush UL jobs */
flush_actor(&UE->ul_actor);
clean_UE_harq(UE);
UE->is_synchronized = 0;
......@@ -631,6 +624,14 @@ static int UE_dl_preprocessing(PHY_VARS_NR_UE *UE,
if (UE->sl_mode == 2)
fp = &UE->SL_UE_PHY_PARAMS.sl_frame_params;
// process what RRC thread sent to MAC
MessageDef *msg = NULL;
do {
itti_poll_msg(TASK_MAC_UE, &msg);
if (msg)
process_msg_rcc_to_mac(msg);
} while (msg);
if (IS_SOFTMODEM_NOS1 || IS_SA_MODE(get_softmodem_params())) {
/* send tick to RLC and PDCP every ms */
if (proc->nr_slot_rx % fp->slots_per_subframe == 0) {
......@@ -875,10 +876,18 @@ void *UE_thread(void *arg)
syncRunning = false;
if (UE->is_synchronized) {
UE->synch_request.received_synch_request = 0;
if (UE->sl_mode == 2)
if (UE->sl_mode == SL_MODE2_SUPPORTED)
decoded_frame_rx = UE->SL_UE_PHY_PARAMS.sync_params.DFN;
else
else {
// We must wait the RRC layer decoded the MIB and sent us the frame number
MessageDef *msg = NULL;
itti_receive_msg(TASK_MAC_UE, &msg);
if (msg)
process_msg_rcc_to_mac(msg);
else
LOG_E(PHY, "It seems we arbort while trying to sync\n");
decoded_frame_rx = mac->mib_frame;
}
LOG_A(PHY,
"UE synchronized! decoded_frame_rx=%d UE->init_sync_frame=%d trashed_frames=%d\n",
decoded_frame_rx,
......@@ -1082,22 +1091,22 @@ void *UE_thread(void *arg)
// Start TX slot processing here. It runs in parallel with RX slot processing
// in current code, DURATION_RX_TO_TX constant is the limit to get UL data to encode from a RX slot
nr_rxtx_thread_data_t *curMsgTx = calloc(1, sizeof(*curMsgTx));
notifiedFIFO_elt_t *newTx = newNotifiedFIFO_elt(sizeof(nr_rxtx_thread_data_t), 0, 0, processSlotTX);
nr_rxtx_thread_data_t *curMsgTx = NotifiedFifoData(newTx);
memset(curMsgTx, 0, sizeof(*curMsgTx));
curMsgTx->proc = curMsg.proc;
curMsgTx->writeBlockSize = writeBlockSize;
curMsgTx->proc.timestamp_tx = writeTimestamp;
curMsgTx->UE = UE;
curMsgTx->stream_status = stream_status;
curMsgTx->proc.nr_slot_tx_offset = nr_slot_tx_offset;
int sync_to_previous_thread = stream_status == STREAM_STATUS_SYNCED ? 1 : 0;
int slot = curMsgTx->proc.nr_slot_tx;
int slot_and_frame = slot + curMsgTx->proc.frame_tx * UE->frame_parms.slots_per_frame;
dynamic_barrier_update(&UE->process_slot_tx_barriers[slot_and_frame % NUM_PROCESS_SLOT_TX_BARRIERS],
tx_wait_for_dlsch[slot] + sync_to_previous_thread,
tx_wait_for_dlsch[slot],
start_process_slot_tx,
curMsgTx);
newTx);
stream_status = STREAM_STATUS_SYNCED;
tx_wait_for_dlsch[slot] = 0;
// apply new duration next run to avoid thread dead lock
......@@ -1133,7 +1142,7 @@ void init_NR_UE_threads(PHY_VARS_NR_UE *UE) {
char thread_name[16];
sprintf(thread_name, "UEthread_%d", UE->Mod_id);
threadCreate(&thread, UE_thread, (void *)UE, thread_name, -1, OAI_PRIORITY_RT_MAX);
if (!IS_SOFTMODEM_NOSTATS_BIT) {
if (!IS_SOFTMODEM_NOSTATS) {
pthread_t stat_pthread;
sprintf(thread_name, "L1_UE_stats_%d", UE->Mod_id);
threadCreate(&stat_pthread, nrL1_UE_stats_thread, UE, thread_name, -1, OAI_PRIORITY_RT_LOW);
......
......@@ -52,6 +52,7 @@
#include "PHY_INTERFACE/phy_interface_vars.h"
#include "NR_IF_Module.h"
#include "openair1/SIMULATION/TOOLS/sim.h"
#include "openair2/RRC/NR_UE/L2_interface_ue.h"
#ifdef SMBV
#include "PHY/TOOLS/smbv.h"
......@@ -98,7 +99,7 @@ nrUE_params_t nrUE_params = {0};
pthread_cond_t nfapi_sync_cond;
pthread_mutex_t nfapi_sync_mutex;
int nfapi_sync_var=-1; //!< protected by mutex \ref nfapi_sync_mutex
uint16_t sf_ahead=6; //??? value ???
int sf_ahead = 6; //??? value ???
pthread_cond_t sync_cond;
pthread_mutex_t sync_mutex;
int sync_var=-1; //!< protected by mutex \ref sync_mutex.
......@@ -403,8 +404,8 @@ int main(int argc, char **argv)
// get options and fill parameters from configuration file
get_options(uniqCfg); // Command-line options specific for NRUE
get_common_options(uniqCfg, SOFTMODEM_5GUE_BIT);
IS_SOFTMODEM_5GUE = true;
get_common_options(uniqCfg);
CONFIG_CLEARRTFLAG(CONFIG_NOEXITONHELP);
softmodem_verify_mode(get_softmodem_params());
......@@ -488,6 +489,12 @@ int main(int argc, char **argv)
get_softmodem_params()->numerology,
nr_band);
} else {
MessageDef *msg = NULL;
do {
itti_poll_msg(TASK_MAC_UE, &msg);
if (msg)
process_msg_rcc_to_mac(msg);
} while (msg);
fapi_nr_config_request_t *nrUE_config = &UE[CC_id]->nrUE_config;
nr_init_frame_parms_ue(&UE[CC_id]->frame_parms, nrUE_config, mac->nr_band);
}
......@@ -497,6 +504,7 @@ int main(int argc, char **argv)
for (int i = 0; i < NUM_DL_ACTORS; i++) {
init_actor(&UE[CC_id]->dl_actors[i], "DL_", -1);
}
init_actor(&UE[CC_id]->ul_actor, "UL_", -1);
init_nr_ue_vars(UE[CC_id], inst);
if (UE[CC_id]->sl_mode) {
......
......@@ -43,16 +43,11 @@
#include <getopt.h>
#include <sys/sysinfo.h>
#undef MALLOC //there are two conflicting definitions, so we better make sure we don't use it at all
#include "assertions.h"
#include "PHY/types.h"
#include "PHY/defs_common.h"
#undef MALLOC //there are two conflicting definitions, so we better make sure we don't use it at all
#include "radio/COMMON/common_lib.h"
#include "radio/ETHERNET/ethernet_lib.h"
......@@ -79,7 +74,6 @@ const char rru_format_options[4][20] = {"OAI_IF5_only","OAI_IF4p5_only","OAI_IF5
const char rru_formats[3][20] = {"OAI_IF5","MBP_IF5","OAI_IF4p5"};
const char ru_if_formats[4][20] = {"LOCAL_RF","REMOTE_OAI_IF5","REMOTE_MBP_IF5","REMOTE_OAI_IF4p5"};
extern int oai_exit;
extern void wait_eNBs(void);
int send_tick(RU_t *ru)
......
/*
* Licensed to the OpenAirInterface (OAI) Software Alliance under one or more
* contributor license agreements. See the NOTICE file distributed with
* this work for additional information regarding copyright ownership.
* The OpenAirInterface Software Alliance licenses this file to You under
* the OAI Public License, Version 1.1 (the "License"); you may not use this file
* except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.openairinterface.org/?page_id=698
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*-------------------------------------------------------------------------------
* For more information about the OpenAirInterface (OAI) Software Alliance:
* contact@openairinterface.org
*/
#ifndef SOFTMODEM_BITS_H
#define SOFTMODEM_BITS_H
// clang-format off
#define BIT_0 (1 << 0)
#define BIT_1 (1 << 1)
#define BIT_2 (1 << 2)
#define BIT_10 (1 << 10)
#define BIT_12 (1 << 12)
#define BIT_13 (1 << 13)
#define BIT_15 (1 << 15)
#define BIT_16 (1 << 16)
#define BIT_17 (1 << 17)
#define BIT_18 (1 << 18)
#define BIT_20 (1 << 20)
#define BIT_21 (1 << 21)
#define BIT_22 (1 << 22)
#define BIT_23 (1 << 23)
#define BIT_24 (1 << 24)
#define BIT_25 (1 << 25)
#define SOFTMODEM_NOS1_BIT BIT_0
#define SOFTMODEM_NOKRNMOD_BIT BIT_1
#define SOFTMODEM_NONBIOT_BIT BIT_2
#define SOFTMODEM_RFSIM_BIT BIT_10
#define SOFTMODEM_SIML1_BIT BIT_12
#define SOFTMODEM_DLSIM_BIT BIT_13
#define SOFTMODEM_DOSCOPE_BIT BIT_15
#define SOFTMODEM_RECPLAY_BIT BIT_16
#define SOFTMODEM_TELNETCLT_BIT BIT_17
#define SOFTMODEM_RECRECORD_BIT BIT_18
#define SOFTMODEM_ENB_BIT BIT_20
#define SOFTMODEM_GNB_BIT BIT_21
#define SOFTMODEM_4GUE_BIT BIT_22
#define SOFTMODEM_5GUE_BIT BIT_23
#define SOFTMODEM_NOSTATS_BIT BIT_24
#define SOFTMODEM_IMSCOPE_BIT BIT_25
// clang-format on
#endif // SOFTMODEM_BITS_H
......@@ -41,55 +41,33 @@
#include "softmodem-common.h"
#include "nfapi/oai_integration/vendor_ext.h"
static softmodem_params_t softmodem_params;
char *parallel_config=NULL;
char *worker_config=NULL;
int usrp_tx_thread = 0;
uint8_t nfapi_mode=0;
static mapping softmodem_funcs[] = MAPPING_SOFTMODEM_FUNCTIONS;
static struct timespec start;
uint64_t get_softmodem_optmask(void) {
return softmodem_params.optmask;
}
uint64_t set_softmodem_optmask(uint64_t bitmask) {
softmodem_params.optmask = softmodem_params.optmask | bitmask;
return softmodem_params.optmask;
}
uint64_t clear_softmodem_optmask(uint64_t bitmask)
{
softmodem_params.optmask = softmodem_params.optmask & (~bitmask);
return softmodem_params.optmask;
}
static softmodem_params_t softmodem_params;
softmodem_params_t *get_softmodem_params(void) {
return &softmodem_params;
}
int32_t check_execmask(uint64_t execmask) {
char *softmodemfunc=map_int_to_str(softmodem_funcs, execmask);
if (softmodemfunc != NULL) {
set_softmodem_optmask(execmask);
return 0;
}
return -1;
}
char *get_softmodem_function(uint64_t *sofmodemfunc_mask_ptr) {
uint64_t fmask=(get_softmodem_optmask()&SOFTMODEM_FUNC_BITS);
char *softmodemfunc=map_int_to_str(softmodem_funcs, fmask);
if (sofmodemfunc_mask_ptr != NULL)
*sofmodemfunc_mask_ptr=fmask;
if (softmodemfunc != NULL) {
return softmodemfunc;
}
char *get_softmodem_function(void)
{
optmask_t fmask = *get_softmodem_optmask();
if (fmask.bit.SOFTMODEM_ENB_BIT)
return "enb";
if (fmask.bit.SOFTMODEM_GNB_BIT)
return "gnb";
if (fmask.bit.SOFTMODEM_4GUE_BIT)
return "4Gue";
if (fmask.bit.SOFTMODEM_5GUE_BIT)
return "5Gue";
return "???";
}
void get_common_options(configmodule_interface_t *cfg, uint32_t execmask)
void get_common_options(configmodule_interface_t *cfg)
{
int32_t stats_disabled = 0;
uint32_t online_log_messages=0;
......@@ -101,7 +79,6 @@ void get_common_options(configmodule_interface_t *cfg, uint32_t execmask)
uint32_t enable_imscope = 0;
int nfapi_index = 0;
char *logmem_filename = NULL;
check_execmask(execmask);
paramdef_t cmdline_params[] = CMDLINE_PARAMS_DESC;
checkedparam_t cmdline_CheckParams[] = CMDLINE_PARAMS_CHECK_DESC;
......@@ -136,7 +113,7 @@ void get_common_options(configmodule_interface_t *cfg, uint32_t execmask)
}
if (start_telnetclt) {
set_softmodem_optmask(SOFTMODEM_TELNETCLT_BIT);
IS_SOFTMODEM_TELNETCLT = true;
}
if (logmem_filename != NULL && strlen(logmem_filename) > 0) {
......@@ -145,23 +122,23 @@ void get_common_options(configmodule_interface_t *cfg, uint32_t execmask)
}
if (noS1) {
set_softmodem_optmask(SOFTMODEM_NOS1_BIT);
IS_SOFTMODEM_NOS1 = true;
}
if (nonbiot) {
set_softmodem_optmask(SOFTMODEM_NONBIOT_BIT);
IS_SOFTMODEM_NONBIOT = true;
}
if (rfsim) {
set_softmodem_optmask(SOFTMODEM_RFSIM_BIT);
IS_SOFTMODEM_RFSIM = true;
}
if (do_forms) {
set_softmodem_optmask(SOFTMODEM_DOSCOPE_BIT);
IS_SOFTMODEM_DOSCOPE = true;
}
if (enable_imscope) {
set_softmodem_optmask(SOFTMODEM_IMSCOPE_BIT);
IS_SOFTMODEM_IMSCOPE_ENABLED = true;
}
if (start_websrv) {
......@@ -173,7 +150,7 @@ void get_common_options(configmodule_interface_t *cfg, uint32_t execmask)
if(worker_config != NULL) set_worker_conf(worker_config);
nfapi_setmode(nfapi_mode);
if (stats_disabled)
set_softmodem_optmask(SOFTMODEM_NOSTATS_BIT);
IS_SOFTMODEM_NOSTATS = true;
}
void softmodem_verify_mode(const softmodem_params_t *p)
......
......@@ -31,12 +31,14 @@
*/
#ifndef SOFTMODEM_COMMON_H
#define SOFTMODEM_COMMON_H
#include "openair1/PHY/defs_common.h"
#include "softmodem-bits.h"
#ifdef __cplusplus
extern "C"
{
#endif
#include <stdint.h>
#include "common/config/config_load_configmodule.h"
/* help strings definition for command line options, used in CMDLINE_XXX_DESC macros and printed when -h option is used */
#define CONFIG_HLP_RFCFGF "Configuration file for front-end (e.g. LMS7002M)\n"
#define CONFIG_HLP_SPLIT73 "Split 7.3 (below rate matching) option: <cu|du>:<remote ip address>:<remote port>\n"
......@@ -268,28 +270,46 @@ extern int usrp_tx_thread;
/***************************************************************************************************************************************/
#define SOFTMODEM_FUNC_BITS (SOFTMODEM_ENB_BIT | SOFTMODEM_GNB_BIT | SOFTMODEM_5GUE_BIT | SOFTMODEM_4GUE_BIT)
#define MAPPING_SOFTMODEM_FUNCTIONS {{"enb",SOFTMODEM_ENB_BIT},{"gnb",SOFTMODEM_GNB_BIT},{"4Gue",SOFTMODEM_4GUE_BIT},{"5Gue",SOFTMODEM_5GUE_BIT}}
#define IS_SOFTMODEM_NOS1 ( get_softmodem_optmask() & SOFTMODEM_NOS1_BIT)
#define IS_SOFTMODEM_NONBIOT ( get_softmodem_optmask() & SOFTMODEM_NONBIOT_BIT)
#define IS_SOFTMODEM_RFSIM ( get_softmodem_optmask() & SOFTMODEM_RFSIM_BIT)
#define IS_SOFTMODEM_SIML1 ( get_softmodem_optmask() & SOFTMODEM_SIML1_BIT)
#define IS_SOFTMODEM_DLSIM ( get_softmodem_optmask() & SOFTMODEM_DLSIM_BIT)
#define IS_SOFTMODEM_DOSCOPE ( get_softmodem_optmask() & SOFTMODEM_DOSCOPE_BIT)
#define IS_SOFTMODEM_IQPLAYER ( get_softmodem_optmask() & SOFTMODEM_RECPLAY_BIT)
#define IS_SOFTMODEM_IQRECORDER ( get_softmodem_optmask() & SOFTMODEM_RECRECORD_BIT)
#define IS_SOFTMODEM_TELNETCLT_BIT ( get_softmodem_optmask() & SOFTMODEM_TELNETCLT_BIT)
#define IS_SOFTMODEM_ENB_BIT ( get_softmodem_optmask() & SOFTMODEM_ENB_BIT)
#define IS_SOFTMODEM_GNB_BIT ( get_softmodem_optmask() & SOFTMODEM_GNB_BIT)
#define IS_SOFTMODEM_4GUE_BIT ( get_softmodem_optmask() & SOFTMODEM_4GUE_BIT)
#define IS_SOFTMODEM_5GUE_BIT ( get_softmodem_optmask() & SOFTMODEM_5GUE_BIT)
#define IS_SOFTMODEM_NOSTATS_BIT ( get_softmodem_optmask() & SOFTMODEM_NOSTATS_BIT)
#define IS_SOFTMODEM_IMSCOPE_ENABLED ( get_softmodem_optmask() & SOFTMODEM_IMSCOPE_BIT)
#define IS_SOFTMODEM_NOS1 (get_softmodem_optmask()->bit.SOFTMODEM_NOS1_BIT)
#define IS_SOFTMODEM_NONBIOT (get_softmodem_optmask()->bit.SOFTMODEM_NONBIOT_BIT)
#define IS_SOFTMODEM_RFSIM (get_softmodem_optmask()->bit.SOFTMODEM_RFSIM_BIT)
#define IS_SOFTMODEM_SIML1 (get_softmodem_optmask()->bit.SOFTMODEM_SIML1_BIT)
#define IS_SOFTMODEM_DLSIM (get_softmodem_optmask()->bit.SOFTMODEM_DLSIM_BIT)
#define IS_SOFTMODEM_DOSCOPE (get_softmodem_optmask()->bit.SOFTMODEM_DOSCOPE_BIT)
#define IS_SOFTMODEM_IQPLAYER (get_softmodem_optmask()->bit.SOFTMODEM_RECPLAY_BIT)
#define IS_SOFTMODEM_IQRECORDER (get_softmodem_optmask()->bit.SOFTMODEM_RECRECORD_BIT)
#define IS_SOFTMODEM_TELNETCLT (get_softmodem_optmask()->bit.SOFTMODEM_TELNETCLT_BIT)
#define IS_SOFTMODEM_ENB (get_softmodem_optmask()->bit.SOFTMODEM_ENB_BIT)
#define IS_SOFTMODEM_GNB (get_softmodem_optmask()->bit.SOFTMODEM_GNB_BIT)
#define IS_SOFTMODEM_4GUE (get_softmodem_optmask()->bit.SOFTMODEM_4GUE_BIT)
#define IS_SOFTMODEM_5GUE (get_softmodem_optmask()->bit.SOFTMODEM_5GUE_BIT)
#define IS_SOFTMODEM_NOSTATS (get_softmodem_optmask()->bit.SOFTMODEM_NOSTATS_BIT)
#define IS_SOFTMODEM_IMSCOPE_ENABLED (get_softmodem_optmask()->bit.SOFTMODEM_IMSCOPE_BIT)
typedef struct optmask_s {
union {
struct {
uint64_t SOFTMODEM_NOS1_BIT: 1;
uint64_t SOFTMODEM_NOKRNMOD_BIT: 1;
uint64_t SOFTMODEM_NONBIOT_BIT: 1;
uint64_t SOFTMODEM_RFSIM_BIT: 1;
uint64_t SOFTMODEM_SIML1_BIT: 1;
uint64_t SOFTMODEM_DLSIM_BIT: 1;
uint64_t SOFTMODEM_DOSCOPE_BIT: 1;
uint64_t SOFTMODEM_RECPLAY_BIT: 1;
uint64_t SOFTMODEM_TELNETCLT_BIT: 1;
uint64_t SOFTMODEM_RECRECORD_BIT: 1;
uint64_t SOFTMODEM_ENB_BIT: 1;
uint64_t SOFTMODEM_GNB_BIT: 1;
uint64_t SOFTMODEM_4GUE_BIT: 1;
uint64_t SOFTMODEM_5GUE_BIT: 1;
uint64_t SOFTMODEM_NOSTATS_BIT: 1;
uint64_t SOFTMODEM_IMSCOPE_BIT: 1;
} bit;
uint64_t v; // allow to export entire bit set, force to 64 bit processor atomic size
};
} optmask_t;
typedef struct {
uint64_t optmask;
optmask_t optmask;
//THREAD_STRUCT thread_struct;
char *rf_config_file;
char *threadPoolConfig;
......@@ -323,19 +343,17 @@ typedef struct {
#define IS_SA_MODE(sM_params) (!(sM_params)->phy_test && !(sM_params)->do_ra && !(sM_params)->nsa)
void softmodem_verify_mode(const softmodem_params_t *p);
uint64_t get_softmodem_optmask(void);
uint64_t set_softmodem_optmask(uint64_t bitmask);
uint64_t clear_softmodem_optmask(uint64_t bitmask);
#define get_softmodem_optmask() (&(get_softmodem_params()->optmask))
softmodem_params_t *get_softmodem_params(void);
void get_common_options(configmodule_interface_t *cfg, uint32_t execmask);
char *get_softmodem_function(uint64_t *sofmodemfunc_mask_ptr);
void get_common_options(configmodule_interface_t *cfg);
char *get_softmodem_function(void);
#define SOFTMODEM_RTSIGNAL (SIGRTMIN+1)
void set_softmodem_sighandler(void);
extern uint64_t downlink_frequency[MAX_NUM_CCs][4];
extern int32_t uplink_frequency_offset[MAX_NUM_CCs][4];
extern int usrp_tx_thread;
extern uint16_t sl_ahead;
extern uint16_t sf_ahead;
extern int sl_ahead;
extern int sf_ahead;
extern int oai_exit;
void ru_tx_func(void *param);
......
......@@ -38,9 +38,8 @@
extern RAN_CONTEXT_t RC;
extern UL_RCC_IND_t UL_RCC_INFO;
extern uint16_t sf_ahead;
extern uint16_t slot_ahead;
extern int sf_ahead;
extern int slot_ahead;
void *aerial_vnf_nr_p7_config_init(void *ptr)
{
......
......@@ -2435,7 +2435,7 @@ void handle_nr_slot_ind(uint16_t sfn, uint16_t slot) {
//send VNF slot indication, which is aligned with TX thread, so that it can call the scheduler
nfapi_nr_slot_indication_scf_t *ind;
ind = (nfapi_nr_slot_indication_scf_t *) malloc(sizeof(nfapi_nr_slot_indication_scf_t));
uint8_t slot_ahead = 6;
int slot_ahead = 6;
uint32_t sfn_slot_tx = sfnslot_add_slot(sfn, slot, slot_ahead);
uint16_t sfn_tx = NFAPI_SFNSLOT2SFN(sfn_slot_tx);
uint8_t slot_tx = NFAPI_SFNSLOT2SLOT(sfn_slot_tx);
......
......@@ -230,7 +230,7 @@ int vnf_nr_unpack_vendor_extension_tlv(nfapi_tl_t *tl,
}
void install_nr_schedule_handlers(NR_IF_Module_t *if_inst);
void install_schedule_handlers(IF_Module_t *if_inst);
extern uint16_t sf_ahead;
extern int sf_ahead;
void oai_create_enb(void) {
int bodge_counter=0;
......
......@@ -31,9 +31,7 @@
#define FAPI2_IP_DSCP 0
extern uint16_t sf_ahead;
//uint16_t sf_ahead=4;
extern int sf_ahead;
void add_slot(uint16_t *frameP, uint16_t *slotP, int offset)
{
......
......@@ -182,24 +182,25 @@ int nfapi_nr_vnf_p7_start(nfapi_vnf_p7_config_t* config)
NFAPI_TRACE(NFAPI_TRACE_DEBUG, "This is the slot_ind queue size %ld in %s():%d\n",
gnb_slot_ind_queue.num_items, __FUNCTION__, __LINE__);
if (slot_ind) {
gNB->UL_INFO.frame = slot_ind->sfn;
gNB->UL_INFO.slot = slot_ind->slot;
NFAPI_TRACE(NFAPI_TRACE_DEBUG, "gNB->UL_INFO.frame = %d and slot %d, prev_slot = %d\n",
gNB->UL_INFO.frame, gNB->UL_INFO.slot, prev_slot);
if (setup_done && prev_slot != gNB->UL_INFO.slot) { //Give the VNF sufficient time to setup before starting scheduling && prev_slot != gNB->UL_INFO.slot
//Call the scheduler
gNB->UL_INFO.module_id = gNB->Mod_id;
gNB->UL_INFO.CC_id = gNB->CC_id;
NFAPI_TRACE(NFAPI_TRACE_DEBUG, "Calling NR_UL_indication for gNB->UL_INFO.frame = %d and slot %d\n",
gNB->UL_INFO.frame, gNB->UL_INFO.slot);
gNB->if_inst->NR_UL_indication(&gNB->UL_INFO);
prev_slot = gNB->UL_INFO.slot;
}
free(slot_ind);
slot_ind = NULL;
}
NR_UL_IND_t UL_INFO = {.frame = slot_ind->sfn, .slot = slot_ind->slot};
NFAPI_TRACE(NFAPI_TRACE_DEBUG, "UL_INFO.frame = %d and slot %d, prev_slot = %d\n", UL_INFO.frame, UL_INFO.slot, prev_slot);
if (setup_done && prev_slot != UL_INFO.slot) { // Give the VNF sufficient time to setup before starting scheduling &&
// prev_slot != UL_INFO.slot
// Call the scheduler
UL_INFO.module_id = gNB->Mod_id;
UL_INFO.CC_id = gNB->CC_id;
NFAPI_TRACE(NFAPI_TRACE_DEBUG,
"Calling NR_UL_indication for UL_INFO.frame = %d and slot %d\n",
UL_INFO.frame,
UL_INFO.slot);
gNB->if_inst->NR_UL_indication(&UL_INFO);
prev_slot = UL_INFO.slot;
}
free(slot_ind);
slot_ind = NULL;
}
selectRetval = pselect(maxSock+1, &rfds, NULL, NULL, &pselect_timeout, NULL);
......
......@@ -114,9 +114,11 @@ Libraries implementing the slotwise LDPC coding must be named `libldpc<_version>
The interface of the library is defined in [nrLDPC_defs.h](file://../nrLDPC_defs.h).
The code loading the LDPC library is in [nrLDPC_load.c](file://../nrLDPC_load.c), in function `load_nrLDPClib`, which must be called at init time.
*Note: LDPC segment coding libraries are not loaded directly by OAI but by the intermediate library `libldpc.so` which is implementing the LDPC slot coding interface using a LDPC segment coding library.*
### Selecting the LDPC library at run time
By default the function `int load_nrLDPClib(void)` looks for `libldpc.so`, this default behavior can be changed using the oai loader configuration options in the configuration file or from the command line as shown below:
By default the function `int load_nrLDPClib(void)` looks for `libldpc_optim8segmulti.so`, this default behavior can be changed using the oai loader configuration options in the configuration file or from the command line as shown below:
#### Examples of ldpc shared lib selection when running nr softmodem's:
......@@ -133,7 +135,7 @@ loading `libldpc_optim8seg.so` instead of `libldpc_optim8segmulti.so`:
........................
```
loading `libldpc_cl.so` instead of `libldpc.so`:
loading `libldpc_cl.so` instead of `libldpc_optim8segmulti.so`:
`make ldpc_cl`
......
......@@ -259,7 +259,7 @@ one_measurement_t test_ldpc(short max_iterations,
printf("To: %d\n", (Kb + nrows - no_punctured_columns) * Zc - removed_bit);
printf("number of undecoded bits: %d\n", (Kb + nrows - no_punctured_columns - 2) * Zc - removed_bit);
encoder_implemparams_t impp = {.Zc = Zc, .Kb = Kb, .BG = BG, .Kr = block_length, .K = block_length};
encoder_implemparams_t impp = {.Zc = Zc, .Kb = Kb, .BG = BG, .K = block_length};
impp.gen_code = 2;
if (ntrials==0)
......@@ -323,7 +323,7 @@ one_measurement_t test_ldpc(short max_iterations,
decParams[j].R = code_rate_vec[R_ind]; // 13;
decParams[j].numMaxIter = max_iterations;
decParams[j].outMode = nrLDPC_outMode_BIT;
decParams[j].E = block_length;
decParams[j].Kprime = block_length;
ldpc_toCompare.LDPCinit();
}
for (int j = 0; j < n_segments; j++) {
......
This diff is collapsed.
......@@ -173,7 +173,7 @@ typedef struct nrLDPC_segment_encoding_parameters_s{
* \var G Available radio resource bits
* \var tbslbrm Transport block size LBRM
* \var A Transport block size (This is A from 38.212 V15.4.0 section 5.1)
* \var Kb Code block size divided by lifting size
* \var Kb Number of time the lifting size needed to fit the payload of a code block
* \var K Code block size at input of encoder
* \var Z lifting size
* \var F filler bits size
......
add_library(ldpc MODULE
add_library(nr_coding_segment_utils OBJECT
nrLDPC_load.c
nr_rate_matching.c
)
add_library(nr_coding_segment_decoder OBJECT
nrLDPC_coding_segment_decoder.c
)
add_library(nr_coding_segment_encoder OBJECT
nrLDPC_coding_segment_encoder.c
${PHY_NR_CODINGIF}
)
#ensure that the T header files are generated before targets depending on them
if (${T_TRACER})
add_dependencies(nr_coding_segment_utils generate_T)
add_dependencies(nr_coding_segment_decoder generate_T)
add_dependencies(nr_coding_segment_encoder generate_T)
endif (${T_TRACER})
add_library(ldpc MODULE)
target_link_libraries(ldpc PRIVATE
nr_coding_segment_decoder
nr_coding_segment_encoder
nr_coding_segment_utils
)
set_target_properties(ldpc PROPERTIES LIBRARY_OUTPUT_DIRECTORY ${CMAKE_BINARY_DIR})
......
......@@ -20,11 +20,11 @@
*/
/*! \file PHY/CODING/nrLDPC_coding/nrLDPC_coding_segment/nrLDPC_coding_segment_decoder.c
* \brief Top-level routines for decoding LDPC transport channels
*/
* \brief Top-level routines for decoding LDPC transport channels
*/
// [from gNB coding]
#include "nr_rate_matching.h"
#include "PHY/defs_gNB.h"
#include "PHY/CODING/coding_extern.h"
#include "PHY/CODING/coding_defs.h"
......@@ -45,10 +45,10 @@
#include <stdint.h>
#include <syscall.h>
#include <time.h>
//#define gNB_DEBUG_TRACE
// #define gNB_DEBUG_TRACE
#define OAI_LDPC_DECODER_MAX_NUM_LLR 27000 //26112 // NR_LDPC_NCOL_BG1*NR_LDPC_ZMAX = 68*384
//#define DEBUG_CRC
#define OAI_LDPC_DECODER_MAX_NUM_LLR 27000 // 26112 // NR_LDPC_NCOL_BG1*NR_LDPC_ZMAX = 68*384
// #define DEBUG_CRC
#ifdef DEBUG_CRC
#define PRINT_CRC_CHECK(a) a
#else
......@@ -64,7 +64,8 @@
* \brief decoding parameter of transport blocks
* \var decoderParms decoder parameters
* \var Qm modulation order
* \var Kc size of base graph input
* \var Kc ratio between the number of columns in the parity check matrix and the lifting size
* it is fixed for a given base graph while the lifting size is chosen to have a sufficient number of columns
* \var rv_index
* \var max_number_iterations maximum number of LDPC iterations
* \var abort_decode pointer to decode abort flag
......@@ -75,7 +76,7 @@
* \var F filler bits size
* \var r segment index in TB
* \var E input llr segment size
* \var C number of segments
* \var C number of segments
* \var llr input llr segment array
* \var d Pointers to code blocks before LDPC decoding (38.212 V15.4.0 section 5.3.2)
* \var d_to_be_cleared
......@@ -88,8 +89,7 @@
* \var p_ts_rate_unmatch pointer to rate unmatching time stats
* \var p_ts_ldpc_decode pointer to decoding time stats
*/
typedef struct nrLDPC_decoding_parameters_s{
typedef struct nrLDPC_decoding_parameters_s {
t_nrLDPC_dec_params decoderParms;
uint8_t Qm;
......@@ -127,14 +127,13 @@ static void nr_process_decode_segment(void *arg)
{
nrLDPC_decoding_parameters_t *rdata = (nrLDPC_decoding_parameters_t *)arg;
t_nrLDPC_dec_params *p_decoderParms = &rdata->decoderParms;
const int Kr = rdata->K;
const int Kr_bytes = Kr >> 3;
const int K_bits_F = Kr - rdata->F;
const int K = rdata->K;
const int Kprime = K - rdata->F;
const int A = rdata->A;
const int E = rdata->E;
const int Qm = rdata->Qm;
const int rv_index = rdata->rv_index;
const uint8_t kc = rdata->Kc;
const uint8_t Kc = rdata->Kc;
short *ulsch_llr = rdata->llr;
int8_t llrProcBuf[OAI_LDPC_DECODER_MAX_NUM_LLR] __attribute__((aligned(32)));
......@@ -166,7 +165,6 @@ static void nr_process_decode_segment(void *arg)
///////////////////////// ulsch_harq->e =====> ulsch_harq->d /////////////////////////
if (nr_rate_matching_ldpc_rx(rdata->tbslbrm,
p_decoderParms->BG,
p_decoderParms->Z,
......@@ -177,9 +175,8 @@ static void nr_process_decode_segment(void *arg)
*rdata->d_to_be_cleared,
E,
rdata->F,
Kr - rdata->F - 2 * (p_decoderParms->Z))
K - rdata->F - 2 * (p_decoderParms->Z))
== -1) {
stop_meas(rdata->p_ts_rate_unmatch);
LOG_E(PHY, "nrLDPC_coding_segment_decoder.c: Problem in rate_matching\n");
......@@ -191,9 +188,8 @@ static void nr_process_decode_segment(void *arg)
*rdata->d_to_be_cleared = false;
memset(rdata->c, 0, Kr_bytes);
p_decoderParms->crc_type = crcType(rdata->C, A);
p_decoderParms->E = lenWithCrc(rdata->C, A);
p_decoderParms->Kprime = lenWithCrc(rdata->C, A);
// set first 2*Z_c bits to zeros
......@@ -203,16 +199,16 @@ static void nr_process_decode_segment(void *arg)
memset(z, 0, 2 * rdata->Z * sizeof(*z));
// set Filler bits
memset(z + K_bits_F, 127, rdata->F * sizeof(*z));
memset(z + Kprime, 127, rdata->F * sizeof(*z));
// Move coded bits before filler bits
memcpy(z + 2 * rdata->Z, rdata->d, (K_bits_F - 2 * rdata->Z) * sizeof(*z));
memcpy(z + 2 * rdata->Z, rdata->d, (Kprime - 2 * rdata->Z) * sizeof(*z));
// skip filler bits
memcpy(z + Kr, rdata->d + (Kr - 2 * rdata->Z), (kc * rdata->Z - Kr) * sizeof(*z));
memcpy(z + K, rdata->d + (K - 2 * rdata->Z), (Kc * rdata->Z - K) * sizeof(*z));
// Saturate coded bits before decoding into 8 bits values
simde__m128i *pv = (simde__m128i *)&z;
int8_t l[68 * 384 + 16] __attribute__((aligned(16)));
simde__m128i *pl = (simde__m128i *)&l;
for (int i = 0, j = 0; j < ((kc * rdata->Z) >> 4) + 1; i += 2, j++) {
for (int i = 0, j = 0; j < ((Kc * rdata->Z) >> 4) + 1; i += 2, j++) {
pl[j] = simde_mm_packs_epi16(pv[i], pv[i + 1]);
}
//////////////////////////////////////////////////////////////////////////////////////////
......@@ -226,9 +222,10 @@ static void nr_process_decode_segment(void *arg)
ldpc_interface_segment.LDPCdecoder(p_decoderParms, 0, 0, 0, l, llrProcBuf, p_procTime, rdata->abort_decode);
if (decodeIterations <= p_decoderParms->numMaxIter) {
memcpy(rdata->c,llrProcBuf, Kr>>3);
memcpy(rdata->c, llrProcBuf, K >> 3);
*rdata->decodeSuccess = true;
} else {
memset(rdata->c, 0, K >> 3);
*rdata->decodeSuccess = false;
}
stop_meas(rdata->p_ts_ldpc_decode);
......@@ -237,9 +234,10 @@ static void nr_process_decode_segment(void *arg)
completed_task_ans(rdata->ans);
}
int nrLDPC_prepare_TB_decoding(nrLDPC_slot_decoding_parameters_t *nrLDPC_slot_decoding_parameters, int pusch_id, thread_info_tm_t *t_info)
int nrLDPC_prepare_TB_decoding(nrLDPC_slot_decoding_parameters_t *nrLDPC_slot_decoding_parameters,
int pusch_id,
thread_info_tm_t *t_info)
{
nrLDPC_TB_decoding_parameters_t *nrLDPC_TB_decoding_parameters = &nrLDPC_slot_decoding_parameters->TBs[pusch_id];
*nrLDPC_TB_decoding_parameters->processedSegments = 0;
......@@ -250,14 +248,12 @@ int nrLDPC_prepare_TB_decoding(nrLDPC_slot_decoding_parameters_t *nrLDPC_slot_de
decParams.outMode = 0;
for (int r = 0; r < nrLDPC_TB_decoding_parameters->C; r++) {
nrLDPC_decoding_parameters_t *rdata = &((nrLDPC_decoding_parameters_t *)t_info->buf)[t_info->len];
DevAssert(t_info->len < t_info->cap);
rdata->ans = &t_info->ans[t_info->len];
t_info->len += 1;
decParams.R = nrLDPC_TB_decoding_parameters->segments[r].R;
decParams.setCombIn = !nrLDPC_TB_decoding_parameters->segments[r].d_to_be_cleared;
rdata->decoderParms = decParams;
rdata->llr = nrLDPC_TB_decoding_parameters->segments[r].llr;
rdata->Kc = decParams.BG == 2 ? 52 : 68;
......@@ -287,29 +283,26 @@ int nrLDPC_prepare_TB_decoding(nrLDPC_slot_decoding_parameters_t *nrLDPC_slot_de
return nrLDPC_TB_decoding_parameters->C;
}
int32_t nrLDPC_coding_init(void){
int32_t nrLDPC_coding_init(void)
{
char *segment_shlibversion = NULL;
paramdef_t LoaderParams[] = {
{"segment_shlibversion", NULL, 0, .strptr = &segment_shlibversion, .defstrval = "_optim8segmulti", TYPE_STRING, 0, NULL}
};
{"segment_shlibversion", NULL, 0, .strptr = &segment_shlibversion, .defstrval = "_optim8segmulti", TYPE_STRING, 0, NULL}};
config_get(config_get_if(), LoaderParams, sizeofArray(LoaderParams), "nrLDPC_coding_segment");
load_LDPClib(segment_shlibversion, &ldpc_interface_segment);
return 0;
}
int32_t nrLDPC_coding_shutdown(void){
int32_t nrLDPC_coding_shutdown(void)
{
free_LDPClib(&ldpc_interface_segment);
return 0;
}
int32_t nrLDPC_coding_decoder(nrLDPC_slot_decoding_parameters_t *nrLDPC_slot_decoding_parameters){
int32_t nrLDPC_coding_decoder(nrLDPC_slot_decoding_parameters_t *nrLDPC_slot_decoding_parameters)
{
int nbSegments = 0;
for (int pusch_id = 0; pusch_id < nrLDPC_slot_decoding_parameters->nb_TBs; pusch_id++) {
nrLDPC_TB_decoding_parameters_t *nrLDPC_TB_decoding_parameters = &nrLDPC_slot_decoding_parameters->TBs[pusch_id];
......@@ -339,6 +332,4 @@ int32_t nrLDPC_coding_decoder(nrLDPC_slot_decoding_parameters_t *nrLDPC_slot_dec
}
}
return 0;
}
......@@ -20,9 +20,10 @@
*/
/*! \file PHY/CODING/nrLDPC_coding/nrLDPC_coding_segment/nrLDPC_coding_segment_encoder.c
* \brief Top-level routines for implementing LDPC encoding of transport channels
*/
* \brief Top-level routines for implementing LDPC encoding of transport channels
*/
#include "nr_rate_matching.h"
#include "PHY/defs_gNB.h"
#include "PHY/CODING/coding_extern.h"
#include "PHY/CODING/coding_defs.h"
......@@ -40,8 +41,8 @@
#include <syscall.h>
//#define DEBUG_LDPC_ENCODING
//#define DEBUG_LDPC_ENCODING_FREE 1
// #define DEBUG_LDPC_ENCODING
// #define DEBUG_LDPC_ENCODING_FREE 1
extern ldpc_interface_t ldpc_interface_segment;
......@@ -61,35 +62,34 @@ static void ldpc8blocks_coding_segment(void *p)
uint32_t A = nrLDPC_TB_encoding_parameters->A;
unsigned int G = nrLDPC_TB_encoding_parameters->G;
LOG_D(PHY,"dlsch coding A %d Kr %d G %d (nb_rb %d, mod_order %d)\n",
A,impp->K,G, nb_rb,(int)mod_order);
LOG_D(PHY, "dlsch coding A %d K %d G %d (nb_rb %d, mod_order %d)\n", A, impp->K, G, nb_rb, (int)mod_order);
// nrLDPC_encoder output is in "d"
// let's make this interface happy!
uint8_t tmp[8][68 * 384]__attribute__((aligned(32)));
uint8_t tmp[8][68 * 384] __attribute__((aligned(32)));
uint8_t *d[impp->n_segments];
for (int rr=impp->macro_num*8, i=0; rr < impp->n_segments && rr < (impp->macro_num+1)*8; rr++,i++ )
for (int rr = impp->macro_num * 8, i = 0; rr < impp->n_segments && rr < (impp->macro_num + 1) * 8; rr++, i++)
d[rr] = tmp[i];
uint8_t *c[nrLDPC_TB_encoding_parameters->C];
for (int r = 0; r < nrLDPC_TB_encoding_parameters->C; r++)
c[r]=nrLDPC_TB_encoding_parameters->segments[r].c;
start_meas(&nrLDPC_TB_encoding_parameters->segments[impp->macro_num*8].ts_ldpc_encode);
c[r] = nrLDPC_TB_encoding_parameters->segments[r].c;
start_meas(&nrLDPC_TB_encoding_parameters->segments[impp->macro_num * 8].ts_ldpc_encode);
ldpc_interface_segment.LDPCencoder(c, d, impp);
stop_meas(&nrLDPC_TB_encoding_parameters->segments[impp->macro_num*8].ts_ldpc_encode);
stop_meas(&nrLDPC_TB_encoding_parameters->segments[impp->macro_num * 8].ts_ldpc_encode);
// Compute where to place in output buffer that is concatenation of all segments
uint32_t r_offset=0;
for (int i=0; i < impp->macro_num*8; i++ )
r_offset+=nrLDPC_TB_encoding_parameters->segments[i].E;
for (int rr=impp->macro_num*8; rr < impp->n_segments && rr < (impp->macro_num+1)*8; rr++ ) {
if (impp->F>0) {
uint32_t r_offset = 0;
for (int i = 0; i < impp->macro_num * 8; i++)
r_offset += nrLDPC_TB_encoding_parameters->segments[i].E;
for (int rr = impp->macro_num * 8; rr < impp->n_segments && rr < (impp->macro_num + 1) * 8; rr++) {
if (impp->F > 0) {
// writing into positions d[r][k-2Zc] as in clause 5.3.2 step 2) in 38.212
memset(&d[rr][impp->K - impp->F - 2 * impp->Zc], NR_NULL, impp->F);
}
#ifdef DEBUG_LDPC_ENCODING
LOG_D(PHY,"rvidx in encoding = %d\n", rel15->rvIndex[0]);
LOG_D(PHY, "rvidx in encoding = %d\n", rel15->rvIndex[0]);
#endif
uint32_t E = nrLDPC_TB_encoding_parameters->segments[rr].E;
LOG_D(NR_PHY,
......@@ -108,7 +108,7 @@ static void ldpc8blocks_coding_segment(void *p)
uint32_t Tbslbrm = nrLDPC_TB_encoding_parameters->tbslbrm;
uint8_t e[E];
bzero (e, E);
bzero(e, E);
start_meas(&nrLDPC_TB_encoding_parameters->segments[rr].ts_rate_match);
nr_rate_matching_ldpc(Tbslbrm,
impp->BG,
......@@ -122,16 +122,10 @@ static void ldpc8blocks_coding_segment(void *p)
E);
stop_meas(&nrLDPC_TB_encoding_parameters->segments[rr].ts_rate_match);
if (impp->K - impp->F - 2 * impp->Zc > E) {
LOG_E(PHY,
"dlsch coding A %d Kr %d G %d (nb_rb %d, mod_order %d)\n",
A,
impp->K,
G,
nb_rb,
(int)mod_order);
LOG_E(PHY, "dlsch coding A %d K %d G %d (nb_rb %d, mod_order %d)\n", A, impp->K, G, nb_rb, (int)mod_order);
LOG_E(NR_PHY,
"Rate Matching, Code segment %d/%d (coded bits (G) %u, E %d, Kr %d, Filler bits %d, Filler offset %d mod_order %d, "
"Rate Matching, Code segment %d/%d (coded bits (G) %u, E %d, K %d, Filler bits %d, Filler offset %d mod_order %d, "
"nb_rb %d)...\n",
rr,
impp->n_segments,
......@@ -145,23 +139,20 @@ static void ldpc8blocks_coding_segment(void *p)
}
#ifdef DEBUG_LDPC_ENCODING
for (int i =0; i<16; i++)
printf("output ratematching e[%d]= %d r_offset %u\n", i,e[i], r_offset);
for (int i = 0; i < 16; i++)
printf("output ratematching e[%d]= %d r_offset %u\n", i, e[i], r_offset);
#endif
start_meas(&nrLDPC_TB_encoding_parameters->segments[rr].ts_interleave);
nr_interleaving_ldpc(E,
mod_order,
e,
impp->output+r_offset);
nr_interleaving_ldpc(E, mod_order, e, impp->output + r_offset);
stop_meas(&nrLDPC_TB_encoding_parameters->segments[rr].ts_interleave);
#ifdef DEBUG_LDPC_ENCODING
for (int i =0; i<16; i++)
printf("output interleaving f[%d]= %d r_offset %u\n", i,impp->output[i+r_offset], r_offset);
for (int i = 0; i < 16; i++)
printf("output interleaving f[%d]= %d r_offset %u\n", i, impp->output[i + r_offset], r_offset);
if (r==impp->n_segments-1)
write_output("enc_output.m","enc",impp->output,G,1,4);
if (r == impp->n_segments - 1)
write_output("enc_output.m", "enc", impp->output, G, 1, 4);
#endif
r_offset += E;
......@@ -171,7 +162,9 @@ static void ldpc8blocks_coding_segment(void *p)
completed_task_ans(impp->ans);
}
static int nrLDPC_prepare_TB_encoding(nrLDPC_slot_encoding_parameters_t *nrLDPC_slot_encoding_parameters, int dlsch_id, thread_info_tm_t *t_info)
static int nrLDPC_prepare_TB_encoding(nrLDPC_slot_encoding_parameters_t *nrLDPC_slot_encoding_parameters,
int dlsch_id,
thread_info_tm_t *t_info)
{
nrLDPC_TB_encoding_parameters_t *nrLDPC_TB_encoding_parameters = &nrLDPC_slot_encoding_parameters->TBs[dlsch_id];
......@@ -211,7 +204,6 @@ static int nrLDPC_prepare_TB_encoding(nrLDPC_slot_encoding_parameters_t *nrLDPC_
int nrLDPC_coding_encoder(nrLDPC_slot_encoding_parameters_t *nrLDPC_slot_encoding_parameters)
{
int nbTasks = 0;
for (int dlsch_id = 0; dlsch_id < nrLDPC_slot_encoding_parameters->nb_TBs; dlsch_id++) {
nrLDPC_TB_encoding_parameters_t *nrLDPC_TB_encoding_parameters = &nrLDPC_slot_encoding_parameters->TBs[dlsch_id];
......@@ -234,5 +226,4 @@ int nrLDPC_coding_encoder(nrLDPC_slot_encoding_parameters_t *nrLDPC_slot_encodin
join_task_ans(ans, nbEncode);
return 0;
}
......@@ -29,7 +29,7 @@
* \note
* \warning
*/
#define _GNU_SOURCE
#define _GNU_SOURCE
#include <sys/types.h>
#include <stdlib.h>
#include <malloc.h>
......@@ -41,7 +41,7 @@
/* arguments used when called from phy simulators exec's which do not use the config module */
/* arg is used to initialize the config module so that the loader works as expected */
char *arg[64]={"ldpctest",NULL};
char *arg[64] = {"ldpctest", NULL};
int load_LDPClib(char *version, ldpc_interface_t *itf)
{
......
/*
* Licensed to the OpenAirInterface (OAI) Software Alliance under one or more
* contributor license agreements. See the NOTICE file distributed with
* this work for additional information regarding copyright ownership.
* The OpenAirInterface Software Alliance licenses this file to You under
* the OAI Public License, Version 1.1 (the "License"); you may not use this file
* except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.openairinterface.org/?page_id=698
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*-------------------------------------------------------------------------------
* For more information about the OpenAirInterface (OAI) Software Alliance:
* contact@openairinterface.org
*/
#ifndef __NR_RATE_MATCHING__H__
#define __NR_RATE_MATCHING__H__
#include <stdint.h>
#define NR_NULL 2
/**
* \brief interleave a code segment after encoding and rate matching
* \param E size of the code segment in bits
* \param Qm modulation order
* \param e input rate matched segment
* \param f output interleaved segment
*/
void nr_interleaving_ldpc(uint32_t E, uint8_t Qm, uint8_t *e, uint8_t *f);
/**
* \brief deinterleave a code segment before RX rate matching and decoding
* \param E size of the code segment in bits
* \param Qm modulation order
* \param e output deinterleaved segment
* \param f input llr segment
*/
void nr_deinterleaving_ldpc(uint32_t E, uint8_t Qm, int16_t *e, int16_t *f);
/**
* \brief rate match a code segment after encoding
* \Tbslbrm Transport Block size LBRM
* \param BG LDPC base graph number
* \param Z segment lifting size
* \param d input encoded segment
* \param e output rate matched segment
* \param C number of segments in the Transport Block
* \param F number of filler bits in the segment
* \param Foffset offset of the filler bits in the segment
* \param rvidx redundancy version index
* \param E size of the code segment in bits
*/
int nr_rate_matching_ldpc(uint32_t Tbslbrm,
uint8_t BG,
uint16_t Z,
uint8_t *d,
uint8_t *e,
uint8_t C,
uint32_t F,
uint32_t Foffset,
uint8_t rvidx,
uint32_t E);
/**
* \brief rate match a code segment before decoding
* \Tbslbrm Transport Block size LBRM
* \param BG LDPC base graph number
* \param Z segment lifting size
* \param d output rate matched segment
* \param soft_input input deinterleaved segment
* \param C number of segments in the Transport Block
* \param rvidx redundancy version index
* \param clear flag to clear d on the first round of a new HARQ process
* \param E size of the code segment in bits
* \param F number of filler bits in the segment
* \param Foffset offset of the filler bits in the segment
*/
int nr_rate_matching_ldpc_rx(uint32_t Tbslbrm,
uint8_t BG,
uint16_t Z,
int16_t *d,
int16_t *soft_input,
uint8_t C,
uint8_t rvidx,
uint8_t clear,
uint32_t E,
uint32_t F,
uint32_t Foffset);
#endif
......@@ -10,8 +10,17 @@ if (ENABLE_LDPC_XDMA)
add_library(ldpc_xdma MODULE
nrLDPC_coding_xdma_offload.c
nrLDPC_coding_xdma.c
../nrLDPC_coding_segment/nrLDPC_coding_segment_encoder.c
../../nrLDPC_load.c
)
target_include_directories(ldpc_xdma PRIVATE ../nrLDPC_coding_segment)
#ensure that the T header files are generated before targets depending on them
if (${T_TRACER})
add_dependencies(ldpc_xdma generate_T)
endif (${T_TRACER})
target_link_libraries(ldpc_xdma PRIVATE
nr_coding_segment_encoder
nr_coding_segment_utils
)
set_target_properties(ldpc_xdma PROPERTIES LIBRARY_OUTPUT_DIRECTORY ${CMAKE_BINARY_DIR})
......
......@@ -855,7 +855,7 @@ static inline uint32_t nrLDPC_decoder_core(int8_t* p_llr,
nrLDPC_llr2bitPacked(p_out, p_llrOut, numLLR);
else // if (outMode == nrLDPC_outMode_BITINT8)
nrLDPC_llr2bit(p_out, p_llrOut, numLLR);
if (p_decParams->check_crc((uint8_t*)p_out, p_decParams->E, p_decParams->crc_type)) {
if (p_decParams->check_crc((uint8_t*)p_out, p_decParams->Kprime, p_decParams->crc_type)) {
LOG_D(PHY, "Segment CRC OK, exiting LDPC decoder\n");
break;
}
......
......@@ -86,11 +86,10 @@ typedef struct nrLDPC_dec_params {
uint16_t Z; /**< Lifting size */
uint8_t R; /**< Decoding rate: Format 15,13,... for code rates 1/5, 1/3,... */
uint8_t numMaxIter; /**< Maximum number of iterations */
int E;
int Kprime; /**< Size of the payload bits and CRC bits in the code block */
e_nrLDPC_outMode outMode; /**< Output format */
int crc_type;
int (*check_crc)(uint8_t* decoded_bytes, uint32_t n, uint8_t crc_type);
uint8_t setCombIn;
int crc_type; /**< Size and type of the parity check bits (16, 24A or 24B) */
int (*check_crc)(uint8_t* decoded_bytes, uint32_t n, uint8_t crc_type); /**< Parity check function */
} t_nrLDPC_dec_params;
/**
......
......@@ -518,7 +518,7 @@ extern "C" int32_t LDPCdecoder(t_nrLDPC_dec_params *p_decParams,
init_LLR_DMA(p_decParams, p_llr, p_out);
uint16_t Zc = p_decParams->Z;
uint8_t BG = p_decParams->BG;
int block_length = p_decParams->E;
int block_length = p_decParams->Kprime;
uint8_t row, col;
if (BG == 1) {
row = 46;
......
......@@ -26,37 +26,51 @@
#include "openair1/PHY/CODING/nrLDPC_decoder/nrLDPC_types.h"
/**
\brief LDPC encoder
\param 1 input
\param 2 channel_input
\param 3 int Zc
\param 4 int Kb
\param 5 short block_length
\param 6 short BG
\param 7 int n_segment
\param 8 unsigned int macro_num
\param 9-12 time_stats_t *tinput,*tprep, *tparity,*toutput
\brief LDPC encoder parameter structure
\var n_segments number of segments in the transport block
\var macro_num index of the subset of segments to encode
within the transport block
\var gen_code flag to generate parity check code
0 -> encoding
1 -> generate parity check code with AVX2
2 -> generate parity check code without AVX2
\var tinput time statistics for data input in the encoder
\var tprep time statistics for data preparation in the encoder
\var tparity time statistics for adding parity bits
\var toutput time statistics for data output from the encoder
\var K size of the complete code segment before encoding
including payload, CRC bits and filler bit
(also known as Kr, see 38.212-5.2.2)
\var Kb number of lifting sizes to fit the payload (see 38.212-5.2.2)
\var Zc lifting size (see 38.212-5.2.2)
\var F number of filler bits (see 38.212-5.2.2)
\var harq pointer to the HARQ process structure
\var BG base graph index
\var output output buffer after INTERLEAVING
\var ans pointer to the task answer
to notify thread pool about completion of the task
*/
typedef struct {
unsigned int n_segments; // optim8seg
unsigned int macro_num; // optim8segmulti
unsigned char gen_code; //orig
unsigned int n_segments; // optim8seg
unsigned int macro_num; // optim8segmulti
unsigned char gen_code; //orig
time_stats_t *tinput;
time_stats_t *tprep;
time_stats_t *tparity;
time_stats_t *toutput;
int Kr;
/// Size in bits of the code segments
uint32_t K;
/// Number of lifting sizes to fit the payload
uint32_t Kb;
/// Lifting size
uint32_t Zc;
/// Number of "Filler" bits
uint32_t F;
void *harq;
/// Encoder BG
uint8_t BG;
/// Interleaver outputs
unsigned char *output;
/// Number of bits in "small" code segments
uint32_t K;
/// Number of "Filler" bits
uint32_t F;
task_ans_t *ans;
} encoder_implemparams_t;
......
......@@ -295,12 +295,12 @@ static inline void nr_polar_deinterleaver(uint8_t *input, uint8_t *output, uint1
static inline void nr_polar_rm_deinterleaving_lut(uint16_t *out, const uint E)
{
int16_t in[E];
for (int i = 0; i < E; i++)
for (uint i = 0; i < E; i++)
in[i] = i;
int T = ceil((sqrt(8 * E + 1) - 1) / 2);
int v_tab[T][T];
memset(v_tab, 0, sizeof(v_tab));
int k = 0;
uint k = 0;
for (int i = 0; i < T; i++) {
for (int j = 0; j < T - i; j++) {
if (k < E) {
......
......@@ -136,8 +136,6 @@ void phy_init_nr_gNB(PHY_VARS_gNB *gNB)
int ret_loader = load_nrLDPC_coding_interface(NULL, &gNB->nrLDPC_coding_interface);
AssertFatal(ret_loader == 0, "error loading LDPC library\n");
pthread_mutex_init(&gNB->UL_INFO.crc_rx_mutex, NULL);
gNB->max_nb_pdsch = MAX_MOBILES_PER_GNB;
init_delay_table(fp->ofdm_symbol_size, MAX_DELAY_COMP, NR_MAX_OFDM_SYMBOL_SIZE, fp->delay_table);
......@@ -231,8 +229,6 @@ void phy_free_nr_gNB(PHY_VARS_gNB *gNB)
const int max_ul_mimo_layers = 4; // taken from phy_init_nr_gNB()
const int n_buf = Prx * max_ul_mimo_layers;
pthread_mutex_destroy(&gNB->UL_INFO.crc_rx_mutex);
PHY_MEASUREMENTS_gNB *meas = &gNB->measurements;
free_and_zero(meas->n0_subband_power);
free_and_zero(meas->n0_subband_power_dB);
......
......@@ -58,8 +58,6 @@
uint64_t deadline,
uint64_t period);*/
extern int oai_exit;
void free_eNB_dlsch(LTE_eNB_DLSCH_t *dlsch) {
int i, r, aa, layer;
......
......@@ -42,8 +42,6 @@
#include "PHY_INTERFACE/phy_interface.h"
#include "transport_proto.h"
extern int oai_exit;
static const int8_t wACK_RX[5][4] = {{-1, -1, -1, -1}, {-1, 1, -1, 1}, {-1, -1, 1, 1}, {-1, 1, 1, -1}, {1, 1, 1, 1}};
void free_eNB_ulsch(LTE_eNB_ULSCH_t *ulsch) {
......
......@@ -20,45 +20,74 @@
*/
/*! \file PHY/NR_TRANSPORT/nr_tbs_tools.c
* \brief Top-level routines for implementing LDPC-coded (DLSCH) transport channels from 38-212, 15.2
* \author H.Wang
* \date 2018
* \version 0.1
* \company Eurecom
* \email:
* \note
* \warning
*/
* \brief Top-level routines for implementing LDPC-coded (DLSCH) transport channels from 38-212, 15.2
* \author H.Wang
* \date 2018
* \version 0.1
* \company Eurecom
* \email:
* \note
* \warning
*/
#include "nr_transport_common_proto.h"
#include "PHY/CODING/coding_defs.h"
#include "PHY/defs_nr_common.h"
uint32_t nr_get_G(uint16_t nb_rb,
uint16_t nb_symb_sch,
uint8_t nb_re_dmrs,
uint16_t length_dmrs,
uint32_t unav_res,
uint8_t Qm,
uint8_t Nl)
uint32_t
nr_get_G(uint16_t nb_rb, uint16_t nb_symb_sch, uint8_t nb_re_dmrs, uint16_t length_dmrs, uint32_t unav_res, uint8_t Qm, uint8_t Nl)
{
uint32_t G = ((NR_NB_SC_PER_RB * nb_symb_sch) - (nb_re_dmrs * length_dmrs)) * nb_rb * Qm * Nl;
G -= unav_res * Qm * Nl;
return(G);
return (G);
}
uint32_t nr_get_E(uint32_t G, uint8_t C, uint8_t Qm, uint8_t Nl, uint8_t r)
{
uint32_t E;
uint8_t Cprime = C; //assume CBGTI not present
uint8_t Cprime = C; // assume CBGTI not present
AssertFatal(Nl > 0, "Nl is 0\n");
AssertFatal(Qm > 0, "Qm is 0\n");
if (r <= Cprime - ((G / (Nl * Qm)) % Cprime) - 1)
E = Nl * Qm * (G / (Nl * Qm * Cprime));
E = Nl * Qm * (G / (Nl * Qm * Cprime));
else
E = Nl * Qm * ((G / (Nl * Qm * Cprime)) + 1);
E = Nl * Qm * ((G / (Nl * Qm * Cprime)) + 1);
LOG_D(PHY,"nr_get_E : (G %d, C %d, Qm %d, Nl %d, r %d), E %d\n",G, C, Qm, Nl, r, E);
LOG_D(PHY, "nr_get_E : (G %d, C %d, Qm %d, Nl %d, r %d), E %d\n", G, C, Qm, Nl, r, E);
return E;
}
static const uint8_t index_k0[2][4] = {{0, 17, 33, 56}, {0, 13, 25, 43}};
int nr_get_R_ldpc_decoder(int rvidx, int E, int BG, int Z, int *llrLen, int round)
{
AssertFatal(BG == 1 || BG == 2, "Unknown BG %d\n", BG);
int Ncb = (BG == 1) ? (66 * Z) : (50 * Z);
int infoBits = (index_k0[BG - 1][rvidx] * Z + E);
if (round == 0)
*llrLen = infoBits;
if (infoBits > Ncb)
infoBits = Ncb;
if (infoBits > *llrLen)
*llrLen = infoBits;
int sysBits = (BG == 1) ? (22 * Z) : (10 * Z);
float decoderR = (float)sysBits / (infoBits + 2 * Z);
if (BG == 2)
if (decoderR < 0.3333)
return 15;
else if (decoderR < 0.6667)
return 13;
else
return 23;
else if (decoderR < 0.6667)
return 13;
else if (decoderR < 0.8889)
return 23;
else
return 89;
}
......@@ -1481,15 +1481,16 @@ int nr_rx_pusch_tp(PHY_VARS_gNB *gNB,
start_meas(&gNB->rx_pusch_symbol_processing_stats);
int numSymbols = gNB->num_pusch_symbols_per_thread;
int total_res = 0;
int const loop_iter = rel15_ul->nr_of_symbols / numSymbols;
int const loop_iter = CEILIDIV(rel15_ul->nr_of_symbols, numSymbols);
puschSymbolProc_t arr[loop_iter];
task_ans_t arr_ans[loop_iter];
memset(arr_ans, 0, loop_iter * sizeof(task_ans_t));
memset(arr_ans, 0, sizeof(arr_ans));
int sz_arr = 0;
for(uint8_t symbol = rel15_ul->start_symbol_index; symbol < end_symbol; symbol += numSymbols) {
for(uint8_t task_index = 0; task_index < loop_iter; task_index++) {
int symbol = task_index * numSymbols + rel15_ul->start_symbol_index;
int res_per_task = 0;
for (int s = 0; s < numSymbols; s++) {
for (int s = 0; s < numSymbols && s + symbol < end_symbol; s++) {
pusch_vars->ul_valid_re_per_slot[symbol+s] = get_nb_re_pusch(frame_parms,rel15_ul,symbol+s);
pusch_vars->llr_offset[symbol+s] = ((symbol+s) == rel15_ul->start_symbol_index) ?
0 :
......@@ -1507,7 +1508,8 @@ int nr_rx_pusch_tp(PHY_VARS_gNB *gNB,
rdata->rel15_ul = rel15_ul;
rdata->slot = slot;
rdata->startSymbol = symbol;
rdata->numSymbols = numSymbols;
// Last task processes remainder symbols
rdata->numSymbols = task_index == loop_iter - 1 ? rel15_ul->nr_of_symbols - (loop_iter - 1) * numSymbols : numSymbols;
rdata->ulsch_id = ulsch_id;
rdata->llr = pusch_vars->llr;
rdata->llr_layers = pusch_vars->llr_layers;
......
......@@ -41,7 +41,7 @@ int main(int argc, char **argv) {
paramdef_t cmdline_params[] = CMDLINE_PARAMS_DESC_GNB ;
CONFIG_SETRTFLAG(CONFIG_NOEXITONHELP);
get_common_options(uniqCfg, SOFTMODEM_GNB_BIT);
get_common_options(uniqCfg);
config_process_cmdline(uniqCfg, cmdline_params, sizeofArray(cmdline_params), NULL);
CONFIG_CLEARRTFLAG(CONFIG_NOEXITONHELP);
lock_memory_to_ram();
......
......@@ -33,7 +33,7 @@
#include "openair1/PHY/defs_nr_UE.h"
extern "C" {
#include "openair1/PHY/TOOLS/phy_scope_interface.h"
uint64_t get_softmodem_optmask(void);
#include "executables/softmodem-common.h"
}
#include <iostream>
#include <vector>
......@@ -42,7 +42,6 @@ uint64_t get_softmodem_optmask(void);
#include <sstream>
#include <mutex>
#include <thread>
#include "executables/softmodem-bits.h"
#define MAX_OFFSETS 14
#define NR_MAX_RB 273
......@@ -678,7 +677,7 @@ void *imscope_thread(void *data_void_ptr)
static double last_frame_time = glfwGetTime();
static int target_fps = 24;
bool is_ue = (get_softmodem_optmask() & SOFTMODEM_5GUE_BIT) > 0;
bool is_ue = IS_SOFTMODEM_5GUE;
bool close_window = false;
while (!glfwWindowShouldClose(window) && close_window == false) {
// Poll and handle events (inputs, window resize, etc.)
......@@ -795,8 +794,7 @@ void *imscope_thread(void *data_void_ptr)
extern "C" void imscope_autoinit(void *dataptr)
{
AssertFatal((get_softmodem_optmask() & SOFTMODEM_5GUE_BIT) || (get_softmodem_optmask() & SOFTMODEM_GNB_BIT),
"Scope cannot find NRUE or GNB context");
AssertFatal(IS_SOFTMODEM_5GUE || IS_SOFTMODEM_GNB, "Scope cannot find NRUE or GNB context");
for (auto i = 0U; i < EXTRA_SCOPE_TYPES; i++) {
scope_array[i].is_data_ready = false;
......@@ -804,7 +802,7 @@ extern "C" void imscope_autoinit(void *dataptr)
scope_array[i].meta = {-1, -1};
}
if (SOFTMODEM_GNB_BIT & get_softmodem_optmask()) {
if (IS_SOFTMODEM_GNB) {
scopeParms_t *scope_params = (scopeParms_t *)dataptr;
scopeData_t *scope = (scopeData_t *)calloc(1, sizeof(scopeData_t));
scope->copyData = copyDataThreadSafe;
......
......@@ -1165,9 +1165,9 @@ STATICFORXSCOPE void nrUEinitScope(PHY_VARS_NR_UE *ue)
}
void nrscope_autoinit(void *dataptr) {
AssertFatal( (IS_SOFTMODEM_GNB_BIT||IS_SOFTMODEM_5GUE_BIT),"Scope cannot find NRUE or GNB context");
AssertFatal((IS_SOFTMODEM_GNB || IS_SOFTMODEM_5GUE), "Scope cannot find NRUE or GNB context");
if (IS_SOFTMODEM_GNB_BIT)
if (IS_SOFTMODEM_GNB)
gNBinitScope(dataptr);
else
nrUEinitScope(dataptr);
......
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment