Le processus de décompilation est exactement le contraire de la compilation, qui consiste à restaurer le langage de programmation compilé à son état non compilé, c'est-à-dire à connaître le code source du langage de programmation. Il s’agit de convertir le langage que la machine peut comprendre en un langage que le programmeur peut comprendre. La décompilation en langage Java fait généralement référence à la conversion de fichiers de classe en fichiers Java.
Outils de décompilation Java couramment utilisés
Cet article présente principalement quatre outils de décompilation Java : javap, jad et cfr ainsi que l'outil de décompilation visuelle JD-GUI
JAVAP
javap est un outil fourni avec jdk. Il peut décompiler le code et afficher le bytecode généré par le compilateur Java. La plus grande différence entre Javap et les deux autres outils de décompilation est que les fichiers qu'il génère ne sont pas des fichiers Java et qu'ils ne sont pas aussi faciles à comprendre que les codes générés par les deux autres outils. Prenons un simple morceau de code comme exemple. Par exemple, si nous voulons analyser comment switch dans Java 7 prend en charge String, nous avons d'abord le code source suivant qui peut être compilé et transmis :
public class switchDemoString { public static void main(String[] args) { String str = "world"; switch (str) { case "hello": System.out.println("hello"); break; case "world": System.out.println("world"); break; default: break; } } }
Exécutez ce qui suit. deux commandes :
javac Decompilation.java javap -c Decompilation.class
Le code généré est le suivant :
Compiled from "Decompilation.java" public class Decompilation { public Decompilation(); Code: 0: aload_0 1: invokespecial #8 // Method java/lang/Object."<init>":()V 4: return public static void main(java.lang.String[]); Code: 0: ldc #16 // String world 2: astore_1 3: aload_1 4: dup 5: astore_2 6: invokevirtual #18 // Method java/lang/String.hashCode:()I 9: lookupswitch { // 2 99162322: 36 113318802: 48 default: 82 } 36: aload_2 37: ldc #24 // String hello 39: invokevirtual #26 // Method java/lang/String.equals:(Ljava/lang/Object;)Z 42: ifne 60 45: goto 82 48: aload_2 49: ldc #16 // String world 51: invokevirtual #26 // Method java/lang/String.equals:(Ljava/lang/Object;)Z 54: ifne 71 57: goto 82 60: getstatic #30 // Field java/lang/System.out:Ljava/io/PrintStream; 63: ldc #24 // String hello 65: invokevirtual #36 // Method java/io/PrintStream.println:(Ljava/lang/String;)V 68: goto 82 71: getstatic #30 // Field java/lang/System.out:Ljava/io/PrintStream; 74: ldc #16 // String world 76: invokevirtual #36 // Method java/io/PrintStream.println:(Ljava/lang/String;)V 79: goto 82 82: return }
javap ne décompile pas le bytecode dans un fichier java, mais génère un bytecode que l'on peut comprendre. En fait, les fichiers générés par javap sont toujours des bytecodes, mais les programmeurs peuvent les comprendre un peu plus. Si vous avez quelques connaissances en bytecode, vous pouvez toujours comprendre le code ci-dessus. En fait, il s'agit de convertir String en hashcode puis de comparer.
JAD
JAD est un outil de décompilation relativement bon Tant que vous téléchargez un outil d'exécution, vous pouvez décompiler les fichiers de classe. Toujours le code source ci-dessus, le contenu après décompilation à l'aide de jad est le suivant :
Commande : jad.exe Decompilation.class générera un fichier Decompilation.jad
Le résultat de la décompilation JAD est le suivant suit :
// Decompiled by Jad v1.5.8g. Copyright 2001 Pavel Kouznetsov. // Jad home page: http://www.kpdus.com/jad.html // Decompiler options: packimports(3) // Source File Name: Decompilation.java package com.yveshe; import java.io.PrintStream; public class Decompilation { public Decompilation() { } public static void main(String args[]) { String str = "world"; String s; switch((s = str).hashCode()) { default: break; case 99162322: if(s.equals("hello")) System.out.println("hello"); break; case 113318802: if(s.equals("world")) System.out.println("world"); break; } } }
Regardez le code ci-dessus, n'est-ce pas le code source Java standard ? Cela montre clairement que le changement de chaîne d'origine est implémenté via les méthodes equals() et hashCode().
CFR
JAD est très utile, mais malheureusement il n'a pas été mis à jour depuis longtemps, je ne peux donc utiliser qu'un nouvel outil pour le remplacer. un bon choix, comparé à JAD, sa syntaxe est peut-être légèrement plus compliquée, mais heureusement il peut être utilisé.
CFR décompilera les fonctionnalités Java modernes – Java 8 lambdas (Java en Java et versions antérieures bêta 103) , Java 7 String a été décompilé, mais CFR est entièrement écrit en Java 6.
Il est recommandé de compiler et de générer manuellement le fichier Decompilation.class via la commande javac Decompilation.java, puis de le tester.
Le résultat de la décompilation réussie est le suivant :
/* * Decompiled with CFR 0_125. */ package com.yveshe; import java.io.PrintStream; public class Decompilation { public static void main(String[] args) { String str; String s = str = "world"; switch (s.hashCode()) { default: { break; } case 99162322: { if (!s.equals("hello")) break; System.out.println("hello"); break; } case 113318802: { if (!s.equals("world")) break; System.out.println("world"); } } } }
Par rapport à Jad, CFR a de nombreux paramètres, et c'est toujours le même code. Si nous utilisons la commande suivante, le résultat de sortie sera. différent :
E :CRF>java -jar cfr_0_125.jar Decompilation.class
/* * Decompiled with CFR 0_125. */ package com.yveshe; import java.io.PrintStream; public class Decompilation { public static void main(String[] args) { String str; String s = str = "world"; switch (s.hashCode()) { default: { break; } case 99162322: { if (!s.equals("hello")) break; System.out.println("hello"); break; } case 113318802: { if (!s.equals("world")) break; System.out.println("world"); } } } }
--decodestringswitch signifie décoder les détails de la chaîne de support du commutateur.
Les exemples similaires incluent --decodeenumswitch, --decodefinally, --decodelambdas, etc.
--decodelambdas peut décompiler les expressions lambda.
JD-GUI
JD-GUI est un outil de décompilation Java développé en C++, développé par Pavel Kouznetsov, et prend en charge les plateformes Windows, Linux et Apple Mac Os. Et fournit le plug-in JD-Eclipse sous la plateforme Eclipse. JD-GUI est basé sur la licence open source GPLv3 et est entièrement gratuit pour un usage personnel. L'essentiel de JD-GUI est de fournir des opérations visuelles. Vous pouvez glisser et déposer des fichiers directement dans la fenêtre. Le rendu est le suivant
JadClipse
Installez le plug-in Jad dans Eclipse. Notez que le plug-in Jad est installé ici, pas le plug-in Jd~Ressources requises : net.sf.jadclipse_3.3.0. Jar du plug-in .jar et logiciel de décompilation JAD.exe (dans Il y a une adresse de téléchargement à la fin de l'article) L'adresse de téléchargement de JadClipse permet de télécharger le package jar du plug-in depuis le site officiel , puis placez le package jar dans le répertoire des plugins d'Eclipse ; ouvrez Eclipse->Fenêtre->Préférences-> Java, à ce stade, vous constaterez qu'il y aura une option JadClipse de plus qu'auparavant. comme indiqué ci-dessous : Une fois la configuration de base terminée, nous pouvons définir la méthode d'ouverture par défaut des fichiers de classe : Eclipse->Fenêtre->Préférences->Général->Editeurs->Associations de fichiers Nous pouvons voir qu'il existe deux façons d'ouvrir les fichiers de classe. Tout d'abord, définissez la visionneuse de fichiers de classe fournie avec JadClipse et Eclipse. ici, et JadClipse est la valeur par défaut. Toutes les configurations sont terminées. Nous pouvons maintenant afficher le code source. Sélectionnez la classe que vous souhaitez afficher et appuyez sur F3 pour afficher le code source. Si JadClipse n'est pas le paramètre par défaut, définissez-le simplement sur le paramètre par défaut. . Plus Pour plus de connaissances sur Java, veuillez faire attention à la colonneJava Basic Tutorial.
Ce qui précède est le contenu détaillé de. pour plus d'informations, suivez d'autres articles connexes sur le site Web de PHP en chinois!