WebAssembly: a binary format for the web

By Axel Rauschmayer

WebAssembly (short: wasm) is a new binary format for the web, created by Google, Microsoft, Mozilla and others. It will be used for performance critical code and to compile other languages (especially C/C++) to the web platform. It can be seen as a next step for asm.js [2].

asm.js

Most JavaScript engines have the following compilation pipeline:

JavaScript source → bytecode → machine code

The idea of asm.js is to code JavaScript in such a way that engines produce machine code that is as efficient as possible. That is, you kind of try to bypass the first compilation step. The results are impressive: if one compiles C++ to asm.js one can reach 70% of native speed in web browsers.

WebAssembly: the next step for asm.js

Initially, WebAssembly is (roughly) a binary format for delivering asm.js code. The two main advantages of such a format are:

  • Faster loading. Especially with large code bases and mobile devices, parsing becomes a bottleneck: “On mobile, large compiled codes can easily take 20–40s just to parse” (WebAssembly FAQ). First experiments show that WebAssembly can be loaded more than 20 times faster, because the work for parsing is minimal.

  • Evolving WebAssembly is simpler: The way that asm.js is currently written is constrained by having to run fast as normal JavaScript (in legacy engines) and by having to support ahead of time compilation within JavaScript syntax.

Legacy engines will be supported via a JavaScript library that translates WebAssembly (binary) to asm.js (source code). First indications are that that is reasonably fast.

WebAssembly does not replace JavaScript

The previous diagram (which is a much simplified depiction of reality) should make it obvious that WebAssembly is not a replacement for JavaScript, it is a new feature of JavaScript engines that builds on their infrastructures. That means that it will fit well into the web platform:

  • It will have the same evolution strategy as JavaScript: everything is always backward-compatible, there is no explicit versioning, code uses feature testing to determine how it should run.
  • It will execute in the same semantic universe as JavaScript and allow synchronous calls to and from JavaScript (including browser APIs).
  • Security will be handled like in JavaScript, via same-origin and permissions security policies.

The nice thing is that WebAssembly removes the burden from JavaScript to be a good compilation target for other languages. For example, the following two methods were only added to ES6 to support asm.js well:

  • Math.fround(x) rounds x to a 32 bit float.
  • Math.imul(x,y) multiplies the two integers x and y.

The big picture

  • Performance critical functionality (games, video and image decoders, etc.) will be implemented via WebAssembly, either by hand-coding it or by yet-to-be-invented languages that are slightly higher-level.

  • External code bases, especially those in C/C++, will be easy to port to the web platform, via WebAssembly.

  • Other than that, JavaScript will continue to evolve and will probably remain a popular way of implementing web apps.

The future

The initial focus is for WebAssembly to be a compilation target for C/C++. Longer term, more features supporting other languages will be added, including the ability to create garbage-collected data (currently, asm.js creates and manages its own heap).

What is different this time?

Why should WebAssembly succeed where previous attempts (such as Adobe Flash and Google Portable Native Client) have failed? There are three reasons:

  • First, this is a collaborative effort, no single company goes it alone. At the moment, the following projects are involved: Firefox, Chromium, Edge and WebKit.

  • Second, the interoperability with the web platform and JavaScript is excellent. Using WebAssembly code from JavaScript will be as simple as importing a module.

  • Third, this is not about replacing JavaScript engines, it is more about adding a new feature to them. That greatly reduces the amount of work to implement WebAssembly and should help with getting the support of the web development community.

A few more interesting tidbits

  • You’ll eventually be able to debug a WebAssembly binary via the source code that was compiled to it. That mechanism will be an evolution of source maps [3] that provide similar services for JavaScript.

  • WebAssembly binaries will encode abstract syntax trees. That is, they are not a linear format like stack- or register-based bytecode. Not surprisingly, the format looks much like asm.js: roughly, a statically typed version of JavaScript without objects.

  • There will be a text format for WebAssembly. It will mirror the semantics of the binaries and contain a tree of statements and expressions.

Further reading

  1. WebAssembly” by Luke Wagner
  2. asm.js: closing the gap between JavaScript and native
  3. Introduction to JavaScript Source Maps” by Ryan Seddon on HTML5 Rocks

Source:: 2ality