Exetools  

Go Back   Exetools > General > General Discussion

Notices

Reply
 
Thread Tools Display Modes
  #1  
Old 09-12-2019, 23:27
Chuck954 Chuck954 is offline
Friend
 
Join Date: Jul 2018
Posts: 42
Rept. Given: 0
Rept. Rcvd 8 Times in 6 Posts
Thanks Given: 21
Thanks Rcvd at 52 Times in 31 Posts
Chuck954 Reputation: 8
Reversing obfuscated and encrypted JAR file

I have tried numerous tools and haven't found much luck. I have a program that I have pretty much cracked but not completely. A handful of options need the jar file to run and if the jar file runs it closes out the program.

The program starts java.exe and it opens the encrypted jar file and runs it. I believe it was obfuscated with proguard. It has a few classes in it that show it decrypting the stream and reading the class files. However the majority of the files inside it are encrypted and you can't tell anything. I took a dump in visualvm.exe and I can see a lot of info but nothing stands out yet. Not sure if anyone has any advice on how I might be able to decrypt the classes so I can see it?

This is the code of one of the loader files it has. All the public deobfuscation tools failed. I'm guessing since it's encrypted as well. I'm not very familiar with java yet so any pointers would help.

Thanks!

Code:
import java.io.ByteArrayInputStream;
import java.io.ByteArrayOutputStream;
import java.io.InputStream;
import java.io.OutputStream;
import java.net.URL;
import java.net.URLClassLoader;
import java.util.zip.GZIPInputStream;
import java.util.zip.GZIPOutputStream;

public class LoaderB
  extends URLClassLoader
{
  protected LoaderB(ClassLoader parent, LoaderB prevClsLoader)
  {
    super(new URL[0], parent);
  }
  
  public void init(String[] args) {}
  
  static byte[] zip(byte[] data)
  {
    try
    {
      ByteArrayInputStream bais = new ByteArrayInputStream(data);
      ByteArrayOutputStream baos = new ByteArrayOutputStream();
      
      GZIPOutputStream gzos = new GZIPOutputStream(baos);
      
      byte[] b = new byte['?'];
      
      int i = bais.read(b);
      while (i != -1)
      {
        gzos.write(b, 0, i);
        i = bais.read(b);
      }
      gzos.finish();
      gzos.flush();
      gzos.close();
      
      return baos.toByteArray();
    }
    catch (Exception e)
    {
      e.printStackTrace();
    }
    return null;
  }
  
  static byte[] load(InputStream is)
  {
    try
    {
      ByteArrayOutputStream baos = new ByteArrayOutputStream();
      
      byte[] b = new byte['?'];
      
      int i = is.read(b);
      while (i != -1)
      {
        baos.write(b, 0, i);
        i = is.read(b);
      }
      baos.flush();
      baos.close();
      
      return baos.toByteArray();
    }
    catch (Exception e)
    {
      e.printStackTrace();
    }
    return null;
  }
  
  public static byte[] unzip(byte[] data)
  {
    try
    {
      ByteArrayInputStream bais = new ByteArrayInputStream(data);
      ByteArrayOutputStream baos = new ByteArrayOutputStream();
      
      GZIPInputStream gzis = new GZIPInputStream(bais);
      
      byte[] b = new byte['?'];
      
      int i = gzis.read(b);
      while (i != -1)
      {
        baos.write(b, 0, i);
        i = gzis.read(b);
      }
      baos.flush();
      baos.close();
      
      return baos.toByteArray();
    }
    catch (Exception e)
    {
      e.printStackTrace();
    }
    return null;
  }
  
  static byte[] crypt(Crypter crypter, byte[] data)
  {
    try
    {
      ByteArrayOutputStream baos = new ByteArrayOutputStream();
      OutputStream os = crypter.getOutputStreamE(baos);
      
      os.write(data);
      
      os.flush();
      os.close();
      baos.close();
      return baos.toByteArray();
    }
    catch (Exception e)
    {
      e.printStackTrace();
    }
    return null;
  }
  
  static byte[] decrypt(Crypter crypter, byte[] data)
  {
    try
    {
      ByteArrayInputStream bais = new ByteArrayInputStream(data);
      InputStream is = crypter.getInputStreamD(bais);
      
      ByteArrayOutputStream baos = new ByteArrayOutputStream();
      
      byte[] b = new byte['?'];
      
      int i = is.read(b);
      while (i != -1)
      {
        baos.write(b, 0, i);
        i = is.read(b);
      }
      baos.flush();
      baos.close();
      
      return baos.toByteArray();
    }
    catch (Exception e)
    {
      e.printStackTrace();
    }
    return null;
  }
}
Reply With Quote
  #2  
