From 8aff418ec867419950bc2e0010f679b8f0216829 Mon Sep 17 00:00:00 2001 From: Sergei Golubchik Date: Wed, 17 Jan 2018 13:09:47 +0100 Subject: crash with too long index comments --- sql/unireg.cc | 41 ++++++++++++++++++++++++++++++++--------- 1 file changed, 32 insertions(+), 9 deletions(-) (limited to 'sql') diff --git a/sql/unireg.cc b/sql/unireg.cc index 528c3025c57..2527d44bbd0 100644 --- a/sql/unireg.cc +++ b/sql/unireg.cc @@ -89,6 +89,28 @@ handle_condition(THD *, return is_handled; } +/* + In ALTER TABLE, mysql_create_frm() gets the temporary table name, + like #sql-3696_2. It's used for error messages, when a table cannot + be created because of some OS error. + If there's a user error (like, too long comment), we want to show + the real table name, though. +*/ +static const char *get_real_table_name(const char *table, + List &fields) +{ + const char *real_table_name= table; + List_iterator it(fields); + Create_field *field; + while ((field=it++)) + { + if (field->field && field->field->table && + (real_table_name= field->field->table->s->table_name.str)) + break; + } + return real_table_name; +} + /* Create a frm (table definition) file @@ -232,15 +254,7 @@ bool mysql_create_frm(THD *thd, const char *file_name, if (tmp_len < create_info->comment.length) { - char *real_table_name= (char*) table; - List_iterator it(create_fields); - Create_field *field; - while ((field=it++)) - { - if (field->field && field->field->table && - (real_table_name= field->field->table->s->table_name.str)) - break; - } + const char *real_table_name= get_real_table_name(table, create_fields); if ((thd->variables.sql_mode & (MODE_STRICT_TRANS_TABLES | MODE_STRICT_ALL_TABLES))) { @@ -285,6 +299,15 @@ bool mysql_create_frm(THD *thd, const char *file_name, keybuff=(uchar*) my_malloc(key_buff_length, MYF(0)); key_info_length= pack_keys(keybuff, keys, key_info, data_offset); + if (key_info_length > UINT_MAX16) + { + my_printf_error(ER_CANT_CREATE_TABLE, + "Cannot create table %`s.%`s: index information is too long. " + "Decrease number of indexes or use shorter index names or shorter comments.", + MYF(0), db, get_real_table_name(table, create_fields)); + goto err; + } + /* Ensure that there are no forms in this newly created form file. Even if the form file exists, create_frm must truncate it to -- cgit v1.2.1