#19: GraalVM: Polyglot Java runtime with faster startup and smaller memory footprint
GraalVM is a set of tools that aim to improve the performance and interoperability of Java Virtual Machine. Taking advantage of GraalVM not only makes your apps run faster. It also allows running different languages like JavaScript or Python with superb speed.
GraalVM consists of quite a few projects, so let’s dive in.
JIT compiler
The most groundbreaking technology is the JIT compiler. To recap, JIT is responsible for translating abstract bytecode into low-level machine code. JIT is the reason why Java is actually quite fast these days. Your code is compiled behind the scenes into heavily optimized CPU instructions. Unfortunately, this wonderful piece of software was buried deeply in Java VM. The JIT codebase in C++ turned out to be too complex to maintain anymore. So someone thought: what if we rewrite JIT compiler in Java? Sounds crazy. But as a matter of fact, JIT is essentially a pure function that takes bytecode as input and returning machine code as output. Byte array in, byte array out. That’s how GraalVM was born. Now you can plug-in a JIT compiler written in Java to a JVM.
Suddenly the codebase became much more maintainable and developer friendly. GraalVM’s JIT compiler quickly outperformed legacy JIT compiler. Essentially it is now much easier to write optimized machine code generation. But it turned out this was just the beginning.
Ahead of time compilation
So you can write an efficient JIT compiler. But what about running it ahead of time, not at runtime? Basically, compiling Java directly into standalone, executable binary? Just to be clear, with GraalVM you can produce native image binary that can run without Java installed. Now, to be fair, this native binary contains necessary subset of Java VM. Mostly we’re talking garbage collector. This stripped Java runtime is called SubstrateVM.
Becauase native binary is already optimized and compiled, it starts blazingly fast. Seriously, bloated Spring applications start within a few hundred milliseconds. Oh, and the memory footprint is reduced by a few times. Believe it or not, Java is actually suitable for serverless. Applications treated with GraalVM don’t have a cold start problem.
SuLong LLVM
OK, it gets even better. GraalVM can run LLVM bitcode. Without diving into details, this means you can run C++, Fortran and R on the JVM. And all the other language that compile to LLVM bitcode. Moreover, libraries and applications written in R can be used directly in Java applications. Truly polyglot experience.
Polyglot programming
To enable even more polyglot programming, Truffle framework was developed.
Truffle is a scaffolding for building interpreters for various languages.
Your task is to write a lexer and parser, for example using ANTLR.
Then, you build an interpreter to handle each language instruction.
Like assignment or if
statement.
What’s the point?
Well, Truffle takes your intepreter and produces highly optimized machine code.
Python, Ruby, R and JavaScript are implemented on top of Truffle.
Their performance is comparable to native implementations, often written in C/C++.
It works especially well with dynamically typed languages that self-evaluate code.
For example eval()
in JavaScript or Python.
Highly discouraged, but anyway…
Disadvantages
OK, any disadvantages?
Well, the biggest one so far is the compilation time of native-image
.
It can literally take minutes.
Also, GraalVM is only partially open source.
Some more advanced JIT optimizations are paid.
Oracle is currently sponsoring this project and it has a lot of momentum.