
Un PoC de la vulnérabilité CVE-2024-56426.
Outillage unifié CVE-2024-56426 pour les familles Galaxy S20, S20 FE et Note20 sous Exynos 990. L'exploit accepte les dix noms de modèles et les mappe sur six familles de bootloader de série vérifiées.
[!CAUTION] Le lot de clés suivi et les images générées sont capables de fusion. La fusion est irréversible. Un téléphone fusionné à une clé ne peut démarrer que des images compatibles avec cette clé. Un mauvais modèle, une révision de rollback, un ensemble de correctifs ou un lot de clés peut laisser l'appareil dans une boucle de démarrage fusionnée. Utilisez des clés de développement et la charge utile UFS lors des itérations. Ajoutez
--no-fuseà chaque commande de préparation/signature, sauf si la fusion de clé personnalisée est explicitement prévue.
Le modèle sélectionné contrôle à la fois l'ID de modèle BL1 et le TSV de correctif LK du modèle exact. Runtime artifact contrôle quel
firmware de série et quelles images fractionnées chiffrées sont utilisés par la pré-vérification. Les quatre indicateurs non-5G qui utilisent des
artefacts d'exécution 5G appariés corrigent également la vérification de l'ID de modèle et le chemin de programmation de l'ID de modèle de LK.
| Indicateur de modèle | Artefact d'exécution | Firmware d'exécution | ID de modèle | EVT | Rollback | Testé |
|---|---|---|---|---|---|---|
G780F | G780F | G780FXXSOFYJ1 | 0x154 | 11 | 24 | ❌ |
G980F | G981B | G981BXXSNHYB1 | 0x143 | 11 | 23 | ✅ |
G981B | G981B | G981BXXSNHYB1 | 0x13D | 11 | 23 | ❌ |
G985F | G986B | G986BXXSNHYB1 | 0x142 | 11 | 23 | ✅ |
G986B | G986B | G986BXXSNHYB1 | 0x13C | 11 | 23 | ✅ |
G988B | G988B | G988BXXSNHYB1 | 0x13E | 11 | 23 | ❌ |
N980F | N981B | N981BXXSIHYH3 | 0x153 | 11 |
Les dix indicateurs de modèle Galaxy S20, S20 FE et Note20 pris en charge disposent d'un
profil de démarrage KVM opt-in uniquement en CLI. Compilez une branche
du noyau Exynos 990
dont le nom contient kvm, et ajoutez --kvm à la commande du modèle exact, par exemple :```bash
python3 exploit/exploit.py --build-sboot --model G985F --no-fuse --kvm
Ce profil supprime le chemin LK H-Arx/UH, demande à EL3 d'entrer dans le noyau à EL2, et applique la table de correctifs du moniteur EL3 déchiffrée/re-chiffrée correspondante. Il reste indisponible pour les modes de flash du bootloader d'origine/altéré. Le centre de contrôle web n'a intentionnellement aucun contrôle KVM. Avec le noyau correspondant et [WindowsInQemu](https://github.com/Creeeeger/WindowsInQemu), Windows peut s'exécuter dans QEMU sur le téléphone à pleine vitesse via KVM.
## Démarrage rapide
Ne traitez pas chaque mode comme une séquence d'installation numérotée. Choisissez un objectif :
| Objectif | Chemin |
|-------------------------------------|----------------------------------------------------------------------------------------------------------------------------|
| Installer une ROM personnalisée signée | Modèle/config exact → EUB → chaîne temporaire `--signed --no-fuse` → flasher la sortie signée complète de la ROM → premier démarrage UFS |
| Tester l'exploit | Optionnel `--prepare --no-fuse` → EUB → `--signed --no-fuse` → arrêt |
| Développer la chaîne de démarrage (CLI uniquement) | Test temporaire no-fuse → construire → flasher les SBoot/TZSW/LDFW générés → UFS |
| Extraction / récupération | Utiliser son flux de travail séparé et ses vérifications d'état de fusible |
`--prepare` est un essai à blanc recommandé, pas un prérequis obligatoire : `--signed`
répète la vérification préalable. La commande Heimdall en trois parties générée est un outil de développement de chaîne de démarrage ; ce n'est pas un flash de ROM personnalisée.
Lisez [USER_GUIDE.md](https://github.com/creeeeger/cve-2024-56426/blob/exynos990/USER_GUIDE.md) et choisissez son flux de travail correspondant avant de toucher à un appareil. Il inclut la remise de la ROM complète ainsi que les règles de récupération pour les états non-fusible, fusible et incertain.
## Interface utilisateur locale optionnelle
L'interface navigateur utilise uniquement la bibliothèque standard de Python et appelle la CLI existante
`exploit/exploit.py`. Le développement de la chaîne de démarrage et sa commande Heimdall en trois parties générée restent des outils
exclusivement en terminal.
Démarrez-la depuis la racine du dépôt :```bash
python3 exynos990_control_center.py
Le lanceur se lie à 127.0.0.1, génère un nouveau jeton d'accès, affiche l'URL locale complète et l'ouvre dans le navigateur
par défaut. Utilisez --no-browser lorsqu'un navigateur ne doit pas être ouvert automatiquement :```bash
python3 exynos990_control_center.py --no-browser
L'interface fournit :
- des vérifications vertes/rouges des dépendances et des ressources du dépôt ;
- un choix global de modèle cible et exactement deux décisions de fusion : Rester non fusionné ou Fusionner ;
- un sélecteur de flux de travail qui n'affiche et ne numérote que les étapes du flux sélectionné ;
- les flux de travail d'installation du ROM, de test d'exploit, de dump du BootROM et de restauration du stock ;
- une action de chargeur altéré spécifique au modèle qui valide l'UH et le flashe dans l'emplacement BOOTLOADER avec Heimdall pour entrer en
EUB ;
- un avertissement permanent de fusion et l'empreinte SHA-256 configurée de la clé/eFuse ;
- une carte de restauration de la chaîne de démarrage du stock réservée aux appareils non fusionnés, indisponible après avoir choisi Fusionner ;
- la sortie de processus en direct, l'annulation et des marqueurs de vérification par étape.
Elle affiche également un avis KVM Exynos 990 réservé à la CLI, mais n'expose délibérément aucune option KVM ni ne transmet `--kvm` à une
action web.
L'accès USB suit les autorisations du processus qui a lancé le centre de contrôle. Configurez les autorisations udev/pilote fournies
avant de le démarrer. L'interface ne demande, ne conserve ni ne transmet d'identifiants de privilèges. Gardez l'URL du jeton imprimée
privée et arrêtez le serveur immédiatement après utilisation.
Les utilisateurs du terminal peuvent ignorer `exynos990_control_center.py` ; chaque commande CLI documentée ci-dessous reste inchangée et entièrement
prise en charge.
## Exigences
Python 3.10 ou plus récent est requis.
Windows 10/11 (PowerShell natif) :```powershell
.\windows\setup.ps1
. .\windows\activate.ps1
python .\exploit\exploit.py --prepare --model G985F --no-fuse
L'installation configure une chaîne d'outils native AArch64 épinglée, LZ4, Heimdall et un environnement virtuel du dépôt, puis compile toutes les charges utiles. Le pilote WinUSB BootROM est une option explicite réservée à l'administrateur, car son certificat auto-signé en amont modifie les magasins de confiance de la machine. Consultez WINDOWS.md pour la configuration complète, l'installation du pilote, la distinction du mode Download, la vérification et le processus de dépannage.
Après l'activation de Windows, utilisez python partout où les exemples multiplateformes restants affichent python3.
Linux :```bash sudo apt-get update sudo apt-get install -y gcc-aarch64-linux-gnu binutils-aarch64-linux-gnu lz4
macOS :```bash
brew tap messense/macos-cross-toolchains
brew install aarch64-unknown-linux-gnu lz4
Les modes de préparation, de signature et de charges utiles exécutent le même pré-vol conscient du modèle :
exploit/extra/images/<model>/ par une copie propre des images fragmentées chiffrées intactes.--no-fuse, générer d'abord une copie TSV effective avec les
cinq lignes de fusion désactivées. Avec --kvm, activer également les lignes LK marquées kvm, déchiffrer et corriger le
TSV du moniteur EL3 correspondant, puis rechiffrer sa région protégée.mem.bin, loader.bin et Exynos990_boot_custom_key.bin.Le processus s'arrête à la première incohérence de firmware, de correctif, de métadonnées ou de signature. Il ne corrige jamais les répertoires sources immuables en place.
Toutes les commandes nécessitent --model.
--no-fuse est un modificateur, pas un mode autonome. Il désactive cinq lignes OTP identifiées à clé personnalisée lors de la reconstruction du
LK de travail. Utilisez-le pour chaque commande qui prépare, envoie ou construit une chaîne de développement non fusionnée. Il n'annule pas une
fusion existante.
Le CLI accepte le modificateur avec les modes UFS et dump car ces commandes exécutent également le pré-vol, mais leurs opérations USB
ne transmettent pas le LK reconstruit. Le LK déjà flashé sur le téléphone détermine le comportement de fusion UFS. Par conséquent, l'interface
ne propose délibérément aucun contrôle de non-fusion pour le mode UFS ou dump BootROM. Les deux modes de flash du chargeur de démarrage rejettent --no-fuse
car ils n'effectuent aucune correction ou signature LK.
--kvm est également un modificateur. Il est accepté avec chaque flux de travail exact au modèle qui exécute le pré-vol. Les lignes KVM dans les TSV sont
ignorées sauf si ce drapeau est présent, et l'interface navigateur ne le fournit jamais.
Exemple :```bash python3 exploit/exploit.py --signed --model N986B --no-fuse
Générez le bootloader signé correspondant sans ouvrir l'USB :```bash
python3 exploit/exploit.py --build-sboot --model N986B --no-fuse
La commande reconstruit le répertoire d'images du modèle à partir d'entrées stock propres, applique le correctif LK, signe et vérifie chaque composant, fusionne sboot.bin, vérifie les composants intégrés et la fin, et affiche sa taille, son SHA-256, ainsi qu'une commande Heimdall qui envoie sboot.bin, tzsw.img signé et ldfw.img signé.
Uniquement sur un appareil connu pour être non fusionné, restaurez la chaîne de démarrage stock exacte à partir du tar BL d'origine du modèle sélectionné :```bash python3 exploit/exploit.py --flash-stock --model N986B --wait
La commande extrait uniquement `sboot.bin.lz4`, `tzsw.img.lz4` et
`ldfw.img.lz4`, les décompresse dans un répertoire temporaire, vérifie que les trois sorties sont présentes et non vides, puis
invoque une opération de flash Heimdall. Les fichiers temporaires sont supprimés ensuite. `--no-reboot` et `--verbose` sont également
pris en charge. Le téléphone doit déjà être dans un mode de téléchargement compatible Heimdall, et le modèle sélectionné doit correspondre exactement
à l'appareil physique.
Cela ne restaure pas Android, AP, modem, CSC, userdata ni une ROM stock complète. Ne l'exécutez jamais sur un appareil
fusionné avec une clé personnalisée. Un tel téléphone nécessite un logiciel basé sur la ROM stock re-signé avec la clé de fusion exacte ; la racine de confiance personnalisée reste
permanente. Si l'état de la fusion est inconnu, arrêtez-vous.
## Note de récupération FRP / PERSISTENT
> [!CAUTION]
> Cette procédure est réservée à un appareil que vous possédez personnellement et que vous êtes
> autorisé à réparer. Son utilisation sur l'appareil d'une autre personne est strictement
> interdite. Un mauvais chemin de partition peut entraîner une perte de données définitive ou laisser
> l'appareil incapable de démarrer. Sauvegardez la partition cible et vérifiez son chemin
> de périphérique bloc résolu et sa taille avant d'écrire quoi que ce soit.
Ce dépôt ne supprime pas automatiquement la protection de réinitialisation d'usine (FRP). Sur les appareils qui utilisent le
`PersistentDataBlockService` d'Android, l'état FRP est stocké dans la partition communément nommée `PERSISTENT`. Voir
[l'implémentation AOSP](https://android.googlesource.com/platform/frameworks/base/+/bc56632da95b/services/core/java/com/android/server/PersistentDataBlockService.java).
Après que la chaîne d'exploitation a démarré une récupération personnalisée fournissant `adb` et
`dd`, identifiez et sauvegardez la partition. Ne substituez pas un chemin de périphérique bloc numérique deviné :```bash
adb shell ls -l /dev/block/by-name/PERSISTENT
adb shell dd if=/dev/block/by-name/PERSISTENT of=/tmp/PERSISTENT.backup.img bs=4096
adb pull /tmp/PERSISTENT.backup.img
Uniquement après que la sauvegarde a été récupérée, mettez à zéro la partition et laissez Android initialiser une nouvelle structure de bloc de données persistantes :```bash adb shell dd if=/dev/zero of=/dev/block/by-name/persistent reboot
Cette méthode est testée et fonctionne, FRP est supprimé et l'appareil est déverrouillé.
## Correctifs LK
La sélection des correctifs suit le mappage des artefacts :```text
G780F -> lk_g780f_selected_patches.tsv
G980F -> lk_g980f_selected_patches.tsv (applied to G981B LK)
G981B -> lk_g981b_selected_patches.tsv
G985F -> lk_g985f_selected_patches.tsv (applied to G986B LK)
G986B -> lk_g986b_selected_patches.tsv
G988B -> lk_g988b_selected_patches.tsv
N980F -> lk_n980f_selected_patches.tsv (applied to N981B LK)
N981B -> lk_n981b_selected_patches.tsv
N985F -> lk_n985f_selected_patches.tsv (applied to N986B LK)
N986B -> lk_n986b_selected_patches.tsv
Valider un TSV par rapport au LK standard sans le modifier :```bash
python3 external/tools/apply_lk_patches.py
bootLoaderFiles/sbootSplitParts_original/G986B/lk.bin
external/ghidra/lk_g986b_selected_patches.tsv
--check
`external/ghidra/ApplyLkPatches.java` accepte le même format TSV à six colonnes et échoue désormais en cas de non-correspondance des octets anciens
au lieu d'appliquer un correctif à l'aveugle. Les lignes dont la première colonne est `kvm` nécessitent un argument de script supplémentaire `--kvm`.
Les lignes héritées `check_signature` et `check_ext4_signature` qui renvoient zéro utilisent le
profil `0` : elles documentent les anciens emplacements de contournement mais ne sont délibérément pas
appliquées, de sorte que les images construites doivent satisfaire aux véritables vérifications de signature Samsung de LK.
## Signature
`external/tools/sign_sboot_images.py` nécessite un modèle et dérive l'ID du modèle, l'EVT et la révision de rollback à partir de
[model_data.py](https://github.com/creeeeger/cve-2024-56426/blob/exynos990/external/tools/model_data.py) :```bash
python3 external/tools/sign_sboot_images.py \
--images-dir exploit/extra/images/G986B \
--keys-dir external/keys/exynos9830_crecker \
--model G986B
Les signatures Stage2 sont vérifiées après la signature. L'outil ne régénère pas les métadonnées AVB Samsung pour ldfw.img ou
tzsw.img ; modifier les octets de démarrage sécurisé dans ces wrappers nécessite toujours la politique AVB distincte utilisée par le flux de démarrage
cible. Une ROM signée complète doit utiliser le modèle AVB exact et le même ensemble de clés, puis être flashée avec son
package généré complet. Voir le
dépôt CreckerROM
et le flux d'installation dans USER_GUIDE.md.
Les packages altérés inclus préservent chaque membre BL d'origine, sauf
sboot.bin.lz4. Ce membre est supprimé et le uh.bin décompressé du package
est stocké sous le nom sboot.bin, correspondant à la disposition déclenchant EUB.
L'interface peut effectuer directement le flux Heimdall correspondant. Elle sélectionne l'archive altérée du modèle physique exact,
vérifie que sboot.bin est octet pour octet identique au uh.bin.lz4 décompressé, et flashe la charge utile UH validée vers le
slot BOOTLOADER :```bash
python3 exploit/exploit.py --flash-tampered --model G986B --wait
Cela empêche volontairement le démarrage normal et force le prochain démarrage en EUB. Cela ne flashe pas les membres restants du
tar BL.
Régénérez un package avec :```bash
python3 external/tools/build_tampered_loader.py \
bootLoaderFiles/originalBl/G986B/BL_G986BXXSNHYB1.tar \
bootLoaderFiles/tamperedLoader/G986B/BL_G986BXXSNHYB1_tampered.tar
Utilisez le chargeur altéré du modèle physique exact lorsque son répertoire est présent. Le mappage d'exécution couplé s'applique à la vérification préalable et à la signature de l'exploit, et non à la sélection du package BL d'origine/altéré archivé.
Gardez à l'esprit que si vous avez fusionné l'appareil, vous devrez flasher un uh.bin signé sur votre partition BOOTLOADER, car le uh d'origine est actuellement signé avec la mauvaise clé.
Diviser et fusionner :```bash python3 exploit/split.py sboot.bin -o /tmp/G986B-splits python3 exploit/merge.py /tmp/G986B-splits
Le fusionneur autonome nécessite `tzsw.img` et `ldfw.img` dans le répertoire des parties et affiche la commande Heimdall en trois parties correspondante. N'utilisez cette commande que lorsque ces deux images ont déjà été signées pour le modèle sélectionné ;
`--build-sboot` effectue et vérifie cette signature automatiquement.
Extraire les enregistrements LDFW individuels :```bash
python3 external/tools/extract_ldfw.py ldfw.img -o LDFWs
La disposition de fractionnement fournie reconstruit chaque sboot.bin canonique d'origine
octet par octet. Le déchiffrement/re-chiffrement EPBL et EL3 monitor effectue également un aller-retour octet par octet pour toutes les familles de firmware lorsque
l'en-tête EPBL reste inchangé.
Tous les téléphones pris en charge partagent le même BootROM Exynos 990. Les charges utiles utilisent des points d'entrée BootROM communs et des adresses IRAM plutôt que des décalages LK spécifiques au modèle. Les binaires générés pointent vers ces points d'entrée :
Le comportement spécifique au modèle est limité au TSV LK, à l'ID de modèle FWBL1 et à la révision de rollback d'origine.
halal-beef), via
halal-beef/hubble : le code backend utilisé par exploit/exploit.py ; la disposition
SoC utilisée par exploit/split.py et
exploit/merge.py ; et run_exploit(), qui implémente l'opération d'adresse/écrasement.VDavid003/exynos-usbdl : le squelette de charge utile à partir duquel la charge utile
à clé personnalisée Exynos990 a été dérivée.18 |
| ❌ |
N981B | N981B | N981BXXSIHYH3 | 0x14E | 11 | 18 | ❌ |
N985F | N986B | N986BXXSIHYH3 | 0x152 | 11 | 18 | ❌ |
N986B | N986B | N986BXXSIHYH3 | 0x14D | 11 | 18 | ❌ |
| Chemin | Objectif |
|---|
bootLoaderFiles/originalBl/<model>/ | Paquets BL_<firmware>.tar propres et exacts au modèle pour les dix modèles. |
bootLoaderFiles/sbootSplitParts_original/<model>/ | Fragments SBoot chiffrés exacts au modèle intacts, ldfw.img, tzsw.img, manifeste et fin. |
bootLoaderFiles/exynos9830Decrypted/<model>/ | Fichiers d'analyse EPBL, EL3, TZSW et LDFW déchiffrés exacts au modèle. |
bootLoaderFiles/tamperedLoader/<model>/ | Paquets BL déclenchant l'EUB exacts au modèle. |
bootLoaderFiles/MODEL_COMPARISON.md | Comparaison firmware exact versus couplé et notes de compatibilité des correctifs. |
bootLoaderFiles/exynos990Bootrom/ | Dump partagé du BootROM Exynos 990. |
bootromNotes/ | Notes partagées sur le flux BootROM et le contexte USB. |
drivers/windows/winusb/ | Paquet WinUSB Houston épinglé pour BootROM/EUB 04e8:1234. |
windows/ | Configuration Windows native, activation de l'environnement et installateur de pilote avec vérification de hachage. |
exploit/extra/images/<model>/ | Sortie de pré-vol jetable spécifique au modèle. |
external/ghidra/ | TSV LK et KVM EL3 exacts au modèle plus le script de correctif Ghidra. |
external/decompiled_G985F/ | Fichiers de référence décompilés réservés au G985F. |
exynos990reverseEng_G985F/ | Projet Ghidra réservé au G985F. |
external/keys/exynos9830_crecker/ | Bundle de clés personnalisées partagé. |
exploit/exploit.py | Point d'entrée CLI stable et coordinateur de flux de travail. |
exploit/build_payloads.py | Générateur de charges utiles natif multiplateforme utilisé par le pré-vol sur Windows, Linux et macOS. |
exploit/preflight.py | Préparation de l'image de travail, correction LK, signature et vérification de fusion. |
exploit/usb_transport.py | Cadrage PyUSB, découverte d'appareils, écrasement et transport de dump. |
exploit/tampered_loader.py | Extraction UH exacte au modèle, validation du chargeur altéré et flash EUB Heimdall. |
exploit/stock_restore.py | Extraction d'archive stock exacte au modèle et construction de commande Heimdall. |
control_center/ | Actions backend navigateur, vérifications de dépendances, tâches et API HTTP. |
external/tools/*_crypto.py | Primitives AES et ECDSA de codage/signature EPBL/EL3 partagées. |
| Mode | Objectif |
|---|
--prepare | Exécuter le pré-vol sans ouvrir l'USB. |
--build-sboot | Exécuter le pré-vol et construire un sboot.bin signé et vérifié dans le répertoire d'images du modèle. |
--signed | Envoyer la charge utile à clé personnalisée et la chaîne de démarrage signée depuis l'EUB. |
--ufs | Démarrer le chemin de démarrage UFS avec loader.bin. |
--dump | Exécuter mem.bin et dumper 0x20000 octets du BootROM. |
--flash-tampered | Valider l'UH exacte au modèle et la flasher vers BOOTLOADER pour forcer l'EUB. |
--flash-stock | Extraire et flasher le SBoot, TZSW et LDFW stock exacts au modèle depuis le tar BL d'origine. |
| Image | Clé de signature personnalisée |
|---|
fwbl1.img | Clé privée BL1 plus blobs publics Stage2 TEE/REE |
epbl.img, el3_mon.img | Stage2 TEE |
bl2.img, lk.bin | Stage2 REE |
ldfw.img, tzsw.img | Stage2 TEE, pieds de page Stage2 internes et externes |
| Charge utile | Saut d'exploitation | Entrée liée |
|---|
mem.bin | 0x02022010 | 0x02022010 |
loader.bin | 0x02022010 | 0x02022010 |
Exynos990_boot_custom_key.bin | 0x02022000 | étape 1 indépendante de la position |
| Partie | Début | Fin |
|---|
fwbl1.img | 0x000000 | 0x003000 |
epbl.img | 0x003000 | 0x016000 |
bl2.img | 0x016000 | 0x082000 |
lk.bin | 0x0DB000 | 0x35B000 |
el3_mon.img | 0x35B000 | 0x39B000 |
| Étape | Adresse de chargement |
|---|
| BL1 | 0x02022000 |
| EPBL | 0x02026000 |
| BL2 | 0x15600000 |
| LK | 0xE8000000 |
| Moniteur EL3 | 0xBFE80000 |