[Gambas-user] New JIT Compiler

Emil Lenngren emil.lenngren at ...626...
Wed May 23 22:20:21 CEST 2012


Hi everybody.

I've been working on a JIT-compiler for Gambas for some months, and I'm now
ready to release an alpha-version in the latest svn of Gambas.
The compiler uses LLVM to produce machine code for x86 or x86_64. You need
LLVM on your computer for it to work, preferably the latest version from
svn (3.0 from Ubuntu repos does not seem to work any well). Find more
instructions in the README file.

To use it, place the word "Fast" at the top of a Gambas Class file, for a
class that you want all functions JIT-compiled instead of interpreted. (At
the moment you cannot make individual functions JIT-compiled, but that is
limited by the gbc compiler.)

As it takes some milliseconds for LLVM to emit machine code and do
optimizations, you should only use it for functions you really need
optimizations.

As the JIT compiler analyses the whole function before execution starts,
some extra type safety is added. In interpreter mode, you can normally do
things like:
Print "hello"
Print 1.3 \ 5
and you will first see hello on the screen, and then an error message
complaining you can't do integer division on floats.
If you run the same function in the JIT compiler, the error message will be
thrown before execution starts instead, hopefully in order to make programs
less buggier.
As a consequence, you can not have code like "Try Print 1.3 \ 5" either. At
the moment the incorrect line is reported in the error message...

The best speed-ups will be in functions that use a lot of low-level
calculations and control flows (except For Each loops), like functions that
do a lot of math. If the function mostly calls other libraries, you won't
see speed-ups either.
There are still the same overhead when calling functions, since the gambas
stack must be maintained as before, to make error handling work.
Using Try/Catch is probably slightly slower too because a real exception
handler must be set up.

Something the LLVM optimizer is very good at is transforming a chain of
if-else statements to a jump table, so code like:
Select Case x
  Case 1:
    ..
  Case 2:
    ..
  Case 3:
    ..
End Select
will be much faster than before, so you don't have to use the "On Goto"
syntax and a lot of labels. This will produce identical machine code.

Most things are implemented, but there are still many bugs to fix.
Some of the (so far) unimplemented features are
Calling external C libraries (the Extern keyword).
The use of "_unknown" special method.
IIf and Choose with different argument data types.
The possibility to use Component.Load to load functions that are executed
right after in the same function.
Profiling
Breakpoints

Some of the benchmarks from http://gambasdoc.org/help/doc/benchmark
Polynom: 102.7 seconds to 4.7 seconds
Primes: 18.3 seconds to 3.5 seconds
Nbody: 16.0 seconds to 1.8 seconds

If you are curious and want to see the optimized LLVM IR you can uncomment
the line M->dump() at the bottom of the jit_codegen.cpp file in gb.jit/src.

I hope the JIT compiler will be useful for you ;)

/Emil



More information about the User mailing list