Hey everyone! In this post, I am going to walk you through the basic concepts of WebAssembly and gradually we will move forward with building some exciting projects with WASM in my upcoming posts.
This is where WebAssembly or WASM comes into picture. WASM is a relatively novel binary-code format that can be run over the browsers and it is also complemented with a WAT file (text file) to make it more readable and debuggable.
The main purpose behind WASM is to enable high performance applications on the Web, but it also does not have any Web specific assumptions in place thus making it possible to be used in other environments as well.
Let's see the steps involved in the JS engine
In order to compile JS code, the engine must do the following things :
The Parser – The parser goes through the code line by line and checks it for valid syntax as well as for the code types. If everything is valid, the Parser creates an Abstract Syntax Tree (AST).
AST to Intermediate Representation (IR) – Then, the engine interpreter takes the AST and turns it into Bytecode, which is an intermediate representation of the code (an IR is an abstraction of machine code).
Compiling the IR to Machine Code – Only then the engine compiler takes the Bytecode and turns it into a code a machine can run on its processor.
Now, let's see How WASM works in comparison :
For a fact, WASM is faster than a JS engine because WASM code goes directly to the compiler, effectively skipping step 1 and 2.
But you might be wondering, why? Why is WASM able to skip steps 1 and 2 and JS not?
The reason for that is because JS is a dynamically-typed language, which means that JS checks the type of variables at run-time by the Parser.
In contrast, statically-typed languages require to declare the types in advance, therefore types are known and are checked at compile time.
In short, following are the steps that WASM goes through to compile the code :
You write code with its types, usually in a statically typed-language.
Then you generate a pre-compiled WASM module.
Then you can run this code straight by the engine compiler, skipping the parsing and the transformation to Intermediate Representation.
Values: WASM provides only 4 value types. These are integers and
numbers, each in 32 and 64 bit width. The normal operations on
these value types are available.
Instructions: Code consists of sequences of instructions that need
to be executed in order (Last in First Out: Stack Based). The
instructions fall in mainly two categories: Simple, these
instructions perform basic operations on data and Complex, these
instructions deal with the control flow like calling a function etc.
Functions: Code is organized into separate functions. Each
function takes in input values and return a sequence of values
Linear Memory : It is contiguous, mutable array of raw bytes.
This memory is initially created with a size but can be grown
Table : A table is an array of values of a particular type. It
allows programs to select such values indirectly through a
Embedder: WASM implementation in generally embedded in an
environment. This environment decides how modules are loaded,
how imports are done etc. Embedder provides details about the
Module :A WebAssembly binary takes the form of a module that
contains definitions for functions, tables, and linear
memories, as well as mutable or immutable _global variables.
Inside the browser :
Better execution for languages and toolkits that are currently
cross-compiled to the Web (C/C++, GWT, …).
Image / video editing.
Peer-to-peer applications (games, collaborative editing,
decentralized and centralized).
Music applications (streaming, caching).
Live video augmentation (e.g. putting hats on people’s heads).
VR and augmented reality (very low latency).
Scientific visualization and simulation.
Outside the browser
Game distribution service (portable and secure).
Server-side compute of untrusted code.
Hybrid native apps on mobile devices.
Symmetric computations across multiple nodes
WebAssembly modules are executed in a sandbox environment that is entirely separate from the host, and separate from the execution environment of other modules. This is a critical feature for browser-based applications. Browsers themselves have a similar sandbox which prevents browser-based applications from accessing the host environment (in this case the user’s operating system). This is also a desirable feature in many other contexts where executing processes share the same underlying physical resources, e.g. cloud computing.
The WebAssembly specification was designed with a range of languages in mind. Furthermore, WebAssembly is vendor agnostic, having been developed in collaboration by many vendors and technologists.
WebAssembly is a simple and low-level runtime, it doesn’t have a specific approach to memory management (e.g. garbage collection), or its own system-level APIs. This has resulted in a runtime that
is both simple and lightweight.
WebAssembly was primarily designed for delivery over the Web,
where the initial download and compilation time is just as important as the eventual runtime performance. Runtime features such as streaming compilation and fast/simple validation rules all contribute to fast start times and near-native performance.
Thank you for reading my post. Please stay tuned for my upcoming tutorials on WebAssembly😎