From 39ae82623d50f3135861cf762b365c2b0e278882 Mon Sep 17 00:00:00 2001 From: Trevor Davenport Date: Fri, 22 Dec 2023 15:38:43 -0700 Subject: [PATCH] Use ObjectID to track cached scene groups. This prevents a crash that could occur when using the Node pointer would reference a Node which had been freed after node_removal. --- editor/groups_editor.cpp | 20 +++++++++++--------- editor/groups_editor.h | 6 +++--- 2 files changed, 14 insertions(+), 12 deletions(-) diff --git a/editor/groups_editor.cpp b/editor/groups_editor.cpp index 9fa9fe5a9d9..77a867f34b3 100644 --- a/editor/groups_editor.cpp +++ b/editor/groups_editor.cpp @@ -274,20 +274,22 @@ void GroupsEditor::_update_groups_and_tree() { _update_tree(); } -void GroupsEditor::_update_scene_groups(Node *p_node) { - if (scene_groups_cache.has(p_node)) { - scene_groups = scene_groups_cache[p_node]; - scene_groups_cache.erase(p_node); +void GroupsEditor::_update_scene_groups(const ObjectID &p_id) { + HashMap>::Iterator I = scene_groups_cache.find(p_id); + if (I) { + scene_groups = I->value; + scene_groups_cache.remove(I); } else { scene_groups = HashMap(); } } -void GroupsEditor::_cache_scene_groups(Node *p_node) { +void GroupsEditor::_cache_scene_groups(const ObjectID &p_id) { const int edited_scene_count = EditorNode::get_editor_data().get_edited_scene_count(); for (int i = 0; i < edited_scene_count; i++) { - if (p_node == EditorNode::get_editor_data().get_edited_scene_root(i)) { - scene_groups_cache[p_node] = scene_groups_for_caching; + Node *edited_scene_root = EditorNode::get_editor_data().get_edited_scene_root(i); + if (edited_scene_root && p_id == edited_scene_root->get_instance_id()) { + scene_groups_cache[p_id] = scene_groups_for_caching; break; } } @@ -305,7 +307,7 @@ void GroupsEditor::set_current(Node *p_node) { if (scene_tree->get_edited_scene_root() != scene_root_node) { scene_root_node = scene_tree->get_edited_scene_root(); - _update_scene_groups(scene_root_node); + _update_scene_groups(scene_root_node->get_instance_id()); _update_groups(); } @@ -803,7 +805,7 @@ void GroupsEditor::_bind_methods() { void GroupsEditor::_node_removed(Node *p_node) { if (scene_root_node == p_node) { scene_groups_for_caching = scene_groups; - callable_mp(this, &GroupsEditor::_cache_scene_groups).call_deferred(p_node); + callable_mp(this, &GroupsEditor::_cache_scene_groups).call_deferred(p_node->get_instance_id()); scene_root_node = nullptr; } diff --git a/editor/groups_editor.h b/editor/groups_editor.h index cf74470b1bf..8a0ca067de3 100644 --- a/editor/groups_editor.h +++ b/editor/groups_editor.h @@ -78,14 +78,14 @@ class GroupsEditor : public VBoxContainer { Button *add = nullptr; Tree *tree = nullptr; - HashMap> scene_groups_cache; + HashMap> scene_groups_cache; HashMap scene_groups_for_caching; HashMap scene_groups; HashMap global_groups; - void _update_scene_groups(Node *p_node); - void _cache_scene_groups(Node *p_node); + void _update_scene_groups(const ObjectID &p_id); + void _cache_scene_groups(const ObjectID &p_id); void _show_add_group_dialog(); void _show_rename_group_dialog();