Browse Source

Replaced occurences of mk! (#212)

pull/215/head
Iovoslav Iovchev 5 years ago committed by GitHub
parent
commit
cf516f656b
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
  1. 207
      src/lib/syntax/parser.rs

207
src/lib/syntax/parser.rs

@ -6,17 +6,6 @@ use crate::syntax::ast::punc::Punctuator;
use crate::syntax::ast::token::{Token, TokenData}; use crate::syntax::ast::token::{Token, TokenData};
use std::collections::btree_map::BTreeMap; use std::collections::btree_map::BTreeMap;
macro_rules! mk (
($this:expr, $def:expr) => {
{
Expr::new($def)
}
};
($this:expr, $def:expr, $first:expr) => {
Expr::new($def)
};
);
/// `ParseError` is an enum which represents errors encounted during parsing an expression /// `ParseError` is an enum which represents errors encounted during parsing an expression
#[derive(Debug, Clone)] #[derive(Debug, Clone)]
pub enum ParseError { pub enum ParseError {
@ -54,8 +43,6 @@ impl Parser {
exprs.push(result); exprs.push(result);
} }
// In the case of `Block` the Positions seem unnecessary
// TODO: refactor this or the `mk!` perhaps?
Ok(Expr::new(ExprDef::Block(exprs))) Ok(Expr::new(ExprDef::Block(exprs)))
} }
@ -97,7 +84,7 @@ impl Parser {
match keyword { match keyword {
Keyword::Throw => { Keyword::Throw => {
let thrown = self.parse()?; let thrown = self.parse()?;
Ok(mk!(self, ExprDef::Throw(Box::new(thrown)))) Ok(Expr::new(ExprDef::Throw(Box::new(thrown))))
} }
// vars, lets and consts are similar in parsing structure, we can group them together // vars, lets and consts are similar in parsing structure, we can group them together
Keyword::Var | Keyword::Let => { Keyword::Var | Keyword::Let => {
@ -202,29 +189,26 @@ impl Parser {
Ok(Expr::new(ExprDef::ConstDecl(vars))) Ok(Expr::new(ExprDef::ConstDecl(vars)))
} }
Keyword::Return => Ok(mk!( Keyword::Return => Ok(Expr::new(ExprDef::Return(Some(Box::new(
self, self.parse()?.clone(),
ExprDef::Return(Some(Box::new(self.parse()?.clone()))) ))))),
)),
Keyword::New => { Keyword::New => {
let call = self.parse()?; let call = self.parse()?;
match call.def { match call.def {
ExprDef::Call(ref func, ref args) => { ExprDef::Call(ref func, ref args) => {
Ok(mk!(self, ExprDef::Construct(func.clone(), args.clone()))) Ok(Expr::new(ExprDef::Construct(func.clone(), args.clone())))
} }
_ => Err(ParseError::ExpectedExpr("constructor", call)), _ => Err(ParseError::ExpectedExpr("constructor", call)),
} }
} }
Keyword::TypeOf => Ok(mk!(self, ExprDef::TypeOf(Box::new(self.parse()?)))), Keyword::TypeOf => Ok(Expr::new(ExprDef::TypeOf(Box::new(self.parse()?)))),
Keyword::If => { Keyword::If => {
self.expect_punc(Punctuator::OpenParen, "if block")?; self.expect_punc(Punctuator::OpenParen, "if block")?;
let cond = self.parse()?; let cond = self.parse()?;
self.expect_punc(Punctuator::CloseParen, "if block")?; self.expect_punc(Punctuator::CloseParen, "if block")?;
let expr = self.parse()?; let expr = self.parse()?;
let next = self.get_token(self.pos); let next = self.get_token(self.pos);
Ok(mk!( Ok(Expr::new(ExprDef::If(
self,
ExprDef::If(
Box::new(cond), Box::new(cond),
Box::new(expr), Box::new(expr),
if next.is_ok() if next.is_ok()
@ -235,19 +219,18 @@ impl Parser {
Some(Box::new(self.parse()?)) Some(Box::new(self.parse()?))
} else { } else {
None None
} },
) )))
))
} }
Keyword::While => { Keyword::While => {
self.expect_punc(Punctuator::OpenParen, "while condition")?; self.expect_punc(Punctuator::OpenParen, "while condition")?;
let cond = self.parse()?; let cond = self.parse()?;
self.expect_punc(Punctuator::CloseParen, "while condition")?; self.expect_punc(Punctuator::CloseParen, "while condition")?;
let expr = self.parse()?; let expr = self.parse()?;
Ok(mk!( Ok(Expr::new(ExprDef::WhileLoop(
self, Box::new(cond),
ExprDef::WhileLoop(Box::new(cond), Box::new(expr)) Box::new(expr),
)) )))
} }
Keyword::Switch => { Keyword::Switch => {
self.expect_punc(Punctuator::OpenParen, "switch value")?; self.expect_punc(Punctuator::OpenParen, "switch value")?;
@ -285,7 +268,7 @@ impl Parser {
_ => block.push(self.parse()?), _ => block.push(self.parse()?),
} }
} }
default = Some(mk!(self, ExprDef::Block(block))); default = Some(Expr::new(ExprDef::Block(block)));
} }
TokenData::Punctuator(Punctuator::CloseBlock) => break, TokenData::Punctuator(Punctuator::CloseBlock) => break,
_ => { _ => {
@ -302,17 +285,14 @@ impl Parser {
} }
} }
self.expect_punc(Punctuator::CloseBlock, "switch block")?; self.expect_punc(Punctuator::CloseBlock, "switch block")?;
Ok(mk!( Ok(Expr::new(ExprDef::Switch(
self,
ExprDef::Switch(
Box::new(value.expect("Could not get value")), Box::new(value.expect("Could not get value")),
cases, cases,
match default { match default {
Some(v) => Some(Box::new(v)), Some(v) => Some(Box::new(v)),
None => None, None => None,
} },
) )))
))
} }
Keyword::Function => { Keyword::Function => {
// function [identifier] () { etc } // function [identifier] () { etc }
@ -334,10 +314,11 @@ impl Parser {
// Now we have the function identifier we should have an open paren for arguments ( ) // Now we have the function identifier we should have an open paren for arguments ( )
let args = self.parse_function_parameters()?; let args = self.parse_function_parameters()?;
let block = self.parse()?; let block = self.parse()?;
Ok(mk!( Ok(Expr::new(ExprDef::FunctionDecl(
self, name,
ExprDef::FunctionDecl(name, args, Box::new(block)) args,
)) Box::new(block),
)))
} }
_ => Err(ParseError::UnexpectedKeyword(keyword)), _ => Err(ParseError::UnexpectedKeyword(keyword)),
} }
@ -357,16 +338,16 @@ impl Parser {
self.parse()? self.parse()?
} }
TokenData::Punctuator(Punctuator::Semicolon) | TokenData::Comment(_) => { TokenData::Punctuator(Punctuator::Semicolon) | TokenData::Comment(_) => {
mk!(self, ExprDef::Const(Const::Undefined)) Expr::new(ExprDef::Const(Const::Undefined))
} }
TokenData::NumericLiteral(num) => mk!(self, ExprDef::Const(Const::Num(num))), TokenData::NumericLiteral(num) => Expr::new(ExprDef::Const(Const::Num(num))),
TokenData::NullLiteral => mk!(self, ExprDef::Const(Const::Null)), TokenData::NullLiteral => Expr::new(ExprDef::Const(Const::Null)),
TokenData::StringLiteral(text) => mk!(self, ExprDef::Const(Const::String(text))), TokenData::StringLiteral(text) => Expr::new(ExprDef::Const(Const::String(text))),
TokenData::BooleanLiteral(val) => mk!(self, ExprDef::Const(Const::Bool(val))), TokenData::BooleanLiteral(val) => Expr::new(ExprDef::Const(Const::Bool(val))),
TokenData::Identifier(ref s) if s == "undefined" => { TokenData::Identifier(ref s) if s == "undefined" => {
mk!(self, ExprDef::Const(Const::Undefined)) Expr::new(ExprDef::Const(Const::Undefined))
} }
TokenData::Identifier(s) => mk!(self, ExprDef::Local(s)), TokenData::Identifier(s) => Expr::new(ExprDef::Local(s)),
TokenData::Keyword(keyword) => self.parse_struct(keyword)?, TokenData::Keyword(keyword) => self.parse_struct(keyword)?,
TokenData::RegularExpressionLiteral(body, flags) => Expr::new(ExprDef::Construct( TokenData::RegularExpressionLiteral(body, flags) => Expr::new(ExprDef::Construct(
Box::new(Expr::new(ExprDef::Local("RegExp".to_string()))), Box::new(Expr::new(ExprDef::Local("RegExp".to_string()))),
@ -383,11 +364,7 @@ impl Parser {
{ {
self.pos += 2; self.pos += 2;
let expr = self.parse()?; let expr = self.parse()?;
mk!( Expr::new(ExprDef::ArrowFunctionDecl(Vec::new(), Box::new(expr)))
self,
ExprDef::ArrowFunctionDecl(Vec::new(), Box::new(expr)),
token
)
} }
_ => { _ => {
let next = self.parse()?; let next = self.parse()?;
@ -449,11 +426,7 @@ impl Parser {
"arrow function", "arrow function",
)?; )?;
let expr = self.parse()?; let expr = self.parse()?;
mk!( Expr::new(ExprDef::ArrowFunctionDecl(args, Box::new(expr)))
self,
ExprDef::ArrowFunctionDecl(args, Box::new(expr)),
token
)
} }
_ => { _ => {
return Err(ParseError::Expected( return Err(ParseError::Expected(
@ -479,7 +452,7 @@ impl Parser {
TokenData::Punctuator(Punctuator::Comma) => { TokenData::Punctuator(Punctuator::Comma) => {
if !saw_expr_last { if !saw_expr_last {
// An elision indicates that a space is saved in the array // An elision indicates that a space is saved in the array
array.push(mk!(self, ExprDef::Const(Const::Undefined))) array.push(Expr::new(ExprDef::Const(Const::Undefined)))
} }
saw_expr_last = false; saw_expr_last = false;
self.pos += 1; self.pos += 1;
@ -502,14 +475,14 @@ impl Parser {
} }
} }
} }
mk!(self, ExprDef::ArrayDecl(array), token) Expr::new(ExprDef::ArrayDecl(array))
} }
TokenData::Punctuator(Punctuator::OpenBlock) TokenData::Punctuator(Punctuator::OpenBlock)
if self.get_token(self.pos)?.data if self.get_token(self.pos)?.data
== TokenData::Punctuator(Punctuator::CloseBlock) => == TokenData::Punctuator(Punctuator::CloseBlock) =>
{ {
self.pos += 1; self.pos += 1;
mk!(self, ExprDef::ObjectDecl(Box::new(BTreeMap::new())), token) Expr::new(ExprDef::ObjectDecl(Box::new(BTreeMap::new())))
} }
TokenData::Punctuator(Punctuator::OpenBlock) TokenData::Punctuator(Punctuator::OpenBlock)
if self.get_token(self.pos.wrapping_add(1))?.data if self.get_token(self.pos.wrapping_add(1))?.data
@ -546,11 +519,7 @@ impl Parser {
self.pos += 1; // { self.pos += 1; // {
let expr = self.parse()?; let expr = self.parse()?;
self.pos += 1; self.pos += 1;
mk!( Expr::new(ExprDef::FunctionDecl(None, args, Box::new(expr)))
self,
ExprDef::FunctionDecl(None, args, Box::new(expr)),
token
)
} }
_ => { _ => {
return Err(ParseError::Expected( return Err(ParseError::Expected(
@ -566,7 +535,7 @@ impl Parser {
map.insert(name, value); map.insert(name, value);
self.pos += 1; self.pos += 1;
} }
mk!(self, ExprDef::ObjectDecl(map), token) Expr::new(ExprDef::ObjectDecl(map))
} }
TokenData::Punctuator(Punctuator::OpenBlock) => { TokenData::Punctuator(Punctuator::OpenBlock) => {
let mut exprs = Vec::new(); let mut exprs = Vec::new();
@ -580,39 +549,35 @@ impl Parser {
} }
} }
self.pos += 1; self.pos += 1;
mk!(self, ExprDef::Block(exprs), token) Expr::new(ExprDef::Block(exprs))
} }
// Empty Block // Empty Block
TokenData::Punctuator(Punctuator::CloseBlock) TokenData::Punctuator(Punctuator::CloseBlock)
if self.get_token(self.pos.wrapping_sub(2))?.data if self.get_token(self.pos.wrapping_sub(2))?.data
== TokenData::Punctuator(Punctuator::OpenBlock) => == TokenData::Punctuator(Punctuator::OpenBlock) =>
{ {
mk!(self, ExprDef::Block(vec!()), token) Expr::new(ExprDef::Block(vec![]))
} }
TokenData::Punctuator(Punctuator::Sub) => mk!( TokenData::Punctuator(Punctuator::Sub) => {
self, Expr::new(ExprDef::UnaryOp(UnaryOp::Minus, Box::new(self.parse()?)))
ExprDef::UnaryOp(UnaryOp::Minus, Box::new(self.parse()?)) }
), TokenData::Punctuator(Punctuator::Add) => {
TokenData::Punctuator(Punctuator::Add) => mk!( Expr::new(ExprDef::UnaryOp(UnaryOp::Plus, Box::new(self.parse()?)))
self, }
ExprDef::UnaryOp(UnaryOp::Plus, Box::new(self.parse()?)) TokenData::Punctuator(Punctuator::Not) => {
), Expr::new(ExprDef::UnaryOp(UnaryOp::Not, Box::new(self.parse()?)))
TokenData::Punctuator(Punctuator::Not) => mk!( }
self, TokenData::Punctuator(Punctuator::Neg) => {
ExprDef::UnaryOp(UnaryOp::Not, Box::new(self.parse()?)) Expr::new(ExprDef::UnaryOp(UnaryOp::Tilde, Box::new(self.parse()?)))
), }
TokenData::Punctuator(Punctuator::Neg) => mk!( TokenData::Punctuator(Punctuator::Inc) => Expr::new(ExprDef::UnaryOp(
self, UnaryOp::IncrementPre,
ExprDef::UnaryOp(UnaryOp::Tilde, Box::new(self.parse()?)) Box::new(self.parse()?),
), )),
TokenData::Punctuator(Punctuator::Inc) => mk!( TokenData::Punctuator(Punctuator::Dec) => Expr::new(ExprDef::UnaryOp(
self, UnaryOp::DecrementPre,
ExprDef::UnaryOp(UnaryOp::IncrementPre, Box::new(self.parse()?)) Box::new(self.parse()?),
), )),
TokenData::Punctuator(Punctuator::Dec) => mk!(
self,
ExprDef::UnaryOp(UnaryOp::DecrementPre, Box::new(self.parse()?))
),
_ => return Err(ParseError::Expected(Vec::new(), token.clone(), "script")), _ => return Err(ParseError::Expected(Vec::new(), token.clone(), "script")),
}; };
if self.pos >= self.tokens.len() { if self.pos >= self.tokens.len() {
@ -632,7 +597,7 @@ impl Parser {
let tk = self.get_token(self.pos)?; let tk = self.get_token(self.pos)?;
match tk.data { match tk.data {
TokenData::Identifier(ref s) => { TokenData::Identifier(ref s) => {
result = mk!(self, ExprDef::GetConstField(Box::new(expr), s.to_string())) result = Expr::new(ExprDef::GetConstField(Box::new(expr), s.to_string()))
} }
_ => { _ => {
return Err(ParseError::Expected( return Err(ParseError::Expected(
@ -676,17 +641,18 @@ impl Parser {
expect_comma_or_end = true; expect_comma_or_end = true;
} }
} }
result = mk!(self, ExprDef::Call(Box::new(expr), args)); result = Expr::new(ExprDef::Call(Box::new(expr), args));
} }
TokenData::Punctuator(Punctuator::Question) => { TokenData::Punctuator(Punctuator::Question) => {
self.pos += 1; self.pos += 1;
let if_e = self.parse()?; let if_e = self.parse()?;
self.expect(TokenData::Punctuator(Punctuator::Colon), "if expression")?; self.expect(TokenData::Punctuator(Punctuator::Colon), "if expression")?;
let else_e = self.parse()?; let else_e = self.parse()?;
result = mk!( result = Expr::new(ExprDef::If(
self, Box::new(expr),
ExprDef::If(Box::new(expr), Box::new(if_e), Some(Box::new(else_e))) Box::new(if_e),
); Some(Box::new(else_e)),
));
} }
TokenData::Punctuator(Punctuator::OpenBracket) => { TokenData::Punctuator(Punctuator::OpenBracket) => {
self.pos += 1; self.pos += 1;
@ -695,7 +661,7 @@ impl Parser {
TokenData::Punctuator(Punctuator::CloseBracket), TokenData::Punctuator(Punctuator::CloseBracket),
"array index", "array index",
)?; )?;
result = mk!(self, ExprDef::GetField(Box::new(expr), Box::new(index))); result = Expr::new(ExprDef::GetField(Box::new(expr), Box::new(index)));
} }
TokenData::Punctuator(Punctuator::Semicolon) | TokenData::Comment(_) => { TokenData::Punctuator(Punctuator::Semicolon) | TokenData::Comment(_) => {
self.pos += 1; self.pos += 1;
@ -703,7 +669,7 @@ impl Parser {
TokenData::Punctuator(Punctuator::Assign) => { TokenData::Punctuator(Punctuator::Assign) => {
self.pos += 1; self.pos += 1;
let next = self.parse()?; let next = self.parse()?;
result = mk!(self, ExprDef::Assign(Box::new(expr), Box::new(next))); result = Expr::new(ExprDef::Assign(Box::new(expr), Box::new(next)));
} }
TokenData::Punctuator(Punctuator::AssignAdd) => { TokenData::Punctuator(Punctuator::AssignAdd) => {
result = self.binop(BinOp::Assign(AssignOp::Add), expr)? result = self.binop(BinOp::Assign(AssignOp::Add), expr)?
@ -746,7 +712,7 @@ impl Parser {
_ => return Err(ParseError::ExpectedExpr("identifier", result)), _ => return Err(ParseError::ExpectedExpr("identifier", result)),
} }
let next = self.parse()?; let next = self.parse()?;
result = mk!(self, ExprDef::ArrowFunctionDecl(args, Box::new(next))); result = Expr::new(ExprDef::ArrowFunctionDecl(args, Box::new(next)));
} }
TokenData::Punctuator(Punctuator::Add) => { TokenData::Punctuator(Punctuator::Add) => {
result = self.binop(BinOp::Num(NumOp::Add), expr)? result = self.binop(BinOp::Num(NumOp::Add), expr)?
@ -812,16 +778,16 @@ impl Parser {
result = self.binop(BinOp::Comp(CompOp::GreaterThanOrEqual), expr)? result = self.binop(BinOp::Comp(CompOp::GreaterThanOrEqual), expr)?
} }
TokenData::Punctuator(Punctuator::Inc) => { TokenData::Punctuator(Punctuator::Inc) => {
result = mk!( result = Expr::new(ExprDef::UnaryOp(
self, UnaryOp::IncrementPost,
ExprDef::UnaryOp(UnaryOp::IncrementPost, Box::new(self.parse()?)) Box::new(self.parse()?),
) ))
} }
TokenData::Punctuator(Punctuator::Dec) => { TokenData::Punctuator(Punctuator::Dec) => {
result = mk!( result = Expr::new(ExprDef::UnaryOp(
self, UnaryOp::DecrementPost,
ExprDef::UnaryOp(UnaryOp::DecrementPost, Box::new(self.parse()?)) Box::new(self.parse()?),
) ))
} }
_ => carry_on = false, _ => carry_on = false,
}; };
@ -840,25 +806,20 @@ impl Parser {
ExprDef::BinOp(ref op2, ref a, ref b) => { ExprDef::BinOp(ref op2, ref a, ref b) => {
let other_precedence = op2.get_precedence(); let other_precedence = op2.get_precedence();
if precedence < other_precedence || (precedence == other_precedence && !assoc) { if precedence < other_precedence || (precedence == other_precedence && !assoc) {
mk!( Expr::new(ExprDef::BinOp(
self,
ExprDef::BinOp(
op2.clone(), op2.clone(),
b.clone(), b.clone(),
Box::new(mk!( Box::new(Expr::new(ExprDef::BinOp(
self, op.clone(),
ExprDef::BinOp(op.clone(), Box::new(orig), a.clone()) Box::new(orig),
a.clone(),
))),
)) ))
)
)
} else { } else {
mk!( Expr::new(ExprDef::BinOp(op, Box::new(orig), Box::new(next.clone())))
self,
ExprDef::BinOp(op, Box::new(orig), Box::new(next.clone()))
)
} }
} }
_ => mk!(self, ExprDef::BinOp(op, Box::new(orig), Box::new(next))), _ => Expr::new(ExprDef::BinOp(op, Box::new(orig), Box::new(next))),
}) })
} }

Loading…
Cancel
Save