diff options
author | Pedro Gomes <pedro.gomes@oracle.com> | 2013-02-15 21:57:35 +0000 |
---|---|---|
committer | Pedro Gomes <pedro.gomes@oracle.com> | 2013-02-15 21:57:35 +0000 |
commit | 7e8c887786dc76c0057acb5a73ff4355a4ea87b1 (patch) | |
tree | 76e93daf7767dbb400bbf4724d4e52c5f9285a16 /sql/sql_repl.cc | |
parent | 795b8acc2a50e9d47945841ce2c3f08d4ad9db03 (diff) | |
download | mariadb-git-7e8c887786dc76c0057acb5a73ff4355a4ea87b1.tar.gz |
BUG#13545447: RPL_ROTATE_LOGS FAILS DUE TO CONCURRENCY ISSUES IN REP. CODE
In method mysql_binlog_send, right after detecting a EOF in the
read event loop, and before deciding if we should change to a new
binlog file there is a execution window where new events can be
written to the binlog and a rotation can happen. When reaching
the test, the function will then change to a new binlog file
ignoring all the events written in this window. This will result
in events not being replicated.
Only when the binlog is detected as deactivated in the event loop
of the dump thread, can we really know that no more events
remain. For this reason, this test is now made under the log lock
in the beginning of the event loop when reading the events.
Diffstat (limited to 'sql/sql_repl.cc')
-rw-r--r-- | sql/sql_repl.cc | 21 |
1 files changed, 17 insertions, 4 deletions
diff --git a/sql/sql_repl.cc b/sql/sql_repl.cc index c15382c669e..6894eaa48b5 100644 --- a/sql/sql_repl.cc +++ b/sql/sql_repl.cc @@ -1,5 +1,5 @@ /* - Copyright (c) 2000, 2011, Oracle and/or its affiliates. All rights reserved. + Copyright (c) 2000, 2013, Oracle and/or its affiliates. All rights reserved. This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by @@ -548,7 +548,10 @@ impossible position"; while (!net->error && net->vio != 0 && !thd->killed) { my_off_t prev_pos= pos; - while (!(error = Log_event::read_log_event(&log, packet, log_lock))) + bool is_active_binlog= false; + while (!(error= Log_event::read_log_event(&log, packet, log_lock, + log_file_name, + &is_active_binlog))) { prev_pos= my_b_tell(&log); #ifndef DBUG_OFF @@ -624,6 +627,13 @@ impossible position"; error=LOG_READ_EOF; } + DBUG_EXECUTE_IF("wait_after_binlog_EOF", + { + const char act[]= "now wait_for signal.rotate_finished"; + DBUG_ASSERT(!debug_sync_set_action(current_thd, + STRING_WITH_LEN(act))); + };); + /* TODO: now that we are logging the offset, check to make sure the recorded offset and the actual match. @@ -634,8 +644,11 @@ impossible position"; if (test_for_non_eof_log_read_errors(error, &errmsg)) goto err; - if (!(flags & BINLOG_DUMP_NON_BLOCK) && - mysql_bin_log.is_active(log_file_name)) + /* + We should only move to the next binlog when the last read event + came from a already deactivated binlog. + */ + if (!(flags & BINLOG_DUMP_NON_BLOCK) && is_active_binlog) { /* Block until there is more data in the log |