1
0
mirror of https://github.com/MariaDB/server.git synced 2025-08-01 03:47:19 +03:00

Backport MySQL WL#2540 into MariaDB.

Patch backported:

bzr diff
'-rrevid:alfranio.correia@oracle.com-20101121143257-se3vpqus73l4mum0
..revid:luis.soares@oracle.com-20101124111752-9b8260bd1qak87hr'
--old=lp:mysql-server --new=lp:mysql-server
This commit is contained in:
unknown
2011-05-03 14:01:11 +02:00
parent d02d52629d
commit 014b8e7f43
67 changed files with 3034 additions and 1243 deletions

View File

@ -0,0 +1,23 @@
Binlog checksum testing
=======================
1. How it works.
The script copies a <suite> to directory <suite>_checksum,
collects test case names for t/ directory (except tests from
disabled def), randomly choose 90% of tests and add them
to disabled.def.
It means that mtr will run only 10% of random tests from each
suite.
At end the script run mtr:
./mysql-test-run.pl --suite=aaa_checksum,bbb_checksum \
--mysqld=--binlog-checksum=CRC32 arg1 ... argN
aaa,bbb - suite names from --suite option
arg1,argN - other command-line arguments of checksum.pl
2. The options:
--suite=suite1,suite2. Mandatory option. The list of suites for
binlog checksum testing.
--percent=N, where N is 1..99. Percent of running tests.

View File

@ -0,0 +1,164 @@
#!/usr/bin/perl
# Copyright (c) 2010, Oracle and/or its affiliates. All rights reserved.
#
# 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., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
use File::Basename;
use File::Copy qw(copy);
use File::Spec qw(catdir);
use File::Path;
use IO::File;
use strict;
# Constants and variables with default values
my $suites;
my $suffix = "_checksum";
my $percent_random_test = 10;
my $mtr_script;
my @mtr_argv;
my @mtr_suites;
# Check some arguments
foreach my $arg ( @ARGV )
{
if ($arg =~ m/\-\-suite\=(.+)/i)
{
$suites = $1;
}
elsif ($arg =~ m/\-\-percent\=(\d{1,2})/i)
{
$percent_random_test= $1;
}
else
{
push(@mtr_argv, $arg);
}
}
if (! defined( $suites ) )
{
die("The script requires --suite argument");
}
print "#################################################################\n";
print "# Binlog checksum testing\n";
print "# Run randomly $percent_random_test\% of tests from following suites: $suites\n";
print "#################################################################\n";
# Set extension directory
my $ext_dir= dirname(File::Spec->rel2abs($0));
# Set mysql-test directory
my $mysql_test_dir= $ext_dir;
$mysql_test_dir =~ s/(\/|\\)suite(\/|\\)rpl(\/|\\)extension$//;
# Main loop
foreach my $src_suite (split(",", $suites))
{
$src_suite=~ s/ //g;
my $dest_suite= $src_suite . $suffix;
push( @mtr_suites, $dest_suite);
print "Creating suite $dest_suite\n";
# *** Set platform-independent pathes ***
# Set source directory of suite
my $src_suite_dir = File::Spec->catdir($mysql_test_dir, "suite", $src_suite);
# Set destination directory of suite
my $dest_suite_dir = File::Spec->catdir($mysql_test_dir, "suite", $dest_suite);
print "Copying files\n\tfrom '$src_suite_dir'\n\tto '$dest_suite_dir'\n";
dircopy($src_suite_dir, $dest_suite_dir);
my $test_case_dir= File::Spec->catdir($dest_suite_dir, "t");
# Read disabled.def
my %disabled = ();
print "Read disabled.def\n";
my $fh = new IO::File File::Spec->catdir($test_case_dir, "disabled.def"), "r";
if ( defined $fh )
{
my @lines = <$fh>;
undef $fh;
foreach my $line ( @lines )
{
if ($line =~ m/^([a-zA-Z0-9_]+).+\:.+/i)
{
$disabled{$1}= 1;
}
}
}
# Read test case list
my %tests = ();
print "Generate test case list\n";
opendir my ($dh), $test_case_dir or die "Could not open dir '$test_case_dir': $!";
for my $entry (readdir $dh)
{
if ( $entry =~ m/^([a-zA-Z0-9_]+)\.test$/i )
{
my $test= $1;
if ( ! defined( $disabled{$test}) )
{
$tests{$test}= 1;
}
}
}
closedir($dh);
#
my @excluded = ();
my $excluded_test= int((((100 - $percent_random_test)/100) * scalar( keys %tests )));
while ( $excluded_test > 0 )
{
my @cases = keys %tests;
my $test = $cases[int(rand(scalar(@cases)))];
push ( @excluded, $test . "\t\t: Excluded for $dest_suite\n" );
delete $tests{$test};
$excluded_test--;
}
my $fh = new IO::File File::Spec->catdir($test_case_dir, "disabled.def"), O_WRONLY|O_APPEND;
if (defined $fh) {
print $fh join ("", sort @excluded);
undef $fh;
}
print "\t" . join("\n\t", sort keys %tests) . "\n";
}
# Set path to mtr with arguments
my $mtr_script = "perl " . File::Spec->catdir($mysql_test_dir, "mysql-test-run.pl") .
" --suite=" . join(",", @mtr_suites) . " " .
" --mysqld=--binlog-checksum=CRC32 " .
join (" ", @mtr_argv);
print "Run $mtr_script\n";
system( $mtr_script );
sub dircopy
{
my ($from_dir, $to_dir)= @_;
mkdir $to_dir if (! -e $to_dir);
opendir my($dh), $from_dir or die "Could not open dir '$from_dir': $!";
for my $entry (readdir $dh)
{
next if $entry =~ /^(\.|\.\.)$/;
my $source = File::Spec->catdir($from_dir, $entry);
my $destination = File::Spec->catdir($to_dir, $entry);
if (-d $source)
{
mkdir $destination or die "mkdir '$destination' failed: $!" if not -e $destination;
dircopy($source, $destination);
}
else
{
copy($source, $destination) or die "copy '$source' to '$destination' failed: $!";
}
}
closedir $dh;
return;
}

