Skip to content

Loading builds...

Changes

#28908 (Jul 1, 2026, 11:58:27 AM)

redmine: upgrade to 6.1.3

Related: SYS#8097
Change-Id: I3e7f746b1a96ff98bbdea2e043a88b9a492672d2
Oliver Smith at

#28907 (Jul 1, 2026, 11:47:46 AM)

library: add f_gsm_fn_{sum,sub,diff}()

Change-Id: Ie91ccef5d3f170f4a341a6cf9d3323a896b299e6
Vadim Yanitskiy at

#28906 (Jul 1, 2026, 11:47:42 AM)

bts: TC_pcu_interf_ind: check reporting interval instead of absolute FN

Recent osmo-bts commit 53f0ec29 broke TC_pcu_interf_ind:

  Verdict: fail reason: Odd TDMA frame number := 935

There's no requirement that periodic interference reports must land
on a TDMA frame number satisfying 'fn mod 104 == 0' - only that they
keep arriving every configured averaging period.  Instead, verify
that the interval between consecutive reports equals 104 TDMA frames
(1 SACCH period), using the new f_gsm_fn_sub() helper.

Change-Id: Ia96f2926400bae8c0a6fb8f81eb56b48ca5f2de9
Related: 53f0ec29 ("l1sap: fix duplicate RF RESOURCE INDICATION on clock bootstrap")
Vadim Yanitskiy at

#28905 (Jul 1, 2026, 11:15:06 AM)

library: add f_gsm_fn_{sum,sub,diff}()

Change-Id: Ie91ccef5d3f170f4a341a6cf9d3323a896b299e6
Vadim Yanitskiy at

#28904 (Jul 1, 2026, 11:15:02 AM)

bts: TC_pcu_interf_ind: check reporting interval instead of absolute FN

Recent osmo-bts commit 53f0ec29 broke TC_pcu_interf_ind:

  Verdict: fail reason: Odd TDMA frame number := 935

There's no requirement that periodic interference reports must land
on a TDMA frame number satisfying 'fn mod 104 == 0' - only that they
keep arriving every configured averaging period.  Instead, verify
that the interval between consecutive reports equals 104 TDMA frames
(1 SACCH period), using the new f_gsm_fn_sub() helper.

Change-Id: Ia96f2926400bae8c0a6fb8f81eb56b48ca5f2de9
Related: 53f0ec29 ("l1sap: fix duplicate RF RESOURCE INDICATION on clock bootstrap")
Vadim Yanitskiy at

#28903 (Jul 1, 2026, 9:48:54 AM)

pySim.log: fix E0611: No name 'style' in module 'cmd2'

Change-Id: I191ea56f4c6e4e1916369f69fe2e1653e1d92df1
Fixes: 597f1e0 ("pySim.log, pySim-shell: fix compatibility with cmd2 >= 3.0.0")
Vadim Yanitskiy at

#28902 (Jun 30, 2026, 4:25:48 PM)

common: reset lchan meas state in gsm_lchan_release()

lchan->meas (including interf_meas_num and num_ul_meas) is normally
only reset by lchan_meas_reset() called from rsl_tx_chan_act_ack() on
RSL CHANNEL ACTIVATION.  Idle logical channels are never RSL-activated,
so their measurement state is never reset via that path.

On an OML link re-establishment, osmo-bts does not exit: abis.c tears
down the signalling links, the bts_shutdown FSM powers down all TRXs,
and then waits for reconnect.  The gsm_bts/trx/ts/lchan structures
remain in memory, so stale interf_meas_num survives the reconnect.

This is why we're seeing these ERRORs while running ttcn3-bts-test:

(bts=0,trx=2,ts=4,ss=6) Not enough room to store interference report (0dBm)

Add a lchan_meas_reset() call to gsm_lchan_release(), which is called
from gsm_ts_release() when the nm_channel_fsm enters state
NM_CHAN_ST_OP_DISABLED_NOTINSTALLED.  This is exactly the right
moment: the radio is fully stopped, so no new samples arrive.

Change-Id: I18dc9d30417b0c5b2e579660d4a087d93445f956
AI-Assisted: yes (Claude)
Vadim Yanitskiy at

#28901 (Jun 30, 2026, 4:25:44 PM)

common: stop buffering UL measurements when SACCH is deactivated

When the BSC sends RSL DEACT SACCH, the per-SACCH UL measurement drain
stops (it runs on SACCH timing), but the producer in lchan_new_ul_meas()
keeps appending the measurement contributions from every received
TCH/SDCCH burst.  After one SACCH period (104 frames) the 104-slot
uplink measurement buffer fills up, yielding a flood of:

  NOTICE measurement.c:336 no space for uplink measurement, num_ul_meas=104

Add a bool sacch_active flag to gsm_lchan, set to true in the common
l1sap_chan_act() and clear in l1sap_chan_deact_sacch().  Guard
lchan_new_ul_meas() with this flag so that measurements are silently
discarded while SACCH is inactive - there is nothing to drain the
buffer and no SACCH channel on which to report the results to the BSC.

Change-Id: I3943c788cab5d2411b06ac681d4d412852bac0a7
AI-Assisted: yes (Claude)
Vadim Yanitskiy at

#28900 (Jun 30, 2026, 4:22:27 PM)

common: flush paging queue in nm_bts_fsm's NOTINSTALLED on_enter

paging_reset() exists to flush stale paging records from the queue,
but was never called anywhere.  Stale paging records can accumulate
when the OML link goes down: osmo-bts does not exit, so the paging
queue survives into the next BSC session.

Call it alongside bts_cbch_reset() and bts_asci_notification_reset()
in st_op_disabled_notinstalled_on_enter(), which fires after all TRXs
are confirmed closed and before a new OML connection is accepted.

Change-Id: I109ab282986b68b68ba5c11859c44b771c0416fd
AI-Assisted: yes (Claude)
Vadim Yanitskiy at

#28899 (Jun 30, 2026, 3:28:42 PM)

rest_api_response_schema: add missing error codes

In SGP.32 V.1.2, new error codes were added to EnableProfileResult,
DisableProfileResult, DeleteProfileResult and AddEimResult

See also: SGP.32, section 2.11.2

Change-Id: I525ca9d3b7fb870405d374160272d8ec26c85880
Related: SYS#8100
pmaier@sysmocom.de at

#28898 (Jun 30, 2026, 3:26:42 PM)

esipa_rest_utils: align IpaEuiccDataResponse to SGP.32 V.1.2

The ASN.1 struct IpaEuiccDataResponse has renamed the error code
member from ipaEuiccDataError to ipaEuiccDataErrorCode. The new
ipaEuiccDataErrorCode is a sequence that has an ipaEuiccDataErrorCode
member, which is the equivalent of the previously existing
ipaEuiccDataError member.

See also: SGP.32, section 2.11.2.2

Change-Id: Ie734a09ed4b0d57de30dc6fb377dfada79ea2ae4
Related: SYS#8100
pmaier@sysmocom.de at

#28897 (Jun 30, 2026, 3:24:07 PM)

esipa_rest_utils: add support for PSMOs added in SGP.32 V.1.2

SGP.32 adds 3 additional PSMOs:
- setFallbackAttribute
- unsetFallbackAttribute
- setDefaultDpAddress

Change-Id: I03cdd70065a83dfc611d614cf32d817c13fad347
Related: SYS#8100
pmaier@sysmocom.de at

#28896 (Jun 30, 2026, 3:20:12 PM)

esipa_rest_utils: add support for PSMOs added in SGP.32 V.1.2

SGP.32 adds 3 additional PSMOs:
- setFallbackAttribute
- unsetFallbackAttribute
- setDefaultDpAddress

Change-Id: I03cdd70065a83dfc611d614cf32d817c13fad347
Related: SYS#8100
pmaier@sysmocom.de at

#28895 (Jun 30, 2026, 3:14:26 PM)

rest_api: move "required" member to the correct level

In some locations in the JSON schema files we find the "required"
member on the same level as the members of "properties" (likewise
"items"). This is incorrect, the "required" member should always
be on the same level as the "properties" or "items" member.

(At the moment the JSON schema files serve only documentation
purposes, they are not used to do any actual validation yet.)

Change-Id: I07d51d0e809a718144bd51a6540ab51187bb4daa
Related: SYS#8100
pmaier@sysmocom.de at

#28894 (Jun 30, 2026, 3:12:07 PM)

eim_cfg: set eimSupportedProtocol and indirectProfileDownload flags

The members eimSupportedProtocol and indirectProfileDownload were
added as optional members to EimConfigurationData with SGP.32 V.1.2.

Since our eIM implementation only supports eIM Package Retrieval via
HTTPs and the Indirect Profile Download procedure is the only Profile
Download procedure we currently support, the EimConfigurationData
should reflect those properties correctly.

(The EimConfigurationData is not announced actively by the eIM, but
this eIM implementation contains a generator to help with the encoding
of the EimConfigurationData that is programmed into the eUICC)

Change-Id: I4ce236fb1bfb8a3790191be95ab0958dce13a9d8
Related: SYS#8100
pmaier@sysmocom.de at

#28893 (Jun 30, 2026, 3:10:12 PM)

esipa_rest_utils: re-align to SGP.32 Section 2.11.2

Section 2.11.2: rename EuiccPackageResultDataSigned.configureAutoEnableResult to EuiccPackageResultDataSigned.configureImmediateEnableResult

Change-Id: Ib4e6a4b4cb4d26a391346169b9047515496dd308
Related: SYS#8100
pmaier@sysmocom.de at

#28892 (Jun 30, 2026, 3:03:05 PM)

esipa_rest_utils: re-align to SGP.32 Section 2.11.2

Section 2.11.2: rename EuiccPackageResultDataSigned.configureAutoEnableResult to EuiccPackageResultDataSigned.configureImmediateEnableResult

Change-Id: Ib4e6a4b4cb4d26a391346169b9047515496dd308
Related: SYS#8100
pmaier@sysmocom.de at

#28891 (Jun 30, 2026, 3:03:01 PM)

eim_cfg: set eimSupportedProtocol and indirectProfileDownload flags

The members eimSupportedProtocol and indirectProfileDownload were
added as optional members to EimConfigurationData with SGP.32 V.1.2.

Since our eIM implementation only supports eIM Package Retrieval via
HTTPs and the Indirect Profile Download procedure is the only Profile
Download procedure we currently support, the EimConfigurationData
should reflect those properties correctly.

(The EimConfigurationData is not announced actively by the eIM, but
this eIM implementation contains a generator to help with the encoding
of the EimConfigurationData that is programmed into the eUICC)

Change-Id: I4ce236fb1bfb8a3790191be95ab0958dce13a9d8
Related: SYS#8100
pmaier@sysmocom.de at

#28890 (Jun 30, 2026, 3:00:57 PM)

esipa_asn1_handler: re-align to SGP.32 section 2.11.2 and section 5.14.6

Section 2.11.2: eIM package result (EuiccPackageResult case) is now concatenated with PendingNotificationList instead of RetrieveNotificationsListResponse
Section 5.14.6: ESipa.ProvideEimPackageResult: Significant change in parameters

Change-Id: Ic0872edefc1844166943c60528557c6b7a6602ce
Related: SYS#8100
pmaier@sysmocom.de at

#28889 (Jun 30, 2026, 2:40:16 PM)

esipa_asn1_handler: re-align to SGP.32 section 2.11.2 and section 5.14.6

Section 2.11.2: eIM package result (EuiccPackageResult case) is now concatenated with PendingNotificationList instead of RetrieveNotificationsListResponse
Section 5.14.6: ESipa.ProvideEimPackageResult: Significant change in parameters

Change-Id: Ic0872edefc1844166943c60528557c6b7a6602ce
Related: SYS#8100
pmaier@sysmocom.de at

#28888 (Jun 30, 2026, 2:36:00 PM)

esipa_asn1_handler: fix transactionId handling

The transactionId member is now called eimTransactionId. It is also
an optional member.

Change-Id: I1340e0c7aed091e8e5a5089ebd6e524512408cf7
Related: SYS#8100
pmaier@sysmocom.de at

#28887 (Jun 30, 2026, 2:33:35 PM)

esipa_asn1_codec: add special handling for ProvideEimPackageResultResponse

In SGP.32 V.1.2 ProvideEimPackageResultResponse is defined as a CHOICE.
This means that this struct now also requires special handling.

Change-Id: I859a175cc28a18ea9334d9b2cf233294fdc95b76
Related: SYS#8100
pmaier@sysmocom.de at

#28886 (Jun 30, 2026, 2:30:40 PM)

es9p_client: section 6.3.2.1, rename euiccCiPKIdToBeused to match SGP.32 V.1.2

Section 6.3.2.1: rename InitiateAuthenticationOkEsipa.euiccCiPKIdToBeused to InitiateAuthenticationOkEsipa.euiccCiPKIdentifierToBeUsed

Change-Id: I44c60a2f0d1129093ea67908d2eed167643a4a87
Related: SYS#8100
pmaier@sysmocom.de at

#28885 (Jun 30, 2026, 10:46:08 AM)

eim_cfg: set eimSupportedProtocol and indirectProfileDownload flags

The members eimSupportedProtocol and indirectProfileDownload were
added as optional members to EimConfigurationData with SGP.32 V.1.2.

Since our eIM implementation only supports eIM Package Retrieval via
HTTPs and the Indirect Profile Download procedure is the only Profile
Download procedure we currently support, the EimConfigurationData
should reflect those properties correctly.

(The EimConfigurationData is not announced actively by the eIM, but
this eIM implementation contains a generator to help with the encoding
of the EimConfigurationData that is programmed into the eUICC)

Change-Id: I4ce236fb1bfb8a3790191be95ab0958dce13a9d8
Related: SYS#8100
pmaier@sysmocom.de at

#28884 (Jun 30, 2026, 10:10:39 AM)

es9p_client: section 6.3.2.1, rename euiccCiPKIdToBeused to match SGP.32 V.1.2

Section 6.3.2.1: rename InitiateAuthenticationOkEsipa.euiccCiPKIdToBeused to InitiateAuthenticationOkEsipa.euiccCiPKIdentifierToBeUsed

Change-Id: I44c60a2f0d1129093ea67908d2eed167643a4a87
Related: SYS#8100
pmaier@sysmocom.de at

#28883 (Jun 30, 2026, 10:10:37 AM)

esipa_rest_utils: re-align to SGP.32 Section 2.11.2

Section 2.11.2: rename EuiccPackageResultDataSigned.configureAutoEnableResult to EuiccPackageResultDataSigned.configureImmediateEnableResult

Change-Id: Ib4e6a4b4cb4d26a391346169b9047515496dd308
Related: SYS#8100
pmaier@sysmocom.de at

#28882 (Jun 30, 2026, 10:10:35 AM)

esipa_asn1_handler: fix transactionId handling

The transactionId member is now called eimTransactionId. It is also
an optional member.

Change-Id: I1340e0c7aed091e8e5a5089ebd6e524512408cf7
Related: SYS#8100
pmaier@sysmocom.de at

#28881 (Jun 30, 2026, 10:10:31 AM)

esipa_asn1_codec: add special handling for ProvideEimPackageResultResponse

In SGP.32 V.1.2 ProvideEimPackageResultResponse is defined as a CHOICE.
This means that this struct now also requires special handling.

Change-Id: I859a175cc28a18ea9334d9b2cf233294fdc95b76
Related: SYS#8100
pmaier@sysmocom.de at

#28880 (Jun 30, 2026, 10:10:27 AM)

esipa_asn1_handler: re-align to SGP.32 section Section 2.11.2 and Section 5.14.6

Section 2.11.2: eIM package result (EuiccPackageResult case) is now concatenated with PendingNotificationList instead of RetrieveNotificationsListResponse
Section 5.14.6: ESipa.ProvideEimPackageResult: Significant change in parameters

Change-Id: Ic0872edefc1844166943c60528557c6b7a6602ce
Related: SYS#8100
pmaier@sysmocom.de at

#28879 (Jun 30, 2026, 9:55:17 AM)

asn1/SGP32Definitions: apply workarounds

- Some ASN.1 structs from SGP.22 are re-defined under the same name by SGP.32.
  This leads to name clashes, which most ASN.1 compilers have problems with.
  Prefixing the re-defined struct in SGP.32 with "SGP32-" solves the problem.

- The erlang asn1ct ASN.1 compiler seems to misinterpret the ASN.1 spec when
  a context specific tag is used (redundently) on a child struct definition
  and in the parent definition at the same time. Removing te context specific
  tag on the child struct definition solves the problem.

Change-Id: Id90b005fc3c8c8f737b0c740d4c067f90842a1fe
Related: SYS#8100
pmaier@sysmocom.de at

#28878 (Jun 30, 2026, 9:47:22 AM)

asn1/SGP32Definitions: upgrade ASN.1 spec to V.1.2

This replaces the existing SGP.32 V.1.0.1 ASN.1 spec with the
unmodified, official SGP.32 V.1.2 spec.

Unfortunately V.1.2 is not backward compatible to V.1.0.1. This means
that the eIM application will still compile, but the result will be
non-functional. The incompatibility problems will be addressed in
the follow-up patches of this patchset.

Change-Id: Id4d217296f43846aa39f5dc7076465e2dab72a7c
Related: SYS#8100
pmaier@sysmocom.de at

#28877 (Jun 30, 2026, 9:12:02 AM)

rebar.config: bump meck version: 0.9.2 -> v1.2.0

This fixes a compilation error with recent Erlang/OTP 29:

[  335s] ===> Compiling meck
[  335s] ===> Compiling _checkouts/meck/src/meck_matcher.erl failed
[  335s] meck_matcher.erl:76:6: 'catch ...' is deprecated; please use 'try ... catch ... end' instead.
[  335s] Compile directive 'nowarn_deprecated_catch' can be used to suppress
[  335s] warnings in selected modules.

Change-Id: If3409de1e09ac1b6ce3355d19e47ef0e160a2d3b
Vadim Yanitskiy at

#28876 (Jun 29, 2026, 2:54:13 PM)

common: stop buffering UL measurements when SACCH is deactivated

When the BSC sends RSL DEACT SACCH, the per-SACCH UL measurement drain
stops (it runs on SACCH timing), but the producer in lchan_new_ul_meas()
keeps appending the measurement contributions from every received
TCH/SDCCH burst.  After one SACCH period (104 frames) the 104-slot
uplink measurement buffer fills up, yielding a flood of:

  NOTICE measurement.c:336 no space for uplink measurement, num_ul_meas=104

Add a bool sacch_active flag to gsm_lchan, set to true in the common
l1sap_chan_act() and clear in l1sap_chan_deact_sacch().  Guard
lchan_new_ul_meas() with this flag so that measurements are silently
discarded while SACCH is inactive - there is nothing to drain the
buffer and no SACCH channel on which to report the results to the BSC.

Change-Id: I3943c788cab5d2411b06ac681d4d412852bac0a7
AI-Assisted: yes (Claude)
Vadim Yanitskiy at

#28875 (Jun 29, 2026, 1:56:23 PM)

common: flush paging queue in nm_bts_fsm's NOTINSTALLED on_enter

paging_reset() exists to flush stale paging records from the queue,
but was never called anywhere.  Stale paging records can accumulate
when the OML link goes down: osmo-bts does not exit, so the paging
queue survives into the next BSC session.

Call it alongside bts_cbch_reset() and bts_asci_notification_reset()
in st_op_disabled_notinstalled_on_enter(), which fires after all TRXs
are confirmed closed and before a new OML connection is accepted.

Change-Id: I109ab282986b68b68ba5c11859c44b771c0416fd
AI-Assisted: yes (Claude)
Vadim Yanitskiy at

