# Session save — to be continued Date: 2026-10-02. HEAD: `7dbd516` (`express-draft-v1`). Tree clean. ## Where we are `src/compiler/` holds the re-read compiler: `COMPILER/SCANNER/ERRORS/CODEGEN` fully renamed + verified clean of numbered identifiers; `SYMTAB.MOD` draft v1 (988 lines, 27 FIXMEs); `EXPRESS.MOD` draft v1 (1489 lines, 137 FIXMEs, 20 FORWARD work-list helpers); `SYMTAB.DEF` expanded (words 10–27); `FRONTEND.md` export map incl. newly found EXPRESS internals; `docs/compiler/` analysis. ## How we work * Upstream dirs git-ignored; only `docs/`, `src/`, `SUMMARY.md`, `SESSION.md` versioned. * Decompile in parallel background workers (3–4 groups per module), each returns Modula-2 with `{/* offset */}` comments; assemble + normalize via script (`Compiler.word6–26`, `Scanner.word2–12`, `Doubles.proc5–11` mappings); verify with `grep -nE '\b(param|local|global|proc|PROC)[0-9]+\b'`. * Drafts are unverified by design: MCD `unassemble.c` diff still pending for all. * Commit per step, tag per milestone (`*-v1`). ## 2026-10-03: audit + proc32 applied (`audit-01`) proc32 WriteOutputFiles added; 8 SYMTAB + 9 EXPRESS signature swaps applied (def headers; bodies/calls positional-consistent by construction); STMT+PASS1 all KEEP; D1/D2 resolved (map stands); CappedStrLen=StrLen alias noted. Next: GENZ80 recon + MCD-diff verification harness. ## 2026-10-03: GENZ80 recon + MCD-diff harness (`genz80-harness-01`) GENZ80: no binary/disassembly anywhere (only call site + overlay-table strings); trigger chain partly open (no setter of nativeCodeRequested found); recovery = extract overlay from original CP/M media. Harness tools/mcdiff.sh: stage 1 green (1a clean, 1b FORWARD-OK, 1d spot-check; fixed StrLenHelper, word6, Doubles.proc5, Scanner.word2, Compiler.word3 leftovers on the way). VM builds clean (gcc, `m2` binary); stage-2 run blocked on terminal I/O (documented pty approach in mcdiff.sh header). Next: GENZ80 media hunt; stage-2 pty-driven MCD diff per module. ## Next steps (in order) 1. DONE (`statemen-draft-v1`): `STATEMEN.MOD` 830 lines + frame-mechanics proof. 2. DONE (`pass1-draft-v1`): `PASS1.MOD` 981 lines; disputes D1-D4 + proc9 recorded. 2. Pass1 bodies (`pass1.txt`, 2975 lines): `~ParseType` (02e6), `ParseRecord`, formals, decls, module heads, `WriteSym` — 3–4 workers. 3. Resolve `SYMTAB.MOD` FIXMEs (AllocSym arity, D-group sketches, LSL) and `EXPRESS.MOD` FORWARDs (CentralError/PushOperand/EmitOp/BoolCondHelper/...). 4. `GENZ80` native backend (untouched so far). 5. Recompile + `unassemble.c` MCD diff verification for every draft. 6. Refresh `SUMMARY.md` + retag when milestones land. ## SCANNER verify checkpoint (2026-10-06, uncommitted -> committing) - SCANNER.MOD compiles on v1.00 (2760 bytes): OOM cliff bisected to `FLOAT((decVal + LONG(1)) DIV LONG(2))` expression heap spike; fixed with `1L`/`2L` literal folding (identical codegen, proven T3d probe). - MCD diff vs Reloaded SCANNER.MCD: 34/41 mnemonic-identical (00-gap stripped, absolute targets masked). Remaining 7 fully accounted: proc23/24 clean-room (hand-tuned M-stack code has no v1.00 source form; algorithms decoded + restored incl. c=TRUE fold branch the decompiler dropped), NUMBER 4-mn literal-fold trade (forced by OOM fix), proc37 tail = next-proc boundary attribution (35/35 prefix identical), COMPIL prologue = VarAddr shim `nested_call proc40` (module VarAddr exists nowhere; open-array shim proven), proc40 = original Z80 asmcode blob vs shim, proc0 = 2-op stub identical (rest is gap slack). - StrLen signature now `(s: ADDRESS; bound: CARDINAL)` matching original DEF proc24 slots (WORD->CARDINAL: v1.00 WORD has no comparisons); SYMTAB.MOD:221 caller fixed to pass bound 128 (proven from symtab.txt `load immediate 128` at call site); CODEGEN.MOD:392 already 2-arg. - Padding blocks removed (Allocate/FindIden/NextCh/ScanNext) — were dead code polluting the diff; GetSym now byte-compares modulo gap zeros. ## CODEGEN verify checkpoint (2026-10-12) - CODEGEN.MOD compiles on v1.00 (2393 bytes): 34/37 mnemonic-identical. - Stale renames fixed (codeBuf/EnterMod/ScanErr). keywordTable saga closed: original COMPILER.MOD also Allocate+CARDINAL-stores (proven byte-shape), CODEGEN reads low byte via `limit_check+shl1+LXB` = `compTab[i][0]` shape; v1.00 can't spell that from ADDRESS global, so local 2D-BYTE overlay (Q1/Q2-proven ADDRESS:=pointer assigns) at 2 use sites, +2mn each. - proc0 trailing region = embedded absolute-address tables shifted by the +6 growth (every byte -4): consequential, not semantic.