View File

@ -1,5 +1,6 @@
include/master-slave.inc
[connection master]
call mtr.add_suppression("Slave I/O: The slave I/O thread stops because a fatal error is encountered when it tried to SET @master_binlog_checksum");
create table t1(n int);
select * from t1;
n

View File

@ -0,0 +1,126 @@
include/master-slave.inc
[connection master]
call mtr.add_suppression('Slave can not handle replication events with the checksum that master is configured to log');
call mtr.add_suppression('Replication event checksum verification failed');
call mtr.add_suppression('Relay log write failure: could not queue event from master');
call mtr.add_suppression('Master is configured to log replication events with checksum, but will not send such events to slaves that cannot process them');
set @master_save_binlog_checksum= @@global.binlog_checksum;
set @save_master_verify_checksum = @@global.master_verify_checksum;
select @@global.binlog_checksum as 'must be CRC32 because of the command line option';
must be CRC32 because of the command line option
CRC32
select @@session.binlog_checksum as 'no session var';
ERROR HY000: Variable 'binlog_checksum' is a GLOBAL variable
select @@global.master_verify_checksum as 'must be zero because of default';
must be zero because of default
0
select @@session.master_verify_checksum as 'no session var';
ERROR HY000: Variable 'master_verify_checksum' is a GLOBAL variable
set @slave_save_binlog_checksum= @@global.binlog_checksum;
set @save_slave_sql_verify_checksum = @@global.slave_sql_verify_checksum;
select @@global.slave_sql_verify_checksum as 'must be one because of default';
must be one because of default
1
select @@session.slave_sql_verify_checksum as 'no session var';
ERROR HY000: Variable 'slave_sql_verify_checksum' is a GLOBAL variable
show binary logs;
Log_name File_size
master-bin.000001 #
set @@global.binlog_checksum = NONE;
*** must be rotations seen ***
show binary logs;
Log_name File_size
master-bin.000001 #
master-bin.000002 #
set @@global.binlog_checksum = default;
set @@global.binlog_checksum = CRC32;
set @@global.binlog_checksum = CRC32;
set @@global.master_verify_checksum = 0;
set @@global.master_verify_checksum = default;
set @@global.binlog_checksum = ADLER32;
ERROR 42000: Variable 'checksum' can't be set to the value of 'ADLER32'
set @@global.master_verify_checksum = 2;
ERROR 42000: Variable 'master_verify_checksum' can't be set to the value of '2'
set @@global.slave_sql_verify_checksum = 0;
set @@global.slave_sql_verify_checksum = default;
set @@global.slave_sql_verify_checksum = 2;
ERROR 42000: Variable 'slave_sql_verify_checksum' can't be set to the value of '2'
set @@global.binlog_checksum = NONE;
create table t1 (a int);
flush logs;
flush logs;
flush logs;
flush logs;
flush logs;
flush logs;
select count(*) as zero from t1;
zero
0
include/stop_slave.inc
set @@global.binlog_checksum = CRC32;
insert into t1 values (1) /* will not be applied on slave due to simulation */;
set @@global.debug='d,simulate_slave_unaware_checksum';
start slave;
include/wait_for_slave_io_to_stop.inc
*** Got IO thread error code: 1236, text: Got fatal error 1236 from master when reading data from binary log: 'Slave can not handle replication events with the checksum that master is configured to log' ***
select count(*) as zero from t1;
zero
0
set @@global.debug='';
include/start_slave.inc
set @@global.master_verify_checksum = 1;
set @@session.debug='d,simulate_checksum_test_failure';
show binlog events;
ERROR HY000: Error when executing command SHOW BINLOG EVENTS: Wrong offset or I/O error
set @@session.debug='';
set @@global.master_verify_checksum = default;
include/stop_slave.inc
create table t2 (a int);
set @@global.debug='d,simulate_checksum_test_failure';
start slave io_thread;
include/wait_for_slave_io_to_stop.inc
*** Got IO thread error code: 1595, text: Relay log write failure: could not queue event from master ***
set @@global.debug='';
start slave io_thread;
include/wait_for_slave_param.inc [Read_Master_Log_Pos]
set @@global.slave_sql_verify_checksum = 1;
set @@global.debug='d,simulate_checksum_test_failure';
start slave sql_thread;
include/wait_for_slave_sql_to_stop.inc
*** Got SQL thread error code: 1593, text: Error initializing relay log position: I/O error reading event at position 4 ***
set @@global.debug='';
include/start_slave.inc
select count(*) as 'must be zero' from t2;
must be zero
0
stop slave;
reset slave;
set @@global.binlog_checksum= IF(floor((rand()*1000)%2), "CRC32", "NONE");
flush logs;
set @@global.binlog_checksum= CRC32;
reset master;
flush logs;
create table t3 (a int, b char(5));
include/start_slave.inc
select count(*) as 'must be zero' from t3;
must be zero
0
include/stop_slave.inc
change master to master_host='127.0.0.1',master_port=MASTER_PORT, master_user='root';
flush logs;
reset master;
insert into t3 value (1, @@global.binlog_checksum);
include/start_slave.inc
flush logs;
select count(*) as 'must be one' from t3;
must be one
1
set @@global.binlog_checksum= IF(floor((rand()*1000)%2), "CRC32", "NONE");
insert into t3 value (1, @@global.binlog_checksum);
drop table t1, t2, t3;
set @@global.binlog_checksum = @master_save_binlog_checksum;
set @@global.master_verify_checksum = @save_master_verify_checksum;
set @@global.binlog_checksum = @slave_save_binlog_checksum;
set @@global.slave_sql_verify_checksum = @save_slave_sql_verify_checksum;
End of tests
include/rpl_end.inc

