8 van de 10 Belgische banken haten deze vreemde eID RCE
Er zijn meerdere ernstige problemen ontdekt. Elke website of iframe kon eID- en Maestro-kaartgegevens van de gebruiker uitlezen en hun eID-pincode herstellen; het binary-bestand stuurde de pincode namelijk terug naar de pagina in een token dat zowel de cijfertekst als de sleutel voor decryptie bevatte. Het ergste van alles is dat elke site een 'drive-by' RCE (Remote Code Execution) kon triggeren door het native binary-bestand een door de aanvaller aangeleverde library te laten laden en uitvoeren. Voor de gebruiker ziet dit eruit als een gewone bestandsdownload, zoals een PDF, terwijl ze in werkelijkheid worden blootgesteld aan RCE.
Het bedrijf achter deze software, Nitro Software Belgium, is een Gekwalificeerde Vertrouwensdienstverlener (Qualified Trust Service Provider) op de EU eIDAS Trusted List, het hoogste vertrouwensniveau dat de regelgeving definieert. De problemen werden 146 dagen na het eerste rapport opgelost.
---
Wat is het Connective-ondertekeningssysteem?
Het Connective-ondertekeningssysteem bestaat uit twee delen: de extensie en de native host. Webpagina's gebruiken de extensie om te communiceren met de native host, die vervolgens communiceert met de smartcardlezers die aan de machine zijn gekoppeld om taken zoals digitale ondertekening uit te voeren.
De extensie is lichtgewicht en fungeert enkel als een communicatielaag tussen de webpagina's en de native host door alle berichten door te sturen.
Het systeem wordt gebruikt voor authenticatie op websites en het ondertekenen van documenten. Met meer dan 2 miljoen gebruikers werd in 2021 gesteld dat Connective werd gebruikt door meer dan 60 overheidsdiensten en meer dan 1.000 bedrijven. Hoewel niet expliciet bevestigd kan worden of alle organisaties de extensie gebruiken, is het aantal wekelijks actieve gebruikers van meer dan 2 miljoen bevestigd.
Waarom is dit onderzocht?
De Connective-ondertekeningsextensie werd onder onze aandacht gebracht nadat een scan uitwees dat de extensie de oorsprong (origin) van het verzoek niet doorstuurde naar de native host. Dit betekende dat het programma op de computer niet wist met welke site het communiceerde, wat een alarmsignaal was.
Hoewel niemand van ons team uit België komt, konden we dit testen door een mock-eID te maken. We merkten dat er voor bijna alle commando's (behalve het "version"-commando) een token vereist was. Zelfs met deze vereiste activationToken vonden we het verdacht dat de oorsprong van het bericht nooit naar de native host werd doorgestuurd, aangezien de native host anders geen manier had om de bron van de website te verifiëren.
We gebruikten dit systeem aanvankelijk als testdata voor onze volledige geautomatiseerde scanning-functionaliteit voor extensies en native hosts, wat verklaart waarom we hier uitgebreider onderzoek naar hebben gedaan dan naar andere ontdekkingen.
Analyse van de activationToken en token-flow
De activationToken is een cryptografisch ondertekend token (RSA 2048), verstrekt door partner-sites die de Connective-extensie gebruiken, om een site toestemming te geven het Connective-systeem op de machine van de gebruiker te gebruiken. Het is in feite de toegangspoort tot alle functionele commando's.
In ruwe vorm ziet dit token er als volgt uit: Lhx4xKzCIJfSRAaP2jdgdM4WYmjQ/Sremo9v/Db/8T9A+NQd6Or3NO0V3nk4Rx9OPL8oDFQfrrZETRlm1dvTt30TBaua4W0OOYuR...
Na decodering via RSA-handtekeningherstel krijgen we dit:
{
"token": "b138fcf4-4619-47eb-846a-dc9cbeb7714d", // UUID - niet gebruikt
"ttl": 1773811513534, // 2026-03-18 05:25:13 UTC
"features": 7 // alle bits gezet = alle operaties toegestaan
}
Dit token bevat een UUID (waarvan we geen doel hebben waargenomen), een TTL (Time To Live) en een features bitmask. Het bitmask bepaalt welke functies zijn ingeschakeld:
| Bit | Mogelijk maakt |
|---|---|
| bit 0 | GETREADERS, READFILE, PINPADAVAILABLE, VERIFYPIN, COMPUTESIGNATURE, COMPUTE_AUTHENTICATION |
| bit 1 | ongebruikt / gereserveerd |
| bit 2 | COMPUTESIGNCHALLENGE, SELECTMAESTRO, GETPROCESSINGOPTIONS, READRECORD |
Het orakel dat we gebruikten om deze tokens te verkrijgen was Doccle.be; hun tokens stonden alle operaties toe en hadden een TTL van 24 uur. Omdat deze activationTokens niet gekoppeld zijn aan een specifieke origin, kan elke willekeurige webpagina deze tokens hergebruiken (replay) om volledige toegang te krijgen tot het Connective-systeem op de machine van de gebruiker.
eID's en Maestro-kaarten lezen zonder toestemming
Met dit activationToken, dat niet aan een origin is gekoppeld, kunnen we verbonden eID's en Maestro-kaarten uitlezen zonder medeweten of toestemming van de gebruiker.
Het PIN-token en de door de aanvaller beheerde dialoog
Toen we ontdekten hoe het pinToken werkte, realiseerden we ons dat dit niet slechts een enkele fout van een ontwikkelaar was, maar dat de ontwikkelaar onvoldoende kennis had van beveiliging.
Het pinToken werd door de native host naar de extensie en vervolgens naar de webpagina gestuurd zodra de gebruiker hun pincode invoerde in de native Connective-dialoog. Tijdens decompilatie via Ghidra identificeerden we het commando om dit pinToken op te vragen. Het bericht dat de webpagina moet sturen ziet er als volgt uit:
{
"cmd": "VERIFY_PIN",
"reader": "Pol Henarejos Pico Key HID Interface",
"entry_title": "Belgian Government - Identity Confirmation",
"entry_message": "Enter your eID PIN to confirm your identity for Tax-on-web",
"activationToken": "IhOcGOSbU/w1TnQNcfz56LUkfYwzmwr4chRgyE68RHNys9jJUt4IH9dAaEVjF8..."
}
De webpagina controleert dus de tekst in de popup, waardoor social engineering om dit pinToken te verkrijgen triviaal is. De popup waarin de gebruiker de pincode invoert, ziet er exact hetzelfde uit als bij een legitieme applicatie; enkel de titel en het bericht zijn door de aanvaller bepaald.
Extractie van de eID-pincode
Zodra een website het pinToken heeft verkregen, kan de werkelijke eID-pincode worden afgeleid. Het token bevat namelijk zowel de cijfertekst als de decryptiesleutel, met een statische IV (Initialization Vector).
Voorbeeld van een pinToken: Z0WLa8YjezJpmDxkc0gzZlHcsHT/XEkZSpToKuxYVWLh+AAByPpJIGoAP3VlbtC0
Het proces van herstel:
- Base64-decodering: Resulteert in 48 raw bytes:
67 45 8b 6b c6 23 7b 32 69 98 3c 64 73 48 33 66 51 dc b0 74 ff 5c 49 19 4a 94 e8 2a ec 58 55 62 e1 f8 00 01 c8 fa 49 20 6a 00 3f 75 65 6e d0 b4
- AES-128 sleutel (bytes 0, 2, 4, ... 30):
67 8b c6 7b 69 3c 73 33 51 b0 ff 49 4a e8 ec 55
- Cijfertekst (bytes 32+):
e1 f8 00 01 c8 fa 49 20 6a 00 3f 75 65 6e d0 b4
- Hardcoded IV (gevonden in het binary-bestand):
a6 a6 a6 a6 a6 a6 a6 a6 a6 a6 a6 a6 a6 a6 a6 a6
- Gedecrypteerde plaintext:
34 32 30 36 39 80 a7 63 98 71 01 00 00 PIN-bytes: 0x34 = '4', 0x32 = '2', 0x30 = '0', 0x36 = '6', 0x39 = '9'. De overige bytes zijn een TTL voor de vervaldatum van het token.
Dit maakt niet alleen phishing mogelijk, maar stelt de pincode direct bloot. Nu we de pincode kunnen extraheren, kunnen we eigen pinTokens genereren om deze op elk gewenst moment te gebruiken. Dit kan worden misbruikt voor het vervalsen van handtekeningen op hypotheekakten of het inloggen op overheidsaccounts (zoals Tax-on-web) met hoog-vertrouwde handtekeningen.
De impact op het Belgische eID-ecosysteem
Het Belgische eID-systeem werkt vanuit de aanname dat uw pincode alleen wordt ingevoerd in software die u bewust uitvoert, en dat uw sleutels alleen worden gebruikt voor acties die u daadwerkelijk wilt uitvoeren. Alles wat hierop volgt, erft dit vertrouwen over. De non-repudiatie-sleutel produceert eIDAS-gekwalificeerde handtekeningen, die wettelijk gelijkstaan aan een papieren handtekening. Dit betekent dat als iemand een handtekening vervalsed, u degene bent die moet bewijzen dat u het niet was.
Hoewel de kaart in de lezer blijft en de sleutels de kaart nooit verlaten, maakt dit voor een aanvaller weinig uit. Het bezitten van de pincode plus de mogelijkheid om commando's naar de kaart te sturen is hetzelfde als de kaart fysiek in handen hebben. Bovendien werkt dit vanuit een iframe; de gebruiker hoeft niet eens direct de kwaadaardige site te bezoeken; een advertentie of onzichtbaar tracking-frame volstaat.
Om online een lening af te sluiten op naam van iemand anders, heb je hun volledige naam, Rijksregisternummer, adres en een verifieerbare handtekening nodig. Al deze gegevens staan op de chip in bestanden die zijn ondertekend door het Rijksregister. Een aanvaller krijgt dus niet alleen de data, maar een door de overheid gecertificeerde kopie ervan, plus de mogelijkheid om elk gewenst document te ondertekenen met een gekwalificeerde handtekening.
itsme: de identiteitslaag voor België
Itsme is de centrale identiteitslaag in België voor online bankieren, Tax-on-web, MyGov, MyPension en meer. Men kan een itsme-account aanmaken via de eID door op de website van itsme de algemene voorwaarden te ondertekenen met de eID (via de Connective-plugin). Deze handtekening dient als identiteitscontrole.
Er is echter een risico op accountovername. Het blokkeren van een itsme-account vereist geen authenticatie; men hoeft enkel het telefoonnummer en de voornamen in te vullen zoals deze op het ID-document staan (gegevens die vaak via databrokers beschikbaar zijn). Zodra een account niet meer actief is, kan het opnieuw worden geactiveerd met een eID op hun website via een nieuw nummer.
Een aanvaller zou dus een working itsme-account kunnen overnemen in de naam van het slachtoffer. Dit account blijft werken nadat de browser is gesloten, de kaart uit de lezer is gehaald en de extensie is gepatcht. Hoewel we dit niet expliciet met itsme hebben getest, konden we wel een accountovername demonstreren bij CSAM.be, die vertrouwde op eID voor authenticatie.
Het zorgwekkende is dat itsme hierin niets fout heeft gedaan. Het hele ecosysteem vertrouwt erop dat QTSPs (Qualified Trust Service Providers) "gekwalificeerd" zijn. Nitro Software Belgium staat op de EU eIDAS Trusted List, het hoogste niveau. Dit scenario is volledig het gevolg van fouten bij Connective / Nitro.
RCE via LoadLibrary
Na het in kaart brengen van alle commando's identificeerden we een kritiek probleem met het GET_READERS commando. Een pagina kan dit als volgt aanvragen:
{
"cmd": "GET_READERS",
"library": "..\\..\\..\\..\\Downloads\\lib.dll"
}
De library-eigenschap stelt elke webpagina in staat om op te geven welke DLL geladen moet worden, waarbij relatieve paden zijn toegestaan. De enige beperking is dat het bestandspad .dll moet bevatten.
Omdat Chrome bestanden met de extensie .dll in downloads automatisch markeert als gevaarlijk, kan een aanvaller gebruikmaken van een 'polyglot'-bestand, bijvoorbeeld genaamd frien.dlly_reminder.pdf. Door relatieve paden te gebruiken vanaf de installatielocatie van de Connective-extensie (onder AppData), kan de aanval terugnavigeren naar de Downloads-map om de library uit te voeren.
Dit maakt een 'drive-by' RCE mogelijk: de gebruiker klikt op een link, een bestand wordt automatisch gedownload en de code wordt uitgevoerd op het niveau van de gebruiker, waardoor de Chrome-sandbox wordt omzeild. Dit is de meest impactvolle bevinding; er zijn geen vreemde configuraties nodig en het zou zich als een worm kunnen verspreiden door sessie-tokens te stelen en links naar andere gebruikers te mailen.
Hoe het is opgelost
Nitro implementeerde de eerste fix op 8 mei 2026, waarbij een origin-check via een remote server werd toegevoegd om verzoeken goed te keuren voordat commando's werden uitgevoerd. Dit loste de RCE en het lekken van het pinToken echter niet op; het betekende enkel dat alleen goedgekeurde sites deze acties konden uitvoeren.
Op 19 mei wezen we Nitro erop dat de fix onvolledig was: het library-commando was nog intact (RCE mogelijk) en het pinToken kon nog steeds naar webpagina's worden doorgestuurd.
De volledige patch werd gepubliceerd op 1 juni:
- Het
library-commando is uitgeschakeld. - Het
pinTokenwordt nu gecachet in de extensie; de site krijgt een willekeurig gegenereerde UUID als referentie in plaats van het token zelf.
Uiteindelijk werden de remote origin-checks op 22 juli afgedwongen, waardoor websites niet langer stilzwijgend eID's kunnen uitlezen of pincodes kunnen phishen.
De aanpak van Nitro
Nitro deed er lang over om dit op te lossen, maar ze beschikten over een beveiligings-e-mailadres, probeerden ons niet te dwingen tot een NDA via een bug bounty-programma en ontkenden de feiten niet. Hoewel de reactiesnelheid tekortschoot, hebben ze het uiteindelijk wel volledig opgelost. Op onze vraag naar een bounty boden ze 200 dollar aan.
Conclusie
Er zijn veel andere extensies met soortgelijke problemen die tientallen tot honderden banken in gevaar brengen. Communicatiebruggen tussen native hosts en willekeurige websites zijn gevaarlijk, maar worden niet als zodanig behandeld.
Er is wetgeving nodig die competente penetratietesten verplicht stelt voor "Qualified Trust Service Providers". Het voelt momenteel aan als 'security theater', aangezien een zo overduidelijk gat in de grootste Belgische eID-ondertekeningsextensie in de Chrome Web Store simpelweg over het hoofd is gezien.
***
¹ Cijfers zoals gepubliceerd in marketingmateriaal van Connective / Nitro Software Belgium. Het aantal wekelijks actieve gebruikers van 2M+ is bevestigd via de Chrome Web Store en Edge-vermeldingen.
Groetjes,