Skip to content

Commit ec47bea

Browse files
committed
Merge parallel replication async deadlock kill into 10.2.
Conflicts: sql/mysqld.cc sql/slave.cc
2 parents 06b7fce + 7e0c9de commit ec47bea

File tree

9 files changed

+269
-47
lines changed

9 files changed

+269
-47
lines changed

mysql-test/suite/perfschema/r/threads_mysql.result

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -44,6 +44,16 @@ processlist_info NULL
4444
unified_parent_thread_id unified parent_thread_id
4545
role NULL
4646
instrumented YES
47+
name thread/sql/slave_background
48+
type BACKGROUND
49+
processlist_user NULL
50+
processlist_host NULL
51+
processlist_db NULL
52+
processlist_command NULL
53+
processlist_info NULL
54+
unified_parent_thread_id unified parent_thread_id
55+
role NULL
56+
instrumented YES
4757
CREATE TEMPORARY TABLE t1 AS
4858
SELECT thread_id FROM performance_schema.threads
4959
WHERE name LIKE 'thread/sql%';
@@ -105,4 +115,5 @@ parent_thread_name child_thread_name
105115
thread/sql/event_scheduler thread/sql/event_worker
106116
thread/sql/main thread/sql/one_connection
107117
thread/sql/main thread/sql/signal_handler
118+
thread/sql/main thread/sql/slave_background
108119
thread/sql/one_connection thread/sql/event_scheduler

sql/mysqld.cc

Lines changed: 18 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -383,7 +383,7 @@ static bool binlog_format_used= false;
383383
LEX_STRING opt_init_connect, opt_init_slave;
384384
mysql_cond_t COND_thread_cache;
385385
static mysql_cond_t COND_flush_thread_cache;
386-
mysql_cond_t COND_slave_init;
386+
mysql_cond_t COND_slave_background;
387387
static DYNAMIC_ARRAY all_options;
388388

389389
/* Global variables */
@@ -754,7 +754,7 @@ mysql_mutex_t
754754
LOCK_crypt,
755755
LOCK_global_system_variables,
756756
LOCK_user_conn, LOCK_slave_list, LOCK_active_mi,
757-
LOCK_connection_count, LOCK_error_messages, LOCK_slave_init;
757+
LOCK_connection_count, LOCK_error_messages, LOCK_slave_background;
758758

759759
mysql_mutex_t LOCK_stats, LOCK_global_user_client_stats,
760760
LOCK_global_table_stats, LOCK_global_index_stats;
@@ -937,7 +937,7 @@ PSI_mutex_key key_LOCK_gtid_waiting;
937937

938938
PSI_mutex_key key_LOCK_after_binlog_sync;
939939
PSI_mutex_key key_LOCK_prepare_ordered, key_LOCK_commit_ordered,
940-
key_LOCK_slave_init;
940+
key_LOCK_slave_background;
941941
PSI_mutex_key key_TABLE_SHARE_LOCK_share;
942942

943943
static PSI_mutex_info all_server_mutexes[]=
@@ -1003,7 +1003,7 @@ static PSI_mutex_info all_server_mutexes[]=
10031003
{ &key_LOCK_prepare_ordered, "LOCK_prepare_ordered", PSI_FLAG_GLOBAL},
10041004
{ &key_LOCK_after_binlog_sync, "LOCK_after_binlog_sync", PSI_FLAG_GLOBAL},
10051005
{ &key_LOCK_commit_ordered, "LOCK_commit_ordered", PSI_FLAG_GLOBAL},
1006-
{ &key_LOCK_slave_init, "LOCK_slave_init", PSI_FLAG_GLOBAL},
1006+
{ &key_LOCK_slave_background, "LOCK_slave_background", PSI_FLAG_GLOBAL},
10071007
{ &key_LOG_INFO_lock, "LOG_INFO::lock", 0},
10081008
{ &key_LOCK_thread_count, "LOCK_thread_count", PSI_FLAG_GLOBAL},
10091009
{ &key_LOCK_thread_cache, "LOCK_thread_cache", PSI_FLAG_GLOBAL},
@@ -1060,7 +1060,7 @@ PSI_cond_key key_TC_LOG_MMAP_COND_queue_busy;
10601060
PSI_cond_key key_COND_rpl_thread_queue, key_COND_rpl_thread,
10611061
key_COND_rpl_thread_stop, key_COND_rpl_thread_pool,
10621062
key_COND_parallel_entry, key_COND_group_commit_orderer,
1063-
key_COND_prepare_ordered, key_COND_slave_init;
1063+
key_COND_prepare_ordered, key_COND_slave_background;
10641064
PSI_cond_key key_COND_wait_gtid, key_COND_gtid_ignore_duplicates;
10651065

