# Developer validation tiers

`tests/run.sh` is the repository-level validation owner. The production
`gododin test` command dispatches its `quick` and `locked` tiers here after
resolving the required compiler explicitly; the shell entrypoint remains useful
for focused developer invocation. Neither path finds Odin on `PATH`.

The [implementation plan's C1–C5 checkpoints](../docs/implementation-plan.md#verification-checkpoints-and-implementation-efficiency)
own when broad validation runs during active development. Use focused checks
while implementing coherent changes, then batch SDK, native/editor/render/export,
and benchmark evidence. Do not invoke overlapping tiers or repeat successful
checks for unchanged artifacts. This document describes each tier's coverage;
it does not require a complete run after every edit.

## Checkout contributor entry

Consumer installation belongs in the [usage guide](../docs/getting-started.md).
A checkout is the authority for repository tools, fixtures and validation;
it is not required in an installed project's ancestry.

Copy [`.gododin/local.example.toml`](../.gododin/local.example.toml) into the
checkout's ignored `.gododin/local.toml`, fill canonical absolute paths and
select exactly one first-CLI mode. For external Odin, build the initial CLI
with the lock's version-matched compiler:

```sh
/absolute/exact/Odin/odin build /absolute/gododin/cmd/gododin \
  -vet -strict-style -warnings-as-errors \
  -out:/absolute/private/bin/gododin
```

For prebuilt entry, authenticate and extract the first-CLI archive named by
`gododin.lock` into the configured cache. Both modes immediately hand off to
`toolchain ensure`; neither finds a compiler on `PATH` or falls back to the
other mode. A checkout-authority consumer names the checkout explicitly:

```sh
/absolute/authenticated/gododin init \
  --project-root /absolute/gododin/projects/my_subsystem \
  --authority-root /absolute/gododin --project-key my_subsystem
```

Its committed `authority_root` is relative; installed projects instead use
an ignored SDK link. For routine validation use the version-matched local
compiler explicitly:

```sh
tests/run.sh quick --odin /absolute/path/to/Odin/odin
```

The quick tier records development evidence and never promotes support.
Installed projects refuse repository `quick`/`locked`, fixed qualification
fixtures and authority update. Application tests use
[public `run`](../docs/usage/development-loop.md#run-an-application-test).

## Evaluation frame pacing

Godot evaluations and benchmarks run with engine VSync disabled and no maximum
FPS cap by default. Launch game evals with `--disable-vsync --max-fps 0` before
the user-argument separator. Directly launchable eval scenes also set and report
the runtime values before measuring, and fail if the requested engine state is
not established. A headless run reports VSync as not applicable; its dummy display
server does not establish rendering throughput.

This rule applies to performance and visual evaluation games, not ordinary
interactive play or editor use. A test specifically evaluating synchronized
presentation must name that exception and its workload. Pure Odin and shim
benchmarks have no display pacing. Engine-reported VSync off does not prove that
the graphics driver or window compositor adds no presentation waits.

Retain earlier paced receipts unchanged. New uncapped measurements must record
the pacing mode, build profile, renderer, workload and frame statistics separately;
do not present earlier VSync-limited frame numbers as uncapped throughput.

## Tier coverage

Every active tier uses the sole exact engine selected by
[`gododin.lock`](../gododin.lock) and the [active-target record](../docs/versioning.md#active-target-and-historical-evidence).
Generation uses that target alone; retained receipts do not qualify a newer pin. Nothing here validates, generates, or
projects against exact 4.7.2 or exact 4.6.2. Both are frozen history whose
vendored corpora receive digest verification and nothing more; do not add a
tier, case, harness, or projection that runs either.

The default `quick` tier uses an explicitly configured local Odin executable. It
requires the locked version, records the executable hash and root, parses the
portable and local TOML inputs, syntax-checks repository shell scripts, runs a
small strict Odin compile/execute test, runs the focused engine-model cases, and
normalizes only the complete selected Godot input corpus. The routine model check
resolves every emitted source pointer, verifies exact category/member counts, and
pins the canonical model digest while keeping that normalized model transient.
The complete raw publication check projects that selected corpus once, reproduces
the exact-target raw source and coverage twice from the same model, strictly
compiles the staged package, and rejects any drift from `bindings/raw` or its
generation receipt. The superseded partial raw vertical-slice generation is not
repeated. The tier also validates the reviewed typed policy against only
the selected target's API records, checks the locked publication hashes and derived
direct-call classifications, compiles the checked-in typed plan/facade, and runs a
fake-engine behavior test across all 11 operations, ownership commits, capability
rejection, dynamic Variant cleanup, and final Ref destruction. Candidate-target
regeneration and cross-version diffing do not exist any more: the projection has
one target. They return only if a post-1.0 decision names a specific exact
version and reinstates the comparison. The quick
tier also runs four production
command-authority tests, the 22-test shared/external/prebuilt first-CLI matrix,
the six documentation-source tests, the six transactional update tests, four
documentation-projection tests, selected-target exact-source verification,
integrity of the frozen historical documentation snapshot, independent GDI
regeneration, and ADR 0040's deterministic C/Odin ABI runner. Phase 2 adds the
serialized 21-case strict Host unit suite (its stable
trampoline router is intentionally process-global) and authenticated
passive-image matrix to this tier. The completed Phase 3 gate strictly compiles
the selected generated catalog projection, runs the catalog contract, projection,
continuity, and project-input tests, the four pure-weather tests, validates the
historical native evidence receipt, and syntax-checks the frozen two-target
harness contract without launching Godot. Under the runner's additive convention
this reports 24 Phase 3 cases in
`quick`; `locked` adds one catalog drift check and eight catalog negative cases
for 33. Phase 4 adds the 22-case standalone build-owner/protocol matrix to both
active tiers. It uses a controlled six-stage child process to prove exact
config/lock target/profile binding, relocation-stable source/build identities,
six stage-failure cleanups, stale-source rejection, same-build concurrent
coalescing, newer-build supersession, inherited-lock interruption recovery,
orphaned-admission recovery, sealed no-replace publication, and separate current-
accepted/last-known-good metadata without invoking a real project compiler or
promoting support. The `locked` tier additionally retains the 22-case generalized
target-neutral project generation matrix. These routine checks do not substitute
for rerunning the exact live matrix. The tier then builds the production CLI,
extracts and invokes the sealed prebuilt twice under hostile inherited state, and
runs the public current-lock `update --check` path. It also runs three public
`gododin init` cases: one initialization into a temporary root under the
repository, which must copy the authority lock byte for byte; a `build-state`
call on the result, whose unpublished-state failure is what proves the
production project reader accepted the written configuration and lock; and a
second initialization on the same root, which must refuse rather than replace.
The locked tier adds two cases on that same project: its first public debug build
must publish an accepted artifact, and `build-state` must expose that exact-target
publication. It then publishes persistent generated output, verifies it, injects
drift and requires `check` to refuse it without mutation, and repairs it through
`generate`. It then holds the build owner lock the way an admitted build does
and requires `clean` to refuse with `CLEAN_BUILD_IN_FLIGHT` without removing
anything. With the lock released, `clean` removes generated and build state
while preserving the managed toolchain, and the project rebuilds from a clean
persistent state. The
initializer's own strict-validation, rollback, and refusal matrix is in the
`cmd/gododin` package tests.
The CLI build check is host-relative (ADR 0065). The darwin recording host
requires an arm64 Mach-O with a macOS 13.0 floor, a valid ad-hoc signature,
and only `/usr/lib/libSystem.B.dylib` as a dynamic dependency; a Linux host
requires an ELF64 x86-64 dynamic executable whose dynamic dependencies stay
inside the recorded libc closure. Cases whose recorded evidence is a darwin
binary — executing the sealed prebuilt, the managed-compiler behavior probe,
the Mach-O passive-image and ABI fixtures, and the external-Odin live
authority — run on a darwin host and print explicit skip sentinels on other
hosts until those platforms record their own artifacts:

```sh
tests/run.sh
tests/run.sh quick --odin /absolute/path/to/Odin/odin
```

The matching public entrypoints are:

```sh
/absolute/path/to/gododin test quick --project-root /absolute/gododin/checkout
/absolute/path/to/gododin test locked --project-root /absolute/gododin/checkout
/absolute/path/to/gododin test native --project-root /absolute/gododin/checkout
/absolute/path/to/gododin test render --project-root /absolute/gododin/checkout/fixtures/compositor
/absolute/path/to/gododin test export --project-root /absolute/gododin/checkout/fixtures/compositor
```

The recording-host preflight and the clean-machine promotion sequence that use
these entrypoints are owned by [`docs/releasing.md`](../docs/releasing.md).

Installed projects deliberately refuse these repository and fixed-fixture test
tiers. Phase 6 instead owns one packed unrelated-consumer gate:

```sh
tools/release/test_installed_sdk.sh \
  --project-root /absolute/gododin \
  --odin /absolute/exact/Odin/odin \
  --godot /absolute/exact/locked-Godot \
  --release <release-identity>
```

It packs the SDK twice byte-identically, authenticates every extracted member,
initializes and builds outside checkout ancestry, exercises its negative
substitution cases, relocates the SDK, attaches it without changing committed
project files, and rebuilds. Its exact pass sentinel is owned by the Phase 6 exit
criteria in [`docs/implementation-plan.md`](../docs/implementation-plan.md).

Phase 7 keeps the flagship example's heavier evidence separate from that minimal
consumer gate:

```sh
examples/cavern_lab/test.sh \
  --sdk /absolute/extracted/sdk \
  --odin /absolute/exact/Odin/odin \
  --godot /absolute/exact/locked-Godot \
  --evidence-dir /absolute/new-cavern-evidence
```

That harness owns the exact installed debug verification and visual processes,
the release benchmark, byte equality, separate generation/presentation timing,
and zero-owner shutdown. Its [current frozen qualification](../examples/cavern_lab/README.md#verification-harnesses)
runs in both normal repository tiers without rerunning the live benchmark.
The contract requires matching lock, catalog, authored/generated inputs and
toolchain facts, and verifies the retained execution trace. The current
installed-SDK receipt also requires cold editor startup without preparatory
import and both exports without native image launcher variables. Missing,
corrupt or stale evidence is a failure; the former engine-gated skip has been
removed.

Both active tiers also run the native-components reload worker's package cases:
- pending promotion, with the displaced record released;
- active cancellation, with the token reset for the next request;
- a cancel admitted before pickup.

They also require the worker template used by the reload and restart harnesses
to equal that tested package apart from its revision marker, so a worker fix
cannot land in only one copy.

`quick` uses the authenticated sealed managed compiler. `locked` uses
`testing.locked_odin_executable` from the authority checkout's ignored local
configuration because its external-Odin behavior probe requires an owner-writable
exact compiler root; pointing it at `.gododin/tools` is rejected. `native` runs
the configured native-basic project through the production run gate. `render`
runs the configured compositor under Forward+/Metal, while `export` drives the
complete recovery-editor, accepted-editor, run, debug/release export, and
exported-application matrix in disposable local evidence. The latter two are
restricted to the authority checkout's configured compositor fixture.

The completed Phase 4 tiers also run seven checksum-addressed candidate-
input cache cases: strict authority validation, fresh immutable fill and reuse,
producer failure, wrong bytes, symlink rejection, corrupt-cache non-repair, and
missing-producer cleanup, plus concurrent exact-winner revalidation. These prove
only byte acquisition/cache ownership. They do not prove an Odin archive, source
build, compiler identity, or managed toolchain publication by themselves. The
separate managed-Odin adapter and public prebuilt integration validate the locked
archive/member/root manifests, compiler/runtime hashes and behavior, immutable
publication, and exact handoff before reporting toolchain readiness.
The minimal behavior probe is intentionally compiled with one Odin worker: it is
an identity check rather than a throughput workload, and the exact locked
compiler can deadlock while joining idle workers after repeated sanitized checks.

Phase 5 adds the rendering, typed-surface, semantic-signature, and bulk-transfer
cases to both active
tiers: the render facade's ownership contracts, the compositor subsystem and its
offline harness contract, the `typedgen` cases, the typed-surface demand and live
receipt contracts, matching and mismatched Signal/Callable compiler cases, the
pure density producer, the staging owner's compensating-control cases, the
density-field-upload measurement, the typed-versus-raw render-cost measurement,
the particle staging fixture's producer, compose, and counter cases, the order
staging fixture's producer, choreography, and counter cases, the debug draw
fixture's helper and scenario cases, and the
configured-project authority check. Each measurement reruns its workload
rather than reconstructing its figures. The bulk tier remeasures
against the instrumented engine and requires
`fixtures/bulk_transfer/bulk-transfer-evidence.json` to reproduce byte for byte,
with the receipt's digest carried in the pinned pass sentinel. The
render-cost tier likewise requires
`fixtures/render_cost/typed-raw-cost-evidence.json` to reproduce byte for byte.
The particle staging tier likewise reruns the three transports at three
populations and requires `fixtures/particle_staging/particle-staging-evidence.json`
to reproduce byte for byte; that fixture is not a gate pass, and the pin guards
drift only. The order staging tier likewise reruns the draw-order-application
workload and requires `fixtures/order_staging/order-staging-evidence.json` to
reproduce byte for byte; the same boundary applies. The debug draw tier
likewise reruns the debug-batch-frame scenario and requires
`fixtures/debug_draw/debug-draw-evidence.json` to reproduce byte for byte;
that fixture is the DevX consumer lane, and the pin guards its documented
batch behavior only.
The
configured-project check binds `fixtures/compositor/gododin.toml`'s Phase 4
composition, requires its lock to be byte-identical to the repository lock, and
requires the fingerprint compiled into the generated compositor catalog to equal
the one both compositor receipts record. The tier reports 80 Phase 5 cases in
`quick`; `locked` adds the render-policy and typed-package drift checks for 82.

The Phase 5 harness contract is offline. Requalifying the Phase 4 editor/export
matrix with the real compositor artifact is a live exact-target matrix and is not
part of any tier. It needs a built CLI, the exact Godot executable, and a
`.gododin/local.toml` inside `fixtures/compositor` naming the same Godot
executable and export home as the repository's:

```sh
fixtures/compositor/live/phase4.sh --cli /absolute/built/gododin --godot /absolute/canonical/Godot-4.8-dev4 --godot-sha256 <sha256> --evidence-dir /absolute/new-directory
```

It publishes through `gododin build`, then drives the recovery editor, the
accepted editor, `gododin run`, and both exports, executes both exported
applications, and requires all three rendering processes to reproduce the frozen
inspected PNG. Rerun it and rewrite
`fixtures/compositor/phase4-evidence.json` whenever the compositor artifact,
the configured project, or the build/editor/run/export path changes.

The Godot-free language protocol is deferred post-1.0 history and is intentionally
absent from both active compiler tiers. Its focused legacy tier retains the 81
mechanically counted cases for broker-owned request identity, bounded ownership,
revision/supersession behavior, cancellation and shutdown, and authenticated
compiler-event provenance:

```sh
tests/run.sh legacy-language --odin /absolute/path/to/Odin/odin
```

The checked-in exact-target raw package is regenerated only through the same
authenticated publication path used by the quick-tier drift check:

```sh
/absolute/path/to/Odin/odin run tools/apigen -- raw --odin /absolute/path/to/Odin/odin --write
/absolute/path/to/Odin/odin run tools/apigen -- raw --odin /absolute/path/to/Odin/odin --check
```

The typed fixture policy has a selected-target pre-1.0 check. The complete
cross-target command remains available for explicitly scoped post-1.0 work:

```sh
/absolute/path/to/Odin/odin run tools/apigen -- fixture-policy --odin /absolute/path/to/Odin/odin --check-selected
/absolute/path/to/Odin/odin run tools/apigen -- fixture-policy --odin /absolute/path/to/Odin/odin --check
```

Both check the one target. `--check-selected` verifies the published facade
against the selected target's API records; full `--check` additionally
reprojects the policy and Host-compatibility publication from the selected
semantic model. The `compare-targets` command that published a cross-target
availability report is gone with the second target; reinstating a comparison is
part of whatever post-1.0 decision names another exact version.

Exact official documentation and the reduced Host/image ABI have focused owners:

```sh
/absolute/path/to/Odin/odin test tools/docsource -vet -strict-style -warnings-as-errors
/absolute/path/to/Odin/odin test tools/docgen/tests -vet -strict-style -warnings-as-errors
/absolute/path/to/Odin/odin run tools/docsource/runner -- verify --repo-root /absolute/repository/root
/absolute/path/to/Odin/odin run tools/docgen/runner -- --repo-root /absolute/repository/root --output-root /new/empty/output
abi/image/run.sh --odin /absolute/path/to/Odin/odin
tools/cataloggen/run.sh check /absolute/path/to/exact/evidence/odin
tools/cataloggen/run.sh test /absolute/path/to/exact/evidence/odin
buildcoord/test.sh /absolute/path/to/exact/evidence/odin
fixtures/native_basic/live/test.sh
```

The documentation runner output must match `docs/generated/engine.gdi` and its
receipt byte-for-byte. These checks are included in `quick`; the explicit commands
are useful for focused diagnosis.

`--allow-compiler-drift` is available only for smoke testing. Its result is
labelled `unlocked-smoke` and cannot update a receipt, accepted evidence, a
generated baseline, or a support status.

The `locked` tier requires the exact project-image evidence compiler hash from
`gododin.lock`. It runs the same active 1.0 cases with that exact compiler. Phase
2 additionally requires the exact pinned Godot snapshot and runs three clean Host lifecycle
processes plus isolated registration, construction, and destroy-callback failure
processes; all six must close with zero owned counters and restart-required
evidence. The Phase 3 locked gate additionally regenerates the
compiler-owned catalog in check mode and runs its determinism, relocation,
corruption, provenance, and compiler-negative matrix. It authenticates the
exact-target receipt but does not rerun that Godot process.
Do not use the historical two-target live builder before 1.0. The tier also
invokes the external-Odin path through the real public first command and requires
exactly one shared handoff. Use it when compiler output or identity is part of the
assertion:

```sh
tests/run.sh locked --odin /absolute/path/to/exact/evidence/odin --godot /absolute/path/to/exact/Godot
```

The raw-bottle product tiers are retired. Historical bootstrap probes remain
under `probes/` and are not routine validation inputs. The accepted prebuilt is
the lock-bound ustar publication under `releases/distributions/`; quick extracts
it to a private cache and proves checksum, metadata, permissions, hostile-
environment containment, exact handoff, and repeated failure recovery.

Ignored `.gododin/local.toml` may make the explicit paths convenient:

```toml
format = 1

[first_cli]
mode = "external_odin"

[first_cli.external_odin]
executable_path = "/absolute/path/to/exact/Odin/odin"
odin_root = "/absolute/path/to/exact/Odin"
home_directory = "/absolute/private/gododin-home"
temporary_directory = "/absolute/private/gododin-tmp"

[testing]
odin_executable = "/absolute/path/to/local/Odin/odin"
locked_odin_executable = "/absolute/path/to/exact/evidence/odin"
godot_4_8_0_executable = "/absolute/path/to/exact/Godot"
```

Select `prebuilt_gododin` instead with a complete
`[first_cli.prebuilt_gododin]` containing absolute `cache_root`,
`home_directory`, and `temporary_directory`; never configure both mode sections.
The testing paths select validation inputs only. Because the validation harness
itself is Odin, every tier also needs the explicit or locally configured
development compiler used to launch it.