#28874 (Jun 29, 2026, 1:56:18 PM)

l1sap: fix duplicate RF RESOURCE INDICATION on clock bootstrap

The TTCN-3 test suite (ttcn3-bts-test) expects to receive exactly one
RF RESOURCE INDICATION message from each TRX during the bootstrap stage,
while waiting for all TRX to come up and be configured by the BSC.

l1sap_interf_meas_report() fires whenever bts->gsm_time.fn % period is
0, where period = intave * 104 (typically 624 frames).  Since CLCK.ind
with FN=0 satisfies this condition, a report is sent at the very
beginning of each clock epoch.

This was not a problem before commit fcfc4e83, because the first
CLCK.ind from the transciever was effectively a no-op: with
last_fn_timer.fn zero-initialised, the first indication at FN=0 yielded
elapsed_fn=0 (not > MAX_FN_SKEW), and the catch-up loop (while fn !=
last_fn_timer.fn) would not execute either.  Downlink scheduling only
started on the second CLCK.ind (at FN=102, which is > MAX_FN_SKEW),
and 102 % 624 != 0, so no RF RESOURCE INDICATION was triggered.

fcfc4e83 changed the logic so that Downlink scheduling now begins
immediately on the first CLCK.ind, via an unconditional call to
trx_setup_clock() -> bts_sched_fn(fn).  When fake_trx starts its frame
counter from FN=0, this immediately triggers l1sap_interf_meas_report()
because 0 % 624 == 0.  A second report follows ~2.88s later when the
periodic timer reaches FN=624, making the bootstrap logic
in ttcn3-bts-test unhappy.

Fix by shifting the trigger to (fn + 1) % period == 0, i.e. the report
fires at the last frame of each period rather than the first.  FN=0 now
yields (0+1) % 624 = 1 != 0, suppressing the spurious bootstrap report.
The periodic behaviour and report cadence are otherwise unchanged.

Change-Id: I6550178427b08e67c9763f0f37efff5b88960b1f
Related: fcfc4e83 ("osmo-bts-trx: fix spurious shutdown on first CLCK.ind from osmo-trx")
AI-Assisted: yes (Claude)
Vadim Yanitskiy at

#28873 (Jun 29, 2026, 1:56:14 PM)

common: reset lchan meas state in gsm_ts_release()

lchan->meas (including interf_meas_num and num_ul_meas) is normally
only reset by lchan_meas_reset() called from rsl_tx_chan_act_ack() on
RSL CHANNEL ACTIVATION.  Idle logical channels are never RSL-activated,
so their measurement state is never reset via that path.

On an OML link re-establishment, osmo-bts does not exit: abis.c tears
down the signalling links, the bts_shutdown FSM powers down all TRXs,
and then waits for reconnect.  The gsm_bts/trx/ts/lchan structures
remain in memory, so stale interf_meas_num survives the reconnect.

This is why we're seeing these ERRORs while running ttcn3-bts-test:

(bts=0,trx=2,ts=4,ss=6) Not enough room to store interference report (0dBm)

Add a lchan_meas_reset() call to gsm_ts_release(), which is called
from nm_channel_fsm's NOTINSTALLED on_enter after the TRX is confirmed
closed.  This is exactly the right moment: the radio is fully stopped,
so no new samples arrive.

Change-Id: I18dc9d30417b0c5b2e579660d4a087d93445f956
AI-Assisted: yes (Claude)
Vadim Yanitskiy at

#28872 (Jun 29, 2026, 1:56:10 PM)

common: stop buffering UL measurements when SACCH is deactivated

When the BSC sends RSL DEACT SACCH, the per-SACCH UL measurement drain
stops (it runs on SACCH timing), but the producer in lchan_new_ul_meas()
keeps appending the measurement contributions from every received
TCH/SDCCH burst.  After one SACCH period (104 frames) the 104-slot
uplink measurement buffer fills up, yielding a flood of:

  NOTICE measurement.c:336 no space for uplink measurement, num_ul_meas=104

Add a bool sacch_active flag to gsm_lchan, set to true in the common
l1sap_chan_act() and clear in l1sap_chan_deact_sacch().  Guard
lchan_new_ul_meas() with this flag so that measurements are silently
discarded while SACCH is inactive - there is nothing to drain the
buffer and no SACCH channel on which to report the results to the BSC.

Change-Id: I3943c788cab5d2411b06ac681d4d412852bac0a7
AI-Assisted: yes (Claude)
Vadim Yanitskiy at

#28871 (Jun 29, 2026, 1:54:02 PM)

oml: validate Intave Parameter range in SET BTS ATTR

3GPP TS 52.021 §9.4.24 defines valid range for the Intave Parameter
as 1..31, matching the fixed size of the per-lchan interference sample
buffer (interf_meas_dbm[31] in lchan.h).  Previously any uint8_t value
was accepted without validation, meaning a buggy BSC could send
intave=0 (silently disabling interference reporting) or intave>31
(causing a buffer overflow in gsm_lchan_interf_meas_push()).

Let's guard against that by NACKing the SET BTS ATTR message with
cause=NM_NACK_PARAM_RANGE if the value is outside the valid range.

Change-Id: Id4d3353d4397aaa2517091b020d38ee15e084e2c
AI-Assisted: yes (Claude)
Vadim Yanitskiy at

#28870 (Jun 29, 2026, 1:22:01 PM)

lint: ignore LINUX_VERSION_CODE

When running the linter against dahdi-linux.git or potentially other
repositories with out-of-tree linux kernel modules, it should not
complain about the LINUX_VERSION_CODE being used there:

> drivers/dahdi/dahdi-base.c:6397: WARNING:LINUX_VERSION_CODE:
> LINUX_VERSION_CODE should be avoided, code should be for the version to
> which it is merged

Change-Id: I82d64d43c04561b1643785cb71cfee92e513e560
Oliver Smith at

#28869 (Jun 29, 2026, 9:59:31 AM)

contrib/jenkins: run 'rebar3 fmt --check'

The pull request "v0.0.2" had a patch that formatted everything with
erlfmt. Let's run it in CI to keep the style consistent.

Related: https://github.com/onomondo/onomondo-eim/pull/10/commits/8bafdb3839d868d6bc18499617761d9acd73d2ad
Change-Id: I271c90dace6e7b6f052b38054815e6dfcbfa60f5
Oliver Smith at

#28868 (Jun 29, 2026, 9:59:29 AM)

src/utils.erl: format with erlfmt

Keep the file consistent with the rest of the codebase by running
'rebar3 fmt -w' on it.

Change-Id: I806c912a1bc82c26ecd23759a927f22328e743b9
Oliver Smith at

#28867 (Jun 29, 2026, 9:55:41 AM)

contrib/jenkins: run 'rebar3 fmt --check'

The pull request "v0.0.2" had a patch that formatted everything with
erlfmt. Let's run it in CI to keep the style consistent.

Related: https://github.com/onomondo/onomondo-eim/pull/10/commits/8bafdb3839d868d6bc18499617761d9acd73d2ad
Change-Id: I271c90dace6e7b6f052b38054815e6dfcbfa60f5
Oliver Smith at

#28866 (Jun 29, 2026, 9:53:16 AM)

contrib/jenkins: run 'rebar3 fmt --check'

The pull request "v0.0.2" had a patch that formatted everything with
erlfmt. Let's run it in CI to keep the style consistent.

Related: https://github.com/onomondo/onomondo-eim/pull/10/commits/8bafdb3839d868d6bc18499617761d9acd73d2ad
Change-Id: I271c90dace6e7b6f052b38054815e6dfcbfa60f5
Oliver Smith at

#28865 (Jun 29, 2026, 9:38:57 AM)

src/grd: use sys.exit

The exit function is a constant from the site module, which "should not
be used in programs". Replace it with sys.exit()

Related: https://docs.python.org/3/library/constants.html#constants-added-by-the-site-module
Change-Id: I95db013e36242d5126ce07b8a392e6dc0a0ecfdd
Oliver Smith at

#28864 (Jun 29, 2026, 9:38:54 AM)

src/grd: apply ruff formatter

The src/grd script is not part of the default "include" pattern as the
script does not end in ".py" (it used to be a shell script earlier). Add
it to the config explicitly and run "ruff format".

Change-Id: Id8da8e6b3325c8301276fd164ba218e8c5a95951
Oliver Smith at

#28863 (Jun 29, 2026, 9:38:50 AM)

src/grd: use origin url to get get host + project

For most projects we can get the gerrit host and project from the git
remote URL already. Do this when a git repository has no ".gitreview"
file so it works even if the file is not present.

Change-Id: Ib2b201e5238ba7036c6121e8875ee85c73da8751
Oliver Smith at

#28862 (Jun 29, 2026, 8:53:25 AM)

jobs/{master,gerrit}: eim,ipa: wipe-workspace

Set wipe-workspace for the onomondo-eim and onomondo-ipa jobs to true,
so previous failures cannot influence new jenkins job runs. E.g.
currently we have gerrit-onomondo-ipa-build failing with:

  + mkdir build
  mkdir: cannot create directory 'build': File exists

Most existing jobs call scripts/osmo-clean-workspace.sh from osmo-ci.git
at the beginning of their jenkins.sh instead of using wipe-workspace.
But this doesn't have any advantage here while making jenkins.sh more
complex. Let's use the built-in feature from jenkins here.

Change-Id: If4ef5ab804b05ad630cfa770741fe6053fdfb637
Oliver Smith at

#28861 (Jun 29, 2026, 8:37:55 AM)

scard: add comment about memory-leak in libpcsclite

As it seems, SCardReleaseContext does not free all of the memory
allocated by SCardEstablishContext. The probem has no real-world
impact, but still showas up in valgrind. Let's add a comment so
that we do not forget what causes the leak.

Related: SYS#8101
Change-Id: I5224f3824ce2ad33e678cd859ad28c47788dbb24
pmaier@sysmocom.de at

#28860 (Jun 29, 2026, 8:36:56 AM)

es10b_get_euicc_info: add explanatory comments regarding EUICCInfo2

onomondo-ipa has a built-in IoT eUICC emulation. This means that we
have to deal with two different EUICCInfo2 formats, which requires
additional logic in ipa_es10b_get_euicc_info_free to free the
allocated structs correctly. Since it is not immediately obvious
how the logic works, let's add some explanary comments to make it
obvious.

Related: SYS#8101
Change-Id: I282fa91a4099a771a353101b0ce17ae3daae9c42
pmaier@sysmocom.de at

#28859 (Jun 26, 2026, 3:42:58 PM)

Revert "bts: limit stderr logging to ERROR to avoid long write() to ext4 fs"

This reverts commit 3c798765f04dd7428c76e3c5cbf3f2ee27a0af4d.

Reducing logging verbosity did not help: we're still seeing the clock
skew errors and restarts.  This makes debugging harder, and is not
relevant anymore because we've switched to tmpfs [1].

Related: [1] docker-playground.git Id9a93f7149ef7e9bfde1f4fe3a8299ba46645d50
Change-Id: Id234394fda1ce752f93448e2fc03887a097f6b9d
Vadim Yanitskiy at

#28858 (Jun 26, 2026, 3:42:51 PM)

Revert "bts: limit stderr logging to NOTICE to avoid long write() to ext4 fs"

This reverts commit c3ab9ec33f37c6837fb8bcb0fa0bbd2e98781fb7.

Reducing logging verbosity did not help: we're still seeing the clock
skew errors and restarts.  This makes debugging harder, and is not
relevant anymore because we've switched to tmpfs [1].

Related: [1] docker-playground.git Id9a93f7149ef7e9bfde1f4fe3a8299ba46645d50
Change-Id: Ief6c3a6ca3053ccf745a186f7bb440e8540336f4
Vadim Yanitskiy at

#28857 (Jun 25, 2026, 10:07:32 PM)

saip/personalization: add MncLen configurable parameter

Add a new ConfigurableParameter that represents the MNC length
(2 or 3 digits) in EF.AD (Administrative Data).

Change-Id: I6c600faeab00ffb072acbe94c9a8b2d1397c07d3
Co-authored-by: Vadim Yanitskiy <vyanitskiy@sysmocom.de>
Jenkins: skip-card-test
Vadim Yanitskiy at

#28856 (Jun 25, 2026, 9:58:07 PM)

saip/personalization: add MncLen configurable parameter

Add a new ConfigurableParameter that represents the MNC length
(2 or 3 digits) in EF.AD (Administrative Data).

Change-Id: I6c600faeab00ffb072acbe94c9a8b2d1397c07d3
Co-authored-by: Vadim Yanitskiy <vyanitskiy@sysmocom.de>
Jenkins: skip-card-test
Vadim Yanitskiy at

#28855 (Jun 25, 2026, 7:48:26 PM)

pySim.log, pySim-shell: fix compatibility with cmd2 >= 3.0.0

Some Linux distributions (e.g. Arch Linux) already ship cmd2 3.x.x,
which removed the style()/Fg/Bg API in favor of stylize()/Color.

Add a version guard to select the right API at runtime.
Adjust the upper bound cap in requirements.txt and setup.py.

Change-Id: Ibf2ac7847933296fb06665c87f53ed6e1f315d27
Vadim Yanitskiy at

#28854 (Jun 25, 2026, 5:52:30 PM)

pySim-shell: drop backwards compat quirks for cmd2 < 2.6.2

Remove version guards for cmd2 < 2.0.0 and < 2.3.0, the Cmd2Compat
and Settable2Compat wrapper classes, and the old fg/bg color API -
none of these are needed since both requirements.txt and setup.py
already mandate cmd2 >= 2.6.2.

Change-Id: Ifd1c484ab66d74323d10e946347daa637cf6f5d8
Vadim Yanitskiy at

#28853 (Jun 25, 2026, 5:52:27 PM)

pySim.log, pySim-shell: fix compatibility with cmd2 >= 3.0.0

Some Linux distributions (e.g. Arch Linux) already ship cmd2 3.x.x,
which removed the style()/Fg/Bg API in favor of stylize()/Color.

Add a version guard to select the right API at runtime.
Adjust the upper bound cap in requirements.txt and setup.py.

Change-Id: Ibf2ac7847933296fb06665c87f53ed6e1f315d27
Vadim Yanitskiy at

#28852 (Jun 25, 2026, 5:52:24 PM)

setup.py: Align cmd2 minimum version with requirements.txt

As pointed out in the commit-log of Change-Id
I5186f242dbc1b770e3ab8cdca7f27d2a1029fff6 we had different minimum
versions for cmd2 in requirements.txt vs setup.py.  Let's align that.

Change-Id: I71cee0ec3ed2abec68ec567beaab13c868721dad
Vadim Yanitskiy at

#28851 (Jun 24, 2026, 9:28:32 AM)

esipa_asn1_handler: fix transactionId handling

The transactionId member is now called eimTransactionId. It is also
an optional member.

Change-Id: I1340e0c7aed091e8e5a5089ebd6e524512408cf7
Related: SYS#8100
pmaier@sysmocom.de at

#28850 (Jun 24, 2026, 9:28:30 AM)

rest_api_response_schema: add missing error codes

In SGP.32 V.1.2, new error codes were added to EnableProfileResult,
DisableProfileResult, DeleteProfileResult and AddEimResult

See also: SGP.32, section 2.11.2

Change-Id: I525ca9d3b7fb870405d374160272d8ec26c85880
Related: SYS#8100
pmaier@sysmocom.de at

#28849 (Jun 24, 2026, 9:28:27 AM)

esipa_asn1_handler: re-align to SGP.32 section Section 2.11.2 and Section 5.14.6

Section 2.11.2: eIM package result (EuiccPackageResult case) is now concatenated with PendingNotificationList instead of RetrieveNotificationsListResponse
Section 5.14.6: ESipa.ProvideEimPackageResult: Significant change in parameters

Change-Id: Ic0872edefc1844166943c60528557c6b7a6602ce
Related: SYS#8100
pmaier@sysmocom.de at

#28848 (Jun 24, 2026, 9:28:25 AM)

eim_cfg: set eimSupportedProtocol and indirectProfileDownload flags

The members eimSupportedProtocol and indirectProfileDownload were
added as optional members to EimConfigurationData with SGP.32 V.1.2.

Since our eIM implementation only supports eIM Package Retrieval via
HTTPs and the Indirect Profile Download procedure is the only Profile
Download procedure we currently support, the EimConfigurationData
should reflect those properties correctly.

(The EimConfigurationData is not announced actively by the eIM, but
this eIM implementation contains a generator to help with the encoding
of the EimConfigurationData that is programmed into the eUICC)

Change-Id: I4ce236fb1bfb8a3790191be95ab0958dce13a9d8
Related: SYS#8100
pmaier@sysmocom.de at

#28847 (Jun 24, 2026, 9:28:22 AM)

esipa_rest_utils: align IpaEuiccDataResponse to SGP.32 V.1.2

The ASN.1 struct IpaEuiccDataResponse has renamed the error code
member from ipaEuiccDataError to ipaEuiccDataErrorCode. The new
ipaEuiccDataErrorCode is a sequence that has an ipaEuiccDataErrorCode
member, which is the equivalent of the previously existing
ipaEuiccDataError member.

See also: SGP.32, section 2.11.2.2

Change-Id: Ie734a09ed4b0d57de30dc6fb377dfada79ea2ae4
Related: SYS#8100
pmaier@sysmocom.de at

#28846 (Jun 24, 2026, 9:28:19 AM)

esipa_rest_utils: re-align to SGP.32 Section 2.11.2

Section 2.11.2: rename EuiccPackageResultDataSigned.configureAutoEnableResult to EuiccPackageResultDataSigned.configureImmediateEnableResult

Change-Id: Ib4e6a4b4cb4d26a391346169b9047515496dd308
Related: SYS#8100
pmaier@sysmocom.de at

#28845 (Jun 24, 2026, 9:28:16 AM)

rest_api: move "required" member to the correct level

In some locations in the JSON schema files we find the "required"
member on the same lavel as the "properties" (likewise "items")
members. This is incorrect, the "required" member should always be
on the same level as the "properties" member

(At the moment the JSON schema files serve only documentation purposes,
they are not used to do any actual validation yet.)

Change-Id: I07d51d0e809a718144bd51a6540ab51187bb4daa
Related: SYS#8100
pmaier@sysmocom.de at

#28844 (Jun 24, 2026, 9:28:12 AM)

rest_api: revert json schema re-formatting

The JSON schema got reformatted in patch 78810e9d0e2c4fcfa0bff2e16aedd225c7145055,
however, the reformatted version now follows a scheme that is incompatible with
the emacs default settings. This makes it very hard to work with those files, so
let's revert this change.

Change-Id: I2361891875a8e190fff7003196c2df76fd877080
Related: SYS#8100
pmaier@sysmocom.de at

#28843 (Jun 24, 2026, 9:28:10 AM)

es9p_client: section 6.3.2.1, rename euiccCiPKIdToBeused to match SGP.32 V.1.2

Section 6.3.2.1: rename InitiateAuthenticationOkEsipa.euiccCiPKIdToBeused to InitiateAuthenticationOkEsipa.euiccCiPKIdentifierToBeUsed

Change-Id: I44c60a2f0d1129093ea67908d2eed167643a4a87
Related: SYS#8100
pmaier@sysmocom.de at

#28842 (Jun 24, 2026, 9:27:37 AM)

esipa_rest_utils: add support for PSMOs added in SGP.32 V.1.2

SGP.32 adds 3 additional PSMOs:
- setFallbackAttribute
- unsetFallbackAttribute
- setDefaultDpAddress

Change-Id: I03cdd70065a83dfc611d614cf32d817c13fad347
Related: SYS#8100
pmaier@sysmocom.de at

#28841 (Jun 24, 2026, 9:27:32 AM)

