Rust 2018

This commit is contained in:
timfish
2019-09-18 11:21:07 +01:00
parent b92ed6201e
commit 82fd20b2b1
41 changed files with 533 additions and 490 deletions

View File

@@ -1,8 +1,8 @@
use std::char;
use std::error::Error;
use std::fmt;
use std::iter::Peekable;
use std::str::Chars;
use std::char;
#[derive(Debug, Clone)]
pub enum LexError {
@@ -10,7 +10,7 @@ pub enum LexError {
MalformedEscapeSequence,
MalformedNumber,
MalformedChar,
Nothing
Nothing,
}
impl Error for LexError {
@@ -20,13 +20,13 @@ impl Error for LexError {
LexError::MalformedEscapeSequence => "Unexpected values in escape sequence",
LexError::MalformedNumber => "Unexpected characters in number",
LexError::MalformedChar => "Char constant not a single character",
LexError::Nothing => "This error is for internal use only"
LexError::Nothing => "This error is for internal use only",
}
}
}
impl fmt::Display for LexError {
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
write!(f, "{}", self.description())
}
}
@@ -65,11 +65,13 @@ impl Error for ParseError {
}
}
fn cause(&self) -> Option<&Error> { None }
fn cause(&self) -> Option<&dyn Error> {
None
}
}
impl fmt::Display for ParseError {
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
write!(f, "{}", self.description())
}
}
@@ -268,11 +270,7 @@ impl Token {
use self::Token::*;
match *self {
UnaryPlus |
UnaryMinus |
Equals |
Bang |
Return => true,
UnaryPlus | UnaryMinus | Equals | Bang | Return => true,
_ => false,
}
}
@@ -390,14 +388,14 @@ impl<'a> TokenIterator<'a> {
fn inner_next(&mut self) -> Option<Token> {
while let Some(c) = self.char_stream.next() {
match c {
'0'...'9' => {
'0'..='9' => {
let mut result = Vec::new();
let mut radix_base: Option<u32> = None;
result.push(c);
while let Some(&nxt) = self.char_stream.peek() {
match nxt {
'0'...'9' => {
'0'..='9' => {
result.push(nxt);
self.char_stream.next();
}
@@ -406,7 +404,7 @@ impl<'a> TokenIterator<'a> {
self.char_stream.next();
while let Some(&nxt_float) = self.char_stream.peek() {
match nxt_float {
'0'...'9' => {
'0'..='9' => {
result.push(nxt_float);
self.char_stream.next();
}
@@ -419,7 +417,7 @@ impl<'a> TokenIterator<'a> {
self.char_stream.next();
while let Some(&nxt_hex) = self.char_stream.peek() {
match nxt_hex {
'0'...'9' | 'a'...'f' | 'A'...'F' => {
'0'..='9' | 'a'..='f' | 'A'..='F' => {
result.push(nxt_hex);
self.char_stream.next();
}
@@ -433,7 +431,7 @@ impl<'a> TokenIterator<'a> {
self.char_stream.next();
while let Some(&nxt_oct) = self.char_stream.peek() {
match nxt_oct {
'0'...'8' => {
'0'..='8' => {
result.push(nxt_oct);
self.char_stream.next();
}
@@ -461,7 +459,12 @@ impl<'a> TokenIterator<'a> {
}
if let Some(radix) = radix_base {
let out: String = result.iter().cloned().skip(2).filter(|c| c != &'_').collect();
let out: String = result
.iter()
.cloned()
.skip(2)
.filter(|c| c != &'_')
.collect();
if let Ok(val) = i64::from_str_radix(&out, radix) {
return Some(Token::IntConst(val));
}
@@ -476,7 +479,7 @@ impl<'a> TokenIterator<'a> {
}
return Some(Token::LexErr(LexError::MalformedNumber));
}
'A'...'Z' | 'a'...'z' | '_' => {
'A'..='Z' | 'a'..='z' | '_' => {
let mut result = Vec::new();
result.push(c);
@@ -505,30 +508,26 @@ impl<'a> TokenIterator<'a> {
x => return Some(Token::Identifier(x.to_string())),
}
}
'"' => {
match self.parse_string_const('"') {
Ok(out) => return Some(Token::StringConst(out)),
Err(e) => return Some(Token::LexErr(e)),
}
}
'\'' => {
match self.parse_string_const('\'') {
Ok(result) => {
let mut chars = result.chars();
'"' => match self.parse_string_const('"') {
Ok(out) => return Some(Token::StringConst(out)),
Err(e) => return Some(Token::LexErr(e)),
},
'\'' => match self.parse_string_const('\'') {
Ok(result) => {
let mut chars = result.chars();
if let Some(out) = chars.next() {
println!("result: {}", result);
if chars.count() != 0 {
return Some(Token::LexErr(LexError::MalformedChar));
}
return Some(Token::CharConst(out));
} else {
if let Some(out) = chars.next() {
println!("result: {}", result);
if chars.count() != 0 {
return Some(Token::LexErr(LexError::MalformedChar));
}
return Some(Token::CharConst(out));
} else {
return Some(Token::LexErr(LexError::MalformedChar));
}
Err(e) => return Some(Token::LexErr(e)),
}
}
Err(e) => return Some(Token::LexErr(e)),
},
'{' => return Some(Token::LCurly),
'}' => return Some(Token::RCurly),
'(' => return Some(Token::LParen),
@@ -540,182 +539,168 @@ impl<'a> TokenIterator<'a> {
Some(&'=') => {
self.char_stream.next();
Some(Token::PlusAssign)
},
}
_ if self.last.is_next_unary() => Some(Token::UnaryPlus),
_ => Some(Token::Plus),
}
},
}
'-' => {
return match self.char_stream.peek() {
Some(&'=') => {
self.char_stream.next();
Some(Token::MinusAssign)
},
}
_ if self.last.is_next_unary() => Some(Token::UnaryMinus),
_ => Some(Token::Minus),
}
},
}
'*' => {
return match self.char_stream.peek() {
Some(&'=') => {
self.char_stream.next();
Some(Token::MultiplyAssign)
},
_ => Some(Token::Multiply)
}
},
'/' => {
match self.char_stream.peek() {
Some(&'/') => {
self.char_stream.next();
while let Some(c) = self.char_stream.next() {
if c == '\n' { break; }
}
}
Some(&'*') => {
let mut level = 1;
self.char_stream.next();
while let Some(c) = self.char_stream.next() {
match c {
'/' => if let Some('*') = self.char_stream.next() {
level+=1;
}
'*' => if let Some('/') = self.char_stream.next() {
level-=1;
}
_ => (),
}
if level == 0 {
break;
}
}
}
Some(&'=') => {
self.char_stream.next();
return Some(Token::DivideAssign);
}
_ => return Some(Token::Divide),
_ => Some(Token::Multiply),
}
}
'/' => match self.char_stream.peek() {
Some(&'/') => {
self.char_stream.next();
while let Some(c) = self.char_stream.next() {
if c == '\n' {
break;
}
}
}
Some(&'*') => {
let mut level = 1;
self.char_stream.next();
while let Some(c) = self.char_stream.next() {
match c {
'/' => {
if let Some('*') = self.char_stream.next() {
level += 1;
}
}
'*' => {
if let Some('/') = self.char_stream.next() {
level -= 1;
}
}
_ => (),
}
if level == 0 {
break;
}
}
}
Some(&'=') => {
self.char_stream.next();
return Some(Token::DivideAssign);
}
_ => return Some(Token::Divide),
},
';' => return Some(Token::Semicolon),
':' => return Some(Token::Colon),
',' => return Some(Token::Comma),
'.' => return Some(Token::Period),
'=' => {
match self.char_stream.peek() {
Some(&'=') => {
self.char_stream.next();
return Some(Token::EqualTo);
}
_ => return Some(Token::Equals),
}
}
'<' => {
match self.char_stream.peek() {
Some(&'=') => {
self.char_stream.next();
return Some(Token::LessThanEqual);
}
Some(&'<') => {
self.char_stream.next();
return match self.char_stream.peek() {
Some(&'=') => {
self.char_stream.next();
Some(Token::LeftShiftAssign)
},
_ => {
self.char_stream.next();
Some(Token::LeftShift)
}
}
}
_ => return Some(Token::LessThan),
}
}
'>' => {
match self.char_stream.peek() {
Some(&'=') => {
self.char_stream.next();
return Some(Token::GreaterThanEqual);
}
Some(&'>') => {
self.char_stream.next();
return match self.char_stream.peek() {
Some(&'=') => {
self.char_stream.next();
Some(Token::RightShiftAssign)
},
_ => {
self.char_stream.next();
Some(Token::RightShift)
}
}
}
_ => return Some(Token::GreaterThan),
}
}
'!' => {
match self.char_stream.peek() {
Some(&'=') => {
self.char_stream.next();
return Some(Token::NotEqualTo);
}
_ => return Some(Token::Bang),
}
}
'|' => {
match self.char_stream.peek() {
Some(&'|') => {
self.char_stream.next();
return Some(Token::Or);
}
Some(&'=') => {
self.char_stream.next();
return Some(Token::OrAssign);
}
_ => return Some(Token::Pipe),
}
}
'&' => {
match self.char_stream.peek() {
Some(&'&') => {
self.char_stream.next();
return Some(Token::And);
}
Some(&'=') => {
self.char_stream.next();
return Some(Token::AndAssign);
}
_ => return Some(Token::Ampersand),
}
}
'^' => {
match self.char_stream.peek() {
Some(&'=') => {
self.char_stream.next();
return Some(Token::XOrAssign);
}
_ => return Some(Token::XOr)
'=' => match self.char_stream.peek() {
Some(&'=') => {
self.char_stream.next();
return Some(Token::EqualTo);
}
_ => return Some(Token::Equals),
},
'%' => {
match self.char_stream.peek() {
Some(&'=') => {
self.char_stream.next();
return Some(Token::ModuloAssign);
}
_ => return Some(Token::Modulo)
'<' => match self.char_stream.peek() {
Some(&'=') => {
self.char_stream.next();
return Some(Token::LessThanEqual);
}
Some(&'<') => {
self.char_stream.next();
return match self.char_stream.peek() {
Some(&'=') => {
self.char_stream.next();
Some(Token::LeftShiftAssign)
}
_ => {
self.char_stream.next();
Some(Token::LeftShift)
}
};
}
_ => return Some(Token::LessThan),
},
'~' => {
match self.char_stream.peek() {
Some(&'=') => {
self.char_stream.next();
return Some(Token::PowerOfAssign);
}
_ => return Some(Token::PowerOf)
'>' => match self.char_stream.peek() {
Some(&'=') => {
self.char_stream.next();
return Some(Token::GreaterThanEqual);
}
Some(&'>') => {
self.char_stream.next();
return match self.char_stream.peek() {
Some(&'=') => {
self.char_stream.next();
Some(Token::RightShiftAssign)
}
_ => {
self.char_stream.next();
Some(Token::RightShift)
}
};
}
_ => return Some(Token::GreaterThan),
},
'!' => match self.char_stream.peek() {
Some(&'=') => {
self.char_stream.next();
return Some(Token::NotEqualTo);
}
_ => return Some(Token::Bang),
},
'|' => match self.char_stream.peek() {
Some(&'|') => {
self.char_stream.next();
return Some(Token::Or);
}
Some(&'=') => {
self.char_stream.next();
return Some(Token::OrAssign);
}
_ => return Some(Token::Pipe),
},
'&' => match self.char_stream.peek() {
Some(&'&') => {
self.char_stream.next();
return Some(Token::And);
}
Some(&'=') => {
self.char_stream.next();
return Some(Token::AndAssign);
}
_ => return Some(Token::Ampersand),
},
'^' => match self.char_stream.peek() {
Some(&'=') => {
self.char_stream.next();
return Some(Token::XOrAssign);
}
_ => return Some(Token::XOr),
},
'%' => match self.char_stream.peek() {
Some(&'=') => {
self.char_stream.next();
return Some(Token::ModuloAssign);
}
_ => return Some(Token::Modulo),
},
'~' => match self.char_stream.peek() {
Some(&'=') => {
self.char_stream.next();
return Some(Token::PowerOfAssign);
}
_ => return Some(Token::PowerOf),
},
_x if _x.is_whitespace() => (),
_ => return Some(Token::LexErr(LexError::UnexpectedChar)),
@@ -739,8 +724,11 @@ impl<'a> Iterator for TokenIterator<'a> {
}
}
pub fn lex(input: &str) -> TokenIterator {
TokenIterator { last: Token::LexErr(LexError::Nothing), char_stream: input.chars().peekable() }
pub fn lex(input: &str) -> TokenIterator<'_> {
TokenIterator {
last: Token::LexErr(LexError::Nothing),
char_stream: input.chars().peekable(),
}
}
fn get_precedence(token: &Token) -> i32 {
@@ -757,24 +745,17 @@ fn get_precedence(token: &Token) -> i32 {
| Token::XOrAssign
| Token::ModuloAssign
| Token::PowerOfAssign => 10,
Token::Or
| Token::XOr
| Token::Pipe => 11,
Token::And
| Token::Ampersand => 12,
Token::Or | Token::XOr | Token::Pipe => 11,
Token::And | Token::Ampersand => 12,
Token::LessThan
| Token::LessThanEqual
| Token::GreaterThan
| Token::GreaterThanEqual
| Token::EqualTo
| Token::NotEqualTo => 15,
Token::Plus
| Token::Minus => 20,
Token::Divide
| Token::Multiply
| Token::PowerOf => 40,
Token::LeftShift
| Token::RightShift => 50,
Token::Plus | Token::Minus => 20,
Token::Divide | Token::Multiply | Token::PowerOf => 40,
Token::LeftShift | Token::RightShift => 50,
Token::Modulo => 60,
Token::Period => 100,
_ => -1,
@@ -782,7 +763,7 @@ fn get_precedence(token: &Token) -> i32 {
}
fn parse_paren_expr<'a>(input: &mut Peekable<TokenIterator<'a>>) -> Result<Expr, ParseError> {
let expr = try!(parse_expr(input));
let expr = parse_expr(input)?;
match input.next() {
Some(Token::RParen) => Ok(expr),
@@ -790,9 +771,10 @@ fn parse_paren_expr<'a>(input: &mut Peekable<TokenIterator<'a>>) -> Result<Expr,
}
}
fn parse_call_expr<'a>(id: String,
input: &mut Peekable<TokenIterator<'a>>)
-> Result<Expr, ParseError> {
fn parse_call_expr<'a>(
id: String,
input: &mut Peekable<TokenIterator<'a>>,
) -> Result<Expr, ParseError> {
let mut args = Vec::new();
if let Some(&Token::RParen) = input.peek() {
@@ -820,9 +802,10 @@ fn parse_call_expr<'a>(id: String,
}
}
fn parse_index_expr<'a>(id: String,
input: &mut Peekable<TokenIterator<'a>>)
-> Result<Expr, ParseError> {
fn parse_index_expr<'a>(
id: String,
input: &mut Peekable<TokenIterator<'a>>,
) -> Result<Expr, ParseError> {
if let Ok(idx) = parse_expr(input) {
match input.peek() {
Some(&Token::RSquare) => {
@@ -836,9 +819,10 @@ fn parse_index_expr<'a>(id: String,
}
}
fn parse_ident_expr<'a>(id: String,
input: &mut Peekable<TokenIterator<'a>>)
-> Result<Expr, ParseError> {
fn parse_ident_expr<'a>(
id: String,
input: &mut Peekable<TokenIterator<'a>>,
) -> Result<Expr, ParseError> {
match input.peek() {
Some(&Token::LParen) => {
input.next();
@@ -862,12 +846,14 @@ fn parse_array_expr<'a>(input: &mut Peekable<TokenIterator<'a>>) -> Result<Expr,
if !skip_contents {
while let Some(_) = input.peek() {
arr.push(try!(parse_expr(input)));
arr.push(parse_expr(input)?);
if let Some(&Token::Comma) = input.peek() {
input.next();
}
if let Some(&Token::RSquare) = input.peek() { break }
if let Some(&Token::RSquare) = input.peek() {
break;
}
}
}
@@ -878,7 +864,6 @@ fn parse_array_expr<'a>(input: &mut Peekable<TokenIterator<'a>>) -> Result<Expr,
}
_ => Err(ParseError::MissingRSquare),
}
}
fn parse_primary<'a>(input: &mut Peekable<TokenIterator<'a>>) -> Result<Expr, ParseError> {
@@ -914,17 +899,27 @@ fn parse_unary<'a>(input: &mut Peekable<TokenIterator<'a>>) -> Result<Expr, Pars
};
match tok {
Token::UnaryMinus => { input.next(); Ok(Expr::FnCall("-".to_string(), vec![parse_primary(input)?])) }
Token::UnaryPlus => { input.next(); parse_primary(input) }
Token::Bang => { input.next(); Ok(Expr::FnCall("!".to_string(), vec![parse_primary(input)?])) }
_ => parse_primary(input)
Token::UnaryMinus => {
input.next();
Ok(Expr::FnCall("-".to_string(), vec![parse_primary(input)?]))
}
Token::UnaryPlus => {
input.next();
parse_primary(input)
}
Token::Bang => {
input.next();
Ok(Expr::FnCall("!".to_string(), vec![parse_primary(input)?]))
}
_ => parse_primary(input),
}
}
fn parse_binop<'a>(input: &mut Peekable<TokenIterator<'a>>,
prec: i32,
lhs: Expr)
-> Result<Expr, ParseError> {
fn parse_binop<'a>(
input: &mut Peekable<TokenIterator<'a>>,
prec: i32,
lhs: Expr,
) -> Result<Expr, ParseError> {
let mut lhs_curr = lhs;
loop {
@@ -939,7 +934,7 @@ fn parse_binop<'a>(input: &mut Peekable<TokenIterator<'a>>,
}
if let Some(op_token) = input.next() {
let mut rhs = try!(parse_unary(input));
let mut rhs = parse_unary(input)?;
let mut next_prec = -1;
@@ -948,10 +943,10 @@ fn parse_binop<'a>(input: &mut Peekable<TokenIterator<'a>>,
}
if curr_prec < next_prec {
rhs = try!(parse_binop(input, curr_prec + 1, rhs));
rhs = parse_binop(input, curr_prec + 1, rhs)?;
} else if curr_prec >= 100 {
// Always bind right to left for precedence over 100
rhs = try!(parse_binop(input, curr_prec, rhs));
rhs = parse_binop(input, curr_prec, rhs)?;
}
lhs_curr = match op_token {
@@ -960,31 +955,27 @@ fn parse_binop<'a>(input: &mut Peekable<TokenIterator<'a>>,
Token::Multiply => Expr::FnCall("*".to_string(), vec![lhs_curr, rhs]),
Token::Divide => Expr::FnCall("/".to_string(), vec![lhs_curr, rhs]),
Token::Equals => Expr::Assignment(Box::new(lhs_curr), Box::new(rhs)),
Token::PlusAssign => {
Token::PlusAssign => {
let lhs_copy = lhs_curr.clone();
Expr::Assignment(
Box::new(lhs_curr),
Box::new(Expr::FnCall("+".to_string(), vec![lhs_copy, rhs]))
Box::new(Expr::FnCall("+".to_string(), vec![lhs_copy, rhs])),
)
},
Token::MinusAssign => {
}
Token::MinusAssign => {
let lhs_copy = lhs_curr.clone();
Expr::Assignment(
Box::new(lhs_curr),
Box::new(Expr::FnCall("-".to_string(), vec![lhs_copy, rhs]))
Box::new(Expr::FnCall("-".to_string(), vec![lhs_copy, rhs])),
)
},
}
Token::Period => Expr::Dot(Box::new(lhs_curr), Box::new(rhs)),
Token::EqualTo => Expr::FnCall("==".to_string(), vec![lhs_curr, rhs]),
Token::NotEqualTo => Expr::FnCall("!=".to_string(), vec![lhs_curr, rhs]),
Token::LessThan => Expr::FnCall("<".to_string(), vec![lhs_curr, rhs]),
Token::LessThanEqual => {
Expr::FnCall("<=".to_string(), vec![lhs_curr, rhs])
}
Token::LessThanEqual => Expr::FnCall("<=".to_string(), vec![lhs_curr, rhs]),
Token::GreaterThan => Expr::FnCall(">".to_string(), vec![lhs_curr, rhs]),
Token::GreaterThanEqual => {
Expr::FnCall(">=".to_string(), vec![lhs_curr, rhs])
}
Token::GreaterThanEqual => Expr::FnCall(">=".to_string(), vec![lhs_curr, rhs]),
Token::Or => Expr::FnCall("||".to_string(), vec![lhs_curr, rhs]),
Token::And => Expr::FnCall("&&".to_string(), vec![lhs_curr, rhs]),
Token::XOr => Expr::FnCall("^".to_string(), vec![lhs_curr, rhs]),
@@ -992,73 +983,71 @@ fn parse_binop<'a>(input: &mut Peekable<TokenIterator<'a>>,
let lhs_copy = lhs_curr.clone();
Expr::Assignment(
Box::new(lhs_curr),
Box::new(Expr::FnCall("|".to_string(), vec![lhs_copy, rhs]))
Box::new(Expr::FnCall("|".to_string(), vec![lhs_copy, rhs])),
)
},
}
Token::AndAssign => {
let lhs_copy = lhs_curr.clone();
Expr::Assignment(
Box::new(lhs_curr),
Box::new(Expr::FnCall("&".to_string(), vec![lhs_copy, rhs]))
Box::new(Expr::FnCall("&".to_string(), vec![lhs_copy, rhs])),
)
},
}
Token::XOrAssign => {
let lhs_copy = lhs_curr.clone();
Expr::Assignment(
Box::new(lhs_curr),
Box::new(Expr::FnCall("^".to_string(), vec![lhs_copy, rhs]))
Box::new(Expr::FnCall("^".to_string(), vec![lhs_copy, rhs])),
)
},
}
Token::MultiplyAssign => {
let lhs_copy = lhs_curr.clone();
Expr::Assignment(
Box::new(lhs_curr),
Box::new(Expr::FnCall("*".to_string(), vec![lhs_copy, rhs]))
Box::new(Expr::FnCall("*".to_string(), vec![lhs_copy, rhs])),
)
},
}
Token::DivideAssign => {
let lhs_copy = lhs_curr.clone();
Expr::Assignment(
Box::new(lhs_curr),
Box::new(Expr::FnCall("/".to_string(), vec![lhs_copy, rhs]))
Box::new(Expr::FnCall("/".to_string(), vec![lhs_copy, rhs])),
)
},
Token::Pipe => {
Expr::FnCall("|".to_string(), vec![lhs_curr, rhs])
},
}
Token::Pipe => Expr::FnCall("|".to_string(), vec![lhs_curr, rhs]),
Token::LeftShift => Expr::FnCall("<<".to_string(), vec![lhs_curr, rhs]),
Token::RightShift => Expr::FnCall(">>".to_string(), vec![lhs_curr, rhs]),
Token::LeftShiftAssign => {
let lhs_copy = lhs_curr.clone();
Expr::Assignment(
Box::new(lhs_curr),
Box::new(Expr::FnCall("<<".to_string(), vec![lhs_copy, rhs]))
Box::new(Expr::FnCall("<<".to_string(), vec![lhs_copy, rhs])),
)
},
}
Token::RightShiftAssign => {
let lhs_copy = lhs_curr.clone();
Expr::Assignment(
Box::new(lhs_curr),
Box::new(Expr::FnCall(">>".to_string(), vec![lhs_copy, rhs]))
Box::new(Expr::FnCall(">>".to_string(), vec![lhs_copy, rhs])),
)
},
}
Token::Ampersand => Expr::FnCall("&".to_string(), vec![lhs_curr, rhs]),
Token::Modulo => Expr::FnCall("%".to_string(), vec![lhs_curr, rhs]),
Token::ModuloAssign => {
let lhs_copy = lhs_curr.clone();
Expr::Assignment(
Box::new(lhs_curr),
Box::new(Expr::FnCall("%".to_string(), vec![lhs_copy, rhs]))
Box::new(Expr::FnCall("%".to_string(), vec![lhs_copy, rhs])),
)
},
}
Token::PowerOf => Expr::FnCall("~".to_string(), vec![lhs_curr, rhs]),
Token::PowerOfAssign => {
let lhs_copy = lhs_curr.clone();
Expr::Assignment(
Box::new(lhs_curr),
Box::new(Expr::FnCall("~".to_string(), vec![lhs_copy, rhs]))
Box::new(Expr::FnCall("~".to_string(), vec![lhs_copy, rhs])),
)
},
}
_ => return Err(ParseError::UnknownOperator),
};
}
@@ -1069,7 +1058,7 @@ fn parse_expr<'a>(input: &mut Peekable<TokenIterator<'a>>) -> Result<Expr, Parse
match input.peek() {
Some(Token::RParen) => Ok(Expr::Unit),
_ => {
let lhs = try!(parse_unary(input));
let lhs = parse_unary(input)?;
parse_binop(input, 0, lhs)
}
@@ -1079,14 +1068,18 @@ fn parse_expr<'a>(input: &mut Peekable<TokenIterator<'a>>) -> Result<Expr, Parse
fn parse_if<'a>(input: &mut Peekable<TokenIterator<'a>>) -> Result<Stmt, ParseError> {
input.next();
let guard = try!(parse_expr(input));
let body = try!(parse_block(input));
let guard = parse_expr(input)?;
let body = parse_block(input)?;
match input.peek() {
Some(&Token::Else) => {
input.next();
let else_body = try!(parse_block(input));
Ok(Stmt::IfElse(Box::new(guard), Box::new(body), Box::new(else_body)))
let else_body = parse_block(input)?;
Ok(Stmt::IfElse(
Box::new(guard),
Box::new(body),
Box::new(else_body),
))
}
_ => Ok(Stmt::If(Box::new(guard), Box::new(body))),
}
@@ -1095,8 +1088,8 @@ fn parse_if<'a>(input: &mut Peekable<TokenIterator<'a>>) -> Result<Stmt, ParseEr
fn parse_while<'a>(input: &mut Peekable<TokenIterator<'a>>) -> Result<Stmt, ParseError> {
input.next();
let guard = try!(parse_expr(input));
let body = try!(parse_block(input));
let guard = parse_expr(input)?;
let body = parse_block(input)?;
Ok(Stmt::While(Box::new(guard), Box::new(body)))
}
@@ -1104,7 +1097,7 @@ fn parse_while<'a>(input: &mut Peekable<TokenIterator<'a>>) -> Result<Stmt, Pars
fn parse_loop<'a>(input: &mut Peekable<TokenIterator<'a>>) -> Result<Stmt, ParseError> {
input.next();
let body = try!(parse_block(input));
let body = parse_block(input)?;
Ok(Stmt::Loop(Box::new(body)))
}
@@ -1120,7 +1113,7 @@ fn parse_var<'a>(input: &mut Peekable<TokenIterator<'a>>) -> Result<Stmt, ParseE
match input.peek() {
Some(&Token::Equals) => {
input.next();
let initializer = try!(parse_expr(input));
let initializer = parse_expr(input)?;
Ok(Stmt::Var(name, Some(Box::new(initializer))))
}
_ => Ok(Stmt::Var(name, None)),
@@ -1144,13 +1137,15 @@ fn parse_block<'a>(input: &mut Peekable<TokenIterator<'a>>) -> Result<Stmt, Pars
if !skip_body {
while let Some(_) = input.peek() {
stmts.push(try!(parse_stmt(input)));
stmts.push(parse_stmt(input)?);
if let Some(&Token::Semicolon) = input.peek() {
input.next();
}
if let Some(&Token::RCurly) = input.peek() { break }
if let Some(&Token::RCurly) = input.peek() {
break;
}
}
}
@@ -1164,7 +1159,7 @@ fn parse_block<'a>(input: &mut Peekable<TokenIterator<'a>>) -> Result<Stmt, Pars
}
fn parse_expr_stmt<'a>(input: &mut Peekable<TokenIterator<'a>>) -> Result<Stmt, ParseError> {
let expr = try!(parse_expr(input));
let expr = parse_expr(input)?;
Ok(Stmt::Expr(Box::new(expr)))
}
@@ -1182,7 +1177,7 @@ fn parse_stmt<'a>(input: &mut Peekable<TokenIterator<'a>>) -> Result<Stmt, Parse
match input.peek() {
Some(&Token::Semicolon) => Ok(Stmt::Return),
_ => {
let ret = try!(parse_expr(input));
let ret = parse_expr(input)?;
Ok(Stmt::ReturnWithVal(Box::new(ret)))
}
}
@@ -1240,15 +1235,16 @@ fn parse_fn<'a>(input: &mut Peekable<TokenIterator<'a>>) -> Result<FnDef, ParseE
})
}
fn parse_top_level<'a>(input: &mut Peekable<TokenIterator<'a>>)
-> Result<(Vec<Stmt>, Vec<FnDef>), ParseError> {
fn parse_top_level<'a>(
input: &mut Peekable<TokenIterator<'a>>,
) -> Result<(Vec<Stmt>, Vec<FnDef>), ParseError> {
let mut stmts = Vec::new();
let mut fndefs = Vec::new();
while let Some(_) = input.peek() {
match input.peek() {
Some(&Token::Fn) => fndefs.push(try!(parse_fn(input))),
_ => stmts.push(try!(parse_stmt(input))),
Some(&Token::Fn) => fndefs.push(parse_fn(input)?),
_ => stmts.push(parse_stmt(input)?),
}
if let Some(&Token::Semicolon) = input.peek() {
@@ -1259,7 +1255,8 @@ fn parse_top_level<'a>(input: &mut Peekable<TokenIterator<'a>>)
Ok((stmts, fndefs))
}
pub fn parse<'a>(input: &mut Peekable<TokenIterator<'a>>)
-> Result<(Vec<Stmt>, Vec<FnDef>), ParseError> {
pub fn parse<'a>(
input: &mut Peekable<TokenIterator<'a>>,
) -> Result<(Vec<Stmt>, Vec<FnDef>), ParseError> {
parse_top_level(input)
}