diff options
-rw-r--r-- | include/my_dbug.h | 2 | ||||
-rw-r--r-- | sql/mysqld.cc | 33 | ||||
-rw-r--r-- | sql/sql_base.cc | 7 |
3 files changed, 33 insertions, 9 deletions
diff --git a/include/my_dbug.h b/include/my_dbug.h index a7ada40f8bc..bcf2015466d 100644 --- a/include/my_dbug.h +++ b/include/my_dbug.h @@ -89,7 +89,7 @@ extern const char* _db_get_func_(void); #define DBUG_END() _db_end_ () #define DBUG_LOCK_FILE _db_lock_file_() #define DBUG_UNLOCK_FILE _db_unlock_file_() -#define DBUG_ASSERT(A) do { _db_flush_(); assert(A); } while(0) +#define DBUG_ASSERT(A) assert(A) #define DBUG_EXPLAIN(buf,len) _db_explain_(0, (buf),(len)) #define DBUG_EXPLAIN_INITIAL(buf,len) _db_explain_init_((buf),(len)) #define DEBUGGER_OFF do { _dbug_on_= 0; } while(0) diff --git a/sql/mysqld.cc b/sql/mysqld.cc index a42d789698e..6cfe402e40e 100644 --- a/sql/mysqld.cc +++ b/sql/mysqld.cc @@ -6681,19 +6681,24 @@ static int show_rpl_status(THD *thd, SHOW_VAR *var, char *buff) static int show_slave_running(THD *thd, SHOW_VAR *var, char *buff) { Master_info *mi; + bool tmp; + var->type= SHOW_MY_BOOL; var->value= buff; + mysql_mutex_unlock(&LOCK_status); mysql_mutex_lock(&LOCK_active_mi); mi= master_info_index-> get_master_info(&thd->variables.default_master_connection, MYSQL_ERROR::WARN_LEVEL_NOTE); if (mi) - *((my_bool *)buff)= (my_bool) (mi->slave_running == - MYSQL_SLAVE_RUN_CONNECT && - mi->rli.slave_running); + tmp= (my_bool) (mi->slave_running == MYSQL_SLAVE_RUN_CONNECT && + mi->rli.slave_running); + mysql_mutex_unlock(&LOCK_active_mi); + mysql_mutex_lock(&LOCK_status); + if (mi) + *((my_bool *)buff)= tmp; else var->type= SHOW_UNDEF; - mysql_mutex_unlock(&LOCK_active_mi); return 0; } @@ -6701,17 +6706,23 @@ static int show_slave_running(THD *thd, SHOW_VAR *var, char *buff) static int show_slave_received_heartbeats(THD *thd, SHOW_VAR *var, char *buff) { Master_info *mi; + longlong tmp; + var->type= SHOW_LONGLONG; var->value= buff; + mysql_mutex_unlock(&LOCK_status); mysql_mutex_lock(&LOCK_active_mi); mi= master_info_index-> get_master_info(&thd->variables.default_master_connection, MYSQL_ERROR::WARN_LEVEL_NOTE); if (mi) - *((longlong *)buff)= mi->received_heartbeats; + tmp= mi->received_heartbeats; + mysql_mutex_unlock(&LOCK_active_mi); + mysql_mutex_lock(&LOCK_status); + if (mi) + *((longlong *)buff)= tmp; else var->type= SHOW_UNDEF; - mysql_mutex_unlock(&LOCK_active_mi); return 0; } @@ -6719,17 +6730,23 @@ static int show_slave_received_heartbeats(THD *thd, SHOW_VAR *var, char *buff) static int show_heartbeat_period(THD *thd, SHOW_VAR *var, char *buff) { Master_info *mi; + float heartbeat_period; + var->type= SHOW_CHAR; var->value= buff; + mysql_mutex_unlock(&LOCK_status); mysql_mutex_lock(&LOCK_active_mi); mi= master_info_index-> get_master_info(&thd->variables.default_master_connection, MYSQL_ERROR::WARN_LEVEL_NOTE); if (mi) - sprintf(buff, "%.3f", mi->heartbeat_period); + heartbeat_period= mi->heartbeat_period; + mysql_mutex_unlock(&LOCK_active_mi); + mysql_mutex_lock(&LOCK_status); + if (mi) + sprintf(buff, "%.3f", heartbeat_period); else var->type= SHOW_UNDEF; - mysql_mutex_unlock(&LOCK_active_mi); return 0; } diff --git a/sql/sql_base.cc b/sql/sql_base.cc index 398099acc90..1f5d9b7b270 100644 --- a/sql/sql_base.cc +++ b/sql/sql_base.cc @@ -380,6 +380,13 @@ bool table_def_init(void) #endif mysql_mutex_init(key_LOCK_open, &LOCK_open, MY_MUTEX_INIT_FAST); mysql_mutex_record_order(&LOCK_active_mi, &LOCK_open); + /* + When we delete from the table_def_cache(), the free function + table_def_free_entry() is invoked from my_hash_delete(), which calls + free_table_share(), which may unload plugins, which can remove status + variables and hence takes LOCK_status. Record this locking order here. + */ + mysql_mutex_record_order(&LOCK_open, &LOCK_status); oldest_unused_share= &end_of_unused_share; end_of_unused_share.prev= &oldest_unused_share; |