summaryrefslogtreecommitdiff
path: root/sql
diff options
context:
space:
mode:
authorAlexey Botchkov <holyfoot@askmonty.org>2013-03-26 21:47:06 +0400
committerAlexey Botchkov <holyfoot@askmonty.org>2013-03-26 21:47:06 +0400
commit045c498691f77ac8e0d8c8b9b705325b3425c69d (patch)
treed1e64ca715c07e5cf1d93afb7de6e37858f7a03f /sql
parent51a707486433d3707ac38deb72c6ad7d3d7bb882 (diff)
downloadmariadb-git-045c498691f77ac8e0d8c8b9b705325b3425c69d.tar.gz
GEOMETRYCOLLECTION EMPTY handling fixed.
The get_mbr() method shouldn't return the error, rather an invalid MBR in this case.
Diffstat (limited to 'sql')
-rw-r--r--sql/item_geofunc.cc12
-rw-r--r--sql/spatial.cc19
-rw-r--r--sql/spatial.h3
3 files changed, 23 insertions, 11 deletions
diff --git a/sql/item_geofunc.cc b/sql/item_geofunc.cc
index 7d0f06d6237..1168813e275 100644
--- a/sql/item_geofunc.cc
+++ b/sql/item_geofunc.cc
@@ -559,8 +559,8 @@ longlong Item_func_spatial_mbr_rel::val_int()
args[1]->null_value ||
!(g1= Geometry::construct(&buffer1, res1->ptr(), res1->length())) ||
!(g2= Geometry::construct(&buffer2, res2->ptr(), res2->length())) ||
- g1->get_mbr(&mbr1, &dummy) ||
- g2->get_mbr(&mbr2, &dummy))))
+ g1->get_mbr(&mbr1, &dummy) || !mbr1.valid() ||
+ g2->get_mbr(&mbr2, &dummy) || !mbr2.valid())))
return 0;
switch (spatial_rel) {
@@ -686,8 +686,8 @@ longlong Item_func_spatial_rel::val_int()
(args[0]->null_value || args[1]->null_value ||
!(g1= Geometry::construct(&buffer1, res1->ptr(), res1->length())) ||
!(g2= Geometry::construct(&buffer2, res2->ptr(), res2->length())) ||
- g1->get_mbr(&mbr1, &c_end) ||
- g2->get_mbr(&mbr2, &c_end))))
+ g1->get_mbr(&mbr1, &c_end) || !mbr1.valid() ||
+ g2->get_mbr(&mbr2, &c_end) || !mbr2.valid())))
goto exit;
umbr= mbr1;
@@ -824,8 +824,8 @@ String *Item_func_spatial_operation::val_str(String *str_value)
(args[0]->null_value || args[1]->null_value ||
!(g1= Geometry::construct(&buffer1, res1->ptr(), res1->length())) ||
!(g2= Geometry::construct(&buffer2, res2->ptr(), res2->length())) ||
- g1->get_mbr(&mbr1, &c_end) ||
- g2->get_mbr(&mbr2, &c_end))))
+ g1->get_mbr(&mbr1, &c_end) || !mbr1.valid() ||
+ g2->get_mbr(&mbr2, &c_end) || !mbr2.valid())))
{
str_value= 0;
goto exit;
diff --git a/sql/spatial.cc b/sql/spatial.cc
index 0da2fdf40b3..cec6150c22a 100644
--- a/sql/spatial.cc
+++ b/sql/spatial.cc
@@ -308,6 +308,9 @@ bool Geometry::envelope(String *result) const
const char *end;
if (get_mbr(&mbr, &end))
+ return 1;
+
+ if (!mbr.valid())
{
/* Empty geometry */
if (result->reserve(1 + 4*2))
@@ -2322,7 +2325,7 @@ bool Gis_geometry_collection::get_mbr(MBR *mbr, const char **end) const
n_objects= uint4korr(data);
data+= 4;
if (n_objects == 0)
- return 1;
+ goto exit;
while (n_objects--)
{
@@ -2339,6 +2342,7 @@ bool Gis_geometry_collection::get_mbr(MBR *mbr, const char **end) const
if (geom->get_mbr(mbr, &data))
return 1;
}
+exit:
*end= data;
return 0;
}
@@ -2356,10 +2360,11 @@ int Gis_geometry_collection::area(double *ar, const char **end) const
return 1;
n_objects= uint4korr(data);
data+= 4;
- if (n_objects == 0)
- return 1;
result= 0.0;
+ if (n_objects == 0)
+ goto exit;
+
while (n_objects--)
{
uint32 wkb_type;
@@ -2376,6 +2381,7 @@ int Gis_geometry_collection::area(double *ar, const char **end) const
return 1;
result+= *ar;
}
+exit:
*end= data;
*ar= result;
return 0;
@@ -2394,10 +2400,11 @@ int Gis_geometry_collection::geom_length(double *len, const char **end) const
return 1;
n_objects= uint4korr(data);
data+= 4;
+ result= 0.0;
+
if (n_objects == 0)
- return 1;
+ goto exit;
- result= 0.0;
while (n_objects--)
{
uint32 wkb_type;
@@ -2414,6 +2421,8 @@ int Gis_geometry_collection::geom_length(double *len, const char **end) const
return 1;
result+= *len;
}
+
+exit:
*end= data;
*len= result;
return 0;
diff --git a/sql/spatial.h b/sql/spatial.h
index 6850cc804d0..1108f5d5e50 100644
--- a/sql/spatial.h
+++ b/sql/spatial.h
@@ -199,6 +199,9 @@ struct MBR
return (d == intersection.dimension());
}
+
+ int valid() const
+ { return xmin <= xmax && ymin <= ymax; }
};