Implement virtual callstack for functions #3087
Closed
Add this suggestion to a batch that can be applied as a single commit.
This suggestion is invalid because no changes were made to the code.
Suggestions cannot be applied while the pull request is closed.
Suggestions cannot be applied while viewing a subset of changes.
Only one suggestion per line can be applied in a batch.
Add this suggestion to a batch that can be applied as a single commit.
Applying suggestions on deleted lines is not supported.
You must change the existing code in this line in order to create a valid suggestion.
Outdated suggestions cannot be applied.
This suggestion has been applied or marked resolved.
Suggestions cannot be applied from pending reviews.
Suggestions cannot be applied on multi-line comments.
Suggestions cannot be applied while the pull request is queued to merge.
Suggestion cannot be applied right now. Please check back later.
This is the first prototype of a vm design that uses a virtual callstack for JS functions and Rust functions.
Right now it's full of hacks and compatibility patches in order to be able to progressively experiment and bugfix, but that'll be solved when this PR is finished.
It currently uses thenext-gen
crate to emulate generators in stable, which is the way this design unifies JS calls with Rust calls.By the way, this is probably blocked on rust-lang/rust#68923, which is why I drafted this implementation for the moment.
Design notes
All functions now return a
JsResult<CallResult>
struct, defined as:This new return value can signal the VM about what to do on several cases:
Value
, which indicates to the VM that the function finished executing and doesn't need to be pushed to the virtual callstack.DirectCall(CallContext)
, it's a tail call, meaning the VM can directly call the inner function without storing the caller's context.Coroutine (JsCoroutine)
, it signals the VM that the callee has inner calls to other JS functions.The coroutine design looks a bit daunting, but it's essentially divided in steps:
This bridges the gap between Rust functions and JS functions, making it possible to track both of them with a single callstack :D
cc @HalidOdat