Repository navigation
feat(verified): t27c run-record reads the receipts and judges one run (R2-4 tool half) - #7130
Conversation
|
All checks that got a runner pass (validate, parse-ratchet, and every non-required check). The only red/missing one is |
3723d2a to
5f981bf
Compare
|
Root cause of the missing |
3f46f4f to
4e34a1b
Compare
|
Third rebase: #7204 (#7148, |
…Closes #7072) R2-4 tool half, epic #6655. The rule half (specs/verified/run_record.t27, PR #7061) landed; this is the reader that applies it. t27c run-record <spec> reads every .trinity/receipts/<stem>-*.json whose spec names the given spec plus the spec's seals in .trinity/seals, collects the four facts -- count, every-receipt-complete by receipt.t27's six-field rule (unknown verdict word = absent), verdict words agreeing, every receipt's toolchain == its cited seal's built_by verbatim (R2-2; a receipt's own seal is the one whose gen_hash_verilog equals its seal_hash) -- and answers run_first_missing, run_complete, and verdict.t27's consumption point (incomplete run => INVALID_NO_RUN before any chain is read). Exit 0 = citable run, 1 = not, 2 = REFUSED (spec does not exist). Twelve fixture tests pin each exit path to run_record.t27's constants, including: unknown verdict word is INCOMPLETE (2), never WORDS_DISAGREE (3); a seal without built_by (every seal minted before #7076) matches no producer; a receipt citing a seal the spec does not hold is a producer mismatch; no receipts at all is TOO_FEW over zero, not a usage error; agreeing FAILs are one complete run (failure_loop owns the rest). Refs #6655, #7058, #7041, #7076. Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com>
…alue is not Ord (Refs #7072) Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com>
…7072) Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com>
…equest events (Refs #7072) The validate/parse-ratchet workflow runs were never created for b7226bd -- GitHub dropped the synchronize events while the runner fleet was starved. An empty commit re-fires them now that the queue is empty. Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com>
The dispatched parse-ratchet run cannot derive BASE_SHA (no pull_request context) and failed on that, leaving a blocking red check on the head; its concurrency group (cancel-in-progress) also cancels any real run for the ref. Only a fresh synchronize event produces a verdict -- this is that event. Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com>
Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com>
4e34a1b to
213a1f1
Compare
|
Fourth collision ( |
… the reference runs them (Closes #7239) (#7270) * t27b: float x*2^k, if as a struct literal field, defer, gf16::GF16 as the reference runs them - ExprBinary(f64 * 2^k): refused only where t27c's strength reduction reaches (top-level assign/local/return of a module-level fn, through binary ops). - ExprIf(left operand): a struct literal field value prints as `.f = v,`. - StmtExpr statement: `defer <stmt>;` is rendered to nothing by gen-zig (T43). - type gf16::GF16: the type mapper (#6533) maps the scoped path to u16; `@as(gf16::GF16, x)` and `*gf16::GF16` stay refused. Conformance specs first: specs/tri/t27b/conformance/float_mul_pow2.t27, struct_lit_if.t27, scope_exit.t27, scoped_gf16.t27. Rust under the owner's approval on #6063 (owner-approved-foreign). Closes #7239 Refs #6063 Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> * t27b lane 2: ledger moves and NOW entry for #7239 Measured on the t27b Railway lab, full corpus at --jobs 2: mismatch 0, reference disagree 0, crash 0, ratchet UNEXPECTED FAILURE 0. Master's ledger plus 8 moves to pass; pass 488 -> 496, not_pass and cap 48 -> 45. Closes #7239 Refs #6063 Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> * feat(automation): crm-duet v4 -- a dry run is free (Closes #6896) (#6897) * feat(automation): crm-duet v4 -- a dry run is free (Closes #6896) Owner, 2026-10-06 (translated): "a dry run must be free, change the spec". v3 kept only the story reel out of a dry run; every other paid tool was offered from seller turn 2, so a run that sends nothing still paid for generations. Now paid_tool_offered(seller_turn, dry_run) is false on every turn of a dry run, and paid_call_refused names the dispatcher's refusal (DRY_RUN_SPENDS = false, DRY_RUN_HIDES_PAID_TOOLS, DRY_RUN_REFUSES_PAID_CALL). A real run is unchanged. t27c test-report 20/20; negative control (the dry run offers paid tools again) fails 2. Census: shell `run: steps` 291 -> 292 (runner-named 270 -> 271) was already moved on master by a workflow step this PR does not touch; the pre-commit census gate asks for the re-bless in the next commit, so it rides here. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> * feat(automation): crm-duet v5 -- a paid tool is one with a price (Refs #6896) v4 hid only the six tools v1 named. The seller is offered the whole registry, and lipsync_generate, story_reel, split_reel and crm_voice_clone charge but were on no list, so a dry run still offered them. - tool_is_paid(price): price > 0; borrowed_price(own, borrowed): a tool that runs a priced tool is priced; priced_tool_offered(price, turn, dry_run) refuses every priced tool on every turn of a dry run. - PAID_TOOLS = 6 removed (PAID_TOOL_IS_PRICED, PAID_TOOLS_HAND_LIST = false): the host derives the set from its price table. - story_offered calls paid_tool_offered: duplicate-bodies grouped the two identical bodies. t27c test-report 21/21; negative control (priced_tool_offered ignoring dry_run) fails the new test. Seal re-saved, verify MATCH. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> --------- Co-authored-by: Claude Opus 5.5 <noreply@anthropic.com> * feat(verified): t27c run-record reads the receipts and judges one run (R2-4 tool half) (#7130) * feat(verified): t27c run-record reads the receipts and judges one run (Closes #7072) R2-4 tool half, epic #6655. The rule half (specs/verified/run_record.t27, PR #7061) landed; this is the reader that applies it. t27c run-record <spec> reads every .trinity/receipts/<stem>-*.json whose spec names the given spec plus the spec's seals in .trinity/seals, collects the four facts -- count, every-receipt-complete by receipt.t27's six-field rule (unknown verdict word = absent), verdict words agreeing, every receipt's toolchain == its cited seal's built_by verbatim (R2-2; a receipt's own seal is the one whose gen_hash_verilog equals its seal_hash) -- and answers run_first_missing, run_complete, and verdict.t27's consumption point (incomplete run => INVALID_NO_RUN before any chain is read). Exit 0 = citable run, 1 = not, 2 = REFUSED (spec does not exist). Twelve fixture tests pin each exit path to run_record.t27's constants, including: unknown verdict word is INCOMPLETE (2), never WORDS_DISAGREE (3); a seal without built_by (every seal minted before #7076) matches no producer; a receipt citing a seal the spec does not hold is a producer mismatch; no receipts at all is TOO_FEW over zero, not a usage error; agreeing FAILs are one complete run (failure_loop owns the rest). Refs #6655, #7058, #7041, #7076. Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com> * fix: sort the receipt and seal listings by file name -- serde_json::Value is not Ord (Refs #7072) Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com> * test: pin that disagreement (3) is judged before producers (4) (Refs #7072) Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com> * chore: resync the PR head after a queue jam that swallowed the pull_request events (Refs #7072) The validate/parse-ratchet workflow runs were never created for b7226bd -- GitHub dropped the synchronize events while the runner fleet was starved. An empty commit re-fires them now that the queue is empty. Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com> * chore: re-fire the pull_request gates (Refs #7072) The dispatched parse-ratchet run cannot derive BASE_SHA (no pull_request context) and failed on that, leaving a blocking red check on the head; its concurrency group (cancel-in-progress) also cancels any real run for the ref. Only a fresh synchronize event produces a verdict -- this is that event. Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com> * docs: say the exit-code contract in the reader test header (Refs #7072) Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com> --------- Co-authored-by: Claude Opus 5.5 (1M context) <noreply@anthropic.com> * t27b: unreached fns may name an unlayable struct; float as casts spelled like gen-zig (Closes #7175 #7179) (#7216) * Port gHashTag/trios:crates/trios-cli/src/lock.rs to specs/port/trios/crates/trios-cli/src/lock.t27 - Implement lock_file_path() function - Implement LockGuard_acquire() function with undefined body - Implement LockGuard_try_acquire() function with undefined body - Implement LockGuard_is_lock_stale() function with undefined body - Implement LockGuard_drop() function with undefined body - Add 5 test cases covering basic functionality - All tests pass with 0 BLOCKED Closes #5673 * Port training state management (train_state) to .t27 Port of gHashTag/trios crates/trios-train-cpu/src/bin/train_state.rs (8b229e9489ee) to specs/port/trios/crates/trios-train-cpu/src/bin/train_state.t27 (module port::trios::crates::trios_train_cpu::src::bin). - OptKind enum (AdamW, Muon); Config, OptWrapper, TrainingState structs. - All four ported functions keep real bodies (no undefined stubs): OptWrapper_adamw (wraps AdamW, casts wd to f64), OptWrapper_muon (hardcodes momentum 0.95, stores lr), OptWrapper_step (dispatches by tag; AdamW takes lr per call and never stores it, Muon stores lr before stepping), and init_training (make_opt per slot, sizes VOCAB*DIM / HIDDEN*DIM / VOCAB*HIDDEN, EMA ramp 0.996 -> 1.0 over cfg.steps, f32::MAX sentinel for best_val_bpb). - Mapping notes: the Rust enum-with-payload OptWrapper becomes a tag struct; Option<JepaPredictor>/Option<NcaObjective> become presence flags; the Vec of NUM_CTX identical ctx wrappers becomes one representative plus count; Instant::now() becomes a caller-passed now parameter. World-touching code (optimizer math, models, predictor, NCA objective, clock) is caller-driven plumbing, so the structs carry only what the decisions read or produce. - 7 tests with field-by-field asserts (struct == is not supported for OptWrapper): constructor parameters, switch dispatch and lr handoff, make_opt config following, init_training defaults and muon/jepa/nca configs, f32::MAX sentinel. t27c parse: 0 errors; typecheck: 0 errors / 0 warnings; test-report: 7 pass / 0 FAIL, no BLOCKED; gen: 0 'not yet implemented'; spec-status: IMPLEMENTED. Closes #5659 * docs: the coordination entry this branch needs to land A pull request must add exactly one docs/now entry and a bee has no way to know that: its brief names a boundary file and acceptance criteria, and docs/now/ is neither. The publisher adds it rather than failing the gate. Closes #5659 Co-Authored-By: Claude Opus 5 <noreply@anthropic.com> * docs: the coordination entry this branch needs to land A pull request must add exactly one docs/now entry and a bee has no way to know that: its brief names a boundary file and acceptance criteria, and docs/now/ is neither. The publisher adds it rather than failing the gate. Closes #5673 Co-Authored-By: Claude Opus 5 <noreply@anthropic.com> * t27b: conformance spec for a fn no test reaches whose signature names an unlayable struct (Refs #7175) Refs #6063. Dogfood spec first: specs/tri/t27b/conformance/unresolved_signature.t27 has a struct that holds itself by value. Only fns that no test reaches name it: as a parameter, as a result, and through a call to another such fn. This mirrors specs/compiler/optimizer.t27. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> * t27b: conformance spec for a float operand cast with as (Refs #7175) Refs #6063 Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> * t27b: unresolved signatures of unreached fns; float as casts spelled like gen-zig (Refs #7175 #7179) Refs #6063 Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> * fix(tri mutate): a hang and a mutant zig rejects are no longer kills (Closes #7148) (#7204) * fix(tri mutate): a hang and a mutant zig rejects are no longer kills (Closes #7148) `tri mutate spec` ran `t27c gen` + `zig test` under one clock and called every non-zero exit a kill, so a hang and a compile error both raised "killed" and neither was listed by line. On one probe spec (lab, zig 0.16.0, same t27c, back to back) master printed "22 of 24 killed (20 by `zig test`, 0 by a gen failure, 2 by a hang)"; this prints "17 of 24 killed (10 by a failing test, 7 by an invariant at compile time); 2 survived, 3 hung, 2 unviable", each of the 7 listed by line. - Three steps, each on its own --timeout clock: `t27c gen`, `zig test --test-no-exec`, then the test binary. Only the test run outliving its clock is a HANG; gen or the compile outliving it is the machine's load and the mutant is NOT RUN (unclebob/mutator issue 1's defect). - A compile error with zig's "called at comptime here" note is an invariant the mutant broke (t27c lowers invariants to comptime): a kill. "evaluation exceeded ... backwards branches" is comptime's own timeout: a HANG. Any other compile error is UNVIABLE. - The issue's "a parameter left unused fails to compile" is wrong: t27c emits `_ = a;` and `_ = &i;`, so such a mutant compiles. The UNVIABLE test uses a type error. - 9 new tests (34, was 25); 6 run zig on lowered fixtures. Five hand-made regressions each turn a named test red. - cli-tri installs zig 0.16.0 before `cargo test -p tri`. Census: `shell` moved 300 -> 301 run: steps (279 -> 280 whose shell the runner names), the new "Install zig" step; re-blessed here, master's pins pass at the base. The workflow edit is in tools/policy/foreign-exceptions.txt. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> * fix(tri mutate): mutants live beside the spec's specs/, so a spec with `use` can be mutated (Refs #7148) t27c resolves `use a::b;` by walking up from the spec file for a `specs/` directory (bootstrap/src/use_resolve.rs, find_specs_root). The copies sat in the system temp dir, which has none, so t27c dropped every import and still exited 0 (#7176). zig then failed the unmutated copy of specs/policy/l2_generation.t27 with "use of undeclared identifier 'LIST_END'", and the tool could not mutate any spec that imports anything. The work dir is now `target/tri-mutate-spec-PID` beside the spec's `specs/`, where the same walk from a copy reaches the spec's own tree. A spec with no `specs/` above it keeps the temp dir. Measured on the Railway lab, default TMPDIR, `--fn diff_kind`: - the previous commit's tri: Unviable("zig: error: use of undeclared identifier 'LIST_END'"); - this commit: "3 of 3 killed (3 by a failing test, 0 by an invariant at compile time); 0 survived, 0 hung, 0 unviable." New test a_copy_in_the_work_dir_resolves_use_against_the_specs_own_tree (35 in mutate::tests; `cargo test -p tri mutate` on the lab: 35 passed). With the work dir put back in the temp dir it fails (left /tmp/tri-mutate-spec-7, right .../r/target/tri-mutate-spec-7). Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> --------- Co-authored-by: Claude Opus 5.5 <noreply@anthropic.com> * fix(port): railway_deployment_create.t27 generates Verilog again (Closes #7228) (#7240) The spec built argv as local [N][]const u8 arrays in its tests, a 2-D aggregate gen-verilog does not lower (W469). That made master's corpus ratchet red since fed07cd (PR #6956). Rewritten in the shape of railway_null_startcmd.t27: decide_args(argc), decide_response(stdout) with a byte-level port of std.mem.indexOf, and main left as plumbing. The original only reads args.len and the "errors" field of curl's stdout, so nothing it decides on is lost. 14 tests, all executing runtime asserts on the lab (test-report 14/14, 0 vacuous). Co-authored-by: Claude Opus 5.5 <noreply@anthropic.com> * t27b: module-level constants that hold an optional (Closes #7116) (#7202) * spec(t27b): conformance spec for module-level optional constants (Closes #7116) Refs #6063. specs/tri/t27b/conformance/const_optional.t27: `?T` constants alone, copied from another, as struct fields beside a `str`, from a field default, and a present zero. The reference gives 4 pass. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> * t27b: module-level constants that hold an optional (Closes #7116) Refs #6063. `const_fill` lays out `?T` as `opt_temp` does: the payload, then the has-value flag. `null` leaves both zero, and another optional constant is copied byte for byte. `const_elem` and the module-level constant path reach it through `rodata`. An optional holding a `str` stays refused as `ConstDecl(?T)`. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> * t27b ledger: parse_conform.t27 and const_optional.t27 pass (Closes #7116) Module-level optional constants unblock parse_conform.t27. Not-pass goes from 50 to 49. NOW entry added. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> * spec(t27b): rename the const_optional row struct to OptionalRow so tri types ratchet stays clean (Closes #7116) Row already has a definition elsewhere in specs/, and the Corpus ratchet's type-conflict ledger counted the new one as a NEW conflict. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> --------- Co-authored-by: Claude Opus 5.5 <noreply@anthropic.com> * fix(specs): six vacuous wave tests and a trapping sign extension (#7246) Closes #7225. Closes #6560. specs/port/scripts/gen_w38{1,2,4,5,6,7}.t27: wave_constants_follow_each_other asserted two constants, which fold at compile time, so it passed with 0 runtime asserts. It now calls next_wave(EXPECTED_LAST_WAVE). specs/isa/tri27_machine.t27: ld_sign_extend read (word as i32) as i64, which the Zig backend narrows with a range-checked @intcast, so words above 2^31 - 1 trap and one test failed. It is written as arithmetic now. The seal is re-saved (10 of 10 tests) and the file leaves tools/seal_baseline.txt. test-report: the six ports 7/7 with 0 vacuous, tri27_machine 10/10. Co-authored-by: Claude Sonnet 5.5 <noreply@anthropic.com> --------- Co-authored-by: Trinity Bee <bee@trinity.local> Co-authored-by: queen-publisher[bot] <noreply@anthropic.com> Co-authored-by: github-actions[bot] <41898282+github-actions[bot]@users.noreply.github.com> Co-authored-by: Dmitrii Fedorov <dmitrii.f@t27.ai> * t27c: name each unresolved `use`; item and brace imports splice from their module (Refs #7176) (#7242) * t27c: name each `use` the splice finds no spec for (Refs #7176) A `use a::b;` whose specs/a/b.t27 does not exist was skipped silently and `gen` exited 0; the first sign was a later "undeclared identifier" in some other tool's output (#7148 met it in a temp-dir copy). typecheck_gate, which each of the 10 gen paths calls once, now prints one stderr line per such `use`: file, line, path and why (no spec; no specs/ directory above the file; a brace list, #2537; one item of a module whose file exists, #5552). The splice and the note share use_path_expr and use_path, so they read the same lines the same way. A warning, not an error: the tracked corpus has 182 such lines in 106 files (112 no spec, 54 items of a module, 16 brace lists, 0 outside specs/), and a qualified reference still makes the zig backend emit @import with no spec to splice (tests/dotted_module_name.rs). The error is #7176's next step. Lab, master 403b27f vs this branch, `gen` on all 1484 tracked .t27 files: stdout differs on 0, exit code on 0, other stderr on 0; 182 new lines. Unit 32/32, CLI unresolved_use 2/2, dotted_module_name and unknown_type green. Negative controls: the gate loop removed -> the CLI test fails; missing_uses returning nothing -> 4 unit tests and the CLI test fail. Foreign Rust under the owner's standing rule (owner-approved-foreign), listed in tools/policy/foreign-exceptions.txt; compiler.rs untouched. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> * fix(t27c): item and brace imports splice from their module; three splice defects (Refs #7176) `use a::b::{X, Y};` and `use a::b::Item;` (when specs/a/b/Item.t27 is not a spec) now splice from specs/a/b.t27, one level up only, as Rust names the module that holds the items. The #7176 warnings drop from 182 to 119, in 70 files (Refs #2537, Refs #5552). The corpus A/B on the Railway lab found three defects of the splice that predate this change, each made visible by a module the item imports now splice: - the importer's own names came from the smallest indent of any declaration; they now come from brace depth (spi_tb gained a second spi_transfer; property_test_template a duplicated DifferentialCase); - a declaration ended at the first line whose {} and [] depth was 0, so a header split over lines was its first line alone (mac_tb); the () depth counts now, and hslm's fall-back note is gone; - a char literal '"' was read as a string start and hid the rest of its line; with the () depth that dropped verdict, put and put_msg from the output of ci/affected and policy/l2_generation in the first lab run. Char literals and `;` prose lines are read as such. Explicit-item precedence over a glob was tried and reverted: the pulled declarations' qualifiers are not rewritten (#7215). specs/neural/forward_pass.t27: 42 call lines realigned with vsa_core's arities; both seals resealed (#7203: seals hash the unspliced source). Measured, commit 1 vs this one, 1484 files x gen/gen-c/gen-rust/gen-verilog: exit changes on 0; output changes on 17 specs; zig on the 17: none goes from pass to fail; 13 of 15 tracked gen/ copies byte-identical under both (gf16 differs from both, #6996). 38 unit tests (32 before); negative controls for the paren depth and the char literals turn named tests red. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> --------- Co-authored-by: Claude Opus 5.5 <noreply@anthropic.com> * t27b: `const Name = T;` is a type alias (Closes #7241) (#7282) * spec(t27b): type_alias conformance spec -- const Name = T is a Zig type alias (Closes #7241) Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> * feat(t27b): const Name = T with no annotation is a type alias wherever a type is read (Closes #7241) A module constant whose value is a bare name that spells a type (a scalar, str, [N]T, ?T, *T, a declared struct or enum, or another such alias) now resolves as that type in lty and ty, and is not lowered as a value. An alias cycle, an alias of a type t27b does not model, and an alias read as a value stay refused. Rust edit under the owner's approval on #6063 (label owner-approved-foreign); files listed in tools/policy/foreign-exceptions.txt. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> * fix(t27b): a type alias counts only in Zig spellings -- str and [N]str are refused (Closes #7241) The reference prints alias text into Zig verbatim, so str / string name nothing there; [N]T counts only when T spells a type. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> * fix(t27b): a struct literal of a scalar alias is refused, not recursed into (Closes #7241) const Duo = u8; Duo{ .lo = 3 } made expr -> struct_temp -> init -> expr_as -> expr loop until the stack overflowed (found by mutant m8 on the lab). Zig refuses it too: 'type u8 does not support struct initialization syntax'. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> * ledger(t27b): type alias moves; NOW entry (Closes #7241) zig_primitive_bindings and the new type_alias spec move to pass; gfternary now stops at ExprCall(@setEvalBranchQuota). The doc comment of lit_type, displaced by struct_lit_ty, goes back above it (comment only). Refs #6063 Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> --------- Co-authored-by: Claude Opus 5.5 <noreply@anthropic.com> * specs: `use` lines name a spec by its path; drop lines that splice nothing (Refs #7191) (#7291) * specs: drop 33 `use` lines that splice nothing (Refs #7191) 33 import lines in 29 specs named no spec t27c could splice and no name the spec reads. Each one left a mark in t27c's own zig output on master: `// use X: no references in this module` (14), or a second `const std = @import("std.zig");` beside the backend's own std import (19), which zig rejects as "duplicate struct member name 'std'". So `use std;` is not a harmless import of an implicit library, as in Rust; in t27 it breaks the zig build. Measured on the Railway lab, 403b27f against this change, on the 29 files, gen/gen-c/gen-rust/gen-verilog under the master binary and the #7176 slice-2 binary: - exit code changes on 0 of 232 runs; - gen-c, gen-rust, gen-verilog output byte-identical; - `gen` loses exactly the 33 lines above and the 19 blank lines after the std imports; - zig test 0.16.0: none goes pass -> fail; 4 pass both ways; 12 move past the duplicate std to their next error; - #7176 warnings on these files: 37 -> 4. Seals: the 28 sealed specs resealed with a clean release build of 403b27f (no bootstrap change on master since); its output equals the A/B binary's on all 232 runs. 58 seal files change: spec_hash, gen_hash_zig, sealed_at, the test record; no gen_hash_c/rust/verilog change. All 28 print "all hashes MATCH". The unsealed specs/port/tools/rename_duplicate_tests.t27 gets no seal. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> * specs: a `use` names the spec's path, not its module name; drop `use tritype-base::usize` (Refs #7191) t27c resolves `use a::b::Item;` by path (specs/a/b.t27). 24 import lines in 13 specs named a spec by its declared module name instead (bus-schema, lsp-schema, provider-schema, config-schema, sync-schema, runtime-process), which is not a path: nothing was spliced. Each now names the path (bus::schema, ...). 8 `use tritype-base::usize;` lines are deleted: specs/base/types.t27 declares no usize; it is a builtin. Measured on the Railway lab, 403b27f plus slice 1 against this change, all 1356 specs under the #7176 build (PR #7242): - gen/gen-c/gen-rust/gen-verilog exit codes: 0 of 4 x 1356 change; output changes only in the 13 edited files; - #7176 warnings 84 -> 52; parse/typecheck failures 0 -> 0; - test-report: 13 blocked before and after; 6 move to the `&.{ _ }` lowering error, config/load to its own `config_schema::` body references (6 names, 22 uses), 6 keep their error; - iverilog: config/load 9 -> 11, provider/transform 21 -> 28, none in the elaboration ratchet. Seals: 13 resealed, 26 files. gen_hash_zig changes on the 8 that lose the tritype-base line; no c/rust/verilog hash changes. A seal hashes the spec's own output before any splice, so master's t27c and the #7176 build both print "all hashes MATCH" on all 13; only the lsp/client and lsp/server test records come from the #7176 build. Lands after #7242. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> * specs: seven more `use` lines name a spec's path; drop `use tritype::base` (Refs #7191) Third slice of #7191, measured on the Railway lab with the #7176 build (PR #7242), all 1356 specs, gen / gen-c / gen-rust / gen-verilog. - 6 lines named a module name or bare file name (`tritype-base`, `tritype`, `core`) and now name the path (`base::types::...`, `test_framework::core::{...}`). - 2 brace lists took GF16 and GF32 from `numeric::golden_float`, which is no spec; each is now `use numeric::gf16::GF16;` and `use numeric::gf32::GF32;`. - `use tritype::base;` in relay_observer is deleted (nothing reads it). Exit codes unchanged on all 4 x 1356 runs; output changes only in the edited files (gen 7, gen-c 6, gen-rust 6, gen-verilog 1); #7176 warnings 52 -> 43. All 7 stay blocked in test-report; bigint, hybrid_bigint and runner now reach the import/splice collision filed as #7281 (0 specs before, 3 after). 15 seals resealed; master's t27c and the #7176 build both verify all 7. forward_pass.t27 waits for #7242. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> * specs: forward_pass names base::types for Trit, held back until #7242 (Refs #7191) `use tritype::Trit;` named no spec. It now reads `use base::types::Trit;`, the same edit the third slice made in six other specs. It waited for #7242, which rewrote this spec's calls and resealed it. Measured on the Railway lab with the #7242 build, master df00ec4 plus this branch: the #7176 warning on the line goes away under gen, gen-c, gen-rust and gen-verilog, and all four outputs are byte-identical before and after. test-report blocks on the same zig error ("expected ']', found ';'") before and after. Resealed on the lab: the two seal files change only in spec_hash and in the temp-dir name inside tests.blocked. seal --verify prints "all hashes MATCH" on the 46 changed specs that have a seal (of 47; specs/port/tools/rename_duplicate_tests.t27 has none on master either), with the #7242 build and the old master build. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> --------- Co-authored-by: Claude Opus 5.5 <noreply@anthropic.com> * t27b: `void` as a parameter, field and pointee type (Closes #7267) (#7296) * t27b: lower void as a parameter, field and pointee type (Closes #7267) `void` outside a fn result is Zig's zero-bit type: a struct with no fields and size 0. Fields around it keep their own offsets, an array of structs holding one keeps its stride, and `alloc: void` / `p: *void` parameters take `undefined` and `&s.field`. A `void` result still means no value. Conformance spec: specs/tri/t27b/conformance/type_void.t27. Refs #6063 Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> * t27b: undefined as a void argument; refuse ?void (Closes #7267) `f(undefined, ..)` for a `void` parameter is that parameter's one value and now lowers to an empty temporary. `?void` is refused as `type ?void`: its only non-null value is `undefined`, which Zig turns into an undefined optional, null flag included, so t27b's JIT and interpreter read never-written bytes there. Refs #6063 Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> * ledger(t27b): type void moves; NOW entry (Closes #7267) background_agent/main.t27 and the new type_void spec move to pass; gen_softmax now stops at ExprCall(@exp). Refs #6063 Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> * chore(t27b): foreign-exceptions block for #7267; ledger counts after the master merge (Closes #7267) The type-void edit to lower.rs gets its own approval block, as the other lane-1 PRs do. The ledger counts are recomputed from the entries after merging origin/master. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> --------- Co-authored-by: Claude Opus 5.5 <noreply@anthropic.com> * fix(specs): delete 16 dead use lines, take PHI from math::constants (Refs #7191) (#7298) Fourth slice of #7191. - 16 `use` lines in 12 specs named no spec (the #7176 warning), and no body reads what they name. Before this change the Zig backend lowered all 16 as `// use X: no references in this module`. - `use base::constants::PHI;` in specs/memory/formula_embed.t27 and specs/memory/semantic_search.t27 now reads `use math::constants::PHI;`, which t27c splices. The splice also brings `abs`, and in formula_embed `pow` with `floor`, `exp_approx` and `E`; `pow` is reached through a false reference to the builtin `@pow` (#7292). - Two comments that described a deleted line are corrected. Measured on the Railway lab with the #7242 build, on all 1363 specs, under gen, gen-c, gen-rust and gen-verilog: - the exit code changes on none of the 4 x 1363 runs; - output changes only in edited files (gen 12, gen-c 3, gen-rust 2, gen-verilog 1); - #7176 warnings drop from 42 to 24 under each backend; - parse and typecheck exit 0 on all 12, before and after. Seals: the 10 sealed specs resealed on the lab; 17 seal files change. Master's t27c and the #7242 build both print "all hashes MATCH" on all 10. Co-authored-by: Claude Opus 5.5 <noreply@anthropic.com> * verified: R2-5 capstone -- ternary_link run citation, silicon-proven end to end (Closes #7177) (#7293) * verified: R2-5 capstone -- the ternary_link run citation, read off the XC7A200T bench (Closes #7177, Refs #6655) Three placements of specs/fpga/ternary_link.t27 (pnr seeds 1, 7, 42) on the QMTech Wukong V1: every placement wrong-part-bracketed, Done=1 on our bitstream, full IDCODE 0x3636093 read live, verdict 0xa5a532bf ok=1 -- the same word Phase H read. Each run wrote a complete receipt (six fields, seeds carried, seal_hash = the seal's gen_hash_verilog, toolchain = the seal's built_by t27c-bootstrap@0.4.0+df00ec428). t27c run-record judges the set: RUN_MISSING_NONE, Run complete: yes, citable, exit 0. specs/verified/ternary_link_run.t27 is the verdict record citing that run through verdict_run_reference -- the R2-4 consumption point -- with every run fact pinned load-bearing, including the seedless fourth placement the reader refused (RUN_RECEIPT_INCOMPLETE) and the run redone seeded. Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com> * verified: fold the last in-body comment above its test -- the lexer trap, hit a fourth time (Refs #7177) Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com> * verified: seal the capstone run citation (Refs #7177) Minted on the Railway lab from this branch; seal --verify reads all hashes MATCH. built_by t27c-bootstrap@0.4.0+339c0443f. Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com> --------- Co-authored-by: Dmitrii Vasilev <playra@users.noreply.github.com> Co-authored-by: Claude Opus 5.5 (1M context) <noreply@anthropic.com> * t27b: a text-form array literal repeated with ** lowers like the reference (Closes #7112) (#7161) * spec(t27b): conformance spec for text-form array repeats (Closes #7112) Refs #6063. `[1] ** 100`, `[a, b] ** n` and `[K, f()] ** 2` as the reference runs them: t27c's Zig backend pastes the element text back as `.{ ... } ** n`, so each element is evaluated once and the list repeated. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> * t27b: a text-form array literal repeated with ** (Closes #7112) Refs #6063. `repeat_lit` parses the left operand of `**` back into its elements with `text_lit` when the parser kept them as text, which is how the reference pastes them (`.{ 1 } ** n`). An empty `[] ** n` stays refused, and the element checks of `text_elem` apply unchanged. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> * t27b: text-form repeat tests use sources the reference accepts (Closes #7112) Refs #6063. `text_form_repeats` passed arrays to a `[u32]` slice parameter, which the reference refuses (it needs `&`); the test now reads elements directly. The `[v + 1] ** 2` rejection case is dropped: `[v + 1]` is parsed with children, not as text, and both the reference and t27b accept it. Checked on the lab: reference 2 pass + 1 FAIL, t27b the same. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> * t27b ledger: transport.t27 and array_repeat_text.t27 pass (Closes #7112) Refs #6063. `clade-meshd/src/transport.t27` and the new conformance spec move to pass; `gen_fuzz.t27` now stops at `ExprCall(@intcast)`. Not-pass 51 -> 50. NOW entry docs/now/2026-10-06-t27b-array-repeat.md. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> --------- Co-authored-by: Claude Opus 5.5 <noreply@anthropic.com> --------- Co-authored-by: Claude Opus 5.5 <noreply@anthropic.com> Co-authored-by: Trinity Bee <bee@trinity.local> Co-authored-by: github-actions[bot] <41898282+github-actions[bot]@users.noreply.github.com> Co-authored-by: Dmitrii Fedorov <dmitrii.f@t27.ai> Co-authored-by: Dmitrii Vasilev <playra@users.noreply.github.com>
…s the reference runs them (Closes #7244) (#7295) * wip: t27b tuple local, @sqrt, out-of-range compare (Refs #7244) Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> * wip: t27b differential pretty printer shows FSqrt (Refs #7244) Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> * t27b: tuple locals, @sqrt, out-of-range compares, unreached &repeat (Closes #7244) Four blockers from the lane 2 list, each with a conformance spec that t27c test-report passes, written first: - ExprTuple: `const t = .{ a, b };` of run-time scalars is a tuple struct in a stack slot (specs/tri/t27b/conformance/tuple_local.t27). - @sqrt of a run-time float: AArch64 FSQRT plus its encoder case; the interpreter uses the host sqrt (float_sqrt.t27). - ExprBinary: `&[_]T{...} ** n` in a fn only a bench names is the stub trap, as Zig never analyzes it (repeat_addr_unreached.t27). - literal out of range: a run-time uN compared with a comptime_int outside its range is settled at compile time, the run-time side still evaluated (cmp_out_of_range.t27). Lab, full corpus at --jobs 2 with the reference: 1362 of 1362 files, mismatch 0, jit/interp 0, reference disagree 0 (812 compared), crash 0, ratchet UNEXPECTED FAILURE 0; cargo test all ok. Ledger: gen_ray, d_f19_test, gft_dup2_jtag and the four specs move to pass; layernorm_layer's blocker is now StmtAssign(undeclared). Wide integer types are parked as #7245. Rust under the owner's owner-approved-foreign approval on #6063 and #7244. Refs #6063 Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> * specs: `use` lines name a spec by its path; drop lines that splice nothing (Refs #7191) (#7291) * specs: drop 33 `use` lines that splice nothing (Refs #7191) 33 import lines in 29 specs named no spec t27c could splice and no name the spec reads. Each one left a mark in t27c's own zig output on master: `// use X: no references in this module` (14), or a second `const std = @import("std.zig");` beside the backend's own std import (19), which zig rejects as "duplicate struct member name 'std'". So `use std;` is not a harmless import of an implicit library, as in Rust; in t27 it breaks the zig build. Measured on the Railway lab, 403b27f29 against this change, on the 29 files, gen/gen-c/gen-rust/gen-verilog under the master binary and the #7176 slice-2 binary: - exit code changes on 0 of 232 runs; - gen-c, gen-rust, gen-verilog output byte-identical; - `gen` loses exactly the 33 lines above and the 19 blank lines after the std imports; - zig test 0.16.0: none goes pass -> fail; 4 pass both ways; 12 move past the duplicate std to their next error; - #7176 warnings on these files: 37 -> 4. Seals: the 28 sealed specs resealed with a clean release build of 403b27f29 (no bootstrap change on master since); its output equals the A/B binary's on all 232 runs. 58 seal files change: spec_hash, gen_hash_zig, sealed_at, the test record; no gen_hash_c/rust/verilog change. All 28 print "all hashes MATCH". The unsealed specs/port/tools/rename_duplicate_tests.t27 gets no seal. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> * specs: a `use` names the spec's path, not its module name; drop `use tritype-base::usize` (Refs #7191) t27c resolves `use a::b::Item;` by path (specs/a/b.t27). 24 import lines in 13 specs named a spec by its declared module name instead (bus-schema, lsp-schema, provider-schema, config-schema, sync-schema, runtime-process), which is not a path: nothing was spliced. Each now names the path (bus::schema, ...). 8 `use tritype-base::usize;` lines are deleted: specs/base/types.t27 declares no usize; it is a builtin. Measured on the Railway lab, 403b27f29 plus slice 1 against this change, all 1356 specs under the #7176 build (PR #7242): - gen/gen-c/gen-rust/gen-verilog exit codes: 0 of 4 x 1356 change; output changes only in the 13 edited files; - #7176 warnings 84 -> 52; parse/typecheck failures 0 -> 0; - test-report: 13 blocked before and after; 6 move to the `&.{ _ }` lowering error, config/load to its own `config_schema::` body references (6 names, 22 uses), 6 keep their error; - iverilog: config/load 9 -> 11, provider/transform 21 -> 28, none in the elaboration ratchet. Seals: 13 resealed, 26 files. gen_hash_zig changes on the 8 that lose the tritype-base line; no c/rust/verilog hash changes. A seal hashes the spec's own output before any splice, so master's t27c and the #7176 build both print "all hashes MATCH" on all 13; only the lsp/client and lsp/server test records come from the #7176 build. Lands after #7242. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> * specs: seven more `use` lines name a spec's path; drop `use tritype::base` (Refs #7191) Third slice of #7191, measured on the Railway lab with the #7176 build (PR #7242), all 1356 specs, gen / gen-c / gen-rust / gen-verilog. - 6 lines named a module name or bare file name (`tritype-base`, `tritype`, `core`) and now name the path (`base::types::...`, `test_framework::core::{...}`). - 2 brace lists took GF16 and GF32 from `numeric::golden_float`, which is no spec; each is now `use numeric::gf16::GF16;` and `use numeric::gf32::GF32;`. - `use tritype::base;` in relay_observer is deleted (nothing reads it). Exit codes unchanged on all 4 x 1356 runs; output changes only in the edited files (gen 7, gen-c 6, gen-rust 6, gen-verilog 1); #7176 warnings 52 -> 43. All 7 stay blocked in test-report; bigint, hybrid_bigint and runner now reach the import/splice collision filed as #7281 (0 specs before, 3 after). 15 seals resealed; master's t27c and the #7176 build both verify all 7. forward_pass.t27 waits for #7242. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> * specs: forward_pass names base::types for Trit, held back until #7242 (Refs #7191) `use tritype::Trit;` named no spec. It now reads `use base::types::Trit;`, the same edit the third slice made in six other specs. It waited for #7242, which rewrote this spec's calls and resealed it. Measured on the Railway lab with the #7242 build, master df00ec428 plus this branch: the #7176 warning on the line goes away under gen, gen-c, gen-rust and gen-verilog, and all four outputs are byte-identical before and after. test-report blocks on the same zig error ("expected ']', found ';'") before and after. Resealed on the lab: the two seal files change only in spec_hash and in the temp-dir name inside tests.blocked. seal --verify prints "all hashes MATCH" on the 46 changed specs that have a seal (of 47; specs/port/tools/rename_duplicate_tests.t27 has none on master either), with the #7242 build and the old master build. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> --------- Co-authored-by: Claude Opus 5.5 <noreply@anthropic.com> * t27b: `void` as a parameter, field and pointee type (Closes #7267) (#7296) * t27b: lower void as a parameter, field and pointee type (Closes #7267) `void` outside a fn result is Zig's zero-bit type: a struct with no fields and size 0. Fields around it keep their own offsets, an array of structs holding one keeps its stride, and `alloc: void` / `p: *void` parameters take `undefined` and `&s.field`. A `void` result still means no value. Conformance spec: specs/tri/t27b/conformance/type_void.t27. Refs #6063 Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> * t27b: undefined as a void argument; refuse ?void (Closes #7267) `f(undefined, ..)` for a `void` parameter is that parameter's one value and now lowers to an empty temporary. `?void` is refused as `type ?void`: its only non-null value is `undefined`, which Zig turns into an undefined optional, null flag included, so t27b's JIT and interpreter read never-written bytes there. Refs #6063 Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> * ledger(t27b): type void moves; NOW entry (Closes #7267) background_agent/main.t27 and the new type_void spec move to pass; gen_softmax now stops at ExprCall(@exp). Refs #6063 Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> * chore(t27b): foreign-exceptions block for #7267; ledger counts after the master merge (Closes #7267) The type-void edit to lower.rs gets its own approval block, as the other lane-1 PRs do. The ledger counts are recomputed from the entries after merging origin/master. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> --------- Co-authored-by: Claude Opus 5.5 <noreply@anthropic.com> * fix(specs): delete 16 dead use lines, take PHI from math::constants (Refs #7191) (#7298) Fourth slice of #7191. - 16 `use` lines in 12 specs named no spec (the #7176 warning), and no body reads what they name. Before this change the Zig backend lowered all 16 as `// use X: no references in this module`. - `use base::constants::PHI;` in specs/memory/formula_embed.t27 and specs/memory/semantic_search.t27 now reads `use math::constants::PHI;`, which t27c splices. The splice also brings `abs`, and in formula_embed `pow` with `floor`, `exp_approx` and `E`; `pow` is reached through a false reference to the builtin `@pow` (#7292). - Two comments that described a deleted line are corrected. Measured on the Railway lab with the #7242 build, on all 1363 specs, under gen, gen-c, gen-rust and gen-verilog: - the exit code changes on none of the 4 x 1363 runs; - output changes only in edited files (gen 12, gen-c 3, gen-rust 2, gen-verilog 1); - #7176 warnings drop from 42 to 24 under each backend; - parse and typecheck exit 0 on all 12, before and after. Seals: the 10 sealed specs resealed on the lab; 17 seal files change. Master's t27c and the #7242 build both print "all hashes MATCH" on all 10. Co-authored-by: Claude Opus 5.5 <noreply@anthropic.com> * verified: R2-5 capstone -- ternary_link run citation, silicon-proven end to end (Closes #7177) (#7293) * verified: R2-5 capstone -- the ternary_link run citation, read off the XC7A200T bench (Closes #7177, Refs #6655) Three placements of specs/fpga/ternary_link.t27 (pnr seeds 1, 7, 42) on the QMTech Wukong V1: every placement wrong-part-bracketed, Done=1 on our bitstream, full IDCODE 0x3636093 read live, verdict 0xa5a532bf ok=1 -- the same word Phase H read. Each run wrote a complete receipt (six fields, seeds carried, seal_hash = the seal's gen_hash_verilog, toolchain = the seal's built_by t27c-bootstrap@0.4.0+df00ec428). t27c run-record judges the set: RUN_MISSING_NONE, Run complete: yes, citable, exit 0. specs/verified/ternary_link_run.t27 is the verdict record citing that run through verdict_run_reference -- the R2-4 consumption point -- with every run fact pinned load-bearing, including the seedless fourth placement the reader refused (RUN_RECEIPT_INCOMPLETE) and the run redone seeded. Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com> * verified: fold the last in-body comment above its test -- the lexer trap, hit a fourth time (Refs #7177) Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com> * verified: seal the capstone run citation (Refs #7177) Minted on the Railway lab from this branch; seal --verify reads all hashes MATCH. built_by t27c-bootstrap@0.4.0+339c0443f. Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com> --------- Co-authored-by: Dmitrii Vasilev <playra@users.noreply.github.com> Co-authored-by: Claude Opus 5.5 (1M context) <noreply@anthropic.com> * t27b: a text-form array literal repeated with ** lowers like the reference (Closes #7112) (#7161) * spec(t27b): conformance spec for text-form array repeats (Closes #7112) Refs #6063. `[1] ** 100`, `[a, b] ** n` and `[K, f()] ** 2` as the reference runs them: t27c's Zig backend pastes the element text back as `.{ ... } ** n`, so each element is evaluated once and the list repeated. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> * t27b: a text-form array literal repeated with ** (Closes #7112) Refs #6063. `repeat_lit` parses the left operand of `**` back into its elements with `text_lit` when the parser kept them as text, which is how the reference pastes them (`.{ 1 } ** n`). An empty `[] ** n` stays refused, and the element checks of `text_elem` apply unchanged. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> * t27b: text-form repeat tests use sources the reference accepts (Closes #7112) Refs #6063. `text_form_repeats` passed arrays to a `[u32]` slice parameter, which the reference refuses (it needs `&`); the test now reads elements directly. The `[v + 1] ** 2` rejection case is dropped: `[v + 1]` is parsed with children, not as text, and both the reference and t27b accept it. Checked on the lab: reference 2 pass + 1 FAIL, t27b the same. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> * t27b ledger: transport.t27 and array_repeat_text.t27 pass (Closes #7112) Refs #6063. `clade-meshd/src/transport.t27` and the new conformance spec move to pass; `gen_fuzz.t27` now stops at `ExprCall(@intCast)`. Not-pass 51 -> 50. NOW entry docs/now/2026-10-06-t27b-array-repeat.md. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> --------- Co-authored-by: Claude Opus 5.5 <noreply@anthropic.com> * spec(crm-story-reel): v27 gallery preview draws the render's end-card defaults (Refs #6973) (#6980) crm-story-reel v27: the template gallery previews the end card from the render's defaults. * t27b: float x*2^k, if as a struct literal field, defer, gf16::GF16 as the reference runs them (Closes #7239) (#7270) * t27b: float x*2^k, if as a struct literal field, defer, gf16::GF16 as the reference runs them - ExprBinary(f64 * 2^k): refused only where t27c's strength reduction reaches (top-level assign/local/return of a module-level fn, through binary ops). - ExprIf(left operand): a struct literal field value prints as `.f = v,`. - StmtExpr statement: `defer <stmt>;` is rendered to nothing by gen-zig (T43). - type gf16::GF16: the type mapper (#6533) maps the scoped path to u16; `@as(gf16::GF16, x)` and `*gf16::GF16` stay refused. Conformance specs first: specs/tri/t27b/conformance/float_mul_pow2.t27, struct_lit_if.t27, scope_exit.t27, scoped_gf16.t27. Rust under the owner's approval on #6063 (owner-approved-foreign). Closes #7239 Refs #6063 Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> * t27b lane 2: ledger moves and NOW entry for #7239 Measured on the t27b Railway lab, full corpus at --jobs 2: mismatch 0, reference disagree 0, crash 0, ratchet UNEXPECTED FAILURE 0. Master's ledger plus 8 moves to pass; pass 488 -> 496, not_pass and cap 48 -> 45. Closes #7239 Refs #6063 Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> * feat(automation): crm-duet v4 -- a dry run is free (Closes #6896) (#6897) * feat(automation): crm-duet v4 -- a dry run is free (Closes #6896) Owner, 2026-10-06 (translated): "a dry run must be free, change the spec". v3 kept only the story reel out of a dry run; every other paid tool was offered from seller turn 2, so a run that sends nothing still paid for generations. Now paid_tool_offered(seller_turn, dry_run) is false on every turn of a dry run, and paid_call_refused names the dispatcher's refusal (DRY_RUN_SPENDS = false, DRY_RUN_HIDES_PAID_TOOLS, DRY_RUN_REFUSES_PAID_CALL). A real run is unchanged. t27c test-report 20/20; negative control (the dry run offers paid tools again) fails 2. Census: shell `run: steps` 291 -> 292 (runner-named 270 -> 271) was already moved on master by a workflow step this PR does not touch; the pre-commit census gate asks for the re-bless in the next commit, so it rides here. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> * feat(automation): crm-duet v5 -- a paid tool is one with a price (Refs #6896) v4 hid only the six tools v1 named. The seller is offered the whole registry, and lipsync_generate, story_reel, split_reel and crm_voice_clone charge but were on no list, so a dry run still offered them. - tool_is_paid(price): price > 0; borrowed_price(own, borrowed): a tool that runs a priced tool is priced; priced_tool_offered(price, turn, dry_run) refuses every priced tool on every turn of a dry run. - PAID_TOOLS = 6 removed (PAID_TOOL_IS_PRICED, PAID_TOOLS_HAND_LIST = false): the host derives the set from its price table. - story_offered calls paid_tool_offered: duplicate-bodies grouped the two identical bodies. t27c test-report 21/21; negative control (priced_tool_offered ignoring dry_run) fails the new test. Seal re-saved, verify MATCH. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> --------- Co-authored-by: Claude Opus 5.5 <noreply@anthropic.com> * feat(verified): t27c run-record reads the receipts and judges one run (R2-4 tool half) (#7130) * feat(verified): t27c run-record reads the receipts and judges one run (Closes #7072) R2-4 tool half, epic #6655. The rule half (specs/verified/run_record.t27, PR #7061) landed; this is the reader that applies it. t27c run-record <spec> reads every .trinity/receipts/<stem>-*.json whose spec names the given spec plus the spec's seals in .trinity/seals, collects the four facts -- count, every-receipt-complete by receipt.t27's six-field rule (unknown verdict word = absent), verdict words agreeing, every receipt's toolchain == its cited seal's built_by verbatim (R2-2; a receipt's own seal is the one whose gen_hash_verilog equals its seal_hash) -- and answers run_first_missing, run_complete, and verdict.t27's consumption point (incomplete run => INVALID_NO_RUN before any chain is read). Exit 0 = citable run, 1 = not, 2 = REFUSED (spec does not exist). Twelve fixture tests pin each exit path to run_record.t27's constants, including: unknown verdict word is INCOMPLETE (2), never WORDS_DISAGREE (3); a seal without built_by (every seal minted before #7076) matches no producer; a receipt citing a seal the spec does not hold is a producer mismatch; no receipts at all is TOO_FEW over zero, not a usage error; agreeing FAILs are one complete run (failure_loop owns the rest). Refs #6655, #7058, #7041, #7076. Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com> * fix: sort the receipt and seal listings by file name -- serde_json::Value is not Ord (Refs #7072) Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com> * test: pin that disagreement (3) is judged before producers (4) (Refs #7072) Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com> * chore: resync the PR head after a queue jam that swallowed the pull_request events (Refs #7072) The validate/parse-ratchet workflow runs were never created for b7226bda2 -- GitHub dropped the synchronize events while the runner fleet was starved. An empty commit re-fires them now that the queue is empty. Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com> * chore: re-fire the pull_request gates (Refs #7072) The dispatched parse-ratchet run cannot derive BASE_SHA (no pull_request context) and failed on that, leaving a blocking red check on the head; its concurrency group (cancel-in-progress) also cancels any real run for the ref. Only a fresh synchronize event produces a verdict -- this is that event. Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com> * docs: say the exit-code contract in the reader test header (Refs #7072) Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com> --------- Co-authored-by: Claude Opus 5.5 (1M context) <noreply@anthropic.com> * t27b: unreached fns may name an unlayable struct; float as casts spelled like gen-zig (Closes #7175 #7179) (#7216) * Port gHashTag/trios:crates/trios-cli/src/lock.rs to specs/port/trios/crates/trios-cli/src/lock.t27 - Implement lock_file_path() function - Implement LockGuard_acquire() function with undefined body - Implement LockGuard_try_acquire() function with undefined body - Implement LockGuard_is_lock_stale() function with undefined body - Implement LockGuard_drop() function with undefined body - Add 5 test cases covering basic functionality - All tests pass with 0 BLOCKED Closes #5673 * Port training state management (train_state) to .t27 Port of gHashTag/trios crates/trios-train-cpu/src/bin/train_state.rs (8b229e9489ee) to specs/port/trios/crates/trios-train-cpu/src/bin/train_state.t27 (module port::trios::crates::trios_train_cpu::src::bin). - OptKind enum (AdamW, Muon); Config, OptWrapper, TrainingState structs. - All four ported functions keep real bodies (no undefined stubs): OptWrapper_adamw (wraps AdamW, casts wd to f64), OptWrapper_muon (hardcodes momentum 0.95, stores lr), OptWrapper_step (dispatches by tag; AdamW takes lr per call and never stores it, Muon stores lr before stepping), and init_training (make_opt per slot, sizes VOCAB*DIM / HIDDEN*DIM / VOCAB*HIDDEN, EMA ramp 0.996 -> 1.0 over cfg.steps, f32::MAX sentinel for best_val_bpb). - Mapping notes: the Rust enum-with-payload OptWrapper becomes a tag struct; Option<JepaPredictor>/Option<NcaObjective> become presence flags; the Vec of NUM_CTX identical ctx wrappers becomes one representative plus count; Instant::now() becomes a caller-passed now parameter. World-touching code (optimizer math, models, predictor, NCA objective, clock) is caller-driven plumbing, so the structs carry only what the decisions read or produce. - 7 tests with field-by-field asserts (struct == is not supported for OptWrapper): constructor parameters, switch dispatch and lr handoff, make_opt config following, init_training defaults and muon/jepa/nca configs, f32::MAX sentinel. t27c parse: 0 errors; typecheck: 0 errors / 0 warnings; test-report: 7 pass / 0 FAIL, no BLOCKED; gen: 0 'not yet implemented'; spec-status: IMPLEMENTED. Closes #5659 * docs: the coordination entry this branch needs to land A pull request must add exactly one docs/now entry and a bee has no way to know that: its brief names a boundary file and acceptance criteria, and docs/now/ is neither. The publisher adds it rather than failing the gate. Closes #5659 Co-Authored-By: Claude Opus 5 <noreply@anthropic.com> * docs: the coordination entry this branch needs to land A pull request must add exactly one docs/now entry and a bee has no way to know that: its brief names a boundary file and acceptance criteria, and docs/now/ is neither. The publisher adds it rather than failing the gate. Closes #5673 Co-Authored-By: Claude Opus 5 <noreply@anthropic.com> * t27b: conformance spec for a fn no test reaches whose signature names an unlayable struct (Refs #7175) Refs #6063. Dogfood spec first: specs/tri/t27b/conformance/unresolved_signature.t27 has a struct that holds itself by value. Only fns that no test reaches name it: as a parameter, as a result, and through a call to another such fn. This mirrors specs/compiler/optimizer.t27. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> * t27b: conformance spec for a float operand cast with as (Refs #7175) Refs #6063 Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> * t27b: unresolved signatures of unreached fns; float as casts spelled like gen-zig (Refs #7175 #7179) Refs #6063 Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> * fix(tri mutate): a hang and a mutant zig rejects are no longer kills (Closes #7148) (#7204) * fix(tri mutate): a hang and a mutant zig rejects are no longer kills (Closes #7148) `tri mutate spec` ran `t27c gen` + `zig test` under one clock and called every non-zero exit a kill, so a hang and a compile error both raised "killed" and neither was listed by line. On one probe spec (lab, zig 0.16.0, same t27c, back to back) master printed "22 of 24 killed (20 by `zig test`, 0 by a gen failure, 2 by a hang)"; this prints "17 of 24 killed (10 by a failing test, 7 by an invariant at compile time); 2 survived, 3 hung, 2 unviable", each of the 7 listed by line. - Three steps, each on its own --timeout clock: `t27c gen`, `zig test --test-no-exec`, then the test binary. Only the test run outliving its clock is a HANG; gen or the compile outliving it is the machine's load and the mutant is NOT RUN (unclebob/mutator issue 1's defect). - A compile error with zig's "called at comptime here" note is an invariant the mutant broke (t27c lowers invariants to comptime): a kill. "evaluation exceeded ... backwards branches" is comptime's own timeout: a HANG. Any other compile error is UNVIABLE. - The issue's "a parameter left unused fails to compile" is wrong: t27c emits `_ = a;` and `_ = &i;`, so such a mutant compiles. The UNVIABLE test uses a type error. - 9 new tests (34, was 25); 6 run zig on lowered fixtures. Five hand-made regressions each turn a named test red. - cli-tri installs zig 0.16.0 before `cargo test -p tri`. Census: `shell` moved 300 -> 301 run: steps (279 -> 280 whose shell the runner names), the new "Install zig" step; re-blessed here, master's pins pass at the base. The workflow edit is in tools/policy/foreign-exceptions.txt. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> * fix(tri mutate): mutants live beside the spec's specs/, so a spec with `use` can be mutated (Refs #7148) t27c resolves `use a::b;` by walking up from the spec file for a `specs/` directory (bootstrap/src/use_resolve.rs, find_specs_root). The copies sat in the system temp dir, which has none, so t27c dropped every import and still exited 0 (#7176). zig then failed the unmutated copy of specs/policy/l2_generation.t27 with "use of undeclared identifier 'LIST_END'", and the tool could not mutate any spec that imports anything. The work dir is now `target/tri-mutate-spec-PID` beside the spec's `specs/`, where the same walk from a copy reaches the spec's own tree. A spec with no `specs/` above it keeps the temp dir. Measured on the Railway lab, default TMPDIR, `--fn diff_kind`: - the previous commit's tri: Unviable("zig: error: use of undeclared identifier 'LIST_END'"); - this commit: "3 of 3 killed (3 by a failing test, 0 by an invariant at compile time); 0 survived, 0 hung, 0 unviable." New test a_copy_in_the_work_dir_resolves_use_against_the_specs_own_tree (35 in mutate::tests; `cargo test -p tri mutate` on the lab: 35 passed). With the work dir put back in the temp dir it fails (left /tmp/tri-mutate-spec-7, right .../r/target/tri-mutate-spec-7). Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> --------- Co-authored-by: Claude Opus 5.5 <noreply@anthropic.com> * fix(port): railway_deployment_create.t27 generates Verilog again (Closes #7228) (#7240) The spec built argv as local [N][]const u8 arrays in its tests, a 2-D aggregate gen-verilog does not lower (W469). That made master's corpus ratchet red since fed07cd82 (PR #6956). Rewritten in the shape of railway_null_startcmd.t27: decide_args(argc), decide_response(stdout) with a byte-level port of std.mem.indexOf, and main left as plumbing. The original only reads args.len and the "errors" field of curl's stdout, so nothing it decides on is lost. 14 tests, all executing runtime asserts on the lab (test-report 14/14, 0 vacuous). Co-authored-by: Claude Opus 5.5 <noreply@anthropic.com> * t27b: module-level constants that hold an optional (Closes #7116) (#7202) * spec(t27b): conformance spec for module-level optional constants (Closes #7116) Refs #6063. specs/tri/t27b/conformance/const_optional.t27: `?T` constants alone, copied from another, as struct fields beside a `str`, from a field default, and a present zero. The reference gives 4 pass. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> * t27b: module-level constants that hold an optional (Closes #7116) Refs #6063. `const_fill` lays out `?T` as `opt_temp` does: the payload, then the has-value flag. `null` leaves both zero, and another optional constant is copied byte for byte. `const_elem` and the module-level constant path reach it through `rodata`. An optional holding a `str` stays refused as `ConstDecl(?T)`. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> * t27b ledger: parse_conform.t27 and const_optional.t27 pass (Closes #7116) Module-level optional constants unblock parse_conform.t27. Not-pass goes from 50 to 49. NOW entry added. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> * spec(t27b): rename the const_optional row struct to OptionalRow so tri types ratchet stays clean (Closes #7116) Row already has a definition elsewhere in specs/, and the Corpus ratchet's type-conflict ledger counted the new one as a NEW conflict. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> --------- Co-authored-by: Claude Opus 5.5 <noreply@anthropic.com> * fix(specs): six vacuous wave tests and a trapping sign extension (#7246) Closes #7225. Closes #6560. specs/port/scripts/gen_w38{1,2,4,5,6,7}.t27: wave_constants_follow_each_other asserted two constants, which fold at compile time, so it passed with 0 runtime asserts. It now calls next_wave(EXPECTED_LAST_WAVE). specs/isa/tri27_machine.t27: ld_sign_extend read (word as i32) as i64, which the Zig backend narrows with a range-checked @intCast, so words above 2^31 - 1 trap and one test failed. It is written as arithmetic now. The seal is re-saved (10 of 10 tests) and the file leaves tools/seal_baseline.txt. test-report: the six ports 7/7 with 0 vacuous, tri27_machine 10/10. Co-authored-by: Claude Sonnet 5.5 <noreply@anthropic.com> --------- Co-authored-by: Trinity Bee <bee@trinity.local> Co-authored-by: queen-publisher[bot] <noreply@anthropic.com> Co-authored-by: github-actions[bot] <41898282+github-actions[bot]@users.noreply.github.com> Co-authored-by: Dmitrii Fedorov <dmitrii.f@t27.ai> * t27c: name each unresolved `use`; item and brace imports splice from their module (Refs #7176) (#7242) * t27c: name each `use` the splice finds no spec for (Refs #7176) A `use a::b;` whose specs/a/b.t27 does not exist was skipped silently and `gen` exited 0; the first sign was a later "undeclared identifier" in some other tool's output (#7148 met it in a temp-dir copy). typecheck_gate, which each of the 10 gen paths calls once, now prints one stderr line per such `use`: file, line, path and why (no spec; no specs/ directory above the file; a brace list, #2537; one item of a module whose file exists, #5552). The splice and the note share use_path_expr and use_path, so they read the same lines the same way. A warning, not an error: the tracked corpus has 182 such lines in 106 files (112 no spec, 54 items of a module, 16 brace lists, 0 outside specs/), and a qualified reference still makes the zig backend emit @import with no spec to splice (tests/dotted_module_name.rs). The error is #7176's next step. Lab, master 403b27f29 vs this branch, `gen` on all 1484 tracked .t27 files: stdout differs on 0, exit code on 0, other stderr on 0; 182 new lines. Unit 32/32, CLI unresolved_use 2/2, dotted_module_name and unknown_type green. Negative controls: the gate loop removed -> the CLI test fails; missing_uses returning nothing -> 4 unit tests and the CLI test fail. Foreign Rust under the owner's standing rule (owner-approved-foreign), listed in tools/policy/foreign-exceptions.txt; compiler.rs untouched. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> * fix(t27c): item and brace imports splice from their module; three splice defects (Refs #7176) `use a::b::{X, Y};` and `use a::b::Item;` (when specs/a/b/Item.t27 is not a spec) now splice from specs/a/b.t27, one level up only, as Rust names the module that holds the items. The #7176 warnings drop from 182 to 119, in 70 files (Refs #2537, Refs #5552). The corpus A/B on the Railway lab found three defects of the splice that predate this change, each made visible by a module the item imports now splice: - the importer's own names came from the smallest indent of any declaration; they now come from brace depth (spi_tb gained a second spi_transfer; property_test_template a duplicated DifferentialCase); - a declaration ended at the first line whose {} and [] depth was 0, so a header split over lines was its first line alone (mac_tb); the () depth counts now, and hslm's fall-back note is gone; - a char literal '"' was read as a string start and hid the rest of its line; with the () depth that dropped verdict, put and put_msg from the output of ci/affected and policy/l2_generation in the first lab run. Char literals and `;` prose lines are read as such. Explicit-item precedence over a glob was tried and reverted: the pulled declarations' qualifiers are not rewritten (#7215). specs/neural/forward_pass.t27: 42 call lines realigned with vsa_core's arities; both seals resealed (#7203: seals hash the unspliced source). Measured, commit 1 vs this one, 1484 files x gen/gen-c/gen-rust/gen-verilog: exit changes on 0; output changes on 17 specs; zig on the 17: none goes from pass to fail; 13 of 15 tracked gen/ copies byte-identical under both (gf16 differs from both, #6996). 38 unit tests (32 before); negative controls for the paren depth and the char literals turn named tests red. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> --------- Co-authored-by: Claude Opus 5.5 <noreply@anthropic.com> * t27b: `const Name = T;` is a type alias (Closes #7241) (#7282) * spec(t27b): type_alias conformance spec -- const Name = T is a Zig type alias (Closes #7241) Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> * feat(t27b): const Name = T with no annotation is a type alias wherever a type is read (Closes #7241) A module constant whose value is a bare name that spells a type (a scalar, str, [N]T, ?T, *T, a declared struct or enum, or another such alias) now resolves as that type in lty and ty, and is not lowered as a value. An alias cycle, an alias of a type t27b does not model, and an alias read as a value stay refused. Rust edit under the owner's approval on #6063 (label owner-approved-foreign); files listed in tools/policy/foreign-exceptions.txt. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> * fix(t27b): a type alias counts only in Zig spellings -- str and [N]str are refused (Closes #7241) The reference prints alias text into Zig verbatim, so str / string name nothing there; [N]T counts only when T spells a type. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> * fix(t27b): a struct literal of a scalar alias is refused, not recursed into (Closes #7241) const Duo = u8; Duo{ .lo = 3 } made expr -> struct_temp -> init -> expr_as -> expr loop until the stack overflowed (found by mutant m8 on the lab). Zig refuses it too: 'type u8 does not support struct initialization syntax'. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> * ledger(t27b): type alias moves; NOW entry (Closes #7241) zig_primitive_bindings and the new type_alias spec move to pass; gfternary now stops at ExprCall(@setEvalBranchQuota). The doc comment of lit_type, displaced by struct_lit_ty, goes back above it (comment only). Refs #6063 Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> --------- Co-authored-by: Claude Opus 5.5 <noreply@anthropic.com> * specs: `use` lines name a spec by its path; drop lines that splice nothing (Refs #7191) (#7291) * specs: drop 33 `use` lines that splice nothing (Refs #7191) 33 import lines in 29 specs named no spec t27c could splice and no name the spec reads. Each one left a mark in t27c's own zig output on master: `// use X: no references in this module` (14), or a second `const std = @import("std.zig");` beside the backend's own std import (19), which zig rejects as "duplicate struct member name 'std'". So `use std;` is not a harmless import of an implicit library, as in Rust; in t27 it breaks the zig build. Measured on the Railway lab, 403b27f29 against this change, on the 29 files, gen/gen-c/gen-rust/gen-verilog under the master binary and the #7176 slice-2 binary: - exit code changes on 0 of 232 runs; - gen-c, gen-rust, gen-verilog output byte-identical; - `gen` loses exactly the 33 lines above and the 19 blank lines after the std imports; - zig test 0.16.0: none goes pass -> fail; 4 pass both ways; 12 move past the duplicate std to their next error; - #7176 warnings on these files: 37 -> 4. Seals: the 28 sealed specs resealed with a clean release build of 403b27f29 (no bootstrap change on master since); its output equals the A/B binary's on all 232 runs. 58 seal files change: spec_hash, gen_hash_zig, sealed_at, the test record; no gen_hash_c/rust/verilog change. All 28 print "all hashes MATCH". The unsealed specs/port/tools/rename_duplicate_tests.t27 gets no seal. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> * specs: a `use` names the spec's path, not its module name; drop `use tritype-base::usize` (Refs #7191) t27c resolves `use a::b::Item;` by path (specs/a/b.t27). 24 import lines in 13 specs named a spec by its declared module name instead (bus-schema, lsp-schema, provider-schema, config-schema, sync-schema, runtime-process), which is not a path: nothing was spliced. Each now names the path (bus::schema, ...). 8 `use tritype-base::usize;` lines are deleted: specs/base/types.t27 declares no usize; it is a builtin. Measured on the Railway lab, 403b27f29 plus slice 1 against this change, all 1356 specs under the #7176 build (PR #7242): - gen/gen-c/gen-rust/gen-verilog exit codes: 0 of 4 x 1356 change; output changes only in the 13 edited files; - #7176 warnings 84 -> 52; parse/typecheck failures 0 -> 0; - test-report: 13 blocked before and after; 6 move to the `&.{ _ }` lowering error, config/load to its own `config_schema::` body references (6 names, 22 uses), 6 keep their error; - iverilog: config/load 9 -> 11, provider/transform 21 -> 28, none in the elaboration ratchet. Seals: 13 resealed, 26 files. gen_hash_zig changes on the 8 that lose the tritype-base line; no c/rust/verilog hash changes. A seal hashes the spec's own output before any splice, so master's t27c and the #7176 build both print "all hashes MATCH" on all 13; only the lsp/client and lsp/server test records come from the #7176 build. Lands after #7242. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> * specs: seven more `use` lines name a spec's path; drop `use tritype::base` (Refs #7191) Third slice of #7191, measured on the Railway lab with the #7176 build (PR #7242), all 1356 specs, gen / gen-c / gen-rust / gen-verilog. - 6 lines named a module name or bare file name (`tritype-base`, `tritype`, `core`) and now name the path (`base::types::...`, `test_framework::core::{...}`). - 2 brace lists took GF16 and GF32 from `numeric::golden_float`, which is no spec; each is now `use numeric::gf16::GF16;` and `use numeric::gf32::GF32;`. - `use tritype::base;` in relay_observer is deleted (nothing reads it). Exit codes unchanged on all 4 x 1356 runs; output changes only in the edited files (gen 7, gen-c 6, gen-rust 6, gen-verilog 1); #7176 warnings 52 -> 43. All 7 stay blocked in test-report; bigint, hybrid_bigint and runner now reach the import/splice collision filed as #7281 (0 specs before, 3 after). 15 seals resealed; master's t27c and the #7176 build both verify all 7. forward_pass.t27 waits for #7242. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> * specs: forward_pass names base::types for Trit, held back until #7242 (Refs #7191) `use tritype::Trit;` named no spec. It now reads `use base::types::Trit;`, the same edit the third slice made in six other specs. It waited for #7242, which rewrote this spec's calls and resealed it. Measured on the Railway lab with the #7242 build, master df00ec428 plus this branch: the #7176 warning on the line goes away under gen, gen-c, gen-rust and gen-verilog, and all four outputs are byte-identical before and after. test-report blocks on the same zig error ("expected ']', found ';'") before and after. Resealed on the lab: the two seal files change only in spec_hash and in the temp-dir name inside tests.blocked. seal --verify prints "all hashes MATCH" on the 46 changed specs that have a seal (of 47; specs/port/tools/rename_duplicate_tests.t27 has none on master either), with the #7242 build and the old master build. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> --------- Co-authored-by: Claude Opus 5.5 <noreply@anthropic.com> * t27b: `void` as a parameter, field and pointee type (Closes #7267) (#7296) * t27b: lower void as a parameter, field and pointee type (Closes #7267) `void` outside a fn result is Zig's zero-bit type: a struct with no fields and size 0. Fields around it keep their own offsets, an array of structs holding one keeps its stride, and `alloc: void` / `p: *void` parameters take `undefined` and `&s.field`. A `void` result still means no value. Conformance spec: specs/tri/t27b/conformance/type_void.t27. Refs #6063 Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> * t27b: undefined as a void argument; refuse ?void (Closes #7267) `f(undefined, ..)` for a `void` parameter is that parameter's one value and now lowers to an empty temporary. `?void` is refused as `type ?void`: its only non-null value is `undefined`, which Zig turns into an undefined optional, null flag included, so t27b's JIT and interpreter read never-written bytes there. Refs #6063 Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> * ledger(t27b): type void moves; NOW entry (Closes #7267) background_agent/main.t27 and the new type_void spec move to pass; gen_softmax now stops at ExprCall(@exp). Refs #6063 Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> * chore(t27b): foreign-exceptions block for #7267; ledger counts after the master merge (Closes #7267) The type-void edit to lower.rs gets its own approval block, as the other lane-1 PRs do. The ledger counts are recomputed from the entries after merging origin/master. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> --------- Co-authored-by: Claude Opus 5.5 <noreply@anthropic.com> * fix(specs): delete 16 dead use lines, take PHI from math::constants (Refs #7191) (#7298) Fourth slice of #7191. - 16 `use` lines in 12 specs named no spec (the #7176 warning), and no body reads what they name. Before this change the Zig backend lowered all 16 as `// use X: no references in this module`. - `use base::constants::PHI;` in specs/memory/formula_embed.t27 and specs/memory/semantic_search.t27 now reads `use math::constants::PHI;`, which t27c splices. The splice also brings `abs`, and in formula_embed `pow` with `floor`, `exp_approx` and `E`; `pow` is reached through a false reference to the builtin `@pow` (#7292). - Two comments that described a deleted line are corrected. Measured on the Railway lab with the #7242 build, on all 1363 specs, under gen, gen-c, gen-rust and gen-verilog: - the exit code changes on none of the 4 x 1363 runs; - output changes only in edited files (gen 12, gen-c 3, gen-rust 2, gen-verilog 1); - #7176 warnings drop from 42 to 24 under each backend; - parse and typecheck exit 0 on all 12, before and after. Seals: the 10 sealed specs resealed on the lab; 17 seal files change. Master's t27c and the #7242 build both print "all hashes MATCH" on all 10. Co-authored-by: Claude Opus 5.5 <noreply@anthropic.com> * verified: R2-5 capstone -- ternary_link run citation, silicon-proven end to end (Closes #7177) (#7293) * verified: R2-5 capstone -- the ternary_link run citation, read off the XC7A200T bench (Closes #7177, Refs #6655) Three placements of specs/fpga/ternary_link.t27 (pnr seeds 1, 7, 42) on the QMTech Wukong V1: every placement wrong-part-bracketed, Done=1 on our bitstream, full IDCODE 0x3636093 read live, verdict 0xa5a532bf ok=1 -- the same word Phase H read. Each run wrote a complete receipt (six fields, seeds carried, seal_hash = the seal's gen_hash_verilog, toolchain = the seal's built_by t27c-bootstrap@0.4.0+df00ec428). t27c run-record judges the set: RUN_MISSING_NONE, Run complete: yes, citable, exit 0. specs/verified/ternary_link_run.t27 is the verdict record citing that run through verdict_run_reference -- the R2-4 consumption point -- with every run fact pinned load-bearing, including the seedless fourth placement the reader refused (RUN_RECEIPT_INCOMPLETE) and the run redone seeded. Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com> * verified: fold the last in-body comment above its test -- the lexer trap, hit a fourth time (Refs #7177) Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com> * verified: seal the capstone run citation (Refs #7177) Minted on the Railway lab from this branch; seal --verify reads all hashes MATCH. built_by t27c-bootstrap@0.4.0+339c0443f. Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com> --------- Co-authored-by: Dmitrii Vasilev <playra@users.noreply.github.com> Co-authored-by: Claude Opus 5.5 (1M context) <noreply@anthropic.com> * t27b: a text-form array literal repeated with ** lowers like the reference (Closes #7112) (#7161) * spec(t27b): conformance spec for text-form array repeats (Closes #7112) Refs #6063. `[1] ** 100`, `[a, b] ** n` and `[K, f()] ** 2` as the reference runs them: t27c's Zig backend pastes the element text back as `.{ ... } ** n`, so each element is evaluated once and the list repeated. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> * t27b: a text-form array literal repeated with ** (Closes #7112) Refs #6063. `repeat_lit` parses the left operand of `**` back into its elements with `text_lit` when the parser kept them as text, which is how the reference pastes them (`.{ 1 } ** n`). An empty `[] ** n` stays refused, and the element checks of `text_elem` apply unchanged. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> * t27b: text-form repeat tests use sources the reference accepts (Closes #7112) Refs #6063. `text_form_repeats` passed arrays to a `[u32]` slice parameter, which the reference refuses (it needs `&`); the test now reads elements directly. The `[v + 1] ** 2` rejection case is dropped: `[v + 1]` is parsed with children, not as text, and both the reference and t27b accept it. Checked on the lab: reference 2 pass + 1 FAIL, t27b the same. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> * t27b ledger: transport.t27 and array_repeat_text.t27 pass (Closes #7112) Refs #6063. `clade-meshd/src/transport.t27` and the new conformance spec move to pass; `gen_fuzz.t27` now stops at `ExprCall(@intCast)`. Not-pass 51 -> 50. NOW entry docs/now/2026-10-06-t27b-array-repeat.md. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> --------- Co-authored-by: Claude Opus 5.5 <noreply@anthropic.com> --------- Co-authored-by: Claude Opus 5.5 <noreply@anthropic.com> Co-authored-by: Trinity Bee <bee@trinity.local> Co-authored-by: github-actions[bot] <41898282+github-actions[bot]@users.noreply.github.com> Co-authored-by: Dmitrii Fedorov <dmitrii.f@t27.ai> Co-authored-by: Dmitrii Vasilev <playra@users.noreply.github.com> * t27c seal: the test record names the spec, not zig's temp dir or a missing zig (Closes #7243) (#7301) * t27c seal: the test record names the spec, not zig's temp dir or a missing zig (Refs #7243) zig printed each error with the absolute path it was given, inside t27c-test-report-<stem>-<pid>, and that line went into a blocked seal's test record: two reseals of one spec with one binary wrote two files. zig now runs from its work dir on bare file names and prints `spec.zig:18:56: error: ...` (t27b already cut the same prefix). With no zig on PATH, `seal --save` exited 0 and wrote "zig not on PATH" over the spec's last measured result. That report is now the verdict `Unmeasured`: refused with exit 1 unless --force. Lab, 403b27f29 tree, two reseals each with one binary: master differs besides sealed_at in 2 lines on base64 (blocked), 0 on orphan_detection; this change 0 and 0. With PATH=/usr/bin:/bin master exits 0 and seals, this change exits 1 and writes nothing. Negative controls: build() as on master and the Unmeasured return removed each turn two named tests red. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> * test(seal): the no-zig case asserts the refusal, then the forced seal (Refs #7243) a_blocked_spec_is_sealed_with_a_notice pinned the old behaviour: with zig off PATH, `seal --save` exited 0 and wrote "zig not on PATH". Since the first commit of #7243 that seal is refused unless --force, and the test failed on the lab (`cargo test --release -p t27c`, merged with 80cbb0cff). It now asserts exit 1, the reason named and no file written, then seals with --force and keeps its old checks: the notice, `tests.blocked`, and no failed count for a spec whose test would fail. Lab, same tree: seal_refuses_failing_tests 4/4, seal_reseal_is_stable 3/3. zig_primitive_bindings failed 1, then 3 tests on two runs, each "failed with SystemResources" on spawn (lab pids 705 of 1000, zombies with PPID 1, #7090); it does not run seal or test-report. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> * docs(now): #7243 entry names the old seal test it updates (Refs #7243) Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> --------- Co-authored-by: Claude Opus 5.5 <noreply@anthropic.com> * t27b: a struct field named for a Zig keyword (Closes #7247) (#7299) * feat(t27b): a struct field named for a Zig keyword is no longer refused (Closes #7247) Since #6451 t27c's Zig backend escapes a keyword field name as @"align" in the declaration, the struct literal, the read and the assignment target, so the ExprStructLit / ExprFieldAccess(zig keyword field) refusals were stale. Conformance spec first: specs/tri/t27b/conformance/zig_keyword_field.t27. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> * ledger(t27b): keyword-field moves; NOW entry (Closes #7247) linker and the new zig_keyword_field spec move to pass; zig_field_syntax now stops at `type str?`. Refs #6063 Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> * chore(t27b): foreign-exceptions block for #7247; ledger counts after the master merge (Closes #7247) The keyword-field edit to lower.rs and source.rs gets its own approval block, as the other lane-1 PRs do. The ledger counts are recomputed from the entries after merging origin/master. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> * chore(t27b): drop two stale ledger rows the master merge left behind (Closes #7247) The merge kept both sides of two rows. zig_primitive_bindings.t27 passes since #7282, and zig_field_syntax.t27 now stops at type str?. Counts recomputed: pass 500, not_pass 42. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> --------- Co-authored-by: Claude Opus 5.5 <noreply@anthropic.com> * spec(queen): merger_gate states the rule the merger runs (Closes #7300) (#7302) The header claimed the runtime mirrors these functions from t27c gen-js output; gen-js lowers no bodies and auto-merge-ready-prs.yml never reads the spec. The header now names tools/bees/merger_gate_selftest.py as the place the two meet, and each new test names the scenario it asserts. gate_open(false, true) == false contradicted the merger and its own self-test ("ruleset unreadable, every check green" is ready). The merger fails closed per check: with no ruleset every check counts as required, so no red is discountable. counts_as_required states that; check_passes adds "not concluded blocks"; gate_open takes posted/running/blocking and keeps the gate shut on zero posted checks. 5 functions (was 3), 22 tests (was 13); zig test 22/22, test-report 0 vacuous of 22. tri mutate spec on the lab: 16 of 16 killed. By hand, 12 more, each killed by the test written for it (unmutated copy passes): each `!`, the literal true for concluded, posted > 0, running == 0, blocking == 0, both new guards dropped. Co-authored-by: Claude Opus 5.5 <noreply@anthropic.com> * t27b: a fn result typed as an anonymous struct (Closes #7256) (#7305) * t27b: lower a fn result typed as an anonymous struct (Closes #7256) A fn declared `-> struct { a: T, b: U }` gets its own struct layout, keyed by the spelling and the fn, and `.{ .a = .. }` fills it like a named struct. Only field types the reference prints as valid Zig are taken (not `str`, not `[T; N]`), and no Zig keyword as a field name: t27c prints the result type verbatim, so those fail there too. Conformance spec: specs/tri/t27b/conformance/anonymous_struct.t27. Refs #6063 Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> * ledger(t27b): anonymous-struct moves; NOW entry (Closes #7256) test-agent-bridge and the new anonymous_struct spec move to pass; the agent-server routes/memory.t27 now stops at `type [N]T` and gen_work_stealing at ExprReturn. Refs #6063 Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> * chore(t27b): foreign-exceptions block for #7256; ledger counts after the master merge (Closes #7256) The anonymous-struct edit to lower.rs gets its own approval block, as the other lane-1 PRs do. The ledger counts are recomputed from the entries after merging origin/master. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> --------- Co-authored-by: Claude Opus 5.5 <noreply@anthropic.com> * crm-story-reel v28: a retry renders only the empty clip slots (#7000) crm-story-reel v28: a retried job keeps clips already made and renders only empty slots. --------- Co-authored-by: Claude Opus 5.5 <noreply@anthropic.com> Co-authored-by: Dmitrii Vasilev <playra@users.noreply.github.com> Co-authored-by: Trinity Bee <bee@trinity.local> Co-authored-by: github-actions[bot] <41898282+github-actions[bot]@users.noreply.github.com> Co-authored-by: Dmitrii Fedorov <dmitrii.f@t27.ai>
Closes #7072, Refs #6655, #7058, #7041, #7076.
R2-4, the tool half. The rule half (specs/verified/run_record.t27, #7061) is on master; this is the reader that applies it.
t27c run-record <spec>reads every.trinity/receipts/<stem>-*.jsonwhosespecnames the given spec (tail-match, the seal lookup's discipline) plus the spec's seals in.trinity/seals/, collects the four facts run_record.t27 judges, and answers:toolchain== the cited seal'sbuilt_byverbatim, where a receipt's own seal is the one whosegen_hash_verilogequals itsseal_hash— the image the device ran, not merely a seal of the same spec.Exit 0 = one verified run a verdict record may cite; 1 = not (first-missing code names why); 2 = REFUSED (the spec named does not exist — judging receipts against a typo answers TOO_FEW over files nobody meant).
Decisions stay in run_record.t27; the Rust mirrors its fixed order (count, completeness, agreement, producer) as I/O plumbing. The reader needs neither #7044 (fixtures are hand-written receipt JSON) nor #7076 to land — but #7076 is load-bearing for real receipts: a seal without
built_bymatches no producer, and that is the honest reading, pinned by a test.Verification (Railway lab, t27c-lab, master toolchain):
cargo build --release -p t27cgreen;cargo test --release -p t27c --test run_record_reader13/13 passed. Thirteen fixture tests pin every exit path to run_record.t27's literal constants, including the order pins: unknown word is INCOMPLETE (2) never WORDS_DISAGREE (3); disagreement (3) is judged before producers (4) when both break; a seal without built_by (every seal before #7076) matches no producer; a receipt citing a seal the spec does not hold is a producer mismatch; zero receipts is TOO_FEW over zero, not a usage error; agreeing FAILs are citable.Foreign (service.rs reader + the integration test + the exceptions entry); self-labeled
owner-approved-foreignper the standing rule. Exceptions entry cites #7072.🤖 Generated with Claude Code