# ==== Purpose ==== # # This script proves there is no deadlock between the applier and receiver # threads of a slave when relay-log-space-limit is reached. # # ==== Implementation ==== # # 1. Create a table on the master and sync it to the slave # 2. Set some debug points and vars so: # - The slave thinks the relay-log-space-limit was reached # - The slave waits before forcing a relay log rotation # - The wait time between MTS checkpoints is minimal # 3. Execute a transaction on the master # - Wait for the IO to be waiting to free space # - Wait for the SQL thread to be waiting for new events # - Sleep an extra seconds for MTS checkpoint sleep # 4. Unblock the code. # The slave should not be stuck and accept new events # 5. Cleanup # # ==== References ==== # # Bug#29842426: MUTEX DEADLOCK BETWEEN LOG_SPACE_LOCK AND LOCK_BINLOG_END_POS # --source include/have_debug_sync.inc # this issue only happened on MTS --source include/only_mts_slave_parallel_workers.inc --source include/master-slave.inc --echo # --echo # 1. Create a table on the master and sync it to the slave --source include/rpl_connection_master.inc CREATE TABLE t1 (i INT); --source include/sync_slave_sql_with_master.inc --echo # --echo # 2. Set some debug points and vars so: --echo # - The slave thinks the relay-log-space-limit was reached --echo # - The slave waits before forcing a relay log rotation --echo # - The wait time between MTS checkpoints is minimal --source include/rpl_connection_slave.inc SET @@GLOBAL.DEBUG= '+d,rpl_set_relay_log_limits'; SET @@GLOBAL.DEBUG= '+d,rpl_before_forced_rotate'; # Reduce this to a minimum --let $slave_checkpoint_period_value = `SELECT @@global.slave_checkpoint_period` SET @@GLOBAL.slave_checkpoint_period= 1; --echo # --echo # 3. Execute a transaction on the master --echo # - Wait for the IO to be waiting to free space --echo # - Wait for the SQL thread to be waiting for new events --echo # - Sleep an extra seconds for MTS checkpoint sleep --source include/rpl_connection_master.inc INSERT INTO t1 VALUES (0); --source include/rpl_connection_slave.inc --let $wait_condition=SELECT COUNT(*)=1 FROM performance_schema.threads WHERE name='thread/sql/slave_io' AND processlist_state= 'Waiting for the slave SQL thread to free enough relay log space' --source include/wait_condition.inc --let $wait_condition=SELECT COUNT(*)=1 FROM performance_schema.threads WHERE name='thread/sql/slave_sql' AND processlist_state= 'Slave has read all relay log; waiting for more updates' --source include/wait_condition.inc # The MTS checkpoint sleep on the SQL thread wait for new events # should be 0.001 seconds --sleep 2 --echo # --echo # 4. Unblock the code. --echo # The slave should not be stuck and accept new events SET @@GLOBAL.DEBUG= '-d,rpl_set_relay_log_limits'; SET DEBUG_SYNC= 'now SIGNAL signal.rpl_before_forced_rotate_continue'; SET @@GLOBAL.DEBUG= '-d,rpl_before_forced_rotate'; --source include/rpl_connection_master.inc INSERT INTO t1 VALUES (1); --source include/sync_slave_sql_with_master.inc --let $assert_text= 'There are 2 values in table t1' --let $assert_cond= [SELECT COUNT(*) AS count FROM t1, count, 1] = 2 --source include/assert.inc --echo # --echo # 5. Cleanup --replace_result $slave_checkpoint_period_value SLAVE_CHECKPOINT_PERIOD --eval SET @@GLOBAL.slave_checkpoint_period= $slave_checkpoint_period_value --source include/rpl_connection_master.inc DROP TABLE t1; --source include/rpl_end.inc