Many decades ago, you programmed computers by flipping switches. It was a slow, error-prone and tedious process. Then came assembly language, which was machine code that humans could actually read. The great age of assembly came in the early 80s, when it was used to power commercial games for 8-bit boxes such as the CBM-64; since basic interpreters were slow and there were no C compilers, only assembly language code ran fast enough.

Still in use today, assembly remains slow and tedious. In the time it would take you to write ten lines of assembly, you could write ten lines of Python or C# that would accomplish far, far more from a software perspective. (That hasn’t stopped the people who still like to write 8-bit assembly; there’s even a C compiler that outputs 6502 machine code for CBM-64/Vic-20, and so on.)

The other issue with assembly is the lack of portability. Converting 6502 to Z80 (or some other assembly language) is a non-trivial piece of work, despite some advances in automation. Thirty years ago, it might have taken you a month to convert, test, and release a working program based on 5,000 lines of assembly code. Things are still pretty slow, but assembly does have its uses in legacy systems and software that must deal directly with hardware (i.e., the Internet of Things).

Introducing WebAssembly

Assembly language has been resurrected via JavaScript under the name asm.js; its legacy also continues with WebAssembly, designed as a faster alternative to parsing and execution than JavaScript.

Asm.js is a strict optimized subset of JavaScript that provides a sandboxed virtual machine for languages such as C/C++. The techniques used mean that browser performance of C/C++ programs converted to asm.js run much faster than native compiled code.

However, even asm.js has its problems. Downloading and compiling large asm.js apps can be quite slow, especially in mobile environments. Instead of source code that is bulky and needs compiling, why not download machine code or something close to it? That’s the thought process that led to the birth of WebAssembly.

WebAssembly

WebAssembly is a low-level binary format, not unlike assembly language. But WebAssembly code isn’t the most readable. Can you figure out what this example does?

get_local 0 i64.const 0 i64.eq if i64 i64.const 1 else get_local 0 get_local 0 i64.const 1 i64.sub call 0 i64.mul end

It’s a recursive factorial function, and i64 is a 64-bit integer variable. You can see the original C/C++ source code, plus this and the binary on the text format page. Only masochists would write programs in wasm (the short name for WebAssembly).

Currently, the main programming languages are C/C++, whose programs are compiled by Emscriptem into wasm; since December 2016, Rust can also be compiled to wasm.

The spec for the WebAssembly VM is available on Github, with a current version readable online.

WebAssembly Architecture

In order to make WebAssembly (and before it, asm.js) as fast as possible, the environment avoided JavaScript features that would allocate memory at runtime. Asm.js used a large array to simulate memory in the virtual machine. Features that make WebAssembly faster than asm.js include numeric variables that are either 32- or 64-bit int or floats; all instructions and operators are explicitly typed with no overloading rules.

Current State of WebAssembly

WebAssembly is still a work in progress. Earlier this year, W3c WebAssembly Community Group announced that the Minimum Viable Product (MVP) was complete, with approximately the same functionality as asm.js (supported platforms include Chrome and Android 57, Opera 44, Edge 15 (experimental) and Firefox 52.)

Mozilla have been very good about documenting WebAssembly’s progress; take a look at the Mozilla WebAssembly pages. Finally it’s worth noting that WebAssembly is intended to go beyond the web; there’s work being done to make it capable of execution without a JavaScript VM present. If you’re interested in older programming languages, or just curious about how the language interfaces with hardware, check it out.