2

I have an older Jar file which I have to modify in order to get it to work. I have already decompiled it with jd-gui and changed the parts that needed change. I would now like to know what I have to do in order to get a jar back? I guess that I have to add the libraries, but there is no extra lib directory.

How do I put everything together?

@Stephen C "Therefore, when you make your changes and recompile, the resulting ".class" file could have unexpected " How exactly is this relevant? I only want the function of the Jar file and not a 1:1 copy of it.

The Jar file is unsigned. What exactly would be the reason to sign a Jar file anyway? If I start it from another program?

TestModus
  • 59
  • 1
  • 4
  • *"How exactly is this relevant?"* - It is relevant to you because you don't want changes that alter the behavior of the JAR in unexpected / unwanted ways. There are circumstances where recompiling (e.g. with a different classpath) can materially change the behavior of a class. And since you are compiling decompiled code, there is the additional problem that the decompiled code may not be a correct decompilation of the original. (That's actually quite common ...) – Stephen C Dec 15 '21 at 23:49
  • *"What exactly would be the reason to sign a Jar file anyway?"* - It allows the person running the JAR to detect whether the JAR has been tampered with. – Stephen C Dec 15 '21 at 23:52
  • Note: people are not notified if you put an @ping in your question. It needs to be in a comment to trigger a notification. Preferably a comment **on the answer** if you are asking for clarification on the answer. (You won't necessarily get a response anyway ... but that's another issue. Remember: this is NOT a help-desk where people are PAID to answer your questions.) – Stephen C Dec 15 '21 at 23:57

4 Answers4

4

If you are missing dependencies after decompiling the entire jar, that could mean the jar did not include them. When you create a jar, you can choose not to include dependencies in it, but this assumes that they will be available on the classpath at runtime. Check if there are any relationships with other jar files on the classpath when you run the original jar. See this answer for details on how to achieve this. Once you have identified all the dependencies, you can easily compile the jar from an IDE such as IntelliJ/Eclipse or from command line.

As a side note, if the changes you would like to make to the jar are minor or isolated I recommend editing the bytecode (much easier for small edits). I prefer this bytecode editor.

If decompilation fails on some parts of the code, the functionality of the jar will not be restored upon recompilation. In this case, instead of going through all available decompilers and hoping that you can decompile that code, I suggest you identify the set of classes which you are trying to edit, modify the rest of the classes such that they compile and do not have any side effects on the classes which are of interest to you (do not delete anything that is referenced by these) and compile the jar (even if this isn't the jar you want). You can then extract only the class files which you wanted to modify from the jar, and overwrite them in the original jar. This will only work if your changes didn't have any side effects.

M B
  • 307
  • 2
  • 8
  • I realise this is an old response, but I was wondering, does the bytecode editor also work if I just need to change an IP address in the persistence.xml file and nothing else? I just want to get the same .jar file back with another IP in the persistence.xml file, I have no idea about dependencies and other stuff (it's not my program and I got no java knowledge at all) – Dennis Dec 11 '21 at 16:42
  • 1
    @Dennis I think there is a much simpler solution in this case, if this persistence.xml file is part of the jar. Extract the jar and verify if persistence.xml is present in there. If it is, then edit it in notepad (or any editor), and overwrite it in the jar. See the extract/overwrite part in my post. – M B Dec 12 '21 at 17:18
1

If you are asking how to create a JAR:

  • You can do it using a build tool such as Maven, Gradle, Ant and so on.
  • You can do it using a Java IDE
  • You can do it using the command line jar tool; see How to create a JAR file from the official Oracle Java tutorials.

But it there is no guarantee that what you are doing will actually work. Here are a couple of the problems.

  • If the original JAR file was signed, you won't be able to re-sign the new JAR ... unless you have the private key that was used when signing.

  • Decompilation is often inaccurate. There is no guarantee that the Java code that it produces is a correct representation of the original class. Therefore, when you make your changes and recompile, the resulting ".class" file could have unexpected / unwanted differences relative to the original.


I guess that I have to add the libraries, but there is no extra lib directory.

I'm not sure what you mean by that. The (new) dependencies of the JAR don't necessarily need to be in the JAR itself. It depends on what kind of JAR it is; e.g. is it a so-called "executable" JAR that you launch using java -jar my.jar ....

Stephen C
  • 698,415
  • 94
  • 811
  • 1,216
0

Use jar plugins for gradle or maven for example, or build it with intelliJ, here's an answer in another post: How to build jars from IntelliJ properly?

  • Please don't use link only answer. Please provide some example with context. In the future the link may not work, and your answer would be useless – Amirhossein Yari Nov 08 '20 at 03:31
0

Since I had trouble getting the .jar file completely recompiled and working with my application, I wanted to share here the steps that were missing in the previous answers.

In my specific case, to make things as easy as possible, I wanted to only modify one .java file in the result of the decompilation and update it directly in the .jar file.

I started from the answer from Paulo Ebermann on a similar question, and I ended up with:

javac -source 8 -target 8 -d classdir -cp \
"\
path/to/dep1.jar; \
path/to/dep2.jar; \
path/to/myoriginal.jar \
" path/to/my/java/class.java

cd classdir
jar -uf path/to/myoriginal.jar path/to/my/java/class.class

Notes:

  • the path/to/myoriginal.jar which is in the path of the dependencies, this forces the java compiler to look for missing classses in the original .jar file rather than in the local decompiled code (which would require recompilation and more dependencies) and therefore I have intentionally left out the . path in the list of class paths
  • the -source 8 -target 8 which were required to force the class to compile for the appropriate version of the runtime machine.
  • the -uf which indicates that the jar tool should only update the file with the provided class
Louis Caron
  • 1,043
  • 1
  • 11
  • 17