Commit 5d6e142b authored by Luis Soares's avatar Luis Soares

BUG#46166

Manual merge from mysql-5.1-bugteam into mysql-5.5-bugteam.

Conflicts
=========

Text conflict in sql/log.cc
Text conflict in sql/log.h
Text conflict in sql/slave.cc
Text conflict in sql/sql_parse.cc
Text conflict in sql/sql_priv.h
parents c872e3db bd0709cc
#
# Takes the flag as an argument:
# -- let $io_thd_injection_fault_flag=+d,fault_injection_new_file_rotate_event
# -- source include/io_thd_fault_injection.inc
#
SET @old_debug=@@global.debug;
-- disable_warnings
-- source include/stop_slave.inc
-- enable_warnings
-- eval SET GLOBAL debug="+d,$io_thd_injection_fault_flag"
START SLAVE io_thread;
-- source include/wait_for_slave_io_to_stop.inc
-- source include/wait_for_slave_io_error.inc
-- eval SET GLOBAL debug="-d,$io_thd_injection_fault_flag"
SET GLOBAL debug=@old_debug;
# restart because slave is in bad shape
-- source include/restart_mysqld.inc
# Write file to make mysql-test-run.pl expect the "crash", but don't start # Write file to make mysql-test-run.pl expect the "crash", but don't start
# it until it's told to # it until it's told to
--exec echo "wait" > $MYSQLTEST_VARDIR/tmp/mysqld.1.expect --let $_server_id= `SELECT @@server_id`
--let $_expect_file_name= $MYSQLTEST_VARDIR/tmp/mysqld.$_server_id.expect
--exec echo "wait" > $_expect_file_name
# Send shutdown to the connected server and give # Send shutdown to the connected server and give
# it 10 seconds to die before zapping it # it 10 seconds to die before zapping it
shutdown_server 10; shutdown_server 10;
# Write file to make mysql-test-run.pl start up the server again # Write file to make mysql-test-run.pl start up the server again
--exec echo "restart" > $MYSQLTEST_VARDIR/tmp/mysqld.1.expect --exec echo "restart" > $_expect_file_name
# Turn on reconnect # Turn on reconnect
--enable_reconnect --enable_reconnect
......
...@@ -2,7 +2,9 @@ call mtr.add_suppression('Attempting backtrace'); ...@@ -2,7 +2,9 @@ call mtr.add_suppression('Attempting backtrace');
call mtr.add_suppression('MSYQL_BIN_LOG::purge_logs failed to process registered files that would be purged.'); call mtr.add_suppression('MSYQL_BIN_LOG::purge_logs failed to process registered files that would be purged.');
call mtr.add_suppression('MSYQL_BIN_LOG::open failed to sync the index file'); call mtr.add_suppression('MSYQL_BIN_LOG::open failed to sync the index file');
call mtr.add_suppression('Turning logging off for the whole duration of the MySQL server process.'); call mtr.add_suppression('Turning logging off for the whole duration of the MySQL server process.');
call mtr.add_suppression('Could not open .*');
call mtr.add_suppression('MSYQL_BIN_LOG::purge_logs failed to clean registers before purging logs.'); call mtr.add_suppression('MSYQL_BIN_LOG::purge_logs failed to clean registers before purging logs.');
RESET MASTER;
flush logs; flush logs;
flush logs; flush logs;
flush logs; flush logs;
...@@ -116,11 +118,31 @@ master-bin.000011 ...@@ -116,11 +118,31 @@ master-bin.000011
# This should put the server in unsafe state and stop # This should put the server in unsafe state and stop
# accepting any command. If we inject a fault at this # accepting any command. If we inject a fault at this
# point and continue the execution the server crashes. # point and continue the execution the server crashes.
# Besides the flush command does not report an error.
# #
SET @index=LOAD_FILE('MYSQLTEST_VARDIR/mysqld.1/data//master-bin.index');
SELECT @index;
@index
master-bin.000006
master-bin.000007
master-bin.000008
master-bin.000009
master-bin.000010
master-bin.000011
# fault_injection_registering_index # fault_injection_registering_index
SET SESSION debug="+d,fault_injection_registering_index"; SET SESSION debug="+d,fault_injection_registering_index";
flush logs; flush logs;
ERROR HY000: Can't open file: './master-bin.000012' (errno: 1)
SET @index=LOAD_FILE('MYSQLTEST_VARDIR/mysqld.1/data//master-bin.index');
SELECT @index;
@index
master-bin.000006
master-bin.000007
master-bin.000008
master-bin.000009
master-bin.000010
master-bin.000011
SET @index=LOAD_FILE('MYSQLTEST_VARDIR/mysqld.1/data//master-bin.index'); SET @index=LOAD_FILE('MYSQLTEST_VARDIR/mysqld.1/data//master-bin.index');
SELECT @index; SELECT @index;
@index @index
...@@ -135,6 +157,18 @@ master-bin.000012 ...@@ -135,6 +157,18 @@ master-bin.000012
# fault_injection_updating_index # fault_injection_updating_index
SET SESSION debug="+d,fault_injection_updating_index"; SET SESSION debug="+d,fault_injection_updating_index";
flush logs; flush logs;
ERROR HY000: Can't open file: './master-bin.000013' (errno: 1)
SET @index=LOAD_FILE('MYSQLTEST_VARDIR/mysqld.1/data//master-bin.index');
SELECT @index;
@index
master-bin.000006
master-bin.000007
master-bin.000008
master-bin.000009
master-bin.000010
master-bin.000011
master-bin.000012
SET @index=LOAD_FILE('MYSQLTEST_VARDIR/mysqld.1/data//master-bin.index'); SET @index=LOAD_FILE('MYSQLTEST_VARDIR/mysqld.1/data//master-bin.index');
SELECT @index; SELECT @index;
@index @index
......
...@@ -10,9 +10,12 @@ call mtr.add_suppression('Attempting backtrace'); ...@@ -10,9 +10,12 @@ call mtr.add_suppression('Attempting backtrace');
call mtr.add_suppression('MSYQL_BIN_LOG::purge_logs failed to process registered files that would be purged.'); call mtr.add_suppression('MSYQL_BIN_LOG::purge_logs failed to process registered files that would be purged.');
call mtr.add_suppression('MSYQL_BIN_LOG::open failed to sync the index file'); call mtr.add_suppression('MSYQL_BIN_LOG::open failed to sync the index file');
call mtr.add_suppression('Turning logging off for the whole duration of the MySQL server process.'); call mtr.add_suppression('Turning logging off for the whole duration of the MySQL server process.');
call mtr.add_suppression('Could not open .*');
call mtr.add_suppression('MSYQL_BIN_LOG::purge_logs failed to clean registers before purging logs.'); call mtr.add_suppression('MSYQL_BIN_LOG::purge_logs failed to clean registers before purging logs.');
let $old=`select @@debug`; let $old=`select @@debug`;
RESET MASTER;
let $MYSQLD_DATADIR= `select @@datadir`; let $MYSQLD_DATADIR= `select @@datadir`;
let $INDEX=$MYSQLD_DATADIR/master-bin.index; let $INDEX=$MYSQLD_DATADIR/master-bin.index;
...@@ -205,12 +208,25 @@ SELECT @index; ...@@ -205,12 +208,25 @@ SELECT @index;
--echo # This should put the server in unsafe state and stop --echo # This should put the server in unsafe state and stop
--echo # accepting any command. If we inject a fault at this --echo # accepting any command. If we inject a fault at this
--echo # point and continue the execution the server crashes. --echo # point and continue the execution the server crashes.
--echo # Besides the flush command does not report an error.
--echo # --echo #
--chmod 0644 $INDEX
-- replace_result $MYSQLTEST_VARDIR MYSQLTEST_VARDIR
-- eval SET @index=LOAD_FILE('$index')
-- replace_regex /\.[\\\/]master/master/
SELECT @index;
--echo # fault_injection_registering_index --echo # fault_injection_registering_index
SET SESSION debug="+d,fault_injection_registering_index"; SET SESSION debug="+d,fault_injection_registering_index";
-- error ER_CANT_OPEN_FILE
flush logs; flush logs;
--chmod 0644 $INDEX
-- replace_result $MYSQLTEST_VARDIR MYSQLTEST_VARDIR
-- eval SET @index=LOAD_FILE('$index')
-- replace_regex /\.[\\\/]master/master/
SELECT @index;
--source include/restart_mysqld.inc --source include/restart_mysqld.inc
--chmod 0644 $INDEX --chmod 0644 $INDEX
...@@ -221,7 +237,15 @@ SELECT @index; ...@@ -221,7 +237,15 @@ SELECT @index;
--echo # fault_injection_updating_index --echo # fault_injection_updating_index
SET SESSION debug="+d,fault_injection_updating_index"; SET SESSION debug="+d,fault_injection_updating_index";
-- error ER_CANT_OPEN_FILE
flush logs; flush logs;
--chmod 0644 $INDEX
-- replace_result $MYSQLTEST_VARDIR MYSQLTEST_VARDIR
-- eval SET @index=LOAD_FILE('$index')
-- replace_regex /\.[\\\/]master/master/
SELECT @index;
--source include/restart_mysqld.inc --source include/restart_mysqld.inc
--chmod 0644 $INDEX --chmod 0644 $INDEX
......
stop slave;
drop table if exists t1,t2,t3,t4,t5,t6,t7,t8,t9;
reset master;
reset slave;
drop table if exists t1,t2,t3,t4,t5,t6,t7,t8,t9;
start slave;
#######################################################################
####################### PART 1: MASTER TESTS ##########################
#######################################################################
include/stop_slave.inc
call mtr.add_suppression("Can't generate a unique log-filename");
call mtr.add_suppression("Writing one row to the row-based binary log failed.*");
call mtr.add_suppression("Error writing file .*");
SET @old_debug= @@global.debug;
SELECT repeat('x',8192) INTO OUTFILE 'MYSQLTEST_VARDIR/tmp/bug_46166.data';
SELECT repeat('x',10) INTO OUTFILE 'MYSQLTEST_VARDIR/tmp/bug_46166-2.data';
RESET MASTER;
###################### TEST #1
FLUSH LOGS;
# assert: must show two binlogs
show binary logs;
Log_name File_size
master-bin.000001 #
master-bin.000002 #
###################### TEST #2
RESET MASTER;
SET GLOBAL debug="+d,error_unique_log_filename";
FLUSH LOGS;
ERROR HY000: Can't generate a unique log-filename master-bin.(1-999)
# assert: must show one binlog
show binary logs;
Log_name File_size
master-bin.000001 #
SET GLOBAL debug="";
RESET MASTER;
###################### TEST #3
CREATE TABLE t1 (a int);
CREATE TABLE t2 (a TEXT) Engine=InnoDB;
CREATE TABLE t4 (a TEXT);
INSERT INTO t1 VALUES (1);
RESET MASTER;
LOAD DATA INFILE 'MYSQLTEST_VARDIR/tmp/bug_46166.data' INTO TABLE t2;
# assert: must show two binlog
show binary logs;
Log_name File_size
master-bin.000001 #
master-bin.000002 #
SET GLOBAL debug="-d,error_unique_log_filename";
DELETE FROM t2;
RESET MASTER;
###################### TEST #4
SET GLOBAL debug="+d,error_unique_log_filename";
LOAD DATA INFILE 'MYSQLTEST_VARDIR/tmp/bug_46166.data' INTO TABLE t2;
ERROR HY000: Can't generate a unique log-filename master-bin.(1-999)
# assert: must show one entry
SELECT count(*) FROM t2;
count(*)
1
SET GLOBAL debug="-d,error_unique_log_filename";
DELETE FROM t2;
RESET MASTER;
###################### TEST #5
SET GLOBAL debug="+d,error_unique_log_filename";
LOAD DATA INFILE 'MYSQLTEST_VARDIR/tmp/bug_46166-2.data' INTO TABLE t2;
# assert: must show one entry
SELECT count(*) FROM t2;
count(*)
1
SET GLOBAL debug="-d,error_unique_log_filename";
DELETE FROM t2;
RESET MASTER;
###################### TEST #6
SET GLOBAL debug="+d,error_unique_log_filename";
SET AUTOCOMMIT=0;
INSERT INTO t2 VALUES ('muse');
LOAD DATA INFILE 'MYSQLTEST_VARDIR/tmp/bug_46166.data' INTO TABLE t2;
INSERT INTO t2 VALUES ('muse');
COMMIT;
ERROR HY000: Can't generate a unique log-filename master-bin.(1-999)
# assert: must show three entries
SELECT count(*) FROM t2;
count(*)
3
SET AUTOCOMMIT= 1;
SET GLOBAL debug="-d,error_unique_log_filename";
DELETE FROM t2;
RESET MASTER;
###################### TEST #7
SET GLOBAL debug="+d,error_unique_log_filename";
SELECT count(*) FROM t4;
count(*)
0
LOAD DATA INFILE 'MYSQLTEST_VARDIR/tmp/bug_46166.data' INTO TABLE t4;
ERROR HY000: Can't generate a unique log-filename master-bin.(1-999)
# assert: must show 1 entry
SELECT count(*) FROM t4;
count(*)
1
### check that the incident event is written to the current log
SET GLOBAL debug="-d,error_unique_log_filename";
FLUSH LOGS;
SHOW BINLOG EVENTS IN 'BINLOG_FILE' FROM <binlog_start> LIMIT 1;
Log_name Pos Event_type Server_id End_log_pos Info
BINLOG_FILE # Incident # # #1 (LOST_EVENTS)
DELETE FROM t4;
RESET MASTER;
###################### TEST #8
SET GLOBAL debug="+d,error_unique_log_filename";
# must show 0 entries
SELECT count(*) FROM t4;
count(*)
0
SELECT count(*) FROM t2;
count(*)
0
LOAD DATA INFILE 'MYSQLTEST_VARDIR/tmp/bug_46166.data' INTO TABLE t4;
ERROR HY000: Can't generate a unique log-filename master-bin.(1-999)
LOAD DATA INFILE 'MYSQLTEST_VARDIR/tmp/bug_46166.data' INTO TABLE t2;
ERROR HY000: Can't generate a unique log-filename master-bin.(1-999)
INSERT INTO t2 VALUES ('aaa'), ('bbb'), ('ccc');
ERROR HY000: Can't generate a unique log-filename master-bin.(1-999)
# INFO: Count(*) Before Offending DELETEs
# assert: must show 1 entry
SELECT count(*) FROM t4;
count(*)
1
# assert: must show 4 entries
SELECT count(*) FROM t2;
count(*)
4
DELETE FROM t4;
ERROR HY000: Can't generate a unique log-filename master-bin.(1-999)
DELETE FROM t2;
ERROR HY000: Can't generate a unique log-filename master-bin.(1-999)
# INFO: Count(*) After Offending DELETEs
# assert: must show zero entries
SELECT count(*) FROM t4;
count(*)
0
SELECT count(*) FROM t2;
count(*)
0
SET GLOBAL debug="-d,error_unique_log_filename";
###################### TEST #9
SET GLOBAL debug="+d,error_unique_log_filename";
SET SQL_LOG_BIN=0;
INSERT INTO t2 VALUES ('aaa'), ('bbb'), ('ccc'), ('ddd');
INSERT INTO t4 VALUES ('eee'), ('fff'), ('ggg'), ('hhh');
# assert: must show four entries
SELECT count(*) FROM t2;
count(*)
4
SELECT count(*) FROM t4;
count(*)
4
DELETE FROM t2;
DELETE FROM t4;
# assert: must show zero entries
SELECT count(*) FROM t2;
count(*)
0
SELECT count(*) FROM t4;
count(*)
0
SET SQL_LOG_BIN=1;
SET GLOBAL debug="-d,error_unique_log_filename";
###################### TEST #10
call mtr.add_suppression("MSYQL_BIN_LOG::open failed to sync the index file.");
call mtr.add_suppression("Could not open .*");
RESET MASTER;
SHOW WARNINGS;
Level Code Message
SET GLOBAL debug="+d,fault_injection_registering_index";
FLUSH LOGS;
ERROR HY000: Can't open file: './master-bin.000002' (errno: 1)
SET GLOBAL debug="-d,fault_injection_registering_index";
SHOW BINARY LOGS;
ERROR HY000: You are not using binary logging
CREATE TABLE t5 (a INT);
INSERT INTO t4 VALUES ('bbbbb');
INSERT INTO t2 VALUES ('aaaaa');
DELETE FROM t4;
DELETE FROM t2;
DROP TABLE t5;
###################### TEST #11
SET GLOBAL debug="+d,fault_injection_openning_index";
FLUSH LOGS;
ERROR HY000: Can't open file: './master-bin.index' (errno: 1)
SET GLOBAL debug="-d,fault_injection_openning_index";
RESET MASTER;
ERROR HY000: Binlog closed, cannot RESET MASTER
CREATE TABLE t5 (a INT);
INSERT INTO t4 VALUES ('bbbbb');
INSERT INTO t2 VALUES ('aaaaa');
DELETE FROM t4;
DELETE FROM t2;
DROP TABLE t5;
###################### TEST #12
SET GLOBAL debug="+d,fault_injection_new_file_rotate_event";
FLUSH LOGS;
ERROR HY000: Can't open file: 'master-bin' (errno: 0)
SET GLOBAL debug="-d,fault_injection_new_file_rotate_event";
RESET MASTER;
ERROR HY000: Binlog closed, cannot RESET MASTER
CREATE TABLE t5 (a INT);
INSERT INTO t4 VALUES ('bbbbb');
INSERT INTO t2 VALUES ('aaaaa');
DELETE FROM t4;
DELETE FROM t2;
DROP TABLE t5;
SET GLOBAL debug= @old_debug;
DROP TABLE t1, t2, t4;
RESET MASTER;
include/start_slave.inc
#######################################################################
####################### PART 2: SLAVE TESTS ###########################
#######################################################################
stop slave;
drop table if exists t1,t2,t3,t4,t5,t6,t7,t8,t9;
reset master;
reset slave;
drop table if exists t1,t2,t3,t4,t5,t6,t7,t8,t9;
start slave;
call mtr.add_suppression("Slave I/O: Relay log write failure: could not queue event from master.*");
call mtr.add_suppression("Error writing file .*");
call mtr.add_suppression("Could not open .*");
call mtr.add_suppression("MSYQL_BIN_LOG::open failed to sync the index file.");
call mtr.add_suppression("Can't generate a unique log-filename .*");
###################### TEST #13
SET @old_debug=@@global.debug;
include/stop_slave.inc
SET GLOBAL debug="+d,error_unique_log_filename";
START SLAVE io_thread;
Last_IO_Error = Relay log write failure: could not queue event from master
SET GLOBAL debug="-d,error_unique_log_filename";
SET GLOBAL debug=@old_debug;
###################### TEST #14
SET @old_debug=@@global.debug;
include/stop_slave.inc
SET GLOBAL debug="+d,fault_injection_new_file_rotate_event";
START SLAVE io_thread;
Last_IO_Error = Relay log write failure: could not queue event from master
SET GLOBAL debug="-d,fault_injection_new_file_rotate_event";
SET GLOBAL debug=@old_debug;
###################### TEST #15
SET @old_debug=@@global.debug;
include/stop_slave.inc
SET GLOBAL debug="+d,fault_injection_registering_index";
START SLAVE io_thread;
Last_IO_Error = Relay log write failure: could not queue event from master
SET GLOBAL debug="-d,fault_injection_registering_index";
SET GLOBAL debug=@old_debug;
###################### TEST #16
SET @old_debug=@@global.debug;
include/stop_slave.inc
SET GLOBAL debug="+d,fault_injection_openning_index";
START SLAVE io_thread;
Last_IO_Error = Relay log write failure: could not queue event from master
SET GLOBAL debug="-d,fault_injection_openning_index";
SET GLOBAL debug=@old_debug;
include/stop_slave.inc
SET GLOBAL debug=@old_debug;
RESET SLAVE;
RESET MASTER;
include/start_slave.inc
This diff is collapsed.
...@@ -1237,7 +1237,11 @@ int ha_commit_trans(THD *thd, bool all) ...@@ -1237,7 +1237,11 @@ int ha_commit_trans(THD *thd, bool all)
error=ha_commit_one_phase(thd, all) ? (cookie ? 2 : 1) : 0; error=ha_commit_one_phase(thd, all) ? (cookie ? 2 : 1) : 0;
DBUG_EXECUTE_IF("crash_commit_before_unlog", DBUG_SUICIDE();); DBUG_EXECUTE_IF("crash_commit_before_unlog", DBUG_SUICIDE(););
if (cookie) if (cookie)
tc_log->unlog(cookie, xid); if(tc_log->unlog(cookie, xid))
{
error= 2;
goto end;
}
DBUG_EXECUTE_IF("crash_commit_after", DBUG_SUICIDE();); DBUG_EXECUTE_IF("crash_commit_after", DBUG_SUICIDE(););
RUN_HOOK(transaction, after_commit, (thd, FALSE)); RUN_HOOK(transaction, after_commit, (thd, FALSE));
end: end:
......
This diff is collapsed.
...@@ -45,7 +45,7 @@ class TC_LOG ...@@ -45,7 +45,7 @@ class TC_LOG
virtual int open(const char *opt_name)=0; virtual int open(const char *opt_name)=0;
virtual void close()=0; virtual void close()=0;
virtual int log_xid(THD *thd, my_xid xid)=0; virtual int log_xid(THD *thd, my_xid xid)=0;
virtual void unlog(ulong cookie, my_xid xid)=0; virtual int unlog(ulong cookie, my_xid xid)=0;
}; };
class TC_LOG_DUMMY: public TC_LOG // use it to disable the logging class TC_LOG_DUMMY: public TC_LOG // use it to disable the logging
...@@ -55,7 +55,7 @@ public: ...@@ -55,7 +55,7 @@ public:
int open(const char *opt_name) { return 0; } int open(const char *opt_name) { return 0; }
void close() { } void close() { }
int log_xid(THD *thd, my_xid xid) { return 1; } int log_xid(THD *thd, my_xid xid) { return 1; }
void unlog(ulong cookie, my_xid xid) { } int unlog(ulong cookie, my_xid xid) { return 0; }
}; };
#ifdef HAVE_MMAP #ifdef HAVE_MMAP
...@@ -100,7 +100,7 @@ class TC_LOG_MMAP: public TC_LOG ...@@ -100,7 +100,7 @@ class TC_LOG_MMAP: public TC_LOG
int open(const char *opt_name); int open(const char *opt_name);
void close(); void close();
int log_xid(THD *thd, my_xid xid); int log_xid(THD *thd, my_xid xid);
void unlog(ulong cookie, my_xid xid); int unlog(ulong cookie, my_xid xid);
int recover(); int recover();
private: private:
...@@ -334,8 +334,8 @@ class MYSQL_BIN_LOG: public TC_LOG, private MYSQL_LOG ...@@ -334,8 +334,8 @@ class MYSQL_BIN_LOG: public TC_LOG, private MYSQL_LOG
new_file() is locking. new_file_without_locking() does not acquire new_file() is locking. new_file_without_locking() does not acquire
LOCK_log. LOCK_log.
*/ */
void new_file_without_locking(); int new_file_without_locking();
void new_file_impl(bool need_lock); int new_file_impl(bool need_lock);
public: public:
MYSQL_LOG::generate_name; MYSQL_LOG::generate_name;
...@@ -365,7 +365,7 @@ public: ...@@ -365,7 +365,7 @@ public:
int open(const char *opt_name); int open(const char *opt_name);
void close(); void close();
int log_xid(THD *thd, my_xid xid); int log_xid(THD *thd, my_xid xid);
void unlog(ulong cookie, my_xid xid); int unlog(ulong cookie, my_xid xid);
int recover(IO_CACHE *log, Format_description_log_event *fdle); int recover(IO_CACHE *log, Format_description_log_event *fdle);
#if !defined(MYSQL_CLIENT) #if !defined(MYSQL_CLIENT)
...@@ -408,7 +408,7 @@ public: ...@@ -408,7 +408,7 @@ public:
bool open_index_file(const char *index_file_name_arg, bool open_index_file(const char *index_file_name_arg,
const char *log_name, bool need_mutex); const char *log_name, bool need_mutex);
/* Use this to start writing a new log file */ /* Use this to start writing a new log file */
void new_file(); int new_file();
bool write(Log_event* event_info); // binary log write bool write(Log_event* event_info); // binary log write
bool write(THD *thd, IO_CACHE *cache, Log_event *commit_event, bool incident); bool write(THD *thd, IO_CACHE *cache, Log_event *commit_event, bool incident);
...@@ -432,7 +432,7 @@ public: ...@@ -432,7 +432,7 @@ public:
void make_log_name(char* buf, const char* log_ident); void make_log_name(char* buf, const char* log_ident);
bool is_active(const char* log_file_name); bool is_active(const char* log_file_name);
int update_log_index(LOG_INFO* linfo, bool need_update_threads); int update_log_index(LOG_INFO* linfo, bool need_update_threads);
void rotate_and_purge(uint flags); int rotate_and_purge(uint flags);
/** /**
Flush binlog cache and synchronize to disk. Flush binlog cache and synchronize to disk.
......
...@@ -2745,7 +2745,7 @@ pthread_handler_t signal_hand(void *arg __attribute__((unused))) ...@@ -2745,7 +2745,7 @@ pthread_handler_t signal_hand(void *arg __attribute__((unused)))
case SIGHUP: case SIGHUP:
if (!abort_loop) if (!abort_loop)
{ {
bool not_used; int not_used;
mysql_print_status(); // Print some debug info mysql_print_status(); // Print some debug info
reload_acl_and_cache((THD*) 0, reload_acl_and_cache((THD*) 0,
(REFRESH_LOG | REFRESH_TABLES | REFRESH_FAST | (REFRESH_LOG | REFRESH_TABLES | REFRESH_FAST |
......
...@@ -237,8 +237,7 @@ int injector::record_incident(THD *thd, Incident incident) ...@@ -237,8 +237,7 @@ int injector::record_incident(THD *thd, Incident incident)
Incident_log_event ev(thd, incident); Incident_log_event ev(thd, incident);
if (int error= mysql_bin_log.write(&ev)) if (int error= mysql_bin_log.write(&ev))
return error; return error;
mysql_bin_log.rotate_and_purge(RP_FORCE_ROTATE); return mysql_bin_log.rotate_and_purge(RP_FORCE_ROTATE);
return 0;
} }
int injector::record_incident(THD *thd, Incident incident, LEX_STRING const message) int injector::record_incident(THD *thd, Incident incident, LEX_STRING const message)
...@@ -246,6 +245,5 @@ int injector::record_incident(THD *thd, Incident incident, LEX_STRING const mess ...@@ -246,6 +245,5 @@ int injector::record_incident(THD *thd, Incident incident, LEX_STRING const mess
Incident_log_event ev(thd, incident, message); Incident_log_event ev(thd, incident, message);
if (int error= mysql_bin_log.write(&ev)) if (int error= mysql_bin_log.write(&ev))
return error; return error;
mysql_bin_log.rotate_and_purge(RP_FORCE_ROTATE); return mysql_bin_log.rotate_and_purge(RP_FORCE_ROTATE);
return 0;
} }
...@@ -3632,8 +3632,7 @@ static int process_io_rotate(Master_info *mi, Rotate_log_event *rev) ...@@ -3632,8 +3632,7 @@ static int process_io_rotate(Master_info *mi, Rotate_log_event *rev)
Rotate the relay log makes binlog format detection easier (at next slave Rotate the relay log makes binlog format detection easier (at next slave
start or mysqlbinlog) start or mysqlbinlog)
*/ */
rotate_relay_log(mi); /* will take the right mutexes */ DBUG_RETURN(rotate_relay_log(mi) /* will take the right mutexes */);
DBUG_RETURN(0);
} }
/* /*
...@@ -4870,12 +4869,13 @@ err: ...@@ -4870,12 +4869,13 @@ err:
is void). is void).
*/ */
void rotate_relay_log(Master_info* mi) int rotate_relay_log(Master_info* mi)
{ {
DBUG_ENTER("rotate_relay_log"); DBUG_ENTER("rotate_relay_log");
Relay_log_info* rli= &mi->rli; Relay_log_info* rli= &mi->rli;
int error= 0;
DBUG_EXECUTE_IF("crash_before_rotate_relaylog", abort();); DBUG_EXECUTE_IF("crash_before_rotate_relaylog", DBUG_SUICIDE(););
/* /*
We need to test inited because otherwise, new_file() will attempt to lock We need to test inited because otherwise, new_file() will attempt to lock
...@@ -4888,7 +4888,8 @@ void rotate_relay_log(Master_info* mi) ...@@ -4888,7 +4888,8 @@ void rotate_relay_log(Master_info* mi)
} }
/* If the relay log is closed, new_file() will do nothing. */ /* If the relay log is closed, new_file() will do nothing. */
rli->relay_log.new_file(); if ((error= rli->relay_log.new_file()))
goto end;
/* /*
We harvest now, because otherwise BIN_LOG_HEADER_SIZE will not immediately We harvest now, because otherwise BIN_LOG_HEADER_SIZE will not immediately
...@@ -4905,7 +4906,7 @@ void rotate_relay_log(Master_info* mi) ...@@ -4905,7 +4906,7 @@ void rotate_relay_log(Master_info* mi)
*/ */
rli->relay_log.harvest_bytes_written(&rli->log_space_total); rli->relay_log.harvest_bytes_written(&rli->log_space_total);
end: end:
DBUG_VOID_RETURN; DBUG_RETURN(error);
} }
......
...@@ -205,7 +205,7 @@ int purge_relay_logs(Relay_log_info* rli, THD *thd, bool just_reset, ...@@ -205,7 +205,7 @@ int purge_relay_logs(Relay_log_info* rli, THD *thd, bool just_reset,
const char** errmsg); const char** errmsg);
void set_slave_thread_options(THD* thd); void set_slave_thread_options(THD* thd);
void set_slave_thread_default_charset(THD *thd, Relay_log_info const *rli); void set_slave_thread_default_charset(THD *thd, Relay_log_info const *rli);
void rotate_relay_log(Master_info* mi); int rotate_relay_log(Master_info* mi);
int apply_event_and_update_pos(Log_event* ev, THD* thd, Relay_log_info* rli); int apply_event_and_update_pos(Log_event* ev, THD* thd, Relay_log_info* rli);
pthread_handler_t handle_slave_io(void *arg); pthread_handler_t handle_slave_io(void *arg);
......
...@@ -625,6 +625,13 @@ int mysql_load(THD *thd,sql_exchange *ex,TABLE_LIST *table_list, ...@@ -625,6 +625,13 @@ int mysql_load(THD *thd,sql_exchange *ex,TABLE_LIST *table_list,
transactional_table, transactional_table,
errcode); errcode);
} }
/*
Flushing the IO CACHE while writing the execute load query log event
may result in error (for instance, because the max_binlog_size has been
reached, and rotation of the binary log failed).
*/
error= error || mysql_bin_log.get_log_file()->error;
} }
if (error) if (error)
goto err; goto err;
......
...@@ -1215,7 +1215,7 @@ bool dispatch_command(enum enum_server_command command, THD *thd, ...@@ -1215,7 +1215,7 @@ bool dispatch_command(enum enum_server_command command, THD *thd,
#endif #endif
case COM_REFRESH: case COM_REFRESH:
{ {
bool not_used; int not_used;
status_var_increment(thd->status_var.com_stat[SQLCOM_FLUSH]); status_var_increment(thd->status_var.com_stat[SQLCOM_FLUSH]);
ulong options= (ulong) (uchar) packet[0]; ulong options= (ulong) (uchar) packet[0];
if (trans_commit_implicit(thd)) if (trans_commit_implicit(thd))
...@@ -2773,7 +2773,11 @@ end_with_restore_list: ...@@ -2773,7 +2773,11 @@ end_with_restore_list:
{ {
Incident_log_event ev(thd, incident); Incident_log_event ev(thd, incident);
(void) mysql_bin_log.write(&ev); /* error is ignored */ (void) mysql_bin_log.write(&ev); /* error is ignored */
mysql_bin_log.rotate_and_purge(RP_FORCE_ROTATE); if (mysql_bin_log.rotate_and_purge(RP_FORCE_ROTATE))
{
res= 1;
break;
}
} }
DBUG_PRINT("debug", ("Just after generate_incident()")); DBUG_PRINT("debug", ("Just after generate_incident()"));
} }
...@@ -3509,8 +3513,7 @@ end_with_restore_list: ...@@ -3509,8 +3513,7 @@ end_with_restore_list:
lex->no_write_to_binlog= 1; lex->no_write_to_binlog= 1;
case SQLCOM_FLUSH: case SQLCOM_FLUSH:
{ {
bool write_to_binlog; int write_to_binlog;
if (check_global_access(thd,RELOAD_ACL)) if (check_global_access(thd,RELOAD_ACL))
goto error; goto error;
...@@ -3539,11 +3542,21 @@ end_with_restore_list: ...@@ -3539,11 +3542,21 @@ end_with_restore_list:
/* /*
Presumably, RESET and binlog writing doesn't require synchronization Presumably, RESET and binlog writing doesn't require synchronization
*/ */
if (!lex->no_write_to_binlog && write_to_binlog)
if (write_to_binlog > 0) // we should write
{ {
if ((res= write_bin_log(thd, FALSE, thd->query(), thd->query_length()))) if (!lex->no_write_to_binlog)
break; res= write_bin_log(thd, FALSE, thd->query(), thd->query_length());
} else if (write_to_binlog < 0)
{
/*
We should not write, but rather report error because
reload_acl_and_cache binlog interactions failed
*/
res= 1;
} }
if (!res)
my_ok(thd); my_ok(thd);
} }
......
...@@ -33,7 +33,11 @@ ...@@ -33,7 +33,11 @@
@param thd Thread handler (can be NULL!) @param thd Thread handler (can be NULL!)
@param options What should be reset/reloaded (tables, privileges, slave...) @param options What should be reset/reloaded (tables, privileges, slave...)
@param tables Tables to flush (if any) @param tables Tables to flush (if any)
@param write_to_binlog True if we can write to the binlog. @param write_to_binlog < 0 if there was an error while interacting with the binary log inside
reload_acl_and_cache,
0 if we should not write to the binary log,
> 0 if we can write to the binlog.
@note Depending on 'options', it may be very bad to write the @note Depending on 'options', it may be very bad to write the
query to the binlog (e.g. FLUSH SLAVE); this is a query to the binlog (e.g. FLUSH SLAVE); this is a
...@@ -47,11 +51,11 @@ ...@@ -47,11 +51,11 @@
*/ */
bool reload_acl_and_cache(THD *thd, unsigned long options, bool reload_acl_and_cache(THD *thd, unsigned long options,
TABLE_LIST *tables, bool *write_to_binlog) TABLE_LIST *tables, int *write_to_binlog)
{ {
bool result=0; bool result=0;
select_errors=0; /* Write if more errors */ select_errors=0; /* Write if more errors */
bool tmp_write_to_binlog= 1; int tmp_write_to_binlog= *write_to_binlog= 1;
DBUG_ASSERT(!thd || !thd->in_sub_stmt); DBUG_ASSERT(!thd || !thd->in_sub_stmt);
...@@ -136,13 +140,17 @@ bool reload_acl_and_cache(THD *thd, unsigned long options, ...@@ -136,13 +140,17 @@ bool reload_acl_and_cache(THD *thd, unsigned long options,
*/ */
tmp_write_to_binlog= 0; tmp_write_to_binlog= 0;
if (mysql_bin_log.is_open()) if (mysql_bin_log.is_open())
mysql_bin_log.rotate_and_purge(RP_FORCE_ROTATE); {
if (mysql_bin_log.rotate_and_purge(RP_FORCE_ROTATE))
*write_to_binlog= -1;
}
} }
if (options & REFRESH_RELAY_LOG) if (options & REFRESH_RELAY_LOG)
{ {
#ifdef HAVE_REPLICATION #ifdef HAVE_REPLICATION
mysql_mutex_lock(&LOCK_active_mi); mysql_mutex_lock(&LOCK_active_mi);
rotate_relay_log(active_mi); if (rotate_relay_log(active_mi))
*write_to_binlog= -1;
mysql_mutex_unlock(&LOCK_active_mi); mysql_mutex_unlock(&LOCK_active_mi);
#endif #endif
} }
...@@ -274,6 +282,7 @@ bool reload_acl_and_cache(THD *thd, unsigned long options, ...@@ -274,6 +282,7 @@ bool reload_acl_and_cache(THD *thd, unsigned long options,
#endif #endif
if (options & REFRESH_USER_RESOURCES) if (options & REFRESH_USER_RESOURCES)
reset_mqh((LEX_USER *) NULL, 0); /* purecov: inspected */ reset_mqh((LEX_USER *) NULL, 0); /* purecov: inspected */
if (*write_to_binlog != -1)
*write_to_binlog= tmp_write_to_binlog; *write_to_binlog= tmp_write_to_binlog;
/* /*
If the query was killed then this function must fail. If the query was killed then this function must fail.
......
...@@ -19,7 +19,7 @@ class THD; ...@@ -19,7 +19,7 @@ class THD;
struct TABLE_LIST; struct TABLE_LIST;
bool reload_acl_and_cache(THD *thd, unsigned long options, bool reload_acl_and_cache(THD *thd, unsigned long options,
TABLE_LIST *tables, bool *write_to_binlog); TABLE_LIST *tables, int *write_to_binlog);
bool flush_tables_with_read_lock(THD *thd, TABLE_LIST *all_tables); bool flush_tables_with_read_lock(THD *thd, TABLE_LIST *all_tables);
......
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