5.2 merge
This commit is contained in:
commit
e308d7417b
@ -184,7 +184,20 @@ SELECT member_id_to, COUNT(*) FROM t1 WHERE r_date =
|
|||||||
member_id_to COUNT(*)
|
member_id_to COUNT(*)
|
||||||
518491 5
|
518491 5
|
||||||
DROP TABLE t1;
|
DROP TABLE t1;
|
||||||
# End of test BUG#12713907
|
#
|
||||||
|
# MDEV-4269: crash when grouping by values()
|
||||||
|
#
|
||||||
|
SELECT @@storage_engine INTO @old_engine;
|
||||||
|
set storage_engine=innodb;
|
||||||
|
create table y select 1 b;
|
||||||
|
select 1 from y group by b;
|
||||||
|
1
|
||||||
|
1
|
||||||
|
select 1 from y group by values(b);
|
||||||
|
1
|
||||||
|
1
|
||||||
|
drop table y;
|
||||||
|
SET storage_engine=@old_engine;
|
||||||
#
|
#
|
||||||
# Bug#13723054 CRASH WITH MIN/MAX AFTER QUICK_GROUP_MIN_MAX_SELECT::NEXT_MIN
|
# Bug#13723054 CRASH WITH MIN/MAX AFTER QUICK_GROUP_MIN_MAX_SELECT::NEXT_MIN
|
||||||
#
|
#
|
||||||
|
@ -2649,4 +2649,11 @@ NULL
|
|||||||
SELECT LPAD('hi', DAY(FROM_UNIXTIME(-1)),'?');
|
SELECT LPAD('hi', DAY(FROM_UNIXTIME(-1)),'?');
|
||||||
LPAD('hi', DAY(FROM_UNIXTIME(-1)),'?')
|
LPAD('hi', DAY(FROM_UNIXTIME(-1)),'?')
|
||||||
NULL
|
NULL
|
||||||
|
create table t1 (i int);
|
||||||
|
insert into t1 values (null),(8);
|
||||||
|
select group_concat( i ), make_set( i, 'a', 'b' ) field from t1 group by field;
|
||||||
|
group_concat( i ) field
|
||||||
|
NULL NULL
|
||||||
|
8
|
||||||
|
drop table t1;
|
||||||
End of 5.1 tests
|
End of 5.1 tests
|
||||||
|
@ -1108,6 +1108,33 @@ NULL
|
|||||||
#
|
#
|
||||||
SELECT GEOMETRYCOLLECTION((SELECT @@OLD));
|
SELECT GEOMETRYCOLLECTION((SELECT @@OLD));
|
||||||
ERROR 22007: Illegal non geometric '' value found during parsing
|
ERROR 22007: Illegal non geometric '' value found during parsing
|
||||||
|
#
|
||||||
|
# MDEV-4252 geometry query crashes server
|
||||||
|
#
|
||||||
|
select astext(0x0100000000030000000100000000000010);
|
||||||
|
astext(0x0100000000030000000100000000000010)
|
||||||
|
NULL
|
||||||
|
select envelope(0x0100000000030000000100000000000010);
|
||||||
|
envelope(0x0100000000030000000100000000000010)
|
||||||
|
NULL
|
||||||
|
select geometryn(0x0100000000070000000100000001030000000200000000000000ffff0000, 1);
|
||||||
|
geometryn(0x0100000000070000000100000001030000000200000000000000ffff0000, 1)
|
||||||
|
NULL
|
||||||
|
select geometryn(0x0100000000070000000100000001030000000200000000000000ffffff0f, 1);
|
||||||
|
geometryn(0x0100000000070000000100000001030000000200000000000000ffffff0f, 1)
|
||||||
|
NULL
|
||||||
|
#
|
||||||
|
# MDEV-4296 Assertion `n_linear_rings > 0' fails in Gis_polygon::centroid_xy
|
||||||
|
#
|
||||||
|
SELECT Centroid( AsBinary( LineString(Point(0,0), Point(0,0), Point(0,0) )));
|
||||||
|
Centroid( AsBinary( LineString(Point(0,0), Point(0,0), Point(0,0) )))
|
||||||
|
NULL
|
||||||
|
#
|
||||||
|
# MDEV-4295 Server crashes in get_point on a query with Area, AsBinary, MultiPoint
|
||||||
|
#
|
||||||
|
SELECT Area(AsBinary(MultiPoint(Point(0,9), Point(0,1), Point(2,2))));
|
||||||
|
Area(AsBinary(MultiPoint(Point(0,9), Point(0,1), Point(2,2))))
|
||||||
|
NULL
|
||||||
End of 5.1 tests
|
End of 5.1 tests
|
||||||
select ST_AREA(ST_GEOMCOLLFROMTEXT(' GEOMETRYCOLLECTION(LINESTRING(100 100, 31 10, 77 80), POLYGON((0 0,4 7,1 1,0 0)), POINT(20 20))'));
|
select ST_AREA(ST_GEOMCOLLFROMTEXT(' GEOMETRYCOLLECTION(LINESTRING(100 100, 31 10, 77 80), POLYGON((0 0,4 7,1 1,0 0)), POINT(20 20))'));
|
||||||
ST_AREA(ST_GEOMCOLLFROMTEXT(' GEOMETRYCOLLECTION(LINESTRING(100 100, 31 10, 77 80), POLYGON((0 0,4 7,1 1,0 0)), POINT(20 20))'))
|
ST_AREA(ST_GEOMCOLLFROMTEXT(' GEOMETRYCOLLECTION(LINESTRING(100 100, 31 10, 77 80), POLYGON((0 0,4 7,1 1,0 0)), POINT(20 20))'))
|
||||||
|
@ -126,7 +126,20 @@ SELECT member_id_to, COUNT(*) FROM t1 WHERE r_date =
|
|||||||
|
|
||||||
DROP TABLE t1;
|
DROP TABLE t1;
|
||||||
|
|
||||||
--echo # End of test BUG#12713907
|
--echo #
|
||||||
|
--echo # MDEV-4269: crash when grouping by values()
|
||||||
|
--echo #
|
||||||
|
|
||||||
|
SELECT @@storage_engine INTO @old_engine;
|
||||||
|
set storage_engine=innodb;
|
||||||
|
|
||||||
|
create table y select 1 b;
|
||||||
|
select 1 from y group by b;
|
||||||
|
select 1 from y group by values(b);
|
||||||
|
drop table y;
|
||||||
|
SET storage_engine=@old_engine;
|
||||||
|
|
||||||
|
### End of 5.1 tests
|
||||||
|
|
||||||
--echo #
|
--echo #
|
||||||
--echo # Bug#13723054 CRASH WITH MIN/MAX AFTER QUICK_GROUP_MIN_MAX_SELECT::NEXT_MIN
|
--echo # Bug#13723054 CRASH WITH MIN/MAX AFTER QUICK_GROUP_MIN_MAX_SELECT::NEXT_MIN
|
||||||
@ -140,3 +153,6 @@ SELECT MIN(c) FROM t1 GROUP BY b;
|
|||||||
EXPLAIN SELECT MIN(c) FROM t1 GROUP BY b;
|
EXPLAIN SELECT MIN(c) FROM t1 GROUP BY b;
|
||||||
|
|
||||||
DROP TABLE t1;
|
DROP TABLE t1;
|
||||||
|
|
||||||
|
### End of 5.2 tests
|
||||||
|
|
||||||
|
@ -1394,5 +1394,12 @@ SELECT REPEAT('1', DAY(FROM_UNIXTIME(-1)));
|
|||||||
SELECT RPAD('hi', DAY(FROM_UNIXTIME(-1)),'?');
|
SELECT RPAD('hi', DAY(FROM_UNIXTIME(-1)),'?');
|
||||||
SELECT LPAD('hi', DAY(FROM_UNIXTIME(-1)),'?');
|
SELECT LPAD('hi', DAY(FROM_UNIXTIME(-1)),'?');
|
||||||
|
|
||||||
|
#
|
||||||
|
# MDEV-4289 Assertion `0' fails in make_sortkey with GROUP_CONCAT, MAKE_SET, GROUP BY
|
||||||
|
#
|
||||||
|
create table t1 (i int);
|
||||||
|
insert into t1 values (null),(8);
|
||||||
|
select group_concat( i ), make_set( i, 'a', 'b' ) field from t1 group by field;
|
||||||
|
drop table t1;
|
||||||
|
|
||||||
--echo End of 5.1 tests
|
--echo End of 5.1 tests
|
||||||
|
@ -820,7 +820,24 @@ SELECT ISCLOSED(CONVERT(CONCAT(' ', 0x2), BINARY(20)));
|
|||||||
--error ER_ILLEGAL_VALUE_FOR_TYPE
|
--error ER_ILLEGAL_VALUE_FOR_TYPE
|
||||||
SELECT GEOMETRYCOLLECTION((SELECT @@OLD));
|
SELECT GEOMETRYCOLLECTION((SELECT @@OLD));
|
||||||
|
|
||||||
|
--echo #
|
||||||
|
--echo # MDEV-4252 geometry query crashes server
|
||||||
|
--echo #
|
||||||
|
select astext(0x0100000000030000000100000000000010);
|
||||||
|
select envelope(0x0100000000030000000100000000000010);
|
||||||
|
select geometryn(0x0100000000070000000100000001030000000200000000000000ffff0000, 1);
|
||||||
|
select geometryn(0x0100000000070000000100000001030000000200000000000000ffffff0f, 1);
|
||||||
|
|
||||||
|
--echo #
|
||||||
|
--echo # MDEV-4296 Assertion `n_linear_rings > 0' fails in Gis_polygon::centroid_xy
|
||||||
|
--echo #
|
||||||
|
|
||||||
|
SELECT Centroid( AsBinary( LineString(Point(0,0), Point(0,0), Point(0,0) )));
|
||||||
|
|
||||||
|
--echo #
|
||||||
|
--echo # MDEV-4295 Server crashes in get_point on a query with Area, AsBinary, MultiPoint
|
||||||
|
--echo #
|
||||||
|
SELECT Area(AsBinary(MultiPoint(Point(0,9), Point(0,1), Point(2,2))));
|
||||||
--echo End of 5.1 tests
|
--echo End of 5.1 tests
|
||||||
|
|
||||||
#bug 850775 ST_AREA does not work on GEOMETRYCOLLECTIONs in maria-5.3-gis
|
#bug 850775 ST_AREA does not work on GEOMETRYCOLLECTIONs in maria-5.3-gis
|
||||||
|
@ -4269,8 +4269,7 @@ Create_func_make_set::create_native(THD *thd, LEX_STRING name,
|
|||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
Item *param_1= item_list->pop();
|
return new (thd->mem_root) Item_func_make_set(*item_list);
|
||||||
return new (thd->mem_root) Item_func_make_set(param_1, *item_list);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@ -2233,38 +2233,14 @@ String *Item_func_elt::val_str(String *str)
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
void Item_func_make_set::split_sum_func(THD *thd, Item **ref_pointer_array,
|
|
||||||
List<Item> &fields)
|
|
||||||
{
|
|
||||||
item->split_sum_func2(thd, ref_pointer_array, fields, &item, TRUE);
|
|
||||||
Item_str_func::split_sum_func(thd, ref_pointer_array, fields);
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
void Item_func_make_set::fix_length_and_dec()
|
void Item_func_make_set::fix_length_and_dec()
|
||||||
{
|
{
|
||||||
max_length=arg_count-1;
|
if (agg_arg_charsets(collation, args+1, arg_count-1, MY_COLL_ALLOW_CONV, 1))
|
||||||
|
|
||||||
if (agg_arg_charsets(collation, args, arg_count, MY_COLL_ALLOW_CONV, 1))
|
|
||||||
return;
|
return;
|
||||||
|
|
||||||
for (uint i=0 ; i < arg_count ; i++)
|
max_length=arg_count-2;
|
||||||
|
for (uint i=1 ; i < arg_count ; i++)
|
||||||
max_length+=args[i]->max_length;
|
max_length+=args[i]->max_length;
|
||||||
|
|
||||||
used_tables_cache|= item->used_tables();
|
|
||||||
not_null_tables_cache&= item->not_null_tables();
|
|
||||||
const_item_cache&= item->const_item();
|
|
||||||
with_sum_func= with_sum_func || item->with_sum_func;
|
|
||||||
with_field= with_field || item->with_field;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
void Item_func_make_set::update_used_tables()
|
|
||||||
{
|
|
||||||
Item_func::update_used_tables();
|
|
||||||
item->update_used_tables();
|
|
||||||
used_tables_cache|=item->used_tables();
|
|
||||||
const_item_cache&=item->const_item();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@ -2273,15 +2249,15 @@ String *Item_func_make_set::val_str(String *str)
|
|||||||
DBUG_ASSERT(fixed == 1);
|
DBUG_ASSERT(fixed == 1);
|
||||||
ulonglong bits;
|
ulonglong bits;
|
||||||
bool first_found=0;
|
bool first_found=0;
|
||||||
Item **ptr=args;
|
Item **ptr=args+1;
|
||||||
String *result=&my_empty_string;
|
String *result=&my_empty_string;
|
||||||
|
|
||||||
bits=item->val_int();
|
bits=args[0]->val_int();
|
||||||
if ((null_value=item->null_value))
|
if ((null_value=args[0]->null_value))
|
||||||
return NULL;
|
return NULL;
|
||||||
|
|
||||||
if (arg_count < 64)
|
if (arg_count < 65)
|
||||||
bits &= ((ulonglong) 1 << arg_count)-1;
|
bits &= ((ulonglong) 1 << (arg_count-1))-1;
|
||||||
|
|
||||||
for (; bits; bits >>= 1, ptr++)
|
for (; bits; bits >>= 1, ptr++)
|
||||||
{
|
{
|
||||||
@ -2321,39 +2297,6 @@ String *Item_func_make_set::val_str(String *str)
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
Item *Item_func_make_set::transform(Item_transformer transformer, uchar *arg)
|
|
||||||
{
|
|
||||||
DBUG_ASSERT(!current_thd->is_stmt_prepare());
|
|
||||||
|
|
||||||
Item *new_item= item->transform(transformer, arg);
|
|
||||||
if (!new_item)
|
|
||||||
return 0;
|
|
||||||
|
|
||||||
/*
|
|
||||||
THD::change_item_tree() should be called only if the tree was
|
|
||||||
really transformed, i.e. when a new item has been created.
|
|
||||||
Otherwise we'll be allocating a lot of unnecessary memory for
|
|
||||||
change records at each execution.
|
|
||||||
*/
|
|
||||||
if (item != new_item)
|
|
||||||
current_thd->change_item_tree(&item, new_item);
|
|
||||||
return Item_str_func::transform(transformer, arg);
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
void Item_func_make_set::print(String *str, enum_query_type query_type)
|
|
||||||
{
|
|
||||||
str->append(STRING_WITH_LEN("make_set("));
|
|
||||||
item->print(str, query_type);
|
|
||||||
if (arg_count)
|
|
||||||
{
|
|
||||||
str->append(',');
|
|
||||||
print_args(str, 0, query_type);
|
|
||||||
}
|
|
||||||
str->append(')');
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
String *Item_func_char::val_str(String *str)
|
String *Item_func_char::val_str(String *str)
|
||||||
{
|
{
|
||||||
DBUG_ASSERT(fixed == 1);
|
DBUG_ASSERT(fixed == 1);
|
||||||
|
@ -506,31 +506,13 @@ public:
|
|||||||
|
|
||||||
class Item_func_make_set :public Item_str_func
|
class Item_func_make_set :public Item_str_func
|
||||||
{
|
{
|
||||||
Item *item;
|
|
||||||
String tmp_str;
|
String tmp_str;
|
||||||
|
|
||||||
public:
|
public:
|
||||||
Item_func_make_set(Item *a,List<Item> &list) :Item_str_func(list),item(a) {}
|
Item_func_make_set(List<Item> &list) :Item_str_func(list) {}
|
||||||
String *val_str(String *str);
|
String *val_str(String *str);
|
||||||
bool fix_fields(THD *thd, Item **ref)
|
|
||||||
{
|
|
||||||
DBUG_ASSERT(fixed == 0);
|
|
||||||
return ((!item->fixed && item->fix_fields(thd, &item)) ||
|
|
||||||
item->check_cols(1) ||
|
|
||||||
Item_func::fix_fields(thd, ref));
|
|
||||||
}
|
|
||||||
void split_sum_func(THD *thd, Item **ref_pointer_array, List<Item> &fields);
|
|
||||||
void fix_length_and_dec();
|
void fix_length_and_dec();
|
||||||
void update_used_tables();
|
|
||||||
const char *func_name() const { return "make_set"; }
|
const char *func_name() const { return "make_set"; }
|
||||||
|
|
||||||
bool walk(Item_processor processor, bool walk_subquery, uchar *arg)
|
|
||||||
{
|
|
||||||
return item->walk(processor, walk_subquery, arg) ||
|
|
||||||
Item_str_func::walk(processor, walk_subquery, arg);
|
|
||||||
}
|
|
||||||
Item *transform(Item_transformer transformer, uchar *arg);
|
|
||||||
virtual void print(String *str, enum_query_type query_type);
|
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
|
@ -443,18 +443,19 @@ const char *Geometry::append_points(String *txt, uint32 n_points,
|
|||||||
const char *Geometry::get_mbr_for_points(MBR *mbr, const char *data,
|
const char *Geometry::get_mbr_for_points(MBR *mbr, const char *data,
|
||||||
uint offset) const
|
uint offset) const
|
||||||
{
|
{
|
||||||
uint32 points;
|
uint32 n_points;
|
||||||
/* read number of points */
|
/* read number of points */
|
||||||
if (no_data(data, 4))
|
if (no_data(data, 4))
|
||||||
return 0;
|
return 0;
|
||||||
points= uint4korr(data);
|
n_points= uint4korr(data);
|
||||||
data+= 4;
|
data+= 4;
|
||||||
|
|
||||||
if (no_data(data, (POINT_DATA_SIZE + offset) * points))
|
if (n_points > max_n_points ||
|
||||||
|
no_data(data, (POINT_DATA_SIZE + offset) * n_points))
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
/* Calculate MBR for points */
|
/* Calculate MBR for points */
|
||||||
while (points--)
|
while (n_points--)
|
||||||
{
|
{
|
||||||
data+= offset;
|
data+= offset;
|
||||||
mbr->add_xy(data, data + SIZEOF_STORED_DOUBLE);
|
mbr->add_xy(data, data + SIZEOF_STORED_DOUBLE);
|
||||||
@ -558,9 +559,12 @@ const Geometry::Class_info *Gis_point::get_class_info() const
|
|||||||
|
|
||||||
uint32 Gis_line_string::get_data_size() const
|
uint32 Gis_line_string::get_data_size() const
|
||||||
{
|
{
|
||||||
if (no_data(m_data, 4))
|
uint32 n_points, size;
|
||||||
|
if (no_data(m_data, 4) ||
|
||||||
|
(n_points= uint4korr(m_data)) > max_n_points ||
|
||||||
|
no_data(m_data, (size= 4 + n_points * POINT_DATA_SIZE)))
|
||||||
return GET_SIZE_ERROR;
|
return GET_SIZE_ERROR;
|
||||||
return 4 + uint4korr(m_data) * POINT_DATA_SIZE;
|
return size;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@ -668,7 +672,8 @@ int Gis_line_string::geom_length(double *len, const char **end) const
|
|||||||
return 1;
|
return 1;
|
||||||
n_points= uint4korr(data);
|
n_points= uint4korr(data);
|
||||||
data+= 4;
|
data+= 4;
|
||||||
if (n_points < 1 || no_data(data, POINT_DATA_SIZE * n_points))
|
if (n_points < 1 || n_points > max_n_points ||
|
||||||
|
no_data(data, POINT_DATA_SIZE * n_points))
|
||||||
return 1;
|
return 1;
|
||||||
|
|
||||||
get_point(&prev_x, &prev_y, data);
|
get_point(&prev_x, &prev_y, data);
|
||||||
@ -716,7 +721,7 @@ int Gis_line_string::is_closed(int *closed) const
|
|||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
data+= 4;
|
data+= 4;
|
||||||
if (n_points == 0 ||
|
if (n_points == 0 || n_points > max_n_points ||
|
||||||
no_data(data, POINT_DATA_SIZE * n_points))
|
no_data(data, POINT_DATA_SIZE * n_points))
|
||||||
return 1;
|
return 1;
|
||||||
|
|
||||||
@ -752,6 +757,9 @@ int Gis_line_string::end_point(String *result) const
|
|||||||
if (no_data(m_data, 4))
|
if (no_data(m_data, 4))
|
||||||
return 1;
|
return 1;
|
||||||
n_points= uint4korr(m_data);
|
n_points= uint4korr(m_data);
|
||||||
|
if (n_points == 0 || n_points > max_n_points ||
|
||||||
|
no_data(m_data, POINT_DATA_SIZE * n_points))
|
||||||
|
return 1;
|
||||||
return create_point(result, m_data + 4 + (n_points - 1) * POINT_DATA_SIZE);
|
return create_point(result, m_data + 4 + (n_points - 1) * POINT_DATA_SIZE);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -761,11 +769,14 @@ int Gis_line_string::point_n(uint32 num, String *result) const
|
|||||||
uint32 n_points;
|
uint32 n_points;
|
||||||
if (no_data(m_data, 4))
|
if (no_data(m_data, 4))
|
||||||
return 1;
|
return 1;
|
||||||
|
num--;
|
||||||
n_points= uint4korr(m_data);
|
n_points= uint4korr(m_data);
|
||||||
if ((uint32) (num - 1) >= n_points) // means (num > n_points || num < 1)
|
if (num >= n_points ||
|
||||||
|
num > max_n_points || // means (num > n_points || num < 1)
|
||||||
|
no_data(m_data, num * POINT_DATA_SIZE))
|
||||||
return 1;
|
return 1;
|
||||||
|
|
||||||
return create_point(result, m_data + 4 + (num - 1) * POINT_DATA_SIZE);
|
return create_point(result, m_data + 4 + num*POINT_DATA_SIZE);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@ -815,6 +826,7 @@ const Geometry::Class_info *Gis_line_string::get_class_info() const
|
|||||||
uint32 Gis_polygon::get_data_size() const
|
uint32 Gis_polygon::get_data_size() const
|
||||||
{
|
{
|
||||||
uint32 n_linear_rings;
|
uint32 n_linear_rings;
|
||||||
|
uint32 n_points;
|
||||||
const char *data= m_data;
|
const char *data= m_data;
|
||||||
|
|
||||||
if (no_data(data, 4))
|
if (no_data(data, 4))
|
||||||
@ -824,10 +836,13 @@ uint32 Gis_polygon::get_data_size() const
|
|||||||
|
|
||||||
while (n_linear_rings--)
|
while (n_linear_rings--)
|
||||||
{
|
{
|
||||||
if (no_data(data, 4))
|
if (no_data(data, 4) ||
|
||||||
|
(n_points= uint4korr(data)) > max_n_points)
|
||||||
return GET_SIZE_ERROR;
|
return GET_SIZE_ERROR;
|
||||||
data+= 4 + uint4korr(data)*POINT_DATA_SIZE;
|
data+= 4 + n_points*POINT_DATA_SIZE;
|
||||||
}
|
}
|
||||||
|
if (no_data(data, 0))
|
||||||
|
return GET_SIZE_ERROR;
|
||||||
return (uint32) (data - m_data);
|
return (uint32) (data - m_data);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -966,7 +981,8 @@ bool Gis_polygon::get_data_as_wkt(String *txt, const char **end) const
|
|||||||
return 1;
|
return 1;
|
||||||
n_points= uint4korr(data);
|
n_points= uint4korr(data);
|
||||||
data+= 4;
|
data+= 4;
|
||||||
if (no_data(data, POINT_DATA_SIZE * n_points) ||
|
if (n_points > max_n_points ||
|
||||||
|
no_data(data, POINT_DATA_SIZE * n_points) ||
|
||||||
txt->reserve(2 + ((MAX_DIGITS_IN_DOUBLE + 1) * 2 + 1) * n_points))
|
txt->reserve(2 + ((MAX_DIGITS_IN_DOUBLE + 1) * 2 + 1) * n_points))
|
||||||
return 1;
|
return 1;
|
||||||
txt->qs_append('(');
|
txt->qs_append('(');
|
||||||
@ -1020,7 +1036,8 @@ int Gis_polygon::area(double *ar, const char **end_of_data) const
|
|||||||
if (no_data(data, 4))
|
if (no_data(data, 4))
|
||||||
return 1;
|
return 1;
|
||||||
n_points= uint4korr(data);
|
n_points= uint4korr(data);
|
||||||
if (no_data(data, POINT_DATA_SIZE * n_points))
|
if (n_points == 0 || n_points > max_n_points ||
|
||||||
|
no_data(data, POINT_DATA_SIZE * n_points))
|
||||||
return 1;
|
return 1;
|
||||||
get_point(&prev_x, &prev_y, data+4);
|
get_point(&prev_x, &prev_y, data+4);
|
||||||
data+= (4+POINT_DATA_SIZE);
|
data+= (4+POINT_DATA_SIZE);
|
||||||
@ -1056,7 +1073,8 @@ int Gis_polygon::exterior_ring(String *result) const
|
|||||||
n_points= uint4korr(data);
|
n_points= uint4korr(data);
|
||||||
data+= 4;
|
data+= 4;
|
||||||
length= n_points * POINT_DATA_SIZE;
|
length= n_points * POINT_DATA_SIZE;
|
||||||
if (no_data(data, length) || result->reserve(1 + 4 + 4 + length))
|
if (n_points > max_n_points ||
|
||||||
|
no_data(data, length) || result->reserve(1+4+4+ length))
|
||||||
return 1;
|
return 1;
|
||||||
|
|
||||||
result->q_append((char) wkb_ndr);
|
result->q_append((char) wkb_ndr);
|
||||||
@ -1122,13 +1140,11 @@ int Gis_polygon::centroid_xy(double *x, double *y) const
|
|||||||
const char *data= m_data;
|
const char *data= m_data;
|
||||||
bool first_loop= 1;
|
bool first_loop= 1;
|
||||||
|
|
||||||
if (no_data(data, 4))
|
if (no_data(data, 4) ||
|
||||||
|
(n_linear_rings= uint4korr(data)) == 0)
|
||||||
return 1;
|
return 1;
|
||||||
n_linear_rings= uint4korr(data);
|
|
||||||
data+= 4;
|
data+= 4;
|
||||||
|
|
||||||
DBUG_ASSERT(n_linear_rings > 0);
|
|
||||||
|
|
||||||
while (n_linear_rings--)
|
while (n_linear_rings--)
|
||||||
{
|
{
|
||||||
uint32 n_points, org_n_points;
|
uint32 n_points, org_n_points;
|
||||||
@ -1141,7 +1157,8 @@ int Gis_polygon::centroid_xy(double *x, double *y) const
|
|||||||
return 1;
|
return 1;
|
||||||
org_n_points= n_points= uint4korr(data);
|
org_n_points= n_points= uint4korr(data);
|
||||||
data+= 4;
|
data+= 4;
|
||||||
if (no_data(data, POINT_DATA_SIZE * n_points))
|
if (n_points == 0 || n_points > max_n_points ||
|
||||||
|
no_data(data, POINT_DATA_SIZE * n_points))
|
||||||
return 1;
|
return 1;
|
||||||
get_point(&prev_x, &prev_y, data);
|
get_point(&prev_x, &prev_y, data);
|
||||||
data+= POINT_DATA_SIZE;
|
data+= POINT_DATA_SIZE;
|
||||||
@ -1268,9 +1285,14 @@ const Geometry::Class_info *Gis_polygon::get_class_info() const
|
|||||||
|
|
||||||
uint32 Gis_multi_point::get_data_size() const
|
uint32 Gis_multi_point::get_data_size() const
|
||||||
{
|
{
|
||||||
if (no_data(m_data, 4))
|
uint32 n_points;
|
||||||
return GET_SIZE_ERROR;
|
uint32 size;
|
||||||
return 4 + uint4korr(m_data)*(POINT_DATA_SIZE + WKB_HEADER_SIZE);
|
|
||||||
|
if (no_data(m_data, 4) ||
|
||||||
|
(n_points= uint4korr(m_data)) > max_n_points ||
|
||||||
|
no_data(m_data, (size= 4 + n_points*(POINT_DATA_SIZE + WKB_HEADER_SIZE))))
|
||||||
|
return GET_SIZE_ERROR;
|
||||||
|
return size;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@ -1364,8 +1386,8 @@ bool Gis_multi_point::get_data_as_wkt(String *txt, const char **end) const
|
|||||||
return 1;
|
return 1;
|
||||||
|
|
||||||
n_points= uint4korr(m_data);
|
n_points= uint4korr(m_data);
|
||||||
if (no_data(m_data+4,
|
if (n_points > max_n_points ||
|
||||||
n_points * (POINT_DATA_SIZE + WKB_HEADER_SIZE)) ||
|
no_data(m_data+4, n_points * (POINT_DATA_SIZE + WKB_HEADER_SIZE)) ||
|
||||||
txt->reserve(((MAX_DIGITS_IN_DOUBLE + 1) * 2 + 1) * n_points))
|
txt->reserve(((MAX_DIGITS_IN_DOUBLE + 1) * 2 + 1) * n_points))
|
||||||
return 1;
|
return 1;
|
||||||
*end= append_points(txt, n_points, m_data+4, WKB_HEADER_SIZE);
|
*end= append_points(txt, n_points, m_data+4, WKB_HEADER_SIZE);
|
||||||
@ -1446,6 +1468,7 @@ const Geometry::Class_info *Gis_multi_point::get_class_info() const
|
|||||||
uint32 Gis_multi_line_string::get_data_size() const
|
uint32 Gis_multi_line_string::get_data_size() const
|
||||||
{
|
{
|
||||||
uint32 n_line_strings;
|
uint32 n_line_strings;
|
||||||
|
uint32 n_points;
|
||||||
const char *data= m_data;
|
const char *data= m_data;
|
||||||
|
|
||||||
if (no_data(data, 4))
|
if (no_data(data, 4))
|
||||||
@ -1455,11 +1478,13 @@ uint32 Gis_multi_line_string::get_data_size() const
|
|||||||
|
|
||||||
while (n_line_strings--)
|
while (n_line_strings--)
|
||||||
{
|
{
|
||||||
if (no_data(data, WKB_HEADER_SIZE + 4))
|
if (no_data(data, WKB_HEADER_SIZE + 4) ||
|
||||||
|
(n_points= uint4korr(data + WKB_HEADER_SIZE)) > max_n_points)
|
||||||
return GET_SIZE_ERROR;
|
return GET_SIZE_ERROR;
|
||||||
data+= (WKB_HEADER_SIZE + 4 + uint4korr(data + WKB_HEADER_SIZE) *
|
data+= (WKB_HEADER_SIZE + 4 + n_points*POINT_DATA_SIZE);
|
||||||
POINT_DATA_SIZE);
|
|
||||||
}
|
}
|
||||||
|
if (no_data(data, 0))
|
||||||
|
return GET_SIZE_ERROR;
|
||||||
return (uint32) (data - m_data);
|
return (uint32) (data - m_data);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -1583,7 +1608,8 @@ bool Gis_multi_line_string::get_data_as_wkt(String *txt,
|
|||||||
return 1;
|
return 1;
|
||||||
n_points= uint4korr(data + WKB_HEADER_SIZE);
|
n_points= uint4korr(data + WKB_HEADER_SIZE);
|
||||||
data+= WKB_HEADER_SIZE + 4;
|
data+= WKB_HEADER_SIZE + 4;
|
||||||
if (no_data(data, n_points * POINT_DATA_SIZE) ||
|
if (n_points > max_n_points ||
|
||||||
|
no_data(data, n_points * POINT_DATA_SIZE) ||
|
||||||
txt->reserve(2 + ((MAX_DIGITS_IN_DOUBLE + 1) * 2 + 1) * n_points))
|
txt->reserve(2 + ((MAX_DIGITS_IN_DOUBLE + 1) * 2 + 1) * n_points))
|
||||||
return 1;
|
return 1;
|
||||||
txt->qs_append('(');
|
txt->qs_append('(');
|
||||||
@ -1644,7 +1670,7 @@ int Gis_multi_line_string::geometry_n(uint32 num, String *result) const
|
|||||||
return 1;
|
return 1;
|
||||||
n_points= uint4korr(data + WKB_HEADER_SIZE);
|
n_points= uint4korr(data + WKB_HEADER_SIZE);
|
||||||
length= WKB_HEADER_SIZE + 4+ POINT_DATA_SIZE * n_points;
|
length= WKB_HEADER_SIZE + 4+ POINT_DATA_SIZE * n_points;
|
||||||
if (no_data(data, length))
|
if (n_points > max_n_points || no_data(data, length))
|
||||||
return 1;
|
return 1;
|
||||||
if (!--num)
|
if (!--num)
|
||||||
break;
|
break;
|
||||||
@ -1755,6 +1781,7 @@ const Geometry::Class_info *Gis_multi_line_string::get_class_info() const
|
|||||||
uint32 Gis_multi_polygon::get_data_size() const
|
uint32 Gis_multi_polygon::get_data_size() const
|
||||||
{
|
{
|
||||||
uint32 n_polygons;
|
uint32 n_polygons;
|
||||||
|
uint32 n_points;
|
||||||
const char *data= m_data;
|
const char *data= m_data;
|
||||||
|
|
||||||
if (no_data(data, 4))
|
if (no_data(data, 4))
|
||||||
@ -1773,11 +1800,14 @@ uint32 Gis_multi_polygon::get_data_size() const
|
|||||||
|
|
||||||
while (n_linear_rings--)
|
while (n_linear_rings--)
|
||||||
{
|
{
|
||||||
if (no_data(data, 4))
|
if (no_data(data, 4) ||
|
||||||
|
(n_points= uint4korr(data)) > max_n_points)
|
||||||
return GET_SIZE_ERROR;
|
return GET_SIZE_ERROR;
|
||||||
data+= 4 + uint4korr(data) * POINT_DATA_SIZE;
|
data+= 4 + n_points * POINT_DATA_SIZE;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
if (no_data(data, 0))
|
||||||
|
return GET_SIZE_ERROR;
|
||||||
return (uint32) (data - m_data);
|
return (uint32) (data - m_data);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -1905,7 +1935,8 @@ bool Gis_multi_polygon::get_data_as_wkt(String *txt, const char **end) const
|
|||||||
return 1;
|
return 1;
|
||||||
uint32 n_points= uint4korr(data);
|
uint32 n_points= uint4korr(data);
|
||||||
data+= 4;
|
data+= 4;
|
||||||
if (no_data(data, POINT_DATA_SIZE * n_points) ||
|
if (n_points > max_n_points ||
|
||||||
|
no_data(data, POINT_DATA_SIZE * n_points) ||
|
||||||
txt->reserve(2 + ((MAX_DIGITS_IN_DOUBLE + 1) * 2 + 1) * n_points,
|
txt->reserve(2 + ((MAX_DIGITS_IN_DOUBLE + 1) * 2 + 1) * n_points,
|
||||||
512))
|
512))
|
||||||
return 1;
|
return 1;
|
||||||
@ -1988,6 +2019,8 @@ int Gis_multi_polygon::geometry_n(uint32 num, String *result) const
|
|||||||
if (no_data(data, 4))
|
if (no_data(data, 4))
|
||||||
return 1;
|
return 1;
|
||||||
n_points= uint4korr(data);
|
n_points= uint4korr(data);
|
||||||
|
if (n_points > max_n_points)
|
||||||
|
return 1;
|
||||||
data+= 4 + POINT_DATA_SIZE * n_points;
|
data+= 4 + POINT_DATA_SIZE * n_points;
|
||||||
}
|
}
|
||||||
} while (--num);
|
} while (--num);
|
||||||
|
@ -211,6 +211,11 @@ struct Geometry_buffer;
|
|||||||
|
|
||||||
class Geometry
|
class Geometry
|
||||||
{
|
{
|
||||||
|
public:
|
||||||
|
// Maximum number of points in feature that can fit into String
|
||||||
|
static const uint32 max_n_points=
|
||||||
|
(uint32) (INT_MAX32 - WKB_HEADER_SIZE - 4 /* n_points */) /
|
||||||
|
POINT_DATA_SIZE;
|
||||||
public:
|
public:
|
||||||
Geometry() {} /* Remove gcc warning */
|
Geometry() {} /* Remove gcc warning */
|
||||||
virtual ~Geometry() {} /* Remove gcc warning */
|
virtual ~Geometry() {} /* Remove gcc warning */
|
||||||
@ -393,10 +398,6 @@ public:
|
|||||||
|
|
||||||
class Gis_line_string: public Geometry
|
class Gis_line_string: public Geometry
|
||||||
{
|
{
|
||||||
// Maximum number of points in LineString that can fit into String
|
|
||||||
static const uint32 max_n_points=
|
|
||||||
(uint32) (UINT_MAX32 - WKB_HEADER_SIZE - 4 /* n_points */) /
|
|
||||||
POINT_DATA_SIZE;
|
|
||||||
public:
|
public:
|
||||||
Gis_line_string() {} /* Remove gcc warning */
|
Gis_line_string() {} /* Remove gcc warning */
|
||||||
virtual ~Gis_line_string() {} /* Remove gcc warning */
|
virtual ~Gis_line_string() {} /* Remove gcc warning */
|
||||||
|
@ -13696,6 +13696,7 @@ Field *create_tmp_field(THD *thd, TABLE *table,Item *item, Item::Type type,
|
|||||||
}
|
}
|
||||||
case Item::FIELD_ITEM:
|
case Item::FIELD_ITEM:
|
||||||
case Item::DEFAULT_VALUE_ITEM:
|
case Item::DEFAULT_VALUE_ITEM:
|
||||||
|
case Item::INSERT_VALUE_ITEM:
|
||||||
{
|
{
|
||||||
Item_field *field= (Item_field*) item;
|
Item_field *field= (Item_field*) item;
|
||||||
bool orig_modify= modify_item;
|
bool orig_modify= modify_item;
|
||||||
|
Loading…
x
Reference in New Issue
Block a user