Fix parser bug.
This commit is contained in:
parent
1011602cf6
commit
83786c992b
@ -1,6 +1,15 @@
|
|||||||
Rhai Release Notes
|
Rhai Release Notes
|
||||||
==================
|
==================
|
||||||
|
|
||||||
|
Version 1.6.0
|
||||||
|
=============
|
||||||
|
|
||||||
|
Bug fixes
|
||||||
|
---------
|
||||||
|
|
||||||
|
* Invalid property or method access such as `a.b::c.d` or `a.b::func()` no longer panics but properly returns a syntax error.
|
||||||
|
|
||||||
|
|
||||||
Version 1.5.0
|
Version 1.5.0
|
||||||
=============
|
=============
|
||||||
|
|
||||||
|
@ -1908,7 +1908,7 @@ fn make_dot_expr(
|
|||||||
// lhs.module::id - syntax error
|
// lhs.module::id - syntax error
|
||||||
#[cfg(not(feature = "no_module"))]
|
#[cfg(not(feature = "no_module"))]
|
||||||
(.., Expr::Variable(.., x)) => {
|
(.., Expr::Variable(.., x)) => {
|
||||||
Err(PERR::PropertyExpected.into_err(x.1.expect("`Some`").0[0].pos))
|
Err(PERR::PropertyExpected.into_err(x.1.expect("`Some`").0.position()))
|
||||||
}
|
}
|
||||||
#[cfg(feature = "no_module")]
|
#[cfg(feature = "no_module")]
|
||||||
(.., Expr::Variable(..)) => unreachable!("qualified property name"),
|
(.., Expr::Variable(..)) => unreachable!("qualified property name"),
|
||||||
@ -1918,6 +1918,41 @@ fn make_dot_expr(
|
|||||||
false,
|
false,
|
||||||
op_pos,
|
op_pos,
|
||||||
)),
|
)),
|
||||||
|
// lhs.nnn::func(...) - syntax error
|
||||||
|
(.., Expr::FnCall(func, ..)) if func.is_qualified() => {
|
||||||
|
Err(PERR::PropertyExpected.into_err(func.namespace.expect("`Some`").position()))
|
||||||
|
}
|
||||||
|
// lhs.Fn() or lhs.eval()
|
||||||
|
(.., Expr::FnCall(func, func_pos))
|
||||||
|
if func.args.is_empty()
|
||||||
|
&& [crate::engine::KEYWORD_FN_PTR, crate::engine::KEYWORD_EVAL]
|
||||||
|
.contains(&func.name.as_ref()) =>
|
||||||
|
{
|
||||||
|
let err_msg = format!(
|
||||||
|
"'{}' should not be called in method style. Try {}(...);",
|
||||||
|
func.name, func.name
|
||||||
|
);
|
||||||
|
Err(LexError::ImproperSymbol(func.name.to_string(), err_msg).into_err(func_pos))
|
||||||
|
}
|
||||||
|
// lhs.func!(...)
|
||||||
|
(.., Expr::FnCall(func, func_pos)) if func.capture_parent_scope => {
|
||||||
|
Err(PERR::MalformedCapture(
|
||||||
|
"method-call style does not support running within the caller's scope".into(),
|
||||||
|
)
|
||||||
|
.into_err(func_pos))
|
||||||
|
}
|
||||||
|
// lhs.func(...)
|
||||||
|
(lhs, Expr::FnCall(mut func, func_pos)) => {
|
||||||
|
// Recalculate hash
|
||||||
|
func.hashes = FnCallHashes::from_all(
|
||||||
|
#[cfg(not(feature = "no_function"))]
|
||||||
|
calc_fn_hash(&func.name, func.args.len()),
|
||||||
|
calc_fn_hash(&func.name, func.args.len() + 1),
|
||||||
|
);
|
||||||
|
|
||||||
|
let rhs = Expr::FnCall(func, func_pos);
|
||||||
|
Ok(Expr::Dot(BinaryExpr { lhs, rhs }.into(), false, op_pos))
|
||||||
|
}
|
||||||
// lhs.dot_lhs.dot_rhs or lhs.dot_lhs[idx_rhs]
|
// lhs.dot_lhs.dot_rhs or lhs.dot_lhs[idx_rhs]
|
||||||
(lhs, rhs @ Expr::Dot(..)) | (lhs, rhs @ Expr::Index(..)) => {
|
(lhs, rhs @ Expr::Dot(..)) | (lhs, rhs @ Expr::Index(..)) => {
|
||||||
let (x, term, pos, is_dot) = match rhs {
|
let (x, term, pos, is_dot) = match rhs {
|
||||||
@ -1927,6 +1962,17 @@ fn make_dot_expr(
|
|||||||
};
|
};
|
||||||
|
|
||||||
match x.lhs {
|
match x.lhs {
|
||||||
|
// lhs.module::id.dot_rhs or lhs.module::id[idx_rhs] - syntax error
|
||||||
|
#[cfg(not(feature = "no_module"))]
|
||||||
|
Expr::Variable(.., x) if x.1.is_some() => {
|
||||||
|
Err(PERR::PropertyExpected.into_err(x.1.expect("`Some`").0.position()))
|
||||||
|
}
|
||||||
|
// lhs.module::func().dot_rhs or lhs.module::func()[idx_rhs] - syntax error
|
||||||
|
#[cfg(not(feature = "no_module"))]
|
||||||
|
Expr::FnCall(func, ..) if func.is_qualified() => {
|
||||||
|
Err(PERR::PropertyExpected.into_err(func.namespace.expect("`Some`").position()))
|
||||||
|
}
|
||||||
|
// lhs.id.dot_rhs or lhs.id[idx_rhs]
|
||||||
Expr::Variable(..) | Expr::Property(..) => {
|
Expr::Variable(..) | Expr::Property(..) => {
|
||||||
let new_lhs = BinaryExpr {
|
let new_lhs = BinaryExpr {
|
||||||
lhs: x.lhs.into_property(state),
|
lhs: x.lhs.into_property(state),
|
||||||
@ -1941,6 +1987,7 @@ fn make_dot_expr(
|
|||||||
};
|
};
|
||||||
Ok(Expr::Dot(BinaryExpr { lhs, rhs }.into(), false, op_pos))
|
Ok(Expr::Dot(BinaryExpr { lhs, rhs }.into(), false, op_pos))
|
||||||
}
|
}
|
||||||
|
// lhs.func().dot_rhs or lhs.func()[idx_rhs]
|
||||||
Expr::FnCall(mut func, func_pos) => {
|
Expr::FnCall(mut func, func_pos) => {
|
||||||
// Recalculate hash
|
// Recalculate hash
|
||||||
func.hashes = FnCallHashes::from_all(
|
func.hashes = FnCallHashes::from_all(
|
||||||
@ -1965,42 +2012,6 @@ fn make_dot_expr(
|
|||||||
expr => unreachable!("invalid dot expression: {:?}", expr),
|
expr => unreachable!("invalid dot expression: {:?}", expr),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
// lhs.nnn::func(...)
|
|
||||||
(.., Expr::FnCall(x, ..)) if x.is_qualified() => {
|
|
||||||
unreachable!("method call should not be namespace-qualified")
|
|
||||||
}
|
|
||||||
// lhs.Fn() or lhs.eval()
|
|
||||||
(.., Expr::FnCall(x, pos))
|
|
||||||
if x.args.is_empty()
|
|
||||||
&& [crate::engine::KEYWORD_FN_PTR, crate::engine::KEYWORD_EVAL]
|
|
||||||
.contains(&x.name.as_ref()) =>
|
|
||||||
{
|
|
||||||
Err(LexError::ImproperSymbol(
|
|
||||||
x.name.to_string(),
|
|
||||||
format!(
|
|
||||||
"'{}' should not be called in method style. Try {}(...);",
|
|
||||||
x.name, x.name
|
|
||||||
),
|
|
||||||
)
|
|
||||||
.into_err(pos))
|
|
||||||
}
|
|
||||||
// lhs.func!(...)
|
|
||||||
(.., Expr::FnCall(x, pos)) if x.capture_parent_scope => Err(PERR::MalformedCapture(
|
|
||||||
"method-call style does not support running within the caller's scope".into(),
|
|
||||||
)
|
|
||||||
.into_err(pos)),
|
|
||||||
// lhs.func(...)
|
|
||||||
(lhs, Expr::FnCall(mut func, func_pos)) => {
|
|
||||||
// Recalculate hash
|
|
||||||
func.hashes = FnCallHashes::from_all(
|
|
||||||
#[cfg(not(feature = "no_function"))]
|
|
||||||
calc_fn_hash(&func.name, func.args.len()),
|
|
||||||
calc_fn_hash(&func.name, func.args.len() + 1),
|
|
||||||
);
|
|
||||||
|
|
||||||
let rhs = Expr::FnCall(func, func_pos);
|
|
||||||
Ok(Expr::Dot(BinaryExpr { lhs, rhs }.into(), false, op_pos))
|
|
||||||
}
|
|
||||||
// lhs.rhs
|
// lhs.rhs
|
||||||
(.., rhs) => Err(PERR::PropertyExpected.into_err(rhs.start_position())),
|
(.., rhs) => Err(PERR::PropertyExpected.into_err(rhs.start_position())),
|
||||||
}
|
}
|
||||||
|
Loading…
Reference in New Issue
Block a user