Commit 920c479c authored by Igor Babaev's avatar Igor Babaev

Fixed bug mdev-4336.

When iterating over a list of conditions using List_iterator
the function remove_eq_conds should skip all predicates that
replace a condition from the list. Otherwise it can come to
an infinite recursion. 
parent b249680f
...@@ -1822,4 +1822,18 @@ b c d ...@@ -1822,4 +1822,18 @@ b c d
5 8 88 5 8 88
5 8 81 5 8 81
DROP TABLE t1,t2; DROP TABLE t1,t2;
#
# Bug mdev-4336: LEFT JOIN with disjunctive
# <non-nullable datetime field> IS NULL in WHERE
# causes a hang and eventual crash
#
CREATE TABLE t1 (
id int(11) NOT NULL,
modified datetime NOT NULL,
PRIMARY KEY (id)
);
SELECT a.* FROM t1 a LEFT JOIN t1 b ON a.id = b.id
WHERE a.modified > b.modified or b.modified IS NULL;
id modified
DROP TABLE t1;
SET optimizer_switch=@save_optimizer_switch; SET optimizer_switch=@save_optimizer_switch;
...@@ -1833,6 +1833,20 @@ b c d ...@@ -1833,6 +1833,20 @@ b c d
5 8 88 5 8 88
5 8 81 5 8 81
DROP TABLE t1,t2; DROP TABLE t1,t2;
#
# Bug mdev-4336: LEFT JOIN with disjunctive
# <non-nullable datetime field> IS NULL in WHERE
# causes a hang and eventual crash
#
CREATE TABLE t1 (
id int(11) NOT NULL,
modified datetime NOT NULL,
PRIMARY KEY (id)
);
SELECT a.* FROM t1 a LEFT JOIN t1 b ON a.id = b.id
WHERE a.modified > b.modified or b.modified IS NULL;
id modified
DROP TABLE t1;
SET optimizer_switch=@save_optimizer_switch; SET optimizer_switch=@save_optimizer_switch;
set join_cache_level=default; set join_cache_level=default;
show variables like 'join_cache_level'; show variables like 'join_cache_level';
......
...@@ -1359,4 +1359,21 @@ ORDER BY t1.b; ...@@ -1359,4 +1359,21 @@ ORDER BY t1.b;
DROP TABLE t1,t2; DROP TABLE t1,t2;
--echo #
--echo # Bug mdev-4336: LEFT JOIN with disjunctive
--echo # <non-nullable datetime field> IS NULL in WHERE
--echo # causes a hang and eventual crash
--echo #
CREATE TABLE t1 (
id int(11) NOT NULL,
modified datetime NOT NULL,
PRIMARY KEY (id)
);
SELECT a.* FROM t1 a LEFT JOIN t1 b ON a.id = b.id
WHERE a.modified > b.modified or b.modified IS NULL;
DROP TABLE t1;
SET optimizer_switch=@save_optimizer_switch; SET optimizer_switch=@save_optimizer_switch;
...@@ -13197,7 +13197,8 @@ remove_eq_conds(THD *thd, COND *cond, Item::cond_result *cond_value) ...@@ -13197,7 +13197,8 @@ remove_eq_conds(THD *thd, COND *cond, Item::cond_result *cond_value)
else else
{ {
Item *list_item; Item *list_item;
Item *new_list_item; Item *new_list_item;
uint cnt= new_item_and_list->elements;
List_iterator<Item> it(*new_item_and_list); List_iterator<Item> it(*new_item_and_list);
while ((list_item= it++)) while ((list_item= it++))
{ {
...@@ -13211,7 +13212,9 @@ remove_eq_conds(THD *thd, COND *cond, Item::cond_result *cond_value) ...@@ -13211,7 +13212,9 @@ remove_eq_conds(THD *thd, COND *cond, Item::cond_result *cond_value)
it.replace(new_list_item); it.replace(new_list_item);
new_list_item->update_used_tables(); new_list_item->update_used_tables();
} }
li.replace(*new_item_and_list); li.replace(*new_item_and_list);
for (cnt--; cnt; cnt--)
item= li++;
} }
cond_and_list->concat((List<Item>*) cond_equal_items); cond_and_list->concat((List<Item>*) cond_equal_items);
} }
...@@ -13232,7 +13235,13 @@ remove_eq_conds(THD *thd, COND *cond, Item::cond_result *cond_value) ...@@ -13232,7 +13235,13 @@ remove_eq_conds(THD *thd, COND *cond, Item::cond_result *cond_value)
if (new_item->type() == Item::COND_ITEM && if (new_item->type() == Item::COND_ITEM &&
((Item_cond*) new_item)->functype() == ((Item_cond*) new_item)->functype() ==
((Item_cond*) cond)->functype()) ((Item_cond*) cond)->functype())
li.replace(*((Item_cond*) new_item)->argument_list()); {
List<Item> *arg_list= ((Item_cond*) new_item)->argument_list();
uint cnt= arg_list->elements;
li.replace(*arg_list);
for ( cnt--; cnt; cnt--)
item= li++;
}
else else
li.replace(new_item); li.replace(new_item);
} }
......
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