esipa_asn1_codec: add special handling for ProvideEimPackageResultResponse

In SGP.32 V.1.2 ProvideEimPackageResultResponse is defined as a CHOICE.
This means that this struct now also requires special handling.

Change-Id: I859a175cc28a18ea9334d9b2cf233294fdc95b76
Related: SYS#8100
pmaier@sysmocom.de at

#28840 (Jun 24, 2026, 8:29:19 AM)

es10b_get_euicc_info: add explanatory comments regarding EUICCInfo2

onomondo-ipa has a built-in IoT eUICC emulation. This means that we
have to deal with two different EUICCInfo2 formats, which requires
additional logic in ipa_es10b_get_euicc_info_free to free the
allocated structs correctly. Since it is not immediately obvious
how the logic works, let's add some explanary comments to make it
obvious.

Related: SYS#8101
Change-Id: I282fa91a4099a771a353101b0ce17ae3daae9c42
pmaier@sysmocom.de at

#28839 (Jun 24, 2026, 8:26:23 AM)

es10b_get_euicc_info: add explanatory comments regarding EUICCInfo2

onomondo-ipa has a built-in IoT eUICC emulation. This means that we
have to deal with two different EUICCInfo2 formats, which requires
additional logic in ipa_es10b_get_euicc_info_free to free the
allocated structs correctly. Since it is not immediately obvious
how the logic works, let's add some explanary comments to make it
obvious.

Related: SYS#8101
Change-Id: I282fa91a4099a771a353101b0ce17ae3daae9c42
pmaier@sysmocom.de at

#28838 (Jun 24, 2026, 8:26:19 AM)

scard: add comment about memory-leak in libpcsclite

As it seems, SCardReleaseContext does not free all of the memory
allocated by SCardEstablishContext. The probem has no real-world
impact, but still showas up in valgrind. Let's add a comment so
that we do not forget what causes the leak.

Related: SYS#8101
Change-Id: I5224f3824ce2ad33e678cd859ad28c47788dbb24
pmaier@sysmocom.de at

#28837 (Jun 24, 2026, 8:24:18 AM)

scard: add comment about memory-leak in libpcsclite

As it seems, SCardReleaseContext does not free all of the memory
allocated by SCardEstablishContext. The probem has no real-world
impact, but still showas up in valgrind. Let's add a comment so
that we do not forget what causes the leak.

Related: SYS#8101
Change-Id: I5224f3824ce2ad33e678cd859ad28c47788dbb24
pmaier@sysmocom.de at

#28836 (Jun 24, 2026, 8:23:46 AM)

es10b_get_euicc_info: add explanatory comments regarding EUICCInfo2

onomondo-ipa has a built-in IoT eUICC emulation. This means that we
have to deal with two different EUICCInfo2 formats, which requires
additional logic in ipa_es10b_get_euicc_info_free to free the
allocated structs correctly. Since it is not immediately obvious
how the logic works, let's add some explanary comments to make it
obvious.

Related: SYS#8101
Change-Id: I282fa91a4099a771a353101b0ce17ae3daae9c42
pmaier@sysmocom.de at

#28835 (Jun 24, 2026, 8:23:43 AM)

scard: add comment about memory-leak in libpcsclite

As it seems, SCardReleaseContext does not free all of the memory
allocated by SCardEstablishContext. The probem has no real-world
impact, but still showas up in valgrind. Let's add a comment so
that we do not forget what causes the leak.

Related: SYS#8101
Change-Id: I5224f3824ce2ad33e678cd859ad28c47788dbb24
pmaier@sysmocom.de at

#28834 (Jun 24, 2026, 8:22:11 AM)

es10b_get_euicc_info: add explanatory comments regarding EUICCInfo2

onomondo-ipa has a built-in IoT eUICC emulation. This means that we
have to deal with two different EUICCInfo2 formats, which requires
additional logic in ipa_es10b_get_euicc_info_free to free the
allocated structs correctly. Since it is not immediately obvious
how the logic works, let's add some explanary comments to make it
obvious.

Related: SYS#8101
Change-Id: I282fa91a4099a771a353101b0ce17ae3daae9c42
pmaier@sysmocom.de at

#28833 (Jun 24, 2026, 8:22:08 AM)

scard: add comment about memory-leak in libpcsclite

As it seems, SCardReleaseContext does not free all of the memory
allocated by SCardEstablishContext. The probem has no real-world
impact, but still showas up in valgrind. Let's add a comment so
that we do not forget what causes the leak.

Related: SYS#8101
Change-Id: I5224f3824ce2ad33e678cd859ad28c47788dbb24
pmaier@sysmocom.de at

#28832 (Jun 23, 2026, 10:46:23 PM)

stp: for TCAP loadshare: use NI == national

Use a non-zero NI. The TCAP tests don't check it
on the receive path, but the osmo-stp is checking
it if it matches the configuration.

Related: SYS#8061
Change-Id: I51ef302ad72ff3c434fddb39006ce50106a5918f
lynxis at

#28831 (Jun 23, 2026, 7:44:16 PM)

osmo-bts-trx: fix spurious clock skew shutdown after self-compensation

When the BTS runs ahead of the transceiver (elapsed_fn < 0),
trx_sched_clock() reschedules the timerfd to deliberately delay the
next FN.  osmo_timerfd_schedule() resets the timerfd and discards any
accumulated expirations, but last_fn_timer.tv was left pointing at
the previous callback.  The next trx_fn_timer_cb() then measures
elapsed_us all the way back to that previous callback - spanning the
deliberate delay (or any OS stall that preceded us) - and falsely
trips the "PC clock skew too high" check, shutting the BTS down
for no good reason.

Advance last_fn_timer.tv to the projected firing time of the
rescheduled timer so that the next callback measures roughly
one FN interval, as expected.

Change-Id: Icdb7db8abe70258ae008d9514b6608bd74bb2881
AI-Assisted: yes (Claude)
Related: OS#6794
Vadim Yanitskiy at

#28830 (Jun 23, 2026, 7:41:57 PM)

osmo-bts-trx: fix spurious shutdown on first CLCK.ind from osmo-trx

osmo-trx starts its frame counter from a random value rather than 0.
When the first CLCK.ind arrives, last_fn_timer and last_clk_ind are
still zero-initialised (set by trx_sched_clock_started()), so:

* compute_elapsed_fn(0, fn) wraps to a large negative for any fn
  greater than hyperframe/2 (1357824), satisfying elapsed_fn < 0;
* compute_elapsed_us({0,0}, &tv_now) returns the full CLOCK_MONOTONIC
  uptime (potentially days), satisfying the error_us threshold.

Together these trip the stale-clock shutdown introduced in the previous
commit (0199c108), even though the transceiver is perfectly healthy:

DL1C NOTICE scheduler_trx.c:490 GSM clock started, waiting for clock indications
DL1C FATAL scheduler_trx.c:589 Stale CLCK.ind: fn=1456348 is 250957770198 us behind
DOML NOTICE bts_shutdown_fsm.c:268 BTS_SHUTDOWN(bts0){NONE}: Shutting down BTS, exit 1, reason: TRX clock skew too high

Fix by adding clk_ind_received to osmo_trx_clock_state.  On the first
CLCK.ind after a (re)start, skip all elapsed-time checks and directly
bootstrap the scheduler from the reported FN.  The stale-clock
detection remains fully active for every subsequent indication,
where last_clk_ind holds a real baseline.

Change-Id: I25e76e02d29fd8f88130d15d0adfe8d90a017924
Fixes: 0199c108 ("osmo-bts-trx: shut down on stale clock indication from transceiver")
Related: OS#7021
Vadim Yanitskiy at

#28829 (Jun 23, 2026, 3:01:42 PM)

stp: tcap-loadshare: add TC_tcap_loadshare_m3ua_to_ipa_udts

If a TCAP message arrives which is:
* not a TCAP Begin or Abort (e.g. a TCAP Continue)
* not in the TCAP session cache/tracking
* not have a dTID for a registered TCAP Add Range

The tcap load-share will reject this message with a UDTS

Related: SYS#8061
Change-Id: I181b25aedfd70d156c08197d361560b6d055e65a
lynxis at

#28828 (Jun 23, 2026, 11:25:41 AM)

asn1/SGP32Definitions: apply workarounds

- Some ASN.1 structs from SGP.22 are re-defined under the same name by SGP.32.
  This leads to name clashes, which most ASN.1 compilers have problems with.
  Prefixing the re-defined struct in SGP.32 with "SGP32-" solves the problem.

- The erlang asn1ct ASN.1 compiler seems to misinterpret the ASN.1 spec when
  a context specific tag is used (redundently) on a child struct definition
  and in the parent definition at the same time. Removing te context specific
  tag on the child struct definition solves the problem.

Change-Id: Id90b005fc3c8c8f737b0c740d4c067f90842a1fe
Related: SYS#8100
pmaier@sysmocom.de at

#28827 (Jun 23, 2026, 11:25:37 AM)

asn1/SGP32Definitions: upgrade ASN.1 spec to V.1.2

This replaces the existing SGP.32 V.1.0.1 ASN.1 spec with the
unmodified, official SGP.32 V.1.2 spec.

Unfortunately V.1.2 is not backward compatible to V.1.0.1. This means
that the eIM application will still compile, but the result will be
non-functional. The incompatibility problems will be addressed in
the follow-up patches of this patchset.

Change-Id: Id4d217296f43846aa39f5dc7076465e2dab72a7c
Related: SYS#8100
pmaier@sysmocom.de at

#28826 (Jun 23, 2026, 11:14:32 AM)

contrib/jenkins: run 'rebar3 fmt --check'

The pull request "v0.0.2" had a patch that formatted everything with
erlfmt. Let's run it in CI to keep the style consistent.

Related: https://github.com/onomondo/onomondo-eim/pull/10/commits/8bafdb3839d868d6bc18499617761d9acd73d2ad
Change-Id: I271c90dace6e7b6f052b38054815e6dfcbfa60f5
Oliver Smith at

#28825 (Jun 23, 2026, 10:44:36 AM)

certificates: fix certificate location, make sure cert/key files are readable

The certificate and key files are placed in the config directory. This is
an unfortunate location, since it causes a lot of trouble when referencing
those files.

The erlang documentation suggests to place so called auxillary files in a
"priv" directory on the same level as the config directory. The path to
the priv directory can then be located using code:priv_dir.

see also: https://www.erlang.org/docs/26/design_principles/applications.html

Let's adopt this mechanism by adding utility functions that allow us to
resolve the file paths to files inside the priv directory. Let's also
automatically check if the referenced file is readable, so that we get
a proper error in the log in case a certificate or key file is missing

Change-Id: Ie09d746a6e28ac6fee3e00dfa32cb01f8a7b947e
Related: SYS#7093
pmaier@sysmocom.de at

#28824 (Jun 23, 2026, 10:38:56 AM)

esipa_rest_utils: fix searchCritera.profileClass type conversion

We currently use utils:hex_to_integer to convert the ProfileClass,
which is supposedly a string, to integer. However, hex_to_inteteger
does not exist and when looking into the related JSON schema
definition of we see that the profileClass member is already defined
as integer. This means that ProfileClass already arrives as integer
and can be used as it is. removing the hex_to_integer call solves
the problem.

Change-Id: I4bd223dbef00be9c800539b8d0dc9a84e3e93b73
pmaier@sysmocom.de at

#28823 (Jun 23, 2026, 9:09:33 AM)

jobs/master-builds: add onomondo-{eim,ipa}

Related: SYS#8103
Change-Id: I07f0cff5ce31e60135dff84554f21d8b404f7c72
Oliver Smith at

#28822 (Jun 23, 2026, 8:19:47 AM)

tls: fix broken certificate hostname verification

verify_cert_cb() retrieved the gnutls session pointer and passed it to
gnutls_certificate_verify_peers3() as the expected hostname.  But the
session pointer is set to the osmo_tls_session struct (it is needed by
cert_callback()), not a hostname string.  Hostname matching was
therefore performed against raw struct bytes, rendering verification
meaningless and potentially reading out of bounds, even when
"tls verify-cert" was enabled.

Store the configured hostname in struct osmo_tls_session and have
verify_cert_cb() read it from there.  Also drop the stray
gnutls_certificate_verify_peers3() call in the client setup: it ran
before any handshake (so there were no peer certificates yet) and its
result was ignored; the real verification happens via the registered
callback during the handshake.

Change-Id: If64950a698bfcfbf556a37ef1be3e68abc124384
AI-Assisted: yes (Claude)
Vadim Yanitskiy at

#28821 (Jun 23, 2026, 8:19:45 AM)

server: fix NULL deref of file_hdr_msg when store is disabled

When a connection has storing disabled (no store), conn->file_hdr_msg
is never populated.  The previous link-header handling skipped the
first branch (gated on conn->store) and fell through to the comparison
branch, which dereferenced the still-NULL conn->file_hdr_msg, crashing
the server on the first PKT_LINK_HDR from such a client.

Gate the whole header tracking on conn->store and simply free the
message when not storing, since osmo_pcap_conn_restart_trace() already
no-ops in that case.

Change-Id: I419e1b66d07307c3e49294984887c153cd8494c3
AI-Assisted: yes (Claude)
Vadim Yanitskiy at

#28820 (Jun 23, 2026, 8:18:42 AM)

server: vty: validate rotate-localtime modulus against the new interval

apply_rotate_localtime() computed the maximum allowed modulus from
pcap_server->rotate_localtime.intv, the currently-stored (old) interval,
rather than the intv argument being applied.  On first configuration the
stored interval is the default 0, so the switch hit the default case and
rejected an otherwise valid command; when changing intervals the modulus
was bounds-checked against the wrong interval.  Switch on intv instead.

Change-Id: I0b367d4e255db3208b41e12adec682026b99cc18
AI-Assisted: yes (Claude)
Vadim Yanitskiy at

#28819 (Jun 23, 2026, 8:18:22 AM)

tls: do not treat GNUTLS_E_AGAIN/INTERRUPTED as fatal on read

osmo_tls_client_bfd_cb() treated any non-positive return from
gnutls_record_recv() as a fatal error and tore down the session.  On a
non-blocking socket gnutls_record_recv() can return GNUTLS_E_AGAIN or
GNUTLS_E_INTERRUPTED (both negative but non-fatal), which would drop
an otherwise healthy TLS session.  Handle them as retryable, mirroring
the existing logic in tls_write().

Change-Id: If2f842b202dd08c07dffe3770c51cf0ce886beee
AI-Assisted: yes (Claude)
Vadim Yanitskiy at

#28818 (Jun 23, 2026, 8:18:12 AM)

client: honor IPv4 header length in GPRS filter

The GPRS-NS/BSSGP filter assumed a fixed 20-byte IPv4 header (IP_LEN)
when locating the UDP header and payload.  When the captured packet
carries IPv4 options (ip_hl > 5), udp_data/payload_data pointed into
the middle of the headers and check_gprs() parsed garbage, classifying
packets incorrectly.

Use the actual header length from ip_hl, reject malformed headers
(ip_hl < 5), and re-validate that the larger headers fit within the
captured length before computing the payload.

Change-Id: Iac1fa9cc2a3c06cbe19c3e7799a0b335f2e3dda9
AI-Assisted: yes (Claude)
Vadim Yanitskiy at

#28817 (Jun 23, 2026, 7:00:35 AM)

utils: fix typos

Change-Id: Ib8ede7cbfed9198f59fe2899fe4b68eac5ac9a23
Oliver Smith at

#28816 (Jun 23, 2026, 7:00:05 AM)

utils/gsmtap-logsend: close infile before exit

Related: SYS#8093
Change-Id: I259cf951c52f7d859475f5f79c803692c29fbec3
Oliver Smith at

#28815 (Jun 22, 2026, 12:57:43 PM)

add comment about not updating existing key_usage_qualifier

Change-Id: Ie23ae5fde17be6b37746784bf1601b4d0874397a
Jenkins: skip-card-test
Vadim Yanitskiy at

#28814 (Jun 22, 2026, 12:57:41 PM)

saip: add numeric_base indicator to ConfigurableParameter

By default, numeric_base = None, to indicate that there are no explicit
limitations on the number space.

For parameters that are definitely decimal, set numeric_base = 10.
For definitely hexadecimal, set numeric_base = 16.

Do the same for ConfigurableParameter as well as ParamSource, so callers
can match them up: if a parameter is numeric_base = 10, then omit
sources that are numeric_base = 16, and vice versa.

Change-Id: Ib0977bbdd9a85167be7eb46dd331fedd529dae01
Jenkins: skip-card-test
Vadim Yanitskiy at

#28813 (Jun 22, 2026, 12:57:39 PM)

test_configurable_parameters.py: add tests for new parameters

For:
SmspTpScAddr
MilenageRotation
MilenageXoringConstants
TuakNrOfKeccak

Change-Id: Iecbea14fe31a9ee08d871dcde7f295d26d7bd001
Jenkins: skip-card-test
Vadim Yanitskiy at

#28812 (Jun 22, 2026, 12:57:36 PM)

saip SmspTpScAddr.get_values_from_pes: allow empty values

Change-Id: Ibbdd08f96160579238b50699091826883f2e9f5a
Jenkins: skip-card-test
Vadim Yanitskiy at

#28811 (Jun 22, 2026, 12:57:32 PM)

SmspTpScAddr: fix SMSP record length and alpha_id padding

apply_val() was re-encoding the SMSP with the minimum total_len of 28,
which produces a 28-byte body with no alpha_id field.  After a DER
round-trip, the profile machinery re-pads the body to the original
record length using the template's fill pattern, which may not be 0xFF.
Those non-0xFF fill bytes end up in the alpha_id area, and GSM 7-bit
decoding then fails with a KeyError when the modified profile is read
back.

Fix by:
- setting alpha_id = '' so the field is present but empty
- setting f_smsp.rec_len = 42 (28 fixed bytes + 14 bytes of alpha_id
  padding) so the re-encoded body carries 0xFF-padded alpha_id space
  and the efFileSize in the fileDescriptor stays consistent
- passing total_len=f_smsp.rec_len to encode_record_bin() so the
  alpha_id area is actually padded to that length

Change-Id: Ief6e02517f3e96158a2509d763b88aec4bd5a296
Jenkins: skip-card-test
Vadim Yanitskiy at

#28810 (Jun 22, 2026, 12:57:29 PM)

MncLen

Change-Id: I6c600faeab00ffb072acbe94c9a8b2d1397c07d3
Jenkins: skip-card-test
Vadim Yanitskiy at

#28809 (Jun 22, 2026, 12:03:42 PM)

gitignore: add build dir

Change-Id: Iea8f79b4094ed79f64b0ed6d6e34212ebaea0c43
Oliver Smith at

#28808 (Jun 22, 2026, 12:03:39 PM)

contrib/jenkins: build with -Werror

Now that all warnings are fixed, let's build with Werror in CI.

Change-Id: I8a8a7bc8a10e8d86a09fbd289b00641c19c3be6e
Oliver Smith at

#28807 (Jun 22, 2026, 12:03:35 PM)

activation_code: fix missing const for item_end

Fix for:
  …/src/ipa/libipa/activation_code.c: In function ‘ipa_activation_code_parse’:
  …/src/ipa/libipa/activation_code.c:62:26: error: assignment discards ‘const’ qualifier from pointer target type [-Werror=discarded-qualifiers]
     62 |                 item_end = strchr(item + 1, '$');
        |                          ^

Change-Id: Idcdd06f57da0e7c05ea184c56cadfc6de85514e6
Oliver Smith at

#28806 (Jun 22, 2026, 12:03:32 PM)

esipa: fix printf fmt str for ssize_t

