1
0

Avoid emitting duplicate return instructions; Clean up

This commit is contained in:
Jeff 2024-10-12 07:12:44 -04:00
parent 02877d06d3
commit f1034534ed

View File

@ -90,20 +90,6 @@ impl<'src> Parser<'src> {
} }
} }
fn _decrement_register(&mut self) -> Result<(), ParseError> {
let current = self.current_register;
if current == 0 {
Err(ParseError::RegisterUnderflow {
position: self.current_position,
})
} else {
self.current_register -= 1;
Ok(())
}
}
fn advance(&mut self) -> Result<(), ParseError> { fn advance(&mut self) -> Result<(), ParseError> {
if self.is_eof() { if self.is_eof() {
return Ok(()); return Ok(());
@ -167,28 +153,28 @@ impl<'src> Parser<'src> {
} }
fn parse_boolean(&mut self, _: Allowed) -> Result<(), ParseError> { fn parse_boolean(&mut self, _: Allowed) -> Result<(), ParseError> {
let boolean_text = if let Token::Boolean(text) = self.current_token { let position = self.current_position;
text
if let Token::Boolean(text) = self.current_token {
self.advance()?;
let boolean = text.parse::<bool>().unwrap();
self.emit_instruction(
Instruction::load_boolean(self.current_register, boolean, false),
position,
);
self.parsed_expression = true;
Ok(())
} else { } else {
return Err(ParseError::ExpectedToken { Err(ParseError::ExpectedToken {
expected: TokenKind::Boolean, expected: TokenKind::Boolean,
found: self.current_token.to_owned(), found: self.current_token.to_owned(),
position: self.current_position, position,
}); })
}; }
let position = self.current_position;
let boolean = boolean_text.parse::<bool>().unwrap();
self.advance()?;
self.emit_instruction(
Instruction::load_boolean(self.current_register, boolean, false),
position,
);
self.parsed_expression = true;
Ok(())
} }
fn parse_byte(&mut self, _: Allowed) -> Result<(), ParseError> { fn parse_byte(&mut self, _: Allowed) -> Result<(), ParseError> {
@ -197,19 +183,22 @@ impl<'src> Parser<'src> {
if let Token::Byte(text) = self.current_token { if let Token::Byte(text) = self.current_token {
self.advance()?; self.advance()?;
let byte = let byte = u8::from_str_radix(&text[2..], 16)
u8::from_str_radix(&text[2..], 16).map_err(|error| ParseError::ParseIntError { .map_err(|error| ParseError::ParseIntError { error, position })?;
error,
position: self.previous_position,
})?;
let value = Value::byte(byte); let value = Value::byte(byte);
self.emit_constant(value, position)?; self.emit_constant(value, position)?;
self.parsed_expression = true;
Ok(())
} else {
Err(ParseError::ExpectedToken {
expected: TokenKind::Byte,
found: self.current_token.to_owned(),
position,
})
} }
self.parsed_expression = true;
Ok(())
} }
fn parse_character(&mut self, _: Allowed) -> Result<(), ParseError> { fn parse_character(&mut self, _: Allowed) -> Result<(), ParseError> {
@ -221,11 +210,17 @@ impl<'src> Parser<'src> {
let value = Value::character(character); let value = Value::character(character);
self.emit_constant(value, position)?; self.emit_constant(value, position)?;
self.parsed_expression = true;
Ok(())
} else {
Err(ParseError::ExpectedToken {
expected: TokenKind::Character,
found: self.current_token.to_owned(),
position,
})
} }
self.parsed_expression = true;
Ok(())
} }
fn parse_float(&mut self, _: Allowed) -> Result<(), ParseError> { fn parse_float(&mut self, _: Allowed) -> Result<(), ParseError> {
@ -243,11 +238,17 @@ impl<'src> Parser<'src> {
let value = Value::float(float); let value = Value::float(float);
self.emit_constant(value, position)?; self.emit_constant(value, position)?;
self.parsed_expression = true;
Ok(())
} else {
Err(ParseError::ExpectedToken {
expected: TokenKind::Float,
found: self.current_token.to_owned(),
position,
})
} }
self.parsed_expression = true;
Ok(())
} }
fn parse_integer(&mut self, _: Allowed) -> Result<(), ParseError> { fn parse_integer(&mut self, _: Allowed) -> Result<(), ParseError> {
@ -265,11 +266,17 @@ impl<'src> Parser<'src> {
let value = Value::integer(integer); let value = Value::integer(integer);
self.emit_constant(value, position)?; self.emit_constant(value, position)?;
self.parsed_expression = true;
Ok(())
} else {
Err(ParseError::ExpectedToken {
expected: TokenKind::Integer,
found: self.current_token.to_owned(),
position,
})
} }
self.parsed_expression = true;
Ok(())
} }
fn parse_string(&mut self, _: Allowed) -> Result<(), ParseError> { fn parse_string(&mut self, _: Allowed) -> Result<(), ParseError> {
@ -281,11 +288,17 @@ impl<'src> Parser<'src> {
let value = Value::string(text); let value = Value::string(text);
self.emit_constant(value, position)?; self.emit_constant(value, position)?;
self.parsed_expression = true;
Ok(())
} else {
Err(ParseError::ExpectedToken {
expected: TokenKind::String,
found: self.current_token.to_owned(),
position,
})
} }
self.parsed_expression = true;
Ok(())
} }
fn parse_grouped(&mut self, _: Allowed) -> Result<(), ParseError> { fn parse_grouped(&mut self, _: Allowed) -> Result<(), ParseError> {
@ -934,13 +947,15 @@ impl<'src> Parser<'src> {
fn parse_statement(&mut self, allowed: Allowed, context: Context) -> Result<(), ParseError> { fn parse_statement(&mut self, allowed: Allowed, context: Context) -> Result<(), ParseError> {
self.parse(Precedence::None, allowed)?; self.parse(Precedence::None, allowed)?;
if let [Some((jump, _)), Some((comparison, comparison_position))] = let previous_instructions = self.chunk.get_last_n_instructions();
self.chunk.get_last_n_instructions()
{ if let [Some((jump, _)), Some((comparison, comparison_position))] = previous_instructions {
if let (Operation::Jump, Operation::Equal | Operation::Less | Operation::LessEqual) = if let (Operation::Jump, Operation::Equal | Operation::Less | Operation::LessEqual) =
(jump.operation(), comparison.operation()) (jump.operation(), comparison.operation())
{ {
if matches!(self.current_token, Token::Eof) || context == Context::Assignment { if matches!(self.current_token, Token::Eof | Token::RightCurlyBrace)
|| context == Context::Assignment
{
let comparison_position = *comparison_position; let comparison_position = *comparison_position;
self.emit_instruction( self.emit_instruction(
@ -955,9 +970,10 @@ impl<'src> Parser<'src> {
} }
} }
let returned = self.chunk.get_last_operation()? == Operation::Return;
let has_semicolon = self.allow(Token::Semicolon)?; let has_semicolon = self.allow(Token::Semicolon)?;
if !has_semicolon && self.parsed_expression && allowed.implicit_return { if allowed.implicit_return && self.parsed_expression && !returned && !has_semicolon {
self.emit_instruction(Instruction::r#return(true), self.current_position); self.emit_instruction(Instruction::r#return(true), self.current_position);
} }
@ -1248,8 +1264,8 @@ struct ParseRule<'a> {
} }
impl From<&Token<'_>> for ParseRule<'_> { impl From<&Token<'_>> for ParseRule<'_> {
fn from(token_kind: &Token) -> Self { fn from(token: &Token) -> Self {
match token_kind { match token {
Token::Async => todo!(), Token::Async => todo!(),
Token::Bang => ParseRule { Token::Bang => ParseRule {
prefix: Some(Parser::parse_unary), prefix: Some(Parser::parse_unary),