swamp_script_semantic/
lib.rs

1/*
2 * Copyright (c) Peter Bjorklund. All rights reserved. https://github.com/swamp/script
3 * Licensed under the MIT License. See LICENSE in the project root for license information.
4 */
5pub mod inst_cache;
6pub mod intr;
7pub mod prelude;
8
9use crate::inst_cache::InstantiationCache;
10use crate::intr::IntrinsicFunction;
11use crate::prelude::IntrinsicFunctionDefinitionRef;
12
13pub use fixed32::Fp;
14use seq_map::SeqMap;
15use std::cmp::PartialEq;
16use std::fmt;
17use std::fmt::{Debug, Display, Formatter};
18use std::rc::Rc;
19use swamp_script_node::Node;
20use swamp_script_types::prelude::*;
21use tracing::error;
22
23#[derive(Debug, Clone)]
24pub struct TypeWithMut {
25    pub resolved_type: Type,
26    pub is_mutable: bool,
27}
28
29#[derive(Debug, Clone)]
30pub enum SemanticError {
31    CouldNotInsertStruct,
32    DuplicateTypeAlias(String),
33    CanOnlyUseStructForMemberFunctions,
34    ResolveNotStruct,
35    DuplicateStructName(String),
36    DuplicateEnumType(String),
37    DuplicateEnumVariantType(String, String),
38    DuplicateFieldName(String),
39    DuplicateExternalFunction(String),
40    DuplicateRustType(String),
41    DuplicateConstName(String),
42    CircularConstantDependency(Vec<ConstantId>),
43    DuplicateConstantId(ConstantId),
44    IncompatibleTypes,
45    WasNotImmutable,
46    WasNotMutable,
47    DuplicateSymbolName(String),
48    DuplicateNamespaceLink(String),
49    MismatchedTypes { expected: Type, found: Vec<Type> },
50    UnknownImplOnType,
51    UnknownTypeVariable,
52}
53
54#[derive(Debug, Eq, PartialEq)]
55pub struct LocalIdentifier(pub Node);
56
57//#[derive(Debug,Clone)]
58pub struct InternalFunctionDefinition {
59    pub body: Expression,
60    pub name: LocalIdentifier,
61    pub assigned_name: String,
62    pub signature: Signature,
63}
64
65impl Default for InternalFunctionDefinition {
66    fn default() -> Self {
67        Self {
68            body: Expression {
69                ty: Type::Never,
70                node: Default::default(),
71                kind: ExpressionKind::Break,
72            },
73            name: LocalIdentifier(Default::default()),
74            assigned_name: "".to_string(),
75            signature: Signature {
76                parameters: vec![],
77                return_type: Box::new(Type::Never),
78            },
79        }
80    }
81}
82
83impl Debug for InternalFunctionDefinition {
84    fn fmt(&self, f: &mut Formatter<'_>) -> fmt::Result {
85        write!(f, "{:?}\n{:?}", self.signature, self.body)
86    }
87}
88
89impl PartialEq<Self> for InternalFunctionDefinition {
90    fn eq(&self, other: &Self) -> bool {
91        self.name == other.name
92    }
93}
94
95impl Eq for InternalFunctionDefinition {}
96
97pub type InternalFunctionDefinitionRef = Rc<InternalFunctionDefinition>;
98
99pub type ExternalFunctionId = u32;
100
101pub type ConstantId = u32;
102
103#[derive(Eq, PartialEq)]
104pub struct ExternalFunctionDefinition {
105    pub name: Option<Node>,
106    pub assigned_name: String,
107    pub signature: Signature,
108    pub id: ExternalFunctionId,
109}
110
111impl Debug for ExternalFunctionDefinition {
112    fn fmt(&self, f: &mut Formatter<'_>) -> fmt::Result {
113        write!(f, "external fn")
114    }
115}
116
117pub type ExternalFunctionDefinitionRef = Rc<crate::ExternalFunctionDefinition>;
118
119#[derive(Debug, Clone)]
120pub struct Variable {
121    pub name: Node,
122    pub resolved_type: Type,
123    pub mutable_node: Option<Node>,
124
125    pub scope_index: usize,
126    pub variable_index: usize,
127}
128
129impl Variable {
130    #[must_use]
131    pub const fn is_mutable(&self) -> bool {
132        self.mutable_node.is_some()
133    }
134}
135
136pub type VariableRef = Rc<Variable>;
137
138#[derive(Debug, Clone)]
139pub struct MutVariable {
140    pub variable_ref: VariableRef,
141}
142
143//type MutVariableRef = Rc<MutVariable>;
144
145#[derive(Debug, Clone)]
146pub enum BinaryOperatorKind {
147    Add,
148    Subtract,
149    Multiply,
150    Divide,
151    Modulo,
152    LogicalOr,
153    LogicalAnd,
154    Equal,
155    NotEqual,
156    LessThan,
157    LessEqual,
158    GreaterThan,
159    GreaterEqual,
160    RangeExclusive,
161}
162
163#[derive(Debug, Clone)]
164pub struct BinaryOperator {
165    pub left: Box<Expression>,
166    pub right: Box<Expression>,
167    pub kind: BinaryOperatorKind,
168    pub node: Node,
169}
170
171#[derive(Debug, Clone)]
172pub enum UnaryOperatorKind {
173    Not,
174    Negate,
175}
176#[derive(Debug, Clone)]
177pub struct UnaryOperator {
178    pub left: Box<Expression>,
179    pub kind: UnaryOperatorKind,
180    pub node: Node,
181}
182
183#[derive()]
184pub struct InternalFunctionCall {
185    pub arguments: Vec<ArgumentExpressionOrLocation>,
186
187    pub function_definition: InternalFunctionDefinitionRef,
188    pub function_expression: Box<Expression>,
189}
190
191impl Debug for InternalFunctionCall {
192    fn fmt(&self, f: &mut Formatter<'_>) -> fmt::Result {
193        write!(
194            f,
195            "InFuncCall({:?} {:?})",
196            self.function_expression, self.arguments
197        )
198    }
199}
200
201#[derive(Debug, Clone)]
202pub struct ExternalFunctionCall {
203    pub arguments: Vec<ArgumentExpressionOrLocation>,
204    pub function_definition: ExternalFunctionDefinitionRef,
205    pub function_expression: Box<Expression>,
206}
207
208pub fn comma_tuple_ref<K: Display, V: Display>(values: &[(&K, &V)]) -> String {
209    let mut result = String::new();
210    for (i, (key, value)) in values.iter().enumerate() {
211        if i > 0 {
212            result.push_str(", ");
213        }
214        result.push_str(format!("{}: {}", key, value).as_str());
215    }
216    result
217}
218
219#[derive(Debug, Clone)]
220pub struct MemberCall {
221    pub function: FunctionRef,
222    pub arguments: Vec<ArgumentExpressionOrLocation>,
223}
224
225#[derive(Debug, Clone)]
226pub struct ArrayItem {
227    pub item_type: Type,
228    pub int_expression: Expression,
229    pub array_expression: Expression,
230    pub array_type: Type,
231}
232
233pub type ArrayItemRef = Rc<ArrayItem>;
234
235#[derive(Debug, Clone)]
236pub enum PrecisionType {
237    Float,
238    String,
239}
240
241#[derive(Debug, Clone)]
242pub enum FormatSpecifierKind {
243    LowerHex,                            // :x
244    UpperHex,                            // :X
245    Binary,                              // :b
246    Float,                               // :f
247    Precision(u32, Node, PrecisionType), // :..2f or :..5s
248}
249
250#[derive(Debug, Clone)]
251pub struct FormatSpecifier {
252    pub node: Node,
253    pub kind: FormatSpecifierKind,
254}
255
256#[derive(Debug, Clone)]
257pub enum StringPart {
258    Literal(Node, String),
259    Interpolation(Expression, Option<FormatSpecifier>),
260}
261
262pub type FunctionRef = Rc<Function>;
263
264#[derive(Debug, Eq, Clone, PartialEq)]
265pub enum Function {
266    Internal(InternalFunctionDefinitionRef),
267    External(ExternalFunctionDefinitionRef),
268}
269
270impl Function {
271    #[must_use]
272    pub fn name(&self) -> String {
273        match self {
274            Self::Internal(x) => x.assigned_name.clone(),
275            Self::External(y) => y.assigned_name.clone(),
276        }
277    }
278
279    #[must_use]
280    pub fn maybe_node(&self) -> Option<&Node> {
281        match self {
282            Self::Internal(x) => Some(&x.name.0),
283            Self::External(y) => y.name.as_ref(),
284        }
285    }
286
287    #[must_use]
288    pub fn node(&self) -> Node {
289        match self {
290            Self::Internal(x) => x.name.0.clone(),
291            Self::External(_y) => Node::new_unknown(),
292        }
293    }
294
295    #[must_use]
296    pub fn signature(&self) -> &Signature {
297        match self {
298            Self::Internal(internal) => &internal.signature,
299            Self::External(external) => &external.signature,
300        }
301    }
302}
303
304#[derive(Debug, Clone)]
305pub struct BooleanExpression {
306    #[allow(unused)]
307    pub expression: Box<Expression>,
308}
309
310#[derive(Debug, Clone)]
311pub struct Match {
312    pub arms: Vec<MatchArm>,
313    pub expression: Box<MutOrImmutableExpression>,
314}
315
316#[derive(Debug, Clone)]
317pub struct MatchArm {
318    #[allow(unused)]
319    pub pattern: Pattern,
320    pub expression: Box<Expression>,
321    pub expression_type: Type,
322}
323
324#[derive(Debug, Clone)]
325pub enum Pattern {
326    Normal(NormalPattern, Option<BooleanExpression>),
327    Wildcard(Node),
328}
329
330#[derive(Debug, Clone)]
331pub enum NormalPattern {
332    PatternList(Vec<PatternElement>),
333    EnumPattern(EnumVariantType, Option<Vec<PatternElement>>),
334    Literal(Literal),
335}
336
337#[derive(Debug, Clone)]
338pub enum PatternElement {
339    Variable(VariableRef),
340    VariableWithFieldIndex(VariableRef, usize),
341    Wildcard(Node),
342}
343
344#[derive(Debug, Clone)]
345pub struct Iterable {
346    pub key_type: Option<Type>, // It does not have to support a key type
347    pub value_type: Type,
348
349    pub resolved_expression: Box<MutOrImmutableExpression>,
350}
351
352#[derive(Debug, Clone)]
353pub struct StructInstantiation {
354    pub source_order_expressions: Vec<(usize, Expression)>,
355    pub struct_type_ref: NamedStructType,
356}
357
358#[derive(Debug, Clone)]
359pub struct AnonymousStructLiteral {
360    pub source_order_expressions: Vec<(usize, Expression)>,
361    pub anonymous_struct_type: AnonymousStructType,
362}
363
364#[derive(Debug, Clone, Eq, PartialEq)]
365pub enum CompoundOperatorKind {
366    Add,
367    Sub,
368    Mul,
369    Div,
370    Modulo,
371}
372
373#[derive(Debug, Clone)]
374pub struct CompoundOperator {
375    pub node: Node,
376    pub kind: CompoundOperatorKind,
377}
378
379#[derive(Debug, Clone)]
380pub struct VariableCompoundAssignment {
381    pub variable_ref: VariableRef, // compound only support single variable
382    pub expression: Box<Expression>,
383    pub compound_operator: CompoundOperator,
384}
385
386pub fn create_rust_type(name: &str, external_number: u32) -> ExternalType {
387    ExternalType {
388        type_name: name.to_string(),
389        number: external_number,
390    }
391}
392
393#[derive(Debug, Clone)]
394pub struct Guard {
395    pub condition: Option<BooleanExpression>,
396    pub result: Expression,
397}
398
399#[derive(Debug, Clone, Eq, PartialEq)]
400pub enum RangeMode {
401    Inclusive,
402    Exclusive,
403}
404
405#[derive(Debug, Clone)]
406pub struct Postfix {
407    pub node: Node,
408    pub ty: Type,
409    pub kind: PostfixKind,
410}
411
412#[derive(Debug, Clone)]
413pub struct Range {
414    pub min: Expression,
415    pub max: Expression,
416    pub mode: RangeMode,
417}
418
419#[derive(Debug, Clone)]
420pub enum PostfixKind {
421    StructField(AnonymousStructType, usize),
422    //    ExternalTypeIndexRef(ExternalTypeRef, Expression),
423    MemberCall(FunctionRef, Vec<ArgumentExpressionOrLocation>),
424    FunctionCall(Vec<ArgumentExpressionOrLocation>),
425    OptionUnwrap, // ? operator
426    NoneCoalesce(Expression),
427    //IntrinsicCallEx(IntrinsicFunction, Vec<ArgumentExpressionOrLocation>),
428    IntrinsicCall(IntrinsicFunction, Vec<Expression>),
429}
430
431#[derive(Debug, Clone)]
432pub enum LocationAccessKind {
433    FieldIndex(AnonymousStructType, usize),
434    IntrinsicCallMut(IntrinsicFunction, Vec<Expression>),
435}
436
437#[derive(Debug, Clone)]
438pub struct LocationAccess {
439    pub node: Node,
440    pub ty: Type,
441    pub kind: LocationAccessKind,
442}
443
444#[derive(Debug, Clone)]
445pub struct SingleLocationExpression {
446    pub kind: SingleLocationExpressionKind,
447    pub node: Node,
448    pub ty: Type,
449
450    pub starting_variable: VariableRef,
451    pub access_chain: Vec<LocationAccess>,
452}
453
454#[derive(Debug, Clone)]
455pub struct SingleMutLocationExpression(pub SingleLocationExpression);
456
457#[derive(Debug, Clone)]
458pub enum SingleLocationExpressionKind {
459    MutVariableRef,
460    MutStructFieldRef(NamedStructType, usize),
461}
462
463#[derive(Debug, Clone)]
464pub struct SliceLocationExpression {
465    pub start: Box<Expression>,
466    pub range_start: Box<Expression>,
467    pub range_end: Box<Expression>,
468    pub mode: RangeMode,
469    pub ty: Type,
470}
471
472#[derive(Debug, Clone)]
473pub struct MutOrImmutableExpression {
474    pub expression_or_location: ArgumentExpressionOrLocation,
475    pub is_mutable: Option<Node>,
476}
477
478impl MutOrImmutableExpression {
479    pub fn expect_immutable(self) -> Result<Expression, SemanticError> {
480        match self.expression_or_location {
481            ArgumentExpressionOrLocation::Expression(expr) => Ok(expr),
482            ArgumentExpressionOrLocation::Location(_) => Err(SemanticError::WasNotImmutable),
483        }
484    }
485
486    pub fn expect_immutable_ref(&self) -> Result<&Expression, SemanticError> {
487        match &self.expression_or_location {
488            ArgumentExpressionOrLocation::Expression(expr) => Ok(expr),
489            ArgumentExpressionOrLocation::Location(_) => Err(SemanticError::WasNotImmutable),
490        }
491    }
492
493    pub fn ty(&self) -> &Type {
494        match &self.expression_or_location {
495            ArgumentExpressionOrLocation::Expression(expr) => &expr.ty,
496            ArgumentExpressionOrLocation::Location(loc) => &loc.ty,
497        }
498    }
499}
500
501#[derive(Debug, Clone)]
502pub enum ArgumentExpressionOrLocation {
503    Expression(Expression),
504    Location(SingleLocationExpression),
505}
506
507#[derive(Clone)]
508pub struct Expression {
509    pub ty: Type,
510    pub node: Node,
511    pub kind: ExpressionKind,
512}
513
514impl Debug for Expression {
515    fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::result::Result<(), std::fmt::Error> {
516        write!(f, "{:?}{},{:?}", self.node, self.ty, self.kind)
517    }
518}
519
520#[derive(Debug, Clone)]
521pub struct WhenBinding {
522    pub variable: VariableRef,
523    pub expr: MutOrImmutableExpression,
524}
525
526#[derive(Debug, Clone)]
527pub enum ExpressionKind {
528    // Access Lookup values
529    ConstantAccess(ConstantRef),
530    VariableAccess(VariableRef),
531    FieldAccess(Box<Expression>, usize),
532    ArrayAccess(
533        Box<Expression>,
534        Type,
535        Box<Expression>, // int index lookup
536    ), // Read from an array: arr[3]
537    MapIndexAccess(Box<Expression>, Type, Type, Box<Expression>),
538    StringRangeAccess(Box<Expression>, Box<Range>),
539    ArrayRangeAccess(Box<Expression>, Box<Range>),
540
541    // ----
542    IntrinsicFunctionAccess(IntrinsicFunctionDefinitionRef),
543    InternalFunctionAccess(InternalFunctionDefinitionRef),
544    ExternalFunctionAccess(ExternalFunctionDefinitionRef),
545
546    // Adding to a collection
547    MapAssignment(
548        Box<SingleMutLocationExpression>,
549        Box<Expression>,
550        Box<Expression>,
551    ), // Motivation: Can not use location since adding is more complex
552
553    // Operators
554    BinaryOp(BinaryOperator),
555    UnaryOp(UnaryOperator),
556    PostfixChain(Box<Expression>, Vec<Postfix>),
557
558    // Conversion
559    // the `?` operator. unwraps the value, unless it is none
560    //NoneCoalesceOperator(Box<Expression>, Box<Expression>),
561    CoerceOptionToBool(Box<Expression>),
562
563    // Calls
564
565    // For calls from returned function values
566    FunctionCall(
567        Signature,
568        Box<Expression>,
569        Vec<ArgumentExpressionOrLocation>,
570    ),
571
572    //MemberCall(MemberCall),
573    InterpolatedString(Vec<StringPart>),
574
575    // Constructing
576    VariableDefinition(VariableRef, Box<MutOrImmutableExpression>), // First time assignment
577    VariableReassignment(VariableRef, Box<MutOrImmutableExpression>),
578
579    StructInstantiation(StructInstantiation),
580    AnonymousStructLiteral(AnonymousStructLiteral),
581    Array(ArrayInstantiation),
582    Tuple(Vec<Expression>),
583    Literal(Literal),
584    Option(Option<Box<Expression>>), // Wrapping an expression in `Some()`
585    Range(Box<Expression>, Box<Expression>, RangeMode),
586
587    // Control
588    ForLoop(ForPattern, Iterable, Box<Expression>),
589    WhileLoop(BooleanExpression, Box<Expression>),
590    Return(Option<Box<Expression>>),
591    Break,
592    Continue, //
593
594    Block(Vec<Expression>),
595
596    // Match and compare
597    Match(Match),
598    Guard(Vec<Guard>),
599    If(BooleanExpression, Box<Expression>, Option<Box<Expression>>),
600
601    When(Vec<WhenBinding>, Box<Expression>, Option<Box<Expression>>),
602
603    TupleDestructuring(Vec<VariableRef>, Vec<Type>, Box<Expression>),
604
605    Assignment(Box<SingleMutLocationExpression>, Box<Expression>),
606    AssignmentSlice(Box<SliceLocationExpression>, Box<Expression>),
607    CompoundAssignment(
608        SingleMutLocationExpression,
609        CompoundOperatorKind,
610        Box<Expression>,
611    ),
612
613    // --------------------------------------------------------------------
614    // Built In members
615    // --------------------------------------------------------------------
616    IntrinsicCallMut(
617        IntrinsicFunction,
618        SingleMutLocationExpression,
619        Vec<Expression>,
620    ),
621
622    //IntrinsicCall(IntrinsicFunction, Vec<Expression>),
623    IntrinsicCallEx(IntrinsicFunction, Vec<ArgumentExpressionOrLocation>),
624}
625
626#[derive(Debug, Clone)]
627pub struct StringConst(pub Node);
628
629#[derive(Debug, Clone)]
630pub enum Literal {
631    FloatLiteral(Fp),
632    NoneLiteral,
633    IntLiteral(i32),
634    StringLiteral(String),
635    BoolLiteral(bool),
636
637    EnumVariantLiteral(EnumVariantType, EnumLiteralData),
638    TupleLiteral(Vec<Type>, Vec<Expression>),
639
640    Slice(Type, Vec<Expression>),
641    SlicePair(Type, Vec<(Expression, Expression)>),
642}
643
644#[derive(Debug, Clone)]
645pub struct ArrayInstantiation {
646    pub expressions: Vec<Expression>,
647    pub item_type: Type,
648    pub array_type: Type,
649    pub array_type_ref: Type,
650}
651
652#[derive(Debug, Clone)]
653pub enum ForPattern {
654    Single(VariableRef),
655    Pair(VariableRef, VariableRef),
656}
657
658impl ForPattern {
659    #[must_use]
660    pub fn is_mutable(&self) -> bool {
661        match self {
662            Self::Single(variable) => variable.is_mutable(),
663            Self::Pair(a, b) => a.is_mutable() || b.is_mutable(),
664        }
665    }
666}
667
668impl Display for ForPattern {
669    fn fmt(&self, f: &mut Formatter<'_>) -> fmt::Result {
670        write!(f, "resolved_for_pattern")
671    }
672}
673
674#[derive(Debug, Eq, PartialEq)]
675pub struct ModulePathItem(pub Node);
676
677#[derive(Debug, Clone, Eq, PartialEq)]
678pub struct LocalTypeIdentifier(pub Node);
679
680#[derive(Debug, Clone)]
681pub struct Constant {
682    pub name: Node,
683    pub assigned_name: String,
684    pub id: ConstantId,
685    pub expr: Expression,
686    pub resolved_type: Type,
687}
688pub type ConstantRef = Rc<Constant>;
689
690pub type OptionTypeRef = Rc<crate::OptionType>;
691
692#[derive(Debug, Clone)]
693pub struct OptionType {
694    pub item_type: Type,
695}
696
697/*
698pub fn sort_struct_fields(
699    unordered_seq_map: &SeqMap<String, StructTypeField>,
700) -> SeqMap<String, StructTypeField> {
701    let mut sorted_pairs: Vec<(&String, &StructTypeField)> = unordered_seq_map.iter().collect();
702    sorted_pairs.sort_by(|a, b| a.0.cmp(b.0));
703    let mut ordered_seq_map = SeqMap::new();
704
705    for (name, field) in sorted_pairs {
706        ordered_seq_map.insert(name, field).unwrap() // We know already that the key fields are unique
707    }
708
709    ordered_seq_map
710}
711
712 */
713
714#[derive(Debug, Clone)]
715pub struct ImplMember {}
716
717#[derive(Debug, Clone)]
718pub enum UseItem {
719    Identifier(Node),
720    TypeIdentifier(Node),
721}
722
723#[derive(Debug, Clone)]
724pub struct Use {
725    pub path: Vec<Node>,
726    pub items: Vec<UseItem>,
727}
728
729#[derive(Debug, Clone)]
730pub struct ImplFunctions {
731    pub functions: SeqMap<String, FunctionRef>,
732}
733
734impl Default for ImplFunctions {
735    fn default() -> Self {
736        Self::new()
737    }
738}
739
740impl ImplFunctions {
741    #[must_use]
742    pub fn new() -> Self {
743        Self {
744            functions: SeqMap::default(),
745        }
746    }
747}
748
749#[derive(Debug, Clone)]
750pub struct AssociatedImpls {
751    pub functions: SeqMap<Type, ImplFunctions>,
752}
753
754impl Default for AssociatedImpls {
755    fn default() -> Self {
756        Self::new()
757    }
758}
759
760impl AssociatedImpls {
761    #[must_use]
762    pub fn new() -> Self {
763        Self {
764            functions: SeqMap::default(),
765        }
766    }
767}
768
769impl AssociatedImpls {
770    pub fn prepare(&mut self, ty: &Type) {
771        self.functions
772            .insert(ty.clone(), ImplFunctions::new())
773            .expect("should work");
774    }
775    #[must_use]
776    pub fn get_member_function(&self, ty: &Type, function_name: &str) -> Option<&FunctionRef> {
777        let maybe_found_impl = self.functions.get(&ty);
778        if let Some(found_impl) = maybe_found_impl {
779            if let Some(func) = found_impl.functions.get(&function_name.to_string()) {
780                return Some(func);
781            }
782        }
783        None
784    }
785
786    pub fn api_get_external_function(
787        &self,
788        ty: &Type,
789        function_name: &str,
790    ) -> Option<&ExternalFunctionDefinitionRef> {
791        if let Some(found) = self.get_member_function(ty, function_name) {
792            if let Function::External(ext_fn) = &**found {
793                return Some(ext_fn);
794            }
795        }
796        None
797    }
798
799    pub fn api_fetch_external_function_id(
800        &self,
801        ty: &Type,
802        function_name: &str,
803    ) -> ExternalFunctionId {
804        self.api_get_external_function(ty, function_name)
805            .unwrap()
806            .id
807    }
808
809    pub fn get_internal_member_function(
810        &self,
811        ty: &Type,
812        function_name: &str,
813    ) -> Option<&InternalFunctionDefinitionRef> {
814        if let Some(found) = self.get_member_function(ty, function_name) {
815            if let Function::Internal(int_fn) = &**found {
816                return Some(int_fn);
817            }
818        }
819        None
820    }
821
822    pub fn add_member_function(
823        &mut self,
824        ty: &Type,
825        name: &str,
826        func: FunctionRef,
827    ) -> Result<(), SemanticError> {
828        let maybe_found_impl = self.functions.get_mut(&ty);
829
830        if let Some(found_impl) = maybe_found_impl {
831            found_impl
832                .functions
833                .insert(name.to_string(), func)
834                .expect("todo");
835            Ok(())
836        } else {
837            error!(%ty, ?name, "wasn't prepared");
838            Err(SemanticError::UnknownImplOnType)
839        }
840    }
841
842    pub fn add_external_member_function(
843        &mut self,
844        ty: &Type,
845        func: ExternalFunctionDefinition,
846    ) -> Result<(), SemanticError> {
847        self.add_member_function(
848            ty,
849            &func.assigned_name.clone(),
850            Function::External(func.into()).into(),
851        )
852    }
853
854    pub fn add_external_struct_member_function(
855        &mut self,
856        named_struct_type: &NamedStructType,
857        func: Function,
858    ) -> Result<(), SemanticError> {
859        self.add_member_function(
860            &Type::NamedStruct(named_struct_type.clone()),
861            &func.name().clone(),
862            func.into(),
863        )
864    }
865
866    pub fn add_external_struct_member_function_external(
867        &mut self,
868        named_struct_type: NamedStructType,
869        func: ExternalFunctionDefinition,
870    ) -> Result<(), SemanticError> {
871        self.add_member_function(
872            &Type::NamedStruct(named_struct_type.clone()),
873            &func.assigned_name.clone(),
874            Function::External(func.into()).into(),
875        )
876    }
877
878    pub fn add_external_struct_member_function_external_ref(
879        &mut self,
880        named_struct_type: NamedStructType,
881        func: ExternalFunctionDefinitionRef,
882    ) -> Result<(), SemanticError> {
883        self.add_member_function(
884            &Type::NamedStruct(named_struct_type.clone()),
885            &func.assigned_name.clone(),
886            Function::External(func.into()).into(),
887        )
888    }
889}
890
891// Mutable part
892#[derive(Debug, Clone)]
893pub struct ProgramState {
894    pub external_function_number: ExternalFunctionId,
895    // It is just so we don't have to do another dependency check of the
896    // modules, we know that these constants have been
897    // evaluated in order already
898    pub constants_in_dependency_order: Vec<ConstantRef>,
899    pub associated_impls: AssociatedImpls,
900    pub instantiation_cache: InstantiationCache,
901}
902
903impl Default for ProgramState {
904    fn default() -> Self {
905        Self::new()
906    }
907}
908
909impl ProgramState {
910    #[must_use]
911    pub fn new() -> Self {
912        Self {
913            external_function_number: 0,
914            constants_in_dependency_order: Vec::new(),
915            associated_impls: AssociatedImpls::new(),
916            instantiation_cache: InstantiationCache::new(),
917        }
918    }
919
920    pub fn allocate_external_function_id(&mut self) -> ExternalFunctionId {
921        self.external_function_number += 1;
922        self.external_function_number
923    }
924}
925
926#[derive(Clone)]
927pub enum EnumLiteralData {
928    Nothing,
929    Tuple(Vec<Expression>),
930    Struct(Vec<(usize, Expression)>),
931}
932
933impl Debug for EnumLiteralData {
934    fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::result::Result<(), std::fmt::Error> {
935        match self {
936            Self::Nothing => Ok(()),
937            Self::Tuple(x) => write!(f, "{x:?}"),
938            Self::Struct(s) => write!(f, "{s:?}"),
939        }
940    }
941}