View File

@ -0,0 +1,119 @@
include/master-slave.inc
[connection master]
call mtr.add_suppression("Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a system function that may return a different value on the slave. Statement: insert into t2 set data=repeat.*'a', @act_size.*");
call mtr.add_suppression("Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a system function that may return a different value on the slave. Statement: insert into t1 values.* NAME_CONST.*'n',.*, @data .*");
set @save_binlog_cache_size = @@global.binlog_cache_size;
set @save_binlog_checksum = @@global.binlog_checksum;
set @save_master_verify_checksum = @@global.master_verify_checksum;
set @@global.binlog_cache_size = 4096;
set @@global.binlog_checksum = CRC32;
set @@global.master_verify_checksum = 1;
include/stop_slave.inc
include/start_slave.inc
flush status;
show status like "binlog_cache_use";
Variable_name Value
Binlog_cache_use 0
show status like "binlog_cache_disk_use";
Variable_name Value
Binlog_cache_disk_use 0
drop table if exists t1;
create table t1 (a int PRIMARY KEY, b CHAR(32)) engine=innodb;
create procedure test.p_init (n int, size int)
begin
while n > 0 do
select round(RAND() * size) into @act_size;
set @data = repeat('a', @act_size);
insert into t1 values(n, @data );
set n= n-1;
end while;
end|
begin;
call test.p_init(4000, 32);
commit;
show status like "binlog_cache_use";
Variable_name Value
Binlog_cache_use 1
*** binlog_cache_disk_use must be non-zero ***
show status like "binlog_cache_disk_use";
Variable_name Value
Binlog_cache_disk_use 1
include/diff_tables.inc [master:test.t1, slave:test.t1]
begin;
delete from t1;
commit;
flush status;
create table t2(a int auto_increment primary key, data VARCHAR(12288)) ENGINE=Innodb;
show status like "binlog_cache_use";
Variable_name Value
Binlog_cache_use 1
*** binlog_cache_disk_use must be non-zero ***
show status like "binlog_cache_disk_use";
Variable_name Value
Binlog_cache_disk_use 1
include/diff_tables.inc [master:test.t2, slave:test.t2]
begin;
delete from t2;
commit;
flush status;
create table t3(a int auto_increment primary key, data VARCHAR(8192)) engine=innodb;
show status like "binlog_cache_use";
Variable_name Value
Binlog_cache_use 1
*** binlog_cache_disk_use must be non-zero ***
show status like "binlog_cache_disk_use";
Variable_name Value
Binlog_cache_disk_use 1
include/diff_tables.inc [master:test.t3, slave:test.t3]
begin;
delete from t3;
commit;
flush status;
create procedure test.p1 (n int)
begin
while n > 0 do
case (select (round(rand()*100) % 3) + 1)
when 1 then
select round(RAND() * 32) into @act_size;
set @data = repeat('a', @act_size);
insert into t1 values(n, @data);
when 2 then
begin
select round(8192 + RAND() * 4096) into @act_size;
insert into t2 set data=repeat('a', @act_size);
end;
when 3 then
begin
select round(3686.4000 + RAND() * 819.2000) into @act_size;
insert into t3 set data= repeat('a', @act_size);
end;
end case;
set n= n-1;
end while;
end|
set autocommit= 0;
begin;
call test.p1(1000);
commit;
show status like "binlog_cache_use";
Variable_name Value
Binlog_cache_use 1
*** binlog_cache_disk_use must be non-zero ***
show status like "binlog_cache_disk_use";
Variable_name Value
Binlog_cache_disk_use 1
include/diff_tables.inc [master:test.t1, slave:test.t1]
include/diff_tables.inc [master:test.t2, slave:test.t2]
include/diff_tables.inc [master:test.t3, slave:test.t3]
begin;
delete from t1;
delete from t2;
delete from t3;
commit;
drop table t1, t2, t3;
set @@global.binlog_cache_size = @save_binlog_cache_size;
set @@global.binlog_checksum = @save_binlog_checksum;
set @@global.master_verify_checksum = @save_master_verify_checksum;
drop procedure test.p_init;
drop procedure test.p1;
include/rpl_end.inc

