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:
authorJoshua Leung <aligorith@gmail.com>2018-08-22 18:15:19 +0300
committerJoshua Leung <aligorith@gmail.com>2018-08-23 08:07:38 +0300
commit6ec933886c363c99da3df4063c6f35b94d42cbfe (patch)
treec7dc2093a9d53e99a8cd4df48c1ab871f31fd964
parent9a0ef0933d39f37e2267102f097ef7e4497d7789 (diff)
Depsgraph: Fix filtering-related crashes
* Simplified operation-relation deletion. Now we collect the relations to delete into a vector, then iterate through that, thus solving issues with iterator invalidation (+ aborts arising from that) * DEG_foreach_ancestor_ID() was assuming that all dependencies were OperationDepsNodes, when in fact, some could be TimeSource nodes
-rw-r--r--source/blender/depsgraph/intern/depsgraph_query_filter.cc25
-rw-r--r--source/blender/depsgraph/intern/depsgraph_query_foreach.cc28
2 files changed, 28 insertions, 25 deletions
diff --git a/source/blender/depsgraph/intern/depsgraph_query_filter.cc b/source/blender/depsgraph/intern/depsgraph_query_filter.cc
index 20de3e6f41a..d6965206844 100644
--- a/source/blender/depsgraph/intern/depsgraph_query_filter.cc
+++ b/source/blender/depsgraph/intern/depsgraph_query_filter.cc
@@ -93,22 +93,19 @@ void deg_add_retained_id_cb(ID *id, void *user_data)
/* TODO: Make this part of OperationDepsNode? */
void deg_unlink_opnode(OperationDepsNode *op_node)
{
- /* Delete inlinks to this operation */
- for (DepsNode::Relations::const_iterator it_rel = op_node->inlinks.begin();
- it_rel != op_node->inlinks.end();
- )
- {
- DepsRelation *rel = *it_rel;
- rel->unlink();
- OBJECT_GUARDED_DELETE(rel, DepsRelation);
+ std::vector<DepsRelation *> all_links;
+
+ /* Collect all inlinks to this operation */
+ foreach (DepsRelation *rel, op_node->inlinks) {
+ all_links.push_back(rel);
+ }
+ /* Collect all outlinks from this operation */
+ foreach (DepsRelation *rel, op_node->outlinks) {
+ all_links.push_back(rel);
}
- /* Delete outlinks from this operation */
- for (DepsNode::Relations::const_iterator it_rel = op_node->outlinks.begin();
- it_rel != op_node->outlinks.end();
- )
- {
- DepsRelation *rel = *it_rel;
+ /* Delete all collected entries */
+ foreach (DepsRelation *rel, all_links) {
rel->unlink();
OBJECT_GUARDED_DELETE(rel, DepsRelation);
}
diff --git a/source/blender/depsgraph/intern/depsgraph_query_foreach.cc b/source/blender/depsgraph/intern/depsgraph_query_foreach.cc
index 83d81d82b26..c8aaf353874 100644
--- a/source/blender/depsgraph/intern/depsgraph_query_foreach.cc
+++ b/source/blender/depsgraph/intern/depsgraph_query_foreach.cc
@@ -178,21 +178,27 @@ static void deg_foreach_ancestor_ID(const Depsgraph *graph,
}
/* Schedule incoming operation nodes. */
if (op_node->inlinks.size() == 1) {
- OperationDepsNode *from_node = (OperationDepsNode *)op_node->inlinks[0]->from;
- if (from_node->scheduled == false) {
- from_node->scheduled = true;
- op_node = from_node;
- }
- else {
- break;
+ DepsNode *from = op_node->inlinks[0]->from;
+ if (from->get_class() == DEG_NODE_CLASS_OPERATION) {
+ OperationDepsNode *from_node = (OperationDepsNode *)from;
+ if (from_node->scheduled == false) {
+ from_node->scheduled = true;
+ op_node = from_node;
+ }
+ else {
+ break;
+ }
}
}
else {
foreach (DepsRelation *rel, op_node->inlinks) {
- OperationDepsNode *from_node = (OperationDepsNode *)rel->from;
- if (from_node->scheduled == false) {
- queue.push_front(from_node);
- from_node->scheduled = true;
+ DepsNode *from = rel->from;
+ if (from->get_class() == DEG_NODE_CLASS_OPERATION) {
+ OperationDepsNode *from_node = (OperationDepsNode *)from;
+ if (from_node->scheduled == false) {
+ queue.push_front(from_node);
+ from_node->scheduled = true;
+ }
}
}
break;