This is a design (not yet implemented). It proposes that Error-Lang become a second front end to the portable trope-checker (hyperpolymath/trope-checker), lowering its Echo operations and its stability factors to the language-neutral Trope IR (v0.1,preventprofile) and consuming the checker’s verified verdict and witness. It defines the object/effect/grade correspondence, the verdict mapping, the architecture (reference, never vendor), and — most importantly — the per-front-end lowering-correctness obligations the trope-checker does not discharge for us.
Both systems already sit on the same substrate: the
echo-types graded-loss line, cited
verbatim by docs/Echo-Decomposition.adoc and by the trope calculus
(trope-checker/spec/calculus.adoc, "Provenance of the ideas"). This document
makes that shared lineage operational.
Error-Lang grades instability with calculateStability (compiler/src/Types.res
lines 270–274):
calculateStability(factors) = max(0, 100 + Σ stabilityImpact(factor))Every stabilityFactor is mapped to a single negative integer and the integers
are summed. That is a scalar collapse of structured loss. The trope-particularity
calculus exists to reject exactly this move — its load-bearing thesis
(calculus.adoc §3) is:
A grade is not a scalar: two operations can lose the same amount yet differ in kind and in honesty.
So the calculus’s three-coordinate grade is a principled upgrade of Error-Lang’s
stability model. It lets us keep which particularity degraded, whether the loss
is recoverable, and whether it is honest — and it yields a use-relative
verdict with a witness edge ("the operation to repair") in place of an opaque
0–100 number. For a language whose entire identity is the visible decomposition
of structure (Echo-Decomposition.adoc, "Decomposition must be visible"), this is
a capability upgrade, not ornament.
Two further alignments make the fit unusually tight:
-
The Echo operations already are trope effects.
echo,echo_to_residue,echo_input,echo_outputimplement witness-retention and irreversible erasure — which the calculus namespreserve,detach, and fieldproject(§5). -
The verification toolchains already overlap. The trope-checker’s core is an Agda reference plus an Idris2 implementation (the
trope-checkerrepo’s Idris2 core,Main.idr); Error-Lang already carries an Idris2 proof of the scalar bound (src/abi/Stability.idr). The integration generalises that proof’s target from a clamped integer to a checked grade.
A trope is a property-instance over the field set
Φ = {quality, bearer, context, record} (calculus.adoc §2). Error-Lang’s
Echo<A,B> — a retained witness x : A with the visible output y : B it
reached — populates Φ as:
| Φ field | Echo content | Justification |
|---|---|---|
|
the witness |
the particular entity the result is a result of |
|
the reached output |
the situated property borne by |
|
the function |
what individuates this fibre element |
|
the runtime pairing |
honest provenance of how |
| Echo form | Trope IR node |
|---|---|
|
|
|
|
The type change Echo → EchoR is exactly the type change Trope → FloatingQuality,
and the reason echo_input is illegal on a residue (Echo-Decomposition.adoc
Plane 3) is, in IR terms, that a FloatingQuality node has no bearer field to
project. The same fact, two vocabularies.
| Echo op | Effect | Grade (per calculus.adoc §5) |
|---|---|---|
|
|
|
|
|
drop |
|
|
legal only while |
|
|
|
The [Stab-Erase] rule (spec/type-system.md §7) debits stability exactly once,
on echo_to_residue, and never on projection. That is precisely the calculus’s
accounting: detach carries the Severed (irrecoverable) loss; project carries
only a recoverable Withheld. The educational invariant "`echo_to_residue` must
not become a silent cast" is the calculus’s refusal of untagged/deceptive
collapse.
echo_to_residue as a detach (illustrative, schema-shaped){
"version": "0.1", "profile": "prevent",
"nodes": [
{ "id": "e", "type": "Trope", "present": ["quality","bearer","context","record"] },
{ "id": "res", "type": "FloatingQuality", "present": ["quality"] }
],
"edges": [
{ "id": "erase", "effect": "detach", "inputs": ["e"], "output": "res",
"grade": {
"fate": { "quality": {"k":"Present"}, "bearer": {"k":"Dropped"},
"context": {"k":"Dropped"}, "record": {"k":"Dropped"} },
"bond": { "k": "Severed" }, "merge": { "k": "Single" } },
"note": "echo_to_residue: witness erased, output reachable" }
],
"use_model": { "output": "res", "floor": { "bond": { "k": "Withheld" } } }
}Here the floor demands bond ⊒ Withheld (the use needs a recoverable bearer);
since detach delivered Severed, the verdict is p-insufficient, witness =
erase. A use that only reads echo_output would declare a quality-only floor and
pass. The score becomes a reason.
Each stabilityFactor becomes a grade, with its stabilityImpact magnitude
feeding the fidelity element δ. Crucially, the two silent instabilities land
on the deceptive Conflated bottom — an untagged merge of particulars — which,
under the prevent profile, is a lowering fault the validator rejects by name.
Error-Lang’s worst bugs are the calculus’s moral-core violation.
| Factor | Grade (faithful lowering) | Honesty |
|---|---|---|
|
|
faithful |
|
|
faithful |
|
|
faithful (visible gap) |
|
|
faithful |
|
|
faithful if tracked |
|
|
faithful |
|
|
deceptive when silent |
|
|
deceptive when silent |
| Error-Lang today | Trope-checker |
|---|---|
|
|
(no locus) |
|
|
per-coordinate retention at each node |
|
human advice attached to the witnessed edge (now principled, not heuristic) |
|
grade soundness ( |
The witness is, by the calculus’s own statement (§6.2), "the trope-particularity
analogue of the invariant-path argmin" — the same argmin shape Stability.idr
already reasons about. The verdict thus subsumes the current score: the score is
recoverable as a projection, but the verdict additionally names the edge to repair.
| Concern | Decision |
|---|---|
Trust boundary |
Pin |
Dependency |
Depend on the |
New backend |
Add a |
Precedent |
The same trust-tagged "fold external prover output back into our report" pattern the panic-attack repo uses in its |
Multi-producer |
Sanctioned by |
The trope-checker proves the composition of grades is sound. It explicitly does
not prove that an Error-Lang construct lowered to effect X is an X
(calculus.adoc §8, firewall 2; §10-O2). Those are our proof obligations:
| ID | Obligation |
|---|---|
L-Echo |
|
L-Grade |
Each |
L-Silent |
The |
L-Floor |
The |
These mirror, in Error-Lang’s setting, the open obligations the calculus states for
itself (O1–O4) — and they are checkable with the same Idris2 discipline already
used in src/abi/.
| Phase | Work |
|---|---|
0 (now) |
Shape the AffineScript Echo types (during the ReScript→AffineScript port) so |
1 |
Implement the |
2 |
Lower |
3 |
Discharge L-Echo / L-Grade / L-Silent / L-Floor as Idris2/Agda proofs; CI-gate the lowering. |
-
Profile. Adopt
prevent(silent merges rejected at validation — strongest, and on-message for "decomposition must be visible") ordetect(representable, caught at the verdict)? This design assumesprevent. -
Residue fidelity (L-Echo):
PresentvsAttenuated(δ)forecho_to_residue. -
Floor authorship. Where do use-models come from — a whole-program default, or per-function loss-signature annotations the learner writes?
-
Coverage (calculus O1): are all eight `stabilityFactor`s expressible with the six writable effects? The table above is a well-chosen mapping, not yet a theorem.
-
docs/Echo-Decomposition.adoc— the three decomposition planes this builds on. -
docs/Design-Philosophy.adoc— consequence amplification and the stability score. -
spec/type-system.md§7 — typing rules and the[Stab-Erase]stability debit. -
src/abi/Stability.idr— the existing Idris2 bound proof (verdict-soundness anchor). -
External (referenced, not vendored): trope-checker (
spec/calculus.adoc,spec/trope-ir.adoc,schemas/trope-ir.schema.json), trope-particularity-workbench (the nine effects), echo-types (shared substrate).