Section 1: Type System Foundation
Goal: Fix type checking to properly use type annotations
SPEC:
spec/08-types.md,spec/09-properties-of-types.md,spec/10-declarations.md
Status: COMPLETE(2026-02-13, verified 2026-03-29). Core (1.1-1.4) verified 2026-02-10. 1.1 all LLVM AOT tests 2026-02-13. 1.1A constant folding 2026-02-13. 1.1B ? LLVM support 2026-02-13. 1.6 type system slots (LifetimeId, ValueCategory, Borrowed tag, StructDef category) + parser &T error + keyword rejection verified 2026-02-13. Independent verification 2026-03-29: 87/88 items confirmed, 1 bug found (Duration/Size ratio division), 3 weak items noted.
Known Bug (RESOLVED): let bindings directly in @main body — type_interner.rs index-out-of-bounds crash. Fixed: type_interner.rs removed during hygiene refactors; 6 regression tests added.
1.1 Primitive Types
Note: Also fixed parser bug where type keywords (int, float, etc.) couldn’t be used as builtin conversion function calls.
-
Implement:
inttype — spec/08-types.md § int- Rust Tests: Type pool pre-interned at index 0; type checker handles int
- Ori Tests:
tests/spec/types/primitives.ori— 159 tests (all pass) - LLVM Support:
TypeInfo::Int→ i64 viastorage_type()+lower_int()in codegen - AOT Tests:
ori_llvm/tests/aot/spec.rs— 12 AOT tests using int
-
Implement:
floattype — spec/08-types.md § float- Rust Tests: Type pool pre-interned at index 1; type checker handles float
- Ori Tests:
tests/spec/types/primitives.ori— float literal, negative, scientific, annotated, arithmetic, comparison tests - LLVM Support:
TypeInfo::Float→ f64 viastorage_type()+lower_float()in codegen - AOT Tests:
ori_llvm/tests/aot/spec.rs— 4 AOT tests (literals, arithmetic, comparison, negation)
-
Implement:
booltype — spec/08-types.md § bool- Rust Tests: Type pool pre-interned at index 2; type checker handles bool
- Ori Tests:
tests/spec/types/primitives.ori— bool literal, logic, short-circuit tests - LLVM Support:
TypeInfo::Bool→ i1 viastorage_type()+lower_bool()in codegen - AOT Tests:
ori_llvm/tests/aot/spec.rs— 7 AOT tests using bool
-
Implement:
strtype — spec/08-types.md § str- Rust Tests: Type pool pre-interned at index 3; type checker handles str
- Ori Tests:
tests/spec/types/primitives.ori— str literal, equality, concatenation tests - LLVM Support:
TypeInfo::Str→ {i64 len, ptr data} viastorage_type()+lower_string()in codegen - AOT Tests:
ori_llvm/tests/aot/spec.rs— 1 AOT test (print_string)
-
Implement:
chartype — spec/08-types.md § char- Rust Tests: Type pool pre-interned at index 4; type checker handles char
- Ori Tests:
tests/spec/types/primitives.ori— char literal, equality tests - LLVM Support:
TypeInfo::Char→ i32 viastorage_type()+lower_char()in codegen - AOT Tests:
ori_llvm/tests/aot/spec.rs— 2 AOT tests (literals, comparison)
-
Implement:
bytetype — spec/08-types.md § byte- Rust Tests: Type pool pre-interned at index 5; type checker handles byte
- Ori Tests:
tests/spec/types/primitives.ori— byte conversion, equality tests - LLVM Support:
TypeInfo::Byte→ i8 viastorage_type() - AOT Tests:
ori_llvm/tests/aot/spec.rs— 1 AOT test (basics, equality, boundary values); fixed byte codegen bug (i64→i8 store mismatch)
-
Implement:
voidtype — spec/08-types.md § void- Rust Tests: Type pool pre-interned at index 6 (Unit); type checker handles void
- Ori Tests:
tests/spec/types/primitives.ori— void function return tests - LLVM Support:
TypeInfo::Unit→ i64 viastorage_type()+lower_unit()(LLVM void cannot be stored) - AOT Tests:
ori_llvm/tests/aot/spec.rs— 5 AOT tests using void return
-
Implement:
Nevertype — spec/08-types.md § Never- Rust Tests: Type pool pre-interned at index 7; type checker handles Never
- Ori Tests:
tests/spec/types/never.ori— 21 tests (all pass) - LLVM Support:
TypeInfo::Never→ i64 viastorage_type() - AOT Tests:
ori_llvm/tests/aot/spec.rs— 2 AOT tests (panic coercion, multi-type conditional branches)
1.1A Duration and Size Types
Proposal: proposals/approved/duration-size-types-proposal.md
Formalize Duration and Size primitive types with literal syntax, arithmetic, and conversion methods.
Lexer
-
Implement: Duration literal tokenization with all units (ns, us, ms, s, m, h)
- Rust Tests:
oric/tests/phases/parse/lexer.rs— 10+ duration tests (units, decimal, many digits) - Ori Tests:
tests/spec/lexical/duration_literals.ori— 60 tests - LLVM Support:
lower_duration()in codegen — Duration → i64 (nanosecond precision) - AOT Tests:
ori_llvm/tests/aot/spec.rs— 4 AOT tests (literals, negative, arithmetic, comparison)
- Rust Tests:
-
Implement: Size literal tokenization with all units (b, kb, mb, gb, tb)
- Rust Tests:
oric/tests/phases/parse/lexer.rs— 5+ size tests - Ori Tests:
tests/spec/lexical/size_literals.ori— 58 tests - LLVM Support:
lower_size()in codegen — Size → i64 (bytes) - AOT Tests:
ori_llvm/tests/aot/spec.rs— 3 AOT tests (literals, arithmetic, comparison)
- Rust Tests:
-
Implement: Error for floating-point prefix on duration/size literals
- Rust Tests:
oric/tests/phases/parse/lexer.rs— float_duration/size error token tests - Note: Parse errors (E0911) cannot use
#[compile_fail]which is for type errors only. Rust-level tests provide complete coverage.
- Rust Tests:
Type System
-
Implement: Duration type representation — spec/08-types.md § Duration
- Rust Tests: Type pool pre-interned at index 9;
TypeInfo::Duration - Ori Tests:
tests/spec/types/primitives.ori— Duration type tests
- Rust Tests: Type pool pre-interned at index 9;
-
Implement: Size type representation — spec/08-types.md § Size
- Rust Tests: Type pool pre-interned at index 10;
TypeInfo::Size - Ori Tests:
tests/spec/types/primitives.ori— Size type tests
- Rust Tests: Type pool pre-interned at index 10;
Arithmetic Operations
-
Implement: Duration arithmetic (+, -, *, /, %, unary -)
- Ori Tests:
tests/spec/types/primitives.ori— Duration arithmetic tests - Verified:
1s + 500ms == 1500ms,2s * 3 == 6s,-(1s) == -1s(viaori parse/cargo st) - Commutative coverage (spec/08-types.md requires both directions):
int * Durationpinned attests/spec/types/primitives.ori:1196(5 * 100ms) andtests/spec/types/duration_size_const.ori:149-153(2 * 1s); type checker accepts both directions via(Tag::Duration, Tag::Int) | (Tag::Int, Tag::Duration)inori_types/src/infer/expr/operators/dispatch.rs:52 - LLVM Support: Duration codegen exists (i64 arithmetic on nanosecond values)
- AOT Tests: Covered by
test_aot_duration_arithmeticinspec.rs
- Ori Tests:
-
Implement: Size arithmetic (+, -, *, /, %)
- Ori Tests:
tests/spec/types/primitives.ori— Size arithmetic tests - Verified:
1kb + 500b == 1500b,2kb * 3 == 6kb(viacargo st) - Commutative coverage (spec/08-types.md requires both directions):
int * Sizepinned attests/spec/types/primitives.ori:1278,1282(5 * 100b,2 * 1kb) andtests/spec/types/duration_size_const.ori:157-161(3 * 500b) - LLVM Support: Size codegen exists (i64 arithmetic on byte values)
- AOT Tests: Covered by
test_aot_size_arithmeticinspec.rs
- Ori Tests:
-
Implement: Compile error for unary negation on Size
- Verified:
-(1kb)→ E2001 “cannot negateSize: Size values must be non-negative” - Negative pin:
tests/compile-fail/size_unary_negation.ori—#[compile_fail("cannot apply operator `-` to type `size`")]rejects-son a Size binding. Dedicated compile-fail file exists at HEAD; the 2026-03-29 weak-test note (no dedicated test file) is resolved.
- Verified:
-
BUG FOUND (blocked-by BUG-02-038): Duration / Duration -> int (ratio) not implemented (found 2026-03-29)
- Spec
08-types.mdsection 8.1.2 definesd1 / d2asDuration / Duration -> int(ratio) - Type checker (
ori_types/src/infer/expr/operators/binary.rs:40-109): the same-type arithmetic arm returns the left type (Idx::DURATION) forDuration / DurationDiv — should returnIdx::INT - Evaluator (
ori_eval/src/operators/duration_size.rs):eval_duration_binarydoes not handle Div for Duration/Duration — falls through toinvalid_binary_op_for - No tests exist for
Duration / Duration - Severity: MINOR (uncommon operation, workaround: use extraction methods)
- Spec
-
BUG FOUND (blocked-by BUG-02-038): Size / Size -> int (ratio) not implemented (found 2026-03-29)
- Spec
08-types.mdsection 8.1.2 definess1 / s2asSize / Size -> int(ratio) - Type checker (
ori_types/src/infer/expr/operators/binary.rs:40-109): the same-type arithmetic arm returns the left type (Idx::SIZE) forSize / SizeDiv — should returnIdx::INT - Evaluator (
ori_eval/src/operators/duration_size.rs):eval_size_binarydoes not handle Div for Size/Size - No tests exist for
Size / Size - Severity: MINOR (uncommon operation, workaround: use extraction methods)
- Spec
-
Implement: Runtime panic for Duration overflow
- Ori Tests:
tests/spec/types/duration_overflow.ori— 15 tests (8 #fail overflow/panic, 7 boundary/identity) - Verified: Checked arithmetic in evaluator panics on add/sub/mul/div/mod/neg overflow, div-by-zero, mod-by-zero
- Ori Tests:
-
Implement: Runtime panic for negative Size result
- Ori Tests:
tests/spec/types/size_overflow.ori— 15 tests (9 #fail overflow/panic, 6 boundary/identity) - Verified: Checked arithmetic panics on sub→negative, add overflow, mul overflow, mul/div by negative, div/mod by zero
- Ori Tests:
Conversion Methods
-
Implement: Duration extraction methods (.nanoseconds(), .microseconds(), etc.)
- Verified:
1s.nanoseconds() == 1000000000,1s.microseconds() == 1000000,1s.milliseconds() == 1000,1s.seconds() == 1
- Verified:
-
Implement: Duration factory methods (Duration.from_seconds(), etc.)
- Verified:
Duration.from_seconds(5) == 5s - Note: Associated function syntax implemented in
plans/roadmap/content/type-declarations--s-3618e11f.md§ 5.9 Associated Functions
- Verified:
-
Implement: Size extraction methods (.bytes(), .kilobytes(), etc.)
- Verified:
1kb.bytes() == 1000,1mb.kilobytes() == 1000
- Verified:
-
Implement: Size factory methods (Size.from_bytes(), etc.)
- Verified:
Size.from_bytes(1024) == 1024b - Note: Associated function syntax implemented in
plans/roadmap/content/type-declarations--s-3618e11f.md§ 5.9 Associated Functions
- Verified:
Trait Implementations
-
Implement: Eq, Comparable for Duration
- Ori Tests:
tests/spec/types/duration_size_comparable.ori— 16 tests (all pass) - Verified:
1s > 500ms == true
- Ori Tests:
-
Implement: Eq, Comparable for Size
- Ori Tests:
tests/spec/types/duration_size_comparable.ori— 16 tests (all pass)
- Ori Tests:
-
Implement: Clone, Printable for Duration
- Ori Tests:
tests/spec/types/duration_size_clone_printable.ori— 26 tests (all pass)
- Ori Tests:
-
Implement: Clone, Printable for Size
- Ori Tests:
tests/spec/types/duration_size_clone_printable.ori— 26 tests (all pass)
- Ori Tests:
-
Implement: Hashable for Duration and Size
- Ori Tests:
tests/spec/types/duration_size_hashable.ori— 13 tests (all pass)
- Ori Tests:
-
Implement: Default for Duration and Size (0ns and 0b)
- Ori Tests:
tests/spec/types/duration_size_default.ori— 10 tests (all pass)
- Ori Tests:
-
Implement: Sendable for Duration and Size
- Ori Tests:
tests/spec/types/duration_size_sendable.ori— 8 tests (all pass)
- Ori Tests:
Constant Folding
-
Implement: Duration/Size constant folding in
ori_canon- Added
extract_const_value()arms forCanExpr::Duration/CanExpr::Size→ConstValue - Added
fold_binary()rules: Duration±Duration, Size±Size, Durationint, Sizeint, Duration/int, Size/int, mod, all comparisons - Added
fold_unary()rule: Duration negation (Size negation correctly rejected) - Rust Tests: 16 unit tests in
ori_canon/src/const_fold/tests.rs— addition, subtraction, comparison, cross-unit equality, negation, mul/div with int, overflow/negative rejection - Ori Tests:
tests/spec/types/duration_size_const.ori— 17 tests covering constant Duration/Size in let bindings, cross-unit arithmetic, comparisons, mixed int operations - LLVM Support: Already handled —
lower_constant()dispatches tolower_duration()/lower_size()with unit conversion
- Added
-
/tpr-reviewpassed — independent review found no critical or major issues (or all findings triaged) -
/impl-hygiene-reviewpassed — hygiene review clean. MUST run AFTER/tpr-reviewis clean. -
Subsection close-out (1.1A) — MANDATORY before starting the next subsection. Run
/improve-toolingretrospectively on THIS subsection’s debugging journey (per.claude/skills/improve-tooling/SKILL.md“Per-Subsection Workflow”): whichdiagnostics/scripts you ran, where you addeddbg!/tracingcalls, where output was hard to interpret, where test failures gave unhelpful messages, where you ran the same command sequence repeatedly. Forward-look: what tool/log/diagnostic would shorten the next regression in this code path by 10 minutes? Implement improvements NOW (zero deferral) and commit each via SEPARATE/commit-pushusing a valid conventional-commit type (build(diagnostics): ... — surfaced by section-1.1A retrospective—build/test/chore/ci/docsare valid;tools(...)is rejected by the lefthook commit-msg hook). Mandatory even when nothing felt painful. If genuinely no gaps, document briefly: “Retrospective 1.1A: no tooling gaps”. Update this subsection’sstatusin section frontmatter tocomplete. -
/sync-claudesection-close doc sync — verify Claude artifacts across all section commits. Map changed crates to rules files, check CLAUDE.md, canon.md. Fix drift NOW. -
Repo hygiene check — run
diagnostics/repo-hygiene.sh --checkand clean any detected temp files.
1.1B Never Type Semantics
Proposal: proposals/approved/never-type-proposal.md
Formalize the Never type as the bottom type with coercion rules, type inference behavior, and pattern matching exhaustiveness.
Status: All Never type features implemented and verified(2026-02-13, verified 2026-03-29). Result type layout bug fixed — TypeInfoStore resolves type variables via Pool::resolve_fully(); Result::unwrap() coerces payload to ok type.
Coercion
-
Implement: Never coerces to any type T in assignment contexts
- Ori Tests:
tests/spec/types/never.ori— 21 tests (all pass) - LLVM Support: Never coercion works in AOT — conditional branches with panic() produce correct values
- AOT Tests:
ori_llvm/tests/aot/spec.rs— 2 AOT tests (panic coercion, multi-type conditional branches)
- Ori Tests:
-
Implement: Never coerces in conditional branches
- Verified:
if true then 42 else panic(msg: "unreachable")returns int correctly
- Verified:
-
Implement: Never coerces in match arms
- Verified:
match(Red, Red -> 42, Green -> panic(msg: "nope"), Blue -> panic(msg: "nope"))returns int
- Verified:
Expressions Producing Never
-
Implement: panic(msg:) returns Never
- Verified:
if true then 42 else panic(msg: "x")type-checks as int (panic coerces to int)
- Verified:
-
Implement: todo() and todo(reason:) return Never
- Verified:
if true then 42 else todo()type-checks as int
- Verified:
-
Implement: unreachable() and unreachable(reason:) return Never
- Verified:
if true then 42 else unreachable()type-checks as int
- Verified:
Pending (Future Work)
-
Implement: break/continue have type Never inside loops
- Verified:
loop(break 42)returns int (break value used as loop result) - LLVM Support: Verified in AOT — 5 tests: basic break value, conditional break, break Never coercion, continue Never coercion, break+continue combined
- Verified:
-
Implement: Early-return path of ? operator has type Never
- Bug Fix:
ControlAction::Propagatewas not caught at function call boundaries —?errors leaked through all call frames instead of becoming the function’s return value. Fixed infunction_call.rswithcatch_propagation(). - Ori Tests:
tests/spec/control_flow/never_propagation.ori— 14 tests (Result and Option propagation, chaining, nested calls, conditional branches, multiple ? in same expression) - LLVM Support: Fixed —
TypeInfoStorenow followsPool::resolve_fully()forTag::Vartype variables;Result::unwrap()coerces payload to ok type - AOT Tests: 11 AOT tests in
ori_llvm/tests/aot/spec.rs— Result/Option constructors,?operator (ok unwrap, err propagation, chained), method dispatch (is_ok/is_err/unwrap)
- Bug Fix:
-
Implement: Infinite loop (no break) has type Never
- Fix:
infer_loop()returnedIdx::UNITfor unresolved break type; now returnsIdx::NEVER. Abreak(even without value) unifies with Unit, so unresolved truly means no break exists. - Rust Tests: Updated
test_infer_infinite_loopto assertIdx::NEVER - Verified:
@diverge () -> int = loop(())type-checks — Never coerces to int
- Fix:
-
Implement: Never variants can be omitted from match exhaustiveness
- Verified:
type MaybeNever = Value(v: int) | Impossible(n: Never)— match omitting Impossible passes - Added
is_variant_uninhabited()inori_canon/src/exhaustiveness/mod.rs - 3 unit tests + 2 Ori spec tests in
tests/spec/patterns/exhaustiveness.ori
- Verified:
-
Implement: Error E2019 for Never as struct field type
- Added
UninhabitedStructFieldvariant toTypeErrorKind - Check in
registration.rsduring struct type registration - Compile-fail test:
tests/compile-fail/never_struct_field.ori - Integration tests:
never_struct_field_rejected,never_in_sum_variant_allowed
- Added
-
Verify: Allow Never in sum type variant payloads
- Already works —
type MaybeNever = Value(v: int) | Impossible(n: Never)compiles - Exhaustiveness checker correctly treats Never variants as uninhabited
- Integration test:
never_in_sum_variant_allowed
- Already works —
1.2 Parameter Type Annotations
-
Implement: Add
type_id_to_type()helper function- Verified: Type annotations on parameters work (e.g.,
@add (a: int, b: int) -> int)
- Verified: Type annotations on parameters work (e.g.,
-
Implement: Use
Param.tywhen present ininfer_function_signature()- Verified:
@greet (name: str) -> str = namecorrectly infers str → str
- Verified:
-
Implement: Use declared return type when present
- Verified:
@typed_return () -> int = 42correctly uses declared return type
- Verified:
-
Implement: Handle
TypeId::INFERfor unannotated parameters- Verified:
@infer_param (x) -> int = xcorrectly infers x: int from context
- Verified:
1.3 Lambda Type Annotations
- WEAK TESTS: No dedicated lambda annotation test file; coverage is transitive through other test suites
-
Implement: Typed lambda parameters
(x: int) -> x + 1- Verified:
let f = (x: int) -> x + 1, f(41)returns 42
- Verified:
-
Implement: Explicit return type
(x: int) -> int = x + 1- Verified:
let f = (x: int) -> int = x * 2, f(21)returns 42
- Verified:
-
Test gap: Add dedicated
tests/spec/types/lambda_annotations.oriexercising typed lambda params and explicit return types -
/tpr-reviewpassed — independent review found no critical or major issues (or all findings triaged) -
/impl-hygiene-reviewpassed — hygiene review clean. MUST run AFTER/tpr-reviewis clean. -
Subsection close-out (1.3) — MANDATORY before starting the next subsection. Run
/improve-toolingretrospectively on THIS subsection’s debugging journey (per.claude/skills/improve-tooling/SKILL.md“Per-Subsection Workflow”): whichdiagnostics/scripts you ran, where you addeddbg!/tracingcalls, where output was hard to interpret, where test failures gave unhelpful messages, where you ran the same command sequence repeatedly. Forward-look: what tool/log/diagnostic would shorten the next regression in this code path by 10 minutes? Implement improvements NOW (zero deferral) and commit each via SEPARATE/commit-pushusing a valid conventional-commit type (build(diagnostics): ... — surfaced by section-1.3 retrospective—build/test/chore/ci/docsare valid;tools(...)is rejected by the lefthook commit-msg hook). Mandatory even when nothing felt painful. If genuinely no gaps, document briefly: “Retrospective 1.3: no tooling gaps”. Update this subsection’sstatusin section frontmatter tocomplete. -
/sync-claudesection-close doc sync — verify Claude artifacts across all section commits. Map changed crates to rules files, check CLAUDE.md, canon.md. Fix drift NOW. -
Repo hygiene check — run
diagnostics/repo-hygiene.sh --checkand clean any detected temp files.
1.4 Let Binding Types
-
Implement: Type annotation in
let x: int = ...- Verified:
let x: int = 42,let x: float = 3.14work correctly (insiderun()) - Bug fixed:
let x: int = 42directly in@mainbody no longer crashes —type_interner.rsremoved during hygiene refactors; 6 regression tests added inoric/tests/phases/common/typecheck/tests.rs
- Verified:
1.6 Low-Level Future-Proofing (Reserved Slots)
Proposal: proposals/approved/low-level-future-proofing-proposal.md
Reserve architectural space in the type system for future low-level features (inline types, borrowed views). No user-visible changes — only internal structure.
Type System Slots
-
Implement: Add
LifetimeIdtype toori_typesLifetimeId(u32)newtype withSTATICandSCOPEDconstants inori_types/src/lifetime/mod.rs- 7 unit tests (roundtrip, display, equality, hash, size assertion)
- Salsa compatibility assertion in
lib.rs
-
Implement: Add
ValueCategoryenum toori_typesBoxed(default),Inline(reserved),View(reserved) inori_types/src/value_category/mod.rs- 5 unit tests (default, predicates, display, size, hash)
- Salsa compatibility assertion in
lib.rs
-
Implement: Add
Borrowedvariant toTagenumTag::Borrowed = 34in two-child containers range, extra layout:[inner_idx, lifetime_id]- Updated all exhaustive matches:
tag.rs,pool/mod.rs,pool/format.rs,type_error/diff.rs,ori_arc/classify.rs,ori_llvm/type_info.rs - Note:
#[doc(hidden)]removed per clippy — variant is internal to compiler, fully visible
-
Implement: Add
categoryfield toStructDefcategory: ValueCategoryfield onStructDef, default toValueCategory::Boxed- Updated all 4 construction sites:
registry/types.rs,output/mod.rs,ori_llvm/type_registration.rs(×2) - WEAK TESTS: Reserved slot always Boxed; no test exercises non-Boxed category (acceptable for dormant feature)
Syntax Reservation
-
Implement: Add
inlineas reserved keyword in lexer- Recognized in
ori_lexer/src/keywords/mod.rs(reserved-future list) - Produces E0015 error: “
inlineis reserved for future use”
- Recognized in
-
Implement: Add
viewas reserved keyword in lexer- Recognized in
ori_lexer/src/keywords/mod.rs(reserved-future list) - Produces E0015 error: “
viewis reserved for future use”
- Recognized in
-
Implement: Reserve
&in type position- Parser detects
&inparse_type()and produces E1001: “borrowed references (&T) are reserved for a future version of Ori” - Recovers by parsing inner type, enabling continued parsing
- 3 parser tests:
&int,&MyType,&alone
- Parser detects
-
Implement: Parser rejects reserved keywords with helpful errors
- Lexer cooker produces
LexError::ReservedFutureKeywordwith E0015 for all 5 reserved-future keywords (asm,inline,static,union,view) - Token still interned as
Identfor parse recovery; error reported to user
- Lexer cooker produces
1.7 Section Completion Checklist
- 1.1 Primitive types complete — all 8 types verified in type checker + evaluator + LLVM codegen(2026-02-10, verified 2026-03-29)
- 1.1A Duration/Size complete — lexer, type system, arithmetic, conversions, all 7 traits(2026-02-10, verified 2026-03-29)
- 1.1B Never type fully implemented(2026-02-13, verified 2026-03-29) — infinite loop→Never,
?propagation fix, exhaustiveness for Never variants, E2019, sum variant payloads,?LLVM support (fixed type variable leak + Result::unwrap coercion) - 1.2 Parameter type annotations complete(2026-02-10, verified 2026-03-29)
- 1.3 Lambda type annotations complete(2026-02-10, verified 2026-03-29)
- 1.4 Let binding types complete(2026-02-10, verified 2026-03-29)
- 1.6 Low-level future-proofing complete(2026-02-13, verified 2026-03-29) — LifetimeId, ValueCategory, Borrowed tag, StructDef category field,
&Tparser error, keyword rejection verified - LLVM AOT tests complete — all 8 primitive types have AOT tests(2026-02-13, verified 2026-03-29); fixed byte codegen bug (i64→i8 store mismatch causing segfault)
- Loop/break/continue AOT tests — 5 tests verifying Never coercion in loops(2026-02-13, verified 2026-03-29)
-
@mainlet binding bug fixed(2026-02-13, verified 2026-03-29) —type_interner.rsremoved during hygiene refactors; 6 regression tests added - Independent verification passed — 87/88 items confirmed, 1 bug found, 3 weak items noted
Verification Findings (2026-03-29)
- BUG FOUND (1): Duration/Size ratio division — recorded at w-56e76a6f below; blocked-by
bug-tracker/plans/BUG-02-038/. - WEAK TESTS (3): recorded at w-844fab75 (Size negation — since resolved by
tests/compile-fail/size_unary_negation.ori), w-afe47e3e (lambda annotations — open gap owned by w-b6cb98c7), and w-41cdbaae (StructDef category — accepted, dormant reserved slot).
Section 1 complete. All subsections (1.1-1.4, 1.6) implemented and verified. Independent verification 2026-03-29 confirmed completion with the gaps dispositioned above.
- AUDIT GAP (blocked-by bug): Duration / Duration -> int and Size / Size -> int ratio division not implemented — spec
08-types.mdsection 8.1.2 defines these but type checker returns wrong type and evaluator rejects the operation. Files:ori_types/src/infer/expr/operators/binary.rs,ori_eval/src/operators/duration_size.rs. Owned bybug-tracker/plans/BUG-02-038/. - RESOLVED weak-test: Size unary negation — dedicated negative pin exists at
tests/compile-fail/size_unary_negation.ori(#[compile_fail("cannot apply operator `-` to type `size`")]). The 2026-03-29 “no dedicated#compile_failtest file” note is stale; not an open gap. Single disposition: pinned by the cited test file (see 1.1A w-a34bdd27). - OPEN test gap (acceptance withdrawn): Lambda annotations 1.3 — no dedicated
tests/spec/types/lambda_annotations.oriexists at HEAD; transitive coverage through other suites does NOT satisfy the dedicated-file gap. Single disposition: the open test-gap item w-b6cb98c7 (1.3) owns the work. - ACCEPTED weak-test: StructDef category field — reserved slot always Boxed, no behavioral test. Acceptable for a dormant reserved-slot feature (no observable behavior to pin); not an open gap.
-
/tpr-reviewpassed — independent review found no critical or major issues (or all findings triaged) -
/impl-hygiene-reviewpassed — hygiene review clean. MUST run AFTER/tpr-reviewis clean. - Subsection close-out (1.7) — MANDATORY before starting the next subsection. Run
/improve-toolingretrospectively on THIS subsection’s debugging journey (per.claude/skills/improve-tooling/SKILL.md“Per-Subsection Workflow”): whichdiagnostics/scripts you ran, where you addeddbg!/tracingcalls, where output was hard to interpret, where test failures gave unhelpful messages, where you ran the same command sequence repeatedly. Forward-look: what tool/log/diagnostic would shorten the next regression in this code path by 10 minutes? Implement improvements NOW (zero deferral) and commit each via SEPARATE/commit-pushusing a valid conventional-commit type (build(diagnostics): ... — surfaced by section-1.7 retrospective—build/test/chore/ci/docsare valid;tools(...)is rejected by the lefthook commit-msg hook). Mandatory even when nothing felt painful. If genuinely no gaps, document briefly: “Retrospective 1.7: no tooling gaps”. Update this subsection’sstatusin section frontmatter tocomplete. -
/sync-claudesection-close doc sync — verify Claude artifacts across all section commits. Map changed crates to rules files, check CLAUDE.md, canon.md. Fix drift NOW. - Repo hygiene check — run
diagnostics/repo-hygiene.sh --checkand clean any detected temp files.