Skip to content

Commit

Permalink
Browse files Browse the repository at this point in the history
When creating geometry collections for GEOS, skip any empty parts
  • Loading branch information
github-actions[bot] authored and nyalldawson committed Jul 9, 2020
1 parent e540cbb commit 7382248
Show file tree
Hide file tree
Showing 2 changed files with 33 additions and 2 deletions.
14 changes: 12 additions & 2 deletions src/core/geometry/qgsgeos.cpp
Expand Up @@ -1055,8 +1055,18 @@ geos::unique_ptr QgsGeos::createGeosCollection( int typeId, const QVector<GEOSGe
{
if ( *geomIt )
{
geomarr[i] = *geomIt;
++i;
if ( GEOSisEmpty_r( geosinit()->ctxt, *geomIt ) )
{
// don't add empty parts to a geos collection, it can cause crashes in GEOS
nNullGeoms++;
nNotNullGeoms--;
GEOSGeom_destroy_r( geosinit()->ctxt, *geomIt );
}
else
{
geomarr[i] = *geomIt;
++i;
}
}
}
geos::unique_ptr geom;
Expand Down
21 changes: 21 additions & 0 deletions tests/src/core/testqgsgeometry.cpp
Expand Up @@ -52,6 +52,7 @@
#include "qgscurvepolygon.h"
#include "qgsproject.h"
#include "qgslinesegment.h"
#include "qgsgeos.h"

//qgs unit test utility class
#include "qgsrenderchecker.h"
Expand Down Expand Up @@ -85,6 +86,7 @@ class TestQgsGeometry : public QObject
void vertexIterator();
void partIterator();

void geos();

// geometry types
void point(); //test QgsPointV2
Expand Down Expand Up @@ -522,6 +524,25 @@ void TestQgsGeometry::partIterator()
// See test_qgsgeometry.py for geometry-type specific checks!
}

void TestQgsGeometry::geos()
{
// test GEOS conversion utils

// empty parts should NOT be added to a GEOS collection -- it can cause crashes in GEOS
QgsMultiPolygon polyWithEmptyParts;
geos::unique_ptr asGeos( QgsGeos::asGeos( &polyWithEmptyParts ) );
QgsGeometry res( QgsGeos::fromGeos( asGeos.get() ) );
QCOMPARE( res.asWkt(), QStringLiteral( "MultiPolygon EMPTY" ) );
polyWithEmptyParts.addGeometry( new QgsPolygon( new QgsLineString() ) );
polyWithEmptyParts.addGeometry( new QgsPolygon( new QgsLineString( QVector< QgsPoint >() << QgsPoint( 0, 0 ) << QgsPoint( 0, 1 ) << QgsPoint( 1, 1 ) << QgsPoint( 0, 0 ) ) ) );
polyWithEmptyParts.addGeometry( new QgsPolygon( new QgsLineString() ) );
polyWithEmptyParts.addGeometry( new QgsPolygon( new QgsLineString( QVector< QgsPoint >() << QgsPoint( 10, 0 ) << QgsPoint( 10, 1 ) << QgsPoint( 11, 1 ) << QgsPoint( 10, 0 ) ) ) );
asGeos = QgsGeos::asGeos( &polyWithEmptyParts );
QCOMPARE( GEOSGetNumGeometries_r( QgsGeos::getGEOSHandler(), asGeos.get() ), 2 );
res = QgsGeometry( QgsGeos::fromGeos( asGeos.get() ) );
QCOMPARE( res.asWkt(), QStringLiteral( "MultiPolygon (((0 0, 0 1, 1 1, 0 0)),((10 0, 10 1, 11 1, 10 0)))" ) );
}

void TestQgsGeometry::point()
{
//test QgsPointV2
Expand Down

0 comments on commit 7382248

Please sign in to comment.