cl-ast: Don't store type metadata in TyTuple. Allow arbitrary TyKind in TyFn args.

This commit is contained in:
John 2024-04-14 23:16:35 -05:00
parent 0fab11c11b
commit d0ed8309f4
2 changed files with 25 additions and 12 deletions

View File

@ -238,7 +238,7 @@ pub enum TyKind {
/// A tuple of [Ty]pes /// A tuple of [Ty]pes
#[derive(Clone, Debug, PartialEq, Eq, Hash)] #[derive(Clone, Debug, PartialEq, Eq, Hash)]
pub struct TyTuple { pub struct TyTuple {
pub types: Vec<Ty>, pub types: Vec<TyKind>,
} }
/// A [Ty]pe-reference expression as (number of `&`, [Path]) /// A [Ty]pe-reference expression as (number of `&`, [Path])
@ -251,7 +251,7 @@ pub struct TyRef {
/// The args and return value for a function pointer [Ty]pe /// The args and return value for a function pointer [Ty]pe
#[derive(Clone, Debug, PartialEq, Eq, Hash)] #[derive(Clone, Debug, PartialEq, Eq, Hash)]
pub struct TyFn { pub struct TyFn {
pub args: TyTuple, pub args: Box<TyKind>,
pub rety: Option<Box<Ty>>, pub rety: Option<Box<Ty>>,
} }

View File

@ -631,7 +631,13 @@ impl<'t> Parser<'t> {
TyKind::SelfTy TyKind::SelfTy
} }
TokenKind::Punct(Punct::Amp) | TokenKind::Punct(Punct::AmpAmp) => self.tyref()?.into(), TokenKind::Punct(Punct::Amp) | TokenKind::Punct(Punct::AmpAmp) => self.tyref()?.into(),
TokenKind::Punct(Punct::LParen) => self.tytuple()?.into(), TokenKind::Punct(Punct::LParen) => {
let out = self.tytuple()?;
match out.types.is_empty() {
true => TyKind::Empty,
false => TyKind::Tuple(out),
}
}
TokenKind::Fn => self.tyfn()?.into(), TokenKind::Fn => self.tyfn()?.into(),
path_like!() => self.path()?.into(), path_like!() => self.path()?.into(),
t => Err(self.error(Unexpected(t), PARSING))?, t => Err(self.error(Unexpected(t), PARSING))?,
@ -644,7 +650,7 @@ impl<'t> Parser<'t> {
const PARSING: Parsing = Parsing::TyTuple; const PARSING: Parsing = Parsing::TyTuple;
Ok(TyTuple { Ok(TyTuple {
types: delim( types: delim(
sep(Self::ty, Punct::Comma, PARENS.1, PARSING), sep(Self::tykind, Punct::Comma, PARENS.1, PARSING),
PARENS, PARENS,
PARSING, PARSING,
)(self)?, )(self)?,
@ -668,19 +674,26 @@ impl<'t> Parser<'t> {
pub fn tyfn(&mut self) -> PResult<TyFn> { pub fn tyfn(&mut self) -> PResult<TyFn> {
const PARSING: Parsing = Parsing::TyFn; const PARSING: Parsing = Parsing::TyFn;
self.match_type(TokenKind::Fn, PARSING)?; self.match_type(TokenKind::Fn, PARSING)?;
Ok(TyFn { Ok(TyFn {
args: self.tytuple()?, args: Box::new(match self.tyfn_args()? {
rety: { t if t.is_empty() => TyKind::Empty,
match self.peek_kind(PARSING)? { types => TyKind::Tuple(TyTuple { types }),
TokenKind::Punct(Punct::Arrow) => { }),
self.consume_peeked(); rety: match self.peek_kind(PARSING) {
Some(self.ty()?.into()) Ok(TokenKind::Punct(Punct::Arrow)) => {
} self.consume_peeked();
_ => None, Some(self.ty()?.into())
} }
_ => None,
}, },
}) })
} }
pub fn tyfn_args(&mut self) -> PResult<Vec<TyKind>> {
const P: Parsing = Parsing::TyFn;
delim(sep(Self::tykind, Punct::Comma, PARENS.1, P), PARENS, P)(self)
}
} }
/// Expands to a pattern which matches literal-like [TokenKind]s /// Expands to a pattern which matches literal-like [TokenKind]s