vinci/parser/instruction/
function.rs1use crate::ast::instructions::function::{Call, Function};
2use crate::ast::instructions::Node;
3use crate::lexer::token::Token;
4use crate::parser::error::ParseError;
5use crate::parser::Parser;
6use crate::types::Type;
7
8pub fn parse_function_instruction(parser: &mut Parser) -> Result<Node, ParseError> {
36 let index;
37 let return_type;
38
39 if let Token::Number(idx) = parser.next_token() {
40 index = idx;
41 } else {
42 return Err(ParseError::UnexpectedToken(
43 Token::Type(Type::INT),
44 parser.current_token(),
45 ));
46 }
47
48 if let Token::Type(tp) = parser.next_token() {
49 return_type = tp;
50 } else {
51 return Err(ParseError::UnexpectedToken(
52 Token::Type(Type::INT),
53 parser.current_token(),
54 ));
55 }
56
57 parser.expected(Token::Arguments)?;
58
59 parser.expected(Token::LeftCurly)?;
60
61 let parameters: Vec<Type> = parse_type_arguments(parser)?;
62
63 parser.expected(Token::Free)?;
64 parser.expected(Token::LeftCurly)?;
65
66 let free: Vec<Type> = parse_type_arguments(parser)?;
67
68 parser.expected(Token::Then)?;
69
70 parser.expected(Token::LeftCurly)?;
71
72 let body = parser.parse_nodes()?;
73
74 parser.expected(Token::Semicolon)?;
75
76 Ok(Node::FUNCTION(Box::new(Function {
77 index: index as u32,
78 return_type,
79 parameters,
80 free,
81 body,
82 })))
83}
84
85pub fn parse_call_instruction(parser: &mut Parser) -> Result<Node, ParseError> {
110 let function_name;
111
112 if let Token::Namespace(ns) = parser.next_token() {
113 function_name = ns;
114 } else {
115 return Err(ParseError::UnexpectedToken(
116 Token::Namespace("namespace::function".to_string()),
117 parser.current_token(),
118 ));
119 }
120
121 parser.expected(Token::LeftCurly)?;
122
123 let arguments = parser.parse_nodes()?;
124
125 parser.expected(Token::Semicolon)?;
126
127 Ok(Node::CALL(Box::new(Call {
128 namespace: function_name,
129 arguments,
130 })))
131}
132
133fn parse_type_arguments(parser: &mut Parser) -> Result<Vec<Type>, ParseError> {
134 let mut parameters: Vec<Type> = Vec::new();
135 let mut next = parser.next_token();
136
137 while next != Token::RightCurly && next != Token::Error {
138 if let Token::Type(tp) = next {
139 parameters.push(tp);
140 parser.expected(Token::Semicolon)?;
141 next = parser.next_token();
142 } else {
143 break;
144 }
145 }
146
147 Ok(parameters)
148}