Branch state (2026-10-18): master and resolve-check are both at
95ca4d6 (merged, fast-forward) and pushed to origin. Work on
master.
Baseline: suite 239/239, fixpoint OK (3,812,771 bytes), corpus 405/612, 0 crashes. The corpus harness resolves transitive imports (method from 2026-10-18).
Policy: follow Modula-2, not gm2 degradation — declaration
before use (only a POINTER's base may forward-reference). In
docs/gaps/, the decl-order and gm2-ext classes are not targets;
the 44-file "undeclared identifier" bucket is inflated by them.
Instantiating one generic twice with arguments from different families fails on the second instantiation:
GENERIC DEFINITION MODULE GStack (T : TYPE);
TYPE NodeRec = RECORD val : T; next : Node END; ...
GStack(CHAR) alone works; GStack(INTEGER) alone works; together,
the second fails (incompatible assignment at n^.val := v).
INTEGER + CARDINAL appears to pass only because the stale binding
still type-checks.
Likely culprit: SymTab.EnterTypeParamBound returns early when the
formal is already visible, so the first instantiation's binding sticks:
IF Lookup(name) AND (SymKind(name) = KindType) THEN RETURN TRUE END;
Steps: five-file repro (generic def/mod + two instantiations + a program); make the substitution per-instantiation (fresh alias); add a regression test with two distinct scalar families; keep the fixpoint green.
gap22 __FILE__/__LINE__ (packed, +1).gap09 scalar actual → ARRAY OF BYTE (aochar,
arrayofbyte, bytearray, +~3).gap12 variant records: empty arms, ELSE, untagged inner
CASE (5 files).gap11 bare procedure value as a statement.gap10 VAR-param type leniency (decide whether to adopt gm2's
same-size rule — non-standard).gap13 remainder: de-reserve the standard builtins (ORD,
CHR, VAL, …) — contextual-keyword parser refactor (ORDL is done).gap18 set-typed CASE labels.Forward references to module-level variables/procedures from a procedure body still work (the two-phase parse defers bodies). Strict declaration-before-use would require order-aware body checking; high risk, touches self-hosting. The declaration part is already strict.
The size-sensitive V3 miscompile ("removing ASTDUMP breaks the
fixpoint") is still unroot-caused. Dedicated bisection session; a real
correctness landmine.
docs/summary_*.md (see docs/INDEX.md).resolve-check → master: done.)compiler/build.sh → compiler/run_tests.sh (must stay 100%) →
bootstrap/fixpoint.sh (byte-identical) → corpusx.sh (record
OK/CRASH + note) → update docs/gaps/ + STATUS/README → commit with
a v3-* tag.
cd .../m2compiler-V3
git checkout master
cd compiler && ./build.sh && ./run_tests.sh # 239/239
cd .. && TMP="$PWD/.scratch/fixpoint" ./bootstrap/fixpoint.sh
M2FLAGS="" ./.scratch/corpusx.sh # 405 OK, 0 crash
Recommendation: P0 first (a real defect), then two P1 wins, and reserve a separate session for P4.