The Courant Test.

Thirty-one real runs. Labels locked.

CaseSolverRunsFaultedHealthySplit
Lid-driven cavityicoFoam761held in
Backward-facing stepsimpleFoam761held in
Turbulent cavitypisoFoam541held in
Dam breakinterFoam312held in
Planar contractionpimpleFoam321held in
Compressible cavityrhoPimpleFoam321held in
Heated roombuoyantPimpleFoam321held out

OpenFOAM v2406 tutorials, run in Docker, faults injected by editing the case the way an engineer’s mistake would. The labels, the scorer and the split are hash-locked; the scorer refuses to score when a lock changes without a recorded relabel decision.
certification/RESULTS.json 6f67ffab5cbed10d…

courant/ctest/data/judge-v0.labels.jsonl 207c35b8350ae1fa…

courant/ctest/score.py 452871b5230376ed…

courant/ctest/splits.py 2eb270d55e1e9db5…

Score any judge.

FIG. T1Three judges on the same 31 runs, verbatimRM-01 v6 · 11 October 2026
$ courant test run --judge courant
all       tasks  31 · accuracy 31/31 · false accepts 0/23 · false alarms 0/8 · abstain 0/31 · top-2 23/23
held_in   tasks  28 · accuracy 28/28 · false accepts 0/21 · false alarms 0/7 · abstain 0/28 · top-2 21/21
held_out  tasks   3 · accuracy 3/3 · false accepts 0/2 · false alarms 0/1 · abstain 0/3 · top-2 2/2

$ courant test run --judge constant:TRUSTWORTHY
all       tasks  31 · accuracy 8/31 · false accepts 23/23 · false alarms 0/8 · abstain 0/31 · top-2 0/23
held_in   tasks  28 · accuracy 7/28 · false accepts 21/21 · false alarms 0/7 · abstain 0/28 · top-2 0/21
held_out  tasks   3 · accuracy 1/3 · false accepts 2/2 · false alarms 0/1 · abstain 0/3 · top-2 0/2

$ courant test run --judge constant:NOT_TRUSTWORTHY
all       tasks  31 · accuracy 23/31 · false accepts 0/23 · false alarms 8/8 · abstain 0/31 · top-2 0/23
held_in   tasks  28 · accuracy 21/28 · false accepts 0/21 · false alarms 7/7 · abstain 0/28 · top-2 0/21
held_out  tasks   3 · accuracy 2/3 · false accepts 0/2 · false alarms 1/1 · abstain 0/3 · top-2 0/2

$ courant test run --judge llm:<provider>:<model>
a model, scored the same way

A judge that trusts every run is right on 8 of 31 and accepts every wrong result. One that trusts nothing accepts no wrong result and rejects every good one. Courant: 31 of 31 correct, 0 of 23 wrong results accepted (95% CI 0–14.3%), 0 of 8 good results rejected (95% CI 0–32.4%). Held out of development: 3 of 3 correct.

Every run, every verdict.