Old 09-13-2019, 15:03
chants chants is offline
Family
 
Join Date: Jul 2016
Posts: 456
Rept. Given: 2
Rept. Rcvd 30 Times in 18 Posts
Thanks Given: 373
Thanks Rcvd at 723 Times in 331 Posts
chants Reputation: 30
If it launches a separate java.exe instance, can just look at the command line and see where the jar file is located and grab it?

The code above does not contain crypter which does the encrypt/decrypt, though its doubtful needed since you will use java and this class to do the work anyway. But also we do not see the loader which actually "executes" the "jar" file.

Otherwise, either check for process functions which invoke JVM java.exe or look for code along the lines of:
Code:
// Create a new JavaClassLoader 
ClassLoader classLoader = this.getClass().getClassLoader();

// Load the target class using its binary name
Class loadedMyClass = classLoader.loadClass(classBinName);
Then you can also trace how the class is processed before loading if you want the jar in case it is not invoked by java.exe but instead by dynamic loading. Check more topics on dynamic loading for more info.
Reply With Quote
  #3  
Old 09-13-2019, 21:47
Chuck954 Chuck954 is offline
Friend
 
Join Date: Jul 2018
Posts: 42
Rept. Given: 0
Rept. Rcvd 8 Times in 6 Posts
Thanks Given: 21
Thanks Rcvd at 52 Times in 31 Posts
Chuck954 Reputation: 8
Thanks for getting back. I know exactly where the jar is and in IDA I can see where it gets the command line info to launch java and the jar file. I can use a tool like APImonitor to see it load java and what APIs are called.

When I extract the JAR contents it has two folders

META-INF which has maven, a services folder and lib folder.

Second folder starts with VN and has the class files. I've seen it mention VNcrypt a few times.

Uploaded a screenshot of the VN folder with these files.

It has 5 .class.
LoaderNoWait.class
LoaderJfx.class
Loader.class
LoaderB.class
a0.class

Then it has 19 .clasz files

a1.clasz
a2.clasz
a3.clasz
through
a17.clasz
a27.clasz
a36.clasz

In the first folder with the META-INF and VN folder, it has around 35,000 files. I took a screenshot of some of them. All look like that.

https://imgur.com/mjrlApo

https://imgur.com/wutVgq6


I believe I can change the command line that loads java and the jar file if needed. Thanks for your time!
Reply With Quote
  #4  
Old 09-27-2019, 20:52
Chuck954 Chuck954 is offline
Friend
 
Join Date: Jul 2018
Posts: 42
Rept. Given: 0
Rept. Rcvd 8 Times in 6 Posts
Thanks Given: 21
Thanks Rcvd at 52 Times in 31 Posts
Chuck954 Reputation: 8
I have made some progress with it and found a decent Java debugger that allows me to step through code and pause it as it decrypts and unzips the classes. I used a hex editor and found the class starts when I see CAFE BABE in the memory. It's kind of a pain to figure out what's the complete class or just part of it as well as where it ends.

Anyone have any suggestions on how to intercept the Java byte-code in the memory without painstakingly searching through memory.

At the moment I'm just trying to get all the byte code for the encrypted classes and see what I'm working with.
Reply With Quote
The Following User Gave Reputation+1 to Chuck954 For This Useful Post:
user1 (09-27-2019)
The Following User Says Thank You to Chuck954 For This Useful Post:
user1 (09-27-2019)
  #5  
Old 09-29-2019, 18:54
sendersu sendersu is offline
VIP
 
