Ramesh has posted 1 posts at DZone. View Full User Profile

Protect Your Java Code From Reverse Engineering

06.17.2008
| 39221 views |
  • submit to reddit

If you are developing a Java application, it is important to understand that the Java class files can be easily reverse-engineered using Java decompilers. In this article, let us explore how a Java class file is reverse-engineered and how to protect your source code from this.

Java source code is compiled to a class file that contains byte code. The Java Virtual Machine needs only the class file for execution. The problem is that the class file can easily be decompiled into the original source code using Java decompiler tools. The best solution to prevent reverse-engineering is to obfuscate the class file so that is will be very hard to reverse-engineer. According to the dictionary Obfuscate means “to make obscure or unclear”. That is exactly what lot of Java obfuscator tools do as explained below.

Decompile Java class file.

Before understanding how to obfuscate the java code, let us first try to understand how someone can reverse engineer your java application. Following 3 steps explains how a class file is reverse engineered to the original java source code.

1. Create HelloWorld.java as shown below.

public class HelloWorld {
    public static void main (String args[]) {
        String userMessage = “Hello World!”;
        int userCount = 100;
        userCount = userCount + 1;
        System.out.println(userMessage);
        System.out.println(userCount);
    }
}

2. Compile HelloWorld.java program and execute it to make sure it works properly.

$ javac HelloWorld.java
$ java HelloWorld
Hello World!
101

Java class file contains only byte code. If you try to view a class file, it will be non-readable as shown below.

$ vi HelloWorld.class
Ãþº¾^@^@^@2^@
^@^G^@^P^H^@^Q  ^@^R^@^S
^@^T^@^V^G^@^W^G^@^X^A^@^F<init>^A^@^C()V^A^@^DCode^A^@^OLineNumberTable
^A^@^Dmain^A^@^V([Ljava/lang/String;)V^A^@
SourceFile^A^@^OHelloWorld.java^L^@^H^@ ^A^@^LHello World!^G^@^Y^L^@^Z^@^[^G^@^\^L^@^]^@^^^L^@^]^@^_^A^@
HelloWorld^A^@^Pjava/lang/Object^A^@^Pjava/lang/System^A^@^Cout^A^@^ULjava/io/PrintStream;^A
^@^Sjava/io/PrintStream^A^@^Gprintln^A^@^U(Ljava/lang/String;)V^A^@^D(I)V^@!^@^F^@^G^@^@^@^@^@^B^@^A^@^H^@  ^@^A^@

3. Decompile HelloWorld.class file and view the original source.

For this demonstration let us use Jad decompiler which is free for non-commercial use. Download the appropriate jad for your platform. Use jad to reverse-engineer the HelloWorld.class file to get the original source as shown below.

$ unzip jadls158.zip
$ ./jad HelloWorld.class
Parsing HelloWorld.class...
Generating HelloWorld.jad
$ vi HelloWorld.jad <This will show the reverse engineered original source code>

Obfuscate your java application

Let us review how to obfuscate and protect your source code from reverse engineering using ProGuard a free GPL licensed software.

1. Download and Install ProGuard

$ cd /home/jsmith
$ unzip proguard4.2.zip

2. Create a proguard config file

Create myconfig.pro that contains all the information about your java application.

  • -injar : Specify the location of your jar file. i.e the compiled java application that contains the class files
  • -outjar: This is the jar file proguard will create after obfuscation. This will contain all the mangled, obscure naming convention of the methods and variables in the class file if someone tries to reverse engineer.
  • -printmapping: ProGurad outputs all the mapping information in this file for your reference.
  • -keep: Indicate the class files or the methods that you don’t want ProGuard to obfuscate. For e.g. mypkg.MainAppFrame contains the entry point for the application with the main class, which will not get obfuscated in this example.
$ cat myconfig.pro
-injars /home/jsmith/myapp.jar
-outjars /home/jsmith/myapp-obfuscated.jar This is the obfuscated jar file
-libraryjars /usr/java/jdk1.5.0_14/jre/lib/rt.jar
-printmapping proguard.map
-verbose
-keep public class mypkg.MainAppFrame

3. Execute ProGuard.

$ cd /home/jsmith/proguard4.2/lib
$ java -jar proguard.jar @myconfig.pro

This creates the following two files:

  • myapp-obfuscated.jar: Contains the obfuscated class files of your application. You can distribute this without having to worry about someone reverse engineering your application easily.
  • proguard.map: This file contains the mapping information for your reference.

4. Sample proguard.map file

This is a sample proguard.map file that indicates the original name of the java source objects (classfile, methods, variable etc.) and the new obfuscated name.

myapp.AppToolBar -> myapp.ae:
javax.swing.JButton btnNew -> d
javax.swing.JButton btnOpen -> e

5. Sample java source code (myapp.AppToolBar) before obfuscation.

