=== added file 'mysql-test/extra/rpl_tests/rpl_temp_error.test'
--- mysql-test/extra/rpl_tests/rpl_temp_error.test	1970-01-01 00:00:00 +0000
+++ mysql-test/extra/rpl_tests/rpl_temp_error.test	2015-01-14 09:34:32 +0000
@@ -0,0 +1,28 @@
+# An auxiliary file for causing temporary error on slave SQL thread.
+
+--echo # [ on slave ]
+connection slave;
+BEGIN;
+--echo # It will lock table t1 on the row in which c1 is 1 until COMMIT or ROLLBACK
+UPDATE t1 SET c2= "slave" WHERE c1= 1;
+
+connection master;
+--echo # [ on master ]
+BEGIN;
+INSERT INTO t3 VALUES(1);
+eval $statement;
+eval UPDATE t1 SET c2='$statement' WHERE c1= 1;
+COMMIT;
+save_master_pos;
+
+connection slave;
+--echo # [ on slave ]
+let $slave_sql_errno= 1205;
+source include/wait_for_slave_sql_error.inc;
+
+ROLLBACK;
+
+START SLAVE SQL_THREAD;
+source include/wait_for_slave_sql_to_start.inc;
+
+sync_with_master;

=== added file 'mysql-test/suite/rpl/r/rpl_DML_error.result'
--- mysql-test/suite/rpl/r/rpl_DML_error.result	1970-01-01 00:00:00 +0000
+++ mysql-test/suite/rpl/r/rpl_DML_error.result	2015-01-14 10:42:42 +0000
@@ -0,0 +1,49 @@
+include/master-slave.inc
+[connection master]
+# Verify the statements can be binlogged correctly when error happens
+# ------------------------------------------------------------------
+CREATE TABLE t1(c1 INT KEY) ENGINE=MyISAM;
+CREATE TABLE t2(c1 INT KEY) ENGINE=MyISAM;
+INSERT INTO t1 VALUES(1);
+INSERT INTO t2 VALUES(1);
+
+# Nothing is inserted.
+INSERT INTO t1 VALUES(1),(2);
+ERROR 23000: Duplicate entry '1' for key 'PRIMARY'
+include/show_binlog_events.inc
+
+# A row is inserted.
+INSERT INTO t1 VALUES(2),(1);
+ERROR 23000: Duplicate entry '1' for key 'PRIMARY'
+include/diff_tables.inc [master:test.t1, slave:test.t1]
+
+# Nothing is inserted.
+INSERT INTO t1 SELECT 1 UNION SELECT 2;
+ERROR 23000: Duplicate entry '1' for key 'PRIMARY'
+include/show_binlog_events.inc
+
+# A row is inserted.
+INSERT INTO t1 SELECT 3 UNION SELECT 2;
+ERROR 23000: Duplicate entry '2' for key 'PRIMARY'
+include/diff_tables.inc [master:test.t1, slave:test.t1]
+
+# A row is updated.
+UPDATE t1 SET c1=4;
+ERROR 23000: Duplicate entry '4' for key 'PRIMARY'
+include/diff_tables.inc [master:test.t1, slave:test.t1]
+# Nothing is updated.
+UPDATE t1 SET c1=4;
+ERROR 23000: Duplicate entry '4' for key 'PRIMARY'
+include/show_binlog_events.inc
+
+# A row is updated.
+UPDATE t1, t2 SET t1.c1= 5, t2.c1=5;
+ERROR 23000: Duplicate entry '5' for key 'PRIMARY'
+include/diff_tables.inc [master:test.t1, slave:test.t1]
+
+Nothing is updated.
+UPDATE t1, t2 SET t1.c1= 5, t2.c1=5;
+ERROR 23000: Duplicate entry '5' for key 'PRIMARY'
+include/show_binlog_events.inc
+DROP TABLE t1, t2;
+include/rpl_end.inc

