The unit tests have been imported with this command:
xmlstarlet sel -t
-m '//testCaseList/testCase[class="Run_Physim"]' \
-v "concat('add_timed_physim_test(physim.5g-offload.',physim_test,'.testX.Y \"',desc,'\" ',physim_test,' ',physim_run_args,')')" \
-n t2_offload_enc_nr_dlsim.xml t2_offload_dec_nr_ulsim.xml >> ../../openair1/SIMULATION/tests/CMakeLists.txt
The next commit will further cleanup this output. I commit it like this
for verification purposes.
Add two new macros that allow to register physim tests for ctest,
including timing thresholds that should be fulfilled.
First, add_timed_physim_test() registers a new test using a helper
script RunTimedTest.cmake. This is because after test execution, we need
to analyze logs, and the recommended way to do multiple steps in one
test is via a helper cmake script:
https://cmake.org/pipermail/cmake-developers/2016-February/027816.html
Second, check_physim_threshold() adds new thresholds. It takes a text to
be parsed, and a condition (e.g., "< 20") to check for the number
following the threshold (which is assumed to be present right after the
threshold). It uses a test property to count the total number of checks
(limiting them to 10), and sets environment variables for the script. I
initially planned to use a test property for checks, but those are only
valid in the same directory, and RunTimedTest.cmake seems to be assumed
by cmake to be "elsewhere", hence I needed to resort to environment
variables.
RunTimedTest.cmake is called through cmake with the test parameters and
checks. It re-constructs a list of checks [1], runs the test, and pipes
the log into a separate script that is passed all checks (see below).
Afterwards, it verifies that both the test and script passed.
A script analyze-timing.sh builds an awk script from the checks passed.
The script analyzes each line of the test output for the threshold, and
compares against the threshold. analyze-timing.sh returns success if all
checks passed.
[1] I did not manage to pass a "list" of checks in a single environment
variable through the check_physim_threshold(), which would be simpler.
Change signature of the macro to take the full test name, a separate
description (previously called a label?), and the executable and test
invocation. The overall signature becomes easier.
The rational for the full test name is that a later commit will
introduce the possibility to define physim tests that are checked for
specific times, in which case we need to reuse the test name. Thus,
using the full name from the beginning leads to more clarity, even
though they are a bit longer.
Add an additional safety check that the given simulator is actually a
target defined within the project (in other words, it actually exists).
Update the documentation correspondingly.
Most (but not all) physical simulators are defined under
openair1/SIMULATION/. Defining physical simulators below there seems to
be the more "obvious" directory anyway, as the physical simulators are
openair1/SIMULATION/tests
Phy(L1) Sim tests => PhySim (tests)
Reworking BWP configuration
This MR reworks the configuration via fail of additional BWPs. Moreover, it
allows for a single BWP to be configured for a given UE at a given time (BWP
switch possible only via reconfiguration). It also reworks PTRS configuration
for consistency with the BWP one.
If the DCI in PDCCH is not correctly received, no PDSCH would be decoded but counted as no error.
Also if the DCI was not correctly received, a TBS of 0 would be used in some computations and memory allocations.
Fix these not counting if there is no PDSCH decoding, and by using the known TBS instead of the one received from the DCI.
Ldpc encoder zc384 optimization
This is a modification for the ldpc encoder which improves performance for
high-throughput cases. It contains a newly-generated file for innermost part of
the parity bit generation which, for AVX512, uses the mm512_permutex2var_epi8
instruction and for 128-bit (aarch64) the mm_alignr_epi8 (vextq_s8) in the
computation corresponding to each non-zero bit of the H matrix. This allows for
removing a very large memcpy and reduces the memory demand for the parity matrix
computation. For the moment this is limited to largest case in BG1, namely
Zc=384. This is the only format used when the number of segments after codeblock
segmentation is large (>8). This improves the timing required for ldpc parity
bits generation by more than a factor 2 with AVX512. This significantly reduces
the total time to generate the DLSCH/PDSCH.
See the merge request description for numbers.
- Use MAX_NUM_NR_UE_INST in NR UE MAC to control number of MAC instances.
- Modify the MAC interface slightly so that nr_l2_init_ue only initializes one instance
RF emulator and improvements of the timers
RF emulator:
Add an RF library emulating a real device without the need of a real
device. This is thought to enable using phy-test without requiring a
radio device or channel simulation. The library synchronizes on the
real time clock, drops TX and generate noise on RX. Noise generation
can be disabled and the noise level configured.
Timers improvements:
- Fix standard deviation for merged timers
- Add display of ULSCH decoding timers
- Add decoding timer in AAL
Taps client for vrtsim
The MR allows vrtsim to connect to the Raytracing Channel Emulator (CE later).
https://gitlab.eurecom.fr/oai/raytracing-channel-emulator
Additional Ubuntu packages required:
- libnanomsg-dev
- flatbuffers-compiler
- libflatbuffers-dev
Everything was tested on the same host. Follow the steps below to
successfully replicate:
1. Build nr-softmodem dependencies
2. Build nr-softmodem for (gNB, nrUE) with OAI_VRTSIM_TAPS_CLIENTset to ON.
3. Start the core network (Optional) follow this tutorial
4. Start the gNB
sudo ./nr-softmodem -O ../../../targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band78.fr1.106PRB.usrpb210.conf --gNBs.[0].min_rxtxtime 6 --device.name vrtsim --vrtsim.role server --vrtsim.timescale 0.5 --vrtsim.taps-socket ipc:///tmp/ru_socket_0
5. Start the nrUE
sudo ./nr-uesoftmodem -C 3619200000 -r 106 --numerology 1 --ssb 516 --band 78 --device.name vrtsim --vrtsim.taps-socket ipc:///tmp/ue_socket_0
6. Start the CE Server, once the UE and gNB are running properly, so the
server can connect to IPC sockets
7. Start CE client; the binaries can be downloaded from a pipeline run
or from this link
8. Move the UE in the CE client to generate a new taps array and
populate the taps in softmodems
Added a libary that can connect to a channel emulator and provide taps
as they are generated.
- Enable connection from vrtsim to channel emulation server
- Depends on flatbuffers definition file from raytracing-channel-emulator
- Depends on libanomsg-dev and flatbuffers-compiler (Ubuntu) or equivalent
- Added a compile time option ENABLE_TAPS_CLIENT to prevent other users
from being affected by additional dependencies
2 functions with same name as static to make it clearer they are separate.
remove unused copy of log_level global var.
remove threequarter sampling variable from the radio board general
configuration. The decision of sampling rate is made above. A better
behavior can be done later, like ask to the radio board what sampling
rate it can do,then use it to decide the appropiate sampling rate from
the gNB configuration. In UE case, it is another issue, as the sampling
rate would change after we decode SIB1, but also it is not developped
yet.
Remove --usim-test command line option
Remove the --usim-test option: to my knowledge, it's not used by users,
and is misleadingly placed in various places where there should not be a
difference w.r.t. USIM configuration.
When making the changes, I assumed that --usim-test would be 0 (the
default), which is the case in all executables when not specified in
options except for the nr_dlsim, nr_pbchsmi, nr_ulsim simulators.
The only exception is the initialization of PDCP from the MAC, which
does not seem to be correct (the PDCP is in the CU, so it does not make
sense to call it from the MAC which is in the DU).
Synchronized Real-Time Data Recording Application Addition
The main Features of Synchronized Real-Time Data Recording Application:
- The Data Recording Application runs in parallel to the gNB or UE
server or in another server as Data Recording or Data Lake Server
- It makes use of (an extended version) of OAI’s T-tracer framework
- It communicates with base station, and user terminal
- It synchronizes and combines data traces and control information
(meta-data) from Base station and User terminal into consistent SigMF
data sets
Details on implementation addition:
- T_tracer Extension to Support up to 35 Parameters in the T() macro
- Add traces on gNB PHY UL and related requirement: FD PUSH IQ, FD DMRS, and UL Channel estimates wi/wo interpolation, and Rx Payload bits:
1. The required memories have been created and initialized in:
openair1/PHY/NR_TRANSPORT/nr_ulsch_demodulation.c
2. Those memories: memory for DMRS signals, memory for channel
estimates based on DMRS positions, memory to store slot grid with
channel coefficients based on DMRS positions after interpolation,
and memory to store extracted data including PUSCH + DMRS.
3. The input parameters to nr_pusch_channel_estimation() has been
updated to get the pointer to the added memories of
pusch_dmrs_slot_mem and pusch_ch_est_dmrs_pos_slot_mem
(openair1/PHY/NR_ESTIMATION/nr_ul_estimation.h)
4. The DMRS grid of NR slot and the estimated channel coefficients at
DMRS locations are logged to created memories in:
openair1/PHY/NR_ESTIMATION/nr_ul_channel_estimation.c
5. The function inner_rx in
openair1/PHY/NR_TRANSPORT/nr_ulsch_demodulation.c is updated to log
the extracted ULSCH PRBs and the interpolated channel coefficients.
6. The T-macro() has been called in
(openair1/PHY/NR_TRANSPORT/nr_ulsch_demodulation.c) to trace added
traces: T_GNB_PHY_UL_FD_DMRS, T_GNB_PHY_UL_FD_CHAN_EST_DMRS_POS,
T_GNB_PHY_UL_FD_PUSCH_IQ, T_GNB_PHY_UL_FD_CHAN_EST_DMRS_INTERPL
- Add traces on UE PHY UL and related requirement: Tx Scrambled bits and Tx payload bits
1. Update input parameters to nr_ulsch_encoding () in
nr_transport_proto_ue.h to get number_dmrs_symbols to be added to
meta-data.
2. In nr_ulsch_coding.c: Trace UE PHY UL Payload TX bits (T_message:
T_UE_PHY_UL_PAYLOAD_TX_BITS) including related meta-data and UTC
time.
3. In nr_ulsch_ue.c: Trace UE PHY UL Scrambled TX bits (T_message:
T_UE_PHY_UL_SCRAMBLED_TX_BITS) including related meta-data and UTC
time.
4. Fix the input prameters in nr_ulsch_encoding () called in
(openair1/SIMULATION/NR_PHY/ulschsim.c) since a new input parameter
has been added.
- Add Data Collection Services (T-Tracers for gNB and UE)
1. Add _tracer_app_gnb and t_tracer_app_ue apps to common/utils/T/tracer/Makefile
2. Add Data collection Service for gNB: common/utils/T/tracer/t_tracer_app_gnb.c
3. Add Data Collection Service for UE: common/utils/T/tracer/t_tracer_app_ue.c
- Add Shared memory configuration
(common/utils/T/tracer/shared_memory_config.h), since we will have too
much memory consumption on the stack if the T-tracer is not fast
enough to process the traces or if we have too much traces. As a
result, tracers start to capture data, write data in shared memory,
then close the T-Tracer after getting the recording of N slots. The
Data recording App will read data from the shared memory.
- Add Main app of Data Recording Application v1.0 including: Config
files, SigMF Interface, Config Interface, Sync Service, and def
messages: The data recording App includes mainly the following files:
1. The main app: data_recording_app_v1.0.py that has the data control
service, interact with tracers, data sync and conversion service.
2. The configuration file:
common/utils/data_recording/config/config_data_recording.json
3. The wireless dictionary file:
common/utils/data_recording/config/wireless_link_parameter_map.yaml
4. Config Interface
(common/utils/data_recording/lib/config_interface.py) that reads
the configuration for both gNB and UE.
5. Sync interface (common/utils/data_recording/lib/sync_service.py)
that sync captured data for gNB and UE before saving them in SigMF
format
6. The SigMF Interface
(common/utils/data_recording/lib/sigmf_interface.py) to store
recorded data and meta-data in SigMF format
7. A simple script
(common/utils/data_recording/sync_validation_demo.py) to validate
that the recorded bits from gNB and UE are in Sync
- For more info look to doc/data_recording.md
Remove the --usim-test option: to my knowledge, it's not used by users,
and is misleadingly placed in various places where there should not be a
difference w.r.t. USIM configuration.
When making the changes, I assumed that --usim-test would be 0 (the
default), which is the case in all executables when not specified in
options except for the nr_dlsim, nr_pbchsmi, nr_ulsim simulators.
The only exception is the initialization of PDCP from the MAC, which is
not correct (the PDCP is in the CU, so it does not make sense to call it
from the MAC which is in the DU). Instead, always initialize from main,
even in the NSA case (NSA was covered by the incorrect initialization
from MAC).
This in turn let to some more cleanup around function du_rlc_data_req().
After receiving GTP packets at the DU, they were given to the PDCP to
enqueue the packet at RLC. This does not work anymore, since the PDCP is
not initialized; it also does not seem necessary, as this enqueue
functionality is necessary to decouple PDCP and RLC to avoid deadlocks
in monolithic, but in split-mode, this cannot happen. Instead, call
directly into the RLC when receiving GTP packets.
- Update input parameters to nr_ulsch_encoding () in
nr_transport_proto_ue.h to get number_dmrs_symbols to be added to
meta-data.
- In nr_ulsch_coding.c: Trace UE PHY UL Payload TX bits (T_message:
T_UE_PHY_UL_PAYLOAD_TX_BITS) including related meta-data and UTC time.
- In nr_ulsch_ue.c: Trace UE PHY UL Scrambled TX bits (T_message:
T_UE_PHY_UL_SCRAMBLED_TX_BITS) including related meta-data and UTC
time.
- Fix the input prameters in nr_ulsch_encoding () called in
(openair1/SIMULATION/NR_PHY/ulschsim.c) since a new input parameter
has been added.
Add WLS as a transport option for VNF/PNF, refactor existing options
This MR adds a new transport mechanism for the VNF and PNF split, using
the Intel WLS library, which makes use of DPDK and shared memory to
transport messages. This transport mechanism is what is used to
interface with Radisys ODU, while also working with OAI VNF/PNF.
The VNF and PNF have been refactored so that the transport-specific
functions are isolated from the rest of the logic, and as such,
interchangeable by means of function pointers.
The same change is done for the packing/unpacking procedures, allowing
to switch between FAPI and nFAPI encoding.
This MR also reduces the amount of duplicated code, by refactoring the
VNF with Aerial, which now only has the transport-relevant functions, as
well as the ones that are unique to it ( for example, the unpacking
procedures where a secondary data buffer is used for the message
payloads )
Additionally a new callback is added to the VNF to process
ERROR.indication messages, which currently only indicates which message
originated the error, and which error occurred.
Recently f buffer was changed to hold packed bits and the correspoinding
change in dlsim was not done so the number of error bits before decoding
was incorrectly reported. This commit fixes it.
NR RRC Reject UE
Improvements in procedures to handle RRCReject message both at gNB and
UE. At gNB we send RRC Reject if the UE cannot be given resources to go
into connected mode.
Adds 3 new function pointers to the P5 and P7 PNF structures, allowing to configure which function to use to pack/unpack the messages, as well as unpack the message header, being then used seamlessly regardless of using the FAPI or nFAPI functions.
Changes the header unpack and message unpack functions to return true on success and false on failure, instead of an int
- remove hardcoded values
- adapt gNB RRC code
- adapt gNB MAC code
- adapt physical simulators, where we put the hardcoded values
that were everywhere else before; if there is a need for those
simulators to get configurable values, more work is needed
(but it's doubtful that it is needed)
A number of radio-related RRC parameters, e.g., CellGroupConfig,
"originate" at the DU and are sent to the CU for forwarding to the UE
only. Similarly, there are additional parameters, e.g., RLC-BearerConfig
(part of CellGroupConfig), that originate at the DU.
Hence, the DU decides about these parameters, depending on the MAC state
and capabilities. To clarify this, move the existing
openair2/RRC/NR/nr_rrc_config.{c,h} => openair2/LAYER2/NR_MAC_gNB/nr_radio_config.{c,h}
So that developers know that while those are RRC parameters, they
originate at the DU.
In other words, the CU/RRC is not supposed to use any of these functions
in the RRC. Correspondingly, includes of this file have been cleaned up
(and when they are not necessary at the MAC as well).
Add physim tests into ctest framework
Convert physim testcases listed in
cmake_targets/autotests/test_case_list.xml into ctest. Note: Tests for
dlsim_tm4 are excluded, due to compilation issues.
CTest evaluates success based on return code: '0' = pass, non-zero =
fail. For some simulators, the return code is non-zero even when the
test is successful (as indicated by success messages in the test logs).
For some simulators, the return code is always '0'. This inconsistency
has been address in the first two commits of this MR.
To build and execute these tests:
- using cmake
cd openairinterface5g
mkdir build && cd build # you can also do that in cmake_targets/ran_build/build
cmake .. -GNinja -DENABLE_PHYSIM_TESTS=ON && ninja tests
ctest
- using build_oai: physim-related ctests are activated when PHY
simulators are built (use build_oai with '-P' or '--phy_simulators'
option)
cd openairinterface5g/cmake_targets
./build_oai --ninja --phy_simulators
cd ran_build/build
ctest
Link to newly created 4g and 5g RAN-Physim-Cluster pipelines:
- RAN-Physim-Cluster-4G: https://jenkins-oai.eurecom.fr/job/RAN-Physim-Cluster-4G/
- RAN-Physim-Cluster-5G: https://jenkins-oai.eurecom.fr/job/RAN-Physim-Cluster-5G/
Setting the DEBUG_UE_TIMING flag caused a flood of UE timing logs, resulting
in dlsim output logs as large as 1.5MB per test in CI. This commit comments
out the line where we set the flag to reduce log verbosity.
- Change return value of nr_dlsim, nr_pbchsim and nr_pucchsim to:
- Return '0' if test succeeds (indicated also by "PDSCH/PBCH/PUCCH test
OK" in the test log).
- Return '1' if test fails.
Improvements for LDPC encoding
AVX512 modifications for LDPC encoding: interleaving, ZC384 BG1, output
formatting for encoder, segmentation (memcpy instead of loop). some
improvement in TX for aarch64 in same places where AVX512 support was
added. Also, rate matching and interleaving are done on bytes containing
8 segments and reformatting of the output is done at the end of segment
processing instead of after ldpc encoding.
This improves the overall performance of the NR DL transmitter in gNB
See the merge request description for numbers.
1. nrLDPC_coding_segment_encoder: pointer not aligned on 64 bits
An undefined behavior was happening because of a shift on a __m64 which
was actually a uint32_t which was not aligned on 64 bits.
This commit suggests a fix by properly loading into a __m64 with _mm_set_pi32
before performing the shift.
2. nr_rate_matching: Filler bits detection
Previously, if the bit selection was reaching Ncb and restarting selection from the beginning of encoded data, the filler bits were detected by testing the bytes again NR_NULL which was equal to 2.
But on this branch the bits of up to 8 segments are stored in one byte while doing rate matching so that one byte could be tested to be a filler while it is not.
So this commit changes the way to test filler bits.
Instead of relying on NR_NULL, bit selection now relies on the offset and size of filler bits.
3. nr_ulsch_coding: missing filling f with zeros
The array `f` of the UE UL HARQ process was not filled with zeros between transmissions.
This is a problem if the encoder does not properly overwrite its output.
In order to avoid such situation, this commit adds a memset to fill `f` with zeros before passing it to the encoder.
4. nrLDPC_coding_segment_encoder: missing init of f to zeros
In the encoder, `f` is not filled with zeros before being used.
`f` is instead somehow filled with arbitrary values.
When writing to `output` by 64 bit vectors, some arbitrary bits may be added after the segment.
Then the arbitrary added ones are not overwritten when writing the next segment because of writing with a logical or.
This commit properly fills `f` and `f2` with zeros.
5. nr_ulschsim & nr_dlschsim: Adapt modulation to new encoder output
The QPSK symbols that are feed to the channel model of nr_dlschsim were determined based on the bytes of the encoder output.
With the new output of the encoder, it had to be reworked to determine the QPSK symbols based on the bits of the encoder output.
1. 3GPP Rate-matching/interleaving on 8-segment blocks, deinterleaving at output of multi-segment processing.
2. Bit-packing done in nrLDPC_coding_segment_encoder.c now instead of nr_scrambling.
Interestingly, it improves performance significantly too.
Tested for AVX512 only for now.
- rewrite add_UE_to_list() and rewrite remove_UE_from_list() to simplify
list handling
- return pointer from get_new_nr_ue_inst(); it's completely freed by
delete_nr_ue_data()
- have add_new_UE_RA() add UE context to access list; remove with
nr_release_ra_UE()
- have add_connected_nr_ue() only add UE to connected list; to move from
access to connected use transition_ra_connected_nr_ue(); remove with
mac_remove_nr_ue() as previously
- free memory on problems during RA
- add some documentation
- in NSA/HO: check for pre-configured RA process
- there are asserts in all functions to clarify when a UE has RA