summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorNuno Carvalho <nuno.carvalho@oracle.com>2012-04-20 23:35:53 +0100
committerNuno Carvalho <nuno.carvalho@oracle.com>2012-04-20 23:35:53 +0100
commitd3968407e6f8417bf5f5483fb71279fc38e75668 (patch)
tree99feffdbf4a45c2da0724742e1fafe70911cd735
parenta7d47adf23a4ac17cc99553cf1e79968ab50e6aa (diff)
parentcdaae1692b1e74c0fdeaaece82e3350a30e3bbd2 (diff)
downloadmariadb-git-d3968407e6f8417bf5f5483fb71279fc38e75668.tar.gz
BUG#13979418: SHOW BINLOG EVENTS MAY CRASH THE SERVER
Merge from 5.1 into 5.5. Conflicts: * sql/log.h * sql/sql_repl.cc
-rw-r--r--mysql-test/suite/rpl/r/rpl_parallel_show_binlog_events_purge_logs.result13
-rw-r--r--mysql-test/suite/rpl/t/rpl_parallel_show_binlog_events_purge_logs.test35
-rw-r--r--sql/log.h5
-rw-r--r--sql/sql_repl.cc5
4 files changed, 57 insertions, 1 deletions
diff --git a/mysql-test/suite/rpl/r/rpl_parallel_show_binlog_events_purge_logs.result b/mysql-test/suite/rpl/r/rpl_parallel_show_binlog_events_purge_logs.result
new file mode 100644
index 00000000000..b69deb17c4c
--- /dev/null
+++ b/mysql-test/suite/rpl/r/rpl_parallel_show_binlog_events_purge_logs.result
@@ -0,0 +1,13 @@
+include/master-slave.inc
+[connection master]
+[connection slave]
+SET DEBUG_SYNC= 'after_show_binlog_events SIGNAL on_show_binlog_events WAIT_FOR end';
+SHOW BINLOG EVENTS;
+[connection slave1]
+SET DEBUG_SYNC= 'now WAIT_FOR on_show_binlog_events';
+FLUSH LOGS;
+SET DEBUG_SYNC= 'now SIGNAL end';
+SET DEBUG_SYNC= 'RESET';
+[connection slave]
+SET DEBUG_SYNC= 'RESET';
+include/rpl_end.inc
diff --git a/mysql-test/suite/rpl/t/rpl_parallel_show_binlog_events_purge_logs.test b/mysql-test/suite/rpl/t/rpl_parallel_show_binlog_events_purge_logs.test
new file mode 100644
index 00000000000..16d986268c9
--- /dev/null
+++ b/mysql-test/suite/rpl/t/rpl_parallel_show_binlog_events_purge_logs.test
@@ -0,0 +1,35 @@
+# BUG#13979418: SHOW BINLOG EVENTS MAY CRASH THE SERVER
+#
+# The function mysql_show_binlog_events has a local stack variable
+# 'LOG_INFO linfo;', which is assigned to thd->current_linfo, however
+# this variable goes out of scope and is destroyed before clean
+# thd->current_linfo.
+#
+# This test case runs SHOW BINLOG EVENTS and FLUSH LOGS to make sure
+# that with the fix local variable linfo is valid along all
+# mysql_show_binlog_events function scope.
+#
+--source include/have_debug_sync.inc
+--source include/master-slave.inc
+
+--echo [connection slave]
+--connection slave
+SET DEBUG_SYNC= 'after_show_binlog_events SIGNAL on_show_binlog_events WAIT_FOR end';
+--send SHOW BINLOG EVENTS
+
+--connection slave1
+--echo [connection slave1]
+SET DEBUG_SYNC= 'now WAIT_FOR on_show_binlog_events';
+FLUSH LOGS;
+SET DEBUG_SYNC= 'now SIGNAL end';
+SET DEBUG_SYNC= 'RESET';
+
+--echo [connection slave]
+--connection slave
+--disable_result_log
+--reap
+--enable_result_log
+SET DEBUG_SYNC= 'RESET';
+
+--connection master
+--source include/rpl_end.inc
diff --git a/sql/log.h b/sql/log.h
index 2e9d308e5e5..6f86d6ca5f8 100644
--- a/sql/log.h
+++ b/sql/log.h
@@ -151,6 +151,11 @@ class Relay_log_info;
extern PSI_mutex_key key_LOG_INFO_lock;
#endif
+/*
+ Note that we destroy the lock mutex in the desctructor here.
+ This means that object instances cannot be destroyed/go out of scope,
+ until we have reset thd->current_linfo to NULL;
+ */
typedef struct st_log_info
{
char log_file_name[FN_REFLEN];
diff --git a/sql/sql_repl.cc b/sql/sql_repl.cc
index 9cad81ac7ab..ffc7aa4bf8a 100644
--- a/sql/sql_repl.cc
+++ b/sql/sql_repl.cc
@@ -1737,6 +1737,8 @@ bool mysql_show_binlog_events(THD* thd)
File file = -1;
MYSQL_BIN_LOG *binary_log= NULL;
int old_max_allowed_packet= thd->variables.max_allowed_packet;
+ LOG_INFO linfo;
+
DBUG_ENTER("mysql_show_binlog_events");
Log_event::init_show_field_list(&field_list);
@@ -1779,7 +1781,6 @@ bool mysql_show_binlog_events(THD* thd)
char search_file_name[FN_REFLEN], *name;
const char *log_file_name = lex_mi->log_file_name;
mysql_mutex_t *log_lock = binary_log->get_log_lock();
- LOG_INFO linfo;
Log_event* ev;
unit->set_limit(thd->lex->current_select);
@@ -1871,6 +1872,8 @@ bool mysql_show_binlog_events(THD* thd)
mysql_mutex_unlock(log_lock);
}
+ // Check that linfo is still on the function scope.
+ DEBUG_SYNC(thd, "after_show_binlog_events");
ret= FALSE;