←back to thread

269 points aapoalas | 1 comments | | HN request time: 0.2s | source

We're building a different kind of JavaScript engine, based on data-oriented design and willingness to try something quite out of left field. This is most concretely visible in our major architectural choices:

1. All data allocated on the JavaScript heap is placed into a type-specific vector. Numbers go into the numbers vector, strings into the strings vector, and so on.

2. All heap references are type-discriminated indexes: A heap number is identified by its discriminant value and the index to which it points to in the numbers vector.

3. Objects are also split up into object kind -specific vectors. Ordinary objects go into one vector, Arrays go into another, DataViews into yet another, and so on.

4. Unordinary objects' heap data does not contain ordinary object data but instead they contain an optional index to the ordinary objects vector.

5. Objects are aggressively split into parts to avoid common use-cases having to reading parts that are known to be unused.

If this sounds interesting, I've written a few blog posts on the internals of Nova over in our blog, you can jump into that here: https://trynova.dev/blog/what-is-the-nova-javascript-engine

Show context
liontwist ◴[] No.42173207[source]
This is a great idea! I had thought about doing this with a lisp interpreter. I had identified a few key advantages:

- homogenous allocation means no alignment gaps - linear access win in garbage collection - indices smaller than pointers - type discriminated index can save some size

I haven’t verified whether those actually work out in the details. I’ll read your blog article.

Don’t bother with these comments immediately comparing it to V8 (a multi billion dollar venture). I don’t know how many creative projects they’ve done before.

You may be be interested in looking at Fabrice Bellard’s JS engine for ideas.

replies(2): >>42173504 #>>42176218 #
aapoalas ◴[] No.42173504[source]
Thank you for the encouragement! Avoiding alignment gaps is indeed pretty great: I have a vision of packing Arrays into 9 bytes split over two or three cache lines.

On typed indexes: If we accept only about 2^24 possible index values then we could use a 32 bit integer for our Values, or at least for Objects (if we want to keep 7 bytes worth of stack data, which is pretty hard to pass on).

I love the comments comparing Nova to V8: That's what I want to aim for after all :) I'm not sure I've heard of Fabrice Bellard's JS engine, thanks, I'll take a look!

replies(1): >>42174861 #
NoahKAndrews ◴[] No.42174861[source]
Your blog mentions QuickJS, which I believe is the mentioned engine by Fabrice
replies(1): >>42175070 #
1. aapoalas ◴[] No.42175070[source]
Oops :D