Proguard warning with [java/lang/String] - java

I'm facing issue with proguard. I've some rules in proguard and one of them is:
-keep class org.jmrtd.** { *; }
-dontwarn org.jmrtd.**
But I've getting this warning when building
Unexpected error while performing partial evaluation:
Class = [org/jmrtd/MRTDFileSystem]
Method = [readBinary(II)[B]
Exception = [java.lang.IllegalArgumentException] (Can't find common super class of [java/lang/String] (with 2 known super classes) and [org/jmrtd/MRTDFileSystem$MRTDFileInfo] (with 1 known super classes))
Unexpected error while preverifying:
Class = [org/jmrtd/MRTDFileSystem]
Method = [readBinary(II)[B]
Exception = [java.lang.IllegalArgumentException] (Can't find common super class of [java/lang/String] (with 2 known super classes) and [org/jmrtd/MRTDFileSystem$MRTDFileInfo] (with 1 known super classes))
Can anybody help me?
Thank you.

It looks like a problem with library jar. Are you sure all libraries is configured properly? MRTDFileInfo is an inner class of MRTDFileSystem, which might be referenced internally.
The processing steps are as follows:
Input Jar --> Strink --> Optimize --> Obfuscate --> Preverify --> output jar
Based on your error trace you are getting an error during the Preverify step: Unexpected error while preverifying
If you want to skip this erorr you can simply use prevent Proguard from preverifying:
-dontpreverify
It will skip preverifying, but I doubt that the jar will run properly
I would suggest you provide your library jars correctly , so that proguard can refer them.
Also apart from -dontwarn , you can also use -ignorewarnings
hope this help in debugging issue.

Related

java.lang.NoClassDefFoundError only in particular conditions

My problem is that when class B tries to use A.check() my execution stops due to a java.lang.NoClassDefFoundError.
So here is my class configuration. NB: the classes are in the same packages and I have already checked that the A.class file is placed where it should be.
public class A{
// vars
// declare some public method
public synchronized static boolean check(){
//do stuff, log some info and return boolean
}
}
public class B implements Runnable{
public void run() {
A.check();
}
}
And here is my stacktrace:
java.lang.NoClassDefFoundError:
org/mypackage/A
at org/mypackage.B.run()
at java.lang.Thread.run(Thread.java:745)
Caused by: java.lang.ClassNotFoundException:
org/mypackage.B
at org.codehaus.plexus.classworlds.strategy.SelfFirstStrategy.loadClass(SelfFirstStrategy.java:50)
The project is really big and class A is used lots of times before this call without any problem, so i don't think that is something relative to the classpath. Note that this is part of the last call of the software that should close up everything.
Moreover, I have two maven goals: the first one execute the questioned code without any problem, instead the second rise this error every time.
So I have solved my problem and I post here the solution so maybe can be useful for someone else.
First of all the error: java.lang.NoClassDefFoundError
This error is really different from ClassNotFoundException and this is where I'have lost a lot of time.
NoClassDefFoundError in Java is raised when JVM is not able to locate a particular class at runtime which was available at compile time. For example, if we have a method call from a class accessing any member of a Class and that class is not available during runtime then JVM will throw NoClassDefFoundError. It’s important to understand that this is different than ClassNotFoundException which comes while trying to load a class at run-time only and the name was provided during runtime, not on compile time. Many Java developer mingles this two Error and gets confused. Here I quote a really useful blog that I uesd.
So in a shorter way NoClassDefFoundError comes if a class was present during compile time but not available in java classpath during runtime.
But even with those information the problem was still there until I found the mystery: one of the reason that can place the class in a state that can be compiled but not located at runtime is that if you have static initialization that fail (e.g. in my class I had as field a static variable instantiated badly).
So remember to check for you initialization phase if you have static variables in your class this could be the reason of your java.lang.NoClassDefFoundError.
By the way I don't get why this kind of error is not raising some more meaninful errors for example java.lang.ExceptionInInitializerError or something like that.
Try to debug maven execution by running: mvn -X <your_goals>
It would be useful to see your POM file.
If you are working with spring mvc and if you made bean entry in dispatche-servlet.xml for Controller class.
Example :
<bean id="MyClass" class="com.aaps.myfolder.MyClass">
<property name="methodNameResolver">
<ref bean="methodNameResolver" />
</property>
</bean>
And if MyClass.java is not compiled & if no class file is generated in classes folder of your project folder then it wil show java.lang.NoClassDefFoundError.
So check whether the MyClass.class is created or not in classes folder if you are working with spring mvc.
Does Class A have anything that is done in a static block. You can get this exception even if a class is being loaded and static blocks fails for any reason reason. try to put in logging to see if something like this is happening.

Android - why do I get this lint error: "This class should be public (android.support.v7.internal.widget.ActionBarView.HomeView)"

This class should be public
(android.support.v7.internal.widget.ActionBarView.HomeView)
Issue: Ensures that classes registered in the manifest file are
instantiatable Id: Instantiatable
Activities, services, broadcast receivers etc. registered in the
manifest file must be "instantiatable" by the system, which means that
the class must be public, it must have an empty public constructor,
and if it's an inner class, it must be a static inner class.
This lint error with the Support Library - which occurs when I try to export my (unobfuscated) Android project - is also described in this SO question. But why does this error occur in the first place? (Is it a bug with the Support Library?)
The suggested advice in that question is to just disable/downgrade the lint message to a 'Warning', but is it perfectly safe/correct to do that (i.e., maybe that is papering over some cracks?) or is there a better solution?

ProGuard ignoring annotation default values

The Issue
I'm having a problem with ProGuard 4.11 (An application that can optimize, shrink and obfuscate Java code), using the proguard-maven-plugin (github.com/wvengen/proguard-maven-plugin) (Although that shouldn't matter that much, since the error is occurring at runtime and the maven plugin just calls the binary with some arguments as far as I know).
I have an annotation class which is stuctured like this (nothing special):
#Retention(RetentionPolicy.RUNTIME) #Target(ElementType.FIELD)
public #interface SqlValueCache {
String value();
SqlValueCache.Type type() default Type.OBJECT_UPDATE; //Type is just an ordinary enum
}
I also have some fields annotated with that annotation, but I'm skipping the type() parameter because I want to use the default value:
#SqlValueCache("nickname")
protected SqlValueHolder<String> nick;
Now I want to process that annotation at runtime:
SqlValueCache annotation = field.getAnnotation(SqlValueCache.class); //Skipped the validation
annotation.value(); //Works fine, because specified
annotation.type(); //java.lang.annotation.IncompleteAnnotationException, *not* using the default
As stated in the comment above, I get an IncompleteAnnotationException, stating that my annotation declaration is missing the type() value. But that value should be implied by the default Type.OBJECT_UPDATE! So now I'm wondering, why is that happening?
Assumptions
I assume that the default thing is stored in some kind of attribute that I need to specify in -keepattributes, but I haven't been able to figure out if this is true or which one it is.
Reproduction
It does work just as intended when not using ProGuard.
I have also made sure that the problem is in fact the missing implied value - The code runs as intended when using ProGuard, but explicitly specifying the type(), like so:
#SqlValueCache(value = "nickname", type = Type.OBJECT_UPDATE)
protected SqlValueHolder<String> nick;
I am using this method as a temporary workaround, but this isn't the prettiest solution in my opinion. Also, as stated above, I still want to know why this error is happening.
Thanks in advance for reading and investigating my question! :)
Appendix/Meta
Yes, I did search the web for solutions and did also use the StackOverflow searchbox. Using the title of this question and various other search queries, I could only find questions complaining about no annotations being kept at all or asking to keep subclasses of classes annotated, etc. I also searched for the exception, but the only useful result was the JavaDoc (docs.oracle.com/javase/7/docs/api/java/lang/annotation/IncompleteAnnotationException.html) of the exception I am encountering.
I'm sorry about the links, but I apparently need 10 reputation to post more than two, although I really like linking stuff :/
Stacktrace
I have attached the Stacktrace I got in console (class names won't be useful at all in my opinion - I can attach them if really necessary; My classes are also loaded by a custom class loader, but I doubt that that makes any difference):
java.lang.ExceptionInInitializerError
at <class with annotated field>
(...)
Caused by: java.lang.annotation.IncompleteAnnotationException: io.github.xxyy.common.sql.builder.annotation.SqlValueCache missing element type
at sun.reflect.annotation.AnnotationInvocationHandler.invoke(AnnotationInvocationHandler.java:72) ~[?:1.7.0_51]
at com.sun.proxy.$Proxy18.type(Unknown Source)
at <line accessing type() of SqlValueCache>
(...)
ProGuard config
Here's my ProGuard config, should that be of any help (That's the part I find relevant to this question - Full file here: pastebin.com/u6wt00cj):
-dontskipnonpubliclibraryclassmembers
-target 1.7
-dontshrink
-dontoptimize
-repackageclasses io.github.xxyy.obf.towerdefense.client
-keepattributes SourceFile,LineNumberTable,*Annotations*,LocalVariable*Table
-keep,allowobfuscation class ** {
<fields>;
<methods>;
}
-keep,allowshrinking class **.annotation** {
<fields>;
<methods>;
}
# Also keep - Enumerations. Keep the special static methods that are required in
# enumeration classes.
-keepclassmembers enum ** {
public static **[] values();
public static ** valueOf(java.lang.String);
}
You also need to keep the AnnotationDefault attribute:
-keepattributes AnnotationDefault
You can get the same effect by changing *Annotations* to *Annotation* in your current -keepattributes option, so the wildcards match AnnotationDefault.

NoClassDefFoundError exception in my thread

I get this error:
Exception in thread "http-server" java.lang.NoClassDefFoundError: org/w3c/jigmonitor/ReplyServer
but I don't undestand why. Could someone explain why does this happen?
This is the class that causes the problem:
public class ReplyServer implements Serializable
{
public ReplyServer()
{
super();
}
}
It looks like the class you're defining isn't being found by something that's trying to load it. In my experience this is caused by one of three problems:
Your package declaration for the class is not correct. In this case something on the http-sever thread is expecting your class to be declared in the package org.w3c.jigmonitor.
Your source file is not located in the correct directory. In this case, your source file should be located in a directory structure like "org/w3c/jigmonitor/", providing that's the package you actually want.
The path of the compiled class for ReplyServer is not in the classpath of your JVM. You can check this by looking at the classpath used to start your JVM and seeing if the class is actually there or not. In most generic setups servlet setups there will be a "WEB-INF/classes" folder for you to go poke around in.
Good luck!
(The link David posted gives a ton of information on this type of issue and the possible causes. I would recommend tucking that away for later)

#NotThreadSafe not found error

0.3 code.
#NotThreadSafe
public class VoicemailPlaybackFragment extends Fragment {
//
}
I am getting compile time error as "NotThreadSafe cannot be resolved to a type"
i.e, #NotThreadSafe not imported
can anyone help, thanks in advance.
That annotation is not in the standard Java or Android codebases yet.
Depending on how and why you are using this, you should either add some third-party JAR containing it to your classpath, or just add a copy to your codebase.
This page lists a few products that include the annotation.

Categories