While this does not happen in real use, and unset btcx can lead to
segfaults in test cases. The other code outside of gprs_bssgp_pcu.cpp
does not depend on bctx being non-NULL:
Sponsored-by: On-Waves ehf
The missing const qualifier prevents the llist_empty() C++ wrapper
function from being compiled successfully when it is used.
Sponsored-by: On-Waves ehf
The TBF object are currently created by using talloc_zero/talloc_free
directly from plain functions. Therefore C++ constructors and destructors
are not called. So the only initialisation that is done is setting
every member to 0. Non POD members do not have their constructors
called either, which makes it impossible to use the current LListHead
class for real members when the LListHead::m_back member has to be set.
This commit changes the TBF allocation functions to call the
corresponding C++ constructor after the call to talloc_zero and to
register the C++ destructor with the talloc context, so that is is
called before talloc_free actually frees the memory.
With this change, non-POD members and custom
constructors/desctructors can be used with gprs_rlcmac_tbf,
gprs_rlcmac_dl_tbf, and gprs_rlcmac_ul_tbf.
Note that this change is only a single step of the plan to turn the
TBF classes into real C++ classes.
Sponsored-by: On-Waves ehf
Currently the pending LLC packets are lost in some cases when MS
objects are merged, for instance after a RACH when there were 2 MS
object for the same MS (they get merged, when the TLLI is known for
both objects).
This patch modifies GprsMs::merge_old_ms to move all pending LLC
packets (if there are any) to the current MS object.
Sponsored-by: On-Waves ehf
This methods takes all LLC frames from the old LLC queue and moves
them into the current. If both queues are ordered chronologically
(recv_time), the resulting queue is also ordered.
Sponsored-by: On-Waves ehf
Currently all active TBF of an MS are killed if a Packet Resource
Request is received from the MS. In general this happens after a RACH
request. This does not happen after a resource request that has been
included into a Downlink Ack/Nack.
Sometimes an UL TBF is requested by an MS via RACH while a DL TBF is
running for instance to send a TCP Ack. This can happen, if a former
request via PACCH did not work.
This commit removes the killing of the DL TBF from
gprs_rlcmac_pdch::rcv_resource_request().
Sponsored-by: On-Waves ehf
This commit fixes several issues:
- Set MS class in request
- Set IMSI in establish_ul_tbf_two_phase
- Fake assigment acknowledgement in establish_ul_tbf_two_phase
- Fix TFI bit offset to 1 (was 2)
Sponsored-by: On-Waves ehf
Currently the merging of the meta information (MS class, IMSI) takes
place in gprs_rlcmac_tbf::merge_and_clear_ms(). This makes it
difficult to merge the internal state and does not directly relate to
TBFs anyway.
This commit moves this into a new method GprsMs::merge_old_ms.
Sponsored-by: On-Waves ehf
Currently the signal S_NS_ALIVE_EXP emitted by the NS layer if the
alive check has timed out too often is ignored. This prevents the PCU
from reconnecting to the SGSN if it has not been accessible for some
time.
This commit modifies nsvc_signal_cb to reset the NSCV if
S_NS_ALIVE_EXP is sent, so that the PCU continues to send NS RESET
message if that happened.
Sponsored-by: On-Waves ehf
Currently there is not support for Network Service (NS) logging.
This commit adds the missing definitions and sets the default level
to INFO. Further configuration can now be done with the 'logging
level ns' VTY command.
Sponsored-by: On-Waves ehf
This commit fixes the go_parent_cb API according to libosmocore's
commit of the same name.
Fixes:
pcu_vty.c:799:2: warning: initialization from incompatible pointer
type [enabled by default]
.go_parent_cb = pcu_vty_go_parent,
Sponsored-by: On-Waves ehf
The IMSI '000' is used as default value for an incoming BSSGP
message's IMSI IE. This can lead to the retrieval of the wrong MS
object from the storage.
This commit changes the get_ms method to skip the IMSI search if such
an IMSI is passed as selector.
Note that changing the default value in the BSSGP code does not help
here.
Sponsored-by: On-Waves ehf
The confirm_tlli method does not handle TLLI clashes in the MS
storage.
This commit changes gprs_rlcmac_dl_tbf::handle() to use update_ms
instead.
Sponsored-by: On-Waves ehf
Currently if an MS retries to access the PCU by using RACH and if
there is already an entry for that MS, a duplicated MS object
referring to the same TLLI is created. This is caused by blindly
setting the TLLI without querying the MS storage to avoid
inconsitencies.
This leads to several entries in the MS storage that are assigned to
the same TLLI. If that happens, 'show ms all' can display multiple
entries with the same TLLI (note that an MS object can belong to
several TLLIs, so there might be an intersection that is not visible
in the list) or 'show tbf all' can show entries with MS_CLASS == 0 in
some cases.
This commit changes update_ms() to merge and clean up old entries
that belong to the given TLLI if they exist. Some data (like the MS
class) is copied to the new MS object.
Note that TBF belonging to the old MS object are deleted immediately
if they have not registered a timer.
Sponsored-by: On-Waves ehf
The current default interval is 2s which seems to be too short when
the DL TBF has to be established. This may cause freezing or really
slow TCP connections.
This commit increases the default value to 4s. When the
dl-tbf-idle-time is set, DL TBF are established less frequent, so
smaller values (like 2s or below) can be used to improve the average
latency when the load is high.
Sponsored-by: On-Waves ehf
When doing an RA Update the network can request to change the TLLI.
In this case, there can be 2 MS objects with different TLLI for a
single real MS. The first is associated with the old TLLI and the
IMSI, while the second is associated with the new TLLI and no IMSI if
it had been created for the uplink TBF. When the first message with
the new TLLI and the IMSI arrives from the network, the PCU is able
to detect this.
Currently this is not handled properly. The TBFs of the old MS object
are not cleaned up properly, keeping the old MS from being deleted.
This patch modifies gprs_rlcmac_dl_tbf::handle to check for this and
if neccessary to move an existing DL TBF and to clean up the old MS
object to ensure its deletion.
Sponsored-by: On-Waves ehf
Currently when receiving a PACKET DL ACK/NACK message with the Final
Ack Indicator bit set, the TBF's state is set to
GPRS_RLCMAC_WAIT_RELEASE but T3193 is only started when the LLC queue is
empty. Otherwise the reuse_tbf() method is called to establish a new
DL TBF. In that case, the timer is not started. This will leave the
current TBF without a timer so it is potentially not released later
on.
This is recognisable by sticky entries in the output of the
'show tbf all' command and possibly allocation failures if there are
too many of them.
This commit changes the code to always start T3193 to make sure, that
a timer is always active when the the state is set to
GPRS_RLCMAC_WAIT_RELEASE.
Note that TS 44.060, 9.3.2.6 requests to release the 'old' TBF
immediately in some cases, which is not implemented by this change.
This will lead to a longer reservation period of the TFI only, which
is safer than reassigning it too early.
Sponsored-by: On-Waves ehf
Currently the initial_cs_dl value is used to compute the maximum leak
rate. This can be too low if adaptive CS selection is used.
This commit changes gprs_bssgp_tx_fc_bvc to derive the max CS level
from the configuration.
Sponsored-by: On-Waves ehf
Currently CoDel is disabled by default.
This commit enables CoDel on start up with the default interval time,
equivalent to the 'queue codel' VTY command.
To disable CoDel, use the 'no queue codel' command.
Sponsored-by: On-Waves ehf
Currently packets are only dropped if they have reached their maximum
life time. This leads to LLC queues being constantly filled under
load, increasing the latency up to the maximum life time. This kind
of bufferbloat hinders TCP's congestion avoidance algorithms. To keep
the queues short, the CoDel active queue management algorithm can be
used.
This commit changes to llc_dequeue method to apply the CoDel
algorithm to selectively drop LLC frames before they passed to the
TBF layer to be encoded in BSNs. This feature is currently disabled
by default.
The CoDel state is managed per MS since the LLC queues are also kept
in the MS objects.
Note that there is still some buffering in the TBF objects, in the
worst case (CS4) 3.5kByte + LLC-MTU octets are stored there. The
resulting additional packet delay is not (yet) taken into account for
CoDel.
Also note that configuration changes are applied to new MS objects
only.
The following VTY commands are added to the 'pcu' node:
- queue codel activates CoDel, the interval is selected by
the implementation
- queue codel interval <1-1000>
activates CoDel with a fixed interval given
in centiseconds (10ms-10s)
- no queue codel deactivates CoDel
Which interval value to use is still an open issue. For high speed
links (e.g. Ethernet), CoDel suggests 100ms. For slower links, the
expected RTT is recommended. The current implementation uses a
default value of 2000ms.
Measurements:
Note that the following measurements depend on several other factors,
most notably the interaction with the SGSN's flow control. They are
just examples to give an idea how CoDel might influence some
parameters.
The measurements have been done with a single E71, first with a
running ping only (Idle), then with an additional TCP download
of a 360k file (Busy). The CoDel interval was set to 1s.
- Idle :
ping ~400ms, avg queue delay 0ms, dropped 0
- Busy, No CoDel:
ping ~6s, avg queue delay 4-6s,
dropped 0, scheduled 948, duration 54s
- Busy, CoDel:
ping 500-1500ms, avg queue delay ~600ms,
dropped 77, scheduled 1040, duration 60s
More measurements with two MS downloading in parallel (two
independant measurements per case).
- Busy, No CoDel:
dropped 0, scheduled 1883, duration 121s
dropped 19, scheduled 2003, duration 133s
- Busy, CoDel:
dropped 22, scheduled 1926, duration 116s
dropped 22, scheduled 1955, duration 108s
Sponsored-by: On-Waves ehf
This commit adds an implementation of the CoDel algorithm based on
the reference pseudocode presented in
http://queue.acm.org/appendices/codel.html. Instead of abstracting
the queue itself, the implementation provides a time stamp based
automaton which is invoked after a package has been dequeued.
Note that the modifications of the algorithm shown in
https://tools.ietf.org/html/draft-ietf-aqm-codel-01 are not yet
applied.
Sponsored-by: On-Waves ehf
Currently the values Bmax/R default MS are computed under the
assumption than min(4, N_PDCH) DL slots are allocated for an MS, even
if multislot assignment is not enabled.
This commit changes the computation to assume 1 DL slot if algorithm
A is selected or the dynamic algorithm is used and has disabled
multislot assigment due to high load.
Sponsored-by: On-Waves ehf
Currently there is no persistent state being used in
alloc_algorithm_dynamic. So algorithm B is even used in persistent
high usage scenarios. If there are many active TBFs, multislot
assigments are not fair, because MS of a "higher" multislot class get
higher troughputs. On the other hand, as long as all PDCH are busy no
bandwidth will be wasted even if all MS use algorithm A.
This commit modifies alloc_algorithm_dynamic to disable algorithm B
when that call fails. It then keeps it disabled until there is a
single PDCH which is idle (it is considered idle, if there is at most
one active DL TBF assigned to it).
Sponsored-by: On-Waves ehf
Currently algorithm A can select an TBF even when there is no free
TBF in the reverse direction. While this does not necessarily lead to
an allocation failure, the probabily is higher. In addition, the
current slot reservations are not taken into account.
This commit changes the selection algorithm to prefer slots where TFI
are available in both directions and which are less reserved.
Sponsored-by: On-Waves ehf
Currently each tx_window combination is checked only once by using a
set containing the sets of TX slots that have been checked already.
This approach does not ensure, that num_tx and ul_ts really match the
tx_window being tested. This does not make a difference with the
current test cases probably because num_tx starts with 1 and is
increased each iteration. Since the bitmap optimization is equivalent
to a cache optimization strategy that only uses tx_window as key. On
the other hand, ul_ts, num_tx, and rx_mask cannot be derived from
tx_window, but these values are also refered to after the call to
test_and_set_bit(). This makes it difficult to prove that correctness
of the caching. While this will not lead to a defect, the results
might be less optimal.
This commit changes the optimization strategy to skip all tx_window
where ul_ts and ul_ts+num_tx-1 are not both contained. This provides
a similar degree of optimization like the set approach (only the
iteration with num_ts == 8 is not optimized, which only applies to to
ms class 18 and 29 MS) but ensures that the values of the related
variables have a clear relationship.
Note that the bitset based optimization for rx_window does not suffer
from a possible cache inconsistency, since only tx_window and
rx_window (tx_slot_count and rx_slot_count can be derived from the
windows and thus are covered by the cache key) are used after the call
to test_and_set_bit(). tx_window is constant over the whole lifetime
of the cache.
Sponsored-by: On-Waves ehf
The dynamic algorithm behaves like B until there are no TFI left.
This commit changes the default algorithm to to former.
Ticket: #1934
Sponsored-by: On-Waves ehf
The idea behind this meta algorithm is to automatically select one of
the other algorithms based on the system state. Basically algorithm B
will be selected if the PDCH usage is low to improve throughput and
latency. Algorithm A will be selected to support more concurrent MS.
This commit adds a first simple state-less version of this algorithm
that always tries B first and only if that fails A is tried
afterwards.
The following VTY command is added to the 'pcu' node:
- alloc-algorithm dynamic
Ticket: #1934
Sponsored-by: On-Waves ehf
This part of algorithm_b has already been disabled. Further work may
depend on this, but it is going out of sync. So this commit removes
it completely.
Sponsored-by: On-Waves ehf
Currently these algorithms modify other objects (MS, TBF, PDCH) even
if the allocation will fail later on. To implement an algorithm that
dynamically tries another algorithm on failure (e.g. A after B), the
first (failing) algorithm should not change or damage anything.
This commit refactors algorithm A and B to delay the actual allocation
until it is known that the allocation will not fail.
Ticket: #1934
Sponsored-by: On-Waves ehf
Currently this code path is only used, if an allocation has been
taken place in a former call to an allocation algorithm function.
If this was for an DL TBF, the first common TS was selected,
otherwise the least used common TS was selected for an UL TBF.
The shrinking of the UL set (to 1<<first_common_ts) is done in the
latter case.
This commit removes an additional code path that aligns the UL set to
first_common_ts, because it has no more influence on the set of
common TS after both UL and DL TBF have been allocated.
Sponsored-by: On-Waves ehf
Currently there is no simple way to determine, whether the MS object
protected by a guard will continue to exist after the guard object is
destroyed.
This patch adds a is_idle() method that will return true if the MS
object is just kept by the guard from being idle. In that case, the
MS object would either be deleted or return true for
GprsMs::is_idle() after the guard's destruction, provided that no
TBF attachment took place in between.
Sponsored-by: On-Waves ehf
Currently the TBFs are registered in a TFI indexed array within the TRX
objects. TBFs can be searched globally by TFI and TRX number. This
conflicts with the use of the same TFI for different TBF on different
PDCH. This use case requires the specification of the PDCH as
additional search dimension.
This commit moves the TFI index TBF arrays into the PDCH objects. The
related methods are updated accordingly.
Ticket: #1793
Sponsored-by: On-Waves ehf
Currently the TFI are managed per TRX, thus only a maximum of 32 TBF
per direction and per TRX are possible simultaneously.
This commit modifies algorithm_a() to allow the sharing of TFI
between different PDCH. Since algorithm A only assigns a single slot
to each TBF, the TFI of each PDCH can be assigned independently.
This increases the maximum to 32 TBF per direction and per PDCH
concerning the TFI allocation.
Ticket: #1793
Sponsored-by: On-Waves ehf
Currently the TFI and the TRX have to be determined before the actual TBF
allocation function is called, passing TFI and TRX number as
parameters. This does fit to TFI reuse for different slots, since
this were tightly coupled with the slot selection.
This commit just moves the TFI selection into the alloc_algorithm
functions. The tfi parameter is removed from the the TFI alloc
functions. The trx parameter is changed into use_trx to optionally
limit the trx selection (same semantics like in tfi_find_free).
Sponsored-by: On-Waves ehf
Currently a single bit set is used to maintain a set of used TFI
without distinguishing between uplink and downlink. Since the
namespaces of UL and DL TFI are separate, this implementation is
not correct.
This commit changes gprs_rlcmac_pdch to use a separate bit set for
each direction. It also replace the corresponding conditional fprintf
statement in check_tfi_usage (AllocTest.cpp) by an equivalent
OSMO_ASSERT.
Sponsored-by: On-Waves ehf
Currently the handling of MS_B and MS_C is not compliant with TS
45.002, annex B.1. These values may only interpreted as 0, if
frequency hopping is not enabled and if there is no change from Rx to
Tx or vice-versa.
This commit sets Ttb/Trb to 1 if the table entry is MS_B/MS_C, since
only combined down/up access modes are supported.
Sponsored-by: On-Waves ehf
Currently the masks are computed equally for each class type. This
does not make much sense for class type 2 MS, since those are capable
to work in full duplex mode.
This commit sets the masks to 0xff for class type 2 MS.
Sponsored-by: On-Waves ehf
According to TS 45.002, 6.4.2.2 the choice whether Tta or Tra has to
be applied, depends on the medium access mode (currently always
dynamic) and the number of UL/DL slots. Currently either value can be
used which might result in combinations not covered by the spec.
This commit changes find_multi_slots() to skip non-compliant
combinations.
Note that this code will have to be extended, if other medium
access modes are implemented.
Sponsored-by: On-Waves ehf
The local enums MASK_TT and MASK_TR replace the hard coded indices.
The variable m_idx is renamed to mask_sel for more clarity.
Sponsored-by: On-Waves ehf
Both functions only differ in the computation of the value for
num_tbfs.
This commit merge both functions and adds a parameter containing a
function for that compuation.
Sponsored-by: On-Waves ehf
The commit 506f156f7a has reverted the
TS search order. The outer loop exit condition was not updated
accordingly. This bug would would only lead to an error if there were
multiple TRX where the first TRX has not got any PDCH assigned.
This commit corrects the break condition.
Fixes: Coverity CID 1311776
Sponsored-by: On-Waves ehf
Fixes: Jenkins build #609 warning
Addresses:
llc.cpp:56, GNU C Compiler 3 (gcc), Priority: Normal
comparison between signed and unsigned integer expressions
Sponsored-by: On-Waves ehf
Currently the slot selection of algorithm A is based on the current
slot usage by active TBF. Especially in the Dl after UL case which
reflects the commen use case "MS initiates TCP connection", the
resulting distribution is not optimal with respect to PDCH usage.
This commit changes the implementation to use the slot reservation
information instead.
Sponsored-by: On-Waves ehf
Currently the search for an enabled PDCH slot for SBA start with the
first TS. If there are more than 2 PDCH slots enabled, this slot will
conflict with an existing multislot reservation for most multislot
classes. This were less likely if the search were reversed and
started with the last slot due to the 3 slot shift between Tx and Rx.
When multislot allocation is enabled and several MS are connected,
and increased rate of poll timeouts can be observed.
This commit tries to reduce the number of poll timeouts by reverting
the slot search order for SBA allocation.
Sponsored-by: On-Waves ehf
The current logging statements within the inner loop of
find_multi_slots drain quite a lot of CPU resources even if
LOGL_DEBUG is not enabled. This might cause issues on the target
hardware.
This commit disables these LOGP calls unless the
ENABLE_TS_ALLOC_DEBUG macro has been set explicitly. This results in
a reduction in the CPU usage reported by callgrind for
find_multi_slots from 42% to 25% when executing AllocTest.
Sponsored-by: On-Waves ehf
According to callgrind, this function consumes 33% CPU when running
the AllocTest program.
This commit uses the assigned_usf() method to get the USFs allocated
by a PDCH instead of traversing the TBFs.
Sponsored-by: On-Waves ehf
Currently is is rather expensive to get TFI and USF usage per PDCH,
because the TBFs need to be scanned to get that information.
This commit adds corresponding bit sets which get updated by the
attach_tbf/detach_tbf methods of the gprs_rlcmac_pdch class.
Sponsored-by: On-Waves ehf
Currently the search of the "best" slot combination is done
separately from the UL slot selection, which can lead to an
allocation failure due to USF exhaustion even if another combination
had been possible.
This commit reduces the probability for this event by skipping UL
slots without free USF while calculation the capacity.
Note that the implementation is rather inefficient which will be
fixed by the following commits.
Sponsored-by: On-Waves ehf