From b335dfafff1f412c396807fd2af65046860b4a54 Mon Sep 17 00:00:00 2001 From: Tim Edwards Date: Sun, 13 Jun 2021 20:17:19 -0400 Subject: [PATCH] Modified the node merging in ExtHier.c to match the node merging optimization done in ExtFlat, which is to keep a count of the number of different node names assigned to the node so that when merging, the one with fewer nodes can be updated to match the one with more nodes. Note: This change is made on the assumption that the names for node1 and node2 are equally preferred. Supposedly the first name in the node list is canonical, so if node1 is preferred in any case, it may be necessary to move the first item of the second list to the beginning (a minor code change). --- extract/ExtHier.c | 157 ++++++++++++++++++++++++++++++++----------- extract/extractInt.h | 1 + 2 files changed, 117 insertions(+), 41 deletions(-) diff --git a/extract/ExtHier.c b/extract/ExtHier.c index 8056a8e9..a16c4702 100644 --- a/extract/ExtHier.c +++ b/extract/ExtHier.c @@ -203,15 +203,32 @@ extHierSubstrate(ha, use, x, y) if (node1 != node2) { - /* - * Both sets of names will now point to node1. - */ - for (nn = node2->node_names; nn->nn_next; nn = nn->nn_next) + if (node1->node_len < node2->node_len) + { + /* + * Both sets of names will now point to node2. + */ + for (nn = node1->node_names; nn->nn_next; nn = nn->nn_next) + nn->nn_node = node2; + nn->nn_node = node2; + nn->nn_next = node2->node_names; + node2->node_names = node1->node_names; + node2->node_len += node1->node_len; + freeMagic((char *)node1); + } + else + { + /* + * Both sets of names will now point to node1. + */ + for (nn = node2->node_names; nn->nn_next; nn = nn->nn_next) nn->nn_node = node1; - nn->nn_node = node1; - nn->nn_next = node1->node_names; - node1->node_names = node2->node_names; - freeMagic((char *) node2); + nn->nn_node = node1; + nn->nn_next = node1->node_names; + node1->node_names = node2->node_names; + node1->node_len += node2->node_len; + freeMagic((char *)node2); + } } freeMagic(nodeList); } @@ -385,17 +402,36 @@ extHierConnectFunc1(oneTile, ha) if (node1 != node2) { - /* - * Both sets of names will now point to node1. - * We don't need to update node_cap since it - * hasn't been computed yet. - */ - for (nn = node2->node_names; nn->nn_next; nn = nn->nn_next) - nn->nn_node = node1; - nn->nn_node = node1; - nn->nn_next = node1->node_names; - node1->node_names = node2->node_names; - freeMagic((char *) node2); + if (node1->node_len < node2->node_len) + { + /* + * Both sets of names will now point to node2. + * We don't need to update node_cap since it + * hasn't been computed yet. + */ + for (nn = node1->node_names; nn->nn_next; nn = nn->nn_next) + nn->nn_node = node2; + nn->nn_node = node2; + nn->nn_next = node2->node_names; + node2->node_names = node1->node_names; + node2->node_len += node1->node_len; + freeMagic((char *) node1); + } + else + { + /* + * Both sets of names will now point to node1. + * We don't need to update node_cap since it + * hasn't been computed yet. + */ + for (nn = node2->node_names; nn->nn_next; nn = nn->nn_next) + nn->nn_node = node1; + nn->nn_node = node1; + nn->nn_next = node1->node_names; + node1->node_names = node2->node_names; + node1->node_len += node2->node_len; + freeMagic((char *) node2); + } } } } @@ -470,17 +506,36 @@ extHierConnectFunc2(cum, ha) if (node1 != node2) { - /* - * Both sets of names will now point to node1. - * We don't need to update node_cap since it - * hasn't been computed yet. - */ - for (nn = node2->node_names; nn->nn_next; nn = nn->nn_next) - nn->nn_node = node1; - nn->nn_node = node1; - nn->nn_next = node1->node_names; - node1->node_names = node2->node_names; - freeMagic((char *) node2); + if (node1->node_len < node2->node_len) + { + /* + * Both sets of names will now point to node2. + * We don't need to update node_cap since it + * hasn't been computed yet. + */ + for (nn = node1->node_names; nn->nn_next; nn = nn->nn_next) + nn->nn_node = node2; + nn->nn_node = node2; + nn->nn_next = node2->node_names; + node2->node_names = node1->node_names; + node2->node_len += node1->node_len; + freeMagic((char *) node1); + } + else + { + /* + * Both sets of names will now point to node1. + * We don't need to update node_cap since it + * hasn't been computed yet. + */ + for (nn = node2->node_names; nn->nn_next; nn = nn->nn_next) + nn->nn_node = node1; + nn->nn_node = node1; + nn->nn_next = node1->node_names; + node1->node_names = node2->node_names; + node1->node_len += node2->node_len; + freeMagic((char *) node2); + } } } else if (r.r_xtop > r.r_xbot && r.r_ytop > r.r_ybot) @@ -553,17 +608,36 @@ extHierConnectFunc3(cum, ha) if (node1 != node2) { - /* - * Both sets of names will now point to node1. - * We don't need to update node_cap since it - * hasn't been computed yet. - */ - for (nn = node2->node_names; nn->nn_next; nn = nn->nn_next) - nn->nn_node = node1; - nn->nn_node = node1; - nn->nn_next = node1->node_names; - node1->node_names = node2->node_names; - freeMagic((char *) node2); + if (node1->node_len < node2->node_len) + { + /* + * Both sets of names will now point to node2. + * We don't need to update node_cap since it + * hasn't been computed yet. + */ + for (nn = node1->node_names; nn->nn_next; nn = nn->nn_next) + nn->nn_node = node2; + nn->nn_node = node2; + nn->nn_next = node2->node_names; + node2->node_names = node1->node_names; + node2->node_len += node1->node_len; + freeMagic((char *) node1); + } + else + { + /* + * Both sets of names will now point to node1. + * We don't need to update node_cap since it + * hasn't been computed yet. + */ + for (nn = node2->node_names; nn->nn_next; nn = nn->nn_next) + nn->nn_node = node1; + nn->nn_node = node1; + nn->nn_next = node1->node_names; + node1->node_names = node2->node_names; + node1->node_len += node2->node_len; + freeMagic((char *) node2); + } } } else if (r.r_xtop > r.r_xbot && r.r_ytop > r.r_ybot) @@ -810,6 +884,7 @@ extHierNewNode(he) nn->nn_name = he->h_key.h_name; node->node_names = nn; node->node_cap = (CapValue) 0; + node->node_len = 1; for (n = 0; n < nclasses; n++) node->node_pa[n].pa_perim = node->node_pa[n].pa_area = 0; HashSetValue(he, (char *) nn); diff --git a/extract/extractInt.h b/extract/extractInt.h index 82d18d51..ad33cce5 100644 --- a/extract/extractInt.h +++ b/extract/extractInt.h @@ -943,6 +943,7 @@ typedef struct node NodeName *node_names; /* List of names for this node. The first name * in the list is the "official" node name. */ + int node_len; /* Number of entries in node_names */ CapValue node_cap; /* Capacitance to substrate */ PerimArea node_pa[1]; /* Dummy; each node actually has * ExtCurStyle->exts_numResistClasses