diff options
Diffstat (limited to 'sql/sql_rename.cc')
-rw-r--r-- | sql/sql_rename.cc | 26 |
1 files changed, 22 insertions, 4 deletions
diff --git a/sql/sql_rename.cc b/sql/sql_rename.cc index 866d82377c0..f5e1b8988f3 100644 --- a/sql/sql_rename.cc +++ b/sql/sql_rename.cc @@ -144,10 +144,13 @@ bool mysql_rename_tables(THD *thd, TABLE_LIST *table_list, bool silent) } } - VOID(pthread_mutex_lock(&LOCK_open)); - if (lock_table_names(thd, table_list)) + pthread_mutex_lock(&LOCK_open); + if (lock_table_names_exclusively(thd, table_list)) + { + pthread_mutex_unlock(&LOCK_open); goto err; - + } + error=0; if ((ren_table=rename_tables(thd,table_list,0))) { @@ -170,6 +173,17 @@ bool mysql_rename_tables(THD *thd, TABLE_LIST *table_list, bool silent) error= 1; } + /* + An exclusive lock on table names is satisfactory to ensure + no other thread accesses this table. + However, NDB assumes that handler::rename_tables is called under + LOCK_open. And it indeed is, from ALTER TABLE. + TODO: remove this limitation. + We still should unlock LOCK_open as early as possible, to provide + higher concurrency - query_cache_invalidate can take minutes to + complete. + */ + pthread_mutex_unlock(&LOCK_open); /* Lets hope this doesn't fail as the result will be messy */ if (!silent && !error) @@ -178,10 +192,14 @@ bool mysql_rename_tables(THD *thd, TABLE_LIST *table_list, bool silent) send_ok(thd); } + if (!error) + query_cache_invalidate3(thd, table_list, 0); + + pthread_mutex_lock(&LOCK_open); unlock_table_names(thd, table_list, (TABLE_LIST*) 0); + pthread_mutex_unlock(&LOCK_open); err: - pthread_mutex_unlock(&LOCK_open); /* enable logging back if needed */ if (disable_logs) { |