Fix for:
  In file included from …/src/ipa/libipa/esipa.c:14:
  …/src/ipa/libipa/esipa.c: In function ‘ipa_esipa_msg_to_eim_enc’:
  …/src/ipa/libipa/esipa.h:16:33: error: format ‘%d’ expects argument of type ‘int’, but argument 7 has type ‘ssize_t’ {aka ‘long int’} [-Werror=form
  at=]
     16 |         IPA_LOGP(SESIPA, level, "%s: " fmt, func, ## args)
        |                                 ^~~~~~
  …/include/onomondo/ipa/log.h:18:53: note: in definition of macro ‘IPA_LOGP’
     18 |         ipa_logp(subsys, level, __FILE__, __LINE__, fmt, ## args)
        |                                                     ^~~
  …/src/ipa/libipa/esipa.c:129:17: note: in expansion of macro ‘IPA_LOGP_ESIPA’
    129 |                 IPA_LOGP_ESIPA(function_name, LERROR, "cannot encode eIM request! rc = %d\n", rc.encoded);
        |                 ^~~~~~~~~~~~~~

Change-Id: I5b210ae5acff362cf845f6a37073d2bffe69c76e
Oliver Smith at

#28805 (Jun 22, 2026, 12:03:28 PM)

utils: ignore Waddress in IPA_STR_FROM_ASN

When building with -Werror, GCC complains about this assert in the macro:

  #define IPA_STR_FROM_ASN(asn1_obj) ({ \
  char *__str; \
  assert(asn1_obj); \    <----------------------
  __str = IPA_ALLOC_N((asn1_obj)->size + 1); \
  assert(__str); \
  memcpy(__str, (asn1_obj)->buf, (asn1_obj)->size); \
  __str[(asn1_obj)->size] = '\0'; \
  __str; \
  })

For example:

  …/src/ipa/libipa/es10b_get_eim_cfg_data.c:48:21: error: the comparison will always evaluate as ‘true’ for the address of ‘eimId’ will never be NULL [-Werror=address]
     48 |                     IPA_STR_FROM_ASN(&res->res->eimConfigurationDataList.list.array[i]->eimId);

Add pragmas to ignore the error, so it can still assert if somebody
should pass NULL to the macro.

Change-Id: Ia2ef30880dd3e5b2ab90eedd0046a95a22614a81
Oliver Smith at

#28804 (Jun 22, 2026, 12:03:25 PM)

contrib/jenkins: new script

Add a script for build verifications on https://jenkins.osmocom.org.

Related: SYS#8103
Change-Id: I0305c3196896667f4963853099d0767e0acbdb30
Oliver Smith at

#28803 (Jun 22, 2026, 10:53:25 AM)

jobs/gerrit-verifications: add onomondo-{eim,ipa}

Related: SYS#8103
Change-Id: Ib07ed316d80cbb857c34aede03e3d4468c3be578
Oliver Smith at

#28802 (Jun 22, 2026, 10:50:58 AM)

esipa: fix printf fmt str for ssize_t

Fix for:
  In file included from …/src/ipa/libipa/esipa.c:14:
  …/src/ipa/libipa/esipa.c: In function ‘ipa_esipa_msg_to_eim_enc’:
  …/src/ipa/libipa/esipa.h:16:33: error: format ‘%d’ expects argument of type ‘int’, but argument 7 has type ‘ssize_t’ {aka ‘long int’} [-Werror=form
  at=]
     16 |         IPA_LOGP(SESIPA, level, "%s: " fmt, func, ## args)
        |                                 ^~~~~~
  …/include/onomondo/ipa/log.h:18:53: note: in definition of macro ‘IPA_LOGP’
     18 |         ipa_logp(subsys, level, __FILE__, __LINE__, fmt, ## args)
        |                                                     ^~~
  …/src/ipa/libipa/esipa.c:129:17: note: in expansion of macro ‘IPA_LOGP_ESIPA’
    129 |                 IPA_LOGP_ESIPA(function_name, LERROR, "cannot encode eIM request! rc = %d\n", rc.encoded);
        |                 ^~~~~~~~~~~~~~

Change-Id: I5b210ae5acff362cf845f6a37073d2bffe69c76e
Oliver Smith at

#28801 (Jun 22, 2026, 10:50:55 AM)

utils: ignore Waddress in IPA_STR_FROM_ASN

When building with -Werror, GCC complains about this assert in the macro:

  #define IPA_STR_FROM_ASN(asn1_obj) ({ \
  char *__str; \
  assert(asn1_obj); \    <-----------------------------------------------
  __str = IPA_ALLOC_N((asn1_obj)->size + 1); \
  assert(__str); \
  memcpy(__str, (asn1_obj)->buf, (asn1_obj)->size); \
  __str[(asn1_obj)->size] = '\0'; \
  __str; \
  })

For example:

  …/src/ipa/libipa/es10b_get_eim_cfg_data.c:48:21: error: the comparison will always evaluate as ‘true’ for the address of ‘eimId’ will never be NULL [-Werror=address]
     48 |                     IPA_STR_FROM_ASN(&res->res->eimConfigurationDataList.list.array[i]->eimId);

Add pragmas to ignore the error, so it can still assert if somebody
should pass NULL to the macro.

Change-Id: Ia2ef30880dd3e5b2ab90eedd0046a95a22614a81
Oliver Smith at

#28800 (Jun 22, 2026, 10:50:53 AM)

contrib/jenkins: build with -Werror

Now that all warnings are fixed, let's build with Werror in CI.

Change-Id: I8a8a7bc8a10e8d86a09fbd289b00641c19c3be6e
Oliver Smith at

#28799 (Jun 22, 2026, 10:50:47 AM)

gitignore: add build dir

Change-Id: Iea8f79b4094ed79f64b0ed6d6e34212ebaea0c43
Oliver Smith at

#28798 (Jun 22, 2026, 10:50:45 AM)

activation_code: fix missing const for item_end

Fix for:
  …/src/ipa/libipa/activation_code.c: In function ‘ipa_activation_code_parse’:
  …/src/ipa/libipa/activation_code.c:62:26: error: assignment discards ‘const’ qualifier from pointer target type [-Werror=discarded-qualifiers]
     62 |                 item_end = strchr(item + 1, '$');
        |                          ^

Change-Id: Idcdd06f57da0e7c05ea184c56cadfc6de85514e6
Oliver Smith at

#28797 (Jun 22, 2026, 10:13:35 AM)

contrib/jenkins: new script

Add a script for build verifications on https://jenkins.osmocom.org.

Related: SYS#8103
Change-Id: I0305c3196896667f4963853099d0767e0acbdb30
Oliver Smith at

#28796 (Jun 22, 2026, 10:00:50 AM)

contrib/jenkins: new script

Add a script for build verifications on https://jenkins.osmocom.org.

Related: SYS#8103
Change-Id: Id5f282fd1e3403be3b5d2fcb962c2dda62bae905
Oliver Smith at

#28795 (Jun 22, 2026, 8:34:42 AM)

CCID: Check if reader times out while expecting procedure byte

A case 3 APDU is sent toward the reader. The reader expects a procedure
byte or a status word. If none of these are sent by the SIM the reader
must timeout and send an error message back to the host.

Change-Id: Iacd6aacaf8220e69b9b7038e354d54c788d1eb05
Andreas Eversberg at

#28794 (Jun 22, 2026, 8:34:37 AM)

CCID: Send procedure byte, when not expected

A case 1 APDU does not request any data from SIM to return. The SIM will
only return a status byte with no procedure byte in advance.

The test sends a procedure byte in advance of the two status bytes
towards the reader. The reader expects SW1 instead of the status byte,
so that it returns it as SW1.

Change-Id: Icffd48d99f0eb48e0898efb027854eba8c22f4a4
Andreas Eversberg at

#28793 (Jun 22, 2026, 8:34:31 AM)

CCID: Check if reader handles Abort correctly

This test fails with osmo-ccid-firmware, because it is not yet
implemented.

Change-Id: Iebe97e73497b8468ebf08faf2c4db700fc76997f
Andreas Eversberg at

#28792 (Jun 22, 2026, 8:34:24 AM)

CCID: Check if reader times out after first status word

A case 1 APDU is sent towards the reader. The reader expects two status
words. If only the first word is sent by the SIM, the reader must
timeout and send an error message back to the host.

Change-Id: Ic5b892e356c13808555d75746c48c6d8c96ec462
Andreas Eversberg at

#28791 (Jun 22, 2026, 8:34:18 AM)

CCID: Send a wrong procedure byte towards the reader

A case 3 request is send and a response with data is expected, but the
first byte replied by the sim is not a procedure byte, nor a valid
status byte.

This text expects the reader to return an error that states an incorrect
received procedure byte.

Change-Id: Iaa0bd8845b3408fba309874fe41c855d8e7efccc
Andreas Eversberg at

#28790 (Jun 20, 2026, 11:02:34 PM)

server: vty: fix docs for cfg_server_rotate_localtime[_mod_n]

Change-Id: I6fd1d081bba035fbd9d72a1705ab58194edf274e
Fixes: 18747641 ("pcap-server: Make rotate-localtime feature configurable through VTY")
Vadim Yanitskiy at

#28789 (Jun 20, 2026, 11:02:31 PM)

vty: clamp configured snaplen to the wire-framing limit

osmo-pcap carries each captured packet in a frame whose length field
(struct osmo_pcap_data.len) is a uint16_t, so any snaplen above ~64 KiB
cannot be transported and is silently clamped by the server when sizing
its receive buffer (calc_data_max_len() caps at UINT16_MAX). The VTY,
however, advertised libpcap's MAXIMUM_SNAPLEN (262144), misleading users
into configuring values that never take effect.

Introduce OSMO_PCAP_MAX_SNAPLEN (65535) and, in both the client "pcap
snaplen" and server "max-snaplen" handlers, warn and cap the value to it
when a larger one is given. The command syntax keeps the <1-262144>
range for backwards compatibility so existing configs still parse; the
help text now documents the effective 64 KiB limit.

Change-Id: Ia56cad48e8cefe8ae103f2f7d2e037bf28438b71
AI-Assisted: yes (Claude)
Related: 6d2f7c52 ("server: Limit rx buffer size to UINT16_MAX")
Related: SYS#8099
Vadim Yanitskiy at

#28788 (Jun 20, 2026, 11:01:59 PM)

doc: clarify 'pcap snaplen' / 'max-snaplen'

Change-Id: Ic2c82173c12814d61f0ee9f7454b9e5dcb0c13f4
Related: SYS#8099
Vadim Yanitskiy at

#28787 (Jun 20, 2026, 9:06:02 PM)

tls: fix broken certificate hostname verification

verify_cert_cb() retrieved the gnutls session pointer and passed it to
gnutls_certificate_verify_peers3() as the expected hostname.  But the
session pointer is set to the osmo_tls_session struct (it is needed by
cert_callback()), not a hostname string.  Hostname matching was
therefore performed against raw struct bytes, rendering verification
meaningless and potentially reading out of bounds, even when
"tls verify-cert" was enabled.

Store the configured hostname in struct osmo_tls_session and have
verify_cert_cb() read it from there.  Also drop the stray
gnutls_certificate_verify_peers3() call in the client setup: it ran
before any handshake (so there were no peer certificates yet) and its
result was ignored; the real verification happens via the registered
callback during the handshake.

Change-Id: If64950a698bfcfbf556a37ef1be3e68abc124384
AI-Assisted: yes (Claude)
Vadim Yanitskiy at

#28786 (Jun 20, 2026, 8:58:09 PM)

tls: fix broken certificate hostname verification

verify_cert_cb() retrieved the gnutls session pointer and passed it to
gnutls_certificate_verify_peers3() as the expected hostname.  But the
session pointer is set to the osmo_tls_session struct (it is needed by
cert_callback()), not a hostname string.  Hostname matching was
therefore performed against raw struct bytes, rendering verification
meaningless and potentially reading out of bounds, even when
"tls verify-cert" was enabled.

Store the configured hostname in struct osmo_tls_session and have
verify_cert_cb() read it from there.  Also drop the stray
gnutls_certificate_verify_peers3() call in the client setup: it ran
before any handshake (so there were no peer certificates yet) and its
result was ignored; the real verification happens via the registered
callback during the handshake.

Change-Id: If64950a698bfcfbf556a37ef1be3e68abc124384
AI-Assisted: yes (Claude)
Vadim Yanitskiy at

#28785 (Jun 20, 2026, 8:58:04 PM)

server: fix NULL deref of file_hdr_msg when store is disabled

When a connection has storing disabled (no store), conn->file_hdr_msg
is never populated.  The previous link-header handling skipped the
first branch (gated on conn->store) and fell through to the comparison
branch, which dereferenced the still-NULL conn->file_hdr_msg, crashing
the server on the first PKT_LINK_HDR from such a client.

Gate the whole header tracking on conn->store and simply free the
message when not storing, since osmo_pcap_conn_restart_trace() already
no-ops in that case.

Change-Id: I419e1b66d07307c3e49294984887c153cd8494c3
AI-Assisted: yes (Claude)
Vadim Yanitskiy at

#28784 (Jun 20, 2026, 8:57:59 PM)

server: fix zmq message leak on send failure

zmq_msg_send() only transfers ownership of the message to ZeroMQ on
success.  On failure the caller retains ownership, so the previously
init'd zmq_msg_t was leaked on every failed publish.  Close it
explicitly on the error path.

Change-Id: I501b1bf55bede4e69fa5d9b3f38d87341482ff49
AI-Assisted: yes (Claude)
Vadim Yanitskiy at

#28783 (Jun 20, 2026, 8:57:56 PM)

server: fix msgb leak on duplicate link header

rx_link_hdr() takes ownership of msg on success (rx_link() only frees
it on failure).  Both branches that call update_conn_file_hdr_msg()
free msg, but when an identical link header was already stored neither
branch ran and msg was leaked.

This happens on every duplicate PKT_LINK_HDR, e.g. a client that
periodically resends its header.  Free msg explicitly in that case.

Change-Id: I79344fe942342f2a736878142b3cf036fc982eef
AI-Assisted: yes (Claude)
Vadim Yanitskiy at

#28782 (Jun 20, 2026, 8:57:51 PM)

client: vty: do not print NULL tls hostname

conn->tls_hostname defaults to NULL and can be cleared via "no tls
hostname".  Writing it unconditionally emitted a "tls hostname (null)"
line, producing a config that does not re-parse.  Guard it like the
other optional tls fields.

Change-Id: I5b920337409d8c9fa1edb8d47177882cf0a6c4e7
AI-Assisted: yes (Claude)
Vadim Yanitskiy at

#28781 (Jun 20, 2026, 8:57:46 PM)

server: do not abort process on short conn message

conn_read_cb() used OSMO_ASSERT() to check that the received
message holds at least a full osmo_pcap_data header.  Although
conn_segmentation_cb2() should only ever hand up complete frames,
asserting on a length derived from network input means a framing
anomaly would abort the entire server (taking down all other clients'
captures).  Close the offending connection gracefully instead,
consistent with the other error paths in this function.

Change-Id: Ia102ff918ef8152d212e10a860f5dc70efec880b
AI-Assisted: yes (Claude)
Vadim Yanitskiy at

#28780 (Jun 20, 2026, 8:57:43 PM)

client: honor IPv4 header length in GPRS filter

The GPRS-NS/BSSGP filter assumed a fixed 20-byte IPv4 header (IP_LEN)
when locating the UDP header and payload.  When the captured packet
carries IPv4 options (ip_hl > 5), udp_data/payload_data pointed into
the middle of the headers and check_gprs() parsed garbage, classifying
packets incorrectly.

Use the actual header length from ip_hl, reject malformed headers
(ip_hl < 5), and re-validate that the larger headers fit within the
captured length before computing the payload.

Change-Id: Iac1fa9cc2a3c06cbe19c3e7799a0b335f2e3dda9
AI-Assisted: yes (Claude)
Vadim Yanitskiy at

#28779 (Jun 20, 2026, 8:57:37 PM)

client: fix off-by-one in wrapped pcap stats counter

When a libpcap stats counter (ps_recv/ps_drop/ps_ifdrop) wraps around
UINT_MAX, get_psbl_wrapped_ctr() computed the delta as
(UINT_MAX - old_val) + new_val, omitting the single increment that
takes the counter from UINT_MAX through zero.  Add the missing +1 so
the reported delta matches the real number of increments.

Change-Id: I66581910dbd1e955831a6ff913042059ad4994a7
AI-Assisted: yes (Claude)
Vadim Yanitskiy at

#28778 (Jun 20, 2026, 8:57:29 PM)

tls: do not treat GNUTLS_E_AGAIN/INTERRUPTED as fatal on read

osmo_tls_client_bfd_cb() treated any non-positive return from
gnutls_record_recv() as a fatal error and tore down the session.  On a
non-blocking socket gnutls_record_recv() can return GNUTLS_E_AGAIN or
GNUTLS_E_INTERRUPTED (both negative but non-fatal), which would drop
an otherwise healthy TLS session.  Handle them as retryable, mirroring
the existing logic in tls_write().

Change-Id: If2f842b202dd08c07dffe3770c51cf0ce886beee
AI-Assisted: yes (Claude)
Vadim Yanitskiy at

#28777 (Jun 20, 2026, 8:57:13 PM)

server: vty: validate rotate-localtime modulus against the new interval

apply_rotate_localtime() computed the maximum allowed modulus from
pcap_server->rotate_localtime.intv, the currently-stored (old) interval,
rather than the intv argument being applied.  On first configuration the
stored interval is the default 0, so the switch hit the default case and
rejected an otherwise valid command; when changing intervals the modulus
was bounds-checked against the wrong interval.  Switch on intv instead.

Change-Id: I0b367d4e255db3208b41e12adec682026b99cc18
AI-Assisted: yes (Claude)
Vadim Yanitskiy at

#28776 (Jun 20, 2026, 8:55:31 PM)

client: Fix 32-bit overflow when computing pcapng EPB timestamp

tv_sec * 1000 * 1000 was evaluated in int arithmetic.  Where time_t /
tv_sec is 32-bit, this overflows for any tv_sec > ~2147, corrupting
the 64-bit timestamp_usec well before the year 2038.  Cast tv_sec to
uint64_t before the multiplication so the whole expression
is computed in 64 bits.

Change-Id: I20d3282b8cba1675ce2d0860e66027e5ee8245ef
AI-Assisted: yes (Claude)
Vadim Yanitskiy at

#28775 (Jun 20, 2026, 8:50:03 PM)

saip/param_source: try to not repeat random values

Change-Id: I4fa743ef5677580f94b9df16a5051d1d178edeb0
Jenkins: skip-card-test
Vadim Yanitskiy at

#28774 (Jun 20, 2026, 8:49:58 PM)

personalization: generate sdkey classes from a list

Change-Id: Ic92ddea6e1fad8167ea75baf78ffc3eb419838c4
Jenkins: skip-card-test
Vadim Yanitskiy at

#28773 (Jun 20, 2026, 8:49:52 PM)

ConfigurableParameter: do not magically overwrite the 'name' attribute

The ClassVarMeta metaclass used to derive each ConfigurableParameter's
'name' attribute automatically from the Python class name (via
camel_to_snake()).  Stop doing this, for three reasons:

1) Python class names follow constraints that do not fit the naming
   commonly used in CSV files.  For example, a name like
   "5GS-SUCI-CalcInfo" starts with a digit and contains dashes,
   neither of which is permissible in a class name.

2) Python class names live in their own namespace, distinct from the
   one used to present eSIM parameters to end users.  Deriving the UI
   name from the class name couples these two namespaces together.

   Taken together, (1) and (2) mean that automatic naming both imposes
   class-name constraints on the user-visible names and merges the
   internal Python namespace with the publicly shown one - a layer
   violation from the perspective of UI design.

