Changes touching this path

  • day 0: loot hosts loot f4c30e75 · dbf3dbe6…
  • evidence: crew minted and verified (#86) 1fada823 · dbf3dbe6…diff
  • normalize working tree to LF: byte-stable co-located bridge (.gitattributes -text) e58fdda6 · dbf3dbe6…diff
  • a move becomes a recorded fact instead of a later guess, and the premise this ticket rested on was false: #98's object reuse is keyed by PATH, so a moved path is absent from the outgoing tree at its new key, falls through to put_sealed and gets a fresh address - the same object under a different key was not a fact waiting to be read off the tree, it had to be made true by extending the reuse across the move, and everything else follows from that. The rule is that a move is recorded only when the path's sealed object survives it, so a move whose content also changed in the same capture window shares no object, records nothing and is two rows, while a move and then an edit across two captures of one change composes and reads as one row saying the content also changed. Empty content and any ambiguity are refused for the same reason the whole design exists: zero bytes equal all zero bytes, and choosing between two vanished twins would make a signed fact depend on iteration order. On the boundary the render side compares nothing at all - resolve reads keys and never an address, a visibility or a byte, pinned by running it twice over trees that agree on every key and differ on every address at three unopenable tiers, with a positive control beside it so agreement is not evidence it answers nothing. The capture side compares once: it opens a vanished object with this identity's own keys, fail-closed so an unopenable object is never read or hashed, and pairs only against an addition at an identical visibility and publication tier, with the digest living for one call, never an address, never stored and never on the wire. What a relay newly learns is that two keys held equal ciphertext, which recording a move states in plaintext anyway since tree paths are plaintext at every tier, so it is inherent to the feature rather than the ADR 0004 oracle - written into that ADR rather than left in a message. Renames ride the label seam change_id and authored_at already use: covered by the finalize signature so a relay cannot rewrite a move, never folded into the version id so two peers reaching one tree by different routes still agree on its address, which is why every existing id and signature is unchanged and a v11 store reads with no move recorded. That was tested rather than argued, against a real store built by the shipped binary, where the old move still renders as a delete and an add in the same repo the new one renders as a rename, because inferring the old one would be the equality oracle arriving through the compatibility door. Three further things were wrong and are corrected rather than worked around: ADR 0019 says an additive change bumps the minor and has never described this project, since the minor is still zero and all five additive changes took the major; plan_moves own doc comment claimed the tier is checked before the digest, three lines above code that does the lookup first, when the property actually holds by the stronger route that nothing unopenable enters the index at all; and the empty-content refusal was written on both sides of the pairing, where each made the other unprovable and removing either left the test green - a duplicated guard is not belt and braces, it is two guards neither of which can be shown to be doing anything (#1539) 3c7e029b · dbf3dbe6…diff
  • the adr 0004 guard stops being a claim about a struct and becomes a question asked of the repo on disk: the pin it left asserts that no field of SealedObject is a function of plaintext, which stays green over a store that has the deleted digest back beside the struct, and that is measured rather than argued, since with DagRepo::put appending blake3 of the plaintext to a file in .loot the pin reports 1 passed and 0 failed while the new census reports 4 passed and 2 failed. plaintext_equality_census records two worlds through the same verbs, one with two paths holding the same bytes and one with them holding different bytes of the same length, builds each world four times, and refuses a persisted difference its readings can see between them: structure cancels because both worlds record the same tree, randomness is filtered by keeping only what every build of a world agrees on, and the wall clock is blanked by value, because adr 0043 stamps a second per version and a gap between two builds read red on that second alone. it walks the repo root rather than a named place, so relocation is the thing it is aimed at, and it is a lower bound and not a proof: a token shorter than its window, an index encrypted per build, and any write path the fixture does not run (a push, a pack, the mirror, the forge and the wire) are outside what it has looked at, which the new adr 0004 amendment states before a reader meets either guard. three oracles are planted as standing controls, one per reading, each the shape of a proposal that has actually been made. red under mutation, counts read each time: the sidecar planted in DagRepo::put (the census 4 passed and 2 failed, the struct pin 1 passed and 0 failed beside it), the value reading removed (5 passed and 1 failed), the shape reading stripped of its lengths (5 passed and 1 failed), the repetition reading removed (5 passed and 1 failed), the walk stopped from recursing (2 passed and 4 failed) and the two worlds made identical (3 passed and 3 failed). adr 0086 gains a pointer where it records the proposal this gap would have waved through, and CONTEXT.md says what the new reading reaches. no migration, no wire or format byte moves and no host behaviour moves, so this owes no deploy. the workspace suite is green (4092 passed over 131 binaries, 8 ignored) (#1894) 327f63f8 · dbf3dbe6…diff
  • adr 0004 is now asked of what a repo encodes to send as well as of what it persists: plaintext_equality_census gains a wire half, which keeps per build the payloads its sent function has the fixture repo encode through the public Workspace doors loot bundle and loot push call (the full bundle, the /stow batches a push to an empty host sends, closed at one object a batch so the first-batch delta framing runs, and the /ingest payload around the metadata-only declaration bundle), and takes the same value, shape and repetition readings over them between the equal and distinct worlds; nothing was exported for it, since the ticket premise that a bundle is unreachable from the test crate was wrong. a premise test opens every object the payloads carry with the key riding beside it and holds each world to the plaintexts it records, a moving-bytes control refuses payloads that never change between builds, and three oracles are planted on the wire: the deleted identity_hash itself, an address-only grouping and a per-build-salted digest. the wire is clean: nothing plaintext-derived was found. the repetition reading, shared with the store half, now counts occurrences of repeated windows rather than distinct ones, because the payloads repeat content and a chance collision merged two repeated windows and lowered the count the minimum keeps: at the distinct count the wire half read red in 4 of 25 runs, at the occurrence count 60 of 60 green. red under mutation, counts read each time: the bundle producer appending a domain-separated blake3 of each carried plaintext (census 11 passed and 2 failed, while engine bundle_carries_no_plaintext_equality_oracle reports 1 passed and 0 failed beside it), sent building nothing (8 and 5), the push batches carrying no object (12 and 1), the value reading removed (11 and 2), the shape reading removed (11 and 2), the repetition reading removed (11 and 2), each restored to green. the forge question is answered in the new adr 0004 amendment: /stow and /ingest decode the same Frame and /ingest takes encode_ingest_payload, so a forge input is what the wire half reads, while what a forge or relay keeps of it is its own store and is not asked; the engine pin doc scopes it to the one value it searches for, and CONTEXT.md names the wire half. no migration, no format byte, no wire byte and no published wording moves, so this owes no deploy. the workspace suite is green (4351 passed over 138 binaries, 12 ignored) (#2172) b98809ca · dbf3dbe6…diff
  • the review-sweep fix-up over #2303, #2159 and #2172. the wake-up sender: its client is built with no_proxy, so a proxy named in the environment is not used, pinned in a test binary of its own that sets the proxy variables and sees the request reach the pinned address and not the proxy; refused_wake_address now refuses every address that is not globally routable unicast, an ipv6 address carrying an ipv4 one (mapped, compatible, nat64 64:ff9b::/96, 6to4) judged by the one it carries, so 64:ff9b::a9fe:a9fe is refused, with the refused blocks copied from the iana special-purpose registries at the code and a table of example addresses pinning the rule; name resolution runs on a thread waited on for at most WAKE_TIMEOUT_SECS with the request given what is left, and the wake-ups in flight are bounded by MAX_WAKES_IN_FLIGHT, a resolver that outlives its wait keeping its place until it returns. the ingest kinds trailer is now a byte per head in head order, still absent when no head declares a kind, so each head is given jobs for its own kinds only and no job is made for a kind a head has no step of; the pre-2159 decoder still reads the new payload, the one-byte union shape was in no release, and neither format constant moves, pinned against the marker put_version writes rather than its digits. MetadataStore::ingest answers the jobs its commit wrote (store::Ingested) and a push wakes runners for those alone, so a triple a racing request filed first wakes nobody here; the proposal job half answers no error once the proposal is committed and logs instead. the job_cost no-kind pin now states the property, that the job half calls the store for nothing when nothing is declared, instead of a list of methods. the seek busy marker: one that does not parse is believed until its mtime is past the window, so the instant between its creation and its clock no longer admits two holders, and a marker that cannot be created for a reason other than one standing there is retried and then refused naming the state rather than counted as held; the held-marker comment is scoped to a round that claimed it. the census wire half plants each oracle into every payload sent builds and asks each payload for moving bytes, calls the now-public verbs::sync::forge_declaration instead of a copy, records that the fixture declares no kinds, and records the measured flake rate of its minimum reading (200 runs: 40 of 1600 store builds and 15 of 1600 wire builds above the floor, none red). false sentences fixed: jobs.rs says what a false proposal declaration costs the owner and what the trust floor does and does not stop, ADR 0091 section 7 and its 2159 amendment are corrected with a 2307 amendment and the reads-not-writes scope of the job cost measurement, ADR 0090 and ADR 0004 gain corrections, CONTEXT.md names the per-head trailer, the census module doc states the property instead of naming places, and an in_progress rewrap leftover is rewrapped. red under mutation, counts read each time, each restored to green: no_proxy dropped (0 passed and 1 failed), the 2159 refusal rule restored (2 and 2), embedded forms unrecognised (3 and 1), 6to4 unrecognised (3 and 1), the resolver thread not holding its place (0 and 1), the ceiling ignored (0 and 1), the resolve wait unbounded (0 and 1), the trailer encoding the union (25 and 2), the forge unioning kinds across heads (1 and 3), the memory ingest answering every handed job (4 and 2), the push waking for planned jobs (5 and 1), the proposal refusing after a failed job write (3 and 2), the job half reading with nothing declared (3 and 1), an unparseable marker read as idle (1 and 1), a failed create counted as held (1 and 1), the census reading the bundle alone (9 and 4), every payload a copy of the bundle (10 and 3), the ingest payload emptied (11 and 2). no migration, no format byte and no published wording moves; the forge binary changes, so the sender and per-head jobs are live once the forge is redeployed. the workspace suite is green (4360 passed over 138 binaries, 12 ignored), and green under bash ci/local.sh against Postgres 18 (#2307) 665b3cec · dbf3dbe6…diff

Renames are not followed. loot's tree maps a path to an address, so a rename is a delete and an add. This list is the history of the name, not of the bytes.