10661066
static PSI_cond_info all_server_conds[]=
@@ -1110,7 +1110,7 @@ static PSI_cond_info all_server_conds[]=
11101110
{ &key_COND_parallel_entry, "COND_parallel_entry", 0},
11111111
{ &key_COND_group_commit_orderer, "COND_group_commit_orderer", 0},
11121112
{ &key_COND_prepare_ordered, "COND_prepare_ordered", 0},
1113-
{ &key_COND_slave_init, "COND_slave_init", 0},
1113+
{ &key_COND_slave_background, "COND_slave_background", 0},
11141114
{ &key_COND_start_thread, "COND_start_thread", PSI_FLAG_GLOBAL},
11151115
{ &key_COND_wait_gtid, "COND_wait_gtid", 0},
11161116
{ &key_COND_gtid_ignore_duplicates, "COND_gtid_ignore_duplicates", 0}
@@ -1119,7 +1119,7 @@ static PSI_cond_info all_server_conds[]=
11191119
PSI_thread_key key_thread_bootstrap, key_thread_delayed_insert,
11201120
key_thread_handle_manager, key_thread_main,
11211121
key_thread_one_connection, key_thread_signal_hand,
1122-
key_thread_slave_init, key_rpl_parallel_thread;
1122+
key_thread_slave_background, key_rpl_parallel_thread;
11231123

11241124
static PSI_thread_info all_server_threads[]=
11251125
{
@@ -1145,7 +1145,7 @@ static PSI_thread_info all_server_threads[]=
11451145
{ &key_thread_main, "main", PSI_FLAG_GLOBAL},
11461146
{ &key_thread_one_connection, "one_connection", 0},
11471147
{ &key_thread_signal_hand, "signal_handler", PSI_FLAG_GLOBAL},
1148-
{ &key_thread_slave_init, "slave_init", PSI_FLAG_GLOBAL},
1148+
{ &key_thread_slave_background, "slave_background", PSI_FLAG_GLOBAL},
11491149
{ &key_rpl_parallel_thread, "rpl_parallel_thread", 0}
11501150
};
11511151

@@ -2351,8 +2351,8 @@ static void clean_up_mutexes()
23512351
mysql_cond_destroy(&COND_prepare_ordered);
23522352
mysql_mutex_destroy(&LOCK_after_binlog_sync);
23532353
mysql_mutex_destroy(&LOCK_commit_ordered);
2354-
mysql_mutex_destroy(&LOCK_slave_init);
2355-
mysql_cond_destroy(&COND_slave_init);
2354+
mysql_mutex_destroy(&LOCK_slave_background);
2355+
mysql_cond_destroy(&COND_slave_background);
23562356
DBUG_VOID_RETURN;
23572357
}
23582358

