Skip to main content

zelkova_compiler/typer/
mod.rs

1//! This module contains the type checker pass of the language
2//!
3//! It works with the source AST and will perform two jobs:
4//! - type checks the different declarations and expression
5//! - infer the types when not declared in the source
6//!
7//! I have no idea how that works; so bear with me while I explore
8//! the space, make mistake and (hopefully) learn something :)
9//!
10//! Some papers on type inference:
11//! - <http://steshaw.org/hm/hindley-milner.pdf>
12//! - <https://pdfs.semanticscholar.org/8983/233b3dff2c5b94efb31235f62bddc22dc899.pdf>
13//! - <http://gallium.inria.fr/~fpottier/publis/fpottier-elaboration.pdf>
14//! - <http://gallium.inria.fr/~fpottier/publis/emlti-final.pdf>
15//!
16//! A type inference problem consists of a type environment Γ , an expression t, and a type T of kind ?
17//!
18//! Constraint generation rules:
19//!
20//! - Equation 1: ⟦x : T⟧ = x ≼ T
21//!   "x has type T if and only if T is an instance of the type scheme associated with x"
22//!   Important part: There is no relation to the typing environment Γ, instead x appears free (and will be bound to Γ later)
23//!
24//! - Equation 2: ⟦λz.t : T⟧ = ∃X1X2.(let z : X1 in ⟦t : X2⟧ ∧ X1 → X2 ≤ T)
25//!   "λz.t has type T if and only if, for some X1 and X2,
26//!   (i) under the assumption that z has type X1, t has type X2, and
27//!   (ii) T is a supertype of X1 → X2."
28//!   z and t types must be fresh (can't generally guess them). They are _existentially_ bound because we are going to
29//!   solve their values. Note that z is _not_ fresh in the condition (i).
30//!
31//! - Equation 3: ⟦t1 t2 : T⟧ = ∃X2.(⟦t1 : X2 → T⟧ ∧ ⟦t2 : X2⟧)
32//!   "t1 t2 has type T if and only if, for some X2, t1 has type X2 → T and t2 has type X2"
33//!
34//! - Equation 4: ⟦let z = t1 in t2 : T⟧ = let z : ∀X[⟦t1 : X⟧].X in ⟦t2 : T⟧
35//!   "let z = t1 in t2 has type T if and only if, under the assumption that z has every type X such that ⟦t1 : X⟧ holds, t2 has type T"
36//!
37//!
38use super::canonical;
39use super::canonical::Module;
40use super::scalars;
41use crate::ir::{
42    pattern_parameter, CaseForm, Constructor, Field, LiteralValue, Predicate, Reference,
43    ReferenceKind, Saturation, Solved, SolvedInstance, SubPattern, Term, TermKind, TermPattern,
44    TermPatternKind, TypeBinder, TypedTerm, TypedTermKind,
45};
46use crate::name::{Name, QualName};
47use crate::{Interface, ModuleName, PhaseError, SpanLabel};
48use log::debug;
49use std::collections::{BTreeMap, HashMap, HashSet};
50use zelkova_syntax::position::NodeSpan;
51use zelkova_syntax::tuple::Tuple;
52
53// ── Provenance ────────────────────────────────────────────────────────────────
54
55/// Why two types were required to match.
56///
57/// A constraint on its own is a pair of types, which is everything inference needs
58/// and nothing a reader can act on. The reason is what turns "cannot match `Bool`
59/// with `Int`" into something located: *this branch* has type `Bool`, and `Int` is
60/// what was expected *because of this annotation*. Elm calls this a `Reason`, rustc
61/// an `ObligationCause`.
62#[derive(Debug, Clone, Copy, PartialEq, Eq)]
63pub enum Reason {
64    /// A declaration's type annotation, which its body has to satisfy.
65    Annotation,
66    /// A literal's own type: `'a'` is a `Char`.
67    Literal,
68    /// A function's type is its parameter's type arrow its body's type.
69    FunctionShape,
70    /// What is applied has to be a function from the argument's type.
71    Application,
72    /// The condition of an `if` has to be a `Bool`.
73    IfCondition,
74    /// Every branch of an `if` has the type of the whole `if`.
75    IfBranch,
76    /// Every branch of a `case` has the type of the whole `case`.
77    CaseBranch,
78    /// A pattern has to match the type of the expression being matched on.
79    CasePattern,
80    /// A parameter written as a pattern has to match the type of the argument it takes.
81    ParameterPattern,
82    /// The body of a declaration that wrote a parameter as a pattern has the type the
83    /// declaration returns. It is the one branch of the match that parameter became,
84    /// and is reported as what the source wrote: a body, not a `case` branch.
85    DeclarationBody,
86    /// A `let` binding has the type of the value bound to it.
87    LetBinding,
88    /// A `let` has the type of its body.
89    LetBody,
90    /// A tuple's type is the tuple of its elements' types.
91    TupleElements,
92    /// `()` is the unit type's one value.
93    Unit,
94    /// A record's type is the record type of its fields' types.
95    RecordFields,
96    /// An update has the type of the record it updates.
97    Update,
98    /// A field's new value in an update has the type the field already has. Carried by
99    /// the equation a `FieldConstraint` of an update becomes once its record type is
100    /// known, at the value's span.
101    UpdateField,
102    /// A field access has the type of the field it reads. Carried by the equation a
103    /// `FieldConstraint` of an access becomes, at the access's span.
104    Access,
105    /// An accessor's result has the type of the field it reads. Carried by the equation
106    /// a `FieldConstraint` of an accessor becomes, at the accessor's span.
107    Accessor,
108    /// A record pattern's entry matches a value of the type its field has. Carried by the
109    /// equation a `FieldConstraint` of a record pattern becomes, at the span of the
110    /// entry's own pattern — `Celsius` in `{ taken = Celsius }` — when that pattern binds
111    /// no name, so that nothing but the pattern decides the entry's type and a mismatch
112    /// is the pattern's.
113    RecordPatternEntry,
114    /// [`RecordPatternEntry`](Self::RecordPatternEntry) for an entry whose pattern is a
115    /// name, the binding in `{ taken }` or `{ taken = t }`. That name's type is constrained
116    /// by nothing but the body's uses of it, so when the equation fails the pattern is
117    /// not what disagrees with the field: a use is, and the note says so. The caret is
118    /// still under the binding ([`ERR-20`](../../docs/tickets/err-20.md)).
119    RecordPatternBinding,
120    /// [`RecordPatternEntry`](Self::RecordPatternEntry) for an entry whose pattern is
121    /// neither a name nor binding-free, `Box x` in `{ taken = Box x }`: either the pattern
122    /// or a use of a name it binds can be what disagrees with the field, and nothing here
123    /// tells which, so the note names both.
124    RecordPatternEntryWithBindings,
125    /// A use of a name whose type has a context. The context's constraints are
126    /// instantiated at the types the use gave its variables, and each requires an
127    /// instance of its class at that type. Carried by an `Obligation` and never by an
128    /// equation, at the span of the use.
129    InstanceRequired,
130    /// An instance a use requires has a context of its own, and each of its constraints
131    /// requires an instance in turn, at the type the instance was used at. Carried by an
132    /// `Obligation` at the span of the use that started the chain.
133    InstanceContext,
134    /// A class with a superclass requires an instance of the superclass at every type it
135    /// has an instance for. Carried by an `Obligation` at the span of the instance
136    /// declaration.
137    SuperclassInstance,
138    /// A binding of an instance has the type its class gave the member, at the type the
139    /// instance is for. It is the reason of the equation the member's signature stands in
140    /// for, at the span of the instance's head line, where an annotation would be.
141    InstanceMember,
142    /// A binding of a derivation has the type the chapter gives it over the member's
143    /// answer type. It is the reason of the equation that type stands in for, at the span
144    /// of `derived member`, where an annotation would be.
145    DerivationBinding,
146}
147
148impl Reason {
149    /// What goes under the caret when the constraint carrying this reason is the one
150    /// that failed: what the underlined text *is*, in the vocabulary of the source.
151    ///
152    /// It names no type, and that is not terseness. By the time a constraint fails,
153    /// `unify` has substituted solutions into both of its sides and may have
154    /// decomposed it into a component of the types the source actually mentions — so
155    /// neither side is reliably "the type of the text under this caret" any more.
156    /// The headline already prints both types; a label that named the wrong one
157    /// would be worse than a label that names none. The example that forced this:
158    /// `answer : Int` with body `'a'` fails on the literal's own constraint *after*
159    /// `Int` was substituted into it, and reading the type off that side produced
160    /// "this literal has type `Int`".
161    fn describes(&self) -> &'static str {
162        match self {
163            Reason::Annotation => "this type annotation",
164            Reason::Literal => "this literal",
165            Reason::FunctionShape => "this function",
166            Reason::Application => "the expression being applied",
167            Reason::IfCondition => "this condition",
168            Reason::IfBranch => "this branch of the `if`",
169            Reason::CaseBranch => "this branch of the `case`",
170            Reason::CasePattern => "this pattern",
171            Reason::ParameterPattern => "this pattern",
172            Reason::DeclarationBody => "the body of this declaration",
173            Reason::LetBinding => "the value bound here",
174            Reason::LetBody => "the body of this `let`",
175            Reason::TupleElements => "this tuple",
176            Reason::Unit => "this unit value",
177            Reason::RecordFields => "this record",
178            Reason::Update => "this update",
179            Reason::UpdateField => "this field's new value",
180            Reason::Access => "this field access",
181            Reason::Accessor => "this accessor",
182            Reason::RecordPatternEntry
183            | Reason::RecordPatternBinding
184            | Reason::RecordPatternEntryWithBindings => "this field's pattern",
185            Reason::InstanceRequired => "this use requires an instance",
186            Reason::InstanceContext => "this use requires an instance, through another's context",
187            Reason::SuperclassInstance => "this instance requires an instance of its superclass",
188            Reason::InstanceMember => "this instance",
189            Reason::DerivationBinding => "this derivation",
190        }
191    }
192
193    /// What goes under the caret when this reason is not the failure itself but the
194    /// explanation for one side of it — see [`Origin::explanation`].
195    ///
196    /// No type is interpolated here, deliberately. Provenance records which
197    /// constraint brought a type into another one; it does not prove that the type
198    /// printed in the failing constraint is still literally the one this constraint
199    /// carried, and a label is not the place to guess.
200    fn explains(&self) -> &'static str {
201        match self {
202            Reason::Annotation => "expected because of this type annotation",
203            Reason::Literal => "expected because of this literal",
204            Reason::FunctionShape => "expected because of this function",
205            Reason::Application => "expected because of this application",
206            Reason::IfCondition => "expected because this is an `if` condition",
207            Reason::IfBranch => "expected because of this branch",
208            Reason::CaseBranch => "expected because of this branch",
209            Reason::CasePattern => "expected because of this pattern",
210            Reason::ParameterPattern => "expected because of this pattern",
211            Reason::DeclarationBody => "expected because of this declaration's body",
212            Reason::LetBinding => "expected because of this value",
213            Reason::LetBody => "expected because of this `let` body",
214            Reason::TupleElements => "expected because of this tuple",
215            Reason::Unit => "expected because of this unit value",
216            Reason::RecordFields => "expected because of this record",
217            Reason::Update => "expected because of this update",
218            Reason::UpdateField => "expected because of this field's new value",
219            Reason::Access => "expected because of this field access",
220            Reason::Accessor => "expected because of this accessor",
221            Reason::RecordPatternEntry
222            | Reason::RecordPatternBinding
223            | Reason::RecordPatternEntryWithBindings => "expected because of this field's pattern",
224            Reason::InstanceRequired => "an instance is required because of this use",
225            Reason::InstanceContext => "an instance is required through another's context here",
226            Reason::SuperclassInstance => "an instance is required because of this superclass",
227            Reason::InstanceMember => "expected because this instance gives the member this type",
228            Reason::DerivationBinding => {
229                "expected because this derivation gives the binding this type"
230            }
231        }
232    }
233
234    /// The rule that was broken, when naming it says something the labels do not.
235    fn note(&self) -> Option<&'static str> {
236        match self {
237            Reason::Annotation => {
238                Some("a declaration's body must have the type its annotation declares")
239            }
240            Reason::IfCondition => Some("the condition of an `if` must be a `Bool`"),
241            Reason::IfBranch => Some("every branch of an `if` must have the same type"),
242            Reason::CaseBranch => Some("every branch of a `case` must have the same type"),
243            Reason::CasePattern => Some(
244                "every pattern of a `case` must match the type of the expression it matches on",
245            ),
246            Reason::ParameterPattern => {
247                Some("a parameter's pattern must match the type of the argument it takes")
248            }
249            Reason::Update => Some("an update has the type of the record it updates"),
250            Reason::UpdateField => {
251                Some("an update cannot change a field's type: each new value must have the type its field already has")
252            }
253            Reason::Access => Some("a field access has the type of the field it reads"),
254            Reason::Accessor => Some("an accessor returns the type of the field it reads"),
255            Reason::RecordPatternEntry => {
256                Some("each entry of a record pattern must match the type of the field it names")
257            }
258            Reason::RecordPatternBinding => Some(
259                "a name a record pattern binds has the type of the field it names, and the body uses this one at another type",
260            ),
261            Reason::RecordPatternEntryWithBindings => Some(
262                "either this entry does not match the type of the field it names, or the body uses a name it binds at another type than that field gives the name",
263            ),
264            Reason::InstanceMember => Some(
265                "an instance's binding must have the type its class gives the member, at the type the instance is for",
266            ),
267            Reason::DerivationBinding => Some(
268                "a derivation's binding has the type its role gives it over the type the member answers with",
269            ),
270            // The error that carries one of these says what is required and why, so a rule
271            // note beside it would say it twice.
272            Reason::InstanceRequired | Reason::InstanceContext | Reason::SuperclassInstance => {
273                None
274            }
275            _ => None,
276        }
277    }
278}
279
280/// One piece of source text, and why it required a type: the answer to "where did
281/// this type come from".
282///
283/// Deliberately flat — no chain. A cause names the constraint that *introduced* a
284/// type, never one that relayed it, and that is arranged when the cause is built
285/// rather than by walking a chain afterwards. See `Origin::cause_of`.
286// No `Eq`: `NodeSpan`'s `PartialEq` is deliberately blind (see its documentation), so
287// equality here is a claim about the reason and not about the position.
288#[derive(Debug, Clone, Copy, PartialEq)]
289pub struct Cause {
290    /// Why that constraint required the two types to match.
291    pub reason: Reason,
292    /// The source text it is about.
293    pub span: NodeSpan,
294}
295
296/// Which side of a constraint a type sits on.
297///
298/// Unification is symmetric and does not care; provenance does. Whether a solved
299/// type was read off the left or the right of the constraint that solved it is what
300/// decides whether that constraint is where the type came from, or merely where a
301/// substitution put it — see [`Origin::cause_of`].
302#[derive(Debug, Clone, Copy, PartialEq, Eq)]
303enum Side {
304    Left,
305    Right,
306}
307
308/// Where a constraint came from, and — once inference has moved types around — where
309/// each of its two types came from.
310#[derive(Debug, Clone, PartialEq)]
311pub struct Origin {
312    /// Why the two types were required to match.
313    pub reason: Reason,
314    /// The source text this constraint is about. A failure here draws its caret at
315    /// this span.
316    pub span: NodeSpan,
317    /// The constraint whose solution first rewrote the left type, if any.
318    ///
319    /// `unify` solves a constraint by substituting a type for a variable and then
320    /// applying that substitution to every constraint left. Once that has happened,
321    /// this side holds a type this constraint never mentioned: it came from wherever
322    /// the substitution did. That is the fact a reader needs — "`Int`, because of the
323    /// annotation two lines up" — and it is what the secondary label of a type error
324    /// renders.
325    ///
326    /// The *first* rewrite is kept and later ones are dropped: the first substitution
327    /// to reach a side is the one that brought a foreign type into it, and later ones
328    /// only rewrite what is already there.
329    left_from: Option<Cause>,
330    /// The same, for the right type.
331    right_from: Option<Cause>,
332}
333
334impl Origin {
335    fn new(reason: Reason, span: NodeSpan) -> Origin {
336        Origin {
337            reason,
338            span,
339            left_from: None,
340            right_from: None,
341        }
342    }
343
344    /// This constraint, as the explanation for a type it introduced itself.
345    fn own_cause(&self) -> Cause {
346        Cause {
347            reason: self.reason,
348            span: self.span,
349        }
350    }
351
352    /// Where the type on `side` came from: whatever rewrote that side, or — when
353    /// nothing did — this constraint itself.
354    ///
355    /// This is the whole of the provenance rule, and it is a rule about *sides*.
356    /// When `unify` solves `t := T` from a constraint, `T` was read off one side of
357    /// it. If that side is a type the constraint was written with, the constraint is
358    /// the answer. If a previous solution had rewritten that side, the constraint is
359    /// only relaying a type, and the answer is whatever rewrote it — which is already
360    /// flat, so the credit passes straight through and no chain is ever built.
361    ///
362    /// Crediting a constraint that merely relayed a type is how `result : Bool` /
363    /// `result = not 42` came to blame the annotation: the `Bool` that `42` fails
364    /// against is `not`'s parameter type, which the application constraint carries on
365    /// its *left*, while the annotation had only rewritten its right.
366    fn cause_of(&self, side: Side) -> Cause {
367        let rewritten = match side {
368            Side::Left => self.left_from,
369            Side::Right => self.right_from,
370        };
371
372        rewritten.unwrap_or_else(|| self.own_cause())
373    }
374
375    /// Record that a solution rewrote one side of this constraint, keeping whatever
376    /// was already recorded for that side. See [`Origin::left_from`].
377    fn rewritten(&mut self, side: Side, cause: Cause) {
378        let slot = match side {
379            Side::Left => &mut self.left_from,
380            Side::Right => &mut self.right_from,
381        };
382
383        if slot.is_none() {
384            *slot = Some(cause);
385        }
386    }
387
388    /// Where the type this constraint clashed on came from, when the constraint is
389    /// not itself where it came from.
390    ///
391    /// This is what a diagnostic's secondary label and its rule note are both read
392    /// off. The left side is preferred because that is the declared or expected side
393    /// by convention (see `Constraint`), so "expected because of …" reads about the
394    /// right one; the right side answers when only it was rewritten.
395    pub fn explanation(&self) -> Option<Cause> {
396        self.left_from.or(self.right_from)
397    }
398}
399
400/// What went wrong, and — for everything unification can raise — where.
401///
402/// Each variant carries the [`Origin`] of the constraint that failed, so a type
403/// error can put its caret under the sub-expression that disagrees instead of across
404/// the declaration containing it. The declaration is still named by [`Error`], one
405/// level up, which is the frame that knows it.
406#[derive(Debug)]
407pub enum ErrorKind {
408    /// Two types were required to match and do not.
409    ///
410    /// The two are written in the order the message reads them out — declared side
411    /// first where the source had one. Neither is reliably "the type of the text the
412    /// origin points at": by the time a constraint fails, unification has substituted
413    /// into both sides and may have decomposed the pair the source actually wrote.
414    // The origins and the types are boxed because an `ErrorKind` is the `Err` half of
415    // a `Result` threaded through the whole of `unify`, and every *successful* return
416    // pays for the size of the largest variant. `Origin` carries a `Cause` per side,
417    // and a `Type` carries a whole `QualName` for every union it names.
418    UnificationFailed {
419        left: Box<Type>,
420        right: Box<Type>,
421        origin: Box<Origin>,
422    },
423    /// A type variable the declaration is universally quantified over — one its annotation
424    /// wrote, or one of an instance's head or of the member signature an instance's
425    /// binding is held to — would have to be a type of its own, which a declaration cannot
426    /// ask of a variable that stands for every type a caller may choose
427    /// ([*An annotation is a promise*](../../docs/spec/types.md#an-annotation-is-a-promise)).
428    ///
429    /// Raised where `unify` meets a rigid variable and anything but that variable: a
430    /// concrete type, or another rigid variable of the same declaration.
431    RigidVariable {
432        /// The variable as the source wrote it, `a`.
433        variable: String,
434        /// What the variable was written in.
435        binder: Binder,
436        /// What the body would need it to be, written with the source's names for the
437        /// other rigid variables it holds. Boxed for the reason `UnificationFailed`'s
438        /// types are.
439        tpe: Box<Type>,
440        origin: Box<Origin>,
441    },
442    /// A type variable would have to occur inside its own solution.
443    CircularType {
444        /// The type the variable would have had to contain itself in. Boxed for the
445        /// reason above.
446        tpe: Box<Type>,
447        origin: Box<Origin>,
448    },
449    /// A name the typer's environment does not know. `type_check` turns this into a
450    /// [`Solved::UnboundName`] rather than an [`Error`]; that variant says why.
451    ///
452    /// `name` is `environment_key`'s `package:Module.name` lookup key, copied
453    /// verbatim from [`Reference::name`] — not a spelling. `message()`'s arm for this
454    /// variant renders it as-is, which would print the package if this variant were
455    /// ever surfaced as a rendered [`Error`]; today `type_check` never does that (see
456    /// above), so the leak has no path to a user yet. Whoever gives this variant a
457    /// live path — `ERR-8`'s planned warning is the likely first one — has to carry a
458    /// displayable name (the bare local name, or a `QualName` rendered the way
459    /// `Spellings` would) alongside this key rather than rendering it directly.
460    UnboundVariable {
461        name: String,
462        /// Where the name was written.
463        span: NodeSpan,
464    },
465    /// A field access, an update, an accessor or a record pattern whose record type
466    /// nothing else in the declaration supplied: once unification had run over the whole
467    /// declaration, the type it reads a field of was still a variable
468    /// ([A use does not decide a record's type](../../docs/spec/records.md#a-use-does-not-decide-a-records-type)).
469    ///
470    /// `span` is the whole form — `person.name`, `{ r | x = 1 }`, `.name`, `{ name }` —
471    /// since what is missing is a type for it, not a label in one.
472    RecordTypeUnknown {
473        label: Name,
474        form: RecordUse,
475        span: NodeSpan,
476        /// What could supply the record type, which is what the note says.
477        supplier: Supplier,
478    },
479    /// A field access, an update, an accessor or a record pattern naming a label the
480    /// record type it is read against does not have. An update naming one is the update
481    /// that would add a field ([Updating a record](../../docs/spec/records.md#updating-a-record)).
482    ///
483    /// `span` is the label for an access, an update's field and a record pattern's entry,
484    /// and the whole accessor for an accessor, whose label is all of it but the `.`.
485    MissingField {
486        /// The record type, as solved. Boxed for the reason `UnificationFailed`'s
487        /// types are.
488        record: Box<Type>,
489        label: Name,
490        form: RecordUse,
491        span: NodeSpan,
492        /// Where the record type came from — the annotation, typically — when something
493        /// brought it in; the secondary label goes under it.
494        because: Option<Cause>,
495    },
496    /// A field access, an update, an accessor or a record pattern whose record is not a
497    /// record at all: the type it reads a field of was solved to a type of another form.
498    ///
499    /// `span` is where [`MissingField`](Self::MissingField)'s would be, and `because` is
500    /// as there.
501    NotARecord {
502        tpe: Box<Type>,
503        label: Name,
504        form: RecordUse,
505        span: NodeSpan,
506        because: Option<Cause>,
507    },
508    /// A class is required of a type, and the type has no instance of it: a declared type,
509    /// a tuple or `()` that no instance in reach is declared for, or a function type,
510    /// which no instance can be.
511    ///
512    /// The type is the one the obligation had once unification was done, so it can be
513    /// the argument of an instance's context rather than the type the use was at:
514    /// [`needed_by`](Self::NoInstance::needed_by) is then the obligation the use raised,
515    /// which asked for this one through an instance of its own.
516    NoInstance {
517        class: QualName,
518        /// Boxed for the reason `UnificationFailed`'s types are.
519        tpe: Box<Type>,
520        needed_by: Option<Box<Predicate>>,
521        origin: Box<Origin>,
522    },
523    /// A class is required of a type variable the declaration's type holds, and the
524    /// constraints its annotation (or an instance's context) wrote do not provide it: the
525    /// constraint to add is the fix. The exception is a variable an instance binding's
526    /// member signature binds, which no context of the instance can constrain:
527    /// [`Written::MemberSignature`] says so.
528    MissingConstraint {
529        class: QualName,
530        /// The variable as the source wrote it, `a`.
531        variable: String,
532        /// What is missing the constraint.
533        written: Written,
534        origin: Box<Origin>,
535    },
536    /// A class is required of a type variable the type of a declaration with no
537    /// annotation holds. A constraint is never inferred
538    /// ([`DEC-24` decision 5](../../docs/decisions/dec-24.md#5--a-constraint-is-never-inferred)),
539    /// so the declaration has to state it.
540    ConstraintNeedsAnnotation {
541        class: QualName,
542        /// What the declaration has to state, constraints and type: `Eq a => a -> a ->
543        /// Bool`.
544        stated: String,
545        origin: Box<Origin>,
546    },
547    /// A class is required of a type variable that is not part of the declaration's type.
548    /// Nothing determines the type the class is needed at, and no annotation on this
549    /// declaration can.
550    UndeterminedConstraint {
551        class: QualName,
552        origin: Box<Origin>,
553    },
554}
555
556/// What a constraint would have to be written in, for [`ErrorKind::MissingConstraint`].
557#[derive(Debug, Clone, Copy, PartialEq, Eq)]
558pub enum Written {
559    /// A declaration's annotation.
560    Annotation,
561    /// An instance's context.
562    InstanceContext,
563    /// The signature of the class member an instance's binding defines: the variable is
564    /// one the member's signature binds and the instance's head does not, so no context
565    /// of the instance can constrain it.
566    MemberSignature,
567    /// A derivation's binding, which is given no context: none of its bindings mentions
568    /// the class variable, so they stand for every type that derives the class.
569    Derivation,
570}
571
572impl ErrorKind {
573    /// The provenance of the constraint that failed, when the failure came from
574    /// unification at all.
575    fn origin(&self) -> Option<&Origin> {
576        match self {
577            ErrorKind::UnificationFailed { origin, .. }
578            | ErrorKind::RigidVariable { origin, .. }
579            | ErrorKind::CircularType { origin, .. }
580            | ErrorKind::NoInstance { origin, .. }
581            | ErrorKind::MissingConstraint { origin, .. }
582            | ErrorKind::ConstraintNeedsAnnotation { origin, .. }
583            | ErrorKind::UndeterminedConstraint { origin, .. } => Some(origin.as_ref()),
584            ErrorKind::UnboundVariable { .. }
585            | ErrorKind::RecordTypeUnknown { .. }
586            | ErrorKind::MissingField { .. }
587            | ErrorKind::NotARecord { .. } => None,
588        }
589    }
590
591    /// The headline, naming each union the way `spellings` says the checked package
592    /// reaches it when the message has to qualify one at all — see [`AdtNames`].
593    fn message(&self, spellings: &Spellings) -> String {
594        match self {
595            ErrorKind::UnificationFailed { left, right, .. } => {
596                // Two modules may each declare a union of the same name, and the
597                // source spells both of them bare. Written that way the sentence
598                // uses one word for two declarations and says nothing; the module
599                // that declared each is what tells them apart, so both sides take
600                // it — both, because a sentence that qualifies one side and not the
601                // other reads as if only one of them had a module.
602                if AdtNames::collide([left.as_ref(), right.as_ref()]) {
603                    format!(
604                        "cannot match `{}` with `{}`",
605                        Qualified(left, spellings),
606                        Qualified(right, spellings)
607                    )
608                } else {
609                    format!("cannot match `{}` with `{}`", left, right)
610                }
611            }
612            ErrorKind::RigidVariable {
613                variable,
614                binder,
615                tpe,
616                ..
617            } => {
618                // An instance's head and the member signature its binding is held to each
619                // write their own variables, and may write one alike: then the message says
620                // whose each is, or `b` would have to be `b`.
621                let other = free_variables_in_order(tpe).into_iter().find_map(|found| {
622                    let found_binder = found.binder()?;
623                    (found.spelling() == *variable && found_binder != *binder)
624                        .then_some(found_binder)
625                });
626
627                match other {
628                    Some(other) => format!(
629                        "`{}` of {} stands for any type, but here it would have to be `{}`, where `{}` is {}",
630                        variable,
631                        binder.of_phrase(),
632                        Spelled(tpe, spellings),
633                        variable,
634                        other.possessive()
635                    ),
636                    None => format!(
637                        "`{}` stands for any type, but here it would have to be `{}`",
638                        variable,
639                        Spelled(tpe, spellings)
640                    ),
641                }
642            }
643            // One type, but it can hold the collision on its own: the variable's
644            // solution is built out of whatever it was unified against, which may
645            // be two same-named unions from two modules.
646            ErrorKind::CircularType { tpe, .. } => {
647                let qualified = Qualified(tpe, spellings);
648                let tpe: &dyn std::fmt::Display = if AdtNames::collide([tpe.as_ref()]) {
649                    &qualified
650                } else {
651                    &**tpe
652                };
653
654                format!(
655                    "circular type: a type variable would have to contain itself in `{}`",
656                    tpe
657                )
658            }
659            // `name` is the internal environment key, not a spelling — see the
660            // doc comment on `UnboundVariable` above. Unreachable today only because
661            // nothing renders this variant as an `Error`.
662            ErrorKind::UnboundVariable { name, .. } => {
663                format!("cannot find a value named `{}`", name)
664            }
665            ErrorKind::RecordTypeUnknown { label, form, .. } => match form {
666                RecordUse::Access => format!(
667                    "cannot read the field `{}`: nothing in this declaration says which record type it is read from",
668                    label.as_str()
669                ),
670                RecordUse::Accessor => format!(
671                    "cannot type the accessor `.{}`: nothing in this declaration says which record type it reads",
672                    label.as_str()
673                ),
674                RecordUse::Update => {
675                    "cannot type this update: nothing in this declaration says which record type it updates"
676                        .to_string()
677                }
678                RecordUse::Pattern => {
679                    "cannot type this record pattern: nothing in this declaration says which record type it matches"
680                        .to_string()
681                }
682            },
683            ErrorKind::MissingField { record, label, .. } => format!(
684                "the record type `{}` has no field `{}`",
685                Spelled(record, spellings),
686                label.as_str()
687            ),
688            ErrorKind::NotARecord { tpe, label, .. } => format!(
689                "`{}` is not a record type, so it has no field `{}`",
690                Spelled(tpe, spellings),
691                label.as_str()
692            ),
693            ErrorKind::NoInstance { class, tpe, .. } => format!(
694                "there is no instance of `{}` for `{}`",
695                class.unqualified_name(),
696                Spelled(tpe, spellings)
697            ),
698            ErrorKind::MissingConstraint {
699                class,
700                variable,
701                written,
702                ..
703            } => format!(
704                "`{} {}` is required here, and {} does not provide it",
705                class.unqualified_name(),
706                variable,
707                match written {
708                    Written::Annotation => "the annotation",
709                    Written::InstanceContext => "the instance's context",
710                    Written::MemberSignature => "the member's signature",
711                    Written::Derivation => "the derivation, which is given no context,",
712                }
713            ),
714            ErrorKind::ConstraintNeedsAnnotation { class, .. } => format!(
715                "a type annotation is needed: `{}` is required of a type this declaration leaves open",
716                class.unqualified_name()
717            ),
718            ErrorKind::UndeterminedConstraint { class, .. } => format!(
719                "`{}` is required of a type nothing in this declaration determines",
720                class.unqualified_name()
721            ),
722        }
723    }
724
725    /// Where the type `MissingField` and `NotARecord` read a field of came from, when
726    /// something brought it in: the secondary label of each, as a mismatch's is.
727    fn record_use_because(&self) -> Option<Cause> {
728        match self {
729            ErrorKind::MissingField { because, .. } | ErrorKind::NotARecord { because, .. } => {
730                *because
731            }
732            _ => None,
733        }
734    }
735
736    /// The caret of one of the three errors a `FieldConstraint` raises itself, which
737    /// carry a span and no [`Origin`]: each is about a form rather than about two types.
738    fn record_use_label(&self) -> Option<(NodeSpan, String)> {
739        match self {
740            ErrorKind::RecordTypeUnknown { span, .. } => {
741                Some((*span, "its record type is not known here".to_string()))
742            }
743            ErrorKind::MissingField { label, span, .. } => Some((
744                *span,
745                format!("the record has no field `{}`", label.as_str()),
746            )),
747            ErrorKind::NotARecord {
748                label,
749                form: RecordUse::Pattern,
750                span,
751                ..
752            } => Some((
753                *span,
754                format!(
755                    "`{}` is matched against a type that is not a record",
756                    label.as_str()
757                ),
758            )),
759            ErrorKind::NotARecord { label, span, .. } => Some((
760                *span,
761                format!(
762                    "`{}` is read from a type that is not a record",
763                    label.as_str()
764                ),
765            )),
766            _ => None,
767        }
768    }
769}
770
771/// A [`Type`] written the way a message about one type writes it: bare, unless two of
772/// the unions it names share a spelling, and then each by its module (see [`AdtNames`]).
773struct Spelled<'a>(&'a Type, &'a Spellings);
774
775impl std::fmt::Display for Spelled<'_> {
776    fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
777        if AdtNames::collide([self.0]) {
778            self.0.write(f, AdtNames::Qualified(self.1), None)
779        } else {
780            self.0.write(f, AdtNames::Unqualified, None)
781        }
782    }
783}
784
785/// A type error: what went wrong, where, and in which declaration.
786///
787/// # Where the positions come from
788///
789/// The typer does not check the canonical AST directly — it translates it into its
790/// own [`Term`] language — but that translation now carries the canonical node's
791/// [`NodeSpan`] along, and each constraint keeps the span of the term that produced
792/// it. So a unification failure knows the sub-expression it is about, and
793/// [`labels`](PhaseError::labels) draws the caret there.
794///
795/// The declaration's own span is still kept as `span`, for the one case that has no
796/// finer answer: an error whose origin came from a hand-built term, or from a
797/// canonical node the parser never spanned. Then the label degrades to the whole
798/// declaration rather than disappearing.
799#[derive(Debug)]
800pub struct Error {
801    pub kind: ErrorKind,
802    /// Where the declaration the error was found in was written. Used only as the
803    /// fallback described above.
804    pub span: NodeSpan,
805    /// That declaration's name, which is what the note names: in a module of a
806    /// hundred declarations, a caret is not much use without it when the diagnostic
807    /// is rendered without a file (see `compile_package`).
808    pub declaration: Name,
809    /// What `declaration` is: a value, a binding of an instance, or an instance.
810    within: Within,
811    /// How the checked package spells each module in reach, which is what a union is
812    /// written by in [`message`](PhaseError::message) when it has to be qualified.
813    spellings: Spellings,
814}
815
816/// What an [`Error`]'s `declaration` names, which is what its first note says.
817#[derive(Debug, Clone, PartialEq)]
818enum Within {
819    /// A value of the module: `declaration` is its name.
820    Value,
821    /// A binding of an instance: `declaration` is the member it defines, and this is the
822    /// instance, written as its head line is.
823    Binding(String),
824    /// An instance, checked as a whole: `declaration` is the instance, written as its head
825    /// line is.
826    Instance,
827    /// A binding of a derivation in a class: `declaration` is the binding, and this is
828    /// the member the derivation is for.
829    Derivation(String),
830}
831
832/// Type errors are about types, and [`Type`]'s `Display` writes them the way the
833/// source does — so the message can name both sides of a mismatch instead of
834/// dumping the typer's internal representation.
835impl PhaseError for Error {
836    fn message(&self) -> String {
837        self.kind.message(&self.spellings)
838    }
839
840    fn notes(&self) -> Vec<String> {
841        let mut notes = vec![match &self.within {
842            Within::Value => format!("in the declaration of `{}`", self.declaration),
843            Within::Binding(instance) => format!(
844                "in the binding of `{}` in the instance `{}`",
845                self.declaration, instance
846            ),
847            Within::Instance => format!("in the instance `{}`", self.declaration),
848            Within::Derivation(member) => format!(
849                "in the binding `{}` of the derivation of `{}`",
850                self.declaration, member
851            ),
852        }];
853
854        // The rule that was broken, taken from the failing constraint and, if that
855        // one has nothing to add, from what explains it. `if`'s "every branch must
856        // have the same type" is on the branch constraint; "a body must have the
857        // type its annotation declares" is on the annotation, which is normally the
858        // explanation rather than the failure.
859        if let Some(origin) = self.kind.origin() {
860            let rule = origin
861                .reason
862                .note()
863                .or_else(|| origin.explanation().and_then(|c| c.reason.note()));
864
865            if let Some(rule) = rule {
866                notes.push(rule.to_owned());
867            }
868        }
869
870        match &self.kind {
871            ErrorKind::UnificationFailed { left, right, .. } => {
872                if let Some(difference) = label_difference(left, right) {
873                    notes.push(difference);
874                }
875            }
876            ErrorKind::RigidVariable {
877                variable, binder, ..
878            } => notes.push(match binder {
879                Binder::InstanceHead => format!(
880                    "a type variable of an instance stands for every type the instance may be used at, so its bindings cannot rely on `{}` being one particular type",
881                    variable
882                ),
883                Binder::Annotation => format!(
884                    "a type variable in an annotation stands for every type a caller may choose, so the body cannot rely on `{}` being one particular type",
885                    variable
886                ),
887                Binder::MemberSignature => format!(
888                    "a type variable of a member's signature stands for every type a caller of the member may choose, so a binding cannot rely on `{}` being one particular type",
889                    variable
890                ),
891            }),
892            ErrorKind::RecordTypeUnknown { supplier, .. } => {
893                notes.push(
894                    "a record's type is never worked out from the fields a declaration uses"
895                        .to_string(),
896                );
897                notes.push(match supplier {
898                    Supplier::Annotation => format!(
899                        "a type annotation on `{}` would supply it",
900                        self.declaration
901                    ),
902                    Supplier::AnnotationVariable => format!(
903                        "the annotation on `{}` does not say which record type this is: it writes a type variable where the record type would be spelled out",
904                        self.declaration
905                    ),
906                    Supplier::Body => format!(
907                        "it is not part of `{}`'s type, so no annotation on `{}` could supply it",
908                        self.declaration, self.declaration
909                    ),
910                });
911            }
912            ErrorKind::MissingField {
913                form: RecordUse::Update,
914                ..
915            } => notes.push(
916                "an update cannot add a field: each label it names must already be a field of the record it updates"
917                    .to_string(),
918            ),
919            ErrorKind::MissingField {
920                form: RecordUse::Pattern,
921                ..
922            } => notes.push(
923                "a record pattern names some of the fields of the record it matches, and each label it names must be one of them"
924                    .to_string(),
925            ),
926            ErrorKind::NoInstance {
927                class,
928                tpe,
929                needed_by,
930                ..
931            } => {
932                let class = class.unqualified_name();
933
934                notes.push(match tpe.as_ref() {
935                    Type::Fun { .. } => {
936                        "a function type has no instances: no instance can be declared for one"
937                            .to_string()
938                    }
939                    _ => format!(
940                        "an instance of `{}` for this type is declared in the module that declares `{}` or in the module that declares the type, and none is in scope here",
941                        class, class
942                    ),
943                });
944
945                if let Some(required) = needed_by {
946                    notes.push(format!(
947                        "it is needed because `{}` is required here, and the instance of `{}` that answers that asks the same of this type",
948                        predicate_text(required, &self.spellings),
949                        required.class.unqualified_name()
950                    ));
951                }
952            }
953            ErrorKind::MissingConstraint {
954                class,
955                variable,
956                written,
957                ..
958            } => notes.push(match written {
959                Written::Annotation => format!(
960                    "add `{} {}` to the constraints of the annotation on `{}`",
961                    class.unqualified_name(),
962                    variable,
963                    self.declaration
964                ),
965                Written::InstanceContext => format!(
966                    "add `{} {}` to the context of the instance",
967                    class.unqualified_name(),
968                    variable
969                ),
970                Written::MemberSignature => format!(
971                    "`{}` is bound by the signature of the member and not by the head of the instance, so no context of the instance can constrain it: the binding has to hold for every `{}`, and cannot need `{} {}`; change the binding, or the member's signature",
972                    variable,
973                    variable,
974                    class.unqualified_name(),
975                    variable
976                ),
977                Written::Derivation => format!(
978                    "a derivation's bindings carry no context, so the binding has to hold for every `{}` and cannot need `{} {}`; change the binding, or the member's signature",
979                    variable,
980                    class.unqualified_name(),
981                    variable
982                ),
983            }),
984            ErrorKind::ConstraintNeedsAnnotation { stated, .. } => {
985                notes.push(
986                    "a constraint is never inferred: it is part of a type only where an annotation writes it"
987                        .to_string(),
988                );
989                notes.push(format!(
990                    "`{}` is what the declaration has to state: `{} : {}`",
991                    self.declaration, self.declaration, stated
992                ));
993            }
994            ErrorKind::UndeterminedConstraint { .. } => notes.push(format!(
995                "the type is not part of `{}`'s type, so no annotation on `{}` could say which it is",
996                self.declaration, self.declaration
997            )),
998            _ => (),
999        }
1000
1001        notes
1002    }
1003
1004    /// A caret under the text that disagrees, and — when inference can say where the
1005    /// type it disagrees with came from — a second, secondary one under that.
1006    ///
1007    /// Falls back to underlining the whole declaration when the failing constraint
1008    /// has no position, which is what a term built by hand, or one translated from a
1009    /// canonical node with no span, produces.
1010    fn labels(&self) -> Vec<SpanLabel> {
1011        let mut labels = Vec::new();
1012
1013        match &self.kind {
1014            ErrorKind::UnboundVariable { span, .. } => {
1015                if let Some(span) = span.span() {
1016                    labels.push(SpanLabel {
1017                        span,
1018                        message: "not found in this scope".to_owned(),
1019                        primary: true,
1020                        file: None,
1021                    });
1022                }
1023            }
1024            kind @ (ErrorKind::RecordTypeUnknown { .. }
1025            | ErrorKind::MissingField { .. }
1026            | ErrorKind::NotARecord { .. }) => {
1027                if let Some((span, message)) = kind.record_use_label() {
1028                    if let Some(span) = span.span() {
1029                        labels.push(SpanLabel {
1030                            span,
1031                            message,
1032                            primary: true,
1033                            file: None,
1034                        });
1035                    }
1036                }
1037
1038                // As a mismatch's below, and for the same two reasons drawn only beside
1039                // a primary label on other text.
1040                if let (Some(primary), Some(because)) = (labels.first(), kind.record_use_because())
1041                {
1042                    match because.span.span() {
1043                        Some(span) if span != primary.span => labels.push(SpanLabel {
1044                            span,
1045                            message: because.reason.explains().to_owned(),
1046                            primary: false,
1047                            file: None,
1048                        }),
1049                        _ => (),
1050                    }
1051                }
1052            }
1053            kind => {
1054                if let Some(origin) = kind.origin() {
1055                    if let Some(span) = origin.span.span() {
1056                        labels.push(SpanLabel {
1057                            span,
1058                            message: origin.reason.describes().to_owned(),
1059                            primary: true,
1060                            file: None,
1061                        });
1062                    }
1063
1064                    // Only worth drawing once the primary one exists: on its own it
1065                    // would be a caret under the annotation with nothing to contrast
1066                    // it against. And not worth drawing at all when it lands on the
1067                    // same text — a literal that is its own explanation renders as two
1068                    // carets under one word saying the same thing twice.
1069                    if let (Some(primary), Some(because)) = (labels.first(), origin.explanation()) {
1070                        match because.span.span() {
1071                            Some(span) if span != primary.span => labels.push(SpanLabel {
1072                                span,
1073                                message: because.reason.explains().to_owned(),
1074                                primary: false,
1075                                file: None,
1076                            }),
1077                            _ => (),
1078                        }
1079                    }
1080                }
1081            }
1082        }
1083
1084        if labels.is_empty() {
1085            if let Some(span) = self.span.span() {
1086                labels.push(SpanLabel {
1087                    span,
1088                    message: format!("in `{}`", self.declaration),
1089                    primary: true,
1090                    file: None,
1091                });
1092            }
1093        }
1094
1095        labels
1096    }
1097}
1098
1099/// The note for two record types that failed to unify because their label sets
1100/// differ, naming the labels each has that the other lacks; `None` for any other pair,
1101/// two record types of one label set included — they failed on a field's type, which
1102/// the headline names.
1103///
1104/// "First" and "second" are the headline's order, which is the constraint's.
1105fn label_difference(left: &Type, right: &Type) -> Option<String> {
1106    let (Type::Record(left), Type::Record(right)) = (left, right) else {
1107        return None;
1108    };
1109
1110    let only = |of: &BTreeMap<Name, Type>, other: &BTreeMap<Name, Type>| -> Vec<String> {
1111        of.keys()
1112            .filter(|label| !other.contains_key(*label))
1113            .map(|label| format!("`{}`", label.as_str()))
1114            .collect()
1115    };
1116    let only_left = only(left, right);
1117    let only_right = only(right, left);
1118
1119    let clause = |which: &str, labels: &[String], other: &str| {
1120        let fields = if labels.len() == 1 {
1121            "a field"
1122        } else {
1123            "fields"
1124        };
1125        format!(
1126            "the {} record type has {} {} that the {} does not",
1127            which,
1128            fields,
1129            labels.join(", "),
1130            other
1131        )
1132    };
1133
1134    match (only_left.is_empty(), only_right.is_empty()) {
1135        (true, true) => None,
1136        (false, true) => Some(clause("first", &only_left, "second")),
1137        (true, false) => Some(clause("second", &only_right, "first")),
1138        (false, false) => Some(format!(
1139            "{}, and the second has {} {} that the first does not",
1140            clause("first", &only_left, "second"),
1141            if only_right.len() == 1 {
1142                "a field"
1143            } else {
1144                "fields"
1145            },
1146            only_right.join(", ")
1147        )),
1148    }
1149}
1150
1151/// What [`type_check_recovering`] found in one module: an answer for every declaration,
1152/// and every error inference reported, side by side.
1153#[derive(Debug)]
1154pub struct TypeCheck {
1155    /// One [`Solved`] per declaration, keyed the way `module.values` is. A declaration
1156    /// inference reported an error for is here as [`Solved::Rejected`], and its error is
1157    /// in [`errors`](Self::errors).
1158    pub solved: HashMap<Name, Solved>,
1159    /// One entry per instance the module declares, in the order
1160    /// [`canonical::Module::instances`] holds them: what each is for and an answer for
1161    /// every binding of its body.
1162    pub instances: Vec<SolvedInstance>,
1163    /// The classes of this module with a derivation binding that was rejected, by name.
1164    /// The error is in [`errors`](Self::errors), at the class.
1165    pub rejected_derivations: Vec<Name>,
1166    /// Every error inference reported, one per rejected declaration, binding or instance.
1167    /// Empty means the module type checked.
1168    pub errors: Vec<Error>,
1169}
1170
1171/// [`type_check_recovering`], reduced to a module that either type checked or did not:
1172/// the solved map when no declaration failed, every error otherwise.
1173pub fn type_check(
1174    module: &Module,
1175    interfaces: &HashMap<Name, Interface>,
1176) -> Result<HashMap<Name, Solved>, Vec<Error>> {
1177    let TypeCheck { solved, errors, .. } = type_check_recovering(module, interfaces);
1178
1179    if errors.is_empty() {
1180        Ok(solved)
1181    } else {
1182        Err(errors)
1183    }
1184}
1185
1186/// Type check one canonical module and hand back what it solved, reporting every value
1187/// whose inference produced a reportable error rather than stopping at the first — the
1188/// shape `compile_package` is built to accumulate.
1189///
1190/// # What comes back
1191///
1192/// One [`Solved`] per declaration, keyed the way `module.values` is, whether or not
1193/// any declaration failed. A declaration the typer could not type is present and says
1194/// so; none is ever merely absent, because absent is indistinguishable from
1195/// checked-and-fine to whatever reads this next
1196/// ([`DEC-18` decision 1](../../docs/decisions/dec-18.md)). One that inference
1197/// reported an error for is [`Solved::Rejected`], with the error in
1198/// [`TypeCheck::errors`], so a module with a type error still has a typed term for
1199/// each of its other declarations
1200/// ([`DEC-23` decision 5](../../docs/decisions/dec-23.md)).
1201///
1202/// The term inside [`Solved::Typed`] is the one `annotate` built, with `unify`'s final
1203/// substitution applied to every node rather than to the declaration's own type alone.
1204/// That interior is the point — a backend needs the type of each sub-expression, not
1205/// just of the declaration containing it.
1206///
1207/// Every instance the module declares is answered for the same way, one
1208/// [`SolvedInstance`] each, with a [`Solved`] for each binding of its body: a binding is a
1209/// declaration whose annotation is the member's signature at the instance's type.
1210///
1211/// # Where an [`Error`] is built
1212///
1213/// Here, and only here: this is the last frame that holds the `canonical::Value`, so
1214/// it is the only one that knows the declaration's name and its span. What went
1215/// *wrong* and *where inside the declaration* comes up from inference on the
1216/// [`ErrorKind`]; see [`Error`].
1217///
1218/// # What a declaration is checked against
1219///
1220/// `interfaces` is the map `module` was canonicalized against. Every value and union
1221/// it exposes is put in the typer's environment beside this module's own, so a
1222/// declaration that forwards an imported value, builds an imported constructor or
1223/// matches on one is checked like any other. Each use of one of those names gets a
1224/// fresh instance of its declared type, so one declaration can use `Just` or
1225/// `Maybe.withDefault` at two types — see `Types`.
1226///
1227/// A name's entry is a context and a type (`Scheme`). A class member's is its
1228/// signature with its class's constraint in front, from the module's own classes and from
1229/// every imported interface's; a function's is its annotation's context and type. Each
1230/// use of one raises the obligations its context asks, which are answered once the
1231/// declaration's equations are solved — see the `classes` module.
1232pub fn type_check_recovering(module: &Module, interfaces: &HashMap<Name, Interface>) -> TypeCheck {
1233    // A `module foreign` facade uses synthetic placeholder bodies, so there is nothing
1234    // to infer — but every declaration still has to be accounted for, so each is
1235    // returned saying why it has no term.
1236    if module.binding_foreign {
1237        return TypeCheck {
1238            solved: module
1239                .values
1240                .keys()
1241                .map(|name| (name.clone(), Solved::NoBody))
1242                .collect(),
1243            instances: Vec::new(),
1244            rejected_derivations: Vec::new(),
1245            errors: Vec::new(),
1246        };
1247    }
1248
1249    // Start at a high offset to avoid collisions with the counter inside
1250    // Types::new() (which starts at 10) used during inference.
1251    let mut counter = 10_000u32;
1252
1253    // First pass: build global env from every declared type in reach — the values
1254    // each imported interface exposes, then this module's own annotated values, broken
1255    // ones included.
1256    let mut global: HashMap<String, Scheme> = HashMap::new();
1257
1258    // An imported value is keyed the way a `VarForeign` reference spells it: its name
1259    // qualified by the package and module that declared it ([`environment_key`]). That
1260    // is the only key, so it cannot collide with a local name or with a same-named value
1261    // of another module, in this package or another. An operator's backing function the
1262    // header did not expose by name is in `infix_functions` rather than `values`, and an
1263    // operator resolves to a `VarForeign` naming it all the same.
1264    for interface in interfaces.values() {
1265        for (name, signature) in interface.values.iter().chain(&interface.infix_functions) {
1266            if let Some(scheme) = scheme_of(&signature.tpe, &signature.context, &mut counter) {
1267                let qname = interface.module_name.qualify_name(name);
1268                global.insert(environment_key(&qname), scheme);
1269            }
1270        }
1271
1272        // A member is in no interface's `values`: it travels with its class, and is
1273        // declared here the way a value is, under the name a `VarForeign` spells.
1274        for (class_name, signature) in &interface.classes {
1275            insert_members(
1276                &mut global,
1277                &interface.module_name,
1278                class_name,
1279                signature,
1280                &mut counter,
1281            );
1282        }
1283    }
1284
1285    // This module's own classes' members, under the name a `VarTopLevel` spells.
1286    for (class_name, class) in &module.classes {
1287        insert_members(
1288            &mut global,
1289            &module.name,
1290            class_name,
1291            &class.signature,
1292            &mut counter,
1293        );
1294    }
1295
1296    // A declaration canonicalization recorded as broken is declared by its annotation,
1297    // when that canonicalized, exactly as an annotated one is: a caller is checked
1298    // against the type the declaration was written with, whatever is wrong with its body.
1299    let annotated = module
1300        .values
1301        .iter()
1302        .filter_map(|(name, value)| match value {
1303            canonical::Value::TypedValue { tpe, context, .. } => Some((name, tpe, context)),
1304            canonical::Value::Value { .. } => None,
1305        });
1306    let broken = module
1307        .broken
1308        .iter()
1309        .filter_map(|broken| Some((&broken.name, broken.tpe.as_ref()?, &broken.context)));
1310
1311    for (name, tpe, context) in annotated.chain(broken) {
1312        if let Some(scheme) = scheme_of(tpe, context, &mut counter) {
1313            // Add both qualified (e.g. "test-project:Test.not") and unqualified (e.g.
1314            // "not") names
1315            let qname = environment_key(&module.name.qualify_name(name));
1316            global.insert(qname, scheme.clone());
1317            global.insert(name.as_str().to_string(), scheme);
1318        }
1319    }
1320
1321    // What the canonical AST is read against: every union in reach, their
1322    // constructors and the arity of each of this module's declarations. See
1323    // [`Translation`].
1324    let translation = Translation::of(module, interfaces);
1325
1326    // Second pass: add constructor types to global from every union in reach, this
1327    // module's own and every imported interface's alike.
1328    for (type_name, union_type) in &translation.unions {
1329        // Fresh type vars for each ADT type parameter (e.g. "a" in Maybe a)
1330        let mut adt_var_map: HashMap<String, TypeVariable> = HashMap::new();
1331        for tv_name in &union_type.variables {
1332            counter += 1;
1333            adt_var_map.insert(
1334                tv_name.as_str().to_string(),
1335                TypeVariable::flexible(counter),
1336            );
1337        }
1338
1339        // Build result type: Adt(type_name, [TypeVar for each param])
1340        let result_args: Vec<Type> = union_type
1341            .variables
1342            .iter()
1343            .map(|v| Type::Variable(adt_var_map[v.as_str()].clone()))
1344            .collect();
1345        let result_type = Type::Adt(type_name.clone(), result_args);
1346
1347        for ctor in &union_type.variants {
1348            let ctor_type = if ctor.type_parameters.is_empty() {
1349                result_type.clone()
1350            } else {
1351                let mut translate_var_map = adt_var_map.clone();
1352                let params: Vec<Type> = ctor
1353                    .type_parameters
1354                    .iter()
1355                    .filter_map(|t| {
1356                        canonical_type_to_typer_type(t, &mut translate_var_map, &mut counter)
1357                    })
1358                    .collect();
1359                if params.len() != ctor.type_parameters.len() {
1360                    continue; // untranslatable param type, skip this constructor
1361                }
1362                // Build Fun type: p1 -> p2 -> ... -> result_type
1363                params
1364                    .into_iter()
1365                    .rev()
1366                    .fold(result_type.clone(), |acc, p| Type::Fun {
1367                        param_tpe: Box::new(p),
1368                        return_tpe: Box::new(acc),
1369                    })
1370            };
1371
1372            // Registered under the qualified name a `VarConstructor` spells —
1373            // "zelkova-core:Maybe.Just", named by the package and module that declared
1374            // the union — and, for this module's own unions only, under the bare name
1375            // too. A union of another package's module of the same name is not this
1376            // module's own: its `QualName` differs in the package.
1377            let qname = type_name.sibling(&ctor.name);
1378            if module.name.qualify_name(&type_name.unqualified_name()) == *type_name {
1379                global.insert(
1380                    ctor.name.as_str().to_string(),
1381                    Scheme::unconstrained(ctor_type.clone()),
1382                );
1383            }
1384            global.insert(environment_key(&qname), Scheme::unconstrained(ctor_type));
1385        }
1386    }
1387
1388    // The constructor of `Basics.Position` builds the place of a constructor from an
1389    // `Int`. A module that declares `Position` has declared it above, and one that does
1390    // not still has a derived instance that builds one.
1391    let (position_name, _) = position_constructor();
1392    global
1393        .entry(environment_key(&position_name))
1394        .or_insert_with(|| {
1395            Scheme::unconstrained(Type::Fun {
1396                param_tpe: Box::new(Type::Literal(TypeLiteral::Int)),
1397                return_tpe: Box::new(position_type()),
1398            })
1399        });
1400
1401    // Third pass: check each value. A value that fails is recorded and the pass
1402    // moves on, so one broken declaration cannot hide the others.
1403    //
1404    // In the order of their names, because each declaration's rigid variables are numbered
1405    // from `counter` and stay in the types that come back: an order that depended on the
1406    // hash map would number the same declaration differently from one run to the next.
1407    let spellings = Spellings::of(module, interfaces);
1408    let table = classes::ClassTable::of(module, interfaces);
1409    let mut errors: Vec<Error> = vec![];
1410    let mut solved: HashMap<Name, Solved> = HashMap::new();
1411    let mut values: Vec<(&Name, &canonical::Value)> = module.values.iter().collect();
1412    values.sort_by(|left, right| left.0.cmp(right.0));
1413    for (name, value) in values {
1414        let Some((term, annotation)) =
1415            value_to_term_and_annotation(value, &translation, &mut counter)
1416        else {
1417            // Unsupported construct: nothing was checked, and the entry says so
1418            // rather than the declaration going missing — see [`Solved`].
1419            solved.insert(name.clone(), Solved::Untranslatable { span: value.span() });
1420            continue;
1421        };
1422
1423        // The annotation is handed to inference rather than checked against its
1424        // result afterwards, which is what lets a mismatch *inside* the body know
1425        // that the type it failed against came from the annotation. Checking the two
1426        // whole types at the end could only ever say "this declaration is `Int` and
1427        // its body is something else", with the caret across the lot.
1428        let answer = match solve(term, annotation, &global, &table) {
1429            Ok(answer) => answer,
1430            // The declaration is answered for as well as reported, so the rest of the
1431            // module keeps the terms it solved.
1432            Err(kind) => {
1433                errors.push(Error {
1434                    kind,
1435                    span: value.span(),
1436                    declaration: name.clone(),
1437                    within: Within::Value,
1438                    spellings: spellings.clone(),
1439                });
1440                Solved::Rejected
1441            }
1442        };
1443        solved.insert(name.clone(), answer);
1444    }
1445
1446    // Fourth pass: the derivations of this module's own classes. A derived instance carries
1447    // these bindings placed in its members, but a class that nothing derives has them
1448    // checked all the same, and an error in one is at the class, where it was written. It
1449    // runs before the instances so that an instance derived from a class whose derivation
1450    // is wrong does not report the same mistake again in the members it was given.
1451    let rejected_derivations = DerivationCheck {
1452        global: &global,
1453        table: &table,
1454        translation: &translation,
1455        spellings: &spellings,
1456    }
1457    .of(module, &mut counter, &mut errors);
1458    let rejected: HashSet<QualName> = rejected_derivations
1459        .iter()
1460        .map(|class| module.name.qualify_name(class))
1461        .collect();
1462
1463    // Fifth pass: every instance, which is checked as a declaration is — its bindings
1464    // are values whose annotation is the member's signature at the instance's type — and
1465    // as a whole, for the superclasses its class asks of it.
1466    let instances = module
1467        .instances
1468        .iter()
1469        .map(|instance| {
1470            let check = InstanceCheck {
1471                global: &global,
1472                table: &table,
1473                translation: &translation,
1474                spellings: &spellings,
1475                rejected: &rejected,
1476            };
1477            check.of(instance, &mut counter, &mut errors)
1478        })
1479        .collect();
1480
1481    TypeCheck {
1482        solved,
1483        instances,
1484        rejected_derivations,
1485        errors,
1486    }
1487}
1488
1489/// Infer one declaration, or one binding of an instance, to the [`Solved`] it ends up as:
1490/// its typed term, or the entry saying a name was out of the typer's reach. An error to
1491/// report is the `Err`.
1492fn solve(
1493    term: Term,
1494    annotation: Option<Annotation>,
1495    global: &HashMap<String, Scheme>,
1496    table: &classes::ClassTable,
1497) -> Result<Solved, ErrorKind> {
1498    match infer_annotated(term, global.clone(), annotation, table) {
1499        // An unbound variable here is a hole in the typer's environment, not a
1500        // mistake in the source — see [`Solved::UnboundName`].
1501        Err(ErrorKind::UnboundVariable { name, span }) => Ok(Solved::UnboundName { name, span }),
1502        Err(kind) => Err(kind),
1503        Ok((term, context)) => Ok(Solved::Typed {
1504            term: Box::new(term),
1505            context,
1506        }),
1507    }
1508}
1509
1510/// What an instance's bindings are checked under: the type the instance is for, where its
1511/// head line was written, and what its context gives of the head's variables.
1512struct InstanceScope<'a> {
1513    head: &'a Type,
1514    span: NodeSpan,
1515    given: &'a [(QualName, TypeVariable)],
1516    names: &'a [(TypeVariable, Name)],
1517}
1518
1519/// What checking an instance reads besides the instance itself.
1520struct InstanceCheck<'a> {
1521    global: &'a HashMap<String, Scheme>,
1522    table: &'a classes::ClassTable<'a>,
1523    translation: &'a Translation<'a>,
1524    spellings: &'a Spellings,
1525    /// The classes of this module whose derivations this pass rejected.
1526    rejected: &'a HashSet<QualName>,
1527}
1528
1529impl InstanceCheck<'_> {
1530    /// Check `instance`: each of its bindings against its member's signature at the
1531    /// instance's type, and the instance as a whole against the superclasses its class
1532    /// has. Errors are pushed onto `errors`.
1533    ///
1534    /// The instance's context is *given* in both, as an annotation's is inside a
1535    /// declaration: the variables the head binds are variables of the unification, a
1536    /// constraint of the context is on one of them, and an obligation on that same
1537    /// variable is answered by it.
1538    ///
1539    /// A derived instance is checked like any other. Canonicalization gave it the members
1540    /// its class's derivation stands for and the context its type's arguments need, so its
1541    /// superclasses are discharged against that context, and an error in a generated
1542    /// binding is on the span of the word `derived`. Where the class's derivations were
1543    /// rejected, in this module or the one that declares it, the class has the error and a
1544    /// derived instance's members, which are generated out of the derivation that failed,
1545    /// report none of their own.
1546    fn of(
1547        &self,
1548        instance: &canonical::Instance,
1549        counter: &mut u32,
1550        errors: &mut Vec<Error>,
1551    ) -> SolvedInstance {
1552        let signature = &instance.signature;
1553
1554        let mut variables: HashMap<String, TypeVariable> = HashMap::new();
1555        let head = instance_head_type(&signature.head, &mut variables, counter);
1556        let head = make_rigid(head, &mut variables, Binder::InstanceHead);
1557        let given: Vec<(QualName, TypeVariable)> = signature
1558            .context
1559            .iter()
1560            .filter_map(|constraint| {
1561                Some((
1562                    constraint.class.clone(),
1563                    variables.get(constraint.variable.as_str())?.clone(),
1564                ))
1565            })
1566            .collect();
1567        let context = given
1568            .iter()
1569            .map(|(class, variable)| Predicate {
1570                class: class.clone(),
1571                tpe: Type::Variable(variable.clone()),
1572            })
1573            .collect();
1574        let mut names: Vec<(TypeVariable, Name)> = variables
1575            .iter()
1576            .map(|(name, variable)| (variable.clone(), Name::new(name.clone())))
1577            .collect();
1578        names.sort_by(|left, right| left.1.cmp(&right.1));
1579
1580        let text = instance_text(signature, &head, &names);
1581        let class = self.table.class(&signature.class);
1582
1583        let mut rejected = false;
1584        let mut bindings = Vec::new();
1585
1586        // The members of an instance derived from a class whose derivations were rejected
1587        // restate the class's error, so an error in one is left to it.
1588        let restated = instance.derived
1589            && (self.rejected.contains(&signature.class)
1590                || class.is_some_and(|class| class.derivations_rejected));
1591
1592        if let Some(class) = class {
1593            let obligations = class
1594                .superclasses
1595                .iter()
1596                .map(|superclass| classes::Obligation {
1597                    class: superclass.class.clone(),
1598                    tpe: head.clone(),
1599                    origin: Origin::new(Reason::SuperclassInstance, signature.span),
1600                })
1601                .collect();
1602
1603            let declared = classes::Declared {
1604                tpe: &head,
1605                annotated: true,
1606                given: &given,
1607                names: &names,
1608                member_variables: &[],
1609                written: Written::InstanceContext,
1610            };
1611
1612            if let Err(kind) =
1613                classes::discharge(self.table, obligations, &Substitution::empty(), &declared)
1614            {
1615                rejected = true;
1616                errors.push(Error {
1617                    kind,
1618                    span: signature.span,
1619                    declaration: Name::new(text.clone()),
1620                    within: Within::Instance,
1621                    spellings: self.spellings.clone(),
1622                });
1623            }
1624        }
1625
1626        for value in &instance.bindings {
1627            let canonical::Value::Value { name, .. } = value else {
1628                continue;
1629            };
1630
1631            let scope = InstanceScope {
1632                head: &head,
1633                span: signature.span,
1634                given: &given,
1635                names: &names,
1636            };
1637
1638            let answer = match self.binding(value, class, &scope, counter) {
1639                Some(Ok(answer)) => answer,
1640                Some(Err(kind)) => {
1641                    if !restated {
1642                        errors.push(Error {
1643                            kind,
1644                            span: value.span(),
1645                            declaration: name.clone(),
1646                            within: Within::Binding(text.clone()),
1647                            spellings: self.spellings.clone(),
1648                        });
1649                    }
1650                    Solved::Rejected
1651                }
1652                None => Solved::Untranslatable { span: value.span() },
1653            };
1654            bindings.push((name.clone(), answer));
1655        }
1656
1657        SolvedInstance {
1658            head,
1659            context,
1660            bindings,
1661            rejected,
1662        }
1663    }
1664
1665    /// One binding of an instance's body, inferred against the signature of the member it
1666    /// defines, with the class variable replaced by the instance's head. `None` when it
1667    /// cannot be read: the binding does not translate, or its class has no member of that
1668    /// name in reach — which canonicalization has reported.
1669    fn binding(
1670        &self,
1671        value: &canonical::Value,
1672        class: Option<&canonical::ClassSignature>,
1673        scope: &InstanceScope,
1674        counter: &mut u32,
1675    ) -> Option<Result<Solved, ErrorKind>> {
1676        let canonical::Value::Value { name, .. } = value else {
1677            return None;
1678        };
1679        let class = class?;
1680        let member = class.members.iter().find(|member| &member.name == name)?;
1681
1682        let (term, _) = value_to_term_and_annotation(value, self.translation, counter)?;
1683
1684        // The member's signature has the class variable free in it. It is translated like
1685        // any annotation, and the variable it came out as is replaced by the head: every
1686        // other variable of the signature stays one of its own.
1687        let mut variables: HashMap<String, TypeVariable> = HashMap::new();
1688        let signature = canonical_type_to_typer_type(&member.tpe, &mut variables, counter)?;
1689        let signature = make_rigid(signature, &mut variables, Binder::MemberSignature);
1690        let class_variable = variables.get(class.variable.as_str())?;
1691        let tpe = Substitution::substitute(signature, class_variable, scope.head);
1692
1693        // What the signature binds besides the class variable is the member's own, and is
1694        // written the way the class wrote it.
1695        let mut names = scope.names.to_vec();
1696        let mut member_variables = Vec::new();
1697        for (written, variable) in &variables {
1698            if variable != class_variable {
1699                names.push((variable.clone(), Name::new(written.clone())));
1700                member_variables.push(variable.clone());
1701            }
1702        }
1703        names.sort_by(|left, right| left.1.cmp(&right.1));
1704
1705        // The head line stands where an annotation would: the span a mismatch with the
1706        // member's signature draws its second label under.
1707        let annotation = Annotation {
1708            tpe,
1709            span: scope.span,
1710            reason: Reason::InstanceMember,
1711            context: scope.given.to_vec(),
1712            names,
1713            member_variables,
1714            written: Written::InstanceContext,
1715        };
1716
1717        Some(solve(term, Some(annotation), self.global, self.table))
1718    }
1719}
1720
1721/// `Basics.Position`'s one constructor, and where it sits: the compiler knows it by
1722/// name, as it knows the scalars ([`scalars::POSITION`]).
1723fn position_constructor() -> (QualName, Constructor) {
1724    let union = scalars::POSITION.qual_name();
1725    let name = Name::new(scalars::POSITION.name);
1726
1727    (
1728        union.sibling(&name),
1729        Constructor {
1730            union,
1731            name,
1732            index: 0,
1733            arity: 1,
1734        },
1735    )
1736}
1737
1738/// The type `Basics.Position`: what `differed` and `atConstructor` are handed.
1739fn position_type() -> Type {
1740    Type::Adt(scalars::POSITION.qual_name(), Vec::new())
1741}
1742
1743/// What checking the derivations of a module's classes reads.
1744struct DerivationCheck<'a> {
1745    global: &'a HashMap<String, Scheme>,
1746    table: &'a classes::ClassTable<'a>,
1747    translation: &'a Translation<'a>,
1748    spellings: &'a Spellings,
1749}
1750
1751impl DerivationCheck<'_> {
1752    /// Check the bindings of every derivation of `module`'s classes, each as a declaration
1753    /// annotated with the type the chapter gives its role over the type the member
1754    /// answers with — `matched : R`, `differed : Position -> Position -> R`,
1755    /// `atConstructor : Position -> R` and `combine : R -> R -> R`. Errors are pushed onto
1756    /// `errors`, classes in the order of their names. The classes with a binding that did
1757    /// not check come back by name, in that order.
1758    ///
1759    /// No context is given to a binding: none of them mentions the class variable, so each
1760    /// stands for every type that derives the class, and what one needs of a type is an
1761    /// instance in scope or an error. A variable the answer type holds is the member
1762    /// signature's own, and is rigid. `Comparable`'s `differed i j = compare i j` needs
1763    /// `Comparable Position`.
1764    fn of(&self, module: &Module, counter: &mut u32, errors: &mut Vec<Error>) -> Vec<Name> {
1765        let mut classes: Vec<_> = module.classes.iter().collect();
1766        classes.sort_by(|left, right| left.0.cmp(right.0));
1767
1768        let mut rejected = Vec::new();
1769        for (name, class) in classes {
1770            let before = errors.len();
1771            for derivation in &class.signature.derivations {
1772                for (role, value) in derivation.bindings.roles() {
1773                    self.binding(derivation, role, value, counter, errors);
1774                }
1775            }
1776            if errors.len() > before {
1777                rejected.push(name.clone());
1778            }
1779        }
1780        rejected
1781    }
1782
1783    fn binding(
1784        &self,
1785        derivation: &canonical::Derivation,
1786        role: canonical::DerivationRole,
1787        value: &canonical::Value,
1788        counter: &mut u32,
1789        errors: &mut Vec<Error>,
1790    ) {
1791        let canonical::Value::Value { name, .. } = value else {
1792            return;
1793        };
1794        let Some((term, _)) = value_to_term_and_annotation(value, self.translation, counter) else {
1795            return;
1796        };
1797
1798        let mut variables: HashMap<String, TypeVariable> = HashMap::new();
1799        let Some(answer) =
1800            canonical_type_to_typer_type(&derivation.result, &mut variables, counter)
1801        else {
1802            return;
1803        };
1804        // A variable of the answer type is one the member's signature binds beyond the
1805        // class's, which every caller of the member chooses for itself: a binding is held
1806        // to every type it may stand for.
1807        let answer = make_rigid(answer, &mut variables, Binder::MemberSignature);
1808        let function = |parameters: Vec<Type>, result: Type| {
1809            parameters
1810                .into_iter()
1811                .rev()
1812                .fold(result, |result, parameter| Type::Fun {
1813                    param_tpe: Box::new(parameter),
1814                    return_tpe: Box::new(result),
1815                })
1816        };
1817        let tpe = match role {
1818            canonical::DerivationRole::Matched => answer.clone(),
1819            canonical::DerivationRole::Differed => {
1820                function(vec![position_type(), position_type()], answer.clone())
1821            }
1822            canonical::DerivationRole::AtConstructor => {
1823                function(vec![position_type()], answer.clone())
1824            }
1825            canonical::DerivationRole::Combine => {
1826                function(vec![answer.clone(), answer.clone()], answer.clone())
1827            }
1828        };
1829
1830        let mut names: Vec<(TypeVariable, Name)> = variables
1831            .iter()
1832            .map(|(name, variable)| (variable.clone(), Name::new(name.clone())))
1833            .collect();
1834        names.sort_by(|left, right| left.1.cmp(&right.1));
1835
1836        let annotation = Annotation {
1837            tpe,
1838            span: derivation.span,
1839            reason: Reason::DerivationBinding,
1840            context: Vec::new(),
1841            names,
1842            member_variables: Vec::new(),
1843            written: Written::Derivation,
1844        };
1845
1846        if let Err(kind) = solve(term, Some(annotation), self.global, self.table) {
1847            errors.push(Error {
1848                kind,
1849                span: value.span(),
1850                declaration: name.clone(),
1851                within: Within::Derivation(derivation.member.to_string()),
1852                spellings: self.spellings.clone(),
1853            });
1854        }
1855    }
1856}
1857
1858/// `instance Eq a => Eq (Box a)`, minus the keyword: how a message names an instance.
1859fn instance_text(
1860    signature: &canonical::InstanceSignature,
1861    head: &Type,
1862    names: &[(TypeVariable, Name)],
1863) -> String {
1864    let names: VariableNames = names
1865        .iter()
1866        .map(|(variable, name)| (variable.clone(), name.to_string()))
1867        .collect();
1868    let text = WithNames(head, &names).to_string();
1869    let head = match head {
1870        Type::Adt(_, args) if !args.is_empty() => format!("({})", text),
1871        _ => text,
1872    };
1873    let constraints: Vec<String> = signature
1874        .context
1875        .iter()
1876        .map(|constraint| {
1877            format!(
1878                "{} {}",
1879                constraint.class.unqualified_name(),
1880                constraint.variable
1881            )
1882        })
1883        .collect();
1884    let context = match constraints.as_slice() {
1885        [] => String::new(),
1886        [one] => format!("{} => ", one),
1887        many => format!("({}) => ", many.join(", ")),
1888    };
1889
1890    format!("{}{} {}", context, signature.class.unqualified_name(), head)
1891}
1892
1893/// The scheme a declared type and the context written in front of it make: the type as
1894/// the typer reads it, and each constraint on the variable it was translated to.
1895fn scheme_of(
1896    tpe: &canonical::Type,
1897    context: &[canonical::Constraint],
1898    counter: &mut u32,
1899) -> Option<Scheme> {
1900    let mut variables = HashMap::new();
1901    let tpe = canonical_type_to_typer_type(tpe, &mut variables, counter)?;
1902    let context = context
1903        .iter()
1904        .filter_map(|constraint| {
1905            Some(Predicate {
1906                class: constraint.class.clone(),
1907                tpe: Type::Variable(variables.get(constraint.variable.as_str())?.clone()),
1908            })
1909        })
1910        .collect();
1911
1912    Some(Scheme { context, tpe })
1913}
1914
1915/// Declare the members of a class `module_name` declares, each under the name a
1916/// reference to it spells ([`environment_key`]): its signature, with the class's own
1917/// constraint in front.
1918fn insert_members(
1919    global: &mut HashMap<String, Scheme>,
1920    module_name: &ModuleName,
1921    class_name: &Name,
1922    class: &canonical::ClassSignature,
1923    counter: &mut u32,
1924) {
1925    let declared = module_name.qualify_name(class_name);
1926
1927    for member in &class.members {
1928        let mut variables = HashMap::new();
1929        let Some(tpe) = canonical_type_to_typer_type(&member.tpe, &mut variables, counter) else {
1930            continue;
1931        };
1932
1933        // Every member's signature mentions the class variable, so it is always found;
1934        // canonicalization rejects a class with a member that does not.
1935        let Some(variable) = variables.get(class.variable.as_str()) else {
1936            continue;
1937        };
1938        let context = vec![Predicate {
1939            class: declared.clone(),
1940            tpe: Type::Variable(variable.clone()),
1941        }];
1942
1943        global.insert(
1944            environment_key(&module_name.qualify_name(&member.name)),
1945            Scheme { context, tpe },
1946        );
1947    }
1948}
1949
1950// ── Translation helpers ───────────────────────────────────────────────────────
1951
1952/// The key the typer's environment holds a declaration's type under: the package that
1953/// declares it, a `:`, then its qualified name — `zelkova-core:Maybe.withDefault`.
1954///
1955/// The package is in the key for the reason it is in a [`QualName`]: two packages may
1956/// each hold a module `Size`, and `Size.foo` alone would give both declarations one
1957/// entry, owned by whichever was inserted last. Neither a package name nor a module name
1958/// can contain a `:`, so no two declarations share a key, and no key is a bare name a
1959/// local is looked up by.
1960fn environment_key(qname: &QualName) -> String {
1961    format!("{}:{}", qname.package(), qname.to_name())
1962}
1963
1964/// Union declarations, keyed by the qualified name of each declaration.
1965///
1966/// Keyed that way rather than by the spelling, so that a lookup answers "is this the
1967/// declaration that module named?" and not "is something spelled like that in reach?".
1968/// The two differ for every imported constructor whose type shares a name with a local
1969/// one, which is what `BUG-35` closed.
1970type Unions<'a> = HashMap<QualName, &'a canonical::UnionType>;
1971
1972/// Everything the translation from the canonical AST reads besides the expression in
1973/// front of it.
1974///
1975/// Each of them answers a question the canonical node cannot: which union a constructor
1976/// belongs to and where in it, and how many arguments a call has to supply before it is a
1977/// direct call. All of them are facts of the module and of what it imports, which is why
1978/// they are gathered once here — the declaration being translated is the only thing that
1979/// changes between calls.
1980struct Translation<'a> {
1981    /// Every union in reach — this module's own, and every one an imported
1982    /// [`Interface`] exposes — keyed by the qualified name that identifies each
1983    /// declaration rather than by the spelling the `type` line wrote. A constructor
1984    /// carries the qualified name of the type it builds, so this key is what finds the
1985    /// declaration a constructor in a pattern belongs to — see [`translate_pattern`].
1986    ///
1987    /// An interface's union is only as complete as its module exposed it: an opaque
1988    /// one crosses with no constructors, which is also why no canonical constructor
1989    /// can name one.
1990    unions: Unions<'a>,
1991    /// The constructors of every union in [`unions`](Self::unions), keyed the way a
1992    /// `VarConstructor` spells one, each with the place in its declaration both
1993    /// backends need.
1994    constructors: HashMap<QualName, Constructor>,
1995    /// How many parameters each of this module's declarations was written with.
1996    ///
1997    /// This is the callee's arity at a call site naming one of them, which is what
1998    /// decides an application's [`Saturation`]. The rule itself — parameter count, not
1999    /// arrow count — is [`canonical::Value::arity`], which `ir::build` reads too.
2000    arities: HashMap<Name, usize>,
2001    /// How many parameters each value an imported [`Interface`] exposes is emitted with
2002    /// ([`Interface::arities`]), keyed the way a `VarForeign` spells it: its name
2003    /// qualified by the package and module that declared it.
2004    ///
2005    /// It is the same fact as [`arities`](Self::arities), recorded by the module that
2006    /// declared the value, so a call to it is saturated at the count its emitted function
2007    /// takes. It is also what [`ReferenceKind::Foreign`] carries, since a backend using an
2008    /// imported function as a value needs its arity too.
2009    foreign_arities: HashMap<QualName, usize>,
2010}
2011
2012impl<'a> Translation<'a> {
2013    /// The translation for `module`, checked against `interfaces`.
2014    ///
2015    /// The interfaces' unions go in first and this module's own after them, so that if
2016    /// the map somehow held an interface of the module under check, the declarations
2017    /// in front of the typer are the ones that win.
2018    fn of(module: &'a Module, interfaces: &'a HashMap<Name, Interface>) -> Translation<'a> {
2019        let mut unions: Unions<'a> = HashMap::new();
2020        let mut foreign_arities = HashMap::new();
2021
2022        for interface in interfaces.values() {
2023            for (name, union_type) in &interface.unions {
2024                unions.insert(interface.module_name.qualify_name(name), union_type);
2025            }
2026
2027            // Every value the typer's environment registers for this interface, so that
2028            // every `VarForeign` it can type has an arity here. One the interface did not
2029            // record is read as a parameterless binding's: see `Interface::arities`.
2030            for name in interface
2031                .values
2032                .keys()
2033                .chain(interface.infix_functions.keys())
2034            {
2035                let arity = interface.arities.get(name).copied().unwrap_or(0);
2036                foreign_arities.insert(interface.module_name.qualify_name(name), arity);
2037            }
2038        }
2039
2040        for (name, union_type) in &module.types {
2041            unions.insert(module.name.qualify_name(name), union_type);
2042        }
2043
2044        let mut constructors = constructors_of(&unions);
2045        // `Basics.Position`'s constructor is known whether or not an interface in reach
2046        // carries it, since a derived instance builds one and no module exposes it.
2047        let (position_name, position) = position_constructor();
2048        constructors.entry(position_name).or_insert(position);
2049
2050        let arities = module
2051            .values
2052            .iter()
2053            .map(|(name, value)| (name.clone(), value.arity()))
2054            .collect();
2055
2056        Translation {
2057            unions,
2058            constructors,
2059            arities,
2060            foreign_arities,
2061        }
2062    }
2063
2064    /// A translation that knows these unions and nothing else: no arity is known, so
2065    /// every application it produces is [`Saturation::Partial`].
2066    #[cfg(test)]
2067    fn of_types(unions: Unions<'a>) -> Translation<'a> {
2068        let constructors = constructors_of(&unions);
2069
2070        Translation {
2071            unions,
2072            constructors,
2073            arities: HashMap::new(),
2074            foreign_arities: HashMap::new(),
2075        }
2076    }
2077
2078    /// How many arguments the callee of an application spine takes, when this module
2079    /// knows.
2080    ///
2081    /// A declaration of this module, one of another module and a constructor each have
2082    /// one. `None` is what makes an application [`Saturation::Partial`], and it is the
2083    /// honest answer twice over: a local is a value rather than a declaration and has no
2084    /// arity at all, and a callee that is itself an expression — the result of a `case`,
2085    /// say — is a value too. A backend that cannot prove a call saturated goes through
2086    /// `$curry`, which is correct for both.
2087    fn callee_arity(&self, callee: &canonical::Expression) -> Option<usize> {
2088        match &callee.kind {
2089            canonical::ExpressionKind::VarTopLevel(qname) => {
2090                self.arities.get(&qname.unqualified_name()).copied()
2091            }
2092            canonical::ExpressionKind::VarForeign(qname, _, _) => Some(self.foreign_arity(qname)),
2093            canonical::ExpressionKind::VarConstructor(qname, _) => {
2094                self.constructors.get(qname).map(|ctor| ctor.arity)
2095            }
2096            _ => None,
2097        }
2098    }
2099
2100    /// The arity of `qname`, a value another module declares, as its interface recorded
2101    /// it — 0 for one no interface in reach records, the arity of a parameterless binding.
2102    ///
2103    /// Every name canonicalization resolves to a `VarForeign` is one an interface in
2104    /// reach exposes, so the fallback is for a value its module recorded as broken, or for
2105    /// a hand-built interface map; see [`Interface::arities`].
2106    fn foreign_arity(&self, qname: &QualName) -> usize {
2107        self.foreign_arities.get(qname).copied().unwrap_or(0)
2108    }
2109}
2110
2111/// Every constructor of `unions`, keyed the way a `VarConstructor` spells one: the
2112/// constructor's name qualified by the package and module that declared the union it
2113/// builds.
2114fn constructors_of(unions: &Unions) -> HashMap<QualName, Constructor> {
2115    let mut constructors = HashMap::new();
2116
2117    for (union, union_type) in unions {
2118        for variant in crate::ir::variants_of(union_type) {
2119            // A union is named by its declaring package and module, so that is where
2120            // its constructors are named from too.
2121            let name = union.sibling(&variant.name);
2122
2123            constructors.insert(
2124                name,
2125                Constructor {
2126                    union: union.clone(),
2127                    name: variant.name,
2128                    index: variant.index,
2129                    arity: variant.arity,
2130                },
2131            );
2132        }
2133    }
2134
2135    constructors
2136}
2137
2138/// Convert a canonical type to the typer's simplified Type representation.
2139///
2140/// Every variant of [`canonical::Type`] converts, so this answers `None` for no type
2141/// today. The `Option` is what a type form the typer cannot read would answer, and the
2142/// callers keep their handling of it: a declaration whose annotation is `None` here is
2143/// left unchecked ([`value_to_term_and_annotation`]), and a value or a constructor whose
2144/// declared type is `None` is not in the environment inference reads, so a name reaching
2145/// one is [`Solved::UnboundName`].
2146///
2147/// `var_map` maps named type variables (e.g. "a") to consistent TypeVariable
2148/// ids, so that `a -> a` produces the same variable on both sides.
2149///
2150/// # How a name decides which type it becomes
2151///
2152/// A [`canonical::Type::Type`] names its declaration in full — `Widget.Size`, not
2153/// `Size` (`AST-4`) — and the whole of that name is what picks the arm. A nullary
2154/// type whose qualified name is [a scalar the compiler
2155/// knows](super::scalars) becomes the matching [`Type::Literal`]; everything else
2156/// becomes a [`Type::Adt`], carrying that name whole.
2157///
2158/// For a name that resolved, that is the declaring module's. For one that resolved to
2159/// nothing it is the module under check, applied to the whole *written* spelling, dots
2160/// and all, because `Type::from_parser_type` hands the undivided name to
2161/// `ModuleName::qualify_name` rather than splitting a module half off it — so an
2162/// unresolved `Missing.Thing` written in `Test` arrives here as `Test.Missing.Thing`
2163/// and does not collapse onto the local `Test.Thing`.
2164pub(crate) fn canonical_type_to_typer_type(
2165    tpe: &canonical::Type,
2166    var_map: &mut HashMap<String, TypeVariable>,
2167    counter: &mut u32,
2168) -> Option<Type> {
2169    match tpe {
2170        canonical::Type::Variable(name) => {
2171            let tv = var_map.entry(name.as_str().to_string()).or_insert_with(|| {
2172                *counter += 1;
2173                TypeVariable::flexible(*counter)
2174            });
2175            Some(Type::Variable(tv.clone()))
2176        }
2177        canonical::Type::Arrow(a, b) => {
2178            let a = canonical_type_to_typer_type(a, var_map, counter)?;
2179            let b = canonical_type_to_typer_type(b, var_map, counter)?;
2180            Some(Type::Fun {
2181                param_tpe: Box::new(a),
2182                return_tpe: Box::new(b),
2183            })
2184        }
2185        // `Tuple::try_map` keeps the arity attached to the value instead of
2186        // re-deriving it here, the same way the parser → canonical conversions
2187        // in `canonical/mod.rs` do.
2188        canonical::Type::Tuple(tuple) => {
2189            let elements = tuple
2190                .try_map(|elem| canonical_type_to_typer_type(elem, var_map, counter).ok_or(()))
2191                .ok()?;
2192            Some(Type::Tuple(elements))
2193        }
2194        canonical::Type::Unit => Some(Type::Unit),
2195        // Label for label: the canonical map is already the set the typer's is.
2196        canonical::Type::Record(fields) => {
2197            let fields = fields
2198                .iter()
2199                .map(|(label, field)| {
2200                    let field = canonical_type_to_typer_type(field, var_map, counter)?;
2201                    Some((label.clone(), field))
2202                })
2203                .collect::<Option<BTreeMap<_, _>>>()?;
2204            Some(Type::Record(fields))
2205        }
2206        canonical::Type::Type(name, args) => {
2207            if args.is_empty() {
2208                if let Some(literal) = scalar_literal(name) {
2209                    return Some(Type::Literal(literal));
2210                }
2211            }
2212
2213            let converted: Option<Vec<Type>> = args
2214                .iter()
2215                .map(|a| canonical_type_to_typer_type(a, var_map, counter))
2216                .collect();
2217            Some(Type::Adt(name.clone(), converted?))
2218        }
2219    }
2220}
2221
2222/// `tpe`, with every variable `variables` names made rigid, and `variables` updated to
2223/// hold the rigid ones.
2224///
2225/// `tpe` and `variables` are what [`canonical_type_to_typer_type`] built for a type the
2226/// declaration being checked is quantified over: an annotation, an instance's head, the
2227/// member signature an instance's binding is held to. Each variable keeps its `id` and
2228/// takes the name it was written by and the `binder` it was written in, so a given built from
2229/// `variables` afterwards is on the variable the type holds, and `unify` will solve none of
2230/// them. A variable already rigid is left as it is.
2231fn make_rigid(tpe: Type, variables: &mut HashMap<String, TypeVariable>, binder: Binder) -> Type {
2232    let mut tpe = tpe;
2233    for (written, variable) in variables.iter_mut() {
2234        if variable.is_rigid() {
2235            continue;
2236        }
2237        let rigid = variable
2238            .clone()
2239            .into_rigid(Name::new(written.clone()), binder);
2240        tpe = Substitution::substitute(tpe, variable, &Type::Variable(rigid.clone()));
2241        *variable = rigid;
2242    }
2243    tpe
2244}
2245
2246/// The literal type the typer gives a [scalar](super::scalars), if `name` is the
2247/// qualified name of one it has a literal type for.
2248///
2249/// Four of the five appear here. [`scalars::BOOL`] does not: it is a scalar *and* an
2250/// ordinary union, so `Bool` in an annotation takes the [`Type::Adt`] path every other
2251/// declaration takes and meets `True` and `False` there. [`bool_type`] is the same type,
2252/// built for the three `Bool`s no source spells.
2253fn scalar_literal(name: &QualName) -> Option<TypeLiteral> {
2254    const LITERALS: &[(scalars::Scalar, TypeLiteral)] = &[
2255        (scalars::INT, TypeLiteral::Int),
2256        (scalars::FLOAT, TypeLiteral::Float),
2257        (scalars::CHAR, TypeLiteral::Char),
2258        (scalars::STRING, TypeLiteral::String),
2259    ];
2260
2261    LITERALS
2262        .iter()
2263        .find(|(scalar, _)| scalar.declares(name))
2264        .map(|(_, literal)| literal.clone())
2265}
2266
2267/// The type of a `Bool`: the union [`scalars::BOOL`] names, with no arguments.
2268///
2269/// `Bool` is [a scalar and an ordinary union at
2270/// once](../../docs/spec/types.md#scalar-types) — the compiler knows its
2271/// representation and nothing about its structure — so this is the very type
2272/// `canonical_type_to_typer_type` produces for an annotation naming `Basics.Bool`, and
2273/// the type `Basics` registers `True` and `False` at.
2274///
2275/// An [`if` condition](../../docs/spec/expressions.md#if--then--else) needs a `Bool`
2276/// the source did not spell, and `translate_pattern` gives a `Basics.True` or
2277/// `Basics.False` pattern this type when it turns it into a test on its value. It
2278/// names `Basics.Bool` and nothing else, so a module declaring its own `type Bool`
2279/// does not satisfy an `if` ([`DEC-15`](../../docs/decisions/dec-15.md) decisions 1
2280/// and 5).
2281pub(super) fn bool_type() -> Type {
2282    Type::Adt(scalars::BOOL.qual_name(), vec![])
2283}
2284
2285/// Convert a canonical expression to a Term, keeping the position it was written at.
2286///
2287/// Returns None for constructs the inference engine doesn't yet handle (a `VarKernel`
2288/// reference), and for a constructor of a union neither this module nor an interface in
2289/// [`Translation`] declares.
2290///
2291/// Every arm attaches `expr.span` to the term it builds. That is the whole of what
2292/// `ERR-4` needed from this function: a constraint can only point at a
2293/// sub-expression if the term that produced it remembers where it came from.
2294///
2295/// # What is recorded here and nowhere else
2296///
2297/// This is the only moment at which a reference's *kind* is known. A local, a
2298/// top-level, an imported value and a constructor are four different things to emit,
2299/// and the spelling each leaves behind is bare for one of them and qualified for the
2300/// rest — so a backend handed only the string could not tell them apart
2301/// ([`DEC-18` decision
2302/// 1](../../docs/decisions/dec-18.md#1--the-backend-reads-a-typed-ir-and-the-typer-is-what-produces-it)).
2303/// Each becomes a [`Reference`] carrying both the lookup key inference uses and what
2304/// the name is. An application spine records the same way whether it is
2305/// [saturated](Saturation), which is a question about the spine and not about any one
2306/// `Apply` node.
2307fn canonical_expr_to_term(
2308    expr: &canonical::Expression,
2309    translation: &Translation,
2310    counter: &mut u32,
2311) -> Option<Term> {
2312    let kind = match &expr.kind {
2313        // Carried at the canonical AST's own width: [`Int` is 64
2314        // bits](../../docs/spec/evaluation-semantics.md#numbers), and a term is what
2315        // code is generated from, so narrowing here would emit a different number than
2316        // the one that was written.
2317        canonical::ExpressionKind::Int(i) => TermKind::Int(*i),
2318        canonical::ExpressionKind::Char(c) => TermKind::Char(*c),
2319        canonical::ExpressionKind::String(s) => TermKind::String(s.clone()),
2320        canonical::ExpressionKind::Float(f) => TermKind::Float(*f),
2321        canonical::ExpressionKind::VarLocal(name) => {
2322            TermKind::Identifier(Reference::local(name.as_str()))
2323        }
2324        canonical::ExpressionKind::VarTopLevel(qname) => TermKind::Identifier(Reference {
2325            name: environment_key(qname),
2326            kind: ReferenceKind::TopLevel(qname.clone()),
2327        }),
2328        // A value another module declares. Its type is the one its module's interface
2329        // declared, which `type_check` registers under this same qualified name.
2330        canonical::ExpressionKind::VarForeign(qname, package, _) => {
2331            TermKind::Identifier(Reference {
2332                name: environment_key(qname),
2333                kind: ReferenceKind::Foreign(
2334                    qname.clone(),
2335                    package.clone(),
2336                    translation.foreign_arity(qname),
2337                ),
2338            })
2339        }
2340        // A constructor builds a tagged value rather than reading a binding, so it
2341        // carries its place in its declaration. That place comes from the union,
2342        // which is in `translation.constructors` whether this module declared it or
2343        // an imported interface did. The type the canonical node carries is not read:
2344        // the one `type_check` registers is built from the union's own variables.
2345        canonical::ExpressionKind::VarConstructor(qname, _) => {
2346            let ctor = translation.constructors.get(qname)?;
2347
2348            TermKind::Identifier(Reference {
2349                name: environment_key(qname),
2350                kind: ReferenceKind::Constructor(ctor.clone()),
2351            })
2352        }
2353        // The spine is walked as a whole rather than one node at a time, because
2354        // whether a call is saturated is a fact about the callee and the number of
2355        // arguments reaching it. Each node keeps its own canonical span, so a type
2356        // error still points where it did.
2357        canonical::ExpressionKind::Apply(_, _) => {
2358            let (callee, applications) = spine(expr);
2359            let arity = translation.callee_arity(callee);
2360
2361            let mut term = canonical_expr_to_term(callee, translation, counter)?;
2362
2363            for (supplied, application) in applications.iter().enumerate() {
2364                // `spine` collects `Apply` nodes and nothing else.
2365                let canonical::ExpressionKind::Apply(_, argument) = &application.kind else {
2366                    return None;
2367                };
2368
2369                let argument = canonical_expr_to_term(argument, translation, counter)?;
2370                // The node that consumes the callee's last argument is the direct
2371                // call; everything before it is a partial application and everything
2372                // after it applies whatever that call returned.
2373                let saturation = match arity {
2374                    Some(arity) if arity == supplied + 1 => Saturation::Saturated,
2375                    _ => Saturation::Partial,
2376                };
2377
2378                term = Term {
2379                    span: application.span,
2380                    kind: TermKind::Apply {
2381                        fun: Box::new(term),
2382                        arg: Box::new(argument),
2383                        saturation,
2384                    },
2385                };
2386            }
2387
2388            return Some(term);
2389        }
2390        canonical::ExpressionKind::If(cond, t, f) => {
2391            let cond = canonical_expr_to_term(cond, translation, counter)?;
2392            let t = canonical_expr_to_term(t, translation, counter)?;
2393            let f = canonical_expr_to_term(f, translation, counter)?;
2394            TermKind::If {
2395                cond: Box::new(cond),
2396                true_branch: Box::new(t),
2397                false_branch: Box::new(f),
2398            }
2399        }
2400        canonical::ExpressionKind::Tuple(tuple) => {
2401            let elements = tuple
2402                .try_map(|elem| canonical_expr_to_term(elem, translation, counter).ok_or(()))
2403                .ok()?;
2404            TermKind::Tuple(elements)
2405        }
2406        canonical::ExpressionKind::Unit => TermKind::Unit,
2407        canonical::ExpressionKind::Case(scrutinee_expr, branches) => {
2408            let scrutinee = canonical_expr_to_term(scrutinee_expr, translation, counter)?;
2409            let term_branches: Vec<(TermPattern, Box<Term>)> = branches
2410                .iter()
2411                .map(|cb| {
2412                    let pattern = translate_pattern(&cb.pattern, translation, counter)?;
2413                    let body = canonical_expr_to_term(&cb.expression, translation, counter)?;
2414                    Some((pattern, Box::new(body)))
2415                })
2416                .collect::<Option<Vec<_>>>()?;
2417            TermKind::Case {
2418                scrutinee: Box::new(scrutinee),
2419                branches: term_branches,
2420                form: CaseForm::Expression,
2421            }
2422        }
2423        // A name that did not resolve. Its error is canonicalization's, and the term
2424        // stands where the name was written so the rest of the body is still checked.
2425        canonical::ExpressionKind::Hole => TermKind::Hole,
2426        // The fields stay in the order they were written: only the record's type is a
2427        // set, and that is built from them by `constraint::collect`.
2428        canonical::ExpressionKind::Record(fields) => {
2429            TermKind::Record(translate_fields(fields, translation, counter)?)
2430        }
2431        canonical::ExpressionKind::Update(record, fields) => TermKind::Update {
2432            record: Box::new(canonical_expr_to_term(record, translation, counter)?),
2433            fields: translate_fields(fields, translation, counter)?,
2434        },
2435        canonical::ExpressionKind::Access(record, label, label_span) => TermKind::Access {
2436            record: Box::new(canonical_expr_to_term(record, translation, counter)?),
2437            label: label.clone(),
2438            label_span: *label_span,
2439        },
2440        canonical::ExpressionKind::Accessor(label, label_span) => TermKind::Accessor {
2441            label: label.clone(),
2442            label_span: *label_span,
2443        },
2444        // Not yet supported: VarKernel
2445        _ => return None,
2446    };
2447
2448    Some(Term {
2449        span: expr.span,
2450        kind,
2451    })
2452}
2453
2454/// The fields of a record or an update, in the order they were written, each with the
2455/// span of its label.
2456fn translate_fields(
2457    fields: &[canonical::Field],
2458    translation: &Translation,
2459    counter: &mut u32,
2460) -> Option<Vec<Field<Term>>> {
2461    fields
2462        .iter()
2463        .map(|field| {
2464            Some(Field {
2465                label: field.label.clone(),
2466                label_span: field.label_span,
2467                value: canonical_expr_to_term(&field.value, translation, counter)?,
2468            })
2469        })
2470        .collect()
2471}
2472
2473/// An application spine: what is being applied, and the `Apply` nodes that apply it,
2474/// innermost first.
2475///
2476/// `f a b` is `Apply(Apply(f, a), b)` in the canonical AST, and one `Apply` node on its
2477/// own cannot say whether the call it is part of supplies everything `f` takes. This is
2478/// what turns the nesting back into a callee and a count. `applications[i]` supplies the
2479/// `i + 1`th argument, and the last of them is `expr` itself.
2480fn spine(expr: &canonical::Expression) -> (&canonical::Expression, Vec<&canonical::Expression>) {
2481    let mut applications = Vec::new();
2482    let mut callee = expr;
2483
2484    while let canonical::ExpressionKind::Apply(fun, _) = &callee.kind {
2485        applications.push(callee);
2486        callee = fun;
2487    }
2488
2489    applications.reverse();
2490
2491    (callee, applications)
2492}
2493
2494/// Translate a canonical pattern into a `TermPattern`. Returns `None` for a pattern the
2495/// term language does not model: a constructor that names no case of its declaration, or
2496/// a sub-pattern that is itself one of those.
2497///
2498/// The pattern keeps its own span, separate from the branch body's: a `case` branch
2499/// whose pattern does not match what is being matched on is about the pattern, and
2500/// the caret belongs there rather than under the expression in the `case … of` line.
2501fn translate_pattern(
2502    pattern: &canonical::Pattern,
2503    translation: &Translation,
2504    counter: &mut u32,
2505) -> Option<TermPattern> {
2506    let kind = match &pattern.kind {
2507        canonical::PatternKind::Anything => TermPatternKind::Anything,
2508        canonical::PatternKind::Variable(name) => {
2509            // The binding's actual type will be unified with the scrutinee type in annotate.
2510            TermPatternKind::Bind(name.as_str().to_string())
2511        }
2512        canonical::PatternKind::Int(value) => TermPatternKind::Literal {
2513            tpe: Type::Literal(TypeLiteral::Int),
2514            value: LiteralValue::Int(*value),
2515        },
2516        canonical::PatternKind::Char(value) => TermPatternKind::Literal {
2517            tpe: Type::Literal(TypeLiteral::Char),
2518            value: LiteralValue::Char(*value),
2519        },
2520        canonical::PatternKind::Float(value) => TermPatternKind::Literal {
2521            tpe: Type::Literal(TypeLiteral::Float),
2522            value: LiteralValue::Float(*value),
2523        },
2524        canonical::PatternKind::String(value) => TermPatternKind::Literal {
2525            tpe: Type::Literal(TypeLiteral::String),
2526            value: LiteralValue::String(value.clone()),
2527        },
2528        canonical::PatternKind::Unit => TermPatternKind::Unit,
2529        // `Basics`' own `True` and `False` are tested by value, as an `Int` or a
2530        // `Char` literal is, so a backend tests a `Bool` scrutinee by equality. The
2531        // type is the same one the constructor would have constrained the scrutinee
2532        // to. A module's own `type Bool = True | False` is not `Basics.Bool` and is
2533        // left alone.
2534        canonical::PatternKind::Constructor { ctor, args }
2535            if args.is_empty() && ctor.tpe == scalars::BOOL.qual_name() =>
2536        {
2537            let value = match ctor.name.as_str() {
2538                "True" => true,
2539                "False" => false,
2540                _ => return None,
2541            };
2542            TermPatternKind::Literal {
2543                tpe: bool_type(),
2544                value: LiteralValue::Bool(value),
2545            }
2546        }
2547        canonical::PatternKind::Constructor { ctor, args } => {
2548            // Look up the parent union to get its type variables. `ctor.tpe` names
2549            // the declaration the constructor builds, module included, and `unions`
2550            // is keyed the same way — so this finds the one declaration the
2551            // constructor belongs to, this module's or an imported one.
2552            let union_type = translation.unions.get(&ctor.tpe)?;
2553
2554            // Which case of that union this pattern matches. Unification needs only
2555            // the union; a decision tree and a WIT `variant` both need the case, and
2556            // the declaration is the only thing that can say where it sits.
2557            let index = union_type
2558                .variants
2559                .iter()
2560                .position(|variant| variant.name == ctor.name)?;
2561
2562            // Create fresh type vars for each ADT type parameter.
2563            let mut adt_var_map: HashMap<String, TypeVariable> = HashMap::new();
2564            for tv_name in &union_type.variables {
2565                *counter += 1;
2566                adt_var_map.insert(
2567                    tv_name.as_str().to_string(),
2568                    TypeVariable::flexible(*counter),
2569                );
2570            }
2571
2572            // Build the ADT result type args from the fresh vars.
2573            let adt_args: Vec<Type> = union_type
2574                .variables
2575                .iter()
2576                .map(|v| Type::Variable(adt_var_map[v.as_str()].clone()))
2577                .collect();
2578
2579            // Translate each constructor type parameter (reuses the same fresh vars).
2580            let param_types: Vec<Type> = ctor
2581                .type_parameters
2582                .iter()
2583                .filter_map(|t| canonical_type_to_typer_type(t, &mut adt_var_map, counter))
2584                .collect();
2585            if param_types.len() != ctor.type_parameters.len() {
2586                return None;
2587            }
2588
2589            // One sub-pattern per argument, so an argument's position is its place in
2590            // the list.
2591            let args = args
2592                .iter()
2593                .zip(param_types)
2594                .map(|(arg_pattern, param_type)| {
2595                    translate_sub_pattern(arg_pattern, param_type, translation, counter)
2596                })
2597                .collect::<Option<Vec<_>>>()?;
2598
2599            TermPatternKind::Constructor {
2600                ctor: Constructor {
2601                    union: ctor.tpe.clone(),
2602                    name: ctor.name.clone(),
2603                    index,
2604                    arity: ctor.type_parameters.len(),
2605                },
2606                adt_args,
2607                args,
2608            }
2609        }
2610        // Each element gets a fresh type, and the matched value has to be the tuple of
2611        // them. An element is translated as a constructor's argument is (see
2612        // `translate_sub_pattern`).
2613        canonical::PatternKind::Tuple(elements) => {
2614            let elements = elements
2615                .try_map(|element| {
2616                    *counter += 1;
2617                    let tpe = Type::Variable(TypeVariable::flexible(*counter));
2618                    translate_sub_pattern(element, tpe, translation, counter).ok_or(())
2619                })
2620                .ok()?;
2621
2622            TermPatternKind::Tuple { elements }
2623        }
2624        // A constructor that did not resolve: nothing says what type it builds or takes,
2625        // so each argument is at a fresh type, and translated as a resolved constructor's
2626        // argument is (see `translate_sub_pattern`).
2627        canonical::PatternKind::Hole(args) => {
2628            let args = args
2629                .iter()
2630                .map(|arg| {
2631                    *counter += 1;
2632                    let tpe = Type::Variable(TypeVariable::flexible(*counter));
2633                    translate_sub_pattern(arg, tpe, translation, counter)
2634                })
2635                .collect::<Option<Vec<_>>>()?;
2636
2637            TermPatternKind::Hole { args }
2638        }
2639        // Each entry's field gets a fresh type, and its pattern is translated as a
2640        // constructor's argument is (see `translate_sub_pattern`). Nothing is built here
2641        // for the record itself: the pattern names a subset of its fields, so its record
2642        // type is whatever the matched value turns out to be, and each entry is read
2643        // against it once the declaration's equations are solved (`FieldConstraint`).
2644        canonical::PatternKind::Record(entries) => {
2645            let fields = entries
2646                .iter()
2647                .map(|entry| {
2648                    *counter += 1;
2649                    let tpe = Type::Variable(TypeVariable::flexible(*counter));
2650                    Some(Field {
2651                        label: entry.label.clone(),
2652                        label_span: entry.label_span,
2653                        value: translate_sub_pattern(&entry.pattern, tpe, translation, counter)?,
2654                    })
2655                })
2656                .collect::<Option<Vec<_>>>()?;
2657
2658            TermPatternKind::Record { fields }
2659        }
2660    };
2661
2662    Some(TermPattern {
2663        span: pattern.span,
2664        kind,
2665    })
2666}
2667
2668/// A pattern written as a constructor's argument, a tuple's element or a record
2669/// pattern's entry, matched against a value of type `tpe`.
2670///
2671/// It is translated by [`translate_pattern`] like a pattern anywhere else, so any
2672/// pattern that translates at the top of a branch translates here too, at any depth, and
2673/// one that does not — a constructor of a union nobody declared, say — answers `None` here as it does there. A
2674/// refutable sub-pattern needs nothing of its own: `pattern_constraints` holds it to
2675/// `tpe` the way a branch's pattern is held to the scrutinee's type, and
2676/// `ir::decision_tree` tests it at its occurrence.
2677fn translate_sub_pattern(
2678    pattern: &canonical::Pattern,
2679    tpe: Type,
2680    translation: &Translation,
2681    counter: &mut u32,
2682) -> Option<SubPattern> {
2683    Some(SubPattern {
2684        tpe,
2685        pattern: translate_pattern(pattern, translation, counter)?,
2686    })
2687}
2688
2689/// A declaration's type annotation, and where it was written.
2690///
2691/// The span is the annotation's alone — `answer : Int`, not the declaration it
2692/// heads — because it is drawn as the secondary label of a mismatch in the body, and
2693/// a span covering the body too would underline the thing it is meant to contrast
2694/// with.
2695///
2696/// An instance's binding has no annotation of its own: the member's signature at the
2697/// instance's type stands in for one, and the head line of the instance for its span.
2698///
2699/// The variables of `tpe` are rigid ([`make_rigid`]) for a declaration's annotation, for an
2700/// instance's binding, head and member signature alike, and for a derivation's binding, whose
2701/// type is the chapter's role type over the derivation's answer type: the variables there
2702/// are the member signature's own.
2703struct Annotation {
2704    tpe: Type,
2705    span: NodeSpan,
2706    /// The reason of the equation the annotation's type is one side of.
2707    reason: Reason,
2708    /// What the annotation requires of its variables — the `=>` in front of it, or the
2709    /// context of the instance — each a class and the variable of `tpe` it is on. These
2710    /// are *given* inside the declaration.
2711    context: Vec<(QualName, TypeVariable)>,
2712    /// The name the source wrote for each variable of `tpe`, sorted by name: what a
2713    /// message about a constraint writes the variable by.
2714    names: Vec<(TypeVariable, Name)>,
2715    /// The variables of `tpe` that `context` cannot be on: the ones a class member's
2716    /// signature binds besides the class's own, when `tpe` is an instance binding's. Empty
2717    /// for an annotation.
2718    member_variables: Vec<TypeVariable>,
2719    /// What a constraint missing from `context` would have to be written in.
2720    written: Written,
2721}
2722
2723/// Convert a canonical Value into a (Term, optional annotation) pair.
2724/// The body is wrapped in nested Fun nodes for each parameter — see
2725/// [`wrap_with_patterns`].
2726/// Returns None if any part of the value cannot be translated, its annotation included:
2727/// a body checked without the annotation it was written with would be checked against
2728/// less than the source says, and pass where the annotation should have failed it. No
2729/// annotation fails to translate today — [`canonical_type_to_typer_type`] reads every
2730/// canonical type — so it is the body alone that can make this `None`; the annotation's
2731/// `?` is kept for the type form that would not.
2732///
2733/// The annotation's variables come back rigid ([`make_rigid`]), and its context is on them.
2734fn value_to_term_and_annotation(
2735    value: &canonical::Value,
2736    translation: &Translation,
2737    counter: &mut u32,
2738) -> Option<(Term, Option<Annotation>)> {
2739    match value {
2740        canonical::Value::Value { patterns, body, .. } => {
2741            let body_term = canonical_expr_to_term(body, translation, counter)?;
2742            let term = wrap_with_patterns(patterns.iter(), body_term, translation, counter)?;
2743            Some((term, None))
2744        }
2745        canonical::Value::TypedValue {
2746            patterns,
2747            body,
2748            tpe,
2749            context,
2750            annotation_span,
2751            ..
2752        } => {
2753            let body_term = canonical_expr_to_term(body, translation, counter)?;
2754            let pattern_iter = patterns.iter().map(|(p, _)| p);
2755            let term = wrap_with_patterns(pattern_iter, body_term, translation, counter)?;
2756            let mut var_map = HashMap::new();
2757            let tpe = canonical_type_to_typer_type(tpe, &mut var_map, counter)?;
2758            let tpe = make_rigid(tpe, &mut var_map, Binder::Annotation);
2759            let given = context
2760                .iter()
2761                .filter_map(|constraint| {
2762                    Some((
2763                        constraint.class.clone(),
2764                        var_map.get(constraint.variable.as_str())?.clone(),
2765                    ))
2766                })
2767                .collect();
2768            let mut names: Vec<(TypeVariable, Name)> = var_map
2769                .iter()
2770                .map(|(name, variable)| (variable.clone(), Name::new(name.clone())))
2771                .collect();
2772            names.sort_by(|left, right| left.1.cmp(&right.1));
2773
2774            let annotation = Annotation {
2775                tpe,
2776                span: *annotation_span,
2777                reason: Reason::Annotation,
2778                context: given,
2779                names,
2780                member_variables: Vec::new(),
2781                written: Written::Annotation,
2782            };
2783            Some((term, Some(annotation)))
2784        }
2785    }
2786}
2787
2788/// Wrap a body Term in nested Fun nodes for each parameter, outermost first.
2789///
2790/// A `Fun` binds one name, so a parameter written as a variable or `_` is bound as it
2791/// is. A parameter written as any other pattern is bound under the name
2792/// [`pattern_parameter`] gives its position, and matched by a single-branch
2793/// [`CaseForm::Parameter`] `Case` on that name: `first (x, _) = x` is translated as
2794/// `first $0 = case $0 of (x, _) -> x` would be. The pattern goes through
2795/// [`translate_pattern`], the same translation a `case` branch's gets, so a parameter
2796/// admits exactly the patterns a branch does. Returns `None` when it does not.
2797///
2798/// Every `Fun` is outside every `Case`. That keeps the first `arity` nodes of the term
2799/// the declaration's parameters and nothing else, which is what `ir::build` reads them
2800/// off by. The `Case`s nest in parameter order, the first outermost, so a name two
2801/// patterned parameters both bind is the later one's in the body — which is how
2802/// canonicalization resolved it. A pattern's names also shadow a same-named parameter
2803/// written as a variable, whichever comes first — and when the pattern comes first,
2804/// that is the opposite of canonicalization, which lets the later parameter win:
2805/// `f (x, _) x = x` reads the pattern's `x` here and the plain parameter's there. Both
2806/// are a name bound twice in one clause, which the language rejects and the compiler
2807/// does not yet (`LANG-18`).
2808///
2809/// Each `Fun` spans its parameter through the body it wraps, so a function whose
2810/// declared shape does not match its definition is underlined from the parameter
2811/// that starts it rather than across the annotation as well. A `Case` built here spans
2812/// its pattern alone: it is what the source wrote in place of a plain parameter.
2813fn wrap_with_patterns<'a>(
2814    patterns: impl Iterator<Item = &'a canonical::Pattern>,
2815    body: Term,
2816    translation: &Translation,
2817    counter: &mut u32,
2818) -> Option<Term> {
2819    let body_span = body.span;
2820    let mut params: Vec<(String, NodeSpan)> = vec![];
2821    let mut matched: Vec<(String, TermPattern)> = vec![];
2822
2823    for (position, pattern) in patterns.enumerate() {
2824        match &pattern.kind {
2825            canonical::PatternKind::Variable(name) => {
2826                params.push((name.as_str().to_string(), pattern.span))
2827            }
2828            canonical::PatternKind::Anything => params.push(("_".to_string(), pattern.span)),
2829            _ => {
2830                let name = pattern_parameter(position);
2831                let translated = translate_pattern(pattern, translation, counter)?;
2832                params.push((name.clone(), pattern.span));
2833                matched.push((name, translated));
2834            }
2835        }
2836    }
2837
2838    let body = matched
2839        .into_iter()
2840        .rev()
2841        .fold(body, |acc, (name, pattern)| {
2842            let span = pattern.span;
2843            Term {
2844                span,
2845                kind: TermKind::Case {
2846                    scrutinee: Box::new(Term {
2847                        span,
2848                        kind: TermKind::Identifier(Reference::local(name)),
2849                    }),
2850                    branches: vec![(pattern, Box::new(acc))],
2851                    form: CaseForm::Parameter,
2852                },
2853            }
2854        });
2855
2856    let term = params
2857        .into_iter()
2858        .rev()
2859        .fold(body, |acc, (param, span)| Term {
2860            span: span.merge(body_span),
2861            kind: TermKind::Fun {
2862                param,
2863                body: Box::new(acc),
2864            },
2865        });
2866
2867    Some(term)
2868}
2869
2870// The term language inference runs on is [`crate::ir`], and it is no longer
2871// only inference's. Every node carries the [`NodeSpan`] of the canonical node it was
2872// built from, so an error found down here can say where in the user's source it
2873// happened (`ERR-4`), and each carries what a backend reads off it — the kind of name a
2874// reference is, a call's saturation, a constructor's place in its declaration — because
2875// the translation below is the only place those are known. Inference reads none of
2876// them.
2877
2878mod annotate;
2879mod classes;
2880mod constraint;
2881mod unifier;
2882
2883pub(crate) use classes::{head_of, instance_head_type};
2884
2885/// A type variable: a placeholder `unify` may solve to a type, or a **rigid** one, which it
2886/// may not.
2887///
2888/// A *flexible* variable is the inference variable of an expression, and the variable of a
2889/// declared type a use instantiates. A *rigid* variable is one the declaration being
2890/// checked is universally quantified over: the variables its annotation wrote, or the
2891/// variables of an instance's head and of the member signature its bindings are held to
2892/// (`make_rigid` makes them). It stands for every type a caller may choose, so it is
2893/// equal to itself and to nothing else, and `unifier::unify` raises
2894/// [`ErrorKind::RigidVariable`] where a body would need it to be anything more specific.
2895///
2896/// A rigid variable is a flexible one's `id` with the name the source wrote it by, which is
2897/// what a message writes it as. The `id` is what tells two variables apart: two rigid
2898/// variables may be written alike, as an instance's head and the member signature its
2899/// binding is held to each write their own.
2900///
2901/// A rigid variable belongs to the declaration whose body is checked: the types of the term
2902/// that comes back hold it, and nothing the environment holds for another declaration does.
2903/// What the environment holds for a use, a `Scheme`, is over flexible variables, which each
2904/// use instantiates fresh.
2905// TODO Copy ?
2906#[derive(Clone, Hash, PartialEq, Eq)]
2907pub struct TypeVariable {
2908    id: u32,
2909    /// The name the source wrote this variable by and what it wrote it in, when it is rigid.
2910    rigid: Option<(Name, Binder)>,
2911}
2912
2913/// What a rigid variable was written in: the three kinds of declared type a body is held to.
2914#[derive(Debug, Clone, Copy, Hash, PartialEq, Eq)]
2915pub enum Binder {
2916    /// A declaration's annotation, or the answer type of a derivation's binding.
2917    Annotation,
2918    /// An instance's head.
2919    InstanceHead,
2920    /// The signature of a class member, for the variables it binds beyond the class's own:
2921    /// the signature an instance's binding is held to.
2922    MemberSignature,
2923}
2924
2925impl Binder {
2926    /// `of` this binder, as a message writes whose a variable is.
2927    fn of_phrase(self) -> &'static str {
2928        match self {
2929            Binder::Annotation => "the annotation",
2930            Binder::InstanceHead => "the instance head",
2931            Binder::MemberSignature => "the member's signature",
2932        }
2933    }
2934
2935    /// What a message calls this binder's variable when it says which of two alike it means.
2936    fn possessive(self) -> &'static str {
2937        match self {
2938            Binder::Annotation => "the annotation's",
2939            Binder::InstanceHead => "the instance head's",
2940            Binder::MemberSignature => "the member signature's",
2941        }
2942    }
2943}
2944
2945impl TypeVariable {
2946    /// The flexible variable numbered `id`.
2947    fn flexible(id: u32) -> TypeVariable {
2948        TypeVariable { id, rigid: None }
2949    }
2950
2951    /// This variable made rigid under `name`: same `id`, so it is the variable the
2952    /// annotation's type was translated with, now one `unify` will not solve.
2953    fn into_rigid(self, name: Name, binder: Binder) -> TypeVariable {
2954        TypeVariable {
2955            id: self.id,
2956            rigid: Some((name, binder)),
2957        }
2958    }
2959
2960    /// What this variable was written in, when it is rigid.
2961    fn binder(&self) -> Option<Binder> {
2962        self.rigid.as_ref().map(|(_, binder)| *binder)
2963    }
2964
2965    /// Whether `unify` may not solve this variable to another type.
2966    fn is_rigid(&self) -> bool {
2967        self.rigid.is_some()
2968    }
2969
2970    /// How a message writes this variable when no name has been given for it: the name the
2971    /// source wrote, for a rigid one, and `t3` for a flexible one, as [`Type`]'s
2972    /// `Display` does.
2973    fn spelling(&self) -> String {
2974        match &self.rigid {
2975            Some((name, _)) => name.to_string(),
2976            None => format!("t{}", self.id),
2977        }
2978    }
2979}
2980
2981impl std::fmt::Debug for TypeVariable {
2982    fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
2983        match &self.rigid {
2984            None => write!(f, "TypeVariable#{}", self.id),
2985            Some((name, _)) => write!(f, "TypeVariable#{}(rigid {})", self.id, name),
2986        }
2987    }
2988}
2989
2990/// The type of an [opaque scalar](../../docs/spec/types.md#scalar-types): a type
2991/// nothing in the language builds or inspects, whose values arrive as literals.
2992///
2993/// `Bool` is not one of them: it is a scalar *and* an ordinary union, so its
2994/// type is a [`Type::Adt`] like any other union's, built by this module's `bool_type`.
2995#[derive(Debug, Clone, Hash, PartialEq, Eq)]
2996pub enum TypeLiteral {
2997    Int,
2998    Char,
2999    Float,
3000    String,
3001}
3002
3003#[derive(Clone, Hash, PartialEq, Eq)]
3004pub enum Type {
3005    Literal(TypeLiteral),
3006    Variable(TypeVariable),
3007    Fun {
3008        param_tpe: Box<Type>,
3009        return_tpe: Box<Type>,
3010    },
3011    Tuple(Tuple<Type>),
3012    /// [The unit type](../../docs/spec/types.md#the-unit-type), `()`, whose one
3013    /// value is also written `()`.
3014    ///
3015    /// A variant of its own, the way [`Type::Tuple`] is, rather than a [`Type::Adt`]
3016    /// known by the qualified name of a declaration the way `Bool` is: nothing
3017    /// declares `()`, it is a form of type expression and never a name, so there is
3018    /// no declaration to name and no same-spelled type it has to be told apart from.
3019    /// See `canonical::Type::Unit`.
3020    Unit,
3021    /// A named algebraic data type, e.g. `Maybe Int` declared in `Maybe` →
3022    /// `Adt(Maybe.Maybe, [Literal(Int)])`.
3023    ///
3024    /// The name is the declaring package's and module's, in full, because that is the
3025    /// identity of the type: `Widget.Size` and `Gadget.Size` are two types and a value
3026    /// of one is never a value of the other, and so are the `Size.Size` of two
3027    /// packages. The unifier's equality on this name is the only thing keeping them
3028    /// apart, so narrowing it to the spelling — which is what the typer used to carry —
3029    /// made every same-named declaration one type (`BUG-35`).
3030    /// [`Display`](std::fmt::Display) still writes the unqualified half, since that is
3031    /// how a module's source spells its own types.
3032    Adt(QualName, Vec<Type>),
3033    /// A [record type](../../docs/spec/records.md#a-record-type-is-a-set-of-fields): each
3034    /// label, and the type of the field it names.
3035    ///
3036    /// A map, for the reason `canonical::Type::Record` is one: a record type is a set of
3037    /// fields, so `{ x : Int, y : Int }` and `{ y : Int, x : Int }` are one value here and
3038    /// nothing downstream can tell the two spellings apart. The map is ordered by label,
3039    /// which is the order [`Display`](std::fmt::Display) writes the fields in.
3040    ///
3041    /// # How two record types unify
3042    ///
3043    /// They unify when they carry **the same set of labels** and each label's two field
3044    /// types unify; see `unify_one_constraint`. There is no row variable, and nothing
3045    /// ever adds a field to a record type: [records are
3046    /// closed](../../docs/spec/records.md#records-are-closed), so a variable only ever
3047    /// stands for a whole type, a record type included. Two record types with different
3048    /// label sets are a plain [`ErrorKind::UnificationFailed`], and its diagnostic names
3049    /// the labels each side has that the other lacks (see [`Error`]'s `notes`).
3050    ///
3051    /// Every walk over a type — substitution, the occurs check, instantiation, the zonk,
3052    /// and both renderings — goes into each field's type as it goes into a tuple's
3053    /// elements, and nothing else about a record is special to any of them.
3054    ///
3055    /// What does *not* produce one is a use of a record: an access, an update or an
3056    /// accessor says of a type only that it has some label, and is read against a record
3057    /// type something else supplied — see `FieldConstraint`.
3058    Record(BTreeMap<Name, Type>),
3059}
3060
3061/// How the name of a [`Type::Adt`] is written out.
3062///
3063/// A type is normally quoted the way the source spells it, which for a union is its
3064/// bare name. That is ambiguous exactly when one message names two declarations that
3065/// share a spelling, and [`ErrorKind::message`] switches to the qualified form there.
3066#[derive(Debug, Clone, Copy)]
3067enum AdtNames<'a> {
3068    /// `Size`.
3069    Unqualified,
3070    /// `Widget.Size`, or `AcmeWidgets.Size.Size`: the union's module as the checked
3071    /// package spells it, then its own name — see [`Spellings`].
3072    Qualified(&'a Spellings),
3073}
3074
3075impl AdtNames<'_> {
3076    /// Whether the types a single message is about have to be written qualified for
3077    /// that message to distinguish the declarations it names.
3078    ///
3079    /// The question is not whether the *types* are spelled alike — `A.Size` against
3080    /// `Lib.Size A.Size` renders as `Size` against `Size Size`, which differs as
3081    /// text while still using one word for three declarations. It is whether any two
3082    /// of the unions named anywhere in those types are different declarations with
3083    /// the same bare name; if so every union in the sentence is qualified, since
3084    /// qualifying only the colliding pair would read as if the rest had no module.
3085    /// Two declarations may share their module's name too, when two packages each
3086    /// hold one, and they are still two: a [`QualName`] carries its package.
3087    fn collide<'t>(types: impl IntoIterator<Item = &'t Type>) -> bool {
3088        let mut names: Vec<&QualName> = Vec::new();
3089
3090        for tpe in types {
3091            tpe.collect_adt_names(&mut names);
3092        }
3093
3094        names.iter().enumerate().any(|(i, name)| {
3095            names[i + 1..]
3096                .iter()
3097                .any(|other| *other != *name && other.unqualified_name() == name.unqualified_name())
3098        })
3099    }
3100}
3101
3102/// How the package being checked spells each module in reach: the key `compile_package`
3103/// stores that module's [`Interface`] under in the map it hands [`type_check`], and the
3104/// module under check's own name.
3105///
3106/// A qualified message writes a union by this spelling rather than by its declaring
3107/// module's own name, because the two differ for a wrapped dependency — and they have to
3108/// differ in the message whenever two packages each hold a module of the same name.
3109/// `AcmeWidgets.Size.Size` against `Size.Size` tells the two unions apart, and is what
3110/// the checked package's own source writes; `Size.Size` against `Size.Size` would not,
3111/// and the package name — `acme-widgets` — is a spelling no Zelkova source contains.
3112#[derive(Debug, Clone, Default)]
3113struct Spellings(HashMap<ModuleName, Name>);
3114
3115impl Spellings {
3116    /// The spellings of every module `interfaces` holds, plus `module`'s own.
3117    ///
3118    /// A module reachable by two spellings is written by the first in alphabetical
3119    /// order, so the message does not change between runs.
3120    fn of(module: &Module, interfaces: &HashMap<Name, Interface>) -> Spellings {
3121        let mut spellings: HashMap<ModuleName, Name> = HashMap::new();
3122
3123        for (spelling, interface) in interfaces {
3124            spellings
3125                .entry(interface.module_name.clone())
3126                .and_modify(|kept| {
3127                    if spelling.as_str() < kept.as_str() {
3128                        *kept = spelling.clone();
3129                    }
3130                })
3131                .or_insert_with(|| spelling.clone());
3132        }
3133
3134        spellings.insert(module.name.clone(), module.name.name().clone());
3135
3136        Spellings(spellings)
3137    }
3138
3139    /// `name` as the checked package writes it: its module's spelling, then its own
3140    /// name. A module with no spelling here — one the checked package cannot import,
3141    /// whose union reached it through another module's signature — is written by its
3142    /// own name.
3143    fn spell(&self, name: &QualName) -> String {
3144        let module = ModuleName::new(name.package().clone(), name.module_name());
3145
3146        match self.0.get(&module) {
3147            Some(spelling) => format!("{}.{}", spelling, name.unqualified_name()),
3148            None => name.to_name().to_string(),
3149        }
3150    }
3151}
3152
3153/// A [`Type`] written with every union named by its module, as the checked package
3154/// spells it.
3155///
3156/// The counterpart of `Type`'s own [`Display`](std::fmt::Display), which writes the
3157/// unqualified half.
3158struct Qualified<'a>(&'a Type, &'a Spellings);
3159
3160impl std::fmt::Display for Qualified<'_> {
3161    fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
3162        self.0.write(f, AdtNames::Qualified(self.1), None)
3163    }
3164}
3165
3166impl std::fmt::Debug for Type {
3167    fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
3168        match self {
3169            Type::Literal(lit) => write!(f, "Lit({:?})", lit),
3170            Type::Variable(TypeVariable { id, rigid: None }) => write!(f, "Var(#{})", id),
3171            Type::Variable(TypeVariable {
3172                id,
3173                rigid: Some((name, _)),
3174            }) => write!(f, "Rigid({}#{})", name, id),
3175            Type::Fun {
3176                param_tpe,
3177                return_tpe,
3178            } => write!(f, "Fun({:?} -> {:?})", param_tpe, return_tpe),
3179            Type::Tuple(Tuple::Two(a, b)) => write!(f, "({:?}, {:?})", a, b),
3180            Type::Tuple(Tuple::Three(a, b, c)) => write!(f, "({:?}, {:?}, {:?})", a, b, c),
3181            Type::Unit => write!(f, "()"),
3182            Type::Adt(name, args) if args.is_empty() => write!(f, "{}", name.to_name()),
3183            Type::Adt(name, args) => write!(f, "{}({:?})", name.to_name(), args),
3184            Type::Record(fields) => {
3185                let fields: Vec<String> = fields
3186                    .iter()
3187                    .map(|(label, tpe)| format!("{}: {:?}", label.as_str(), tpe))
3188                    .collect();
3189                write!(f, "{{{}}}", fields.join(", "))
3190            }
3191        }
3192    }
3193}
3194
3195/// Writes a type the way the source would spell it, so diagnostics can quote it.
3196///
3197/// This is deliberately not `Debug`: `Debug` prints the typer's own vocabulary
3198/// (`Lit(Int)`, `Var(#3)`), which is what you want at a breakpoint and never what
3199/// you want in a message the user reads. Inference variables have no source syntax
3200/// at all, so they are written `t3` — Elm's convention for an unsolved variable.
3201impl std::fmt::Display for Type {
3202    fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
3203        self.write(f, AdtNames::Unqualified, None)
3204    }
3205}
3206
3207impl Type {
3208    /// The type as a message writes one that has variables of no source's naming: each
3209    /// variable is a letter, `a` to `z` and on, in the order it first appears, where
3210    /// [`Display`](std::fmt::Display) writes the inference variable (`t10122`) that no
3211    /// source mentions. A type with no variable reads the same either way.
3212    pub(crate) fn written_with_letters(&self) -> String {
3213        let names: VariableNames = free_variables_in_order(self)
3214            .into_iter()
3215            .enumerate()
3216            .map(|(position, variable)| (variable, classes::letter(position)))
3217            .collect();
3218        WithNames(self, &names).to_string()
3219    }
3220
3221    /// Every union named anywhere in this type, outermost first, appended to `out`.
3222    ///
3223    /// A union's arguments are types in their own right and may name unions of their
3224    /// own, so this recurses rather than reading the head alone. [`AdtNames::collide`]
3225    /// is what it exists for: deciding how to write a type means looking at every
3226    /// name the rendering will contain, not only the one at the top.
3227    fn collect_adt_names<'a>(&'a self, out: &mut Vec<&'a QualName>) {
3228        match self {
3229            Type::Literal(_) | Type::Variable(_) | Type::Unit => {}
3230            Type::Fun {
3231                param_tpe,
3232                return_tpe,
3233            } => {
3234                param_tpe.collect_adt_names(out);
3235                return_tpe.collect_adt_names(out);
3236            }
3237            Type::Tuple(Tuple::Two(a, b)) => {
3238                a.collect_adt_names(out);
3239                b.collect_adt_names(out);
3240            }
3241            Type::Tuple(Tuple::Three(a, b, c)) => {
3242                a.collect_adt_names(out);
3243                b.collect_adt_names(out);
3244                c.collect_adt_names(out);
3245            }
3246            Type::Adt(name, args) => {
3247                out.push(name);
3248                for arg in args {
3249                    arg.collect_adt_names(out);
3250                }
3251            }
3252            Type::Record(fields) => {
3253                for tpe in fields.values() {
3254                    tpe.collect_adt_names(out);
3255                }
3256            }
3257        }
3258    }
3259
3260    /// The body of every rendering: the same text each time, except for how a union is
3261    /// named and how a variable is. See [`AdtNames`], and [`Display`](std::fmt::Display)
3262    /// for why unions are normally written bare.
3263    ///
3264    /// A variable is `t3` unless `variables` has a name for it, which is how a message
3265    /// writes the variables of an annotation the way the source did.
3266    fn write(
3267        &self,
3268        f: &mut std::fmt::Formatter<'_>,
3269        names: AdtNames,
3270        variables: Option<&VariableNames>,
3271    ) -> std::fmt::Result {
3272        /// The same, wrapped in parentheses.
3273        fn parenthesised(
3274            tpe: &Type,
3275            f: &mut std::fmt::Formatter<'_>,
3276            names: AdtNames,
3277            variables: Option<&VariableNames>,
3278        ) -> std::fmt::Result {
3279            write!(f, "(")?;
3280            tpe.write(f, names, variables)?;
3281            write!(f, ")")
3282        }
3283
3284        match self {
3285            Type::Literal(TypeLiteral::Int) => write!(f, "Int"),
3286            Type::Literal(TypeLiteral::Char) => write!(f, "Char"),
3287            Type::Literal(TypeLiteral::Float) => write!(f, "Float"),
3288            Type::Literal(TypeLiteral::String) => write!(f, "String"),
3289            Type::Variable(variable) => match variables.and_then(|names| names.get(variable)) {
3290                Some(name) => write!(f, "{}", name),
3291                None => write!(f, "{}", variable.spelling()),
3292            },
3293            // The parameter of a function type is parenthesised when it is itself a
3294            // function, because `->` is right-associative: `(a -> b) -> c` and
3295            // `a -> b -> c` are different types.
3296            Type::Fun {
3297                param_tpe,
3298                return_tpe,
3299            } => {
3300                match **param_tpe {
3301                    Type::Fun { .. } => parenthesised(param_tpe, f, names, variables)?,
3302                    _ => param_tpe.write(f, names, variables)?,
3303                }
3304                write!(f, " -> ")?;
3305                return_tpe.write(f, names, variables)
3306            }
3307            Type::Tuple(Tuple::Two(a, b)) => {
3308                write!(f, "( ")?;
3309                a.write(f, names, variables)?;
3310                write!(f, ", ")?;
3311                b.write(f, names, variables)?;
3312                write!(f, " )")
3313            }
3314            Type::Tuple(Tuple::Three(a, b, c)) => {
3315                write!(f, "( ")?;
3316                a.write(f, names, variables)?;
3317                write!(f, ", ")?;
3318                b.write(f, names, variables)?;
3319                write!(f, ", ")?;
3320                c.write(f, names, variables)?;
3321                write!(f, " )")
3322            }
3323            Type::Unit => write!(f, "()"),
3324            Type::Adt(name, args) => {
3325                match names {
3326                    AdtNames::Unqualified => write!(f, "{}", name.unqualified_name())?,
3327                    AdtNames::Qualified(spellings) => write!(f, "{}", spellings.spell(name))?,
3328                }
3329                for arg in args {
3330                    // Same reason as above: an argument that is itself applied or a
3331                    // function needs parentheses to stay the same type when re-read.
3332                    write!(f, " ")?;
3333                    match arg {
3334                        Type::Adt(_, inner) if !inner.is_empty() => {
3335                            parenthesised(arg, f, names, variables)?
3336                        }
3337                        Type::Fun { .. } => parenthesised(arg, f, names, variables)?,
3338                        _ => arg.write(f, names, variables)?,
3339                    }
3340                }
3341                Ok(())
3342            }
3343            // The spelling [Records](../../docs/spec/records.md#the-type) uses, the
3344            // fields in label order. The braces delimit it, so no position needs it
3345            // parenthesised, and a field's type is written as it is anywhere else.
3346            Type::Record(fields) => {
3347                write!(f, "{{ ")?;
3348                for (position, (label, tpe)) in fields.iter().enumerate() {
3349                    if position > 0 {
3350                        write!(f, ", ")?;
3351                    }
3352                    write!(f, "{} : ", label.as_str())?;
3353                    tpe.write(f, names, variables)?;
3354                }
3355                write!(f, " }}")
3356            }
3357        }
3358    }
3359}
3360
3361/// Two types that have to match, and why.
3362///
3363/// # What the two sides mean
3364///
3365/// Unification treats them symmetrically; the order is a rendering convention, and
3366/// the only thing that reads it is the headline — *cannot match `left` with `right`*.
3367/// `collect` therefore writes the declared or expected side first where the source
3368/// has one (an annotation's type, a pattern's type) and the inferred side second, so
3369/// the sentence comes out in the order a reader expects.
3370///
3371/// What the sides are emphatically *not* is a way to tell which type belongs to the
3372/// text at `origin.span`. By the time a constraint fails, `unify` has substituted
3373/// other constraints' solutions into both sides, and may have decomposed it into a
3374/// component of the types the source mentioned. That is why the labels name the
3375/// [`Reason`] and leave the types to the headline — see [`Reason::describes`].
3376///
3377/// # Why these are held in a `Vec` and not a `HashSet`
3378///
3379/// They used to be a `HashSet<Constraint>`, back when a constraint was a bare pair of
3380/// types. An origin makes that collection wrong twice over. Deduplication now
3381/// discards *provenance*: two constraints with equal types but different origins are
3382/// one entry, and which origin survives is whichever was inserted first. And the
3383/// order a `HashSet` yields is unspecified, so which constraint `unify` reaches first
3384/// — and therefore which one is reported when several are unsatisfiable — would vary
3385/// between runs of the same compiler on the same file.
3386///
3387/// A `Vec` fixes both, and buys a third thing: source order. The annotation is
3388/// pushed first, so its type is substituted into the body's constraints before they
3389/// are solved, which is what lets a mismatch deep in the body say that `Int` came
3390/// from the annotation. The cost is that duplicate constraints are no longer
3391/// collapsed, which is a few more `unify` steps on terms that repeat a type.
3392#[derive(Debug, Clone, PartialEq)]
3393struct Constraint {
3394    left: Type,
3395    right: Type,
3396    origin: Origin,
3397}
3398
3399impl Constraint {
3400    fn new(left: Type, right: Type, reason: Reason, span: NodeSpan) -> Constraint {
3401        Constraint {
3402            left,
3403            right,
3404            origin: Origin::new(reason, span),
3405        }
3406    }
3407
3408    /// A constraint between two components of this one — the parameters of two
3409    /// function types being matched, say — which is about the same source text and
3410    /// was required for the same reason.
3411    ///
3412    /// The origin is inherited whole, side provenance included: if a substitution
3413    /// rewrote the left type, it rewrote whatever the left type decomposes into. That
3414    /// is an over-approximation — a substitution that reached only the return half of
3415    /// an arrow is credited with the parameter half too — but it errs towards naming
3416    /// a constraint that did carry a type in, which is the direction that keeps a
3417    /// caret on the source rather than on the compiler's working.
3418    fn component(&self, left: Type, right: Type) -> Constraint {
3419        Constraint {
3420            left,
3421            right,
3422            origin: self.origin.clone(),
3423        }
3424    }
3425}
3426
3427/// Which use of a record wrote a `FieldConstraint`. It decides what the constraint's
3428/// errors say and which text their carets are under; nothing about how the constraint
3429/// is solved depends on it.
3430#[derive(Debug, Clone, Copy, PartialEq, Eq)]
3431pub enum RecordUse {
3432    /// `record.label`.
3433    Access,
3434    /// `.label`, applied or not.
3435    Accessor,
3436    /// One field of `{ record | label = value }`.
3437    Update,
3438    /// One entry of a record pattern, `{ label = pattern }` or `{ label }`.
3439    Pattern,
3440}
3441
3442/// What could supply the record type an [`ErrorKind::RecordTypeUnknown`] is missing —
3443/// which is what its note tells the reader to do about it. `unifier::unknown` decides it.
3444///
3445/// "Part of the declaration's type" means a variable of the declaration's solved type
3446/// — a parameter's, the result's, or inside either — or the field type of another use
3447/// whose record type is one: an annotation, unified with that type, would solve the
3448/// variable, and reading the use would solve the next.
3449#[derive(Debug, Clone, Copy, PartialEq, Eq)]
3450pub enum Supplier {
3451    /// The declaration has no annotation, and the record type is part of its type: an
3452    /// annotation writing a record type there would supply it.
3453    Annotation,
3454    /// The record type is part of the declaration's type, and the declaration's
3455    /// annotation writes a type variable there — `f : a -> Int` with body `r.x` — or
3456    /// around it.
3457    AnnotationVariable,
3458    /// The record type is not part of the declaration's type — `.x` passed where any
3459    /// value is taken, as in `first n .x` — so no annotation on the declaration could
3460    /// supply it, and only its body can.
3461    Body,
3462}
3463
3464/// A type said to be a record holding `label`, with that field at `field`: what a field
3465/// access, an update, an accessor and each entry of a record pattern say about the record
3466/// they use.
3467///
3468/// # Why it is not a [`Constraint`]
3469///
3470/// `person.name` says of `person`'s type only that it has a `name`. That is not an
3471/// equation between two types this unifier can write: a record type names every field it
3472/// has ([records are closed](../../docs/spec/records.md#records-are-closed)), and there is
3473/// no row variable to stand for the fields `person.name` does not mention. Solving it
3474/// would mean inventing a record type out of the labels the declaration happens to touch,
3475/// which is exactly what [the language rules
3476/// out](../../docs/spec/records.md#a-use-does-not-decide-a-records-type): `nameOf person =
3477/// person.name` would take a record with one field. So a field constraint is never an
3478/// equation while its record type is unknown, and **nothing here ever solves a variable
3479/// standing for a record type**. The type has to come from somewhere else in the
3480/// declaration — its annotation, a record expression, a function of known type, a
3481/// constructor's argument — and the constraint only reads it.
3482///
3483/// # When it is read
3484///
3485/// After [`unifier::unify`] has solved every ordinary constraint of the declaration, by
3486/// `unifier::read_fields`. What supplies the record type may be written after the form
3487/// as well as before it, so a field constraint cannot be decided at the point
3488/// `constraint::collect` meets it; with the whole declaration solved, it can. Then, with
3489/// the substitution applied to `record`:
3490///
3491/// - **A record type holding `label`**: the constraint becomes the ordinary equation
3492///   between that field's type and `field`, solved at once and merged into the
3493///   substitution. A mismatch there is an [`ErrorKind::UnificationFailed`] with the
3494///   caret at `field_span` and the constraint's own `reason`.
3495/// - **A record type without it**: [`ErrorKind::MissingField`], at `label_span`. For an
3496///   update that is the update that would add a field.
3497/// - **Another type that is not a variable**: [`ErrorKind::NotARecord`], at
3498///   `label_span`. Each of these two carries what brought the record type in — the
3499///   probe's origin's cause for its left side — for a secondary label, as a mismatch's
3500///   explanation is.
3501/// - **Still a variable**: not decided yet. Reading another field constraint may solve
3502///   it: in `r.a.b` the record type of `.b` is the field type `.a` reads, and in `(.a
3503///   r).b` it is the accessor's result. So the constraints are read in passes, in the
3504///   order they were collected — which is the order their labels were written — each
3505///   pass seeing what the ones before it solved. A pass that decides none of the
3506///   constraints left is the end: nothing will ever supply their record types, and one
3507///   of them is [`ErrorKind::RecordTypeUnknown`], with the caret on the whole form —
3508///   unless a name that did not resolve, a hole, explains every one of them, its own
3509///   error standing already. `unifier::unknown` says which one and when a hole explains
3510///   it. Every pass decides at least one constraint or is the last, so the passes stop.
3511///
3512/// A record type only becomes *more* known as the passes go, never less, so whether a
3513/// declaration's field constraints are all satisfied does not depend on the order they
3514/// are read in. Which of several unknown ones is reported does not depend on it either
3515/// as long as one is the root the others wait on — `r.a` in an unannotated `r.a.b` or
3516/// `.b r.a` — and otherwise the order picks it, the same on every run. Only that one is
3517/// reported, as only a declaration's first failed equation is.
3518///
3519/// # Why there is nothing to generalise past
3520///
3521/// A declaration is put in the environment other declarations are checked against by
3522/// its annotation alone, and one with no annotation is not put there at all
3523/// ([`Solved::UnboundName`]). So a field constraint is always read inside the one
3524/// declaration that wrote it, and a use of that declaration from another one never
3525/// supplies its record type — which is the rule as
3526/// [Records](../../docs/spec/records.md#a-use-does-not-decide-a-records-type) states it.
3527/// A type variable an annotation writes, `get : { x : a } -> a`, is a variable inside a
3528/// record type and not a record type's variable, so `r.x` reads it; one written for the
3529/// record itself, `f : a -> Int` with body `r.x`, supplies no record type and is
3530/// [`ErrorKind::RecordTypeUnknown`].
3531///
3532/// That rests on there being no generalisation step. One that generalised a type still
3533/// carrying a waiting field constraint — a `let`-bound `get r = r.x` used as `get { x =
3534/// 1 }`, once [`LANG-33`](../../docs/tickets/lang-33.md) brings `let` — would copy the
3535/// constraint's variable at each use, and the constraint, waiting on the original, would
3536/// never be decided: it would fail safe, as a `RecordTypeUnknown`, but not by the rule.
3537/// So a generalisation step must read the field constraints first, or refuse to
3538/// generalise over a variable one of them is still waiting on.
3539///
3540/// # A record pattern
3541///
3542/// A record pattern names a subset of a record's fields and says of the type it is matched
3543/// against what an accessor says of its argument's, once per entry: it is the fourth
3544/// [`RecordUse`], one field constraint per entry, whose `record` is the type the pattern
3545/// is matched against — a `case`'s scrutinee, a parameter's, or the type of the position
3546/// it is written in inside another pattern — and whose `field` is the entry's own type,
3547/// the one its sub-pattern is held to and a name it binds is bound at. `form_span` is the
3548/// whole pattern, `label_span` the entry's label and `field_span` the entry's own pattern,
3549/// so a mismatch between that pattern and the field's declared type is blamed on the
3550/// sub-pattern. `constraint::pattern_constraints` writes them in the order the labels were
3551/// written at any depth: each entry just before the entries of a record pattern nested in
3552/// it, and those before the next entry, so `{ a = { b }, d }` gives `a`, `b`, `d`. The
3553/// field types of a pattern nested in an entry, `{ centre = { x } }`, are therefore read
3554/// in turn as `r.a.b`'s are.
3555///
3556/// That is the mechanism unchanged, but not quite nothing more than a variant:
3557/// `constraint::pattern_constraints`, which `constraint::collect` reaches through `walk`,
3558/// pushes onto the field list as well as onto the equations, the equation a decided entry
3559/// becomes carries a [`Reason`] of its own — one of three, by whether the entry's pattern
3560/// is a name, binds none or binds some, since that decides what a failure of it can mean
3561/// and so what its note says — and the argument types of a constructor pattern that did
3562/// not resolve count as holes, since that constructor's real type is what would have
3563/// supplied a record pattern written as one of its arguments.
3564///
3565/// The read comes after every equation, the branch body's included, so a name a record
3566/// pattern binds is solved by the body's use of it before the entry is read. A body that
3567/// uses `name` at another type than its field's is therefore reported at the entry, as a
3568/// mismatch of the field's type with the use's, and not at the body, as it would be under
3569/// a tuple pattern, whose equation comes first ([`ERR-20`](../../docs/tickets/err-20.md)).
3570/// Only the note, [`Reason::RecordPatternBinding`]'s, says that a use is what failed.
3571///
3572/// # What else is read late
3573///
3574/// A class obligation is the other kind of constraint the solver can only answer once
3575/// unification has run: a third list beside this one in `constraint::Constraints`, read
3576/// by `classes::discharge` after `unifier::read_fields` in `infer_annotated` — after,
3577/// because reading a field can solve the variable an instance is looked up by. Reading an
3578/// obligation adds nothing to the substitution: an instance's context is more obligations
3579/// and never an equation, so no obligation can decide a field constraint, and the order of
3580/// the two reads has one direction only.
3581#[derive(Debug, Clone)]
3582struct FieldConstraint {
3583    /// The type said to be a record. Usually still a variable when collected.
3584    record: Type,
3585    label: Name,
3586    /// The type the field is used at: the access's own type, an update's new value's, an
3587    /// accessor's result, or a record pattern's entry's.
3588    field: Type,
3589    form: RecordUse,
3590    /// The reason the equation this constraint becomes carries, once its record type is
3591    /// known: [`Reason::Access`], [`Reason::Accessor`] or [`Reason::UpdateField`] for the
3592    /// first three forms, and for a record pattern's entry one of the three record
3593    /// pattern reasons, chosen by what the entry's own pattern binds.
3594    reason: Reason,
3595    /// The whole form — the caret of [`ErrorKind::RecordTypeUnknown`].
3596    form_span: NodeSpan,
3597    /// The label for an access, an update and a record pattern's entry, and the whole
3598    /// accessor for an accessor — the caret of [`ErrorKind::MissingField`] and
3599    /// [`ErrorKind::NotARecord`].
3600    label_span: NodeSpan,
3601    /// The text whose type is `field` — the access, the new value, the accessor, the
3602    /// entry's own pattern — and the caret of a mismatch between it and the field's
3603    /// declared type.
3604    field_span: NodeSpan,
3605}
3606
3607impl FieldConstraint {
3608    /// This constraint read against everything solved so far: the equation it has
3609    /// become, `None` while its record type is still a variable, or the error it is.
3610    ///
3611    /// The equation is written declared-first, as `Constraint` asks: the field's type in
3612    /// the record, then the type it is used at. Its origin is the one
3613    /// [`Substitution::apply`] gives a constraint between `record` and `field`, so the
3614    /// declared side is explained by whatever brought the record type in — the
3615    /// annotation, typically — and a mismatch can say so.
3616    fn read(&self, substitution: &Substitution) -> Result<Option<Constraint>, ErrorKind> {
3617        let probe = substitution.apply(&Constraint::new(
3618            self.record.clone(),
3619            self.field.clone(),
3620            self.reason,
3621            self.field_span,
3622        ));
3623
3624        match &probe.left {
3625            Type::Variable(_) => Ok(None),
3626            Type::Record(fields) => match fields.get(&self.label) {
3627                Some(declared) => Ok(Some(Constraint {
3628                    left: declared.clone(),
3629                    right: probe.right,
3630                    origin: probe.origin,
3631                })),
3632                None => Err(ErrorKind::MissingField {
3633                    record: Box::new(probe.left.clone()),
3634                    label: self.label.clone(),
3635                    form: self.form,
3636                    span: self.label_span,
3637                    because: probe.origin.left_from,
3638                }),
3639            },
3640            other => Err(ErrorKind::NotARecord {
3641                tpe: Box::new(other.clone()),
3642                label: self.label.clone(),
3643                form: self.form,
3644                span: self.label_span,
3645                because: probe.origin.left_from,
3646            }),
3647        }
3648    }
3649
3650    /// The error this constraint is when nothing ever supplied its record type.
3651    fn unknown(&self, supplier: Supplier) -> ErrorKind {
3652        ErrorKind::RecordTypeUnknown {
3653            label: self.label.clone(),
3654            form: self.form,
3655            span: self.form_span,
3656            supplier,
3657        }
3658    }
3659}
3660
3661/// What one type variable was solved to, and where that type came from.
3662///
3663/// The cause is not used by inference at all. It is carried so that when this
3664/// solution is substituted into another constraint and *that* constraint then fails,
3665/// the failure can say where the type it failed against came from — see
3666/// [`Origin::left_from`].
3667///
3668/// It is a [`Cause`] and not an `Origin` because the question it answers is already
3669/// settled: [`Origin::cause_of`] resolved, at the moment the variable was solved,
3670/// whether the solving constraint introduced this type or was handed it. Nothing
3671/// downstream has to walk anything.
3672// No `Eq`: a `Cause` holds a `NodeSpan`, whose `PartialEq` is deliberately blind
3673// (see its documentation), so equality here is a claim about the types and the
3674// reasons, not about the positions.
3675#[derive(Debug, PartialEq, Clone)]
3676struct Solution {
3677    tpe: Type,
3678    cause: Cause,
3679}
3680
3681#[derive(Debug, PartialEq)]
3682struct Substitution {
3683    solutions: HashMap<TypeVariable, Solution>,
3684}
3685
3686impl Substitution {
3687    // constructors
3688
3689    fn empty() -> Substitution {
3690        Substitution {
3691            solutions: HashMap::new(),
3692        }
3693    }
3694
3695    fn one(tvar: TypeVariable, tpe: Type, cause: Cause) -> Substitution {
3696        let mut sub = Substitution::empty();
3697
3698        sub.solutions.insert(tvar, Solution { tpe, cause });
3699
3700        sub
3701    }
3702
3703    // methods
3704
3705    /// Rewrite a constraint with everything solved so far, recording for each side
3706    /// which solution first reached it.
3707    ///
3708    /// The two sides are tracked apart, because that is what tells a relayed type
3709    /// from an introduced one later on — see [`Origin::cause_of`]. A solution that
3710    /// rewrites only the right side has said nothing about the left, and treating it
3711    /// as though it had is what made a type error blame an annotation that was not
3712    /// load-bearing.
3713    ///
3714    /// The solutions are visited in type-variable order rather than in `HashMap`
3715    /// order: "first" has to mean the same thing on every run, or the secondary label
3716    /// of a diagnostic would move between compilations of an unchanged file. Ids are
3717    /// handed out as inference walks the term, so that order is roughly the order the
3718    /// user wrote things in.
3719    fn apply(&self, c: &Constraint) -> Constraint {
3720        let mut origin = c.origin.clone();
3721
3722        let mut solutions: Vec<_> = self.solutions.iter().collect();
3723        solutions.sort_by_key(|(tvar, _)| tvar.id);
3724
3725        for (tvar, solution) in solutions {
3726            // A solution that does not mention a variable a side uses rewrites
3727            // nothing there, and explains nothing about it either.
3728            if occurs(tvar, &c.left) {
3729                origin.rewritten(Side::Left, solution.cause);
3730            }
3731            if occurs(tvar, &c.right) {
3732                origin.rewritten(Side::Right, solution.cause);
3733            }
3734        }
3735
3736        Constraint {
3737            left: self.apply_type(&c.left),
3738            right: self.apply_type(&c.right),
3739            origin,
3740        }
3741    }
3742
3743    fn apply_type(&self, tpe: &Type) -> Type {
3744        self.solutions
3745            .iter()
3746            .fold(tpe.clone(), |tpe, (tvar, solution)| {
3747                Substitution::substitute(tpe, tvar, &solution.tpe)
3748            })
3749    }
3750
3751    /// Rewrite **every** type in a typed term with everything solved — the *zonk*.
3752    ///
3753    /// `annotate` gives each node a fresh inference variable and unification solves
3754    /// those variables somewhere else entirely, so until this runs a node's `tpe` is a
3755    /// `t17` that means nothing on its own. Applying the substitution to the root's
3756    /// type alone is enough to answer "what type is this declaration", which is all
3757    /// inference ever needed; it leaves every node below still holding a variable,
3758    /// which is not enough to generate code from
3759    /// ([`DEC-18` decision 1](../../docs/decisions/dec-18.md)).
3760    ///
3761    /// The types a pattern carries are rewritten too: a constructor pattern's
3762    /// arguments and the bindings it introduces are the types the branch body's
3763    /// variables were bound at.
3764    fn apply_term(&self, term: TypedTerm) -> TypedTerm {
3765        let kind = match term.kind {
3766            kind @ (TypedTermKind::Int(_)
3767            | TypedTermKind::Char(_)
3768            | TypedTermKind::String(_)
3769            | TypedTermKind::Float(_)
3770            | TypedTermKind::Unit
3771            | TypedTermKind::Hole) => kind,
3772            TypedTermKind::Identifier { reference, context } => TypedTermKind::Identifier {
3773                reference,
3774                context: self.apply_predicates(context),
3775            },
3776            TypedTermKind::Fun { param, body } => TypedTermKind::Fun {
3777                param: self.apply_binder(param),
3778                body: Box::new(self.apply_term(*body)),
3779            },
3780            TypedTermKind::Apply {
3781                fun,
3782                arg,
3783                saturation,
3784            } => TypedTermKind::Apply {
3785                fun: Box::new(self.apply_term(*fun)),
3786                arg: Box::new(self.apply_term(*arg)),
3787                saturation,
3788            },
3789            TypedTermKind::If {
3790                cond,
3791                true_branch,
3792                false_branch,
3793            } => TypedTermKind::If {
3794                cond: Box::new(self.apply_term(*cond)),
3795                true_branch: Box::new(self.apply_term(*true_branch)),
3796                false_branch: Box::new(self.apply_term(*false_branch)),
3797            },
3798            TypedTermKind::Let {
3799                binding,
3800                value,
3801                body,
3802            } => TypedTermKind::Let {
3803                binding: self.apply_binder(binding),
3804                value: Box::new(self.apply_term(*value)),
3805                body: Box::new(self.apply_term(*body)),
3806            },
3807            TypedTermKind::Tuple(Tuple::Two(a, b)) => {
3808                TypedTermKind::Tuple(Tuple::two(self.apply_term(*a), self.apply_term(*b)))
3809            }
3810            TypedTermKind::Tuple(Tuple::Three(a, b, c)) => TypedTermKind::Tuple(Tuple::three(
3811                self.apply_term(*a),
3812                self.apply_term(*b),
3813                self.apply_term(*c),
3814            )),
3815            TypedTermKind::Case {
3816                scrutinee,
3817                branches,
3818                form,
3819            } => TypedTermKind::Case {
3820                scrutinee: Box::new(self.apply_term(*scrutinee)),
3821                branches: branches
3822                    .into_iter()
3823                    .map(|(pattern, body)| {
3824                        (
3825                            self.apply_pattern(pattern),
3826                            Box::new(self.apply_term(*body)),
3827                        )
3828                    })
3829                    .collect(),
3830                form,
3831            },
3832            TypedTermKind::Record(fields) => TypedTermKind::Record(self.apply_fields(fields)),
3833            TypedTermKind::Update { record, fields } => TypedTermKind::Update {
3834                record: Box::new(self.apply_term(*record)),
3835                fields: self.apply_fields(fields),
3836            },
3837            TypedTermKind::Access {
3838                record,
3839                label,
3840                label_span,
3841            } => TypedTermKind::Access {
3842                record: Box::new(self.apply_term(*record)),
3843                label,
3844                label_span,
3845            },
3846            kind @ TypedTermKind::Accessor { .. } => kind,
3847        };
3848
3849        TypedTerm {
3850            span: term.span,
3851            tpe: self.apply_type(&term.tpe),
3852            kind,
3853        }
3854    }
3855
3856    /// Rewrite the type of each predicate: the context of a use, or a declaration's own,
3857    /// as it stands once everything is solved.
3858    fn apply_predicates(&self, predicates: Vec<Predicate>) -> Vec<Predicate> {
3859        predicates
3860            .into_iter()
3861            .map(|predicate| Predicate {
3862                class: predicate.class,
3863                tpe: self.apply_type(&predicate.tpe),
3864            })
3865            .collect()
3866    }
3867
3868    fn apply_fields(&self, fields: Vec<Field<TypedTerm>>) -> Vec<Field<TypedTerm>> {
3869        fields
3870            .into_iter()
3871            .map(|field| Field {
3872                label: field.label,
3873                label_span: field.label_span,
3874                value: self.apply_term(field.value),
3875            })
3876            .collect()
3877    }
3878
3879    fn apply_binder(&self, binder: TypeBinder) -> TypeBinder {
3880        TypeBinder {
3881            tpe: self.apply_type(&binder.tpe),
3882            name: binder.name,
3883        }
3884    }
3885
3886    fn apply_pattern(&self, pattern: TermPattern) -> TermPattern {
3887        let kind = match pattern.kind {
3888            kind @ (TermPatternKind::Anything
3889            | TermPatternKind::Bind(_)
3890            | TermPatternKind::Unit) => kind,
3891            TermPatternKind::Literal { tpe, value } => TermPatternKind::Literal {
3892                tpe: self.apply_type(&tpe),
3893                value,
3894            },
3895            TermPatternKind::Constructor {
3896                ctor,
3897                adt_args,
3898                args,
3899            } => TermPatternKind::Constructor {
3900                ctor,
3901                adt_args: adt_args.iter().map(|a| self.apply_type(a)).collect(),
3902                args: args
3903                    .into_iter()
3904                    .map(|arg| self.apply_sub_pattern(arg))
3905                    .collect(),
3906            },
3907            TermPatternKind::Tuple { elements } => TermPatternKind::Tuple {
3908                elements: elements.map(|element| self.apply_sub_pattern(element.clone())),
3909            },
3910            TermPatternKind::Hole { args } => TermPatternKind::Hole {
3911                args: args
3912                    .into_iter()
3913                    .map(|arg| self.apply_sub_pattern(arg))
3914                    .collect(),
3915            },
3916            TermPatternKind::Record { fields } => TermPatternKind::Record {
3917                fields: fields
3918                    .into_iter()
3919                    .map(|field| Field {
3920                        label: field.label,
3921                        label_span: field.label_span,
3922                        value: self.apply_sub_pattern(field.value),
3923                    })
3924                    .collect(),
3925            },
3926        };
3927
3928        TermPattern {
3929            span: pattern.span,
3930            kind,
3931        }
3932    }
3933
3934    fn apply_sub_pattern(&self, sub: SubPattern) -> SubPattern {
3935        SubPattern {
3936            tpe: self.apply_type(&sub.tpe),
3937            pattern: self.apply_pattern(sub.pattern),
3938        }
3939    }
3940
3941    fn substitute(tpe: Type, tvar: &TypeVariable, replacement: &Type) -> Type {
3942        match tpe {
3943            Type::Literal(_) | Type::Unit => tpe,
3944            Type::Fun {
3945                param_tpe,
3946                return_tpe,
3947            } => Type::Fun {
3948                param_tpe: Box::new(Substitution::substitute(*param_tpe, tvar, replacement)),
3949                return_tpe: Box::new(Substitution::substitute(*return_tpe, tvar, replacement)),
3950            },
3951            Type::Tuple(Tuple::Two(a, b)) => Type::Tuple(Tuple::two(
3952                Substitution::substitute(*a, tvar, replacement),
3953                Substitution::substitute(*b, tvar, replacement),
3954            )),
3955            Type::Tuple(Tuple::Three(a, b, c)) => Type::Tuple(Tuple::three(
3956                Substitution::substitute(*a, tvar, replacement),
3957                Substitution::substitute(*b, tvar, replacement),
3958                Substitution::substitute(*c, tvar, replacement),
3959            )),
3960            Type::Adt(name, args) => Type::Adt(
3961                name,
3962                args.into_iter()
3963                    .map(|a| Substitution::substitute(a, tvar, replacement))
3964                    .collect(),
3965            ),
3966            Type::Record(fields) => Type::Record(
3967                fields
3968                    .into_iter()
3969                    .map(|(label, tpe)| (label, Substitution::substitute(tpe, tvar, replacement)))
3970                    .collect(),
3971            ),
3972            Type::Variable(tvar2) if tvar == &tvar2 => replacement.clone(),
3973            tpe @ Type::Variable(_) => tpe,
3974        }
3975    }
3976
3977    fn merge(&self, other: Substitution) -> Substitution {
3978        // This merge means we should try sub_tail first, and then sub_head
3979        // Merging other in self means we apply `other` substitution to `self` solutions
3980        // When merging, we want `other` solutions to take precedences over `self` solutions
3981
3982        let self_solutions = self.solutions.iter().map(|(k, v)| {
3983            (
3984                k.clone(),
3985                Solution {
3986                    tpe: other.apply_type(&v.tpe),
3987                    // The cause says where this variable's type came from, which
3988                    // rewriting the type does not change.
3989                    cause: v.cause,
3990                },
3991            )
3992        });
3993
3994        let mut sub = Substitution::empty();
3995
3996        sub.solutions.extend(self_solutions);
3997        sub.solutions.extend(other.solutions);
3998
3999        sub
4000    }
4001}
4002
4003/// Does `tvar` appear anywhere inside `tpe`?
4004///
4005/// Two callers, for two different reasons: `unify_variable` uses it as the occurs
4006/// check that keeps it from building an infinite type, and `Substitution::apply` uses
4007/// it to tell whether a solution actually rewrites a given constraint — which is what
4008/// decides whether that solution explains one of the constraint's types.
4009fn occurs(tvar: &TypeVariable, tpe: &Type) -> bool {
4010    match tpe {
4011        Type::Fun {
4012            param_tpe,
4013            return_tpe,
4014        } => occurs(tvar, param_tpe) || occurs(tvar, return_tpe),
4015        Type::Tuple(tuple) => tuple.iter().any(|t| occurs(tvar, t)),
4016        Type::Adt(_, args) => args.iter().any(|a| occurs(tvar, a)),
4017        Type::Record(fields) => fields.values().any(|t| occurs(tvar, t)),
4018        Type::Variable(tvar2) => tvar == tvar2,
4019        _ => false,
4020    }
4021}
4022
4023/// Every variable of `tpe`, each once, in the order it first appears.
4024fn free_variables_in_order(tpe: &Type) -> Vec<TypeVariable> {
4025    fn walk(tpe: &Type, into: &mut Vec<TypeVariable>) {
4026        match tpe {
4027            Type::Literal(_) | Type::Unit => (),
4028            Type::Variable(tvar) => {
4029                if !into.contains(tvar) {
4030                    into.push(tvar.clone());
4031                }
4032            }
4033            Type::Fun {
4034                param_tpe,
4035                return_tpe,
4036            } => {
4037                walk(param_tpe, into);
4038                walk(return_tpe, into);
4039            }
4040            Type::Tuple(tuple) => tuple.iter().for_each(|t| walk(t, into)),
4041            Type::Adt(_, args) => args.iter().for_each(|t| walk(t, into)),
4042            Type::Record(fields) => fields.values().for_each(|t| walk(t, into)),
4043        }
4044    }
4045
4046    let mut variables = Vec::new();
4047    walk(tpe, &mut variables);
4048    variables
4049}
4050
4051/// A [`Type`] written with its variables named, the way an annotation wrote them, and
4052/// every union bare.
4053struct WithNames<'a>(&'a Type, &'a VariableNames);
4054
4055impl std::fmt::Display for WithNames<'_> {
4056    fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
4057        self.0.write(f, AdtNames::Unqualified, Some(self.1))
4058    }
4059}
4060
4061/// A predicate written as the source writes a constraint's use: the class, then the type,
4062/// in parentheses when it is itself applied.
4063fn predicate_text(predicate: &Predicate, spellings: &Spellings) -> String {
4064    let applied = match &predicate.tpe {
4065        Type::Fun { .. } => true,
4066        Type::Adt(_, args) => !args.is_empty(),
4067        _ => false,
4068    };
4069    let tpe = Spelled(&predicate.tpe, spellings);
4070
4071    if applied {
4072        format!("{} ({})", predicate.class.unqualified_name(), tpe)
4073    } else {
4074        format!("{} {}", predicate.class.unqualified_name(), tpe)
4075    }
4076}
4077
4078/// The names in scope while one declaration is annotated, and the counter its fresh
4079/// type variables come from.
4080///
4081/// Two kinds of name, looked up differently:
4082///
4083/// - A **binder** — a parameter, a `case` binding — is introduced by the term being
4084///   annotated. Its type is one type: every use of it shares its variables, which is
4085///   what lets inference learn a parameter's type from how the body uses it.
4086/// - A **global** — a declaration of this module or of an imported one, or a
4087///   constructor — comes from `type_check`'s environment. Its type is read as quantified
4088///   over every variable in it, and [`by_name`](Self::by_name) hands each use a copy
4089///   with those variables replaced by fresh ones. That is what lets one declaration use
4090///   `Just` at `Maybe Int` and `Nothing` at `Maybe Char`, or `identity` at two types.
4091///
4092/// Reading every variable of a global as quantified is only right because each one was
4093/// translated from a declared type — an annotation or a union — on its own, so none of
4094/// its variables is shared with anything else in the environment. A binder shadows a
4095/// global of the same name.
4096struct Types {
4097    counter: u32,
4098    env: HashMap<String, Type>,
4099    globals: HashMap<String, Scheme>,
4100}
4101
4102/// What the typer's environment holds for a global: a type, and the context its
4103/// constraints wrote in front of it.
4104///
4105/// Both are read as quantified over every variable in the type, and
4106/// [`Types::by_name`] instantiates them together — the same variable by the same fresh
4107/// one in the context as in the type — so that a use of `min : Comparable a => a -> a ->
4108/// a` at `Int` is one use of `a`. Each constraint of the context is on one of the type's
4109/// variables, since an annotation's constraint has to be: `canonical::Error::
4110/// ConstraintVariableNotInType`.
4111#[derive(Debug, Clone)]
4112struct Scheme {
4113    /// The constraints, in the order written, each a class and the variable of `tpe`
4114    /// it is required of.
4115    context: Vec<Predicate>,
4116    tpe: Type,
4117}
4118
4119impl Scheme {
4120    /// A scheme with no constraint.
4121    fn unconstrained(tpe: Type) -> Scheme {
4122        Scheme {
4123            context: Vec::new(),
4124            tpe,
4125        }
4126    }
4127}
4128
4129/// Names for type variables, for the messages that write a type the way an annotation
4130/// did.
4131type VariableNames = HashMap<TypeVariable, String>;
4132
4133impl Types {
4134    fn new() -> Types {
4135        let counter = 10;
4136        let env = HashMap::new();
4137        let globals = HashMap::new();
4138
4139        Types {
4140            counter,
4141            env,
4142            globals,
4143        }
4144    }
4145
4146    /// Put the declarations of an outer scope in reach, as globals.
4147    fn extends_with(&mut self, global: HashMap<String, Scheme>) {
4148        self.globals.extend(global)
4149    }
4150
4151    fn fresh_var(&mut self) -> Type {
4152        self.counter += 1;
4153
4154        Type::Variable(TypeVariable::flexible(self.counter))
4155    }
4156
4157    fn add_binder(&mut self, binding: TypeBinder) {
4158        self.env.insert(binding.name, binding.tpe);
4159    }
4160
4161    fn remove_binder(&mut self, name: &str) {
4162        self.env.remove(name);
4163    }
4164
4165    /// The type of one use of `name` — a binder's own type, or a fresh instance of a
4166    /// global's — and the constraints of that use: the global's context, instantiated
4167    /// with the same fresh variables as its type. A binder has none.
4168    ///
4169    /// Each constraint is an obligation of the use, which `constraint::collect` turns
4170    /// into one and `discharge` answers once unification is done.
4171    fn by_name(&mut self, name: &String) -> Option<(Type, Vec<Predicate>)> {
4172        if let Some(tpe) = self.env.get(name) {
4173            return Some((tpe.clone(), Vec::new()));
4174        }
4175
4176        let scheme = self.globals.get(name)?.clone();
4177        let mut fresh = HashMap::new();
4178        let tpe = self.instantiate(scheme.tpe, &mut fresh);
4179        let context = scheme
4180            .context
4181            .into_iter()
4182            .map(|predicate| Predicate {
4183                class: predicate.class,
4184                tpe: self.instantiate(predicate.tpe, &mut fresh),
4185            })
4186            .collect();
4187
4188        Some((tpe, context))
4189    }
4190
4191    /// `tpe` with each of its variables replaced by a fresh one, the same variable by
4192    /// the same fresh one throughout.
4193    fn instantiate(&mut self, tpe: Type, fresh: &mut HashMap<TypeVariable, Type>) -> Type {
4194        match tpe {
4195            Type::Literal(_) | Type::Unit => tpe,
4196            Type::Variable(tvar) => {
4197                if let Some(replacement) = fresh.get(&tvar) {
4198                    return replacement.clone();
4199                }
4200                let replacement = self.fresh_var();
4201                fresh.insert(tvar, replacement.clone());
4202                replacement
4203            }
4204            Type::Fun {
4205                param_tpe,
4206                return_tpe,
4207            } => Type::Fun {
4208                param_tpe: Box::new(self.instantiate(*param_tpe, fresh)),
4209                return_tpe: Box::new(self.instantiate(*return_tpe, fresh)),
4210            },
4211            Type::Tuple(Tuple::Two(a, b)) => Type::Tuple(Tuple::two(
4212                self.instantiate(*a, fresh),
4213                self.instantiate(*b, fresh),
4214            )),
4215            Type::Tuple(Tuple::Three(a, b, c)) => Type::Tuple(Tuple::three(
4216                self.instantiate(*a, fresh),
4217                self.instantiate(*b, fresh),
4218                self.instantiate(*c, fresh),
4219            )),
4220            Type::Adt(name, args) => Type::Adt(
4221                name,
4222                args.into_iter()
4223                    .map(|arg| self.instantiate(arg, fresh))
4224                    .collect(),
4225            ),
4226            Type::Record(fields) => Type::Record(
4227                fields
4228                    .into_iter()
4229                    .map(|(label, tpe)| (label, self.instantiate(tpe, fresh)))
4230                    .collect(),
4231            ),
4232        }
4233    }
4234}
4235
4236/// infer the type of the given term given known function defined in the outer scopes.
4237/// This is a translation of the algorithm demonstrated by
4238/// [Ionut Gan at I T.A.K.E Unconference 2015](https://www.youtube.com/watch?v=oPVTNxiMcSU)
4239pub fn infer(term: Term, global: HashMap<String, Type>) -> Result<Type, ErrorKind> {
4240    let global = global
4241        .into_iter()
4242        .map(|(name, tpe)| (name, Scheme::unconstrained(tpe)))
4243        .collect();
4244
4245    infer_annotated(term, global, None, &classes::ClassTable::empty()).map(|(term, _)| term.tpe)
4246}
4247
4248/// [`infer`], with the declaration's type annotation as a constraint of its own, and
4249/// answering with the whole solved term rather than only its type.
4250///
4251/// The annotation is put *first*, before the constraints the body generates, and that
4252/// ordering is the point of the function. `unify` solves constraints in order, so the
4253/// annotated type is substituted into the body's constraints before any of them are
4254/// solved; when one of them then fails, its [`Origin::explanation`] names the annotation,
4255/// and the diagnostic can say `Int` was expected *because of the annotation* rather
4256/// than merely that the declaration as a whole does not check.
4257///
4258/// The annotation's variables are rigid when it arrives (see [`TypeVariable`]), so `unify`
4259/// raises [`ErrorKind::RigidVariable`] where the body needs one of them to be a type of its
4260/// own, and a given of the annotation's context can only answer an obligation on the very
4261/// variable it is on.
4262///
4263/// The term handed back is zonked — see [`Substitution::apply_term`] — so every node
4264/// carries the type inference solved for it and not the variable `annotate` gave it.
4265/// Beside it comes the context the annotation required of its variables, each on the
4266/// rigid variable it was given on.
4267///
4268/// # The order of the steps
4269///
4270/// Equations first, then field constraints, then obligations. A field constraint can
4271/// solve the variable an instance is looked up by, so an obligation is read only once
4272/// both have run. Whether reading an instance's context can in turn decide a field
4273/// constraint does not arise: an obligation only reads the solution and adds nothing to
4274/// it.
4275fn infer_annotated(
4276    term: Term,
4277    global: HashMap<String, Scheme>,
4278    annotation: Option<Annotation>,
4279    table: &classes::ClassTable,
4280) -> Result<(TypedTerm, Vec<Predicate>), ErrorKind> {
4281    let mut env = Types::new();
4282    env.extends_with(global);
4283
4284    let typed_term = annotate::annotate(term, &mut env)?;
4285    debug!("typed term: {:#?}", typed_term);
4286
4287    let mut constraints = Vec::new();
4288    let annotated = annotation.is_some();
4289    let mut given = Vec::new();
4290    let mut names = Vec::new();
4291    let mut member_variables = Vec::new();
4292    let mut written = Written::Annotation;
4293
4294    if let Some(annotation) = annotation {
4295        given = annotation.context;
4296        names = annotation.names;
4297        member_variables = annotation.member_variables;
4298        written = annotation.written;
4299
4300        // Left is the annotation's type, because left is the type of the text the
4301        // span points at — see `Constraint`.
4302        constraints.push(Constraint::new(
4303            annotation.tpe,
4304            typed_term.tpe.clone(),
4305            annotation.reason,
4306            annotation.span,
4307        ));
4308    }
4309
4310    let constraint::Constraints {
4311        equations,
4312        fields,
4313        holes,
4314        obligations,
4315    } = constraint::collect(&typed_term);
4316    constraints.extend(equations);
4317    debug!("Constraints: {:#?}", constraints);
4318
4319    let substitution = unifier::unify(constraints)?;
4320    // Read only now, with every equation of the declaration solved: see
4321    // `FieldConstraint`.
4322    let declaration = unifier::Declaration {
4323        holes: &holes,
4324        declared: &typed_term.tpe,
4325        annotated,
4326    };
4327    let substitution = unifier::read_fields(substitution, fields, &declaration)?;
4328
4329    // Read last, against the final substitution: see the `classes` module.
4330    classes::discharge(
4331        table,
4332        obligations,
4333        &substitution,
4334        &classes::Declared {
4335            tpe: &typed_term.tpe,
4336            annotated,
4337            given: &given,
4338            names: &names,
4339            member_variables: &member_variables,
4340            written,
4341        },
4342    )?;
4343
4344    let context = given
4345        .iter()
4346        .map(|(class, variable)| Predicate {
4347            class: class.clone(),
4348            tpe: Type::Variable(variable.clone()),
4349        })
4350        .collect();
4351
4352    Ok((substitution.apply_term(typed_term), context))
4353}
4354
4355// TODO Once we have changed the Term to the zelkova primitives, rewrite the tests
4356// to use actual source code instead of AST. It's a pain to write them but it's even
4357// more of a pain to read them :)
4358// TODO Also write some assertions on the type instead of just printing XD
4359// TODO Import remaining tests. Plus the one for the modules above.
4360#[cfg(test)]
4361mod tests {
4362    use super::*;
4363
4364    // These terms are written by hand rather than translated from source, so they
4365    // have no position — `Term::bare`. What they pin is inference, which does not
4366    // read spans; the tests that pin what a *diagnostic* points at go through real
4367    // source, in `crates/zelkova-compiler/tests/typer.rs`.
4368    fn int(i: i64) -> Term {
4369        Term::bare(TermKind::Int(i))
4370    }
4371    fn var(n: &str) -> Term {
4372        Term::bare(TermKind::Identifier(Reference::local(n)))
4373    }
4374    fn fun(arg: &str, body: Term) -> Term {
4375        Term::bare(TermKind::Fun {
4376            param: arg.to_owned(),
4377            body: Box::new(body),
4378        })
4379    }
4380    fn if_(cond: Term, true_branch: Term, false_branch: Term) -> Term {
4381        Term::bare(TermKind::If {
4382            cond: Box::new(cond),
4383            true_branch: Box::new(true_branch),
4384            false_branch: Box::new(false_branch),
4385        })
4386    }
4387    fn apply(fun: Term, arg: Term) -> Term {
4388        Term::bare(TermKind::Apply {
4389            fun: Box::new(fun),
4390            arg: Box::new(arg),
4391            saturation: Saturation::Partial,
4392        })
4393    }
4394    fn let_(binding: &str, value: Term, body: Term) -> Term {
4395        Term::bare(TermKind::Let {
4396            binding: binding.to_owned(),
4397            value: Box::new(value),
4398            body: Box::new(body),
4399        })
4400    }
4401
4402    #[derive(Default)]
4403    struct Signature {
4404        counter: u8, // max 255 letters
4405        known: HashMap<u32, String>,
4406    }
4407
4408    impl Signature {
4409        // Helper function to reduce boilerplate
4410        fn of_type(tpe: Type) -> String {
4411            let mut sig: Signature = Default::default();
4412            sig.type_signature(tpe)
4413        }
4414
4415        fn type_signature(&mut self, tpe: Type) -> String {
4416            match tpe {
4417                Type::Literal(TypeLiteral::Int) => "Int".to_owned(),
4418                Type::Literal(TypeLiteral::Char) => "Char".to_owned(),
4419                Type::Literal(TypeLiteral::Float) => "Float".to_owned(),
4420                Type::Literal(TypeLiteral::String) => "String".to_owned(),
4421                Type::Unit => "()".to_owned(),
4422                Type::Variable(TypeVariable { id, .. }) => {
4423                    if let Some(name) = self.known.get(&id) {
4424                        name.clone()
4425                    } else {
4426                        let name = self.counter_as_letter();
4427                        self.counter += 1;
4428
4429                        self.known.insert(id, name.clone());
4430
4431                        name
4432                    }
4433                }
4434                Type::Fun {
4435                    param_tpe,
4436                    return_tpe,
4437                } => {
4438                    let is_param_fun = matches!(param_tpe.as_ref(), Type::Fun { .. });
4439                    let param = self.type_signature(*param_tpe);
4440                    let retur = self.type_signature(*return_tpe);
4441
4442                    if is_param_fun {
4443                        format!("({}) -> {}", param, retur)
4444                    } else {
4445                        format!("{} -> {}", param, retur)
4446                    }
4447                }
4448                Type::Tuple(Tuple::Two(a, b)) => {
4449                    format!("({}, {})", self.type_signature(*a), self.type_signature(*b))
4450                }
4451                Type::Tuple(Tuple::Three(a, b, c)) => {
4452                    format!(
4453                        "({}, {}, {})",
4454                        self.type_signature(*a),
4455                        self.type_signature(*b),
4456                        self.type_signature(*c)
4457                    )
4458                }
4459                Type::Adt(name, args) if args.is_empty() => name.unqualified_name().to_string(),
4460                Type::Adt(name, args) => {
4461                    let arg_strs: Vec<String> =
4462                        args.into_iter().map(|a| self.type_signature(a)).collect();
4463                    format!("{} {}", name.unqualified_name(), arg_strs.join(" "))
4464                }
4465                Type::Record(fields) => {
4466                    let fields: Vec<String> = fields
4467                        .into_iter()
4468                        .map(|(label, tpe)| {
4469                            format!("{} : {}", label.as_str(), self.type_signature(tpe))
4470                        })
4471                        .collect();
4472                    format!("{{ {} }}", fields.join(", "))
4473                }
4474            }
4475        }
4476
4477        fn counter_as_letter(&self) -> String {
4478            let m = self.counter % 26;
4479            let d = self.counter / 26;
4480
4481            let m_char = (97 + m) as char; // 97 is 'a'
4482            let d_char = (96 + d) as char; // -1 because we start at 1
4483
4484            if d > 0 {
4485                format!("{}{}", d_char, m_char)
4486            } else {
4487                format!("{}", m_char)
4488            }
4489        }
4490    }
4491
4492    #[test]
4493    fn infer_identity_function() {
4494        let global = HashMap::new();
4495        let term = fun("a", var("a"));
4496        let infered = infer(term, global).unwrap();
4497
4498        assert_eq!(Signature::of_type(infered), "a -> a".to_owned());
4499    }
4500
4501    #[test]
4502    fn infer_const_function() {
4503        let global = HashMap::new();
4504        let term = fun("a", fun("b", var("a")));
4505        let infered = infer(term, global).unwrap();
4506
4507        assert_eq!(Signature::of_type(infered), "a -> b -> a".to_owned());
4508    }
4509
4510    #[test]
4511    fn infer_compose_function() {
4512        let global = HashMap::new();
4513        // \f -> \g -> \x -> f ( g x )
4514        let term = fun(
4515            "f",
4516            fun("g", fun("x", apply(var("f"), apply(var("g"), var("x"))))),
4517        );
4518        let infered = infer(term, global).unwrap();
4519
4520        assert_eq!(
4521            Signature::of_type(infered),
4522            "(a -> b) -> (c -> a) -> c -> b".to_owned()
4523        );
4524    }
4525
4526    #[test]
4527    fn infer_pred_function() {
4528        let global = HashMap::new();
4529        let term = fun("pred", if_(apply(var("pred"), int(1)), int(2), int(3)));
4530        let infered = infer(term, global).unwrap();
4531
4532        // Integer literals infer as `Int`
4533        assert_eq!(
4534            Signature::of_type(infered),
4535            "(Int -> Bool) -> Int".to_owned()
4536        );
4537    }
4538
4539    #[test]
4540    fn infer_increment_function() {
4541        let mut global = HashMap::new();
4542        // "+" -> Type.FUN(Type.INT, Type.FUN(Type.INT, Type.INT)),
4543        global.insert(
4544            "+".to_owned(),
4545            Type::Fun {
4546                param_tpe: Box::new(Type::Literal(TypeLiteral::Int)),
4547                return_tpe: Box::new(Type::Fun {
4548                    param_tpe: Box::new(Type::Literal(TypeLiteral::Int)),
4549                    return_tpe: Box::new(Type::Literal(TypeLiteral::Int)),
4550                }),
4551            },
4552        );
4553        let term = let_(
4554            "inc",
4555            fun("a", apply(apply(var("+"), var("a")), int(1))),
4556            apply(var("inc"), int(42)),
4557        );
4558        let infered = infer(term, global).unwrap();
4559
4560        assert_eq!(Signature::of_type(infered), "Int".to_owned());
4561    }
4562
4563    #[test]
4564    fn infer_incdec_function() {
4565        let mut global = HashMap::new();
4566        global.insert(
4567            "+".to_owned(),
4568            Type::Fun {
4569                param_tpe: Box::new(Type::Literal(TypeLiteral::Int)),
4570                return_tpe: Box::new(Type::Fun {
4571                    param_tpe: Box::new(Type::Literal(TypeLiteral::Int)),
4572                    return_tpe: Box::new(Type::Literal(TypeLiteral::Int)),
4573                }),
4574            },
4575        );
4576        global.insert(
4577            "-".to_owned(),
4578            Type::Fun {
4579                param_tpe: Box::new(Type::Literal(TypeLiteral::Int)),
4580                return_tpe: Box::new(Type::Fun {
4581                    param_tpe: Box::new(Type::Literal(TypeLiteral::Int)),
4582                    return_tpe: Box::new(Type::Literal(TypeLiteral::Int)),
4583                }),
4584            },
4585        );
4586        let term = let_(
4587            "inc",
4588            fun("a", apply(apply(var("+"), var("a")), int(1))),
4589            let_(
4590                "dec",
4591                fun("a", apply(apply(var("-"), var("a")), int(1))),
4592                apply(var("dec"), apply(var("inc"), int(42))),
4593            ),
4594        );
4595        let infered = infer(term, global).unwrap();
4596
4597        assert_eq!(Signature::of_type(infered), "Int".to_owned());
4598    }
4599
4600    #[test]
4601    fn infer_cannot_possible() {
4602        let mut global = HashMap::new();
4603        global.insert(
4604            "+".to_owned(),
4605            Type::Fun {
4606                param_tpe: Box::new(Type::Literal(TypeLiteral::Int)),
4607                return_tpe: Box::new(Type::Fun {
4608                    param_tpe: Box::new(Type::Literal(TypeLiteral::Int)),
4609                    return_tpe: Box::new(Type::Literal(TypeLiteral::Int)),
4610                }),
4611            },
4612        );
4613        global.insert("True".to_owned(), bool_type());
4614        let term = apply(apply(var("+"), var("True")), int(1));
4615        assert!(infer(term, global).is_err());
4616    }
4617
4618    // --- A constructor pattern finds only this module's own unions ------------
4619
4620    /// The qualified name of `name` as declared by `module` of the package `main`.
4621    fn qual(module: &str, name: &str) -> QualName {
4622        QualName::in_module(crate::PackageName::new("main").unwrap(), module, name)
4623    }
4624
4625    /// `Main`'s own unions, as `translate_pattern` receives them: one nullary
4626    /// `Main.Size`.
4627    fn main_size() -> (QualName, canonical::UnionType) {
4628        (
4629            qual("Main", "Size"),
4630            canonical::UnionType {
4631                span: NodeSpan::none(),
4632                variables: vec![],
4633                variants: vec![canonical::TypeConstructor {
4634                    name: "Big".into(),
4635                    type_parameters: vec![],
4636                    tpe: qual("Main", "Size"),
4637                }],
4638            },
4639        )
4640    }
4641
4642    /// A nullary constructor pattern for `name`, building the union `tpe`.
4643    fn constructor_pattern(name: &str, tpe: QualName) -> canonical::Pattern {
4644        canonical::Pattern {
4645            span: NodeSpan::none(),
4646            kind: canonical::PatternKind::Constructor {
4647                ctor: canonical::TypeConstructor {
4648                    name: name.into(),
4649                    type_parameters: vec![],
4650                    tpe,
4651                },
4652                args: vec![],
4653            },
4654        }
4655    }
4656
4657    /// The four things `canonical::ExpressionKind` calls a name stay four things in the
4658    /// IR.
4659    ///
4660    /// They used to be one: every one of them became `TermKind::Identifier(String)`, and
4661    /// the string is bare for a local and qualified for the other three, so nothing
4662    /// downstream could tell a parameter from an import from a constructor
4663    /// ([`DEC-18` decision
4664    /// 1](../../docs/decisions/dec-18.md#1--the-backend-reads-a-typed-ir-and-the-typer-is-what-produces-it)).
4665    ///
4666    /// Written against hand-built canonical expressions rather than against source, so
4667    /// that all four are read off one translation with no other module needing to be
4668    /// checked first.
4669    ///
4670    /// Mutation-checked by giving the `VarForeign` and `VarTopLevel` arms of
4671    /// `canonical_expr_to_term` the same `ReferenceKind`, which is the collapse this
4672    /// pins: the two assertions naming them then read the same value.
4673    #[test]
4674    fn the_four_kinds_of_name_stay_apart() {
4675        let (union_name, union) = main_size();
4676        let translation = Translation::of_types(HashMap::from([(union_name.clone(), &union)]));
4677        let lib = crate::PackageName::new("lib").unwrap();
4678        let lib_size = QualName::in_module(lib.clone(), "Lib", "size");
4679
4680        let reference = |kind: canonical::ExpressionKind| {
4681            let mut counter = 0;
4682            let expression = canonical::Expression::bare(kind);
4683
4684            match canonical_expr_to_term(&expression, &translation, &mut counter) {
4685                Some(Term {
4686                    kind: TermKind::Identifier(reference),
4687                    ..
4688                }) => reference,
4689                other => panic!("expected a name, got {:?}", other),
4690            }
4691        };
4692
4693        assert_eq!(
4694            reference(canonical::ExpressionKind::VarLocal("size".into())).kind,
4695            ReferenceKind::Local
4696        );
4697        assert_eq!(
4698            reference(canonical::ExpressionKind::VarTopLevel(qual("Main", "size"))).kind,
4699            ReferenceKind::TopLevel(qual("Main", "size"))
4700        );
4701        assert_eq!(
4702            reference(canonical::ExpressionKind::VarForeign(
4703                lib_size.clone(),
4704                lib.clone(),
4705                canonical::Type::Variable("a".into())
4706            ))
4707            .kind,
4708            ReferenceKind::Foreign(lib_size, lib, 0)
4709        );
4710        assert_eq!(
4711            reference(canonical::ExpressionKind::VarConstructor(
4712                qual("Main", "Big"),
4713                canonical::Type::Type(union_name.clone(), vec![])
4714            ))
4715            .kind,
4716            ReferenceKind::Constructor(Constructor {
4717                union: union_name,
4718                name: "Big".into(),
4719                index: 0,
4720                arity: 0,
4721            })
4722        );
4723    }
4724
4725    /// `A.S` builds `A.Size`, and a `Main` that happens to declare its own `Size`
4726    /// is not where that union is found.
4727    ///
4728    /// `BUG-35`: the lookup narrowed the constructor's type to its unqualified half,
4729    /// so `A.S` found `Main.Size` and the pattern was translated at the local type.
4730    /// With no `A` in the translation, the lookup finds nothing at all.
4731    ///
4732    /// Mutation-checked by restoring the narrowed lookup
4733    /// (`unions` keyed by `Name`, `get(&ctor.tpe.unqualified_name())`): the
4734    /// pattern is then translated and the assertion goes red.
4735    #[test]
4736    fn an_imported_constructor_does_not_find_a_local_type_of_the_same_name() {
4737        let (name, union) = main_size();
4738        let translation = Translation::of_types(HashMap::from([(name, &union)]));
4739        let mut counter = 0;
4740
4741        let pattern = constructor_pattern("S", qual("A", "Size"));
4742
4743        assert!(
4744            translate_pattern(&pattern, &translation, &mut counter).is_none(),
4745            "`A.S` is not a constructor of `Main.Size`"
4746        );
4747    }
4748
4749    /// The other half: `Main`'s own constructor still finds `Main`'s own union, so
4750    /// the test above is not passing because the lookup stopped finding anything.
4751    #[test]
4752    fn a_local_constructor_finds_its_own_type() {
4753        let (name, union) = main_size();
4754        let translation = Translation::of_types(HashMap::from([(name, &union)]));
4755        let mut counter = 0;
4756
4757        let pattern = constructor_pattern("Big", qual("Main", "Size"));
4758
4759        let translated = translate_pattern(&pattern, &translation, &mut counter)
4760            .expect("`Main.Big` is a constructor of `Main.Size`");
4761
4762        match translated.kind {
4763            TermPatternKind::Constructor { ctor, .. } => {
4764                assert_eq!(ctor.union, qual("Main", "Size"));
4765            }
4766            other => panic!("expected a constructor pattern, got {:?}", other),
4767        }
4768    }
4769
4770    // --- Display for Type ---------------------------------------------------
4771
4772    fn int_t() -> Type {
4773        Type::Literal(TypeLiteral::Int)
4774    }
4775    fn bool_t() -> Type {
4776        bool_type()
4777    }
4778    fn char_t() -> Type {
4779        Type::Literal(TypeLiteral::Char)
4780    }
4781    fn fun_t(param: Type, ret: Type) -> Type {
4782        Type::Fun {
4783            param_tpe: Box::new(param),
4784            return_tpe: Box::new(ret),
4785        }
4786    }
4787    /// A union declared in a module called `Widget`, which is never what `Display`
4788    /// writes — the point of the tests below is that it writes the bare `name`.
4789    fn adt(name: &str, args: Vec<Type>) -> Type {
4790        Type::Adt(qual("Widget", name), args)
4791    }
4792
4793    /// `Display for Type` is the text diagnostics quote back to the user, so its two
4794    /// parenthesisation rules and its inference-variable spelling are user-visible
4795    /// output. Nothing else pins them: the pipeline test that renders a type mismatch
4796    /// only ever reaches the `Literal` arms. Dropping a parenthesis here would print
4797    /// `Maybe Maybe Int`, which reads as a different type, with the suite still green.
4798    #[test]
4799    fn display_writes_types_the_way_the_source_spells_them() {
4800        let cases: Vec<(Type, &str)> = vec![
4801            // A function in *parameter* position is parenthesised, because `->` is
4802            // right-associative: `(a -> b) -> c` and `a -> b -> c` are different types.
4803            (
4804                fun_t(fun_t(int_t(), bool_t()), int_t()),
4805                "(Int -> Bool) -> Int",
4806            ),
4807            // In *return* position it is not, for the same reason: the chain already
4808            // re-reads as itself.
4809            (
4810                fun_t(int_t(), fun_t(bool_t(), char_t())),
4811                "Int -> Bool -> Char",
4812            ),
4813            // An applied `Adt` nested inside another needs parens to survive a re-read.
4814            (
4815                adt("Maybe", vec![adt("Maybe", vec![int_t()])]),
4816                "Maybe (Maybe Int)",
4817            ),
4818            // So does a function used as an `Adt` argument.
4819            (
4820                adt("Maybe", vec![fun_t(int_t(), bool_t())]),
4821                "Maybe (Int -> Bool)",
4822            ),
4823            // A *nullary* `Adt` argument does not: there is nothing to mis-group.
4824            (adt("List", vec![adt("Never", vec![])]), "List Never"),
4825            // And an applied `Adt` in parameter position does not either — application
4826            // binds tighter than `->`.
4827            (
4828                fun_t(adt("Maybe", vec![int_t()]), bool_t()),
4829                "Maybe Int -> Bool",
4830            ),
4831            (Type::Tuple(Tuple::two(int_t(), bool_t())), "( Int, Bool )"),
4832            (
4833                Type::Tuple(Tuple::three(int_t(), bool_t(), char_t())),
4834                "( Int, Bool, Char )",
4835            ),
4836            // Inference variables have no source syntax; Elm spells them `t{n}`.
4837            (Type::Variable(TypeVariable::flexible(7)), "t7"),
4838        ];
4839
4840        for (tpe, expected) in cases {
4841            assert_eq!(format!("{}", tpe), expected, "rendering {:?}", tpe);
4842        }
4843    }
4844
4845    /// `ErrorKind::CircularType` names one type, but the solution a variable would
4846    /// have had to contain itself in is built out of everything it was unified
4847    /// against — so one type is enough to hold two same-named declarations.
4848    ///
4849    /// Written by hand because no Zelkova source available today produces a circular
4850    /// type at all: the constructs that do (`let`, lambdas) are unimplemented, and
4851    /// `unifier.rs` is the only thing that raises the variant.
4852    ///
4853    /// Mutation-checked by quoting `tpe` through `Display` unconditionally, the way
4854    /// the arm was first written, which reports *contain itself in `Box Size Size`*.
4855    #[test]
4856    fn a_circular_type_naming_two_modules_alike_qualifies_both() {
4857        let tpe = Type::Adt(
4858            qual("Lib", "Box"),
4859            vec![
4860                Type::Adt(qual("A", "Size"), vec![]),
4861                Type::Adt(qual("B", "Size"), vec![]),
4862            ],
4863        );
4864
4865        let kind = ErrorKind::CircularType {
4866            tpe: Box::new(tpe),
4867            origin: Box::new(Origin::new(Reason::Annotation, NodeSpan::none())),
4868        };
4869
4870        assert_eq!(
4871            kind.message(&Spellings::default()),
4872            "circular type: a type variable would have to contain itself in \
4873             `Lib.Box A.Size B.Size`"
4874        );
4875    }
4876
4877    /// The counterpart: one declaration per spelling, so the type is quoted the way
4878    /// the source writes it.
4879    #[test]
4880    fn a_circular_type_with_no_collision_stays_unqualified() {
4881        let kind = ErrorKind::CircularType {
4882            tpe: Box::new(adt("Box", vec![adt("Size", vec![])])),
4883            origin: Box::new(Origin::new(Reason::Annotation, NodeSpan::none())),
4884        };
4885
4886        assert_eq!(
4887            kind.message(&Spellings::default()),
4888            "circular type: a type variable would have to contain itself in `Box Size`"
4889        );
4890    }
4891}