diff --git a/VERSION b/VERSION index 3d73f92b..896df0cf 100644 --- a/VERSION +++ b/VERSION @@ -1 +1 @@ -8.3.80 +8.3.81 diff --git a/calma/CalmaWrite.c b/calma/CalmaWrite.c index 2118c18a..41732d23 100644 --- a/calma/CalmaWrite.c +++ b/calma/CalmaWrite.c @@ -799,6 +799,9 @@ calmaProcessDef(def, outf, do_library) if (isReadOnly && hasContent && CalmaAddendum) return (0); + /* Give some feedback to the user */ + TxPrintf(" Writing cell %s\n", def->cd_name); + /* * Output the definitions for any of our descendants that have * not already been output. Numbers are assigned to the subcells @@ -1008,7 +1011,8 @@ calmaOutFunc(def, f, cliprect) /* Output all the tiles associated with this cell; skip temporary layers */ GEO_EXPAND(&def->cd_bbox, CIFCurStyle->cs_radius, &bigArea); CIFErrorDef = def; - CIFGen(def, def, &bigArea, CIFPlanes, &DBAllTypeBits, TRUE, TRUE, (ClientData) f); + CIFGen(def, def, &bigArea, CIFPlanes, &DBAllTypeBits, TRUE, TRUE, FALSE, + (ClientData)f); if (!CIFHierWriteDisable) CIFGenSubcells(def, &bigArea, CIFPlanes); if (!CIFArrayWriteDisable) diff --git a/cif/CIFgen.c b/cif/CIFgen.c index 938729be..8321da85 100644 --- a/cif/CIFgen.c +++ b/cif/CIFgen.c @@ -4656,7 +4656,7 @@ cifBridgeLimFunc2(tile, brlims) */ Plane * -CIFGenLayer(op, area, cellDef, origDef, temps, clientdata) +CIFGenLayer(op, area, cellDef, origDef, temps, hier, clientdata) CIFOp *op; /* List of CIFOps telling how to make layer. */ Rect *area; /* Area to consider when generating CIF. Only * material in this area will be considered, so @@ -4672,6 +4672,7 @@ CIFGenLayer(op, area, cellDef, origDef, temps, clientdata) Plane *temps[]; /* Temporary layers to be used when needed * for operation. */ + bool hier; /* TRUE if called from CIFGenSubcell or CIFGenArray */ ClientData clientdata; /* * Data that may be passed to the CIF operation * function. @@ -4689,6 +4690,7 @@ CIFGenLayer(op, area, cellDef, origDef, temps, clientdata) BridgeStruct brs; BridgeLimStruct brlims; BridgeData *bridge; + bool hstop = FALSE; int (*cifGrowFuncPtr)() = (CIFCurStyle->cs_flags & CWF_GROW_EUCLIDEAN) ? cifGrowEuclideanFunc : cifGrowFunc; @@ -4703,6 +4705,10 @@ CIFGenLayer(op, area, cellDef, origDef, temps, clientdata) /* Go through the geometric operations and process them one * at a time. + * + * NOTE: Some opcodes (and whatever follows them) should never + * be run during hierarchical processing. That includes BOUNDARY, + * SQUARES/SLOTS, BBOX, and NET. */ for ( ; op != NULL; op = op->co_next) @@ -4961,6 +4967,11 @@ CIFGenLayer(op, area, cellDef, origDef, temps, clientdata) break; case CIFOP_SQUARES: + if (hier) + { + hstop = TRUE; /* Stop hierarchical processing */ + break; + } if (CalmaContactArrays == FALSE) { DBClearPaintPlane(nextPlane); @@ -4973,6 +4984,11 @@ CIFGenLayer(op, area, cellDef, origDef, temps, clientdata) break; case CIFOP_SQUARES_G: + if (hier) + { + hstop = TRUE; /* Stop hierarchical processing */ + break; + } DBClearPaintPlane(nextPlane); cifPlane = nextPlane; cifSquaresFillArea(op, cellDef, curPlane); @@ -4982,6 +4998,11 @@ CIFGenLayer(op, area, cellDef, origDef, temps, clientdata) break; case CIFOP_SLOTS: + if (hier) + { + hstop = TRUE; /* Stop hierarchical processing */ + break; + } DBClearPaintPlane(nextPlane); cifPlane = nextPlane; cifSlotsFillArea(op, cellDef, curPlane); @@ -5002,6 +5023,11 @@ CIFGenLayer(op, area, cellDef, origDef, temps, clientdata) break; case CIFOP_NET: + if (hier) + { + hstop = TRUE; /* Stop hierarchical processing */ + break; + } netname = (char *)op->co_client; cifPlane = curPlane; ttype = CmdFindNetProc(netname, CIFDummyUse, &bbox, FALSE); @@ -5022,6 +5048,11 @@ CIFGenLayer(op, area, cellDef, origDef, temps, clientdata) break; case CIFOP_BOUNDARY: + if (hier) + { + hstop = TRUE; /* Stop hierarchical processing */ + break; + } cifPlane = curPlane; /* This function for cifoutput only. cifinput handled separately. */ @@ -5047,6 +5078,11 @@ CIFGenLayer(op, area, cellDef, origDef, temps, clientdata) break; case CIFOP_BBOX: + if (hier) + { + hstop = TRUE; /* Stop hierarchical processing */ + break; + } if (CIFErrorDef == NULL) break; /* co_client contains the flag (1) for top-level only */ @@ -5084,6 +5120,7 @@ CIFGenLayer(op, area, cellDef, origDef, temps, clientdata) default: continue; } + if (hstop) break; /* Don't process any further rules */ } return curPlane; @@ -5112,7 +5149,7 @@ CIFGenLayer(op, area, cellDef, origDef, temps, clientdata) */ void -CIFGen(cellDef, origDef, area, planes, layers, replace, genAllPlanes, clientdata) +CIFGen(cellDef, origDef, area, planes, layers, replace, genAllPlanes, hier, clientdata) CellDef *cellDef; /* Cell for which CIF is to be generated. */ CellDef *origDef; /* Original cell, if different from cellDef */ Rect *area; /* Any CIF overlapping this area (in coords @@ -5135,6 +5172,7 @@ CIFGen(cellDef, origDef, area, planes, layers, replace, genAllPlanes, clientdata * those layers not specified as being * generated in the 'layers' mask above. */ + bool hier; /* TRUE if called from CIFGenSubcell or CIFGenArray */ ClientData clientdata; /* Data that may be passed along to the * CIF operation functions. */ @@ -5160,7 +5198,7 @@ CIFGen(cellDef, origDef, area, planes, layers, replace, genAllPlanes, clientdata { CIFErrorLayer = i; new[i] = CIFGenLayer(CIFCurStyle->cs_layers[i]->cl_ops, - &expanded, cellDef, origDef, new, clientdata); + &expanded, cellDef, origDef, new, hier, clientdata); /* Clean up the non-manhattan geometry in the plane */ if (CIFUnfracture) DBMergeNMTiles(new[i], &expanded, diff --git a/cif/CIFhier.c b/cif/CIFhier.c index d5afda0e..4759862c 100644 --- a/cif/CIFhier.c +++ b/cif/CIFhier.c @@ -27,6 +27,7 @@ static char rcsid[] __attribute__ ((unused)) = "$Header: /usr/cvsroot/magic-8.0/ #include +#include "tcltk/tclmagic.h" #include "utils/magic.h" #include "utils/geometry.h" #include "tiles/tile.h" @@ -35,6 +36,7 @@ static char rcsid[] __attribute__ ((unused)) = "$Header: /usr/cvsroot/magic-8.0/ #include "cif/CIFint.h" #include "cif/cif.h" #include "drc/drc.h" +#include "graphics/graphics.h" #include "textio/textio.h" #include "utils/undo.h" #include "utils/malloc.h" @@ -326,7 +328,8 @@ cifHierCellFunc(scx) CIFErrorDef = (CellDef *) NULL; GeoTransRect(&scx->scx_trans, &scx->scx_area, &rootArea); CIFGen(CIFComponentDef, scx->scx_use->cu_def, &rootArea, - CIFComponentPlanes, &CIFCurStyle->cs_hierLayers, FALSE, TRUE); + CIFComponentPlanes, &CIFCurStyle->cs_hierLayers, FALSE, + TRUE, TRUE, (ClientData)NULL); return 0; } @@ -523,6 +526,8 @@ CIFGenSubcells(def, area, output) int stepSize, x, y, i, radius, oldTileOps, oldTileOps2; Rect totalArea, square, interaction; SearchContext scx; + int cuts, totcuts; + float pdone, plast; UndoDisable(); CIFInitCells(); @@ -537,6 +542,16 @@ CIFGenSubcells(def, area, output) scx.scx_use = CIFDummyUse; scx.scx_trans = GeoIdentityTransform; + /* This routine can take a long time, so use the display + * timer to force a 5-second progress check (like is done + * with extract) + */ + GrDisplayStatus = DISPLAY_IN_PROGRESS; + SigSetTimer(5); /* Print at 5-second intervals */ + cuts = 0; + pdone = 0.0; + plast = 0.0; + /* Any tile operations processed here get billed to hierarchy * in addition to being added to the total. */ @@ -551,6 +566,12 @@ CIFGenSubcells(def, area, output) totalArea = *area; GeoClip(&totalArea, &def->cd_bbox); + + totcuts = (totalArea.r_ytop - totalArea.r_ybot + stepSize - 1) + / stepSize; + totcuts *= ((totalArea.r_xtop - totalArea.r_xbot + stepSize - 1) + / stepSize); + for (y = totalArea.r_ybot; y < totalArea.r_ytop; y += stepSize) for (x = totalArea.r_xbot; x < totalArea.r_xtop; x += stepSize) { @@ -576,7 +597,8 @@ CIFGenSubcells(def, area, output) cifHierCopyFunc, (ClientData) CIFTotalDef); CIFErrorDef = def; CIFGen(CIFTotalDef, def, &interaction, CIFTotalPlanes, - &CIFCurStyle->cs_hierLayers, TRUE, TRUE); + &CIFCurStyle->cs_hierLayers, TRUE, TRUE, TRUE, + (ClientData)NULL); /* Now go through all the subcells overlapping the area * and generate CIF for each subcell individually. OR this @@ -593,7 +615,8 @@ CIFGenSubcells(def, area, output) CIFErrorDef = (CellDef *) NULL; CIFGen(def, def, &interaction, CIFComponentPlanes, - &CIFCurStyle->cs_hierLayers, FALSE, TRUE); + &CIFCurStyle->cs_hierLayers, FALSE, TRUE, TRUE, + (ClientData)NULL); /* Make sure everything in the pieces is also in the overall * CIF, then erase the piece stuff from the overall, and @@ -618,9 +641,33 @@ CIFGenSubcells(def, area, output) CIFHierRects += CIFTileOps - oldTileOps2; cifHierCleanup(); + + cuts++; + pdone = 100.0 * ((float)cuts / (float)totcuts); + if ((((pdone - plast) > 1.0) || (cuts == totcuts)) && (cuts > 1)) + { + /* Only print something if the 5-second timer has expired */ + if (GrDisplayStatus == DISPLAY_BREAK_PENDING) + { + TxPrintf("Completed %d%%\n", (int)(pdone + 0.5)); + plast = pdone; + TxFlushOut(); + + GrDisplayStatus = DISPLAY_IN_PROGRESS; + SigSetTimer(5); + } +#ifdef MAGIC_WRAPPER + /* We need to let Tk paint the console display */ + while (Tcl_DoOneEvent(TCL_DONT_WAIT) != 0); +#endif + } } CIFHierTileOps += CIFTileOps - oldTileOps; + + GrDisplayStatus = DISPLAY_IDLE; + SigRemoveTimer(); + UndoEnable(); } @@ -680,7 +727,8 @@ cifHierElementFunc(use, transform, x, y, checkArea) CIFErrorDef = (CellDef *) NULL; CIFGen(CIFComponentDef, use->cu_def, checkArea, CIFComponentPlanes, - &CIFCurStyle->cs_hierLayers, FALSE, TRUE); + &CIFCurStyle->cs_hierLayers, FALSE, TRUE, TRUE, + (ClientData)NULL); return 0; } @@ -921,7 +969,8 @@ cifHierArrayFunc(scx, output) (ClientData) &A); CIFErrorDef = use->cu_parent; CIFGen(CIFTotalDef, use->cu_def, &A, CIFTotalPlanes, - &CIFCurStyle->cs_hierLayers, FALSE, TRUE); + &CIFCurStyle->cs_hierLayers, FALSE, TRUE, TRUE, + (ClientData)NULL); anyInteractions = TRUE; } @@ -938,7 +987,8 @@ cifHierArrayFunc(scx, output) (ClientData) &C); CIFErrorDef = use->cu_parent; CIFGen(CIFTotalDef, use->cu_def, &C, CIFTotalPlanes, - &CIFCurStyle->cs_hierLayers, FALSE, TRUE); + &CIFCurStyle->cs_hierLayers, FALSE, TRUE, TRUE, + (ClientData)NULL); anyInteractions = TRUE; } @@ -955,7 +1005,8 @@ cifHierArrayFunc(scx, output) (ClientData) &B); CIFErrorDef = use->cu_parent; CIFGen(CIFTotalDef, use->cu_def, &B, CIFTotalPlanes, - &CIFCurStyle->cs_hierLayers, FALSE, TRUE); + &CIFCurStyle->cs_hierLayers, FALSE, TRUE, TRUE, + (ClientData)NULL); /* D */ @@ -968,7 +1019,8 @@ cifHierArrayFunc(scx, output) (ClientData) &D); CIFErrorDef = use->cu_parent; CIFGen(CIFTotalDef, use->cu_def, &D, CIFTotalPlanes, - &CIFCurStyle->cs_hierLayers, FALSE, TRUE); + &CIFCurStyle->cs_hierLayers, FALSE, TRUE, TRUE, + (ClientData)NULL); } if (anyInteractions) diff --git a/cif/CIFrdcl.c b/cif/CIFrdcl.c index 02114afb..10dd823a 100644 --- a/cif/CIFrdcl.c +++ b/cif/CIFrdcl.c @@ -572,7 +572,8 @@ CIFPaintCurrent(filetype) CIFOp *op; plane = CIFGenLayer(cifCurReadStyle->crs_layers[i]->crl_ops, - &TiPlaneRect, (CellDef *)NULL, (CellDef *)NULL, cifCurReadPlanes); + &TiPlaneRect, (CellDef *)NULL, (CellDef *)NULL, + cifCurReadPlanes, FALSE, (ClientData)NULL); /* Generate a paint/erase table, then paint from the CIF * plane into the current Magic cell. diff --git a/cif/CIFsee.c b/cif/CIFsee.c index 4b880266..e450e003 100644 --- a/cif/CIFsee.c +++ b/cif/CIFsee.c @@ -164,7 +164,8 @@ CIFPaintLayer(rootDef, area, cifLayer, magicLayer, paintDef) cifHierCopyFunc, (ClientData) CIFComponentDef); oldCount = DBWFeedbackCount; - CIFGen(CIFComponentDef, rootDef, area, CIFPlanes, &depend, TRUE, TRUE); + CIFGen(CIFComponentDef, rootDef, area, CIFPlanes, &depend, TRUE, TRUE, FALSE, + (ClientData)NULL); DBCellClearDef(CIFComponentDef); /* Report any errors that occurred. */ @@ -278,7 +279,8 @@ CIFSeeLayer(rootDef, area, layer) (void) DBTreeSrTiles(&scx, &DBAllButSpaceAndDRCBits, 0, cifHierCopyFunc, (ClientData) CIFComponentDef); oldCount = DBWFeedbackCount; - CIFGen(CIFComponentDef, rootDef, area, CIFPlanes, &depend, TRUE, TRUE); + CIFGen(CIFComponentDef, rootDef, area, CIFPlanes, &depend, TRUE, TRUE, + FALSE, (ClientData)NULL); DBCellClearDef(CIFComponentDef); /* Report any errors that occurred. */ @@ -441,7 +443,8 @@ CIFCoverageLayer(rootDef, area, layer) scx.scx_trans = GeoIdentityTransform; (void) DBTreeSrTiles(&scx, &DBAllButSpaceAndDRCBits, 0, cifHierCopyFunc, (ClientData) CIFComponentDef); - CIFGen(CIFComponentDef, rootDef, area, CIFPlanes, &depend, TRUE, TRUE); + CIFGen(CIFComponentDef, rootDef, area, CIFPlanes, &depend, TRUE, TRUE, + FALSE, (ClientData)NULL); DBCellClearDef(CIFComponentDef); cstats.coverage = 0; diff --git a/cif/CIFtech.c b/cif/CIFtech.c index 07343f05..ce939289 100644 --- a/cif/CIFtech.c +++ b/cif/CIFtech.c @@ -1537,6 +1537,12 @@ cifComputeRadii(layer, des) for (op = layer->cl_ops; op != NULL; op = op->co_next) { + /* BBOX and NET operators should never be used hierarchically */ + /* so ignore any grow/shrink operators that come after them. */ + + if (op->co_opcode == CIFOP_BBOX || op->co_opcode == CIFOP_NET) + break; + /* If CIF layers are used, switch to the max of current * distances and those of the layers used. */ @@ -1597,6 +1603,7 @@ cifComputeRadii(layer, des) case CIFOP_BRIDGELIM: break; case CIFOP_SQUARES: break; case CIFOP_SQUARES_G: break; + } } diff --git a/cif/CIFwrite.c b/cif/CIFwrite.c index 558f147c..8f40c2b2 100644 --- a/cif/CIFwrite.c +++ b/cif/CIFwrite.c @@ -378,7 +378,8 @@ cifOutFunc(def, f) GEO_EXPAND(&def->cd_bbox, CIFCurStyle->cs_radius, &bigArea); CIFErrorDef = def; - CIFGen(def, def, &bigArea, CIFPlanes, &DBAllTypeBits, TRUE, TRUE); + CIFGen(def, def, &bigArea, CIFPlanes, &DBAllTypeBits, TRUE, TRUE, FALSE, + (ClientData)NULL); if (!CIFHierWriteDisable) CIFGenSubcells(def, &bigArea, CIFPlanes); if (!CIFArrayWriteDisable) diff --git a/drc/DRCcif.c b/drc/DRCcif.c index c280c4bd..a06d8d0d 100644 --- a/drc/DRCcif.c +++ b/drc/DRCcif.c @@ -552,7 +552,7 @@ drcCifCheck(arg) oldTiles = DRCstatTiles; CIFGen(arg->dCD_celldef, arg->dCD_celldef, checkRect, CIFPlanes, - &DBAllTypeBits, TRUE, TRUE); + &DBAllTypeBits, TRUE, TRUE, FALSE, (ClientData)NULL); for (i = 0; i < drcCifStyle->cs_nLayers; i++) { diff --git a/graphics/W3Dmain.c b/graphics/W3Dmain.c index 656f37b8..ec77baf3 100644 --- a/graphics/W3Dmain.c +++ b/graphics/W3Dmain.c @@ -1739,7 +1739,8 @@ W3DCIFredisplay(w, rootArea, clipArea) scx.scx_trans = GeoIdentityTransform; (void) DBTreeSrTiles(&scx, &DBAllButSpaceAndDRCBits, 0, cifHierCopyFunc, (ClientData) CIFComponentDef); - CIFGen(CIFComponentDef, cellDef, &clipRect, CIFPlanes, &DBAllTypeBits, TRUE, TRUE); + CIFGen(CIFComponentDef, cellDef, &clipRect, CIFPlanes, &DBAllTypeBits, TRUE, + TRUE, FALSE, (ClientData)NULL); DBCellClearDef(CIFComponentDef); w3dClear();