View File

@ -0,0 +1,49 @@
include/master-slave.inc
[connection master]
call mtr.add_suppression('Found invalid event in binary log');
call mtr.add_suppression('Slave I/O: Relay log write failure: could not queue event from master');
call mtr.add_suppression('event read from binlog did not pass crc check');
call mtr.add_suppression('Replication event checksum verification failed');
SET @old_master_verify_checksum = @@master_verify_checksum;
# 1. Creating test table/data and set corruption position for testing
* insert/update/delete rows in table t1 *
CREATE TABLE t1 (a INT NOT NULL PRIMARY KEY, b VARCHAR(10), c VARCHAR(100));
include/stop_slave.inc
# 2. Corruption in master binlog and SHOW BINLOG EVENTS
SET GLOBAL debug="+d,corrupt_read_log_event_char";
SHOW BINLOG EVENTS;
ERROR HY000: Error when executing command SHOW BINLOG EVENTS: Wrong offset or I/O error
SET GLOBAL debug="-d,corrupt_read_log_event_char";
# 3. Master read a corrupted event from binlog and send the error to slave
SET GLOBAL debug="+d,corrupt_read_log_event2";
START SLAVE IO_THREAD;
include/wait_for_slave_io_error.inc [errno=1236]
SET GLOBAL debug="-d,corrupt_read_log_event2";
# 4. Master read a corrupted event from binlog and send it to slave
SET GLOBAL master_verify_checksum=0;
SET GLOBAL debug="+d,corrupt_read_log_event2";
START SLAVE IO_THREAD;
include/wait_for_slave_io_error.inc [errno=1595]
SET GLOBAL debug="-d,corrupt_read_log_event2";
SET GLOBAL debug= "";
SET GLOBAL master_verify_checksum=1;
# 5. Slave. Corruption in network
SET GLOBAL debug="+d,corrupt_queue_event";
START SLAVE IO_THREAD;
include/wait_for_slave_io_error.inc [errno=1595]
SET GLOBAL debug="-d,corrupt_queue_event";
# 6. Slave. Corruption in relay log
SET GLOBAL debug="+d,corrupt_read_log_event_char";
START SLAVE;
include/wait_for_slave_sql_error.inc [errno=1593]
SET GLOBAL debug="-d,corrupt_read_log_event_char";
SET GLOBAL debug= "";
# 7. Seek diff for tables on master and slave
include/start_slave.inc
include/diff_tables.inc [master:test.t1, slave:test.t1]
# 8. Clean up
SET GLOBAL debug= "";
SET GLOBAL master_verify_checksum = @old_master_verify_checksum;
DROP TABLE t1;
SET GLOBAL debug= "";
include/rpl_end.inc

View File

@ -69,7 +69,7 @@ insert into temp_table values ("testing temporary tables part 2");
create table t3 (n int);
select count(*) from t3 where n >= 4;
count(*)
100
90
create table t4 select * from temp_table;
show binary logs;
Log_name File_size
@ -88,7 +88,7 @@ include/check_slave_is_running.inc
lock tables t3 read;
select count(*) from t3 where n >= 4;
count(*)
100
90
unlock tables;
drop table if exists t1,t2,t3,t4;
End of 4.1 tests

View File

@ -22,7 +22,7 @@ a
[on slave]
---- Wait until slave stops with an error ----
include/wait_for_slave_sql_error.inc [errno=1062]
Last_SQL_Error = Could not execute Write_rows event on table test.t1; Duplicate entry '1' for key 'PRIMARY', Error_code: 1062; handler error HA_ERR_FOUND_DUPP_KEY; the event's master log master-bin.000001, end_log_pos 480 (expected "duplicate key" error)
Last_SQL_Error = Could not execute Write_rows event on table test.t1; Duplicate entry '1' for key 'PRIMARY', Error_code: 1062; handler error HA_ERR_FOUND_DUPP_KEY; the event's master log master-bin.000001, end_log_pos 485 (expected "duplicate key" error)
SELECT * FROM t1;
a
1

View File

@ -3,6 +3,7 @@
# I/O thread left (some old bug fixed in 4.0.17)
source include/master-slave.inc;
call mtr.add_suppression("Slave I/O: The slave I/O thread stops because a fatal error is encountered when it tried to SET @master_binlog_checksum");
connection master;
# Make SQL slave thread advance a bit

View File

@ -0,0 +1 @@
--binlog-checksum=CRC32

View File