Join Date: Oct 2010
Posts: 830
Rept. Given: 324
Rept. Rcvd 216 Times in 110 Posts
Thanks Given: 168
Thanks Rcvd at 342 Times in 192 Posts
sendersu Reputation: 200-299 sendersu Reputation: 200-299 sendersu Reputation: 200-299
whats the name of "a decent Java debugger that allows me to step through code and pause it "

never seen such a tool before to be honest...
is it a kind of super tool for .net - dnSpy?
Reply With Quote
  #6  
Old 09-29-2019, 20:59
Chuck954 Chuck954 is offline
Friend
 
Join Date: Jul 2018
Posts: 42
Rept. Given: 0
Rept. Rcvd 8 Times in 6 Posts
Thanks Given: 21
Thanks Rcvd at 52 Times in 31 Posts
Chuck954 Reputation: 8
Well perhaps "step through code" is a bit of a stretch since I don't have original source, although I have managed to get several of the decrypted byte code classes from memory. I can set a breakpoint as each class is loaded and it pauses after each decryption so I can get the decrypted byte code in memory

I have only been studying Java for a few months and so still learning quite a bit. I found a newer version of jdebug with a 30 day trial. However the authors domain expired. I found an earlier version with a crack below. It's not perfect and kind of cumbersome but it allowed me to view the stack and a lot of different data. There was another one but I forgot the name at the moment.


https://webscene.ir/tools/show/JDebugTool-and-crack-v4.1.1
Reply With Quote
The Following 2 Users Say Thank You to Chuck954 For This Useful Post:
niculaita (09-29-2019), sendersu (09-30-2019)
  #7  
Old 09-30-2019, 02:14
sendersu sendersu is offline
VIP
 
Join Date: Oct 2010
Posts: 830
Rept. Given: 324
Rept. Rcvd 216 Times in 110 Posts
Thanks Given: 168
Thanks Rcvd at 342 Times in 192 Posts
sendersu Reputation: 200-299 sendersu Reputation: 200-299 sendersu Reputation: 200-299
wow, this tool is from 2008, does it really capable of debugging nowadays javas?
2) it is pass locked
Reply With Quote
  #8  
Old 09-30-2019, 04:56
Chuck954 Chuck954 is offline
Friend
 
Join Date: Jul 2018
Posts: 42
Rept. Given: 0
Rept. Rcvd 8 Times in 6 Posts
Thanks Given: 21
Thanks Rcvd at 52 Times in 31 Posts
Chuck954 Reputation: 8
Woops sorry. Password is www.webscene.ir
The newer version is much more streamlined but it did surprisingly work well for me. It's got a lot of options. I had been using javasnoop but it just never worked right.

If I get some time I'll try and figure out how the newer version stores the 30 day trial countdown and see if I can easily bypass it.
Reply With Quote
  #9  
Old 10-11-2019, 10:04
Chuck954 Chuck954 is offline
Friend
 
Join Date: Jul 2018
Posts: 42
Rept. Given: 0
Rept. Rcvd 8 Times in 6 Posts
Thanks Given: 21
Thanks Rcvd at 52 Times in 31 Posts
Chuck954 Reputation: 8
Ha! Finally did it!!! I found a class dumper on github that actually worked after modifying and figuring out the crappy instructions. Ended up modifying the source code a bit and after a couple days I got it working. It dumped 96 encrypted classes that were encrypted then obfuscated. This seriously worked better then I could have ever Imagined. I've spent several days now working with the byte code and made huge progress. Considering I've never worked with Java, I am very pleased with the results. I still have a ways to go but since I expected modifying the poorly converted byte code to be the issue, I am excited with my progress. Been working on this since May... I am willing to release the modified source code I used if anyone's interested. I've invested a lot of time in decrypting the proguard Java obfuscation my target uses.
Reply With Quote
The Following User Says Thank You to Chuck954 For This Useful Post:
niculaita (10-12-2019)
Reply

Thread Tools
Display Modes

Posting Rules
You may not post new threads
You may not post replies
You may not post attachments
You may not edit your posts

BB code is On
Smilies are On
[IMG] code is Off
HTML code is Off



All times are GMT +8. The time now is 13:11.


��ICP��05004977��
Always Your Best Friend: Aaron, JMI, ahmadmansoor, ZeNiX