W2b (D-DCR-2b): one-hop field-map slices, rebased + reconciled with the #1127 census - #1128
Conversation
… split, with carrier and skeleton primitive Second-round operator ruling on the field map, recorded and built against: - The siting questions were a category error — asking where the map is written is asking where the OUs are in a distinguished name. An HHTL position is addressed by its path and every truncation of the path is itself an entry (NiblePath already ships parent/prefix/is_ancestor_of), so which-lane, versioned-vs-live and sweep-granularity all dissolve: the node at each prefix IS the row; rows are Lance-versioned because every row is; a sweep is scoped by a prefix at caller-chosen depth. - Every node is an SoA row; the three corpora differ only in how much of the tree has rows (books: not yet minted by DeepNSM-v2; rails without nodes: at least the hierarchy; OWL: parent/child almost always preserved). The load-bearing split: MECHANICAL hydration (mint the row at a nameable DN from the hierarchy — structure only) is distinguished from ORIGINAL causality predicates (dismech palette, Tarski-precise assertions, signed agreement lanes — epistemic, evidence-borne, never fabricated by a mint). A mint's epistemic output is exactly silence. Shipped, zero-dep, in contract: - basin_lanes::BasinLanes — the 24 x i4 reading of the node's own 12-byte register (fourth carving beside G6D2/G4D3/G3D4, the only signed one; reuses I4x32::sext4, now pub(crate), instead of a third nibble-codec copy). SILENT is the default and the zero register; is_silent() is the checkable half of the mint rule. The whale case holds at the carrier: a negative lane is recorded disagreement — countable, round-tripping, distinct from silence and agreement — and nothing else moves. - hhtl::missing_ancestors — the mechanical-hydration address list: every strict ancestor DN implied by the occupied paths that is not itself occupied, shallow-to-deep so parents mint before children, EMPTY ignored and never yielded. Returns addresses ONLY — the signature cannot carry a lane value, the type-level half of the split. The partial-hydration test is readiness state (c) exactly: basin + leaf occupied, only the gap returned. Still open as probes, not rulings: the lane-filling arithmetic (whether semiring.add is right for SIGNED agreement is unmeasured) and the provenance marker (mechanically-hydrated vs original). 1293 lib tests green; clippy -p lance-graph-contract --no-deps -D warnings clean; fmt clean. Plan sW2b updated; EPIPHANIES prepended; STATUS_BOARD row to In progress; supersession index regenerated last. Co-Authored-By: Claude Fable 5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01PFnYKqw6d7TTiB9cT8eFdK
…ildren Third-round operator ruling, recorded and built against: a parent's register expresses its DIRECT children accumulated — agreement AND disagreement — never the grandchildren. One hop up and down. Grandchild information reaches a grandparent only through the child's own accumulated register, so the field map is a composition of one-hop summaries (the tree-shaped Chapman-Kolmogorov discipline the substrate already holds in I-SUBSTRATE-MARKOV and FieldMask::inherit), and sweep convergence is settled structurally: bottom-up one-hop passes, each node a pure function of its direct children. Also ruled: the register width is a floor, not a cap — nibbles can be expanded, and a node further up may carry multiple 24 x i4 registers where valuable (mammal: accumulated agree/disagree; whale family: generic vs mammal-specific; whale: specific). Corpora ladder widened: book / redmine / odoo / AD (literally the DN case) / OWL / RDF — each landing in one of the three readiness states already tabled. Shipped, zero-dep, contract: - hhtl::direct_children — the one-hop selector: exactly depth+1, never grandchildren, EMPTY has no children, deduped, deterministic order. Any accumulator it feeds is structurally unable to reach past the children; locality is enforced at selection, not policed in arithmetic. - BasinLanes::accumulate_children — per-lane saturating signed sum (agreement stacks, disagreement pulls down, bound = the carrier's own range; empty -> SILENT). Locality observable across two levels: a grandchild move absorbed by the child's own saturation leaves the grandparent byte-identical; one that moves the child moves the grandparent. Measured limitation pinned loud, not hidden: in ONE register a balanced conflict (+3 vs -3 on a lane) sums to 0 — indistinguishable from silence. a_balanced_conflict_collapses_to_silence_in_one_register pins it as current behaviour and is the concrete case for the ruled multi-register expansion, whose semantics stay the operator's to shape. 1301 lib tests green; clippy -p lance-graph-contract --no-deps -D warnings clean; fmt clean. Plan sW2b third-round block; EPIPHANIES prepended; STATUS_BOARD updated; supersession index regenerated last. Co-Authored-By: Claude Fable 5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01PFnYKqw6d7TTiB9cT8eFdK
…guards Two of slice 2's own disable-runs PASSED, and each pass was a finding: - Stepwise saturating_add survived a wrapping_add disable because pack's clamp masked it — and worse, stepwise saturation makes accumulation ORDER-DEPENDENT for mixed signs ([+7,+7,-7] is 0 stepwise, 7 summed). One hop is a SET of children, not a sequence. Fixed: exact i32 sums, one clamp at pack — associative and commutative exactly. New falsifier accumulation_is_independent_of_child_order, verified failing against the stepwise implementation before it was replaced; the saturation behaviour stays falsifiable at its one home (disabling pack's clamp sign-flips it, verified red). - direct_children's explicit EMPTY early-return could never fire: is_ancestor_of already makes EMPTY an ancestor of nothing. Guard removed; the test pins the semantics through the API, wherever they live. Process note recorded by example: the first landing of this fix was eaten by running a disable-run's git checkout over uncommitted work — the exact trap the workspace notes warn about (commit first, then disable, then checkout). Re-applied and committed before any further disable cycle. 1302 lib tests green; clippy --no-deps -D warnings clean; fmt clean. Co-Authored-By: Claude Fable 5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01PFnYKqw6d7TTiB9cT8eFdK
…ctions, cross-refs #1125/#1126/#1127 merged while this branch's slices 1+2 were stranded; rebased onto main (commits kept per the merged-PR rule) and audited for overlap BEFORE re-pushing, so corrections and stranded work land together. Collisions corrected: - My "fourth carving / not in the shipped set / only signed one" claim was FALSE and the #1127 census had already proven it so: G24N4 ships as CausalWitnessFacet's loci reading of ValueTenant::CausalWitness. basin_lanes is re-positioned as what it actually is — the MAGNITUDE register in the shipped shape, exactly the sibling the census concluded must exist because that lane's operator-locked loci-never-magnitude law (plus reserved slots 16..24) forbids a child-summary there. Which tenant it occupies stays the operator's mint (append margin at slab 220, 260 B free). Module doc, both unpushed board entries, and the plan's RULED table corrected. - The plan's "which lane — dissolved" row conflated two axes: the DN ruling dissolves TREE-siting (the node at each prefix IS the row); the census constrains SLAB-siting (which tenant inside the 480-byte value), which is real, half-answered (not CausalWitness), operator's to mint. The row now says both. - The whale was pinned twice under two names — register-level in tests/w2b_one_node_field.rs (borrowed codec) and carrier-level in basin_lanes. Both kept, cross-referenced in both directions. Convergence kept as evidence, not deduped: w2b_one_node_field's summarise and accumulate_children arrived at the SAME per-lane shape (exact signed sum, one clamp) independently in two sessions — and it is what the one-hop ruling's "accumulated including disagreement" needs. Residue flagged, not fixed: the i4 sign-extension now has three homes (atoms::sext4, causal_witness inline, I4x64-via-I4x32); the dedup is a one-line follow-up, deliberately not bundled here. Full lance-graph-contract suite: 1378 passed / 0 failed (lib + every integration binary incl. w2b_one_node_field); clippy --no-deps -D warnings clean; fmt clean. EPIPHANIES audit entry prepended; STATUS_BOARD row merged (census + slices); supersession index regenerated last. Co-Authored-By: Claude Fable 5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01PFnYKqw6d7TTiB9cT8eFdK
Bugbot couldn't run - usage limit reachedBugbot is counted against Cursor usage for this user or team, and this run hit a usage or spend limit. A user or team admin can review and increase usage limits in the Cursor dashboard. (requestId: serverGenReqId_afae44ee-6f39-4b5a-80f8-ee92a0381cbe) |
There was a problem hiding this comment.
💡 Codex Review
Here are some automated review suggestions for this pull request.
Reviewed commit: 54c5a41883
ℹ️ About Codex in GitHub
Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you
- Open a pull request for review
- Mark a draft as ready
- Comment "@codex review".
If Codex has suggestions, it will comment; otherwise it will react with 👍.
Codex can also answer questions or update the PR. Try commenting "@codex address that feedback".
| let mut out: Vec<NiblePath> = occupied | ||
| .iter() | ||
| .copied() | ||
| .filter(|c| c.depth() == parent.depth() + 1 && parent.is_ancestor_of(*c)) | ||
| .collect(); |
There was a problem hiding this comment.
Index children before the bottom-up sweep
When the bottom-up field pass calls this selector for every occupied parent, each invocation scans the entire occupied slice to return at most 16 children, making a pass over N nodes O(N²). That is prohibitive for the repository's large HHTL datasets; build a parent-to-children index once, or change the API to consume pre-indexed candidates instead of rescanning all positions per node.
Useful? React with 👍 / 👎.
| if !occupied.contains(&parent) && !out.contains(&parent) { | ||
| out.push(parent); |
There was a problem hiding this comment.
Use set lookups while finding missing ancestors
For a large hydration input, every path visits up to 15 ancestors and performs linear searches through both occupied and the growing out vector, so generating the skeleton becomes quadratic rather than O(N·depth). Even book-sized inputs can require hundreds of millions of comparisons, while the documented 115M-node HHTL scale is infeasible; construct hash sets for occupied and already-emitted paths, then sort the result once.
Useful? React with 👍 / 👎.
| let mut out = [0i8; BASIN_LANES]; | ||
| for (o, a) in out.iter_mut().zip(acc.iter()) { | ||
| *o = (*a).clamp(-8, 7) as i8; | ||
| } | ||
| Self::pack(&out) |
There was a problem hiding this comment.
Do not promise associativity after clamping
Callers that combine partial accumulations or incrementally reduce child batches do not get the advertised associative merge because each intermediate BasinLanes has already been clamped. For example, accumulating [+7, +7, −7] in one call produces +7, while accumulating the first two and then merging −7 produces 0; this can make field results depend on batching or traversal strategy. Preserve an unclamped wider accumulator across reduction stages or document and enforce that all direct children must be supplied in one call.
Useful? React with 👍 / 👎.
| /// [`NiblePath::EMPTY`] entries in `occupied` are ignored (no route ⇒ no | ||
| /// implied ancestors), and `EMPTY` is never yielded — depth-0 is "not yet | ||
| /// routed", not a mintable position. | ||
| /// The DIRECT children of `parent` among `occupied` — exactly depth+1 |
There was a problem hiding this comment.
Attach hydration docs to the correct function
In generated API documentation, this uninterrupted doc-comment block attaches both the mechanical-hydration description and the child-selection description to direct_children, while missing_ancestors is left undocumented. Consumers therefore see direct_children described as returning missing ancestors and cannot find the intended contract on the hydration API; terminate the first block at missing_ancestors or move the function before the direct-child documentation.
Useful? React with 👍 / 👎.
…ung-ruling commit) Hygiene for three merged PRs plus the cherry-picked rung-per-classid plan commit that stranded at #1130's merge. Armed parity re-verified GREEN against OGAR main post-#296 (both directions, count pin 6). Co-Authored-By: Claude Fable 5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01PFnYKqw6d7TTiB9cT8eFdK
W2b (D-DCR-2b) slices 1+2, rebased past #1125/#1126/#1127 and reconciled
The four commits stranded when #1125 merged, rebased onto main (kept per the
merged-PR rule) plus a reconciliation audit against what #1126/#1127 landed in
parallel — run BEFORE re-pushing, so the corrections and the stranded work land
together instead of stale claims landing twice.
The rulings built against (three rounds, recorded in the plan)
the node at each prefix IS the row; rows are Lance-versioned because every
row is; a sweep is scoped by a prefix at caller-chosen depth.
the hierarchy alone (book TOC via DeepNSM-v2; redmine/odoo/AD; OWL/RDF);
original causality predicates are epistemic and never fabricated by a mint
— a mint's epistemic output is exactly silence.
accumulated, agreement AND disagreement, never the grandchildren. Width is
a floor: nibbles expandable, multiple 24×i4 registers further up where
valuable.
Shipped (zero-dep, contract)
basin_lanes::BasinLanes— the magnitude register in the shipped G24N4shape (
+agreement /−disagreement /0silence). Not a new shape:the W2b: the value-lane census and the one-node field falsifier (D-DCR-2b) #1127 census measured G24N4 already shipping as
CausalWitnessFacet'sloci reading — and that lane's operator-locked loci-never-magnitude law is
exactly why this sibling type must exist. Which
ValueTenantit occupiesstays the operator's mint (census: append margin at slab 220, 260 B free).
BasinLanes::accumulate_children— one-hop merge, exact i32 sums, oneclamp at pack (associative/commutative exactly; empty →
SILENT). Localityobservable across two levels: a grandchild move absorbed by the child's own
saturation leaves the grandparent byte-identical.
hhtl::missing_ancestors— the mechanical-hydration address list(shallow→deep, parents before children; addresses ONLY — the signature
cannot carry a lane value).
hhtl::direct_children— the one-hop selector: exactly depth+1, nevergrandchildren.
Reconciliation against #1126/#1127 (the audit commit)
the shipped set / the fourth carving / the only signed one" — the census
had already proven it false. Module doc, board entries and the plan's RULED
table fixed; the survey's stale sentence was already ⊘-annotated by W2b: the value-lane census and the one-node field falsifier (D-DCR-2b) #1127.
ruling) vs SLAB-siting real and census-constrained (not
CausalWitness;tenant mint = operator's).
w2b_one_node_field.rs, carrier-level here) — both kept, cross-referencedboth ways.
summarise(their test-local arithmetic)and
accumulate_childrenarrived at the same exact-sum-then-clamp shapeindependently.
(
atoms::sext4,causal_witnessinline,I4x64viaI4x32) — one-linededup follow-up.
Disable-runs
Six red under their named disables; two PASSED and each pass was a
finding, fixed: stepwise
saturating_addwas masked by pack's clamp ANDorder-dependent for mixed signs (
[+7,+7,−7]= 0 stepwise, 7 summed) —replaced with exact-sum-then-clamp plus an order-independence falsifier
verified red against the old body; and an EMPTY guard in
direct_childrenthat could never fire (
is_ancestor_ofalready carries the semantics) —removed.
Pinned loud
a_balanced_conflict_collapses_to_silence_in_one_register: in ONE register+3vs−3sums to0, indistinguishable from silence — the concrete casefor the ruled multi-register expansion, whose semantics are deliberately not
designed here.
Still open — operator's, surfaced not decided
ValueTenantmint for the magnitude register.Gates: full
lance-graph-contractsuite 1378 passed / 0 failed (lib +every integration binary incl.
w2b_one_node_field); clippy--no-deps -D warningsclean; fmt clean; supersession index regenerated last.Generated by Claude Code