Passing arrays to AssemblyScript from JS

643 views Asked by At

I have recently started attempting to add WebAssembly into an app I'm working on, but seem to be running into some trouble. I keep getting one of two errors: memory access out of bound or unreachable. I'm attempting to send an Float32Array of length 128 to the wasm module, but its not working. Here is an example of the code I'm using:

zero.ts:

export function zero(arr: number[], length: number): number[] {
    for (var i = 0; i < length; i++) {
        arr[i] = 0;
    }
    return arr;
}

and compiling using the following terminal command:

asc zero.ts -o zero.wasm

Then it is used in an AudioWorkletNode like so:

//wasmBytes is passed in form the main thread

var mod;
var importObject = {};
WebAssembly.instantiate(wasmBytes, importObject).then((instance) => {
  mod = instance.instance.exports;
            
  var f = new Float32Array(mod.memory.buffer, 0, arr.length);
  f.set(arr);
  var x = mod.zero(f.byteOffset, arr.length);
});

Any help would be greatly appreciated.

1

There are 1 answers

0
MaxGraey On

WebAssembly can only pass numbers via js-wasm boundary. That's why managedby runtime objects like arrays are passed through Wasm linear memory. Each language that can be compiled into WebAssembly has its own structure & memory layout for representing arrays, strings etc. Encoding and decoding such structures is often not trivial, so there are tools to automate this. AssemblyScript since version 0.20.x can also do this. You will need two things - add the --exportRuntimeand --bindings esm flags. You can read more about it in the documentation: https://www.assemblyscript.org/compiler.html#host-bindings

I also recommend this video: https://www.youtube.com/watch?v=H1O2j4w78j8