Changeset: 4e895eccbc05 for MonetDB
URL: http://dev.monetdb.org/hg/MonetDB?cmd=changeset;node=4e895eccbc05
Modified Files:
        geom/lib/libgeom.h
        geom/monetdb5/geom.c
        geom/monetdb5/geom.h
Branch: Jun2016
Log Message:

Lots of error checking and possible leaks fixed.


diffs (truncated from 1934 to 300 lines):

diff --git a/geom/lib/libgeom.h b/geom/lib/libgeom.h
--- a/geom/lib/libgeom.h
+++ b/geom/lib/libgeom.h
@@ -134,7 +134,6 @@ libgeom_export void libgeom_exit(void);
  * On failure, returns NULL.
  */
 //#define wkb2geos( geom ) wkb_isnil((geom))? NULL: 
GEOSGeomFromWKB_buf((unsigned char *)((geom)->data), (geom)->len)
-//#define wkb_nil geos2wkb(NULL);
 #define mbr_nil mbrFromGeos(NULL); 
 
 libgeom_export int wkb_isnil(wkb *wkbp);
diff --git a/geom/monetdb5/geom.c b/geom/monetdb5/geom.c
--- a/geom/monetdb5/geom.c
+++ b/geom/monetdb5/geom.c
@@ -15,6 +15,8 @@
 
 int TYPE_mbr;
 
