6

I'm looking for a compiler to translate Java bytecode to platform-independent C code before runtime (Ahead-of-Time compilation).

I should then be able to use a standard C compiler to compile the C code into an executable for the target platform. I understand this approach is suitable only for certain Java applications that are modified infrequently.

So what Java-to-C compilers are available?

Rudiger
  • 6,634
  • 9
  • 40
  • 57
  • Found this link for the specific case of Oracle Database: http://download.oracle.com/docs/cd/B28359_01/java.111/b31225/chone.htm#BABCIHGA – Rudiger Dec 21 '09 at 17:43
  • What is the exact goal you want to accomplish? An EXE file? – Thorbjørn Ravn Andersen Dec 22 '09 at 16:47
  • Well, not an executable, but the source code in portable C. – Rudiger Dec 29 '09 at 21:31
  • Most of the complexity and functionality of of Java is in its libraries. Without these libraries as well what is the point? – Peter Lawrey Dec 29 '09 at 21:45
  • The hard part is not making C out of the byte code (even if the C will be a horrible read), the hard part is to make something out of it that will either work with a GC suitable for C or without a GC and to translate every single piece of byte code in there for collections, exception handling etc. I really don't see the point in even considering it. – Fredrik Dec 29 '09 at 21:52
  • To Mr. Lawrey's point, I had the same question. It seems one can use Ahead-of-Time compilation to deliver core Java class libraries in natively compiled form. – Rudiger Dec 30 '09 at 00:18

7 Answers7

8

I could suggest a tool called JCGO which is a Java source to C translator. If you need to convert bytecode then you can decompile the class files by some tool (e.g., JadRetro+Jad) and pass the source files to JCGO. The tool translates all the classes of your java program at once and produces C files (one .c and .h for each class), which could, further, be compiled (by third-party tools) into highly-optimized native code for the target platform. Java generics is not supported yet. AWT/Swing and SWT are supported.

JeremyP
  • 84,577
  • 15
  • 123
  • 161
Ivan Maidanski
  • 251
  • 2
  • 2
3

Why do that? The Java virtual machine includes a runtime Java-to-assembly compiler.

Compilation at runtime can yield better performance, since all information about runtime values is available. While ahead-of-time compilation has to take assumptions about runtime values and thus may emits less fast code. Please refer to Java vs C performance by Cliff Click for more details.

akuhn
  • 27,477
  • 2
  • 76
  • 91
  • Compilation at runtime *can* yield[] better performance. Depends on your use case, just like it says in the link. Not that that is a reason to compile java to c. – dmckee --- ex-moderator kitten Dec 21 '09 at 17:05
  • @dmckee true enough, added weasel worlds :) – akuhn Dec 21 '09 at 17:21
  • "Why do that?". One possible reason could be that GCC, and other C compilers, target more platforms and architectures than any JIT, and probably more than the union of all JITs in existence. That said, if your target doesn't have a suitable JIT-enhanced JVM, that might be because it's too feeble for any practical Java code, and the Java->C->native route won't actually work either. – Steve Jessop Dec 21 '09 at 17:31
  • If your platform doesn't support Java, you're probably better off writing it in C or C++ than relying on a Java-to-native compiler. It'll run faster and be easier to work with. Also, I've heard of **no case** where a Java-to-native compiler beats Hotspot in anything but startup time. I don't think you need the weasel words. – BobMcGee Dec 21 '09 at 19:17
  • @bobmcgee also never heard of that. In any case, the weasel words cover the case of equals speed, don't they? :) – akuhn Dec 21 '09 at 21:41
  • Except the native-compiled Java is *slower*, rather than equal... :P – BobMcGee Dec 21 '09 at 21:59
  • "you're probably better off writing it in C or C++ than relying on a Java-to-native compiler" - sure, but the questioner is asking how to compile Java bytecode (not Java source). Re-writing Java bytecode by hand in C doesn't sound much fun to me. – Steve Jessop Dec 21 '09 at 22:37
  • I may stand corrected about performance... but the differences usually aren't that huge, anyway, barring startup times. As for rewriting: Java and C++ aren't *that* different, and the C++ result has more room for hand optimizations, assembly, etc. If you're that focused on speed, you should do it the right way rather than relying on a java-to-native AOT compiler. – BobMcGee Dec 23 '09 at 00:42
