2017-07-31 6 views
11

Nous développons une application de bureau. Lors de l'exécution ProGuard (version 5.3.3) sur le code en utilisant les indicateurs de configuration suivants:Proguard - Impossible de trouver super classe commun/java.lang.VerifyError

-dontoptimize 
-allowaccessmodification 
-dontusemixedcaseclassnames 
-dontwarn 

Proguard donne l'erreur suivante:

Unexpected error while performing partial evaluation: 
    Class  = [com/code/backend/e/b/b] 
    Method  = [b(Ljava/lang/String;)Ljava/nio/file/Path;] 
    Exception = [java.lang.IllegalArgumentException] (Can't find common super class of [com/google/common/collect/ImmutableList] (with 2 known super classes) and [com/google/common/collect/UnmodifiableIterator] (with 1 known super classes)) 
Unexpected error while preverifying: 
    Class  = [com/code/backend/e/b/b] 
    Method  = [b(Ljava/lang/String;)Ljava/nio/file/Path;] 
    Exception = [java.lang.IllegalArgumentException] (Can't find common super class of [com/google/common/collect/ImmutableList] (with 2 known super classes) and [com/google/common/collect/UnmodifiableIterator] (with 1 known super classes)) 


FAILURE: Build failed with an exception. 

* What went wrong: 
Execution failed for task 'proguard'. 
> Can't find common super class of [com/google/common/collect/ImmutableList] (with 2 known super classes) and [com/google/common/collect/UnmodifiableIterator] (with 1 known super classes) 

Si le drapeau -dontpreverify est ajouté à la configuration de la construction allons réussir. Cependant lors de l'exécution du pot-fichier que nous obtenons alors l'erreur suivante:

Error: A JNI error has occurred, please check your installation and try again 
Exception in thread "main" java.lang.VerifyError: Expecting a stackmap frame at branch target 11 
Exception Details: 
    Location: 
    com/code/code2/MainWindow.b(Lcom/code/code2/ClientAPIProtos$SoftwareStatus;)V @1: ifnull 
    Reason: 
    Expected stackmap frame at this location. 
    Bytecode: 
    0x0000000: 2bc6 000a 2ab4 00bc c700 04b1 2bb2 00a4 
    0x0000010: a500 0a2b b800 f599 0018 2ab4 00bc b601 
    0x0000020: 9299 0020 2ab4 00bc 03b6 0193 a700 152a 
    0x0000030: b400 bcb6 0192 9a00 0b2a b400 bc04 b601 
    0x0000040: 932b b800 f699 0012 1225 4db8 0138 4e2a 
    0x0000050: 04b5 00c8 a700 0f12 1e4d b801 3a4e 2a03 
    0x0000060: b500 c82a b400 bcb6 0191 3a04 1904 c600 
    0x0000070: 0c2c 1904 b601 799a 000b 2ab4 00bc 2cb6 
    0x0000080: 0195 2ab4 00bc b601 903a 0519 05c6 0009 
    0x0000090: 2d19 05a5 000b 2ab4 00bc 2db6 0194 b1 

    at java.lang.Class.getDeclaredMethods0(Native Method) 
    at java.lang.Class.privateGetDeclaredMethods(Class.java:2701) 
    at java.lang.Class.privateGetMethodRecursive(Class.java:3048) 
    at java.lang.Class.getMethod0(Class.java:3018) 
    at java.lang.Class.getMethod(Class.java:1784) 
    at sun.launcher.LauncherHelper.validateMainClass(LauncherHelper.java:544) 
    at sun.launcher.LauncherHelper.checkAndLoadMain(LauncherHelper.java:526) 

qui peut être évité en utilisant le drapeau JVM -noverify. La lecture du fil:

Obfuscation causes VerifyError: Expecting a stackmap frame

Nous aimerions éviter ces drapeaux « aucune vérification » si possible.

Note: L'erreur de compilation se produit même lors de l'ajout

-dontobfuscate 
-dontshrink 

Répondre

6

Vous spécifiez l'option -dontwarn pour supprimer les avertissements relatifs aux références non résolues. Cela peut entraîner des problèmes lors du traitement du code. ProGuard a besoin de ces références, par ex. dans l'étape de préverification. L'erreur suggère en effet que l'entrée ne contient pas toutes les dépendances nécessaires: une superclasse commune ou une interface de ImmutableList et UnmodifiableIterator est manquante. Pour une application de bureau, vous devez vérifier que vous spécifiez un pot d'exécution Java avec toutes les classes nécessaires:

-libraryjars <java.home>/lib/rt.jar 

Voir le manuel ProGuard> Dépannage>Warning: can't find superclass or interface

2

Initialisation, la vérification et la validation font partie du projet de construction. Je crois que flag -allowaccessmodification est de permettre la modification lors de la construction du projet, c'est-à-dire que vos classes sont modifiées à partir de la structure d'origine. Lorsque la structure de classe d'origine est modifiée, les cadres des piles sont perturbés. Cela conduit à l'échec de la vérification. Si vous voulez ignorer l'erreur de vérification, alors comme mentionné, vous devez utiliser l'indicateur qui suspend la vérification.

1

Troubleshooting

ProGuard peut imprimer des notes et des avertissements non-fatals:

Remarque: impossible de trouver la classe référencée dynamiquement ProGuard ne trouve pas de classe ou d'interface à laquelle votre code accède par la moyenne s de l'introspection. Vous devriez vérifier si vous voulez ajouter le jar qui contient cette classe.

Remarque: ... appelle '(...) Class.forName (variable) .newInstance()' ProGuard répertorie tous les lancements de classe d'instances de classe créées dynamiquement, comme "(MyClass) Class.forName (variable) .newInstance() ". Selon votre application, vous devrez peut-être conserver les classes mentionnées avec une option comme "-keep class MyClass", ou leurs implémentations avec une option comme "-keep class * implémente MyClass". Vous pouvez désactiver ces notes en spécifiant l'option -dontnote.

Remarque: ... accède dynamiquement à un champ/méthode '...' ProGuard répertorie un certain nombre de constructions telles que ".getField (" myField ")".Selon votre application, vous devrez peut-être déterminer où les membres de classe mentionnés sont définis et les conserver avec une option comme "-keep class MyClass {MyFieldType myField;}". Sinon, ProGuard peut supprimer ou masquer les membres de la classe, car il ne peut pas savoir lesquels ils sont exactement. Il liste les candidats possibles, pour votre information. Vous pouvez désactiver ces notes en spécifiant l'option -dontnote.