Commit 495fd27c authored by Sergei Golubchik's avatar Sergei Golubchik

MDEV-4284 Assertion `cmp_items[(uint)cmp_type]' fails in sql/item_cmpfunc.cc

Flip the switch and create Item_cache based on the argument's cmp_type, not argument's result_type().
Fix subselect_engine to calculate cmp_type correctly

sql/item_subselect.h:
  mdev:4284
parent ecd4bf62
...@@ -7,5 +7,4 @@ a ...@@ -7,5 +7,4 @@ a
2002-03-04 2002-03-04
Warnings: Warnings:
Note 1003 2000-01-01 Note 1003 2000-01-01
Note 1003 2000-01-06
drop table t1; drop table t1;
...@@ -96,3 +96,9 @@ b + interval a day ...@@ -96,3 +96,9 @@ b + interval a day
2002-02-04 2002-02-04
drop table t1; drop table t1;
End of 5.0 tests End of 5.0 tests
create table t1 (a varchar(10));
insert t1 values ('2000-12-03'),('2008-05-03');
select * from t1 where case a when adddate( '2012-12-12', 7 ) then true end;
a
drop table t1;
End of 5.5 tests
...@@ -88,3 +88,15 @@ select b + interval a day from t1; ...@@ -88,3 +88,15 @@ select b + interval a day from t1;
drop table t1; drop table t1;
--echo End of 5.0 tests --echo End of 5.0 tests
#
# MDEV-4284 Assertion `cmp_items[(uint)cmp_type]' fails in sql/item_cmpfunc.cc
#
create table t1 (a varchar(10));
insert t1 values ('2000-12-03'),('2008-05-03');
select * from t1 where case a when adddate( '2012-12-12', 7 ) then true end;
drop table t1;
--echo End of 5.5 tests
...@@ -8643,7 +8643,7 @@ int stored_field_cmp_to_item(THD *thd, Field *field, Item *item) ...@@ -8643,7 +8643,7 @@ int stored_field_cmp_to_item(THD *thd, Field *field, Item *item)
Item_cache* Item_cache::get_cache(const Item *item) Item_cache* Item_cache::get_cache(const Item *item)
{ {
return get_cache(item, item->result_type()); return get_cache(item, item->cmp_type());
} }
......
...@@ -1087,6 +1087,11 @@ enum Item_result Item_singlerow_subselect::result_type() const ...@@ -1087,6 +1087,11 @@ enum Item_result Item_singlerow_subselect::result_type() const
return engine->type(); return engine->type();
} }
enum Item_result Item_singlerow_subselect::cmp_type() const
{
return engine->cmptype();
}
/* /*
Don't rely on the result type to calculate field type. Don't rely on the result type to calculate field type.
Ask the engine instead. Ask the engine instead.
...@@ -3044,12 +3049,13 @@ void subselect_engine::set_row(List<Item> &item_list, Item_cache **row) ...@@ -3044,12 +3049,13 @@ void subselect_engine::set_row(List<Item> &item_list, Item_cache **row)
{ {
Item *sel_item; Item *sel_item;
List_iterator_fast<Item> li(item_list); List_iterator_fast<Item> li(item_list);
res_type= STRING_RESULT; cmp_type= res_type= STRING_RESULT;
res_field_type= MYSQL_TYPE_VAR_STRING; res_field_type= MYSQL_TYPE_VAR_STRING;
for (uint i= 0; (sel_item= li++); i++) for (uint i= 0; (sel_item= li++); i++)
{ {
item->max_length= sel_item->max_length; item->max_length= sel_item->max_length;
res_type= sel_item->result_type(); res_type= sel_item->result_type();
cmp_type= sel_item->cmp_type();
res_field_type= sel_item->field_type(); res_field_type= sel_item->field_type();
item->decimals= sel_item->decimals; item->decimals= sel_item->decimals;
item->unsigned_flag= sel_item->unsigned_flag; item->unsigned_flag= sel_item->unsigned_flag;
...@@ -3060,7 +3066,7 @@ void subselect_engine::set_row(List<Item> &item_list, Item_cache **row) ...@@ -3060,7 +3066,7 @@ void subselect_engine::set_row(List<Item> &item_list, Item_cache **row)
//psergey-backport-timours: row[i]->store(sel_item); //psergey-backport-timours: row[i]->store(sel_item);
} }
if (item_list.elements > 1) if (item_list.elements > 1)
res_type= ROW_RESULT; cmp_type= res_type= ROW_RESULT;
} }
void subselect_single_select_engine::fix_length_and_dec(Item_cache **row) void subselect_single_select_engine::fix_length_and_dec(Item_cache **row)
......
...@@ -286,6 +286,7 @@ class Item_singlerow_subselect :public Item_subselect ...@@ -286,6 +286,7 @@ class Item_singlerow_subselect :public Item_subselect
bool val_bool(); bool val_bool();
bool get_date(MYSQL_TIME *ltime, ulonglong fuzzydate); bool get_date(MYSQL_TIME *ltime, ulonglong fuzzydate);
enum Item_result result_type() const; enum Item_result result_type() const;
enum Item_result cmp_type() const;
enum_field_types field_type() const; enum_field_types field_type() const;
void fix_length_and_dec(); void fix_length_and_dec();
...@@ -698,6 +699,7 @@ class subselect_engine: public Sql_alloc ...@@ -698,6 +699,7 @@ class subselect_engine: public Sql_alloc
THD *thd; /* pointer to current THD */ THD *thd; /* pointer to current THD */
Item_subselect *item; /* item, that use this engine */ Item_subselect *item; /* item, that use this engine */
enum Item_result res_type; /* type of results */ enum Item_result res_type; /* type of results */
enum Item_result cmp_type; /* how to compare the results */
enum_field_types res_field_type; /* column type of the results */ enum_field_types res_field_type; /* column type of the results */
bool maybe_null; /* may be null (first item in select) */ bool maybe_null; /* may be null (first item in select) */
public: public:
...@@ -712,7 +714,7 @@ class subselect_engine: public Sql_alloc ...@@ -712,7 +714,7 @@ class subselect_engine: public Sql_alloc
{ {
result= res; result= res;
item= si; item= si;
res_type= STRING_RESULT; cmp_type= res_type= STRING_RESULT;
res_field_type= MYSQL_TYPE_VAR_STRING; res_field_type= MYSQL_TYPE_VAR_STRING;
maybe_null= 0; maybe_null= 0;
set_thd(thd_arg); set_thd(thd_arg);
...@@ -752,6 +754,7 @@ class subselect_engine: public Sql_alloc ...@@ -752,6 +754,7 @@ class subselect_engine: public Sql_alloc
virtual uint cols()= 0; /* return number of columns in select */ virtual uint cols()= 0; /* return number of columns in select */
virtual uint8 uncacheable()= 0; /* query is uncacheable */ virtual uint8 uncacheable()= 0; /* query is uncacheable */
enum Item_result type() { return res_type; } enum Item_result type() { return res_type; }
enum Item_result cmptype() { return cmp_type; }
enum_field_types field_type() { return res_field_type; } enum_field_types field_type() { return res_field_type; }
virtual void exclude()= 0; virtual void exclude()= 0;
virtual bool may_be_null() { return maybe_null; }; virtual bool may_be_null() { return maybe_null; };
......
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