diff --git a/commands/CmdCD.c b/commands/CmdCD.c index 65db84f9..6cd842a0 100644 --- a/commands/CmdCD.c +++ b/commands/CmdCD.c @@ -3678,7 +3678,7 @@ cmdDumpParseArgs(cmdName, w, cmd, dummy, scx) Point childPoint, editPoint, rootPoint; CellDef *def, *rootDef, *editDef; bool hasChild, hasRoot, hasTrans; - Rect rootBox; + Rect rootBox, bbox; Transform *tx_cell, trans_cell; char **av; char *cellnameptr, *fullpathname; @@ -3792,6 +3792,25 @@ cmdDumpParseArgs(cmdName, w, cmd, dummy, scx) return FALSE; } + /* + * Get def's bounding box. If def is an abstract view with CDFIXEDBBOX + * set, then used the property FIXED_BBOX to set the bounding box. + */ + bbox = def->cd_bbox; + if (def->cd_flags & CDFIXEDBBOX) + { + char *propvalue; + bool found; + + propvalue = DBPropGet(def, "FIXED_BBOX", &found); + if (found) + { + if (sscanf(propvalue, "%d %d %d %d", &bbox.r_xbot, &bbox.r_ybot, + &bbox.r_xtop, &bbox.r_ytop) != 4) + bbox = def->cd_bbox; + } + } + /* * Parse the remainder of the arguments to find out the reference * points in the child cell and the edit cell. Use the defaults diff --git a/database/DBcellbox.c b/database/DBcellbox.c index 6eb8d95d..db702aa5 100644 --- a/database/DBcellbox.c +++ b/database/DBcellbox.c @@ -616,11 +616,6 @@ dbReComputeBboxFunc(cellDef, boundProc, recurseProc) bool foundAny; int pNum; - /* Cells which declare their bounding box to be fixed */ - /* must return immediately. */ - - if (cellDef->cd_flags & CDFIXEDBBOX) return; - /* * Include area of subcells separately */ diff --git a/database/DBcellsrch.c b/database/DBcellsrch.c index a8fb9edc..5590f230 100644 --- a/database/DBcellsrch.c +++ b/database/DBcellsrch.c @@ -1810,6 +1810,31 @@ donecell: DBScalePoint(&cellDef->cd_extended.r_ll, scalen, scaled); DBScalePoint(&cellDef->cd_extended.r_ur, scalen, scaled); + /* If the cell is an abstract view with a fixed bounding box, then */ + /* adjust the bounding box property to match the new scale. */ + + if ((cellDef->cd_flags & CDFIXEDBBOX) != 0) + { + Rect r; + bool found; + char *propval; + + propval = (char *)DBPropGet(cellDef, "FIXED_BBOX", &found); + if (found) + { + if (sscanf(propval, "%d %d %d %d", &r.r_xbot, &r.r_ybot, + &r.r_xtop, &r.r_ytop) == 4) + { + DBScalePoint(&r.r_ll, scalen, scaled); + DBScalePoint(&r.r_ur, scalen, scaled); + + propval = (char *)mallocMagic(40); + sprintf(propval, "%d %d %d %d", r.r_xbot, r.r_ybot, + r.r_xtop, r.r_ytop); + DBPropPut(cellDef, "FIXED_BBOX", propval); + } + } + } return 0; } diff --git a/database/DBio.c b/database/DBio.c index 09ee7d7a..3f6aca45 100644 --- a/database/DBio.c +++ b/database/DBio.c @@ -1584,17 +1584,17 @@ dbReadProperties(cellDef, line, len, f, scalen, scaled) if (!strcmp(propertyname, "GDS_FILE")) cellDef->cd_flags |= CDVENDORGDS; - /* Also process FIXED_BBOX property, but do not keep */ - /* the property, as it should be regenerated on cell */ - /* output from the current scale. */ + /* Also process FIXED_BBOX property, as units must match */ if (!strcmp(propertyname, "FIXED_BBOX")) { + Rect locbbox; + if (sscanf(propertyvalue, "%d %d %d %d", - &(cellDef->cd_bbox.r_xbot), - &(cellDef->cd_bbox.r_ybot), - &(cellDef->cd_bbox.r_xtop), - &(cellDef->cd_bbox.r_ytop)) != 4) + &(locbbox.r_xbot), + &(locbbox.r_ybot), + &(locbbox.r_xtop), + &(locbbox.r_ytop)) != 4) { TxError("Cannot read bounding box values in %s property", propertyname); @@ -1605,20 +1605,25 @@ dbReadProperties(cellDef, line, len, f, scalen, scaled) { if (scalen > 1) { - cellDef->cd_bbox.r_xbot *= scalen; - cellDef->cd_bbox.r_ybot *= scalen; - cellDef->cd_bbox.r_xtop *= scalen; - cellDef->cd_bbox.r_ytop *= scalen; + locbbox.r_xbot *= scalen; + locbbox.r_ybot *= scalen; + locbbox.r_xtop *= scalen; + locbbox.r_ytop *= scalen; } if (scaled > 1) { - cellDef->cd_bbox.r_xbot /= scaled; - cellDef->cd_bbox.r_ybot /= scaled; - cellDef->cd_bbox.r_xtop /= scaled; - cellDef->cd_bbox.r_ytop /= scaled; + locbbox.r_xbot /= scaled; + locbbox.r_ybot /= scaled; + locbbox.r_xtop /= scaled; + locbbox.r_ytop /= scaled; } - cellDef->cd_extended = cellDef->cd_bbox; cellDef->cd_flags |= CDFIXEDBBOX; + storedvalue = (char *)mallocMagic(40); + sprintf(storedvalue, "%d %d %d %d", + locbbox.r_xbot, locbbox.r_ybot, + locbbox.r_xtop, locbbox.r_ytop); + (void) DBPropPut(cellDef, propertyname, storedvalue); + } } else @@ -2538,27 +2543,6 @@ DBCellWriteFile(cellDef, f) DBPropEnum(cellDef, dbWritePropFunc, (ClientData)f); } - /* Fixed bounding box goes into a special property in output file */ - /* This is not kept internally as a property, so that it can be */ - /* read and written in the correct units without regard to internal */ - /* changes in scaling. */ - - if (cellDef->cd_flags & CDFIXEDBBOX) - { - // If there were no explicit properties, then we need to - // write the header - - if (cellDef->cd_props == (ClientData)NULL) - FPRINTF(f, "<< properties >>\n"); - - sprintf(lstring, "string FIXED_BBOX %d %d %d %d\n", - cellDef->cd_bbox.r_xbot / reducer, - cellDef->cd_bbox.r_ybot / reducer, - cellDef->cd_bbox.r_xtop / reducer, - cellDef->cd_bbox.r_ytop / reducer); - FPRINTF(f, lstring); - } - FPRINTF(f, "<< end >>\n"); if (fflush(f) == EOF || ferror(f)) diff --git a/lef/defRead.c b/lef/defRead.c index 370e3992..0b5e3261 100644 --- a/lef/defRead.c +++ b/lef/defRead.c @@ -577,7 +577,7 @@ DefReadLocation(use, f, oscale, tptr) float oscale; Transform *tptr; { - Rect *r, tr; + Rect *r, tr, rect; int keyword; char *token; float x, y; @@ -611,7 +611,25 @@ DefReadLocation(use, f, oscale, tptr) /* restore the lower-left corner position. */ if (use) + { r = &use->cu_def->cd_bbox; + + /* Abstract views with fixed bounding boxes use the FIXED_BBOX property */ + + if (use->cu_def->cd_flags & CDFIXEDBBOX) + { + char *propval; + bool found; + + propval = DBPropGet(use->cu_def, "FIXED_BBOX", &found); + if (found) + { + if (sscanf(propval, "%d %d %d %d", &rect.r_xbot, &rect.r_ybot, + &rect.r_xtop, &rect.r_ytop) == 4) + r = ▭ + } + } + } else r = &GeoNullRect; diff --git a/lef/lefRead.c b/lef/lefRead.c index d9986192..3904ade4 100644 --- a/lef/lefRead.c +++ b/lef/lefRead.c @@ -1370,7 +1370,7 @@ LefReadMacro(f, mname, oscale, importForeign) CellDef *lefMacro; HashEntry *he; - char *token, tsave[128]; + char *token, tsave[128], *propval; int keyword, pinNum; float x, y; bool has_size, is_imported = FALSE; @@ -1558,40 +1558,50 @@ origin_error: } /* Finish up creating the cell */ + DBReComputeBbox(lefMacro); if (is_imported) { - /* Redefine cell bounding box to match the LEF macro */ - /* Leave "extended" to mark the original bounding box */ + /* Define the FIXED_BBOX property to match the LEF macro */ if (has_size) { - lefMacro->cd_bbox = lefBBox; lefMacro->cd_flags |= CDFIXEDBBOX; + propval = (char *)mallocMagic(40); + sprintf(propval, "%d %d %d %d", + lefBBox.r_xbot, lefBBox.r_ybot, + lefBBox.r_xtop, lefBBox.r_ytop); + DBPropPut(lefMacro, "FIXED_BBOX", propval); } } else { DBAdjustLabelsNew(lefMacro, &TiPlaneRect, 1); - if (!has_size) + if (has_size) { - LefError(" Macro does not define size: computing from geometry\n"); - DBReComputeBbox(lefMacro); + lefMacro->cd_flags |= CDFIXEDBBOX; + propval = (char *)mallocMagic(40); + sprintf(propval, "%d %d %d %d", + lefBBox.r_xbot, lefBBox.r_ybot, + lefBBox.r_xtop, lefBBox.r_ytop); + DBPropPut(lefMacro, "FIXED_BBOX", propval); } else { - char *propstr = (char *)mallocMagic(64); - int reducer = DBCellFindScale(lefMacro); + LefError(" Macro does not define size: computing from geometry\n"); - lefMacro->cd_bbox = lefBBox; - lefMacro->cd_extended = lefBBox; + /* Set the placement bounding box property to the current bounding box */ + lefMacro->cd_flags |= CDFIXEDBBOX; + propval = (char *)mallocMagic(40); + sprintf(propval, "%d %d %d %d", + lefMacro->cd_bbox.r_xbot, + lefMacro->cd_bbox.r_ybot, + lefMacro->cd_bbox.r_xtop, + lefMacro->cd_bbox.r_ytop); + DBPropPut(lefMacro, "FIXED_BBOX", propval); + DRCCheckThis(lefMacro, TT_CHECKPAINT, &lefMacro->cd_bbox); } - - /* Fix the bounding box and do not allow edits */ - lefMacro->cd_flags |= /* CDNOEDIT | */ CDFIXEDBBOX; - - DRCCheckThis(lefMacro, TT_CHECKPAINT, &lefMacro->cd_bbox); } /* Note: The value here is ignored, setting to "TRUE". */ diff --git a/select/selDisplay.c b/select/selDisplay.c index 90b06233..aa84a2b1 100644 --- a/select/selDisplay.c +++ b/select/selDisplay.c @@ -307,11 +307,34 @@ selRedisplayCellFunc(scx, window) SearchContext *scx; /* Describes cell found. */ MagWindow *window; /* Window in which to redisplay. */ { - Rect tmp, screen; + Rect tmp, screen, bbox; Point p; char idName[100]; - GeoTransRect(&scx->scx_trans, &scx->scx_use->cu_def->cd_bbox, &tmp); + /* Selections of cells with a fixed bounding box flag show the outline */ + /* of the fixed bounding box, not the actual bounding box. */ + + if (scx->scx_use->cu_def->cd_flags & CDFIXEDBBOX) + { + bool found; + char *propval; + + propval = (char *)DBPropGet(scx->scx_use->cu_def, "FIXED_BBOX", &found); + if (found) + { + if (sscanf(propval, "%d %d %d %d", &bbox.r_xbot, &bbox.r_ybot, + &bbox.r_xtop, &bbox.r_ytop) == 4) + GeoTransRect(&scx->scx_trans, &bbox, &tmp); + else + found = FALSE; + } + if (!found) + GeoTransRect(&scx->scx_trans, &scx->scx_use->cu_def->cd_bbox, &tmp); + } + else + { + GeoTransRect(&scx->scx_trans, &scx->scx_use->cu_def->cd_bbox, &tmp); + } if (!DBSrPaintArea((Tile *) NULL, selRedisplayPlane, &tmp, &DBAllButSpaceBits, selAlways1, (ClientData) NULL)) return 0;