Commit 84ed5e1d authored by Monty's avatar Monty Committed by Sergei Golubchik

Fixed hang doing FLUSH TABLES WITH READ LOCK and parallel replication

The problem was that waiting for pause_for_ftwrl was done before
event_group was completed. This caused rpl_pause_for_ftwrl() to wait
forever during FLUSH TABLES WITH READ LOCK.
Now we only wait for FLUSH TABLES WITH READ LOCK when we are changing
to a new event group.
parent f3c65ce9
...@@ -1253,39 +1253,16 @@ handle_rpl_parallel_thread(void *arg) ...@@ -1253,39 +1253,16 @@ handle_rpl_parallel_thread(void *arg)
*/ */
rpt->batch_free(); rpt->batch_free();
for (;;) if ((events= rpt->event_queue) != NULL)
{ {
if ((events= rpt->event_queue) != NULL)
{
/*
Take next group of events from the replication pool.
This is faster than having to wakeup the pool manager thread to give
us a new event.
*/
rpt->dequeue1(events);
mysql_mutex_unlock(&rpt->LOCK_rpl_thread);
goto more_events;
}
if (!rpt->pause_for_ftwrl ||
(in_event_group && !group_rgi->parallel_entry->force_abort))
break;
/* /*
We are currently in the delicate process of pausing parallel Take next group of events from the replication pool.
replication while FLUSH TABLES WITH READ LOCK is starting. We must This is faster than having to wakeup the pool manager thread to give
not de-allocate the thread (setting rpt->current_owner= NULL) until us a new event.
rpl_unpause_after_ftwrl() has woken us up.
*/ */
mysql_mutex_lock(&rpt->current_entry->LOCK_parallel_entry); rpt->dequeue1(events);
mysql_mutex_unlock(&rpt->LOCK_rpl_thread); mysql_mutex_unlock(&rpt->LOCK_rpl_thread);
if (rpt->pause_for_ftwrl) goto more_events;
mysql_cond_wait(&rpt->current_entry->COND_parallel_entry,
&rpt->current_entry->LOCK_parallel_entry);
mysql_mutex_unlock(&rpt->current_entry->LOCK_parallel_entry);
mysql_mutex_lock(&rpt->LOCK_rpl_thread);
/*
Now loop to check again for more events available, since we released
and re-aquired the LOCK_rpl_thread mutex.
*/
} }
rpt->inuse_relaylog_refcount_update(); rpt->inuse_relaylog_refcount_update();
...@@ -1335,11 +1312,13 @@ handle_rpl_parallel_thread(void *arg) ...@@ -1335,11 +1312,13 @@ handle_rpl_parallel_thread(void *arg)
mysql_mutex_unlock(&e->LOCK_parallel_entry); mysql_mutex_unlock(&e->LOCK_parallel_entry);
mysql_mutex_lock(&rpt->LOCK_rpl_thread); mysql_mutex_lock(&rpt->LOCK_rpl_thread);
} }
rpt->current_owner= NULL; rpt->current_owner= NULL;
/* Tell wait_for_done() that we are done, if it is waiting. */ /* Tell wait_for_done() that we are done, if it is waiting. */
if (likely(rpt->current_entry) && if (likely(rpt->current_entry) &&
unlikely(rpt->current_entry->force_abort)) unlikely(rpt->current_entry->force_abort))
mysql_cond_broadcast(&rpt->COND_rpl_thread_stop); mysql_cond_broadcast(&rpt->COND_rpl_thread_stop);
rpt->current_entry= NULL; rpt->current_entry= NULL;
if (!rpt->stop) if (!rpt->stop)
rpt->pool->release_thread(rpt); rpt->pool->release_thread(rpt);
...@@ -2116,6 +2095,11 @@ rpl_parallel::find(uint32 domain_id) ...@@ -2116,6 +2095,11 @@ rpl_parallel::find(uint32 domain_id)
return e; return e;
} }
/**
Wait until all sql worker threads has stopped processing
This is called when sql thread has been killed/stopped
*/
void void
rpl_parallel::wait_for_done(THD *thd, Relay_log_info *rli) rpl_parallel::wait_for_done(THD *thd, Relay_log_info *rli)
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment