FROMDEV

Securing your code: Techniques Beyond Java Obfuscation

Reverse engineering Java classes is very easy and Obfuscation also can not stop anyone from reverse engineering your proprietary class. but it makes it far too difficult to reverse engineer and utilize the same code. I was writing a key generation algorithm and thought it should not be reverse engineered easily.

I tried obfuscation by Proguard : http://proguard.sourceforge.net/ and it did a good job in obfuscating my code. I tried decompiling using Eclipse Jadclipse plugin: http://sourceforge.net/projects/jadclipse/ which is a really good decompiler and did most of the Java code generation pretty well.

The generated Java files have few classes which are as is, and a few are obfuscated. so when I try understanding the logic inside the code it gets little difficult to understand. But I didnt want to stop here, I need to create more confusion in the regenerated code. So here are few techniques I wanted to share which can make your code reverse engineering a nightmare for anyone. I am sure these techniques are not best way of implementing your code, and there could be other issues in implementing them, but in case your only goal is to keep your code safer and not easily being copied then this may sound useful.

Code inside finally block

If you see a decompiled Java file most difficult areas are the once where we have Exception handling, this code is usually replaced with the lines like

JVM INSTR dup ;

L1: So thought of utilizing this piece. Here is what I tried. I created a try/catch block in my code and called a dummy method which does nothing. And then I surround this by lots of RuntimeException catch and finally blocks. Then move the actual code inside the finally block.

Now when I obfuscate and then de-compile the classes. Now decompiler is generating a lot of code for a small method which had only one block of code in finally block.

Here is the example what I did

private String myCoreMethod1(String s) {

try
{

doSomeStuff();
} catch
(SecurityException e) {

System.err
.println(e);
} catch
(NumberFormatException e) {

System.err
.println(e);
} catch
(RuntimeException e) {

System.err
.println(e);
} finally
{

//My Secret Code here
}
}
}
return
s;
}

private
void doSomeStuff() {

//Doing nothing
}

This technique should make your de-compiled code really difficult to understand, I have tried Jadclipse plugin to decompile, but I am sure this is goiong to be pretty much confusing for other decompilers as well.

Code inside Inner Classes

Another way of coding I observed is Inner classes. If your code is written inside a inner class it makes it far more complex to understand when its decompiled. Create a LocalImplementation inner class in your code which has your core methods implemented. This way reaching to core method level becomes difficult while doing code walk thru. In fact if you can write the same implementation in a annonymous inner class then it can make it more difficult.

Use of Reflection

Java Reflection is a powerfull way of dynamically loading and invoking classes/methods. Using Reflection code to call your key methods may make it difficult for people to understand as it does not tell which method is being called. This is how I did it, Keep a list of core classes which has core methods. Also have a list of core method names which need to be called, now interate through the list of classes and call each method one by one. If the class does not have a method then go for next class this way you can make it more un-obvious to undestand the sequence of calls. Well I know this is not the best way but there could be many ways of creating such confusions. I know its not the best use of reflection, but to hide my core algorithm I would probably do it.

All of above techniques are to make it reverse engineered code more complex, but you may need to maintain the same code yourself so make sure following things

  • Writing a utility for such a custom obfuscation would be a good idea for your project, if this can be done the you can follow standard code practices and run the custom obfuscator on distribution jars.
  • If you are not creating a utility then: Try to apply above technique in only the code piece which you would want to make difficult to understand.
  • Document it, so that new developers to maintain or enhance can understand the practice and follow it too.
Beyond Obfuscation, tricks for obfusction, techniques of obfuscation, code safety, securing java code, making decompiler useless, can not decompile class file, obfuscation techniques, obfuscation, Obfuscator, simple tricks beyond obfuscation, simple tricks after obfuscation, effective obfuscation, difficult decompilation, difficult to pirate java code
Exit mobile version