WebAssembly in Action

Author of the book "WebAssembly in Action"
Save 40% with the code: ggallantbl
The book's original source code can be downloaded from the Manning website and GitHub. The GitHub repository includes an updated-code branch that has been adjusted to work with the latest version of Emscripten (currently version 3.1.44).
Showing posts with label Manning. Show all posts
Showing posts with label Manning. Show all posts

Saturday, August 29, 2020

WebAssembly in Action is Manning's Deal of the Day

"WebAssembly in Action" is 50% off today (August 29th, 2020) as part of Manning’s Deal of the Day.

Use code dotd082920au at https://bit.ly/2ECq0zt

Thursday, November 29, 2018

WebAssembly in Action is now in MEAP

Interested in WebAssembly? Want to learn about the various ways that WebAssembly modules can be created using C or C++ and the Emscripten toolkit?

After a number of long nights, weekends, stat holidays, and some vacation time, I've finally reached a milestone!

WebAssembly in Action just launched as part of Manning's early access program (MEAP)!

Saturday, December 30, 2017

WebAssembly - WasmFiddle and Inline WebAssembly Modules


WasmFiddle

JSFiddle, and tools like it, allow you to test code in the browser to see how it will work instead of having to write an application just to test something. Another advantage of tools like this is that you can share your example code on sites like Stack Overflow.

It turns out that there is a similar tool for WebAssembly called WasmFiddle: https://wasdk.github.io/WasmFiddle


If we replace the code that is in the top-left pane with our code below we can compile the code by pressing the Build button:

int add(int x, int y){ return x + y; }

Because we changed the method in the top-left pain from 'main' to 'add', we need to adjust the logic in the top-right pane from this:
log(wasmInstance.exports.main());
to this:
log(wasmInstance.exports.add(1, 2));

Once you make this change, you can click the Run button which will display the result of the call in the bottom-right pane.

Note: One difference between WasmFiddle's output as compared to Emscripten's output is that there is no underscore character before the method's name when using WasmFiddle.

To share your WebAssembly code with someone, you first need to click on the Share button (above the top-right pane) which will update the URI both in the browser's address bar and just above the top-left pane. You can then copy and share the address.


Inline WebAssembly Modules

WasmFiddle also allows you to download the wasm file or simply view the file's text format or binary representation in the bottom-left pane.

The binary representation from WasmFiddle offers an interesting option when it comes instantiating WebAssembly modules. With the array that you're given, you can bypass the fetch of the wasm file and instantiate a WebAssembly module directly with the array.

The following is some sample code using our Code Buffer from WasmFiddle:
var wasmCode = new Uint8Array([0, 97, 115, 109, 1, 0, 0, 0, 1, 135, 128, 128, 128, 0, 1, 96, 2, 127, 127, 1, 127, 3, 130, 128, 128, 128, 0, 1, 0, 4, 132, 128, 128, 128, 0, 1, 112, 0, 0, 5, 131, 128, 128, 128, 0, 1, 0, 1, 6, 129, 128, 128, 128, 0, 0, 7, 144, 128, 128, 128, 0, 2, 6, 109, 101, 109, 111, 114, 121, 2, 0, 3, 97, 100, 100, 0, 0, 10, 141, 128, 128, 128, 0, 1, 135, 128, 128, 128, 0, 0, 32, 1, 32, 0, 106, 11]);

WebAssembly.compile(wasmCode).then(wasmModule =>
WebAssembly.instantiate(wasmModule, g_importObject)
).then(instance =>
//Warning: No underscore character when using WasmFiddle
alert(instance.exports.add(1, 2))
);

Note: WasmFiddle shows the use of WebAssembly.Module in the top-right pane but that is not recommended because that compiles the module synchronously. The recommended way to compile a module is by using the asynchronous WebAssembly.Compile method as shown in our example above.



If you'd like to know more about WebAssembly, the following are a few articles that might be of interest:
A New Book

I’ve been honored with an opportunity to write a book about WebAssembly.

If you enjoyed this article and would like to know more about WebAssembly, I welcome you to check out my book: WebAssembly in Action

Saturday, December 16, 2017

WebAssembly – Calling into JavaScript from bare bones C code


In my previous blog post, we explored the idea of creating a bare bones WebAssembly module with no Emscripten plumbing. In that article, we were able to call into the module from JavaScript but we didn't get into the reverse:

How does one call into JavaScript from a module?


Calling into JavaScript from a WebAssembly module

In this article we're going to try and get a WebAssembly module to call a method that's defined in our JavaScript.

In order to compile C code, when the method being used isn't in the source code, you need to define the method signature using the extern keyword as shown in the following example:

// Define the JavaScript method's signature that we're going to be calling.
extern void CallJS(int iVal);

// A method that the JavaScript will call into to trigger our code
// that will in turn call a JavaScript method passing along the value
// received.
void Test(int iVal){ CallJS(iVal); }

You can run the following command line to build the wasm file:

emcc test.c -s WASM=1 -s SIDE_MODULE=1 -O1 -o test.wasm

To define the method in our JavaScript, we just need to add it to the env object that is part of the main object that we pass as the 2nd parameter to the WebAssembly.instantiate method:

var importObject = {
'env': {
// ... (other properties/methods of this object)

'_CallJS': function(iVal){ alert("value received: " + iVal.toString()); }
}
};

Just like how we needed to add an underscore character before the method name when calling into the module from JavaScript, we also need to include an underscore before the method name here.

The following is the full HTML/JavaScript for our example module:
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8"/>
</head>
<body>
<input type="text" id="txtValue" />
<input type="button" value="Pass Value" onclick="PassValue();" />

<script type="text/javascript">
var gModule = null;

var importObject = {
'env': {
'memoryBase': 0,
'tableBase': 0,
'memory': new WebAssembly.Memory({initial: 256}),
'table': new WebAssembly.Table({initial: 0, element: 'anyfunc'}),

'_CallJS': function(iVal){ alert("value received: " + iVal.toString()); }
}
};

fetch('test.wasm').then(response =>
response.arrayBuffer()
).then(bytes =>
WebAssembly.instantiate(bytes, importObject)
).then(results => {
gModule = results.instance; // Hold onto the module's instance so that we can reuse it
});

function PassValue(){
// Get the value from the textbox (convert the value from a string to an int)
var iVal = parseInt(document.getElementById("txtValue").value,10);

// Call the method in the module
gModule.exports._Test(iVal);
}
</script>
</body>
</html>



A New Book

I’ve been honored with an opportunity to write a book about WebAssembly.

If you enjoyed this article and would like to know more about WebAssembly, I welcome you to check out my book: WebAssembly in Action