List:Commits« Previous MessageNext Message »
From:Davi Arnaut Date:July 19 2008 1:24am
Subject:bzr commit into mysql-6.0 branch (davi:2682) WL#4284
View as plain text  
# At a local mysql-6.0 repository of davi

 2682 Davi Arnaut	2008-07-18
      WL#4284: Transactional DDL locking
      
      Chapter I - SQL statements' effect on transactions.
      
      Currently the MySQL server and its storage engines are not
      capable of rolling back operations that define or modify data
      structures (also known as DDL statements) or operations that
      alter any of the system tables (the mysql database). Allowing
      these group of statements to participate in transactions
      is unfeasible at this time (since rollback has no effect
      whatsoever on them) and goes against the design of our metadata
      locking subsystem.
      
      The solution is to issue implicit commits before and after
      those statements execution. This effectively confines each of
      those statements to its own special transaction and ensures
      that metadata locks taken during this special transaction
      are not leaked into posterior statements/transactions.
      
      The overall objective of this this patch is to provide groundwork
      for the design of transactional DDL locking by cleaning up the
      transaction high level API to better distinguish operations implicit
      and explicit, and single statement transaction from operations on
      the normal transaction.
added:
  mysql-test/include/wrap_trans_log.inc
  mysql-test/r/implicit_commit.result
  mysql-test/t/implicit_commit.test
  sql/transaction.cc
  sql/transaction.h
modified:
  libmysqld/CMakeLists.txt
  libmysqld/Makefile.am
  mysql-test/include/commit.inc
  mysql-test/r/commit_1innodb.result
  sql/CMakeLists.txt
  sql/Makefile.am
  sql/backup/be_snapshot.cc
  sql/backup/be_snapshot.h
  sql/events.cc
  sql/handler.cc
  sql/handler.h
  sql/lock.cc
  sql/log_event.cc
  sql/log_event_old.cc
  sql/mdl.h
  sql/mysql_priv.h
  sql/rpl_injector.cc
  sql/rpl_rli.cc
  sql/set_var.cc
  sql/slave.cc
  sql/sql_base.cc
  sql/sql_class.cc
  sql/sql_class.h
  sql/sql_delete.cc
  sql/sql_do.cc
  sql/sql_insert.cc
  sql/sql_parse.cc
  sql/sql_partition.cc
  sql/sql_table.cc
  storage/maria/ha_maria.cc

per-file messages:
  libmysqld/CMakeLists.txt
    Add new file to the windows build.
  libmysqld/Makefile.am
    Add new file to the build.
  mysql-test/include/commit.inc
    Alter table rename was not committing the normal transaction and
    the commit was being issued in the next DDL command (rename table)
    that actually doesn't commit at all. Other changes are to take
    into account the implicit commits issued before and after the DDL
    command execution.
  mysql-test/include/wrap_trans_log.inc
    Add auxiliary test that shows if a statement issued a
    implicit commit.
  mysql-test/r/commit_1innodb.result
    Update test case result.
  mysql-test/r/implicit_commit.result
    Test implicit commit behavior of some SQL commands.
  mysql-test/t/implicit_commit.test
    Test implicit commit behavior of some SQL commands.
  sql/CMakeLists.txt
    Add new file to the windows build.
  sql/Makefile.am
    Add new file to the build.
  sql/backup/be_snapshot.cc
    Use new functions.
  sql/backup/be_snapshot.h
    Use new function.
  sql/events.cc
    Transaction is now ended before the command execution.
  sql/handler.cc
    Remove obsolete function that was used to commit or rollback
    a statement transaction. Also remove useless variable on the
    ha_prepare function.
  sql/handler.h
    Remove wrappers in favor of new functions.
  sql/lock.cc
    Commit statement transaction.
  sql/log_event.cc
    Commit statement and normal transaction.
  sql/log_event_old.cc
    Use the new function to commit a staetment transaction.
  sql/mdl.h
    Typedef lock data iterator for ease of use.
  sql/mysql_priv.h
    Add new header which exports the transaction wrapper functions.
    Remove obsolete functions for implicit and explicit commit.
  sql/rpl_injector.cc
    Use the new function to commit a staetment transaction.
  sql/rpl_rli.cc
    Use the new function to commit a staetment transaction.
  sql/set_var.cc
    Commit normal transaction. In the future will be a implicit
    commit.
  sql/slave.cc
    Use the new function to rollback a transaction.
  sql/sql_base.cc
    Commit or rollback statement transaction.
  sql/sql_class.cc
    Use the new function to rollback a transaction.
  sql/sql_class.h
    Add flags to control when to issue implicit
    commits before and after a command execution.
  sql/sql_delete.cc
    Remove now unnecessary commits. Transaction is
    ended at the end of the statement for the TRUNCATE
    command.
  sql/sql_do.cc
    Use the new function to rollback a statement transaction.
  sql/sql_insert.cc
    Use new functions.
  sql/sql_parse.cc
    Mark commands that need implicit commits before and
    after their executions. The implicit commits are now
    issue regardless of the user access privileges.
    
    Remove obsolete functions in favor of new transaction
    wrappers.
  sql/sql_partition.cc
    Use new functions.
  sql/sql_table.cc
    Use new functions.
  sql/transaction.cc
    Implement wrapper functions to differentiate operations on
    the single statement transaction from the ones operating
    on the normal transaction.
  sql/transaction.h
    Export new functions for dealing with transaction commands.
  storage/maria/ha_maria.cc
    Fix comment to reflect new functions.
=== modified file 'libmysqld/CMakeLists.txt'
--- a/libmysqld/CMakeLists.txt	2008-06-30 20:21:41 +0000
+++ b/libmysqld/CMakeLists.txt	2008-07-19 01:23:51 +0000
@@ -202,6 +202,7 @@ SET(LIBMYSQLD_SOURCES emb_qcache.cc libm
            ../sql/scheduler.cc ../sql/sql_audit.cc
            ../sql/ddl_blocker.cc ../sql/si_objects.cc
            ../sql/event_parse_data.cc ../sql/mdl.cc
+           ../sql/transaction.cc
            ${GEN_SOURCES}
            ${LIB_SOURCES})
 

=== modified file 'libmysqld/Makefile.am'
--- a/libmysqld/Makefile.am	2008-06-28 11:00:59 +0000
+++ b/libmysqld/Makefile.am	2008-07-19 01:23:51 +0000
@@ -78,7 +78,7 @@ sqlsources = derror.cc field.cc field_co
 	sp_head.cc sp_pcontext.cc sp.cc sp_cache.cc sp_rcontext.cc \
 	parse_file.cc sql_view.cc sql_trigger.cc my_decimal.cc \
 	rpl_filter.cc sql_partition.cc sql_builtin.cc sql_plugin.cc \
-	sql_tablespace.cc \
+	sql_tablespace.cc transaction.cc \
 	rpl_injector.cc my_user.c partition_info.cc \
 	sql_servers.cc ddl_blocker.cc si_objects.cc sql_audit.cc \
         event_parse_data.cc mdl.cc

