Commit ba7c0196 authored by unknown's avatar unknown

Bug #29070: Error in spatial index

1. Threat MBR for a key as double[] and convert it only
when about to store it on disk.
2. Remove the redundant function get_double().


myisam/sp_key.c:
  Bug #29070: 
  1. threat MBR for a key as double[] and convert it only
  when about to store it on disk.
  2. remove the redundant function get_double()
mysql-test/r/gis-rtree.result:
  Bug #29070: test case
mysql-test/t/gis-rtree.test:
  Bug #29070: test case
parent b94c9fa8
......@@ -31,11 +31,6 @@ static int sp_get_geometry_mbr(uchar *(*wkb), uchar *end, uint n_dims,
double *mbr, int top);
static int sp_mbr_from_wkb(uchar (*wkb), uint size, uint n_dims, double *mbr);
static void get_double(double *d, const byte *pos)
{
float8get(*d, pos);
}
uint sp_make_key(register MI_INFO *info, uint keynr, uchar *key,
const byte *record, my_off_t filepos)
{
......@@ -62,48 +57,40 @@ uint sp_make_key(register MI_INFO *info, uint keynr, uchar *key,
for (i = 0, keyseg = keyinfo->seg; keyseg->type; keyseg++, i++)
{
uint length = keyseg->length;
uint length = keyseg->length, start= keyseg->start;
double val;
DBUG_ASSERT(length == sizeof(double));
DBUG_ASSERT(!(start % sizeof(double)));
DBUG_ASSERT(start < sizeof(mbr));
DBUG_ASSERT(keyseg->type == HA_KEYTYPE_DOUBLE);
pos = ((byte*)mbr) + keyseg->start;
if (keyseg->flag & HA_SWAP_KEY)
{
val= mbr[start / sizeof (double)];
#ifdef HAVE_ISNAN
if (keyseg->type == HA_KEYTYPE_FLOAT)
{
float nr;
float4get(nr, pos);
if (isnan(nr))
{
/* Replace NAN with zero */
bzero(key, length);
key+= length;
continue;
}
}
else if (keyseg->type == HA_KEYTYPE_DOUBLE)
{
double nr;
get_double(&nr, pos);
if (isnan(nr))
{
bzero(key, length);
key+= length;
continue;
}
}
if (isnan(val))
{
bzero(key, length);
key+= length;
len+= length;
continue;
}
#endif
pos += length;
while (length--)
{
if (keyseg->flag & HA_SWAP_KEY)
{
char buf[sizeof(double)];
float8store(buf, val);
pos= &buf[length];
while (pos > buf)
*key++ = *--pos;
}
}
else
{
memcpy((byte*)key, pos, length);
key += keyseg->length;
float8store((byte *)key, val);
key += length;
}
len += keyseg->length;
len+= length;
}
_mi_dpointer(info, key, filepos);
return len;
......@@ -141,13 +128,13 @@ static int sp_add_point_to_mbr(uchar *(*wkb), uchar *end, uint n_dims,
{
if ((*wkb) > end - 8)
return -1;
get_double(&ord, (const byte*) *wkb);
float8get(ord, (const byte*) *wkb);
(*wkb)+= 8;
if (ord < *mbr)
float8store((char*) mbr, ord);
*mbr= ord;
mbr++;
if (ord > *mbr)
float8store((char*) mbr, ord);
*mbr= ord;
mbr++;
}
return 0;
......
......@@ -1444,3 +1444,16 @@ OPTIMIZE TABLE t1;
Table Op Msg_type Msg_text
test.t1 optimize status OK
DROP TABLE t1;
CREATE TABLE t1 (a INT, b GEOMETRY NOT NULL, SPATIAL KEY b(b));
INSERT INTO t1 VALUES (1, GEOMFROMTEXT('LINESTRING(1102218.456 1,2000000 2)'));
INSERT INTO t1 VALUES (2, GEOMFROMTEXT('LINESTRING(1102218.456 1,2000000 2)'));
SELECT COUNT(*) FROM t1 WHERE
MBRINTERSECTS(b, GEOMFROMTEXT('LINESTRING(1 1,1102219 2)') );
COUNT(*)
2
SELECT COUNT(*) FROM t1 IGNORE INDEX (b) WHERE
MBRINTERSECTS(b, GEOMFROMTEXT('LINESTRING(1 1,1102219 2)') );
COUNT(*)
2
DROP TABLE t1;
End of 5.0 tests.
......@@ -827,3 +827,22 @@ INSERT INTO t1 (b) SELECT b FROM t1;
OPTIMIZE TABLE t1;
DROP TABLE t1;
#
# Bug #29070: Error in spatial index
#
CREATE TABLE t1 (a INT, b GEOMETRY NOT NULL, SPATIAL KEY b(b));
INSERT INTO t1 VALUES (1, GEOMFROMTEXT('LINESTRING(1102218.456 1,2000000 2)'));
INSERT INTO t1 VALUES (2, GEOMFROMTEXT('LINESTRING(1102218.456 1,2000000 2)'));
# must return the same number as the next select
SELECT COUNT(*) FROM t1 WHERE
MBRINTERSECTS(b, GEOMFROMTEXT('LINESTRING(1 1,1102219 2)') );
SELECT COUNT(*) FROM t1 IGNORE INDEX (b) WHERE
MBRINTERSECTS(b, GEOMFROMTEXT('LINESTRING(1 1,1102219 2)') );
DROP TABLE t1;
--echo End of 5.0 tests.
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment