Skip to main content

sml_lang/
validator.rs

1use crate::lexer::Token;
2use crate::error::{Error, ErrorType};
3
4enum State {
5    ExpectIdentifier,
6    ExpectAssign,
7    ExpectValue,
8    ExpectNewline,
9}
10
11pub fn validate(tokens: &[Token]) -> Result<(), Error> {
12    let mut state = State::ExpectIdentifier;
13
14    for token in tokens {
15        state = match state {
16
17            State::ExpectIdentifier => {
18                match token {
19                    Token::Identifier(_) => State::ExpectAssign,
20                    Token::Newline => State::ExpectIdentifier, // allow empty lines
21                    _ => return Err(unexpected("Identifier")),
22                }
23            }
24
25            State::ExpectAssign => {
26                match token {
27                    Token::Assign => State::ExpectValue,
28                    _ => return Err(unexpected("ASSIGN")),
29                }
30            }
31
32            State::ExpectValue => {
33                match token {
34                    Token::Int(_) | Token::Float(_) => State::ExpectNewline,
35                    _ => return Err(unexpected("Int or Float")),
36                }
37            }
38
39            State::ExpectNewline => {
40                match token {
41                    Token::Newline => State::ExpectIdentifier,
42                    _ => return Err(unexpected("Newline")),
43                }
44            }
45        }
46    }
47
48    Ok(())
49}
50
51fn unexpected(expected: &str) -> Error {
52    Error {
53        error_type: ErrorType::SyntaxError,
54        description: format!("unexpected token, expected {}", expected),
55    }
56}