WebAssembly (WASM)
WebAssembly, a.k.a. WASM, is... how best to describe it... a virtual machine hosting a low-level programming language (WASM) which many other programming languages can be compiled to. Wasm has been described as "neither web, nor assembly" and, though it is primarily a web-based platform, numerous efforts are underway to make Wasm more widely applicable. Imagine desktop applications written in 5 different programming languages, all of which interact seamlessly by virtue of having been compiled into a common low-level language.
Sidebar: Wasm is conceptually akin to the CIL/CLR Microsoft introduced with their DotNet platform in the early 2000s, the main difference being that MS never managed to gain a widespread critical mass of support for that technology whereas Wasm is at that point now. (That always seemed strange to me, as CIL stood to change the software landscape in ways Wasm is now doing. Presumably its lack of traction was largely due to CIL originating from a company which was, at the time, outright hostile to FOSS development and infamous for its vendor lock-in tactics. Much as changed at Microsoft since then, but that history still haunts them to this day.)
Some links...
- webassembly.org is the platform's main online presence.
- sqlite.org/wasm is maintained by yours truly.
- The MDN docs for WebAssembly are a must-read for folks writing JavaScript code to work with Wasm. (Though Wasm is not strictly tied to JS, it was designed specifically to be scripted by JS, so the two have a close relationship.)
- The WebAssembly System Interface (WASI) is an effort to provide conventional system-level APIs to Wasm applications (e.g. filesystem access APIs).
- Emscripten is, by leaps and bounds, the current king of the Wasm toolchain landscape, making it absolutely trivial to deploy a wide array of "legacy" C code as Wasm.
- Jaccwabyt is my JavaScript library for creating two-way bindings for C structs, such that changes made to them in C are visible in JS and vice versa. That project also hosts a small utility library which replaces much of Emscripten's auto-generated "glue" code, the goal being to help JS code escape Emscripten's orbit.
And some evangelism/hype...
My first experience with Wasm was not until mid-2022, when the opportunity came up to do a proof-of-concept application for the sqlite project. It very quickly became clear that the ease with which C code can be compiled and run in a web page was going to impact my development for the foreseeable future. Though my record for predicting tech trends has historically been exceptionally poor, it seems safe to predict that Wasm is going to change the way software is targeted over the next decade.
Wasm's ease of use and utility took me completely by surprise. (Getting sqlite3's shell app built and running in Wasm was my first-ever Wasm task and it took all of about 27 minutes, most of that time being spent figuring out how to install and use Emscripten.) i'd heard whispers of it for years but never paid any attention until the notion of the sqlite proof-of-concept project came up. Though i have a strong allergy against hype, i'm thoroughly convinced that Wasm is worth every bit of hype for several reasons:
- There's been a lot of pressure in some software development circles to "rewrite everything in Rust" because Rust is a so-called "safe" language, in that it's difficult or impossible (barring Rust compiler bugs) to write code which can go stomping all over your process's memory like it is in C. Rewriting (and retesting and redocumenting) all C code isn't practical, but compiling it to Wasm is trivial and inherently provides a sandboxed environment for it to run in, achieving much of the safety factor of Rust with sub-0.1-percent of the effort for any non-trivial project. It is definitely easy to stomp your whole app's memory in Wasm, but you're trapped in that sandbox so you cannot use such memory misuse to do things like execute arbitrary code in the OS and other maliciousness with which C has long-since been associated (whether rightly or wrongly is not a detail which will be debated here!).
- Wasm immediately breathes new life into, and provides new channels for, code which was never envisioned to run anywhere outside of a C or C++ library. For example, within a couple of weeks of implementing sqlite's /fiddle app, we created a similar app for Richard Hipp's pikchr. The prior version of that app required round-trip client/server traffic to render SVG images on the server and send them back to the client, whereas Wasm gives us a way to perform all of that work directly in the client-side browser, a use case never considered when pikchr was written.
- Some (not me) have concerns that C coding, as a skill, is becoming less and less relevant. With Wasm, that concern itself is largely irrelevant because we (the C coders of the world) can now continue to write C while targeting modern browser-side apps at the same time. The long-touted efficiency of C now becomes available to developers who don't know C, simply by compiling it to Wasm or integrating a precompiled Wasm file into one's JS project.
- It "just works." Going in, i expected all sorts of friction between JavaScript and C APIs because of wildly differing language-level semantics. The Wasm middle-man accomodates both very well, though, providing a common ground which is neither strongly partial to one language or the other nor antagonistic to either.
- It's trivial to get up and running using Emscripten. Though i
advise against becoming 100% dependent on any given toolchain,
Emscripten is currently the unambiguously clear leader in the
realm of Wasm toolchains and its "get immediate results" approach
to building, which optionally includes generation of the HTML and
JavaScript needed to use Wasm-compiled C code, provides an
excellent basis for "working backwards" to understand what tasks
it is performing under the hood.
Sidebar: Emscripten makes transforming C to Wasm trivially easy by taking over several layers of the process, and i've nothing against Emscripten, but when it comes to building code, vendor lockin (even if when the vendor is an FOSS project) doesn't sit well with me, so i continue to search for solutions to building C code with other Wasm toolchains.
Wasm still has some maturing to do, certainly, but its 1.0 version is already plenty usable for a wide range of cases and provides a solid target for "replatforming" non-web code into web environments. A movement is underway to provide the same capability to non-web targets, as well as to provide a portable basis for applications to be unaware of whether they're running inside or outside of a browser but, as of this writing, the WASI efforts aren't quite up to the task, primarily in the realm of filesystem-related APIs. It's still (as of mid-2022) effectively impossible to get any code C which uses filesystem APIs to build for a web target unless it uses the Emscripten toolchain, as that one provides its own compatibility layer for such APIs.