Always search scope after scope is modified.

This commit is contained in:
Stephen Chung 2023-01-27 22:31:14 +08:00
parent 733bb07d2d
commit f4949a2beb
3 changed files with 27 additions and 4 deletions

View File

@ -505,14 +505,21 @@ impl Engine {
event: DebuggerEvent, event: DebuggerEvent,
) -> Result<Option<DebuggerStatus>, Box<crate::EvalAltResult>> { ) -> Result<Option<DebuggerStatus>, Box<crate::EvalAltResult>> {
if let Some(ref x) = self.debugger_interface { if let Some(ref x) = self.debugger_interface {
let orig_scope_len = scope.len();
let src = global.source_raw().cloned(); let src = global.source_raw().cloned();
let src = src.as_ref().map(|s| s.as_str()); let src = src.as_ref().map(|s| s.as_str());
let context = EvalContext::new(self, global, caches, scope, this_ptr); let context = EvalContext::new(self, global, caches, scope, this_ptr);
let (.., ref on_debugger) = **x; let (.., ref on_debugger) = **x;
let command = on_debugger(context, event, node, src, node.position())?; let command = on_debugger(context, event, node, src, node.position());
match command { if orig_scope_len != scope.len() {
// The scope is changed, always search from now on
global.always_search_scope = true;
}
match command? {
DebuggerCommand::Continue => { DebuggerCommand::Continue => {
global.debugger_mut().status = DebuggerStatus::CONTINUE; global.debugger_mut().status = DebuggerStatus::CONTINUE;
Ok(None) Ok(None)

View File

@ -174,9 +174,18 @@ impl Engine {
// Check the variable resolver, if any // Check the variable resolver, if any
if let Some(ref resolve_var) = self.resolve_var { if let Some(ref resolve_var) = self.resolve_var {
let orig_scope_len = scope.len();
let context = EvalContext::new(self, global, caches, scope, this_ptr); let context = EvalContext::new(self, global, caches, scope, this_ptr);
let var_name = expr.get_variable_name(true).expect("`Expr::Variable`"); let var_name = expr.get_variable_name(true).expect("`Expr::Variable`");
match resolve_var(var_name, index, context) { let resolved_var = resolve_var(var_name, index, context);
if orig_scope_len != scope.len() {
// The scope is changed, always search from now on
global.always_search_scope = true;
}
match resolved_var {
Ok(Some(mut result)) => { Ok(Some(mut result)) => {
result.set_access_mode(AccessMode::ReadOnly); result.set_access_mode(AccessMode::ReadOnly);
return Ok(result.into()); return Ok(result.into());

View File

@ -728,10 +728,17 @@ impl Engine {
nesting_level: global.scope_level, nesting_level: global.scope_level,
will_shadow, will_shadow,
}; };
let orig_scope_len = scope.len();
let context = let context =
EvalContext::new(self, global, caches, scope, this_ptr.as_deref_mut()); EvalContext::new(self, global, caches, scope, this_ptr.as_deref_mut());
let filter_result = filter(true, info, context);
if !filter(true, info, context)? { if orig_scope_len != scope.len() {
// The scope is changed, always search from now on
global.always_search_scope = true;
}
if !filter_result? {
return Err(ERR::ErrorForbiddenVariable(var_name.to_string(), *pos).into()); return Err(ERR::ErrorForbiddenVariable(var_name.to_string(), *pos).into());
} }
} }