Commit graph

540 commits

Author SHA1 Message Date
Shay
3a72d69678
Merge pull request #545 from AssetOverflow/docs/ratify-sensorium-afferent
docs: ratify sensorium afferent ADRs + work-sequencing acknowledgment
2026-06-03 22:29:50 -07:00
Shay
7160e5e77f
Merge pull request #544 from AssetOverflow/feat/r4-goal-residual
feat(r4): cv-0005 goal-residual to serving — train_sample 6/44/0 → 7/43/0 (ADR-0207 §5 step 2)
2026-06-03 22:29:21 -07:00
Shay
bd6e0377e1 docs: ratify sensorium afferent ADRs + acknowledge arc in work-sequencing
Authority-ratified per the ADR-0207 convention (Accepted (ratified DATE)):
- ADR-0181 (audio), ADR-0197 (vision), ADR-0208 (environmental loop),
  ADR-0209 (sensorimotor afferent) -> Accepted (ratified 2026-06-03).
  All four are implemented + test-backed (0208/0209 falsifiability deeply
  verified in the lookback; 0181/0197 backed by CRDT-merge/compiler/mount/
  eval-gate suites, all green in the 182-test sweep).
- ADR-0198 deliberately NOT ratified: partially-implemented spike (Gap A +
  fail-closed efferent gate landed; \xc2\xa73 verdict-lowering + motor decoder
  deferred behind a dedicated motor governance ADR).

CLAUDE.md Work Sequencing now records the sensorium/modalities arc as a
sanctioned parallel track that does not displace the near-term sequence and
is disjoint from the GSM8K serving path. Markdown only; no test asserts ADR
status or the work-sequencing text.
2026-06-03 22:21:50 -07:00
Shay
ad9cf57069 feat(r4): flip cv-0005 to serving — train_sample 6/44/0 -> 7/43/0 (ADR-0207 §5 step 2)
Wires the R4 goal-residual production to serving via
resolve_promotable_goal_residual (math_candidate_graph.py, mirroring
product_bridge). cv-0005 / train_sample 0037 now solves on serving as
goal - Σprogress = 10 - 3 - 4 = 3. First Phase-5b composition lift on serving.

wrong=0 preserved on every runnable surface:
- train_sample 6/44/0 -> 7/43/0 (0037 added; 6 prior correct intact; wrong=0).
- Fires on 2/455 visible GSM8K cases, both correct, ZERO wrong.
- Gain-goal divergence firewall proves it reads the GOAL, not a possession.
- smoke 73, math+invariants 53, derivation/pool/practice 341, corpus, all green.

Lockstep updates (the ratified metric move, 6/44/0 -> 7/43/0):
- report.json; 7 ADR test lanes that pinned 6/44/0; corpus cv-0005 baseline
  fields + snapshot (4/18 -> 5/17) + contract; plan-doc cv-0018 control fix.

⚠ SEALED MEASUREMENT REQUIRED — NOT DONE. The sealed 1,319 (encrypted, not
CI-reproducible) is the real bar (ADR-0207 §6) and was NOT re-measured. The
operator/CI must decrypt+run it and confirm sealed wrong==0; if wrong>0, revert
the resolve_promotable_goal_residual block (isolated). See
docs/handoff/sealed-measurement-obligation-2026-06-04.md.
2026-06-03 22:20:12 -07:00
Shay
b4fb9df8e7 feat(sensorium): fail-closed efferent gate for actuating decode (ADR-0198 §3)
DefaultEfferentGate is a capability/shape pre-filter only; it does not
lower decoded actions into safety/ethics pack verdicts (ADR-0198 §3 /
§1.2 Gap B). ModalityRegistry.decode/decode_batch now refuse fail-closed
any emission through a gate whose enforces_action_verdicts is False,
unless an explicit allow_unverified_efferent sandbox opt-in is set.

A real motor decoder thus cannot emit through the capability-only gate;
the §3 verdict-lowering gate must be built and installed first. No
production caller of the decode path exists today, so this closes the
latent hazard before a motor decoder makes it load-bearing. Adds two
falsifiable tests (fail-closed refusal; verdict-enforcing gate allowed).
Disjoint from the GSM8K serving path.
2026-06-03 22:03:35 -07:00
Shay
e5bc73ebb9 docs: reconcile sensorium ADR statuses with shipped implementation
ADR-0181/0197/0208/0209 were marked Proposed despite test-backed
afferent implementations merged to main; flip to Accepted with
verifiable Implementation lines (paths + PRs + falsifiable tests).
ADR-0198's 'no implementation' status was stale (Gap A protocol
change + baseline efferent gate landed in #541); correct it and
document the deferred §3 safety/ethics verdict-lowering as an
explicit blocking obligation before any motor decoder mounts.
2026-06-03 21:51:59 -07:00
Shay
5ae377065e docs: composition-wall execution scope (ADR-0207 §5 step 2)
Three reviewed, non-serving analysis/handoff docs for the COMPOSITION lever.
Read-only; no serving code; train_sample 6/44/0 untouched.

- analysis/wiring-promotion-gate-brief: product_bridge is the only serving
  derivation tendril (two-token target whitelist); resolve_pooled refuses all
  ten R1/R4/R5/R6 positives and wrong-commits 0016 -> 510. Wiring is trivial;
  the gate is the work.
- analysis/composition-wall-execution-plan: per-case stage taxonomy (A/B/C/D)
  for all 15 corpus positives, reproduced live; R4-first scope (new
  goal-residual production, verified by code-read of accumulate.py, NOT a
  target tweak); promotion gate generalizes product_bridge, never disagreement
  alone; gates inherit ADR-0207 §6 (corpus + sealed 1,319).
- handoff/stage-c-composition-investigation: dispatch task for the execution
  lane to pin the per-case bail for the production-wrong shapes (the real
  grouping/op-order wall), read-only, in-tree.
2026-06-03 21:14:02 -07:00
Shay
d9fc7f9e56
Merge pull request #540 from AssetOverflow/codex/vision-eval-environment-sensorimotor
[codex] Add vision evidence and sensorimotor contracts
2026-06-03 20:41:10 -07:00
Shay
2d2b096784 Add vision evidence and sensorimotor contracts 2026-06-03 20:27:46 -07:00
Shay
a6c36cc26f docs: amend ADR-0207 §5 step 1 — WIRING not the lowest-risk crux (tree-verified)
Reading the actual gate logic (product_bridge/pool/verify) corrected §5's
sequencing optimism, before merge:

- The safe wire is already done (product_bridge at :530); its safety is a
  two-token target whitelist (money+make/earn, weight+total/move) hardcoded to
  0003/0021 — it generalizes nothing.
- Verified live (2026-06-03): the general composer resolve_pooled refuses ALL
  ten R1/R4/R5/R6 corpus positives (R1/R4 build zero candidates; R5 only wrong
  ones) -> wiring yields +0 correct; and it wrong-commits 0016 -> 510, so wiring
  it wholesale is a live wrong=0 regression the disagreement rule does not catch.

So WIRING and COMPOSITION are the same task: composer production per shape, each
behind a structural promotion gate (extract_target + target_units, not
disagreement alone); the wire is the trivial last step. Core ratification
(freeze, design-of-record, gates, sealed-set measurement) unchanged.
2026-06-03 20:13:03 -07:00
Shay
fc01be715c
Merge pull request #537 from AssetOverflow/codex/sensorium-compiler-vision
[codex] Add sensorium compiler law and tile vision
2026-06-03 20:09:31 -07:00
Shay
282679bd85 Add sensorium compiler law and tile vision 2026-06-03 19:58:36 -07:00
Shay
94bf1be1bc docs: ratify ADR-0207 — GSM8K comprehension/composition substrate
Consolidating ratification of the GSM8K design of record. Ratify the built
comprehension/derivation substrate, freeze the serving regex recognizer/
injector path to lexemes + refusal-only, pin Phase 5b execution to
WIRING -> COMPOSITION -> LEXICON.

- ADR-0207: new consolidating decision (Accepted, ratified 2026-06-03).
  Supersedes ADR-0163 §Phase B-E + ADR-0136 regex sentence-template
  prescriptions. Freeze + wrong=0 gates (22-case corpus + sealed 1,319).
- ADR-0164/0165/0174/0178/0179: -> Accepted (ratified by ADR-0207,
  2026-06-03). 0164 keeps its implementation clause (Phase 1+2 shipped;
  remainder per §5) so Accepted != fully built.
- composition_validation/v1: 20 -> 22 cases (2nd R4/R5 positives,
  dataset-sourced golds), +contract invariants 6-7, +dataset-gold test.
  Baseline 4/18/0; 47 passed.
- docs/analysis: extraction-richness audit (read-only) reconciling
  ADR-0179 to the tree (EX-1/2/4/5/6 landed; EX-3 deferred).

Non-serving (evals/docs/tests only). train_sample 6/44/0 unchanged;
no-ref <N> times hazard stays refused. GB3b/0136 untouched.
2026-06-03 19:42:47 -07:00
Shay
b2b3678deb docs: mark ADR-0174 Phase 5a shipped in composition-capability-scope
Phase 5a (retire the inert GSM8K scoring-path comprehension-reader
dispatch, -1,038 LOC) landed in 3fd3172, an ancestor of HEAD 8327c6b,
but composition-capability-scope.md still listed it as remaining work --
drift that mis-scoped a downstream brief. Re-anchor the canonical doc to
the tree:

- §1: the lifecycle.py GSM8K-scoring dispatch row now reads "retired in
  Phase 5a (3fd3172)" instead of "inert ... retirable in 5a".
- §2: Phase 5a marked SHIPPED with a runway-status banner; the §9
  completeness-gate precondition marked LANDED (PR #534, e1bcdf6).
- §4: sequencing restructured -- items 0 (§9 precondition), 1 (gating
  analysis), 3 (5a) are DONE; the live runway starts at item 2 (the
  <=20-case validation sub-corpus), then Phase 5b.
- §9: status banner noting the recommended guard landed (#534); the
  "RED on main" statements are the pre-landing measurement, kept for
  provenance.

Docs-only. No code/eval/serving change. Baseline re-verified at HEAD:
train_sample 6/44/0 (all 44 refusals at branches_enumerated=0),
completeness-guard suite 21 passed.
2026-06-03 16:23:53 -07:00
Shay
018181c95b Add canonical composition analysis docs 2026-06-03 15:35:58 -07:00
Shay
e1bcdf6286 Harden no-reference n-times comparative guard 2026-06-03 15:22:42 -07:00
Shay
d5872a2e96 feat(adr-0206): response-governance bridge scaffold (STRICT-only, inert)
Adds the first consumer of CORE's two built epistemic substrates — the
decode-state taxonomy (core/epistemic_state.py) and the risk-reward
reliability gate (core/reliability_gate/, ADR-0175) — beginning to close
the LABEL-ONLY consumption gap they sat behind.

Ships the scaffold only:
- core/response_governance/policy.py — ReachLevel (STRICT < APPROXIMATE <
  EXTRAPOLATE < CREATIVE), ReachPolicy, govern_response (STRICT-only stub),
  shape_surface (STRICT = identity transform; higher levels real but
  unreachable in production), and the 9/5/1 EpistemicState partition.
- chat/runtime.py — cognition-path seam: the response surface now flows
  through shape_surface(govern_response(...)). STRICT = identity, so the
  path is byte-identical to pre-bridge. reach_level carried on ChatResponse.
- core/physics/identity.py — reach_level on TurnEvent (default "strict").

wrong==0 untouched: select_self_verified is NOT touched (ADR-0206 §5);
reach_level is NOT added to the telemetry JSONL dict, so pinned lane SHAs
stay byte-identical. Widening, SITUATE/FEED-BACK, the math-serving seam,
and the EVIDENCED reconcile are deferred to their own PRs.

Tests (tests/test_response_governance.py): STRICT-only contract over all
states x license x stakes, STRICT identity, live-wiring proof (forces
APPROXIMATE -> policy-sensitive surface), total+disjoint taxonomy
partition. Each fails loudly under the violation it guards.
2026-06-03 10:39:12 -07:00
Shay
64f3da18a7 feat: modus_ponens + disagreement rule — proof_chain wrong=0 mechanism (ADR-0205)
Phase 2.3: the first inference rule + the wrong=0 mechanism for proofs.

- generate/proof_chain/rules.py: evaluate_modus_ponens / evaluate_proof_conclusion.
  Proof-layer dispatch (Option B) over proposition FORMULAS via the canonicalizer;
  never touches check_admissibility/_resolve_dep_units (proofs have no units).
  Disagreement rule = the select_self_verified twin: pool ALL admissible single-step
  MP derivations, require a unique canonical key == declared conclusion. Pooling (not
  filter-to-declared-first) is the soundness mechanism.
- generate/logic_canonical.py: parse_top_implication (+ _unparse) — recovers an
  implication's syntactic antecedent/consequent (the ROBDD form doesn't preserve it).
- Closed typed-reason set; the corpus's finer labels consolidate (6 disagreement
  refuse-labels -> conclusion_disagreement; 4 antecedent-flavor labels ->
  unestablished_antecedent — same redundancy, same mechanism-makes-one-distinction
  principle).