@@ -4738,9 +4738,9 @@ static int init_thread_environment()
47384738
MY_MUTEX_INIT_SLOW);
47394739
mysql_mutex_init(key_LOCK_commit_ordered, &LOCK_commit_ordered,
47404740
MY_MUTEX_INIT_SLOW);
4741-
mysql_mutex_init(key_LOCK_slave_init, &LOCK_slave_init,
4741+
mysql_mutex_init(key_LOCK_slave_background, &LOCK_slave_background,
47424742
MY_MUTEX_INIT_SLOW);
4743-
mysql_cond_init(key_COND_slave_init, &COND_slave_init, NULL);
4743+
mysql_cond_init(key_COND_slave_background, &COND_slave_background, NULL);
47444744

47454745
#ifdef HAVE_OPENSSL
47464746
mysql_mutex_init(key_LOCK_des_key_file,
@@ -10172,6 +10172,9 @@ PSI_stage_info stage_waiting_for_rpl_thread_pool= { 0, "Waiting while replicatio
1017210172
PSI_stage_info stage_master_gtid_wait_primary= { 0, "Waiting in MASTER_GTID_WAIT() (primary waiter)", 0};
1017310173
PSI_stage_info stage_master_gtid_wait= { 0, "Waiting in MASTER_GTID_WAIT()", 0};
1017410174
PSI_stage_info stage_gtid_wait_other_connection= { 0, "Waiting for other master connection to process GTID received on multiple master connections", 0};
10175+
PSI_stage_info stage_slave_background_process_request= { 0, "Processing requests", 0};
10176+
PSI_stage_info stage_slave_background_wait_request= { 0, "Waiting for requests", 0};
10177+
PSI_stage_info stage_waiting_for_deadlock_kill= { 0, "Waiting for parallel replication deadlock handling to complete", 0};
1017510178

1017610179
#ifdef HAVE_PSI_INTERFACE
1017710180

@@ -10296,7 +10299,9 @@ PSI_stage_info *all_server_stages[]=
1029610299
& stage_waiting_to_get_readlock,
1029710300
& stage_master_gtid_wait_primary,
1029810301
& stage_master_gtid_wait,
10299-
& stage_gtid_wait_other_connection
10302+
& stage_gtid_wait_other_connection,
10303+
& stage_slave_background_process_request,
10304+
& stage_slave_background_wait_request
1030010305
};
1030110306

1030210307
PSI_socket_key key_socket_tcpip, key_socket_unix, key_socket_client_connection;

sql/mysqld.h

Lines changed: 7 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -342,8 +342,8 @@ extern PSI_cond_key key_COND_wait_gtid, key_COND_gtid_ignore_duplicates;
342342

343343
extern PSI_thread_key key_thread_bootstrap, key_thread_delayed_insert,
344344
key_thread_handle_manager, key_thread_kill_server, key_thread_main,
345-
key_thread_one_connection, key_thread_signal_hand, key_thread_slave_init,
346-
key_rpl_parallel_thread;
345+
key_thread_one_connection, key_thread_signal_hand,
346+
key_thread_slave_background, key_rpl_parallel_thread;
347347

348348
extern PSI_file_key key_file_binlog, key_file_binlog_index, key_file_casetest,
349349
key_file_dbopt, key_file_des_key_file, key_file_ERRMSG, key_select_to_file,
@@ -489,6 +489,9 @@ extern PSI_stage_info stage_waiting_for_rpl_thread_pool;
489489
extern PSI_stage_info stage_master_gtid_wait_primary;
490490
extern PSI_stage_info stage_master_gtid_wait;
491491
extern PSI_stage_info stage_gtid_wait_other_connection;
492+
extern PSI_stage_info stage_slave_background_process_request;
493+
extern PSI_stage_info stage_slave_background_wait_request;
494+
extern PSI_stage_info stage_waiting_for_deadlock_kill;
492495

493496
#ifdef HAVE_PSI_STATEMENT_INTERFACE
494497
/**
@@ -558,7 +561,7 @@ extern mysql_mutex_t
558561
LOCK_slave_list, LOCK_active_mi, LOCK_manager,
559562
LOCK_global_system_variables, LOCK_user_conn,
560563
LOCK_prepared_stmt_count, LOCK_error_messages, LOCK_connection_count,
561-
LOCK_slave_init;
564+
LOCK_slave_background;
562565
extern MYSQL_PLUGIN_IMPORT mysql_mutex_t LOCK_thread_count;
563566
extern mysql_mutex_t LOCK_start_thread;
564567
#ifdef HAVE_OPENSSL
@@ -571,7 +574,7 @@ extern mysql_rwlock_t LOCK_grant, LOCK_sys_init_connect, LOCK_sys_init_slave;
571574
extern mysql_rwlock_t LOCK_system_variables_hash;
572575
extern mysql_cond_t COND_thread_count, COND_start_thread;
573576
extern mysql_cond_t COND_manager;
574-
extern mysql_cond_t COND_slave_init;
577+
extern mysql_cond_t COND_slave_background;
575578
extern int32 thread_running;
576579
extern int32 thread_count, service_thread_count;
577580

sql/rpl_parallel.cc

Lines changed: 26 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -107,6 +107,25 @@ handle_queued_pos_update(THD *thd, rpl_parallel_thread::queued_event *qev)
107107
}
108108

109109

110+
/*
111+
Wait for any pending deadlock kills. Since deadlock kills happen
112+
asynchronously, we need to be sure they will be completed before starting a
113+
new transaction. Otherwise the new transaction might suffer a spurious kill.
114+
*/
115+
static void
116+
wait_for_pending_deadlock_kill(THD *thd, rpl_group_info *rgi)
117+
{
118+
PSI_stage_info old_stage;
119+
120+
mysql_mutex_lock(&thd->LOCK_wakeup_ready);
121+
thd->ENTER_COND(&thd->COND_wakeup_ready, &thd->LOCK_wakeup_ready,
122+
&stage_waiting_for_deadlock_kill, &old_stage);
123+
while (rgi->killed_for_retry == rpl_group_info::RETRY_KILL_PENDING)
124+
mysql_cond_wait(&thd->COND_wakeup_ready, &thd->LOCK_wakeup_ready);
125+
thd->EXIT_COND(&old_stage);
126+
}
127+
128+
110129
static void
111130
finish_event_group(rpl_parallel_thread *rpt, uint64 sub_id,
112131
rpl_parallel_entry *entry, rpl_group_info *rgi)
@@ -212,6 +231,8 @@ finish_event_group(rpl_parallel_thread *rpt, uint64 sub_id,
212231
entry->stop_on_error_sub_id= sub_id;
213232
mysql_mutex_unlock(&entry->LOCK_parallel_entry);
214233

234+
if (rgi->killed_for_retry == rpl_group_info::RETRY_KILL_PENDING)
235+
wait_for_pending_deadlock_kill(thd, rgi);
215236
thd->clear_error();
216237
thd->reset_killed();
217238
/*
@@ -610,7 +631,6 @@ convert_kill_to_deadlock_error(rpl_group_info *rgi)
610631
{
611632
thd->clear_error();
612633
my_error(ER_LOCK_DEADLOCK, MYF(0));
613-
rgi->killed_for_retry= false;
614634
thd->reset_killed();
615635
}
616636
}
@@ -701,14 +721,16 @@ retry_event_group(rpl_group_info *rgi, rpl_parallel_thread *rpt,
701721
thd->wait_for_commit_ptr->unregister_wait_for_prior_commit();
702722
DBUG_EXECUTE_IF("inject_mdev8031", {
703723
/* Simulate that we get deadlock killed at this exact point. */
704-
rgi->killed_for_retry= true;
724+
rgi->killed_for_retry= rpl_group_info::RETRY_KILL_KILLED;
705725
mysql_mutex_lock(&thd->LOCK_thd_data);
706726
thd->killed= KILL_CONNECTION;
707727
mysql_mutex_unlock(&thd->LOCK_thd_data);
708728
});
709729
rgi->cleanup_context(thd, 1);
730+
wait_for_pending_deadlock_kill(thd, rgi);
710731
thd->reset_killed();
711732
thd->clear_error();
733+
rgi->killed_for_retry = rpl_group_info::RETRY_KILL_NONE;
712734

713735
/*
714736
If we retry due to a deadlock kill that occurred during the commit step, we
@@ -847,7 +869,7 @@ retry_event_group(rpl_group_info *rgi, rpl_parallel_thread *rpt,
847869
{
848870
/* Simulate that we get deadlock killed during open_binlog(). */
849871
thd->reset_for_next_command();
850-
rgi->killed_for_retry= true;
872+
rgi->killed_for_retry= rpl_group_info::RETRY_KILL_KILLED;
851873
mysql_mutex_lock(&thd->LOCK_thd_data);
852874
thd->killed= KILL_CONNECTION;
853875
mysql_mutex_unlock(&thd->LOCK_thd_data);
@@ -1747,7 +1769,7 @@ rpl_parallel_thread::get_rgi(Relay_log_info *rli, Gtid_log_event *gtid_ev,
17471769
rgi->relay_log= rli->last_inuse_relaylog;
17481770
rgi->retry_start_offset= rli->future_event_relay_log_pos-event_size;
17491771
rgi->retry_event_count= 0;
1750-
rgi->killed_for_retry= false;
1772+
rgi->killed_for_retry= rpl_group_info::RETRY_KILL_NONE;
17511773

17521774
return rgi;
17531775
}

sql/rpl_rli.h

Lines changed: 6 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -713,7 +713,12 @@ struct rpl_group_info
713713
*/
714714
SPECULATE_WAIT
715715
} speculation;
716-
bool killed_for_retry;
716+
enum enum_retry_killed {
717+
RETRY_KILL_NONE = 0,
718+
RETRY_KILL_PENDING,
719+
RETRY_KILL_KILLED
720+
};
721+
uchar killed_for_retry;
717722

718723
rpl_group_info(Relay_log_info *rli_);
719724
~rpl_group_info();

0 commit comments

Comments
 (0)