Attention is currently required from: laforge.
falconia has posted comments on this change by falconia. ( https://gerrit.osmocom.org/c/libosmo-abis/+/42680?usp=email )
Change subject: lapd_sap_stop(): fix use of uninitialized stack memory
......................................................................
Patch Set 1:
(1 comment)
Patchset:
PS1:
This patch now has two CR+1 votes from @vyanitskiy@sysmocom.de and @pespin@sysmocom.de, but a little over 48 h ago @pespin@sysmocom.de also requested review from @laforge@osmocom.org, who hasn't commented yet. I shall give it another couple of days, then do CR+2 to myself and merge.
--
To view, visit https://gerrit.osmocom.org/c/libosmo-abis/+/42680?usp=email
To unsubscribe, or for help writing mail filters, visit https://gerrit.osmocom.org/settings?usp=email
Gerrit-MessageType: comment
Gerrit-Project: libosmo-abis
Gerrit-Branch: master
Gerrit-Change-Id: Ic1469698ee8edf9b6fb55df8f79cc062be711f61
Gerrit-Change-Number: 42680
Gerrit-PatchSet: 1
Gerrit-Owner: falconia <falcon(a)freecalypso.org>
Gerrit-Reviewer: Jenkins Builder
Gerrit-Reviewer: fixeria <vyanitskiy(a)sysmocom.de>
Gerrit-Reviewer: laforge <laforge(a)osmocom.org>
Gerrit-Reviewer: pespin <pespin(a)sysmocom.de>
Gerrit-Attention: laforge <laforge(a)osmocom.org>
Gerrit-Comment-Date: Wed, 29 Apr 2026 19:42:24 +0000
Gerrit-HasComments: Yes
Gerrit-Has-Labels: No
laforge has submitted this change. ( https://gerrit.osmocom.org/c/pysim/+/42667?usp=email )
Change subject: pySim-prog/cards: fix programming of EF.SMSP
......................................................................
pySim-prog/cards: fix programming of EF.SMSP
The legacy code found in legacy/cards.py does not use the modern
construct based encoder (pySim-read uses it). The card classes either
use their own implementation of update_smsp or use the generic method
provided by the SimCard class. The latter one is true for FairwavesSIM
and WavemobileSim.
Unfortunately the implementation found in the SimCard is wrong. It
adds padding at the end of the file instead of the beginning. This
completely messes up the contents of EF.SMSP for the cards using this
method. To fix this, let's use the leftpad feature provided by
the update_record. This will ensure a correct alignment of the file
contents.
Related: SYS#7765
Change-Id: Ie112418f1f1461762d61365d3863181ca6be7245
---
M pySim/legacy/cards.py
M tests/pySim-prog_test/Fairwaves-SIM.ok
M tests/pySim-prog_test/Wavemobile-SIM.ok
3 files changed, 4 insertions(+), 3 deletions(-)
Approvals:
Jenkins Builder: Verified
laforge: Looks good to me, approved
diff --git a/pySim/legacy/cards.py b/pySim/legacy/cards.py
index 9efa66b..3b66328 100644
--- a/pySim/legacy/cards.py
+++ b/pySim/legacy/cards.py
@@ -152,7 +152,8 @@
return sw
def update_smsp(self, smsp):
- data, sw = self._scc.update_record(EF['SMSP'], 1, rpad(smsp, 84))
+ print("using update_smsp")
+ data, sw = self._scc.update_record(EF['SMSP'], 1, smsp, leftpad=True)
return sw
def update_ad(self, mnc=None, opmode=None, ofm=None, path=EF['AD']):
diff --git a/tests/pySim-prog_test/Fairwaves-SIM.ok b/tests/pySim-prog_test/Fairwaves-SIM.ok
index 42e92e8..5210d01 100644
--- a/tests/pySim-prog_test/Fairwaves-SIM.ok
+++ b/tests/pySim-prog_test/Fairwaves-SIM.ok
@@ -5,7 +5,7 @@
IMSI: 001010000000111
GID1: ffffffffffffffff
GID2: ffffffffffffffff
-SMSP: e1ffffffffffffffffffffffff0581005155f5ffffffffffff000000ffffffffffffffffffffffffffff
+SMSP: ffffffffffffffffffffffffffffe1ffffffffffffffffffffffff0581005155f5ffffffffffff000000
SMSC: 0015555
SPN: Fairwaves
Show in HPLMN: False
diff --git a/tests/pySim-prog_test/Wavemobile-SIM.ok b/tests/pySim-prog_test/Wavemobile-SIM.ok
index 86f4830..3d9e9b3 100644
--- a/tests/pySim-prog_test/Wavemobile-SIM.ok
+++ b/tests/pySim-prog_test/Wavemobile-SIM.ok
@@ -5,7 +5,7 @@
IMSI: 001010000000102
GID1: Can't read file -- SW match failed! Expected 9000 and got 6a82.
GID2: Can't read file -- SW match failed! Expected 9000 and got 6a82.
-SMSP: e1ffffffffffffffffffffffff0581005155f5ffffffffffff000000ffffffffffffffffffffffffffff
+SMSP: ffffffffffffffffffffffffffffe1ffffffffffffffffffffffff0581005155f5ffffffffffff000000
SMSC: 0015555
SPN: wavemobile
Show in HPLMN: False
--
To view, visit https://gerrit.osmocom.org/c/pysim/+/42667?usp=email
To unsubscribe, or for help writing mail filters, visit https://gerrit.osmocom.org/settings?usp=email
Gerrit-MessageType: merged
Gerrit-Project: pysim
Gerrit-Branch: master
Gerrit-Change-Id: Ie112418f1f1461762d61365d3863181ca6be7245
Gerrit-Change-Number: 42667
Gerrit-PatchSet: 5
Gerrit-Owner: dexter <pmaier(a)sysmocom.de>
Gerrit-Reviewer: Jenkins Builder
Gerrit-Reviewer: fixeria <vyanitskiy(a)sysmocom.de>
Gerrit-Reviewer: laforge <laforge(a)osmocom.org>
Gerrit-Reviewer: neels <nhofmeyr(a)sysmocom.de>
laforge has submitted this change. ( https://gerrit.osmocom.org/c/pysim/+/42662?usp=email )
Change subject: ts_51_011/EF.SMSP: fix handling of 'alpha_id' field
......................................................................
ts_51_011/EF.SMSP: fix handling of 'alpha_id' field
The field 'alpha_id' is technically not an optional field, even though
the specification describes it as optional. Once the card manufacturer
decides that the field should be present, it must be always present and
vice versa.
(see code comment for a more detailed description)
Related: SYS#7765
Change-Id: I0ec99b2648b22c56f9145345e4cd8776f9217701
---
M pySim/ts_51_011.py
1 file changed, 31 insertions(+), 1 deletion(-)
Approvals:
laforge: Looks good to me, approved
Jenkins Builder: Verified
diff --git a/pySim/ts_51_011.py b/pySim/ts_51_011.py
index 0dbf6eb..89ff824 100644
--- a/pySim/ts_51_011.py
+++ b/pySim/ts_51_011.py
@@ -251,6 +251,16 @@
"numbering_plan_id": "isdn_e164" },
"call_number": "4915790109999" },
"tp_pid": b"\x00", "tp_dcs": b"\x00", "tp_vp_minutes": 4320 } ),
+ ( 'e1ffffffffffffffffffffffff0891945197109099f9ffffff0000a9',
+ { "alpha_id": "", "parameter_indicators": { "tp_dest_addr": False, "tp_sc_addr": True,
+ "tp_pid": True, "tp_dcs": True, "tp_vp": True },
+ "tp_dest_addr": { "length": 255, "ton_npi": { "ext": True, "type_of_number": "reserved_for_extension",
+ "numbering_plan_id": "reserved_for_extension" },
+ "call_number": "" },
+ "tp_sc_addr": { "length": 8, "ton_npi": { "ext": True, "type_of_number": "international",
+ "numbering_plan_id": "isdn_e164" },
+ "call_number": "4915790109999" },
+ "tp_pid": b"\x00", "tp_dcs": b"\x00", "tp_vp_minutes": 4320 } ),
( '454e6574776f726b73fffffffffffffff1ffffffffffffffffffffffffffffffffffffffffffffffff0000a7',
{ "alpha_id": "ENetworks", "parameter_indicators": { "tp_dest_addr": False, "tp_sc_addr": True,
"tp_pid": True, "tp_dcs": True, "tp_vp": False },
@@ -331,7 +341,8 @@
'ton_npi'/TonNpi, 'call_number'/PaddedBcdAdapter(Rpad(Bytes(10))))
DestAddr = Struct('length'/Rebuild(Int8ub, lambda ctx: EF_SMSP.dest_addr_len(ctx)),
'ton_npi'/TonNpi, 'call_number'/PaddedBcdAdapter(Rpad(Bytes(10))))
- self._construct = Struct('alpha_id'/COptional(GsmOrUcs2Adapter(Rpad(Bytes(this._.total_len-28)))),
+ # (see comment below)
+ self._construct = Struct('alpha_id'/GsmOrUcs2Adapter(Rpad(Bytes(this._.total_len-28))),
'parameter_indicators'/InvertAdapter(BitStruct(
Const(7, BitsInteger(3)),
'tp_vp'/Flag,
@@ -345,6 +356,25 @@
'tp_dcs'/Bytes(1),
'tp_vp_minutes'/EF_SMSP.ValidityPeriodAdapter(Byte))
+ # Ensure 'alpha_id' is always present
+ def encode_record_hex(self, abstract_data: dict, record_nr: int, total_len: int = None) -> str:
+ # Problem: TS 51.011 Section 10.5.6 describes the 'alpha_id' field as optional. However, this is only true
+ # at the time when the record length of the file is set up in the file system. A card manufacturer may decide
+ # to remove the field by setting the record length to 28. Likewise, the card manaufacturer may also decide to
+ # set the field to a distinct length by setting the record length to a value greater than 28 (e.g. 14 bytes
+ # 'alpha_id' + 28 bytes). Due to the fixed nature of the record length, this eventually means that in practice
+ # 'alpha_id' is a mandatory field with a fixed length.
+ #
+ # Due to the problematic specification of 'alpha_id' as a pseudo-optional field at the beginning of a
+ # fixed-size memory, the construct definition in self._construct has been incorrectly implemented and the field
+ # has been marked as COptional. We may correct the problem by removing COptional. But to maintain compatibility,
+ # we then have to ensure that in case the field is not provided (None), it is set to an empty string ('').
+ #
+ # See also ts_31_102.py, class EF_OCI for a correct example.
+ if abstract_data['alpha_id'] is None:
+ abstract_data['alpha_id'] = ''
+ return super().encode_record_hex(abstract_data, record_nr, total_len)
+
# TS 51.011 Section 10.5.7
class EF_SMSS(TransparentEF):
class MemCapAdapter(Adapter):
--
To view, visit https://gerrit.osmocom.org/c/pysim/+/42662?usp=email
To unsubscribe, or for help writing mail filters, visit https://gerrit.osmocom.org/settings?usp=email
Gerrit-MessageType: merged
Gerrit-Project: pysim
Gerrit-Branch: master
Gerrit-Change-Id: I0ec99b2648b22c56f9145345e4cd8776f9217701
Gerrit-Change-Number: 42662
Gerrit-PatchSet: 7
Gerrit-Owner: dexter <pmaier(a)sysmocom.de>
Gerrit-Reviewer: Jenkins Builder
Gerrit-Reviewer: fixeria <vyanitskiy(a)sysmocom.de>
Gerrit-Reviewer: laforge <laforge(a)osmocom.org>
Gerrit-Reviewer: lynxis lazus <lynxis(a)fe80.eu>
Gerrit-Reviewer: neels <nhofmeyr(a)sysmocom.de>
Attention is currently required from: fixeria, neels.
laforge has posted comments on this change by neels. ( https://gerrit.osmocom.org/c/pysim/+/42155?usp=email )
Change subject: esim/http_json_api.py: support text/plain response Content-Type
......................................................................
Patch Set 2:
(1 comment)
Patchset:
PS2:
> I would argue that we should not change the default of this code intended for ES2+ and ES9+ (where e […]
Or optionally, When instantiating the object there could be a parameter modifying the behaviour, so we don't clutter every call to call() ?
--
To view, visit https://gerrit.osmocom.org/c/pysim/+/42155?usp=email
To unsubscribe, or for help writing mail filters, visit https://gerrit.osmocom.org/settings?usp=email
Gerrit-MessageType: comment
Gerrit-Project: pysim
Gerrit-Branch: master
Gerrit-Change-Id: Iba6e4cef1048b376050a435a900c0f395655a790
Gerrit-Change-Number: 42155
Gerrit-PatchSet: 2
Gerrit-Owner: neels <nhofmeyr(a)sysmocom.de>
Gerrit-Reviewer: Jenkins Builder
Gerrit-Reviewer: laforge <laforge(a)osmocom.org>
Gerrit-Attention: neels <nhofmeyr(a)sysmocom.de>
Gerrit-Attention: fixeria <vyanitskiy(a)sysmocom.de>
Gerrit-Comment-Date: Wed, 29 Apr 2026 19:38:10 +0000
Gerrit-HasComments: Yes
Gerrit-Has-Labels: No
Comment-In-Reply-To: laforge <laforge(a)osmocom.org>
Attention is currently required from: fixeria, neels.
laforge has posted comments on this change by neels. ( https://gerrit.osmocom.org/c/pysim/+/42155?usp=email )
Change subject: esim/http_json_api.py: support text/plain response Content-Type
......................................................................
Patch Set 2:
(1 comment)
Patchset:
PS2:
I would argue that we should not change the default of this code intended for ES2+ and ES9+ (where enforcing JSON makes sense). Can't we just have some optional kwarg where the caller of the call() method can enable non-JSON?
--
To view, visit https://gerrit.osmocom.org/c/pysim/+/42155?usp=email
To unsubscribe, or for help writing mail filters, visit https://gerrit.osmocom.org/settings?usp=email
Gerrit-MessageType: comment
Gerrit-Project: pysim
Gerrit-Branch: master
Gerrit-Change-Id: Iba6e4cef1048b376050a435a900c0f395655a790
Gerrit-Change-Number: 42155
Gerrit-PatchSet: 2
Gerrit-Owner: neels <nhofmeyr(a)sysmocom.de>
Gerrit-Reviewer: Jenkins Builder
Gerrit-Reviewer: laforge <laforge(a)osmocom.org>
Gerrit-Attention: neels <nhofmeyr(a)sysmocom.de>
Gerrit-Attention: fixeria <vyanitskiy(a)sysmocom.de>
Gerrit-Comment-Date: Wed, 29 Apr 2026 19:37:24 +0000
Gerrit-HasComments: Yes
Gerrit-Has-Labels: No
laforge has submitted this change. ( https://gerrit.osmocom.org/c/pysim/+/42301?usp=email )
Change subject: pySim/transport: fix GET RESPONSE behaviour
......................................................................
pySim/transport: fix GET RESPONSE behaviour
The current behavior we implement in the method __send_apdu_T0 is
incomplete. Some details discussed in ETSI TS 102 221,
section 7.3.1.1.4, clause 4 seem to be not fully implemented. We
may also end up sending a GET RESPONSE in other APDU cases than
case 4 (the only case that uses the GET RESPONSE command).
Related: OS#6970
Change-Id: I26f0566af0cdd61dcc97f5f502479dc76adc37cc
---
M pySim/transport/__init__.py
M tests/pySim-shell_test/apdu/test_apdu.script
2 files changed, 60 insertions(+), 16 deletions(-)
Approvals:
laforge: Looks good to me, approved
fixeria: Looks good to me, but someone else must approve
Jenkins Builder: Verified
diff --git a/pySim/transport/__init__.py b/pySim/transport/__init__.py
index 6833a90..d689a0a 100644
--- a/pySim/transport/__init__.py
+++ b/pySim/transport/__init__.py
@@ -301,24 +301,54 @@
prev_tpdu = tpdu
data, sw = self.send_tpdu(tpdu)
+ log.debug("T0: case #%u TPDU: %s => %s %s", case, tpdu, data or "(no data)", sw or "(no status word)")
+ if sw is None:
+ raise ValueError("no status word received")
- # When we have sent the first APDU, the SW may indicate that there are response bytes
- # available. There are two SWs commonly used for this 9fxx (sim) and 61xx (usim), where
- # xx is the number of response bytes available.
- # See also:
- if sw is not None:
- while (sw[0:2] in ['9f', '61', '62', '63']):
- # SW1=9F: 3GPP TS 51.011 9.4.1, Responses to commands which are correctly executed
- # SW1=61: ISO/IEC 7816-4, Table 5 — General meaning of the interindustry values of SW1-SW2
- # SW1=62: ETSI TS 102 221 7.3.1.1.4 Clause 4b): 62xx, 63xx, 9xxx != 9000
- tpdu_gr = tpdu[0:2] + 'c00000' + sw[2:4]
+ # After sending the APDU/TPDU the UICC/eUICC or SIM may response with a status word that indicates that further
+ # TPDUs have to be sent in order to complete the task.
+ if case == 4 or self.apdu_strict == False:
+ # In case the APDU is a case #4 APDU, the UICC/eUICC/SIM may indicate that there is response data
+ # available which has to be retrieved using a GET RESPONSE command TPDU.
+ #
+ # ETSI TS 102 221, section 7.3.1.1.4 is very cleare about the fact that the GET RESPONSE mechanism
+ # shall only apply on case #4 APDUs but unfortunately it is impossible to distinguish between case #3
+ # and case #4 when the APDU format is not strictly followed. In order to be able to detect case #4
+ # correctly the Le byte (usually 0x00) must be present, is often forgotten. To avoid problems with
+ # legacy scripts that use raw APDU strings, we will still loosely apply GET RESPONSE based on what
+ # the status word indicates. Unless the user explicitly enables the strict mode (set apdu_strict true)
+ while True:
+ if sw in ['9000', '9100']:
+ # A status word of 9000 (or 9100 in case there is pending data from a proactive SIM command)
+ # indicates that either no response data was returnd or all response data has been retrieved
+ # successfully. We may discontinue the processing at this point.
+ break;
+ if sw[0:2] in ['61', '9f']:
+ # A status word of 61xx or 9fxx indicates that there is (still) response data available. We
+ # send a GET RESPONSE command with the length value indicated in the second byte of the status
+ # word. (see also ETSI TS 102 221, section 7.3.1.1.4, clause 4a and 3GPP TS 51.011 9.4.1 and
+ # ISO/IEC 7816-4, Table 5)
+ le_gr = sw[2:4]
+ elif sw[0:2] in ['62', '63']:
+ # There are corner cases (status word is 62xx or 63xx) where the UICC/eUICC/SIM asks us
+ # to send a dummy GET RESPONSE command. We send a GET RESPONSE command with a length of 0.
+ # (see also ETSI TS 102 221, section 7.3.1.1.4, clause 4b and ETSI TS 151 011, section 9.4.1)
+ le_gr = '00'
+ else:
+ # A status word other then the ones covered by the above logic may indicate an error. In this
+ # case we will discontinue the processing as well.
+ # (see also ETSI TS 102 221, section 7.3.1.1.4, clause 4c)
+ break
+ tpdu_gr = tpdu[0:2] + 'c00000' + le_gr
prev_tpdu = tpdu_gr
- d, sw = self.send_tpdu(tpdu_gr)
- data += d
- if sw[0:2] == '6c':
- # SW1=6C: ETSI TS 102 221 Table 7.1: Procedure byte coding
- tpdu_gr = prev_tpdu[0:8] + sw[2:4]
- data, sw = self.send_tpdu(tpdu_gr)
+ data_gr, sw = self.send_tpdu(tpdu_gr)
+ log.debug("T0: GET RESPONSE TPDU: %s => %s %s", tpdu_gr, data_gr or "(no data)", sw or "(no status word)")
+ data += data_gr
+ if sw[0:2] == '6c':
+ # SW1=6C: ETSI TS 102 221 Table 7.1: Procedure byte coding
+ tpdu_gr = prev_tpdu[0:8] + sw[2:4]
+ data, sw = self.send_tpdu(tpdu_gr)
+ log.debug("T0: repated case #%u TPDU: %s => %s %s", case, tpdu_gr, data or "(no data)", sw or "(no status word)")
return data, sw
diff --git a/tests/pySim-shell_test/apdu/test_apdu.script b/tests/pySim-shell_test/apdu/test_apdu.script
index a949b2d..2531987 100644
--- a/tests/pySim-shell_test/apdu/test_apdu.script
+++ b/tests/pySim-shell_test/apdu/test_apdu.script
@@ -7,10 +7,24 @@
# No command data field, No response data field present
apdu 00700001 --expect-sw 9000 --expect-response-regex '^$'
+# Case #1: (verify pin)
+# This command returns the number of remaining authentication attempts in the
+# form of a status that has the form 63cX, where X is the number of remaining
+# attempts. Such a status word can be easily confused with the response to a
+# case #4 APDU. This test checks if the transport layer correctly distinguishes
+# the between APDU case #1 and APDU case #4.
+apdu 0020000A --expect-sw 63c? --expect-response-regex '^$'
+
# Case #2: (status)
# No command data field, Response data field present
apdu 80F2000000 --expect-sw 9000 --expect-response-regex '^[a-fA-F0-9]+$'
+# Case #2: (verify pin)
+# (see also above). This test checks if the transport layer is also able to
+# distinguish correctly between APDU case #2 (with zero length response) and
+# APDU case #4.
+apdu 0020000A00 --expect-sw 63c? --expect-response-regex '^$'
+
# Case #3: (terminal capability)
# Command data field present, No response data field
apdu 80AA000005a903830180 --expect-sw 9000 --expect-response-regex '^$'
--
To view, visit https://gerrit.osmocom.org/c/pysim/+/42301?usp=email
To unsubscribe, or for help writing mail filters, visit https://gerrit.osmocom.org/settings?usp=email
Gerrit-MessageType: merged
Gerrit-Project: pysim
Gerrit-Branch: master
Gerrit-Change-Id: I26f0566af0cdd61dcc97f5f502479dc76adc37cc
Gerrit-Change-Number: 42301
Gerrit-PatchSet: 9
Gerrit-Owner: dexter <pmaier(a)sysmocom.de>
Gerrit-Reviewer: Jenkins Builder
Gerrit-Reviewer: fixeria <vyanitskiy(a)sysmocom.de>
Gerrit-Reviewer: laforge <laforge(a)osmocom.org>