emscripten-core / emscripten

Emscripten: An LLVM-to-WebAssembly Compiler
Other
25.81k stars 3.31k forks source link

Feature request: Load WASM things on-demand in JS glue #16557

Open jasl opened 2 years ago

jasl commented 2 years ago

Hi team,

Thank you for the great work!

I'm trying to build a sort of script engine based on Emscripten so I can make it both run at browser and backend.

For backend, I want to reduce init time (load BIG JS glue and WASM which usually the big part for running simple user script), so I'm evaluting V8 snapshot feature work with Emscripten.

During a quick research it seems V8 snapshot can't manage WASM land, I can snapshot JS code (which certainty), but it will failed when JS code call WebAssembly methods such as WebAssembly.memory and WebAssembly.instantize, etc.

I see generated JS glue create WebAssembly.memory at the top level, so that made I can't get benefit from V8 snapshot.

is it possible to create or load WebAssembly.memory and other WebAssembly things on demand?

kripken commented 2 years ago

Hmm, perhaps JS snapshots don't help wasm, but V8 does have support for serializing compiled wasm code (the by-far longest part of wasm startup). That should be very fast. I would suggest making sure that you are using that feature and then measure things.

Creating a wasm memory should not take much time. If you see that as slow, perhaps there is something I'm missing, though.

jasl commented 2 years ago

Creating a wasm memory should not take much time. If you see that as slow, perhaps there is something I'm missing, though.

It's not about performance, I found V8 ScriptCompiler::Compile(context, &source) seems can't handle if the evaluate path has invoke WebAssembly object. so I check the generated JS glue, I saw it's eager to create WASM memory, so I'm not sure it is possible to create it on-demand (e.g. when instantize WASM instance) But I have no confidence about my opinion, because the JS glue has thousands lines, I'm not sure this is enough.

V8 does have support for serializing compiled wasm code (the by-far longest part of wasm startup)

Thank you for the tip, this is what I'm looking for, but can it work with generated JS glue?

kripken commented 2 years ago

In Chrome, V8 will cache basically any large-enough wasm to speed up the second startup of a page. It does that regardless of the JS or HTML or anything else on the page. I'm not familiar enough with the V8 API itself, but I assume if Chrome can use V8 that way then so can other embedders like you.