Reproduce, with the run directory this repository ships
$ launchbound apply runs/reduce-stable-metal --kernel reduce-stable
// ==== launchbound apply: reduce-stable / c1-43e865c2e1620697 ====
// measured: 0.0968 ms [0.0968, 0.0969] on Apple M4 Pro (gate cc metal, measured)
...
pub const TILE: usize = 128;
pub const LB_MAX: u32 = 256;
verifying the emitted specialization with cargo reconverge --strict ...
error: the chosen configuration no longer passes the gate: ToolError { detail:
"cargo reconverge exited 2:\nerror: `metal` is not a compute capability;
expected e.g. `8.6`" } — refusing to emit
$ echo $?
2
Why it can never succeed
The Metal path has no convergence gate — deliberately, and report says so on
every render:
*** NO convergence gate exists on the Metal path: the same bug class is NOT checked ***
So a Metal run records gate_cc: "metal", a sentinel rather than a compute
capability. cmd_apply then hands that straight to the gate:
cc: report.gate_cc.clone(),
and reconverge — correctly — refuses, because metal is not a compute
capability. There is no input that makes this work: the failure is structural,
so apply cannot emit for any Metal run at all. launchbound tune --backend metal is a documented backend with a committed example run, and the
final step of the documented pipeline refuses its output.
Three smaller things in the same line
- It is a
Debug dump. ToolError { detail: "…\n…" } — a Rust struct with
escaped newlines, in a message a user is meant to act on.
- "no longer passes the gate" says a regression happened. Nothing
regressed: on this path the gate never ran, and cannot. The sentence
misdiagnoses a category error as a change.
- It emits and then refuses to emit. The
params.rs is printed to stdout
before verification runs, so "refusing to emit" arrives after the emission —
and a reader who piped stdout to a file has the file.
Fix
Decide what apply means on an ungated run, then say it once:
- Refuse deliberately, early, and by name — before printing anything:
"this run was measured on the Metal path, which has no convergence gate
(docs/SAFETY.md §3.4); there is no gate verdict to re-verify. Re-run the
configuration through launchbound prune --cc <target> for the part you
will deploy on." That is honest and keeps stdout clean.
- Or emit with the notice
report already carries, and skip a
verification that has nothing to verify — the specialization is still the
thing that measured fastest, and the Metal notice is what qualifies it.
Either is defensible; the present behaviour is neither. Whichever is chosen,
verification should happen before stdout is written, so a refusal is a
refusal.
The Debug formatting should go regardless: ToolError wants a Display that
prints its detail.
Done when
apply on a Metal run gives one clear answer, before it prints anything, and
no user-facing message contains a Rust struct literal.
Reproduce, with the run directory this repository ships
Why it can never succeed
The Metal path has no convergence gate — deliberately, and
reportsays so onevery render:
So a Metal run records
gate_cc: "metal", a sentinel rather than a computecapability.
cmd_applythen hands that straight to the gate:and reconverge — correctly — refuses, because
metalis not a computecapability. There is no input that makes this work: the failure is structural,
so
applycannot emit for any Metal run at all.launchbound tune --backend metalis a documented backend with a committed example run, and thefinal step of the documented pipeline refuses its output.
Three smaller things in the same line
Debugdump.ToolError { detail: "…\n…" }— a Rust struct withescaped newlines, in a message a user is meant to act on.
regressed: on this path the gate never ran, and cannot. The sentence
misdiagnoses a category error as a change.
params.rsis printed to stdoutbefore verification runs, so "refusing to emit" arrives after the emission —
and a reader who piped stdout to a file has the file.
Fix
Decide what
applymeans on an ungated run, then say it once:"this run was measured on the Metal path, which has no convergence gate
(docs/SAFETY.md §3.4); there is no gate verdict to re-verify. Re-run the
configuration through
launchbound prune --cc <target>for the part youwill deploy on." That is honest and keeps stdout clean.
reportalready carries, and skip averification that has nothing to verify — the specialization is still the
thing that measured fastest, and the Metal notice is what qualifies it.
Either is defensible; the present behaviour is neither. Whichever is chosen,
verification should happen before stdout is written, so a refusal is a
refusal.
The
Debugformatting should go regardless:ToolErrorwants aDisplaythatprints its detail.
Done when
applyon a Metal run gives one clear answer, before it prints anything, andno user-facing message contains a Rust struct literal.