Skip to content

Commit 83d64d9

Browse files
AliSQLAliSQL
authored andcommitted
[Feature] Issue#11 REDO LOG GROUP COMMIT AT SERVER LAYER
Summary: ======== When binlog is on, innodb redo log will write at innodb prepare stage, and binlog will write at binlog commit stage. Actually, write innodb redo log could move to binlog commit stage only if it write before binlog. Then, redo log and binlog can use original binary group commit logic to improve performance.
1 parent 950300e commit 83d64d9

31 files changed

+520
-173
lines changed

include/mysql/plugin.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -563,6 +563,7 @@ char *thd_security_context(MYSQL_THD thd, char *buffer, unsigned int length,
563563
/* Increments the row counter, see THD::row_count */
564564
void thd_inc_row_count(MYSQL_THD thd);
565565
int thd_allow_batch(MYSQL_THD thd);
566+
void thd_store_lsn(MYSQL_THD thd, unsigned long long lsn, int db_type);
566567

567568
/**
568569
Create a temporary file.

include/mysql/plugin_audit.h.pp

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -234,6 +234,7 @@
234234
unsigned int max_query_len);
235235
void thd_inc_row_count(void* thd);
236236
int thd_allow_batch(void* thd);
237+
void thd_store_lsn(void* thd, unsigned long long lsn, int db_type);
237238
int mysql_tmpfile(const char *prefix);
238239
int thd_killed(const void* thd);
239240
void thd_binlog_pos(const void* thd,

include/mysql/plugin_auth.h.pp

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -234,6 +234,7 @@
234234
unsigned int max_query_len);
235235
void thd_inc_row_count(void* thd);
236236
int thd_allow_batch(void* thd);
237+
void thd_store_lsn(void* thd, unsigned long long lsn, int db_type);
237238
int mysql_tmpfile(const char *prefix);
238239
int thd_killed(const void* thd);
239240
void thd_binlog_pos(const void* thd,

include/mysql/plugin_ftparser.h.pp

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -187,6 +187,7 @@
187187
unsigned int max_query_len);
188188
void thd_inc_row_count(void* thd);
189189
int thd_allow_batch(void* thd);
190+
void thd_store_lsn(void* thd, unsigned long long lsn, int db_type);
190191
int mysql_tmpfile(const char *prefix);
191192
int thd_killed(const void* thd);
192193
void thd_binlog_pos(const void* thd,

mysql-test/r/mysqld--help-notwin.result

Lines changed: 0 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -96,11 +96,6 @@ The following options may be given as the first argument:
9696
--binlog-ignore-db=name
9797
Tells the master that updates to the given database
9898
should not be logged to the binary log.
99-
--binlog-max-flush-queue-time=#
100-
The maximum time that the binary log group commit will
101-
keep reading transactions before it flush the
102-
transactions to the binary log (and optionally sync,
103-
depending on the value of sync_binlog).
10499
--binlog-order-commits
105100
Issue internal commit calls in the same order as
106101
transactions are written to the binary log. Default is to
@@ -1047,7 +1042,6 @@ binlog-direct-non-transactional-updates FALSE
10471042
binlog-error-action IGNORE_ERROR
10481043
binlog-format STATEMENT
10491044
binlog-gtid-simple-recovery FALSE
1050-
binlog-max-flush-queue-time 0
10511045
binlog-order-commits TRUE
10521046
binlog-row-event-max-size 8192
10531047
binlog-row-image FULL
Lines changed: 28 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,28 @@
1+
CREATE TABLE t1(c1 INT) ENGINE= InnoDB;
2+
# Crash right after flushing InnoDB redo log
3+
SET SESSION DEBUG="+d,crash_after_flush_engine_log";
4+
BEGIN;
5+
INSERT INTO t1 VALUES(1);
6+
COMMIT;
7+
ERROR HY000: Lost connection to MySQL server during query
8+
# Restart the master server
9+
#
10+
# Verify that a transaction can not be recovered during server
11+
# recovery from a crash, which happened after flushing it to
12+
# InnoDB redo log and before flushing it to binary log.
13+
#
14+
include/assert.inc [Table t1 must not contain 1]
15+
# Crash right after flushing binary log
16+
SET SESSION DEBUG="+d,crash_after_flush_binlog";
17+
BEGIN;
18+
INSERT INTO t1 VALUES(2);
19+
COMMIT;
20+
ERROR HY000: Lost connection to MySQL server during query
21+
# Restart the master server
22+
#
23+
# Verify that a transaction can be recovered during server
24+
# recovery from a crash, which happened after flushing it
25+
# to binary log.
26+
#
27+
include/assert.inc [Table t1 must contain 2]
28+
DROP TABLE t1;
Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1 @@
1+
--sync-binlog=1 --innodb-flush-log-at-trx-commit=1
Lines changed: 69 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,69 @@
1+
#
2+
# Bug#19424075 WRITE/SYNC REDO LOG BEFORE FLUSH THREAD CACHE TO BINLOG
3+
#
4+
# Verify that a transaction can not be recovered during server
5+
# recovery from a crash, which happened after flushing it to
6+
# InnoDB redo log and before flushing it to binary log. And
7+
# a transaction can be recovered during server recovery from
8+
# a crash, which happened after flushing it to binary log.
9+
#
10+
--source include/not_embedded.inc
11+
--source include/not_valgrind.inc
12+
--source include/have_log_bin.inc
13+
-- source include/have_debug.inc
14+
-- source include/have_innodb.inc
15+
16+
CREATE TABLE t1(c1 INT) ENGINE= InnoDB;
17+
18+
--exec echo "wait" > $MYSQLTEST_VARDIR/tmp/mysqld.1.expect
19+
--echo # Crash right after flushing InnoDB redo log
20+
SET SESSION DEBUG="+d,crash_after_flush_engine_log";
21+
BEGIN;
22+
INSERT INTO t1 VALUES(1);
23+
# 2013 - CR_SERVER_LOST
24+
--error 2013
25+
COMMIT;
26+
--source include/wait_until_disconnected.inc
27+
28+
--enable_reconnect
29+
--echo # Restart the master server
30+
--exec echo "restart" > $MYSQLTEST_VARDIR/tmp/mysqld.1.expect
31+
--source include/wait_until_connected_again.inc
32+
--disable_reconnect
33+
34+
--echo #
35+
--echo # Verify that a transaction can not be recovered during server
36+
--echo # recovery from a crash, which happened after flushing it to
37+
--echo # InnoDB redo log and before flushing it to binary log.
38+
--echo #
39+
--let $assert_text= Table t1 must not contain 1
40+
--let $assert_cond= [SELECT count(*) FROM t1 WHERE c1=1] = 0
41+
--source include/assert.inc
42+
43+
--exec echo "wait" > $MYSQLTEST_VARDIR/tmp/mysqld.1.expect
44+
--echo # Crash right after flushing binary log
45+
SET SESSION DEBUG="+d,crash_after_flush_binlog";
46+
BEGIN;
47+
INSERT INTO t1 VALUES(2);
48+
# 2013 - CR_SERVER_LOST
49+
--error 2013
50+
COMMIT;
51+
--source include/wait_until_disconnected.inc
52+
53+
--enable_reconnect
54+
--echo # Restart the master server
55+
--exec echo "restart" > $MYSQLTEST_VARDIR/tmp/mysqld.1.expect
56+
--source include/wait_until_connected_again.inc
57+
--disable_reconnect
58+
59+
--echo #
60+
--echo # Verify that a transaction can be recovered during server
61+
--echo # recovery from a crash, which happened after flushing it
62+
--echo # to binary log.
63+
--echo #
64+
--let $assert_text= Table t1 must contain 2
65+
--let $assert_cond= [SELECT count(*) FROM t1 WHERE c1=2] = 1
66+
--source include/assert.inc
67+
68+
# Cleanup
69+
DROP TABLE t1;
Lines changed: 37 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,37 @@
1+
include/master-slave.inc
2+
[connection master]
3+
CREATE TABLE t1 (a INT AUTO_INCREMENT PRIMARY KEY, b INT) ENGINE=INNODB;
4+
SET GLOBAL innodb_flush_log_at_trx_commit = 1;
5+
INSERT INTO t1(b) VALUES(1),(2),(3);
6+
SET GLOBAL innodb_flush_log_at_trx_commit= 0;
7+
UPDATE t1 SET b=b+1;
8+
SET GLOBAL innodb_flush_log_at_trx_commit=1;
9+
XA START '123';
10+
INSERT INTO t1(b) VALUES(4);
11+
XA END '123';
12+
XA PREPARE '123';
13+
XA COMMIT '123';
14+
SET DEBUG_SYNC="RESET";
15+
SET DEBUG_SYNC="process_as_leader SIGNAL leader_ready WAIT_FOR follower_ready";
16+
UPDATE t1 SET b=b+1 WHERE a=1;
17+
SET DEBUG_SYNC= "RESET";
18+
SET DEBUG_SYNC= "NOW WAIT_FOR leader_ready";
19+
SET DEBUG_SYNC= "wait_as_follower SIGNAL follower_ready";
20+
INSERT INTO t1(b) VALUES (8);
21+
FLUSH LOGS;
22+
SELECT * FROM t1 ORDER BY a;
23+
a b
24+
1 3
25+
2 3
26+
3 4
27+
4 4
28+
5 8
29+
SELECT * FROM t1 ORDER BY a;
30+
a b
31+
1 3
32+
2 3
33+
3 4
34+
4 4
35+
5 8
36+
DROP TABLE t1;
37+
include/rpl_end.inc
Lines changed: 64 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,64 @@
1+
--source include/have_innodb.inc
2+
--source include/have_debug.inc
3+
--source include/not_embedded.inc
4+
--disable_warnings
5+
--source include/master-slave.inc
6+
--enable_warnings
7+
connection master;
8+
9+
connect(con1,localhost,root,,);
10+
connect(con2,localhost,root,,);
11+
12+
connection con1;
13+
# Create table for the test.
14+
CREATE TABLE t1 (a INT AUTO_INCREMENT PRIMARY KEY, b INT) ENGINE=INNODB;
15+
16+
#Set innodb_flush_log_at_trx_commit to non-zero
17+
SET GLOBAL innodb_flush_log_at_trx_commit = 1;
18+
19+
# For a simple workload
20+
INSERT INTO t1(b) VALUES(1),(2),(3);
21+
22+
# If innodb_flush_log_at_trx_commit is 0 or XA PREPARE, LSN is not stored in THD.
23+
SET GLOBAL innodb_flush_log_at_trx_commit= 0;
24+
UPDATE t1 SET b=b+1;
25+
26+
SET GLOBAL innodb_flush_log_at_trx_commit=1;
27+
# Test XA transaction
28+
XA START '123';
29+
INSERT INTO t1(b) VALUES(4);
30+
XA END '123';
31+
XA PREPARE '123';
32+
XA COMMIT '123';
33+
34+
35+
# Two threads in one group and both stored lsn in THD.
36+
SET DEBUG_SYNC="RESET";
37+
SET DEBUG_SYNC="process_as_leader SIGNAL leader_ready WAIT_FOR follower_ready";
38+
send UPDATE t1 SET b=b+1 WHERE a=1;
39+
40+
connection con2;
41+
SET DEBUG_SYNC= "RESET";
42+
SET DEBUG_SYNC= "NOW WAIT_FOR leader_ready";
43+
SET DEBUG_SYNC= "wait_as_follower SIGNAL follower_ready";
44+
send INSERT INTO t1(b) VALUES (8);
45+
46+
connection con1;
47+
reap;
48+
49+
connection con2;
50+
reap;
51+
52+
connection master;
53+
FLUSH LOGS;
54+
sync_slave_with_master;
55+
56+
connection slave;
57+
SELECT * FROM t1 ORDER BY a;
58+
59+
connection master;
60+
SELECT * FROM t1 ORDER BY a;
61+
62+
#cleanup
63+
DROP TABLE t1;
64+
--source include/rpl_end.inc

0 commit comments

Comments
 (0)