@ -0,0 +1,247 @@
# WL2540 replication events checksum
# Testing configuration parameters
--source include/master-slave.inc
--source include/have_debug.inc
--source include/have_binlog_format_mixed.inc
call mtr.add_suppression('Slave can not handle replication events with the checksum that master is configured to log');
call mtr.add_suppression('Replication event checksum verification failed');
# due to C failure simulation
call mtr.add_suppression('Relay log write failure: could not queue event from master');
call mtr.add_suppression('Master is configured to log replication events with checksum, but will not send such events to slaves that cannot process them');
# A. read/write access to the global vars:
# binlog_checksum master_verify_checksum slave_sql_verify_checksum
connection master;
set @master_save_binlog_checksum= @@global.binlog_checksum;
set @save_master_verify_checksum = @@global.master_verify_checksum;
select @@global.binlog_checksum as 'must be CRC32 because of the command line option';
--error ER_INCORRECT_GLOBAL_LOCAL_VAR
select @@session.binlog_checksum as 'no session var';
select @@global.master_verify_checksum as 'must be zero because of default';
--error ER_INCORRECT_GLOBAL_LOCAL_VAR
select @@session.master_verify_checksum as 'no session var';
connection slave;
set @slave_save_binlog_checksum= @@global.binlog_checksum;
set @save_slave_sql_verify_checksum = @@global.slave_sql_verify_checksum;
select @@global.slave_sql_verify_checksum as 'must be one because of default';
--error ER_INCORRECT_GLOBAL_LOCAL_VAR
select @@session.slave_sql_verify_checksum as 'no session var';
connection master;
source include/show_binary_logs.inc;
set @@global.binlog_checksum = NONE;
--echo *** must be rotations seen ***
source include/show_binary_logs.inc;
set @@global.binlog_checksum = default;
# testing lack of side-effects in non-effective update of binlog_checksum:
set @@global.binlog_checksum = CRC32;
set @@global.binlog_checksum = CRC32;
set @@global.master_verify_checksum = 0;
set @@global.master_verify_checksum = default;
--error ER_WRONG_VALUE_FOR_VAR
set @@global.binlog_checksum = ADLER32;
--error ER_WRONG_VALUE_FOR_VAR
set @@global.master_verify_checksum = 2; # the var is of bool type
connection slave;
set @@global.slave_sql_verify_checksum = 0;
set @@global.slave_sql_verify_checksum = default;
--error ER_WRONG_VALUE_FOR_VAR
set @@global.slave_sql_verify_checksum = 2; # the var is of bool type
#
# B. Old Slave to New master conditions
#
# while master does not send a checksum-ed binlog the Old Slave can
# work with the New Master
connection master;
set @@global.binlog_checksum = NONE;
create table t1 (a int);
# testing that binlog rotation preserves opt_binlog_checksum value
flush logs;
flush logs;
flush logs;
sync_slave_with_master;
#connection slave;
# checking that rotation on the slave side leaves slave stable
flush logs;
flush logs;
flush logs;
select count(*) as zero from t1;
source include/stop_slave.inc;
connection master;
set @@global.binlog_checksum = CRC32;
insert into t1 values (1) /* will not be applied on slave due to simulation */;
# instruction to the dump thread
### set @@global.debug='d,simulate_slave_unaware_checksum'; # merge todo: +/- d syntax fails in my clone
connection slave;
set @@global.debug='d,simulate_slave_unaware_checksum'; # merge todo: +/- d syntax fails in my clone
start slave;
source include/wait_for_slave_io_to_stop.inc;
let $errno= query_get_value(SHOW SLAVE STATUS, Last_IO_Errno, 1);
let $error= query_get_value(SHOW SLAVE STATUS, Last_IO_Error, 1);
--echo *** Got IO thread error code: $errno, text: $error ***
select count(*) as zero from t1;
###connection master;
set @@global.debug=''; # merge todo: +/- d syntax fails in my clone
connection slave;
source include/start_slave.inc;
#
# C. checksum failure simulations
#
# C1. Failure by a client thread
connection master;
set @@global.master_verify_checksum = 1;
set @@session.debug='d,simulate_checksum_test_failure'; # merge todo deploy +/- syntax
--error ER_ERROR_WHEN_EXECUTING_COMMAND
show binlog events;
set @@session.debug=''; # merge todo: +/- d syntax fails in my clone
set @@global.master_verify_checksum = default;
#connection master;
sync_slave_with_master;
connection slave;
source include/stop_slave.inc;
connection master;
create table t2 (a int);
let $pos_master= query_get_value(SHOW MASTER STATUS, Position, 1);
connection slave;
# C2. Failure by IO thread
# instruction to io thread
set @@global.debug='d,simulate_checksum_test_failure'; # merge todo deploy +/- syntax
start slave io_thread;
source include/wait_for_slave_io_to_stop.inc;
let $errno= query_get_value(SHOW SLAVE STATUS, Last_IO_Errno, 1);
let $error= query_get_value(SHOW SLAVE STATUS, Last_IO_Error, 1);
--echo *** Got IO thread error code: $errno, text: $error ***
set @@global.debug=''; # todo: merge
# to make IO thread re-read it again w/o the failure
start slave io_thread;
let $slave_param= Read_Master_Log_Pos;
let $slave_param_value= $pos_master;
source include/wait_for_slave_param.inc;
# C3. Failure by SQL thread
# instruction to sql thread;
set @@global.slave_sql_verify_checksum = 1;
set @@global.debug='d,simulate_checksum_test_failure'; # merge todo deploy +/- syntax
start slave sql_thread;
source include/wait_for_slave_sql_to_stop.inc;
let $errno= query_get_value(SHOW SLAVE STATUS, Last_SQL_Errno, 1);
let $error= query_get_value(SHOW SLAVE STATUS, Last_SQL_Error, 1);
--echo *** Got SQL thread error code: $errno, text: $error ***
# resuming SQL thread to parse out the event w/o the failure
set @@global.debug='';
source include/start_slave.inc;
connection master;
sync_slave_with_master;
#connection slave;
select count(*) as 'must be zero' from t2;
#
# D. Reset slave, Change-Master, Binlog & Relay-log rotations with
# random value on binlog_checksum on both master and slave
#
connection slave;
stop slave;
reset slave;
# randomize slave server's own checksum policy
set @@global.binlog_checksum= IF(floor((rand()*1000)%2), "CRC32", "NONE");
flush logs;
connection master;
set @@global.binlog_checksum= CRC32;
reset master;
flush logs;
create table t3 (a int, b char(5));
connection slave;
source include/start_slave.inc;
connection master;
sync_slave_with_master;
#connection slave;
select count(*) as 'must be zero' from t3;
source include/stop_slave.inc;
--replace_result $MASTER_MYPORT MASTER_PORT
eval change master to master_host='127.0.0.1',master_port=$MASTER_MYPORT, master_user='root';
connection master;
flush logs;
reset master;
insert into t3 value (1, @@global.binlog_checksum);
connection slave;
source include/start_slave.inc;
flush logs;
connection master;
sync_slave_with_master;
#connection slave;
select count(*) as 'must be one' from t3;
connection master;
set @@global.binlog_checksum= IF(floor((rand()*1000)%2), "CRC32", "NONE");
insert into t3 value (1, @@global.binlog_checksum);
sync_slave_with_master;
#connection slave;
#clean-up
connection master;
drop table t1, t2, t3;
set @@global.binlog_checksum = @master_save_binlog_checksum;
set @@global.master_verify_checksum = @save_master_verify_checksum;
#connection slave;
sync_slave_with_master;
set @@global.binlog_checksum = @slave_save_binlog_checksum;
set @@global.slave_sql_verify_checksum = @save_slave_sql_verify_checksum;
--echo End of tests
--source include/rpl_end.inc

