From 6947f2d1316c7b0b7ede841a097328da8c21aa4d Mon Sep 17 00:00:00 2001 From: unknown Date: Wed, 18 Jul 2007 12:13:45 +0500 Subject: [PATCH] Fix for bug #28125: ERROR 2013 when adding index. Problem: we may break a multibyte char sequence using a key reduced to maximum allowed length for a storage engine (that leads to failed assertion in the innodb code, see also #17530). Fix: align truncated key length to multibyte char boundary. mysql-test/r/innodb_mysql.result: Fix for bug #28125: ERROR 2013 when adding index. - test result. mysql-test/t/innodb_mysql.test: Fix for bug #28125: ERROR 2013 when adding index. - test case. sql/sql_table.cc: Fix for bug #28125: ERROR 2013 when adding index. - align truncated key length to multibyte char boundary. - display real key length in bytes raising warnings. --- mysql-test/r/innodb_mysql.result | 14 +++++++++++++- mysql-test/t/innodb_mysql.test | 9 +++++++++ sql/sql_table.cc | 6 ++++-- 3 files changed, 26 insertions(+), 3 deletions(-) diff --git a/mysql-test/r/innodb_mysql.result b/mysql-test/r/innodb_mysql.result index 4535710c905..4c1e7189998 100644 --- a/mysql-test/r/innodb_mysql.result +++ b/mysql-test/r/innodb_mysql.result @@ -418,7 +418,7 @@ DROP TABLE t1,t2; create table t1(f1 varchar(800) binary not null, key(f1)) engine = innodb character set utf8 collate utf8_general_ci; Warnings: -Warning 1071 Specified key was too long; max key length is 765 bytes +Warning 1071 Specified key was too long; max key length is 767 bytes insert into t1 values('aaa'); drop table t1; CREATE TABLE t1 (a INT PRIMARY KEY, b INT, c FLOAT, KEY b(b)) ENGINE = INNODB; @@ -735,4 +735,16 @@ COUNT(*) 3072 set @@sort_buffer_size=default; DROP TABLE t1,t2; +create table t1(a text) engine=innodb default charset=utf8; +insert into t1 values('aaa'); +alter table t1 add index(a(1024)); +Warnings: +Warning 1071 Specified key was too long; max key length is 767 bytes +show create table t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` text, + KEY `a` (`a`(255)) +) ENGINE=InnoDB DEFAULT CHARSET=utf8 +drop table t1; End of 5.0 tests diff --git a/mysql-test/t/innodb_mysql.test b/mysql-test/t/innodb_mysql.test index d4ce997ddb1..4930ec81a62 100644 --- a/mysql-test/t/innodb_mysql.test +++ b/mysql-test/t/innodb_mysql.test @@ -741,4 +741,13 @@ set @@sort_buffer_size=default; DROP TABLE t1,t2; +# +# Bug #28125: ERROR 2013 when adding index. +# +create table t1(a text) engine=innodb default charset=utf8; +insert into t1 values('aaa'); +alter table t1 add index(a(1024)); +show create table t1; +drop table t1; + --echo End of 5.0 tests diff --git a/sql/sql_table.cc b/sql/sql_table.cc index 87f23097a66..0da639f9896 100644 --- a/sql/sql_table.cc +++ b/sql/sql_table.cc @@ -1357,6 +1357,8 @@ static int mysql_prepare_table(THD *thd, HA_CREATE_INFO *create_info, length); push_warning(thd, MYSQL_ERROR::WARN_LEVEL_WARN, ER_TOO_LONG_KEY, warn_buff); + /* Align key length to multibyte char boundary */ + length-= length % sql_field->charset->mbmaxlen; } else { @@ -1387,8 +1389,6 @@ static int mysql_prepare_table(THD *thd, HA_CREATE_INFO *create_info, if (length > file->max_key_part_length() && key->type != Key::FULLTEXT) { length= file->max_key_part_length(); - /* Align key length to multibyte char boundary */ - length-= length % sql_field->charset->mbmaxlen; if (key->type == Key::MULTIPLE) { /* not a critical problem */ @@ -1397,6 +1397,8 @@ static int mysql_prepare_table(THD *thd, HA_CREATE_INFO *create_info, length); push_warning(thd, MYSQL_ERROR::WARN_LEVEL_WARN, ER_TOO_LONG_KEY, warn_buff); + /* Align key length to multibyte char boundary */ + length-= length % sql_field->charset->mbmaxlen; } else {