diff --git a/calma/CalmaRdcl.c b/calma/CalmaRdcl.c index b036bd26..15cc4531 100644 --- a/calma/CalmaRdcl.c +++ b/calma/CalmaRdcl.c @@ -994,12 +994,39 @@ calmaElementSref( * and place the cell in the magic database. However, if this is * a cell to be flattened a la "gds flatten", then we keep the GDS * coordinates, and don't scale to the magic database. + * + * NOTE: Scaling everything in the middle or reading array data + * and then retroactively adjusting the array data read earlier + * is problematic, and probably incorrect. */ for (n = 0; n < nref; n++) { savescale = cifCurReadStyle->crs_scaleFactor; - calmaReadPoint(&refarray[n], 1); + + /* If there is only one column, then X data in the 2nd or 3rd + * entry is irrelevant. If there is only one row, then Y data + * in the 2nd or 3rd entry is irrelevant. Prevent issues caused + * by incorrect/uninitialized data in these positions by ignoring + * them as needed. + */ + if ((n > 0) && (rows == 1)) + { + calmaReadX(&refarray[n], 1); + calmaSkipBytes(4); + refarray[n].p_y = 0; + } + else if ((n > 0) && (cols == 1)) + { + calmaSkipBytes(4); + calmaReadY(&refarray[n], 1); + refarray[n].p_x = 0; + } + else + { + calmaReadPoint(&refarray[n], 1); + } + refunscaled[n] = refarray[n]; // Save for CDFLATGDS cells refarray[n].p_x = CIFScaleCoord(refarray[n].p_x, COORD_EXACT); if (savescale != cifCurReadStyle->crs_scaleFactor) diff --git a/calma/CalmaRdpt.c b/calma/CalmaRdpt.c index ef0cf396..767b2a90 100644 --- a/calma/CalmaRdpt.c +++ b/calma/CalmaRdpt.c @@ -114,6 +114,8 @@ calmaInputRescale( /* * ---------------------------------------------------------------------------- * + * calmaReadX --- + * calmaReadY --- * calmaReadPoint --- * * Read a point from the input. @@ -132,11 +134,17 @@ calmaInputRescale( * encountered, then everything in the GDS planes is rescaled * to match. * + * Notes: + * This routine has been split into individual X and Y reads so that + * array data can be read while ignoring offset information when there + * is only one row or column; otherwise, bad or uninitialized data + * in the record can cause unnecessary and incorrect scaling. + * * ---------------------------------------------------------------------------- */ void -calmaReadPoint( +calmaReadX( Point *p, int iscale) { @@ -163,6 +171,15 @@ calmaReadPoint( } } p->p_x /= calmaReadScale2; +} + + +void +calmaReadY( + Point *p, + int iscale) +{ + int rescale; READI4((p)->p_y); p->p_y *= (calmaReadScale1 * iscale); @@ -188,6 +205,15 @@ calmaReadPoint( p->p_y /= calmaReadScale2; } +void +calmaReadPoint( + Point *p, + int iscale) +{ + calmaReadX(p, iscale); + calmaReadY(p, iscale); +} + /* * ---------------------------------------------------------------------------- diff --git a/calma/calma.h b/calma/calma.h index f745e1d6..394323a9 100644 --- a/calma/calma.h +++ b/calma/calma.h @@ -82,6 +82,8 @@ extern int calmaProcessDefZ(CellDef *def, gzFile outf, bool do_library); #endif extern bool calmaReadI2Record(int type, int *pvalue); extern bool calmaReadI4Record(int type, int *pvalue); +extern void calmaReadX(Point *p, int iscale); +extern void calmaReadY(Point *p, int iscale); extern void calmaReadPoint(Point *p, int iscale); extern bool calmaReadR8(double *pd); extern bool calmaReadStampRecord(int type, int *stampptr);