=== modified file 'mysql-test/suite/rpl/r/rpl_begin_commit_rollback.result'
--- mysql-test/suite/rpl/r/rpl_begin_commit_rollback.result	2013-09-14 01:09:36 +0000
+++ mysql-test/suite/rpl/r/rpl_begin_commit_rollback.result	2015-01-14 10:18:19 +0000
@@ -172,6 +172,299 @@
 # Verify INSERT statements on the Innodb table are rolled back;
 SELECT * FROM db1.t1 WHERE a IN (30, 40);
 a
+
+# BUG#55798 Slave SQL retry on transaction inserts extra data into
+# non-transaction table
+# ----------------------------------------------------------------
+# To verify that SQL thread does not retry a transaction which can
+# not be rolled back safely, even though only a temporary error is
+# encountered.
+
+# [ on master ]
+USE db1;
+DROP TABLE t1, t2;
+CREATE TABLE t1(c1 INT KEY, c2 CHAR(100)) ENGINE=InnoDB;
+CREATE TABLE t2(c1 INT) ENGINE=MyISAM;
+CREATE TABLE t3(c1 INT) ENGINE=InnoDB;
+INSERT INTO t1 VALUES(1, "master");
+SET @@session.binlog_direct_non_transactional_updates= FALSE;
+# [ on slave ]
+USE db1;
+SET @timeout_old= @@GLOBAL.innodb_lock_wait_timeout;
+SET GLOBAL innodb_lock_wait_timeout= 1;
+STOP SLAVE SQL_THREAD;
+include/wait_for_slave_sql_to_stop.inc
+START SLAVE SQL_THREAD;
+include/wait_for_slave_sql_to_start.inc
+# Verify the SQL thread doesn't retry the transaction when one of
+# its statements has modified a non-transactional table.
+# ----------------------------------------------------------------
+
+# INSERT statement inserts a row to a non-transactional table.
+# [ on slave ]
+BEGIN;
+# It will lock table t1 on the row in which c1 is 1 until COMMIT or ROLLBACK
+UPDATE t1 SET c2= "slave" WHERE c1= 1;
+# [ on master ]
+BEGIN;
+INSERT INTO t3 VALUES(1);
+INSERT INTO t2 VALUES(1);
+Warnings:
+Note	1592	Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it accesses a non-transactional table after accessing a transactional table within the same transaction.
+UPDATE t1 SET c2='INSERT INTO t2 VALUES(1)' WHERE c1= 1;
+COMMIT;
+# [ on slave ]
+include/wait_for_slave_sql_error.inc [errno=1205]
+ROLLBACK;
+START SLAVE SQL_THREAD;
+include/wait_for_slave_sql_to_start.inc
+
+# INSERT ... SELECT statement inserts a row to a non-transactional table.
+# [ on slave ]
+BEGIN;
+# It will lock table t1 on the row in which c1 is 1 until COMMIT or ROLLBACK
+UPDATE t1 SET c2= "slave" WHERE c1= 1;
+# [ on master ]
+BEGIN;
+INSERT INTO t3 VALUES(1);
+INSERT INTO t2 SELECT 2;
+Warnings:
+Note	1592	Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it accesses a non-transactional table after accessing a transactional table within the same transaction.
+UPDATE t1 SET c2='INSERT INTO t2 SELECT 2' WHERE c1= 1;
+COMMIT;
+# [ on slave ]
+include/wait_for_slave_sql_error.inc [errno=1205]
+ROLLBACK;
+START SLAVE SQL_THREAD;
+include/wait_for_slave_sql_to_start.inc
+
+# UPDATE statement updates a row to a non-transactional table.
+# [ on slave ]
+BEGIN;
+# It will lock table t1 on the row in which c1 is 1 until COMMIT or ROLLBACK
+UPDATE t1 SET c2= "slave" WHERE c1= 1;
+# [ on master ]
+BEGIN;
+INSERT INTO t3 VALUES(1);
+UPDATE t2 SET c1= 3;
+Warnings:
+Note	1592	Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it accesses a non-transactional table after accessing a transactional table within the same transaction.
+UPDATE t1 SET c2='UPDATE t2 SET c1= 3' WHERE c1= 1;
+COMMIT;
+# [ on slave ]
+include/wait_for_slave_sql_error.inc [errno=1205]
+ROLLBACK;
+START SLAVE SQL_THREAD;
+include/wait_for_slave_sql_to_start.inc
+
+# MULTI-UPDATE statement updates a row to a non-transactional table.
+# [ on slave ]
+BEGIN;
+# It will lock table t1 on the row in which c1 is 1 until COMMIT or ROLLBACK
+UPDATE t1 SET c2= "slave" WHERE c1= 1;
+# [ on master ]
+BEGIN;
+INSERT INTO t3 VALUES(1);
+UPDATE t2, t3 SET t2.c1=4, t3.c1= 4;
+Warnings:
+Note	1592	Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement accesses nontransactional table as well as transactional or temporary table, and writes to any of them.
+UPDATE t1 SET c2='UPDATE t2, t3 SET t2.c1=4, t3.c1= 4' WHERE c1= 1;
+COMMIT;
+# [ on slave ]
+include/wait_for_slave_sql_error.inc [errno=1205]
+ROLLBACK;
+START SLAVE SQL_THREAD;
+include/wait_for_slave_sql_to_start.inc
+
+# DELETE statement deletes a row from a non-transactional table.
+# [ on slave ]
+BEGIN;
+# It will lock table t1 on the row in which c1 is 1 until COMMIT or ROLLBACK
+UPDATE t1 SET c2= "slave" WHERE c1= 1;
+# [ on master ]
+BEGIN;
+INSERT INTO t3 VALUES(1);
+DELETE FROM t2;
+Warnings:
+Note	1592	Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it accesses a non-transactional table after accessing a transactional table within the same transaction.
+UPDATE t1 SET c2='DELETE FROM t2' WHERE c1= 1;
+COMMIT;
+# [ on slave ]
+include/wait_for_slave_sql_error.inc [errno=1205]
+ROLLBACK;
+START SLAVE SQL_THREAD;
+include/wait_for_slave_sql_to_start.inc
+
+# CREATE TEMPORARY TABLE statement in the transaction
+# [ on slave ]
+BEGIN;
+# It will lock table t1 on the row in which c1 is 1 until COMMIT or ROLLBACK
+UPDATE t1 SET c2= "slave" WHERE c1= 1;
+# [ on master ]
+BEGIN;
+INSERT INTO t3 VALUES(1);
+CREATE TEMPORARY TABLE IF NOT EXISTS temp_t(c1 INT);
+UPDATE t1 SET c2='CREATE TEMPORARY TABLE IF NOT EXISTS temp_t(c1 INT)' WHERE c1= 1;
+COMMIT;
+# [ on slave ]
+include/wait_for_slave_sql_error.inc [errno=1205]
+ROLLBACK;
+START SLAVE SQL_THREAD;
+include/wait_for_slave_sql_to_start.inc
+
+# DROP TEMPORARY TABLE statement in the transaction
+# [ on slave ]
+BEGIN;
+# It will lock table t1 on the row in which c1 is 1 until COMMIT or ROLLBACK
+UPDATE t1 SET c2= "slave" WHERE c1= 1;
+# [ on master ]
+BEGIN;
+INSERT INTO t3 VALUES(1);
+DROP TEMPORARY TABLE IF EXISTS temp_t;
+UPDATE t1 SET c2='DROP TEMPORARY TABLE IF EXISTS temp_t' WHERE c1= 1;
+COMMIT;
+# [ on slave ]
+include/wait_for_slave_sql_error.inc [errno=1205]
+ROLLBACK;
+START SLAVE SQL_THREAD;
+include/wait_for_slave_sql_to_start.inc
+
+# Verify that the SQL thread doesn't retry the transaction if one
+# of the sub-statements has modified a non-transactional table.
+# ----------------------------------------------------------------
+CREATE FUNCTION f_insert()
+RETURNS INT
+BEGIN
+INSERT INTO t2 VALUES(1);
+RETURN 2;
+END|
+CREATE FUNCTION f_insert_select()
+RETURNS INT
+BEGIN
+INSERT INTO t2 SELECT 2;
+RETURN 2;
+END|
+CREATE FUNCTION f_update()
+RETURNS INT
+BEGIN
+UPDATE t2 SET c1=3;
+RETURN 2;
+END |
+CREATE TABLE t4 (c1 INT);
+INSERT INTO t4 VAlUES(1),(2);
+CREATE FUNCTION f_multi_update()
+RETURNS INT
+BEGIN
+UPDATE t2, t4 SET t2.c1=4, t4.c1= 4;
+RETURN 2;
+END |
+CREATE FUNCTION f_delete()
+RETURNS INT
+BEGIN
+DELETE FROM t2;
+RETURN 2;
+END |
+
+# The INSERT statement in a function inserts a row into a
+# non-transactional table.
+# [ on slave ]
+BEGIN;
+# It will lock table t1 on the row in which c1 is 1 until COMMIT or ROLLBACK
+UPDATE t1 SET c2= "slave" WHERE c1= 1;
+# [ on master ]
+BEGIN;
+INSERT INTO t3 VALUES(1);
+INSERT INTO t3 VALUES(f_insert());
+Warnings:
+Note	1592	Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement accesses nontransactional table as well as transactional or temporary table, and writes to any of them.
+UPDATE t1 SET c2='INSERT INTO t3 VALUES(f_insert())' WHERE c1= 1;
+COMMIT;
+# [ on slave ]
+include/wait_for_slave_sql_error.inc [errno=1205]
+ROLLBACK;
+START SLAVE SQL_THREAD;
+include/wait_for_slave_sql_to_start.inc
+
+# The INSERT ... SELECT statement in a function inserts a row into a
+# non-transactional table.
+# [ on slave ]
+BEGIN;
+# It will lock table t1 on the row in which c1 is 1 until COMMIT or ROLLBACK
+UPDATE t1 SET c2= "slave" WHERE c1= 1;
+# [ on master ]
+BEGIN;
+INSERT INTO t3 VALUES(1);
+INSERT INTO t3 VALUES(f_insert());
+Warnings:
+Note	1592	Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement accesses nontransactional table as well as transactional or temporary table, and writes to any of them.
+UPDATE t1 SET c2='INSERT INTO t3 VALUES(f_insert())' WHERE c1= 1;
+COMMIT;
+# [ on slave ]
+include/wait_for_slave_sql_error.inc [errno=1205]
+ROLLBACK;
+START SLAVE SQL_THREAD;
+include/wait_for_slave_sql_to_start.inc
+
+# The UPDATE statement in a function updates a row of a
+# non-transactional table.
+# [ on slave ]
+BEGIN;
+# It will lock table t1 on the row in which c1 is 1 until COMMIT or ROLLBACK
+UPDATE t1 SET c2= "slave" WHERE c1= 1;
+# [ on master ]
+BEGIN;
+INSERT INTO t3 VALUES(1);
+INSERT INTO t3 VALUES(f_update());
+Warnings:
+Note	1592	Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement accesses nontransactional table as well as transactional or temporary table, and writes to any of them.
+UPDATE t1 SET c2='INSERT INTO t3 VALUES(f_update())' WHERE c1= 1;
+COMMIT;
+# [ on slave ]
+include/wait_for_slave_sql_error.inc [errno=1205]
+ROLLBACK;
+START SLAVE SQL_THREAD;
+include/wait_for_slave_sql_to_start.inc
+
+# The MULTI-UPDATE statement in a function updates a row of a
+# non-transactional table.
+# [ on slave ]
+BEGIN;
+# It will lock table t1 on the row in which c1 is 1 until COMMIT or ROLLBACK
+UPDATE t1 SET c2= "slave" WHERE c1= 1;
+# [ on master ]
+BEGIN;
+INSERT INTO t3 VALUES(1);
+INSERT INTO t3 VALUES(f_multi_update());
+Warnings:
+Note	1592	Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement accesses nontransactional table as well as transactional or temporary table, and writes to any of them.
+UPDATE t1 SET c2='INSERT INTO t3 VALUES(f_multi_update())' WHERE c1= 1;
+COMMIT;
+# [ on slave ]
+include/wait_for_slave_sql_error.inc [errno=1205]
+ROLLBACK;
+START SLAVE SQL_THREAD;
+include/wait_for_slave_sql_to_start.inc
+
+# The DELETE statement in a function deletes a row from a
+# non-transactional table.
+# [ on slave ]
+BEGIN;
+# It will lock table t1 on the row in which c1 is 1 until COMMIT or ROLLBACK
+UPDATE t1 SET c2= "slave" WHERE c1= 1;
+# [ on master ]
+BEGIN;
+INSERT INTO t3 VALUES(1);
+INSERT INTO t3 VALUES(f_delete());
+Warnings:
+Note	1592	Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement accesses nontransactional table as well as transactional or temporary table, and writes to any of them.
+UPDATE t1 SET c2='INSERT INTO t3 VALUES(f_delete())' WHERE c1= 1;
+COMMIT;
+# [ on slave ]
+include/wait_for_slave_sql_error.inc [errno=1205]
+ROLLBACK;
+START SLAVE SQL_THREAD;
+include/wait_for_slave_sql_to_start.inc
+SET @@global.innodb_lock_wait_timeout= @timeout_old;
 #
 # Clean up
 #

