From 2532a696e445496c0bf2fcc67392ae66009dd0ba Mon Sep 17 00:00:00 2001 From: Tim Edwards Date: Thu, 18 Mar 2021 11:37:44 -0400 Subject: [PATCH] Correction from a recent commit; complicated sets of "equiv" statement in a .ext file require that all aliases of a node name be rehashed after a node merge, or else node loops can occur. Also prevented statements of the form "equiv A A" from being output in the .ext file, as they are useless. --- VERSION | 2 +- extflat/EFbuild.c | 18 +++++++++++++++--- extract/ExtBasic.c | 8 ++++++-- 3 files changed, 22 insertions(+), 6 deletions(-) diff --git a/VERSION b/VERSION index 5d5b8a8f..8d330699 100644 --- a/VERSION +++ b/VERSION @@ -1 +1 @@ -8.3.142 +8.3.143 diff --git a/extflat/EFbuild.c b/extflat/EFbuild.c index 97c71124..ef0cbb06 100644 --- a/extflat/EFbuild.c +++ b/extflat/EFbuild.c @@ -454,6 +454,8 @@ efBuildEquiv(def, nodeName1, nodeName2) nn1 = (EFNodeName *) HashGetValue(he1); nn2 = (EFNodeName *) HashGetValue(he2); + if (nn1 == nn2) return; /* These nodes already merged */ + if (nn2 == (EFNodeName *) NULL) { /* Create nodeName1 if it doesn't exist */ @@ -482,6 +484,10 @@ efBuildEquiv(def, nodeName1, nodeName2) return; /* Repeated "equiv" statement */ if (nn1->efnn_node != nn2->efnn_node) { + struct efnode *node1 = nn1->efnn_node; + struct efnode *node2 = nn2->efnn_node; + HashSearch hs; + if (efWarn) efReadError("Merged nodes %s and %s\n", nodeName1, nodeName2); efNodeMerge(&nn1->efnn_node, &nn2->efnn_node); @@ -489,17 +495,23 @@ efBuildEquiv(def, nodeName1, nodeName2) else if (nn2->efnn_port > 0) nn1->efnn_port = nn2->efnn_port; /* If a node has been merged away, make sure that its name */ - /* points to the merged name's hash. */ + /* and all aliases point to the merged name's hash. */ if (nn1->efnn_node == NULL) { - HashSetValue(he1, (char *)nn2); nn2->efnn_refc += nn1->efnn_refc + 1; + HashStartSearch(&hs); + while (he1 = HashNext(&def->def_nodes, &hs)) + if ((EFNodeName *)HashGetValue(he1) == nn1) + HashSetValue(he1, (char *)nn2); } else if (nn2->efnn_node == NULL) { - HashSetValue(he2, (char *)nn1); nn1->efnn_refc += nn2->efnn_refc + 1; + HashStartSearch(&hs); + while (he2 = HashNext(&def->def_nodes, &hs)) + if ((EFNodeName *)HashGetValue(he2) == nn2) + HashSetValue(he2, (char *)nn1); } } return; diff --git a/extract/ExtBasic.c b/extract/ExtBasic.c index 184d1be5..c5e0b1c3 100644 --- a/extract/ExtBasic.c +++ b/extract/ExtBasic.c @@ -727,13 +727,17 @@ extOutputNodes(nodeList, outFile) fprintf(outFile, "\"\n"); } - /* Output the alternate names for the node */ + /* Output the alternate names for the node. Avoid generating */ + /* unnecessary "equiv A A" entries for labels on disconnected */ + /* nets. */ + for (ll = reg->nreg_labels; ll; ll = ll->ll_next) if (ll->ll_label->lab_text == text) { for (ll = ll->ll_next; ll; ll = ll->ll_next) if (extLabType(ll->ll_label->lab_text, LABTYPE_NAME)) - fprintf(outFile, "equiv \"%s\" \"%s\"\n", + if (strcmp(text, ll->ll_label->lab_text)) + fprintf(outFile, "equiv \"%s\" \"%s\"\n", text, ll->ll_label->lab_text); break; }