+static wkb *geos2wkb(const GEOSGeometry *geosGeometry);
+
 static inline int
 geometryHasZ(int info)
 {
@@ -60,7 +62,7 @@ radians2degrees(double *x, double *y, do
 }
 
 static str
-transformCoordSeq(int idx, int coordinatesNum, projPJ proj4_src, projPJ 
proj4_dst, const GEOSCoordSequence *gcs_old, GEOSCoordSequence **gcs_new)
+transformCoordSeq(int idx, int coordinatesNum, projPJ proj4_src, projPJ 
proj4_dst, const GEOSCoordSequence *gcs_old, GEOSCoordSeq gcs_new)
 {
        double x = 0, y = 0, z = 0;
        int *errorNum = 0;
@@ -91,11 +93,11 @@ transformCoordSeq(int idx, int coordinat
        if (pj_is_latlong(proj4_dst))
                radians2degrees(&x, &y, &z);
 
-       GEOSCoordSeq_setX(*gcs_new, idx, x);
-       GEOSCoordSeq_setY(*gcs_new, idx, y);
+       GEOSCoordSeq_setX(gcs_new, idx, x);
+       GEOSCoordSeq_setY(gcs_new, idx, y);
 
        if (coordinatesNum > 2)
-               GEOSCoordSeq_setZ(*gcs_new, idx, z);
+               GEOSCoordSeq_setZ(gcs_new, idx, z);
 
        return MAL_SUCCEED;
 }
@@ -108,28 +110,34 @@ transformPoint(GEOSGeometry **transforme
        GEOSCoordSeq gcs_new;
        str ret = MAL_SUCCEED;
 
+       *transformedGeometry = NULL;
+
        /* get the number of coordinates the geometry has */
        coordinatesNum = GEOSGeom_getCoordinateDimension(geosGeometry);
        /* get the coordinates of the points comprising the geometry */
        gcs_old = GEOSGeom_getCoordSeq(geosGeometry);
 
-       if (gcs_old == NULL) {
-               *transformedGeometry = NULL;
+       if (gcs_old == NULL)
                throw(MAL, "geom.wkbTransform", "GEOSGeom_getCoordSeq failed");
-       }
 
        /* create the coordinates sequence for the transformed geometry */
        gcs_new = GEOSCoordSeq_create(1, coordinatesNum);
+       if (gcs_new == NULL)
+               throw(MAL, "geom.wkbTransform", "GEOSGeom_getCoordSeq failed");
 
        /* create the transformed coordinates */
-       ret = transformCoordSeq(0, coordinatesNum, proj4_src, proj4_dst, 
gcs_old, &gcs_new);
+       ret = transformCoordSeq(0, coordinatesNum, proj4_src, proj4_dst, 
gcs_old, gcs_new);
        if (ret != MAL_SUCCEED) {
-               *transformedGeometry = NULL;
+               GEOSCoordSeq_destroy(gcs_new);
                return ret;
        }
 
-       /* create the geometry from the coordinates seqience */
+       /* create the geometry from the coordinates sequence */
        *transformedGeometry = GEOSGeom_createPoint(gcs_new);
+       if (*transformedGeometry == NULL) {
+               GEOSCoordSeq_destroy(gcs_new);
+               throw(MAL, "geom.wkbTransform", "GEOSGeom_getCoordSeq failed");
+       }
 
        return MAL_SUCCEED;
 }
@@ -155,10 +163,12 @@ transformLine(GEOSCoordSeq *gcs_new, con
 
        /* create the coordinates sequence for the transformed geometry */
        *gcs_new = GEOSCoordSeq_create(pointsNum, coordinatesNum);
+       if (*gcs_new == NULL)
+               throw(MAL, "geom.wkbTransform", "GEOSCoordSeq_create failed");
 
        /* create the transformed coordinates */
        for (i = 0; i < pointsNum; i++) {
-               ret = transformCoordSeq(i, coordinatesNum, proj4_src, 
proj4_dst, gcs_old, gcs_new);
+               ret = transformCoordSeq(i, coordinatesNum, proj4_src, 
proj4_dst, gcs_old, *gcs_new);
                if (ret != MAL_SUCCEED) {
                        GEOSCoordSeq_destroy(*gcs_new);
                        *gcs_new = NULL;
@@ -176,7 +186,6 @@ transformLineString(GEOSGeometry **trans
        str ret = MAL_SUCCEED;
 
        ret = transformLine(&coordSeq, geosGeometry, proj4_src, proj4_dst);
-
        if (ret != MAL_SUCCEED) {
                *transformedGeometry = NULL;
                return ret;
@@ -184,6 +193,10 @@ transformLineString(GEOSGeometry **trans
 
        /* create the geometry from the coordinates sequence */
        *transformedGeometry = GEOSGeom_createLineString(coordSeq);
+       if (*transformedGeometry == NULL) {
+               GEOSCoordSeq_destroy(coordSeq);
+               throw(MAL, "geom.Transform", "GEOSGeom_createLineString 
failed");
+       }
 
        return ret;
 }
@@ -195,7 +208,6 @@ transformLinearRing(GEOSGeometry **trans
        str ret = MAL_SUCCEED;
 
        ret = transformLine(&coordSeq, geosGeometry, proj4_src, proj4_dst);
-
        if (ret != MAL_SUCCEED) {
                *transformedGeometry = NULL;
                return ret;
@@ -203,11 +215,10 @@ transformLinearRing(GEOSGeometry **trans
 
        /* create the geometry from the coordinates sequence */
        *transformedGeometry = GEOSGeom_createLinearRing(coordSeq);
-
-       GEOSCoordSeq_destroy(coordSeq);
-
-       if (*transformedGeometry == NULL)
-               throw(MAL, "geom.wkbTransform", "GEOSGeom_createLinearRing 
failed");
+       if (*transformedGeometry == NULL) {
+               GEOSCoordSeq_destroy(coordSeq);
+               throw(MAL, "geom.Transform", "GEOSGeom_createLineString 
failed");
+       }
 
        return ret;
 }
@@ -223,7 +234,7 @@ transformPolygon(GEOSGeometry **transfor
 
        /* get the exterior ring of the polygon */
        exteriorRingGeometry = GEOSGetExteriorRing(geosGeometry);
-       if (!exteriorRingGeometry) {
+       if (exteriorRingGeometry == NULL) {
                *transformedGeometry = NULL;
                throw(MAL, "geom.wkbTransform", "GEOSGetExteriorRing failed");
        }
@@ -255,6 +266,7 @@ transformPolygon(GEOSGeometry **transfor
                        while (--i >= 0)
                                
GEOSGeom_destroy(transformedInteriorRingGeometries[i]);
                        GDKfree(transformedInteriorRingGeometries);
+                       GEOSGeom_destroy(transformedExteriorRingGeometry);
                        *transformedGeometry = NULL;
                        return ret;
                }
@@ -268,6 +280,7 @@ transformPolygon(GEOSGeometry **transfor
                ret = createException(MAL, "geom.wkbTransform", 
"GEOSGeom_createPolygon failed");
        }
        GDKfree(transformedInteriorRingGeometries);
+       GEOSGeom_destroy(transformedExteriorRingGeometry);
 
        return ret;
 }
@@ -282,6 +295,8 @@ transformMultiGeometry(GEOSGeometry **tr
 
        geometriesNum = GEOSGetNumGeometries(geosGeometry);
        transformedMultiGeometries = GDKmalloc(geometriesNum * 
sizeof(GEOSGeometry *));
+       if (transformedMultiGeometries == NULL)
+               throw(MAL, "geom.Transform", MAL_MALLOC_FAIL);
 
        for (i = 0; i < geometriesNum; i++) {
                multiGeometry = GEOSGetGeometryN(geosGeometry, i);
@@ -302,12 +317,14 @@ transformMultiGeometry(GEOSGeometry **tr
                        ret = transformPolygon(&transformedMultiGeometries[i], 
multiGeometry, proj4_src, proj4_dst, srid);
                        break;
                default:
-                       transformedMultiGeometries[i] = NULL;
                        ret = createException(MAL, "geom.Transform", "Unknown 
geometry type");
+                       break;
                }
 
                if (ret != MAL_SUCCEED) {
-                       GDKfree(*transformedMultiGeometries);
+                       while (--i >= 0)
+                               GEOSGeom_destroy(transformedMultiGeometries[i]);
+                       GDKfree(transformedMultiGeometries);
                        *transformedGeometry = NULL;
                        return ret;
                }
@@ -316,16 +333,22 @@ transformMultiGeometry(GEOSGeometry **tr
        }
 
        *transformedGeometry = GEOSGeom_createCollection(geometryType - 1, 
transformedMultiGeometries, geometriesNum);
+       if (*transformedGeometry == NULL) {
+               for (i = 0; i < geometriesNum; i++)
+                       GEOSGeom_destroy(transformedMultiGeometries[i]);
+               ret = createException(MAL, "geom.Transform", 
"GEOSGeom_createCollection failed");
+       }
+       GDKfree(transformedMultiGeometries);
 
        return ret;
 }
 
 /* the following function is used in postgis to get projPJ from str.
- * it is necessary to do it ina detailed way like that because pj_init_plus
+ * it is necessary to do it in a detailed way like that because pj_init_plus
  * does not set all parameters correctly and I cannot test whether the
  * coordinate reference systems are geographic or not */
 static projPJ
-projFromStr(char *projStr)
+projFromStr(const char *projStr)
 {
        int t;
        char *params[1024];     // one for each parameter
@@ -345,25 +368,16 @@ projFromStr(char *projStr)
 
        params[0] = str;        // 1st param, we'll null terminate at the " " 
soon
 
-       loc = str;
        t = 1;
-       while ((loc != NULL) && (*loc != 0)) {
-               loc = strchr(loc, ' ');
-               if (loc != NULL) {
-                       *loc = 0;       // null terminate
-                       params[t] = loc + 1;
-                       loc++;  // next char
-                       t++;    //next param
-               }
-       }
-
-       if (!(result = pj_init(t, params))) {
-               GDKfree(str);
-               return NULL;
-       }
+       for (loc = strchr(str, ' '); loc != NULL; loc = strchr(loc, ' ')) {
+               *loc++ = 0;     // null terminate and advance
+               params[t++] = loc;
+       }
+
+       result = pj_init(t, params);
        GDKfree(str);
+
        return result;
-
 }
 #endif
 
@@ -390,13 +404,18 @@ wkbTransform(wkb **transformedWKB, wkb *
                throw(MAL, "geom.wkbTransform", "Could not find in 
spatial_ref_sys srid %d\n", *srid_src);
        if (!strcmp(*proj4_dst_str, "null"))
                throw(MAL, "geom.wkbTransform", "Could not find in 
spatial_ref_sys srid %d\n", *srid_dst);
+
+       if (*geomWKB == NULL)
+               throw(MAL, "geom.Transform", "wkb is null");
+
        proj4_src = /*pj_init_plus */ projFromStr(*proj4_src_str);
        proj4_dst = /*pj_init_plus */ projFromStr(*proj4_dst_str);
-
-       if (*geomWKB == NULL) {
-               pj_free(proj4_src);
-               pj_free(proj4_dst);
-               throw(MAL, "geom.Transform", "wkb is null");
+       if (proj4_src == NULL || proj4_dst == NULL) {
+               if (proj4_src)
+                       pj_free(proj4_src);
+               if (proj4_dst)
+                       pj_free(proj4_dst);
+               throw(MAL, "geom.Transform", "pj_init failed");
        }
 
        /* get the geosGeometry from the wkb */
@@ -431,7 +450,8 @@ wkbTransform(wkb **transformedWKB, wkb *
                /* set the new srid */
                GEOSSetSRID(transformedGeosGeometry, *srid_dst);
                /* get the wkb */
-               *transformedWKB = geos2wkb(transformedGeosGeometry);
+               if ((*transformedWKB = geos2wkb(transformedGeosGeometry)) == 
NULL)
+                       ret = createException(MAL, "geom.wkbTransform", 
"geos2wkb failed");
                /* destroy the geos geometries */
                GEOSGeom_destroy(transformedGeosGeometry);
        }
@@ -446,7 +466,7 @@ wkbTransform(wkb **transformedWKB, wkb *
 
 //gets a coord seq and forces it to have dim dimensions adding or removing 
extra dimensions
 static str
-forceDimCoordSeq(int idx, int coordinatesNum, int dim, const GEOSCoordSequence 
*gcs_old, GEOSCoordSequence **gcs_new)
+forceDimCoordSeq(int idx, int coordinatesNum, int dim, const GEOSCoordSequence 
*gcs_old, GEOSCoordSeq gcs_new)
 {
        double x = 0, y = 0, z = 0;
 
@@ -460,12 +480,12 @@ forceDimCoordSeq(int idx, int coordinate
                        throw(MAL, "geom.ForceDim", "GEOSCoordSeq_getZ failed");
 
_______________________________________________
checkin-list mailing list
checkin-list@monetdb.org
https://www.monetdb.org/mailman/listinfo/checkin-list

Reply via email to