#!/usr/bin/env python3 # (C) 2023-2024 by Harald Welte # # This program is free software: you can redistribute it and/or modify # it under the terms of the GNU General Public License as published by # the Free Software Foundation, either version 2 of the License, or # (at your option) any later version. # # This program is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the # GNU General Public License for more details. # # You should have received a copy of the GNU General Public License # along with this program. If not, see . import unittest import logging import base64 from osmocom.utils import b2h, h2b from pySim.esim.bsp import * import pySim.esim.rsp as rsp class BSP_Test(unittest.TestCase): shared_secret = h2b('8902dca391bbb22570fe60c176076246f568b1941265dff1d729e63039658089') eid_bin = h2b('89049032123451234512345678901335') def test_kdf(self): s_enc, s_mac, icv = bsp_key_derivation(self.shared_secret, 0x88, 16, b'\x80'*8, self.eid_bin) self.assertEqual(s_enc, h2b('d782d575b22a38334556a3d9a1e2ae6b')) self.assertEqual(s_mac, h2b('a35addc192ae8f934e2932116c7e89e7')) self.assertEqual(icv, h2b('734bc93ddb10c71c5ad13d420dc08b5b')) class BSP_Test_mode51(unittest.TestCase): """This test was created using hex-dumps from a log/trace of a 3rd party SM-DP+. We therefore use these test vectors to verify our implementation is in agreement with that other implementation.""" shared_secret = h2b('c9a993dd4879a8f7161f2085410edd4f9652f1df37be097ba96ba2ca6be528fe') eid_bin = h2b('89049032123451234512345678901235') def test_kdf(self): s_enc, s_mac, icv = bsp_key_derivation(self.shared_secret, 0x88, 16, b'\x80'*8, self.eid_bin) self.assertEqual(s_enc, h2b('472f5bfadd97f21d34f3ce9b51b92751')) self.assertEqual(s_mac, h2b('9ec07f5b36a13e12a991d66e294e6242')) self.assertEqual(icv, h2b('406d507b448a699e7a36a38494debbde')) def test_ciphering(self): bi = BspInstance(h2b('472f5bfadd97f21d34f3ce9b51b92751'), h2b('9ec07f5b36a13e12a991d66e294e6242'), h2b('406d507b448a699e7a36a38494debbde')) output = bi.encrypt_and_mac(0x87, h2b('bf2400')) self.assertEqual(output[0], h2b('8718f6fe031e4b9cfe87c8e1e62f3fde85c49412d7722a6a2d89')) output = bi.mac_only(0x88, h2b('bf252d5a0a98001032547698103214910947534d415f54455354921147534d415f544553545f50524f46494c45950100')) self.assertEqual(output[0], h2b('8838bf252d5a0a98001032547698103214910947534d415f54455354921147534d415f544553545f50524f46494c459501008a62cc9adbb5ccbc')) output = bi.encrypt_and_mac(0x87, h2b('bf26368010000102030405060708090a0b0c0d0e0f8110010102030405060708090a0b0c0d0e0f8210020102030405060708090a0b0c0d0e0f')) self.assertEqual(output[0], h2b('8748a14c800a001992351cd46ad2945654674369701d82b7b46567652bc8fbed234939fc57fba748015525fd6c651e9d3d1330652d42a0cfad950e912122af4ec5362d3c0bc535729c40')) # new key material after replaceSessionKeys bi = BspInstance(b'\x01\x01\x02\x03\x04\x05\x06\x07\x08\t\n\x0b\x0c\r\x0e\x0f', b'\x02\x01\x02\x03\x04\x05\x06\x07\x08\t\n\x0b\x0c\r\x0e\x0f', b'\x00\x01\x02\x03\x04\x05\x06\x07\x08\t\n\x0b\x0c\r\x0e\x0f') segment0 = h2b('a048800102810101821a53494d616c6c69616e63652053616d706c652050726f66696c65830a89000123456789012341a506810084008b00a610060667810f010201060667810f010204b08201f8a0058000810101810667810f010201a207a105c60301020aa305a1038b010fa40c830a98001032547698103214a527a109820442210026800198831a61184f10a0000000871002ff33ff01890000010050045553494da682019ea10a8204422100258002022b831b8001019000800102a406830101950108800158a40683010a95010882010a8316800101a40683010195010880015aa40683010a95010882010f830b80015ba40683010a95010882011a830a800101900080015a970082011b8316800103a406830101950108800158a40683010a95010882010f8316800111a40683010195010880014aa40683010a95010882010f8321800103a406830101950108800158a40683010a950108840132a4068301019501088201048321800101a406830101950108800102a406830181950108800158a40683010a950108820104831b800101900080011aa406830101950108800140a40683010a95010882010a8310800101900080015aa40683010a95010882011583158001019000800118a40683010a95010880014297008201108310800101a40683010195010880015a97008201158316800113a406830101950108800148a40683010a95010882010f830b80015ea40683010a95010882011a83258001019000800102a010a406830101950108a406830102950108800158a40683010a950108a33fa0058000810102a13630118001018108303030303030303082020099300d800102810831323334353637383012800200818108313233343536373882020088a241a0058000810103a138a0363010800101810831323334ffffffff8201013010800102810830303030ffffffff820102301080010a810835363738ffffffff830101a182029ea0058000810104a18202933082028f62228202782183027ff18410a0000000871002ff33ff0189000001008b010ac60301810a62118202412183026f078b01028001098801388109082943019134876765621482044221002583026f068b010a8801b8c7022f06621a8202412183026f088b0105800121880140a507c00180c10207ff621a8202412183026f098b0105800121880148a507c00180c10207ff62168202412183026f318b0102800101880190a503c1010a62118202412183026f388b010280010e880120810d0a2e178ce73204000000000000621982044221001a83026f3b8b0108800202088800a504c10200ff62198204422100b083026f3c8b0105800206e08800a504c10200ff621282044221002683026f428b0105800126') output = bi.encrypt_and_mac_one(0x86, segment0) self.assertEqual(output, h2b('868203f80fd36b066b43e53906b33263c4141d18036fcac7bde47faed79e76514d39f1f405d9785ff04badf379a96bcf4685eb861239da34eeb213d0cd1e0d85e96e36097a52f600907e08b6f01232eb3792a00cc6b3288cc832c7f30357edfe0818d1f39ad8d55b5bd5d9c65917d0d16ee7e1421a44453714d66209bf441425bf6d153a85ba7e7406d58a4c46fb930bb14eefd6a853434619805429cbbb003bd5a56e7bceaf4666eb352ad46f47ea572c6ad311683803db3bec4d783583858f2ecfbaec3ed780fb3e3a645b1bf5cfd1047e5862c4a8877382dabd6aef6fa72ec6378ce7b21502d3267514b29bd589703ee7bd5b1e6d868b6b7c55006bc32406a924f44bfdb6c801d490450a54633bbd66bb0ece8b3a9be09433c537f3e3b2b8e45833365a94479b1895e9ba13387fca116565c267b6bc1274c82510b21ac9fa77574412351468fd1eac8928c9494e5eb8a909d9372476c62e8a2b556b557a79cdb47503ba5d9fd86d1962c23b3289f37df9a05668957df34c37806359af1d8dfecedf9bbf4888be9753f2b449ce4e5cde510572f9be4fb506f329a848c4583ac9ac710e53d512ad504f2e3769c2911c34f84ad0622c5428446d1e9c59bb6b2029f231b05ef45d3ec60fceff121ba684a023037b753f855e1067b8ad02783c04eb81ba47fcec0947bbc9661d90c6f00c0f4e6f9c22e0b25905379f8b265b436a4a74253a64c5734f956d134cf5b6c0671125b20b735f405fee1fc1941ed141734fa6856e898dc655fb91b045b3797d14b97a68ed3480ec137565d6c4d007f95ee705d452d0344ce9e9bbd0712f399ef8604f3f472b403ea64f00c969fd30a012cb8be049c54556994117fc5f6043930107774910be5f47c780427de063a56d45400a814c86dfcc2465262baf273a6ca89e77bb8c73efe2d22d975516b80c648404b10d3f329776a21251bedf445ade24b656e8635f0d7fe39772d942d9432766efb5152c6e990123c52744f1c402962a381ff2aaddaa1bd522a9b65a229f9adcd4099475b3f9ba45161ee35206365181e1d69d263d8d27444a7c3a2d7ddbb398ac5affea28cb0373057dad7741e52adb95822fee5157ce3c0ad978c5231a219ca0726d50eeb0c69d579094a54820194aeef13a365d85c52257f51cb65c567e0cdf1ce38b80eaa4d131ab7086e303c5728cf41a25df954d60ac12400d2a2990e67dbeff866736937beb8fce526be1dd5dc5d77d00b8783b34691a3e9bda7e697eec4cfa70b25914795af23ec6d258530f71402b9230947dc99f9140b16a54ba1291f54ef736de6711c1ae074b627dfc2fc5d5250f812b7ecd1d0f5020a3acf20ad5759cd9e761ce21882977f7db66aaba2d8f5190f6f23996af14b670ccac066c93af06a41f19d9ee712ce13fbe73b99e55401b208b991c8ced12d34c')) segment1 = h2b('880062158202412183026f438b01058001028800a503c0018062128202412183026f468b036f060a8001118800810c0253494d616c6c69616e636562118202412183026f568b0108800101880128810100621b8202412183026f5b8b0105800106880178a508c00180c203f0000062168202412183026f5c8b0102800103880180a503c0018062168202412183026f738b010580010e880160a503c00180020107810700f1100000ff0162118202412183026f788b01028001028801308102004062118202412183026f7b8b010580010c88016862168202412183026f7e8b010580010b880158a503c0018002010781040000ff0162168202412183026fad8b010a800104880118a503c10100020103810102621382044221000483026fb78b010a800104880108810419f1ff0162158202412183026fc48b01058001808800a503c0018062168202412183026fe38b01058001128801f0a503c0018002010f810300000162168202412183026fe48b01058001508801c0a503c00180a225a0058000810105a11ca01a301880020081810831323334ffffffff82020081830101840122a43aa0058000810106a131a12f8001018101018210000102030405060708090a0b0c0d0e0f83100102030405060708090a0b0c0d0e0f008603010203a681bba0058000810107a1444f07a00000015153504f08a0000001515350414f08a000000151000000820382dc0083010fc90a810280008201f08701f0ea11800f0100000100000002011203b2010000a26c3022950138820101830101301730158001808610112233445566778899aabbccddeeff103022950134820102830101301730158001808610112233445566778899aabbccddeeff1030229501c8820103830101301730158001808610112233445566778899aabbccddeeff10a681c0a0058000810108a1494f07a00000015153504f08a0000001515350414f10a00000055910100102736456616c7565820380800083010fc907810280008201f0ea11800f01000001000000020112036c756500a26c30229501388201018301013017301580018086108811223344556677881122334455667730229501348201028301013017301580018086108811223344556677881122334455667730229501c882010383010130173015800180861088112233445566778811223344556677a8820263a0058000810109a18202184f08a000000559101001c482020a01002edecaffed020204000108a0000005591010011b636f6d2f67736d612f65756963632f746573742f6170706c657431020021002e0021000f003b002a00210066000a000e0000008a040f00000000000004010004003b04030107a0000000620101000110a0000000090005ffffffff') output = bi.encrypt_and_mac_one(0x86, segment1) self.assertEqual(output, h2b('868203f8648e034ae0dc4ce022ee1e60b130dda95e13b21b0da3de7677677f47900c1beb3637b8aa35f3a9e096c0285ffe3e931983df900b36b7e6bc4b9af14b0ee3d49637eb2d4cff314b5d00789a751dfd9554651fb2b7c66ad4e22a794d5b88cb71ccf4c05d53abeba8bd3b0c8209346f014cbdee62be4878e3fea09a96007135a6c584aa843c48972842bdbece1c439723021b3f0d535d557995beedbd2b56f416148df90cb1a4d2fa26288801d56a2cbb0a404f2fd9a73042d7a3486bfb7256c1d274aae5b7ec24e8eba28b7dce69edc44189b24186b98397b4a74831f8ab46e8e46a2ed3077d4924f5d3f6e4c1de5ddffd194e7f0f97d94ea2801d1364835c9871bae6539e3e1355c5970711d845864f04d9c1dccac0d4068dcf4664e9976509fe43fec6beb3ddc96839aba6d89bb1593c5b6ebbc32fff39c4a5bb3e5c9df6a1abc05818dbd5149733381e69521066e1bbd648eb19b00602767e90beaeb3b3b92679940a603c0500e37892d7b4fa44355c3deec8af207f89d04f83cd88603e9cb9c96f74643816e87af85a8a9d0283cdf535d1fbaefb930fd4a0dba2ae30ee9d2d9e2a31827a012a6380af42ac87f3bfd7079ddd8fa27d2299fb4d5879e9a17a5062e13cab4f7bed22ed54932fa53d630bca8592f957a7ed148e9d4f28075c2565a550694b876091a1181ba512e70fde4f28ae6968a18d721396c0fee9cd7744dee90bf85f5adddb3417b3ede9ea3cfd5eae2d820b17600ce3b95f6df38a5bc39302c5155c3f241ddfc7cee527af7f6a67868a577c39e76e26c4ed5d6aca031a97c280da27ae8de20e57a1dbab40a31e96e054f9a6f50578fd00156e37b70eead71af3258075c1ba84282aea462553504a868443b301ed99dcd5f414b720ef67cf5c4d16f1f7b9df741c2343246dcb717f3fa62b633539bdcc0082d161499caad8d097be78133dafd19777559f77c6d7a8f61323ff660613aa47cee26a4f7515204eee3c7eaa00eb55529b0ddae3436ec679fc591fe2063de94db00b5d0f041beeb80a91f108f7cf4b3b1344b0fbb437630ee437b4c7744c54009a59a9099681f3a3fa386f294c0eb4562581202a369772833efdc6e840695352de3864671e7fb0fd081ec162a2a62ea5b8a9da837f3920b4196fbe2ec912ade440537ae4a07dfc115c9c030539f278e0801bda4f15298ba50e329b18992af8b899686ec97175509d4a217d2eba8feef5f5732fc7be86370f7723896b784bd45517af86a7521e952b6be924d91a5190e3c2c65ce8924df43ddb25c529dde324a722a156df459f4b38bb062975fad9fadd27f6425e422b1abd9a7259f0bd712a486e1aa25ca848cf65c5fb888bf61ae136b68cf55cb643c198537cd83df0dbb842c5f4982ca3088cc2d8e867c3049a84b515ec39b0b774a8482099327006acff')) class TestBSPdecode(unittest.TestCase): """This test verifies whether some fully encoded/encrypted/MACed bound profile package can be properly decrypted and verified using our BSP code base.""" bpp_b64 = "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" def test_decrypt_and_mac_verify(self): bpp_bin = base64.b64decode(self.bpp_b64) iscr = rsp.asn1.decode('BoundProfilePackage', bpp_bin) # BSP segment for ConfigureISDP using S-ENC/S-MAC bsp = BspInstance(h2b('f11b921c302efb1df6bf218bf2de0dd8'), h2b('8cd4d3a761eeac108641d5f4531a137e'), h2b('ee3140eafd692b68eff40119b363bc6c')) plain_cfg_isdp = bsp.demac_and_decrypt(iscr['firstSequenceOf87']) self.assertEqual(plain_cfg_isdp, h2b('bf2400')) # BSP segment for StoreMetadata using /S-MAC plain_smd = bsp.demac_only(iscr['sequenceOf88']) self.assertEqual(plain_smd, h2b('bf25285a0a89000123456789012341910a4f736d6f636f6d53504e920e4f736d6f636f6d50726f66696c65')) # BSP payload using PPK-ENC/PPK-MAC bsp_ppk = BspInstance(h2b('00000000000000000000000000000000'), h2b('11111111111111111111111111111111'), h2b('22222222222222222222222222222222')) plain_upp = bsp_ppk.demac_and_decrypt(iscr['sequenceOf86']) original_upp = b'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wLSCCiugBYAAgQEJgQZngQ8BAgWiEaEPggJBIYMCbwWLA28GBaUAoxmhF4ICQSGDAm83iwNvBgmIAKUGwAFAwgEApB+hHYIERiEAA4MCbzmLA28GC4ABD4gB4KUGwAGAwgEApRqhFIICQSGDAm8+iwNvBgSAAQKIAKUAgwL//6YaoRSCAkEhgwJvP4sDbwYEgAECiAClAIMC//+nGKEWggRCIQAcgwJvQIsDbwYEgAE4iAClAKgaoRGCAkEhgwJvQYsDbwYBiAClAIMF////AACpFqEUggJBIYMCb0WLA28GAoABCIgApQCqFKESggJBIYMCb0iLA28GBIABCKUAqxihFoIEQiEAHIMCb0mLA28GCoABjIgApQCsHKEaggRCIQANgwJvS4sDbwYBgAFBiAClBMECAP+tHKEaggRCIQANgwJvTIsDbwYDgAFBiAClBMECAP+uFqEUggJBIYMCb1CLA28GBoABEIgApQCvgcGhEoICQSGDAm9giwNvBgaAAaqlAIOBqv///wAA////AAD///8AAP///wAA////AAD///8AAP///wAA////AAD///8AAP///wAA////AAD///8AAP///wAA////AAD///8AAP///wAA////AAD///8AAP///wAA////AAD///8AAP///wAA////AAD///8AAP///wAA////AAD///8AAP///wAA////AAD///8AAP///wAA////AAD///8AAP///wAAsIIBEaESggJBIYMCb2GLA28GA4AB+qUAg4H6////AAD///8AAP///wAA////AAD///8AAP///wAA////AAD///8AAP///wAA////AAD///8AAP///wAA////AAD///8AAP///wAA////AAD///8AAP///wAA////AAD///8AAP///wAA////AAD///8AAP///wAA////AAD///8AAP///wAA////AAD///8AAP///wAA////AAD///8AAP///wAA////AAD///8AAP///wAA////AAD///8AAP///wAA////AAD///8AAP///wAA////AAD///8AAP///wAA////AAD///8AAP///wAA////AAD///8AALGCARGhEoICQSGDAm9iiwNvBgOAAfqlAIOB+v///wAA////AAD///8AAP///wAA////AAD///8AAP///wAA////AAD///8AAP///wAA////AAD///8AAP///wAA////AAD///8AAP///wAA////AAD///8AAP///wAA////AAD///8AAP///wAA////AAD///8AAP///wAA////AAD///8AAP///wAA////AAD///8AAP///wAA////AAD///8AAP///wAA////AAD///8AAP///wAA////AAD///8AAP///wAA////AAD///8AAP///wAA////AAD///8AAP///wAA////AAD///8AAP///wAA////AACyFqEUggJBIYMCbyyLA28GAogApQPAAUCzGaEXggJBIYMCbzKLA28GA4ABPIgApQPAAUC0HaEbggRCIQAegwJvR4sDbwYCgAIBLIgApQTBAgD/tRuhGYIEQiEAFYMCb02LA28GAYABP4gApQPAAUC2HKEaggRCIQANgwJvTosDbwYCgAFBiAClBMECAP+3E6ERggRCIQAPgwJvT4sDbwYCpQC5GqEYggJBIYMCb1eLA28GAYAByIgApQTBAgD/uhuhGYIEQiEAVYMCb1iLA28GA4ABqogApQPAAUC7RKFCggRGIQAqgwJvgIsDbwYCgAHSpS7AAYDBKf//////////////////////////////////////////////AAAAAAD/vEOhQYIERiEAKYMCb4GLA28GAoABzaUtwAGAwSj//////////////////////////////////////////////wAAAAD/vR6hHIIERiEAA4MCb4KLA28GC4ABHogApQbAAYDCAQC+HqEcggRGIQADgwJvg4sDbwYLgAEeiAClBsABgMIBAL8fgeShF4ICQSGDAm+xiwNvBgSAAciIAKUDwAFAg4HIIf///yHz//8hQ///IUP4/yFDGf8hUyD5IVPx/yFT8v8hU/P/IVP0/yFT9f8hU/b/IVP3/yFT+P8hU/n/AgDw/wIA8f8CAPL/AgDz/wIA9P8CAPX/AgD2/wIA9/8CAPj/AgD5/wIQ8P9mZvD/Zmbx/2Zm8v9mZoP/Zmb0/2Zm9f9mZvb/Zmb3/2Zm+P9mZvn/Znbw/wgh8P8IIfH/CCHy/wgh8/8IIfT/CCH1/wgh9v8IIff/CCH4/wgh+f8IMfD/mZn5/xEREfm/IB+hFIICQSGDAm+yiwNvBgOIAKUDwAFAgwcVAAAA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' self.assertEqual(plain_upp, base64.b64decode(original_upp)) if __name__ == "__main__": unittest.main()