=== modified file 'mysql-test/include/commit.inc'
--- a/mysql-test/include/commit.inc	2008-04-01 15:13:57 +0000
+++ b/mysql-test/include/commit.inc	2008-07-19 01:23:51 +0000
@@ -726,15 +726,15 @@ call p_verify_status_increment(4, 4, 4, 
 alter table t3 add column (b int);
 call p_verify_status_increment(2, 0, 2, 0);
 alter table t3 rename t4;
-call p_verify_status_increment(1, 0, 1, 0);
+call p_verify_status_increment(2, 0, 2, 0);
 rename table t4 to t3;
-call p_verify_status_increment(1, 0, 1, 0);
+call p_verify_status_increment(0, 0, 0, 0);
 truncate table t3;
 call p_verify_status_increment(2, 2, 2, 2);
 create view v1 as select * from t2;
-call p_verify_status_increment(1, 0, 1, 0);
+call p_verify_status_increment(2, 0, 2, 0);
 check table t1;
-call p_verify_status_increment(3, 0, 3, 0);
+call p_verify_status_increment(2, 0, 2, 0);
 --echo # Sic: after this bug is fixed, CHECK leaves no pending transaction
 commit;
 call p_verify_status_increment(0, 0, 0, 0);

=== added file 'mysql-test/include/wrap_trans_log.inc'
--- a/mysql-test/include/wrap_trans_log.inc	1970-01-01 00:00:00 +0000
+++ b/mysql-test/include/wrap_trans_log.inc	2008-07-19 01:23:51 +0000
@@ -0,0 +1,9 @@
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+--disable_result_log
+eval $statement;
+--enable_result_log
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+source include/show_binlog_events.inc;

=== modified file 'mysql-test/r/commit_1innodb.result'
--- a/mysql-test/r/commit_1innodb.result	2008-04-01 15:13:57 +0000
+++ b/mysql-test/r/commit_1innodb.result	2008-07-19 01:23:51 +0000
@@ -842,11 +842,11 @@ call p_verify_status_increment(2, 0, 2, 
 SUCCESS
 
 alter table t3 rename t4;
-call p_verify_status_increment(1, 0, 1, 0);
+call p_verify_status_increment(2, 0, 2, 0);
 SUCCESS
 
 rename table t4 to t3;
-call p_verify_status_increment(1, 0, 1, 0);
+call p_verify_status_increment(0, 0, 0, 0);
 SUCCESS
 
 truncate table t3;
@@ -854,13 +854,13 @@ call p_verify_status_increment(2, 2, 2, 
 SUCCESS
 
 create view v1 as select * from t2;
-call p_verify_status_increment(1, 0, 1, 0);
+call p_verify_status_increment(2, 0, 2, 0);
 SUCCESS
 
 check table t1;
 Table	Op	Msg_type	Msg_text
 test.t1	check	status	OK
-call p_verify_status_increment(3, 0, 3, 0);
+call p_verify_status_increment(2, 0, 2, 0);
 SUCCESS
 
 # Sic: after this bug is fixed, CHECK leaves no pending transaction

=== added file 'mysql-test/r/implicit_commit.result'
--- a/mysql-test/r/implicit_commit.result	1970-01-01 00:00:00 +0000
+++ b/mysql-test/r/implicit_commit.result	2008-07-19 01:23:51 +0000
@@ -0,0 +1,2024 @@
+SET GLOBAL EVENT_SCHEDULER = OFF;
+SET BINLOG_FORMAT = STATEMENT;
+CREATE DATABASE db1;
+USE db1;
+CREATE TABLE t1 (a INT, KEY a(a)) ENGINE=INNODB;
+INSERT INTO t1 VALUES (1),(2),(3),(4),(5);
+CREATE TABLE t3 (a INT) ENGINE=MyISAM;
+INSERT INTO t3 SELECT * FROM t1;
+SET AUTOCOMMIT = FALSE;
+#
+# SQLCOM_SELECT
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+select 1 as res from t1 where (1) in (select * from t1);
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_CREATE_TABLE LIKE
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+create table t2 like t1;
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+master-bin.000001	#	Query	#	#	use `db1`; create table t2 like t1
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_SHOW_CREATE
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+show create table t2;
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_DROP_TABLE
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+drop table t2;
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+master-bin.000001	#	Query	#	#	use `db1`; drop table t2
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_CREATE_TABLE TEMPORARY
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+create temporary table t2 as select * from t1;
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Query	#	#	use `db1`; create temporary table t2 as select * from t1
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_DROP_TABLE TEMPORARY
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+drop temporary table t2;
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Query	#	#	use `db1`; drop temporary table t2
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_CREATE_TABLE
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+create table t2 as select * from t1;
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+master-bin.000001	#	Query	#	#	use `db1`; create table t2 as select * from t1
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_UPDATE
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+update t2 set a=a+1 where (1) in (select * from t1);
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Query	#	#	use `db1`; update t2 set a=a+1 where (1) in (select * from t1)
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_INSERT
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+insert into t2 set a=((1) in (select * from t1));
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Query	#	#	use `db1`; insert into t2 set a=((1) in (select * from t1))
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_INSERT_SELECT
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+insert into t2 select * from t1;
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Query	#	#	use `db1`; insert into t2 select * from t1
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_REPLACE
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+replace t2 set a=((1) in (select * from t1));
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Query	#	#	use `db1`; replace t2 set a=((1) in (select * from t1))
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_REPLACE_SELECT
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+replace t2 select * from t1;
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Query	#	#	use `db1`; replace t2 select * from t1
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_DELETE
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+delete from t2 where (1) in (select * from t1);
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Query	#	#	use `db1`; delete from t2 where (1) in (select * from t1)
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_DELETE_MULTI
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+delete t2, t3 from t2, t3 where (1) in (select * from t1);
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Query	#	#	use `db1`; delete t2, t3 from t2, t3 where (1) in (select * from t1)
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_UPDATE_MULTI
+#
+select * from t2;
+a
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+update t2, t3 set t3.a=t2.a, t2.a=null where (1) in (select * from t1);
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Query	#	#	use `db1`; update t2, t3 set t3.a=t2.a, t2.a=null where (1) in (select * from t1)
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_LOAD
+#
+create table t4 (a varchar(100));
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+load data infile '../std_data_ln/words.dat' into table t4;
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Begin_load_query	#	#	;file_id=#;block_len=581
+master-bin.000001	#	Execute_load_query	#	#	use `db1`; load data infile '../std_data_ln/words.dat' into table t4 ;file_id=#
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+drop table t4;
+#
+# SQLCOM_SHOW_DATABASES
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+show databases where (1) in (select * from t1);
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_SHOW_TABLES
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+show tables where (1) in (select * from t1);
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_SHOW_FIELDS
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+show fields from t1 where (1) in (select * from t1);
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_SHOW_KEYS
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+show keys from t1 where (1) in (select * from t1);
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_SHOW_VARIABLES
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+show variables where (1) in (select * from t1);
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_SHOW_STATUS
+#
+#
+# SQLCOM_SHOW_ENGINE_MUTEX
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+show engine all mutex;
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_SHOW_PROCESSLIST
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+show processlist;
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_SHOW_ENGINE_LOGS
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+show engine all logs;
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_SHOW_ENGINE_STATUS
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+show engine all status;
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_SHOW_CHARSETS
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+show charset where (1) in (select * from t1);
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_SHOW_COLLATIONS
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+show collation where (1) in (select * from t1);
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_SHOW_TABLE_STATUS
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+show table status where (1) in (select * from t1);
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_SHOW_TRIGGERS
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+show triggers where (1) in (select * from t1);
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_SHOW_OPEN_TABLES
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+show open tables where (1) in (select * from t1);
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_SHOW_STATUS_PROC
+#
+#
+# SQLCOM_SHOW_STATUS_FUNC
+#
+#
+# SQLCOM_SET_OPTION
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+set @a=((1) in (select * from t1));
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_DO
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+do ((1) in (select * from t1));
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_CALL
+#
+create procedure p1(a int) begin end;
+drop procedure p1;
+#
+# SQLCOM_CREATE_VIEW
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+create view v1 as select * from t1;
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+master-bin.000001	#	Query	#	#	use `db1`; CREATE ALGORITHM=UNDEFINED DEFINER=`root`@`localhost` SQL SECURITY DEFINER VIEW `v1` AS select * from t1
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_ALTER_VIEW
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+alter view v1 as select 2;
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+master-bin.000001	#	Query	#	#	use `db1`; ALTER ALGORITHM=UNDEFINED DEFINER=`root`@`localhost` SQL SECURITY DEFINER VIEW `v1` AS select 2
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_DROP_VIEW
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+drop view v1;
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+master-bin.000001	#	Query	#	#	use `db1`; drop view v1
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_CREATE_INDEX
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+create index idx1 on t1(a);
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+master-bin.000001	#	Query	#	#	use `db1`; create index idx1 on t1(a)
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_DROP_INDEX
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+drop index idx1 on t1;
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+master-bin.000001	#	Query	#	#	use `db1`; drop index idx1 on t1
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_ALTER_TABLE
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+alter table t1 add column b int;
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+master-bin.000001	#	Query	#	#	use `db1`; alter table t1 add column b int
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+alter table t1 change b c int;
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+master-bin.000001	#	Query	#	#	use `db1`; alter table t1 change b c int
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+alter table t1 drop column c;
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+master-bin.000001	#	Query	#	#	use `db1`; alter table t1 drop column c
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_ALTER_TABLE TEMPORARY
+#
+create temporary table t4 (a int);
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+alter table t1 add column b int;
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+master-bin.000001	#	Query	#	#	use `db1`; alter table t1 add column b int
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+alter table t1 change b c int;
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+master-bin.000001	#	Query	#	#	use `db1`; alter table t1 change b c int
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+alter table t1 drop column c;
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+master-bin.000001	#	Query	#	#	use `db1`; alter table t1 drop column c
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+drop table t4;
+#
+# SQLCOM_TRUNCATE
+#
+insert into t2 select * from t1;
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+truncate table t2;
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+master-bin.000001	#	Query	#	#	use `db1`; truncate table t2
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+insert into t2 select * from t1;
+#
+# SQLCOM_TRUNCATE TEMPORARY
+#
+create temporary table t4 as select * from t1;
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+truncate table t4;
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+master-bin.000001	#	Query	#	#	use `db1`; truncate table t4
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+drop temporary table t4;
+#
+# SQLCOM_SHOW_MASTER_STAT
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+show master status;
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_SHOW_SLAVE_STAT
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+show slave status;
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_GRANT
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+grant all on test.t1 to mysqltest_2@localhost with grant option;
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+master-bin.000001	#	Query	#	#	use `db1`; grant all on test.t1 to mysqltest_2@localhost with grant option
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_REVOKE
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+revoke select on test.t1 from mysqltest_2@localhost;
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+master-bin.000001	#	Query	#	#	use `db1`; revoke select on test.t1 from mysqltest_2@localhost
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_REVOKE_ALL
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+revoke all on test.t1 from mysqltest_2@localhost;
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+master-bin.000001	#	Query	#	#	use `db1`; revoke all on test.t1 from mysqltest_2@localhost
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_SHOW_GRANTS
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+show grants;
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+show grants for current_user();
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_LOCK_TABLES
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+lock tables t1 write;
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_UNLOCK_TABLES
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+unlock tables;
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_CREATE_DB
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+create database db2;
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+master-bin.000001	#	Query	#	#	create database db2
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_CHANGE_DB
+#
+create table db2.t1 (a int);
+insert into db2.t1 values (1);
+commit;
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+use db2;
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db2`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Query	#	#	use `db2`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_SHOW_CREATE_DB
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+show create database db2;
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db2`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Query	#	#	use `db2`; INSERT INTO t1 (a) VALUES (2)
+#
+# SQLCOM_ALTER_DB
+#
+#
+# SQLCOM_ALTER_DB_UPGRADE
+#
+#
+# SQLCOM_DROP_DB
+#
+use db1;
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+drop database db2;
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+master-bin.000001	#	Query	#	#	drop database db2
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_REPAIR
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+repair table t2;
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+master-bin.000001	#	Query	#	#	use `db1`; repair table t2
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+repair table t2 use_frm;
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+master-bin.000001	#	Query	#	#	use `db1`; repair table t2 use_frm
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_OPTIMIZE
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+optimize table t1;
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+master-bin.000001	#	Query	#	#	use `db1`; optimize table t1
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_CHECK
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+check table t1;
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+check table t1 extended;
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_ASSIGN_TO_KEYCACHE
+#
+set global keycache.key_buffer_size=128*1024;
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+cache index t3 in keycache;
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+set global keycache.key_buffer_size=0;
+#
+# SQLCOM_PRELOAD_KEYS
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+load index into cache t3;
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_FLUSH
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+flush local privileges;
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+flush privileges;
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Query	#	#	use `db1`; flush privileges
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_KILL
+#
+#
+# SQLCOM_ANALYZE
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+analyze table t1;
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+master-bin.000001	#	Query	#	#	use `db1`; analyze table t1
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_ROLLBACK
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+rollback;
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_ROLLBACK_TO_SAVEPOINT
+#
+#
+# SQLCOM_COMMIT
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+commit;
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_SAVEPOINT
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+savepoint sp1;
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Query	#	#	use `db1`; savepoint sp1
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_RELEASE_SAVEPOINT
+#
+#
+# SQLCOM_SLAVE_START
+#
+#
+# SQLCOM_SLAVE_STOP
+#
+#
+# SQLCOM_BEGIN
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+begin;
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_CHANGE_MASTER
+#
+#
+# SQLCOM_RENAME_TABLE
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+rename table t3 to t4;
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+master-bin.000001	#	Query	#	#	use `db1`; rename table t3 to t4
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+rename table t4 to t3;
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+master-bin.000001	#	Query	#	#	use `db1`; rename table t4 to t3
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_RESET
+#
+#
+# SQLCOM_PURGE
+#
+#
+# SQLCOM_PURGE_BEFORE
+#
+#
+# SQLCOM_SHOW_BINLOGS
+#
+#
+# SQLCOM_HA_OPEN
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+handler t1 open as ha1;
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_HA_READ
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+handler ha1 read a first;
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_HA_CLOSE
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+handler ha1 close;
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_SHOW_SLAVE_HOSTS
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+show slave hosts;
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_SHOW_BINLOG_EVENTS
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+show binlog events;
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_SHOW_NEW_MASTER
+#
+#
+# SQLCOM_SHOW_WARNS
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+show warnings;
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_EMPTY_QUERY
+#
+#
+# SQLCOM_SHOW_ERRORS
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+show errors;
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_SHOW_STORAGE_ENGINES
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+show engines;
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_SHOW_PRIVILEGES
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+show privileges;
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_HELP
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+help 'foo';
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_CREATE_USER
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+create user trxusr1;
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+master-bin.000001	#	Query	#	#	use `db1`; create user trxusr1
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_RENAME_USER
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+rename user 'trxusr1' to 'trxusr2';
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+master-bin.000001	#	Query	#	#	use `db1`; rename user 'trxusr1' to 'trxusr2'
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_DROP_USER
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+drop user trxusr2;
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+master-bin.000001	#	Query	#	#	use `db1`; drop user trxusr2
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_CHECKSUM
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+checksum table t1;
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_CREATE_PROCEDURE
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+create procedure p1(a int) begin end;
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+master-bin.000001	#	Query	#	#	use `db1`; CREATE DEFINER=`root`@`localhost` PROCEDURE `p1`(a int)
+begin end
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_ALTER_PROCEDURE
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+alter procedure p1 comment 'foobar';
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+master-bin.000001	#	Query	#	#	use `db1`; alter procedure p1 comment 'foobar'
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_SHOW_CREATE_PROC
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+show create procedure p1;
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_SHOW_STATUS_PROC
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+show procedure status;
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_SHOW_PROC_CODE
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+show procedure code p1;
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_DROP_PROCEDURE
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+drop procedure p1;
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+master-bin.000001	#	Query	#	#	use `db1`; drop procedure p1
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_CREATE_FUNCTION
+#
+#
+# SQLCOM_DROP_FUNCTION
+#
+#
+# SQLCOM_CREATE_SPFUNCTION
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+create function f1() returns int return 69;
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+master-bin.000001	#	Query	#	#	use `db1`; CREATE DEFINER=`root`@`localhost` FUNCTION `f1`() RETURNS int(11)
+return 69
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_ALTER_FUNCTION
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+alter function f1 comment 'comment';
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+master-bin.000001	#	Query	#	#	use `db1`; alter function f1 comment 'comment'
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_SHOW_CREATE_FUNC
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+show create function f1;
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_SHOW_STATUS_FUNC
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+show function status like '%f%';
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_SHOW_FUNC_CODE
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+show function code f1;
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_PREPARE
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+prepare stmt1 from "insert into t1 values (5)";
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_EXECUTE
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+execute stmt1;
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Query	#	#	use `db1`; insert into t1 values (5)
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_DEALLOCATE_PREPARE
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+deallocate prepare stmt1;
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_CREATE_TRIGGER
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+create trigger trg1 before insert on t1 for each row set @a:=1;
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+master-bin.000001	#	Query	#	#	use `db1`; CREATE DEFINER=`root`@`localhost` trigger trg1 before insert on t1 for each row set @a:=1
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_SHOW_CREATE_TRIGGER
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+show create trigger trg1;
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_DROP_TRIGGER
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+drop trigger trg1;
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+master-bin.000001	#	Query	#	#	use `db1`; drop trigger trg1
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_XA_START
+#
+#
+# SQLCOM_XA_END
+#
+#
+# SQLCOM_XA_PREPARE
+#
+#
+# SQLCOM_XA_COMMIT
+#
+#
+# SQLCOM_XA_ROLLBACK
+#
+#
+# SQLCOM_XA_RECOVER
+#
+#
+# SQLCOM_ALTER_TABLESPACE
+#
+#
+# SQLCOM_INSTALL_PLUGIN
+#
+#
+# SQLCOM_SHOW_PLUGINS
+#
+#
+# SQLCOM_UNINSTALL_PLUGIN
+#
+#
+# SQLCOM_SHOW_AUTHORS
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+show authors;
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_BINLOG_BASE64_EVENT
+#
+#
+# SQLCOM_SHOW_CONTRIBUTORS
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+show contributors;
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_CREATE_SERVER
+#
+#
+# SQLCOM_ALTER_SERVER
+#
+#
+# SQLCOM_DROP_SERVER
+#
+#
+# SQLCOM_CREATE_EVENT
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+create event ev1 on schedule every 1 second do insert into t1 values (6);
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+master-bin.000001	#	Query	#	#	use `db1`; create event ev1 on schedule every 1 second do insert into t1 values (6)
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_ALTER_EVENT
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+alter event ev1 rename to ev2 disable;
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+master-bin.000001	#	Query	#	#	use `db1`; alter event ev1 rename to ev2 disable
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_SHOW_CREATE_EVENT
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+show create event ev2;
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_SHOW_EVENTS
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+show events;
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_DROP_EVENT
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+drop event ev2;
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+master-bin.000001	#	Query	#	#	use `db1`; drop event ev2
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_BACKUP
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+backup database db1 to 'backup_db1.ba';
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_SHOW_ARCHIVE
+#
+#
+# SQLCOM_RESTORE
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+restore from 'backup_db1.ba';
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+master-bin.000001	#	Query	#	#	DROP DATABASE IF EXISTS `db1`
+master-bin.000001	#	Query	#	#	CREATE DATABASE `db1` DEFAULT CHARACTER SET latin1
+master-bin.000001	#	Query	#	#	DROP TABLE IF EXISTS `db1`.`t1`
+master-bin.000001	#	Query	#	#	use `db1`; CREATE TABLE `t1` (
+  `a` int(11) DEFAULT NULL,
+  KEY `a` (`a`)
+) ENGINE=InnoDB DEFAULT CHARSET=latin1
+master-bin.000001	#	Query	#	#	use `db1`; DROP TABLE IF EXISTS `db1`.`t2`
+master-bin.000001	#	Query	#	#	use `db1`; CREATE TABLE `t2` (
+  `a` int(11) DEFAULT NULL
+) ENGINE=MyISAM DEFAULT CHARSET=latin1
+master-bin.000001	#	Query	#	#	use `db1`; DROP TABLE IF EXISTS `db1`.`t3`
+master-bin.000001	#	Query	#	#	use `db1`; CREATE TABLE `t3` (
+  `a` int(11) DEFAULT NULL
+) ENGINE=MyISAM DEFAULT CHARSET=latin1
+master-bin.000001	#	Query	#	#	use `db1`; CREATE DEFINER=`root`@`localhost` FUNCTION `f1`() RETURNS int(11)
+    COMMENT 'comment'
+return 69
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_BACKUP_TEST
+#
+#
+# SQLCOM_SHOW_PROFILE
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+show profile memory;
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+#
+# SQLCOM_SHOW_PROFILES
+#
+RESET MASTER;
+BEGIN;
+INSERT INTO t1 (a) VALUES (1);
+show profiles;
+INSERT INTO t1 (a) VALUES (2);
+COMMIT;
+show binlog events from <binlog_start>;
+Log_name	Pos	Event_type	Server_id	End_log_pos	Info
+master-bin.000001	#	Query	#	#	use `db1`; BEGIN
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (1)
+master-bin.000001	#	Query	#	#	use `db1`; INSERT INTO t1 (a) VALUES (2)
+master-bin.000001	#	Xid	#	#	COMMIT /* XID */
+DROP TABLE t1;
+DROP TABLE t2;
+DROP TABLE t3;
+USE test;
+DROP DATABASE db1;
+End of tests

