From e7074e572369da877bf43921e8403a36c8a9c106 Mon Sep 17 00:00:00 2001 From: Tim Edwards Date: Wed, 14 Oct 2020 17:20:45 -0400 Subject: [PATCH] Added two small features: (1) Added the "-annotate" option to "lef read". While "lef read" normally annotates existing layout, this option ensures that no additional cells are created from macros in the input LEF file. (2) Added a check on the "Input off lambda grid" warning during CIF/GDS input such that it is not repeated once issued, as it tends to be output many times when it occurs. --- VERSION | 2 +- cif/CIFrdutils.c | 18 +++++++++++++----- lef/lefCmd.c | 11 +++++++++-- lef/lefRead.c | 16 +++++++++++++--- utils/main.c | 2 +- 5 files changed, 37 insertions(+), 12 deletions(-) diff --git a/VERSION b/VERSION index 50db9de7..1212715f 100644 --- a/VERSION +++ b/VERSION @@ -1 +1 @@ -8.3.65 +8.3.66 diff --git a/cif/CIFrdutils.c b/cif/CIFrdutils.c index 1e5ab408..7450a7e6 100644 --- a/cif/CIFrdutils.c +++ b/cif/CIFrdutils.c @@ -60,6 +60,7 @@ FILE *cifErrorFile; int cifLineNumber; /* Number of current line. */ int cifTotalWarnings; /* Number of warnings detected */ int cifTotalErrors; /* Number of errors detected */ +bool cifSeenSnapWarning; /* Track this to prevent excessive messaging */ /* The variables used below hold general information about what * we're currently working on. @@ -218,8 +219,10 @@ CIFScaleCoord(cifCoord, snap_type) switch (snap_type) { case COORD_EXACT: - CIFReadWarning("Input off lambda grid by %d/%d; grid redefined.\n", + if (!cifSeenSnapWarning) + CIFReadWarning("Input off lambda grid by %d/%d; grid redefined.\n", remain, denom); + cifSeenSnapWarning = TRUE; CIFTechInputScale(1, denom, FALSE); CIFTechOutputScale(1, denom); @@ -243,8 +246,10 @@ CIFScaleCoord(cifCoord, snap_type) case COORD_HALF_U: case COORD_HALF_L: if (denom > 2) { - CIFReadWarning("Input off lambda grid by %d/%d; grid redefined.\n", - remain, denom); + if (!cifSeenSnapWarning) + CIFReadWarning("Input off lambda grid by %d/%d; " + "grid redefined.\n", remain, denom); + cifSeenSnapWarning = TRUE; /* scale to nearest half-lambda */ if (!(denom & 0x1)) denom >>= 1; @@ -277,8 +282,10 @@ CIFScaleCoord(cifCoord, snap_type) break; case COORD_ANY: - CIFReadWarning("Input off lambda grid by %d/%d; snapped to grid.\n", - abs(remain), abs(denom)); + if (!cifSeenSnapWarning) + CIFReadWarning("Input off lambda grid by %d/%d; snapped to grid.\n", + abs(remain), abs(denom)); + cifSeenSnapWarning = TRUE; /* Careful: must round down a bit more for negative numbers, in * order to ensure that a point exactly halfway between Magic units @@ -1591,6 +1598,7 @@ CIFReadFile(file) cifTotalWarnings = 0; cifTotalErrors = 0; CifPolygonCount = 0; + cifSeenSnapWarning = FALSE; cifInputFile = file; cifReadScale1 = 1; diff --git a/lef/lefCmd.c b/lef/lefCmd.c index 233ed893..e8984361 100644 --- a/lef/lefCmd.c +++ b/lef/lefCmd.c @@ -72,6 +72,10 @@ CmdLef(w, cmd) * when the FOREIGN statement * is encountered in a macro. */ + bool lefAnnotate = FALSE; /* Indicates that no celldefs should be + * created from any LEF files, which + * will be used for annotation only. + */ bool lefTopCell = TRUE; /* Indicates whether or not we * write the top-level cell to * LEF, or just the subcells. @@ -108,7 +112,8 @@ CmdLef(w, cmd) static char *cmdLefOption[] = { "read [filename] read a LEF file filename[.lef]\n" - " read [filename] -import read a LEF file; import cells from .mag files", + " read [filename] -import read a LEF file; import cells from .mag files\n", + " read [filename] -annotate read a LEF file for cell annotation only.", "write [filename] [-tech] write LEF for current cell\n" " write [filename] -hide hide all details other than ports\n", " write [filename] -hide hide details in area set back distance ", @@ -181,6 +186,8 @@ CmdLef(w, cmd) { if (!strncmp(cmd->tx_argv[i], "-import", 7)) lefImport = TRUE; + else if (!strncmp(cmd->tx_argv[i], "-anno", 5)) + lefAnnotate = TRUE; else if (!strncmp(cmd->tx_argv[i], "-label", 6)) { if (is_lef) @@ -196,7 +203,7 @@ CmdLef(w, cmd) namep = cmd->tx_argv[2]; if (is_lef) - LefRead(namep, lefImport); + LefRead(namep, lefImport, lefAnnotate); else DefRead(namep, defLabelNets); break; diff --git a/lef/lefRead.c b/lef/lefRead.c index 53ad5f07..5c55c143 100644 --- a/lef/lefRead.c +++ b/lef/lefRead.c @@ -1713,13 +1713,16 @@ enum lef_macro_keys {LEF_CLASS = 0, LEF_SIZE, LEF_ORIGIN, LEF_TIMING, LEF_FOREIGN, LEF_PROPERTY, LEF_MACRO_END}; void -LefReadMacro(f, mname, oscale, importForeign) +LefReadMacro(f, mname, oscale, importForeign, doAnnotate) FILE *f; /* LEF file being read */ char *mname; /* name of the macro */ float oscale; /* scale factor um->magic units */ bool importForeign; /* Whether we should try to read * in a cell. */ + bool doAnnotate; /* If true, ignore all macros that are + * not already CellDefs. + */ { CellDef *lefMacro; HashEntry *he; @@ -1764,6 +1767,12 @@ LefReadMacro(f, mname, oscale, importForeign) lefMacro = DBCellLookDef(newname); if (lefMacro == NULL) { + if (doAnnotate) + { + /* Ignore any macro that does not correspond to an existing cell */ + LefSkipSection(f, "MACRO"); + return; + } lefMacro = lefFindCell(newname); DBCellClearDef(lefMacro); DBCellSetAvail(lefMacro); @@ -2508,9 +2517,10 @@ enum lef_sections {LEF_VERSION = 0, LEF_END}; void -LefRead(inName, importForeign) +LefRead(inName, importForeign, doAnnotate) char *inName; bool importForeign; + bool doAnnotate; { FILE *f; char *filename; @@ -2734,7 +2744,7 @@ LefRead(inName, importForeign) TxPrintf("LEF file: Defines new cell %s\n", token); */ sprintf(tsave, "%.127s", token); - LefReadMacro(f, tsave, oscale, importForeign); + LefReadMacro(f, tsave, oscale, importForeign, doAnnotate); break; case LEF_END: if (LefParseEndStatement(f, "LIBRARY") == 0) diff --git a/utils/main.c b/utils/main.c index 1e1c28a1..55988732 100644 --- a/utils/main.c +++ b/utils/main.c @@ -1153,7 +1153,7 @@ mainInitFinal() break; #ifdef LEF_MODULE case FN_LEF_FILE: - LefRead(temporary->fn, FALSE); + LefRead(temporary->fn, FALSE, FALSE); break; case FN_DEF_FILE: DefRead(temporary->fn, FALSE);