3) Overriding 'name' from __new__() makes manual naming impossible: a
   subclass that sets 'name = "bar"' as a class attribute would still
   end up with the value computed by the metaclass, which is
   surprising and hard to track down:

       class MySuper(metaclass=...):  # __new__ sets name = 'foo'
           ...
       class MySub(MySuper):
           name = 'bar'
       print(MySub().name)  # 'foo', not 'bar' as one would expect

Change-Id: I6f631444c6addeb7ccc5f6c55b9be3dc83409169
Jenkins: skip-card-test
Vadim Yanitskiy at

#28772 (Jun 20, 2026, 8:49:48 PM)

saip: add numeric_base indicator to ConfigurableParameter

By default, numeric_base = None, to indicate that there are no explicit
limitations on the number space.

For parameters that are definitely decimal, set numeric_base = 10.
For definitely hexadecimal, set numeric_base = 16.

Do the same for ConfigurableParameter as well as ParamSource, so callers
can match them up: if a parameter is numeric_base = 10, then omit
sources that are numeric_base = 16, and vice versa.

Change-Id: Ib0977bbdd9a85167be7eb46dd331fedd529dae01
Jenkins: skip-card-test
Vadim Yanitskiy at

#28771 (Jun 20, 2026, 8:49:45 PM)

add comment about not updating existing key_usage_qualifier

Change-Id: Ie23ae5fde17be6b37746784bf1601b4d0874397a
Jenkins: skip-card-test
Vadim Yanitskiy at

#28770 (Jun 20, 2026, 8:49:42 PM)

add test_param_src.py

Change-Id: I03087b84030fddae98b965e0075d44e04ec6ba5c
Jenkins: skip-card-test
Vadim Yanitskiy at

#28769 (Jun 20, 2026, 8:49:39 PM)

personalization.ConfigurableParameter: fix BytesIO() input

Change-Id: I0ad160eef9015e76eef10baee7c6b606fe249123
Jenkins: skip-card-test
Vadim Yanitskiy at

#28768 (Jun 20, 2026, 8:49:35 PM)

ConfigurableParameter: safer val length check

validate_val() calls len() to check the value against allow_len,
min_len and max_len. len() requires the object to have a __len__()
method, which integers do not — calling len() on an int raises
TypeError.

Fix this by checking for __len__ first: if present, use len(val) as
usual; otherwise fall back to len(str(val)), which gives the number
of decimal digits for integer values.

Change-Id: Ibe91722ed1477b00d20ef5e4e7abd9068ff2f3e4
Jenkins: skip-card-test
Vadim Yanitskiy at

#28767 (Jun 20, 2026, 8:49:31 PM)

UppAudit: better indicate exception cause

Change-Id: I4d986b89a473a5b12ed56b4710263b034876a33e
Jenkins: skip-card-test
Vadim Yanitskiy at

#28766 (Jun 20, 2026, 8:49:28 PM)

test_configurable_parameters.py: add tests for new parameters

For:
SmspTpScAddr
MilenageRotation
MilenageXoringConstants
TuakNrOfKeccak

Change-Id: Iecbea14fe31a9ee08d871dcde7f295d26d7bd001
Jenkins: skip-card-test
Vadim Yanitskiy at

#28765 (Jun 20, 2026, 8:49:23 PM)

MncLen

Change-Id: I6c600faeab00ffb072acbe94c9a8b2d1397c07d3
Jenkins: skip-card-test
Vadim Yanitskiy at

#28764 (Jun 20, 2026, 8:49:17 PM)

param_source: use secrets.SystemRandom as secure random nr source

secrets.SystemRandom is defined as the most secure random source
available on the given operating system.

Change-Id: I8049cd1292674b3ced82b0926569128535af6efe
Jenkins: skip-card-test
Vadim Yanitskiy at

#28763 (Jun 20, 2026, 8:49:14 PM)

param_source: use random.SystemRandom as random nr source

Python's random module uses a PRNG (Mersenne Twister) which is
utterly insecure for key generation - it was so far only used for
testing.  Replace it with random.SystemRandom(), which draws from
/dev/urandom and is suitable for generating cryptographic key material.

Change-Id: I6de38c14ac6dd55bc84d53974192509c18d02bfa
Jenkins: skip-card-test
Vadim Yanitskiy at

#28762 (Jun 20, 2026, 8:49:08 PM)

add test_configurable_parameters.py

Add ConfigurableParameterTest, which applies each parameter to a real
UPP DER template and reads it back, comparing results against a stored
expected-output snapshot (xo/test_configurable_parameters).

Add TestValidateVal covering validate_val() for Iccid, Imsi, Pin1, Puk1
and K, testing both valid inputs and invalid ones expected to raise
ValueError.

Add TestEnumParam covering the EnumParam methods (validate_val,
map_name_to_val, map_val_to_name, name_normalize, clean_name_str) using
AlgorithmID as the concrete subclass, including fuzzy name matching.

Also add get_value_from_pes() to ConfigurableParameter as a convenience
wrapper around get_values_from_pes() that asserts all returned values
are identical and returns the single result.

Change-Id: Ia55f0d11f8197ca15a948a83a34b3488acf1a0b4
Co-authored-by: Vadim Yanitskiy <vyanitskiy@sysmocom.de>
Jenkins: skip-card-test
Vadim Yanitskiy at

#28761 (Jun 20, 2026, 8:49:01 PM)

param_source: allow plugging a random implementation (for testing)

Change-Id: Idce2b18af70c17844d6f09f7704efc869456ac39
Jenkins: skip-card-test
Vadim Yanitskiy at

#28760 (Jun 20, 2026, 8:48:55 PM)

personalization: add int as input type for BinaryParameter

Change-Id: I31d8142cb0847a8b291f8dc614d57cb4734f0190
Jenkins: skip-card-test
Vadim Yanitskiy at

#28759 (Jun 20, 2026, 8:48:45 PM)

personalization: fix EF_SMSP length, alpha_id padding

The efFileSize needs to be updated and the alpha_id needs to be != None.

Change-Id: Ief6e02517f3e96158a2509d763b88aec4bd5a296
Jenkins: skip-card-test
Vadim Yanitskiy at

#28758 (Jun 20, 2026, 8:48:37 PM)

saip SmspTpScAddr.get_values_from_pes: allow empty values

Change-Id: Ibbdd08f96160579238b50699091826883f2e9f5a
Jenkins: skip-card-test
Vadim Yanitskiy at

#28757 (Jun 20, 2026, 7:12:18 AM)

struct gsm_bts: drop unused ms_max_power

Change-Id: I0b02015db8b8e670eaff40c578f0474d9be9bb45
Vadim Yanitskiy at

#28756 (Jun 20, 2026, 7:12:15 AM)

common: track whether gsm_time has been initialized

l1sap_info_time_ind() used 'bts->gsm_time.fn != 0' as a proxy for
"we have a previous frame number to diff against".  This is unreliable:
Fn=0 is a _valid_ frame number, recurring on every hyperframe wrap.
If gsm_time.fn happened to be 0 and the next time indication jumped
forward by more than one frame, the real gap was silently swallowed.

It also gave no clean way to suppress the bogus "Invalid condition
detected: Frame difference is ..." message that appears when the PHY
(re)starts its TDMA frame number (e.g. from 0) on bring-up.

Introduce an explicit 'bts->gsm_time_valid' flag instead:

* l1sap_info_time_ind() treats the first indication of an epoch as
  having no gap (frames_expired = 0): no warning, no RACH-slot
  accounting;
* the flag is cleared in st_op_disabled_notinstalled_on_enter(), so
  each BTS bring-up starts a fresh clock epoch regardless of which
  FN the PHY reports first.

Change-Id: I7022b0ad084a0c224f7e8c04aca0648915b1a1c6
AI-Assisted: yes (Claude)
Related: OS#7020
Vadim Yanitskiy at

#28755 (Jun 20, 2026, 7:12:11 AM)

tests/meas: remove unused 'delta'

gcc 16.1.1 emits a -Wunused-but-set-variable warning.

Change-Id: I2540d701743caefb4bf54bb5b4ebe683d3257071
Vadim Yanitskiy at

#28754 (Jun 20, 2026, 7:07:18 AM)

osmo-bts-trx: fix spurious clock skew shutdown after self-compensation

When the BTS runs ahead of the transceiver (elapsed_fn < 0),
trx_sched_clock() reschedules the timerfd to deliberately delay the
next FN.  osmo_timerfd_schedule() resets the timerfd and discards any
accumulated expirations, but last_fn_timer.tv was left pointing at
the previous callback.  The next trx_fn_timer_cb() then measures
elapsed_us all the way back to that previous callback - spanning the
deliberate delay (or any OS stall that preceded us) - and falsely
trips the "PC clock skew too high" check, shutting the BTS down
for no good reason.

Advance last_fn_timer.tv to the projected firing time of the
rescheduled timer so that the next callback measures roughly
one FN interval, as expected.

Change-Id: Icdb7db8abe70258ae008d9514b6608bd74bb2881
AI-Assisted: yes (Claude)
Related: OS#6794
Vadim Yanitskiy at

#28753 (Jun 20, 2026, 7:07:12 AM)

osmo-bts-trx: shut down on stale clock indication from transceiver

We expect the transceiver to be a reliable, monotonic clock source.
If it reports an FN far behind our local timer (elapsed_fn < 0) while
far more wall-clock time elapsed than its FN advance accounts for,
its clock has likely stalled and the indication carries a stale frame
number.  Acting on it drags the scheduler backwards and re-transmits
already-sent TDMA frames, corrupting lchan-internal state(s).

Detect this and shut down the process, same rationale as the existing
"PC clock skew too high" check in trx_fn_timer_cb().

Change-Id: If787ab7ed70aa2dcb0389ceb58620c2302c3431a
AI-Assisted: yes (Claude)
Related: OS#7020, OS#6794
Vadim Yanitskiy at

#28752 (Jun 18, 2026, 12:17:26 PM)

CCID: Check if reader sends request TPDU with maximum size

The maximum size of a request TPDU can have 5 bytes header and 255 bytes
data. It is expected that the reader transmits all bytes to SIM without
failure.

Change-Id: I7c1cb52b578c19d6c0ec1493e45f6ed9c43735b4
Andreas Eversberg at

#28751 (Jun 18, 2026, 12:17:22 PM)

CCID: Check if reader times out while expecting status words

A case 1 APDU is sent toward the reader. The reader expects two status
words. If none of these are sent by the SIM the reader must timeout and
send an error message back to the host.

Change-Id: I054b56a9e2f10e5b984ad0398efb4be5696ce16c
Andreas Eversberg at

#28750 (Jun 18, 2026, 12:17:18 PM)

CCID: Check if reader handles Abort correctly

This test fails with osmo-ccid-firmware, because it is not yet
implemented.

Change-Id: Iebe97e73497b8468ebf08faf2c4db700fc76997f
Andreas Eversberg at

#28749 (Jun 18, 2026, 12:17:14 PM)

SIMTRACE: Increase USB receive buffer size

The maximum SIM request data can be 255 bytes. Additionally, the
SIMtrace PDU header is 14 bytes. So increase the buffer to 269 bytes.

Change-Id: I05261b4a754b4892955d0b4e426bd32be261efa7
Andreas Eversberg at

#28748 (Jun 18, 2026, 12:17:10 PM)

CCID: Check if reader times out while expecting procedure byte

A case 3 APDU is sent toward the reader. The reader expects a procedure
byte or a status word. If none of these are sent by the SIM the reader
must timeout and send an error message back to the host.

Change-Id: Iacd6aacaf8220e69b9b7038e354d54c788d1eb05
Andreas Eversberg at

#28747 (Jun 18, 2026, 12:17:07 PM)

CCID: Add testenv.cfg to run tests using testenv

Change-Id: I97c9da414facf438aa28d5200c4152730ff763a2
Andreas Eversberg at

#28746 (Jun 18, 2026, 12:17:03 PM)

CCID: Send a wrong procedure byte towards the reader

A case 3 request is send and a response with data is expected, but the
first byte replied by the sim is not a procedure byte, nor a valid
status byte.

This text expects the reader to return an error that states an incorrect
received procedure byte.

Change-Id: Iaa0bd8845b3408fba309874fe41c855d8e7efccc
Andreas Eversberg at

#28745 (Jun 18, 2026, 12:16:59 PM)

CCID: Send procedure byte, when not expected

A case 1 APDU does not request any data from SIM to return. The SIM will
only return a status byte with no procedure byte in advance.

The test sends a procedure byte in advance of the two status bytes
towards the reader. The reader expects SW1 instead of the status byte,
so that it returns it as SW1.

Change-Id: Icffd48d99f0eb48e0898efb027854eba8c22f4a4
Andreas Eversberg at

#28744 (Jun 18, 2026, 12:16:41 PM)

CCID: Check if reader accepts highest P3 value 0xff

This test should ensure that there is no buffer overflow when receiving
large responses from SIM.

Change-Id: I298795d791f2964758bd4792e10131f92cf561bc
Andreas Eversberg at

#28743 (Jun 18, 2026, 12:16:33 PM)

CCID: Check if reader handles special P3 value 0x00 correctly

If data is requested from SIM with P3 set 0x00, it means that 256
bytes are requested. The reader will receive a procedure byte, which
must cause it to receive all 256 data bytes + two status words.

Change-Id: Icc3fd1937b9829fcf825c58d7b676aa2be2c48e7
Andreas Eversberg at

#28742 (Jun 18, 2026, 12:15:20 PM)

CCID: Check response of reader with empty SIM carrier

The reader has a SIM carrier inserted, but there is no response from the
SIM while expecting the ATR. The reader will get a timeout and is
expected to respond with a suitable error code.

The test uses the slot with the SIMtrace inserted. The SIMtrace will not
respond with an ATR. This way there is no (extra) empty slot required
for this test.

Change-Id: Ifebdcce8f9dd9a51de5a5cb6cf223041d5c38622
Andreas Eversberg at

#28741 (Jun 18, 2026, 12:15:14 PM)

CCID: Check if reader restarts WWT upon NULL procedure byte

The reader will receive a NULL procedure byte every 0.2 for a long time.
The reader may only respond with a status that time extension was
requested. At the end the SIM proceeds with a valid response. This
response must be returned by the reader.

Change-Id: I4eb09e86f88df19d96e9ec55872654352ca2ebd5
Andreas Eversberg at

#28740 (Jun 18, 2026, 12:11:09 PM)

CCID: Send procedure byte, when not expected

A case 1 APDU does not request any data from SIM to return. The SIM will
only return a status byte with no procedure byte in advance.

The test sends a procedure byte in advance of the two status bytes
towards the reader. The reader expects SW1 instead of the status byte,
so that it returns it as SW1.

Change-Id: Icffd48d99f0eb48e0898efb027854eba8c22f4a4
Andreas Eversberg at

#28739 (Jun 18, 2026, 12:11:05 PM)

CCID: Add testenv.cfg to run tests using testenv

Change-Id: I97c9da414facf438aa28d5200c4152730ff763a2
Andreas Eversberg at

#28738 (Jun 18, 2026, 12:11:00 PM)

CCID: Check if reader sends request TPDU with maximum size

The maximum size of a request TPDU can have 5 bytes header and 255 bytes
data. It is expected that the reader transmits all bytes to SIM without
failure.

Change-Id: I7c1cb52b578c19d6c0ec1493e45f6ed9c43735b4
Andreas Eversberg at

#28737 (Jun 18, 2026, 12:10:55 PM)

CCID: Send a wrong procedure byte towards the reader

A case 3 request is send and a response with data is expected, but the
first byte replied by the sim is not a procedure byte, nor a valid
status byte.

This text expects the reader to return an error that states an incorrect
received procedure byte.

Change-Id: Iaa0bd8845b3408fba309874fe41c855d8e7efccc
Andreas Eversberg at

#28736 (Jun 18, 2026, 12:10:51 PM)

CCID: Check if reader accepts highest P3 value 0xff

This test should ensure that there is no buffer overflow when receiving
large responses from SIM.

Change-Id: I298795d791f2964758bd4792e10131f92cf561bc
Andreas Eversberg at

#28735 (Jun 18, 2026, 12:10:43 PM)

CCID: Check if reader handles Abort correctly

This test fails with osmo-ccid-firmware, because it is not yet
implemented.

Change-Id: Iebe97e73497b8468ebf08faf2c4db700fc76997f
Andreas Eversberg at

#28734 (Jun 18, 2026, 12:10:35 PM)

CCID: Check if reader restarts WWT upon NULL procedure byte

The reader will receive a NULL procedure byte every 0.2 for a long time.
The reader may only respond with a status that time extension was
requested. At the end the SIM proceeds with a valid response. This
response must be returned by the reader.

Change-Id: I4eb09e86f88df19d96e9ec55872654352ca2ebd5
Andreas Eversberg at

#28733 (Jun 18, 2026, 12:10:29 PM)

CCID: Check if reader handles special P3 value 0x00 correctly

If data is requested from SIM with P3 set 0x00, it means that 256
bytes are requested. The reader will receive a procedure byte, which
must cause it to receive all 256 data bytes + two status words.

Change-Id: Icc3fd1937b9829fcf825c58d7b676aa2be2c48e7
Andreas Eversberg at

#28732 (Jun 18, 2026, 12:10:16 PM)

CCID: Check if reader times out while expecting status words

A case 1 APDU is sent toward the reader. The reader expects two status
words. If none of these are sent by the SIM the reader must timeout and
send an error message back to the host.

Change-Id: I054b56a9e2f10e5b984ad0398efb4be5696ce16c
Andreas Eversberg at

#28731 (Jun 18, 2026, 12:10:07 PM)

SIMTRACE: Increase USB receive buffer size

The maximum SIM request data can be 255 bytes. Additionally, the
SIMtrace PDU header is 14 bytes. So increase the buffer to 269 bytes.

Change-Id: I05261b4a754b4892955d0b4e426bd32be261efa7
Andreas Eversberg at

#28730 (Jun 18, 2026, 12:08:16 PM)

CCID: Check if reader times out while expecting procedure byte

A case 3 APDU is sent toward the reader. The reader expects a procedure
byte or a status word. If none of these are sent by the SIM the reader
must timeout and send an error message back to the host.

Change-Id: Iacd6aacaf8220e69b9b7038e354d54c788d1eb05
Andreas Eversberg at

#28729 (Jun 18, 2026, 12:08:09 PM)

CCID: Check response of reader with empty SIM carrier

The reader has a SIM carrier inserted, but there is no response from the
SIM while expecting the ATR. The reader will get a timeout and is
expected to respond with a suitable error code.

The test uses the slot with the SIMtrace inserted. The SIMtrace will not
respond with an ATR. This way there is no (extra) empty slot required
for this test.

Change-Id: Ifebdcce8f9dd9a51de5a5cb6cf223041d5c38622
Andreas Eversberg at

#28728 (Jun 17, 2026, 11:50:19 PM)

osmo-bts-trx: shut down on stale clock indication from transceiver

We expect the transceiver to be a reliable, monotonic clock source.
If it reports an FN far behind our local timer (elapsed_fn < 0) while
far more wall-clock time elapsed than its FN advance accounts for,
its clock has likely stalled and the indication carries a stale frame
number.  Acting on it drags the scheduler backwards and re-transmits
already-sent TDMA frames, corrupting lchan-internal state(s).

Detect this and shut down the process, same rationale as the existing
"PC clock skew too high" check in trx_fn_timer_cb().

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
Change-Id: If787ab7ed70aa2dcb0389ceb58620c2302c3431a
Related: OS#7020, OS#6794
Vadim Yanitskiy at

