
Plugin IDA Pro pour filtrer les fonctions par motifs d'assemblage, séquences d'octets, références de chaînes/noms et contraintes de taille, avec recherche basée sur des règles et copie binaire avancée.
FindFunc est un plugin IDA Pro pour trouver des fonctions de code qui contiennent un certain motif assembleur ou d'octets, référencent un certain nom ou une chaîne, ou sont conformes à diverses autres contraintes.
FindFunc a remporté la troisième place au Concours de plugins IDA Pro HexRays 2022 !

La fonctionnalité principale de FindFunc est de permettre à l'utilisateur de spécifier un ensemble de « Règles » ou contraintes qu'une fonction de code dans IDA Pro doit satisfaire. FF trouvera et listera alors toutes les fonctions qui satisfont TOUTES les règles (donc actuellement toutes les règles sont en conjonction ET). Exception : les règles peuvent être « inversées » pour être des correspondances négatives. De telles règles respectent donc « ET NON ».
FF planifiera les règles dans un ordre intelligent pour minimiser le temps de traitement. Aperçu des fonctionnalités :
Le bouton « Find Functions » efface les résultats existants et lance une nouvelle recherche, « Refine Results » ne considère que les résultats de la recherche précédente.
Une fonctionnalité secondaire de FF est l'option de copier la représentation binaire des instructions avec les options suivantes :
Voir la section « copie avancée » ci-dessous pour les détails. Cette fonctionnalité complète bien la règle de motif d'octets !
FindFunc est un plugin Python IDA Pro sans dépendances de paquets externes. Il peut être installé en téléchargeant le dépôt et en copiant le fichier 'findfuncmain.py' et le dossier 'findfunc' dans votre répertoire de plugins IDA Pro. Pour IDA 9.0+, le dépôt peut également être cloné directement dans le répertoire des plugins. Dans les deux cas, aucune compilation n'est requise.
Prérequis : IDA Pro 8.x (8.3+) avec environnement python3. FindFunc est conçu uniquement pour l'architecture x86/x64. Il a été testé avec IDA 8.3 - 9.2, Python 3.11 sur Windows 10 + 11
Actuellement, les six règles suivantes sont disponibles. Elles sont triées ici de lourde à légère en ce qui concerne l'impact sur les performances. Avec de grandes bases de données, il est conseillé de réduire d'abord les fonctions candidates avec une règle peu coûteuse, avant d'effectuer une correspondance lourde via, par exemple, les règles de code. FF planifiera automatiquement les règles de manière intelligente.
Règle pour filtrer les fonctions en fonction de la présence d'un extrait de code assembleur donné. Ce n'est PAS une recherche textuelle de la représentation de désassemblage textuelle d'IDA, mais plutôt une correspondance avancée de l'instruction sous-jacente. L'extrait peut contenir plusieurs instructions consécutives, une par ligne. Les chunks de fonctions sont pris en charge. Prend en charge la correspondance avec des caractères génériques spéciaux, en plus de l'assembleur littéral :
plus d'exemples :
mov r64, [r32 * 8 + 0x100]
mov r, [r * 8 - 0x100]
mov r64, [r32 * 8 + imm]
pass
mov r, word [eax + r32 * 8 - 0x100]
any r64, r64
push imm
push any
Pièges : Soyez prudent lorsque vous copiez de l'assembleur depuis IDA. IDA mélange les noms de variables locales et d'autres informations dans l'instruction, ce qui entraîne un échec de la correspondance. De plus, les labels ne sont pas pris en charge (« call sub_123456 »).
Notez que les motifs de code sont la règle la plus coûteuse, et si seules les règles de code sont présentes, FF n'a d'autre choix que de désassembler l'intégralité de la base de données. Cela peut prendre jusqu'à plusieurs minutes pour de très gros binaires. Voir les notes sur les performances ci-dessous.
La fonction doit contenir la valeur immédiate donnée au moins une fois dans n'importe quelle position. Une valeur immédiate est une valeur fixée dans la représentation binaire de l'instruction. Exemples d'instructions correspondant à la valeur immédiate 0x100 :
mov eax, 0x100
mov eax, [0x100]
and al, [eax + ebx*8 + 0x100]
push 0x100
Les immédiats peuvent être collés directement depuis le presse-papiers dans la liste des règles. Remarque : IDA effectue une correspondance étendue de toute taille et de toute position de l'immédiat. Si vous savez qu'il s'agit d'une largeur spécifique de 4 ou 8 octets, un motif d'octets peut être plus rapide (mais peut produire des faux positifs).
La fonction doit contenir le motif d'octets donné au moins une fois. Le motif est du même format que la recherche binaire d'IDA et prend donc en charge les caractères génériques - la correspondance parfaite pour la fonction de copie avancée !
Exemples :
11 22 33 44 aa bb cc
11 22 33 ?? ?? bb cc -> ?? peut être n'importe quel octet
Les motifs d'octets peuvent être collés directement depuis le presse-papiers dans la liste des règles. Remarque : La correspondance de motifs est assez rapide et un bon candidat pour réduire rapidement les correspondances !
La fonction doit référencer la chaîne donnée au moins une fois. La chaîne est mise en correspondance selon le module 'fnmatch' de Python, et prend donc en charge une correspondance de type caractère générique. La correspondance est effectuée sans tenir compte de la casse. Les chaînes des formats suivants sont considérées : [idaapi.STRTYPE_C, idaapi.STRTYPE_C_16] (cela peut être modifié dans la classe Config).
Exemples :
Remarque : La correspondance de chaînes est rapide et un bon choix pour réduire rapidement les candidats !
La fonction doit référencer le nom/label donné au moins une fois. Le nom/label est mis en correspondance selon le module 'fnmatch' de Python, et prend donc en charge une correspondance de type caractère générique. La correspondance est effectuée sans tenir compte de la casse.
Exemples :
Remarque : La correspondance de noms est très rapide et idéale pour réduire rapidement les candidats !
La taille de la fonction doit être dans la limite donnée : « min <= functionsize <= max ». Les données sont saisies sous forme de chaîne de la forme « min,max ». La taille d'une fonction inclut tous ses chunks.
Remarque : La correspondance de taille de fonction est très rapide et idéale pour réduire rapidement les candidats !
Pour faciliter l'utilisation, FF peut être utilisé via les raccourcis clavier suivants :
Utilisation supplémentaire de l'interface
Fréquemment, nous voulons rechercher des motifs binaires d'assembleur, mais sans adresses et valeurs codées en dur (immédiats), ou même seulement les opcodes réels de l'instruction. FindFunc facilite cela en ajoutant trois options de copie au menu contextuel du désassemblage :
Copie tous les octets d'instructions sous forme de chaîne hexadécimale dans le presse-papiers, pour utilisation dans une règle de motif d'octets (ou la recherche binaire d'IDA).
B8 44332211 mov eax,11223344
68 00000001 push 1000000
66:894424 70 mov word ptr ss:[esp+70],ax
sera copié comme
b8 44 33 22 11 68 00 00 00 01 66 89 44 24 70
Copie les octets d'instructions pour l'instruction donnée, en masquant toutes les valeurs immédiates. Exemple :
B8 44332211 mov eax,11223344
68 00000001 push 1000000
66:894424 70 mov word ptr ss:[esp+70],ax
sera copié comme
b8 ?? ?? ?? ?? 68 ?? ?? ?? ?? 66 89 44 24 ??
Copie tous les octets d'instructions sous forme de chaîne hexadécimale dans le presse-papiers, en masquant tous les octets qui ne sont pas l'opcode réel (y compris sib, modrm, mais en conservant les préfixes hérités).
B8 44332211 mov eax,11223344
68 00000001 push 1000000
66:894424 70 mov word ptr ss:[esp+70],ax
sera copié comme
b8 ?? ?? ?? ?? 68 ?? ?? ?? ?? 66 89 ?? ?? ??
Une combinaison qui conserve l'opcode et les immédiats, mais masque par exemple mod r/m. Notez que cela conserve les opcodes même s'ils imposent des registres spécifiques, par exemple
B8 44332211 mov eax,11223344
conservera l'opcode B8.
Remarque : Il s'agit d'un « meilleur effort » utilisant l'API d'IDA, donc il peut y avoir quelques cas où cela ne fonctionne que partiellement. Pour une solution 100 % correcte, nous devrions inclure une bibliothèque de désassemblage x86 dédiée.
Des résultats similaires peuvent être obtenus avec les règles de motif de code, mais cela peut être plus rapide, tant pour l'interaction utilisateur que pour la recherche réelle.
Copie le désassemblage sélectionné dans le presse-papiers, tel qu'il apparaît dans IDA.
Un mot rapide sur les performances :