Skip to Content
Nouvelle version 12 disponible 🎉
ObfuscatorRenommage des symbolesDécoder les traces de pile

Décoder les traces de pile

Obfusquer une application protège la propriété intellectuelle et procure un avantage concurrentiel en rendant la rétro-ingénierie plus difficile. Cette sécurité supplémentaire complique toutefois le signalement des erreurs. L’obfuscation peut rendre l’analyse des plantages plus difficile, car la trace de pile se réduit souvent à une suite de symboles illisibles, ce qui complique le débogage.

Décoder les traces de pile dans .NET

Les développeurs .NET s’appuient généralement sur les traces de pile pour localiser la cause des erreurs d’une application. L’obfuscation rend cependant ces traces inintelligibles. Avec Babel Obfuscator, décoder ces traces de pile obfusquées est simple. L’outil a besoin d’un fichier de mappage, généré pendant l’obfuscation.

Générer le fichier de mappage

Lorsque vous activez la génération du fichier de mappage XML dans Babel Obfuscator, ce fichier est généré par défaut dans le même répertoire que l’assembly obfusqué. Il porte le nom de l’assembly d’origine, suivi de .map.xml (par exemple MyApp.exe.map.xml).

Le fichier de mappage généré contient la correspondance entre les noms de symboles obfusqués et les noms d’origine.

Notez qu’il est préférable de désactiver le renommage avec surcharge (--nooverloaded), car il attribue le même nom à des méthodes différentes, ce qui peut rendre le décodage de la trace de pile ambigu. Si le renommage avec surcharge est activé, Babel indique lors du décodage toutes les méthodes qui peuvent correspondre.

Vous pouvez choisir l’emplacement de sortie du fichier de mappage de différentes manières, selon la façon dont vous utilisez Babel.

Ligne de commande

babel MyApp.exe --mapout CustomPath/MyMapping.xml

Si vous omettez le chemin du fichier, Babel applique la convention de nommage par défaut dans le répertoire cible.

Tâche MSBuild

<Babel GenerateMapOutFile="true" MapOutFile="CustomPath/MyMapping.xml" />

Package NuGet Babel Obfuscator

<PropertyGroup> <GenerateMapOutFile>true</GenerateMapOutFile> <BabelMapOutFile>CustomPath/MyMapping.xml</BabelMapOutFile> </PropertyGroup>

Babel Desktop

Dans Babel Desktop, sélectionnez l’assembly et activez GenerateMapOutFile dans le groupe Output & diagnostics du panneau des propriétés. Définissez MapOutFile pour écrire le fichier de mappage à un emplacement personnalisé. Voir Projets d’obfuscation.

Décoder la trace de pile obfusquée

Lorsqu’une application obfusquée plante et produit une trace de pile obfusquée, utilisez Babel pour la décoder. Babel Obfuscator fournit des outils intégrés qui décodent les traces de pile obfusquées à l’aide des fichiers de mappage.

Babel Desktop

Les étapes ci-dessous sont un résumé ; voir Décodeur de pile pour le guide complet.

Ouvrir le décodeur de pile

Ouvrez la palette de commandes et exécutez Outils : décodeur de pile.

Ajouter les fichiers de mappage

Ajoutez les fichiers de mappage XML avec Ajouter des fichiers map…, ou déposez-les sur le décodeur. Vous pouvez ajouter plusieurs fichiers de mappage lorsque la trace couvre plusieurs assemblies.

Coller la trace de pile

Collez la trace de pile obfusquée, ou chargez-la depuis un fichier avec Ouvrir une trace….

Décoder

Cliquez sur Décoder pour afficher la trace de pile décodée.

Ligne de commande

Vous pouvez aussi utiliser l’outil en ligne de commande babel :

babel --stacktrace StackTrace.txt --mapin MyApp.exe.map.xml --mapin Library.dll.map.xml

Vous pouvez indiquer plusieurs fichiers de mappage si la trace de pile concerne plusieurs assemblies.

Frames du proxy dynamique

Lorsque le proxy dynamique est activé, Babel fait passer les appels éligibles par des méthodes de pont générées. Chaque pont apparaît comme une frame supplémentaire, si bien qu’une trace décodée entremêle vos propres méthodes et la mécanique interne de Babel. Babel enregistre dans le fichier de mappage la méthode que chaque pont remplace, et le décodeur l’affiche :

at Acme.Backup.ZipReader.OpenZip(System.String filename) at (System.String ) -> proxy for System.IO.Compression.ZipFile::OpenRead at Acme.Backup.BackupReader.IsBackupFile(System.String path)

L’annotation -> proxy for <DeclaringType>::<Method> indique exactement quelle méthode le pont appelait. La signature figure déjà sur la frame et n’est donc pas répétée dans l’annotation. Les fichiers de mappage produits par des versions antérieures de Babel, qui n’enregistrent pas la cible du proxy, sont décodés comme auparavant et affichent à la place la mention générique -> babel generated code.

Masquer les frames générées par Babel

Si seule votre propre chaîne d’appels vous intéresse, Babel peut retirer toutes les frames qu’il a générées (les ponts de proxy et les frames anonymes créées à l’exécution par lesquelles ils passent), ce qui laisse une trace identique à celle que produirait l’application non obfusquée.

Depuis la ligne de commande, ajoutez la clé frames=user à l’option --stacktrace :

babel --stacktrace StackTrace.txt --stacktrace frames=user --mapin MyApp.exe.map.xml

frames=all est la valeur par défaut et conserve toutes les frames. Dans Babel Desktop, le décodeur de pile masque ces frames par défaut : la case Masquer les frames ajoutées par Babel est cochée. Décochez-la pour conserver toutes les frames.

