ast: add gens for ty and impl, raw ptr types, make fn return value non-optional
This commit is contained in:
@@ -28,6 +28,11 @@ impl fmt::Display for Entry<'_, '_> {
|
||||
let h_id = self.with_id(id);
|
||||
write_name_or(h_id, f)
|
||||
}
|
||||
&TypeKind::Ptr(id) => {
|
||||
f.write_str("*")?;
|
||||
let h_id = self.with_id(id);
|
||||
write_name_or(h_id, f)
|
||||
}
|
||||
TypeKind::Slice(id) => {
|
||||
write_name_or(self.with_id(*id), &mut f.delimit_with("[", "]"))
|
||||
}
|
||||
@@ -66,10 +71,7 @@ fn write_adt(adt: &Adt, h: &Entry, f: &mut impl Write) -> fmt::Result {
|
||||
let mut variants = variants.iter();
|
||||
separate(", ", || {
|
||||
variants.next().map(|(name, def)| {
|
||||
move |f: &mut Delimit<_>| {
|
||||
write!(f, "{name}: ")?;
|
||||
write_name_or(h.with_id(*def), f)
|
||||
}
|
||||
move |f: &mut Delimit<_>| write!(f, "{name}: {}", h.with_id(*def))
|
||||
})
|
||||
})(f.delimit_with("enum {", "}"))
|
||||
}
|
||||
@@ -77,20 +79,14 @@ fn write_adt(adt: &Adt, h: &Entry, f: &mut impl Write) -> fmt::Result {
|
||||
let mut members = members.iter();
|
||||
separate(", ", || {
|
||||
let (name, vis, id) = members.next()?;
|
||||
Some(move |f: &mut Delimit<_>| {
|
||||
write!(f, "{vis}{name}: ")?;
|
||||
write_name_or(h.with_id(*id), f)
|
||||
})
|
||||
Some(move |f: &mut Delimit<_>| write!(f, "{vis}{name}: {}", h.with_id(*id)))
|
||||
})(f.delimit_with("struct {", "}"))
|
||||
}
|
||||
Adt::TupleStruct(members) => {
|
||||
let mut members = members.iter();
|
||||
separate(", ", || {
|
||||
let (vis, def) = members.next()?;
|
||||
Some(move |f: &mut Delimit<_>| {
|
||||
write!(f, "{vis}")?;
|
||||
write_name_or(h.with_id(*def), f)
|
||||
})
|
||||
Some(move |f: &mut Delimit<_>| write!(f, "{vis}{}", h.with_id(*def)))
|
||||
})(f.delimit_with("struct (", ")"))
|
||||
}
|
||||
Adt::UnitStruct => write!(f, "struct"),
|
||||
|
||||
@@ -70,7 +70,7 @@ fn import_tree<'a>(
|
||||
UseTree::Path(part, rest) => {
|
||||
let source = table
|
||||
.nav(src, slice::from_ref(part))
|
||||
.ok_or_else(|| Error::NotFound(src, part.clone()))?;
|
||||
.ok_or(Error::NotFound(src, *part))?;
|
||||
import_tree(table, source, dst, rest, seen)
|
||||
}
|
||||
UseTree::Alias(src_name, dst_name) => {
|
||||
|
||||
@@ -496,6 +496,7 @@ impl<'table, 'a> InferenceEngine<'table, 'a> {
|
||||
todo!()
|
||||
}
|
||||
(TypeKind::Ref(a), TypeKind::Ref(b)) => self.unify(*a, *b),
|
||||
(TypeKind::Ptr(a), TypeKind::Ptr(b)) => self.unify(*a, *b),
|
||||
(TypeKind::Slice(a), TypeKind::Slice(b)) => self.unify(*a, *b),
|
||||
// Slice unifies with array
|
||||
(TypeKind::Array(a, _), TypeKind::Slice(b)) => self.unify(*a, *b),
|
||||
|
||||
@@ -121,7 +121,7 @@ impl<'a> Table<'a> {
|
||||
self.impls.push(item);
|
||||
}
|
||||
|
||||
pub fn handle_iter(&mut self) -> impl Iterator<Item = Handle> + use<> {
|
||||
pub fn handle_iter(&self) -> impl Iterator<Item = Handle> + use<> {
|
||||
self.kinds.keys()
|
||||
}
|
||||
|
||||
|
||||
@@ -2,7 +2,7 @@
|
||||
//! construct type bindings in a [Table]'s typing context.
|
||||
|
||||
use crate::{handle::Handle, table::Table, type_kind::TypeKind};
|
||||
use cl_ast::{PathPart, Ty, TyArray, TyFn, TyKind, TyRef, TySlice, TyTuple};
|
||||
use cl_ast::{PathPart, Sym, Ty, TyArray, TyFn, TyKind, TyPtr, TyRef, TySlice, TyTuple};
|
||||
|
||||
#[derive(Clone, Debug, PartialEq, Eq)] // TODO: impl Display and Error
|
||||
pub enum Error {
|
||||
@@ -48,6 +48,7 @@ impl TypeExpression for TyKind {
|
||||
TyKind::Slice(s) => s.evaluate(table, node),
|
||||
TyKind::Tuple(t) => t.evaluate(table, node),
|
||||
TyKind::Ref(r) => r.evaluate(table, node),
|
||||
TyKind::Ptr(r) => r.evaluate(table, node),
|
||||
TyKind::Fn(f) => f.evaluate(table, node),
|
||||
}
|
||||
}
|
||||
@@ -68,6 +69,15 @@ impl TypeExpression for [PathPart] {
|
||||
}
|
||||
}
|
||||
|
||||
impl TypeExpression for Sym {
|
||||
fn evaluate(&self, table: &mut Table, node: Handle) -> Result<Handle, Error> {
|
||||
let path = [PathPart::Ident(*self)];
|
||||
table
|
||||
.nav(node, &path)
|
||||
.ok_or_else(|| Error::BadPath { parent: node, path: path.to_vec() })
|
||||
}
|
||||
}
|
||||
|
||||
impl TypeExpression for TyArray {
|
||||
fn evaluate(&self, table: &mut Table, node: Handle) -> Result<Handle, Error> {
|
||||
let Self { ty, count } = self;
|
||||
@@ -107,15 +117,21 @@ impl TypeExpression for TyRef {
|
||||
}
|
||||
}
|
||||
|
||||
impl TypeExpression for TyPtr {
|
||||
fn evaluate(&self, table: &mut Table, node: Handle) -> Result<Handle, Error> {
|
||||
let Self { to } = self;
|
||||
let mut t = to.evaluate(table, node)?;
|
||||
t = table.anon_type(TypeKind::Ptr(t));
|
||||
Ok(t)
|
||||
}
|
||||
}
|
||||
|
||||
impl TypeExpression for TyFn {
|
||||
fn evaluate(&self, table: &mut Table, node: Handle) -> Result<Handle, Error> {
|
||||
let Self { args, rety } = self;
|
||||
let kind = TypeKind::FnSig {
|
||||
args: args.evaluate(table, node)?,
|
||||
rety: match rety {
|
||||
Some(ty) => ty.evaluate(table, node)?,
|
||||
None => TyKind::Empty.evaluate(table, node)?,
|
||||
},
|
||||
rety: rety.evaluate(table, node)?,
|
||||
};
|
||||
Ok(table.anon_type(kind))
|
||||
}
|
||||
|
||||
@@ -22,6 +22,8 @@ pub enum TypeKind {
|
||||
Adt(Adt),
|
||||
/// A reference to an already-defined type: &T
|
||||
Ref(Handle),
|
||||
/// A raw pointer to an already-defined type: &T
|
||||
Ptr(Handle),
|
||||
/// A contiguous view of dynamically sized memory
|
||||
Slice(Handle),
|
||||
/// A contiguous view of statically sized memory
|
||||
@@ -67,6 +69,7 @@ pub enum Primitive {
|
||||
Integer, Float, // Inferred int and float
|
||||
Bool, // boolean value
|
||||
Char, // Unicode codepoint
|
||||
Str, // UTF-8 string
|
||||
}
|
||||
|
||||
#[rustfmt::skip]
|
||||
@@ -117,6 +120,7 @@ impl FromStr for Primitive {
|
||||
"fsize" => Primitive::Fsize,
|
||||
"bool" => Primitive::Bool,
|
||||
"char" => Primitive::Char,
|
||||
"str" => Primitive::Str,
|
||||
_ => Err(())?,
|
||||
})
|
||||
}
|
||||
|
||||
@@ -14,6 +14,7 @@ impl Display for TypeKind {
|
||||
TypeKind::Primitive(i) => i.fmt(f),
|
||||
TypeKind::Adt(a) => a.fmt(f),
|
||||
TypeKind::Ref(def) => write!(f, "&{def}"),
|
||||
TypeKind::Ptr(def) => write!(f, "*{def}"),
|
||||
TypeKind::Slice(def) => write!(f, "slice [#{def}]"),
|
||||
TypeKind::Array(def, size) => write!(f, "array [#{def}; {size}]"),
|
||||
TypeKind::Tuple(defs) => {
|
||||
@@ -92,6 +93,7 @@ impl Display for Primitive {
|
||||
Primitive::Float => f.write_str("{float}"),
|
||||
Primitive::Bool => f.write_str("bool"),
|
||||
Primitive::Char => f.write_str("char"),
|
||||
Primitive::Str => f.write_str("str"),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user