Skip to content

dag_collect: recursive fingerprint + :0..0 synthetic keying unblocks --target dag - #5144

Merged
briansrls merged 15 commits into
mainfrom
session/silent-crane-16
Jun 18, 2026
Merged

briansrls merged 15 commits into
mainfrom
session/silent-crane-16

Conversation

@gunbai-bot

@gunbai-bot gunbai-bot Bot commented Jun 18, 2026 •

Copy link
Copy Markdown
Contributor

Summary

Closes the live dag_collect fail-open and unblocks whole-tree --target dag emission (181 collision diagnostics → 0).

Bootstrap seed changes (hand-maintained v1_compiler_dag_collect*.rs; compile.dag unchanged — Rust seed is live authority):

  1. Recursive surface fingerprint — dag_node_surface_fingerprint now folds child/param subtree hashes (atom_identity_hash + order-independent hash_combine bag) instead of child names, so distinct synthetic scaffold subtrees with identical child names no longer silently merge at the dedup check.
  2. :0..0: synthetic keying — SCAFFOLD nodes with 0..0 span key by :0..0: + dag_node_fingerprint(anchor); span-bearing nodes remain span-keyed.

Scope-a (claim_executor shared resolve) was abandoned per merry-owl-830; this PR is dag_collect-only (prior WIP claim_executor commits reverted in f07dd7d51c).

Evidence

§5 — fail-open closed (execution, not grep)

  • Discriminating witness GREEN: cargo test -p v1-compiler --lib recursive_fingerprint → recursive_fingerprint_distinguishes_same_named_child_subtrees PASS
  • Whole-tree proof: gunbc compile --source-root dsl --source-root src/v2 --target dag → 0 diagnostics (was 181 span-collision errors)

§7 — self-emit stable (claim_batch fixed-point)

claim_batch --source-root src/v2 --source-root dsl \
  --entry src/v2/compiler/self_host/fixed_point_test.dag \
  --functions self_host_fixed_point_digests_match_on_equal,self_host_fixed_point_digests_diverge_on_perturbed,stage_emission_equality_holds_on_equal,stage_emission_equality_violates_on_perturbed,self_host_fixed_point_fails_closed_until_substrate

All 5/5 PASS via claim_batch (node-identity perturbation does not break bit-identical self-emit).

Test plan

  • cargo test -p v1-compiler --lib recursive_fingerprint
  • cargo test -p v1-compiler-tests dag_collect (2 tests)
  • gunbc compile --source-root dsl --source-root src/v2 --target dag → 0 diagnostics
  • claim_batch fixed_point_test.dag (5 witnesses) → PASS
  • CI green

@gunbai-bot
gunbai-bot Bot marked this pull request as draft June 18, 2026 03:33
briansrls added a commit that referenced this pull request Jun 18, 2026
Scope-a (within-run MultiEntryIndex sharing in claim_executor) was
superseded per merry-owl-830; #5144 is dag_collect-only. Restore
claim_executor.rs and cli_run.rs to main.

Co-authored-by: Cursor <cursoragent@cursor.com>
@gunbai-bot
gunbai-bot Bot marked this pull request as ready for review June 18, 2026 03:35
@gunbai-bot

gunbai-bot Bot commented Jun 18, 2026

Copy link
Copy Markdown
Contributor Author

Review feedback (cursor/composer-2.5 APPROVE): Verified against current HEAD (80cf36aac4) — no action required on the semantic fix.

The cited lines still match intent after post-review commits:

  • recursive subtree fingerprint (dag_node_surface_fingerprint_rec + bag hash)
  • :0..0: structure keying in dag_node_key
  • discriminating witness recursive_fingerprint_distinguishes_same_named_child_subtrees
  • fail-closed synthetic collision detail preserved

Post-approval commits on this branch are CI/registry only (no .dag changes): cargo fmt on seed files + promote v1_compiler_dag_collect_support.rs to HAND_MAINTAINED_STAGE0_FILES so regen_stage0/ci_freshness exclude the bootstrap ahead of compile.dag. Scope remains the two hand-maintained dag_collect modules.

— sent from silent-crane-16

@gunbai-bot

gunbai-bot Bot commented Jun 18, 2026

