List:Commits« Previous MessageNext Message »
From:Jon Olav Hauglid Date:September 13 2010 4:59pm
Subject:bzr commit into mysql-5.5-runtime branch (jon.hauglid:3136) Bug#56595
View as plain text  
#At file:///export/home/x/mysql-5.5-runtime-bug56595/ based on revid:jon.hauglid@stripped

 3136 Jon Olav Hauglid	2010-09-13
      Bug #56595 RENAME TABLE causes assert on OS X
      
      The problem was that RENAME TABLE caused an assert if the system variable
      lower_case_table_names was 2 (default on Mac OS X) and the old table name
      was given in upper case. This caused lowercase_table2.test to fail.
      
      The assert checks that an exclusive metadata lock is held by the connection
      trying to do RENAME TABLE - specificially during updates of table triggers.
      The assert was triggered since the check is case sensitive and the lock
      was held on the normalized (lower case) version of the table name.
      
      This patch fixes the problem by making sure a normalized version of the
      table name is used for the metadata lock check, while using a non-normalized
      version of the table name for the rename of trigger files. The same is done
      for ALTER TABLE ... RENAME.
      
      No test case added since this problem is already covered by 
      lowercase_table2.test

    modified:
      sql/sql_rename.cc
      sql/sql_table.cc
      sql/sql_trigger.cc
      sql/sql_trigger.h
=== modified file 'sql/sql_rename.cc'
--- a/sql/sql_rename.cc	2010-08-10 11:16:44 +0000
+++ b/sql/sql_rename.cc	2010-09-13 16:59:50 +0000
@@ -284,7 +284,8 @@ do_rename(THD *thd, TABLE_LIST *ren_tabl
                                      new_db, new_alias, 0)))
         {
           if ((rc= Table_triggers_list::change_table_name(thd, ren_table->db,
-                                                          old_alias,
+                                                          ren_table->alias,
+                                                          ren_table->table_name,
                                                           new_db,
                                                           new_alias)))
           {

=== modified file 'sql/sql_table.cc'
--- a/sql/sql_table.cc	2010-09-03 07:42:51 +0000
+++ b/sql/sql_table.cc	2010-09-13 16:59:50 +0000
@@ -5918,7 +5918,9 @@ bool mysql_alter_table(THD *thd,char *ne
         *fn_ext(new_name)=0;
         if (mysql_rename_table(old_db_type,db,table_name,new_db,new_alias, 0))
           error= -1;
-        else if (Table_triggers_list::change_table_name(thd, db, table_name,
+        else if (Table_triggers_list::change_table_name(thd, db,
+                                                        table_list->alias,
+                                                        table_name,
                                                         new_db, new_alias))
         {
           (void) mysql_rename_table(old_db_type, new_db, new_alias, db,
@@ -6555,7 +6557,8 @@ bool mysql_alter_table(THD *thd,char *ne
            (need_copy_table != ALTER_TABLE_METADATA_ONLY ||
             mysql_rename_table(save_old_db_type, db, table_name, new_db,
                                new_alias, NO_FRM_RENAME)) &&
-           Table_triggers_list::change_table_name(thd, db, table_name,
+           Table_triggers_list::change_table_name(thd, db, table_list->alias,
+                                                  table_name,
                                                   new_db, new_alias)))
   {
     /* Try to get everything back. */

=== modified file 'sql/sql_trigger.cc'
--- a/sql/sql_trigger.cc	2010-08-31 09:52:56 +0000
+++ b/sql/sql_trigger.cc	2010-09-13 16:59:50 +0000
@@ -1890,6 +1890,7 @@ Table_triggers_list::change_table_name_i
 */
 
 bool Table_triggers_list::change_table_name(THD *thd, const char *db,
+                                            const char *old_alias,
                                             const char *old_table,
                                             const char *new_db,
                                             const char *new_table)
@@ -1910,17 +1911,25 @@ bool Table_triggers_list::change_table_n
   DBUG_ASSERT(thd->mdl_context.is_lock_owner(MDL_key::TABLE, db, old_table,
                                              MDL_EXCLUSIVE));
 
+  /*
+    With lower_case_table_names == 1, we're always using lowercase filenames.
+    Therefore use the normalized version of the table name rather than whatever
+    case was in the SQL statement string.
+  */
+  if (lower_case_table_names == 1)
+    old_alias= old_table;
+
   DBUG_ASSERT(my_strcasecmp(table_alias_charset, db, new_db) ||
-              my_strcasecmp(table_alias_charset, old_table, new_table));
+              my_strcasecmp(table_alias_charset, old_alias, new_table));
 
-  if (Table_triggers_list::check_n_load(thd, db, old_table, &table, TRUE))
+  if (Table_triggers_list::check_n_load(thd, db, old_alias, &table, TRUE))
   {
     result= 1;
     goto end;
   }
   if (table.triggers)
   {
-    LEX_STRING old_table_name= { (char *) old_table, strlen(old_table) };
+    LEX_STRING old_table_name= { (char *) old_alias, strlen(old_alias) };
     LEX_STRING new_table_name= { (char *) new_table, strlen(new_table) };
     /*
       Since triggers should be in the same schema as their subject tables

=== modified file 'sql/sql_trigger.h'
--- a/sql/sql_trigger.h	2010-03-31 14:05:33 +0000
+++ b/sql/sql_trigger.h	2010-09-13 16:59:50 +0000
@@ -157,6 +157,7 @@ public:
                            TABLE *table, bool names_only);
   static bool drop_all_triggers(THD *thd, char *db, char *table_name);
   static bool change_table_name(THD *thd, const char *db,
+                                const char *old_alias,
                                 const char *old_table,
                                 const char *new_db,
                                 const char *new_table);


Attachment: [text/bzr-bundle] bzr/jon.hauglid@oracle.com-20100913165950-dcsdnbqof0m2frqw.bundle
Thread
bzr commit into mysql-5.5-runtime branch (jon.hauglid:3136) Bug#56595Jon Olav Hauglid13 Sep