From 1afb11074ea2f156dcfda7c28b9e7e47eb68c5ba Mon Sep 17 00:00:00 2001 From: Sergei Golubchik Date: Thu, 9 Feb 2017 12:06:15 +0100 Subject: [PATCH] MDEV-11582 InnoDB: Failing assertion: !((field)->vcol_info && !(field)->stored_in_db()) change the parser not to allow SERIAL as a normal data type. make a special rule for it, where it could be used for define fields, but not generated fields, not return type of a stored function, etc. --- mysql-test/r/parser.result | 20 ++++++++++++++ mysql-test/t/parser.test | 20 ++++++++++++++ sql/sql_yacc.yy | 54 +++++++++++++++++++++++++++----------- 3 files changed, 78 insertions(+), 16 deletions(-) diff --git a/mysql-test/r/parser.result b/mysql-test/r/parser.result index 7a0a8667350..cfca156f3d6 100644 --- a/mysql-test/r/parser.result +++ b/mysql-test/r/parser.result @@ -1289,3 +1289,23 @@ SELECT 1; ERROR 42000: You have an error in your SQL syntax; check the manual that corresponds to your MariaDB server version for the right syntax to use near 'UNION SELECT 1' at line 2 DROP TABLE t1; +create table t1 (a serial null); +ERROR 42000: You have an error in your SQL syntax; check the manual that corresponds to your MariaDB server version for the right syntax to use near 'null)' at line 1 +create table t1 (a serial auto_increment); +ERROR 42000: You have an error in your SQL syntax; check the manual that corresponds to your MariaDB server version for the right syntax to use near 'auto_increment)' at line 1 +create table t1 (a serial serial default value); +ERROR 42000: You have an error in your SQL syntax; check the manual that corresponds to your MariaDB server version for the right syntax to use near 'serial default value)' at line 1 +create table t1 (a serial collate binary); +ERROR 42000: You have an error in your SQL syntax; check the manual that corresponds to your MariaDB server version for the right syntax to use near 'collate binary)' at line 1 +create table t1 (i int, vc serial as (i)); +ERROR 42000: You have an error in your SQL syntax; check the manual that corresponds to your MariaDB server version for the right syntax to use near 'as (i))' at line 1 +create function fs() returns serial return 1; +ERROR 42000: You have an error in your SQL syntax; check the manual that corresponds to your MariaDB server version for the right syntax to use near 'serial return 1' at line 1 +create table t1 ( id serial ); +show create table t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `id` bigint(20) unsigned NOT NULL AUTO_INCREMENT, + UNIQUE KEY `id` (`id`) +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +drop table t1; diff --git a/mysql-test/t/parser.test b/mysql-test/t/parser.test index 1fa7df7fc3d..4bd594bdf8e 100644 --- a/mysql-test/t/parser.test +++ b/mysql-test/t/parser.test @@ -1321,3 +1321,23 @@ UNION SELECT 1; DROP TABLE t1; + +# +# MDEV-11582 InnoDB: Failing assertion: !((field)->vcol_info && !(field)->stored_in_db()) +# +--error ER_PARSE_ERROR +create table t1 (a serial null); +--error ER_PARSE_ERROR +create table t1 (a serial auto_increment); +--error ER_PARSE_ERROR +create table t1 (a serial serial default value); +--error ER_PARSE_ERROR +create table t1 (a serial collate binary); +--error ER_PARSE_ERROR +create table t1 (i int, vc serial as (i)); +--error ER_PARSE_ERROR +create function fs() returns serial return 1; + +create table t1 ( id serial ); +show create table t1; +drop table t1; diff --git a/sql/sql_yacc.yy b/sql/sql_yacc.yy index b84944c2ae2..124eab89cd3 100644 --- a/sql/sql_yacc.yy +++ b/sql/sql_yacc.yy @@ -1993,6 +1993,7 @@ bool my_yyoverflow(short **a, YYSTYPE **b, ulong *yystacksize); definer_opt no_definer definer get_diagnostics parse_vcol_expr vcol_opt_specifier vcol_opt_attribute vcol_opt_attribute_list vcol_attribute + opt_serial_attribute opt_serial_attribute_list serial_attribute explainable_command END_OF_INPUT @@ -6151,8 +6152,7 @@ field_spec: lex->init_last_field(f, $1.str, NULL); $$= f; } - field_type { Lex->set_last_field_type($3); } - field_def + field_type_or_serial { LEX *lex=Lex; $$= $2; @@ -6170,6 +6170,30 @@ field_spec: } ; +field_type_or_serial: + field_type { Lex->set_last_field_type($1); } field_def + | SERIAL_SYM + { + Lex_field_type_st type; + type.set(MYSQL_TYPE_LONGLONG); + Lex->set_last_field_type(type); + Lex->last_field->flags|= AUTO_INCREMENT_FLAG | NOT_NULL_FLAG + | UNSIGNED_FLAG | UNIQUE_KEY_FLAG; + } + opt_serial_attribute + ; + +opt_serial_attribute: + /* empty */ {} + | opt_serial_attribute_list {} + ; + +opt_serial_attribute_list: + opt_serial_attribute_list serial_attribute {} + | serial_attribute + ; + + field_def: opt_attribute | opt_generated_always AS virtual_column_func @@ -6447,12 +6471,6 @@ field_type: { $$.set(MYSQL_TYPE_SET); } | LONG_SYM opt_binary { $$.set(MYSQL_TYPE_MEDIUM_BLOB); } - | SERIAL_SYM - { - $$.set(MYSQL_TYPE_LONGLONG); - Lex->last_field->flags|= (AUTO_INCREMENT_FLAG | NOT_NULL_FLAG | UNSIGNED_FLAG | - UNIQUE_KEY_FLAG); - } ; spatial_type: @@ -6575,7 +6593,6 @@ opt_attribute_list: attribute: NULL_SYM { Lex->last_field->flags&= ~ NOT_NULL_FLAG; } - | not NULL_SYM { Lex->last_field->flags|= NOT_NULL_FLAG; } | DEFAULT column_default_expr { Lex->last_field->default_value= $2; } | ON UPDATE_SYM NOW_SYM opt_default_time_precision { @@ -6591,6 +6608,18 @@ attribute: lex->last_field->flags|= AUTO_INCREMENT_FLAG | NOT_NULL_FLAG | UNIQUE_KEY_FLAG; lex->alter_info.flags|= Alter_info::ALTER_ADD_INDEX; } + | COLLATE_SYM collation_name + { + if (Lex->charset && !my_charset_same(Lex->charset,$2)) + my_yyabort_error((ER_COLLATION_CHARSET_MISMATCH, MYF(0), + $2->name,Lex->charset->csname)); + Lex->last_field->charset= $2; + } + | serial_attribute + ; + +serial_attribute: + not NULL_SYM { Lex->last_field->flags|= NOT_NULL_FLAG; } | opt_primary KEY_SYM { LEX *lex=Lex; @@ -6610,13 +6639,6 @@ attribute: lex->alter_info.flags|= Alter_info::ALTER_ADD_INDEX; } | COMMENT_SYM TEXT_STRING_sys { Lex->last_field->comment= $2; } - | COLLATE_SYM collation_name - { - if (Lex->charset && !my_charset_same(Lex->charset,$2)) - my_yyabort_error((ER_COLLATION_CHARSET_MISMATCH, MYF(0), - $2->name,Lex->charset->csname)); - Lex->last_field->charset= $2; - } | IDENT_sys equal TEXT_STRING_sys { if ($3.length > ENGINE_OPTION_MAX_LENGTH)