What is WebAssembly (WASM)? How it works and when to use it
WebAssembly is a binary instruction format for a stack-based virtual machine — a portable compilation target that lets you run C, C++, Rust, and other compiled languages in the browser and beyond. Here's how it works and when it's worth using.
On this page
- Why WebAssembly exists
- How WebAssembly works
- The binary format
- The virtual machine
- Sandbox security
- WASI: WebAssembly System Interface
- Languages that compile to WebAssembly
- Use cases
- High-performance web applications
- Porting existing codebases
- Server-side and edge computing
- Plugin systems
- Browser support
- WebAssembly vs JavaScript
- When to use WebAssembly
- When to use JavaScript
- Key limitation: the DOM
- Performance characteristics
- FAQ
- What is the difference between WebAssembly and JavaScript?
- Can WebAssembly replace JavaScript?
- Is WebAssembly only for browsers?
- What does WASI mean?
- Is WebAssembly secure?
- Summary
WebAssembly (abbreviated Wasm) is a binary instruction format for a stack-based virtual machine, designed as a portable compilation target for programming languages. It enables high-performance applications to run in the browser, on servers, and at the edge — anywhere a Wasm runtime exists.
The WebAssembly specification is maintained by the W3C WebAssembly Working Group. The first W3C Recommendation (version 1.0) shipped in December 2019. Version 2.0 became a W3C standard in December 2024, and version 3.0 arrived in September 2025 with 64-bit address space, garbage-collected types, and improved exception handling.
Why WebAssembly exists
JavaScript was designed for interactivity, not for compute-intensive tasks. As web applications grew in complexity — video editors, 3D games, audio workstations, scientific simulations — JavaScript alone hit performance ceilings.
WebAssembly solves this by providing a compact binary format that runs at near-native speed in the browser's virtual machine. Any language that can compile to Wasm — C, C++, Rust, Go, Python, and dozens more — can run on the web without being rewritten in JavaScript.
WebAssembly is not a replacement for JavaScript. It is a complement: JavaScript handles the DOM and the web ecosystem, while Wasm handles the heavy computation underneath.
How WebAssembly works
The binary format
WebAssembly code is distributed as .wasm files — binary files designed for machines, not humans. A companion human-readable text format .wat exists, using S-expressions, with a 1:1 correspondence to the binary format.
The binary format has a simple structure: a magic number (\0asm, bytes 0x00 0x61 0x73 0x6d), a 4-byte version field, and a sequence of sections — type definitions, function declarations, exports, code, memory, tables, and data.
Instructions use LEB128 variable-length encoding, keeping the format compact.
The virtual machine
WebAssembly runs inside a virtual machine embedded in browsers (or standalone runtimes). The VM is a stack machine: instructions pop arguments from an implicit operand stack and push results back. The stack layout is fixed, so Wasm engines can compile the stack away and produce efficient machine code for registers at runtime.
Four key concepts define a Wasm module:
- Module — the compiled Wasm binary: stateless, shareable.
- Memory — a resizable ArrayBuffer (a linear array of bytes) that Wasm code reads and writes with
loadandstoreinstructions at byte-level granularity. - Table — a resizable typed array of references (such as function references) that cannot be stored directly in Memory for safety and portability reasons.
- Instance — a Module paired with its runtime state (Memory, Table, imported values).
Sandbox security
Wasm runs in a sandboxed environment. It cannot access the filesystem, network, or system APIs unless the host explicitly grants those capabilities through imports. This makes Wasm safe to run even on untrusted code — it cannot corrupt memory or escalate privileges.
WASI: WebAssembly System Interface
WASI (WebAssembly System Interface) is a set of standardized APIs that lets Wasm modules access system resources — file I/O, environment variables, clocks, random numbers, sockets — in a portable, secure way. WASI uses capability-based security: a Wasm module starts with no ambient authority; it can only do what the host explicitly grants.
WASI 0.1 (Preview 1) launched the ecosystem. WASI 0.2 (Preview 2) introduced the Component Model, enabling composable multi-language Wasm applications. WASI 0.3 (Preview 3) added native async support via streams and futures.
Runtimes supporting WASI include Wasmtime, Wasmer, WasmEdge, WAMR, and wazero.
Languages that compile to WebAssembly
As of 2021, around 40 programming languages support WebAssembly as a compilation target. The most mature options:
- C/C++ — via Emscripten (LLVM/Clang-based, default output changed to Wasm in 2019) or standalone Clang 8+. Used to port Unreal Engine 3, SQLite, AutoCAD, and Qt to the browser.
- Rust — first-class support via
rustcwithwasm32-wasiorwasm32-unknown-unknowntargets. The Rust WebAssembly Working Group maintains the tooling. - Go — native support introduced in Go 1.11.
- AssemblyScript — a TypeScript variant that compiles to Wasm. Developers familiar with TypeScript can target Wasm without learning a new language.
- Python (Pyodide), .NET (Blazor), Java/Kotlin (CheerpJ), Ruby (MRuby), Dart (Flutter web builds), and others.
Use cases
High-performance web applications
WebAssembly shines for compute-intensive tasks where JavaScript hits performance limits: 3D games, Virtual/Augmented Reality, computer vision, image and video editing, audio processing, scientific simulations. Figma, the collaborative design tool, uses C++ compiled to Wasm to process complex design files in the browser — a task that would be sluggish in JavaScript alone.
Porting existing codebases
Emscripten has been used to port SQLite, AutoCAD, and game engines (Unity, Godot, Unreal Engine 3) to the browser. Companies get browser versions of their native applications without rewriting them in JavaScript.
Server-side and edge computing
Outside the browser, Wasm runtimes let you run Wasm modules as server-side plugins or at the edge. Cloudflare Workers uses Wasm via V8 isolates to execute code at edge locations with fast cold starts. AWS Lambda and similar platforms are exploring Wasm for lower latency and better isolation than traditional containers.
Plugin systems
Proxy-Wasm (the WebAssembly-based ABI used by Envoy and other proxy servers) allows plugins to extend infrastructure safely without native code risks. Software platforms distribute modular pieces as Wasm components for sandboxed extensibility.
Browser support
WebAssembly reached broad browser support in March 2017:
- Chrome version 57 (March 2017)
- Firefox version 52 (March 2017)
- Safari version 11 (September 2017)
- Microsoft Edge version 16 (October 2017)
All major browsers today support WebAssembly. Feature availability varies:
- SIMD — Chrome 91+, Firefox 79+, Safari 15.2+
- Threads — Chrome 75+, Firefox 79+, Safari 14.1+
- Memory64 — Chrome 133+, Firefox 134+, Safari (not yet)
- WasmGC (garbage-collected types) — shipped in browsers in early 2025
WebAssembly vs JavaScript
When to use WebAssembly
- Compute-intensive tasks requiring near-native speed: image/video processing, cryptography, physics simulations, 3D rendering.
- Running existing C/C++, Rust, or other compiled code in the browser without a full port to JavaScript.
- Predictable, deterministic performance (Wasm avoids JavaScript engine JIT warm-up variability).
- Large codebases where the binary format is significantly smaller than the equivalent JavaScript bundle.
When to use JavaScript
- DOM manipulation and direct Web API access (Wasm cannot directly access the DOM; it calls JavaScript, which calls Web APIs).
- Rapid development, prototyping, flexible dynamic typing.
- Small to medium-sized applications where the JavaScript ecosystem and npm library landscape are a bigger advantage.
- Tasks where garbage collection pauses are acceptable.
Key limitation: the DOM
Wasm cannot directly access the browser's Document Object Model (DOM). It can only pass primitive data types (integers and floating-point numbers) to JavaScript functions. JavaScript then handles the DOM and Web API calls. WasmGC (garbage-collected types) plans to allow Wasm to call Web APIs directly, but full DOM access is still in the future.
Performance characteristics
- Wasm vs native code: Early benchmarks showed Wasm running at about 91% of comparable native speed. Later benchmarks show a range of 33%–200% depending on workload.
- Wasm vs JavaScript: A 2022 study found Wasm runs approximately 20% faster than comparable JavaScript on compute tasks.
- Cryptography: The fastest Wasm runtime runs cryptographic operations roughly 2.3x slower than native code. Some operations can be up to 80x slower when native CPU instructions are unavailable in Wasm.
- Cold start: Wasm modules can have faster cold-start times than JavaScript Virtual Machines for large applications, because parsing and compilation are simpler.
FAQ
What is the difference between WebAssembly and JavaScript?
JavaScript is an interpreted, dynamically typed language that runs in the browser's JavaScript engine and can directly manipulate the DOM. WebAssembly is a binary compilation target that runs in a sandboxed virtual machine — it is faster for compute-intensive tasks but cannot directly access the DOM. They are complementary: JavaScript handles the web ecosystem, while Wasm handles heavy computation. A typical architecture runs JavaScript to call Wasm functions for the heavy lifting.
Can WebAssembly replace JavaScript?
No. WebAssembly is not a replacement for JavaScript — it is a complement. WebAssembly cannot access the DOM directly, cannot load modules from the web the way ES modules work, and does not have the same developer experience as JavaScript. The standard pattern is to use JavaScript to orchestrate the application and call Wasm functions for compute-intensive parts.
Is WebAssembly only for browsers?
No. The WebAssembly Component Model and WASI (WebAssembly System Interface) enable WebAssembly to run on servers, at the edge, in plugins, and in embedded systems. Cloudflare Workers, AWS Lambda, and many other platforms run Wasm outside the browser. The specification is platform-independent by design.
What does WASI mean?
WASI stands for WebAssembly System Interface. It is a standardized set of APIs that gives Wasm modules portable, secure access to system resources — files, clocks, random numbers, networking — without requiring browser-specific JavaScript APIs. WASI makes it practical to compile the same Wasm module to run on a browser, a server, or an edge function.
Is WebAssembly secure?
Yes. WebAssembly runs in a sandbox that prevents memory corruption and unauthorized system access. A Wasm module cannot read or write memory outside its linear memory region, and it cannot access the filesystem, network, or other system resources unless the host explicitly grants those capabilities. WASI extends this with capability-based security: modules start with zero authority and receive only the specific capabilities they need.
Summary
WebAssembly is a binary instruction format for a stack-based virtual machine — a compilation target that runs at near-native speed in browsers, on servers, and at the edge. It solves JavaScript's performance ceiling for compute-intensive tasks by letting you run C, C++, Rust, Go, and other compiled languages on the web without rewriting them.
Wasm is not a JavaScript replacement. It cannot access the DOM, and it works best alongside JavaScript: JavaScript handles the web ecosystem, Wasm handles the heavy computation. The technology has matured from an MVP in 2017 to version 3.0 in 2025, with WASI enabling serious server-side and edge computing use cases.
For developers building performance-critical web applications, porting existing native codebases to the browser, or running sandboxed server-side plugins, WebAssembly is worth understanding — and increasingly worth using.
Sources
- MDN — WebAssembly concepts (developer.mozilla.org/en-US/docs/WebAssembly/Guides/Concepts
- CC-BY-SA 2.5+)
- Wikipedia — WebAssembly (en.wikipedia.org/wiki/WebAssembly
- CC BY-SA 4.0)
- Wikipedia — Emscripten (en.wikipedia.org/wiki/Emscripten
- CC BY-SA 4.0)
- Wikipedia — AssemblyScript (en.wikipedia.org/wiki/AssemblyScript
- CC BY-SA 4.0)
- Wikipedia — SQLite (en.wikipedia.org/wiki/SQLite
- CC BY-SA 4.0)
- W3C — WebAssembly Core Specification (w3.org/TR/wasm-core
- W3C standard)
Share this guide
Related guides
- What is the JavaScript event loop? How the call stack, task queue, and microtask queue work
The JavaScript event loop is the runtime model that lets single-threaded JavaScript run asynchronous code. Learn how the call stack, the task queue, and the microtask queue cooperate, and why Promise callbacks fire before setTimeout.
- What is an API? A plain-language guide to how APIs work
What an API is, how REST APIs work over HTTP, the methods you'll actually meet — GET, POST, PUT, PATCH, DELETE — and how to read a response.
- What is a Regular Expression (regex)? A practical guide
A regular expression (regex or regexp) is a sequence of characters that forms a search pattern for matching and manipulating text. Built on a formal mathematical foundation and common to almost every programming language and tool, regex lets you validate input, find and replace text, extract data, and transform strings with a compact, declarative syntax. This guide explains what regex is, its core syntax, how it is implemented, and how to use it safely.