RunTruthVerdictRuleLeading causeWhy
Heated room
healthy
healthyAcceptVER-5.6NUM.MISSING_ADJUSTABLE_DTNo check failed.
Heated room
cfl blowup
faultedRejectVER-5.2NUM.MISSING_ADJUSTABLE_DTrun.crash · value SIGFPE
Heated room
laminar on turbulent
faultedRejectVER-5.4PHYS.LAMINAR_TURBULENTphysics.laminar_unstable
Lid-driven cavity
healthy
healthyAcceptVER-5.6—No check failed.
Lid-driven cavity
bad initial field
faultedRejectVER-5.2NUM.CFL_VIOLATIONrun.crash · value SIGFPE
Lid-driven cavity
cfl blowup
faultedRejectVER-5.3NUM.CFL_VIOLATIONcfl.max · value 9.66086 · threshold 1.0
Lid-driven cavity
extreme aspect ratio
faultedRejectVER-5.2NUM.CFL_VIOLATIONrun.crash · value SIGFPE
Lid-driven cavity
high skewness
faultedRejectVER-5.2NUM.CFL_VIOLATIONrun.crash · value SIGFPE
Lid-driven cavity
missing dict
faultedRejectVER-5.2ENV.MISSING_DICTrun.crash · value FOAM FATAL ERROR
Lid-driven cavity
transport units
faultedRejectVER-5.4PHYS.TRANSPORT_UNITSphysics.nu · value 1e-09
Dam break
cfl blowup
healthy, relabelledAcceptVER-5.6NUM.CFL_VIOLATIONNo check failed.
Dam break
healthy
healthyAcceptVER-5.6PHYS.LAMINAR_TURBULENTNo check failed.
Dam break
fixed dt on adaptive solver
faultedRejectVER-5.3NUM.MISSING_ADJUSTABLE_DTcfl.max · value 7.37424 · threshold 1.0
Planar contraction
healthy
healthyAcceptVER-5.6PHYS.LAMINAR_TURBULENTNo check failed.
Planar contraction
cfl blowup
faultedRejectVER-5.3NUM.CFL_VIOLATIONconvergence.residual · value 0.015446261
Planar contraction
fixed dt on adaptive solver
faultedRejectVER-5.3NUM.MISSING_ADJUSTABLE_DTconvergence.residual · value 0.015446261
Turbulent cavity
healthy
healthyAcceptVER-5.6—No check failed.
Turbulent cavity
cfl blowup
faultedRejectVER-5.3NUM.CFL_VIOLATIONconvergence.residual · value 0.070853
Turbulent cavity
laminar on turbulent
faultedRejectVER-5.2PHYS.LAMINAR_TURBULENTrun.crash · value SIGFPE
Turbulent cavity
loose solver tolerance
faultedRejectVER-5.4NUM.SOLVER_TOLERANCEsolver.loose_tolerance · value 0.1 · threshold 0.0001
Turbulent cavity
wrong turbulence model
faultedRejectVER-5.2ENV.MISSING_DICTrun.crash · value FOAM FATAL ERROR
Compressible cavity
healthy
healthyAcceptVER-5.6NUM.MISSING_ADJUSTABLE_DTNo check failed.
Compressible cavity
cfl blowup
faultedRejectVER-5.2NUM.MISSING_ADJUSTABLE_DTrun.crash · value SIGFPE
Compressible cavity
missing dict
faultedRejectVER-5.2ENV.MISSING_DICTrun.crash · value FOAM FATAL ERROR
Backward-facing step
healthy
healthyAcceptVER-5.6—bounds.turbulence · value 4.0
Backward-facing step
mass imbalance
faultedRejectVER-5.4NUM.SOLVER_TOLERANCEresidual.not_converged · value 0.0097967 · threshold 0.001
Backward-facing step
oscillation
faultedRejectVER-5.2NUM.OVER_RELAXATIONrun.crash · value SIGFPE
Backward-facing step
over relaxation
faultedRejectVER-5.2NUM.OVER_RELAXATIONrun.crash · value SIGFPE
Backward-facing step
overconstrained pu
faultedRejectVER-5.4BC.OVERCONSTRAINED_PUbc.overconstrained
Backward-facing step
residual plateau
faultedRejectVER-5.4CONV.RESIDUAL_PLATEAUresidual.not_converged · value 0.00186427 · threshold 0.001
Backward-facing step
unbounded scheme
faultedRejectVER-5.3NUM.UNBOUNDED_SCHEMEbounds.turbulence · value 208.0

The 31 records as JSON: /data/verdicts.json

Written down before the run.

HypothesisStatementThresholdObservedResult
RM-01.H1at most 2 false accepts over the faulted runs≤ 20 of 23supported
RM-01.H2zero false alarms over the healthy runs== 00 of 8supported
RM-02.H1.held_infault in the top two on at least 18 held-in faulted tasks≥ 1821 of 21supported
RM-02.H1.held_outfault in the top two on at least 3 held-out faulted tasks≥ 32 of 2refuted

The held-out hypothesis is recorded as refuted, not re-scored. Its threshold was set when two solver families were held out; with one, only two faulted runs remain, so three could not be reached. Both of the two were ranked correctly.

Point it at a folder of past runs.

Become a design partner

Open source · free