diff --git a/reid/examples/array.rs b/reid/examples/array.rs new file mode 100644 index 0000000..9952667 --- /dev/null +++ b/reid/examples/array.rs @@ -0,0 +1,11 @@ +use reid::compile; + +pub static ARRAY: &str = include_str!("./reid/array.reid"); + +fn main() { + let text = match compile(ARRAY) { + Ok(t) => t, + Err(e) => panic!("{}", e), + }; + println!("{}", text); +} diff --git a/reid/examples/reid/array.reid b/reid/examples/reid/array.reid new file mode 100644 index 0000000..3856e00 --- /dev/null +++ b/reid/examples/reid/array.reid @@ -0,0 +1,13 @@ +// Arithmetic, function calls and imports! + +fn array() -> [u16; 4] { + return true; +} + +fn main() -> u16 { + let heehoo = 10; + + let list = array(); + + return heehoo; +} diff --git a/reid/examples/reid/medium.reid b/reid/examples/reid/medium.reid deleted file mode 100644 index 018c054..0000000 --- a/reid/examples/reid/medium.reid +++ /dev/null @@ -1,12 +0,0 @@ -// if-statements, functions - -import std::print; - -fn fibonacci(value: i32) -> i32 { - if value < 3 { - return 1; - } - return fibonacci(value - 1) + fibonacci(value - 2); -} - -print(fibonacci(15)); \ No newline at end of file diff --git a/reid/src/ast/mod.rs b/reid/src/ast/mod.rs index 557b73a..f9bc5e7 100644 --- a/reid/src/ast/mod.rs +++ b/reid/src/ast/mod.rs @@ -6,10 +6,10 @@ use crate::token_stream::TokenRange; pub mod parse; pub mod process; -#[derive(Debug, Clone, Copy)] +#[derive(Debug, Clone)] pub struct Type(pub TypeKind, pub TokenRange); -#[derive(Debug, Clone, Copy)] +#[derive(Debug, Clone)] pub enum TypeKind { Bool, I8, @@ -22,6 +22,7 @@ pub enum TypeKind { U32, U64, U128, + Array(Box, u64), } #[derive(Debug, Clone)] diff --git a/reid/src/ast/parse.rs b/reid/src/ast/parse.rs index fa49d06..edebb0c 100644 --- a/reid/src/ast/parse.rs +++ b/reid/src/ast/parse.rs @@ -13,24 +13,37 @@ where impl Parse for Type { fn parse(mut stream: TokenStream) -> Result { - let kind = if let Some(Token::Identifier(ident)) = stream.next() { - Ok(match &*ident { - "bool" => TypeKind::Bool, - "i8" => TypeKind::I8, - "i16" => TypeKind::I16, - "i32" => TypeKind::I32, - "i64" => TypeKind::I64, - "i128" => TypeKind::I128, - "u8" => TypeKind::U8, - "u16" => TypeKind::U16, - "u32" => TypeKind::U32, - "u64" => TypeKind::U64, - "u128" => TypeKind::U128, - _ => panic!("asd"), - }) + let kind = if let Some(Token::BracketOpen) = stream.peek() { + stream.expect(Token::BracketOpen)?; + let inner = stream.parse::()?; + stream.expect(Token::Semi)?; + let length = if let Some(Token::DecimalValue(length)) = stream.next() { + length + } else { + return Err(stream.expected_err("array length (number)")?); + }; + stream.expect(Token::BracketClose)?; + TypeKind::Array(Box::new(inner.0), length) } else { - Err(stream.expected_err("type identifier")?) - }?; + if let Some(Token::Identifier(ident)) = stream.next() { + match &*ident { + "bool" => TypeKind::Bool, + "i8" => TypeKind::I8, + "i16" => TypeKind::I16, + "i32" => TypeKind::I32, + "i64" => TypeKind::I64, + "i128" => TypeKind::I128, + "u8" => TypeKind::U8, + "u16" => TypeKind::U16, + "u32" => TypeKind::U32, + "u64" => TypeKind::U64, + "u128" => TypeKind::U128, + _ => Err(stream.expected_err("known type identifier")?)?, + } + } else { + return Err(stream.expected_err("type identifier")?)?; + } + }; Ok(Type(kind, stream.get_range().unwrap())) } @@ -68,7 +81,7 @@ impl Parse for PrimaryExpression { Expression(Kind::VariableName(v.clone()), stream.get_range().unwrap()) } Token::DecimalValue(v) => Expression( - Kind::Literal(Literal::Number(v.parse().unwrap())), + Kind::Literal(Literal::Number(*v)), stream.get_range().unwrap(), ), Token::True => Expression( diff --git a/reid/src/ast/process.rs b/reid/src/ast/process.rs index 44cb533..e3a926f 100644 --- a/reid/src/ast/process.rs +++ b/reid/src/ast/process.rs @@ -29,6 +29,7 @@ impl ast::Module { name: signature.name.clone(), return_type: signature .return_type + .clone() .map(|r| r.0.into()) .unwrap_or(mir::TypeKind::Void), parameters: signature @@ -63,6 +64,7 @@ impl ast::Block { mir::VariableReference( s_let .1 + .clone() .map(|t| t.0.into()) .unwrap_or(mir::TypeKind::Vague(mir::VagueType::Unknown)), s_let.0.clone(), @@ -181,7 +183,7 @@ impl ast::Literal { impl From for mir::TypeKind { fn from(value: ast::TypeKind) -> Self { - match value { + match &value { ast::TypeKind::Bool => mir::TypeKind::Bool, ast::TypeKind::I8 => mir::TypeKind::I8, ast::TypeKind::I16 => mir::TypeKind::I16, @@ -193,6 +195,7 @@ impl From for mir::TypeKind { ast::TypeKind::U32 => mir::TypeKind::U32, ast::TypeKind::U64 => mir::TypeKind::U64, ast::TypeKind::U128 => mir::TypeKind::U128, + ast::TypeKind::Array(type_kind, length) => todo!(), } } } diff --git a/reid/src/lexer.rs b/reid/src/lexer.rs index 32238e4..7fd0517 100644 --- a/reid/src/lexer.rs +++ b/reid/src/lexer.rs @@ -7,7 +7,7 @@ pub enum Token { // Values Identifier(String), /// Number with at most one decimal point - DecimalValue(String), + DecimalValue(u64), // Keywords /// `let` @@ -62,6 +62,10 @@ pub enum Token { BraceOpen, /// `}` BraceClose, + /// `[` + BracketOpen, + /// `]` + BracketClose, /// `,` Comma, @@ -194,7 +198,7 @@ pub fn tokenize>(to_tokenize: T) -> Result, Error value += &c.to_string(); cursor.next(); } - Token::DecimalValue(value) + Token::DecimalValue(value.parse().expect("Decimal not parseable to u64")) } '-' if cursor.first() == Some('>') => { cursor.next(); // Eat `>` @@ -213,6 +217,8 @@ pub fn tokenize>(to_tokenize: T) -> Result, Error '!' => Token::Exclamation, '(' => Token::ParenOpen, ')' => Token::ParenClose, + '[' => Token::BracketOpen, + ']' => Token::BracketClose, '{' => Token::BraceOpen, '}' => Token::BraceClose, ',' => Token::Comma,