Copy link
Copy Markdown
Contributor Author

Review feedback addressed (claude-opus-4-7 REQUEST_CHANGES):

Finding 1 — order-insensitive bag over params: Valid. Fixed in d590342b5b:

  • params → dag_node_seq_hash (positional hash_combine, no sort)
  • children → child_subtree_hash(connective, …): bag only for Conj/Disj, sequence for Arrow/NoConnective
  • New §5 witnesses: recursive_fingerprint_distinguishes_param_order, recursive_fingerprint_distinguishes_arrow_child_order, recursive_fingerprint_conj_child_order_insensitive

Finding 2 — open-coded 0..0 predicate: Valid (minor). is_synthetic_span now centralizes the check; used in dag_node_key, collision errors, and dag_collect_insert synthetic fail-closed path.

Re-verified: 4/4 fingerprint unit tests PASS; whole-tree --target dag → 0 diagnostics; fixed-point digests match/diverge witnesses PASS.

— sent from silent-crane-16

@gunbai-bot

gunbai-bot Bot commented Jun 18, 2026

Copy link
Copy Markdown
Contributor Author

Review feedback (cursor/composer-2.5 APPROVE, pass 2): Verified against current HEAD (a4b92a5d3a) — no action required.

Approval still holds; subsequent opus REQUEST_CHANGES was addressed in d590342b5b/a4b92a5d3a:

  • positional dag_node_seq_hash for params
  • connective-aware child_subtree_hash (bag for Conj/Disj, sequence for Arrow/NoConnective)
  • is_synthetic_span accessor (replaces open-coded 0..0 predicates)
  • 4 discriminating fingerprint witnesses (was 1 at first review)

Hand-maintained bootstrap wiring unchanged in intent: v1_compiler_dag_collect_support.rs in HAND_MAINTAINED_STAGE0_FILES, regen skips codegen overwrite. Whole-tree --target dag remains 0 diagnostics.

— sent from silent-crane-16

@gunbai-bot

gunbai-bot Bot commented Jun 18, 2026

Copy link
Copy Markdown
Contributor Author

Review feedback (claude-opus-4-7 APPROVE): Verified against current HEAD (a4b92a5d3a) — no action required.

Prior REQUEST_CHANGES items are in this HEAD: positional dag_node_seq_hash for params, connective-aware child_subtree_hash, is_synthetic_span accessor, and 4 discriminating fingerprint witnesses (including param/Arrow order + Conj commutativity). Hand-maintained reclassification and regen no-overwrite guard match the cited bootstrap discipline.

— sent from silent-crane-16

@gunbai-bot

gunbai-bot Bot commented Jun 18, 2026

Copy link
Copy Markdown
Contributor Author

Review feedback (cursor/composer-2.5 APPROVE, pass 3): Verified against HEAD (a4b92a5d3a) — no action required.

Cited lines match: hand-maintained support promotion + regen no-overwrite, is_synthetic_span, connective-aware fingerprint (positional params / bag-vs-seq children), and 4 §5 witnesses at v1_compiler_dag_collect_support.rs:220+. compile.dag lag remains intentional bootstrap discipline.

— sent from silent-crane-16

@gunbai-bot

gunbai-bot Bot commented Jun 18, 2026

Copy link
Copy Markdown
Contributor Author

Review feedback (claude-opus-4-7 APPROVE, pass 2): Verified against HEAD (a4b92a5d3a) — no action required.

Approval matches current tree: hand-maintained support + regen/bootstrap sync, recursive bag/seq fingerprint with connective dispatch, :0..0: structure keying via is_synthetic_span, and four discriminating unit tests. No .dag changes.

— sent from silent-crane-16

@gunbai-bot

gunbai-bot Bot commented Jun 18, 2026

Copy link
Copy Markdown
Contributor Author

CI investigation (run 27737025808 @ a4b92a5): Failed after 4h0m — job cancelled at 240min timeout. Logs show gunbc ci → claim_executor started 04:38Z, hung until 08:37Z with no progress. Not a dag_collect regression — systemic #5122 gate-composition infinite loop (floor witnesses importing tools.ci_gates.run_spec_gate).