3

GCJ has this capability, but it hasn't got great support for Java features past 1.4, and Swing support is likely to be troublesome. In practice though, the HotSpot JIT compiler beats all the ahead-of-time compilers for Java. See benchmarks from Excelsior JET. To clarify: GCJ converts java source/bytecode to natively compiled code

Toba will convert (old) Java bytecode to C source. However, it hasn't been updated since Java 1.1. It may be helpful to partially facilitate the porting, but it just can't handle all the complex libraries Java has.

BobMcGee
  • 19,824
  • 10
  • 45
  • 57
  • Could you give please a link to the place where the capability to compile **into C** is documented for GCC/GCJ? – imz -- Ivan Zakharyaschev Feb 04 '16 at 19:10
  • The GCJ compiler is no longer available. Alternatively, it might be possible to compile Java bytecode to WebAssembly using [TeaVM](https://github.com/konsoletyper/teavm) or [JWebAssembly](https://github.com/i-net-software/JWebAssembly), and then decompile it to C using [wasm2c](https://github.com/WebAssembly/wabt/tree/master/wasm2c). – Anderson Green Aug 27 '20 at 15:59
2

(I've been googling for this stuff, this is how I came to this question at SO.)

imz -- Ivan Zakharyaschev
  • 4,921
  • 6
  • 53
  • 104
1

AFAIK, there is no such product but you have two options:

  • Implement your own byte-code to C transpiler. Byte-code is pretty simple, this isn't too hard.

  • If you just want a native binary (i.e. when you don't need the C source code), then give GCJ a try.

Note: If you're doing this for performance reasons, then you're going to be disappointed. Java is generally as fast as C/C++. Moreover, improvements to the VM will make all Java code faster but not your native binary. Compiling the code will just give you a little better startup time.

Aaron Digulla
  • 321,842
  • 108
  • 597
  • 820
  • I believe this is one of the modes for GCJ, although it is normally compiled from source to bytecode or source to native. I agree about the poor performance though. – BobMcGee Dec 21 '09 at 16:59
  • @BobMcGee Could you give please a link to the place where the capability to compile **into C** is documented for GCC/GCJ? – imz -- Ivan Zakharyaschev Feb 04 '16 at 19:10
1

Not really an answer to my own question, but how does Oracle do it?

http://download.oracle.com/docs/cd/B28359_01/java.111/b31225/chone.htm#BABCIHGA

Rudiger
  • 6,634
  • 9
  • 40
  • 57
0

There used to be a product called TowerJ, which was essentially a "via C" static compiler for Java, but it is long gone.

I was told that Sun Labs has created something like this as part of the Sun SPOT project, but I am not sure if it is public.

@BobMcGee: In the benchmarks you refer to, GCJ indeed loses, but Excelsior JET (which is a 32-bit AOT compiler) beats the 32-bit HotSpot on all three test systems, so I am not sure what was your point.

But, after all, there are lies, damn lies, and benchmarks. :)

Dmitry Leskov
  • 3,233
  • 1
  • 20
  • 17
  • Oh, damn. I could have sworn Excelsior JET was just doing a bytecode optimizer and proprietary JIT VM for that test. This is what you get for not reading carefully enough. – BobMcGee Dec 23 '09 at 00:46
  • 1
    @BobMcGee: No problem. :) By the way, many customers buy Excelsior JET to protect their apps against Java decompilers; they do not care about performance as long as it is about the same as on HotSpot. – Dmitry Leskov Dec 23 '09 at 05:43