Below is the list of changes that have just been committed into a local
5.1 repository of mats. When mats does a push these changes will
be propagated to the main repository and, within 24 hours after the
push, to the public repository.
For information on how to access the public repository
see http://dev.mysql.com/doc/mysql/en/installing-source-tree.html
ChangeSet@stripped, 2006-08-16 14:55:57+02:00, mats@romeo.(none) +4 -0
BUG#20863 (if binlog format is changed between update and unlock table, wrong binlogging):
Fix to allow the binlog format to be changed between the LOCK and
UNLOCK tables, as well as under MIXED mode.
mysql-test/r/rpl_switch_stm_row_mixed.result@stripped, 2006-08-16 14:55:52+02:00, mats@romeo.(none) +29 -6
Result change
mysql-test/t/rpl_switch_stm_row_mixed.test@stripped, 2006-08-16 14:55:52+02:00, mats@romeo.(none) +32 -1
Adding test to see that binlog format can be changed when using
LOCK/UNLOCK TABLES both under ROW format and MIXED format.
sql/log.cc@stripped, 2006-08-16 14:55:52+02:00, mats@romeo.(none) +1 -1
Removing pre-condition assertion since binlog can now be
statement based.
sql/sql_class.cc@stripped, 2006-08-16 14:55:53+02:00, mats@romeo.(none) +21 -19
Adding code to always flush pending event regardless of the binlog
format used. The only exception is if we are inside a stored routine,
where the pending event is never flushed.
# This is a BitKeeper patch. What follows are the unified diffs for the
# set of deltas contained in the patch. The rest of the patch, the part
# that BitKeeper cares about, is below these diffs.
# User: mats
# Host: romeo.(none)
# Root: /home/bk/b20863-mysql-5.1-new-rpl
--- 1.218/sql/log.cc 2006-08-16 14:56:03 +02:00
+++ 1.219/sql/log.cc 2006-08-16 14:56:03 +02:00
@@ -3153,7 +3153,7 @@
flush_and_set_pending_rows_event(THD *thd, Rows_log_event* event)
{
DBUG_ENTER("MYSQL_BIN_LOG::flush_and_set_pending_rows_event(event)");
- DBUG_ASSERT(thd->current_stmt_binlog_row_based && mysql_bin_log.is_open());
+ DBUG_ASSERT(mysql_bin_log.is_open());
DBUG_PRINT("enter", ("event=%p", event));
int error= 0;
--- 1.272/sql/sql_class.cc 2006-08-16 14:56:03 +02:00
+++ 1.273/sql/sql_class.cc 2006-08-16 14:56:03 +02:00
@@ -2649,7 +2649,12 @@
int THD::binlog_flush_pending_rows_event(bool stmt_end)
{
DBUG_ENTER("THD::binlog_flush_pending_rows_event");
- if (!current_stmt_binlog_row_based || !mysql_bin_log.is_open())
+ /*
+ We shall flush the pending event even if we are not in row-based
+ mode: it might be the case that we left row-based mode before
+ flushing anything (e.g., if we have explicitly locked tables).
+ */
+ if (!mysql_bin_log.is_open())
DBUG_RETURN(0);
/*
@@ -2715,6 +2720,21 @@
DBUG_PRINT("enter", ("qtype=%d, query='%s'", qtype, query));
DBUG_ASSERT(query && mysql_bin_log.is_open());
+ /*
+ If we are not in prelocked mode, mysql_unlock_tables() will be
+ called after this binlog_query(), so we have to flush the pending
+ rows event with the STMT_END_F set to unlock all tables at the
+ slave side as well.
+
+ If we are in prelocked mode, the flushing will be done inside the
+ top-most close_thread_tables().
+ */
+#ifdef HAVE_ROW_BASED_REPLICATION
+ if (this->prelocked_mode == NON_PRELOCKED)
+ if (int error= binlog_flush_pending_rows_event(TRUE))
+ DBUG_RETURN(error);
+#endif /*HAVE_ROW_BASED_REPLICATION*/
+
switch (qtype) {
case THD::MYSQL_QUERY_TYPE:
/*
@@ -2728,25 +2748,7 @@
case THD::ROW_QUERY_TYPE:
#ifdef HAVE_ROW_BASED_REPLICATION
if (current_stmt_binlog_row_based)
- {
- /*
- If thd->lock is set, then we are not inside a stored function.
- In that case, mysql_unlock_tables() will be called after this
- binlog_query(), so we have to flush the pending rows event
- with the STMT_END_F set to unlock all tables at the slave side
- as well.
-
- We will not flush the pending event, if thd->lock is NULL.
- This means that we are inside a stored function or trigger, so
- the flushing will be done inside the top-most
- close_thread_tables().
- */
-#ifdef HAVE_ROW_BASED_REPLICATION
- if (this->lock)
- DBUG_RETURN(binlog_flush_pending_rows_event(TRUE));
-#endif /*HAVE_ROW_BASED_REPLICATION*/
DBUG_RETURN(0);
- }
#endif
/* Otherwise, we fall through */
case THD::STMT_QUERY_TYPE:
--- 1.5/mysql-test/r/rpl_switch_stm_row_mixed.result 2006-08-16 14:56:03 +02:00
+++ 1.6/mysql-test/r/rpl_switch_stm_row_mixed.result 2006-08-16 14:56:03 +02:00
@@ -7,6 +7,8 @@
drop database if exists mysqltest1;
create database mysqltest1;
use mysqltest1;
+set session binlog_format=row;
+set global binlog_format=row;
show global variables like "binlog_format%";
Variable_name Value
binlog_format ROW
@@ -157,11 +159,29 @@
select count(*) from t5;
count(*)
58
+SET SESSION BINLOG_FORMAT=STATEMENT;
+CREATE TABLE t11 (song VARCHAR(255));
+LOCK TABLES t11 WRITE;
+SET SESSION BINLOG_FORMAT=ROW;
+INSERT INTO t11 VALUES('Several Species of Small Furry Animals Gathered Together in a Cave and Grooving With a Pict');
+SET SESSION BINLOG_FORMAT=STATEMENT;
+INSERT INTO t11 VALUES('Careful With That Axe, Eugene');
+UNLOCK TABLES;
+SELECT * FROM t11;
+song Several Species of Small Furry Animals Gathered Together in a Cave and Grooving With a Pict
+song Careful With That Axe, Eugene
+USE mysqltest1;
+SELECT * FROM t11;
+song Several Species of Small Furry Animals Gathered Together in a Cave and Grooving With a Pict
+song Careful With That Axe, Eugene
+SET SESSION BINLOG_FORMAT=MIXED;
+CREATE TABLE t12 (data LONG);
+LOCK TABLES t12 WRITE;
+INSERT INTO t12 VALUES(UUID());
+UNLOCK TABLES;
show binlog events from 102;
Log_name Pos Event_type Server_id End_log_pos Info
master-bin.000001 # Query 1 # drop database if exists mysqltest1
-master-bin.000001 # Table_map 1 # table_id: # (mysql.proc)
-master-bin.000001 # Write_rows 1 # table_id: # flags: STMT_END_F
master-bin.000001 # Query 1 # create database mysqltest1
master-bin.000001 # Query 1 # use `mysqltest1`; CREATE TABLE t1 (a varchar(100))
master-bin.000001 # Table_map 1 # table_id: # (mysqltest1.t1)
@@ -178,10 +198,6 @@
master-bin.000001 # Write_rows 1 # table_id: # flags: STMT_END_F
master-bin.000001 # Table_map 1 # table_id: # (mysqltest1.t1)
master-bin.000001 # Write_rows 1 # table_id: # flags: STMT_END_F
-master-bin.000001 # Table_map 1 # table_id: # (mysqltest1.t1)
-master-bin.000001 # Write_rows 1 # table_id: # flags: STMT_END_F
-master-bin.000001 # Table_map 1 # table_id: # (mysqltest1.t1)
-master-bin.000001 # Write_rows 1 # table_id: # flags: STMT_END_F
master-bin.000001 # Query 1 # use `mysqltest1`; insert into t1 values("work")
master-bin.000001 # User var 1 # @`string`=_latin1 0x656D657267656E6379 COLLATE latin1_swedish_ci
master-bin.000001 # Query 1 # use `mysqltest1`; insert into t1 select @'string'
@@ -268,5 +284,12 @@
master-bin.000001 # Table_map 1 # table_id: # (mysqltest1.t1)
master-bin.000001 # Write_rows 1 # table_id: # flags: STMT_END_F
master-bin.000001 # Table_map 1 # table_id: # (mysqltest1.t1)
+master-bin.000001 # Write_rows 1 # table_id: # flags: STMT_END_F
+master-bin.000001 # Query 1 # use `mysqltest1`; CREATE TABLE t11 (song VARCHAR(255))
+master-bin.000001 # Table_map 1 # table_id: # (mysqltest1.t11)
+master-bin.000001 # Write_rows 1 # table_id: # flags: STMT_END_F
+master-bin.000001 # Query 1 # use `mysqltest1`; INSERT INTO t11 VALUES('Careful With That Axe, Eugene')
+master-bin.000001 # Query 1 # use `mysqltest1`; CREATE TABLE t12 (data LONG)
+master-bin.000001 # Table_map 1 # table_id: # (mysqltest1.t12)
master-bin.000001 # Write_rows 1 # table_id: # flags: STMT_END_F
drop database mysqltest1;
--- 1.4/mysql-test/t/rpl_switch_stm_row_mixed.test 2006-08-16 14:56:03 +02:00
+++ 1.5/mysql-test/t/rpl_switch_stm_row_mixed.test 2006-08-16 14:56:03 +02:00
@@ -1,4 +1,4 @@
--- source include/have_binlog_format_row.inc
+-- source include/have_row_based.inc
-- source include/master-slave.inc
connection master;
@@ -8,6 +8,9 @@
--enable_warnings
use mysqltest1;
+set session binlog_format=row;
+set global binlog_format=row;
+
show global variables like "binlog_format%";
show session variables like "binlog_format%";
select @@global.binlog_format, @@session.binlog_format;
@@ -196,10 +199,38 @@
select count(*) from t9;
}
+#
+# Bug#20863 If binlog format is changed between update and unlock of
+# tables, wrong binlog
+#
+
+connection master;
+SET SESSION BINLOG_FORMAT=STATEMENT;
+CREATE TABLE t11 (song VARCHAR(255));
+LOCK TABLES t11 WRITE;
+SET SESSION BINLOG_FORMAT=ROW;
+INSERT INTO t11 VALUES('Several Species of Small Furry Animals Gathered Together in a Cave and Grooving With a Pict');
+SET SESSION BINLOG_FORMAT=STATEMENT;
+INSERT INTO t11 VALUES('Careful With That Axe, Eugene');
+UNLOCK TABLES;
+
+--query_vertical SELECT * FROM t11
+sync_slave_with_master;
+USE mysqltest1;
+--query_vertical SELECT * FROM t11
+
+connection master;
+SET SESSION BINLOG_FORMAT=MIXED;
+CREATE TABLE t12 (data LONG);
+LOCK TABLES t12 WRITE;
+INSERT INTO t12 VALUES(UUID());
+UNLOCK TABLES;
+
--replace_column 2 # 5 #
--replace_regex /table_id: [0-9]+/table_id: #/
show binlog events from 102;
sync_slave_with_master;
+
# as we're using UUID we don't SELECT but use "diff" like in rpl_row_UUID
--exec $MYSQL_DUMP --compact --order-by-primary --skip-extended-insert --no-create-info mysqltest1 > $MYSQLTEST_VARDIR/tmp/rpl_switch_stm_row_mixed_master.sql
--exec $MYSQL_DUMP_SLAVE --compact --order-by-primary --skip-extended-insert --no-create-info mysqltest1 > $MYSQLTEST_VARDIR/tmp/rpl_switch_stm_row_mixed_slave.sql
| Thread |
|---|
| • bk commit into 5.1 tree (mats:1.2234) BUG#20863 | Mats Kindahl | 16 Aug |