SSTIC 2024 - J1
Hey, ça faisait longtemps qu'on avait pas livebloggué un SSTIC hein ! (ouai, un an, comme chaque année). Comme d'hab, c'est au couvent des jacobins, comme d'hab on retrouve les copains, et des nouvelles têtes qui viennent découvrir le monde de l'in(sécurité) informatique 😄
Conférence d'introduction
Par Pascal Andrei, CSO d'AIRBUS
Dans l'aéronautique, la sûreté vise à rendre l'avion resilient aux menaces diverses, de la sécurité physique des sites de production, à la sécurité informatique des systèmes embarqués dans l'avion. Pour apporter de la sécurité dans l'entreprise, il a fallu casser des silos de fonctionnement, car les menaces ne font pas dans le détail et s'en foutent de ce qu'ils cassent si c'est la filliale A ou B. Autre défi, la communication, pour casser l'image de "Men In Black" afin d'obtenir l'adhésion des équipes. Et dernier défi majeur, montrer qu'on sert la production et qu'on est là pour préserver le business.
Côté liste des "assets", aka biens critiques et essentiels au fonctionnement de l'entreprise, ce ne sont pas les composants qui manquent, des centres de productions à l'IT. Ces sites étant répartis dans le monde, la géopolitique à forcément un impact sur l'entreprise, et il faut en tenir compte pour la sûreté du groupe. Quand votre logistique passe par des voies maritimes impactées par des conflits internationaux, il faut réussir à sécuriser l'approvisionnement.
La numérisation massive des assets provoque mécaniquement une augmentation de la surface d'attaque numérique. Surface qui se fait scanner et attaquer par un peu de tout, de l'activiste à la menace étatique en passant par les cybercriminels.
La sécurité informatique depuis le système de divertissement en cabine à fait parti des scénarios de menaces qu'il a fallu expérimenter au début des années 2000 avec deux hackers dans un vol simulé. Le premier via le wifi de l'avion, l'autre en utilisant l'écran dédié à la gestion. En provoquant une panique des passagers pour les basculer vers l'arrière de l'avion suite à une alerte à la bombe, le centre de gravité de l'avion change, et en phase d'atterrisage ça peut vraiment foutre le bordel. De ce fait le scénario théorique validé, a permis la sécurisation de ce SI de divertissement qui peut avoir un impact fort sur l'image de la compagnie.
Un avion, c'est quelque-chose qu'on achète pour 20 ou 30 ans, rendant le patch-management assez délicat. Et du coup faut réussir a faire redescendre sur l'ensemble des fournisseurs des exigences contractuelles afin de pas se retrouver avec un problème du type "la maj c'est pas dans le contrat". La production d'un équipement d'avion, ça prend du temps, et du coup il faut réussir à anticiper les menaces.
La question "tarte à la crème" qui est souvent posée, c'est "est-ce qu'on peut hacker un avion". Lorsqu'un avion est vendu, il est "propre", sans défauts ni vulnérabilités. Mais après il faut assurer le maintient en condition de sécurité. Mais les fournisseurs de matériel tiers genre les sièges etc... sont alors contraints de suivre des guides de sécurité afin d'éviter qu'ils ne viennent dégrader la sûreté de l'avion avec leurs gadgets à la mode.
Menace concrète issue des conflits internationaux: le brouillage GPS et le spoofing qui vient perturber l'horloge, la postion, l'altitude à un impact fort sur l'avionique. En cas de brouillage, le pilote bascule sur une centrale inertielle qui fournit une position moins précise mais "indépendante". Pour le spoofing, il faut interférer sur 3 signaux, issue du sol, de satellites basse altitude, et du système GPS. Le spoofing et le brouillage nécessite d'émettre plus fort que les émetteurs légitimes. Ce ne sont pas les exemples qui manquent sur FlightRadar24 avec des avions qui se "téléportent" sur la carte.
Evolution de la sécurité du moteur JavaScript V8
V8 c'est le moteur JS qu'on retrouve partout, dans les clients lourds JS genre electron, mais aussi les navigateurs Edge, Opera, Chrome. Une attaque (low level, dans le binaire pour ce talk) c'est une exécution de code JavaScript malveillant qui vient déclencher une vuln (off by one, confusion de type, overflow, etc...). Le tas V8 est constituté d'ArrayBuffer qui gère un peu toutes les données binaires de V8 (chaînes de caractères, objets JS, etc... ) et de WasmInstance lorsqu'il s'agit de code WebAssembly. Pour exploiter la vulnérabilité, l'attaquant doit essayer de corrompre les structures mémoire et de permettre de créer un faux objet en mémoire. Avec ce faux objet, on peut obtenir un moyen de lecture/écriture arbitraire qui permet l'écriture d'un shellcode dans l'environement d'exécution WebAssembly.
Côté contre-mesures, les protections mémoire Write xor Execute ont forcé les attaquants à aller écrire dans les zones de compilation du JavaScript en assembleur. Afin d'éviter que l'attaquant puisse lire/écrire en dehors du tas de V8, une sandbox à été mise en place, appellée hypercage. L'objectif de la sandbox est de retirer l'ensemble des pointeurs 64bits des zones "non-sûres" pour que l'attaquant ne puisse plus écraser une addresse arbitraire. Une table de pointeurs est utilisée pour gérer l'accès au DOM par le JavaScript afin d'éviter de filer un accès direct à l'addresse mémoire du DOM.
Ce modèle de Sandboxing force les attaquant une fois capable de lire et écrire de la mémoire arbitrairement à aller poser des gadgets (un moyen de rebond) dans des flottants d'une variable JS, et à appeller la fonction JS plein plein de fois. Cette action provoque l'appel à un mécanisme d'optimisation qui appelle le compilateur JIT, permettant d'y exploiter des vulnérabilités dans la gestion de ces flottants et de cette compilation à la volée.
Pour éviter ces vulnérabilités, les concepteurs de V8 ont mis en place des pointeurs sur fonction sécurisés dans une table à part, la code pointer table. Pour contourner ce mécanisme, les attaquant doivent mettre en oeuvre une fausse pile d'exécution JavaScript cohérente.
Pour contrer ces attaques, un "Trusted Space" à été créé pour stocker les informations sensibles comme les pointeurs vers les fonctions JavaScript, ou les structures de contrôle de l'environement d'exécution de WebAssembly.
Crypto-Condor: Compliance testing for cryptographic primitives
Une primitive cryptographique, genre AES, c'est la fonction de base d'un protocole de crypto type TLS. Du coup pour s'assurer que l'implem fonctionne bien, il faut s'assurer que les implem ne sont pas vulnérables et font bien leur taff correctement. Pour ce faire, lors d'un audit type CSPN, on utilise des cas de test appellés "test vectors" sur lesquels on va appeller les fonction et vérifer qu'elles ne sont pas vulnérables. CryptoCondor est donc un framework de test en python qui permet la génération de ces vecteurs de tests et de valider l'implémentation des primitives cryptographiques.
Pour appeller correctement l'implem de la primitive crypto, crypto-condor utilise un wrapper qui va gérer l'appel de la fonction crypto. Autre façon de gérer, la prise en compte d'appels et de sorties de fonction dans un fichier texte qui sera vérifié par crypto-condor. Le paquet est disponible sur pypi. La doc et le source est en ligne.
Exemple du fonctionnement de crypto-condor avec Cryme, une implémentation matrix volontairement vulnérable.
Frinet: Reverse-engineering using Frida & Tenet
En reverse, on a deux approches, la dynamique avec du debugger, de l'instrumentation, etc... et l'approche statique, ou on regarde l'ASM, et on l'annote proprement. Tenet est un plugin IDA Pro qui permet d'avoir une vue d'une trace d'exécution sous forme de commentaires/annotations. Tenet est livré avec des traceurs x86. Frida lui est un framework d'instrumentation dynamique de code qui supporte des infra pc et mobiles (iOS & Android). Les orateurs ont ajouté un module Frida capable de générer des traces format Tenet, et on amélioré le plugin Tenet avec un mécanisme de gestion de la pile d'appel.
Démo avec le mécanisme de mise à jour d'OTA sous Android. L'extension va faciliter la navigation entre pseudo-code, trace d'exécution & valeurs de registre.
ZED-Files: Aux frontières du réel
Une information Diffusion Restreinte est considéré comme une information Sensible. Cette dernière pour son transport doit utiliser un moyen agréé par l'ANSSI. Pour ce faire on a des Certifications, des Qualification et des Agréments. Cet agrément, n'est pas une garantie de sécurité absolue. La récupération de l'information de quel logiciel est agréé, c'est pas simple à trouver. Les conditions d'emploi c'est là ou le bas blesse, parceque les conditions d'emploi décrivent les conditions garanties par l'agréement.
Zed! fait l'objet d'un agréement EAL3+. Mais la cible ne couvre pas forcément tous les usages. Zed! gère des conteneurs cryptographiques avec un mécanisme de chiffrement/déchiffrement basé sur un mot de passe (de préférence fort ;) ). En ligne on retrouve des cibles de sécurité, des vulns, un guide de l'anssi, etc... La création d'une clef pour un accès utilisateur produit des fichiers .zaf qui doivent d'une façon ou d'une autre contenir la clef privée de l'utilisateur. Mais quand on crée un conteneur et qu'on l'envoie à quelqu'un, on a pas besoin de la clef privée de l'utilisateur. Le conteneur contient donc les moyens de déchiffrement nécessaires. A coup de reverse-engineering on peut identifier les fonctions crypto employées, ici AES. Du coup en regardant le foncitonnement d'un fichier .zaf on a une clef hardcodée, qui chiffre des données format TLV. Du coup un fichier .zaf dont le mot de passe est faible peut etre bruteforcé. C'est pour ça qu'il est recommandé de changer le mot de passe tout les 90 jours. Vu que l'archive Zed! est auto-extractible, elle contien donc un équivalent du fichier .zaf. L'archive contieny uassi le chemin intitial de création.
QBinDiff: A modular differ to enhance binary diffing and graph alignment
Le BinDiff consiste à comparer deux binaires, par exemple pour l'analyse d'un patch afin de découvrir une 1-Day, ou vérifier la bonne implémentation d'une contre-mesure sur un correctif de sécurité. Lorsque le binaire est obfusqué, c'est plus compliqué car l'application de l'obfuscation casse les ressemblances entre deux versions d'un binaire. Parfois ce n'est que le contenu des fonctions et pas le graph d'appel qui est obfusqué. Quand on fait du diffing, on va s'appuyer sur une mesure de distance qui évalue la similarité entre deux fonctions. Comme un programme c'est un graph, on peut faire de la similarité sur ces graph et identifier les portions de ce dernier qui ont changé. QBinDiff permet de jouer sur les différentes fonctions de l'algo de diffing, aussi bien la mesure de similarité que le désassembleur.
La rétro-ingéniérie de code malveillant dans la CTI
La CTI s'intéresse (entre autre) aux moyens techniques des attaquants pour mieux se défendre. Un attaquant dépends de moyens techniques comme leur infrastructure hébergeant leur charges ou les serveurs de command & control, et de divers codes: malwares, loaders, packers etc...
Exemple avec TA410, découvert en 2019 par proofpoint, puis reversé par ESET dans une publication en 2021. C'est un Threat Actor supposé d'origine chinoise associé à APT-10. Son arsenal est basé sur des malwares comme PlugX, QuazarRAT, Tendyron ou FlowCloud. FlowCloud crée un service sur la machine de la victime qui exécute une application vulnérable à un dll-sideloading chargeant la dll de flowcloud. Sur VT on peut retrouver la dll en question et la reverser. Dedans on trouve des techniques d'anti-analyse genre jump in the middle de quelques octets. Du coup une fois la désobfuscation faite, on peut analyser la bestiole. Cette dernière dépend d'un fichier .dat qui n'est pas disponible sur VT. Par contre, le pattern d'anti-reverse est assez signant, et permet de mettre en oeuvre une règle de hunt Yara permettant de découvrir des variants. Ces variants ont d'autres mécanismes d'anti-analyse. A partir de l'analyse de ces mécanismes on obtiens de quoi construire une nouvelle règle Yara. Avec cette règle, l'orateur à trouvé sur VT une dll appellée msedgeupdate.dll avec un score à 0. Quand on a bien suivis l'histoire de cette .dll on sait qu'elle vient déchiffrer un .dat qui contient le shellcode chargé par la .dll.
Retour d'expérience sur l'organisation d'un CTF
Le FCSC est un CTF individuel organisé par l'ANSSI tous les printemps. Le CTF est hébergé sous CTFd, avec diverses catégories. Certaines épreuves nécessitent d'interragir avec des services en lignes hébergés dans l'infra et doivent être isolées les unes des autres. Quand on organise des chall, il y a des surprises. Sur une épreuve de pwn, la conteneurisation a impacté le layout mémoire, rendant le chall beaucoup difficile à résoudre. D'ou l'intérêt d'avoir une pré-production. Parfois certains joueurs utilisent des 1-day voir des 0-day. L'infra est montée pour l'épreuve puis démontée après. Elle est reconstruite chaque année, et suite aux vagues de ddos de 2021 forçant la re-structuration de l'infra. Les épreuves sont derrière des HAProxy pour le load-balancing, la partie CTFd est sur un cluster différent ce qui limite les risques de mouvement latéral depuis les conteneurs vers l'infra de scoring. Du coup le durcissement des épreuves prend énormément de temps.
Pour rendre les conteneurs plus étanches, les orateurs ont choisi de basculer vers des microVM: Firecracker. Cependant cette solution est brute et nécessite de bosser l'intégration pour automatiser la création des interfaces réseaux, du rootfs et le patch du kernel. Du coup les orateurs sont parti sur une solution maison avec deux versions, une en rust et une en golang.
La gestion des DDoS sur le CTFd rendait l'épreuve moins agréable. Les orgas ont tenté l'utilisation d'un fail2ban mais qui s'avère insuffisant. Les orateurs ont décidé de créer Hodor qui surveille les logs du serveur web, et lorsque le rate-limiting est déclanché plusieurs fois, l'IP du client va finir dans un blocage basé sur eBPF, ce qui permet de drop 1M de paquets par seconde. En 2023, le DDoS a été plus important, avec plusieur milliers d'IP.
Fin d'année dernière, les épreuves des années précédentes sont mises à dispo sur le site Hackropole.
RedTeam like an APT
Histoire d'un engagement red-team sans phishing ni attaque physique dans le scope. La cible étant mature, la surface d'attaque n'était pas énorme. Comme le client avait du MobileIron de déployé, les orateurs ont décidé de creuser. En installant l'appliance en local, ils se sont rendu compte que l'appli balance pas masses de logs et c'est donc une grosse boite noire pour le SOC.
MobileIron est un MDM acheté par Ivanti en 2020. Cette solution permet de gérer la flotte mobile, et d'exposer des appli aux mobiles sous la forme d'un proxy. Ce proxy écoute sur le port 443, et sur le 9997 pour l'authentification. Vu que les proxy chainés sont de type différents, on peut faire de l'http request smuggling. Ici on a du Apache et du Tomcat du coup c'est vuln. L'attaque consiste à injecter des %0A pour obtenir à l'autre bout des retours chariots, ce qui permet de faire faire au reverse-proxy des requêtes arbitraires.
L'interface web de gestion des GPO est vulnérable à une "Zip slip" attaque, et lorsque la solution décompresse le zip, on peut déposer un webshell au bon endroit. Sur le portail MICS il existe une méthode "rce as a service" qui permet d'exécuter des commandes arbitraires. Pour prendre pied sur le SI est accéder à l'ensemble du réseau, les orateurs ont utilisé stunnel pour lancer un serveur socks en local, et modifier le firewall local pour rediriger les paquets publiques vers le serveur socks.
Dans les fichiers de conf de la solution, on peut récupérer les credz ldap et les comptes kerberos pour la délégation kerberos permettant au proxy de rendre les services internes accessibles aux téléphones. L'instance mobileiron enregistre pas mal de mots de passe. Le déchiffrement des clefs du compte Kerberos se fait sur la base des éléments présent sur le serveur. A partir de là, avec les comptes Kerberos, on peut accéder au serveur Exchange sur lequel on peut faire du PSRemoting sur le 443 via un compte administrateur. Grâce à la délégation Kerberos, et à l'exécution de code sur le Exchange les orateurs on pu migrer vers le VCenter, d'ou ils ont dump le DC. à partir des credz présents dans le Dump, ils ont pu compromettre le domaine.
Le zip slip à été remonté, mais il n'a pas été patché. La RCE sur Sentry est patchée. Les exploits seront publiés sur github.
dig .com AXFR +dnssec
Lister tout l'internet avec DNSSec. Un hacker belge à fait la une en enregistrant des noms de domaines oubliés appartenant au gouvernement belge. Il existe actuellement 1449 TLD, les .com, .fr etc... L'orateur s'est posé la question de savoir s'il était possible de lister tous les noms de domaines qui existent sur Internet ? La première façon d'avoir l'info, c'est via l'ICANN, d'autres sites vendent l'accès à ces informations, d'autres gestionnaires de zone font de l'open-data, et donc les infos sont publiques. Récupérer tous les enregistrements DNS d'un TLD ça s'appelle un AXFR. Une des façons de faire, c'est de bruteforcer tous les noms des serveurs de gestion de zone, et de leur demander "gentillement" les infos. Une vulnérabilité connue de DNSSEc consiste à faire du Zone walking. L'interrogation d'un serveur racine en DNSSec permet d'obtenir une signature RRSIG. Si on tape un domaine J.com qui n'existe pas, on a des infos suplémentaires dans le RRSIG. En effet, le RRSIG contient deux bornes en "justification" qui dit ya rien entre le nom de domaine A.com et L.com.
NSEC3 introduit un mécanisme cryptographique pour complexifier le listage des domaines. Si le TLD est protégé par NSEC3, on apprend comment c'est hashé, si c'est protégé, combien d'itérations et avec ou sans sel. Du coup avec NSEC3 on récupère 2 hash de noms de domaines qui existent. L'orateur a créé un outil pour faire ce travail d'énumération. Prour trouver les "trous" entre les domaines, l'orateur a implémenté en OpenCL un mécanisme de récupération qui génère 2GH/s sur une RTX4090, ce qui permet de dump un TLD en plusieurs heures. Une fois la liste des hashs des noms de domaines récupérée, il faut la casser avec hashcat pour lequel le support NSEC3 à été ajouté. l'espace de caractères est petit, et comme il y a pas mal de noms de domaines basés sur des mots, ça casse assez bien. Cependant sur des gros TLD, on peut retrouver que la moitié des noms.
Utilisation de DHCP pour contourner routeurs et pare-feux
Il arrive parfois que des pare-feux soient configuré comme client DHCP. Notamment lorsque ces pare-feux sont connecté à des réseaux WAN tiers. De même les machines qui hébergent des VM ou des conteneurs peuvent avoir des pare-feux ou être un pare-feux. Voir même ils peuvent être configuré via cloud-init en dhcp.
DHCP permet à une machine de récupérer une addresse IP et d'éviter des conflits d'addresses. Les options intéressant sont par exemple celles qui impactent les tables de routage comme l'option 1 IP/Mask, l'option 121 pour pousser des routes arbitraires, etc... L'attaque se déroule dans un SI ou l'attaquant à pris pieds sur le serveur DHCP, ou alors qu'il peut faire du MITM et usurper l'identité du serveur DHCP. Comme la route la plus précise est la plus prioritaire, si via l'option 121 l'attaquant spécifie son IP comme destination unique, le trafic de la machine victime sera routée vers l'attaquant.
Les VPN sont un cas particulier de ce cas, TunnelCrack est un exemple d'usage des tables de routage pour mettre à mal la sécurité. Pour écouter le trafic entre un client et un serveur, on peut pousser une route qui pointe vers son serveur DHCP controlé pour le sous réseau local derrière le pare-feu. Est-ce que les pare-feux du marché sont concernés ? Plus maintenant pour Stormshield et PfSense. Fortigate n'est pas concerné car il n'accepte pas par défaut les paquets qui font partie d'une connexion établie.
Une contre-mesure possible consiste à utiliser du policy-based routing. Une autre consiste à dégager le "ct state established accept" et à le re-préciser sur les routes & interfaces spécifiques.
Pour conclure, le mécanisme de suivi de connexion est mal utilisé et mal compris.