- Honesty boundary (exact scope): guarantees a unique conclusion among SINGLE-STEP MP
  over the premises, NOT "uniquely entailed" by all strategies.

Cross-check: all 24 GPT-5.5 adversarial corpus cases agree on OUTCOME against the real
rule (no rule bug / no corpus outcome-misread); reasons consolidate as above.
Mutation: filter-to-declared-first makes DISAGREE-007/010 wrongly admit -> pooling
tests fail (pooling load-bearing).

Drive-by fix (cleanup-as-you-find): merged ADR-0204 ProofNode.__post_init__ was
dedented to module level -> all ProofNode validation was silently DEAD (smoke skips
the dedicated test file; the smoke != full-suite hazard). Re-indented; validation
restored.

Additive (math lane untouched). Full binding-graph surface green; smoke 67.
2026-06-02 20:56:57 -07:00
Shay
0850e6fde7
Merge pull request #527 from AssetOverflow/feat/adr-0204-proof-builder
proof_chain 2.2: proof-graph builder (ADR-0204)
2026-06-02 20:22:34 -07:00
Shay
4cae904563 feat: proof-graph builder — proof_chain's first binding-graph consumer (ADR-0204)
Phase 2.2, structure only (no inference rule — modus_ponens is 2.3). Translates a
Proof into a SemanticSymbolicBindingGraph; the ADR-0203 acyclicity guard + ADR-0132
referential integrity fire at construction.

- generate/proof_chain/model.py: the one canonical proof input shape (ProofNode/Proof
  + proof_from_premises desugaring of the corpus premises/conclusion shape).
- generate/proof_chain/builder.py: build_proof_graph — node→symbol+equation;
  canonical_key→rhs_canonical, depends_on→dependencies, rule→operation_kind;
  premises = empty-deps/op="premise"; unit_proof=PROOF_NO_UNIT, admissibility="pending";
  conclusion tracked as conclusion_symbol_id.
- tests: 9 — valid DAG (PC-MP-001 desugared) + multistep construct; PC-CYCLE-001
  refuses THROUGH the real builder (circular_dependency); canonical_key round-trips
  byte-identical + equivalent formulas share rhs_canonical; admissibility-dispatch
  confirmation; self/dangling refusals; out-of-regime node refuses. Mutation-verified
  (drop dep-wiring -> cycle admitted -> test fails).

Admissibility dispatch confirmed graceful on proof operation_kinds: unknown kinds
-> AdmissibilityError(unknown_operation), unitless deps -> unit_unbound; NEVER
misroutes into _check_additive. Named 2.3 constraint: check_admissibility runs
_resolve_dep_units before dispatch, so modus_ponens must bypass unit-resolution.

Open items named for 2.3 (ADR-0204): conclusion typing (BoundUnknown revisit),
semantic_role="unknown" (closed vocab has no "proposition"), unit_proof sentinel.

Additive (first consumer; math lane untouched). Full binding-graph surface green;
smoke 67. Honesty boundary: through 2.3, sound over declared atoms, not grounded in input.
2026-06-02 19:53:41 -07:00
Shay
15307ca1f3 Add proof-chain corpus fixtures 2026-06-02 19:26:46 -07:00
Shay
69a7d8bae8 feat: principled out-of-regime detector — typed out_of_decidable_regime (ADR-0201.1)
GPT-5.5's independent corpus caught that the canonicalizer refused quantified/
predicate input only by accident (tokenizer chokes on '.'), not by design — a
by-luck-not-by-design refusal the wrong=0 discipline rejects. ADR-0202 §3 names a
typed `out_of_decidable_regime` refusal; the keystone emitted a generic grammar error.

- logic_canonical.py: LogicRegimeError(LogicError) + OUT_OF_DECIDABLE_REGIME;
  _reject_out_of_regime_text (quantifier words forall/exists + symbols ∀/∃, pre-scan)
  and _reject_out_of_regime_tokens (predicate-application ATOM-then-LPAREN), run BEFORE
  the generic grammar error. Refusal only — no predicate/FOL capability added.
- logic_equivalence.py: typed regime branch (before the generic LogicError branch).
- tests: 43 total (10 new) — OOR refuses with typed reason; equivalence path too;
  genuine grammar errors stay plain LogicError (no over-fire); `not (P)` not mistaken
  for predicate application. Mutation-verified by-design (neuter -> falls through to
  generic grammar error).
- ADR-0201.1: additive sub-ADR of 0201 (not an amendment; sub-number preserves the
  landed ADR-0203 forward refs + phase-2 plan numbering). Honesty boundary load-bearing.

Corpus now 22/22 (PC-OOR-001/002 agree on the principled reason). Full canonicalizer
suite green; smoke 67 passed. modus_ponens rule-reasons remain deferred to ADR-0205 (2.3).
2026-06-02 19:12:41 -07:00
Shay
451c4b1e17 feat: binding-graph acyclicity invariant — circular_dependency guard (ADR-0203)
proof_chain phase 2.1: the acyclicity guard at the shared binding-graph
construction boundary, before phase 2.2 wiring can build a cyclic-capable structure.

- generate/binding_graph/acyclicity.py: pure find_cycle(adjacency) detector
  (deterministic three-colour DFS; isolated, no model import).
- model.py __post_init__: builds {lhs: deps} adjacency over equations and raises
  BindingGraphError(circular_dependency ...) on a cycle. Runs on every binding
  graph (math + future proof) — illegal states unrepresentable for all consumers.
- tests/test_binding_graph_acyclicity.py: 17 tests (pure checker + construction
  enforcement); mutation-verified non-vacuous.
- ADR-0203: new ADDITIVE invariant referencing ADR-0132 (not an amendment —
  preserves the why-added-later history).

Math-lane regression proof: the only producer (math adapter) is acyclic by
construction (fresh result symbol per op, deps point backward); full
binding-graph + admissibility surface 392 green; guard refuses no existing graph.

Honesty boundary (load-bearing): through phase 2.3, proof_chain is SOUND OVER
DECLARED ATOMS, not grounded in recognized input (grounding is phase 2.4).

full binding-graph/admissibility surface: 392 passed. smoke: 67 passed.
2026-06-02 18:42:40 -07:00
Shay
e8e0fbb014 feat: propositional canonicalizer keystone + representation contract (ADR-0201/0202)
The proof_chain keystone: a hand-rolled ROBDD canonicalizer mirroring
math_symbolic_equivalence one domain over (normalize -> canonical key ->
byte-equality -> three-valued verdict; REFUSED preserves wrong=0).

- generate/logic_canonical.py: formula -> ROBDD identity under sorted-atom
  ordering; LogicError/LogicBudgetError refusals; inspectable canonical key.
- generate/logic_equivalence.py: EQUIVALENT/NOT_EQUIVALENT/REFUSED wrapper.
- tests/test_logic_canonical.py: 33 standalone tests (canonicity laws,
  discrimination, terminals, determinism, refusals); mutation-verified non-vacuous.
- ADR-0201: canonicalizer decision (ROBDD not CNF/DNF; hand-rolled;
  propositional-only honesty boundary).
- ADR-0202: proposition representation contract — single source the canonicalizer
  and the proof corpus conform to (formula grammar + atom layer binding to ADR-0144
  EpistemicNode + honesty boundary).