btnNew = changeButtonLabel(btnNew, language.getText("new"));
btnOpen = changeButtonLabel(btnOpen, language.getText("open"));

6. Sample java source code that was decompiled from the class file (myapp.ae) after obfuscation.

d = a(d, n.a("new"));
e = a(e, n.a("open"));

You can see that the line “btnNew = changeButtonLabel(btnNew, language.getText(”new”));” got translated to “d = a(d, n.a(”new”));”, by the ProGuard, which will not make any sense to someone who is using java decompiler tools to reverse engineer the class file.

From http://www.thegeekstuff.com

Published at DZone with permission of its author, Ramesh Natarajan.

(Note: Opinions expressed in this article and its replies are the opinions of their respective authors and not those of DZone, Inc.)

Comments

Thomas Baldwin replied on Tue, 2008/06/17 - 5:02am

Years back I tried a similar product. I still remember that one had problem with dynamic class loading. For example, if some code loads "HelloWorld.java" by calling Class.forName("HelloWorld") method, that obfuscator wasn't smart enough to change this string while updating class signature. I hope this problem has been solved.

Raphael Valyi replied on Tue, 2008/06/17 - 5:28am

tranquiliser,

 You can usually exclude some packages or classes from obfuscation to avoid this kind of trouble. Also notice that once you do things like class.forName("foo"), there is not always a consistent way of updating the obfuscation, indeed "foo" can result of arbirary string operations so once you use the Java reflection API, you should use code obfuscation really carefully.

 Also, usually, the best framworks and code use to keep the codebase small and consistent by using the reflection API a lot (like for serialisation, persistence...) . Also notice that higher productivity language such as (J)Ruby and co also use a very powerfull reflection API to boost their meta programming abilities and provide, in turn, simple frameworks to use such as Rails.

That's why I think traditionnal code obfuscation days are more or less counted, open source just won that battle as well. Unless may be the JVM level code obfuscation such as for instance compiling a JRuby code to .class files which don't mapp back to java source class while preserving metaprogramming abilities (untill a JRuby .class decompiler is written but given the JRuby compiler features, this won't be easy)...

 Regards,

 Raphaël Valyi.

Jakob Jenkov replied on Tue, 2008/06/17 - 7:51am

You could also encrypt the class files. I think this what IntelliJ IDEA does. Not 100% secure, but works against the average joe blocks trying to reverse-engineer your code.

Ignacio Coloma replied on Wed, 2008/06/18 - 3:13am

I hate when people obfuscate their code just to keep some should-be secret sauce recipe to themselves. Most of the time they just put things in the way to debugging their own framework.

Last week I had to debug a NPE in a framework where the stack trace only included 'a', 'b' and 'c' methods. It's paranoid, if you are going to obfuscate your code, at least make it bug-free.

Akarsh MG replied on Thu, 2008/06/26 - 5:00am

Hi,

Very much interesting post on the reverse engineering.

I was assigned to a project where we did not have the source code of the project as the person who was earlier working had moved out of the organization, finally after sometime other people where assinged to carry outt this task, the project moved around with different teams and finally some one was about to start the realised the source code of project was missing.

Finally our team got this project, we just got the class files whatever that was stored in the server. 

I used DJ Decompiler and JAD to decompile, it took almost entire 4 months to get the entire application running without any problems.

After it launch now its been used by 100's of users.

I defientely see the are pros and cons in reverse engineering.

Regards,
Akarsh

 

 

 

Michael Manske replied on Sun, 2008/06/29 - 11:14am in response to: Ignacio Coloma

Real-world business applications mostly contain business rules or at least algorithms based on months or years of research and analysis. Such business secrets make the difference between a product and it's competitors. For commercial applications it is just a must-have to protect the intellectual property. No other developer should be able to "debug" such a product. If it contains an error, the software producer has to fix it. It might be another case with frameworks. You are right, frameworks - even commercial frameworks - shouldn't be obfuscated or they should at least offer the sources after signing a non-dislosure agreement.

Gabriele Kahlout replied on Sun, 2011/04/17 - 1:36am in response to: Raphael Valyi

@Raphael - could you explain with an example what you mean by:

class.forName("foo"), there is not always a consistent way of updating the obfuscation, indeed "foo" can result of arbirary string operation

Jack Jackson replied on Tue, 2013/07/23 - 10:26am

The 100% pure Java protection against reverse-engineering does not exist at all, but the idea is that we can add enough security layers to make that hacking process almost impossible due to the time effort. For example, Shield4J obfuscates the Java bytecodes and optionally it can encrypt Strings and encrypt the resulting obfuscated classes. There are lots of similar tools/services on the internet, open source or commercial. When more security layers, better.

Comment viewing options

Select your preferred way to display the comments and click "Save settings" to activate your changes.