diff options
author | Teemu Ollakka <teemu.ollakka@galeracluster.com> | 2019-04-06 12:33:51 +0300 |
---|---|---|
committer | Jan Lindström <jan.lindstrom@mariadb.com> | 2019-04-06 12:33:51 +0300 |
commit | eb872ceb2710034eb507bfb7f5133022d814c59f (patch) | |
tree | 26af870c685195ed480498bebccf2603272c9fc0 /sql/wsrep_client_service.cc | |
parent | fe62ff6e1c8d6931935a0f9a10613abf93e3668f (diff) | |
download | mariadb-git-eb872ceb2710034eb507bfb7f5133022d814c59f.tar.gz |
Fixed wsrep replaying for stored procedures (#1256)mariadb-10.4.4
- Changed replaying to always allocate a separate THD object
for applying log events. This is to avoid tampering original
THD state during replay process.
- Return success from sp_instr_stmt::exec_core() if replaying
succeeds.
- Do not push warnings/errors into diagnostics area if the
transaction must be replayed. This is to avoid reporting
transient errors to the client.
Added two tests galera_sp_bf_abort, galera_sp_insert_parallel.
Wsrep-lib position updated.
Diffstat (limited to 'sql/wsrep_client_service.cc')
-rw-r--r-- | sql/wsrep_client_service.cc | 36 |
1 files changed, 27 insertions, 9 deletions
diff --git a/sql/wsrep_client_service.cc b/sql/wsrep_client_service.cc index c042a1ea051..b182691c593 100644 --- a/sql/wsrep_client_service.cc +++ b/sql/wsrep_client_service.cc @@ -250,20 +250,38 @@ void Wsrep_client_service::will_replay() enum wsrep::provider::status Wsrep_client_service::replay() { + DBUG_ASSERT(m_thd == current_thd); - Wsrep_replayer_service replayer_service(m_thd); - wsrep::provider& provider(m_thd->wsrep_cs().provider()); - mysql_mutex_lock(&m_thd->LOCK_thd_data); - m_thd->killed= NOT_KILLED; - mysql_mutex_unlock(&m_thd->LOCK_thd_data); - enum wsrep::provider::status ret= - provider.replay(m_thd->wsrep_trx().ws_handle(), &replayer_service); - replayer_service.replay_status(ret); + DBUG_ENTER("Wsrep_client_service::replay"); + + /* + Allocate separate THD for replaying to avoid tampering + original THD state during replication event applying. + */ + THD *replayer_thd= new THD(true, true); + replayer_thd->thread_stack= m_thd->thread_stack; + replayer_thd->real_id= pthread_self(); + replayer_thd->prior_thr_create_utime= + replayer_thd->start_utime= microsecond_interval_timer(); + replayer_thd->set_command(COM_SLEEP); + replayer_thd->reset_for_next_command(true); + + enum wsrep::provider::status ret; + { + Wsrep_replayer_service replayer_service(replayer_thd, m_thd); + wsrep::provider& provider(replayer_thd->wsrep_cs().provider()); + ret= provider.replay(replayer_thd->wsrep_trx().ws_handle(), + &replayer_service); + replayer_service.replay_status(ret); + } + + delete replayer_thd; + mysql_mutex_lock(&LOCK_wsrep_replaying); --wsrep_replaying; mysql_cond_broadcast(&COND_wsrep_replaying); mysql_mutex_unlock(&LOCK_wsrep_replaying); - return ret; + DBUG_RETURN(ret); } void Wsrep_client_service::wait_for_replayers(wsrep::unique_lock<wsrep::mutex>& lock) |