summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorNikita Malyavin <nikitamalyavin@gmail.com>2021-06-28 20:59:29 +0300
committerNikita Malyavin <nikitamalyavin@gmail.com>2021-07-22 22:35:23 +0300
commitdba7cd25e1449298f3122286dbf73f1b84bbdc5c (patch)
tree95a663fdf01becbff1eabc86447fe0072521c06f
parentb50ea900636ba8d584b997649dd201014152f719 (diff)
downloadmariadb-git-bb-10.3-MDEV-25560.tar.gz
MDEV-25560 Creating table with certain generated column crashes serverbb-10.3-MDEV-25560
Fix RPAD() handling without 3rd argument of padding, in which case default padding is used.
-rw-r--r--mysql-test/main/func_str.result16
-rw-r--r--mysql-test/main/func_str.test18
-rw-r--r--sql/item_strfunc.cc19
3 files changed, 47 insertions, 6 deletions
diff --git a/mysql-test/main/func_str.result b/mysql-test/main/func_str.result
index 9e63f6e4580..eccec315a45 100644
--- a/mysql-test/main/func_str.result
+++ b/mysql-test/main/func_str.result
@@ -5153,5 +5153,21 @@ c1
42
DROP TABLE t1, t2;
#
+# MDEV-25560 Creating table with certain generated column crashes server
+#
+CREATE TABLE t1 (i int, b int AS (RPAD(123,1)) stored);
+# Original case from the reporter
+CREATE TABLE crash_test_2 (
+DATA_VALUE CHAR(10) NULL,
+HAS_DATA BIT NOT NULL,
+TEST_COLUMN CHAR(10) AS (RPAD(CASE WHEN HAS_DATA = 1
+THEN DATA_VALUE ELSE NULL END, 10)) STORED);
+Warnings:
+Warning 1901 Function or expression 'rpad(case when `HAS_DATA` = 1 then `DATA_VALUE` else NULL end,10)' cannot be used in the GENERATED ALWAYS AS clause of `TEST_COLUMN`
+Warning 1105 Expression depends on the @@sql_mode value PAD_CHAR_TO_FULL_LENGTH
+# Cleanup
+DROP TABLE t1;
+DROP TABLE crash_test_2;
+#
# End of 10.3 tests
#
diff --git a/mysql-test/main/func_str.test b/mysql-test/main/func_str.test
index 780783e316f..8f8628f7142 100644
--- a/mysql-test/main/func_str.test
+++ b/mysql-test/main/func_str.test
@@ -2091,5 +2091,23 @@ DROP TABLE t1, t2;
--echo #
+--echo # MDEV-25560 Creating table with certain generated column crashes server
+--echo #
+
+CREATE TABLE t1 (i int, b int AS (RPAD(123,1)) stored);
+
+--echo # Original case from the reporter
+CREATE TABLE crash_test_2 (
+ DATA_VALUE CHAR(10) NULL,
+ HAS_DATA BIT NOT NULL,
+ TEST_COLUMN CHAR(10) AS (RPAD(CASE WHEN HAS_DATA = 1
+ THEN DATA_VALUE ELSE NULL END, 10)) STORED);
+
+--echo # Cleanup
+DROP TABLE t1;
+DROP TABLE crash_test_2;
+
+
+--echo #
--echo # End of 10.3 tests
--echo #
diff --git a/sql/item_strfunc.cc b/sql/item_strfunc.cc
index 0e63bb2a50c..361feb9055d 100644
--- a/sql/item_strfunc.cc
+++ b/sql/item_strfunc.cc
@@ -3192,6 +3192,14 @@ err:
}
+static String *default_pad_str(String *pad_str, CHARSET_INFO *collation)
+{
+ pad_str->set_charset(collation);
+ pad_str->length(0);
+ pad_str->append(" ", 1);
+ return pad_str;
+}
+
bool Item_func_pad::fix_length_and_dec()
{
if (arg_count == 3)
@@ -3207,9 +3215,7 @@ bool Item_func_pad::fix_length_and_dec()
{
if (agg_arg_charsets_for_string_result(collation, &args[0], 1, 1))
return TRUE;
- pad_str.set_charset(collation.collation);
- pad_str.length(0);
- pad_str.append(" ", 1);
+ default_pad_str(&pad_str, collation.collation);
}
DBUG_ASSERT(collation.collation->mbmaxlen > 0);
@@ -3232,9 +3238,9 @@ bool Item_func_pad::fix_length_and_dec()
Sql_mode_dependency Item_func_rpad::value_depends_on_sql_mode() const
{
DBUG_ASSERT(fixed);
- DBUG_ASSERT(arg_count == 3);
+ DBUG_ASSERT(arg_count >= 2);
if (!args[1]->value_depends_on_sql_mode_const_item() ||
- !args[2]->value_depends_on_sql_mode_const_item())
+ (arg_count == 3 && !args[2]->value_depends_on_sql_mode_const_item()))
return Item_func::value_depends_on_sql_mode();
Longlong_hybrid len= args[1]->to_longlong_hybrid();
if (args[1]->null_value || len.neg())
@@ -3242,7 +3248,8 @@ Sql_mode_dependency Item_func_rpad::value_depends_on_sql_mode() const
if (len.abs() > 0 && len.abs() < args[0]->max_char_length())
return Item_func::value_depends_on_sql_mode();
StringBuffer<64> padstrbuf;
- String *padstr= args[2]->val_str(&padstrbuf);
+ String *padstr= arg_count == 3 ? args[2]->val_str(&padstrbuf) :
+ default_pad_str(&padstrbuf, collation.collation);
if (!padstr || !padstr->length())
return Sql_mode_dependency(); // will return NULL
if (padstr->lengthsp() != 0)