#28727 (Jun 17, 2026, 10:28:26 PM)

osmo-bts-trx: reset BTS GSM time on clock (re)start

trx_sched_clock_started() is called when the transceiver is powered
on, e.g. after an A-bis link re-establishment, which in ttcn3-bts-test
happens once per testcase.  The transceiver restarts its TDMA frame
number from ~0, but we only reset the per-TRX clock state (tcs),
leaving bts->gsm_time.fn at the previous epoch's value.

As a result the first (low) FN reported by the transceiver is mistaken
for a huge backwards jump, e.g.:

  l1sap.c:628 Invalid condition detected: Frame difference is 102-10386=2705364 > 1!

Reset bts->gsm_time to FN 0 here so each clock epoch starts clean.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
Change-Id: Id8da126e460d3846a3be5bdb271553457fdd0590
Vadim Yanitskiy at

#28726 (Jun 17, 2026, 1:56:04 PM)

server: do not abort process on short conn message

conn_read_cb() used OSMO_ASSERT() to check that the received
message holds at least a full osmo_pcap_data header.  Although
conn_segmentation_cb2() should only ever hand up complete frames,
asserting on a length derived from network input means a framing
anomaly would abort the entire server (taking down all other clients'
captures).  Close the offending connection gracefully instead,
consistent with the other error paths in this function.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
Change-Id: Ia102ff918ef8152d212e10a860f5dc70efec880b
Vadim Yanitskiy at

#28725 (Jun 17, 2026, 1:56:01 PM)

tls: do not treat GNUTLS_E_AGAIN/INTERRUPTED as fatal on read

osmo_tls_client_bfd_cb() treated any non-positive return from
gnutls_record_recv() as a fatal error and tore down the session.  On a
non-blocking socket gnutls_record_recv() can return GNUTLS_E_AGAIN or
GNUTLS_E_INTERRUPTED (both negative but non-fatal), which would drop
an otherwise healthy TLS session.  Handle them as retryable, mirroring
the existing logic in tls_write().

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
Change-Id: If2f842b202dd08c07dffe3770c51cf0ce886beee
Vadim Yanitskiy at

#28724 (Jun 17, 2026, 1:55:58 PM)

tls: fix broken certificate hostname verification

verify_cert_cb() retrieved the gnutls session pointer and passed it to
gnutls_certificate_verify_peers3() as the expected hostname.  But the
session pointer is set to the osmo_tls_session struct (it is needed by
cert_callback()), not a hostname string.  Hostname matching was
therefore performed against raw struct bytes, rendering verification
meaningless and potentially reading out of bounds, even when
"tls verify-cert" was enabled.

Store the configured hostname in struct osmo_tls_session and have
verify_cert_cb() read it from there.  Also drop the stray
gnutls_certificate_verify_peers3() call in the client setup: it ran
before any handshake (so there were no peer certificates yet) and its
result was ignored; the real verification happens via the registered
callback during the handshake.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
Change-Id: If64950a698bfcfbf556a37ef1be3e68abc124384
Vadim Yanitskiy at

#28723 (Jun 17, 2026, 1:55:53 PM)

server: fix zmq message leak on send failure

zmq_msg_send() only transfers ownership of the message to ZeroMQ on
success.  On failure the caller retains ownership, so the previously
init'd zmq_msg_t was leaked on every failed publish.  Close it
explicitly on the error path.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
Change-Id: I501b1bf55bede4e69fa5d9b3f38d87341482ff49
Vadim Yanitskiy at

#28722 (Jun 17, 2026, 1:55:50 PM)

client: Fix 32-bit overflow when computing pcapng EPB timestamp

tv_sec * 1000 * 1000 was evaluated in int arithmetic.  Where time_t /
tv_sec is 32-bit, this overflows for any tv_sec > ~2147, corrupting
the 64-bit timestamp_usec well before the year 2038.  Cast tv_sec to
uint64_t before the multiplication so the whole expression
is computed in 64 bits.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
Change-Id: I20d3282b8cba1675ce2d0860e66027e5ee8245ef
Vadim Yanitskiy at

#28721 (Jun 17, 2026, 1:55:48 PM)

client: fix off-by-one in wrapped pcap stats counter

When a libpcap stats counter (ps_recv/ps_drop/ps_ifdrop) wraps around
UINT_MAX, get_psbl_wrapped_ctr() computed the delta as
(UINT_MAX - old_val) + new_val, omitting the single increment that
takes the counter from UINT_MAX through zero.  Add the missing +1 so
the reported delta matches the real number of increments.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
Change-Id: I66581910dbd1e955831a6ff913042059ad4994a7
Vadim Yanitskiy at

#28720 (Jun 17, 2026, 1:55:45 PM)

server: fix NULL deref of file_hdr_msg when store is disabled

When a connection has storing disabled (no store), conn->file_hdr_msg
is never populated.  The previous link-header handling skipped the
first branch (gated on conn->store) and fell through to the comparison
branch, which dereferenced the still-NULL conn->file_hdr_msg, crashing
the server on the first PKT_LINK_HDR from such a client.

Gate the whole header tracking on conn->store and simply free the
message when not storing, since osmo_pcap_conn_restart_trace() already
no-ops in that case.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
Change-Id: I419e1b66d07307c3e49294984887c153cd8494c3
Vadim Yanitskiy at

#28719 (Jun 17, 2026, 1:55:42 PM)

client: vty: do not print NULL tls hostname

conn->tls_hostname defaults to NULL and can be cleared via "no tls
hostname".  Writing it unconditionally emitted a "tls hostname (null)"
line, producing a config that does not re-parse.  Guard it like the
other optional tls fields.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
Change-Id: I5b920337409d8c9fa1edb8d47177882cf0a6c4e7
Vadim Yanitskiy at

#28718 (Jun 17, 2026, 1:55:38 PM)

client: honor IPv4 header length in GPRS filter

The GPRS-NS/BSSGP filter assumed a fixed 20-byte IPv4 header (IP_LEN)
when locating the UDP header and payload.  When the captured packet
carries IPv4 options (ip_hl > 5), udp_data/payload_data pointed into
the middle of the headers and check_gprs() parsed garbage, classifying
packets incorrectly.

Use the actual header length from ip_hl, reject malformed headers
(ip_hl < 5), and re-validate that the larger headers fit within the
captured length before computing the payload.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
Change-Id: Iac1fa9cc2a3c06cbe19c3e7799a0b335f2e3dda9
Vadim Yanitskiy at

#28717 (Jun 17, 2026, 1:55:34 PM)

server: vty: validate rotate-localtime modulus against the new interval

apply_rotate_localtime() computed the maximum allowed modulus from
pcap_server->rotate_localtime.intv, the currently-stored (old) interval,
rather than the intv argument being applied.  On first configuration the
stored interval is the default 0, so the switch hit the default case and
rejected an otherwise valid command; when changing intervals the modulus
was bounds-checked against the wrong interval.  Switch on intv instead.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
Change-Id: I0b367d4e255db3208b41e12adec682026b99cc18
Vadim Yanitskiy at

#28716 (Jun 17, 2026, 1:55:29 PM)

server: fix msgb leak on duplicate link header

rx_link_hdr() takes ownership of msg on success (rx_link() only frees
it on failure).  Both branches that call update_conn_file_hdr_msg()
free msg, but when an identical link header was already stored neither
branch ran and msg was leaked.

This happens on every duplicate PKT_LINK_HDR, e.g. a client that
periodically resends its header.  Free msg explicitly in that case.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
Change-Id: I79344fe942342f2a736878142b3cf036fc982eef
Vadim Yanitskiy at

#28715 (Jun 17, 2026, 1:54:17 PM)

server: fix misleading data length validation log message

The format string "%u < %u <= %u" was printed with arguments
(min_len, data->len, max_len), placing the offending length in
the middle and mislabeling it.  This is confusing.  Let's print
the actual length followed by the expected interval instead.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
Change-Id: Ice95c1f8ad1aa8de259364bd70eba0db8918b19e
Vadim Yanitskiy at

#28714 (Jun 17, 2026, 1:50:26 PM)

server: vty: fix docs for cfg_server_rotate_localtime[_mod_n]

Change-Id: I6fd1d081bba035fbd9d72a1705ab58194edf274e
Fixes: 18747641 ("pcap-server: Make rotate-localtime feature configurable through VTY")
Vadim Yanitskiy at

#28713 (Jun 17, 2026, 12:57:24 PM)

vty: clamp configured snaplen to the wire-framing limit

osmo-pcap carries each captured packet in a frame whose length field
(struct osmo_pcap_data.len) is a uint16_t, so any snaplen above ~64 KiB
cannot be transported and is silently clamped by the server when sizing
its receive buffer (calc_data_max_len() caps at UINT16_MAX). The VTY,
however, advertised libpcap's MAXIMUM_SNAPLEN (262144), misleading users
into configuring values that never take effect.

Introduce OSMO_PCAP_MAX_SNAPLEN (65535) and, in both the client "pcap
snaplen" and server "max-snaplen" handlers, warn and cap the value to it
when a larger one is given. The command syntax keeps the <1-262144>
range for backwards compatibility so existing configs still parse; the
help text now documents the effective 64 KiB limit.

Related: SYS#8099
Related: 6d2f7c52 ("server: Limit rx buffer size to UINT16_MAX")
Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
Change-Id: Ia56cad48e8cefe8ae103f2f7d2e037bf28438b71
Vadim Yanitskiy at

#28712 (Jun 17, 2026, 12:57:22 PM)

doc: clarify 'pcap snaplen' / 'max-snaplen'

Change-Id: Ic2c82173c12814d61f0ee9f7454b9e5dcb0c13f4
Related: SYS#8099
Vadim Yanitskiy at

#28711 (Jun 12, 2026, 11:51:07 PM)

saip.PES.rebuild_mandatory_services(): set 5G get-identity, profile-a-x25519, profile-b-p256

Related: SYS#8096 SYS#8037
Change-Id: Ibc29c6437c5c92e2b14938b733156536863465c1
Jenkins: skip-card-test
Neels Hofmeyr at

#28710 (Jun 12, 2026, 11:42:47 PM)

saip.PES.rebuild_mandatory_services(): set 5G get-identity, profile-a-x25519, profile-b-p256

Related: SYS#8096 SYS#8037
Change-Id: Ibc29c6437c5c92e2b14938b733156536863465c1
Neels Hofmeyr at

#28709 (Jun 12, 2026, 11:39:42 PM)

saip.PES.rebuild_mandatory_services(): set 5G get-identity, profile-a-x25519, profile-b-p256

Change-Id: Ibc29c6437c5c92e2b14938b733156536863465c1
Neels Hofmeyr at

#28708 (Jun 12, 2026, 1:55:55 PM)

libosmo_emb: type-safe tearfree_u64_t wrapper for LDRD/STRD access

Although types are frowned upon because memorizing all differerent flavors
of void* is the usual way to get acquainted with any mature C code base
some heretics decided to introduce generics in C11, which can be used to
make aligned access (which guarantees tear-free/restartable 64 bit access
on cortex m4) less exciting.

Change-Id: I458bfaf53e27c51882c7a8c1326e51d12943b0bb
Andreas Eversberg at

#28707 (Jun 12, 2026, 1:15:02 PM)

7816fsm: Handle unexpected procedure bytes gracefully

Dispatch TPDU_FAILED_IND and don't assert for wrong procedure bytes.

Closes:SYS#8050
Change-Id: Ic53814540775f902fce644a5565a7bd2f177a7fe
Andreas Eversberg at

#28706 (Jun 12, 2026, 12:59:17 PM)

libosmo_emb: type-safe tearfree_u64_t wrapper for LDRD/STRD access

Although types are frowned upon because memorizing all differerent flavors
of void* is the usual way to get acquainted with any mature C code base
some heretics decided to introduce generics in C11, which can be used to
make aligned access (which guarantees tear-free/restartable 64 bit access
on cortex m4) less exciting.

Change-Id: I458bfaf53e27c51882c7a8c1326e51d12943b0bb
Andreas Eversberg at

#28705 (Jun 12, 2026, 12:47:33 PM)

ccid: ICC_MUTE instead of CMD_NOT_SUPPORTED on XfrBlock to unpowered slot

The command is supported, just currently impossible.

Closes:OS#7015
Change-Id: I7f64475b023bd2b6fd1c4263850e56dd84d20b3e
Andreas Eversberg at

#28704 (Jun 12, 2026, 12:40:38 PM)

7816fsm: state_chg before card_uart_tx in tpdu_s_procedure_action

State change must precede the TX to ensure we don't lose
TX_COMPLETE notifications that arrive at a bad time.

Change-Id: Id66f836452674209e25dc3ee4c37d616de30001b
Andreas Eversberg at

#28703 (Jun 12, 2026, 12:23:17 PM)

7816fsm: fail PPS on invalid first byte in PPS_S_WAIT_PPSX

Change-Id: I5b74b8443a98224c0c95a664a886066495d8b64a
Andreas Eversberg at

#28702 (Jun 12, 2026, 12:21:57 PM)

7816fsm: reset stale cuart state on FSM RESET entry

Reset paths reached without power-cycling (WTIME_EXP, HW_ERR,
CARD_REMOVAL during a warm reset) leave the cuart with stale tx_busy,
rx_threshold and wtime_etu from the prior transaction. The next ATR
then hits card_uart_tx tx_busy assertion, or the ATR receive stalls
because the 33-byte ATR can never reach a multi-byte rx_threshold
left from a TPDU.

The new card_uart_tx_abort() clears tx_busy + rx_after_tx_compl + WT,
without driving a synthetic TX_COMPLETE through the FSM.

iso7816_3_reset_onenter is the right place to do this alongside
rx_threshold=1 and wtime_etu=default, this mirrors what
card_uart_ctrl(POWER_*=0) already does, but for the warm-reset paths
that don't touch power.

Change-Id: Iac8bd7f4f0eecccc9acce149277a4f5016fec7c1
Andreas Eversberg at

#28701 (Jun 12, 2026, 12:08:23 PM)

cuart: Fix waiting time to be per-byte instead of total timeout

The previous code multiplied WT by the number of expected bytes,
creating a total timeout proportional to the transfer size. This works
fine for (currently unsupported) high baud rates, but it makes it look
like the reader "freezes" at default rates due to the very long delay.

Just reset it upon rx and do not multiply it so it behaves as expected.

Closes:OS#7012
Change-Id: Ic00040b88e1b204db3f4f3edad09878aa28d35a1
Andreas Eversberg at

#28700 (Jun 12, 2026, 7:57:16 AM)

cuart: Fix waiting time to be per-byte instead of total timeout

The previous code multiplied WT by the number of expected bytes,
creating a total timeout proportional to the transfer size. This works
fine for (currently unsupported) high baud rates, but it makes it look
like the reader "freezes" at default rates due to the very long delay.

Just reset it upon rx and do not multiply it so it behaves as expected.

Closes:OS#7012
Change-Id: Ic00040b88e1b204db3f4f3edad09878aa28d35a1
Andreas Eversberg at

#28699 (Jun 10, 2026, 1:51:32 PM)

CCID: Check if reader times out while expecting status words

A case 1 APDU is sent toward the reader. The reader expects two status
words. If none of these are sent by the SIM the reader must timeout and
send an error message back to the host.

Change-Id: I054b56a9e2f10e5b984ad0398efb4be5696ce16c
Andreas Eversberg at

#28698 (Jun 10, 2026, 1:51:27 PM)

CCID: Check response of reader with empty SIM carrier

The reader has a SIM carrier inserted, but there is no response from the
SIM while expecting the ATR. The reader will get a timeout and is
expected to respond with a suitable error code.

The test uses the slot with the SIMtrace inserted. The SIMtrace will not
respond with an ATR. This way there is no (extra) empty slot required
for this test.

Change-Id: Ifebdcce8f9dd9a51de5a5cb6cf223041d5c38622
Andreas Eversberg at

#28697 (Jun 10, 2026, 1:51:23 PM)

CCID: Check if reader handles special P3 value 0x00 correctly

If data is requested from SIM with P3 set 0x00, it means that 256
bytes are requested. The reader will receive a procedure byte, which
must cause it to receive all 256 data bytes + two status words.

Change-Id: Icc3fd1937b9829fcf825c58d7b676aa2be2c48e7
Andreas Eversberg at

#28696 (Jun 10, 2026, 1:51:19 PM)

SIMTRACE: Increase USB receive buffer size

The maximum SIM request data can be 255 bytes. Additionally, the
SIMtrace PDU header is 14 bytes. So increase the buffer to 269 bytes.

Change-Id: I05261b4a754b4892955d0b4e426bd32be261efa7
Andreas Eversberg at

#28695 (Jun 10, 2026, 1:51:14 PM)

CCID: Check if reader restarts WWT upon NULL procedure byte

The reader will receive a NULL procedure byte every 0.2 for a long time.
The reader may only respond with a status that time extension was
requested. At the end the SIM proceeds with a valid response. This
response must be returned by the reader.

Change-Id: I4eb09e86f88df19d96e9ec55872654352ca2ebd5
Andreas Eversberg at

#28694 (Jun 10, 2026, 1:51:10 PM)

CCID: Check if reader handles Abort correctly

This test fails with osmo-ccid-firmware, because it is not yet
implemented.

Change-Id: Iebe97e73497b8468ebf08faf2c4db700fc76997f
Andreas Eversberg at

#28693 (Jun 10, 2026, 1:51:06 PM)

CCID: Integrate SIMTRACE emulation into test cases

This integration allows to add tests that use SIMtrace hardware instead
of a physical SIM. These tests can be used to test handling of invalid
behaviors, such as invalid responses or timeouts.

The number of slots (mp_use_slot_count) are reduced to 7, so that the
8th slot can be used with a SIMtrace for subsequent tests.

Change-Id: Ia27dd5198edb188bc73196ac3fbd6d56ba75812e
Andreas Eversberg at

#28692 (Jun 10, 2026, 1:51:01 PM)

CCID: Check if reader accepts highest P3 value 0xff

This test should ensure that there is no buffer overflow when receiving
large responses from SIM.

Change-Id: I298795d791f2964758bd4792e10131f92cf561bc
Andreas Eversberg at

#28691 (Jun 10, 2026, 1:50:57 PM)

CCID: Update titan.TestPorts.USB to current head

Update the USB test port dependency to include recent changes and
bugfixes that are required for further CCID tests.

Change-Id: I9dd769d2098822721f673b1293542fffa46542cc
Andreas Eversberg at

#28690 (Jun 10, 2026, 1:50:54 PM)

CCID: Add test to verify a working Simtrace setup

This test checks if a valid request is forwarded to SIMtrace and a
valid response is returned back to the reader.

Change-Id: I19264bc257024e9028996e417ff23bbbaebf5f92
Andreas Eversberg at

#28689 (Jun 10, 2026, 1:50:50 PM)

CCID: Send procedure byte, when not expected

A case 1 APDU does not request any data from SIM to return. The SIM will
only return a status byte with no procedure byte in advance.

The test sends a procedure byte in advance of the two status bytes
towards the reader. The reader expects SW1 instead of the status byte,
so that it returns it as SW1.

Change-Id: Icffd48d99f0eb48e0898efb027854eba8c22f4a4
Andreas Eversberg at

#28688 (Jun 10, 2026, 1:50:46 PM)

CCID: Check if reader times out while expecting procedure byte

A case 3 APDU is sent toward the reader. The reader expects a procedure
byte or a status word. If none of these are sent by the SIM the reader
must timeout and send an error message back to the host.

Change-Id: Iacd6aacaf8220e69b9b7038e354d54c788d1eb05
Andreas Eversberg at

