summaryrefslogtreecommitdiff
path: root/sql/sql_class.cc
diff options
context:
space:
mode:
Diffstat (limited to 'sql/sql_class.cc')
-rw-r--r--sql/sql_class.cc150
1 files changed, 104 insertions, 46 deletions
diff --git a/sql/sql_class.cc b/sql/sql_class.cc
index 4be28457859..c8347d0f585 100644
--- a/sql/sql_class.cc
+++ b/sql/sql_class.cc
@@ -337,17 +337,6 @@ void thd_set_killed(THD *thd)
}
/**
- Clear errors from the previous THD
-
- @param thd THD object
-*/
-void thd_clear_errors(THD *thd)
-{
- my_errno= 0;
- thd->mysys_var->abort= 0;
-}
-
-/**
Set thread stack in THD object
@param thd Thread object
@@ -456,7 +445,7 @@ my_socket thd_get_fd(THD *thd)
{
return mysql_socket_getfd(thd->net.vio->mysql_socket);
}
-#endif
+#endif /* ONLY_FOR_MYSQL_CLOSED_SOURCE_SCHEDULED */
/**
Get current THD object from thread local data
@@ -469,6 +458,18 @@ THD *thd_get_current_thd()
}
/**
+ Clear errors from the previous THD
+
+ @param thd THD object
+*/
+void thd_clear_errors(THD *thd)
+{
+ my_errno= 0;
+ thd->mysys_var->abort= 0;
+}
+
+
+/**
Get thread attributes for connection threads
@retval Reference to thread attribute for connection threads
@@ -845,7 +846,7 @@ extern "C" void thd_kill_timeout(THD* thd)
}
-THD::THD(bool is_wsrep_applier)
+THD::THD(my_thread_id id, bool is_wsrep_applier)
:Statement(&main_lex, &main_mem_root, STMT_CONVENTIONAL_EXECUTION,
/* statement id */ 0),
rli_fake(0), rgi_fake(0), rgi_slave(NULL),
@@ -854,17 +855,13 @@ THD::THD(bool is_wsrep_applier)
binlog_unsafe_warning_flags(0),
binlog_table_maps(0),
table_map_for_update(0),
- arg_of_last_insert_id_function(FALSE),
- first_successful_insert_id_in_prev_stmt(0),
- first_successful_insert_id_in_prev_stmt_for_binlog(0),
- first_successful_insert_id_in_cur_stmt(0),
- stmt_depends_on_first_successful_insert_id_in_prev_stmt(FALSE),
m_examined_row_count(0),
accessed_rows_and_keys(0),
m_digest(NULL),
m_statement_psi(NULL),
m_idle_psi(NULL),
- thread_id(0),
+ thread_id(id),
+ thread_dbug_id(id),
os_thread_id(0),
global_disable_checkpoint(0),
failed_com_change_user(0),
@@ -910,6 +907,7 @@ THD::THD(bool is_wsrep_applier)
set_current_thd(this);
status_var.local_memory_used= sizeof(THD);
status_var.global_memory_used= 0;
+ variables.pseudo_thread_id= thread_id;
main_da.init();
/*
@@ -973,14 +971,12 @@ THD::THD(bool is_wsrep_applier)
#ifndef DBUG_OFF
dbug_sentry=THD_SENTRY_MAGIC;
#endif
-#ifndef EMBEDDED_LIBRARY
mysql_audit_init_thd(this);
-#endif
net.vio=0;
net.buff= 0;
client_capabilities= 0; // minimalistic client
system_thread= NON_SYSTEM_THREAD;
- cleanup_done= abort_on_warning= 0;
+ cleanup_done= free_connection_done= abort_on_warning= 0;
peer_port= 0; // For SHOW PROCESSLIST
transaction.m_pending_rows_event= 0;
transaction.on= 1;
@@ -1003,7 +999,6 @@ THD::THD(bool is_wsrep_applier)
/* Variables with default values */
proc_info="login";
where= THD::DEFAULT_WHERE;
- variables.server_id = global_system_variables.server_id;
slave_net = 0;
m_command=COM_CONNECT;
*scramble= '\0';
@@ -1064,7 +1059,6 @@ THD::THD(bool is_wsrep_applier)
tmp= (ulong) (my_rnd(&sql_rand) * 0xffffffff);
my_rnd_init(&rand, tmp + (ulong) &rand, tmp + (ulong) ::global_query_id);
substitute_null_with_insert_id = FALSE;
- thr_lock_info_init(&lock_info); /* safety: will be reset after start */
lock_info.mysql_thd= (void *)this;
m_token_array= NULL;
@@ -1425,10 +1419,16 @@ void THD::init(void)
reset_binlog_local_stmt_filter();
set_status_var_init();
bzero((char *) &org_status_var, sizeof(org_status_var));
+ status_in_global= 0;
start_bytes_received= 0;
last_commit_gtid.seq_no= 0;
last_stmt= NULL;
- status_in_global= 0;
+ /* Reset status of last insert id */
+ arg_of_last_insert_id_function= FALSE;
+ stmt_depends_on_first_successful_insert_id_in_prev_stmt= FALSE;
+ first_successful_insert_id_in_prev_stmt= 0;
+ first_successful_insert_id_in_prev_stmt_for_binlog= 0;
+ first_successful_insert_id_in_cur_stmt= 0;
#ifdef WITH_WSREP
wsrep_exec_mode= wsrep_applier ? REPL_RECV : LOCAL_STATE;
wsrep_conflict_state= NO_CONFLICT;
@@ -1547,12 +1547,14 @@ void THD::init_for_queries()
void THD::change_user(void)
{
- add_status_to_global();
+ if (!status_in_global) // Reset in init()
+ add_status_to_global();
- cleanup();
- reset_killed();
+ if (!cleanup_done)
+ cleanup();
cleanup_done= 0;
- status_in_global= 0;
+ reset_killed();
+ thd_clear_errors(this);
init();
stmt_map.reset();
my_hash_init(&user_vars, system_charset_info, USER_VARS_HASH_SIZE, 0, 0,
@@ -1616,6 +1618,8 @@ void THD::cleanup(void)
my_hash_free(&user_vars);
sp_cache_clear(&sp_proc_cache);
sp_cache_clear(&sp_func_cache);
+ auto_inc_intervals_forced.empty();
+ auto_inc_intervals_in_cur_stmt_for_binlog.empty();
mysql_ull_cleanup(this);
/* All metadata locks must have been released by now. */
@@ -1627,6 +1631,63 @@ void THD::cleanup(void)
}
+/*
+ Free all connection related resources associated with a THD.
+ This is used when we put a thread into the thread cache.
+ After this call should either call ~THD or reset_for_reuse() depending on
+ circumstances.
+*/
+
+void THD::free_connection()
+{
+ DBUG_ASSERT(free_connection_done == 0);
+ my_free(db);
+ db= NULL;
+#ifndef EMBEDDED_LIBRARY
+ if (net.vio)
+ vio_delete(net.vio);
+ net.vio= 0;
+ net_end(&net);
+#endif
+ ha_close_connection(this);
+ plugin_thdvar_cleanup(this);
+ mysql_audit_free_thd(this);
+ main_security_ctx.destroy();
+ /* close all prepared statements, to save memory */
+ stmt_map.reset();
+ free_connection_done= 1;
+ profiling.restart(); // Reset profiling
+}
+
+/*
+ Reset thd for reuse by another connection
+ This is only used for user connections, so the following variables doesn't
+ have to be reset:
+ - Replication (slave) variables.
+ - Variables not reset between each statements. See reset_for_next_command.
+*/
+
+void THD::reset_for_reuse()
+{
+ mysql_audit_init_thd(this);
+ change_user(); // Calls cleanup() & init()
+ get_stmt_da()->reset_diagnostics_area();
+ main_security_ctx.init();
+ failed_com_change_user= 0;
+ is_fatal_error= 0;
+ client_capabilities= 0;
+ peer_port= 0;
+ query_name_consts= 0; // Safety
+ abort_on_warning= 0;
+ free_connection_done= 0;
+ m_command= COM_CONNECT;
+ profiling.reset();
+#ifdef SIGNAL_WITH_VIO_CLOSE
+ active_vio = 0;
+#endif
+}
+
+
THD::~THD()
{
THD *orig_thd= current_thd;
@@ -1653,26 +1714,15 @@ THD::~THD()
mysql_mutex_lock(&LOCK_wsrep_thd);
mysql_mutex_unlock(&LOCK_wsrep_thd);
mysql_mutex_destroy(&LOCK_wsrep_thd);
- if (wsrep_rgi) delete wsrep_rgi;
-#endif
- /* Close connection */
-#ifndef EMBEDDED_LIBRARY
- if (net.vio)
- vio_delete(net.vio);
- net_end(&net);
+ delete wsrep_rgi;
#endif
- stmt_map.reset(); /* close all prepared statements */
+ if (!free_connection_done)
+ free_connection();
if (!cleanup_done)
cleanup();
mdl_context.destroy();
- ha_close_connection(this);
- mysql_audit_release(this);
- plugin_thdvar_cleanup(this);
- main_security_ctx.destroy();
- my_free(db);
- db= NULL;
free_root(&transaction.mem_root,MYF(0));
mysql_cond_destroy(&COND_wakeup_ready);
mysql_mutex_destroy(&LOCK_wakeup_ready);
@@ -1692,7 +1742,6 @@ THD::~THD()
rli_fake= NULL;
}
- mysql_audit_free_thd(this);
if (rgi_slave)
rgi_slave->cleanup_after_session();
my_free(semisync_info);
@@ -2089,7 +2138,16 @@ bool THD::store_globals()
Let mysqld define the thread id (not mysys)
This allows us to move THD to different threads if needed.
*/
- mysys_var->id= thread_id;
+ mysys_var->id= thread_id;
+
+ /* thread_dbug_id should not change for a THD */
+ if (!thread_dbug_id)
+ thread_dbug_id= mysys_var->dbug_id;
+ else
+ {
+ /* This only changes if we are using pool-of-threads */
+ mysys_var->dbug_id= thread_dbug_id;
+ }
#ifdef __NR_gettid
os_thread_id= (uint32)syscall(__NR_gettid);
#else
@@ -2106,7 +2164,7 @@ bool THD::store_globals()
We have to call thr_lock_info_init() again here as THD may have been
created in another thread
*/
- thr_lock_info_init(&lock_info);
+ thr_lock_info_init(&lock_info, mysys_var);
return 0;
}