Improve position display.
This commit is contained in:
@@ -306,7 +306,7 @@ impl Expr {
|
||||
|
||||
Err(
|
||||
PERR::MismatchedType("a boolean expression".to_string(), type_name.to_string())
|
||||
.into_err(self.position()),
|
||||
.into_err(self.start_position()),
|
||||
)
|
||||
}
|
||||
/// Raise an error if the expression can never yield an iterable value.
|
||||
@@ -326,7 +326,7 @@ impl Expr {
|
||||
|
||||
Err(
|
||||
PERR::MismatchedType("an iterable value".to_string(), type_name.to_string())
|
||||
.into_err(self.position()),
|
||||
.into_err(self.start_position()),
|
||||
)
|
||||
}
|
||||
}
|
||||
@@ -521,6 +521,7 @@ fn parse_fn_call(
|
||||
namespace,
|
||||
hashes,
|
||||
args,
|
||||
pos: settings.pos,
|
||||
..Default::default()
|
||||
}
|
||||
.into_fn_call_expr(settings.pos));
|
||||
@@ -585,6 +586,7 @@ fn parse_fn_call(
|
||||
namespace,
|
||||
hashes,
|
||||
args,
|
||||
pos: settings.pos,
|
||||
..Default::default()
|
||||
}
|
||||
.into_fn_call_expr(settings.pos));
|
||||
@@ -652,7 +654,7 @@ fn parse_index_chain(
|
||||
return Err(PERR::MalformedIndexExpr(
|
||||
"Only arrays, object maps and strings can be indexed".into(),
|
||||
)
|
||||
.into_err(lhs.position()))
|
||||
.into_err(lhs.start_position()))
|
||||
}
|
||||
|
||||
Expr::CharConstant(_, _)
|
||||
@@ -663,7 +665,7 @@ fn parse_index_chain(
|
||||
return Err(PERR::MalformedIndexExpr(
|
||||
"Only arrays, object maps and strings can be indexed".into(),
|
||||
)
|
||||
.into_err(lhs.position()))
|
||||
.into_err(lhs.start_position()))
|
||||
}
|
||||
|
||||
_ => (),
|
||||
@@ -677,7 +679,7 @@ fn parse_index_chain(
|
||||
return Err(PERR::MalformedIndexExpr(
|
||||
"Array or string expects numeric index, not a string".into(),
|
||||
)
|
||||
.into_err(idx_expr.position()))
|
||||
.into_err(idx_expr.start_position()))
|
||||
}
|
||||
|
||||
#[cfg(not(feature = "no_float"))]
|
||||
@@ -685,7 +687,7 @@ fn parse_index_chain(
|
||||
return Err(PERR::MalformedIndexExpr(
|
||||
"Only arrays, object maps and strings can be indexed".into(),
|
||||
)
|
||||
.into_err(lhs.position()))
|
||||
.into_err(lhs.start_position()))
|
||||
}
|
||||
|
||||
Expr::CharConstant(_, _)
|
||||
@@ -696,7 +698,7 @@ fn parse_index_chain(
|
||||
return Err(PERR::MalformedIndexExpr(
|
||||
"Only arrays, object maps and strings can be indexed".into(),
|
||||
)
|
||||
.into_err(lhs.position()))
|
||||
.into_err(lhs.start_position()))
|
||||
}
|
||||
|
||||
_ => (),
|
||||
@@ -708,35 +710,35 @@ fn parse_index_chain(
|
||||
return Err(PERR::MalformedIndexExpr(
|
||||
"Array access expects integer index, not a float".into(),
|
||||
)
|
||||
.into_err(x.position()))
|
||||
.into_err(x.start_position()))
|
||||
}
|
||||
// lhs[char]
|
||||
x @ Expr::CharConstant(_, _) => {
|
||||
return Err(PERR::MalformedIndexExpr(
|
||||
"Array access expects integer index, not a character".into(),
|
||||
)
|
||||
.into_err(x.position()))
|
||||
.into_err(x.start_position()))
|
||||
}
|
||||
// lhs[()]
|
||||
x @ Expr::Unit(_) => {
|
||||
return Err(PERR::MalformedIndexExpr(
|
||||
"Array access expects integer index, not ()".into(),
|
||||
)
|
||||
.into_err(x.position()))
|
||||
.into_err(x.start_position()))
|
||||
}
|
||||
// lhs[??? && ???], lhs[??? || ???]
|
||||
x @ Expr::And(_, _) | x @ Expr::Or(_, _) => {
|
||||
return Err(PERR::MalformedIndexExpr(
|
||||
"Array access expects integer index, not a boolean".into(),
|
||||
)
|
||||
.into_err(x.position()))
|
||||
.into_err(x.start_position()))
|
||||
}
|
||||
// lhs[true], lhs[false]
|
||||
x @ Expr::BoolConstant(_, _) => {
|
||||
return Err(PERR::MalformedIndexExpr(
|
||||
"Array access expects integer index, not a boolean".into(),
|
||||
)
|
||||
.into_err(x.position()))
|
||||
.into_err(x.start_position()))
|
||||
}
|
||||
// All other expressions
|
||||
_ => (),
|
||||
@@ -1048,7 +1050,7 @@ fn parse_switch(
|
||||
|
||||
let (hash, range) = if let Some(expr) = expr {
|
||||
let value = expr.get_literal_value().ok_or_else(|| {
|
||||
PERR::ExprExpected("a literal".to_string()).into_err(expr.position())
|
||||
PERR::ExprExpected("a literal".to_string()).into_err(expr.start_position())
|
||||
})?;
|
||||
|
||||
let guard = value.read_lock::<ExclusiveRange>();
|
||||
@@ -1058,14 +1060,14 @@ fn parse_switch(
|
||||
} else if let Some(range) = value.read_lock::<InclusiveRange>() {
|
||||
(None, Some((*range.start(), *range.end(), true)))
|
||||
} else if value.is::<INT>() && !ranges.is_empty() {
|
||||
return Err(PERR::WrongSwitchIntegerCase.into_err(expr.position()));
|
||||
return Err(PERR::WrongSwitchIntegerCase.into_err(expr.start_position()));
|
||||
} else {
|
||||
let hasher = &mut get_hasher();
|
||||
value.hash(hasher);
|
||||
let hash = hasher.finish();
|
||||
|
||||
if cases.contains_key(&hash) {
|
||||
return Err(PERR::DuplicatedSwitchCase.into_err(expr.position()));
|
||||
return Err(PERR::DuplicatedSwitchCase.into_err(expr.start_position()));
|
||||
}
|
||||
(Some(hash), None)
|
||||
}
|
||||
@@ -1682,6 +1684,7 @@ fn parse_unary(
|
||||
name: state.get_identifier("", "-"),
|
||||
hashes: FnCallHashes::from_native(calc_fn_hash("-", 1)),
|
||||
args,
|
||||
pos,
|
||||
..Default::default()
|
||||
}
|
||||
.into_fn_call_expr(pos))
|
||||
@@ -1708,6 +1711,7 @@ fn parse_unary(
|
||||
name: state.get_identifier("", "+"),
|
||||
hashes: FnCallHashes::from_native(calc_fn_hash("+", 1)),
|
||||
args,
|
||||
pos,
|
||||
..Default::default()
|
||||
}
|
||||
.into_fn_call_expr(pos))
|
||||
@@ -1725,6 +1729,7 @@ fn parse_unary(
|
||||
name: state.get_identifier("", "!"),
|
||||
hashes: FnCallHashes::from_native(calc_fn_hash("!", 1)),
|
||||
args,
|
||||
pos,
|
||||
..Default::default()
|
||||
}
|
||||
.into_fn_call_expr(pos))
|
||||
@@ -1753,7 +1758,7 @@ fn make_assignment_stmt(
|
||||
}
|
||||
Expr::Property(_, _) => None,
|
||||
// Anything other than a property after dotting (e.g. a method call) is not an l-value
|
||||
ref e => Some(e.position()),
|
||||
ref e => Some(e.start_position()),
|
||||
},
|
||||
Expr::Index(x, term, _) | Expr::Dot(x, term, _) => match x.lhs {
|
||||
Expr::Property(_, _) => unreachable!("unexpected Expr::Property in indexing"),
|
||||
@@ -1762,7 +1767,7 @@ fn make_assignment_stmt(
|
||||
},
|
||||
Expr::Property(_, _) if parent_is_dot => None,
|
||||
Expr::Property(_, _) => unreachable!("unexpected Expr::Property in indexing"),
|
||||
e if parent_is_dot => Some(e.position()),
|
||||
e if parent_is_dot => Some(e.start_position()),
|
||||
_ => None,
|
||||
}
|
||||
}
|
||||
@@ -1772,7 +1777,7 @@ fn make_assignment_stmt(
|
||||
match lhs {
|
||||
// const_expr = rhs
|
||||
ref expr if expr.is_constant() => {
|
||||
Err(PERR::AssignmentToConstant("".into()).into_err(lhs.position()))
|
||||
Err(PERR::AssignmentToConstant("".into()).into_err(lhs.start_position()))
|
||||
}
|
||||
// var (non-indexed) = rhs
|
||||
Expr::Variable(None, _, ref x) if x.0.is_none() => Ok(Stmt::Assignment(
|
||||
@@ -1814,10 +1819,8 @@ fn make_assignment_stmt(
|
||||
op_pos,
|
||||
)),
|
||||
// expr[???] = rhs, expr.??? = rhs
|
||||
ref expr => {
|
||||
Err(PERR::AssignmentToInvalidLHS("".to_string())
|
||||
.into_err(expr.position()))
|
||||
}
|
||||
ref expr => Err(PERR::AssignmentToInvalidLHS("".to_string())
|
||||
.into_err(expr.start_position())),
|
||||
}
|
||||
}
|
||||
Some(err_pos) => {
|
||||
@@ -1832,7 +1835,7 @@ fn make_assignment_stmt(
|
||||
)
|
||||
.into_err(op_pos)),
|
||||
// expr = rhs
|
||||
_ => Err(PERR::AssignmentToInvalidLHS("".to_string()).into_err(lhs.position())),
|
||||
_ => Err(PERR::AssignmentToInvalidLHS("".to_string()).into_err(lhs.start_position())),
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1983,7 +1986,7 @@ fn make_dot_expr(
|
||||
Ok(Expr::Dot(BinaryExpr { lhs, rhs }.into(), false, op_pos))
|
||||
}
|
||||
// lhs.rhs
|
||||
(_, rhs) => Err(PERR::PropertyExpected.into_err(rhs.position())),
|
||||
(_, rhs) => Err(PERR::PropertyExpected.into_err(rhs.start_position())),
|
||||
}
|
||||
}
|
||||
|
||||
@@ -2065,6 +2068,7 @@ fn parse_binary_op(
|
||||
let op_base = FnCallExpr {
|
||||
name: state.get_identifier("", op),
|
||||
hashes: FnCallHashes::from_native(hash),
|
||||
pos,
|
||||
..Default::default()
|
||||
};
|
||||
|
||||
@@ -2082,7 +2086,10 @@ fn parse_binary_op(
|
||||
| Token::LessThan
|
||||
| Token::LessThanEqualsTo
|
||||
| Token::GreaterThan
|
||||
| Token::GreaterThanEqualsTo => FnCallExpr { args, ..op_base }.into_fn_call_expr(pos),
|
||||
| Token::GreaterThanEqualsTo => {
|
||||
let pos = args[0].start_position();
|
||||
FnCallExpr { args, ..op_base }.into_fn_call_expr(pos)
|
||||
}
|
||||
|
||||
Token::Or => {
|
||||
let rhs = args.pop().unwrap();
|
||||
@@ -2111,6 +2118,7 @@ fn parse_binary_op(
|
||||
Token::In => {
|
||||
// Swap the arguments
|
||||
let current_lhs = args.remove(0);
|
||||
let pos = current_lhs.start_position();
|
||||
args.push(current_lhs);
|
||||
args.shrink_to_fit();
|
||||
|
||||
@@ -2132,6 +2140,7 @@ fn parse_binary_op(
|
||||
.map_or(false, Option::is_some) =>
|
||||
{
|
||||
let hash = calc_fn_hash(&s, 2);
|
||||
let pos = args[0].start_position();
|
||||
|
||||
FnCallExpr {
|
||||
hashes: if is_valid_function_name(&s) {
|
||||
@@ -2145,7 +2154,10 @@ fn parse_binary_op(
|
||||
.into_fn_call_expr(pos)
|
||||
}
|
||||
|
||||
_ => FnCallExpr { args, ..op_base }.into_fn_call_expr(pos),
|
||||
_ => {
|
||||
let pos = args[0].start_position();
|
||||
FnCallExpr { args, ..op_base }.into_fn_call_expr(pos)
|
||||
}
|
||||
};
|
||||
}
|
||||
}
|
||||
@@ -2734,13 +2746,10 @@ fn parse_block(
|
||||
#[cfg(not(feature = "no_module"))]
|
||||
let orig_imports_len = state.imports.len();
|
||||
|
||||
loop {
|
||||
let end_pos = loop {
|
||||
// Terminated?
|
||||
match input.peek().expect(NEVER_ENDS) {
|
||||
(Token::RightBrace, _) => {
|
||||
eat_token(input, Token::RightBrace);
|
||||
break;
|
||||
}
|
||||
(Token::RightBrace, _) => break eat_token(input, Token::RightBrace),
|
||||
(Token::EOF, pos) => {
|
||||
return Err(PERR::MissingToken(
|
||||
Token::RightBrace.into(),
|
||||
@@ -2767,10 +2776,7 @@ fn parse_block(
|
||||
|
||||
match input.peek().expect(NEVER_ENDS) {
|
||||
// { ... stmt }
|
||||
(Token::RightBrace, _) => {
|
||||
eat_token(input, Token::RightBrace);
|
||||
break;
|
||||
}
|
||||
(Token::RightBrace, _) => break eat_token(input, Token::RightBrace),
|
||||
// { ... stmt;
|
||||
(Token::SemiColon, _) if need_semicolon => {
|
||||
eat_token(input, Token::SemiColon);
|
||||
@@ -2793,7 +2799,7 @@ fn parse_block(
|
||||
.into_err(*pos));
|
||||
}
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
state.stack.truncate(state.entry_stack_len);
|
||||
state.entry_stack_len = prev_entry_stack_len;
|
||||
@@ -2801,7 +2807,10 @@ fn parse_block(
|
||||
#[cfg(not(feature = "no_module"))]
|
||||
state.imports.truncate(orig_imports_len);
|
||||
|
||||
Ok(Stmt::Block(statements.into_boxed_slice(), settings.pos))
|
||||
Ok(Stmt::Block(
|
||||
statements.into_boxed_slice(),
|
||||
(settings.pos, end_pos),
|
||||
))
|
||||
}
|
||||
|
||||
/// Parse an expression as a statement.
|
||||
@@ -3244,6 +3253,7 @@ fn make_curry_from_externals(
|
||||
num_externals + 1,
|
||||
)),
|
||||
args,
|
||||
pos,
|
||||
..Default::default()
|
||||
}
|
||||
.into_fn_call_expr(pos);
|
||||
@@ -3253,7 +3263,7 @@ fn make_curry_from_externals(
|
||||
let mut statements = StaticVec::with_capacity(externals.len() + 1);
|
||||
statements.extend(externals.into_iter().map(Stmt::Share));
|
||||
statements.push(Stmt::Expr(expr));
|
||||
Expr::Stmt(crate::ast::StmtBlock::new(statements, pos).into())
|
||||
Expr::Stmt(crate::ast::StmtBlock::new(statements, pos, Position::NONE).into())
|
||||
}
|
||||
|
||||
/// Parse an anonymous function definition.
|
||||
|
Reference in New Issue
Block a user