#28687 (Jun 10, 2026, 1:50:43 PM)

SIMTRACE: Add missing pres_pol to CardEmu_BD_Config message

Change-Id: I443e8151b0aa9bff150222ab6b507ed1f7946768
Andreas Eversberg at

#28686 (Jun 10, 2026, 1:50:39 PM)

CCID: Add testenv.cfg to run tests using testenv

Change-Id: I97c9da414facf438aa28d5200c4152730ff763a2
Andreas Eversberg at

#28685 (Jun 10, 2026, 1:50:27 PM)

CCID: Truncated APDU test

A SELECT APDU must have a header + two bytes of data (what to select).
The test truncates this APDU in all variants, ranging from 6 bytes down
to 0 bytes. The reader may respond with an error caused by invald
request or with and error caused by timeout of the SIM.

Change-Id: I3df2ad9871bccdd03f618a6a457671adb1624590
Andreas Eversberg at

#28684 (Jun 10, 2026, 1:49:26 PM)

CCID: Check if reader handles truncated SIM response

The reader knows how many byte of data is expected in the SIM response.
The emulated SIM will truncate that response, so that some data and the
final status words are not sent by the SIM. The tests expects the
reader to time out and return an appropriate error core.

Change-Id: I6db6d7889a1355ee9aa2005e676fed5d20a3f2dc
Andreas Eversberg at

#28683 (Jun 10, 2026, 1:47:55 PM)

CCID: Check if reader sends request TPDU with maximum size

The maximum size of a request TPDU can have 5 bytes header and 255 bytes
data. It is expected that the reader transmits all bytes to SIM without
failure.

Change-Id: I7c1cb52b578c19d6c0ec1493e45f6ed9c43735b4
Andreas Eversberg at

#28682 (Jun 10, 2026, 1:47:50 PM)

CCID: Send a wrong procedure byte towards the reader

A case 3 request is send and a response with data is expected, but the
first byte replied by the sim is not a procedure byte, nor a valid
status byte.

This text expects the reader to return an error that states an incorrect
received procedure byte.

Change-Id: Iaa0bd8845b3408fba309874fe41c855d8e7efccc
Andreas Eversberg at

#28681 (Jun 10, 2026, 1:29:25 PM)

CCID: Check if reader times out while expecting procedure byte

A case 3 APDU is sent toward the reader. The reader expects a procedure
byte or a status word. If none of these are sent by the SIM the reader
must timeout and send an error message back to the host.

Change-Id: Iacd6aacaf8220e69b9b7038e354d54c788d1eb05
Andreas Eversberg at

#28680 (Jun 10, 2026, 1:29:21 PM)

CCID: Send procedure byte, when not expected

A case 1 APDU does not request any data from SIM to return. The SIM will
only return a status byte with no procedure byte in advance.

The test sends a procedure byte in advance of the two status bytes
towards the reader. The reader expects SW1 instead of the status byte,
so that it returns it as SW1.

Change-Id: Icffd48d99f0eb48e0898efb027854eba8c22f4a4
Andreas Eversberg at

#28679 (Jun 10, 2026, 1:29:17 PM)

CCID: Check response of reader with empty SIM carrier

The reader has a SIM carrier inserted, but there is no response from the
SIM while expecting the ATR. The reader will get a timeout and is
expected to respond with a suitable error code.

The test uses the slot with the SIMtrace inserted. The SIMtrace will not
respond with an ATR. This way there is no (extra) empty slot required
for this test.

Change-Id: Ifebdcce8f9dd9a51de5a5cb6cf223041d5c38622
Andreas Eversberg at

#28678 (Jun 10, 2026, 1:29:13 PM)

CCID: Check if reader handles special P3 value 0x00 correctly

If data is requested from SIM with P3 set 0x00, it means that 256
bytes are requested. The reader will receive a procedure byte, which
must cause it to receive all 256 data bytes + two status words.

Change-Id: Icc3fd1937b9829fcf825c58d7b676aa2be2c48e7
Andreas Eversberg at

#28677 (Jun 10, 2026, 1:29:09 PM)

CCID: Check if reader accepts highest P3 value 0xff

This test should ensure that there is no buffer overflow when receiving
large responses from SIM.

Change-Id: I298795d791f2964758bd4792e10131f92cf561bc
Andreas Eversberg at

#28676 (Jun 10, 2026, 1:29:05 PM)

CCID: Integrate SIMTRACE emulation into test cases

This integration allows to add tests that use SIMtrace hardware instead
of a physical SIM. These tests can be used to test handling of invalid
behaviors, such as invalid responses or timeouts.

The number of slots (mp_use_slot_count) are reduced to 7, so that the
8th slot can be used with a SIMtrace for subsequent tests.

Change-Id: Ia27dd5198edb188bc73196ac3fbd6d56ba75812e
Andreas Eversberg at

#28675 (Jun 10, 2026, 1:29:01 PM)

CCID: Add testenv.cfg to run tests using testenv

Change-Id: I97c9da414facf438aa28d5200c4152730ff763a2
Andreas Eversberg at

#28674 (Jun 10, 2026, 1:28:57 PM)

CCID: Check if reader sends request TPDU with maximum size

The maximum size of a request TPDU can have 5 bytes header and 255 bytes
data. It is expected that the reader transmits all bytes to SIM without
failure.

Change-Id: I7c1cb52b578c19d6c0ec1493e45f6ed9c43735b4
Andreas Eversberg at

#28673 (Jun 10, 2026, 1:28:53 PM)

CCID: Check if reader handles Abort correctly

This test fails with osmo-ccid-firmware, because it is not yet
implemented.

Change-Id: Iebe97e73497b8468ebf08faf2c4db700fc76997f
Andreas Eversberg at

#28672 (Jun 10, 2026, 1:28:49 PM)

CCID: Send a wrong procedure byte towards the reader

A case 3 request is send and a response with data is expected, but the
first byte replied by the sim is not a procedure byte, nor a valid
status byte.

This text expects the reader to return an error that states an incorrect
received procedure byte.

Change-Id: Iaa0bd8845b3408fba309874fe41c855d8e7efccc
Andreas Eversberg at

#28671 (Jun 10, 2026, 1:28:45 PM)

CCID: Add test to verify a working Simtrace setup

This test checks if a valid request is forwarded to SIMtrace and a
valid response is returned back to the reader.

Change-Id: I19264bc257024e9028996e417ff23bbbaebf5f92
Andreas Eversberg at

#28670 (Jun 10, 2026, 1:28:40 PM)

CCID: Check if reader restarts WWT upon NULL procedure byte

The reader will receive a NULL procedure byte every 0.2 for a long time.
The reader may only respond with a status that time extension was
requested. At the end the SIM proceeds with a valid response. This
response must be returned by the reader.

Change-Id: I4eb09e86f88df19d96e9ec55872654352ca2ebd5
Andreas Eversberg at

#28669 (Jun 10, 2026, 1:28:32 PM)

CCID: Truncated APDU test

A SELECT APDU must have a header + two bytes of data (what to select).
The test truncates this APDU in all variants, ranging from 6 bytes down
to 0 bytes. The reader may respond with an error caused by invald
request or with and error caused by timeout of the SIM.

Change-Id: I3df2ad9871bccdd03f618a6a457671adb1624590
Andreas Eversberg at

#28668 (Jun 10, 2026, 1:28:27 PM)

CCID: Check if reader times out while expecting status words

A case 1 APDU is sent toward the reader. The reader expects two status
words. If none of these are sent by the SIM the reader must timeout and
send an error message back to the host.

Change-Id: I054b56a9e2f10e5b984ad0398efb4be5696ce16c
Andreas Eversberg at

#28667 (Jun 10, 2026, 1:28:16 PM)

SIMTRACE: Add missing pres_pol to CardEmu_BD_Config message

Change-Id: I443e8151b0aa9bff150222ab6b507ed1f7946768
Andreas Eversberg at

#28666 (Jun 10, 2026, 1:26:52 PM)

CCID: Check if reader handles truncated SIM response

The reader knows how many byte of data is expected in the SIM response.
The emulated SIM will truncate that response, so that some data and the
final status words are not sent by the SIM. The tests expects the
reader to time out and return an appropriate error core.

Change-Id: I6db6d7889a1355ee9aa2005e676fed5d20a3f2dc
Andreas Eversberg at

#28665 (Jun 10, 2026, 1:26:44 PM)

SIMTRACE: Increase USB receive buffer size

The maximum SIM request data can be 255 bytes. Additionally, the
SIMtrace PDU header is 14 bytes. So increase the buffer to 269 bytes.

Change-Id: I05261b4a754b4892955d0b4e426bd32be261efa7
Andreas Eversberg at

#28664 (Jun 10, 2026, 9:35:29 AM)

NGAP: UESecurityCapabilities is optional in PathSwitchRequestAcknowledge

Current master branch of Open5GS includes UESecurityCapabilities IE
in PathSwitchRequestAcknowledge, older versions do not. In order to
match message of all versions, replace the IE by an an asterisk.

Change-Id: I4849709d2601505d9aa3ea6c85b718ec65540dff
Andreas Eversberg at

#28663 (Jun 9, 2026, 4:18:50 PM)

Transceiver52M: fix viterbi-eq soft bits on platforms where char is unsigned

The viterbi-eq demodulator stores soft bits into chars.
"char" is signed on x86/amd64 but unsigned on arm64.
On arm64 the stored byte 0x81 (== -127) is read back as +129, so after the
sign flip and vectorSlicer() clamp every soft bit collapses to 0.0.

The same issue also appears to be present in the MS code path, so it was
(blindly) fixed there as well. The MS fixes are untested!

Change-Id: I1cda66228f3d48e1b941b25614d599c16ad79aa0
Manawyrm at

#28662 (Jun 9, 2026, 4:10:30 PM)

stp: for TCAP loadshare: use NI == national

Use a non-zero NI. The TCAP tests don't check it
on the receive path, but the osmo-stp is checking
it if it matches the configuration.

Related: SYS#8061
Change-Id: I51ef302ad72ff3c434fddb39006ce50106a5918f
lynxis at

#28661 (Jun 9, 2026, 4:10:25 PM)

stp: tcap-loadshare: add TC_tcap_loadshare_m3ua_to_ipa_udts

If a TCAP message arrives which is:
* not a TCAP Begin or Abort (e.g. a TCAP Continue)
* not in the TCAP session cache/tracking
* not have a dTID for a registered TCAP Add Range

The tcap load-share will reject this message with a UDTS

Related: SYS#8061
Change-Id: I181b25aedfd70d156c08197d361560b6d055e65a
lynxis at

#28660 (Jun 9, 2026, 3:33:34 PM)

m3ua: fix missing decoding of message priority & network indicator flag

The missing parenthesis always or'ed with a 0x0 into the sio field because
of operator precendence. Left shift is stronger than a binary and.

Change-Id: I7a07363646f66c5c672a2c0d261ca33356b43031
lynxis at

#28659 (Jun 9, 2026, 12:10:44 PM)

Transceiver52M: fix viterbi-eq soft bits on platforms where char is unsigned

The viterbi-eq demodulator stores soft bits into chars.
"char" is signed on x86/amd64 but unsigned on arm64.
On arm64 the stored byte 0x81 (== -127) is read back as +129, so after the
sign flip and vectorSlicer() clamp every soft bit collapses to 0.0.

The same issue also appears to be present in the MS code path, so it was
(blindly) fixed there as well. The MS fixes are untested!

Change-Id: I1cda66228f3d48e1b941b25614d599c16ad79aa0
Manawyrm at

#28658 (Jun 9, 2026, 11:51:19 AM)

cuart: Fix waiting time to be per-byte instead of total timeout

The previous code multiplied WT by the number of expected bytes,
creating a total timeout proportional to the transfer size. This works
fine for (currently unsupported) high baud rates, but it makes it look
like the reader "freezes" at default rates due to the very long delay.

Just reset it upon rx and do not multiply it so it behaves as expected.

Closes:OS#7012
Change-Id: Ic00040b88e1b204db3f4f3edad09878aa28d35a1
Andreas Eversberg at

#28657 (Jun 9, 2026, 11:51:16 AM)

7816fsm: Handle unexpected procedure bytes gracefully

Dispatch TPDU_FAILED_IND and don't assert for wrong procedure bytes.

Closes:SYS#8050
Change-Id: Ic53814540775f902fce644a5565a7bd2f177a7fe
Andreas Eversberg at

#28656 (Jun 9, 2026, 11:51:14 AM)

ccid: ICC_MUTE instead of CMD_NOT_SUPPORTED on XfrBlock to unpowered slot

The command is supported, just currently impossible.

Closes:OS#7015
Change-Id: I7f64475b023bd2b6fd1c4263850e56dd84d20b3e
Andreas Eversberg at

#28655 (Jun 9, 2026, 11:51:11 AM)

7816fsm: state_chg before card_uart_tx in tpdu_s_procedure_action

State change must precede the TX to ensure we don't lose
TX_COMPLETE notifications that arrive at a bad time.

Change-Id: Id66f836452674209e25dc3ee4c37d616de30001b
Andreas Eversberg at

#28654 (Jun 9, 2026, 11:51:09 AM)

7816fsm: reset stale cuart state on FSM RESET entry

Reset paths reached without power-cycling (WTIME_EXP, HW_ERR,
CARD_REMOVAL during a warm reset) leave the cuart with stale tx_busy,
rx_threshold and wtime_etu from the prior transaction. The next ATR
then hits card_uart_tx tx_busy assertion, or the ATR receive stalls
because the 33-byte ATR can never reach a multi-byte rx_threshold
left from a TPDU.

The new card_uart_tx_abort() clears tx_busy + rx_after_tx_compl + WT,
without driving a synthetic TX_COMPLETE through the FSM.

iso7816_3_reset_onenter is the right place to do this alongside
rx_threshold=1 and wtime_etu=default, this mirrors what
card_uart_ctrl(POWER_*=0) already does, but for the warm-reset paths
that don't touch power.

Change-Id: Iac8bd7f4f0eecccc9acce149277a4f5016fec7c1
Andreas Eversberg at

#28653 (Jun 9, 2026, 11:51:06 AM)

7816fsm: fail PPS on invalid first byte in PPS_S_WAIT_PPSX

Change-Id: I5b74b8443a98224c0c95a664a886066495d8b64a
Andreas Eversberg at

#28652 (Jun 9, 2026, 11:51:01 AM)

ccid: reject invalid bClockCommand

Change-Id: I34dedcaaaf3cd67e22b207016f08e745736dd625
Andreas Eversberg at

#28651 (Jun 9, 2026, 11:50:55 AM)

libosmo_emb: type-safe tearfree_u64_t wrapper for LDRD/STRD access

Although types are frowned upon because memorizing all differerent flavors
of void* is the usual way to get acquainted with any mature C code base
some heretics decided to introduce generics in C11, which can be used to
make aligned access (which guarantees tear-free/restartable 64 bit access
on cortex m4) less exciting.

Change-Id: I458bfaf53e27c51882c7a8c1326e51d12943b0bb
Andreas Eversberg at

#28650 (Jun 9, 2026, 11:50:51 AM)

usb: properly handle data toggle bit

Same config SetConfig is currently not properly handled and stale toggle
bits lead to weird transfers until USB resyncs because the asf4 code itself
does not properly handle the toggle bit.

- USB 2.0 §9.4.5 states that ClearFeature(ENDPOINT_HALT) unconditionally
resets the data toggle to DATA0
- USB 2.0 §9.1.1.5 demands toggle reset even when the same config/interface
is selected

The old code was only doing a proper reset upon receiving a bus reset,
but the actual state reset path outlined in the spec is the set config command.
The easy fix here is to split the existing reset code which already does
everything we need into two parts for the actual usb reset and SetConfig.

The current halt clear code only resets DTGL if the endpoint is
actually halted and a fix is a bit more complicated.
_usb_d_dev_ep_stall_clr() is also called from the SETUP-packet cleanup
path in hal_usb_device.c
    _usb_d_dev_ep_stall(ep, USB_EP_STALL_CLR);
    _usb_d_dev_ep_stall(ep | USB_EP_DIR, USB_EP_STALL_CLR);

This runs on every SETUP packet as defensive cleanup of any
leftover stall from a previous failed transfer. That might be why the
asf4 usb code is wrong, because a toggle reset here breaks SETUP.

So the unconditional DTGL reset for halt clearing must therefore happen
in _usb_d_ep_halt_clr itself, which is only reached via the ClearFeature
host request (usbdc_clear_ftr_req -> usb_d_ep_halt(HALT_CLR)),
using a small HPL helper function.

Closes:OS#7016
Change-Id: I5dbca9bd2212407108b44815ecf566fc9c22336d
Andreas Eversberg at

#28649 (Jun 9, 2026, 9:19:37 AM)

tcap_as_loadshare: Fix compare ignoring non-TCAP messages and remove assert

The previous check in asp_loadshare_tcap_sccp()  was was never true because it
checked msg class twice instead of class and type.

Also remove the OSMO_ASSERT in send_back_udts() limiting the function to
CL/DT messages.

Related: SYS#5432
Change-Id: I0831b289e4e4e94fd1b719e6c7164c3dd87c9f88
dwillmann at

#28648 (Jun 9, 2026, 9:13:01 AM)

coverity/jenkins: check if upload was successful

When the server returns an error, the curl command does not fail -
probably because the server sends a wrong http status code:

  curl \
   --form token="$token" \
   --form email=holger@freyther.de --form file=@Osmocom.tgz \
   --form version=Version --form description=AutoUpload \
   https://scan.coverity.com/builds?project=Osmocom
  + set +x
    % Total    % Received % Xferd  Average Speed   Time    Time     Time  Current
                                   Dload  Upload   Total   Spent    Left  Speed
  …
  <html>
  <head><title>413 Request Entity Too Large</title></head>
  <body>
  <center><h1>413 Request Entity Too Large</h1></center>
  <hr><center>nginx/1.19.10</center>
  </body>
  </html>
  Finished: SUCCESS

Fail if the output doesn't contain the "Build successfully submitted"
string, so the job fails if there was an error.

(The request entity too large error is probably an error on their end,
scan.coverity.com still says they are performing upgrades on their
servers.)

Change-Id: Ie63a33dfa7648b38f1f01cb8c87db76949f69e10
Oliver Smith at

#28647 (Jun 9, 2026, 8:16:56 AM)

tcap_as_loadshare: Fix newline on log message

Change-Id: Iad85ec2d4e6a64d84a865c23eb00fddcb6d767c9
dwillmann at

#28646 (Jun 8, 2026, 11:55:02 AM)

fix(ts_51_011): fix lifecycle decoding

- implement proper LCS decoding per TS 102 221 / TS 31.101
- previous implementation misclassified multiple states

Related: OS#7018
Change-Id: I8a3bd820b9fbc13c025f8302d1d2eac21686c541
pmaier@sysmocom.de at

#28645 (Jun 8, 2026, 11:54:59 AM)

fix(ts_51_011): apply correct access conditions length

When the access conditions are extracted from resp_bin, the wrong length
is used and only 2 bytes instead of 3 are extracted.

3GPP TS 51.011, section 9.2.1, table below "Response parameters/data
in case of an EF", clearly states that the length should be 3 bytes
(position 9-11)

Related: OS#7018
Change-Id: I410fb58c395beafba8de6d5ab4e71452f424cdf2
pmaier@sysmocom.de at

#28644 (Jun 8, 2026, 7:24:42 AM)

7816fsm: fail PPS on invalid first byte in PPS_S_WAIT_PPSX

Change-Id: I5b74b8443a98224c0c95a664a886066495d8b64a
ewild at

#28643 (Jun 5, 2026, 1:36:37 PM)

