aboutsummaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorEven Rouault <even.rouault@spatialys.com>2019-03-20 19:55:46 +0100
committerEven Rouault <even.rouault@spatialys.com>2019-03-20 19:58:25 +0100
commitfe01efca4e02d4ded4b397c6dcd0cd8ab8f6123a (patch)
tree2425c9f4a73cd70c65ace2485b53aa7e738b1058 /src
parentc223eb7753c9241defcfba361ade49f1b20e6fd3 (diff)
downloadPROJ-fe01efca4e02d4ded4b397c6dcd0cd8ab8f6123a.tar.gz
PROJ-fe01efca4e02d4ded4b397c6dcd0cd8ab8f6123a.zip
isea: detect various int overflows and div by zero
Fixes https://bugs.chromium.org/p/oss-fuzz/issues/detail?id=2199 https://bugs.chromium.org/p/oss-fuzz/issues/detail?id=2241 https://bugs.chromium.org/p/oss-fuzz/issues/detail?id=2390 https://bugs.chromium.org/p/oss-fuzz/issues/detail?id=7674 Credit to OSS Fuzz
Diffstat (limited to 'src')
-rw-r--r--src/projections/isea.cpp24
1 files changed, 22 insertions, 2 deletions
diff --git a/src/projections/isea.cpp b/src/projections/isea.cpp
index fc74bebe..659ca790 100644
--- a/src/projections/isea.cpp
+++ b/src/projections/isea.cpp
@@ -10,6 +10,8 @@
#include <stdlib.h>
#include <string.h>
+#include <limits>
+
#define PJ_LIB__
#include "proj_internal.h"
#include "proj_math.h"
@@ -89,6 +91,9 @@ static void hexbin2(double width, double x, double y, long *i, long *j) {
y = y - x / 2.0; /* adjustment for rotated X */
/* adjust for actual hexwidth */
+ if( width == 0 ) {
+ throw "Division by zero";
+ }
x /= width;
y /= width;
@@ -100,6 +105,9 @@ static void hexbin2(double width, double x, double y, long *i, long *j) {
iy = lround(ry);
rz = floor(z + 0.5);
iz = lround(rz);
+ if( fabs(rx + ry + rz) > std::numeric_limits<int>::max() ) {
+ throw "Integer overflow";
+ }
s = ix + iy + iz;
@@ -764,11 +772,18 @@ static int isea_dddi(struct isea_dgg *g, int quad, struct isea_pt *pt,
}
/* todo might want to do this as an iterated loop */
if (g->aperture >0) {
- sidelength = lround(pow(g->aperture, g->resolution / 2.0));
+ double sidelengthDouble = pow(g->aperture, g->resolution / 2.0);
+ if( fabs(sidelengthDouble) > std::numeric_limits<int>::max() ) {
+ throw "Integer overflow";
+ }
+ sidelength = lround(sidelengthDouble);
} else {
sidelength = g->resolution;
}
+ if( sidelength == 0 ) {
+ throw "Division by zero";
+ }
hexwidth = 1.0 / sidelength;
v = *pt;
@@ -1004,7 +1019,12 @@ static PJ_XY s_forward (PJ_LP lp, PJ *P) { /* Spheroidal, forward */
in.lon = lp.lam;
in.lat = lp.phi;
- out = isea_forward(&Q->dgg, &in);
+ try {
+ out = isea_forward(&Q->dgg, &in);
+ } catch( const char* ) {
+ proj_errno_set(P, PJD_ERR_NON_CONVERGENT);
+ return proj_coord_error().xy;
+ }
xy.x = out.x;
xy.y = out.y;