A WebAssembly to native code compiler using Binaryen and dstogov/ir.
Wasm2Sea translates WebAssembly bytecode to an intermediate representation (IR), then generates native code through the dstogov/ir backend. The project demonstrates a complete compilation pipeline from WASM to executable code.
- Arithmetic Operations: add, sub, mul, div (signed/unsigned), rem
- Comparisons: eq, ne, lt, gt, le, ge (signed/unsigned), eqz
- Bitwise Operations: and, or, xor, shl, shr (arithmetic/logical)
- Local Variables: local.get, local.set, local.tee
- Control Flow:
- Select (ternary operator)
- If-else with complex branches
- Nested conditionals
- Loops: Loop structures parsed, execution not yet implemented
- Block structures
- Function calls
- Memory operations
- Additional types (i64, f32, f64)
See TODO.md for complete list.
- CMake 3.10+
- C++17 compiler
- Binaryen library
- dstogov/ir framework
mkdir build && cd build
cmake ..
make- Write WebAssembly text format (.wat):
(module
(func $add (export "test") (param i32 i32) (result i32)
local.get 0
local.get 1
i32.add
)
)- Compile to WASM:
wat2wasm add.wat -o add.wasm- Convert to IR:
./wasm2sea add.wasm- Generate and compile C code:
cd ../third_party/dstogov-ir
./ir_main ../../build/out.ir --emit-c out.c
cc -O2 out.c run_varargs_ffi.c -o a.out $(pkg-config --cflags --libs libffi)- Run:
./a.out 10 20 # Returns 30Use the provided test script:
./test_wasm_ffi.sh test_add 10 20- wasm_reader: Parse WASM binary using Binaryen
- wasm_lower: Lower to SSA-form ValueIR
- ir_bridge: Convert to dstogov/ir graph
- dstogov/ir: Generate native code
- Visitor Pattern: Manual control over AST traversal for correct control flow handling
- SSA Form: Each value assigned once, simplifies optimization
- Label Management: WebAssembly labels converted to depth-based indexing
- PHI Nodes: Handle value merging at control flow joins
- dstogov/ir converts
GT(a,b)toLT(b,a)internally - This affects PHI parameter ordering in control flow
- Select and if-else require different PHI orders as a result
See tests/ directory for examples:
test_select.wat: Ternary operatortest_if_else.wat: Conditional branchestest_if_complex.wat: Complex branch logictest_loop_countdown.wat: Loop structure (parsing only)
# Individual test
./test_wasm_ffi.sh test_name [args...]
# Example
./test_wasm_ffi.sh test_if_else 10 5 # Expected: 10Uncomment debug prints in wasm_reader.cpp to see instruction sequence.
- Add to
WasmOpenum inwasm_instr.hpp - Handle in
visitExpressioninwasm_reader.cpp - Lower to ValueIR in
wasm_lower.cpp - Map to dstogov/ir in
ir_bridge.cpp
This is a research/educational project demonstrating WebAssembly compilation. Current focus is on implementing loop support, which is the most complex remaining feature.
See PROGRESS.md for detailed status and TODO.md for roadmap.
[Add your license here]