summaryrefslogtreecommitdiffstats
path: root/modules/gdscript/gdscript_function.cpp
diff options
context:
space:
mode:
authorGeorge Marques <george@gmarqu.es>2019-05-10 16:38:48 -0300
committerGeorge Marques <george@gmarqu.es>2019-05-14 11:39:40 -0300
commitbdc6649b7991b1c11549a8efb0a708345bf12783 (patch)
tree524c6ea38e9a06cc99bba2cd59a8c420f3df82c1 /modules/gdscript/gdscript_function.cpp
parentbdf79f4c6e98c0e95a31fc6e05d4a072b4fcb362 (diff)
downloadredot-engine-bdc6649b7991b1c11549a8efb0a708345bf12783.tar.gz
Keep GDScript functions in stack while yielding
This prevents GDScript functions from leaving the stack too soon when they are resuming from yield, allowing the ones expecting it to finish to know the caller. Helps debugging cases when you use: `yield(function_which_yields(), "completed")` since now it shows the call that resumed that function.
Diffstat (limited to 'modules/gdscript/gdscript_function.cpp')
-rw-r--r--modules/gdscript/gdscript_function.cpp45
1 files changed, 39 insertions, 6 deletions
diff --git a/modules/gdscript/gdscript_function.cpp b/modules/gdscript/gdscript_function.cpp
index cff9ba55b8..2b9d40b10e 100644
--- a/modules/gdscript/gdscript_function.cpp
+++ b/modules/gdscript/gdscript_function.cpp
@@ -1583,15 +1583,26 @@ Variant GDScriptFunction::call(GDScriptInstance *p_instance, const Variant **p_a
GDScriptLanguage::get_singleton()->script_frame_time += time_taken - function_call_time;
}
- if (ScriptDebugger::get_singleton())
- GDScriptLanguage::get_singleton()->exit_function();
+ bool yielded = retvalue.is_ref() && Object::cast_to<GDScriptFunctionState>(retvalue);
+
+ // Check if this is the last time the function is resuming from yield
+ // Will be true if never yielded as well
+ // When it's the last resume it will postpone the exit from stack,
+ // so the debugger knows which function triggered the resume of the next function (if any)
+ if (!p_state || yielded) {
+ if (ScriptDebugger::get_singleton())
+ GDScriptLanguage::get_singleton()->exit_function();
#endif
- if (_stack_size) {
- //free stack
- for (int i = 0; i < _stack_size; i++)
- stack[i].~Variant();
+ if (_stack_size) {
+ //free stack
+ for (int i = 0; i < _stack_size; i++)
+ stack[i].~Variant();
+ }
+
+#ifdef DEBUG_ENABLED
}
+#endif
return retvalue;
}
@@ -1830,6 +1841,17 @@ Variant GDScriptFunctionState::_signal_callback(const Variant **p_args, int p_ar
}
}
+#ifdef DEBUG_ENABLED
+ if (ScriptDebugger::get_singleton())
+ GDScriptLanguage::get_singleton()->exit_function();
+ if (state.stack_size) {
+ //free stack
+ Variant *stack = (Variant *)state.stack.ptr();
+ for (int i = 0; i < state.stack_size; i++)
+ stack[i].~Variant();
+ }
+#endif
+
return ret;
}
@@ -1884,6 +1906,17 @@ Variant GDScriptFunctionState::resume(const Variant &p_arg) {
} else {
emit_signal("completed", ret);
}
+
+#ifdef DEBUG_ENABLED
+ if (ScriptDebugger::get_singleton())
+ GDScriptLanguage::get_singleton()->exit_function();
+ if (state.stack_size) {
+ //free stack
+ Variant *stack = (Variant *)state.stack.ptr();
+ for (int i = 0; i < state.stack_size; i++)
+ stack[i].~Variant();
+ }
+#endif
}
return ret;