Skip to content

Commit a0b77eb

Browse files
committed
MDEV-36685 CREATE-SELECT may lose in binlog side-effects of stored-routine
When the SELECT sub-statement executes a stored function that is defined to modify a non-transactional table, like delimiter |; create function f_ia(arg int) returns integer begin insert into ti_pk set a=1; insert into ta set a=1; insert into ti_pk set a=arg; return 1; end | delimiter ;| any modified records that the function has succeeded on must be binlogged as a "side effect" of CREATE-SELECT. It is expected that a failing CREATE-SELECT like --error ER_DUP_ENTRY set statement binlog_format = ROW for create table t_y (a int) engine=aria select f_ia(1 /* err in Innodb after Aria stmt is done */) as a; leaves upon itself the following state: include/show_binlog_events.inc Log_name Pos Event_type Server_id End_log_pos Info master-bin.000001 # Gtid # # BEGIN GTID #-#-# master-bin.000001 # Table_map # # table_id: # (test. ta) master-bin.000001 # Write_rows_v1 # # table_id: # flags: STMT_END_F master-bin.000001 # Query # # COMMIT select * from ta; a 1 select count(*) = 0 from ti_pk; true However it's not so for the binlog part. The reason is that prior to MDEV-34150 fixes the CREATE-SELECT's errored phase leaves the binlog caches intact (the file:pos from 10.11 c06c362) to defer their reset to the rollback phase of the top-level /* the statement cache gets binlogged */ where the side-effect changes gets binlogged. MDEV-34150 fixes harmed (+#4 line) the statement cache in particular in the error phase (file:pos are from 395db6f the current 11.8 ) /* The caches incl the statement cache are gone */ /* 'cos of MDEV-34150 */ +#4 0x00005d75f9b6a92e in THD::binlog_remove_rows_events (this=0x52c000240288) at log.cc:579 Apparently it should not have been there, as proper emptying (either with reset for the transactional cache or flush and then reset for the statement cache) is (must be) always done via binlog_rollback of the top-level statement. To observe the above requirement the case is fixed with the removal of thd->binlog_remove_rows_events() and its definition. Tested with rpl.rpl_create_select_row. Reviewed-by Brandon Nesterenko.
1 parent 82867e0 commit a0b77eb

File tree

3 files changed

+0
-26
lines changed

3 files changed

+0
-26
lines changed

sql/log.cc

-22
Original file line numberDiff line numberDiff line change
@@ -558,28 +558,6 @@ class binlog_cache_mngr {
558558
binlog_cache_mngr(const binlog_cache_mngr& info);
559559
};
560560

561-
562-
/*
563-
Remove all row event from all binlog caches and clear all caches.
564-
This is only called from CREATE .. SELECT, in which case it safe to delete
565-
also events from the statement cache.
566-
*/
567-
568-
void THD::binlog_remove_rows_events()
569-
{
570-
binlog_cache_mngr *cache_mngr= binlog_get_cache_mngr();
571-
DBUG_ENTER("THD::binlog_remove_rows_events");
572-
573-
if (!cache_mngr ||
574-
(!WSREP_EMULATE_BINLOG_NNULL(this) && !mysql_bin_log.is_open()))
575-
DBUG_VOID_RETURN;
576-
577-
MYSQL_BIN_LOG::remove_pending_rows_event(this, &cache_mngr->stmt_cache);
578-
MYSQL_BIN_LOG::remove_pending_rows_event(this, &cache_mngr->trx_cache);
579-
cache_mngr->reset(1,1);
580-
DBUG_VOID_RETURN;
581-
}
582-
583561
/**
584562
The function handles the first phase of two-phase binlogged ALTER.
585563
On master binlogs START ALTER when that is configured to do so.

sql/sql_class.h

-1
Original file line numberDiff line numberDiff line change
@@ -3338,7 +3338,6 @@ class THD: public THD_count, /* this must be first */
33383338
binlog_flush_pending_rows_event(stmt_end, TRUE));
33393339
}
33403340
int binlog_flush_pending_rows_event(bool stmt_end, bool is_transactional);
3341-
void binlog_remove_rows_events();
33423341
uint has_pending_row_events();
33433342
bool binlog_need_stmt_format(bool is_transactional) const
33443343
{

sql/sql_insert.cc

-3
Original file line numberDiff line numberDiff line change
@@ -5438,9 +5438,6 @@ void select_create::abort_result_set()
54385438
bool table_creation_was_logged= (!tmp_table ||
54395439
table->s->table_creation_was_logged);
54405440

5441-
/* CREATE SELECT failed. Remove all row events and clear caches */
5442-
thd->binlog_remove_rows_events();
5443-
54445441
if (tmp_table)
54455442
{
54465443
DBUG_ASSERT(saved_tmp_table_share);

0 commit comments

Comments
 (0)