Add struct indexing parsing
This commit is contained in:
		
							parent
							
								
									c83d53ae53
								
							
						
					
					
						commit
						d9a1e8456d
					
				| @ -44,12 +44,13 @@ pub enum ExpressionKind { | ||||
|     VariableName(String), | ||||
|     Literal(Literal), | ||||
|     Array(Vec<Expression>), | ||||
|     Index(Box<Expression>, u64), | ||||
|     ArrayIndex(Box<Expression>, u64), | ||||
|     StructIndex(Box<Expression>, String), | ||||
|     Binop(BinaryOperator, Box<Expression>, Box<Expression>), | ||||
|     FunctionCall(Box<FunctionCallExpression>), | ||||
|     BlockExpr(Box<Block>), | ||||
|     IfExpr(Box<IfExpression>), | ||||
|     StructInit(StructInit), | ||||
|     StructExpression(StructExpression), | ||||
| } | ||||
| 
 | ||||
| #[derive(Debug, Clone, Copy)] | ||||
| @ -132,7 +133,7 @@ pub enum ReturnType { | ||||
| } | ||||
| 
 | ||||
| #[derive(Debug, Clone)] | ||||
| pub struct StructInit { | ||||
| pub struct StructExpression { | ||||
|     name: String, | ||||
|     fields: Vec<(String, Expression)>, | ||||
| } | ||||
| @ -150,7 +151,8 @@ pub struct VariableReference(pub VariableReferenceKind, pub TokenRange); | ||||
| #[derive(Debug, Clone)] | ||||
| pub enum VariableReferenceKind { | ||||
|     Name(String, TokenRange), | ||||
|     Index(Box<VariableReference>, u64), | ||||
|     ArrayIndex(Box<VariableReference>, u64), | ||||
|     StructIndex(Box<VariableReference>, String), | ||||
| } | ||||
| 
 | ||||
| #[derive(Debug, Clone)] | ||||
|  | ||||
| @ -80,7 +80,7 @@ impl Parse for PrimaryExpression { | ||||
|             (stream.peek(), stream.peek2()) | ||||
|         { | ||||
|             Expression( | ||||
|                 Kind::StructInit(stream.parse()?), | ||||
|                 Kind::StructExpression(stream.parse()?), | ||||
|                 stream.get_range().unwrap(), | ||||
|             ) | ||||
|         } else if let Some(token) = stream.next() { | ||||
| @ -88,7 +88,7 @@ impl Parse for PrimaryExpression { | ||||
|                 Token::Identifier(v) => { | ||||
|                     if let Some(Token::BraceOpen) = stream.peek() { | ||||
|                         Expression( | ||||
|                             Kind::StructInit(stream.parse()?), | ||||
|                             Kind::StructExpression(stream.parse()?), | ||||
|                             stream.get_range().unwrap(), | ||||
|                         ) | ||||
|                     } else { | ||||
| @ -134,11 +134,21 @@ impl Parse for PrimaryExpression { | ||||
|             Err(stream.expected_err("expression")?)? | ||||
|         }; | ||||
| 
 | ||||
|         while let Ok(ValueIndex(idx)) = stream.parse() { | ||||
|             expr = Expression( | ||||
|                 ExpressionKind::Index(Box::new(expr), idx), | ||||
|                 stream.get_range().unwrap(), | ||||
|             ); | ||||
|         while let Ok(index) = stream.parse::<ValueIndex>() { | ||||
|             match index { | ||||
|                 ValueIndex::Array(ArrayValueIndex(idx)) => { | ||||
|                     expr = Expression( | ||||
|                         ExpressionKind::ArrayIndex(Box::new(expr), idx), | ||||
|                         stream.get_range().unwrap(), | ||||
|                     ); | ||||
|                 } | ||||
|                 ValueIndex::Struct(StructValueIndex(name)) => { | ||||
|                     expr = Expression( | ||||
|                         ExpressionKind::StructIndex(Box::new(expr), name), | ||||
|                         stream.get_range().unwrap(), | ||||
|                     ); | ||||
|                 } | ||||
|             } | ||||
|         } | ||||
| 
 | ||||
|         Ok(PrimaryExpression(expr)) | ||||
| @ -415,9 +425,9 @@ impl Parse for VariableReference { | ||||
|                 stream.get_range().unwrap(), | ||||
|             ); | ||||
| 
 | ||||
|             while let Ok(ValueIndex(idx)) = stream.parse() { | ||||
|             while let Ok(ArrayValueIndex(idx)) = stream.parse() { | ||||
|                 var_ref = VariableReference( | ||||
|                     VariableReferenceKind::Index(Box::new(var_ref), idx), | ||||
|                     VariableReferenceKind::ArrayIndex(Box::new(var_ref), idx), | ||||
|                     stream.get_range().unwrap(), | ||||
|                 ); | ||||
|             } | ||||
| @ -429,7 +439,7 @@ impl Parse for VariableReference { | ||||
|     } | ||||
| } | ||||
| 
 | ||||
| impl Parse for StructInit { | ||||
| impl Parse for StructExpression { | ||||
|     fn parse(mut stream: TokenStream) -> Result<Self, Error> { | ||||
|         let Some(Token::Identifier(name)) = stream.next() else { | ||||
|             return Err(stream.expected_err("struct identifier")?); | ||||
| @ -439,9 +449,8 @@ impl Parse for StructInit { | ||||
|         let fields = named_list.0.into_iter().map(|f| (f.0, f.1)).collect(); | ||||
| 
 | ||||
|         stream.expect(Token::BraceClose)?; | ||||
|         stream.expect(Token::Semi)?; | ||||
| 
 | ||||
|         Ok(StructInit { name, fields }) | ||||
|         Ok(StructExpression { name, fields }) | ||||
|     } | ||||
| } | ||||
| 
 | ||||
| @ -480,21 +489,51 @@ impl<T: Parse + std::fmt::Debug> Parse for NamedField<T> { | ||||
|     } | ||||
| } | ||||
| 
 | ||||
| #[derive(Debug, Clone, Copy)] | ||||
| pub struct ValueIndex(u64); | ||||
| #[derive(Debug, Clone)] | ||||
| pub enum ValueIndex { | ||||
|     Array(ArrayValueIndex), | ||||
|     Struct(StructValueIndex), | ||||
| } | ||||
| 
 | ||||
| impl Parse for ValueIndex { | ||||
|     fn parse(mut stream: TokenStream) -> Result<Self, Error> { | ||||
|         match stream.peek() { | ||||
|             Some(Token::BracketOpen) => Ok(ValueIndex::Array(stream.parse()?)), | ||||
|             Some(Token::Dot) => Ok(ValueIndex::Struct(stream.parse()?)), | ||||
|             _ => Err(stream.expected_err("value or struct index")?), | ||||
|         } | ||||
|     } | ||||
| } | ||||
| 
 | ||||
| #[derive(Debug, Clone, Copy)] | ||||
| pub struct ArrayValueIndex(u64); | ||||
| 
 | ||||
| impl Parse for ArrayValueIndex { | ||||
|     fn parse(mut stream: TokenStream) -> Result<Self, Error> { | ||||
|         stream.expect(Token::BracketOpen)?; | ||||
|         if let Some(Token::DecimalValue(idx)) = stream.next() { | ||||
|             stream.expect(Token::BracketClose)?; | ||||
|             Ok(ValueIndex(idx)) | ||||
|             Ok(ArrayValueIndex(idx)) | ||||
|         } else { | ||||
|             return Err(stream.expected_err("array index (number)")?); | ||||
|         } | ||||
|     } | ||||
| } | ||||
| 
 | ||||
| #[derive(Debug, Clone)] | ||||
| pub struct StructValueIndex(String); | ||||
| 
 | ||||
| impl Parse for StructValueIndex { | ||||
|     fn parse(mut stream: TokenStream) -> Result<Self, Error> { | ||||
|         stream.expect(Token::Dot)?; | ||||
|         if let Some(Token::Identifier(name)) = stream.next() { | ||||
|             Ok(StructValueIndex(name)) | ||||
|         } else { | ||||
|             return Err(stream.expected_err("struct index (number)")?); | ||||
|         } | ||||
|     } | ||||
| } | ||||
| 
 | ||||
| impl Parse for BlockLevelStatement { | ||||
|     fn parse(mut stream: TokenStream) -> Result<Self, Error> { | ||||
|         use BlockLevelStatement as Stmt; | ||||
|  | ||||
| @ -152,9 +152,12 @@ impl ast::VariableReferenceKind { | ||||
|                     (*range).into(), | ||||
|                 )) | ||||
|             } | ||||
|             ast::VariableReferenceKind::Index(var_ref, idx) => { | ||||
|             ast::VariableReferenceKind::ArrayIndex(var_ref, idx) => { | ||||
|                 mir::IndexedVariableReferenceKind::Index(Box::new(var_ref.process()), *idx) | ||||
|             } | ||||
|             ast::VariableReferenceKind::StructIndex(variable_reference, _) => { | ||||
|                 todo!("struct indexing into mir") | ||||
|             } | ||||
|         } | ||||
|     } | ||||
| } | ||||
| @ -194,12 +197,15 @@ impl ast::Expression { | ||||
|             ast::ExpressionKind::Array(expressions) => { | ||||
|                 mir::ExprKind::Array(expressions.iter().map(|e| e.process()).collect()) | ||||
|             } | ||||
|             ast::ExpressionKind::Index(expression, idx) => mir::ExprKind::Index( | ||||
|             ast::ExpressionKind::ArrayIndex(expression, idx) => mir::ExprKind::Index( | ||||
|                 Box::new(expression.process()), | ||||
|                 mir::TypeKind::Vague(mir::VagueType::Unknown), | ||||
|                 *idx, | ||||
|             ), | ||||
|             ast::ExpressionKind::StructInit(struct_init) => todo!("implement struct init process"), | ||||
|             ast::ExpressionKind::StructExpression(struct_init) => { | ||||
|                 todo!("implement struct init process") | ||||
|             } | ||||
|             ast::ExpressionKind::StructIndex(expression, _) => todo!("struct index expression"), | ||||
|         }; | ||||
| 
 | ||||
|         mir::Expression(kind, self.1.into()) | ||||
|  | ||||
		Loading…
	
		Reference in New Issue
	
	Block a user