View File

@ -0,0 +1,255 @@
-- source include/have_innodb.inc
-- source include/master-slave.inc
--disable_warnings
call mtr.add_suppression("Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a system function that may return a different value on the slave. Statement: insert into t2 set data=repeat.*'a', @act_size.*");
call mtr.add_suppression("Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a system function that may return a different value on the slave. Statement: insert into t1 values.* NAME_CONST.*'n',.*, @data .*");
--enable_warnings
connection master;
set @save_binlog_cache_size = @@global.binlog_cache_size;
set @save_binlog_checksum = @@global.binlog_checksum;
set @save_master_verify_checksum = @@global.master_verify_checksum;
set @@global.binlog_cache_size = 4096;
set @@global.binlog_checksum = CRC32;
set @@global.master_verify_checksum = 1;
# restart slave to force the dump thread to verify events (on master side)
connection slave;
source include/stop_slave.inc;
source include/start_slave.inc;
connection master;
#
# Testing a critical part of checksum handling dealing with transaction cache.
# The cache's buffer size is set to be less than the transaction's footprint
# in binlog.
#
# To verify combined buffer-by-buffer read out of the file and fixing crc per event
# there are the following parts:
#
# 1. the event size is much less than the cache's buffer
# 2. the event size is bigger than the cache's buffer
# 3. the event size if approximately the same as the cache's buffer
# 4. all in above
#
# 1. the event size is much less than the cache's buffer
#
flush status;
show status like "binlog_cache_use";
show status like "binlog_cache_disk_use";
--disable_warnings
drop table if exists t1;
--enable_warnings
#
# parameter to ensure the test slightly varies binlog content
# between different invocations
#
let $deviation_size=32;
eval create table t1 (a int PRIMARY KEY, b CHAR($deviation_size)) engine=innodb;
# Now we are going to create transaction which is long enough so its
# transaction binlog will be flushed to disk...
delimiter |;
create procedure test.p_init (n int, size int)
begin
while n > 0 do
select round(RAND() * size) into @act_size;
set @data = repeat('a', @act_size);
insert into t1 values(n, @data );
set n= n-1;
end while;
end|
delimiter ;|
let $1 = 4000; # PB2 can run it slow to time out on following sync_slave_with_master:s
begin;
--disable_warnings
# todo: check if it is really so.
#+Note 1592 Unsafe statement binlogged in statement format since BINLOG_FORMAT = STATEMENT. Reason for unsafeness: Statement uses a system function whose value may differ on slave.
eval call test.p_init($1, $deviation_size);
--enable_warnings
commit;
show status like "binlog_cache_use";
--echo *** binlog_cache_disk_use must be non-zero ***
show status like "binlog_cache_disk_use";
sync_slave_with_master;
let $diff_tables=master:test.t1, slave:test.t1;
source include/diff_tables.inc;
# undoing changes with verifying the above once again
connection master;
begin;
delete from t1;
commit;
sync_slave_with_master;
#
# 2. the event size is bigger than the cache's buffer
#
connection master;
flush status;
let $t2_data_size= `select 3 * @@global.binlog_cache_size`;
let $t2_aver_size= `select 2 * @@global.binlog_cache_size`;
let $t2_max_rand= `select 1 * @@global.binlog_cache_size`;
eval create table t2(a int auto_increment primary key, data VARCHAR($t2_data_size)) ENGINE=Innodb;
let $1=100;
--disable_query_log
begin;
while ($1)
{
eval select round($t2_aver_size + RAND() * $t2_max_rand) into @act_size;
set @data = repeat('a', @act_size);
insert into t2 set data = @data;
dec $1;
}
commit;
--enable_query_log
show status like "binlog_cache_use";
--echo *** binlog_cache_disk_use must be non-zero ***
show status like "binlog_cache_disk_use";
sync_slave_with_master;
let $diff_tables=master:test.t2, slave:test.t2;
source include/diff_tables.inc;
# undoing changes with verifying the above once again
connection master;
begin;
delete from t2;
commit;
sync_slave_with_master;
#
# 3. the event size if approximately the same as the cache's buffer
#
connection master;
flush status;
let $t3_data_size= `select 2 * @@global.binlog_cache_size`;
let $t3_aver_size= `select (9 * @@global.binlog_cache_size) / 10`;
let $t3_max_rand= `select (2 * @@global.binlog_cache_size) / 10`;
eval create table t3(a int auto_increment primary key, data VARCHAR($t3_data_size)) engine=innodb;
let $1= 300;
--disable_query_log
begin;
while ($1)
{
eval select round($t3_aver_size + RAND() * $t3_max_rand) into @act_size;
insert into t3 set data= repeat('a', @act_size);
dec $1;
}
commit;
--enable_query_log
show status like "binlog_cache_use";
--echo *** binlog_cache_disk_use must be non-zero ***
show status like "binlog_cache_disk_use";
sync_slave_with_master;
let $diff_tables=master:test.t3, slave:test.t3;
source include/diff_tables.inc;
# undoing changes with verifying the above once again
connection master;
begin;
delete from t3;
commit;
sync_slave_with_master;
#
# 4. all in above
#
connection master;
flush status;
delimiter |;
eval create procedure test.p1 (n int)
begin
while n > 0 do
case (select (round(rand()*100) % 3) + 1)
when 1 then
select round(RAND() * $deviation_size) into @act_size;
set @data = repeat('a', @act_size);
insert into t1 values(n, @data);
when 2 then
begin
select round($t2_aver_size + RAND() * $t2_max_rand) into @act_size;
insert into t2 set data=repeat('a', @act_size);
end;
when 3 then
begin
select round($t3_aver_size + RAND() * $t3_max_rand) into @act_size;
insert into t3 set data= repeat('a', @act_size);
end;
end case;
set n= n-1;
end while;
end|
delimiter ;|
let $1= 1000;
set autocommit= 0;
begin;
--disable_warnings
eval call test.p1($1);
--enable_warnings
commit;
show status like "binlog_cache_use";
--echo *** binlog_cache_disk_use must be non-zero ***
show status like "binlog_cache_disk_use";
sync_slave_with_master;
let $diff_tables=master:test.t1, slave:test.t1;
source include/diff_tables.inc;
let $diff_tables=master:test.t2, slave:test.t2;
source include/diff_tables.inc;
let $diff_tables=master:test.t3, slave:test.t3;
source include/diff_tables.inc;
connection master;
begin;
delete from t1;
delete from t2;
delete from t3;
commit;
drop table t1, t2, t3;
set @@global.binlog_cache_size = @save_binlog_cache_size;
set @@global.binlog_checksum = @save_binlog_checksum;
set @@global.master_verify_checksum = @save_master_verify_checksum;
drop procedure test.p_init;
drop procedure test.p1;
--source include/rpl_end.inc

