diff --git a/compiler/noirc_frontend/src/parser/errors.rs b/compiler/noirc_frontend/src/parser/errors.rs index bcb4ce1c616..899928528e6 100644 --- a/compiler/noirc_frontend/src/parser/errors.rs +++ b/compiler/noirc_frontend/src/parser/errors.rs @@ -19,6 +19,8 @@ pub enum ParserErrorReason { UnexpectedComma, #[error("Expected a `{token}` separating these two {items}")] ExpectedTokenSeparatingTwoItems { token: Token, items: &'static str }, + #[error("Expected `mut` after `&`, found `{found}`")] + ExpectedMutAfterAmpersand { found: Token }, #[error("Invalid left-hand side of assignment")] InvalidLeftHandSideOfAssignment, #[error("Expected trait, found {found}")] @@ -265,6 +267,11 @@ impl<'a> From<&'a ParserError> for Diagnostic { error.span, ), ParserErrorReason::Lexer(error) => error.into(), + ParserErrorReason::ExpectedMutAfterAmpersand { found } => Diagnostic::simple_error( + format!("Expected `mut` after `&`, found `{found}`"), + "Noir doesn't have immutable references, only mutable references".to_string(), + error.span, + ), other => Diagnostic::simple_error(format!("{other}"), String::new(), error.span), }, None => { diff --git a/compiler/noirc_frontend/src/parser/parser.rs b/compiler/noirc_frontend/src/parser/parser.rs index f369839ddd4..c2f7b781873 100644 --- a/compiler/noirc_frontend/src/parser/parser.rs +++ b/compiler/noirc_frontend/src/parser/parser.rs @@ -498,6 +498,13 @@ impl<'a> Parser<'a> { self.push_error(ParserErrorReason::ExpectedTokenSeparatingTwoItems { token, items }, span); } + fn expected_mut_after_ampersand(&mut self) { + self.push_error( + ParserErrorReason::ExpectedMutAfterAmpersand { found: self.token.token().clone() }, + self.current_token_span, + ); + } + fn modifiers_not_followed_by_an_item(&mut self, modifiers: Modifiers) { self.visibility_not_followed_by_an_item(modifiers); self.unconstrained_not_followed_by_an_item(modifiers); diff --git a/compiler/noirc_frontend/src/parser/parser/types.rs b/compiler/noirc_frontend/src/parser/parser/types.rs index be3d5287cab..0de94a89be5 100644 --- a/compiler/noirc_frontend/src/parser/parser/types.rs +++ b/compiler/noirc_frontend/src/parser/parser/types.rs @@ -341,7 +341,10 @@ impl<'a> Parser<'a> { fn parses_mutable_reference_type(&mut self) -> Option { if self.eat(Token::Ampersand) { - self.eat_keyword_or_error(Keyword::Mut); + if !self.eat_keyword(Keyword::Mut) { + self.expected_mut_after_ampersand(); + } + return Some(UnresolvedTypeData::MutableReference(Box::new( self.parse_type_or_error(), )));