=== added file 'mysql-test/t/implicit_commit.test'
--- a/mysql-test/t/implicit_commit.test	1970-01-01 00:00:00 +0000
+++ b/mysql-test/t/implicit_commit.test	2008-07-19 01:23:51 +0000
@@ -0,0 +1,1149 @@
+source include/have_innodb.inc;
+source include/have_log_bin.inc;
+
+SET GLOBAL EVENT_SCHEDULER = OFF;
+SET BINLOG_FORMAT = STATEMENT;
+
+LET $OLD_DB= `SELECT DATABASE()`;
+
+CREATE DATABASE db1;
+USE db1;
+CREATE TABLE t1 (a INT, KEY a(a)) ENGINE=INNODB;
+INSERT INTO t1 VALUES (1),(2),(3),(4),(5);
+CREATE TABLE t3 (a INT) ENGINE=MyISAM;
+INSERT INTO t3 SELECT * FROM t1;
+
+SET AUTOCOMMIT = FALSE;
+
+--echo #
+--echo # SQLCOM_SELECT
+--echo #
+
+let $statement=
+  select 1 as res from t1 where (1) in (select * from t1);
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_CREATE_TABLE LIKE
+--echo #
+
+let $statement=
+  create table t2 like t1;
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_SHOW_CREATE
+--echo #
+
+let $statement=
+  show create table t2;
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_DROP_TABLE
+--echo #
+
+let $statement=
+  drop table t2;
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_CREATE_TABLE TEMPORARY
+--echo #
+
+let $statement=
+  create temporary table t2 as select * from t1;
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_DROP_TABLE TEMPORARY
+--echo #
+
+let $statement=
+  drop temporary table t2;
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_CREATE_TABLE
+--echo #
+
+let $statement=
+  create table t2 as select * from t1;
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_UPDATE
+--echo #
+
+let $statement=
+  update t2 set a=a+1 where (1) in (select * from t1);
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_INSERT
+--echo #
+
+let $statement=
+  insert into t2 set a=((1) in (select * from t1));
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_INSERT_SELECT
+--echo #
+
+let $statement=
+  insert into t2 select * from t1;
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_REPLACE
+--echo #
+
+let $statement=
+  replace t2 set a=((1) in (select * from t1));
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_REPLACE_SELECT
+--echo #
+
+let $statement=
+  replace t2 select * from t1;
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_DELETE
+--echo #
+
+let $statement=
+  delete from t2 where (1) in (select * from t1);
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_DELETE_MULTI
+--echo #
+
+let $statement=
+  delete t2, t3 from t2, t3 where (1) in (select * from t1);
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_UPDATE_MULTI
+--echo #
+
+select * from t2;
+let $statement=
+  update t2, t3 set t3.a=t2.a, t2.a=null where (1) in (select * from t1);
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_LOAD
+--echo #
+
+create table t4 (a varchar(100));
+
+let $statement=
+  load data infile '../std_data_ln/words.dat' into table t4;
+source include/wrap_trans_log.inc;
+
+drop table t4;
+
+--echo #
+--echo # SQLCOM_SHOW_DATABASES
+--echo #
+
+let $statement=
+  show databases where (1) in (select * from t1);
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_SHOW_TABLES
+--echo #
+
+let $statement=
+  show tables where (1) in (select * from t1);
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_SHOW_FIELDS
+--echo #
+
+let $statement=
+  show fields from t1 where (1) in (select * from t1);
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_SHOW_KEYS
+--echo #
+
+let $statement=
+  show keys from t1 where (1) in (select * from t1);
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_SHOW_VARIABLES
+--echo #
+
+let $statement=
+  show variables where (1) in (select * from t1);
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_SHOW_STATUS
+--echo #
+
+#
+# Bug#37908
+#
+#let $statement=
+#  show status where (1) in (select * from t1);
+#source include/wrap_trans_log.inc;
+#
+
+--echo #
+--echo # SQLCOM_SHOW_ENGINE_MUTEX
+--echo #
+
+let $statement=
+  show engine all mutex;
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_SHOW_PROCESSLIST
+--echo #
+
+let $statement=
+  show processlist;
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_SHOW_ENGINE_LOGS
+--echo #
+
+let $statement=
+  show engine all logs;
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_SHOW_ENGINE_STATUS
+--echo #
+
+let $statement=
+  show engine all status;
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_SHOW_CHARSETS
+--echo #
+
+let $statement=
+  show charset where (1) in (select * from t1);
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_SHOW_COLLATIONS
+--echo #
+
+let $statement=
+  show collation where (1) in (select * from t1);
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_SHOW_TABLE_STATUS
+--echo #
+
+let $statement=
+  show table status where (1) in (select * from t1);
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_SHOW_TRIGGERS
+--echo #
+
+let $statement=
+  show triggers where (1) in (select * from t1);
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_SHOW_OPEN_TABLES
+--echo #
+
+let $statement=
+  show open tables where (1) in (select * from t1);
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_SHOW_STATUS_PROC
+--echo #
+
+#
+# Bug#37908
+#
+#let $statement=
+#  show procedure status where (1) in (select * from t1);
+#source include/wrap_trans_log.inc;
+#
+
+--echo #
+--echo # SQLCOM_SHOW_STATUS_FUNC
+--echo #
+
+#
+# Bug#37908
+#
+#let $statement=
+#  show function status where (1) in (select * from t1);
+#source include/wrap_trans_log.inc;
+#
+
+--echo #
+--echo # SQLCOM_SET_OPTION
+--echo #
+
+let $statement=
+  set @a=((1) in (select * from t1));
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_DO
+--echo #
+
+let $statement=
+  do ((1) in (select * from t1));
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_CALL
+--echo #
+
+create procedure p1(a int) begin end;
+
+#
+# Bug#37949
+#
+#let $statement=
+#  call p1((1) in (select * from t1));
+#source include/wrap_trans_log.inc;
+#
+
+drop procedure p1;
+
+--echo #
+--echo # SQLCOM_CREATE_VIEW
+--echo #
+
+let $statement=
+  create view v1 as select * from t1;
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_ALTER_VIEW
+--echo #
+
+let $statement=
+  alter view v1 as select 2;
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_DROP_VIEW
+--echo #
+
+let $statement=
+  drop view v1;
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_CREATE_INDEX
+--echo #
+
+let $statement=
+  create index idx1 on t1(a);
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_DROP_INDEX
+--echo #
+
+let $statement=
+  drop index idx1 on t1;
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_ALTER_TABLE
+--echo #
+
+let $statement=
+  alter table t1 add column b int;
+source include/wrap_trans_log.inc;
+
+let $statement=
+  alter table t1 change b c int;
+source include/wrap_trans_log.inc;
+
+let $statement=
+  alter table t1 drop column c;
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_ALTER_TABLE TEMPORARY
+--echo #
+
+create temporary table t4 (a int);
+
+let $statement=
+  alter table t1 add column b int;
+source include/wrap_trans_log.inc;
+
+let $statement=
+  alter table t1 change b c int;
+source include/wrap_trans_log.inc;
+
+let $statement=
+  alter table t1 drop column c;
+source include/wrap_trans_log.inc;
+
+drop table t4;
+
+--echo #
+--echo # SQLCOM_TRUNCATE
+--echo #
+
+insert into t2 select * from t1;
+let $statement=
+  truncate table t2;
+source include/wrap_trans_log.inc;
+insert into t2 select * from t1;
+
+--echo #
+--echo # SQLCOM_TRUNCATE TEMPORARY
+--echo #
+
+create temporary table t4 as select * from t1;
+let $statement=
+  truncate table t4;
+source include/wrap_trans_log.inc;
+drop temporary table t4;
+
+--echo #
+--echo # SQLCOM_SHOW_MASTER_STAT
+--echo #
+
+let $statement=
+  show master status;
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_SHOW_SLAVE_STAT
+--echo #
+
+let $statement=
+  show slave status;
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_GRANT
+--echo #
+
+let $statement=
+  grant all on test.t1 to mysqltest_2@localhost with grant option;
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_REVOKE
+--echo #
+let $statement=
+  revoke select on test.t1 from mysqltest_2@localhost;
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_REVOKE_ALL
+--echo #
+
+let $statement=
+  revoke all on test.t1 from mysqltest_2@localhost;
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_SHOW_GRANTS
+--echo #
+
+let $statement=
+  show grants;
+source include/wrap_trans_log.inc;
+
+let $statement=
+  show grants for current_user();
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_LOCK_TABLES
+--echo #
+
+let $statement=
+  lock tables t1 write;
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_UNLOCK_TABLES
+--echo #
+
+let $statement=
+  unlock tables;
+source include/wrap_trans_log.inc;
+
+# faltando lock tables transactional
+
+--echo #
+--echo # SQLCOM_CREATE_DB
+--echo #
+
+let $statement=
+  create database db2;
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_CHANGE_DB
+--echo #
+
+create table db2.t1 (a int);
+insert into db2.t1 values (1);
+commit;
+
+let $statement=
+  use db2;
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_SHOW_CREATE_DB
+--echo #
+
+let $statement=
+  show create database db2;
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_ALTER_DB
+--echo #
+
+#let $statement=
+#  alter database db2 character set koi8r;
+#source include/wrap_trans_log.inc;
+
+#let $statement=
+#  alter database db2 collate cp1251_general_cs;
+#source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_ALTER_DB_UPGRADE
+--echo #
+
+#let $statement=
+#  alter database `#mysql50#db3` upgrade data directory name;
+#source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_DROP_DB
+--echo #
+
+use db1;
+
+let $statement=
+  drop database db2;
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_REPAIR
+--echo #
+
+let $statement=
+  repair table t2;
+source include/wrap_trans_log.inc;
+
+let $statement=
+  repair table t2 use_frm;
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_OPTIMIZE
+--echo #
+
+let $statement=
+  optimize table t1;
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_CHECK
+--echo #
+
+let $statement=
+  check table t1;
+source include/wrap_trans_log.inc;
+
+let $statement=
+  check table t1 extended;
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_ASSIGN_TO_KEYCACHE
+--echo #
+
+set global keycache.key_buffer_size=128*1024;
+
+let $statement=
+  cache index t3 in keycache;
+source include/wrap_trans_log.inc;
+
+set global keycache.key_buffer_size=0;
+
+--echo #
+--echo # SQLCOM_PRELOAD_KEYS
+--echo #
+
+let $statement=
+  load index into cache t3;
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_FLUSH
+--echo #
+
+let $statement=
+  flush local privileges;
+source include/wrap_trans_log.inc;
+
+let $statement=
+  flush privileges;
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_KILL
+--echo #
+
+#
+#
+#
+
+--echo #
+--echo # SQLCOM_ANALYZE
+--echo #
+
+let $statement=
+  analyze table t1;
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_ROLLBACK
+--echo #
+
+let $statement=
+  rollback;
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_ROLLBACK_TO_SAVEPOINT
+--echo #
+
+
+--echo #
+--echo # SQLCOM_COMMIT
+--echo #
+
+let $statement=
+  commit;
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_SAVEPOINT
+--echo #
+
+let $statement=
+  savepoint sp1;
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_RELEASE_SAVEPOINT
+--echo #
+
+--echo #
+--echo # SQLCOM_SLAVE_START
+--echo #
+
+--echo #
+--echo # SQLCOM_SLAVE_STOP
+--echo #
+
+--echo #
+--echo # SQLCOM_BEGIN
+--echo #
+
+let $statement=
+  begin;
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_CHANGE_MASTER
+--echo #
+
+--echo #
+--echo # SQLCOM_RENAME_TABLE
+--echo #
+
+let $statement=
+  rename table t3 to t4;
+source include/wrap_trans_log.inc;
+
+let $statement=
+  rename table t4 to t3;
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_RESET
+--echo #
+
+--echo #
+--echo # SQLCOM_PURGE
+--echo #
+
+--echo #
+--echo # SQLCOM_PURGE_BEFORE
+--echo #
+
+--echo #
+--echo # SQLCOM_SHOW_BINLOGS
+--echo #
+
+--echo #
+--echo # SQLCOM_HA_OPEN
+--echo #
+
+let $statement=
+  handler t1 open as ha1;
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_HA_READ
+--echo #
+
+let $statement=
+  handler ha1 read a first;
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_HA_CLOSE
+--echo #
+
+let $statement=
+  handler ha1 close;
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_SHOW_SLAVE_HOSTS
+--echo #
+
+let $statement=
+  show slave hosts;
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_SHOW_BINLOG_EVENTS
+--echo #
+
+let $statement=
+  show binlog events;
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_SHOW_NEW_MASTER
+--echo #
+
+--echo #
+--echo # SQLCOM_SHOW_WARNS
+--echo #
+
+let $statement=
+  show warnings;
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_EMPTY_QUERY
+--echo #
+
+--echo #
+--echo # SQLCOM_SHOW_ERRORS
+--echo #
+
+let $statement=
+  show errors;
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_SHOW_STORAGE_ENGINES
+--echo #
+
+let $statement=
+  show engines;
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_SHOW_PRIVILEGES
+--echo #
+
+let $statement=
+  show privileges;
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_HELP
+--echo #
+
+let $statement=
+  help 'foo';
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_CREATE_USER
+--echo #
+
+let $statement=
+  create user trxusr1;
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_RENAME_USER
+--echo #
+
+let $statement=
+  rename user 'trxusr1' to 'trxusr2';
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_DROP_USER
+--echo #
+
+let $statement=
+  drop user trxusr2;
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_CHECKSUM
+--echo #
+
+let $statement=
+  checksum table t1;
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_CREATE_PROCEDURE
+--echo #
+
+let $statement=
+  create procedure p1(a int) begin end;
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_ALTER_PROCEDURE
+--echo #
+
+let $statement=
+  alter procedure p1 comment 'foobar';
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_SHOW_CREATE_PROC
+--echo #
+
+let $statement=
+  show create procedure p1;
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_SHOW_STATUS_PROC
+--echo #
+
+let $statement=
+  show procedure status;
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_SHOW_PROC_CODE
+--echo #
+
+let $statement=
+  show procedure code p1;
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_DROP_PROCEDURE
+--echo #
+
+let $statement=
+  drop procedure p1;
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_CREATE_FUNCTION
+--echo #
+
+--echo #
+--echo # SQLCOM_DROP_FUNCTION
+--echo #
+
+--echo #
+--echo # SQLCOM_CREATE_SPFUNCTION
+--echo #
+
+let $statement=
+  create function f1() returns int return 69;
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_ALTER_FUNCTION
+--echo #
+
+let $statement=
+  alter function f1 comment 'comment';
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_SHOW_CREATE_FUNC
+--echo #
+
+let $statement=
+  show create function f1;
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_SHOW_STATUS_FUNC
+--echo #
+
+let $statement=
+  show function status like '%f%';
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_SHOW_FUNC_CODE
+--echo #
+
+let $statement=
+  show function code f1;
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_PREPARE
+--echo #
+
+let $statement=
+  prepare stmt1 from "insert into t1 values (5)";
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_EXECUTE
+--echo #
+
+let $statement=
+  execute stmt1;
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_DEALLOCATE_PREPARE
+--echo #
+
+let $statement=
+  deallocate prepare stmt1;
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_CREATE_TRIGGER
+--echo #
+
+let $statement=
+  create trigger trg1 before insert on t1 for each row set @a:=1;
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_SHOW_CREATE_TRIGGER
+--echo #
+
+let $statement=
+  show create trigger trg1;
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_DROP_TRIGGER
+--echo #
+
+let $statement=
+  drop trigger trg1;
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_XA_START
+--echo #
+
+--echo #
+--echo # SQLCOM_XA_END
+--echo #
+
+--echo #
+--echo # SQLCOM_XA_PREPARE
+--echo #
+
+--echo #
+--echo # SQLCOM_XA_COMMIT
+--echo #
+
+--echo #
+--echo # SQLCOM_XA_ROLLBACK
+--echo #
+
+--echo #
+--echo # SQLCOM_XA_RECOVER
+--echo #
+
+--echo #
+--echo # SQLCOM_ALTER_TABLESPACE
+--echo #
+
+--echo #
+--echo # SQLCOM_INSTALL_PLUGIN
+--echo #
+
+--echo #
+--echo # SQLCOM_SHOW_PLUGINS
+--echo #
+
+--echo #
+--echo # SQLCOM_UNINSTALL_PLUGIN
+--echo #
+
+--echo #
+--echo # SQLCOM_SHOW_AUTHORS
+--echo #
+
+let $statement=
+  show authors;
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_BINLOG_BASE64_EVENT
+--echo #
+
+--echo #
+--echo # SQLCOM_SHOW_CONTRIBUTORS
+--echo #
+
+let $statement=
+  show contributors;
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_CREATE_SERVER
+--echo #
+
+--echo #
+--echo # SQLCOM_ALTER_SERVER
+--echo #
+
+--echo #
+--echo # SQLCOM_DROP_SERVER
+--echo #
+
+--echo #
+--echo # SQLCOM_CREATE_EVENT
+--echo #
+
+let $statement=
+  create event ev1 on schedule every 1 second do insert into t1 values (6);
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_ALTER_EVENT
+--echo #
+
+let $statement=
+  alter event ev1 rename to ev2 disable;
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_SHOW_CREATE_EVENT
+--echo #
+
+let $statement=
+  show create event ev2;
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_SHOW_EVENTS
+--echo #
+
+let $statement=
+  show events;
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_DROP_EVENT
+--echo #
+
+let $statement=
+  drop event ev2;
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_BACKUP
+--echo #
+
+let $statement=
+  backup database db1 to 'backup_db1.ba';
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_SHOW_ARCHIVE
+--echo #
+
+#
+# --error ER_NOT_ALLOWED_COMMAND
+#
+#let $statement=
+#  show backup 'backup_db1.ba';
+#source include/wrap_trans_log.inc;
+#
+
+--echo #
+--echo # SQLCOM_RESTORE
+--echo #
+
+let $statement=
+  restore from 'backup_db1.ba';
+source include/wrap_trans_log.inc;
+
+--remove_file $MYSQLTEST_VARDIR/master-data/backup_db1.ba
+
+--echo #
+--echo # SQLCOM_BACKUP_TEST
+--echo #
+
+# BACKUP_TEST
+
+--echo #
+--echo # SQLCOM_SHOW_PROFILE
+--echo #
+
+let $statement=
+  show profile memory;
+source include/wrap_trans_log.inc;
+
+--echo #
+--echo # SQLCOM_SHOW_PROFILES
+--echo #
+
+let $statement=
+  show profiles;
+source include/wrap_trans_log.inc;
+
+DROP TABLE t1;
+DROP TABLE t2;
+DROP TABLE t3;
+eval USE $OLD_DB;
+DROP DATABASE db1;
+
+--echo End of tests

