Feitian ePass 2003 je PKCS#11 kompatibilní token, který podporuje RSA klíče s velikostí modulu 512 až 2048 bitů, algoritmy z rodin SHA-1, SHA-2, GOST, RIPEMD160 a některé další. Klíče jsou chráněny alfanumerickým PIN-em (heslem) o délce 6–16 znaků.
Podporu PKCS#11 zajišťuje projekt OpenSC, a pro tento token je potřeba verze alespoň 0.13.0. Mnoho našich oprav je už zamergováno v „master“ větvi, ke které ovšem dlouho nebyla vydána otagovaná stabilní verze. Správci projektu OpenSC jsou ale dost opatrní, takže by měla fungovat ručně přeložená verze z aktuálního HEAD.
Poznámka: i když jsou v OpenSC zdrojáky k ePass 2003, neexistuje žádná dokumentace výrobce, která by se celkem hodila k jeho proprietárním instrukcím.
S tokenem lze použít aplikace, které podporují PKCS#11 rozhraní:
- OpenSSH funguje spolehlivě, ale člověk nesmí mít moc klíčů na tokenu, pokud mu jich totiž klient nabídne příliš mnoho, server zavře spojení (u většiny serverů je default myslím 5 nabídnutých klíčů). OpenSC je vyžadováno jen na straně klienta.
- Firefox umožňuje přihlašování s klientským SSL/TLS certitikátem a klíčem na tokenu; zde je drobný problém s „replug bugem“ – pokud se token odpojí a připojí během života procesu Firefoxu.
- OpenDNSSEC s tokenem fungoval také, pouze je potřeba v konfiguraci HSM pro OpenDNSSEC použít název tokenu i s řetězcem „ (User PIN)“ na konci
- autentizace přes PAM použitímpam_pkcs11
Vcelku dobré návody pro rozchození různých aplikací s tokenem jsou na gooze.eu.
GnuPG lze rozchodit ePass emulací OpenPGP karty – PKCS#15 a OpenPGP karta jsou velmi různé formáty a podpora OpenPGP je limitována na jeden PGP/GPG klíč, plus dva podklíče a celé je to uživatelsky dost nepřívětivé. Alternativně existuje projekt gnupg-pkcs11-daemon, ten je už ale hodně dlouho bez podpory a neumožňuje import existujícího PGP klíče. Import existujícího klíče lze rozchodit úpravou SCD démona a „ohnutí“ SCD příkazu KEYTOCARD. Bohužel se při tom nevyhnete manuální manipulaci s PGP packet formátem.
Pro multiplatformní podporu (Windows, Linux, Mac) je nutné použít OpenSC, protože standardní Windows drivery používají na tokenu proprietární schéma souborů, které není kompatibilní s PKCS#15 (další radost proprietárních řešení).
Souborový systém
Token používá PKCS#15-kompatibilní souborový systém. Víc se podobá speciálním filesystémům jako procfs, než klasickým filesystémům na harddiscích a jiných blokových zařízeních. Jedním specifickým důvodem je to, že nechceme, aby bylo možné číst privátní klíče.
Níže je uveden příklad soborů na jednom tokenu. Každý soubor je označen dvěma bajty: main file (MF), nebo-li kořenový adresář, má označení 3F00. Adresář se v terminologii smartkaret nazývá dedicated file (DF). Pod MF 3F00 se nachází DF 5015, obsahující soubory spojené s PKCS#15.
Poslední typ, working elementary file (wEF), je už celkem blízko běžnému souboru, jak jej známe z PC, ale existují různé podtypy.
FileID Typ Velikost Komentář [3F00] MF # MF - main file - neboli „kořenový adresář“ 2F00 wEF 0 [5015] DF 0 # DF pro PKCS#15, název: \xA0\x00\x00\x00cPKCS-15 9F00 wEF 2 5031 wEF 512 # ODF 5032 wEF 128 # TokenInfo 5033 wEF 128 # UnusedSpace 4401 wEF 256 # metadata PIN(ů) 4402 wEF 1024 # metadata privátních klíčů 4403 wEF 1024 # metadata veřejných klíčů 4404 wEF 2048 # metadata certifikátů 4405 wEF 256 # metadata datových objektů 4946 wEF 128 2900 iEF 0 # privátní RSA klíč, neextrahovatelný 3000 wEF 270 # veřejný RSA klíč, PKCS#1 formát
Ve výpisu je ještě vidět soubor 3F00/5015/2900. Je to takový soubor-nesoubor, jeho struktura je daná interní implementací smartkarty a nelze jej číst, protože obsahuje privátní klíč (internal elementary file, iEF). Použití je možné jen s některými APDU, třeba pro podepisování.
Většina souborů má vnitřní obsah kódován v ASN.1, přesná struktura je popsána v PKCS#15. Celkově je ve standardu specifikováno 252 definicí ASN.1 struktur, což je celkem hodně na zdánlivě jednoduchý souborový systém.
Soubory mají navíc k sobě přiřazeny práva (access control list – ACL). Obsahují například, zda je na smazání nebo úpravu potřeba PIN, a nebo že to není možné ani s PIN-em. ACL se k souboru přiřadí v momentě jeho vytvoření. Při definici ACL na souborech, je zapotřebí si dávat pozor, protože s příliš přísnými právy je možné token „bricknout“, tj. dostat ho do stavu, kdy se soubory nedají smazat, ale ani vytvořit.
Šifrování na USB vrstvě – SCP01
Token používá šifrování APDU na USB-CCID vrstvě. Je to featura, o které po pravdě netuším, proti jakému druhu útoku má chránit – útočník se schopností přistupovat k USB sběrnici buďto softwarově nebo hardwarově dokáže mnohem zajímavější věci. Naopak bych SCP01 hodnotil jako anti-featuru, jenom ztěžující debugování a snižující použitelnost. Navíc SCP01 je deprecated minimálně od roku 2006 (GlobalPlatform 2.2).
SCP01 začíná tak, že token a PC si na začátku pošlou „host random“ a „card random“, každé o 64 bitech, z nichž se odvodí 128-bit klíč na šifrování. Do odvozovacího algoritmu vstupuje další symetrický klíč, jenže ten je natvrdo jak v zdrojácích ovladače, tak v tokenu. Odposlechem USB lze rekonstruovat klíč, na kterém se domluvil PC s tokenem. Navíc se šifruje jen data sekce APDU, bajty INS, P1 a P2 jsou viditelné. V CLA se nahradí 2 bity indikující, že se používá „secure messaging“.
Příklad výměny host random a card random, random části klíče jsou zvýrazněny podtržením:
- PC vyšle APDU, posledních 8 bytů je „host random“
- 80 50 00 00 08 _BF C3 29 11 C7 18 C3 40 1C_
- token pošle v odpovědi na APDU svůj „card random“
- 06 05 04 03 02 01 03 08 12 01 FF 01 _08 44 44 A9 53 1A 0A 00_ A6 77 B5 36 B4 03 ED DF 90 00
- dejme tomu že nešifrovaná APDU, kterou chce PC odeslat, vypadá:
- 00 A4 00 00 02 3F 00 00
- po zašifrování bude tělo APDU šifrováno, pole INS, P1 a P2 zůstavají stejná
- 0C A4 00 00 20 87 11 01 56 72 18 C6 FC E8 6B 38 …
Zmíněný „replug bug“ v OpenSC ePass 2003 driveru způsobuje, že pokud se ePass vytáhne a připojí během života procesu aplikace, token v daném procesu nezačne znova správně fungovat, dokud se aplikace opětovně nespustí. Může to vadit třeba u Firefoxu, který u spousty lidí běží dlouhou dobu. Je za to odpovědné právě SCP01, které se nereinicializuje správně. Zjistili jsme, že by na to stačilo v správné chvíli zavolat z OpenSC funkci epass2003_refresh(), ale to není jednoduché do OpenSC našroubovat bez ošklivých hacků.
Další věc, která bohužel nefunguje, je cachování hesla ssh-agentem (myslím, že to také souvisí se SCP01), ale v tomhle případě je z operativních důvodů lepší cachování nepoužívat. Člověk tím pádem musí oželet vymoženosti shell-completion, jako doplňování cesty vzdáleného stroje u scp.
Fyzický přístup
Vraťme se k tokenu, kterému jsme upilovali plastový kryt.
Jednoduchý nápad číst data z pinů logickým analyzátorem k zajímavým odhalením nevedl, to už je snazší odposlouchávat data rovnou z USB sběrnice tcpdumpem z usbmon zařízení, nebo si je nechat vypisovat z debugovacích hlášek pcscd démona po úpravě OpenSC, aby tam nepřekáželo SCP01.
Možná by něco odhalilo měření postranních kanálů při spotřebě, datasheet ale zmiňuje, že čip by měl odolat diferenciální analýze spotřeby. Pro útočníka je už tohle prakticky nezajímavé, protože potřebuje PIN. Když už má PIN a fyzický přístup k tokenu, nepotřebuje složitě získavat původní klíč (pokud není zrovna zadáním explicitně kopie RSA klíče).
Token je designován jako „tamper evident“ (součást FIPS-140–2 Level 2) ale ne „tamper resistant“. To značí, že pokusy o fyzickou manipulaci mají být zřejmé, ale není tam žádný „kill switch“, který by zničil čip při pokusu o otevření plastového krytu.