From b6cb1fb54a1935c9cb6c2c90f392a846c149b5ed Mon Sep 17 00:00:00 2001 From: Tim Edwards Date: Tue, 3 Mar 2020 17:13:37 -0500 Subject: [PATCH] Modified the LEF VIAGEN reading such that it can accomodate a different order of layers than specified in the LEF/DEF spec. It is not clear whether this is common practice, or a bug in the tool that produced the DEF file that prompted this change. NOTE: The "grow" function applied in this case should be replaced by the actual GDS input rule sequence, that includes the grow and shrink merge. Otherwise, vias read from DEF files do not match the layout from those read from GDS, even though the mask layers represented by the layouts are the same. --- ext2spice/ext2spice.c | 9 ++++++++- lef/defRead.c | 29 +++++++++++++++++++++++++++++ 2 files changed, 37 insertions(+), 1 deletion(-) diff --git a/ext2spice/ext2spice.c b/ext2spice/ext2spice.c index b51215ce..94b2eb53 100644 --- a/ext2spice/ext2spice.c +++ b/ext2spice/ext2spice.c @@ -2873,7 +2873,14 @@ int spcnAP(node, resClass, scale, asterm, psterm, m, outf, w) if (!esDistrJunct || w == -1) goto oldFmt; - dsc = w / ((nodeClient*)node->efnode_client)->m_w.widths[resClass]; + if (((nodeClient*)node->efnode_client)->m_w.widths != NULL) + dsc = w / ((nodeClient*)node->efnode_client)->m_w.widths[resClass]; + else + { + TxError("Device missing records for source/drain area/perim.\n"); + dsc = w; + } + if (esScale < 0) { if (asterm) diff --git a/lef/defRead.c b/lef/defRead.c index 70446ab4..7091c1c9 100644 --- a/lef/defRead.c +++ b/lef/defRead.c @@ -1287,6 +1287,35 @@ DefReadVias(f, sname, oscale, total) blayer = LefReadLayer(f, FALSE); clayer = LefReadLayer(f, FALSE); tlayer = LefReadLayer(f, FALSE); + + /* Provisional behavior: A known tool generating */ + /* DEF uses the order (bottom, top, cut). This may */ + /* be a bug in the tool and an issue is being */ + /* raised. However, there is no harm in detecting */ + /* which layer is the cut and swapping as needed. */ + + if (!DBIsContact(clayer)) + { + TileType swaplayer; + LefError(DEF_WARNING, "Improper layer order for" + " VIARULE.\n"); + if (DBIsContact(tlayer)) + { + swaplayer = clayer; + clayer = tlayer; + tlayer = swaplayer; + } + else if (DBIsContact(blayer)) + { + swaplayer = clayer; + clayer = blayer; + blayer = swaplayer; + } + else + LefError(DEF_ERROR, "No cut layer specified in" + " VIARULE.\n"); + } + generated = TRUE; break; case DEF_VIAS_PROP_CUTSPACING: