Commit 0fcd0ee3 authored by Sergei Golubchik's avatar Sergei Golubchik

MDEV-9500 Bug after upgrade to 10.1.10 (and 10.1.11)

Case: table with a NOT NULL field, BEFORE UPDATE trigger,
and UPDATE with a subquery that uses GROUP BY on that
NOT NULL field, and needs a temporary table for it.

Because of the BEFORE trigger, the field becomes nullable
temporarily. But its Item_field (used in GROUP BY) doesn't.
When working with the temptable some code looked at
item->maybe_null, some - at field->null_ptr.
The fix: make Item_field nullable when its field is.

This triggers an assert. The group key size is calculated
before the item is made nullable, so the group key doesn't
have a null byte. The fix: make fields/items nullable
before the group key size is calculated.
parent a38b705f
...@@ -322,3 +322,15 @@ select * from t1; ...@@ -322,3 +322,15 @@ select * from t1;
id id
0 0
drop table t1; drop table t1;
create table t1 (a int not null, b int);
create trigger trgi before update on t1 for each row do 1;
insert t1 values (1,1),(2,2),(3,3),(1,4);
create table t2 select a as c, b as d from t1;
update t1 set a=(select count(c) from t2 where c+1=a+1 group by a);
select * from t1;
a b
2 1
1 2
1 3
2 4
drop table t1, t2;
...@@ -339,3 +339,13 @@ insert t1 values (0); ...@@ -339,3 +339,13 @@ insert t1 values (0);
select * from t1; select * from t1;
drop table t1; drop table t1;
#
# MDEV-9500 Bug after upgrade to 10.1.10 (and 10.1.11)
#
create table t1 (a int not null, b int);
create trigger trgi before update on t1 for each row do 1;
insert t1 values (1,1),(2,2),(3,3),(1,4);
create table t2 select a as c, b as d from t1;
update t1 set a=(select count(c) from t2 where c+1=a+1 group by a);
select * from t1;
drop table t1, t2;
...@@ -2394,6 +2394,7 @@ bool Item_field::switch_to_nullable_fields_processor(uchar *arg) ...@@ -2394,6 +2394,7 @@ bool Item_field::switch_to_nullable_fields_processor(uchar *arg)
Field **new_fields= (Field **)arg; Field **new_fields= (Field **)arg;
set_field_to_new_field(&field, new_fields); set_field_to_new_field(&field, new_fields);
set_field_to_new_field(&result_field, new_fields); set_field_to_new_field(&result_field, new_fields);
maybe_null= field && field->maybe_null();
return 0; return 0;
} }
......
...@@ -368,6 +368,9 @@ int mysql_update(THD *thd, ...@@ -368,6 +368,9 @@ int mysql_update(THD *thd,
if (check_unique_table(thd, table_list)) if (check_unique_table(thd, table_list))
DBUG_RETURN(TRUE); DBUG_RETURN(TRUE);
switch_to_nullable_trigger_fields(fields, table);
switch_to_nullable_trigger_fields(values, table);
/* Apply the IN=>EXISTS transformation to all subqueries and optimize them. */ /* Apply the IN=>EXISTS transformation to all subqueries and optimize them. */
if (select_lex->optimize_unflattened_subqueries(false)) if (select_lex->optimize_unflattened_subqueries(false))
DBUG_RETURN(TRUE); DBUG_RETURN(TRUE);
...@@ -455,8 +458,6 @@ int mysql_update(THD *thd, ...@@ -455,8 +458,6 @@ int mysql_update(THD *thd,
} }
init_ftfuncs(thd, select_lex, 1); init_ftfuncs(thd, select_lex, 1);
switch_to_nullable_trigger_fields(fields, table);
switch_to_nullable_trigger_fields(values, table);
table->mark_columns_needed_for_update(); table->mark_columns_needed_for_update();
table->update_const_key_parts(conds); table->update_const_key_parts(conds);
......
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