View File

@ -0,0 +1 @@
--binlog-checksum=CRC32 --master-verify-checksum=1

View File

@ -0,0 +1 @@
--binlog-checksum=CRC32 --slave-sql-verify-checksum=1

View File

@ -0,0 +1,131 @@
############################################################
# Author: Serge Kozlov <serge.kozlov@oracle.com>
# Date: 17 Oct 2010
# Purpose: WL#5064 Testing with corrupted events.
# The test emulates the corruption at the vary stages
# of replication:
# - in binlog file
# - in network
# - in relay log
############################################################
--source include/have_debug.inc
--source include/master-slave.inc
# Block legal errors for MTR
call mtr.add_suppression('Found invalid event in binary log');
call mtr.add_suppression('Slave I/O: Relay log write failure: could not queue event from master');
call mtr.add_suppression('event read from binlog did not pass crc check');
call mtr.add_suppression('Replication event checksum verification failed');
SET @old_master_verify_checksum = @@master_verify_checksum;
# Creating test table/data and set corruption position for testing
--echo # 1. Creating test table/data and set corruption position for testing
--connection master
--echo * insert/update/delete rows in table t1 *
# Corruption algorithm modifies only the first event and
# then will be reset. To avoid checking always the first event
# from binlog (usually it is FD) we randomly execute different
# statements and set position for corruption inside events.
CREATE TABLE t1 (a INT NOT NULL PRIMARY KEY, b VARCHAR(10), c VARCHAR(100));
--disable_query_log
let $i=`SELECT 3+CEILING(10*RAND())`;
let $j=1;
let $pos=0;
while ($i) {
eval INSERT INTO t1 VALUES ($j, 'a', NULL);
if (`SELECT RAND() > 0.7`)
{
eval UPDATE t1 SET c = REPEAT('a', 20) WHERE a = $j;
}
if (`SELECT RAND() > 0.8`)
{
eval DELETE FROM t1 WHERE a = $j;
}
if (!$pos) {
let $pos= query_get_value(SHOW MASTER STATUS, Position, 1);
--sync_slave_with_master
--source include/stop_slave.inc
--disable_query_log
--connection master
}
dec $i;
inc $j;
}
--enable_query_log
# Emulate corruption in binlog file when SHOW BINLOG EVENTS is executing
--echo # 2. Corruption in master binlog and SHOW BINLOG EVENTS
SET GLOBAL debug="+d,corrupt_read_log_event_char";
--echo SHOW BINLOG EVENTS;
--disable_query_log
send_eval SHOW BINLOG EVENTS FROM $pos;
--enable_query_log
--error ER_ERROR_WHEN_EXECUTING_COMMAND
reap;
SET GLOBAL debug="-d,corrupt_read_log_event_char";
# Emulate corruption on master with crc checking on master
--echo # 3. Master read a corrupted event from binlog and send the error to slave
SET GLOBAL debug="+d,corrupt_read_log_event2";
--connection slave
START SLAVE IO_THREAD;
let $slave_io_errno= 1236;
--source include/wait_for_slave_io_error.inc
--connection master
SET GLOBAL debug="-d,corrupt_read_log_event2";
# Emulate corruption on master without crc checking on master
--echo # 4. Master read a corrupted event from binlog and send it to slave
--connection master
SET GLOBAL master_verify_checksum=0;
SET GLOBAL debug="+d,corrupt_read_log_event2";
--connection slave
START SLAVE IO_THREAD;
let $slave_io_errno= 1595;
--source include/wait_for_slave_io_error.inc
--connection master
SET GLOBAL debug="-d,corrupt_read_log_event2";
SET GLOBAL debug= "";
SET GLOBAL master_verify_checksum=1;
# Emulate corruption in network
--echo # 5. Slave. Corruption in network
--connection slave
SET GLOBAL debug="+d,corrupt_queue_event";
START SLAVE IO_THREAD;
let $slave_io_errno= 1595;
--source include/wait_for_slave_io_error.inc
SET GLOBAL debug="-d,corrupt_queue_event";
# Emulate corruption in relay log
--echo # 6. Slave. Corruption in relay log
SET GLOBAL debug="+d,corrupt_read_log_event_char";
START SLAVE;
let $slave_sql_errno= 1593;
--source include/wait_for_slave_sql_error.inc
SET GLOBAL debug="-d,corrupt_read_log_event_char";
SET GLOBAL debug= "";
# Start normal replication and compare same table on master
# and slave
--echo # 7. Seek diff for tables on master and slave
--connection slave
--source include/start_slave.inc
--connection master
--sync_slave_with_master
let $diff_tables= master:test.t1, slave:test.t1;
--source include/diff_tables.inc
# Clean up
--echo # 8. Clean up
--connection master
SET GLOBAL debug= "";
SET GLOBAL master_verify_checksum = @old_master_verify_checksum;
DROP TABLE t1;
--sync_slave_with_master
SET GLOBAL debug= "";
--source include/rpl_end.inc

View File

@ -4,11 +4,14 @@
# imitate the bug, so it has to stop).
source include/have_debug.inc;
# because of pretend_version_50034_in_binlog the test can't run with checksum
source include/have_binlog_checksum_off.inc;
source include/master-slave.inc;
# Currently only statement-based-specific bugs are here
-- source include/have_binlog_format_mixed_or_statement.inc
#
# This is to test that slave properly detects if
# master may suffer from:

View File

@ -142,7 +142,10 @@ select * from t2;
connection master;
create temporary table temp_table (a char(80) not null);
insert into temp_table values ("testing temporary tables part 2");
let $1=100;
# the nummber of produced logs is sensitive to whether checksum is NONE or CRC32
# the value of 90 makes it even
let $1=90;
create table t3 (n int);
disable_query_log;

View File

@ -12,7 +12,7 @@ create table t1(n int);
sync_slave_with_master;
stop slave;
connection master;
let $1=5000;
let $1=2500;
disable_query_log;
while ($1)
{