=== added file 'mysql-test/suite/rpl/t/rpl_DML_error.test'
--- mysql-test/suite/rpl/t/rpl_DML_error.test	1970-01-01 00:00:00 +0000
+++ mysql-test/suite/rpl/t/rpl_DML_error.test	2015-01-14 10:40:25 +0000
@@ -0,0 +1,77 @@
+source include/master-slave.inc;
+source include/have_innodb.inc;
+
+--echo # Verify the statements can be binlogged correctly when error happens
+--echo # ------------------------------------------------------------------
+CREATE TABLE t1(c1 INT KEY) ENGINE=MyISAM;
+CREATE TABLE t2(c1 INT KEY) ENGINE=MyISAM;
+INSERT INTO t1 VALUES(1);
+INSERT INTO t2 VALUES(1);
+
+--echo
+--echo # Nothing is inserted.
+let $binlog_start= query_get_value(SHOW MASTER STATUS, Position, 1);
+--error 1062
+INSERT INTO t1 VALUES(1),(2);
+source include/show_binlog_events.inc;
+
+--echo
+--echo # A row is inserted.
+--error 1062
+INSERT INTO t1 VALUES(2),(1);
+sync_slave_with_master;
+let $diff_tables= master:test.t1, slave:test.t1;
+source include/diff_tables.inc;
+
+--echo
+--echo # Nothing is inserted.
+connection master;
+let $binlog_start= query_get_value(SHOW MASTER STATUS, Position, 1);
+--error 1062
+INSERT INTO t1 SELECT 1 UNION SELECT 2;
+source include/show_binlog_events.inc;
+
+--echo
+--echo # A row is inserted.
+--error 1062
+INSERT INTO t1 SELECT 3 UNION SELECT 2;
+sync_slave_with_master;
+source include/diff_tables.inc;
+
+
+--echo
+--echo # A row is updated.
+connection master;
+let $binlog_start= query_get_value(SHOW MASTER STATUS, Position, 1);
+--error 1062
+UPDATE t1 SET c1=4;
+sync_slave_with_master;
+source include/diff_tables.inc;
+
+--echo # Nothing is updated.
+connection master;
+let $binlog_start= query_get_value(SHOW MASTER STATUS, Position, 1);
+--error 1062
+UPDATE t1 SET c1=4;
+source include/show_binlog_events.inc;
+
+--echo
+--echo # A row is updated.
+connection master;
+--error 1062
+UPDATE t1, t2 SET t1.c1= 5, t2.c1=5;
+sync_slave_with_master;
+source include/diff_tables.inc;
+
+--echo
+--echo Nothing is updated.
+connection master;
+let $binlog_start= query_get_value(SHOW MASTER STATUS, Position, 1);
+--error 1062
+UPDATE t1, t2 SET t1.c1= 5, t2.c1=5;
+source include/show_binlog_events.inc;
+
+DROP TABLE t1, t2;
+
+
+source include/rpl_end.inc;

