WasmLinux Terminal:
(Please wait for / #
prompt. If it doesn't appear, focus the terminal and hit Enter. See below for why...)
GitHub / X (formerly Twitter) / (J) Blog article on Zenn
Here is WasmLinux, prototype of WebAssembly "native" Linux system.
Unlike existing Linux-on-Wasm solutions like WebVM(x86) or container2wasm(RISC-V, x86), WasmLinux does not use emulator of any existing CPU architecture, both userland and kernel.
This is composed with patched NOMMU Linux(LKL) + lightly patched Linux MUSL libc + lightly patched Busybox, compiled to Wasm (and processed with Wasm2c and compiled again with Emscripten, just for setjmp/longjmp)
We are working on native setjmp/longjmp implementation, just like WASI libc #467 so we can drop wasm2c usage in future.
Click the terminal above, then say ls
, then hit Enter twice
Currently the only app provided is BusyBox. You can do other things such as vi
, dmesg
, ifconfig lo up
then ping 127.0.0.1
or even top
. To get list of available commands, say busybox
.
WasmLinux has several unimplemented features. Namely;
read
(2) by-hand. This is why an additional Enter required for each commands.mmap
(2) so we don't have fork
(2) either. Actually, WasmLinux kernel is just a Wasm executable that contains LKL (Linux kernel library -- Linux kernel as userland library) so there is no real "kernel-mode" code. We will eventually implement mmap
or POSIX signal emulations on it but I don't think WasmLinux will become actual linux arch.
To recover from hang, just reload this page. It does not have any persistent data.
Many things are broken since we don't have proper POSIX signal implementation yet. Incomplete list of bugs;
dmesg | less
, instead, say dmesg > out
then less out
ls; ls
yet.Comming soon(TM). Current near-term roadmap is;
fork
(2).wasm32-linux
ABI and provide SDK so users can add appsLong-term goal is to support mmap
(2) with address translation (like v86) but I'm not really sure when it is ready.
PC(native) builds with wasm2c
will remain as Tier1 platform of WasmLinux. PC builds will be the only way to implement "hardmmu" memory management.
Currently, it is just a PoC state thus sources are just complete mess; do not waste your time on it...
For reference, build flow overview:
Every source code reference is submoduled on GitHub wasmlinux-project repository.
Tentative syscall protocol is baked in Musl patches and implemented in runner source. It is just a Wasm export and will get final names elsewhere. User code should not call the export directly and encouraged to use libc.
On user's syscall, runner will call kernel through its wasm export that is exported from the kernel. Currently, wasm2c is the only Wasm engine that the runner support. Runner has knowledge of syscall argument counts and will adjust syscall argument when required -- calling C function with correct argument count is strict requirement of Wasm.
The runner has "pseudo inetd" feature that invokes a process on incomming connection and relay socket pair I/O to the host system. Host I/O backend is abstructed to miniio library and on PC build, it will use libuv. On browser build, it has dedicated localhost-only stub which is implemented on host pthread.
To communicate with WasmLinux system, BusyBox telnetd
will be used. On PC build, conventional telnet client (e.g. PuTTY) will work. On browser build, our own minitelnet telnet client which is implemented on miniio will be used. Minitelnet assumes host environment supports Linux-like PTY and it is implemented using xterm-pty on this page.
Write once(by other folks), run anywhere(i want). I know we already have WASI or WALI, but unfortunately they need to be ported to some serious OS to work with. Since WasmLinux covers Linux kernel as well, required porting effort is quite little; it even have filesystems or device drivers. Even if you designed your own ISA just runs Wasm, WasmLinux (theoretically) easily ported on it and no need to port other apps that runs on WasmLinux.
... anyway, I think WALI still require apps to be ported to its environment because it doesn't provide enough platform abstraction to make porting effortless (e.g. page size is 64k, no setjmp/longjmp, ...). WasmLinux choose to develop native Linux Kernel that can be implemented on browser Wasm environments to ensure its ABI is enough portable.
Currently we can support BusyBox for almost zero porting effort, because it already supports NOMMU environment. We'd like to extend these to non-NOMMU apps by adding memory protection etc in future. Unfortunately many Linux apps assumes Linux environment is ELF, have computed goto
s, have __builtin_return_address
, assume implicit function pointer cast, etc. We believe WasmLinux solves some sort-of chicken/egg problem; some of these are good candidate for Wasm extension and existence of real apps would be helpful.
For now, entire WasmLinux system is just a usermode C++20 application; LKL and MUSL+BusyBox are ported on bare-bone Wasm environment then translated with wasm2c
and linked with a thin runtime stub. We have intentionally avoided Emscripten for first porting to ensure ported WasmLinux kernel and apps can run on (mostly) standard WebAssembly engines, and wasm2c
can turn it to plain C application. setjmp
, longjmp
and vfork
are last remaining parts that require special Wasm engine capability but i think they can be implemented with Wasm exception proposal so we would be able to make entire system Emscripten-free eventually.
Terminal is implemented with xterm-pty. CSS is Water.css. Web page libraries are served by unpkg. Embedded telnet client is based on libtelnet.