=== modified file 'sql/CMakeLists.txt'
--- a/sql/CMakeLists.txt	2008-06-28 11:00:59 +0000
+++ b/sql/CMakeLists.txt	2008-07-19 01:23:51 +0000
@@ -74,7 +74,7 @@ ADD_EXECUTABLE(mysqld
                sql_tablespace.cc events.cc ../sql-common/my_user.c 
                partition_info.cc rpl_utility.cc rpl_injector.cc sql_locale.cc
                rpl_rli.cc rpl_mi.cc sql_servers.cc sql_audit.cc
-               sql_connect.cc scheduler.cc 
+               sql_connect.cc scheduler.cc transaction.cc
                ddl_blocker.cc si_objects.cc
                sql_profile.cc event_parse_data.cc mdl.cc
                ${PROJECT_SOURCE_DIR}/sql/sql_yacc.cc

=== modified file 'sql/Makefile.am'
--- a/sql/Makefile.am	2008-06-28 11:00:59 +0000
+++ b/sql/Makefile.am	2008-07-19 01:23:51 +0000
@@ -87,7 +87,7 @@ noinst_HEADERS =	item.h item_func.h item
 			sql_plugin.h authors.h event_parse_data.h \
 			event_data_objects.h event_scheduler.h \
 			sql_partition.h partition_info.h partition_element.h \
-			probes.h sql_audit.h \
+			probes.h sql_audit.h transaction.h \
 			contributors.h sql_servers.h ddl_blocker.h \
 			si_objects.h sql_plist.h mdl.h
 
@@ -135,7 +135,7 @@ mysqld_SOURCES =	sql_lex.cc sql_handler.
 			sql_builtin.cc sql_tablespace.cc partition_info.cc \
 			sql_servers.cc sql_audit.cc sha2.cc \
 			ddl_blocker.cc si_objects.cc event_parse_data.cc \
-			mdl.cc
+			mdl.cc transaction.cc
 
 if HAVE_DTRACE
   mysqld_SOURCES += probes.d

=== modified file 'sql/backup/be_snapshot.cc'
--- a/sql/backup/be_snapshot.cc	2008-03-20 14:53:16 +0000
+++ b/sql/backup/be_snapshot.cc	2008-07-19 01:23:51 +0000
@@ -87,7 +87,7 @@ result_t Backup::lock()
   locking_thd->m_thd->lex->sql_command= SQLCOM_SELECT; 
   locking_thd->m_thd->lex->start_transaction_opt|=
     MYSQL_START_TRANS_OPT_WITH_CONS_SNAPSHOT;
-  int res= begin_trans(locking_thd->m_thd);
+  int res= trans_begin(locking_thd->m_thd);
   if (res)
     DBUG_RETURN(ERROR);
   locking_thd->lock_state= LOCK_ACQUIRED;
@@ -121,8 +121,8 @@ result_t Backup::get_data(Buffer &buf)
   if (locking_thd->lock_state == LOCK_SIGNAL)
   {
     locking_thd->lock_state= LOCK_DONE; // set lock done so destructor won't wait
-    ha_autocommit_or_rollback(locking_thd->m_thd, 0);
-    end_active_trans(locking_thd->m_thd);
+    trans_commit_stmt(locking_thd->m_thd);
+    trans_commit_implicit(locking_thd->m_thd);
     close_thread_tables(locking_thd->m_thd);
   }
   return(res);

=== modified file 'sql/backup/be_snapshot.h'
--- a/sql/backup/be_snapshot.h	2007-11-30 09:03:02 +0000
+++ b/sql/backup/be_snapshot.h	2008-07-19 01:23:51 +0000
@@ -64,7 +64,7 @@ class Backup: public default_backup::Bac
     {
       if (locking_thd->lock_state == LOCK_ACQUIRED)
       {
-        end_active_trans(locking_thd->m_thd);
+        trans_commit_implicit(locking_thd->m_thd);
         close_thread_tables(locking_thd->m_thd);
       }
     };

=== modified file 'sql/events.cc'
--- a/sql/events.cc	2008-06-17 20:04:19 +0000
+++ b/sql/events.cc	2008-07-19 01:23:51 +0000
@@ -363,15 +363,6 @@ Events::create_event(THD *thd, Event_par
   int ret;
   DBUG_ENTER("Events::create_event");
 
-  /*
-    Let's commit the transaction first - MySQL manual specifies
-    that a DDL issues an implicit commit, and it doesn't say "successful
-    DDL", so that an implicit commit is a property of any successfully
-    parsed DDL statement.
-  */
-  if (end_active_trans(thd))
-    DBUG_RETURN(TRUE);
-
   if (check_if_system_tables_error())
     DBUG_RETURN(TRUE);
 
@@ -467,13 +458,6 @@ Events::update_event(THD *thd, Event_par
 
   DBUG_ENTER("Events::update_event");
 
-  /*
-    For consistency, implicit COMMIT should be the first thing in the
-    execution chain.
-  */
-  if (end_active_trans(thd))
-    DBUG_RETURN(TRUE);
-
   if (check_if_system_tables_error())
     DBUG_RETURN(TRUE);
 
@@ -590,20 +574,6 @@ Events::drop_event(THD *thd, LEX_STRING 
   int ret;
   DBUG_ENTER("Events::drop_event");
 
-  /*
-    In MySQL, DDL must always commit: since mysql.* tables are
-    non-transactional, we must modify them outside a transaction
-    to not break atomicity.
-    But the second and more important reason to commit here
-    regardless whether we're actually changing mysql.event table
-    or not is replication: end_active_trans syncs the binary log,
-    and unless we run DDL in it's own transaction it may simply
-    never appear on the slave in case the outside transaction
-    rolls back.
-  */
-  if (end_active_trans(thd))
-    DBUG_RETURN(TRUE);
-
   if (check_if_system_tables_error())
     DBUG_RETURN(TRUE);
 

=== modified file 'sql/handler.cc'
--- a/sql/handler.cc	2008-07-14 12:49:19 +0000
+++ b/sql/handler.cc	2008-07-19 01:23:51 +0000
@@ -837,7 +837,7 @@ void ha_close_connection(THD* thd)
   do not "register" in thd->transaction lists, and thus do not
   modify the transaction state. Besides, each DDL in
   MySQL is prefixed with an implicit normal transaction commit
-  (a call to end_active_trans()), and thus leaves nothing
+  (a call to trans_commit_implicit()), and thus leaves nothing
   to modify.
   However, as it has been pointed out with CREATE TABLE .. SELECT,
   some DDL statements can start a *new* transaction.
@@ -918,8 +918,8 @@ void trans_register_ha(THD *thd, bool al
 */
 int ha_prepare(THD *thd)
 {
-  int error=0, all=1;
-  THD_TRANS *trans=all ? &thd->transaction.all : &thd->transaction.stmt;
+  int error= 0;
+  THD_TRANS *trans= &thd->transaction.all;
   Ha_trx_info *ha_info= trans->ha_list;
   DBUG_ENTER("ha_prepare");
 
@@ -932,10 +932,10 @@ int ha_prepare(THD *thd)
       status_var_increment(thd->status_var.ha_prepare_count);
       if (ht->prepare)
       {
-        if ((err= ht->prepare(ht, thd, all)))
+        if ((err= ht->prepare(ht, thd, TRUE)))
         {
           my_error(ER_ERROR_DURING_COMMIT, MYF(0), err);
-          ha_rollback_trans(thd, all);
+          ha_rollback_trans(thd, TRUE);
           error=1;
           break;
         }
@@ -1281,42 +1281,6 @@ int ha_rollback_trans(THD *thd, bool all
   DBUG_RETURN(error);
 }
 
-/**
-  This is used to commit or rollback a single statement depending on
-  the value of error.
-
-  @note
-    Note that if the autocommit is on, then the following call inside
-    InnoDB will commit or rollback the whole transaction (= the statement). The
-    autocommit mechanism built into InnoDB is based on counting locks, but if
-    the user has used LOCK TABLES then that mechanism does not know to do the
-    commit.
-*/
-int ha_autocommit_or_rollback(THD *thd, int error)
-{
-  DBUG_ENTER("ha_autocommit_or_rollback");
-
-  if (thd->transaction.stmt.ha_list)
-  {
-    if (!error)
-    {
-      if (ha_commit_trans(thd, 0))
-	error=1;
-    }
-    else 
-    {
-      (void) ha_rollback_trans(thd, 0);
-      if (thd->transaction_rollback_request && !thd->in_sub_stmt)
-        (void) ha_rollback(thd);
-    }
-
-    thd->variables.tx_isolation=thd->session_tx_isolation;
-  }
-
-  DBUG_RETURN(error);
-}
-
-
 struct xahton_st {
   XID *xid;
   int result;
@@ -3381,7 +3345,7 @@ int ha_enable_transaction(THD *thd, bool
       So, let's commit an open transaction (if any) now.
     */
     if (!(error= ha_commit_trans(thd, 0)))
-      error= end_trans(thd, COMMIT);
+      error= trans_commit_implicit(thd);
   }
   DBUG_RETURN(error);
 }

=== modified file 'sql/handler.h'
--- a/sql/handler.h	2008-07-11 16:22:44 +0000
+++ b/sql/handler.h	2008-07-19 01:23:51 +0000
@@ -289,9 +289,6 @@ typedef Bitmap<HA_MAX_ALTER_FLAGS> HA_AL
 #define HA_CACHE_TBL_ASKTRANSACT 2
 #define HA_CACHE_TBL_TRANSACT    4
 
-/* Options of START TRANSACTION statement (and later of SET TRANSACTION stmt) */
-#define MYSQL_START_TRANS_OPT_WITH_CONS_SNAPSHOT 1
-
 /* Flags for method is_fatal_error */
 #define HA_CHECK_DUP_KEY 1
 #define HA_CHECK_DUP_UNIQUE 2
@@ -2403,10 +2400,6 @@ extern TYPELIB tx_isolation_typelib;
 extern TYPELIB myisam_stats_method_typelib;
 extern ulong total_ha, total_ha_2pc;
 
-       /* Wrapper functions */
-#define ha_commit(thd) (ha_commit_trans((thd), TRUE))
-#define ha_rollback(thd) (ha_rollback_trans((thd), TRUE))
-
 /* lookups */
 handlerton *ha_default_handlerton(THD *thd);
 plugin_ref ha_resolve_by_name(THD *thd, const LEX_STRING *name);
@@ -2483,13 +2476,12 @@ int ha_release_temporary_latches(THD *th
 int ha_start_consistent_snapshot(THD *thd);
 int ha_commit_or_rollback_by_xid(XID *xid, bool commit);
 int ha_commit_one_phase(THD *thd, bool all);
+int ha_commit_trans(THD *thd, bool all);
 int ha_rollback_trans(THD *thd, bool all);
 int ha_prepare(THD *thd);
 int ha_recover(HASH *commit_list);
 
 /* transactions: these functions never call handlerton functions directly */
-int ha_commit_trans(THD *thd, bool all);
-int ha_autocommit_or_rollback(THD *thd, int error);
 int ha_enable_transaction(THD *thd, bool on);
 
 /* savepoints */

=== modified file 'sql/lock.cc'
--- a/sql/lock.cc	2008-06-28 11:00:59 +0000
+++ b/sql/lock.cc	2008-07-19 01:23:51 +0000
@@ -1383,7 +1383,7 @@ int try_transactional_lock(THD *thd, TAB
 
  err:
   /* We need to explicitly commit if autocommit mode is active. */
-  (void) ha_autocommit_or_rollback(thd, 0);
+  trans_commit_stmt(thd);
   /* Close the tables. The locks (if taken) persist in the storage engines. */
   close_tables_for_reopen(thd, &table_list, FALSE);
   thd->in_lock_tables= FALSE;

=== modified file 'sql/log_event.cc'
--- a/sql/log_event.cc	2008-07-03 21:26:51 +0000
+++ b/sql/log_event.cc	2008-07-19 01:23:51 +0000
@@ -4506,7 +4506,7 @@ int Xid_log_event::do_apply_event(Relay_
   /* For a slave Xid_log_event is COMMIT */
   general_log_print(thd, COM_QUERY,
                     "COMMIT /* implicit, from Xid_log_event */");
-  return end_trans(thd, COMMIT);
+  return trans_commit(thd);
 }
 
 Log_event::enum_skip_reason
@@ -6824,7 +6824,7 @@ Rows_log_event::do_update_pos(Relay_log_
       are involved, commit the transaction and flush the pending event to the
       binlog.
     */
-    error= ha_autocommit_or_rollback(thd, 0);
+    error= trans_commit_stmt(thd);
 
     /*
       Now what if this is not a transactional engine? we still need to

=== modified file 'sql/log_event_old.cc'
--- a/sql/log_event_old.cc	2008-06-28 11:00:59 +0000
+++ b/sql/log_event_old.cc	2008-07-19 01:23:51 +0000
@@ -1827,7 +1827,7 @@ Old_rows_log_event::do_update_pos(Relay_
       are involved, commit the transaction and flush the pending event to the
       binlog.
     */
-    error= ha_autocommit_or_rollback(thd, 0);
+    error= trans_commit_stmt(thd);
 
     /*
       Now what if this is not a transactional engine? we still need to

=== modified file 'sql/mdl.h'
--- a/sql/mdl.h	2008-06-20 13:11:20 +0000
+++ b/sql/mdl.h	2008-07-19 01:23:51 +0000
@@ -207,10 +207,11 @@ inline bool mdl_has_locks(MDL_CONTEXT *c
    Get iterator for walking through all lock requests in the context.
 */
 
-inline I_P_List_iterator<MDL_LOCK_DATA, MDL_LOCK_DATA_context>
-mdl_get_locks(MDL_CONTEXT *ctx)
+typedef I_P_List_iterator<MDL_LOCK_DATA, MDL_LOCK_DATA_context> MDL_LOCK_DATA_iterator;
+
+inline MDL_LOCK_DATA_iterator mdl_get_locks(MDL_CONTEXT *ctx)
 {
-  I_P_List_iterator<MDL_LOCK_DATA, MDL_LOCK_DATA_context> result(ctx->locks);
+  MDL_LOCK_DATA_iterator result(ctx->locks);
   return result;
 }
 

=== modified file 'sql/mysql_priv.h'
--- a/sql/mysql_priv.h	2008-06-28 11:00:59 +0000
+++ b/sql/mysql_priv.h	2008-07-19 01:23:51 +0000
@@ -780,6 +780,7 @@ typedef my_bool (*qc_engine_callback)(TH
 #include "sql_udf.h"
 #include "sql_profile.h"
 #include "sql_partition.h"
+#include "transaction.h"
 
 class user_var_entry;
 class Security_context;
@@ -866,15 +867,6 @@ bool parse_sql(THD *thd,
                class Lex_input_stream *lip,
                class Object_creation_ctx *creation_ctx);
 
-enum enum_mysql_completiontype {
-  ROLLBACK_RELEASE=-2, ROLLBACK=1,  ROLLBACK_AND_CHAIN=7,
-  COMMIT_RELEASE=-1,   COMMIT=0,    COMMIT_AND_CHAIN=6
-};
-
-bool begin_trans(THD *thd);
-bool end_active_trans(THD *thd);
-int end_trans(THD *thd, enum enum_mysql_completiontype completion);
-
 Item *negate_expression(THD *thd, Item *expr);
 
 /* log.cc */

=== modified file 'sql/rpl_injector.cc'
--- a/sql/rpl_injector.cc	2008-05-29 15:44:11 +0000
+++ b/sql/rpl_injector.cc	2008-07-19 01:23:51 +0000
@@ -36,7 +36,7 @@ injector::transaction::transaction(MYSQL
   m_start_pos.m_file_pos= log_info.pos;
 
   m_thd->lex->start_transaction_opt= 0; /* for begin_trans() */
-  begin_trans(m_thd);
+  trans_begin(m_thd);
 
   thd->set_current_stmt_binlog_row_based();
 }
@@ -82,8 +82,8 @@ int injector::transaction::commit()
      is committed by committing the statement transaction
      explicitly.
    */
-   ha_autocommit_or_rollback(m_thd, 0);
-   end_trans(m_thd, COMMIT);
+   trans_commit_stmt(m_thd);
+   trans_commit(m_thd);
    DBUG_RETURN(0);
 }
 

=== modified file 'sql/rpl_rli.cc'
--- a/sql/rpl_rli.cc	2008-06-28 11:00:59 +0000
+++ b/sql/rpl_rli.cc	2008-07-19 01:23:51 +0000
@@ -1162,8 +1162,8 @@ void Relay_log_info::cleanup_context(THD
   */
   if (error)
   {
-    ha_autocommit_or_rollback(thd, 1); // if a "statement transaction"
-    end_trans(thd, ROLLBACK); // if a "real transaction"
+    trans_rollback_stmt(thd); // if a "statement transaction"
+    trans_rollback(thd);      // if a "real transaction"
   }
   m_table_map.clear_tables();
   slave_close_thread_tables(thd);

=== modified file 'sql/set_var.cc'
--- a/sql/set_var.cc	2008-07-04 10:48:08 +0000
+++ b/sql/set_var.cc	2008-07-19 01:23:51 +0000
@@ -2973,7 +2973,7 @@ static bool set_option_autocommit(THD *t
    */
   if (var->save_result.ulong_value != 0 &&
       (thd->options & OPTION_NOT_AUTOCOMMIT) &&
-      ha_commit(thd))
+      trans_commit(thd))
     return 1;
 
   if (var->save_result.ulong_value != 0)

=== modified file 'sql/slave.cc'
--- a/sql/slave.cc	2008-06-28 11:00:59 +0000
+++ b/sql/slave.cc	2008-07-19 01:23:51 +0000
@@ -1953,7 +1953,7 @@ static int exec_relay_log_event(THD* thd
           else
           {
             exec_res= 0;
-            end_trans(thd, ROLLBACK);
+            trans_rollback(thd);
             /* chance for concurrent connection to get more locks */
             safe_sleep(thd, min(rli->trans_retries, MAX_SLAVE_RETRY_PAUSE),
                        (CHECK_KILLED_FUNC)sql_slave_killed, (void*)rli);

=== modified file 'sql/sql_base.cc'
--- a/sql/sql_base.cc	2008-06-28 11:00:59 +0000
+++ b/sql/sql_base.cc	2008-07-19 01:23:51 +0000
@@ -1354,7 +1354,7 @@ void close_thread_tables(THD *thd,
   if (!(thd->state_flags & Open_tables_state::BACKUPS_AVAIL))
   {
     thd->main_da.can_overwrite_status= TRUE;
-    ha_autocommit_or_rollback(thd, thd->is_error());
+    thd->is_error() ? trans_rollback_stmt(thd) : trans_commit_stmt(thd);
     thd->main_da.can_overwrite_status= FALSE;
 
     /*

=== modified file 'sql/sql_class.cc'
--- a/sql/sql_class.cc	2008-07-03 21:26:51 +0000
+++ b/sql/sql_class.cc	2008-07-19 01:23:51 +0000
@@ -838,7 +838,7 @@ void THD::cleanup(void)
   }
 #endif
   {
-    ha_rollback(this);
+    trans_rollback(this);
     xid_cache_delete(&transaction.xid_state);
   }
   locked_tables_list.unlock_locked_tables(this);

=== modified file 'sql/sql_class.h'
--- a/sql/sql_class.h	2008-07-03 21:26:51 +0000
+++ b/sql/sql_class.h	2008-07-19 01:23:51 +0000
@@ -3029,11 +3029,11 @@ public:
 
 /* Bits in sql_command_flags */
 
-#define CF_CHANGES_DATA		1
-#define CF_HAS_ROW_COUNT	2
-#define CF_STATUS_COMMAND	4
-#define CF_SHOW_TABLE_COMMAND	8
-#define CF_WRITE_LOGS_COMMAND  16
+#define CF_CHANGES_DATA           (1U << 0)
+#define CF_HAS_ROW_COUNT          (1U << 1)
+#define CF_STATUS_COMMAND         (1U << 2)
+#define CF_SHOW_TABLE_COMMAND     (1U << 3)
+#define CF_WRITE_LOGS_COMMAND     (1U << 4)
 /**
   Must be set for SQL statements that may contain
   Item expressions and/or use joins and tables.
@@ -3047,7 +3047,37 @@ public:
   reprepare. Consequently, complex item expressions and
   joins are currently prohibited in these statements.
 */
-#define CF_REEXECUTION_FRAGILE 32
+#define CF_REEXECUTION_FRAGILE    (1U << 5)
+/**
+  Implicitly commit before the SQL statement is executed.
+
+  Statements marked with this flag will cause any active
+  transaction to end (commit) before proceeding with the
+  command execution.
+
+  This flag should be set for statements that probably can't
+  be rolled back or that do not expect any previously metadata
+  locked tables.
+*/
+#define CF_IMPLICT_COMMIT_BEGIN   (1U << 6)
+/**
+  Implicitly commit or rollback after the SQL statement.
+
+  Statements marked with this flag are automatically committed
+  or rolled back at the end of the statement.
+
+  This flag should be set for statements that will implicitly
+  open and take metadata locks on system tables that should not
+  be carried for the whole duration of a active transaction.
+*/
+#define CF_IMPLICIT_COMMIT_END    (1U << 7)
+/**
+  CF_IMPLICT_COMMIT_BEGIN and CF_IMPLICIT_COMMIT_END are used
+  to ensure that the active transaction is implicitly committed
+  before and after every DDL statement and any statement that
+  modifies our currently non-transactional system tables.
+*/
+#define CF_AUTO_COMMIT_TRANS  (CF_IMPLICT_COMMIT_BEGIN | CF_IMPLICIT_COMMIT_END)
 
 /* Functions in sql_class.cc */
 

=== modified file 'sql/sql_delete.cc'
--- a/sql/sql_delete.cc	2008-06-28 11:00:59 +0000
+++ b/sql/sql_delete.cc	2008-07-19 01:23:51 +0000
@@ -1112,12 +1112,6 @@ trunc_by_del:
   error= mysql_delete(thd, table_list, (COND*) 0, (SQL_LIST*) 0,
                       HA_POS_ERROR, LL(0), TRUE);
   ha_enable_transaction(thd, TRUE);
-  /*
-    Safety, in case the engine ignored ha_enable_transaction(FALSE)
-    above. Also clears thd->transaction.*.
-  */
-  error= ha_autocommit_or_rollback(thd, error);
-  ha_commit(thd);
   thd->options= save_options;
   thd->current_stmt_binlog_row_based= save_binlog_row_based;
   DBUG_RETURN(error);

=== modified file 'sql/sql_do.cc'
--- a/sql/sql_do.cc	2008-02-19 12:45:21 +0000
+++ b/sql/sql_do.cc	2008-07-19 01:23:51 +0000
@@ -36,7 +36,7 @@ bool mysql_do(THD *thd, List<Item> &valu
       will clear the error and the rollback in the end of
       dispatch_command() won't work.
     */
-    ha_autocommit_or_rollback(thd, thd->is_error());
+    trans_rollback_stmt(thd);
     thd->clear_error(); // DO always is OK
   }
   my_ok(thd);

=== modified file 'sql/sql_insert.cc'
--- a/sql/sql_insert.cc	2008-06-28 11:00:59 +0000
+++ b/sql/sql_insert.cc	2008-07-19 01:23:51 +0000
@@ -2492,7 +2492,7 @@ pthread_handler_t handle_delayed_insert(
       */
       di->table->file->ha_release_auto_increment();
       mysql_unlock_tables(thd, lock);
-      ha_autocommit_or_rollback(thd, 0);
+      trans_commit_stmt(thd);
       di->group_count=0;
       mysql_audit_release(thd);
       pthread_mutex_lock(&di->mutex);
@@ -2513,7 +2513,7 @@ err:
     first call to ha_*_row() instead. Remove code that are used to
     cover for the case outlined above.
    */
-  ha_autocommit_or_rollback(thd, 1);
+  trans_rollback_stmt(thd);
 
 #ifndef __WIN__
 end:
@@ -3751,8 +3751,8 @@ bool select_create::send_eof()
     */
     if (!table->s->tmp_table)
     {
-      ha_autocommit_or_rollback(thd, 0);
-      end_active_trans(thd);
+      trans_commit_stmt(thd);
+      trans_commit_implicit(thd);
     }
 
     table->file->extra(HA_EXTRA_NO_IGNORE_DUP_KEY);

=== modified file 'sql/sql_parse.cc'
--- a/sql/sql_parse.cc	2008-07-08 02:15:51 +0000
+++ b/sql/sql_parse.cc	2008-07-19 01:23:51 +0000
@@ -34,9 +34,6 @@
 #ifdef BACKUP_TEST
 #include "backup/backup_test.h"
 #endif
-#ifdef WITH_MARIA_STORAGE_ENGINE
-#include "../storage/maria/ha_maria.h"
-#endif
 
 /**
   @defgroup Runtime_Environment Runtime Environment
@@ -98,65 +95,38 @@ const char *xa_state_names[]={
 
 extern DDL_blocker_class *DDL_blocker;
 
-bool end_active_trans(THD *thd)
+static bool opt_implicit_commit(THD *thd, uint mask)
 {
-  int error=0;
-  DBUG_ENTER("end_active_trans");
-  if (unlikely(thd->in_sub_stmt))
-  {
-    my_error(ER_COMMIT_NOT_ALLOWED_IN_SF_OR_TRG, MYF(0));
-    DBUG_RETURN(1);
-  }
-  if (thd->transaction.xid_state.xa_state != XA_NOTR)
-  {
-    my_error(ER_XAER_RMFAIL, MYF(0),
-             xa_state_names[thd->transaction.xid_state.xa_state]);
-    DBUG_RETURN(1);
-  }
-  if (thd->options & (OPTION_NOT_AUTOCOMMIT | OPTION_BEGIN |
-		      OPTION_TABLE_LOCK))
-  {
-    DBUG_PRINT("info",("options: 0x%llx", thd->options));
-    /* Safety if one did "drop table" on locked tables */
-    if (!thd->locked_tables_mode)
-      thd->options&= ~OPTION_TABLE_LOCK;
-    thd->server_status&= ~SERVER_STATUS_IN_TRANS;
-    if (ha_commit(thd))
-      error=1;
-#ifdef WITH_MARIA_STORAGE_ENGINE
-    ha_maria::implicit_commit(thd);
-#endif
-  }
-  thd->options&= ~(OPTION_BEGIN | OPTION_KEEP_LOG);
-  thd->transaction.all.modified_non_trans_table= FALSE;
-  DBUG_RETURN(error);
-}
+  bool skip= FALSE;
+  LEX *lex= thd->lex;
+  DBUG_ENTER("opt_implicit_commit");
 
+  if (!(sql_command_flags[lex->sql_command] & mask))
+    DBUG_RETURN(FALSE);
 
-bool begin_trans(THD *thd)
-{
-  int error=0;
-  if (unlikely(thd->in_sub_stmt))
-  {
-    my_error(ER_COMMIT_NOT_ALLOWED_IN_SF_OR_TRG, MYF(0));
-    return 1;
+  switch (lex->sql_command) {
+  case SQLCOM_DROP_TABLE:
+    skip= lex->drop_temporary;
+    break;
+  case SQLCOM_ALTER_TABLE:
+  case SQLCOM_CREATE_TABLE:
+    /* If CREATE TABLE of non-temporary table, do implicit commit */
+    skip= (lex->create_info.options & HA_LEX_CREATE_TMP_TABLE);
+    break;
+  case SQLCOM_SET_OPTION:
+    skip= lex->autocommit ? FALSE : TRUE;
+    break;
+  case SQLCOM_END:
+    skip= TRUE;
+    break;
+  default:
+    break;
   }
 
-  thd->locked_tables_list.unlock_locked_tables(thd);
-
-  if (end_active_trans(thd))
-    error= -1;
-  else
-  {
-    LEX *lex= thd->lex;
-    thd->options|= OPTION_BEGIN;
-    thd->server_status|= SERVER_STATUS_IN_TRANS;
-    if (lex->start_transaction_opt & MYSQL_START_TRANS_OPT_WITH_CONS_SNAPSHOT)
-      error= ha_start_consistent_snapshot(thd);
-  }
-  return error;
+  DBUG_RETURN(skip ? FALSE : trans_commit_implicit(thd));
 }
 
+
 #ifdef HAVE_REPLICATION
 /**
   Returns true if all tables should be ignored.
@@ -201,22 +171,29 @@ void init_update_queries(void)
 {
   bzero((uchar*) &sql_command_flags, sizeof(sql_command_flags));
 
-  sql_command_flags[SQLCOM_CREATE_TABLE]=   CF_CHANGES_DATA | CF_REEXECUTION_FRAGILE;
-  sql_command_flags[SQLCOM_CREATE_INDEX]=   CF_CHANGES_DATA;
-  sql_command_flags[SQLCOM_ALTER_TABLE]=    CF_CHANGES_DATA | CF_WRITE_LOGS_COMMAND;
-  sql_command_flags[SQLCOM_TRUNCATE]=       CF_CHANGES_DATA | CF_WRITE_LOGS_COMMAND;
-  sql_command_flags[SQLCOM_DROP_TABLE]=     CF_CHANGES_DATA;
+  sql_command_flags[SQLCOM_CREATE_TABLE]=   CF_CHANGES_DATA | CF_REEXECUTION_FRAGILE |
+                                            CF_AUTO_COMMIT_TRANS;
+  sql_command_flags[SQLCOM_CREATE_INDEX]=   CF_CHANGES_DATA | CF_AUTO_COMMIT_TRANS;
+  sql_command_flags[SQLCOM_ALTER_TABLE]=    CF_CHANGES_DATA | CF_WRITE_LOGS_COMMAND |
+                                            CF_AUTO_COMMIT_TRANS;
+  sql_command_flags[SQLCOM_TRUNCATE]=       CF_CHANGES_DATA | CF_WRITE_LOGS_COMMAND |
+                                            CF_AUTO_COMMIT_TRANS;
+  sql_command_flags[SQLCOM_DROP_TABLE]=     CF_CHANGES_DATA | CF_AUTO_COMMIT_TRANS;
   sql_command_flags[SQLCOM_LOAD]=           CF_CHANGES_DATA | CF_REEXECUTION_FRAGILE;
-  sql_command_flags[SQLCOM_CREATE_DB]=      CF_CHANGES_DATA;
-  sql_command_flags[SQLCOM_DROP_DB]=        CF_CHANGES_DATA;
-  sql_command_flags[SQLCOM_RENAME_TABLE]=   CF_CHANGES_DATA;
+  sql_command_flags[SQLCOM_CREATE_DB]=      CF_CHANGES_DATA | CF_AUTO_COMMIT_TRANS;
+  sql_command_flags[SQLCOM_DROP_DB]=        CF_CHANGES_DATA | CF_AUTO_COMMIT_TRANS;
+  sql_command_flags[SQLCOM_ALTER_DB_UPGRADE]= CF_AUTO_COMMIT_TRANS;
+  sql_command_flags[SQLCOM_RENAME_TABLE]=   CF_CHANGES_DATA | CF_AUTO_COMMIT_TRANS;
   sql_command_flags[SQLCOM_RESTORE]=        CF_CHANGES_DATA;
-  sql_command_flags[SQLCOM_DROP_INDEX]=     CF_CHANGES_DATA;
-  sql_command_flags[SQLCOM_CREATE_VIEW]=    CF_CHANGES_DATA | CF_REEXECUTION_FRAGILE;
-  sql_command_flags[SQLCOM_DROP_VIEW]=      CF_CHANGES_DATA;
-  sql_command_flags[SQLCOM_CREATE_EVENT]=   CF_CHANGES_DATA;
-  sql_command_flags[SQLCOM_ALTER_EVENT]=    CF_CHANGES_DATA;
-  sql_command_flags[SQLCOM_DROP_EVENT]=     CF_CHANGES_DATA;
+  sql_command_flags[SQLCOM_DROP_INDEX]=     CF_CHANGES_DATA | CF_AUTO_COMMIT_TRANS;
+  sql_command_flags[SQLCOM_CREATE_VIEW]=    CF_CHANGES_DATA | CF_REEXECUTION_FRAGILE |
+                                            CF_AUTO_COMMIT_TRANS;
+  sql_command_flags[SQLCOM_DROP_VIEW]=      CF_CHANGES_DATA | CF_AUTO_COMMIT_TRANS;
+  sql_command_flags[SQLCOM_CREATE_TRIGGER]= CF_AUTO_COMMIT_TRANS;
+  sql_command_flags[SQLCOM_DROP_TRIGGER]=   CF_AUTO_COMMIT_TRANS;
+  sql_command_flags[SQLCOM_CREATE_EVENT]=   CF_CHANGES_DATA | CF_AUTO_COMMIT_TRANS;
+  sql_command_flags[SQLCOM_ALTER_EVENT]=    CF_CHANGES_DATA | CF_AUTO_COMMIT_TRANS;
+  sql_command_flags[SQLCOM_DROP_EVENT]=     CF_CHANGES_DATA | CF_AUTO_COMMIT_TRANS;
 
   sql_command_flags[SQLCOM_UPDATE]=	    CF_CHANGES_DATA | CF_HAS_ROW_COUNT |
                                             CF_REEXECUTION_FRAGILE;
@@ -235,7 +212,8 @@ void init_update_queries(void)
   sql_command_flags[SQLCOM_REPLACE_SELECT]= CF_CHANGES_DATA | CF_HAS_ROW_COUNT |
                                             CF_REEXECUTION_FRAGILE;
   sql_command_flags[SQLCOM_SELECT]=         CF_REEXECUTION_FRAGILE;
-  sql_command_flags[SQLCOM_SET_OPTION]=     CF_REEXECUTION_FRAGILE;
+  sql_command_flags[SQLCOM_SET_OPTION]=     CF_REEXECUTION_FRAGILE |
+                                            CF_AUTO_COMMIT_TRANS;
   sql_command_flags[SQLCOM_DO]=             CF_REEXECUTION_FRAGILE;
 
   sql_command_flags[SQLCOM_SHOW_STATUS_PROC]= CF_STATUS_COMMAND | CF_REEXECUTION_FRAGILE;
@@ -299,9 +277,25 @@ void init_update_queries(void)
     The following admin table operations are allowed
     on log tables.
   */
-  sql_command_flags[SQLCOM_REPAIR]=           CF_WRITE_LOGS_COMMAND;
-  sql_command_flags[SQLCOM_OPTIMIZE]=         CF_WRITE_LOGS_COMMAND;
+  sql_command_flags[SQLCOM_REPAIR]=           CF_WRITE_LOGS_COMMAND |
+                                              CF_AUTO_COMMIT_TRANS;
+  sql_command_flags[SQLCOM_OPTIMIZE]=         CF_WRITE_LOGS_COMMAND |
+                                              CF_AUTO_COMMIT_TRANS;
   sql_command_flags[SQLCOM_ANALYZE]=          CF_WRITE_LOGS_COMMAND;
+
+  sql_command_flags[SQLCOM_CREATE_USER]=      CF_AUTO_COMMIT_TRANS;
+  sql_command_flags[SQLCOM_DROP_USER]=        CF_AUTO_COMMIT_TRANS;
+  sql_command_flags[SQLCOM_RENAME_USER]=      CF_AUTO_COMMIT_TRANS;
+  sql_command_flags[SQLCOM_REVOKE_ALL]=       CF_AUTO_COMMIT_TRANS;
+  sql_command_flags[SQLCOM_REVOKE]=           CF_AUTO_COMMIT_TRANS;
+  sql_command_flags[SQLCOM_GRANT]=            CF_AUTO_COMMIT_TRANS;
+
+  sql_command_flags[SQLCOM_CREATE_PROCEDURE]=   CF_AUTO_COMMIT_TRANS;
+  sql_command_flags[SQLCOM_CREATE_SPFUNCTION]=  CF_AUTO_COMMIT_TRANS;
+  sql_command_flags[SQLCOM_ALTER_PROCEDURE]=    CF_AUTO_COMMIT_TRANS;
+  sql_command_flags[SQLCOM_ALTER_FUNCTION]=     CF_AUTO_COMMIT_TRANS;
+  sql_command_flags[SQLCOM_ASSIGN_TO_KEYCACHE]= CF_AUTO_COMMIT_TRANS;
+  sql_command_flags[SQLCOM_PRELOAD_KEYS]=       CF_AUTO_COMMIT_TRANS;
 }
 
 
@@ -544,81 +538,6 @@ void cleanup_items(Item *item)
   DBUG_VOID_RETURN;
 }
 
-/**
-  Ends the current transaction and (maybe) begin the next.
-
-  @param thd            Current thread
-  @param completion     Completion type
-
-  @retval
-    0   OK
-*/
-
-int end_trans(THD *thd, enum enum_mysql_completiontype completion)
-{
-  bool do_release= 0;
-  int res= 0;
-  DBUG_ENTER("end_trans");
-
-  if (unlikely(thd->in_sub_stmt))
-  {
-    my_error(ER_COMMIT_NOT_ALLOWED_IN_SF_OR_TRG, MYF(0));
-    DBUG_RETURN(1);
-  }
-  if (thd->transaction.xid_state.xa_state != XA_NOTR)
-  {
-    my_error(ER_XAER_RMFAIL, MYF(0),
-             xa_state_names[thd->transaction.xid_state.xa_state]);
-    DBUG_RETURN(1);
-  }
-  thd->lex->start_transaction_opt= 0; /* for begin_trans() */
-  switch (completion) {
-  case COMMIT:
-    /*
-     We don't use end_active_trans() here to ensure that this works
-     even if there is a problem with the OPTION_AUTO_COMMIT flag
-     (Which of course should never happen...)
-    */
-    thd->server_status&= ~SERVER_STATUS_IN_TRANS;
-    res= ha_commit(thd);
-    thd->options&= ~(OPTION_BEGIN | OPTION_KEEP_LOG);
-    thd->transaction.all.modified_non_trans_table= FALSE;
-    break;
-  case COMMIT_RELEASE:
-    do_release= 1; /* fall through */
-  case COMMIT_AND_CHAIN:
-    res= end_active_trans(thd);
-    if (!res && completion == COMMIT_AND_CHAIN)
-      res= begin_trans(thd);
-    break;
-  case ROLLBACK_RELEASE:
-    do_release= 1; /* fall through */
-  case ROLLBACK:
-  case ROLLBACK_AND_CHAIN:
-  {
-    thd->server_status&= ~SERVER_STATUS_IN_TRANS;
-    if (ha_rollback(thd))
-      res= -1;
-    thd->options&= ~(OPTION_BEGIN | OPTION_KEEP_LOG);
-    thd->transaction.all.modified_non_trans_table= FALSE;
-    if (!res && (completion == ROLLBACK_AND_CHAIN))
-      res= begin_trans(thd);
-    break;
-  }
-  default:
-    res= -1;
-    my_error(ER_UNKNOWN_COM_ERROR, MYF(0));
-    DBUG_RETURN(-1);
-  }
-
-  if (res < 0)
-    my_error(thd->killed_errno(), MYF(0));
-  else if ((res == 0) && do_release)
-    thd->killed= THD::KILL_CONNECTION;
-
-  DBUG_RETURN(res);
-}
-
 #ifndef EMBEDDED_LIBRARY
 
 /**
@@ -1403,7 +1322,8 @@ bool dispatch_command(enum enum_server_c
 
   /* If commit fails, we should be able to reset the OK status. */
   thd->main_da.can_overwrite_status= TRUE;
-  ha_autocommit_or_rollback(thd, thd->is_error());
+  thd->is_error() ? trans_rollback_stmt(thd) : trans_commit_stmt(thd);
+  opt_implicit_commit(thd, CF_IMPLICIT_COMMIT_END);
   thd->main_da.can_overwrite_status= FALSE;
 
   thd->transaction.stmt.reset();
@@ -1947,7 +1867,16 @@ mysql_execute_command(THD *thd)
   status_var_increment(thd->status_var.com_stat[lex->sql_command]);
 
   DBUG_ASSERT(thd->transaction.stmt.modified_non_trans_table == FALSE);
-  
+
+  /*
+    End a active transaction so that this command will have it's
+    own transaction and will also sync the binary log. If a DDL is
+    not run in it's own transaction it may simply never appear on
+    the slave in case the outside transaction rolls back.
+  */
+  if (opt_implicit_commit(thd, CF_IMPLICT_COMMIT_BEGIN))
+    goto error;
+
   switch (lex->sql_command) {
 
   case SQLCOM_SHOW_EVENTS:
@@ -2255,15 +2184,6 @@ mysql_execute_command(THD *thd)
     }
   case SQLCOM_CREATE_TABLE:
   {
-    /* If CREATE TABLE of non-temporary table, do implicit commit */
-    if (!(lex->create_info.options & HA_LEX_CREATE_TMP_TABLE))
-    {
-      if (end_active_trans(thd))
-      {
-	res= -1;
-	break;
-      }
-    }
     DBUG_ASSERT(first_table == all_tables && first_table != 0);
     bool link_to_local;
     // Skip first table, which is the table we are creating
@@ -2483,8 +2403,6 @@ end_with_restore_list:
     DBUG_ASSERT(first_table == all_tables && first_table != 0);
     if (check_one_table_access(thd, INDEX_ACL, all_tables))
       goto error; /* purecov: inspected */
-    if (end_active_trans(thd))
-      goto error;
     /*
       Currently CREATE INDEX or DROP INDEX cause a full table rebuild
       and thus classify as slow administrative statements just like
@@ -2608,9 +2526,6 @@ end_with_restore_list:
         push_warning(thd, MYSQL_ERROR::WARN_LEVEL_WARN, 0,
                      "INDEX DIRECTORY option ignored");
       create_info.data_file_name= create_info.index_file_name= NULL;
-      /* ALTER TABLE ends previous transaction */
-      if (end_active_trans(thd))
-	goto error;
 
       if (!thd->locked_tables_mode &&
           !(need_start_waiting= !wait_if_global_read_lock(thd, 0, 1)))
@@ -2657,13 +2572,13 @@ end_with_restore_list:
         goto error;
     }
 
-      DDL_blocker->check_DDL_blocker(thd);
-    if (end_active_trans(thd) || mysql_rename_tables(thd, first_table, 0))
-      {
-        DDL_blocker->end_DDL();
-        goto error;
-      }
+    DDL_blocker->check_DDL_blocker(thd);
+    if (mysql_rename_tables(thd, first_table, 0))
+    {
       DDL_blocker->end_DDL();
+      goto error;
+    }
+    DDL_blocker->end_DDL();
     break;
   }
 #ifndef EMBEDDED_LIBRARY
@@ -3035,11 +2950,6 @@ end_with_restore_list:
     break;
   }
   case SQLCOM_TRUNCATE:
-    if (end_active_trans(thd))
-    {
-      res= -1;
-      break;
-    }
     DBUG_ASSERT(first_table == all_tables && first_table != 0);
     if (check_one_table_access(thd, DROP_ACL, all_tables))
       goto error;
@@ -3140,8 +3050,6 @@ end_with_restore_list:
     {
       if (check_table_access(thd, DROP_ACL, all_tables, FALSE, FALSE, UINT_MAX))
 	goto error;				/* purecov: inspected */
-      if (end_active_trans(thd))
-        goto error;
     }
     else
     {
@@ -3238,9 +3146,6 @@ end_with_restore_list:
   {
     List<set_var_base> *lex_var_list= &lex->var_list;
 
-    if (lex->autocommit && end_active_trans(thd))
-      goto error;
-
     if ((check_table_access(thd, SELECT_ACL, all_tables, FALSE, FALSE, UINT_MAX) ||
 	 open_and_lock_tables(thd, all_tables)))
       goto error;
@@ -3283,7 +3188,7 @@ end_with_restore_list:
     thd->locked_tables_list.unlock_locked_tables(thd);
     if (thd->options & OPTION_TABLE_LOCK)
     {
-      end_active_trans(thd);
+      trans_commit_implicit(thd);
       thd->options&= ~(OPTION_TABLE_LOCK);
     }
     if (thd->global_read_lock)
@@ -3337,7 +3242,7 @@ end_with_restore_list:
       goto error;
     thd->locked_tables_list.unlock_locked_tables(thd);
     /* we must end the trasaction first, regardless of anything */
-    if (end_active_trans(thd))
+    if (trans_commit_implicit(thd))
       goto error;
 
     alloc_mdl_locks(all_tables, thd->locked_tables_list.locked_tables_root());
@@ -3360,8 +3265,8 @@ end_with_restore_list:
         can free its locks if LOCK TABLES locked some tables before finding
         that it can't lock a table in its list
       */
-      ha_autocommit_or_rollback(thd, 1);
-      end_active_trans(thd);
+      trans_rollback_stmt(thd);
+      trans_commit_implicit(thd);
       thd->options&= ~(OPTION_TABLE_LOCK);
     }
     else
@@ -3382,11 +3287,6 @@ end_with_restore_list:
       prepared statement- safe.
     */
     HA_CREATE_INFO create_info(lex->create_info);
-    if (end_active_trans(thd))
-    {
-      res= -1;
-      break;
-    }
     char *alias;
     if (!(alias=thd->strmake(lex->name.str, lex->name.length)) ||
         check_db_name(&lex->name))
@@ -3421,11 +3321,6 @@ end_with_restore_list:
   }
   case SQLCOM_DROP_DB:
   {
-    if (end_active_trans(thd))
-    {
-      res= -1;
-      break;
-    }
     if (check_db_name(&lex->name))
     {
       my_error(ER_WRONG_DB_NAME, MYF(0), lex->name.str);
@@ -3464,11 +3359,6 @@ end_with_restore_list:
   case SQLCOM_ALTER_DB_UPGRADE:
   {
     LEX_STRING *db= & lex->name;
-    if (end_active_trans(thd))
-    {
-      res= 1;
-      break;
-    }
 #ifdef HAVE_REPLICATION
     if (thd->slave_thread && 
        (!rpl_filter->db_ok(db->str) ||
@@ -3635,8 +3525,6 @@ end_with_restore_list:
     if (check_access(thd, INSERT_ACL, "mysql", 0, 1, 1, 0) &&
         check_global_access(thd,CREATE_USER_ACL))
       break;
-    if (end_active_trans(thd))
-      goto error;
     /* Conditionally writes to binlog */
     if (!(res= mysql_create_user(thd, lex->users_list)))
       my_ok(thd);
@@ -3647,8 +3535,6 @@ end_with_restore_list:
     if (check_access(thd, DELETE_ACL, "mysql", 0, 1, 1, 0) &&
         check_global_access(thd,CREATE_USER_ACL))
       break;
-    if (end_active_trans(thd))
-      goto error;
     /* Conditionally writes to binlog */
     if (!(res= mysql_drop_user(thd, lex->users_list)))
       my_ok(thd);
@@ -3659,8 +3545,6 @@ end_with_restore_list:
     if (check_access(thd, UPDATE_ACL, "mysql", 0, 1, 1, 0) &&
         check_global_access(thd,CREATE_USER_ACL))
       break;
-    if (end_active_trans(thd))
-      goto error;
     /* Conditionally writes to binlog */
     if (!(res= mysql_rename_user(thd, lex->users_list)))
       my_ok(thd);
@@ -3668,8 +3552,6 @@ end_with_restore_list:
   }
   case SQLCOM_REVOKE_ALL:
   {
-    if (end_active_trans(thd))
-      goto error;
     if (check_access(thd, UPDATE_ACL, "mysql", 0, 1, 1, 0) &&
         check_global_access(thd,CREATE_USER_ACL))
       break;
@@ -3681,9 +3563,6 @@ end_with_restore_list:
   case SQLCOM_REVOKE:
   case SQLCOM_GRANT:
   {
-    if (end_active_trans(thd))
-      goto error;
-
     if (check_access(thd, lex->grant | lex->grant_tot_col | GRANT_ACL,
 		     first_table ?  first_table->db : select_lex->db,
 		     first_table ? &first_table->grant.privilege : 0,
@@ -3876,135 +3755,54 @@ end_with_restore_list:
     break;
 
   case SQLCOM_BEGIN:
-    if (thd->transaction.xid_state.xa_state != XA_NOTR)
-    {
-      my_error(ER_XAER_RMFAIL, MYF(0),
-               xa_state_names[thd->transaction.xid_state.xa_state]);
-      break;
-    }
-    /*
-      Breakpoints for backup testing.
-    */
+    /* Breakpoints for backup testing. */
     BACKUP_BREAKPOINT("backup_commit_blocker");
-    if (begin_trans(thd))
+    if (trans_begin(thd, lex->start_transaction_opt))
       goto error;
     my_ok(thd);
     break;
   case SQLCOM_COMMIT:
     DBUG_ASSERT(thd->lock == NULL ||
                 thd->locked_tables_mode == LTM_LOCK_TABLES);
-    if (end_trans(thd, lex->tx_release ? COMMIT_RELEASE :
-                              lex->tx_chain ? COMMIT_AND_CHAIN : COMMIT))
+    if (trans_commit(thd))
       goto error;
-    /*
-      Breakpoints for backup testing.
-    */
+    /* Begin transaction with the same isolation level. */
+    if (lex->tx_chain && trans_begin(thd))
+      goto error;
+    /* Disconnect the current client connection. */
+    if (lex->tx_release)
+      thd->killed= THD::KILL_CONNECTION;
+    /* Breakpoints for backup testing. */
     BACKUP_BREAKPOINT("backup_commit_blocker");
     my_ok(thd);
     break;
   case SQLCOM_ROLLBACK:
     DBUG_ASSERT(thd->lock == NULL ||
                 thd->locked_tables_mode == LTM_LOCK_TABLES);
-    if (end_trans(thd, lex->tx_release ? ROLLBACK_RELEASE :
-                              lex->tx_chain ? ROLLBACK_AND_CHAIN : ROLLBACK))
+    if (trans_rollback(thd))
+      goto error;
+    /* Begin transaction with the same isolation level. */
+    if (lex->tx_chain && trans_begin(thd))
       goto error;
+    /* Disconnect the current client connection. */
+    if (lex->tx_release)
+      thd->killed= THD::KILL_CONNECTION;
     my_ok(thd);
     break;
   case SQLCOM_RELEASE_SAVEPOINT:
-  {
-    SAVEPOINT *sv;
-    for (sv=thd->transaction.savepoints; sv; sv=sv->prev)
-    {
-      if (my_strnncoll(system_charset_info,
-                       (uchar *)lex->ident.str, lex->ident.length,
-                       (uchar *)sv->name, sv->length) == 0)
-        break;
-    }
-    if (sv)
-    {
-      if (ha_release_savepoint(thd, sv))
-        res= TRUE; // cannot happen
-      else
-        my_ok(thd);
-      thd->transaction.savepoints=sv->prev;
-    }
-    else
-      my_error(ER_SP_DOES_NOT_EXIST, MYF(0), "SAVEPOINT", lex->ident.str);
+    if (trans_release_savepoint(thd, lex->ident))
+      goto error;
+    my_ok(thd);
     break;
-  }
   case SQLCOM_ROLLBACK_TO_SAVEPOINT:
-  {
-    SAVEPOINT *sv;
-    for (sv=thd->transaction.savepoints; sv; sv=sv->prev)
-    {
-      if (my_strnncoll(system_charset_info,
-                       (uchar *)lex->ident.str, lex->ident.length,
-                       (uchar *)sv->name, sv->length) == 0)
-        break;
-    }
-    if (sv)
-    {
-      if (ha_rollback_to_savepoint(thd, sv))
-        res= TRUE; // cannot happen
-      else
-      {
-        if (((thd->options & OPTION_KEEP_LOG) || 
-             thd->transaction.all.modified_non_trans_table) &&
-            !thd->slave_thread)
-          push_warning(thd, MYSQL_ERROR::WARN_LEVEL_WARN,
-                       ER_WARNING_NOT_COMPLETE_ROLLBACK,
-                       ER(ER_WARNING_NOT_COMPLETE_ROLLBACK));
-        my_ok(thd);
-      }
-      thd->transaction.savepoints=sv;
-    }
-    else
-      my_error(ER_SP_DOES_NOT_EXIST, MYF(0), "SAVEPOINT", lex->ident.str);
+    if (trans_rollback_to_savepoint(thd, lex->ident))
+      goto error;
+    my_ok(thd);
     break;
-  }
   case SQLCOM_SAVEPOINT:
-    if (!(thd->options & (OPTION_NOT_AUTOCOMMIT | OPTION_BEGIN) ||
-          thd->in_sub_stmt) || !opt_using_transactions)
-      my_ok(thd);
-    else
-    {
-      SAVEPOINT **sv, *newsv;
-      for (sv=&thd->transaction.savepoints; *sv; sv=&(*sv)->prev)
-      {
-        if (my_strnncoll(system_charset_info,
-                         (uchar *)lex->ident.str, lex->ident.length,
-                         (uchar *)(*sv)->name, (*sv)->length) == 0)
-          break;
-      }
-      if (*sv) /* old savepoint of the same name exists */
-      {
-        newsv=*sv;
-        ha_release_savepoint(thd, *sv); // it cannot fail
-        *sv=(*sv)->prev;
-      }
-      else if ((newsv=(SAVEPOINT *) alloc_root(&thd->transaction.mem_root,
-                                               savepoint_alloc_size)) == 0)
-      {
-        my_error(ER_OUT_OF_RESOURCES, MYF(0));
-        break;
-      }
-      newsv->name=strmake_root(&thd->transaction.mem_root,
-                               lex->ident.str, lex->ident.length);
-      newsv->length=lex->ident.length;
-      /*
-        if we'll get an error here, don't add new savepoint to the list.
-        we'll lose a little bit of memory in transaction mem_root, but it'll
-        be free'd when transaction ends anyway
-      */
-      if (ha_savepoint(thd, newsv))
-        res= TRUE;
-      else
-      {
-        newsv->prev=thd->transaction.savepoints;
-        thd->transaction.savepoints=newsv;
-        my_ok(thd);
-      }
-    }
+    if (trans_savepoint(thd, lex->ident))
+      goto error;
+    my_ok(thd);
     break;
   case SQLCOM_CREATE_PROCEDURE:
   case SQLCOM_CREATE_SPFUNCTION:
@@ -4040,9 +3838,6 @@ end_with_restore_list:
                      is_schema_db(lex->sphead->m_db.str)))
       goto create_sp_error;
 
-    if (end_active_trans(thd))
-      goto create_sp_error;
-
     name= lex->sphead->name(&namelen);
 #ifdef HAVE_DLOPEN
     if (lex->sphead->m_type == TYPE_ENUM_FUNCTION)
@@ -4237,8 +4032,6 @@ create_sp_error:
                                  lex->sql_command == SQLCOM_ALTER_PROCEDURE, 0))
 	  goto error;
 
-        if (end_active_trans(thd)) 
-          goto error;
 	memcpy(&lex->sp_chistics, &chistics, sizeof(lex->sp_chistics));
         if ((sp->m_type == TYPE_ENUM_FUNCTION) &&
             !trust_function_creators &&  mysql_bin_log.is_open() &&
@@ -4351,7 +4144,7 @@ create_sp_error:
                                  lex->sql_command == SQLCOM_DROP_PROCEDURE, 0))
           goto error;
 
-        if (end_active_trans(thd)) 
+        if (trans_commit_implicit(thd))
           goto error;
 #ifndef NO_EMBEDDED_ACCESS_CHECKS
 	if (sp_automatic_privileges && !opt_noacl &&
@@ -4452,16 +4245,12 @@ create_sp_error:
         Note: SQLCOM_CREATE_VIEW also handles 'ALTER VIEW' commands
         as specified through the thd->lex->create_view_mode flag.
       */
-      if (end_active_trans(thd))
-        goto error;
-
       res= mysql_create_view(thd, first_table, thd->lex->create_view_mode);
       break;
     }
   case SQLCOM_DROP_VIEW:
     {
-      if (check_table_access(thd, DROP_ACL, all_tables, FALSE, FALSE, UINT_MAX) ||
-          end_active_trans(thd))
+      if (check_table_access(thd, DROP_ACL, all_tables, FALSE, FALSE, UINT_MAX))
         goto error;
       /* Conditionally writes to binlog. */
       res= mysql_drop_view(thd, first_table, thd->lex->drop_mode);
@@ -4469,9 +4258,6 @@ create_sp_error:
     }
   case SQLCOM_CREATE_TRIGGER:
   {
-    if (end_active_trans(thd))
-      goto error;
-
     /* Conditionally writes to binlog. */
     res= mysql_create_or_drop_trigger(thd, all_tables, 1);
 
@@ -4479,9 +4265,6 @@ create_sp_error:
   }
   case SQLCOM_DROP_TRIGGER:
   {
-    if (end_active_trans(thd))
-      goto error;
-
     /* Conditionally writes to binlog. */
     res= mysql_create_or_drop_trigger(thd, all_tables, 0);
     break;
@@ -4590,7 +4373,7 @@ create_sp_error:
         thd->lex->xa_opt == XA_ONE_PHASE)
     {
       int r;
-      if ((r= ha_commit(thd)))
+      if ((r= ha_commit_trans(thd, TRUE)))
         my_error(r == 1 ? ER_XA_RBROLLBACK : ER_XAER_RMERR, MYF(0));
       else
         my_ok(thd);
@@ -4600,7 +4383,7 @@ create_sp_error:
     {
       if (wait_if_global_read_lock(thd, 0, 0))
       {
-        ha_rollback(thd);
+        ha_rollback_trans(thd, TRUE);
         my_error(ER_XAER_RMERR, MYF(0));
       }
       else
@@ -4645,7 +4428,7 @@ create_sp_error:
                xa_state_names[thd->transaction.xid_state.xa_state]);
       break;
     }
-    if (ha_rollback(thd))
+    if (ha_rollback_trans(thd, TRUE))
       my_error(ER_XAER_RMERR, MYF(0));
     else
       my_ok(thd);

=== modified file 'sql/sql_partition.cc'
--- a/sql/sql_partition.cc	2008-06-11 11:49:58 +0000
+++ b/sql/sql_partition.cc	2008-07-19 01:23:51 +0000
@@ -3966,8 +3966,8 @@ static int fast_end_partition(THD *thd, 
   if (!is_empty)
     query_cache_invalidate3(thd, table_list, 0);
 
-  error= ha_autocommit_or_rollback(thd, 0);
-  if (end_active_trans(thd))
+  error= trans_commit_stmt(thd);
+  if (trans_commit_implicit(thd))
     error= 1;
 
   if (error)

=== modified file 'sql/sql_table.cc'
--- a/sql/sql_table.cc	2008-07-14 12:49:19 +0000
+++ b/sql/sql_table.cc	2008-07-19 01:23:51 +0000
@@ -4155,8 +4155,6 @@ static bool mysql_admin_table(THD* thd, 
   CHARSET_INFO *cs= system_charset_info;
   DBUG_ENTER("mysql_admin_table");
 
-  if (end_active_trans(thd))
-    DBUG_RETURN(1);
   field_list.push_back(item = new Item_empty_string("Table",
                                                     NAME_CHAR_LEN * 2,
                                                     cs));
@@ -4219,8 +4217,8 @@ static bool mysql_admin_table(THD* thd, 
       DBUG_PRINT("admin", ("calling prepare_func"));
       switch ((*prepare_func)(thd, table, check_opt)) {
       case  1:           // error, message written to net
-        ha_autocommit_or_rollback(thd, 1);
-        end_trans(thd, ROLLBACK);
+        trans_rollback_stmt(thd);
+        trans_rollback(thd);
         close_thread_tables(thd);
         DBUG_PRINT("admin", ("simple error, admin next table"));
         continue;
@@ -4278,8 +4276,8 @@ static bool mysql_admin_table(THD* thd, 
       length= my_snprintf(buff, sizeof(buff), ER(ER_OPEN_AS_READONLY),
                           table_name);
       protocol->store(buff, length, system_charset_info);
-      ha_autocommit_or_rollback(thd, 0);
-      end_trans(thd, COMMIT);
+      trans_commit_stmt(thd);
+      trans_commit(thd);
       close_thread_tables(thd);
       lex->reset_query_tables_list(FALSE);
       table->table=0;				// For query cache
@@ -4327,7 +4325,7 @@ static bool mysql_admin_table(THD* thd, 
            HA_ADMIN_NEEDS_ALTER))
       {
         DBUG_PRINT("admin", ("recreating table"));
-        ha_autocommit_or_rollback(thd, 1);
+        trans_rollback_stmt(thd);
         close_thread_tables(thd);
         tmp_disable_binlog(thd); // binlogging is done by caller if wanted
         result_code= mysql_recreate_table(thd, table);
@@ -4440,7 +4438,7 @@ send_result_message:
         "try with alter", so here we close the table, do an ALTER TABLE,
         reopen the table and do ha_innobase::analyze() on it.
       */
-      ha_autocommit_or_rollback(thd, 0);
+      trans_commit_stmt(thd);
       close_thread_tables(thd);
       TABLE_LIST *save_next_local= table->next_local,
                  *save_next_global= table->next_global;
@@ -4456,7 +4454,7 @@ send_result_message:
       */
       if (thd->main_da.is_ok())
         thd->main_da.reset_diagnostics_area();
-      ha_autocommit_or_rollback(thd, 0);
+      trans_commit_stmt(thd);
       close_thread_tables(thd);
       if (!result_code) // recreation went ok
       {
@@ -4545,8 +4543,8 @@ send_result_message:
         query_cache_invalidate3(thd, table->table, 0);
       }
     }
-    ha_autocommit_or_rollback(thd, 0);
-    end_trans(thd, COMMIT);
+    trans_commit_stmt(thd);
+    trans_commit_implicit(thd);
     close_thread_tables(thd);
     table->table=0;				// For query cache
     if (protocol->write())
@@ -4557,8 +4555,8 @@ send_result_message:
   DBUG_RETURN(FALSE);
 
 err:
-  ha_autocommit_or_rollback(thd, 1);
-  end_trans(thd, ROLLBACK);
+  trans_rollback_stmt(thd);
+  trans_rollback(thd);
   close_thread_tables(thd);			// Shouldn't be needed
   if (table)
     table->table=0;
@@ -5050,15 +5048,15 @@ mysql_discard_or_import_tablespace(THD *
   query_cache_invalidate3(thd, table_list, 0);
 
   /* The ALTER TABLE is always in its own transaction */
-  error = ha_autocommit_or_rollback(thd, 0);
-  if (end_active_trans(thd))
+  error= trans_commit_stmt(thd);
+  if (trans_commit_implicit(thd))
     error=1;
   if (error)
     goto err;
   write_bin_log(thd, FALSE, thd->query, thd->query_length);
 
 err:
-  ha_autocommit_or_rollback(thd, error);
+  trans_rollback_stmt(thd);
   thd->tablespace_op=FALSE;
 
   if (error == 0)
@@ -5815,8 +5813,8 @@ mysql_fast_or_online_alter_table(THD *th
     wait_if_global_read_lock(), which could create a deadlock if called
     with LOCK_open.
   */
-  error= ha_autocommit_or_rollback(thd, 0);
-  if (ha_commit(thd))
+  error= trans_commit_stmt(thd);
+  if (trans_commit_implicit(thd))
     error= 1;
 
   if (error)
@@ -6949,8 +6947,8 @@ view_err:
   }
   else
   {
-    error= ha_autocommit_or_rollback(thd, 0);
-    if (end_active_trans(thd))
+    error= trans_commit_stmt(thd);
+    if (trans_commit_implicit(thd))
       error= 1;
   }
   thd->count_cuted_fields= CHECK_FIELD_IGNORE;
@@ -7392,9 +7390,9 @@ err:
     Ensure that the new table is saved properly to disk so that we
     can do a rename
   */
-  if (ha_autocommit_or_rollback(thd, 0))
+  if (trans_commit_stmt(thd))
     error=1;
-  if (end_active_trans(thd))
+  if (trans_commit_implicit(thd))
     error=1;
 
   thd->variables.sql_mode= save_sql_mode;

=== added file 'sql/transaction.cc'
--- a/sql/transaction.cc	1970-01-01 00:00:00 +0000
+++ b/sql/transaction.cc	2008-07-19 01:23:51 +0000
@@ -0,0 +1,365 @@
+/* Copyright (C) 2008 Sun/MySQL
+
+   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
+   the Free Software Foundation; version 2 of the License.
+
+   This program is distributed in the hope that it will be useful,
+   but WITHOUT ANY WARRANTY; without even the implied warranty of
+   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+   GNU General Public License for more details.
+
+   You should have received a copy of the GNU General Public License
+   along with this program; if not, write to the Free Software
+   Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA */
+
+
+#ifdef USE_PRAGMA_IMPLEMENTATION
+#pragma implementation				// gcc: Class implementation
+#endif
+
+#include "mysql_priv.h"
+
+#ifdef WITH_MARIA_STORAGE_ENGINE
+#include "../storage/maria/ha_maria.h"
+#endif
+
+/* Conditions under which the transaction state must not change. */
+static bool trans_check(THD *thd)
+{
+  enum xa_states xa_state= thd->transaction.xid_state.xa_state;
+  DBUG_ENTER("trans_check");
+
+  if (unlikely(thd->in_sub_stmt))
+    my_error(ER_COMMIT_NOT_ALLOWED_IN_SF_OR_TRG, MYF(0));
+  if (xa_state != XA_NOTR)
+    my_error(ER_XAER_RMFAIL, MYF(0), xa_state_names[xa_state]);
+  else
+    DBUG_RETURN(FALSE);
+
+  DBUG_RETURN(TRUE);
+}
+
+
+/**
+  Begin a new transaction.
+
+  @note Beginning a transaction implicitly commits any current
+        transaction and releases existing locks.
+
+  @param thd     Current thread
+
+  @retval FALSE  Success
+  @retval TRUE   Failure
+*/
+
+bool trans_begin(THD *thd, uint flags)
+{
+  int res= FALSE;
+  DBUG_ENTER("trans_begin");
+
+  if (trans_check(thd))
+    DBUG_RETURN(TRUE);
+
+  thd->locked_tables_list.unlock_locked_tables(thd);
+
+  if (trans_commit_implicit(thd))
+    DBUG_RETURN(TRUE);
+
+  thd->options|= OPTION_BEGIN;
+  thd->server_status|= SERVER_STATUS_IN_TRANS;
+
+  if (flags & MYSQL_START_TRANS_OPT_WITH_CONS_SNAPSHOT)
+    res= ha_start_consistent_snapshot(thd);
+
+  DBUG_RETURN(test(res));
+}
+
+
+/**
+  Commit the current transaction, making its changes permanent.
+
+  @param thd     Current thread
+
+  @retval FALSE  Success
+  @retval TRUE   Failure
+*/
+
+bool trans_commit(THD *thd)
+{
+  int res;
+  DBUG_ENTER("trans_commit");
+
+  if (trans_check(thd))
+    DBUG_RETURN(TRUE);
+
+  thd->server_status&= ~SERVER_STATUS_IN_TRANS;
+  res= ha_commit_trans(thd, TRUE);
+  thd->options&= ~(OPTION_BEGIN | OPTION_KEEP_LOG);
+  thd->transaction.all.modified_non_trans_table= FALSE;
+
+  DBUG_RETURN(test(res));
+}
+
+
+/**
+  Implicitly commit the current transaction.
+
+  @note A implicit commit does not releases existing table locks.
+
+  @param thd     Current thread
+
+  @retval FALSE  Success
+  @retval TRUE   Failure
+*/
+
+bool trans_commit_implicit(THD *thd)
+{
+  bool res= FALSE;
+  DBUG_ENTER("trans_commit_implicit");
+
+  if (trans_check(thd))
+    DBUG_RETURN(TRUE);
+
+  if (thd->options & (OPTION_NOT_AUTOCOMMIT | OPTION_BEGIN |
+                      OPTION_TABLE_LOCK))
+  {
+    /* Safety if one did "drop table" on locked tables */
+    if (!thd->locked_tables_mode)
+      thd->options&= ~OPTION_TABLE_LOCK;
+    thd->server_status&= ~SERVER_STATUS_IN_TRANS;
+    res= test(ha_commit_trans(thd, TRUE));
+#ifdef WITH_MARIA_STORAGE_ENGINE
+    ha_maria::implicit_commit(thd);
+#endif
+  }
+
+  thd->options&= ~(OPTION_BEGIN | OPTION_KEEP_LOG);
+  thd->transaction.all.modified_non_trans_table= FALSE;
+
+  DBUG_RETURN(res);
+}
+
+
+/**
+  Rollback the current transaction, canceling its changes.
+
+  @param thd     Current thread
+
+  @retval FALSE  Success
+  @retval TRUE   Failure
+*/
+
+bool trans_rollback(THD *thd)
+{
+  int res;
+  DBUG_ENTER("trans_rollback");
+
+  if (trans_check(thd))
+    DBUG_RETURN(TRUE);
+
+  thd->server_status&= ~SERVER_STATUS_IN_TRANS;
+  res= ha_rollback_trans(thd, TRUE);
+  thd->options&= ~(OPTION_BEGIN | OPTION_KEEP_LOG);
+  thd->transaction.all.modified_non_trans_table= FALSE;
+
+  DBUG_RETURN(test(res));
+}
+
+
+/**
+  Commit the single statement transaction.
+
+  @note Note that if the autocommit is on, then the following call
+        inside InnoDB will commit or rollback the whole transaction
+        (= the statement). The autocommit mechanism built into InnoDB
+        is based on counting locks, but if the user has used LOCK
+        TABLES then that mechanism does not know to do the commit.
+
+  @param thd     Current thread
+
+  @retval FALSE  Success
+  @retval TRUE   Failure
+*/
+
+bool trans_commit_stmt(THD *thd)
+{
+  DBUG_ENTER("trans_commit_stmt");
+  int res= FALSE;
+  if (thd->transaction.stmt.ha_list)
+    res= ha_commit_trans(thd, FALSE);
+  DBUG_RETURN(test(res));
+}
+
+
+/**
+  Rollback the single statement transaction.
+
+  @param thd     Current thread
+
+  @retval FALSE  Success
+  @retval TRUE   Failure
+*/
+bool trans_rollback_stmt(THD *thd)
+{
+  DBUG_ENTER("trans_rollback_stmt");
+
+  if (thd->transaction.stmt.ha_list)
+  {
+    thd->transaction_rollback_request= FALSE;
+    ha_rollback_trans(thd, FALSE);
+    if (thd->transaction_rollback_request && !thd->in_sub_stmt)
+      ha_rollback_trans(thd, TRUE);
+  }
+
+  DBUG_RETURN(FALSE);
+}
+
+/* Find a named savepoint in the current transaction. */
+static SAVEPOINT **
+find_savepoint(THD *thd, LEX_STRING name)
+{
+  SAVEPOINT **sv= &thd->transaction.savepoints;
+
+  while (*sv)
+  {
+    if (my_strnncoll(system_charset_info, (uchar *) name.str, name.length,
+                     (uchar *) (*sv)->name, (*sv)->length) == 0)
+      break;
+    sv= &(*sv)->prev;
+  }
+
+  return sv;
+}
+
+
+/**
+  Set a named transaction savepoint.
+
+  @param thd    Current thread
+  @param name   Savepoint name
+
+  @retval FALSE  Success
+  @retval TRUE   Failure
+*/
+
+bool trans_savepoint(THD *thd, LEX_STRING name)
+{
+  SAVEPOINT **sv, *newsv;
+  DBUG_ENTER("trans_savepoint");
+
+  if (!(thd->options & (OPTION_NOT_AUTOCOMMIT | OPTION_BEGIN) ||
+        thd->in_sub_stmt) || !opt_using_transactions)
+    DBUG_RETURN(FALSE);
+
+  sv= find_savepoint(thd, name);
+
+  if (*sv) /* old savepoint of the same name exists */
+  {
+    newsv= *sv;
+    ha_release_savepoint(thd, *sv);
+    *sv= (*sv)->prev;
+  }
+  else if ((newsv= (SAVEPOINT *) alloc_root(&thd->transaction.mem_root,
+                                            savepoint_alloc_size)) == NULL)
+  {
+    my_error(ER_OUT_OF_RESOURCES, MYF(0));
+    DBUG_RETURN(TRUE);
+  }
+
+  newsv->name= strmake_root(&thd->transaction.mem_root, name.str, name.length);
+  newsv->length= name.length;
+
+  /*
+    if we'll get an error here, don't add new savepoint to the list.
+    we'll lose a little bit of memory in transaction mem_root, but it'll
+    be free'd when transaction ends anyway
+  */
+  if (ha_savepoint(thd, newsv))
+    DBUG_RETURN(TRUE);
+
+  newsv->prev= thd->transaction.savepoints;
+  thd->transaction.savepoints= newsv;
+
+  DBUG_RETURN(FALSE);
+}
+
+
+/**
+  Rollback a transaction to the named savepoint.
+
+  @note Modifications that the current transaction made to
+        rows after the savepoint was set are undone in the
+        rollback.
+
+  @note Savepoints that were set at a later time than the
+        named savepoint are deleted.
+
+  @param thd    Current thread
+  @param name   Savepoint name
+
+  @retval FALSE  Success
+  @retval TRUE   Failure
+*/
+
+bool trans_rollback_to_savepoint(THD *thd, LEX_STRING name)
+{
+  int res= FALSE;
+  SAVEPOINT *sv= *find_savepoint(thd, name);
+  DBUG_ENTER("trans_rollback_to_savepoint");
+
+  if (sv == NULL)
+  {
+    my_error(ER_SP_DOES_NOT_EXIST, MYF(0), "SAVEPOINT", name.str);
+    DBUG_RETURN(TRUE);
+  }
+
+  if (ha_rollback_to_savepoint(thd, sv))
+    res= TRUE;
+  else if (((thd->options & OPTION_KEEP_LOG) ||
+            thd->transaction.all.modified_non_trans_table) &&
+           !thd->slave_thread)
+    push_warning(thd, MYSQL_ERROR::WARN_LEVEL_WARN,
+                 ER_WARNING_NOT_COMPLETE_ROLLBACK,
+                 ER(ER_WARNING_NOT_COMPLETE_ROLLBACK));
+
+  thd->transaction.savepoints= sv;
+
+  DBUG_RETURN(test(res));
+}
+
+
+/**
+  Remove the named savepoint from the set of savepoints of
+  the current transaction.
+
+  @note No commit or rollback occurs. It is an error if the
+        savepoint does not exist.
+
+  @param thd    Current thread
+  @param name   Savepoint name
+
+  @retval FALSE  Success
+  @retval TRUE   Failure
+*/
+
+bool trans_release_savepoint(THD *thd, LEX_STRING name)
+{
+  int res= FALSE;
+  SAVEPOINT *sv= *find_savepoint(thd, name);
+  DBUG_ENTER("trans_release_savepoint");
+
+  if (sv == NULL)
+  {
+    my_error(ER_SP_DOES_NOT_EXIST, MYF(0), "SAVEPOINT", name.str);
+    DBUG_RETURN(TRUE);
+  }
+
+  if (ha_release_savepoint(thd, sv))
+    res= TRUE;
+
+  thd->transaction.savepoints=sv->prev;
+
+  DBUG_RETURN(test(res));
+}
+

=== added file 'sql/transaction.h'
--- a/sql/transaction.h	1970-01-01 00:00:00 +0000
+++ b/sql/transaction.h	2008-07-19 01:23:51 +0000
@@ -0,0 +1,38 @@
+/* Copyright (C) 2008 Sun/MySQL
+
+   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
+   the Free Software Foundation; version 2 of the License.
+
+   This program is distributed in the hope that it will be useful,
+   but WITHOUT ANY WARRANTY; without even the implied warranty of
+   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+   GNU General Public License for more details.
+
+   You should have received a copy of the GNU General Public License
+   along with this program; if not, write to the Free Software
+   Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA */
+
+#ifdef USE_PRAGMA_INTERFACE
+#pragma interface			/* gcc class implementation */
+#endif
+
+#ifndef TRANSACTION_H
+#define TRANSACTION_H
+
+/* Options of START TRANSACTION statement (and later of SET TRANSACTION stmt) */
+#define MYSQL_START_TRANS_OPT_WITH_CONS_SNAPSHOT    (1U << 0)
+
+bool trans_begin(THD *thd, uint flags= 0);
+bool trans_commit(THD *thd);
+bool trans_commit_implicit(THD *thd);
+bool trans_rollback(THD *thd);
+
+bool trans_commit_stmt(THD *thd);
+bool trans_rollback_stmt(THD *thd);
+
+bool trans_savepoint(THD *thd, LEX_STRING name);
+bool trans_rollback_to_savepoint(THD *thd, LEX_STRING name);
+bool trans_release_savepoint(THD *thd, LEX_STRING name);
+
+#endif /* TRANSACTION_H */

=== modified file 'storage/maria/ha_maria.cc'
--- a/storage/maria/ha_maria.cc	2008-06-30 09:59:59 +0000
+++ b/storage/maria/ha_maria.cc	2008-07-19 01:23:51 +0000
@@ -2277,8 +2277,8 @@ int ha_maria::start_stmt(THD *thd, thr_l
 
   This can be considered a hack. When Maria loses HA_NO_TRANSACTIONS it will
   be participant in the connection's transaction and so the implicit commits
-  (ha_commit()) (like in end_active_trans()) will do the implicit commit
-  without need to call this function which can then be removed.
+  (ha_commit_trans()) (like in trans_commit_implicit()) will do the implicit
+  commit without need to call this function which can then be removed.
 */
 
 int ha_maria::implicit_commit(THD *thd)

Thread
bzr commit into mysql-6.0 branch (davi:2682) WL#4284Davi Arnaut19 Jul
  • Re: bzr commit into mysql-6.0 branch (davi:2682) WL#4284Konstantin Osipov24 Jul
    • Re: bzr commit into mysql-6.0 branch (davi:2682) WL#4284Davi Arnaut24 Jul