From 082aea7742455246fdcfd112a392b78c793dfebc Mon Sep 17 00:00:00 2001 From: Sergei Golubchik Date: Sat, 21 Oct 2023 17:33:29 +0200 Subject: [PATCH] MDEV-31112 vcol circular references lead to stack overflow --- mysql-test/suite/vcol/r/vcol_misc.result | 11 +++++++++++ mysql-test/suite/vcol/t/vcol_misc.test | 13 +++++++++++++ sql/item.cc | 7 ++++--- 3 files changed, 28 insertions(+), 3 deletions(-) diff --git a/mysql-test/suite/vcol/r/vcol_misc.result b/mysql-test/suite/vcol/r/vcol_misc.result index 0a86d68b3ad87..8038f18ffc702 100644 --- a/mysql-test/suite/vcol/r/vcol_misc.result +++ b/mysql-test/suite/vcol/r/vcol_misc.result @@ -569,3 +569,14 @@ drop table t1; # # End of 10.3 tests # +# +# MDEV-31112 vcol circular references lead to stack overflow +# +create table t (a int, c int as (a)); +alter table t alter column c drop default; +alter table t modify column a int as (c) stored; +ERROR 01000: Expression for field `a` is referring to uninitialized field `c` +drop table t; +# +# End of 10.4 tests +# diff --git a/mysql-test/suite/vcol/t/vcol_misc.test b/mysql-test/suite/vcol/t/vcol_misc.test index f696d5d581465..3bbed408f6f81 100644 --- a/mysql-test/suite/vcol/t/vcol_misc.test +++ b/mysql-test/suite/vcol/t/vcol_misc.test @@ -536,3 +536,16 @@ drop table t1; --echo # --echo # End of 10.3 tests --echo # + +--echo # +--echo # MDEV-31112 vcol circular references lead to stack overflow +--echo # +create table t (a int, c int as (a)); +alter table t alter column c drop default; +--error ER_EXPRESSION_REFERS_TO_UNINIT_FIELD +alter table t modify column a int as (c) stored; +drop table t; + +--echo # +--echo # End of 10.4 tests +--echo # diff --git a/sql/item.cc b/sql/item.cc index f9d8ac490aed9..34272156aade2 100644 --- a/sql/item.cc +++ b/sql/item.cc @@ -908,14 +908,15 @@ bool Item_field::register_field_in_write_map(void *arg) This is used by fix_vcol_expr() when a table is opened - We don't have to check fields that are marked as NO_DEFAULT_VALUE - as the upper level will ensure that all these will be given a value. + We don't have to check non-virtual fields that are marked as + NO_DEFAULT_VALUE as the upper level will ensure that all these + will be given a value. */ bool Item_field::check_field_expression_processor(void *arg) { Field *org_field= (Field*) arg; - if (field->flags & NO_DEFAULT_VALUE_FLAG) + if (field->flags & NO_DEFAULT_VALUE_FLAG && !field->vcol_info) return 0; if ((field->default_value && field->default_value->flags) || field->vcol_info) {