summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorAdam Scott <ascott.ca@gmail.com>2022-12-02 13:27:26 -0500
committerAdam Scott <ascott.ca@gmail.com>2022-12-06 09:35:39 -0500
commit88f3045301470fd13bbe3ade6537a1c1cb1227fe (patch)
tree1b14193cbf349ab4136fd5bd32fa61712daf9282
parentf3e6750a7e4702918e05f42b1376e30e652f2f90 (diff)
Move GDScript uninitialization to `GDScriptLanguage::finalize()`
Co-authored-by: Ricardo Buring <ricardo.buring@gmail.com> Co-authored-by: kleonc <9283098+kleonc@users.noreply.github.com>
-rw-r--r--modules/gdscript/gdscript.cpp66
-rw-r--r--modules/gdscript/gdscript_cache.cpp30
-rw-r--r--modules/gdscript/gdscript_cache.h2
-rw-r--r--scene/resources/shape_2d.cpp5
-rw-r--r--scene/resources/shape_3d.cpp5
5 files changed, 61 insertions, 47 deletions
diff --git a/modules/gdscript/gdscript.cpp b/modules/gdscript/gdscript.cpp
index 60230257e0..c8195de640 100644
--- a/modules/gdscript/gdscript.cpp
+++ b/modules/gdscript/gdscript.cpp
@@ -2019,6 +2019,42 @@ Error GDScriptLanguage::execute_file(const String &p_path) {
}
void GDScriptLanguage::finish() {
+ if (_call_stack) {
+ memdelete_arr(_call_stack);
+ _call_stack = nullptr;
+ }
+
+ // Clear the cache before parsing the script_list
+ GDScriptCache::clear();
+
+ // Clear dependencies between scripts, to ensure cyclic references are broken
+ // (to avoid leaks at exit).
+ SelfList<GDScript> *s = script_list.first();
+ while (s) {
+ // This ensures the current script is not released before we can check
+ // what's the next one in the list (we can't get the next upfront because we
+ // don't know if the reference breaking will cause it -or any other after
+ // it, for that matter- to be released so the next one is not the same as
+ // before).
+ Ref<GDScript> scr = s->self();
+ if (scr.is_valid()) {
+ for (KeyValue<StringName, GDScriptFunction *> &E : scr->member_functions) {
+ GDScriptFunction *func = E.value;
+ for (int i = 0; i < func->argument_types.size(); i++) {
+ func->argument_types.write[i].script_type_ref = Ref<Script>();
+ }
+ func->return_type.script_type_ref = Ref<Script>();
+ }
+ for (KeyValue<StringName, GDScript::MemberInfo> &E : scr->member_indices) {
+ E.value.data_type.script_type_ref = Ref<Script>();
+ }
+
+ // Clear backup for scripts that could slip out of the cyclic reference
+ // check
+ scr->clear();
+ }
+ s = s->next();
+ }
}
void GDScriptLanguage::profiling_start() {
@@ -2530,36 +2566,6 @@ GDScriptLanguage::GDScriptLanguage() {
}
GDScriptLanguage::~GDScriptLanguage() {
- if (_call_stack) {
- memdelete_arr(_call_stack);
- }
-
- // Clear dependencies between scripts, to ensure cyclic references are broken (to avoid leaks at exit).
- SelfList<GDScript> *s = script_list.first();
- while (s) {
- // This ensures the current script is not released before we can check what's the next one
- // in the list (we can't get the next upfront because we don't know if the reference breaking
- // will cause it -or any other after it, for that matter- to be released so the next one
- // is not the same as before).
- Ref<GDScript> scr = s->self();
- if (scr.is_valid()) {
- for (KeyValue<StringName, GDScriptFunction *> &E : scr->member_functions) {
- GDScriptFunction *func = E.value;
- for (int i = 0; i < func->argument_types.size(); i++) {
- func->argument_types.write[i].script_type_ref = Ref<Script>();
- }
- func->return_type.script_type_ref = Ref<Script>();
- }
- for (KeyValue<StringName, GDScript::MemberInfo> &E : scr->member_indices) {
- E.value.data_type.script_type_ref = Ref<Script>();
- }
-
- // Clear backup for scripts that could slip out of the cyclic reference check
- scr->clear();
- }
- s = s->next();
- }
-
singleton = nullptr;
}
diff --git a/modules/gdscript/gdscript_cache.cpp b/modules/gdscript/gdscript_cache.cpp
index 021504f242..699ce67933 100644
--- a/modules/gdscript/gdscript_cache.cpp
+++ b/modules/gdscript/gdscript_cache.cpp
@@ -381,15 +381,15 @@ void GDScriptCache::clear_unreferenced_packed_scenes() {
}
}
-GDScriptCache::GDScriptCache() {
- singleton = this;
-}
+void GDScriptCache::clear() {
+ if (singleton == nullptr) {
+ return;
+ }
-GDScriptCache::~GDScriptCache() {
- destructing = true;
+ MutexLock lock(singleton->mutex);
RBSet<Ref<GDScriptParserRef>> parser_map_refs;
- for (KeyValue<String, GDScriptParserRef *> &E : parser_map) {
+ for (KeyValue<String, GDScriptParserRef *> &E : singleton->parser_map) {
parser_map_refs.insert(E.value);
}
@@ -399,12 +399,20 @@ GDScriptCache::~GDScriptCache() {
}
parser_map_refs.clear();
- parser_map.clear();
- shallow_gdscript_cache.clear();
- full_gdscript_cache.clear();
+ singleton->parser_map.clear();
+ singleton->shallow_gdscript_cache.clear();
+ singleton->full_gdscript_cache.clear();
- packed_scene_cache.clear();
- packed_scene_dependencies.clear();
+ singleton->packed_scene_cache.clear();
+ singleton->packed_scene_dependencies.clear();
+}
+
+GDScriptCache::GDScriptCache() {
+ singleton = this;
+}
+GDScriptCache::~GDScriptCache() {
+ destructing = true;
+ clear();
singleton = nullptr;
}
diff --git a/modules/gdscript/gdscript_cache.h b/modules/gdscript/gdscript_cache.h
index 2195932aa3..e7e1901d5d 100644
--- a/modules/gdscript/gdscript_cache.h
+++ b/modules/gdscript/gdscript_cache.h
@@ -111,6 +111,8 @@ public:
return singleton->destructing;
};
+ static void clear();
+
GDScriptCache();
~GDScriptCache();
};
diff --git a/scene/resources/shape_2d.cpp b/scene/resources/shape_2d.cpp
index 413670d23e..87c6c36ee9 100644
--- a/scene/resources/shape_2d.cpp
+++ b/scene/resources/shape_2d.cpp
@@ -124,7 +124,6 @@ Shape2D::Shape2D(const RID &p_rid) {
}
Shape2D::~Shape2D() {
- if (PhysicsServer2D::get_singleton() != nullptr) {
- PhysicsServer2D::get_singleton()->free(shape);
- }
+ ERR_FAIL_NULL(PhysicsServer2D::get_singleton());
+ PhysicsServer2D::get_singleton()->free(shape);
}
diff --git a/scene/resources/shape_3d.cpp b/scene/resources/shape_3d.cpp
index 44f21d2a48..7992ba9fd4 100644
--- a/scene/resources/shape_3d.cpp
+++ b/scene/resources/shape_3d.cpp
@@ -128,7 +128,6 @@ Shape3D::Shape3D(RID p_shape) :
shape(p_shape) {}
Shape3D::~Shape3D() {
- if (PhysicsServer3D::get_singleton() != nullptr) {
- PhysicsServer3D::get_singleton()->free(shape);
- }
+ ERR_FAIL_NULL(PhysicsServer3D::get_singleton());
+ PhysicsServer3D::get_singleton()->free(shape);
}