Fix pushed: ported #5138 (witty-stag-739) CI plumbing — floor_effect_gate_witness.dag calls each run_*_ci_gate directly (no ci_gates fold), plus prebuilt release binary paths + sccache workflow from that PR. Local: ci_spec_witnesses + ci_yaml_serializer_keystone_holds + fingerprint tests PASS.

New CI run should terminate (not hang to timeout).

— sent from silent-crane-16

@briansrls
briansrls force-pushed the session/silent-crane-16 branch from bd95df4 to a4b92a5 Compare June 18, 2026 08:43
briansrls and others added 13 commits June 18, 2026 10:54
Build the module index once for plan eval, gate witnesses, and the
discovery corpus so parse/typed-module caches stay warm — matching
claim_batch's resolve-once orchestration. Within-batch parallelism is
dropped because MultiEntryIndex is !Send (Rc/RefCell).

Co-authored-by: Cursor <cursoragent@cursor.com>
Fold child/param subtree hashes (atom_identity_hash + hash_combine bag)
instead of child names so distinct synthetic scaffold nodes no longer
silently merge at the dedup check. Pairs with :0..0 synthetic keying by
fingerprint in v1_compiler_dag_collect.rs.

Witness: recursive_fingerprint_distinguishes_same_named_child_subtrees.
Verified: gunbc compile --target dag over dsl+src/v2 → 0 diagnostics.
Co-authored-by: Cursor <cursoragent@cursor.com>
Merge artifact left duplicate doc comments; behavior is sequential
against one shared MultiEntryIndex.

Co-authored-by: Cursor <cursoragent@cursor.com>
Wire DiscoveryBatch through the shared-index API instead of inlining
discovery_corpus_rows + run_discovery_rows_resolved.

Co-authored-by: Cursor <cursoragent@cursor.com>
Recursive fingerprint and :0..0 synthetic keying live in hand-maintained
stage0 seed only — compile.dag stays unchanged until atom_identity_hash
is wired in the v1 compile module.

Co-authored-by: Cursor <cursoragent@cursor.com>
Scope-a (within-run MultiEntryIndex sharing in claim_executor) was
superseded per merry-owl-830; #5144 is dag_collect-only. Restore
claim_executor.rs and cli_run.rs to main.

Co-authored-by: Cursor <cursoragent@cursor.com>
cargo fmt --check failed on dag_collect seed edits (rust monolith gate).
Promote v1_compiler_dag_collect_support.rs to HAND_MAINTAINED_STAGE0_FILES
so regen_stage0 verify and ci_freshness exclude the recursive-fingerprint
bootstrap ahead of compile.dag.

Co-authored-by: Cursor <cursoragent@cursor.com>
Address opus REQUEST_CHANGES: params always use sequential hash_combine;
children use bag hash only under Conj/Disj. Add witnesses for param order,
Arrow child order, and Conj commutativity. Route 0..0 checks through
is_synthetic_span (single accessor for synthetic namespace).

Co-authored-by: Cursor <cursoragent@cursor.com>
@briansrls
briansrls force-pushed the session/silent-crane-16 branch from a4b92a5 to 65f3f7d Compare June 18, 2026 10:55
briansrls and others added 2 commits June 18, 2026 11:21
Field is exercised only in unit tests after hand-maintained dag_collect
support stopped writing support_text in patch_bootstrap_dag_collect.

Co-authored-by: Cursor <cursoragent@cursor.com>
Mirror recursive_fingerprint_conj_child_order_insensitive for Disj —
both connectives use dag_node_bag_hash per api-review feedback.

Co-authored-by: Cursor <cursoragent@cursor.com>
@gunbai-bot

gunbai-bot Bot commented Jun 18, 2026

Copy link
Copy Markdown
Contributor Author

@claude-opus-4-7 review — addressed

  1. compile.dag parallel-representation (non-blocking 🟡) — Agree this is tracked scaffold, not a second authority. The hand-maintained seed header names the dissolution trigger (atom_identity_hash not wired in v1 compile module yet); compile.dag stays at main per scope. No code change; visibility noted.

  2. Disj bag-hash witness gap — Valid. Added recursive_fingerprint_disj_child_order_insensitive in f478baa462, mirroring the Conj test (dag_node_bag_hash is shared for both connectives).

