# sx Inline Assembly — Checkpoint (ASM stream) Companion to `current/PLAN-ASM.md`; design in [docs/inline-asm-design.md](../docs/inline-asm-design.md). Update after every commit, one step at a time per the cadence rule (no commit may both add a test and make it pass). ## Last completed step **0.2** — docs: CLAUDE.md §Testing + §Test-layout now document the `.build` JSON sidecar (`aot` + `target` keys, ir-only arch-gating, unknown-key-is-error) and list it alongside the other `expected/` files, replacing the stale standalone `.aot` marker prose. Docs-only — no build impact. **Phase 0 COMPLETE.** Prior: **0.1** — corpus runner **ir-only branch** for cross-target examples. Replaced 0.0's loud placeholder bail: when `cfg.target` doesn't match the host (`ir_only`), `sweepRoot` skips run/build/exec and verifies via `sx ir --target` only — asserting `.exit` (ir cmd) + `.ir` (normalized stdout) + `.stderr`, never `.stdout` (write skipped in update mode, assertion skipped in verify mode). An `.ir` snapshot is **required** in ir-only mode — its absence is a loud failure ("needs an .ir snapshot for ir-only mode"). Locked with `examples/1639-platform-target-cross.sx` (asm-free `main :: () -> i64 { return 0; }`), `.build` `{ "target": "x86_64-linux" }`, + checked-in `.ir`. Verified both guards fire: corrupting the `.ir` → IR mismatch; deleting it → the require-failure. `zig build test` green (647 corpus, 0 failed; 444 unit). Files: `src/corpus_run.test.zig`, `examples/1639-*`. ## Current state Phase 0 steps 0.0 + 0.1 landed (test-infra only — no compiler code). The corpus runner reads `expected/.build` (JSON `{ aot, target }`), threads `--target`, and gates on host arch+os: a matching target **executes** (full exit/stdout/stderr + optional `.ir`); a mismatch runs **ir-only** (`sx ir --target`, asserting exit+ir+stderr, `.ir` required). Phase A–E feasibility already confirmed against the live tree (`LLVMGetInlineAsm` / `LLVMBuildCall2` / `LLVMAppendModuleInlineAsm` in LLVM@19 `Core.h`; ERR-stream `extractvalue`→tuple in `emit_llvm.zig:726-927`; lib-less `extern`, 60 sites; `--target` a global CLI flag). ## Next step **A.0** (Phase A — first compiler code) — add the `kw_asm` keyword: `Token.Tag` entry + keyword `StaticStringMap` in `src/token.zig`, plus a unit lex test (`asm → kw_asm`). `volatile`/`clobbers` stay out of the global table (contextual). This is a **lock** commit (behavior-locking passing test). Then A.1 (parse `asm { … }` → `AsmExpr`, lowering bails loudly). See `PLAN-ASM.md` Phase A. ## Log - (init) Plan + design doc written; ASM stream opened. - (0.0) Corpus runner target-gating: `.build` JSON config (replaces `.aot` marker), `--target` threading, `hostMatchesTarget` execute-gate, loud cross-target placeholder bail. Migrated 1226/1227 `.aot`→`.build`; locked with 1638 fixture + unit tests. `zig build test` green. - (0.1) ir-only branch: cross-target examples verify via `sx ir --target` only (exit+ir+stderr, no stdout; `.ir` required). Locked with 1639 fixture; verified corrupt-.ir → mismatch and missing-.ir → loud failure. `zig build test` green. - (0.2) docs: CLAUDE.md documents `.build` JSON sidecar (aot + target + ir-only gating), replacing stale `.aot` marker prose. **Phase 0 COMPLETE.** ## Known issues None yet.