diff --git a/VERSION b/VERSION index 0fcb5ebb..e77e1a74 100644 --- a/VERSION +++ b/VERSION @@ -1 +1 @@ -8.3.383 +8.3.384 diff --git a/calma/CalmaWrite.c b/calma/CalmaWrite.c index ee76aed3..fe297041 100644 --- a/calma/CalmaWrite.c +++ b/calma/CalmaWrite.c @@ -50,6 +50,7 @@ static char rcsid[] __attribute__ ((unused)) ="$Header: /usr/cvsroot/magic-8.0/c #include "utils/styles.h" #include "textio/textio.h" #include "calma/calmaInt.h" +#include "extract/extractInt.h" /* for LabelList */ #include "utils/main.h" /* for Path and CellLibPath */ #include "utils/stack.h" @@ -117,7 +118,7 @@ typedef struct { #define GDS_UNPROCESSED CLIENTDEFAULT #define GDS_PROCESSED 1 -#define PUSHTILE(tp) \ +#define PUSHTILEC(tp) \ if ((tp)->ti_client == (ClientData) GDS_UNPROCESSED) { \ (tp)->ti_client = (ClientData) GDS_PENDING; \ STACKPUSH((ClientData) (tp), SegStack); \ @@ -1244,6 +1245,30 @@ calmaProcessDef(def, outf, do_library) return 0; } +/* + * ---------------------------------------------------------------------------- + * + * compport --- + * + * Compare two port labels by port index. Sorting function used with + * qsort(). + * + * ---------------------------------------------------------------------------- + */ + +int +compport(const void *one, const void *two) +{ + PortLabel *pl1 = (PortLabel *)one; + PortLabel *pl2 = (PortLabel *)two; + + if (pl1->pl_port < pl2->pl_port) + return -1; + if (pl1->pl_port > pl2->pl_port) + return 1; + else + return 0; +} /* * ---------------------------------------------------------------------------- @@ -1383,7 +1408,8 @@ calmaOutFunc(def, f, cliprect) if (CalmaDoLabels) { - int i, ltype, maxport = -1; + int i, ltype, numports = 0; + LabelList *ll = NULL, *newll; for (lab = def->cd_labels; lab; lab = lab->lab_next) { @@ -1395,23 +1421,42 @@ calmaOutFunc(def, f, cliprect) } else { - if ((int)lab->lab_port > maxport) - maxport = (int)lab->lab_port; + newll = (LabelList *)mallocMagic(sizeof(LabelList)); + newll->ll_label = lab; + newll->ll_attr = (unsigned int)lab->lab_port; + newll->ll_next = ll; + ll = newll; + numports++; } } - if (maxport >= 0) - for (i = 0; i <= maxport; i++) - for (lab = def->cd_labels; lab; lab = lab->lab_next) - { - ltype = CIFCurStyle->cs_portText[lab->lab_type]; - type = CIFCurStyle->cs_portLayer[lab->lab_type]; - if ((type >= 0) && ((lab->lab_flags & PORT_DIR_MASK) != 0) && - (lab->lab_port == i)) - { - calmaWriteLabelFunc(lab, ltype, type, f); - /* break; */ /* Do not limit to unique labels! */ - } - } + if (newll != NULL) + { + /* Turn linked list into an array, then run qsort on it */ + /* to sort by port number. */ + + PortLabel *pllist = (PortLabel *)mallocMagic(numports * sizeof(PortLabel)); + i = 0; + while (ll != NULL) + { + pllist[i].pl_label = ll->ll_label; + pllist[i].pl_port = (unsigned int)ll->ll_attr; + freeMagic(ll); + ll = ll->ll_next; + i++; + } + + qsort(pllist, numports, sizeof(PortLabel), compport); + + for (i = 0; i < numports; i++) + { + lab = pllist[i].pl_label; + ltype = CIFCurStyle->cs_portText[lab->lab_type]; + type = CIFCurStyle->cs_portLayer[lab->lab_type]; + if (type >= 0) + calmaWriteLabelFunc(lab, ltype, type, f); + } + freeMagic(pllist); + } } /* End of structure */ @@ -2461,7 +2506,7 @@ calmaMergePaintFunc(tile, cos) if (SegStack == (Stack *)NULL) SegStack = StackNew(64); - PUSHTILE(tile); + PUSHTILEC(tile); while (!StackEmpty(SegStack)) { t = (Tile *) STACKPOP(SegStack); @@ -2629,7 +2674,7 @@ calmaMergePaintFunc(tile, cos) intedges += calmaAddSegment(&lb, is_ext, MIN(RIGHT(t), RIGHT(tp)), TOP(t), MAX(LEFT(t), LEFT(tp)), TOP(t)); - if (!is_ext) PUSHTILE(tp); + if (!is_ext) PUSHTILEC(tp); } if (split_type == 0x3) @@ -2649,7 +2694,7 @@ left_search: intedges += calmaAddSegment(&lb, is_ext, LEFT(t), MIN(TOP(t), TOP(tp)), LEFT(t), MAX(BOTTOM(t), BOTTOM(tp))); - if (!is_ext) PUSHTILE(tp); + if (!is_ext) PUSHTILEC(tp); } if (split_type == 0x0) @@ -2669,7 +2714,7 @@ bottom_search: intedges += calmaAddSegment(&lb, is_ext, MAX(LEFT(t), LEFT(tp)), BOTTOM(t), MIN(RIGHT(t), RIGHT(tp)), BOTTOM(t)); - if (!is_ext) PUSHTILE(tp); + if (!is_ext) PUSHTILEC(tp); } if (split_type == 0x1) @@ -2688,7 +2733,7 @@ right_search: intedges += calmaAddSegment(&lb, is_ext, RIGHT(t), MAX(BOTTOM(t), BOTTOM(tp)), RIGHT(t), MIN(TOP(t), TOP(tp))); - if (!is_ext) PUSHTILE(tp); + if (!is_ext) PUSHTILEC(tp); } /* If tile is isolated, process it now and we're done */ diff --git a/calma/CalmaWriteZ.c b/calma/CalmaWriteZ.c index 200290af..650ad1db 100644 --- a/calma/CalmaWriteZ.c +++ b/calma/CalmaWriteZ.c @@ -60,6 +60,7 @@ static char rcsid[] __attribute__ ((unused)) ="$Header: /usr/cvsroot/magic-8.0/c #include "utils/styles.h" #include "textio/textio.h" #include "calma/calmaInt.h" +#include "extract/extractInt.h" /* for LabelList */ #include "utils/main.h" /* for Path and CellLibPath */ #include "utils/stack.h" @@ -122,7 +123,7 @@ typedef struct { #define GDS_UNPROCESSED CLIENTDEFAULT #define GDS_PROCESSED 1 -#define PUSHTILE(tp) \ +#define PUSHTILEZ(tp) \ if ((tp)->ti_client == (ClientData) GDS_UNPROCESSED) { \ (tp)->ti_client = (ClientData) GDS_PENDING; \ STACKPUSH((ClientData) (tp), SegStack); \ @@ -1186,6 +1187,7 @@ calmaOutFuncZ(def, f, cliprect) calmaOutputStructZ cos; bool propfound; char *propvalue; + extern int compport(); /* Forward declaration */ cos.f = f; cos.area = (cliprect == &TiPlaneRect) ? NULL : cliprect; @@ -1290,7 +1292,8 @@ calmaOutFuncZ(def, f, cliprect) if (CalmaDoLabels) { - int i, ltype, maxport = -1; + int i, ltype, numports = 0; + LabelList *ll = NULL, *newll; for (lab = def->cd_labels; lab; lab = lab->lab_next) { @@ -1302,23 +1305,42 @@ calmaOutFuncZ(def, f, cliprect) } else { - if ((int)lab->lab_port > maxport) - maxport = (int)lab->lab_port; + newll = (LabelList *)mallocMagic(sizeof(LabelList)); + newll->ll_label = lab; + newll->ll_attr = (unsigned int)lab->lab_port; + newll->ll_next = ll; + ll = newll; + numports++; } } - if (maxport >= 0) - for (i = 0; i <= maxport; i++) - for (lab = def->cd_labels; lab; lab = lab->lab_next) - { - ltype = CIFCurStyle->cs_portText[lab->lab_type]; - type = CIFCurStyle->cs_portLayer[lab->lab_type]; - if ((type >= 0) && ((lab->lab_flags & PORT_DIR_MASK) != 0) && - (lab->lab_port == i)) - { - calmaWriteLabelFuncZ(lab, ltype, type, f); - /* break; */ /* Do not limit to unique labels! */ - } - } + if (newll != NULL) + { + /* Turn linked list into an array, then run qsort on it */ + /* to sort by port number. */ + + PortLabel *pllist = (PortLabel *)mallocMagic(numports * sizeof(PortLabel)); + i = 0; + while (ll != NULL) + { + pllist[i].pl_label = ll->ll_label; + pllist[i].pl_port = (unsigned int)ll->ll_attr; + freeMagic(ll); + ll = ll->ll_next; + i++; + } + + qsort(pllist, numports, sizeof(PortLabel), compport); + + for (i = 0; i < numports; i++) + { + lab = pllist[i].pl_label; + ltype = CIFCurStyle->cs_portText[lab->lab_type]; + type = CIFCurStyle->cs_portLayer[lab->lab_type]; + if (type >= 0) + calmaWriteLabelFuncZ(lab, ltype, type, f); + } + freeMagic(pllist); + } } /* End of structure */ @@ -1737,7 +1759,7 @@ calmaWriteContactsZ(f) /* Get clip bounds, so that residue surround is */ /* minimum. Note that these values are in CIF/GDS */ /* units, and the clipping rectangle passed to */ - /* calmaOutFunc is also in CIF/GDS units. */ + /* calmaOutFuncZ is also in CIF/GDS units. */ halfsize = CIFGetContactSize(type, NULL, NULL, NULL) >> 1; @@ -1882,7 +1904,7 @@ calmaMergePaintFuncZ(tile, cos) if (SegStack == (Stack *)NULL) SegStack = StackNew(64); - PUSHTILE(tile); + PUSHTILEZ(tile); while (!StackEmpty(SegStack)) { t = (Tile *) STACKPOP(SegStack); @@ -2050,7 +2072,7 @@ calmaMergePaintFuncZ(tile, cos) intedges += calmaAddSegment(&lb, is_ext, MIN(RIGHT(t), RIGHT(tp)), TOP(t), MAX(LEFT(t), LEFT(tp)), TOP(t)); - if (!is_ext) PUSHTILE(tp); + if (!is_ext) PUSHTILEZ(tp); } if (split_type == 0x3) @@ -2070,7 +2092,7 @@ left_search: intedges += calmaAddSegment(&lb, is_ext, LEFT(t), MIN(TOP(t), TOP(tp)), LEFT(t), MAX(BOTTOM(t), BOTTOM(tp))); - if (!is_ext) PUSHTILE(tp); + if (!is_ext) PUSHTILEZ(tp); } if (split_type == 0x0) @@ -2090,7 +2112,7 @@ bottom_search: intedges += calmaAddSegment(&lb, is_ext, MAX(LEFT(t), LEFT(tp)), BOTTOM(t), MIN(RIGHT(t), RIGHT(tp)), BOTTOM(t)); - if (!is_ext) PUSHTILE(tp); + if (!is_ext) PUSHTILEZ(tp); } if (split_type == 0x1) @@ -2109,7 +2131,7 @@ right_search: intedges += calmaAddSegment(&lb, is_ext, RIGHT(t), MAX(BOTTOM(t), BOTTOM(tp)), RIGHT(t), MIN(TOP(t), TOP(tp))); - if (!is_ext) PUSHTILE(tp); + if (!is_ext) PUSHTILEZ(tp); } /* If tile is isolated, process it now and we're done */ diff --git a/calma/calmaInt.h b/calma/calmaInt.h index 60485aa9..4fb56a2f 100644 --- a/calma/calmaInt.h +++ b/calma/calmaInt.h @@ -216,6 +216,14 @@ typedef union { char uc[4]; unsigned int ul; } FourByteInt; UNREADRH(nb, rt); \ } +/* Structure used for sorting ports by number */ + +typedef struct portlabel +{ + Label *pl_label; + unsigned int pl_port; +} PortLabel; + /* Other commonly used globals */ extern HashTable calmaLayerHash; extern int calmaElementIgnore[]; @@ -230,6 +238,8 @@ extern bool calmaIsContactCell; extern char *calmaRecordName(); extern void calmaSkipSet(); +extern int compport(); + /* ------------------- Imports from CIF reading ----------------------- */ extern CellDef *cifReadCellDef; diff --git a/ext2spice/ext2spice.c b/ext2spice/ext2spice.c index 802c4209..aa6c9588 100644 --- a/ext2spice/ext2spice.c +++ b/ext2spice/ext2spice.c @@ -3189,8 +3189,8 @@ int spcnAP(dterm, node, resClass, scale, asterm, psterm, m, outf, w) return 1; } - if (asterm) sprintf(afmt, " %s=", asterm); - if (psterm) sprintf(pfmt, " %s=", psterm); + if (asterm) snprintf(afmt, sizeof afmt, " %s=", asterm); + if (psterm) snprintf(pfmt, sizeof pfmt, " %s=", psterm); if (!esDistrJunct || w == -1) goto newFmt; @@ -3206,13 +3206,13 @@ int spcnAP(dterm, node, resClass, scale, asterm, psterm, m, outf, w) { if (asterm) { - fprintf(outf, afmt); + fputs(afmt, outf); esSIvalue(outf, 1.0E-12 * node->efnode_pa[resClass].pa_area * scale * scale * dsc); } if (psterm) { - fprintf(outf, pfmt); + fputs(pfmt, outf); esSIvalue(outf, 1.0E-6 * node->efnode_pa[resClass].pa_perim * scale * dsc); } } @@ -3220,13 +3220,13 @@ int spcnAP(dterm, node, resClass, scale, asterm, psterm, m, outf, w) { if (asterm) { - fprintf(outf, afmt); + fputs(afmt, outf); esSIvalue(outf, 1.0E-12 * ((float)node->efnode_pa[resClass].pa_area * scale * scale) * esScale * esScale * dsc); } if (psterm) { - fprintf(outf, pfmt); + fputs(pfmt, outf); esSIvalue(outf, 1.0E-6 * ((float)node->efnode_pa[resClass].pa_perim * scale) * esScale * dsc); } @@ -3274,12 +3274,12 @@ newFmt: { if (asterm) { - fprintf(outf, afmt); + fputs(afmt, outf); esSIvalue(outf, 1.0E-12 * area * scale * scale / m); } if (psterm) { - fprintf(outf, pfmt); + fputs(pfmt, outf); esSIvalue(outf, 1.0E-6 * perim * scale / m); } } @@ -3287,12 +3287,12 @@ newFmt: { if (asterm) { - fprintf(outf, afmt); + fputs(afmt, outf); esSIvalue(outf, 1.0E-12 * ((float)area * scale * scale) * esScale * esScale); } if (psterm) { - fprintf(outf, pfmt); + fputs(pfmt, outf); esSIvalue(outf, 1.0E-6 * ((float)perim * scale) * esScale); } } @@ -3357,16 +3357,16 @@ int spcnAPHier(dterm, hierName, resClass, scale, asterm, psterm, m, outf) if (esScale < 0) { - fprintf(outf, afmt); + fputs(afmt, outf); esSIvalue(outf, 1.0E-12 * area * scale * scale / m); - fprintf(outf, pfmt); + fputs(pfmt, outf); esSIvalue(outf, 1.0E-6 * perim * scale / m); } else { - fprintf(outf, afmt); + fputs(afmt, outf); esSIvalue(outf, 1.0E-12 * ((float)area * scale) * esScale * esScale); - fprintf(outf, pfmt); + fputs(pfmt, outf); esSIvalue(outf, 1.0E-6 * ((float)perim * scale) * esScale); } return 0;