Skip to content
Vihan edited this page Jan 30, 2019 · 4 revisions

VSL has native WASM support. That said, WASM has certain requirements and dependencies. As stated on the installation page, you must have:

  • LLVM (with WASM built)
  • LLD (the LLVM linker)

To ensure you correctly have all dependencies it is highly recommended to follow the Recommended LLVM build steps

Ensuring WASM-compatible installation

To ensure your VSL installation and dependencies support WASM run the following:

llc -version

and see if there is a wasm32 entry. If not, you need to build LLVM with WASM support using the -DLLVM_EXPERIMENTAL_TARGETS_TO_BUILD=WebAssembly flag.


Also check if LLD exists:

type lld

Compiling for WASM

Compiling for WASM is easy. Using vsl build we can specify the wasm target, let's take a test.vsl with the following contents:

func main() {
    print("Hello, World!");
}

You can compile this to wasm using:

$ vsl build -t wasm test.vsl -o test.wasm

you should see something along the lines of:

<input.ll> -> .vsl-temp7604231b.o
.vsl-temp7604231b.o -> .vsl-temp7604231b.wast
.vsl-temp7604231b.wast -> .vsl-temp7604231b.wasm
.vsl-temp7604231b.wasm -> <output>

Succesfully compiled in 64.13ms

Now you have your .wasm file which you can load in your browser. That said, certain VSL functions are not linked, the next section described how to fix this.

Using VSL wasm files

VSL needs to link libvsl (and its dependencies e.g. libc) so if you try to run a WASM file with no configuration you will get an error, to resolve this, VSL offers two options, using VSL(...) and libvsl

Using VSL

This is the easiest way, simply run:

import { VSL } from 'vsl/wasm';

VSL('path/to/wasm')
    .then(instance => /* do something interesting */);

For the test.vsl function above, we'd do:

import { VSL } from 'vsl/wasm';

VSL('./test.wasm')
    .then(instance => instance.exports.main())

Using libvsl

If you have your own way to instantiate the WebAssembly classes, you can alternatively just use libvsl:

import { libvsl } from 'vsl/wasm';

const wasmModule = /* some code to get a wasm module */
const instance = WebAssembly.instantiate(instance, libvsl);

Interacting with the DOM

This is a (very) important thing to be able to do. VSL offers a Web library offering seamless binding between DOM functions and JS. VSL at the same time provides idiomatic bindings for properly styled VSL code.

Take a look at the same code in JS and VSL:

JS:

document.getElementById("goat").addEventListener('click', () => {
    // ... code
});

VSL (DOM):

document.getElementById("goat").addEventListener("click", { event:
    // ... code
})

VSL (Web):

Event.when document.findElement(id: "goat").clicked {
    // ... code
}