Building a baseline JIT for Lua automatically
sillycross.github.ioDeegen is my research meta-compiler to make high-performance VMs easier to write. Deegen takes in a semantic description of the VM bytecodes in C++, and use it as the single source of truth to automatically generate a high-performance VM at build time
> To solve [forward branches], those bytecodes would push information about how the branch destination address shall be fixed up into a late-patch buffer.
This reminds me of how Forth `if` and `then` can be compiled in a single pass -- `if` writes the branch instruction and pushes the current instruction pointer to the stack, and `then` pops it and patches the instruction to point to the current instruction pointer.
That's an interesting approach :) Though it only works if the control flow in the language is exactly "paired" (no continue/break, no goto, etc), I guess?
I don’t understand how you can remove the calls with copy-and-patch. It seems like you would have to inline evaluate_lhs and evaluate_rhs to remove calls completely.
Look at the CPS-version of the add.
I saw that. I think I understand a little better. The CPS is to remove the calls between bytecodes, but wouldn’t do anything about lua function calls.
That's correct. Lua function calls are not that easy to remove, as function is first-class value in Lua so can be redefined at any time. To remove a function call, you need speculative compilation and OSR-exit, which is outside the job of the baseline JIT.
Great work! This was a very interesting read. A lot of clever approaches here to make a generic JIT. How would one try out deegen?