cl_typeck/entry/
display.rs1use super::*;
2use crate::{format_utils::*, type_kind::Adt};
3use std::fmt::{self, Write};
4
5fn write_name_or(h: Entry, f: &mut impl Write) -> fmt::Result {
7 match h.name() {
8 Some(name) => write!(f, "{name}"),
9 None => write!(f, "{h}"),
10 }
11}
12
13impl fmt::Display for Entry<'_, '_> {
14 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
15 let Some(&kind) = self.kind() else {
16 return write!(f, "<invalid type: {}>", self.id);
17 };
18
19 if let Some(ty) = self.ty() {
20 match ty {
21 TypeKind::Inferred => write!(f, "<_{}>", self.id),
22 TypeKind::Variable => write!(f, "<?{}>", self.id),
23 TypeKind::Instance(id) => write!(f, "{}", self.with_id(*id)),
24 TypeKind::Primitive(kind) => write!(f, "{kind}"),
25 TypeKind::Adt(adt) => write_adt(adt, self, f),
26 &TypeKind::Ref(id) => {
27 f.write_str("&")?;
28 let h_id = self.with_id(id);
29 write_name_or(h_id, f)
30 }
31 &TypeKind::Ptr(id) => {
32 f.write_str("*")?;
33 let h_id = self.with_id(id);
34 write_name_or(h_id, f)
35 }
36 TypeKind::Slice(id) => {
37 write_name_or(self.with_id(*id), &mut f.delimit_with("[", "]"))
38 }
39 &TypeKind::Array(t, cnt) => {
40 let mut f = f.delimit_with("[", "]");
41 write_name_or(self.with_id(t), &mut f)?;
42 write!(f, "; {cnt}")
43 }
44 TypeKind::Tuple(ids) => {
45 let mut f = f.delimit_with("(", ")");
46 for (index, &id) in ids.iter().enumerate() {
47 if index > 0 {
48 write!(f, ", ")?;
49 }
50 write_name_or(self.with_id(id), &mut f)?;
51 }
52 Ok(())
53 }
54 TypeKind::FnSig { args, rety } => {
55 write!(f, "fn {} -> ", self.with_id(*args))?;
56 write_name_or(self.with_id(*rety), f)
57 }
58 TypeKind::Module => write!(f, "module?"),
59 }
60 } else {
61 match kind {
62 NodeKind::Type
63 | NodeKind::Const
64 | NodeKind::Static
65 | NodeKind::Temporary
66 | NodeKind::Let => write!(f, "WARNING: NO TYPE ASSIGNED FOR {}", self.id),
67 _ => write!(f, "{kind}"),
68 }
69 }
70 }
71}
72
73fn write_adt(adt: &Adt, h: &Entry, f: &mut impl Write) -> fmt::Result {
74 match adt {
75 Adt::Enum(variants) => {
76 let mut variants = variants.iter();
77 separate(", ", || {
78 variants.next().map(|(name, def)| {
79 move |f: &mut Delimit<_>| write!(f, "{name}: {}", h.with_id(*def))
80 })
81 })(f.delimit_with("enum {", "}"))
82 }
83 Adt::Struct(members) => {
84 let mut members = members.iter();
85 separate(", ", || {
86 let (name, vis, id) = members.next()?;
87 Some(move |f: &mut Delimit<_>| write!(f, "{vis}{name}: {}", h.with_id(*id)))
88 })(f.delimit_with("struct {", "}"))
89 }
90 Adt::TupleStruct(members) => {
91 let mut members = members.iter();
92 separate(", ", || {
93 let (vis, def) = members.next()?;
94 Some(move |f: &mut Delimit<_>| write!(f, "{vis}{}", h.with_id(*def)))
95 })(f.delimit_with("struct (", ")"))
96 }
97 Adt::UnitStruct => write!(f, "struct"),
98 Adt::Union(_) => todo!("Display union types"),
99 }
100}