prism_compiler/lang/
mod.rs1use crate::lang::env::{Env, UniqueVariableId};
2use crate::lang::error::TypeError;
3use prism_parser::core::pos::Pos;
4use prism_parser::core::span::Span;
5use std::collections::{HashMap, HashSet};
6use std::fmt::{Display, Formatter};
7use std::ops::Deref;
8
9mod beta_reduce;
10mod beta_reduce_head;
11pub mod display;
12pub mod env;
13pub mod error;
14mod expect_beq;
15mod expect_beq_internal;
16pub mod from_action_result;
17pub mod is_beta_equal;
18pub mod simplify;
19pub mod type_check;
20
21type QueuedConstraint = (
22 (Env, HashMap<UniqueVariableId, usize>),
23 (UnionIndex, Env, HashMap<UniqueVariableId, usize>),
24);
25
26#[derive(Default)]
27pub struct TcEnv {
28 pub values: Vec<PartialExpr>,
29 pub value_origins: Vec<ValueOrigin>,
30 value_types: HashMap<UnionIndex, UnionIndex>,
31
32 tc_id: usize,
33 pub errors: Vec<TypeError>,
34 toxic_values: HashSet<UnionIndex>,
35
36 queued_beq_free: HashMap<UnionIndex, Vec<QueuedConstraint>>,
38 }
40
41#[derive(Copy, Clone, Hash, Eq, PartialEq, Debug)]
42pub enum ValueOrigin {
43 SourceCode(Span),
45 TypeOf(UnionIndex),
47 FreeSub(UnionIndex),
49 Failure,
51}
52
53#[derive(Copy, Clone, Hash, Eq, PartialEq, Debug)]
54pub struct UnionIndex(usize);
55
56impl Display for UnionIndex {
57 fn fmt(&self, f: &mut Formatter<'_>) -> std::fmt::Result {
58 write!(f, "[{}]", self.0)
59 }
60}
61
62impl Deref for UnionIndex {
63 type Target = usize;
64
65 fn deref(&self) -> &Self::Target {
66 &self.0
67 }
68}
69
70#[derive(Copy, Clone, Eq, PartialEq, Debug)]
71pub enum PartialExpr {
72 Free,
73 Type,
74 Let(UnionIndex, UnionIndex),
75 DeBruijnIndex(usize),
76 FnType(UnionIndex, UnionIndex),
77 FnConstruct(UnionIndex),
78 FnDestruct(UnionIndex, UnionIndex),
79 Shift(UnionIndex, usize),
80 TypeAssert(UnionIndex, UnionIndex),
81}
82
83impl TcEnv {
84 pub fn store_from_source(&mut self, e: PartialExpr, span: Span) -> UnionIndex {
85 self.store(e, ValueOrigin::SourceCode(span))
86 }
87
88 pub fn store_test(&mut self, e: PartialExpr) -> UnionIndex {
89 self.store(
90 e,
91 ValueOrigin::SourceCode(Span::new(Pos::start(), Pos::start())),
92 )
93 }
94
95 fn store(&mut self, e: PartialExpr, origin: ValueOrigin) -> UnionIndex {
96 self.values.push(e);
97 self.value_origins.push(origin);
98 UnionIndex(self.values.len() - 1)
99 }
100
101 pub fn reset(&mut self) {
102 self.queued_beq_free.clear();
103 self.errors.clear();
104 self.toxic_values.clear();
105 self.tc_id = 0;
106 }
107}