Une fois les frames générées masquées, la trace ci-dessus devient :

at System.IO.Compression.ZipFile.Open(System.String archiveFileName) at Acme.Backup.ZipReader.OpenZip(System.String filename) at Acme.Backup.BackupReader.IsBackupFile(System.String path)

Automatiser la désobfuscation des traces de pile

Babel Obfuscator fournit une interface pour automatiser le décodage des traces de pile. Ajoutez à votre assembly .NET une référence à babel.dll (ou à babel.exe pour les anciennes applications .NET Framework) et utilisez l’API fournie pour décoder les traces de pile par programmation.

L’extrait de code ci-dessous montre comment configurer une application console pour désobfusquer une trace de pile chargée depuis un fichier externe :

// Example of setting up the console application static int Main(string[] args) { if (args.Length < 2) { Console.WriteLine("Usage: stackdecode.exe <filename> <xmlmapfile1> [xmlmapfile2 ...]"); return 1; } StackTraceDeobfuscator stk = new StackTraceDeobfuscator(); foreach (var xmlMapFile in args.Skip(1)) { try { stk.AddMapFile(xmlMapFile); } catch (Exception ex) { Console.WriteLine(String.Format("Error reading XML map file '{0}':n{1}", xmlMapFile, ex.Message)); return 1; } } try { StreamReader sr = new StreamReader(args[0]); Console.WriteLine("Deobfuscated Stack Trace:"); Console.WriteLine(stk.DeobfuscateStack(sr)); } catch (Exception ex) { Console.WriteLine(String.Format("Could not decode stack trace file '{0}':n{1}", args[0], ex.Message)); return 1; } return 0; }

Pour retirer les frames générées par Babel (voir Masquer les frames générées par Babel) lors d’un décodage par programmation, définissez HideGeneratedFrames sur le désobfuscateur avant d’appeler DeobfuscateStack :

StackTraceDeobfuscator stk = new StackTraceDeobfuscator(); stk.HideGeneratedFrames = true;

L’interface de programmation de désobfuscation des traces de pile donne aux développeurs un outil pour améliorer leurs pratiques de débogage. En intégrant ce mécanisme à leurs applications, ils peuvent automatiser le décodage, traiter efficacement les traces de pile obfusquées et préserver l’intégrité et la sécurité de leur code.

Utiliser les fichiers PDB avec les traces de pile obfusquées

Vous pouvez aussi utiliser des fichiers PDB en production pour obtenir le fichier source et les numéros de ligne dans la trace de pile décodée. Plus précisément, Babel peut chiffrer les noms de fichiers et les noms de symboles dans les PDB : ils apparaissent alors chiffrés dans les traces de pile, ce qui évite de révéler des informations sensibles sur les chemins de fichiers.

Pour activer cette fonctionnalité, définissez un mot de passe PDB. Choisissez un mot de passe sûr : il chiffre les noms de fichiers dans le PDB et sera nécessaire plus tard pour désobfusquer les traces de pile.

  • Ligne de commande : utilisez l’option --pdbpwd, par exemple babel MyApp.exe --debug --pdbpwd <password>.
  • MSBuild : dĂ©finissez la propriĂ©tĂ© PdbPwd de la tâche Babel.
  • Babel Desktop : sĂ©lectionnez l’assembly et dĂ©finissez PdbPwd dans le groupe Advanced du panneau des propriĂ©tĂ©s. Le mot de passe n’est conservĂ© que pour la session en cours : il n’est pas enregistrĂ© dans le projet et doit ĂŞtre saisi de nouveau après le redĂ©marrage de Babel Desktop.

Une fois cette fonctionnalité activée et le mot de passe PDB défini, Babel chiffre les noms de fichiers et les autres informations concernées pendant l’obfuscation. Dans vos traces de pile, les noms de fichiers apparaissent donc sous forme de chaînes chiffrées et non plus sous forme de chemins d’origine.

System.Exception: (0x80131904): A network-related or instance-specific error occurred while establishing a connection to the server. at System.Data.SqlClient.SqlConnection.Open() at b.a(String g) at c.b() in <GFpQHv9iwQzX1Zmh+… >:line 21 at c.a(String h) at Acme.ViewModel.MainViewModel.get_Message() in <GFpQHv9iwQzX1Zmh+… >:line 28

Toutes les données nécessaires au déchiffrement sont stockées dans le fichier de mappage XML : le fichier PDB n’est donc pas nécessaire au décodage. La trace de pile décodée contient le nom de fichier déchiffré.

System.Exception: (0x80131904): A network-related or instance-specific error occurred while establishing a connection to the server. at System.Data.SqlClient.SqlConnection.Open() at Acme.Entities.DatabaseContext.ConnectToDatabase(System.String connectionString) at Acme.ViewModel.RS.CheckResourceLoaded() in C:AcmeAcme.ViewModelRS.cs:line 21 at Acme.ViewModel.RS.GetString(System.String name) at Acme.ViewModel.MainViewModel.get_Message() in C:AcmeAcme.ViewModelViewModelMainViewModel.cs:line 28

Cette méthode concilie sécurité et maintenabilité. Elle protège la propriété intellectuelle que révèle l’organisation de vos fichiers, tout en vous laissant tirer des traces de pile des informations utiles au débogage et à l’analyse des erreurs.

Avec le chiffrement des PDB, la structure interne de votre application et l’organisation de ses fichiers restent protégées et confidentielles, même lorsque vous partagez des PDB à des fins de dépannage ou d’assistance.

Last updated on