Patching Java Executables – The Easy Way
The process of patching a Java executable (.jar files) without the original source code has been known for a while. As I know of, currently there are two ways of doing it:
- Decompile the executable > Import decompiled classes to an IDE (Eclipse, NetBeans, etc.) > Modify source code > Recompile > Repack
- Extract Java classes from executable > Modify Java Bytecode > Verify > Repack
Method (1) has big advantage if you are already familiar Java or similar OO-styled languages. However, in practice it has two main drawbacks:
- Typically, the targeted jar file has dependencies to other libraries. You should be familiar with linking those dependencies to your project
- The decompilation process is not an exact science, so expect to fix syntactical errors before getting it to recompile
On one project after importing a decompiled jar file into Eclipse there are nearly 1000 syntactical errors. Going through and fixing all of it would be a pain, especially what you want to do is just edit a few lines of code.
In this blog post, I want to introduce to you a method (2) of patching Java. It is faster, less error-prone and quite simple to execute. I hope it will be useful for developers that are in need of patching Java. Some potential use cases are:
- Bypass software restrictions (license, signature, hash, etc.)
- Patch security issues without original source code
- Inject custom code to application
In the example below, I will show you how to patch the JBoss encrypting library to use custom private key to encrypt data source strings.
Background
JBoss has a SecureIdentityLoginModule utility to encrypt data source password in XML configuration files. More info can be found at the JBoss Community Site. In JBoss 7, the module is located in picketbox-4.0.7.Final.jar
The actual command to encrypt the password is:
java -cp modulesorgJBossloggingmainJBoss-logging-3.1.0.GA.jar;modulesorgpicketboxmainpicketbox-4.0.7.Final.jar org.picketbox.datasource.security.SecureIdentityLoginModule password
Encoded password: 5dfc52b51bd35553df8592078de921bc
Problem
If you peek into the source code, the utility is using Blowfish encryption algorithm with a fixed key set to: “jaas is the way”. There is already a tool to decrypt it located at https://usefulfor.com/security/2009/09/24/beware-of-JBoss-secureidentityloginmodule/.
Objective
The objective is to modify default private key. The key is still in the jar file and you can call the corresponding decode() function of the jar file to decrypt it anyway. Hence for a production system I would recommend switching to use the keystore-based JaasSecurityDomainIdentityLoginModule instead. More information could be found at https://community.JBoss.org/wiki/EncryptingDataSourcePasswords.
High-level steps:
- Setup the environment
- Use JD-GUI to peek into the jar file
- Unpack the jar file
- Modify the .class file with a Java Bytecode Editor
- Repack the modified classes into new archive file
- Verify it with JD-GUI
Step 1: Setup the Java environment
Most computers should have the JRE installed by default. For this tutorial, you will need to download and install the latest version of JDK. For this example, I am using JDK 6 update 35.
You may also need to add the JDK bin folder to your PATH environment variable. Upon completion, open up a command line console and type:
java -version
The result should look something like this:
java version “1.6.0_35″
Java(TM) SE Runtime Environment (build 1.6.0_35-b10)
Java HotSpot(TM) 64-Bit Server VM (build 20.10-b01, mixed mode)
Step 2: Use JD-GUI to peek into the jar file
Bytecode editors typically do not support decompiling Java executables. For that reason, I prefer to use a standalone decompiler to quickly browse decompiled classes and identify potential classes/methods. My favorite tool for this task is JD-GUI (we also need it later on to verify the modified bytecode):
As shown in the picture above, browsing to SecurityIdentityLoginModule reveals the default secret key used to encrypt string.
Step 3: Unpack the jar file
The below commands will create new directory > Copy jar file > Extract all the classes (note that in Windows you can use 7zip to extract them as well)
cd <JBOSS_HOME>modulesorgpicketboxmain
mkdir picketbox
cp picketbox-4.0.7.Final.jar picketbox
cd picketbox
jar -xf picketbox-4.0.7.Final.jar
Step 4: Modify the .class file with a Java Bytecode Editor
Download and run Java Bytecode Editor (JBE)
In this example we need to modify two methods of SecureIdentityLoginModule class: encode() and decode(). Note that the original encryption/decryption methods only work with 16-character key. To keep it simple, I will modify default key “jaas is the way” to “java is the way” to keep the length intact.
Step 5: Repack the jar file
Take the changed class file and repack the jar file
cd picketbox
jar -cvf picketbox.jar *.*
Step 6: Verify the changes with JD-GUI
JBE tool has Code Verification feature, but in practice, I found it complains too much . Hence, I use JD-GUI again to verify correctness of the modified jar file.
If there’s any error in the modified class file, JD-GUI will not able to render the new jar file. If things go well, you should see your changes reflected in the patched jar file:
Final test:
java -cp modulesorgJBossloggingmainJBoss-logging-3.1.0.GA.jar;modulesorgpicketboxmainpicketbox.jar org.picketbox.datasource.security.SecureIdentityLoginModule password
Encoded password: 3f8c894b05a5462a4a06c734ae626874
The last step would be overwriting the patched file to the original one.
I hope you had fun. Thanks Steve for helping me proofread this and happy hacking!
References:
https://java.decompiler.free.fr/?q=jdgui
https://www.oracle.com/technetwork/java/javase/downloads/jdk6u35-downloads-1836443.html
https://community.JBoss.org/wiki/EncryptingDataSourcePasswords
https://usefulfor.com/security/2009/09/24/beware-of-JBoss-secureidentityloginmodule/
Explore more blog posts
CTEM Defined: The Fundamentals of Continuous Threat Exposure Management
Learn how continuous threat exposure management (CTEM) boosts cybersecurity with proactive strategies to assess, manage, and reduce risks.
Balancing Security and Usability of Large Language Models: An LLM Benchmarking Framework
Explore the integration of Large Language Models (LLMs) in critical systems and the balance between security and usability with a new LLM benchmarking framework.
From Informational to Critical: Chaining & Elevating Web Vulnerabilities
Learn about administrative access and Remote Code Execution (RCE) exploitation from a recent Web Application Pentest.