Changes touching this path
- every conflict-stopping verb gets a named way out, and building it corrected the ticket in both directions rather than just adding flags: merge does not stop on a conflict at all, since merge_tips records the triples and fold_onto then signs the merge node and materializes the merged tree, so an abort there is a view step off signed history rather than the forgetting of a stop; while cherry-pick, revert and squash do the opposite and return before writing anything of their own, so their stop leaves even the paths that merged cleanly unapplied. the five named verbs are also not the whole set: converge, pull, adopt and ferrys carry bounce reach the same fold and the same ingest, and the stale-disk settle files a conflict on the way past any capturing verb with no operation behind it at all, so the covered set is now a census rather than an assumption. the state is one position-owned artifact at .loot/position/in-progress carrying the verb, its operand, and the op-log index the view sat at before the verb ran, declared Refuse on malformed content because a torn record read as absent answers nothing to abort over a tree that really is mid-operation, which is the single failure the record exists to prevent. it is a real artifact rather than a derivation because conflicts-are-non-empty-and-the-newest-op-is-a-stopping-verb answers no the instant the last resolve lands, which is exactly when continue must still work. nothing here re-implements a rollback: the inventory row is Captured at ordinal 7, so abort is that one index handed to op restore, which already restores the view, re-materializes the tree, refuses over edits made after the stop, and appends the compensating operation the op-log criterion asked for; force is declared on the five verbs and refused without abort. continue closes the stop rather than replaying it, because the re-run was built first and measured to reproduce the identical conflict: these verbs are capture-first and a resolve on the pre-dock home position never writes the tree, so the closure states instead that the operation applied nothing. status and conflicts name the operation through one derivation, and the pin asserts the identical line in both (#1506)
21b9faf1 · dbf3dbe6… - three copies of one false sentence collapse into one statement the other five are pinned to: the help for cherry-pick and revert said --continue re-runs the operation while squash, apply and merge said it closes the stop three lines away, so the shipped help disagreed with ADR 0080 section 4, with resume::cont, and with itself, on exactly the two verbs whose re-run was built first and measured wrong. USAGE is a literal and there is no const concatenation, so the fact now lives once as resume::USAGE_NOTE and a new census asserts all five USAGE lines carry those bytes verbatim, which means a reword turns five red together where three hand-typed copies turned none; the comments in pick.rs and in_progress.rs now point at that statement instead of paraphrasing it. ere.rs cited the help of loot grep for a claim the help never made, so the sentence exists now as ere::HELP_NOTE and is pinned the same way: a dot matches one BYTE, and [:alpha:], \d, \b and \s are not implemented. the help for restore asserted that nothing ever recorded those bytes of every run, while the module it documents splits IRRECOVERABLE from OVERWRITTEN precisely because that is false under --source. item 5 was wrong twice: a stop cannot be the FIRST operation of a repo, because loot init records a genesis floor op, and the refusal is not an off-by-one either, since op_index answers 0 for an empty log, no operation 0 exists to hold a captured view, and the pre-operation pointer bytes were never snapshotted, so no other number reaches them. what is true is that .loot/ops is lane-owned and nothing plants a floor in a spawned lane, making the unabortable case an ordinary one: the first view-changing command an agent runs inside a fresh lane. so the refusal stands, the message now says that and names --continue, and it is pinned through a really spawned lane whose empty op log is the control. the ATTACHED census control is now derived from the census rather than kept as a second hand-written list, and resolves each censused group name to its canonical const so an empty group of the same name cannot satisfy it vacuously, proven by a mutation that leaves the census green and turns the control red on grep, the one attached leaf that had no control at all (#1799)
51aea3d1 · dbf3dbe6…diff - the branch and reorder forms land as FLAGS ON MOVE rather than as verbs of their own, and the branch form is a SELECTOR SUBSTITUTION rather than a second planner: branch_root walks the first-parent line and stops at the first node the destination already descends from, the change just below it becomes the source, and the ordinary plan_move decides everything else - so the branch form CANNOT DRIFT from the subtree form refusals, clash set or sealed-carry rule, because there is one planner under both. reorder is DELTA COMPOSITION: the moved manifest becomes anchor then lower-over-upper, the overtaken one anchor then lower then upper, which equals its old tree exactly when the two touch disjoint paths - which is WHY descendants are re-parented with their manifests UNTOUCHED - and the intersection of the two deltas is the clash set, decided from trees before anything is minted. a DEFECT IN WHAT LANDED AN HOUR AGO is fixed here rather than filed: loot move <finalized> --onto @ was NOT refused, because @ on a different fork passes every #1517 guard - not self, not a descendant, not the current parent, not a merge - so it would have minted SIGNED HISTORY PARENTED ON THE UNSIGNED WORKING CHANGE, a version no push, bundle or fetch carries. the repair is stated as a rule over the parent-to-child EDGES a restructure creates, asked of the DRAFT POINTER and never the signature, because a keyless repo signs nothing - so both forms and any seventh Refit inherit the refusal instead of each enumerating its own cases. AC1 was already satisfied by #1517 and is CITED rather than re-pinned, verified against move_onto live-descendant closure rather than taken on trust. non-adjacent insertion is REFUSED BY NAME rather than half-built, because inserting at an arbitrary point re-parents the line it lands in front of, which is the -r shape #1836 holds. fourteen pins, each reddened by a named mutation with the count read - including two draft pins that go red together, which is the census proving the rule sits on the edge rather than on the verb. and two prose censuses caught the USAGE text itself, where a -b inside a jj rebase citation tokenized as an undeclared flag (#1518)
066564a1 · dbf3dbe6…diff - loot resolve on the untracked home position now writes the resolved path to disk, and only that path, through the one-path settle a tip-tracking position already used, so the next capture no longer reads the pre-resolution bytes as an edit and loot new no longer signs a change that reverts the resolution. measured first in scratch repos on the home position, on a primary with a pinned tip and in a spawned lane: only the home position left the tree untouched, and on all three a re-run of the stopped revert over a tree showing the resolution still stops on the same path with the resolution as ours, because change_delta_merge runs its three-way without the settled ledger on purpose (#744). so --continue still closes rather than replays, ADR 0080 gains a #1798 amendment giving that reason, the resume module doc no longer names the tip-tracking arm as the one that skipped the write, and CONTEXT.md gives the reason too and names the stopping verbs by STOPPING rather than by a list that lacked apply-patch and move. the two new tests went red on the unchanged code (0 passed, 2 failed), the home-position test went red at its loot cat assertion with the disk assertion removed and at its sibling-edit assertion with the write widened to a whole-tree materialize (0 passed, 1 failed each), and the replay pin went red with the full ledger handed to the three-way (11 passed, 1 failed). the workspace suite is green (#1798)
31ffdf95 · dbf3dbe6…diff - loot resolve now refuses, naming the path, when the bytes on disk at the path it resolves differ both from the bytes recorded for it, in the change the disk mirrors or as the conflicts ours side, and from the resolution, so the one-path write #1798 gave every position no longer destroys an uncaptured edit to that file, while an in-place resolve still proceeds. the ours side is there because a home position with more than one head can mirror a head the disk does not show, which a ferry bounce test hit. spawned-binary tests on the home position and in a lane went red with the guard call removed (2 passed, 2 failed), the in-place pair went red with the resolution check removed (2 passed, 2 failed), and dropping the recorded check turned six resume tests red (10 passed, 6 failed). the line-ending land refusal now also refuses a NUL byte in the files it walks, which held none: a planted NUL went red before the change and with the check emptied (13 passed, 1 failed each). ADR 0080 scopes its ledger reason to revert and cherry-pick and records the guard, workflow.md and two skills say a format skew owes a relay and a forge redeploy and that the relay run needs the ALLOW_FORMAT_MAJOR_CHANGE override, and the sweep 9 citation, rationale, doc, long-line and short-line leftovers are fixed. the workspace suite is green (#1988)
a1bfdaa2 · dbf3dbe6…diff - loot resolve no longer refuses a delete/modify conflict that ours deleted: the #1988 guard reads a conflict record whose ours is its base as a deletion, so a disk with no file there matches it and a file written back there is still refused over, and on a shared primary its refusal names loot describe --allow-primary, the capture that works there. spawned-binary tests on a ferry-bounced two-head home position went red before the change for the ours-deleted resolve and the restored file (1 passed, 3 failed with the primary hint test), and with the deleted-ours arm removed (3 passed, 1 failed), with ours read as bytes whatever the record says (2 passed, 2 failed) and with a position-blind hint (3 passed, 1 failed). the implement brief now takes the job cap as a placeholder, keeps deploys inside the warrant and names SKILL.md, cites only what AGENTS.md says, says which commands need the lane position and gives the CR count and describe in PowerShell too; AGENTS.md gains the cargo fmt ban, ADR 0062 names the per-ticket safeguard that replaced the implement review, and the redeploy commands in workflow.md and diagnose-push-rejected name the new tag, scope the relay override to a forward bump and say the forge takes none, as the scripts repo reads them. ADR 0082 and apply-patch say the text deletion arm checks no preimage either (#1992) and pin that --check refuses a binary deletion the same way, the line-ending docs say CRLF and NUL, nul_offenders is private, and the sweep 10 wrap leftovers are fixed. the workspace suite is green (#1993)
7ecaa467 · dbf3dbe6…diff - a stop that will not be performed says so at the stop, and the promise #1518 AC4 made is restated as what holds. move, squash and the pick pair printed then loot <verb> --continue under their conflict lists and left the warning that the verb applied nothing to the closure, after the operator had resolved every path - reproduced through the spawned binary on a move --onto clash, where resolve then --continue closed the stop, C kept its version and its parent, and the signed resolution was the only new change. the advice is now resume::stop_advice, one sentence worded by applies_its_own_effect and reached from history.rs and pick.rs, so the stop and the closure read one table; whether a move or squash stop could resume stays the unmeasured question #1986 holds and is not decided here. the capture a restructure writes before its refusals is load-bearing, not merely early - @ names the draft the capture records and the working change travels with the line, read off the graph - so refused before anything is written is corrected to refused before anything of the restructure is minted in the AC4 pin, move_onto, reorder, CONTEXT.md and ADR 0080, and a new pin measures the cost: an uncaptured edit is the working change after a refused move, reorder or squash, and the signed graph is the graph the refusal found. measured too and recorded rather than changed: on a clean tree straight after loot new that same capture mints an empty working change that loot edit then refuses over, the #682 shape the snapshotted door gates and these wrappers bypass, which the machine-shape pins #1837 landed hold as the shipped carry. red first, three ways: the old sentence restored in stop_advice reddens the unit pin and both spawned pins (2 passed, 1 failed; 0 passed, 2 failed), the reorder stop keeping its own copy reddens only the reorder-squash-revert pin (3 passed, 0 failed; 1 passed, 1 failed), and the capture removed from move_onto reddens the cost pin on the assertion that measures it while the AC4 pin stays green (2 passed, 1 failed; 2 passed, 0 failed). no migration, no wire or format byte moves, and no forge or relay byte moves, so this owes no deploy. the workspace suite is green (3899 passed over 122 binaries, 7 ignored) (#1842)
7fd74d7b · dbf3dbe6…diff - every place that repeats a stop now says what --continue will and will not do, and an F row carries the role as it was signed. resume::continue_clause is the one wording, read through ways_out, once_resolved and stop_advice by the stops, by the in-progress note status and conflicts print (which said only --continue once loot conflicts is empty), by the wrong-verb refusal (which said --continue finishes it), by apply-patch (whose own copy never said its clean paths stay unwritten), and by the apply and merge stops, which now name both ways out without the disclaimer, the reason written at stop_advice. a census in resume.rs refuses a production line of loot-cli outside that module that spells --continue, USAGE lines carrying USAGE_NOTE excepted, and its first run caught the move --before USAGE line paraphrasing the note without its disclaimer, which every_stopping_verb_documents_one_resume_sentence misses because it reads one line per verb. the note fold carries each live record role as signed (loot_core::note::LiveNote), so notes show --json role is the signed bytes for a generation spelled +2 where it was re-encoded as 2; every other row byte is pinned unchanged through the spawned binary, ADR 0023 records the amendment, and Note::parse is not made stricter, since this repo lane held no records to measure and refusing would reclassify signed records held elsewhere. manifest prose names an attester through attestation_shape::attester_name, the naming its JSON used, so the own key stops printing as hex there; unprintable is one const in delta_shape; ADR 0066 says notes stands for notes show; the ChangeGraph insert doc states its rule instead of a caller list; Pathspec::matches names the crate-private policy items instead of linking them, which removes five cargo doc warnings. declined: compile_fail,E0624, measured inert on the pinned stable toolchain (a probe edited to E0599 stayed green) and honoured only under RUSTC_BOOTSTRAP=1, the reason written at the probe. red first: the new pins failed before the fix (resume 21 passed, 2 failed; attestation_machine_shape 3 passed, 1 failed; apply_patch 12 passed, 1 failed); with the fixes undone in two rounds, the in-progress note, apply-patch copy, apply advice, re-encoded role and hex naming redden the census (1267 passed, 1 failed), apply_patch (12 passed, 1 failed), attestation_machine_shape (2 passed, 2 failed) and resume (21 passed, 2 failed), and the fold re-encoding, the old wrong-verb sentence and the old merge sentence redden the codec pin (158 passed, 1 failed), the census (1267 passed, 1 failed), attestation_machine_shape (3 passed, 1 failed) and resume (22 passed, 1 failed). no migration, no wire or format byte moves, and no forge or relay byte moves, so this owes no deploy. the workspace suite ran 3917 tests over 122 binaries with 7 ignored, and all passed but concurrent_stage_of_same_address_does_not_tear, an os error 5 in untouched persist_codec code that passed on a loot-core rerun (637 passed) and three times alone (#2052)
d5fad7c8 · dbf3dbe6…diff - loot revert --continue and loot cherry-pick --continue now replay the stopped pick instead of closing the stop, on the answers loot resolve gave to that stop and on nothing else: the in-progress record gains the version the verb applies, the conflicts its stop recorded and the answers, resolve writes an answer there only when the conflict it settles is the one the stop recorded at that path, and change_delta_merge takes only the answers its caller hands in, none from an ordinary run, so the repo settled ledger is still never read by a pick (#744). a path whose content moved after it was answered is asked again rather than merged, a path holding the answer bytes at another address keeps it, a replay that stops again keeps the record restore point, and a record written before this closes as it always did. ADR 0080 gains the #1986 amendment deciding the three questions and recording, measured through the binary, that move, squash and apply-patch stop again after a resolve for reasons that are not a ledger and that apply and merge have nothing to replay; CONTEXT.md, the resume module and the usage note say the same. the resume runs to completion through the binary on the home position, on a pinned primary and in a lane. red under mutation, counts read each time: the repo ledger handed to the resume (0 passed, 1 failed in the stale-entry pin), the repo ledger handed to the three-way (0 and 1 in the loot-core pin, 0 and 1 in the re-run pin), a moved path left to the three-way (0 and 1), the address test alone (0 and 1 in loot-core, 0 and 1 through the binary), an answer keyed on the path alone (0 and 1), the record sentence worded by verb (0 and 1), the replay branch emptied (0 and 4), the re-stop taking a new restore point (0 and 1) and the usage note dropping revert (0 and 1), each restored to green. the record gains a trailing section, no format byte moves and there is no migration, so this owes no deploy. the workspace suite is green (4302 passed over 138 test binaries, 12 ignored) (#1986)
8bd8e53c · dbf3dbe6…diff - the review-sweep fix-up over #2287, #2283 and #1986. a resumed pick now asks again about a path its stop asked about when the record holds no answer for it, rather than handing it to the three-way, which merged over the resolution and put back the edit it rejected: change_delta_merge takes the stopped record whole and takes every question on it out of the three-way, keeping an answer only where the line still holds it, so a resolve that recorded no answer (a loot from before #1986, or a failed answer write, which the workspace comment now truthfully says costs a re-ask) re-stops with nothing applied, keeps the restore point, and lands once the question is answered again; refusing --continue was weighed and rejected in the ADR 0080 #2291 amendment, since nothing would be left to resolve. the replay reads its direction from pick::SPECS, which now pairs each spec with it, and a record naming a version under a verb SPECS does not hold refuses instead of replaying as a cherry-pick. the usage note names no verb, so each stopping verb line is true of its own verb, and its test now fails if the note names a verb that replays. a cherry-pick replay to completion is pinned through the binary on the home position, a pinned primary and a lane. false sentences fixed: the in-progress operand reader, the pick stop comment, the resume test doc link, the continue_clause list, the CONTEXT.md in-progress entry and HUNT-PERF on graph file reads; rewrap leftovers in fixture.rs and engine.rs are fixed, and the replaying tests keep their resolution file outside the working tree. red under mutation, counts read each time: questions taken from the answers alone (16 passed and 1 failed in the loot-core pin, 31 and 2 through the binary), an unknown verb replayed as not inverted (20 and 1), the note naming cherry-pick and revert again (19 and 2, the second the census the usage lines no longer matched), each restored to green. no migration and no format byte moves, so this owes no deploy. the workspace suite is green (4309 passed over 138 binaries, 12 ignored) (#2291)
812c48c7 · dbf3dbe6…diff - test scratch directories are named by one shared helper, common::scratch, from the process id and a per-process counter rather than the clock, so two tests asking for one tag at once are no longer handed one directory that the second caller empties and refills (the #2258 mechanism): 19 test files under crates/*/tests named a temp_dir path from SystemTime nanoseconds in 21 statements and now call fresh_dir or fresh_path, loot-cli files reaching it through mod common and loot-first exit_codes compiling the same std-only file by path, and revset_everywhere and plaintext_equality_census, which already counted, call it too. scratch_dirs.rs holds the #2258 pin, moved from revset_everywhere and aimed at the shared helper, red under the clock naming in 13 runs of 13 (0 passed and 1 failed, 1 to 16 of 400 directories handed twice), and a guard that walks every .rs file under crates/*/tests and refuses a temp_dir statement that reads the clock, red over the unconverted tree naming the 19 files (1 passed and 1 failed), red with buoy_exit put back (1 and 1) and red when the walk finds nothing (0 and 1), each restored green. no other test changes what it asserts. the workspace suite is green (4533 passed over 140 binaries, 13 ignored, from 4532 over 139: the guard is new and the pin moved into its own binary). test-only, so it owes no deploy (#2358)
6dd1e05b · 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.