diff options
author | Aleksey Midenkov <midenok@gmail.com> | 2022-08-31 11:55:05 +0300 |
---|---|---|
committer | Aleksey Midenkov <midenok@gmail.com> | 2022-08-31 11:55:05 +0300 |
commit | 24fff8267d0722b20ca780cf144ce27560df1394 (patch) | |
tree | 4169f75f1a43abdb26292baa0dad477fd8937249 /sql/table.cc | |
parent | 2af15914cb3ae204d3b413995a96c7722ad60d93 (diff) | |
download | mariadb-git-24fff8267d0722b20ca780cf144ce27560df1394.tar.gz |
MDEV-25292 gcol.gcol_bugfixes --ps fix
Related to MDEV-24176.
1. vcol_fix_expr() generates new tree changes:
Type_std_attributes::agg_item_set_converter() does change_item_tree().
The changes are allocated on expr_arena (via Vcol_expr_context as per
MDEV-24176).
2. vcol_cleanup_expr() doesn't remove these changes (can be a bug of
Type_std_attributes or per design).
3. Atomic CREATE OR REPLACE renames old table to backup
(finalize_atomic_replace()). It does that via
rename_table_and_triggers() and that closes table share and releases
expr_arena root. Hence now we have Item corpses in thd->change_list.
4. PS cleanup phase tries to rollback thd->change_list and accesses
already freed item corpses.
The fix saves and restores change_list on
vcol_fix_expr()/vcol_cleanup_expr().
Diffstat (limited to 'sql/table.cc')
-rw-r--r-- | sql/table.cc | 21 |
1 files changed, 21 insertions, 0 deletions
diff --git a/sql/table.cc b/sql/table.cc index 5e17eb60b30..e1161fd98c3 100644 --- a/sql/table.cc +++ b/sql/table.cc @@ -3723,6 +3723,13 @@ bool TABLE::vcol_fix_expr(THD *thd) return false; } + if (!thd->Item_change_list::is_empty()) + { + DBUG_ASSERT(!saved_change_list); + saved_change_list= new Item_change_list; + thd->move_elements_to(saved_change_list); + } + Vcol_expr_context expr_ctx(thd, this); if (expr_ctx.init()) return true; @@ -3743,7 +3750,12 @@ error: bool TABLE::vcol_cleanup_expr(THD *thd) { if (vcol_refix_list.is_empty()) + { + DBUG_ASSERT(!saved_change_list); return false; + } + + thd->rollback_item_tree_changes(); List_iterator<Virtual_column_info> it(vcol_refix_list); bool result= false; @@ -3751,6 +3763,15 @@ bool TABLE::vcol_cleanup_expr(THD *thd) while (Virtual_column_info *vcol= it++) result|= vcol->cleanup_session_expr(); + if (saved_change_list) + { + DBUG_ASSERT(!vcol_refix_list.is_empty()); + DBUG_ASSERT(!saved_change_list->is_empty()); + saved_change_list->move_elements_to(thd); + delete saved_change_list; + saved_change_list= NULL; + } + DBUG_ASSERT(!result || thd->get_stmt_da()->is_error()); return result; } |