Additive: no existing file touched, zero consumers. Standalone keystone only;
binding-graph wiring, acyclicity refusal, and inference rules deferred. smoke: 67 passed.
2026-06-02 16:24:32 -07:00
Shay
b2d1125743 Add Brain Corp technical brief
1-page exec + backing brief for a first technical conversation, written to
survive a skeptical CTO. Every number/status sourced to docs/claims_ledger.md;
substrate-beneath-BrainOS framing held (not perception/motor); verify block is
fresh-clone-green. Prepared for internal review — not for distribution.
2026-06-02 12:07:32 -07:00
Shay
f3680aa302 reconcile amr demo wording with claims ledger 2026-06-02 10:38:00 -07:00
Shay
99c94f71f0 add amr decision substrate demo 2026-06-02 10:38:00 -07:00
Shay
2d18976fa4 docs(claims): ADR-0200 reconciliation — expert claim to audit-passed truth
Reconcile every artifact that asserted the (since auto-reverted) mathematics_logic
expert promotion to the live machine state. Determinism proven intact (Week-1a):
the digest divergence is genuine single-source evidence-drift (GSM8K coverage probe
3/47 -> 4/46 via #310/#488), not a non-determinism defect. ADR-0120's fail-closed
property fired as designed; CORE revoked its own expert claim.

History keeps receipts; current-state reconciles to truth:
- Regenerate expert_claims_math_v1_signed.json -> promote_admitted:false,
  reviewer_signature_matches:false, digest 02f6d3c8.
- reviewers.yaml math_expert_claims: quarantine note; entry kept (mismatch-refusal
  keeps firing); intentionally NOT re-signed.
- ADR-0120-math-expert-ledger-flip: dated valid-at/auto-reverted header note.
- README: "next gate" narrative -> built-attempted-reverted; refresh stale count.
- docs/decisions/README: revert note + ADR-0200 index row.
- 3 fail-closed tests (2 files): "is-expert" -> fail-closed-revert assertions.
  Were RED on main; now green (30 passed).

No eval gate, threshold, or safety boundary changed.
2026-06-02 10:06:16 -07:00
Shay
96b6c5e4b2 docs(claims): ADR-0200 + claims ledger — single source of truth (additive)
Add docs/claims_ledger.md (every public claim -> in-repo evidence, with the
four GSM8K numbers separated and labeled) and ADR-0200 recording the
mathematics_logic expert fail-closed revert as designed behavior (proven
single-source evidence-drift; determinism intact).

Additive only: no existing claim, eval gate, or test is touched. The
review-gated reconciliation diffs (reviewers.yaml quarantine note, ADR-0120
header note, signed-JSON regen, README narrative, 3 test reconciliations) are
listed in ADR-0200 section 4 and await operator ratification.
2026-06-02 09:35:44 -07:00
Shay
ab9e1afe04 docs(adr): backfill ADR index — add 0184-0195 + 0197-0199 (12 missing rows)
The decisions README index table stopped at ADR-0183 then jumped to
ADR-0196, omitting every top-level ADR that landed in between plus the
three newest. PRs #513/#514/#515 added ADR-0197/0198/0199 files without
touching the index; the 0184-0195 gap predates them.

Adds 12 rows in numeric order with title + status pulled from each ADR
header. No content/runtime change; pure index backfill.

- files-vs-index drift check: now empty (was 12)
- all 12 new link targets verified to resolve
2026-06-01 12:14:44 -07:00
Shay
1d12c3b01e
docs(adr): ADR-0199 cross-domain learning arena contract (#515) 2026-05-31 20:36:56 -07:00
Shay
918eb5552d
docs(adr): ADR-0198 motor efferent decoder spike (#514) 2026-05-31 20:32:26 -07:00
Shay
81062bb0fb
ADR-0197: vision compiler over Delta-CRDT (docs only) (#513) 2026-05-31 20:32:08 -07:00
Shay
77feadaab1
Merge pull request #511 from AssetOverflow/feat/adr-0180-crdt-contract-lock 2026-05-31 20:30:26 -07:00
Shay
497d1a9a22
Merge pull request #510 from AssetOverflow/feat/lang-foundation-reland 2026-05-31 20:30:00 -07:00
Shay
3fba044e51 docs(zig): add STATUS.md handoff page (current state, next action, gotchas)
Single portable 'where we are / what's next' page for the Zig native-substrate
work: gate status per component, the locked G1 CRDT contract, the immediate
next action (a new ADR to clear G2 before any Zig code), env gotchas
(PYO3_PYTHON=3.12; the public_demo wall-clock lane flake), and verification
commands. Lets any operator/agent resume cold.

Sibling links resolve once #509 (docs/zig/**) lands on main; merge #509 first.
2026-05-31 16:30:44 -07:00
Shay
92ea9ee6f5 feat(vault): lock Delta-CRDT reference contract (ADR-0180 -> Accepted, gate G1)
Establishes the canonical Delta-CRDT reference contract so a future native
(Rust/Zig) backend is gate-G1-eligible under ADR-0196 — the ZC-0 'contract
pinning' slice. No Zig code; ZC-1+ remains gated at G2.

- vault/crdt.py: canonical Python reference (ArenaEntry, Delta, LocalArena,
  merge_kernel, canonical_bytes, delta_hash). Pure content law — content-
  addressed by IEEE-754 bits then provenance; no normalization, no versor
  closure, no global Vault writes.
- ZC-0 contract tests (semilattice C-1..C-5; content ordering / signed-zero /
  NaN bit-addressing; C-7 no-global-write) — all failable (mutation-checked:
  no-dedup breaks C3/C5, arrival-order breaks C1).
- Golden fixture corpus (tests/fixtures/crdt/) regenerated deterministically
  from the reference; single source of truth also emits the Rust expected hex.
- core-rs: Delta::canonical_bytes + test_crdt_hash_parity.rs proving Rust
  produces byte-identical canonical_bytes to the Python reference.
- ADR-0180 -> Accepted: locked contract, byte layout, obligation map, and the
  explicit boundary that no Zig is authorized.

Verification: ZC-0 21 passed, Rust arena+parity 16 passed, architectural
invariants 40 passed, smoke 67 passed. Serving frozen: 7/8 lane SHAs match;
the public_demo miss is a pre-existing wall-clock budget overrun (ADR-0099,
~46-48s > 30s) reproduced identically on clean main — environmental.
2026-05-31 16:25:21 -07:00
Shay
18a679c29d feat(packs): reland en_core_syntax_v1 foundation vocabulary (collision-audited)
First foundation-curriculum substrate pack: 24 reviewed noun lemmas for
syntax/claim/provenance vocabulary (subject, predicate, agent_role,
clause, antecedent, consequent_role, polarity, negation, evidence_span,
…).  Substrate only — no parser, no runtime generation change.

This is the clean reland of #503 (merged then reverted via #508 for
shipping two failing tests).  Root cause of the revert was lemma
collision: the smoke CI gate does not collect dedicated test files, so
the pack merged green while its own test asserted resolver routings that
were false.

Reland fixes, with the full collision audit done against every on-disk
pack (not just the one the original author checked):

- agent      -> agent_role        (bare `agent` owned by en_core_meta_v1)
- comparison -> comparison_relation(bare `comparison` owned by en_core_cognition_v1)
- consequent -> consequent_role   (bare `consequent` owned by en_core_causation_v1)
- negation   kept bare on purpose: no *mounted* pack owned it
  (en_mathematics_logic_v1 is a domain pack, not in
  DEFAULT_RESOLVABLE_PACK_IDS), so mounting syntax now grounds a word
  that previously returned None.  Renaming would have lost grounding.

The original test also mis-asserted prior resolution: it claimed
`cause` -> en_core_causation_v1, but first-match-wins resolves it to
en_core_cognition_v1 (mounted at index 0).  The test now pins the TRUE
current owner; this pack does not change it.

Resolver: en_core_syntax_v1 mounted after en_core_polarity_v1 and before
en_core_relations_v1 — purely additive, steals no prior resolution.

Evidence:
- tests/test_en_core_syntax_v1_pack.py: 13/13 (was 4 failed, 9 passed)
- pack/resolver/grounding/invariants blast radius: 415 passed
- core test --suite smoke: 67 passed
- core test --suite packs: 1 failed, 140 passed — the single failure
  (test_lilibeth_canary_solves_end_to_end, GSM8K candidate-graph reader)
  is PRE-EXISTING on clean main f79b647, byte-identical, and untouched by
  this PR.
- lane SHAs: 7/8 content-match; the public_demo miss is a wall-clock
  DemoContractError (>30s budget), not content drift — serving frozen.

PR checklist:
- Capability: foundation-curriculum language substrate vocabulary.
- Field invariant: pack loads through checksum-sealed compiler; no
  algebra/versor path touched.
- Lane: core test --suite packs / smoke; dedicated pack test.
- No hidden normalization, stochastic fallback, approximate recall, or
  unreviewed mutation.
- Trust boundary: language-pack loading only; manifest checksums hash the
  exact bytes on disk (recomputed after the two renames).
2026-05-31 16:18:26 -07:00
Shay
9ead270fda docs: ratify Zig native-substrate doctrine (ADR-0196)
Bring the docs/zig/** decision package and README 'Native Substrate
Direction' section into main, and record ADR-0196 (Accepted) as the
binding ratification.

The doctrine is explicitly NOT a wholesale Zig rewrite. It establishes a
ring architecture (Python = semantic source of truth; Rust = incumbent
algebra backend; Zig = Ring 1 native-substrate candidate only) and the
G0-G8 adoption gate ladder. Zig may enter only by clearing gates against
a locked reference contract; default-by-availability is forbidden.

ADR-0196 forward-references ADR-0180 as the first G1 instantiation (the
CRDT contract lock / ZC-0 slice). No Zig code is authorized.
2026-05-31 15:13:19 -07:00
Shay
5c75853a0b Revert "Merge pull request #503 from AssetOverflow/feat/en-core-syntax-relations-v1"
This reverts commit 2405e9b06e, reversing
changes made to 95bf0dfa60.
2026-05-31 09:00:15 -07:00
Shay
69b89df606
Merge pull request #495 from AssetOverflow/feat/adr-0175-propose-step
feat(adr-0175): wire the PROPOSE step — autonomous attempt-and-eliminate loop closes
2026-05-31 08:37:23 -07:00
Shay
2b299c1090
Merge pull request #501 from AssetOverflow/docs/foundation-curriculum-roadmap
docs(curriculum): foundation curriculum roadmap
2026-05-31 08:37:20 -07:00
Shay
2405e9b06e
Merge pull request #503 from AssetOverflow/feat/en-core-syntax-relations-v1
feat(language): add en_core_syntax_v1 foundation pack
2026-05-31 08:35:30 -07:00
Shay
95bf0dfa60 docs(handoff): next-subjects readiness brief for ChatGPT (GitHub-connector lane)
Execution-free brief for the read-only GitHub-connector lane: comprehension-
primitive inventory, question-layer gap survey, subject-readiness recommendation,
then gated capability-axis/ADR/corpus drafts. Proposal-only; serving stays frozen
(wrong=0, pinned lanes). Companion to the Claude execute/validate/commit lane.
2026-05-31 08:19:12 -07:00
Shay
f0c51b002c docs(curriculum): note syntax consequent role collision boundary 2026-05-31 03:58:41 -07:00
Shay
74570757df docs(curriculum): document en core syntax pack 2026-05-31 03:52:24 -07:00
Shay
f8d9a36eeb docs(curriculum): add foundation curriculum tracker 2026-05-30 18:35:47 -07:00
Shay
e74a51f5db docs(curriculum): add foundation curriculum roadmap 2026-05-30 18:35:13 -07:00
Shay
9df1e6522b
feat(adr-0195): GSM8K product promotion bridge — serving 4/46/0 → 6/44/0, wrong=0 (#500)
Narrow product promotion boundary (`generate/derivation/product_bridge.py`)
wired into `generate/math_candidate_graph.py`: only complete pure-product
derivations with a product-target question and no known hazard surface lift
from the sealed pooled derivation reader into serving.

- Serving train_sample: 4/46/0 → 6/44/0, wrong=0; case 0050 still refused.
- Renumbered from the collided ADR-0194 (labeled-container, #499) to ADR-0195
  and rebased onto current main.

CI: smoke + verify-pinned-lane-SHAs green on the merge commit.
2026-05-30 17:33:56 -07:00
Shay
84db129629
feat(adr-0194): labeled-container subject entity shape — 'Jar A has N' parses, wrong=0-proven (substrate) (#499)
GSM8K labels containers/regions with a trailing single-letter or short-numeric
label ('Jar A has 28 marbles', 'Section G has 10 cars', 'District 2 has 19
voters'); the initial-possession entity slot captured only 'Jar' and the label
broke the match. Adds a separate sibling pattern _INITIAL_HAS_LABELED_RE
(mirroring ADR-0136.S.4 localisation) that REQUIRES the label, so the global
_ENTITY is unchanged and bare subjects yield no duplicate candidate.

- Composes with ADR-0193 aggregate question: 'Jar A has 28 marbles. Jar B has
  12 marbles. How many marbles are there in total?' -> 40.0.
- 0 real-corpus metric flip (honest substrate): the one real multi-container
  aggregate additionally needs comparative + multiplicative + lowercase-ref.
- wrong=0 HOLDS full corpus (7,473 q); train_sample byte-identical 4/46/0;
  synthetic-registry capability-axis gate + G5 lane green; smoke 67 passed.
- Label bounded by the possession verb: multi-word nouns ('Jar Apple') do NOT
  match. wrong=0 held downstream by completeness + round-trip + disagreement.

Co-authored-by: Claude Opus 4.8 <noreply@anthropic.com>
2026-05-30 16:56:09 -07:00
Shay
39bf549e94
feat(adr-0193): aggregate existential question frame — 'are there <cue>' composes, wrong=0-proven (#498)
Extends ADR-0131.G.5's total-across aggregate branch with the existential
verb frame 'How many <unit> are there <cue>?' over the SAME closed cue
vocabulary (no cue-set widening). The solver already sums entity=None
total-across; the wall was purely the question parser's verb-frame coverage.

- Composes end-to-end: 'Jamie has 28 marbles. Kyle has 12 marbles. How many
  marbles are there in total?' -> 40.0 (load-bearing, not inert).
- 23 real GSM8K problems now parse the question (advance past the Q-wall to
  the statement-parse wall).
- wrong=0 HOLDS on the full 7,473-q corpus; train_sample byte-identical
  4/46/0; no metric delta (composition-wall lesson, third instance).
- Cross-ADR discipline: 'What is the total number of <unit>?' is DEFERRED,
  not contradicted — ADR-0131.G.5 pins it as a refusal probe; promoting it
  must amend that ADR's closed-cue contract. test_total_number_of_still_deferred
  locks the boundary.

Firewall: completeness guard (ADR-0191) + question round-trip refuse conjoined
('dogs and cats') and derived ('animal legs') units. G5 lane + synthetic-registry
wrong=0 capability-axis gate green; smoke 67 passed.

Co-authored-by: Claude Opus 4.8 <noreply@anthropic.com>
2026-05-30 16:35:22 -07:00
Shay
a7024bb1f8
feat(adr-0192): open discrete_count noun class — 8x statements parse, wrong=0-proven (substrate) (#497)
The discrete_count matcher gated the counted noun on a CLOSED ratified set
(observed_counted_nouns): 'Betty has 24 marbles' matched, 'Randy has 60 mango
trees' / 'Sam has 12 red apples' did not — purely because the noun was unseen.

Open the single-anchor possession/acquisition path to an open noun phrase
(adjective* + 1-3 word head, bounded by a stop-word lookahead so it never
swallows a trailing PP), keeping every other narrowness layer (proper-noun
subject, verb whitelist, single numeric token, no clause-split). Closed
observed nouns still match (capitalized compounds preserved); compound
enumeration stays closed.

Safe because ADR-0191 moved the wrong=0 guarantee downstream: an open-vocab
mis-parse hits the completeness guard + round-trip + branch-disagreement.
Proof: full real corpus 61->494 discrete_count anchors (8x), wrong=0 HOLDS,
zero confabulations.

Substrate PR — 0 metric delta by design (train_sample byte-identical 4/46/0;
the problems still need composition downstream). Value: the foundation every
discrete_count flip consumes, and empirical proof open-vocab is firewall-safe.

Co-authored-by: Claude Opus 4.8 <noreply@anthropic.com>
2026-05-30 16:06:25 -07:00
Shay
25580e18b0
fix(adr-0191): candidate-graph completeness guard — real-corpus wrong 5→0 (#496)
* fix(adr-0191): candidate-graph completeness guard — real-corpus wrong 5->0

The candidate-graph reader (serving) checked grounding + round-trip but had
no completeness obligation, so problems whose later clauses failed to parse
emitted a partial reading. Over the full 7,473-question real GSM8K train
split this confabulated 5 answers (wrong!=0) the 47-case train_sample hid;
2 were regressions from #488.

Add the missing admissibility leg (mirrors the derivation reader's verify.py):
every source quantity (all statements + question) must be consumed by the
chosen reading, else refuse. Refusal-only -> cannot create a wrong answer.
Number-sense is pack-authoritative (en_numerics_v1 parse_compound_cardinal +
lookup_multiplier + all 6 currency symbols) so it never disagrees with the
engine; aggregating initials expose consumed_value_tokens provenance.

Evidence: real-corpus wrong 5->0, correct held at 4; train_sample byte-
identical 4/46/0; G1-G5+S1+G3.1 green; smoke 67 passed; math_teaching_corpus
lane byte-identical.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>

* feat(adr-0191): committed full-corpus GSM8K microscope (standing wrong=0 + coverage instrument)

Promotes the throwaway tmp/ microscope that found the 5 confabulations into a
committed tool. Runs the canonical serving reader over any GSM8K corpus and
reports failures-first: correct/wrong/refused, every wrong answer by name,
refusal families, and the no-injection per-category coverage map that ranks
which injector to build next by real frequency.

Default corpus is the committed 47-case train_sample (always available);
--corpus path runs the full real split. This is the ADR-0191 follow-up: re-run
after every capability PR, not just train_sample — a flip is only real if it
does not widen the confabulation surface.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>

---------

Co-authored-by: Claude Opus 4.8 <noreply@anthropic.com>
2026-05-30 15:45:07 -07:00
Shay
b82897a0dd feat(adr-0175): wire the PROPOSE step — autonomous loop closes (attempt->tether->ledger->propose)
The attempt/score/ledger half existed (run_practice -> ClassTally scored vs
gold); nothing consulted the gate to turn earned reliability into a ratifiable
proposal. Adds core/reliability_gate/propose.py (propose_from_ledger +
RatifiableProposal): for each class, license_for(PROPOSE) emits a proposal iff
its conservative Wilson floor (0 below N_MIN=10) clears theta=0.85. Refusals
never penalize; deterministic; PROPOSAL-ONLY (never a serving mutation).

propose_runner.py closes the loop end-to-end with an aggressive sealed scorer
(resolve_pooled): practice 95c/5w/50r -> ONE proposal (additive, reliability
0.8608>=0.85, 95/100); 5 wrongs tolerated but floor held; rest stayed sealed.
The gold-tethered autonomous contemplation: the engine earns the right to ASK,
not to SERVE. 11 failing-under-violation tests.
2026-05-30 13:50:24 -07:00
Shay
0770648257
feat(GSM8K): comprehension reading → first metric move 3/47/0 → 4/46/0 (#488)
* feat(adr-0189): comparative reading — anchor-verb widening + multi-word units

The candidate-graph comparative extractor (ADR-0131.G.2) read only has/have +
single-word units, so real-GSM8K comparatives ('Brooke does three times as many
jumping jacks as Sidney') didn't parse — a dark statement in 17 places blocking
15 of the 47 refused train_sample cases, despite the ADR-0123 solver already
supporting compare_additive/compare_multiplicative.

Widens the anchor-verb set (reusing legacy vetted lemmas + does/collected/
gained/studied…), EXCLUDING polarity-inverting verbs (lose/spend/give/sell/win)
to preserve wrong=0; admits 1-2 word units via the existing multi-word
_unit_grounds branch. Feeds the existing solver unchanged.

wrong=0 proven: G2_comparatives 29/29, G3 20/0, G4 32/32, train_sample 3/47/0
byte-identical; polarity-inverting verbs proven refused (failing-under-violation).
Chain composes correctly in isolation (146 -> 438). Flips 0 cases ALONE — every
comparative case needs a composing partner (aggregation / multi-word-noun
injection); this ships the component, not yet a flip.

- generate/math_candidate_parser.py: _comparison_anchor_verb widening + 1-2 word
  unit slots in the two multiplicative comparative regexes.
- tests/test_adr_0131_G2a_*: 5 tests incl. polarity-inversion wrong=0 guards.
- docs/decisions/ADR-0189: gap, change, wrong=0 evidence, honest scope.

* feat(adr-0189a): first metric move 3/47/0 -> 4/46/0 (case 0024, comprehension-composed)

Case 0024 now SOLVES (answer 438) by composing three general comprehension
capabilities feeding the unchanged ADR-0123 solver:
  1. day-of-week count enumeration: Sidney = 20+36+40+50 = 146
     (_day_enumeration_candidates; derived sum grounds via first count token,
      mirroring _embedded_quantifier; closed to the 7 day names)
  2. comparative reading (ADR-0189): Brooke = 3 x Sidney
  3. activity question 'How many <unit> did <Entity> <verb>?' (_Q_DID_RE)
Plus do/does/did added to the CandidateInitial anchor whitelist (production-
possession), admitted only via the closed day-enumeration shape.

wrong=0 PROVEN across every lane: all 8 capability axes wrong=0 (G2_comparatives
29/29, G3 20/0, G4 32/32, G5/S1/S3/S4 all pass), train_sample 4/46/0 wrong=0,
verify_lane_shas exit 0 (no pinned lane changed), generate_claims --check OK.
872 tests pass; new tests are failing-under-violation incl. wrong=0 guards
(non-day comma list not summed; polarity-inverting comparative verbs refused).

Re-baselined report.json + train_sample_coverage_report.json (latter also clears
pre-existing reason drift) + CLAIMS.md to the new 4/46/0 metric. Decode-not-guess:
0024 solved by READING its structure, not storing an answer. Remaining pre-existing
failures (G3 committed-report, telemetry) unrelated, fail on pristine main.

- generate/math_candidate_parser.py: day-enum extractor + _Q_DID_RE + does-anchor.
- tests/test_adr_0189a_day_enum_activity.py: 5 tests (incl. end-to-end 0024=438).
- docs/decisions/ADR-0189a + report.json/coverage/CLAIMS re-baseline.
2026-05-30 09:21:48 -07:00
Shay
390b6f376d
docs: semantic-state transition blueprint and ADR-0184 scope (#489)
* docs: add semantic state transition blueprint

* docs: add ADR-0184 semantic state transitions

* docs: add RB-GSM solver design input notes
2026-05-30 08:35:50 -07:00
Shay
171b1cd7a5
feat(adr-0186): sealed candidate-graph injector lane + topology correction (#487)
* docs(adr-0186): sealed candidate-graph injector lane (resume ADR-0170 W2-W5 under ADR-0175 seal)

Topology audit found two disjoint GSM8K readers: the candidate-graph reader
owns the official 3/47/0 metric and already has divide/multiply/compare; its
wall is the recognizer->injection coverage gap (ADR-0170 W2-W5 backlog), not
arithmetic. The derivation reader (resolve_pooled) is a separate sealed organ
that cannot reach the goal without an unbuilt Phase-5 bridge.

ADR-0186 reconciles ADR-0170's injector roadmap with ADR-0175's serving seal:
develop W2-W5 injectors behind a default-off 'sealed' flag on inject_from_match,
measured on a new report_sealed.json, with frozen 3/47/0 byte-identical until a
reviewed Phase-5 promotion. wrong=0 gated on both paths.

Live-loop instrumentation found a schema-vs-extraction split: rate_with_currency
and temporal_aggregation matchers already extract full anchors (blocked on the
CandidateRate union / apply_rate primitive), while discrete_count/currency/
multiplicative are blocked on matcher extraction. And no refused case is one
injector away - every case is multi-statement, so the unit of measurable
progress is a target case's complete injector+composition set. Sequencing:
seal mechanism first, CandidateRate schema next, then a first complete
target-case unlock.

* feat(adr-0186): sealed candidate-graph injector lane mechanism (default-off)

Adds the seal mechanism for developing ADR-0170 W2-W5 injectors without
mutating the frozen serving metric:

- inject_from_match(match, sentence, *, sealed=False): when sealed=True,
  consults the new _SEALED_INJECTORS table first; default-off never touches it.
- _SEALED_INJECTORS: empty at land (this PR ships the mechanism; the first
  sealed capability is the CandidateRate schema, ADR-0186 §5.3).
- parse_and_solve(text, *, sealed=False): threads the flag to the per-statement
  injection site. The seal is injector eligibility, not a forked reader.

wrong=0 guarantees (tests/test_adr_0186_sealed_injector_lane.py, failing-
under-violation): empty seal is a strict no-op; a registered sealed injector
admits ONLY under sealed=True and is invisible to the frozen path; train_sample
report stays 3/47/0. Verified: coverage probe 3/47/0 byte-identical, smoke +
architectural invariants green, 288 candidate-graph/recognizer tests pass (2
pre-existing failures unrelated, confirmed on unmodified main).

* docs(adr-0185): mark superseded by ADR-0186 (premise refuted by topology audit)

The topology audit proved ADR-0185's premise ('the engine cannot divide') is
true only of the derivation reader, which is disjoint from the candidate-graph
reader that owns the official 3/47/0 metric. The goal organ already divides;
its wall is injection coverage. ADR-0185 is retained as a record, not
implemented; cross-referenced from ADR-0186 §header.
2026-05-30 08:35:43 -07:00
Shay
e195a229c9
feat(adr-0184): distinct-unit product rule — sealed reader wrong 13→8 (#486)
* docs(adr-0184): scope the distinct-unit product rule — cut the product-of-all over-commit

The 47-refusal coverage diagnostic surfaced that the headline 3/47/0 (serving
recognizer) hides the sealed comprehension reader's real state: resolve_pooled over
the 50 real train_sample cases is 2 correct / 13 WRONG / 35 refused. The confuser
probe's wrong=0 was a misleading proxy — all 13 real wrongs are the whole-text
product-of-all, the unique complete candidate, committed unopposed.

Scopes the first lever, decided by MEASURING candidate refusal rules against the real
metric (correct up, wrong down on train_sample):

  baseline                         2 / 13 / 35
  distinct-unit product (chosen)   2 /  8 / 40   <- cuts 5, zero coverage loss
  product spans >1 clause          1 /  4 / 45   <- destroys correct 0003
  drop all products                0 /  2 / 48

The distinct-unit rule: multiply/divide may compose DISTINCT units but a multiply
step whose operand repeats a non-empty unit already in the product (apples x apples,
cards x cards) is unit-incoherence -> refuse (unit^2 is never the answer). Empty-unit
operands exempt (0003 multiplies a blank-unit 0.75). Dimensional, not lexical
(ADR-0165-safe); refines verify.py clause 3 shared by self_verifies + classify.

Honest scope: 13->8, NOT 0. The remaining 8 are distinct-unit products in the wrong
shape (rate problems) = cue precision (ADR-0177 CP-2b), the next lever, NOT to be
faked with a per-case rule. Establishes the real scoreboard (resolve_pooled over
train_sample) and notes the ratification bridge (ADR-0175 Phase 5) as the separate
dependency for any of this to reach the serving headline.

Spec only; serving 3/47/0 untouched (verify is not on the serving path).

* feat(adr-0184): distinct-unit product rule — sealed reader real-GSM8K wrong 13->8

Cuts the over-eager product-of-all on real GSM8K. The sealed comprehension reader
(resolve_pooled over train_sample) was 2 correct / 13 WRONG / 35 refused; all 13 are
the whole-text product-of-all committed unopposed (0042->2.4M, 0048->19200,
0001->14400). This is the first lever measured against the REAL metric (resolve_pooled
over train_sample), not the curated confuser count.

Mechanism (verify._is_repeated_unit_product + classify_derivation downgrade):
a pure multiplicative chain whose operands repeat a non-empty unit forms unit^2
(apples x apples, cards x cards) -- never the answer; it is the product-of-all
multiplying independent groups. Such a product is classified `exempt`
(commit-INELIGIBLE), NOT removed. Empty units exempt (0003 multiplies blank-unit
0.75); divide exempt (feet/feet = legitimate count). Dimensional, not lexical
(ADR-0165-safe).

Implementation finding (folded into ADR §3.1): the naive version put the predicate
in the shared _base_reasons gate, which DROPPED the product and regressed the
confuser probe 1->3 -- the disguised-polarity 0001/0003 refuse only because the
coins x coins product DISAGREES with the coins + coins accumulation reading; dropping
it unmasked the additive reading as a unique wrong commit (80/30). The fix is the
downgrade: keep it as a commit-ineligible `exempt` candidate so it still forces the
disagreement. Pinned by test_downgrade_not_removal_preserves_disagreement_refusal.

Evidence (sealed lane; chat/ does not import verify -> serving frozen):
- resolve_pooled over train_sample: 2 correct / 8 wrong / 40 refused (was 2/13/35);
  the 5 repeated-unit products (0001/0017/0042/0045/0048) now refuse, 0003/0021 kept.
- confuser probe: wrong unchanged (no 0001/0003 regression), positives still solve.
- serving train_sample 3/47/0 and practice (accumulation + search) 3/47/0
  byte-identical; self_verifies/_base_reasons unchanged so search lanes are untouched.
- 171 derivation/pool/verify tests + 40 architectural invariants green.

Honest scope: 13->8, NOT 0. The remaining 8 (0011/0016/0018/0019/0025/0028/0032/0047)
are distinct-unit products in the wrong shape (rate problems) = cue precision
(ADR-0177 CP-2b), the next lever -- not to be faked with a per-case rule. Carries the
corrected ADR-0184 (supersedes the spec-only #484).
2026-05-30 08:35:35 -07:00
Shay
4e36abff6e docs: add edge sync completion status 2026-05-29 19:50:44 -07:00
Shay
c20842c3f3 docs: add edge sync implementation brief 2026-05-29 18:56:50 -07:00
Shay
76fe5be379 docs: add edge sync artifact contract 2026-05-29 18:52:54 -07:00
Shay
c654b3f22d docs: add edge S3 persistence architecture 2026-05-29 18:50:11 -07:00
Shay
6ed8fc21fc
docs(adr-0182): realized results + status Accepted/Implemented (lookback amendment) (#483)
The lookback review of the four-PR stack (EX-6/pooling/prior-state/anchor-skip)
found the ADR-0182 spec under-predicted and under-scoped 0016. Records actuals
without editing the original spec (retained for provenance):

- Status -> Accepted/Implemented (PRs #476, #480, #481).
- §8 Realized results: confuser wrong spec-predicted 5->4->3, ACTUAL 5->2->1->0.
  Pooling also caught disguised-polarity (bonus); 0016 needed anchor-skip PLUS
  intra-clause accumulation (a conjunction split the spec framed as anchor-skip
  alone) and yielded the bonus 0017 *solve*; the prior-state guard (#480) is a
  distinct question-time lever sharing resolve_pooled.
- Folds in the lookback findings: solid items, the closed test-coverage gap
  (anchor-skip refuse branches, #481 4205605), no live wrong=0 hazard (multi-actor
  product-commit predates anchor-skip), and the open 0010 multi-referent spurious
  (a graduation question, not a wrong).

Serving 3/47/0 byte-identical throughout. Doc only.
2026-05-29 14:50:22 -07:00
Shay
4dd824f4f6 docs(adr-0055): status reflects Phase C shipped (0056/0057), D–E landed; add cross-refs 2026-05-29 14:32:53 -07:00
Shay
84570a9c7d
docs: refresh ADR README narrative (current frontier, chain notes, session logs) (#482)
* docs: refresh ADR README narrative (current frontier, chain notes, session logs)

* docs: drop stray historical marker on refreshed Proposed list
2026-05-29 14:27:17 -07:00
Shay
ac7bda019b docs: refresh ADR index — all 229 ADRs (was 51)
Regenerated the docs/decisions/README.md ## Index table from each ADR's own
title + Status line, naturally sorted by ADR id (handles 0114a, 0119.1,
0131.G.3.1, 0136.S2, etc.). The index had drifted to 51 of 229 ADRs; it now
lists every ADR through 0183. Only the Index table was replaced; the Current
frontier / chain notes / reasoning-capable-domains / session-log narrative is
untouched (it remains a curated, historically-scoped account, not the index).
2026-05-29 14:08:34 -07:00
Shay
83de943cdd docs(adr-0183): stub ADR for the lawful audio→lexeme path
Records the fork for getting words from audio WITHOUT a serving-time learned
model: (A) words-as-text, or (B) deterministic formant/phonetic decode + taught
vocabulary. Status: Proposed (stub) — deferred, not a committed design. Captures
the problem, the 0-param/decode-not-borrow/refuse-over-fabricate/reviewed-growth
constraints, and the open questions a full ADR must answer. Exists so the
serving path doesn't silently reach for Whisper. Cross-linked from
docs/audio_pipeline_overview.md §9.
2026-05-29 14:02:40 -07:00
Shay
a58571d410 docs(audio): record teacher=scaffolding / serving-path-stays-Whisper-free boundary
Adds §9 subsection: a teacher is bootstrap scaffolding for the teaching phase,
not a production component (not ML distillation — CORE has no weights). Serving
path must never call a teacher. Production is Whisper-free conditioned on a
lawful runtime path: (A) words-as-text, or (B) matured deterministic
audio→lexeme decode. Flags the trap: teaching with a model does not auto-transfer
word-recognition into a 0-param engine. 'The teacher teaches; the lawful path
serves.'
2026-05-29 13:59:43 -07:00
Shay
c7290f5ab9 docs: start running model & dependency size tally
Living ledger of architecture/model/dependency footprint. Headline: CORE is a
0-parameter, 0-weight architecture (substrate is algebra, not weights), enforced
by the teacher versor-invariance test. Tracks: learned params (0), optional
teacher lanes (4 declared, all inert, no model size chosen), 10 Python runtime
deps (datasets dominates), 8 Rust crates, 0 weight files. Includes a Whisper
size reference for when/if a lane is wired, and an update-on-PR + changelog
discipline. Lives at docs/model_dependency_size_tally.md.
2026-05-29 13:51:30 -07:00
Shay
ae48a3cbf9 docs: audio section pipeline overview & primer
A from-the-ground-up reference for the audio modality: waveform → canonicalize
→ frames → acoustic lexer → typed AudioIR → operators/rotors → (32,) versor,
with every spec/constant grounded in the code (PR-2..PR-6 stack).

Includes the three-way clarification of learned models: embeddings (never),
audio specs (CORE's own DSP, not any model), text transcript (Whisper/NeMo as
typed labels only). Documents the substrate-vs-evidence split, the verbatim
teacher policy, current inert/gated status, and the 'scrutinise the consumer'
flag. Cross-links ADR-0180/0181 + spec + eval-plan. Lives at
docs/audio_pipeline_overview.md.
2026-05-29 13:47:31 -07:00
Shay
47a406b590
docs(adr-0163-f2): clarify refuse is maturity-relative — confusers are solvable coverage targets that graduate (#478)
A confuser's `expected: refuse` does not mean unanswerable. Every confuser carries
its true gold (`answer_numeric`) and is a solvable coverage target; `refuse` means
"the reader can't yet comprehend this category, so refusing is the honest outcome —
committing a WRONG value is the defect." Example: 0001 "buys a toy for 30 coins …
how many left?" is plain 50-30=20; it is refuse only because today's reader takes
`buys` as a gain.

Adds §2.1 (graduation protocol): when a general mechanism reads a category correctly
(validated on train_sample + the category, wrong=0 preserved), those cases graduate
refuse -> solve and committing their gold becomes a win. Reframes the `spurious`
verdict as "solved-before-graduation" (a graduation signal, with pair-consistency as
the genuine-reading-vs-surface-match discriminator), not automatically a defect.
Notes that no v1 category is degenerate, and how a truly-unanswerable case would be
labelled (answer_numeric: null + degenerate: true) so the two senses of "refuse"
stay distinguishable.

Spec only; no corpus/runner change (today's commits are wrong-reading, so spurious
stays flagged until a category genuinely graduates).
2026-05-29 13:23:02 -07:00
Shay
a8f9e3685d
docs(adr-0182): scope cross-composer disagreement pooling for distractor refusal (#474)
The confuser probe's two distractor-quantity wrongs (0014 ->300, 0016 ->3840)
have no clean tight fix: the `for` cue licenses both the 0014 distractor product
and the correct train-0021 product, and a target+foreign-unit refusal rule breaks
the canonical train-0003 boxes x erasers product. Telling a real multiplier from a
distractor by cue is the cue-precision problem ADR-0177 measured as not-yet-solvable
-- a tight rule here would be a reactive surface patch (the overfitting trap).

This ADR scopes the general, non-reactive alternative: let the wrong=0 DISAGREEMENT
rule do the refusing. Pool self-verifying candidates across composers so a blunt
product reading and a competing additive reading of the same problem disagree ->
refuse; legitimate products (0021/0003) have no competing reading, so they still
commit -- the structural property that distinguishes them, expressed without a cue.

Scoping surfaced two things a one-line plan would have missed:
- Completeness FORCES the distractor into every reading, so naive pooling changes
  nothing. The mechanism needs a narrow, commit-INELIGIBLE completeness exemption
  for isolated-foreign quantities -- it can only buy a refusal, never an answer, so
  the commit-path completeness guarantee (ADR-0175's 9->2 multi-step fix) is intact.
- MS-1 Target exposes the union of body unit-shapes, NOT the question's asked-for
  unit (verified). The exemption is therefore keyed to a reading's used-operand
  units, not an asked unit that does not exist.
- 0016's distractor sits in the anchor-position clause, so it needs distractor-aware
  anchor selection too: 0014 is the guaranteed win (wrong 5->4); 0016 lands (->3)
  only when anchor-skip is built. Doc declines to claim both before that is proven.

Spec only, no code. Sealed lane; serving 3/47/0 untouched.
2026-05-29 13:21:36 -07:00
Shay
62d9db7a7c docs(adr-0180): amend §1.5.3/§2.2 per T-1..T-4 findings
§1.5.3: content-addressed re-sort obligation is vacuous at compute_trace_hash
(folds vault_hits count, not contents); amend to apply at recall() result set
+ any future contents-bearing hash.

§2.2: Merge Kernel must content-address equal-score recall ties (multivector +
provenance bytes), not arrival/deque-index order — the general-path analog of
ADR-0181 §2.2's audio merge key.

Both sharpen the substrate ahead of the vault.rs LocalArena/SemilatticeDelta
refactor; neither blocks it. Sourced: docs/audit/ADR-0180-t1-t4-findings.md.
2026-05-29 12:20:54 -07:00
Shay
d95f8a99e0
docs: session wrap-up (comprehension chaining + overfitting discipline) + CLAUDE.md substrate (#472)
- New session record SESSION-2026-05-29-comprehension-and-overfitting-discipline.md:
  the reconciliation wave, CP-1/CP-2a (no cue reliable yet -> structure-first),
  GB-3a referent guard, GB-3b.1 accumulation (practice 0->55), the GB-3b.2
  overfitting course-correction (96/150 synthetic vs 1/50 real -> torn down), and
  the confuser corpus (baseline: 7 defects surfaced). Serving 3/47/0 throughout.
- Lands the prior dangling SESSION-2026-05-29-multistep-build-arc.md (was untracked).
- CLAUDE.md "Current Key Modules": adds the sealed GSM8K comprehension substrate
  (core/reliability_gate, generate/derivation, generate/cue_precision,
  evals/gsm8k_math {train_sample,practice,confusers}, the lane-SHA gate).
2026-05-29 11:18:27 -07:00
Shay
a67b475e59
docs(adr-0173): accept workbench ratification trust boundary (W0); queue reconciled W3 corridor brief (#469)
Flip ADR-0173 Proposed -> Accepted. This is the W0 gate for the
workbench-UI ratification wave: it amends ADR-0160's read-only stance
narrowly to admit operator-driven invocation of the three existing,
replay-gated Tier 1.5 handlers (apply_lexical_claim, apply_frame_claim,
apply_composition_claim) as a local keyboard accelerator over ADR-0161
Surface C. No UI code; implementation remains gated to the W1..W4
acceptance gates in the ADR.

Also lands the reconciled W3 ratification-corridor brief. It supersedes
the stale W3 section of WORKBENCH-UI-WAVE-BRIEF-PACK.md, which assumed a
'frontend zero' state (W1/W2 already merged via #295/#299/#329/#327/
#328/#303) and prescribed a Zustand store this repo never adopted. The
reconciled brief names the load-bearing facts the old one glossed:
- /ratify is advisory-only today (routes, never applies); W3's core
  backend task is the advisory->in-process flip.
- live proposals carry shape_category='uncategorized', so the safe
  category/polarity must be operator-supplied and allowlist-gated, not
  hard-coded -- the exact silent-wrong-category path case 0050 guards.

Verification this session: read-only workbench v1 confirmed working
(API serves real deterministic data, honest 404s, traversal rejected,
ratify advisory/no-mutation; 31 python + 104 UI tests green; pnpm build
green).

No runtime/algebra/eval paths touched. Docs only.
2026-05-29 11:14:25 -07:00
Shay
31d9cb429d
docs(adr-0163-f2): confuser corpus spec — a discrimination probe, not a coverage target (#468)
Follow-on to ADR-0163 §F that corrects the metric exposed by the overfitting
finding (96/150 synthetic flips vs 1/50 real; the 0002 cable/fraction problem read
as accumulation -> 996). Specs a small, hand-curated, real-sourced set of hard
negatives + near-miss confusers (disguised-polarity verbs, pseudo-accumulation
fractions, multi-referent/multi-actor, distractor quantities, temporal/question-
scope, comparative-referent, unit confusers) with minimal-pair construction.

Scored the opposite way from a coverage lane: success = wrong=0 on confusers +
pair-consistency + honest refusal frontier, NEVER solved-count. Held-out by
contract (not a training-to-fit target); the CP ledger consumes the wrong attempts
as the hard negatives the templated corpus lacked. Guardrails forbid reactive vocab
growth and template expansion.
2026-05-29 11:13:53 -07:00
Shay
274c81ea37
docs(adr-0178-gb3b): scope referent-aware accumulation chaining (#464)
Grounded scope for GB-3b, the next Gap B move. Measured opportunity: 46/150
additive practice cases are sum-of-all==gold, all currently refusing, all the
single-referent accumulation shape ('X has N. He buys M more.' -> N+M). They
refuse correctly (GB-3a's multi-clause guard / the Alice+Bob hazard); the safe
ones differ by referent identity + a change-verb cue, which GB-3b reads.

Scope covers: the reading (anchor + change steps), the wrong=0-critical referent
model (minimal no-new-actor guard; cross-references ADR-0164.2/.3 + ADR-0174's
multi-actor hazard; deliberately does NOT resurrect the retired gender-blind
resolver), the proof-carrying wrong=0 obligations, the cue-precision coupling
(change cues should finally be reliable, closing CP-2a), the increments, and
honest flip expectations (big chunk in practice-additive; modest train_sample;
serving stays 3/47/0 until ratification).
2026-05-29 10:41:54 -07:00
Shay
cecf7b82cc
test(adr-0180): T-1..T-4 Delta-CRDT pre-refactor obligations (Python, green) (#463)
ADR-0180 §1.5.4 + CLAUDE.md work-sequencing item 5 require these four
properties green on main before any core-rs/src/vault.rs change. They are
also the foundation ADR-0181 PR-5 (audio Delta-CRDT wiring) rides on.

  T-1  set-equality of vault writes under shuffled ingest (+ idempotent
       re-ingest at the content-addressed layer)
  T-2  trace-hash invariance to vault order, + recall result-set invariance
       to insertion order (the genuinely-failable half)
  T-3  versor_apply non-commutativity (negative guard)
  T-4  ProjectionHead.project purity across calls and threads

Findings (docs/audit/ADR-0180-t1-t4-findings.md):
- compute_trace_hash folds only vault_hits (a count), NOT vault contents, so
  ADR-0180 §1.5.3's "re-sort vault state in content-addressed order" is
  currently vacuous at the trace-hash layer; the live order-invariance
  obligation is at recall() (result-set + count). Recommend amending §1.5.3.
- equal-score recall ties are index-sensitive; the Merge Kernel needs a
  content-addressed tiebreak (mirrors ADR-0181 §2.2 merge key). Recommend
  amending §2.2.
- append is genuinely semilattice-eligible; versor_apply is non-commutative.

7 passed; smoke suite green. No runtime/core mutation — tests + audit only.
2026-05-29 10:40:52 -07:00
Shay
7451e7cd74
feat(adr-0177-cp2a): cue-precision ledger training + measurement (+ unit hygiene) (#461)
CP-2a populates the CP-1 ledger from gold-labelled candidate readings and reports
per-pattern reliability — the measurement the cue-precision thesis rests on. Plus
the function-word unit filter, whose value this measurement makes concrete (clean
unit_shape labelling).

What landed (all sealed; serving 3/47/0 byte-identical):
- generate/cue_precision/trainer.py — train_from_cases(cases, enumerators): folds
  gold-labelled candidate chains into the ledger via record_case. Decoupled (the
  candidate enumerators are injected, so the package still imports nothing from
  search). candidates_for dedupes a reading shared by two enumerators.
- generate/derivation/multistep.py — extracted the enumeration half of search_chain
  into public candidate_chains(problem_text); search_chain now delegates (verified
  byte-identical: ms3 tests + practice counts unchanged). CP-2 needs the readings
  the search weighs, not just the one it resolves.
- generate/derivation/extract.py — function-word unit filter (_NON_UNIT_WORDS):
  blanks spurious function-word units ($0.75 each -> "", 3/4 of -> "") that
  corrupt same-unit detection and unit_shape. Closed lexeme set, ADR-0165-safe.
- evals/gsm8k_math/practice/v1/cue_precision_report.py — trains over 200 sealed
  cases (50 train_sample + 150 ADR-0163-F additive) with the real enumerators and
  prints the per-pattern reliability table.
- tests/test_adr_0177_cp2a_training.py — trainer obligations (credit/dedupe/
  determinism/empty) via synthetic enumerators; real-measurement well-formedness;
  search_chain parity.

Load-bearing finding (recorded in ADR-0177): over 200 cases EVERY (cue,op,unit_shape)
pattern floors at ~0.0 reliability (best: for-multiply-cross_unit 0.0116 at 2/34).
The blunt product/sum-of-all readings are almost always wrong vs gold, so the
conservative floor correctly trusts nothing. => CP-2b (trust reliable cues) is
blocked on candidate GENERATION, not the ledger: candidate readings must get less
crude (clause/referent structure, ADR-0178 GB-3b) before any cue earns reliability.
Cue-precision and compositional structure are coupled; structure comes first.

Verification: 107 targeted tests green (CP-2a/CP-1/extract/ms3/GB-1/2/3/MS-1/2) +
architectural invariants; serving CLAIMS.md sha unchanged; practice 4/1/45 and
0/1/149 unchanged. Inert: trains/reports only, consulted by no search/gate.
2026-05-29 10:21:58 -07:00
Shay
fd96074230
docs(adr-0181): propose CORE-native audio compiler over Delta-CRDT substrate (#462)
Maps the AssetOverflow audio-compiler proposal onto the existing
sensorium ProjectionHead boundary (ADR-0013) and the Delta-CRDT
sharded substrate (ADR-0180).

Core mapping decision: the audio chunk boundary IS the CRDT delta
boundary. In-chunk rotor composition (compile_events) is the explicit
serialization barrier ADR-0180 §1.5.2 requires for non-commutative
versor_apply; the resulting AudioCompilationUnit is the order-invariant
delta written at the only semilattice-eligible layer (vault/store).
The compiler's checksum chain supplies the content-addressed merge key
(canonical, ir, projection sha256) that ADR-0180 §1.5.3 demands, making
idempotence structural and the sequential==concurrent trace-hash proof
checkable.

Adds:
- docs/decisions/ADR-0181-audio-compiler-delta-crdt.md (decision + mapping)
- docs/plans/audio-compiler-spec.md (typed AudioIR, operator table,
  manifest, numeric determinism, delta interface)
- docs/plans/audio-compiler-eval-plan.md (corpus, gates, A-1..A-6 CRDT
  proof obligations, teacher-migration policy)

Docs only; no runtime/core mutation. PR-2..PR-6 substrate work sequenced
in the ADR, with PR-5 gated on ADR-0180 §1.5.4 (T-1..T-4) green on main.
2026-05-29 10:19:54 -07:00
Shay
b1416814ea
docs(adr-0180): propose CRDT-sharded vault concurrency substrate (#457)
* docs(handoff): parallel-work plan post-GB-3a (CP-1 / scale / EX-3 tracks)

Three disjoint-file tracks dispatchable in parallel with Claude's serial Gap-B
line; records the hard constraint that GB-3b/4/5 are serial on compose.py.

* docs(adr-0180): propose CRDT-sharded vault concurrency substrate

Drafts ADR-0180 (Proposed) for a Delta-CRDT sharded substrate to support
forthcoming multimodal ingestion (vision, kinematics) without serializing
on a global Vault lock.

§1.5 grounds the proof obligation against the existing single-threaded
Python ingest path (sensorium → ingest/gate → field → vault/store →
compute_trace_hash) and enumerates four pre-refactor test obligations
(T-1..T-4) that must be green on main before any change to
core-rs/src/vault.rs lands, per CLAUDE.md work-sequencing item 5.

§1.5.5 explicitly fences out: approximate recall (exact CGA recall is
non-negotiable), hidden background execution (Merge Kernel must be
explicitly mounted with telemetry), and MLX/UMA hardware optimization
(deferred to a follow-up ADR; CPU-only Rust path lands first).

Proposed only — no code changes to core-rs, sensorium, or field.
2026-05-29 09:42:01 -07:00
Shay
5c1e9e7fe4
feat(adr-0178-gb3a): clause-scoped referent guard — refuse cross-clause aggregation (#456)
The mandated lookback review before GB-3 (CLAUDE.md §Lookback Review Discipline)
confirmed the audit's hazards H1/H2/H3 were LIVE: compose_sequential summed
same-unit quantities from the whole problem, merging unrelated referents/scopes
and admitting wrong structures whose value happened to ground:
  H1 (second actor's apples)      -> 6+4+2  = 12
  H2 (comparative on other actor) -> (6+4)*2 = 20
  H3 (later depletion event)      -> 6+4+3  = 13

Root cause is the audit's G1/D2 drift: GB-2a re-extracts from the whole text and
ignores GB-1's clause structure. The fix is the GB-3 increment — make the composer
clause-scoped (consume segment_clauses), refusing when the licensed structure spans
clauses, because this slice cannot model referents:
  - quantities must live in exactly ONE clause (0 or >1 -> refuse);
  - a comparative outside that clause -> refuse (unmodelled referent binding).

All three hazards now refuse; all 7 GB-2 single-clause structures preserved
(list-sum, three-item, sum-then-scale, and the mixed-unit/disagreement/too-few
refusals). tests/test_adr_0178_gb3_referent_guard.py would fail against the
pre-guard code (12/20/13), so the obligation is proven, not decorative.

Scope/safety:
- compose_sequential is sealed substrate, not wired to a scorer -> serving
  byte-identical 3/47/0 (lane-SHA 8/8, generate_claims --check OK); practice
  unchanged 4/1/45. No new test failures (2 pre-existing on main).
- ADR-0178 amended: GB-2 relabelled GB-2a (list slice, drift G1 recorded);
  GB-3 split into GB-3a (this referent guard, landed) and GB-3b (constructive
  cross-clause chaining, next).
2026-05-29 09:15:52 -07:00
Shay
38ef66c2a9 docs(backlog): capture everyday-atoms grounding pack idea (closed #449)
#449 shipped an inert, duplicated, unvalidated pack off-brief; closed it but kept
the on-thesis idea (ground the nouns GSM8K problems use) with the real scope it
would need to be beneficial.
2026-05-29 08:55:08 -07:00
Shay
65d857e72a
feat(adr-0179): integrate EX-1/EX-4/EX-5 extraction richness (sealed lane) (#455)
Reconciles ChatGPT's four independently-branched extraction PRs (#451/#452/
#453/#454) into one coherent generate/derivation/extract.py. They each rewrote
the same file + same new test off main, so they conflicted pairwise and needed
integration, not a merge.

Integrated (span-tracked, most-specific-pass-first so numbers are never double
counted):
- EX-1 word-numbers (#452): reuses WORD_NUMBERS; tens-one hyphen compounds;
  factor-bearing half/third/quarter excluded.
- EX-4 list-unit inheritance (#451): bare numeric list with one trailing unit.
- EX-5 sentence-final numbers (#454): bare final number with empty unit.

Deferred: EX-3 multi-word units (#453). Its greedy lowercase span reads
"6 apples and 4 apples" as unit "apples and", regressing GB-2's
test_same_unit_list_sums, and still can't recover real multi-word units from
0024-class text ("jumping jacks on"). Needs a tighter rule; see
docs/handoff/AUDIT-ADR-0179-EX-RECONCILE.md.

Verification (sealed lane only; chat/ does not import this module):
- Serving frozen: lane-SHA 8/8 match, generate_claims --check OK -> 3/47/0
  byte-identical, wrong=0 held.
- Sealed practice improved 4/2/44 -> 4/1/45: case 0025 flips wrong->refused.
  EX-1 reads "three", so completeness sees a quantity the 6x50 chain omits and
  refuses the spurious 300 (gold 1200) instead of committing it.
- No new test failures (3 pre-existing on main).

Also fixes stale test drift from EX-2 (#447): TestDecimalGroundingGapIsDeferred
asserted decimals still refuse, but #447 made $0.75-class resolve to 864.
Renamed to TestDecimalGroundingResolves and updated to assert the flip.

Honest scope note: EX-4 does NOT unblock real case 0024 (its PR test used a
fabricated bare-list paraphrase). TestRealCase0024StillBlocked pins the true
boundary.
2026-05-29 08:43:03 -07:00
Shay
e7032f9e0a
audit: ADR-0178 GB-1/GB-2 lookback (findings only — no code change) (#450)
* add audit report

* docs(audit): expand ADR-0178 GB-1/GB-2 lookback report
2026-05-29 08:42:58 -07:00
Shay
fbcefba00c
docs(adr-0179): scope extraction richness — the prerequisite that unblocks coverage (#446)
The recurring wall every recent measurement hit: the structure machinery (MS-3,
GB-1, GB-2) is built but STARVED by thin extraction. extract.py's digit+single-word
regex loses word-numbers ('three'), multi-word units ('jumping jacks'), currency/
decimals, sentence-final numbers, and mis-attributes units ('36 on Tuesday'->'on',
which blocks GB-2 same-unit list-sum on 0024).

Two layers, very different risk:
(A) sealed derivation extractor (extract.py) — safe to enrich (over-extraction is
caught by the gate's completeness+grounding+uniqueness; refuse-preferring). Bulk
lives here.
(B) shared grounding primitive (_value_grounds/_tokens) — wrong=0-sensitive (serving
round-trip uses it). EXACTLY ONE change: bare-decimal grounding ('N.M' grounds when
digit-runs N,M appear — symmetric with existing .NN/N/M logic), wrong=0-gated by
serving 3/47/0 byte-identical (lane-SHA gate). _value_grounds already handles /bin/zsh.75
but the extractor strips the $ -> bare 0.75 fails; that's the 0003 gap.

Reuses en_numerics_v1 + WORD_NUMBERS (word-numbers) + existing currency/fraction/
compound grounding (ADR-0128/0131.G.3) — extends, never reinvents. Lexeme-level
(ADR-0165). Sub-phases EX-1 word-numbers, EX-2 currency/decimal + grounding fix,
EX-3 multi-word units, EX-4 list-unit inheritance (unblocks 0024), EX-5 sentence-
final, EX-6 measure.

Honest payoff: unblocks BUILT capability — uniform units -> GB-2 list-sum fires
(0024); decimals -> MS-3 product flips (0003); word-numbers -> comparatives resolve;
new gold-matching chains -> feed cue-precision (0177's bottleneck). Flip-curve
should finally move on extraction-blocked cases; op-ambiguity + scale still gate the
rest. wrong=0 obligations: serving byte-identical after the grounding fix; over-
extraction refuse-preferring; determinism.
2026-05-29 08:42:54 -07:00
Shay
8807d29f50 docs(handoff): remote-work brief for ChatGPT connector (audit GB-1/GB-2 + ADR-0179 sealed extraction) 2026-05-28 17:44:48 -07:00
Shay
5dacc6625e
Merge pull request #443 from AssetOverflow/docs/adr-0178-compositional-structure
ADR-0178 (Proposed): Compositional Structure — comprehension-guided multi-step (Gap B)
2026-05-28 17:15:52 -07:00
Shay
9a7f9f6a66 docs(adr-0178): scope Gap B — comprehension-guided compositional structure
The actual coverage lever (ADR-0177 established cue-precision is its gate+prune,
not the unlock). Gap B = which quantities group via which ops in what order.

The reframe that resolves the rich-search-vs-uniqueness tension: structure-from-
READING, not enumeration. The text encodes its own structure — every gold case
fits a sequential clause-by-clause read (0021 one clause 15x10x3; 0003 48 ->x24
->x0.75; 0024 sum ->x3; 0033 seq chain + branch). So Gap B is comprehension: read
the problem, build the derivation structure as you read, hold alternatives on
ambiguity, reevaluate on lookback. This IS the project's original 'word-to-word
with lookback + problem-solving throughout' articulation, and the synthesis of
reader (0174) + solver/gate (0176) + learning (0177) + packs.

Decision: a comprehension-guided sequential composer — clause-local bounded
sub-derivations combined across clauses via relational cues (per/each/of->multiply,
and-list->sum, comparative->scale, more/older->add, fewer/less->subtract), held-
hypothesis on ambiguity + eliminate/reevaluate (REPOINT ADR-0174's inert reader
substrate from parse to STRUCTURE — where it finally becomes load-bearing), scored
by the 0176 self-verification gate + uniqueness, guided by 0177 cue-precision.
Locality bounds the search; relational cues constrain the cross-clause op so
uniqueness can RESOLVE (not just refuse). Coverage rises only as far as the reading
constrains structure; irreducible ambiguity refuses (wrong=0).

wrong=0 obligations: per-step self-verification, irreducible-ambiguity-refuses,
completeness+uniqueness over the whole structure, no-spurious-structure, determinism,
sealed. Honest hard parts: relational-cue precision (co-dependent with 0177 +
data-starved), clause segmentation, referent binding, branch/DAG (0033 quantity
reuse, GB-5), scale. This is the comprehension core — largest remaining capability;
serving lift materialises here, incrementally. Sub-phases GB-1..GB-6.
2026-05-28 17:06:35 -07:00
Shay
b57e5dca9a docs(adr-0177): scope cue-precision learning (the self-supervised half)
The lever MS-1->MS-3 proved: learn which (cue->op) readings are reliable from
practice eliminations, closing ADR-0175's self-verification 'necessary-not-
sufficient' gap before Phase 5.

Mechanism: per-(cue, op, unit_shape) reliability ledger (reuses ADR-0175 ClassTally
+ conservative_floor), fed by gold-labelling search candidate chains. Three uses:
U1 self-verification TRUST (near-term value: makes the Phase 5 proposal gate honest;
cold ledger => refuse, no junk proposals), U2 search guidance, U3 disagreement
resolution (coverage lever, hard-gated: margin+theta, ties refuse).

Load-bearing honesty (the bottleneck): a pattern earns POSITIVE signal only from a
gold-MATCHING chain; current blunt shapes match gold for ~4/50 cases, so the ledger
is starved (all-blame) AND structure failures (Gap B) pollute cue->op credit (a
correct op penalised for a product-of-ALL structure error). Plus data starvation
(50 cases << N_min). So cue-precision is COUPLED to richer guided shapes (Gap B) +
scale; it co-evolves (Gap B supplies gold-matching candidates -> cue-precision earns
signal -> prunes Gap B's search). It is the TRUST substrate + pruning engine, NOT
the coverage unlock by itself.

Recommended sequencing: CP-1/CP-2 (mechanism + self-verification trust, near-term
correctness value) now; richer guided shapes (Gap B) next as the flip lever; scale
makes it compound. wrong=0 obligations: cold=>no regression, ties refuse, theta-gated
serving, credit-noise can't flip serving (floor+N_min+margin+ratification+gold-tether),
determinism. Sub-phases CP-1..CP-4.
2026-05-28 17:00:33 -07:00
Shay
68e6cbd4ef docs(adr-0176): scope multi-step grounded composition with question-targeting
The dominant remaining lever for serving lift (79% need mul, median 3 steps;
single-step search + completeness flips only 0021). Grounded in gold step
structures: derivations are CHAINS with intermediate results as operands;
quantities come from body AND question (0033's '25'); several need comparatives
(half/N-times).

Decision: bounded, deterministic, TARGET-GUIDED multi-step grounded derivation
search, gated by ADR-0175's strengthened self-verification (grounding ∧ cue ∧
unit ∧ completeness) + uniqueness + a new question-target match. Sealed practice.

Two new ideas beyond 0175: question-targeting (turn the question into a target =
search-pruning + stopping criterion) and multi-step chaining (intermediates as
derived operands). Sub-phases MS-1..MS-5, wrong=0-first (gate/target before broad
search). Invariant #2 extended to chains. Honest hard part: search explosion +
uniqueness refuses most -> target-pruning + cue-guidance + depth-bound are the
tractability levers; low coverage initially; comparatives pack is a prerequisite;
serving lift still waits on 0175 Phase 5 ratification. Reuses solver +
question extraction + round-trip primitives.
2026-05-28 16:00:00 -07:00
Shay
dd6064065f
Merge pull request #431 from AssetOverflow/feat/adr-0175-calibrated-learning
ADR-0175 (Proposed): Calibrated Attempt-and-Eliminate Learning — two regimes under wrong=0
2026-05-28 15:43:15 -07:00
Shay
5ecfda3fab docs(adr-0175): record Phases 1-3b lookback review
Solid: 4 invariants proven by failing-under-violation tests; 84 green; seal
verified. No live hazards (9 search wrongs are sealed eliminations).
Drift: (1) 3a gate is PARTIAL vs spec — round-trip + no-contradiction not wired;
3b's necessary-not-sufficient finding follows -> a self-verification-strengthening
phase must precede Phase 5. (2) class taxonomy: Phase 2 uses gold operation-class
not capability-axis. (3) minor defensive-branch test gaps (no risk).
2026-05-28 15:34:21 -07:00
Shay
13d016c90b docs(adr-0175): pre-implementation audit — correct reuse overclaims, record findings
Lookback/cross-reference audit before any code. No hard blockers. Corrects 3
overclaims of reuse and records the audit:
- reliability ledger is NEW (calibration/ is a grid-search param tuner, not a ledger)
- 0174 eliminate/reevaluate/contemplate is reading-coupled -> 'repoint to solving'
  needs generalization, not drop-in reuse
- teaching corridor evidence (MathReaderRefusalEvidence) is reader-refusal-coupled
  -> solver-practice proposals need a new evidence type
Constraints recorded: wrong=0 pinned on serving lane by ~25 tests + train_sample
runner -> practice MUST be a separate lane (phasing updated). Alignments noted:
ADR-0165 (lexemes-not-grammar) fulfilled by thin-front-end/thick-solver split;
INV-07 governance = no-self-authorization pre-wired; MAX_TOTAL_BRANCHES precedent
for bounded deterministic search; seal exists.
2026-05-28 14:55:53 -07:00
Shay
e3c28773ff docs(adr-0175): pin conservative_floor (Wilson lower bound) + N_min
Resolves Open Question #1. conservative_floor(s,k) = one-sided Wilson lower
bound over COMMITTED trials (k=correct+wrong; refusals excluded so coverage
never penalizes reliability). Constants: z=2.576 (single global pessimism
knob), N_min=10. Range [0,1) — never returns exactly 1.0. float64 rounded
half-to-even to 1e-9 for cross-backend replay. z (estimator skepticism) and
per-class theta (action's required reliability, human-set) are independent
dials; engine touches neither. Worked cost-to-clear table + asymmetry example
included.
2026-05-28 14:51:50 -07:00
Shay
8c2e469be0 docs(adr-0175): calibrated attempt-and-eliminate learning architecture
Proposed ADR + session derivation doc capturing the 2026-05-28 design
discussion that took GSM8K Phase 5b from 'build another matcher' to a
self-calibrating problem solver.

Session doc (docs/sessions/SESSION-2026-05-28-...): the full journey —
problem (per-shape matchers can't compound; 79% need mul, 0% single-step),
dead-ends (brute-force spurious matches; 0021 is the only single-sentence
case and it's idiosyncratic), and the four pivots that converged on the
solution.

ADR-0175 (Proposed): the decision —
- two regimes: serving (wrong=0, unchanged) vs sealed practice
  (attempt-and-eliminate; wrong is the learning signal)
- proof-carrying seal: practice never writes serving; ratification only
- deterministic attempt/refuse gate: reliability(C) / theta_required >= 1
  (NOT RL; regimes collapse the reward side so only reliability is quantified)
- per-class calibration ledger of replayable COUNTS + conservative lower
  bound; human-set theta ceilings raised only on evidence
- checkability ladder (gold > convergent self-verification > consistency-only),
  privilege proportional to reversibility; provenance + gold tether against
  correlated self-delusion
- diagnostic refusal routes skill vs knowledge vs ambiguity; three
  compounding stores (vault/packs/pruning); self-proving acquisition narrows
  human input without bypassing the gate
- five proof-obligation invariants (wrong=0 on serving, no spurious banking,
  determinism, no self-authorization, retractability)

Supersedes the matcher-oriented ADR-0174 5b sub-phases; repoints the
0174 eliminate/reevaluate/contemplate substrate from reading to solving.
Open question: shape of conservative_floor + N_min.
2026-05-28 14:45:17 -07:00
Shay
5830c1fb8c docs(adr-0174): write Phase 5b scope — operation-capability buildout
Grounded in a ground-truth measurement of the 47 train_sample refusals
against GSM8K's own <<a*b=c>> calculator annotations:
- 37/47 (79%) use multiplication; 43/47 use mul-or-div; 0/47 single-step
- multiplication is the foundational general capability (breadth = the
  anti-overfitting signal), but necessary-not-sufficient: no case flips
  from an operation matcher alone

Solver already supports {add,subtract,transfer,multiply,divide,apply_rate,
compare_additive,compare_multiplicative}; the gap is the reader->injector->
Operation front-end (matcher extracts 0 anchors on real sentences).

Sub-phase sequence (biggest-chunk-first, measure-the-flip-gated):
- 5b.1 single-sentence multiplicative aggregate (cleanest proof, ~2-4)
- 5b.2 shallow 2-3 step composition (25/47, the real chunk)
- 5b.3 deep multi-step 4-7 (22/47) under held-hypothesis elimination
Generality guard: flipped cases must hold under ADR-0114a perturbation/OOD.
Explicitly NOT widening discrete_count injector (overfitting + wrong=0 hazard).
2026-05-28 13:48:58 -07:00
Shay
3fd317290b feat(adr-0174-phase5a): retire inert GSM8K scoring-path reader
The recognizer/candidate-graph path is the single canonical reader.
Retires the flag-gated incremental-reader dispatch that admitted 0/50 on
train_sample and only added a dead fall-through:

- remove _try_comprehension_reader, _try_reader_for_question, _tokenize_sentence
  and both dispatch blocks from generate/math_candidate_graph.py
- delete generate/comprehension/lifecycle_runtime_adapter.py (402 LOC,
  used only by the question-reader dispatch)
- drop the comprehension_reader_questions config flag and the parse_and_solve
  / _score_one_candidate_graph config threading
- remove the --use-reader runner plumbing + flag-ON/OFF delta report from
  the train_sample runner; refresh report.json (drops stale use_reader field
  and a stale refusal-reason; verdicts unchanged at 3/47/0)
- remove the now-dead use_reader field from teaching/coverage.py
  CoverageReport + the core teaching coverage CLI flag
- delete tests/test_reader_coexistence.py (flag-ON/OFF premise dissolved);
  fix 3 ADR-0174 build_report calls and 2 subprocess invocations

lifecycle.py and audit.py are KEPT — they are load-bearing for the ADR-0172
math-contemplation teaching corridor (audit_problem -> teaching/math_*),
which a pre-deletion trace surfaced. The parent ADR's plan to delete
lifecycle.py was wrong; only its GSM8K scoring dispatch was inert.

Net -1,038 LOC (code + tests). Behavior-preserving:
- train_sample 3/47/0, byte-identical verdicts to pre-5a baseline
- determinism holds; smoke/packs/runtime/cognition/teaching lanes green
- contemplation corridor + lifecycle/audit tests pass

Pre-existing (NOT introduced here; reproduce on base with changes stashed):
5 out-of-curated-lane stale committed-artifact / stale-assertion failures
(test_math_evidence_e2e, test_adr_0126_runner_wiring, G3/coverage_probe
report-match, test_refusal_taxonomy_lane rebuild).
2026-05-28 13:38:44 -07:00
Shay
62a3e23318 docs(adr-0174): amend Phase 5 scope — invert premise, split 5a/5b
Pre-implementation investigation (lookback discipline) found the original
Phase 5 text inverted against shipped code:
- math_parser.py already out of runtime + candidate-graph scoring path
- lifecycle.py admits 0/50 (inert parallel parser, not the reader to promote)
- correct>=25 is a semantic gate structural collapse cannot meet

Decision (Invert + split): recognizer/candidate-graph path is the canonical
reader; lifecycle.py is retired. Phase 5a = structural retirement (net -LOC,
3/47/0 byte-identical, wrong=0). Phase 5b = semantic narrowness removal (the
real lift, own sub-phases, per-layer wrong=0 obligations).
2026-05-28 13:19:30 -07:00
Shay
619cd62227 fix(adr-0174-phase3a): multi-actor pronoun hazard defense + test backfills + ADR amendment
All findings from the 2026-05-28 Phase 1-3a lookback review addressed
in one commit on the Phase 3a branch:

Wrong=0 hazard defense (the load-bearing fix):
- generate/math_candidate_graph.py: Phase 3a wiring now collects the
  set of distinct proper-noun subjects seen in prior context. When
  more than one exists, refuses with no_antecedent_ambiguous trace
  event rather than guessing the most-recent (which was gender-blind
  single-binding — wrong attribution in multi-actor problems).
- Refusals from the statement loop now preserve _statement_trace via
  reader_trace in CandidateGraphResult (pre-existing latent issue:
  Phase 2/3 trace events were dropped on early statement refusal).
- New tests assert: ambiguous case refuses with correct trace; single-
  actor case still resolves normally.

Test coverage backfills (closes the 13 untested predicate-name gaps):
- TestCheckConstraintsInitialPredicateNames — 3 tests asserting the
  exact predicate name on initial.value_grounds / initial.unit_grounds
  / initial.entity_grounds failure paths.
- TestCheckConstraintsOperationPredicateNames — 3 tests asserting
  operation.verb_grounds / operation.value_grounds / operation.unit_grounds
  failure-predicate-name parity.
- TestCheckConstraintsComposedInitialPath — 4 tests for the RAT-1
  composed_initial path which was entirely untested in Phase 2
  (parity manually verified during lookback review; now automated).

ADR amendment (honest doc vs impl drift):
- docs/decisions/ADR-0174-held-hypothesis-comprehension.md: appended
  'Implementation Notes' section documenting:
  - reevaluate signature differs from spec text (shipped is more
    composable; treat as amended)
  - Phase 2 wires per-candidate, not per-token (per-token is Phase 5)
  - Lookback recompute is candidate-level, not token-level
  - Hypothesis.constraint_state is never populated by Phase 2
  - Multi-actor pronoun hazard defense rationale
  - Honest LOC accounting: Phases 1-3a net +1,500 lines (Phase 5
    delivers the projected net removal)
  - Test coverage backfill summary

Cosmetic:
- lookback.py:297 unreachable raise — added # type: ignore[unreachable]
  with comment explaining defensive future-proofing for Phase 3b.

Acceptance verified:
- 124/124 Phase 1+2+3a + reader tests pass (was 95/95 before backfills)
- Smoke 67/67, packs 141/141
- train_sample 3/47/0 preserved (wrong=0 invariant held)
- Multi-actor hazard live-tested: parse_and_solve refuses the
  Alice/Bob/She case with no_antecedent_ambiguous trace event

See CLAUDE.md §Lookback Review Discipline and memory
feedback-lookback-review-discipline for the doctrine that surfaced
all of these issues at the right time.
2026-05-28 10:49:20 -07:00