=== modified file 'mysql-test/suite/rpl/t/rpl_begin_commit_rollback.test'
--- mysql-test/suite/rpl/t/rpl_begin_commit_rollback.test	2010-12-19 17:15:12 +0000
+++ mysql-test/suite/rpl/t/rpl_begin_commit_rollback.test	2015-01-14 09:36:22 +0000
@@ -171,10 +171,165 @@
 --echo # Verify INSERT statements on the Innodb table are rolled back;
 SELECT * FROM db1.t1 WHERE a IN (30, 40);
 
+--echo
+--echo # BUG#55798 Slave SQL retry on transaction inserts extra data into
+--echo # non-transaction table
+--echo # ----------------------------------------------------------------
+--echo # To verify that SQL thread does not retry a transaction which can
+--echo # not be rolled back safely, even though only a temporary error is
+--echo # encountered.
+--echo
+--echo # [ on master ]
+connection master;
+USE db1;
+DROP TABLE t1, t2;
+CREATE TABLE t1(c1 INT KEY, c2 CHAR(100)) ENGINE=InnoDB;
+CREATE TABLE t2(c1 INT) ENGINE=MyISAM;
+CREATE TABLE t3(c1 INT) ENGINE=InnoDB;
+INSERT INTO t1 VALUES(1, "master");
+
+SET @@session.binlog_direct_non_transactional_updates= FALSE;
+
+sync_slave_with_master;
+
+--echo # [ on slave ]
+USE db1;
+
+SET @timeout_old= @@GLOBAL.innodb_lock_wait_timeout;
+SET GLOBAL innodb_lock_wait_timeout= 1;
+
+STOP SLAVE SQL_THREAD;
+source include/wait_for_slave_sql_to_stop.inc;
+START SLAVE SQL_THREAD;
+source include/wait_for_slave_sql_to_start.inc;
+
+--echo # Verify the SQL thread doesn't retry the transaction when one of
+--echo # its statements has modified a non-transactional table.
+--echo # ----------------------------------------------------------------
+--echo
+--echo # INSERT statement inserts a row to a non-transactional table.
+let $statement= INSERT INTO t2 VALUES(1);
+source extra/rpl_tests/rpl_temp_error.test;
+
+--echo
+--echo # INSERT ... SELECT statement inserts a row to a non-transactional table.
+let $statement= INSERT INTO t2 SELECT 2;
+source extra/rpl_tests/rpl_temp_error.test;
+
+--echo
+--echo # UPDATE statement updates a row to a non-transactional table.
+connection master;
+let $statement= UPDATE t2 SET c1= 3;
+source extra/rpl_tests/rpl_temp_error.test;
+
+--echo
+--echo # MULTI-UPDATE statement updates a row to a non-transactional table.
+connection master;
+let $statement= UPDATE t2, t3 SET t2.c1=4, t3.c1= 4;
+source extra/rpl_tests/rpl_temp_error.test;
+
+--echo
+--echo # DELETE statement deletes a row from a non-transactional table.
+connection master;
+let $statement= DELETE FROM t2;
+source extra/rpl_tests/rpl_temp_error.test;
+
+--echo
+--echo # CREATE TEMPORARY TABLE statement in the transaction
+let $statement= CREATE TEMPORARY TABLE IF NOT EXISTS temp_t(c1 INT);
+source extra/rpl_tests/rpl_temp_error.test;
+
+--echo
+--echo # DROP TEMPORARY TABLE statement in the transaction
+let $statement= DROP TEMPORARY TABLE IF EXISTS temp_t;
+source extra/rpl_tests/rpl_temp_error.test;
+
+--echo
+--echo # Verify that the SQL thread doesn't retry the transaction if one
+--echo # of the sub-statements has modified a non-transactional table.
+--echo # ----------------------------------------------------------------
+
+connection master;
+--delimiter |
+
+CREATE FUNCTION f_insert()
+RETURNS INT
+BEGIN
+  INSERT INTO t2 VALUES(1);
+  RETURN 2;
+END|
+
+CREATE FUNCTION f_insert_select()
+RETURNS INT
+BEGIN
+  INSERT INTO t2 SELECT 2;
+  RETURN 2;
+END|
+
+CREATE FUNCTION f_update()
+RETURNS INT
+BEGIN
+  UPDATE t2 SET c1=3;
+  RETURN 2;
+END |
+
+CREATE TABLE t4 (c1 INT);
+INSERT INTO t4 VAlUES(1),(2);
+CREATE FUNCTION f_multi_update()
+RETURNS INT
+BEGIN
+  UPDATE t2, t4 SET t2.c1=4, t4.c1= 4;
+  RETURN 2;
+END |
+
+CREATE FUNCTION f_delete()
+RETURNS INT
+BEGIN
+  DELETE FROM t2;
+  RETURN 2;
+END |
+--delimiter ;
+
+--echo
+--echo # The INSERT statement in a function inserts a row into a
+--echo # non-transactional table.
+let $statement= INSERT INTO t3 VALUES(f_insert());
+source extra/rpl_tests/rpl_temp_error.test;
+
+--echo
+--echo # The INSERT ... SELECT statement in a function inserts a row into a
+--echo # non-transactional table.
+let $statement= INSERT INTO t3 VALUES(f_insert());
+source extra/rpl_tests/rpl_temp_error.test;
+
+--echo
+--echo # The UPDATE statement in a function updates a row of a
+--echo # non-transactional table.
+connection master;
+let $statement= INSERT INTO t3 VALUES(f_update());
+source extra/rpl_tests/rpl_temp_error.test;
+
+--echo
+--echo # The MULTI-UPDATE statement in a function updates a row of a
+--echo # non-transactional table.
+connection master;
+let $statement= INSERT INTO t3 VALUES(f_multi_update());
+source extra/rpl_tests/rpl_temp_error.test;
+
+--echo
+--echo # The DELETE statement in a function deletes a row from a
+--echo # non-transactional table.
+connection master;
+let $statement= INSERT INTO t3 VALUES(f_delete());
+source extra/rpl_tests/rpl_temp_error.test;
+
+SET @@global.innodb_lock_wait_timeout= @timeout_old;
+
 --echo #
 --echo # Clean up
 --echo #
 connection master;
 DROP DATABASE db1;
 DROP DATABASE db2;
