From 42520856630d53f71c2b7e3eb66905ec9fd468c7 Mon Sep 17 00:00:00 2001 From: Matthias Koefferlein Date: Thu, 25 Mar 2021 01:56:23 +0100 Subject: [PATCH] Fixed an internal error in netlist compare Problem was that during ambiguity resolution a choice may be invalidated by further choices. This is taken care by locking nets against re-mapping. --- src/db/db/dbNetlistCompare.cc | 21 ++++++++++++++++++--- 1 file changed, 18 insertions(+), 3 deletions(-) diff --git a/src/db/db/dbNetlistCompare.cc b/src/db/db/dbNetlistCompare.cc index 0bd23ec43..752bed8cf 100644 --- a/src/db/db/dbNetlistCompare.cc +++ b/src/db/db/dbNetlistCompare.cc @@ -2357,7 +2357,7 @@ NetGraph::derive_node_identities_from_ambiguity_group (const NodeRange &nr, Devi { // marks the nodes from the ambiguity group as unknown so we don't revisit them (causing deep recursion) - TentativeNodeMapping tn2unknown; + TentativeNodeMapping tn_temp; // collect and mark the ambiguity combinations to consider std::vector >::const_iterator> iters1, iters2; @@ -2366,7 +2366,7 @@ NetGraph::derive_node_identities_from_ambiguity_group (const NodeRange &nr, Devi if (! i1->first->has_any_other ()) { iters1.push_back (i1); size_t ni = node_index_for_net (i1->first->net ()); - TentativeNodeMapping::map_to_unknown (&tn2unknown, this, ni); + TentativeNodeMapping::map_to_unknown (&tn_temp, this, ni); } } @@ -2374,7 +2374,7 @@ NetGraph::derive_node_identities_from_ambiguity_group (const NodeRange &nr, Devi if (! i2->first->has_any_other ()) { iters2.push_back (i2); size_t other_ni = data->other->node_index_for_net (i2->first->net ()); - TentativeNodeMapping::map_to_unknown (&tn2unknown, data->other, other_ni); + TentativeNodeMapping::map_to_unknown (&tn_temp, data->other, other_ni); } } @@ -2463,7 +2463,22 @@ NetGraph::derive_node_identities_from_ambiguity_group (const NodeRange &nr, Devi } if (to_remove != iters2.end ()) { + + // Add the new pair to the temporary mapping (even in tentative mode) + // Reasoning: doing the mapping may render other nets incompatible, so to ensure "edges_are_compatible" works properly we + // need to lock the current pairs resources such as devices by listing them in the mapping. This is doing by "derive_*_equivalence" inside + // TentativeNodeMapping::map_pair + + std::vector >::const_iterator i2 = *to_remove; + + size_t ni = node_index_for_net (i1->first->net ()); + size_t other_ni = data->other->node_index_for_net (i2->first->net ()); + + TentativeNodeMapping::map_pair (&tn_temp, this, ni, data->other, other_ni, dm, dm_other, *data->device_equivalence, scm, scm_other, *data->subcircuit_equivalence, depth); + + // now we can get rid of the node and reduce the "other" list of ambiguous nodes iters2.erase (to_remove); + } if (! any && tentative) {