Welcome to mirror list, hosted at ThFree Co, Russian Federation.

git.blender.org/blender.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorSergey Sharybin <sergey.vfx@gmail.com>2020-01-02 19:09:57 +0300
committerSergey Sharybin <sergey.vfx@gmail.com>2020-01-02 19:19:29 +0300
commit311178fcf275846d63d2801b6521082396133f6e (patch)
treeaf378ce3cd81186dcd3adefdeb771132ae462d68 /source/blender/blenkernel/intern/scene.c
parentde530a95dc7b482dc22c933b9b8b2a98c79b5663 (diff)
Fix T72821: Crash when IOD is removed from post-update callback
IDs recalc clear flag was accessing freed memory. There is more detailed comment about solution in the code.
Diffstat (limited to 'source/blender/blenkernel/intern/scene.c')
-rw-r--r--source/blender/blenkernel/intern/scene.c17
1 files changed, 17 insertions, 0 deletions
diff --git a/source/blender/blenkernel/intern/scene.c b/source/blender/blenkernel/intern/scene.c
index f84ef92d074..e57a50a8a23 100644
--- a/source/blender/blenkernel/intern/scene.c
+++ b/source/blender/blenkernel/intern/scene.c
@@ -1355,6 +1355,19 @@ static void scene_graph_update_tagged(Depsgraph *depsgraph, Main *bmain, bool on
if (run_callbacks) {
BKE_callback_exec_id_depsgraph(
bmain, &scene->id, depsgraph, BKE_CB_EVT_DEPSGRAPH_UPDATE_POST);
+
+ /* It is possible that the custom callback modified scene and removed some IDs from the main
+ * database. In this case DEG_ids_clear_recalc() will crash because it iterates over all IDs
+ * which depsgraph was built for.
+ *
+ * The solution is to update relations prior to this call, avoiding access to freed IDs.
+ * Should be safe because relations update is supposed to preserve flags of all IDs which are
+ * still a part of the dependency graph. If an ID is kicked out of the dependency graph it
+ * should also be fine because when/if it's added to another dependency graph it will need to
+ * be tagged for an update anyway.
+ *
+ * If there are no relations changed by the callback this call will do nothing. */
+ DEG_graph_relations_update(depsgraph, bmain, scene, view_layer);
}
/* Inform editors about possible changes. */
DEG_ids_check_recalc(bmain, depsgraph, scene, view_layer, false);
@@ -1420,6 +1433,10 @@ void BKE_scene_graph_update_for_newframe(Depsgraph *depsgraph, Main *bmain)
/* Notify editors and python about recalc. */
if (pass == 0) {
BKE_callback_exec_id_depsgraph(bmain, &scene->id, depsgraph, BKE_CB_EVT_FRAME_CHANGE_POST);
+
+ /* NOTE: Similar to this case in scene_graph_update_tagged(). Need to ensure that
+ * DEG_ids_clear_recalc() doesn't access freed memory of possibly removed ID. */
+ DEG_graph_relations_update(depsgraph, bmain, scene, view_layer);
}
/* Inform editors about possible changes. */