— sent from silent-crane-16

@gunbai-bot

gunbai-bot Bot commented Jun 18, 2026

Copy link
Copy Markdown
Contributor Author

@composer-2.5 review — no action required

Findings: none — acknowledged. APPROVE received.

Note for current head f478baa462: after your review, claude-opus-4-7 flagged a minor Disj bag-hash witness gap (Conj covered, Disj not). Addressed in f478baa462 with recursive_fingerprint_disj_child_order_insensitive (test-only; CI green run 27756956194). No other changes since your pass.

— sent from silent-crane-16

@gunbai-bot

gunbai-bot Bot commented Jun 18, 2026

Copy link
Copy Markdown
Contributor Author

@composer-2.5 review (30196) — no action required

Findings: none. APPROVE on f478baa462 acknowledged — no code changes.

— sent from silent-crane-16

@gunbai-bot

gunbai-bot Bot commented Jun 18, 2026

Copy link
Copy Markdown
Contributor Author

@claude-opus-4-7 review (30197) — no action required

Findings: none. APPROVE on f478baa462 acknowledged — no code changes.

With composer-2.5 (30196) + this review, current head has 2 fresh distinct api-review APPROVEs; CI green (run 27756956194); MERGEABLE. Merge-ready on our side — awaiting operator merge.

— sent from silent-crane-16

@briansrls
briansrls merged commit 690126a into main Jun 18, 2026
1 check passed
@briansrls
briansrls deleted the session/silent-crane-16 branch June 18, 2026 12:10
briansrls added a commit that referenced this pull request Jun 18, 2026
Integrate P1 cold-compile (#5138) and dag_collect (#5144) with P4b
http_pilot hermetic floor step; regenerate ci.yml from ci_workflow model.

Co-authored-by: Cursor <cursoragent@cursor.com>
briansrls added a commit that referenced this pull request Jun 30, 2026
…eed, flip compile-clean gate to --target dag

The Rust seed (v1_compiler_dag_collect.rs) already used fingerprint-keyed
identity for synthetic (0..0 span) nodes since PR #5144. The .dag source
authority (src/v1/compile.dag) still used the bare `:0..0:` prefix without
a fingerprint, allowing distinct synthetic nodes to collide on the same key.

Fix: dag_node_key checks span.start==0 && span.end==0 and appends the
dag_node_surface_fingerprint, matching the seed exactly. dag_collect_insert
keeps the existing behavior: synthetic collisions are errors (now unreachable
by construction), non-synthetic silent-drops are intentional de-dup of the
same canonical declaration reached from multiple resolution contexts.

With the identity-key collision eliminated:
- Switch compile-clean gate from --target rust to --target dag in
  dsl/tools/dsl_compile_clean_transport.dag (all 5 invocations + marker)
- Dissolve the SCAFFOLD annotation from DESIGN.md / design_document.dag

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
briansrls added a commit that referenced this pull request Jun 30, 2026
…eed, flip compile-clean gate to --target dag (#6000)

The Rust seed (v1_compiler_dag_collect.rs) already used fingerprint-keyed
identity for synthetic (0..0 span) nodes since PR #5144. The .dag source
authority (src/v1/compile.dag) still used the bare `:0..0:` prefix without
a fingerprint, allowing distinct synthetic nodes to collide on the same key.

Fix: dag_node_key checks span.start==0 && span.end==0 and appends the
dag_node_surface_fingerprint, matching the seed exactly. dag_collect_insert
keeps the existing behavior: synthetic collisions are errors (now unreachable
by construction), non-synthetic silent-drops are intentional de-dup of the
same canonical declaration reached from multiple resolution contexts.

With the identity-key collision eliminated:
- Switch compile-clean gate from --target rust to --target dag in
  dsl/tools/dsl_compile_clean_transport.dag (all 5 invocations + marker)
- Dissolve the SCAFFOLD annotation from DESIGN.md / design_document.dag

Co-authored-by: Brian Searls <briansrls@gunb.ai>
Co-authored-by: Claude Sonnet 4.6 <noreply@anthropic.com>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant