Return to Video

#days: Ange Albertini: Such a weird processor - messing with x86 opcodes

  • 0:05 - 0:10
    Quel processeur bizarre - faire des misères au x86... et un peu de PE [Portable Executable]
  • 0:10 - 0:19
    Bienvenue... et surtout, dites-moi si je vais trop vite
  • 0:19 - 0:28
    Je vais parler des opcodes, et un peu du format PE et de leurs bizarreries
  • 0:28 - 0:35
    Je fais du reverse depuis quelque temps. J'ai créé un projet appelé Corkami.
  • 0:35 - 0:42
    Dans le passé, j'ai participé à Mame, l'émulateur Arcade, et professionnellement, analyste de virus,
  • 0:42 - 0:48
    mais je suis ici à titre personnel, ce sont mes propres expériences à la maison.
  • 0:48 - 0:57
    Donc, je viens de mentionner Corkami. C'est le nom du projet de mon projet de reverse [rétro-ingénierie]
  • 0:57 - 1:03
    Je n'y parle que de choses techniques, pas de pubs, pas de login requis
  • 1:03 - 1:06
    Directement le pur jus.
  • 1:06 - 1:12
    J'essaie de le maintenir à jour, et util. J'ai créé des fiches pense-bêtes et d'autre documents
  • 1:12 - 1:15
    que j'utilise moi-même au boulot, au quotidien
  • 1:15 - 1:18
    mais c'est juste un loisir. je commence quand les enfants sont couchés
  • 1:18 - 1:23
    tard dans la nuit, donc ça n'a probablement pas le polish professionnel
  • 1:23 - 1:25
    que j'aimerais qu'il ait.
  • 1:25 - 1:30
    Actuellement, Corkami est un wiki et des pense-bêtes
  • 1:30 - 1:37
    et je me focalise sur la création de preuves de concepts [démonstration d'hypothèse, "proof of concept] [Tiens, salut Bob!]
  • 1:37 - 1:42
    donc les binaires sont fait-main, d'habitude je n'utilise pas de compilateurs, je créé la structure du PE à la main
  • 1:42 - 1:46
    pour que ce soit focalisé sur le point pertinent
  • 1:46 - 1:49
    et qu'on est pas de parasites. on n'a probablement pas besoin d'IDA
  • 1:49 - 1:51
    pour comprendre ce qui se passe
  • 1:51 - 1:54
    car je me concentre uniquement sur ce qui est important.
  • 1:54 - 1:58
    Les binaires sont directement téléchargeables pour que vous puissiez
  • 1:58 - 2:01
    tester avec votre débogueur, vos outils, vos connaissances,
  • 2:01 - 2:03
    directement.
  • 2:03 - 2:07
    pour l'instant, je me suis concentré sur le PDF, l'assembleur et le format PE
  • 2:07 - 2:11
    quelques autres trucs, mais ce sont les sujets les plus approfondis
  • 2:11 - 2:15
    du site, et je partage tout ça avec une licence
  • 2:15 - 2:19
    très permissive, BSD, donc vous pouvez réutiliser commercialement
  • 2:19 - 2:24
    Même les images sont en format ouvert.
  • 2:24 - 2:29
    Donc, la raison de cette présentation... il y a quelque temps,
  • 2:29 - 2:32
    J'étais jeune et innocent, et je pensais que les CPUs, fait de transistors,
  • 2:32 - 2:38
    était parfaitement logique
  • 2:38 - 2:41
    et ensuite, un virus m'a piégé... simplement,
  • 2:41 - 2:46
    IDA était rendu inutile. Donc j'ai décidé de repartir à zéro
  • 2:46 - 2:49
    et d'étudier l'assembleur et le PE du début.
  • 2:49 - 2:52
    j'ai écrit en chemin des documents, partagés sur Corkami
  • 2:52 - 2:57
    et maintenant je vous présente le résultat plus ou moins final,
  • 2:57 - 3:01
    ou du moins quelques buts atteints. Si j'étais juste un gars qui a étudié l'assembleur
  • 3:01 - 3:05
    je ne serais probablement pas en train de présenter ici,
  • 3:05 - 3:10
    à moins d'avoir eu quelques résultats avec certains outils.
  • 3:10 - 3:13
    Donc, pour résumer, j'ai trouvés des bogues dans tous les désassembleurs que j'ai essayé
  • 3:13 - 3:22
    et j'ai aussi obtenus quelques plantages. J'insiste que tous les auteurs ont été contactés
  • 3:22 - 3:26
    et que la plupart des problèmes ont déjà été corrigé,
  • 3:26 - 3:30
    mais en tout cas, en version 6.1, il plante directement, mais dans la version 6.2
  • 3:30 - 3:33
    c'est corrigé.
  • 3:33 - 3:37
    et la dernière version de Hiew [Hacker's view] (enfin, pas la dernière publique)
  • 3:37 - 3:41
    corrige ça aussi.
  • 3:41 - 3:44
    Donc, pour cette présentation, je commencerais facile,
  • 3:44 - 3:50
    je pars du principe que vous êtes tous habitués à l'assembleur ?
  • 3:50 - 3:57
    Oui. et vous êtes tous habitués, ou
  • 3:57 - 4:02
    vous avez déjà rencontré des cas d'opcodes non documentés?
  • 4:02 - 4:06
    Genre vous faites confiance à IDA, point barre.
  • 4:06 - 4:10
    Est-ce habituel de voir quelque chose non géré par IDA ?
  • 4:10 - 4:14
    Levez les bras... ok, pas tant que ça.
  • 4:14 - 4:19
    Bon, après l'introduction en accéléré,
  • 4:19 - 4:25
    Je parlerais de quelques techniques, puis présenterai CoST, mon programme
  • 4:25 - 4:28
    et je parlerais aussi un peu du format PE
  • 4:28 - 4:34
    Bon, vous connaissez tous l'assembleur, on va survoler ...
  • 4:34 - 4:37
    Donc, on compile un binaire, il y a de l'assembleur, il y a
  • 4:37 - 4:44
    un rapport, des points communs entre le code source et l'assembleur généré...
  • 4:44 - 4:48
    et bien sûr, une relation entre langage machine et les opcodes
  • 4:48 - 4:53
    ce qui est important est que l'assembleur est généré par le compilateur, mais ce qui reste
  • 4:56 - 4:59
    dans le binaire, sont uniquement les opcodes, qui sont interprétés
  • 4:59 - 5:03
    directement par le processeur, ce qui implique qu'il sache quoi faire avec,
  • 5:03 - 5:07
    il s'en fiche si vous ou vos outils
  • 5:07 - 5:10
    ne savent pas ce qui va arriver. il le fait, tout simplement.
  • 5:10 - 5:16
    Et le problème, c'est que d'habitude, on ne lit pas les opcodes directement, mais le désassemblage
  • 5:16 - 5:20
    donc si le désassemblage échoue, on est bloqué
  • 5:20 - 5:25
    on est aveugle, on ne sait pas ce qui va s'exécuter
  • 5:25 - 5:28
    l'autre problème est comme les instructions sont de longueurs variables
  • 5:28 - 5:30
    on ne sait pas ou la suivante commence
  • 5:30 - 5:32
    donc même la suite est inconnue.
  • 5:32 - 5:40
    Donc, on créé une seule instruction non documentée dans un programme simple
  • 5:40 - 5:48
    on utilise le mot-clef 'emit' -- c'est Visual Studio 2010 ultimate --
  • 5:48 - 5:52
    et on obtient un octet non identifié au désassemblage
  • 5:52 - 5:58
    on a des juste points d'interrogations.
  • 5:58 - 6:01
    et donc, même si Visual Studio coûte plusieurs milliers d'euros
  • 6:01 - 6:05
    il ne sait pas ce qui va se produire....
  • 6:05 - 6:09
    et si on regarde les documentations Intel
  • 6:09 - 6:14
    circulez, il y a rien a voir... l'opcode D6... inconnu au bataillon
  • 6:14 - 6:17
    Microsoft n'a rien à dire, Intel non plus,
  • 6:17 - 6:21
    donc d'habitude, si vous essayez des choses comme ça, attendez-vous au pire.
  • 6:21 - 6:26
    Donc, aucune information... en général, ça annonce un plantage...
  • 6:26 - 6:29
    mais dans ce cas particulier, aucun problème...
  • 6:29 - 6:35
    nous ne savons pas ce qui se passe, si on regarde les docs Intel et Microsoft, on n'en sait pas plus.
  • 6:35 - 6:41
    Mais le CPU a juste fait son boulot dans son coin. Ce qui s'est passé est qu'en fait
  • 6:41 - 6:49
    D6 est un opcode très simple, qui ne fait pas grand chose, mais pas documenté par Intel,
  • 6:49 - 6:53
    par contre, il l'est par AMD, et la plupart le sont aussi également, par AMD mais pas Intel
  • 6:53 - 6:58
    aucune idée pourquoi. si quelqu'un le sait...
  • 6:58 - 7:04
    c'est un opcode pourtant trivial, pourtant... 'y a rien à voir, continuez votre chemin'
  • 7:04 - 7:08
    Il est utilisé souvent... l'utilisation habituelle de tels opcodes sont les virus et les packeurs
  • 7:08 - 7:13
    pour éviter les analyses automatisées où trop facile.
  • 7:13 - 7:22
    Ce qui est ironique, c'est que si vous regardez la doc, elle est pleine de trous. mais le désassembleur d'Intel,
  • 7:22 - 7:25
    Xed, qui est gratuit mais pas ouvert, gère tous ces opcodes sans problème...
  • 7:25 - 7:35
    Alors que Microsoft, Visual Studio, et WinDBG, suivent la documentation aveuglément
  • 7:35 - 7:43
    Donc vous obtiendrez des points d'interrogation alors qu'Intel sait très bien ce qui se passe
  • 7:43 - 7:52
    'faites ce que je fais, pas ce que je dit'
  • 7:52 - 8:01
    donc, bien sûr, vous me direz que WinDbg est fait uniquement ce qui est généré
  • 8:01 - 8:08
    par les compilateurs Microsoft, mais ça exclut WinDBG comme outil d'analyse de virus:
  • 8:08 - 8:17
    vous rajoutez D6, trivial, et WinDbg est muet.
  • 8:17 - 8:25
    pas génial
  • 8:25 - 8:32
    un autre problème est que toutes ses choses non documentées
  • 8:32 - 8:37
    sont peut-être présentes, l'une dans un virus,
  • 8:37 - 8:42
    l'autre dans un packeur, etc... donc il n'est pas facile
  • 8:42 - 8:46
    de trouver un bon regroupement de tels fichiers pour rassembler toutes ces informations
  • 8:46 - 8:50
    donc par exemple,
  • 8:50 - 8:53
    quelqu'un vous parle d'une astuce
  • 8:53 - 8:55
    et vous dit qu'elle est enfouit dans MebRoot (un virus costaud)
  • 8:55 - 8:58
    donc vous êtes obligé de creuser pour voir juste la partie qui vous intéresse
  • 8:58 - 9:03
    et en plus, on sait que c'est un virus, donc ca ne circule pas facilement,
  • 9:03 - 9:08
    et il y a plein de trucs dedans qui n'ont rien à voir dedans,
  • 9:08 - 9:15
    avant ou après ce qui vous intéresse. Donc c'est le fossé que je veux remplir en fournissant
  • 9:15 - 9:21
    un groupe de fichier à la fois simple et complet, et focalisé.
  • 9:21 - 9:27
    Donc, on commence. enfin, du vrai, quelques opcodes non documentés.
  • 9:27 - 9:37
    Mais avant d'avoir commencé à étudier, je me suis demandé quelles étaient les vrais capacités
  • 9:37 - 9:44
    des processeurs, quelles instructions existent vraiment.
  • 9:44 - 9:52
    C'est un peu comme l'anglais: la plupart de la population mondiale comprend ces mots, et
  • 9:52 - 9:57
    si vous avez déjà désassemblé quelque chose, vous êtes habitués à ces instructions
  • 9:57 - 10:04
    tous les compilateurs les utilisent. elles sont tellement répandues que si elles sont absentes,
  • 10:04 - 10:08
    on se sent pris au dépourvu.
  • 10:08 - 10:19
    mais les processeurs Intels datent des années 70. Donc,
  • 10:19 - 10:27
    comme l'anglais de Shakespeare, vous voyez que c'est de l'anglais... mais, ça veut dire quoi en fait ?
  • 10:27 - 10:30
    d'ailleurs, j'ai déjà oublié
  • 10:30 - 10:36
    ces instructions sont toutes gérées par tous nos processeurs, pourtant, on n'a plus l'habitude de les lire
  • 10:36 - 10:41
    c'est plus que génant
  • 10:41 - 10:46
    En fait, j'ai écrit un exemple qui n'utilisent que ces vieilles instructions, qui font vraiment quelque chose
  • 10:46 - 10:53
    donc si vous vous sentez ici comme chez vous, je voudrais vous demander 'quel âge avez-vous ?'
  • 10:53 - 10:59
    parce que même moi, j'ai l'habitude de PUSH/JUMP/CALLs, mais ça, euhh...
  • 10:59 - 11:05
    pourtant, ça marche même sur un i7, et c'est utilisable par les virus,
  • 11:05 - 11:13
    les packeurs, etc... pourtant, la plupart est complètement inutilisée de nos jours, bien que parfaitement
  • 11:13 - 11:15
    gérées par nos processeurs modernes.
  • 11:15 - 11:21
    Et, tel l'anglais, c'est une langue qui évolue, et les générations précédentes
  • 11:21 - 11:27
    n'ont pas l'habitude des derniers mots à la mode.
  • 11:27 - 11:35
    Ces instructions sont parfois présentes sur les processeurs les plus récent. en une seule instruction, on fait
  • 11:35 - 11:41
    un CRC32, on décrypte l'AES, on compare des chaînes, ou d'autres opérations complexes.
  • 11:41 - 11:47
    Donc, c'est possible sur un processeur moderne. pas tous, bien sûr.
  • 11:47 - 11:54
    une que j'aime bien est MOVBE -- move big endian -- parce que c'est le vilain petit canard du lot...
  • 11:54 - 12:01
    uniquement implémentée sur les processeurs Atom, donc comme ce netbook, qui la gère...
  • 12:01 - 12:09
    alors qu'un i7 64-bits ne l'a pas, même si lui aura CRC32, peut-être AES, etc...
  • 12:09 - 12:12
    donc, tant pis pour la retro-compatibilité
  • 12:12 - 12:20
    à ma connaissance, il n'y existe aucun processeur qui gère à la fois CRC32 et MOVBE.
  • 12:20 - 12:24
    De plus, MOVBE est un peu inutile car il fait la même chose que MOV et BSWAP réunit...
  • 12:24 - 12:32
    donc, bizarre. en tout cas, ce mini-PC a une instruction que la plupart des PC n'ont pas
  • 12:32 - 12:35
    Pourquoi ? quelqu'un sait?
  • 12:35 - 12:37
    [Auditeur:] "cette instruction est documentée ?"
  • 12:37 - 12:38
    oui
  • 12:38 - 12:42
    totalement documentée officiellement
  • 12:42 - 12:46
    [Auditeur:] "Mais, c'est un drapeau du processeur juste pour cette instruction, ou implicitement lié au
  • 12:46 - 12:51
    processeurs Atom ?
  • 12:51 - 12:58
    mmm, je ne sais pas. je vérifie la valeur par CPUID, mais j'ai oublié la définition exacte.
  • 12:58 - 13:07
    il y a tant d'informations données par CPUID que j'ai vite oublié.
  • 13:07 - 13:13
    Autre chose, spécifique à Windows, car je m'intéresse aux virus...
  • 13:13 - 13:22
    avant d'exécuter quoi que ce soit, je me demandais quelle était la valeur initiale de chaque registre
  • 13:22 - 13:28
    quand le programme démarre.
  • 13:28 - 13:33
    et ça vous donne en fait de l'information fiable, qu'on retrouve utilisée par les virus
  • 13:33 - 13:40
    donc par exemple, au démarrage, EAX vous dit si vous êtes sur un OS ancien (XP ou avant)
  • 13:40 - 13:42
    ou plus récent, Vista ou 7.
  • 13:42 - 13:50
    de même, ce n'est pas utilisé par les virus à mon souvenir, mais si GS est nul, on est dans un OS 32 bits
  • 13:50 - 13:54
    sinon, sur un 64b.
  • 13:54 - 13:56
    J'utilise ça régulièrement, on le verra plus tard.
  • 13:56 - 14:04
    De même, la relation entre les registres n'est pas forcément évidente. il y en a beaucoup,
  • 14:04 - 14:10
    et j'ai été surpris qu'une instruction à virgule flottante (FPU) change le statut (FST), les registres
  • 14:10 - 14:18
    eux-mêmes (STx), les registres MMx aussi, mais en plus, toutes les documentations en ligne associent
  • 14:18 - 14:24
    ST0 et MM0, ce qui semble logique, alors qu'en fait, une seule instruction modifie
  • 14:24 - 14:31
    non pas MM0, mais MM7, dans l'autre sens.
  • 14:31 - 14:36
    donc après une instruction comme "load PI" [FLDPI] on regarde la valeur de MM7,
  • 14:36 - 14:39
    ça peut-être utilisé comme astuce simple.
  • 14:39 - 14:45
    alors que toutes les documentations, Wikipedia ou autre, se trompent.
  • 14:45 - 14:53
    quelque chose d'autre qui peut être utilisé comme anti-débogueur sous XP: le FPU modifie aussi CR0
  • 14:53 - 14:59
    donc ça fait une astuce anti-émulateur plutôt inattendue rien qu'avec le FPU.
  • 14:59 - 15:09
    'store machine status word' [SMSW] est une instruction qui date du 286, quand le mode protégé était
  • 15:09 - 15:18
    récent et incomplet, qui permet de lire les valeurs de CR0, même depuis le mode utilisateur.
  • 15:18 - 15:26
    alors que 'MOV CR0' est privilégiée
  • 15:26 - 15:34
    pour une raison inconnue, le mot de poid fort est officiellement non défini.
  • 15:34 - 15:40
    donc à priori, on ne sait pas ce qu'il va contenir,
  • 15:40 - 15:45
    mais en fait il s'agit bien du même mot de poid fort que CR0.
  • 15:45 - 15:52
    et, sous XP, après une instruction FPU, la valeur de CR0 est modifiée, mais reprend sa valeur initiale
  • 15:52 - 16:00
    toute seule par la suite. donc juste avec SMSW, verifier le résultat, puis faire une opération FPU,
  • 16:00 - 16:05
    alors SMSW donnera un résultat différent, mais ensuite, le résultat redeviendra comme à l'origine.
  • 16:05 - 16:11
    un moyen élégant de faire des boucles en apparence infinies. une astuce complexe anti-émulateurs.
  • 16:11 - 16:18
    Une astuce similaire sous Windows 32b, où GS n'est pas stocké dans le CONTEXT, donc quand l'OS passe d'un
  • 16:18 - 16:25
    fil d'exécution à l'autre (thread-switch), GS est remis à zero. Donc, si on attend, quoi qu'on fasse,
  • 16:25 - 16:33
    GS change comme par enchantement. Mais si vous faites du pas à pas, c'est lent, donc l'OS change de fil,
  • 16:33 - 16:40
    et GS est perdu dès l'instruction suivante.
  • 16:40 - 16:45
    De même, si on attend que GS devienne nul, on finira par sortir de la boucle.
  • 16:45 - 16:53
    En tout cas, la première fois, ça défiait mon entendement... sans autres process ou autre, je ne comprenais
  • 16:53 - 16:58
    pas d'où ça venait. Au moins, mon exemple commence dès le début avec ça
  • 16:58 - 17:02
    c'est plus pratique
  • 17:02 - 17:11
    une autre particularité, c'est que ça met du temps pour être remis à zéro. en faisant 2 boucles d'attentes,
  • 17:11 - 17:17
    et mesurant le temps entre les 2 (changement de fil), ça prend somme toute assez longtemps, comparé à une
  • 17:17 - 17:25
    exécution standard. ça fait un anti-émulation solide.
  • 17:25 - 17:33
    Je pensais tout naturellement que NOP était parfait! NOP, c'est NOP, ça ne fait rien, donc, aucun problème !
  • 17:33 - 17:44
    Mais à l'origine, NOP est 'échange ?AX avec lui-même' (xchg ?ax, ?ax) mais c'est le cas pour le NOP encodé 0x90
  • 17:44 - 17:51
    mais il y a un autre encodage de XCHG EAX, EAX, qui ne fait rien non plus en 32b
  • 17:51 - 17:54
    mais, à l'instar de toutes les instructions sur 32b en mode 64b
  • 17:54 - 17:58
    cette instruction remet à zéro le double mot de poid fort
  • 17:58 - 18:02
    donc on a un XCHG EAX [,EAX] qui fait quelque chose.
  • 18:02 - 18:05
    bien qu'initialement il semblerait ne rien faire, de sa relation avec NOP
  • 18:05 - 18:10
    mais heureusement, le NOP 0x90, lui, ne fait toujours rien, un vrai fainéant ;)
  • 18:10 - 18:14
    Celui-ci est maintenant bien répandu,
  • 18:14 - 18:18
    le HINT NOP est un NOP sur plusieurs octets
  • 18:18 - 18:23
    qui indique au processeur ce qui va être exécuté ou accédé ensuite
  • 18:23 - 18:24
    quelque soit l'adresse dans un HINT NOP en mémoire,
  • 18:24 - 18:26
    aucune exception n'est déclenchée
  • 18:26 - 18:32
    mais ...
  • 18:32 - 18:37
    autre chose, il est partiellement non documenté par Intel
  • 18:37 - 18:44
    (comme d'habitude, ce n'est pas le cas avec AMD)
  • 18:44 - 18:48
    en outre, comme c'est une instruction sur plusieurs octets, avec des opérandes immédiates
  • 18:48 - 18:51
    si on met ces octets à la fin d'une page mémoire
  • 18:51 - 18:55
    alors le processeur va vouloir lire l'encodage des opérandes,
  • 18:55 - 18:56
    et ça va déclencher une exception
  • 18:56 - 19:01
    donc c'est un NOP qui peut déclencher une exception en bas de page
  • 19:01 - 19:04
    Merci, Intel
  • 19:04 - 19:07
    MOV également, je croyais...
  • 19:07 - 19:11
    qu'il devrait être parfaitement logique
  • 19:11 - 19:16
    mais, même s'il est documenté, il y a des cas compliqués,
  • 19:16 - 19:19
    qui n'étaient pas parfaitement gérés dans tous les assembleurs que j'ai essayé
  • 19:19 - 19:22
    sauf peut-être Xed
  • 19:22 - 19:29
    on ne peut pas faire un MOV de ou vers CR0 en mémoire,
  • 19:29 - 19:33
    la documentation dit que le Mod/RM est ignoré
  • 19:33 - 19:34
    ce qui ne veut pas dire que l'instruction est invalide
  • 19:34 - 19:35
    simplement, considéré comme n'utilisant pas la mémoire
  • 19:35 - 19:36
    sinon, ça ferait un plantage
  • 19:36 - 19:39
    donc, voici l'équivalent
  • 19:39 - 19:42
    ce qui mettait en tord tous les désassembleurs
  • 19:42 - 19:44
    jusque récemment
  • 19:44 - 19:50
    MOVSXD est une instruction 64b, qui étend un registre
  • 19:50 - 19:55
    donc, d'un registre vers un plus gros
  • 19:55 - 19:58
    mais sans préfixe REX - ce qui n'est pas encouragé,
  • 19:58 - 20:02
    on peut l'utiliser comme un MOV standard, de 32b vers 32b
  • 20:02 - 20:04
    et dans l'autre sens,
  • 20:04 - 20:09
    MOV d'un selecteur à un registre 32b marche sans problème,
  • 20:09 - 20:13
    alors que beaucoup de désassembleurs afficheraient MOV AX, CS, ce qui semble logique
  • 20:13 - 20:16
    niveau taille
  • 20:16 - 20:19
    mais en fait le mot de poid fort du registre cible est 'non défini'
  • 20:19 - 20:21
    mais ici, pas de surprise amusante,
  • 20:21 - 20:25
    ce sont juste des zéros
  • 20:25 - 20:30
    donc c'est équivalent à MOV EAX, CS
  • 20:30 - 20:32
    BSWAP est un de mes favoris
  • 20:32 - 20:35
    parce que je le compare à une administration:
  • 20:35 - 20:38
    il est supposé passer d'un endianisme [endianness] à l' autre
  • 20:38 - 20:42
    mais pour diverses raisons,
  • 20:42 - 20:45
    il ne peut jamais faire son travail correctement
  • 20:45 - 20:50
    donc, c'est juste en 64b que tout se passe
  • 20:50 - 20:51
    comme prévu
  • 20:51 - 20:55
    en 32b, comme toutes les autres instruction 32b
  • 20:55 - 20:59
    le double mot de poid fort est mis à zéro...
  • 20:59 - 21:02
    et sur un mot, il est non défini officiellement,
  • 21:02 - 21:04
    mais il est pourtant utilisé couramment dans les virus et les packeurs
  • 21:04 - 21:07
    car il remet simplement à zéro le registre,
  • 21:07 - 21:09
    comme un simple XOR AX, AX
  • 21:09 - 21:14
    donc, devant un résultat si inexplicable, je comprends
  • 21:14 - 21:18
    qu'Intel ne veuille pas en parler
  • 21:18 - 21:20
    ça serait sûrement gênant de devoir expliquer
  • 21:20 - 21:24
    ce résultat plutôt comique.
  • 21:24 - 21:33
    BSWAP AX est aussi mal géré par WinDbg et les autres
  • 21:33 - 21:35
    on lira BSWAP EAX
  • 21:35 - 21:42
    alors que le registre est remis à zéro... génant
  • 21:42 - 21:47
    tout le monde comprend ce code?
  • 21:47 - 21:53
    quelqu'un voit un piège possible?
  • 21:53 - 21:56
    l'adresse de est empilée
  • 21:56 - 22:00
    puis dépilée par RETN
  • 22:00 - 22:05
    donc, on saute vers une adresse immédiates
  • 22:05 - 22:11
    l'ordre d'exécution ?
  • 22:11 - 22:18
    oui, l'exécution démarre ici
  • 22:18 - 22:20
    non, rien à voir ici
  • 22:20 - 22:26
    voilà OllyDbg 1 - c'est corrigé dans le 2
  • 22:26 - 22:28
    Olly essaie même d'être sympa et de vous dire
  • 22:28 - 22:30
    via un commentaire automatique,
  • 22:30 - 22:33
    que RET sera utilisé comme saut vers
  • 22:33 - 22:36
    et, voyez le résultat, plutôt différent
  • 22:36 - 22:37
    donc, que c'est-il passé ?
  • 22:37 - 22:40
    quelqu'un voit ?
  • 22:40 - 22:43
    donc, RETN a un prefix 66
  • 22:43 - 22:47
    donc, il retourne vers IP (16b), pas EIP
  • 22:47 - 22:56
    donc on ne saute pas vers 401008, mais 00001008
  • 22:56 - 22:58
    et dans mon exemple, la page nulle a été allouée
  • 22:58 - 23:01
    et du code a été placé à 1008
  • 23:01 - 23:06
    donc, ça ne retourne pas vers []
  • 23:06 - 23:10
    mais l'autre problème est que c'est aussi appelé un RETN
  • 23:10 - 23:15
    bien que ce soit différent. les désassembleurs ont leur propre façon de l'afficher
  • 23:15 - 23:19
    tel que 'small retn', 'ret.16', ou autre
  • 23:19 - 23:22
    mais officiellement, c'est la même instruction qu'un RETN standard.
  • 23:22 - 23:28
    donc, le dernier Hiew, et OllyDbg 1
  • 23:28 - 23:31
    peut-être pas le 2
  • 23:31 - 23:33
    mais on peut se faire avoir
  • 23:33 - 23:41
    et le préfixe 66 a le même role avec CALLs, RETs, LOOPs, JMPs
  • 23:41 - 23:45
    toutes les instructions contrôlant le flux d'exécution
  • 23:45 - 23:48
    je ne vais pas tout énumérer
  • 23:48 - 23:51
    car sinon vous allez mourir d'ennui
  • 23:51 - 23:55
    pour en savoir plus, j'ai créé une page sur Corkami [x86.corkami.com],
  • 23:55 - 24:00
    avec quelques graphiques et penses-bêtes
  • 24:00 - 24:04
    pour faciliter le boulot
  • 24:04 - 24:06
    bon, trop de théorie
  • 24:06 - 24:11
    je n'aime pas lire sans avoir quelque chose à me mettre sous le débogueur,
  • 24:11 - 24:13
    donc j'ai créé CoST
  • 24:13 - 24:16
    ce qui signifie Corkami Standard Test
  • 24:16 - 24:20
    CoST est un unique binaire, sans option de ligne de commande
  • 24:20 - 24:25
    on l'exécute, il fait plein de tests
  • 24:25 - 24:28
    le tout dans un PE compliqué
  • 24:28 - 24:35
    pour aussi tester vos outils PE
  • 24:35 - 24:36
    ou vos connaissances
  • 24:36 - 24:40
    mais, dans ce PE compliqué, il est casse-pied à déboguer
  • 24:40 - 24:42
    donc j'ai fait aussi une version 'PE standard'
  • 24:42 - 24:47
    si on ne veut étudier que l'assembleur
  • 24:47 - 24:49
    sans difficultés
  • 24:49 - 24:57
    donc, CoST contient de nombreux tests
  • 24:57 - 24:59
    les classiques, triviaux,
  • 24:59 - 25:03
    un peu plus compliqués, JMP to IP, IRET...
  • 25:03 - 25:05
    les non documentés
  • 25:05 - 25:10
    les spécifiques aux processeurs, comme MOVBE, POPCNT, CRC32
  • 25:10 - 25:17
    les détections d'OS et VM
  • 25:17 - 25:25
    comme le fameux 'red pill'... juste une instruction SLDT, on compare le résultat,
  • 25:25 - 25:29
    et on baptise ça 'red pill'... sans commentaire...
  • 25:29 - 25:32
    et aussi, des bogues des SE, parce que Windows XP
  • 25:32 - 25:35
    se trompe en essayant de vous dire
  • 25:35 - 25:38
    quelle exception vient de se produire,
  • 25:38 - 25:44
    ce qui permettrait de différencier un SE réel d'un émulateur.
  • 25:44 - 25:50
    CoST est écrit en assembleur, donc rien de superflu
  • 25:50 - 25:52
    pas compilé, ni généré
  • 25:52 - 25:56
    mais pour le documenter un peu plus, j'ai ajouté des exports internes
  • 25:56 - 26:00
    donc on peut aller facilement d'une section à l'autre
  • 26:00 - 26:05
    donc on se retrouve facilement à la partie qui nous intéresse
  • 26:05 - 26:08
    via les exports,
  • 26:08 - 26:13
    et je voulais pouvoir afficher un message de manière pratique
  • 26:13 - 26:18
    sans que ça allonge trop le listing
  • 26:18 - 26:21
    je veux dire, devoir faire défiler l'écran parce qu'il est couvert d'appel à printf
  • 26:21 - 26:25
    donc j'au utilisé un Vectored Exception Handler, et une instruction-marqueur
  • 26:25 - 26:28
    donc plein de commentaires sont affichés,
  • 26:28 - 26:30
    directement dans le code
  • 26:30 - 26:34
    donc ça fait un code binaire documenté sans fichier de symboles de débogage
  • 26:34 - 26:38
    et vous avez vu, il n'y a pas beaucoup d'affichage
  • 26:38 - 26:41
    mais en fait, il y a beaucoup plus d'affichage de déboguage
  • 26:41 - 26:46
    une centaine au moins, qui indiquent même ce qui va se produire, etc
  • 26:46 - 26:49
    donc on est pas pris au dépourvu
  • 26:49 - 26:57
    on est guidé lors de l'analyse
  • 26:57 - 27:00
    quelqu'un comprend de quoi il s'agit?
  • 27:00 - 27:02
    c'est un de mes préférés
  • 27:02 - 27:06
    on ne peut pas voir les opcodes
  • 27:06 - 27:17
    ah, il n'y a pas d'astuce à ce niveau là cette fois-ci ;)
  • 27:17 - 27:19
    donc, on empile des valeurs
  • 27:19 - 27:21
    on saute ici
  • 27:21 - 27:26
    et avec le RETF, j'ai empilé l'adresse de 'push_eip'
  • 27:26 - 27:28
    et un mot, 0x33
  • 27:28 - 27:31
    donc on va revenir de loin ici
  • 27:31 - 27:35
    donc on retourne à cette adresse avec un sélecteur 33
  • 27:35 - 27:39
    qui est réservé au mode 64b, même pour un programme en 32b
  • 27:39 - 27:42
    donc on va revenir ici, en mode 64b
  • 27:42 - 27:47
    car 33 est le sélecteur pour le mode 64b
  • 27:47 - 27:49
    qu'on peut atteindre depuis un programme 32b
  • 27:49 - 27:56
    donc le code sera d'abord exécuté en mode 32b, avec le sélecteur standard,
  • 27:56 - 28:01
    puis à nouveau, avec le sélecteur 33
  • 28:01 - 28:04
    en mode 64b
  • 28:04 - 28:08
    donc on a la même adresse, les mêmes opcodes,
  • 28:08 - 28:10
    mais le désassemblage sera différent
  • 28:10 - 28:14
    et j'ai choisi des opcodes qui génèrent des instructions
  • 28:14 - 28:18
    spécifique à chaque mode
  • 28:18 - 28:22
    donc, c'est déjà une belle s*loperie à désassembler,
  • 28:22 - 28:27
    car avec la même EIP, si on ne fait pas attention au sélecteur,
  • 28:27 - 28:29
    on est bloqué
  • 28:29 - 28:46
    On peut déboguer un tel code - voir ma présentation à BerlinSides, transparent de démonstration 58
  • 28:46 - 28:50
    Si on l'exécute en passant par dessus, on retourne au sélecteur d'origine
  • 28:50 - 28:52
    qui était sauvé par le PUSH CS
  • 28:52 - 28:56
    donc on retourne à avec le sélecteur initial
  • 28:56 - 28:58
    l'exécution est rapide,
  • 28:58 - 29:00
    mais difficile à déboguer (uniquement avec WinDbg+wow64exts)
  • 29:00 - 29:03
    ça rend inutile les désassembleurs, et la plupart des débogueurs
  • 29:03 - 29:04
    pourtant, c'est si simple.
  • 29:04 - 29:07
    Voilà ce que donne CoST
  • 29:07 - 29:10
    sous la dernière version de Hiew
  • 29:10 - 29:13
    je pense que ce sera bientôt corrigé
  • 29:13 - 29:16
    c'est un HINT NOP non documenté par Intel
  • 29:16 - 29:21
    et oublié par la plupart des désassembleurs
  • 29:21 - 29:24
    donc WinDbg et Hiew
  • 29:24 - 29:29
    vous donnent des points d'interrogations
  • 29:29 - 29:34
    au début, je pensais m'arrêter là pour Hashdays
  • 29:34 - 29:39
    mais j'ai décidé de rajouter quelques astuces PE à CoST
  • 29:39 - 29:43
    donc, en voici l'en-tête... MZ, puis du texte
  • 29:43 - 29:44
    donc on peut taper 'type cost.exe', comme ce bon vieux Budokan...
  • 29:44 - 29:46
    et ensuite,
  • 29:46 - 29:51
    l'en-tête 'NT headers' - appelé 'PE' car il commence par ces lettres-là,
  • 29:51 - 29:54
    et en fait à la fin du fichier
  • 29:54 - 29:56
    le 'pied-de-page PE'
  • 29:56 - 29:59
    et les valeurs de l'en-tête sont un peu extrême
  • 29:59 - 30:01
    donc, pour le moins inattendu
  • 30:01 - 30:03
    donc voici ce qu'IDA 6.1 en pensait
  • 30:03 - 30:07
    ...plantage directe...
  • 30:07 - 30:11
    ça lui apprendra à se fier aux valeurs
  • 30:11 - 30:15
    mais, aussi bien dans CoST, on peut changer un registre, faire une comparaison, tester,
  • 30:15 - 30:17
    et enchaîner ainsi plein de tests,
  • 30:17 - 30:19
    aussi bien, côté PE, on n'a qu'un seul binaire, donc
  • 30:19 - 30:21
    un seul essai
  • 30:21 - 30:25
    donc même si CoST n'a pas de section, des TLS bizarres,....
  • 30:25 - 30:27
    il ne peut pas tout tester
  • 30:27 - 30:31
    donc, j'ai créé pour ça une autre page sur Corkami
  • 30:31 - 30:37
    avec comme d'habitudes, des exemples, des graphiques,
  • 30:37 - 30:40
    elle n'est pas finie, mais déjà largement suffisante pour tester ou faire planter
  • 30:40 - 30:42
    n'importe quel outil
  • 30:42 - 30:46
    j'ai déjà une centaine d'exemples,
  • 30:46 - 30:51
    qui mettent l'accent sur de nombreux aspects, avec parfois des résultats inattendus
  • 30:51 - 30:55
    donc, voici une table de section virtuelle, et Hiew
  • 30:55 - 31:00
    quand les alignements sont bas, on n'a pas besoin de section
  • 31:00 - 31:03
    ou la table peut être vide
  • 31:03 - 31:08
    donc, j'ai modifié SizeOfOptionalHeader pour qu'il pointe en espace mémoire virtuel
  • 31:08 - 31:11
    donc la table des sections est en dehors du PE, pleines de zéros
  • 31:11 - 31:16
    et Hiew n'aime pas ça. En conséquence, il ne pense même pas que c'est un PE
  • 31:16 - 31:18
    alors que ça marche parfaitement, du moins sous XP
  • 31:18 - 31:27
    car Windows 7 est plus capricieux concernant les valeurs de la table des section
  • 31:27 - 31:29
    ensuite...
  • 31:29 - 31:34
    si on fait de l'art dans les Data Directories
  • 31:34 - 31:37
    vous pouvez commencer à vous inquiéter
  • 31:37 - 31:40
    si vous avez un dessin plus joli, je suis preneur
  • 31:40 - 31:43
    donc, il s'agit du 'Dual PE header', présenté
  • 31:43 - 31:46
    par Reversing Labs à la BlackHat
  • 31:46 - 31:50
    quelqu'un connaît ?
  • 31:50 - 31:52
    donc, on augmente SizeOfHeader pour que
  • 31:52 - 31:59
    les en-têtes NT soient en fait assez loin,
  • 31:59 - 32:04
    pour qu'il soit aligné avec les sections
  • 32:04 - 32:05
    quand il se charge en mémoire
  • 32:05 - 32:08
    la première section sera chargée par dessus
  • 32:08 - 32:13
    la première partie du OPTIONAL_HEADER est lue dans le fichier
  • 32:13 - 32:16
    donc, prise en compte pour charger le fichier
  • 32:16 - 32:20
    mais les Data Directories sont lus en mémoire
  • 32:20 - 32:25
    donc, d'abord l'OPTIONAL_HEADER est analysé, chargé en mémoire,
  • 32:25 - 32:29
    puis la section est dépliée sur la partie basse de l'en-tête
  • 32:29 - 32:31
    et les vrais Data directories qui étaient initialement au début de la section
  • 32:31 - 32:34
    vont être pris en compte,
  • 32:34 - 32:39
    donc tout ceci est du pipeau présent dans le fichier, à la suite de SizeOfOptionalHeader
  • 32:39 - 32:45
    mais en mémoire, ce sera écrasé et ignoré
  • 32:45 - 32:47
    une autre bizarrerie est que les noms d'exports peuvent avoir n'importe quelle valeur,
  • 32:47 - 32:51
    jusqu'au caractère zéro
  • 32:51 - 32:53
    donc, absolument n'importe quoi,
  • 32:53 - 32:56
    et de plus,
  • 32:56 - 32:57
    Hiew les affichent directement
  • 32:57 - 32:59
    donc on peut insérer ses propres messages
  • 32:59 - 33:02
    ce sont juste des noms d'exports, d'ailleurs
  • 33:02 - 33:05
    l'un d'entre eux est excessivement long,
  • 33:05 - 33:08
    idéal pour tester les dépassement de tampon [buffer overflow]
  • 33:08 - 33:10
    dans votre outil favori
  • 33:10 - 33:14
    et il est également possible d'avoir un export avec un nom nul,
  • 33:14 - 33:16
    on peut donc importer l'api nulle
  • 33:16 - 33:19
    sans problème
  • 33:19 - 33:23
    j'ai aussi essayé les différentes possibilités,
  • 33:23 - 33:26
    avec des fichiers contenant un maximum de section,
  • 33:26 - 33:31
    la limite est 96 sous XP, et 64K sous Vista et Windows 7
  • 33:31 - 33:33
    ce qui donne
  • 33:33 - 33:36
    avec le dernier OllyDbg 2 ce message surprenant
  • 33:36 - 33:38
    mais le fichier charge quand même
  • 33:38 - 33:41
    OllyDbg 1, lui, plante directement
  • 33:41 - 33:45
    il reste du temps ?
  • 33:45 - 33:48
    un dernier... pas très visuel
  • 33:48 - 33:52
    l'adresse AddressOfIndex du TLS est mise à zéro au chargement
  • 33:52 - 33:59
    et le terminus [terminator] des imports n'a pas besoin d'être composé de 5 doubles mots nuls
  • 33:59 - 34:03
    mais juste d'un seul, pour son AddressOfName
  • 34:03 - 34:05
    pour être considéré comme le terminus
  • 34:05 - 34:10
    donc, si on fait pointer AddressOfIndex vers l'AddressOfName d'un descripteur d'imports
  • 34:10 - 34:15
    s'il est mis à zéro,
  • 34:15 - 34:16
    les imports seront tronqués
  • 34:16 - 34:20
    et en fait, le comportement est différent sous XP ou 7
  • 34:20 - 34:25
    donc, sous XP, il est écrasé après que les imports soient chargés,
  • 34:25 - 34:28
    donc la table n'est pas tronquée
  • 34:28 - 34:32
    alors que sous 7, il est écrasé avant les imports
  • 34:32 - 34:35
    donc, pour le même PE, on a 2 comportements différents
  • 34:35 - 34:37
    sous deux versions de Windows différentes,
  • 34:37 - 34:43
    alors que le fichier marche sous les 2 versions.
  • 34:43 - 34:55
    ah, attendez, on a encore le temps?
  • 34:55 - 34:56
    15 minutes ? ok
  • 34:56 - 35:01
    je vais commencer la démonstration
  • 35:01 - 35:23
    pour vous montrer...
  • 35:23 - 35:26
    le style de PE que je créé d'habitude
  • 35:26 - 35:29
    avec le minimum d'éléments définis
  • 35:29 - 35:31
    c'est en fait un pilotes [driver]
  • 35:31 - 35:36
    même si j'ai utilisé des opcodes non documentés,
  • 35:36 - 35:40
    ce pilote marche, sans le vrac
  • 35:40 - 35:43
    habituel rajouté par le compilateurs
  • 35:43 - 35:47
    donc, un exemple clair, simple
  • 35:47 - 35:51
    sans rien pour vous géner la vue
  • 35:51 - 35:52
    ou votre débogueur
  • 35:52 - 36:02
    donc, cet exemple regarde les valeurs de CR0
  • 36:02 - 36:07
    via SMSW, officiellement non défini sur un double mot
  • 36:07 - 36:10
    mais en fait donne la même valeur
  • 36:10 - 36:11
    que le MOV EAX, CR0 standard
  • 36:11 - 36:16
    ensuite, MOV EAX, CR0 avec un 'mauvais' Mod/RM
  • 36:16 - 36:39
    sous le dernier Hiew, ce n'est en fait même pas désassemblé
  • 36:39 - 36:43
    on espère que ça ne plante pas...
  • 36:43 - 36:47
    donc, vous voyez, on obtient les mêmes valeurs
  • 36:47 - 36:55
    via le CR0 standard, l'invalide, et le non défini
  • 36:55 - 36:57
    dont la partie de poids fort est non définie
  • 36:57 - 37:00
    d'habitude, en langage Intel, non défini signifie 'mis à zéro',
  • 37:00 - 37:02
    mais ici, on a bien CR0 entier
  • 37:02 - 37:03
    et ma machine n'a même pas plantée
  • 37:03 - 37:05
    ce qui signifie que le pilote fonctionne correctement
  • 37:05 - 37:08
    donc vous pouvez étudier des petits pilotes
  • 37:08 - 37:12
    le premier exemple présenté aujourd'hui
  • 37:12 - 37:15
    était celui avec l'assembleur ancien
  • 37:15 - 37:20
    quelqu'un connaît le résultat final ?
  • 37:20 - 37:23
    certaines instructions sont inutiles,
  • 37:23 - 37:28
    juste pour vérifier que le processeur les gère
  • 37:28 - 37:30
    mais d'autres modifient les registres
  • 37:30 - 37:37
    et ces instructions des années 70-80
  • 37:37 - 37:43
    sont toujours gérées par les processeurs modernes
  • 37:43 - 37:47
    un des exemples que j'ai crée teste
  • 37:47 - 37:50
    les valeurs initiales de chaque registre
  • 37:50 - 37:56
    donc on peut voir les valeurs possibles sous XP ou W7
  • 37:56 - 38:01
    à chaque fois [TLS, EntryPoint, DllMain], je sauve tous les registres
  • 38:01 - 38:04
    et je compare à diverses valeurs possibles
  • 38:04 - 38:06
    successivement
  • 38:06 - 38:10
    en fait, au TLS, on a beaucoup de contrôles de ces valeurs,
  • 38:10 - 38:16
    car ces valeurs proviennent du Data Directory
  • 38:16 - 38:20
    en particulier, son adresse relative, sa taille, les callbacks...
  • 38:20 - 38:26
    pour plus de détail, voir le source...
  • 38:26 - 38:33
    ça vous permet d'imiter mieux un SE dans votre émulateur,
  • 38:33 - 38:35
    si ça vous intéresse
  • 38:35 - 38:41
    on utilise SMSW, on compare la valeur
  • 38:41 - 38:46
    ensuite, après une opération FPU, on regarde si la valeur a changé
  • 38:46 - 38:48
    et si elle revient à sa valeur initiale.
  • 38:48 - 38:52
    une autre bizarrerie, si quelqu'un a l'explication
  • 38:52 - 38:54
    est qu'en fait
  • 38:54 - 39:01
    ça se comporte différemment si on exécute le fichier normalement
  • 39:01 - 39:04
    ou avec une redirection
  • 39:04 - 39:08
    si on redirige, 'échec'
  • 39:08 - 39:11
    sinon, ça marche normalement.
  • 39:11 - 39:22
    pour vous montrer... on exécute, et on lance TYPE
  • 39:22 - 39:24
    normal : OK
  • 39:24 - 39:26
    redirection: ECHEC
  • 39:26 - 39:30
    si vous avez une explication, je suis preneur
  • 39:30 - 39:37
    tu as essayé de rediriger vers autre chose ?
  • 39:37 - 39:42
    non, je n'ai pas essayé
  • 39:42 - 39:45
    donc, rediriger vers un autre périphérique?
  • 39:45 - 39:46
    mais, comment on récupère le résultat ?
  • 39:46 - 39:48
    imprimante ?
  • 39:48 - 39:54
    je n'ai pas de périphérique COM
  • 39:54 - 39:56
    non, je ne sais pas
  • 39:56 - 39:59
    mais c'était surprenant, car je lançais tous mes tests...
  • 39:59 - 40:02
    et d'un coup, 'ECHEC'...
  • 40:02 - 40:07
    alors qu'à la main, aucun problème.
  • 40:07 - 40:09
    l'astuce avec GS
  • 40:09 - 40:11
    très simple
  • 40:11 - 40:19
    et quelques affichages
  • 40:19 - 40:21
    je modifie GS, qui se remet à zéro
  • 40:21 - 40:23
    puis j'attends le résultat,
  • 40:23 - 40:26
    ensuite je fais 2 tests et je compare le temps entre
  • 40:26 - 40:30
    car ça ne doit pas arriver trop vite
  • 40:30 - 40:37
    NOPs
  • 40:37 - 40:39
    je teste les NOPs non documentés
  • 40:39 - 40:45
    celui sur une page invalide
  • 40:45 - 41:01
    NOP standard
  • 41:01 - 41:07
    32 bits
  • 41:07 - 41:15
    tous mes tests 64b sont fait dans des programmes 32b, car on peut les exécuter sur un OS normal
  • 41:15 - 41:19
    et ensuite je regarde GS pour voir si le mode 64b est disponible
  • 41:19 - 41:21
    dans ce cas, on obtiendrait un résultat différent
  • 41:21 - 41:26
    donc, en 64b, que je n'ai aps ici, on obtiendrait
  • 41:26 - 41:28
    les tests en 64b
  • 41:28 - 41:31
    et ces results.
  • 41:31 - 41:35
    mais, pas si facile à déboguer
  • 41:35 - 41:39
    mais ici, pas de piège, donc on peut revenir facilement en 32b
  • 41:39 - 41:45
    on saute le code 64b et revient en 32b
  • 41:45 - 41:48
    PUSH/RET
  • 41:48 - 41:52
    on affiche le message et ensuite...
  • 41:52 - 41:58
    Olly vous dit qu'on va sauter vers [4010]08
  • 41:58 - 42:03
    mais en fait - ici, c'est correct
  • 42:03 - 42:05
    et le TLS a alloué la page NULLE
  • 42:05 - 42:09
    qui affiche 'ECHEC'
  • 42:09 - 42:15
    donc, comme mentionné auparavant, pas de façon standard de désassembler ça correctement
  • 42:15 - 42:23
    je ne peux pas exécuter les 64K sections
  • 42:23 - 42:27
    et en fait, cet exemple exécute tout le code (l'espace virtuel complet des 65535 sections)
  • 42:27 - 42:29
    elles sont grosses,
  • 42:29 - 42:33
    et je modifie EAX pour que tous les 00 00 soient exécutés
  • 42:33 - 42:35
    juste pour faire un printf à la fin
  • 42:35 - 42:39
    ça prend plusieurs secondes sur un i7
  • 42:39 - 42:43
    c'est assez amusant: on le lance, et même avec le cache,
  • 42:43 - 42:50
    et que le SE n'est pas occupé, ça prend un temps visible, juste pour un tas de 00
  • 42:50 - 43:00
    les sections virtuelles... celui que le dernier Hiew ne voit pas comme un PE
  • 43:00 - 43:02
    enfin, bientôt corrigé
  • 43:02 - 43:08
    ah, je ne peux pas l'analyser car il ne pense même pas que c'est un PE
  • 43:08 - 43:13
    mais, pour simplifier, OPTIONAL_HEADER pointe au delà
  • 43:13 - 43:14
    du fichier
  • 43:14 - 43:17
    l'en-tête plié...
  • 43:17 - 43:18
    quelques messages d'erreurs,
  • 43:18 - 43:21
    à cause des faux Data Directories
  • 43:21 - 43:30
    et les DD réels sont au début
  • 43:30 - 43:33
    de la première section
  • 43:33 - 43:42
    ceci deviendra les imports, et le vrai Data Directory
  • 43:42 - 43:49
    et pour finir, celui avec TLS AddressOfIndex qui pointe...
  • 43:49 - 44:02
    ...dans les descripteurs d'imports, sur AddressOfName
  • 44:02 - 44:04
    donc, il sera écrasé au chargement
  • 44:04 - 44:11
    et quand on le charge, il reconnait XP
  • 44:11 - 44:14
    à la façon dont les imports ont été chargés
  • 44:14 - 44:17
    et sous 7, on obtiendra un autre résultat.
  • 44:17 - 44:19
    pour finir, les exports
  • 44:19 - 44:24
    certains ont des noms très longs
  • 44:24 - 44:30
    en fait, on remarque que j'écrase le désassemblage même
  • 44:30 - 44:33
    donc je répète les faux opcodes et adresses
  • 44:33 - 44:37
    donc le désassembleur est perturbé
  • 44:37 - 44:40
    mais c'est juste visuel, pas vraiment grave
  • 44:40 - 44:43
    bien que ce soit un problème récent dans IDA
  • 44:43 - 44:47
    ou si on met un export au milieu d'une instruction
  • 44:47 - 44:49
    l'export aura priorité sur le désassemblage,
  • 44:49 - 44:52
    et casse l'instruction en deux
  • 44:52 - 44:58
    il y a bien sûr un exemple pour ça sur Corkami
  • 44:58 - 45:05
    donc, voilà pour les démonstrations
  • 45:05 - 45:10
    Je voulais donc en savoir plus sur le x86 et le PE
  • 45:10 - 45:12
    qui sont loin d'être correctement documentés
  • 45:12 - 45:14
    et qui ne le sont toujours pas,
  • 45:14 - 45:18
    mais j'en ai couvert un peu
  • 45:18 - 45:20
    il y a encore des flous
  • 45:20 - 45:24
    mais de moins en moins, j'y travaille
  • 45:24 - 45:27
    en publiant mes recherches librement
  • 45:27 - 45:31
    tel WinDbg, si vous suivez les documentations officielles à la lettre,
  • 45:31 - 45:36
    vous êtes voués à l'échec, surtout avec tous les virus et packeurs existants
  • 45:36 - 45:40
    si vous êtes intéressés, ou que vous programmez un outil, un émulateur, un moteur...
  • 45:40 - 45:44
    vous savez que vous pouvez aller sur Corkami, lire les pages
  • 45:44 - 45:48
    télécharger les exemples, qui sont disponibles librement, à tout point de vue
  • 45:48 - 45:50
    et si vous trouvez des bugs, ce qui pourrait arriver
  • 45:50 - 45:57
    envoyez-moi une carte postale, ou un t-shirt croix rouge ;)
  • 45:57 - 46:01
    Merci à Peter Ferrie, et tous mes relecteurs et contributeurs
  • 46:01 - 46:03
    vous avez des questions ?
  • 46:03 - 46:10
    tu les as testés sur des anti-virus ? tu devrais trouver une ch*ée de 0days
  • 46:10 - 46:23
    mouai, non, je ne saurais pas en faire des exploits...
  • 46:23 - 46:29
    tenir en échec les désassembleurs me suffit
  • 46:29 - 46:40
    j'ai trouvé un crash dans Xed d'Intel, ça me suffit
  • 46:40 - 46:45
    une autre question ? tout le monde a survécu ?
  • 46:45 - 46:46
    c'était une super présentation, mec
  • 46:46 - 46:48
    merci!
  • 46:48 - 46:50
    MERCI!
Title:
#days: Ange Albertini: Such a weird processor - messing with x86 opcodes
Description:

#days Security & Risk Conference: Ange Albertini: Such a weird processor - messing with x86 opcodes

more » « less
Video Language:
English
Duration:
47:07

French subtitles

Revisions