tcap loadsharing: tcap_as_rx_sccp_asp: Fix memory leak

Change-Id: Id0b21bffcad43d9999f7579d92e5ef2f4a0d9f1a
lynxis at

#28642 (Jun 5, 2026, 8:57:34 AM)

testenv: move titan_min to testsrcdir.cfg

Adjust the code so it gets titan_min= from testsrcdir.cfg, instead of
having it in testenv.cfg and enforcing that the value is the same across
all files in the same source directory.

While at it, set the default to 11.1.0 (the value that is currently in
all testenv.cfg files), so we don't need to repeat it in all source
directories.

Change-Id: Ife12e3b3294ce16ebedee1b7998d3b89856f0328
Oliver Smith at

#28641 (Jun 5, 2026, 8:57:27 AM)

testenv: introduce testsrcdir.cfg

Source directories can have more than one testenv.cfg file. Some options
have been added to testenv.cfg that are not really specific to a single
testsuite or how it gets executed, but to the whole source directory.

This is not ideal, because we need to have additional code that ensures
these options have the same value across all testenv.cfg files in the
same source directory, and we need functions that just pick the value
from the first of these configs. When we change such a value, we also
need to potentially make the change in multiple files.

Resolve this by introducing a new config file testsrcdir.cfg, that can
be optionally present in the source directory, and has options that
count for all testsuites in the same source directory.

Move max_jobs_per_gb_ram= as first option to the new file. The following
patches will move all other source directory specific options to
testsrcdir.cfg.

I have also considered naming the new file testdir.cfg, but the name
"testdir" is already used in the source code for the place where we
execute the individual testsuites after copying configs into that
directory.

Change-Id: I8eceea7b874ce1352e2cc9780b77d2a8e694cd28
Oliver Smith at

#28640 (Jun 5, 2026, 8:57:23 AM)

testenv: fix podman_extra with multiple cfgs

Do not reuse the container that gets started to build the testsuite and
test components, to also do the the first testsuite run. Restart it
after selecting the current testenv*.cfg, and use the podman_extra value
from the right config instead.

As side-effect, this also makes the container restart logic much
simpler.

Change-Id: I12e187726673e1ca1b1ecfff6b34b1803127be86
Oliver Smith at

#28639 (Jun 5, 2026, 7:45:37 AM)

Add VTY test for "listen" node of osmo-stp VTY config

Change-Id: Ia1ceb5f0374f47ff269b557be30fc4d59550d1a6
Andreas Eversberg at

#28638 (Jun 5, 2026, 7:45:34 AM)

Add test case to verify proper DSCP settings

Related: SYS#8071
Change-Id: I6ac965998433b4d8213cce30fc3fcf8fe485a092
Andreas Eversberg at

#28637 (Jun 5, 2026, 7:44:48 AM)

Add DSCP configuration support for each individual ASP

Introduce VTY command to configure the Differentiated Services Code
Point (DSCP) values for each Application Server Process.

If the ASP connection has the role "server", it will inherit the DSCP
settings of the listener, unless it is configured at the ASP connection.

Related: SYS#8071
Change-Id: Ia125a392eec5605553809774162675b5249b8494
Andreas Eversberg at

#28636 (Jun 4, 2026, 12:18:07 PM)

Add VTY test for "listen" node of osmo-stp VTY config

Change-Id: Ia1ceb5f0374f47ff269b557be30fc4d59550d1a6
Andreas Eversberg at

#28635 (Jun 4, 2026, 12:16:47 PM)

Add DSCP configuration support for each individual ASP

Introduce VTY command to configure the Differentiated Services Code
Point (DSCP) values for each Application Server Process.

If the ASP connection has the role "server", it will inherit the DSCP
settings of the listener, unless it is configured at the ASP connection.

Related: SYS#8071
Change-Id: Ia125a392eec5605553809774162675b5249b8494
Andreas Eversberg at

#28634 (Jun 4, 2026, 12:16:44 PM)

Add DSCP configuration support for server transport role

Introduce VTY command to configure the Differentiated Services Code
Point (DSCP) values for transport "role" server.

The configured DSCP value is applied to the listener socket. Incoming
socket connections will then automatically inherit these DSCP settings
from the listener socket.

It is not (yet) possible to configure DSCP values for individual active
server connections. The setting applies globally via the listener.
A later patch will allow DSCP configuration of each individual ASP.

Related: SYS#8071
Depends: libosmo-netif.git Change-Id Ic70422ec73c753b61843444582f8665ca42e7a6d
Change-Id: I35eab3672157c318616f51ee3042243aed263d4e
Andreas Eversberg at

#28633 (Jun 4, 2026, 12:16:41 PM)

Add test case to verify proper DSCP settings

Related: SYS#8071
Change-Id: I6ac965998433b4d8213cce30fc3fcf8fe485a092
Andreas Eversberg at

#28632 (Jun 3, 2026, 10:19:11 AM)

CCID: Integrate SIMTRACE emulation into test cases

This integration allows to add tests that use SIMtrace hardware instead
of a physical SIM. These tests can be used to test handling of invalid
behaviors, such as invalid responses or timeouts.

The number of slots (mp_use_slot_count) are reduced to 7, so that the
8th slot can be used with a SIMtrace for subsequent tests.

Change-Id: Ia27dd5198edb188bc73196ac3fbd6d56ba75812e
jolly at

#28631 (Jun 3, 2026, 10:19:05 AM)

SIMTRACE: Add missing pres_pol to CardEmu_BD_Config message

Change-Id: I443e8151b0aa9bff150222ab6b507ed1f7946768
jolly at

#28630 (Jun 3, 2026, 10:18:56 AM)

CCID: Truncated APDU test

A SELECT APDU must have a header + two bytes of data (what to select).
The test truncates this APDU in all variants, ranging from 6 bytes down
to 0 bytes. The reader may respond with an error caused by invald
request or with and error caused by timeout of the SIM.

Change-Id: I3df2ad9871bccdd03f618a6a457671adb1624590
jolly at

#28629 (Jun 3, 2026, 10:18:51 AM)

CCID: Successful case 2 and 3 APDU tests

A SELECT APDU has data and must respond without any data, just the
status words.

A READ BINARY APDU has no data, but it must respond with data, followed
by the status words.

Change-Id: I9110250020c11bc7382b6308a182c09bb79e5e5e
jolly at

#28628 (Jun 3, 2026, 10:18:36 AM)

CCID: Successful case 1 APDU test

A MANAGE CHANNEL APDU has no data and must respond without any data,
just the status words.

Change-Id: I7d5ee9bbd8bb2505a762e3fd80238db658940c16
jolly at

#28627 (Jun 3, 2026, 10:18:09 AM)

CCID: Successful case 4 APDU test

A GET RESPONSE APDU must respond with the exact number of bytes that
have been indicated by SW2 of the previous SELECT MF APDU.

Change-Id: I88c5ad3285c025f584b1c0296095beb918ab3f4e
jolly at

#28626 (Jun 3, 2026, 10:18:01 AM)

CCID: Fix “unsupported Secure” test case

Expect SlotStatus or DataBlock. The specification states that DataBlock
response is used to indicate, if Secure command is not suppported.
Existing implementation, such as Omnikey Cardman 3121 or
osmo-ccid-firmware respond with SlotStatus instead.

Change-Id: I21517c3e28e0d0e42e8a177b7c668bff15c35aa0
jolly at

#28625 (Jun 3, 2026, 10:17:53 AM)

testenv: move titan_min to testsrcdir.cfg

Adjust the code so it gets titan_min= from testsrcdir.cfg, instead of
having it in testenv.cfg and enforcing that the value is the same across
all files in the same source directory.

While at it, set the default to 11.1.0 (the value that is currently in
all testenv.cfg files), so we don't need to repeat it in all source
directories.

Change-Id: Ife12e3b3294ce16ebedee1b7998d3b89856f0328
Oliver Smith at

#28624 (Jun 3, 2026, 10:17:49 AM)

testenv: move podman_extra to testsrcdir.cfg

Move podman_extra to testsrcdir.cfg, as it also needs to be set for the
whole source directory at once.

We actually didn't have a function that ensures it is the same in all
testenv.cfg files, which could lead to subtle bugs such as setting it in
only one of two testenv_*.cfg files in a source directory and then
having testenv pick the file where it is not set and therefore not using
the option when starting the podman container that is used for all
testsuites. This problem is resolved with this patch.

Change-Id: I12e187726673e1ca1b1ecfff6b34b1803127be86
Oliver Smith at

#28623 (Jun 3, 2026, 10:17:44 AM)

testenv: introduce testsrcdir.cfg

Source directories can have more than one testenv.cfg file. Some options
have been added to testenv.cfg that are not really specific to a single
testsuite or how it gets executed, but to the whole source directory.

This is not ideal, because we need to have additional code that ensures
these options have the same value across all testenv.cfg files in the
same source directory, and we need functions that just pick the value
from the first of these configs. When we change such a value, we also
need to potentially make the change in multiple files.

Resolve this by introducing a new config file testsrcdir.cfg, that can
be optionally in the source directory, and has options that count for
all testsuites in the same source directory.

Move max_jobs_per_gb_ram= as first option to the new file. The following
patches will move all other source directory specific options to
testsrcdir.cfg.

I have also considered naming the new file testdir.cfg, but the name
"testdir" is already used in the source code for the place where we
execute the individual testsuites after copying configs into that
directory.

Change-Id: I8eceea7b874ce1352e2cc9780b77d2a8e694cd28
Oliver Smith at

#28622 (Jun 3, 2026, 10:17:26 AM)

CCID: Check if parameters keep unchanged, if set without change.

Using SetParameters with the current set of parameter must not cause
them to change.

Change-Id: Id1bf5e58ba910d0633104b3bc3e902ce7d31cb10
jolly at

#28621 (Jun 3, 2026, 9:33:40 AM)

Add DSCP configuration support for each individual ASP

Introduce VTY command to configure the Differentiated Services Code
Point (DSCP) values for each Application Server Process.

If the ASP connection has the role "server", it will inherit the DSCP
settings of the listener, unless it is configured at the ASP connection.

Related: SYS#8071
Change-Id: Ia125a392eec5605553809774162675b5249b8494
Andreas Eversberg at

#28620 (Jun 3, 2026, 9:32:45 AM)

Add test case to verify proper DSCP settings

Related: SYS#8071
Change-Id: I6ac965998433b4d8213cce30fc3fcf8fe485a092
Andreas Eversberg at

#28619 (Jun 3, 2026, 9:32:42 AM)

Add DSCP configuration support for server transport role

Introduce VTY command to configure the Differentiated Services Code
Point (DSCP) values for transport "role" server.

The configured DSCP value is applied to the listener socket. Incoming
socket connections will then automatically inherit these DSCP settings
from the listener socket.

It is not (yet) possible to configure DSCP values for individual active
server connections. The setting applies globally via the listener.
A later patch will allow DSCP configuration of each individual ASP.

Related: SYS#8071
Depends: libosmo-netif.git Change-Id Ic70422ec73c753b61843444582f8665ca42e7a6d
Change-Id: I35eab3672157c318616f51ee3042243aed263d4e
Andreas Eversberg at

#28618 (Jun 2, 2026, 6:59:48 PM)

trx-usrp1: make single daughterboard VTY configurable

Adds the usrp1-singledb enable/disable option to specify the
daughterboard configuration on USRP1 devices. This will allow users
to use single-daughterboard devices without compliling from source to
use the --with-singledb configure option.
Also removed some daughterboard configuration related code that
wasn't being used.
More info in the modified trx-backends.adoc

Change-Id: I618fdcc7fec1ca1e87249992798c265430c177a0
jackleea1b at

#28617 (Jun 2, 2026, 11:58:26 AM)

Add test case to verify proper DSCP settings

Related: SYS#8071
Change-Id: I6ac965998433b4d8213cce30fc3fcf8fe485a092
Andreas Eversberg at

#28616 (Jun 2, 2026, 11:58:23 AM)

Add DSCP configuration support for each individual ASP

Introduce VTY command to configure the Differentiated Services Code
Point (DSCP) values for each Application Server Process.

If the ASP connection has the role "server", it will inherit the DSCP
settings of the listener, unless it is configured at the ASP connection.

Related: SYS#8071
Change-Id: Ia125a392eec5605553809774162675b5249b8494
Andreas Eversberg at

#28615 (Jun 2, 2026, 11:16:28 AM)

Add DSCP configuration support for each individual ASP

Introduce VTY command to configure the Differentiated Services Code
Point (DSCP) values for each Application Server Process.

If the ASP connection has the role "server", it will inherit the DSCP
settings of the listener, unless it is configured at the ASP connection.

Related: SYS#8071
Change-Id: Ia125a392eec5605553809774162675b5249b8494
Andreas Eversberg at

#28614 (Jun 2, 2026, 11:16:26 AM)

Add test case to verify proper DSCP settings

Related: SYS#8071
Change-Id: I6ac965998433b4d8213cce30fc3fcf8fe485a092
Andreas Eversberg at

#28613 (Jun 2, 2026, 11:15:48 AM)

Add DSCP configuration support for server transport role

Introduce VTY command to configure the Differentiated Services Code
Point (DSCP) values for transport "role" server.

The configured DSCP value is applied to the listener socket. Incoming
socket connections will then automatically inherit these DSCP settings
from the listener socket.

It is not (yet) possible to configure DSCP values for individual active
server connections. The setting applies globally via the listener.
A later patch will allow DSCP configuration of each individual ASP.

Related: SYS#8071
Depends: libosmo-netif.git Change-Id Ic70422ec73c753b61843444582f8665ca42e7a6d
Change-Id: I35eab3672157c318616f51ee3042243aed263d4e
Andreas Eversberg at

#28612 (Jun 2, 2026, 10:57:37 AM)

jobs/osmo-ccid-firmware: run hooks for logs

Run the start-hook.sh / stop-hook.sh scripts that store pcscd logs and a
usbmon capture. The jenkins node is configured to allow running these
two scripts with sudo as jenkins user. Store the resulting files as
artifacts.

Related: OS#8011
Change-Id: Id0d9a39fda24813572b979588c0ca22918829ad4
Oliver Smith at

#28611 (Jun 2, 2026, 10:57:32 AM)

jobs/octsim_osmo-ccid-firmware: add timeout arg

For testing the hook scripts (see next patch), it is useful to have a
shorter timeout for some test runs. Make it configurable.

Related: SYS#8011
Change-Id: I3bac142a9e2e5f144ad52ea7c36c05ffbad6f5d1
Oliver Smith at

#28610 (Jun 2, 2026, 9:55:52 AM)

tcap loadshare: move last_asp_idx_sent from cfg to runtime struct

The last_asp_idx_sent is a runtime information and not configurable.
Move it to the other runtime state.

Change-Id: Id52bb0f6c67949b5e03f7ad36996f37a0d25214a
lynxis at

#28609 (Jun 2, 2026, 9:55:49 AM)

vty-tests: Re-introduce the check on the help

With the support of regex within vty tests,
the help message can be checked again.

Depends-on: Iadcd7a8c3677548a6405e098fe53d0614ef2012c (osmo-python-tests)
Change-Id: I3fad268b7a8925f378f6331fcab073637bd80e08
lynxis at

#28608 (Jun 2, 2026, 9:54:50 AM)

tcap loadshare: allow to define the fallback mechanism for unroutable TCAP messages

When a TCAP Continue/End/Abort message is received, but no TCAP session entry can be found
and no valid TCAP range is available for the dtid, the message can be either:

- rejected by returning an error with udts
- routed by round robin to all available ASP of this AS

To define the behaviour, a new vty option is introduced:
```
   tcap-unroutable-sessions (reject-udts | load-share-over-as)
```
Defaults to reject-udts.

Related: SYS#5432
Change-Id: Ic1c876da30b05065a476d3a7c1bbf0680adf55bd
lynxis at

#28607 (Jun 2, 2026, 7:47:21 AM)

trx-usrp1: make single daughterboard VTY configurable

Adds the usrp1-singledb enable/disable option to specify the
daughterboard configuration on USRP1 devices. This will allow users
to use single-daughterboard devices without compliling from source to
use the --with-singledb configure option.
Also removed some daughterboard configuration related code that
wasn't being used.
More info in the modified trx-backends.adoc

Change-Id: I618fdcc7fec1ca1e87249992798c265430c177a0
jackleea1b at

#28606 (Jun 2, 2026, 7:33:36 AM)

trx-usrp1: make single daughterboard VTY configurable

Adds the usrp1-singledb enable/disable option to specify the
daughterboard configuration on USRP1 devices. This will allow users
to use single-daughterboard devices without compliling from source to
use the --with-singledb configure option.
Also removed some daughterboard configuration related code that
wasn't being used.
More info in the modified trx-backends.adoc

Change-Id: I618fdcc7fec1ca1e87249992798c265430c177a0
jackleea1b at

#28605 (Jun 1, 2026, 1:41:22 PM)

Also apply DSCP settings on listening socket

The TOS values should be packets that are sent during handshake.
Therefore the DSCP setting must be applied to the listening socket also.

Related: SYS#8071
Change-Id: Ic70422ec73c753b61843444582f8665ca42e7a6d
Andreas Eversberg at

#28604 (Jun 1, 2026, 1:29:59 PM)

Add test case to verify proper DSCP settings

Related: SYS#8071
Change-Id: I6ac965998433b4d8213cce30fc3fcf8fe485a092
Andreas Eversberg at

#28603 (Jun 1, 2026, 1:12:10 PM)

Add DSCP configuration support for STP client

Introduce VTY command to configure the Differentiated Services Code
Point (DSCP) values for the STP clients.

Related: SYS#8071
Change-Id: Ia125a392eec5605553809774162675b5249b8494
Andreas Eversberg at

#28602 (Jun 1, 2026, 1:11:31 PM)

Add test case to verify proper DSCP settings

Related: SYS#8071
Change-Id: I6ac965998433b4d8213cce30fc3fcf8fe485a092
Andreas Eversberg at

#28601 (Jun 1, 2026, 12:48:17 PM)

Add DSCP configuration support for STP client

Introduce VTY command to configure the Differentiated Services Code
Point (DSCP) values for the STP clients.

Related: SYS#8071
Change-Id: Ia125a392eec5605553809774162675b5249b8494
Andreas Eversberg at

#28600 (Jun 1, 2026, 12:48:15 PM)

Add test case to verify proper DSCP settings

Related: SYS#8071
Change-Id: I6ac965998433b4d8213cce30fc3fcf8fe485a092
Andreas Eversberg at

#28599 (Jun 1, 2026, 12:47:40 PM)

Add DSCP configuration support for STP server

Introduce VTY command to configure the Differentiated Services Code
Point (DSCP) values for the STP server.

Related: SYS#8071
Change-Id: I35eab3672157c318616f51ee3042243aed263d4e
Andreas Eversberg at

#28598 (Jun 1, 2026, 12:07:13 PM)

Add DSCP configuration support for STP client

Introduce VTY command to configure the Differentiated Services Code
Point (DSCP) values for the STP clients.

Related: SYS#8071
Change-Id: Ia125a392eec5605553809774162675b5249b8494
Andreas Eversberg at

#28597 (Jun 1, 2026, 12:07:10 PM)

Add DSCP configuration support for STP server

Introduce VTY command to configure the Differentiated Services Code
Point (DSCP) values for the STP server.

Related: SYS#8071
Change-Id: I35eab3672157c318616f51ee3042243aed263d4e
Andreas Eversberg at

#28596 (Jun 1, 2026, 12:06:33 PM)

Add test case to verify proper DSCP settings

Related: SYS#8071
Change-Id: I6ac965998433b4d8213cce30fc3fcf8fe485a092
Andreas Eversberg at