#At file:///home/acorreia/workspace.sun/repository.mysql/bzrwork/bug-47287/mysql-5.1-bugteam/ based on revid:satya.bn@stripped
3111 Alfranio Correia 2009-09-17
BUG#47287 RBR: replication diff on basic case with txn- and non-txn tables in a statement
Let
- T be a transactional table and N non-transactional table.
- B be begin, C commit and R rollback.
- M be a mixed statement, i.e. a statement that updates both T and N.
- M* be a mixed statement that fails while updating either T or N.
This patch restore the behavior presented in 5.1.37 for rows either produced in
the RBR or MIXED modes, when a M* statement that happened early in a transaction
had their changes written to the binary log outside the boundaries of the
transaction and wrapped in a BEGIN/ROLLBACK. This was done to keep the slave
consistent with with the master as the rollback would keep the changes on N and
undo them on T. In particular, we do what folllows:
. B M* T C would log - B M* R B T C.
Note that, we are not preserving history from the master as we are introducing a
rollback that never happened. However, this seems to be more acceptable than
making the slave diverge. We do not fix the following case:
. B T M* C would log B T M* C.
The slave will diverge as the changes on T tables that originated from the M
statement are rolled back on the master but not on the slave. Unfortunately, we
cannot simply rollback the transaction as this would undo any uncommitted
changes on T tables.
SBR is not considered in this patch because a failing statement is written to
the binary along with the error code and a slave executes and then rolls back
the statement when it has an associated error code, thus undoing the effects
on T. In RBR and MBR, a full-fledge fix will be pushed after the WL 2687.
added:
mysql-test/extra/rpl_tests/rpl_failure_mixing_engines.test
mysql-test/suite/rpl/r/rpl_mixed_failure_mixing_engines.result
mysql-test/suite/rpl/r/rpl_row_failure_mixing_engines.result
mysql-test/suite/rpl/t/rpl_mixed_failure_mixing_engines.test
mysql-test/suite/rpl/t/rpl_row_failure_mixing_engines.test
modified:
sql/log.cc
=== added file 'mysql-test/extra/rpl_tests/rpl_failure_mixing_engines.test'
--- a/mysql-test/extra/rpl_tests/rpl_failure_mixing_engines.test 1970-01-01 00:00:00 +0000
+++ b/mysql-test/extra/rpl_tests/rpl_failure_mixing_engines.test 2009-09-17 15:22:06 +0000
@@ -0,0 +1,123 @@
+################################################################################
+# Let
+# - T be a transactional table and N non-transactional table.
+# - B be begin, C commit and R rollback.
+# - M be a mixed statement, i.e. a statement that updates both T and N.
+# - M* be a mixed statement that fails while updating either T or N.
+#
+# In this test case, when changes are logged as rows either in the RBR or MIXED
+# modes, we check if a M* statement that happens early in a transaction is
+# written to the binary log outside the boundaries of the transaction and
+# wrapped in a BEGIN/ROLLBACK. This is done to keep the slave consistent with
+# with the master as the rollback will keep the changes on N and undo them on
+# T. In particular, we expect the following behavior:
+#
+# 1. B M* T C would log - B M* R B T C.
+# 2. B T M* C would log B T M* C.
+#
+# SBR is not considered in this test because a failing statement is written to
+# the binary along with the error code and a slave executes and then rolls back
+# the statement when it has an associated error code, thus undoing the effects
+# on T.
+#
+# Note that, in the first case, we are not preserving history from the master as
+# we are introducing a rollback that never happened. However, this seems to be
+# more acceptable than making the slave diverge. In the second case, the slave
+# will diverge as the changes on T tables that originated from the M statement
+# are rolled back on the master but not on the slave. Unfortunately, we cannot
+# simply rollback the transaction as this would undo any uncommitted changes
+# on T tables.
+#
+# Such issues do not happen in SBR. In RBR and MBR, a fix will be pushed after
+# the WL 2687.
+################################################################################
+
+
+--echo ###################################################################################
+--echo # CONFIGURATION
+--echo ###################################################################################
+connection master;
+
+SET SQL_LOG_BIN=0;
+CREATE TABLE nt_1 (a text, b int PRIMARY KEY, c text) ENGINE = MyISAM;
+CREATE TABLE nt_2 (a text, b int PRIMARY KEY, c text) ENGINE = MyISAM;
+CREATE TABLE tt_1 (a text, b int PRIMARY KEY, c text) ENGINE = Innodb;
+CREATE TABLE tt_2 (a text, b int PRIMARY KEY, c text) ENGINE = Innodb;
+SET SQL_LOG_BIN=1;
+
+connection slave;
+
+SET SQL_LOG_BIN=0;
+CREATE TABLE nt_1 (a text, b int PRIMARY KEY, c text) ENGINE = MyISAM;
+CREATE TABLE nt_2 (a text, b int PRIMARY KEY, c text) ENGINE = MyISAM;
+CREATE TABLE tt_1 (a text, b int PRIMARY KEY, c text) ENGINE = Innodb;
+CREATE TABLE tt_2 (a text, b int PRIMARY KEY, c text) ENGINE = Innodb;
+SET SQL_LOG_BIN=1;
+
+connection master;
+
+DELIMITER |;
+
+CREATE TRIGGER tr_i_tt_1_to_nt_1 BEFORE INSERT ON tt_1 FOR EACH ROW
+BEGIN
+ INSERT INTO nt_1 VALUES (NEW.a, NEW.b, NEW.c);
+END|
+
+CREATE TRIGGER tr_i_nt_2_to_tt_2 BEFORE INSERT ON nt_2 FOR EACH ROW
+BEGIN
+ INSERT INTO tt_2 VALUES (NEW.a, NEW.b, NEW.c);
+END|
+
+DELIMITER ;|
+
+--echo ###################################################################################
+--echo # CHECK HISTORY IN BINLOG
+--echo ###################################################################################
+let $binlog_start= query_get_value("SHOW MASTER STATUS", Position, 1);
+
+
+--echo *** "B M* T C" with error in M* generates in the binlog the "M B T C" entries
+INSERT INTO nt_1 VALUES ("new text 1", 1, '');
+BEGIN;
+--error ER_DUP_ENTRY
+INSERT INTO tt_1 VALUES ("new text 2", 2, USER()), ("new text 1", 1, USER());
+INSERT INTO tt_1 VALUES ("new text 3", 3, ''), ("new text 4", 4, '');
+COMMIT;
+
+INSERT INTO tt_2 VALUES ("new text 5", 5, '');
+BEGIN;
+--error ER_DUP_ENTRY
+INSERT INTO nt_2 VALUES ("new text 6", 6, USER()), ("new text 5", 5, USER());
+INSERT INTO tt_2 VALUES ("new text 7", 7, '');
+COMMIT;
+
+--echo *** "B M M T C" with error in M* generates in the binlog the "B M M* T C" entries
+INSERT INTO nt_1 VALUES ("new text 11", 11, '');
+BEGIN;
+INSERT INTO tt_1 VALUES ("new text 8", 8, ''), ("new text 9", 9, '');
+--error ER_DUP_ENTRY
+INSERT INTO tt_1 VALUES ("new text 10", 10, USER()), ("new text 11", 11, USER());
+INSERT INTO tt_2 VALUES ("new text 12", 12, '');
+COMMIT;
+
+INSERT INTO tt_2 VALUES ("new text 16", 16, '');
+BEGIN;
+INSERT INTO nt_2 VALUES ("new text 13", 13, ''), ("new text 14", 14, '');
+--error ER_DUP_ENTRY
+INSERT INTO nt_2 VALUES ("new text 15", 15, USER()), ("new text 16", 16, USER());
+INSERT INTO tt_2 VALUES ("new text 17", 17, '');
+COMMIT;
+
+--source include/show_binlog_events.inc
+
+--echo ###################################################################################
+--echo # CLEAN
+--echo ###################################################################################
+
+connection master;
+DROP TABLE tt_1;
+DROP TABLE tt_2;
+DROP TABLE nt_1;
+DROP TABLE nt_2;
+
+sync_slave_with_master;
=== added file 'mysql-test/suite/rpl/r/rpl_mixed_failure_mixing_engines.result'
--- a/mysql-test/suite/rpl/r/rpl_mixed_failure_mixing_engines.result 1970-01-01 00:00:00 +0000
+++ b/mysql-test/suite/rpl/r/rpl_mixed_failure_mixing_engines.result 2009-09-17 15:22:06 +0000
@@ -0,0 +1,111 @@
+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;
+###################################################################################
+# CONFIGURATION
+###################################################################################
+SET SQL_LOG_BIN=0;
+CREATE TABLE nt_1 (a text, b int PRIMARY KEY, c text) ENGINE = MyISAM;
+CREATE TABLE nt_2 (a text, b int PRIMARY KEY, c text) ENGINE = MyISAM;
+CREATE TABLE tt_1 (a text, b int PRIMARY KEY, c text) ENGINE = Innodb;
+CREATE TABLE tt_2 (a text, b int PRIMARY KEY, c text) ENGINE = Innodb;
+SET SQL_LOG_BIN=1;
+SET SQL_LOG_BIN=0;
+CREATE TABLE nt_1 (a text, b int PRIMARY KEY, c text) ENGINE = MyISAM;
+CREATE TABLE nt_2 (a text, b int PRIMARY KEY, c text) ENGINE = MyISAM;
+CREATE TABLE tt_1 (a text, b int PRIMARY KEY, c text) ENGINE = Innodb;
+CREATE TABLE tt_2 (a text, b int PRIMARY KEY, c text) ENGINE = Innodb;
+SET SQL_LOG_BIN=1;
+CREATE TRIGGER tr_i_tt_1_to_nt_1 BEFORE INSERT ON tt_1 FOR EACH ROW
+BEGIN
+INSERT INTO nt_1 VALUES (NEW.a, NEW.b, NEW.c);
+END|
+CREATE TRIGGER tr_i_nt_2_to_tt_2 BEFORE INSERT ON nt_2 FOR EACH ROW
+BEGIN
+INSERT INTO tt_2 VALUES (NEW.a, NEW.b, NEW.c);
+END|
+###################################################################################
+# CHECK HISTORY IN BINLOG
+###################################################################################
+*** "B M* T C" with error in M* generates in the binlog the "M B T C" entries
+INSERT INTO nt_1 VALUES ("new text 1", 1, '');
+BEGIN;
+INSERT INTO tt_1 VALUES ("new text 2", 2, USER()), ("new text 1", 1, USER());
+ERROR 23000: Duplicate entry '1' for key 'PRIMARY'
+INSERT INTO tt_1 VALUES ("new text 3", 3, ''), ("new text 4", 4, '');
+COMMIT;
+INSERT INTO tt_2 VALUES ("new text 5", 5, '');
+BEGIN;
+INSERT INTO nt_2 VALUES ("new text 6", 6, USER()), ("new text 5", 5, USER());
+ERROR 23000: Duplicate entry '5' for key 'PRIMARY'
+INSERT INTO tt_2 VALUES ("new text 7", 7, '');
+COMMIT;
+*** "B M M T C" with error in M* generates in the binlog the "B M M* T C" entries
+INSERT INTO nt_1 VALUES ("new text 11", 11, '');
+BEGIN;
+INSERT INTO tt_1 VALUES ("new text 8", 8, ''), ("new text 9", 9, '');
+INSERT INTO tt_1 VALUES ("new text 10", 10, USER()), ("new text 11", 11, USER());
+ERROR 23000: Duplicate entry '11' for key 'PRIMARY'
+INSERT INTO tt_2 VALUES ("new text 12", 12, '');
+COMMIT;
+INSERT INTO tt_2 VALUES ("new text 16", 16, '');
+BEGIN;
+INSERT INTO nt_2 VALUES ("new text 13", 13, ''), ("new text 14", 14, '');
+INSERT INTO nt_2 VALUES ("new text 15", 15, USER()), ("new text 16", 16, USER());
+ERROR 23000: Duplicate entry '16' for key 'PRIMARY'
+INSERT INTO tt_2 VALUES ("new text 17", 17, '');
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name Pos Event_type Server_id End_log_pos Info
+master-bin.000001 # Query # # use `test`; INSERT INTO nt_1 VALUES ("new text 1", 1, '')
+master-bin.000001 # Query # # BEGIN
+master-bin.000001 # Table_map # # table_id: # (test.tt_1)
+master-bin.000001 # Table_map # # table_id: # (test.nt_1)
+master-bin.000001 # Write_rows # # table_id: #
+master-bin.000001 # Write_rows # # table_id: # flags: STMT_END_F
+master-bin.000001 # Query # # ROLLBACK
+master-bin.000001 # Query # # BEGIN
+master-bin.000001 # Query # # use `test`; INSERT INTO tt_1 VALUES ("new text 3", 3, ''), ("new text 4", 4, '')
+master-bin.000001 # Xid # # COMMIT /* XID */
+master-bin.000001 # Query # # BEGIN
+master-bin.000001 # Query # # use `test`; INSERT INTO tt_2 VALUES ("new text 5", 5, '')
+master-bin.000001 # Xid # # COMMIT /* XID */
+master-bin.000001 # Query # # BEGIN
+master-bin.000001 # Table_map # # table_id: # (test.nt_2)
+master-bin.000001 # Table_map # # table_id: # (test.tt_2)
+master-bin.000001 # Write_rows # # table_id: #
+master-bin.000001 # Write_rows # # table_id: # flags: STMT_END_F
+master-bin.000001 # Query # # ROLLBACK
+master-bin.000001 # Query # # BEGIN
+master-bin.000001 # Query # # use `test`; INSERT INTO tt_2 VALUES ("new text 7", 7, '')
+master-bin.000001 # Xid # # COMMIT /* XID */
+master-bin.000001 # Query # # use `test`; INSERT INTO nt_1 VALUES ("new text 11", 11, '')
+master-bin.000001 # Query # # BEGIN
+master-bin.000001 # Query # # use `test`; INSERT INTO tt_1 VALUES ("new text 8", 8, ''), ("new text 9", 9, '')
+master-bin.000001 # Table_map # # table_id: # (test.tt_1)
+master-bin.000001 # Table_map # # table_id: # (test.nt_1)
+master-bin.000001 # Write_rows # # table_id: #
+master-bin.000001 # Write_rows # # table_id: # flags: STMT_END_F
+master-bin.000001 # Query # # use `test`; INSERT INTO tt_2 VALUES ("new text 12", 12, '')
+master-bin.000001 # Xid # # COMMIT /* XID */
+master-bin.000001 # Query # # BEGIN
+master-bin.000001 # Query # # use `test`; INSERT INTO tt_2 VALUES ("new text 16", 16, '')
+master-bin.000001 # Xid # # COMMIT /* XID */
+master-bin.000001 # Query # # BEGIN
+master-bin.000001 # Query # # use `test`; INSERT INTO nt_2 VALUES ("new text 13", 13, ''), ("new text 14", 14, '')
+master-bin.000001 # Table_map # # table_id: # (test.nt_2)
+master-bin.000001 # Table_map # # table_id: # (test.tt_2)
+master-bin.000001 # Write_rows # # table_id: #
+master-bin.000001 # Write_rows # # table_id: # flags: STMT_END_F
+master-bin.000001 # Query # # use `test`; INSERT INTO tt_2 VALUES ("new text 17", 17, '')
+master-bin.000001 # Xid # # COMMIT /* XID */
+###################################################################################
+# CLEAN
+###################################################################################
+DROP TABLE tt_1;
+DROP TABLE tt_2;
+DROP TABLE nt_1;
+DROP TABLE nt_2;
=== added file 'mysql-test/suite/rpl/r/rpl_row_failure_mixing_engines.result'
--- a/mysql-test/suite/rpl/r/rpl_row_failure_mixing_engines.result 1970-01-01 00:00:00 +0000
+++ b/mysql-test/suite/rpl/r/rpl_row_failure_mixing_engines.result 2009-09-17 15:22:06 +0000
@@ -0,0 +1,137 @@
+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;
+###################################################################################
+# CONFIGURATION
+###################################################################################
+SET SQL_LOG_BIN=0;
+CREATE TABLE nt_1 (a text, b int PRIMARY KEY, c text) ENGINE = MyISAM;
+CREATE TABLE nt_2 (a text, b int PRIMARY KEY, c text) ENGINE = MyISAM;
+CREATE TABLE tt_1 (a text, b int PRIMARY KEY, c text) ENGINE = Innodb;
+CREATE TABLE tt_2 (a text, b int PRIMARY KEY, c text) ENGINE = Innodb;
+SET SQL_LOG_BIN=1;
+SET SQL_LOG_BIN=0;
+CREATE TABLE nt_1 (a text, b int PRIMARY KEY, c text) ENGINE = MyISAM;
+CREATE TABLE nt_2 (a text, b int PRIMARY KEY, c text) ENGINE = MyISAM;
+CREATE TABLE tt_1 (a text, b int PRIMARY KEY, c text) ENGINE = Innodb;
+CREATE TABLE tt_2 (a text, b int PRIMARY KEY, c text) ENGINE = Innodb;
+SET SQL_LOG_BIN=1;
+CREATE TRIGGER tr_i_tt_1_to_nt_1 BEFORE INSERT ON tt_1 FOR EACH ROW
+BEGIN
+INSERT INTO nt_1 VALUES (NEW.a, NEW.b, NEW.c);
+END|
+CREATE TRIGGER tr_i_nt_2_to_tt_2 BEFORE INSERT ON nt_2 FOR EACH ROW
+BEGIN
+INSERT INTO tt_2 VALUES (NEW.a, NEW.b, NEW.c);
+END|
+###################################################################################
+# CHECK HISTORY IN BINLOG
+###################################################################################
+*** "B M* T C" with error in M* generates in the binlog the "M B T C" entries
+INSERT INTO nt_1 VALUES ("new text 1", 1, '');
+BEGIN;
+INSERT INTO tt_1 VALUES ("new text 2", 2, USER()), ("new text 1", 1, USER());
+ERROR 23000: Duplicate entry '1' for key 'PRIMARY'
+INSERT INTO tt_1 VALUES ("new text 3", 3, ''), ("new text 4", 4, '');
+COMMIT;
+INSERT INTO tt_2 VALUES ("new text 5", 5, '');
+BEGIN;
+INSERT INTO nt_2 VALUES ("new text 6", 6, USER()), ("new text 5", 5, USER());
+ERROR 23000: Duplicate entry '5' for key 'PRIMARY'
+INSERT INTO tt_2 VALUES ("new text 7", 7, '');
+COMMIT;
+*** "B M M T C" with error in M* generates in the binlog the "B M M* T C" entries
+INSERT INTO nt_1 VALUES ("new text 11", 11, '');
+BEGIN;
+INSERT INTO tt_1 VALUES ("new text 8", 8, ''), ("new text 9", 9, '');
+INSERT INTO tt_1 VALUES ("new text 10", 10, USER()), ("new text 11", 11, USER());
+ERROR 23000: Duplicate entry '11' for key 'PRIMARY'
+INSERT INTO tt_2 VALUES ("new text 12", 12, '');
+COMMIT;
+INSERT INTO tt_2 VALUES ("new text 16", 16, '');
+BEGIN;
+INSERT INTO nt_2 VALUES ("new text 13", 13, ''), ("new text 14", 14, '');
+INSERT INTO nt_2 VALUES ("new text 15", 15, USER()), ("new text 16", 16, USER());
+ERROR 23000: Duplicate entry '16' for key 'PRIMARY'
+INSERT INTO tt_2 VALUES ("new text 17", 17, '');
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name Pos Event_type Server_id End_log_pos Info
+master-bin.000001 # Query # # BEGIN
+master-bin.000001 # Table_map # # table_id: # (test.nt_1)
+master-bin.000001 # Write_rows # # table_id: # flags: STMT_END_F
+master-bin.000001 # Query # # COMMIT
+master-bin.000001 # Query # # BEGIN
+master-bin.000001 # Table_map # # table_id: # (test.tt_1)
+master-bin.000001 # Table_map # # table_id: # (test.nt_1)
+master-bin.000001 # Write_rows # # table_id: #
+master-bin.000001 # Write_rows # # table_id: # flags: STMT_END_F
+master-bin.000001 # Query # # ROLLBACK
+master-bin.000001 # Query # # BEGIN
+master-bin.000001 # Table_map # # table_id: # (test.tt_1)
+master-bin.000001 # Table_map # # table_id: # (test.nt_1)
+master-bin.000001 # Write_rows # # table_id: #
+master-bin.000001 # Write_rows # # table_id: #
+master-bin.000001 # Write_rows # # table_id: #
+master-bin.000001 # Write_rows # # table_id: # flags: STMT_END_F
+master-bin.000001 # Xid # # COMMIT /* XID */
+master-bin.000001 # Query # # BEGIN
+master-bin.000001 # Table_map # # table_id: # (test.tt_2)
+master-bin.000001 # Write_rows # # table_id: # flags: STMT_END_F
+master-bin.000001 # Xid # # COMMIT /* XID */
+master-bin.000001 # Query # # BEGIN
+master-bin.000001 # Table_map # # table_id: # (test.nt_2)
+master-bin.000001 # Table_map # # table_id: # (test.tt_2)
+master-bin.000001 # Write_rows # # table_id: #
+master-bin.000001 # Write_rows # # table_id: # flags: STMT_END_F
+master-bin.000001 # Query # # ROLLBACK
+master-bin.000001 # Query # # BEGIN
+master-bin.000001 # Table_map # # table_id: # (test.tt_2)
+master-bin.000001 # Write_rows # # table_id: # flags: STMT_END_F
+master-bin.000001 # Xid # # COMMIT /* XID */
+master-bin.000001 # Query # # BEGIN
+master-bin.000001 # Table_map # # table_id: # (test.nt_1)
+master-bin.000001 # Write_rows # # table_id: # flags: STMT_END_F
+master-bin.000001 # Query # # COMMIT
+master-bin.000001 # Query # # BEGIN
+master-bin.000001 # Table_map # # table_id: # (test.tt_1)
+master-bin.000001 # Table_map # # table_id: # (test.nt_1)
+master-bin.000001 # Write_rows # # table_id: #
+master-bin.000001 # Write_rows # # table_id: #
+master-bin.000001 # Write_rows # # table_id: #
+master-bin.000001 # Write_rows # # table_id: # flags: STMT_END_F
+master-bin.000001 # Table_map # # table_id: # (test.tt_1)
+master-bin.000001 # Table_map # # table_id: # (test.nt_1)
+master-bin.000001 # Write_rows # # table_id: #
+master-bin.000001 # Write_rows # # table_id: # flags: STMT_END_F
+master-bin.000001 # Table_map # # table_id: # (test.tt_2)
+master-bin.000001 # Write_rows # # table_id: # flags: STMT_END_F
+master-bin.000001 # Xid # # COMMIT /* XID */
+master-bin.000001 # Query # # BEGIN
+master-bin.000001 # Table_map # # table_id: # (test.tt_2)
+master-bin.000001 # Write_rows # # table_id: # flags: STMT_END_F
+master-bin.000001 # Xid # # COMMIT /* XID */
+master-bin.000001 # Query # # BEGIN
+master-bin.000001 # Table_map # # table_id: # (test.nt_2)
+master-bin.000001 # Table_map # # table_id: # (test.tt_2)
+master-bin.000001 # Write_rows # # table_id: #
+master-bin.000001 # Write_rows # # table_id: #
+master-bin.000001 # Write_rows # # table_id: #
+master-bin.000001 # Write_rows # # table_id: # flags: STMT_END_F
+master-bin.000001 # Table_map # # table_id: # (test.nt_2)
+master-bin.000001 # Table_map # # table_id: # (test.tt_2)
+master-bin.000001 # Write_rows # # table_id: #
+master-bin.000001 # Write_rows # # table_id: # flags: STMT_END_F
+master-bin.000001 # Table_map # # table_id: # (test.tt_2)
+master-bin.000001 # Write_rows # # table_id: # flags: STMT_END_F
+master-bin.000001 # Xid # # COMMIT /* XID */
+###################################################################################
+# CLEAN
+###################################################################################
+DROP TABLE tt_1;
+DROP TABLE tt_2;
+DROP TABLE nt_1;
+DROP TABLE nt_2;
=== added file 'mysql-test/suite/rpl/t/rpl_mixed_failure_mixing_engines.test'
--- a/mysql-test/suite/rpl/t/rpl_mixed_failure_mixing_engines.test 1970-01-01 00:00:00 +0000
+++ b/mysql-test/suite/rpl/t/rpl_mixed_failure_mixing_engines.test 2009-09-17 15:22:06 +0000
@@ -0,0 +1,5 @@
+--source include/have_binlog_format_mixed.inc
+--source include/master-slave.inc
+--source include/have_innodb.inc
+
+--source extra/rpl_tests/rpl_failure_mixing_engines.test
=== added file 'mysql-test/suite/rpl/t/rpl_row_failure_mixing_engines.test'
--- a/mysql-test/suite/rpl/t/rpl_row_failure_mixing_engines.test 1970-01-01 00:00:00 +0000
+++ b/mysql-test/suite/rpl/t/rpl_row_failure_mixing_engines.test 2009-09-17 15:22:06 +0000
@@ -0,0 +1,5 @@
+--source include/have_binlog_format_row.inc
+--source include/master-slave.inc
+--source include/have_innodb.inc
+
+--source extra/rpl_tests/rpl_failure_mixing_engines.test
=== modified file 'sql/log.cc'
--- a/sql/log.cc 2009-09-11 17:06:27 +0000
+++ b/sql/log.cc 2009-09-17 15:22:06 +0000
@@ -182,7 +182,10 @@ public:
{
DBUG_PRINT("info", ("truncating to position %lu", (ulong) pos));
DBUG_PRINT("info", ("before_stmt_pos=%lu", (ulong) pos));
- delete pending();
+ if (pending())
+ {
+ delete pending();
+ }
set_pending(0);
reinit_io_cache(&trans_log, WRITE_CACHE, pos, 0, 0);
trans_log.end_of_file= max_binlog_cache_size;
@@ -205,8 +208,7 @@ public:
completely.
*/
void reset() {
- if (!empty())
- truncate(0);
+ truncate(0);
before_stmt_pos= MY_OFF_T_UNDEF;
incident= FALSE;
trans_log.end_of_file= max_binlog_cache_size;
@@ -1539,9 +1541,10 @@ static int binlog_commit(handlerton *hto
{
Query_log_event qev(thd, STRING_WITH_LEN("COMMIT"), TRUE, TRUE, 0);
error= binlog_end_trans(thd, trx_data, &qev, all);
- goto end;
}
+ trx_data->at_least_one_stmt = my_b_tell(&trx_data->trans_log) > 0;
+
end:
if (!all)
trx_data->before_stmt_pos = MY_OFF_T_UNDEF; // part of the stmt commit
@@ -1617,6 +1620,9 @@ static int binlog_rollback(handlerton *h
if ((all && thd->transaction.all.modified_non_trans_table) ||
(!all && thd->transaction.stmt.modified_non_trans_table &&
!(thd->options & (OPTION_BEGIN | OPTION_NOT_AUTOCOMMIT))) ||
+ (!all && thd->transaction.stmt.modified_non_trans_table &&
+ !trx_data->at_least_one_stmt &&
+ thd->current_stmt_binlog_row_based) ||
((thd->options & OPTION_KEEP_LOG)))
{
Query_log_event qev(thd, STRING_WITH_LEN("ROLLBACK"), TRUE, TRUE, 0);
Attachment: [text/bzr-bundle]