+
 --source include/rpl_end.inc

=== added file 'mysql-test/suite/rpl/t/rpl_rollback_transactional.test'
--- mysql-test/suite/rpl/t/rpl_rollback_transactional.test	1970-01-01 00:00:00 +0000
+++ mysql-test/suite/rpl/t/rpl_rollback_transactional.test	2015-01-14 10:45:34 +0000
@@ -0,0 +1,33 @@
+source include/master-slave.inc;
+source include/have_innodb.inc;
+
+--echo #
+--echo # MDEV-6012: MySQL Bug#56184 Rolled back transaction without non-trasactional table updated was binlogged
+--echo #
+connection master;
+CREATE TABLE t1(c1 INT KEY) ENGINE=MyISAM;
+CREATE TABLE t2(c1 INT NOT NULL PRIMARY KEY) ENGINE=innodb;
+BEGIN;
+INSERT INTO t1 VALUES(1);
+INSERT INTO t2 VALUES(1);
+ROLLBACK;
+select * from t1;
+select * from t2;
+source include/show_binlog_events.inc;
+sync_slave_with_master;
+let $diff_tables= master:test.t1, slave:test.t1;
+source include/diff_tables.inc;
+
+BEGIN;
+INSERT INTO t1 VALUES(2);
+--error 1062
+INSERT INTO t2 VALUES (2),(2);
+select * from t1;
+select * from t2;
+source include/show_binlog_events.inc;
+sync_slave_with_master;
+source include/diff_tables.inc;
+
+drop table t1, t2;
+
+source include/rpl_end.inc;
\ No newline at end of file
