{"id":18016658,"url":"https://github.com/bytecodealliance/waffle","last_synced_at":"2025-04-05T12:04:37.098Z","repository":{"id":255598441,"uuid":"850057647","full_name":"bytecodealliance/waffle","owner":"bytecodealliance","description":"Wasm Analysis Framework For Lightweight Experiments","archived":false,"fork":false,"pushed_at":"2024-11-25T21:55:44.000Z","size":607,"stargazers_count":42,"open_issues_count":0,"forks_count":4,"subscribers_count":10,"default_branch":"main","last_synced_at":"2025-03-29T11:06:55.592Z","etag":null,"topics":["compiler","ssa","wasm"],"latest_commit_sha":null,"homepage":"","language":"Rust","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"apache-2.0","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/bytecodealliance.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":"CONTRIBUTING.md","funding":null,"license":"LICENSE","code_of_conduct":"CODE_OF_CONDUCT.md","threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null}},"created_at":"2024-08-30T19:41:34.000Z","updated_at":"2025-02-25T17:28:43.000Z","dependencies_parsed_at":"2024-10-30T04:42:43.059Z","dependency_job_id":null,"html_url":"https://github.com/bytecodealliance/waffle","commit_stats":null,"previous_names":["bytecodealliance/waffle"],"tags_count":1,"template":false,"template_full_name":null,"repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/bytecodealliance%2Fwaffle","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/bytecodealliance%2Fwaffle/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/bytecodealliance%2Fwaffle/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/bytecodealliance%2Fwaffle/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/bytecodealliance","download_url":"https://codeload.github.com/bytecodealliance/waffle/tar.gz/refs/heads/main","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":247332601,"owners_count":20921853,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["compiler","ssa","wasm"],"created_at":"2024-10-30T04:18:49.307Z","updated_at":"2025-04-05T12:04:37.075Z","avatar_url":"https://github.com/bytecodealliance.png","language":"Rust","readme":"\u003cdiv align=\"center\"\u003e\n  \u003ch1\u003ewaffle\u003c/h1\u003e\n\n  \u003cp\u003e\n    \u003cstrong\u003ewaffle Wasm compiler library\u003c/strong\u003e\n  \u003c/p\u003e\n\n  \u003cstrong\u003eA \u003ca href=\"https://bytecodealliance.org/\"\u003eBytecode Alliance\u003c/a\u003e project\u003c/strong\u003e\n\n  \u003cp\u003e\n    \u003ca href=\"https://github.com/bytecodealliance/waffle/actions?query=workflow%3ACI\"\u003e\u003cimg src=\"https://github.com/bytecodealliance/waffle/workflows/CI/badge.svg\" alt=\"build status\" /\u003e\u003c/a\u003e\n    \u003ca href=\"https://bytecodealliance.zulipchat.com/#narrow/stream/223391-wasm\"\u003e\u003cimg src=\"https://img.shields.io/badge/zulip-join_chat-brightgreen.svg\" alt=\"zulip chat\" /\u003e\u003c/a\u003e\n    \u003ca href=\"https://docs.rs/waffle\"\u003e\u003cimg src=\"https://docs.rs/waffle/badge.svg\" alt=\"Documentation Status\" /\u003e\u003c/a\u003e\n  \u003c/p\u003e\n\n  \u003ch3\u003e\n    \u003ca href=\"https://docs.rs/waffle\"\u003eAPI Docs\u003c/a\u003e\n    \u003cspan\u003e | \u003c/span\u003e\n    \u003ca href=\"https://github.com/bytecodealliance/waffle/blob/main/CONTRIBUTING.md\"\u003eContributing\u003c/a\u003e\n    \u003cspan\u003e | \u003c/span\u003e\n    \u003ca href=\"https://bytecodealliance.zulipchat.com/#narrow/stream/223391-wasm\"\u003eChat\u003c/a\u003e\n  \u003c/h3\u003e\n\u003c/div\u003e\n\nwaffle (the Wasm Analysis Framework for Lightweight Experimentation)\nis an SSA IR compiler framework for Wasm-to-Wasm transforms, in Rust.\n\n## Status\n\nThe transforms from Wasm to IR and from IR to Wasm work well, and has been\nfuzzed in various ways. In particular, waffle is fuzzed by roundtripping Wasm\nthrough SSA IR and back, and differentially executing the original and\nroundtripped Wasm under Wasmtime (with limits on execution time). At this time,\nno correctness bugs are known.\n\nWaffle is able to roundtrip (convert to IR, then compile back to Wasm) complex\nmodules such as the SpiderMonkey JS engine compiled to Wasm.\n\nWaffle has some basic mid-end optimizations working, such as GVN and constant\npropagation. Much more could be done on this.\n\nThere are various ways in which the generated Wasm bytecode could be improved;\nwork is ongoing on this.\n\nwaffle is in use by [weval](https://github.com/bytecodealliance/weval), the\nWebAssembly partial evaluator, and was developed for this purpose.\n\n## Architecture\n\nThe IR is a CFG of blocks, containing operators that correspond 1-to-1 to Wasm\noperators. Dataflow is via SSA, and blocks have blockparams (rather than\nphi-nodes). Wasm locals are not used in the IR (they are converted to SSA).\n\nThe frontend converts Wasm into this IR by building SSA as it goes, inserting\nblockparams when it discovers multiple reaching definitions for a local.\nMultivalue Wasm (parameters and results for every control-flow block) is fully\nsupported, and converted to SSA. This process more or less works like\nCranelift's does, except that memory, table, etc. operations remain at the Wasm\nabstraction layer (are not lowered into implementation details), and arithmetic\noperators mirror Wasm's exactly.\n\nThe backend operates in four stages:\n\n* [Reducifier](src/backend/reducify.rs), which uses context-sensitive\n  block duplication to turn loops with side-entrances (which are\n  irreducible) into reducible control flow, suitable for lowering to\n  Wasm control-flow primitives.\n\n* [Structured control flow recovery](src/backend/stackify.rs), which uses\n  [Ramsey's algorithm](https://dl.acm.org/doi/abs/10.1145/3547621) to convert\n  the CFG back into an AST of Wasm control-flow primitives (blocks, loops, and\n  if-then AST nodes).\n\n* [Treeification](src/backend/treeify.rs), which computes whether some SSA\n  values are used only once and can be moved to just before their single\n  consumer, computing the value directly onto the Wasm stack without the need\n  for an intermediate local. This is a very simple form of code scheduling.\n\n* [Localification](src/backend/localify.rs), which performs a register\n  allocation (using a simple linear-scan algorithm) to assign all SSA values to\n  locals such that no live-ranges overlap in the same local.\n\n## Comparisons / Related Work\n\n- Like [Binaryen](https://github.com/WebAssembly/binaryen) but with an SSA IR,\n  rather than an AST-based IR. Dataflow analyses are much easier when one\n  doesn't have to handle arbitrary reads and writes to locals. Binaryen is able\n  to stackify/reloop arbitrary control flow (CFG to Wasm) but does not\n  implement the other direction (Wasm to CFG), and it has only a C/C++ API, not\n  Rust.\n\n- Like [Walrus](https://github.com/rustwasm/walrus) but also with an SSA IR.\n  Walrus is in Rust and designed for Wasm-to-Wasm transforms as well, but its\n  IR mirrors the Wasm bytecode closely and thus presents the same difficulties\n  as Binaryen for traditional CFG-of-SSA-style compiler analyses and\n  transforms.\n\n- Halfway like\n  [Cranelift](https://github.com/bytecodealliance/wasmtime/tree/main/cranelift/),\n  in that the IR is similar to Cranelift's (a CFG of SSA IR with blockparams),\n  but with the Wasm backend as well (Cranelift only does Wasm-to-IR). WAFFLE's\n  IR also deliberately remains at the Wasm abstraction level, maintaining\n  1-to-1 correspondence with all operators and maintaining the concepts of\n  memories, tables, etc., while Cranelift lowers operations and storage\n  abstractions into runtime/embedding-specific implementation details in the\n  IR.\n","funding_links":[],"categories":[],"sub_categories":[],"project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fbytecodealliance%2Fwaffle","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fbytecodealliance%2Fwaffle","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fbytecodealliance%2Fwaffle/lists"}