From b558c8c46cfcf3d9eed10c100c73456e8139ce32 Mon Sep 17 00:00:00 2001 From: Bjorn Munch Date: Tue, 23 Feb 2010 13:33:07 +0100 Subject: [PATCH 001/129] Removed duplicated mtr warning suppressions --- mysql-test/include/mtr_warnings.sql | 8 -------- 1 file changed, 8 deletions(-) diff --git a/mysql-test/include/mtr_warnings.sql b/mysql-test/include/mtr_warnings.sql index 462a900df6d..caadf10109c 100644 --- a/mysql-test/include/mtr_warnings.sql +++ b/mysql-test/include/mtr_warnings.sql @@ -185,14 +185,6 @@ INSERT INTO global_suppressions VALUES ("Master server does not support or not configured semi-sync replication, fallback to asynchronous"), (": The MySQL server is running with the --secure-backup-file-priv option so it cannot execute this statement"), ("Slave: Unknown table 't1' Error_code: 1051"), - /* - Transient network failures that cause warnings on reconnect. - BUG#47743 and BUG#47983. - */ - ("Slave I/O: Get master SERVER_ID failed with error:.*"), - ("Slave I/O: Get master clock failed with error:.*"), - ("Slave I/O: Get master COLLATION_SERVER failed with error:.*"), - ("Slave I/O: Get master TIME_ZONE failed with error:.*"), /* Messages from valgrind */ ("==[0-9]*== Memcheck,"), From 4760adbf3f8e283cb83912bc51d79d531787f0ba Mon Sep 17 00:00:00 2001 From: Bjorn Munch Date: Tue, 2 Mar 2010 12:39:32 +0100 Subject: [PATCH 002/129] Bug #51590 mysqltest: --disable_abort_on_error does not work inside while/if abort_on_error flag for stmt was set at initial parse (Re)-set flag before execution instead, also added to test --- client/mysqltest.cc | 7 ++++--- mysql-test/r/mysqltest.result | 1 + mysql-test/t/mysqltest.test | 6 +++++- 3 files changed, 10 insertions(+), 4 deletions(-) diff --git a/client/mysqltest.cc b/client/mysqltest.cc index d45f9acd87a..8ba1271e1fa 100644 --- a/client/mysqltest.cc +++ b/client/mysqltest.cc @@ -7571,9 +7571,6 @@ void get_command_type(struct st_command* command) sizeof(saved_expected_errors)); DBUG_PRINT("info", ("There are %d expected errors", command->expected_errors.count)); - command->abort_on_error= (command->expected_errors.count == 0 && - abort_on_error); - DBUG_VOID_RETURN; } @@ -7918,6 +7915,10 @@ int main(int argc, char **argv) command->type= Q_COMMENT; } + /* (Re-)set abort_on_error for this command */ + command->abort_on_error= (command->expected_errors.count == 0 && + abort_on_error); + /* delimiter needs to be executed so we can continue to parse */ my_bool ok_to_do= cur_block->ok || command->type == Q_DELIMITER; /* diff --git a/mysql-test/r/mysqltest.result b/mysql-test/r/mysqltest.result index 67c08b0ae97..38112c032b5 100644 --- a/mysql-test/r/mysqltest.result +++ b/mysql-test/r/mysqltest.result @@ -325,6 +325,7 @@ outer=2 ifval=0 outer=1 ifval=1 here is the sourced script ERROR 42S02: Table 'test.nowhere' doesn't exist +ERROR 42000: You have an error in your SQL syntax; check the manual that corresponds to your MySQL server version for the right syntax to use near 'else' at line 1 In loop here is the sourced script diff --git a/mysql-test/t/mysqltest.test b/mysql-test/t/mysqltest.test index 25293ff29e7..b2d7c59a8a0 100644 --- a/mysql-test/t/mysqltest.test +++ b/mysql-test/t/mysqltest.test @@ -863,7 +863,7 @@ while ($outer) } # Test source in an if in a while which is false on 1st iteration -# Also test --error in same context +# Also test --error and --disable_abort_on_error in same context let $outer= 2; # Number of outer loops let $ifval= 0; # false 1st time while ($outer) @@ -874,6 +874,10 @@ while ($outer) --source $MYSQLTEST_VARDIR/tmp/sourced.inc --error ER_NO_SUCH_TABLE SELECT * from nowhere; + --disable_abort_on_error +# Statement giving a different error, to make sure we don't mask it + SELECT * FROM nowhere else; + --enable_abort_on_error } dec $outer; inc $ifval; From 1a6a540286e4a35e647a6802449d0e10baf2d90f Mon Sep 17 00:00:00 2001 From: Bjorn Munch Date: Wed, 3 Mar 2010 11:17:00 +0100 Subject: [PATCH 003/129] followup test fix after 49761 --- mysql-test/t/mysqltest.test | 11 ++++++++++- 1 file changed, 10 insertions(+), 1 deletion(-) diff --git a/mysql-test/t/mysqltest.test b/mysql-test/t/mysqltest.test index b2d7c59a8a0..0c31af8b641 100644 --- a/mysql-test/t/mysqltest.test +++ b/mysql-test/t/mysqltest.test @@ -1728,7 +1728,16 @@ select 1; --reap EOF --error 1 ---exec $MYSQL_TEST < $MYSQLTEST_VARDIR/tmp/mysqltest.in 2>&1 +# Must filter unpredictable extra warning from output +--exec $MYSQL_TEST < $MYSQLTEST_VARDIR/tmp/mysqltest.in > $MYSQL_TMP_DIR/mysqltest.out 2>&1 +--perl + my $dir= $ENV{'MYSQL_TMP_DIR'}; + open (FILE, "$dir/mysqltest.out"); + while () { + print unless /Note: net_clear/; # This shows up on rare occations + } +EOF +remove_file $MYSQL_TMP_DIR/mysqltest.out; remove_file $MYSQLTEST_VARDIR/tmp/mysqltest.in; drop table t1; From 27326d2c11d5557ac9f0472ae0522e5ed510069a Mon Sep 17 00:00:00 2001 From: Bjorn Munch Date: Thu, 4 Mar 2010 11:09:09 +0100 Subject: [PATCH 004/129] Bug #45482 MTR2: --default-storage-engine=csv is rejected by mtr Added csv to list of builtin engines Fixed dysfunctional part of csv.test so it actuallu used csv --- mysql-test/lib/mtr_cases.pm | 2 +- mysql-test/r/csv.result | 43 ++++++++++++++++++------------------- mysql-test/t/csv.test | 15 ++++++------- 3 files changed, 29 insertions(+), 31 deletions(-) diff --git a/mysql-test/lib/mtr_cases.pm b/mysql-test/lib/mtr_cases.pm index 1b6896e5a80..a596dfceab5 100644 --- a/mysql-test/lib/mtr_cases.pm +++ b/mysql-test/lib/mtr_cases.pm @@ -648,7 +648,7 @@ sub optimize_cases { # Check that engine selected by # --default-storage-engine= is supported # ======================================================= - my %builtin_engines = ('myisam' => 1, 'memory' => 1); + my %builtin_engines = ('myisam' => 1, 'memory' => 1, 'csv' => 1); foreach my $opt ( @{$tinfo->{master_opt}} ) { my $default_engine= diff --git a/mysql-test/r/csv.result b/mysql-test/r/csv.result index 4b96f5a5ed0..7418cd3a564 100644 --- a/mysql-test/r/csv.result +++ b/mysql-test/r/csv.result @@ -5138,7 +5138,7 @@ insert t1 values (1),(2),(3),(4),(5); truncate table t1; affected rows: 0 drop table t1; -create table t1 (v varchar(32) not null); +create table t1 (v varchar(32) not null) engine=csv; insert into t1 values ('def'),('abc'),('hij'),('3r4f'); select * from t1; v @@ -5146,14 +5146,14 @@ def abc hij 3r4f -alter table t1 change v v2 varchar(32); +alter table t1 change v v2 varchar(32) not null; select * from t1; v2 def abc hij 3r4f -alter table t1 change v2 v varchar(64); +alter table t1 change v2 v varchar(64) not null; select * from t1; v def @@ -5163,35 +5163,34 @@ hij update t1 set v = 'lmn' where v = 'hij'; select * from t1; v +lmn def abc -lmn 3r4f -alter table t1 add i int auto_increment not null primary key first; +alter table t1 add i int not null first; select * from t1; i v -1 def -2 abc -3 lmn -4 3r4f -update t1 set i=5 where i=3; +0 lmn +0 def +0 abc +0 3r4f +update t1 set i=3 where v = 'abc'; select * from t1; i v -1 def -2 abc -5 lmn -4 3r4f -alter table t1 change i i bigint; +3 abc +0 lmn +0 def +0 3r4f +alter table t1 change i i bigint not null; select * from t1; i v -1 def -2 abc -5 lmn -4 3r4f -alter table t1 add unique key (i, v); -select * from t1 where i between 2 and 4 and v in ('def','3r4f','lmn'); +3 abc +0 lmn +0 def +0 3r4f +select * from t1 where i between 2 and 4 and v in ('def','3r4f','abc'); i v -4 3r4f +3 abc drop table t1; create table bug15205 (val int(11) not null) engine=csv; create table bug15205_2 (val int(11) not null) engine=csv; diff --git a/mysql-test/t/csv.test b/mysql-test/t/csv.test index cdf274190dd..cf6d5b6d4c1 100644 --- a/mysql-test/t/csv.test +++ b/mysql-test/t/csv.test @@ -1553,26 +1553,25 @@ drop table t1; # whole alter table code is being tested all around the test suite already. # -create table t1 (v varchar(32) not null); +create table t1 (v varchar(32) not null) engine=csv; insert into t1 values ('def'),('abc'),('hij'),('3r4f'); select * from t1; # Fast alter, no copy performed -alter table t1 change v v2 varchar(32); +alter table t1 change v v2 varchar(32) not null; select * from t1; # Fast alter, no copy performed -alter table t1 change v2 v varchar(64); +alter table t1 change v2 v varchar(64) not null; select * from t1; update t1 set v = 'lmn' where v = 'hij'; select * from t1; # Regular alter table -alter table t1 add i int auto_increment not null primary key first; +alter table t1 add i int not null first; select * from t1; -update t1 set i=5 where i=3; +update t1 set i=3 where v = 'abc'; select * from t1; -alter table t1 change i i bigint; +alter table t1 change i i bigint not null; select * from t1; -alter table t1 add unique key (i, v); -select * from t1 where i between 2 and 4 and v in ('def','3r4f','lmn'); +select * from t1 where i between 2 and 4 and v in ('def','3r4f','abc'); drop table t1; # From eb235387ae623507ca8a3549b3c433b47ad357d3 Mon Sep 17 00:00:00 2001 From: Bjorn Munch Date: Tue, 16 Mar 2010 10:45:32 +0100 Subject: [PATCH 005/129] Bug #51767 Implement --start-and-exit also for MTR v2 Added option and logic, bypass safe_process Adapted after review comments --- mysql-test/lib/My/SafeProcess.pm | 15 ++++++++++++++- mysql-test/mysql-test-run.pl | 30 +++++++++++++++++++++++++++++- 2 files changed, 43 insertions(+), 2 deletions(-) diff --git a/mysql-test/lib/My/SafeProcess.pm b/mysql-test/lib/My/SafeProcess.pm index bfcad910a16..a4ae988ed9e 100644 --- a/mysql-test/lib/My/SafeProcess.pm +++ b/mysql-test/lib/My/SafeProcess.pm @@ -60,11 +60,12 @@ use My::Platform; my %running; my $_verbose= 0; +my $start_exit= 0; END { # Kill any children still running for my $proc (values %running){ - if ( $proc->is_child($$) ){ + if ( $proc->is_child($$) and ! $start_exit){ #print "Killing: $proc\n"; if ($proc->wait_one(0)){ $proc->kill(); @@ -149,6 +150,11 @@ sub new { push(@safe_args, "--"); push(@safe_args, $path); # The program safe_process should execute + + if ($start_exit) { # Bypass safe_process instead, start program directly + @safe_args= (); + $safe_path= $path; + } push(@safe_args, @$$args); print "### safe_path: ", $safe_path, " ", join(" ", @safe_args), "\n" @@ -528,6 +534,13 @@ sub wait_all { } } +# +# Set global flag to tell all safe_process to exit after starting child +# + +sub start_exit { + $start_exit= 1; +} # # Check if any process has exited, but don't wait. diff --git a/mysql-test/mysql-test-run.pl b/mysql-test/mysql-test-run.pl index a35741bebda..91ae508422f 100755 --- a/mysql-test/mysql-test-run.pl +++ b/mysql-test/mysql-test-run.pl @@ -218,6 +218,7 @@ sub check_timeout { return $opt_testcase_timeout * 6; }; my $opt_start; my $opt_start_dirty; +my $opt_start_exit; my $start_only; my $opt_wait_all; my $opt_repeat= 1; @@ -345,6 +346,12 @@ sub main { mtr_report("Using parallel: $opt_parallel"); } + if ($opt_parallel > 1 && $opt_start_exit) { + mtr_warning("Parallel and --start-and-exit cannot be combined\n" . + "Setting parallel to 1"); + $opt_parallel= 1; + } + # Create server socket on any free port my $server = new IO::Socket::INET ( @@ -384,6 +391,8 @@ sub main { my $completed= run_test_server($server, $tests, $opt_parallel); + exit(0) if $opt_start_exit; + # Send Ctrl-C to any children still running kill("INT", keys(%children)); @@ -910,6 +919,7 @@ sub command_line_setup { 'verbose-restart' => \&report_option, 'sleep=i' => \$opt_sleep, 'start-dirty' => \$opt_start_dirty, + 'start-and-exit' => \$opt_start_exit, 'start' => \$opt_start, 'wait-all' => \$opt_wait_all, 'print-testcases' => \&collect_option, @@ -1316,7 +1326,7 @@ sub command_line_setup { # -------------------------------------------------------------------------- # Modified behavior with --start options # -------------------------------------------------------------------------- - if ($opt_start or $opt_start_dirty) { + if ($opt_start or $opt_start_dirty or $opt_start_exit) { collect_option ('quick-collect', 1); $start_only= 1; } @@ -3400,6 +3410,18 @@ sub run_testcase ($) { mtr_print ($mysqld->name() . " " . $mysqld->value('port') . " " . $mysqld->value('socket')); } + if ( $opt_start_exit ) + { + mtr_print("Server(s) started, not waiting for them to finish"); + if (IS_WINDOWS) + { + POSIX::_exit(0); # exit hangs here in ActiveState Perl + } + else + { + exit(0); + } + } mtr_print("Waiting for server(s) to exit..."); if ( $opt_wait_all ) { My::SafeProcess->wait_all(); @@ -4644,6 +4666,12 @@ sub stop_servers($$) { sub start_servers($) { my ($tinfo)= @_; + # Make sure the safe_process also exits from now on + # Could not be done before, as we don't want this for the bootstrap + if ($opt_start_exit) { + My::SafeProcess->start_exit(); + } + # Start clusters foreach my $cluster ( clusters() ) { From ddb6a95abdd2578b39a3fdff907e714baa1b81e2 Mon Sep 17 00:00:00 2001 From: Bjorn Munch Date: Wed, 17 Mar 2010 15:25:55 +0100 Subject: [PATCH 006/129] Bug #43588 mysqltest command disable_abort_on_error logs connect commands Only log connects after --error A few small test adjustments needed/possible --- client/mysqltest.cc | 2 +- mysql-test/r/mysqltest.result | 1 - mysql-test/t/innodb_mysql.test | 4 ---- mysql-test/t/mysqltest.test | 1 - 4 files changed, 1 insertion(+), 7 deletions(-) diff --git a/client/mysqltest.cc b/client/mysqltest.cc index 64cf06736a0..18af4088e68 100644 --- a/client/mysqltest.cc +++ b/client/mysqltest.cc @@ -4920,7 +4920,7 @@ int connect_n_handle_errors(struct st_command *command, ds= &ds_res; /* Only log if an error is expected */ - if (!command->abort_on_error && + if (command->expected_errors.count > 0 && !disable_query_log) { /* diff --git a/mysql-test/r/mysqltest.result b/mysql-test/r/mysqltest.result index 38112c032b5..de7a3eefb6a 100644 --- a/mysql-test/r/mysqltest.result +++ b/mysql-test/r/mysqltest.result @@ -447,7 +447,6 @@ OK mysqltest: The test didn't produce any output mysqltest: In included file "MYSQLTEST_VARDIR/tmp/mysqltest.sql": At line 3: connection 'test_con1' not found in connection pool mysqltest: In included file "MYSQLTEST_VARDIR/tmp/mysqltest.sql": At line 2: Connection test_con1 already exists -connect(localhost,root,,test,MASTER_PORT,MASTER_SOCKET); show tables; ERROR 3D000: No database selected Output from mysqltest-x.inc diff --git a/mysql-test/t/innodb_mysql.test b/mysql-test/t/innodb_mysql.test index a3c11b8b8d6..9d68d01b79c 100644 --- a/mysql-test/t/innodb_mysql.test +++ b/mysql-test/t/innodb_mysql.test @@ -500,11 +500,7 @@ INSERT INTO t2 VALUES (),(); CREATE OR REPLACE VIEW v1 AS SELECT 1 FROM t2 WHERE b =(SELECT a FROM t1 LIMIT 1); ---disable_query_log ---disable_result_log CONNECT (con1, localhost, root,,); ---enable_query_log ---enable_result_log CONNECTION default; DELIMITER |; diff --git a/mysql-test/t/mysqltest.test b/mysql-test/t/mysqltest.test index 0c31af8b641..649a5fce366 100644 --- a/mysql-test/t/mysqltest.test +++ b/mysql-test/t/mysqltest.test @@ -1441,7 +1441,6 @@ EOF remove_file $MYSQLTEST_VARDIR/tmp/mysqltest.sql; # connect when "disable_abort_on_error" caused "connection not found" ---replace_result $MASTER_MYSOCK MASTER_SOCKET $MASTER_MYPORT MASTER_PORT --disable_abort_on_error connect (con1,localhost,root,,); connection default; From 9d313a5e2483c00b53c4c96f315fa786b66a1ae7 Mon Sep 17 00:00:00 2001 From: Bjorn Munch Date: Fri, 19 Mar 2010 09:56:26 +0100 Subject: [PATCH 007/129] Fixed many funcs_1 tests after 43588 --- .../funcs_1/r/innodb_storedproc_06.result | 11 ----------- .../funcs_1/r/innodb_storedproc_10.result | 4 ---- .../suite/funcs_1/r/innodb_trig_03.result | 19 ------------------- .../suite/funcs_1/r/innodb_trig_03e.result | 16 ---------------- .../suite/funcs_1/r/innodb_trig_0407.result | 2 -- .../suite/funcs_1/r/innodb_trig_08.result | 2 -- .../funcs_1/r/memory_storedproc_06.result | 11 ----------- .../funcs_1/r/memory_storedproc_10.result | 4 ---- .../suite/funcs_1/r/memory_trig_03.result | 19 ------------------- .../suite/funcs_1/r/memory_trig_03e.result | 15 --------------- .../suite/funcs_1/r/memory_trig_0407.result | 2 -- .../suite/funcs_1/r/memory_trig_08.result | 2 -- .../funcs_1/r/myisam_storedproc_06.result | 11 ----------- .../funcs_1/r/myisam_storedproc_10.result | 4 ---- .../suite/funcs_1/r/myisam_trig_03.result | 19 ------------------- .../suite/funcs_1/r/myisam_trig_03e.result | 15 --------------- .../suite/funcs_1/r/myisam_trig_0407.result | 2 -- .../suite/funcs_1/r/myisam_trig_08.result | 2 -- mysql-test/suite/funcs_1/r/ndb_trig_03.result | 19 ------------------- .../suite/funcs_1/r/ndb_trig_03e.result | 16 ---------------- .../suite/funcs_1/r/ndb_trig_0407.result | 2 -- mysql-test/suite/funcs_1/r/ndb_trig_08.result | 2 -- mysql-test/suite/funcs_1/r/storedproc.result | 1 - .../funcs_1/storedproc/storedproc_06.inc | 11 ----------- .../funcs_1/storedproc/storedproc_10.inc | 4 ---- .../suite/funcs_1/triggers/triggers_03.inc | 19 ------------------- .../funcs_1/triggers/triggers_03e_columns.inc | 2 -- .../triggers/triggers_03e_db_level.inc | 2 -- .../triggers/triggers_03e_db_table_mix.inc | 2 -- .../funcs_1/triggers/triggers_03e_definer.inc | 1 - .../triggers/triggers_03e_global_db_mix.inc | 4 ---- .../funcs_1/triggers/triggers_03e_prepare.inc | 2 -- .../triggers/triggers_03e_table_level.inc | 2 -- .../triggers/triggers_03e_transaction.inc | 1 - .../suite/funcs_1/triggers/triggers_0407.inc | 2 -- .../suite/funcs_1/triggers/triggers_08.inc | 2 -- 36 files changed, 254 deletions(-) diff --git a/mysql-test/suite/funcs_1/r/innodb_storedproc_06.result b/mysql-test/suite/funcs_1/r/innodb_storedproc_06.result index 67d9c76ccac..ee1548fe012 100644 --- a/mysql-test/suite/funcs_1/r/innodb_storedproc_06.result +++ b/mysql-test/suite/funcs_1/r/innodb_storedproc_06.result @@ -78,7 +78,6 @@ grant all on db_storedproc_1.* to 'user_1'@'localhost'; revoke create routine on db_storedproc_1.* from 'user_1'@'localhost'; flush privileges; DROP PROCEDURE IF EXISTS sp1; -connect(localhost,user_1,,db_storedproc_1,MYSQL_PORT,MYSQL_SOCK); user_1@localhost db_storedproc_1 USE db_storedproc_1; @@ -91,7 +90,6 @@ USE db_storedproc_1; root@localhost db_storedproc_1 GRANT CREATE ROUTINE ON db_storedproc_1.* TO 'user_1'@'localhost'; -connect(localhost,user_1,,db_storedproc_1,MYSQL_PORT,MYSQL_SOCK); user_1@localhost db_storedproc_1 USE db_storedproc_1; @@ -112,7 +110,6 @@ Ensure that root always has the GRANT CREATE ROUTINE privilege. -------------------------------------------------------------------------------- grant create routine on db_storedproc_1.* to 'user_1'@'localhost'; flush privileges; -connect(localhost,user_1,,db_storedproc_1,MYSQL_PORT,MYSQL_SOCK); user_1@localhost db_storedproc_1 DROP PROCEDURE IF EXISTS sp3; @@ -149,7 +146,6 @@ CREATE PROCEDURE sp4(v1 char(20)) BEGIN SELECT * from db_storedproc_1.t6 where t6.f2= 'xyz'; END// -connect(localhost,user_1,,db_storedproc_1,MYSQL_PORT,MYSQL_SOCK); user_1@localhost db_storedproc_1 USE db_storedproc_1; @@ -191,7 +187,6 @@ grant create routine on db_storedproc_1.* to 'user_1'@'localhost'; grant SELECT on db_storedproc_1.* to 'user_2'@'localhost'; grant execute on db_storedproc_1.* to 'user_2'@'localhost'; flush privileges; -connect(localhost,user_1,,db_storedproc_1,MYSQL_PORT,MYSQL_SOCK); user_1@localhost db_storedproc_1 CREATE PROCEDURE sp5_s_i () sql security definer @@ -207,7 +202,6 @@ CREATE PROCEDURE sp5_ins () sql security definer BEGIN insert into db_storedproc_1.t3165 values ('inserted', 'from sp5_ins', 1000); END// -connect(localhost,user_2,,db_storedproc_1,MYSQL_PORT,MYSQL_SOCK); user_2@localhost db_storedproc_1 CALL sp5_s_i(); @@ -305,7 +299,6 @@ GRANT CREATE ROUTINE ON db_storedproc_1.* TO 'user_1'@'localhost'; GRANT SELECT ON db_storedproc_1.* TO 'user_2'@'localhost'; GRANT EXECUTE ON db_storedproc_1.* TO 'user_2'@'localhost'; FLUSH PRIVILEGES; -connect(localhost,user_1,,db_storedproc_1,MYSQL_PORT,MYSQL_SOCK); user_1@localhost db_storedproc_1 CREATE PROCEDURE sp3166_s_i () SQL SECURITY INVOKER @@ -321,7 +314,6 @@ CREATE PROCEDURE sp3166_ins () SQL SECURITY INVOKER BEGIN insert into db_storedproc_1.t3166 values ('inserted from sp3166_ins'); END// -connect(localhost,user_2,,db_storedproc_1,MYSQL_PORT,MYSQL_SOCK); user_2@localhost db_storedproc_1 CALL sp3166_s_i(); @@ -340,7 +332,6 @@ c1 inserted outside SP GRANT INSERT ON db_storedproc_1.* TO 'user_2'@'localhost'; FLUSH PRIVILEGES; -connect(localhost,user_2,,db_storedproc_1,MYSQL_PORT,MYSQL_SOCK); user_2@localhost db_storedproc_1 CALL sp3166_s_i(); @@ -361,7 +352,6 @@ inserted from sp3166_s_i inserted from sp3166_ins REVOKE SELECT ON db_storedproc_1.* FROM 'user_2'@'localhost'; FLUSH PRIVILEGES; -connect(localhost,user_2,,db_storedproc_1,MYSQL_PORT,MYSQL_SOCK); user_2@localhost db_storedproc_1 CALL sp3166_s_i(); @@ -379,7 +369,6 @@ inserted from sp3166_ins root@localhost db_storedproc_1 REVOKE EXECUTE on db_storedproc_1.* FROM 'user_2'@'localhost'; FLUSH PRIVILEGES; -connect(localhost,user_2,,db_storedproc_1,MYSQL_PORT,MYSQL_SOCK); user_2@localhost db_storedproc_1 CALL sp3166_s_i(); diff --git a/mysql-test/suite/funcs_1/r/innodb_storedproc_10.result b/mysql-test/suite/funcs_1/r/innodb_storedproc_10.result index 24ebd38e403..6591a138d73 100644 --- a/mysql-test/suite/funcs_1/r/innodb_storedproc_10.result +++ b/mysql-test/suite/funcs_1/r/innodb_storedproc_10.result @@ -81,7 +81,6 @@ create user 'user_2'@'localhost'; GRANT CREATE ROUTINE ON db_storedproc.* TO 'user_1'@'localhost'; GRANT SELECT ON db_storedproc.* TO 'user_2'@'localhost'; FLUSH PRIVILEGES; -connect(localhost,user_1,,db_storedproc,MYSQL_PORT,MYSQL_SOCK); user_1@localhost db_storedproc CREATE PROCEDURE sp31102 () SQL SECURITY INVOKER @@ -94,7 +93,6 @@ DECLARE res INT; SET res = n * n; RETURN res; END// -connect(localhost,user_2,,db_storedproc,MYSQL_PORT,MYSQL_SOCK); user_2@localhost db_storedproc CALL sp31102(); @@ -113,7 +111,6 @@ fn31105( 9 ) 81 GRANT EXECUTE ON db_storedproc.* TO 'user_2'@'localhost'; FLUSH PRIVILEGES; -connect(localhost,user_2,,db_storedproc,MYSQL_PORT,MYSQL_SOCK); user_2@localhost db_storedproc CALL sp31102(); @@ -134,7 +131,6 @@ a` a` 1000-01-01 -5000 a` -5000 SELECT fn31105( 9 ); fn31105( 9 ) 81 -connect(localhost,user_2,,db_storedproc,MYSQL_PORT,MYSQL_SOCK); user_2@localhost db_storedproc CALL sp31102(); diff --git a/mysql-test/suite/funcs_1/r/innodb_trig_03.result b/mysql-test/suite/funcs_1/r/innodb_trig_03.result index b02fba0f38d..a7fce94c91d 100644 --- a/mysql-test/suite/funcs_1/r/innodb_trig_03.result +++ b/mysql-test/suite/funcs_1/r/innodb_trig_03.result @@ -85,8 +85,6 @@ show grants for test_yesprivs@localhost; Grants for test_yesprivs@localhost GRANT TRIGGER ON *.* TO 'test_yesprivs'@'localhost' IDENTIFIED BY PASSWORD '*C49735D016A099C0CF104EF9183F374A54CA2576' GRANT SELECT ON `priv_db`.`t1` TO 'test_yesprivs'@'localhost' -connect(localhost,test_noprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); -connect(localhost,test_yesprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); Testcase 3.5.3.2: ----------------- @@ -161,8 +159,6 @@ grant TRIGGER, UPDATE on *.* to test_yesprivs@localhost; show grants for test_yesprivs@localhost; Grants for test_yesprivs@localhost GRANT UPDATE, TRIGGER ON *.* TO 'test_yesprivs'@'localhost' IDENTIFIED BY PASSWORD '*C49735D016A099C0CF104EF9183F374A54CA2576' -connect(localhost,test_noprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); -connect(localhost,test_yesprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); select current_user; current_user test_noprivs@localhost @@ -222,8 +218,6 @@ show grants for test_yesprivs@localhost; Grants for test_yesprivs@localhost GRANT TRIGGER ON *.* TO 'test_yesprivs'@'localhost' IDENTIFIED BY PASSWORD '*C49735D016A099C0CF104EF9183F374A54CA2576' GRANT UPDATE ON `priv_db`.* TO 'test_yesprivs'@'localhost' -connect(localhost,test_noprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); -connect(localhost,test_yesprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); show grants; Grants for test_noprivs@localhost GRANT USAGE ON *.* TO 'test_noprivs'@'localhost' IDENTIFIED BY PASSWORD '*C49735D016A099C0CF104EF9183F374A54CA2576' @@ -296,8 +290,6 @@ show grants for test_yesprivs@localhost; Grants for test_yesprivs@localhost GRANT TRIGGER ON *.* TO 'test_yesprivs'@'localhost' IDENTIFIED BY PASSWORD '*C49735D016A099C0CF104EF9183F374A54CA2576' GRANT UPDATE ON `priv_db`.`t1` TO 'test_yesprivs'@'localhost' -connect(localhost,test_noprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); -connect(localhost,test_yesprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); show grants; Grants for test_noprivs@localhost GRANT TRIGGER ON *.* TO 'test_noprivs'@'localhost' IDENTIFIED BY PASSWORD '*C49735D016A099C0CF104EF9183F374A54CA2576' @@ -351,8 +343,6 @@ grant UPDATE (f1) on priv_db.t1 to test_yesprivs@localhost; show grants for test_noprivs; Grants for test_noprivs@% GRANT TRIGGER ON *.* TO 'test_noprivs'@'%' -connect(localhost,test_noprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); -connect(localhost,test_yesprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); show grants; Grants for test_noprivs@localhost GRANT TRIGGER ON *.* TO 'test_noprivs'@'localhost' IDENTIFIED BY PASSWORD '*C49735D016A099C0CF104EF9183F374A54CA2576' @@ -407,8 +397,6 @@ grant TRIGGER, SELECT on *.* to test_yesprivs@localhost; show grants for test_yesprivs@localhost; Grants for test_yesprivs@localhost GRANT SELECT, TRIGGER ON *.* TO 'test_yesprivs'@'localhost' IDENTIFIED BY PASSWORD '*C49735D016A099C0CF104EF9183F374A54CA2576' -connect(localhost,test_noprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); -connect(localhost,test_yesprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); select current_user; current_user test_noprivs@localhost @@ -464,8 +452,6 @@ show grants for test_yesprivs@localhost; Grants for test_yesprivs@localhost GRANT TRIGGER ON *.* TO 'test_yesprivs'@'localhost' IDENTIFIED BY PASSWORD '*C49735D016A099C0CF104EF9183F374A54CA2576' GRANT SELECT ON `priv_db`.* TO 'test_yesprivs'@'localhost' -connect(localhost,test_noprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); -connect(localhost,test_yesprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); show grants; Grants for test_noprivs@localhost GRANT TRIGGER ON *.* TO 'test_noprivs'@'localhost' IDENTIFIED BY PASSWORD '*C49735D016A099C0CF104EF9183F374A54CA2576' @@ -519,8 +505,6 @@ show grants for test_yesprivs@localhost; Grants for test_yesprivs@localhost GRANT TRIGGER ON *.* TO 'test_yesprivs'@'localhost' IDENTIFIED BY PASSWORD '*C49735D016A099C0CF104EF9183F374A54CA2576' GRANT SELECT ON `priv_db`.`t1` TO 'test_yesprivs'@'localhost' -connect(localhost,test_noprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); -connect(localhost,test_yesprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); show grants; Grants for test_noprivs@localhost GRANT TRIGGER ON *.* TO 'test_noprivs'@'localhost' IDENTIFIED BY PASSWORD '*C49735D016A099C0CF104EF9183F374A54CA2576' @@ -565,8 +549,6 @@ show grants for test_noprivs@localhost; Grants for test_noprivs@localhost GRANT TRIGGER ON *.* TO 'test_noprivs'@'localhost' IDENTIFIED BY PASSWORD '*C49735D016A099C0CF104EF9183F374A54CA2576' GRANT INSERT (f1), UPDATE (f1) ON `priv_db`.`t1` TO 'test_noprivs'@'localhost' -connect(localhost,test_noprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); -connect(localhost,test_yesprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); show grants; Grants for test_noprivs@localhost GRANT TRIGGER ON *.* TO 'test_noprivs'@'localhost' IDENTIFIED BY PASSWORD '*C49735D016A099C0CF104EF9183F374A54CA2576' @@ -611,7 +593,6 @@ Grants for test_yesprivs@localhost GRANT TRIGGER ON *.* TO 'test_yesprivs'@'localhost' IDENTIFIED BY PASSWORD '*C49735D016A099C0CF104EF9183F374A54CA2576' GRANT SELECT ON `priv_db`.`t2` TO 'test_yesprivs'@'localhost' GRANT SELECT, UPDATE ON `priv_db`.`t1` TO 'test_yesprivs'@'localhost' -connect(localhost,test_yesprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); select current_user; current_user test_yesprivs@localhost diff --git a/mysql-test/suite/funcs_1/r/innodb_trig_03e.result b/mysql-test/suite/funcs_1/r/innodb_trig_03e.result index 476ccc6ebd8..5b760116801 100644 --- a/mysql-test/suite/funcs_1/r/innodb_trig_03e.result +++ b/mysql-test/suite/funcs_1/r/innodb_trig_03e.result @@ -24,7 +24,6 @@ show grants for test_noprivs@localhost; Grants for test_noprivs@localhost GRANT USAGE ON *.* TO 'test_noprivs'@'localhost' IDENTIFIED BY PASSWORD '*C49735D016A099C0CF104EF9183F374A54CA2576' GRANT SELECT, INSERT ON `priv_db`.* TO 'test_noprivs'@'localhost' -connect(localhost,test_yesprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); no trigger privilege on db level for create: -------------------------------------------- @@ -32,7 +31,6 @@ use priv_db; create trigger trg1_1 before INSERT on t1 for each row set new.f1 = 'trig 1_1-no'; ERROR 42000: TRIGGER command denied to user 'test_yesprivs'@'localhost' for table 't1' -connect(localhost,test_noprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); use priv_db; insert into t1 (f1) values ('insert-yes'); select f1 from t1 order by f1; @@ -253,8 +251,6 @@ revoke ALL PRIVILEGES, GRANT OPTION FROM test_yesprivs@localhost; create User test_noprivs@localhost; set password for test_noprivs@localhost = password('PWD'); revoke ALL PRIVILEGES, GRANT OPTION FROM test_noprivs@localhost; -connect(localhost,test_yesprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); -connect(localhost,test_noprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); no trigger privilege on table level for create: ----------------------------------------------- @@ -513,8 +509,6 @@ grant SELECT,INSERT on *.* to test_noprivs@localhost; show grants for test_noprivs@localhost; Grants for test_noprivs@localhost GRANT SELECT, INSERT ON *.* TO 'test_noprivs'@'localhost' IDENTIFIED BY PASSWORD '*C49735D016A099C0CF104EF9183F374A54CA2576' -connect(localhost,test_yesprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); -connect(localhost,test_noprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); select current_user; current_user test_yesprivs@localhost @@ -563,7 +557,6 @@ revoke TRIGGER on *.* from test_yesprivs@localhost; show grants for test_yesprivs@localhost; Grants for test_yesprivs@localhost GRANT SELECT, INSERT, UPDATE, DELETE, CREATE, DROP, RELOAD, SHUTDOWN, PROCESS, FILE, REFERENCES, INDEX, ALTER, SHOW DATABASES, SUPER, CREATE TEMPORARY TABLES, LOCK TABLES, EXECUTE, REPLICATION SLAVE, REPLICATION CLIENT, CREATE VIEW, SHOW VIEW, CREATE ROUTINE, ALTER ROUTINE, CREATE USER, EVENT ON *.* TO 'test_yesprivs'@'localhost' IDENTIFIED BY PASSWORD '*C49735D016A099C0CF104EF9183F374A54CA2576' -connect(localhost,test_yesprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); select current_user; current_user test_yesprivs@localhost @@ -698,7 +691,6 @@ select f1 from t1 order by f1; f1 insert-yes insert-yes -connect(localhost,test_yesprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); select current_user; current_user test_yesprivs@localhost @@ -767,9 +759,7 @@ Grants for test_noprivs@localhost GRANT USAGE ON *.* TO 'test_noprivs'@'localhost' IDENTIFIED BY PASSWORD '*C49735D016A099C0CF104EF9183F374A54CA2576' GRANT SELECT, INSERT, UPDATE ON `priv1_db`.* TO 'test_noprivs'@'localhost' GRANT SELECT, INSERT ON `priv2_db`.* TO 'test_noprivs'@'localhost' -connect(localhost,test_yesprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); use priv1_db; -connect(localhost,test_noprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); use priv1_db; trigger privilege on one db1 db level, not on db2 @@ -982,7 +972,6 @@ create User test_useprivs@localhost; set password for test_useprivs@localhost = password('PWD'); revoke ALL PRIVILEGES, GRANT OPTION FROM test_yesprivs@localhost; revoke ALL PRIVILEGES, GRANT OPTION FROM test_useprivs@localhost; -connect(localhost,test_yesprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); select current_user; current_user root@localhost @@ -1010,7 +999,6 @@ select f1 from t1 order by f1; f1 trig 1_1-yes prepare ins1 from 'insert into t1 (f1) values (''insert2-no'')'; -connect(localhost,test_useprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); select current_user; current_user test_useprivs@localhost @@ -1206,7 +1194,6 @@ create table t1 (f1 char(20)) engine= innodb; create User test_yesprivs@localhost; set password for test_yesprivs@localhost = password('PWD'); revoke ALL PRIVILEGES, GRANT OPTION FROM test_yesprivs@localhost; -connect(localhost,test_yesprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); select current_user; current_user root@localhost @@ -1303,7 +1290,6 @@ create table t1 (f1 char(20)) engine= innodb; create User test_yesprivs@localhost; set password for test_yesprivs@localhost = password('PWD'); revoke ALL PRIVILEGES, GRANT OPTION FROM test_yesprivs@localhost; -connect(localhost,test_yesprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); select current_user; current_user root@localhost @@ -1375,8 +1361,6 @@ show grants for test_noprivs@localhost; Grants for test_noprivs@localhost GRANT USAGE ON *.* TO 'test_noprivs'@'localhost' IDENTIFIED BY PASSWORD '*C49735D016A099C0CF104EF9183F374A54CA2576' GRANT SELECT, UPDATE ON `priv_db`.* TO 'test_noprivs'@'localhost' -connect(localhost,test_yesprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); -connect(localhost,test_noprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); update only on column: ---------------------- diff --git a/mysql-test/suite/funcs_1/r/innodb_trig_0407.result b/mysql-test/suite/funcs_1/r/innodb_trig_0407.result index 33e58f50ec1..8597f252e54 100644 --- a/mysql-test/suite/funcs_1/r/innodb_trig_0407.result +++ b/mysql-test/suite/funcs_1/r/innodb_trig_0407.result @@ -67,8 +67,6 @@ revoke ALL PRIVILEGES, GRANT OPTION FROM test_general@localhost; create User test_super@localhost; set password for test_super@localhost = password('PWD'); grant ALL on *.* to test_super@localhost with grant OPTION; -connect(localhost,test_general,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); -connect(localhost,test_super,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); Testcase 3.5.4: --------------- diff --git a/mysql-test/suite/funcs_1/r/innodb_trig_08.result b/mysql-test/suite/funcs_1/r/innodb_trig_08.result index 6ced07cef73..b2b38694680 100644 --- a/mysql-test/suite/funcs_1/r/innodb_trig_08.result +++ b/mysql-test/suite/funcs_1/r/innodb_trig_08.result @@ -67,8 +67,6 @@ revoke ALL PRIVILEGES, GRANT OPTION FROM test_general@localhost; create User test_super@localhost; set password for test_super@localhost = password('PWD'); grant ALL on *.* to test_super@localhost with grant OPTION; -connect(localhost,test_general,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); -connect(localhost,test_super,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); Testcase 3.5.8.1: (implied in previous tests) --------------------------------------------- diff --git a/mysql-test/suite/funcs_1/r/memory_storedproc_06.result b/mysql-test/suite/funcs_1/r/memory_storedproc_06.result index eb617c68ae9..096cbd1261e 100644 --- a/mysql-test/suite/funcs_1/r/memory_storedproc_06.result +++ b/mysql-test/suite/funcs_1/r/memory_storedproc_06.result @@ -79,7 +79,6 @@ grant all on db_storedproc_1.* to 'user_1'@'localhost'; revoke create routine on db_storedproc_1.* from 'user_1'@'localhost'; flush privileges; DROP PROCEDURE IF EXISTS sp1; -connect(localhost,user_1,,db_storedproc_1,MYSQL_PORT,MYSQL_SOCK); user_1@localhost db_storedproc_1 USE db_storedproc_1; @@ -92,7 +91,6 @@ USE db_storedproc_1; root@localhost db_storedproc_1 GRANT CREATE ROUTINE ON db_storedproc_1.* TO 'user_1'@'localhost'; -connect(localhost,user_1,,db_storedproc_1,MYSQL_PORT,MYSQL_SOCK); user_1@localhost db_storedproc_1 USE db_storedproc_1; @@ -113,7 +111,6 @@ Ensure that root always has the GRANT CREATE ROUTINE privilege. -------------------------------------------------------------------------------- grant create routine on db_storedproc_1.* to 'user_1'@'localhost'; flush privileges; -connect(localhost,user_1,,db_storedproc_1,MYSQL_PORT,MYSQL_SOCK); user_1@localhost db_storedproc_1 DROP PROCEDURE IF EXISTS sp3; @@ -150,7 +147,6 @@ CREATE PROCEDURE sp4(v1 char(20)) BEGIN SELECT * from db_storedproc_1.t6 where t6.f2= 'xyz'; END// -connect(localhost,user_1,,db_storedproc_1,MYSQL_PORT,MYSQL_SOCK); user_1@localhost db_storedproc_1 USE db_storedproc_1; @@ -192,7 +188,6 @@ grant create routine on db_storedproc_1.* to 'user_1'@'localhost'; grant SELECT on db_storedproc_1.* to 'user_2'@'localhost'; grant execute on db_storedproc_1.* to 'user_2'@'localhost'; flush privileges; -connect(localhost,user_1,,db_storedproc_1,MYSQL_PORT,MYSQL_SOCK); user_1@localhost db_storedproc_1 CREATE PROCEDURE sp5_s_i () sql security definer @@ -208,7 +203,6 @@ CREATE PROCEDURE sp5_ins () sql security definer BEGIN insert into db_storedproc_1.t3165 values ('inserted', 'from sp5_ins', 1000); END// -connect(localhost,user_2,,db_storedproc_1,MYSQL_PORT,MYSQL_SOCK); user_2@localhost db_storedproc_1 CALL sp5_s_i(); @@ -306,7 +300,6 @@ GRANT CREATE ROUTINE ON db_storedproc_1.* TO 'user_1'@'localhost'; GRANT SELECT ON db_storedproc_1.* TO 'user_2'@'localhost'; GRANT EXECUTE ON db_storedproc_1.* TO 'user_2'@'localhost'; FLUSH PRIVILEGES; -connect(localhost,user_1,,db_storedproc_1,MYSQL_PORT,MYSQL_SOCK); user_1@localhost db_storedproc_1 CREATE PROCEDURE sp3166_s_i () SQL SECURITY INVOKER @@ -322,7 +315,6 @@ CREATE PROCEDURE sp3166_ins () SQL SECURITY INVOKER BEGIN insert into db_storedproc_1.t3166 values ('inserted from sp3166_ins'); END// -connect(localhost,user_2,,db_storedproc_1,MYSQL_PORT,MYSQL_SOCK); user_2@localhost db_storedproc_1 CALL sp3166_s_i(); @@ -341,7 +333,6 @@ c1 inserted outside SP GRANT INSERT ON db_storedproc_1.* TO 'user_2'@'localhost'; FLUSH PRIVILEGES; -connect(localhost,user_2,,db_storedproc_1,MYSQL_PORT,MYSQL_SOCK); user_2@localhost db_storedproc_1 CALL sp3166_s_i(); @@ -362,7 +353,6 @@ inserted from sp3166_s_i inserted from sp3166_ins REVOKE SELECT ON db_storedproc_1.* FROM 'user_2'@'localhost'; FLUSH PRIVILEGES; -connect(localhost,user_2,,db_storedproc_1,MYSQL_PORT,MYSQL_SOCK); user_2@localhost db_storedproc_1 CALL sp3166_s_i(); @@ -380,7 +370,6 @@ inserted from sp3166_ins root@localhost db_storedproc_1 REVOKE EXECUTE on db_storedproc_1.* FROM 'user_2'@'localhost'; FLUSH PRIVILEGES; -connect(localhost,user_2,,db_storedproc_1,MYSQL_PORT,MYSQL_SOCK); user_2@localhost db_storedproc_1 CALL sp3166_s_i(); diff --git a/mysql-test/suite/funcs_1/r/memory_storedproc_10.result b/mysql-test/suite/funcs_1/r/memory_storedproc_10.result index f5e34b0063c..4a932ee826b 100644 --- a/mysql-test/suite/funcs_1/r/memory_storedproc_10.result +++ b/mysql-test/suite/funcs_1/r/memory_storedproc_10.result @@ -82,7 +82,6 @@ create user 'user_2'@'localhost'; GRANT CREATE ROUTINE ON db_storedproc.* TO 'user_1'@'localhost'; GRANT SELECT ON db_storedproc.* TO 'user_2'@'localhost'; FLUSH PRIVILEGES; -connect(localhost,user_1,,db_storedproc,MYSQL_PORT,MYSQL_SOCK); user_1@localhost db_storedproc CREATE PROCEDURE sp31102 () SQL SECURITY INVOKER @@ -95,7 +94,6 @@ DECLARE res INT; SET res = n * n; RETURN res; END// -connect(localhost,user_2,,db_storedproc,MYSQL_PORT,MYSQL_SOCK); user_2@localhost db_storedproc CALL sp31102(); @@ -114,7 +112,6 @@ fn31105( 9 ) 81 GRANT EXECUTE ON db_storedproc.* TO 'user_2'@'localhost'; FLUSH PRIVILEGES; -connect(localhost,user_2,,db_storedproc,MYSQL_PORT,MYSQL_SOCK); user_2@localhost db_storedproc CALL sp31102(); @@ -135,7 +132,6 @@ a` a` 1000-01-01 -5000 a` -5000 SELECT fn31105( 9 ); fn31105( 9 ) 81 -connect(localhost,user_2,,db_storedproc,MYSQL_PORT,MYSQL_SOCK); user_2@localhost db_storedproc CALL sp31102(); diff --git a/mysql-test/suite/funcs_1/r/memory_trig_03.result b/mysql-test/suite/funcs_1/r/memory_trig_03.result index 7f38fd1f182..0d622915dca 100644 --- a/mysql-test/suite/funcs_1/r/memory_trig_03.result +++ b/mysql-test/suite/funcs_1/r/memory_trig_03.result @@ -86,8 +86,6 @@ show grants for test_yesprivs@localhost; Grants for test_yesprivs@localhost GRANT TRIGGER ON *.* TO 'test_yesprivs'@'localhost' IDENTIFIED BY PASSWORD '*C49735D016A099C0CF104EF9183F374A54CA2576' GRANT SELECT ON `priv_db`.`t1` TO 'test_yesprivs'@'localhost' -connect(localhost,test_noprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); -connect(localhost,test_yesprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); Testcase 3.5.3.2: ----------------- @@ -162,8 +160,6 @@ grant TRIGGER, UPDATE on *.* to test_yesprivs@localhost; show grants for test_yesprivs@localhost; Grants for test_yesprivs@localhost GRANT UPDATE, TRIGGER ON *.* TO 'test_yesprivs'@'localhost' IDENTIFIED BY PASSWORD '*C49735D016A099C0CF104EF9183F374A54CA2576' -connect(localhost,test_noprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); -connect(localhost,test_yesprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); select current_user; current_user test_noprivs@localhost @@ -223,8 +219,6 @@ show grants for test_yesprivs@localhost; Grants for test_yesprivs@localhost GRANT TRIGGER ON *.* TO 'test_yesprivs'@'localhost' IDENTIFIED BY PASSWORD '*C49735D016A099C0CF104EF9183F374A54CA2576' GRANT UPDATE ON `priv_db`.* TO 'test_yesprivs'@'localhost' -connect(localhost,test_noprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); -connect(localhost,test_yesprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); show grants; Grants for test_noprivs@localhost GRANT USAGE ON *.* TO 'test_noprivs'@'localhost' IDENTIFIED BY PASSWORD '*C49735D016A099C0CF104EF9183F374A54CA2576' @@ -297,8 +291,6 @@ show grants for test_yesprivs@localhost; Grants for test_yesprivs@localhost GRANT TRIGGER ON *.* TO 'test_yesprivs'@'localhost' IDENTIFIED BY PASSWORD '*C49735D016A099C0CF104EF9183F374A54CA2576' GRANT UPDATE ON `priv_db`.`t1` TO 'test_yesprivs'@'localhost' -connect(localhost,test_noprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); -connect(localhost,test_yesprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); show grants; Grants for test_noprivs@localhost GRANT TRIGGER ON *.* TO 'test_noprivs'@'localhost' IDENTIFIED BY PASSWORD '*C49735D016A099C0CF104EF9183F374A54CA2576' @@ -352,8 +344,6 @@ grant UPDATE (f1) on priv_db.t1 to test_yesprivs@localhost; show grants for test_noprivs; Grants for test_noprivs@% GRANT TRIGGER ON *.* TO 'test_noprivs'@'%' -connect(localhost,test_noprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); -connect(localhost,test_yesprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); show grants; Grants for test_noprivs@localhost GRANT TRIGGER ON *.* TO 'test_noprivs'@'localhost' IDENTIFIED BY PASSWORD '*C49735D016A099C0CF104EF9183F374A54CA2576' @@ -408,8 +398,6 @@ grant TRIGGER, SELECT on *.* to test_yesprivs@localhost; show grants for test_yesprivs@localhost; Grants for test_yesprivs@localhost GRANT SELECT, TRIGGER ON *.* TO 'test_yesprivs'@'localhost' IDENTIFIED BY PASSWORD '*C49735D016A099C0CF104EF9183F374A54CA2576' -connect(localhost,test_noprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); -connect(localhost,test_yesprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); select current_user; current_user test_noprivs@localhost @@ -465,8 +453,6 @@ show grants for test_yesprivs@localhost; Grants for test_yesprivs@localhost GRANT TRIGGER ON *.* TO 'test_yesprivs'@'localhost' IDENTIFIED BY PASSWORD '*C49735D016A099C0CF104EF9183F374A54CA2576' GRANT SELECT ON `priv_db`.* TO 'test_yesprivs'@'localhost' -connect(localhost,test_noprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); -connect(localhost,test_yesprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); show grants; Grants for test_noprivs@localhost GRANT TRIGGER ON *.* TO 'test_noprivs'@'localhost' IDENTIFIED BY PASSWORD '*C49735D016A099C0CF104EF9183F374A54CA2576' @@ -520,8 +506,6 @@ show grants for test_yesprivs@localhost; Grants for test_yesprivs@localhost GRANT TRIGGER ON *.* TO 'test_yesprivs'@'localhost' IDENTIFIED BY PASSWORD '*C49735D016A099C0CF104EF9183F374A54CA2576' GRANT SELECT ON `priv_db`.`t1` TO 'test_yesprivs'@'localhost' -connect(localhost,test_noprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); -connect(localhost,test_yesprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); show grants; Grants for test_noprivs@localhost GRANT TRIGGER ON *.* TO 'test_noprivs'@'localhost' IDENTIFIED BY PASSWORD '*C49735D016A099C0CF104EF9183F374A54CA2576' @@ -566,8 +550,6 @@ show grants for test_noprivs@localhost; Grants for test_noprivs@localhost GRANT TRIGGER ON *.* TO 'test_noprivs'@'localhost' IDENTIFIED BY PASSWORD '*C49735D016A099C0CF104EF9183F374A54CA2576' GRANT INSERT (f1), UPDATE (f1) ON `priv_db`.`t1` TO 'test_noprivs'@'localhost' -connect(localhost,test_noprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); -connect(localhost,test_yesprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); show grants; Grants for test_noprivs@localhost GRANT TRIGGER ON *.* TO 'test_noprivs'@'localhost' IDENTIFIED BY PASSWORD '*C49735D016A099C0CF104EF9183F374A54CA2576' @@ -612,7 +594,6 @@ Grants for test_yesprivs@localhost GRANT TRIGGER ON *.* TO 'test_yesprivs'@'localhost' IDENTIFIED BY PASSWORD '*C49735D016A099C0CF104EF9183F374A54CA2576' GRANT SELECT ON `priv_db`.`t2` TO 'test_yesprivs'@'localhost' GRANT SELECT, UPDATE ON `priv_db`.`t1` TO 'test_yesprivs'@'localhost' -connect(localhost,test_yesprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); select current_user; current_user test_yesprivs@localhost diff --git a/mysql-test/suite/funcs_1/r/memory_trig_03e.result b/mysql-test/suite/funcs_1/r/memory_trig_03e.result index bbee7d47e7e..95c833b90c3 100644 --- a/mysql-test/suite/funcs_1/r/memory_trig_03e.result +++ b/mysql-test/suite/funcs_1/r/memory_trig_03e.result @@ -25,7 +25,6 @@ show grants for test_noprivs@localhost; Grants for test_noprivs@localhost GRANT USAGE ON *.* TO 'test_noprivs'@'localhost' IDENTIFIED BY PASSWORD '*C49735D016A099C0CF104EF9183F374A54CA2576' GRANT SELECT, INSERT ON `priv_db`.* TO 'test_noprivs'@'localhost' -connect(localhost,test_yesprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); no trigger privilege on db level for create: -------------------------------------------- @@ -33,7 +32,6 @@ use priv_db; create trigger trg1_1 before INSERT on t1 for each row set new.f1 = 'trig 1_1-no'; ERROR 42000: TRIGGER command denied to user 'test_yesprivs'@'localhost' for table 't1' -connect(localhost,test_noprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); use priv_db; insert into t1 (f1) values ('insert-yes'); select f1 from t1 order by f1; @@ -254,8 +252,6 @@ revoke ALL PRIVILEGES, GRANT OPTION FROM test_yesprivs@localhost; create User test_noprivs@localhost; set password for test_noprivs@localhost = password('PWD'); revoke ALL PRIVILEGES, GRANT OPTION FROM test_noprivs@localhost; -connect(localhost,test_yesprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); -connect(localhost,test_noprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); no trigger privilege on table level for create: ----------------------------------------------- @@ -514,8 +510,6 @@ grant SELECT,INSERT on *.* to test_noprivs@localhost; show grants for test_noprivs@localhost; Grants for test_noprivs@localhost GRANT SELECT, INSERT ON *.* TO 'test_noprivs'@'localhost' IDENTIFIED BY PASSWORD '*C49735D016A099C0CF104EF9183F374A54CA2576' -connect(localhost,test_yesprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); -connect(localhost,test_noprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); select current_user; current_user test_yesprivs@localhost @@ -564,7 +558,6 @@ revoke TRIGGER on *.* from test_yesprivs@localhost; show grants for test_yesprivs@localhost; Grants for test_yesprivs@localhost GRANT SELECT, INSERT, UPDATE, DELETE, CREATE, DROP, RELOAD, SHUTDOWN, PROCESS, FILE, REFERENCES, INDEX, ALTER, SHOW DATABASES, SUPER, CREATE TEMPORARY TABLES, LOCK TABLES, EXECUTE, REPLICATION SLAVE, REPLICATION CLIENT, CREATE VIEW, SHOW VIEW, CREATE ROUTINE, ALTER ROUTINE, CREATE USER, EVENT ON *.* TO 'test_yesprivs'@'localhost' IDENTIFIED BY PASSWORD '*C49735D016A099C0CF104EF9183F374A54CA2576' -connect(localhost,test_yesprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); select current_user; current_user test_yesprivs@localhost @@ -699,7 +692,6 @@ select f1 from t1 order by f1; f1 insert-yes insert-yes -connect(localhost,test_yesprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); select current_user; current_user test_yesprivs@localhost @@ -768,9 +760,7 @@ Grants for test_noprivs@localhost GRANT USAGE ON *.* TO 'test_noprivs'@'localhost' IDENTIFIED BY PASSWORD '*C49735D016A099C0CF104EF9183F374A54CA2576' GRANT SELECT, INSERT, UPDATE ON `priv1_db`.* TO 'test_noprivs'@'localhost' GRANT SELECT, INSERT ON `priv2_db`.* TO 'test_noprivs'@'localhost' -connect(localhost,test_yesprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); use priv1_db; -connect(localhost,test_noprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); use priv1_db; trigger privilege on one db1 db level, not on db2 @@ -983,7 +973,6 @@ create User test_useprivs@localhost; set password for test_useprivs@localhost = password('PWD'); revoke ALL PRIVILEGES, GRANT OPTION FROM test_yesprivs@localhost; revoke ALL PRIVILEGES, GRANT OPTION FROM test_useprivs@localhost; -connect(localhost,test_yesprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); select current_user; current_user root@localhost @@ -1011,7 +1000,6 @@ select f1 from t1 order by f1; f1 trig 1_1-yes prepare ins1 from 'insert into t1 (f1) values (''insert2-no'')'; -connect(localhost,test_useprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); select current_user; current_user test_useprivs@localhost @@ -1207,7 +1195,6 @@ create table t1 (f1 char(20)) engine= memory; create User test_yesprivs@localhost; set password for test_yesprivs@localhost = password('PWD'); revoke ALL PRIVILEGES, GRANT OPTION FROM test_yesprivs@localhost; -connect(localhost,test_yesprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); select current_user; current_user root@localhost @@ -1319,8 +1306,6 @@ show grants for test_noprivs@localhost; Grants for test_noprivs@localhost GRANT USAGE ON *.* TO 'test_noprivs'@'localhost' IDENTIFIED BY PASSWORD '*C49735D016A099C0CF104EF9183F374A54CA2576' GRANT SELECT, UPDATE ON `priv_db`.* TO 'test_noprivs'@'localhost' -connect(localhost,test_yesprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); -connect(localhost,test_noprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); update only on column: ---------------------- diff --git a/mysql-test/suite/funcs_1/r/memory_trig_0407.result b/mysql-test/suite/funcs_1/r/memory_trig_0407.result index 2f76f5544b9..b8d15b5403b 100644 --- a/mysql-test/suite/funcs_1/r/memory_trig_0407.result +++ b/mysql-test/suite/funcs_1/r/memory_trig_0407.result @@ -68,8 +68,6 @@ revoke ALL PRIVILEGES, GRANT OPTION FROM test_general@localhost; create User test_super@localhost; set password for test_super@localhost = password('PWD'); grant ALL on *.* to test_super@localhost with grant OPTION; -connect(localhost,test_general,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); -connect(localhost,test_super,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); Testcase 3.5.4: --------------- diff --git a/mysql-test/suite/funcs_1/r/memory_trig_08.result b/mysql-test/suite/funcs_1/r/memory_trig_08.result index ab570072087..03505af95c5 100644 --- a/mysql-test/suite/funcs_1/r/memory_trig_08.result +++ b/mysql-test/suite/funcs_1/r/memory_trig_08.result @@ -68,8 +68,6 @@ revoke ALL PRIVILEGES, GRANT OPTION FROM test_general@localhost; create User test_super@localhost; set password for test_super@localhost = password('PWD'); grant ALL on *.* to test_super@localhost with grant OPTION; -connect(localhost,test_general,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); -connect(localhost,test_super,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); Testcase 3.5.8.1: (implied in previous tests) --------------------------------------------- diff --git a/mysql-test/suite/funcs_1/r/myisam_storedproc_06.result b/mysql-test/suite/funcs_1/r/myisam_storedproc_06.result index eb617c68ae9..096cbd1261e 100644 --- a/mysql-test/suite/funcs_1/r/myisam_storedproc_06.result +++ b/mysql-test/suite/funcs_1/r/myisam_storedproc_06.result @@ -79,7 +79,6 @@ grant all on db_storedproc_1.* to 'user_1'@'localhost'; revoke create routine on db_storedproc_1.* from 'user_1'@'localhost'; flush privileges; DROP PROCEDURE IF EXISTS sp1; -connect(localhost,user_1,,db_storedproc_1,MYSQL_PORT,MYSQL_SOCK); user_1@localhost db_storedproc_1 USE db_storedproc_1; @@ -92,7 +91,6 @@ USE db_storedproc_1; root@localhost db_storedproc_1 GRANT CREATE ROUTINE ON db_storedproc_1.* TO 'user_1'@'localhost'; -connect(localhost,user_1,,db_storedproc_1,MYSQL_PORT,MYSQL_SOCK); user_1@localhost db_storedproc_1 USE db_storedproc_1; @@ -113,7 +111,6 @@ Ensure that root always has the GRANT CREATE ROUTINE privilege. -------------------------------------------------------------------------------- grant create routine on db_storedproc_1.* to 'user_1'@'localhost'; flush privileges; -connect(localhost,user_1,,db_storedproc_1,MYSQL_PORT,MYSQL_SOCK); user_1@localhost db_storedproc_1 DROP PROCEDURE IF EXISTS sp3; @@ -150,7 +147,6 @@ CREATE PROCEDURE sp4(v1 char(20)) BEGIN SELECT * from db_storedproc_1.t6 where t6.f2= 'xyz'; END// -connect(localhost,user_1,,db_storedproc_1,MYSQL_PORT,MYSQL_SOCK); user_1@localhost db_storedproc_1 USE db_storedproc_1; @@ -192,7 +188,6 @@ grant create routine on db_storedproc_1.* to 'user_1'@'localhost'; grant SELECT on db_storedproc_1.* to 'user_2'@'localhost'; grant execute on db_storedproc_1.* to 'user_2'@'localhost'; flush privileges; -connect(localhost,user_1,,db_storedproc_1,MYSQL_PORT,MYSQL_SOCK); user_1@localhost db_storedproc_1 CREATE PROCEDURE sp5_s_i () sql security definer @@ -208,7 +203,6 @@ CREATE PROCEDURE sp5_ins () sql security definer BEGIN insert into db_storedproc_1.t3165 values ('inserted', 'from sp5_ins', 1000); END// -connect(localhost,user_2,,db_storedproc_1,MYSQL_PORT,MYSQL_SOCK); user_2@localhost db_storedproc_1 CALL sp5_s_i(); @@ -306,7 +300,6 @@ GRANT CREATE ROUTINE ON db_storedproc_1.* TO 'user_1'@'localhost'; GRANT SELECT ON db_storedproc_1.* TO 'user_2'@'localhost'; GRANT EXECUTE ON db_storedproc_1.* TO 'user_2'@'localhost'; FLUSH PRIVILEGES; -connect(localhost,user_1,,db_storedproc_1,MYSQL_PORT,MYSQL_SOCK); user_1@localhost db_storedproc_1 CREATE PROCEDURE sp3166_s_i () SQL SECURITY INVOKER @@ -322,7 +315,6 @@ CREATE PROCEDURE sp3166_ins () SQL SECURITY INVOKER BEGIN insert into db_storedproc_1.t3166 values ('inserted from sp3166_ins'); END// -connect(localhost,user_2,,db_storedproc_1,MYSQL_PORT,MYSQL_SOCK); user_2@localhost db_storedproc_1 CALL sp3166_s_i(); @@ -341,7 +333,6 @@ c1 inserted outside SP GRANT INSERT ON db_storedproc_1.* TO 'user_2'@'localhost'; FLUSH PRIVILEGES; -connect(localhost,user_2,,db_storedproc_1,MYSQL_PORT,MYSQL_SOCK); user_2@localhost db_storedproc_1 CALL sp3166_s_i(); @@ -362,7 +353,6 @@ inserted from sp3166_s_i inserted from sp3166_ins REVOKE SELECT ON db_storedproc_1.* FROM 'user_2'@'localhost'; FLUSH PRIVILEGES; -connect(localhost,user_2,,db_storedproc_1,MYSQL_PORT,MYSQL_SOCK); user_2@localhost db_storedproc_1 CALL sp3166_s_i(); @@ -380,7 +370,6 @@ inserted from sp3166_ins root@localhost db_storedproc_1 REVOKE EXECUTE on db_storedproc_1.* FROM 'user_2'@'localhost'; FLUSH PRIVILEGES; -connect(localhost,user_2,,db_storedproc_1,MYSQL_PORT,MYSQL_SOCK); user_2@localhost db_storedproc_1 CALL sp3166_s_i(); diff --git a/mysql-test/suite/funcs_1/r/myisam_storedproc_10.result b/mysql-test/suite/funcs_1/r/myisam_storedproc_10.result index f5e34b0063c..4a932ee826b 100644 --- a/mysql-test/suite/funcs_1/r/myisam_storedproc_10.result +++ b/mysql-test/suite/funcs_1/r/myisam_storedproc_10.result @@ -82,7 +82,6 @@ create user 'user_2'@'localhost'; GRANT CREATE ROUTINE ON db_storedproc.* TO 'user_1'@'localhost'; GRANT SELECT ON db_storedproc.* TO 'user_2'@'localhost'; FLUSH PRIVILEGES; -connect(localhost,user_1,,db_storedproc,MYSQL_PORT,MYSQL_SOCK); user_1@localhost db_storedproc CREATE PROCEDURE sp31102 () SQL SECURITY INVOKER @@ -95,7 +94,6 @@ DECLARE res INT; SET res = n * n; RETURN res; END// -connect(localhost,user_2,,db_storedproc,MYSQL_PORT,MYSQL_SOCK); user_2@localhost db_storedproc CALL sp31102(); @@ -114,7 +112,6 @@ fn31105( 9 ) 81 GRANT EXECUTE ON db_storedproc.* TO 'user_2'@'localhost'; FLUSH PRIVILEGES; -connect(localhost,user_2,,db_storedproc,MYSQL_PORT,MYSQL_SOCK); user_2@localhost db_storedproc CALL sp31102(); @@ -135,7 +132,6 @@ a` a` 1000-01-01 -5000 a` -5000 SELECT fn31105( 9 ); fn31105( 9 ) 81 -connect(localhost,user_2,,db_storedproc,MYSQL_PORT,MYSQL_SOCK); user_2@localhost db_storedproc CALL sp31102(); diff --git a/mysql-test/suite/funcs_1/r/myisam_trig_03.result b/mysql-test/suite/funcs_1/r/myisam_trig_03.result index 7f38fd1f182..0d622915dca 100644 --- a/mysql-test/suite/funcs_1/r/myisam_trig_03.result +++ b/mysql-test/suite/funcs_1/r/myisam_trig_03.result @@ -86,8 +86,6 @@ show grants for test_yesprivs@localhost; Grants for test_yesprivs@localhost GRANT TRIGGER ON *.* TO 'test_yesprivs'@'localhost' IDENTIFIED BY PASSWORD '*C49735D016A099C0CF104EF9183F374A54CA2576' GRANT SELECT ON `priv_db`.`t1` TO 'test_yesprivs'@'localhost' -connect(localhost,test_noprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); -connect(localhost,test_yesprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); Testcase 3.5.3.2: ----------------- @@ -162,8 +160,6 @@ grant TRIGGER, UPDATE on *.* to test_yesprivs@localhost; show grants for test_yesprivs@localhost; Grants for test_yesprivs@localhost GRANT UPDATE, TRIGGER ON *.* TO 'test_yesprivs'@'localhost' IDENTIFIED BY PASSWORD '*C49735D016A099C0CF104EF9183F374A54CA2576' -connect(localhost,test_noprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); -connect(localhost,test_yesprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); select current_user; current_user test_noprivs@localhost @@ -223,8 +219,6 @@ show grants for test_yesprivs@localhost; Grants for test_yesprivs@localhost GRANT TRIGGER ON *.* TO 'test_yesprivs'@'localhost' IDENTIFIED BY PASSWORD '*C49735D016A099C0CF104EF9183F374A54CA2576' GRANT UPDATE ON `priv_db`.* TO 'test_yesprivs'@'localhost' -connect(localhost,test_noprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); -connect(localhost,test_yesprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); show grants; Grants for test_noprivs@localhost GRANT USAGE ON *.* TO 'test_noprivs'@'localhost' IDENTIFIED BY PASSWORD '*C49735D016A099C0CF104EF9183F374A54CA2576' @@ -297,8 +291,6 @@ show grants for test_yesprivs@localhost; Grants for test_yesprivs@localhost GRANT TRIGGER ON *.* TO 'test_yesprivs'@'localhost' IDENTIFIED BY PASSWORD '*C49735D016A099C0CF104EF9183F374A54CA2576' GRANT UPDATE ON `priv_db`.`t1` TO 'test_yesprivs'@'localhost' -connect(localhost,test_noprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); -connect(localhost,test_yesprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); show grants; Grants for test_noprivs@localhost GRANT TRIGGER ON *.* TO 'test_noprivs'@'localhost' IDENTIFIED BY PASSWORD '*C49735D016A099C0CF104EF9183F374A54CA2576' @@ -352,8 +344,6 @@ grant UPDATE (f1) on priv_db.t1 to test_yesprivs@localhost; show grants for test_noprivs; Grants for test_noprivs@% GRANT TRIGGER ON *.* TO 'test_noprivs'@'%' -connect(localhost,test_noprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); -connect(localhost,test_yesprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); show grants; Grants for test_noprivs@localhost GRANT TRIGGER ON *.* TO 'test_noprivs'@'localhost' IDENTIFIED BY PASSWORD '*C49735D016A099C0CF104EF9183F374A54CA2576' @@ -408,8 +398,6 @@ grant TRIGGER, SELECT on *.* to test_yesprivs@localhost; show grants for test_yesprivs@localhost; Grants for test_yesprivs@localhost GRANT SELECT, TRIGGER ON *.* TO 'test_yesprivs'@'localhost' IDENTIFIED BY PASSWORD '*C49735D016A099C0CF104EF9183F374A54CA2576' -connect(localhost,test_noprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); -connect(localhost,test_yesprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); select current_user; current_user test_noprivs@localhost @@ -465,8 +453,6 @@ show grants for test_yesprivs@localhost; Grants for test_yesprivs@localhost GRANT TRIGGER ON *.* TO 'test_yesprivs'@'localhost' IDENTIFIED BY PASSWORD '*C49735D016A099C0CF104EF9183F374A54CA2576' GRANT SELECT ON `priv_db`.* TO 'test_yesprivs'@'localhost' -connect(localhost,test_noprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); -connect(localhost,test_yesprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); show grants; Grants for test_noprivs@localhost GRANT TRIGGER ON *.* TO 'test_noprivs'@'localhost' IDENTIFIED BY PASSWORD '*C49735D016A099C0CF104EF9183F374A54CA2576' @@ -520,8 +506,6 @@ show grants for test_yesprivs@localhost; Grants for test_yesprivs@localhost GRANT TRIGGER ON *.* TO 'test_yesprivs'@'localhost' IDENTIFIED BY PASSWORD '*C49735D016A099C0CF104EF9183F374A54CA2576' GRANT SELECT ON `priv_db`.`t1` TO 'test_yesprivs'@'localhost' -connect(localhost,test_noprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); -connect(localhost,test_yesprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); show grants; Grants for test_noprivs@localhost GRANT TRIGGER ON *.* TO 'test_noprivs'@'localhost' IDENTIFIED BY PASSWORD '*C49735D016A099C0CF104EF9183F374A54CA2576' @@ -566,8 +550,6 @@ show grants for test_noprivs@localhost; Grants for test_noprivs@localhost GRANT TRIGGER ON *.* TO 'test_noprivs'@'localhost' IDENTIFIED BY PASSWORD '*C49735D016A099C0CF104EF9183F374A54CA2576' GRANT INSERT (f1), UPDATE (f1) ON `priv_db`.`t1` TO 'test_noprivs'@'localhost' -connect(localhost,test_noprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); -connect(localhost,test_yesprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); show grants; Grants for test_noprivs@localhost GRANT TRIGGER ON *.* TO 'test_noprivs'@'localhost' IDENTIFIED BY PASSWORD '*C49735D016A099C0CF104EF9183F374A54CA2576' @@ -612,7 +594,6 @@ Grants for test_yesprivs@localhost GRANT TRIGGER ON *.* TO 'test_yesprivs'@'localhost' IDENTIFIED BY PASSWORD '*C49735D016A099C0CF104EF9183F374A54CA2576' GRANT SELECT ON `priv_db`.`t2` TO 'test_yesprivs'@'localhost' GRANT SELECT, UPDATE ON `priv_db`.`t1` TO 'test_yesprivs'@'localhost' -connect(localhost,test_yesprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); select current_user; current_user test_yesprivs@localhost diff --git a/mysql-test/suite/funcs_1/r/myisam_trig_03e.result b/mysql-test/suite/funcs_1/r/myisam_trig_03e.result index e4dc67098ad..9e0811d29fd 100644 --- a/mysql-test/suite/funcs_1/r/myisam_trig_03e.result +++ b/mysql-test/suite/funcs_1/r/myisam_trig_03e.result @@ -25,7 +25,6 @@ show grants for test_noprivs@localhost; Grants for test_noprivs@localhost GRANT USAGE ON *.* TO 'test_noprivs'@'localhost' IDENTIFIED BY PASSWORD '*C49735D016A099C0CF104EF9183F374A54CA2576' GRANT SELECT, INSERT ON `priv_db`.* TO 'test_noprivs'@'localhost' -connect(localhost,test_yesprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); no trigger privilege on db level for create: -------------------------------------------- @@ -33,7 +32,6 @@ use priv_db; create trigger trg1_1 before INSERT on t1 for each row set new.f1 = 'trig 1_1-no'; ERROR 42000: TRIGGER command denied to user 'test_yesprivs'@'localhost' for table 't1' -connect(localhost,test_noprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); use priv_db; insert into t1 (f1) values ('insert-yes'); select f1 from t1 order by f1; @@ -254,8 +252,6 @@ revoke ALL PRIVILEGES, GRANT OPTION FROM test_yesprivs@localhost; create User test_noprivs@localhost; set password for test_noprivs@localhost = password('PWD'); revoke ALL PRIVILEGES, GRANT OPTION FROM test_noprivs@localhost; -connect(localhost,test_yesprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); -connect(localhost,test_noprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); no trigger privilege on table level for create: ----------------------------------------------- @@ -514,8 +510,6 @@ grant SELECT,INSERT on *.* to test_noprivs@localhost; show grants for test_noprivs@localhost; Grants for test_noprivs@localhost GRANT SELECT, INSERT ON *.* TO 'test_noprivs'@'localhost' IDENTIFIED BY PASSWORD '*C49735D016A099C0CF104EF9183F374A54CA2576' -connect(localhost,test_yesprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); -connect(localhost,test_noprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); select current_user; current_user test_yesprivs@localhost @@ -564,7 +558,6 @@ revoke TRIGGER on *.* from test_yesprivs@localhost; show grants for test_yesprivs@localhost; Grants for test_yesprivs@localhost GRANT SELECT, INSERT, UPDATE, DELETE, CREATE, DROP, RELOAD, SHUTDOWN, PROCESS, FILE, REFERENCES, INDEX, ALTER, SHOW DATABASES, SUPER, CREATE TEMPORARY TABLES, LOCK TABLES, EXECUTE, REPLICATION SLAVE, REPLICATION CLIENT, CREATE VIEW, SHOW VIEW, CREATE ROUTINE, ALTER ROUTINE, CREATE USER, EVENT ON *.* TO 'test_yesprivs'@'localhost' IDENTIFIED BY PASSWORD '*C49735D016A099C0CF104EF9183F374A54CA2576' -connect(localhost,test_yesprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); select current_user; current_user test_yesprivs@localhost @@ -699,7 +692,6 @@ select f1 from t1 order by f1; f1 insert-yes insert-yes -connect(localhost,test_yesprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); select current_user; current_user test_yesprivs@localhost @@ -768,9 +760,7 @@ Grants for test_noprivs@localhost GRANT USAGE ON *.* TO 'test_noprivs'@'localhost' IDENTIFIED BY PASSWORD '*C49735D016A099C0CF104EF9183F374A54CA2576' GRANT SELECT, INSERT, UPDATE ON `priv1_db`.* TO 'test_noprivs'@'localhost' GRANT SELECT, INSERT ON `priv2_db`.* TO 'test_noprivs'@'localhost' -connect(localhost,test_yesprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); use priv1_db; -connect(localhost,test_noprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); use priv1_db; trigger privilege on one db1 db level, not on db2 @@ -983,7 +973,6 @@ create User test_useprivs@localhost; set password for test_useprivs@localhost = password('PWD'); revoke ALL PRIVILEGES, GRANT OPTION FROM test_yesprivs@localhost; revoke ALL PRIVILEGES, GRANT OPTION FROM test_useprivs@localhost; -connect(localhost,test_yesprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); select current_user; current_user root@localhost @@ -1011,7 +1000,6 @@ select f1 from t1 order by f1; f1 trig 1_1-yes prepare ins1 from 'insert into t1 (f1) values (''insert2-no'')'; -connect(localhost,test_useprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); select current_user; current_user test_useprivs@localhost @@ -1207,7 +1195,6 @@ create table t1 (f1 char(20)) engine= myisam; create User test_yesprivs@localhost; set password for test_yesprivs@localhost = password('PWD'); revoke ALL PRIVILEGES, GRANT OPTION FROM test_yesprivs@localhost; -connect(localhost,test_yesprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); select current_user; current_user root@localhost @@ -1319,8 +1306,6 @@ show grants for test_noprivs@localhost; Grants for test_noprivs@localhost GRANT USAGE ON *.* TO 'test_noprivs'@'localhost' IDENTIFIED BY PASSWORD '*C49735D016A099C0CF104EF9183F374A54CA2576' GRANT SELECT, UPDATE ON `priv_db`.* TO 'test_noprivs'@'localhost' -connect(localhost,test_yesprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); -connect(localhost,test_noprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); update only on column: ---------------------- diff --git a/mysql-test/suite/funcs_1/r/myisam_trig_0407.result b/mysql-test/suite/funcs_1/r/myisam_trig_0407.result index 2f76f5544b9..b8d15b5403b 100644 --- a/mysql-test/suite/funcs_1/r/myisam_trig_0407.result +++ b/mysql-test/suite/funcs_1/r/myisam_trig_0407.result @@ -68,8 +68,6 @@ revoke ALL PRIVILEGES, GRANT OPTION FROM test_general@localhost; create User test_super@localhost; set password for test_super@localhost = password('PWD'); grant ALL on *.* to test_super@localhost with grant OPTION; -connect(localhost,test_general,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); -connect(localhost,test_super,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); Testcase 3.5.4: --------------- diff --git a/mysql-test/suite/funcs_1/r/myisam_trig_08.result b/mysql-test/suite/funcs_1/r/myisam_trig_08.result index ab570072087..03505af95c5 100644 --- a/mysql-test/suite/funcs_1/r/myisam_trig_08.result +++ b/mysql-test/suite/funcs_1/r/myisam_trig_08.result @@ -68,8 +68,6 @@ revoke ALL PRIVILEGES, GRANT OPTION FROM test_general@localhost; create User test_super@localhost; set password for test_super@localhost = password('PWD'); grant ALL on *.* to test_super@localhost with grant OPTION; -connect(localhost,test_general,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); -connect(localhost,test_super,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); Testcase 3.5.8.1: (implied in previous tests) --------------------------------------------- diff --git a/mysql-test/suite/funcs_1/r/ndb_trig_03.result b/mysql-test/suite/funcs_1/r/ndb_trig_03.result index b02fba0f38d..a7fce94c91d 100644 --- a/mysql-test/suite/funcs_1/r/ndb_trig_03.result +++ b/mysql-test/suite/funcs_1/r/ndb_trig_03.result @@ -85,8 +85,6 @@ show grants for test_yesprivs@localhost; Grants for test_yesprivs@localhost GRANT TRIGGER ON *.* TO 'test_yesprivs'@'localhost' IDENTIFIED BY PASSWORD '*C49735D016A099C0CF104EF9183F374A54CA2576' GRANT SELECT ON `priv_db`.`t1` TO 'test_yesprivs'@'localhost' -connect(localhost,test_noprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); -connect(localhost,test_yesprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); Testcase 3.5.3.2: ----------------- @@ -161,8 +159,6 @@ grant TRIGGER, UPDATE on *.* to test_yesprivs@localhost; show grants for test_yesprivs@localhost; Grants for test_yesprivs@localhost GRANT UPDATE, TRIGGER ON *.* TO 'test_yesprivs'@'localhost' IDENTIFIED BY PASSWORD '*C49735D016A099C0CF104EF9183F374A54CA2576' -connect(localhost,test_noprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); -connect(localhost,test_yesprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); select current_user; current_user test_noprivs@localhost @@ -222,8 +218,6 @@ show grants for test_yesprivs@localhost; Grants for test_yesprivs@localhost GRANT TRIGGER ON *.* TO 'test_yesprivs'@'localhost' IDENTIFIED BY PASSWORD '*C49735D016A099C0CF104EF9183F374A54CA2576' GRANT UPDATE ON `priv_db`.* TO 'test_yesprivs'@'localhost' -connect(localhost,test_noprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); -connect(localhost,test_yesprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); show grants; Grants for test_noprivs@localhost GRANT USAGE ON *.* TO 'test_noprivs'@'localhost' IDENTIFIED BY PASSWORD '*C49735D016A099C0CF104EF9183F374A54CA2576' @@ -296,8 +290,6 @@ show grants for test_yesprivs@localhost; Grants for test_yesprivs@localhost GRANT TRIGGER ON *.* TO 'test_yesprivs'@'localhost' IDENTIFIED BY PASSWORD '*C49735D016A099C0CF104EF9183F374A54CA2576' GRANT UPDATE ON `priv_db`.`t1` TO 'test_yesprivs'@'localhost' -connect(localhost,test_noprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); -connect(localhost,test_yesprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); show grants; Grants for test_noprivs@localhost GRANT TRIGGER ON *.* TO 'test_noprivs'@'localhost' IDENTIFIED BY PASSWORD '*C49735D016A099C0CF104EF9183F374A54CA2576' @@ -351,8 +343,6 @@ grant UPDATE (f1) on priv_db.t1 to test_yesprivs@localhost; show grants for test_noprivs; Grants for test_noprivs@% GRANT TRIGGER ON *.* TO 'test_noprivs'@'%' -connect(localhost,test_noprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); -connect(localhost,test_yesprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); show grants; Grants for test_noprivs@localhost GRANT TRIGGER ON *.* TO 'test_noprivs'@'localhost' IDENTIFIED BY PASSWORD '*C49735D016A099C0CF104EF9183F374A54CA2576' @@ -407,8 +397,6 @@ grant TRIGGER, SELECT on *.* to test_yesprivs@localhost; show grants for test_yesprivs@localhost; Grants for test_yesprivs@localhost GRANT SELECT, TRIGGER ON *.* TO 'test_yesprivs'@'localhost' IDENTIFIED BY PASSWORD '*C49735D016A099C0CF104EF9183F374A54CA2576' -connect(localhost,test_noprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); -connect(localhost,test_yesprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); select current_user; current_user test_noprivs@localhost @@ -464,8 +452,6 @@ show grants for test_yesprivs@localhost; Grants for test_yesprivs@localhost GRANT TRIGGER ON *.* TO 'test_yesprivs'@'localhost' IDENTIFIED BY PASSWORD '*C49735D016A099C0CF104EF9183F374A54CA2576' GRANT SELECT ON `priv_db`.* TO 'test_yesprivs'@'localhost' -connect(localhost,test_noprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); -connect(localhost,test_yesprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); show grants; Grants for test_noprivs@localhost GRANT TRIGGER ON *.* TO 'test_noprivs'@'localhost' IDENTIFIED BY PASSWORD '*C49735D016A099C0CF104EF9183F374A54CA2576' @@ -519,8 +505,6 @@ show grants for test_yesprivs@localhost; Grants for test_yesprivs@localhost GRANT TRIGGER ON *.* TO 'test_yesprivs'@'localhost' IDENTIFIED BY PASSWORD '*C49735D016A099C0CF104EF9183F374A54CA2576' GRANT SELECT ON `priv_db`.`t1` TO 'test_yesprivs'@'localhost' -connect(localhost,test_noprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); -connect(localhost,test_yesprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); show grants; Grants for test_noprivs@localhost GRANT TRIGGER ON *.* TO 'test_noprivs'@'localhost' IDENTIFIED BY PASSWORD '*C49735D016A099C0CF104EF9183F374A54CA2576' @@ -565,8 +549,6 @@ show grants for test_noprivs@localhost; Grants for test_noprivs@localhost GRANT TRIGGER ON *.* TO 'test_noprivs'@'localhost' IDENTIFIED BY PASSWORD '*C49735D016A099C0CF104EF9183F374A54CA2576' GRANT INSERT (f1), UPDATE (f1) ON `priv_db`.`t1` TO 'test_noprivs'@'localhost' -connect(localhost,test_noprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); -connect(localhost,test_yesprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); show grants; Grants for test_noprivs@localhost GRANT TRIGGER ON *.* TO 'test_noprivs'@'localhost' IDENTIFIED BY PASSWORD '*C49735D016A099C0CF104EF9183F374A54CA2576' @@ -611,7 +593,6 @@ Grants for test_yesprivs@localhost GRANT TRIGGER ON *.* TO 'test_yesprivs'@'localhost' IDENTIFIED BY PASSWORD '*C49735D016A099C0CF104EF9183F374A54CA2576' GRANT SELECT ON `priv_db`.`t2` TO 'test_yesprivs'@'localhost' GRANT SELECT, UPDATE ON `priv_db`.`t1` TO 'test_yesprivs'@'localhost' -connect(localhost,test_yesprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); select current_user; current_user test_yesprivs@localhost diff --git a/mysql-test/suite/funcs_1/r/ndb_trig_03e.result b/mysql-test/suite/funcs_1/r/ndb_trig_03e.result index 84260822edf..ec7cbeb2876 100644 --- a/mysql-test/suite/funcs_1/r/ndb_trig_03e.result +++ b/mysql-test/suite/funcs_1/r/ndb_trig_03e.result @@ -24,7 +24,6 @@ show grants for test_noprivs@localhost; Grants for test_noprivs@localhost GRANT USAGE ON *.* TO 'test_noprivs'@'localhost' IDENTIFIED BY PASSWORD '*C49735D016A099C0CF104EF9183F374A54CA2576' GRANT SELECT, INSERT ON `priv_db`.* TO 'test_noprivs'@'localhost' -connect(localhost,test_yesprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); no trigger privilege on db level for create: -------------------------------------------- @@ -32,7 +31,6 @@ use priv_db; create trigger trg1_1 before INSERT on t1 for each row set new.f1 = 'trig 1_1-no'; ERROR 42000: TRIGGER command denied to user 'test_yesprivs'@'localhost' for table 't1' -connect(localhost,test_noprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); use priv_db; insert into t1 (f1) values ('insert-yes'); select f1 from t1 order by f1; @@ -253,8 +251,6 @@ revoke ALL PRIVILEGES, GRANT OPTION FROM test_yesprivs@localhost; create User test_noprivs@localhost; set password for test_noprivs@localhost = password('PWD'); revoke ALL PRIVILEGES, GRANT OPTION FROM test_noprivs@localhost; -connect(localhost,test_yesprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); -connect(localhost,test_noprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); no trigger privilege on table level for create: ----------------------------------------------- @@ -513,8 +509,6 @@ grant SELECT,INSERT on *.* to test_noprivs@localhost; show grants for test_noprivs@localhost; Grants for test_noprivs@localhost GRANT SELECT, INSERT ON *.* TO 'test_noprivs'@'localhost' IDENTIFIED BY PASSWORD '*C49735D016A099C0CF104EF9183F374A54CA2576' -connect(localhost,test_yesprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); -connect(localhost,test_noprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); select current_user; current_user test_yesprivs@localhost @@ -563,7 +557,6 @@ revoke TRIGGER on *.* from test_yesprivs@localhost; show grants for test_yesprivs@localhost; Grants for test_yesprivs@localhost GRANT SELECT, INSERT, UPDATE, DELETE, CREATE, DROP, RELOAD, SHUTDOWN, PROCESS, FILE, REFERENCES, INDEX, ALTER, SHOW DATABASES, SUPER, CREATE TEMPORARY TABLES, LOCK TABLES, EXECUTE, REPLICATION SLAVE, REPLICATION CLIENT, CREATE VIEW, SHOW VIEW, CREATE ROUTINE, ALTER ROUTINE, CREATE USER, EVENT ON *.* TO 'test_yesprivs'@'localhost' IDENTIFIED BY PASSWORD '*C49735D016A099C0CF104EF9183F374A54CA2576' -connect(localhost,test_yesprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); select current_user; current_user test_yesprivs@localhost @@ -698,7 +691,6 @@ select f1 from t1 order by f1; f1 insert-yes insert-yes -connect(localhost,test_yesprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); select current_user; current_user test_yesprivs@localhost @@ -767,9 +759,7 @@ Grants for test_noprivs@localhost GRANT USAGE ON *.* TO 'test_noprivs'@'localhost' IDENTIFIED BY PASSWORD '*C49735D016A099C0CF104EF9183F374A54CA2576' GRANT SELECT, INSERT, UPDATE ON `priv1_db`.* TO 'test_noprivs'@'localhost' GRANT SELECT, INSERT ON `priv2_db`.* TO 'test_noprivs'@'localhost' -connect(localhost,test_yesprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); use priv1_db; -connect(localhost,test_noprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); use priv1_db; trigger privilege on one db1 db level, not on db2 @@ -982,7 +972,6 @@ create User test_useprivs@localhost; set password for test_useprivs@localhost = password('PWD'); revoke ALL PRIVILEGES, GRANT OPTION FROM test_yesprivs@localhost; revoke ALL PRIVILEGES, GRANT OPTION FROM test_useprivs@localhost; -connect(localhost,test_yesprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); select current_user; current_user root@localhost @@ -1010,7 +999,6 @@ select f1 from t1 order by f1; f1 trig 1_1-yes prepare ins1 from 'insert into t1 (f1) values (''insert2-no'')'; -connect(localhost,test_useprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); select current_user; current_user test_useprivs@localhost @@ -1206,7 +1194,6 @@ create table t1 (f1 char(20)) engine= ndb; create User test_yesprivs@localhost; set password for test_yesprivs@localhost = password('PWD'); revoke ALL PRIVILEGES, GRANT OPTION FROM test_yesprivs@localhost; -connect(localhost,test_yesprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); select current_user; current_user root@localhost @@ -1303,7 +1290,6 @@ create table t1 (f1 char(20)) engine= ndb; create User test_yesprivs@localhost; set password for test_yesprivs@localhost = password('PWD'); revoke ALL PRIVILEGES, GRANT OPTION FROM test_yesprivs@localhost; -connect(localhost,test_yesprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); select current_user; current_user root@localhost @@ -1375,8 +1361,6 @@ show grants for test_noprivs@localhost; Grants for test_noprivs@localhost GRANT USAGE ON *.* TO 'test_noprivs'@'localhost' IDENTIFIED BY PASSWORD '*C49735D016A099C0CF104EF9183F374A54CA2576' GRANT SELECT, UPDATE ON `priv_db`.* TO 'test_noprivs'@'localhost' -connect(localhost,test_yesprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); -connect(localhost,test_noprivs,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); update only on column: ---------------------- diff --git a/mysql-test/suite/funcs_1/r/ndb_trig_0407.result b/mysql-test/suite/funcs_1/r/ndb_trig_0407.result index 33e58f50ec1..8597f252e54 100644 --- a/mysql-test/suite/funcs_1/r/ndb_trig_0407.result +++ b/mysql-test/suite/funcs_1/r/ndb_trig_0407.result @@ -67,8 +67,6 @@ revoke ALL PRIVILEGES, GRANT OPTION FROM test_general@localhost; create User test_super@localhost; set password for test_super@localhost = password('PWD'); grant ALL on *.* to test_super@localhost with grant OPTION; -connect(localhost,test_general,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); -connect(localhost,test_super,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); Testcase 3.5.4: --------------- diff --git a/mysql-test/suite/funcs_1/r/ndb_trig_08.result b/mysql-test/suite/funcs_1/r/ndb_trig_08.result index 6ced07cef73..b2b38694680 100644 --- a/mysql-test/suite/funcs_1/r/ndb_trig_08.result +++ b/mysql-test/suite/funcs_1/r/ndb_trig_08.result @@ -67,8 +67,6 @@ revoke ALL PRIVILEGES, GRANT OPTION FROM test_general@localhost; create User test_super@localhost; set password for test_super@localhost = password('PWD'); grant ALL on *.* to test_super@localhost with grant OPTION; -connect(localhost,test_general,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); -connect(localhost,test_super,PWD,test,MASTER_MYPORT,MASTER_MYSOCK); Testcase 3.5.8.1: (implied in previous tests) --------------------------------------------- diff --git a/mysql-test/suite/funcs_1/r/storedproc.result b/mysql-test/suite/funcs_1/r/storedproc.result index 3efb361dc82..8da7213bded 100644 --- a/mysql-test/suite/funcs_1/r/storedproc.result +++ b/mysql-test/suite/funcs_1/r/storedproc.result @@ -1834,7 +1834,6 @@ CREATE PROCEDURE sp11() insert into mysql.t1 values('a'); SELECT security_type from mysql.proc where specific_name='sp11'; security_type DEFINER -connect(localhost,user_1,,db_storedproc,MYSQL_PORT,MYSQL_SOCK); user_1@localhost db_storedproc CALL sp11(); diff --git a/mysql-test/suite/funcs_1/storedproc/storedproc_06.inc b/mysql-test/suite/funcs_1/storedproc/storedproc_06.inc index f2df99fb5a3..4ecca63351d 100644 --- a/mysql-test/suite/funcs_1/storedproc/storedproc_06.inc +++ b/mysql-test/suite/funcs_1/storedproc/storedproc_06.inc @@ -53,7 +53,6 @@ flush privileges; DROP PROCEDURE IF EXISTS sp1; --enable_warnings ---replace_result $MASTER_MYPORT MYSQL_PORT $MASTER_MYSOCK MYSQL_SOCK connect (user1a, localhost, user_1, , db_storedproc_1); --source suite/funcs_1/include/show_connection.inc @@ -75,7 +74,6 @@ USE db_storedproc_1; --source suite/funcs_1/include/show_connection.inc GRANT CREATE ROUTINE ON db_storedproc_1.* TO 'user_1'@'localhost'; ---replace_result $MASTER_MYPORT MYSQL_PORT $MASTER_MYSOCK MYSQL_SOCK connect (user1b, localhost, user_1, , db_storedproc_1); --source suite/funcs_1/include/show_connection.inc @@ -120,7 +118,6 @@ grant create routine on db_storedproc_1.* to 'user_1'@'localhost'; flush privileges; # disconnect default; ---replace_result $MASTER_MYPORT MYSQL_PORT $MASTER_MYSOCK MYSQL_SOCK connect (user2, localhost, user_1, , db_storedproc_1); --source suite/funcs_1/include/show_connection.inc @@ -187,7 +184,6 @@ delimiter ;// #disconnect default; ---replace_result $MASTER_MYPORT MYSQL_PORT $MASTER_MYSOCK MYSQL_SOCK connect (user3, localhost, user_1, , db_storedproc_1); --source suite/funcs_1/include/show_connection.inc @@ -234,7 +230,6 @@ grant SELECT on db_storedproc_1.* to 'user_2'@'localhost'; grant execute on db_storedproc_1.* to 'user_2'@'localhost'; flush privileges; ---replace_result $MASTER_MYPORT MYSQL_PORT $MASTER_MYSOCK MYSQL_SOCK connect (user5_1, localhost, user_1, , db_storedproc_1); --source suite/funcs_1/include/show_connection.inc @@ -258,7 +253,6 @@ delimiter ;// disconnect user5_1; ---replace_result $MASTER_MYPORT MYSQL_PORT $MASTER_MYSOCK MYSQL_SOCK connect (user5_2, localhost, user_2, , db_storedproc_1); --source suite/funcs_1/include/show_connection.inc @@ -365,7 +359,6 @@ GRANT SELECT ON db_storedproc_1.* TO 'user_2'@'localhost'; GRANT EXECUTE ON db_storedproc_1.* TO 'user_2'@'localhost'; FLUSH PRIVILEGES; ---replace_result $MASTER_MYPORT MYSQL_PORT $MASTER_MYSOCK MYSQL_SOCK connect (user6_1, localhost, user_1, , db_storedproc_1); --source suite/funcs_1/include/show_connection.inc @@ -389,7 +382,6 @@ delimiter ;// disconnect user6_1; ---replace_result $MASTER_MYPORT MYSQL_PORT $MASTER_MYSOCK MYSQL_SOCK connect (user6_2, localhost, user_2, , db_storedproc_1); --source suite/funcs_1/include/show_connection.inc @@ -407,7 +399,6 @@ GRANT INSERT ON db_storedproc_1.* TO 'user_2'@'localhost'; FLUSH PRIVILEGES; disconnect user6_2; ---replace_result $MASTER_MYPORT MYSQL_PORT $MASTER_MYSOCK MYSQL_SOCK connect (user6_3, localhost, user_2, , db_storedproc_1); --source suite/funcs_1/include/show_connection.inc CALL sp3166_s_i(); @@ -422,7 +413,6 @@ CALL sp3166_sel(); REVOKE SELECT ON db_storedproc_1.* FROM 'user_2'@'localhost'; FLUSH PRIVILEGES; ---replace_result $MASTER_MYPORT MYSQL_PORT $MASTER_MYSOCK MYSQL_SOCK connect (user6_4, localhost, user_2, , db_storedproc_1); --source suite/funcs_1/include/show_connection.inc --error ER_TABLEACCESS_DENIED_ERROR @@ -439,7 +429,6 @@ CALL sp3166_s_i(); REVOKE EXECUTE on db_storedproc_1.* FROM 'user_2'@'localhost'; FLUSH PRIVILEGES; ---replace_result $MASTER_MYPORT MYSQL_PORT $MASTER_MYSOCK MYSQL_SOCK connect (user6_5, localhost, user_2, , db_storedproc_1); --source suite/funcs_1/include/show_connection.inc --error ER_PROCACCESS_DENIED_ERROR diff --git a/mysql-test/suite/funcs_1/storedproc/storedproc_10.inc b/mysql-test/suite/funcs_1/storedproc/storedproc_10.inc index 83f5f2105c5..8382bcc1e55 100644 --- a/mysql-test/suite/funcs_1/storedproc/storedproc_10.inc +++ b/mysql-test/suite/funcs_1/storedproc/storedproc_10.inc @@ -58,7 +58,6 @@ GRANT CREATE ROUTINE ON db_storedproc.* TO 'user_1'@'localhost'; GRANT SELECT ON db_storedproc.* TO 'user_2'@'localhost'; FLUSH PRIVILEGES; ---replace_result $MASTER_MYPORT MYSQL_PORT $MASTER_MYSOCK MYSQL_SOCK connect (user2_1, localhost, user_1, , db_storedproc); --source suite/funcs_1/include/show_connection.inc @@ -80,7 +79,6 @@ delimiter ;// disconnect user2_1; ---replace_result $MASTER_MYPORT MYSQL_PORT $MASTER_MYSOCK MYSQL_SOCK connect (user2_2, localhost, user_2, , db_storedproc); --source suite/funcs_1/include/show_connection.inc @@ -102,7 +100,6 @@ FLUSH PRIVILEGES; disconnect user2_2; # new connection ---replace_result $MASTER_MYPORT MYSQL_PORT $MASTER_MYSOCK MYSQL_SOCK connect (user2_3, localhost, user_2, , db_storedproc); --source suite/funcs_1/include/show_connection.inc CALL sp31102(); @@ -121,7 +118,6 @@ FLUSH PRIVILEGES; CALL sp31102(); SELECT fn31105( 9 ); ---replace_result $MASTER_MYPORT MYSQL_PORT $MASTER_MYSOCK MYSQL_SOCK connect (user2_4, localhost, user_2, , db_storedproc); --source suite/funcs_1/include/show_connection.inc CALL sp31102(); diff --git a/mysql-test/suite/funcs_1/triggers/triggers_03.inc b/mysql-test/suite/funcs_1/triggers/triggers_03.inc index 9ef6a9ac9af..f48d1979f77 100644 --- a/mysql-test/suite/funcs_1/triggers/triggers_03.inc +++ b/mysql-test/suite/funcs_1/triggers/triggers_03.inc @@ -62,9 +62,7 @@ let $message= Testcase 3.5.3.2/6:; grant SELECT on priv_db.t1 to test_yesprivs@localhost; show grants for test_yesprivs@localhost; - --replace_result $MASTER_MYPORT MASTER_MYPORT $MASTER_MYSOCK MASTER_MYSOCK connect (no_privs,localhost,test_noprivs,PWD,test,$MASTER_MYPORT,$MASTER_MYSOCK); - --replace_result $MASTER_MYPORT MASTER_MYPORT $MASTER_MYSOCK MASTER_MYSOCK connect (yes_privs,localhost,test_yesprivs,PWD,test,$MASTER_MYPORT,$MASTER_MYSOCK); connection default; @@ -155,9 +153,7 @@ let $message=Testcase 3.5.3.7a:; grant TRIGGER, UPDATE on *.* to test_yesprivs@localhost; show grants for test_yesprivs@localhost; - --replace_result $MASTER_MYPORT MASTER_MYPORT $MASTER_MYSOCK MASTER_MYSOCK connect (no_privs_424a,localhost,test_noprivs,PWD,test,$MASTER_MYPORT,$MASTER_MYSOCK); - --replace_result $MASTER_MYPORT MASTER_MYPORT $MASTER_MYSOCK MASTER_MYSOCK connect (yes_privs_424a,localhost,test_yesprivs,PWD,test,$MASTER_MYPORT,$MASTER_MYSOCK); connection no_privs_424a; @@ -209,9 +205,7 @@ let $message= Testcase 3.5.3.7b:; grant UPDATE on priv_db.* to test_yesprivs@localhost; show grants for test_yesprivs@localhost; - --replace_result $MASTER_MYPORT MASTER_MYPORT $MASTER_MYSOCK MASTER_MYSOCK connect (no_privs_424b,localhost,test_noprivs,PWD,test,$MASTER_MYPORT,$MASTER_MYSOCK); - --replace_result $MASTER_MYPORT MASTER_MYPORT $MASTER_MYSOCK MASTER_MYSOCK connect (yes_privs_424b,localhost,test_yesprivs,PWD,test,$MASTER_MYPORT,$MASTER_MYSOCK); connection default; @@ -263,9 +257,7 @@ let $message= Testcase 3.5.3.7c; grant UPDATE on priv_db.t1 to test_yesprivs@localhost; show grants for test_yesprivs@localhost; - --replace_result $MASTER_MYPORT MASTER_MYPORT $MASTER_MYSOCK MASTER_MYSOCK connect (no_privs_424c,localhost,test_noprivs,PWD,test,$MASTER_MYPORT,$MASTER_MYSOCK); - --replace_result $MASTER_MYPORT MASTER_MYPORT $MASTER_MYSOCK MASTER_MYSOCK connect (yes_privs_424c,localhost,test_yesprivs,PWD,test,$MASTER_MYPORT,$MASTER_MYSOCK); connection default; @@ -316,9 +308,7 @@ let $message= Testcase 3.5.3.7d:; grant UPDATE (f1) on priv_db.t1 to test_yesprivs@localhost; show grants for test_noprivs; - --replace_result $MASTER_MYPORT MASTER_MYPORT $MASTER_MYSOCK MASTER_MYSOCK connect (no_privs_424d,localhost,test_noprivs,PWD,test,$MASTER_MYPORT,$MASTER_MYSOCK); - --replace_result $MASTER_MYPORT MASTER_MYPORT $MASTER_MYSOCK MASTER_MYSOCK connect (yes_privs_424d,localhost,test_yesprivs,PWD,test,$MASTER_MYPORT,$MASTER_MYSOCK); connection default; @@ -369,9 +359,7 @@ let $message= Testcase 3.5.3.8a:; grant TRIGGER, SELECT on *.* to test_yesprivs@localhost; show grants for test_yesprivs@localhost; - --replace_result $MASTER_MYPORT MASTER_MYPORT $MASTER_MYSOCK MASTER_MYSOCK connect (no_privs_425a,localhost,test_noprivs,PWD,test,$MASTER_MYPORT,$MASTER_MYSOCK); - --replace_result $MASTER_MYPORT MASTER_MYPORT $MASTER_MYSOCK MASTER_MYSOCK connect (yes_privs_425a,localhost,test_yesprivs,PWD,test,$MASTER_MYPORT,$MASTER_MYSOCK); connection default; @@ -426,9 +414,7 @@ let $message= Testcase: 3.5.3.8b; grant SELECT on priv_db.* to test_yesprivs@localhost; show grants for test_yesprivs@localhost; - --replace_result $MASTER_MYPORT MASTER_MYPORT $MASTER_MYSOCK MASTER_MYSOCK connect (no_privs_425b,localhost,test_noprivs,PWD,test,$MASTER_MYPORT,$MASTER_MYSOCK); - --replace_result $MASTER_MYPORT MASTER_MYPORT $MASTER_MYSOCK MASTER_MYSOCK connect (yes_privs_425b,localhost,test_yesprivs,PWD,test,$MASTER_MYPORT,$MASTER_MYSOCK); connection default; @@ -482,9 +468,7 @@ let $message= Testcase 3.5.3.8c:; grant SELECT on priv_db.t1 to test_yesprivs@localhost; show grants for test_yesprivs@localhost; - --replace_result $MASTER_MYPORT MASTER_MYPORT $MASTER_MYSOCK MASTER_MYSOCK connect (no_privs_425c,localhost,test_noprivs,PWD,test,$MASTER_MYPORT,$MASTER_MYSOCK); - --replace_result $MASTER_MYPORT MASTER_MYPORT $MASTER_MYSOCK MASTER_MYSOCK connect (yes_privs_425c,localhost,test_yesprivs,PWD,test,$MASTER_MYPORT,$MASTER_MYSOCK); connection default; @@ -534,9 +518,7 @@ let $message=Testcase: 3.5.3.8d:; grant SELECT (f1) on priv_db.t1 to test_yesprivs@localhost; show grants for test_noprivs@localhost; - --replace_result $MASTER_MYPORT MASTER_MYPORT $MASTER_MYSOCK MASTER_MYSOCK connect (no_privs_425d,localhost,test_noprivs,PWD,test,$MASTER_MYPORT,$MASTER_MYSOCK); - --replace_result $MASTER_MYPORT MASTER_MYPORT $MASTER_MYSOCK MASTER_MYSOCK connect (yes_privs_425d,localhost,test_yesprivs,PWD,test,$MASTER_MYPORT,$MASTER_MYSOCK); connection default; @@ -592,7 +574,6 @@ let $message=Testcase: 3.5.3.x:; grant SELECT on priv_db.t2 to test_yesprivs@localhost; show grants for test_yesprivs@localhost; - --replace_result $MASTER_MYPORT MASTER_MYPORT $MASTER_MYSOCK MASTER_MYSOCK connect (yes_353x,localhost,test_yesprivs,PWD,test,$MASTER_MYPORT,$MASTER_MYSOCK); connection yes_353x; diff --git a/mysql-test/suite/funcs_1/triggers/triggers_03e_columns.inc b/mysql-test/suite/funcs_1/triggers/triggers_03e_columns.inc index 475063587d4..2f0ad2c1ccc 100644 --- a/mysql-test/suite/funcs_1/triggers/triggers_03e_columns.inc +++ b/mysql-test/suite/funcs_1/triggers/triggers_03e_columns.inc @@ -36,10 +36,8 @@ let $message= ####### Testcase for column privileges of triggers: #######; grant SELECT,UPDATE on priv_db.* to test_noprivs@localhost; show grants for test_noprivs@localhost; - --replace_result $MASTER_MYPORT MASTER_MYPORT $MASTER_MYSOCK MASTER_MYSOCK connect (yes_privs,localhost,test_yesprivs,PWD,test,$MASTER_MYPORT,$MASTER_MYSOCK); - --replace_result $MASTER_MYPORT MASTER_MYPORT $MASTER_MYSOCK MASTER_MYSOCK connect (no_privs,localhost,test_noprivs,PWD,test,$MASTER_MYPORT,$MASTER_MYSOCK); # grant TRIGGER and UPDATE on column -> succeed diff --git a/mysql-test/suite/funcs_1/triggers/triggers_03e_db_level.inc b/mysql-test/suite/funcs_1/triggers/triggers_03e_db_level.inc index e5933eb84a8..9e6d8598e6f 100644 --- a/mysql-test/suite/funcs_1/triggers/triggers_03e_db_level.inc +++ b/mysql-test/suite/funcs_1/triggers/triggers_03e_db_level.inc @@ -37,7 +37,6 @@ let $message= Testcase for db level:; show grants for test_noprivs@localhost; # no trigger privilege->create trigger must fail: - --replace_result $MASTER_MYPORT MASTER_MYPORT $MASTER_MYSOCK MASTER_MYSOCK connect (yes_privs,localhost,test_yesprivs,PWD,test,$MASTER_MYPORT,$MASTER_MYSOCK); let $message= no trigger privilege on db level for create:; --source include/show_msg.inc @@ -47,7 +46,6 @@ let $message= no trigger privilege on db level for create:; set new.f1 = 'trig 1_1-no'; # user with minimum privs on t1->no trigger executed; - --replace_result $MASTER_MYPORT MASTER_MYPORT $MASTER_MYSOCK MASTER_MYSOCK connect (no_privs,localhost,test_noprivs,PWD,test,$MASTER_MYPORT,$MASTER_MYSOCK); use priv_db; insert into t1 (f1) values ('insert-yes'); diff --git a/mysql-test/suite/funcs_1/triggers/triggers_03e_db_table_mix.inc b/mysql-test/suite/funcs_1/triggers/triggers_03e_db_table_mix.inc index 82f4a28f664..2bbcc5f88f0 100644 --- a/mysql-test/suite/funcs_1/triggers/triggers_03e_db_table_mix.inc +++ b/mysql-test/suite/funcs_1/triggers/triggers_03e_db_table_mix.inc @@ -41,10 +41,8 @@ let $message= ####### Testcase for mix of db and table level: #######; grant SELECT,INSERT on priv2_db.* to test_noprivs@localhost; show grants for test_noprivs@localhost; - --replace_result $MASTER_MYPORT MASTER_MYPORT $MASTER_MYSOCK MASTER_MYSOCK connect (yes_privs,localhost,test_yesprivs,PWD,test,$MASTER_MYPORT,$MASTER_MYSOCK); use priv1_db; - --replace_result $MASTER_MYPORT MASTER_MYPORT $MASTER_MYSOCK MASTER_MYSOCK connect (no_privs,localhost,test_noprivs,PWD,test,$MASTER_MYPORT,$MASTER_MYSOCK); use priv1_db; diff --git a/mysql-test/suite/funcs_1/triggers/triggers_03e_definer.inc b/mysql-test/suite/funcs_1/triggers/triggers_03e_definer.inc index f1efff990f1..9988e1cafc2 100644 --- a/mysql-test/suite/funcs_1/triggers/triggers_03e_definer.inc +++ b/mysql-test/suite/funcs_1/triggers/triggers_03e_definer.inc @@ -27,7 +27,6 @@ let $message= ######### Testcase for definer: ########; revoke ALL PRIVILEGES, GRANT OPTION FROM test_yesprivs@localhost; - --replace_result $MASTER_MYPORT MASTER_MYPORT $MASTER_MYSOCK MASTER_MYSOCK connect (yes_privs,localhost,test_yesprivs,PWD,test,$MASTER_MYPORT,$MASTER_MYSOCK); # create trigger with not existing definer shall deliver a warning: diff --git a/mysql-test/suite/funcs_1/triggers/triggers_03e_global_db_mix.inc b/mysql-test/suite/funcs_1/triggers/triggers_03e_global_db_mix.inc index b6f4af7e0a7..eebdff5b588 100644 --- a/mysql-test/suite/funcs_1/triggers/triggers_03e_global_db_mix.inc +++ b/mysql-test/suite/funcs_1/triggers/triggers_03e_global_db_mix.inc @@ -38,10 +38,8 @@ let $message= #### Testcase for mix of user(global) and db level: ####; grant SELECT,INSERT on *.* to test_noprivs@localhost; show grants for test_noprivs@localhost; - --replace_result $MASTER_MYPORT MASTER_MYPORT $MASTER_MYSOCK MASTER_MYSOCK connect (yes_privs,localhost,test_yesprivs,PWD,test,$MASTER_MYPORT,$MASTER_MYSOCK); - --replace_result $MASTER_MYPORT MASTER_MYPORT $MASTER_MYSOCK MASTER_MYSOCK connect (no_privs,localhost,test_noprivs,PWD,test,$MASTER_MYPORT,$MASTER_MYSOCK); connection yes_privs; @@ -83,7 +81,6 @@ let $message= trigger privilege on user level for create:; --disable_warnings disconnect yes_privs; --enable_warnings - --replace_result $MASTER_MYPORT MASTER_MYPORT $MASTER_MYSOCK MASTER_MYSOCK connect (yes_privs,localhost,test_yesprivs,PWD,test,$MASTER_MYPORT,$MASTER_MYSOCK); select current_user; use priv_db; @@ -184,7 +181,6 @@ let $message= trigger privilege on db level for create:; --disable_warnings disconnect yes_privs; --enable_warnings - --replace_result $MASTER_MYPORT MASTER_MYPORT $MASTER_MYSOCK MASTER_MYSOCK connect (yes_privs,localhost,test_yesprivs,PWD,test,$MASTER_MYPORT,$MASTER_MYSOCK); select current_user; use no_priv_db; diff --git a/mysql-test/suite/funcs_1/triggers/triggers_03e_prepare.inc b/mysql-test/suite/funcs_1/triggers/triggers_03e_prepare.inc index ea7c385768c..6258b040642 100644 --- a/mysql-test/suite/funcs_1/triggers/triggers_03e_prepare.inc +++ b/mysql-test/suite/funcs_1/triggers/triggers_03e_prepare.inc @@ -32,7 +32,6 @@ let $message= #### Testcase for trigger privilege on execution time ########; revoke ALL PRIVILEGES, GRANT OPTION FROM test_yesprivs@localhost; revoke ALL PRIVILEGES, GRANT OPTION FROM test_useprivs@localhost; - --replace_result $MASTER_MYPORT MASTER_MYPORT $MASTER_MYSOCK MASTER_MYSOCK connect (yes_privs,localhost,test_yesprivs,PWD,test,$MASTER_MYPORT,$MASTER_MYSOCK); connection default; @@ -56,7 +55,6 @@ let $message= #### Testcase for trigger privilege on execution time ########; select f1 from t1 order by f1; prepare ins1 from 'insert into t1 (f1) values (''insert2-no'')'; - --replace_result $MASTER_MYPORT MASTER_MYPORT $MASTER_MYSOCK MASTER_MYSOCK connect (use_privs,localhost,test_useprivs,PWD,test,$MASTER_MYPORT,$MASTER_MYSOCK); select current_user; use priv_db; diff --git a/mysql-test/suite/funcs_1/triggers/triggers_03e_table_level.inc b/mysql-test/suite/funcs_1/triggers/triggers_03e_table_level.inc index 94f30fe13c2..ca4b9e2a0a9 100644 --- a/mysql-test/suite/funcs_1/triggers/triggers_03e_table_level.inc +++ b/mysql-test/suite/funcs_1/triggers/triggers_03e_table_level.inc @@ -30,10 +30,8 @@ let $message= ######### Testcase for table level: ########; set password for test_noprivs@localhost = password('PWD'); revoke ALL PRIVILEGES, GRANT OPTION FROM test_noprivs@localhost; - --replace_result $MASTER_MYPORT MASTER_MYPORT $MASTER_MYSOCK MASTER_MYSOCK connect (yes_privs,localhost,test_yesprivs,PWD,test,$MASTER_MYPORT,$MASTER_MYSOCK); - --replace_result $MASTER_MYPORT MASTER_MYPORT $MASTER_MYSOCK MASTER_MYSOCK connect (no_privs,localhost,test_noprivs,PWD,test,$MASTER_MYPORT,$MASTER_MYSOCK); ################ Section 3.5.3 ############ diff --git a/mysql-test/suite/funcs_1/triggers/triggers_03e_transaction.inc b/mysql-test/suite/funcs_1/triggers/triggers_03e_transaction.inc index e43f4ce97a3..2f72ba64bfd 100644 --- a/mysql-test/suite/funcs_1/triggers/triggers_03e_transaction.inc +++ b/mysql-test/suite/funcs_1/triggers/triggers_03e_transaction.inc @@ -27,7 +27,6 @@ let $message= ######### Testcase for transactions: ########; revoke ALL PRIVILEGES, GRANT OPTION FROM test_yesprivs@localhost; - --replace_result $MASTER_MYPORT MASTER_MYPORT $MASTER_MYSOCK MASTER_MYSOCK connect (yes_privs,localhost,test_yesprivs,PWD,test,$MASTER_MYPORT,$MASTER_MYSOCK); connection default; diff --git a/mysql-test/suite/funcs_1/triggers/triggers_0407.inc b/mysql-test/suite/funcs_1/triggers/triggers_0407.inc index d68b3d79086..2bc9dd66478 100644 --- a/mysql-test/suite/funcs_1/triggers/triggers_0407.inc +++ b/mysql-test/suite/funcs_1/triggers/triggers_0407.inc @@ -22,9 +22,7 @@ let $message= Testcase: 3.5:; create User test_super@localhost; set password for test_super@localhost = password('PWD'); grant ALL on *.* to test_super@localhost with grant OPTION; - --replace_result $MASTER_MYPORT MASTER_MYPORT $MASTER_MYSOCK MASTER_MYSOCK connect (con1_general,localhost,test_general,PWD,test,$MASTER_MYPORT,$MASTER_MYSOCK); - --replace_result $MASTER_MYPORT MASTER_MYPORT $MASTER_MYSOCK MASTER_MYSOCK connect (con1_super,localhost,test_super,PWD,test,$MASTER_MYPORT,$MASTER_MYSOCK); connection default; diff --git a/mysql-test/suite/funcs_1/triggers/triggers_08.inc b/mysql-test/suite/funcs_1/triggers/triggers_08.inc index 087f18e8e6b..996a5aa69ae 100644 --- a/mysql-test/suite/funcs_1/triggers/triggers_08.inc +++ b/mysql-test/suite/funcs_1/triggers/triggers_08.inc @@ -23,9 +23,7 @@ let $message= Testcase: 3.5:; create User test_super@localhost; set password for test_super@localhost = password('PWD'); grant ALL on *.* to test_super@localhost with grant OPTION; - --replace_result $MASTER_MYPORT MASTER_MYPORT $MASTER_MYSOCK MASTER_MYSOCK connect (con2_general,localhost,test_general,PWD,test,$MASTER_MYPORT,$MASTER_MYSOCK); - --replace_result $MASTER_MYPORT MASTER_MYPORT $MASTER_MYSOCK MASTER_MYSOCK connect (con2_super,localhost,test_super,PWD,test,$MASTER_MYPORT,$MASTER_MYSOCK); connection default; From 7f20e9fd060a5cc0f3c9c3e20f5167c0dab3bb5b Mon Sep 17 00:00:00 2001 From: Bjorn Munch Date: Mon, 22 Mar 2010 11:28:57 +0100 Subject: [PATCH 008/129] Bug #43603 mysqltest command disable_abort_on_error does not affect all built-in commands After disable_abort_on_error, behaved as if --error was in effect Add condition before die, as after queries --- client/mysqltest.cc | 20 ++++++++++++-------- mysql-test/r/mysqltest.result | 2 +- mysql-test/t/mysqltest.test | 9 +++++++++ 3 files changed, 22 insertions(+), 9 deletions(-) diff --git a/client/mysqltest.cc b/client/mysqltest.cc index 18af4088e68..e184061d4d3 100644 --- a/client/mysqltest.cc +++ b/client/mysqltest.cc @@ -1081,8 +1081,9 @@ void handle_command_error(struct st_command *command, uint error) command->first_word_len, command->query, error)); DBUG_VOID_RETURN; } - die("command \"%.*s\" failed with wrong error: %d", - command->first_word_len, command->query, error); + if (command->expected_errors.count > 0) + die("command \"%.*s\" failed with wrong error: %d", + command->first_word_len, command->query, error); } else if (command->expected_errors.err[0].type == ERR_ERRNO && command->expected_errors.err[0].code.errnum != 0) @@ -1352,14 +1353,14 @@ void log_msg(const char *fmt, ...) */ -void cat_file(DYNAMIC_STRING* ds, const char* filename) +int cat_file(DYNAMIC_STRING* ds, const char* filename) { int fd; size_t len; char buff[512]; if ((fd= my_open(filename, O_RDONLY, MYF(0))) < 0) - die("Failed to open file '%s'", filename); + return 1; while((len= my_read(fd, (uchar*)&buff, sizeof(buff), MYF(0))) > 0) { @@ -1383,6 +1384,7 @@ void cat_file(DYNAMIC_STRING* ds, const char* filename) dynstr_append_mem(ds, start, p-start); } my_close(fd, MYF(0)); + return 0; } @@ -2722,8 +2724,9 @@ void do_exec(struct st_command *command) else { dynstr_free(&ds_cmd); - die("command \"%s\" failed with wrong error: %d", - command->first_argument, status); + if (command->expected_errors.count > 0) + die("command \"%s\" failed with wrong error: %d", + command->first_argument, status); } } else if (command->expected_errors.err[0].type == ERR_ERRNO && @@ -3498,6 +3501,7 @@ void do_append_file(struct st_command *command) void do_cat_file(struct st_command *command) { + int error; static DYNAMIC_STRING ds_filename; const struct command_arg cat_file_args[] = { { "filename", ARG_STRING, TRUE, &ds_filename, "File to read from" } @@ -3512,8 +3516,8 @@ void do_cat_file(struct st_command *command) DBUG_PRINT("info", ("Reading from, file: %s", ds_filename.str)); - cat_file(&ds_res, ds_filename.str); - + error= cat_file(&ds_res, ds_filename.str); + handle_command_error(command, error); dynstr_free(&ds_filename); DBUG_VOID_RETURN; } diff --git a/mysql-test/r/mysqltest.result b/mysql-test/r/mysqltest.result index de7a3eefb6a..84412d2f387 100644 --- a/mysql-test/r/mysqltest.result +++ b/mysql-test/r/mysqltest.result @@ -572,7 +572,7 @@ if things work as expected Some data for cat_file command of mysqltest -mysqltest: At line 1: Failed to open file 'non_existing_file' +mysqltest: At line 1: command "cat_file" failed with error 1 mysqltest: At line 1: Missing required argument 'filename' to command 'file_exists' mysqltest: At line 1: Missing required argument 'from_file' to command 'copy_file' mysqltest: At line 1: Missing required argument 'to_file' to command 'copy_file' diff --git a/mysql-test/t/mysqltest.test b/mysql-test/t/mysqltest.test index 649a5fce366..09916f4f8cf 100644 --- a/mysql-test/t/mysqltest.test +++ b/mysql-test/t/mysqltest.test @@ -325,6 +325,15 @@ eval select $mysql_errno as "after_!errno_masked_error" ; --error 1 --exec echo "disable_abort_on_error; error 1000; select 3 from t1; error 1000; select 3 from t1;" | $MYSQL_TEST 2>&1 +# ---------------------------------------------------------------------------- +# Check some non-query statements that would fail +# ---------------------------------------------------------------------------- +--exec illegal_command +--cat_file does_not_exist +--perl + exit(1); +EOF + # ---------------------------------------------------------------------------- # Switch the abort on error on and check the effect on $mysql_errno # ---------------------------------------------------------------------------- From b83d5835d48d7cccd58aa2acd83ec2708c971e41 Mon Sep 17 00:00:00 2001 From: Bjorn Munch Date: Mon, 22 Mar 2010 11:32:17 +0100 Subject: [PATCH 009/129] Two more funcs_1 updates after 43588 --- mysql-test/suite/funcs_1/r/ndb_storedproc_06.result | 11 ----------- mysql-test/suite/funcs_1/r/ndb_storedproc_10.result | 4 ---- 2 files changed, 15 deletions(-) diff --git a/mysql-test/suite/funcs_1/r/ndb_storedproc_06.result b/mysql-test/suite/funcs_1/r/ndb_storedproc_06.result index 67d9c76ccac..ee1548fe012 100644 --- a/mysql-test/suite/funcs_1/r/ndb_storedproc_06.result +++ b/mysql-test/suite/funcs_1/r/ndb_storedproc_06.result @@ -78,7 +78,6 @@ grant all on db_storedproc_1.* to 'user_1'@'localhost'; revoke create routine on db_storedproc_1.* from 'user_1'@'localhost'; flush privileges; DROP PROCEDURE IF EXISTS sp1; -connect(localhost,user_1,,db_storedproc_1,MYSQL_PORT,MYSQL_SOCK); user_1@localhost db_storedproc_1 USE db_storedproc_1; @@ -91,7 +90,6 @@ USE db_storedproc_1; root@localhost db_storedproc_1 GRANT CREATE ROUTINE ON db_storedproc_1.* TO 'user_1'@'localhost'; -connect(localhost,user_1,,db_storedproc_1,MYSQL_PORT,MYSQL_SOCK); user_1@localhost db_storedproc_1 USE db_storedproc_1; @@ -112,7 +110,6 @@ Ensure that root always has the GRANT CREATE ROUTINE privilege. -------------------------------------------------------------------------------- grant create routine on db_storedproc_1.* to 'user_1'@'localhost'; flush privileges; -connect(localhost,user_1,,db_storedproc_1,MYSQL_PORT,MYSQL_SOCK); user_1@localhost db_storedproc_1 DROP PROCEDURE IF EXISTS sp3; @@ -149,7 +146,6 @@ CREATE PROCEDURE sp4(v1 char(20)) BEGIN SELECT * from db_storedproc_1.t6 where t6.f2= 'xyz'; END// -connect(localhost,user_1,,db_storedproc_1,MYSQL_PORT,MYSQL_SOCK); user_1@localhost db_storedproc_1 USE db_storedproc_1; @@ -191,7 +187,6 @@ grant create routine on db_storedproc_1.* to 'user_1'@'localhost'; grant SELECT on db_storedproc_1.* to 'user_2'@'localhost'; grant execute on db_storedproc_1.* to 'user_2'@'localhost'; flush privileges; -connect(localhost,user_1,,db_storedproc_1,MYSQL_PORT,MYSQL_SOCK); user_1@localhost db_storedproc_1 CREATE PROCEDURE sp5_s_i () sql security definer @@ -207,7 +202,6 @@ CREATE PROCEDURE sp5_ins () sql security definer BEGIN insert into db_storedproc_1.t3165 values ('inserted', 'from sp5_ins', 1000); END// -connect(localhost,user_2,,db_storedproc_1,MYSQL_PORT,MYSQL_SOCK); user_2@localhost db_storedproc_1 CALL sp5_s_i(); @@ -305,7 +299,6 @@ GRANT CREATE ROUTINE ON db_storedproc_1.* TO 'user_1'@'localhost'; GRANT SELECT ON db_storedproc_1.* TO 'user_2'@'localhost'; GRANT EXECUTE ON db_storedproc_1.* TO 'user_2'@'localhost'; FLUSH PRIVILEGES; -connect(localhost,user_1,,db_storedproc_1,MYSQL_PORT,MYSQL_SOCK); user_1@localhost db_storedproc_1 CREATE PROCEDURE sp3166_s_i () SQL SECURITY INVOKER @@ -321,7 +314,6 @@ CREATE PROCEDURE sp3166_ins () SQL SECURITY INVOKER BEGIN insert into db_storedproc_1.t3166 values ('inserted from sp3166_ins'); END// -connect(localhost,user_2,,db_storedproc_1,MYSQL_PORT,MYSQL_SOCK); user_2@localhost db_storedproc_1 CALL sp3166_s_i(); @@ -340,7 +332,6 @@ c1 inserted outside SP GRANT INSERT ON db_storedproc_1.* TO 'user_2'@'localhost'; FLUSH PRIVILEGES; -connect(localhost,user_2,,db_storedproc_1,MYSQL_PORT,MYSQL_SOCK); user_2@localhost db_storedproc_1 CALL sp3166_s_i(); @@ -361,7 +352,6 @@ inserted from sp3166_s_i inserted from sp3166_ins REVOKE SELECT ON db_storedproc_1.* FROM 'user_2'@'localhost'; FLUSH PRIVILEGES; -connect(localhost,user_2,,db_storedproc_1,MYSQL_PORT,MYSQL_SOCK); user_2@localhost db_storedproc_1 CALL sp3166_s_i(); @@ -379,7 +369,6 @@ inserted from sp3166_ins root@localhost db_storedproc_1 REVOKE EXECUTE on db_storedproc_1.* FROM 'user_2'@'localhost'; FLUSH PRIVILEGES; -connect(localhost,user_2,,db_storedproc_1,MYSQL_PORT,MYSQL_SOCK); user_2@localhost db_storedproc_1 CALL sp3166_s_i(); diff --git a/mysql-test/suite/funcs_1/r/ndb_storedproc_10.result b/mysql-test/suite/funcs_1/r/ndb_storedproc_10.result index 24ebd38e403..6591a138d73 100644 --- a/mysql-test/suite/funcs_1/r/ndb_storedproc_10.result +++ b/mysql-test/suite/funcs_1/r/ndb_storedproc_10.result @@ -81,7 +81,6 @@ create user 'user_2'@'localhost'; GRANT CREATE ROUTINE ON db_storedproc.* TO 'user_1'@'localhost'; GRANT SELECT ON db_storedproc.* TO 'user_2'@'localhost'; FLUSH PRIVILEGES; -connect(localhost,user_1,,db_storedproc,MYSQL_PORT,MYSQL_SOCK); user_1@localhost db_storedproc CREATE PROCEDURE sp31102 () SQL SECURITY INVOKER @@ -94,7 +93,6 @@ DECLARE res INT; SET res = n * n; RETURN res; END// -connect(localhost,user_2,,db_storedproc,MYSQL_PORT,MYSQL_SOCK); user_2@localhost db_storedproc CALL sp31102(); @@ -113,7 +111,6 @@ fn31105( 9 ) 81 GRANT EXECUTE ON db_storedproc.* TO 'user_2'@'localhost'; FLUSH PRIVILEGES; -connect(localhost,user_2,,db_storedproc,MYSQL_PORT,MYSQL_SOCK); user_2@localhost db_storedproc CALL sp31102(); @@ -134,7 +131,6 @@ a` a` 1000-01-01 -5000 a` -5000 SELECT fn31105( 9 ); fn31105( 9 ) 81 -connect(localhost,user_2,,db_storedproc,MYSQL_PORT,MYSQL_SOCK); user_2@localhost db_storedproc CALL sp31102(); From 9b9d01b31a5fc28bda47e1cf7f3191cc558b8be7 Mon Sep 17 00:00:00 2001 From: Bjorn Munch Date: Tue, 23 Mar 2010 15:01:40 +0100 Subject: [PATCH 010/129] Bug #52301 Add --protocol to mysqltest Implement as for other clients --- client/mysqltest.cc | 19 ++++++++++++++++--- 1 file changed, 16 insertions(+), 3 deletions(-) diff --git a/client/mysqltest.cc b/client/mysqltest.cc index e184061d4d3..4205d5518dc 100644 --- a/client/mysqltest.cc +++ b/client/mysqltest.cc @@ -188,6 +188,8 @@ static void init_re(void); static int match_re(my_regex_t *, char *); static void free_re(void); +static uint opt_protocol=0; + DYNAMIC_ARRAY q_lines; #include "sslopt-vars.h" @@ -5165,11 +5167,13 @@ void do_connect(struct st_command *command) #ifdef __WIN__ if (con_pipe) { - uint protocol= MYSQL_PROTOCOL_PIPE; - mysql_options(&con_slot->mysql, MYSQL_OPT_PROTOCOL, &protocol); + opt_protocol= MYSQL_PROTOCOL_PIPE; } #endif + if (opt_protocol) + mysql_options(&con_slot->mysql, MYSQL_OPT_PROTOCOL, (char*) &opt_protocol); + #ifdef HAVE_SMEM if (con_shm) { @@ -5886,6 +5890,8 @@ static struct my_option my_long_options[] = GET_INT, REQUIRED_ARG, 128, 8, 5120, 0, 0, 0}, {"password", 'p', "Password to use when connecting to server.", 0, 0, 0, GET_STR, OPT_ARG, 0, 0, 0, 0, 0, 0}, + {"protocol", OPT_MYSQL_PROTOCOL, "The protocol of connection (tcp,socket,pipe,memory).", + 0, 0, 0, GET_STR, REQUIRED_ARG, 0, 0, 0, 0, 0, 0}, {"port", 'P', "Port number to use for connection or 0 for default to, in " "order of preference, my.cnf, $MYSQL_TCP_PORT, " #if MYSQL_PORT_DEFAULT == 0 @@ -6023,7 +6029,7 @@ void read_embedded_server_arguments(const char *name) static my_bool -get_one_option(int optid, const struct my_option *opt __attribute__((unused)), +get_one_option(int optid, const struct my_option *opt, char *argument) { switch(optid) { @@ -6112,6 +6118,10 @@ get_one_option(int optid, const struct my_option *opt __attribute__((unused)), case 'V': print_version(); exit(0); + case OPT_MYSQL_PROTOCOL: + opt_protocol= find_type_or_exit(argument, &sql_protocol_typelib, + opt->name); + break; case '?': usage(); exit(0); @@ -7862,6 +7872,9 @@ int main(int argc, char **argv) mysql_options(&con->mysql, MYSQL_SET_CHARSET_DIR, opt_charsets_dir); + if (opt_protocol) + mysql_options(&con->mysql,MYSQL_OPT_PROTOCOL,(char*)&opt_protocol); + #ifdef HAVE_OPENSSL if (opt_use_ssl) From 5a5cbff970605952e1a086bf7a09d8b218fde5f6 Mon Sep 17 00:00:00 2001 From: Bjorn Munch Date: Tue, 13 Apr 2010 10:01:04 +0200 Subject: [PATCH 011/129] Bug #42513 mtr2: mysqltest doesn't count internal commands output as real output MTR insited in exit; if run without result file Simply remove the else part producing the error and let test finish --- client/mysqltest.cc | 10 ---------- 1 file changed, 10 deletions(-) diff --git a/client/mysqltest.cc b/client/mysqltest.cc index 4205d5518dc..57dcb258221 100644 --- a/client/mysqltest.cc +++ b/client/mysqltest.cc @@ -8311,16 +8311,6 @@ int main(int argc, char **argv) check_result(); } } - else - { - /* - No result_file_name specified, the result - has been printed to stdout, exit with error - unless script has called "exit" to indicate success - */ - if (abort_flag == 0) - die("Exit with failure! Call 'exit' in script to return with sucess"); - } } else { From d5e9a45efdc0edd1ce5bb9741b0c1750e3a23b43 Mon Sep 17 00:00:00 2001 From: Bjorn Munch Date: Tue, 13 Apr 2010 12:41:42 +0200 Subject: [PATCH 012/129] Bug #52214 Misleading error msg when test fails before having produced any query output Print error message only if real error --- client/mysqltest.cc | 7 +++++-- 1 file changed, 5 insertions(+), 2 deletions(-) diff --git a/client/mysqltest.cc b/client/mysqltest.cc index 57dcb258221..878de31d4ed 100644 --- a/client/mysqltest.cc +++ b/client/mysqltest.cc @@ -610,8 +610,11 @@ public: if ((bytes= fread(buf, 1, sizeof(buf), m_file)) <= 0) { - fprintf(stderr, "Failed to read from '%s', errno: %d\n", - m_file_name, errno); + // ferror=0 will happen here if no queries executed yet + if (ferror(m_file)) + fprintf(stderr, + "Failed to read from '%s', errno: %d, feof:%d, ferror:%d\n", + m_file_name, errno, feof(m_file), ferror(m_file)); DBUG_VOID_RETURN; } From bb6e8b6942333e523f50d3e0bdda7b61b9fff1da Mon Sep 17 00:00:00 2001 From: Bjorn Munch Date: Mon, 7 Jun 2010 13:30:23 +0200 Subject: [PATCH 013/129] Bug #53374 Don't delete temporary perl file if perl fails Simple condition on the delete stmt But NB: next mtr run will clean up and remove the temp file --- client/mysqltest.cc | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/client/mysqltest.cc b/client/mysqltest.cc index 217428f7db3..a3ae0ebb18c 100644 --- a/client/mysqltest.cc +++ b/client/mysqltest.cc @@ -3785,8 +3785,9 @@ void do_perl(struct st_command *command) } error= pclose(res_file); - /* Remove the temporary file */ - my_delete(temp_file_path, MYF(0)); + /* Remove the temporary file, but keep it if perl failed */ + if (!error) + my_delete(temp_file_path, MYF(0)); handle_command_error(command, WEXITSTATUS(error)); } From 30e69ec03b4ad59da4060edde76636ca06c0e596 Mon Sep 17 00:00:00 2001 From: Bjorn Munch Date: Wed, 9 Jun 2010 10:21:46 +0200 Subject: [PATCH 014/129] Bug #53949 Allow MTR2 to start server without hardcoded command-line options Added option --user-args, to be used with --start* Only keeps --defaults-file and --defaults-group-suffix Also added missing help text entry for --start-and-exit --- mysql-test/mysql-test-run.pl | 29 +++++++++++++++++++++++++---- 1 file changed, 25 insertions(+), 4 deletions(-) diff --git a/mysql-test/mysql-test-run.pl b/mysql-test/mysql-test-run.pl index 91ae508422f..9e29de89406 100755 --- a/mysql-test/mysql-test-run.pl +++ b/mysql-test/mysql-test-run.pl @@ -221,6 +221,7 @@ my $opt_start_dirty; my $opt_start_exit; my $start_only; my $opt_wait_all; +my $opt_user_args; my $opt_repeat= 1; my $opt_retry= 3; my $opt_retry_failure= env_or_val(MTR_RETRY_FAILURE => 2); @@ -921,6 +922,7 @@ sub command_line_setup { 'start-dirty' => \$opt_start_dirty, 'start-and-exit' => \$opt_start_exit, 'start' => \$opt_start, + 'user-args' => \$opt_user_args, 'wait-all' => \$opt_wait_all, 'print-testcases' => \&collect_option, 'repeat=i' => \$opt_repeat, @@ -1331,13 +1333,24 @@ sub command_line_setup { $start_only= 1; } + # -------------------------------------------------------------------------- + # Check use of user-args + # -------------------------------------------------------------------------- + + if ($opt_user_args) { + mtr_error("--user-args only valid with --start options") + unless $start_only; + mtr_error("--user-args cannot be combined with named suites or tests") + if $opt_suites || @opt_cases; + } + # -------------------------------------------------------------------------- # Check use of wait-all # -------------------------------------------------------------------------- if ($opt_wait_all && ! $start_only) { - mtr_error("--wait-all can only be used with --start or --start-dirty"); + mtr_error("--wait-all can only be used with --start options"); } # -------------------------------------------------------------------------- @@ -4252,7 +4265,7 @@ sub mysqld_arguments ($$$) { } } - if ( $mysql_version_id >= 50106 ) + if ( $mysql_version_id >= 50106 && !$opt_user_args) { # Turn on logging to file mtr_add_arg($args, "--log-output=file"); @@ -4290,7 +4303,7 @@ sub mysqld_arguments ($$$) { } } $opt_skip_core = $found_skip_core; - if ( !$found_skip_core ) + if ( !$found_skip_core && !$opt_user_args ) { mtr_add_arg($args, "%s", "--core-file"); } @@ -4298,7 +4311,7 @@ sub mysqld_arguments ($$$) { # Enable the debug sync facility, set default wait timeout. # Facility stays disabled if timeout value is zero. mtr_add_arg($args, "--loose-debug-sync-timeout=%s", - $opt_debug_sync_timeout); + $opt_debug_sync_timeout) unless $opt_user_args; return $args; } @@ -4596,6 +4609,9 @@ sub envsubst { sub get_extra_opts { + # No extra options if --user-args + return \@opt_extra_mysqld_opt if $opt_user_args; + my ($mysqld, $tinfo)= @_; my $opts= @@ -5468,8 +5484,13 @@ Misc options startup settings for the first specified test case Example: $0 --start alias & + start-and-exit Same as --start, but mysql-test-run terminates and + leaves just the server running start-dirty Only start the servers (without initialization) for the first specified test case + user-args In combination with start* and no test name, drops + arguments to mysqld except those speficied with + --mysqld (if any) wait-all If --start or --start-dirty option is used, wait for all servers to exit before finishing the process fast Run as fast as possible, dont't wait for servers From c9d57b0c0f30739b64d30f0a57b1b72e20f07f50 Mon Sep 17 00:00:00 2001 From: Bjorn Munch Date: Thu, 10 Jun 2010 10:34:16 +0200 Subject: [PATCH 015/129] Bug #54364 Allow multiple --experimental command line options for MTR Convert --experimental into a multi option Size of diff is caused by intenting code put into a for loop --- mysql-test/lib/mtr_report.pm | 2 +- mysql-test/mysql-test-run.pl | 66 +++++++++++++++++++----------------- 2 files changed, 36 insertions(+), 32 deletions(-) diff --git a/mysql-test/lib/mtr_report.pm b/mysql-test/lib/mtr_report.pm index 1c4b940bbee..77f6920771d 100644 --- a/mysql-test/lib/mtr_report.pm +++ b/mysql-test/lib/mtr_report.pm @@ -124,7 +124,7 @@ sub mtr_report_test ($) { my $timest = format_time(); my $fail = "fail"; - if ( $::opt_experimental ) + if ( @$::experimental_test_cases ) { # Find out if this test case is an experimental one, so we can treat # the failure as an expected failure instead of a regression. diff --git a/mysql-test/mysql-test-run.pl b/mysql-test/mysql-test-run.pl index 91ae508422f..46a9fdafdbf 100755 --- a/mysql-test/mysql-test-run.pl +++ b/mysql-test/mysql-test-run.pl @@ -187,7 +187,7 @@ our $opt_client_debugger; my $config; # The currently running config my $current_config_name; # The currently running config file template -our $opt_experimental; +our @opt_experimentals; our $experimental_test_cases; my $baseport; @@ -846,7 +846,7 @@ sub command_line_setup { 'big-test' => \$opt_big_test, 'combination=s' => \@opt_combinations, 'skip-combinations' => \&collect_option, - 'experimental=s' => \$opt_experimental, + 'experimental=s' => \@opt_experimentals, 'skip-im' => \&ignore_option, # Specify ports @@ -1028,43 +1028,47 @@ sub command_line_setup { mtr_print_thick_line('#'); } - if ( $opt_experimental ) + if ( @opt_experimentals ) { # $^O on Windows considered not generic enough my $plat= (IS_WINDOWS) ? 'windows' : $^O; - # read the list of experimental test cases from the file specified on + # read the list of experimental test cases from the files specified on # the command line - open(FILE, "<", $opt_experimental) or mtr_error("Can't read experimental file: $opt_experimental"); - mtr_report("Using experimental file: $opt_experimental"); $experimental_test_cases = []; - while() { - chomp; - # remove comments (# foo) at the beginning of the line, or after a - # blank at the end of the line - s/( +|^)#.*$//; - # If @ platform specifier given, use this entry only if it contains - # @ or @! where xxx != platform - if (/\@.*/) - { - next if (/\@!$plat/); - next unless (/\@$plat/ or /\@!/); - # Then remove @ and everything after it - s/\@.*$//; + foreach my $exp_file (@opt_experimentals) + { + open(FILE, "<", $exp_file) + or mtr_error("Can't read experimental file: $exp_file"); + mtr_report("Using experimental file: $exp_file"); + while() { + chomp; + # remove comments (# foo) at the beginning of the line, or after a + # blank at the end of the line + s/( +|^)#.*$//; + # If @ platform specifier given, use this entry only if it contains + # @ or @! where xxx != platform + if (/\@.*/) + { + next if (/\@!$plat/); + next unless (/\@$plat/ or /\@!/); + # Then remove @ and everything after it + s/\@.*$//; + } + # remove whitespace + s/^ +//; + s/ +$//; + # if nothing left, don't need to remember this line + if ( $_ eq "" ) { + next; + } + # remember what is left as the name of another test case that should be + # treated as experimental + print " - $_\n"; + push @$experimental_test_cases, $_; } - # remove whitespace - s/^ +//; - s/ +$//; - # if nothing left, don't need to remember this line - if ( $_ eq "" ) { - next; - } - # remember what is left as the name of another test case that should be - # treated as experimental - print " - $_\n"; - push @$experimental_test_cases, $_; + close FILE; } - close FILE; } foreach my $arg ( @ARGV ) From 145b1fe1f9e1327d076a0f5dd9732b93b65dd7b0 Mon Sep 17 00:00:00 2001 From: Bjorn Munch Date: Mon, 14 Jun 2010 15:34:43 +0200 Subject: [PATCH 016/129] Bug #54368 MTR does not recognize carriage return in --defaults-file Remove any leftover trailing ^M from lines read in --- mysql-test/lib/My/Config.pm | 2 ++ 1 file changed, 2 insertions(+) diff --git a/mysql-test/lib/My/Config.pm b/mysql-test/lib/My/Config.pm index f8416e3df3a..315e415e219 100644 --- a/mysql-test/lib/My/Config.pm +++ b/mysql-test/lib/My/Config.pm @@ -188,6 +188,8 @@ sub new { while ( my $line= <$F> ) { chomp($line); + # Remove any trailing CR from Windows edited files + $line=~ s/\cM$//; # [group] if ( $line =~ /^\[(.*)\]/ ) { From 070064f2d48d9f697f4b24c0995bca523d5be6b0 Mon Sep 17 00:00:00 2001 From: Bjorn Munch Date: Tue, 15 Jun 2010 11:16:38 +0200 Subject: [PATCH 017/129] Bug #52321 mtr test suite paths need to be updated Use $suitedir instead of $basedir to find suites Add 'testdir' to ConfigFactory --- mysql-test/lib/My/ConfigFactory.pm | 11 +++++++++-- mysql-test/lib/mtr_cases.pm | 8 ++++---- mysql-test/mysql-test-run.pl | 2 ++ 3 files changed, 15 insertions(+), 6 deletions(-) diff --git a/mysql-test/lib/My/ConfigFactory.pm b/mysql-test/lib/My/ConfigFactory.pm index 41b595c80e8..342390edef8 100644 --- a/mysql-test/lib/My/ConfigFactory.pm +++ b/mysql-test/lib/My/ConfigFactory.pm @@ -30,6 +30,13 @@ sub get_basedir { return $basedir; } +sub get_testdir { + my ($self, $group)= @_; + my $testdir= $group->if_exist('testdir') || + $self->{ARGS}->{testdir}; + return $testdir; +} + sub fix_charset_dir { my ($self, $config, $group_name, $group)= @_; @@ -142,8 +149,8 @@ sub fix_secure_file_priv { sub fix_std_data { my ($self, $config, $group_name, $group)= @_; - my $basedir= $self->get_basedir($group); - return "$basedir/mysql-test/std_data"; + my $testdir= $self->get_testdir($group); + return "$testdir/std_data"; } sub ssl_supported { diff --git a/mysql-test/lib/mtr_cases.pm b/mysql-test/lib/mtr_cases.pm index 0ef993aa92d..835ae6319fa 100644 --- a/mysql-test/lib/mtr_cases.pm +++ b/mysql-test/lib/mtr_cases.pm @@ -266,11 +266,11 @@ sub collect_one_suite($) } else { - $suitedir= my_find_dir($::basedir, - ["mysql-test/suite", - "mysql-test", + $suitedir= my_find_dir($suitedir, + ["suite", + ".", # Look in storage engine specific suite dirs - "storage/*/mysql-test-suites" + "../storage/*/mysql-test-suites" ], [$suite]); } diff --git a/mysql-test/mysql-test-run.pl b/mysql-test/mysql-test-run.pl index 91ae508422f..f58e78d5b77 100755 --- a/mysql-test/mysql-test-run.pl +++ b/mysql-test/mysql-test-run.pl @@ -2742,6 +2742,7 @@ sub default_mysqld { my $config= My::ConfigFactory->new_config ( { basedir => $basedir, + testdir => $glob_mysql_test_dir, template_path => "include/default_my.cnf", vardir => $opt_vardir, tmpdir => $opt_tmpdir, @@ -3350,6 +3351,7 @@ sub run_testcase ($) { $config= My::ConfigFactory->new_config ( { basedir => $basedir, + testdir => $glob_mysql_test_dir, template_path => $tinfo->{template_path}, extra_template_path => $tinfo->{extra_template_path}, vardir => $opt_vardir, From 7f6ffe9a36099d94a68a5b44515464b07ca07768 Mon Sep 17 00:00:00 2001 From: Bjorn Munch Date: Tue, 15 Jun 2010 11:29:24 +0200 Subject: [PATCH 018/129] Bug #54111 mysqltest command remove_files_wildcard does not work in embedded server Wildcard chars are changed in embedded mode Temporarily reset the wild_* variables before wild_compare, also for list_files --- client/mysqltest.cc | 42 ++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 42 insertions(+) diff --git a/client/mysqltest.cc b/client/mysqltest.cc index a3ae0ebb18c..ba8e882f33e 100644 --- a/client/mysqltest.cc +++ b/client/mysqltest.cc @@ -2875,6 +2875,41 @@ void do_system(struct st_command *command) } +/* + SYNOPSIS + set_wild_chars + set true to set * etc. as wild char, false to reset + + DESCRIPTION + Auxiliary function to set "our" wild chars before calling wild_compare + This is needed because the default values are changed to SQL syntax + in mysqltest_embedded. +*/ + +void set_wild_chars (my_bool set) +{ + static char old_many= 0, old_one, old_prefix; + + if (set) + { + if (wild_many == '*') return; // No need + old_many= wild_many; + old_one= wild_one; + old_prefix= wild_prefix; + wild_many= '*'; + wild_one= '?'; + wild_prefix= 0; + } + else + { + if (! old_many) return; // Was not set + wild_many= old_many; + wild_one= old_one; + wild_prefix= old_prefix; + } +} + + /* SYNOPSIS do_remove_file @@ -2951,6 +2986,10 @@ void do_remove_files_wildcard(struct st_command *command) dir_separator[0]= FN_LIBCHAR; dir_separator[1]= 0; dynstr_append(&ds_file_to_remove, dir_separator); + + /* Set default wild chars for wild_compare, is changed in embedded mode */ + set_wild_chars(1); + for (i= 0; i < (uint) dir_info->number_off_files; i++) { file= dir_info->dir_entry + i; @@ -2970,6 +3009,7 @@ void do_remove_files_wildcard(struct st_command *command) if (error) break; } + set_wild_chars(0); my_dirend(dir_info); end: @@ -3211,6 +3251,7 @@ static int get_list_files(DYNAMIC_STRING *ds, const DYNAMIC_STRING *ds_dirname, /* Note that my_dir sorts the list if not given any flags */ if (!(dir_info= my_dir(ds_dirname->str, MYF(0)))) DBUG_RETURN(1); + set_wild_chars(1); for (i= 0; i < (uint) dir_info->number_off_files; i++) { file= dir_info->dir_entry + i; @@ -3224,6 +3265,7 @@ static int get_list_files(DYNAMIC_STRING *ds, const DYNAMIC_STRING *ds_dirname, dynstr_append(ds, file->name); dynstr_append(ds, "\n"); } + set_wild_chars(0); my_dirend(dir_info); DBUG_RETURN(0); } From 9edbfe0f4cf9cf53a673bd7e2cf5a56ef4ff08de Mon Sep 17 00:00:00 2001 From: Bjorn Munch Date: Tue, 15 Jun 2010 13:37:53 +0200 Subject: [PATCH 019/129] Bug #54364 Allow multiple --experimental command line options for MTR Bummer: MTR fails if a test fails and no --experimental is used $experimental_test_cases must be intialized --- mysql-test/mysql-test-run.pl | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/mysql-test/mysql-test-run.pl b/mysql-test/mysql-test-run.pl index e802c8807a4..fce8ce5ec1c 100755 --- a/mysql-test/mysql-test-run.pl +++ b/mysql-test/mysql-test-run.pl @@ -188,7 +188,7 @@ my $config; # The currently running config my $current_config_name; # The currently running config file template our @opt_experimentals; -our $experimental_test_cases; +our $experimental_test_cases= []; my $baseport; # $opt_build_thread may later be set from $opt_port_base From 429454f76ecfbc107fafeb25a33ef4d90f221fc0 Mon Sep 17 00:00:00 2001 From: Konstantin Osipov Date: Fri, 18 Jun 2010 20:14:10 +0400 Subject: [PATCH 020/129] A new implementation for the TABLE_SHARE cache in MDL subsystem. Fix a number of caveates that the previous implementation suffered from, including unprotected access to shared data and lax resource accounting (share->ref_count) that could lead to deadlocks. The new implementation still suffers from a number of potential deadlocks in some edge cases, and this is still not enabled by default. Especially since performance testing has shown that it gives only marginable (not even exceeding measuring accuracy) improvements. @todo: - Remove calls to close_cached_tables() with REFRESH_FAST, and have_lock, because they break the MDL cache. - rework FLUSH TABLES to not use close_cached_tables() - make sure that whenever we set TABLE_SHARE::version to 0 we free MDL cache references to it. sql/mdl.cc: We may cache references to TABLE_SHARE objects in MDL_lock objects for tables. Create a separate MDL_lock class to represent a table. sql/mdl.h: Adjust the MDL caching API to avoid races. sql/sql_base.cc: Move all caching functionality close together. Implement a solution for deadlocks caused by close_cached_tables() when MDL cache is enabled (incomplete). sql/sql_yacc.yy: Adjust FLUSH rule to do the necessary initialization of TABLE_LIST elements used in for FLUSH TABLES , and thus work OK with flush_mdl_cache() function. --- sql/mdl.cc | 82 ++++++++++++------- sql/mdl.h | 5 +- sql/sql_base.cc | 209 +++++++++++++++++++++++++++++++++++++----------- sql/sql_yacc.yy | 12 ++- 4 files changed, 228 insertions(+), 80 deletions(-) diff --git a/sql/mdl.cc b/sql/mdl.cc index 184b3c6051d..22ad15d2360 100644 --- a/sql/mdl.cc +++ b/sql/mdl.cc @@ -284,8 +284,8 @@ public: public: /** The key of the object (data) being protected. */ MDL_key key; - void *cached_object; - mdl_cached_object_release_hook cached_object_release_hook; + /** A cached reference to the TABLE_SHARE. Protected by LOCK_open. */ + void *m_cached_object; /** Read-write lock protecting this lock context. @@ -362,8 +362,7 @@ public: MDL_lock(const MDL_key *key_arg) : key(key_arg), - cached_object(NULL), - cached_object_release_hook(NULL), + m_cached_object(NULL), m_ref_usage(0), m_ref_release(0), m_is_destroyed(FALSE) @@ -371,6 +370,8 @@ public: mysql_prlock_init(key_MDL_lock_rwlock, &m_rwlock); } + /* Overridden for TABLE objects, to support TABLE_SHARE cache in MDL. */ + virtual void release_cached_object() {} virtual ~MDL_lock() { mysql_prlock_destroy(&m_rwlock); @@ -458,6 +459,25 @@ private: }; +/** + A lock implementation for MDL_key::TABLE. +*/ + +class MDL_table_lock: public MDL_object_lock +{ +public: + MDL_table_lock(const MDL_key *key_arg) + : MDL_object_lock(key_arg) + { } +#ifdef DISABLED_UNTIL_GRL_IS_MADE_PART_OF_MDL + virtual void release_cached_object() + { + tdc_release_cached_share(&m_cached_object); + } +#endif +}; + + static MDL_map mdl_locks; extern "C" @@ -674,8 +694,7 @@ void MDL_map::remove(MDL_lock *lock) { uint ref_usage, ref_release; - if (lock->cached_object) - (*lock->cached_object_release_hook)(lock->cached_object); + lock->release_cached_object(); /* Destroy the MDL_lock object, but ensure that anyone that is @@ -839,6 +858,8 @@ inline MDL_lock *MDL_lock::create(const MDL_key *mdl_key) { case MDL_key::GLOBAL: return new MDL_global_lock(mdl_key); + case MDL_key::TABLE: + return new MDL_table_lock(mdl_key); default: return new MDL_object_lock(mdl_key); } @@ -1181,11 +1202,6 @@ void MDL_lock::reschedule_waiters() */ m_waiting.remove_ticket(ticket); m_granted.add_ticket(ticket); - - /* If we are granting an X lock, release the cached object. */ - if (ticket->get_type() == MDL_EXCLUSIVE && cached_object) - (*cached_object_release_hook)(cached_object); - cached_object= NULL; } /* If we could not update the wait slot of the waiter, @@ -1655,14 +1671,13 @@ MDL_context::try_acquire_lock_impl(MDL_request *mdl_request, { lock->m_granted.add_ticket(ticket); - if (mdl_request->type == MDL_EXCLUSIVE && lock->cached_object) - (*lock->cached_object_release_hook)(lock->cached_object); - lock->cached_object= NULL; - mysql_prlock_unlock(&lock->m_rwlock); m_tickets.push_front(ticket); + if (ticket->get_type() == MDL_EXCLUSIVE) + ticket->clear_cached_object(); + mdl_request->ticket= ticket; } else @@ -1864,6 +1879,9 @@ MDL_context::acquire_lock(MDL_request *mdl_request, ulong lock_wait_timeout) */ DBUG_ASSERT(wait_status == MDL_wait::GRANTED); + if (ticket->get_type() == MDL_EXCLUSIVE) + ticket->clear_cached_object(); + m_tickets.push_front(ticket); mdl_request->ticket= ticket; @@ -2450,7 +2468,7 @@ bool MDL_ticket::has_pending_conflicting_lock() const This function has the following usage pattern: - try to acquire an MDL lock - - when done, call for mdl_get_cached_object(). If it returns NULL, our + - when done, call for get_cached_object(). If it returns NULL, our thread has the only lock on this table. - look up TABLE_SHARE in the table definition cache - call mdl_set_cache_object() to assign the share to the opaque pointer. @@ -2460,28 +2478,33 @@ bool MDL_ticket::has_pending_conflicting_lock() const */ void -MDL_ticket::set_cached_object(void *cached_object, - mdl_cached_object_release_hook release_hook) +MDL_ticket::set_cached_object(void *cached_object) { - DBUG_ENTER("mdl_set_cached_object"); + DBUG_ENTER("MDL_ticket::set_cached_object"); DBUG_PRINT("enter", ("db=%s name=%s cached_object=%p", m_lock->key.db_name(), m_lock->key.name(), cached_object)); - /* - TODO: This assumption works now since we do get_cached_object() - and set_cached_object() in the same critical section. Once - this becomes false we will have to call release_hook here and - use additional mutex protecting 'cached_object' member. - */ - DBUG_ASSERT(!m_lock->cached_object); + mysql_mutex_assert_owner(&LOCK_open); + DBUG_ASSERT(m_lock->key.mdl_namespace() == MDL_key::TABLE); + DBUG_ASSERT(!m_lock->m_cached_object); - m_lock->cached_object= cached_object; - m_lock->cached_object_release_hook= release_hook; + m_lock->m_cached_object= cached_object; DBUG_VOID_RETURN; } +/** + A helper function to flush the table share cached in MDL. + @pre The ticket is acquired. +*/ + +void MDL_ticket::clear_cached_object() +{ + m_lock->release_cached_object(); +} + + /** Get a pointer to an opaque object that associated with the lock. @@ -2492,7 +2515,8 @@ MDL_ticket::set_cached_object(void *cached_object, void *MDL_ticket::get_cached_object() { - return m_lock->cached_object; + mysql_mutex_assert_owner(&LOCK_open); + return m_lock->m_cached_object; } diff --git a/sql/mdl.h b/sql/mdl.h index 43d88c143c0..ad3945f524c 100644 --- a/sql/mdl.h +++ b/sql/mdl.h @@ -397,8 +397,8 @@ public: bool has_pending_conflicting_lock() const; void *get_cached_object(); - void set_cached_object(void *cached_object, - mdl_cached_object_release_hook release_hook); + void set_cached_object(void *cached_object); + void clear_cached_object(); MDL_context *get_ctx() const { return m_ctx; } bool is_upgradable_or_exclusive() const { @@ -724,6 +724,7 @@ extern "C" const char *set_thd_proc_info(void *thd_arg, const char *info, const char *calling_function, const char *calling_file, const unsigned int calling_line); +extern void tdc_release_cached_share(void *ptr); #ifndef DBUG_OFF extern mysql_mutex_t LOCK_open; #endif diff --git a/sql/sql_base.cc b/sql/sql_base.cc index 78862985e97..bd73dd57367 100644 --- a/sql/sql_base.cc +++ b/sql/sql_base.cc @@ -755,27 +755,6 @@ TABLE_SHARE *get_cached_table_share(const char *db, const char *table_name) } -#ifdef DISABLED_UNTIL_GRL_IS_MADE_PART_OF_MDL -/** - @brief Mark table share as having one more user (increase its reference - count). - - @param share Table share for which reference count should be increased. -*/ - -static void reference_table_share(TABLE_SHARE *share) -{ - DBUG_ENTER("reference_table_share"); - DBUG_ASSERT(share->ref_count); - mysql_mutex_assert_owner(&LOCK_open); - share->ref_count++; - DBUG_PRINT("exit", ("share: 0x%lx ref_count: %u", - (ulong) share, share->ref_count)); - DBUG_VOID_RETURN; -} -#endif - - /* Create a list for all open tables matching SQL expression @@ -941,6 +920,141 @@ static void kill_delayed_threads_for_table(TABLE_SHARE *share) } +#ifdef DISABLED_UNTIL_GRL_IS_MADE_PART_OF_MDL +/** + Flush MDL cached objects. + + How MDL table share cache works + ------------------------------- + Since we take a table share from the table definition + cache only after taking an MDL lock, the MDL lock + object is a convenient place to cache a pointer + to the table share. However, not all SQL in MySQL + takes an MDL lock prior to working with the TDC, + various forms of FLUSH TABLES (including SET GLOBAL + read_only) being the one and only exception. + + To make FLUSH TABLES work, and avoid having dangling + references to TABLE_SHARE objects in MDL subsystem + after a flush, we make sure that all references + to table shares are released whenever a flush comes. + This is done in this function. + + To sum up, the following invariants are held: + - no statement can work with a TABLE_SHARE without + a metadata lock. The only exception is FLUSH TABLES. + - a metadata lock object can be used to store + a cached reference (pointer) to the corresponding + TABLE_SHARE, if and only if this TABLE_SHARE is + not stale (version == refresh_version). In other words, + checking TABLE_SHARE version and setting the reference + must happen only in the same critical section protected + by LOCK_open. + - FLUSH will mark all subject TABLE_SHARE objects + as stale, and then will manually release all TABLE_SHARE + references in MDL cache. Since marking TABLE_SHARE + objects is done inside a critical section protected + by LOCK_open and prior to calling flush_mdl_cache(), + it's guaranteed that a flush will take place before + a new reference to the table share is established + in some other connection. +*/ + +bool flush_mdl_cache(THD *thd, TABLE_LIST *table_list) +{ + MDL_request_list mdl_requests; + MDL_request *mdl_request; + + DBUG_ENTER("flush_mdl_cache"); + + if (table_list == NULL) + { + mysql_mutex_lock(&LOCK_open); + for (uint idx= 0 ; idx < table_def_cache.records; idx++) + { + TABLE_SHARE *share=(TABLE_SHARE*) my_hash_element(&table_def_cache, + idx); + if (share->needs_reopen()) + { + mdl_request= MDL_request::create(MDL_key::TABLE, + share->db.str, + share->table_name.str, + MDL_SHARED_HIGH_PRIO, + thd->mem_root); + if (! mdl_request) + { + mysql_mutex_unlock(&LOCK_open); + DBUG_RETURN(TRUE); + } + mdl_requests.push_front(mdl_request); + } + } + mysql_mutex_unlock(&LOCK_open); + } + else + { + for (TABLE_LIST *tables= table_list; tables; tables= tables->next_global) + { + DBUG_ASSERT(tables->mdl_request.type == MDL_SHARED_HIGH_PRIO); + mdl_requests.push_front(&tables->mdl_request); + } + } + + for (MDL_request_list::Iterator it(mdl_requests); + (mdl_request= it++); ) + { + if (thd->mdl_context.try_acquire_lock(mdl_request)) + DBUG_RETURN(TRUE); + if (mdl_request->ticket) + { + mdl_request->ticket->clear_cached_object(); + thd->mdl_context.release_lock(mdl_request->ticket); + } + } + DBUG_RETURN(FALSE); +} + + +/** + @brief Helper function used by MDL subsystem for releasing TABLE_SHARE + objects in cases when it no longer wants to cache reference to it. +*/ + +void tdc_release_cached_share(void *ptr) +{ + TABLE_SHARE **share= (TABLE_SHARE **) ptr; + mysql_mutex_lock(&LOCK_open); + if (*share) + { + release_table_share(*share); + *share= NULL; + broadcast_refresh(); + } + mysql_mutex_unlock(&LOCK_open); +} + + +/** + @brief Mark table share as having one more user (increase its reference + count). + + @param share Table share for which reference count should be increased. +*/ + +static void tdc_reference_table_share(TABLE_SHARE *share) +{ + DBUG_ENTER("tdc_reference_table_share"); + DBUG_ASSERT(share->ref_count); + mysql_mutex_assert_owner(&LOCK_open); + share->ref_count++; + DBUG_PRINT("exit", ("share: 0x%lx ref_count: %u", + (ulong) share, share->ref_count)); + DBUG_VOID_RETURN; +} + + +#endif // DISABLED_UNTIL_GRL_IS_MADE_PART_OF + /* Close all tables which aren't in use by any thread @@ -1052,6 +1166,15 @@ bool close_cached_tables(THD *thd, TABLE_LIST *tables, bool have_lock, /* Wait until all threads have closed all the tables we are flushing. */ DBUG_PRINT("info", ("Waiting for other threads to close their open tables")); +#ifdef DISABLED_UNTIL_GRL_IS_MADE_PART_OF + /* + @todo We need to do this for fast refresh as well, otherwise + deadlocks are possible. + */ + if (flush_mdl_cache(thd, tables)) + goto err_with_reopen; +#endif // DISABLED_UNTIL_GRL_IS_MADE_PART_OF_MDL + while (found && ! thd->killed) { found= FALSE; @@ -2361,20 +2484,6 @@ end: } -/** - @brief Helper function used by MDL subsystem for releasing TABLE_SHARE - objects in cases when it no longer wants to cache reference to it. -*/ - -void table_share_release_hook(void *share) -{ - mysql_mutex_lock(&LOCK_open); - release_table_share((TABLE_SHARE*) share); - broadcast_refresh(); - mysql_mutex_unlock(&LOCK_open); -} - - /** An error handler which converts, if possible, ER_LOCK_DEADLOCK error that can occur when we are trying to acquire a metadata lock to @@ -2869,8 +2978,8 @@ bool open_table(THD *thd, TABLE_LIST *table_list, MEM_ROOT *mem_root, mysql_mutex_lock(&LOCK_open); #ifdef DISABLED_UNTIL_GRL_IS_MADE_PART_OF_MDL if (!(share= (TABLE_SHARE *) mdl_ticket->get_cached_object())) -#endif { +#endif // DISABLED_UNTIL_GRL_IS_MADE_PART_OF_MDL if (!(share= get_table_share_with_create(thd, table_list, key, key_length, OPEN_VIEW, &error, @@ -2927,14 +3036,15 @@ bool open_table(THD *thd, TABLE_LIST *table_list, MEM_ROOT *mem_root, #ifdef DISABLED_UNTIL_GRL_IS_MADE_PART_OF_MDL /* - We are going to to store extra reference to the share in MDL-subsystem - so we need to increase reference counter; + We are going to to store extra reference to the share + in MDL-subsystem so we need to increase reference counter. */ - reference_table_share(share); - mdl_ticket->set_cached_object(share, table_share_release_hook); -#endif + if (! share->needs_reopen()) + { + mdl_ticket->set_cached_object(share); + tdc_reference_table_share(share); + } } -#ifdef DISABLED_UNTIL_GRL_IS_MADE_PART_OF_MDL else { if (table_list->view) @@ -2943,19 +3053,19 @@ bool open_table(THD *thd, TABLE_LIST *table_list, MEM_ROOT *mem_root, check_and_update_table_version(thd, table_list, share); /* Always an error. */ DBUG_ASSERT(thd->is_error()); - goto err_unlock; + goto err_unlock2; } /* When we have cached TABLE_SHARE we know that is not a view. */ if (table_list->i_s_requested_object & OPEN_VIEW_ONLY) - goto err_unlock; + goto err_unlock2; /* We are going to use this share for construction of new TABLE object so reference counter should be increased. */ - reference_table_share(share); + tdc_reference_table_share(share); } -#endif +#endif // DISABLED_UNTIL_GRL_IS_MADE_PART_OF_MDL /* @@ -8755,6 +8865,13 @@ void tdc_remove_table(THD *thd, enum_tdc_remove_table_type remove_type, automatically deleted once it is no longer referenced. */ share->version= 0; +#ifdef DISABLED_UNTIL_GRL_IS_MADE_PART_OF_MDL + /* + If lock type is not EXCLUSIVE, we must call + MDL_ticket::release_cached_object() here to make sure there + is no self-reference left on the share in MDL_lock. + */ +#endif while ((table= it++)) free_cache_entry(table); } diff --git a/sql/sql_yacc.yy b/sql/sql_yacc.yy index 1c673f4ca42..73935d2a0b1 100644 --- a/sql/sql_yacc.yy +++ b/sql/sql_yacc.yy @@ -11186,10 +11186,10 @@ flush_options: Lex->type|= REFRESH_TABLES; /* Set type of metadata and table locks for - FLUSH TABLES table_list WITH READ LOCK. + FLUSH TABLES table_list [WITH READ LOCK]. */ YYPS->m_lock_type= TL_READ_NO_INSERT; - YYPS->m_mdl_type= MDL_EXCLUSIVE; + YYPS->m_mdl_type= MDL_SHARED_HIGH_PRIO; } opt_table_list {} opt_with_read_lock {} @@ -11199,7 +11199,13 @@ flush_options: opt_with_read_lock: /* empty */ {} | WITH READ_SYM LOCK_SYM - { Lex->type|= REFRESH_READ_LOCK; } + { + TABLE_LIST *tables= Lex->query_tables; + Lex->type|= REFRESH_READ_LOCK; + /* We acquire an X lock currently and then downgrade. */ + for (; tables; tables= tables->next_global) + tables->mdl_request.set_type(MDL_EXCLUSIVE); + } ; flush_options_list: From ebdd52838299fbb036b8399b53dd347400644a8d Mon Sep 17 00:00:00 2001 From: unknown Date: Tue, 22 Jun 2010 19:21:25 +0200 Subject: [PATCH 021/129] Set version number for mysql-5.1.46sp1 release --- configure.in | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/configure.in b/configure.in index 904c54abb5f..9098ed1f3cb 100644 --- a/configure.in +++ b/configure.in @@ -12,7 +12,7 @@ dnl dnl When changing the major version number please also check the switch dnl statement in mysqlbinlog::check_master_version(). You may also need dnl to update version.c in ndb. -AC_INIT([MySQL Server], [5.1.46], [], [mysql]) +AC_INIT([MySQL Server], [5.1.46sp1], [], [mysql]) AC_CONFIG_SRCDIR([sql/mysqld.cc]) AC_CANONICAL_SYSTEM From eea50ea20dcdae7fe8c3bb182d030cdb79e8c1e0 Mon Sep 17 00:00:00 2001 From: MySQL Build Team Date: Tue, 22 Jun 2010 21:42:14 +0200 Subject: [PATCH 022/129] Backport into build-201006221614-5.1.46sp1 > ------------------------------------------------------------ > revno: 3362 > revision-id: davi.arnaut@sun.com-20100401131522-895y8uzvv8ag44gs > parent: ramil@mysql.com-20100429045409-r7r5lcyiruis15v7 > committer: Davi Arnaut > branch nick: 50755-5.1 > timestamp: Thu 2010-04-01 10:15:22 -0300 > message: > Bug#50755: Crash if stored routine def contains version comments > > The problem was that a syntactically invalid trigger could cause > the server to crash when trying to list triggers. The crash would > happen due to a mishap in the backup/restore procedure that should > protect parser items which are not associated with the trigger. The > backup/restore is used to isolate the parse tree (and context) of > a statement from the load (and parsing) of a trigger. In this case, > a error during the parsing of a trigger could cause the improper > backup/restore sequence. > > The solution is to properly restore the original statement context > before the parser is exited due to syntax errors in the trigger body. --- mysql-test/r/trigger.result | 23 +++++++++++++++++++++++ mysql-test/t/trigger.test | 31 +++++++++++++++++++++++++++++++ sql/sp_head.cc | 36 ++++++++++++++---------------------- sql/sp_head.h | 4 ---- sql/sql_lex.cc | 1 + 5 files changed, 69 insertions(+), 26 deletions(-) diff --git a/mysql-test/r/trigger.result b/mysql-test/r/trigger.result index 3446babbb52..e3c0b0e1dd9 100644 --- a/mysql-test/r/trigger.result +++ b/mysql-test/r/trigger.result @@ -2128,4 +2128,27 @@ Warning 1048 Column 'id' cannot be null Warning 1048 Column 'id' cannot be null DROP TRIGGER t1_bu; DROP TABLE t1,t2; +# +# Bug#50755: Crash if stored routine def contains version comments +# +DROP DATABASE IF EXISTS db1; +DROP TRIGGER IF EXISTS trg1; +DROP TABLE IF EXISTS t1, t2; +CREATE DATABASE db1; +USE db1; +CREATE TABLE t1 (b INT); +CREATE TABLE t2 (a INT); +CREATE TRIGGER trg1 BEFORE INSERT ON t2 FOR EACH ROW INSERT/*!INTO*/t1 VALUES (1); +# Used to crash +SHOW TRIGGERS IN db1; +Trigger Event Table Statement Timing Created sql_mode Definer character_set_client collation_connection Database Collation +Warnings: +Warning 1064 You have an error in your SQL syntax; check the manual that corresponds to your MySQL server version for the right syntax to use near 'VALUES (1)' at line 1 +INSERT INTO t2 VALUES (1); +ERROR 42000: You have an error in your SQL syntax; check the manual that corresponds to your MySQL server version for the right syntax to use near 'VALUES (1)' at line 1 +SELECT * FROM t1; +b +# Work around Bug#45235 +DROP DATABASE db1; +USE test; End of 5.1 tests. diff --git a/mysql-test/t/trigger.test b/mysql-test/t/trigger.test index 368271f1fb2..bcbca4d2139 100644 --- a/mysql-test/t/trigger.test +++ b/mysql-test/t/trigger.test @@ -2439,4 +2439,35 @@ UPDATE t1 SET id=NULL; DROP TRIGGER t1_bu; DROP TABLE t1,t2; +--echo # +--echo # Bug#50755: Crash if stored routine def contains version comments +--echo # + +--disable_warnings +DROP DATABASE IF EXISTS db1; +DROP TRIGGER IF EXISTS trg1; +DROP TABLE IF EXISTS t1, t2; +--enable_warnings + +CREATE DATABASE db1; +USE db1; + +CREATE TABLE t1 (b INT); +CREATE TABLE t2 (a INT); + +CREATE TRIGGER trg1 BEFORE INSERT ON t2 FOR EACH ROW INSERT/*!INTO*/t1 VALUES (1); +--echo # Used to crash +SHOW TRIGGERS IN db1; +--error ER_PARSE_ERROR +INSERT INTO t2 VALUES (1); +SELECT * FROM t1; + +--echo # Work around Bug#45235 +let $MYSQLD_DATADIR = `select @@datadir`; +--remove_file $MYSQLD_DATADIR/db1/t2.TRG +--remove_file $MYSQLD_DATADIR/db1/trg1.TRN + +DROP DATABASE db1; +USE test; + --echo End of 5.1 tests. diff --git a/sql/sp_head.cc b/sql/sp_head.cc index 11d5e5f830b..cadda38053c 100644 --- a/sql/sp_head.cc +++ b/sql/sp_head.cc @@ -745,21 +745,12 @@ sp_head::create(THD *thd) sp_head::~sp_head() { - DBUG_ENTER("sp_head::~sp_head"); - destroy(); - delete m_next_cached_sp; - if (m_thd) - restore_thd_mem_root(m_thd); - DBUG_VOID_RETURN; -} - -void -sp_head::destroy() -{ - sp_instr *i; LEX *lex; - DBUG_ENTER("sp_head::destroy"); - DBUG_PRINT("info", ("name: %s", m_name.str)); + sp_instr *i; + DBUG_ENTER("sp_head::~sp_head"); + + /* sp_head::restore_thd_mem_root() must already have been called. */ + DBUG_ASSERT(m_thd == NULL); for (uint ip = 0 ; (i = get_instr(ip)) ; ip++) delete i; @@ -770,21 +761,22 @@ sp_head::destroy() /* If we have non-empty LEX stack then we just came out of parser with error. Now we should delete all auxilary LEXes and restore original - THD::lex (In this case sp_head::restore_thd_mem_root() was not called - too, so m_thd points to the current thread context). - It is safe to not update LEX::ptr because further query string parsing - and execution will be stopped anyway. + THD::lex. It is safe to not update LEX::ptr because further query + string parsing and execution will be stopped anyway. */ - DBUG_ASSERT(m_lex.is_empty() || m_thd); while ((lex= (LEX *)m_lex.pop())) { - lex_end(m_thd->lex); - delete m_thd->lex; - m_thd->lex= lex; + THD *thd= lex->thd; + lex_end(thd->lex); + delete thd->lex; + thd->lex= lex; } hash_free(&m_sptabs); hash_free(&m_sroutines); + + delete m_next_cached_sp; + DBUG_VOID_RETURN; } diff --git a/sql/sp_head.h b/sql/sp_head.h index 00c96d44f70..d422adc8927 100644 --- a/sql/sp_head.h +++ b/sql/sp_head.h @@ -289,10 +289,6 @@ public: virtual ~sp_head(); - /// Free memory - void - destroy(); - bool execute_trigger(THD *thd, const LEX_STRING *db_name, diff --git a/sql/sql_lex.cc b/sql/sql_lex.cc index 5097ca2ad5b..a3776f59241 100644 --- a/sql/sql_lex.cc +++ b/sql/sql_lex.cc @@ -2106,6 +2106,7 @@ void st_lex::cleanup_lex_after_parse_error(THD *thd) */ if (thd->lex->sphead) { + thd->lex->sphead->restore_thd_mem_root(thd); delete thd->lex->sphead; thd->lex->sphead= NULL; } From d2c104fd129c648b6b89d612d9144b4594525732 Mon Sep 17 00:00:00 2001 From: MySQL Build Team Date: Tue, 22 Jun 2010 21:50:47 +0200 Subject: [PATCH 023/129] Backport into build-201006221614-5.1.46sp1 MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit > ------------------------------------------------------------ > revno: 3351.14.50 > revision-id: marko.makela@oracle.com-20100421185359-8qaxoa2yyrpzwdd7 > parent: marko.makela@oracle.com-20100421102723-0i80uezbyu0ekj5d > committer: Marko Mäkelä > branch nick: 5.1-innodb > timestamp: Wed 2010-04-21 21:53:59 +0300 > message: > btr_page_split_and_insert(): Avoid an infinite loop. (Bug #52964) > > btr_page_tuple_smaller(): New function, refactored from > btr_page_split_and_insert(). > > btr_page_get_split_rec(): Renamed from btr_page_get_sure_split_rec(). > Note that a NULL return may mean that the tuple is to be inserted into > either the lower or upper page, to be determined by btr_page_tuple_smaller(). > > btr_page_split_and_insert(): When btr_page_get_split_rec() returns NULL, > invoke btr_page_tuple_smaller() to determine which half-page the tuple > belongs to. > > Reviewed by Sunny Bains --- storage/innodb_plugin/btr/btr0btr.c | 91 +++++++++++++++++++---------- 1 file changed, 59 insertions(+), 32 deletions(-) diff --git a/storage/innodb_plugin/btr/btr0btr.c b/storage/innodb_plugin/btr/btr0btr.c index fa4fc05d96b..cd8f42b3818 100644 --- a/storage/innodb_plugin/btr/btr0btr.c +++ b/storage/innodb_plugin/btr/btr0btr.c @@ -1451,11 +1451,11 @@ Calculates a split record such that the tuple will certainly fit on its half-page when the split is performed. We assume in this function only that the cursor page has at least one user record. @return split record, or NULL if tuple will be the first record on -upper half-page */ +the lower or upper half-page (determined by btr_page_tuple_smaller()) */ static rec_t* -btr_page_get_sure_split_rec( -/*========================*/ +btr_page_get_split_rec( +/*===================*/ btr_cur_t* cursor, /*!< in: cursor at which insert should be made */ const dtuple_t* tuple, /*!< in: tuple to insert */ ulint n_ext) /*!< in: number of externally stored columns */ @@ -1831,6 +1831,37 @@ btr_attach_half_pages( btr_page_set_next(upper_page, upper_page_zip, next_page_no, mtr); } +/*************************************************************//** +Determine if a tuple is smaller than any record on the page. +@return TRUE if smaller */ +static +ibool +btr_page_tuple_smaller( +/*===================*/ + btr_cur_t* cursor, /*!< in: b-tree cursor */ + const dtuple_t* tuple, /*!< in: tuple to consider */ + ulint* offsets,/*!< in/out: temporary storage */ + ulint n_uniq, /*!< in: number of unique fields + in the index page records */ + mem_heap_t** heap) /*!< in/out: heap for offsets */ +{ + buf_block_t* block; + const rec_t* first_rec; + page_cur_t pcur; + + /* Read the first user record in the page. */ + block = btr_cur_get_block(cursor); + page_cur_set_before_first(block, &pcur); + page_cur_move_to_next(&pcur); + first_rec = page_cur_get_rec(&pcur); + + offsets = rec_get_offsets( + first_rec, cursor->index, offsets, + n_uniq, heap); + + return(cmp_dtuple_rec(tuple, first_rec, offsets) < 0); +} + /*************************************************************//** Splits an index page to halves and inserts the tuple. It is assumed that mtr holds an x-latch to the index tree. NOTE: the tree x-latch is @@ -1905,49 +1936,45 @@ func_start: if (n_iterations > 0) { direction = FSP_UP; hint_page_no = page_no + 1; - split_rec = btr_page_get_sure_split_rec(cursor, tuple, n_ext); + split_rec = btr_page_get_split_rec(cursor, tuple, n_ext); + if (UNIV_UNLIKELY(split_rec == NULL)) { + insert_left = btr_page_tuple_smaller( + cursor, tuple, offsets, n_uniq, &heap); + } } else if (btr_page_get_split_rec_to_right(cursor, &split_rec)) { direction = FSP_UP; hint_page_no = page_no + 1; + insert_left = FALSE; } else if (btr_page_get_split_rec_to_left(cursor, &split_rec)) { direction = FSP_DOWN; hint_page_no = page_no - 1; + ut_ad(split_rec); } else { direction = FSP_UP; hint_page_no = page_no + 1; - if (page_get_n_recs(page) == 1) { - page_cur_t pcur; + /* If there is only one record in the index page, we + can't split the node in the middle by default. We need + to determine whether the new record will be inserted + to the left or right. */ - /* There is only one record in the index page - therefore we can't split the node in the middle - by default. We need to determine whether the - new record will be inserted to the left or right. */ - - /* Read the first (and only) record in the page. */ - page_cur_set_before_first(block, &pcur); - page_cur_move_to_next(&pcur); - first_rec = page_cur_get_rec(&pcur); - - offsets = rec_get_offsets( - first_rec, cursor->index, offsets, - n_uniq, &heap); - - /* If the new record is less than the existing record - the split in the middle will copy the existing - record to the new node. */ - if (cmp_dtuple_rec(tuple, first_rec, offsets) < 0) { - split_rec = page_get_middle_rec(page); - } else { - split_rec = NULL; - } - } else { + if (page_get_n_recs(page) > 1) { split_rec = page_get_middle_rec(page); + } else if (btr_page_tuple_smaller(cursor, tuple, + offsets, n_uniq, &heap)) { + split_rec = page_rec_get_next( + page_get_infimum_rec(page)); + } else { + split_rec = NULL; + insert_left = FALSE; } } + /* At this point, insert_left is initialized if split_rec == NULL + and may be uninitialized otherwise. */ + /* 2. Allocate a new page to the index */ new_block = btr_page_alloc(cursor->index, hint_page_no, direction, btr_page_get_level(page, mtr), mtr); @@ -1974,11 +2001,11 @@ func_start: avoid further splits by inserting the record to an empty page. */ split_rec = NULL; - goto insert_right; + goto insert_empty; } } else { -insert_right: - insert_left = FALSE; +insert_empty: + ut_ad(!split_rec); buf = mem_alloc(rec_get_converted_size(cursor->index, tuple, n_ext)); From 65379cccc84bb5324413dfd6d3fd09b496612361 Mon Sep 17 00:00:00 2001 From: MySQL Build Team Date: Tue, 22 Jun 2010 21:52:43 +0200 Subject: [PATCH 024/129] Backport into build-201006221614-5.1.46sp1 MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit > ------------------------------------------------------------ > revno: 3351.14.74 > revision-id: marko.makela@oracle.com-20100504093128-44v6glupe1dsh0ug > parent: marko.makela@oracle.com-20100503122859-k73bl51re93o0mt4 > committer: Marko Mäkelä > branch nick: 5.1-innodb > timestamp: Tue 2010-05-04 12:31:28 +0300 > message: > btr_page_split_and_insert(): Correct the fix of Bug #52964. > When split_rec==NULL, choose the correct node pointer key (first_rec). --- storage/innodb_plugin/btr/btr0btr.c | 10 +++++++++- 1 file changed, 9 insertions(+), 1 deletion(-) diff --git a/storage/innodb_plugin/btr/btr0btr.c b/storage/innodb_plugin/btr/btr0btr.c index cd8f42b3818..1d6b4f5a0e6 100644 --- a/storage/innodb_plugin/btr/btr0btr.c +++ b/storage/innodb_plugin/btr/btr0btr.c @@ -2003,9 +2003,13 @@ func_start: split_rec = NULL; goto insert_empty; } + } else if (UNIV_UNLIKELY(insert_left)) { + first_rec = page_rec_get_next(page_get_infimum_rec(page)); + move_limit = page_rec_get_next(btr_cur_get_rec(cursor)); } else { insert_empty: ut_ad(!split_rec); + ut_ad(!insert_left); buf = mem_alloc(rec_get_converted_size(cursor->index, tuple, n_ext)); @@ -2029,7 +2033,11 @@ insert_empty: && btr_page_insert_fits(cursor, split_rec, offsets, tuple, n_ext, heap); } else { - mem_free(buf); + if (!insert_left) { + mem_free(buf); + buf = NULL; + } + insert_will_fit = !new_page_zip && btr_page_insert_fits(cursor, NULL, NULL, tuple, n_ext, heap); From 1cab479221f6d9fbe0fc44414b5b6a9bc7c9f009 Mon Sep 17 00:00:00 2001 From: MySQL Build Team Date: Tue, 22 Jun 2010 21:54:41 +0200 Subject: [PATCH 025/129] Backport into build-201006221614-5.1.46sp1 MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit > ------------------------------------------------------------ > revno: 3351.47.1 > revision-id: marko.makela@oracle.com-20100511104500-c6kzd0bg5s42p8e9 > parent: vasil.dimov@oracle.com-20100510132852-cz457uqvj8iiy9mm > committer: Marko Mäkelä > branch nick: mysql-5.1-innodb2 > timestamp: Tue 2010-05-11 13:45:00 +0300 > message: > Remove a stray expression. Spotted by Sunny Bains. --- storage/innodb_plugin/page/page0zip.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/storage/innodb_plugin/page/page0zip.c b/storage/innodb_plugin/page/page0zip.c index aa5e39ff04a..a64a41ea518 100644 --- a/storage/innodb_plugin/page/page0zip.c +++ b/storage/innodb_plugin/page/page0zip.c @@ -571,7 +571,7 @@ page_zip_dir_encode( /* Traverse the list of stored records in the collation order, starting from the first user record. */ - rec = page + PAGE_NEW_INFIMUM, TRUE; + rec = page + PAGE_NEW_INFIMUM; i = 0; From e87a2d917b39043ce7124aae8788e8247e611211 Mon Sep 17 00:00:00 2001 From: MySQL Build Team Date: Tue, 22 Jun 2010 21:56:18 +0200 Subject: [PATCH 026/129] Backport into build-201006221614-5.1.46sp1 MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit > ------------------------------------------------------------ > revno: 3351.47.2 > revision-id: marko.makela@oracle.com-20100511104910-nim8kgguawpis7zo > parent: marko.makela@oracle.com-20100511104500-c6kzd0bg5s42p8e9 > committer: Marko Mäkelä > branch nick: mysql-5.1-innodb2 > timestamp: Tue 2010-05-11 13:49:10 +0300 > message: > btr_page_split_and_insert(): Add an assertion > suggested by Sunny Bains when reviewing Bug #52964. --- storage/innodb_plugin/btr/btr0btr.c | 1 + 1 file changed, 1 insertion(+) diff --git a/storage/innodb_plugin/btr/btr0btr.c b/storage/innodb_plugin/btr/btr0btr.c index 1d6b4f5a0e6..0fd209e0216 100644 --- a/storage/innodb_plugin/btr/btr0btr.c +++ b/storage/innodb_plugin/btr/btr0btr.c @@ -2004,6 +2004,7 @@ func_start: goto insert_empty; } } else if (UNIV_UNLIKELY(insert_left)) { + ut_a(n_iterations > 0); first_rec = page_rec_get_next(page_get_infimum_rec(page)); move_limit = page_rec_get_next(btr_cur_get_rec(cursor)); } else { From f5a0316a3962ce34f3586574be5598d2bacd5ccb Mon Sep 17 00:00:00 2001 From: MySQL Build Team Date: Tue, 22 Jun 2010 21:59:35 +0200 Subject: [PATCH 027/129] Backport into build-201006221614-5.1.46sp1 MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit > ------------------------------------------------------------ > revno: 3351.14.47 > revision-id: marko.makela@oracle.com-20100421095033-0acvzxb8um8cms0a > parent: marko.makela@oracle.com-20100421094032-ir4glqk46qvg2ywn > committer: Marko Mäkelä > branch nick: 5.1-innodb > timestamp: Wed 2010-04-21 12:50:33 +0300 > message: > dtuple_convert_big_rec(): Store locally any fields whose maximum length > is less than 256 bytes. (Bug #52745) > Add related comments and debug assertions to the "offsets" > functions in rem0rec.c. > Approved by Sunny Bains --- storage/innodb_plugin/data/data0data.c | 15 +++++++ storage/innodb_plugin/rem/rem0rec.c | 59 +++++++++++++++++++++++++- 2 files changed, 72 insertions(+), 2 deletions(-) diff --git a/storage/innodb_plugin/data/data0data.c b/storage/innodb_plugin/data/data0data.c index e3c1f1b4f23..0715b49bf9c 100644 --- a/storage/innodb_plugin/data/data0data.c +++ b/storage/innodb_plugin/data/data0data.c @@ -666,6 +666,21 @@ dtuple_convert_big_rec( goto skip_field; } + /* In DYNAMIC and COMPRESSED format, store + locally any non-BLOB columns whose maximum + length does not exceed 256 bytes. This is + because there is no room for the "external + storage" flag when the maximum length is 255 + bytes or less. This restriction trivially + holds in REDUNDANT and COMPACT format, because + there we always store locally columns whose + length is up to local_len == 788 bytes. + @see rec_init_offsets_comp_ordinary */ + if (ifield->col->mtype != DATA_BLOB + && ifield->col->len < 256) { + goto skip_field; + } + longest_i = i; longest = savings; diff --git a/storage/innodb_plugin/rem/rem0rec.c b/storage/innodb_plugin/rem/rem0rec.c index 27c11dacc8c..59cf6e887d1 100644 --- a/storage/innodb_plugin/rem/rem0rec.c +++ b/storage/innodb_plugin/rem/rem0rec.c @@ -212,6 +212,13 @@ rec_get_n_extern_new( const dict_col_t* col = dict_field_get_col(field); len = *lens--; + /* If the maximum length of the field is up + to 255 bytes, the actual length is always + stored in one byte. If the maximum length is + more than 255 bytes, the actual length is + stored in one byte for 0..127. The length + will be encoded in two bytes when it is 128 or + more, or when the field is stored externally. */ if (UNIV_UNLIKELY(col->len > 255) || UNIV_UNLIKELY(col->mtype == DATA_BLOB)) { if (len & 0x80) { @@ -294,6 +301,13 @@ rec_init_offsets_comp_ordinary( const dict_col_t* col = dict_field_get_col(field); len = *lens--; + /* If the maximum length of the field is up + to 255 bytes, the actual length is always + stored in one byte. If the maximum length is + more than 255 bytes, the actual length is + stored in one byte for 0..127. The length + will be encoded in two bytes when it is 128 or + more, or when the field is stored externally. */ if (UNIV_UNLIKELY(col->len > 255) || UNIV_UNLIKELY(col->mtype == DATA_BLOB)) { @@ -425,6 +439,15 @@ rec_init_offsets( const dict_col_t* col = dict_field_get_col(field); len = *lens--; + /* If the maximum length of the field + is up to 255 bytes, the actual length + is always stored in one byte. If the + maximum length is more than 255 bytes, + the actual length is stored in one + byte for 0..127. The length will be + encoded in two bytes when it is 128 or + more, or when the field is stored + externally. */ if (UNIV_UNLIKELY(col->len > 255) || UNIV_UNLIKELY(col->mtype == DATA_BLOB)) { @@ -647,6 +670,13 @@ rec_get_offsets_reverse( const dict_col_t* col = dict_field_get_col(field); len = *lens++; + /* If the maximum length of the field is up + to 255 bytes, the actual length is always + stored in one byte. If the maximum length is + more than 255 bytes, the actual length is + stored in one byte for 0..127. The length + will be encoded in two bytes when it is 128 or + more, or when the field is stored externally. */ if (UNIV_UNLIKELY(col->len > 255) || UNIV_UNLIKELY(col->mtype == DATA_BLOB)) { if (len & 0x80) { @@ -781,12 +811,20 @@ rec_get_converted_size_comp_prefix( ut_ad(len <= col->len || col->mtype == DATA_BLOB); + /* If the maximum length of a variable-length field + is up to 255 bytes, the actual length is always stored + in one byte. If the maximum length is more than 255 + bytes, the actual length is stored in one byte for + 0..127. The length will be encoded in two bytes when + it is 128 or more, or when the field is stored externally. */ + if (field->fixed_len) { ut_ad(len == field->fixed_len); /* dict_index_add_col() should guarantee this */ ut_ad(!field->prefix_len || field->fixed_len == field->prefix_len); } else if (dfield_is_ext(&fields[i])) { + ut_ad(col->len >= 256 || col->mtype == DATA_BLOB); extra_size += 2; } else if (len < 128 || (col->len < 256 && col->mtype != DATA_BLOB)) { @@ -1086,6 +1124,8 @@ rec_convert_dtuple_to_rec_comp( /* Store the data and the offsets */ for (i = 0, field = fields; i < n_fields; i++, field++) { + const dict_field_t* ifield; + type = dfield_get_type(field); len = dfield_get_len(field); @@ -1120,12 +1160,20 @@ rec_convert_dtuple_to_rec_comp( /* only nullable fields can be null */ ut_ad(!dfield_is_null(field)); - fixed_len = dict_index_get_nth_field(index, i)->fixed_len; - + ifield = dict_index_get_nth_field(index, i); + fixed_len = ifield->fixed_len; + /* If the maximum length of a variable-length field + is up to 255 bytes, the actual length is always stored + in one byte. If the maximum length is more than 255 + bytes, the actual length is stored in one byte for + 0..127. The length will be encoded in two bytes when + it is 128 or more, or when the field is stored externally. */ if (fixed_len) { ut_ad(len == fixed_len); ut_ad(!dfield_is_ext(field)); } else if (dfield_is_ext(field)) { + ut_ad(ifield->col->len >= 256 + || ifield->col->mtype == DATA_BLOB); ut_ad(len <= REC_MAX_INDEX_COL_LEN + BTR_EXTERN_FIELD_REF_SIZE); *lens-- = (byte) (len >> 8) | 0xc0; @@ -1402,6 +1450,13 @@ rec_copy_prefix_to_buf( prefix_len += field->fixed_len; } else { ulint len = *lens--; + /* If the maximum length of the column is up + to 255 bytes, the actual length is always + stored in one byte. If the maximum length is + more than 255 bytes, the actual length is + stored in one byte for 0..127. The length + will be encoded in two bytes when it is 128 or + more, or when the column is stored externally. */ if (col->len > 255 || col->mtype == DATA_BLOB) { if (len & 0x80) { /* 1exxxxxx */ From 4f066e52694cb41ed950ed0a92d4518de9cd89bf Mon Sep 17 00:00:00 2001 From: MySQL Build Team Date: Tue, 22 Jun 2010 22:09:31 +0200 Subject: [PATCH 028/129] Backport into 5.1.46sp1: > revno: 3351.14.56 > committer: Marko Mdkeld > branch nick: 5.1-innodb > timestamp: Mon 2010-04-26 14:08:56 +0300 > message: > Add a test case for Bug #52745. --- .../innodb_plugin/r/innodb_bug52745.result | 130 ++++++++++++++++++ .../innodb_plugin/t/innodb_bug52745.test | 109 +++++++++++++++ 2 files changed, 239 insertions(+) create mode 100644 mysql-test/suite/innodb_plugin/r/innodb_bug52745.result create mode 100644 mysql-test/suite/innodb_plugin/t/innodb_bug52745.test diff --git a/mysql-test/suite/innodb_plugin/r/innodb_bug52745.result b/mysql-test/suite/innodb_plugin/r/innodb_bug52745.result new file mode 100644 index 00000000000..254c6525257 --- /dev/null +++ b/mysql-test/suite/innodb_plugin/r/innodb_bug52745.result @@ -0,0 +1,130 @@ +SET GLOBAL innodb_file_format='Barracuda'; +SET GLOBAL innodb_file_per_table=on; +CREATE TABLE bug52745 ( +a2 int(10) unsigned DEFAULT NULL, +col37 time DEFAULT NULL, +col38 char(229) CHARACTER SET utf8 DEFAULT NULL, +col39 text, +col40 timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP, +col41 int(10) unsigned DEFAULT NULL, +col42 varchar(248) CHARACTER SET utf8 DEFAULT NULL, +col43 smallint(5) unsigned zerofill DEFAULT NULL, +col44 varchar(150) CHARACTER SET utf8 DEFAULT NULL, +col45 float unsigned zerofill DEFAULT NULL, +col46 binary(1) DEFAULT NULL, +col47 tinyint(4) DEFAULT NULL, +col48 tinyint(1) DEFAULT NULL, +col49 timestamp NOT NULL DEFAULT '0000-00-00 00:00:00', +col50 binary(1) DEFAULT NULL, +col51 double unsigned zerofill DEFAULT NULL, +col52 int(10) unsigned DEFAULT NULL, +col53 time DEFAULT NULL, +col54 double unsigned DEFAULT NULL, +col55 time DEFAULT NULL, +col56 mediumtext CHARACTER SET latin2, +col57 blob, +col58 decimal(52,16) unsigned zerofill NOT NULL DEFAULT '000000000000000000000000000000000000.0000000000000000', +col59 binary(1) DEFAULT NULL, +col60 longblob, +col61 time DEFAULT NULL, +col62 longtext CHARACTER SET utf8 COLLATE utf8_persian_ci, +col63 timestamp NOT NULL DEFAULT '0000-00-00 00:00:00', +col64 int(10) unsigned DEFAULT NULL, +col65 date DEFAULT NULL, +col66 timestamp NOT NULL DEFAULT '0000-00-00 00:00:00', +col67 binary(1) DEFAULT NULL, +col68 tinyblob, +col69 date DEFAULT NULL, +col70 tinyint(3) unsigned zerofill DEFAULT NULL, +col71 varchar(44) CHARACTER SET utf8 DEFAULT NULL, +col72 datetime DEFAULT NULL, +col73 smallint(5) unsigned zerofill DEFAULT NULL, +col74 longblob, +col75 bit(34) DEFAULT NULL, +col76 float unsigned zerofill DEFAULT NULL, +col77 year(2) DEFAULT NULL, +col78 tinyint(3) unsigned DEFAULT NULL, +col79 set('msfheowh','tbpxbgf','by','wahnrjw','myqfasxz','rsokyumrt') CHARACTER SET latin2 DEFAULT NULL, +col80 datetime DEFAULT NULL, +col81 smallint(6) DEFAULT NULL, +col82 enum('xtaurnqfqz','rifrse','kuzwpbvb','niisabk','zxavro','rbvasv','','uulrfaove','','') DEFAULT NULL, +col83 bigint(20) unsigned zerofill DEFAULT NULL, +col84 float unsigned zerofill DEFAULT NULL, +col85 double DEFAULT NULL, +col86 enum('ylannv','','vlkhycqc','snke','cxifustp','xiaxaswzp','oxl') CHARACTER SET latin1 COLLATE latin1_german2_ci DEFAULT NULL, +col87 varbinary(221) DEFAULT NULL, +col88 double unsigned DEFAULT NULL, +col89 float unsigned zerofill DEFAULT NULL, +col90 tinyblob +) ENGINE=InnoDB DEFAULT CHARSET=latin1 ROW_FORMAT=COMPRESSED KEY_BLOCK_SIZE=1; +Warnings: +Note 1291 Column 'col82' has duplicated value '' in ENUM +Note 1291 Column 'col82' has duplicated value '' in ENUM +INSERT INTO bug52745 SET +col40='0000-00-00 00:00:00', +col51=16547, +col53='7711484', +col54=-28604, +col55='7112612', +col56='wakefulness\'', +col57=repeat('absorbefacient\'',106), +col58=11027, +col59='AM09gW7', +col60=repeat('Noelani\'',16), +col61='2520576', +col62='substitutiv', +col63='19950106155112', +col64=-12038, +col65='86238806', +col66='19600719080256', +col68=repeat('Sagittarius\'',54), +col69='38943902', +col70=1232, +col71='Elora\'', +col74=repeat('zipp',11), +col75='0', +col76=23254, +col78=13247, +col79='56219', +col80='20500609035724', +col81=11632, +col82=7, +col84=-23863, +col85=6341, +col87='HZdkf.4 s7t,5Rmq 8so fmr,ruGLUG25TrtI.yQ 2SuHq0ML7rw7.4 b2yf2E5TJxOtBBZImezDnzpj,uPYfznnEUDN1e9aQoO 2DsplB7TFWy oQJ br HLF :F,eQ p4i1oWsr lL3PG,hjCz6hYqN h1QTjLCjrv:QCdSzpYBibJAtZCxLOk3l6Blsh.W', +col88=16894, +col89=6161, +col90=repeat('gale',48); +Warnings: +Warning 1265 Data truncated for column 'col53' at row 1 +Warning 1264 Out of range value for column 'col54' at row 1 +Warning 1265 Data truncated for column 'col59' at row 1 +Warning 1265 Data truncated for column 'col61' at row 1 +Warning 1264 Out of range value for column 'col64' at row 1 +Warning 1265 Data truncated for column 'col65' at row 1 +Warning 1264 Out of range value for column 'col66' at row 1 +Warning 1265 Data truncated for column 'col68' at row 1 +Warning 1265 Data truncated for column 'col69' at row 1 +Warning 1264 Out of range value for column 'col70' at row 1 +Warning 1264 Out of range value for column 'col78' at row 1 +Warning 1265 Data truncated for column 'col79' at row 1 +Warning 1264 Out of range value for column 'col84' at row 1 +SHOW WARNINGS; +Level Code Message +Warning 1265 Data truncated for column 'col53' at row 1 +Warning 1264 Out of range value for column 'col54' at row 1 +Warning 1265 Data truncated for column 'col59' at row 1 +Warning 1265 Data truncated for column 'col61' at row 1 +Warning 1264 Out of range value for column 'col64' at row 1 +Warning 1265 Data truncated for column 'col65' at row 1 +Warning 1264 Out of range value for column 'col66' at row 1 +Warning 1265 Data truncated for column 'col68' at row 1 +Warning 1265 Data truncated for column 'col69' at row 1 +Warning 1264 Out of range value for column 'col70' at row 1 +Warning 1264 Out of range value for column 'col78' at row 1 +Warning 1265 Data truncated for column 'col79' at row 1 +Warning 1264 Out of range value for column 'col84' at row 1 +DROP TABLE bug52745; +SET GLOBAL innodb_file_format=Antelope; +SET GLOBAL innodb_file_format_check=Antelope; +SET GLOBAL innodb_file_per_table=0; diff --git a/mysql-test/suite/innodb_plugin/t/innodb_bug52745.test b/mysql-test/suite/innodb_plugin/t/innodb_bug52745.test new file mode 100644 index 00000000000..b20a993a2d1 --- /dev/null +++ b/mysql-test/suite/innodb_plugin/t/innodb_bug52745.test @@ -0,0 +1,109 @@ +-- source include/have_innodb_plugin.inc + +let $file_format=`select @@innodb_file_format`; +let $file_format_check=`select @@innodb_file_format_check`; +let $file_per_table=`select @@innodb_file_per_table`; +SET GLOBAL innodb_file_format='Barracuda'; +SET GLOBAL innodb_file_per_table=on; + +CREATE TABLE bug52745 ( + a2 int(10) unsigned DEFAULT NULL, + col37 time DEFAULT NULL, + col38 char(229) CHARACTER SET utf8 DEFAULT NULL, + col39 text, + col40 timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP, + col41 int(10) unsigned DEFAULT NULL, + col42 varchar(248) CHARACTER SET utf8 DEFAULT NULL, + col43 smallint(5) unsigned zerofill DEFAULT NULL, + col44 varchar(150) CHARACTER SET utf8 DEFAULT NULL, + col45 float unsigned zerofill DEFAULT NULL, + col46 binary(1) DEFAULT NULL, + col47 tinyint(4) DEFAULT NULL, + col48 tinyint(1) DEFAULT NULL, + col49 timestamp NOT NULL DEFAULT '0000-00-00 00:00:00', + col50 binary(1) DEFAULT NULL, + col51 double unsigned zerofill DEFAULT NULL, + col52 int(10) unsigned DEFAULT NULL, + col53 time DEFAULT NULL, + col54 double unsigned DEFAULT NULL, + col55 time DEFAULT NULL, + col56 mediumtext CHARACTER SET latin2, + col57 blob, + col58 decimal(52,16) unsigned zerofill NOT NULL DEFAULT '000000000000000000000000000000000000.0000000000000000', + col59 binary(1) DEFAULT NULL, + col60 longblob, + col61 time DEFAULT NULL, + col62 longtext CHARACTER SET utf8 COLLATE utf8_persian_ci, + col63 timestamp NOT NULL DEFAULT '0000-00-00 00:00:00', + col64 int(10) unsigned DEFAULT NULL, + col65 date DEFAULT NULL, + col66 timestamp NOT NULL DEFAULT '0000-00-00 00:00:00', + col67 binary(1) DEFAULT NULL, + col68 tinyblob, + col69 date DEFAULT NULL, + col70 tinyint(3) unsigned zerofill DEFAULT NULL, + col71 varchar(44) CHARACTER SET utf8 DEFAULT NULL, + col72 datetime DEFAULT NULL, + col73 smallint(5) unsigned zerofill DEFAULT NULL, + col74 longblob, + col75 bit(34) DEFAULT NULL, + col76 float unsigned zerofill DEFAULT NULL, + col77 year(2) DEFAULT NULL, + col78 tinyint(3) unsigned DEFAULT NULL, + col79 set('msfheowh','tbpxbgf','by','wahnrjw','myqfasxz','rsokyumrt') CHARACTER SET latin2 DEFAULT NULL, + col80 datetime DEFAULT NULL, + col81 smallint(6) DEFAULT NULL, + col82 enum('xtaurnqfqz','rifrse','kuzwpbvb','niisabk','zxavro','rbvasv','','uulrfaove','','') DEFAULT NULL, + col83 bigint(20) unsigned zerofill DEFAULT NULL, + col84 float unsigned zerofill DEFAULT NULL, + col85 double DEFAULT NULL, + col86 enum('ylannv','','vlkhycqc','snke','cxifustp','xiaxaswzp','oxl') CHARACTER SET latin1 COLLATE latin1_german2_ci DEFAULT NULL, + col87 varbinary(221) DEFAULT NULL, + col88 double unsigned DEFAULT NULL, + col89 float unsigned zerofill DEFAULT NULL, + col90 tinyblob +) ENGINE=InnoDB DEFAULT CHARSET=latin1 ROW_FORMAT=COMPRESSED KEY_BLOCK_SIZE=1; + +INSERT INTO bug52745 SET +col40='0000-00-00 00:00:00', +col51=16547, +col53='7711484', +col54=-28604, +col55='7112612', +col56='wakefulness\'', +col57=repeat('absorbefacient\'',106), +col58=11027, +col59='AM09gW7', +col60=repeat('Noelani\'',16), +col61='2520576', +col62='substitutiv', +col63='19950106155112', +col64=-12038, +col65='86238806', +col66='19600719080256', +col68=repeat('Sagittarius\'',54), +col69='38943902', +col70=1232, +col71='Elora\'', +col74=repeat('zipp',11), +col75='0', +col76=23254, +col78=13247, +col79='56219', +col80='20500609035724', +col81=11632, +col82=7, +col84=-23863, +col85=6341, +col87='HZdkf.4 s7t,5Rmq 8so fmr,ruGLUG25TrtI.yQ 2SuHq0ML7rw7.4 b2yf2E5TJxOtBBZImezDnzpj,uPYfznnEUDN1e9aQoO 2DsplB7TFWy oQJ br HLF :F,eQ p4i1oWsr lL3PG,hjCz6hYqN h1QTjLCjrv:QCdSzpYBibJAtZCxLOk3l6Blsh.W', +col88=16894, +col89=6161, +col90=repeat('gale',48); + +SHOW WARNINGS; + +DROP TABLE bug52745; + +EVAL SET GLOBAL innodb_file_format=$file_format; +EVAL SET GLOBAL innodb_file_format_check=$file_format_check; +EVAL SET GLOBAL innodb_file_per_table=$file_per_table; From 01490413d26cd31f319928e30724bd5a28e82e42 Mon Sep 17 00:00:00 2001 From: MySQL Build Team Date: Tue, 22 Jun 2010 22:34:48 +0200 Subject: [PATCH 029/129] Backport into build-201006221614-5.1.46sp1 > ------------------------------------------------------------ > revno: 1810.3987.13 > revision-id: ramil@mysql.com-20100429044232-f0pkyx8fnpszf142 > parent: alexey.kopytov@sun.com-20100426200600-op06qy98llzpzgl1 > committer: Ramil Kalimullin > branch nick: b53237-5.0-bugteam > timestamp: Thu 2010-04-29 08:42:32 +0400 > message: > Fix for bug #53237: mysql_list_fields/COM_FIELD_LIST stack smashing > > Problem: "COM_FIELD_LIST is an old command of the MySQL server, before there was real move to only > SQL. Seems that the data sent to COM_FIELD_LIST( mysql_list_fields() function) is not > checked for sanity. By sending long data for the table a buffer is overflown, which can > be used deliberately to include code that harms". > > Fix: check incoming data length. The patch did not apply cleanly: - Line numbers are completely off, roughly it is 2030 -> 1313 - What is called "pend" in the patch, is "arg_end" in the source. --- sql/sql_parse.cc | 10 +++++++++- 1 file changed, 9 insertions(+), 1 deletion(-) diff --git a/sql/sql_parse.cc b/sql/sql_parse.cc index 5228a37f490..11481933c8a 100644 --- a/sql/sql_parse.cc +++ b/sql/sql_parse.cc @@ -1300,8 +1300,16 @@ bool dispatch_command(enum enum_server_command command, THD *thd, We have name + wildcard in packet, separated by endzero */ arg_end= strend(packet); + uint arg_length= arg_end - packet; + + /* Check given table name length. */ + if (arg_length >= packet_length || arg_length > NAME_LEN) + { + my_message(ER_UNKNOWN_COM_ERROR, ER(ER_UNKNOWN_COM_ERROR), MYF(0)); + break; + } thd->convert_string(&conv_name, system_charset_info, - packet, (uint) (arg_end - packet), thd->charset()); + packet, arg_length, thd->charset()); table_list.alias= table_list.table_name= conv_name.str; packet= arg_end + 1; From fb8791e2bc36c3da93540b68d86ff1f2c3ddb2b2 Mon Sep 17 00:00:00 2001 From: MySQL Build Team Date: Tue, 22 Jun 2010 22:51:35 +0200 Subject: [PATCH 030/129] Backport into build-201006221614-5.1.46sp1 > ------------------------------------------------------------ > revno: 1810.3987.14 > revision-id: davi.arnaut@sun.com-20100429132816-ictyul6d75itek22 > parent: ramil@mysql.com-20100429044232-f0pkyx8fnpszf142 > committer: Davi Arnaut > branch nick: 50974-5.0 > timestamp: Thu 2010-04-29 10:28:16 -0300 > message: > Bug#50974: Server keeps receiving big (> max_allowed_packet) packets indefinitely. > > The server could be tricked to read packets indefinitely if it > received a packet larger than the maximum size of one packet. > This problem is aggravated by the fact that it can be triggered > before authentication. > > The solution is to no skip big packets for non-authenticated > sessions. If a big packet is sent before a session is authen- > ticated, a error is returned and the connection is closed. > ------------------------------------------------------------ > revno: 3363 [merge] > revision-id: davi.arnaut@sun.com-20100429231819-i3anwzrdasjmezvt > parent: davi.arnaut@sun.com-20100401131522-895y8uzvv8ag44gs > parent: davi.arnaut@sun.com-20100429132816-ictyul6d75itek22 > committer: Davi Arnaut > branch nick: mysql-5.1-bugteam > timestamp: Thu 2010-04-29 20:18:19 -0300 > message: > Manual merge. > ------------------------------------------------------------ > Use --include-merges or -n0 to see merged revisions. --- include/mysql_com.h | 10 ++++++++++ sql/net_serv.cc | 4 ++++ sql/sql_connect.cc | 7 +++++++ 3 files changed, 21 insertions(+) diff --git a/include/mysql_com.h b/include/mysql_com.h index db5a5eb8741..7d3dd3d4f34 100644 --- a/include/mysql_com.h +++ b/include/mysql_com.h @@ -277,6 +277,16 @@ typedef struct st_net { /** Client library sqlstate buffer. Set along with the error message. */ char sqlstate[SQLSTATE_LENGTH+1]; void *extension; +#if defined(MYSQL_SERVER) && !defined(EMBEDDED_LIBRARY) + /* + Controls whether a big packet should be skipped. + + Initially set to FALSE by default. Unauthenticated sessions must have + this set to FALSE so that the server can't be tricked to read packets + indefinitely. + */ + my_bool skip_big_packet; +#endif } NET; diff --git a/sql/net_serv.cc b/sql/net_serv.cc index 73892f31ccf..15c0c581108 100644 --- a/sql/net_serv.cc +++ b/sql/net_serv.cc @@ -136,6 +136,9 @@ my_bool my_net_init(NET *net, Vio* vio) #else net->query_cache_query= 0; #endif +#if defined(MYSQL_SERVER) && !defined(EMBEDDED_LIBRARY) + net->skip_big_packet= FALSE; +#endif if (vio != 0) /* If real connection */ { @@ -949,6 +952,7 @@ my_real_read(NET *net, size_t *complen) { #if defined(MYSQL_SERVER) && !defined(NO_ALARM) if (!net->compress && + net->skip_big_packet && !my_net_skip_rest(net, (uint32) len, &alarmed, &alarm_buff)) net->error= 3; /* Successfully skiped packet */ #endif diff --git a/sql/sql_connect.cc b/sql/sql_connect.cc index 16f11fe22c4..2039c7f7449 100644 --- a/sql/sql_connect.cc +++ b/sql/sql_connect.cc @@ -471,6 +471,13 @@ check_user(THD *thd, enum enum_server_command command, } my_ok(thd); thd->password= test(passwd_len); // remember for error messages + /* + Allow the network layer to skip big packets. Although a malicious + authenticated session might use this to trick the server to read + big packets indefinitely, this is a previously established behavior + that needs to be preserved as to not break backwards compatibility. + */ + thd->net.skip_big_packet= TRUE; /* Ready to handle queries */ DBUG_RETURN(0); } From a0a850318b964ca92b660e0127c35061ad8f7a54 Mon Sep 17 00:00:00 2001 From: MySQL Build Team Date: Tue, 22 Jun 2010 22:53:01 +0200 Subject: [PATCH 031/129] Backport into build-201006221614-5.1.46sp1 > ------------------------------------------------------------ > revno: 3351.41.1 > revision-id: alexey.kopytov@sun.com-20100430111048-jdls6ofn4kkmpt09 > parent: sergey.glukhov@sun.com-20100329134249-03wyhzp5k92dzhcb > committer: Alexey Kopytov > branch nick: my51-bug48419 > timestamp: Fri 2010-04-30 15:10:48 +0400 > message: > Bug #48419: another explain crash.. > > WHERE predicates containing references to empty tables in a > subquery were handled incorrectly by the optimizer when > executing EXPLAIN. As a result, the optimizer could try to > evaluate such predicates rather than just stop with > "Impossible WHERE noticed after reading const tables" as > it would do in a non-subquery case. This led to valgrind > errors and crashes. > > Fixed the code checking the above condition so that subqueries > are not excluded and hence are handled in the same way as top > level SELECTs. --- mysql-test/r/explain.result | 12 ++++++++++++ mysql-test/r/ps.result | 12 ++++++------ mysql-test/t/explain.test | 15 +++++++++++++++ sql/sql_select.cc | 3 +-- 4 files changed, 34 insertions(+), 8 deletions(-) diff --git a/mysql-test/r/explain.result b/mysql-test/r/explain.result index b8db8b53e06..8f2d704b312 100644 --- a/mysql-test/r/explain.result +++ b/mysql-test/r/explain.result @@ -226,4 +226,16 @@ Warnings: Note 1276 Field or reference 'test.t1.c' of SELECT #2 was resolved in SELECT #1 Note 1003 select (select 1 from `test`.`t2` where (`test`.`t2`.`d` = NULL)) AS `(SELECT 1 FROM t2 WHERE d = c)` from `test`.`t1` DROP TABLE t1, t2; +# +# Bug #48419: another explain crash.. +# +CREATE TABLE t1 (a INT); +CREATE TABLE t2 (b BLOB, KEY b(b(100))); +INSERT INTO t2 VALUES ('1'), ('2'), ('3'); +FLUSH TABLES; +EXPLAIN SELECT 1 FROM t1 WHERE a = (SELECT 1 FROM t1 t JOIN t2 WHERE b <= 1 AND t.a); +id select_type table type possible_keys key key_len ref rows Extra +1 PRIMARY NULL NULL NULL NULL NULL NULL NULL Impossible WHERE noticed after reading const tables +2 SUBQUERY NULL NULL NULL NULL NULL NULL NULL Impossible WHERE noticed after reading const tables +DROP TABLE t1, t2; End of 5.1 tests. diff --git a/mysql-test/r/ps.result b/mysql-test/r/ps.result index cf08d763e5c..84b9cdf930c 100644 --- a/mysql-test/r/ps.result +++ b/mysql-test/r/ps.result @@ -155,24 +155,24 @@ execute stmt1 ; id select_type table type possible_keys key key_len ref rows Extra 1 PRIMARY NULL NULL NULL NULL NULL NULL NULL Impossible WHERE noticed after reading const tables 6 DERIVED NULL NULL NULL NULL NULL NULL NULL no matching row in const table -5 DEPENDENT SUBQUERY t2 system NULL NULL NULL NULL 0 const row not found -4 DEPENDENT SUBQUERY t2 system NULL NULL NULL NULL 0 const row not found +5 DEPENDENT SUBQUERY NULL NULL NULL NULL NULL NULL NULL Impossible WHERE noticed after reading const tables +4 DEPENDENT SUBQUERY NULL NULL NULL NULL NULL NULL NULL Impossible WHERE noticed after reading const tables 3 DEPENDENT SUBQUERY NULL NULL NULL NULL NULL NULL NULL Impossible WHERE noticed after reading const tables 2 DEPENDENT SUBQUERY NULL NULL NULL NULL NULL NULL NULL Impossible WHERE noticed after reading const tables execute stmt1 ; id select_type table type possible_keys key key_len ref rows Extra 1 PRIMARY NULL NULL NULL NULL NULL NULL NULL Impossible WHERE noticed after reading const tables 6 DERIVED NULL NULL NULL NULL NULL NULL NULL no matching row in const table -5 DEPENDENT SUBQUERY t2 system NULL NULL NULL NULL 0 const row not found -4 DEPENDENT SUBQUERY t2 system NULL NULL NULL NULL 0 const row not found +5 DEPENDENT SUBQUERY NULL NULL NULL NULL NULL NULL NULL Impossible WHERE noticed after reading const tables +4 DEPENDENT SUBQUERY NULL NULL NULL NULL NULL NULL NULL Impossible WHERE noticed after reading const tables 3 DEPENDENT SUBQUERY NULL NULL NULL NULL NULL NULL NULL Impossible WHERE noticed after reading const tables 2 DEPENDENT SUBQUERY NULL NULL NULL NULL NULL NULL NULL Impossible WHERE noticed after reading const tables explain SELECT (SELECT SUM(c1 + c12 + 0.0) FROM t2 where (t1.c2 - 0e-3) = t2.c2 GROUP BY t1.c15 LIMIT 1) as scalar_s, exists (select 1.0e+0 from t2 where t2.c3 * 9.0000000000 = t1.c4) as exists_s, c5 * 4 in (select c6 + 0.3e+1 from t2) as in_s, (c7 - 4, c8 - 4) in (select c9 + 4.0, c10 + 40e-1 from t2) as in_row_s FROM t1, (select c25 x, c32 y from t2) tt WHERE x * 1 = c25; id select_type table type possible_keys key key_len ref rows Extra 1 PRIMARY NULL NULL NULL NULL NULL NULL NULL Impossible WHERE noticed after reading const tables 6 DERIVED NULL NULL NULL NULL NULL NULL NULL no matching row in const table -5 DEPENDENT SUBQUERY t2 system NULL NULL NULL NULL 0 const row not found -4 DEPENDENT SUBQUERY t2 system NULL NULL NULL NULL 0 const row not found +5 DEPENDENT SUBQUERY NULL NULL NULL NULL NULL NULL NULL Impossible WHERE noticed after reading const tables +4 DEPENDENT SUBQUERY NULL NULL NULL NULL NULL NULL NULL Impossible WHERE noticed after reading const tables 3 DEPENDENT SUBQUERY NULL NULL NULL NULL NULL NULL NULL Impossible WHERE noticed after reading const tables 2 DEPENDENT SUBQUERY NULL NULL NULL NULL NULL NULL NULL Impossible WHERE noticed after reading const tables deallocate prepare stmt1; diff --git a/mysql-test/t/explain.test b/mysql-test/t/explain.test index 3c2f7bbbe96..ba6be72dbdc 100644 --- a/mysql-test/t/explain.test +++ b/mysql-test/t/explain.test @@ -198,4 +198,19 @@ INSERT INTO t2 VALUES (NULL), (0); EXPLAIN EXTENDED SELECT (SELECT 1 FROM t2 WHERE d = c) FROM t1; DROP TABLE t1, t2; + +--echo # +--echo # Bug #48419: another explain crash.. +--echo # + +CREATE TABLE t1 (a INT); +CREATE TABLE t2 (b BLOB, KEY b(b(100))); +INSERT INTO t2 VALUES ('1'), ('2'), ('3'); + +FLUSH TABLES; + +EXPLAIN SELECT 1 FROM t1 WHERE a = (SELECT 1 FROM t1 t JOIN t2 WHERE b <= 1 AND t.a); + +DROP TABLE t1, t2; + --echo End of 5.1 tests. diff --git a/sql/sql_select.cc b/sql/sql_select.cc index a426f4b68a1..291432c2bb6 100644 --- a/sql/sql_select.cc +++ b/sql/sql_select.cc @@ -1107,8 +1107,7 @@ JOIN::optimize() } if (conds && const_table_map != found_const_table_map && - (select_options & SELECT_DESCRIBE) && - select_lex->master_unit() == &thd->lex->unit) // upper level SELECT + (select_options & SELECT_DESCRIBE)) { conds=new Item_int((longlong) 0,1); // Always false } From c658c3ed34b99e8fef0c41898ad295b1223071f3 Mon Sep 17 00:00:00 2001 From: sunanda Date: Wed, 23 Jun 2010 12:03:22 +0200 Subject: [PATCH 032/129] Backport into build-201006221614-5.1.46sp1 > ------------------------------------------------------------ > revno: 3367 [merge] > revision-id: joro@sun.com-20100504140328-srxf3c088j2twnq6 > parent: kristofer.pettersson@sun.com-20100503172109-f9hracq5pqsaomb1 > parent: joro@sun.com-20100503151651-nakknn8amrapmdp7 > committer: Georgi Kodinov > branch nick: B53371-5.1-bugteam > timestamp: Tue 2010-05-04 17:03:28 +0300 > message: > Bug #53371: COM_FIELD_LIST can be abused to bypass table level grants. > > This is the 5.1 merge and extension of the fix. > The server was happily accepting paths in table name in all places a table > name is accepted (e.g. a SELECT). This allowed all users that have some > privilege over some database to read all tables in all databases in all > mysql server instances that the server file system has access to. > Fixed by : > 1. making sure no path elements are allowed in quoted table name when > constructing the path (note that the path symbols are still valid in table names > when they're properly escaped by the server). > 2. checking the #mysql50# prefixed names the same way they're checked for > path elements in mysql-5.0. > ------------------------------------------------------------ > Use --include-merges or -n0 to see merged revisions. --- mysql-test/r/grant.result | 16 ++++++++++++++ mysql-test/t/grant.test | 25 ++++++++++++++++++++++ sql/mysql_priv.h | 2 +- sql/partition_info.cc | 4 ++-- sql/sql_parse.cc | 9 +++++++- sql/sql_table.cc | 14 ++++++++++++ sql/sql_yacc.yy | 2 +- sql/table.cc | 29 ++++++++++++++++++++++--- tests/mysql_client_test.c | 45 +++++++++++++++++++++++++++++++++++++++ 9 files changed, 138 insertions(+), 8 deletions(-) diff --git a/mysql-test/r/grant.result b/mysql-test/r/grant.result index 92beccd2a9e..6831ef6183d 100644 --- a/mysql-test/r/grant.result +++ b/mysql-test/r/grant.result @@ -1413,3 +1413,19 @@ DROP USER 'user1'; DROP USER 'user1'@'localhost'; DROP USER 'user2'; DROP DATABASE db1; +CREATE DATABASE db1; +CREATE DATABASE db2; +GRANT SELECT ON db1.* to 'testbug'@localhost; +USE db2; +CREATE TABLE t1 (a INT); +USE test; +SELECT * FROM `../db2/tb2`; +ERROR 42S02: Table 'db1.../db2/tb2' doesn't exist +SELECT * FROM `../db2`.tb2; +ERROR 42000: SELECT command denied to user 'testbug'@'localhost' for table 'tb2' +SELECT * FROM `#mysql50#/../db2/tb2`; +ERROR 42S02: Table 'db1.#mysql50#/../db2/tb2' doesn't exist +DROP USER 'testbug'@localhost; +DROP TABLE db2.t1; +DROP DATABASE db1; +DROP DATABASE db2; diff --git a/mysql-test/t/grant.test b/mysql-test/t/grant.test index bcd393bd6ab..cb8d3c63be8 100644 --- a/mysql-test/t/grant.test +++ b/mysql-test/t/grant.test @@ -1525,5 +1525,30 @@ DROP USER 'user1'@'localhost'; DROP USER 'user2'; DROP DATABASE db1; + +# +# Bug #53371: COM_FIELD_LIST can be abused to bypass table level grants. +# + +CREATE DATABASE db1; +CREATE DATABASE db2; +GRANT SELECT ON db1.* to 'testbug'@localhost; +USE db2; +CREATE TABLE t1 (a INT); +USE test; +connect (con1,localhost,testbug,,db1); +--error ER_NO_SUCH_TABLE +SELECT * FROM `../db2/tb2`; +--error ER_TABLEACCESS_DENIED_ERROR +SELECT * FROM `../db2`.tb2; +--error ER_NO_SUCH_TABLE +SELECT * FROM `#mysql50#/../db2/tb2`; +connection default; +disconnect con1; +DROP USER 'testbug'@localhost; +DROP TABLE db2.t1; +DROP DATABASE db1; +DROP DATABASE db2; + # Wait till we reached the initial number of concurrent sessions --source include/wait_until_count_sessions.inc diff --git a/sql/mysql_priv.h b/sql/mysql_priv.h index 56175d069c5..3ecbef4d456 100644 --- a/sql/mysql_priv.h +++ b/sql/mysql_priv.h @@ -2263,7 +2263,7 @@ void update_create_info_from_table(HA_CREATE_INFO *info, TABLE *form); int rename_file_ext(const char * from,const char * to,const char * ext); bool check_db_name(LEX_STRING *db); bool check_column_name(const char *name); -bool check_table_name(const char *name, uint length); +bool check_table_name(const char *name, uint length, bool check_for_path_chars); char *get_field(MEM_ROOT *mem, Field *field); bool get_field(MEM_ROOT *mem, Field *field, class String *res); int wild_case_compare(CHARSET_INFO *cs, const char *str,const char *wildstr); diff --git a/sql/partition_info.cc b/sql/partition_info.cc index ba9ea0e876e..6e2f7dfad26 100644 --- a/sql/partition_info.cc +++ b/sql/partition_info.cc @@ -972,7 +972,7 @@ bool partition_info::check_partition_info(THD *thd, handlerton **eng_type, part_elem->engine_type= default_engine_type; } if (check_table_name(part_elem->partition_name, - strlen(part_elem->partition_name))) + strlen(part_elem->partition_name), FALSE)) { my_error(ER_WRONG_PARTITION_NAME, MYF(0)); goto end; @@ -990,7 +990,7 @@ bool partition_info::check_partition_info(THD *thd, handlerton **eng_type, { sub_elem= sub_it++; if (check_table_name(sub_elem->partition_name, - strlen(sub_elem->partition_name))) + strlen(sub_elem->partition_name), FALSE)) { my_error(ER_WRONG_PARTITION_NAME, MYF(0)); goto end; diff --git a/sql/sql_parse.cc b/sql/sql_parse.cc index 11481933c8a..93d80164ffb 100644 --- a/sql/sql_parse.cc +++ b/sql/sql_parse.cc @@ -1310,6 +1310,13 @@ bool dispatch_command(enum enum_server_command command, THD *thd, } thd->convert_string(&conv_name, system_charset_info, packet, arg_length, thd->charset()); + if (check_table_name(conv_name.str, conv_name.length, FALSE)) + { + /* this is OK due to convert_string() null-terminating the string */ + my_error(ER_WRONG_TABLE_NAME, MYF(0), conv_name.str); + break; + } + table_list.alias= table_list.table_name= conv_name.str; packet= arg_end + 1; @@ -6233,7 +6240,7 @@ TABLE_LIST *st_select_lex::add_table_to_list(THD *thd, DBUG_RETURN(0); // End of memory alias_str= alias ? alias->str : table->table.str; if (!test(table_options & TL_OPTION_ALIAS) && - check_table_name(table->table.str, table->table.length)) + check_table_name(table->table.str, table->table.length, FALSE)) { my_error(ER_WRONG_TABLE_NAME, MYF(0), table->table.str); DBUG_RETURN(0); diff --git a/sql/sql_table.cc b/sql/sql_table.cc index ad72cab664e..84e6c721d72 100644 --- a/sql/sql_table.cc +++ b/sql/sql_table.cc @@ -435,7 +435,21 @@ uint tablename_to_filename(const char *from, char *to, uint to_length) DBUG_PRINT("enter", ("from '%s'", from)); if ((length= check_n_cut_mysql50_prefix(from, to, to_length))) + { + /* + Check if the name supplied is a valid mysql 5.0 name and + make the name a zero length string if it's not. + Note that just returning zero length is not enough : + a lot of places don't check the return value and expect + a zero terminated string. + */ + if (check_table_name(to, length, TRUE)) + { + to[0]= 0; + length= 0; + } DBUG_RETURN(length); + } length= strconvert(system_charset_info, from, &my_charset_filename, to, to_length, &errors); if (check_if_legal_tablename(to) && diff --git a/sql/sql_yacc.yy b/sql/sql_yacc.yy index 4f43ab8bebd..f815da006b1 100644 --- a/sql/sql_yacc.yy +++ b/sql/sql_yacc.yy @@ -6133,7 +6133,7 @@ alter_list_item: { MYSQL_YYABORT; } - if (check_table_name($3->table.str,$3->table.length) || + if (check_table_name($3->table.str,$3->table.length, FALSE) || ($3->db.str && check_db_name(&$3->db))) { my_error(ER_WRONG_TABLE_NAME, MYF(0), $3->table.str); diff --git a/sql/table.cc b/sql/table.cc index a4e2c59fb87..04d7b3a8d0a 100644 --- a/sql/table.cc +++ b/sql/table.cc @@ -494,6 +494,26 @@ inline bool is_system_table_name(const char *name, uint length) } +/** + Check if a string contains path elements +*/ + +static inline bool has_disabled_path_chars(const char *str) +{ + for (; *str; str++) + switch (*str) + { + case FN_EXTCHAR: + case '/': + case '\\': + case '~': + case '@': + return TRUE; + } + return FALSE; +} + + /* Read table definition from a binary / text based .frm file @@ -549,7 +569,8 @@ int open_table_def(THD *thd, TABLE_SHARE *share, uint db_flags) This kind of tables must have been opened only by the my_open() above. */ - if (strchr(share->table_name.str, '@') || + if (has_disabled_path_chars(share->table_name.str) || + has_disabled_path_chars(share->db.str) || !strncmp(share->db.str, MYSQL50_TABLE_NAME_PREFIX, MYSQL50_TABLE_NAME_PREFIX_LENGTH) || !strncmp(share->table_name.str, MYSQL50_TABLE_NAME_PREFIX, @@ -2711,7 +2732,6 @@ bool check_db_name(LEX_STRING *org_name) (name_length > NAME_CHAR_LEN)); /* purecov: inspected */ } - /* Allow anything as a table name, as long as it doesn't contain an ' ' at the end @@ -2719,7 +2739,7 @@ bool check_db_name(LEX_STRING *org_name) */ -bool check_table_name(const char *name, uint length) +bool check_table_name(const char *name, uint length, bool check_for_path_chars) { uint name_length= 0; // name length in symbols const char *end= name+length; @@ -2746,6 +2766,9 @@ bool check_table_name(const char *name, uint length) continue; } } + if (check_for_path_chars && + (*name == '/' || *name == '\\' || *name == '~' || *name == FN_EXTCHAR)) + return 1; #endif name++; name_length++; diff --git a/tests/mysql_client_test.c b/tests/mysql_client_test.c index f65e549fd96..b99461ecd06 100644 --- a/tests/mysql_client_test.c +++ b/tests/mysql_client_test.c @@ -18049,6 +18049,50 @@ static void test_bug44495() DBUG_VOID_RETURN; } +static void test_bug53371() +{ + int rc; + MYSQL_RES *result; + + myheader("test_bug53371"); + + rc= mysql_query(mysql, "DROP TABLE IF EXISTS t1"); + myquery(rc); + rc= mysql_query(mysql, "DROP DATABASE IF EXISTS bug53371"); + myquery(rc); + rc= mysql_query(mysql, "DROP USER 'testbug'@localhost"); + + rc= mysql_query(mysql, "CREATE TABLE t1 (a INT)"); + myquery(rc); + rc= mysql_query(mysql, "CREATE DATABASE bug53371"); + myquery(rc); + rc= mysql_query(mysql, "GRANT SELECT ON bug53371.* to 'testbug'@localhost"); + myquery(rc); + + rc= mysql_change_user(mysql, "testbug", NULL, "bug53371"); + myquery(rc); + + rc= mysql_query(mysql, "SHOW COLUMNS FROM client_test_db.t1"); + DIE_UNLESS(rc); + DIE_UNLESS(mysql_errno(mysql) == 1142); + + result= mysql_list_fields(mysql, "../client_test_db/t1", NULL); + DIE_IF(result); + + result= mysql_list_fields(mysql, "#mysql50#/../client_test_db/t1", NULL); + DIE_IF(result); + + rc= mysql_change_user(mysql, opt_user, opt_password, current_db); + myquery(rc); + rc= mysql_query(mysql, "DROP TABLE t1"); + myquery(rc); + rc= mysql_query(mysql, "DROP DATABASE bug53371"); + myquery(rc); + rc= mysql_query(mysql, "DROP USER 'testbug'@localhost"); + myquery(rc); +} + + /* Read and parse arguments and MySQL options from my.cnf */ @@ -18358,6 +18402,7 @@ static struct my_tests_st my_tests[]= { { "test_bug30472", test_bug30472 }, { "test_bug20023", test_bug20023 }, { "test_bug45010", test_bug45010 }, + { "test_bug53371", test_bug53371 }, { "test_bug31418", test_bug31418 }, { "test_bug31669", test_bug31669 }, { "test_bug28386", test_bug28386 }, From 12c4c7a0ee06685e727d1fb0b8d6d5560a732816 Mon Sep 17 00:00:00 2001 From: sunanda Date: Wed, 23 Jun 2010 12:14:23 +0200 Subject: [PATCH 033/129] Backport into build-201006221614-5.1.46sp1 > ------------------------------------------------------------ > revno: 3386 > revision-id: sergey.glukhov@sun.com-20100518082821-yajhvbv1ghmlpu1n > parent: aelkin@mysql.com-20100516170332-x8priwrdjwolc065 > committer: Sergey Glukhov > branch nick: mysql-5.1-bugteam > timestamp: Tue 2010-05-18 13:28:21 +0500 > message: > Bug#48729 SELECT ... FROM INFORMATION_SCHEMA.ROUTINES causes memory to grow > Analysis showed that in case of accessing I_S table > ROUTINES we perform unnecessary allocations > with get_field() function for every processed row that > in their turn causes significant memory growth. > the fix is to avoid use of get_field(). --- sql/sql_show.cc | 74 ++++++++++++++++++++++++------------------------- 1 file changed, 37 insertions(+), 37 deletions(-) diff --git a/sql/sql_show.cc b/sql/sql_show.cc index cb60027842d..b4881125b14 100644 --- a/sql/sql_show.cc +++ b/sql/sql_show.cc @@ -4180,24 +4180,37 @@ int fill_schema_coll_charset_app(THD *thd, TABLE_LIST *tables, COND *cond) } +static inline void copy_field_as_string(Field *to_field, Field *from_field) +{ + char buff[MAX_FIELD_WIDTH]; + String tmp_str(buff, sizeof(buff), system_charset_info); + from_field->val_str(&tmp_str); + to_field->store(tmp_str.ptr(), tmp_str.length(), system_charset_info); +} + + bool store_schema_proc(THD *thd, TABLE *table, TABLE *proc_table, const char *wild, bool full_access, const char *sp_user) { - String tmp_string; - String sp_db, sp_name, definer; MYSQL_TIME time; LEX *lex= thd->lex; CHARSET_INFO *cs= system_charset_info; - get_field(thd->mem_root, proc_table->field[0], &sp_db); - get_field(thd->mem_root, proc_table->field[1], &sp_name); - get_field(thd->mem_root, proc_table->field[11], &definer); + char sp_db_buff[NAME_LEN + 1], sp_name_buff[NAME_LEN + 1], + definer_buff[USERNAME_LENGTH + HOSTNAME_LENGTH + 2]; + String sp_db(sp_db_buff, sizeof(sp_db_buff), cs); + String sp_name(sp_name_buff, sizeof(sp_name_buff), cs); + String definer(definer_buff, sizeof(definer_buff), cs); + + proc_table->field[0]->val_str(&sp_db); + proc_table->field[1]->val_str(&sp_name); + proc_table->field[11]->val_str(&definer); + if (!full_access) - full_access= !strcmp(sp_user, definer.ptr()); - if (!full_access && check_some_routine_access(thd, sp_db.ptr(), - sp_name.ptr(), - proc_table->field[2]-> - val_int() == - TYPE_ENUM_PROCEDURE)) + full_access= !strcmp(sp_user, definer.c_ptr_safe()); + if (!full_access && + check_some_routine_access(thd, sp_db.c_ptr_safe(), sp_name.c_ptr_safe(), + proc_table->field[2]->val_int() == + TYPE_ENUM_PROCEDURE)) return 0; if ((lex->sql_command == SQLCOM_SHOW_STATUS_PROC && @@ -4207,55 +4220,42 @@ bool store_schema_proc(THD *thd, TABLE *table, TABLE *proc_table, (sql_command_flags[lex->sql_command] & CF_STATUS_COMMAND) == 0) { restore_record(table, s->default_values); - if (!wild || !wild[0] || !wild_compare(sp_name.ptr(), wild, 0)) + if (!wild || !wild[0] || !wild_compare(sp_name.c_ptr_safe(), wild, 0)) { int enum_idx= (int) proc_table->field[5]->val_int(); table->field[3]->store(sp_name.ptr(), sp_name.length(), cs); - get_field(thd->mem_root, proc_table->field[3], &tmp_string); - table->field[0]->store(tmp_string.ptr(), tmp_string.length(), cs); + copy_field_as_string(table->field[0], proc_table->field[3]); table->field[2]->store(sp_db.ptr(), sp_db.length(), cs); - get_field(thd->mem_root, proc_table->field[2], &tmp_string); - table->field[4]->store(tmp_string.ptr(), tmp_string.length(), cs); + copy_field_as_string(table->field[4], proc_table->field[2]); if (proc_table->field[2]->val_int() == TYPE_ENUM_FUNCTION) { - get_field(thd->mem_root, proc_table->field[9], &tmp_string); - table->field[5]->store(tmp_string.ptr(), tmp_string.length(), cs); + copy_field_as_string(table->field[5], proc_table->field[9]); table->field[5]->set_notnull(); } if (full_access) { - get_field(thd->mem_root, proc_table->field[19], &tmp_string); - table->field[7]->store(tmp_string.ptr(), tmp_string.length(), cs); + copy_field_as_string(table->field[7], proc_table->field[19]); table->field[7]->set_notnull(); } table->field[6]->store(STRING_WITH_LEN("SQL"), cs); table->field[10]->store(STRING_WITH_LEN("SQL"), cs); - get_field(thd->mem_root, proc_table->field[6], &tmp_string); - table->field[11]->store(tmp_string.ptr(), tmp_string.length(), cs); + copy_field_as_string(table->field[11], proc_table->field[6]); table->field[12]->store(sp_data_access_name[enum_idx].str, sp_data_access_name[enum_idx].length , cs); - get_field(thd->mem_root, proc_table->field[7], &tmp_string); - table->field[14]->store(tmp_string.ptr(), tmp_string.length(), cs); + copy_field_as_string(table->field[14], proc_table->field[7]); + bzero((char *)&time, sizeof(time)); ((Field_timestamp *) proc_table->field[12])->get_time(&time); table->field[15]->store_time(&time, MYSQL_TIMESTAMP_DATETIME); bzero((char *)&time, sizeof(time)); ((Field_timestamp *) proc_table->field[13])->get_time(&time); table->field[16]->store_time(&time, MYSQL_TIMESTAMP_DATETIME); - get_field(thd->mem_root, proc_table->field[14], &tmp_string); - table->field[17]->store(tmp_string.ptr(), tmp_string.length(), cs); - get_field(thd->mem_root, proc_table->field[15], &tmp_string); - table->field[18]->store(tmp_string.ptr(), tmp_string.length(), cs); + copy_field_as_string(table->field[17], proc_table->field[14]); + copy_field_as_string(table->field[18], proc_table->field[15]); table->field[19]->store(definer.ptr(), definer.length(), cs); - - get_field(thd->mem_root, proc_table->field[16], &tmp_string); - table->field[20]->store(tmp_string.ptr(), tmp_string.length(), cs); - - get_field(thd->mem_root, proc_table->field[17], &tmp_string); - table->field[21]->store(tmp_string.ptr(), tmp_string.length(), cs); - - get_field(thd->mem_root, proc_table->field[18], &tmp_string); - table->field[22]->store(tmp_string.ptr(), tmp_string.length(), cs); + copy_field_as_string(table->field[20], proc_table->field[16]); + copy_field_as_string(table->field[21], proc_table->field[17]); + copy_field_as_string(table->field[22], proc_table->field[18]); return schema_table_store_record(thd, table); } From 1c87c8b1eeaf06e77a2651bbff80ec1a0170547d Mon Sep 17 00:00:00 2001 From: sunanda Date: Wed, 23 Jun 2010 12:22:05 +0200 Subject: [PATCH 034/129] Backport into build-201006221614-5.1.46sp1 > ------------------------------------------------------------ > revno: 3392.1.1 > revision-id: gshchepa@mysql.com-20100521184732-0jvpzinv0uwyvr2d > parent: sven.sandberg@sun.com-20100520153801-yyhujm1qqa4eyfn0 > committer: Gleb Shchepa > branch nick: 53804-5.1 > timestamp: Fri 2010-05-21 22:47:32 +0400 > message: > Bug #53804: serious flaws in the alter database .. upgrade > data directory name command > > The check_db_name function has been modified to validate tails of > #mysql50#-prefixed database names for compliance with MySQL 5.0 > database name encoding rules (the check_table_name function call > has been reused). --- mysql-test/r/renamedb.result | 2 +- mysql-test/r/upgrade.result | 28 ++++++++++++++++++++++++++++ mysql-test/t/renamedb.test | 2 +- mysql-test/t/upgrade.test | 34 ++++++++++++++++++++++++++++++++++ sql/mysql_priv.h | 1 + sql/sql_table.cc | 23 ++++++++++++++++++++--- sql/table.cc | 34 ++++++++++------------------------ 7 files changed, 95 insertions(+), 29 deletions(-) diff --git a/mysql-test/r/renamedb.result b/mysql-test/r/renamedb.result index ff8f89592fc..e77aca0d0b7 100644 --- a/mysql-test/r/renamedb.result +++ b/mysql-test/r/renamedb.result @@ -7,6 +7,6 @@ ERROR HY000: Incorrect usage of ALTER DATABASE UPGRADE DATA DIRECTORY NAME and n ALTER DATABASE `#mysql51#not-yet` UPGRADE DATA DIRECTORY NAME; ERROR HY000: Incorrect usage of ALTER DATABASE UPGRADE DATA DIRECTORY NAME and name ALTER DATABASE `#mysql50#` UPGRADE DATA DIRECTORY NAME; -ERROR HY000: Incorrect usage of ALTER DATABASE UPGRADE DATA DIRECTORY NAME and name +ERROR 42000: Incorrect database name '#mysql50#' ALTER DATABASE `#mysql50#upgrade-me` UPGRADE DATA DIRECTORY NAME; ERROR 42000: Unknown database '#mysql50#upgrade-me' diff --git a/mysql-test/r/upgrade.result b/mysql-test/r/upgrade.result index 034242079b1..da2f55b5bb1 100644 --- a/mysql-test/r/upgrade.result +++ b/mysql-test/r/upgrade.result @@ -112,3 +112,31 @@ select * from `a-b-c`.v1; f1 drop database `a-b-c`; use test; +# End of 5.0 tests +# +# Bug #53804: serious flaws in the alter database .. upgrade data +# directory name command +# +ALTER DATABASE `#mysql50#:` UPGRADE DATA DIRECTORY NAME; +ERROR 42000: Unknown database '#mysql50#:' +ALTER DATABASE `#mysql50#.` UPGRADE DATA DIRECTORY NAME; +ERROR 42000: Incorrect database name '#mysql50#.' +ALTER DATABASE `#mysql50#../` UPGRADE DATA DIRECTORY NAME; +ERROR 42000: Incorrect database name '#mysql50#../' +ALTER DATABASE `#mysql50#../..` UPGRADE DATA DIRECTORY NAME; +ERROR 42000: Incorrect database name '#mysql50#../..' +ALTER DATABASE `#mysql50#../../` UPGRADE DATA DIRECTORY NAME; +ERROR 42000: Incorrect database name '#mysql50#../../' +ALTER DATABASE `#mysql50#./blablabla` UPGRADE DATA DIRECTORY NAME; +ERROR 42000: Incorrect database name '#mysql50#./blablabla' +ALTER DATABASE `#mysql50#../blablabla` UPGRADE DATA DIRECTORY NAME; +ERROR 42000: Incorrect database name '#mysql50#../blablabla' +ALTER DATABASE `#mysql50#/` UPGRADE DATA DIRECTORY NAME; +ERROR 42000: Incorrect database name '#mysql50#/' +ALTER DATABASE `#mysql50#/.` UPGRADE DATA DIRECTORY NAME; +ERROR 42000: Incorrect database name '#mysql50#/.' +USE `#mysql50#.`; +ERROR 42000: Incorrect database name '#mysql50#.' +USE `#mysql50#../blablabla`; +ERROR 42000: Incorrect database name '#mysql50#../blablabla' +# End of 5.1 tests diff --git a/mysql-test/t/renamedb.test b/mysql-test/t/renamedb.test index 84315090b7a..71d0c127058 100644 --- a/mysql-test/t/renamedb.test +++ b/mysql-test/t/renamedb.test @@ -44,7 +44,7 @@ ALTER DATABASE `#mysql41#not-supported` UPGRADE DATA DIRECTORY NAME; --error ER_WRONG_USAGE ALTER DATABASE `#mysql51#not-yet` UPGRADE DATA DIRECTORY NAME; ---error ER_WRONG_USAGE +--error ER_WRONG_DB_NAME ALTER DATABASE `#mysql50#` UPGRADE DATA DIRECTORY NAME; --error ER_BAD_DB_ERROR diff --git a/mysql-test/t/upgrade.test b/mysql-test/t/upgrade.test index e390e8a1253..a7b9a1531ff 100644 --- a/mysql-test/t/upgrade.test +++ b/mysql-test/t/upgrade.test @@ -137,3 +137,37 @@ select * from `a-b-c`.v1; --enable_ps_protocol drop database `a-b-c`; use test; + +--echo # End of 5.0 tests + +--echo # +--echo # Bug #53804: serious flaws in the alter database .. upgrade data +--echo # directory name command +--echo # + +--error ER_BAD_DB_ERROR +ALTER DATABASE `#mysql50#:` UPGRADE DATA DIRECTORY NAME; +--error ER_WRONG_DB_NAME +ALTER DATABASE `#mysql50#.` UPGRADE DATA DIRECTORY NAME; +--error ER_WRONG_DB_NAME +ALTER DATABASE `#mysql50#../` UPGRADE DATA DIRECTORY NAME; +--error ER_WRONG_DB_NAME +ALTER DATABASE `#mysql50#../..` UPGRADE DATA DIRECTORY NAME; +--error ER_WRONG_DB_NAME +ALTER DATABASE `#mysql50#../../` UPGRADE DATA DIRECTORY NAME; +--error ER_WRONG_DB_NAME +ALTER DATABASE `#mysql50#./blablabla` UPGRADE DATA DIRECTORY NAME; +--error ER_WRONG_DB_NAME +ALTER DATABASE `#mysql50#../blablabla` UPGRADE DATA DIRECTORY NAME; +--error ER_WRONG_DB_NAME +ALTER DATABASE `#mysql50#/` UPGRADE DATA DIRECTORY NAME; +--error ER_WRONG_DB_NAME +ALTER DATABASE `#mysql50#/.` UPGRADE DATA DIRECTORY NAME; + +--error ER_WRONG_DB_NAME +USE `#mysql50#.`; +--error ER_WRONG_DB_NAME +USE `#mysql50#../blablabla`; + +--echo # End of 5.1 tests + diff --git a/sql/mysql_priv.h b/sql/mysql_priv.h index 3ecbef4d456..30f3a1af437 100644 --- a/sql/mysql_priv.h +++ b/sql/mysql_priv.h @@ -2287,6 +2287,7 @@ uint explain_filename(THD* thd, const char *from, char *to, uint to_length, uint filename_to_tablename(const char *from, char *to, uint to_length); uint tablename_to_filename(const char *from, char *to, uint to_length); uint check_n_cut_mysql50_prefix(const char *from, char *to, uint to_length); +bool check_mysql50_prefix(const char *name); #endif /* MYSQL_SERVER || INNODB_COMPATIBILITY_HOOKS */ #ifdef MYSQL_SERVER uint build_table_filename(char *buff, size_t bufflen, const char *db, diff --git a/sql/sql_table.cc b/sql/sql_table.cc index 84e6c721d72..babc025db87 100644 --- a/sql/sql_table.cc +++ b/sql/sql_table.cc @@ -391,6 +391,25 @@ uint filename_to_tablename(const char *from, char *to, uint to_length) } +/** + Check if given string begins with "#mysql50#" prefix + + @param name string to check cut + + @retval + FALSE no prefix found + @retval + TRUE prefix found +*/ + +bool check_mysql50_prefix(const char *name) +{ + return (name[0] == '#' && + !strncmp(name, MYSQL50_TABLE_NAME_PREFIX, + MYSQL50_TABLE_NAME_PREFIX_LENGTH)); +} + + /** Check if given string begins with "#mysql50#" prefix, cut it if so. @@ -406,9 +425,7 @@ uint filename_to_tablename(const char *from, char *to, uint to_length) uint check_n_cut_mysql50_prefix(const char *from, char *to, uint to_length) { - if (from[0] == '#' && - !strncmp(from, MYSQL50_TABLE_NAME_PREFIX, - MYSQL50_TABLE_NAME_PREFIX_LENGTH)) + if (check_mysql50_prefix(from)) return (uint) (strmake(to, from + MYSQL50_TABLE_NAME_PREFIX_LENGTH, to_length - 1) - to); return 0; diff --git a/sql/table.cc b/sql/table.cc index 04d7b3a8d0a..23d41760495 100644 --- a/sql/table.cc +++ b/sql/table.cc @@ -2701,44 +2701,30 @@ bool check_db_name(LEX_STRING *org_name) { char *name= org_name->str; uint name_length= org_name->length; + bool check_for_path_chars; if (!name_length || name_length > NAME_LEN) return 1; + if ((check_for_path_chars= check_mysql50_prefix(name))) + { + name+= MYSQL50_TABLE_NAME_PREFIX_LENGTH; + name_length-= MYSQL50_TABLE_NAME_PREFIX_LENGTH; + } + if (lower_case_table_names && name != any_db) my_casedn_str(files_charset_info, name); -#if defined(USE_MB) && defined(USE_MB_IDENT) - if (use_mb(system_charset_info)) - { - name_length= 0; - bool last_char_is_space= TRUE; - char *end= name + org_name->length; - while (name < end) - { - int len; - last_char_is_space= my_isspace(system_charset_info, *name); - len= my_ismbchar(system_charset_info, name, end); - if (!len) - len= 1; - name+= len; - name_length++; - } - return (last_char_is_space || name_length > NAME_CHAR_LEN); - } - else -#endif - return ((org_name->str[org_name->length - 1] != ' ') || - (name_length > NAME_CHAR_LEN)); /* purecov: inspected */ + return check_table_name(name, name_length, check_for_path_chars); } + /* Allow anything as a table name, as long as it doesn't contain an ' ' at the end returns 1 on error */ - bool check_table_name(const char *name, uint length, bool check_for_path_chars) { uint name_length= 0; // name length in symbols @@ -2766,10 +2752,10 @@ bool check_table_name(const char *name, uint length, bool check_for_path_chars) continue; } } +#endif if (check_for_path_chars && (*name == '/' || *name == '\\' || *name == '~' || *name == FN_EXTCHAR)) return 1; -#endif name++; name_length++; } From a1c6a39a1320ec2cb1ec816543873513a97ee0a5 Mon Sep 17 00:00:00 2001 From: Jon Olav Hauglid Date: Wed, 23 Jun 2010 13:34:40 +0200 Subject: [PATCH 035/129] Backport from mysql-6.0-codebase of: ------------------------------------------------------------ revno: 3672 committer: lars-erik.bjork@sun.com branch nick: 48067-mysql-6.0-codebase-bugfixing timestamp: Mon 2009-10-26 13:51:43 +0100 message: This is a patch for bug#48067 "A temp table with the same name as an existing table, makes drop database fail" When dropping the database, mysql_rm_known_files() reads the contents of the database directory, and creates a TABLE_LIST object, for each .frm file encountered. Temporary tables, however, are not associated with any .frm file. The list of tables to drop are passed to mysql_rm_table_part2(). This method prefers temporary tables over regular tables, so if there is a temporary table with the same name as a regular, the temporary is removed, leaving the regular table intact. Regular tables are only deleted if there are no temporary tables with the same name. This fix ensures, that for all TABLE_LIST objects that are created by mysql_rm_known_files(), 'open_type' is set to 'OT_BASE_ONLY', to indicate that this is a regular table. In all cases in mysql_rm_table_part2() where we prefer a temporary table to a non-temporary table, we chek if 'open_type' equals 'OT_BASE_ONLY'. mysql-test/r/temp_table.result: The expected result of the test. mysql-test/t/temp_table.test: Test based on the bug report. sql/sql_db.cc: For all TABLE_LIST objects that are created by mysql_rm_known_files(), 'open_type' is set to 'OT_BASE_ONLY', to indicate that these are regular tables. sql/sql_table.cc: Check if 'open_type' is set to 'OT_BASE_ONLY, every place a temporary table is preferred to a non-temporary table. --- mysql-test/r/temp_table.result | 12 ++++++++++++ mysql-test/t/temp_table.test | 15 +++++++++++++++ sql/sql_db.cc | 1 + sql/sql_table.cc | 10 +++++++--- 4 files changed, 35 insertions(+), 3 deletions(-) diff --git a/mysql-test/r/temp_table.result b/mysql-test/r/temp_table.result index ba6b9f81a2d..33f5c6b5165 100644 --- a/mysql-test/r/temp_table.result +++ b/mysql-test/r/temp_table.result @@ -210,4 +210,16 @@ UPDATE t1,t2 SET t1.a = t2.a; INSERT INTO t2 SELECT f1(); DROP TABLE t1,t2,t3; DROP FUNCTION f1; +# +# Bug #48067: A temp table with the same name as an existing table, +# makes drop database fail. +# +DROP TEMPORARY TABLE IF EXISTS bug48067.t1; +DROP DATABASE IF EXISTS bug48067; +CREATE DATABASE bug48067; +CREATE TABLE bug48067.t1 (c1 int); +INSERT INTO bug48067.t1 values (1); +CREATE TEMPORARY TABLE bug48067.t1 (c1 int); +DROP DATABASE bug48067; +DROP TEMPORARY table bug48067.t1; End of 5.1 tests diff --git a/mysql-test/t/temp_table.test b/mysql-test/t/temp_table.test index 2bfa4936c91..92c22242cdb 100644 --- a/mysql-test/t/temp_table.test +++ b/mysql-test/t/temp_table.test @@ -235,4 +235,19 @@ INSERT INTO t2 SELECT f1(); DROP TABLE t1,t2,t3; DROP FUNCTION f1; +--echo # +--echo # Bug #48067: A temp table with the same name as an existing table, +--echo # makes drop database fail. +--echo # +--disable_warnings +DROP TEMPORARY TABLE IF EXISTS bug48067.t1; +DROP DATABASE IF EXISTS bug48067; +--enable_warnings +CREATE DATABASE bug48067; +CREATE TABLE bug48067.t1 (c1 int); +INSERT INTO bug48067.t1 values (1); +CREATE TEMPORARY TABLE bug48067.t1 (c1 int); +DROP DATABASE bug48067; +DROP TEMPORARY table bug48067.t1; + --echo End of 5.1 tests diff --git a/sql/sql_db.cc b/sql/sql_db.cc index 2e48475f298..5e992d2391c 100644 --- a/sql/sql_db.cc +++ b/sql/sql_db.cc @@ -1196,6 +1196,7 @@ static long mysql_rm_known_files(THD *thd, MY_DIR *dirp, const char *db, (void) filename_to_tablename(file->name, table_list->table_name, MYSQL50_TABLE_NAME_PREFIX_LENGTH + strlen(file->name) + 1); + table_list->open_type= OT_BASE_ONLY; /* To be able to correctly look up the table in the table cache. */ if (lower_case_table_names) diff --git a/sql/sql_table.cc b/sql/sql_table.cc index 902e7fa7b5f..e0e32b81e03 100644 --- a/sql/sql_table.cc +++ b/sql/sql_table.cc @@ -1964,7 +1964,8 @@ int mysql_rm_table_part2(THD *thd, TABLE_LIST *tables, bool if_exists, else { for (table= tables; table; table= table->next_local) - if (find_temporary_table(thd, table->db, table->table_name)) + if (table->open_type != OT_BASE_ONLY && + find_temporary_table(thd, table->db, table->table_name)) { /* A temporary table. @@ -2009,8 +2010,11 @@ int mysql_rm_table_part2(THD *thd, TABLE_LIST *tables, bool if_exists, table->db, table->table_name, (long) table->table, table->table ? (long) table->table->s : (long) -1)); - error= drop_temporary_table(thd, table); - + if (table->open_type == OT_BASE_ONLY) + error= 1; + else + error= drop_temporary_table(thd, table); + switch (error) { case 0: // removed temporary table From 9b5d1d98da9c3d1e216e43849ac05527852ec410 Mon Sep 17 00:00:00 2001 From: Jon Olav Hauglid Date: Fri, 25 Jun 2010 09:07:18 +0200 Subject: [PATCH 036/129] Bug #53757 assert in mysql_truncate_by_delete The assert was triggered if a connection executing TRUNCATE on a InnoDB table was killed during open_tables. This bug was fixed in the scope of Bug #45643 "InnoDB does not support replication of TRUNCATE TABLE". This patch adds test coverage to innodb_mysql_sync.test. --- mysql-test/r/innodb_mysql_sync.result | 18 ++++++++++++++++++ mysql-test/t/innodb_mysql_sync.test | 26 ++++++++++++++++++++++++++ sql/sql_base.cc | 1 + 3 files changed, 45 insertions(+) diff --git a/mysql-test/r/innodb_mysql_sync.result b/mysql-test/r/innodb_mysql_sync.result index 0e75e62b13a..43a98829d4e 100644 --- a/mysql-test/r/innodb_mysql_sync.result +++ b/mysql-test/r/innodb_mysql_sync.result @@ -48,3 +48,21 @@ Warnings: Error 1146 Table 'test.t1' doesn't exist # Connection default SET DEBUG_SYNC= "RESET"; +# +# Bug#53757 assert in mysql_truncate_by_delete +# +DROP TABLE IF EXISTS t1, t2; +CREATE TABLE t1(a INT) Engine=InnoDB; +CREATE TABLE t2(id INT); +INSERT INTO t1 VALUES (1), (2); +INSERT INTO t2 VALUES(connection_id()); +SET DEBUG_SYNC= "open_and_process_table SIGNAL opening WAIT_FOR killed"; +# Sending: (not reaped since connection is killed later) +TRUNCATE t1; +SET DEBUG_SYNC= "now WAIT_FOR opening"; +SELECT ((@id := id) - id) FROM t2; +((@id := id) - id) +0 +KILL @id; +SET DEBUG_SYNC= "now SIGNAL killed"; +DROP TABLE t1, t2; diff --git a/mysql-test/t/innodb_mysql_sync.test b/mysql-test/t/innodb_mysql_sync.test index ee92ee9f52e..07f75afec40 100644 --- a/mysql-test/t/innodb_mysql_sync.test +++ b/mysql-test/t/innodb_mysql_sync.test @@ -80,6 +80,32 @@ disconnect con1; SET DEBUG_SYNC= "RESET"; +--echo # +--echo # Bug#53757 assert in mysql_truncate_by_delete +--echo # + +--disable_warnings +DROP TABLE IF EXISTS t1, t2; +--enable_warnings + +CREATE TABLE t1(a INT) Engine=InnoDB; +CREATE TABLE t2(id INT); +INSERT INTO t1 VALUES (1), (2); + +connect (con1, localhost, root); +INSERT INTO t2 VALUES(connection_id()); +SET DEBUG_SYNC= "open_and_process_table SIGNAL opening WAIT_FOR killed"; +--echo # Sending: (not reaped since connection is killed later) +--send TRUNCATE t1 + +connection default; +SET DEBUG_SYNC= "now WAIT_FOR opening"; +SELECT ((@id := id) - id) FROM t2; +KILL @id; +SET DEBUG_SYNC= "now SIGNAL killed"; +DROP TABLE t1, t2; + + # Check that all connections opened by test cases in this file are really # gone so execution of other tests won't be affected by their presence. --source include/wait_until_count_sessions.inc diff --git a/sql/sql_base.cc b/sql/sql_base.cc index bd73dd57367..0d4d949d701 100644 --- a/sql/sql_base.cc +++ b/sql/sql_base.cc @@ -4429,6 +4429,7 @@ open_and_process_table(THD *thd, LEX *lex, TABLE_LIST *tables, bool error= FALSE; bool safe_to_ignore_table= FALSE; DBUG_ENTER("open_and_process_table"); + DEBUG_SYNC(thd, "open_and_process_table"); /* Ignore placeholders for derived tables. After derived tables From 349b34b3638e70eccdbbfa98daebb5c382ab4f29 Mon Sep 17 00:00:00 2001 From: Jon Olav Hauglid Date: Sat, 26 Jun 2010 22:23:28 +0200 Subject: [PATCH 037/129] Bug #49891 View DDL breaks REPEATABLE READ The problem was that if a query accessing a view was blocked due to conflicting locks on tables in the view definition, it would be possible for a different connection to alter the view definition before the view query completed. When the view query later resumed, it used the old view definition. This meant that if the view query was later repeated inside the same transaction, the two executions of the query would give different results, thus breaking repeatable read. (The first query used the old view definition, the second used the new view definition). This bug is no longer repeatable with the recent changes to the metadata locking subsystem (revno: 3040). The view query will no longer back-off and release the lock on the view definiton. Instead it will wait for the conflicting lock(s) to go away while keeping the view definition lock. This means that it is no longer possible for a concurrent connection to alter the view definition. Instead, any such attempt will be blocked. In the case from the bug report where the same view query was executed twice inside the same transaction, any ALTER VIEW from other connections will now be blocked until the transaction has completed (or aborted). The view queries will therefore use the same view definition and we will have repeatable read. Test case added to innodb_mysql_lock.test. This patch contains no code changes. --- mysql-test/r/innodb_mysql_lock.result | 32 +++++++++++++ mysql-test/t/innodb_mysql_lock.test | 68 +++++++++++++++++++++++++++ 2 files changed, 100 insertions(+) diff --git a/mysql-test/r/innodb_mysql_lock.result b/mysql-test/r/innodb_mysql_lock.result index 95adf712cb4..bf1c3a89f40 100644 --- a/mysql-test/r/innodb_mysql_lock.result +++ b/mysql-test/r/innodb_mysql_lock.result @@ -116,3 +116,35 @@ Table Op Msg_type Msg_text test.t1 optimize note Table does not support optimize, doing recreate + analyze instead test.t1 optimize status OK DROP TABLE t1; +# +# Bug#49891 View DDL breaks REPEATABLE READ +# +DROP TABLE IF EXISTS t1, t2; +DROP VIEW IF EXISTS v2; +CREATE TABLE t1 ( f1 INTEGER ) ENGINE = innodb; +CREATE TABLE t2 ( f1 INTEGER ); +CREATE VIEW v1 AS SELECT 1 FROM t1; +# Connection con3 +LOCK TABLE t1 WRITE; +# Connection default +START TRANSACTION; +# Sending: +SELECT * FROM v1; +# Connection con2 +# Waiting for 'SELECT * FROM v1' to sync in. +# Sending: +ALTER VIEW v1 AS SELECT 2 FROM t2; +# Connection con3 +# Waiting for 'ALTER VIEW v1 AS SELECT 2 FROM t2' to sync in. +UNLOCK TABLES; +# Connection default; +# Reaping: SELECT * FROM v1 +1 +SELECT * FROM v1; +1 +COMMIT; +# Connection con2 +# Reaping: ALTER VIEW v1 AS SELECT 2 FROM t2 +# Connection default +DROP TABLE t1, t2; +DROP VIEW v1; diff --git a/mysql-test/t/innodb_mysql_lock.test b/mysql-test/t/innodb_mysql_lock.test index 36d09b4c411..c8ece729b19 100644 --- a/mysql-test/t/innodb_mysql_lock.test +++ b/mysql-test/t/innodb_mysql_lock.test @@ -209,6 +209,74 @@ disconnect con1; DROP TABLE t1; +--echo # +--echo # Bug#49891 View DDL breaks REPEATABLE READ +--echo # + +--disable_warnings +DROP TABLE IF EXISTS t1, t2; +DROP VIEW IF EXISTS v2; +--enable_warnings + +CREATE TABLE t1 ( f1 INTEGER ) ENGINE = innodb; +CREATE TABLE t2 ( f1 INTEGER ); +CREATE VIEW v1 AS SELECT 1 FROM t1; + +connect (con2, localhost, root); +connect (con3, localhost, root); + +--echo # Connection con3 +connection con3; +LOCK TABLE t1 WRITE; + +--echo # Connection default +connection default; +START TRANSACTION; +# This should block due to t1 being locked. +--echo # Sending: +--send SELECT * FROM v1 + +--echo # Connection con2 +connection con2; +--echo # Waiting for 'SELECT * FROM v1' to sync in. +let $wait_condition= + SELECT COUNT(*) = 1 FROM information_schema.processlist + WHERE state = "Waiting for table" AND info = "SELECT * FROM v1"; +--source include/wait_condition.inc +# This should block due to v1 being locked. +--echo # Sending: +--send ALTER VIEW v1 AS SELECT 2 FROM t2 + +--echo # Connection con3 +connection con3; +--echo # Waiting for 'ALTER VIEW v1 AS SELECT 2 FROM t2' to sync in. +let $wait_condition= + SELECT COUNT(*) = 1 FROM information_schema.processlist + WHERE state = "Waiting for table" AND info = "ALTER VIEW v1 AS SELECT 2 FROM t2"; +--source include/wait_condition.inc +# Unlock t1 allowing SELECT * FROM v1 to proceed. +UNLOCK TABLES; + +--echo # Connection default; +connection default; +--echo # Reaping: SELECT * FROM v1 +--reap +SELECT * FROM v1; +COMMIT; + +--echo # Connection con2 +connection con2; +--echo # Reaping: ALTER VIEW v1 AS SELECT 2 FROM t2 +--reap + +--echo # Connection default +connection default; +DROP TABLE t1, t2; +DROP VIEW v1; +disconnect con2; +disconnect con3; + + # Check that all connections opened by test cases in this file are really # gone so execution of other tests won't be affected by their presence. --source include/wait_until_count_sessions.inc From 1b31b3a38aabefc942ac55d2d6932b2c810d744d Mon Sep 17 00:00:00 2001 From: Jimmy Yang Date: Mon, 28 Jun 2010 19:41:37 -0700 Subject: [PATCH 038/129] Check in fix for bug #53756: "ALTER TABLE ADD PRIMARY KEY affects crash recovery" rb://369 approved by Marko --- .../suite/innodb/r/innodb_bug53756.result | 118 +++++++++++ .../suite/innodb/t/innodb_bug53756.test | 184 ++++++++++++++++++ storage/innobase/dict/dict0load.c | 27 ++- 3 files changed, 315 insertions(+), 14 deletions(-) create mode 100644 mysql-test/suite/innodb/r/innodb_bug53756.result create mode 100644 mysql-test/suite/innodb/t/innodb_bug53756.test diff --git a/mysql-test/suite/innodb/r/innodb_bug53756.result b/mysql-test/suite/innodb/r/innodb_bug53756.result new file mode 100644 index 00000000000..67797f9c90f --- /dev/null +++ b/mysql-test/suite/innodb/r/innodb_bug53756.result @@ -0,0 +1,118 @@ +DROP TABLE IF EXISTS bug_53756 ; +CREATE TABLE bug_53756 (pk INT, c1 INT) ENGINE=InnoDB; +ALTER TABLE bug_53756 ADD PRIMARY KEY (pk); +INSERT INTO bug_53756 VALUES(1, 11), (2, 22), (3, 33), (4, 44); + +# Select a less restrictive isolation level. +SET GLOBAL TRANSACTION ISOLATION LEVEL READ COMMITTED; +SET SESSION TRANSACTION ISOLATION LEVEL READ COMMITTED; +COMMIT; + +# Start a transaction in the default connection for isolation. +START TRANSACTION; +SELECT @@tx_isolation; +@@tx_isolation +READ-COMMITTED +SELECT * FROM bug_53756; +pk c1 +1 11 +2 22 +3 33 +4 44 + +# connection con1 deletes row 1 +START TRANSACTION; +SELECT @@tx_isolation; +@@tx_isolation +READ-COMMITTED +DELETE FROM bug_53756 WHERE pk=1; + +# connection con2 deletes row 2 +START TRANSACTION; +SELECT @@tx_isolation; +@@tx_isolation +READ-COMMITTED +DELETE FROM bug_53756 WHERE pk=2; + +# connection con3 updates row 3 +START TRANSACTION; +SELECT @@tx_isolation; +@@tx_isolation +READ-COMMITTED +UPDATE bug_53756 SET c1=77 WHERE pk=3; + +# connection con4 updates row 4 +START TRANSACTION; +SELECT @@tx_isolation; +@@tx_isolation +READ-COMMITTED +UPDATE bug_53756 SET c1=88 WHERE pk=4; + +# connection con5 inserts row 5 +START TRANSACTION; +SELECT @@tx_isolation; +@@tx_isolation +READ-COMMITTED +INSERT INTO bug_53756 VALUES(5, 55); + +# connection con6 inserts row 6 +START TRANSACTION; +SELECT @@tx_isolation; +@@tx_isolation +READ-COMMITTED +INSERT INTO bug_53756 VALUES(6, 66); + +# connection con1 commits. +COMMIT; + +# connection con3 commits. +COMMIT; + +# connection con4 rolls back. +ROLLBACK; + +# connection con6 rolls back. +ROLLBACK; + +# The connections 2 and 5 stay open. + +# connection default selects resulting data. +# Delete of row 1 was committed. +# Dpdate of row 3 was committed. +# Due to isolation level read committed, these should be included. +# All other changes should not be included. +SELECT * FROM bug_53756; +pk c1 +2 22 +3 77 +4 44 + +# connection default +# +# Crash server. +START TRANSACTION; +INSERT INTO bug_53756 VALUES (666,666); +SET SESSION debug="+d,crash_commit_before"; +COMMIT; +ERROR HY000: Lost connection to MySQL server during query + +# +# disconnect con1, con2, con3, con4, con5, con6. +# +# Restart server. + +# +# Select recovered data. +# Delete of row 1 was committed. +# Update of row 3 was committed. +# These should be included. +# All other changes should not be included. +# Delete of row 2 and insert of row 5 should be rolled back +SELECT * FROM bug_53756; +pk c1 +2 22 +3 77 +4 44 + +# Clean up. +DROP TABLE bug_53756; diff --git a/mysql-test/suite/innodb/t/innodb_bug53756.test b/mysql-test/suite/innodb/t/innodb_bug53756.test new file mode 100644 index 00000000000..85a09478486 --- /dev/null +++ b/mysql-test/suite/innodb/t/innodb_bug53756.test @@ -0,0 +1,184 @@ +# This is the test case for bug #53756. Alter table operation could +# leave a deleted record for the temp table (later renamed to the altered +# table) in the SYS_TABLES secondary index, we should ignore this row and +# find the first non-deleted row for the specified table_id when load table +# metadata in the function dict_load_table_on_id() during crash recovery. + +# +# innobackup needs to connect to the server. Not supported in embedded. +--source include/not_embedded.inc +# +# This test case needs to crash the server. Needs a debug server. +--source include/have_debug.inc +# +# Don't test this under valgrind, memory leaks will occur. +--source include/not_valgrind.inc +# +# This test case needs InnoDB. +--source include/have_innodb.inc + +# +# Precautionary clean up. +# +--disable_warnings +DROP TABLE IF EXISTS bug_53756 ; +--enable_warnings + +# +# Create test data. +# +CREATE TABLE bug_53756 (pk INT, c1 INT) ENGINE=InnoDB; +ALTER TABLE bug_53756 ADD PRIMARY KEY (pk); +INSERT INTO bug_53756 VALUES(1, 11), (2, 22), (3, 33), (4, 44); + +--echo +--echo # Select a less restrictive isolation level. +# Don't use user variables. They won't survive server crash. +--let $global_isolation= `SELECT @@global.tx_isolation`; +--let $session_isolation= `SELECT @@session.tx_isolation`; +SET GLOBAL TRANSACTION ISOLATION LEVEL READ COMMITTED; +SET SESSION TRANSACTION ISOLATION LEVEL READ COMMITTED; +COMMIT; + +--echo +--echo # Start a transaction in the default connection for isolation. +START TRANSACTION; +SELECT @@tx_isolation; +SELECT * FROM bug_53756; + +--echo +--echo # connection con1 deletes row 1 +--connect (con1,localhost,root,,) +START TRANSACTION; +SELECT @@tx_isolation; +DELETE FROM bug_53756 WHERE pk=1; + +--echo +--echo # connection con2 deletes row 2 +--connect (con2,localhost,root,,) +START TRANSACTION; +SELECT @@tx_isolation; +DELETE FROM bug_53756 WHERE pk=2; + +--echo +--echo # connection con3 updates row 3 +--connect (con3,localhost,root,,) +START TRANSACTION; +SELECT @@tx_isolation; +UPDATE bug_53756 SET c1=77 WHERE pk=3; + +--echo +--echo # connection con4 updates row 4 +--connect (con4,localhost,root,,) +START TRANSACTION; +SELECT @@tx_isolation; +UPDATE bug_53756 SET c1=88 WHERE pk=4; + +--echo +--echo # connection con5 inserts row 5 +--connect (con5,localhost,root,,) +START TRANSACTION; +SELECT @@tx_isolation; +INSERT INTO bug_53756 VALUES(5, 55); + +--echo +--echo # connection con6 inserts row 6 +--connect (con6,localhost,root,,) +START TRANSACTION; +SELECT @@tx_isolation; +INSERT INTO bug_53756 VALUES(6, 66); + +--echo +--echo # connection con1 commits. +--connection con1 +COMMIT; + +--echo +--echo # connection con3 commits. +--connection con3 +COMMIT; + +--echo +--echo # connection con4 rolls back. +--connection con4 +ROLLBACK; + +--echo +--echo # connection con6 rolls back. +--connection con6 +ROLLBACK; + +--echo +--echo # The connections 2 and 5 stay open. + +--echo +--echo # connection default selects resulting data. +--echo # Delete of row 1 was committed. +--echo # Dpdate of row 3 was committed. +--echo # Due to isolation level read committed, these should be included. +--echo # All other changes should not be included. +--connection default +SELECT * FROM bug_53756; + +--echo +--echo # connection default +--connection default +--echo # +--echo # Crash server. +# +# Write file to make mysql-test-run.pl expect the "crash", but don't start +# it until it's told to +--exec echo "wait" > $MYSQLTEST_VARDIR/tmp/mysqld.1.expect +# +START TRANSACTION; +INSERT INTO bug_53756 VALUES (666,666); +# +# Request a crash on next execution of commit. +SET SESSION debug="+d,crash_commit_before"; +# +# Execute the statement that causes the crash. +--error 2013 +COMMIT; +--echo +--echo # +--echo # disconnect con1, con2, con3, con4, con5, con6. +--disconnect con1 +--disconnect con2 +--disconnect con3 +--disconnect con4 +--disconnect con5 +--disconnect con6 +--echo # +--echo # Restart server. +# +# Write file to make mysql-test-run.pl start up the server again +--exec echo "restart" > $MYSQLTEST_VARDIR/tmp/mysqld.1.expect +# +# Turn on reconnect +--enable_reconnect +# +# Call script that will poll the server waiting for it to be back online again +--source include/wait_until_connected_again.inc +# +# Turn off reconnect again +--disable_reconnect +--echo + +--echo # +--echo # Select recovered data. +--echo # Delete of row 1 was committed. +--echo # Update of row 3 was committed. +--echo # These should be included. +--echo # All other changes should not be included. +--echo # Delete of row 2 and insert of row 5 should be rolled back +SELECT * FROM bug_53756; + +--echo +--echo # Clean up. +DROP TABLE bug_53756; + +--disable_query_log +eval SET GLOBAL tx_isolation= '$global_isolation'; +eval SET SESSION tx_isolation= '$session_isolation'; +--enable_query_log + diff --git a/storage/innobase/dict/dict0load.c b/storage/innobase/dict/dict0load.c index 65f1c9536bd..d5e7600f4d0 100644 --- a/storage/innobase/dict/dict0load.c +++ b/storage/innobase/dict/dict0load.c @@ -927,6 +927,8 @@ dict_load_table_on_id( ut_ad(mutex_own(&(dict_sys->mutex))); + table = NULL; + /* NOTE that the operation of this function is protected by the dictionary mutex, and therefore no deadlocks can occur with other dictionary operations. */ @@ -953,15 +955,17 @@ dict_load_table_on_id( BTR_SEARCH_LEAF, &pcur, &mtr); rec = btr_pcur_get_rec(&pcur); - if (!btr_pcur_is_on_user_rec(&pcur, &mtr) - || rec_get_deleted_flag(rec, 0)) { + if (!btr_pcur_is_on_user_rec(&pcur, &mtr)) { /* Not found */ + goto func_exit; + } - btr_pcur_close(&pcur); - mtr_commit(&mtr); - mem_heap_free(heap); - - return(NULL); + /* Find the first record that is not delete marked */ + while (rec_get_deleted_flag(rec, 0)) { + if (!btr_pcur_move_to_next_user_rec(&pcur, &mtr)) { + goto func_exit; + } + rec = btr_pcur_get_rec(&pcur); } /*---------------------------------------------------*/ @@ -974,19 +978,14 @@ dict_load_table_on_id( /* Check if the table id in record is the one searched for */ if (ut_dulint_cmp(table_id, mach_read_from_8(field)) != 0) { - - btr_pcur_close(&pcur); - mtr_commit(&mtr); - mem_heap_free(heap); - - return(NULL); + goto func_exit; } /* Now we get the table name from the record */ field = rec_get_nth_field_old(rec, 1, &len); /* Load the table definition to memory */ table = dict_load_table(mem_heap_strdupl(heap, (char*) field, len)); - +func_exit: btr_pcur_close(&pcur); mtr_commit(&mtr); mem_heap_free(heap); From 7ccbf9b817b47d0393fe66bda6f6013ec24486ba Mon Sep 17 00:00:00 2001 From: Dmitry Shulga Date: Tue, 29 Jun 2010 16:32:03 +0700 Subject: [PATCH 039/129] Fixed bug #51855. Race condition in XA START. If several threads concurrently execute the statement XA START 'x', then mysqld server could crash. sql/sql_class.cc: xid_cache_insert: added checking for element in cache before insert it, return TRUE if such element already exists. sql/sql_parse.cc: mysql_execute_command modified: * sequence of calls to xid_cache_search(..)/xid_cache_insert(...) replaced by call to xid_cache_insert(...) in alternative 'case SQLCOM_XA_START:' * added comment to alternative 'case SQLCOM_XA_COMMIT:'. --- sql/sql_class.cc | 10 +++++++--- sql/sql_parse.cc | 26 ++++++++++++++++++-------- 2 files changed, 25 insertions(+), 11 deletions(-) diff --git a/sql/sql_class.cc b/sql/sql_class.cc index 93aa6a8268c..99792f2b262 100644 --- a/sql/sql_class.cc +++ b/sql/sql_class.cc @@ -3365,9 +3365,13 @@ bool xid_cache_insert(XID *xid, enum xa_states xa_state) bool xid_cache_insert(XID_STATE *xid_state) { pthread_mutex_lock(&LOCK_xid_cache); - DBUG_ASSERT(hash_search(&xid_cache, xid_state->xid.key(), - xid_state->xid.key_length())==0); - my_bool res=my_hash_insert(&xid_cache, (uchar*)xid_state); + if (hash_search(&xid_cache, xid_state->xid.key(), xid_state->xid.key_length())) + { + pthread_mutex_unlock(&LOCK_xid_cache); + my_error(ER_XAER_DUPID, MYF(0)); + return TRUE; + } + my_bool res= my_hash_insert(&xid_cache, (uchar*)xid_state); pthread_mutex_unlock(&LOCK_xid_cache); return res; } diff --git a/sql/sql_parse.cc b/sql/sql_parse.cc index ed2c76fdcb8..a8dede3e7f5 100644 --- a/sql/sql_parse.cc +++ b/sql/sql_parse.cc @@ -4730,7 +4730,7 @@ create_sp_error: my_error(ER_XAER_NOTA, MYF(0)); break; } - thd->transaction.xid_state.xa_state=XA_ACTIVE; + thd->transaction.xid_state.xa_state= XA_ACTIVE; my_ok(thd); break; } @@ -4750,16 +4750,16 @@ create_sp_error: my_error(ER_XAER_OUTSIDE, MYF(0)); break; } - if (xid_cache_search(thd->lex->xid)) - { - my_error(ER_XAER_DUPID, MYF(0)); - break; - } DBUG_ASSERT(thd->transaction.xid_state.xid.is_null()); - thd->transaction.xid_state.xa_state=XA_ACTIVE; + thd->transaction.xid_state.xa_state= XA_ACTIVE; thd->transaction.xid_state.rm_error= 0; thd->transaction.xid_state.xid.set(thd->lex->xid); - xid_cache_insert(&thd->transaction.xid_state); + if (xid_cache_insert(&thd->transaction.xid_state)) + { + thd->transaction.xid_state.xa_state= XA_NOTR; + thd->transaction.xid_state.xid.null(); + break; + } thd->transaction.all.modified_non_trans_table= FALSE; thd->options= ((thd->options & ~(OPTION_KEEP_LOG)) | OPTION_BEGIN); thd->server_status|= SERVER_STATUS_IN_TRANS; @@ -4813,6 +4813,16 @@ create_sp_error: case SQLCOM_XA_COMMIT: if (!thd->transaction.xid_state.xid.eq(thd->lex->xid)) { + /* + xid_state.in_thd is always true beside of xa recovery + procedure. Note, that there is no race condition here + between xid_cache_search and xid_cache_delete, since we're always + deleting our own XID (thd->lex->xid == thd->transaction.xid_state.xid). + The only case when thd->lex->xid != thd->transaction.xid_state.xid + and xid_state->in_thd == 0 is in ha_recover() functionality, + which is called before starting client connections, and thus is + always single-threaded. + */ XID_STATE *xs=xid_cache_search(thd->lex->xid); if (!xs || xs->in_thd) my_error(ER_XAER_NOTA, MYF(0)); From 62084feb5578164832ed487286798d5f7fc7a5ce Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Marko=20M=C3=A4kel=C3=A4?= Date: Tue, 29 Jun 2010 15:55:18 +0300 Subject: [PATCH 040/129] Bug#54358: READ UNCOMMITTED access failure of off-page DYNAMIC or COMPRESSED columns When the server crashes after a record stub has been inserted and before all its off-page columns have been written, the record will contain incomplete off-page columns after crash recovery. Such records may only be accessed at the READ UNCOMMITTED isolation level or when rolling back a recovered transaction in recv_recovery_rollback_active(). Skip these records at the READ UNCOMMITTED isolation level. TODO: Add assertions for checking the above assumptions hold when an incomplete BLOB is encountered. btr_rec_copy_externally_stored_field(): Return NULL if the field is incomplete. row_prebuilt_t::templ_contains_blob: Clarify what "BLOB" means in this context. Hint: MySQL BLOBs are not the same as InnoDB BLOBs. row_sel_store_mysql_rec(): Return FALSE if not all columns could be retrieved. Previously this function always returned TRUE. Assert that the record is not delete-marked. row_sel_push_cache_row_for_mysql(): Return FALSE if not all columns could be retrieved. row_search_for_mysql(): Skip records containing incomplete off-page columns. Assert that the transaction isolation level is READ UNCOMMITTED. rb://380 approved by Jimmy Yang --- storage/innodb_plugin/btr/btr0cur.c | 24 ++++- storage/innodb_plugin/include/btr0cur.h | 2 +- storage/innodb_plugin/include/row0mysql.h | 6 +- storage/innodb_plugin/row/row0merge.c | 5 + storage/innodb_plugin/row/row0sel.c | 113 +++++++++++++++++++--- 5 files changed, 133 insertions(+), 17 deletions(-) diff --git a/storage/innodb_plugin/btr/btr0cur.c b/storage/innodb_plugin/btr/btr0cur.c index 50531ad3bd7..9b28f26f054 100644 --- a/storage/innodb_plugin/btr/btr0cur.c +++ b/storage/innodb_plugin/btr/btr0cur.c @@ -4814,7 +4814,7 @@ btr_copy_externally_stored_field( /*******************************************************************//** Copies an externally stored field of a record to mem heap. -@return the field copied to heap */ +@return the field copied to heap, or NULL if the field is incomplete */ UNIV_INTERN byte* btr_rec_copy_externally_stored_field( @@ -4844,6 +4844,28 @@ btr_rec_copy_externally_stored_field( data = rec_get_nth_field(rec, offsets, no, &local_len); + ut_a(local_len >= BTR_EXTERN_FIELD_REF_SIZE); + + if (UNIV_UNLIKELY + (!memcmp(data + local_len - BTR_EXTERN_FIELD_REF_SIZE, + field_ref_zero, BTR_EXTERN_FIELD_REF_SIZE))) { + /* The externally stored field was not written + yet. This is only a valid condition when the server + crashed after the time a record stub was freshly + inserted but before all its columns were written. This + record should only be seen by + recv_recovery_rollback_active() or any + TRX_ISO_READ_UNCOMMITTED transactions. */ + + /* TODO: assert that there is an owner_trx with + owner_trx->id == DB_TRX_ID and owner_trx->is_recovered */ + + /* TODO: assert that for the current transaction trx, + either (trx == owner_trx && trx_is_recv(trx)) or + trx->isolation_level == TRX_ISO_READ_UNCOMMITTED. */ + return(NULL); + } + return(btr_copy_externally_stored_field(len, data, zip_size, local_len, heap)); } diff --git a/storage/innodb_plugin/include/btr0cur.h b/storage/innodb_plugin/include/btr0cur.h index 716f15c4267..7dc2eb63cf5 100644 --- a/storage/innodb_plugin/include/btr0cur.h +++ b/storage/innodb_plugin/include/btr0cur.h @@ -570,7 +570,7 @@ btr_copy_externally_stored_field_prefix( ulint local_len);/*!< in: length of data, in bytes */ /*******************************************************************//** Copies an externally stored field of a record to mem heap. -@return the field copied to heap */ +@return the field copied to heap, or NULL if the field is incomplete */ UNIV_INTERN byte* btr_rec_copy_externally_stored_field( diff --git a/storage/innodb_plugin/include/row0mysql.h b/storage/innodb_plugin/include/row0mysql.h index 39ea240772c..b69e657361b 100644 --- a/storage/innodb_plugin/include/row0mysql.h +++ b/storage/innodb_plugin/include/row0mysql.h @@ -622,7 +622,11 @@ struct row_prebuilt_struct { the secondary index, then this is set to TRUE */ unsigned templ_contains_blob:1;/*!< TRUE if the template contains - BLOB column(s) */ + a column with DATA_BLOB == + get_innobase_type_from_mysql_type(); + not to be confused with InnoDB + externally stored columns + (VARCHAR can be off-page too) */ mysql_row_templ_t* mysql_template;/*!< template used to transform rows fast between MySQL and Innobase formats; memory for this template diff --git a/storage/innodb_plugin/row/row0merge.c b/storage/innodb_plugin/row/row0merge.c index 70cc7912fad..56a68b58225 100644 --- a/storage/innodb_plugin/row/row0merge.c +++ b/storage/innodb_plugin/row/row0merge.c @@ -1780,6 +1780,11 @@ row_merge_copy_blobs( (below). */ data = btr_rec_copy_externally_stored_field( mrec, offsets, zip_size, i, &len, heap); + /* Because we have locked the table, any records + written by incomplete transactions must have been + rolled back already. There must not be any incomplete + BLOB columns. */ + ut_a(data); dfield_set_data(field, data, len); } diff --git a/storage/innodb_plugin/row/row0sel.c b/storage/innodb_plugin/row/row0sel.c index 2861235a995..ab8c78e4f4a 100644 --- a/storage/innodb_plugin/row/row0sel.c +++ b/storage/innodb_plugin/row/row0sel.c @@ -416,7 +416,7 @@ row_sel_fetch_columns( field_no))) { /* Copy an externally stored field to the - temporary heap */ + temporary heap, if possible. */ heap = mem_heap_create(1); @@ -425,6 +425,21 @@ row_sel_fetch_columns( dict_table_zip_size(index->table), field_no, &len, heap); + /* data == NULL means that the + externally stored field was not + written yet. This is only a valid + condition when the server crashed + after the time a record stub was + freshly inserted but before all its + columns were written. This record + should only be seen by + recv_recovery_rollback_active() or any + TRX_ISO_READ_UNCOMMITTED + transactions. The InnoDB SQL parser + (the sole caller of this function) + does not implement READ UNCOMMITTED, + and it is not involved during rollback. */ + ut_a(data); ut_a(len != UNIV_SQL_NULL); needs_copy = TRUE; @@ -926,6 +941,7 @@ row_sel_get_clust_rec( when plan->clust_pcur was positioned. The latch will not be released until mtr_commit(mtr). */ + ut_ad(!rec_get_deleted_flag(clust_rec, rec_offs_comp(offsets))); row_sel_fetch_columns(index, clust_rec, offsets, UT_LIST_GET_FIRST(plan->columns)); *out_rec = clust_rec; @@ -1628,6 +1644,13 @@ skip_lock: } if (old_vers == NULL) { + /* The record does not exist + in our read view. Skip it, but + first attempt to determine + whether the index segment we + are searching through has been + exhausted. */ + offsets = rec_get_offsets( rec, index, offsets, ULINT_UNDEFINED, &heap); @@ -2647,9 +2670,8 @@ Convert a row in the Innobase format to a row in the MySQL format. Note that the template in prebuilt may advise us to copy only a few columns to mysql_rec, other columns are left blank. All columns may not be needed in the query. -@return TRUE if success, FALSE if could not allocate memory for a BLOB -(though we may also assert in that case) */ -static +@return TRUE on success, FALSE if not all columns could be retrieved */ +static __attribute__((warn_unused_result)) ibool row_sel_store_mysql_rec( /*====================*/ @@ -2672,6 +2694,7 @@ row_sel_store_mysql_rec( ut_ad(prebuilt->mysql_template); ut_ad(prebuilt->default_rec); ut_ad(rec_offs_validate(rec, NULL, offsets)); + ut_ad(!rec_get_deleted_flag(rec, rec_offs_comp(offsets))); if (UNIV_LIKELY_NULL(prebuilt->blob_heap)) { mem_heap_free(prebuilt->blob_heap); @@ -2719,6 +2742,26 @@ row_sel_store_mysql_rec( dict_table_zip_size(prebuilt->table), templ->rec_field_no, &len, heap); + if (UNIV_UNLIKELY(!data)) { + /* The externally stored field + was not written yet. This is + only a valid condition when + the server crashed after the + time a record stub was freshly + inserted but before all its + columns were written. This + record should only be seen by + recv_recovery_rollback_active() + or any TRX_ISO_READ_UNCOMMITTED + transactions. */ + + if (extern_field_heap) { + mem_heap_free(extern_field_heap); + } + + return(FALSE); + } + ut_a(len != UNIV_SQL_NULL); } else { /* Field is stored in the row. */ @@ -3136,9 +3179,10 @@ row_sel_pop_cached_row_for_mysql( } /********************************************************************//** -Pushes a row for MySQL to the fetch cache. */ -UNIV_INLINE -void +Pushes a row for MySQL to the fetch cache. +@return TRUE on success, FALSE if the record contains incomplete BLOBs */ +UNIV_INLINE __attribute__((warn_unused_result)) +ibool row_sel_push_cache_row_for_mysql( /*=============================*/ row_prebuilt_t* prebuilt, /*!< in: prebuilt struct */ @@ -3180,10 +3224,11 @@ row_sel_push_cache_row_for_mysql( prebuilt->fetch_cache[ prebuilt->n_fetch_cached], prebuilt, rec, offsets))) { - ut_error; + return(FALSE); } prebuilt->n_fetch_cached++; + return(TRUE); } /*********************************************************************//** @@ -3578,6 +3623,24 @@ row_search_for_mysql( if (!row_sel_store_mysql_rec(buf, prebuilt, rec, offsets)) { + /* Only fresh inserts at + server crash time may contain + incomplete externally stored + columns. Pretend that such + records do not exist. Such + records may only be accessed + at the READ UNCOMMITTED + isolation level or when + rolling back a recovered + transaction. Rollback happens + at a lower level, not here. */ + ut_a(trx->isolation_level + == TRX_ISO_READ_UNCOMMITTED); + /* TODO: assert that there is + an owner_trx with + owner_trx->id == DB_TRX_ID and + owner_trx->is_recovered */ + err = DB_TOO_BIG_RECORD; /* We let the main loop to do the @@ -4357,9 +4420,20 @@ requires_clust_rec: not cache rows because there the cursor is a scrollable cursor. */ - row_sel_push_cache_row_for_mysql(prebuilt, result_rec, - offsets); - if (prebuilt->n_fetch_cached == MYSQL_FETCH_CACHE_SIZE) { + if (!row_sel_push_cache_row_for_mysql(prebuilt, result_rec, + offsets)) { + /* Only fresh inserts at server crash time may contain + incomplete externally stored columns. Pretend that + such records do not exist. Such records may only be + accessed at the READ UNCOMMITTED isolation level or + when rolling back a recovered transaction. Rollback + happens at a lower level, not here. */ + ut_a(trx->isolation_level == TRX_ISO_READ_UNCOMMITTED); + /* TODO: assert that there is an owner_trx + with owner_trx->id == DB_TRX_ID and + owner_trx->is_recovered */ + } else if (prebuilt->n_fetch_cached + == MYSQL_FETCH_CACHE_SIZE) { goto got_row; } @@ -4375,9 +4449,20 @@ requires_clust_rec: } else { if (!row_sel_store_mysql_rec(buf, prebuilt, result_rec, offsets)) { - err = DB_TOO_BIG_RECORD; - - goto lock_wait_or_error; + /* Only fresh inserts at server crash + time may contain incomplete externally + stored columns. Pretend that such + records do not exist. Such records may + only be accessed at the READ UNCOMMITTED + isolation level or when rolling back a + recovered transaction. Rollback happens + at a lower level, not here. */ + ut_a(trx->isolation_level + == TRX_ISO_READ_UNCOMMITTED); + /* TODO: assert that there is an owner_trx + with owner_trx->id == DB_TRX_ID and + owner_trx->is_recovered */ + goto next_rec; } } From 4ee0dc7cca6f0f5a0acabed38715203d6bc951ef Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Marko=20M=C3=A4kel=C3=A4?= Date: Tue, 29 Jun 2010 15:56:53 +0300 Subject: [PATCH 041/129] ChangeLog entry for Bug #54358 --- storage/innodb_plugin/ChangeLog | 7 +++++++ 1 file changed, 7 insertions(+) diff --git a/storage/innodb_plugin/ChangeLog b/storage/innodb_plugin/ChangeLog index 328fcf8e0bb..5e41c5f180a 100644 --- a/storage/innodb_plugin/ChangeLog +++ b/storage/innodb_plugin/ChangeLog @@ -1,3 +1,10 @@ +2010-06-29 The InnoDB Team + + * btr/btr0cur.c, include/btr0cur.h, + include/row0mysql.h, row/row0merge.c, row/row0sel.c: + Fix Bug#54358 READ UNCOMMITTED access failure of off-page DYNAMIC + or COMPRESSED columns + 2010-06-24 The InnoDB Team * handler/ha_innodb.cc: From 63c44558dc02e7c03b224afb09ee4d882619ccf0 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Marko=20M=C3=A4kel=C3=A4?= Date: Tue, 29 Jun 2010 16:00:58 +0300 Subject: [PATCH 042/129] Bug#54408: txn rollback after recovery: row0umod.c:673 dict_table_get_format(index->table) The REDUNDANT and COMPACT formats store a local 768-byte prefix of each externally stored column. No row_ext cache is needed, but we initialized one nevertheless. When the BLOB pointer was zero, we would ignore the locally stored prefix as well. This triggered an assertion failure in row_undo_mod_upd_exist_sec(). row_build(): Allow ext==NULL when a REDUNDANT or COMPACT table contains externally stored columns. row_undo_search_clust_to_pcur(), row_upd_store_row(): Invoke row_build() with ext==NULL on REDUNDANT and COMPACT tables. rb://382 approved by Jimmy Yang --- storage/innodb_plugin/row/row0row.c | 8 +++++++- storage/innodb_plugin/row/row0undo.c | 18 +++++++++++++++++- storage/innodb_plugin/row/row0upd.c | 17 ++++++++++++++++- 3 files changed, 40 insertions(+), 3 deletions(-) diff --git a/storage/innodb_plugin/row/row0row.c b/storage/innodb_plugin/row/row0row.c index cb7dfa2b7c9..8e806a14a98 100644 --- a/storage/innodb_plugin/row/row0row.c +++ b/storage/innodb_plugin/row/row0row.c @@ -294,7 +294,13 @@ row_build( ut_ad(dtuple_check_typed(row)); - if (j) { + if (!ext) { + /* REDUNDANT and COMPACT formats store a local + 768-byte prefix of each externally stored + column. No cache is needed. */ + ut_ad(dict_table_get_format(index->table) + < DICT_TF_FORMAT_ZIP); + } else if (j) { *ext = row_ext_create(j, ext_cols, row, dict_table_zip_size(index->table), heap); diff --git a/storage/innodb_plugin/row/row0undo.c b/storage/innodb_plugin/row/row0undo.c index 9ef842b5114..fd28a4f6520 100644 --- a/storage/innodb_plugin/row/row0undo.c +++ b/storage/innodb_plugin/row/row0undo.c @@ -199,8 +199,24 @@ row_undo_search_clust_to_pcur( ret = FALSE; } else { + row_ext_t** ext; + + if (dict_table_get_format(node->table) >= DICT_TF_FORMAT_ZIP) { + /* In DYNAMIC or COMPRESSED format, there is + no prefix of externally stored columns in the + clustered index record. Build a cache of + column prefixes. */ + ext = &node->ext; + } else { + /* REDUNDANT and COMPACT formats store a local + 768-byte prefix of each externally stored + column. No cache is needed. */ + ext = NULL; + node->ext = NULL; + } + node->row = row_build(ROW_COPY_DATA, clust_index, rec, - offsets, NULL, &node->ext, node->heap); + offsets, NULL, ext, node->heap); if (node->update) { node->undo_row = dtuple_copy(node->row, node->heap); row_upd_replace(node->undo_row, &node->undo_ext, diff --git a/storage/innodb_plugin/row/row0upd.c b/storage/innodb_plugin/row/row0upd.c index d0aaecd3dae..397b117c067 100644 --- a/storage/innodb_plugin/row/row0upd.c +++ b/storage/innodb_plugin/row/row0upd.c @@ -1398,6 +1398,7 @@ row_upd_store_row( dict_index_t* clust_index; rec_t* rec; mem_heap_t* heap = NULL; + row_ext_t** ext; ulint offsets_[REC_OFFS_NORMAL_SIZE]; const ulint* offsets; rec_offs_init(offsets_); @@ -1414,8 +1415,22 @@ row_upd_store_row( offsets = rec_get_offsets(rec, clust_index, offsets_, ULINT_UNDEFINED, &heap); + + if (dict_table_get_format(node->table) >= DICT_TF_FORMAT_ZIP) { + /* In DYNAMIC or COMPRESSED format, there is no prefix + of externally stored columns in the clustered index + record. Build a cache of column prefixes. */ + ext = &node->ext; + } else { + /* REDUNDANT and COMPACT formats store a local + 768-byte prefix of each externally stored column. + No cache is needed. */ + ext = NULL; + node->ext = NULL; + } + node->row = row_build(ROW_COPY_DATA, clust_index, rec, offsets, - NULL, &node->ext, node->heap); + NULL, ext, node->heap); if (node->is_delete) { node->upd_row = NULL; node->upd_ext = NULL; From d8421300944dd04597c65f7dfd081e44f41664cd Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Marko=20M=C3=A4kel=C3=A4?= Date: Tue, 29 Jun 2010 16:12:19 +0300 Subject: [PATCH 043/129] ChangeLog entry for Bug #54408 --- storage/innodb_plugin/ChangeLog | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/storage/innodb_plugin/ChangeLog b/storage/innodb_plugin/ChangeLog index 5e41c5f180a..f7e9a3df943 100644 --- a/storage/innodb_plugin/ChangeLog +++ b/storage/innodb_plugin/ChangeLog @@ -1,3 +1,8 @@ +2010-06-29 The InnoDB Team + * row/row0row.c, row/row0undo.c, row/row0upd.c: + Fix Bug#54408 txn rollback after recovery: row0umod.c:673 + dict_table_get_format(index->table) + 2010-06-29 The InnoDB Team * btr/btr0cur.c, include/btr0cur.h, From 52f361ecb863eab4fda5e3e5b5da7f4c430e9e65 Mon Sep 17 00:00:00 2001 From: Konstantin Osipov Date: Tue, 29 Jun 2010 18:01:33 +0400 Subject: [PATCH 044/129] A fix for Bug#54811 "Assert in mysql_lock_have_duplicate()". Remove mysql_lock_have_duplicate(), since now we always have TABLE_LIST objects for MyISAMMRG children in lex->query_tables and keep it till the end of the statement (sub-statement). mysql-test/r/merge.result: Update results (Bug#54811). mysql-test/t/merge-big.test: Update to new wait state. mysql-test/t/merge.test: Add a test case for Bug#54811. sql/lock.cc: Remove a function that is now unused. sql/lock.h: Remove a function that is now unused. sql/sql_base.cc: Don't try to search for duplicate table among THR_LOCK objects, TABLE_LIST list contains all used tables. --- mysql-test/r/merge.result | 102 +++++++++++++++++++++++++++++++ mysql-test/t/merge-big.test | 4 +- mysql-test/t/merge.test | 119 ++++++++++++++++++++++++++++++++++++ sql/lock.cc | 104 ------------------------------- sql/lock.h | 2 - sql/sql_base.cc | 85 ++++++++++++++++++++------ 6 files changed, 288 insertions(+), 128 deletions(-) diff --git a/mysql-test/r/merge.result b/mysql-test/r/merge.result index 8f7ebb06c06..63b957e7a3f 100644 --- a/mysql-test/r/merge.result +++ b/mysql-test/r/merge.result @@ -2718,4 +2718,106 @@ m2 CREATE TABLE `m2` ( `i` int(11) DEFAULT NULL ) ENGINE=MRG_MyISAM DEFAULT CHARSET=latin1 INSERT_METHOD=FIRST UNION=(`t1`) drop tables m1, m2, t1; +# +# Test case for Bug#54811 "Assert in mysql_lock_have_duplicate()" +# Check that unique_table() works correctly for merge tables. +# +drop table if exists t1, t2, t3, m1, m2; +create table t1 (a int); +create table t2 (a int); +create table t3 (b int); +create view v1 as select * from t3,t1; +create table m1 (a int) engine=merge union (t1, t2) insert_method=last; +create table m2 (a int) engine=merge union (t1, t2) insert_method=first; +create temporary table tmp (b int); +insert into tmp (b) values (1); +insert into t1 (a) values (1); +insert into t3 (b) values (1); +insert into m1 (a) values ((select max(a) from m1)); +ERROR HY000: You can't specify target table 'm1' for update in FROM clause +insert into m1 (a) values ((select max(a) from m2)); +ERROR HY000: You can't specify target table 'm1' for update in FROM clause +insert into m1 (a) values ((select max(a) from t1)); +ERROR HY000: You can't specify target table 'm1' for update in FROM clause +insert into m1 (a) values ((select max(a) from t2)); +ERROR HY000: You can't specify target table 'm1' for update in FROM clause +insert into m1 (a) values ((select max(a) from t3, m1)); +ERROR HY000: You can't specify target table 'm1' for update in FROM clause +insert into m1 (a) values ((select max(a) from t3, m2)); +ERROR HY000: You can't specify target table 'm1' for update in FROM clause +insert into m1 (a) values ((select max(a) from t3, t1)); +ERROR HY000: You can't specify target table 'm1' for update in FROM clause +insert into m1 (a) values ((select max(a) from t3, t2)); +ERROR HY000: You can't specify target table 'm1' for update in FROM clause +insert into m1 (a) values ((select max(a) from tmp, m1)); +ERROR HY000: You can't specify target table 'm1' for update in FROM clause +insert into m1 (a) values ((select max(a) from tmp, m2)); +ERROR HY000: You can't specify target table 'm1' for update in FROM clause +insert into m1 (a) values ((select max(a) from tmp, t1)); +ERROR HY000: You can't specify target table 'm1' for update in FROM clause +insert into m1 (a) values ((select max(a) from tmp, t2)); +ERROR HY000: You can't specify target table 'm1' for update in FROM clause +insert into m1 (a) values ((select max(a) from v1)); +ERROR HY000: The definition of table 'v1' prevents operation INSERT on table 'm1'. +insert into m1 (a) values ((select max(a) from tmp, v1)); +ERROR HY000: The definition of table 'v1' prevents operation INSERT on table 'm1'. +update m1 set a = ((select max(a) from m1)); +ERROR HY000: You can't specify target table 'm1' for update in FROM clause +update m1 set a = ((select max(a) from m2)); +ERROR HY000: You can't specify target table 'm1' for update in FROM clause +update m1 set a = ((select max(a) from t1)); +ERROR HY000: You can't specify target table 'm1' for update in FROM clause +update m1 set a = ((select max(a) from t2)); +ERROR HY000: You can't specify target table 'm1' for update in FROM clause +update m1 set a = ((select max(a) from t3, m1)); +ERROR HY000: You can't specify target table 'm1' for update in FROM clause +update m1 set a = ((select max(a) from t3, m2)); +ERROR HY000: You can't specify target table 'm1' for update in FROM clause +update m1 set a = ((select max(a) from t3, t1)); +ERROR HY000: You can't specify target table 'm1' for update in FROM clause +update m1 set a = ((select max(a) from t3, t2)); +ERROR HY000: You can't specify target table 'm1' for update in FROM clause +update m1 set a = ((select max(a) from tmp, m1)); +ERROR HY000: You can't specify target table 'm1' for update in FROM clause +update m1 set a = ((select max(a) from tmp, m2)); +ERROR HY000: You can't specify target table 'm1' for update in FROM clause +update m1 set a = ((select max(a) from tmp, t1)); +ERROR HY000: You can't specify target table 'm1' for update in FROM clause +update m1 set a = ((select max(a) from tmp, t2)); +ERROR HY000: You can't specify target table 'm1' for update in FROM clause +update m1 set a = ((select max(a) from v1)); +ERROR HY000: The definition of table 'v1' prevents operation UPDATE on table 'm1'. +update m1 set a = ((select max(a) from tmp, v1)); +ERROR HY000: The definition of table 'v1' prevents operation UPDATE on table 'm1'. +delete from m1 where a = (select max(a) from m1); +ERROR HY000: You can't specify target table 'm1' for update in FROM clause +delete from m1 where a = (select max(a) from m2); +ERROR HY000: You can't specify target table 'm1' for update in FROM clause +delete from m1 where a = (select max(a) from t1); +ERROR HY000: You can't specify target table 'm1' for update in FROM clause +delete from m1 where a = (select max(a) from t2); +ERROR HY000: You can't specify target table 'm1' for update in FROM clause +delete from m1 where a = (select max(a) from t3, m1); +ERROR HY000: You can't specify target table 'm1' for update in FROM clause +delete from m1 where a = (select max(a) from t3, m2); +ERROR HY000: You can't specify target table 'm1' for update in FROM clause +delete from m1 where a = (select max(a) from t3, t1); +ERROR HY000: You can't specify target table 'm1' for update in FROM clause +delete from m1 where a = (select max(a) from t3, t2); +ERROR HY000: You can't specify target table 'm1' for update in FROM clause +delete from m1 where a = (select max(a) from tmp, m1); +ERROR HY000: You can't specify target table 'm1' for update in FROM clause +delete from m1 where a = (select max(a) from tmp, m2); +ERROR HY000: You can't specify target table 'm1' for update in FROM clause +delete from m1 where a = (select max(a) from tmp, t1); +ERROR HY000: You can't specify target table 'm1' for update in FROM clause +delete from m1 where a = (select max(a) from tmp, t2); +ERROR HY000: You can't specify target table 'm1' for update in FROM clause +delete from m1 where a = (select max(a) from v1); +ERROR HY000: The definition of table 'v1' prevents operation DELETE on table 'm1'. +delete from m1 where a = (select max(a) from tmp, v1); +ERROR HY000: The definition of table 'v1' prevents operation DELETE on table 'm1'. +drop view v1; +drop temporary table tmp; +drop table t1, t2, t3, m1, m2; End of 6.0 tests diff --git a/mysql-test/t/merge-big.test b/mysql-test/t/merge-big.test index 33bd93791f1..509c7742dac 100644 --- a/mysql-test/t/merge-big.test +++ b/mysql-test/t/merge-big.test @@ -51,7 +51,7 @@ connection default; #--sleep 8 #SELECT ID,STATE,INFO FROM INFORMATION_SCHEMA.PROCESSLIST; let $wait_condition= SELECT 1 FROM INFORMATION_SCHEMA.PROCESSLIST - WHERE ID = $con1_id AND STATE = 'Table lock'; + WHERE ID = $con1_id AND STATE = 'Waiting for table'; --source include/wait_condition.inc #SELECT NOW(); --echo # Kick INSERT out of thr_multi_lock(). @@ -61,7 +61,7 @@ FLUSH TABLES; #--sleep 8 #SELECT ID,STATE,INFO FROM INFORMATION_SCHEMA.PROCESSLIST; let $wait_condition= SELECT 1 FROM INFORMATION_SCHEMA.PROCESSLIST - WHERE ID = $con1_id AND STATE = 'Table lock'; + WHERE ID = $con1_id AND STATE = 'Waiting for table'; --source include/wait_condition.inc #SELECT NOW(); --echo # Unlock and close table and wait for con1 to close too. diff --git a/mysql-test/t/merge.test b/mysql-test/t/merge.test index 29c0eae1df6..d7026011055 100644 --- a/mysql-test/t/merge.test +++ b/mysql-test/t/merge.test @@ -2201,6 +2201,125 @@ show create table m1; show create table m2; drop tables m1, m2, t1; +--echo # +--echo # Test case for Bug#54811 "Assert in mysql_lock_have_duplicate()" +--echo # Check that unique_table() works correctly for merge tables. +--echo # +--disable_warnings +drop table if exists t1, t2, t3, m1, m2; +--enable_warnings +create table t1 (a int); +create table t2 (a int); +create table t3 (b int); +create view v1 as select * from t3,t1; +create table m1 (a int) engine=merge union (t1, t2) insert_method=last; +create table m2 (a int) engine=merge union (t1, t2) insert_method=first; +create temporary table tmp (b int); +insert into tmp (b) values (1); + +insert into t1 (a) values (1); +insert into t3 (b) values (1); +--error ER_UPDATE_TABLE_USED +insert into m1 (a) values ((select max(a) from m1)); +--error ER_UPDATE_TABLE_USED +insert into m1 (a) values ((select max(a) from m2)); +--error ER_UPDATE_TABLE_USED +insert into m1 (a) values ((select max(a) from t1)); +--error ER_UPDATE_TABLE_USED +insert into m1 (a) values ((select max(a) from t2)); + +--error ER_UPDATE_TABLE_USED +insert into m1 (a) values ((select max(a) from t3, m1)); +--error ER_UPDATE_TABLE_USED +insert into m1 (a) values ((select max(a) from t3, m2)); +--error ER_UPDATE_TABLE_USED +insert into m1 (a) values ((select max(a) from t3, t1)); +--error ER_UPDATE_TABLE_USED +insert into m1 (a) values ((select max(a) from t3, t2)); + +--error ER_UPDATE_TABLE_USED +insert into m1 (a) values ((select max(a) from tmp, m1)); +--error ER_UPDATE_TABLE_USED +insert into m1 (a) values ((select max(a) from tmp, m2)); +--error ER_UPDATE_TABLE_USED +insert into m1 (a) values ((select max(a) from tmp, t1)); +--error ER_UPDATE_TABLE_USED +insert into m1 (a) values ((select max(a) from tmp, t2)); + +--error ER_VIEW_PREVENT_UPDATE +insert into m1 (a) values ((select max(a) from v1)); +--error ER_VIEW_PREVENT_UPDATE +insert into m1 (a) values ((select max(a) from tmp, v1)); + + +--error ER_UPDATE_TABLE_USED +update m1 set a = ((select max(a) from m1)); +--error ER_UPDATE_TABLE_USED +update m1 set a = ((select max(a) from m2)); +--error ER_UPDATE_TABLE_USED +update m1 set a = ((select max(a) from t1)); +--error ER_UPDATE_TABLE_USED +update m1 set a = ((select max(a) from t2)); + +--error ER_UPDATE_TABLE_USED +update m1 set a = ((select max(a) from t3, m1)); +--error ER_UPDATE_TABLE_USED +update m1 set a = ((select max(a) from t3, m2)); +--error ER_UPDATE_TABLE_USED +update m1 set a = ((select max(a) from t3, t1)); +--error ER_UPDATE_TABLE_USED +update m1 set a = ((select max(a) from t3, t2)); + +--error ER_UPDATE_TABLE_USED +update m1 set a = ((select max(a) from tmp, m1)); +--error ER_UPDATE_TABLE_USED +update m1 set a = ((select max(a) from tmp, m2)); +--error ER_UPDATE_TABLE_USED +update m1 set a = ((select max(a) from tmp, t1)); +--error ER_UPDATE_TABLE_USED +update m1 set a = ((select max(a) from tmp, t2)); + +--error ER_VIEW_PREVENT_UPDATE +update m1 set a = ((select max(a) from v1)); +--error ER_VIEW_PREVENT_UPDATE +update m1 set a = ((select max(a) from tmp, v1)); + + +--error ER_UPDATE_TABLE_USED +delete from m1 where a = (select max(a) from m1); +--error ER_UPDATE_TABLE_USED +delete from m1 where a = (select max(a) from m2); +--error ER_UPDATE_TABLE_USED +delete from m1 where a = (select max(a) from t1); +--error ER_UPDATE_TABLE_USED +delete from m1 where a = (select max(a) from t2); + +--error ER_UPDATE_TABLE_USED +delete from m1 where a = (select max(a) from t3, m1); +--error ER_UPDATE_TABLE_USED +delete from m1 where a = (select max(a) from t3, m2); +--error ER_UPDATE_TABLE_USED +delete from m1 where a = (select max(a) from t3, t1); +--error ER_UPDATE_TABLE_USED +delete from m1 where a = (select max(a) from t3, t2); + +--error ER_UPDATE_TABLE_USED +delete from m1 where a = (select max(a) from tmp, m1); +--error ER_UPDATE_TABLE_USED +delete from m1 where a = (select max(a) from tmp, m2); +--error ER_UPDATE_TABLE_USED +delete from m1 where a = (select max(a) from tmp, t1); +--error ER_UPDATE_TABLE_USED +delete from m1 where a = (select max(a) from tmp, t2); + +--error ER_VIEW_PREVENT_UPDATE +delete from m1 where a = (select max(a) from v1); +--error ER_VIEW_PREVENT_UPDATE +delete from m1 where a = (select max(a) from tmp, v1); + +drop view v1; +drop temporary table tmp; +drop table t1, t2, t3, m1, m2; --echo End of 6.0 tests diff --git a/sql/lock.cc b/sql/lock.cc index 52d97a2422b..de0f39018f7 100644 --- a/sql/lock.cc +++ b/sql/lock.cc @@ -627,110 +627,6 @@ MYSQL_LOCK *mysql_lock_merge(MYSQL_LOCK *a,MYSQL_LOCK *b) } -/** - Find duplicate lock in tables. - - Temporary tables are ignored here like they are ignored in - get_lock_data(). If we allow two opens on temporary tables later, - both functions should be checked. - - @param thd The current thread. - @param needle The table to check for duplicate lock. - @param haystack The list of tables to search for the dup lock. - - @note - This is mainly meant for MERGE tables in INSERT ... SELECT - situations. The 'real', underlying tables can be found only after - the MERGE tables are opened. This function assumes that the tables are - already locked. - - @retval - NULL No duplicate lock found. - @retval - !NULL First table from 'haystack' that matches a lock on 'needle'. -*/ - -TABLE_LIST *mysql_lock_have_duplicate(THD *thd, TABLE_LIST *needle, - TABLE_LIST *haystack) -{ - MYSQL_LOCK *mylock; - TABLE **lock_tables; - TABLE *table; - TABLE *table2; - THR_LOCK_DATA **lock_locks; - THR_LOCK_DATA **table_lock_data; - THR_LOCK_DATA **end_data; - THR_LOCK_DATA **lock_data2; - THR_LOCK_DATA **end_data2; - DBUG_ENTER("mysql_lock_have_duplicate"); - - /* - Table may not be defined for derived or view tables. - Table may not be part of a lock for delayed operations. - */ - if (! (table= needle->table) || ! table->lock_count) - goto end; - - /* A temporary table does not have locks. */ - if (table->s->tmp_table == NON_TRANSACTIONAL_TMP_TABLE) - goto end; - - /* Get command lock or LOCK TABLES lock. Maybe empty for INSERT DELAYED. */ - if (! (mylock= thd->lock)) - goto end; - - /* If we have less than two tables, we cannot have duplicates. */ - if (mylock->table_count < 2) - goto end; - - lock_locks= mylock->locks; - lock_tables= mylock->table; - - /* Prepare table related variables that don't change in loop. */ - DBUG_ASSERT((table->lock_position < mylock->table_count) && - (table == lock_tables[table->lock_position])); - table_lock_data= lock_locks + table->lock_data_start; - end_data= table_lock_data + table->lock_count; - - for (; haystack; haystack= haystack->next_global) - { - if (haystack->placeholder()) - continue; - table2= haystack->table; - if (table2->s->tmp_table == NON_TRANSACTIONAL_TMP_TABLE) - continue; - - /* All tables in list must be in lock. */ - DBUG_ASSERT((table2->lock_position < mylock->table_count) && - (table2 == lock_tables[table2->lock_position])); - - for (lock_data2= lock_locks + table2->lock_data_start, - end_data2= lock_data2 + table2->lock_count; - lock_data2 < end_data2; - lock_data2++) - { - THR_LOCK_DATA **lock_data; - THR_LOCK *lock2= (*lock_data2)->lock; - - for (lock_data= table_lock_data; - lock_data < end_data; - lock_data++) - { - if ((*lock_data)->lock == lock2) - { - DBUG_PRINT("info", ("haystack match: '%s'", haystack->table_name)); - DBUG_RETURN(haystack); - } - } - } - } - - end: - DBUG_PRINT("info", ("no duplicate found")); - DBUG_RETURN(NULL); -} - - /** Unlock a set of external. */ static int unlock_external(THD *thd, TABLE **table,uint count) diff --git a/sql/lock.h b/sql/lock.h index 84c7bce0679..4bdf0085d07 100644 --- a/sql/lock.h +++ b/sql/lock.h @@ -60,8 +60,6 @@ void mysql_lock_remove(THD *thd, MYSQL_LOCK *locked,TABLE *table); void mysql_lock_abort(THD *thd, TABLE *table, bool upgrade_lock); bool mysql_lock_abort_for_thread(THD *thd, TABLE *table); MYSQL_LOCK *mysql_lock_merge(MYSQL_LOCK *a,MYSQL_LOCK *b); -TABLE_LIST *mysql_lock_have_duplicate(THD *thd, TABLE_LIST *needle, - TABLE_LIST *haystack); void broadcast_refresh(void); /* Lock based on name */ bool lock_table_names(THD *thd, TABLE_LIST *table_list); diff --git a/sql/sql_base.cc b/sql/sql_base.cc index 0d4d949d701..3758ec7253d 100644 --- a/sql/sql_base.cc +++ b/sql/sql_base.cc @@ -1931,15 +1931,14 @@ TABLE_LIST *find_table_in_list(TABLE_LIST *table, } -/* + +/** Test that table is unique (It's only exists once in the table list) - SYNOPSIS - unique_table() - thd thread handle - table table which should be checked - table_list list of tables - check_alias whether to check tables' aliases + @param thd thread handle + @param table table which should be checked + @param table_list list of tables + @param check_alias whether to check tables' aliases NOTE: to exclude derived tables from check we use following mechanism: a) during derived table processing set THD::derived_tables_processing @@ -1950,7 +1949,7 @@ TABLE_LIST *find_table_in_list(TABLE_LIST *table, processing loop, because multi-update call fix_fields() for some its items (which mean JOIN::prepare for subqueries) before unique_table call to detect which tables should be locked for write). - c) unique_table skip all tables which belong to SELECT with + c) find_dup_table skip all tables which belong to SELECT with SELECT::exclude_from_table_unique_test set. Also SELECT::exclude_from_table_unique_test used to exclude from check tables of main SELECT of multi-delete and multi-update @@ -1962,17 +1961,17 @@ TABLE_LIST *find_table_in_list(TABLE_LIST *table, TODO: when we will have table/view change detection we can do this check only once for PS/SP - RETURN - found duplicate - 0 if table is unique + @retval !=0 found duplicate + @retval 0 if table is unique */ -TABLE_LIST* unique_table(THD *thd, TABLE_LIST *table, TABLE_LIST *table_list, - bool check_alias) +static +TABLE_LIST* find_dup_table(THD *thd, TABLE_LIST *table, TABLE_LIST *table_list, + bool check_alias) { TABLE_LIST *res; const char *d_name, *t_name, *t_alias; - DBUG_ENTER("unique_table"); + DBUG_ENTER("find_dup_table"); DBUG_PRINT("enter", ("table alias: %s", table->alias)); /* @@ -1987,6 +1986,9 @@ TABLE_LIST* unique_table(THD *thd, TABLE_LIST *table, TABLE_LIST *table_list, */ if (table->table) { + /* All MyISAMMRG children are plain MyISAM tables. */ + DBUG_ASSERT(table->table->file->ht->db_type != DB_TYPE_MRG_MYISAM); + /* temporary table is always unique */ if (table->table && table->table->s->tmp_table != NO_TMP_TABLE) DBUG_RETURN(0); @@ -2008,8 +2010,7 @@ TABLE_LIST* unique_table(THD *thd, TABLE_LIST *table, TABLE_LIST *table_list, Table is unique if it is present only once in the global list of tables and once in the list of table locks. */ - if (! (res= find_table_in_global_list(table_list, d_name, t_name)) && - ! (res= mysql_lock_have_duplicate(thd, table, table_list))) + if (! (res= find_table_in_global_list(table_list, d_name, t_name))) break; /* Skip if same underlying table. */ @@ -2048,6 +2049,37 @@ next: } +/** + Test that the subject table of INSERT/UPDATE/DELETE/CREATE + or (in case of MyISAMMRG) one of its children are not used later + in the query. + + @retval non-NULL The table list element for the table that + represents the duplicate. + @retval NULL No duplicates found. +*/ + +TABLE_LIST* +unique_table(THD *thd, TABLE_LIST *table, TABLE_LIST *table_list, + bool check_alias) +{ + TABLE_LIST *dup; + if (table->table && table->table->file->ht->db_type == DB_TYPE_MRG_MYISAM) + { + TABLE_LIST *child; + dup= NULL; + /* Check duplicates of all merge children. */ + for (child= table->next_global; child && child->parent_l == table; + child= child->next_global) + { + if ((dup= find_dup_table(thd, child, child->next_global, check_alias))) + break; + } + } + else + dup= find_dup_table(thd, table, table_list, check_alias); + return dup; +} /* Issue correct error message in case we found 2 duplicate tables which prevent some update operation @@ -3204,8 +3236,7 @@ bool open_table(THD *thd, TABLE_LIST *table_list, MEM_ROOT *mem_root, table_list->table= table; DBUG_ASSERT(table->key_read == 0); /* Tables may be reused in a sub statement. */ - if (table->file->extra(HA_EXTRA_IS_ATTACHED_CHILDREN)) - table->file->extra(HA_EXTRA_DETACH_CHILDREN); + DBUG_ASSERT(! table->file->extra(HA_EXTRA_IS_ATTACHED_CHILDREN)); DBUG_RETURN(FALSE); err_lock: @@ -5563,11 +5594,25 @@ bool open_normal_and_derived_tables(THD *thd, TABLE_LIST *tables, uint flags) or schema tables) as free for reuse. */ -static void mark_real_tables_as_free_for_reuse(TABLE_LIST *table) +static void mark_real_tables_as_free_for_reuse(TABLE_LIST *table_list) { - for (; table; table= table->next_global) + TABLE_LIST *table; + for (table= table_list; table; table= table->next_global) if (!table->placeholder()) + { table->table->query_id= 0; + } + for (table= table_list; table; table= table->next_global) + if (!table->placeholder()) + { + /* + Detach children of MyISAMMRG tables used in + sub-statements, they will be reattached at open. + This has to be done in a separate loop to make sure + that children have had their query_id cleared. + */ + table->table->file->extra(HA_EXTRA_DETACH_CHILDREN); + } } From c3b1a5751ac0e9acbad30ce680255638e5f1825a Mon Sep 17 00:00:00 2001 From: Konstantin Osipov Date: Tue, 29 Jun 2010 18:28:36 +0400 Subject: [PATCH 045/129] Salvage comments added by Ingo while working on Bug#52114 and Bug#50788. The bugs themselves are regressions that are introduced by an incomplete fix for Bug#36171 and will not be pushed. --- mysys/mf_iocache.c | 52 ++++++++++++++++++++++++++++++++++--- sql/sql_base.cc | 6 ++++- storage/myisam/mi_statrec.c | 7 ++++- 3 files changed, 59 insertions(+), 6 deletions(-) diff --git a/mysys/mf_iocache.c b/mysys/mf_iocache.c index 620ac667a8b..b7fe36ac049 100644 --- a/mysys/mf_iocache.c +++ b/mysys/mf_iocache.c @@ -455,7 +455,9 @@ my_bool reinit_io_cache(IO_CACHE *info, enum cache_type type, RETURN 0 we succeeded in reading all data - 1 Error: can't read requested characters + 1 Error: couldn't read requested characters. In this case: + If info->error == -1, we got a read error. + Otherwise info->error contains the number of bytes in Buffer. */ int _my_b_read(register IO_CACHE *info, uchar *Buffer, size_t Count) @@ -464,6 +466,7 @@ int _my_b_read(register IO_CACHE *info, uchar *Buffer, size_t Count) my_off_t pos_in_file; DBUG_ENTER("_my_b_read"); + /* If the buffer is not empty yet, copy what is available. */ if ((left_length= (size_t) (info->read_end-info->read_pos))) { DBUG_ASSERT(Count >= left_length); /* User is not using my_b_read() */ @@ -475,7 +478,7 @@ int _my_b_read(register IO_CACHE *info, uchar *Buffer, size_t Count) /* pos_in_file always point on where info->buffer was read */ pos_in_file=info->pos_in_file+ (size_t) (info->read_end - info->buffer); - /* + /* Whenever a function which operates on IO_CACHE flushes/writes some part of the IO_CACHE to disk it will set the property "seek_not_done" to indicate this to other functions operating @@ -502,19 +505,38 @@ int _my_b_read(register IO_CACHE *info, uchar *Buffer, size_t Count) } } + /* + Calculate, how much we are within a IO_SIZE block. Ideally this + should be zero. + */ diff_length= (size_t) (pos_in_file & (IO_SIZE-1)); + + /* + If more than a block plus the rest of the current block is wanted, + we do read directly, without filling the buffer. + */ if (Count >= (size_t) (IO_SIZE+(IO_SIZE-diff_length))) { /* Fill first intern buffer */ size_t read_length; if (info->end_of_file <= pos_in_file) - { /* End of file */ + { + /* End of file. Return, what we did copy from the buffer. */ info->error= (int) left_length; DBUG_RETURN(1); } + /* + Crop the wanted count to a multiple of IO_SIZE and subtract, + what we did already read from a block. That way, the read will + end aligned with a block. + */ length=(Count & (size_t) ~(IO_SIZE-1))-diff_length; if ((read_length= my_read(info->file,Buffer, length, info->myflags)) != length) { + /* + If we didn't get, what we wanted, we either return -1 for a read + error, or (it's end of file), how much we got in total. + */ info->error= (read_length == (size_t) -1 ? -1 : (int) (read_length+left_length)); DBUG_RETURN(1); @@ -526,15 +548,27 @@ int _my_b_read(register IO_CACHE *info, uchar *Buffer, size_t Count) diff_length=0; } + /* + At this point, we want less than one and a partial block. + We will read a full cache, minus the number of bytes, we are + within a block already. So we will reach new alignment. + */ max_length= info->read_length-diff_length; + /* We will not read past end of file. */ if (info->type != READ_FIFO && max_length > (info->end_of_file - pos_in_file)) max_length= (size_t) (info->end_of_file - pos_in_file); + /* + If there is nothing left to read, + we either are done, or we failed to fulfill the request. + Otherwise, we read max_length into the cache. + */ if (!max_length) { if (Count) { - info->error= left_length; /* We only got this many char */ + /* We couldn't fulfil the request. Return, how much we got. */ + info->error= left_length; DBUG_RETURN(1); } length=0; /* Didn't read any chars */ @@ -543,13 +577,23 @@ int _my_b_read(register IO_CACHE *info, uchar *Buffer, size_t Count) info->myflags)) < Count || length == (size_t) -1) { + /* + We got an read error, or less than requested (end of file). + If not a read error, copy, what we got. + */ if (length != (size_t) -1) memcpy(Buffer, info->buffer, length); info->pos_in_file= pos_in_file; + /* For a read error, return -1, otherwise, what we got in total. */ info->error= length == (size_t) -1 ? -1 : (int) (length+left_length); info->read_pos=info->read_end=info->buffer; DBUG_RETURN(1); } + /* + Count is the remaining number of bytes requested. + length is the amount of data in the cache. + Read Count bytes from the cache. + */ info->read_pos=info->buffer+Count; info->read_end=info->buffer+length; info->pos_in_file=pos_in_file; diff --git a/sql/sql_base.cc b/sql/sql_base.cc index 3758ec7253d..d69a5b1aa77 100644 --- a/sql/sql_base.cc +++ b/sql/sql_base.cc @@ -1931,7 +1931,6 @@ TABLE_LIST *find_table_in_list(TABLE_LIST *table, } - /** Test that table is unique (It's only exists once in the table list) @@ -2054,6 +2053,11 @@ next: or (in case of MyISAMMRG) one of its children are not used later in the query. + For MyISAMMRG tables, it is assumed that all the underlying + tables of @c table (if any) are listed right after it and that + their @c parent_l field points at the main table. + + @retval non-NULL The table list element for the table that represents the duplicate. @retval NULL No duplicates found. diff --git a/storage/myisam/mi_statrec.c b/storage/myisam/mi_statrec.c index 74fca5902f5..7d595916d78 100644 --- a/storage/myisam/mi_statrec.c +++ b/storage/myisam/mi_statrec.c @@ -273,7 +273,12 @@ int _mi_read_rnd_static_record(MI_INFO *info, uchar *buf, DBUG_RETURN(error); } - /* Read record with cacheing */ + /* + Read record with caching. If my_b_read() returns TRUE, less than the + requested bytes have been read. In this case rec_cache.error is + either -1 for a read error, or contains the number of bytes copied + into the buffer. + */ error=my_b_read(&info->rec_cache,(uchar*) buf,share->base.reclength); if (info->s->base.pack_reclength != info->s->base.reclength && !error) { From 707a3bef6e95b1125c91d3a5ecc821bba20caa26 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Marko=20M=C3=A4kel=C3=A4?= Date: Wed, 30 Jun 2010 12:31:49 +0300 Subject: [PATCH 046/129] Correct some comments that were added in the fix of Bug #54358 (READ UNCOMMITTED access failure of off-page DYNAMIC or COMPRESSED columns). Records that lack incompletely written externally stored columns may be accessed by READ UNCOMMITTED transaction even without involving a crash during an INSERT or UPDATE operation. I verified this as follows. (1) added a delay after the mini-transaction for writing the clustered index 'stub' record was committed (patch attached) (2) started mysqld in gdb, setting breakpoints to the where the assertions about READ UNCOMMITTED were added in the bug fix (3) invoked ibtest3 --create-options=key_block_size=2 to create BLOBs in a COMPRESSED table (4) invoked the following: yes 'set transaction isolation level read uncommitted; checksum table blobt3;select sleep(1);'|mysql -uroot test (5) noted that one of the breakpoints was triggered (return(NULL) in btr_rec_copy_externally_stored_field()) === modified file 'storage/innodb_plugin/row/row0ins.c' --- storage/innodb_plugin/row/row0ins.c 2010-06-30 08:17:25 +0000 +++ storage/innodb_plugin/row/row0ins.c 2010-06-30 08:17:25 +0000 @@ -2120,6 +2120,7 @@ function_exit: rec_t* rec; ulint* offsets; mtr_start(&mtr); + os_thread_sleep(5000000); btr_cur_search_to_nth_level(index, 0, entry, PAGE_CUR_LE, BTR_MODIFY_TREE, &cursor, 0, === modified file 'storage/innodb_plugin/row/row0upd.c' --- storage/innodb_plugin/row/row0upd.c 2010-06-30 08:11:55 +0000 +++ storage/innodb_plugin/row/row0upd.c 2010-06-30 08:11:55 +0000 @@ -1763,6 +1763,7 @@ row_upd_clust_rec( rec_offs_init(offsets_); mtr_start(mtr); + os_thread_sleep(5000000); ut_a(btr_pcur_restore_position(BTR_MODIFY_TREE, pcur, mtr)); rec = btr_cur_get_rec(btr_cur); --- storage/innodb_plugin/btr/btr0cur.c | 14 ++------ storage/innodb_plugin/row/row0sel.c | 53 +++++++++-------------------- 2 files changed, 19 insertions(+), 48 deletions(-) diff --git a/storage/innodb_plugin/btr/btr0cur.c b/storage/innodb_plugin/btr/btr0cur.c index 9b28f26f054..7fa7d42320a 100644 --- a/storage/innodb_plugin/btr/btr0cur.c +++ b/storage/innodb_plugin/btr/btr0cur.c @@ -4849,20 +4849,10 @@ btr_rec_copy_externally_stored_field( if (UNIV_UNLIKELY (!memcmp(data + local_len - BTR_EXTERN_FIELD_REF_SIZE, field_ref_zero, BTR_EXTERN_FIELD_REF_SIZE))) { - /* The externally stored field was not written - yet. This is only a valid condition when the server - crashed after the time a record stub was freshly - inserted but before all its columns were written. This - record should only be seen by + /* The externally stored field was not written yet. + This record should only be seen by recv_recovery_rollback_active() or any TRX_ISO_READ_UNCOMMITTED transactions. */ - - /* TODO: assert that there is an owner_trx with - owner_trx->id == DB_TRX_ID and owner_trx->is_recovered */ - - /* TODO: assert that for the current transaction trx, - either (trx == owner_trx && trx_is_recv(trx)) or - trx->isolation_level == TRX_ISO_READ_UNCOMMITTED. */ return(NULL); } diff --git a/storage/innodb_plugin/row/row0sel.c b/storage/innodb_plugin/row/row0sel.c index ab8c78e4f4a..d0c59862fce 100644 --- a/storage/innodb_plugin/row/row0sel.c +++ b/storage/innodb_plugin/row/row0sel.c @@ -427,11 +427,7 @@ row_sel_fetch_columns( /* data == NULL means that the externally stored field was not - written yet. This is only a valid - condition when the server crashed - after the time a record stub was - freshly inserted but before all its - columns were written. This record + written yet. This record should only be seen by recv_recovery_rollback_active() or any TRX_ISO_READ_UNCOMMITTED @@ -2744,12 +2740,7 @@ row_sel_store_mysql_rec( if (UNIV_UNLIKELY(!data)) { /* The externally stored field - was not written yet. This is - only a valid condition when - the server crashed after the - time a record stub was freshly - inserted but before all its - columns were written. This + was not written yet. This record should only be seen by recv_recovery_rollback_active() or any TRX_ISO_READ_UNCOMMITTED @@ -3623,8 +3614,7 @@ row_search_for_mysql( if (!row_sel_store_mysql_rec(buf, prebuilt, rec, offsets)) { - /* Only fresh inserts at - server crash time may contain + /* Only fresh inserts may contain incomplete externally stored columns. Pretend that such records do not exist. Such @@ -3636,10 +3626,6 @@ row_search_for_mysql( at a lower level, not here. */ ut_a(trx->isolation_level == TRX_ISO_READ_UNCOMMITTED); - /* TODO: assert that there is - an owner_trx with - owner_trx->id == DB_TRX_ID and - owner_trx->is_recovered */ err = DB_TOO_BIG_RECORD; @@ -4422,16 +4408,14 @@ requires_clust_rec: if (!row_sel_push_cache_row_for_mysql(prebuilt, result_rec, offsets)) { - /* Only fresh inserts at server crash time may contain - incomplete externally stored columns. Pretend that - such records do not exist. Such records may only be - accessed at the READ UNCOMMITTED isolation level or - when rolling back a recovered transaction. Rollback - happens at a lower level, not here. */ + /* Only fresh inserts may contain incomplete + externally stored columns. Pretend that such + records do not exist. Such records may only be + accessed at the READ UNCOMMITTED isolation + level or when rolling back a recovered + transaction. Rollback happens at a lower + level, not here. */ ut_a(trx->isolation_level == TRX_ISO_READ_UNCOMMITTED); - /* TODO: assert that there is an owner_trx - with owner_trx->id == DB_TRX_ID and - owner_trx->is_recovered */ } else if (prebuilt->n_fetch_cached == MYSQL_FETCH_CACHE_SIZE) { @@ -4449,19 +4433,16 @@ requires_clust_rec: } else { if (!row_sel_store_mysql_rec(buf, prebuilt, result_rec, offsets)) { - /* Only fresh inserts at server crash - time may contain incomplete externally - stored columns. Pretend that such - records do not exist. Such records may - only be accessed at the READ UNCOMMITTED + /* Only fresh inserts may contain + incomplete externally stored + columns. Pretend that such records do + not exist. Such records may only be + accessed at the READ UNCOMMITTED isolation level or when rolling back a - recovered transaction. Rollback happens - at a lower level, not here. */ + recovered transaction. Rollback + happens at a lower level, not here. */ ut_a(trx->isolation_level == TRX_ISO_READ_UNCOMMITTED); - /* TODO: assert that there is an owner_trx - with owner_trx->id == DB_TRX_ID and - owner_trx->is_recovered */ goto next_rec; } } From 38d8ca8cec7c8e38c41bd8f17b1caa8f5142827c Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Marko=20M=C3=A4kel=C3=A4?= Date: Wed, 30 Jun 2010 12:38:47 +0300 Subject: [PATCH 047/129] Bug#54358 follow-up: Correct some error handling. --- storage/innodb_plugin/row/row0sel.c | 9 +++------ 1 file changed, 3 insertions(+), 6 deletions(-) diff --git a/storage/innodb_plugin/row/row0sel.c b/storage/innodb_plugin/row/row0sel.c index d0c59862fce..76c144e5a8c 100644 --- a/storage/innodb_plugin/row/row0sel.c +++ b/storage/innodb_plugin/row/row0sel.c @@ -3627,11 +3627,8 @@ row_search_for_mysql( ut_a(trx->isolation_level == TRX_ISO_READ_UNCOMMITTED); - err = DB_TOO_BIG_RECORD; - - /* We let the main loop to do the - error handling */ - goto shortcut_fails_too_big_rec; + /* Proceed as in case SEL_RETRY. */ + break; } mtr_commit(&mtr); @@ -3671,7 +3668,7 @@ release_search_latch_if_needed: default: ut_ad(0); } -shortcut_fails_too_big_rec: + mtr_commit(&mtr); mtr_start(&mtr); } From 29e9130d60d79b88b9e6593a111ced4363e9225e Mon Sep 17 00:00:00 2001 From: Jon Olav Hauglid Date: Wed, 30 Jun 2010 13:37:03 +0200 Subject: [PATCH 048/129] Temporary fix for bug#54835 MTR version 1 cannot start server - bootstrap reports unknown InnoDB engine Removes --loose-skip-innodb from the list of server startup options. --- mysql-test/lib/v1/mysql-test-run.pl | 1 - 1 file changed, 1 deletion(-) diff --git a/mysql-test/lib/v1/mysql-test-run.pl b/mysql-test/lib/v1/mysql-test-run.pl index 64d7376605e..36acea3ab6d 100755 --- a/mysql-test/lib/v1/mysql-test-run.pl +++ b/mysql-test/lib/v1/mysql-test-run.pl @@ -3114,7 +3114,6 @@ sub install_db ($$) { mtr_add_arg($args, "--bootstrap"); mtr_add_arg($args, "--basedir=%s", $path_my_basedir); mtr_add_arg($args, "--datadir=%s", $data_dir); - mtr_add_arg($args, "--loose-skip-innodb"); mtr_add_arg($args, "--loose-skip-ndbcluster"); mtr_add_arg($args, "--tmpdir=."); mtr_add_arg($args, "--core-file"); From 7f19cc824f0ad0367f731783bb45e0d7bff98be4 Mon Sep 17 00:00:00 2001 From: Jimmy Yang Date: Wed, 30 Jun 2010 22:06:01 -0700 Subject: [PATCH 049/129] Port fix for bug #54311 from mysql-trunk-innodb to mysql-5.1-innodb codeline. Bug #54311: Crash on CHECK PARTITION after concurrent LOAD DATA and adaptive_hash_index=OFF --- storage/innodb_plugin/ChangeLog | 6 ++++++ storage/innodb_plugin/btr/btr0sea.c | 11 ++++++++++- storage/innodb_plugin/ha/ha0ha.c | 15 +++++++++++---- storage/innodb_plugin/handler/ha_innodb.cc | 1 + storage/innodb_plugin/include/btr0sea.h | 8 +++++++- 5 files changed, 35 insertions(+), 6 deletions(-) diff --git a/storage/innodb_plugin/ChangeLog b/storage/innodb_plugin/ChangeLog index f7e9a3df943..a49a6b54a39 100644 --- a/storage/innodb_plugin/ChangeLog +++ b/storage/innodb_plugin/ChangeLog @@ -1,3 +1,9 @@ +2010-06-30 The InnoDB Team + + * btr/btr0sea.c, ha/ha0ha.c, handler/ha_innodb.cc, include/btr0sea.h: + Fix Bug#54311 Crash on CHECK PARTITION after concurrent LOAD DATA + and adaptive_hash_index=OFF + 2010-06-29 The InnoDB Team * row/row0row.c, row/row0undo.c, row/row0upd.c: Fix Bug#54408 txn rollback after recovery: row0umod.c:673 diff --git a/storage/innodb_plugin/btr/btr0sea.c b/storage/innodb_plugin/btr/btr0sea.c index c91afa31bf0..ac7248fef20 100644 --- a/storage/innodb_plugin/btr/btr0sea.c +++ b/storage/innodb_plugin/btr/btr0sea.c @@ -46,6 +46,7 @@ Created 2/17/1996 Heikki Tuuri /** Flag: has the search system been enabled? Protected by btr_search_latch and btr_search_enabled_mutex. */ UNIV_INTERN char btr_search_enabled = TRUE; +UNIV_INTERN ibool btr_search_fully_disabled = FALSE; /** Mutex protecting btr_search_enabled */ static mutex_t btr_search_enabled_mutex; @@ -201,12 +202,19 @@ btr_search_disable(void) mutex_enter(&btr_search_enabled_mutex); rw_lock_x_lock(&btr_search_latch); + /* Disable access to hash index, also tell ha_insert_for_fold() + stop adding new nodes to hash index, but still allow updating + existing nodes */ btr_search_enabled = FALSE; /* Clear all block->is_hashed flags and remove all entries from btr_search_sys->hash_index. */ buf_pool_drop_hash_index(); + /* hash index has been cleaned up, disallow any operation to + the hash index */ + btr_search_fully_disabled = TRUE; + /* btr_search_enabled_mutex should guarantee this. */ ut_ad(!btr_search_enabled); @@ -225,6 +233,7 @@ btr_search_enable(void) rw_lock_x_lock(&btr_search_latch); btr_search_enabled = TRUE; + btr_search_fully_disabled = FALSE; rw_lock_x_unlock(&btr_search_latch); mutex_exit(&btr_search_enabled_mutex); @@ -1363,7 +1372,7 @@ btr_search_build_page_hash_index( rw_lock_x_lock(&btr_search_latch); - if (UNIV_UNLIKELY(!btr_search_enabled)) { + if (UNIV_UNLIKELY(btr_search_fully_disabled)) { goto exit_func; } diff --git a/storage/innodb_plugin/ha/ha0ha.c b/storage/innodb_plugin/ha/ha0ha.c index 9d9d341ad39..f9e798012f8 100644 --- a/storage/innodb_plugin/ha/ha0ha.c +++ b/storage/innodb_plugin/ha/ha0ha.c @@ -31,9 +31,7 @@ Created 8/22/1994 Heikki Tuuri #ifdef UNIV_DEBUG # include "buf0buf.h" #endif /* UNIV_DEBUG */ -#ifdef UNIV_SYNC_DEBUG -# include "btr0sea.h" -#endif /* UNIV_SYNC_DEBUG */ +#include "btr0sea.h" #include "page0page.h" /*************************************************************//** @@ -127,7 +125,8 @@ ha_clear( /*************************************************************//** Inserts an entry into a hash table. If an entry with the same fold number is found, its node is updated to point to the new data, and no new node -is inserted. +is inserted. If btr_search_enabled is set to FALSE, we will only allow +updating existing nodes, but no new node is allowed to be added. @return TRUE if succeed, FALSE if no more memory could be allocated */ UNIV_INTERN ibool @@ -174,6 +173,7 @@ ha_insert_for_fold_func( prev_block->n_pointers--; block->n_pointers++; } + ut_ad(!btr_search_fully_disabled); # endif /* !UNIV_HOTBACKUP */ prev_node->block = block; @@ -186,6 +186,13 @@ ha_insert_for_fold_func( prev_node = prev_node->next; } + /* We are in the process of disabling hash index, do not add + new chain node */ + if (!btr_search_enabled) { + ut_ad(!btr_search_fully_disabled); + return(TRUE); + } + /* We have to allocate a new chain node */ node = mem_heap_alloc(hash_get_heap(table, fold), sizeof(ha_node_t)); diff --git a/storage/innodb_plugin/handler/ha_innodb.cc b/storage/innodb_plugin/handler/ha_innodb.cc index aa80814dbe0..c6042815e6c 100644 --- a/storage/innodb_plugin/handler/ha_innodb.cc +++ b/storage/innodb_plugin/handler/ha_innodb.cc @@ -2270,6 +2270,7 @@ innobase_change_buffering_inited_ok: /* Get the current high water mark format. */ innobase_file_format_check = (char*) trx_sys_file_format_max_get(); + btr_search_fully_disabled = (!btr_search_enabled); DBUG_RETURN(FALSE); error: DBUG_RETURN(TRUE); diff --git a/storage/innodb_plugin/include/btr0sea.h b/storage/innodb_plugin/include/btr0sea.h index f98ba386f9c..20a2be7f877 100644 --- a/storage/innodb_plugin/include/btr0sea.h +++ b/storage/innodb_plugin/include/btr0sea.h @@ -190,7 +190,13 @@ btr_search_validate(void); /** Flag: has the search system been enabled? Protected by btr_search_latch and btr_search_enabled_mutex. */ -extern char btr_search_enabled; +extern char btr_search_enabled; + +/** Flag: whether the search system has completed its disabling process, +It is set to TRUE right after buf_pool_drop_hash_index() in +btr_search_disable(), indicating hash index entries are cleaned up. +Protected by btr_search_latch and btr_search_enabled_mutex. */ +extern ibool btr_search_fully_disabled; /** The search info struct in an index */ struct btr_search_struct{ From 9ff272fbbd9f8e8bb412cf8ddc12d6e97242ef63 Mon Sep 17 00:00:00 2001 From: Jon Olav Hauglid Date: Thu, 1 Jul 2010 15:53:46 +0200 Subject: [PATCH 050/129] A 5.5 version of the fix for Bug #54360 "Deadlock DROP/ALTER/CREATE DATABASE with open HANDLER" Remove LOCK_create_db, database name locks, and use metadata locks instead. This exposes CREATE/DROP/ALTER DATABASE statements to the graph-based deadlock detector in MDL, and paves the way for a safe, deadlock-free implementation of RENAME DATABASE. Database DDL statements will now take exclusive metadata locks on the database name, while table/view/routine DDL statements take intention exclusive locks on the database name. This prevents race conditions between database DDL and table/view/routine DDL. (e.g. DROP DATABASE with concurrent CREATE/ALTER/DROP TABLE) By adding database name locks, this patch implements WL#4450 "DDL locking: CREATE/DROP DATABASE must use database locks" and WL#4985 "DDL locking: namespace/hierarchical locks". The patch also changes code to use init_one_table() where appropriate. The new lock_table_names() function requires TABLE_LIST::db_length to be set correctly, and this is taken care of by init_one_table(). This patch also adds a simple template to help work with the mysys HASH data structure. Most of the patch was written by Konstantin Osipov. --- mysql-test/r/mdl_sync.result | 237 +++++++++ mysql-test/r/partition_debug_sync.result | 2 +- mysql-test/r/schema.result | 50 +- .../suite/perfschema/r/server_init.result | 8 - .../suite/perfschema/t/server_init.test | 6 - mysql-test/t/mdl_sync.test | 475 ++++++++++++++++++ mysql-test/t/partition_debug_sync.test | 2 +- mysql-test/t/schema.test | 98 +++- sql/lock.cc | 67 ++- sql/lock.h | 3 +- sql/mdl.cc | 76 +-- sql/mdl.h | 10 +- sql/mysqld.cc | 21 +- sql/mysqld.h | 6 +- sql/sql_acl.cc | 97 ++-- sql/sql_base.cc | 167 +++--- sql/sql_base.h | 10 +- sql/sql_db.cc | 320 ++---------- sql/sql_db.h | 7 +- sql/sql_help.cc | 23 +- sql/sql_hset.h | 117 +++++ sql/sql_parse.cc | 37 +- sql/sql_rename.cc | 10 +- sql/sql_table.cc | 49 +- sql/sql_table.h | 1 - sql/sql_truncate.cc | 42 +- sql/sql_view.cc | 7 +- sql/sql_yacc.yy | 4 +- 28 files changed, 1300 insertions(+), 652 deletions(-) create mode 100644 sql/sql_hset.h diff --git a/mysql-test/r/mdl_sync.result b/mysql-test/r/mdl_sync.result index 67d778211dd..1b0ffc588e1 100644 --- a/mysql-test/r/mdl_sync.result +++ b/mysql-test/r/mdl_sync.result @@ -2527,3 +2527,240 @@ SET DEBUG_SYNC= "now SIGNAL completed"; Field Type Collation Null Key Default Extra Privileges Comment a char(255) latin1_swedish_ci YES NULL # DROP TABLE t1; +# +# Tests for schema-scope locks +# +DROP DATABASE IF EXISTS db1; +DROP DATABASE IF EXISTS db2; +# Test 1: +# CREATE DATABASE blocks database DDL on the same database, but +# not database DDL on different databases. Tests X vs X lock. +# +# Connection default +SET DEBUG_SYNC= 'after_wait_locked_schema_name SIGNAL locked WAIT_FOR blocked'; +# Sending: +CREATE DATABASE db1; +# Connection con2 +SET DEBUG_SYNC= 'now WAIT_FOR locked'; +# Sending: +CREATE DATABASE db1; +# Connection con3 +CREATE DATABASE db2; +ALTER DATABASE db2 DEFAULT CHARACTER SET utf8; +DROP DATABASE db2; +SET DEBUG_SYNC= 'now SIGNAL blocked'; +# Connection default +# Reaping: CREATE DATABASE db1 +# Connection con2 +# Reaping: CREATE DATABASE db1 +ERROR HY000: Can't create database 'db1'; database exists +# Test 2: +# ALTER DATABASE blocks database DDL on the same database, but +# not database DDL on different databases. Tests X vs X lock. +# +# Connection default +SET DEBUG_SYNC= 'after_wait_locked_schema_name SIGNAL locked WAIT_FOR blocked'; +# Sending: +ALTER DATABASE db1 DEFAULT CHARACTER SET utf8; +# Connection con2 +SET DEBUG_SYNC= 'now WAIT_FOR locked'; +# Sending: +ALTER DATABASE db1 DEFAULT CHARACTER SET utf8; +# Connection con3 +CREATE DATABASE db2; +ALTER DATABASE db2 DEFAULT CHARACTER SET utf8; +DROP DATABASE db2; +SET DEBUG_SYNC= 'now SIGNAL blocked'; +# Connection default +# Reaping: ALTER DATABASE db1 DEFAULT CHARACTER SET utf8 +# Connection con2 +# Reaping: ALTER DATABASE db1 DEFAULT CHARACTER SET utf8 +# Connection default +SET DEBUG_SYNC= 'after_wait_locked_schema_name SIGNAL locked WAIT_FOR blocked'; +# Sending: +ALTER DATABASE db1 DEFAULT CHARACTER SET utf8; +# Connection con2 +SET DEBUG_SYNC= 'now WAIT_FOR locked'; +# Sending: +DROP DATABASE db1; +# Connection con3 +SET DEBUG_SYNC= 'now SIGNAL blocked'; +# Connection default +# Reaping: ALTER DATABASE db1 DEFAULT CHARACTER SET utf8 +# Connection con2 +# Reaping: DROP DATABASE db1 +CREATE DATABASE db1; +# Test 3: +# Two ALTER..UPGRADE of the same database are mutually exclusive, but +# two ALTER..UPGRADE of different databases are not. Tests X vs X lock. +# +# Connection default +SET DEBUG_SYNC= 'after_wait_locked_schema_name SIGNAL locked WAIT_FOR blocked'; +# Sending: +ALTER DATABASE `#mysql50#a-b-c` UPGRADE DATA DIRECTORY NAME; +# Connection con2 +SET DEBUG_SYNC= 'now WAIT_FOR locked'; +# Sending: +ALTER DATABASE `#mysql50#a-b-c` UPGRADE DATA DIRECTORY NAME; +# Connection con3 +ALTER DATABASE `#mysql50#a-b-c-d` UPGRADE DATA DIRECTORY NAME; +SET DEBUG_SYNC= 'now SIGNAL blocked'; +# Connection default +# Reaping: ALTER DATABASE '#mysql50#a-b-c' UPGRADE DATA DIRECTORY NAME +# Connection con2 +# Reaping: ALTER DATABASE '#mysql50#a-b-c' UPGRADE DATA DIRECTORY NAME +ERROR 42000: Unknown database '#mysql50#a-b-c' +DROP DATABASE `a-b-c`; +DROP DATABASE `a-b-c-d`; +# Test 4: +# DROP DATABASE blocks database DDL on the same database, but +# not database DDL on different databases. Tests X vs X lock. +# +# Connection default +SET DEBUG_SYNC= 'after_wait_locked_schema_name SIGNAL locked WAIT_FOR blocked'; +# Sending: +DROP DATABASE db1; +# Connection con2 +SET DEBUG_SYNC= 'now WAIT_FOR locked'; +# Sending: +DROP DATABASE db1; +# Connection con3 +CREATE DATABASE db2; +ALTER DATABASE db2 DEFAULT CHARACTER SET utf8; +DROP DATABASE db2; +SET DEBUG_SYNC= 'now SIGNAL blocked'; +# Connection default +# Reaping: DROP DATABASE db1 +# Connection con2 +# Reaping: DROP DATABASE db1 +ERROR HY000: Can't drop database 'db1'; database doesn't exist +# Connection default +CREATE DATABASE db1; +SET DEBUG_SYNC= 'after_wait_locked_schema_name SIGNAL locked WAIT_FOR blocked'; +# Sending: +DROP DATABASE db1; +# Connection con2 +SET DEBUG_SYNC= 'now WAIT_FOR locked'; +# Sending: +ALTER DATABASE db1 DEFAULT CHARACTER SET utf8; +# Connection con3 +SET DEBUG_SYNC= 'now SIGNAL blocked'; +# Connection default +# Reaping: DROP DATABASE db1 +# Connection con2 +# Reaping: ALTER DATABASE db1 DEFAULT CHARACTER SET utf8 +ERROR HY000: Can't create/write to file './db1/db.opt' (Errcode: 2) +# Test 5: +# Locked database name prevents CREATE of tables in that database. +# Tests X vs IX lock. +# +# Connection default +CREATE DATABASE db1; +SET DEBUG_SYNC= 'after_wait_locked_schema_name SIGNAL locked WAIT_FOR blocked'; +# Sending: +DROP DATABASE db1; +# Connection con2 +SET DEBUG_SYNC= 'now WAIT_FOR locked'; +# Sending: +CREATE TABLE db1.t1 (a INT); +# Connection con3 +SET DEBUG_SYNC= 'now SIGNAL blocked'; +# Connection default +# Reaping: DROP DATABASE db1 +# Connection con2 +# Reaping: CREATE TABLE db1.t1 (a INT) +ERROR 42000: Unknown database 'db1' +# Test 6: +# Locked database name prevents RENAME of tables to/from that database. +# Tests X vs IX lock. +# +# Connection default +CREATE DATABASE db1; +CREATE TABLE db1.t1 (a INT); +SET DEBUG_SYNC= 'after_wait_locked_schema_name SIGNAL locked WAIT_FOR blocked'; +# Sending: +DROP DATABASE db1; +# Connection con2 +SET DEBUG_SYNC= 'now WAIT_FOR locked'; +# Sending: +RENAME TABLE db1.t1 TO test.t1; +# Connection con3 +SET DEBUG_SYNC= 'now SIGNAL blocked'; +# Connection default +# Reaping: DROP DATABASE db1 +# Connection con2 +# Reaping: RENAME TABLE db1.t1 TO test.t1 +ERROR HY000: Can't find file: './db1/t1.frm' (errno: 2) +# Connection default +CREATE DATABASE db1; +CREATE TABLE test.t2 (a INT); +SET DEBUG_SYNC= 'after_wait_locked_schema_name SIGNAL locked WAIT_FOR blocked'; +# Sending: +DROP DATABASE db1; +# Connection con2 +SET DEBUG_SYNC= 'now WAIT_FOR locked'; +# Sending: +RENAME TABLE test.t2 TO db1.t2; +# Connection con3 +SET DEBUG_SYNC= 'now SIGNAL blocked'; +# Connection default +# Reaping: DROP DATABASE db1 +# Connection con2 +# Reaping: RENAME TABLE test.t2 TO db1.t2 +ERROR HY000: Error on rename of './test/t2.MYI' to './db1/t2.MYI' (Errcode: 2) +DROP TABLE test.t2; +# Test 7: +# Locked database name prevents DROP of tables in that database. +# Tests X vs IX lock. +# +# Connection default +CREATE DATABASE db1; +CREATE TABLE db1.t1 (a INT); +SET DEBUG_SYNC= 'after_wait_locked_schema_name SIGNAL locked WAIT_FOR blocked'; +# Sending: +DROP DATABASE db1; +# Connection con2 +SET DEBUG_SYNC= 'now WAIT_FOR locked'; +# Sending: +DROP TABLE db1.t1; +# Connection con3 +SET DEBUG_SYNC= 'now SIGNAL blocked'; +# Connection default +# Reaping: DROP DATABASE db1 +# Connection con2 +# Reaping: DROP TABLE db1.t1 +ERROR 42S02: Unknown table 't1' +# Connection default +SET DEBUG_SYNC= 'RESET'; +# +# End of tests for schema-scope locks +# +# +# Tests of granted global S lock (FLUSH TABLE WITH READ LOCK) +# +CREATE DATABASE db1; +CREATE TABLE db1.t1(a INT); +# Connection default +FLUSH TABLE WITH READ LOCK; +# Connection con2 +CREATE TABLE db1.t2(a INT); +# Connection default +UNLOCK TABLES; +# Connection con2 +# Reaping CREATE TABLE db1.t2(a INT) +# Connection default +FLUSH TABLE WITH READ LOCK; +# Connection con2 +ALTER DATABASE db1 DEFAULT CHARACTER SET utf8; +# Connection default +UNLOCK TABLES; +# Connection con2 +# Reaping ALTER DATABASE db1 DEFAULT CHARACTER SET utf8 +# Connection default +FLUSH TABLE WITH READ LOCK; +# Connection con2 +FLUSH TABLE WITH READ LOCK; +UNLOCK TABLES; +# Connection default +UNLOCK TABLES; +DROP DATABASE db1; diff --git a/mysql-test/r/partition_debug_sync.result b/mysql-test/r/partition_debug_sync.result index 5ab1044934b..0e3241cf88e 100644 --- a/mysql-test/r/partition_debug_sync.result +++ b/mysql-test/r/partition_debug_sync.result @@ -47,7 +47,7 @@ ENGINE = MYISAM PARTITION p1 VALUES LESS THAN (20), PARTITION p2 VALUES LESS THAN (100), PARTITION p3 VALUES LESS THAN MAXVALUE ) */; -SET DEBUG_SYNC= 'open_tables_acquire_upgradable_mdl SIGNAL removing_partitions WAIT_FOR waiting_for_alter'; +SET DEBUG_SYNC= 'alter_table_before_open_tables SIGNAL removing_partitions WAIT_FOR waiting_for_alter'; SET DEBUG_SYNC= 'alter_table_before_rename_result_table WAIT_FOR delete_done'; ALTER TABLE t2 REMOVE PARTITIONING; # Con default diff --git a/mysql-test/r/schema.result b/mysql-test/r/schema.result index 2919606d74a..890f53669b5 100644 --- a/mysql-test/r/schema.result +++ b/mysql-test/r/schema.result @@ -16,19 +16,21 @@ drop schema foo; # Bug #48940 MDL deadlocks against mysql_rm_db # DROP SCHEMA IF EXISTS schema1; +DROP SCHEMA IF EXISTS schema2; # Connection default CREATE SCHEMA schema1; +CREATE SCHEMA schema2; CREATE TABLE schema1.t1 (a INT); SET autocommit= FALSE; INSERT INTO schema1.t1 VALUES (1); # Connection 2 DROP SCHEMA schema1; # Connection default -ALTER SCHEMA schema1 DEFAULT CHARACTER SET utf8; -Got one of the listed errors +ALTER SCHEMA schema2 DEFAULT CHARACTER SET utf8; SET autocommit= TRUE; # Connection 2 # Connection default +DROP SCHEMA schema2; # # Bug #49988 MDL deadlocks with mysql_create_db, reload_acl_and_cache # @@ -48,3 +50,47 @@ ERROR HY000: Can't execute the given command because you have active locked tabl UNLOCK TABLES; # Connection con2 # Connection default +# +# Bug#54360 Deadlock DROP/ALTER/CREATE DATABASE with open HANDLER +# +CREATE DATABASE db1; +CREATE TABLE db1.t1 (a INT); +INSERT INTO db1.t1 VALUES (1), (2); +# Connection con1 +HANDLER db1.t1 OPEN; +# Connection default +# Sending: +DROP DATABASE db1; +# Connection con2 +# Connection con1 +CREATE DATABASE db2; +ALTER DATABASE db2 DEFAULT CHARACTER SET utf8; +DROP DATABASE db2; +# Connection default +# Reaping: DROP DATABASE db1 +# +# Tests for increased CREATE/ALTER/DROP DATABASE concurrency with +# database name locks. +# +DROP DATABASE IF EXISTS db1; +DROP DATABASE IF EXISTS db2; +# Connection default +CREATE DATABASE db1; +CREATE TABLE db1.t1 (id INT); +START TRANSACTION; +INSERT INTO db1.t1 VALUES (1); +# Connection 2 +# DROP DATABASE should block due to the active transaction +# Sending: +DROP DATABASE db1; +# Connection 3 +# But it should still be possible to CREATE/ALTER/DROP other databases. +CREATE DATABASE db2; +ALTER DATABASE db2 DEFAULT CHARACTER SET utf8; +DROP DATABASE db2; +# Connection default +# End the transaction so DROP DATABASE db1 can continue +COMMIT; +# Connection 2 +# Reaping: DROP DATABASE db1 +# Connection default; diff --git a/mysql-test/suite/perfschema/r/server_init.result b/mysql-test/suite/perfschema/r/server_init.result index ac340f8eb67..a37a5805dd7 100644 --- a/mysql-test/suite/perfschema/r/server_init.result +++ b/mysql-test/suite/perfschema/r/server_init.result @@ -40,18 +40,10 @@ where name like "wait/synch/cond/mysys/THR_COND_threads"; count(name) 1 select count(name) from MUTEX_INSTANCES -where name like "wait/synch/mutex/sql/LOCK_mysql_create_db"; -count(name) -1 -select count(name) from MUTEX_INSTANCES where name like "wait/synch/mutex/sql/LOCK_open"; count(name) 1 select count(name) from MUTEX_INSTANCES -where name like "wait/synch/mutex/sql/LOCK_lock_db"; -count(name) -1 -select count(name) from MUTEX_INSTANCES where name like "wait/synch/mutex/sql/LOCK_thread_count"; count(name) 1 diff --git a/mysql-test/suite/perfschema/t/server_init.test b/mysql-test/suite/perfschema/t/server_init.test index cd9357cce67..0bb3dd84ac4 100644 --- a/mysql-test/suite/perfschema/t/server_init.test +++ b/mysql-test/suite/perfschema/t/server_init.test @@ -68,15 +68,9 @@ select count(name) from COND_INSTANCES # Verify that these global mutexes have been properly initilized in sql -select count(name) from MUTEX_INSTANCES - where name like "wait/synch/mutex/sql/LOCK_mysql_create_db"; - select count(name) from MUTEX_INSTANCES where name like "wait/synch/mutex/sql/LOCK_open"; -select count(name) from MUTEX_INSTANCES - where name like "wait/synch/mutex/sql/LOCK_lock_db"; - select count(name) from MUTEX_INSTANCES where name like "wait/synch/mutex/sql/LOCK_thread_count"; diff --git a/mysql-test/t/mdl_sync.test b/mysql-test/t/mdl_sync.test index 19f9b396087..441cabb10e2 100644 --- a/mysql-test/t/mdl_sync.test +++ b/mysql-test/t/mdl_sync.test @@ -3705,6 +3705,481 @@ DROP TABLE t1; disconnect con1; +--echo # +--echo # Tests for schema-scope locks +--echo # + +--disable_warnings +DROP DATABASE IF EXISTS db1; +DROP DATABASE IF EXISTS db2; +--enable_warnings + +connect (con2, localhost, root); +connect (con3, localhost, root); + +--echo # Test 1: +--echo # CREATE DATABASE blocks database DDL on the same database, but +--echo # not database DDL on different databases. Tests X vs X lock. +--echo # + +--echo # Connection default +connection default; +SET DEBUG_SYNC= 'after_wait_locked_schema_name SIGNAL locked WAIT_FOR blocked'; +--echo # Sending: +--send CREATE DATABASE db1 + +--echo # Connection con2 +connection con2; +SET DEBUG_SYNC= 'now WAIT_FOR locked'; +--echo # Sending: +# This should block. +--send CREATE DATABASE db1 + +--echo # Connection con3 +connection con3; +let $wait_condition=SELECT COUNT(*)=1 FROM information_schema.processlist + WHERE state='Waiting for table' AND info='CREATE DATABASE db1'; +--source include/wait_condition.inc +# This should not block. +CREATE DATABASE db2; +ALTER DATABASE db2 DEFAULT CHARACTER SET utf8; +DROP DATABASE db2; +SET DEBUG_SYNC= 'now SIGNAL blocked'; + +--echo # Connection default +connection default; +--echo # Reaping: CREATE DATABASE db1 +--reap + +--echo # Connection con2 +connection con2; +--echo # Reaping: CREATE DATABASE db1 +--error ER_DB_CREATE_EXISTS +--reap + +--echo # Test 2: +--echo # ALTER DATABASE blocks database DDL on the same database, but +--echo # not database DDL on different databases. Tests X vs X lock. +--echo # + +--echo # Connection default +connection default; +SET DEBUG_SYNC= 'after_wait_locked_schema_name SIGNAL locked WAIT_FOR blocked'; +--echo # Sending: +--send ALTER DATABASE db1 DEFAULT CHARACTER SET utf8 + +--echo # Connection con2 +connection con2; +SET DEBUG_SYNC= 'now WAIT_FOR locked'; +--echo # Sending: +# This should block. +--send ALTER DATABASE db1 DEFAULT CHARACTER SET utf8 + +--echo # Connection con3 +connection con3; +let $wait_condition=SELECT COUNT(*)=1 FROM information_schema.processlist + WHERE state='Waiting for table' + AND info='ALTER DATABASE db1 DEFAULT CHARACTER SET utf8'; +--source include/wait_condition.inc +# This should not block. +CREATE DATABASE db2; +ALTER DATABASE db2 DEFAULT CHARACTER SET utf8; +DROP DATABASE db2; +SET DEBUG_SYNC= 'now SIGNAL blocked'; + +--echo # Connection default +connection default; +--echo # Reaping: ALTER DATABASE db1 DEFAULT CHARACTER SET utf8 +--reap + +--echo # Connection con2 +connection con2; +--echo # Reaping: ALTER DATABASE db1 DEFAULT CHARACTER SET utf8 +--reap + +--echo # Connection default +connection default; +SET DEBUG_SYNC= 'after_wait_locked_schema_name SIGNAL locked WAIT_FOR blocked'; +--echo # Sending: +--send ALTER DATABASE db1 DEFAULT CHARACTER SET utf8 + +--echo # Connection con2 +connection con2; +SET DEBUG_SYNC= 'now WAIT_FOR locked'; +--echo # Sending: +# This should also block. +--send DROP DATABASE db1 + +--echo # Connection con3 +connection con3; +let $wait_condition=SELECT COUNT(*)=1 FROM information_schema.processlist + WHERE state='Waiting for table' AND info='DROP DATABASE db1'; +--source include/wait_condition.inc +SET DEBUG_SYNC= 'now SIGNAL blocked'; + +--echo # Connection default +connection default; +--echo # Reaping: ALTER DATABASE db1 DEFAULT CHARACTER SET utf8 +--reap + +--echo # Connection con2 +connection con2; +--echo # Reaping: DROP DATABASE db1 +--reap +# Recreate the database +CREATE DATABASE db1; + +--echo # Test 3: +--echo # Two ALTER..UPGRADE of the same database are mutually exclusive, but +--echo # two ALTER..UPGRADE of different databases are not. Tests X vs X lock. +--echo # + +let $MYSQLD_DATADIR= `select @@datadir`; +# Manually make a 5.0 database from the template +--mkdir $MYSQLD_DATADIR/a-b-c +--copy_file $MYSQLD_DATADIR/db1/db.opt $MYSQLD_DATADIR/a-b-c/db.opt +--mkdir $MYSQLD_DATADIR/a-b-c-d +--copy_file $MYSQLD_DATADIR/db1/db.opt $MYSQLD_DATADIR/a-b-c-d/db.opt + +--echo # Connection default +connection default; +SET DEBUG_SYNC= 'after_wait_locked_schema_name SIGNAL locked WAIT_FOR blocked'; +--echo # Sending: +--send ALTER DATABASE `#mysql50#a-b-c` UPGRADE DATA DIRECTORY NAME + +--echo # Connection con2 +connection con2; +SET DEBUG_SYNC= 'now WAIT_FOR locked'; +--echo # Sending: +# This should block. +--send ALTER DATABASE `#mysql50#a-b-c` UPGRADE DATA DIRECTORY NAME + +--echo # Connection con3 +connection con3; +let $wait_condition=SELECT COUNT(*)=1 FROM information_schema.processlist + WHERE state='Waiting for table' + AND info='ALTER DATABASE `#mysql50#a-b-c` UPGRADE DATA DIRECTORY NAME'; +--source include/wait_condition.inc +# This should not block. +ALTER DATABASE `#mysql50#a-b-c-d` UPGRADE DATA DIRECTORY NAME; +SET DEBUG_SYNC= 'now SIGNAL blocked'; + +--echo # Connection default +connection default; +--echo # Reaping: ALTER DATABASE '#mysql50#a-b-c' UPGRADE DATA DIRECTORY NAME +--reap + +--echo # Connection con2 +connection con2; +--echo # Reaping: ALTER DATABASE '#mysql50#a-b-c' UPGRADE DATA DIRECTORY NAME +--error ER_BAD_DB_ERROR +--reap +DROP DATABASE `a-b-c`; +DROP DATABASE `a-b-c-d`; + +--echo # Test 4: +--echo # DROP DATABASE blocks database DDL on the same database, but +--echo # not database DDL on different databases. Tests X vs X lock. +--echo # + +--echo # Connection default +connection default; +SET DEBUG_SYNC= 'after_wait_locked_schema_name SIGNAL locked WAIT_FOR blocked'; +--echo # Sending: +--send DROP DATABASE db1 + +--echo # Connection con2 +connection con2; +SET DEBUG_SYNC= 'now WAIT_FOR locked'; +--echo # Sending: +# This should block. +--send DROP DATABASE db1 + +--echo # Connection con3 +connection con3; +let $wait_condition=SELECT COUNT(*)=1 FROM information_schema.processlist + WHERE state='Waiting for table' AND info='DROP DATABASE db1'; +--source include/wait_condition.inc +# This should not block. +CREATE DATABASE db2; +ALTER DATABASE db2 DEFAULT CHARACTER SET utf8; +DROP DATABASE db2; +SET DEBUG_SYNC= 'now SIGNAL blocked'; + +--echo # Connection default +connection default; +--echo # Reaping: DROP DATABASE db1 +--reap + +--echo # Connection con2 +connection con2; +--echo # Reaping: DROP DATABASE db1 +--error ER_DB_DROP_EXISTS +--reap + +--echo # Connection default +connection default; +CREATE DATABASE db1; +SET DEBUG_SYNC= 'after_wait_locked_schema_name SIGNAL locked WAIT_FOR blocked'; +--echo # Sending: +--send DROP DATABASE db1 + +--echo # Connection con2 +connection con2; +SET DEBUG_SYNC= 'now WAIT_FOR locked'; +--echo # Sending: +# This should also block. +--send ALTER DATABASE db1 DEFAULT CHARACTER SET utf8 + +--echo # Connection con3 +connection con3; +let $wait_condition=SELECT COUNT(*)=1 FROM information_schema.processlist + WHERE state='Waiting for table' + AND info='ALTER DATABASE db1 DEFAULT CHARACTER SET utf8'; +--source include/wait_condition.inc +SET DEBUG_SYNC= 'now SIGNAL blocked'; + +--echo # Connection default +connection default; +--echo # Reaping: DROP DATABASE db1 +--reap + +--echo # Connection con2 +connection con2; +--echo # Reaping: ALTER DATABASE db1 DEFAULT CHARACTER SET utf8 +--error 1 # Wrong error pending followup patch for bug#54360 +--reap + + +--echo # Test 5: +--echo # Locked database name prevents CREATE of tables in that database. +--echo # Tests X vs IX lock. +--echo # + +--echo # Connection default +connection default; +CREATE DATABASE db1; +SET DEBUG_SYNC= 'after_wait_locked_schema_name SIGNAL locked WAIT_FOR blocked'; +--echo # Sending: +--send DROP DATABASE db1 + +--echo # Connection con2 +connection con2; +SET DEBUG_SYNC= 'now WAIT_FOR locked'; +--echo # Sending: +# This should block. +--send CREATE TABLE db1.t1 (a INT) + +--echo # Connection con3 +connection con3; +let $wait_condition=SELECT COUNT(*)=1 FROM information_schema.processlist + WHERE state='Waiting for table' AND info='CREATE TABLE db1.t1 (a INT)'; +--source include/wait_condition.inc +SET DEBUG_SYNC= 'now SIGNAL blocked'; + +--echo # Connection default +connection default; +--echo # Reaping: DROP DATABASE db1 +--reap + +--echo # Connection con2 +connection con2; +--echo # Reaping: CREATE TABLE db1.t1 (a INT) +--error ER_BAD_DB_ERROR +--reap + +--echo # Test 6: +--echo # Locked database name prevents RENAME of tables to/from that database. +--echo # Tests X vs IX lock. +--echo # + +--echo # Connection default +connection default; +CREATE DATABASE db1; +CREATE TABLE db1.t1 (a INT); +SET DEBUG_SYNC= 'after_wait_locked_schema_name SIGNAL locked WAIT_FOR blocked'; +--echo # Sending: +--send DROP DATABASE db1 + +--echo # Connection con2 +connection con2; +SET DEBUG_SYNC= 'now WAIT_FOR locked'; +--echo # Sending: +# This should block. +--send RENAME TABLE db1.t1 TO test.t1 + +--echo # Connection con3 +connection con3; +let $wait_condition=SELECT COUNT(*)=1 FROM information_schema.processlist + WHERE state='Waiting for table' AND info='RENAME TABLE db1.t1 TO test.t1'; +--source include/wait_condition.inc +SET DEBUG_SYNC= 'now SIGNAL blocked'; + +--echo # Connection default +connection default; +--echo # Reaping: DROP DATABASE db1 +--reap + +--echo # Connection con2 +connection con2; +--echo # Reaping: RENAME TABLE db1.t1 TO test.t1 +--error ER_FILE_NOT_FOUND +--reap + +--echo # Connection default +connection default; +CREATE DATABASE db1; +CREATE TABLE test.t2 (a INT); +SET DEBUG_SYNC= 'after_wait_locked_schema_name SIGNAL locked WAIT_FOR blocked'; +--echo # Sending: +--send DROP DATABASE db1 + +--echo # Connection con2 +connection con2; +SET DEBUG_SYNC= 'now WAIT_FOR locked'; +--echo # Sending: +# This should block. +--send RENAME TABLE test.t2 TO db1.t2 + +--echo # Connection con3 +connection con3; +let $wait_condition=SELECT COUNT(*)=1 FROM information_schema.processlist + WHERE state='Waiting for table' AND info='RENAME TABLE test.t2 TO db1.t2'; +--source include/wait_condition.inc +SET DEBUG_SYNC= 'now SIGNAL blocked'; + +--echo # Connection default +connection default; +--echo # Reaping: DROP DATABASE db1 +--reap + +--echo # Connection con2 +connection con2; +--echo # Reaping: RENAME TABLE test.t2 TO db1.t2 +--error 7 # Wrong error pending followup patch for bug#54360 +--reap +DROP TABLE test.t2; + + +--echo # Test 7: +--echo # Locked database name prevents DROP of tables in that database. +--echo # Tests X vs IX lock. +--echo # + +--echo # Connection default +connection default; +CREATE DATABASE db1; +CREATE TABLE db1.t1 (a INT); +SET DEBUG_SYNC= 'after_wait_locked_schema_name SIGNAL locked WAIT_FOR blocked'; +--echo # Sending: +--send DROP DATABASE db1 + +--echo # Connection con2 +connection con2; +SET DEBUG_SYNC= 'now WAIT_FOR locked'; +--echo # Sending: +# This should block. +--send DROP TABLE db1.t1 + +--echo # Connection con3 +connection con3; +let $wait_condition=SELECT COUNT(*)=1 FROM information_schema.processlist + WHERE state='Waiting for table' AND info='DROP TABLE db1.t1'; +--source include/wait_condition.inc +SET DEBUG_SYNC= 'now SIGNAL blocked'; + +--echo # Connection default +connection default; +--echo # Reaping: DROP DATABASE db1 +--reap + +--echo # Connection con2 +connection con2; +--echo # Reaping: DROP TABLE db1.t1 +--error ER_BAD_TABLE_ERROR +--reap + +--echo # Connection default +connection default; +disconnect con2; +disconnect con3; +SET DEBUG_SYNC= 'RESET'; + +--echo # +--echo # End of tests for schema-scope locks +--echo # + +--echo # +--echo # Tests of granted global S lock (FLUSH TABLE WITH READ LOCK) +--echo # + +CREATE DATABASE db1; +CREATE TABLE db1.t1(a INT); +connect(con2, localhost, root); +connect(con3, localhost, root); + +--echo # Connection default +connection default; +FLUSH TABLE WITH READ LOCK; + +--echo # Connection con2 +connection con2; +# IX global lock should block +--send CREATE TABLE db1.t2(a INT) + +--echo # Connection default +connection default; +let $wait_condition=SELECT COUNT(*)=1 FROM information_schema.processlist + WHERE state='Waiting for release of readlock' + AND info='CREATE TABLE db1.t2(a INT)'; +--source include/wait_condition.inc +UNLOCK TABLES; + +--echo # Connection con2 +connection con2; +--echo # Reaping CREATE TABLE db1.t2(a INT) +--reap + +--echo # Connection default +connection default; +FLUSH TABLE WITH READ LOCK; + +--echo # Connection con2 +connection con2; +# X global lock should block +--send ALTER DATABASE db1 DEFAULT CHARACTER SET utf8 + +--echo # Connection default +connection default; +let $wait_condition=SELECT COUNT(*)=1 FROM information_schema.processlist + WHERE state='Waiting for release of readlock' + AND info='ALTER DATABASE db1 DEFAULT CHARACTER SET utf8'; +--source include/wait_condition.inc +UNLOCK TABLES; + +--echo # Connection con2 +connection con2; +--echo # Reaping ALTER DATABASE db1 DEFAULT CHARACTER SET utf8 +--reap + +--echo # Connection default +connection default; +FLUSH TABLE WITH READ LOCK; + +--echo # Connection con2 +connection con2; +# S global lock should not block +FLUSH TABLE WITH READ LOCK; +UNLOCK TABLES; + +--echo # Connection default +connection default; +UNLOCK TABLES; +DROP DATABASE db1; +disconnect con2; +disconnect con3; + + # Check that all connections opened by test cases in this file are really # gone so execution of other tests won't be affected by their presence. --source include/wait_until_count_sessions.inc diff --git a/mysql-test/t/partition_debug_sync.test b/mysql-test/t/partition_debug_sync.test index 9165006f537..cde94856ae6 100644 --- a/mysql-test/t/partition_debug_sync.test +++ b/mysql-test/t/partition_debug_sync.test @@ -65,7 +65,7 @@ ENGINE = MYISAM PARTITION p1 VALUES LESS THAN (20), PARTITION p2 VALUES LESS THAN (100), PARTITION p3 VALUES LESS THAN MAXVALUE ) */; -SET DEBUG_SYNC= 'open_tables_acquire_upgradable_mdl SIGNAL removing_partitions WAIT_FOR waiting_for_alter'; +SET DEBUG_SYNC= 'alter_table_before_open_tables SIGNAL removing_partitions WAIT_FOR waiting_for_alter'; SET DEBUG_SYNC= 'alter_table_before_rename_result_table WAIT_FOR delete_done'; --send ALTER TABLE t2 REMOVE PARTITIONING connection default; diff --git a/mysql-test/t/schema.test b/mysql-test/t/schema.test index f106b9e4865..e3592f39780 100644 --- a/mysql-test/t/schema.test +++ b/mysql-test/t/schema.test @@ -23,6 +23,7 @@ drop schema foo; --disable_warnings DROP SCHEMA IF EXISTS schema1; +DROP SCHEMA IF EXISTS schema2; --enable_warnings connect(con2, localhost, root); @@ -31,6 +32,7 @@ connect(con2, localhost, root); connection default; CREATE SCHEMA schema1; +CREATE SCHEMA schema2; CREATE TABLE schema1.t1 (a INT); SET autocommit= FALSE; @@ -46,9 +48,7 @@ let $wait_condition= SELECT COUNT(*)= 1 FROM information_schema.processlist WHERE state= 'Waiting for table' AND info='DROP SCHEMA schema1'; --source include/wait_condition.inc -# Listing the error twice to prevent result diffences based on filename ---error 1,1 -ALTER SCHEMA schema1 DEFAULT CHARACTER SET utf8; +ALTER SCHEMA schema2 DEFAULT CHARACTER SET utf8; SET autocommit= TRUE; --echo # Connection 2 @@ -57,6 +57,7 @@ connection con2; --echo # Connection default connection default; +DROP SCHEMA schema2; disconnect con2; @@ -102,6 +103,97 @@ connection con2; connection default; disconnect con2; + +--echo # +--echo # Bug#54360 Deadlock DROP/ALTER/CREATE DATABASE with open HANDLER +--echo # + +CREATE DATABASE db1; +CREATE TABLE db1.t1 (a INT); +INSERT INTO db1.t1 VALUES (1), (2); + +--echo # Connection con1 +connect (con1, localhost, root); +HANDLER db1.t1 OPEN; + +--echo # Connection default +connection default; +--echo # Sending: +--send DROP DATABASE db1 + +--echo # Connection con2 +connect (con2, localhost, root); +let $wait_condition=SELECT COUNT(*)=1 FROM information_schema.processlist + WHERE state='Waiting for table' AND info='DROP DATABASE db1'; +--source include/wait_condition.inc + +--echo # Connection con1 +connection con1; +# All these statements before resulted in deadlock. +CREATE DATABASE db2; +ALTER DATABASE db2 DEFAULT CHARACTER SET utf8; +DROP DATABASE db2; + +--echo # Connection default +connection default; +--echo # Reaping: DROP DATABASE db1 +--reap +disconnect con1; +disconnect con2; + + +--echo # +--echo # Tests for increased CREATE/ALTER/DROP DATABASE concurrency with +--echo # database name locks. +--echo # + +--disable_warnings +DROP DATABASE IF EXISTS db1; +DROP DATABASE IF EXISTS db2; +--enable_warnings + +connect (con2, localhost, root); +connect (con3, localhost, root); + +--echo # Connection default +connection default; +CREATE DATABASE db1; +CREATE TABLE db1.t1 (id INT); +START TRANSACTION; +INSERT INTO db1.t1 VALUES (1); + +--echo # Connection 2 +connection con2; +--echo # DROP DATABASE should block due to the active transaction +--echo # Sending: +--send DROP DATABASE db1 + +--echo # Connection 3 +connection con3; +let $wait_condition=SELECT COUNT(*)=1 FROM information_schema.processlist + WHERE state='Waiting for table' and info='DROP DATABASE db1'; +--source include/wait_condition.inc +--echo # But it should still be possible to CREATE/ALTER/DROP other databases. +CREATE DATABASE db2; +ALTER DATABASE db2 DEFAULT CHARACTER SET utf8; +DROP DATABASE db2; + +--echo # Connection default +connection default; +--echo # End the transaction so DROP DATABASE db1 can continue +COMMIT; + +--echo # Connection 2 +connection con2; +--echo # Reaping: DROP DATABASE db1 +--reap + +--echo # Connection default; +connection default; +disconnect con2; +disconnect con3; + + # Check that all connections opened by test cases in this file are really # gone so execution of other tests won't be affected by their presence. --source include/wait_until_count_sessions.inc diff --git a/sql/lock.cc b/sql/lock.cc index de0f39018f7..dcee018276f 100644 --- a/sql/lock.cc +++ b/sql/lock.cc @@ -747,62 +747,48 @@ static MYSQL_LOCK *get_lock_data(THD *thd, TABLE **table_ptr, uint count, } -/***************************************************************************** - Lock table based on the name. - This is used when we need total access to a closed, not open table -*****************************************************************************/ - /** - Obtain exclusive metadata locks on the list of tables. + Obtain an exclusive metadata lock on a schema name. - @param thd Thread handle - @param table_list List of tables to lock + @param thd Thread handle. + @param db The database name. - @note This function assumes that no metadata locks were acquired - before calling it. Also it cannot be called while holding - LOCK_open mutex. Both these invariants are enforced by asserts - in MDL_context::acquire_locks(). - @note Initialization of MDL_request members of TABLE_LIST elements - is a responsibility of the caller. + This function cannot be called while holding LOCK_open mutex. + To avoid deadlocks, we do not try to obtain exclusive metadata + locks in LOCK TABLES mode, since in this mode there may be + other metadata locks already taken by the current connection, + and we must not wait for MDL locks while holding locks. - @retval FALSE Success. - @retval TRUE Failure (OOM or thread was killed). + @retval FALSE Success. + @retval TRUE Failure: we're in LOCK TABLES mode, or out of memory, + or this connection was killed. */ -bool lock_table_names(THD *thd, TABLE_LIST *table_list) +bool lock_schema_name(THD *thd, const char *db) { MDL_request_list mdl_requests; MDL_request global_request; - TABLE_LIST *lock_table; + MDL_request mdl_request; + + if (thd->locked_tables_mode) + { + my_message(ER_LOCK_OR_ACTIVE_TRANSACTION, + ER(ER_LOCK_OR_ACTIVE_TRANSACTION), MYF(0)); + return TRUE; + } global_request.init(MDL_key::GLOBAL, "", "", MDL_INTENTION_EXCLUSIVE); + mdl_request.init(MDL_key::SCHEMA, db, "", MDL_EXCLUSIVE); - for (lock_table= table_list; lock_table; lock_table= lock_table->next_local) - mdl_requests.push_front(&lock_table->mdl_request); - + mdl_requests.push_front(&mdl_request); mdl_requests.push_front(&global_request); if (thd->mdl_context.acquire_locks(&mdl_requests, thd->variables.lock_wait_timeout)) - return 1; + return TRUE; - return 0; -} - - -/** - Release all metadata locks previously obtained by lock_table_names(). - - @param thd Thread handle. - - @note Cannot be called while holding LOCK_open mutex. -*/ - -void unlock_table_names(THD *thd) -{ - DBUG_ENTER("unlock_table_names"); - thd->mdl_context.release_transactional_locks(); - DBUG_VOID_RETURN; + DEBUG_SYNC(thd, "after_wait_locked_schema_name"); + return FALSE; } @@ -837,6 +823,7 @@ bool lock_routine_name(THD *thd, bool is_function, MDL_key::PROCEDURE); MDL_request_list mdl_requests; MDL_request global_request; + MDL_request schema_request; MDL_request mdl_request; if (thd->locked_tables_mode) @@ -850,9 +837,11 @@ bool lock_routine_name(THD *thd, bool is_function, DEBUG_SYNC(thd, "before_wait_locked_pname"); global_request.init(MDL_key::GLOBAL, "", "", MDL_INTENTION_EXCLUSIVE); + schema_request.init(MDL_key::SCHEMA, db, "", MDL_INTENTION_EXCLUSIVE); mdl_request.init(mdl_type, db, name, MDL_EXCLUSIVE); mdl_requests.push_front(&mdl_request); + mdl_requests.push_front(&schema_request); mdl_requests.push_front(&global_request); if (thd->mdl_context.acquire_locks(&mdl_requests, diff --git a/sql/lock.h b/sql/lock.h index 4bdf0085d07..0083dd3ba18 100644 --- a/sql/lock.h +++ b/sql/lock.h @@ -62,8 +62,7 @@ bool mysql_lock_abort_for_thread(THD *thd, TABLE *table); MYSQL_LOCK *mysql_lock_merge(MYSQL_LOCK *a,MYSQL_LOCK *b); void broadcast_refresh(void); /* Lock based on name */ -bool lock_table_names(THD *thd, TABLE_LIST *table_list); -void unlock_table_names(THD *thd); +bool lock_schema_name(THD *thd, const char *db); /* Lock based on stored routine name */ bool lock_routine_name(THD *thd, bool is_function, const char *db, const char *name); diff --git a/sql/mdl.cc b/sql/mdl.cc index 22ad15d2360..631d8f52b5f 100644 --- a/sql/mdl.cc +++ b/sql/mdl.cc @@ -406,14 +406,15 @@ public: /** - An implementation of the global metadata lock. The only locking modes - which are supported at the moment are SHARED and INTENTION EXCLUSIVE. + An implementation of the scoped metadata lock. The only locking modes + which are supported at the moment are SHARED and INTENTION EXCLUSIVE + and EXCLUSIVE */ -class MDL_global_lock : public MDL_lock +class MDL_scoped_lock : public MDL_lock { public: - MDL_global_lock(const MDL_key *key_arg) + MDL_scoped_lock(const MDL_key *key_arg) : MDL_lock(key_arg) { } @@ -857,7 +858,8 @@ inline MDL_lock *MDL_lock::create(const MDL_key *mdl_key) switch (mdl_key->mdl_namespace()) { case MDL_key::GLOBAL: - return new MDL_global_lock(mdl_key); + case MDL_key::SCHEMA: + return new MDL_scoped_lock(mdl_key); case MDL_key::TABLE: return new MDL_table_lock(mdl_key); default: @@ -1217,61 +1219,66 @@ void MDL_lock::reschedule_waiters() /** - Compatibility (or rather "incompatibility") matrices for global metadata + Compatibility (or rather "incompatibility") matrices for scoped metadata lock. Arrays of bitmaps which elements specify which granted/waiting locks are incompatible with type of lock being requested. - Here is how types of individual locks are translated to type of global lock: + Here is how types of individual locks are translated to type of scoped lock: ----------------+-------------+ Type of request | Correspond. | - for indiv. lock | global lock | + for indiv. lock | scoped lock | ----------------+-------------+ S, SH, SR, SW | IS | SNW, SNRW, X | IX | SNW, SNRW -> X | IX (*) | The first array specifies if particular type of request can be satisfied - if there is granted global lock of certain type. + if there is granted scoped lock of certain type. - | Type of active | - Request | global lock | - type | IS(**) IX S | - ---------+----------------+ - IS | + + + | - IX | + + - | - S | + - + | + | Type of active | + Request | scoped lock | + type | IS(**) IX S X | + ---------+------------------+ + IS | + + + + | + IX | + + - - | + S | + - + - | + X | + - - - | The second array specifies if particular type of request can be satisfied - if there is already waiting request for the global lock of certain type. + if there is already waiting request for the scoped lock of certain type. I.e. it specifies what is the priority of different lock types. - | Pending | - Request | global lock | - type | IS(**) IX S | - ---------+--------------+ - IS | + + + | - IX | + + - | - S | + + + | + | Pending | + Request | scoped lock | + type | IS(**) IX S X | + ---------+-----------------+ + IS | + + + + | + IX | + + - - | + S | + + + - | + X | + + + + | Here: "+" -- means that request can be satisfied "-" -- means that request can't be satisfied and should wait - (*) Since for upgradable locks we always take intention exclusive global + (*) Since for upgradable locks we always take intention exclusive scoped lock at the same time when obtaining the shared lock, there is no need to obtain such lock during the upgrade itself. - (**) Since intention shared global locks are compatible with all other + (**) Since intention shared scoped locks are compatible with all other type of locks we don't even have any accounting for them. */ -const MDL_lock::bitmap_t MDL_global_lock::m_granted_incompatible[MDL_TYPE_END] = +const MDL_lock::bitmap_t MDL_scoped_lock::m_granted_incompatible[MDL_TYPE_END] = { - MDL_BIT(MDL_SHARED), MDL_BIT(MDL_INTENTION_EXCLUSIVE), 0, 0, 0, 0, 0, 0 + MDL_BIT(MDL_EXCLUSIVE) | MDL_BIT(MDL_SHARED), + MDL_BIT(MDL_EXCLUSIVE) | MDL_BIT(MDL_INTENTION_EXCLUSIVE), 0, 0, 0, 0, 0, + MDL_BIT(MDL_EXCLUSIVE) | MDL_BIT(MDL_SHARED) | MDL_BIT(MDL_INTENTION_EXCLUSIVE) }; -const MDL_lock::bitmap_t MDL_global_lock::m_waiting_incompatible[MDL_TYPE_END] = +const MDL_lock::bitmap_t MDL_scoped_lock::m_waiting_incompatible[MDL_TYPE_END] = { - MDL_BIT(MDL_SHARED), 0, 0, 0, 0, 0, 0, 0 + MDL_BIT(MDL_EXCLUSIVE) | MDL_BIT(MDL_SHARED), + MDL_BIT(MDL_EXCLUSIVE), 0, 0, 0, 0, 0, 0 }; @@ -1912,7 +1919,7 @@ extern "C" int mdl_request_ptr_cmp(const void* ptr1, const void* ptr2) @note The list of requests should not contain non-exclusive lock requests. There should not be any acquired locks in the context. - @note Assumes that one already owns global intention exclusive lock. + @note Assumes that one already owns scoped intention exclusive lock. @retval FALSE Success @retval TRUE Failure @@ -1929,13 +1936,6 @@ bool MDL_context::acquire_locks(MDL_request_list *mdl_requests, if (req_count == 0) return FALSE; - /* - To reduce deadlocks, the server acquires all exclusive - locks at once. For shared locks, try_acquire_lock() is - used instead. - */ - DBUG_ASSERT(m_tickets.is_empty() || m_tickets.front() == m_trans_sentinel); - /* Sort requests according to MDL_key. */ if (! (sort_buf= (MDL_request **)my_malloc(req_count * sizeof(MDL_request*), diff --git a/sql/mdl.h b/sql/mdl.h index ad3945f524c..5c58289aea2 100644 --- a/sql/mdl.h +++ b/sql/mdl.h @@ -40,15 +40,16 @@ class Deadlock_detection_visitor; Type of metadata lock request. @sa Comments for MDL_object_lock::can_grant_lock() and - MDL_global_lock::can_grant_lock() for details. + MDL_scoped_lock::can_grant_lock() for details. */ enum enum_mdl_type { /* - An intention exclusive metadata lock. Used only for global locks. + An intention exclusive metadata lock. Used only for scoped locks. Owner of this type of lock can acquire upgradable exclusive locks on individual objects. - Compatible with other IX locks, but is incompatible with global S lock. + Compatible with other IX locks, but is incompatible with scoped S and + X locks. */ MDL_INTENTION_EXCLUSIVE= 0, /* @@ -179,6 +180,7 @@ public: MDL_key is also used outside of the MDL subsystem. */ enum enum_mdl_namespace { GLOBAL=0, + SCHEMA, TABLE, FUNCTION, PROCEDURE, @@ -646,6 +648,8 @@ private: closes all open HANDLERs. However, one can open a few HANDLERs after entering the read only mode. + * LOCK TABLES locks include intention exclusive locks on + involved schemas. */ Ticket_list m_tickets; /** diff --git a/sql/mysqld.cc b/sql/mysqld.cc index 28cad51aa41..0ba796a5eb8 100644 --- a/sql/mysqld.cc +++ b/sql/mysqld.cc @@ -27,8 +27,8 @@ // reset_status_vars #include "strfunc.h" // find_set_from_flags #include "parse_file.h" // File_parser_dummy_hook -#include "sql_db.h" // my_database_names_free, - // my_database_names_init +#include "sql_db.h" // my_dboptions_cache_free + // my_dboptions_cache_init #include "sql_table.h" // release_ddl_log, execute_ddl_log_recovery #include "sql_connect.h" // free_max_user_conn, init_max_user_conn, // handle_one_connection @@ -653,7 +653,7 @@ SHOW_COMP_OPTION have_profiling; pthread_key(MEM_ROOT**,THR_MALLOC); pthread_key(THD*, THR_THD); mysql_mutex_t LOCK_thread_count; -mysql_mutex_t LOCK_mysql_create_db, LOCK_open, +mysql_mutex_t LOCK_open, LOCK_mapped_file, LOCK_status, LOCK_global_read_lock, LOCK_error_log, LOCK_uuid_generator, LOCK_delayed_insert, LOCK_delayed_status, LOCK_delayed_create, @@ -1488,7 +1488,7 @@ void clean_up(bool print_message) bitmap_free(&slave_error_mask); #endif my_tz_free(); - my_database_names_free(); + my_dboptions_cache_free(); #ifndef NO_EMBEDDED_ACCESS_CHECKS servers_free(1); acl_free(1); @@ -1597,8 +1597,6 @@ static void wait_for_signal_thread_to_end() static void clean_up_mutexes() { - mysql_mutex_destroy(&LOCK_mysql_create_db); - mysql_mutex_destroy(&LOCK_lock_db); mysql_rwlock_destroy(&LOCK_grant); mysql_mutex_destroy(&LOCK_open); mysql_mutex_destroy(&LOCK_thread_count); @@ -3730,7 +3728,7 @@ static int init_common_variables() use_temp_pool= 0; #endif - if (my_database_names_init()) + if (my_dboptions_cache_init()) return 1; /* @@ -3787,9 +3785,6 @@ You should consider changing lower_case_table_names to 1 or 2", static int init_thread_environment() { - mysql_mutex_init(key_LOCK_mysql_create_db, - &LOCK_mysql_create_db, MY_MUTEX_INIT_SLOW); - mysql_mutex_init(key_LOCK_lock_db, &LOCK_lock_db, MY_MUTEX_INIT_SLOW); mysql_mutex_init(key_LOCK_open, &LOCK_open, MY_MUTEX_INIT_FAST); mysql_mutex_init(key_LOCK_thread_count, &LOCK_thread_count, MY_MUTEX_INIT_FAST); mysql_mutex_init(key_LOCK_mapped_file, &LOCK_mapped_file, MY_MUTEX_INIT_SLOW); @@ -8007,8 +8002,8 @@ PSI_mutex_key key_BINLOG_LOCK_index, key_BINLOG_LOCK_prep_xids, key_LOCK_connection_count, key_LOCK_crypt, key_LOCK_delayed_create, key_LOCK_delayed_insert, key_LOCK_delayed_status, key_LOCK_error_log, key_LOCK_gdl, key_LOCK_global_read_lock, key_LOCK_global_system_variables, - key_LOCK_lock_db, key_LOCK_manager, key_LOCK_mapped_file, - key_LOCK_mysql_create_db, key_LOCK_open, key_LOCK_prepared_stmt_count, + key_LOCK_manager, key_LOCK_mapped_file, + key_LOCK_open, key_LOCK_prepared_stmt_count, key_LOCK_rpl_status, key_LOCK_server_started, key_LOCK_status, key_LOCK_system_variables_hash, key_LOCK_table_share, key_LOCK_thd_data, key_LOCK_user_conn, key_LOCK_uuid_generator, key_LOG_LOCK_log, @@ -8046,10 +8041,8 @@ static PSI_mutex_info all_server_mutexes[]= { &key_LOCK_gdl, "LOCK_gdl", PSI_FLAG_GLOBAL}, { &key_LOCK_global_read_lock, "LOCK_global_read_lock", PSI_FLAG_GLOBAL}, { &key_LOCK_global_system_variables, "LOCK_global_system_variables", PSI_FLAG_GLOBAL}, - { &key_LOCK_lock_db, "LOCK_lock_db", PSI_FLAG_GLOBAL}, { &key_LOCK_manager, "LOCK_manager", PSI_FLAG_GLOBAL}, { &key_LOCK_mapped_file, "LOCK_mapped_file", PSI_FLAG_GLOBAL}, - { &key_LOCK_mysql_create_db, "LOCK_mysql_create_db", PSI_FLAG_GLOBAL}, { &key_LOCK_open, "LOCK_open", PSI_FLAG_GLOBAL}, { &key_LOCK_prepared_stmt_count, "LOCK_prepared_stmt_count", PSI_FLAG_GLOBAL}, { &key_LOCK_rpl_status, "LOCK_rpl_status", PSI_FLAG_GLOBAL}, diff --git a/sql/mysqld.h b/sql/mysqld.h index e14cd15ceb8..b07d148f507 100644 --- a/sql/mysqld.h +++ b/sql/mysqld.h @@ -234,8 +234,8 @@ extern PSI_mutex_key key_BINLOG_LOCK_index, key_BINLOG_LOCK_prep_xids, key_LOCK_connection_count, key_LOCK_crypt, key_LOCK_delayed_create, key_LOCK_delayed_insert, key_LOCK_delayed_status, key_LOCK_error_log, key_LOCK_gdl, key_LOCK_global_read_lock, key_LOCK_global_system_variables, - key_LOCK_lock_db, key_LOCK_logger, key_LOCK_manager, key_LOCK_mapped_file, - key_LOCK_mysql_create_db, key_LOCK_open, key_LOCK_prepared_stmt_count, + key_LOCK_logger, key_LOCK_manager, key_LOCK_mapped_file, + key_LOCK_open, key_LOCK_prepared_stmt_count, key_LOCK_rpl_status, key_LOCK_server_started, key_LOCK_status, key_LOCK_table_share, key_LOCK_thd_data, key_LOCK_user_conn, key_LOCK_uuid_generator, key_LOG_LOCK_log, @@ -323,7 +323,7 @@ extern MYSQL_PLUGIN_IMPORT key_map key_map_full; /* Should be threaded /* Server mutex locks and condition variables. */ -extern mysql_mutex_t LOCK_mysql_create_db, LOCK_open, LOCK_lock_db, +extern mysql_mutex_t LOCK_open, LOCK_mapped_file, LOCK_user_locks, LOCK_status, LOCK_error_log, LOCK_delayed_insert, LOCK_uuid_generator, LOCK_delayed_status, LOCK_delayed_create, LOCK_crypt, LOCK_timezone, diff --git a/sql/sql_acl.cc b/sql/sql_acl.cc index ec25e4cb68b..99226bad03f 100644 --- a/sql/sql_acl.cc +++ b/sql/sql_acl.cc @@ -677,16 +677,15 @@ my_bool acl_reload(THD *thd) To avoid deadlocks we should obtain table locks before obtaining acl_cache->lock mutex. */ - bzero((char*) tables, sizeof(tables)); - tables[0].alias= tables[0].table_name= (char*) "host"; - tables[1].alias= tables[1].table_name= (char*) "user"; - tables[2].alias= tables[2].table_name= (char*) "db"; - tables[0].db=tables[1].db=tables[2].db=(char*) "mysql"; + tables[0].init_one_table(C_STRING_WITH_LEN("mysql"), + C_STRING_WITH_LEN("host"), "host", TL_READ); + tables[1].init_one_table(C_STRING_WITH_LEN("mysql"), + C_STRING_WITH_LEN("user"), "user", TL_READ); + tables[2].init_one_table(C_STRING_WITH_LEN("mysql"), + C_STRING_WITH_LEN("db"), "db", TL_READ); tables[0].next_local= tables[0].next_global= tables+1; tables[1].next_local= tables[1].next_global= tables+2; - tables[0].lock_type=tables[1].lock_type=tables[2].lock_type=TL_READ; tables[0].open_type= tables[1].open_type= tables[2].open_type= OT_BASE_ONLY; - init_mdl_requests(tables); if (open_and_lock_tables(thd, tables, FALSE, MYSQL_LOCK_IGNORE_TIMEOUT)) { @@ -1925,9 +1924,8 @@ static bool test_if_create_new_users(THD *thd) { TABLE_LIST tl; ulong db_access; - bzero((char*) &tl,sizeof(tl)); - tl.db= (char*) "mysql"; - tl.table_name= (char*) "user"; + tl.init_one_table(C_STRING_WITH_LEN("mysql"), + C_STRING_WITH_LEN("user"), "user", TL_WRITE); create_new_users= 1; db_access=acl_get(sctx->host, sctx->ip, @@ -3107,20 +3105,18 @@ int mysql_table_grant(THD *thd, TABLE_LIST *table_list, /* open the mysql.tables_priv and mysql.columns_priv tables */ - bzero((char*) &tables,sizeof(tables)); - tables[0].alias=tables[0].table_name= (char*) "user"; - tables[1].alias=tables[1].table_name= (char*) "tables_priv"; - tables[2].alias=tables[2].table_name= (char*) "columns_priv"; + tables[0].init_one_table(C_STRING_WITH_LEN("mysql"), + C_STRING_WITH_LEN("user"), "user", TL_WRITE); + tables[1].init_one_table(C_STRING_WITH_LEN("mysql"), + C_STRING_WITH_LEN("tables_priv"), + "tables_priv", TL_WRITE); + tables[2].init_one_table(C_STRING_WITH_LEN("mysql"), + C_STRING_WITH_LEN("columns_priv"), + "columns_priv", TL_WRITE); tables[0].next_local= tables[0].next_global= tables+1; /* Don't open column table if we don't need it ! */ - tables[1].next_local= - tables[1].next_global= ((column_priv || - (revoke_grant && - ((rights & COL_ACLS) || columns.elements))) - ? tables+2 : 0); - tables[0].lock_type=tables[1].lock_type=tables[2].lock_type=TL_WRITE; - tables[0].db=tables[1].db=tables[2].db=(char*) "mysql"; - init_mdl_requests(tables); + if (column_priv || (revoke_grant && ((rights & COL_ACLS) || columns.elements))) + tables[1].next_local= tables[1].next_global= tables+2; /* This statement will be replicated as a statement, even when using @@ -3354,13 +3350,11 @@ bool mysql_routine_grant(THD *thd, TABLE_LIST *table_list, bool is_proc, /* open the mysql.user and mysql.procs_priv tables */ - bzero((char*) &tables,sizeof(tables)); - tables[0].alias=tables[0].table_name= (char*) "user"; - tables[1].alias=tables[1].table_name= (char*) "procs_priv"; + tables[0].init_one_table(C_STRING_WITH_LEN("mysql"), + C_STRING_WITH_LEN("user"), "user", TL_WRITE); + tables[1].init_one_table(C_STRING_WITH_LEN("mysql"), + C_STRING_WITH_LEN("procs_priv"), "procs_priv", TL_WRITE); tables[0].next_local= tables[0].next_global= tables+1; - tables[0].lock_type=tables[1].lock_type=TL_WRITE; - tables[0].db=tables[1].db=(char*) "mysql"; - init_mdl_requests(tables); /* This statement will be replicated as a statement, even when using @@ -3511,13 +3505,11 @@ bool mysql_grant(THD *thd, const char *db, List &list, } /* open the mysql.user and mysql.db tables */ - bzero((char*) &tables,sizeof(tables)); - tables[0].alias=tables[0].table_name=(char*) "user"; - tables[1].alias=tables[1].table_name=(char*) "db"; + tables[0].init_one_table(C_STRING_WITH_LEN("mysql"), + C_STRING_WITH_LEN("user"), "user", TL_WRITE); + tables[1].init_one_table(C_STRING_WITH_LEN("mysql"), + C_STRING_WITH_LEN("db"), "db", TL_WRITE); tables[0].next_local= tables[0].next_global= tables+1; - tables[0].lock_type=tables[1].lock_type=TL_WRITE; - tables[0].db=tables[1].db=(char*) "mysql"; - init_mdl_requests(tables); /* This statement will be replicated as a statement, even when using @@ -3930,14 +3922,14 @@ my_bool grant_reload(THD *thd) if (!initialized) DBUG_RETURN(0); - bzero((char*) tables, sizeof(tables)); - tables[0].alias= tables[0].table_name= (char*) "tables_priv"; - tables[1].alias= tables[1].table_name= (char*) "columns_priv"; - tables[0].db= tables[1].db= (char *) "mysql"; + tables[0].init_one_table(C_STRING_WITH_LEN("mysql"), + C_STRING_WITH_LEN("tables_priv"), + "tables_priv", TL_READ); + tables[1].init_one_table(C_STRING_WITH_LEN("mysql"), + C_STRING_WITH_LEN("columns_priv"), + "columns_priv", TL_READ); tables[0].next_local= tables[0].next_global= tables+1; - tables[0].lock_type= tables[1].lock_type= TL_READ; tables[0].open_type= tables[1].open_type= OT_BASE_ONLY; - init_mdl_requests(tables); /* To avoid deadlocks we should obtain table locks before @@ -5209,22 +5201,23 @@ int open_grant_tables(THD *thd, TABLE_LIST *tables) DBUG_RETURN(-1); } - bzero((char*) tables, GRANT_TABLES*sizeof(*tables)); - tables->alias= tables->table_name= (char*) "user"; - (tables+1)->alias= (tables+1)->table_name= (char*) "db"; - (tables+2)->alias= (tables+2)->table_name= (char*) "tables_priv"; - (tables+3)->alias= (tables+3)->table_name= (char*) "columns_priv"; - (tables+4)->alias= (tables+4)->table_name= (char*) "procs_priv"; + tables->init_one_table(C_STRING_WITH_LEN("mysql"), + C_STRING_WITH_LEN("user"), "user", TL_WRITE); + (tables+1)->init_one_table(C_STRING_WITH_LEN("mysql"), + C_STRING_WITH_LEN("db"), "db", TL_WRITE); + (tables+2)->init_one_table(C_STRING_WITH_LEN("mysql"), + C_STRING_WITH_LEN("tables_priv"), + "tables_priv", TL_WRITE); + (tables+3)->init_one_table(C_STRING_WITH_LEN("mysql"), + C_STRING_WITH_LEN("columns_priv"), + "columns_priv", TL_WRITE); + (tables+4)->init_one_table(C_STRING_WITH_LEN("mysql"), + C_STRING_WITH_LEN("procs_priv"), + "procs_priv", TL_WRITE); tables->next_local= tables->next_global= tables+1; (tables+1)->next_local= (tables+1)->next_global= tables+2; (tables+2)->next_local= (tables+2)->next_global= tables+3; (tables+3)->next_local= (tables+3)->next_global= tables+4; - tables->lock_type= (tables+1)->lock_type= - (tables+2)->lock_type= (tables+3)->lock_type= - (tables+4)->lock_type= TL_WRITE; - tables->db= (tables+1)->db= (tables+2)->db= - (tables+3)->db= (tables+4)->db= (char*) "mysql"; - init_mdl_requests(tables); #ifdef HAVE_REPLICATION /* diff --git a/sql/sql_base.cc b/sql/sql_base.cc index d69a5b1aa77..426c9db2717 100644 --- a/sql/sql_base.cc +++ b/sql/sql_base.cc @@ -53,6 +53,7 @@ #include "rpl_filter.h" #include "sql_table.h" // build_table_filename #include "datadict.h" // dd_frm_type() +#include "sql_hset.h" // Hash_set #ifdef __WIN__ #include #endif @@ -4029,7 +4030,6 @@ end_unlock: Open_table_context::Open_table_context(THD *thd, uint flags) :m_failed_table(NULL), m_start_of_statement_svp(thd->mdl_context.mdl_savepoint()), - m_global_mdl_request(NULL), m_timeout(flags & MYSQL_LOCK_IGNORE_TIMEOUT ? LONG_TIMEOUT : thd->variables.lock_wait_timeout), m_flags(flags), @@ -4040,26 +4040,6 @@ Open_table_context::Open_table_context(THD *thd, uint flags) {} -/** - Get MDL_request object for global intention exclusive lock which - is acquired during opening tables for statements which take - upgradable shared metadata locks. -*/ - -MDL_request *Open_table_context::get_global_mdl_request(THD *thd) -{ - if (! m_global_mdl_request) - { - if ((m_global_mdl_request= new (thd->mem_root) MDL_request())) - { - m_global_mdl_request->init(MDL_key::GLOBAL, "", "", - MDL_INTENTION_EXCLUSIVE); - } - } - return m_global_mdl_request; -} - - /** Check if we can back-off and set back off action if we can. Otherwise report and return error. @@ -4108,13 +4088,23 @@ request_backoff_action(enum_open_table_action action_arg, my_error(ER_LOCK_DEADLOCK, MYF(0)); return TRUE; } - m_action= action_arg; /* If auto-repair or discovery are requested, a pointer to table list element must be provided. */ - DBUG_ASSERT((m_action != OT_DISCOVER && m_action != OT_REPAIR) || table); - m_failed_table= table; + if (table) + { + DBUG_ASSERT(action_arg == OT_DISCOVER || action_arg == OT_REPAIR); + m_failed_table= (TABLE_LIST*) current_thd->alloc(sizeof(TABLE_LIST)); + if (m_failed_table == NULL) + return TRUE; + m_failed_table->init_one_table(table->db, table->db_length, + table->table_name, + table->table_name_length, + table->alias, TL_WRITE); + m_failed_table->mdl_request.set_type(MDL_EXCLUSIVE); + } + m_action= action_arg; return FALSE; } @@ -4136,11 +4126,6 @@ Open_table_context:: recover_from_failed_open(THD *thd) { bool result= FALSE; - /* - Remove reference to released ticket from MDL_request. - */ - if (m_global_mdl_request) - m_global_mdl_request->ticket= NULL; /* Execute the action. */ switch (m_action) { @@ -4152,19 +4137,9 @@ recover_from_failed_open(THD *thd) break; case OT_DISCOVER: { - MDL_request mdl_global_request; - MDL_request mdl_xlock_request(&m_failed_table->mdl_request); - MDL_request_list mdl_requests; - - mdl_global_request.init(MDL_key::GLOBAL, "", "", - MDL_INTENTION_EXCLUSIVE); - mdl_xlock_request.set_type(MDL_EXCLUSIVE); - - mdl_requests.push_front(&mdl_xlock_request); - mdl_requests.push_front(&mdl_global_request); - - if ((result= - thd->mdl_context.acquire_locks(&mdl_requests, get_timeout()))) + if ((result= lock_table_names(thd, m_failed_table, NULL, + get_timeout(), + MYSQL_OPEN_SKIP_TEMPORARY))) break; mysql_mutex_lock(&LOCK_open); @@ -4181,19 +4156,9 @@ recover_from_failed_open(THD *thd) } case OT_REPAIR: { - MDL_request mdl_global_request; - MDL_request mdl_xlock_request(&m_failed_table->mdl_request); - MDL_request_list mdl_requests; - - mdl_global_request.init(MDL_key::GLOBAL, "", "", - MDL_INTENTION_EXCLUSIVE); - mdl_xlock_request.set_type(MDL_EXCLUSIVE); - - mdl_requests.push_front(&mdl_xlock_request); - mdl_requests.push_front(&mdl_global_request); - - if ((result= - thd->mdl_context.acquire_locks(&mdl_requests, get_timeout()))) + if ((result= lock_table_names(thd, m_failed_table, NULL, + get_timeout(), + MYSQL_OPEN_SKIP_TEMPORARY))) break; mysql_mutex_lock(&LOCK_open); @@ -4688,32 +4653,40 @@ end: DBUG_RETURN(error); } +extern "C" uchar *schema_set_get_key(const uchar *record, size_t *length, + my_bool not_used __attribute__((unused))) +{ + TABLE_LIST *table=(TABLE_LIST*) record; + *length= table->db_length; + return (uchar*) table->db; +} /** - Acquire upgradable (SNW, SNRW) metadata locks on tables to be opened - for LOCK TABLES or a DDL statement. Under LOCK TABLES, we can't take + Acquire upgradable (SNW, SNRW) metadata locks on tables used by + LOCK TABLES or by a DDL statement. Under LOCK TABLES, we can't take new locks, so use open_tables_check_upgradable_mdl() instead. - @param thd Thread context. - @param tables_start Start of list of tables on which upgradable locks - should be acquired. - @param tables_end End of list of tables. - @param ot_ctx Context of open_tables() operation. - @param flags Bitmap of flags to modify how the tables will be - open, see open_table() description for details. + @param thd Thread context. + @param tables_start Start of list of tables on which upgradable locks + should be acquired. + @param tables_end End of list of tables. + @param lock_wait_timeout Seconds to wait before timeout. + @param flags Bitmap of flags to modify how the tables will be + open, see open_table() description for details. @retval FALSE Success. @retval TRUE Failure (e.g. connection was killed) */ -static bool -open_tables_acquire_upgradable_mdl(THD *thd, TABLE_LIST *tables_start, - TABLE_LIST *tables_end, - Open_table_context *ot_ctx, - uint flags) +bool +lock_table_names(THD *thd, + TABLE_LIST *tables_start, TABLE_LIST *tables_end, + ulong lock_wait_timeout, uint flags) { MDL_request_list mdl_requests; TABLE_LIST *table; + MDL_request global_request; + Hash_set schema_set; DBUG_ASSERT(!thd->locked_tables_mode); @@ -4726,30 +4699,37 @@ open_tables_acquire_upgradable_mdl(THD *thd, TABLE_LIST *tables_start, (table->open_type != OT_BASE_ONLY && ! (flags & MYSQL_OPEN_SKIP_TEMPORARY) && find_temporary_table(thd, table)))) + { + if (schema_set.insert(table)) + return TRUE; mdl_requests.push_front(&table->mdl_request); + } } if (! mdl_requests.is_empty()) { - DEBUG_SYNC(thd, "open_tables_acquire_upgradable_mdl"); - - MDL_request *global_request= ot_ctx->get_global_mdl_request(thd); - - if (global_request == NULL) - return TRUE; - mdl_requests.push_front(global_request); + /* + Scoped locks: Take intention exclusive locks on all involved + schemas. + */ + Hash_set::Iterator it(schema_set); + while ((table= it++)) + { + MDL_request *schema_request= new (thd->mem_root) MDL_request; + if (schema_request == NULL) + return TRUE; + schema_request->init(MDL_key::SCHEMA, table->db, "", + MDL_INTENTION_EXCLUSIVE); + mdl_requests.push_front(schema_request); + } + /* Take the global intention exclusive lock. */ + global_request.init(MDL_key::GLOBAL, "", "", MDL_INTENTION_EXCLUSIVE); + mdl_requests.push_front(&global_request); } - if (thd->mdl_context.acquire_locks(&mdl_requests, ot_ctx->get_timeout())) + if (thd->mdl_context.acquire_locks(&mdl_requests, lock_wait_timeout)) return TRUE; - for (table= tables_start; table && table != tables_end; - table= table->next_global) - { - if (table->mdl_request.type >= MDL_SHARED_NO_WRITE) - table->mdl_request.ticket= NULL; - } - return FALSE; } @@ -4921,12 +4901,21 @@ restart: goto err; } } - else if (open_tables_acquire_upgradable_mdl(thd, *start, - thd->lex->first_not_own_table(), - &ot_ctx, flags)) + else { - error= TRUE; - goto err; + TABLE_LIST *table; + if (lock_table_names(thd, *start, thd->lex->first_not_own_table(), + ot_ctx.get_timeout(), flags)) + { + error= TRUE; + goto err; + } + for (table= *start; table && table != thd->lex->first_not_own_table(); + table= table->next_global) + { + if (table->mdl_request.type >= MDL_SHARED_NO_WRITE) + table->mdl_request.ticket= NULL; + } } } diff --git a/sql/sql_base.h b/sql/sql_base.h index 20a068e27d7..67e5601663a 100644 --- a/sql/sql_base.h +++ b/sql/sql_base.h @@ -205,6 +205,9 @@ int setup_ftfuncs(SELECT_LEX* select); int init_ftfuncs(THD *thd, SELECT_LEX* select, bool no_order); void wait_for_condition(THD *thd, mysql_mutex_t *mutex, mysql_cond_t *cond); +bool lock_table_names(THD *thd, TABLE_LIST *table_list, + TABLE_LIST *table_list_end, ulong lock_wait_timeout, + uint flags); bool open_tables(THD *thd, TABLE_LIST **tables, uint *counter, uint flags, Prelocking_strategy *prelocking_strategy); /* open_and_lock_tables with optional derived handling */ @@ -480,8 +483,6 @@ public: return m_start_of_statement_svp; } - MDL_request *get_global_mdl_request(THD *thd); - inline ulong get_timeout() const { return m_timeout; @@ -498,11 +499,6 @@ private: */ TABLE_LIST *m_failed_table; MDL_ticket *m_start_of_statement_svp; - /** - Request object for global intention exclusive lock which is acquired during - opening tables for statements which take upgradable shared metadata locks. - */ - MDL_request *m_global_mdl_request; /** Lock timeout in seconds. Initialized to LONG_TIMEOUT when opening system tables or to the "lock_wait_timeout" system variable for regular tables. diff --git a/sql/sql_db.cc b/sql/sql_db.cc index 5e992d2391c..c4a7dc53972 100644 --- a/sql/sql_db.cc +++ b/sql/sql_db.cc @@ -58,106 +58,6 @@ static void mysql_change_db_impl(THD *thd, CHARSET_INFO *new_db_charset); -/* Database lock hash */ -HASH lock_db_cache; -mysql_mutex_t LOCK_lock_db; -int creating_database= 0; // how many database locks are made - - -/* Structure for database lock */ -typedef struct my_dblock_st -{ - char *name; /* Database name */ - uint name_length; /* Database length name */ -} my_dblock_t; - - -/* - lock_db key. -*/ - -extern "C" uchar* lock_db_get_key(my_dblock_t *, size_t *, my_bool not_used); - -uchar* lock_db_get_key(my_dblock_t *ptr, size_t *length, - my_bool not_used __attribute__((unused))) -{ - *length= ptr->name_length; - return (uchar*) ptr->name; -} - - -/* - Free lock_db hash element. -*/ - -extern "C" void lock_db_free_element(void *ptr); - -void lock_db_free_element(void *ptr) -{ - my_free(ptr, MYF(0)); -} - - -/* - Put a database lock entry into the hash. - - DESCRIPTION - Insert a database lock entry into hash. - LOCK_db_lock must be previously locked. - - RETURN VALUES - 0 on success. - 1 on error. -*/ - -static my_bool lock_db_insert(const char *dbname, uint length) -{ - my_dblock_t *opt; - my_bool error= 0; - DBUG_ENTER("lock_db_insert"); - - mysql_mutex_assert_owner(&LOCK_lock_db); - - if (!(opt= (my_dblock_t*) my_hash_search(&lock_db_cache, - (uchar*) dbname, length))) - { - /* Db is not in the hash, insert it */ - char *tmp_name; - if (!my_multi_malloc(MYF(MY_WME | MY_ZEROFILL), - &opt, (uint) sizeof(*opt), &tmp_name, (uint) length+1, - NullS)) - { - error= 1; - goto end; - } - - opt->name= tmp_name; - strmov(opt->name, dbname); - opt->name_length= length; - - if ((error= my_hash_insert(&lock_db_cache, (uchar*) opt))) - my_free(opt, MYF(0)); - } - -end: - DBUG_RETURN(error); -} - - -/* - Delete a database lock entry from hash. -*/ - -void lock_db_delete(const char *name, uint length) -{ - my_dblock_t *opt; - mysql_mutex_assert_owner(&LOCK_lock_db); - if ((opt= (my_dblock_t *)my_hash_search(&lock_db_cache, - (const uchar*) name, length))) - my_hash_delete(&lock_db_cache, (uchar*) opt); -} - - /* Database options hash */ static HASH dboptions; static my_bool dboptions_init= 0; @@ -233,21 +133,16 @@ static void init_database_names_psi_keys(void) } #endif -/* - Initialize database option hash and locked database hash. +/** + Initialize database option cache. - SYNOPSIS - my_database_names() + @note Must be called before any other database function is called. - NOTES - Must be called before any other database function is called. - - RETURN - 0 ok - 1 Fatal error + @retval 0 ok + @retval 1 Fatal error */ -bool my_database_names_init(void) +bool my_dboptions_cache_init(void) { #ifdef HAVE_PSI_INTERFACE init_database_names_psi_keys(); @@ -261,36 +156,30 @@ bool my_database_names_init(void) error= my_hash_init(&dboptions, lower_case_table_names ? &my_charset_bin : system_charset_info, 32, 0, 0, (my_hash_get_key) dboptions_get_key, - free_dbopt,0) || - my_hash_init(&lock_db_cache, lower_case_table_names ? - &my_charset_bin : system_charset_info, - 32, 0, 0, (my_hash_get_key) lock_db_get_key, - lock_db_free_element,0); - + free_dbopt,0); } return error; } -/* +/** Free database option hash and locked databases hash. */ -void my_database_names_free(void) +void my_dboptions_cache_free(void) { if (dboptions_init) { dboptions_init= 0; my_hash_free(&dboptions); mysql_rwlock_destroy(&LOCK_dboptions); - my_hash_free(&lock_db_cache); } } -/* - Cleanup cached options +/** + Cleanup cached options. */ void my_dbopt_cleanup(void) @@ -395,7 +284,7 @@ end: Deletes database options from the hash. */ -void del_dbopt(const char *path) +static void del_dbopt(const char *path) { my_dbopt_t *opt; mysql_rwlock_wrlock(&LOCK_dboptions); @@ -664,25 +553,8 @@ int mysql_create_db(THD *thd, char *db, HA_CREATE_INFO *create_info, DBUG_RETURN(-1); } - /* - Do not create database if another thread is holding read lock. - Wait for global read lock before acquiring LOCK_mysql_create_db. - After wait_if_global_read_lock() we have protection against another - global read lock. If we would acquire LOCK_mysql_create_db first, - another thread could step in and get the global read lock before we - reach wait_if_global_read_lock(). If this thread tries the same as we - (admin a db), it would then go and wait on LOCK_mysql_create_db... - Furthermore wait_if_global_read_lock() checks if the current thread - has the global read lock and refuses the operation with - ER_CANT_UPDATE_WITH_READLOCK if applicable. - */ - if (thd->global_read_lock.wait_if_global_read_lock(thd, FALSE, TRUE)) - { - error= -1; - goto exit2; - } - - mysql_mutex_lock(&LOCK_mysql_create_db); + if (lock_schema_name(thd, db)) + DBUG_RETURN(-1); /* Check directory */ path_len= build_table_filename(path, sizeof(path) - 1, db, "", "", 0); @@ -786,7 +658,10 @@ not_silent: qinfo.db = db; qinfo.db_len = strlen(db); - /* These DDL methods and logging protected with LOCK_mysql_create_db */ + /* + These DDL methods and logging are protected with the exclusive + metadata lock on the schema + */ if (mysql_bin_log.write(&qinfo)) { error= -1; @@ -797,9 +672,6 @@ not_silent: } exit: - mysql_mutex_unlock(&LOCK_mysql_create_db); - thd->global_read_lock.start_waiting_global_read_lock(thd); -exit2: DBUG_RETURN(error); } @@ -813,22 +685,8 @@ bool mysql_alter_db(THD *thd, const char *db, HA_CREATE_INFO *create_info) int error= 0; DBUG_ENTER("mysql_alter_db"); - /* - Do not alter database if another thread is holding read lock. - Wait for global read lock before acquiring LOCK_mysql_create_db. - After wait_if_global_read_lock() we have protection against another - global read lock. If we would acquire LOCK_mysql_create_db first, - another thread could step in and get the global read lock before we - reach wait_if_global_read_lock(). If this thread tries the same as we - (admin a db), it would then go and wait on LOCK_mysql_create_db... - Furthermore wait_if_global_read_lock() checks if the current thread - has the global read lock and refuses the operation with - ER_CANT_UPDATE_WITH_READLOCK if applicable. - */ - if ((error= thd->global_read_lock.wait_if_global_read_lock(thd, FALSE, TRUE))) - goto exit2; - - mysql_mutex_lock(&LOCK_mysql_create_db); + if (lock_schema_name(thd, db)) + DBUG_RETURN(TRUE); /* Recreate db options file: /dbpath/.db.opt @@ -866,16 +724,16 @@ bool mysql_alter_db(THD *thd, const char *db, HA_CREATE_INFO *create_info) qinfo.db = db; qinfo.db_len = strlen(db); - /* These DDL methods and logging protected with LOCK_mysql_create_db */ + /* + These DDL methods and logging are protected with the exclusive + metadata lock on the schema. + */ if ((error= mysql_bin_log.write(&qinfo))) goto exit; } my_ok(thd, result); exit: - mysql_mutex_unlock(&LOCK_mysql_create_db); - thd->global_read_lock.start_waiting_global_read_lock(thd); -exit2: DBUG_RETURN(error); } @@ -907,25 +765,9 @@ bool mysql_rm_db(THD *thd,char *db,bool if_exists, bool silent) TABLE_LIST* dropped_tables= 0; DBUG_ENTER("mysql_rm_db"); - /* - Do not drop database if another thread is holding read lock. - Wait for global read lock before acquiring LOCK_mysql_create_db. - After wait_if_global_read_lock() we have protection against another - global read lock. If we would acquire LOCK_mysql_create_db first, - another thread could step in and get the global read lock before we - reach wait_if_global_read_lock(). If this thread tries the same as we - (admin a db), it would then go and wait on LOCK_mysql_create_db... - Furthermore wait_if_global_read_lock() checks if the current thread - has the global read lock and refuses the operation with - ER_CANT_UPDATE_WITH_READLOCK if applicable. - */ - if (thd->global_read_lock.wait_if_global_read_lock(thd, FALSE, TRUE)) - { - error= -1; - goto exit2; - } - mysql_mutex_lock(&LOCK_mysql_create_db); + if (lock_schema_name(thd, db)) + DBUG_RETURN(TRUE); length= build_table_filename(path, sizeof(path) - 1, db, "", "", 0); strmov(path+length, MY_DB_OPT_FILE); // Append db option file name @@ -1013,7 +855,10 @@ bool mysql_rm_db(THD *thd,char *db,bool if_exists, bool silent) qinfo.db = db; qinfo.db_len = strlen(db); - /* These DDL methods and logging protected with LOCK_mysql_create_db */ + /* + These DDL methods and logging are protected with the exclusive + metadata lock on the schema. + */ if (mysql_bin_log.write(&qinfo)) { error= -1; @@ -1045,7 +890,10 @@ bool mysql_rm_db(THD *thd,char *db,bool if_exists, bool silent) tbl_name_len= strlen(tbl->table_name) + 3; if (query_pos + tbl_name_len + 1 >= query_end) { - /* These DDL methods and logging protected with LOCK_mysql_create_db */ + /* + These DDL methods and logging are protected with the exclusive + metadata lock on the schema. + */ if (write_to_binlog(thd, query, query_pos -1 - query, db, db_len)) { error= -1; @@ -1062,7 +910,10 @@ bool mysql_rm_db(THD *thd,char *db,bool if_exists, bool silent) if (query_pos != query_data_start) { - /* These DDL methods and logging protected with LOCK_mysql_create_db */ + /* + These DDL methods and logging are protected with the exclusive + metadata lock on the schema. + */ if (write_to_binlog(thd, query, query_pos -1 - query, db, db_len)) { error= -1; @@ -1080,9 +931,6 @@ exit: */ if (thd->db && !strcmp(thd->db, db) && error == 0) mysql_change_db_impl(thd, NULL, 0, thd->variables.collation_server); - mysql_mutex_unlock(&LOCK_mysql_create_db); - thd->global_read_lock.start_waiting_global_read_lock(thd); -exit2: DBUG_RETURN(error); } @@ -1099,12 +947,12 @@ static long mysql_rm_known_files(THD *thd, MY_DIR *dirp, const char *db, long deleted=0; ulong found_other_files=0; char filePath[FN_REFLEN]; - TABLE_LIST *tot_list=0, **tot_list_next; + TABLE_LIST *tot_list=0, **tot_list_next_local, **tot_list_next_global; List raid_dirs; DBUG_ENTER("mysql_rm_known_files"); DBUG_PRINT("enter",("path: %s", org_path)); - tot_list_next= &tot_list; + tot_list_next_local= tot_list_next_global= &tot_list; for (uint idx=0 ; idx < (uint) dirp->number_off_files && !thd->killed ; @@ -1192,23 +1040,28 @@ static long mysql_rm_known_files(THD *thd, MY_DIR *dirp, const char *db, if (!table_list) goto err; table_list->db= (char*) (table_list+1); - table_list->table_name= strmov(table_list->db, db) + 1; - (void) filename_to_tablename(file->name, table_list->table_name, - MYSQL50_TABLE_NAME_PREFIX_LENGTH + - strlen(file->name) + 1); + table_list->db_length= strmov(table_list->db, db) - table_list->db; + table_list->table_name= table_list->db + table_list->db_length + 1; + table_list->table_name_length= filename_to_tablename(file->name, + table_list->table_name, + MYSQL50_TABLE_NAME_PREFIX_LENGTH + + strlen(file->name) + 1); table_list->open_type= OT_BASE_ONLY; /* To be able to correctly look up the table in the table cache. */ if (lower_case_table_names) - my_casedn_str(files_charset_info, table_list->table_name); + table_list->table_name_length= my_casedn_str(files_charset_info, + table_list->table_name); table_list->alias= table_list->table_name; // If lower_case_table_names=2 table_list->internal_tmp_table= is_prefix(file->name, tmp_file_prefix); table_list->mdl_request.init(MDL_key::TABLE, table_list->db, table_list->table_name, MDL_EXCLUSIVE); /* Link into list */ - (*tot_list_next)= table_list; - tot_list_next= &table_list->next_local; + (*tot_list_next_local)= table_list; + (*tot_list_next_global)= table_list; + tot_list_next_local= &table_list->next_local; + tot_list_next_global= &table_list->next_global; deleted++; } else @@ -1771,60 +1624,6 @@ bool mysql_opt_change_db(THD *thd, } -static int -lock_databases(THD *thd, const char *db1, uint length1, - const char *db2, uint length2) -{ - mysql_mutex_lock(&LOCK_lock_db); - while (!thd->killed && - (my_hash_search(&lock_db_cache,(uchar*) db1, length1) || - my_hash_search(&lock_db_cache,(uchar*) db2, length2))) - { - wait_for_condition(thd, &LOCK_lock_db, &COND_refresh); - mysql_mutex_lock(&LOCK_lock_db); - } - - if (thd->killed) - { - mysql_mutex_unlock(&LOCK_lock_db); - return 1; - } - - lock_db_insert(db1, length1); - lock_db_insert(db2, length2); - creating_database++; - - /* - Wait if a concurent thread is creating a table at the same time. - The assumption here is that it will not take too long until - there is a point in time when a table is not created. - */ - - while (!thd->killed && creating_table) - { - wait_for_condition(thd, &LOCK_lock_db, &COND_refresh); - mysql_mutex_lock(&LOCK_lock_db); - } - - if (thd->killed) - { - lock_db_delete(db1, length1); - lock_db_delete(db2, length2); - creating_database--; - mysql_mutex_unlock(&LOCK_lock_db); - mysql_cond_signal(&COND_refresh); - return(1); - } - - /* - We can unlock now as the hash will protect against anyone creating a table - in the databases we are using - */ - mysql_mutex_unlock(&LOCK_lock_db); - return 0; -} - - /** Upgrade a 5.0 database. This function is invoked whenever an ALTER DATABASE UPGRADE query is executed: @@ -1866,9 +1665,9 @@ bool mysql_upgrade_db(THD *thd, LEX_STRING *old_db) new_db.str= old_db->str + MYSQL50_TABLE_NAME_PREFIX_LENGTH; new_db.length= old_db->length - MYSQL50_TABLE_NAME_PREFIX_LENGTH; - if (lock_databases(thd, old_db->str, old_db->length, - new_db.str, new_db.length)) - DBUG_RETURN(1); + /* Lock the old name, the new name will be locked by mysql_create_db().*/ + if (lock_schema_name(thd, old_db->str)) + DBUG_RETURN(-1); /* Let's remember if we should do "USE newdb" afterwards. @@ -2035,15 +1834,6 @@ bool mysql_upgrade_db(THD *thd, LEX_STRING *old_db) error|= mysql_change_db(thd, & new_db, FALSE); exit: - mysql_mutex_lock(&LOCK_lock_db); - /* Remove the databases from db lock cache */ - lock_db_delete(old_db->str, old_db->length); - lock_db_delete(new_db.str, new_db.length); - creating_database--; - /* Signal waiting CREATE TABLE's to continue */ - mysql_cond_signal(&COND_refresh); - mysql_mutex_unlock(&LOCK_lock_db); - DBUG_RETURN(error); } diff --git a/sql/sql_db.h b/sql/sql_db.h index 96b3de80d3a..ecb8deaa397 100644 --- a/sql/sql_db.h +++ b/sql/sql_db.h @@ -35,8 +35,8 @@ bool mysql_opt_change_db(THD *thd, LEX_STRING *saved_db_name, bool force_switch, bool *cur_db_changed); -bool my_database_names_init(void); -void my_database_names_free(void); +bool my_dboptions_cache_init(void); +void my_dboptions_cache_free(void); bool check_db_dir_existence(const char *db_name); bool load_db_opt(THD *thd, const char *path, HA_CREATE_INFO *create); bool load_db_opt_by_name(THD *thd, const char *db_name, @@ -45,9 +45,6 @@ CHARSET_INFO *get_default_db_collation(THD *thd, const char *db_name); bool my_dbopt_init(void); void my_dbopt_cleanup(void); -extern int creating_database; // How many database locks are made -extern HASH lock_db_cache; - #define MY_DB_OPT_FILE "db.opt" #endif /* SQL_DB_INCLUDED */ diff --git a/sql/sql_help.cc b/sql/sql_help.cc index 7bea236269a..4e3df950134 100644 --- a/sql/sql_help.cc +++ b/sql/sql_help.cc @@ -643,23 +643,24 @@ bool mysqld_help(THD *thd, const char *mask) MEM_ROOT *mem_root= thd->mem_root; DBUG_ENTER("mysqld_help"); - bzero((uchar*)tables,sizeof(tables)); - tables[0].alias= tables[0].table_name= (char*) "help_topic"; - tables[0].lock_type= TL_READ; + tables[0].init_one_table(C_STRING_WITH_LEN("mysql"), + C_STRING_WITH_LEN("help_topic"), + "help_topic", TL_READ); + tables[1].init_one_table(C_STRING_WITH_LEN("mysql"), + C_STRING_WITH_LEN("help_category"), + "help_category", TL_READ); + tables[2].init_one_table(C_STRING_WITH_LEN("mysql"), + C_STRING_WITH_LEN("help_relation"), + "help_relation", TL_READ); + tables[3].init_one_table(C_STRING_WITH_LEN("mysql"), + C_STRING_WITH_LEN("help_keyword"), + "help_keyword", TL_READ); tables[0].next_global= tables[0].next_local= tables[0].next_name_resolution_table= &tables[1]; - tables[1].alias= tables[1].table_name= (char*) "help_category"; - tables[1].lock_type= TL_READ; tables[1].next_global= tables[1].next_local= tables[1].next_name_resolution_table= &tables[2]; - tables[2].alias= tables[2].table_name= (char*) "help_relation"; - tables[2].lock_type= TL_READ; tables[2].next_global= tables[2].next_local= tables[2].next_name_resolution_table= &tables[3]; - tables[3].alias= tables[3].table_name= (char*) "help_keyword"; - tables[3].lock_type= TL_READ; - tables[0].db= tables[1].db= tables[2].db= tables[3].db= (char*) "mysql"; - init_mdl_requests(tables); /* HELP must be available under LOCK TABLES. diff --git a/sql/sql_hset.h b/sql/sql_hset.h new file mode 100644 index 00000000000..c3b98b881f5 --- /dev/null +++ b/sql/sql_hset.h @@ -0,0 +1,117 @@ +#ifndef SQL_HSET_INCLUDED +#define SQL_HSET_INCLUDED +/* 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., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA */ + +#include "my_global.h" +#include "hash.h" + + +/** + A type-safe wrapper around mysys HASH. +*/ + +template +class Hash_set +{ +public: + typedef T Value_type; + enum { START_SIZE= 8 }; + /** + Constructs an empty hash. Does not allocate memory, it is done upon + the first insert. Thus does not cause or return errors. + */ + Hash_set(); + /** + Destroy the hash by freeing the buckets table. Does + not call destructors for the elements. + */ + ~Hash_set(); + /** + Insert a single value into a hash. Does not tell whether + the value was inserted -- if an identical value existed, + it is not replaced. + + @retval TRUE Out of memory. + @retval FALSE OK. The value either was inserted or existed + in the hash. + */ + bool insert(T *value); + /** Is this hash set empty? */ + bool is_empty() const { return m_hash.records == 0; } + /** Returns the number of unique elements. */ + size_t size() const { return static_cast(m_hash.records); } + /** An iterator over hash elements. Is not insert-stable. */ + class Iterator + { + public: + Iterator(Hash_set &hash_set); + /** + Return the current element and reposition the iterator to the next + element. + */ + inline T *operator++(int); + void rewind() { m_idx= 0; } + private: + HASH *m_hash; + uint m_idx; + }; +private: + HASH m_hash; +}; + + +template +Hash_set::Hash_set() +{ + my_hash_clear(&m_hash); +} + + +template +Hash_set::~Hash_set() +{ + my_hash_free(&m_hash); +} + + +template +bool Hash_set::insert(T *value) +{ + my_hash_init_opt(&m_hash, &my_charset_bin, START_SIZE, 0, 0, K, 0, MYF(0)); + size_t key_len; + const uchar *key= K(reinterpret_cast(value), &key_len, FALSE); + if (my_hash_search(&m_hash, key, key_len) == NULL) + return my_hash_insert(&m_hash, reinterpret_cast(value)); + return FALSE; +} + + +template +Hash_set::Iterator::Iterator(Hash_set &set_arg) + :m_hash(&set_arg.m_hash), + m_idx(0) +{} + + +template +inline T *Hash_set::Iterator::operator++(int) +{ + if (m_idx < m_hash->records) + return reinterpret_cast(my_hash_element(m_hash, m_idx++)); + return NULL; +} + +#endif // SQL_HSET_INCLUDED diff --git a/sql/sql_parse.cc b/sql/sql_parse.cc index 273eadf4205..31eaf4111ce 100644 --- a/sql/sql_parse.cc +++ b/sql/sql_parse.cc @@ -270,10 +270,10 @@ void init_update_queries(void) sql_command_flags[SQLCOM_LOAD]= CF_CHANGES_DATA | CF_REEXECUTION_FRAGILE | CF_PROTECT_AGAINST_GRL | CF_CAN_GENERATE_ROW_EVENTS; - 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_ALTER_DB]= CF_CHANGES_DATA | CF_AUTO_COMMIT_TRANS; + sql_command_flags[SQLCOM_CREATE_DB]= CF_CHANGES_DATA | CF_AUTO_COMMIT_TRANS | CF_PROTECT_AGAINST_GRL; + sql_command_flags[SQLCOM_DROP_DB]= CF_CHANGES_DATA | CF_AUTO_COMMIT_TRANS | CF_PROTECT_AGAINST_GRL; + sql_command_flags[SQLCOM_ALTER_DB_UPGRADE]= CF_AUTO_COMMIT_TRANS | CF_PROTECT_AGAINST_GRL; + sql_command_flags[SQLCOM_ALTER_DB]= CF_CHANGES_DATA | CF_AUTO_COMMIT_TRANS | CF_PROTECT_AGAINST_GRL; sql_command_flags[SQLCOM_RENAME_TABLE]= CF_CHANGES_DATA | CF_AUTO_COMMIT_TRANS; 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 | @@ -1803,7 +1803,8 @@ static bool flush_tables_with_read_lock(THD *thd, TABLE_LIST *all_tables) current internal MDL asserts, fix after discussing with Dmitry. */ - if (lock_table_names(thd, all_tables)) + if (lock_table_names(thd, all_tables, 0, thd->variables.lock_wait_timeout, + MYSQL_OPEN_SKIP_TEMPORARY)) goto error; for (table_list= all_tables; table_list; @@ -3644,12 +3645,6 @@ end_with_restore_list: #endif if (check_access(thd, CREATE_ACL, lex->name.str, NULL, NULL, 1, 0)) break; - if (thd->locked_tables_mode) - { - my_message(ER_LOCK_OR_ACTIVE_TRANSACTION, - ER(ER_LOCK_OR_ACTIVE_TRANSACTION), MYF(0)); - goto error; - } res= mysql_create_db(thd,(lower_case_table_names == 2 ? alias : lex->name.str), &create_info, 0); break; @@ -3679,12 +3674,6 @@ end_with_restore_list: #endif if (check_access(thd, DROP_ACL, lex->name.str, NULL, NULL, 1, 0)) break; - if (thd->locked_tables_mode) - { - my_message(ER_LOCK_OR_ACTIVE_TRANSACTION, - ER(ER_LOCK_OR_ACTIVE_TRANSACTION), MYF(0)); - goto error; - } res= mysql_rm_db(thd, lex->name.str, lex->drop_if_exists, 0); break; } @@ -3713,14 +3702,6 @@ end_with_restore_list: res= 1; break; } - if (thd->locked_tables_mode) - { - res= 1; - my_message(ER_LOCK_OR_ACTIVE_TRANSACTION, - ER(ER_LOCK_OR_ACTIVE_TRANSACTION), MYF(0)); - goto error; - } - res= mysql_upgrade_db(thd, db); if (!res) my_ok(thd); @@ -3753,12 +3734,6 @@ end_with_restore_list: #endif if (check_access(thd, ALTER_ACL, db->str, NULL, NULL, 1, 0)) break; - if (thd->locked_tables_mode) - { - my_message(ER_LOCK_OR_ACTIVE_TRANSACTION, - ER(ER_LOCK_OR_ACTIVE_TRANSACTION), MYF(0)); - goto error; - } res= mysql_alter_db(thd, db->str, &create_info); break; } diff --git a/sql/sql_rename.cc b/sql/sql_rename.cc index 130a99a374f..301b22bd70e 100644 --- a/sql/sql_rename.cc +++ b/sql/sql_rename.cc @@ -24,10 +24,9 @@ #include "sql_table.h" // build_table_filename #include "sql_view.h" // mysql_frm_type, mysql_rename_view #include "sql_trigger.h" -#include "lock.h" // wait_if_global_read_lock, lock_table_names, - // unlock_table_names, +#include "lock.h" // wait_if_global_read_lock // start_waiting_global_read_lock -#include "sql_base.h" // tdc_remove_table +#include "sql_base.h" // tdc_remove_table, lock_table_names, #include "sql_handler.h" // mysql_ha_rm_tables #include "datadict.h" @@ -144,7 +143,8 @@ bool mysql_rename_tables(THD *thd, TABLE_LIST *table_list, bool silent) } } - if (lock_table_names(thd, table_list)) + if (lock_table_names(thd, table_list, 0, thd->variables.lock_wait_timeout, + MYSQL_OPEN_SKIP_TEMPORARY)) goto err; mysql_mutex_lock(&LOCK_open); @@ -197,7 +197,7 @@ bool mysql_rename_tables(THD *thd, TABLE_LIST *table_list, bool silent) if (!error) query_cache_invalidate3(thd, table_list, 0); - unlock_table_names(thd); + thd->mdl_context.release_transactional_locks(); err: thd->global_read_lock.start_waiting_global_read_lock(thd); diff --git a/sql/sql_table.cc b/sql/sql_table.cc index 97c8f59d7df..74acd134910 100644 --- a/sql/sql_table.cc +++ b/sql/sql_table.cc @@ -22,17 +22,17 @@ #include "sql_rename.h" // do_rename #include "sql_parse.h" // test_if_data_home_dir #include "sql_cache.h" // query_cache_* -#include "sql_base.h" // open_temporary_table -#include "lock.h" // wait_if_global_read_lock, lock_table_names, +#include "sql_base.h" // open_temporary_table, lock_table_names +#include "lock.h" // wait_if_global_read_lock // start_waiting_global_read_lock, - // unlock_table_names, mysql_unlock_tables + // mysql_unlock_tables #include "strfunc.h" // find_type2, find_set #include "sql_view.h" // view_checksum #include "sql_truncate.h" // regenerate_locked_table #include "sql_partition.h" // mem_alloc_error, // generate_partition_syntax, // partition_info -#include "sql_db.h" // load_db_opt_by_name, lock_db_cache, creating_database +#include "sql_db.h" // load_db_opt_by_name #include "sql_time.h" // make_truncated_value_warning #include "records.h" // init_read_record, end_read_record #include "filesort.h" // filesort_free_buffers @@ -58,8 +58,6 @@ #include #endif -int creating_table= 0; // How many mysql_create_table are running - const char *primary_key_name="PRIMARY"; static bool check_if_keyname_exists(const char *name,KEY *start, KEY *end); @@ -1954,7 +1952,8 @@ int mysql_rm_table_part2(THD *thd, TABLE_LIST *tables, bool if_exists, { if (!thd->locked_tables_mode) { - if (lock_table_names(thd, tables)) + if (lock_table_names(thd, tables, NULL, thd->variables.lock_wait_timeout, + MYSQL_OPEN_SKIP_TEMPORARY)) DBUG_RETURN(1); mysql_mutex_lock(&LOCK_open); for (table= tables; table; table= table->next_local) @@ -2296,7 +2295,7 @@ err: leaving LOCK TABLES mode if we have dropped only temporary tables. */ if (! thd->locked_tables_mode) - unlock_table_names(thd); + thd->mdl_context.release_transactional_locks(); else { if (thd->lock && thd->lock->table_count == 0 && non_temp_tables_count > 0) @@ -4226,24 +4225,6 @@ bool mysql_create_table(THD *thd, TABLE_LIST *create_table, bool result; DBUG_ENTER("mysql_create_table"); - /* Wait for any database locks */ - mysql_mutex_lock(&LOCK_lock_db); - while (!thd->killed && - my_hash_search(&lock_db_cache, (uchar*)create_table->db, - create_table->db_length)) - { - wait_for_condition(thd, &LOCK_lock_db, &COND_refresh); - mysql_mutex_lock(&LOCK_lock_db); - } - - if (thd->killed) - { - mysql_mutex_unlock(&LOCK_lock_db); - DBUG_RETURN(TRUE); - } - creating_table++; - mysql_mutex_unlock(&LOCK_lock_db); - /* Open or obtain an exclusive metadata lock on table being created. */ @@ -4282,10 +4263,6 @@ bool mysql_create_table(THD *thd, TABLE_LIST *create_table, } unlock: - mysql_mutex_lock(&LOCK_lock_db); - if (!--creating_table && creating_database) - mysql_cond_signal(&COND_refresh); - mysql_mutex_unlock(&LOCK_lock_db); DBUG_RETURN(result); } @@ -4458,8 +4435,6 @@ static int prepare_for_repair(THD *thd, TABLE_LIST *table_list, { char key[MAX_DBKEY_LENGTH]; uint key_length; - MDL_request mdl_global_request; - MDL_request_list mdl_requests; /* If the table didn't exist, we have a shared metadata lock on it that is left from mysql_admin_table()'s attempt to @@ -4479,12 +4454,9 @@ static int prepare_for_repair(THD *thd, TABLE_LIST *table_list, table_list->db, table_list->table_name, MDL_EXCLUSIVE); - mdl_global_request.init(MDL_key::GLOBAL, "", "", MDL_INTENTION_EXCLUSIVE); - mdl_requests.push_front(&table_list->mdl_request); - mdl_requests.push_front(&mdl_global_request); - - if (thd->mdl_context.acquire_locks(&mdl_requests, - thd->variables.lock_wait_timeout)) + if (lock_table_names(thd, table_list, table_list->next_global, + thd->variables.lock_wait_timeout, + MYSQL_OPEN_SKIP_TEMPORARY)) DBUG_RETURN(0); has_mdl_lock= TRUE; @@ -6577,6 +6549,7 @@ bool mysql_alter_table(THD *thd,char *new_db, char *new_name, Alter_table_prelocking_strategy alter_prelocking_strategy(alter_info); + DEBUG_SYNC(thd, "alter_table_before_open_tables"); error= open_and_lock_tables(thd, table_list, FALSE, 0, &alter_prelocking_strategy); diff --git a/sql/sql_table.h b/sql/sql_table.h index 40b24605bd6..dca4b706605 100644 --- a/sql/sql_table.h +++ b/sql/sql_table.h @@ -210,7 +210,6 @@ uint explain_filename(THD* thd, const char *from, char *to, uint to_length, extern MYSQL_PLUGIN_IMPORT const char *primary_key_name; -extern int creating_table; // How many mysql_create_table() are running extern mysql_mutex_t LOCK_gdl; #endif /* SQL_TABLE_INCLUDED */ diff --git a/sql/sql_truncate.cc b/sql/sql_truncate.cc index 901ab8e987d..6bbf86cbe55 100644 --- a/sql/sql_truncate.cc +++ b/sql/sql_truncate.cc @@ -242,9 +242,10 @@ static bool open_and_lock_table_for_truncate(THD *thd, TABLE_LIST *table_ref, MDL_ticket **ticket_downgrade) { TABLE *table= NULL; - MDL_ticket *mdl_ticket= NULL; DBUG_ENTER("open_and_lock_table_for_truncate"); + DBUG_ASSERT(table_ref->lock_type == TL_WRITE); + DBUG_ASSERT(table_ref->mdl_request.type == MDL_SHARED_NO_READ_WRITE); /* Before doing anything else, acquire a metadata lock on the table, or ensure we have one. We don't use open_and_lock_tables() @@ -266,6 +267,7 @@ static bool open_and_lock_table_for_truncate(THD *thd, TABLE_LIST *table_ref, *hton_can_recreate= ha_check_storage_engine_flag(table->s->db_type(), HTON_CAN_RECREATE); + table_ref->mdl_request.ticket= table->mdl_ticket; } else { @@ -273,21 +275,12 @@ static bool open_and_lock_table_for_truncate(THD *thd, TABLE_LIST *table_ref, Even though we could use the previous execution branch here just as well, we must not try to open the table: */ - MDL_request mdl_global_request, mdl_request; - MDL_request_list mdl_requests; - - mdl_global_request.init(MDL_key::GLOBAL, "", "", MDL_INTENTION_EXCLUSIVE); - mdl_request.init(MDL_key::TABLE, table_ref->db, table_ref->table_name, - MDL_SHARED_NO_READ_WRITE); - mdl_requests.push_front(&mdl_request); - mdl_requests.push_front(&mdl_global_request); - - if (thd->mdl_context.acquire_locks(&mdl_requests, - thd->variables.lock_wait_timeout)) + DBUG_ASSERT(table_ref->next_global == NULL); + if (lock_table_names(thd, table_ref, NULL, + thd->variables.lock_wait_timeout, + MYSQL_OPEN_SKIP_TEMPORARY)) DBUG_RETURN(TRUE); - mdl_ticket= mdl_request.ticket; - if (dd_check_storage_engine_flag(thd, table_ref->db, table_ref->table_name, HTON_CAN_RECREATE, hton_can_recreate)) DBUG_RETURN(TRUE); @@ -313,7 +306,9 @@ static bool open_and_lock_table_for_truncate(THD *thd, TABLE_LIST *table_ref, else { ulong timeout= thd->variables.lock_wait_timeout; - if (thd->mdl_context.upgrade_shared_lock_to_exclusive(mdl_ticket, timeout)) + if (thd->mdl_context. + upgrade_shared_lock_to_exclusive(table_ref->mdl_request.ticket, + timeout)) DBUG_RETURN(TRUE); mysql_mutex_lock(&LOCK_open); tdc_remove_table(thd, TDC_RT_REMOVE_ALL, table_ref->db, @@ -335,15 +330,14 @@ static bool open_and_lock_table_for_truncate(THD *thd, TABLE_LIST *table_ref, table_ref->required_type= FRMTYPE_TABLE; /* We don't need to load triggers. */ DBUG_ASSERT(table_ref->trg_event_map == 0); - /* Work around partition parser rules using alter table's. */ - if (thd->lex->alter_info.flags & ALTER_ADMIN_PARTITION) - { - table_ref->lock_type= TL_WRITE; - table_ref->mdl_request.set_type(MDL_SHARED_WRITE); - } - /* Ensure proper lock types (e.g. from the parser). */ - DBUG_ASSERT(table_ref->lock_type == TL_WRITE); - DBUG_ASSERT(table_ref->mdl_request.type == MDL_SHARED_WRITE); + /* + Even though we have an MDL lock on the table here, we don't + pass MYSQL_OPEN_HAS_MDL_LOCK to open_and_lock_tables + since to truncate a MERGE table, we must open and lock + merge children, and on those we don't have an MDL lock. + Thus clear the ticket to satisfy MDL asserts. + */ + table_ref->mdl_request.ticket= NULL; /* Open the table as it will handle some required preparations. diff --git a/sql/sql_view.cc b/sql/sql_view.cc index 69abe70e863..be13349b5a1 100644 --- a/sql/sql_view.cc +++ b/sql/sql_view.cc @@ -19,10 +19,10 @@ #include "sql_priv.h" #include "unireg.h" #include "sql_view.h" -#include "sql_base.h" // find_table_in_global_list +#include "sql_base.h" // find_table_in_global_list, lock_table_names #include "sql_parse.h" // sql_parse #include "sql_cache.h" // query_cache_* -#include "lock.h" // wait_if_global_read_lock, lock_table_names +#include "lock.h" // wait_if_global_read_lock #include "sql_show.h" // append_identifier #include "sql_table.h" // build_table_filename #include "sql_db.h" // mysql_opt_change_db, mysql_change_db @@ -1652,7 +1652,8 @@ bool mysql_drop_view(THD *thd, TABLE_LIST *views, enum_drop_mode drop_mode) DBUG_RETURN(TRUE); } - if (lock_table_names(thd, views)) + if (lock_table_names(thd, views, 0, thd->variables.lock_wait_timeout, + MYSQL_OPEN_SKIP_TEMPORARY)) DBUG_RETURN(TRUE); mysql_mutex_lock(&LOCK_open); diff --git a/sql/sql_yacc.yy b/sql/sql_yacc.yy index 73935d2a0b1..934ec9c35ab 100644 --- a/sql/sql_yacc.yy +++ b/sql/sql_yacc.yy @@ -6442,6 +6442,8 @@ alter_commands: lex->sql_command= SQLCOM_TRUNCATE; lex->alter_info.flags|= ALTER_ADMIN_PARTITION; lex->check_opt.init(); + lex->query_tables->mdl_request.set_type(MDL_SHARED_NO_READ_WRITE); + lex->query_tables->lock_type= TL_WRITE; } | reorg_partition_rule ; @@ -10695,7 +10697,7 @@ truncate: lex->select_lex.sql_cache= SELECT_LEX::SQL_CACHE_UNSPECIFIED; lex->select_lex.init_order(); YYPS->m_lock_type= TL_WRITE; - YYPS->m_mdl_type= MDL_SHARED_WRITE; + YYPS->m_mdl_type= MDL_SHARED_NO_READ_WRITE; } table_name {} From 10582e2abec2e05589125131bf0150c568a7cc31 Mon Sep 17 00:00:00 2001 From: Dmitry Lenev Date: Thu, 1 Jul 2010 18:58:47 +0400 Subject: [PATCH 051/129] A follow-up for 5.5 version of fix for bug#54360 "Deadlock DROP/ALTER/CREATE DATABASE with open HANDLER". Remove wait_for_condition() which became unused after database locks were replaced with MDL scoped locks. If one needs functionality provided by this call one can always use THD::enter_cond()/exit_cond() methods. Also removed an unused include from sql_db.cc and updated comment describing one of used includes to reflect current situation. --- sql/sql_base.cc | 45 --------------------------------------------- sql/sql_base.h | 2 -- sql/sql_db.cc | 4 +--- 3 files changed, 1 insertion(+), 50 deletions(-) diff --git a/sql/sql_base.cc b/sql/sql_base.cc index 426c9db2717..ea688ad6e0f 100644 --- a/sql/sql_base.cc +++ b/sql/sql_base.cc @@ -2412,51 +2412,6 @@ void drop_open_table(THD *thd, TABLE *table, const char *db_name, } -/* - Wait for condition but allow the user to send a kill to mysqld - - SYNOPSIS - wait_for_condition() - thd Thread handler - mutex mutex that is currently hold that is associated with condition - Will be unlocked on return - cond Condition to wait for -*/ - -void wait_for_condition(THD *thd, mysql_mutex_t *mutex, mysql_cond_t *cond) -{ - /* Wait until the current table is up to date */ - const char *proc_info; - thd->mysys_var->current_mutex= mutex; - thd->mysys_var->current_cond= cond; - proc_info=thd->proc_info; - thd_proc_info(thd, "Waiting for table"); - DBUG_ENTER("wait_for_condition"); - DEBUG_SYNC(thd, "waiting_for_table"); - if (!thd->killed) - mysql_cond_wait(cond, mutex); - - /* - We must unlock mutex first to avoid deadlock becasue conditions are - sent to this thread by doing locks in the following order: - lock(mysys_var->mutex) - lock(mysys_var->current_mutex) - - One by effect of this that one can only use wait_for_condition with - condition variables that are guranteed to not disapper (freed) even if this - mutex is unlocked - */ - - mysql_mutex_unlock(mutex); - mysql_mutex_lock(&thd->mysys_var->mutex); - thd->mysys_var->current_mutex= 0; - thd->mysys_var->current_cond= 0; - thd_proc_info(thd, proc_info); - mysql_mutex_unlock(&thd->mysys_var->mutex); - DBUG_VOID_RETURN; -} - - /** Check that table exists in table definition cache, on disk or in some storage engine. diff --git a/sql/sql_base.h b/sql/sql_base.h index 67e5601663a..24669bd2597 100644 --- a/sql/sql_base.h +++ b/sql/sql_base.h @@ -203,8 +203,6 @@ int setup_conds(THD *thd, TABLE_LIST *tables, TABLE_LIST *leaves, COND **conds); int setup_ftfuncs(SELECT_LEX* select); int init_ftfuncs(THD *thd, SELECT_LEX* select, bool no_order); -void wait_for_condition(THD *thd, mysql_mutex_t *mutex, - mysql_cond_t *cond); bool lock_table_names(THD *thd, TABLE_LIST *table_list, TABLE_LIST *table_list_end, ulong lock_wait_timeout, uint flags); diff --git a/sql/sql_db.cc b/sql/sql_db.cc index c4a7dc53972..fe4b112196c 100644 --- a/sql/sql_db.cc +++ b/sql/sql_db.cc @@ -21,14 +21,12 @@ #include "unireg.h" #include "sql_db.h" #include "sql_cache.h" // query_cache_* -#include "lock.h" // wait_if_global_read_lock, - // start_waiting_global_read_lock +#include "lock.h" // lock_schema_name #include "sql_table.h" // build_table_filename, // filename_to_tablename #include "sql_rename.h" // mysql_rename_tables #include "sql_acl.h" // SELECT_ACL, DB_ACLS, // acl_get, check_grant_db -#include "sql_base.h" // wait_for_condition #include "log_event.h" // Query_log_event #include #include "sp.h" From 6afc935c40220440ef59607bccca3172fbadcd32 Mon Sep 17 00:00:00 2001 From: Dmitry Lenev Date: Thu, 1 Jul 2010 19:48:56 +0400 Subject: [PATCH 052/129] Another follow-up for 5.5 version of fix for bug#54360 "Deadlock DROP/ALTER/CREATE DATABASE with open HANDLER". Fixes production build which was broken by the fix for bug#54360 due to missing instantiation of some Hash_set template's methods. Circumvent requirement of explicit instantiation of non-inline methods by making all Hash_set methods inline. --- sql/sql_hset.h | 74 ++++++++++++++++++-------------------------------- 1 file changed, 27 insertions(+), 47 deletions(-) diff --git a/sql/sql_hset.h b/sql/sql_hset.h index c3b98b881f5..2ea70b91da8 100644 --- a/sql/sql_hset.h +++ b/sql/sql_hset.h @@ -33,12 +33,18 @@ public: Constructs an empty hash. Does not allocate memory, it is done upon the first insert. Thus does not cause or return errors. */ - Hash_set(); + Hash_set() + { + my_hash_clear(&m_hash); + } /** Destroy the hash by freeing the buckets table. Does not call destructors for the elements. */ - ~Hash_set(); + ~Hash_set() + { + my_hash_free(&m_hash); + } /** Insert a single value into a hash. Does not tell whether the value was inserted -- if an identical value existed, @@ -48,7 +54,15 @@ public: @retval FALSE OK. The value either was inserted or existed in the hash. */ - bool insert(T *value); + bool insert(T *value) + { + my_hash_init_opt(&m_hash, &my_charset_bin, START_SIZE, 0, 0, K, 0, MYF(0)); + size_t key_len; + const uchar *key= K(reinterpret_cast(value), &key_len, FALSE); + if (my_hash_search(&m_hash, key, key_len) == NULL) + return my_hash_insert(&m_hash, reinterpret_cast(value)); + return FALSE; + } /** Is this hash set empty? */ bool is_empty() const { return m_hash.records == 0; } /** Returns the number of unique elements. */ @@ -57,12 +71,20 @@ public: class Iterator { public: - Iterator(Hash_set &hash_set); + Iterator(Hash_set &hash_set) + : m_hash(&hash_set.m_hash), + m_idx(0) + {} /** Return the current element and reposition the iterator to the next element. */ - inline T *operator++(int); + inline T *operator++(int) + { + if (m_idx < m_hash->records) + return reinterpret_cast(my_hash_element(m_hash, m_idx++)); + return NULL; + } void rewind() { m_idx= 0; } private: HASH *m_hash; @@ -72,46 +94,4 @@ private: HASH m_hash; }; - -template -Hash_set::Hash_set() -{ - my_hash_clear(&m_hash); -} - - -template -Hash_set::~Hash_set() -{ - my_hash_free(&m_hash); -} - - -template -bool Hash_set::insert(T *value) -{ - my_hash_init_opt(&m_hash, &my_charset_bin, START_SIZE, 0, 0, K, 0, MYF(0)); - size_t key_len; - const uchar *key= K(reinterpret_cast(value), &key_len, FALSE); - if (my_hash_search(&m_hash, key, key_len) == NULL) - return my_hash_insert(&m_hash, reinterpret_cast(value)); - return FALSE; -} - - -template -Hash_set::Iterator::Iterator(Hash_set &set_arg) - :m_hash(&set_arg.m_hash), - m_idx(0) -{} - - -template -inline T *Hash_set::Iterator::operator++(int) -{ - if (m_idx < m_hash->records) - return reinterpret_cast(my_hash_element(m_hash, m_idx++)); - return NULL; -} - #endif // SQL_HSET_INCLUDED From 3ffa8b3b90b551ea558ebf9323f1b34376605188 Mon Sep 17 00:00:00 2001 From: Jon Olav Hauglid Date: Fri, 2 Jul 2010 11:26:27 +0200 Subject: [PATCH 053/129] Followup to Bug #54360 Deadlock DROP/ALTER/CREATE DATABASE with open HANDLER Fixes problem which caused mdl_sync.test to fail on Solaris and Windows due to path name differences in error messages in the result file. --- mysql-test/r/mdl_sync.result | 6 +++--- mysql-test/t/mdl_sync.test | 6 +++--- 2 files changed, 6 insertions(+), 6 deletions(-) diff --git a/mysql-test/r/mdl_sync.result b/mysql-test/r/mdl_sync.result index 1b0ffc588e1..0fd408b0208 100644 --- a/mysql-test/r/mdl_sync.result +++ b/mysql-test/r/mdl_sync.result @@ -2649,7 +2649,7 @@ SET DEBUG_SYNC= 'now SIGNAL blocked'; # Reaping: DROP DATABASE db1 # Connection con2 # Reaping: ALTER DATABASE db1 DEFAULT CHARACTER SET utf8 -ERROR HY000: Can't create/write to file './db1/db.opt' (Errcode: 2) +Got one of the listed errors # Test 5: # Locked database name prevents CREATE of tables in that database. # Tests X vs IX lock. @@ -2690,7 +2690,7 @@ SET DEBUG_SYNC= 'now SIGNAL blocked'; # Reaping: DROP DATABASE db1 # Connection con2 # Reaping: RENAME TABLE db1.t1 TO test.t1 -ERROR HY000: Can't find file: './db1/t1.frm' (errno: 2) +Got one of the listed errors # Connection default CREATE DATABASE db1; CREATE TABLE test.t2 (a INT); @@ -2707,7 +2707,7 @@ SET DEBUG_SYNC= 'now SIGNAL blocked'; # Reaping: DROP DATABASE db1 # Connection con2 # Reaping: RENAME TABLE test.t2 TO db1.t2 -ERROR HY000: Error on rename of './test/t2.MYI' to './db1/t2.MYI' (Errcode: 2) +Got one of the listed errors DROP TABLE test.t2; # Test 7: # Locked database name prevents DROP of tables in that database. diff --git a/mysql-test/t/mdl_sync.test b/mysql-test/t/mdl_sync.test index 441cabb10e2..6b721ace07f 100644 --- a/mysql-test/t/mdl_sync.test +++ b/mysql-test/t/mdl_sync.test @@ -3947,7 +3947,7 @@ connection default; --echo # Connection con2 connection con2; --echo # Reaping: ALTER DATABASE db1 DEFAULT CHARACTER SET utf8 ---error 1 # Wrong error pending followup patch for bug#54360 +--error 1,1 # Wrong error pending followup patch for bug#54360 --reap @@ -4023,7 +4023,7 @@ connection default; --echo # Connection con2 connection con2; --echo # Reaping: RENAME TABLE db1.t1 TO test.t1 ---error ER_FILE_NOT_FOUND +--error ER_FILE_NOT_FOUND, ER_FILE_NOT_FOUND --reap --echo # Connection default @@ -4056,7 +4056,7 @@ connection default; --echo # Connection con2 connection con2; --echo # Reaping: RENAME TABLE test.t2 TO db1.t2 ---error 7 # Wrong error pending followup patch for bug#54360 +--error 7, 7 # Wrong error pending followup patch for bug#54360 --reap DROP TABLE test.t2; From 8e154c93ab1df7a488fea44dee67bab66c107599 Mon Sep 17 00:00:00 2001 From: Jon Olav Hauglid Date: Fri, 2 Jul 2010 11:54:14 +0200 Subject: [PATCH 054/129] Followup for Bug #54360 Deadlock DROP/ALTER/CREATE DATABASE with open HANDLER Fixes a problem with schema.test visible using embedded server. The HANDLER was not closed which caused the test to hang. The problem was not visible if the test was run on a normal server as the the handler there was implicitly closed by DATABASE DDL statements doing Events::drop_schema_events(). --- mysql-test/r/schema.result | 1 + mysql-test/t/schema.test | 1 + 2 files changed, 2 insertions(+) diff --git a/mysql-test/r/schema.result b/mysql-test/r/schema.result index 890f53669b5..853c3bcf575 100644 --- a/mysql-test/r/schema.result +++ b/mysql-test/r/schema.result @@ -66,6 +66,7 @@ DROP DATABASE db1; CREATE DATABASE db2; ALTER DATABASE db2 DEFAULT CHARACTER SET utf8; DROP DATABASE db2; +HANDLER t1 CLOSE; # Connection default # Reaping: DROP DATABASE db1 # diff --git a/mysql-test/t/schema.test b/mysql-test/t/schema.test index e3592f39780..ed3b98ec2f7 100644 --- a/mysql-test/t/schema.test +++ b/mysql-test/t/schema.test @@ -133,6 +133,7 @@ connection con1; CREATE DATABASE db2; ALTER DATABASE db2 DEFAULT CHARACTER SET utf8; DROP DATABASE db2; +HANDLER t1 CLOSE; --echo # Connection default connection default; From 1afe6ff03aea2be84b3d060d78a091a040c93496 Mon Sep 17 00:00:00 2001 From: Konstantin Osipov Date: Fri, 2 Jul 2010 19:21:07 +0400 Subject: [PATCH 055/129] A test case for Bug#50788 "main.merge fails on HPUX", and a backport of relevant changes from the 6.0 version of the fix done by Ingo Struewing. The bug itself was fixed by the patch for Bug#54811. MyISAMMRG engine would try to use MMAP on its children even on platforms that don't support it and even if myisam_use_mmap option was off. This lead to an infinite hang in INSERT ... SELECT into a MyISAMMRG table when the destination MyISAM table was also selected from. A bug in duplicate detection fixed by 54811 was essential to the hang - when a duplicate is detected, the optimizer disables the use of memory mapped files, and it wasn't the case. The patch below is also to not turn on MMAP on children tables if myisam_use_mmap is off. A test case is added to cover MyISAMMRG and myisam_use_mmap option. mysql-test/r/merge_mmap.result: Result file - Bug#50788. mysql-test/t/merge_mmap-master.opt: An option file for the test for Bug#50788 -- use mmap. mysql-test/t/merge_mmap.test: Try INSERT ... SELECT into a merge table when myisam_use_mmap is on (Bug#50788). storage/myisam/mi_statrec.c: Fixed misinterpretation of the return value of my_b_read(). storage/myisammrg/ha_myisammrg.cc: Skip HA_EXTRA_MMAP if MyISAM memory mapping is disabled. --- mysql-test/r/merge_mmap.result | 64 ++++++++++++++++++++++++++++++ mysql-test/t/merge_mmap-master.opt | 1 + mysql-test/t/merge_mmap.test | 60 ++++++++++++++++++++++++++++ storage/myisam/mi_statrec.c | 13 +++++- storage/myisammrg/ha_myisammrg.cc | 2 + 5 files changed, 138 insertions(+), 2 deletions(-) create mode 100644 mysql-test/r/merge_mmap.result create mode 100644 mysql-test/t/merge_mmap-master.opt create mode 100644 mysql-test/t/merge_mmap.test diff --git a/mysql-test/r/merge_mmap.result b/mysql-test/r/merge_mmap.result new file mode 100644 index 00000000000..d975a1be377 --- /dev/null +++ b/mysql-test/r/merge_mmap.result @@ -0,0 +1,64 @@ +SET GLOBAL storage_engine = MyISAM; +SET SESSION storage_engine = MyISAM; +DROP TABLE IF EXISTS t1, t2, m1, m2; +CREATE TABLE t1 (c1 INT); +CREATE TABLE t2 (c1 INT); +CREATE TABLE m1 (c1 INT) ENGINE=MRG_MyISAM UNION=(t1,t2) +INSERT_METHOD=LAST; +CREATE TABLE m2 (c1 INT) ENGINE=MRG_MyISAM UNION=(t1,t2) +INSERT_METHOD=LAST; +INSERT INTO t1 VALUES (1); +INSERT INTO t2 VALUES (2), (3), (4); +INSERT INTO m2 SELECT * FROM m1; +SELECT * FROM m2; +c1 +1 +2 +3 +4 +1 +2 +3 +4 +SELECT * FROM t2; +c1 +2 +3 +4 +1 +2 +3 +4 +DROP TABLE m2, m1, t2, t1; +CREATE TABLE t1 (c1 INT); +CREATE TABLE t2 (c1 INT); +CREATE TABLE m1 (c1 INT) ENGINE=MRG_MyISAM UNION=(t1,t2) +INSERT_METHOD=LAST; +CREATE TABLE m2 (c1 INT) ENGINE=MRG_MyISAM UNION=(t1,t2) +INSERT_METHOD=LAST; +LOCK TABLE m1 WRITE, m2 WRITE; +INSERT INTO t1 VALUES (1); +INSERT INTO t2 VALUES (2), (3), (4); +INSERT INTO m2 SELECT * FROM m1; +SELECT * FROM m2; +c1 +1 +2 +3 +4 +1 +2 +3 +4 +SELECT * FROM t2; +c1 +2 +3 +4 +1 +2 +3 +4 +UNLOCK TABLES; +DROP TABLE m2, m1, t2, t1; +End of 6.0 tests diff --git a/mysql-test/t/merge_mmap-master.opt b/mysql-test/t/merge_mmap-master.opt new file mode 100644 index 00000000000..9606fb57187 --- /dev/null +++ b/mysql-test/t/merge_mmap-master.opt @@ -0,0 +1 @@ +--myisam-use-mmap diff --git a/mysql-test/t/merge_mmap.test b/mysql-test/t/merge_mmap.test new file mode 100644 index 00000000000..3468702ca45 --- /dev/null +++ b/mysql-test/t/merge_mmap.test @@ -0,0 +1,60 @@ +# +# Test of MERGE TABLES with MyISAM memory mapping enabled (--myisam-use-mmap) +# + +# MERGE tables require MyISAM tables +--let $default=`SELECT @@global.storage_engine` +SET GLOBAL storage_engine = MyISAM; +SET SESSION storage_engine = MyISAM; + +# Clean up resources used in this test case. +--disable_warnings +DROP TABLE IF EXISTS t1, t2, m1, m2; +--enable_warnings + +#################### +## No locked tables. +#################### +# +# INSERT-SELECT with no TEMPORARY table. +# +CREATE TABLE t1 (c1 INT); +CREATE TABLE t2 (c1 INT); +CREATE TABLE m1 (c1 INT) ENGINE=MRG_MyISAM UNION=(t1,t2) + INSERT_METHOD=LAST; +CREATE TABLE m2 (c1 INT) ENGINE=MRG_MyISAM UNION=(t1,t2) + INSERT_METHOD=LAST; +INSERT INTO t1 VALUES (1); +INSERT INTO t2 VALUES (2), (3), (4); +INSERT INTO m2 SELECT * FROM m1; +SELECT * FROM m2; +SELECT * FROM t2; +DROP TABLE m2, m1, t2, t1; + +#################### +## With LOCK TABLES. +#################### +# +# INSERT-SELECT with no TEMPORARY table. +# +CREATE TABLE t1 (c1 INT); +CREATE TABLE t2 (c1 INT); +CREATE TABLE m1 (c1 INT) ENGINE=MRG_MyISAM UNION=(t1,t2) + INSERT_METHOD=LAST; +CREATE TABLE m2 (c1 INT) ENGINE=MRG_MyISAM UNION=(t1,t2) + INSERT_METHOD=LAST; +LOCK TABLE m1 WRITE, m2 WRITE; +INSERT INTO t1 VALUES (1); +INSERT INTO t2 VALUES (2), (3), (4); +INSERT INTO m2 SELECT * FROM m1; +SELECT * FROM m2; +SELECT * FROM t2; +UNLOCK TABLES; +DROP TABLE m2, m1, t2, t1; +--echo End of 6.0 tests + +--disable_result_log +--disable_query_log +eval SET GLOBAL storage_engine = $default; +--enable_result_log +--enable_query_log diff --git a/storage/myisam/mi_statrec.c b/storage/myisam/mi_statrec.c index 7d595916d78..f83afa3c886 100644 --- a/storage/myisam/mi_statrec.c +++ b/storage/myisam/mi_statrec.c @@ -298,8 +298,17 @@ int _mi_read_rnd_static_record(MI_INFO *info, uchar *buf, info->update|= HA_STATE_AKTIV | HA_STATE_KEY_CHANGED; DBUG_RETURN(0); } - /* my_errno should be set if rec_cache.error == -1 */ + /* error is TRUE. my_errno should be set if rec_cache.error == -1 */ if (info->rec_cache.error != -1 || my_errno == 0) - my_errno=HA_ERR_WRONG_IN_RECORD; + { + /* + If we could not get a full record, we either have a broken record, + or are at end of file. + */ + if (info->rec_cache.error == 0) + my_errno= HA_ERR_END_OF_FILE; + else + my_errno= HA_ERR_WRONG_IN_RECORD; + } DBUG_RETURN(my_errno); /* Something wrong (EOF?) */ } diff --git a/storage/myisammrg/ha_myisammrg.cc b/storage/myisammrg/ha_myisammrg.cc index 67b81225b13..1681f062117 100644 --- a/storage/myisammrg/ha_myisammrg.cc +++ b/storage/myisammrg/ha_myisammrg.cc @@ -1322,6 +1322,8 @@ int ha_myisammrg::extra(enum ha_extra_function operation) if (operation == HA_EXTRA_FORCE_REOPEN || operation == HA_EXTRA_PREPARE_FOR_DROP) return 0; + if (operation == HA_EXTRA_MMAP && !opt_myisam_use_mmap) + return 0; return myrg_extra(file,operation,0); } From 05617af0251b91d886f7b9305643ee05251dd93c Mon Sep 17 00:00:00 2001 From: Konstantin Osipov Date: Fri, 2 Jul 2010 20:07:57 +0400 Subject: [PATCH 056/129] A fix and a test case for Bug#36171 "CREATE TEMPORARY TABLE and MERGE engine". Backport the patch from 6.0 by Ingo Struewing: revid:ingo.struewing@sun.com-20091028183659-6kmv1k3gdq6cpg4d Bug#36171 - CREATE TEMPORARY TABLE and MERGE engine In former MySQL versions, up to 5.1.23/6.0.4 it was possible to create temporary MERGE tables with non-temporary MyISAM tables. This has been changed in the mentioned version due to Bug 19627 (temporary merge table locking). MERGE children were locked through the parent table. If the parent was temporary, it was not locked and so the children were not locked either. Parallel use of the MyISAM tables corrupted them. Since 6.0.6 (WL 4144 - Lock MERGE engine children), the children are locked independently from the parent. Now it is possible to allow non-temporary children with a temporary parent. Even though the temporary MERGE table itself is not locked, each non-temporary MyISAM table is locked anyway. NOTE: Behavior change: In 5.1.23/6.0.4 we prohibited non-temporary children with a temporary MERGE table. Now we re-allow it. An important side-effect is that temporary tables, which overlay non-temporary MERGE children, overlay the children in the MERGE table. mysql-test/r/merge.result: Update results (Bug#36171). mysql-test/r/merge_mmap.result: Update results (Bug#36171). mysql-test/t/merge.test: Add tests for Bug#36171 mysql-test/t/merge_mmap.test: Add tests for Bug#36171. storage/myisammrg/ha_myisammrg.cc: Changed constraint for temporary state of tables. --- mysql-test/r/merge.result | 738 +++++++++++++++++++++++++++++- mysql-test/r/merge_mmap.result | 126 +++++ mysql-test/t/merge.test | 335 +++++++++++++- mysql-test/t/merge_mmap.test | 91 ++++ storage/myisammrg/ha_myisammrg.cc | 23 +- 5 files changed, 1291 insertions(+), 22 deletions(-) diff --git a/mysql-test/r/merge.result b/mysql-test/r/merge.result index 43f456a6d95..f7f0cea3b19 100644 --- a/mysql-test/r/merge.result +++ b/mysql-test/r/merge.result @@ -1,3 +1,5 @@ +set global storage_engine=myisam; +set session storage_engine=myisam; drop table if exists t1,t2,t3,t4,t5,t6; drop database if exists mysqltest; create table t1 (a int not null primary key auto_increment, message char(20)); @@ -584,7 +586,9 @@ INSERT INTO t1 VALUES (1); INSERT INTO t2 VALUES (2); CREATE TEMPORARY TABLE t3 (c1 INT NOT NULL) ENGINE=MRG_MYISAM UNION=(t1,t2); SELECT * FROM t3; -ERROR HY000: Unable to open underlying table which is differently defined or of non-MyISAM type or doesn't exist +c1 +1 +2 CREATE TEMPORARY TABLE t4 (c1 INT NOT NULL); CREATE TEMPORARY TABLE t5 (c1 INT NOT NULL); INSERT INTO t4 VALUES (4); @@ -613,7 +617,9 @@ ERROR HY000: Unable to open underlying table which is differently defined or of drop table t3; create temporary table t3 (a int not null) ENGINE=MERGE UNION=(t1,t2); select * from t3; -ERROR HY000: Unable to open underlying table which is differently defined or of non-MyISAM type or doesn't exist +a +1 +2 drop table t3, t2, t1; # CREATE...SELECT is not implemented for MERGE tables. CREATE TEMPORARY TABLE t1 (c1 INT NOT NULL); @@ -1196,12 +1202,13 @@ ERROR HY000: Table 't4' was not locked with LOCK TABLES # it can even be used. CREATE TEMPORARY TABLE t4 LIKE t3; SHOW CREATE TABLE t4; -ERROR HY000: Unable to open underlying table which is differently defined or of non-MyISAM type or doesn't exist +Table Create Table +t4 CREATE TEMPORARY TABLE `t4` ( + `c1` int(11) DEFAULT NULL +) ENGINE=MRG_MyISAM DEFAULT CHARSET=latin1 INSERT_METHOD=LAST UNION=(`t1`,`t2`) INSERT INTO t4 VALUES (4); -ERROR HY000: Unable to open underlying table which is differently defined or of non-MyISAM type or doesn't exist UNLOCK TABLES; INSERT INTO t4 VALUES (4); -ERROR HY000: Unable to open underlying table which is differently defined or of non-MyISAM type or doesn't exist DROP TABLE t4; # # Rename child. @@ -1229,6 +1236,8 @@ c1 2 3 4 +4 +4 RENAME TABLE t2 TO t5; SELECT * FROM t3 ORDER BY c1; ERROR HY000: Unable to open underlying table which is differently defined or of non-MyISAM type or doesn't exist @@ -1239,6 +1248,8 @@ c1 2 3 4 +4 +4 # # 3. Normal rename with locked tables. LOCK TABLES t1 WRITE, t2 WRITE, t3 WRITE; @@ -1248,6 +1259,8 @@ c1 2 3 4 +4 +4 RENAME TABLE t2 TO t5; ERROR HY000: Can't execute the given command because you have active locked tables or an active transaction SELECT * FROM t3 ORDER BY c1; @@ -1256,6 +1269,8 @@ c1 2 3 4 +4 +4 RENAME TABLE t5 TO t2; ERROR HY000: Can't execute the given command because you have active locked tables or an active transaction SELECT * FROM t3 ORDER BY c1; @@ -1264,6 +1279,8 @@ c1 2 3 4 +4 +4 UNLOCK TABLES; # # 4. Alter table rename. @@ -1277,6 +1294,8 @@ c1 2 3 4 +4 +4 # # 5. Alter table rename with locked tables. LOCK TABLES t1 WRITE, t2 WRITE, t3 WRITE; @@ -1293,6 +1312,8 @@ c1 2 3 4 +4 +4 # # Rename parent. # @@ -1304,6 +1325,8 @@ c1 2 3 4 +4 +4 RENAME TABLE t3 TO t5; ERROR HY000: Can't execute the given command because you have active locked tables or an active transaction SELECT * FROM t3 ORDER BY c1; @@ -1312,6 +1335,8 @@ c1 2 3 4 +4 +4 RENAME TABLE t5 TO t3; ERROR HY000: Can't execute the given command because you have active locked tables or an active transaction SELECT * FROM t3 ORDER BY c1; @@ -1320,6 +1345,8 @@ c1 2 3 4 +4 +4 # # 5. Alter table rename with locked tables. ALTER TABLE t3 RENAME TO t5; @@ -1335,6 +1362,8 @@ c1 2 3 4 +4 +4 DROP TABLE t1, t2, t3; # # Drop locked tables. @@ -2650,6 +2679,705 @@ test.t1 optimize Error Unable to open underlying table which is differently defi test.t1 optimize note The storage engine for the table doesn't support optimize DROP TABLE t1; # +# Bug#36171 - CREATE TEMPORARY TABLE and MERGE engine +# More tests with TEMPORARY MERGE table and permanent children. +# First without locked tables. +# +DROP TABLE IF EXISTS t1, t2, t3, t4, m1, m2; +# +CREATE TABLE t1 (c1 INT, c2 INT) ENGINE=MyISAM; +CREATE TABLE t2 (c1 INT, c2 INT) ENGINE=MyISAM; +CREATE TEMPORARY TABLE m1 (c1 INT, c2 INT) ENGINE=MRG_MyISAM UNION=(t1,t2) +INSERT_METHOD=LAST; +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `c1` int(11) DEFAULT NULL, + `c2` int(11) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +SHOW CREATE TABLE m1; +Table Create Table +m1 CREATE TEMPORARY TABLE `m1` ( + `c1` int(11) DEFAULT NULL, + `c2` int(11) DEFAULT NULL +) ENGINE=MRG_MyISAM DEFAULT CHARSET=latin1 INSERT_METHOD=LAST UNION=(`t1`,`t2`) +SELECT * FROM m1; +c1 c2 +INSERT INTO t1 VALUES (111, 121); +INSERT INTO m1 VALUES (211, 221); +SELECT * FROM m1; +c1 c2 +111 121 +211 221 +SELECT * FROM t1; +c1 c2 +111 121 +SELECT * FROM t2; +c1 c2 +211 221 +# +ALTER TABLE m1 RENAME m2; +SHOW CREATE TABLE m2; +Table Create Table +m2 CREATE TEMPORARY TABLE `m2` ( + `c1` int(11) DEFAULT NULL, + `c2` int(11) DEFAULT NULL +) ENGINE=MRG_MyISAM DEFAULT CHARSET=latin1 INSERT_METHOD=LAST UNION=(`t1`,`t2`) +SELECT * FROM m2; +c1 c2 +111 121 +211 221 +# +CREATE TEMPORARY TABLE m1 (c1 INT, c2 INT) ENGINE=MRG_MyISAM UNION=(t1,t2) +INSERT_METHOD=LAST; +ALTER TABLE m2 RENAME m1; +ERROR 42S01: Table 'm1' already exists +DROP TABLE m1; +ALTER TABLE m2 RENAME m1; +SHOW CREATE TABLE m1; +Table Create Table +m1 CREATE TEMPORARY TABLE `m1` ( + `c1` int(11) DEFAULT NULL, + `c2` int(11) DEFAULT NULL +) ENGINE=MRG_MyISAM DEFAULT CHARSET=latin1 INSERT_METHOD=LAST UNION=(`t1`,`t2`) +SELECT * FROM m1; +c1 c2 +111 121 +211 221 +# +ALTER TABLE m1 ADD COLUMN c3 INT; +INSERT INTO m1 VALUES (212, 222, 232); +ERROR HY000: Unable to open underlying table which is differently defined or of non-MyISAM type or doesn't exist +SELECT * FROM m1; +ERROR HY000: Unable to open underlying table which is differently defined or of non-MyISAM type or doesn't exist +ALTER TABLE t1 ADD COLUMN c3 INT; +ALTER TABLE t2 ADD COLUMN c3 INT; +INSERT INTO m1 VALUES (212, 222, 232); +SELECT * FROM m1; +c1 c2 c3 +111 121 NULL +211 221 NULL +212 222 232 +# +ALTER TABLE m1 DROP COLUMN c3; +INSERT INTO m1 VALUES (213, 223); +ERROR HY000: Unable to open underlying table which is differently defined or of non-MyISAM type or doesn't exist +SELECT * FROM m1; +ERROR HY000: Unable to open underlying table which is differently defined or of non-MyISAM type or doesn't exist +ALTER TABLE t1 DROP COLUMN c3; +ALTER TABLE t2 DROP COLUMN c3; +INSERT INTO m1 VALUES (213, 223); +SELECT * FROM m1; +c1 c2 +111 121 +211 221 +212 222 +213 223 +# +CREATE TABLE t3 (c1 INT, c2 INT) ENGINE=MyISAM; +ALTER TABLE m1 UNION=(t1,t2,t3); +INSERT INTO m1 VALUES (311, 321); +SELECT * FROM m1; +c1 c2 +111 121 +211 221 +212 222 +213 223 +311 321 +SELECT * FROM t1; +c1 c2 +111 121 +SELECT * FROM t2; +c1 c2 +211 221 +212 222 +213 223 +SELECT * FROM t3; +c1 c2 +311 321 +# +CREATE TEMPORARY TABLE t4 (c1 INT, c2 INT) ENGINE=MyISAM; +ALTER TABLE m1 UNION=(t1,t2,t3,t4); +INSERT INTO m1 VALUES (411, 421); +SELECT * FROM m1; +c1 c2 +111 121 +211 221 +212 222 +213 223 +311 321 +411 421 +SELECT * FROM t1; +c1 c2 +111 121 +SELECT * FROM t2; +c1 c2 +211 221 +212 222 +213 223 +SELECT * FROM t3; +c1 c2 +311 321 +SELECT * FROM t4; +c1 c2 +411 421 +# +ALTER TABLE m1 ENGINE=MyISAM; +SHOW CREATE TABLE m1; +Table Create Table +m1 CREATE TEMPORARY TABLE `m1` ( + `c1` int(11) DEFAULT NULL, + `c2` int(11) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +INSERT INTO m1 VALUES (511, 521); +SELECT * FROM m1; +c1 c2 +111 121 +211 221 +212 222 +213 223 +311 321 +411 421 +511 521 +# +ALTER TABLE m1 ENGINE=MRG_MyISAM UNION=(t1,t2) +INSERT_METHOD=LAST; +SELECT * FROM m1; +c1 c2 +111 121 +211 221 +212 222 +213 223 +SELECT * FROM t1; +c1 c2 +111 121 +SELECT * FROM t2; +c1 c2 +211 221 +212 222 +213 223 +# +CREATE TEMPORARY TABLE t1 (c1 INT, c2 INT) ENGINE=MyISAM; +INSERT INTO t1 VALUES (611, 621); +SELECT * FROM m1; +c1 c2 +611 621 +211 221 +212 222 +213 223 +DROP TABLE t1; +SELECT * FROM m1; +c1 c2 +111 121 +211 221 +212 222 +213 223 +# +# +SHOW CREATE TABLE m1; +Table Create Table +m1 CREATE TEMPORARY TABLE `m1` ( + `c1` int(11) DEFAULT NULL, + `c2` int(11) DEFAULT NULL +) ENGINE=MRG_MyISAM DEFAULT CHARSET=latin1 INSERT_METHOD=LAST UNION=(`t1`,`t2`) +# +CREATE TABLE m2 SELECT * FROM m1; +SHOW CREATE TABLE m2; +Table Create Table +m2 CREATE TABLE `m2` ( + `c1` int(11) DEFAULT NULL, + `c2` int(11) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +SELECT * FROM m2; +c1 c2 +111 121 +211 221 +212 222 +213 223 +DROP TABLE m2; +# +CREATE TEMPORARY TABLE m2 SELECT * FROM m1; +SHOW CREATE TABLE m2; +Table Create Table +m2 CREATE TEMPORARY TABLE `m2` ( + `c1` int(11) DEFAULT NULL, + `c2` int(11) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +SELECT * FROM m2; +c1 c2 +111 121 +211 221 +212 222 +213 223 +DROP TABLE m2; +# +CREATE TABLE m2 (c1 INT, c2 INT) ENGINE=MRG_MyISAM UNION=(t3,t4) +INSERT_METHOD=LAST; +SELECT * FROM m2; +ERROR HY000: Unable to open underlying table which is differently defined or of non-MyISAM type or doesn't exist +DROP TABLE m2; +# +CREATE TABLE m2 (c1 INT, c2 INT) ENGINE=MRG_MyISAM UNION=(t3,t4) +INSERT_METHOD=LAST SELECT * FROM m1; +ERROR HY000: 'test.m2' is not BASE TABLE +# +CREATE TEMPORARY TABLE m2 (c1 INT, c2 INT) ENGINE=MRG_MyISAM UNION=(t3,t4) +INSERT_METHOD=LAST SELECT * FROM m1; +ERROR HY000: 'test.m2' is not BASE TABLE +# +CREATE TABLE m2 LIKE m1; +SHOW CREATE TABLE m2; +Table Create Table +m2 CREATE TABLE `m2` ( + `c1` int(11) DEFAULT NULL, + `c2` int(11) DEFAULT NULL +) ENGINE=MRG_MyISAM DEFAULT CHARSET=latin1 INSERT_METHOD=LAST UNION=(`t1`,`t2`) +SELECT * FROM m2; +c1 c2 +111 121 +211 221 +212 222 +213 223 +INSERT INTO m2 SELECT * FROM m1; +SELECT * FROM m2; +c1 c2 +111 121 +211 221 +212 222 +213 223 +111 121 +211 221 +212 222 +213 223 +DROP TABLE m2; +# +CREATE TEMPORARY TABLE m2 LIKE m1; +SHOW CREATE TABLE m2; +Table Create Table +m2 CREATE TEMPORARY TABLE `m2` ( + `c1` int(11) DEFAULT NULL, + `c2` int(11) DEFAULT NULL +) ENGINE=MRG_MyISAM DEFAULT CHARSET=latin1 INSERT_METHOD=LAST UNION=(`t1`,`t2`) +SELECT * FROM m2; +c1 c2 +111 121 +211 221 +212 222 +213 223 +111 121 +211 221 +212 222 +213 223 +INSERT INTO m2 SELECT * FROM m1; +SELECT * FROM m2; +c1 c2 +111 121 +211 221 +212 222 +213 223 +111 121 +211 221 +212 222 +213 223 +111 121 +211 221 +212 222 +213 223 +111 121 +211 221 +212 222 +213 223 +DROP TABLE m2; +# +CREATE TEMPORARY TABLE m2 (c1 INT, c2 INT) ENGINE=MRG_MyISAM UNION=(t3,t4) +INSERT_METHOD=LAST; +INSERT INTO m2 SELECT * FROM m1; +SELECT * FROM m2; +c1 c2 +311 321 +411 421 +111 121 +211 221 +212 222 +213 223 +111 121 +211 221 +212 222 +213 223 +111 121 +211 221 +212 222 +213 223 +111 121 +211 221 +212 222 +213 223 +# +# +LOCK TABLE m1 WRITE, m2 WRITE; +SELECT * FROM m1,m2 WHERE m1.c1=m2.c1; +c1 c2 c1 c2 +111 121 111 121 +111 121 111 121 +111 121 111 121 +111 121 111 121 +211 221 211 221 +211 221 211 221 +211 221 211 221 +211 221 211 221 +212 222 212 222 +212 222 212 222 +212 222 212 222 +212 222 212 222 +213 223 213 223 +213 223 213 223 +213 223 213 223 +213 223 213 223 +111 121 111 121 +111 121 111 121 +111 121 111 121 +111 121 111 121 +211 221 211 221 +211 221 211 221 +211 221 211 221 +211 221 211 221 +212 222 212 222 +212 222 212 222 +212 222 212 222 +212 222 212 222 +213 223 213 223 +213 223 213 223 +213 223 213 223 +213 223 213 223 +111 121 111 121 +111 121 111 121 +111 121 111 121 +111 121 111 121 +211 221 211 221 +211 221 211 221 +211 221 211 221 +211 221 211 221 +212 222 212 222 +212 222 212 222 +212 222 212 222 +212 222 212 222 +213 223 213 223 +213 223 213 223 +213 223 213 223 +213 223 213 223 +111 121 111 121 +111 121 111 121 +111 121 111 121 +111 121 111 121 +211 221 211 221 +211 221 211 221 +211 221 211 221 +211 221 211 221 +212 222 212 222 +212 222 212 222 +212 222 212 222 +212 222 212 222 +213 223 213 223 +213 223 213 223 +213 223 213 223 +213 223 213 223 +UNLOCK TABLES; +DROP TABLE t1, t2, t3, t4, m1, m2; +# +# Bug#36171 - CREATE TEMPORARY TABLE and MERGE engine +# More tests with TEMPORARY MERGE table and permanent children. +# (continued) Now the same with locked table. +# +CREATE TABLE t1 (c1 INT, c2 INT) ENGINE=MyISAM; +CREATE TABLE t2 (c1 INT, c2 INT) ENGINE=MyISAM; +CREATE TEMPORARY TABLE m1 (c1 INT, c2 INT) ENGINE=MRG_MyISAM UNION=(t1,t2) +INSERT_METHOD=LAST; +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `c1` int(11) DEFAULT NULL, + `c2` int(11) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +SHOW CREATE TABLE m1; +Table Create Table +m1 CREATE TEMPORARY TABLE `m1` ( + `c1` int(11) DEFAULT NULL, + `c2` int(11) DEFAULT NULL +) ENGINE=MRG_MyISAM DEFAULT CHARSET=latin1 INSERT_METHOD=LAST UNION=(`t1`,`t2`) +SELECT * FROM m1; +c1 c2 +INSERT INTO t1 VALUES (111, 121); +INSERT INTO m1 VALUES (211, 221); +SELECT * FROM m1; +c1 c2 +111 121 +211 221 +SELECT * FROM t1; +c1 c2 +111 121 +SELECT * FROM t2; +c1 c2 +211 221 +# +LOCK TABLE m1 WRITE, t1 WRITE, t2 WRITE; +# +ALTER TABLE m1 RENAME m2; +SHOW CREATE TABLE m2; +Table Create Table +m2 CREATE TEMPORARY TABLE `m2` ( + `c1` int(11) DEFAULT NULL, + `c2` int(11) DEFAULT NULL +) ENGINE=MRG_MyISAM DEFAULT CHARSET=latin1 INSERT_METHOD=LAST UNION=(`t1`,`t2`) +SELECT * FROM m2; +c1 c2 +111 121 +211 221 +# +CREATE TEMPORARY TABLE m1 (c1 INT, c2 INT) ENGINE=MRG_MyISAM UNION=(t1,t2) +INSERT_METHOD=LAST; +ALTER TABLE m2 RENAME m1; +ERROR 42S01: Table 'm1' already exists +DROP TABLE m1; +ALTER TABLE m2 RENAME m1; +SHOW CREATE TABLE m1; +Table Create Table +m1 CREATE TEMPORARY TABLE `m1` ( + `c1` int(11) DEFAULT NULL, + `c2` int(11) DEFAULT NULL +) ENGINE=MRG_MyISAM DEFAULT CHARSET=latin1 INSERT_METHOD=LAST UNION=(`t1`,`t2`) +SELECT * FROM m1; +c1 c2 +111 121 +211 221 +# +ALTER TABLE m1 ADD COLUMN c3 INT; +INSERT INTO m1 VALUES (212, 222, 232); +ERROR HY000: Unable to open underlying table which is differently defined or of non-MyISAM type or doesn't exist +SELECT * FROM m1; +ERROR HY000: Unable to open underlying table which is differently defined or of non-MyISAM type or doesn't exist +ALTER TABLE t1 ADD COLUMN c3 INT; +ALTER TABLE t2 ADD COLUMN c3 INT; +INSERT INTO m1 VALUES (212, 222, 232); +SELECT * FROM m1; +c1 c2 c3 +111 121 NULL +211 221 NULL +212 222 232 +# +ALTER TABLE m1 DROP COLUMN c3; +INSERT INTO m1 VALUES (213, 223); +ERROR HY000: Unable to open underlying table which is differently defined or of non-MyISAM type or doesn't exist +SELECT * FROM m1; +ERROR HY000: Unable to open underlying table which is differently defined or of non-MyISAM type or doesn't exist +ALTER TABLE t1 DROP COLUMN c3; +ALTER TABLE t2 DROP COLUMN c3; +INSERT INTO m1 VALUES (213, 223); +SELECT * FROM m1; +c1 c2 +111 121 +211 221 +212 222 +213 223 +# +UNLOCK TABLES; +CREATE TABLE t3 (c1 INT, c2 INT) ENGINE=MyISAM; +ALTER TABLE m1 UNION=(t1,t2,t3); +LOCK TABLE m1 WRITE; +INSERT INTO m1 VALUES (311, 321); +SELECT * FROM m1; +c1 c2 +111 121 +211 221 +212 222 +213 223 +311 321 +SELECT * FROM t1; +c1 c2 +111 121 +SELECT * FROM t2; +c1 c2 +211 221 +212 222 +213 223 +SELECT * FROM t3; +c1 c2 +311 321 +# +CREATE TEMPORARY TABLE t4 (c1 INT, c2 INT) ENGINE=MyISAM; +ALTER TABLE m1 UNION=(t1,t2,t3,t4); +INSERT INTO m1 VALUES (411, 421); +SELECT * FROM m1; +c1 c2 +111 121 +211 221 +212 222 +213 223 +311 321 +411 421 +SELECT * FROM t1; +c1 c2 +111 121 +SELECT * FROM t2; +c1 c2 +211 221 +212 222 +213 223 +SELECT * FROM t3; +c1 c2 +311 321 +SELECT * FROM t4; +c1 c2 +411 421 +# +ALTER TABLE m1 ENGINE=MyISAM; +SHOW CREATE TABLE m1; +Table Create Table +m1 CREATE TEMPORARY TABLE `m1` ( + `c1` int(11) DEFAULT NULL, + `c2` int(11) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +INSERT INTO m1 VALUES (511, 521); +SELECT * FROM m1; +c1 c2 +111 121 +211 221 +212 222 +213 223 +311 321 +411 421 +511 521 +# +ALTER TABLE m1 ENGINE=MRG_MyISAM UNION=(t1,t2) +INSERT_METHOD=LAST; +SELECT * FROM m1; +c1 c2 +111 121 +211 221 +212 222 +213 223 +SELECT * FROM t1; +c1 c2 +111 121 +SELECT * FROM t2; +c1 c2 +211 221 +212 222 +213 223 +# +CREATE TEMPORARY TABLE t1 (c1 INT, c2 INT) ENGINE=MyISAM; +INSERT INTO t1 VALUES (611, 621); +SELECT * FROM m1; +c1 c2 +611 621 +211 221 +212 222 +213 223 +DROP TABLE t1; +SELECT * FROM m1; +c1 c2 +111 121 +211 221 +212 222 +213 223 +# +# +SHOW CREATE TABLE m1; +Table Create Table +m1 CREATE TEMPORARY TABLE `m1` ( + `c1` int(11) DEFAULT NULL, + `c2` int(11) DEFAULT NULL +) ENGINE=MRG_MyISAM DEFAULT CHARSET=latin1 INSERT_METHOD=LAST UNION=(`t1`,`t2`) +CREATE TABLE m2 SELECT * FROM m1; +ERROR HY000: Table 'm2' was not locked with LOCK TABLES +# +CREATE TEMPORARY TABLE m2 SELECT * FROM m1; +SHOW CREATE TABLE m2; +Table Create Table +m2 CREATE TEMPORARY TABLE `m2` ( + `c1` int(11) DEFAULT NULL, + `c2` int(11) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +SELECT * FROM m2; +c1 c2 +111 121 +211 221 +212 222 +213 223 +DROP TABLE m2; +# +CREATE TEMPORARY TABLE m2 (c1 INT, c2 INT) ENGINE=MRG_MyISAM UNION=(t3,t4) +INSERT_METHOD=LAST; +SELECT * FROM m2; +c1 c2 +311 321 +411 421 +LOCK TABLE m1 WRITE, m2 WRITE; +UNLOCK TABLES; +DROP TABLE m2; +LOCK TABLE m1 WRITE; +# +# ER_TABLE_NOT_LOCKED is returned in ps-protocol +CREATE TABLE m2 (c1 INT, c2 INT) ENGINE=MRG_MyISAM UNION=(t3,t4) +INSERT_METHOD=LAST SELECT * FROM m1; +Got one of the listed errors +# +CREATE TEMPORARY TABLE m2 (c1 INT, c2 INT) ENGINE=MRG_MyISAM UNION=(t3,t4) +INSERT_METHOD=LAST SELECT * FROM m1; +ERROR HY000: 'test.m2' is not BASE TABLE +# +CREATE TEMPORARY TABLE m2 LIKE m1; +SHOW CREATE TABLE m2; +Table Create Table +m2 CREATE TEMPORARY TABLE `m2` ( + `c1` int(11) DEFAULT NULL, + `c2` int(11) DEFAULT NULL +) ENGINE=MRG_MyISAM DEFAULT CHARSET=latin1 INSERT_METHOD=LAST UNION=(`t1`,`t2`) +LOCK TABLE m1 WRITE, m2 WRITE; +SHOW CREATE TABLE m2; +Table Create Table +m2 CREATE TEMPORARY TABLE `m2` ( + `c1` int(11) DEFAULT NULL, + `c2` int(11) DEFAULT NULL +) ENGINE=MRG_MyISAM DEFAULT CHARSET=latin1 INSERT_METHOD=LAST UNION=(`t1`,`t2`) +SELECT * FROM m2; +c1 c2 +111 121 +211 221 +212 222 +213 223 +INSERT INTO m2 SELECT * FROM m1; +SELECT * FROM m2; +c1 c2 +111 121 +211 221 +212 222 +213 223 +111 121 +211 221 +212 222 +213 223 +DROP TABLE m2; +# +CREATE TEMPORARY TABLE m2 (c1 INT, c2 INT) ENGINE=MRG_MyISAM UNION=(t3,t4) +INSERT_METHOD=LAST; +LOCK TABLE m1 WRITE, m2 WRITE; +INSERT INTO m2 SELECT * FROM m1; +SELECT * FROM m2; +c1 c2 +311 321 +411 421 +111 121 +211 221 +212 222 +213 223 +111 121 +211 221 +212 222 +213 223 +# +UNLOCK TABLES; +DROP TABLE t1, t2, t3, t4, m1, m2; +# # Bug47098 assert in MDL_context::destroy on HANDLER # OPEN # diff --git a/mysql-test/r/merge_mmap.result b/mysql-test/r/merge_mmap.result index d975a1be377..e8014259a4a 100644 --- a/mysql-test/r/merge_mmap.result +++ b/mysql-test/r/merge_mmap.result @@ -32,6 +32,66 @@ c1 DROP TABLE m2, m1, t2, t1; CREATE TABLE t1 (c1 INT); CREATE TABLE t2 (c1 INT); +CREATE TEMPORARY TABLE m1 (c1 INT) ENGINE=MRG_MyISAM UNION=(t1,t2) +INSERT_METHOD=LAST; +CREATE TABLE m2 (c1 INT) ENGINE=MRG_MyISAM UNION=(t1,t2) +INSERT_METHOD=LAST; +INSERT INTO t1 VALUES (1); +INSERT INTO t2 VALUES (2), (3), (4); +INSERT INTO m2 SELECT * FROM m1; +SELECT * FROM m2; +c1 +1 +2 +3 +4 +1 +2 +3 +4 +DROP TABLE m2, m1, t2, t1; +CREATE TABLE t1 (c1 INT); +CREATE TABLE t2 (c1 INT); +CREATE TABLE m1 (c1 INT) ENGINE=MRG_MyISAM UNION=(t1,t2) +INSERT_METHOD=LAST; +CREATE TEMPORARY TABLE m2 (c1 INT) ENGINE=MRG_MyISAM UNION=(t1,t2) +INSERT_METHOD=LAST; +INSERT INTO t1 VALUES (1); +INSERT INTO t2 VALUES (2), (3), (4); +INSERT INTO m2 SELECT * FROM m1; +SELECT * FROM m2; +c1 +1 +2 +3 +4 +1 +2 +3 +4 +DROP TABLE m2, m1, t2, t1; +CREATE TABLE t1 (c1 INT); +CREATE TABLE t2 (c1 INT); +CREATE TEMPORARY TABLE m1 (c1 INT) ENGINE=MRG_MyISAM UNION=(t1,t2) +INSERT_METHOD=LAST; +CREATE TEMPORARY TABLE m2 (c1 INT) ENGINE=MRG_MyISAM UNION=(t1,t2) +INSERT_METHOD=LAST; +INSERT INTO t1 VALUES (1); +INSERT INTO t2 VALUES (2), (3), (4); +INSERT INTO m2 SELECT * FROM m1; +SELECT * FROM m2; +c1 +1 +2 +3 +4 +1 +2 +3 +4 +DROP TABLE m2, m1, t2, t1; +CREATE TABLE t1 (c1 INT); +CREATE TABLE t2 (c1 INT); CREATE TABLE m1 (c1 INT) ENGINE=MRG_MyISAM UNION=(t1,t2) INSERT_METHOD=LAST; CREATE TABLE m2 (c1 INT) ENGINE=MRG_MyISAM UNION=(t1,t2) @@ -61,4 +121,70 @@ c1 4 UNLOCK TABLES; DROP TABLE m2, m1, t2, t1; +CREATE TABLE t1 (c1 INT); +CREATE TABLE t2 (c1 INT); +CREATE TEMPORARY TABLE m1 (c1 INT) ENGINE=MRG_MyISAM UNION=(t1,t2) +INSERT_METHOD=LAST; +CREATE TABLE m2 (c1 INT) ENGINE=MRG_MyISAM UNION=(t1,t2) +INSERT_METHOD=LAST; +LOCK TABLE m1 WRITE, m2 WRITE; +INSERT INTO t1 VALUES (1); +INSERT INTO t2 VALUES (2), (3), (4); +INSERT INTO m2 SELECT * FROM m1; +SELECT * FROM m2; +c1 +1 +2 +3 +4 +1 +2 +3 +4 +UNLOCK TABLES; +DROP TABLE m2, m1, t2, t1; +CREATE TABLE t1 (c1 INT); +CREATE TABLE t2 (c1 INT); +CREATE TABLE m1 (c1 INT) ENGINE=MRG_MyISAM UNION=(t1,t2) +INSERT_METHOD=LAST; +CREATE TEMPORARY TABLE m2 (c1 INT) ENGINE=MRG_MyISAM UNION=(t1,t2) +INSERT_METHOD=LAST; +LOCK TABLE m1 WRITE, m2 WRITE; +INSERT INTO t1 VALUES (1); +INSERT INTO t2 VALUES (2), (3), (4); +INSERT INTO m2 SELECT * FROM m1; +SELECT * FROM m2; +c1 +1 +2 +3 +4 +1 +2 +3 +4 +UNLOCK TABLES; +DROP TABLE m2, m1, t2, t1; +CREATE TABLE t1 (c1 INT); +CREATE TABLE t2 (c1 INT); +CREATE TEMPORARY TABLE m1 (c1 INT) ENGINE=MRG_MyISAM UNION=(t1,t2) +INSERT_METHOD=LAST; +CREATE TEMPORARY TABLE m2 (c1 INT) ENGINE=MRG_MyISAM UNION=(t1,t2) +INSERT_METHOD=LAST; +LOCK TABLE m1 WRITE, m2 WRITE; +INSERT INTO t1 VALUES (1); +INSERT INTO t2 VALUES (2), (3), (4); +INSERT INTO m2 SELECT * FROM m1; +SELECT * FROM m2; +c1 +1 +2 +3 +4 +1 +2 +3 +4 +UNLOCK TABLES; +DROP TABLE m2, m1, t2, t1; End of 6.0 tests diff --git a/mysql-test/t/merge.test b/mysql-test/t/merge.test index 252495cc1be..31bc8a5e881 100644 --- a/mysql-test/t/merge.test +++ b/mysql-test/t/merge.test @@ -2,6 +2,12 @@ # Test of MERGE TABLES # +# MERGE tables require MyISAM tables +let $default=`select @@global.storage_engine`; +set global storage_engine=myisam; +set session storage_engine=myisam; + +# Clean up resources used in this test case. --disable_warnings drop table if exists t1,t2,t3,t4,t5,t6; drop database if exists mysqltest; @@ -222,7 +228,6 @@ CREATE TABLE t2 (c1 INT NOT NULL); INSERT INTO t1 VALUES (1); INSERT INTO t2 VALUES (2); CREATE TEMPORARY TABLE t3 (c1 INT NOT NULL) ENGINE=MRG_MYISAM UNION=(t1,t2); ---error ER_WRONG_MRG_TABLE SELECT * FROM t3; CREATE TEMPORARY TABLE t4 (c1 INT NOT NULL); CREATE TEMPORARY TABLE t5 (c1 INT NOT NULL); @@ -254,7 +259,6 @@ create table t3 (a int not null) ENGINE=MERGE UNION=(t1,t2); select * from t3; drop table t3; create temporary table t3 (a int not null) ENGINE=MERGE UNION=(t1,t2); ---error ER_WRONG_MRG_TABLE select * from t3; drop table t3, t2, t1; --echo # CREATE...SELECT is not implemented for MERGE tables. @@ -891,12 +895,9 @@ INSERT INTO t4 VALUES (4); --echo # If the temporary MERGE table uses the locked children only, --echo # it can even be used. CREATE TEMPORARY TABLE t4 LIKE t3; ---error ER_WRONG_MRG_TABLE SHOW CREATE TABLE t4; ---error ER_WRONG_MRG_TABLE INSERT INTO t4 VALUES (4); UNLOCK TABLES; ---error ER_WRONG_MRG_TABLE INSERT INTO t4 VALUES (4); DROP TABLE t4; # @@ -2116,6 +2117,325 @@ ALTER TABLE t1 ENGINE=MERGE UNION(t_not_exists,t1); OPTIMIZE TABLE t1; DROP TABLE t1; +--echo # +--echo # Bug#36171 - CREATE TEMPORARY TABLE and MERGE engine +--echo # More tests with TEMPORARY MERGE table and permanent children. +--echo # First without locked tables. +--echo # +--disable_warnings +DROP TABLE IF EXISTS t1, t2, t3, t4, m1, m2; +--enable_warnings +# +--echo # +CREATE TABLE t1 (c1 INT, c2 INT) ENGINE=MyISAM; +CREATE TABLE t2 (c1 INT, c2 INT) ENGINE=MyISAM; +CREATE TEMPORARY TABLE m1 (c1 INT, c2 INT) ENGINE=MRG_MyISAM UNION=(t1,t2) + INSERT_METHOD=LAST; +SHOW CREATE TABLE t1; +SHOW CREATE TABLE m1; +SELECT * FROM m1; +INSERT INTO t1 VALUES (111, 121); +INSERT INTO m1 VALUES (211, 221); +SELECT * FROM m1; +SELECT * FROM t1; +SELECT * FROM t2; +# +--echo # +ALTER TABLE m1 RENAME m2; +SHOW CREATE TABLE m2; +SELECT * FROM m2; +# +--echo # +CREATE TEMPORARY TABLE m1 (c1 INT, c2 INT) ENGINE=MRG_MyISAM UNION=(t1,t2) + INSERT_METHOD=LAST; +--error ER_TABLE_EXISTS_ERROR +ALTER TABLE m2 RENAME m1; +DROP TABLE m1; +ALTER TABLE m2 RENAME m1; +SHOW CREATE TABLE m1; +SELECT * FROM m1; +# +--echo # +ALTER TABLE m1 ADD COLUMN c3 INT; +--error ER_WRONG_MRG_TABLE +INSERT INTO m1 VALUES (212, 222, 232); +--error ER_WRONG_MRG_TABLE +SELECT * FROM m1; +ALTER TABLE t1 ADD COLUMN c3 INT; +ALTER TABLE t2 ADD COLUMN c3 INT; +INSERT INTO m1 VALUES (212, 222, 232); +SELECT * FROM m1; +# +--echo # +ALTER TABLE m1 DROP COLUMN c3; +--error ER_WRONG_MRG_TABLE +INSERT INTO m1 VALUES (213, 223); +--error ER_WRONG_MRG_TABLE +SELECT * FROM m1; +ALTER TABLE t1 DROP COLUMN c3; +ALTER TABLE t2 DROP COLUMN c3; +INSERT INTO m1 VALUES (213, 223); +SELECT * FROM m1; +# +--echo # +CREATE TABLE t3 (c1 INT, c2 INT) ENGINE=MyISAM; +ALTER TABLE m1 UNION=(t1,t2,t3); +INSERT INTO m1 VALUES (311, 321); +SELECT * FROM m1; +SELECT * FROM t1; +SELECT * FROM t2; +SELECT * FROM t3; +# +--echo # +CREATE TEMPORARY TABLE t4 (c1 INT, c2 INT) ENGINE=MyISAM; +ALTER TABLE m1 UNION=(t1,t2,t3,t4); +INSERT INTO m1 VALUES (411, 421); +SELECT * FROM m1; +SELECT * FROM t1; +SELECT * FROM t2; +SELECT * FROM t3; +SELECT * FROM t4; +# +--echo # +ALTER TABLE m1 ENGINE=MyISAM; +SHOW CREATE TABLE m1; +INSERT INTO m1 VALUES (511, 521); +SELECT * FROM m1; +# +--echo # +ALTER TABLE m1 ENGINE=MRG_MyISAM UNION=(t1,t2) + INSERT_METHOD=LAST; +SELECT * FROM m1; +SELECT * FROM t1; +SELECT * FROM t2; +# +--echo # +CREATE TEMPORARY TABLE t1 (c1 INT, c2 INT) ENGINE=MyISAM; +INSERT INTO t1 VALUES (611, 621); +SELECT * FROM m1; +DROP TABLE t1; +SELECT * FROM m1; +# +# +--echo # +--echo # +SHOW CREATE TABLE m1; +# +--echo # +CREATE TABLE m2 SELECT * FROM m1; +SHOW CREATE TABLE m2; +SELECT * FROM m2; +DROP TABLE m2; +# +--echo # +CREATE TEMPORARY TABLE m2 SELECT * FROM m1; +SHOW CREATE TABLE m2; +SELECT * FROM m2; +DROP TABLE m2; +# +--echo # +CREATE TABLE m2 (c1 INT, c2 INT) ENGINE=MRG_MyISAM UNION=(t3,t4) + INSERT_METHOD=LAST; +--error ER_WRONG_MRG_TABLE +SELECT * FROM m2; +DROP TABLE m2; +# +--echo # +--error ER_WRONG_OBJECT +CREATE TABLE m2 (c1 INT, c2 INT) ENGINE=MRG_MyISAM UNION=(t3,t4) + INSERT_METHOD=LAST SELECT * FROM m1; +# +--echo # +--error ER_WRONG_OBJECT +CREATE TEMPORARY TABLE m2 (c1 INT, c2 INT) ENGINE=MRG_MyISAM UNION=(t3,t4) + INSERT_METHOD=LAST SELECT * FROM m1; +# +--echo # +CREATE TABLE m2 LIKE m1; +SHOW CREATE TABLE m2; +SELECT * FROM m2; +INSERT INTO m2 SELECT * FROM m1; +SELECT * FROM m2; +DROP TABLE m2; +# +--echo # +CREATE TEMPORARY TABLE m2 LIKE m1; +SHOW CREATE TABLE m2; +SELECT * FROM m2; +INSERT INTO m2 SELECT * FROM m1; +SELECT * FROM m2; +DROP TABLE m2; +# +--echo # +CREATE TEMPORARY TABLE m2 (c1 INT, c2 INT) ENGINE=MRG_MyISAM UNION=(t3,t4) + INSERT_METHOD=LAST; +INSERT INTO m2 SELECT * FROM m1; +SELECT * FROM m2; +# +# +--echo # +--echo # +LOCK TABLE m1 WRITE, m2 WRITE; +SELECT * FROM m1,m2 WHERE m1.c1=m2.c1; +UNLOCK TABLES; +# +DROP TABLE t1, t2, t3, t4, m1, m2; +# +# +# +--echo # +--echo # Bug#36171 - CREATE TEMPORARY TABLE and MERGE engine +--echo # More tests with TEMPORARY MERGE table and permanent children. +--echo # (continued) Now the same with locked table. +--echo # +CREATE TABLE t1 (c1 INT, c2 INT) ENGINE=MyISAM; +CREATE TABLE t2 (c1 INT, c2 INT) ENGINE=MyISAM; +CREATE TEMPORARY TABLE m1 (c1 INT, c2 INT) ENGINE=MRG_MyISAM UNION=(t1,t2) + INSERT_METHOD=LAST; +SHOW CREATE TABLE t1; +SHOW CREATE TABLE m1; +SELECT * FROM m1; +INSERT INTO t1 VALUES (111, 121); +INSERT INTO m1 VALUES (211, 221); +SELECT * FROM m1; +SELECT * FROM t1; +SELECT * FROM t2; +# +--echo # +LOCK TABLE m1 WRITE, t1 WRITE, t2 WRITE; +# +--echo # +ALTER TABLE m1 RENAME m2; +SHOW CREATE TABLE m2; +SELECT * FROM m2; +# +--echo # +CREATE TEMPORARY TABLE m1 (c1 INT, c2 INT) ENGINE=MRG_MyISAM UNION=(t1,t2) + INSERT_METHOD=LAST; +--error ER_TABLE_EXISTS_ERROR +ALTER TABLE m2 RENAME m1; +DROP TABLE m1; +ALTER TABLE m2 RENAME m1; +SHOW CREATE TABLE m1; +SELECT * FROM m1; +# +--echo # +ALTER TABLE m1 ADD COLUMN c3 INT; +--error ER_WRONG_MRG_TABLE +INSERT INTO m1 VALUES (212, 222, 232); +--error ER_WRONG_MRG_TABLE +SELECT * FROM m1; +ALTER TABLE t1 ADD COLUMN c3 INT; +ALTER TABLE t2 ADD COLUMN c3 INT; +INSERT INTO m1 VALUES (212, 222, 232); +SELECT * FROM m1; +# +--echo # +ALTER TABLE m1 DROP COLUMN c3; +--error ER_WRONG_MRG_TABLE +INSERT INTO m1 VALUES (213, 223); +--error ER_WRONG_MRG_TABLE +SELECT * FROM m1; +ALTER TABLE t1 DROP COLUMN c3; +ALTER TABLE t2 DROP COLUMN c3; +INSERT INTO m1 VALUES (213, 223); +SELECT * FROM m1; +# +--echo # +UNLOCK TABLES; +CREATE TABLE t3 (c1 INT, c2 INT) ENGINE=MyISAM; +ALTER TABLE m1 UNION=(t1,t2,t3); +LOCK TABLE m1 WRITE; +INSERT INTO m1 VALUES (311, 321); +SELECT * FROM m1; +SELECT * FROM t1; +SELECT * FROM t2; +SELECT * FROM t3; +# +--echo # +CREATE TEMPORARY TABLE t4 (c1 INT, c2 INT) ENGINE=MyISAM; +ALTER TABLE m1 UNION=(t1,t2,t3,t4); +INSERT INTO m1 VALUES (411, 421); +SELECT * FROM m1; +SELECT * FROM t1; +SELECT * FROM t2; +SELECT * FROM t3; +SELECT * FROM t4; +# +--echo # +ALTER TABLE m1 ENGINE=MyISAM; +SHOW CREATE TABLE m1; +INSERT INTO m1 VALUES (511, 521); +SELECT * FROM m1; +# +--echo # +ALTER TABLE m1 ENGINE=MRG_MyISAM UNION=(t1,t2) + INSERT_METHOD=LAST; +SELECT * FROM m1; +SELECT * FROM t1; +SELECT * FROM t2; +# +--echo # +CREATE TEMPORARY TABLE t1 (c1 INT, c2 INT) ENGINE=MyISAM; +INSERT INTO t1 VALUES (611, 621); +SELECT * FROM m1; +DROP TABLE t1; +SELECT * FROM m1; +# +# +--echo # +--echo # +SHOW CREATE TABLE m1; +--error ER_TABLE_NOT_LOCKED +CREATE TABLE m2 SELECT * FROM m1; +# +--echo # +CREATE TEMPORARY TABLE m2 SELECT * FROM m1; +SHOW CREATE TABLE m2; +SELECT * FROM m2; +DROP TABLE m2; +# +--echo # +CREATE TEMPORARY TABLE m2 (c1 INT, c2 INT) ENGINE=MRG_MyISAM UNION=(t3,t4) + INSERT_METHOD=LAST; +SELECT * FROM m2; +LOCK TABLE m1 WRITE, m2 WRITE; +UNLOCK TABLES; +DROP TABLE m2; +LOCK TABLE m1 WRITE; +# +--echo # +--echo # ER_TABLE_NOT_LOCKED is returned in ps-protocol +--error ER_WRONG_OBJECT, ER_TABLE_NOT_LOCKED +CREATE TABLE m2 (c1 INT, c2 INT) ENGINE=MRG_MyISAM UNION=(t3,t4) + INSERT_METHOD=LAST SELECT * FROM m1; +# +--echo # +--error ER_WRONG_OBJECT +CREATE TEMPORARY TABLE m2 (c1 INT, c2 INT) ENGINE=MRG_MyISAM UNION=(t3,t4) + INSERT_METHOD=LAST SELECT * FROM m1; +# +--echo # +CREATE TEMPORARY TABLE m2 LIKE m1; +SHOW CREATE TABLE m2; +LOCK TABLE m1 WRITE, m2 WRITE; +SHOW CREATE TABLE m2; +SELECT * FROM m2; +INSERT INTO m2 SELECT * FROM m1; +SELECT * FROM m2; +DROP TABLE m2; +# +--echo # +CREATE TEMPORARY TABLE m2 (c1 INT, c2 INT) ENGINE=MRG_MyISAM UNION=(t3,t4) + INSERT_METHOD=LAST; +LOCK TABLE m1 WRITE, m2 WRITE; +INSERT INTO m2 SELECT * FROM m1; +SELECT * FROM m2; +# +--echo # +UNLOCK TABLES; +DROP TABLE t1, t2, t3, t4, m1, m2; + --echo # --echo # Bug47098 assert in MDL_context::destroy on HANDLER --echo # OPEN @@ -2347,3 +2667,8 @@ drop table t1, t2, t3, m1, m2; --echo End of 6.0 tests +--disable_result_log +--disable_query_log +eval set global storage_engine=$default; +--enable_result_log +--enable_query_log diff --git a/mysql-test/t/merge_mmap.test b/mysql-test/t/merge_mmap.test index 3468702ca45..c97b029754d 100644 --- a/mysql-test/t/merge_mmap.test +++ b/mysql-test/t/merge_mmap.test @@ -30,6 +30,48 @@ INSERT INTO m2 SELECT * FROM m1; SELECT * FROM m2; SELECT * FROM t2; DROP TABLE m2, m1, t2, t1; +# +# INSERT-SELECT with TEMPORARY select table. +# +CREATE TABLE t1 (c1 INT); +CREATE TABLE t2 (c1 INT); +CREATE TEMPORARY TABLE m1 (c1 INT) ENGINE=MRG_MyISAM UNION=(t1,t2) + INSERT_METHOD=LAST; +CREATE TABLE m2 (c1 INT) ENGINE=MRG_MyISAM UNION=(t1,t2) + INSERT_METHOD=LAST; +INSERT INTO t1 VALUES (1); +INSERT INTO t2 VALUES (2), (3), (4); +INSERT INTO m2 SELECT * FROM m1; +SELECT * FROM m2; +DROP TABLE m2, m1, t2, t1; +# +# INSERT-SELECT with TEMPORARY insert table. +# +CREATE TABLE t1 (c1 INT); +CREATE TABLE t2 (c1 INT); +CREATE TABLE m1 (c1 INT) ENGINE=MRG_MyISAM UNION=(t1,t2) + INSERT_METHOD=LAST; +CREATE TEMPORARY TABLE m2 (c1 INT) ENGINE=MRG_MyISAM UNION=(t1,t2) + INSERT_METHOD=LAST; +INSERT INTO t1 VALUES (1); +INSERT INTO t2 VALUES (2), (3), (4); +INSERT INTO m2 SELECT * FROM m1; +SELECT * FROM m2; +DROP TABLE m2, m1, t2, t1; +# +# INSERT-SELECT with TEMPORARY both tables. +# +CREATE TABLE t1 (c1 INT); +CREATE TABLE t2 (c1 INT); +CREATE TEMPORARY TABLE m1 (c1 INT) ENGINE=MRG_MyISAM UNION=(t1,t2) + INSERT_METHOD=LAST; +CREATE TEMPORARY TABLE m2 (c1 INT) ENGINE=MRG_MyISAM UNION=(t1,t2) + INSERT_METHOD=LAST; +INSERT INTO t1 VALUES (1); +INSERT INTO t2 VALUES (2), (3), (4); +INSERT INTO m2 SELECT * FROM m1; +SELECT * FROM m2; +DROP TABLE m2, m1, t2, t1; #################### ## With LOCK TABLES. @@ -51,6 +93,55 @@ SELECT * FROM m2; SELECT * FROM t2; UNLOCK TABLES; DROP TABLE m2, m1, t2, t1; +# +# INSERT-SELECT with TEMPORARY select table. +# +CREATE TABLE t1 (c1 INT); +CREATE TABLE t2 (c1 INT); +CREATE TEMPORARY TABLE m1 (c1 INT) ENGINE=MRG_MyISAM UNION=(t1,t2) + INSERT_METHOD=LAST; +CREATE TABLE m2 (c1 INT) ENGINE=MRG_MyISAM UNION=(t1,t2) + INSERT_METHOD=LAST; +LOCK TABLE m1 WRITE, m2 WRITE; +INSERT INTO t1 VALUES (1); +INSERT INTO t2 VALUES (2), (3), (4); +INSERT INTO m2 SELECT * FROM m1; +SELECT * FROM m2; +UNLOCK TABLES; +DROP TABLE m2, m1, t2, t1; +# +# INSERT-SELECT with TEMPORARY insert table. +# +CREATE TABLE t1 (c1 INT); +CREATE TABLE t2 (c1 INT); +CREATE TABLE m1 (c1 INT) ENGINE=MRG_MyISAM UNION=(t1,t2) + INSERT_METHOD=LAST; +CREATE TEMPORARY TABLE m2 (c1 INT) ENGINE=MRG_MyISAM UNION=(t1,t2) + INSERT_METHOD=LAST; +LOCK TABLE m1 WRITE, m2 WRITE; +INSERT INTO t1 VALUES (1); +INSERT INTO t2 VALUES (2), (3), (4); +INSERT INTO m2 SELECT * FROM m1; +SELECT * FROM m2; +UNLOCK TABLES; +DROP TABLE m2, m1, t2, t1; +# +# INSERT-SELECT with TEMPORARY both tables. +# +CREATE TABLE t1 (c1 INT); +CREATE TABLE t2 (c1 INT); +CREATE TEMPORARY TABLE m1 (c1 INT) ENGINE=MRG_MyISAM UNION=(t1,t2) + INSERT_METHOD=LAST; +CREATE TEMPORARY TABLE m2 (c1 INT) ENGINE=MRG_MyISAM UNION=(t1,t2) + INSERT_METHOD=LAST; +LOCK TABLE m1 WRITE, m2 WRITE; +INSERT INTO t1 VALUES (1); +INSERT INTO t2 VALUES (2), (3), (4); +INSERT INTO m2 SELECT * FROM m1; +SELECT * FROM m2; +UNLOCK TABLES; +DROP TABLE m2, m1, t2, t1; + --echo End of 6.0 tests --disable_result_log diff --git a/storage/myisammrg/ha_myisammrg.cc b/storage/myisammrg/ha_myisammrg.cc index 1681f062117..08aa9dfd0e4 100644 --- a/storage/myisammrg/ha_myisammrg.cc +++ b/storage/myisammrg/ha_myisammrg.cc @@ -476,10 +476,7 @@ int ha_myisammrg::add_children_list(void) child_l->parent_l= parent_l; /* Copy select_lex. Used in unique_table() at least. */ child_l->select_lex= parent_l->select_lex; - /* - Set the expected table version, to not cause spurious re-prepare. - @todo: revise after the fix for Bug#36171 - */ + /* Set the expected table version, to not cause spurious re-prepare. */ child_l->set_table_ref_id(mrg_child_def->get_child_table_ref_type(), mrg_child_def->get_child_def_version()); /* Link TABLE_LIST object into the children list. */ @@ -618,15 +615,17 @@ extern "C" MI_INFO *myisammrg_attach_children_callback(void *callback_param) param->need_compat_check= TRUE; /* - If parent is temporary, children must be temporary too and vice - versa. This check must be done for every child on every open because - the table def version can overlap between temporary and - non-temporary tables. We need to detect the case where a - non-temporary table has been replaced with a temporary table of the - same version. Or vice versa. A very unlikely case, but it could - happen. + If child is temporary, parent must be temporary as well. Other + parent/child combinations are allowed. This check must be done for + every child on every open because the table def version can overlap + between temporary and non-temporary tables. We need to detect the + case where a non-temporary table has been replaced with a temporary + table of the same version. Or vice versa. A very unlikely case, but + it could happen. (Note that the condition was different from + 5.1.23/6.0.4(Bug#19627) to 5.5.6 (Bug#36171): child->s->tmp_table != + parent->s->tmp_table. Tables were required to have the same status.) */ - if (child->s->tmp_table != parent->s->tmp_table) + if (child->s->tmp_table && !parent->s->tmp_table) { DBUG_PRINT("error", ("temporary table mismatch parent: %d child: %d", parent->s->tmp_table, child->s->tmp_table)); From 132ccf93d8030a3c9a5b0d60bacf52e6d043abc7 Mon Sep 17 00:00:00 2001 From: Jon Olav Hauglid Date: Mon, 5 Jul 2010 13:59:34 +0200 Subject: [PATCH 057/129] Bug #54401 assert in Diagnostics_area::set_eof_status , HANDLER This assert checks that the server does not try to send EOF to the client if there has been some error during processing. This to make sure that the error is in fact sent to the client. The problem was that any errors during processing of WHERE conditions in HANDLER ... READ statements where not detected by the handler code. The handler code therefore still tried to send EOF to the client, triggering the assert. The bug was only noticeable in debug builds. This patch fixes the problem by making sure that the handler code checks for errors during condition processing and acts accordingly. --- mysql-test/include/handler.inc | 32 ++++++++++++++++++++++++++++++ mysql-test/r/handler_innodb.result | 20 +++++++++++++++++++ mysql-test/r/handler_myisam.result | 20 +++++++++++++++++++ sql/sql_handler.cc | 4 ++++ 4 files changed, 76 insertions(+) diff --git a/mysql-test/include/handler.inc b/mysql-test/include/handler.inc index 0031cb68647..98988ab55ba 100644 --- a/mysql-test/include/handler.inc +++ b/mysql-test/include/handler.inc @@ -1757,3 +1757,35 @@ disconnect con51355; --echo # Connection default connection default; + +--echo # +--echo # Bug#54401 assert in Diagnostics_area::set_eof_status , HANDLER +--echo # + +--disable_warnings +DROP TABLE IF EXISTS t1, t2; +DROP FUNCTION IF EXISTS f1; +--enable_warnings + +delimiter |; +CREATE FUNCTION f1() RETURNS INTEGER +BEGIN + SELECT 1 FROM t2 INTO @a; + RETURN 1; +END| +delimiter ;| + +# Get f1() parsed and cached +--error ER_NO_SUCH_TABLE +SELECT f1(); + +CREATE TABLE t1(a INT); +INSERT INTO t1 VALUES (1); +HANDLER t1 OPEN; +# This used to cause the assert +--error ER_NO_SUCH_TABLE +HANDLER t1 READ FIRST WHERE f1() = 1; +HANDLER t1 CLOSE; + +DROP FUNCTION f1; +DROP TABLE t1; diff --git a/mysql-test/r/handler_innodb.result b/mysql-test/r/handler_innodb.result index 08d2fc58e8a..121cfa89f1c 100644 --- a/mysql-test/r/handler_innodb.result +++ b/mysql-test/r/handler_innodb.result @@ -1710,3 +1710,23 @@ ERROR 42S02: Table 'test.t1' doesn't exist HANDLER t1 CLOSE; # Connection con51355 # Connection default +# +# Bug#54401 assert in Diagnostics_area::set_eof_status , HANDLER +# +DROP TABLE IF EXISTS t1, t2; +DROP FUNCTION IF EXISTS f1; +CREATE FUNCTION f1() RETURNS INTEGER +BEGIN +SELECT 1 FROM t2 INTO @a; +RETURN 1; +END| +SELECT f1(); +ERROR 42S02: Table 'test.t2' doesn't exist +CREATE TABLE t1(a INT); +INSERT INTO t1 VALUES (1); +HANDLER t1 OPEN; +HANDLER t1 READ FIRST WHERE f1() = 1; +ERROR 42S02: Table 'test.t2' doesn't exist +HANDLER t1 CLOSE; +DROP FUNCTION f1; +DROP TABLE t1; diff --git a/mysql-test/r/handler_myisam.result b/mysql-test/r/handler_myisam.result index 31bc828b0b9..fd08fd12f15 100644 --- a/mysql-test/r/handler_myisam.result +++ b/mysql-test/r/handler_myisam.result @@ -1707,6 +1707,26 @@ HANDLER t1 CLOSE; # Connection con51355 # Connection default # +# Bug#54401 assert in Diagnostics_area::set_eof_status , HANDLER +# +DROP TABLE IF EXISTS t1, t2; +DROP FUNCTION IF EXISTS f1; +CREATE FUNCTION f1() RETURNS INTEGER +BEGIN +SELECT 1 FROM t2 INTO @a; +RETURN 1; +END| +SELECT f1(); +ERROR 42S02: Table 'test.t2' doesn't exist +CREATE TABLE t1(a INT); +INSERT INTO t1 VALUES (1); +HANDLER t1 OPEN; +HANDLER t1 READ FIRST WHERE f1() = 1; +ERROR 42S02: Table 'test.t2' doesn't exist +HANDLER t1 CLOSE; +DROP FUNCTION f1; +DROP TABLE t1; +# # BUG #46456: HANDLER OPEN + TRUNCATE + DROP (temporary) TABLE, crash # CREATE TABLE t1 AS SELECT 1 AS f1; diff --git a/sql/sql_handler.cc b/sql/sql_handler.cc index d6f2a472e05..e49da2b0423 100644 --- a/sql/sql_handler.cc +++ b/sql/sql_handler.cc @@ -747,7 +747,11 @@ retry: goto ok; } if (cond && !cond->val_int()) + { + if (thd->is_error()) + goto err; continue; + } if (num_rows >= offset_limit_cnt) { protocol->prepare_for_resend(); From 19ea597a385c768fe749c48c2453036a3fb7d6d8 Mon Sep 17 00:00:00 2001 From: Jimmy Yang Date: Mon, 5 Jul 2010 19:26:38 -0700 Subject: [PATCH 058/129] Add innodb_bug53756-master.opt for innodb_bug53756 test. --- mysql-test/suite/innodb/r/innodb_bug53756.result | 2 +- mysql-test/suite/innodb/t/innodb_bug53756-master.opt | 1 + mysql-test/suite/innodb/t/innodb_bug53756.test | 2 +- 3 files changed, 3 insertions(+), 2 deletions(-) create mode 100644 mysql-test/suite/innodb/t/innodb_bug53756-master.opt diff --git a/mysql-test/suite/innodb/r/innodb_bug53756.result b/mysql-test/suite/innodb/r/innodb_bug53756.result index 67797f9c90f..37453be8201 100644 --- a/mysql-test/suite/innodb/r/innodb_bug53756.result +++ b/mysql-test/suite/innodb/r/innodb_bug53756.result @@ -78,7 +78,7 @@ ROLLBACK; # connection default selects resulting data. # Delete of row 1 was committed. -# Dpdate of row 3 was committed. +# Update of row 3 was committed. # Due to isolation level read committed, these should be included. # All other changes should not be included. SELECT * FROM bug_53756; diff --git a/mysql-test/suite/innodb/t/innodb_bug53756-master.opt b/mysql-test/suite/innodb/t/innodb_bug53756-master.opt new file mode 100644 index 00000000000..425fda95086 --- /dev/null +++ b/mysql-test/suite/innodb/t/innodb_bug53756-master.opt @@ -0,0 +1 @@ +--skip-stack-trace --skip-core-file diff --git a/mysql-test/suite/innodb/t/innodb_bug53756.test b/mysql-test/suite/innodb/t/innodb_bug53756.test index 85a09478486..8324f2640a2 100644 --- a/mysql-test/suite/innodb/t/innodb_bug53756.test +++ b/mysql-test/suite/innodb/t/innodb_bug53756.test @@ -114,7 +114,7 @@ ROLLBACK; --echo --echo # connection default selects resulting data. --echo # Delete of row 1 was committed. ---echo # Dpdate of row 3 was committed. +--echo # Update of row 3 was committed. --echo # Due to isolation level read committed, these should be included. --echo # All other changes should not be included. --connection default From 7f0f32d659c5e3eff1d6ed6249cad59ff6df5723 Mon Sep 17 00:00:00 2001 From: Jon Olav Hauglid Date: Wed, 7 Jul 2010 15:20:07 +0200 Subject: [PATCH 059/129] Bug #37521 Row inserted through view not always visible in base table immediately after The problem was that rows inserted in a table by one connection was not immediately visible if another connection queried the table, even if the insert had committed. The reason for the problem was that the server sent a status reply to the client before it actually did the commit. Therefore it was possible to get an OK from the server before the changes were made permanent and visible to other connections. This patch fixes the problem by not sending status messages to the server until any changes made have been committed. No test case added as reproducing the error requires very specific timing betweeen the server and two or more clients. This patch also fixes the following (duplicate) bugs: Bug #29334 pseudo-finished SHOW GLOBAL STATUS Bug #36618 myisam insert not immediately visible to select from another client Bug #45864 insert on one connection, immediate query on another produces no result Bug #51329 Inserts from one connection not immediately visible in second connection Bug #41516 Assertion fails when error returned from handler::external_lock(thd, F_UNLCK) --- sql/sql_parse.cc | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/sql/sql_parse.cc b/sql/sql_parse.cc index 31eaf4111ce..dd47dfb88af 100644 --- a/sql/sql_parse.cc +++ b/sql/sql_parse.cc @@ -1511,13 +1511,13 @@ bool dispatch_command(enum enum_server_command command, THD *thd, thd->transaction.stmt.reset(); - thd->protocol->end_statement(); - query_cache_end_of_result(thd); - thd->proc_info= "closing tables"; /* Free tables */ close_thread_tables(thd); + thd->protocol->end_statement(); + query_cache_end_of_result(thd); + if (!thd->is_error() && !thd->killed_errno()) mysql_audit_general(thd, MYSQL_AUDIT_GENERAL_RESULT, 0, 0); From 0469e7df7ff4251c1afb8a832b34f84a74d4988f Mon Sep 17 00:00:00 2001 From: Vasil Dimov Date: Wed, 7 Jul 2010 20:51:30 +0300 Subject: [PATCH 060/129] Add the innodb_plugin tests to "make dist". --- mysql-test/Makefile.am | 2 ++ 1 file changed, 2 insertions(+) diff --git a/mysql-test/Makefile.am b/mysql-test/Makefile.am index 06aea68b52d..13e2388858f 100644 --- a/mysql-test/Makefile.am +++ b/mysql-test/Makefile.am @@ -100,6 +100,8 @@ TEST_DIRS = t r include std_data std_data/parts collections \ suite/rpl_ndb suite/rpl_ndb/t suite/rpl_ndb/r \ suite/parts suite/parts/t suite/parts/r suite/parts/inc \ suite/innodb suite/innodb/t suite/innodb/r suite/innodb/include \ + suite/innodb_plugin suite/innodb_plugin/t suite/innodb_plugin/r \ + suite/innodb_plugin/include \ suite/engines suite/engines/funcs suite/engines/iuds suite/engines/rr_trx \ suite/engines/funcs/r suite/engines/funcs/t suite/engines/iuds/r \ suite/engines/iuds/t suite/engines/rr_trx/include suite/engines/rr_trx/r \ From 2f570f7ce3a41d5bb99ce454c88e3e321751fc49 Mon Sep 17 00:00:00 2001 From: sunanda Date: Wed, 7 Jul 2010 20:34:50 +0200 Subject: [PATCH 061/129] rko Mdkeld change, revision 3351.14.134 add innodb_plugin to mysql-test-run default suites was not complete. Bootstrap failed to pick up necessary files needed by test and hence all tests failed. --- mysql-test/Makefile.am | 1 + 1 file changed, 1 insertion(+) diff --git a/mysql-test/Makefile.am b/mysql-test/Makefile.am index 06aea68b52d..066c8d53c14 100644 --- a/mysql-test/Makefile.am +++ b/mysql-test/Makefile.am @@ -100,6 +100,7 @@ TEST_DIRS = t r include std_data std_data/parts collections \ suite/rpl_ndb suite/rpl_ndb/t suite/rpl_ndb/r \ suite/parts suite/parts/t suite/parts/r suite/parts/inc \ suite/innodb suite/innodb/t suite/innodb/r suite/innodb/include \ + suite/innodb_plugin suite/innodb_plugin/t suite/innodb_plugin/r suite/innodb_plugin/include \ suite/engines suite/engines/funcs suite/engines/iuds suite/engines/rr_trx \ suite/engines/funcs/r suite/engines/funcs/t suite/engines/iuds/r \ suite/engines/iuds/t suite/engines/rr_trx/include suite/engines/rr_trx/r \ From 6ad06b15222300e4eed4fe3972d1ad249c4c42a2 Mon Sep 17 00:00:00 2001 From: unknown Date: Fri, 9 Jul 2010 14:23:48 +0200 Subject: [PATCH 062/129] Fix bug #55039 Failing assertion: space_id > 0 in fil0fil.c. --- storage/innodb_plugin/dict/dict0crea.c | 18 +++++++++++++++--- storage/innodb_plugin/os/os0file.c | 12 ++++++++++-- 2 files changed, 25 insertions(+), 5 deletions(-) diff --git a/storage/innodb_plugin/dict/dict0crea.c b/storage/innodb_plugin/dict/dict0crea.c index f185371bfca..09353c45c8c 100644 --- a/storage/innodb_plugin/dict/dict0crea.c +++ b/storage/innodb_plugin/dict/dict0crea.c @@ -240,17 +240,29 @@ dict_build_table_def_step( ibool is_path; mtr_t mtr; ulint space = 0; + ibool file_per_table; ut_ad(mutex_own(&(dict_sys->mutex))); table = node->table; - dict_hdr_get_new_id(&table->id, NULL, - srv_file_per_table ? &space : NULL); + /* Cache the global variable "srv_file_per_table" to + a local variable before using it. Please note + "srv_file_per_table" is not under dict_sys mutex + protection, and could be changed while executing + this function. So better to cache the current value + to a local variable, and all future reference to + "srv_file_per_table" should use this local variable. */ + file_per_table = srv_file_per_table; + + dict_hdr_get_new_id(&table->id, NULL, NULL); thr_get_trx(thr)->table_id = table->id; - if (srv_file_per_table) { + if (file_per_table) { + /* Get a new space id if srv_file_per_table is set */ + dict_hdr_get_new_id(NULL, NULL, &space); + if (UNIV_UNLIKELY(space == ULINT_UNDEFINED)) { return(DB_ERROR); } diff --git a/storage/innodb_plugin/os/os0file.c b/storage/innodb_plugin/os/os0file.c index b244e3974b3..9f937b9def2 100644 --- a/storage/innodb_plugin/os/os0file.c +++ b/storage/innodb_plugin/os/os0file.c @@ -1339,7 +1339,11 @@ try_again: /* When srv_file_per_table is on, file creation failure may not be critical to the whole instance. Do not crash the server in - case of unknown errors. */ + case of unknown errors. + Please note "srv_file_per_table" is a global variable with + no explicit synchronization protection. It could be + changed during this execution path. It might not have the + same value as the one when building the table definition */ if (srv_file_per_table) { retry = os_file_handle_error_no_exit(name, create_mode == OS_FILE_CREATE ? @@ -1426,7 +1430,11 @@ try_again: /* When srv_file_per_table is on, file creation failure may not be critical to the whole instance. Do not crash the server in - case of unknown errors. */ + case of unknown errors. + Please note "srv_file_per_table" is a global variable with + no explicit synchronization protection. It could be + changed during this execution path. It might not have the + same value as the one when building the table definition */ if (srv_file_per_table) { retry = os_file_handle_error_no_exit(name, create_mode == OS_FILE_CREATE ? From e98169d52c8610efa523040d4409054e352f92df Mon Sep 17 00:00:00 2001 From: Alexey Kopytov Date: Mon, 12 Jul 2010 18:58:55 +0400 Subject: [PATCH 063/129] Bug#55061: Build failing on sol 8 x86 - assembler code vs compiler problem GCC-style inline assembly is not supported by the Sun Studio compilers prior to version 12. Added a check for the Sun Studio version to avoid using _FPU_GETCW() / _FPU_SETCW() when inline assembly is unsupported. This can lead to some differences in floating point calculations on Solaris 8/x86 which, however, is not worth bothering with Sun-style assembly .il templates. --- sql/mysqld.cc | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/sql/mysqld.cc b/sql/mysqld.cc index 99f16b36dfa..598db8d993c 100644 --- a/sql/mysqld.cc +++ b/sql/mysqld.cc @@ -190,7 +190,7 @@ typedef fp_except fp_except_t; # define fpu_control_t unsigned int # define _FPU_EXTENDED 0x300 # define _FPU_DOUBLE 0x200 -# if defined(__GNUC__) || defined(__SUNPRO_CC) +# if defined(__GNUC__) || (defined(__SUNPRO_CC) && __SUNPRO_CC >= 0x590) # define _FPU_GETCW(cw) asm volatile ("fnstcw %0" : "=m" (*&cw)) # define _FPU_SETCW(cw) asm volatile ("fldcw %0" : : "m" (*&cw)) # else From a6a8e10c799d093e13ec136b960703f9b657df74 Mon Sep 17 00:00:00 2001 From: Dmitry Lenev Date: Tue, 13 Jul 2010 22:01:54 +0400 Subject: [PATCH 064/129] A pre-requisite for patch fixing bug #52044 "FLUSH TABLES WITH READ LOCK and FLUSH TABLES WITH READ LOCK are incompatible", which adds information about waits caused by FLUSH TABLES statement to deadlock detector in MDL subsystem. Remove API supporting caching of pointers to TABLE_SHARE object in MDL subsystem and all code related to it. The problem was that locking requirements of code implementing this API conflicted with locking requirements of code which adds information about waits caused by flushes to deadlock detector in MDL subsystem (the former needed to lock LOCK_open or its future equivalent while having write-lock on MDL_lock's rwlock, and the latter needs to be able to read-lock MDL_lock rwlock while owning LOCK_open or its future equivalent). Since caching of pointers to TABLE_SHARE objects in MDL subsystem didn't bring expected performance benefits we decided to remove caching API rather than try to come up with some complex solution for this problem. --- sql/mdl.cc | 103 ------------------ sql/mdl.h | 4 - sql/sql_base.cc | 282 +++++++++--------------------------------------- 3 files changed, 48 insertions(+), 341 deletions(-) diff --git a/sql/mdl.cc b/sql/mdl.cc index c5b84902823..818b736e597 100644 --- a/sql/mdl.cc +++ b/sql/mdl.cc @@ -284,8 +284,6 @@ public: public: /** The key of the object (data) being protected. */ MDL_key key; - /** A cached reference to the TABLE_SHARE. Protected by LOCK_open. */ - void *m_cached_object; /** Read-write lock protecting this lock context. @@ -362,7 +360,6 @@ public: MDL_lock(const MDL_key *key_arg) : key(key_arg), - m_cached_object(NULL), m_ref_usage(0), m_ref_release(0), m_is_destroyed(FALSE) @@ -370,8 +367,6 @@ public: mysql_prlock_init(key_MDL_lock_rwlock, &m_rwlock); } - /* Overridden for TABLE objects, to support TABLE_SHARE cache in MDL. */ - virtual void release_cached_object() {} virtual ~MDL_lock() { mysql_prlock_destroy(&m_rwlock); @@ -460,25 +455,6 @@ private: }; -/** - A lock implementation for MDL_key::TABLE. -*/ - -class MDL_table_lock: public MDL_object_lock -{ -public: - MDL_table_lock(const MDL_key *key_arg) - : MDL_object_lock(key_arg) - { } -#ifdef DISABLED_UNTIL_GRL_IS_MADE_PART_OF_MDL - virtual void release_cached_object() - { - tdc_release_cached_share(&m_cached_object); - } -#endif -}; - - static MDL_map mdl_locks; extern "C" @@ -695,8 +671,6 @@ void MDL_map::remove(MDL_lock *lock) { uint ref_usage, ref_release; - lock->release_cached_object(); - /* Destroy the MDL_lock object, but ensure that anyone that is holding a reference to the object is not remaining, if so he @@ -860,8 +834,6 @@ inline MDL_lock *MDL_lock::create(const MDL_key *mdl_key) case MDL_key::GLOBAL: case MDL_key::SCHEMA: return new MDL_scoped_lock(mdl_key); - case MDL_key::TABLE: - return new MDL_table_lock(mdl_key); default: return new MDL_object_lock(mdl_key); } @@ -1682,9 +1654,6 @@ MDL_context::try_acquire_lock_impl(MDL_request *mdl_request, m_tickets.push_front(ticket); - if (ticket->get_type() == MDL_EXCLUSIVE) - ticket->clear_cached_object(); - mdl_request->ticket= ticket; } else @@ -1886,9 +1855,6 @@ MDL_context::acquire_lock(MDL_request *mdl_request, ulong lock_wait_timeout) */ DBUG_ASSERT(wait_status == MDL_wait::GRANTED); - if (ticket->get_type() == MDL_EXCLUSIVE) - ticket->clear_cached_object(); - m_tickets.push_front(ticket); mdl_request->ticket= ticket; @@ -2451,75 +2417,6 @@ bool MDL_ticket::has_pending_conflicting_lock() const } -/** - Associate pointer to an opaque object with a lock. - - @param cached_object Pointer to the object - @param release_hook Cleanup function to be called when MDL subsystem - decides to remove lock or associate another object. - - This is used to cache a pointer to TABLE_SHARE in the lock - structure. Such caching can save one acquisition of LOCK_open - and one table definition cache lookup for every table. - - Since the pointer may be stored only inside an acquired lock, - the caching is only effective when there is more than one lock - granted on a given table. - - This function has the following usage pattern: - - try to acquire an MDL lock - - when done, call for get_cached_object(). If it returns NULL, our - thread has the only lock on this table. - - look up TABLE_SHARE in the table definition cache - - call mdl_set_cache_object() to assign the share to the opaque pointer. - - The release hook is invoked when the last shared metadata - lock on this name is released. -*/ - -void -MDL_ticket::set_cached_object(void *cached_object) -{ - DBUG_ENTER("MDL_ticket::set_cached_object"); - DBUG_PRINT("enter", ("db=%s name=%s cached_object=%p", - m_lock->key.db_name(), m_lock->key.name(), - cached_object)); - mysql_mutex_assert_owner(&LOCK_open); - DBUG_ASSERT(m_lock->key.mdl_namespace() == MDL_key::TABLE); - DBUG_ASSERT(!m_lock->m_cached_object); - - m_lock->m_cached_object= cached_object; - - DBUG_VOID_RETURN; -} - - -/** - A helper function to flush the table share cached in MDL. - @pre The ticket is acquired. -*/ - -void MDL_ticket::clear_cached_object() -{ - m_lock->release_cached_object(); -} - - -/** - Get a pointer to an opaque object that associated with the lock. - - @param ticket Lock ticket for the lock which the object is associated to. - - @return Pointer to an opaque object associated with the lock. -*/ - -void *MDL_ticket::get_cached_object() -{ - mysql_mutex_assert_owner(&LOCK_open); - return m_lock->m_cached_object; -} - - /** Releases metadata locks that were acquired after a specific savepoint. diff --git a/sql/mdl.h b/sql/mdl.h index 5c58289aea2..319c16cf6ce 100644 --- a/sql/mdl.h +++ b/sql/mdl.h @@ -398,9 +398,6 @@ public: public: bool has_pending_conflicting_lock() const; - void *get_cached_object(); - void set_cached_object(void *cached_object); - void clear_cached_object(); MDL_context *get_ctx() const { return m_ctx; } bool is_upgradable_or_exclusive() const { @@ -728,7 +725,6 @@ extern "C" const char *set_thd_proc_info(void *thd_arg, const char *info, const char *calling_function, const char *calling_file, const unsigned int calling_line); -extern void tdc_release_cached_share(void *ptr); #ifndef DBUG_OFF extern mysql_mutex_t LOCK_open; #endif diff --git a/sql/sql_base.cc b/sql/sql_base.cc index d57554785b8..f18d5e26f01 100644 --- a/sql/sql_base.cc +++ b/sql/sql_base.cc @@ -921,141 +921,6 @@ static void kill_delayed_threads_for_table(TABLE_SHARE *share) } -#ifdef DISABLED_UNTIL_GRL_IS_MADE_PART_OF_MDL -/** - Flush MDL cached objects. - - How MDL table share cache works - ------------------------------- - Since we take a table share from the table definition - cache only after taking an MDL lock, the MDL lock - object is a convenient place to cache a pointer - to the table share. However, not all SQL in MySQL - takes an MDL lock prior to working with the TDC, - various forms of FLUSH TABLES (including SET GLOBAL - read_only) being the one and only exception. - - To make FLUSH TABLES work, and avoid having dangling - references to TABLE_SHARE objects in MDL subsystem - after a flush, we make sure that all references - to table shares are released whenever a flush comes. - This is done in this function. - - To sum up, the following invariants are held: - - no statement can work with a TABLE_SHARE without - a metadata lock. The only exception is FLUSH TABLES. - - a metadata lock object can be used to store - a cached reference (pointer) to the corresponding - TABLE_SHARE, if and only if this TABLE_SHARE is - not stale (version == refresh_version). In other words, - checking TABLE_SHARE version and setting the reference - must happen only in the same critical section protected - by LOCK_open. - - FLUSH will mark all subject TABLE_SHARE objects - as stale, and then will manually release all TABLE_SHARE - references in MDL cache. Since marking TABLE_SHARE - objects is done inside a critical section protected - by LOCK_open and prior to calling flush_mdl_cache(), - it's guaranteed that a flush will take place before - a new reference to the table share is established - in some other connection. -*/ - -bool flush_mdl_cache(THD *thd, TABLE_LIST *table_list) -{ - MDL_request_list mdl_requests; - MDL_request *mdl_request; - - DBUG_ENTER("flush_mdl_cache"); - - if (table_list == NULL) - { - mysql_mutex_lock(&LOCK_open); - for (uint idx= 0 ; idx < table_def_cache.records; idx++) - { - TABLE_SHARE *share=(TABLE_SHARE*) my_hash_element(&table_def_cache, - idx); - if (share->needs_reopen()) - { - mdl_request= MDL_request::create(MDL_key::TABLE, - share->db.str, - share->table_name.str, - MDL_SHARED_HIGH_PRIO, - thd->mem_root); - if (! mdl_request) - { - mysql_mutex_unlock(&LOCK_open); - DBUG_RETURN(TRUE); - } - mdl_requests.push_front(mdl_request); - } - } - mysql_mutex_unlock(&LOCK_open); - } - else - { - for (TABLE_LIST *tables= table_list; tables; tables= tables->next_global) - { - DBUG_ASSERT(tables->mdl_request.type == MDL_SHARED_HIGH_PRIO); - mdl_requests.push_front(&tables->mdl_request); - } - } - - for (MDL_request_list::Iterator it(mdl_requests); - (mdl_request= it++); ) - { - if (thd->mdl_context.try_acquire_lock(mdl_request)) - DBUG_RETURN(TRUE); - if (mdl_request->ticket) - { - mdl_request->ticket->clear_cached_object(); - thd->mdl_context.release_lock(mdl_request->ticket); - } - } - DBUG_RETURN(FALSE); -} - - -/** - @brief Helper function used by MDL subsystem for releasing TABLE_SHARE - objects in cases when it no longer wants to cache reference to it. -*/ - -void tdc_release_cached_share(void *ptr) -{ - TABLE_SHARE **share= (TABLE_SHARE **) ptr; - mysql_mutex_lock(&LOCK_open); - if (*share) - { - release_table_share(*share); - *share= NULL; - broadcast_refresh(); - } - mysql_mutex_unlock(&LOCK_open); -} - - -/** - @brief Mark table share as having one more user (increase its reference - count). - - @param share Table share for which reference count should be increased. -*/ - -static void tdc_reference_table_share(TABLE_SHARE *share) -{ - DBUG_ENTER("tdc_reference_table_share"); - DBUG_ASSERT(share->ref_count); - mysql_mutex_assert_owner(&LOCK_open); - share->ref_count++; - DBUG_PRINT("exit", ("share: 0x%lx ref_count: %u", - (ulong) share, share->ref_count)); - DBUG_VOID_RETURN; -} - - -#endif // DISABLED_UNTIL_GRL_IS_MADE_PART_OF - /* Close all tables which aren't in use by any thread @@ -1167,15 +1032,6 @@ bool close_cached_tables(THD *thd, TABLE_LIST *tables, bool have_lock, /* Wait until all threads have closed all the tables we are flushing. */ DBUG_PRINT("info", ("Waiting for other threads to close their open tables")); -#ifdef DISABLED_UNTIL_GRL_IS_MADE_PART_OF - /* - @todo We need to do this for fast refresh as well, otherwise - deadlocks are possible. - */ - if (flush_mdl_cache(thd, tables)) - goto err_with_reopen; -#endif // DISABLED_UNTIL_GRL_IS_MADE_PART_OF_MDL - while (found && ! thd->killed) { found= FALSE; @@ -2969,97 +2825,61 @@ bool open_table(THD *thd, TABLE_LIST *table_list, MEM_ROOT *mem_root, DBUG_RETURN(FALSE); mysql_mutex_lock(&LOCK_open); -#ifdef DISABLED_UNTIL_GRL_IS_MADE_PART_OF_MDL - if (!(share= (TABLE_SHARE *) mdl_ticket->get_cached_object())) + + if (!(share= get_table_share_with_create(thd, table_list, key, + key_length, OPEN_VIEW, + &error, + hash_value))) + goto err_unlock2; + + if (share->is_view) { -#endif // DISABLED_UNTIL_GRL_IS_MADE_PART_OF_MDL - if (!(share= get_table_share_with_create(thd, table_list, key, - key_length, OPEN_VIEW, - &error, - hash_value))) - goto err_unlock2; - - if (share->is_view) - { - /* - If parent_l of the table_list is non null then a merge table - has this view as child table, which is not supported. - */ - if (table_list->parent_l) - { - my_error(ER_WRONG_MRG_TABLE, MYF(0)); - goto err_unlock; - } - - /* - This table is a view. Validate its metadata version: in particular, - that it was a view when the statement was prepared. - */ - if (check_and_update_table_version(thd, table_list, share)) - goto err_unlock; - if (table_list->i_s_requested_object & OPEN_TABLE_ONLY) - goto err_unlock; - - /* Open view */ - if (open_new_frm(thd, share, alias, - (uint) (HA_OPEN_KEYFILE | HA_OPEN_RNDFILE | - HA_GET_INDEX | HA_TRY_READ_ONLY), - READ_KEYINFO | COMPUTE_TYPES | EXTRA_RECORD, - thd->open_options, - 0, table_list, mem_root)) - goto err_unlock; - - /* TODO: Don't free this */ - release_table_share(share); - - DBUG_ASSERT(table_list->view); - - mysql_mutex_unlock(&LOCK_open); - DBUG_RETURN(FALSE); - } /* - Note that situation when we are trying to open a table for what - was a view during previous execution of PS will be handled in by - the caller. Here we should simply open our table even if - TABLE_LIST::view is true. + If parent_l of the table_list is non null then a merge table + has this view as child table, which is not supported. */ + if (table_list->parent_l) + { + my_error(ER_WRONG_MRG_TABLE, MYF(0)); + goto err_unlock; + } - if (table_list->i_s_requested_object & OPEN_VIEW_ONLY) + /* + This table is a view. Validate its metadata version: in particular, + that it was a view when the statement was prepared. + */ + if (check_and_update_table_version(thd, table_list, share)) + goto err_unlock; + if (table_list->i_s_requested_object & OPEN_TABLE_ONLY) goto err_unlock; -#ifdef DISABLED_UNTIL_GRL_IS_MADE_PART_OF_MDL - /* - We are going to to store extra reference to the share - in MDL-subsystem so we need to increase reference counter. - */ - if (! share->needs_reopen()) - { - mdl_ticket->set_cached_object(share); - tdc_reference_table_share(share); - } - } - else - { - if (table_list->view) - { - DBUG_ASSERT(thd->m_reprepare_observer); - check_and_update_table_version(thd, table_list, share); - /* Always an error. */ - DBUG_ASSERT(thd->is_error()); - goto err_unlock2; - } - /* When we have cached TABLE_SHARE we know that is not a view. */ - if (table_list->i_s_requested_object & OPEN_VIEW_ONLY) - goto err_unlock2; + /* Open view */ + if (open_new_frm(thd, share, alias, + (uint) (HA_OPEN_KEYFILE | HA_OPEN_RNDFILE | + HA_GET_INDEX | HA_TRY_READ_ONLY), + READ_KEYINFO | COMPUTE_TYPES | EXTRA_RECORD, + thd->open_options, + 0, table_list, mem_root)) + goto err_unlock; - /* - We are going to use this share for construction of new TABLE object - so reference counter should be increased. - */ - tdc_reference_table_share(share); - } -#endif // DISABLED_UNTIL_GRL_IS_MADE_PART_OF_MDL + /* TODO: Don't free this */ + release_table_share(share); + DBUG_ASSERT(table_list->view); + + mysql_mutex_unlock(&LOCK_open); + DBUG_RETURN(FALSE); + } + + /* + Note that situation when we are trying to open a table for what + was a view during previous execution of PS will be handled in by + the caller. Here we should simply open our table even if + TABLE_LIST::view is true. + */ + + if (table_list->i_s_requested_object & OPEN_VIEW_ONLY) + goto err_unlock; /* If the version changes while we're opening the tables, @@ -8860,13 +8680,7 @@ void tdc_remove_table(THD *thd, enum_tdc_remove_table_type remove_type, automatically deleted once it is no longer referenced. */ share->version= 0; -#ifdef DISABLED_UNTIL_GRL_IS_MADE_PART_OF_MDL - /* - If lock type is not EXCLUSIVE, we must call - MDL_ticket::release_cached_object() here to make sure there - is no self-reference left on the share in MDL_lock. - */ -#endif + while ((table= it++)) free_cache_entry(table); } From f8354dddffdf2f78ccf04580b1c159bd1028ee6c Mon Sep 17 00:00:00 2001 From: Bjorn Munch Date: Fri, 16 Jul 2010 10:21:06 +0200 Subject: [PATCH 065/129] Bug #54835 MTR version 1 cannot start server - bootstrap reports unknown InnoDB engine Remove --loose-skip-innodb from startup options This is a simple backport of change done in WL #5349 Same as shown as "temporary fix", cherry picked to -mtr branch --- mysql-test/lib/v1/mysql-test-run.pl | 1 - 1 file changed, 1 deletion(-) diff --git a/mysql-test/lib/v1/mysql-test-run.pl b/mysql-test/lib/v1/mysql-test-run.pl index 64d7376605e..36acea3ab6d 100755 --- a/mysql-test/lib/v1/mysql-test-run.pl +++ b/mysql-test/lib/v1/mysql-test-run.pl @@ -3114,7 +3114,6 @@ sub install_db ($$) { mtr_add_arg($args, "--bootstrap"); mtr_add_arg($args, "--basedir=%s", $path_my_basedir); mtr_add_arg($args, "--datadir=%s", $data_dir); - mtr_add_arg($args, "--loose-skip-innodb"); mtr_add_arg($args, "--loose-skip-ndbcluster"); mtr_add_arg($args, "--tmpdir=."); mtr_add_arg($args, "--core-file"); From d79e6c2e4594dc506d4d30cdc53545321b475ada Mon Sep 17 00:00:00 2001 From: Georgi Kodinov Date: Mon, 19 Jul 2010 17:47:17 +0300 Subject: [PATCH 066/129] fix tree names --- .bzr-mysql/default.conf | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/.bzr-mysql/default.conf b/.bzr-mysql/default.conf index 77df77c6021..f044f8e62da 100644 --- a/.bzr-mysql/default.conf +++ b/.bzr-mysql/default.conf @@ -1,4 +1,4 @@ [MYSQL] -post_commit_to = "dbg_mysql_security@sun.com" -post_push_to = "dbg_mysql_security@sun.com" -tree_name = "mysql-5.1-security" +post_commit_to = "commits@lists.mysql.com" +post_push_to = "commits@lists.mysql.com" +tree_name = "mysql-5.1" From 689a96fcce55221101b8c9b613104c0b96edfb6b Mon Sep 17 00:00:00 2001 From: Sven Sandberg Date: Tue, 20 Jul 2010 17:27:13 +0200 Subject: [PATCH 067/129] BUG#55322: SHOW BINLOG EVENTS increases @@SESSION.MAX_ALLOWED_PACKET Problem: when SHOW BINLOG EVENTS was issued, it increased the value of @@session.max_allowed_packet. This allowed a non-root user to increase the amount of memory used by her thread arbitrarily. Thus, it removes the bound on the amount of system resources used by a client, so it presents a security risk (DoS attack). Fix: it is correct to increase the value of @@session.max_allowed_packet while executing SHOW BINLOG EVENTS (see BUG 30435). However, the increase should only be temporary. Thus, the fix is to restore the value when SHOW BINLOG EVENTS ends. The value of @@session.max_allowed_packet is also increased in mysql_binlog_send (i.e., the binlog dump thread). It is not clear if this can cause any trouble, since normally the client that issues COM_BINLOG_DUMP will not issue any other commands that would be affected by the increased value of @@session.max_allowed_packet. However, we restore the value just in case. mysql-test/suite/rpl/r/rpl_packet.result: update result file mysql-test/suite/rpl/t/rpl_packet.test: Add test that verifies that @@session.max_allowed_packet does not change when issuing SHOW BINLOG EVENTS. Make previous sub-test clean up. Add comments listing the bugs in this test case. sql/sql_repl.cc: Restore the old value of thd->variables.max_allowed_packet at the end of mysql_binlog_send and mysql_show_binlog_events. --- mysql-test/suite/rpl/r/rpl_packet.result | 8 +++++ mysql-test/suite/rpl/t/rpl_packet.test | 39 +++++++++++++++++++++++- sql/sql_repl.cc | 5 +++ 3 files changed, 51 insertions(+), 1 deletion(-) diff --git a/mysql-test/suite/rpl/r/rpl_packet.result b/mysql-test/suite/rpl/r/rpl_packet.result index 0a9495751fe..1ec9259a1fb 100644 --- a/mysql-test/suite/rpl/r/rpl_packet.result +++ b/mysql-test/suite/rpl/r/rpl_packet.result @@ -49,6 +49,14 @@ Slave_IO_Running = No (expect No) SELECT "Got fatal error 1236 from master when reading data from binary log: 'log event entry exceeded max_allowed_packet; Increase max_allowed_packet on master'" AS Last_IO_Error; Last_IO_Error Got fatal error 1236 from master when reading data from binary log: 'log event entry exceeded max_allowed_packet; Increase max_allowed_packet on master' +STOP SLAVE; +RESET SLAVE; +RESET MASTER; +SET @max_allowed_packet_0= @@session.max_allowed_packet; +SHOW BINLOG EVENTS; +SET @max_allowed_packet_1= @@session.max_allowed_packet; +SHOW BINLOG EVENTS; +SET @max_allowed_packet_2= @@session.max_allowed_packet; ==== clean up ==== DROP TABLE t1; SET @@global.max_allowed_packet= 1024; diff --git a/mysql-test/suite/rpl/t/rpl_packet.test b/mysql-test/suite/rpl/t/rpl_packet.test index bfc144c759b..08a533e22ca 100644 --- a/mysql-test/suite/rpl/t/rpl_packet.test +++ b/mysql-test/suite/rpl/t/rpl_packet.test @@ -1,7 +1,12 @@ +# ==== Purpose ==== # # Check replication protocol packet size handling -# Bug#19402 SQL close to the size of the max_allowed_packet fails on slave # +# ==== Related bugs ==== +# Bug#19402 SQL close to the size of the max_allowed_packet fails on slave +# BUG#23755: Replicated event larger that max_allowed_packet infinitely re-transmits +# BUG#42914: No LAST_IO_ERROR for max_allowed_packet errors +# BUG#55322: SHOW BINLOG EVENTS increases @@SESSION.MAX_ALLOWED_PACKET # max-out size db name source include/master-slave.inc; @@ -119,6 +124,38 @@ let $slave_io_running= query_get_value(SHOW SLAVE STATUS, Slave_IO_Running, 1); let $last_io_error= query_get_value(SHOW SLAVE STATUS, Last_IO_Error, 1); eval SELECT "$last_io_error" AS Last_IO_Error; +# Remove the bad binlog and clear error status on slave. +STOP SLAVE; +RESET SLAVE; +--connection master +RESET MASTER; + + +# +# BUG#55322: SHOW BINLOG EVENTS increases @@SESSION.MAX_ALLOWED_PACKET +# +# In BUG#55322, @@session.max_allowed_packet increased each time SHOW +# BINLOG EVENTS was issued. To verify that this bug is fixed, we +# execute SHOW BINLOG EVENTS twice and check that max_allowed_packet +# never changes. We turn off the result log because we don't care +# about the contents of the binlog. + +--disable_result_log +SET @max_allowed_packet_0= @@session.max_allowed_packet; +SHOW BINLOG EVENTS; +SET @max_allowed_packet_1= @@session.max_allowed_packet; +SHOW BINLOG EVENTS; +SET @max_allowed_packet_2= @@session.max_allowed_packet; +--enable_result_log +if (`SELECT NOT(@max_allowed_packet_0 = @max_allowed_packet_1 AND @max_allowed_packet_1 = @max_allowed_packet_2)`) +{ + --echo ERROR: max_allowed_packet changed after executing SHOW BINLOG EVENTS + --source include/show_rpl_debug_info.inc + SELECT @max_allowed_packet_0, @max_allowed_packet_1, @max_allowed_packet_2; + --die @max_allowed_packet changed after executing SHOW BINLOG EVENTS +} + + --echo ==== clean up ==== connection master; DROP TABLE t1; diff --git a/sql/sql_repl.cc b/sql/sql_repl.cc index c220f609c09..dcbc982b4aa 100644 --- a/sql/sql_repl.cc +++ b/sql/sql_repl.cc @@ -357,6 +357,7 @@ void mysql_binlog_send(THD* thd, char* log_ident, my_off_t pos, #ifndef DBUG_OFF int left_events = max_binlog_dump_events; #endif + int old_max_allowed_packet= thd->variables.max_allowed_packet; DBUG_ENTER("mysql_binlog_send"); DBUG_PRINT("enter",("log_ident: '%s' pos: %ld", log_ident, (long) pos)); @@ -762,6 +763,7 @@ end: pthread_mutex_lock(&LOCK_thread_count); thd->current_linfo = 0; pthread_mutex_unlock(&LOCK_thread_count); + thd->variables.max_allowed_packet= old_max_allowed_packet; DBUG_VOID_RETURN; err: @@ -779,6 +781,7 @@ err: pthread_mutex_unlock(&LOCK_thread_count); if (file >= 0) (void) my_close(file, MYF(MY_WME)); + thd->variables.max_allowed_packet= old_max_allowed_packet; my_message(my_errno, errmsg, MYF(0)); DBUG_VOID_RETURN; @@ -1422,6 +1425,7 @@ bool mysql_show_binlog_events(THD* thd) bool ret = TRUE; IO_CACHE log; File file = -1; + int old_max_allowed_packet= thd->variables.max_allowed_packet; DBUG_ENTER("mysql_show_binlog_events"); Log_event::init_show_field_list(&field_list); @@ -1560,6 +1564,7 @@ err: pthread_mutex_lock(&LOCK_thread_count); thd->current_linfo = 0; pthread_mutex_unlock(&LOCK_thread_count); + thd->variables.max_allowed_packet= old_max_allowed_packet; DBUG_RETURN(ret); } From b0035c76d46caf25d6b52f4e1552c1e83f7f0911 Mon Sep 17 00:00:00 2001 From: Davi Arnaut Date: Tue, 20 Jul 2010 14:36:15 -0300 Subject: [PATCH 068/129] Bug#54453: Failing assertion: trx->active_trans when renaming a table with active trx Essentially, the problem is that InnoDB does a implicit commit when a cursor (table handler) is unlocked/closed, creating a dissonance between the transaction state within the server layer and the storage engine layer. Theoretically, a statement transaction can encompass several table instances in a similar manner to a multiple statement transaction, hence it does not make sense to limit a statement transaction to the lifetime of the table instances (cursors) used within it. Since this particular instance of the problem is only triggerable on 5.1 and is masked on 5.5 due 2PC being skipped (assertion is in the prepare phase of a 2PC), the solution (which is less risky) is to explicitly end the transaction before the cached table is unlock on rename table. The patch is to be null merged into trunk. mysql-test/include/commit.inc: Fix counters, the binlog engine does not get involved anymore. mysql-test/suite/innodb_plugin/r/innodb_bug54453.result: Add test case result for Bug#54453 mysql-test/suite/innodb_plugin/t/innodb_bug54453.test: Add test case for Bug#54453 sql/sql_table.cc: End transaction as otherwise InnoDB will end it behind our backs. --- mysql-test/include/commit.inc | 4 ++-- mysql-test/r/commit_1innodb.result | 4 ++-- .../suite/innodb_plugin/r/innodb_bug54453.result | 9 +++++++++ .../suite/innodb_plugin/t/innodb_bug54453.test | 15 +++++++++++++++ sql/sql_table.cc | 8 ++++++++ 5 files changed, 36 insertions(+), 4 deletions(-) create mode 100644 mysql-test/suite/innodb_plugin/r/innodb_bug54453.result create mode 100644 mysql-test/suite/innodb_plugin/t/innodb_bug54453.test diff --git a/mysql-test/include/commit.inc b/mysql-test/include/commit.inc index d91ba8291fd..d412eae8364 100644 --- a/mysql-test/include/commit.inc +++ b/mysql-test/include/commit.inc @@ -725,9 +725,9 @@ call p_verify_status_increment(4, 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(2, 2, 2, 2); +call p_verify_status_increment(1, 0, 1, 0); rename table t4 to t3; -call p_verify_status_increment(2, 2, 2, 2); +call p_verify_status_increment(1, 0, 1, 0); truncate table t3; call p_verify_status_increment(4, 4, 4, 4); create view v1 as select * from t2; diff --git a/mysql-test/r/commit_1innodb.result b/mysql-test/r/commit_1innodb.result index 51c4ac3002c..1f0b2c8019b 100644 --- a/mysql-test/r/commit_1innodb.result +++ b/mysql-test/r/commit_1innodb.result @@ -841,11 +841,11 @@ call p_verify_status_increment(2, 0, 2, 0); SUCCESS alter table t3 rename t4; -call p_verify_status_increment(2, 2, 2, 2); +call p_verify_status_increment(1, 0, 1, 0); SUCCESS rename table t4 to t3; -call p_verify_status_increment(2, 2, 2, 2); +call p_verify_status_increment(1, 0, 1, 0); SUCCESS truncate table t3; diff --git a/mysql-test/suite/innodb_plugin/r/innodb_bug54453.result b/mysql-test/suite/innodb_plugin/r/innodb_bug54453.result new file mode 100644 index 00000000000..e623989a9d4 --- /dev/null +++ b/mysql-test/suite/innodb_plugin/r/innodb_bug54453.result @@ -0,0 +1,9 @@ +# +# Bug#54453: Failing assertion: trx->active_trans when renaming a table with active trx +# +DROP TABLE IF EXISTS bug54453; +CREATE TABLE bug54453(a INT) ENGINE=InnoDB; +ALTER TABLE bug54453 RENAME TO bug54453_2; +SELECT * FROM bug54453_2; +a +DROP TABLE bug54453_2; diff --git a/mysql-test/suite/innodb_plugin/t/innodb_bug54453.test b/mysql-test/suite/innodb_plugin/t/innodb_bug54453.test new file mode 100644 index 00000000000..486695d326d --- /dev/null +++ b/mysql-test/suite/innodb_plugin/t/innodb_bug54453.test @@ -0,0 +1,15 @@ +--source include/have_innodb_plugin.inc +--source include/have_log_bin.inc + +--echo # +--echo # Bug#54453: Failing assertion: trx->active_trans when renaming a table with active trx +--echo # + +--disable_warnings +DROP TABLE IF EXISTS bug54453; +--enable_warnings + +CREATE TABLE bug54453(a INT) ENGINE=InnoDB; +ALTER TABLE bug54453 RENAME TO bug54453_2; +SELECT * FROM bug54453_2; +DROP TABLE bug54453_2; diff --git a/sql/sql_table.cc b/sql/sql_table.cc index 50045ec6d90..47b91fcca0e 100644 --- a/sql/sql_table.cc +++ b/sql/sql_table.cc @@ -6848,6 +6848,14 @@ view_err: if (!error && (new_name != table_name || new_db != db)) { thd_proc_info(thd, "rename"); + + /* + Workaround InnoDB ending the transaction when the table instance + is unlocked/closed (close_cached_table below), otherwise the trx + state will differ between the server and storage engine layers. + */ + ha_autocommit_or_rollback(thd, 0); + /* Then do a 'simple' rename of the table. First we need to close all instances of 'source' table. From c36fee08f6fa7974324438572a260101335cb4b4 Mon Sep 17 00:00:00 2001 From: Davi Arnaut Date: Tue, 20 Jul 2010 14:44:29 -0300 Subject: [PATCH 069/129] Bug#52514: mysql 5.1 do_abi_check does not compile w/ gcc4.5 due to GCC preprocessor change The problem is that newer GCC versions treats missing headers as fatal errors. The solution is to use a guard macro to prevent the inclusion of system headers when checking the ABI with the C Preprocessor. Reference: http://gcc.gnu.org/bugzilla/show_bug.cgi?id=15638 http://gcc.gnu.org/bugzilla/show_bug.cgi?id=44836 Makefile.am: Define guard macro. configure.in: Remove workaround. include/mysql.h: Guard the header inclusion. include/mysql.h.pp: Header is not included anymore. --- Makefile.am | 2 +- configure.in | 11 +---------- include/mysql.h | 2 ++ include/mysql.h.pp | 1 - 4 files changed, 4 insertions(+), 12 deletions(-) diff --git a/Makefile.am b/Makefile.am index 7953b81fb7b..4ce753ad8aa 100644 --- a/Makefile.am +++ b/Makefile.am @@ -314,7 +314,7 @@ abi_check_all: $(TEST_PREPROCESSOR_HEADER) do_abi_check: set -ex; \ for file in $(abi_headers); do \ - @CC@ -E -nostdinc -dI \ + @CC@ -E -nostdinc -dI -DMYSQL_ABI_CHECK \ -I$(top_srcdir)/include \ -I$(top_srcdir)/include/mysql \ -I$(top_srcdir)/sql \ diff --git a/configure.in b/configure.in index 0264c351b07..8dcdecf8ea2 100644 --- a/configure.in +++ b/configure.in @@ -444,16 +444,7 @@ if test "$GCC" != "yes" || expr "$CC" : ".*icc.*" then ABI_CHECK="" else - # Workaround GCC >= 4.5 - See Bug#52514 - case `$CC -dumpversion` in - [[4-9]].[[5-9]]*) - AC_MSG_WARN([ABI check disabled (GCC >= 4.5)]) - ABI_CHECK="" - ;; - *) - ABI_CHECK="abi_check" - ;; - esac + ABI_CHECK="abi_check" fi AC_SUBST(ABI_CHECK) diff --git a/include/mysql.h b/include/mysql.h index d114afb6c93..dcf3e167e6a 100644 --- a/include/mysql.h +++ b/include/mysql.h @@ -44,7 +44,9 @@ extern "C" { #endif #ifndef _global_h /* If not standard header */ +#ifndef MYSQL_ABI_CHECK #include +#endif #ifdef __LCC__ #include /* For windows */ #endif diff --git a/include/mysql.h.pp b/include/mysql.h.pp index 633cde41130..0a397863022 100644 --- a/include/mysql.h.pp +++ b/include/mysql.h.pp @@ -1,4 +1,3 @@ -#include typedef char my_bool; typedef int my_socket; #include "mysql_version.h" From 774194634297aebf6ecbbda7c5601c796f43e5fc Mon Sep 17 00:00:00 2001 From: Davi Arnaut Date: Tue, 20 Jul 2010 14:55:16 -0300 Subject: [PATCH 070/129] Fix tree name. --- .bzr-mysql/default.conf | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.bzr-mysql/default.conf b/.bzr-mysql/default.conf index 4eab3d239d0..658c8ba845b 100644 --- a/.bzr-mysql/default.conf +++ b/.bzr-mysql/default.conf @@ -1,4 +1,4 @@ [MYSQL] post_commit_to = "commits@lists.mysql.com" post_push_to = "commits@lists.mysql.com" -tree_name = "mysql-trunk-bugfixing" +tree_name = "mysql-trunk-merge" From 9a5fa17fd3c4885262e31bf14cf495d02e5f6b27 Mon Sep 17 00:00:00 2001 From: Davi Arnaut Date: Tue, 20 Jul 2010 15:07:36 -0300 Subject: [PATCH 071/129] Bug#45288: pb2 returns a lot of compilation warnings on linux Fix warnings flagged by the new warning option -Wunused-but-set-variable that was added to GCC 4.6 and that is enabled by -Wunused and -Wall. The option causes a warning whenever a local variable is assigned to but is later unused. It also warns about meaningless pointer dereferences. client/mysql.cc: Meaningless pointer dereferences. client/mysql_upgrade.c: Check whether reading from the file succeeded. extra/comp_err.c: Unused. extra/yassl/src/yassl_imp.cpp: Skip instead of reading data that is discarded. include/my_pthread.h: Variable is only used in debug builds. include/mysys_err.h: Add new error messages. mysys/errors.c: Add new error message for permission related functions. mysys/mf_iocache.c: Variable is only checked under THREAD. mysys/my_copy.c: Raise a error if chmod or chown fails. mysys/my_redel.c: Raise a error if chmod or chown fails. regex/engine.c: Use a equivalent variable for the assert. server-tools/instance-manager/instance_options.cc: Unused. sql/field.cc: Unused. sql/item.cc: Unused. sql/log.cc: Do not ignore the return value of freopen: only set buffer if reopening succeeds. Adjust doxygen comment to the right function. Pass message lenght to log function. sql/mysqld.cc: Do not ignore the return value of freopen: only set buffer if reopening succeeds. sql/partition_info.cc: Unused. sql/slave.cc: No need to set pointer to the address of '\0'. sql/spatial.cc: Unused. Left for historical purposes. sql/sql_acl.cc: Unused. sql/sql_base.cc: Pointers are always set to the same variables. sql/sql_parse.cc: End statement if reading fails. Store the buffer after it has actually been updated. sql/sql_repl.cc: No need to set pointer to the address of '\0'. sql/sql_show.cc: Put variable under the same ifdef block. sql/udf_example.c: Set null pointer flag appropriately. storage/csv/ha_tina.cc: Meaningless dereferences. storage/example/ha_example.cc: Return the error since it's available. storage/myisam/mi_locking.c: Remove unused and dead code. --- client/mysql.cc | 4 +- client/mysql_upgrade.c | 5 +- extra/comp_err.c | 2 - extra/yassl/src/yassl_imp.cpp | 24 ++---- include/my_pthread.h | 5 +- include/mysys_err.h | 4 +- mysys/errors.c | 6 +- mysys/mf_iocache.c | 11 ++- mysys/my_copy.c | 20 ++++- mysys/my_redel.c | 24 ++++-- regex/engine.c | 17 ++--- .../instance-manager/instance_options.cc | 3 - sql/field.cc | 2 - sql/item.cc | 7 +- sql/log.cc | 73 ++++++++++--------- sql/mysqld.cc | 7 +- sql/partition_info.cc | 2 - sql/slave.cc | 7 +- sql/spatial.cc | 3 +- sql/sql_acl.cc | 2 - sql/sql_base.cc | 14 +--- sql/sql_load.cc | 13 ++-- sql/sql_parse.cc | 17 +++-- sql/sql_repl.cc | 7 +- sql/sql_show.cc | 4 +- sql/sql_table.cc | 2 - sql/table.cc | 3 +- sql/udf_example.c | 2 +- storage/csv/ha_tina.cc | 12 +-- storage/example/ha_example.cc | 2 +- storage/myisam/mi_locking.c | 14 +--- storage/myisam/rt_split.c | 3 - storage/myisammrg/myrg_open.c | 5 -- strings/decimal.c | 3 +- 34 files changed, 155 insertions(+), 174 deletions(-) diff --git a/client/mysql.cc b/client/mysql.cc index edcc72b60bf..5b90f318629 100644 --- a/client/mysql.cc +++ b/client/mysql.cc @@ -3639,7 +3639,7 @@ xmlencode_print(const char *src, uint length) tee_fputs("NULL", PAGER); else { - for (const char *p = src; length; *p++, length--) + for (const char *p = src; length; p++, length--) { const char *t; if ((t = array_value(xmlmeta, *p))) @@ -4726,7 +4726,7 @@ static const char* construct_prompt() struct tm *t = localtime(&lclock); /* parse thru the settings for the prompt */ - for (char *c = current_prompt; *c ; *c++) + for (char *c = current_prompt; *c ; c++) { if (*c != PROMPT_CHAR) processed_prompt.append(*c); diff --git a/client/mysql_upgrade.c b/client/mysql_upgrade.c index 0b8b43775ed..3122cc25731 100644 --- a/client/mysql_upgrade.c +++ b/client/mysql_upgrade.c @@ -595,7 +595,10 @@ static int upgrade_already_done(void) my_fclose(in, MYF(0)); - return (strncmp(buf, MYSQL_SERVER_VERSION, + if (!res) + return 0; /* Could not read from file => not sure */ + + return (strncmp(res, MYSQL_SERVER_VERSION, sizeof(MYSQL_SERVER_VERSION)-1)==0); } diff --git a/extra/comp_err.c b/extra/comp_err.c index c02c7ca3d2a..7e0b47a7dc7 100644 --- a/extra/comp_err.c +++ b/extra/comp_err.c @@ -831,7 +831,6 @@ static struct message *parse_message_string(struct message *new_message, static struct errors *parse_error_string(char *str, int er_count) { struct errors *new_error; - char *start; DBUG_ENTER("parse_error_string"); DBUG_PRINT("enter", ("str: %s", str)); @@ -842,7 +841,6 @@ static struct errors *parse_error_string(char *str, int er_count) DBUG_RETURN(0); /* OOM: Fatal error */ /* getting the error name */ - start= str; str= skip_delimiters(str); if (!(new_error->er_name= get_word(&str))) diff --git a/extra/yassl/src/yassl_imp.cpp b/extra/yassl/src/yassl_imp.cpp index f079df8c7ce..86799f961ae 100644 --- a/extra/yassl/src/yassl_imp.cpp +++ b/extra/yassl/src/yassl_imp.cpp @@ -884,21 +884,19 @@ void Alert::Process(input_buffer& input, SSL& ssl) else hmac(ssl, verify, data, aSz, alert, true); - // read mac and fill + // read mac and skip fill int digestSz = ssl.getCrypto().get_digest().get_digestSize(); opaque mac[SHA_LEN]; input.read(mac, digestSz); if (ssl.getSecurity().get_parms().cipher_type_ == block) { int ivExtra = 0; - opaque fill; if (ssl.isTLSv1_1()) ivExtra = ssl.getCrypto().get_cipher().get_blockSize(); int padSz = ssl.getSecurity().get_parms().encrypt_size_ - ivExtra - aSz - digestSz; - for (int i = 0; i < padSz; i++) - fill = input[AUTO]; + input.set_current(input.get_current() + padSz); } // verify @@ -981,17 +979,17 @@ output_buffer& operator<<(output_buffer& output, const Data& data) void Data::Process(input_buffer& input, SSL& ssl) { int msgSz = ssl.getSecurity().get_parms().encrypt_size_; - int pad = 0, padByte = 0; + int pad = 0, padSz = 0; int ivExtra = 0; if (ssl.getSecurity().get_parms().cipher_type_ == block) { if (ssl.isTLSv1_1()) // IV ivExtra = ssl.getCrypto().get_cipher().get_blockSize(); pad = *(input.get_buffer() + input.get_current() + msgSz -ivExtra - 1); - padByte = 1; + padSz = 1; } int digestSz = ssl.getCrypto().get_digest().get_digestSize(); - int dataSz = msgSz - ivExtra - digestSz - pad - padByte; + int dataSz = msgSz - ivExtra - digestSz - pad - padSz; opaque verify[SHA_LEN]; const byte* rawData = input.get_buffer() + input.get_current(); @@ -1020,14 +1018,10 @@ void Data::Process(input_buffer& input, SSL& ssl) hmac(ssl, verify, rawData, dataSz, application_data, true); } - // read mac and fill + // read mac and skip fill opaque mac[SHA_LEN]; - opaque fill; input.read(mac, digestSz); - for (int i = 0; i < pad; i++) - fill = input[AUTO]; - if (padByte) - fill = input[AUTO]; + input.set_current(input.get_current() + pad + padSz); // verify if (dataSz) { @@ -2073,11 +2067,9 @@ void Finished::Process(input_buffer& input, SSL& ssl) if (ssl.isTLSv1_1()) ivExtra = ssl.getCrypto().get_cipher().get_blockSize(); - opaque fill; int padSz = ssl.getSecurity().get_parms().encrypt_size_ - ivExtra - HANDSHAKE_HEADER - finishedSz - digestSz; - for (int i = 0; i < padSz; i++) - fill = input[AUTO]; + input.set_current(input.get_current() + padSz); // verify mac if (memcmp(mac, verifyMAC, digestSz)) { diff --git a/include/my_pthread.h b/include/my_pthread.h index eff6a677192..fec7c972a7b 100644 --- a/include/my_pthread.h +++ b/include/my_pthread.h @@ -269,13 +269,14 @@ int sigwait(sigset_t *setp, int *sigp); /* Use our implemention */ we want to make sure that no such flags are set. */ #if defined(HAVE_SIGACTION) && !defined(my_sigset) -#define my_sigset(A,B) do { struct sigaction l_s; sigset_t l_set; int l_rc; \ +#define my_sigset(A,B) do { struct sigaction l_s; sigset_t l_set; \ + IF_DBUG(int l_rc); \ DBUG_ASSERT((A) != 0); \ sigemptyset(&l_set); \ l_s.sa_handler = (B); \ l_s.sa_mask = l_set; \ l_s.sa_flags = 0; \ - l_rc= sigaction((A), &l_s, (struct sigaction *) NULL);\ + IF_DBUG(l_rc=) sigaction((A), &l_s, NULL); \ DBUG_ASSERT(l_rc == 0); \ } while (0) #elif defined(HAVE_SIGSET) && !defined(my_sigset) diff --git a/include/mysys_err.h b/include/mysys_err.h index 09e77248c17..6294b37f773 100644 --- a/include/mysys_err.h +++ b/include/mysys_err.h @@ -62,7 +62,9 @@ extern const char * NEAR globerrs[]; /* my_error_messages is here */ #define EE_UNKNOWN_COLLATION 28 #define EE_FILENOTFOUND 29 #define EE_FILE_NOT_CLOSED 30 -#define EE_ERROR_LAST 30 /* Copy last error nr */ +#define EE_CHANGE_OWNERSHIP 31 +#define EE_CHANGE_PERMISSIONS 32 +#define EE_ERROR_LAST 32 /* Copy last error nr */ /* Add error numbers before EE_ERROR_LAST and change it accordingly. */ /* exit codes for all MySQL programs */ diff --git a/mysys/errors.c b/mysys/errors.c index 8d3303cac9f..a5ad4a956ab 100644 --- a/mysys/errors.c +++ b/mysys/errors.c @@ -49,7 +49,9 @@ const char * NEAR globerrs[GLOBERRS]= "Can't sync file '%s' to disk (Errcode: %d)", "Collation '%s' is not a compiled collation and is not specified in the '%s' file", "File '%s' not found (Errcode: %d)", - "File '%s' (fileno: %d) was not closed" + "File '%s' (fileno: %d) was not closed", + "Can't change ownership of the file '%s' (Errcode: %d)", + "Can't change permissions of the file '%s' (Errcode: %d)", }; void init_glob_errs(void) @@ -90,6 +92,8 @@ void init_glob_errs() EE(EE_UNKNOWN_COLLATION)= "Collation '%s' is not a compiled collation and is not specified in the %s file"; EE(EE_FILENOTFOUND) = "File '%s' not found (Errcode: %d)"; EE(EE_FILE_NOT_CLOSED) = "File '%s' (fileno: %d) was not closed"; + EE(EE_CHANGE_OWNERSHIP) = "Can't change ownership of the file '%s' (Errcode: %d)"; + EE(EE_CHANGE_PERMISSIONS) = "Can't change permissions of the file '%s' (Errcode: %d)"; } #endif diff --git a/mysys/mf_iocache.c b/mysys/mf_iocache.c index 1a47982b221..e9b947b04a6 100644 --- a/mysys/mf_iocache.c +++ b/mysys/mf_iocache.c @@ -1701,16 +1701,19 @@ int my_block_write(register IO_CACHE *info, const uchar *Buffer, size_t Count, #endif -int my_b_flush_io_cache(IO_CACHE *info, int need_append_buffer_lock) +int my_b_flush_io_cache(IO_CACHE *info, + int need_append_buffer_lock __attribute__((unused))) { size_t length; - my_bool append_cache; my_off_t pos_in_file; + my_bool append_cache= (info->type == SEQ_READ_APPEND); DBUG_ENTER("my_b_flush_io_cache"); DBUG_PRINT("enter", ("cache: 0x%lx", (long) info)); - if (!(append_cache = (info->type == SEQ_READ_APPEND))) - need_append_buffer_lock=0; +#ifdef THREAD + if (!append_cache) + need_append_buffer_lock= 0; +#endif if (info->type == WRITE_CACHE || append_cache) { diff --git a/mysys/my_copy.c b/mysys/my_copy.c index 418e2b6f8a2..d0c1fc29229 100644 --- a/mysys/my_copy.c +++ b/mysys/my_copy.c @@ -16,6 +16,7 @@ #include "mysys_priv.h" #include /* for stat */ #include +#include "mysys_err.h" #if defined(HAVE_UTIME_H) #include #elif defined(HAVE_SYS_UTIME_H) @@ -56,7 +57,6 @@ int my_copy(const char *from, const char *to, myf MyFlags) File from_file,to_file; uchar buff[IO_SIZE]; MY_STAT stat_buff,new_stat_buff; - int res; DBUG_ENTER("my_copy"); DBUG_PRINT("my",("from %s to %s MyFlags %d", from, to, MyFlags)); @@ -102,9 +102,23 @@ int my_copy(const char *from, const char *to, myf MyFlags) if (MyFlags & MY_HOLD_ORIGINAL_MODES && !new_file_stat) DBUG_RETURN(0); /* File copyed but not stat */ - res= chmod(to, stat_buff.st_mode & 07777); /* Copy modes */ + /* Copy modes */ + if (chmod(to, stat_buff.st_mode & 07777)) + { + my_errno= errno; + if (MyFlags & (MY_FAE+MY_WME)) + my_error(EE_CHANGE_PERMISSIONS, MYF(ME_BELL+ME_WAITTANG), from, errno); + goto err; + } #if !defined(__WIN__) && !defined(__NETWARE__) - res= chown(to, stat_buff.st_uid,stat_buff.st_gid); /* Copy ownership */ + /* Copy ownership */ + if (chown(to, stat_buff.st_uid,stat_buff.st_gid)) + { + my_errno= errno; + if (MyFlags & (MY_FAE+MY_WME)) + my_error(EE_CHANGE_OWNERSHIP, MYF(ME_BELL+ME_WAITTANG), from, errno); + goto err; + } #endif #if !defined(VMS) && !defined(__ZTC__) if (MyFlags & MY_COPYTIME) diff --git a/mysys/my_redel.c b/mysys/my_redel.c index 6521253f949..4013c5c8323 100644 --- a/mysys/my_redel.c +++ b/mysys/my_redel.c @@ -76,11 +76,8 @@ end: int my_copystat(const char *from, const char *to, int MyFlags) { struct stat statbuf; -#if !defined(__WIN__) && !defined(__NETWARE__) - int res; -#endif - if (stat((char*) from, &statbuf)) + if (stat(from, &statbuf)) { my_errno=errno; if (MyFlags & (MY_FAE+MY_WME)) @@ -89,7 +86,15 @@ int my_copystat(const char *from, const char *to, int MyFlags) } if ((statbuf.st_mode & S_IFMT) != S_IFREG) return 1; - VOID(chmod(to, statbuf.st_mode & 07777)); /* Copy modes */ + + /* Copy modes */ + if (chmod(to, statbuf.st_mode & 07777)) + { + my_errno= errno; + if (MyFlags & (MY_FAE+MY_WME)) + my_error(EE_CHANGE_PERMISSIONS, MYF(ME_BELL+ME_WAITTANG), from, errno); + return -1; + } #if !defined(__WIN__) && !defined(__NETWARE__) if (statbuf.st_nlink > 1 && MyFlags & MY_LINK_WARNING) @@ -97,7 +102,14 @@ int my_copystat(const char *from, const char *to, int MyFlags) if (MyFlags & MY_LINK_WARNING) my_error(EE_LINK_WARNING,MYF(ME_BELL+ME_WAITTANG),from,statbuf.st_nlink); } - res= chown(to, statbuf.st_uid, statbuf.st_gid); /* Copy ownership */ + /* Copy ownership */ + if (chown(to, statbuf.st_uid, statbuf.st_gid)) + { + my_errno= errno; + if (MyFlags & (MY_FAE+MY_WME)) + my_error(EE_CHANGE_OWNERSHIP, MYF(ME_BELL+ME_WAITTANG), from, errno); + return -1; + } #endif /* !__WIN__ && !__NETWARE__ */ #ifndef VMS diff --git a/regex/engine.c b/regex/engine.c index 1968ca61a96..be08adf8601 100644 --- a/regex/engine.c +++ b/regex/engine.c @@ -256,7 +256,6 @@ sopno stopst; register char *ssp; /* start of string matched by subsubRE */ register char *sep; /* end of string matched by subsubRE */ register char *oldssp; /* previous ssp */ - register char *dp; /* used in debug mode to check asserts */ AT("diss", start, stop, startst, stopst); sp = start; @@ -314,11 +313,9 @@ sopno stopst; ssub = ss + 1; esub = es - 1; /* did innards match? */ - if (slow(charset, m, sp, rest, ssub, esub) != NULL) { - dp = dissect(charset, m, sp, rest, ssub, esub); - assert(dp == rest); - } else /* no */ - assert(sp == rest); + if (slow(charset, m, sp, rest, ssub, esub) != NULL) + sp = dissect(charset, m, sp, rest, ssub, esub); + assert(sp == rest); sp = rest; break; case OPLUS_: @@ -353,8 +350,8 @@ sopno stopst; } assert(sep == rest); /* must exhaust substring */ assert(slow(charset, m, ssp, sep, ssub, esub) == rest); - dp = dissect(charset, m, ssp, sep, ssub, esub); - assert(dp == sep); + sp = dissect(charset, m, ssp, sep, ssub, esub); + assert(sp == sep); sp = rest; break; case OCH_: @@ -388,8 +385,8 @@ sopno stopst; else assert(OP(m->g->strip[esub]) == O_CH); } - dp = dissect(charset, m, sp, rest, ssub, esub); - assert(dp == rest); + sp = dissect(charset, m, sp, rest, ssub, esub); + assert(sp == rest); sp = rest; break; case O_PLUS: diff --git a/server-tools/instance-manager/instance_options.cc b/server-tools/instance-manager/instance_options.cc index 8b96d6f0f96..725089e2f42 100644 --- a/server-tools/instance-manager/instance_options.cc +++ b/server-tools/instance-manager/instance_options.cc @@ -303,7 +303,6 @@ bool Instance_options::fill_log_options() enum { MAX_LOG_OPTION_LENGTH= 256 }; char datadir[MAX_LOG_OPTION_LENGTH]; char hostname[MAX_LOG_OPTION_LENGTH]; - uint hostname_length; struct log_files_st { const char *name; @@ -335,8 +334,6 @@ bool Instance_options::fill_log_options() strmov(hostname, "mysql"); hostname[MAX_LOG_OPTION_LENGTH - 1]= 0; /* Safety */ - hostname_length= strlen(hostname); - for (log_files= logs_st; log_files->name; log_files++) { diff --git a/sql/field.cc b/sql/field.cc index c648b53e139..c887a5f1c9b 100644 --- a/sql/field.cc +++ b/sql/field.cc @@ -5541,7 +5541,6 @@ int Field_date::store(const char *from, uint len,CHARSET_INFO *cs) int Field_date::store(double nr) { longlong tmp; - int error= 0; if (nr >= 19000000000000.0 && nr <= 99991231235959.0) nr=floor(nr/1000000.0); // Timestamp to date if (nr < 0.0 || nr > 99991231.0) @@ -5550,7 +5549,6 @@ int Field_date::store(double nr) set_datetime_warning(MYSQL_ERROR::WARN_LEVEL_WARN, ER_WARN_DATA_OUT_OF_RANGE, nr, MYSQL_TIMESTAMP_DATE); - error= 1; } else tmp= (longlong) rint(nr); diff --git a/sql/item.cc b/sql/item.cc index db2c4c0974b..66c5314c16e 100644 --- a/sql/item.cc +++ b/sql/item.cc @@ -255,11 +255,10 @@ my_decimal *Item::val_decimal_from_int(my_decimal *decimal_value) my_decimal *Item::val_decimal_from_string(my_decimal *decimal_value) { String *res; - char *end_ptr; - if (!(res= val_str(&str_value))) - return 0; // NULL or EOM - end_ptr= (char*) res->ptr()+ res->length(); + if (!(res= val_str(&str_value))) + return NULL; + if (str2my_decimal(E_DEC_FATAL_ERROR & ~E_DEC_BAD_NUM, res->ptr(), res->length(), res->charset(), decimal_value) & E_DEC_BAD_NUM) diff --git a/sql/log.cc b/sql/log.cc index d8d5f6fa418..614a07e6b63 100644 --- a/sql/log.cc +++ b/sql/log.cc @@ -5050,6 +5050,22 @@ void sql_perror(const char *message) } +/* + Unfortunately, there seems to be no good way + to restore the original streams upon failure. +*/ +static bool redirect_std_streams(const char *file) +{ + if (freopen(file, "a+", stdout) && freopen(file, "a+", stderr)) + { + setbuf(stderr, NULL); + return FALSE; + } + + return TRUE; +} + + bool flush_error_log() { bool result=0; @@ -5077,11 +5093,7 @@ bool flush_error_log() setbuf(stderr, NULL); (void) my_delete(err_renamed, MYF(0)); my_rename(log_error_file,err_renamed,MYF(0)); - if (freopen(log_error_file,"a+",stdout)) - { - freopen(log_error_file,"a+",stderr); - setbuf(stderr, NULL); - } + redirect_std_streams(log_error_file); if ((fd = my_open(err_temp, O_RDONLY, MYF(0))) >= 0) { @@ -5096,13 +5108,7 @@ bool flush_error_log() result= 1; #else my_rename(log_error_file,err_renamed,MYF(0)); - if (freopen(log_error_file,"a+",stdout)) - { - FILE *reopen; - reopen= freopen(log_error_file,"a+",stderr); - setbuf(stderr, NULL); - } - else + if (redirect_std_streams(log_error_file)) result= 1; #endif VOID(pthread_mutex_unlock(&LOCK_error_log)); @@ -5153,25 +5159,9 @@ static void print_buffer_to_nt_eventlog(enum loglevel level, char *buff, #endif /* __NT__ */ -/** - Prints a printf style message to the error log and, under NT, to the - Windows event log. - - This function prints the message into a buffer and then sends that buffer - to other functions to write that message to other logging sources. - - @param event_type Type of event to write (Error, Warning, or Info) - @param format Printf style format of message - @param args va_list list of arguments for the message - - @returns - The function always returns 0. The return value is present in the - signature to be compatible with other logging routines, which could - return an error (e.g. logging to the log tables) -*/ - #ifndef EMBEDDED_LIBRARY -static void print_buffer_to_file(enum loglevel level, const char *buffer) +static void print_buffer_to_file(enum loglevel level, const char *buffer, + size_t length) { time_t skr; struct tm tm_tmp; @@ -5185,7 +5175,7 @@ static void print_buffer_to_file(enum loglevel level, const char *buffer) localtime_r(&skr, &tm_tmp); start=&tm_tmp; - fprintf(stderr, "%02d%02d%02d %2d:%02d:%02d [%s] %s\n", + fprintf(stderr, "%02d%02d%02d %2d:%02d:%02d [%s] %.*s\n", start->tm_year % 100, start->tm_mon+1, start->tm_mday, @@ -5194,7 +5184,7 @@ static void print_buffer_to_file(enum loglevel level, const char *buffer) start->tm_sec, (level == ERROR_LEVEL ? "ERROR" : level == WARNING_LEVEL ? "Warning" : "Note"), - buffer); + (int) length, buffer); fflush(stderr); @@ -5202,7 +5192,22 @@ static void print_buffer_to_file(enum loglevel level, const char *buffer) DBUG_VOID_RETURN; } +/** + Prints a printf style message to the error log and, under NT, to the + Windows event log. + This function prints the message into a buffer and then sends that buffer + to other functions to write that message to other logging sources. + + @param level The level of the msg significance + @param format Printf style format of message + @param args va_list list of arguments for the message + + @returns + The function always returns 0. The return value is present in the + signature to be compatible with other logging routines, which could + return an error (e.g. logging to the log tables) +*/ int vprint_msg_to_log(enum loglevel level, const char *format, va_list args) { char buff[1024]; @@ -5210,7 +5215,7 @@ int vprint_msg_to_log(enum loglevel level, const char *format, va_list args) DBUG_ENTER("vprint_msg_to_log"); length= my_vsnprintf(buff, sizeof(buff), format, args); - print_buffer_to_file(level, buff); + print_buffer_to_file(level, buff, length); #ifdef __NT__ print_buffer_to_nt_eventlog(level, buff, length, sizeof(buff)); @@ -5218,7 +5223,7 @@ int vprint_msg_to_log(enum loglevel level, const char *format, va_list args) DBUG_RETURN(0); } -#endif /*EMBEDDED_LIBRARY*/ +#endif /* EMBEDDED_LIBRARY */ void sql_print_error(const char *format, ...) diff --git a/sql/mysqld.cc b/sql/mysqld.cc index 99f16b36dfa..fda64e5a1ea 100644 --- a/sql/mysqld.cc +++ b/sql/mysqld.cc @@ -3783,7 +3783,6 @@ static void end_ssl() static int init_server_components() { - FILE* reopen; DBUG_ENTER("init_server_components"); /* We need to call each of these following functions to ensure that @@ -3826,8 +3825,8 @@ static int init_server_components() if (freopen(log_error_file, "a+", stdout)) #endif { - reopen= freopen(log_error_file, "a+", stderr); - setbuf(stderr, NULL); + if (freopen(log_error_file, "a+", stderr)) + setbuf(stderr, NULL); } } } @@ -8222,7 +8221,7 @@ mysqld_get_one_option(int optid, *val= 0; val+= 2; while (*val && my_isspace(mysqld_charset, *val)) - *val++; + val++; if (!*val) { sql_print_error("Bad syntax in replicate-rewrite-db - empty TO db!\n"); diff --git a/sql/partition_info.cc b/sql/partition_info.cc index d85888e295c..f37151ea51d 100644 --- a/sql/partition_info.cc +++ b/sql/partition_info.cc @@ -1206,13 +1206,11 @@ bool partition_info::set_up_charset_field_preps() i= 0; while ((field= *(ptr++))) { - CHARSET_INFO *cs; uchar *field_buf; LINT_INIT(field_buf); if (!field_is_partition_charset(field)) continue; - cs= ((Field_str*)field)->charset(); size= field->pack_length(); if (!(field_buf= (uchar*) sql_calloc(size))) goto error; diff --git a/sql/slave.cc b/sql/slave.cc index 795bc481071..f1e0962e7e8 100644 --- a/sql/slave.cc +++ b/sql/slave.cc @@ -3035,11 +3035,8 @@ log '%s' at position %s, relay log '%s' position: %s", RPL_LOG_NAME, pthread_mutex_lock(&rli->data_lock); if (rli->slave_skip_counter) { - char *pos; - pos= strmake(saved_log_name, rli->group_relay_log_name, FN_REFLEN - 1); - pos= '\0'; - pos= strmake(saved_master_log_name, rli->group_master_log_name, FN_REFLEN - 1); - pos= '\0'; + strmake(saved_log_name, rli->group_relay_log_name, FN_REFLEN - 1); + strmake(saved_master_log_name, rli->group_master_log_name, FN_REFLEN - 1); saved_log_pos= rli->group_relay_log_pos; saved_master_log_pos= rli->group_master_log_pos; saved_skip= rli->slave_skip_counter; diff --git a/sql/spatial.cc b/sql/spatial.cc index 11df6c00dc5..2305a8eb97d 100644 --- a/sql/spatial.cc +++ b/sql/spatial.cc @@ -159,11 +159,10 @@ Geometry *Geometry::construct(Geometry_buffer *buffer, { uint32 geom_type; Geometry *result; - char byte_order; if (data_len < SRID_SIZE + WKB_HEADER_SIZE) // < 4 + (1 + 4) return NULL; - byte_order= data[SRID_SIZE]; + /* + 1 to skip the byte order (stored in position SRID_SIZE). */ geom_type= uint4korr(data + SRID_SIZE + 1); if (!(result= create_by_typeid(buffer, (int) geom_type))) return NULL; diff --git a/sql/sql_acl.cc b/sql/sql_acl.cc index 90eef872115..b507b70d1fb 100644 --- a/sql/sql_acl.cc +++ b/sql/sql_acl.cc @@ -5701,7 +5701,6 @@ bool mysql_create_user(THD *thd, List &list) { int result; String wrong_users; - ulong sql_mode; LEX_USER *user_name, *tmp_user_name; List_iterator user_list(list); TABLE_LIST tables[GRANT_TABLES]; @@ -5748,7 +5747,6 @@ bool mysql_create_user(THD *thd, List &list) } some_users_created= TRUE; - sql_mode= thd->variables.sql_mode; if (replace_user_table(thd, tables[0].table, *user_name, 0, 0, 1, 0)) { append_user(&wrong_users, user_name); diff --git a/sql/sql_base.cc b/sql/sql_base.cc index d2392bdd9b1..c38526a6d0b 100644 --- a/sql/sql_base.cc +++ b/sql/sql_base.cc @@ -5674,7 +5674,7 @@ static void update_field_dependencies(THD *thd, Field *field, TABLE *table) DBUG_ENTER("update_field_dependencies"); if (thd->mark_used_columns != MARK_COLUMNS_NONE) { - MY_BITMAP *current_bitmap, *other_bitmap; + MY_BITMAP *bitmap; /* We always want to register the used keys, as the column bitmap may have @@ -5685,15 +5685,9 @@ static void update_field_dependencies(THD *thd, Field *field, TABLE *table) table->merge_keys.merge(field->part_of_key); if (thd->mark_used_columns == MARK_COLUMNS_READ) - { - current_bitmap= table->read_set; - other_bitmap= table->write_set; - } + bitmap= table->read_set; else - { - current_bitmap= table->write_set; - other_bitmap= table->read_set; - } + bitmap= table->write_set; /* The test-and-set mechanism in the bitmap is not reliable during @@ -5702,7 +5696,7 @@ static void update_field_dependencies(THD *thd, Field *field, TABLE *table) only those columns that are used in the SET clause. I.e they are being set here. See multi_update::prepare() */ - if (bitmap_fast_test_and_set(current_bitmap, field->field_index)) + if (bitmap_fast_test_and_set(bitmap, field->field_index)) { if (thd->mark_used_columns == MARK_COLUMNS_WRITE) { diff --git a/sql/sql_load.cc b/sql/sql_load.cc index ee7481234a4..a4cf46b35e8 100644 --- a/sql/sql_load.cc +++ b/sql/sql_load.cc @@ -128,6 +128,7 @@ int mysql_load(THD *thd,sql_exchange *ex,TABLE_LIST *table_list, bool is_fifo=0; #ifndef EMBEDDED_LIBRARY LOAD_FILE_INFO lf_info; + THD::killed_state killed_status; #endif char *db = table_list->db; // This is never null /* @@ -138,7 +139,6 @@ int mysql_load(THD *thd,sql_exchange *ex,TABLE_LIST *table_list, char *tdb= thd->db ? thd->db : db; // Result is never null ulong skip_lines= ex->skip_lines; bool transactional_table; - THD::killed_state killed_status= THD::NOT_KILLED; DBUG_ENTER("mysql_load"); #ifdef EMBEDDED_LIBRARY @@ -455,7 +455,11 @@ int mysql_load(THD *thd,sql_exchange *ex,TABLE_LIST *table_list, error=1; thd->killed= THD::KILL_QUERY; };); - killed_status= (error == 0)? THD::NOT_KILLED : thd->killed; + +#ifndef EMBEDDED_LIBRARY + killed_status= (error == 0) ? THD::NOT_KILLED : thd->killed; +#endif + /* We must invalidate the table in query cache before binlog writing and ha_autocommit_... @@ -708,12 +712,9 @@ read_fixed_length(THD *thd, COPY_INFO &info, TABLE_LIST *table_list, List_iterator_fast it(fields_vars); Item_field *sql_field; TABLE *table= table_list->table; - ulonglong id; bool err; DBUG_ENTER("read_fixed_length"); - id= 0; - while (!read_info.read_fixed_length()) { if (thd->killed) @@ -839,12 +840,10 @@ read_sep_field(THD *thd, COPY_INFO &info, TABLE_LIST *table_list, Item *item; TABLE *table= table_list->table; uint enclosed_length; - ulonglong id; bool err; DBUG_ENTER("read_sep_field"); enclosed_length=enclosed.length(); - id= 0; for (;;it.rewind()) { diff --git a/sql/sql_parse.cc b/sql/sql_parse.cc index 1f3d29ffec0..134517e5bf7 100644 --- a/sql/sql_parse.cc +++ b/sql/sql_parse.cc @@ -465,6 +465,12 @@ static void handle_bootstrap_impl(THD *thd) } buff= (char*) thd->net.buff; res= fgets(buff + length, thd->net.max_packet - length, file); + if (!res && !feof(file)) + { + net_end_statement(thd); + bootstrap_error= 1; + break; + } length+= (ulong) strlen(buff + length); /* purecov: end */ } @@ -1535,7 +1541,7 @@ bool dispatch_command(enum enum_server_command command, THD *thd, { STATUS_VAR current_global_status_var; ulong uptime; - uint length; + uint length __attribute__((unused)); ulonglong queries_per_second1000; char buff[250]; uint buff_len= sizeof(buff); @@ -1548,7 +1554,7 @@ bool dispatch_command(enum enum_server_command command, THD *thd, else queries_per_second1000= thd->query_id * LL(1000) / uptime; - length= my_snprintf((char*) buff, buff_len - 1, + length= my_snprintf(buff, buff_len - 1, "Uptime: %lu Threads: %d Questions: %lu " "Slow queries: %lu Opens: %lu Flush tables: %lu " "Open tables: %u Queries per second avg: %u.%u", @@ -1560,10 +1566,6 @@ bool dispatch_command(enum enum_server_command command, THD *thd, cached_open_tables(), (uint) (queries_per_second1000 / 1000), (uint) (queries_per_second1000 % 1000)); -#ifdef EMBEDDED_LIBRARY - /* Store the buffer in permanent memory */ - my_ok(thd, 0, 0, buff); -#endif #ifdef SAFEMALLOC if (sf_malloc_cur_memory) // Using SAFEMALLOC { @@ -1578,6 +1580,9 @@ bool dispatch_command(enum enum_server_command command, THD *thd, VOID(my_net_write(net, (uchar*) buff, length)); VOID(net_flush(net)); thd->main_da.disable_status(); +#else + /* Store the buffer in permanent memory */ + my_ok(thd, 0, 0, buff); #endif break; } diff --git a/sql/sql_repl.cc b/sql/sql_repl.cc index f6045e4704e..d7dd3eb63f2 100644 --- a/sql/sql_repl.cc +++ b/sql/sql_repl.cc @@ -1168,12 +1168,9 @@ bool change_master(THD* thd, Master_info* mi) /* Before processing the command, save the previous state. */ - char *pos; - pos= strmake(saved_host, mi->host, HOSTNAME_LENGTH); - pos= '\0'; + strmake(saved_host, mi->host, HOSTNAME_LENGTH); saved_port= mi->port; - pos= strmake(saved_log_name, mi->master_log_name, FN_REFLEN - 1); - pos= '\0'; + strmake(saved_log_name, mi->master_log_name, FN_REFLEN - 1); saved_log_pos= mi->master_log_pos; /* diff --git a/sql/sql_show.cc b/sql/sql_show.cc index d0e76e501e2..eb5d3a1965d 100644 --- a/sql/sql_show.cc +++ b/sql/sql_show.cc @@ -3868,7 +3868,6 @@ static int get_schema_column_record(THD *thd, TABLE_LIST *tables, uint flags=field->flags; char tmp[MAX_FIELD_WIDTH]; String type(tmp,sizeof(tmp), system_charset_info); - char *end; int decimals, field_length; if (wild && wild[0] && @@ -3889,7 +3888,7 @@ static int get_schema_column_record(THD *thd, TABLE_LIST *tables, field->field_name) & COL_ACLS; if (!tables->schema_table && !col_access) continue; - end= tmp; + char *end= tmp; for (uint bitnr=0; col_access ; col_access>>=1,bitnr++) { if (col_access & 1) @@ -4015,7 +4014,6 @@ static int get_schema_column_record(THD *thd, TABLE_LIST *tables, table->field[15]->store((const char*) pos, strlen((const char*) pos), cs); - end= tmp; if (field->unireg_check == Field::NEXT_NUMBER) table->field[16]->store(STRING_WITH_LEN("auto_increment"), cs); if (show_table->timestamp_field == field && diff --git a/sql/sql_table.cc b/sql/sql_table.cc index 47b91fcca0e..f765e5c5cae 100644 --- a/sql/sql_table.cc +++ b/sql/sql_table.cc @@ -6507,7 +6507,6 @@ bool mysql_alter_table(THD *thd,char *new_db, char *new_name, uint index_add_count= 0; uint *index_add_buffer= NULL; uint candidate_key_count= 0; - bool committed= 0; bool no_pk; DBUG_ENTER("mysql_alter_table"); @@ -7380,7 +7379,6 @@ view_err: DBUG_PRINT("info", ("Committing before unlocking table")); if (ha_autocommit_or_rollback(thd, 0) || end_active_trans(thd)) goto err1; - committed= 1; } /*end of if (! new_table) for add/drop index*/ diff --git a/sql/table.cc b/sql/table.cc index dde3654dab1..e989ab039a0 100644 --- a/sql/table.cc +++ b/sql/table.cc @@ -534,7 +534,7 @@ int open_table_def(THD *thd, TABLE_SHARE *share, uint db_flags) int error, table_type; bool error_given; File file; - uchar head[288], *disk_buff; + uchar head[288]; char path[FN_REFLEN]; MEM_ROOT **root_ptr, *old_root; DBUG_ENTER("open_table_def"); @@ -543,7 +543,6 @@ int open_table_def(THD *thd, TABLE_SHARE *share, uint db_flags) error= 1; error_given= 0; - disk_buff= NULL; strxmov(path, share->normalized_path.str, reg_ext, NullS); if ((file= my_open(path, O_RDONLY | O_SHARE, MYF(0))) < 0) diff --git a/sql/udf_example.c b/sql/udf_example.c index 637293209e0..468118b44ef 100644 --- a/sql/udf_example.c +++ b/sql/udf_example.c @@ -1067,7 +1067,7 @@ char *myfunc_argument_name(UDF_INIT *initid __attribute__((unused)), { if (!args->attributes[0]) { - null_value= 0; + *null_value= 1; return 0; } (*length)--; /* space for ending \0 (for debugging purposes) */ diff --git a/storage/csv/ha_tina.cc b/storage/csv/ha_tina.cc index e3bc7f55dd2..5a3399b2401 100644 --- a/storage/csv/ha_tina.cc +++ b/storage/csv/ha_tina.cc @@ -468,7 +468,7 @@ int ha_tina::encode_quote(uchar *buf) const char *ptr; const char *end_ptr; const bool was_null= (*field)->is_null(); - + /* assistance for backwards compatibility in production builds. note: this will not work for ENUM columns. @@ -480,7 +480,7 @@ int ha_tina::encode_quote(uchar *buf) } (*field)->val_str(&attribute,&attribute); - + if (was_null) (*field)->set_null(); @@ -491,34 +491,30 @@ int ha_tina::encode_quote(uchar *buf) buffer.append('"'); - while (ptr < end_ptr) + for (; ptr < end_ptr; ptr++) { if (*ptr == '"') { buffer.append('\\'); buffer.append('"'); - *ptr++; } else if (*ptr == '\r') { buffer.append('\\'); buffer.append('r'); - *ptr++; } else if (*ptr == '\\') { buffer.append('\\'); buffer.append('\\'); - *ptr++; } else if (*ptr == '\n') { buffer.append('\\'); buffer.append('n'); - *ptr++; } else - buffer.append(*ptr++); + buffer.append(*ptr); } buffer.append('"'); } diff --git a/storage/example/ha_example.cc b/storage/example/ha_example.cc index 604722c3c8c..2a4fe538c85 100644 --- a/storage/example/ha_example.cc +++ b/storage/example/ha_example.cc @@ -153,7 +153,7 @@ static int example_done_func(void *p) hash_free(&example_open_tables); pthread_mutex_destroy(&example_mutex); - DBUG_RETURN(0); + DBUG_RETURN(error); } diff --git a/storage/myisam/mi_locking.c b/storage/myisam/mi_locking.c index 342efff4842..589b9cf89b7 100644 --- a/storage/myisam/mi_locking.c +++ b/storage/myisam/mi_locking.c @@ -29,7 +29,6 @@ int mi_lock_database(MI_INFO *info, int lock_type) int error; uint count; MYISAM_SHARE *share=info->s; - uint flag; DBUG_ENTER("mi_lock_database"); DBUG_PRINT("enter",("lock_type: %d old lock %d r_locks: %u w_locks: %u " "global_changed: %d open_count: %u name: '%s'", @@ -48,7 +47,7 @@ int mi_lock_database(MI_INFO *info, int lock_type) DBUG_RETURN(0); } - flag=error=0; + error= 0; pthread_mutex_lock(&share->intern_lock); if (share->kfile >= 0) /* May only be false on windows */ { @@ -120,14 +119,12 @@ int mi_lock_database(MI_INFO *info, int lock_type) { if (share->r_locks) { /* Only read locks left */ - flag=1; if (my_lock(share->kfile,F_RDLCK,0L,F_TO_EOF, MYF(MY_WME | MY_SEEK_NOT_DONE)) && !error) error=my_errno; } else if (!share->w_locks) { /* No more locks */ - flag=1; if (my_lock(share->kfile,F_UNLCK,0L,F_TO_EOF, MYF(MY_WME | MY_SEEK_NOT_DONE)) && !error) error=my_errno; @@ -148,7 +145,6 @@ int mi_lock_database(MI_INFO *info, int lock_type) */ if (share->w_locks == 1) { - flag=1; if (my_lock(share->kfile,lock_type,0L,F_TO_EOF, MYF(MY_SEEK_NOT_DONE))) { @@ -163,7 +159,6 @@ int mi_lock_database(MI_INFO *info, int lock_type) } if (!share->r_locks && !share->w_locks) { - flag=1; if (my_lock(share->kfile,lock_type,0L,F_TO_EOF, info->lock_wait | MY_SEEK_NOT_DONE)) { @@ -188,7 +183,6 @@ int mi_lock_database(MI_INFO *info, int lock_type) { /* Change READONLY to RW */ if (share->r_locks == 1) { - flag=1; if (my_lock(share->kfile,lock_type,0L,F_TO_EOF, MYF(info->lock_wait | MY_SEEK_NOT_DONE))) { @@ -205,7 +199,6 @@ int mi_lock_database(MI_INFO *info, int lock_type) { if (!share->w_locks) { - flag=1; if (my_lock(share->kfile,lock_type,0L,F_TO_EOF, info->lock_wait | MY_SEEK_NOT_DONE)) { @@ -252,11 +245,6 @@ int mi_lock_database(MI_INFO *info, int lock_type) } #endif pthread_mutex_unlock(&share->intern_lock); -#if defined(FULL_LOG) || defined(_lint) - lock_type|=(int) (flag << 8); /* Set bit to set if real lock */ - myisam_log_command(MI_LOG_LOCK,info,(uchar*) &lock_type,sizeof(lock_type), - error); -#endif DBUG_RETURN(error); } /* mi_lock_database */ diff --git a/storage/myisam/rt_split.c b/storage/myisam/rt_split.c index 88cf643faf9..03d22de68fa 100644 --- a/storage/myisam/rt_split.c +++ b/storage/myisam/rt_split.c @@ -255,7 +255,6 @@ int rtree_split_page(MI_INFO *info, MI_KEYDEF *keyinfo, uchar *page, uchar *key, SplitStruct *stop; double *coord_buf; double *next_coord; - double *old_coord; int n_dim; uchar *source_cur, *cur1, *cur2; uchar *new_page= info->buff; @@ -293,8 +292,6 @@ int rtree_split_page(MI_INFO *info, MI_KEYDEF *keyinfo, uchar *page, uchar *key, rtree_d_mbr(keyinfo->seg, key, key_length, cur->coords); cur->key = key; - old_coord = next_coord; - if (split_rtree_node(task, max_keys + 1, mi_getint(page) + full_length + 2, full_length, rt_PAGE_MIN_SIZE(keyinfo->block_length), diff --git a/storage/myisammrg/myrg_open.c b/storage/myisammrg/myrg_open.c index 5fcbe0c3297..18f8aa8d2c0 100644 --- a/storage/myisammrg/myrg_open.c +++ b/storage/myisammrg/myrg_open.c @@ -227,9 +227,7 @@ MYRG_INFO *myrg_parent_open(const char *parent_name, int save_errno; int insert_method; uint length; - uint dir_length; uint child_count; - size_t name_buff_length; File fd; IO_CACHE file_cache; char parent_name_buff[FN_REFLEN * 2]; @@ -299,7 +297,6 @@ MYRG_INFO *myrg_parent_open(const char *parent_name, } /* Call callback for each child. */ - dir_length= dirname_part(parent_name_buff, parent_name, &name_buff_length); my_b_seek(&file_cache, 0); while ((length= my_b_gets(&file_cache, child_name_buff, FN_REFLEN - 1))) { @@ -379,7 +376,6 @@ int myrg_attach_children(MYRG_INFO *m_info, int handle_locking, { ulonglong file_offset; MI_INFO *myisam; - int rc; int errpos; int save_errno; uint idx; @@ -398,7 +394,6 @@ int myrg_attach_children(MYRG_INFO *m_info, int handle_locking, here and in ha_myisammrg::store_lock() forces consistent data. */ pthread_mutex_lock(&m_info->mutex); - rc= 1; errpos= 0; file_offset= 0; min_keys= 0; diff --git a/strings/decimal.c b/strings/decimal.c index 4403fc9fd6b..bda296ce832 100644 --- a/strings/decimal.c +++ b/strings/decimal.c @@ -1934,8 +1934,7 @@ static int do_sub(decimal_t *from1, decimal_t *from2, decimal_t *to) int decimal_intg(decimal_t *from) { int res; - dec1 *tmp_res; - tmp_res= remove_leading_zeroes(from, &res); + remove_leading_zeroes(from, &res); return res; } From 70822d52ada9a81542b799dd238bf9db4771f7c4 Mon Sep 17 00:00:00 2001 From: Davi Arnaut Date: Tue, 20 Jul 2010 16:34:20 -0300 Subject: [PATCH 072/129] Bug#52514: mysql 5.1 do_abi_check does not compile w/ gcc4.5 due to GCC preprocessor change Addendum for trunk: do not include system header when checking the ABI. --- include/mysql/plugin.h.pp | 3 --- include/mysql/service_my_snprintf.h | 3 +++ include/mysql/service_thd_alloc.h | 2 ++ 3 files changed, 5 insertions(+), 3 deletions(-) diff --git a/include/mysql/plugin.h.pp b/include/mysql/plugin.h.pp index 3a1b03742da..ce9902ee418 100644 --- a/include/mysql/plugin.h.pp +++ b/include/mysql/plugin.h.pp @@ -1,7 +1,5 @@ #include #include -#include -#include extern struct my_snprintf_service_st { size_t (*my_snprintf_type)(char*, size_t, const char*, ...); size_t (*my_vsnprintf_type)(char *, size_t, const char*, va_list); @@ -9,7 +7,6 @@ extern struct my_snprintf_service_st { size_t my_snprintf(char* to, size_t n, const char* fmt, ...); size_t my_vsnprintf(char *to, size_t n, const char* fmt, va_list ap); #include -#include struct st_mysql_lex_string { char *str; diff --git a/include/mysql/service_my_snprintf.h b/include/mysql/service_my_snprintf.h index 9e5fe7f9c9f..d7f8d07e110 100644 --- a/include/mysql/service_my_snprintf.h +++ b/include/mysql/service_my_snprintf.h @@ -70,8 +70,11 @@ extern "C" { #endif +#ifndef MYSQL_ABI_CHECK #include #include +#endif + extern struct my_snprintf_service_st { size_t (*my_snprintf_type)(char*, size_t, const char*, ...); size_t (*my_vsnprintf_type)(char *, size_t, const char*, va_list); diff --git a/include/mysql/service_thd_alloc.h b/include/mysql/service_thd_alloc.h index 86158ba1359..7061c2bd4d5 100644 --- a/include/mysql/service_thd_alloc.h +++ b/include/mysql/service_thd_alloc.h @@ -27,7 +27,9 @@ allocations - they are better served with my_malloc. */ +#ifndef MYSQL_ABI_CHECK #include +#endif #ifdef __cplusplus extern "C" { From 7f87c8f0997af4b8d5ee9c7d07a362e60aaa2b99 Mon Sep 17 00:00:00 2001 From: Davi Arnaut Date: Tue, 20 Jul 2010 16:53:39 -0300 Subject: [PATCH 073/129] Bug#52514: mysql 5.1 do_abi_check does not compile w/ gcc4.5 due to GCC preprocessor change Addendum for trunk: add -DMYSQL_ABI_CHECK to the cmake ABI check. --- Makefile.am | 2 +- cmake/abi_check.cmake | 4 ++-- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/Makefile.am b/Makefile.am index 9a9a53ebd16..a736a61fb59 100644 --- a/Makefile.am +++ b/Makefile.am @@ -63,7 +63,7 @@ dist-hook: test ! -f $(top_srcdir)/configure.am || \ $(INSTALL_DATA) $(top_srcdir)/configure.am $(distdir) -all-local: @ABI_CHECK@ +all-local: @ABI_CHECK@ tags: support-files/build-tags diff --git a/cmake/abi_check.cmake b/cmake/abi_check.cmake index 0d5bf21f540..7911b7848a8 100644 --- a/cmake/abi_check.cmake +++ b/cmake/abi_check.cmake @@ -38,7 +38,7 @@ IF(CMAKE_COMPILER_IS_GNUCC AND CMAKE_SYSTEM_NAME MATCHES "Linux") -DCOMPILER=${COMPILER} -DSOURCE_DIR=${CMAKE_SOURCE_DIR} -DBINARY_DIR=${CMAKE_BINARY_DIR} - "-DABI_HEADERS=${API_PREPROCESSOR_HEADER}" + "-DDMYSQL_ABI_CHECK -DABI_HEADERS=${API_PREPROCESSOR_HEADER}" -P ${CMAKE_SOURCE_DIR}/cmake/do_abi_check.cmake VERBATIM ) @@ -48,7 +48,7 @@ IF(CMAKE_COMPILER_IS_GNUCC AND CMAKE_SYSTEM_NAME MATCHES "Linux") -DCMAKE_C_COMPILER=${COMPILER} -DCMAKE_SOURCE_DIR=${CMAKE_SOURCE_DIR} -DCMAKE_BINARY_DIR=${CMAKE_BINARY_DIR} - "-DABI_HEADERS=${API_PREPROCESSOR_HEADER}" + "-DMYSQL_ABI_CHECK -DABI_HEADERS=${API_PREPROCESSOR_HEADER}" -P ${CMAKE_SOURCE_DIR}/cmake/scripts/do_abi_check.cmake VERBATIM ) From bd41af86ebc53510760504b980f073be4438f6e9 Mon Sep 17 00:00:00 2001 From: Dmitry Shulga Date: Wed, 21 Jul 2010 14:56:43 +0700 Subject: [PATCH 074/129] Fixed bug #42496 - the server could crash on a debug assert after a failure to write into a closed socket sql/protocol.cc: Protocol::flush modified: set thd->main_da.can_overwrite_status= TRUE before call to net_flush() in order to prevent crash on assert in case of socket write failure, reset it to FALSE when net_flush() returned; Protocol::send_fields modified: return from method with error if call to my_net_write(), proto.write() or write_eof_packet() failed. sql/sql_cache.cc: Query_cache::send_result_to_client modified: call to thd->main_da.disable_status() only if write to socket was successful. sql/sql_cursor.cc: Materialized_cursor::fetch modified: leave method if call to result->send_data() failed. sql/sql_prepare.cc: send_prep_stmt() modified: call to thd->main_da.disable_status() only if thd->protocol_text.send_fields() completed successfully. --- sql/protocol.cc | 15 +++++++++++---- sql/sql_cache.cc | 3 ++- sql/sql_cursor.cc | 7 ++++++- sql/sql_prepare.cc | 7 +++++-- 4 files changed, 24 insertions(+), 8 deletions(-) diff --git a/sql/protocol.cc b/sql/protocol.cc index dc53e029647..dfb78462f13 100644 --- a/sql/protocol.cc +++ b/sql/protocol.cc @@ -534,7 +534,11 @@ void Protocol::end_partial_result_set(THD *thd_arg) bool Protocol::flush() { #ifndef EMBEDDED_LIBRARY - return net_flush(&thd->net); + bool error; + thd->main_da.can_overwrite_status= TRUE; + error= net_flush(&thd->net); + thd->main_da.can_overwrite_status= FALSE; + return error; #else return 0; #endif @@ -574,7 +578,8 @@ bool Protocol::send_fields(List *list, uint flags) if (flags & SEND_NUM_ROWS) { // Packet with number of elements uchar *pos= net_store_length(buff, list->elements); - (void) my_net_write(&thd->net, buff, (size_t) (pos-buff)); + if (my_net_write(&thd->net, buff, (size_t) (pos-buff))) + DBUG_RETURN(1); } #ifndef DBUG_OFF @@ -698,7 +703,7 @@ bool Protocol::send_fields(List *list, uint flags) if (flags & SEND_DEFAULTS) item->send(&prot, &tmp); // Send default value if (prot.write()) - break; /* purecov: inspected */ + DBUG_RETURN(1); #ifndef DBUG_OFF field_types[count++]= field.type; #endif @@ -711,7 +716,9 @@ bool Protocol::send_fields(List *list, uint flags) to show that there is no cursor. Send no warning information, as it will be sent at statement end. */ - write_eof_packet(thd, &thd->net, thd->server_status, thd->total_warn_count); + if (write_eof_packet(thd, &thd->net, thd->server_status, + thd->total_warn_count)) + DBUG_RETURN(1); } DBUG_RETURN(prepare_for_send(list)); diff --git a/sql/sql_cache.cc b/sql/sql_cache.cc index f862cbed4f1..fcf4edbdc22 100644 --- a/sql/sql_cache.cc +++ b/sql/sql_cache.cc @@ -1653,7 +1653,8 @@ def_week_frmt: %lu, in_trans: %d, autocommit: %d", thd->limit_found_rows = query->found_rows(); thd->status_var.last_query_cost= 0.0; - thd->main_da.disable_status(); + if (!thd->main_da.is_set()) + thd->main_da.disable_status(); BLOCK_UNLOCK_RD(query_block); DBUG_RETURN(1); // Result sent to client diff --git a/sql/sql_cursor.cc b/sql/sql_cursor.cc index 6f61dc40f66..d7d029d28d4 100644 --- a/sql/sql_cursor.cc +++ b/sql/sql_cursor.cc @@ -658,7 +658,12 @@ void Materialized_cursor::fetch(ulong num_rows) if ((res= table->file->rnd_next(table->record[0]))) break; /* Send data only if the read was successful. */ - result->send_data(item_list); + /* + If network write failed (i.e. due to a closed socked), + the error has already been set. Just return. + */ + if (result->send_data(item_list)) + return; } switch (res) { diff --git a/sql/sql_prepare.cc b/sql/sql_prepare.cc index 041d9f7c30b..bd152866deb 100644 --- a/sql/sql_prepare.cc +++ b/sql/sql_prepare.cc @@ -263,8 +263,11 @@ static bool send_prep_stmt(Prepared_statement *stmt, uint columns) &stmt->lex->param_list, Protocol::SEND_EOF); } - /* Flag that a response has already been sent */ - thd->main_da.disable_status(); + + if (!error) + /* Flag that a response has already been sent */ + thd->main_da.disable_status(); + DBUG_RETURN(error); } #else From e24abd9091ce28a27f27073ab70aed94851362bc Mon Sep 17 00:00:00 2001 From: Georgi Kodinov Date: Wed, 21 Jul 2010 18:05:57 +0300 Subject: [PATCH 075/129] Addendum #4 to bug #53095 SHOW DATABASES LIKE ... was not converting to lowercase on comparison as the documentation is suggesting. Fixed it to behave similarly to SHOW TABLES LIKE ... and updated the failing on MacOSX lowercase_table2 test case. --- mysql-test/r/lowercase_table2.result | 3 ++- sql/sql_show.cc | 15 +++++++++++++-- 2 files changed, 15 insertions(+), 3 deletions(-) diff --git a/mysql-test/r/lowercase_table2.result b/mysql-test/r/lowercase_table2.result index 51c2ac0faf5..c9a46b70fab 100644 --- a/mysql-test/r/lowercase_table2.result +++ b/mysql-test/r/lowercase_table2.result @@ -56,6 +56,7 @@ CREATE DATABASE `TEST_$1`; SHOW DATABASES LIKE "TEST%"; Database (TEST%) TEST_$1 +test DROP DATABASE `test_$1`; CREATE TABLE T1 (a int) engine=innodb; INSERT INTO T1 VALUES (1); @@ -171,6 +172,6 @@ create table myUC (i int); select TABLE_SCHEMA,TABLE_NAME FROM information_schema.TABLES where TABLE_SCHEMA ='mysqltest_LC2'; TABLE_SCHEMA TABLE_NAME -mysqltest_LC2 myUC +mysqltest_lc2 myUC use test; drop database mysqltest_LC2; diff --git a/sql/sql_show.cc b/sql/sql_show.cc index eb5d3a1965d..616bced8f4a 100644 --- a/sql/sql_show.cc +++ b/sql/sql_show.cc @@ -521,8 +521,19 @@ find_files(THD *thd, List *files, const char *db, continue; file_name_len= filename_to_tablename(file->name, uname, sizeof(uname)); - if (wild && wild_compare(uname, wild, 0)) - continue; + if (wild) + { + if (lower_case_table_names) + { + if (my_wildcmp(files_charset_info, + uname, uname + file_name_len, + wild, wild + wild_length, + wild_prefix, wild_one,wild_many)) + continue; + } + else if (wild_compare(uname, wild, 0)) + continue; + } if (!(file_name= thd->make_lex_string(file_name, uname, file_name_len, TRUE))) { From ec002090b90a5da614582b24a82313995fa7e87b Mon Sep 17 00:00:00 2001 From: Jon Olav Hauglid Date: Thu, 22 Jul 2010 10:00:32 +0200 Subject: [PATCH 076/129] Bug #55223 assert in Protocol::end_statement during CREATE DATABASE The problem was that a statement could cause an assert if it was aborted by KILL QUERY while it waited on a metadata lock. This assert checks that a statement either sends OK or an error to the client. If the bug was triggered on release builds, it caused OK to be sent to the client instead of ER_QUERY_INTERRUPTED. The root cause of the problem was that there are two separate ways to tell if a statement is killed: thd->killed and mysys_var->abort. KILL QUERY causes both to be set, thd->killed before mysys_var->abort. Also, both values are reset at the end of statement execution. This means that it is possible for KILL QUERY to first set thd->killed, then have the killed statement reset both thd->killed and mysys_var->abort and finally have KILL QUERY set mysys_var->abort. This means that the connection with the killed statement will start executing the next statement with the two values out of sync - i.e. thd->killed not set but mysys_var->abort set. Since mysys_var->abort is used to check if a wait for a metadata lock should be aborted, the next statement would immediately abort any such waiting. When waiting is aborted, no OK message is sent and thd->killed is checked to see if ER_QUERY_INTERRUPTED should be sent to the client. But since the->killed had been reset, neither OK nor an error message was sent to the client. This then triggered the assert. This patch fixes the problem by changing the metadata lock waiting code to check thd->killed. No test case added as reproducing the assert is dependent on very exact timing of two (or more) threads. The patch has been checked using RQG and the grammar posted on the bug report. --- sql/mdl.cc | 72 ++++-------------------------------------------------- sql/mdl.h | 8 +++--- 2 files changed, 9 insertions(+), 71 deletions(-) diff --git a/sql/mdl.cc b/sql/mdl.cc index 818b736e597..ca66799baed 100644 --- a/sql/mdl.cc +++ b/sql/mdl.cc @@ -881,67 +881,6 @@ uint MDL_ticket::get_deadlock_weight() const } -/** - Helper functions and macros to be used for killable waiting in metadata - locking subsystem. - - @sa THD::enter_cond()/exit_cond()/killed. - - @note We can't use THD::enter_cond()/exit_cond()/killed directly here - since this will make metadata subsystem dependent on THD class - and thus prevent us from writing unit tests for it. And usage of - wrapper functions to access THD::killed/enter_cond()/exit_cond() - will probably introduce too much overhead. -*/ - -#define MDL_ENTER_COND(A, B, C, D) \ - mdl_enter_cond(A, B, C, D, __func__, __FILE__, __LINE__) - -static inline const char *mdl_enter_cond(THD *thd, - st_my_thread_var *mysys_var, - mysql_cond_t *cond, - mysql_mutex_t *mutex, - const char *calling_func, - const char *calling_file, - const unsigned int calling_line) -{ - mysql_mutex_assert_owner(mutex); - - mysys_var->current_mutex= mutex; - mysys_var->current_cond= cond; - - DEBUG_SYNC(thd, "mdl_enter_cond"); - - return set_thd_proc_info(thd, "Waiting for table", - calling_func, calling_file, calling_line); -} - -#define MDL_EXIT_COND(A, B, C, D) \ - mdl_exit_cond(A, B, C, D, __func__, __FILE__, __LINE__) - -static inline void mdl_exit_cond(THD *thd, - st_my_thread_var *mysys_var, - mysql_mutex_t *mutex, - const char* old_msg, - const char *calling_func, - const char *calling_file, - const unsigned int calling_line) -{ - DBUG_ASSERT(mutex == mysys_var->current_mutex); - - mysql_mutex_unlock(mutex); - mysql_mutex_lock(&mysys_var->mutex); - mysys_var->current_mutex= NULL; - mysys_var->current_cond= NULL; - mysql_mutex_unlock(&mysys_var->mutex); - - DEBUG_SYNC(thd, "mdl_exit_cond"); - - (void) set_thd_proc_info(thd, old_msg, calling_func, - calling_file, calling_line); -} - - /** Construct an empty wait slot. */ MDL_wait::MDL_wait() @@ -1021,15 +960,14 @@ MDL_wait::timed_wait(THD *thd, struct timespec *abs_timeout, { const char *old_msg; enum_wait_status result; - st_my_thread_var *mysys_var= my_thread_var; int wait_result= 0; mysql_mutex_lock(&m_LOCK_wait_status); - old_msg= MDL_ENTER_COND(thd, mysys_var, &m_COND_wait_status, - &m_LOCK_wait_status); + old_msg= thd_enter_cond(thd, &m_COND_wait_status, &m_LOCK_wait_status, + "Waiting for table"); - while (!m_wait_status && !mysys_var->abort && + while (!m_wait_status && !thd_killed(thd) && wait_result != ETIMEDOUT && wait_result != ETIME) wait_result= mysql_cond_timedwait(&m_COND_wait_status, &m_LOCK_wait_status, abs_timeout); @@ -1048,14 +986,14 @@ MDL_wait::timed_wait(THD *thd, struct timespec *abs_timeout, false, which means that the caller intends to restart the wait. */ - if (mysys_var->abort) + if (thd_killed(thd)) m_wait_status= KILLED; else if (set_status_on_timeout) m_wait_status= TIMEOUT; } result= m_wait_status; - MDL_EXIT_COND(thd, mysys_var, &m_LOCK_wait_status, old_msg); + thd_exit_cond(thd, old_msg); return result; } diff --git a/sql/mdl.h b/sql/mdl.h index 319c16cf6ce..c8acd69c0f1 100644 --- a/sql/mdl.h +++ b/sql/mdl.h @@ -721,10 +721,10 @@ void mdl_destroy(); extern bool mysql_notify_thread_having_shared_lock(THD *thd, THD *in_use, bool needs_thr_lock_abort); -extern "C" const char *set_thd_proc_info(void *thd_arg, const char *info, - const char *calling_function, - const char *calling_file, - const unsigned int calling_line); +extern "C" const char* thd_enter_cond(MYSQL_THD thd, mysql_cond_t *cond, + mysql_mutex_t *mutex, const char *msg); +extern "C" void thd_exit_cond(MYSQL_THD thd, const char *old_msg); + #ifndef DBUG_OFF extern mysql_mutex_t LOCK_open; #endif From 2857a84985a2fa1aa994fd2e6473a2b191f10841 Mon Sep 17 00:00:00 2001 From: Jon Olav Hauglid Date: Thu, 22 Jul 2010 11:10:35 +0200 Subject: [PATCH 077/129] Bug #54905 Connection with WRITE lock cannot ALTER table due to concurrent SHOW CREATE The problem was that a SHOW CREATE TABLE statement issued inside a transaction did not release its metadata locks at the end of the statement execution. This happened even if SHOW CREATE TABLE is an information statement. The consequence was that SHOW CREATE TABLE was able to block other connections from accessing the table (e.g. using ALTER TABLE). This patch fixes the problem by explicitly releasing any metadata locks taken by SHOW CREATE TABLE after the statement completes. Test case added to show_check.test. --- mysql-test/r/show_check.result | 21 +++++++++++++++++++++ mysql-test/t/show_check.test | 33 +++++++++++++++++++++++++++++++++ sql/sql_show.cc | 32 +++++++++++++++++++++++--------- 3 files changed, 77 insertions(+), 9 deletions(-) diff --git a/mysql-test/r/show_check.result b/mysql-test/r/show_check.result index ef2277fef38..f49366cbf08 100644 --- a/mysql-test/r/show_check.result +++ b/mysql-test/r/show_check.result @@ -1466,3 +1466,24 @@ t1 CREATE TABLE `t1` ( # Switching to connection 'default'. UNLOCK TABLES; DROP TABLE t1; +# +# Bug#54905 Connection with WRITE lock cannot ALTER table due to +# concurrent SHOW CREATE +# +DROP TABLE IF EXISTS t1; +CREATE TABLE t1(a INT); +# Connection con1 +LOCK TABLE t1 WRITE; +# Connection default +START TRANSACTION; +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +# Connection con1 +ALTER TABLE t1 CHARACTER SET = utf8; +UNLOCK TABLES; +# Connection default +COMMIT; +DROP TABLE t1; diff --git a/mysql-test/t/show_check.test b/mysql-test/t/show_check.test index fa003c2fe69..89a43f24296 100644 --- a/mysql-test/t/show_check.test +++ b/mysql-test/t/show_check.test @@ -1246,6 +1246,39 @@ UNLOCK TABLES; DROP TABLE t1; +--echo # +--echo # Bug#54905 Connection with WRITE lock cannot ALTER table due to +--echo # concurrent SHOW CREATE +--echo # + +--disable_warnings +DROP TABLE IF EXISTS t1; +--enable_warnings + +CREATE TABLE t1(a INT); + +--echo # Connection con1 +connect (con1,localhost,root); +LOCK TABLE t1 WRITE; + +--echo # Connection default +connection default; +START TRANSACTION; +SHOW CREATE TABLE t1; + +--echo # Connection con1 +connection con1; +# Used to block +ALTER TABLE t1 CHARACTER SET = utf8; +UNLOCK TABLES; + +--echo # Connection default +connection default; +COMMIT; +disconnect con1; +DROP TABLE t1; + + # Wait till all disconnects are completed --source include/wait_until_count_sessions.inc diff --git a/sql/sql_show.cc b/sql/sql_show.cc index a8ae5832a2a..8647237ce72 100644 --- a/sql/sql_show.cc +++ b/sql/sql_show.cc @@ -649,22 +649,30 @@ mysqld_show_create(THD *thd, TABLE_LIST *table_list) Protocol *protocol= thd->protocol; char buff[2048]; String buffer(buff, sizeof(buff), system_charset_info); + List field_list; + bool error= TRUE; DBUG_ENTER("mysqld_show_create"); DBUG_PRINT("enter",("db: %s table: %s",table_list->db, table_list->table_name)); + /* + Metadata locks taken during SHOW CREATE should be released when + the statmement completes as it is an information statement. + */ + MDL_ticket *mdl_savepoint= thd->mdl_context.mdl_savepoint(); + /* We want to preserve the tree for views. */ thd->lex->view_prepare_mode= TRUE; { Show_create_error_handler view_error_suppressor(thd, table_list); thd->push_internal_handler(&view_error_suppressor); - bool error= + bool open_error= open_normal_and_derived_tables(thd, table_list, MYSQL_OPEN_FORCE_SHARED_HIGH_PRIO_MDL); thd->pop_internal_handler(); - if (error && (thd->killed || thd->is_error())) - DBUG_RETURN(TRUE); + if (open_error && (thd->killed || thd->is_error())) + goto exit; } /* TODO: add environment variables show when it become possible */ @@ -672,7 +680,7 @@ mysqld_show_create(THD *thd, TABLE_LIST *table_list) { my_error(ER_WRONG_OBJECT, MYF(0), table_list->db, table_list->table_name, "VIEW"); - DBUG_RETURN(TRUE); + goto exit; } buffer.length(0); @@ -684,9 +692,8 @@ mysqld_show_create(THD *thd, TABLE_LIST *table_list) view_store_create_info(thd, table_list, &buffer) : store_create_info(thd, table_list, &buffer, NULL, FALSE /* show_database */))) - DBUG_RETURN(TRUE); + goto exit; - List field_list; if (table_list->view) { field_list.push_back(new Item_empty_string("View",NAME_CHAR_LEN)); @@ -707,7 +714,8 @@ mysqld_show_create(THD *thd, TABLE_LIST *table_list) if (protocol->send_result_set_metadata(&field_list, Protocol::SEND_NUM_ROWS | Protocol::SEND_EOF)) - DBUG_RETURN(TRUE); + goto exit; + protocol->prepare_for_resend(); if (table_list->view) protocol->store(table_list->view_name.str, system_charset_info); @@ -735,10 +743,16 @@ mysqld_show_create(THD *thd, TABLE_LIST *table_list) protocol->store(buffer.ptr(), buffer.length(), buffer.charset()); if (protocol->write()) - DBUG_RETURN(TRUE); + goto exit; + error= FALSE; my_eof(thd); - DBUG_RETURN(FALSE); + +exit: + close_thread_tables(thd); + /* Release any metadata locks taken during SHOW CREATE. */ + thd->mdl_context.rollback_to_savepoint(mdl_savepoint); + DBUG_RETURN(error); } bool mysqld_show_create_db(THD *thd, char *dbname, From 5f9de42e26f9a97eca87227ea5315ea7d20c51c3 Mon Sep 17 00:00:00 2001 From: Davi Arnaut Date: Thu, 22 Jul 2010 08:30:14 -0300 Subject: [PATCH 078/129] Do not generate autotools configuration scripts when cmake is to be used. --- BUILD/FINISH.sh | 1 + BUILD/Makefile.am | 2 +- BUILD/autorun.sh | 36 +++++++++++-------- ...choose_configure.sh => cmake_configure.sh} | 0 4 files changed, 23 insertions(+), 16 deletions(-) rename BUILD/{choose_configure.sh => cmake_configure.sh} (100%) diff --git a/BUILD/FINISH.sh b/BUILD/FINISH.sh index 142ff7eb08e..b7f7a1db77e 100644 --- a/BUILD/FINISH.sh +++ b/BUILD/FINISH.sh @@ -6,6 +6,7 @@ configure="./configure $base_configs $extra_configs" commands="\ $make -k maintainer-clean || true /bin/rm -rf */.deps/*.P configure config.cache storage/*/configure storage/*/config.cache autom4te.cache storage/*/autom4te.cache; +/bin/rm -rf CMakeCache.txt CMakeFiles/ path=`dirname $0` . \"$path/autorun.sh\"" diff --git a/BUILD/Makefile.am b/BUILD/Makefile.am index c7bf813c9fe..c5732d43fbf 100644 --- a/BUILD/Makefile.am +++ b/BUILD/Makefile.am @@ -20,7 +20,7 @@ EXTRA_DIST = FINISH.sh \ SETUP.sh \ autorun.sh \ - choose_configure.sh \ + cmake_configure.sh \ build_mccge.sh \ check-cpu \ cleanup \ diff --git a/BUILD/autorun.sh b/BUILD/autorun.sh index f45b1f7d08c..9fdd0486360 100755 --- a/BUILD/autorun.sh +++ b/BUILD/autorun.sh @@ -21,18 +21,24 @@ done IFS="$save_ifs" rm -rf configure -aclocal || die "Can't execute aclocal" -autoheader || die "Can't execute autoheader" -# --force means overwrite ltmain.sh script if it already exists -$LIBTOOLIZE --automake --force --copy || die "Can't execute libtoolize" - -# --add-missing instructs automake to install missing auxiliary files -# and --force to overwrite them if they already exist -automake --add-missing --force --copy || die "Can't execute automake" -autoconf || die "Can't execute autoconf" -# Do not use autotools generated configure directly. Instead, use a script -# that will either call CMake or original configure shell script at build -# time (CMake is preferred if installed). -mv configure configure.am -cp BUILD/choose_configure.sh configure -chmod a+x configure + +# Ensure that cmake and perl are available. Required for cmake based builds. +cmake -P cmake/check_minimal_version.cmake >/dev/null 2>&1 || HAVE_CMAKE=no +perl --version >/dev/null 2>&1 || HAVE_CMAKE=no + +# Whether to use the autotools configuration script or cmake. +if test "$HAVE_CMAKE" = "no" +then + aclocal || die "Can't execute aclocal" + autoheader || die "Can't execute autoheader" + # --force means overwrite ltmain.sh script if it already exists + $LIBTOOLIZE --automake --force --copy || die "Can't execute libtoolize" + # --add-missing instructs automake to install missing auxiliary files + # and --force to overwrite them if they already exist + automake --add-missing --force --copy || die "Can't execute automake" + autoconf || die "Can't execute autoconf" +else + path=`dirname $0` + cp $path/cmake_configure.sh $path/../configure + chmod +x $path/../configure +fi diff --git a/BUILD/choose_configure.sh b/BUILD/cmake_configure.sh similarity index 100% rename from BUILD/choose_configure.sh rename to BUILD/cmake_configure.sh From e9a52f962f2d89fe1938145105bcb35f970a2414 Mon Sep 17 00:00:00 2001 From: unknown Date: Thu, 22 Jul 2010 11:15:15 -0500 Subject: [PATCH 079/129] Bug#49542 - Do as the comment suggests and downgrade directory errors from find_file() to a warning unless they happen during a SHOW command. --- sql/sql_show.cc | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/sql/sql_show.cc b/sql/sql_show.cc index eb5d3a1965d..c979d44dc1c 100644 --- a/sql/sql_show.cc +++ b/sql/sql_show.cc @@ -1,4 +1,4 @@ -/* Copyright 2000-2008 MySQL AB, 2008 Sun Microsystems, Inc. +/* Copyright 2000, 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 @@ -9,9 +9,9 @@ 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 */ + 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 Street, Fifth Floor, Boston, MA 02110-1301 USA */ /* Function with list databases, tables or fields */ @@ -2986,7 +2986,7 @@ make_table_name_list(THD *thd, List *table_names, LEX *lex, */ if (res == FIND_FILES_DIR) { - if (lex->sql_command != SQLCOM_SELECT) + if (sql_command_flags[lex->sql_command] & CF_STATUS_COMMAND) return 1; thd->clear_error(); return 2; From 54c5e7c88f322b6fe1afc643d448d4e8c6edd113 Mon Sep 17 00:00:00 2001 From: Jon Olav Hauglid Date: Fri, 23 Jul 2010 10:44:55 +0200 Subject: [PATCH 080/129] Bug #55498 SHOW CREATE TRIGGER takes wrong type of metadata lock The first problem was that SHOW CREATE TRIGGER took a stronger metadata lock than required. This caused the statement to be blocked when it was not needed. For example, LOCK TABLE WRITE in one connection would block SHOW CREATE TRIGGER in another connection. Another problem was that a SHOW CREATE TRIGGER statement issued inside a transaction did not release its metadata locks at the end of the statement execution. This happened even if SHOW CREATE TRIGGER is an information statement. The consequence was that SHOW CREATE TRIGGER was able to block other connections from accessing the table (e.g. using ALTER TABLE). This patch fixes the problem by changing SHOW CREATE TRIGGER to take a MDL_SHARED_HIGH_PRIO metadata lock similar to what is already done for SHOW CREATE TABLE. The patch also changes SHOW CREATE TRIGGER to explicitly release any metadata locks taken by the statement after it completes. Test case added to show_check.test. --- mysql-test/r/show_check.result | 27 ++++++++++++++++++++ mysql-test/t/show_check.test | 46 ++++++++++++++++++++++++++++++++++ sql/sql_show.cc | 38 +++++++++++++++++----------- 3 files changed, 97 insertions(+), 14 deletions(-) diff --git a/mysql-test/r/show_check.result b/mysql-test/r/show_check.result index f49366cbf08..c1a75281e0e 100644 --- a/mysql-test/r/show_check.result +++ b/mysql-test/r/show_check.result @@ -1487,3 +1487,30 @@ UNLOCK TABLES; # Connection default COMMIT; DROP TABLE t1; +# +# Bug#55498 SHOW CREATE TRIGGER takes wrong type of metadata lock. +# +DROP TABLE IF EXISTS t1; +CREATE TABLE t1 (a INT); +CREATE TRIGGER t1_bi BEFORE INSERT ON t1 FOR EACH ROW SET new.a = 1; +# Test 1: SHOW CREATE TRIGGER with WRITE locked table. +# Connection con1 +LOCK TABLE t1 WRITE; +# Connection default +SHOW CREATE TRIGGER t1_bi; +Trigger sql_mode SQL Original Statement character_set_client collation_connection Database Collation +t1_bi CREATE DEFINER=`root`@`localhost` TRIGGER t1_bi BEFORE INSERT ON t1 FOR EACH ROW SET new.a = 1 utf8 utf8_general_ci latin1_swedish_ci +# Connection con1 +UNLOCK TABLES; +# Test 2: ALTER TABLE with SHOW CREATE TRIGGER in transaction +# Connection default +START TRANSACTION; +SHOW CREATE TRIGGER t1_bi; +Trigger sql_mode SQL Original Statement character_set_client collation_connection Database Collation +t1_bi CREATE DEFINER=`root`@`localhost` TRIGGER t1_bi BEFORE INSERT ON t1 FOR EACH ROW SET new.a = 1 utf8 utf8_general_ci latin1_swedish_ci +# Connection con1 +ALTER TABLE t1 CHARACTER SET = utf8; +# Connection default +COMMIT; +DROP TRIGGER t1_bi; +DROP TABLE t1; diff --git a/mysql-test/t/show_check.test b/mysql-test/t/show_check.test index 89a43f24296..0323f015e88 100644 --- a/mysql-test/t/show_check.test +++ b/mysql-test/t/show_check.test @@ -1279,6 +1279,52 @@ disconnect con1; DROP TABLE t1; +--echo # +--echo # Bug#55498 SHOW CREATE TRIGGER takes wrong type of metadata lock. +--echo # + +--disable_warnings +DROP TABLE IF EXISTS t1; +--enable_warnings + +CREATE TABLE t1 (a INT); +CREATE TRIGGER t1_bi BEFORE INSERT ON t1 FOR EACH ROW SET new.a = 1; + +--echo # Test 1: SHOW CREATE TRIGGER with WRITE locked table. + +--echo # Connection con1 +connect (con1, localhost, root); +LOCK TABLE t1 WRITE; + +--echo # Connection default +connection default; +# Should not block. +SHOW CREATE TRIGGER t1_bi; + +--echo # Connection con1 +connection con1; +UNLOCK TABLES; + +--echo # Test 2: ALTER TABLE with SHOW CREATE TRIGGER in transaction + +--echo # Connection default +connection default; +START TRANSACTION; +SHOW CREATE TRIGGER t1_bi; + +--echo # Connection con1 +connection con1; +# Should not block. +ALTER TABLE t1 CHARACTER SET = utf8; + +--echo # Connection default +connection default; +COMMIT; +DROP TRIGGER t1_bi; +DROP TABLE t1; +disconnect con1; + + # Wait till all disconnects are completed --source include/wait_until_count_sessions.inc diff --git a/sql/sql_show.cc b/sql/sql_show.cc index 8647237ce72..dc3784eb538 100644 --- a/sql/sql_show.cc +++ b/sql/sql_show.cc @@ -7779,6 +7779,10 @@ TABLE_LIST *get_trigger_table(THD *thd, const sp_name *trg_name) bool show_create_trigger(THD *thd, const sp_name *trg_name) { TABLE_LIST *lst= get_trigger_table(thd, trg_name); + uint num_tables; /* NOTE: unused, only to pass to open_tables(). */ + Table_triggers_list *triggers; + int trigger_idx; + bool error= TRUE; if (!lst) return TRUE; @@ -7790,35 +7794,35 @@ bool show_create_trigger(THD *thd, const sp_name *trg_name) } /* - Open the table by name in order to load Table_triggers_list object. - - NOTE: there is race condition here -- the table can be dropped after - LOCK_open is released. It will be fixed later by acquiring shared - metadata lock on trigger or table name. + Metadata locks taken during SHOW CREATE TRIGGER should be released when + the statement completes as it is an information statement. */ + MDL_ticket *mdl_savepoint= thd->mdl_context.mdl_savepoint(); - uint num_tables; /* NOTE: unused, only to pass to open_tables(). */ - - if (open_tables(thd, &lst, &num_tables, 0)) + /* + Open the table by name in order to load Table_triggers_list object. + */ + if (open_tables(thd, &lst, &num_tables, + MYSQL_OPEN_FORCE_SHARED_HIGH_PRIO_MDL)) { my_error(ER_TRG_CANT_OPEN_TABLE, MYF(0), (const char *) trg_name->m_db.str, (const char *) lst->table_name); - return TRUE; + goto exit; /* Perform closing actions and return error status. */ } - Table_triggers_list *triggers= lst->table->triggers; + triggers= lst->table->triggers; if (!triggers) { my_error(ER_TRG_DOES_NOT_EXIST, MYF(0)); - return TRUE; + goto exit; } - int trigger_idx= triggers->find_trigger_by_name(&trg_name->m_name); + trigger_idx= triggers->find_trigger_by_name(&trg_name->m_name); if (trigger_idx < 0) { @@ -7826,16 +7830,22 @@ bool show_create_trigger(THD *thd, const sp_name *trg_name) (const char *) trg_name->m_db.str, (const char *) lst->table_name); - return TRUE; + goto exit; } - return show_create_trigger_impl(thd, triggers, trigger_idx); + error= show_create_trigger_impl(thd, triggers, trigger_idx); /* NOTE: if show_create_trigger_impl() failed, that means we could not send data to the client. In this case we simply raise the error status and client connection will be closed. */ + +exit: + close_thread_tables(thd); + /* Release any metadata locks taken during SHOW CREATE TRIGGER. */ + thd->mdl_context.rollback_to_savepoint(mdl_savepoint); + return error; } class IS_internal_schema_access : public ACL_internal_schema_access From 50cdef087d4a9787ae66ebc672b29e9c7ccd3c42 Mon Sep 17 00:00:00 2001 From: Bjorn Munch Date: Fri, 23 Jul 2010 14:53:09 +0200 Subject: [PATCH 081/129] Bug #55503 MTR fails to filter LEAK SUMMARY from valgrind report of restarted servers Was not covered by "skip" pattern Replace with a more generic pattern for SUMMARY --- mysql-test/mysql-test-run.pl | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/mysql-test/mysql-test-run.pl b/mysql-test/mysql-test-run.pl index fce8ce5ec1c..93f9b671f5a 100755 --- a/mysql-test/mysql-test-run.pl +++ b/mysql-test/mysql-test-run.pl @@ -3791,7 +3791,8 @@ sub extract_warning_lines ($$) { if ($opt_valgrind_mysqld) { # Skip valgrind summary from tests where server has been restarted # Should this contain memory leaks, the final report will find it - $skip_valgrind= 1 if $line =~ /^==\d+== ERROR SUMMARY:/; + # Use a generic pattern for summaries + $skip_valgrind= 1 if $line =~ /^==\d+== [A-Z ]+ SUMMARY:/; $skip_valgrind= 0 unless $line =~ /^==\d+==/; next if $skip_valgrind; } From 6c4335b4cdb5207e7fbc5bff60d0488af4897be7 Mon Sep 17 00:00:00 2001 From: Vasil Dimov Date: Fri, 23 Jul 2010 19:32:38 +0300 Subject: [PATCH 082/129] Increment InnoDB Plugin version to 1.0.11. InnoDB Plugin 1.0.10 has been released with MySQL 5.1.49. --- storage/innodb_plugin/include/univ.i | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/storage/innodb_plugin/include/univ.i b/storage/innodb_plugin/include/univ.i index b8e595161b9..aa56c18e44e 100644 --- a/storage/innodb_plugin/include/univ.i +++ b/storage/innodb_plugin/include/univ.i @@ -46,7 +46,7 @@ Created 1/20/1994 Heikki Tuuri #define INNODB_VERSION_MAJOR 1 #define INNODB_VERSION_MINOR 0 -#define INNODB_VERSION_BUGFIX 10 +#define INNODB_VERSION_BUGFIX 11 /* The following is the InnoDB version as shown in SELECT plugin_version FROM information_schema.plugins; From 2529ee72ec1af6d27a4f1dc5db2c4f2f001b6120 Mon Sep 17 00:00:00 2001 From: Davi Arnaut Date: Fri, 23 Jul 2010 21:55:03 -0300 Subject: [PATCH 083/129] Bug#55501: Disable innodb plugin usage in the embedded server on certain OSes Do not attempt to test the innodb plugin with the embedded server, it's not supported for now. --- mysql-test/include/have_innodb_plugin.inc | 1 + 1 file changed, 1 insertion(+) diff --git a/mysql-test/include/have_innodb_plugin.inc b/mysql-test/include/have_innodb_plugin.inc index 99a79465f52..df876deb2d7 100644 --- a/mysql-test/include/have_innodb_plugin.inc +++ b/mysql-test/include/have_innodb_plugin.inc @@ -1,3 +1,4 @@ +--source include/not_embedded.inc disable_query_log; --require r/true.require SELECT (plugin_library LIKE 'ha_innodb_plugin%') AS `TRUE` FROM information_schema.plugins WHERE LOWER(plugin_name) = 'innodb' AND LOWER(plugin_status) = 'active'; From e57a9d6fe035df7d200b90c518256b68b6a9fc49 Mon Sep 17 00:00:00 2001 From: Alexander Barkov Date: Mon, 26 Jul 2010 09:06:18 +0400 Subject: [PATCH 084/129] Bug#45012 my_like_range_cp932 generates invalid string Problem: The functions my_like_range_xxx() returned badly formed maximum strings for Asian character sets, which made problems for storage engines. Fix: - Removed a number my_like_range_xxx() implementations, which were in fact dumplicate code pieces. - Using generic my_like_range_mb() instead. - Setting max_sort_char member properly for Asian character sets - Adding unittest/strings/strings-t.c, to test that my_like_range_xxx() return well-formed min and max strings. Notes: - No additional tests in mysql/t/ available. Old tests cover the affected code well enough. --- configure.in | 3 +- strings/ctype-big5.c | 86 +------------------------- strings/ctype-cp932.c | 76 +---------------------- strings/ctype-euc_kr.c | 4 +- strings/ctype-eucjpms.c | 4 +- strings/ctype-gb2312.c | 4 +- strings/ctype-gbk.c | 86 +------------------------- strings/ctype-mb.c | 22 +++++-- strings/ctype-sjis.c | 85 +------------------------- strings/ctype-ujis.c | 4 +- unittest/Makefile.am | 4 +- unittest/strings/Makefile.am | 27 +++++++++ unittest/strings/strings-t.c | 114 +++++++++++++++++++++++++++++++++++ 13 files changed, 181 insertions(+), 338 deletions(-) create mode 100644 unittest/strings/Makefile.am create mode 100644 unittest/strings/strings-t.c diff --git a/configure.in b/configure.in index 0af6a92fcc9..efd291f953c 100644 --- a/configure.in +++ b/configure.in @@ -2880,7 +2880,8 @@ fi AC_CONFIG_FILES(Makefile extra/Makefile mysys/Makefile dnl unittest/Makefile unittest/mytap/Makefile unittest/mytap/t/Makefile dnl - unittest/mysys/Makefile unittest/examples/Makefile dnl + unittest/mysys/Makefile unittest/strings/Makefile dnl + unittest/examples/Makefile dnl strings/Makefile regex/Makefile storage/Makefile dnl man/Makefile BUILD/Makefile vio/Makefile dnl libmysql/Makefile libmysql_r/Makefile client/Makefile dnl diff --git a/strings/ctype-big5.c b/strings/ctype-big5.c index 3da307b82fc..2cb40c266d2 100644 --- a/strings/ctype-big5.c +++ b/strings/ctype-big5.c @@ -377,86 +377,6 @@ static int my_strxfrm_big5(uchar *dest, const uchar *src, int len) #endif -/* -** Calculate min_str and max_str that ranges a LIKE string. -** Arguments: -** ptr Pointer to LIKE string. -** ptr_length Length of LIKE string. -** escape Escape character in LIKE. (Normally '\'). -** All escape characters should be removed from min_str and max_str -** res_length Length of min_str and max_str. -** min_str Smallest case sensitive string that ranges LIKE. -** Should be space padded to res_length. -** max_str Largest case sensitive string that ranges LIKE. -** Normally padded with the biggest character sort value. -** -** The function should return 0 if ok and 1 if the LIKE string can't be -** optimized ! -*/ - -#define max_sort_char ((char) 255) - -static my_bool my_like_range_big5(CHARSET_INFO *cs __attribute__((unused)), - const char *ptr,size_t ptr_length, - pbool escape, pbool w_one, pbool w_many, - size_t res_length, - char *min_str, char *max_str, - size_t *min_length, size_t *max_length) -{ - const char *end= ptr + ptr_length; - char *min_org=min_str; - char *min_end=min_str+res_length; - size_t charlen= res_length / cs->mbmaxlen; - - for (; ptr != end && min_str != min_end && charlen > 0; ptr++, charlen--) - { - if (ptr+1 != end && isbig5code(ptr[0],ptr[1])) - { - *min_str++= *max_str++ = *ptr++; - *min_str++= *max_str++ = *ptr; - continue; - } - if (*ptr == escape && ptr+1 != end) - { - ptr++; /* Skip escape */ - if (isbig5code(ptr[0], ptr[1])) - *min_str++= *max_str++ = *ptr++; - if (min_str < min_end) - *min_str++= *max_str++= *ptr; - continue; - } - if (*ptr == w_one) /* '_' in SQL */ - { - *min_str++='\0'; /* This should be min char */ - *max_str++=max_sort_char; - continue; - } - if (*ptr == w_many) /* '%' in SQL */ - { - /* - Calculate length of keys: - 'a\0\0... is the smallest possible string when we have space expand - a\ff\ff... is the biggest possible string - */ - *min_length= ((cs->state & MY_CS_BINSORT) ? (size_t) (min_str - min_org) : - res_length); - *max_length= res_length; - do { - *min_str++ = 0; - *max_str++ = max_sort_char; - } while (min_str != min_end); - return 0; - } - *min_str++= *max_str++ = *ptr; - } - - *min_length= *max_length= (size_t) (min_str-min_org); - while (min_str != min_end) - *min_str++= *max_str++= ' '; - return 0; -} - - static uint ismbchar_big5(CHARSET_INFO *cs __attribute__((unused)), const char* p, const char *e) { @@ -6338,7 +6258,7 @@ static MY_COLLATION_HANDLER my_collation_big5_chinese_ci_handler = my_strnncollsp_big5, my_strnxfrm_big5, my_strnxfrmlen_simple, - my_like_range_big5, + my_like_range_mb, my_wildcmp_mb, my_strcasecmp_mb, my_instr_mb, @@ -6402,7 +6322,7 @@ CHARSET_INFO my_charset_big5_chinese_ci= 1, /* mbminlen */ 2, /* mbmaxlen */ 0, /* min_sort_char */ - 255, /* max_sort_char */ + 0xF9D5, /* max_sort_char */ ' ', /* pad char */ 1, /* escape_with_backslash_is_dangerous */ &my_charset_big5_handler, @@ -6435,7 +6355,7 @@ CHARSET_INFO my_charset_big5_bin= 1, /* mbminlen */ 2, /* mbmaxlen */ 0, /* min_sort_char */ - 255, /* max_sort_char */ + 0xF9FE, /* max_sort_char */ ' ', /* pad char */ 1, /* escape_with_backslash_is_dangerous */ &my_charset_big5_handler, diff --git a/strings/ctype-cp932.c b/strings/ctype-cp932.c index 07191c436b7..238c6f61baa 100644 --- a/strings/ctype-cp932.c +++ b/strings/ctype-cp932.c @@ -306,76 +306,6 @@ static size_t my_strnxfrm_cp932(CHARSET_INFO *cs __attribute__((unused)), } -/* -** Calculate min_str and max_str that ranges a LIKE string. -** Arguments: -** ptr Pointer to LIKE string. -** ptr_length Length of LIKE string. -** escape Escape character in LIKE. (Normally '\'). -** All escape characters should be removed from min_str and max_str -** res_length Length of min_str and max_str. -** min_str Smallest case sensitive string that ranges LIKE. -** Should be space padded to res_length. -** max_str Largest case sensitive string that ranges LIKE. -** Normally padded with the biggest character sort value. -** -** The function should return 0 if ok and 1 if the LIKE string can't be -** optimized ! -*/ - -#define max_sort_char ((char) 255) - -static my_bool my_like_range_cp932(CHARSET_INFO *cs __attribute__((unused)), - const char *ptr,size_t ptr_length, - pbool escape, pbool w_one, pbool w_many, - size_t res_length, - char *min_str,char *max_str, - size_t *min_length, size_t *max_length) -{ - const char *end=ptr+ptr_length; - char *min_org=min_str; - char *min_end=min_str+res_length; - - while (ptr < end && min_str < min_end) { - if (ismbchar_cp932(cs, ptr, end)) { - *min_str++ = *max_str++ = *ptr++; - if (min_str < min_end) - *min_str++ = *max_str++ = *ptr++; - continue; - } - if (*ptr == escape && ptr+1 < end) { - ptr++; /* Skip escape */ - if (ismbchar_cp932(cs, ptr, end)) - *min_str++ = *max_str++ = *ptr++; - if (min_str < min_end) - *min_str++ = *max_str++ = *ptr++; - continue; - } - if (*ptr == w_one) { /* '_' in SQL */ - *min_str++ = '\0'; /* This should be min char */ - *max_str++ = max_sort_char; - ptr++; - continue; - } - if (*ptr == w_many) - { /* '%' in SQL */ - *min_length = (size_t)(min_str - min_org); - *max_length = res_length; - do - { - *min_str++= 0; - *max_str++= max_sort_char; - } while (min_str < min_end); - return 0; - } - *min_str++ = *max_str++ = *ptr++; - } - *min_length = *max_length = (size_t) (min_str - min_org); - while (min_str < min_end) - *min_str++ = *max_str++ = ' '; /* Because if key compression */ - return 0; -} - /* page 0 0x00A1-0x00DF */ static uint16 tab_cp932_uni0[]={ 0xFF61,0xFF62,0xFF63,0xFF64,0xFF65,0xFF66,0xFF67,0xFF68, @@ -5467,7 +5397,7 @@ static MY_COLLATION_HANDLER my_collation_ci_handler = my_strnncollsp_cp932, my_strnxfrm_cp932, my_strnxfrmlen_simple, - my_like_range_cp932, + my_like_range_mb, my_wildcmp_mb, /* wildcmp */ my_strcasecmp_8bit, my_instr_mb, @@ -5533,7 +5463,7 @@ CHARSET_INFO my_charset_cp932_japanese_ci= 1, /* mbminlen */ 2, /* mbmaxlen */ 0, /* min_sort_char */ - 255, /* max_sort_char */ + 0xFCFC, /* max_sort_char */ ' ', /* pad char */ 1, /* escape_with_backslash_is_dangerous */ &my_charset_handler, @@ -5565,7 +5495,7 @@ CHARSET_INFO my_charset_cp932_bin= 1, /* mbminlen */ 2, /* mbmaxlen */ 0, /* min_sort_char */ - 255, /* max_sort_char */ + 0xFCFC, /* max_sort_char */ ' ', /* pad char */ 1, /* escape_with_backslash_is_dangerous */ &my_charset_handler, diff --git a/strings/ctype-euc_kr.c b/strings/ctype-euc_kr.c index fc0af7e35d5..ee957304716 100644 --- a/strings/ctype-euc_kr.c +++ b/strings/ctype-euc_kr.c @@ -8762,7 +8762,7 @@ CHARSET_INFO my_charset_euckr_korean_ci= 1, /* mbminlen */ 2, /* mbmaxlen */ 0, /* min_sort_char */ - 255, /* max_sort_char */ + 0xFEFE, /* max_sort_char */ ' ', /* pad char */ 0, /* escape_with_backslash_is_dangerous */ &my_charset_handler, @@ -8795,7 +8795,7 @@ CHARSET_INFO my_charset_euckr_bin= 1, /* mbminlen */ 2, /* mbmaxlen */ 0, /* min_sort_char */ - 255, /* max_sort_char */ + 0xFEFE, /* max_sort_char */ ' ', /* pad char */ 0, /* escape_with_backslash_is_dangerous */ &my_charset_handler, diff --git a/strings/ctype-eucjpms.c b/strings/ctype-eucjpms.c index b8b04dfca6b..615981b4d27 100644 --- a/strings/ctype-eucjpms.c +++ b/strings/ctype-eucjpms.c @@ -8710,7 +8710,7 @@ CHARSET_INFO my_charset_eucjpms_japanese_ci= 1, /* mbminlen */ 3, /* mbmaxlen */ 0, /* min_sort_char */ - 255, /* max_sort_char */ + 0xFEFE, /* max_sort_char */ ' ', /* pad_char */ 0, /* escape_with_backslash_is_dangerous */ &my_charset_handler, @@ -8743,7 +8743,7 @@ CHARSET_INFO my_charset_eucjpms_bin= 1, /* mbminlen */ 3, /* mbmaxlen */ 0, /* min_sort_char */ - 255, /* max_sort_char */ + 0xFEFE, /* max_sort_char */ ' ', /* pad_char */ 0, /* escape_with_backslash_is_dangerous */ &my_charset_handler, diff --git a/strings/ctype-gb2312.c b/strings/ctype-gb2312.c index 0267f35ff5c..84f67dbbc2e 100644 --- a/strings/ctype-gb2312.c +++ b/strings/ctype-gb2312.c @@ -5790,7 +5790,7 @@ CHARSET_INFO my_charset_gb2312_chinese_ci= 1, /* mbminlen */ 2, /* mbmaxlen */ 0, /* min_sort_char */ - 255, /* max_sort_char */ + 0xF7FE, /* max_sort_char */ ' ', /* pad char */ 0, /* escape_with_backslash_is_dangerous */ &my_charset_handler, @@ -5822,7 +5822,7 @@ CHARSET_INFO my_charset_gb2312_bin= 1, /* mbminlen */ 2, /* mbmaxlen */ 0, /* min_sort_char */ - 255, /* max_sort_char */ + 0xF7FE, /* max_sort_char */ ' ', /* pad char */ 0, /* escape_with_backslash_is_dangerous */ &my_charset_handler, diff --git a/strings/ctype-gbk.c b/strings/ctype-gbk.c index 7b8bb85652b..89607823d34 100644 --- a/strings/ctype-gbk.c +++ b/strings/ctype-gbk.c @@ -2690,86 +2690,6 @@ static size_t my_strnxfrm_gbk(CHARSET_INFO *cs __attribute__((unused)), } -/* -** Calculate min_str and max_str that ranges a LIKE string. -** Arguments: -** ptr Pointer to LIKE string. -** ptr_length Length of LIKE string. -** escape Escape character in LIKE. (Normally '\'). -** All escape characters should be removed from min_str and max_str -** res_length Length of min_str and max_str. -** min_str Smallest case sensitive string that ranges LIKE. -** Should be space padded to res_length. -** max_str Largest case sensitive string that ranges LIKE. -** Normally padded with the biggest character sort value. -** -** The function should return 0 if ok and 1 if the LIKE string can't be -** optimized ! -*/ - -#define max_sort_char ((uchar) 255) - -static my_bool my_like_range_gbk(CHARSET_INFO *cs __attribute__((unused)), - const char *ptr,size_t ptr_length, - pbool escape, pbool w_one, pbool w_many, - size_t res_length, - char *min_str,char *max_str, - size_t *min_length,size_t *max_length) -{ - const char *end= ptr + ptr_length; - char *min_org=min_str; - char *min_end=min_str+res_length; - size_t charlen= res_length / cs->mbmaxlen; - - for (; ptr != end && min_str != min_end && charlen > 0; ptr++, charlen--) - { - if (ptr+1 != end && isgbkcode(ptr[0],ptr[1])) - { - *min_str++= *max_str++ = *ptr++; - *min_str++= *max_str++ = *ptr; - continue; - } - if (*ptr == escape && ptr+1 != end) - { - ptr++; /* Skip escape */ - if (isgbkcode(ptr[0], ptr[1])) - *min_str++= *max_str++ = *ptr; - if (min_str < min_end) - *min_str++= *max_str++= *ptr; - continue; - } - if (*ptr == w_one) /* '_' in SQL */ - { - *min_str++='\0'; /* This should be min char */ - *max_str++=max_sort_char; - continue; - } - if (*ptr == w_many) /* '%' in SQL */ - { - /* - Calculate length of keys: - 'a\0\0... is the smallest possible string when we have space expand - a\ff\ff... is the biggest possible string - */ - *min_length= ((cs->state & MY_CS_BINSORT) ? (size_t) (min_str - min_org) : - res_length); - *max_length= res_length; - do { - *min_str++= 0; - *max_str++= max_sort_char; - } while (min_str != min_end); - return 0; - } - *min_str++= *max_str++ = *ptr; - } - - *min_length= *max_length = (size_t) (min_str - min_org); - while (min_str != min_end) - *min_str++= *max_str++= ' '; /* Because if key compression */ - return 0; -} - - static uint ismbchar_gbk(CHARSET_INFO *cs __attribute__((unused)), const char* p, const char *e) { @@ -9983,7 +9903,7 @@ static MY_COLLATION_HANDLER my_collation_ci_handler = my_strnncollsp_gbk, my_strnxfrm_gbk, my_strnxfrmlen_simple, - my_like_range_gbk, + my_like_range_mb, my_wildcmp_mb, my_strcasecmp_mb, my_instr_mb, @@ -10048,7 +9968,7 @@ CHARSET_INFO my_charset_gbk_chinese_ci= 1, /* mbminlen */ 2, /* mbmaxlen */ 0, /* min_sort_char */ - 255, /* max_sort_char */ + 0xA967, /* max_sort_char */ ' ', /* pad char */ 1, /* escape_with_backslash_is_dangerous */ &my_charset_handler, @@ -10080,7 +10000,7 @@ CHARSET_INFO my_charset_gbk_bin= 1, /* mbminlen */ 2, /* mbmaxlen */ 0, /* min_sort_char */ - 255, /* max_sort_char */ + 0xFEFE, /* max_sort_char */ ' ', /* pad char */ 1, /* escape_with_backslash_is_dangerous */ &my_charset_handler, diff --git a/strings/ctype-mb.c b/strings/ctype-mb.c index 903811e2ab9..e3788fc4dff 100644 --- a/strings/ctype-mb.c +++ b/strings/ctype-mb.c @@ -498,7 +498,9 @@ static void my_hash_sort_mb_bin(CHARSET_INFO *cs __attribute__((unused)), DESCRIPTION Write max key: - for non-Unicode character sets: - just set to 255. + just bfill using max_sort_char if max_sort_char is one byte. + In case when max_sort_char is two bytes, fill with double-byte pairs + and optionally pad with a single space character. - for Unicode character set (utf-8): create a buffer with multibyte representation of the max_sort_char character, and copy it into max_str in a loop. @@ -510,12 +512,20 @@ static void pad_max_char(CHARSET_INFO *cs, char *str, char *end) if (!(cs->state & MY_CS_UNICODE)) { - bfill(str, end - str, 255); - return; + if (cs->max_sort_char <= 255) + { + bfill(str, end - str, cs->max_sort_char); + return; + } + buf[0]= cs->max_sort_char >> 8; + buf[1]= cs->max_sort_char & 0xFF; + buflen= 2; + } + else + { + buflen= cs->cset->wc_mb(cs, cs->max_sort_char, (uchar*) buf, + (uchar*) buf + sizeof(buf)); } - - buflen= cs->cset->wc_mb(cs, cs->max_sort_char, (uchar*) buf, - (uchar*) buf + sizeof(buf)); DBUG_ASSERT(buflen > 0); do diff --git a/strings/ctype-sjis.c b/strings/ctype-sjis.c index ac426e0d7b5..3f479ffc102 100644 --- a/strings/ctype-sjis.c +++ b/strings/ctype-sjis.c @@ -304,85 +304,6 @@ static size_t my_strnxfrm_sjis(CHARSET_INFO *cs __attribute__((unused)), } -/* -** Calculate min_str and max_str that ranges a LIKE string. -** Arguments: -** ptr Pointer to LIKE string. -** ptr_length Length of LIKE string. -** escape Escape character in LIKE. (Normally '\'). -** All escape characters should be removed from min_str and max_str -** res_length Length of min_str and max_str. -** min_str Smallest case sensitive string that ranges LIKE. -** Should be space padded to res_length. -** max_str Largest case sensitive string that ranges LIKE. -** Normally padded with the biggest character sort value. -** -** The function should return 0 if ok and 1 if the LIKE string can't be -** optimized ! -*/ - -#define max_sort_char ((char) 255) - -static my_bool my_like_range_sjis(CHARSET_INFO *cs __attribute__((unused)), - const char *ptr,size_t ptr_length, - pbool escape, pbool w_one, pbool w_many, - size_t res_length, - char *min_str,char *max_str, - size_t *min_length,size_t *max_length) -{ - const char *end= ptr + ptr_length; - char *min_org=min_str; - char *min_end=min_str+res_length; - size_t charlen= res_length / cs->mbmaxlen; - - for ( ; ptr < end && min_str < min_end && charlen > 0 ; charlen--) - { - if (ismbchar_sjis(cs, ptr, end)) { - *min_str++ = *max_str++ = *ptr++; - if (min_str < min_end) - *min_str++ = *max_str++ = *ptr++; - continue; - } - if (*ptr == escape && ptr+1 < end) { - ptr++; /* Skip escape */ - if (ismbchar_sjis(cs, ptr, end)) - *min_str++ = *max_str++ = *ptr++; - if (min_str < min_end) - *min_str++ = *max_str++ = *ptr++; - continue; - } - if (*ptr == w_one) { /* '_' in SQL */ - *min_str++ = '\0'; /* This should be min char */ - *max_str++ = max_sort_char; - ptr++; - continue; - } - if (*ptr == w_many) - { /* '%' in SQL */ - /* - Calculate length of keys: - 'a\0\0... is the smallest possible string when we have space expand - a\ff\ff... is the biggest possible string - */ - *min_length= ((cs->state & MY_CS_BINSORT) ? (size_t) (min_str - min_org) : - res_length); - *max_length= res_length; - do - { - *min_str++= 0; - *max_str++= max_sort_char; - } while (min_str < min_end); - return 0; - } - *min_str++ = *max_str++ = *ptr++; - } - - *min_length= *max_length= (size_t) (min_str - min_org); - while (min_str != min_end) - *min_str++= *max_str++= ' '; /* Because if key compression */ - return 0; -} - /* page 0 0x00A1-0x00DF */ static uint16 tab_sjis_uni0[]={ 0xFF61,0xFF62,0xFF63,0xFF64,0xFF65,0xFF66,0xFF67,0xFF68, @@ -4628,7 +4549,7 @@ static MY_COLLATION_HANDLER my_collation_ci_handler = my_strnncollsp_sjis, my_strnxfrm_sjis, my_strnxfrmlen_simple, - my_like_range_sjis, + my_like_range_mb, my_wildcmp_mb, /* wildcmp */ my_strcasecmp_8bit, my_instr_mb, @@ -4694,7 +4615,7 @@ CHARSET_INFO my_charset_sjis_japanese_ci= 1, /* mbminlen */ 2, /* mbmaxlen */ 0, /* min_sort_char */ - 255, /* max_sort_char */ + 0xFCFC, /* max_sort_char */ ' ', /* pad char */ 1, /* escape_with_backslash_is_dangerous */ &my_charset_handler, @@ -4726,7 +4647,7 @@ CHARSET_INFO my_charset_sjis_bin= 1, /* mbminlen */ 2, /* mbmaxlen */ 0, /* min_sort_char */ - 255, /* max_sort_char */ + 0xFCFC, /* max_sort_char */ ' ', /* pad char */ 1, /* escape_with_backslash_is_dangerous */ &my_charset_handler, diff --git a/strings/ctype-ujis.c b/strings/ctype-ujis.c index 1a872a92595..4474bd0cf96 100644 --- a/strings/ctype-ujis.c +++ b/strings/ctype-ujis.c @@ -8567,7 +8567,7 @@ CHARSET_INFO my_charset_ujis_japanese_ci= 1, /* mbminlen */ 3, /* mbmaxlen */ 0, /* min_sort_char */ - 255, /* max_sort_char */ + 0xFEFE, /* max_sort_char */ ' ', /* pad char */ 0, /* escape_with_backslash_is_dangerous */ &my_charset_handler, @@ -8600,7 +8600,7 @@ CHARSET_INFO my_charset_ujis_bin= 1, /* mbminlen */ 3, /* mbmaxlen */ 0, /* min_sort_char */ - 255, /* max_sort_char */ + 0xFEFE, /* max_sort_char */ ' ', /* pad char */ 0, /* escape_with_backslash_is_dangerous */ &my_charset_handler, diff --git a/unittest/Makefile.am b/unittest/Makefile.am index 65fa615fb98..889e029f6ef 100644 --- a/unittest/Makefile.am +++ b/unittest/Makefile.am @@ -13,12 +13,12 @@ # along with this program; if not, write to the Free Software # Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA -SUBDIRS = mytap . mysys examples +SUBDIRS = mytap . mysys examples strings EXTRA_DIST = unit.pl CLEANFILES = unit -unittests = mytap mysys @mysql_se_unittest_dirs@ @mysql_pg_unittest_dirs@ +unittests = mytap mysys strings @mysql_se_unittest_dirs@ @mysql_pg_unittest_dirs@ test: perl unit.pl run $(unittests) diff --git a/unittest/strings/Makefile.am b/unittest/strings/Makefile.am new file mode 100644 index 00000000000..5b18d89f58e --- /dev/null +++ b/unittest/strings/Makefile.am @@ -0,0 +1,27 @@ +# Copyright 2000, 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 + +AM_CPPFLAGS = @ZLIB_INCLUDES@ -I$(top_builddir)/include +AM_CPPFLAGS += -I$(top_srcdir)/include -I$(top_srcdir)/unittest/mytap + +LDADD = $(top_builddir)/unittest/mytap/libmytap.a \ + $(top_builddir)/mysys/libmysys.a \ + $(top_builddir)/dbug/libdbug.a \ + $(top_builddir)/strings/libmystrings.a + +noinst_PROGRAMS = strings-t + +# Don't update the files from bitkeeper +%::SCCS/s.% diff --git a/unittest/strings/strings-t.c b/unittest/strings/strings-t.c new file mode 100644 index 00000000000..2d246cfa17f --- /dev/null +++ b/unittest/strings/strings-t.c @@ -0,0 +1,114 @@ +/* Copyright 2000, 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 */ + +#include +#include +#include + + +/* + Test that like_range() returns well-formed results. +*/ +static int +test_like_range_for_charset(CHARSET_INFO *cs, const char *src, size_t src_len) +{ + char min_str[32], max_str[32]; + size_t min_len, max_len, min_well_formed_len, max_well_formed_len; + int error= 0; + + cs->coll->like_range(cs, src, src_len, '\\', '_', '%', + sizeof(min_str), min_str, max_str, &min_len, &max_len); + diag("min_len=%d\tmax_len=%d\t%s", min_len, max_len, cs->name); + min_well_formed_len= cs->cset->well_formed_len(cs, + min_str, min_str + min_len, + 10000, &error); + max_well_formed_len= cs->cset->well_formed_len(cs, + max_str, max_str + max_len, + 10000, &error); + if (min_len != min_well_formed_len) + diag("Bad min_str: min_well_formed_len=%d min_str[%d]=0x%02X", + min_well_formed_len, min_well_formed_len, + (uchar) min_str[min_well_formed_len]); + if (max_len != max_well_formed_len) + diag("Bad max_str: max_well_formed_len=%d max_str[%d]=0x%02X", + max_well_formed_len, max_well_formed_len, + (uchar) max_str[max_well_formed_len]); + return + min_len == min_well_formed_len && + max_len == max_well_formed_len ? 0 : 1; +} + + +static CHARSET_INFO *charset_list[]= +{ +#ifdef HAVE_CHARSET_big5 + &my_charset_big5_chinese_ci, + &my_charset_big5_bin, +#endif +#ifdef HAVE_CHARSET_euckr + &my_charset_euckr_korean_ci, + &my_charset_euckr_bin, +#endif +#ifdef HAVE_CHARSET_gb2312 + &my_charset_gb2312_chinese_ci, + &my_charset_gb2312_bin, +#endif +#ifdef HAVE_CHARSET_gbk + &my_charset_gbk_chinese_ci, + &my_charset_gbk_bin, +#endif +#ifdef HAVE_CHARSET_latin1 + &my_charset_latin1, + &my_charset_latin1_bin, +#endif +#ifdef HAVE_CHARSET_sjis + &my_charset_sjis_japanese_ci, + &my_charset_sjis_bin, +#endif +#ifdef HAVE_CHARSET_tis620 + &my_charset_tis620_thai_ci, + &my_charset_tis620_bin, +#endif +#ifdef HAVE_CHARSET_ujis + &my_charset_ujis_japanese_ci, + &my_charset_ujis_bin, +#endif +#ifdef HAVE_CHARSET_utf8 + &my_charset_utf8_general_ci, + &my_charset_utf8_unicode_ci, + &my_charset_utf8_bin, +#endif +}; + + +int main() +{ + size_t i, failed= 0; + + plan(1); + diag("Testing my_like_range_xxx() functions"); + + for (i= 0; i < array_elements(charset_list); i++) + { + CHARSET_INFO *cs= charset_list[i]; + if (test_like_range_for_charset(cs, "abc%", 4)) + { + ++failed; + diag("Failed for %s", cs->name); + } + } + ok(failed == 0, "Testing my_like_range_xxx() functions"); + return exit_status(); +} From c9e579bbb095738e603ea45d0e6a171484dd71f2 Mon Sep 17 00:00:00 2001 From: Dmitry Lenev Date: Mon, 26 Jul 2010 13:22:38 +0400 Subject: [PATCH 085/129] Test for bug #53820 "ALTER a MEDIUMINT column table causes full table copy". This patch only adds test case as the bug itself was addressed by Ramil's fix for bug 50946 "fast index creation still seems to copy the table". --- mysql-test/r/alter_table.result | 13 +++++++++++++ mysql-test/t/alter_table.test | 16 ++++++++++++++++ 2 files changed, 29 insertions(+) diff --git a/mysql-test/r/alter_table.result b/mysql-test/r/alter_table.result index 90dde034e10..304f562d47d 100644 --- a/mysql-test/r/alter_table.result +++ b/mysql-test/r/alter_table.result @@ -1370,3 +1370,16 @@ CREATE TABLE t1 (id int); INSERT INTO t1 VALUES (1), (2); ALTER TABLE t1 ADD COLUMN (f1 INT), ADD COLUMN (f2 INT), ADD KEY f2k(f2); DROP TABLE t1; +# +# Test for bug #53820 "ALTER a MEDIUMINT column table causes full +# table copy". +# +DROP TABLE IF EXISTS t1; +CREATE TABLE t1 (a INT, b MEDIUMINT); +INSERT INTO t1 VALUES (1, 1), (2, 2); +# The below ALTER should not copy table and so no rows should +# be shown as affected. +ALTER TABLE t1 CHANGE a id INT; +affected rows: 0 +info: Records: 0 Duplicates: 0 Warnings: 0 +DROP TABLE t1; diff --git a/mysql-test/t/alter_table.test b/mysql-test/t/alter_table.test index d7f7a12cbf8..5b5fdf50c16 100644 --- a/mysql-test/t/alter_table.test +++ b/mysql-test/t/alter_table.test @@ -1128,3 +1128,19 @@ INSERT INTO t1 VALUES (1), (2); ALTER TABLE t1 ADD COLUMN (f1 INT), ADD COLUMN (f2 INT), ADD KEY f2k(f2); DROP TABLE t1; + +--echo # +--echo # Test for bug #53820 "ALTER a MEDIUMINT column table causes full +--echo # table copy". +--echo # +--disable_warnings +DROP TABLE IF EXISTS t1; +--enable_warnings +CREATE TABLE t1 (a INT, b MEDIUMINT); +INSERT INTO t1 VALUES (1, 1), (2, 2); +--echo # The below ALTER should not copy table and so no rows should +--echo # be shown as affected. +--enable_info +ALTER TABLE t1 CHANGE a id INT; +--disable_info +DROP TABLE t1; From 36290c092392c460132f3d7256aeeb8f94debe8f Mon Sep 17 00:00:00 2001 From: Konstantin Osipov Date: Tue, 27 Jul 2010 14:25:53 +0400 Subject: [PATCH 086/129] A pre-requisite patch for the fix for Bug#52044. This patch also fixes Bug#55452 "SET PASSWORD is replicated twice in RBR mode". The goal of this patch is to remove the release of metadata locks from close_thread_tables(). This is necessary to not mistakenly release the locks in the course of a multi-step operation that involves multiple close_thread_tables() or close_tables_for_reopen(). On the same token, move statement commit outside close_thread_tables(). Other cleanups: Cleanup COM_FIELD_LIST. Don't call close_thread_tables() in COM_SHUTDOWN -- there are no open tables there that can be closed (we leave the locked tables mode in THD destructor, and this close_thread_tables() won't leave it anyway). Make open_and_lock_tables() and open_and_lock_tables_derived() call close_thread_tables() upon failure. Remove the calls to close_thread_tables() that are now unnecessary. Simplify the back off condition in Open_table_context. Streamline metadata lock handling in LOCK TABLES implementation. Add asserts to ensure correct life cycle of statement transaction in a session. Remove a piece of dead code that has also become redundant after the fix for Bug 37521. mysql-test/r/variables.result: Update results: set @@autocommit and statement transaction/ prelocked mode. mysql-test/r/view.result: A harmless change in CHECK TABLE status for a broken view. If previously a failure to prelock all functions used in a view would leave the connection in LTM_PRELOCKED mode, now we call close_thread_tables() from open_and_lock_tables() and leave prelocked mode, thus some check in mysql_admin_table() that works only in prelocked/locked tables mode is no longer activated. mysql-test/suite/rpl/r/rpl_row_implicit_commit_binlog.result: Fixed Bug#55452 "SET PASSWORD is replicated twice in RBR mode": extra binlog events are gone from the binary log. mysql-test/t/variables.test: Add a test case: set autocommit and statement transaction/prelocked mode. sql/event_data_objects.cc: Simplify code in Event_job_data::execute(). Move sp_head memory management to lex_end(). sql/event_db_repository.cc: Move the release of metadata locks outside close_thread_tables(). Make sure we call close_thread_tables() when open_and_lock_tables() fails and remove extra code from the events data dictionary. Use close_mysql_tables(), a new internal function to properly close mysql.* tables in the data dictionary. Contract Event_db_repository::drop_events_by_field, drop_schema_events into one function. When dropping all events in a schema, make sure we don't mistakenly release all locks acquired by DROP DATABASE. These include locks on the database name and the global intention exclusive metadata lock. sql/event_db_repository.h: Function open_event_table() does not require an instance of Event_db_repository. sql/events.cc: Use close_mysql_tables() instead of close_thread_tables() to bootstrap events, since the latter no longer releases metadata locks. sql/ha_ndbcluster.cc: - mysql_rm_table_part2 no longer releases acquired metadata locks. Do it in the caller. sql/ha_ndbcluster_binlog.cc: Deploy the new protocol for closing thread tables in run_query() and ndb_binlog_index code. sql/handler.cc: Assert that we never call ha_commit_trans/ ha_rollback_trans in sub-statement, which is now the case. sql/handler.h: Add an accessor to check whether THD_TRANS object is empty (has no transaction started). sql/log.cc: Update a comment. sql/log_event.cc: Since now we commit/rollback statement transaction in mysql_execute_command(), we need a mechanism to communicate from Query_log_event::do_apply_event() to mysql_execute_command() that the statement transaction should be rolled back, not committed. Ideally it would be a virtual method of THD. I hesitate to make THD a virtual base class in this already large patch. Use a thd->variables.option_bits for now. Remove a call to close_thread_tables() from the slave IO thread. It doesn't open any tables, and the protocol for closing thread tables is more complicated now. Make sure we properly close thread tables, however, in Load_data_log_event, which doesn't follow the standard server execution procedure with mysql_execute_command(). @todo: this piece should use Server_runnable framework instead. Remove an unnecessary call to mysql_unlock_tables(). sql/rpl_rli.cc: Update Relay_log_info::slave_close_thread_tables() to follow the new close protocol. sql/set_var.cc: Remove an unused header. sql/slave.cc: Remove an unnecessary call to close_thread_tables(). sql/sp.cc: Remove unnecessary calls to close_thread_tables() from SP DDL implementation. The tables will be closed by the caller, in mysql_execute_command(). When dropping all routines in a database, make sure to not mistakenly drop all metadata locks acquired so far, they include the scoped lock on the schema. sql/sp_head.cc: Correct the protocol that closes thread tables in an SP instruction. Clear lex->sphead before cleaning up lex with lex_end to make sure that we don't delete the sphead twice. It's considered to be "cleaner" and more in line with future changes than calling delete lex->sphead in other places that cleanup the lex. sql/sp_head.h: When destroying m_lex_keeper of an instruction, don't delete the sphead that all lex objects share. @todo: don't store a reference to routine's sp_head instance in instruction's lex. sql/sql_acl.cc: Don't call close_thread_tables() where the caller will do that for us. Fix Bug#55452 "SET PASSWORD is replicated twice in RBR mode" by disabling RBR replication in change_password() function. Use close_mysql_tables() in bootstrap and ACL reload code to make sure we release all metadata locks. sql/sql_base.cc: This is the main part of the patch: - remove manipulation with thd->transaction and thd->mdl_context from close_thread_tables(). Now this function is only responsible for closing tables, nothing else. This is necessary to be able to easily use close_thread_tables() in procedures, that involve multiple open/close tables, which all need to be protected continuously by metadata locks. Add asserts ensuring that TABLE object is only used when is protected by a metadata lock. Simplify the back off condition of Open_table_context, we no longer need to look at the autocommit mode. Make open_and_lock_tables() and open_normal_and_derived_tables() close thread tables and release metadata locks acquired so-far upon failure. This simplifies their usage. Implement close_mysql_tables(). sql/sql_base.h: Add declaration for close_mysql_tables(). sql/sql_class.cc: Remove a piece of dead code that has also become redundant after the fix for Bug 37521. The code became dead when my_eof() was made a non-protocol method, but a method that merely modifies the diagnostics area. The code became redundant with the fix for Bug#37521, when we started to cal close_thread_tables() before Protocol::end_statement(). sql/sql_do.cc: Do nothing in DO if inside a substatement (the assert moved out of trans_rollback_stmt). sql/sql_handler.cc: Add comments. sql/sql_insert.cc: Remove dead code. Release metadata locks explicitly at the end of the delayed insert thread. sql/sql_lex.cc: Add destruction of lex->sphead to lex_end(), lex "reset" method called at the end of each statement. sql/sql_parse.cc: Move close_thread_tables() and other related cleanups to mysql_execute_command() from dispatch_command(). This has become possible after the fix for Bug#37521. Mark federated SERVER statements as DDL. Next step: make sure that we don't store eof packet in the query cache, and move the query cache code outside mysql_parse. Brush up the code of COM_FIELD_LIST. Remove unnecessary calls to close_thread_tables(). When killing a query, don't report "OK" if it was a suicide. sql/sql_parse.h: Remove declaration of a function that is now static. sql/sql_partition.cc: Remove an unnecessary call to close_thread_tables(). sql/sql_plugin.cc: open_and_lock_tables() will clean up after itself after a failure. Move close_thread_tables() above end: label, and replace with close_mysql_tables(), which will also release the metadata lock on mysql.plugin. sql/sql_prepare.cc: Now that we no longer release locks in close_thread_tables() statement prepare code has become more straightforward. Remove the now redundant check for thd->killed() (used only by the backup project) from Execute_server_runnable. Reorder code to take into account that now mysql_execute_command() performs lex->unit.cleanup() and close_thread_tables(). sql/sql_priv.h: Add a new option to server options to interact between the slave SQL thread and execution framework (hack). @todo: use a virtual method of class THD instead. sql/sql_servers.cc: Due to Bug 25705 replication of DROP/CREATE/ALTER SERVER is broken. Make sure at least we do not attempt to replicate these statements using RBR, as this violates the assert in close_mysql_tables(). sql/sql_table.cc: Do not release metadata locks in mysql_rm_table_part2, this is done by the caller. Do not call close_thread_tables() in mysql_create_table(), this is done by the caller. Fix a bug in DROP TABLE under LOCK TABLES when, upon error in wait_while_table_is_used() we would mistakenly release the metadata lock on a non-dropped table. Explicitly release metadata locks when doing an implicit commit. sql/sql_trigger.cc: Now that we delete lex->sphead in lex_end(), zero the trigger's sphead in lex after loading the trigger, to avoid double deletion. sql/sql_udf.cc: Use close_mysql_tables() instead of close_thread_tables(). sql/sys_vars.cc: Remove code added in scope of WL#4284 which would break when we perform set @@session.autocommit along with setting other variables and using tables or functions. A test case added to variables.test. sql/transaction.cc: Add asserts. sql/tztime.cc: Use close_mysql_tables() rather than close_thread_tables(). --- mysql-test/r/variables.result | 22 ++ mysql-test/r/view.result | 6 +- .../r/rpl_row_implicit_commit_binlog.result | 4 - mysql-test/t/variables.test | 26 +++ sql/event_data_objects.cc | 18 +- sql/event_db_repository.cc | 74 +++--- sql/event_db_repository.h | 5 +- sql/events.cc | 14 +- sql/ha_ndbcluster.cc | 3 +- sql/ha_ndbcluster_binlog.cc | 19 +- sql/handler.cc | 4 +- sql/handler.h | 1 + sql/log.cc | 2 +- sql/log_event.cc | 60 ++--- sql/rpl_rli.cc | 16 ++ sql/set_var.cc | 1 - sql/slave.cc | 1 - sql/sp.cc | 16 +- sql/sp_head.cc | 49 +++- sql/sp_head.h | 2 + sql/sql_acl.cc | 46 ++-- sql/sql_base.cc | 155 +++++++------ sql/sql_base.h | 1 + sql/sql_class.cc | 7 - sql/sql_cursor.cc | 2 + sql/sql_do.cc | 5 +- sql/sql_handler.cc | 21 +- sql/sql_insert.cc | 34 +-- sql/sql_lex.cc | 3 + sql/sql_parse.cc | 214 ++++++++++-------- sql/sql_parse.h | 1 - sql/sql_partition.cc | 3 +- sql/sql_plugin.cc | 4 +- sql/sql_prepare.cc | 42 +--- sql/sql_priv.h | 10 + sql/sql_servers.cc | 17 +- sql/sql_table.cc | 65 +++--- sql/sql_trigger.cc | 27 +-- sql/sql_udf.cc | 4 +- sql/sys_vars.cc | 15 +- sql/transaction.cc | 27 +++ sql/tztime.cc | 12 +- 42 files changed, 590 insertions(+), 468 deletions(-) diff --git a/mysql-test/r/variables.result b/mysql-test/r/variables.result index b6ad1ff31bf..be81afe1a43 100644 --- a/mysql-test/r/variables.result +++ b/mysql-test/r/variables.result @@ -1677,3 +1677,25 @@ SET @@sql_quote_show_create = @sql_quote_show_create_saved; # End of Bug#34828. +# Make sure we can manipulate with autocommit in the +# along with other variables. +drop table if exists t1; +drop function if exists t1_max; +drop function if exists t1_min; +create table t1 (a int) engine=innodb; +insert into t1(a) values (0), (1); +create function t1_max() returns int return (select max(a) from t1); +create function t1_min() returns int return (select min(a) from t1); +select t1_min(); +t1_min() +0 +select t1_max(); +t1_max() +1 +set @@session.autocommit=t1_min(), @@session.autocommit=t1_max(), +@@session.autocommit=t1_min(), @@session.autocommit=t1_max(), +@@session.autocommit=t1_min(), @@session.autocommit=t1_max(); +# Cleanup. +drop table t1; +drop function t1_min; +drop function t1_max; diff --git a/mysql-test/r/view.result b/mysql-test/r/view.result index e1c1d6f4128..96b45f0d5bb 100644 --- a/mysql-test/r/view.result +++ b/mysql-test/r/view.result @@ -1955,15 +1955,15 @@ CHECK TABLE v1, v2, v3, v4, v5, v6; Table Op Msg_type Msg_text test.v1 check Error FUNCTION test.f1 does not exist test.v1 check Error View 'test.v1' references invalid table(s) or column(s) or function(s) or definer/invoker of view lack rights to use them -test.v1 check status Operation failed +test.v1 check error Corrupt test.v2 check status OK test.v3 check Error FUNCTION test.f1 does not exist test.v3 check Error View 'test.v3' references invalid table(s) or column(s) or function(s) or definer/invoker of view lack rights to use them -test.v3 check status Operation failed +test.v3 check error Corrupt test.v4 check status OK test.v5 check Error FUNCTION test.f1 does not exist test.v5 check Error View 'test.v5' references invalid table(s) or column(s) or function(s) or definer/invoker of view lack rights to use them -test.v5 check status Operation failed +test.v5 check error Corrupt test.v6 check status OK create function f1 () returns int return (select max(col1) from t1); DROP TABLE t1; diff --git a/mysql-test/suite/rpl/r/rpl_row_implicit_commit_binlog.result b/mysql-test/suite/rpl/r/rpl_row_implicit_commit_binlog.result index 896ba90b865..459dc83e01d 100644 --- a/mysql-test/suite/rpl/r/rpl_row_implicit_commit_binlog.result +++ b/mysql-test/suite/rpl/r/rpl_row_implicit_commit_binlog.result @@ -165,10 +165,6 @@ master-bin.000001 # Table_map # # table_id: # (test.tt_1) master-bin.000001 # Write_rows # # table_id: # flags: STMT_END_F master-bin.000001 # Xid # # COMMIT /* XID */ master-bin.000001 # Query # # use `test`; SET PASSWORD FOR 'user'@'localhost'='*D8DECEC305209EEFEC43008E1D420E1AA06B19E0' -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Table_map # # table_id: # (mysql.user) -master-bin.000001 # Update_rows # # table_id: # flags: STMT_END_F -master-bin.000001 # Query # # COMMIT -e-e-e-e-e-e-e-e-e-e-e- >> << -e-e-e-e-e-e-e-e-e-e-e- -b-b-b-b-b-b-b-b-b-b-b- >> << -b-b-b-b-b-b-b-b-b-b-b- diff --git a/mysql-test/t/variables.test b/mysql-test/t/variables.test index d865851841f..75099523062 100644 --- a/mysql-test/t/variables.test +++ b/mysql-test/t/variables.test @@ -1405,4 +1405,30 @@ SET @@sql_quote_show_create = @sql_quote_show_create_saved; --echo # End of Bug#34828. --echo +--echo # Make sure we can manipulate with autocommit in the +--echo # along with other variables. + + +--disable_warnings +drop table if exists t1; +drop function if exists t1_max; +drop function if exists t1_min; +--enable_warnings + +create table t1 (a int) engine=innodb; +insert into t1(a) values (0), (1); +create function t1_max() returns int return (select max(a) from t1); +create function t1_min() returns int return (select min(a) from t1); +select t1_min(); +select t1_max(); +set @@session.autocommit=t1_min(), @@session.autocommit=t1_max(), + @@session.autocommit=t1_min(), @@session.autocommit=t1_max(), + @@session.autocommit=t1_min(), @@session.autocommit=t1_max(); + +--echo # Cleanup. +drop table t1; +drop function t1_min; +drop function t1_max; + + ########################################################################### diff --git a/sql/event_data_objects.cc b/sql/event_data_objects.cc index dd1845b29bc..52c509621ac 100644 --- a/sql/event_data_objects.cc +++ b/sql/event_data_objects.cc @@ -1402,6 +1402,8 @@ Event_job_data::execute(THD *thd, bool drop) */ thd->set_db(dbname.str, dbname.length); + lex_start(thd); + #ifndef NO_EMBEDDED_ACCESS_CHECKS if (event_sctx.change_security_context(thd, &definer_user, &definer_host, @@ -1411,7 +1413,7 @@ Event_job_data::execute(THD *thd, bool drop) "[%s].[%s.%s] execution failed, " "failed to authenticate the user.", definer.str, dbname.str, name.str); - goto end_no_lex_start; + goto end; } #endif @@ -1427,11 +1429,11 @@ Event_job_data::execute(THD *thd, bool drop) "[%s].[%s.%s] execution failed, " "user no longer has EVENT privilege.", definer.str, dbname.str, name.str); - goto end_no_lex_start; + goto end; } if (construct_sp_sql(thd, &sp_sql)) - goto end_no_lex_start; + goto end; /* Set up global thread attributes to reflect the properties of @@ -1451,8 +1453,6 @@ Event_job_data::execute(THD *thd, bool drop) if (parser_state.init(thd, thd->query(), thd->query_length())) goto end; - lex_start(thd); - if (parse_sql(thd, & parser_state, creation_ctx)) { sql_print_error("Event Scheduler: " @@ -1484,13 +1484,6 @@ Event_job_data::execute(THD *thd, bool drop) } end: - if (thd->lex->sphead) /* NULL only if a parse error */ - { - delete thd->lex->sphead; - thd->lex->sphead= NULL; - } - -end_no_lex_start: if (drop && !thd->is_fatal_error) { /* @@ -1529,7 +1522,6 @@ end_no_lex_start: if (save_sctx) event_sctx.restore_security_context(thd, save_sctx); #endif - lex_end(thd->lex); thd->lex->unit.cleanup(); thd->end_statement(); thd->cleanup_after_query(); diff --git a/sql/event_db_repository.cc b/sql/event_db_repository.cc index b7c01f10066..d47f1641bb0 100644 --- a/sql/event_db_repository.cc +++ b/sql/event_db_repository.cc @@ -518,17 +518,20 @@ Event_db_repository::table_scan_all_for_i_s(THD *thd, TABLE *schema_table, */ bool -Event_db_repository::fill_schema_events(THD *thd, TABLE_LIST *tables, +Event_db_repository::fill_schema_events(THD *thd, TABLE_LIST *i_s_table, const char *db) { - TABLE *schema_table= tables->table; - TABLE *event_table= NULL; + TABLE *schema_table= i_s_table->table; + Open_tables_backup open_tables_backup; + TABLE_LIST event_table; int ret= 0; DBUG_ENTER("Event_db_repository::fill_schema_events"); DBUG_PRINT("info",("db=%s", db? db:"(null)")); - if (open_event_table(thd, TL_READ, &event_table)) + event_table.init_one_table("mysql", 5, "event", 5, "event", TL_READ); + + if (open_system_tables_for_read(thd, &event_table, &open_tables_backup)) DBUG_RETURN(TRUE); /* @@ -541,11 +544,11 @@ Event_db_repository::fill_schema_events(THD *thd, TABLE_LIST *tables, every single row's `db` with the schema which we show. */ if (db) - ret= index_read_for_db_for_i_s(thd, schema_table, event_table, db); + ret= index_read_for_db_for_i_s(thd, schema_table, event_table.table, db); else - ret= table_scan_all_for_i_s(thd, schema_table, event_table); + ret= table_scan_all_for_i_s(thd, schema_table, event_table.table); - close_thread_tables(thd); + close_system_tables(thd, &open_tables_backup); DBUG_PRINT("info", ("Return code=%d", ret)); DBUG_RETURN(ret); @@ -584,10 +587,7 @@ Event_db_repository::open_event_table(THD *thd, enum thr_lock_type lock_type, tables.init_one_table("mysql", 5, "event", 5, "event", lock_type); if (open_and_lock_tables(thd, &tables, FALSE, MYSQL_LOCK_IGNORE_TIMEOUT)) - { - close_thread_tables(thd); DBUG_RETURN(TRUE); - } *table= tables.table; tables.table->use_all_columns(); @@ -700,7 +700,8 @@ Event_db_repository::create_event(THD *thd, Event_parse_data *parse_data, end: if (table) - close_thread_tables(thd); + close_mysql_tables(thd); + thd->variables.sql_mode= saved_mode; DBUG_RETURN(test(ret)); } @@ -811,7 +812,8 @@ Event_db_repository::update_event(THD *thd, Event_parse_data *parse_data, end: if (table) - close_thread_tables(thd); + close_mysql_tables(thd); + thd->variables.sql_mode= saved_mode; DBUG_RETURN(test(ret)); } @@ -865,7 +867,7 @@ Event_db_repository::drop_event(THD *thd, LEX_STRING db, LEX_STRING name, end: if (table) - close_thread_tables(thd); + close_mysql_tables(thd); DBUG_RETURN(test(ret)); } @@ -933,34 +935,14 @@ Event_db_repository::find_named_event(LEX_STRING db, LEX_STRING name, void Event_db_repository::drop_schema_events(THD *thd, LEX_STRING schema) -{ - DBUG_ENTER("Event_db_repository::drop_schema_events"); - drop_events_by_field(thd, ET_FIELD_DB, schema); - DBUG_VOID_RETURN; -} - - -/** - Drops all events which have a specific value of a field. - - @pre The thread handle has no open tables. - - @param[in,out] thd Thread - @param[in,out] table mysql.event TABLE - @param[in] field Which field of the row to use for matching - @param[in] field_value The value that should match -*/ - -void -Event_db_repository::drop_events_by_field(THD *thd, - enum enum_events_table_field field, - LEX_STRING field_value) { int ret= 0; TABLE *table= NULL; READ_RECORD read_record_info; - DBUG_ENTER("Event_db_repository::drop_events_by_field"); - DBUG_PRINT("enter", ("field=%d field_value=%s", field, field_value.str)); + enum enum_events_table_field field= ET_FIELD_DB; + MDL_ticket *mdl_savepoint= thd->mdl_context.mdl_savepoint(); + DBUG_ENTER("Event_db_repository::drop_schema_events"); + DBUG_PRINT("enter", ("field=%d schema=%s", field, schema.str)); if (open_event_table(thd, TL_WRITE, &table)) DBUG_VOID_RETURN; @@ -979,7 +961,7 @@ Event_db_repository::drop_events_by_field(THD *thd, get_field(thd->mem_root, table->field[ET_FIELD_NAME]))); - if (!sortcmp_lex_string(et_field_lex, field_value, system_charset_info)) + if (!sortcmp_lex_string(et_field_lex, schema, system_charset_info)) { DBUG_PRINT("info", ("Dropping")); if ((ret= table->file->ha_delete_row(table->record[0]))) @@ -989,6 +971,11 @@ Event_db_repository::drop_events_by_field(THD *thd, } end_read_record(&read_record_info); close_thread_tables(thd); + /* + Make sure to only release the MDL lock on mysql.event, not other + metadata locks DROP DATABASE might have acquired. + */ + thd->mdl_context.rollback_to_savepoint(mdl_savepoint); DBUG_VOID_RETURN; } @@ -1026,7 +1013,7 @@ Event_db_repository::load_named_event(THD *thd, LEX_STRING dbname, else if ((ret= etn->load_from_row(thd, table))) my_error(ER_CANNOT_LOAD_FROM_TABLE, MYF(0), "event"); - close_thread_tables(thd); + close_mysql_tables(thd); } thd->variables.sql_mode= saved_mode; @@ -1104,7 +1091,8 @@ update_timing_fields_for_event(THD *thd, end: if (table) - close_thread_tables(thd); + close_mysql_tables(thd); + /* Restore the state of binlog format */ DBUG_ASSERT(!thd->is_current_stmt_binlog_format_row()); if (save_binlog_row_based) @@ -1151,7 +1139,7 @@ Event_db_repository::check_system_tables(THD *thd) if (table_intact.check(tables.table, &mysql_db_table_def)) ret= 1; - close_thread_tables(thd); + close_mysql_tables(thd); } /* Check mysql.user */ tables.init_one_table("mysql", 5, "user", 4, "user", TL_READ); @@ -1171,7 +1159,7 @@ Event_db_repository::check_system_tables(THD *thd) event_priv_column_position); ret= 1; } - close_thread_tables(thd); + close_mysql_tables(thd); } /* Check mysql.event */ tables.init_one_table("mysql", 5, "event", 5, "event", TL_READ); @@ -1185,7 +1173,7 @@ Event_db_repository::check_system_tables(THD *thd) { if (table_intact.check(tables.table, &event_table_def)) ret= 1; - close_thread_tables(thd); + close_mysql_tables(thd); } DBUG_RETURN(test(ret)); diff --git a/sql/event_db_repository.h b/sql/event_db_repository.h index ef778407d1e..ea7f3bbac0e 100644 --- a/sql/event_db_repository.h +++ b/sql/event_db_repository.h @@ -91,7 +91,7 @@ public: bool load_named_event(THD *thd, LEX_STRING dbname, LEX_STRING name, Event_basic *et); - bool + static bool open_event_table(THD *thd, enum thr_lock_type lock_type, TABLE **table); bool @@ -109,9 +109,6 @@ public: static bool check_system_tables(THD *thd); private: - void - drop_events_by_field(THD *thd, enum enum_events_table_field field, - LEX_STRING field_value); bool index_read_for_db_for_i_s(THD *thd, TABLE *schema_table, TABLE *event_table, const char *db); diff --git a/sql/events.cc b/sql/events.cc index a548bda53e2..5379ec2c9eb 100644 --- a/sql/events.cc +++ b/sql/events.cc @@ -16,7 +16,7 @@ #include "sql_priv.h" #include "unireg.h" #include "sql_parse.h" // check_access -#include "sql_base.h" // close_thread_tables +#include "sql_base.h" // close_mysql_tables #include "sql_show.h" // append_definer #include "events.h" #include "sql_db.h" // check_db_dir_existence @@ -754,7 +754,6 @@ Events::fill_schema_events(THD *thd, TABLE_LIST *tables, COND * /* cond */) { char *db= NULL; int ret; - Open_tables_backup open_tables_backup; DBUG_ENTER("Events::fill_schema_events"); if (check_if_system_tables_error()) @@ -773,15 +772,7 @@ Events::fill_schema_events(THD *thd, TABLE_LIST *tables, COND * /* cond */) DBUG_RETURN(1); db= thd->lex->select_lex.db; } - /* - Reset and backup of the currently open tables in this thread - is a way to allow SELECTs from INFORMATION_SCHEMA.events under - LOCK TABLES and in pre-locked mode. See also - Events::show_create_event for additional comments. - */ - thd->reset_n_backup_open_tables_state(&open_tables_backup); ret= db_repository->fill_schema_events(thd, tables, db); - thd->restore_backup_open_tables_state(&open_tables_backup); DBUG_RETURN(ret); } @@ -1161,8 +1152,7 @@ Events::load_events_from_db(THD *thd) end: end_read_record(&read_record_info); - close_thread_tables(thd); - + close_mysql_tables(thd); DBUG_RETURN(ret); } diff --git a/sql/ha_ndbcluster.cc b/sql/ha_ndbcluster.cc index ecf2984a4c0..7cac8373bc4 100644 --- a/sql/ha_ndbcluster.cc +++ b/sql/ha_ndbcluster.cc @@ -7417,7 +7417,8 @@ int ndbcluster_find_files(handlerton *hton, THD *thd, FALSE, /* drop_temporary */ FALSE, /* drop_view */ TRUE /* dont_log_query*/); - + trans_commit_implicit(thd); /* Safety, should be unnecessary. */ + thd->mdl_context.release_transactional_locks(); /* Clear error message that is returned when table is deleted */ thd->clear_error(); } diff --git a/sql/ha_ndbcluster_binlog.cc b/sql/ha_ndbcluster_binlog.cc index 4f8bb66fcb0..b610687496e 100644 --- a/sql/ha_ndbcluster_binlog.cc +++ b/sql/ha_ndbcluster_binlog.cc @@ -298,13 +298,6 @@ static void run_query(THD *thd, char *buf, char *end, thd_ndb->m_error_code, (int) thd->is_error(), thd->is_slave_error); } - - /* - After executing statement we should unlock and close tables open - by it as well as release meta-data locks obtained by it. - */ - close_thread_tables(thd); - /* XXX: this code is broken. mysql_parse()/mysql_reset_thd_for_next_command() can not be called from within a statement, and @@ -2422,7 +2415,11 @@ int ndb_add_ndb_binlog_index(THD *thd, void *_row) } add_ndb_binlog_index_err: + thd->stmt_da->can_overwrite_status= TRUE; + thd->is_error() ? trans_rollback_stmt(thd) : trans_commit_stmt(thd); + thd->stmt_da->can_overwrite_status= FALSE; close_thread_tables(thd); + thd->mdl_context.release_transactional_locks(); ndb_binlog_index= 0; thd->variables.option_bits= saved_options; return error; @@ -3969,7 +3966,9 @@ restart: { if (ndb_binlog_index->s->needs_reopen()) { + trans_commit_stmt(thd); close_thread_tables(thd); + thd->mdl_context.release_transactional_locks(); ndb_binlog_index= 0; } } @@ -4280,7 +4279,9 @@ restart: if (do_ndbcluster_binlog_close_connection == BCCC_restart) { ndb_binlog_tables_inited= FALSE; + trans_commit_stmt(thd); close_thread_tables(thd); + thd->mdl_context.release_transactional_locks(); ndb_binlog_index= 0; goto restart; } @@ -4288,7 +4289,11 @@ err: sql_print_information("Stopping Cluster Binlog"); DBUG_PRINT("info",("Shutting down cluster binlog thread")); thd->proc_info= "Shutting down"; + thd->stmt_da->can_overwrite_status= TRUE; + thd->is_error() ? trans_rollback_stmt(thd) : trans_commit_stmt(thd); + thd->stmt_da->can_overwrite_status= FALSE; close_thread_tables(thd); + thd->mdl_context.release_transactional_locks(); mysql_mutex_lock(&injector_mutex); /* don't mess with the injector_ndb anymore from other threads */ injector_thd= 0; diff --git a/sql/handler.cc b/sql/handler.cc index b42840c7b1b..e67f5d6862c 100644 --- a/sql/handler.cc +++ b/sql/handler.cc @@ -1145,6 +1145,7 @@ int ha_commit_trans(THD *thd, bool all) if (thd->in_sub_stmt) { + DBUG_ASSERT(0); /* Since we don't support nested statement transactions in 5.0, we can't commit or rollback stmt transactions while we are inside @@ -1159,7 +1160,6 @@ int ha_commit_trans(THD *thd, bool all) bail out with error even before ha_commit_trans() call. To be 100% safe let us throw error in non-debug builds. */ - DBUG_ASSERT(0); my_error(ER_COMMIT_NOT_ALLOWED_IN_SF_OR_TRG, MYF(0)); DBUG_RETURN(2); } @@ -1342,6 +1342,7 @@ int ha_rollback_trans(THD *thd, bool all) if (thd->in_sub_stmt) { + DBUG_ASSERT(0); /* If we are inside stored function or trigger we should not commit or rollback current statement transaction. See comment in ha_commit_trans() @@ -1349,7 +1350,6 @@ int ha_rollback_trans(THD *thd, bool all) */ if (!all) DBUG_RETURN(0); - DBUG_ASSERT(0); my_error(ER_COMMIT_NOT_ALLOWED_IN_SF_OR_TRG, MYF(0)); DBUG_RETURN(1); } diff --git a/sql/handler.h b/sql/handler.h index 96095798d18..9f262542a4f 100644 --- a/sql/handler.h +++ b/sql/handler.h @@ -846,6 +846,7 @@ struct THD_TRANS bool modified_non_trans_table; void reset() { no_2pc= FALSE; modified_non_trans_table= FALSE; } + bool is_empty() const { return ha_list == NULL; } }; diff --git a/sql/log.cc b/sql/log.cc index b398cb1e73f..6eab16bc3a4 100644 --- a/sql/log.cc +++ b/sql/log.cc @@ -27,7 +27,7 @@ #include "my_global.h" /* NO_EMBEDDED_ACCESS_CHECKS */ #include "sql_priv.h" #include "log.h" -#include "sql_base.h" // close_thread_tables +#include "sql_base.h" // open_log_table #include "sql_repl.h" #include "sql_delete.h" // mysql_truncate #include "sql_parse.h" // command_name diff --git a/sql/log_event.cc b/sql/log_event.cc index 5236a2794cf..8f70282ce79 100644 --- a/sql/log_event.cc +++ b/sql/log_event.cc @@ -3332,6 +3332,19 @@ int Query_log_event::do_apply_event(Relay_log_info const *rli, thd->table_map_for_update= (table_map)table_map_for_update; thd->set_invoker(&user, &host); + /* + Flag if we need to rollback the statement transaction on + slave if it by chance succeeds. + If we expected a non-zero error code and get nothing and, + it is a concurrency issue or ignorable issue, effects + of the statement should be rolled back. + */ + if (expected_error && + (ignored_error_code(expected_error) || + concurrency_error_code(expected_error))) + { + thd->variables.option_bits|= OPTION_MASTER_SQL_ERROR; + } /* Execute the query (note that we bypass dispatch_command()) */ Parser_state parser_state; if (!parser_state.init(thd, thd->query(), thd->query_length())) @@ -3340,6 +3353,8 @@ int Query_log_event::do_apply_event(Relay_log_info const *rli, log_slow_statement(thd); } + thd->variables.option_bits&= ~OPTION_MASTER_SQL_ERROR; + /* Resetting the enable_slow_log thd variable. @@ -3382,7 +3397,6 @@ START SLAVE; . Query: '%s'", expected_error, thd->query()); general_log_write(thd, COM_QUERY, thd->query(), thd->query_length()); compare_errors: - /* In the slave thread, we may sometimes execute some DROP / * 40005 TEMPORARY * / TABLE that come from parts of binlogs (likely if we @@ -3430,25 +3444,7 @@ Default database: '%s'. Query: '%s'", DBUG_PRINT("info",("error ignored")); clear_all_errors(thd, const_cast(rli)); thd->killed= THD::NOT_KILLED; - /* - When an error is expected and matches the actual error the - slave does not report any error and by consequence changes - on transactional tables are not rolled back in the function - close_thread_tables(). For that reason, we explicitly roll - them back here. - */ - if (expected_error && expected_error == actual_error) - trans_rollback_stmt(thd); } - /* - If we expected a non-zero error code and get nothing and, it is a concurrency - issue or should be ignored. - */ - else if (expected_error && !actual_error && - (concurrency_error_code(expected_error) || - ignored_error_code(expected_error))) - trans_rollback_stmt(thd); - /* Other cases: mostly we expected no error and get one. */ @@ -3516,7 +3512,6 @@ end: thd->set_db(NULL, 0); /* will free the current database */ thd->set_query(NULL, 0); DBUG_PRINT("info", ("end: query= 0")); - close_thread_tables(thd); /* As a disk space optimization, future masters will not log an event for LAST_INSERT_ID() if that function returned 0 (and thus they will be able @@ -4946,7 +4941,22 @@ error: thd->catalog= 0; thd->set_db(NULL, 0); /* will free the current database */ thd->set_query(NULL, 0); + thd->stmt_da->can_overwrite_status= TRUE; + thd->is_error() ? trans_rollback_stmt(thd) : trans_commit_stmt(thd); + thd->stmt_da->can_overwrite_status= FALSE; close_thread_tables(thd); + /* + - If inside a multi-statement transaction, + defer the release of metadata locks until the current + transaction is either committed or rolled back. This prevents + other statements from modifying the table for the entire + duration of this transaction. This provides commit ordering + and guarantees serializability across multiple transactions. + - If in autocommit mode, or outside a transactional context, + automatically release metadata locks of the current statement. + */ + if (! thd->in_multi_stmt_transaction_mode()) + thd->mdl_context.release_transactional_locks(); DBUG_EXECUTE_IF("LOAD_DATA_INFILE_has_fatal_error", thd->is_slave_error= 0; thd->is_fatal_error= 1;); @@ -5531,11 +5541,9 @@ int Xid_log_event::do_apply_event(Relay_log_info const *rli) /* For a slave Xid_log_event is COMMIT */ general_log_print(thd, COM_QUERY, "COMMIT /* implicit, from Xid_log_event */"); - if (!(res= trans_commit(thd))) - { - close_thread_tables(thd); - thd->mdl_context.release_transactional_locks(); - } + res= trans_commit(thd); /* Automatically rolls back on error. */ + thd->mdl_context.release_transactional_locks(); + return res; } @@ -7610,8 +7618,6 @@ int Rows_log_event::do_apply_event(Relay_log_info const *rli) We should not honour --slave-skip-errors at this point as we are having severe errors which should not be skiped. */ - mysql_unlock_tables(thd, thd->lock); - thd->lock= 0; thd->is_slave_error= 1; const_cast(rli)->slave_close_thread_tables(thd); DBUG_RETURN(ERR_BAD_TABLE_DEF); diff --git a/sql/rpl_rli.cc b/sql/rpl_rli.cc index 03c369394bf..af9b452acd8 100644 --- a/sql/rpl_rli.cc +++ b/sql/rpl_rli.cc @@ -1257,7 +1257,23 @@ void Relay_log_info::clear_tables_to_lock() void Relay_log_info::slave_close_thread_tables(THD *thd) { + thd->stmt_da->can_overwrite_status= TRUE; + thd->is_error() ? trans_rollback_stmt(thd) : trans_commit_stmt(thd); + thd->stmt_da->can_overwrite_status= FALSE; + close_thread_tables(thd); + /* + - If inside a multi-statement transaction, + defer the release of metadata locks until the current + transaction is either committed or rolled back. This prevents + other statements from modifying the table for the entire + duration of this transaction. This provides commit ordering + and guarantees serializability across multiple transactions. + - If in autocommit mode, or outside a transactional context, + automatically release metadata locks of the current statement. + */ + if (! thd->in_multi_stmt_transaction_mode()) + thd->mdl_context.release_transactional_locks(); clear_tables_to_lock(); } #endif diff --git a/sql/set_var.cc b/sql/set_var.cc index ec9c09f02a3..9daaf883ea8 100644 --- a/sql/set_var.cc +++ b/sql/set_var.cc @@ -27,7 +27,6 @@ #include "mysqld.h" // lc_messages_dir #include "sys_vars_shared.h" #include "transaction.h" -#include "sql_base.h" // close_thread_tables #include "sql_locale.h" // my_locale_by_number, // my_locale_by_name #include "strfunc.h" // find_set_from_flags, find_set diff --git a/sql/slave.cc b/sql/slave.cc index d41d0479dde..a6199854e48 100644 --- a/sql/slave.cc +++ b/sql/slave.cc @@ -3044,7 +3044,6 @@ err: change_rpl_status(RPL_ACTIVE_SLAVE,RPL_IDLE_SLAVE); DBUG_ASSERT(thd->net.buff != 0); net_end(&thd->net); // destructor will not free it, because net.vio is 0 - close_thread_tables(thd); mysql_mutex_lock(&LOCK_thread_count); THD_CHECK_SENTRY(thd); delete thd; diff --git a/sql/sp.cc b/sql/sp.cc index 5328471f4c0..0265ef45a2a 100644 --- a/sql/sp.cc +++ b/sql/sp.cc @@ -450,10 +450,7 @@ static TABLE *open_proc_table_for_update(THD *thd) if (!proc_table_intact.check(table, &proc_table_def)) DBUG_RETURN(table); - close_thread_tables(thd); - DBUG_RETURN(NULL); - } @@ -856,6 +853,7 @@ db_load_routine(THD *thd, int type, sp_name *name, sp_head **sphp, } end: + thd->lex->sphead= NULL; lex_end(thd->lex); thd->lex= old_lex; return ret; @@ -1159,8 +1157,6 @@ sp_create_routine(THD *thd, int type, sp_head *sp) done: thd->count_cuted_fields= saved_count_cuted_fields; thd->variables.sql_mode= saved_mode; - - close_thread_tables(thd); /* Restore the state of binlog format */ DBUG_ASSERT(!thd->is_current_stmt_binlog_format_row()); if (save_binlog_row_based) @@ -1239,8 +1235,6 @@ sp_drop_routine(THD *thd, int type, sp_name *name) sp_cache_flush_obsolete(spc, &sp); } } - - close_thread_tables(thd); /* Restore the state of binlog format */ DBUG_ASSERT(!thd->is_current_stmt_binlog_format_row()); if (save_binlog_row_based) @@ -1348,7 +1342,6 @@ sp_update_routine(THD *thd, int type, sp_name *name, st_sp_chistics *chistics) sp_cache_invalidate(); } err: - close_thread_tables(thd); /* Restore the state of binlog format */ DBUG_ASSERT(!thd->is_current_stmt_binlog_format_row()); if (save_binlog_row_based) @@ -1370,6 +1363,7 @@ sp_drop_db_routines(THD *thd, char *db) TABLE *table; int ret; uint key_len; + MDL_ticket *mdl_savepoint= thd->mdl_context.mdl_savepoint(); DBUG_ENTER("sp_drop_db_routines"); DBUG_PRINT("enter", ("db: %s", db)); @@ -1410,6 +1404,11 @@ sp_drop_db_routines(THD *thd, char *db) table->file->ha_index_end(); close_thread_tables(thd); + /* + Make sure to only release the MDL lock on mysql.proc, not other + metadata locks DROP DATABASE might have acquired. + */ + thd->mdl_context.rollback_to_savepoint(mdl_savepoint); err: DBUG_RETURN(ret); @@ -2142,6 +2141,7 @@ sp_load_for_information_schema(THD *thd, TABLE *proc_table, String *db, newlex.current_select= NULL; sp= sp_compile(thd, &defstr, sql_mode, creation_ctx); *free_sp_head= 1; + thd->lex->sphead= NULL; lex_end(thd->lex); thd->lex= old_lex; return sp; diff --git a/sql/sp_head.cc b/sql/sp_head.cc index f75acf11984..11f138e67be 100644 --- a/sql/sp_head.cc +++ b/sql/sp_head.cc @@ -38,6 +38,7 @@ #include "set_var.h" #include "sql_parse.h" // cleanup_items #include "sql_base.h" // close_thread_tables +#include "transaction.h" // trans_commit_stmt /* Sufficient max length of printed destinations and frame offsets (all uints). @@ -795,6 +796,7 @@ sp_head::~sp_head() while ((lex= (LEX *)m_lex.pop())) { THD *thd= lex->thd; + thd->lex->sphead= NULL; lex_end(thd->lex); delete thd->lex; thd->lex= lex; @@ -1995,17 +1997,24 @@ sp_head::execute_procedure(THD *thd, List *args) arguments evaluation. If arguments evaluation required prelocking mode, we'll leave it here. */ + thd->lex->unit.cleanup(); + if (!thd->in_sub_stmt) { - thd->lex->unit.cleanup(); - - thd_proc_info(thd, "closing tables"); - close_thread_tables(thd); - thd_proc_info(thd, 0); - - thd->rollback_item_tree_changes(); + thd->stmt_da->can_overwrite_status= TRUE; + thd->is_error() ? trans_rollback_stmt(thd) : trans_commit_stmt(thd); + thd->stmt_da->can_overwrite_status= FALSE; } + thd_proc_info(thd, "closing tables"); + close_thread_tables(thd); + thd_proc_info(thd, 0); + + if (! thd->in_sub_stmt && ! thd->in_multi_stmt_transaction_mode()) + thd->mdl_context.release_transactional_locks(); + + thd->rollback_item_tree_changes(); + DBUG_PRINT("info",(" %.*s: eval args done", (int) m_name.length, m_name.str)); } @@ -2197,6 +2206,7 @@ sp_head::restore_lex(THD *thd) merge_table_list(thd, sublex->query_tables, sublex); if (! sublex->sp_lex_in_use) { + sublex->sphead= NULL; lex_end(sublex); delete sublex; } @@ -2806,12 +2816,27 @@ sp_lex_keeper::reset_lex_and_exec_core(THD *thd, uint *nextp, DBUG_PRINT("info",("exec_core returned: %d", res)); } - m_lex->unit.cleanup(); + /* + Call after unit->cleanup() to close open table + key read. + */ + if (open_tables) + { + m_lex->unit.cleanup(); + /* Here we also commit or rollback the current statement. */ + if (! thd->in_sub_stmt) + { + thd->stmt_da->can_overwrite_status= TRUE; + thd->is_error() ? trans_rollback_stmt(thd) : trans_commit_stmt(thd); + thd->stmt_da->can_overwrite_status= FALSE; + } + thd_proc_info(thd, "closing tables"); + close_thread_tables(thd); + thd_proc_info(thd, 0); - thd_proc_info(thd, "closing tables"); - /* Here we also commit or rollback the current statement. */ - close_thread_tables(thd); - thd_proc_info(thd, 0); + if (! thd->in_sub_stmt && ! thd->in_multi_stmt_transaction_mode()) + thd->mdl_context.release_transactional_locks(); + } if (m_lex->query_tables_own_last) { diff --git a/sql/sp_head.h b/sql/sp_head.h index 9796c49fdfb..b2446c8f680 100644 --- a/sql/sp_head.h +++ b/sql/sp_head.h @@ -682,6 +682,8 @@ public: { if (m_lex_resp) { + /* Prevent endless recursion. */ + m_lex->sphead= NULL; lex_end(m_lex); delete m_lex; } diff --git a/sql/sql_acl.cc b/sql/sql_acl.cc index d4c4f464884..0008968de2a 100644 --- a/sql/sql_acl.cc +++ b/sql/sql_acl.cc @@ -27,7 +27,7 @@ #include "my_global.h" /* NO_EMBEDDED_ACCESS_CHECKS */ #include "sql_priv.h" #include "sql_acl.h" // MYSQL_DB_FIELD_COUNT, ACL_ACCESS -#include "sql_base.h" // close_thread_tables +#include "sql_base.h" // close_mysql_tables #include "key.h" // key_copy, key_cmp_if_same, key_restore #include "sql_show.h" // append_identifier #include "sql_table.h" // build_table_filename @@ -730,9 +730,7 @@ my_bool acl_reload(THD *thd) if (old_initialized) mysql_mutex_unlock(&acl_cache->lock); end: - trans_commit_implicit(thd); - close_thread_tables(thd); - thd->mdl_context.release_transactional_locks(); + close_mysql_tables(thd); DBUG_RETURN(return_val); } @@ -1585,6 +1583,7 @@ bool change_password(THD *thd, const char *host, const char *user, /* Buffer should be extended when password length is extended. */ char buff[512]; ulong query_length; + bool save_binlog_row_based; uint new_password_len= (uint) strlen(new_password); bool result= 1; DBUG_ENTER("change_password"); @@ -1614,10 +1613,17 @@ bool change_password(THD *thd, const char *host, const char *user, DBUG_RETURN(0); } #endif - if (!(table= open_ltable(thd, &tables, TL_WRITE, MYSQL_LOCK_IGNORE_TIMEOUT))) DBUG_RETURN(1); + /* + This statement will be replicated as a statement, even when using + row-based replication. The flag will be reset at the end of the + statement. + */ + if ((save_binlog_row_based= thd->is_current_stmt_binlog_format_row())) + thd->clear_current_stmt_binlog_format_row(); + mysql_mutex_lock(&acl_cache->lock); ACL_USER *acl_user; if (!(acl_user= find_acl_user(host, user, TRUE))) @@ -1652,7 +1658,13 @@ bool change_password(THD *thd, const char *host, const char *user, FALSE, FALSE, FALSE, 0); } end: - close_thread_tables(thd); + close_mysql_tables(thd); + + /* Restore the state of binlog format */ + DBUG_ASSERT(!thd->is_current_stmt_binlog_format_row()); + if (save_binlog_row_based) + thd->set_current_stmt_binlog_format_row(); + DBUG_RETURN(result); } @@ -3082,7 +3094,7 @@ int mysql_table_grant(THD *thd, TABLE_LIST *table_list, DBUG_RETURN(TRUE); column_priv|= column->rights; } - close_thread_tables(thd); + close_mysql_tables(thd); } else { @@ -3172,7 +3184,6 @@ int mysql_table_grant(THD *thd, TABLE_LIST *table_list, thd->lex->sql_command= backup.sql_command; if (open_and_lock_tables(thd, tables, FALSE, MYSQL_LOCK_IGNORE_TIMEOUT)) { // Should never happen - close_thread_tables(thd); /* purecov: deadcode */ /* Restore the state of binlog format */ DBUG_ASSERT(!thd->is_current_stmt_binlog_format_row()); if (save_binlog_row_based) @@ -3398,7 +3409,6 @@ bool mysql_routine_grant(THD *thd, TABLE_LIST *table_list, bool is_proc, if (open_and_lock_tables(thd, tables, FALSE, MYSQL_LOCK_IGNORE_TIMEOUT)) { // Should never happen - close_thread_tables(thd); /* Restore the state of binlog format */ DBUG_ASSERT(!thd->is_current_stmt_binlog_format_row()); if (save_binlog_row_based) @@ -3553,7 +3563,6 @@ bool mysql_grant(THD *thd, const char *db, List &list, if (open_and_lock_tables(thd, tables, FALSE, MYSQL_LOCK_IGNORE_TIMEOUT)) { // This should never happen - close_thread_tables(thd); /* purecov: deadcode */ /* Restore the state of binlog format */ DBUG_ASSERT(!thd->is_current_stmt_binlog_format_row()); if (save_binlog_row_based) @@ -3613,7 +3622,6 @@ bool mysql_grant(THD *thd, const char *db, List &list, } mysql_rwlock_unlock(&LOCK_grant); - close_thread_tables(thd); if (!result) my_ok(thd); @@ -3874,10 +3882,7 @@ static my_bool grant_reload_procs_priv(THD *thd) table.open_type= OT_BASE_ONLY; if (open_and_lock_tables(thd, &table, FALSE, MYSQL_LOCK_IGNORE_TIMEOUT)) - { - close_thread_tables(thd); DBUG_RETURN(TRUE); - } mysql_rwlock_wrlock(&LOCK_grant); /* Save a copy of the current hash if we need to undo the grant load */ @@ -3899,7 +3904,7 @@ static my_bool grant_reload_procs_priv(THD *thd) } mysql_rwlock_unlock(&LOCK_grant); - close_thread_tables(thd); + close_mysql_tables(thd); DBUG_RETURN(return_val); } @@ -3970,9 +3975,7 @@ my_bool grant_reload(THD *thd) free_root(&old_mem,MYF(0)); } mysql_rwlock_unlock(&LOCK_grant); - trans_commit_implicit(thd); - close_thread_tables(thd); - thd->mdl_context.release_transactional_locks(); + close_mysql_tables(thd); /* It is OK failing to load procs_priv table because we may be @@ -5250,7 +5253,6 @@ int open_grant_tables(THD *thd, TABLE_LIST *tables) if (open_and_lock_tables(thd, tables, FALSE, MYSQL_LOCK_IGNORE_TIMEOUT)) { // This should never happen - close_thread_tables(thd); DBUG_RETURN(-1); } @@ -5890,7 +5892,6 @@ bool mysql_create_user(THD *thd, List &list) result |= write_bin_log(thd, FALSE, thd->query(), thd->query_length()); mysql_rwlock_unlock(&LOCK_grant); - close_thread_tables(thd); /* Restore the state of binlog format */ DBUG_ASSERT(!thd->is_current_stmt_binlog_format_row()); if (save_binlog_row_based) @@ -5975,7 +5976,6 @@ bool mysql_drop_user(THD *thd, List &list) result |= write_bin_log(thd, FALSE, thd->query(), thd->query_length()); mysql_rwlock_unlock(&LOCK_grant); - close_thread_tables(thd); thd->variables.sql_mode= old_sql_mode; /* Restore the state of binlog format */ DBUG_ASSERT(!thd->is_current_stmt_binlog_format_row()); @@ -6072,7 +6072,6 @@ bool mysql_rename_user(THD *thd, List &list) result |= write_bin_log(thd, FALSE, thd->query(), thd->query_length()); mysql_rwlock_unlock(&LOCK_grant); - close_thread_tables(thd); /* Restore the state of binlog format */ DBUG_ASSERT(!thd->is_current_stmt_binlog_format_row()); if (save_binlog_row_based) @@ -6270,8 +6269,6 @@ bool mysql_revoke_all(THD *thd, List &list) write_bin_log(thd, FALSE, thd->query(), thd->query_length()); mysql_rwlock_unlock(&LOCK_grant); - close_thread_tables(thd); - /* Restore the state of binlog format */ DBUG_ASSERT(!thd->is_current_stmt_binlog_format_row()); if (save_binlog_row_based) @@ -6418,7 +6415,6 @@ bool sp_revoke_privileges(THD *thd, const char *sp_db, const char *sp_name, mysql_mutex_unlock(&acl_cache->lock); mysql_rwlock_unlock(&LOCK_grant); - close_thread_tables(thd); thd->pop_internal_handler(); /* Restore the state of binlog format */ diff --git a/sql/sql_base.cc b/sql/sql_base.cc index 790898baae6..7a59fefdddd 100644 --- a/sql/sql_base.cc +++ b/sql/sql_base.cc @@ -1402,6 +1402,9 @@ void close_thread_tables(THD *thd) DEBUG_SYNC(thd, "before_close_thread_tables"); #endif + DBUG_ASSERT(thd->transaction.stmt.is_empty() || thd->in_sub_stmt || + (thd->state_flags & Open_tables_state::BACKUPS_AVAIL)); + /* Detach MERGE children after every statement. Even under LOCK TABLES. */ for (table= thd->open_tables; table; table= table->next) { @@ -1446,28 +1449,6 @@ void close_thread_tables(THD *thd) Mark all temporary tables used by this statement as free for reuse. */ mark_temp_tables_as_free_for_reuse(thd); - /* - Let us commit transaction for statement. Since in 5.0 we only have - one statement transaction and don't allow several nested statement - transactions this call will do nothing if we are inside of stored - function or trigger (i.e. statement transaction is already active and - does not belong to statement for which we do close_thread_tables()). - TODO: This should be fixed in later releases. - */ - if (!(thd->state_flags & Open_tables_state::BACKUPS_AVAIL)) - { - thd->stmt_da->can_overwrite_status= TRUE; - thd->is_error() ? trans_rollback_stmt(thd) : trans_commit_stmt(thd); - thd->stmt_da->can_overwrite_status= FALSE; - - /* - Reset transaction state, but only if we're not inside a - sub-statement of a prelocked statement. - */ - if (thd->locked_tables_mode <= LTM_LOCK_TABLES || - thd->lex->requires_prelocking()) - thd->transaction.stmt.reset(); - } if (thd->locked_tables_mode) { @@ -1528,26 +1509,6 @@ void close_thread_tables(THD *thd) if (thd->open_tables) close_open_tables(thd); - /* - - If inside a multi-statement transaction, - defer the release of metadata locks until the current - transaction is either committed or rolled back. This prevents - other statements from modifying the table for the entire - duration of this transaction. This provides commit ordering - and guarantees serializability across multiple transactions. - - If closing a system table, defer the release of metadata locks - to the caller. We have no sentinel in MDL subsystem to guard - transactional locks from system tables locks, so don't know - which locks are which here. - - If in autocommit mode, or outside a transactional context, - automatically release metadata locks of the current statement. - */ - if (! thd->in_multi_stmt_transaction_mode() && - ! (thd->state_flags & Open_tables_state::BACKUPS_AVAIL)) - { - thd->mdl_context.release_transactional_locks(); - } - DBUG_VOID_RETURN; } @@ -1562,7 +1523,14 @@ bool close_thread_table(THD *thd, TABLE **table_ptr) DBUG_ASSERT(table->key_read == 0); DBUG_ASSERT(!table->file || table->file->inited == handler::NONE); mysql_mutex_assert_not_owner(&LOCK_open); - + /* + The metadata lock must be released after giving back + the table to the table cache. + */ + DBUG_ASSERT(thd->mdl_context.is_lock_owner(MDL_key::TABLE, + table->s->db.str, + table->s->table_name.str, + MDL_SHARED)); table->mdl_ticket= NULL; mysql_mutex_lock(&thd->LOCK_thd_data); @@ -3188,6 +3156,7 @@ Locked_tables_list::init_locked_tables(THD *thd) return FALSE; } + /** Leave LTM_LOCK_TABLES mode if it's been entered. @@ -3224,7 +3193,12 @@ Locked_tables_list::unlock_locked_tables(THD *thd) } thd->leave_locked_tables_mode(); + DBUG_ASSERT(thd->transaction.stmt.is_empty()); close_thread_tables(thd); + /* + We rely on the caller to implicitly commit the + transaction and release transactional locks. + */ } /* After closing tables we can free memory used for storing lock @@ -3810,9 +3784,7 @@ Open_table_context::Open_table_context(THD *thd, uint flags) LONG_TIMEOUT : thd->variables.lock_wait_timeout), m_flags(flags), m_action(OT_NO_ACTION), - m_has_locks((thd->in_multi_stmt_transaction_mode() && - thd->mdl_context.has_locks()) || - thd->mdl_context.trans_sentinel()) + m_has_locks(thd->mdl_context.has_locks()) {} @@ -5264,6 +5236,8 @@ TABLE *open_ltable(THD *thd, TABLE_LIST *table_list, thr_lock_type lock_type, table= 0; end: + if (table == NULL) + close_thread_tables(thd); thd_proc_info(thd, 0); DBUG_RETURN(table); } @@ -5282,7 +5256,8 @@ end: should work for this statement. @note - The lock will automaticaly be freed by close_thread_tables() + The thr_lock locks will automatically be freed by + close_thread_tables(). @retval FALSE OK. @retval TRUE Error @@ -5293,11 +5268,12 @@ bool open_and_lock_tables(THD *thd, TABLE_LIST *tables, Prelocking_strategy *prelocking_strategy) { uint counter; + MDL_ticket *mdl_savepoint= thd->mdl_context.mdl_savepoint(); DBUG_ENTER("open_and_lock_tables"); DBUG_PRINT("enter", ("derived handling: %d", derived)); if (open_tables(thd, &tables, &counter, flags, prelocking_strategy)) - DBUG_RETURN(TRUE); + goto err; DBUG_EXECUTE_IF("sleep_open_and_lock_after_open", { const char *old_proc_info= thd->proc_info; @@ -5306,15 +5282,22 @@ bool open_and_lock_tables(THD *thd, TABLE_LIST *tables, thd->proc_info= old_proc_info;}); if (lock_tables(thd, tables, counter, flags)) - DBUG_RETURN(TRUE); + goto err; if (derived && (mysql_handle_derived(thd->lex, &mysql_derived_prepare) || (thd->fill_derived_tables() && mysql_handle_derived(thd->lex, &mysql_derived_filling)))) - DBUG_RETURN(TRUE); /* purecov: inspected */ + goto err; DBUG_RETURN(FALSE); +err: + if (! thd->in_sub_stmt) + trans_rollback_stmt(thd); /* Necessary if derived handling failed. */ + close_thread_tables(thd); + /* Don't keep locks for a failed statement. */ + thd->mdl_context.rollback_to_savepoint(mdl_savepoint); + DBUG_RETURN(TRUE); } @@ -5340,13 +5323,24 @@ bool open_and_lock_tables(THD *thd, TABLE_LIST *tables, bool open_normal_and_derived_tables(THD *thd, TABLE_LIST *tables, uint flags) { + DML_prelocking_strategy prelocking_strategy; uint counter; + MDL_ticket *mdl_savepoint= thd->mdl_context.mdl_savepoint(); DBUG_ENTER("open_normal_and_derived_tables"); DBUG_ASSERT(!thd->fill_derived_tables()); - if (open_tables(thd, &tables, &counter, flags) || + if (open_tables(thd, &tables, &counter, flags, &prelocking_strategy) || mysql_handle_derived(thd->lex, &mysql_derived_prepare)) - DBUG_RETURN(TRUE); /* purecov: inspected */ + goto end; + DBUG_RETURN(0); +end: + /* No need to rollback statement transaction, it's not started. */ + DBUG_ASSERT(thd->transaction.stmt.is_empty()); + close_thread_tables(thd); + /* Don't keep locks for a failed statement. */ + thd->mdl_context.rollback_to_savepoint(mdl_savepoint); + + DBUG_RETURN(TRUE); /* purecov: inspected */ } @@ -5607,6 +5601,14 @@ void close_tables_for_reopen(THD *thd, TABLE_LIST **tables, /* We have to cleanup translation tables of views. */ tmp->cleanup_items(); } + /* + No need to commit/rollback the statement transaction: it's + either not started or we're filling in an INFORMATION_SCHEMA + table on the fly, and thus mustn't manipulate with the + transaction of the enclosing statement. + */ + DBUG_ASSERT(thd->transaction.stmt.is_empty() || + (thd->state_flags & Open_tables_state::BACKUPS_AVAIL)); close_thread_tables(thd); thd->mdl_context.rollback_to_savepoint(start_of_statement_svp); } @@ -9034,7 +9036,8 @@ open_system_tables_for_read(THD *thd, TABLE_LIST *table_list, MYSQL_LOCK_IGNORE_TIMEOUT)) { lex->restore_backup_query_tables_list(&query_tables_list_backup); - goto error; + thd->restore_backup_open_tables_state(backup); + DBUG_RETURN(TRUE); } for (TABLE_LIST *tables= table_list; tables; tables= tables->next_global) @@ -9045,11 +9048,6 @@ open_system_tables_for_read(THD *thd, TABLE_LIST *table_list, lex->restore_backup_query_tables_list(&query_tables_list_backup); DBUG_RETURN(FALSE); - -error: - close_system_tables(thd, backup); - - DBUG_RETURN(TRUE); } @@ -9072,6 +9070,38 @@ close_system_tables(THD *thd, Open_tables_backup *backup) } +/** + A helper function to close a mysql.* table opened + in an auxiliary THD during bootstrap or in the main + connection, when we know that there are no locks + held by the connection due to a preceding implicit + commit. + + This function assumes that there is no + statement transaction started for the operation + itself, since mysql.* tables are not transactional + and when they are used the binlog is off (DDL + binlogging is always statement-based. + + We need this function since we'd like to not + just close the system table, but also release + the metadata lock on it. + + Note, that in LOCK TABLES mode this function + does not release the metadata lock. But in this + mode the table can be opened only if it is locked + explicitly with LOCK TABLES. +*/ + +void +close_mysql_tables(THD *thd) +{ + /* No need to commit/rollback statement transaction, it's not started. */ + DBUG_ASSERT(thd->transaction.stmt.is_empty()); + close_thread_tables(thd); + thd->mdl_context.release_transactional_locks(); +} + /* Open and lock one system table for update. @@ -9143,16 +9173,7 @@ open_log_table(THD *thd, TABLE_LIST *one_table, Open_tables_backup *backup) table->timestamp_field_type= TIMESTAMP_NO_AUTO_SET; } else - { - /* - If error in mysql_lock_tables(), open_ltable doesn't close the - table. Thread kill during mysql_lock_tables() is such error. But - open tables cannot be accepted when restoring the open tables - state. - */ - close_thread_tables(thd); thd->restore_backup_open_tables_state(backup); - } thd->utime_after_lock= save_utime_after_lock; DBUG_RETURN(table); diff --git a/sql/sql_base.h b/sql/sql_base.h index 24669bd2597..b912f80d44f 100644 --- a/sql/sql_base.h +++ b/sql/sql_base.h @@ -240,6 +240,7 @@ bool is_equal(const LEX_STRING *a, const LEX_STRING *b); bool open_system_tables_for_read(THD *thd, TABLE_LIST *table_list, Open_tables_backup *backup); void close_system_tables(THD *thd, Open_tables_backup *backup); +void close_mysql_tables(THD *thd); TABLE *open_system_table_for_update(THD *thd, TABLE_LIST *one_table); TABLE *open_log_table(THD *thd, TABLE_LIST *one_table, Open_tables_backup *backup); void close_log_table(THD *thd, Open_tables_backup *backup); diff --git a/sql/sql_class.cc b/sql/sql_class.cc index eb4d353db81..f3ef440c2f0 100644 --- a/sql/sql_class.cc +++ b/sql/sql_class.cc @@ -29,7 +29,6 @@ #include "sql_priv.h" #include "unireg.h" // REQUIRED: for other includes #include "sql_class.h" -#include "lock.h" // unlock_global_read_lock, mysql_unlock_tables #include "sql_cache.h" // query_cache_abort #include "sql_base.h" // close_thread_tables #include "sql_time.h" // date_time_format_copy @@ -1817,12 +1816,6 @@ bool select_send::send_eof() */ ha_release_temporary_latches(thd); - /* Unlock tables before sending packet to gain some speed */ - if (thd->lock && ! thd->locked_tables_mode) - { - mysql_unlock_tables(thd, thd->lock); - thd->lock=0; - } /* Don't send EOF if we're in error condition (which implies we've already sent or are sending an error) diff --git a/sql/sql_cursor.cc b/sql/sql_cursor.cc index ca724ec262f..28d2bd8b4de 100644 --- a/sql/sql_cursor.cc +++ b/sql/sql_cursor.cc @@ -22,6 +22,7 @@ #include "sql_select.h" #include "probes_mysql.h" #include "sql_parse.h" // mysql_execute_command +#include "sql_base.h" /**************************************************************************** Declarations. @@ -523,6 +524,7 @@ Sensitive_cursor::close() thd->derived_tables= derived_tables; thd->lock= lock; + close_thread_tables(thd); /* Is expected to at least close tables and empty thd->change_list */ stmt_arena->cleanup_stmt(); diff --git a/sql/sql_do.cc b/sql/sql_do.cc index 79e488ac2a5..085473c24b8 100644 --- a/sql/sql_do.cc +++ b/sql/sql_do.cc @@ -39,9 +39,10 @@ bool mysql_do(THD *thd, List &values) /* Rollback the effect of the statement, since next instruction will clear the error and the rollback in the end of - dispatch_command() won't work. + mysql_execute_command() won't work. */ - trans_rollback_stmt(thd); + if (! thd->in_sub_stmt) + trans_rollback_stmt(thd); thd->clear_error(); // DO always is OK } my_ok(thd); diff --git a/sql/sql_handler.cc b/sql/sql_handler.cc index 8e38cf5eed0..f1dddbb2eb5 100644 --- a/sql/sql_handler.cc +++ b/sql/sql_handler.cc @@ -59,7 +59,7 @@ #include "key.h" // key_copy #include "sql_base.h" // insert_fields #include "sql_select.h" -#include +#include "transaction.h" #define HANDLER_TABLES_HASH_SIZE 120 @@ -309,9 +309,15 @@ bool mysql_ha_open(THD *thd, TABLE_LIST *tables, bool reopen) } if (error) { + /* + No need to rollback statement transaction, it's not started. + If called with reopen flag, no need to rollback either, + it will be done at statement end. + */ + DBUG_ASSERT(thd->transaction.stmt.is_empty()); close_thread_tables(thd); - thd->set_open_tables(backup_open_tables); thd->mdl_context.rollback_to_savepoint(mdl_savepoint); + thd->set_open_tables(backup_open_tables); if (!reopen) my_hash_delete(&thd->handler_tables_hash, (uchar*) hash_tables); else @@ -578,6 +584,11 @@ retry: if (sql_handler_lock_error.need_reopen()) { DBUG_ASSERT(!lock && !thd->is_error()); + /* + Always close statement transaction explicitly, + so that the engine doesn't have to count locks. + */ + trans_rollback_stmt(thd); mysql_ha_close_table(thd, hash_tables); goto retry; } @@ -764,12 +775,18 @@ retry: num_rows++; } ok: + /* + Always close statement transaction explicitly, + so that the engine doesn't have to count locks. + */ + trans_commit_stmt(thd); mysql_unlock_tables(thd,lock); my_eof(thd); DBUG_PRINT("exit",("OK")); DBUG_RETURN(FALSE); err: + trans_rollback_stmt(thd); mysql_unlock_tables(thd,lock); err0: DBUG_PRINT("exit",("ERROR")); diff --git a/sql/sql_insert.cc b/sql/sql_insert.cc index c783d74b363..cc0b6ba3a2d 100644 --- a/sql/sql_insert.cc +++ b/sql/sql_insert.cc @@ -1862,7 +1862,10 @@ public: while ((row=rows.get())) delete row; if (table) + { close_thread_tables(&thd); + thd.mdl_context.release_transactional_locks(); + } mysql_mutex_lock(&LOCK_thread_count); mysql_mutex_destroy(&mutex); mysql_cond_destroy(&cond); @@ -2414,6 +2417,8 @@ bool Delayed_insert::open_and_lock_table() } if (!(table->file->ha_table_flags() & HA_CAN_INSERT_DELAYED)) { + /* To rollback InnoDB statement transaction. */ + trans_rollback_stmt(&thd); my_error(ER_DELAYED_NOT_SUPPORTED, MYF(ME_FATALERROR), table_list.table_name); return TRUE; @@ -2480,12 +2485,6 @@ pthread_handler_t handle_delayed_insert(void *arg) goto err; } - /* - Open table requires an initialized lex in case the table is - partitioned. The .frm file contains a partial SQL string which is - parsed using a lex, that depends on initialized thd->lex. - */ - lex_start(thd); thd->lex->sql_command= SQLCOM_INSERT; // For innodb::store_lock() /* Statement-based replication of INSERT DELAYED has problems with RAND() @@ -2619,28 +2618,11 @@ pthread_handler_t handle_delayed_insert(void *arg) } err: - /* - mysql_lock_tables() can potentially start a transaction and write - a table map. In the event of an error, that transaction has to be - rolled back. We only need to roll back a potential statement - transaction, since real transactions are rolled back in - close_thread_tables(). - - TODO: This is not true any more, table maps are generated on the - first call to ha_*_row() instead. Remove code that are used to - cover for the case outlined above. - */ - trans_rollback_stmt(thd); - DBUG_LEAVE; } - /* - di should be unlinked from the thread handler list and have no active - clients - */ - close_thread_tables(thd); // Free the table + thd->mdl_context.release_transactional_locks(); di->table=0; thd->killed= THD::KILL_CONNECTION; // If error mysql_cond_broadcast(&di->cond_client); // Safety @@ -2648,6 +2630,10 @@ pthread_handler_t handle_delayed_insert(void *arg) mysql_mutex_lock(&LOCK_delayed_create); // Because of delayed_get_table mysql_mutex_lock(&LOCK_delayed_insert); + /* + di should be unlinked from the thread handler list and have no active + clients + */ delete di; mysql_mutex_unlock(&LOCK_delayed_insert); mysql_mutex_unlock(&LOCK_delayed_create); diff --git a/sql/sql_lex.cc b/sql/sql_lex.cc index aefddc0b6a5..eef139d5698 100644 --- a/sql/sql_lex.cc +++ b/sql/sql_lex.cc @@ -450,6 +450,9 @@ void lex_end(LEX *lex) } reset_dynamic(&lex->plugins); + delete lex->sphead; + lex->sphead= NULL; + DBUG_VOID_RETURN; } diff --git a/sql/sql_parse.cc b/sql/sql_parse.cc index 8a94aea8aa7..53c2ca6fa39 100644 --- a/sql/sql_parse.cc +++ b/sql/sql_parse.cc @@ -115,6 +115,7 @@ "FUNCTION" : "PROCEDURE") static bool execute_sqlcom_select(THD *thd, TABLE_LIST *all_tables); +static void sql_kill(THD *thd, ulong id, bool only_kill_query); const char *any_db="*any*"; // Special symbol for check_access @@ -413,6 +414,9 @@ void init_update_queries(void) sql_command_flags[SQLCOM_FLUSH]= CF_AUTO_COMMIT_TRANS; sql_command_flags[SQLCOM_RESET]= CF_AUTO_COMMIT_TRANS; sql_command_flags[SQLCOM_CHECK]= CF_AUTO_COMMIT_TRANS; + sql_command_flags[SQLCOM_CREATE_SERVER]= CF_AUTO_COMMIT_TRANS; + sql_command_flags[SQLCOM_ALTER_SERVER]= CF_AUTO_COMMIT_TRANS; + sql_command_flags[SQLCOM_DROP_SERVER]= CF_AUTO_COMMIT_TRANS; } bool sqlcom_can_generate_row_events(const THD *thd) @@ -568,7 +572,6 @@ static void handle_bootstrap_impl(THD *thd) } mysql_parse(thd, thd->query(), length, &parser_state); - close_thread_tables(thd); // Free tables bootstrap_error= thd->is_error(); thd->protocol->end_statement(); @@ -1139,13 +1142,11 @@ bool dispatch_command(enum enum_server_command command, THD *thd, { char *beginning_of_next_stmt= (char*) parser_state.m_lip.found_semicolon; - - thd->protocol->end_statement(); - query_cache_end_of_result(thd); /* Multiple queries exits, execute them individually */ - close_thread_tables(thd); + thd->protocol->end_statement(); + query_cache_end_of_result(thd); ulong length= (ulong)(packet_end - beginning_of_next_stmt); log_slow_statement(thd); @@ -1197,38 +1198,54 @@ bool dispatch_command(enum enum_server_command command, THD *thd, char *fields, *packet_end= packet + packet_length, *arg_end; /* Locked closure of all tables */ TABLE_LIST table_list; - LEX_STRING conv_name; - - /* used as fields initializator */ - lex_start(thd); + LEX_STRING table_name; + LEX_STRING db; + /* + SHOW statements should not add the used tables to the list of tables + used in a transaction. + */ + MDL_ticket *mdl_savepoint= thd->mdl_context.mdl_savepoint(); status_var_increment(thd->status_var.com_stat[SQLCOM_SHOW_FIELDS]); - bzero((char*) &table_list,sizeof(table_list)); - if (thd->copy_db_to(&table_list.db, &table_list.db_length)) + if (thd->copy_db_to(&db.str, &db.length)) break; /* We have name + wildcard in packet, separated by endzero */ arg_end= strend(packet); uint arg_length= arg_end - packet; - + /* Check given table name length. */ if (arg_length >= packet_length || arg_length > NAME_LEN) { my_message(ER_UNKNOWN_COM_ERROR, ER(ER_UNKNOWN_COM_ERROR), MYF(0)); break; } - thd->convert_string(&conv_name, system_charset_info, + thd->convert_string(&table_name, system_charset_info, packet, arg_length, thd->charset()); - if (check_table_name(conv_name.str, conv_name.length, FALSE)) + if (check_table_name(table_name.str, table_name.length, FALSE)) { /* this is OK due to convert_string() null-terminating the string */ - my_error(ER_WRONG_TABLE_NAME, MYF(0), conv_name.str); + my_error(ER_WRONG_TABLE_NAME, MYF(0), table_name.str); break; } - - table_list.alias= table_list.table_name= conv_name.str; packet= arg_end + 1; + mysql_reset_thd_for_next_command(thd); + lex_start(thd); + /* Must be before we init the table list. */ + if (lower_case_table_names) + table_name.length= my_casedn_str(files_charset_info, table_name.str); + table_list.init_one_table(db.str, db.length, table_name.str, + table_name.length, table_name.str, TL_READ); + /* + Init TABLE_LIST members necessary when the undelrying + table is view. + */ + table_list.select_lex= &(thd->lex->select_lex); + thd->lex-> + select_lex.table_list.link_in_list(&table_list, + &table_list.next_local); + thd->lex->add_to_query_tables(&table_list); if (is_infoschema_db(table_list.db, table_list.db_length)) { @@ -1242,32 +1259,23 @@ bool dispatch_command(enum enum_server_command command, THD *thd, break; thd->set_query(fields, query_length); general_log_print(thd, command, "%s %s", table_list.table_name, fields); - if (lower_case_table_names) - my_casedn_str(files_charset_info, table_list.table_name); - if (check_access(thd, SELECT_ACL, table_list.db, - &table_list.grant.privilege, - &table_list.grant.m_internal, - 0, 0)) + if (check_table_access(thd, SELECT_ACL, &table_list, + TRUE, UINT_MAX, FALSE)) break; - if (check_grant(thd, SELECT_ACL, &table_list, TRUE, UINT_MAX, FALSE)) - break; - /* init structures for VIEW processing */ - table_list.select_lex= &(thd->lex->select_lex); - - lex_start(thd); - mysql_reset_thd_for_next_command(thd); - - thd->lex-> - select_lex.table_list.link_in_list(&table_list, - &table_list.next_local); - thd->lex->add_to_query_tables(&table_list); - init_mdl_requests(&table_list); - - /* switch on VIEW optimisation: do not fill temporary tables */ + /* + Turn on an optimization relevant if the underlying table + is a view: do not fill derived tables. + */ thd->lex->sql_command= SQLCOM_SHOW_FIELDS; + mysqld_list_fields(thd,&table_list,fields); thd->lex->unit.cleanup(); + /* No need to rollback statement transaction, it's not started. */ + DBUG_ASSERT(thd->transaction.stmt.is_empty()); + close_thread_tables(thd); + thd->mdl_context.rollback_to_savepoint(mdl_savepoint); + thd->cleanup_after_query(); break; } @@ -1315,7 +1323,6 @@ bool dispatch_command(enum enum_server_command command, THD *thd, ulong options= (ulong) (uchar) packet[0]; if (trans_commit_implicit(thd)) break; - close_thread_tables(thd); thd->mdl_context.release_transactional_locks(); if (check_global_access(thd,RELOAD_ACL)) break; @@ -1377,7 +1384,6 @@ bool dispatch_command(enum enum_server_command command, THD *thd, DBUG_PRINT("quit",("Got shutdown command for level %u", level)); general_log_print(thd, command, NullS); my_eof(thd); - close_thread_tables(thd); // Free before kill kill_mysql(); error=TRUE; break; @@ -1480,29 +1486,9 @@ bool dispatch_command(enum enum_server_command command, THD *thd, my_message(ER_UNKNOWN_COM_ERROR, ER(ER_UNKNOWN_COM_ERROR), MYF(0)); break; } - - /* report error issued during command execution */ - if (thd->killed_errno()) - { - if (! thd->stmt_da->is_set()) - thd->send_kill_message(); - } - if (thd->killed == THD::KILL_QUERY || thd->killed == THD::KILL_BAD_DATA) - { - thd->killed= THD::NOT_KILLED; - thd->mysys_var->abort= 0; - } - - /* If commit fails, we should be able to reset the OK status. */ - thd->stmt_da->can_overwrite_status= TRUE; - thd->is_error() ? trans_rollback_stmt(thd) : trans_commit_stmt(thd); - thd->stmt_da->can_overwrite_status= FALSE; - - thd->transaction.stmt.reset(); - - thd->proc_info= "closing tables"; - /* Free tables */ - close_thread_tables(thd); + DBUG_ASSERT(thd->derived_tables == NULL && + (thd->open_tables == NULL || + (thd->locked_tables_mode == LTM_LOCK_TABLES))); thd->protocol->end_statement(); query_cache_end_of_result(thd); @@ -1715,6 +1701,9 @@ int prepare_schema_table(THD *thd, LEX *lex, Table_ident *table_ident, In brief: take exclusive locks, expel tables from the table cache, reopen the tables, enter the 'LOCKED TABLES' mode, downgrade the locks. + Note: the function is written to be called from + mysql_execute_command(), it is not reusable in arbitrary + execution context. Required privileges ------------------- @@ -1816,9 +1805,9 @@ static bool flush_tables_with_read_lock(THD *thd, TABLE_LIST *all_tables) &lock_tables_prelocking_strategy) || thd->locked_tables_list.init_locked_tables(thd)) { - close_thread_tables(thd); goto error; } + thd->variables.option_bits|= OPTION_TABLE_LOCK; /* Downgrade the exclusive locks. @@ -2041,6 +2030,7 @@ mysql_execute_command(THD *thd) thd->work_part_info= 0; #endif + DBUG_ASSERT(thd->transaction.stmt.is_empty() || thd->in_sub_stmt); /* In many cases first table of main SELECT_LEX have special meaning => check that it is first table in global list and relink it first in @@ -2222,8 +2212,7 @@ mysql_execute_command(THD *thd) /* Commit the normal transaction if one is active. */ if (trans_commit_implicit(thd)) goto error; - /* Close tables and release metadata locks. */ - close_thread_tables(thd); + /* Release metadata locks acquired in this transaction. */ thd->mdl_context.release_transactional_locks(); } @@ -3536,24 +3525,27 @@ end_with_restore_list: done FLUSH TABLES WITH READ LOCK + BEGIN. If this assumption becomes false, mysqldump will not work. */ - thd->locked_tables_list.unlock_locked_tables(thd); if (thd->variables.option_bits & OPTION_TABLE_LOCK) { - trans_commit_implicit(thd); + res= trans_commit_implicit(thd); + thd->locked_tables_list.unlock_locked_tables(thd); thd->mdl_context.release_transactional_locks(); thd->variables.option_bits&= ~(OPTION_TABLE_LOCK); } if (thd->global_read_lock.is_acquired()) thd->global_read_lock.unlock_global_read_lock(thd); + if (res) + goto error; my_ok(thd); break; case SQLCOM_LOCK_TABLES: + /* We must end the transaction first, regardless of anything */ + res= trans_commit_implicit(thd); thd->locked_tables_list.unlock_locked_tables(thd); - /* we must end the trasaction first, regardless of anything */ - if (trans_commit_implicit(thd)) - goto error; - /* release transactional metadata locks. */ + /* Release transactional metadata locks. */ thd->mdl_context.release_transactional_locks(); + if (res) + goto error; if (check_table_access(thd, LOCK_TABLES_ACL | SELECT_ACL, all_tables, FALSE, UINT_MAX, FALSE)) goto error; @@ -3576,17 +3568,14 @@ end_with_restore_list: if (res) { + trans_rollback_stmt(thd); /* Need to end the current transaction, so the storage engine (InnoDB) can free its locks if LOCK TABLES locked some tables before finding that it can't lock a table in its list */ - trans_rollback_stmt(thd); trans_commit_implicit(thd); - /* - Close tables and release metadata locks otherwise a later call to - close_thread_tables might not release the locks if autocommit is off. - */ + /* Close tables and release metadata locks. */ close_thread_tables(thd); DBUG_ASSERT(!thd->locked_tables_mode); thd->mdl_context.release_transactional_locks(); @@ -4205,9 +4194,7 @@ end_with_restore_list: locks in the MDL context, so there is no risk to deadlock. */ - trans_commit_implicit(thd); - close_thread_tables(thd); - thd->mdl_context.release_transactional_locks(); + close_mysql_tables(thd); /* Check if the definer exists on slave, then use definer privilege to insert routine privileges to mysql.procs_priv. @@ -4484,9 +4471,7 @@ create_sp_error: locks in the MDL context, so there is no risk to deadlock. */ - trans_commit_implicit(thd); - close_thread_tables(thd); - thd->mdl_context.release_transactional_locks(); + close_mysql_tables(thd); if (sp_automatic_privileges && !opt_noacl && sp_revoke_privileges(thd, db, name, @@ -4778,17 +4763,60 @@ finish: DBUG_ASSERT(!thd->in_active_multi_stmt_transaction() || thd->in_multi_stmt_transaction_mode()); + + if (! thd->in_sub_stmt) + { + /* report error issued during command execution */ + if (thd->killed_errno()) + { + if (! thd->stmt_da->is_set()) + thd->send_kill_message(); + } + if (thd->killed == THD::KILL_QUERY || thd->killed == THD::KILL_BAD_DATA) + { + thd->killed= THD::NOT_KILLED; + thd->mysys_var->abort= 0; + } + if (thd->is_error() || (thd->variables.option_bits & OPTION_MASTER_SQL_ERROR)) + trans_rollback_stmt(thd); + else + { + /* If commit fails, we should be able to reset the OK status. */ + thd->stmt_da->can_overwrite_status= TRUE; + trans_commit_stmt(thd); + thd->stmt_da->can_overwrite_status= FALSE; + } + } + + lex->unit.cleanup(); + /* Free tables */ + thd_proc_info(thd, "closing tables"); + close_thread_tables(thd); + thd_proc_info(thd, 0); + if (stmt_causes_implicit_commit(thd, CF_IMPLICIT_COMMIT_END)) { + /* No transaction control allowed in sub-statements. */ + DBUG_ASSERT(! thd->in_sub_stmt); /* If commit fails, we should be able to reset the OK status. */ thd->stmt_da->can_overwrite_status= TRUE; - /* Commit or rollback the statement transaction. */ - thd->is_error() ? trans_rollback_stmt(thd) : trans_commit_stmt(thd); /* Commit the normal transaction if one is active. */ trans_commit_implicit(thd); thd->stmt_da->can_overwrite_status= FALSE; - /* Close tables and release metadata locks. */ - close_thread_tables(thd); + thd->mdl_context.release_transactional_locks(); + } + else if (! thd->in_sub_stmt && ! thd->in_multi_stmt_transaction_mode()) + { + /* + - If inside a multi-statement transaction, + defer the release of metadata locks until the current + transaction is either committed or rolled back. This prevents + other statements from modifying the table for the entire + duration of this transaction. This provides commit ordering + and guarantees serializability across multiple transactions. + - If in autocommit mode, or outside a transactional context, + automatically release metadata locks of the current statement. + */ thd->mdl_context.release_transactional_locks(); } @@ -5886,12 +5914,6 @@ void mysql_parse(THD *thd, const char *inBuf, uint length, query_cache_abort(&thd->query_cache_tls); } - if (thd->lex->sphead) - { - delete thd->lex->sphead; - thd->lex->sphead= 0; - } - lex->unit.cleanup(); thd_proc_info(thd, "freeing items"); thd->end_statement(); thd->cleanup_after_query(); @@ -6997,11 +7019,15 @@ uint kill_one_thread(THD *thd, ulong id, bool only_kill_query) only_kill_query Should it kill the query or the connection */ +static void sql_kill(THD *thd, ulong id, bool only_kill_query) { uint error; if (!(error= kill_one_thread(thd, id, only_kill_query))) - my_ok(thd); + { + if (! thd->killed) + my_ok(thd); + } else my_error(error, MYF(0), id); } diff --git a/sql/sql_parse.h b/sql/sql_parse.h index 475811d45b7..7304836ed0f 100644 --- a/sql/sql_parse.h +++ b/sql/sql_parse.h @@ -51,7 +51,6 @@ bool parse_sql(THD *thd, Object_creation_ctx *creation_ctx); uint kill_one_thread(THD *thd, ulong id, bool only_kill_query); -void sql_kill(THD *thd, ulong id, bool only_kill_query); void free_items(Item *item); void cleanup_items(Item *item); diff --git a/sql/sql_partition.cc b/sql/sql_partition.cc index d7ff753dfd0..2c8b5d67d04 100644 --- a/sql/sql_partition.cc +++ b/sql/sql_partition.cc @@ -59,7 +59,7 @@ #include "my_md5.h" #include "transaction.h" -#include "sql_base.h" // close_thread_tables +#include "sql_base.h" // close_all_tables_for_name #include "sql_table.h" // build_table_filename, // build_table_shadow_filename, // table_to_filename @@ -6758,7 +6758,6 @@ uint fast_alter_partition_table(THD *thd, TABLE *table, table_list, FALSE, NULL, written_bin_log)); err: - close_thread_tables(thd); DBUG_RETURN(TRUE); } #endif diff --git a/sql/sql_plugin.cc b/sql/sql_plugin.cc index 2b6be403fc6..27cd03d8edd 100644 --- a/sql/sql_plugin.cc +++ b/sql/sql_plugin.cc @@ -21,7 +21,7 @@ #include "sql_locale.h" #include "sql_plugin.h" #include "sql_parse.h" // check_table_access -#include "sql_base.h" // close_thread_tables +#include "sql_base.h" // close_mysql_tables #include "key.h" // key_copy #include "sql_show.h" // remove_status_vars, add_status_vars #include "strfunc.h" // find_set @@ -1511,8 +1511,8 @@ static void plugin_load(MEM_ROOT *tmp_root, int *argc, char **argv) sql_print_error(ER(ER_GET_ERRNO), my_errno); end_read_record(&read_record_info); table->m_needs_reopen= TRUE; // Force close to free memory + close_mysql_tables(new_thd); end: - close_thread_tables(new_thd); /* Remember that we don't have a THD */ my_pthread_setspecific_ptr(THR_THD, 0); DBUG_VOID_RETURN; diff --git a/sql/sql_prepare.cc b/sql/sql_prepare.cc index 089e751900e..151a135125e 100644 --- a/sql/sql_prepare.cc +++ b/sql/sql_prepare.cc @@ -90,7 +90,7 @@ When one supplies long data for a placeholder: #include "set_var.h" #include "sql_prepare.h" #include "sql_parse.h" // insert_precheck, update_precheck, delete_precheck -#include "sql_base.h" // close_thread_tables +#include "sql_base.h" // open_normal_and_derived_tables #include "sql_cache.h" // query_cache_* #include "sql_view.h" // create_view_precheck #include "sql_delete.h" // mysql_prepare_delete @@ -2989,12 +2989,6 @@ Execute_sql_statement::execute_server_code(THD *thd) error= mysql_execute_command(thd); - if (thd->killed_errno()) - { - if (! thd->stmt_da->is_set()) - thd->send_kill_message(); - } - /* report error issued during command execution */ if (error == 0 && thd->spcont == NULL) general_log_write(thd, COM_STMT_EXECUTE, @@ -3102,13 +3096,8 @@ void Prepared_statement::cleanup_stmt() DBUG_ENTER("Prepared_statement::cleanup_stmt"); DBUG_PRINT("enter",("stmt: 0x%lx", (long) this)); - delete lex->sphead; - lex->sphead= 0; - /* The order is important */ - lex->unit.cleanup(); cleanup_items(free_list); thd->cleanup_after_query(); - close_thread_tables(thd); thd->rollback_item_tree_changes(); DBUG_VOID_RETURN; @@ -3272,21 +3261,16 @@ bool Prepared_statement::prepare(const char *packet, uint packet_len) to PREPARE stmt FROM "CREATE PROCEDURE ..." */ DBUG_ASSERT(lex->sphead == NULL || error != 0); - if (lex->sphead) - { - delete lex->sphead; - lex->sphead= NULL; - } + /* The order is important */ + lex->unit.cleanup(); + /* No need to commit statement transaction, it's not started. */ + DBUG_ASSERT(thd->transaction.stmt.is_empty()); + + close_thread_tables(thd); + thd->mdl_context.rollback_to_savepoint(mdl_savepoint); lex_end(lex); cleanup_stmt(); - /* - If not inside a multi-statement transaction, the metadata - locks have already been released and our savepoint points - to ticket which has been released as well. - */ - if (thd->in_multi_stmt_transaction_mode()) - thd->mdl_context.rollback_to_savepoint(mdl_savepoint); thd->restore_backup_statement(this, &stmt_backup); thd->stmt_arena= old_stmt_arena; @@ -3393,11 +3377,6 @@ Prepared_statement::set_parameters(String *expanded_query, and execute of a new statement. If this happens repeatedly more than MAX_REPREPARE_ATTEMPTS times, we give up. - In future we need to be able to keep the metadata locks between - prepare and execute, but right now open_and_lock_tables(), as - well as close_thread_tables() are buried deep inside - execution code (mysql_execute_command()). - @return TRUE if an error, FALSE if success @retval TRUE either MAX_REPREPARE_ATTEMPTS has been reached, or some general error @@ -3484,11 +3463,6 @@ Prepared_statement::execute_server_runnable(Server_runnable *server_runnable) error= server_runnable->execute_server_code(thd); - delete lex->sphead; - lex->sphead= 0; - /* The order is important */ - lex->unit.cleanup(); - close_thread_tables(thd); thd->cleanup_after_query(); thd->restore_active_arena(this, &stmt_backup); diff --git a/sql/sql_priv.h b/sql/sql_priv.h index 604890ffbe5..708608fc2f1 100644 --- a/sql/sql_priv.h +++ b/sql/sql_priv.h @@ -135,6 +135,16 @@ extern char err_shared_dir[]; Type of locks to be acquired is specified directly. */ #define SELECT_HIGH_PRIORITY (1ULL << 34) // SELECT, user +/** + Is set in slave SQL thread when there was an + error on master, which, when is not reproducible + on slave (i.e. the query succeeds on slave), + is not terminal to the state of repliation, + and should be ignored. The slave SQL thread, + however, needs to rollback the effects of the + succeeded statement to keep replication consistent. +*/ +#define OPTION_MASTER_SQL_ERROR (1ULL << 35) /* The rest of the file is included in the server only */ diff --git a/sql/sql_servers.cc b/sql/sql_servers.cc index c7f9cf0b132..cfbf8e96719 100644 --- a/sql/sql_servers.cc +++ b/sql/sql_servers.cc @@ -36,7 +36,7 @@ #include "sql_priv.h" #include "sql_servers.h" #include "unireg.h" -#include "sql_base.h" // close_thread_tables +#include "sql_base.h" // close_mysql_tables #include "records.h" // init_read_record, end_read_record #include "hash_filo.h" #include @@ -280,9 +280,7 @@ bool servers_reload(THD *thd) } end: - trans_commit_implicit(thd); - close_thread_tables(thd); - thd->mdl_context.release_transactional_locks(); + close_mysql_tables(thd); DBUG_PRINT("info", ("unlocking servers_cache")); mysql_rwlock_unlock(&THR_LOCK_servers); DBUG_RETURN(return_val); @@ -535,6 +533,7 @@ int insert_server_record(TABLE *table, FOREIGN_SERVER *server) { int error; DBUG_ENTER("insert_server_record"); + tmp_disable_binlog(table->in_use); table->use_all_columns(); empty_record(table); @@ -571,6 +570,8 @@ int insert_server_record(TABLE *table, FOREIGN_SERVER *server) } else error= ER_FOREIGN_SERVER_EXISTS; + + reenable_binlog(table->in_use); DBUG_RETURN(error); } @@ -625,7 +626,7 @@ int drop_server(THD *thd, LEX_SERVER_OPTIONS *server_options) error= delete_server_record(table, name.str, name.length); /* close the servers table before we call closed_cached_connection_tables */ - close_thread_tables(thd); + close_mysql_tables(thd); if (close_cached_connection_tables(thd, TRUE, &name)) { @@ -880,6 +881,7 @@ update_server_record(TABLE *table, FOREIGN_SERVER *server) { int error=0; DBUG_ENTER("update_server_record"); + tmp_disable_binlog(table->in_use); table->use_all_columns(); /* set the field that's the PK to the value we're looking for */ table->field[0]->store(server->server_name, @@ -913,6 +915,7 @@ update_server_record(TABLE *table, FOREIGN_SERVER *server) } end: + reenable_binlog(table->in_use); DBUG_RETURN(error); } @@ -938,6 +941,7 @@ delete_server_record(TABLE *table, { int error; DBUG_ENTER("delete_server_record"); + tmp_disable_binlog(table->in_use); table->use_all_columns(); /* set the field that's the PK to the value we're looking for */ @@ -959,6 +963,7 @@ delete_server_record(TABLE *table, table->file->print_error(error, MYF(0)); } + reenable_binlog(table->in_use); DBUG_RETURN(error); } @@ -1050,7 +1055,7 @@ int alter_server(THD *thd, LEX_SERVER_OPTIONS *server_options) error= update_server(thd, existing, altered); /* close the servers table before we call closed_cached_connection_tables */ - close_thread_tables(thd); + close_mysql_tables(thd); if (close_cached_connection_tables(thd, FALSE, &name)) { diff --git a/sql/sql_table.cc b/sql/sql_table.cc index cacfcedff23..42b3dfaad83 100644 --- a/sql/sql_table.cc +++ b/sql/sql_table.cc @@ -2285,18 +2285,13 @@ err: { /* Under LOCK TABLES we should release meta-data locks on the tables - which were dropped. Otherwise we can rely on close_thread_tables() - doing this. Unfortunately in this case we are likely to get more - false positives in try_acquire_lock() function. So - it makes sense to remove exclusive meta-data locks in all cases. + which were dropped. Leave LOCK TABLES mode if we managed to drop all tables which were locked. Additional check for 'non_temp_tables_count' is to avoid leaving LOCK TABLES mode if we have dropped only temporary tables. */ - if (! thd->locked_tables_mode) - thd->mdl_context.release_transactional_locks(); - else + if (thd->locked_tables_mode) { if (thd->lock && thd->lock->table_count == 0 && non_temp_tables_count > 0) { @@ -2305,7 +2300,8 @@ err: } for (table= tables; table; table= table->next_local) { - if (table->mdl_request.ticket) + /* Drop locks for all successfully dropped tables. */ + if (table->table == NULL && table->mdl_request.ticket) { /* Under LOCK TABLES we may have several instances of table open @@ -2316,6 +2312,10 @@ err: } } } + /* + Rely on the caller to implicitly commit the transaction + and release metadata locks. + */ } end: @@ -4214,8 +4214,14 @@ warn: } -/* - Database and name-locking aware wrapper for mysql_create_table_no_lock(), +/** + Implementation of SQLCOM_CREATE_TABLE. + + Take the metadata locks (including a shared lock on the affected + schema) and create the table. Is written to be called from + mysql_execute_command(), to which it delegates the common parts + with other commands (i.e. implicit commit before and after, + close of thread tables. */ bool mysql_create_table(THD *thd, TABLE_LIST *create_table, @@ -4231,7 +4237,7 @@ bool mysql_create_table(THD *thd, TABLE_LIST *create_table, if (open_and_lock_tables(thd, thd->lex->query_tables, FALSE, 0)) { result= TRUE; - goto unlock; + goto end; } /* Got lock. */ @@ -4253,16 +4259,7 @@ bool mysql_create_table(THD *thd, TABLE_LIST *create_table, !(create_info->options & HA_LEX_CREATE_TMP_TABLE)))) result= write_bin_log(thd, TRUE, thd->query(), thd->query_length()); - if (!(create_info->options & HA_LEX_CREATE_TMP_TABLE)) - { - /* - close_thread_tables() takes care about both closing open tables (which - might be still around in case of error) and releasing metadata locks. - */ - close_thread_tables(thd); - } - -unlock: +end: DBUG_RETURN(result); } @@ -4752,6 +4749,7 @@ static bool mysql_admin_table(THD* thd, TABLE_LIST* tables, trans_rollback_stmt(thd); trans_rollback(thd); close_thread_tables(thd); + thd->mdl_context.release_transactional_locks(); DBUG_PRINT("admin", ("simple error, admin next table")); continue; case -1: // error, message could be written to net @@ -5038,11 +5036,11 @@ send_result_message: trans_commit_stmt(thd); trans_commit(thd); close_thread_tables(thd); - table->table= NULL; thd->mdl_context.release_transactional_locks(); + table->table= NULL; if (!result_code) // recreation went ok { - /* Clear the ticket released in close_thread_tables(). */ + /* Clear the ticket released above. */ table->mdl_request.ticket= NULL; DEBUG_SYNC(thd, "ha_admin_open_ltable"); table->mdl_request.set_type(MDL_SHARED_WRITE); @@ -6729,13 +6727,11 @@ bool mysql_alter_table(THD *thd,char *new_db, char *new_name, goto err; DBUG_EXECUTE_IF("sleep_alter_enable_indexes", my_sleep(6000000);); error= table->file->ha_enable_indexes(HA_KEY_SWITCH_NONUNIQ_SAVE); - /* COND_refresh will be signaled in close_thread_tables() */ break; case DISABLE: if (wait_while_table_is_used(thd, table, HA_EXTRA_FORCE_REOPEN)) goto err; error=table->file->ha_disable_indexes(HA_KEY_SWITCH_NONUNIQ_SAVE); - /* COND_refresh will be signaled in close_thread_tables() */ break; default: DBUG_ASSERT(FALSE); @@ -6821,8 +6817,8 @@ bool mysql_alter_table(THD *thd,char *new_db, char *new_name, { /* Under LOCK TABLES we should adjust meta-data locks before finishing - statement. Otherwise we can rely on close_thread_tables() releasing - them. + statement. Otherwise we can rely on them being released + along with the implicit commit. */ if (new_name != table_name || new_db != db) { @@ -7360,8 +7356,8 @@ bool mysql_alter_table(THD *thd,char *new_db, char *new_name, 5) Write statement to the binary log. 6) If we are under LOCK TABLES and do ALTER TABLE ... RENAME we remove placeholders and release metadata locks. - 7) If we are not not under LOCK TABLES we rely on close_thread_tables() - call to remove placeholders and releasing metadata locks. + 7) If we are not not under LOCK TABLES we rely on the caller + (mysql_execute_command()) to release metadata locks. */ thd_proc_info(thd, "rename result table"); @@ -7990,7 +7986,13 @@ bool mysql_checksum_table(THD *thd, TABLE_LIST *tables, } } thd->clear_error(); + if (! thd->in_sub_stmt) + trans_rollback_stmt(thd); close_thread_tables(thd); + /* + Don't release metadata locks, this will be done at + statement end. + */ table->table=0; // For query cache } if (protocol->write()) @@ -8000,10 +8002,7 @@ bool mysql_checksum_table(THD *thd, TABLE_LIST *tables, my_eof(thd); DBUG_RETURN(FALSE); - err: - close_thread_tables(thd); // Shouldn't be needed - if (table) - table->table=0; +err: DBUG_RETURN(TRUE); } diff --git a/sql/sql_trigger.cc b/sql/sql_trigger.cc index 2f084c369b6..a5664b00287 100644 --- a/sql/sql_trigger.cc +++ b/sql/sql_trigger.cc @@ -540,9 +540,9 @@ end: } /* - If we are under LOCK TABLES we should restore original state of meta-data - locks. Otherwise call to close_thread_tables() will take care about both - TABLE instance created by open_n_lock_single_table() and metadata lock. + If we are under LOCK TABLES we should restore original state of + meta-data locks. Otherwise all locks will be released along + with the implicit commit. */ if (thd->locked_tables_mode && tables && lock_upgrade_done) mdl_ticket->downgrade_exclusive_lock(MDL_SHARED_NO_READ_WRITE); @@ -1321,6 +1321,7 @@ bool Table_triggers_list::check_n_load(THD *thd, const char *db, thd->reset_db((char*) db, strlen(db)); while ((trg_create_str= it++)) { + sp_head *sp; trg_sql_mode= itm++; LEX_STRING *trg_definer= it_definer++; @@ -1357,13 +1358,14 @@ bool Table_triggers_list::check_n_load(THD *thd, const char *db, */ lex.set_trg_event_type_for_tables(); - lex.sphead->set_info(0, 0, &lex.sp_chistics, (ulong) *trg_sql_mode); - int event= lex.trg_chistics.event; int action_time= lex.trg_chistics.action_time; - lex.sphead->set_creation_ctx(creation_ctx); - triggers->bodies[event][action_time]= lex.sphead; + sp= triggers->bodies[event][action_time]= lex.sphead; + lex.sphead= NULL; /* Prevent double cleanup. */ + + sp->set_info(0, 0, &lex.sp_chistics, (ulong) *trg_sql_mode); + sp->set_creation_ctx(creation_ctx); if (!trg_definer->length) { @@ -1376,27 +1378,26 @@ bool Table_triggers_list::check_n_load(THD *thd, const char *db, push_warning_printf(thd, MYSQL_ERROR::WARN_LEVEL_WARN, ER_TRG_NO_DEFINER, ER(ER_TRG_NO_DEFINER), (const char*) db, - (const char*) lex.sphead->m_name.str); + (const char*) sp->m_name.str); /* Set definer to the '' to correct displaying in the information schema. */ - lex.sphead->set_definer((char*) "", 0); + sp->set_definer((char*) "", 0); /* Triggers without definer information are executed under the authorization of the invoker. */ - lex.sphead->m_chistics->suid= SP_IS_NOT_SUID; + sp->m_chistics->suid= SP_IS_NOT_SUID; } else - lex.sphead->set_definer(trg_definer->str, trg_definer->length); + sp->set_definer(trg_definer->str, trg_definer->length); - if (triggers->names_list.push_back(&lex.sphead->m_name, - &table->mem_root)) + if (triggers->names_list.push_back(&sp->m_name, &table->mem_root)) goto err_with_lex_cleanup; if (!(on_table_name= alloc_lex_string(&table->mem_root))) diff --git a/sql/sql_udf.cc b/sql/sql_udf.cc index 3d197303fb1..ba1d0ceadeb 100644 --- a/sql/sql_udf.cc +++ b/sql/sql_udf.cc @@ -33,7 +33,7 @@ #include "sql_priv.h" #include "unireg.h" -#include "sql_base.h" // close_thread_tables +#include "sql_base.h" // close_mysql_tables #include "sql_parse.h" // check_identifier_name #include "sql_table.h" // write_bin_log #include "records.h" // init_read_record, end_read_record @@ -251,7 +251,7 @@ void udf_init() table->m_needs_reopen= TRUE; // Force close to free memory end: - close_thread_tables(new_thd); + close_mysql_tables(new_thd); delete new_thd; /* Remember that we don't have a THD */ my_pthread_setspecific_ptr(THR_THD, 0); diff --git a/sql/sys_vars.cc b/sql/sys_vars.cc index 6e95961ebb0..9e212fb95e9 100644 --- a/sql/sys_vars.cc +++ b/sql/sys_vars.cc @@ -2203,14 +2203,21 @@ static bool fix_autocommit(sys_var *self, THD *thd, enum_var_type type) thd->variables.option_bits & OPTION_NOT_AUTOCOMMIT) { // activating autocommit - if (trans_commit(thd)) + if (trans_commit_stmt(thd) || trans_commit(thd)) { thd->variables.option_bits&= ~OPTION_AUTOCOMMIT; return true; } - close_thread_tables(thd); - thd->mdl_context.release_transactional_locks(); - + /* + Don't close thread tables or release metadata locks: if we do so, we + risk releasing locks/closing tables of expressions used to assign + other variables, as in: + set @var=my_stored_function1(), @@autocommit=1, @var2=(select max(a) + from my_table), ... + The locks will be released at statement end anyway, as SET + statement that assigns autocommit is marked to commit + transaction implicitly at the end (@sa stmt_causes_implicitcommit()). + */ thd->variables.option_bits&= ~(OPTION_BEGIN | OPTION_KEEP_LOG | OPTION_NOT_AUTOCOMMIT); thd->transaction.all.modified_non_trans_table= false; diff --git a/sql/transaction.cc b/sql/transaction.cc index f6786f20dcf..a28fba8805d 100644 --- a/sql/transaction.cc +++ b/sql/transaction.cc @@ -28,6 +28,12 @@ static bool trans_check(THD *thd) enum xa_states xa_state= thd->transaction.xid_state.xa_state; DBUG_ENTER("trans_check"); + /* + Always commit statement transaction before manipulating with + the normal one. + */ + DBUG_ASSERT(thd->transaction.stmt.is_empty()); + if (unlikely(thd->in_sub_stmt)) my_error(ER_COMMIT_NOT_ALLOWED_IN_SF_OR_TRG, MYF(0)); if (xa_state != XA_NOTR) @@ -252,6 +258,14 @@ bool trans_commit_stmt(THD *thd) { DBUG_ENTER("trans_commit_stmt"); int res= FALSE; + /* + We currently don't invoke commit/rollback at end of + a sub-statement. In future, we perhaps should take + a savepoint for each nested statement, and release the + savepoint when statement has succeeded. + */ + DBUG_ASSERT(! thd->in_sub_stmt); + if (thd->transaction.stmt.ha_list) { res= ha_commit_trans(thd, FALSE); @@ -267,6 +281,9 @@ bool trans_commit_stmt(THD *thd) RUN_HOOK(transaction, after_rollback, (thd, FALSE)); else RUN_HOOK(transaction, after_commit, (thd, FALSE)); + + thd->transaction.stmt.reset(); + DBUG_RETURN(test(res)); } @@ -283,6 +300,14 @@ bool trans_rollback_stmt(THD *thd) { DBUG_ENTER("trans_rollback_stmt"); + /* + We currently don't invoke commit/rollback at end of + a sub-statement. In future, we perhaps should take + a savepoint for each nested statement, and release the + savepoint when statement has succeeded. + */ + DBUG_ASSERT(! thd->in_sub_stmt); + if (thd->transaction.stmt.ha_list) { ha_rollback_trans(thd, FALSE); @@ -294,6 +319,8 @@ bool trans_rollback_stmt(THD *thd) RUN_HOOK(transaction, after_rollback, (thd, FALSE)); + thd->transaction.stmt.reset(); + DBUG_RETURN(FALSE); } diff --git a/sql/tztime.cc b/sql/tztime.cc index af8574c38f1..43d43123158 100644 --- a/sql/tztime.cc +++ b/sql/tztime.cc @@ -49,13 +49,6 @@ #include "lock.h" // MYSQL_LOCK_IGNORE_FLUSH, // MYSQL_LOCK_IGNORE_TIMEOUT -/* - This forward declaration is needed because including sql_base.h - causes further includes. [TODO] Eliminate this forward declaration - and include a file with the prototype instead. -*/ -extern void close_thread_tables(THD *thd); - /* Now we don't use abbreviations in server but we will do this in future. */ @@ -1784,10 +1777,7 @@ end_with_setting_default_tz: end_with_close: if (time_zone_tables_exist) - { - close_thread_tables(thd); - thd->mdl_context.release_transactional_locks(); - } + close_mysql_tables(thd); end_with_cleanup: From 740c0d3a87c07dd5f482db5705449143993e7385 Mon Sep 17 00:00:00 2001 From: Konstantin Osipov Date: Tue, 27 Jul 2010 16:42:36 +0400 Subject: [PATCH 087/129] Implement WL#5502 Remove dead 5.0 class Sensitive_cursor. Remove dead and unused code. Update to reflect the code review requests. include/thr_lock.h: Remove declarations for THR_LOCK_OWNER, added along with the patch for sensitive cursors. mysys/thr_lock.c: Remove support for multiple thr_lock requestors per THD. sql/lock.cc: Revert the patch that added support for sensitive cursors. sql/sp_rcontext.cc: Updated the use of mysql_open_cursor(). sql/sql_class.cc: Move the instance of Server_side_cursor from class Prepared_statement to class Statement. sql/sql_class.h: Move the isntance of Server_side_cursor from class Prepared_statement to class Statement. Remove multiple lock_ids of thr_lock. sql/sql_cursor.cc: Remove Sensitive_cursor implementation. sql/sql_cursor.h: Remove declarations for sensitive cursors. sql/sql_prepare.cc: Move the declaration of instance of Server_side_cursor from class Statement to class Prepared_statement, where it's used. sql/sql_select.cc: Remove sensitive cursor support. sql/sql_select.h: Remove sensitive cursor support. sql/sql_union.cc: Remove sensitive cursor support. --- include/thr_lock.h | 19 +-- mysys/thr_lock.c | 51 ++---- sql/lock.cc | 2 +- sql/sp_rcontext.cc | 3 +- sql/sql_class.cc | 5 - sql/sql_class.h | 6 +- sql/sql_cursor.cc | 380 ++------------------------------------------- sql/sql_cursor.h | 16 +- sql/sql_prepare.cc | 6 +- sql/sql_select.cc | 89 +++-------- sql/sql_select.h | 6 - sql/sql_union.cc | 3 +- 12 files changed, 64 insertions(+), 522 deletions(-) diff --git a/include/thr_lock.h b/include/thr_lock.h index 37dc37f8017..5626c067e5e 100644 --- a/include/thr_lock.h +++ b/include/thr_lock.h @@ -89,23 +89,11 @@ typedef struct st_thr_lock_info { pthread_t thread; my_thread_id thread_id; - ulong n_cursors; } THR_LOCK_INFO; -/* - Lock owner identifier. Globally identifies the lock owner within the - thread and among all the threads. The address of an instance of this - structure is used as id. -*/ - -typedef struct st_thr_lock_owner -{ - THR_LOCK_INFO *info; -} THR_LOCK_OWNER; - typedef struct st_thr_lock_data { - THR_LOCK_OWNER *owner; + THR_LOCK_INFO *owner; struct st_thr_lock_data *next,**prev; struct st_thr_lock *lock; mysql_cond_t *cond; @@ -141,19 +129,18 @@ extern LIST *thr_lock_thread_list; extern mysql_mutex_t THR_LOCK_lock; my_bool init_thr_lock(void); /* Must be called once/thread */ -#define thr_lock_owner_init(owner, info_arg) (owner)->info= (info_arg) void thr_lock_info_init(THR_LOCK_INFO *info); void thr_lock_init(THR_LOCK *lock); void thr_lock_delete(THR_LOCK *lock); void thr_lock_data_init(THR_LOCK *lock,THR_LOCK_DATA *data, void *status_param); enum enum_thr_lock_result thr_lock(THR_LOCK_DATA *data, - THR_LOCK_OWNER *owner, + THR_LOCK_INFO *owner, enum thr_lock_type lock_type, ulong lock_wait_timeout); void thr_unlock(THR_LOCK_DATA *data); enum enum_thr_lock_result thr_multi_lock(THR_LOCK_DATA **data, - uint count, THR_LOCK_OWNER *owner, + uint count, THR_LOCK_INFO *owner, ulong lock_wait_timeout); void thr_multi_unlock(THR_LOCK_DATA **data,uint count); void diff --git a/mysys/thr_lock.c b/mysys/thr_lock.c index 9d10ba1fb01..7ba0490cb29 100644 --- a/mysys/thr_lock.c +++ b/mysys/thr_lock.c @@ -107,7 +107,7 @@ my_bool init_thr_lock() } static inline my_bool -thr_lock_owner_equal(THR_LOCK_OWNER *rhs, THR_LOCK_OWNER *lhs) +thr_lock_owner_equal(THR_LOCK_INFO *rhs, THR_LOCK_INFO *lhs) { return rhs == lhs; } @@ -122,7 +122,7 @@ static int check_lock(struct st_lock_list *list, const char* lock_type, { THR_LOCK_DATA *data,**prev; uint count=0; - THR_LOCK_OWNER *UNINIT_VAR(first_owner); + THR_LOCK_INFO *UNINIT_VAR(first_owner); prev= &list->data; if (list->data) @@ -341,7 +341,6 @@ void thr_lock_info_init(THR_LOCK_INFO *info) struct st_my_thread_var *tmp= my_thread_var; info->thread= tmp->pthread_self; info->thread_id= tmp->id; - info->n_cursors= 0; } /* Initialize a lock instance */ @@ -357,7 +356,7 @@ void thr_lock_data_init(THR_LOCK *lock,THR_LOCK_DATA *data, void *param) static inline my_bool -has_old_lock(THR_LOCK_DATA *data, THR_LOCK_OWNER *owner) +has_old_lock(THR_LOCK_DATA *data, THR_LOCK_INFO *owner) { for ( ; data ; data=data->next) { @@ -506,13 +505,12 @@ wait_for_lock(struct st_lock_list *wait, THR_LOCK_DATA *data, enum enum_thr_lock_result -thr_lock(THR_LOCK_DATA *data, THR_LOCK_OWNER *owner, +thr_lock(THR_LOCK_DATA *data, THR_LOCK_INFO *owner, enum thr_lock_type lock_type, ulong lock_wait_timeout) { THR_LOCK *lock=data->lock; enum enum_thr_lock_result result= THR_LOCK_SUCCESS; struct st_lock_list *wait_queue; - THR_LOCK_DATA *lock_owner; DBUG_ENTER("thr_lock"); data->next=0; @@ -521,7 +519,7 @@ thr_lock(THR_LOCK_DATA *data, THR_LOCK_OWNER *owner, data->owner= owner; /* Must be reset ! */ mysql_mutex_lock(&lock->mutex); DBUG_PRINT("lock",("data: 0x%lx thread: 0x%lx lock: 0x%lx type: %d", - (long) data, data->owner->info->thread_id, + (long) data, data->owner->thread_id, (long) lock, (int) lock_type)); check_locks(lock,(uint) lock_type <= (uint) TL_READ_NO_INSERT ? "enter read_lock" : "enter write_lock",0); @@ -558,7 +556,7 @@ thr_lock(THR_LOCK_DATA *data, THR_LOCK_OWNER *owner, */ DBUG_PRINT("lock",("write locked 1 by thread: 0x%lx", - lock->write.data->owner->info->thread_id)); + lock->write.data->owner->thread_id)); if (thr_lock_owner_equal(data->owner, lock->write.data->owner) || (lock->write.data->type <= TL_WRITE_DELAYED && (((int) lock_type <= (int) TL_READ_HIGH_PRIORITY) || @@ -707,7 +705,7 @@ thr_lock(THR_LOCK_DATA *data, THR_LOCK_OWNER *owner, goto end; } DBUG_PRINT("lock",("write locked 2 by thread: 0x%lx", - lock->write.data->owner->info->thread_id)); + lock->write.data->owner->thread_id)); } else { @@ -743,23 +741,10 @@ thr_lock(THR_LOCK_DATA *data, THR_LOCK_OWNER *owner, } } DBUG_PRINT("lock",("write locked 3 by thread: 0x%lx type: %d", - lock->read.data->owner->info->thread_id, data->type)); + lock->read.data->owner->thread_id, data->type)); } wait_queue= &lock->write_wait; } - /* - Try to detect a trivial deadlock when using cursors: attempt to - lock a table that is already locked by an open cursor within the - same connection. lock_owner can be zero if we succumbed to a high - priority writer in the write_wait queue. - */ - lock_owner= lock->read.data ? lock->read.data : lock->write.data; - if (lock_owner && lock_owner->owner->info == owner->info) - { - DBUG_PRINT("lock",("deadlock")); - result= THR_LOCK_DEADLOCK; - goto end; - } /* Can't get lock yet; Wait for it */ DBUG_RETURN(wait_for_lock(wait_queue, data, 0, lock_wait_timeout)); end: @@ -807,7 +792,7 @@ static inline void free_all_read_locks(THR_LOCK *lock, } /* purecov: begin inspected */ DBUG_PRINT("lock",("giving read lock to thread: 0x%lx", - data->owner->info->thread_id)); + data->owner->thread_id)); /* purecov: end */ data->cond=0; /* Mark thread free */ mysql_cond_signal(cond); @@ -826,7 +811,7 @@ void thr_unlock(THR_LOCK_DATA *data) enum thr_lock_type lock_type=data->type; DBUG_ENTER("thr_unlock"); DBUG_PRINT("lock",("data: 0x%lx thread: 0x%lx lock: 0x%lx", - (long) data, data->owner->info->thread_id, (long) lock)); + (long) data, data->owner->thread_id, (long) lock)); mysql_mutex_lock(&lock->mutex); check_locks(lock,"start of release lock",0); @@ -915,7 +900,7 @@ static void wake_up_waiters(THR_LOCK *lock) data->type=TL_WRITE; /* Upgrade lock */ /* purecov: begin inspected */ DBUG_PRINT("lock",("giving write lock of type %d to thread: 0x%lx", - data->type, data->owner->info->thread_id)); + data->type, data->owner->thread_id)); /* purecov: end */ { mysql_cond_t *cond= data->cond; @@ -1020,7 +1005,7 @@ static void sort_locks(THR_LOCK_DATA **data,uint count) enum enum_thr_lock_result -thr_multi_lock(THR_LOCK_DATA **data, uint count, THR_LOCK_OWNER *owner, +thr_multi_lock(THR_LOCK_DATA **data, uint count, THR_LOCK_INFO *owner, ulong lock_wait_timeout) { THR_LOCK_DATA **pos,**end; @@ -1144,7 +1129,7 @@ void thr_multi_unlock(THR_LOCK_DATA **data,uint count) else { DBUG_PRINT("lock",("Free lock: data: 0x%lx thread: 0x%lx lock: 0x%lx", - (long) *pos, (*pos)->owner->info->thread_id, + (long) *pos, (*pos)->owner->thread_id, (long) (*pos)->lock)); } } @@ -1200,7 +1185,7 @@ my_bool thr_abort_locks_for_thread(THR_LOCK *lock, my_thread_id thread_id) mysql_mutex_lock(&lock->mutex); for (data= lock->read_wait.data; data ; data= data->next) { - if (data->owner->info->thread_id == thread_id) /* purecov: tested */ + if (data->owner->thread_id == thread_id) /* purecov: tested */ { DBUG_PRINT("info",("Aborting read-wait lock")); data->type= TL_UNLOCK; /* Mark killed */ @@ -1217,7 +1202,7 @@ my_bool thr_abort_locks_for_thread(THR_LOCK *lock, my_thread_id thread_id) } for (data= lock->write_wait.data; data ; data= data->next) { - if (data->owner->info->thread_id == thread_id) /* purecov: tested */ + if (data->owner->thread_id == thread_id) /* purecov: tested */ { DBUG_PRINT("info",("Aborting write-wait lock")); data->type= TL_UNLOCK; @@ -1387,7 +1372,7 @@ static void thr_print_lock(const char* name,struct st_lock_list *list) prev= &list->data; for (data=list->data; data && count++ < MAX_LOCKS ; data=data->next) { - printf("0x%lx (%lu:%d); ", (ulong) data, data->owner->info->thread_id, + printf("0x%lx (%lu:%d); ", (ulong) data, data->owner->thread_id, (int) data->type); if (data->prev != prev) printf("\nWarning: prev didn't point at previous lock\n"); @@ -1525,7 +1510,6 @@ static void *test_thread(void *arg) { int i,j,param=*((int*) arg); THR_LOCK_DATA data[MAX_LOCK_COUNT]; - THR_LOCK_OWNER owner; THR_LOCK_INFO lock_info; THR_LOCK_DATA *multi_locks[MAX_LOCK_COUNT]; my_thread_init(); @@ -1534,7 +1518,6 @@ static void *test_thread(void *arg) thr_lock_info_init(&lock_info); - thr_lock_owner_init(&owner, &lock_info); for (i=0; i < lock_counts[param] ; i++) thr_lock_data_init(locks+tests[param][i].lock_nr,data+i,NULL); for (j=1 ; j < 10 ; j++) /* try locking 10 times */ @@ -1544,7 +1527,7 @@ static void *test_thread(void *arg) multi_locks[i]= &data[i]; data[i].type= tests[param][i].lock_type; } - thr_multi_lock(multi_locks, lock_counts[param], &owner, TEST_TIMEOUT); + thr_multi_lock(multi_locks, lock_counts[param], &lock_info, TEST_TIMEOUT); mysql_mutex_lock(&LOCK_thread_count); { int tmp=rand() & 7; /* Do something from 0-2 sec */ diff --git a/sql/lock.cc b/sql/lock.cc index 7c0acb58e7c..1a77b576e67 100644 --- a/sql/lock.cc +++ b/sql/lock.cc @@ -313,7 +313,7 @@ MYSQL_LOCK *mysql_lock_tables(THD *thd, TABLE **tables, uint count, uint flags) rc= thr_lock_errno_to_mysql[(int) thr_multi_lock(sql_lock->locks + sql_lock->lock_count, sql_lock->lock_count, - thd->lock_id, timeout)]; + &thd->lock_info, timeout)]; if (rc) { if (sql_lock->table_count) diff --git a/sql/sp_rcontext.cc b/sql/sp_rcontext.cc index 047cec76486..b08f8008b59 100644 --- a/sql/sp_rcontext.cc +++ b/sql/sp_rcontext.cc @@ -525,8 +525,7 @@ sp_cursor::open(THD *thd) MYF(0)); return -1; } - if (mysql_open_cursor(thd, (uint) ALWAYS_MATERIALIZED_CURSOR, &result, - &server_side_cursor)) + if (mysql_open_cursor(thd, &result, &server_side_cursor)) return -1; return 0; } diff --git a/sql/sql_class.cc b/sql/sql_class.cc index f3ef440c2f0..9d48c1282d5 100644 --- a/sql/sql_class.cc +++ b/sql/sql_class.cc @@ -490,7 +490,6 @@ THD::THD() :Statement(&main_lex, &main_mem_root, CONVENTIONAL_EXECUTION, /* statement id */ 0), rli_fake(0), - lock_id(&main_lock_id), user_time(0), in_sub_stmt(0), binlog_unsafe_warning_flags(0), stmt_accessed_table_flag(0), @@ -624,7 +623,6 @@ THD::THD() randominit(&rand, tmp + (ulong) &rand, tmp + (ulong) ::global_query_id); substitute_null_with_insert_id = FALSE; thr_lock_info_init(&lock_info); /* safety: will be reset after start */ - thr_lock_owner_init(&main_lock_id, &lock_info); m_internal_handler= NULL; current_user_used= FALSE; @@ -1113,7 +1111,6 @@ THD::~THD() } #endif stmt_map.reset(); /* close all prepared statements */ - DBUG_ASSERT(lock_info.n_cursors == 0); if (!cleanup_done) cleanup(); @@ -2589,7 +2586,6 @@ Statement::Statement(LEX *lex_arg, MEM_ROOT *mem_root_arg, id(id_arg), mark_used_columns(MARK_COLUMNS_READ), lex(lex_arg), - cursor(0), db(NULL), db_length(0) { @@ -2611,7 +2607,6 @@ void Statement::set_statement(Statement *stmt) mark_used_columns= stmt->mark_used_columns; lex= stmt->lex; query_string= stmt->query_string; - cursor= stmt->cursor; } diff --git a/sql/sql_class.h b/sql/sql_class.h index c095fee6232..8a54e7069b1 100644 --- a/sql/sql_class.h +++ b/sql/sql_class.h @@ -38,7 +38,7 @@ #include "protocol.h" /* Protocol_text, Protocol_binary */ #include "violite.h" /* vio_is_connected */ #include "thr_lock.h" /* thr_lock_type, THR_LOCK_DATA, - THR_LOCK_INFO, THR_LOCK_OWNER */ + THR_LOCK_INFO */ class Reprepare_observer; @@ -723,7 +723,6 @@ public: ENGINE INNODB STATUS. */ LEX_STRING query_string; - Server_side_cursor *cursor; inline char *query() { return query_string.str; } inline uint32 query_length() { return query_string.length; } @@ -1416,9 +1415,6 @@ public: struct system_status_var status_var; // Per thread statistic vars struct system_status_var *initial_status_var; /* used by show status */ THR_LOCK_INFO lock_info; // Locking info of this thread - THR_LOCK_OWNER main_lock_id; // To use for conventional queries - THR_LOCK_OWNER *lock_id; // If not main_lock_id, points to - // the lock_id of a cursor. /** Protects THD data accessed from other threads: - thd->query and thd->query_length (used by SHOW ENGINE diff --git a/sql/sql_cursor.cc b/sql/sql_cursor.cc index 28d2bd8b4de..9a3eb6ff526 100644 --- a/sql/sql_cursor.cc +++ b/sql/sql_cursor.cc @@ -19,60 +19,13 @@ #include "sql_priv.h" #include "unireg.h" #include "sql_cursor.h" -#include "sql_select.h" #include "probes_mysql.h" #include "sql_parse.h" // mysql_execute_command -#include "sql_base.h" /**************************************************************************** Declarations. ****************************************************************************/ -/** - Sensitive_cursor -- a sensitive non-materialized server side - cursor. An instance of this class cursor has its own runtime - state -- list of used items and memory root for runtime memory, - open and locked tables, change list for the changes of the - parsed tree. This state is freed when the cursor is closed. -*/ - -class Sensitive_cursor: public Server_side_cursor -{ - MEM_ROOT main_mem_root; - Query_arena *stmt_arena; - JOIN *join; - TABLE *open_tables; - MYSQL_LOCK *lock; - TABLE *derived_tables; - /* List of items created during execution */ - query_id_t query_id; - struct Engine_info - { - handlerton *ht; - void *read_view; - }; - Engine_info ht_info[MAX_HA]; - Item_change_list change_list; - my_bool close_at_commit; - THR_LOCK_OWNER lock_id; -private: - /* bzero cursor state in THD */ - void reset_thd(THD *thd); -public: - Sensitive_cursor(THD *thd, select_result *result_arg); - - THR_LOCK_OWNER *get_lock_id() { return &lock_id; } - /* Save THD state into cursor */ - void post_open(THD *thd); - - virtual bool is_open() const { return join != 0; } - virtual int open(JOIN *join); - virtual void fetch(ulong num_rows); - virtual void close(); - virtual ~Sensitive_cursor(); -}; - - /** Materialized_cursor -- an insensitive materialized server-side cursor. The result set of this cursor is saved in a temporary @@ -125,10 +78,9 @@ public: /**************************************************************************/ /** - Attempt to open a materialized or non-materialized cursor. + Attempt to open a materialized cursor. @param thd thread handle - @param[in] flags create a materialized cursor or not @param[in] result result class of the caller used as a destination for the rows fetched from the cursor @param[out] pcursor a pointer to store a pointer to cursor in @@ -141,37 +93,21 @@ public: non-zero an error, 'pcursor' has been left intact. */ -int mysql_open_cursor(THD *thd, uint flags, select_result *result, +int mysql_open_cursor(THD *thd, select_result *result, Server_side_cursor **pcursor) { - Sensitive_cursor *sensitive_cursor; select_result *save_result; Select_materialize *result_materialize; LEX *lex= thd->lex; int rc; - /* - The lifetime of the sensitive cursor is the same or less as the - lifetime of the runtime memory of the statement it's opened for. - */ if (! (result_materialize= new (thd->mem_root) Select_materialize(result))) return 1; - if (! (sensitive_cursor= new (thd->mem_root) Sensitive_cursor(thd, result))) - { - delete result_materialize; - result_materialize= NULL; - return 1; - } - save_result= lex->result; lex->result= result_materialize; - if (! (flags & (uint) ALWAYS_MATERIALIZED_CURSOR)) - { - thd->lock_id= sensitive_cursor->get_lock_id(); - thd->cursor= sensitive_cursor; - } + MYSQL_QUERY_EXEC_START(thd->query(), thd->thread_id, (char *) (thd->db ? thd->db : ""), @@ -182,20 +118,14 @@ int mysql_open_cursor(THD *thd, uint flags, select_result *result, MYSQL_QUERY_EXEC_DONE(rc); lex->result= save_result; - thd->lock_id= &thd->main_lock_id; - thd->cursor= 0; - /* Possible options here: - - a sensitive cursor is open. In this case rc is 0 and - result_materialize->materialized_cursor is NULL, or - a materialized cursor is open. In this case rc is 0 and result_materialize->materialized is not NULL - an error occurred during materialization. result_materialize->materialized_cursor is not NULL, but rc != 0 - successful completion of mysql_execute_command without - a cursor: rc is 0, result_materialize->materialized_cursor is NULL, - sensitive_cursor is not open. + a cursor: rc is 0, result_materialize->materialized_cursor is NULL. This is possible if some command writes directly to the network, bypassing select_result mechanism. An example of such command is SHOW VARIABLES or SHOW STATUS. @@ -204,23 +134,10 @@ int mysql_open_cursor(THD *thd, uint flags, select_result *result, { if (result_materialize->materialized_cursor) delete result_materialize->materialized_cursor; - goto err_open; - } - - if (sensitive_cursor->is_open()) - { - DBUG_ASSERT(!result_materialize->materialized_cursor); - /* - It's safer if we grab THD state after mysql_execute_command - is finished and not in Sensitive_cursor::open(), because - currently the call to Sensitive_cursor::open is buried deep - in JOIN::exec of the top level join. - */ - sensitive_cursor->post_open(thd); - *pcursor= sensitive_cursor; goto end; } - else if (result_materialize->materialized_cursor) + + if (result_materialize->materialized_cursor) { Materialized_cursor *materialized_cursor= result_materialize->materialized_cursor; @@ -228,18 +145,13 @@ int mysql_open_cursor(THD *thd, uint flags, select_result *result, if ((rc= materialized_cursor->open(0))) { delete materialized_cursor; - materialized_cursor= NULL; - goto err_open; + goto end; } *pcursor= materialized_cursor; thd->stmt_arena->cleanup_stmt(); - goto end; } -err_open: - DBUG_ASSERT(! (sensitive_cursor && sensitive_cursor->is_open())); - delete sensitive_cursor; end: delete result_materialize; return rc; @@ -271,280 +183,6 @@ void Server_side_cursor::operator delete(void *ptr, size_t size) DBUG_VOID_RETURN; } -/**************************************************************************** - Sensitive_cursor -****************************************************************************/ - -Sensitive_cursor::Sensitive_cursor(THD *thd, select_result *result_arg) - :Server_side_cursor(&main_mem_root, result_arg), - stmt_arena(0), - join(0), - close_at_commit(FALSE) -{ - /* We will overwrite it at open anyway. */ - init_sql_alloc(&main_mem_root, ALLOC_ROOT_MIN_BLOCK_SIZE, 0); - thr_lock_owner_init(&lock_id, &thd->lock_info); - bzero((void*) ht_info, sizeof(ht_info)); -} - - -/** - Save THD state into cursor. - - @todo - - What problems can we have with it if cursor is open? - - TODO: must be fixed because of the prelocked mode. -*/ -void -Sensitive_cursor::post_open(THD *thd) -{ - Engine_info *info; - /* - We need to save and reset thd->mem_root, otherwise it'll be - freed later in mysql_parse. - - We can't just change thd->mem_root here as we want to keep the - things that are already allocated in thd->mem_root for - Sensitive_cursor::fetch() - */ - *mem_root= *thd->mem_root; - stmt_arena= thd->stmt_arena; - state= stmt_arena->state; - /* Allocate a new memory root for thd */ - init_sql_alloc(thd->mem_root, - thd->variables.query_alloc_block_size, - thd->variables.query_prealloc_size); - - /* - Save tables and zero THD pointers to prevent table close in - close_thread_tables. - */ - derived_tables= thd->derived_tables; - open_tables= thd->open_tables; - lock= thd->lock; - query_id= thd->query_id; - free_list= thd->free_list; - thd->change_list.move_elements_to(&change_list); - reset_thd(thd); - /* Now we have an active cursor and can cause a deadlock */ - thd->lock_info.n_cursors++; - - close_at_commit= FALSE; /* reset in case we're reusing the cursor */ - info= &ht_info[0]; - for (Ha_trx_info *ha_trx_info= thd->transaction.stmt.ha_list; - ha_trx_info; ha_trx_info= ha_trx_info->next()) - { - handlerton *ht= ha_trx_info->ht(); - close_at_commit|= test(ht->flags & HTON_CLOSE_CURSORS_AT_COMMIT); - if (ht->create_cursor_read_view) - { - info->ht= ht; - info->read_view= (ht->create_cursor_read_view)(ht, thd); - ++info; - } - } - /* - What problems can we have with it if cursor is open? - TODO: must be fixed because of the prelocked mode. - */ -} - - -/** - bzero cursor state in THD. -*/ - -void -Sensitive_cursor::reset_thd(THD *thd) -{ - thd->derived_tables= 0; - thd->set_open_tables(NULL); - thd->lock= 0; - thd->free_list= 0; - thd->change_list.empty(); -} - - -int -Sensitive_cursor::open(JOIN *join_arg) -{ - join= join_arg; - THD *thd= join->thd; - /* First non-constant table */ - JOIN_TAB *join_tab= join->join_tab + join->const_tables; - DBUG_ENTER("Sensitive_cursor::open"); - - join->change_result(result); - /* - Send fields description to the client; server_status is sent - in 'EOF' packet, which follows send_result_set_metadata(). - We don't simply use SEND_EOF flag of send_result_set_metadata because we also - want to flush the network buffer, which is done only in a standalone - send_eof(). - */ - result->send_result_set_metadata(*join->fields, Protocol::SEND_NUM_ROWS); - thd->server_status|= SERVER_STATUS_CURSOR_EXISTS; - result->send_eof(); - thd->server_status&= ~SERVER_STATUS_CURSOR_EXISTS; - - /* Prepare JOIN for reading rows. */ - join->tmp_table= 0; - join->join_tab[join->tables-1].next_select= setup_end_select_func(join); - join->send_records= 0; - join->fetch_limit= join->unit->offset_limit_cnt; - - /* Disable JOIN CACHE as it is not working with cursors yet */ - for (JOIN_TAB *tab= join_tab; - tab != join->join_tab + join->tables - 1; - tab++) - { - if (tab->next_select == sub_select_cache) - tab->next_select= sub_select; - } - - DBUG_ASSERT(join_tab->table->reginfo.not_exists_optimize == 0); - DBUG_ASSERT(join_tab->not_used_in_distinct == 0); - /* - null_row is set only if row not found and it's outer join: should never - happen for the first table in join_tab list - */ - DBUG_ASSERT(join_tab->table->null_row == 0); - DBUG_RETURN(0); -} - - -/** - Fetch next num_rows rows from the cursor and send them to the client. - - Precondition: - - Sensitive_cursor is open - - @param num_rows fetch up to this number of rows (maybe less) -*/ - -void -Sensitive_cursor::fetch(ulong num_rows) -{ - THD *thd= join->thd; - JOIN_TAB *join_tab= join->join_tab + join->const_tables; - enum_nested_loop_state error= NESTED_LOOP_OK; - Query_arena backup_arena; - Engine_info *info; - DBUG_ENTER("Sensitive_cursor::fetch"); - DBUG_PRINT("enter",("rows: %lu", num_rows)); - - DBUG_ASSERT(thd->derived_tables == 0 && thd->open_tables == 0 && - thd->lock == 0); - - thd->derived_tables= derived_tables; - thd->set_open_tables(open_tables); - thd->lock= lock; - thd->set_query_id(query_id); - change_list.move_elements_to(&thd->change_list); - /* save references to memory allocated during fetch */ - thd->set_n_backup_active_arena(this, &backup_arena); - - for (info= ht_info; info->read_view ; info++) - (info->ht->set_cursor_read_view)(info->ht, thd, info->read_view); - - join->fetch_limit+= num_rows; - - error= sub_select(join, join_tab, 0); - if (error == NESTED_LOOP_OK || error == NESTED_LOOP_NO_MORE_ROWS) - error= sub_select(join,join_tab,1); - if (error == NESTED_LOOP_QUERY_LIMIT) - error= NESTED_LOOP_OK; /* select_limit used */ - if (error == NESTED_LOOP_CURSOR_LIMIT) - join->resume_nested_loop= TRUE; - - ha_release_temporary_latches(thd); - - /* Grab free_list here to correctly free it in close */ - thd->restore_active_arena(this, &backup_arena); - - thd->change_list.move_elements_to(&change_list); - reset_thd(thd); - - for (info= ht_info; info->read_view; info++) - (info->ht->set_cursor_read_view)(info->ht, thd, 0); - - if (error == NESTED_LOOP_CURSOR_LIMIT) - { - /* Fetch limit worked, possibly more rows are there */ - thd->server_status|= SERVER_STATUS_CURSOR_EXISTS; - result->send_eof(); - thd->server_status&= ~SERVER_STATUS_CURSOR_EXISTS; - } - else - { - close(); - if (error == NESTED_LOOP_OK) - { - thd->server_status|= SERVER_STATUS_LAST_ROW_SENT; - result->send_eof(); - thd->server_status&= ~SERVER_STATUS_LAST_ROW_SENT; - } - else if (error != NESTED_LOOP_KILLED) - my_message(ER_OUT_OF_RESOURCES, ER(ER_OUT_OF_RESOURCES), MYF(0)); - } - DBUG_VOID_RETURN; -} - - -/** - @todo - Another hack: we need to set THD state as if in a fetch to be - able to call stmt close. -*/ -void -Sensitive_cursor::close() -{ - THD *thd= join->thd; - DBUG_ENTER("Sensitive_cursor::close"); - - for (Engine_info *info= ht_info; info->read_view; info++) - { - (info->ht->close_cursor_read_view)(info->ht, thd, info->read_view); - info->read_view= 0; - info->ht= 0; - } - - change_list.move_elements_to(&thd->change_list); - { - /* - XXX: Another hack: we need to set THD state as if in a fetch to be - able to call stmt close. - */ - DBUG_ASSERT(lock || open_tables || derived_tables); - - TABLE *tmp_derived_tables= thd->derived_tables; - MYSQL_LOCK *tmp_lock= thd->lock; - - thd->set_open_tables(open_tables); - thd->derived_tables= derived_tables; - thd->lock= lock; - - close_thread_tables(thd); - /* Is expected to at least close tables and empty thd->change_list */ - stmt_arena->cleanup_stmt(); - - thd->set_open_tables(tmp_derived_tables); - thd->derived_tables= tmp_derived_tables; - thd->lock= tmp_lock; - } - thd->lock_info.n_cursors--; /* Decrease the number of active cursors */ - join= 0; - stmt_arena= 0; - free_items(); - DBUG_VOID_RETURN; -} - - -Sensitive_cursor::~Sensitive_cursor() -{ - if (is_open()) - close(); -} /*************************************************************************** Materialized_cursor @@ -570,7 +208,8 @@ Materialized_cursor::Materialized_cursor(select_result *result_arg, @param send_result_set_metadata List of fields that would be sent. */ -int Materialized_cursor::fill_item_list(THD *thd, List &send_result_set_metadata) +int Materialized_cursor::fill_item_list(THD *thd, + List &send_result_set_metadata) { Query_arena backup_arena; int rc; @@ -608,6 +247,7 @@ end: return rc || thd->is_error(); } + int Materialized_cursor::open(JOIN *join __attribute__((unused))) { THD *thd= fake_unit.thd; diff --git a/sql/sql_cursor.h b/sql/sql_cursor.h index 2a394e281b4..ed7bfac821a 100644 --- a/sql/sql_cursor.h +++ b/sql/sql_cursor.h @@ -32,11 +32,11 @@ class JOIN; */ /** - Server_side_cursor -- an interface for materialized and - sensitive (non-materialized) implementation of cursors. All - cursors are self-contained (created in their own memory root). - For that reason they must be deleted only using a pointer to - Server_side_cursor, not to its base class. + Server_side_cursor -- an interface for materialized + implementation of cursors. All cursors are self-contained + (created in their own memory root). For that reason they must + be deleted only using a pointer to Server_side_cursor, not to + its base class. */ class Server_side_cursor: protected Query_arena, public Sql_alloc @@ -60,11 +60,7 @@ public: }; -int mysql_open_cursor(THD *thd, uint flags, - select_result *result, +int mysql_open_cursor(THD *thd, select_result *result, Server_side_cursor **res); -/** Possible values for flags */ -enum { ANY_CURSOR= 1, ALWAYS_MATERIALIZED_CURSOR= 2 }; - #endif /* _sql_cusor_h_ */ diff --git a/sql/sql_prepare.cc b/sql/sql_prepare.cc index 151a135125e..bbdac26d985 100644 --- a/sql/sql_prepare.cc +++ b/sql/sql_prepare.cc @@ -152,6 +152,7 @@ public: THD *thd; Select_fetch_protocol_binary result; Item_param **param_array; + Server_side_cursor *cursor; uint param_count; uint last_errno; uint flags; @@ -2672,7 +2673,6 @@ void mysqld_stmt_fetch(THD *thd, char *packet, uint packet_length) if (!cursor->is_open()) { stmt->close_cursor(); - thd->cursor= 0; reset_stmt_params(stmt); } @@ -3010,6 +3010,7 @@ Prepared_statement::Prepared_statement(THD *thd_arg) thd(thd_arg), result(thd_arg), param_array(0), + cursor(0), param_count(0), last_errno(0), flags((uint) IS_IN_USE) @@ -3751,8 +3752,7 @@ bool Prepared_statement::execute(String *expanded_query, bool open_cursor) /* Go! */ if (open_cursor) - error= mysql_open_cursor(thd, (uint) ALWAYS_MATERIALIZED_CURSOR, - &result, &cursor); + error= mysql_open_cursor(thd, &result, &cursor); else { /* diff --git a/sql/sql_select.cc b/sql/sql_select.cc index 11378ac0d11..1d61c37ba13 100644 --- a/sql/sql_select.cc +++ b/sql/sql_select.cc @@ -33,7 +33,6 @@ #include "sql_select.h" #include "sql_cache.h" // query_cache_* #include "sql_table.h" // primary_key_name -#include "sql_cursor.h" #include "probes_mysql.h" #include "key.h" // key_copy, key_cmp, key_cmp_if_same #include "lock.h" // mysql_unlock_some_tables, @@ -2340,35 +2339,13 @@ JOIN::exec() curr_join->fields= curr_fields_list; curr_join->procedure= procedure; - if (is_top_level_join() && thd->cursor && tables != const_tables) - { - /* - We are here if this is JOIN::exec for the last select of the main unit - and the client requested to open a cursor. - We check that not all tables are constant because this case is not - handled by do_select() separately, and this case is not implemented - for cursors yet. - */ - DBUG_ASSERT(error == 0); - /* - curr_join is used only for reusable joins - that is, - to perform SELECT for each outer row (like in subselects). - This join is main, so we know for sure that curr_join == join. - */ - DBUG_ASSERT(curr_join == this); - /* Open cursor for the last join sweep */ - error= thd->cursor->open(this); - } - else - { - thd_proc_info(thd, "Sending data"); - DBUG_PRINT("info", ("%s", thd->proc_info)); - result->send_result_set_metadata((procedure ? curr_join->procedure_fields_list : - *curr_fields_list), - Protocol::SEND_NUM_ROWS | Protocol::SEND_EOF); - error= do_select(curr_join, curr_fields_list, NULL, procedure); - thd->limit_found_rows= curr_join->send_records; - } + thd_proc_info(thd, "Sending data"); + DBUG_PRINT("info", ("%s", thd->proc_info)); + result->send_result_set_metadata((procedure ? curr_join->procedure_fields_list : + *curr_fields_list), + Protocol::SEND_NUM_ROWS | Protocol::SEND_EOF); + error= do_select(curr_join, curr_fields_list, NULL, procedure); + thd->limit_found_rows= curr_join->send_records; /* Accumulate the counts from all join iterations of all join parts. */ thd->examined_row_count+= curr_join->examined_rows; @@ -2563,16 +2540,6 @@ mysql_select(THD *thd, Item ***rref_pointer_array, join->exec(); - if (thd->cursor && thd->cursor->is_open()) - { - /* - A cursor was opened for the last sweep in exec(). - We are here only if this is mysql_select for top-level SELECT_LEX_UNIT - and there were no error. - */ - free_join= 0; - } - if (thd->lex->describe & DESCRIBE_EXTENDED) { select_lex->where= join->conds_history; @@ -11642,37 +11609,23 @@ sub_select(JOIN *join,JOIN_TAB *join_tab,bool end_of_records) enum_nested_loop_state rc; READ_RECORD *info= &join_tab->read_record; - if (join->resume_nested_loop) + join->return_tab= join_tab; + + if (join_tab->last_inner) { - /* If not the last table, plunge down the nested loop */ - if (join_tab < join->join_tab + join->tables - 1) - rc= (*join_tab->next_select)(join, join_tab + 1, 0); - else - { - join->resume_nested_loop= FALSE; - rc= NESTED_LOOP_OK; - } + /* join_tab is the first inner table for an outer join operation. */ + + /* Set initial state of guard variables for this table.*/ + join_tab->found=0; + join_tab->not_null_compl= 1; + + /* Set first_unmatched for the last inner table of this group */ + join_tab->last_inner->first_unmatched= join_tab; } - else - { - join->return_tab= join_tab; + join->thd->warning_info->reset_current_row_for_warning(); - if (join_tab->last_inner) - { - /* join_tab is the first inner table for an outer join operation. */ - - /* Set initial state of guard variables for this table.*/ - join_tab->found=0; - join_tab->not_null_compl= 1; - - /* Set first_unmatched for the last inner table of this group */ - join_tab->last_inner->first_unmatched= join_tab; - } - join->thd->warning_info->reset_current_row_for_warning(); - - error= (*join_tab->read_first_record)(join_tab); - rc= evaluate_join_record(join, join_tab, error); - } + error= (*join_tab->read_first_record)(join_tab); + rc= evaluate_join_record(join, join_tab, error); while (rc == NESTED_LOOP_OK) { diff --git a/sql/sql_select.h b/sql/sql_select.h index 0496870bb3f..40f9e6d4054 100644 --- a/sql/sql_select.h +++ b/sql/sql_select.h @@ -309,11 +309,6 @@ public: bool sort_and_group; bool first_record,full_join,group, no_field_update; bool do_send_rows; - /** - TRUE when we want to resume nested loop iterations when - fetching data from a cursor - */ - bool resume_nested_loop; table_map const_table_map,found_const_table_map; /* Bitmap of all inner tables from outer joins @@ -479,7 +474,6 @@ public: sort_and_group= 0; first_record= 0; do_send_rows= 1; - resume_nested_loop= FALSE; send_records= 0; found_records= 0; fetch_limit= HA_POS_ERROR; diff --git a/sql/sql_union.cc b/sql/sql_union.cc index 9ca4556524f..acc0f704c44 100644 --- a/sql/sql_union.cc +++ b/sql/sql_union.cc @@ -36,8 +36,7 @@ bool mysql_union(THD *thd, LEX *lex, select_result *result, if (!(res= unit->prepare(thd, result, SELECT_NO_UNLOCK | setup_tables_done_option))) res= unit->exec(); - if (res || !thd->cursor || !thd->cursor->is_open()) - res|= unit->cleanup(); + res|= unit->cleanup(); DBUG_RETURN(res); } From 277b055f141173316ef38588721f0522ccabc4a5 Mon Sep 17 00:00:00 2001 From: Jimmy Yang Date: Wed, 28 Jul 2010 03:20:44 -0700 Subject: [PATCH 088/129] Fix bug #55581 by backporting fix of #52546 from mysql-trunk-innodb to mysql-5.1-innodb plugin. --- storage/innodb_plugin/ChangeLog | 6 ++++ storage/innodb_plugin/include/mem0pool.h | 12 ------- storage/innodb_plugin/mem/mem0mem.c | 12 +++---- storage/innodb_plugin/mem/mem0pool.c | 41 +++++++++++++++--------- storage/innodb_plugin/srv/srv0start.c | 6 +++- 5 files changed, 43 insertions(+), 34 deletions(-) diff --git a/storage/innodb_plugin/ChangeLog b/storage/innodb_plugin/ChangeLog index 5bc4ea7c303..3e802360d23 100644 --- a/storage/innodb_plugin/ChangeLog +++ b/storage/innodb_plugin/ChangeLog @@ -1,3 +1,9 @@ +2010-07-27 The InnoDB Team + + * include/mem0pool.h, mem/mem0mem.c, mem/mem0pool.c, srv/srv0start.c: + Fix Bug#55581 shutdown with innodb-use-sys-malloc=0: assert + mutex->magic_n == MUTEX_MAGIC_N. + 2010-06-30 The InnoDB Team * btr/btr0sea.c, ha/ha0ha.c, handler/ha_innodb.cc, include/btr0sea.h: diff --git a/storage/innodb_plugin/include/mem0pool.h b/storage/innodb_plugin/include/mem0pool.h index 5e93bf88a47..fa8be296ec9 100644 --- a/storage/innodb_plugin/include/mem0pool.h +++ b/storage/innodb_plugin/include/mem0pool.h @@ -100,18 +100,6 @@ mem_pool_get_reserved( /*==================*/ mem_pool_t* pool); /*!< in: memory pool */ /********************************************************************//** -Reserves the mem pool mutex. */ -UNIV_INTERN -void -mem_pool_mutex_enter(void); -/*======================*/ -/********************************************************************//** -Releases the mem pool mutex. */ -UNIV_INTERN -void -mem_pool_mutex_exit(void); -/*=====================*/ -/********************************************************************//** Validates a memory pool. @return TRUE if ok */ UNIV_INTERN diff --git a/storage/innodb_plugin/mem/mem0mem.c b/storage/innodb_plugin/mem/mem0mem.c index c0ce8a3e1ac..1dd4db30841 100644 --- a/storage/innodb_plugin/mem/mem0mem.c +++ b/storage/innodb_plugin/mem/mem0mem.c @@ -367,7 +367,7 @@ mem_heap_create_block( block->line = line; #ifdef MEM_PERIODIC_CHECK - mem_pool_mutex_enter(); + mutex_enter(&(mem_comm_pool->mutex)); if (!mem_block_list_inited) { mem_block_list_inited = TRUE; @@ -376,7 +376,7 @@ mem_heap_create_block( UT_LIST_ADD_LAST(mem_block_list, mem_block_list, block); - mem_pool_mutex_exit(); + mutex_exit(&(mem_comm_pool->mutex)); #endif mem_block_set_len(block, len); mem_block_set_type(block, type); @@ -479,11 +479,11 @@ mem_heap_block_free( UT_LIST_REMOVE(list, heap->base, block); #ifdef MEM_PERIODIC_CHECK - mem_pool_mutex_enter(); + mutex_enter(&(mem_comm_pool->mutex)); UT_LIST_REMOVE(mem_block_list, mem_block_list, block); - mem_pool_mutex_exit(); + mutex_exit(&(mem_comm_pool->mutex)); #endif ut_ad(heap->total_size >= block->len); @@ -556,7 +556,7 @@ mem_validate_all_blocks(void) { mem_block_t* block; - mem_pool_mutex_enter(); + mutex_enter(&(mem_comm_pool->mutex)); block = UT_LIST_GET_FIRST(mem_block_list); @@ -568,6 +568,6 @@ mem_validate_all_blocks(void) block = UT_LIST_GET_NEXT(mem_block_list, block); } - mem_pool_mutex_exit(); + mutex_exit(&(mem_comm_pool->mutex)); } #endif diff --git a/storage/innodb_plugin/mem/mem0pool.c b/storage/innodb_plugin/mem/mem0pool.c index c4f8af607e0..3291453eeb5 100644 --- a/storage/innodb_plugin/mem/mem0pool.c +++ b/storage/innodb_plugin/mem/mem0pool.c @@ -34,6 +34,7 @@ Created 5/12/1997 Heikki Tuuri #include "ut0lst.h" #include "ut0byte.h" #include "mem0mem.h" +#include "srv0start.h" /* We would like to use also the buffer frames to allocate memory. This would be desirable, because then the memory consumption of the database @@ -121,23 +122,33 @@ mysql@lists.mysql.com */ UNIV_INTERN ulint mem_n_threads_inside = 0; /********************************************************************//** -Reserves the mem pool mutex. */ -UNIV_INTERN +Reserves the mem pool mutex if we are not in server shutdown. Use +this function only in memory free functions, since only memory +free functions are used during server shutdown. */ +UNIV_INLINE void -mem_pool_mutex_enter(void) -/*======================*/ +mem_pool_mutex_enter( +/*=================*/ + mem_pool_t* pool) /*!< in: memory pool */ { - mutex_enter(&(mem_comm_pool->mutex)); + if (srv_shutdown_state < SRV_SHUTDOWN_EXIT_THREADS) { + mutex_enter(&(pool->mutex)); + } } /********************************************************************//** -Releases the mem pool mutex. */ -UNIV_INTERN +Releases the mem pool mutex if we are not in server shutdown. As +its corresponding mem_pool_mutex_enter() function, use it only +in memory free functions */ +UNIV_INLINE void -mem_pool_mutex_exit(void) -/*=====================*/ +mem_pool_mutex_exit( +/*================*/ + mem_pool_t* pool) /*!< in: memory pool */ { - mutex_exit(&(mem_comm_pool->mutex)); + if (srv_shutdown_state < SRV_SHUTDOWN_EXIT_THREADS) { + mutex_exit(&(pool->mutex)); + } } /********************************************************************//** @@ -567,7 +578,7 @@ mem_area_free( n = ut_2_log(size); - mutex_enter(&(pool->mutex)); + mem_pool_mutex_enter(pool); mem_n_threads_inside++; ut_a(mem_n_threads_inside == 1); @@ -595,7 +606,7 @@ mem_area_free( pool->reserved += ut_2_exp(n); mem_n_threads_inside--; - mutex_exit(&(pool->mutex)); + mem_pool_mutex_exit(pool); mem_area_free(new_ptr, pool); @@ -611,7 +622,7 @@ mem_area_free( } mem_n_threads_inside--; - mutex_exit(&(pool->mutex)); + mem_pool_mutex_exit(pool); ut_ad(mem_pool_validate(pool)); } @@ -630,7 +641,7 @@ mem_pool_validate( ulint free; ulint i; - mutex_enter(&(pool->mutex)); + mem_pool_mutex_enter(pool); free = 0; @@ -658,7 +669,7 @@ mem_pool_validate( ut_a(free + pool->reserved == pool->size); - mutex_exit(&(pool->mutex)); + mem_pool_mutex_exit(pool); return(TRUE); } diff --git a/storage/innodb_plugin/srv/srv0start.c b/storage/innodb_plugin/srv/srv0start.c index e517b9a86b0..ba9fc831b39 100644 --- a/storage/innodb_plugin/srv/srv0start.c +++ b/storage/innodb_plugin/srv/srv0start.c @@ -2018,9 +2018,13 @@ innobase_shutdown_for_mysql(void) pars_lexer_close(); log_mem_free(); buf_pool_free(); - ut_free_all_mem(); mem_close(); + /* ut_free_all_mem() frees all allocated memory not freed yet + in shutdown, and it will also free the ut_list_mutex, so it + should be the last one for all operation */ + ut_free_all_mem(); + if (os_thread_count != 0 || os_event_count != 0 || os_mutex_count != 0 From cf5b700bac3c647df5a9ca422f0ff082138b326a Mon Sep 17 00:00:00 2001 From: Bjorn Munch Date: Wed, 28 Jul 2010 12:24:38 +0200 Subject: [PATCH 089/129] Bug #55597 MTR: Restart the server, from within the test case, with new CLI options. The expect file can now include "restart:" Also drop check-testcase if this has been done --- mysql-test/mysql-test-run.pl | 22 +++++++++++++++++++--- 1 file changed, 19 insertions(+), 3 deletions(-) diff --git a/mysql-test/mysql-test-run.pl b/mysql-test/mysql-test-run.pl index 91ae508422f..afca6df4cdf 100755 --- a/mysql-test/mysql-test-run.pl +++ b/mysql-test/mysql-test-run.pl @@ -2988,7 +2988,8 @@ sub check_testcase($$) my %started; foreach my $mysqld ( mysqlds() ) { - if ( defined $mysqld->{'proc'} ) + # Skip if server has been restarted with additional options + if ( defined $mysqld->{'proc'} && ! exists $mysqld->{'restart_opts'} ) { my $proc= start_check_testcase($tinfo, $mode, $mysqld); $started{$proc->pid()}= $proc; @@ -3982,6 +3983,12 @@ sub check_expected_crash_and_restart { next; } + if ($last_line =~ /restart:(.+)/) { + my @rest_opt= split(' ', $1); + $mysqld->{'restart_opts'}= \@rest_opt; + } else { + delete $mysqld->{'restart_opts'}; + } unlink($expect_file); # Start server with same settings as last time @@ -4326,7 +4333,13 @@ sub mysqld_start ($$) { } mtr_add_arg($args, "--defaults-group-suffix=%s", $mysqld->after('mysqld')); - mysqld_arguments($args,$mysqld,$extra_opts); + + # Add any additional options from an in-test restart + my @all_opts= @$extra_opts; + if (exists $mysqld->{'restart_opts'}) { + push (@all_opts, @{$mysqld->{'restart_opts'}}); + } + mysqld_arguments($args,$mysqld,\@all_opts); if ( $opt_debug ) { @@ -4507,7 +4520,10 @@ sub server_need_restart { my $extra_opts= get_extra_opts($server, $tinfo); my $started_opts= $server->{'started_opts'}; - if (!My::Options::same($started_opts, $extra_opts) ) + # Also, always restart if server had been restarted with additional + # options within test. + if (!My::Options::same($started_opts, $extra_opts) || + exists $server->{'restart_opts'}) { my $use_dynamic_option_switch= 0; if (!$use_dynamic_option_switch) From 928140d90ec0e039ba7d27aa06bfa8a416e96822 Mon Sep 17 00:00:00 2001 From: Alexander Nozdrin Date: Wed, 28 Jul 2010 15:17:19 +0400 Subject: [PATCH 090/129] Rename select_send::abort() to select_send::abort_result_set() to be more descriptive. --- sql/sql_class.cc | 4 ++-- sql/sql_class.h | 12 ++++++------ sql/sql_delete.cc | 4 ++-- sql/sql_insert.cc | 10 +++++----- sql/sql_parse.cc | 4 ++-- sql/sql_select.cc | 2 +- sql/sql_update.cc | 4 ++-- 7 files changed, 20 insertions(+), 20 deletions(-) diff --git a/sql/sql_class.cc b/sql/sql_class.cc index 1bec02afa96..9c5e9e84cfc 100644 --- a/sql/sql_class.cc +++ b/sql/sql_class.cc @@ -1741,9 +1741,9 @@ bool select_send::send_result_set_metadata(List &list, uint flags) return res; } -void select_send::abort() +void select_send::abort_result_set() { - DBUG_ENTER("select_send::abort"); + DBUG_ENTER("select_send::abort_result_set"); if (is_result_set_started && thd->spcont) { diff --git a/sql/sql_class.h b/sql/sql_class.h index c095fee6232..1afd4fe097c 100644 --- a/sql/sql_class.h +++ b/sql/sql_class.h @@ -2991,7 +2991,7 @@ public: @retval TRUE error, an error message is set */ virtual bool check_simple_select() const; - virtual void abort() {} + virtual void abort_result_set() {} /* Cleanup instance of this class for next execution of a prepared statement/stored procedure. @@ -3034,7 +3034,7 @@ public: bool send_data(List &items); bool send_eof(); virtual bool check_simple_select() const { return FALSE; } - void abort(); + void abort_result_set(); virtual void cleanup(); }; @@ -3126,7 +3126,7 @@ class select_insert :public select_result_interceptor { virtual bool can_rollback_data() { return 0; } void send_error(uint errcode,const char *err); bool send_eof(); - void abort(); + virtual void abort_result_set(); /* not implemented: select_insert is never re-used in prepared statements */ void cleanup(); }; @@ -3162,7 +3162,7 @@ public: void store_values(List &values); void send_error(uint errcode,const char *err); bool send_eof(); - void abort(); + virtual void abort_result_set(); virtual bool can_rollback_data() { return 1; } // Needed for access from local class MY_HOOKS in prepare(), since thd is proteted. @@ -3496,7 +3496,7 @@ public: { return deleted; } - virtual void abort(); + virtual void abort_result_set(); }; @@ -3547,7 +3547,7 @@ public: { return updated; } - virtual void abort(); + virtual void abort_result_set(); }; class my_var : public Sql_alloc { diff --git a/sql/sql_delete.cc b/sql/sql_delete.cc index 00666bc85b4..2f69bac917e 100644 --- a/sql/sql_delete.cc +++ b/sql/sql_delete.cc @@ -770,9 +770,9 @@ void multi_delete::send_error(uint errcode,const char *err) } -void multi_delete::abort() +void multi_delete::abort_result_set() { - DBUG_ENTER("multi_delete::abort"); + DBUG_ENTER("multi_delete::abort_result_set"); /* the error was handled or nothing deleted and no side effects return */ if (error_handled || diff --git a/sql/sql_insert.cc b/sql/sql_insert.cc index c783d74b363..58609ead548 100644 --- a/sql/sql_insert.cc +++ b/sql/sql_insert.cc @@ -3413,9 +3413,9 @@ bool select_insert::send_eof() DBUG_RETURN(0); } -void select_insert::abort() { +void select_insert::abort_result_set() { - DBUG_ENTER("select_insert::abort"); + DBUG_ENTER("select_insert::abort_result_set"); /* If the creation of the table failed (due to a syntax error, for example), no table will have been opened and therefore 'table' @@ -3952,9 +3952,9 @@ bool select_create::send_eof() } -void select_create::abort() +void select_create::abort_result_set() { - DBUG_ENTER("select_create::abort"); + DBUG_ENTER("select_create::abort_result_set"); /* In select_insert::abort() we roll back the statement, including @@ -3972,7 +3972,7 @@ void select_create::abort() log state. */ tmp_disable_binlog(thd); - select_insert::abort(); + select_insert::abort_result_set(); thd->transaction.stmt.modified_non_trans_table= FALSE; reenable_binlog(thd); /* possible error of writing binary log is ignored deliberately */ diff --git a/sql/sql_parse.cc b/sql/sql_parse.cc index ff7080e6c1b..56461f1174b 100644 --- a/sql/sql_parse.cc +++ b/sql/sql_parse.cc @@ -3401,7 +3401,7 @@ end_with_restore_list: res|= thd->is_error(); MYSQL_MULTI_DELETE_DONE(res, del_result->num_deleted()); if (res) - del_result->abort(); + del_result->abort_result_set(); delete del_result; } else @@ -4858,7 +4858,7 @@ static bool execute_sqlcom_select(THD *thd, TABLE_LIST *all_tables) ER_YES, str.ptr()); } if (res) - result->abort(); + result->abort_result_set(); else result->send_eof(); delete result; diff --git a/sql/sql_select.cc b/sql/sql_select.cc index e18486d718a..0c351813d4e 100644 --- a/sql/sql_select.cc +++ b/sql/sql_select.cc @@ -300,7 +300,7 @@ bool handle_select(THD *thd, LEX *lex, select_result *result, thd->is_error())); res|= thd->is_error(); if (unlikely(res)) - result->abort(); + result->abort_result_set(); MYSQL_SELECT_DONE((int) res, (ulong) thd->limit_found_rows); DBUG_RETURN(res); diff --git a/sql/sql_update.cc b/sql/sql_update.cc index c52467531a9..35478e28520 100644 --- a/sql/sql_update.cc +++ b/sql/sql_update.cc @@ -1261,7 +1261,7 @@ bool mysql_multi_update(THD *thd, { /* If we had a another error reported earlier then this will be ignored */ (*result)->send_error(ER_UNKNOWN_ERROR, ER(ER_UNKNOWN_ERROR)); - (*result)->abort(); + (*result)->abort_result_set(); } thd->abort_on_warning= 0; DBUG_RETURN(res); @@ -1861,7 +1861,7 @@ void multi_update::send_error(uint errcode,const char *err) } -void multi_update::abort() +void multi_update::abort_result_set() { /* the error was handled or nothing deleted and no side effects return */ if (error_handled || From aa93035b8869f24eefd213ea751441102642c1b6 Mon Sep 17 00:00:00 2001 From: Bjorn Munch Date: Wed, 28 Jul 2010 13:28:21 +0200 Subject: [PATCH 091/129] Bug #54660 MTR cannot start server properly with non-default innodb_log_file_size Pass any --innodb* options to bootstrap as well Backported to v1, where also a removal of --loose-skip-innodb is needed --- mysql-test/lib/v1/mysql-test-run.pl | 14 +++++++++----- mysql-test/mysql-test-run.pl | 9 +++++++++ 2 files changed, 18 insertions(+), 5 deletions(-) diff --git a/mysql-test/lib/v1/mysql-test-run.pl b/mysql-test/lib/v1/mysql-test-run.pl index 5e785c86027..4e4f09981cc 100755 --- a/mysql-test/lib/v1/mysql-test-run.pl +++ b/mysql-test/lib/v1/mysql-test-run.pl @@ -3126,6 +3126,15 @@ sub install_db ($$) { mtr_add_arg($args, "--lc-messages-dir=%s", $path_language); mtr_add_arg($args, "--character-sets-dir=%s", $path_charsetsdir); + # InnoDB arguments that affect file location and sizes may + # need to be given to the bootstrap process as well as the + # server process. + foreach my $extra_opt ( @opt_extra_mysqld_opt ) { + if ($extra_opt =~ /--innodb/) { + mtr_add_arg($args, $extra_opt); + } + } + # If DISABLE_GRANT_OPTIONS is defined when the server is compiled (e.g., # configure --disable-grant-options), mysqld will not recognize the # --bootstrap or --skip-grant-tables options. The user can set @@ -3925,11 +3934,6 @@ sub mysqld_arguments ($$$$) { mtr_add_arg($args, "%s--local-infile", $prefix); - if ( $idx > 0 or !$use_innodb) - { - mtr_add_arg($args, "%s--loose-skip-innodb", $prefix); - } - my $cluster= $clusters->[$mysqld->{'cluster'}]; if ( $cluster->{'pid'} || # Cluster is started $cluster->{'use_running'} ) # Using running cluster diff --git a/mysql-test/mysql-test-run.pl b/mysql-test/mysql-test-run.pl index c7b48ebdd74..46d194bfc09 100755 --- a/mysql-test/mysql-test-run.pl +++ b/mysql-test/mysql-test-run.pl @@ -2888,6 +2888,15 @@ sub mysql_install_db { mtr_add_arg($args, "--lc-messages-dir=%s", $install_lang); mtr_add_arg($args, "--character-sets-dir=%s", $install_chsdir); + # InnoDB arguments that affect file location and sizes may + # need to be given to the bootstrap process as well as the + # server process. + foreach my $extra_opt ( @opt_extra_mysqld_opt ) { + if ($extra_opt =~ /--innodb/) { + mtr_add_arg($args, $extra_opt); + } + } + # If DISABLE_GRANT_OPTIONS is defined when the server is compiled (e.g., # configure --disable-grant-options), mysqld will not recognize the # --bootstrap or --skip-grant-tables options. The user can set From 8c4e3896066c613abf60b8d5ec6b57102fdb139b Mon Sep 17 00:00:00 2001 From: Konstantin Osipov Date: Wed, 28 Jul 2010 21:56:15 +0400 Subject: [PATCH 092/129] Fix a failing assert when running funcs_1.innodb_trig_03 test. The failure was introduced by a precursor patch for the fix for Bug#52044. When opening tables for GRANT statement to check that subject columns exist, mysql_table_grant() would try to lock the tables, and thus start a transaction. This was unnecessary and lead to an assert. sql/sql_acl.cc: Use open_normal_and_derived_tables() rather than open_and_lock_tables() to avoid an assert that no transaction is started in GRANT statement. --- sql/sql_acl.cc | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/sql/sql_acl.cc b/sql/sql_acl.cc index 0008968de2a..7163702d401 100644 --- a/sql/sql_acl.cc +++ b/sql/sql_acl.cc @@ -3072,7 +3072,7 @@ int mysql_table_grant(THD *thd, TABLE_LIST *table_list, class LEX_COLUMN *column; List_iterator column_iter(columns); - if (open_and_lock_tables(thd, table_list, TRUE, 0)) + if (open_normal_and_derived_tables(thd, table_list, 0)) DBUG_RETURN(TRUE); while ((column = column_iter++)) From 2124538d9cea1cea39b01f0b8b99052b36004fb9 Mon Sep 17 00:00:00 2001 From: unknown Date: Thu, 29 Jul 2010 11:00:57 +0800 Subject: [PATCH 093/129] BUG#49124 Security issue with /*!-versioned */ SQL statements on Slave /*![:version:] Query Code */, where [:version:] is a sequence of 5 digits representing the mysql server version(e.g /*!50200 ... */), is a special comment that the query in it can be executed on those servers whose versions are larger than the version appearing in the comment. It leads to a security issue when slave's version is larger than master's. A malicious user can improve his privileges on slaves. Because slave SQL thread is running with SUPER privileges, so it can execute queries that he/she does not have privileges on master. This bug is fixed with the logic below: - To replace '!' with ' ' in the magic comments which are not applied on master. So they become common comments and will not be applied on slave. - Example: 'INSERT INTO t1 VALUES (1) /*!10000, (2)*/ /*!99999 ,(3)*/ will be binlogged as 'INSERT INTO t1 VALUES (1) /*!10000, (2)*/ /* 99999 ,(3)*/ mysql-test/suite/rpl/t/rpl_conditional_comments.test: Test the patch for this bug. sql/mysql_priv.h: Rename inBuf as rawBuf and remove the const limitation. sql/sql_lex.cc: To replace '!' with ' ' in the magic comments which are not applied on master. sql/sql_lex.h: Remove the const limitation on parameter buff, as it can be modified in the function since this patch. Add member function yyUnput for Lex_input_stream. It set a character back the query buff. sql/sql_parse.cc: Rename inBuf as rawBuf and remove the const limitation. sql/sql_partition.cc: Remove the const limitation on parameter part_buff, as it can be modified in the function since this patch. sql/sql_partition.h: Remove the const limitation on parameter part_buff, as it can be modified in the function since this patch. sql/table.h: Remove the const limitation on variable partition_info, as it can be modified since this patch. --- .../rpl/r/rpl_conditional_comments.result | 57 ++++++++++++++ .../suite/rpl/t/rpl_conditional_comments.test | 74 +++++++++++++++++++ sql/mysql_priv.h | 2 +- sql/sql_lex.cc | 19 ++++- sql/sql_lex.h | 20 ++++- sql/sql_parse.cc | 12 +-- sql/sql_partition.cc | 2 +- sql/sql_partition.h | 2 +- sql/table.h | 2 +- 9 files changed, 173 insertions(+), 17 deletions(-) create mode 100644 mysql-test/suite/rpl/r/rpl_conditional_comments.result create mode 100644 mysql-test/suite/rpl/t/rpl_conditional_comments.test diff --git a/mysql-test/suite/rpl/r/rpl_conditional_comments.result b/mysql-test/suite/rpl/r/rpl_conditional_comments.result new file mode 100644 index 00000000000..105d3bc59f3 --- /dev/null +++ b/mysql-test/suite/rpl/r/rpl_conditional_comments.result @@ -0,0 +1,57 @@ +stop slave; +drop table if exists t1,t2,t3,t4,t5,t6,t7,t8,t9; +reset master; +reset slave; +drop table if exists t1,t2,t3,t4,t5,t6,t7,t8,t9; +start slave; +CREATE TABLE t1(c1 INT); +show binlog events from ; +Log_name Pos Event_type Server_id End_log_pos Info +master-bin.000001 # Query # # use `test`; CREATE TABLE t1(c1 INT) + +# Case 1: +# ------------------------------------------------------------------ +# In a statement, some CCs are applied while others are not. The CCs +# which are not applied on master will be binlogged as common comments. +/*!99999 --- */INSERT /*!INTO*/ /*!10000 t1 */ VALUES(10) /*!99999 ,(11)*/; +show binlog events from ; +Log_name Pos Event_type Server_id End_log_pos Info +master-bin.000001 # Query # # use `test`; /* 99999 --- */INSERT /*!INTO*/ /*!10000 t1 */ VALUES(10) /* 99999 ,(11)*/ +Comparing tables master:test.t1 and slave:test.t1 + +# Case 2: +# ----------------------------------------------------------------- +# Verify whether it can be binlogged correctly when executing prepared +# statement. +PREPARE stmt FROM 'INSERT INTO /*!99999 blabla*/ t1 VALUES(60) /*!99999 ,(61)*/'; +EXECUTE stmt; +DROP TABLE t1; +CREATE TABLE t1(c1 INT); +EXECUTE stmt; +Comparing tables master:test.t1 and slave:test.t1 + +SET @value=62; +PREPARE stmt FROM 'INSERT INTO /*!99999 blabla */ t1 VALUES(?) /*!99999 ,(63)*/'; +EXECUTE stmt USING @value; +DROP TABLE t1; +CREATE TABLE t1(c1 INT); +EXECUTE stmt USING @value; +show binlog events from ; +Log_name Pos Event_type Server_id End_log_pos Info +master-bin.000001 # Query # # use `test`; INSERT INTO /* 99999 blabla*/ t1 VALUES(60) /* 99999 ,(61)*/ +master-bin.000001 # Query # # use `test`; DROP TABLE t1 +master-bin.000001 # Query # # use `test`; CREATE TABLE t1(c1 INT) +master-bin.000001 # Query # # use `test`; INSERT INTO /* 99999 blabla*/ t1 VALUES(60) /* 99999 ,(61)*/ +master-bin.000001 # Query # # use `test`; INSERT INTO /* 99999 blabla */ t1 VALUES(62) /* 99999 ,(63)*/ +master-bin.000001 # Query # # use `test`; DROP TABLE t1 +master-bin.000001 # Query # # use `test`; CREATE TABLE t1(c1 INT) +master-bin.000001 # Query # # use `test`; INSERT INTO /* 99999 blabla */ t1 VALUES(62) /* 99999 ,(63)*/ +Comparing tables master:test.t1 and slave:test.t1 + +# Case 3: +# ----------------------------------------------------------------- +# Verify it can restore the '!', if the it is an uncomplete conditional +# comments +SELECT c1 FROM /*!99999 t1 WHEREN; +ERROR 42000: You have an error in your SQL syntax; check the manual that corresponds to your MySQL server version for the right syntax to use near '/*!99999 t1 WHEREN' at line 1 +DROP TABLE t1; diff --git a/mysql-test/suite/rpl/t/rpl_conditional_comments.test b/mysql-test/suite/rpl/t/rpl_conditional_comments.test new file mode 100644 index 00000000000..14251d5eb37 --- /dev/null +++ b/mysql-test/suite/rpl/t/rpl_conditional_comments.test @@ -0,0 +1,74 @@ +############################################################################### +# After the patch for BUG#49124: +# - Use ' ' instead of '!' in the conditional comments which are not applied on +# master. So they become common comments and will not be applied on slave. +# +# - Example: +# 'INSERT INTO t1 VALUES (1) /*!10000, (2)*/ /*!99999 ,(3)*/ +# will be binlogged as +# 'INSERT INTO t1 VALUES (1) /*!10000, (2)*/ /* 99999 ,(3)*/'. +############################################################################### +source include/master-slave.inc; +source include/have_binlog_format_statement.inc; + +CREATE TABLE t1(c1 INT); +source include/show_binlog_events.inc; +let $binlog_start= query_get_value(SHOW MASTER STATUS, Position, 1); + +--echo +--echo # Case 1: +--echo # ------------------------------------------------------------------ +--echo # In a statement, some CCs are applied while others are not. The CCs +--echo # which are not applied on master will be binlogged as common comments. + +/*!99999 --- */INSERT /*!INTO*/ /*!10000 t1 */ VALUES(10) /*!99999 ,(11)*/; + +source include/show_binlog_events.inc; +let $binlog_start= query_get_value(SHOW MASTER STATUS, Position, 1); +sync_slave_with_master; +let $diff_table_1=master:test.t1; +let $diff_table_2=slave:test.t1; +source include/diff_tables.inc; + +--echo +--echo # Case 2: +--echo # ----------------------------------------------------------------- +--echo # Verify whether it can be binlogged correctly when executing prepared +--echo # statement. +PREPARE stmt FROM 'INSERT INTO /*!99999 blabla*/ t1 VALUES(60) /*!99999 ,(61)*/'; +EXECUTE stmt; +DROP TABLE t1; +CREATE TABLE t1(c1 INT); +EXECUTE stmt; + +sync_slave_with_master; +let $diff_table_1=master:test.t1; +let $diff_table_2=slave:test.t1; +source include/diff_tables.inc; + +--echo +SET @value=62; +PREPARE stmt FROM 'INSERT INTO /*!99999 blabla */ t1 VALUES(?) /*!99999 ,(63)*/'; +EXECUTE stmt USING @value; +DROP TABLE t1; +CREATE TABLE t1(c1 INT); +EXECUTE stmt USING @value; + +source include/show_binlog_events.inc; +let $binlog_start= query_get_value(SHOW MASTER STATUS, Position, 1); + +sync_slave_with_master; +let $diff_table_1=master:test.t1; +let $diff_table_2=slave:test.t1; +source include/diff_tables.inc; + +--echo +--echo # Case 3: +--echo # ----------------------------------------------------------------- +--echo # Verify it can restore the '!', if the it is an uncomplete conditional +--echo # comments +--error 1064 +SELECT c1 FROM /*!99999 t1 WHEREN; + +DROP TABLE t1; +source include/master-slave-end.inc; diff --git a/sql/mysql_priv.h b/sql/mysql_priv.h index 88f3763ef50..9f2c0b04f2c 100644 --- a/sql/mysql_priv.h +++ b/sql/mysql_priv.h @@ -1024,7 +1024,7 @@ bool mysql_opt_change_db(THD *thd, bool force_switch, bool *cur_db_changed); -void mysql_parse(THD *thd, const char *inBuf, uint length, +void mysql_parse(THD *thd, char *rawbuf, uint length, const char ** semicolon); bool mysql_test_parse_for_slave(THD *thd,char *inBuf,uint length); diff --git a/sql/sql_lex.cc b/sql/sql_lex.cc index 6bfd6f3906c..2bff036b1f1 100644 --- a/sql/sql_lex.cc +++ b/sql/sql_lex.cc @@ -111,7 +111,7 @@ st_parsing_options::reset() } -bool Lex_input_stream::init(THD *thd, const char *buff, unsigned int length) +bool Lex_input_stream::init(THD *thd, char *buff, unsigned int length) { DBUG_EXECUTE_IF("bug42064_simulate_oom", DBUG_SET("+d,simulate_out_of_memory");); @@ -1292,11 +1292,10 @@ int MYSQLlex(void *arg, void *yythd) ulong version; version=strtol(version_str, NULL, 10); - /* Accept 'M' 'm' 'm' 'd' 'd' */ - lip->yySkipn(5); - if (version <= MYSQL_VERSION_ID) { + /* Accept 'M' 'm' 'm' 'd' 'd' */ + lip->yySkipn(5); /* Expand the content of the special comment as real code */ lip->set_echo(TRUE); state=MY_LEX_START; @@ -1304,7 +1303,19 @@ int MYSQLlex(void *arg, void *yythd) } else { + const char* version_mark= lip->get_ptr() - 1; + DBUG_ASSERT(*version_mark == '!'); + /* + Patch and skip the conditional comment to avoid it + being propagated infinitely (eg. to a slave). + */ + char *pcom= lip->yyUnput(' '); comment_closed= ! consume_comment(lip, 1); + if (! comment_closed) + { + DBUG_ASSERT(pcom == version_mark); + *pcom= '!'; + } /* version allowed to have one level of comment inside. */ } } diff --git a/sql/sql_lex.h b/sql/sql_lex.h index cefb0cb49fb..7403bb5a1a4 100644 --- a/sql/sql_lex.h +++ b/sql/sql_lex.h @@ -1180,7 +1180,7 @@ public: @retval FALSE OK @retval TRUE Error */ - bool init(THD *thd, const char *buff, unsigned int length); + bool init(THD *thd, char *buff, unsigned int length); /** Set the echo mode. @@ -1294,6 +1294,20 @@ public: m_ptr += n; } + /** + Puts a character back into the stream, canceling + the effect of the last yyGet() or yySkip(). + Note that the echo mode should not change between calls + to unput, get, or skip from the stream. + */ + char *yyUnput(char ch) + { + *--m_ptr= ch; + if (m_echo) + m_cpp_ptr--; + return m_ptr; + } + /** End of file indicator for the query text to parse. @return true if there are no more characters to parse @@ -1440,7 +1454,7 @@ public: private: /** Pointer to the current position in the raw input stream. */ - const char *m_ptr; + char *m_ptr; /** Starting position of the last token parsed, in the raw buffer. */ const char *m_tok_start; @@ -1972,7 +1986,7 @@ public: @retval FALSE OK @retval TRUE Error */ - bool init(THD *thd, const char *buff, unsigned int length) + bool init(THD *thd, char *buff, unsigned int length) { return m_lip.init(thd, buff, length); } diff --git a/sql/sql_parse.cc b/sql/sql_parse.cc index 0a509f62849..9ec03ea1d5f 100644 --- a/sql/sql_parse.cc +++ b/sql/sql_parse.cc @@ -5946,13 +5946,13 @@ void mysql_init_multi_delete(LEX *lex) Parse a query. @param thd Current thread - @param inBuf Begining of the query text + @param rawbuf Begining of the query text @param length Length of the query text @param[out] found_semicolon For multi queries, position of the character of the next query in the query text. */ -void mysql_parse(THD *thd, const char *inBuf, uint length, +void mysql_parse(THD *thd, char *rawbuf, uint length, const char ** found_semicolon) { DBUG_ENTER("mysql_parse"); @@ -5978,7 +5978,7 @@ void mysql_parse(THD *thd, const char *inBuf, uint length, lex_start(thd); mysql_reset_thd_for_next_command(thd); - if (query_cache_send_result_to_client(thd, (char*) inBuf, length) <= 0) + if (query_cache_send_result_to_client(thd, rawbuf, length) <= 0) { LEX *lex= thd->lex; @@ -5987,7 +5987,7 @@ void mysql_parse(THD *thd, const char *inBuf, uint length, Parser_state parser_state; bool err; - if (!(err= parser_state.init(thd, inBuf, length))) + if (!(err= parser_state.init(thd, rawbuf, length))) { err= parse_sql(thd, & parser_state, NULL); *found_semicolon= parser_state.m_lip.found_semicolon; @@ -6073,14 +6073,14 @@ void mysql_parse(THD *thd, const char *inBuf, uint length, 1 can be ignored */ -bool mysql_test_parse_for_slave(THD *thd, char *inBuf, uint length) +bool mysql_test_parse_for_slave(THD *thd, char *rawbuf, uint length) { LEX *lex= thd->lex; bool error= 0; DBUG_ENTER("mysql_test_parse_for_slave"); Parser_state parser_state; - if (!(error= parser_state.init(thd, inBuf, length))) + if (!(error= parser_state.init(thd, rawbuf, length))) { lex_start(thd); mysql_reset_thd_for_next_command(thd); diff --git a/sql/sql_partition.cc b/sql/sql_partition.cc index 122ae661046..76caa2b0c8d 100644 --- a/sql/sql_partition.cc +++ b/sql/sql_partition.cc @@ -3876,7 +3876,7 @@ void get_partition_set(const TABLE *table, uchar *buf, const uint index, */ bool mysql_unpack_partition(THD *thd, - const char *part_buf, uint part_info_len, + char *part_buf, uint part_info_len, const char *part_state, uint part_state_len, TABLE* table, bool is_create_table_ind, handlerton *default_db_type, diff --git a/sql/sql_partition.h b/sql/sql_partition.h index b9efbf25a00..02a5ead1117 100644 --- a/sql/sql_partition.h +++ b/sql/sql_partition.h @@ -78,7 +78,7 @@ void get_full_part_id_from_key(const TABLE *table, uchar *buf, KEY *key_info, const key_range *key_spec, part_id_range *part_spec); -bool mysql_unpack_partition(THD *thd, const char *part_buf, +bool mysql_unpack_partition(THD *thd, char *part_buf, uint part_info_len, const char *part_state, uint part_state_len, TABLE *table, bool is_create_table_ind, diff --git a/sql/table.h b/sql/table.h index 3ef3c5e0cb2..8ea7175eec4 100644 --- a/sql/table.h +++ b/sql/table.h @@ -442,7 +442,7 @@ typedef struct st_table_share #ifdef WITH_PARTITION_STORAGE_ENGINE /** @todo: Move into *ha_data for partitioning */ bool auto_partitioned; - const char *partition_info; + char *partition_info; uint partition_info_len; uint partition_info_buffer_size; const char *part_state; From 6f6a3e529310fa3f719ff0381ee94e83e7e93683 Mon Sep 17 00:00:00 2001 From: Alexander Barkov Date: Thu, 29 Jul 2010 10:12:44 +0400 Subject: [PATCH 094/129] Postfix for BUG#45012. Problem: The original patch didn't compile on debug_werror due to wrong format in printf("%d") for size_t variables. Fix: Adding cast to (int). --- unittest/strings/strings-t.c | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/unittest/strings/strings-t.c b/unittest/strings/strings-t.c index 2d246cfa17f..278f42e56a5 100644 --- a/unittest/strings/strings-t.c +++ b/unittest/strings/strings-t.c @@ -30,7 +30,7 @@ test_like_range_for_charset(CHARSET_INFO *cs, const char *src, size_t src_len) cs->coll->like_range(cs, src, src_len, '\\', '_', '%', sizeof(min_str), min_str, max_str, &min_len, &max_len); - diag("min_len=%d\tmax_len=%d\t%s", min_len, max_len, cs->name); + diag("min_len=%d\tmax_len=%d\t%s", (int) min_len, (int) max_len, cs->name); min_well_formed_len= cs->cset->well_formed_len(cs, min_str, min_str + min_len, 10000, &error); @@ -39,11 +39,11 @@ test_like_range_for_charset(CHARSET_INFO *cs, const char *src, size_t src_len) 10000, &error); if (min_len != min_well_formed_len) diag("Bad min_str: min_well_formed_len=%d min_str[%d]=0x%02X", - min_well_formed_len, min_well_formed_len, + (int) min_well_formed_len, (int) min_well_formed_len, (uchar) min_str[min_well_formed_len]); if (max_len != max_well_formed_len) diag("Bad max_str: max_well_formed_len=%d max_str[%d]=0x%02X", - max_well_formed_len, max_well_formed_len, + (int) max_well_formed_len, (int) max_well_formed_len, (uchar) max_str[max_well_formed_len]); return min_len == min_well_formed_len && From dd135df6a8ef67e0c9615a5732ce89737f144e68 Mon Sep 17 00:00:00 2001 From: Konstantin Osipov Date: Thu, 29 Jul 2010 12:35:12 +0400 Subject: [PATCH 095/129] Fix a Windows failure of main.merge test introduced by the precursor patch for Bug#52044. When passing the TABLE instance for invalidation to the query cache, we didn't always have a valid share (in case of error). Make sure we invalidate the table using TABLE_LIST, not TABLE, object. sql/sql_table.cc: Make sure we invalidate the table using TABLE_LIST, not TABLE, object. --- sql/sql_table.cc | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/sql/sql_table.cc b/sql/sql_table.cc index c4b4a37b35a..0447e1a24af 100644 --- a/sql/sql_table.cc +++ b/sql/sql_table.cc @@ -5144,7 +5144,8 @@ send_result_message: May be something modified. Consequently, we have to invalidate the query cache. */ - query_cache_invalidate3(thd, table->table, 0); + table->table= 0; // For query cache + query_cache_invalidate3(thd, table, 0); } } /* Error path, a admin command failed. */ @@ -5152,7 +5153,6 @@ send_result_message: trans_commit_implicit(thd); close_thread_tables(thd); thd->mdl_context.release_transactional_locks(); - table->table=0; // For query cache /* If it is CHECK TABLE v1, v2, v3, and v1, v2, v3 are views, we will run From ca4c028267d0abba049f5cd587ae4cab447428b1 Mon Sep 17 00:00:00 2001 From: Alexander Nozdrin Date: Thu, 29 Jul 2010 19:35:22 +0400 Subject: [PATCH 096/129] Fix build failure. --- sql/ha_ndbcluster.cc | 1 + sql/ha_ndbcluster_binlog.cc | 1 + 2 files changed, 2 insertions(+) diff --git a/sql/ha_ndbcluster.cc b/sql/ha_ndbcluster.cc index 7cac8373bc4..d4a98265c49 100644 --- a/sql/ha_ndbcluster.cc +++ b/sql/ha_ndbcluster.cc @@ -36,6 +36,7 @@ #include "discover.h" // readfrm #include "sql_acl.h" // wild_case_compare #include "rpl_mi.h" +#include "transaction.h" /* There is an incompatibility between GNU ar and the Solaris linker diff --git a/sql/ha_ndbcluster_binlog.cc b/sql/ha_ndbcluster_binlog.cc index b610687496e..26fdb8e1425 100644 --- a/sql/ha_ndbcluster_binlog.cc +++ b/sql/ha_ndbcluster_binlog.cc @@ -36,6 +36,7 @@ #include "lock.h" // MYSQL_LOCK_IGNORE_FLUSH, // mysql_unlock_tables #include "sql_parse.h" // mysql_parse +#include "transaction.h" #ifdef ndb_dynamite #undef assert From 5861d8e7682833fa29173af9264e398c39d63451 Mon Sep 17 00:00:00 2001 From: Konstantin Osipov Date: Thu, 29 Jul 2010 20:15:37 +0400 Subject: [PATCH 097/129] Fix a compilation failure of ha_ndbcluster_binlog.cc. sql/ha_ndbcluster_binlog.cc: Fix a compilation failure when built with autotools. --- sql/ha_ndbcluster_binlog.cc | 1 + 1 file changed, 1 insertion(+) diff --git a/sql/ha_ndbcluster_binlog.cc b/sql/ha_ndbcluster_binlog.cc index b610687496e..26fdb8e1425 100644 --- a/sql/ha_ndbcluster_binlog.cc +++ b/sql/ha_ndbcluster_binlog.cc @@ -36,6 +36,7 @@ #include "lock.h" // MYSQL_LOCK_IGNORE_FLUSH, // mysql_unlock_tables #include "sql_parse.h" // mysql_parse +#include "transaction.h" #ifdef ndb_dynamite #undef assert From 70f04844e5a41889b584af03d1228c9a3239da37 Mon Sep 17 00:00:00 2001 From: Konstantin Osipov Date: Thu, 29 Jul 2010 20:29:01 +0400 Subject: [PATCH 098/129] Fix the tree name. --- .bzr-mysql/default.conf | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.bzr-mysql/default.conf b/.bzr-mysql/default.conf index be5e1c348fa..4eab3d239d0 100644 --- a/.bzr-mysql/default.conf +++ b/.bzr-mysql/default.conf @@ -1,4 +1,4 @@ [MYSQL] post_commit_to = "commits@lists.mysql.com" post_push_to = "commits@lists.mysql.com" -tree_name = "mysql-trunk-runtime" +tree_name = "mysql-trunk-bugfixing" From a0ab253fbd622429beab6027cd532e3f203188be Mon Sep 17 00:00:00 2001 From: Alexander Nozdrin Date: Fri, 30 Jul 2010 19:28:36 +0400 Subject: [PATCH 099/129] Auto-merge from mysql-trunk-bugfixing. ****** This patch fixes the following bugs: - Bug#5889: Exit handler for a warning doesn't hide the warning in trigger - Bug#9857: Stored procedures: handler for sqlwarning ignored - Bug#23032: Handlers declared in a SP do not handle warnings generated in sub-SP - Bug#36185: Incorrect precedence for warning and exception handlers The problem was in the way warnings/errors during stored routine execution were handled. Prior to this patch the logic was as follows: - when a warning/an error happens: if we're executing a stored routine, and there is a handler for that warning/error, remember the handler, ignore the warning/error and continue execution. - after a stored routine instruction is executed: check for a remembered handler and activate one (if any). This logic caused several problems: - if one instruction generates several warnings (errors) it's impossible to choose the right handler -- a handler for the first generated condition was chosen and remembered for activation. - mess with handling conditions in scopes different from the current one. - not putting generated warnings/errors into Warning Info (Diagnostic Area) is against The Standard. The patch changes the logic as follows: - Diagnostic Area is cleared on the beginning of each statement that either is able to generate warnings, or is able to work with tables. - at the end of a stored routine instruction, Diagnostic Area is left intact. - Diagnostic Area is checked after each stored routine instruction. If an instruction generates several condition, it's now possible to take a look at all of them and determine an appropriate handler. mysql-test/r/signal.result: Update result file: 1. handled conditions are not cleared any more; 2. reflect changes in signal.test mysql-test/r/signal_demo3.result: Update result file: handled conditions are not cleared any more. Due to playing with max_error_count, resulting warning lists have changed. mysql-test/r/sp-big.result: Update result file: handled conditions are not cleared any more. mysql-test/r/sp-bugs.result: Update result file: handled conditions are not cleared any more. mysql-test/r/sp-code.result: Update result file: 1. handled conditions are not cleared any more. 2. add result for a new test case in sp-code.test. mysql-test/r/sp-error.result: Update result file: 1. handled conditions are not cleared any more. 2. add result for a new test case in sp-error.test. mysql-test/r/sp.result: Update result file: handled conditions are not cleared any more. mysql-test/r/sp_trans.result: Update result file: handled conditions are not cleared any more. mysql-test/r/strict.result: Update result file: handled conditions are not cleared any more. mysql-test/r/view.result: Update result file: handled conditions are not cleared any more. mysql-test/suite/funcs_1/r/innodb_storedproc_02.result: Update result file: handled conditions are not cleared any more. mysql-test/suite/funcs_1/r/memory_storedproc_02.result: Update result file: handled conditions are not cleared any more. mysql-test/suite/funcs_1/r/myisam_storedproc_02.result: Update result file: handled conditions are not cleared any more. mysql-test/suite/funcs_1/r/storedproc.result: Update result file: handled conditions are not cleared any more. mysql-test/suite/rpl/r/rpl_row_sp005.result: Update result file: handled conditions are not cleared any more. mysql-test/suite/rpl/r/rpl_row_sp006_InnoDB.result: Update result file: handled conditions are not cleared any more. mysql-test/suite/rpl/r/rpl_row_trig003.result: Update result file: handled conditions are not cleared any more. mysql-test/t/signal.test: Make a test case more readable in the result file. mysql-test/t/sp-code.test: Add a test case for Bug#23032 checking that No Data takes precedence on Warning. mysql-test/t/sp-error.test: Adding test cases for: - Bug#23032 - Bug#36185 - Bug#5889 - Bug#9857 mysql-test/t/sp.test: Fixing test case to reflect behavioral changes made by the patch. sql/sp_head.cc: Reset the per-statement warning count before executing a stored procedure instruction. Move to a separate function code which checks the completion status of the executed statement and searches for a handler. Remove redundant code now that search for a handler is done after execution, errors are always pushed. sql/sp_pcontext.h: Remove unused code. sql/sp_rcontext.cc: - Polish sp_rcontext::find_handler(): use sp_rcontext::m_hfound instead of an extra local variable; - Remove sp_rcontext::handle_condition(); - Introduce sp_rcontext::activate_handler(), which prepares previously found handler for execution. - Move sp_rcontext::enter_handler() code into activate_handler(), because enter_handler() is used only from there; - Cleanups; - Introduce DBUG_EXECUTE_IF() for a test case in sp-code.test sql/sp_rcontext.h: - Remove unused code - Cleanups sql/sql_class.cc: Merge THD::raise_condition_no_handler() into THD::raise_condition(). After the patch raise_condition_no_handler() was called in raise_condition() only. sql/sql_class.h: Remove raise_condition_no_handler(). sql/sql_error.cc: Remove Warning_info::reserve_space() -- handled conditions are not cleared any more, so there is no need for RESIGNAL to re-push them. sql/sql_error.h: Remove Warning_info::reserve_space(). sql/sql_signal.cc: Handled conditions are not cleared any more, so there is no need for RESIGNAL to re-push them. --- mysql-test/r/signal.result | 41 ++- mysql-test/r/signal_demo3.result | 18 +- mysql-test/r/sp-big.result | 2 + mysql-test/r/sp-bugs.result | 2 + mysql-test/r/sp-code.result | 57 ++++ mysql-test/r/sp-error.result | 247 ++++++++++++++++ mysql-test/r/sp.result | 176 +++++++++++- mysql-test/r/sp_trans.result | 4 + mysql-test/r/strict.result | 2 + mysql-test/r/view.result | 2 + .../funcs_1/r/innodb_storedproc_02.result | 44 +++ .../funcs_1/r/memory_storedproc_02.result | 44 +++ .../funcs_1/r/myisam_storedproc_02.result | 44 +++ mysql-test/suite/funcs_1/r/storedproc.result | 76 +++++ mysql-test/suite/rpl/r/rpl_row_sp005.result | 2 + .../suite/rpl/r/rpl_row_sp006_InnoDB.result | 2 + mysql-test/suite/rpl/r/rpl_row_trig003.result | 6 + mysql-test/t/signal.test | 5 +- mysql-test/t/sp-code.test | 53 ++++ mysql-test/t/sp-error.test | 270 ++++++++++++++++++ mysql-test/t/sp.test | 35 ++- sql/sp_head.cc | 193 ++++++++----- sql/sp_pcontext.h | 7 - sql/sp_rcontext.cc | 241 ++++++++-------- sql/sp_rcontext.h | 73 ++--- sql/sql_class.cc | 30 +- sql/sql_class.h | 17 -- sql/sql_error.cc | 8 - sql/sql_error.h | 16 +- sql/sql_signal.cc | 12 - 30 files changed, 1385 insertions(+), 344 deletions(-) diff --git a/mysql-test/r/signal.result b/mysql-test/r/signal.result index 410abffcdf0..67bf9330451 100644 --- a/mysql-test/r/signal.result +++ b/mysql-test/r/signal.result @@ -1189,6 +1189,8 @@ end $$ call test_signal() $$ Caught by SQLSTATE Caught by SQLSTATE +Warnings: +Warning 1012 Raising a warning drop procedure test_signal $$ create procedure test_signal() begin @@ -1204,6 +1206,8 @@ end $$ call test_signal() $$ Caught by number Caught by number +Warnings: +Warning 1012 Raising a warning drop procedure test_signal $$ create procedure test_signal() begin @@ -1219,6 +1223,8 @@ end $$ call test_signal() $$ Caught by SQLWARNING Caught by SQLWARNING +Warnings: +Warning 1012 Raising a warning drop procedure test_signal $$ create procedure test_signal() begin @@ -1234,6 +1240,8 @@ end $$ call test_signal() $$ Caught by SQLSTATE Caught by SQLSTATE +Warnings: +Error 1012 Raising a not found drop procedure test_signal $$ create procedure test_signal() begin @@ -1249,6 +1257,8 @@ end $$ call test_signal() $$ Caught by number Caught by number +Warnings: +Error 1012 Raising a not found drop procedure test_signal $$ create procedure test_signal() begin @@ -1264,6 +1274,8 @@ end $$ call test_signal() $$ Caught by NOT FOUND Caught by NOT FOUND +Warnings: +Error 1012 Raising a not found drop procedure test_signal $$ create procedure test_signal() begin @@ -1279,6 +1291,8 @@ end $$ call test_signal() $$ Caught by SQLSTATE Caught by SQLSTATE +Warnings: +Error 1012 Raising an error drop procedure test_signal $$ create procedure test_signal() begin @@ -1294,6 +1308,8 @@ end $$ call test_signal() $$ Caught by number Caught by number +Warnings: +Error 1012 Raising an error drop procedure test_signal $$ create procedure test_signal() begin @@ -1309,6 +1325,8 @@ end $$ call test_signal() $$ Caught by SQLEXCEPTION Caught by SQLEXCEPTION +Warnings: +Error 1012 Raising an error drop procedure test_signal $$ # # Test where SIGNAL can be used @@ -1455,6 +1473,7 @@ after RESIGNAL after RESIGNAL Warnings: Warning 1012 Raising a warning +Warning 1012 Raising a warning drop procedure test_resignal $$ create procedure test_resignal() begin @@ -1509,6 +1528,7 @@ after RESIGNAL after RESIGNAL Warnings: Warning 1264 Out of range value for column 'a' at row 1 +Warning 1264 Out of range value for column 'a' at row 1 drop procedure test_resignal $$ create procedure test_resignal() begin @@ -1565,6 +1585,7 @@ before RESIGNAL after RESIGNAL after RESIGNAL Warnings: +Warning 1012 Raising a warning Warning 5555 RESIGNAL of a warning drop procedure test_resignal $$ create procedure test_resignal() @@ -1625,6 +1646,7 @@ before RESIGNAL after RESIGNAL after RESIGNAL Warnings: +Warning 1264 Out of range value for column 'a' at row 1 Warning 5555 RESIGNAL of a warning drop procedure test_resignal $$ create procedure test_resignal() @@ -2126,6 +2148,9 @@ CALL peter_p2() $$ ERROR 42000: Hi, I am a useless error message show warnings $$ Level Code Message +Error 1231 Variable 'sql_mode' can't be set to the value of 'NULL' +Error 1231 Variable 'sql_mode' can't be set to the value of 'NULL' +Error 9999 Variable 'sql_mode' can't be set to the value of 'NULL' Error 9999 Hi, I am a useless error message drop procedure peter_p1 $$ drop procedure peter_p2 $$ @@ -2135,15 +2160,17 @@ DECLARE x CONDITION FOR SQLSTATE '42000'; DECLARE EXIT HANDLER FOR x BEGIN SELECT '2'; +SHOW WARNINGS; RESIGNAL x SET MYSQL_ERRNO = 9999; END; BEGIN DECLARE EXIT HANDLER FOR x BEGIN SELECT '1'; +SHOW WARNINGS; RESIGNAL x SET SCHEMA_NAME = 'test', -MYSQL_ERRNO= 1231; +MYSQL_ERRNO= 1232; END; /* Raises ER_WRONG_VALUE_FOR_VAR : 1231, SQLSTATE 42000 */ SET @@sql_mode=NULL; @@ -2156,6 +2183,7 @@ DECLARE x CONDITION for SQLSTATE '42000'; DECLARE EXIT HANDLER FOR x BEGIN SELECT '3'; +SHOW WARNINGS; RESIGNAL x SET MESSAGE_TEXT = 'Hi, I am a useless error message', MYSQL_ERRNO = 9999; @@ -2166,15 +2194,24 @@ $$ CALL peter_p2() $$ 1 1 +Level Code Message +Error 1231 Variable 'sql_mode' can't be set to the value of 'NULL' 2 2 +Level Code Message +Error 1231 Variable 'sql_mode' can't be set to the value of 'NULL' +Error 1232 Variable 'sql_mode' can't be set to the value of 'NULL' 3 3 +Level Code Message +Error 1231 Variable 'sql_mode' can't be set to the value of 'NULL' +Error 1232 Variable 'sql_mode' can't be set to the value of 'NULL' +Error 9999 Variable 'sql_mode' can't be set to the value of 'NULL' ERROR 42000: Hi, I am a useless error message show warnings $$ Level Code Message Error 1231 Variable 'sql_mode' can't be set to the value of 'NULL' -Error 1231 Variable 'sql_mode' can't be set to the value of 'NULL' +Error 1232 Variable 'sql_mode' can't be set to the value of 'NULL' Error 9999 Variable 'sql_mode' can't be set to the value of 'NULL' Error 9999 Hi, I am a useless error message drop procedure peter_p1 $$ diff --git a/mysql-test/r/signal_demo3.result b/mysql-test/r/signal_demo3.result index aa769659e51..a89ce703d20 100644 --- a/mysql-test/r/signal_demo3.result +++ b/mysql-test/r/signal_demo3.result @@ -95,11 +95,11 @@ call proc_1(); ERROR 45000: Oops in proc_1 show warnings; Level Code Message -Error 1644 Oops in proc_5 -Error 1644 Oops in proc_4 -Error 1644 Oops in proc_3 -Error 1644 Oops in proc_2 -Error 1644 Oops in proc_1 +Error 1051 Unknown table 'oops_it_is_not_here' +Error 1644 Oops in proc_9 +Error 1644 Oops in proc_8 +Error 1644 Oops in proc_7 +Error 1644 Oops in proc_6 SET @@session.max_error_count = 7; SELECT @@session.max_error_count; @@session.max_error_count @@ -108,13 +108,13 @@ call proc_1(); ERROR 45000: Oops in proc_1 show warnings; Level Code Message +Error 1051 Unknown table 'oops_it_is_not_here' +Error 1644 Oops in proc_9 +Error 1644 Oops in proc_8 Error 1644 Oops in proc_7 Error 1644 Oops in proc_6 Error 1644 Oops in proc_5 Error 1644 Oops in proc_4 -Error 1644 Oops in proc_3 -Error 1644 Oops in proc_2 -Error 1644 Oops in proc_1 SET @@session.max_error_count = 9; SELECT @@session.max_error_count; @@session.max_error_count @@ -123,6 +123,7 @@ call proc_1(); ERROR 45000: Oops in proc_1 show warnings; Level Code Message +Error 1051 Unknown table 'oops_it_is_not_here' Error 1644 Oops in proc_9 Error 1644 Oops in proc_8 Error 1644 Oops in proc_7 @@ -131,7 +132,6 @@ Error 1644 Oops in proc_5 Error 1644 Oops in proc_4 Error 1644 Oops in proc_3 Error 1644 Oops in proc_2 -Error 1644 Oops in proc_1 drop database demo; SET @@global.max_error_count = @start_global_value; SELECT @@global.max_error_count; diff --git a/mysql-test/r/sp-big.result b/mysql-test/r/sp-big.result index 9765508859c..d28b7004330 100644 --- a/mysql-test/r/sp-big.result +++ b/mysql-test/r/sp-big.result @@ -46,6 +46,8 @@ end while; close cur1; end| call p1(); +Warnings: +Error 1329 No data - zero rows fetched, selected, or processed select count(*) from t1; count(*) 256 diff --git a/mysql-test/r/sp-bugs.result b/mysql-test/r/sp-bugs.result index 2374b433fba..a88c89537e2 100644 --- a/mysql-test/r/sp-bugs.result +++ b/mysql-test/r/sp-bugs.result @@ -43,6 +43,8 @@ END| SELECT f2 (); f2 () NULL +Warnings: +Error 1305 FUNCTION testdb.f_not_exists does not exist DROP SCHEMA testdb; USE test; # diff --git a/mysql-test/r/sp-code.result b/mysql-test/r/sp-code.result index 0a0f620b80a..c7ea4cbb311 100644 --- a/mysql-test/r/sp-code.result +++ b/mysql-test/r/sp-code.result @@ -711,6 +711,8 @@ looping i looping 1 looping i looping 0 +Warnings: +Error 1062 Duplicate entry '1' for key 'a' call proc_26977_works(2); do something do something @@ -730,6 +732,8 @@ looping i looping 0 optimizer: keep hreturn optimizer: keep hreturn +Warnings: +Error 1062 Duplicate entry '2' for key 'a' drop table t1; drop procedure proc_26977_broken; drop procedure proc_26977_works; @@ -888,3 +892,56 @@ Pos Instruction 4 jump 6 5 error 1339 DROP PROCEDURE p1; +# +# Bug#23032: Handlers declared in a SP do not handle warnings generated in sub-SP +# + +# - Case 4: check that "No Data trumps Warning". + +CREATE TABLE t1(a INT); +INSERT INTO t1 VALUES (1), (2), (3); +CREATE PROCEDURE p1() +BEGIN +DECLARE c CURSOR FOR SELECT a FROM t1; +OPEN c; +BEGIN +DECLARE v INT; +DECLARE CONTINUE HANDLER FOR SQLWARNING +BEGIN +SELECT "Warning found!"; +SHOW WARNINGS; +END; +DECLARE EXIT HANDLER FOR NOT FOUND +BEGIN +SELECT "End of Result Set found!"; +SHOW WARNINGS; +END; +WHILE TRUE DO +FETCH c INTO v; +END WHILE; +END; +CLOSE c; +SELECT a INTO @foo FROM t1 LIMIT 1; # Clear warning stack +END| +SET SESSION debug="+d,bug23032_emit_warning"; +CALL p1(); +Warning found! +Warning found! +Level Code Message +Warning 1105 Unknown error +Warning found! +Warning found! +Level Code Message +Warning 1105 Unknown error +Warning found! +Warning found! +Level Code Message +Warning 1105 Unknown error +End of Result Set found! +End of Result Set found! +Level Code Message +Warning 1105 Unknown error +Error 1329 No data - zero rows fetched, selected, or processed +SET SESSION debug="-d,bug23032_emit_warning"; +DROP PROCEDURE p1; +DROP TABLE t1; diff --git a/mysql-test/r/sp-error.result b/mysql-test/r/sp-error.result index 0f658ee831e..7b8364379df 100644 --- a/mysql-test/r/sp-error.result +++ b/mysql-test/r/sp-error.result @@ -1344,6 +1344,8 @@ set @in_func := 0; select func_20713_a(); func_20713_a() NULL +Warnings: +Error 1146 Table 'test.bogus_table_20713' doesn't exist select @in_func; @in_func 2 @@ -1351,6 +1353,8 @@ set @in_func := 0; select func_20713_b(); func_20713_b() NULL +Warnings: +Error 1146 Table 'test.bogus_table_20713' doesn't exist select @in_func; @in_func 2 @@ -1714,3 +1718,246 @@ DROP PROCEDURE p1; DROP VIEW v1; DROP TABLE t1; End of 5.1 tests +# +# Bug#23032: Handlers declared in a SP do not handle warnings generated in sub-SP +# + +# - Case 1 + +DROP PROCEDURE IF EXISTS p1; +DROP PROCEDURE IF EXISTS p2; +DROP PROCEDURE IF EXISTS p3; +DROP PROCEDURE IF EXISTS p4; +DROP PROCEDURE IF EXISTS p5; +DROP PROCEDURE IF EXISTS p6; +CREATE PROCEDURE p1() +BEGIN +SELECT CAST('10 ' as unsigned integer); +SELECT 1; +CALL p2(); +END| +CREATE PROCEDURE p2() +BEGIN +SELECT CAST('10 ' as unsigned integer); +END| +CALL p1(); +CAST('10 ' as unsigned integer) +10 +1 +1 +CAST('10 ' as unsigned integer) +10 +Warnings: +Warning 1292 Truncated incorrect INTEGER value: '10 ' +DROP PROCEDURE p1; +DROP PROCEDURE p2; + +# - Case 2 + +CREATE PROCEDURE p1() +BEGIN +DECLARE c INT DEFAULT 0; +DECLARE CONTINUE HANDLER FOR SQLWARNING SET c = c + 1; +CALL p2(); +CALL p3(); +CALL p4(); +SELECT c; +SELECT @@warning_count; +SHOW WARNINGS; +END| +CREATE PROCEDURE p2() +BEGIN +SELECT CAST('10 ' as unsigned integer); +END| +CREATE PROCEDURE p3() +BEGIN +SELECT CAST('10 ' as unsigned integer); +SELECT 1; +END| +CREATE PROCEDURE p4() +BEGIN +SELECT CAST('10 ' as unsigned integer); +CALL p2(); +END| +CREATE PROCEDURE p5() +BEGIN +SELECT CAST('10 ' as unsigned integer); +SHOW WARNINGS; +END| +CREATE PROCEDURE P6() +BEGIN +DECLARE c INT DEFAULT 0; +DECLARE CONTINUE HANDLER FOR SQLWARNING SET c = c + 1; +CALL p5(); +SELECT c; +END| +CALL p1(); +CAST('10 ' as unsigned integer) +10 +CAST('10 ' as unsigned integer) +10 +1 +1 +CAST('10 ' as unsigned integer) +10 +CAST('10 ' as unsigned integer) +10 +c +3 +@@warning_count +1 +Level Code Message +Warning 1292 Truncated incorrect INTEGER value: '10 ' +Warnings: +Warning 1292 Truncated incorrect INTEGER value: '10 ' +CALL p6(); +CAST('10 ' as unsigned integer) +10 +Level Code Message +Warning 1292 Truncated incorrect INTEGER value: '10 ' +c +1 +Warnings: +Warning 1292 Truncated incorrect INTEGER value: '10 ' +DROP PROCEDURE p1; +DROP PROCEDURE p2; +DROP PROCEDURE p3; +DROP PROCEDURE p4; +DROP PROCEDURE p5; +DROP PROCEDURE p6; + +# - Case 3: check that "Exception trumps No Data". + +DROP TABLE IF EXISTS t1; +CREATE TABLE t1(a INT); +INSERT INTO t1 VALUES (1), (2), (3); +CREATE PROCEDURE p1() +BEGIN +DECLARE c CURSOR FOR SELECT a FROM t1; +OPEN c; +BEGIN +DECLARE v1 INT; +DECLARE v2 INT; +DECLARE EXIT HANDLER FOR SQLEXCEPTION +SELECT "Error caught (expected)"; +DECLARE EXIT HANDLER FOR NOT FOUND +SELECT "End of Result Set found!"; +WHILE TRUE DO +FETCH c INTO v1, v2; +END WHILE; +END; +CLOSE c; +SELECT a INTO @foo FROM t1 LIMIT 1; # Clear warning stack +END| +CALL p1(); +Error caught (expected) +Error caught (expected) +DROP PROCEDURE p1; +DROP TABLE t1; +# +# Bug#36185: Incorrect precedence for warning and exception handlers +# +DROP TABLE IF EXISTS t1; +DROP PROCEDURE IF EXISTS p1; +CREATE TABLE t1 (a INT, b INT NOT NULL); +CREATE PROCEDURE p1() +BEGIN +DECLARE CONTINUE HANDLER FOR SQLWARNING SELECT 'warning'; +DECLARE CONTINUE HANDLER FOR SQLEXCEPTION SELECT 'exception'; +INSERT INTO t1 VALUES (CAST('10 ' AS SIGNED), NULL); +END| +CALL p1(); +exception +exception +Warnings: +Warning 1292 Truncated incorrect INTEGER value: '10 ' +Error 1048 Column 'b' cannot be null +DROP TABLE t1; +DROP PROCEDURE p1; +# +# Bug#5889: Exit handler for a warning doesn't hide the warning in trigger +# + +# - Case 1 + +CREATE TABLE t1(a INT, b INT); +INSERT INTO t1 VALUES (1, 2); +CREATE TRIGGER t1_bu BEFORE UPDATE ON t1 FOR EACH ROW +BEGIN +DECLARE EXIT HANDLER FOR SQLWARNING +SET NEW.a = 10; +SET NEW.a = 99999999999; +END| +UPDATE t1 SET b = 20; +Warnings: +Warning 1264 Out of range value for column 'a' at row 1 +SHOW WARNINGS; +Level Code Message +Warning 1264 Out of range value for column 'a' at row 1 +SELECT * FROM t1; +a b +10 20 +DROP TRIGGER t1_bu; +DROP TABLE t1; + +# - Case 2 + +CREATE TABLE t1(a INT); +CREATE TABLE t2(b CHAR(1)); +CREATE TRIGGER t1_bi BEFORE INSERT ON t1 FOR EACH ROW +BEGIN +INSERT INTO t2 VALUES('ab'); # Produces a warning. +INSERT INTO t2 VALUES('b'); # Does not produce a warning, +# previous warning should be cleared. +END| +INSERT INTO t1 VALUES(0); +SHOW WARNINGS; +Level Code Message +SELECT * FROM t1; +a +0 +SELECT * FROM t2; +b +a +b +DROP TRIGGER t1_bi; +DROP TABLE t1; +DROP TABLE t2; +# +# Bug#9857: Stored procedures: handler for sqlwarning ignored +# +SET @sql_mode_saved = @@sql_mode; +SET sql_mode = traditional; +CREATE PROCEDURE p1() +BEGIN +DECLARE CONTINUE HANDLER FOR SQLWARNING +SELECT 'warning caught (expected)'; +SELECT 5 / 0; +END| +CREATE PROCEDURE p2() +BEGIN +DECLARE CONTINUE HANDLER FOR SQLEXCEPTION +SELECT 'error caught (unexpected)'; +SELECT 5 / 0; +END| +CALL p1(); +5 / 0 +NULL +warning caught (expected) +warning caught (expected) +Warnings: +Warning 1365 Division by 0 +SHOW WARNINGS; +Level Code Message +Warning 1365 Division by 0 +CALL p2(); +5 / 0 +NULL +Warnings: +Warning 1365 Division by 0 +SHOW WARNINGS; +Level Code Message +Warning 1365 Division by 0 +DROP PROCEDURE p1; +DROP PROCEDURE p2; +SET sql_mode = @sql_mode_saved; diff --git a/mysql-test/r/sp.result b/mysql-test/r/sp.result index 76d4bf2dea0..243bfb6c07d 100644 --- a/mysql-test/r/sp.result +++ b/mysql-test/r/sp.result @@ -737,6 +737,8 @@ close c; end| insert into t2 values ("foo", 42, -1.9), ("bar", 3, 12.1), ("zap", 666, -3.14)| call cur1()| +Warnings: +Error 1329 No data - zero rows fetched, selected, or processed select * from t1| id data foo 40 @@ -772,6 +774,8 @@ close c1; close c2; end| call cur2()| +Warnings: +Error 1329 No data - zero rows fetched, selected, or processed select * from t3 order by i,s| s i bar 3 @@ -861,6 +865,8 @@ end$ set @@sql_mode = ''| set sql_select_limit = 1| call modes(@c1, @c2)| +Warnings: +Error 1329 No data - zero rows fetched, selected, or processed set sql_select_limit = default| select @c1, @c2| @c1 @c2 @@ -1682,42 +1688,64 @@ end| call h_ee()| h_ee Inner (good) +Warnings: +Error 1062 Duplicate entry '1' for key 'PRIMARY' call h_es()| h_es Outer (good) +Warnings: +Error 1062 Duplicate entry '1' for key 'PRIMARY' call h_en()| h_en Outer (good) +Warnings: +Warning 1329 No data - zero rows fetched, selected, or processed call h_ew()| h_ew Outer (good) call h_ex()| h_ex Outer (good) +Warnings: +Error 1062 Duplicate entry '1' for key 'PRIMARY' call h_se()| h_se Inner (good) +Warnings: +Error 1062 Duplicate entry '1' for key 'PRIMARY' call h_ss()| h_ss Inner (good) +Warnings: +Error 1062 Duplicate entry '1' for key 'PRIMARY' call h_sn()| h_sn Outer (good) +Warnings: +Warning 1329 No data - zero rows fetched, selected, or processed call h_sw()| h_sw Outer (good) call h_sx()| h_sx Outer (good) +Warnings: +Error 1062 Duplicate entry '1' for key 'PRIMARY' call h_ne()| h_ne Inner (good) +Warnings: +Warning 1329 No data - zero rows fetched, selected, or processed call h_ns()| h_ns Inner (good) +Warnings: +Warning 1329 No data - zero rows fetched, selected, or processed call h_nn()| h_nn Inner (good) +Warnings: +Warning 1329 No data - zero rows fetched, selected, or processed call h_we()| h_we Inner (good) @@ -1730,12 +1758,18 @@ Inner (good) call h_xe()| h_xe Inner (good) +Warnings: +Error 1062 Duplicate entry '1' for key 'PRIMARY' call h_xs()| h_xs Inner (good) +Warnings: +Error 1062 Duplicate entry '1' for key 'PRIMARY' call h_xx()| h_xx Inner (good) +Warnings: +Error 1062 Duplicate entry '1' for key 'PRIMARY' drop table t3| drop procedure h_ee| drop procedure h_es| @@ -1884,6 +1918,8 @@ set @x2 = 2; close c1; end| call bug2260()| +Warnings: +Error 1329 No data - zero rows fetched, selected, or processed select @x2| @x2 2 @@ -2027,6 +2063,8 @@ insert into t3 values (123456789012); insert into t3 values (0); end| call bug2780()| +Warnings: +Warning 1264 Out of range value for column 's1' at row 1 select @x| @x 1 @@ -2449,6 +2487,8 @@ declare continue handler for sqlstate 'HY000' begin end; select s1 from t3 union select s2 from t3; end| call bug4904()| +Warnings: +Error 1267 Illegal mix of collations (latin1_swedish_ci,IMPLICIT) and (latin2_general_ci,IMPLICIT) for operation 'UNION' drop procedure bug4904| drop table t3| drop procedure if exists bug336| @@ -2588,13 +2628,17 @@ select row_count()| row_count() 1 call bug4905()| +Warnings: +Error 1062 Duplicate entry '1' for key 'PRIMARY' select row_count()| row_count() -0 +-1 call bug4905()| +Warnings: +Error 1062 Duplicate entry '1' for key 'PRIMARY' select row_count()| row_count() -0 +-1 select * from t3| s1 1 @@ -2615,10 +2659,14 @@ insert into t3 values (1)| call bug6029()| sqlstate 23000 sqlstate 23000 +Warnings: +Error 1062 Duplicate entry '1' for key 'PRIMARY' delete from t3| call bug6029()| 1136 1136 +Warnings: +Error 1136 Column count doesn't match value count at row 1 drop procedure bug6029| drop table t3| drop procedure if exists bug8540| @@ -2910,15 +2958,23 @@ end| call bug6900()| 2 2 +Warnings: +Error 1136 Column count doesn't match value count at row 1 call bug9074()| x1 x2 x3 x4 x5 x6 1 1 1 1 1 1 +Warnings: +Error 1062 Duplicate entry 'a' for key 'w' call bug6900_9074(0)| sqlexception sqlexception +Warnings: +Error 1136 Column count doesn't match value count at row 1 call bug6900_9074(1)| 23000 23000 +Warnings: +Error 1062 Duplicate entry 'a' for key 'w' drop procedure bug6900| drop procedure bug9074| drop procedure bug6900_9074| @@ -2961,9 +3017,13 @@ delete from t1| call bug9856()| 16 16 +Warnings: +Error 1329 No data - zero rows fetched, selected, or processed call bug9856()| 16 16 +Warnings: +Error 1329 No data - zero rows fetched, selected, or processed drop procedure bug9856| drop procedure if exists bug9674_1| drop procedure if exists bug9674_2| @@ -3194,6 +3254,8 @@ x 2 x 3 +Warnings: +Error 1326 Cursor is not open call bug10961()| x 1 @@ -3201,6 +3263,8 @@ x 2 x 3 +Warnings: +Error 1326 Cursor is not open drop procedure bug10961| DROP PROCEDURE IF EXISTS bug6866| DROP VIEW IF EXISTS tv| @@ -3316,7 +3380,11 @@ insert into t1 values ('Name4', 13), ('Name5', 14)| call bug11529()| +Warnings: +Error 1329 No data - zero rows fetched, selected, or processed call bug11529()| +Warnings: +Error 1329 No data - zero rows fetched, selected, or processed delete from t1| drop procedure bug11529| set character set utf8| @@ -3490,24 +3558,32 @@ end; end if; end| call bug12168('a')| +Warnings: +Error 1329 No data - zero rows fetched, selected, or processed select * from t4| a 1 3 truncate t4| call bug12168('b')| +Warnings: +Error 1329 No data - zero rows fetched, selected, or processed select * from t4| a 2 4 truncate t4| call bug12168('a')| +Warnings: +Error 1329 No data - zero rows fetched, selected, or processed select * from t4| a 1 3 truncate t4| call bug12168('b')| +Warnings: +Error 1329 No data - zero rows fetched, selected, or processed select * from t4| a 2 @@ -3807,6 +3883,8 @@ end| call bug7049_2()| Result Caught it +Warnings: +Error 1062 Duplicate entry '42' for key 'x' select * from t3| x 42 @@ -3814,12 +3892,16 @@ delete from t3| call bug7049_4()| Result Caught it +Warnings: +Error 1062 Duplicate entry '42' for key 'x' select * from t3| x 42 select bug7049_2()| bug7049_2() 1 +Warnings: +Error 1062 Duplicate entry '42' for key 'x' drop table t3| drop procedure bug7049_1| drop procedure bug7049_2| @@ -3947,6 +4029,8 @@ end| call bug14845()| a 0 +Warnings: +Error 1329 No data - zero rows fetched, selected, or processed drop procedure bug14845| drop procedure if exists bug13549_1| drop procedure if exists bug13549_2| @@ -4150,6 +4234,8 @@ end| call bug13729()| 55 55 +Warnings: +Error 1062 Duplicate entry '1' for key 'PRIMARY' select * from t3| s1 1 @@ -4186,11 +4272,15 @@ Handler boo v isnull(v) NULL 1 +Warnings: +Error 1054 Unknown column 'undefined_var' in 'field list' call bug14643_2()| Handler boo Handler boo +Warnings: +Error 1054 Unknown column 'undefined_var' in 'field list' drop procedure bug14643_1| drop procedure bug14643_2| drop procedure if exists bug14304| @@ -4514,11 +4604,15 @@ Handler error End done +Warnings: +Error 1054 Unknown column 'v' in 'field list' call bug14498_2()| Handler error End done +Warnings: +Error 1054 Unknown column 'v' in 'field list' call bug14498_3()| v maybe @@ -4526,16 +4620,22 @@ Handler error End done +Warnings: +Error 1054 Unknown column 'v' in 'field list' call bug14498_4()| Handler error End done +Warnings: +Error 1054 Unknown column 'v' in 'field list' call bug14498_5()| Handler error End done +Warnings: +Error 1054 Unknown column 'v' in 'field list' drop procedure bug14498_1| drop procedure bug14498_2| drop procedure bug14498_3| @@ -4546,6 +4646,8 @@ drop procedure if exists bug15231_1| drop procedure if exists bug15231_2| drop procedure if exists bug15231_3| drop procedure if exists bug15231_4| +drop procedure if exists bug15231_5| +drop procedure if exists bug15231_6| create table t3 (id int not null)| create procedure bug15231_1() begin @@ -4568,7 +4670,7 @@ end| create procedure bug15231_3() begin declare exit handler for sqlwarning -select 'Caught it (wrong)' as 'Result'; +select 'Caught it (correct)' as 'Result'; call bug15231_4(); end| create procedure bug15231_4() @@ -4576,6 +4678,20 @@ begin declare x decimal(2,1); set x = 'zap'; select 'Missed it (correct)' as 'Result'; +show warnings; +end| +create procedure bug15231_5() +begin +declare exit handler for sqlwarning +select 'Caught it (wrong)' as 'Result'; +call bug15231_6(); +end| +create procedure bug15231_6() +begin +declare x decimal(2,1); +set x = 'zap'; +select 'Missed it (correct)' as 'Result'; +select id from t3; end| call bug15231_1()| 1 @@ -4583,19 +4699,29 @@ Before NOT FOUND condition is triggered 2 After NOT FOUND condtition is triggered xid xdone -1 0 +1 1 Warnings: Warning 1329 No data - zero rows fetched, selected, or processed call bug15231_3()| Result Missed it (correct) +Level Code Message +Warning 1366 Incorrect decimal value: 'zap' for column 'x' at row 1 +Result +Caught it (correct) Warnings: Warning 1366 Incorrect decimal value: 'zap' for column 'x' at row 1 -drop table if exists t3| -drop procedure if exists bug15231_1| -drop procedure if exists bug15231_2| -drop procedure if exists bug15231_3| -drop procedure if exists bug15231_4| +call bug15231_5()| +Result +Missed it (correct) +id +drop table t3| +drop procedure bug15231_1| +drop procedure bug15231_2| +drop procedure bug15231_3| +drop procedure bug15231_4| +drop procedure bug15231_5| +drop procedure bug15231_6| drop procedure if exists bug15011| create table t3 (c1 int primary key)| insert into t3 values (1)| @@ -4613,6 +4739,8 @@ end| call bug15011()| Handler Inner +Warnings: +Error 1062 Duplicate entry '1' for key 'PRIMARY' drop procedure bug15011| drop table t3| drop procedure if exists bug17476| @@ -4688,6 +4816,8 @@ i 1 i 0 +Warnings: +Error 1329 No data - zero rows fetched, selected, or processed drop table t3| drop procedure bug16887| drop procedure if exists bug16474_1| @@ -4760,6 +4890,8 @@ declare continue handler for sqlexception begin end; select no_such_function(); end| call bug18787()| +Warnings: +Error 1305 FUNCTION test.no_such_function does not exist drop procedure bug18787| create database bug18344_012345678901| use bug18344_012345678901| @@ -5133,6 +5265,8 @@ statement failed statement failed statement after update statement after update +Warnings: +Error 1242 Subquery returns more than 1 row select * from t3| a 1 @@ -5144,6 +5278,8 @@ statement failed statement failed statement after update statement after update +Warnings: +Error 1242 Subquery returns more than 1 row select * from t3| a 1 @@ -5176,6 +5312,8 @@ in continue handler in continue handler reachable code a2 reachable code a2 +Warnings: +Error 1242 Subquery returns more than 1 row select * from t3| a 1 @@ -5191,6 +5329,8 @@ in continue handler in continue handler reachable code a2 reachable code a2 +Warnings: +Error 1242 Subquery returns more than 1 row select * from t3| a 1 @@ -5224,6 +5364,8 @@ in continue handler in continue handler reachable code a2 reachable code a2 +Warnings: +Error 1305 FUNCTION test.no_such_function does not exist drop procedure bug8153_proc_a| drop procedure bug8153_proc_b| drop table t3| @@ -5792,9 +5934,13 @@ end| select func_8407_a()| func_8407_a() NULL +Warnings: +Error 1146 Table 'test.no_such_view' doesn't exist select func_8407_b()| func_8407_b() 1500 +Warnings: +Error 1146 Table 'test.no_such_view' doesn't exist drop function func_8407_a| drop function func_8407_b| drop table if exists table_26503| @@ -5916,6 +6062,8 @@ looping i looping 0 leaving handler leaving handler +Warnings: +Error 1062 Duplicate entry '1' for key 'a' call proc_26503_ok_2(2)| do something do something @@ -5927,6 +6075,8 @@ looping i looping 4 leaving handler leaving handler +Warnings: +Error 1062 Duplicate entry '2' for key 'a' call proc_26503_ok_3(3)| do something do something @@ -5946,6 +6096,8 @@ looping i looping 0 leaving handler leaving handler +Warnings: +Error 1062 Duplicate entry '3' for key 'a' call proc_26503_ok_4(4)| do something do something @@ -5957,6 +6109,8 @@ looping i looping 4 leaving handler leaving handler +Warnings: +Error 1062 Duplicate entry '4' for key 'a' drop table table_26503| drop procedure proc_26503_ok_1| drop procedure proc_26503_ok_2| @@ -6670,6 +6824,8 @@ DECLARE CONTINUE HANDLER FOR SQLEXCEPTION SET @exception:= 'run'; SELECT x FROM t1; END| CALL bug29770(); +Warnings: +Error 1054 Unknown column 'x' in 'field list' SELECT @state, @exception; @state @exception run NULL @@ -6708,6 +6864,8 @@ end; end while; end// call proc_33618(20); +Warnings: +Error 1329 No data - zero rows fetched, selected, or processed drop table t_33618; drop procedure proc_33618; # diff --git a/mysql-test/r/sp_trans.result b/mysql-test/r/sp_trans.result index f55e535a293..4fa91121f50 100644 --- a/mysql-test/r/sp_trans.result +++ b/mysql-test/r/sp_trans.result @@ -99,6 +99,8 @@ return i; end| set @error_in_func:= 0| insert into t1 values (bug10015_6(5)), (bug10015_6(6))| +Warnings: +Error 1062 Duplicate entry '1' for key 'PRIMARY' select @error_in_func| @error_in_func 1 @@ -524,6 +526,8 @@ until done end repeat; close c; end| call bug14210()| +Warnings: +Error 1329 No data - zero rows fetched, selected, or processed select count(*) from t4| count(*) 256 diff --git a/mysql-test/r/strict.result b/mysql-test/r/strict.result index 4f259fc4d7d..79f8c20a150 100644 --- a/mysql-test/r/strict.result +++ b/mysql-test/r/strict.result @@ -1190,6 +1190,8 @@ select'a'; insert into t1 values (200); end;| call t1(); a a +Warnings: +Error 1264 Out of range value for column 'col1' at row 1 select * from t1; col1 drop procedure t1; diff --git a/mysql-test/r/view.result b/mysql-test/r/view.result index 96b45f0d5bb..777ac9c258f 100644 --- a/mysql-test/r/view.result +++ b/mysql-test/r/view.result @@ -3946,6 +3946,8 @@ create view a as select 1; end| call p(); call p(); +Warnings: +Error 1050 Table 'a' already exists drop view a; drop procedure p; # diff --git a/mysql-test/suite/funcs_1/r/innodb_storedproc_02.result b/mysql-test/suite/funcs_1/r/innodb_storedproc_02.result index 3e2d084aa0c..2bc9a75a13e 100644 --- a/mysql-test/suite/funcs_1/r/innodb_storedproc_02.result +++ b/mysql-test/suite/funcs_1/r/innodb_storedproc_02.result @@ -347,6 +347,8 @@ CALL h1(); -7- 1 1 1 1 1 1 END x1 x2 x3 x4 x5 x6 END 1 1 1 1 1 1 +Warnings: +Error 1062 Duplicate entry 'a' for key 'w' DROP TABLE IF EXISTS tnull; DROP PROCEDURE IF EXISTS sp1; CREATE TABLE tnull(f1 int); @@ -445,6 +447,8 @@ END// CALL h2(); x1 x2 x3 x4 x5 x6 1 1 1 1 1 1 +Warnings: +Error 1062 Duplicate entry 'a' for key 'w' SELECT * FROM res_t1; w x a b @@ -550,6 +554,8 @@ exit handler 2 exit handler 2 exit handler 1 exit handler 1 +Warnings: +Error 1146 Table 'db_storedproc.tqq' doesn't exist create table res_t1(w char unique, x char); insert into res_t1 values ('a', 'b'); CREATE PROCEDURE h1 () @@ -580,6 +586,8 @@ END// CALL h1(); x1 x2 x3 x4 x5 x6 1 1 1 1 1 1 +Warnings: +Error 1062 Duplicate entry 'a' for key 'w' This will fail, SQLSTATE 00000 is not allowed CREATE PROCEDURE sp1() begin1_label:BEGIN @@ -623,6 +631,8 @@ CALL sp2(); NULL @x2 @x 1 2 +Warnings: +Error 1318 Incorrect number of arguments for PROCEDURE db_storedproc.sp1; expected 2, got 1 DROP PROCEDURE sp1; DROP PROCEDURE sp2; @@ -654,6 +664,8 @@ ERROR 42000: Incorrect number of arguments for PROCEDURE db_storedproc.sp1; expe CALL sp2(); -1- @x2 @x -1- 0 1 +Warnings: +Error 1318 Incorrect number of arguments for PROCEDURE db_storedproc.sp1; expected 2, got 1 SELECT '-3-', @x2, @x; -3- @x2 @x -3- 1 1 @@ -696,6 +708,8 @@ CALL sp2(); -2- 1 20 -4- @x2 @x -4- 11 22 +Warnings: +Error 1318 Incorrect number of arguments for PROCEDURE db_storedproc.sp1; expected 2, got 1 DROP PROCEDURE sp1; DROP PROCEDURE sp2; @@ -762,21 +776,33 @@ SELECT @done, @x; 0 1 INSERT INTO temp VALUES('1', NULL); CALL sp1(); +Warnings: +Warning 1265 Data truncated for column 'f1' at row 1 +Warning 1265 Data truncated for column 'f2' at row 1 SELECT @done, @x; @done @x 1 1 INSERT INTO temp VALUES('2', NULL); CALL sp2(); +Warnings: +Warning 1265 Data truncated for column 'f1' at row 1 +Warning 1265 Data truncated for column 'f2' at row 1 SELECT @done, @x; @done @x 1 1 INSERT INTO temp VALUES('3', NULL); CALL sp3(); +Warnings: +Warning 1265 Data truncated for column 'f1' at row 1 +Warning 1265 Data truncated for column 'f2' at row 1 SELECT @done, @x; @done @x 1 0 INSERT INTO temp VALUES('4', NULL); CALL sp4(); +Warnings: +Warning 1265 Data truncated for column 'f1' at row 1 +Warning 1265 Data truncated for column 'f2' at row 1 SELECT @done, @x; @done @x 1 0 @@ -885,18 +911,26 @@ SELECT @done, @x; @done @x 0 1 CALL sp1(); +Warnings: +Error 1329 No data - zero rows fetched, selected, or processed SELECT @done, @x; @done @x 1 2 CALL sp2(); +Warnings: +Error 1329 No data - zero rows fetched, selected, or processed SELECT @done, @x; @done @x 1 2 CALL sp3(); +Warnings: +Error 1329 No data - zero rows fetched, selected, or processed SELECT @done, @x; @done @x 1 1 CALL sp4(); +Warnings: +Error 1329 No data - zero rows fetched, selected, or processed SELECT @done, @x; @done @x 1 1 @@ -1031,6 +1065,8 @@ SQLSTATE 21000 SQLSTATE 24000 +Warnings: +Error 1326 Cursor is not open SELECT '-1-', @x; -1- @x -1- 6 @@ -1041,18 +1077,24 @@ SQLSTATE SQLEXCEPTION SQLSTATE 24000 +Warnings: +Error 1326 Cursor is not open SELECT '-2-', @x; -2- @x -2- 6 CALL sp3(); SQLSTATE 20000 +Warnings: +Error 1339 Case not found for CASE statement SELECT '-3-', @x; -3- @x -3- 1 CALL sp4(); SQLSTATE SQLEXCEPTION +Warnings: +Error 1339 Case not found for CASE statement SELECT '-4-', @x; -4- @x -4- 1 @@ -1335,6 +1377,8 @@ CLOSE cur1; CLOSE cur2; END// CALL sp_outer(); +Warnings: +Error 1329 No data - zero rows fetched, selected, or processed SELECT * FROM temp1; f0 cnt f1 f2 f3 f4 _sp_out_ 1 a` a` 1000-01-01 -5000 diff --git a/mysql-test/suite/funcs_1/r/memory_storedproc_02.result b/mysql-test/suite/funcs_1/r/memory_storedproc_02.result index 16dde71400e..f18678e3896 100644 --- a/mysql-test/suite/funcs_1/r/memory_storedproc_02.result +++ b/mysql-test/suite/funcs_1/r/memory_storedproc_02.result @@ -348,6 +348,8 @@ CALL h1(); -7- 1 1 1 1 1 1 END x1 x2 x3 x4 x5 x6 END 1 1 1 1 1 1 +Warnings: +Error 1062 Duplicate entry 'a' for key 'w' DROP TABLE IF EXISTS tnull; DROP PROCEDURE IF EXISTS sp1; CREATE TABLE tnull(f1 int); @@ -446,6 +448,8 @@ END// CALL h2(); x1 x2 x3 x4 x5 x6 1 1 1 1 1 1 +Warnings: +Error 1062 Duplicate entry 'a' for key 'w' SELECT * FROM res_t1; w x a b @@ -551,6 +555,8 @@ exit handler 2 exit handler 2 exit handler 1 exit handler 1 +Warnings: +Error 1146 Table 'db_storedproc.tqq' doesn't exist create table res_t1(w char unique, x char); insert into res_t1 values ('a', 'b'); CREATE PROCEDURE h1 () @@ -581,6 +587,8 @@ END// CALL h1(); x1 x2 x3 x4 x5 x6 1 1 1 1 1 1 +Warnings: +Error 1062 Duplicate entry 'a' for key 'w' This will fail, SQLSTATE 00000 is not allowed CREATE PROCEDURE sp1() begin1_label:BEGIN @@ -624,6 +632,8 @@ CALL sp2(); NULL @x2 @x 1 2 +Warnings: +Error 1318 Incorrect number of arguments for PROCEDURE db_storedproc.sp1; expected 2, got 1 DROP PROCEDURE sp1; DROP PROCEDURE sp2; @@ -655,6 +665,8 @@ ERROR 42000: Incorrect number of arguments for PROCEDURE db_storedproc.sp1; expe CALL sp2(); -1- @x2 @x -1- 0 1 +Warnings: +Error 1318 Incorrect number of arguments for PROCEDURE db_storedproc.sp1; expected 2, got 1 SELECT '-3-', @x2, @x; -3- @x2 @x -3- 1 1 @@ -697,6 +709,8 @@ CALL sp2(); -2- 1 20 -4- @x2 @x -4- 11 22 +Warnings: +Error 1318 Incorrect number of arguments for PROCEDURE db_storedproc.sp1; expected 2, got 1 DROP PROCEDURE sp1; DROP PROCEDURE sp2; @@ -763,21 +777,33 @@ SELECT @done, @x; 0 1 INSERT INTO temp VALUES('1', NULL); CALL sp1(); +Warnings: +Warning 1265 Data truncated for column 'f1' at row 1 +Warning 1265 Data truncated for column 'f2' at row 1 SELECT @done, @x; @done @x 1 1 INSERT INTO temp VALUES('2', NULL); CALL sp2(); +Warnings: +Warning 1265 Data truncated for column 'f1' at row 1 +Warning 1265 Data truncated for column 'f2' at row 1 SELECT @done, @x; @done @x 1 1 INSERT INTO temp VALUES('3', NULL); CALL sp3(); +Warnings: +Warning 1265 Data truncated for column 'f1' at row 1 +Warning 1265 Data truncated for column 'f2' at row 1 SELECT @done, @x; @done @x 1 0 INSERT INTO temp VALUES('4', NULL); CALL sp4(); +Warnings: +Warning 1265 Data truncated for column 'f1' at row 1 +Warning 1265 Data truncated for column 'f2' at row 1 SELECT @done, @x; @done @x 1 0 @@ -886,18 +912,26 @@ SELECT @done, @x; @done @x 0 1 CALL sp1(); +Warnings: +Error 1329 No data - zero rows fetched, selected, or processed SELECT @done, @x; @done @x 1 2 CALL sp2(); +Warnings: +Error 1329 No data - zero rows fetched, selected, or processed SELECT @done, @x; @done @x 1 2 CALL sp3(); +Warnings: +Error 1329 No data - zero rows fetched, selected, or processed SELECT @done, @x; @done @x 1 1 CALL sp4(); +Warnings: +Error 1329 No data - zero rows fetched, selected, or processed SELECT @done, @x; @done @x 1 1 @@ -1032,6 +1066,8 @@ SQLSTATE 21000 SQLSTATE 24000 +Warnings: +Error 1326 Cursor is not open SELECT '-1-', @x; -1- @x -1- 6 @@ -1042,18 +1078,24 @@ SQLSTATE SQLEXCEPTION SQLSTATE 24000 +Warnings: +Error 1326 Cursor is not open SELECT '-2-', @x; -2- @x -2- 6 CALL sp3(); SQLSTATE 20000 +Warnings: +Error 1339 Case not found for CASE statement SELECT '-3-', @x; -3- @x -3- 1 CALL sp4(); SQLSTATE SQLEXCEPTION +Warnings: +Error 1339 Case not found for CASE statement SELECT '-4-', @x; -4- @x -4- 1 @@ -1336,6 +1378,8 @@ CLOSE cur1; CLOSE cur2; END// CALL sp_outer(); +Warnings: +Error 1329 No data - zero rows fetched, selected, or processed SELECT * FROM temp1; f0 cnt f1 f2 f3 f4 _sp_out_ 1 a` a` 1000-01-01 -5000 diff --git a/mysql-test/suite/funcs_1/r/myisam_storedproc_02.result b/mysql-test/suite/funcs_1/r/myisam_storedproc_02.result index 16dde71400e..f18678e3896 100644 --- a/mysql-test/suite/funcs_1/r/myisam_storedproc_02.result +++ b/mysql-test/suite/funcs_1/r/myisam_storedproc_02.result @@ -348,6 +348,8 @@ CALL h1(); -7- 1 1 1 1 1 1 END x1 x2 x3 x4 x5 x6 END 1 1 1 1 1 1 +Warnings: +Error 1062 Duplicate entry 'a' for key 'w' DROP TABLE IF EXISTS tnull; DROP PROCEDURE IF EXISTS sp1; CREATE TABLE tnull(f1 int); @@ -446,6 +448,8 @@ END// CALL h2(); x1 x2 x3 x4 x5 x6 1 1 1 1 1 1 +Warnings: +Error 1062 Duplicate entry 'a' for key 'w' SELECT * FROM res_t1; w x a b @@ -551,6 +555,8 @@ exit handler 2 exit handler 2 exit handler 1 exit handler 1 +Warnings: +Error 1146 Table 'db_storedproc.tqq' doesn't exist create table res_t1(w char unique, x char); insert into res_t1 values ('a', 'b'); CREATE PROCEDURE h1 () @@ -581,6 +587,8 @@ END// CALL h1(); x1 x2 x3 x4 x5 x6 1 1 1 1 1 1 +Warnings: +Error 1062 Duplicate entry 'a' for key 'w' This will fail, SQLSTATE 00000 is not allowed CREATE PROCEDURE sp1() begin1_label:BEGIN @@ -624,6 +632,8 @@ CALL sp2(); NULL @x2 @x 1 2 +Warnings: +Error 1318 Incorrect number of arguments for PROCEDURE db_storedproc.sp1; expected 2, got 1 DROP PROCEDURE sp1; DROP PROCEDURE sp2; @@ -655,6 +665,8 @@ ERROR 42000: Incorrect number of arguments for PROCEDURE db_storedproc.sp1; expe CALL sp2(); -1- @x2 @x -1- 0 1 +Warnings: +Error 1318 Incorrect number of arguments for PROCEDURE db_storedproc.sp1; expected 2, got 1 SELECT '-3-', @x2, @x; -3- @x2 @x -3- 1 1 @@ -697,6 +709,8 @@ CALL sp2(); -2- 1 20 -4- @x2 @x -4- 11 22 +Warnings: +Error 1318 Incorrect number of arguments for PROCEDURE db_storedproc.sp1; expected 2, got 1 DROP PROCEDURE sp1; DROP PROCEDURE sp2; @@ -763,21 +777,33 @@ SELECT @done, @x; 0 1 INSERT INTO temp VALUES('1', NULL); CALL sp1(); +Warnings: +Warning 1265 Data truncated for column 'f1' at row 1 +Warning 1265 Data truncated for column 'f2' at row 1 SELECT @done, @x; @done @x 1 1 INSERT INTO temp VALUES('2', NULL); CALL sp2(); +Warnings: +Warning 1265 Data truncated for column 'f1' at row 1 +Warning 1265 Data truncated for column 'f2' at row 1 SELECT @done, @x; @done @x 1 1 INSERT INTO temp VALUES('3', NULL); CALL sp3(); +Warnings: +Warning 1265 Data truncated for column 'f1' at row 1 +Warning 1265 Data truncated for column 'f2' at row 1 SELECT @done, @x; @done @x 1 0 INSERT INTO temp VALUES('4', NULL); CALL sp4(); +Warnings: +Warning 1265 Data truncated for column 'f1' at row 1 +Warning 1265 Data truncated for column 'f2' at row 1 SELECT @done, @x; @done @x 1 0 @@ -886,18 +912,26 @@ SELECT @done, @x; @done @x 0 1 CALL sp1(); +Warnings: +Error 1329 No data - zero rows fetched, selected, or processed SELECT @done, @x; @done @x 1 2 CALL sp2(); +Warnings: +Error 1329 No data - zero rows fetched, selected, or processed SELECT @done, @x; @done @x 1 2 CALL sp3(); +Warnings: +Error 1329 No data - zero rows fetched, selected, or processed SELECT @done, @x; @done @x 1 1 CALL sp4(); +Warnings: +Error 1329 No data - zero rows fetched, selected, or processed SELECT @done, @x; @done @x 1 1 @@ -1032,6 +1066,8 @@ SQLSTATE 21000 SQLSTATE 24000 +Warnings: +Error 1326 Cursor is not open SELECT '-1-', @x; -1- @x -1- 6 @@ -1042,18 +1078,24 @@ SQLSTATE SQLEXCEPTION SQLSTATE 24000 +Warnings: +Error 1326 Cursor is not open SELECT '-2-', @x; -2- @x -2- 6 CALL sp3(); SQLSTATE 20000 +Warnings: +Error 1339 Case not found for CASE statement SELECT '-3-', @x; -3- @x -3- 1 CALL sp4(); SQLSTATE SQLEXCEPTION +Warnings: +Error 1339 Case not found for CASE statement SELECT '-4-', @x; -4- @x -4- 1 @@ -1336,6 +1378,8 @@ CLOSE cur1; CLOSE cur2; END// CALL sp_outer(); +Warnings: +Error 1329 No data - zero rows fetched, selected, or processed SELECT * FROM temp1; f0 cnt f1 f2 f3 f4 _sp_out_ 1 a` a` 1000-01-01 -5000 diff --git a/mysql-test/suite/funcs_1/r/storedproc.result b/mysql-test/suite/funcs_1/r/storedproc.result index 082da9938f7..bdb3b285189 100644 --- a/mysql-test/suite/funcs_1/r/storedproc.result +++ b/mysql-test/suite/funcs_1/r/storedproc.result @@ -9325,6 +9325,8 @@ insert into t2 values (1); set @x = 3; END// CALL sp1(); +Warnings: +Error 1136 Column count doesn't match value count at row 1 DROP PROCEDURE sp1; DROP PROCEDURE IF EXISTS sp1; Warnings: @@ -13754,6 +13756,8 @@ END// CALL sp1(); x y @x NULL a 3 +Warnings: +Error 1305 PROCEDURE db_storedproc.nonsexist does not exist SELECT @v1, @v2; @v1 @v2 4 a @@ -14938,6 +14942,8 @@ NULL NULL NULL NULL @x @y NULL NULL +Warnings: +Error 1329 No data - zero rows fetched, selected, or processed DROP PROCEDURE sp1; Testcase 4.2.63: @@ -15097,6 +15103,8 @@ END; fetch cur1 into newf1, newf2, newf4, newf3; END// CALL sp1(); +Warnings: +Error 1329 No data - zero rows fetched, selected, or processed DROP PROCEDURE sp1; Testcase 4.2.70: @@ -22447,6 +22455,8 @@ END// CALL h1 (); @x @x2 1 1 +Warnings: +Error 1318 Incorrect number of arguments for PROCEDURE db_storedproc.sp1; expected 2, got 1 DROP PROCEDURE h1; DROP PROCEDURE sp1; @@ -22464,6 +22474,8 @@ END// CALL h1 (); @x @x2 1 1 +Warnings: +Error 1305 PROCEDURE db_storedproc.sp1 does not exist DROP PROCEDURE h1; Testcase 4.11.3: @@ -22483,6 +22495,8 @@ CALL sp1 (1); set @x=0; END// CALL h1(); +Warnings: +Error 1318 Incorrect number of arguments for PROCEDURE db_storedproc.sp1; expected 2, got 1 SELECT @x, @x2; @x @x2 1 1 @@ -22501,6 +22515,8 @@ CALL sp1 (1); set @x=0; END// CALL h1 (); +Warnings: +Error 1305 PROCEDURE db_storedproc.sp1 does not exist SELECT @x, @x2; @x @x2 1 1 @@ -22525,6 +22541,8 @@ END// CALL h1 (); @x @x2 1 1 +Warnings: +Error 1318 Incorrect number of arguments for PROCEDURE db_storedproc.sp1; expected 2, got 1 DROP PROCEDURE h1; DROP PROCEDURE sp1; @@ -22547,6 +22565,8 @@ END// CALL h1 (); @x @x2 1 1 +Warnings: +Error 1318 Incorrect number of arguments for PROCEDURE db_storedproc.sp1; expected 2, got 1 DROP PROCEDURE h1; DROP PROCEDURE sp1; @@ -22569,6 +22589,8 @@ END// CALL h1 (); @x @x2 1 1 +Warnings: +Error 1318 Incorrect number of arguments for PROCEDURE db_storedproc.sp1; expected 2, got 1 DROP PROCEDURE h1; DROP PROCEDURE sp1; @@ -22586,6 +22608,8 @@ END// CALL h1 (); @x @x2 1 1 +Warnings: +Error 1305 PROCEDURE db_storedproc.sp1 does not exist DROP PROCEDURE h1; Testcase 4.11.9: @@ -22605,6 +22629,8 @@ CALL sp1 (1); set @x=0; END// CALL h1(); +Warnings: +Error 1318 Incorrect number of arguments for PROCEDURE db_storedproc.sp1; expected 2, got 1 SELECT @x, @x2; @x @x2 1 1 @@ -22623,6 +22649,8 @@ CALL sp1 (1); set @x=0; END// CALL h1 (); +Warnings: +Error 1305 PROCEDURE db_storedproc.sp1 does not exist SELECT @x, @x2; @x @x2 1 1 @@ -22647,6 +22675,8 @@ END// CALL h1 (); @x @x2 1 1 +Warnings: +Error 1318 Incorrect number of arguments for PROCEDURE db_storedproc.sp1; expected 2, got 1 DROP PROCEDURE h1; DROP PROCEDURE sp1; @@ -22669,6 +22699,8 @@ END// CALL h1 (); @x @x2 1 1 +Warnings: +Error 1318 Incorrect number of arguments for PROCEDURE db_storedproc.sp1; expected 2, got 1 DROP PROCEDURE h1; DROP PROCEDURE sp1; @@ -22704,6 +22736,8 @@ done 1 done 1 +Warnings: +Error 1329 No data - zero rows fetched, selected, or processed DROP PROCEDURE IF EXISTS h1; DROP TABLE IF EXISTS res_t1; DROP TABLE IF EXISTS res_t2; @@ -22777,6 +22811,8 @@ done 0 done 1 +Warnings: +Error 1329 No data - zero rows fetched, selected, or processed DROP PROCEDURE IF EXISTS h1; DROP TABLE IF EXISTS res_t1; DROP TABLE IF EXISTS res_t2; @@ -22814,6 +22850,8 @@ done 0 done 1 +Warnings: +Error 1329 No data - zero rows fetched, selected, or processed DROP PROCEDURE IF EXISTS h1; DROP TABLE IF EXISTS res_t1; DROP TABLE IF EXISTS res_t2; @@ -22844,6 +22882,8 @@ done 0 done 1 +Warnings: +Error 1328 Incorrect number of FETCH variables DROP PROCEDURE IF EXISTS h1; DROP TABLE IF EXISTS res_t1; DROP TABLE IF EXISTS res_t2; @@ -22874,6 +22914,8 @@ done 0 done 1 +Warnings: +Error 1328 Incorrect number of FETCH variables DROP PROCEDURE IF EXISTS h1; DROP TABLE IF EXISTS res_t1; DROP TABLE IF EXISTS res_t2; @@ -22904,6 +22946,8 @@ END// CALL h1(); done 0 +Warnings: +Error 1328 Incorrect number of FETCH variables DROP PROCEDURE IF EXISTS h1; DROP TABLE IF EXISTS res_t1; DROP TABLE IF EXISTS res_t2; @@ -22934,6 +22978,8 @@ END// CALL h1(); done 0 +Warnings: +Error 1328 Incorrect number of FETCH variables DROP PROCEDURE IF EXISTS h1; DROP TABLE IF EXISTS res_t1; DROP TABLE IF EXISTS res_t2; @@ -22964,6 +23010,8 @@ done 0 done 1 +Warnings: +Error 1325 Cursor is already open DROP PROCEDURE IF EXISTS h1; DROP TABLE IF EXISTS res_t1; DROP TABLE IF EXISTS res_t2; @@ -22995,6 +23043,8 @@ done 0 done @x 1 1 +Warnings: +Error 1325 Cursor is already open DROP PROCEDURE IF EXISTS h1; DROP TABLE IF EXISTS res_t1; DROP TABLE IF EXISTS res_t2; @@ -23025,6 +23075,8 @@ END// CALL h1(); done 0 +Warnings: +Error 1325 Cursor is already open DROP PROCEDURE IF EXISTS h1; DROP TABLE IF EXISTS res_t1; DROP TABLE IF EXISTS res_t2; @@ -23055,6 +23107,8 @@ END// CALL h1(); done 0 +Warnings: +Error 1325 Cursor is already open DROP PROCEDURE IF EXISTS h1; DROP TABLE IF EXISTS res_t1; DROP TABLE IF EXISTS res_t2; @@ -23082,6 +23136,8 @@ END// CALL h1(); done @x 1 1 +Warnings: +Error 1326 Cursor is not open DROP PROCEDURE IF EXISTS h1; DROP TABLE IF EXISTS res_t1; DROP TABLE IF EXISTS res_t2; @@ -23109,6 +23165,8 @@ END// CALL h1(); done @x 1 1 +Warnings: +Error 1326 Cursor is not open DROP PROCEDURE IF EXISTS h1; DROP TABLE IF EXISTS res_t1; DROP TABLE IF EXISTS res_t2; @@ -23134,6 +23192,8 @@ set @x=1; SELECT done, @x; END// CALL h1(); +Warnings: +Error 1326 Cursor is not open DROP PROCEDURE IF EXISTS h1; DROP TABLE IF EXISTS res_t1; DROP TABLE IF EXISTS res_t2; @@ -23159,6 +23219,8 @@ set @x=1; SELECT done, @x; END// CALL h1(); +Warnings: +Error 1326 Cursor is not open DROP PROCEDURE IF EXISTS h1; drop table IF EXISTS res_t1; drop table IF EXISTS res_t2; @@ -23189,6 +23251,8 @@ END// CALL h1(); done @x 1 1 +Warnings: +Error 1339 Case not found for CASE statement DROP PROCEDURE IF EXISTS h1; drop table IF EXISTS res_t1; drop table IF EXISTS res_t2; @@ -23219,6 +23283,8 @@ END// CALL h1(); done @x 1 1 +Warnings: +Error 1339 Case not found for CASE statement DROP PROCEDURE IF EXISTS h1; drop table IF EXISTS res_t1; drop table IF EXISTS res_t2; @@ -23247,6 +23313,8 @@ set @x=1; SELECT done, @x; END// CALL h1(); +Warnings: +Error 1339 Case not found for CASE statement DROP PROCEDURE IF EXISTS h1; drop table IF EXISTS res_t1; drop table IF EXISTS res_t2; @@ -23275,6 +23343,8 @@ set @x=1; SELECT done, @x; END// CALL h1(); +Warnings: +Error 1339 Case not found for CASE statement DROP PROCEDURE IF EXISTS h1; DROP TABLE IF EXISTS res_t1; DROP TABLE IF EXISTS res_t2; @@ -23423,6 +23493,9 @@ CREATE TABLE res_t1(w CHAR, x CHAR); INSERT INTO res_t1 VALUES('a', 'b'); INSERT INTO res_t1 VALUES('c', 'd'); CALL h1(); +Warnings: +Warning 1265 Data truncated for column 'w' at row 1 +Warning 1265 Data truncated for column 'x' at row 1 SELECT @done, @x; @done @x 1 1 @@ -23445,6 +23518,9 @@ CREATE TABLE res_t1(w CHAR, x CHAR); INSERT INTO res_t1 VALUES('a', 'b'); INSERT INTO res_t1 VALUES('c', 'd'); CALL h1(); +Warnings: +Warning 1265 Data truncated for column 'w' at row 1 +Warning 1265 Data truncated for column 'x' at row 1 SELECT @done, @x; @done @x 1 1 diff --git a/mysql-test/suite/rpl/r/rpl_row_sp005.result b/mysql-test/suite/rpl/r/rpl_row_sp005.result index 01e1970e0df..58c53b394b2 100644 --- a/mysql-test/suite/rpl/r/rpl_row_sp005.result +++ b/mysql-test/suite/rpl/r/rpl_row_sp005.result @@ -77,6 +77,8 @@ id2 < ---- Master selects-- > ------------------------- CALL test.p1(); +Warnings: +Error 1329 No data - zero rows fetched, selected, or processed SELECT * FROM test.t3 ORDER BY id3; id3 c 1 MySQL diff --git a/mysql-test/suite/rpl/r/rpl_row_sp006_InnoDB.result b/mysql-test/suite/rpl/r/rpl_row_sp006_InnoDB.result index 6792a701577..079e750e2eb 100644 --- a/mysql-test/suite/rpl/r/rpl_row_sp006_InnoDB.result +++ b/mysql-test/suite/rpl/r/rpl_row_sp006_InnoDB.result @@ -38,6 +38,8 @@ INSERT INTO t1 VALUES ('MySQL','1993-02-04'),('ROCKS', '1990-08-27'),('Texas', ' END| CALL p2(); CALL p1(); +Warnings: +Error 1329 No data - zero rows fetched, selected, or processed DROP TABLE t1; DROP TABLE t2; DROP PROCEDURE p1; diff --git a/mysql-test/suite/rpl/r/rpl_row_trig003.result b/mysql-test/suite/rpl/r/rpl_row_trig003.result index 43c2ecde2b4..131af933b41 100644 --- a/mysql-test/suite/rpl/r/rpl_row_trig003.result +++ b/mysql-test/suite/rpl/r/rpl_row_trig003.result @@ -69,9 +69,15 @@ INSERT INTO test.t2 VALUES(NULL,0,'Testing MySQL databases is a cool ', 'MySQL C UPDATE test.t1 SET b1 = 0 WHERE b1 = 1; INSERT INTO test.t2 VALUES(NULL,1,'This is an after update test.', 'If this works, total will not be zero on the master or slave',1.4321,5.221,0,YEAR(NOW()),NOW()); UPDATE test.t2 SET b1 = 0 WHERE b1 = 1; +Warnings: +Error 1329 No data - zero rows fetched, selected, or processed INSERT INTO test.t1 VALUES(NULL,1,'add some more test data test.', 'and hope for the best', 3.321,5.221,0,YEAR(NOW()),NOW()); DELETE FROM test.t1 WHERE id = 1; +Warnings: +Error 1329 No data - zero rows fetched, selected, or processed DELETE FROM test.t2 WHERE id = 1; +Warnings: +Error 1329 No data - zero rows fetched, selected, or processed DROP TRIGGER test.t1_bi; DROP TRIGGER test.t2_ai; DROP TRIGGER test.t1_bu; diff --git a/mysql-test/t/signal.test b/mysql-test/t/signal.test index bdb6625ba32..4c8e6159371 100644 --- a/mysql-test/t/signal.test +++ b/mysql-test/t/signal.test @@ -2408,6 +2408,7 @@ BEGIN DECLARE EXIT HANDLER FOR x BEGIN SELECT '2'; + SHOW WARNINGS; RESIGNAL x SET MYSQL_ERRNO = 9999; END; @@ -2415,9 +2416,10 @@ BEGIN DECLARE EXIT HANDLER FOR x BEGIN SELECT '1'; + SHOW WARNINGS; RESIGNAL x SET SCHEMA_NAME = 'test', - MYSQL_ERRNO= 1231; + MYSQL_ERRNO= 1232; END; /* Raises ER_WRONG_VALUE_FOR_VAR : 1231, SQLSTATE 42000 */ SET @@sql_mode=NULL; @@ -2431,6 +2433,7 @@ BEGIN DECLARE EXIT HANDLER FOR x BEGIN SELECT '3'; + SHOW WARNINGS; RESIGNAL x SET MESSAGE_TEXT = 'Hi, I am a useless error message', MYSQL_ERRNO = 9999; diff --git a/mysql-test/t/sp-code.test b/mysql-test/t/sp-code.test index 247c84fda39..90b4c18895a 100644 --- a/mysql-test/t/sp-code.test +++ b/mysql-test/t/sp-code.test @@ -649,3 +649,56 @@ END// DELIMITER ;// SHOW PROCEDURE CODE p1; DROP PROCEDURE p1; + +--echo # +--echo # Bug#23032: Handlers declared in a SP do not handle warnings generated in sub-SP +--echo # + +--echo +--echo # - Case 4: check that "No Data trumps Warning". +--echo + +CREATE TABLE t1(a INT); +INSERT INTO t1 VALUES (1), (2), (3); + +delimiter |; + +CREATE PROCEDURE p1() +BEGIN + DECLARE c CURSOR FOR SELECT a FROM t1; + + OPEN c; + + BEGIN + DECLARE v INT; + + DECLARE CONTINUE HANDLER FOR SQLWARNING + BEGIN + SELECT "Warning found!"; + SHOW WARNINGS; + END; + + DECLARE EXIT HANDLER FOR NOT FOUND + BEGIN + SELECT "End of Result Set found!"; + SHOW WARNINGS; + END; + + WHILE TRUE DO + FETCH c INTO v; + END WHILE; + END; + + CLOSE c; + + SELECT a INTO @foo FROM t1 LIMIT 1; # Clear warning stack +END| + +delimiter ;| + +SET SESSION debug="+d,bug23032_emit_warning"; +CALL p1(); +SET SESSION debug="-d,bug23032_emit_warning"; + +DROP PROCEDURE p1; +DROP TABLE t1; diff --git a/mysql-test/t/sp-error.test b/mysql-test/t/sp-error.test index c8b2595e23d..13ca55a0127 100644 --- a/mysql-test/t/sp-error.test +++ b/mysql-test/t/sp-error.test @@ -2543,3 +2543,273 @@ DROP TABLE t1; --echo End of 5.1 tests +--echo # +--echo # Bug#23032: Handlers declared in a SP do not handle warnings generated in sub-SP +--echo # + +--echo +--echo # - Case 1 +--echo + +--disable_warnings +DROP PROCEDURE IF EXISTS p1; +DROP PROCEDURE IF EXISTS p2; +DROP PROCEDURE IF EXISTS p3; +DROP PROCEDURE IF EXISTS p4; +DROP PROCEDURE IF EXISTS p5; +DROP PROCEDURE IF EXISTS p6; +--enable_warnings + +delimiter |; + +CREATE PROCEDURE p1() + BEGIN + SELECT CAST('10 ' as unsigned integer); + SELECT 1; + CALL p2(); + END| + +CREATE PROCEDURE p2() + BEGIN + SELECT CAST('10 ' as unsigned integer); + END| + +delimiter ;| + +CALL p1(); + +DROP PROCEDURE p1; +DROP PROCEDURE p2; + +--echo +--echo # - Case 2 +--echo + +delimiter |; + +CREATE PROCEDURE p1() + BEGIN + DECLARE c INT DEFAULT 0; + DECLARE CONTINUE HANDLER FOR SQLWARNING SET c = c + 1; + CALL p2(); + CALL p3(); + CALL p4(); + SELECT c; + SELECT @@warning_count; + SHOW WARNINGS; + END| + +CREATE PROCEDURE p2() + BEGIN + SELECT CAST('10 ' as unsigned integer); + END| + +CREATE PROCEDURE p3() + BEGIN + SELECT CAST('10 ' as unsigned integer); + SELECT 1; + END| + +CREATE PROCEDURE p4() + BEGIN + SELECT CAST('10 ' as unsigned integer); + CALL p2(); + END| + +CREATE PROCEDURE p5() + BEGIN + SELECT CAST('10 ' as unsigned integer); + SHOW WARNINGS; + END| + +CREATE PROCEDURE P6() + BEGIN + DECLARE c INT DEFAULT 0; + DECLARE CONTINUE HANDLER FOR SQLWARNING SET c = c + 1; + CALL p5(); + SELECT c; + END| + +delimiter ;| + +CALL p1(); +CALL p6(); + +DROP PROCEDURE p1; +DROP PROCEDURE p2; +DROP PROCEDURE p3; +DROP PROCEDURE p4; +DROP PROCEDURE p5; +DROP PROCEDURE p6; + +--echo +--echo # - Case 3: check that "Exception trumps No Data". +--echo + +--disable_warnings +DROP TABLE IF EXISTS t1; +--enable_warnings + +CREATE TABLE t1(a INT); +INSERT INTO t1 VALUES (1), (2), (3); + +delimiter |; + +CREATE PROCEDURE p1() +BEGIN + DECLARE c CURSOR FOR SELECT a FROM t1; + + OPEN c; + + BEGIN + DECLARE v1 INT; + DECLARE v2 INT; + + DECLARE EXIT HANDLER FOR SQLEXCEPTION + SELECT "Error caught (expected)"; + + DECLARE EXIT HANDLER FOR NOT FOUND + SELECT "End of Result Set found!"; + + WHILE TRUE DO + FETCH c INTO v1, v2; + END WHILE; + END; + + CLOSE c; + + SELECT a INTO @foo FROM t1 LIMIT 1; # Clear warning stack +END| + +delimiter ;| + +CALL p1(); + +DROP PROCEDURE p1; +DROP TABLE t1; + +--echo # +--echo # Bug#36185: Incorrect precedence for warning and exception handlers +--echo # + +--disable_warnings +DROP TABLE IF EXISTS t1; +DROP PROCEDURE IF EXISTS p1; +--enable_warnings + +CREATE TABLE t1 (a INT, b INT NOT NULL); + +delimiter |; + +CREATE PROCEDURE p1() +BEGIN + DECLARE CONTINUE HANDLER FOR SQLWARNING SELECT 'warning'; + DECLARE CONTINUE HANDLER FOR SQLEXCEPTION SELECT 'exception'; + INSERT INTO t1 VALUES (CAST('10 ' AS SIGNED), NULL); +END| + +delimiter ;| + +CALL p1(); + +DROP TABLE t1; +DROP PROCEDURE p1; + +--echo # +--echo # Bug#5889: Exit handler for a warning doesn't hide the warning in trigger +--echo # + +--echo +--echo # - Case 1 +--echo + +CREATE TABLE t1(a INT, b INT); +INSERT INTO t1 VALUES (1, 2); + +delimiter |; + +CREATE TRIGGER t1_bu BEFORE UPDATE ON t1 FOR EACH ROW +BEGIN + DECLARE EXIT HANDLER FOR SQLWARNING + SET NEW.a = 10; + + SET NEW.a = 99999999999; +END| + +delimiter ;| + +UPDATE t1 SET b = 20; + +SHOW WARNINGS; + +SELECT * FROM t1; + +DROP TRIGGER t1_bu; +DROP TABLE t1; + +--echo +--echo # - Case 2 +--echo + +CREATE TABLE t1(a INT); +CREATE TABLE t2(b CHAR(1)); + +delimiter |; + +CREATE TRIGGER t1_bi BEFORE INSERT ON t1 FOR EACH ROW +BEGIN + INSERT INTO t2 VALUES('ab'); # Produces a warning. + + INSERT INTO t2 VALUES('b'); # Does not produce a warning, + # previous warning should be cleared. +END| + +delimiter ;| + +INSERT INTO t1 VALUES(0); + +SHOW WARNINGS; + +SELECT * FROM t1; +SELECT * FROM t2; + +DROP TRIGGER t1_bi; +DROP TABLE t1; +DROP TABLE t2; + +--echo # +--echo # Bug#9857: Stored procedures: handler for sqlwarning ignored +--echo # + +SET @sql_mode_saved = @@sql_mode; +SET sql_mode = traditional; + +delimiter |; + +CREATE PROCEDURE p1() +BEGIN + DECLARE CONTINUE HANDLER FOR SQLWARNING + SELECT 'warning caught (expected)'; + + SELECT 5 / 0; +END| + +CREATE PROCEDURE p2() +BEGIN + DECLARE CONTINUE HANDLER FOR SQLEXCEPTION + SELECT 'error caught (unexpected)'; + + SELECT 5 / 0; +END| + +delimiter ;| + +CALL p1(); +SHOW WARNINGS; + +CALL p2(); +SHOW WARNINGS; + +DROP PROCEDURE p1; +DROP PROCEDURE p2; +SET sql_mode = @sql_mode_saved; diff --git a/mysql-test/t/sp.test b/mysql-test/t/sp.test index da949016a03..11edeaf9811 100644 --- a/mysql-test/t/sp.test +++ b/mysql-test/t/sp.test @@ -5432,6 +5432,8 @@ drop procedure if exists bug15231_1| drop procedure if exists bug15231_2| drop procedure if exists bug15231_3| drop procedure if exists bug15231_4| +drop procedure if exists bug15231_5| +drop procedure if exists bug15231_6| --enable_warnings create table t3 (id int not null)| @@ -5461,7 +5463,7 @@ end| create procedure bug15231_3() begin declare exit handler for sqlwarning - select 'Caught it (wrong)' as 'Result'; + select 'Caught it (correct)' as 'Result'; call bug15231_4(); end| @@ -5472,16 +5474,37 @@ begin set x = 'zap'; select 'Missed it (correct)' as 'Result'; + show warnings; +end| + +create procedure bug15231_5() +begin + declare exit handler for sqlwarning + select 'Caught it (wrong)' as 'Result'; + + call bug15231_6(); +end| + +create procedure bug15231_6() +begin + declare x decimal(2,1); + + set x = 'zap'; + select 'Missed it (correct)' as 'Result'; + select id from t3; end| call bug15231_1()| call bug15231_3()| +call bug15231_5()| -drop table if exists t3| -drop procedure if exists bug15231_1| -drop procedure if exists bug15231_2| -drop procedure if exists bug15231_3| -drop procedure if exists bug15231_4| +drop table t3| +drop procedure bug15231_1| +drop procedure bug15231_2| +drop procedure bug15231_3| +drop procedure bug15231_4| +drop procedure bug15231_5| +drop procedure bug15231_6| # diff --git a/sql/sp_head.cc b/sql/sp_head.cc index 11f138e67be..2d3a32c7f7f 100644 --- a/sql/sp_head.cc +++ b/sql/sp_head.cc @@ -1075,6 +1075,104 @@ void sp_head::recursion_level_error(THD *thd) } +/** + Find an SQL handler for any condition (warning or error) after execution + of a stored routine instruction. Basically, this function looks for an + appropriate SQL handler in RT-contexts. If an SQL handler is found, it is + remembered in the RT-context for future activation (the context can be + inactive at the moment). + + If there is no pending condition, the function just returns. + + If there was an error during the execution, an SQL handler for it will be + searched within the current and outer scopes. + + There might be several errors in the Warning Info (that's possible by using + SIGNAL/RESIGNAL in nested scopes) -- the function is looking for an SQL + handler for the latest (current) error only. + + If there was a warning during the execution, an SQL handler for it will be + searched within the current scope only. + + If several warnings were thrown during the execution and there are different + SQL handlers for them, it is not determined which SQL handler will be chosen. + Only one SQL handler will be executed. + + If warnings and errors were thrown during the execution, the error takes + precedence. I.e. error handler will be executed. If there is no handler + for that error, condition will remain unhandled. + + Once a warning or an error has been handled it is not removed from + Warning Info. + + According to The Standard (quoting PeterG): + + An SQL procedure statement works like this ... + SQL/Foundation 13.5 + (General Rules) (greatly summarized) says: + (1) Empty diagnostics area, thus clearing the condition. + (2) Execute statement. + During execution, if Exception Condition occurs, + set Condition Area = Exception Condition and stop + statement. + During execution, if No Data occurs, + set Condition Area = No Data Condition and continue + statement. + During execution, if Warning occurs, + and Condition Area is not already full due to + an earlier No Data condition, set Condition Area + = Warning and continue statement. + (3) Finish statement. + At end of execution, if Condition Area is not + already full due to an earlier No Data or Warning, + set Condition Area = Successful Completion. + In effect, this system means there is a precedence: + Exception trumps No Data, No Data trumps Warning, + Warning trumps Successful Completion. + + NB: "Procedure statements" include any DDL or DML or + control statements. So CREATE and DELETE and WHILE + and CALL and RETURN are procedure statements. But + DECLARE and END are not procedure statements. + + @param thd thread handle + @param ctx runtime context of the stored routine +*/ + +static void +find_handler_after_execution(THD *thd, sp_rcontext *ctx) +{ + if (thd->is_error()) + { + ctx->find_handler(thd, + thd->stmt_da->sql_errno(), + thd->stmt_da->get_sqlstate(), + MYSQL_ERROR::WARN_LEVEL_ERROR, + thd->stmt_da->message()); + } + else if (thd->warning_info->statement_warn_count()) + { + List_iterator it(thd->warning_info->warn_list()); + MYSQL_ERROR *err; + while ((err= it++)) + { + if (err->get_level() != MYSQL_ERROR::WARN_LEVEL_WARN && + err->get_level() != MYSQL_ERROR::WARN_LEVEL_NOTE) + continue; + + if (ctx->find_handler(thd, + err->get_sql_errno(), + err->get_sqlstate(), + err->get_level(), + err->get_message_text())) + { + break; + } + } + } +} + + /** Execute the routine. The main instruction jump loop is there. Assume the parameters already set. @@ -1096,7 +1194,7 @@ sp_head::execute(THD *thd) LEX_STRING saved_cur_db_name= { saved_cur_db_name_buf, sizeof(saved_cur_db_name_buf) }; bool cur_db_changed= FALSE; - sp_rcontext *ctx; + sp_rcontext *ctx= thd->spcont; bool err_status= FALSE; uint ip= 0; ulong save_sql_mode; @@ -1157,8 +1255,6 @@ sp_head::execute(THD *thd) goto done; } - if ((ctx= thd->spcont)) - ctx->clear_handler(); thd->is_slave_error= 0; old_arena= thd->stmt_arena; @@ -1243,7 +1339,6 @@ sp_head::execute(THD *thd) do { sp_instr *i; - uint hip; #if defined(ENABLED_PROFILING) /* @@ -1265,6 +1360,9 @@ sp_head::execute(THD *thd) break; } + /* Reset number of warnings for this query. */ + thd->warning_info->reset_for_next_command(); + DBUG_PRINT("execute", ("Instruction %u", ip)); /* @@ -1309,40 +1407,28 @@ sp_head::execute(THD *thd) free_root(&execute_mem_root, MYF(0)); /* - Check if an exception has occurred and a handler has been found - Note: We have to check even if err_status == FALSE, since warnings (and - some errors) don't return a non-zero value. We also have to check even - if thd->killed != 0, since some errors return with this even when a - handler has been found (e.g. "bad data"). + Find and process SQL handlers unless it is a fatal error (fatal + errors are not catchable by SQL handlers) or the connection has been + killed during execution. */ - if (ctx) + if (!thd->is_fatal_error && !thd->killed_errno()) { - uint handler_index; + /* + Find SQL handler in the appropriate RT-contexts: + - warnings can be handled by SQL handlers within + the current scope only; + - errors can be handled by any SQL handler from outer scope. + */ + find_handler_after_execution(thd, ctx); - switch (ctx->found_handler(& hip, & handler_index)) { - case SP_HANDLER_NONE: - break; - case SP_HANDLER_CONTINUE: - thd->restore_active_arena(&execute_arena, &backup_arena); - thd->set_n_backup_active_arena(&execute_arena, &backup_arena); - ctx->push_hstack(i->get_cont_dest()); - /* Fall through */ - default: - if (ctx->end_partial_result_set) - thd->protocol->end_partial_result_set(thd); - ip= hip; + /* If found, activate handler for the current scope. */ + if (ctx->activate_handler(thd, &ip, i, &execute_arena, &backup_arena)) err_status= FALSE; - ctx->clear_handler(); - ctx->enter_handler(hip, handler_index); - thd->clear_error(); - thd->is_fatal_error= 0; - thd->killed= THD::NOT_KILLED; - thd->mysys_var->abort= 0; - continue; - } - - ctx->end_partial_result_set= FALSE; } + + /* Reset sp_rcontext::end_partial_result_set flag. */ + ctx->end_partial_result_set= FALSE; + } while (!err_status && !thd->killed && !thd->is_fatal_error); #if defined(ENABLED_PROFILING) @@ -3037,23 +3123,14 @@ sp_instr_set::exec_core(THD *thd, uint *nextp) { int res= thd->spcont->set_variable(thd, m_offset, &m_value); - if (res && thd->spcont->found_handler_here()) + if (res) { - /* - Failed to evaluate the value, and a handler has been found. Reset the - variable to NULL. - */ + /* Failed to evaluate the value. Reset the variable to NULL. */ if (thd->spcont->set_variable(thd, m_offset, 0)) { /* If this also failed, let's abort. */ - - sp_rcontext *spcont= thd->spcont; - - thd->spcont= NULL; /* Avoid handlers */ - my_error(ER_OUT_OF_RESOURCES, MYF(0)); - spcont->clear_handler(); - thd->spcont= spcont; + my_error(ER_OUT_OF_RESOURCES, MYF(ME_FATALERROR)); } } @@ -3586,18 +3663,6 @@ sp_instr_copen::execute(THD *thd, uint *nextp) if (thd->stmt_arena->free_list) cleanup_items(thd->stmt_arena->free_list); thd->stmt_arena= old_arena; - /* - Work around the fact that errors in selects are not returned properly - (but instead converted into a warning), so if a condition handler - caught, we have lost the result code. - */ - if (!res) - { - uint dummy1, dummy2; - - if (thd->spcont->found_handler(&dummy1, &dummy2)) - res= -1; - } /* TODO: Assert here that we either have an error or a cursor */ } DBUG_RETURN(res); @@ -3773,13 +3838,11 @@ sp_instr_set_case_expr::exec_core(THD *thd, uint *nextp) { int res= thd->spcont->set_case_expr(thd, m_case_expr_id, &m_case_expr); - if (res && - !thd->spcont->get_case_expr(m_case_expr_id) && - thd->spcont->found_handler_here()) + if (res && !thd->spcont->get_case_expr(m_case_expr_id)) { /* Failed to evaluate the value, the case expression is still not - initialized, and a handler has been found. Set to NULL so we can continue. + initialized. Set to NULL so we can continue. */ Item *null_item= new Item_null(); @@ -3788,13 +3851,7 @@ sp_instr_set_case_expr::exec_core(THD *thd, uint *nextp) thd->spcont->set_case_expr(thd, m_case_expr_id, &null_item)) { /* If this also failed, we have to abort. */ - - sp_rcontext *spcont= thd->spcont; - - thd->spcont= NULL; /* Avoid handlers */ - my_error(ER_OUT_OF_RESOURCES, MYF(0)); - spcont->clear_handler(); - thd->spcont= spcont; + my_error(ER_OUT_OF_RESOURCES, MYF(ME_FATALERROR)); } } else diff --git a/sql/sp_pcontext.h b/sql/sp_pcontext.h index b12d5362c6b..c27c7d22da2 100644 --- a/sql/sp_pcontext.h +++ b/sql/sp_pcontext.h @@ -332,13 +332,6 @@ public: int push_cond(LEX_STRING *name, sp_cond_type_t *val); - inline void - pop_cond(uint num) - { - while (num--) - pop_dynamic(&m_conds); - } - sp_cond_type_t * find_cond(LEX_STRING *name, my_bool scoped=0); diff --git a/sql/sp_rcontext.cc b/sql/sp_rcontext.cc index b08f8008b59..e76a5e9ebde 100644 --- a/sql/sp_rcontext.cc +++ b/sql/sp_rcontext.cc @@ -171,48 +171,50 @@ sp_rcontext::set_return_value(THD *thd, Item **return_value_item) #define IS_NOT_FOUND_CONDITION(S) ((S)[0] == '0' && (S)[1] == '2') #define IS_EXCEPTION_CONDITION(S) ((S)[0] != '0' || (S)[1] > '2') -/* - Find a handler for the given errno. - This is called from all error message functions (e.g. push_warning, - net_send_error, et al) when a sp_rcontext is in effect. If a handler - is found, no error is sent, and the the SP execution loop will instead - invoke the found handler. - This might be called several times before we get back to the execution - loop, so m_hfound can be >= 0 if a handler has already been found. - (In which case we don't search again - the first found handler will - be used.) - Handlers are pushed on the stack m_handler, with the latest/innermost +/** + Find an SQL handler for the given error. + + SQL handlers are pushed on the stack m_handler, with the latest/innermost one on the top; we then search for matching handlers from the top and down. + We search through all the handlers, looking for the most specific one (sql_errno more specific than sqlstate more specific than the rest). Note that mysql error code handlers is a MySQL extension, not part of the standard. - SYNOPSIS - sql_errno The error code - level Warning level + SQL handlers for warnings are searched in the current scope only. - RETURN - 1 if a handler was found, m_hfound is set to its index (>= 0) - 0 if not found, m_hfound is -1 + SQL handlers for errors are searched in the current and in outer scopes. + That's why finding and activation of handler must be separated: an errror + handler might be located in the outer scope, which is not active at the + moment. Before such handler can be activated, execution flow should + unwind to that scope. + + Found SQL handler is remembered in m_hfound for future activation. + If no handler is found, m_hfound is -1. + + @param thd Thread handle + @param sql_errno The error code + @param sqlstate The error SQL state + @param level The error level + @param msg The error message + + @retval TRUE if an SQL handler was found + @retval FALSE otherwise */ bool sp_rcontext::find_handler(THD *thd, uint sql_errno, - const char* sqlstate, + const char *sqlstate, MYSQL_ERROR::enum_warning_level level, - const char* msg, - MYSQL_ERROR ** cond_hdl) + const char *msg) { - if (m_hfound >= 0) - { - *cond_hdl= NULL; - return TRUE; // Already got one - } + int i= m_hcount; - int i= m_hcount, found= -1; + /* Reset previously found handler. */ + m_hfound= -1; /* If this is a fatal sub-statement error, and this runtime @@ -240,105 +242,56 @@ sp_rcontext::find_handler(THD *thd, { case sp_cond_type_t::number: if (sql_errno == cond->mysqlerr && - (found < 0 || m_handler[found].cond->type > sp_cond_type_t::number)) - found= i; // Always the most specific + (m_hfound < 0 || m_handler[m_hfound].cond->type > sp_cond_type_t::number)) + m_hfound= i; // Always the most specific break; case sp_cond_type_t::state: if (strcmp(sqlstate, cond->sqlstate) == 0 && - (found < 0 || m_handler[found].cond->type > sp_cond_type_t::state)) - found= i; + (m_hfound < 0 || m_handler[m_hfound].cond->type > sp_cond_type_t::state)) + m_hfound= i; break; case sp_cond_type_t::warning: if ((IS_WARNING_CONDITION(sqlstate) || level == MYSQL_ERROR::WARN_LEVEL_WARN) && - found < 0) - found= i; + m_hfound < 0) + m_hfound= i; break; case sp_cond_type_t::notfound: - if (IS_NOT_FOUND_CONDITION(sqlstate) && found < 0) - found= i; + if (IS_NOT_FOUND_CONDITION(sqlstate) && m_hfound < 0) + m_hfound= i; break; case sp_cond_type_t::exception: if (IS_EXCEPTION_CONDITION(sqlstate) && level == MYSQL_ERROR::WARN_LEVEL_ERROR && - found < 0) - found= i; + m_hfound < 0) + m_hfound= i; break; } } - if (found < 0) + + if (m_hfound >= 0) { - /* - Only "exception conditions" are propagated to handlers in calling - contexts. If no handler is found locally for a "completion condition" - (warning or "not found") we will simply resume execution. - */ - if (m_prev_runtime_ctx && IS_EXCEPTION_CONDITION(sqlstate) && - level == MYSQL_ERROR::WARN_LEVEL_ERROR) - return m_prev_runtime_ctx->find_handler(thd, - sql_errno, - sqlstate, - level, - msg, - cond_hdl); - *cond_hdl= NULL; - return FALSE; + DBUG_ASSERT((uint) m_hfound < m_root_parsing_ctx->max_handler_index()); + + m_raised_conditions[m_hfound].clear(); + m_raised_conditions[m_hfound].set(sql_errno, sqlstate, level, msg); + + return TRUE; } - m_hfound= found; - - MYSQL_ERROR *raised= NULL; - DBUG_ASSERT(m_hfound >= 0); - DBUG_ASSERT((uint) m_hfound < m_root_parsing_ctx->max_handler_index()); - raised= & m_raised_conditions[m_hfound]; - raised->clear(); - raised->set(sql_errno, sqlstate, level, msg); - - *cond_hdl= raised; - return TRUE; -} - -/* - Handle the error for a given errno. - The severity of the error is adjusted depending of the current sql_mode. - If an handler is present for the error (see find_handler()), - this function will return true. - If a handler is found and if the severity of the error indicate - that the current instruction executed should abort, - the flag thd->net.report_error is also set. - This will cause the execution of the current instruction in a - sp_instr* to fail, and give control to the handler code itself - in the sp_head::execute() loop. - - SYNOPSIS - sql_errno The error code - level Warning level - thd The current thread - - RETURN - TRUE if a handler was found. - FALSE if no handler was found. -*/ -bool -sp_rcontext::handle_condition(THD *thd, - uint sql_errno, - const char* sqlstate, - MYSQL_ERROR::enum_warning_level level, - const char* msg, - MYSQL_ERROR ** cond_hdl) -{ - MYSQL_ERROR::enum_warning_level elevated_level= level; - - - /* Depending on the sql_mode of execution, - warnings may be considered errors */ - if ((level == MYSQL_ERROR::WARN_LEVEL_WARN) && - thd->really_abort_on_warning()) + /* + Only "exception conditions" are propagated to handlers in calling + contexts. If no handler is found locally for a "completion condition" + (warning or "not found") we will simply resume execution. + */ + if (m_prev_runtime_ctx && IS_EXCEPTION_CONDITION(sqlstate) && + level == MYSQL_ERROR::WARN_LEVEL_ERROR) { - elevated_level= MYSQL_ERROR::WARN_LEVEL_ERROR; + return m_prev_runtime_ctx->find_handler(thd, sql_errno, sqlstate, + level, msg); } - return find_handler(thd, sql_errno, sqlstate, elevated_level, msg, cond_hdl); + return FALSE; } void @@ -384,7 +337,9 @@ sp_rcontext::pop_handlers(uint count) { DBUG_ENTER("sp_rcontext::pop_handlers"); DBUG_ASSERT(m_hcount >= count); + m_hcount-= count; + DBUG_PRINT("info", ("m_hcount: %d", m_hcount)); DBUG_VOID_RETURN; } @@ -394,7 +349,9 @@ sp_rcontext::push_hstack(uint h) { DBUG_ENTER("sp_rcontext::push_hstack"); DBUG_ASSERT(m_hsp < m_root_parsing_ctx->max_handler_index()); + m_hstack[m_hsp++]= h; + DBUG_PRINT("info", ("m_hsp: %d", m_hsp)); DBUG_VOID_RETURN; } @@ -405,21 +362,74 @@ sp_rcontext::pop_hstack() uint handler; DBUG_ENTER("sp_rcontext::pop_hstack"); DBUG_ASSERT(m_hsp); + handler= m_hstack[--m_hsp]; + DBUG_PRINT("info", ("m_hsp: %d", m_hsp)); DBUG_RETURN(handler); } -void -sp_rcontext::enter_handler(uint hip, uint hindex) +/** + Prepare found handler to be executed. + + @retval TRUE if an SQL handler is activated (was found) and IP of the + first handler instruction. + @retval FALSE if there is no active handler +*/ + +bool +sp_rcontext::activate_handler(THD *thd, + uint *ip, + sp_instr *instr, + Query_arena *execute_arena, + Query_arena *backup_arena) { - DBUG_ENTER("sp_rcontext::enter_handler"); - DBUG_ASSERT(m_ihsp < m_root_parsing_ctx->max_handler_index()); - m_in_handler[m_ihsp].ip= hip; - m_in_handler[m_ihsp].index= hindex; - m_ihsp++; - DBUG_PRINT("info", ("m_ihsp: %d", m_ihsp)); - DBUG_VOID_RETURN; + if (m_hfound < 0) + return FALSE; + + switch (m_handler[m_hfound].type) { + case SP_HANDLER_NONE: + break; + + case SP_HANDLER_CONTINUE: + thd->restore_active_arena(execute_arena, backup_arena); + thd->set_n_backup_active_arena(execute_arena, backup_arena); + push_hstack(instr->get_cont_dest()); + + /* Fall through */ + + default: + /* End aborted result set. */ + + if (end_partial_result_set) + thd->protocol->end_partial_result_set(thd); + + /* Enter handler. */ + + DBUG_ASSERT(m_ihsp < m_root_parsing_ctx->max_handler_index()); + DBUG_ASSERT(m_hfound >= 0); + + m_in_handler[m_ihsp].ip= m_handler[m_hfound].handler; + m_in_handler[m_ihsp].index= m_hfound; + m_ihsp++; + + DBUG_PRINT("info", ("Entering handler...")); + DBUG_PRINT("info", ("m_ihsp: %d", m_ihsp)); + + /* Reset error state. */ + + thd->clear_error(); + thd->killed= THD::NOT_KILLED; // Some errors set thd->killed + // (e.g. "bad data"). + + /* Return IP of the activated SQL handler. */ + *ip= m_handler[m_hfound].handler; + + /* Reset found handler. */ + m_hfound= -1; + } + + return TRUE; } void @@ -427,9 +437,11 @@ sp_rcontext::exit_handler() { DBUG_ENTER("sp_rcontext::exit_handler"); DBUG_ASSERT(m_ihsp); + uint hindex= m_in_handler[m_ihsp-1].index; m_raised_conditions[hindex].clear(); m_ihsp-= 1; + DBUG_PRINT("info", ("m_ihsp: %d", m_ihsp)); DBUG_VOID_RETURN; } @@ -567,6 +579,11 @@ sp_cursor::fetch(THD *thd, List *vars) return -1; } + DBUG_EXECUTE_IF("bug23032_emit_warning", + push_warning(thd, MYSQL_ERROR::WARN_LEVEL_WARN, + ER_UNKNOWN_ERROR, + ER(ER_UNKNOWN_ERROR));); + result.set_spvar_list(vars); /* Attempt to fetch one row */ diff --git a/sql/sp_rcontext.h b/sql/sp_rcontext.h index fad253706cb..1af758ed0af 100644 --- a/sql/sp_rcontext.h +++ b/sql/sp_rcontext.h @@ -131,67 +131,40 @@ class sp_rcontext : public Sql_alloc return m_return_value_set; } + /* + SQL handlers support. + */ + void push_handler(struct sp_cond_type *cond, uint h, int type); void pop_handlers(uint count); - // Returns 1 if a handler was found, 0 otherwise. bool find_handler(THD *thd, uint sql_errno, - const char* sqlstate, + const char *sqlstate, MYSQL_ERROR::enum_warning_level level, - const char* msg, - MYSQL_ERROR ** cond_hdl); + const char *msg); + + MYSQL_ERROR * + raised_condition() const; + + void + push_hstack(uint h); + + uint + pop_hstack(); - // If there is an error handler for this error, handle it and return TRUE. bool - handle_condition(THD *thd, - uint sql_errno, - const char* sqlstate, - MYSQL_ERROR::enum_warning_level level, - const char* msg, - MYSQL_ERROR ** cond_hdl); + activate_handler(THD *thd, + uint *ip, + sp_instr *instr, + Query_arena *execute_arena, + Query_arena *backup_arena); - // Returns handler type and sets *ip to location if one was found - inline int - found_handler(uint *ip, uint *index) - { - if (m_hfound < 0) - return SP_HANDLER_NONE; - *ip= m_handler[m_hfound].handler; - *index= m_hfound; - return m_handler[m_hfound].type; - } - MYSQL_ERROR* raised_condition() const; - - // Returns true if we found a handler in this context - inline bool - found_handler_here() - { - return (m_hfound >= 0); - } - - // Clears the handler find state - inline void - clear_handler() - { - m_hfound= -1; - } - - void push_hstack(uint h); - - uint pop_hstack(); - - /** - Enter a SQL exception handler. - @param hip the handler instruction pointer - @param index the handler index - */ - void enter_handler(uint hip, uint index); - - void exit_handler(); + void + exit_handler(); void push_cursor(sp_lex_keeper *lex_keeper, sp_instr_cpush *i); @@ -199,7 +172,7 @@ class sp_rcontext : public Sql_alloc void pop_cursors(uint count); - void + inline void pop_all_cursors() { pop_cursors(m_ccount); diff --git a/sql/sql_class.cc b/sql/sql_class.cc index 7eb4911c744..60a871e9e88 100644 --- a/sql/sql_class.cc +++ b/sql/sql_class.cc @@ -845,35 +845,6 @@ MYSQL_ERROR* THD::raise_condition(uint sql_errno, } } - /* - If a continue handler is found, the error message will be cleared - by the stored procedures code. - */ - if (!is_fatal_error && spcont && - spcont->handle_condition(this, sql_errno, sqlstate, level, msg, &cond)) - { - /* - Do not push any warnings, a handled error must be completely - silenced. - */ - DBUG_RETURN(cond); - } - - /* Un-handled conditions */ - - cond= raise_condition_no_handler(sql_errno, sqlstate, level, msg); - DBUG_RETURN(cond); -} - -MYSQL_ERROR* -THD::raise_condition_no_handler(uint sql_errno, - const char* sqlstate, - MYSQL_ERROR::enum_warning_level level, - const char* msg) -{ - MYSQL_ERROR *cond= NULL; - DBUG_ENTER("THD::raise_condition_no_handler"); - query_cache_abort(&query_cache_tls); /* FIXME: broken special case */ @@ -886,6 +857,7 @@ THD::raise_condition_no_handler(uint sql_errno, cond= warning_info->push_warning(this, sql_errno, sqlstate, level, msg); DBUG_RETURN(cond); } + extern "C" void *thd_alloc(MYSQL_THD thd, unsigned int size) { diff --git a/sql/sql_class.h b/sql/sql_class.h index c719f5a09ad..b23b65dae2f 100644 --- a/sql/sql_class.h +++ b/sql/sql_class.h @@ -2800,23 +2800,6 @@ private: MYSQL_ERROR::enum_warning_level level, const char* msg); - /** - Raise a generic SQL condition, without activation any SQL condition - handlers. - This method is necessary to support the RESIGNAL statement, - which is allowed to bypass SQL exception handlers. - @param sql_errno the condition error number - @param sqlstate the condition SQLSTATE - @param level the condition level - @param msg the condition message text - @return The condition raised, or NULL - */ - MYSQL_ERROR* - raise_condition_no_handler(uint sql_errno, - const char* sqlstate, - MYSQL_ERROR::enum_warning_level level, - const char* msg); - public: /** Overloaded to guard query/query_length fields */ virtual void set_statement(Statement *stmt); diff --git a/sql/sql_error.cc b/sql/sql_error.cc index e5d0f79b2d7..8c038e10a1f 100644 --- a/sql/sql_error.cc +++ b/sql/sql_error.cc @@ -494,14 +494,6 @@ void Warning_info::clear_warning_info(ulonglong warn_id_arg) m_current_row_for_warning= 1; /* Start counting from the first row */ } -void Warning_info::reserve_space(THD *thd, uint count) -{ - /* Make room for count conditions */ - while ((m_warn_list.elements > 0) && - ((m_warn_list.elements + count) > thd->variables.max_error_count)) - m_warn_list.pop(); -} - /** Append warnings only if the original contents of the routine warning info was replaced. diff --git a/sql/sql_error.h b/sql/sql_error.h index 9e649a004df..87e98e27673 100644 --- a/sql/sql_error.h +++ b/sql/sql_error.h @@ -153,8 +153,8 @@ private: Representation of a SQL condition. A SQL condition can be a completion condition (note, warning), or an exception condition (error, not found). - @note This class is named MYSQL_ERROR instead of SQL_condition for historical reasons, - to facilitate merging code with previous releases. + @note This class is named MYSQL_ERROR instead of SQL_condition for + historical reasons, to facilitate merging code with previous releases. */ class MYSQL_ERROR : public Sql_alloc { @@ -471,18 +471,6 @@ public: ulong statement_warn_count() const { return m_statement_warn_count; } - /** - Reserve some space in the condition area. - This is a privileged operation, reserved for the RESIGNAL implementation, - as only the RESIGNAL statement is allowed to remove conditions from - the condition area. - For other statements, new conditions are not added to the condition - area once the condition area is full. - @param thd The current thread - @param count The number of slots to reserve - */ - void reserve_space(THD *thd, uint count); - /** Add a new condition to the current list. */ MYSQL_ERROR *push_warning(THD *thd, uint sql_errno, const char* sqlstate, diff --git a/sql/sql_signal.cc b/sql/sql_signal.cc index f340da373e8..09e9a828fa1 100644 --- a/sql/sql_signal.cc +++ b/sql/sql_signal.cc @@ -499,18 +499,6 @@ bool Resignal_statement::execute(THD *thd) } /* RESIGNAL with signal_value */ - - /* Make room for 2 conditions */ - thd->warning_info->reserve_space(thd, 2); - - MYSQL_ERROR *raised= NULL; - raised= thd->raise_condition_no_handler(signaled->get_sql_errno(), - signaled->get_sqlstate(), - signaled->get_level(), - signaled->get_message_text()); - if (raised) - raised->copy_opt_attributes(signaled); - result= raise_condition(thd, signaled); DBUG_RETURN(result); From 0fd9564dfb49d3c94a7d56e06714768ca84fdb58 Mon Sep 17 00:00:00 2001 From: Alexander Nozdrin Date: Fri, 30 Jul 2010 19:29:17 +0400 Subject: [PATCH 100/129] Update .bzrignore. --- .bzrignore | 1 + 1 file changed, 1 insertion(+) diff --git a/.bzrignore b/.bzrignore index f5f678ca360..a17b1dec6cb 100644 --- a/.bzrignore +++ b/.bzrignore @@ -3101,3 +3101,4 @@ libmysqld/merge_archives_mysqlserver.cmake libmysqld/mysqlserver_depends.c libmysqld/examples/mysql_embedded sql/.empty +mysys/thr_lock From 6878d03963365848550965045fe3c05104cba596 Mon Sep 17 00:00:00 2001 From: Davi Arnaut Date: Fri, 30 Jul 2010 18:29:54 -0300 Subject: [PATCH 101/129] Revert revision which disabled the generating of configuration scripts if cmake is available. We need to always generate the scripts in order for the dual cmake/autotools support to work. --- BUILD/autorun.sh | 36 +++++++++++++++--------------------- 1 file changed, 15 insertions(+), 21 deletions(-) diff --git a/BUILD/autorun.sh b/BUILD/autorun.sh index 9fdd0486360..f4508ab12b6 100755 --- a/BUILD/autorun.sh +++ b/BUILD/autorun.sh @@ -21,24 +21,18 @@ done IFS="$save_ifs" rm -rf configure - -# Ensure that cmake and perl are available. Required for cmake based builds. -cmake -P cmake/check_minimal_version.cmake >/dev/null 2>&1 || HAVE_CMAKE=no -perl --version >/dev/null 2>&1 || HAVE_CMAKE=no - -# Whether to use the autotools configuration script or cmake. -if test "$HAVE_CMAKE" = "no" -then - aclocal || die "Can't execute aclocal" - autoheader || die "Can't execute autoheader" - # --force means overwrite ltmain.sh script if it already exists - $LIBTOOLIZE --automake --force --copy || die "Can't execute libtoolize" - # --add-missing instructs automake to install missing auxiliary files - # and --force to overwrite them if they already exist - automake --add-missing --force --copy || die "Can't execute automake" - autoconf || die "Can't execute autoconf" -else - path=`dirname $0` - cp $path/cmake_configure.sh $path/../configure - chmod +x $path/../configure -fi +aclocal || die "Can't execute aclocal" +autoheader || die "Can't execute autoheader" +# --force means overwrite ltmain.sh script if it already exists +$LIBTOOLIZE --automake --force --copy || die "Can't execute libtoolize" + +# --add-missing instructs automake to install missing auxiliary files +# and --force to overwrite them if they already exist +automake --add-missing --force --copy || die "Can't execute automake" +autoconf || die "Can't execute autoconf" +# Do not use autotools generated configure directly. Instead, use a script +# that will either call CMake or original configure shell script at build +# time (CMake is preferred if installed). +mv configure configure.am +cp BUILD/cmake_configure.sh configure +chmod a+x configure From 75fd19ad0d2a6e6b9e813ceb1c6d5a282554abe9 Mon Sep 17 00:00:00 2001 From: Alexander Nozdrin Date: Sat, 31 Jul 2010 11:45:05 +0400 Subject: [PATCH 102/129] A follow-up patch for Bug 23032: fix federated_server.result. --- mysql-test/suite/federated/federated_server.result | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/mysql-test/suite/federated/federated_server.result b/mysql-test/suite/federated/federated_server.result index 5079a4dcfa0..422505bdd30 100644 --- a/mysql-test/suite/federated/federated_server.result +++ b/mysql-test/suite/federated/federated_server.result @@ -272,6 +272,10 @@ END// use test; call p1(); call p1(); +Warnings: +Error 1477 The foreign server name you are trying to reference does not exist. Data source error: s +Warnings: +Error 1476 The foreign server, s, you are trying to create already exists. drop procedure p1; drop server if exists s; DROP TABLE IF EXISTS federated.t1; From bf5b5b05efef24370d2a0e161e7ba2e5480366c1 Mon Sep 17 00:00:00 2001 From: Alexander Nozdrin Date: Sat, 31 Jul 2010 17:10:27 +0400 Subject: [PATCH 103/129] Fix federated.federated_server.test. --- mysql-test/suite/federated/federated_server.result | 12 ++++++------ mysql-test/suite/federated/federated_server.test | 8 ++++++-- 2 files changed, 12 insertions(+), 8 deletions(-) diff --git a/mysql-test/suite/federated/federated_server.result b/mysql-test/suite/federated/federated_server.result index 422505bdd30..e5cff2bb2bf 100644 --- a/mysql-test/suite/federated/federated_server.result +++ b/mysql-test/suite/federated/federated_server.result @@ -54,7 +54,7 @@ PASSWORD '', PORT SLAVE_PORT, SOCKET '', OWNER 'root'); -select * from mysql.servers; +select * from mysql.servers order by Server_name; Server_name Host Db Username Password Port Socket Wrapper Owner server_one 127.0.0.1 first_db root SLAVE_PORT mysql root server_two 127.0.0.1 second_db root SLAVE_PORT mysql root @@ -154,7 +154,7 @@ id name drop table federated.t1; drop server 'server_one'; drop server 'server_two'; -select * from mysql.servers; +select * from mysql.servers order by Server_name; Server_name Host Db Username Password Port Socket Wrapper Owner drop table first_db.t1; drop table second_db.t1; @@ -254,6 +254,8 @@ password '', socket '', owner '', port 3306); drop server 's1'; # End of 5.1 tests use test; +create table t1(a int); +insert into t1 values (1); create procedure p1 () begin DECLARE v INT DEFAULT 0; @@ -268,15 +270,13 @@ ALTER SERVER s OPTIONS (USER 'Remote'); DROP SERVER s; SET v = v + 1; END WHILE; +select a into @a from t1; # Just reset warnings END// use test; call p1(); call p1(); -Warnings: -Error 1477 The foreign server name you are trying to reference does not exist. Data source error: s -Warnings: -Error 1476 The foreign server, s, you are trying to create already exists. drop procedure p1; +drop table t1; drop server if exists s; DROP TABLE IF EXISTS federated.t1; DROP DATABASE federated; diff --git a/mysql-test/suite/federated/federated_server.test b/mysql-test/suite/federated/federated_server.test index ec952d071f2..9e883743450 100644 --- a/mysql-test/suite/federated/federated_server.test +++ b/mysql-test/suite/federated/federated_server.test @@ -62,7 +62,7 @@ eval create server 'server_two' foreign data wrapper 'mysql' options OWNER 'root'); --replace_result $SLAVE_MYPORT SLAVE_PORT -eval select * from mysql.servers; +eval select * from mysql.servers order by Server_name; DROP TABLE IF EXISTS federated.old; --replace_result $SLAVE_MYPORT SLAVE_PORT @@ -147,7 +147,7 @@ drop table federated.t1; drop server 'server_one'; drop server 'server_two'; -select * from mysql.servers; +select * from mysql.servers order by Server_name; connection slave; drop table first_db.t1; @@ -301,6 +301,8 @@ drop server 's1'; connect (other,localhost,root,,); connection master; use test; +create table t1(a int); +insert into t1 values (1); delimiter //; create procedure p1 () begin @@ -316,6 +318,7 @@ begin DROP SERVER s; SET v = v + 1; END WHILE; + select a into @a from t1; # Just reset warnings END// delimiter ;// connection other; @@ -326,6 +329,7 @@ call p1(); connection other; reap; drop procedure p1; +drop table t1; drop server if exists s; From 8147199f62a0793f2b0936d086960aa1a9fc57fc Mon Sep 17 00:00:00 2001 From: Evgeny Potemkin Date: Mon, 2 Aug 2010 16:36:41 +0400 Subject: [PATCH 104/129] Bug#55648: Server crash on MIX/MAX on maximum time value A typo in the Item_cache_datetime::val_str caused an assertion to fail on the maximum time value. mysql-test/r/func_group.result: A test case for the bug#55648. mysql-test/t/func_group.test: A test case for the bug#55648. sql/item.cc: Bug#55648: Server crash on MIX/MAX on maximum time value Corrected assertion. --- mysql-test/r/func_group.result | 11 +++++++++++ mysql-test/t/func_group.test | 10 ++++++++++ sql/item.cc | 4 ++-- 3 files changed, 23 insertions(+), 2 deletions(-) diff --git a/mysql-test/r/func_group.result b/mysql-test/r/func_group.result index 6838dcf944c..45c93971852 100644 --- a/mysql-test/r/func_group.result +++ b/mysql-test/r/func_group.result @@ -1714,3 +1714,14 @@ NULL NULL NULL NULL NULL drop table t1; # End of 5.1 tests +# +# Bug#55648: Server crash on MIX/MAX on maximum time value +# +CREATE TABLE t1(c1 TIME NOT NULL); +INSERT INTO t1 VALUES('837:59:59'); +INSERT INTO t1 VALUES('838:59:59'); +SELECT MAX(c1) FROM t1; +MAX(c1) +838:59:59 +DROP TABLE t1; +# End of the bug#55648 diff --git a/mysql-test/t/func_group.test b/mysql-test/t/func_group.test index 6dbc8a05789..2914bb15d18 100644 --- a/mysql-test/t/func_group.test +++ b/mysql-test/t/func_group.test @@ -1085,3 +1085,13 @@ drop table t1; --echo # --echo End of 5.1 tests +--echo # +--echo # Bug#55648: Server crash on MIX/MAX on maximum time value +--echo # +CREATE TABLE t1(c1 TIME NOT NULL); +INSERT INTO t1 VALUES('837:59:59'); +INSERT INTO t1 VALUES('838:59:59'); +SELECT MAX(c1) FROM t1; +DROP TABLE t1; +--echo # End of the bug#55648 + diff --git a/sql/item.cc b/sql/item.cc index 8210f4e6caf..1decb5ec426 100644 --- a/sql/item.cc +++ b/sql/item.cc @@ -7510,13 +7510,13 @@ String *Item_cache_datetime::val_str(String *str) if (cached_field_type == MYSQL_TYPE_TIME) { ulonglong time= int_value; - DBUG_ASSERT(time < TIME_MAX_VALUE); + DBUG_ASSERT(time <= TIME_MAX_VALUE); set_zero_time(<ime, MYSQL_TIMESTAMP_TIME); ltime.second= time % 100; time/= 100; ltime.minute= time % 100; time/= 100; - ltime.hour= time % 100; + ltime.hour= time; } else { From 5e92df6e0ee01cdea7865d3f0b6d02f840bf0402 Mon Sep 17 00:00:00 2001 From: Bjorn Munch Date: Tue, 3 Aug 2010 16:11:23 +0200 Subject: [PATCH 105/129] Bug #55582 mtr root detection (and if-expression execution) broken if() treated any non-numeric string as false Fixed to treat those as true instead Added some test cases Fixed missing $ in variable name in include/mix2.inc --- client/mysqltest.cc | 17 ++++++++++++++++- mysql-test/include/mix2.inc | 4 ++-- mysql-test/r/mysqltest.result | 2 ++ mysql-test/t/mysqltest.test | 19 +++++++++++++++++++ 4 files changed, 39 insertions(+), 3 deletions(-) diff --git a/client/mysqltest.cc b/client/mysqltest.cc index ba8e882f33e..4a090f5481e 100644 --- a/client/mysqltest.cc +++ b/client/mysqltest.cc @@ -2383,6 +2383,9 @@ void eval_expr(VAR *v, const char *p, const char **p_end) if ((vp= var_get(p, p_end, 0, 0))) var_copy(v, vp); + /* Apparently it is not safe to assume null-terminated string */ + v->str_val[v->str_val_len]= 0; + /* Make sure there was just a $variable and nothing else */ const char* end= *p_end + 1; if (end < expected_end) @@ -5391,8 +5394,20 @@ void do_block(enum block_cmd cmd, struct st_command* command) /* Define inner block */ cur_block++; cur_block->cmd= cmd; - cur_block->ok= (v.int_val ? TRUE : FALSE); + if (v.int_val) + { + cur_block->ok= TRUE; + } else + /* Any non-empty string which does not begin with 0 is also TRUE */ + { + p= v.str_val; + /* First skip any leading white space or unary -+ */ + while (*p && ((my_isspace(charset_info, *p) || *p == '-' || *p == '+'))) + p++; + cur_block->ok= (*p && *p != '0') ? TRUE : FALSE; + } + if (not_expr) cur_block->ok = !cur_block->ok; diff --git a/mysql-test/include/mix2.inc b/mysql-test/include/mix2.inc index b4c4a9b8836..123d049855a 100644 --- a/mysql-test/include/mix2.inc +++ b/mysql-test/include/mix2.inc @@ -1910,7 +1910,7 @@ select hex(s1) from t4; drop table t1,t2,t3,t4; } -if (test_foreign_keys) +if ($test_foreign_keys) { eval create table t1 (a int primary key,s1 varbinary(3) not null unique) engine=$engine_type; eval create table t2 (s1 binary(2) not null, constraint c foreign key(s1) references t1(s1) on update cascade) engine=$engine_type; @@ -2405,7 +2405,7 @@ drop table t1, t2, t3, t5, t6, t8, t9; } # End transactional tests -if (test_foreign_keys) +if ($test_foreign_keys) { # bug 18934, "InnoDB crashes when table uses column names like DB_ROW_ID" --error 1005 diff --git a/mysql-test/r/mysqltest.result b/mysql-test/r/mysqltest.result index 84412d2f387..721050bae19 100644 --- a/mysql-test/r/mysqltest.result +++ b/mysql-test/r/mysqltest.result @@ -393,6 +393,8 @@ true-inner again true-outer Counter is greater than 0, (counter=10) Counter is not 0, (counter=0) +Counter is true, (counter=alpha) +Beta is true 1 Testing while with not mysqltest: In included file "MYSQLTEST_VARDIR/tmp/mysqltest_while.inc": At line 64: Nesting too deeply diff --git a/mysql-test/t/mysqltest.test b/mysql-test/t/mysqltest.test index 09916f4f8cf..b88cde8c8f0 100644 --- a/mysql-test/t/mysqltest.test +++ b/mysql-test/t/mysqltest.test @@ -1105,6 +1105,25 @@ if (!$counter) echo Counter is not 0, (counter=0); } +# ---------------------------------------------------------------------------- +# Test if with some non-numerics +# ---------------------------------------------------------------------------- + +let $counter=alpha; +if ($counter) +{ + echo Counter is true, (counter=alpha); +} +let $counter= ; +if ($counter) +{ + echo oops, space is true; +} +if (beta) +{ + echo Beta is true; +} + # ---------------------------------------------------------------------------- # Test while, { and } # ---------------------------------------------------------------------------- From 81906cdf3805fe5fcea47fef11945f9adbcef4d8 Mon Sep 17 00:00:00 2001 From: Alexander Nozdrin Date: Wed, 4 Aug 2010 12:14:25 +0400 Subject: [PATCH 106/129] Fix default.conf. --- .bzr-mysql/default.conf | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.bzr-mysql/default.conf b/.bzr-mysql/default.conf index fcb3cab2de6..43d479a1043 100644 --- a/.bzr-mysql/default.conf +++ b/.bzr-mysql/default.conf @@ -1,4 +1,4 @@ [MYSQL] post_commit_to = "commits@lists.mysql.com" post_push_to = "commits@lists.mysql.com" -tree_name = "mysql-trunk" +tree_name = "mysql-5.5" From 2d2da6e79359668111b24734be0f9011f289a281 Mon Sep 17 00:00:00 2001 From: Bjorn Munch Date: Wed, 4 Aug 2010 10:52:45 +0200 Subject: [PATCH 107/129] Bug #55582 mtr root detection (and if-expression execution) broken Follow-up patch: added test cases for -0 and while --- mysql-test/r/mysqltest.result | 1 + mysql-test/t/mysqltest.test | 11 +++++++++++ 2 files changed, 12 insertions(+) diff --git a/mysql-test/r/mysqltest.result b/mysql-test/r/mysqltest.result index 721050bae19..e4f68d68c3f 100644 --- a/mysql-test/r/mysqltest.result +++ b/mysql-test/r/mysqltest.result @@ -395,6 +395,7 @@ Counter is greater than 0, (counter=10) Counter is not 0, (counter=0) Counter is true, (counter=alpha) Beta is true +while with string, only once 1 Testing while with not mysqltest: In included file "MYSQLTEST_VARDIR/tmp/mysqltest_while.inc": At line 64: Nesting too deeply diff --git a/mysql-test/t/mysqltest.test b/mysql-test/t/mysqltest.test index b88cde8c8f0..031c51a0720 100644 --- a/mysql-test/t/mysqltest.test +++ b/mysql-test/t/mysqltest.test @@ -1119,10 +1119,21 @@ if ($counter) { echo oops, space is true; } +let $counter=-0; +if ($counter) +{ + echo oops, -0 is true; +} if (beta) { echo Beta is true; } +let $counter=gamma; +while ($counter) +{ + echo while with string, only once; + let $counter=000; +} # ---------------------------------------------------------------------------- # Test while, { and } From de6b5b0a326af86c9425f9296da188d2e8000f3e Mon Sep 17 00:00:00 2001 From: Alexander Nozdrin Date: Wed, 4 Aug 2010 13:14:09 +0400 Subject: [PATCH 108/129] Fix default.conf. --- .bzr-mysql/default.conf | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.bzr-mysql/default.conf b/.bzr-mysql/default.conf index 43d479a1043..7d0379c08a0 100644 --- a/.bzr-mysql/default.conf +++ b/.bzr-mysql/default.conf @@ -1,4 +1,4 @@ [MYSQL] post_commit_to = "commits@lists.mysql.com" post_push_to = "commits@lists.mysql.com" -tree_name = "mysql-5.5" +tree_name = "mysql-5.5-bugfixing" From b94d86215d3f785962cfe2398a2b4ad9b68c028e Mon Sep 17 00:00:00 2001 From: Vladislav Vaintroub Date: Thu, 5 Aug 2010 18:38:24 +0200 Subject: [PATCH 109/129] Build cleanups - Simplify sql-bench installation, do not try to resolve names : this leads to probem if builddir is symlink located on different filesystem. (reported by alik) - Make WITHOUT_XXX (disabling plugin) work for DEFAULT plugins. Prior to the patch is behaved just like MANDATORY. - LINK_LIBRARIES in MYSQL_ADD_PLUGIN had no effect for statically linked plugins. - Fix constant rebuild of initdb target on Windows. --- CMakeLists.txt | 3 ++- cmake/plugin.cmake | 29 +++++++++++++++++++++++------ scripts/CMakeLists.txt | 1 + sql-bench/CMakeLists.txt | 33 ++++++++++++++++++--------------- sql/CMakeLists.txt | 11 ++++++----- 5 files changed, 50 insertions(+), 27 deletions(-) diff --git a/CMakeLists.txt b/CMakeLists.txt index fed3d61be8f..9a2107bca48 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -46,7 +46,8 @@ OPTION(COMMUNITY_BUILD "Set to true if this is a community build" ON) SET(MANUFACTURER_DOCSTRING "Set the entity that appears as the manufacturer of packages that support a manufacturer field.") IF(NOT DEFINED MANUFACTURER) - SET(MANUFACTURER "Built from Source" CACHE BOOL ${MANUFACTURER_DOCSTRING}) + SET(MANUFACTURER "Built from Source" CACHE STRING ${MANUFACTURER_DOCSTRING}) + MARK_AS_ADVANCED(MANUFACTURER) ENDIF() # We choose to provide WITH_DEBUG as alias to standard CMAKE_BUILD_TYPE=Debug diff --git a/cmake/plugin.cmake b/cmake/plugin.cmake index 94edfb8741a..138901dfa8a 100644 --- a/cmake/plugin.cmake +++ b/cmake/plugin.cmake @@ -57,11 +57,17 @@ MACRO(MYSQL_ADD_PLUGIN) SET(WITHOUT_NDBCLUSTER 1) ENDIF() + IF(ARG_DEFAULT) + IF(NOT DEFINED WITH_${plugin} AND + NOT DEFINED WITH_${plugin}_STORAGE_ENGINE) + SET(WITH_${plugin} 1) + ENDIF() + ENDIF() + IF(WITH_${plugin}_STORAGE_ENGINE OR WITH_{$plugin} OR WITH_ALL OR WITH_MAX - OR ARG_DEFAULT AND NOT WITHOUT_${plugin}_STORAGE_ENGINE AND NOT WITHOUT_${plugin} AND NOT ARG_MODULE_ONLY) @@ -88,6 +94,7 @@ MACRO(MYSQL_ADD_PLUGIN) IF(NOT ARG_DEPENDENCIES) SET(ARG_DEPENDENCIES) ENDIF() + SET(BUILD_PLUGIN 1) # Build either static library or module IF (WITH_${plugin} AND NOT ARG_MODULE_ONLY) ADD_LIBRARY(${target} STATIC ${SOURCES}) @@ -148,9 +155,6 @@ MACRO(MYSQL_ADD_PLUGIN) DTRACE_INSTRUMENT(${target}) SET_TARGET_PROPERTIES (${target} PROPERTIES PREFIX "" COMPILE_DEFINITIONS "MYSQL_DYNAMIC_PLUGIN") - IF(ARG_LINK_LIBRARIES) - TARGET_LINK_LIBRARIES (${target} ${ARG_LINK_LIBRARIES}) - ENDIF() TARGET_LINK_LIBRARIES (${target} mysqlservices) # Plugin uses symbols defined in mysqld executable. @@ -165,17 +169,30 @@ MACRO(MYSQL_ADD_PLUGIN) ENDIF() ADD_DEPENDENCIES(${target} GenError ${ARG_DEPENDENCIES}) - IF(NOT ARG_MODULE_ONLY) + IF(NOT ARG_MODULE_ONLY) # set cached variable, e.g with checkbox in GUI SET(${with_var} OFF CACHE BOOL "Link ${plugin} statically to the server" FORCE) - ENDIF() + ENDIF() SET_TARGET_PROPERTIES(${target} PROPERTIES OUTPUT_NAME "${ARG_MODULE_OUTPUT_NAME}") # Install dynamic library MYSQL_INSTALL_TARGETS(${target} DESTINATION ${INSTALL_PLUGINDIR} COMPONENT Server) INSTALL_DEBUG_TARGET(${target} DESTINATION ${INSTALL_PLUGINDIR}/debug) + ELSE() + IF(WITHOUT_${plugin}) + # Update cache variable + STRING(REPLACE "WITH_" "WITHOUT_" without_var ${with_var}) + SET(${without_var} ON CACHE BOOL "Don't build ${plugin}" + FORCE) + ENDIF() + SET(BUILD_PLUGIN 0) ENDIF() + + IF(BUILD_PLUGIN AND ARG_LINK_LIBRARIES) + TARGET_LINK_LIBRARIES (${target} ${ARG_LINK_LIBRARIES}) + ENDIF() + ENDMACRO() diff --git a/scripts/CMakeLists.txt b/scripts/CMakeLists.txt index ced207da98b..188bd4bdaa5 100644 --- a/scripts/CMakeLists.txt +++ b/scripts/CMakeLists.txt @@ -24,6 +24,7 @@ ENDIF() # Build mysql_fix_privilege_tables.sql (concatenate 2 sql scripts) IF(NOT WIN32 OR CMAKE_CROSSCOMPILING) FIND_PROGRAM(CAT_EXECUTABLE cat DOC "path to the executable") + MARK_AS_ADVANCED(CAT_EXECUTABLE) ENDIF() IF(CAT_EXECUTABLE) diff --git a/sql-bench/CMakeLists.txt b/sql-bench/CMakeLists.txt index be0aeca70b0..95f69fd2a8e 100644 --- a/sql-bench/CMakeLists.txt +++ b/sql-bench/CMakeLists.txt @@ -14,12 +14,6 @@ # Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA # Install sql-bench files -FILE(GLOB all_files -${CMAKE_SOURCE_DIR}/sql-bench/* -${CMAKE_SOURCE_DIR}/sql-bench/Data/ATIS/* -${CMAKE_SOURCE_DIR}/sql-bench/Data/Wisconsin/* -${CMAKE_SOURCE_DIR}/sql-bench/limits/* -) IF(NOT INSTALL_SQLBENCHDIR) RETURN() @@ -31,30 +25,39 @@ ELSE() SET(prefix ${INSTALL_SQLBENCHDIR}/) ENDIF() -GET_FILENAME_COMPONENT(basedir ${CMAKE_SOURCE_DIR} ABSOLUTE) +INSTALL(DIRECTORY ${CMAKE_CURRENT_SOURCE_DIR}/Data/ATIS + DESTINATION ${prefix}sql-bench/Data) + +INSTALL(DIRECTORY ${CMAKE_CURRENT_SOURCE_DIR}/Data/Wisconsin + DESTINATION ${prefix}sql-bench/Data) + +INSTALL(DIRECTORY ${CMAKE_CURRENT_SOURCE_DIR}/limits + DESTINATION ${prefix}sql-bench) + +FILE(GLOB all_files ${CMAKE_CURRENT_SOURCE_DIR}/*) + FOREACH(file ${all_files}) IF(NOT IS_DIRECTORY ${file} AND NOT ${file} MATCHES "Make|as3ap|/example$" ) - FILE(RELATIVE_PATH relpath ${basedir} ${file}) - SET(target_relpath ${relpath}) GET_FILENAME_COMPONENT(ext ${file} EXT) - GET_FILENAME_COMPONENT(dir ${relpath} PATH) + GET_FILENAME_COMPONENT(name ${file} NAME) + SET(target ${name}) IF(ext MATCHES ".sh$") # Those are perl files actually - STRING(REPLACE ".sh" "" target_relpath ${target_relpath} ) + STRING(REPLACE ".sh" "" target ${target} ) IF(WIN32) IF(NOT ext MATCHES ".pl") - SET(target_relpath "${target_relpath}.pl") + SET(target "${target}.pl") ENDIF() ENDIF() ENDIF() - SET(target "${CMAKE_BINARY_DIR}/${target_relpath}") + SET(target "${CMAKE_CURRENT_BINARY_DIR}/${target}") CONFIGURE_FILE(${file} ${target} COPYONLY) IF (ext MATCHES ".bat") IF(WIN32) - INSTALL(FILES ${target} DESTINATION ${prefix}${dir}) + INSTALL(FILES ${target} DESTINATION ${prefix}sql-bench) ENDIF() ELSE() - INSTALL(FILES ${target} DESTINATION ${prefix}${dir}) + INSTALL(FILES ${target} DESTINATION ${prefix}sql-bench) ENDIF() ENDIF() ENDFOREACH() diff --git a/sql/CMakeLists.txt b/sql/CMakeLists.txt index e8a594c4d8b..879e1bbed90 100644 --- a/sql/CMakeLists.txt +++ b/sql/CMakeLists.txt @@ -42,7 +42,6 @@ SET (SQL_SOURCE ../sql-common/client.c derror.cc des_key_file.cc discover.cc ../libmysql/errmsg.c field.cc field_conv.cc filesort.cc gstream.cc sha2.cc - ha_partition.cc handler.cc hash_filo.h sql_plugin_services.h hostname.cc init.cc item.cc item_buff.cc item_cmpfunc.cc item_create.cc item_func.cc item_geofunc.cc item_row.cc @@ -266,18 +265,20 @@ IF(WIN32 AND MYSQLD_EXECUTABLE) ENDIF() MAKE_DIRECTORY(${CMAKE_CURRENT_BINARY_DIR}/data) ADD_CUSTOM_COMMAND( - OUTPUT ${CMAKE_CURRENT_BINARY_DIR}/data/mysql/user.frm + OUTPUT initdb.dep COMMAND ${CMAKE_COMMAND} ${CONFIG_PARAM} -P ${CMAKE_CURRENT_BINARY_DIR}/create_initial_db.cmake WORKING_DIRECTORY ${CMAKE_CURRENT_BINARY_DIR}/data + COMMAND ${CMAKE_COMMAND} -E touch initdb.dep + WORKING_DIRECTORY ${CMAKE_CURRENT_BINARY_DIR} DEPENDS mysqld ) ADD_CUSTOM_TARGET(initial_database ALL - DEPENDS ${CMAKE_CURRENT_BINARY_DIR}/data/mysql/user.frm + DEPENDS initdb.dep ) - INSTALL(DIRECTORY ${CMAKE_CURRENT_BINARY_DIR}/data DESTINATION . COMPONENT DataFiles - PATTERN "bootstrap.sql" EXCLUDE) + INSTALL(DIRECTORY ${CMAKE_CURRENT_BINARY_DIR}/data DESTINATION . + COMPONENT DataFiles PATTERN "initdb.dep" EXCLUDE PATTERN "bootstrap.sql" EXCLUDE) ELSE() # Not windows or cross compiling, just install an empty directory INSTALL(FILES ${DUMMY_FILE} DESTINATION data/mysql) From 9d503b77e40436e1e90c8f383fddf210026b9623 Mon Sep 17 00:00:00 2001 From: Davi Arnaut Date: Thu, 5 Aug 2010 09:32:23 -0300 Subject: [PATCH 110/129] Bug#55601: BUILD/check-cpu in mysql-trunk is broken on Mac OS X 10.5 Restore the original behavior of check-cpu with respect to core2. It isn't used as a actual target processor type, but as a mean to perform other kinds of architecture checks. --- BUILD/check-cpu | 146 +++++++++++++++++++++++++----------------------- 1 file changed, 75 insertions(+), 71 deletions(-) diff --git a/BUILD/check-cpu b/BUILD/check-cpu index f9f5d423f4f..585043de67c 100755 --- a/BUILD/check-cpu +++ b/BUILD/check-cpu @@ -7,6 +7,79 @@ # check_cpu_args : Arguments for GCC compiler settings # +check_compiler_cpu_flags () { + # different compiler versions have different option names + # for CPU specific command line options + if test -z "$CC" ; then + cc="gcc"; + else + cc=$CC + fi + + # check if compiler is gcc and dump its version + cc_verno=`$cc -dumpversion 2>/dev/null` + if test "x$?" = "x0" ; then + set -- `echo $cc_verno | tr '.' ' '` + cc_ver="GCC" + cc_major=$1 + cc_minor=$2 + cc_patch=$3 + cc_comp=`expr $cc_major '*' 100 '+' $cc_minor` + fi + + case "$cc_ver--$cc_verno" in + *GCC*) + # different gcc backends (and versions) have different CPU flags + case `gcc -dumpmachine` in + i?86-* | x86_64-*) + if test "$cc_comp" -lt 304 ; then + check_cpu_cflags="-mcpu=${cpu_arg}" + elif test "$cc_comp" -ge 402 ; then + check_cpu_cflags="-mtune=native" + else + check_cpu_cflags="-mtune=${cpu_arg}" + fi + ;; + ppc-*) + check_cpu_cflags="-mcpu=${cpu_arg} -mtune=${cpu_arg}" + ;; + *) + check_cpu_cflags="" + return + ;; + esac + ;; + 2.95.*) + # GCC 2.95 doesn't expose its name in --version output + check_cpu_cflags="-m${cpu_arg}" + ;; + *) + check_cpu_cflags="" + return + ;; + esac + + # now we check whether the compiler really understands the cpu type + touch __test.c + + while [ "$cpu_arg" ] ; do + printf "testing $cpu_arg ... " >&2 + + # compile check + eval "$cc -c $check_cpu_cflags __test.c" 2>/dev/null + if test "x$?" = "x0" ; then + echo ok >&2 + break; + fi + + echo failed >&2 + check_cpu_cflags="" + break; + done + rm __test.* + return 0 +} + check_cpu () { CPUINFO=/proc/cpuinfo if test -n "$TEST_CPUINFO" ; then @@ -179,83 +252,14 @@ check_cpu () { return fi - # different compiler versions have different option names - # for CPU specific command line options - if test -z "$CC" ; then - cc="gcc"; - else - cc=$CC + if test "x$compiler" = "x" ; then + check_compiler_cpu_flags fi if test "x$core2" = "xyes" ; then cpu_arg="core2" fi - if test "x$compiler" != "x" ; then - return 0 - fi - - # check if compiler is gcc and dump its version - cc_verno=`$cc -dumpversion 2>/dev/null` - if test "x$?" = "x0" ; then - set -- `echo $cc_verno | tr '.' ' '` - cc_ver="GCC" - cc_major=$1 - cc_minor=$2 - cc_patch=$3 - cc_comp=`expr $cc_major '*' 100 '+' $cc_minor` - fi - - case "$cc_ver--$cc_verno" in - *GCC*) - # different gcc backends (and versions) have different CPU flags - case `gcc -dumpmachine` in - i?86-* | x86_64-*) - if test "$cc_comp" -lt 304 ; then - check_cpu_cflags="-mcpu=${cpu_arg}" - elif test "$cc_comp" -ge 402 ; then - check_cpu_cflags="-mtune=native" - else - check_cpu_cflags="-mtune=${cpu_arg}" - fi - ;; - ppc-*) - check_cpu_cflags="-mcpu=${cpu_arg} -mtune=${cpu_arg}" - ;; - *) - check_cpu_cflags="" - return - ;; - esac - ;; - 2.95.*) - # GCC 2.95 doesn't expose its name in --version output - check_cpu_cflags="-m${cpu_arg}" - ;; - *) - check_cpu_cflags="" - return - ;; - esac - - # now we check whether the compiler really understands the cpu type - touch __test.c - - while [ "$cpu_arg" ] ; do - printf "testing $cpu_arg ... " >&2 - - # compile check - eval "$cc -c $check_cpu_cflags __test.c" 2>/dev/null - if test "x$?" = "x0" ; then - echo ok >&2 - break; - fi - - echo failed >&2 - check_cpu_cflags="" - break; - done - rm __test.* return 0 } From 76382d2746adc7f0d0a16e3addd317e559261a26 Mon Sep 17 00:00:00 2001 From: Davi Arnaut Date: Fri, 6 Aug 2010 09:59:38 -0300 Subject: [PATCH 111/129] Bug#34043: Server loops excessively in _checkchunk() when safemalloc is enabled Post-merge fix: remove --with-debug=full, it was only used for safemalloc. BUILD/compile-pentium-mysqlfs-debug: Remove build script for a feature that is long gone. --- BUILD/Makefile.am | 1 - BUILD/SETUP.sh | 12 ++---------- BUILD/build_mccge.sh | 18 ++---------------- BUILD/compile-ndb-autotest | 12 +----------- BUILD/compile-pentium-debug | 1 - BUILD/compile-pentium-debug-max | 1 - BUILD/compile-pentium-debug-max-no-ndb | 1 - BUILD/compile-pentium-debug-openssl | 2 +- BUILD/compile-pentium-debug-yassl | 2 +- BUILD/compile-pentium-mysqlfs-debug | 11 ----------- BUILD/compile-pentium64-debug | 1 - BUILD/compile-pentium64-debug-max | 1 - CMakeLists.txt | 14 ++++---------- cmake/configure.pl | 5 ----- config/ac-macros/ha_ndbcluster.m4 | 2 +- configure.in | 10 +--------- storage/innobase/CMakeLists.txt | 2 +- 17 files changed, 14 insertions(+), 82 deletions(-) delete mode 100755 BUILD/compile-pentium-mysqlfs-debug diff --git a/BUILD/Makefile.am b/BUILD/Makefile.am index c5732d43fbf..56c86e7a80c 100644 --- a/BUILD/Makefile.am +++ b/BUILD/Makefile.am @@ -52,7 +52,6 @@ EXTRA_DIST = FINISH.sh \ compile-pentium-icc-yassl \ compile-pentium-max \ compile-pentium-myodbc \ - compile-pentium-mysqlfs-debug \ compile-pentium-pgcc \ compile-pentium-valgrind-max \ compile-pentium64 \ diff --git a/BUILD/SETUP.sh b/BUILD/SETUP.sh index afb8eca08f2..a23a801e7e0 100755 --- a/BUILD/SETUP.sh +++ b/BUILD/SETUP.sh @@ -14,7 +14,6 @@ Usage: $0 [-h|-n] [configure-options] -h, --help Show this help message. -n, --just-print Don't actually run any commands; just print them. -c, --just-configure Stop after running configure. - --with-debug=full Build with full debug. --warning-mode=[old|pedantic|maintainer] Influences the debug flags. Old is default. --prefix=path Build with prefix 'path'. @@ -30,8 +29,6 @@ parse_options() case "$1" in --prefix=*) prefix=`get_key_value "$1"`;; - --with-debug=full) - full_debug="=full";; --warning-mode=*) warning_mode=`get_key_value "$1"`;; -c | --just-configure) @@ -60,7 +57,6 @@ fi prefix="/usr/local/mysql" just_print= just_configure= -full_debug= warning_mode= maintainer_mode= @@ -116,7 +112,6 @@ else cxx_warnings="$warnings -Wno-unused-parameter" # cxx_warnings="$cxx_warnings -Woverloaded-virtual -Wsign-promo" cxx_warnings="$cxx_warnings -Wctor-dtor-privacy -Wnon-virtual-dtor" -# Added unless --with-debug=full debug_extra_cflags="-O0 -g3 -gdwarf-2" fi @@ -141,11 +136,8 @@ base_cxxflags="-felide-constructors -fno-exceptions -fno-rtti" # Be as fast as we can be without losing our ability to backtrace. fast_cflags="-O3 -fno-omit-frame-pointer" -debug_configs="--with-debug$full_debug" -if [ -z "$full_debug" ] -then - debug_cflags="$debug_cflags $debug_extra_cflags" -fi +debug_configs="--with-debug" +debug_cflags="$debug_cflags $debug_extra_cflags" # # Configuration options. diff --git a/BUILD/build_mccge.sh b/BUILD/build_mccge.sh index aae017aa54d..cb70a8cef67 100755 --- a/BUILD/build_mccge.sh +++ b/BUILD/build_mccge.sh @@ -148,7 +148,6 @@ Usage: $0 [options] --extended-help Show extended help message --without-debug Build non-debug version --with-debug Build debug version - --with-debug=full Build with full debug. --configure-only Stop after running configure. --use-autotools Start by running autoconf, automake,.. tools --no-autotools Start from configure @@ -262,10 +261,6 @@ extended_usage() This flag prevents the use of GPL libraries which cannot be used under a commercial license, such as the readline library. - --with-debug[=full] - This option will ensure that the version is built with debug - information enabled; the optimisation level is decreased to -O. - --developer This option changes a number of things to make the version built more appropriate to the debugging and testing needs of developers. @@ -658,11 +653,6 @@ parse_options() --datadir=*) datadir=`get_key_value "$1"` ;; - --with-debug=full) - full_debug="=full" - with_debug_flag="yes" - fast_flag="no" - ;; --without-debug) with_debug_flag="no" if test "x$fast_flag" != "xyes" ; then @@ -1044,10 +1034,7 @@ set_warning_flags() # C++ warnings cxx_warnings="$warnings -Woverloaded-virtual -Wsign-promo -Wreorder" cxx_warnings="$warnings -Wctor-dtor-privacy -Wnon-virtual-dtor" -# Added unless --with-debug=full - if test "x$full_debug" = "x" ; then - compiler_flags="$compiler_flags -Wuninitialized" - fi + compiler_flags="$compiler_flags -Wuninitialized" elif test "x$warning_mode" = "xpedantic" ; then warnings="-W -Wall -ansi -pedantic -Wno-long-long -D_POSIX_SOURCE" c_warnings="$warnings" @@ -1113,7 +1100,7 @@ set_base_configs() base_configs="$base_configs --localstatedir=$datadir" fi if test "x$with_debug_flag" = "xyes" ; then - base_configs="$base_configs --with-debug$full_debug" + base_configs="$base_configs --with-debug" fi base_configs="$base_configs --enable-local-infile" base_configs="$base_configs --enable-thread-safe-client" @@ -1546,7 +1533,6 @@ gpl="yes" version_text= developer_flag="no" just_configure= -full_debug= warning_mode= with_flags= error_inject_flag= diff --git a/BUILD/compile-ndb-autotest b/BUILD/compile-ndb-autotest index be28cc28346..6f86eeb7464 100755 --- a/BUILD/compile-ndb-autotest +++ b/BUILD/compile-ndb-autotest @@ -4,16 +4,6 @@ path=`dirname $0` . "$path/SETUP.sh" extra_configs="$max_configs --with-ndb-test --with-ndb-ccflags='-DERROR_INSERT'" -if [ "$full_debug" ] -then - extra_flags="$debug_cflags" - c_warnings="$c_warnings $debug_extra_warnings" - cxx_warnings="$cxx_warnings $debug_extra_warnings" - extra_configs="$debug_configs $extra_configs" -else - extra_flags="$fast_cflags" -fi - -extra_flags="$extra_flags $max_cflags -g" +extra_flags="$fast_cflags $max_cflags -g" . "$path/FINISH.sh" diff --git a/BUILD/compile-pentium-debug b/BUILD/compile-pentium-debug index 3f4027c5dd6..37381cc47df 100755 --- a/BUILD/compile-pentium-debug +++ b/BUILD/compile-pentium-debug @@ -1,7 +1,6 @@ #! /bin/sh path=`dirname $0` -set -- "$@" --with-debug=full . "$path/SETUP.sh" extra_flags="$pentium_cflags $debug_cflags" diff --git a/BUILD/compile-pentium-debug-max b/BUILD/compile-pentium-debug-max index 941a63a209f..5c56ceb37ba 100755 --- a/BUILD/compile-pentium-debug-max +++ b/BUILD/compile-pentium-debug-max @@ -1,7 +1,6 @@ #! /bin/sh path=`dirname $0` -set -- "$@" --with-debug=full . "$path/SETUP.sh" extra_flags="$pentium_cflags $debug_cflags" diff --git a/BUILD/compile-pentium-debug-max-no-ndb b/BUILD/compile-pentium-debug-max-no-ndb index 3f7a7904050..f1e14b73ecd 100755 --- a/BUILD/compile-pentium-debug-max-no-ndb +++ b/BUILD/compile-pentium-debug-max-no-ndb @@ -1,7 +1,6 @@ #! /bin/sh path=`dirname $0` -set -- "$@" --with-debug=full . "$path/SETUP.sh" extra_flags="$pentium_cflags $debug_cflags" diff --git a/BUILD/compile-pentium-debug-openssl b/BUILD/compile-pentium-debug-openssl index 2e24dbfd2f1..7026e0fde05 100755 --- a/BUILD/compile-pentium-debug-openssl +++ b/BUILD/compile-pentium-debug-openssl @@ -6,6 +6,6 @@ path=`dirname $0` extra_flags="$pentium_cflags $debug_cflags" extra_configs="$pentium_configs $debug_configs" -extra_configs="$extra_configs --with-debug=full --with-ssl=/usr" +extra_configs="$extra_configs --with-debug --with-ssl=/usr" . "$path/FINISH.sh" diff --git a/BUILD/compile-pentium-debug-yassl b/BUILD/compile-pentium-debug-yassl index 61ad2937c4a..3f9a36ce5a1 100755 --- a/BUILD/compile-pentium-debug-yassl +++ b/BUILD/compile-pentium-debug-yassl @@ -6,6 +6,6 @@ path=`dirname $0` extra_flags="$pentium_cflags $debug_cflags" extra_configs="$pentium_configs $debug_configs" -extra_configs="$extra_configs --with-debug=full --with-ssl" +extra_configs="$extra_configs --with-debug --with-ssl" . "$path/FINISH.sh" diff --git a/BUILD/compile-pentium-mysqlfs-debug b/BUILD/compile-pentium-mysqlfs-debug deleted file mode 100755 index c871200604e..00000000000 --- a/BUILD/compile-pentium-mysqlfs-debug +++ /dev/null @@ -1,11 +0,0 @@ -#! /bin/sh - -path=`dirname $0` -. "$path/SETUP.sh" - -extra_flags="$pentium_cflags $debug_cflags" -extra_configs="$pentium_configs $debug_configs $static_link" - -extra_configs="$extra_configs --with-debug=full --with-mysqlfs --without-server --without-pstack" - -. "$path/FINISH.sh" diff --git a/BUILD/compile-pentium64-debug b/BUILD/compile-pentium64-debug index 06ee672789c..7d11ee9df76 100755 --- a/BUILD/compile-pentium64-debug +++ b/BUILD/compile-pentium64-debug @@ -1,7 +1,6 @@ #! /bin/sh path=`dirname $0` -set -- "$@" --with-debug=full . "$path/SETUP.sh" extra_flags="$pentium64_cflags $debug_cflags" diff --git a/BUILD/compile-pentium64-debug-max b/BUILD/compile-pentium64-debug-max index b8b271688be..322b232a20c 100755 --- a/BUILD/compile-pentium64-debug-max +++ b/BUILD/compile-pentium64-debug-max @@ -1,7 +1,6 @@ #! /bin/sh path=`dirname $0` -set -- "$@" --with-debug=full . "$path/SETUP.sh" extra_flags="$pentium64_cflags $debug_cflags" diff --git a/CMakeLists.txt b/CMakeLists.txt index 9a2107bca48..62ade30e3a4 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -34,7 +34,6 @@ ENDIF() SET(CUSTOM_C_FLAGS $ENV{CFLAGS}) OPTION(WITH_DEBUG "Use dbug/safemutex" OFF) -OPTION(WITH_DEBUG_FULL "Use dbug and safemutex. Slow." OFF) # Distinguish between community and non-community builds, with the # default being a community build. This does not impact the feature @@ -60,7 +59,7 @@ SET(BUILDTYPE_DOCSTRING "Choose the type of build, options are: None(CMAKE_CXX_FLAGS or CMAKE_C_FLAGS used) Debug Release RelWithDebInfo MinSizeRel") -IF(WITH_DEBUG OR WITH_DEBUG_FULL) +IF(WITH_DEBUG) SET(CMAKE_BUILD_TYPE "Debug" CACHE STRING ${BUILDTYPE_DOCSTRING} FORCE) SET(OLD_WITH_DEBUG 1 CACHE INTERNAL "" FORCE) ELSEIF(NOT HAVE_CMAKE_BUILD_TYPE OR OLD_WITH_DEBUG) @@ -202,15 +201,10 @@ ENDIF() # Add safemutex for debug configurations, except on Windows # (safemutex has never worked on Windows) -IF(WITH_DEBUG OR WITH_DEBUG_FULL AND NOT WIN32) +IF(WITH_DEBUG AND NOT WIN32) FOREACH(LANG C CXX) - IF(WITH_DEBUG_FULL) - SET(CMAKE_${LANG}_FLAGS_DEBUG - "${CMAKE_${LANG}_FLAGS_DEBUG} -DSAFE_MUTEX") - ELSE() - SET(CMAKE_${LANG}_FLAGS_DEBUG - "${CMAKE_${LANG}_FLAGS_DEBUG} -DSAFE_MUTEX") - ENDIF() + SET(CMAKE_${LANG}_FLAGS_DEBUG + "${CMAKE_${LANG}_FLAGS_DEBUG} -DSAFE_MUTEX") ENDFOREACH() ENDIF() diff --git a/cmake/configure.pl b/cmake/configure.pl index 5be47ce5a31..1dc8080810c 100644 --- a/cmake/configure.pl +++ b/cmake/configure.pl @@ -179,11 +179,6 @@ foreach my $option (@ARGV) $cmakeargs = $cmakeargs." -DMYSQL_DATADIR=".substr($option,14); next; } - if ($option =~ /with-debug=full/) - { - $cmakeargs = $cmakeargs." -DWITH_DEBUG_FULL=1"; - next; - } if ($option =~ /mysql-maintainer-mode/) { $cmakeargs = $cmakeargs." -DMYSQL_MAINTAINER_MODE=" . diff --git a/config/ac-macros/ha_ndbcluster.m4 b/config/ac-macros/ha_ndbcluster.m4 index 3718b64f688..533dba09feb 100644 --- a/config/ac-macros/ha_ndbcluster.m4 +++ b/config/ac-macros/ha_ndbcluster.m4 @@ -206,7 +206,7 @@ AC_DEFUN([MYSQL_SETUP_NDBCLUSTER], [ NDB_DEFS="-DNDB_DEBUG_FULL -DVM_TRACE -DERROR_INSERT -DARRAY_GUARD" else # no extra ndb debug but still do asserts if debug version - if test "$with_debug" = "yes" -o "$with_debug" = "full" + if test "$with_debug" = "yes" then NDB_DEFS="" else diff --git a/configure.in b/configure.in index 7121a521f87..93a447919da 100644 --- a/configure.in +++ b/configure.in @@ -1732,22 +1732,14 @@ then fi AC_ARG_WITH(debug, - [ --with-debug Add debug code - --with-debug=full Add debug code (adds memory checker, very slow)], + [AS_HELP_STRING([--with-debug], [Add debug code @<:@default=no@:>@])] [with_debug=$withval], [with_debug=no]) if test "$with_debug" = "yes" then - # Medium debug. AC_DEFINE([DBUG_ON], [1], [Use libdbug]) CFLAGS="$DEBUG_CFLAGS $DEBUG_OPTIMIZE_CC -DSAFE_MUTEX $CFLAGS" CXXFLAGS="$DEBUG_CXXFLAGS $DEBUG_OPTIMIZE_CXX -DSAFE_MUTEX $CXXFLAGS" -elif test "$with_debug" = "full" -then - # Full debug. Very slow in some cases - AC_DEFINE([DBUG_ON], [1], [Use libdbug]) - CFLAGS="$DEBUG_CFLAGS -DSAFE_MUTEX $CFLAGS" - CXXFLAGS="$DEBUG_CXXFLAGS -DSAFE_MUTEX $CXXFLAGS" else # Optimized version. No debug AC_DEFINE([DBUG_OFF], [1], [Don't use libdbug]) diff --git a/storage/innobase/CMakeLists.txt b/storage/innobase/CMakeLists.txt index 218dbad2df0..2575580d646 100644 --- a/storage/innobase/CMakeLists.txt +++ b/storage/innobase/CMakeLists.txt @@ -43,7 +43,7 @@ ENDIF() # Enable InnoDB's UNIV_DEBUG if MySQL's WITH_DEBUG[_FULL] is defined # enable when this bug is resolved: # Bug#54861 Additional connections not handled properly in mtr --embedded -#IF(WITH_DEBUG OR WITH_DEBUG_FULL) +#IF(WITH_DEBUG) # ADD_DEFINITIONS("-DUNIV_DEBUG") #ENDIF() From 4c44e2a74644c5cf9404f36411c329f62733a7ea Mon Sep 17 00:00:00 2001 From: Davi Arnaut Date: Mon, 9 Aug 2010 10:23:14 -0300 Subject: [PATCH 112/129] Bug#34043: Server loops excessively in _checkchunk() when safemalloc is enabled Post-merge fix: add missing comma. --- configure.in | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/configure.in b/configure.in index 93a447919da..e12214524fa 100644 --- a/configure.in +++ b/configure.in @@ -1732,7 +1732,7 @@ then fi AC_ARG_WITH(debug, - [AS_HELP_STRING([--with-debug], [Add debug code @<:@default=no@:>@])] + [AS_HELP_STRING([--with-debug], [Add debug code @<:@default=no@:>@])], [with_debug=$withval], [with_debug=no]) if test "$with_debug" = "yes" From 7b7efa1261720e6c6ad76cbe9a5d922ba2dd7fc2 Mon Sep 17 00:00:00 2001 From: Davi Arnaut Date: Mon, 9 Aug 2010 10:23:55 -0300 Subject: [PATCH 113/129] Remove error injection option, it's not being used. --- CMakeLists.txt | 7 ------- configure.in | 15 --------------- 2 files changed, 22 deletions(-) diff --git a/CMakeLists.txt b/CMakeLists.txt index 62ade30e3a4..3ba9e1cf7f9 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -161,13 +161,6 @@ IF(ENABLE_DEBUG_SYNC) SET(CMAKE_C_FLAGS_DEBUG "${CMAKE_C_FLAGS_DEBUG} -DENABLED_DEBUG_SYNC") ENDIF() -OPTION(WITH_ERROR_INJECT - "Enable error injection in MySQL Server (debug builds only)" OFF) -IF(WITH_ERROR_INJECT) - SET(CMAKE_CXX_FLAGS_DEBUG "${CMAKE_CXX_FLAGS_DEBUG} -DERROR_INJECT_SUPPORT") - SET(CMAKE_C_FLAGS_DEBUG "${CMAKE_C_FLAGS_DEBUG} -DERROR_INJECT_SUPPORT") -ENDIF() - OPTION(ENABLED_LOCAL_INFILE "If we should should enable LOAD DATA LOCAL by default" ${IF_WIN}) MARK_AS_ADVANCED(ENABLED_LOCAL_INFILE) diff --git a/configure.in b/configure.in index e12214524fa..238cfc50a68 100644 --- a/configure.in +++ b/configure.in @@ -1775,21 +1775,6 @@ else AC_MSG_RESULT([no]) fi -# If we should allow error injection tests -AC_ARG_WITH(error-inject, - AC_HELP_STRING([--with-error-inject],[Enable error injection in MySQL Server]), - [ with_error_inject=$withval ], - [ with_error_inject=no ]) - -if test $with_debug != "no" -then - if test "$with_error_inject" = "yes" - then - AC_DEFINE([ERROR_INJECT_SUPPORT], [1], - [Enable error injection in MySQL Server]) - fi -fi - AC_ARG_WITH([fast-mutexes], AC_HELP_STRING([--with-fast-mutexes], [Compile with fast mutexes (default is disabled)]), From d8d55a57d5b09934a94b3542f64b0c0d40113697 Mon Sep 17 00:00:00 2001 From: Jonathan Perkin Date: Mon, 9 Aug 2010 14:27:04 +0100 Subject: [PATCH 114/129] Apply wlad's fix for bug#55215 --- .bzr-mysql/default.conf | 2 +- scripts/CMakeLists.txt | 64 +++++++++++++++++++---------------------- scripts/mysql_config.sh | 2 +- 3 files changed, 31 insertions(+), 37 deletions(-) diff --git a/.bzr-mysql/default.conf b/.bzr-mysql/default.conf index 43d479a1043..e6d5aedcd5f 100644 --- a/.bzr-mysql/default.conf +++ b/.bzr-mysql/default.conf @@ -1,4 +1,4 @@ [MYSQL] post_commit_to = "commits@lists.mysql.com" post_push_to = "commits@lists.mysql.com" -tree_name = "mysql-5.5" +tree_name = "mysql-5.5-itch" diff --git a/scripts/CMakeLists.txt b/scripts/CMakeLists.txt index ced207da98b..5831679828c 100644 --- a/scripts/CMakeLists.txt +++ b/scripts/CMakeLists.txt @@ -1,4 +1,3 @@ -# Copyright (C) 2006 MySQL AB # # 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 @@ -251,43 +250,38 @@ IF(POLICY CMP0007) CMAKE_POLICY(SET CMP0007 OLD) ENDIF() -LIST(REMOVE_ITEM mysqlclient_LIB_DEPENDS "") -LIST(REMOVE_DUPLICATES mysqlclient_LIB_DEPENDS) -FOREACH(lib ${mysqlclient_LIB_DEPENDS}) - # Filter out "general", it is not a library, just CMake hint - IF(NOT lib STREQUAL "general" AND NOT CLIENT_LIBS MATCHES "-l${lib} ") - IF (lib MATCHES "^\\-l") - SET(CLIENT_LIBS "${CLIENT_LIBS} ${lib} ") - ELSEIF(lib MATCHES "^/") - # Full path, convert to just filename, strip "lib" prefix and extension - GET_FILENAME_COMPONENT(lib "${lib}" NAME_WE) - STRING(REGEX REPLACE "^lib" "" lib "${lib}") - SET(CLIENT_LIBS "${CLIENT_LIBS}-l${lib} " ) - ELSE() - SET(CLIENT_LIBS "${CLIENT_LIBS}-l${lib} " ) - ENDIF() +# Extract dependencies using CMake's internal ${target}_LIB_DEPENDS variable +# returned string in ${var} is can be passed to linker's command line +MACRO(EXTRACT_LINK_LIBRARIES target var) + LIST(REMOVE_ITEM ${target}_LIB_DEPENDS "") + LIST(REMOVE_DUPLICATES ${target}_LIB_DEPENDS) + FOREACH(lib ${${target}_LIB_DEPENDS}) + # Filter out "general", it is not a library, just CMake hint + # Also, remove duplicates + IF(NOT lib STREQUAL "general" AND NOT ${var} MATCHES "-l${lib} ") + IF (lib MATCHES "^\\-l") + SET(${var} "${${var}} ${lib} ") + ELSEIF(lib MATCHES "^/") + # Full path, convert to just filename, strip "lib" prefix and extension + GET_FILENAME_COMPONENT(lib "${lib}" NAME_WE) + STRING(REGEX REPLACE "^lib" "" lib "${lib}") + SET(${var} "${${var}}-l${lib} " ) + ELSE() + SET(${var} "${${var}}-l${lib} " ) + ENDIF() + ENDIF() + ENDFOREACH() + IF(MSVC) + STRING(REPLACE "-l" "" ${var} "${${var}}") ENDIF() -ENDFOREACH() +ENDMACRO() +EXTRACT_LINK_LIBRARIES(mysqlclient CLIENT_LIBS) +EXTRACT_LINK_LIBRARIES(mysqlserver LIBS) -IF(LIBDL AND NOT LIBDL MATCHES "-l") - SET(LIBDL "-l${LIBDL}") -ENDIF() - -IF(LIBWRAP) - SET(WRAPLIBS "-lwrap") -ENDIF() - -SET(LIBS "${CLIENT_LIBS}") - -IF(LIBCRYPT) - SET(LIBS "${LIBS} -l${LIBCRYPT}") -ENDIF() - -IF(MSVC) - STRING(REPLACE "-l" "" CLIENT_LIBS "${CLIENT_LIBS}") - STRING(REPLACE "-l" "" LIBS "${LIBS}" ) -ENDIF() +# mysql_config evaluates ${LIBDL}, we want to avoid it +# as our CLIENT_LIBS and LIBS are already correct +SET(LIBDL) SET(NON_THREADED_LIBS ${CLIENT_LIBS}) SET(mysql_config_COMPONENT COMPONENT Development) diff --git a/scripts/mysql_config.sh b/scripts/mysql_config.sh index 10755fc698b..69ec88d6724 100644 --- a/scripts/mysql_config.sh +++ b/scripts/mysql_config.sh @@ -108,7 +108,7 @@ fi # We intentionally add a space to the beginning and end of lib strings, simplifies replace later libs=" $ldflags -L$pkglibdir -lmysqlclient @ZLIB_DEPS@ @NON_THREADED_LIBS@" libs="$libs @openssl_libs@ @STATIC_NSS_FLAGS@ " -libs_r=" $ldflags -L$pkglibdir -lmysqlclient_r @ZLIB_DEPS@ @LIBS@ @openssl_libs@ " +libs_r=" $ldflags -L$pkglibdir -lmysqlclient_r @ZLIB_DEPS@ @CLIENT_LIBS@ @openssl_libs@ " embedded_libs=" $ldflags -L$pkglibdir -lmysqld @LIBDL@ @ZLIB_DEPS@ @LIBS@ @WRAPLIBS@ @openssl_libs@ " if [ -r "$pkglibdir/libmygcc.a" ]; then From 2355224c8b76c54dff6a8781c8ea761ce6cd53d8 Mon Sep 17 00:00:00 2001 From: Jonathan Perkin Date: Mon, 9 Aug 2010 15:41:15 +0100 Subject: [PATCH 115/129] Don't try to remove from an empty list. --- scripts/CMakeLists.txt | 36 +++++++++++++++++++----------------- 1 file changed, 19 insertions(+), 17 deletions(-) diff --git a/scripts/CMakeLists.txt b/scripts/CMakeLists.txt index 5831679828c..e97b664d106 100644 --- a/scripts/CMakeLists.txt +++ b/scripts/CMakeLists.txt @@ -253,24 +253,26 @@ ENDIF() # Extract dependencies using CMake's internal ${target}_LIB_DEPENDS variable # returned string in ${var} is can be passed to linker's command line MACRO(EXTRACT_LINK_LIBRARIES target var) - LIST(REMOVE_ITEM ${target}_LIB_DEPENDS "") - LIST(REMOVE_DUPLICATES ${target}_LIB_DEPENDS) - FOREACH(lib ${${target}_LIB_DEPENDS}) - # Filter out "general", it is not a library, just CMake hint - # Also, remove duplicates - IF(NOT lib STREQUAL "general" AND NOT ${var} MATCHES "-l${lib} ") - IF (lib MATCHES "^\\-l") - SET(${var} "${${var}} ${lib} ") - ELSEIF(lib MATCHES "^/") - # Full path, convert to just filename, strip "lib" prefix and extension - GET_FILENAME_COMPONENT(lib "${lib}" NAME_WE) - STRING(REGEX REPLACE "^lib" "" lib "${lib}") - SET(${var} "${${var}}-l${lib} " ) - ELSE() - SET(${var} "${${var}}-l${lib} " ) + IF(${target}_LIB_DEPENDS) + LIST(REMOVE_ITEM ${target}_LIB_DEPENDS "") + LIST(REMOVE_DUPLICATES ${target}_LIB_DEPENDS) + FOREACH(lib ${${target}_LIB_DEPENDS}) + # Filter out "general", it is not a library, just CMake hint + # Also, remove duplicates + IF(NOT lib STREQUAL "general" AND NOT ${var} MATCHES "-l${lib} ") + IF (lib MATCHES "^\\-l") + SET(${var} "${${var}} ${lib} ") + ELSEIF(lib MATCHES "^/") + # Full path, convert to just filename, strip "lib" prefix and extension + GET_FILENAME_COMPONENT(lib "${lib}" NAME_WE) + STRING(REGEX REPLACE "^lib" "" lib "${lib}") + SET(${var} "${${var}}-l${lib} " ) + ELSE() + SET(${var} "${${var}}-l${lib} " ) + ENDIF() ENDIF() - ENDIF() - ENDFOREACH() + ENDFOREACH() + ENDIF() IF(MSVC) STRING(REPLACE "-l" "" ${var} "${${var}}") ENDIF() From 191efc05a3b4c34846a963488979c581833dcac8 Mon Sep 17 00:00:00 2001 From: Alexander Nozdrin Date: Mon, 9 Aug 2010 20:52:26 +0400 Subject: [PATCH 116/129] Follow-up for Bug 23032: update NDB result files. --- mysql-test/suite/ndb/r/ndb_cursor.result | 2 ++ mysql-test/suite/rpl_ndb/r/rpl_ndb_sp006.result | 2 ++ 2 files changed, 4 insertions(+) diff --git a/mysql-test/suite/ndb/r/ndb_cursor.result b/mysql-test/suite/ndb/r/ndb_cursor.result index b3b815ef891..3e6f207e153 100644 --- a/mysql-test/suite/ndb/r/ndb_cursor.result +++ b/mysql-test/suite/ndb/r/ndb_cursor.result @@ -29,6 +29,8 @@ end; select * from t2 order by a; a b call test_cursor(); +Warnings: +Error 1329 No data - zero rows fetched, selected, or processed select * from t2 order by a; a b 1 10 diff --git a/mysql-test/suite/rpl_ndb/r/rpl_ndb_sp006.result b/mysql-test/suite/rpl_ndb/r/rpl_ndb_sp006.result index 047402f826f..21a2cfe5441 100644 --- a/mysql-test/suite/rpl_ndb/r/rpl_ndb_sp006.result +++ b/mysql-test/suite/rpl_ndb/r/rpl_ndb_sp006.result @@ -38,6 +38,8 @@ INSERT INTO t1 VALUES ('MySQL','1993-02-04'),('ROCKS', '1990-08-27'),('Texas', ' END| CALL p2(); CALL p1(); +Warnings: +Error 1329 No data - zero rows fetched, selected, or processed DROP TABLE t1; DROP TABLE t2; DROP PROCEDURE p1; From a8974baef73632d88882651ff1cc060e723e2f46 Mon Sep 17 00:00:00 2001 From: Alexander Nozdrin Date: Mon, 9 Aug 2010 20:55:26 +0400 Subject: [PATCH 117/129] Disable rpl_ndb.rpl_ndb_row_implicit_commit_binlog due to Bug 55849. --- mysql-test/suite/rpl_ndb/t/disabled.def | 1 + 1 file changed, 1 insertion(+) diff --git a/mysql-test/suite/rpl_ndb/t/disabled.def b/mysql-test/suite/rpl_ndb/t/disabled.def index 6bfb20f2205..8eda2f18958 100644 --- a/mysql-test/suite/rpl_ndb/t/disabled.def +++ b/mysql-test/suite/rpl_ndb/t/disabled.def @@ -12,6 +12,7 @@ rpl_ndb_stm_innodb : Bug#54850 2010-07-02 alik rpl_ndb.rpl_ndb_stm_innodb and rpl_ndb.rpl_ndb_2other fails rpl_ndb_2other : Bug#54850 2010-07-02 alik rpl_ndb.rpl_ndb_stm_innodb and rpl_ndb.rpl_ndb_2other fails +rpl_ndb_row_implicit_commit_binlog : Bug#55849 2010-08-09 alik rpl_ndb.rpl_ndb_row_implicit_commit_binlog fails # the below testcase have been reworked to avoid the bug, test contains comment, keep bug open rpl_ndb_2ndb : Bug#45974: rpl_ndb_2ndb fails sporadically From 8685b8427e286dc2856219740c1ad8a7dc9c9e5d Mon Sep 17 00:00:00 2001 From: Vladislav Vaintroub Date: Mon, 9 Aug 2010 21:47:26 +0200 Subject: [PATCH 118/129] Bug #55842 CMake: bad dependencies on sql/lex_hash.h Fix by adding "DEPENDS gen_lex_hash" to ADD_CUSTOM_COMMAND(), so it regenerates lex_hash.h whenever gen_lex_lash changes. Also, make sql dependent on GenServerSource to avoid concurrent generation of lex_hash.h (once for sql , and in parallel for embedded) --- sql/CMakeLists.txt | 2 ++ 1 file changed, 2 insertions(+) diff --git a/sql/CMakeLists.txt b/sql/CMakeLists.txt index 879e1bbed90..943d6b2eece 100644 --- a/sql/CMakeLists.txt +++ b/sql/CMakeLists.txt @@ -82,6 +82,7 @@ MYSQL_ADD_PLUGIN(partition ha_partition.cc STORAGE_ENGINE DEFAULT STATIC_ONLY RECOMPILE_FOR_EMBEDDED) ADD_LIBRARY(sql STATIC ${SQL_SOURCE}) +ADD_DEPENDENCIES(sql GenServerSource) DTRACE_INSTRUMENT(sql) TARGET_LINK_LIBRARIES(sql ${MYSQLD_STATIC_PLUGIN_LIBS} mysys dbug strings vio regex @@ -188,6 +189,7 @@ ADD_EXECUTABLE(gen_lex_hash gen_lex_hash.cc) ADD_CUSTOM_COMMAND( OUTPUT ${CMAKE_CURRENT_BINARY_DIR}/lex_hash.h COMMAND gen_lex_hash > lex_hash.h + DEPENDS gen_lex_hash ) MYSQL_ADD_EXECUTABLE(mysql_tzinfo_to_sql tztime.cc) From 88b3205653a2a478743861e94f950f81560286be Mon Sep 17 00:00:00 2001 From: Alfranio Correia Date: Tue, 10 Aug 2010 12:32:54 +0100 Subject: [PATCH 119/129] BUG#50312 Warnings for unsafe sub-statement not returned to client After BUG#36649, warnings for sub-statements are cleared when a new sub-statement is started. This is problematic since it suppresses warnings for unsafe statements in some cases. It is important that we always give a warning to the client, because the user needs to know when there is a risk that the slave goes out of sync. We fixed the problem by generating warning messages for unsafe statements while returning from a stored procedure, function, trigger or while executing a top level statement. We also started checking unsafeness when both performance and log tables are used. This is necessary after the performance schema which does a distinction between performance and log tables. mysql-test/extra/rpl_tests/create_recursive_construct.inc: Changed the order of the calls in the procedure because the code that checks if a warning message is printed out expects that the first statement gives an warning what is not the case for INSERT INTO ta$CRC_ARG_level VALUES (47); mysql-test/suite/binlog/r/binlog_stm_unsafe_warning.result: Updated the result file. mysql-test/suite/binlog/r/binlog_unsafe.result: There are several changes here: (1) - Changed the CREATE PROCEDURE $CRC. (2) - The procedure $CRC was failing and the content of the binlog was being printed out, after fix (1) the failure disappeared. (3) - The warning message for unsafeness due to auto-increment collumns was changed. (4) - The warning message for unsafeness due to VERSION(), RAND() was changed. mysql-test/suite/binlog/t/binlog_stm_unsafe_warning.test: Tested filters. mysql-test/suite/binlog/t/binlog_unsafe.test: Reenabled the test case binlog_unsafe. mysql-test/suite/binlog/t/disabled.def: Reenabled the test case binlog_unsafe. mysql-test/suite/rpl/r/rpl_begin_commit_rollback.result: Updated the result file. mysql-test/suite/rpl/r/rpl_non_direct_stm_mixing_engines.result: Updated the result file. mysql-test/suite/rpl/r/rpl_stm_auto_increment_bug33029.result: Updated the result file. sql/sql_class.cc: Moved the stmt_accessed_table_flag variable and related information to the LEX as we need the variable reset after each statement even inside a stored procedure, what did not happen if the information was in the THD. Changed the routine in the THD::binlog_query that prints the warning messages to avoid trying to print them when inside a stored procedure, function or trigger. Checked for unsafeness when both performance and log tables where used. After the introduction of the performance schema, we need to check both. --- .../rpl_tests/create_recursive_construct.inc | 23 +- .../binlog/r/binlog_stm_unsafe_warning.result | 22 + .../suite/binlog/r/binlog_unsafe.result | 1497 +++++------------ .../binlog/t/binlog_stm_unsafe_warning.test | 20 + mysql-test/suite/binlog/t/binlog_unsafe.test | 1 + mysql-test/suite/binlog/t/disabled.def | 1 - .../rpl/r/rpl_begin_commit_rollback.result | 2 + .../rpl_non_direct_stm_mixing_engines.result | 48 + .../r/rpl_stm_auto_increment_bug33029.result | 4 + sql/log.cc | 2 +- sql/log_event.cc | 4 +- sql/sp_head.cc | 19 + sql/sql_class.cc | 122 +- sql/sql_class.h | 149 +- sql/sql_lex.cc | 1 + sql/sql_lex.h | 125 ++ sql/sql_parse.cc | 1 - 17 files changed, 782 insertions(+), 1259 deletions(-) diff --git a/mysql-test/extra/rpl_tests/create_recursive_construct.inc b/mysql-test/extra/rpl_tests/create_recursive_construct.inc index 628f1735726..3a9c628cbb0 100644 --- a/mysql-test/extra/rpl_tests/create_recursive_construct.inc +++ b/mysql-test/extra/rpl_tests/create_recursive_construct.inc @@ -200,7 +200,7 @@ if (`SELECT $CRC_ARG_type = 1`) { if (`SELECT $CRC_ARG_type = 2`) { # It will be unsafe to call this procedure. --let $CRC_name= proc_$CRC_ARG_level - --let $CRC_create= CREATE PROCEDURE $CRC_name() BEGIN INSERT INTO ta$CRC_ARG_level VALUES (47); $CRC_ARG_stmt_sidef; END + --let $CRC_create= CREATE PROCEDURE $CRC_name() BEGIN $CRC_ARG_stmt_sidef; INSERT INTO ta$CRC_ARG_level VALUES (47); END --let $CRC_RET_stmt_sidef= CALL $CRC_name() --let $CRC_RET_value= --let $CRC_RET_sel_retval= @@ -344,25 +344,8 @@ if (`SELECT '$CRC_RET_stmt_sidef' != ''`) { if (`SELECT '$event_type' != 'Table_map'`) { --enable_query_log --echo ******** Failure! Event number 3 was a '$event_type', not a 'Table_map'. ******** - - # Currently, there is a bug causing some statements to be logged - # partially in statement format. Hence, we don't fail here, we - # just print the events (masking out nondeterministic components - # of the output) and continue. When binloggging works perfectly, - # we should instead execute: - #--enable_query_log - #SHOW BINLOG EVENTS; - #--die Wrong events in binlog. - - # Here, we should really source - # include/show_binlog_events.inc. But due to BUG#41913, that - # doesn't work, and we have to inline the entire file here. Sigh - # :-( - --replace_result $MYSQLTEST_VARDIR MYSQLTEST_VARDIR 107 - --replace_column 2 # 4 # 5 # - --replace_regex /\/\* xid=.* \*\//\/* XID *\// /table_id: [0-9]+/table_id: #/ /file_id=[0-9]+/file_id=#/ /block_len=[0-9]+/block_len=#/ - --eval SHOW BINLOG EVENTS FROM 107 - --disable_query_log + SHOW BINLOG EVENTS; + --die Wrong events in binlog. } SET binlog_format = STATEMENT; diff --git a/mysql-test/suite/binlog/r/binlog_stm_unsafe_warning.result b/mysql-test/suite/binlog/r/binlog_stm_unsafe_warning.result index d6d44ccad8e..23943474541 100644 --- a/mysql-test/suite/binlog/r/binlog_stm_unsafe_warning.result +++ b/mysql-test/suite/binlog/r/binlog_stm_unsafe_warning.result @@ -28,6 +28,25 @@ INSERT INTO t1 VALUES (1,2), (2,3); UPDATE t1 SET b='4' WHERE a=1 LIMIT 1; UPDATE t1 SET b='5' WHERE a=2 ORDER BY a LIMIT 1; DROP TABLE t1; +CREATE TABLE t1 (a VARCHAR(1000)); +INSERT INTO t1 VALUES (CURRENT_USER()); +INSERT INTO t1 VALUES (FOUND_ROWS()); +INSERT INTO t1 VALUES (GET_LOCK('tmp', 1)); +INSERT INTO t1 VALUES (IS_FREE_LOCK('tmp')); +INSERT INTO t1 VALUES (IS_USED_LOCK('tmp')); +INSERT INTO t1 VALUES (LOAD_FILE('../../std_data/words2.dat')); +INSERT INTO t1 VALUES (MASTER_POS_WAIT('dummy arg', 4711, 1)); +INSERT INTO t1 VALUES (RELEASE_LOCK('tmp')); +INSERT INTO t1 VALUES (ROW_COUNT()); +INSERT INTO t1 VALUES (SESSION_USER()); +INSERT INTO t1 VALUES (SLEEP(1)); +INSERT INTO t1 VALUES (SYSDATE()); +INSERT INTO t1 VALUES (SYSTEM_USER()); +INSERT INTO t1 VALUES (USER()); +INSERT INTO t1 VALUES (UUID()); +INSERT INTO t1 VALUES (UUID_SHORT()); +INSERT INTO t1 VALUES (VERSION()); +INSERT INTO t1 VALUES (RAND()); DROP DATABASE b42851; USE test; # @@ -67,8 +86,11 @@ Note 1592 Unsafe statement written to the binary log using statement format sinc SELECT sf_bug50192(); sf_bug50192() 1 +Warnings: +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it invokes a trigger or a stored function that inserts into an AUTO_INCREMENT column. Inserted values cannot be logged correctly. SHOW WARNINGS; Level Code Message +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it invokes a trigger or a stored function that inserts into an AUTO_INCREMENT column. Inserted values cannot be logged correctly. DROP FUNCTION sf_bug50192; DROP TRIGGER tr_bug50192; DROP TABLE t1, t2; diff --git a/mysql-test/suite/binlog/r/binlog_unsafe.result b/mysql-test/suite/binlog/r/binlog_unsafe.result index e9d1cdad856..ba361e59428 100644 --- a/mysql-test/suite/binlog/r/binlog_unsafe.result +++ b/mysql-test/suite/binlog/r/binlog_unsafe.result @@ -35,7 +35,7 @@ CREATE FUNCTION func_retval_1() RETURNS VARCHAR(100) BEGIN INSERT INTO ta1 VALUE * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO t1 VALUES (func_retval_1()); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 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. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. * Invoke statement so that return value is dicarded: expect no warning. @@ -46,7 +46,7 @@ CREATE FUNCTION func_retval_2() RETURNS VARCHAR(100) BEGIN INSERT INTO ta2 VALUE * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO t2 VALUES (func_retval_2()); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 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. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. * Invoke statement so that return value is dicarded: expect no warning. @@ -58,31 +58,19 @@ CREATE FUNCTION func_sidef_2() RETURNS VARCHAR(100) BEGIN INSERT INTO ta2 VALUES * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO t2 SELECT func_sidef_2(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 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. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP FUNCTION func_sidef_2; Invoking procedure proc_2 invoking function func_retval_1 returning value from unsafe UUID() function. -CREATE PROCEDURE proc_2() BEGIN INSERT INTO ta2 VALUES (47); INSERT INTO t1 VALUES (func_retval_1()); END; +CREATE PROCEDURE proc_2() BEGIN INSERT INTO t1 VALUES (func_retval_1()); INSERT INTO ta2 VALUES (47); END; * binlog_format = STATEMENT: expect 1 warnings. CALL proc_2(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 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. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. -******** Failure! Event number 3 was a 'Query', not a 'Table_map'. ******** -SHOW BINLOG EVENTS FROM ; -Log_name Pos Event_type Server_id End_log_pos Info -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Query # # use `test`; INSERT INTO ta2 VALUES (47) -master-bin.000001 # Query # # COMMIT -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Table_map # # table_id: # (test.t1) -master-bin.000001 # Table_map # # table_id: # (test.ta1) -master-bin.000001 # Write_rows # # table_id: # -master-bin.000001 # Write_rows # # table_id: # flags: STMT_END_F -master-bin.000001 # Query # # COMMIT DROP PROCEDURE proc_2; Invoking trigger trig_2 invoking function func_retval_1 returning value from unsafe UUID() function. @@ -90,7 +78,7 @@ CREATE TRIGGER trig_2 BEFORE INSERT ON trigger_table_2 FOR EACH ROW BEGIN INSERT * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO trigger_table_2 VALUES (1); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 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. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP TRIGGER trig_2; @@ -98,11 +86,11 @@ DROP TRIGGER trig_2; Invoking view view_retval_2 returning value from function func_retval_1 returning value from unsafe UUID() function. CREATE VIEW view_retval_2 AS SELECT func_retval_1(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 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. * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO t2 SELECT * FROM view_retval_2; Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 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. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. * Invoke statement so that return value is dicarded: expect no warning. @@ -114,7 +102,7 @@ PREPARE prep_2 FROM "INSERT INTO t1 VALUES (func_retval_1())"; * binlog_format = STATEMENT: expect 1 warnings. EXECUTE prep_2; Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 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. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP PREPARE prep_2; @@ -125,7 +113,7 @@ CREATE FUNCTION func_sidef_1() RETURNS VARCHAR(100) BEGIN INSERT INTO ta1 VALUES * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO t1 SELECT func_sidef_1(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 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. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. @@ -134,33 +122,19 @@ CREATE FUNCTION func_sidef_2() RETURNS VARCHAR(100) BEGIN INSERT INTO ta2 VALUES * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO t2 SELECT func_sidef_2(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 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. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP FUNCTION func_sidef_2; Invoking procedure proc_2 invoking function func_sidef_1 invoking unsafe UUID() function. -CREATE PROCEDURE proc_2() BEGIN INSERT INTO ta2 VALUES (47); INSERT INTO t1 SELECT func_sidef_1(); END; +CREATE PROCEDURE proc_2() BEGIN INSERT INTO t1 SELECT func_sidef_1(); INSERT INTO ta2 VALUES (47); END; * binlog_format = STATEMENT: expect 1 warnings. CALL proc_2(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 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. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. -******** Failure! Event number 3 was a 'Query', not a 'Table_map'. ******** -SHOW BINLOG EVENTS FROM ; -Log_name Pos Event_type Server_id End_log_pos Info -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Query # # use `test`; INSERT INTO ta2 VALUES (47) -master-bin.000001 # Query # # COMMIT -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Table_map # # table_id: # (test.t1) -master-bin.000001 # Table_map # # table_id: # (test.t0) -master-bin.000001 # Table_map # # table_id: # (test.ta1) -master-bin.000001 # Write_rows # # table_id: # -master-bin.000001 # Write_rows # # table_id: # -master-bin.000001 # Write_rows # # table_id: # flags: STMT_END_F -master-bin.000001 # Query # # COMMIT DROP PROCEDURE proc_2; Invoking trigger trig_2 invoking function func_sidef_1 invoking unsafe UUID() function. @@ -168,7 +142,7 @@ CREATE TRIGGER trig_2 BEFORE INSERT ON trigger_table_2 FOR EACH ROW BEGIN INSERT * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO trigger_table_2 VALUES (1); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 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. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP TRIGGER trig_2; @@ -176,11 +150,11 @@ DROP TRIGGER trig_2; Invoking view view_sidef_2 invoking function func_sidef_1 invoking unsafe UUID() function. CREATE VIEW view_sidef_2 AS SELECT func_sidef_1(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 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. * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO t2 SELECT * FROM view_sidef_2; Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 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. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP VIEW view_sidef_2; @@ -190,18 +164,18 @@ PREPARE prep_2 FROM "INSERT INTO t1 SELECT func_sidef_1()"; * binlog_format = STATEMENT: expect 1 warnings. EXECUTE prep_2; Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 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. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP PREPARE prep_2; DROP FUNCTION func_sidef_1; Invoking procedure proc_1 invoking unsafe UUID() function. -CREATE PROCEDURE proc_1() BEGIN INSERT INTO ta1 VALUES (47); INSERT INTO t0 VALUES (UUID()); END; +CREATE PROCEDURE proc_1() BEGIN INSERT INTO t0 VALUES (UUID()); INSERT INTO ta1 VALUES (47); END; * binlog_format = STATEMENT: expect 1 warnings. CALL proc_1(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 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. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. @@ -210,33 +184,19 @@ CREATE FUNCTION func_sidef_2() RETURNS VARCHAR(100) BEGIN INSERT INTO ta2 VALUES * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO t2 SELECT func_sidef_2(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 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. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP FUNCTION func_sidef_2; Invoking procedure proc_2 invoking procedure proc_1 invoking unsafe UUID() function. -CREATE PROCEDURE proc_2() BEGIN INSERT INTO ta2 VALUES (47); CALL proc_1(); END; +CREATE PROCEDURE proc_2() BEGIN CALL proc_1(); INSERT INTO ta2 VALUES (47); END; * binlog_format = STATEMENT: expect 1 warnings. CALL proc_2(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 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. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. -******** Failure! Event number 3 was a 'Query', not a 'Table_map'. ******** -SHOW BINLOG EVENTS FROM ; -Log_name Pos Event_type Server_id End_log_pos Info -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Query # # use `test`; INSERT INTO ta2 VALUES (47) -master-bin.000001 # Query # # COMMIT -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Table_map # # table_id: # (test.ta1) -master-bin.000001 # Write_rows # # table_id: # flags: STMT_END_F -master-bin.000001 # Query # # COMMIT -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Table_map # # table_id: # (test.t0) -master-bin.000001 # Write_rows # # table_id: # flags: STMT_END_F -master-bin.000001 # Query # # COMMIT DROP PROCEDURE proc_2; Invoking trigger trig_2 invoking procedure proc_1 invoking unsafe UUID() function. @@ -244,7 +204,7 @@ CREATE TRIGGER trig_2 BEFORE INSERT ON trigger_table_2 FOR EACH ROW BEGIN INSERT * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO trigger_table_2 VALUES (1); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 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. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP TRIGGER trig_2; @@ -254,7 +214,7 @@ PREPARE prep_2 FROM "CALL proc_1()"; * binlog_format = STATEMENT: expect 1 warnings. EXECUTE prep_2; Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 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. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP PREPARE prep_2; @@ -265,7 +225,7 @@ CREATE TRIGGER trig_1 BEFORE INSERT ON trigger_table_1 FOR EACH ROW BEGIN INSERT * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO trigger_table_1 VALUES (1); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 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. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. @@ -274,33 +234,19 @@ CREATE FUNCTION func_sidef_2() RETURNS VARCHAR(100) BEGIN INSERT INTO ta2 VALUES * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO t2 SELECT func_sidef_2(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 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. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP FUNCTION func_sidef_2; Invoking procedure proc_2 invoking trigger trig_1 invoking unsafe UUID() function. -CREATE PROCEDURE proc_2() BEGIN INSERT INTO ta2 VALUES (47); INSERT INTO trigger_table_1 VALUES (1); END; +CREATE PROCEDURE proc_2() BEGIN INSERT INTO trigger_table_1 VALUES (1); INSERT INTO ta2 VALUES (47); END; * binlog_format = STATEMENT: expect 1 warnings. CALL proc_2(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 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. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. -******** Failure! Event number 3 was a 'Query', not a 'Table_map'. ******** -SHOW BINLOG EVENTS FROM ; -Log_name Pos Event_type Server_id End_log_pos Info -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Query # # use `test`; INSERT INTO ta2 VALUES (47) -master-bin.000001 # Query # # COMMIT -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Table_map # # table_id: # (test.trigger_table_1) -master-bin.000001 # Table_map # # table_id: # (test.t0) -master-bin.000001 # Table_map # # table_id: # (test.ta1) -master-bin.000001 # Write_rows # # table_id: # -master-bin.000001 # Write_rows # # table_id: # -master-bin.000001 # Write_rows # # table_id: # flags: STMT_END_F -master-bin.000001 # Query # # COMMIT DROP PROCEDURE proc_2; Invoking trigger trig_2 invoking trigger trig_1 invoking unsafe UUID() function. @@ -308,7 +254,7 @@ CREATE TRIGGER trig_2 BEFORE INSERT ON trigger_table_2 FOR EACH ROW BEGIN INSERT * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO trigger_table_2 VALUES (1); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 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. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP TRIGGER trig_2; @@ -318,7 +264,7 @@ PREPARE prep_2 FROM "INSERT INTO trigger_table_1 VALUES (1)"; * binlog_format = STATEMENT: expect 1 warnings. EXECUTE prep_2; Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 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. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP PREPARE prep_2; @@ -326,12 +272,10 @@ DROP TRIGGER trig_1; Invoking view view_retval_1 returning value from unsafe UUID() function. CREATE VIEW view_retval_1 AS SELECT UUID(); -Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO t1 SELECT * FROM view_retval_1; Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 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. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. * Invoke statement so that return value is dicarded: expect no warning. @@ -342,29 +286,19 @@ CREATE FUNCTION func_sidef_2() RETURNS VARCHAR(100) BEGIN INSERT INTO ta2 VALUES * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO t2 SELECT func_sidef_2(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 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. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP FUNCTION func_sidef_2; Invoking procedure proc_2 invoking view view_retval_1 returning value from unsafe UUID() function. -CREATE PROCEDURE proc_2() BEGIN INSERT INTO ta2 VALUES (47); INSERT INTO t1 SELECT * FROM view_retval_1; END; +CREATE PROCEDURE proc_2() BEGIN INSERT INTO t1 SELECT * FROM view_retval_1; INSERT INTO ta2 VALUES (47); END; * binlog_format = STATEMENT: expect 1 warnings. CALL proc_2(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 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. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. -******** Failure! Event number 3 was a 'Query', not a 'Table_map'. ******** -SHOW BINLOG EVENTS FROM ; -Log_name Pos Event_type Server_id End_log_pos Info -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Query # # use `test`; INSERT INTO ta2 VALUES (47) -master-bin.000001 # Query # # COMMIT -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Table_map # # table_id: # (test.t1) -master-bin.000001 # Write_rows # # table_id: # flags: STMT_END_F -master-bin.000001 # Query # # COMMIT DROP PROCEDURE proc_2; Invoking trigger trig_2 invoking view view_retval_1 returning value from unsafe UUID() function. @@ -372,19 +306,17 @@ CREATE TRIGGER trig_2 BEFORE INSERT ON trigger_table_2 FOR EACH ROW BEGIN INSERT * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO trigger_table_2 VALUES (1); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 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. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP TRIGGER trig_2; Invoking view view_retval_2 returning value from view view_retval_1 returning value from unsafe UUID() function. CREATE VIEW view_retval_2 AS SELECT * FROM view_retval_1; -Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO t2 SELECT * FROM view_retval_2; Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 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. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. * Invoke statement so that return value is dicarded: expect no warning. @@ -396,7 +328,7 @@ PREPARE prep_2 FROM "INSERT INTO t1 SELECT * FROM view_retval_1"; * binlog_format = STATEMENT: expect 1 warnings. EXECUTE prep_2; Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 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. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP PREPARE prep_2; @@ -407,7 +339,7 @@ PREPARE prep_1 FROM "INSERT INTO t0 VALUES (UUID())"; * binlog_format = STATEMENT: expect 1 warnings. EXECUTE prep_1; Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 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. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP PREPARE prep_1; @@ -416,7 +348,7 @@ Invoking unsafe UUID() function. * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO t0 VALUES (UUID()); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 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. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. * Invoke statement so that return value is dicarded: expect no warning. @@ -429,7 +361,7 @@ CREATE FUNCTION func_retval_1() RETURNS VARCHAR(100) BEGIN INSERT INTO ta1 VALUE * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO t1 VALUES (func_retval_1()); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system variable that may have a different value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a system variable that may have a different value on the slave. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. * Invoke statement so that return value is dicarded: expect no warning. @@ -440,7 +372,7 @@ CREATE FUNCTION func_retval_2() RETURNS VARCHAR(100) BEGIN INSERT INTO ta2 VALUE * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO t2 VALUES (func_retval_2()); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system variable that may have a different value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a system variable that may have a different value on the slave. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. * Invoke statement so that return value is dicarded: expect no warning. @@ -452,31 +384,19 @@ CREATE FUNCTION func_sidef_2() RETURNS VARCHAR(100) BEGIN INSERT INTO ta2 VALUES * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO t2 SELECT func_sidef_2(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system variable that may have a different value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a system variable that may have a different value on the slave. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP FUNCTION func_sidef_2; Invoking procedure proc_2 invoking function func_retval_1 returning value from unsafe @@hostname variable. -CREATE PROCEDURE proc_2() BEGIN INSERT INTO ta2 VALUES (47); INSERT INTO t1 VALUES (func_retval_1()); END; +CREATE PROCEDURE proc_2() BEGIN INSERT INTO t1 VALUES (func_retval_1()); INSERT INTO ta2 VALUES (47); END; * binlog_format = STATEMENT: expect 1 warnings. CALL proc_2(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system variable that may have a different value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a system variable that may have a different value on the slave. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. -******** Failure! Event number 3 was a 'Query', not a 'Table_map'. ******** -SHOW BINLOG EVENTS FROM ; -Log_name Pos Event_type Server_id End_log_pos Info -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Query # # use `test`; INSERT INTO ta2 VALUES (47) -master-bin.000001 # Query # # COMMIT -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Table_map # # table_id: # (test.t1) -master-bin.000001 # Table_map # # table_id: # (test.ta1) -master-bin.000001 # Write_rows # # table_id: # -master-bin.000001 # Write_rows # # table_id: # flags: STMT_END_F -master-bin.000001 # Query # # COMMIT DROP PROCEDURE proc_2; Invoking trigger trig_2 invoking function func_retval_1 returning value from unsafe @@hostname variable. @@ -484,7 +404,7 @@ CREATE TRIGGER trig_2 BEFORE INSERT ON trigger_table_2 FOR EACH ROW BEGIN INSERT * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO trigger_table_2 VALUES (1); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system variable that may have a different value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a system variable that may have a different value on the slave. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP TRIGGER trig_2; @@ -492,11 +412,11 @@ DROP TRIGGER trig_2; Invoking view view_retval_2 returning value from function func_retval_1 returning value from unsafe @@hostname variable. CREATE VIEW view_retval_2 AS SELECT func_retval_1(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system variable that may have a different value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a system variable that may have a different value on the slave. * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO t2 SELECT * FROM view_retval_2; Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system variable that may have a different value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a system variable that may have a different value on the slave. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. * Invoke statement so that return value is dicarded: expect no warning. @@ -508,7 +428,7 @@ PREPARE prep_2 FROM "INSERT INTO t1 VALUES (func_retval_1())"; * binlog_format = STATEMENT: expect 1 warnings. EXECUTE prep_2; Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system variable that may have a different value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a system variable that may have a different value on the slave. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP PREPARE prep_2; @@ -519,7 +439,7 @@ CREATE FUNCTION func_sidef_1() RETURNS VARCHAR(100) BEGIN INSERT INTO ta1 VALUES * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO t1 SELECT func_sidef_1(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system variable that may have a different value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a system variable that may have a different value on the slave. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. @@ -528,33 +448,19 @@ CREATE FUNCTION func_sidef_2() RETURNS VARCHAR(100) BEGIN INSERT INTO ta2 VALUES * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO t2 SELECT func_sidef_2(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system variable that may have a different value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a system variable that may have a different value on the slave. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP FUNCTION func_sidef_2; Invoking procedure proc_2 invoking function func_sidef_1 invoking unsafe @@hostname variable. -CREATE PROCEDURE proc_2() BEGIN INSERT INTO ta2 VALUES (47); INSERT INTO t1 SELECT func_sidef_1(); END; +CREATE PROCEDURE proc_2() BEGIN INSERT INTO t1 SELECT func_sidef_1(); INSERT INTO ta2 VALUES (47); END; * binlog_format = STATEMENT: expect 1 warnings. CALL proc_2(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system variable that may have a different value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a system variable that may have a different value on the slave. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. -******** Failure! Event number 3 was a 'Query', not a 'Table_map'. ******** -SHOW BINLOG EVENTS FROM ; -Log_name Pos Event_type Server_id End_log_pos Info -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Query # # use `test`; INSERT INTO ta2 VALUES (47) -master-bin.000001 # Query # # COMMIT -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Table_map # # table_id: # (test.t1) -master-bin.000001 # Table_map # # table_id: # (test.t0) -master-bin.000001 # Table_map # # table_id: # (test.ta1) -master-bin.000001 # Write_rows # # table_id: # -master-bin.000001 # Write_rows # # table_id: # -master-bin.000001 # Write_rows # # table_id: # flags: STMT_END_F -master-bin.000001 # Query # # COMMIT DROP PROCEDURE proc_2; Invoking trigger trig_2 invoking function func_sidef_1 invoking unsafe @@hostname variable. @@ -562,7 +468,7 @@ CREATE TRIGGER trig_2 BEFORE INSERT ON trigger_table_2 FOR EACH ROW BEGIN INSERT * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO trigger_table_2 VALUES (1); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system variable that may have a different value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a system variable that may have a different value on the slave. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP TRIGGER trig_2; @@ -570,11 +476,11 @@ DROP TRIGGER trig_2; Invoking view view_sidef_2 invoking function func_sidef_1 invoking unsafe @@hostname variable. CREATE VIEW view_sidef_2 AS SELECT func_sidef_1(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system variable that may have a different value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a system variable that may have a different value on the slave. * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO t2 SELECT * FROM view_sidef_2; Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system variable that may have a different value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a system variable that may have a different value on the slave. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP VIEW view_sidef_2; @@ -584,18 +490,18 @@ PREPARE prep_2 FROM "INSERT INTO t1 SELECT func_sidef_1()"; * binlog_format = STATEMENT: expect 1 warnings. EXECUTE prep_2; Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system variable that may have a different value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a system variable that may have a different value on the slave. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP PREPARE prep_2; DROP FUNCTION func_sidef_1; Invoking procedure proc_1 invoking unsafe @@hostname variable. -CREATE PROCEDURE proc_1() BEGIN INSERT INTO ta1 VALUES (47); INSERT INTO t0 VALUES (@@hostname); END; +CREATE PROCEDURE proc_1() BEGIN INSERT INTO t0 VALUES (@@hostname); INSERT INTO ta1 VALUES (47); END; * binlog_format = STATEMENT: expect 1 warnings. CALL proc_1(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system variable that may have a different value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a system variable that may have a different value on the slave. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. @@ -604,33 +510,19 @@ CREATE FUNCTION func_sidef_2() RETURNS VARCHAR(100) BEGIN INSERT INTO ta2 VALUES * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO t2 SELECT func_sidef_2(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system variable that may have a different value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a system variable that may have a different value on the slave. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP FUNCTION func_sidef_2; Invoking procedure proc_2 invoking procedure proc_1 invoking unsafe @@hostname variable. -CREATE PROCEDURE proc_2() BEGIN INSERT INTO ta2 VALUES (47); CALL proc_1(); END; +CREATE PROCEDURE proc_2() BEGIN CALL proc_1(); INSERT INTO ta2 VALUES (47); END; * binlog_format = STATEMENT: expect 1 warnings. CALL proc_2(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system variable that may have a different value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a system variable that may have a different value on the slave. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. -******** Failure! Event number 3 was a 'Query', not a 'Table_map'. ******** -SHOW BINLOG EVENTS FROM ; -Log_name Pos Event_type Server_id End_log_pos Info -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Query # # use `test`; INSERT INTO ta2 VALUES (47) -master-bin.000001 # Query # # COMMIT -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Table_map # # table_id: # (test.ta1) -master-bin.000001 # Write_rows # # table_id: # flags: STMT_END_F -master-bin.000001 # Query # # COMMIT -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Table_map # # table_id: # (test.t0) -master-bin.000001 # Write_rows # # table_id: # flags: STMT_END_F -master-bin.000001 # Query # # COMMIT DROP PROCEDURE proc_2; Invoking trigger trig_2 invoking procedure proc_1 invoking unsafe @@hostname variable. @@ -638,7 +530,7 @@ CREATE TRIGGER trig_2 BEFORE INSERT ON trigger_table_2 FOR EACH ROW BEGIN INSERT * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO trigger_table_2 VALUES (1); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system variable that may have a different value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a system variable that may have a different value on the slave. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP TRIGGER trig_2; @@ -648,7 +540,7 @@ PREPARE prep_2 FROM "CALL proc_1()"; * binlog_format = STATEMENT: expect 1 warnings. EXECUTE prep_2; Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system variable that may have a different value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a system variable that may have a different value on the slave. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP PREPARE prep_2; @@ -659,7 +551,7 @@ CREATE TRIGGER trig_1 BEFORE INSERT ON trigger_table_1 FOR EACH ROW BEGIN INSERT * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO trigger_table_1 VALUES (1); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system variable that may have a different value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a system variable that may have a different value on the slave. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. @@ -668,33 +560,19 @@ CREATE FUNCTION func_sidef_2() RETURNS VARCHAR(100) BEGIN INSERT INTO ta2 VALUES * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO t2 SELECT func_sidef_2(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system variable that may have a different value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a system variable that may have a different value on the slave. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP FUNCTION func_sidef_2; Invoking procedure proc_2 invoking trigger trig_1 invoking unsafe @@hostname variable. -CREATE PROCEDURE proc_2() BEGIN INSERT INTO ta2 VALUES (47); INSERT INTO trigger_table_1 VALUES (1); END; +CREATE PROCEDURE proc_2() BEGIN INSERT INTO trigger_table_1 VALUES (1); INSERT INTO ta2 VALUES (47); END; * binlog_format = STATEMENT: expect 1 warnings. CALL proc_2(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system variable that may have a different value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a system variable that may have a different value on the slave. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. -******** Failure! Event number 3 was a 'Query', not a 'Table_map'. ******** -SHOW BINLOG EVENTS FROM ; -Log_name Pos Event_type Server_id End_log_pos Info -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Query # # use `test`; INSERT INTO ta2 VALUES (47) -master-bin.000001 # Query # # COMMIT -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Table_map # # table_id: # (test.trigger_table_1) -master-bin.000001 # Table_map # # table_id: # (test.t0) -master-bin.000001 # Table_map # # table_id: # (test.ta1) -master-bin.000001 # Write_rows # # table_id: # -master-bin.000001 # Write_rows # # table_id: # -master-bin.000001 # Write_rows # # table_id: # flags: STMT_END_F -master-bin.000001 # Query # # COMMIT DROP PROCEDURE proc_2; Invoking trigger trig_2 invoking trigger trig_1 invoking unsafe @@hostname variable. @@ -702,7 +580,7 @@ CREATE TRIGGER trig_2 BEFORE INSERT ON trigger_table_2 FOR EACH ROW BEGIN INSERT * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO trigger_table_2 VALUES (1); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system variable that may have a different value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a system variable that may have a different value on the slave. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP TRIGGER trig_2; @@ -712,7 +590,7 @@ PREPARE prep_2 FROM "INSERT INTO trigger_table_1 VALUES (1)"; * binlog_format = STATEMENT: expect 1 warnings. EXECUTE prep_2; Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system variable that may have a different value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a system variable that may have a different value on the slave. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP PREPARE prep_2; @@ -723,7 +601,7 @@ PREPARE prep_1 FROM "INSERT INTO t0 VALUES (@@hostname)"; * binlog_format = STATEMENT: expect 1 warnings. EXECUTE prep_1; Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system variable that may have a different value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a system variable that may have a different value on the slave. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP PREPARE prep_1; @@ -732,7 +610,7 @@ Invoking unsafe @@hostname variable. * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO t0 VALUES (@@hostname); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system variable that may have a different value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a system variable that may have a different value on the slave. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. @@ -743,7 +621,7 @@ CREATE FUNCTION func_sidef_1() RETURNS VARCHAR(100) BEGIN INSERT INTO ta1 VALUES * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO t1 SELECT func_sidef_1(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. @@ -752,33 +630,19 @@ CREATE FUNCTION func_sidef_2() RETURNS VARCHAR(100) BEGIN INSERT INTO ta2 VALUES * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO t2 SELECT func_sidef_2(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP FUNCTION func_sidef_2; Invoking procedure proc_2 invoking function func_sidef_1 invoking unsafe SELECT...LIMIT statement. -CREATE PROCEDURE proc_2() BEGIN INSERT INTO ta2 VALUES (47); INSERT INTO t1 SELECT func_sidef_1(); END; +CREATE PROCEDURE proc_2() BEGIN INSERT INTO t1 SELECT func_sidef_1(); INSERT INTO ta2 VALUES (47); END; * binlog_format = STATEMENT: expect 1 warnings. CALL proc_2(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. -******** Failure! Event number 3 was a 'Query', not a 'Table_map'. ******** -SHOW BINLOG EVENTS FROM ; -Log_name Pos Event_type Server_id End_log_pos Info -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Query # # use `test`; INSERT INTO ta2 VALUES (47) -master-bin.000001 # Query # # COMMIT -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Table_map # # table_id: # (test.t1) -master-bin.000001 # Table_map # # table_id: # (test.t0) -master-bin.000001 # Table_map # # table_id: # (test.ta1) -master-bin.000001 # Write_rows # # table_id: # -master-bin.000001 # Write_rows # # table_id: # -master-bin.000001 # Write_rows # # table_id: # flags: STMT_END_F -master-bin.000001 # Query # # COMMIT DROP PROCEDURE proc_2; Invoking trigger trig_2 invoking function func_sidef_1 invoking unsafe SELECT...LIMIT statement. @@ -786,7 +650,7 @@ CREATE TRIGGER trig_2 BEFORE INSERT ON trigger_table_2 FOR EACH ROW BEGIN INSERT * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO trigger_table_2 VALUES (1); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP TRIGGER trig_2; @@ -794,11 +658,11 @@ DROP TRIGGER trig_2; Invoking view view_sidef_2 invoking function func_sidef_1 invoking unsafe SELECT...LIMIT statement. CREATE VIEW view_sidef_2 AS SELECT func_sidef_1(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO t2 SELECT * FROM view_sidef_2; Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP VIEW view_sidef_2; @@ -808,18 +672,18 @@ PREPARE prep_2 FROM "INSERT INTO t1 SELECT func_sidef_1()"; * binlog_format = STATEMENT: expect 1 warnings. EXECUTE prep_2; Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP PREPARE prep_2; DROP FUNCTION func_sidef_1; Invoking procedure proc_1 invoking unsafe SELECT...LIMIT statement. -CREATE PROCEDURE proc_1() BEGIN INSERT INTO ta1 VALUES (47); INSERT INTO t0 SELECT * FROM data_table LIMIT 1; END; +CREATE PROCEDURE proc_1() BEGIN INSERT INTO t0 SELECT * FROM data_table LIMIT 1; INSERT INTO ta1 VALUES (47); END; * binlog_format = STATEMENT: expect 1 warnings. CALL proc_1(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. @@ -828,33 +692,19 @@ CREATE FUNCTION func_sidef_2() RETURNS VARCHAR(100) BEGIN INSERT INTO ta2 VALUES * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO t2 SELECT func_sidef_2(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP FUNCTION func_sidef_2; Invoking procedure proc_2 invoking procedure proc_1 invoking unsafe SELECT...LIMIT statement. -CREATE PROCEDURE proc_2() BEGIN INSERT INTO ta2 VALUES (47); CALL proc_1(); END; +CREATE PROCEDURE proc_2() BEGIN CALL proc_1(); INSERT INTO ta2 VALUES (47); END; * binlog_format = STATEMENT: expect 1 warnings. CALL proc_2(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. -******** Failure! Event number 3 was a 'Query', not a 'Table_map'. ******** -SHOW BINLOG EVENTS FROM ; -Log_name Pos Event_type Server_id End_log_pos Info -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Query # # use `test`; INSERT INTO ta2 VALUES (47) -master-bin.000001 # Query # # COMMIT -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Table_map # # table_id: # (test.ta1) -master-bin.000001 # Write_rows # # table_id: # flags: STMT_END_F -master-bin.000001 # Query # # COMMIT -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Table_map # # table_id: # (test.t0) -master-bin.000001 # Write_rows # # table_id: # flags: STMT_END_F -master-bin.000001 # Query # # COMMIT DROP PROCEDURE proc_2; Invoking trigger trig_2 invoking procedure proc_1 invoking unsafe SELECT...LIMIT statement. @@ -862,7 +712,7 @@ CREATE TRIGGER trig_2 BEFORE INSERT ON trigger_table_2 FOR EACH ROW BEGIN INSERT * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO trigger_table_2 VALUES (1); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP TRIGGER trig_2; @@ -872,7 +722,7 @@ PREPARE prep_2 FROM "CALL proc_1()"; * binlog_format = STATEMENT: expect 1 warnings. EXECUTE prep_2; Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP PREPARE prep_2; @@ -883,7 +733,7 @@ CREATE TRIGGER trig_1 BEFORE INSERT ON trigger_table_1 FOR EACH ROW BEGIN INSERT * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO trigger_table_1 VALUES (1); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. @@ -892,33 +742,19 @@ CREATE FUNCTION func_sidef_2() RETURNS VARCHAR(100) BEGIN INSERT INTO ta2 VALUES * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO t2 SELECT func_sidef_2(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP FUNCTION func_sidef_2; Invoking procedure proc_2 invoking trigger trig_1 invoking unsafe SELECT...LIMIT statement. -CREATE PROCEDURE proc_2() BEGIN INSERT INTO ta2 VALUES (47); INSERT INTO trigger_table_1 VALUES (1); END; +CREATE PROCEDURE proc_2() BEGIN INSERT INTO trigger_table_1 VALUES (1); INSERT INTO ta2 VALUES (47); END; * binlog_format = STATEMENT: expect 1 warnings. CALL proc_2(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. -******** Failure! Event number 3 was a 'Query', not a 'Table_map'. ******** -SHOW BINLOG EVENTS FROM ; -Log_name Pos Event_type Server_id End_log_pos Info -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Query # # use `test`; INSERT INTO ta2 VALUES (47) -master-bin.000001 # Query # # COMMIT -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Table_map # # table_id: # (test.trigger_table_1) -master-bin.000001 # Table_map # # table_id: # (test.t0) -master-bin.000001 # Table_map # # table_id: # (test.ta1) -master-bin.000001 # Write_rows # # table_id: # -master-bin.000001 # Write_rows # # table_id: # -master-bin.000001 # Write_rows # # table_id: # flags: STMT_END_F -master-bin.000001 # Query # # COMMIT DROP PROCEDURE proc_2; Invoking trigger trig_2 invoking trigger trig_1 invoking unsafe SELECT...LIMIT statement. @@ -926,7 +762,7 @@ CREATE TRIGGER trig_2 BEFORE INSERT ON trigger_table_2 FOR EACH ROW BEGIN INSERT * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO trigger_table_2 VALUES (1); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP TRIGGER trig_2; @@ -936,7 +772,7 @@ PREPARE prep_2 FROM "INSERT INTO trigger_table_1 VALUES (1)"; * binlog_format = STATEMENT: expect 1 warnings. EXECUTE prep_2; Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP PREPARE prep_2; @@ -944,12 +780,10 @@ DROP TRIGGER trig_1; Invoking view view_retval_1 returning value from unsafe SELECT...LIMIT statement. CREATE VIEW view_retval_1 AS SELECT * FROM data_table LIMIT 1; -Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO t1 SELECT * FROM view_retval_1; Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. * Invoke statement so that return value is dicarded: expect no warning. @@ -960,29 +794,19 @@ CREATE FUNCTION func_sidef_2() RETURNS VARCHAR(100) BEGIN INSERT INTO ta2 VALUES * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO t2 SELECT func_sidef_2(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP FUNCTION func_sidef_2; Invoking procedure proc_2 invoking view view_retval_1 returning value from unsafe SELECT...LIMIT statement. -CREATE PROCEDURE proc_2() BEGIN INSERT INTO ta2 VALUES (47); INSERT INTO t1 SELECT * FROM view_retval_1; END; +CREATE PROCEDURE proc_2() BEGIN INSERT INTO t1 SELECT * FROM view_retval_1; INSERT INTO ta2 VALUES (47); END; * binlog_format = STATEMENT: expect 1 warnings. CALL proc_2(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. -******** Failure! Event number 3 was a 'Query', not a 'Table_map'. ******** -SHOW BINLOG EVENTS FROM ; -Log_name Pos Event_type Server_id End_log_pos Info -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Query # # use `test`; INSERT INTO ta2 VALUES (47) -master-bin.000001 # Query # # COMMIT -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Table_map # # table_id: # (test.t1) -master-bin.000001 # Write_rows # # table_id: # flags: STMT_END_F -master-bin.000001 # Query # # COMMIT DROP PROCEDURE proc_2; Invoking trigger trig_2 invoking view view_retval_1 returning value from unsafe SELECT...LIMIT statement. @@ -990,19 +814,17 @@ CREATE TRIGGER trig_2 BEFORE INSERT ON trigger_table_2 FOR EACH ROW BEGIN INSERT * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO trigger_table_2 VALUES (1); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP TRIGGER trig_2; Invoking view view_retval_2 returning value from view view_retval_1 returning value from unsafe SELECT...LIMIT statement. CREATE VIEW view_retval_2 AS SELECT * FROM view_retval_1; -Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO t2 SELECT * FROM view_retval_2; Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. * Invoke statement so that return value is dicarded: expect no warning. @@ -1014,7 +836,7 @@ PREPARE prep_2 FROM "INSERT INTO t1 SELECT * FROM view_retval_1"; * binlog_format = STATEMENT: expect 1 warnings. EXECUTE prep_2; Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP PREPARE prep_2; @@ -1025,7 +847,7 @@ PREPARE prep_1 FROM "INSERT INTO t0 SELECT * FROM data_table LIMIT 1"; * binlog_format = STATEMENT: expect 1 warnings. EXECUTE prep_1; Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP PREPARE prep_1; @@ -1034,7 +856,7 @@ Invoking unsafe SELECT...LIMIT statement. * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO t0 SELECT * FROM data_table LIMIT 1; Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. * Invoke statement so that return value is dicarded: expect no warning. @@ -1047,7 +869,7 @@ CREATE FUNCTION func_sidef_1() RETURNS VARCHAR(100) BEGIN INSERT INTO ta1 VALUES * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO t1 SELECT func_sidef_1(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses INSERT DELAYED. This is unsafe because the time when rows are inserted cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses INSERT DELAYED. This is unsafe because the times when rows are inserted cannot be predicted. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. @@ -1056,33 +878,19 @@ CREATE FUNCTION func_sidef_2() RETURNS VARCHAR(100) BEGIN INSERT INTO ta2 VALUES * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO t2 SELECT func_sidef_2(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses INSERT DELAYED. This is unsafe because the time when rows are inserted cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses INSERT DELAYED. This is unsafe because the times when rows are inserted cannot be predicted. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP FUNCTION func_sidef_2; Invoking procedure proc_2 invoking function func_sidef_1 invoking unsafe INSERT DELAYED statement. -CREATE PROCEDURE proc_2() BEGIN INSERT INTO ta2 VALUES (47); INSERT INTO t1 SELECT func_sidef_1(); END; +CREATE PROCEDURE proc_2() BEGIN INSERT INTO t1 SELECT func_sidef_1(); INSERT INTO ta2 VALUES (47); END; * binlog_format = STATEMENT: expect 1 warnings. CALL proc_2(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses INSERT DELAYED. This is unsafe because the time when rows are inserted cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses INSERT DELAYED. This is unsafe because the times when rows are inserted cannot be predicted. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. -******** Failure! Event number 3 was a 'Query', not a 'Table_map'. ******** -SHOW BINLOG EVENTS FROM ; -Log_name Pos Event_type Server_id End_log_pos Info -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Query # # use `test`; INSERT INTO ta2 VALUES (47) -master-bin.000001 # Query # # COMMIT -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Table_map # # table_id: # (test.t1) -master-bin.000001 # Table_map # # table_id: # (test.t0) -master-bin.000001 # Table_map # # table_id: # (test.ta1) -master-bin.000001 # Write_rows # # table_id: # -master-bin.000001 # Write_rows # # table_id: # -master-bin.000001 # Write_rows # # table_id: # flags: STMT_END_F -master-bin.000001 # Query # # COMMIT DROP PROCEDURE proc_2; Invoking trigger trig_2 invoking function func_sidef_1 invoking unsafe INSERT DELAYED statement. @@ -1090,7 +898,7 @@ CREATE TRIGGER trig_2 BEFORE INSERT ON trigger_table_2 FOR EACH ROW BEGIN INSERT * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO trigger_table_2 VALUES (1); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses INSERT DELAYED. This is unsafe because the time when rows are inserted cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses INSERT DELAYED. This is unsafe because the times when rows are inserted cannot be predicted. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP TRIGGER trig_2; @@ -1098,11 +906,11 @@ DROP TRIGGER trig_2; Invoking view view_sidef_2 invoking function func_sidef_1 invoking unsafe INSERT DELAYED statement. CREATE VIEW view_sidef_2 AS SELECT func_sidef_1(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses INSERT DELAYED. This is unsafe because the time when rows are inserted cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses INSERT DELAYED. This is unsafe because the times when rows are inserted cannot be predicted. * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO t2 SELECT * FROM view_sidef_2; Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses INSERT DELAYED. This is unsafe because the time when rows are inserted cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses INSERT DELAYED. This is unsafe because the times when rows are inserted cannot be predicted. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP VIEW view_sidef_2; @@ -1112,18 +920,18 @@ PREPARE prep_2 FROM "INSERT INTO t1 SELECT func_sidef_1()"; * binlog_format = STATEMENT: expect 1 warnings. EXECUTE prep_2; Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses INSERT DELAYED. This is unsafe because the time when rows are inserted cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses INSERT DELAYED. This is unsafe because the times when rows are inserted cannot be predicted. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP PREPARE prep_2; DROP FUNCTION func_sidef_1; Invoking procedure proc_1 invoking unsafe INSERT DELAYED statement. -CREATE PROCEDURE proc_1() BEGIN INSERT INTO ta1 VALUES (47); INSERT DELAYED INTO t0 VALUES (1), (2); END; +CREATE PROCEDURE proc_1() BEGIN INSERT DELAYED INTO t0 VALUES (1), (2); INSERT INTO ta1 VALUES (47); END; * binlog_format = STATEMENT: expect 1 warnings. CALL proc_1(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses INSERT DELAYED. This is unsafe because the time when rows are inserted cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses INSERT DELAYED. This is unsafe because the times when rows are inserted cannot be predicted. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. @@ -1132,33 +940,19 @@ CREATE FUNCTION func_sidef_2() RETURNS VARCHAR(100) BEGIN INSERT INTO ta2 VALUES * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO t2 SELECT func_sidef_2(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses INSERT DELAYED. This is unsafe because the time when rows are inserted cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses INSERT DELAYED. This is unsafe because the times when rows are inserted cannot be predicted. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP FUNCTION func_sidef_2; Invoking procedure proc_2 invoking procedure proc_1 invoking unsafe INSERT DELAYED statement. -CREATE PROCEDURE proc_2() BEGIN INSERT INTO ta2 VALUES (47); CALL proc_1(); END; +CREATE PROCEDURE proc_2() BEGIN CALL proc_1(); INSERT INTO ta2 VALUES (47); END; * binlog_format = STATEMENT: expect 1 warnings. CALL proc_2(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses INSERT DELAYED. This is unsafe because the time when rows are inserted cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses INSERT DELAYED. This is unsafe because the times when rows are inserted cannot be predicted. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. -******** Failure! Event number 3 was a 'Query', not a 'Table_map'. ******** -SHOW BINLOG EVENTS FROM ; -Log_name Pos Event_type Server_id End_log_pos Info -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Query # # use `test`; INSERT INTO ta2 VALUES (47) -master-bin.000001 # Query # # COMMIT -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Table_map # # table_id: # (test.ta1) -master-bin.000001 # Write_rows # # table_id: # flags: STMT_END_F -master-bin.000001 # Query # # COMMIT -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Table_map # # table_id: # (test.t0) -master-bin.000001 # Write_rows # # table_id: # flags: STMT_END_F -master-bin.000001 # Query # # COMMIT DROP PROCEDURE proc_2; Invoking trigger trig_2 invoking procedure proc_1 invoking unsafe INSERT DELAYED statement. @@ -1166,7 +960,7 @@ CREATE TRIGGER trig_2 BEFORE INSERT ON trigger_table_2 FOR EACH ROW BEGIN INSERT * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO trigger_table_2 VALUES (1); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses INSERT DELAYED. This is unsafe because the time when rows are inserted cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses INSERT DELAYED. This is unsafe because the times when rows are inserted cannot be predicted. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP TRIGGER trig_2; @@ -1176,7 +970,7 @@ PREPARE prep_2 FROM "CALL proc_1()"; * binlog_format = STATEMENT: expect 1 warnings. EXECUTE prep_2; Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses INSERT DELAYED. This is unsafe because the time when rows are inserted cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses INSERT DELAYED. This is unsafe because the times when rows are inserted cannot be predicted. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP PREPARE prep_2; @@ -1187,7 +981,7 @@ CREATE TRIGGER trig_1 BEFORE INSERT ON trigger_table_1 FOR EACH ROW BEGIN INSERT * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO trigger_table_1 VALUES (1); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses INSERT DELAYED. This is unsafe because the time when rows are inserted cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses INSERT DELAYED. This is unsafe because the times when rows are inserted cannot be predicted. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. @@ -1196,33 +990,19 @@ CREATE FUNCTION func_sidef_2() RETURNS VARCHAR(100) BEGIN INSERT INTO ta2 VALUES * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO t2 SELECT func_sidef_2(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses INSERT DELAYED. This is unsafe because the time when rows are inserted cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses INSERT DELAYED. This is unsafe because the times when rows are inserted cannot be predicted. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP FUNCTION func_sidef_2; Invoking procedure proc_2 invoking trigger trig_1 invoking unsafe INSERT DELAYED statement. -CREATE PROCEDURE proc_2() BEGIN INSERT INTO ta2 VALUES (47); INSERT INTO trigger_table_1 VALUES (1); END; +CREATE PROCEDURE proc_2() BEGIN INSERT INTO trigger_table_1 VALUES (1); INSERT INTO ta2 VALUES (47); END; * binlog_format = STATEMENT: expect 1 warnings. CALL proc_2(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses INSERT DELAYED. This is unsafe because the time when rows are inserted cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses INSERT DELAYED. This is unsafe because the times when rows are inserted cannot be predicted. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. -******** Failure! Event number 3 was a 'Query', not a 'Table_map'. ******** -SHOW BINLOG EVENTS FROM ; -Log_name Pos Event_type Server_id End_log_pos Info -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Query # # use `test`; INSERT INTO ta2 VALUES (47) -master-bin.000001 # Query # # COMMIT -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Table_map # # table_id: # (test.trigger_table_1) -master-bin.000001 # Table_map # # table_id: # (test.t0) -master-bin.000001 # Table_map # # table_id: # (test.ta1) -master-bin.000001 # Write_rows # # table_id: # -master-bin.000001 # Write_rows # # table_id: # -master-bin.000001 # Write_rows # # table_id: # flags: STMT_END_F -master-bin.000001 # Query # # COMMIT DROP PROCEDURE proc_2; Invoking trigger trig_2 invoking trigger trig_1 invoking unsafe INSERT DELAYED statement. @@ -1230,7 +1010,7 @@ CREATE TRIGGER trig_2 BEFORE INSERT ON trigger_table_2 FOR EACH ROW BEGIN INSERT * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO trigger_table_2 VALUES (1); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses INSERT DELAYED. This is unsafe because the time when rows are inserted cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses INSERT DELAYED. This is unsafe because the times when rows are inserted cannot be predicted. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP TRIGGER trig_2; @@ -1240,7 +1020,7 @@ PREPARE prep_2 FROM "INSERT INTO trigger_table_1 VALUES (1)"; * binlog_format = STATEMENT: expect 1 warnings. EXECUTE prep_2; Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses INSERT DELAYED. This is unsafe because the time when rows are inserted cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses INSERT DELAYED. This is unsafe because the times when rows are inserted cannot be predicted. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP PREPARE prep_2; @@ -1251,7 +1031,7 @@ PREPARE prep_1 FROM "INSERT DELAYED INTO t0 VALUES (1), (2)"; * binlog_format = STATEMENT: expect 1 warnings. EXECUTE prep_1; Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses INSERT DELAYED. This is unsafe because the time when rows are inserted cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses INSERT DELAYED. This is unsafe because the times when rows are inserted cannot be predicted. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP PREPARE prep_1; @@ -1260,7 +1040,7 @@ Invoking unsafe INSERT DELAYED statement. * binlog_format = STATEMENT: expect 1 warnings. INSERT DELAYED INTO t0 VALUES (1), (2); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses INSERT DELAYED. This is unsafe because the time when rows are inserted cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses INSERT DELAYED. This is unsafe because the times when rows are inserted cannot be predicted. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. @@ -1271,7 +1051,7 @@ CREATE FUNCTION func_sidef_1() RETURNS VARCHAR(100) BEGIN INSERT INTO ta1 VALUES * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO t1 SELECT func_sidef_1(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it invokes a trigger or a stored function that inserts into AUTO_INCREMENT column. The inserted values cannot be correctly logged. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it invokes a trigger or a stored function that inserts into an AUTO_INCREMENT column. Inserted values cannot be logged correctly. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. @@ -1280,35 +1060,19 @@ CREATE FUNCTION func_sidef_2() RETURNS VARCHAR(100) BEGIN INSERT INTO ta2 VALUES * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO t2 SELECT func_sidef_2(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it invokes a trigger or a stored function that inserts into AUTO_INCREMENT column. The inserted values cannot be correctly logged. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it invokes a trigger or a stored function that inserts into an AUTO_INCREMENT column. Inserted values cannot be logged correctly. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP FUNCTION func_sidef_2; Invoking procedure proc_2 invoking function func_sidef_1 invoking unsafe update of two autoinc columns. -CREATE PROCEDURE proc_2() BEGIN INSERT INTO ta2 VALUES (47); INSERT INTO t1 SELECT func_sidef_1(); END; +CREATE PROCEDURE proc_2() BEGIN INSERT INTO t1 SELECT func_sidef_1(); INSERT INTO ta2 VALUES (47); END; * binlog_format = STATEMENT: expect 1 warnings. CALL proc_2(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it invokes a trigger or a stored function that inserts into AUTO_INCREMENT column. The inserted values cannot be correctly logged. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it invokes a trigger or a stored function that inserts into an AUTO_INCREMENT column. Inserted values cannot be logged correctly. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. -******** Failure! Event number 3 was a 'Query', not a 'Table_map'. ******** -SHOW BINLOG EVENTS FROM ; -Log_name Pos Event_type Server_id End_log_pos Info -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Query # # use `test`; INSERT INTO ta2 VALUES (47) -master-bin.000001 # Query # # COMMIT -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Table_map # # table_id: # (test.t1) -master-bin.000001 # Table_map # # table_id: # (test.double_autoinc_table) -master-bin.000001 # Table_map # # table_id: # (test.ta1) -master-bin.000001 # Table_map # # table_id: # (test.autoinc_table) -master-bin.000001 # Write_rows # # table_id: # -master-bin.000001 # Write_rows # # table_id: # -master-bin.000001 # Write_rows # # table_id: # -master-bin.000001 # Write_rows # # table_id: # flags: STMT_END_F -master-bin.000001 # Query # # COMMIT DROP PROCEDURE proc_2; Invoking trigger trig_2 invoking function func_sidef_1 invoking unsafe update of two autoinc columns. @@ -1316,7 +1080,7 @@ CREATE TRIGGER trig_2 BEFORE INSERT ON trigger_table_2 FOR EACH ROW BEGIN INSERT * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO trigger_table_2 VALUES (1); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it invokes a trigger or a stored function that inserts into AUTO_INCREMENT column. The inserted values cannot be correctly logged. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it invokes a trigger or a stored function that inserts into an AUTO_INCREMENT column. Inserted values cannot be logged correctly. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP TRIGGER trig_2; @@ -1324,11 +1088,11 @@ DROP TRIGGER trig_2; Invoking view view_sidef_2 invoking function func_sidef_1 invoking unsafe update of two autoinc columns. CREATE VIEW view_sidef_2 AS SELECT func_sidef_1(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it invokes a trigger or a stored function that inserts into AUTO_INCREMENT column. The inserted values cannot be correctly logged. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it invokes a trigger or a stored function that inserts into an AUTO_INCREMENT column. Inserted values cannot be logged correctly. * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO t2 SELECT * FROM view_sidef_2; Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it invokes a trigger or a stored function that inserts into AUTO_INCREMENT column. The inserted values cannot be correctly logged. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it invokes a trigger or a stored function that inserts into an AUTO_INCREMENT column. Inserted values cannot be logged correctly. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP VIEW view_sidef_2; @@ -1338,66 +1102,39 @@ PREPARE prep_2 FROM "INSERT INTO t1 SELECT func_sidef_1()"; * binlog_format = STATEMENT: expect 1 warnings. EXECUTE prep_2; Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it invokes a trigger or a stored function that inserts into AUTO_INCREMENT column. The inserted values cannot be correctly logged. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it invokes a trigger or a stored function that inserts into an AUTO_INCREMENT column. Inserted values cannot be logged correctly. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP PREPARE prep_2; DROP FUNCTION func_sidef_1; Invoking procedure proc_1 invoking unsafe update of two autoinc columns. -CREATE PROCEDURE proc_1() BEGIN INSERT INTO ta1 VALUES (47); INSERT INTO double_autoinc_table VALUES (NULL); END; +CREATE PROCEDURE proc_1() BEGIN INSERT INTO double_autoinc_table VALUES (NULL); INSERT INTO ta1 VALUES (47); END; * binlog_format = STATEMENT: expect 1 warnings. CALL proc_1(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it invokes a trigger or a stored function that inserts into AUTO_INCREMENT column. The inserted values cannot be correctly logged. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it invokes a trigger or a stored function that inserts into an AUTO_INCREMENT column. Inserted values cannot be logged correctly. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. -******** Failure! Event number 3 was a 'Query', not a 'Table_map'. ******** -SHOW BINLOG EVENTS FROM ; -Log_name Pos Event_type Server_id End_log_pos Info -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Query # # use `test`; INSERT INTO ta1 VALUES (47) -master-bin.000001 # Query # # COMMIT -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Table_map # # table_id: # (test.double_autoinc_table) -master-bin.000001 # Table_map # # table_id: # (test.autoinc_table) -master-bin.000001 # Write_rows # # table_id: # -master-bin.000001 # Write_rows # # table_id: # flags: STMT_END_F -master-bin.000001 # Query # # COMMIT Invoking function func_sidef_2 invoking procedure proc_1 invoking unsafe update of two autoinc columns. CREATE FUNCTION func_sidef_2() RETURNS VARCHAR(100) BEGIN INSERT INTO ta2 VALUES (47); CALL proc_1(); RETURN 0; END; * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO t2 SELECT func_sidef_2(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it invokes a trigger or a stored function that inserts into AUTO_INCREMENT column. The inserted values cannot be correctly logged. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it invokes a trigger or a stored function that inserts into an AUTO_INCREMENT column. Inserted values cannot be logged correctly. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP FUNCTION func_sidef_2; Invoking procedure proc_2 invoking procedure proc_1 invoking unsafe update of two autoinc columns. -CREATE PROCEDURE proc_2() BEGIN INSERT INTO ta2 VALUES (47); CALL proc_1(); END; +CREATE PROCEDURE proc_2() BEGIN CALL proc_1(); INSERT INTO ta2 VALUES (47); END; * binlog_format = STATEMENT: expect 1 warnings. CALL proc_2(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it invokes a trigger or a stored function that inserts into AUTO_INCREMENT column. The inserted values cannot be correctly logged. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it invokes a trigger or a stored function that inserts into an AUTO_INCREMENT column. Inserted values cannot be logged correctly. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. -******** Failure! Event number 3 was a 'Query', not a 'Table_map'. ******** -SHOW BINLOG EVENTS FROM ; -Log_name Pos Event_type Server_id End_log_pos Info -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Query # # use `test`; INSERT INTO ta2 VALUES (47) -master-bin.000001 # Query # # COMMIT -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Query # # use `test`; INSERT INTO ta1 VALUES (47) -master-bin.000001 # Query # # COMMIT -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Table_map # # table_id: # (test.double_autoinc_table) -master-bin.000001 # Table_map # # table_id: # (test.autoinc_table) -master-bin.000001 # Write_rows # # table_id: # -master-bin.000001 # Write_rows # # table_id: # flags: STMT_END_F -master-bin.000001 # Query # # COMMIT DROP PROCEDURE proc_2; Invoking trigger trig_2 invoking procedure proc_1 invoking unsafe update of two autoinc columns. @@ -1405,7 +1142,7 @@ CREATE TRIGGER trig_2 BEFORE INSERT ON trigger_table_2 FOR EACH ROW BEGIN INSERT * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO trigger_table_2 VALUES (1); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it invokes a trigger or a stored function that inserts into AUTO_INCREMENT column. The inserted values cannot be correctly logged. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it invokes a trigger or a stored function that inserts into an AUTO_INCREMENT column. Inserted values cannot be logged correctly. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP TRIGGER trig_2; @@ -1415,21 +1152,9 @@ PREPARE prep_2 FROM "CALL proc_1()"; * binlog_format = STATEMENT: expect 1 warnings. EXECUTE prep_2; Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it invokes a trigger or a stored function that inserts into AUTO_INCREMENT column. The inserted values cannot be correctly logged. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it invokes a trigger or a stored function that inserts into an AUTO_INCREMENT column. Inserted values cannot be logged correctly. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. -******** Failure! Event number 3 was a 'Query', not a 'Table_map'. ******** -SHOW BINLOG EVENTS FROM ; -Log_name Pos Event_type Server_id End_log_pos Info -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Query # # use `test`; INSERT INTO ta1 VALUES (47) -master-bin.000001 # Query # # COMMIT -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Table_map # # table_id: # (test.double_autoinc_table) -master-bin.000001 # Table_map # # table_id: # (test.autoinc_table) -master-bin.000001 # Write_rows # # table_id: # -master-bin.000001 # Write_rows # # table_id: # flags: STMT_END_F -master-bin.000001 # Query # # COMMIT DROP PREPARE prep_2; DROP PROCEDURE proc_1; @@ -1438,7 +1163,7 @@ CREATE TRIGGER trig_1 BEFORE INSERT ON trigger_table_1 FOR EACH ROW BEGIN INSERT * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO trigger_table_1 VALUES (1); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it invokes a trigger or a stored function that inserts into AUTO_INCREMENT column. The inserted values cannot be correctly logged. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it invokes a trigger or a stored function that inserts into an AUTO_INCREMENT column. Inserted values cannot be logged correctly. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. @@ -1447,35 +1172,19 @@ CREATE FUNCTION func_sidef_2() RETURNS VARCHAR(100) BEGIN INSERT INTO ta2 VALUES * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO t2 SELECT func_sidef_2(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it invokes a trigger or a stored function that inserts into AUTO_INCREMENT column. The inserted values cannot be correctly logged. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it invokes a trigger or a stored function that inserts into an AUTO_INCREMENT column. Inserted values cannot be logged correctly. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP FUNCTION func_sidef_2; Invoking procedure proc_2 invoking trigger trig_1 invoking unsafe update of two autoinc columns. -CREATE PROCEDURE proc_2() BEGIN INSERT INTO ta2 VALUES (47); INSERT INTO trigger_table_1 VALUES (1); END; +CREATE PROCEDURE proc_2() BEGIN INSERT INTO trigger_table_1 VALUES (1); INSERT INTO ta2 VALUES (47); END; * binlog_format = STATEMENT: expect 1 warnings. CALL proc_2(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it invokes a trigger or a stored function that inserts into AUTO_INCREMENT column. The inserted values cannot be correctly logged. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it invokes a trigger or a stored function that inserts into an AUTO_INCREMENT column. Inserted values cannot be logged correctly. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. -******** Failure! Event number 3 was a 'Query', not a 'Table_map'. ******** -SHOW BINLOG EVENTS FROM ; -Log_name Pos Event_type Server_id End_log_pos Info -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Query # # use `test`; INSERT INTO ta2 VALUES (47) -master-bin.000001 # Query # # COMMIT -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Table_map # # table_id: # (test.trigger_table_1) -master-bin.000001 # Table_map # # table_id: # (test.double_autoinc_table) -master-bin.000001 # Table_map # # table_id: # (test.ta1) -master-bin.000001 # Table_map # # table_id: # (test.autoinc_table) -master-bin.000001 # Write_rows # # table_id: # -master-bin.000001 # Write_rows # # table_id: # -master-bin.000001 # Write_rows # # table_id: # -master-bin.000001 # Write_rows # # table_id: # flags: STMT_END_F -master-bin.000001 # Query # # COMMIT DROP PROCEDURE proc_2; Invoking trigger trig_2 invoking trigger trig_1 invoking unsafe update of two autoinc columns. @@ -1483,7 +1192,7 @@ CREATE TRIGGER trig_2 BEFORE INSERT ON trigger_table_2 FOR EACH ROW BEGIN INSERT * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO trigger_table_2 VALUES (1); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it invokes a trigger or a stored function that inserts into AUTO_INCREMENT column. The inserted values cannot be correctly logged. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it invokes a trigger or a stored function that inserts into an AUTO_INCREMENT column. Inserted values cannot be logged correctly. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP TRIGGER trig_2; @@ -1493,7 +1202,7 @@ PREPARE prep_2 FROM "INSERT INTO trigger_table_1 VALUES (1)"; * binlog_format = STATEMENT: expect 1 warnings. EXECUTE prep_2; Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it invokes a trigger or a stored function that inserts into AUTO_INCREMENT column. The inserted values cannot be correctly logged. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it invokes a trigger or a stored function that inserts into an AUTO_INCREMENT column. Inserted values cannot be logged correctly. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP PREPARE prep_2; @@ -1504,7 +1213,7 @@ PREPARE prep_1 FROM "INSERT INTO double_autoinc_table VALUES (NULL)"; * binlog_format = STATEMENT: expect 1 warnings. EXECUTE prep_1; Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it invokes a trigger or a stored function that inserts into AUTO_INCREMENT column. The inserted values cannot be correctly logged. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it invokes a trigger or a stored function that inserts into an AUTO_INCREMENT column. Inserted values cannot be logged correctly. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP PREPARE prep_1; @@ -1513,7 +1222,7 @@ Invoking unsafe update of two autoinc columns. * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO double_autoinc_table VALUES (NULL); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it invokes a trigger or a stored function that inserts into AUTO_INCREMENT column. The inserted values cannot be correctly logged. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it invokes a trigger or a stored function that inserts into an AUTO_INCREMENT column. Inserted values cannot be logged correctly. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. @@ -1524,7 +1233,7 @@ CREATE FUNCTION func_retval_1() RETURNS VARCHAR(100) BEGIN INSERT INTO ta1 VALUE * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO t1 VALUES (func_retval_1()); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a UDF. It cannot be determined if the UDF will return the same value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a UDF which may not return the same value on the slave. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. * Invoke statement so that return value is dicarded: expect no warning. @@ -1535,7 +1244,7 @@ CREATE FUNCTION func_retval_2() RETURNS VARCHAR(100) BEGIN INSERT INTO ta2 VALUE * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO t2 VALUES (func_retval_2()); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a UDF. It cannot be determined if the UDF will return the same value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a UDF which may not return the same value on the slave. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. * Invoke statement so that return value is dicarded: expect no warning. @@ -1547,31 +1256,19 @@ CREATE FUNCTION func_sidef_2() RETURNS VARCHAR(100) BEGIN INSERT INTO ta2 VALUES * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO t2 SELECT func_sidef_2(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a UDF. It cannot be determined if the UDF will return the same value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a UDF which may not return the same value on the slave. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP FUNCTION func_sidef_2; Invoking procedure proc_2 invoking function func_retval_1 returning value from unsafe UDF. -CREATE PROCEDURE proc_2() BEGIN INSERT INTO ta2 VALUES (47); INSERT INTO t1 VALUES (func_retval_1()); END; +CREATE PROCEDURE proc_2() BEGIN INSERT INTO t1 VALUES (func_retval_1()); INSERT INTO ta2 VALUES (47); END; * binlog_format = STATEMENT: expect 1 warnings. CALL proc_2(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a UDF. It cannot be determined if the UDF will return the same value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a UDF which may not return the same value on the slave. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. -******** Failure! Event number 3 was a 'Query', not a 'Table_map'. ******** -SHOW BINLOG EVENTS FROM ; -Log_name Pos Event_type Server_id End_log_pos Info -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Query # # use `test`; INSERT INTO ta2 VALUES (47) -master-bin.000001 # Query # # COMMIT -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Table_map # # table_id: # (test.t1) -master-bin.000001 # Table_map # # table_id: # (test.ta1) -master-bin.000001 # Write_rows # # table_id: # -master-bin.000001 # Write_rows # # table_id: # flags: STMT_END_F -master-bin.000001 # Query # # COMMIT DROP PROCEDURE proc_2; Invoking trigger trig_2 invoking function func_retval_1 returning value from unsafe UDF. @@ -1579,7 +1276,7 @@ CREATE TRIGGER trig_2 BEFORE INSERT ON trigger_table_2 FOR EACH ROW BEGIN INSERT * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO trigger_table_2 VALUES (1); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a UDF. It cannot be determined if the UDF will return the same value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a UDF which may not return the same value on the slave. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP TRIGGER trig_2; @@ -1587,11 +1284,11 @@ DROP TRIGGER trig_2; Invoking view view_retval_2 returning value from function func_retval_1 returning value from unsafe UDF. CREATE VIEW view_retval_2 AS SELECT func_retval_1(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a UDF. It cannot be determined if the UDF will return the same value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a UDF which may not return the same value on the slave. * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO t2 SELECT * FROM view_retval_2; Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a UDF. It cannot be determined if the UDF will return the same value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a UDF which may not return the same value on the slave. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. * Invoke statement so that return value is dicarded: expect no warning. @@ -1603,7 +1300,7 @@ PREPARE prep_2 FROM "INSERT INTO t1 VALUES (func_retval_1())"; * binlog_format = STATEMENT: expect 1 warnings. EXECUTE prep_2; Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a UDF. It cannot be determined if the UDF will return the same value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a UDF which may not return the same value on the slave. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP PREPARE prep_2; @@ -1614,7 +1311,7 @@ CREATE FUNCTION func_sidef_1() RETURNS VARCHAR(100) BEGIN INSERT INTO ta1 VALUES * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO t1 SELECT func_sidef_1(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a UDF. It cannot be determined if the UDF will return the same value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a UDF which may not return the same value on the slave. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. @@ -1623,33 +1320,19 @@ CREATE FUNCTION func_sidef_2() RETURNS VARCHAR(100) BEGIN INSERT INTO ta2 VALUES * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO t2 SELECT func_sidef_2(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a UDF. It cannot be determined if the UDF will return the same value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a UDF which may not return the same value on the slave. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP FUNCTION func_sidef_2; Invoking procedure proc_2 invoking function func_sidef_1 invoking unsafe UDF. -CREATE PROCEDURE proc_2() BEGIN INSERT INTO ta2 VALUES (47); INSERT INTO t1 SELECT func_sidef_1(); END; +CREATE PROCEDURE proc_2() BEGIN INSERT INTO t1 SELECT func_sidef_1(); INSERT INTO ta2 VALUES (47); END; * binlog_format = STATEMENT: expect 1 warnings. CALL proc_2(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a UDF. It cannot be determined if the UDF will return the same value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a UDF which may not return the same value on the slave. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. -******** Failure! Event number 3 was a 'Query', not a 'Table_map'. ******** -SHOW BINLOG EVENTS FROM ; -Log_name Pos Event_type Server_id End_log_pos Info -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Query # # use `test`; INSERT INTO ta2 VALUES (47) -master-bin.000001 # Query # # COMMIT -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Table_map # # table_id: # (test.t1) -master-bin.000001 # Table_map # # table_id: # (test.t0) -master-bin.000001 # Table_map # # table_id: # (test.ta1) -master-bin.000001 # Write_rows # # table_id: # -master-bin.000001 # Write_rows # # table_id: # -master-bin.000001 # Write_rows # # table_id: # flags: STMT_END_F -master-bin.000001 # Query # # COMMIT DROP PROCEDURE proc_2; Invoking trigger trig_2 invoking function func_sidef_1 invoking unsafe UDF. @@ -1657,7 +1340,7 @@ CREATE TRIGGER trig_2 BEFORE INSERT ON trigger_table_2 FOR EACH ROW BEGIN INSERT * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO trigger_table_2 VALUES (1); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a UDF. It cannot be determined if the UDF will return the same value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a UDF which may not return the same value on the slave. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP TRIGGER trig_2; @@ -1665,11 +1348,11 @@ DROP TRIGGER trig_2; Invoking view view_sidef_2 invoking function func_sidef_1 invoking unsafe UDF. CREATE VIEW view_sidef_2 AS SELECT func_sidef_1(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a UDF. It cannot be determined if the UDF will return the same value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a UDF which may not return the same value on the slave. * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO t2 SELECT * FROM view_sidef_2; Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a UDF. It cannot be determined if the UDF will return the same value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a UDF which may not return the same value on the slave. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP VIEW view_sidef_2; @@ -1679,18 +1362,18 @@ PREPARE prep_2 FROM "INSERT INTO t1 SELECT func_sidef_1()"; * binlog_format = STATEMENT: expect 1 warnings. EXECUTE prep_2; Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a UDF. It cannot be determined if the UDF will return the same value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a UDF which may not return the same value on the slave. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP PREPARE prep_2; DROP FUNCTION func_sidef_1; Invoking procedure proc_1 invoking unsafe UDF. -CREATE PROCEDURE proc_1() BEGIN INSERT INTO ta1 VALUES (47); INSERT INTO t0 VALUES (myfunc_int(10)); END; +CREATE PROCEDURE proc_1() BEGIN INSERT INTO t0 VALUES (myfunc_int(10)); INSERT INTO ta1 VALUES (47); END; * binlog_format = STATEMENT: expect 1 warnings. CALL proc_1(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a UDF. It cannot be determined if the UDF will return the same value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a UDF which may not return the same value on the slave. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. @@ -1699,33 +1382,19 @@ CREATE FUNCTION func_sidef_2() RETURNS VARCHAR(100) BEGIN INSERT INTO ta2 VALUES * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO t2 SELECT func_sidef_2(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a UDF. It cannot be determined if the UDF will return the same value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a UDF which may not return the same value on the slave. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP FUNCTION func_sidef_2; Invoking procedure proc_2 invoking procedure proc_1 invoking unsafe UDF. -CREATE PROCEDURE proc_2() BEGIN INSERT INTO ta2 VALUES (47); CALL proc_1(); END; +CREATE PROCEDURE proc_2() BEGIN CALL proc_1(); INSERT INTO ta2 VALUES (47); END; * binlog_format = STATEMENT: expect 1 warnings. CALL proc_2(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a UDF. It cannot be determined if the UDF will return the same value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a UDF which may not return the same value on the slave. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. -******** Failure! Event number 3 was a 'Query', not a 'Table_map'. ******** -SHOW BINLOG EVENTS FROM ; -Log_name Pos Event_type Server_id End_log_pos Info -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Query # # use `test`; INSERT INTO ta2 VALUES (47) -master-bin.000001 # Query # # COMMIT -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Table_map # # table_id: # (test.ta1) -master-bin.000001 # Write_rows # # table_id: # flags: STMT_END_F -master-bin.000001 # Query # # COMMIT -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Table_map # # table_id: # (test.t0) -master-bin.000001 # Write_rows # # table_id: # flags: STMT_END_F -master-bin.000001 # Query # # COMMIT DROP PROCEDURE proc_2; Invoking trigger trig_2 invoking procedure proc_1 invoking unsafe UDF. @@ -1733,7 +1402,7 @@ CREATE TRIGGER trig_2 BEFORE INSERT ON trigger_table_2 FOR EACH ROW BEGIN INSERT * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO trigger_table_2 VALUES (1); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a UDF. It cannot be determined if the UDF will return the same value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a UDF which may not return the same value on the slave. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP TRIGGER trig_2; @@ -1743,7 +1412,7 @@ PREPARE prep_2 FROM "CALL proc_1()"; * binlog_format = STATEMENT: expect 1 warnings. EXECUTE prep_2; Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a UDF. It cannot be determined if the UDF will return the same value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a UDF which may not return the same value on the slave. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP PREPARE prep_2; @@ -1754,7 +1423,7 @@ CREATE TRIGGER trig_1 BEFORE INSERT ON trigger_table_1 FOR EACH ROW BEGIN INSERT * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO trigger_table_1 VALUES (1); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a UDF. It cannot be determined if the UDF will return the same value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a UDF which may not return the same value on the slave. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. @@ -1763,33 +1432,19 @@ CREATE FUNCTION func_sidef_2() RETURNS VARCHAR(100) BEGIN INSERT INTO ta2 VALUES * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO t2 SELECT func_sidef_2(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a UDF. It cannot be determined if the UDF will return the same value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a UDF which may not return the same value on the slave. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP FUNCTION func_sidef_2; Invoking procedure proc_2 invoking trigger trig_1 invoking unsafe UDF. -CREATE PROCEDURE proc_2() BEGIN INSERT INTO ta2 VALUES (47); INSERT INTO trigger_table_1 VALUES (1); END; +CREATE PROCEDURE proc_2() BEGIN INSERT INTO trigger_table_1 VALUES (1); INSERT INTO ta2 VALUES (47); END; * binlog_format = STATEMENT: expect 1 warnings. CALL proc_2(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a UDF. It cannot be determined if the UDF will return the same value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a UDF which may not return the same value on the slave. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. -******** Failure! Event number 3 was a 'Query', not a 'Table_map'. ******** -SHOW BINLOG EVENTS FROM ; -Log_name Pos Event_type Server_id End_log_pos Info -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Query # # use `test`; INSERT INTO ta2 VALUES (47) -master-bin.000001 # Query # # COMMIT -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Table_map # # table_id: # (test.trigger_table_1) -master-bin.000001 # Table_map # # table_id: # (test.t0) -master-bin.000001 # Table_map # # table_id: # (test.ta1) -master-bin.000001 # Write_rows # # table_id: # -master-bin.000001 # Write_rows # # table_id: # -master-bin.000001 # Write_rows # # table_id: # flags: STMT_END_F -master-bin.000001 # Query # # COMMIT DROP PROCEDURE proc_2; Invoking trigger trig_2 invoking trigger trig_1 invoking unsafe UDF. @@ -1797,7 +1452,7 @@ CREATE TRIGGER trig_2 BEFORE INSERT ON trigger_table_2 FOR EACH ROW BEGIN INSERT * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO trigger_table_2 VALUES (1); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a UDF. It cannot be determined if the UDF will return the same value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a UDF which may not return the same value on the slave. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP TRIGGER trig_2; @@ -1807,7 +1462,7 @@ PREPARE prep_2 FROM "INSERT INTO trigger_table_1 VALUES (1)"; * binlog_format = STATEMENT: expect 1 warnings. EXECUTE prep_2; Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a UDF. It cannot be determined if the UDF will return the same value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a UDF which may not return the same value on the slave. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP PREPARE prep_2; @@ -1815,12 +1470,10 @@ DROP TRIGGER trig_1; Invoking view view_sidef_1 invoking unsafe UDF. CREATE VIEW view_sidef_1 AS SELECT myfunc_int(10); -Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a UDF. It cannot be determined if the UDF will return the same value on slave. * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO t1 SELECT * FROM view_sidef_1; Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a UDF. It cannot be determined if the UDF will return the same value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a UDF which may not return the same value on the slave. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. @@ -1829,29 +1482,19 @@ CREATE FUNCTION func_sidef_2() RETURNS VARCHAR(100) BEGIN INSERT INTO ta2 VALUES * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO t2 SELECT func_sidef_2(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a UDF. It cannot be determined if the UDF will return the same value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a UDF which may not return the same value on the slave. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP FUNCTION func_sidef_2; Invoking procedure proc_2 invoking view view_sidef_1 invoking unsafe UDF. -CREATE PROCEDURE proc_2() BEGIN INSERT INTO ta2 VALUES (47); INSERT INTO t1 SELECT * FROM view_sidef_1; END; +CREATE PROCEDURE proc_2() BEGIN INSERT INTO t1 SELECT * FROM view_sidef_1; INSERT INTO ta2 VALUES (47); END; * binlog_format = STATEMENT: expect 1 warnings. CALL proc_2(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a UDF. It cannot be determined if the UDF will return the same value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a UDF which may not return the same value on the slave. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. -******** Failure! Event number 3 was a 'Query', not a 'Table_map'. ******** -SHOW BINLOG EVENTS FROM ; -Log_name Pos Event_type Server_id End_log_pos Info -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Query # # use `test`; INSERT INTO ta2 VALUES (47) -master-bin.000001 # Query # # COMMIT -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Table_map # # table_id: # (test.t1) -master-bin.000001 # Write_rows # # table_id: # flags: STMT_END_F -master-bin.000001 # Query # # COMMIT DROP PROCEDURE proc_2; Invoking trigger trig_2 invoking view view_sidef_1 invoking unsafe UDF. @@ -1859,19 +1502,17 @@ CREATE TRIGGER trig_2 BEFORE INSERT ON trigger_table_2 FOR EACH ROW BEGIN INSERT * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO trigger_table_2 VALUES (1); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a UDF. It cannot be determined if the UDF will return the same value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a UDF which may not return the same value on the slave. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP TRIGGER trig_2; Invoking view view_sidef_2 invoking view view_sidef_1 invoking unsafe UDF. CREATE VIEW view_sidef_2 AS SELECT * FROM view_sidef_1; -Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a UDF. It cannot be determined if the UDF will return the same value on slave. * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO t2 SELECT * FROM view_sidef_2; Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a UDF. It cannot be determined if the UDF will return the same value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a UDF which may not return the same value on the slave. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP VIEW view_sidef_2; @@ -1881,7 +1522,7 @@ PREPARE prep_2 FROM "INSERT INTO t1 SELECT * FROM view_sidef_1"; * binlog_format = STATEMENT: expect 1 warnings. EXECUTE prep_2; Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a UDF. It cannot be determined if the UDF will return the same value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a UDF which may not return the same value on the slave. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP PREPARE prep_2; @@ -1892,7 +1533,7 @@ PREPARE prep_1 FROM "INSERT INTO t0 VALUES (myfunc_int(10))"; * binlog_format = STATEMENT: expect 1 warnings. EXECUTE prep_1; Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a UDF. It cannot be determined if the UDF will return the same value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a UDF which may not return the same value on the slave. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP PREPARE prep_1; @@ -1901,7 +1542,7 @@ Invoking unsafe UDF. * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO t0 VALUES (myfunc_int(10)); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a UDF. It cannot be determined if the UDF will return the same value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a UDF which may not return the same value on the slave. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. @@ -1912,7 +1553,7 @@ CREATE FUNCTION func_sidef_1() RETURNS VARCHAR(100) BEGIN INSERT INTO ta1 VALUES * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO t1 SELECT func_sidef_1(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general_log, slow_log or performance_schema table(s). This is unsafe because system tables may differ on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general log, slow query log, or performance_schema table(s). This is unsafe because system tables may differ on slaves. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. @@ -1921,33 +1562,19 @@ CREATE FUNCTION func_sidef_2() RETURNS VARCHAR(100) BEGIN INSERT INTO ta2 VALUES * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO t2 SELECT func_sidef_2(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general_log, slow_log or performance_schema table(s). This is unsafe because system tables may differ on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general log, slow query log, or performance_schema table(s). This is unsafe because system tables may differ on slaves. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP FUNCTION func_sidef_2; Invoking procedure proc_2 invoking function func_sidef_1 invoking unsafe use of mysql.general_log. -CREATE PROCEDURE proc_2() BEGIN INSERT INTO ta2 VALUES (47); INSERT INTO t1 SELECT func_sidef_1(); END; +CREATE PROCEDURE proc_2() BEGIN INSERT INTO t1 SELECT func_sidef_1(); INSERT INTO ta2 VALUES (47); END; * binlog_format = STATEMENT: expect 1 warnings. CALL proc_2(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general_log, slow_log or performance_schema table(s). This is unsafe because system tables may differ on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general log, slow query log, or performance_schema table(s). This is unsafe because system tables may differ on slaves. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. -******** Failure! Event number 3 was a 'Query', not a 'Table_map'. ******** -SHOW BINLOG EVENTS FROM ; -Log_name Pos Event_type Server_id End_log_pos Info -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Query # # use `test`; INSERT INTO ta2 VALUES (47) -master-bin.000001 # Query # # COMMIT -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Table_map # # table_id: # (test.t1) -master-bin.000001 # Table_map # # table_id: # (test.t0) -master-bin.000001 # Table_map # # table_id: # (test.ta1) -master-bin.000001 # Write_rows # # table_id: # -master-bin.000001 # Write_rows # # table_id: # -master-bin.000001 # Write_rows # # table_id: # flags: STMT_END_F -master-bin.000001 # Query # # COMMIT DROP PROCEDURE proc_2; Invoking trigger trig_2 invoking function func_sidef_1 invoking unsafe use of mysql.general_log. @@ -1955,7 +1582,7 @@ CREATE TRIGGER trig_2 BEFORE INSERT ON trigger_table_2 FOR EACH ROW BEGIN INSERT * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO trigger_table_2 VALUES (1); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general_log, slow_log or performance_schema table(s). This is unsafe because system tables may differ on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general log, slow query log, or performance_schema table(s). This is unsafe because system tables may differ on slaves. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP TRIGGER trig_2; @@ -1963,11 +1590,11 @@ DROP TRIGGER trig_2; Invoking view view_sidef_2 invoking function func_sidef_1 invoking unsafe use of mysql.general_log. CREATE VIEW view_sidef_2 AS SELECT func_sidef_1(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general_log, slow_log or performance_schema table(s). This is unsafe because system tables may differ on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general log, slow query log, or performance_schema table(s). This is unsafe because system tables may differ on slaves. * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO t2 SELECT * FROM view_sidef_2; Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general_log, slow_log or performance_schema table(s). This is unsafe because system tables may differ on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general log, slow query log, or performance_schema table(s). This is unsafe because system tables may differ on slaves. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP VIEW view_sidef_2; @@ -1977,62 +1604,39 @@ PREPARE prep_2 FROM "INSERT INTO t1 SELECT func_sidef_1()"; * binlog_format = STATEMENT: expect 1 warnings. EXECUTE prep_2; Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general_log, slow_log or performance_schema table(s). This is unsafe because system tables may differ on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general log, slow query log, or performance_schema table(s). This is unsafe because system tables may differ on slaves. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP PREPARE prep_2; DROP FUNCTION func_sidef_1; Invoking procedure proc_1 invoking unsafe use of mysql.general_log. -CREATE PROCEDURE proc_1() BEGIN INSERT INTO ta1 VALUES (47); INSERT INTO t0 SELECT COUNT(*) FROM mysql.general_log; END; +CREATE PROCEDURE proc_1() BEGIN INSERT INTO t0 SELECT COUNT(*) FROM mysql.general_log; INSERT INTO ta1 VALUES (47); END; * binlog_format = STATEMENT: expect 1 warnings. CALL proc_1(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general_log, slow_log or performance_schema table(s). This is unsafe because system tables may differ on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general log, slow query log, or performance_schema table(s). This is unsafe because system tables may differ on slaves. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. -******** Failure! Event number 3 was a 'Query', not a 'Table_map'. ******** -SHOW BINLOG EVENTS FROM ; -Log_name Pos Event_type Server_id End_log_pos Info -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Query # # use `test`; INSERT INTO ta1 VALUES (47) -master-bin.000001 # Query # # COMMIT -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Table_map # # table_id: # (test.t0) -master-bin.000001 # Write_rows # # table_id: # flags: STMT_END_F -master-bin.000001 # Query # # COMMIT Invoking function func_sidef_2 invoking procedure proc_1 invoking unsafe use of mysql.general_log. CREATE FUNCTION func_sidef_2() RETURNS VARCHAR(100) BEGIN INSERT INTO ta2 VALUES (47); CALL proc_1(); RETURN 0; END; * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO t2 SELECT func_sidef_2(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general_log, slow_log or performance_schema table(s). This is unsafe because system tables may differ on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general log, slow query log, or performance_schema table(s). This is unsafe because system tables may differ on slaves. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP FUNCTION func_sidef_2; Invoking procedure proc_2 invoking procedure proc_1 invoking unsafe use of mysql.general_log. -CREATE PROCEDURE proc_2() BEGIN INSERT INTO ta2 VALUES (47); CALL proc_1(); END; +CREATE PROCEDURE proc_2() BEGIN CALL proc_1(); INSERT INTO ta2 VALUES (47); END; * binlog_format = STATEMENT: expect 1 warnings. CALL proc_2(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general_log, slow_log or performance_schema table(s). This is unsafe because system tables may differ on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general log, slow query log, or performance_schema table(s). This is unsafe because system tables may differ on slaves. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. -******** Failure! Event number 3 was a 'Query', not a 'Table_map'. ******** -SHOW BINLOG EVENTS FROM ; -Log_name Pos Event_type Server_id End_log_pos Info -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Query # # use `test`; INSERT INTO ta2 VALUES (47) -master-bin.000001 # Query # # COMMIT -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Query # # use `test`; INSERT INTO ta1 VALUES (47) -master-bin.000001 # Query # # COMMIT -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Table_map # # table_id: # (test.t0) -master-bin.000001 # Write_rows # # table_id: # flags: STMT_END_F -master-bin.000001 # Query # # COMMIT DROP PROCEDURE proc_2; Invoking trigger trig_2 invoking procedure proc_1 invoking unsafe use of mysql.general_log. @@ -2040,7 +1644,7 @@ CREATE TRIGGER trig_2 BEFORE INSERT ON trigger_table_2 FOR EACH ROW BEGIN INSERT * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO trigger_table_2 VALUES (1); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general_log, slow_log or performance_schema table(s). This is unsafe because system tables may differ on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general log, slow query log, or performance_schema table(s). This is unsafe because system tables may differ on slaves. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP TRIGGER trig_2; @@ -2050,19 +1654,9 @@ PREPARE prep_2 FROM "CALL proc_1()"; * binlog_format = STATEMENT: expect 1 warnings. EXECUTE prep_2; Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general_log, slow_log or performance_schema table(s). This is unsafe because system tables may differ on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general log, slow query log, or performance_schema table(s). This is unsafe because system tables may differ on slaves. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. -******** Failure! Event number 3 was a 'Query', not a 'Table_map'. ******** -SHOW BINLOG EVENTS FROM ; -Log_name Pos Event_type Server_id End_log_pos Info -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Query # # use `test`; INSERT INTO ta1 VALUES (47) -master-bin.000001 # Query # # COMMIT -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Table_map # # table_id: # (test.t0) -master-bin.000001 # Write_rows # # table_id: # flags: STMT_END_F -master-bin.000001 # Query # # COMMIT DROP PREPARE prep_2; DROP PROCEDURE proc_1; @@ -2071,7 +1665,7 @@ CREATE TRIGGER trig_1 BEFORE INSERT ON trigger_table_1 FOR EACH ROW BEGIN INSERT * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO trigger_table_1 VALUES (1); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general_log, slow_log or performance_schema table(s). This is unsafe because system tables may differ on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general log, slow query log, or performance_schema table(s). This is unsafe because system tables may differ on slaves. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. @@ -2080,33 +1674,19 @@ CREATE FUNCTION func_sidef_2() RETURNS VARCHAR(100) BEGIN INSERT INTO ta2 VALUES * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO t2 SELECT func_sidef_2(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general_log, slow_log or performance_schema table(s). This is unsafe because system tables may differ on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general log, slow query log, or performance_schema table(s). This is unsafe because system tables may differ on slaves. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP FUNCTION func_sidef_2; Invoking procedure proc_2 invoking trigger trig_1 invoking unsafe use of mysql.general_log. -CREATE PROCEDURE proc_2() BEGIN INSERT INTO ta2 VALUES (47); INSERT INTO trigger_table_1 VALUES (1); END; +CREATE PROCEDURE proc_2() BEGIN INSERT INTO trigger_table_1 VALUES (1); INSERT INTO ta2 VALUES (47); END; * binlog_format = STATEMENT: expect 1 warnings. CALL proc_2(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general_log, slow_log or performance_schema table(s). This is unsafe because system tables may differ on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general log, slow query log, or performance_schema table(s). This is unsafe because system tables may differ on slaves. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. -******** Failure! Event number 3 was a 'Query', not a 'Table_map'. ******** -SHOW BINLOG EVENTS FROM ; -Log_name Pos Event_type Server_id End_log_pos Info -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Query # # use `test`; INSERT INTO ta2 VALUES (47) -master-bin.000001 # Query # # COMMIT -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Table_map # # table_id: # (test.trigger_table_1) -master-bin.000001 # Table_map # # table_id: # (test.t0) -master-bin.000001 # Table_map # # table_id: # (test.ta1) -master-bin.000001 # Write_rows # # table_id: # -master-bin.000001 # Write_rows # # table_id: # -master-bin.000001 # Write_rows # # table_id: # flags: STMT_END_F -master-bin.000001 # Query # # COMMIT DROP PROCEDURE proc_2; Invoking trigger trig_2 invoking trigger trig_1 invoking unsafe use of mysql.general_log. @@ -2114,7 +1694,7 @@ CREATE TRIGGER trig_2 BEFORE INSERT ON trigger_table_2 FOR EACH ROW BEGIN INSERT * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO trigger_table_2 VALUES (1); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general_log, slow_log or performance_schema table(s). This is unsafe because system tables may differ on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general log, slow query log, or performance_schema table(s). This is unsafe because system tables may differ on slaves. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP TRIGGER trig_2; @@ -2124,7 +1704,7 @@ PREPARE prep_2 FROM "INSERT INTO trigger_table_1 VALUES (1)"; * binlog_format = STATEMENT: expect 1 warnings. EXECUTE prep_2; Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general_log, slow_log or performance_schema table(s). This is unsafe because system tables may differ on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general log, slow query log, or performance_schema table(s). This is unsafe because system tables may differ on slaves. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP PREPARE prep_2; @@ -2132,12 +1712,10 @@ DROP TRIGGER trig_1; Invoking view view_retval_1 returning value from unsafe use of mysql.general_log. CREATE VIEW view_retval_1 AS SELECT COUNT(*) FROM mysql.general_log; -Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general_log, slow_log or performance_schema table(s). This is unsafe because system tables may differ on slave. * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO t1 SELECT * FROM view_retval_1; Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general_log, slow_log or performance_schema table(s). This is unsafe because system tables may differ on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general log, slow query log, or performance_schema table(s). This is unsafe because system tables may differ on slaves. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. * Invoke statement so that return value is dicarded: expect no warning. @@ -2148,29 +1726,19 @@ CREATE FUNCTION func_sidef_2() RETURNS VARCHAR(100) BEGIN INSERT INTO ta2 VALUES * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO t2 SELECT func_sidef_2(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general_log, slow_log or performance_schema table(s). This is unsafe because system tables may differ on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general log, slow query log, or performance_schema table(s). This is unsafe because system tables may differ on slaves. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP FUNCTION func_sidef_2; Invoking procedure proc_2 invoking view view_retval_1 returning value from unsafe use of mysql.general_log. -CREATE PROCEDURE proc_2() BEGIN INSERT INTO ta2 VALUES (47); INSERT INTO t1 SELECT * FROM view_retval_1; END; +CREATE PROCEDURE proc_2() BEGIN INSERT INTO t1 SELECT * FROM view_retval_1; INSERT INTO ta2 VALUES (47); END; * binlog_format = STATEMENT: expect 1 warnings. CALL proc_2(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general_log, slow_log or performance_schema table(s). This is unsafe because system tables may differ on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general log, slow query log, or performance_schema table(s). This is unsafe because system tables may differ on slaves. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. -******** Failure! Event number 3 was a 'Query', not a 'Table_map'. ******** -SHOW BINLOG EVENTS FROM ; -Log_name Pos Event_type Server_id End_log_pos Info -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Query # # use `test`; INSERT INTO ta2 VALUES (47) -master-bin.000001 # Query # # COMMIT -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Table_map # # table_id: # (test.t1) -master-bin.000001 # Write_rows # # table_id: # flags: STMT_END_F -master-bin.000001 # Query # # COMMIT DROP PROCEDURE proc_2; Invoking trigger trig_2 invoking view view_retval_1 returning value from unsafe use of mysql.general_log. @@ -2178,19 +1746,17 @@ CREATE TRIGGER trig_2 BEFORE INSERT ON trigger_table_2 FOR EACH ROW BEGIN INSERT * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO trigger_table_2 VALUES (1); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general_log, slow_log or performance_schema table(s). This is unsafe because system tables may differ on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general log, slow query log, or performance_schema table(s). This is unsafe because system tables may differ on slaves. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP TRIGGER trig_2; Invoking view view_retval_2 returning value from view view_retval_1 returning value from unsafe use of mysql.general_log. CREATE VIEW view_retval_2 AS SELECT * FROM view_retval_1; -Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general_log, slow_log or performance_schema table(s). This is unsafe because system tables may differ on slave. * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO t2 SELECT * FROM view_retval_2; Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general_log, slow_log or performance_schema table(s). This is unsafe because system tables may differ on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general log, slow query log, or performance_schema table(s). This is unsafe because system tables may differ on slaves. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. * Invoke statement so that return value is dicarded: expect no warning. @@ -2202,7 +1768,7 @@ PREPARE prep_2 FROM "INSERT INTO t1 SELECT * FROM view_retval_1"; * binlog_format = STATEMENT: expect 1 warnings. EXECUTE prep_2; Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general_log, slow_log or performance_schema table(s). This is unsafe because system tables may differ on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general log, slow query log, or performance_schema table(s). This is unsafe because system tables may differ on slaves. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP PREPARE prep_2; @@ -2213,7 +1779,7 @@ PREPARE prep_1 FROM "INSERT INTO t0 SELECT COUNT(*) FROM mysql.general_log"; * binlog_format = STATEMENT: expect 1 warnings. EXECUTE prep_1; Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general_log, slow_log or performance_schema table(s). This is unsafe because system tables may differ on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general log, slow query log, or performance_schema table(s). This is unsafe because system tables may differ on slaves. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP PREPARE prep_1; @@ -2222,7 +1788,7 @@ Invoking unsafe use of mysql.general_log. * binlog_format = STATEMENT: expect 1 warnings. INSERT INTO t0 SELECT COUNT(*) FROM mysql.general_log; Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general_log, slow_log or performance_schema table(s). This is unsafe because system tables may differ on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general log, slow query log, or performance_schema table(s). This is unsafe because system tables may differ on slaves. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. * Invoke statement so that return value is dicarded: expect no warning. @@ -2235,13 +1801,13 @@ CREATE FUNCTION func_sidef_1() RETURNS VARCHAR(100) BEGIN INSERT INTO ta1 VALUES * binlog_format = STATEMENT: expect 7 warnings. INSERT INTO t1 SELECT func_sidef_1(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses INSERT DELAYED. This is unsafe because the time when rows are inserted cannot be predicted. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general_log, slow_log or performance_schema table(s). This is unsafe because system tables may differ on slave. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it invokes a trigger or a stored function that inserts into AUTO_INCREMENT column. The inserted values cannot be correctly logged. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a UDF. It cannot be determined if the UDF will return the same value on slave. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system variable that may have a different value on slave. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses INSERT DELAYED. This is unsafe because the times when rows are inserted cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general log, slow query log, or performance_schema table(s). This is unsafe because system tables may differ on slaves. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it invokes a trigger or a stored function that inserts into an AUTO_INCREMENT column. Inserted values cannot be logged correctly. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a UDF which may not return the same value on the slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a system variable that may have a different value on the slave. +Note 1592 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. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. @@ -2250,47 +1816,31 @@ CREATE FUNCTION func_sidef_2() RETURNS VARCHAR(100) BEGIN INSERT INTO ta2 VALUES * binlog_format = STATEMENT: expect 7 warnings. INSERT INTO t2 SELECT func_sidef_2(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses INSERT DELAYED. This is unsafe because the time when rows are inserted cannot be predicted. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general_log, slow_log or performance_schema table(s). This is unsafe because system tables may differ on slave. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it invokes a trigger or a stored function that inserts into AUTO_INCREMENT column. The inserted values cannot be correctly logged. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a UDF. It cannot be determined if the UDF will return the same value on slave. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system variable that may have a different value on slave. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses INSERT DELAYED. This is unsafe because the times when rows are inserted cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general log, slow query log, or performance_schema table(s). This is unsafe because system tables may differ on slaves. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it invokes a trigger or a stored function that inserts into an AUTO_INCREMENT column. Inserted values cannot be logged correctly. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a UDF which may not return the same value on the slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a system variable that may have a different value on the slave. +Note 1592 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. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP FUNCTION func_sidef_2; Invoking procedure proc_2 invoking function func_sidef_1 invoking statement that is unsafe in many ways. -CREATE PROCEDURE proc_2() BEGIN INSERT INTO ta2 VALUES (47); INSERT INTO t1 SELECT func_sidef_1(); END; +CREATE PROCEDURE proc_2() BEGIN INSERT INTO t1 SELECT func_sidef_1(); INSERT INTO ta2 VALUES (47); END; * binlog_format = STATEMENT: expect 7 warnings. CALL proc_2(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses INSERT DELAYED. This is unsafe because the time when rows are inserted cannot be predicted. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general_log, slow_log or performance_schema table(s). This is unsafe because system tables may differ on slave. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it invokes a trigger or a stored function that inserts into AUTO_INCREMENT column. The inserted values cannot be correctly logged. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a UDF. It cannot be determined if the UDF will return the same value on slave. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system variable that may have a different value on slave. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses INSERT DELAYED. This is unsafe because the times when rows are inserted cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general log, slow query log, or performance_schema table(s). This is unsafe because system tables may differ on slaves. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it invokes a trigger or a stored function that inserts into an AUTO_INCREMENT column. Inserted values cannot be logged correctly. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a UDF which may not return the same value on the slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a system variable that may have a different value on the slave. +Note 1592 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. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. -******** Failure! Event number 3 was a 'Query', not a 'Table_map'. ******** -SHOW BINLOG EVENTS FROM ; -Log_name Pos Event_type Server_id End_log_pos Info -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Query # # use `test`; INSERT INTO ta2 VALUES (47) -master-bin.000001 # Query # # COMMIT -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Table_map # # table_id: # (test.t1) -master-bin.000001 # Table_map # # table_id: # (test.ta1) -master-bin.000001 # Table_map # # table_id: # (test.double_autoinc_table) -master-bin.000001 # Table_map # # table_id: # (test.autoinc_table) -master-bin.000001 # Write_rows # # table_id: # -master-bin.000001 # Write_rows # # table_id: # -master-bin.000001 # Write_rows # # table_id: # -master-bin.000001 # Write_rows # # table_id: # flags: STMT_END_F -master-bin.000001 # Query # # COMMIT DROP PROCEDURE proc_2; Invoking trigger trig_2 invoking function func_sidef_1 invoking statement that is unsafe in many ways. @@ -2298,13 +1848,13 @@ CREATE TRIGGER trig_2 BEFORE INSERT ON trigger_table_2 FOR EACH ROW BEGIN INSERT * binlog_format = STATEMENT: expect 7 warnings. INSERT INTO trigger_table_2 VALUES (1); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses INSERT DELAYED. This is unsafe because the time when rows are inserted cannot be predicted. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general_log, slow_log or performance_schema table(s). This is unsafe because system tables may differ on slave. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it invokes a trigger or a stored function that inserts into AUTO_INCREMENT column. The inserted values cannot be correctly logged. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a UDF. It cannot be determined if the UDF will return the same value on slave. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system variable that may have a different value on slave. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses INSERT DELAYED. This is unsafe because the times when rows are inserted cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general log, slow query log, or performance_schema table(s). This is unsafe because system tables may differ on slaves. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it invokes a trigger or a stored function that inserts into an AUTO_INCREMENT column. Inserted values cannot be logged correctly. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a UDF which may not return the same value on the slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a system variable that may have a different value on the slave. +Note 1592 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. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP TRIGGER trig_2; @@ -2312,23 +1862,23 @@ DROP TRIGGER trig_2; Invoking view view_sidef_2 invoking function func_sidef_1 invoking statement that is unsafe in many ways. CREATE VIEW view_sidef_2 AS SELECT func_sidef_1(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses INSERT DELAYED. This is unsafe because the time when rows are inserted cannot be predicted. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general_log, slow_log or performance_schema table(s). This is unsafe because system tables may differ on slave. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it invokes a trigger or a stored function that inserts into AUTO_INCREMENT column. The inserted values cannot be correctly logged. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a UDF. It cannot be determined if the UDF will return the same value on slave. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system variable that may have a different value on slave. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses INSERT DELAYED. This is unsafe because the times when rows are inserted cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general log, slow query log, or performance_schema table(s). This is unsafe because system tables may differ on slaves. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it invokes a trigger or a stored function that inserts into an AUTO_INCREMENT column. Inserted values cannot be logged correctly. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a UDF which may not return the same value on the slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a system variable that may have a different value on the slave. +Note 1592 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. * binlog_format = STATEMENT: expect 7 warnings. INSERT INTO t2 SELECT * FROM view_sidef_2; Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses INSERT DELAYED. This is unsafe because the time when rows are inserted cannot be predicted. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general_log, slow_log or performance_schema table(s). This is unsafe because system tables may differ on slave. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it invokes a trigger or a stored function that inserts into AUTO_INCREMENT column. The inserted values cannot be correctly logged. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a UDF. It cannot be determined if the UDF will return the same value on slave. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system variable that may have a different value on slave. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses INSERT DELAYED. This is unsafe because the times when rows are inserted cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general log, slow query log, or performance_schema table(s). This is unsafe because system tables may differ on slaves. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it invokes a trigger or a stored function that inserts into an AUTO_INCREMENT column. Inserted values cannot be logged correctly. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a UDF which may not return the same value on the slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a system variable that may have a different value on the slave. +Note 1592 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. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP VIEW view_sidef_2; @@ -2338,30 +1888,30 @@ PREPARE prep_2 FROM "INSERT INTO t1 SELECT func_sidef_1()"; * binlog_format = STATEMENT: expect 7 warnings. EXECUTE prep_2; Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses INSERT DELAYED. This is unsafe because the time when rows are inserted cannot be predicted. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general_log, slow_log or performance_schema table(s). This is unsafe because system tables may differ on slave. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it invokes a trigger or a stored function that inserts into AUTO_INCREMENT column. The inserted values cannot be correctly logged. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a UDF. It cannot be determined if the UDF will return the same value on slave. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system variable that may have a different value on slave. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses INSERT DELAYED. This is unsafe because the times when rows are inserted cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general log, slow query log, or performance_schema table(s). This is unsafe because system tables may differ on slaves. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it invokes a trigger or a stored function that inserts into an AUTO_INCREMENT column. Inserted values cannot be logged correctly. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a UDF which may not return the same value on the slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a system variable that may have a different value on the slave. +Note 1592 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. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP PREPARE prep_2; DROP FUNCTION func_sidef_1; Invoking procedure proc_1 invoking statement that is unsafe in many ways. -CREATE PROCEDURE proc_1() BEGIN INSERT INTO ta1 VALUES (47); INSERT DELAYED INTO double_autoinc_table SELECT CONCAT(UUID(), @@hostname, myfunc_int(), NULL) FROM mysql.general_log LIMIT 1; END; +CREATE PROCEDURE proc_1() BEGIN INSERT DELAYED INTO double_autoinc_table SELECT CONCAT(UUID(), @@hostname, myfunc_int(), NULL) FROM mysql.general_log LIMIT 1; INSERT INTO ta1 VALUES (47); END; * binlog_format = STATEMENT: expect 7 warnings. CALL proc_1(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses INSERT DELAYED. This is unsafe because the time when rows are inserted cannot be predicted. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a UDF. It cannot be determined if the UDF will return the same value on slave. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system variable that may have a different value on slave. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general_log, slow_log or performance_schema table(s). This is unsafe because system tables may differ on slave. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it invokes a trigger or a stored function that inserts into AUTO_INCREMENT column. The inserted values cannot be correctly logged. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses INSERT DELAYED. This is unsafe because the times when rows are inserted cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general log, slow query log, or performance_schema table(s). This is unsafe because system tables may differ on slaves. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it invokes a trigger or a stored function that inserts into an AUTO_INCREMENT column. Inserted values cannot be logged correctly. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a UDF which may not return the same value on the slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a system variable that may have a different value on the slave. +Note 1592 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. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. @@ -2370,47 +1920,31 @@ CREATE FUNCTION func_sidef_2() RETURNS VARCHAR(100) BEGIN INSERT INTO ta2 VALUES * binlog_format = STATEMENT: expect 7 warnings. INSERT INTO t2 SELECT func_sidef_2(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses INSERT DELAYED. This is unsafe because the time when rows are inserted cannot be predicted. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general_log, slow_log or performance_schema table(s). This is unsafe because system tables may differ on slave. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it invokes a trigger or a stored function that inserts into AUTO_INCREMENT column. The inserted values cannot be correctly logged. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a UDF. It cannot be determined if the UDF will return the same value on slave. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system variable that may have a different value on slave. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses INSERT DELAYED. This is unsafe because the times when rows are inserted cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general log, slow query log, or performance_schema table(s). This is unsafe because system tables may differ on slaves. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it invokes a trigger or a stored function that inserts into an AUTO_INCREMENT column. Inserted values cannot be logged correctly. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a UDF which may not return the same value on the slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a system variable that may have a different value on the slave. +Note 1592 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. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP FUNCTION func_sidef_2; Invoking procedure proc_2 invoking procedure proc_1 invoking statement that is unsafe in many ways. -CREATE PROCEDURE proc_2() BEGIN INSERT INTO ta2 VALUES (47); CALL proc_1(); END; +CREATE PROCEDURE proc_2() BEGIN CALL proc_1(); INSERT INTO ta2 VALUES (47); END; * binlog_format = STATEMENT: expect 7 warnings. CALL proc_2(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses INSERT DELAYED. This is unsafe because the time when rows are inserted cannot be predicted. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a UDF. It cannot be determined if the UDF will return the same value on slave. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system variable that may have a different value on slave. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general_log, slow_log or performance_schema table(s). This is unsafe because system tables may differ on slave. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it invokes a trigger or a stored function that inserts into AUTO_INCREMENT column. The inserted values cannot be correctly logged. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses INSERT DELAYED. This is unsafe because the times when rows are inserted cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general log, slow query log, or performance_schema table(s). This is unsafe because system tables may differ on slaves. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it invokes a trigger or a stored function that inserts into an AUTO_INCREMENT column. Inserted values cannot be logged correctly. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a UDF which may not return the same value on the slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a system variable that may have a different value on the slave. +Note 1592 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. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. -******** Failure! Event number 3 was a 'Query', not a 'Table_map'. ******** -SHOW BINLOG EVENTS FROM ; -Log_name Pos Event_type Server_id End_log_pos Info -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Query # # use `test`; INSERT INTO ta2 VALUES (47) -master-bin.000001 # Query # # COMMIT -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Table_map # # table_id: # (test.ta1) -master-bin.000001 # Write_rows # # table_id: # flags: STMT_END_F -master-bin.000001 # Query # # COMMIT -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Table_map # # table_id: # (test.double_autoinc_table) -master-bin.000001 # Table_map # # table_id: # (test.autoinc_table) -master-bin.000001 # Write_rows # # table_id: # -master-bin.000001 # Write_rows # # table_id: # flags: STMT_END_F -master-bin.000001 # Query # # COMMIT DROP PROCEDURE proc_2; Invoking trigger trig_2 invoking procedure proc_1 invoking statement that is unsafe in many ways. @@ -2418,13 +1952,13 @@ CREATE TRIGGER trig_2 BEFORE INSERT ON trigger_table_2 FOR EACH ROW BEGIN INSERT * binlog_format = STATEMENT: expect 7 warnings. INSERT INTO trigger_table_2 VALUES (1); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses INSERT DELAYED. This is unsafe because the time when rows are inserted cannot be predicted. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general_log, slow_log or performance_schema table(s). This is unsafe because system tables may differ on slave. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it invokes a trigger or a stored function that inserts into AUTO_INCREMENT column. The inserted values cannot be correctly logged. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a UDF. It cannot be determined if the UDF will return the same value on slave. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system variable that may have a different value on slave. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses INSERT DELAYED. This is unsafe because the times when rows are inserted cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general log, slow query log, or performance_schema table(s). This is unsafe because system tables may differ on slaves. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it invokes a trigger or a stored function that inserts into an AUTO_INCREMENT column. Inserted values cannot be logged correctly. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a UDF which may not return the same value on the slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a system variable that may have a different value on the slave. +Note 1592 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. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP TRIGGER trig_2; @@ -2434,13 +1968,13 @@ PREPARE prep_2 FROM "CALL proc_1()"; * binlog_format = STATEMENT: expect 7 warnings. EXECUTE prep_2; Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses INSERT DELAYED. This is unsafe because the time when rows are inserted cannot be predicted. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a UDF. It cannot be determined if the UDF will return the same value on slave. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system variable that may have a different value on slave. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general_log, slow_log or performance_schema table(s). This is unsafe because system tables may differ on slave. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it invokes a trigger or a stored function that inserts into AUTO_INCREMENT column. The inserted values cannot be correctly logged. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses INSERT DELAYED. This is unsafe because the times when rows are inserted cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general log, slow query log, or performance_schema table(s). This is unsafe because system tables may differ on slaves. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it invokes a trigger or a stored function that inserts into an AUTO_INCREMENT column. Inserted values cannot be logged correctly. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a UDF which may not return the same value on the slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a system variable that may have a different value on the slave. +Note 1592 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. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP PREPARE prep_2; @@ -2451,13 +1985,13 @@ CREATE TRIGGER trig_1 BEFORE INSERT ON trigger_table_1 FOR EACH ROW BEGIN INSERT * binlog_format = STATEMENT: expect 7 warnings. INSERT INTO trigger_table_1 VALUES (1); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses INSERT DELAYED. This is unsafe because the time when rows are inserted cannot be predicted. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general_log, slow_log or performance_schema table(s). This is unsafe because system tables may differ on slave. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it invokes a trigger or a stored function that inserts into AUTO_INCREMENT column. The inserted values cannot be correctly logged. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a UDF. It cannot be determined if the UDF will return the same value on slave. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system variable that may have a different value on slave. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses INSERT DELAYED. This is unsafe because the times when rows are inserted cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general log, slow query log, or performance_schema table(s). This is unsafe because system tables may differ on slaves. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it invokes a trigger or a stored function that inserts into an AUTO_INCREMENT column. Inserted values cannot be logged correctly. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a UDF which may not return the same value on the slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a system variable that may have a different value on the slave. +Note 1592 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. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. @@ -2466,47 +2000,31 @@ CREATE FUNCTION func_sidef_2() RETURNS VARCHAR(100) BEGIN INSERT INTO ta2 VALUES * binlog_format = STATEMENT: expect 7 warnings. INSERT INTO t2 SELECT func_sidef_2(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses INSERT DELAYED. This is unsafe because the time when rows are inserted cannot be predicted. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general_log, slow_log or performance_schema table(s). This is unsafe because system tables may differ on slave. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it invokes a trigger or a stored function that inserts into AUTO_INCREMENT column. The inserted values cannot be correctly logged. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a UDF. It cannot be determined if the UDF will return the same value on slave. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system variable that may have a different value on slave. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses INSERT DELAYED. This is unsafe because the times when rows are inserted cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general log, slow query log, or performance_schema table(s). This is unsafe because system tables may differ on slaves. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it invokes a trigger or a stored function that inserts into an AUTO_INCREMENT column. Inserted values cannot be logged correctly. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a UDF which may not return the same value on the slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a system variable that may have a different value on the slave. +Note 1592 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. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP FUNCTION func_sidef_2; Invoking procedure proc_2 invoking trigger trig_1 invoking statement that is unsafe in many ways. -CREATE PROCEDURE proc_2() BEGIN INSERT INTO ta2 VALUES (47); INSERT INTO trigger_table_1 VALUES (1); END; +CREATE PROCEDURE proc_2() BEGIN INSERT INTO trigger_table_1 VALUES (1); INSERT INTO ta2 VALUES (47); END; * binlog_format = STATEMENT: expect 7 warnings. CALL proc_2(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses INSERT DELAYED. This is unsafe because the time when rows are inserted cannot be predicted. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general_log, slow_log or performance_schema table(s). This is unsafe because system tables may differ on slave. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it invokes a trigger or a stored function that inserts into AUTO_INCREMENT column. The inserted values cannot be correctly logged. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a UDF. It cannot be determined if the UDF will return the same value on slave. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system variable that may have a different value on slave. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses INSERT DELAYED. This is unsafe because the times when rows are inserted cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general log, slow query log, or performance_schema table(s). This is unsafe because system tables may differ on slaves. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it invokes a trigger or a stored function that inserts into an AUTO_INCREMENT column. Inserted values cannot be logged correctly. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a UDF which may not return the same value on the slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a system variable that may have a different value on the slave. +Note 1592 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. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. -******** Failure! Event number 3 was a 'Query', not a 'Table_map'. ******** -SHOW BINLOG EVENTS FROM ; -Log_name Pos Event_type Server_id End_log_pos Info -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Query # # use `test`; INSERT INTO ta2 VALUES (47) -master-bin.000001 # Query # # COMMIT -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Table_map # # table_id: # (test.trigger_table_1) -master-bin.000001 # Table_map # # table_id: # (test.ta1) -master-bin.000001 # Table_map # # table_id: # (test.double_autoinc_table) -master-bin.000001 # Table_map # # table_id: # (test.autoinc_table) -master-bin.000001 # Write_rows # # table_id: # -master-bin.000001 # Write_rows # # table_id: # -master-bin.000001 # Write_rows # # table_id: # -master-bin.000001 # Write_rows # # table_id: # flags: STMT_END_F -master-bin.000001 # Query # # COMMIT DROP PROCEDURE proc_2; Invoking trigger trig_2 invoking trigger trig_1 invoking statement that is unsafe in many ways. @@ -2514,13 +2032,13 @@ CREATE TRIGGER trig_2 BEFORE INSERT ON trigger_table_2 FOR EACH ROW BEGIN INSERT * binlog_format = STATEMENT: expect 7 warnings. INSERT INTO trigger_table_2 VALUES (1); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses INSERT DELAYED. This is unsafe because the time when rows are inserted cannot be predicted. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general_log, slow_log or performance_schema table(s). This is unsafe because system tables may differ on slave. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it invokes a trigger or a stored function that inserts into AUTO_INCREMENT column. The inserted values cannot be correctly logged. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a UDF. It cannot be determined if the UDF will return the same value on slave. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system variable that may have a different value on slave. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses INSERT DELAYED. This is unsafe because the times when rows are inserted cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general log, slow query log, or performance_schema table(s). This is unsafe because system tables may differ on slaves. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it invokes a trigger or a stored function that inserts into an AUTO_INCREMENT column. Inserted values cannot be logged correctly. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a UDF which may not return the same value on the slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a system variable that may have a different value on the slave. +Note 1592 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. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP TRIGGER trig_2; @@ -2530,13 +2048,13 @@ PREPARE prep_2 FROM "INSERT INTO trigger_table_1 VALUES (1)"; * binlog_format = STATEMENT: expect 7 warnings. EXECUTE prep_2; Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses INSERT DELAYED. This is unsafe because the time when rows are inserted cannot be predicted. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general_log, slow_log or performance_schema table(s). This is unsafe because system tables may differ on slave. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it invokes a trigger or a stored function that inserts into AUTO_INCREMENT column. The inserted values cannot be correctly logged. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a UDF. It cannot be determined if the UDF will return the same value on slave. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system variable that may have a different value on slave. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses INSERT DELAYED. This is unsafe because the times when rows are inserted cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general log, slow query log, or performance_schema table(s). This is unsafe because system tables may differ on slaves. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it invokes a trigger or a stored function that inserts into an AUTO_INCREMENT column. Inserted values cannot be logged correctly. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a UDF which may not return the same value on the slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a system variable that may have a different value on the slave. +Note 1592 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. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP PREPARE prep_2; @@ -2547,13 +2065,13 @@ PREPARE prep_1 FROM "INSERT DELAYED INTO double_autoinc_table SELECT CONCAT(UUID * binlog_format = STATEMENT: expect 7 warnings. EXECUTE prep_1; Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses INSERT DELAYED. This is unsafe because the time when rows are inserted cannot be predicted. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general_log, slow_log or performance_schema table(s). This is unsafe because system tables may differ on slave. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it invokes a trigger or a stored function that inserts into AUTO_INCREMENT column. The inserted values cannot be correctly logged. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a UDF. It cannot be determined if the UDF will return the same value on slave. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system variable that may have a different value on slave. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses INSERT DELAYED. This is unsafe because the times when rows are inserted cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general log, slow query log, or performance_schema table(s). This is unsafe because system tables may differ on slaves. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it invokes a trigger or a stored function that inserts into an AUTO_INCREMENT column. Inserted values cannot be logged correctly. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a UDF which may not return the same value on the slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a system variable that may have a different value on the slave. +Note 1592 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. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP PREPARE prep_1; @@ -2562,13 +2080,13 @@ Invoking statement that is unsafe in many ways. * binlog_format = STATEMENT: expect 7 warnings. INSERT DELAYED INTO double_autoinc_table SELECT CONCAT(UUID(), @@hostname, myfunc_int(), NULL) FROM mysql.general_log LIMIT 1; Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses INSERT DELAYED. This is unsafe because the time when rows are inserted cannot be predicted. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general_log, slow_log or performance_schema table(s). This is unsafe because system tables may differ on slave. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it invokes a trigger or a stored function that inserts into AUTO_INCREMENT column. The inserted values cannot be correctly logged. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a UDF. It cannot be determined if the UDF will return the same value on slave. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system variable that may have a different value on slave. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses INSERT DELAYED. This is unsafe because the times when rows are inserted cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses the general log, slow query log, or performance_schema table(s). This is unsafe because system tables may differ on slaves. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it invokes a trigger or a stored function that inserts into an AUTO_INCREMENT column. Inserted values cannot be logged correctly. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a UDF which may not return the same value on the slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a system variable that may have a different value on the slave. +Note 1592 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. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. @@ -2579,8 +2097,8 @@ CREATE FUNCTION func_sidef_1() RETURNS VARCHAR(100) BEGIN INSERT INTO ta1 VALUES * binlog_format = STATEMENT: expect 2 warnings. INSERT INTO t1 SELECT func_sidef_1(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system variable that may have a different value on slave. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a system variable that may have a different value on the slave. +Note 1592 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. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. @@ -2589,37 +2107,21 @@ CREATE FUNCTION func_sidef_2() RETURNS VARCHAR(100) BEGIN INSERT INTO ta2 VALUES * binlog_format = STATEMENT: expect 2 warnings. INSERT INTO t2 SELECT func_sidef_2(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system variable that may have a different value on slave. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a system variable that may have a different value on the slave. +Note 1592 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. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP FUNCTION func_sidef_2; Invoking procedure proc_2 invoking function func_sidef_1 invoking statement that is unsafe several times. -CREATE PROCEDURE proc_2() BEGIN INSERT INTO ta2 VALUES (47); INSERT INTO t1 SELECT func_sidef_1(); END; +CREATE PROCEDURE proc_2() BEGIN INSERT INTO t1 SELECT func_sidef_1(); INSERT INTO ta2 VALUES (47); END; * binlog_format = STATEMENT: expect 2 warnings. CALL proc_2(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system variable that may have a different value on slave. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a system variable that may have a different value on the slave. +Note 1592 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. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. -******** Failure! Event number 3 was a 'Query', not a 'Table_map'. ******** -SHOW BINLOG EVENTS FROM ; -Log_name Pos Event_type Server_id End_log_pos Info -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Query # # use `test`; INSERT INTO ta2 VALUES (47) -master-bin.000001 # Query # # COMMIT -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Table_map # # table_id: # (test.t1) -master-bin.000001 # Table_map # # table_id: # (test.ta0) -master-bin.000001 # Table_map # # table_id: # (test.ta1) -master-bin.000001 # Table_map # # table_id: # (test.t0) -master-bin.000001 # Write_rows # # table_id: # -master-bin.000001 # Write_rows # # table_id: # -master-bin.000001 # Write_rows # # table_id: # -master-bin.000001 # Write_rows # # table_id: # flags: STMT_END_F -master-bin.000001 # Query # # COMMIT DROP PROCEDURE proc_2; Invoking trigger trig_2 invoking function func_sidef_1 invoking statement that is unsafe several times. @@ -2627,8 +2129,8 @@ CREATE TRIGGER trig_2 BEFORE INSERT ON trigger_table_2 FOR EACH ROW BEGIN INSERT * binlog_format = STATEMENT: expect 2 warnings. INSERT INTO trigger_table_2 VALUES (1); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system variable that may have a different value on slave. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a system variable that may have a different value on the slave. +Note 1592 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. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP TRIGGER trig_2; @@ -2636,13 +2138,13 @@ DROP TRIGGER trig_2; Invoking view view_sidef_2 invoking function func_sidef_1 invoking statement that is unsafe several times. CREATE VIEW view_sidef_2 AS SELECT func_sidef_1(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system variable that may have a different value on slave. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a system variable that may have a different value on the slave. +Note 1592 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. * binlog_format = STATEMENT: expect 2 warnings. INSERT INTO t2 SELECT * FROM view_sidef_2; Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system variable that may have a different value on slave. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a system variable that may have a different value on the slave. +Note 1592 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. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP VIEW view_sidef_2; @@ -2652,70 +2154,43 @@ PREPARE prep_2 FROM "INSERT INTO t1 SELECT func_sidef_1()"; * binlog_format = STATEMENT: expect 2 warnings. EXECUTE prep_2; Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system variable that may have a different value on slave. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a system variable that may have a different value on the slave. +Note 1592 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. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP PREPARE prep_2; DROP FUNCTION func_sidef_1; Invoking procedure proc_1 invoking statement that is unsafe several times. -CREATE PROCEDURE proc_1() BEGIN INSERT INTO ta1 VALUES (47); INSERT INTO ta0 VALUES (multi_unsafe_func()); END; +CREATE PROCEDURE proc_1() BEGIN INSERT INTO ta0 VALUES (multi_unsafe_func()); INSERT INTO ta1 VALUES (47); END; * binlog_format = STATEMENT: expect 2 warnings. CALL proc_1(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system variable that may have a different value on slave. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a system variable that may have a different value on the slave. +Note 1592 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. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. -******** Failure! Event number 3 was a 'Query', not a 'Table_map'. ******** -SHOW BINLOG EVENTS FROM ; -Log_name Pos Event_type Server_id End_log_pos Info -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Query # # use `test`; INSERT INTO ta1 VALUES (47) -master-bin.000001 # Query # # COMMIT -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Table_map # # table_id: # (test.ta0) -master-bin.000001 # Table_map # # table_id: # (test.t0) -master-bin.000001 # Write_rows # # table_id: # -master-bin.000001 # Write_rows # # table_id: # flags: STMT_END_F -master-bin.000001 # Query # # COMMIT Invoking function func_sidef_2 invoking procedure proc_1 invoking statement that is unsafe several times. CREATE FUNCTION func_sidef_2() RETURNS VARCHAR(100) BEGIN INSERT INTO ta2 VALUES (47); CALL proc_1(); RETURN 0; END; * binlog_format = STATEMENT: expect 2 warnings. INSERT INTO t2 SELECT func_sidef_2(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system variable that may have a different value on slave. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a system variable that may have a different value on the slave. +Note 1592 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. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP FUNCTION func_sidef_2; Invoking procedure proc_2 invoking procedure proc_1 invoking statement that is unsafe several times. -CREATE PROCEDURE proc_2() BEGIN INSERT INTO ta2 VALUES (47); CALL proc_1(); END; +CREATE PROCEDURE proc_2() BEGIN CALL proc_1(); INSERT INTO ta2 VALUES (47); END; * binlog_format = STATEMENT: expect 2 warnings. CALL proc_2(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system variable that may have a different value on slave. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a system variable that may have a different value on the slave. +Note 1592 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. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. -******** Failure! Event number 3 was a 'Query', not a 'Table_map'. ******** -SHOW BINLOG EVENTS FROM ; -Log_name Pos Event_type Server_id End_log_pos Info -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Query # # use `test`; INSERT INTO ta2 VALUES (47) -master-bin.000001 # Query # # COMMIT -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Query # # use `test`; INSERT INTO ta1 VALUES (47) -master-bin.000001 # Query # # COMMIT -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Table_map # # table_id: # (test.ta0) -master-bin.000001 # Table_map # # table_id: # (test.t0) -master-bin.000001 # Write_rows # # table_id: # -master-bin.000001 # Write_rows # # table_id: # flags: STMT_END_F -master-bin.000001 # Query # # COMMIT DROP PROCEDURE proc_2; Invoking trigger trig_2 invoking procedure proc_1 invoking statement that is unsafe several times. @@ -2723,8 +2198,8 @@ CREATE TRIGGER trig_2 BEFORE INSERT ON trigger_table_2 FOR EACH ROW BEGIN INSERT * binlog_format = STATEMENT: expect 2 warnings. INSERT INTO trigger_table_2 VALUES (1); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system variable that may have a different value on slave. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a system variable that may have a different value on the slave. +Note 1592 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. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP TRIGGER trig_2; @@ -2734,22 +2209,10 @@ PREPARE prep_2 FROM "CALL proc_1()"; * binlog_format = STATEMENT: expect 2 warnings. EXECUTE prep_2; Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system variable that may have a different value on slave. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a system variable that may have a different value on the slave. +Note 1592 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. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. -******** Failure! Event number 3 was a 'Query', not a 'Table_map'. ******** -SHOW BINLOG EVENTS FROM ; -Log_name Pos Event_type Server_id End_log_pos Info -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Query # # use `test`; INSERT INTO ta1 VALUES (47) -master-bin.000001 # Query # # COMMIT -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Table_map # # table_id: # (test.ta0) -master-bin.000001 # Table_map # # table_id: # (test.t0) -master-bin.000001 # Write_rows # # table_id: # -master-bin.000001 # Write_rows # # table_id: # flags: STMT_END_F -master-bin.000001 # Query # # COMMIT DROP PREPARE prep_2; DROP PROCEDURE proc_1; @@ -2758,8 +2221,8 @@ CREATE TRIGGER trig_1 BEFORE INSERT ON trigger_table_1 FOR EACH ROW BEGIN INSERT * binlog_format = STATEMENT: expect 2 warnings. INSERT INTO trigger_table_1 VALUES (1); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system variable that may have a different value on slave. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a system variable that may have a different value on the slave. +Note 1592 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. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. @@ -2768,37 +2231,21 @@ CREATE FUNCTION func_sidef_2() RETURNS VARCHAR(100) BEGIN INSERT INTO ta2 VALUES * binlog_format = STATEMENT: expect 2 warnings. INSERT INTO t2 SELECT func_sidef_2(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system variable that may have a different value on slave. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a system variable that may have a different value on the slave. +Note 1592 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. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP FUNCTION func_sidef_2; Invoking procedure proc_2 invoking trigger trig_1 invoking statement that is unsafe several times. -CREATE PROCEDURE proc_2() BEGIN INSERT INTO ta2 VALUES (47); INSERT INTO trigger_table_1 VALUES (1); END; +CREATE PROCEDURE proc_2() BEGIN INSERT INTO trigger_table_1 VALUES (1); INSERT INTO ta2 VALUES (47); END; * binlog_format = STATEMENT: expect 2 warnings. CALL proc_2(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system variable that may have a different value on slave. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a system variable that may have a different value on the slave. +Note 1592 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. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. -******** Failure! Event number 3 was a 'Query', not a 'Table_map'. ******** -SHOW BINLOG EVENTS FROM ; -Log_name Pos Event_type Server_id End_log_pos Info -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Query # # use `test`; INSERT INTO ta2 VALUES (47) -master-bin.000001 # Query # # COMMIT -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Table_map # # table_id: # (test.trigger_table_1) -master-bin.000001 # Table_map # # table_id: # (test.ta0) -master-bin.000001 # Table_map # # table_id: # (test.ta1) -master-bin.000001 # Table_map # # table_id: # (test.t0) -master-bin.000001 # Write_rows # # table_id: # -master-bin.000001 # Write_rows # # table_id: # -master-bin.000001 # Write_rows # # table_id: # -master-bin.000001 # Write_rows # # table_id: # flags: STMT_END_F -master-bin.000001 # Query # # COMMIT DROP PROCEDURE proc_2; Invoking trigger trig_2 invoking trigger trig_1 invoking statement that is unsafe several times. @@ -2806,8 +2253,8 @@ CREATE TRIGGER trig_2 BEFORE INSERT ON trigger_table_2 FOR EACH ROW BEGIN INSERT * binlog_format = STATEMENT: expect 2 warnings. INSERT INTO trigger_table_2 VALUES (1); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system variable that may have a different value on slave. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a system variable that may have a different value on the slave. +Note 1592 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. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP TRIGGER trig_2; @@ -2817,8 +2264,8 @@ PREPARE prep_2 FROM "INSERT INTO trigger_table_1 VALUES (1)"; * binlog_format = STATEMENT: expect 2 warnings. EXECUTE prep_2; Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system variable that may have a different value on slave. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a system variable that may have a different value on the slave. +Note 1592 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. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP PREPARE prep_2; @@ -2827,13 +2274,13 @@ DROP TRIGGER trig_1; Invoking view view_sidef_1 invoking statement that is unsafe several times. CREATE VIEW view_sidef_1 AS SELECT multi_unsafe_func(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system variable that may have a different value on slave. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a system variable that may have a different value on the slave. +Note 1592 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. * binlog_format = STATEMENT: expect 2 warnings. INSERT INTO t1 SELECT * FROM view_sidef_1; Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system variable that may have a different value on slave. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a system variable that may have a different value on the slave. +Note 1592 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. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. @@ -2842,33 +2289,21 @@ CREATE FUNCTION func_sidef_2() RETURNS VARCHAR(100) BEGIN INSERT INTO ta2 VALUES * binlog_format = STATEMENT: expect 2 warnings. INSERT INTO t2 SELECT func_sidef_2(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system variable that may have a different value on slave. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a system variable that may have a different value on the slave. +Note 1592 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. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP FUNCTION func_sidef_2; Invoking procedure proc_2 invoking view view_sidef_1 invoking statement that is unsafe several times. -CREATE PROCEDURE proc_2() BEGIN INSERT INTO ta2 VALUES (47); INSERT INTO t1 SELECT * FROM view_sidef_1; END; +CREATE PROCEDURE proc_2() BEGIN INSERT INTO t1 SELECT * FROM view_sidef_1; INSERT INTO ta2 VALUES (47); END; * binlog_format = STATEMENT: expect 2 warnings. CALL proc_2(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system variable that may have a different value on slave. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a system variable that may have a different value on the slave. +Note 1592 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. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. -******** Failure! Event number 3 was a 'Query', not a 'Table_map'. ******** -SHOW BINLOG EVENTS FROM ; -Log_name Pos Event_type Server_id End_log_pos Info -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Query # # use `test`; INSERT INTO ta2 VALUES (47) -master-bin.000001 # Query # # COMMIT -master-bin.000001 # Query # # BEGIN -master-bin.000001 # Table_map # # table_id: # (test.t1) -master-bin.000001 # Table_map # # table_id: # (test.t0) -master-bin.000001 # Write_rows # # table_id: # -master-bin.000001 # Write_rows # # table_id: # flags: STMT_END_F -master-bin.000001 # Query # # COMMIT DROP PROCEDURE proc_2; Invoking trigger trig_2 invoking view view_sidef_1 invoking statement that is unsafe several times. @@ -2876,8 +2311,8 @@ CREATE TRIGGER trig_2 BEFORE INSERT ON trigger_table_2 FOR EACH ROW BEGIN INSERT * binlog_format = STATEMENT: expect 2 warnings. INSERT INTO trigger_table_2 VALUES (1); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system variable that may have a different value on slave. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a system variable that may have a different value on the slave. +Note 1592 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. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP TRIGGER trig_2; @@ -2885,13 +2320,13 @@ DROP TRIGGER trig_2; Invoking view view_sidef_2 invoking view view_sidef_1 invoking statement that is unsafe several times. CREATE VIEW view_sidef_2 AS SELECT * FROM view_sidef_1; Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system variable that may have a different value on slave. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a system variable that may have a different value on the slave. +Note 1592 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. * binlog_format = STATEMENT: expect 2 warnings. INSERT INTO t2 SELECT * FROM view_sidef_2; Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system variable that may have a different value on slave. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a system variable that may have a different value on the slave. +Note 1592 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. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP VIEW view_sidef_2; @@ -2901,8 +2336,8 @@ PREPARE prep_2 FROM "INSERT INTO t1 SELECT * FROM view_sidef_1"; * binlog_format = STATEMENT: expect 2 warnings. EXECUTE prep_2; Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system variable that may have a different value on slave. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a system variable that may have a different value on the slave. +Note 1592 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. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP PREPARE prep_2; @@ -2913,8 +2348,8 @@ PREPARE prep_1 FROM "INSERT INTO ta0 VALUES (multi_unsafe_func())"; * binlog_format = STATEMENT: expect 2 warnings. EXECUTE prep_1; Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system variable that may have a different value on slave. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a system variable that may have a different value on the slave. +Note 1592 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. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP PREPARE prep_1; @@ -2923,8 +2358,8 @@ Invoking statement that is unsafe several times. * binlog_format = STATEMENT: expect 2 warnings. INSERT INTO ta0 VALUES (multi_unsafe_func()); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system variable that may have a different value on slave. -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a system variable that may have a different value on the slave. +Note 1592 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. * SQL_LOG_BIN = 0: expect nothing logged and no warning. * binlog_format = MIXED: expect row events in binlog and no warning. DROP TRIGGER double_autoinc_trig; @@ -2962,24 +2397,24 @@ INSERT INTO autoinc_table VALUES (NULL); The following variables *should* give a warning, despite they are replicated. INSERT INTO t1 VALUES (@@session.sql_mode); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system variable that may have a different value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a system variable that may have a different value on the slave. INSERT INTO t1 VALUES (@@session.insert_id); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system variable that may have a different value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a system variable that may have a different value on the slave. DROP TABLE t1, autoinc_table; CREATE TABLE t1(a INT, b INT, KEY(a), PRIMARY KEY(b)); INSERT INTO t1 SELECT * FROM t1 LIMIT 1; Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. REPLACE INTO t1 SELECT * FROM t1 LIMIT 1; Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. UPDATE t1 SET a=1 LIMIT 1; Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. DELETE FROM t1 LIMIT 1; Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. CREATE PROCEDURE p1() BEGIN INSERT INTO t1 SELECT * FROM t1 LIMIT 1; @@ -2989,7 +2424,7 @@ DELETE FROM t1 LIMIT 1; END| CALL p1(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. DROP PROCEDURE p1; DROP TABLE t1; DROP TABLE IF EXISTS t1; @@ -2997,7 +2432,7 @@ CREATE TABLE t1 (a VARCHAR(100), b VARCHAR(100)); INSERT INTO t1 VALUES ('a','b'); UPDATE t1 SET b = '%s%s%s%s%s%s%s%s%s%s%s%s%s%s' WHERE a = 'a' LIMIT 1; Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. DROP TABLE t1; DROP TABLE IF EXISTS t1, t2; CREATE TABLE t1(i INT PRIMARY KEY); @@ -3006,7 +2441,7 @@ CREATE TABLE t3(i INT, ch CHAR(50)); "Should issue message Statement may not be safe to log in statement format." INSERT INTO t1 SELECT * FROM t2 LIMIT 1; Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. CREATE FUNCTION func6() RETURNS INT BEGIN @@ -3018,7 +2453,7 @@ END| "Should issue message Statement may not be safe to log in statement format only once" INSERT INTO t3 VALUES(func6(), UUID()); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 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. "Check whether SET @@SQL_LOG_BIN = 0/1 doesn't work in substatements" CREATE FUNCTION fun_check_log_bin() RETURNS INT BEGIN @@ -3028,10 +2463,7 @@ RETURN 100; END| "One unsafe warning should be issued in the following statement" SELECT fun_check_log_bin(); -fun_check_log_bin() -100 -Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system variable that may have a different value on slave. +ERROR HY000: Cannot change the sql_log_bin inside a stored function or trigger "SQL_LOG_BIN should be ON still" SHOW VARIABLES LIKE "SQL_LOG_BIN"; Variable_name Value @@ -3087,16 +2519,16 @@ CREATE TABLE t1(i INT PRIMARY KEY); CREATE TABLE t2(i INT PRIMARY KEY); INSERT INTO t1 SELECT * FROM t2 LIMIT 1; Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. INSERT INTO t1 VALUES(@@global.sync_binlog); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system variable that may have a different value on slave. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a system variable that may have a different value on the slave. UPDATE t1 SET i = 999 LIMIT 1; Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. DELETE FROM t1 LIMIT 1; Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a LIMIT clause. This is unsafe because the set of rows included cannot be predicted. DROP TABLE t1, t2; SET @@SESSION.SQL_MODE = @save_sql_mode; SET @old_binlog_format = @@session.binlog_format; @@ -3146,18 +2578,18 @@ END| # so it should produce unsafe warning. INSERT INTO t2 SET a = func_modify_t1(); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it invokes a trigger or a stored function that inserts into AUTO_INCREMENT column. The inserted values cannot be correctly logged. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it invokes a trigger or a stored function that inserts into an AUTO_INCREMENT column. Inserted values cannot be logged correctly. SET SESSION binlog_format = MIXED; # Check if the statement is logged in row format. INSERT INTO t2 SET a = func_modify_t1(); -SHOW BINLOG EVENTS FROM 1493; +show binlog events from ; Log_name Pos Event_type Server_id End_log_pos Info -master-bin.000001 1493 Query 1 1561 BEGIN -master-bin.000001 1561 Table_map 1 1603 table_id: 205 (test.t2) -master-bin.000001 1603 Table_map 1 1645 table_id: 206 (test.t1) -master-bin.000001 1645 Write_rows 1 1683 table_id: 206 -master-bin.000001 1683 Write_rows 1 1721 table_id: 205 flags: STMT_END_F -master-bin.000001 1721 Query 1 1790 COMMIT +master-bin.000001 # Query # # BEGIN +master-bin.000001 # Table_map # # table_id: # (test.t2) +master-bin.000001 # Table_map # # table_id: # (test.t1) +master-bin.000001 # Write_rows # # table_id: # +master-bin.000001 # Write_rows # # table_id: # flags: STMT_END_F +master-bin.000001 # Query # # COMMIT DROP TABLE t1,t2; DROP FUNCTION func_modify_t1; SET SESSION binlog_format = STATEMENT; @@ -3173,77 +2605,80 @@ end | # so it should produce unsafe warning INSERT INTO t1 SET a = 1; Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it invokes a trigger or a stored function that inserts into AUTO_INCREMENT column. The inserted values cannot be correctly logged. +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it invokes a trigger or a stored function that inserts into an AUTO_INCREMENT column. Inserted values cannot be logged correctly. SET SESSION binlog_format = MIXED; # Check if the statement is logged in row format. INSERT INTO t1 SET a = 2; -SHOW BINLOG EVENTS FROM 2773; +show binlog events from ; Log_name Pos Event_type Server_id End_log_pos Info -master-bin.000001 2773 Query 1 2841 BEGIN -master-bin.000001 2841 Table_map 1 2882 table_id: 208 (test.t1) -master-bin.000001 2882 Table_map 1 2924 table_id: 209 (test.t3) -master-bin.000001 2924 Table_map 1 2966 table_id: 210 (test.t2) -master-bin.000001 2966 Write_rows 1 3004 table_id: 210 -master-bin.000001 3004 Write_rows 1 3042 table_id: 209 -master-bin.000001 3042 Write_rows 1 3076 table_id: 208 flags: STMT_END_F -master-bin.000001 3076 Query 1 3145 COMMIT +master-bin.000001 # Query # # BEGIN +master-bin.000001 # Table_map # # table_id: # (test.t1) +master-bin.000001 # Table_map # # table_id: # (test.t3) +master-bin.000001 # Table_map # # table_id: # (test.t2) +master-bin.000001 # Write_rows # # table_id: # flags: STMT_END_F +master-bin.000001 # Table_map # # table_id: # (test.t1) +master-bin.000001 # Table_map # # table_id: # (test.t3) +master-bin.000001 # Table_map # # table_id: # (test.t2) +master-bin.000001 # Write_rows # # table_id: # +master-bin.000001 # Write_rows # # table_id: # flags: STMT_END_F +master-bin.000001 # Query # # COMMIT DROP TABLE t1,t2,t3; SET SESSION binlog_format = STATEMENT; CREATE TABLE t1 (a VARCHAR(1000)); INSERT INTO t1 VALUES (CURRENT_USER()); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 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. INSERT INTO t1 VALUES (FOUND_ROWS()); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 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. INSERT INTO t1 VALUES (GET_LOCK('tmp', 1)); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 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. INSERT INTO t1 VALUES (IS_FREE_LOCK('tmp')); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 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. INSERT INTO t1 VALUES (IS_USED_LOCK('tmp')); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 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. INSERT INTO t1 VALUES (LOAD_FILE('../../std_data/words2.dat')); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 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. INSERT INTO t1 VALUES (MASTER_POS_WAIT('dummy arg', 4711, 1)); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 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. INSERT INTO t1 VALUES (RELEASE_LOCK('tmp')); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 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. INSERT INTO t1 VALUES (ROW_COUNT()); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 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. INSERT INTO t1 VALUES (SESSION_USER()); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 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. INSERT INTO t1 VALUES (SLEEP(1)); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 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. INSERT INTO t1 VALUES (SYSDATE()); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 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. INSERT INTO t1 VALUES (SYSTEM_USER()); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 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. INSERT INTO t1 VALUES (USER()); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 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. INSERT INTO t1 VALUES (UUID()); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 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. INSERT INTO t1 VALUES (UUID_SHORT()); Warnings: -Note 1592 Unsafe statement written to the binary log in statement format since BINLOG_FORMAT = STATEMENT. The statement is unsafe because it uses a system function that may return a different value on slave. +Note 1592 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. INSERT INTO t1 VALUES (VERSION()); Warnings: -Note 1592 Statement may not be safe to log in statement format. +Note 1592 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. INSERT INTO t1 VALUES (RAND()); Warnings: -Note 1592 Statement may not be safe to log in statement format. +Note 1592 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. DELETE FROM t1; SET TIMESTAMP=1000000; INSERT INTO t1 VALUES diff --git a/mysql-test/suite/binlog/t/binlog_stm_unsafe_warning.test b/mysql-test/suite/binlog/t/binlog_stm_unsafe_warning.test index 45fae25e0df..a2f6afc1004 100644 --- a/mysql-test/suite/binlog/t/binlog_stm_unsafe_warning.test +++ b/mysql-test/suite/binlog/t/binlog_stm_unsafe_warning.test @@ -72,6 +72,26 @@ UPDATE t1 SET b='4' WHERE a=1 LIMIT 1; UPDATE t1 SET b='5' WHERE a=2 ORDER BY a LIMIT 1; DROP TABLE t1; +CREATE TABLE t1 (a VARCHAR(1000)); +INSERT INTO t1 VALUES (CURRENT_USER()); #marked unsafe before BUG#47995 +INSERT INTO t1 VALUES (FOUND_ROWS()); #marked unsafe before BUG#47995 +INSERT INTO t1 VALUES (GET_LOCK('tmp', 1)); #marked unsafe in BUG#47995 +INSERT INTO t1 VALUES (IS_FREE_LOCK('tmp')); #marked unsafe in BUG#47995 +INSERT INTO t1 VALUES (IS_USED_LOCK('tmp')); #marked unsafe in BUG#47995 +INSERT INTO t1 VALUES (LOAD_FILE('../../std_data/words2.dat')); #marked unsafe in BUG#39701 +INSERT INTO t1 VALUES (MASTER_POS_WAIT('dummy arg', 4711, 1)); +INSERT INTO t1 VALUES (RELEASE_LOCK('tmp')); #marked unsafe in BUG#47995 +INSERT INTO t1 VALUES (ROW_COUNT()); #marked unsafe before BUG#47995 +INSERT INTO t1 VALUES (SESSION_USER()); #marked unsafe before BUG#47995 +INSERT INTO t1 VALUES (SLEEP(1)); #marked unsafe in BUG#47995 +INSERT INTO t1 VALUES (SYSDATE()); #marked unsafe in BUG#47995 +INSERT INTO t1 VALUES (SYSTEM_USER()); #marked unsafe before BUG#47995 +INSERT INTO t1 VALUES (USER()); #marked unsafe before BUG#47995 +INSERT INTO t1 VALUES (UUID()); #marked unsafe before BUG#47995 +INSERT INTO t1 VALUES (UUID_SHORT()); #marked unsafe before BUG#47995 +INSERT INTO t1 VALUES (VERSION()); #marked unsafe in BUG#47995 +INSERT INTO t1 VALUES (RAND()); #marked unsafe in BUG#49222 + # clean up DROP DATABASE b42851; diff --git a/mysql-test/suite/binlog/t/binlog_unsafe.test b/mysql-test/suite/binlog/t/binlog_unsafe.test index cb0cac17930..ed42a2cdb19 100644 --- a/mysql-test/suite/binlog/t/binlog_unsafe.test +++ b/mysql-test/suite/binlog/t/binlog_unsafe.test @@ -468,6 +468,7 @@ BEGIN END| DELIMITER ;| --echo "One unsafe warning should be issued in the following statement" +--error ER_STORED_FUNCTION_PREVENTS_SWITCH_SQL_LOG_BIN SELECT fun_check_log_bin(); --echo "SQL_LOG_BIN should be ON still" SHOW VARIABLES LIKE "SQL_LOG_BIN"; diff --git a/mysql-test/suite/binlog/t/disabled.def b/mysql-test/suite/binlog/t/disabled.def index 35ecf52decf..a9841f592f8 100644 --- a/mysql-test/suite/binlog/t/disabled.def +++ b/mysql-test/suite/binlog/t/disabled.def @@ -11,5 +11,4 @@ ############################################################################## binlog_truncate_innodb : BUG#42643 2009-02-06 mats Changes to InnoDB requires to complete fix for BUG#36763 -binlog_unsafe : BUG#50312 2010-01-13 lsoares Warnings for unsafe sub-statement not returned to client binlog_spurious_ddl_errors : BUG#54195 2010-06-03 alik binlog_spurious_ddl_errors.test fails, thus disabled diff --git a/mysql-test/suite/rpl/r/rpl_begin_commit_rollback.result b/mysql-test/suite/rpl/r/rpl_begin_commit_rollback.result index a65ee7d208e..1ed7e0116a2 100644 --- a/mysql-test/suite/rpl/r/rpl_begin_commit_rollback.result +++ b/mysql-test/suite/rpl/r/rpl_begin_commit_rollback.result @@ -72,6 +72,8 @@ before call db1.p1() INSERT INTO db1.t2 VALUES ('before call db1.p2()'); BEGIN; CALL db1.p2(); +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. ROLLBACK; INSERT INTO db1.t2 VALUES ('after call db1.p2()'); SELECT * FROM db1.t1; diff --git a/mysql-test/suite/rpl/r/rpl_non_direct_stm_mixing_engines.result b/mysql-test/suite/rpl/r/rpl_non_direct_stm_mixing_engines.result index 7c1ef59d9bd..d716886e5bf 100644 --- a/mysql-test/suite/rpl/r/rpl_non_direct_stm_mixing_engines.result +++ b/mysql-test/suite/rpl/r/rpl_non_direct_stm_mixing_engines.result @@ -3661,6 +3661,8 @@ Log_name Pos Event_type Server_id End_log_pos Info SELECT fc_i_nt_5_suc (135, 4); fc_i_nt_5_suc (135, 4) fc_i_nt_5_suc +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. Log_name Pos Event_type Server_id End_log_pos Info -e-e-e-e-e-e-e-e-e-e-e- >> N-func << -e-e-e-e-e-e-e-e-e-e-e- -b-b-b-b-b-b-b-b-b-b-b- >> C << -b-b-b-b-b-b-b-b-b-b-b- @@ -3689,6 +3691,8 @@ Log_name Pos Event_type Server_id End_log_pos Info -e-e-e-e-e-e-e-e-e-e-e- >> T << -e-e-e-e-e-e-e-e-e-e-e- -b-b-b-b-b-b-b-b-b-b-b- >> N-proc << -b-b-b-b-b-b-b-b-b-b-b- CALL pc_i_nt_5_suc (136, 4); +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. Log_name Pos Event_type Server_id End_log_pos Info -e-e-e-e-e-e-e-e-e-e-e- >> N-proc << -e-e-e-e-e-e-e-e-e-e-e- -b-b-b-b-b-b-b-b-b-b-b- >> C << -b-b-b-b-b-b-b-b-b-b-b- @@ -3781,6 +3785,8 @@ Log_name Pos Event_type Server_id End_log_pos Info SELECT fc_i_nt_5_suc (139, 4); fc_i_nt_5_suc (139, 4) fc_i_nt_5_suc +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. Log_name Pos Event_type Server_id End_log_pos Info -e-e-e-e-e-e-e-e-e-e-e- >> N-func << -e-e-e-e-e-e-e-e-e-e-e- -b-b-b-b-b-b-b-b-b-b-b- >> C << -b-b-b-b-b-b-b-b-b-b-b- @@ -3809,6 +3815,8 @@ Log_name Pos Event_type Server_id End_log_pos Info -e-e-e-e-e-e-e-e-e-e-e- >> T-trig << -e-e-e-e-e-e-e-e-e-e-e- -b-b-b-b-b-b-b-b-b-b-b- >> N-proc << -b-b-b-b-b-b-b-b-b-b-b- CALL pc_i_nt_5_suc (140, 4); +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. Log_name Pos Event_type Server_id End_log_pos Info -e-e-e-e-e-e-e-e-e-e-e- >> N-proc << -e-e-e-e-e-e-e-e-e-e-e- -b-b-b-b-b-b-b-b-b-b-b- >> C << -b-b-b-b-b-b-b-b-b-b-b- @@ -3907,6 +3915,8 @@ Log_name Pos Event_type Server_id End_log_pos Info SELECT fc_i_nt_5_suc (143, 4); fc_i_nt_5_suc (143, 4) fc_i_nt_5_suc +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. Log_name Pos Event_type Server_id End_log_pos Info -e-e-e-e-e-e-e-e-e-e-e- >> N-func << -e-e-e-e-e-e-e-e-e-e-e- -b-b-b-b-b-b-b-b-b-b-b- >> C << -b-b-b-b-b-b-b-b-b-b-b- @@ -3937,6 +3947,8 @@ Log_name Pos Event_type Server_id End_log_pos Info -e-e-e-e-e-e-e-e-e-e-e- >> T-func << -e-e-e-e-e-e-e-e-e-e-e- -b-b-b-b-b-b-b-b-b-b-b- >> N-proc << -b-b-b-b-b-b-b-b-b-b-b- CALL pc_i_nt_5_suc (144, 4); +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. Log_name Pos Event_type Server_id End_log_pos Info -e-e-e-e-e-e-e-e-e-e-e- >> N-proc << -e-e-e-e-e-e-e-e-e-e-e- -b-b-b-b-b-b-b-b-b-b-b- >> C << -b-b-b-b-b-b-b-b-b-b-b- @@ -4033,6 +4045,8 @@ Log_name Pos Event_type Server_id End_log_pos Info SELECT fc_i_nt_5_suc (147, 4); fc_i_nt_5_suc (147, 4) fc_i_nt_5_suc +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. Log_name Pos Event_type Server_id End_log_pos Info -e-e-e-e-e-e-e-e-e-e-e- >> N-func << -e-e-e-e-e-e-e-e-e-e-e- -b-b-b-b-b-b-b-b-b-b-b- >> C << -b-b-b-b-b-b-b-b-b-b-b- @@ -4063,6 +4077,8 @@ Log_name Pos Event_type Server_id End_log_pos Info -e-e-e-e-e-e-e-e-e-e-e- >> T-proc << -e-e-e-e-e-e-e-e-e-e-e- -b-b-b-b-b-b-b-b-b-b-b- >> N-proc << -b-b-b-b-b-b-b-b-b-b-b- CALL pc_i_nt_5_suc (148, 4); +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. Log_name Pos Event_type Server_id End_log_pos Info -e-e-e-e-e-e-e-e-e-e-e- >> N-proc << -e-e-e-e-e-e-e-e-e-e-e- -b-b-b-b-b-b-b-b-b-b-b- >> C << -b-b-b-b-b-b-b-b-b-b-b- @@ -4295,6 +4311,8 @@ Log_name Pos Event_type Server_id End_log_pos Info SELECT fc_i_nt_5_suc (155, 4); fc_i_nt_5_suc (155, 4) fc_i_nt_5_suc +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. Log_name Pos Event_type Server_id End_log_pos Info -e-e-e-e-e-e-e-e-e-e-e- >> N-func << -e-e-e-e-e-e-e-e-e-e-e- -b-b-b-b-b-b-b-b-b-b-b- >> R << -b-b-b-b-b-b-b-b-b-b-b- @@ -4325,6 +4343,8 @@ Log_name Pos Event_type Server_id End_log_pos Info -e-e-e-e-e-e-e-e-e-e-e- >> T << -e-e-e-e-e-e-e-e-e-e-e- -b-b-b-b-b-b-b-b-b-b-b- >> N-proc << -b-b-b-b-b-b-b-b-b-b-b- CALL pc_i_nt_5_suc (156, 4); +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. Log_name Pos Event_type Server_id End_log_pos Info -e-e-e-e-e-e-e-e-e-e-e- >> N-proc << -e-e-e-e-e-e-e-e-e-e-e- -b-b-b-b-b-b-b-b-b-b-b- >> R << -b-b-b-b-b-b-b-b-b-b-b- @@ -4423,6 +4443,8 @@ Log_name Pos Event_type Server_id End_log_pos Info SELECT fc_i_nt_5_suc (159, 4); fc_i_nt_5_suc (159, 4) fc_i_nt_5_suc +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. Log_name Pos Event_type Server_id End_log_pos Info -e-e-e-e-e-e-e-e-e-e-e- >> N-func << -e-e-e-e-e-e-e-e-e-e-e- -b-b-b-b-b-b-b-b-b-b-b- >> R << -b-b-b-b-b-b-b-b-b-b-b- @@ -4453,6 +4475,8 @@ Log_name Pos Event_type Server_id End_log_pos Info -e-e-e-e-e-e-e-e-e-e-e- >> T-trig << -e-e-e-e-e-e-e-e-e-e-e- -b-b-b-b-b-b-b-b-b-b-b- >> N-proc << -b-b-b-b-b-b-b-b-b-b-b- CALL pc_i_nt_5_suc (160, 4); +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. Log_name Pos Event_type Server_id End_log_pos Info -e-e-e-e-e-e-e-e-e-e-e- >> N-proc << -e-e-e-e-e-e-e-e-e-e-e- -b-b-b-b-b-b-b-b-b-b-b- >> R << -b-b-b-b-b-b-b-b-b-b-b- @@ -4557,6 +4581,8 @@ Log_name Pos Event_type Server_id End_log_pos Info SELECT fc_i_nt_5_suc (163, 4); fc_i_nt_5_suc (163, 4) fc_i_nt_5_suc +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. Log_name Pos Event_type Server_id End_log_pos Info -e-e-e-e-e-e-e-e-e-e-e- >> N-func << -e-e-e-e-e-e-e-e-e-e-e- -b-b-b-b-b-b-b-b-b-b-b- >> R << -b-b-b-b-b-b-b-b-b-b-b- @@ -4589,6 +4615,8 @@ Log_name Pos Event_type Server_id End_log_pos Info -e-e-e-e-e-e-e-e-e-e-e- >> T-func << -e-e-e-e-e-e-e-e-e-e-e- -b-b-b-b-b-b-b-b-b-b-b- >> N-proc << -b-b-b-b-b-b-b-b-b-b-b- CALL pc_i_nt_5_suc (164, 4); +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. Log_name Pos Event_type Server_id End_log_pos Info -e-e-e-e-e-e-e-e-e-e-e- >> N-proc << -e-e-e-e-e-e-e-e-e-e-e- -b-b-b-b-b-b-b-b-b-b-b- >> R << -b-b-b-b-b-b-b-b-b-b-b- @@ -4691,6 +4719,8 @@ Log_name Pos Event_type Server_id End_log_pos Info SELECT fc_i_nt_5_suc (167, 4); fc_i_nt_5_suc (167, 4) fc_i_nt_5_suc +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. Log_name Pos Event_type Server_id End_log_pos Info -e-e-e-e-e-e-e-e-e-e-e- >> N-func << -e-e-e-e-e-e-e-e-e-e-e- -b-b-b-b-b-b-b-b-b-b-b- >> R << -b-b-b-b-b-b-b-b-b-b-b- @@ -4723,6 +4753,8 @@ Log_name Pos Event_type Server_id End_log_pos Info -e-e-e-e-e-e-e-e-e-e-e- >> T-proc << -e-e-e-e-e-e-e-e-e-e-e- -b-b-b-b-b-b-b-b-b-b-b- >> N-proc << -b-b-b-b-b-b-b-b-b-b-b- CALL pc_i_nt_5_suc (168, 4); +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. Log_name Pos Event_type Server_id End_log_pos Info -e-e-e-e-e-e-e-e-e-e-e- >> N-proc << -e-e-e-e-e-e-e-e-e-e-e- -b-b-b-b-b-b-b-b-b-b-b- >> R << -b-b-b-b-b-b-b-b-b-b-b- @@ -5291,6 +5323,8 @@ Log_name Pos Event_type Server_id End_log_pos Info -e-e-e-e-e-e-e-e-e-e-e- >> B << -e-e-e-e-e-e-e-e-e-e-e- -b-b-b-b-b-b-b-b-b-b-b- >> N-proc << -b-b-b-b-b-b-b-b-b-b-b- CALL pc_i_nt_5_suc (185, 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. Log_name Pos Event_type Server_id End_log_pos Info master-bin.000001 # Query # # BEGIN master-bin.000001 # Query # # use `test`; INSERT INTO nt_5(trans_id, stmt_id) VALUES ( NAME_CONST('p_trans_id',185), NAME_CONST('in_stmt_id',1)) @@ -5329,6 +5363,8 @@ Log_name Pos Event_type Server_id End_log_pos Info -e-e-e-e-e-e-e-e-e-e-e- >> B << -e-e-e-e-e-e-e-e-e-e-e- -b-b-b-b-b-b-b-b-b-b-b- >> N-proc << -b-b-b-b-b-b-b-b-b-b-b- CALL pc_i_nt_5_suc (186, 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. Log_name Pos Event_type Server_id End_log_pos Info master-bin.000001 # Query # # BEGIN master-bin.000001 # Query # # use `test`; INSERT INTO nt_5(trans_id, stmt_id) VALUES ( NAME_CONST('p_trans_id',186), NAME_CONST('in_stmt_id',1)) @@ -5367,6 +5403,8 @@ Log_name Pos Event_type Server_id End_log_pos Info -e-e-e-e-e-e-e-e-e-e-e- >> B << -e-e-e-e-e-e-e-e-e-e-e- -b-b-b-b-b-b-b-b-b-b-b- >> N-proc << -b-b-b-b-b-b-b-b-b-b-b- CALL pc_i_nt_5_suc (187, 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. Log_name Pos Event_type Server_id End_log_pos Info master-bin.000001 # Query # # BEGIN master-bin.000001 # Query # # use `test`; INSERT INTO nt_5(trans_id, stmt_id) VALUES ( NAME_CONST('p_trans_id',187), NAME_CONST('in_stmt_id',1)) @@ -5407,6 +5445,8 @@ Log_name Pos Event_type Server_id End_log_pos Info -e-e-e-e-e-e-e-e-e-e-e- >> B << -e-e-e-e-e-e-e-e-e-e-e- -b-b-b-b-b-b-b-b-b-b-b- >> N-proc << -b-b-b-b-b-b-b-b-b-b-b- CALL pc_i_nt_5_suc (188, 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. Log_name Pos Event_type Server_id End_log_pos Info master-bin.000001 # Query # # BEGIN master-bin.000001 # Query # # use `test`; INSERT INTO nt_5(trans_id, stmt_id) VALUES ( NAME_CONST('p_trans_id',188), NAME_CONST('in_stmt_id',1)) @@ -5885,6 +5925,8 @@ Log_name Pos Event_type Server_id End_log_pos Info -e-e-e-e-e-e-e-e-e-e-e- >> B << -e-e-e-e-e-e-e-e-e-e-e- -b-b-b-b-b-b-b-b-b-b-b- >> N-proc << -b-b-b-b-b-b-b-b-b-b-b- CALL pc_i_nt_5_suc (201, 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. Log_name Pos Event_type Server_id End_log_pos Info master-bin.000001 # Query # # BEGIN master-bin.000001 # Query # # use `test`; INSERT INTO nt_5(trans_id, stmt_id) VALUES ( NAME_CONST('p_trans_id',201), NAME_CONST('in_stmt_id',1)) @@ -5925,6 +5967,8 @@ Log_name Pos Event_type Server_id End_log_pos Info -e-e-e-e-e-e-e-e-e-e-e- >> B << -e-e-e-e-e-e-e-e-e-e-e- -b-b-b-b-b-b-b-b-b-b-b- >> N-proc << -b-b-b-b-b-b-b-b-b-b-b- CALL pc_i_nt_5_suc (202, 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. Log_name Pos Event_type Server_id End_log_pos Info master-bin.000001 # Query # # BEGIN master-bin.000001 # Query # # use `test`; INSERT INTO nt_5(trans_id, stmt_id) VALUES ( NAME_CONST('p_trans_id',202), NAME_CONST('in_stmt_id',1)) @@ -5967,6 +6011,8 @@ Log_name Pos Event_type Server_id End_log_pos Info -e-e-e-e-e-e-e-e-e-e-e- >> B << -e-e-e-e-e-e-e-e-e-e-e- -b-b-b-b-b-b-b-b-b-b-b- >> N-proc << -b-b-b-b-b-b-b-b-b-b-b- CALL pc_i_nt_5_suc (203, 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. Log_name Pos Event_type Server_id End_log_pos Info master-bin.000001 # Query # # BEGIN master-bin.000001 # Query # # use `test`; INSERT INTO nt_5(trans_id, stmt_id) VALUES ( NAME_CONST('p_trans_id',203), NAME_CONST('in_stmt_id',1)) @@ -6007,6 +6053,8 @@ Log_name Pos Event_type Server_id End_log_pos Info -e-e-e-e-e-e-e-e-e-e-e- >> B << -e-e-e-e-e-e-e-e-e-e-e- -b-b-b-b-b-b-b-b-b-b-b- >> N-proc << -b-b-b-b-b-b-b-b-b-b-b- CALL pc_i_nt_5_suc (204, 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. Log_name Pos Event_type Server_id End_log_pos Info master-bin.000001 # Query # # BEGIN master-bin.000001 # Query # # use `test`; INSERT INTO nt_5(trans_id, stmt_id) VALUES ( NAME_CONST('p_trans_id',204), NAME_CONST('in_stmt_id',1)) diff --git a/mysql-test/suite/rpl/r/rpl_stm_auto_increment_bug33029.result b/mysql-test/suite/rpl/r/rpl_stm_auto_increment_bug33029.result index 72de5950bb3..7cbe1d73254 100644 --- a/mysql-test/suite/rpl/r/rpl_stm_auto_increment_bug33029.result +++ b/mysql-test/suite/rpl/r/rpl_stm_auto_increment_bug33029.result @@ -39,6 +39,8 @@ INSERT INTO t2 VALUES (NULL); RETURN i; END// CALL p1(); +Warnings: +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it invokes a trigger or a stored function that inserts into an AUTO_INCREMENT column. Inserted values cannot be logged correctly. show binlog events from ; Log_name Pos Event_type Server_id End_log_pos Info master-bin.000001 # Query # # BEGIN @@ -123,6 +125,8 @@ SELECT * FROM t2; id DROP TRIGGER tr1; CALL p2(); +Warnings: +Note 1592 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it invokes a trigger or a stored function that inserts into an AUTO_INCREMENT column. Inserted values cannot be logged correctly. show binlog events from ; Log_name Pos Event_type Server_id End_log_pos Info master-bin.000001 # Query # # BEGIN diff --git a/sql/log.cc b/sql/log.cc index 1e4682e4bc3..86f8100be07 100644 --- a/sql/log.cc +++ b/sql/log.cc @@ -4704,7 +4704,7 @@ bool MYSQL_BIN_LOG::write(Log_event *event_info) file= cache_mngr->get_binlog_cache_log(is_trans_cache); cache_data= cache_mngr->get_binlog_cache_data(is_trans_cache); - if (thd->stmt_accessed_non_trans_temp_table()) + if (thd->lex->stmt_accessed_non_trans_temp_table()) cache_data->set_changes_to_non_trans_temp_table(); thd->binlog_start_trans_and_stmt(); diff --git a/sql/log_event.cc b/sql/log_event.cc index ea7f4b4b245..d224f555cf2 100644 --- a/sql/log_event.cc +++ b/sql/log_event.cc @@ -679,7 +679,7 @@ Log_event::Log_event(THD* thd_arg, uint16 flags_arg, bool using_trans) server_id= thd->server_id; when= thd->start_time; cache_type= ((using_trans || stmt_has_updated_trans_table(thd) || - (thd->stmt_accessed_temp_table() && + (thd->lex->stmt_accessed_temp_table() && trans_has_updated_trans_table(thd))) ? Log_event::EVENT_TRANSACTIONAL_CACHE : Log_event::EVENT_STMT_CACHE); @@ -2573,7 +2573,7 @@ Query_log_event::Query_log_event(THD* thd_arg, const char* query_arg, else { cache_type= ((using_trans || stmt_has_updated_trans_table(thd) || trx_cache || - (thd->stmt_accessed_temp_table() && + (thd->lex->stmt_accessed_temp_table() && trans_has_updated_trans_table(thd))) ? Log_event::EVENT_TRANSACTIONAL_CACHE : Log_event::EVENT_STMT_CACHE); diff --git a/sql/sp_head.cc b/sql/sp_head.cc index 2d3a32c7f7f..e94b005b9ba 100644 --- a/sql/sp_head.cc +++ b/sql/sp_head.cc @@ -1950,6 +1950,14 @@ err_with_cleanup: free_root(&call_mem_root, MYF(0)); thd->spcont= octx; + /* + If not insided a procedure and a function printing warning + messsages. + */ + if (need_binlog_call && + thd->spcont == NULL && !thd->binlog_evt_union.do_union) + thd->issue_unsafe_warnings(); + DBUG_RETURN(err_status); } @@ -2195,6 +2203,17 @@ sp_head::execute_procedure(THD *thd, List *args) thd->spcont= save_spcont; thd->utime_after_lock= utime_before_sp_exec; + /* + If not insided a procedure and a function printing warning + messsages. + */ + bool need_binlog_call= mysql_bin_log.is_open() && + (thd->variables.option_bits & OPTION_BIN_LOG) && + !thd->is_current_stmt_binlog_format_row(); + if (need_binlog_call && thd->spcont == NULL && + !thd->binlog_evt_union.do_union) + thd->issue_unsafe_warnings(); + DBUG_RETURN(err_status); } diff --git a/sql/sql_class.cc b/sql/sql_class.cc index 60a871e9e88..2fdf270ae66 100644 --- a/sql/sql_class.cc +++ b/sql/sql_class.cc @@ -492,7 +492,6 @@ THD::THD() rli_fake(0), user_time(0), in_sub_stmt(0), binlog_unsafe_warning_flags(0), - stmt_accessed_table_flag(0), binlog_table_maps(0), table_map_for_update(0), arg_of_last_insert_id_function(FALSE), @@ -3675,8 +3674,17 @@ int THD::decide_logging_format(TABLE_LIST *tables) Innodb and Falcon; Innodb and MyIsam. */ my_bool multi_access_engine= FALSE; - + /* + Identifies if a table is changed. + */ + my_bool is_write= FALSE; + /* + A pointer to a previous table that was changed. + */ TABLE* prev_write_table= NULL; + /* + A pointer to a previous table that was accessed. + */ TABLE* prev_access_table= NULL; #ifndef DBUG_OFF @@ -3700,7 +3708,8 @@ int THD::decide_logging_format(TABLE_LIST *tables) if (table->placeholder()) continue; - if (table->table->s->table_category == TABLE_CATEGORY_PERFORMANCE) + if (table->table->s->table_category == TABLE_CATEGORY_PERFORMANCE || + table->table->s->table_category == TABLE_CATEGORY_LOG) lex->set_stmt_unsafe(LEX::BINLOG_STMT_UNSAFE_SYSTEM_TABLE); handler::Table_flags const flags= table->table->file->ha_table_flags(); @@ -3716,16 +3725,18 @@ int THD::decide_logging_format(TABLE_LIST *tables) my_bool trans= table->table->file->has_transactions(); if (table->table->s->tmp_table) - set_stmt_accessed_table(trans ? STMT_WRITES_TEMP_TRANS_TABLE : - STMT_WRITES_TEMP_NON_TRANS_TABLE); + lex->set_stmt_accessed_table(trans ? LEX::STMT_WRITES_TEMP_TRANS_TABLE : + LEX::STMT_WRITES_TEMP_NON_TRANS_TABLE); else - set_stmt_accessed_table(trans ? STMT_WRITES_TRANS_TABLE : - STMT_WRITES_NON_TRANS_TABLE); + lex->set_stmt_accessed_table(trans ? LEX::STMT_WRITES_TRANS_TABLE : + LEX::STMT_WRITES_NON_TRANS_TABLE); flags_write_all_set &= flags; flags_write_some_set |= flags; + is_write= TRUE; prev_write_table= table->table; + } flags_access_some_set |= flags; @@ -3736,11 +3747,11 @@ int THD::decide_logging_format(TABLE_LIST *tables) my_bool trans= table->table->file->has_transactions(); if (table->table->s->tmp_table) - set_stmt_accessed_table(trans ? STMT_READS_TEMP_TRANS_TABLE : - STMT_READS_TEMP_NON_TRANS_TABLE); + lex->set_stmt_accessed_table(trans ? LEX::STMT_READS_TEMP_TRANS_TABLE : + LEX::STMT_READS_TEMP_NON_TRANS_TABLE); else - set_stmt_accessed_table(trans ? STMT_READS_TRANS_TABLE : - STMT_READS_NON_TRANS_TABLE); + lex->set_stmt_accessed_table(trans ? LEX::STMT_READS_TRANS_TABLE : + LEX::STMT_READS_NON_TRANS_TABLE); } if (prev_access_table && prev_access_table->file->ht != @@ -3812,24 +3823,24 @@ int THD::decide_logging_format(TABLE_LIST *tables) my_bool non_trans_unsafe= FALSE; /* Case 1. */ - if (stmt_accessed_table(STMT_WRITES_TRANS_TABLE) && - stmt_accessed_table(STMT_WRITES_NON_TRANS_TABLE)) + if (lex->stmt_accessed_table(LEX::STMT_WRITES_TRANS_TABLE) && + lex->stmt_accessed_table(LEX::STMT_WRITES_NON_TRANS_TABLE)) mixed_unsafe= TRUE; /* Case 2. */ - else if (stmt_accessed_table(STMT_WRITES_TEMP_TRANS_TABLE) && - stmt_accessed_table(STMT_WRITES_NON_TRANS_TABLE)) + else if (lex->stmt_accessed_table(LEX::STMT_WRITES_TEMP_TRANS_TABLE) && + lex->stmt_accessed_table(LEX::STMT_WRITES_NON_TRANS_TABLE)) mixed_unsafe= TRUE; /* Case 3. */ - else if (stmt_accessed_table(STMT_WRITES_TRANS_TABLE) && - stmt_accessed_table(STMT_READS_NON_TRANS_TABLE)) + else if (lex->stmt_accessed_table(LEX::STMT_WRITES_TRANS_TABLE) && + lex->stmt_accessed_table(LEX::STMT_READS_NON_TRANS_TABLE)) mixed_unsafe= TRUE; /* Case 4. */ - else if (stmt_accessed_table(STMT_WRITES_TEMP_TRANS_TABLE) && - stmt_accessed_table(STMT_READS_NON_TRANS_TABLE)) + else if (lex->stmt_accessed_table(LEX::STMT_WRITES_TEMP_TRANS_TABLE) && + lex->stmt_accessed_table(LEX::STMT_READS_NON_TRANS_TABLE)) mixed_unsafe= TRUE; /* Case 5. */ - else if (stmt_accessed_table(STMT_WRITES_NON_TRANS_TABLE) && - stmt_accessed_table(STMT_READS_TRANS_TABLE) && + else if (lex->stmt_accessed_table(LEX::STMT_WRITES_NON_TRANS_TABLE) && + lex->stmt_accessed_table(LEX::STMT_READS_TRANS_TABLE) && tx_isolation < ISO_REPEATABLE_READ) /* By default, InnoDB operates in REPEATABLE READ and with the option @@ -3847,28 +3858,28 @@ int THD::decide_logging_format(TABLE_LIST *tables) if (trans_has_updated_trans_table(this)) { /* Case 6. */ - if (stmt_accessed_table(STMT_WRITES_NON_TRANS_TABLE) && - stmt_accessed_table(STMT_READS_TRANS_TABLE)) + if (lex->stmt_accessed_table(LEX::STMT_WRITES_NON_TRANS_TABLE) && + lex->stmt_accessed_table(LEX::STMT_READS_TRANS_TABLE)) mixed_unsafe= TRUE; /* Case 7. */ - else if (stmt_accessed_table(STMT_WRITES_NON_TRANS_TABLE) && - stmt_accessed_table(STMT_READS_TEMP_TRANS_TABLE)) + else if (lex->stmt_accessed_table(LEX::STMT_WRITES_NON_TRANS_TABLE) && + lex->stmt_accessed_table(LEX::STMT_READS_TEMP_TRANS_TABLE)) mixed_unsafe= TRUE; /* Case 8. */ - else if (stmt_accessed_table(STMT_WRITES_NON_TRANS_TABLE) && - stmt_accessed_table(STMT_READS_TEMP_NON_TRANS_TABLE)) + else if (lex->stmt_accessed_table(LEX::STMT_WRITES_NON_TRANS_TABLE) && + lex->stmt_accessed_table(LEX::STMT_READS_TEMP_NON_TRANS_TABLE)) mixed_unsafe= TRUE; /* Case 9. */ - else if (stmt_accessed_table(STMT_WRITES_TEMP_NON_TRANS_TABLE) && - stmt_accessed_table(STMT_WRITES_NON_TRANS_TABLE)) + else if (lex->stmt_accessed_table(LEX::STMT_WRITES_TEMP_NON_TRANS_TABLE) && + lex->stmt_accessed_table(LEX::STMT_WRITES_NON_TRANS_TABLE)) mixed_unsafe= TRUE; /* Case 10. */ - else if (stmt_accessed_table(STMT_WRITES_TEMP_NON_TRANS_TABLE) && - stmt_accessed_table(STMT_READS_NON_TRANS_TABLE)) + else if (lex->stmt_accessed_table(LEX::STMT_WRITES_TEMP_NON_TRANS_TABLE) && + lex->stmt_accessed_table(LEX::STMT_READS_NON_TRANS_TABLE)) mixed_unsafe= TRUE; /* Case 11. */ else if (!variables.binlog_direct_non_trans_update && - stmt_accessed_table(STMT_WRITES_NON_TRANS_TABLE)) + lex->stmt_accessed_table(LEX::STMT_WRITES_NON_TRANS_TABLE)) non_trans_unsafe= TRUE; } @@ -3959,13 +3970,14 @@ int THD::decide_logging_format(TABLE_LIST *tables) */ my_error((error= ER_BINLOG_STMT_MODE_AND_ROW_ENGINE), MYF(0), ""); } - else if ((unsafe_flags= lex->get_stmt_unsafe_flags()) != 0) + else if (is_write && (unsafe_flags= lex->get_stmt_unsafe_flags()) != 0) { /* 7. Warning: Unsafe statement logged as statement due to binlog_format = STATEMENT */ binlog_unsafe_warning_flags|= unsafe_flags; + DBUG_PRINT("info", ("Scheduling warning to be issued by " "binlog_query: '%s'", ER(ER_BINLOG_UNSAFE_STATEMENT))); @@ -4441,23 +4453,10 @@ void THD::issue_unsafe_warnings() Ensure that binlog_unsafe_warning_flags is big enough to hold all bits. This is actually a constant expression. */ - DBUG_ASSERT(2 * LEX::BINLOG_STMT_UNSAFE_COUNT <= + DBUG_ASSERT(LEX::BINLOG_STMT_UNSAFE_COUNT <= sizeof(binlog_unsafe_warning_flags) * CHAR_BIT); uint32 unsafe_type_flags= binlog_unsafe_warning_flags; - - /* - Clear: (1) bits above BINLOG_STMT_UNSAFE_COUNT; (2) bits for - warnings that have been printed already. - */ - unsafe_type_flags &= (LEX::BINLOG_STMT_UNSAFE_ALL_FLAGS ^ - (unsafe_type_flags >> LEX::BINLOG_STMT_UNSAFE_COUNT)); - /* If all warnings have been printed already, return. */ - if (unsafe_type_flags == 0) - DBUG_VOID_RETURN; - - DBUG_PRINT("info", ("unsafe_type_flags: 0x%x", unsafe_type_flags)); - /* For each unsafe_type, check if the statement is unsafe in this way and issue a warning. @@ -4481,12 +4480,6 @@ void THD::issue_unsafe_warnings() } } } - /* - Mark these unsafe types as already printed, to avoid printing - warnings for them again. - */ - binlog_unsafe_warning_flags|= - unsafe_type_flags << LEX::BINLOG_STMT_UNSAFE_COUNT; DBUG_VOID_RETURN; } @@ -4540,19 +4533,32 @@ int THD::binlog_query(THD::enum_binlog_query_type qtype, char const *query_arg, /* Warnings for unsafe statements logged in statement format are - printed here instead of in decide_logging_format(). This is - because the warnings should be printed only if the statement is - actually logged. When executing decide_logging_format(), we cannot - know for sure if the statement will be logged. + printed in three places instead of in decide_logging_format(). + This is because the warnings should be printed only if the statement + is actually logged. When executing decide_logging_format(), we cannot + know for sure if the statement will be logged: + + 1 - sp_head::execute_procedure which prints out warnings for calls to + stored procedures. + + 2 - sp_head::execute_function which prints out warnings for calls + involving functions. + + 3 - THD::binlog_query (here) which prints warning for top level + statements not covered by the two cases above: i.e., if not insided a + procedure and a function. Besides, we should not try to print these warnings if it is not possible to write statements to the binary log as it happens when the execution is inside a function, or generaly speaking, when the variables.option_bits & OPTION_BIN_LOG is false. + */ - if (variables.option_bits & OPTION_BIN_LOG) + if ((variables.option_bits & OPTION_BIN_LOG) && + spcont == NULL && !binlog_evt_union.do_union) issue_unsafe_warnings(); + switch (qtype) { /* ROW_QUERY_TYPE means that the statement may be logged either in diff --git a/sql/sql_class.h b/sql/sql_class.h index b23b65dae2f..78eeda5843d 100644 --- a/sql/sql_class.h +++ b/sql/sql_class.h @@ -1566,125 +1566,6 @@ public: return current_stmt_binlog_format == BINLOG_FORMAT_ROW; } - enum enum_stmt_accessed_table - { - /* - If a transactional table is about to be read. Note that - a write implies a read. - */ - STMT_READS_TRANS_TABLE= 0, - /* - If a transactional table is about to be updated. - */ - STMT_WRITES_TRANS_TABLE, - /* - If a non-transactional table is about to be read. Note that - a write implies a read. - */ - STMT_READS_NON_TRANS_TABLE, - /* - If a non-transactional table is about to be updated. - */ - STMT_WRITES_NON_TRANS_TABLE, - /* - If a temporary transactional table is about to be read. Note - that a write implies a read. - */ - STMT_READS_TEMP_TRANS_TABLE, - /* - If a temporary transactional table is about to be updated. - */ - STMT_WRITES_TEMP_TRANS_TABLE, - /* - If a temporary non-transactional table is about to be read. Note - that a write implies a read. - */ - STMT_READS_TEMP_NON_TRANS_TABLE, - /* - If a temporary non-transactional table is about to be updated. - */ - STMT_WRITES_TEMP_NON_TRANS_TABLE, - /* - The last element of the enumeration. Please, if necessary add - anything before this. - */ - STMT_ACCESS_TABLE_COUNT - }; - - /** - Sets the type of table that is about to be accessed while executing a - statement. - - @param accessed_table Enumeration type that defines the type of table, - e.g. temporary, transactional, non-transactional. - */ - inline void set_stmt_accessed_table(enum_stmt_accessed_table accessed_table) - { - DBUG_ENTER("THD::set_stmt_accessed_table"); - - DBUG_ASSERT(accessed_table >= 0 && accessed_table < STMT_ACCESS_TABLE_COUNT); - stmt_accessed_table_flag |= (1U << accessed_table); - - DBUG_VOID_RETURN; - } - - /** - Checks if a type of table is about to be accessed while executing a - statement. - - @param accessed_table Enumeration type that defines the type of table, - e.g. temporary, transactional, non-transactional. - - @return - @retval TRUE if the type of the table is about to be accessed - @retval FALSE otherwise - */ - inline bool stmt_accessed_table(enum_stmt_accessed_table accessed_table) - { - DBUG_ENTER("THD::stmt_accessed_table"); - - DBUG_ASSERT(accessed_table >= 0 && accessed_table < STMT_ACCESS_TABLE_COUNT); - - DBUG_RETURN((stmt_accessed_table_flag & (1U << accessed_table)) != 0); - } - - /** - Checks if a temporary table is about to be accessed while executing a - statement. - - @return - @retval TRUE if a temporary table is about to be accessed - @retval FALSE otherwise - */ - inline bool stmt_accessed_temp_table() - { - DBUG_ENTER("THD::stmt_accessed_temp_table"); - - DBUG_RETURN((stmt_accessed_table_flag & - ((1U << STMT_READS_TEMP_TRANS_TABLE) | - (1U << STMT_WRITES_TEMP_TRANS_TABLE) | - (1U << STMT_READS_TEMP_NON_TRANS_TABLE) | - (1U << STMT_WRITES_TEMP_NON_TRANS_TABLE))) != 0); - } - - /** - Checks if a temporary non-transactional table is about to be accessed - while executing a statement. - - @return - @retval TRUE if a temporary non-transactional table is about to be - accessed - @retval FALSE otherwise - */ - inline bool stmt_accessed_non_trans_temp_table() - { - DBUG_ENTER("THD::stmt_accessed_non_trans_temp_table"); - - DBUG_RETURN((stmt_accessed_table_flag & - ((1U << STMT_READS_TEMP_NON_TRANS_TABLE) | - (1U << STMT_WRITES_TEMP_NON_TRANS_TABLE))) != 0); - } - private: /** Indicates the format in which the current statement will be @@ -1695,24 +1576,8 @@ private: /** Bit field for the state of binlog warnings. - There are two groups of bits: - - - The first Lex::BINLOG_STMT_UNSAFE_COUNT bits list all types of - unsafeness that the current statement has. - - - The following Lex::BINLOG_STMT_UNSAFE_COUNT bits list all types - of unsafeness that the current statement has issued warnings - for. - - Hence, this variable must be big enough to hold - 2*Lex::BINLOG_STMT_UNSAFE_COUNT bits. This is asserted in @c - issue_unsafe_warnings(). - - The first and second groups of bits are set by @c - decide_logging_format() when it detects that a warning should be - issued. The third group of bits is set from @c binlog_query() - when a warning is issued. All bits are cleared at the end of the - top-level statement. + The first Lex::BINLOG_STMT_UNSAFE_COUNT bits list all types of + unsafeness that the current statement has. This must be a member of THD and not of LEX, because warnings are detected and issued in different places (@c @@ -1722,20 +1587,14 @@ private: */ uint32 binlog_unsafe_warning_flags; - /** - Bit field that determines the type of tables that are about to be - be accessed while executing a statement. - */ - uint32 stmt_accessed_table_flag; - - void issue_unsafe_warnings(); - /* Number of outstanding table maps, i.e., table maps in the transaction cache. */ uint binlog_table_maps; public: + void issue_unsafe_warnings(); + uint get_binlog_table_maps() const { return binlog_table_maps; } diff --git a/sql/sql_lex.cc b/sql/sql_lex.cc index 6411b194a8a..b70f33a6c3f 100644 --- a/sql/sql_lex.cc +++ b/sql/sql_lex.cc @@ -2300,6 +2300,7 @@ void Query_tables_list::reset_query_tables_list(bool init) sroutines_list_own_last= sroutines_list.next; sroutines_list_own_elements= 0; binlog_stmt_flags= 0; + stmt_accessed_table_flag= 0; } diff --git a/sql/sql_lex.h b/sql/sql_lex.h index f1b558b8be4..e6c4e69d1a6 100644 --- a/sql/sql_lex.h +++ b/sql/sql_lex.h @@ -1276,6 +1276,125 @@ public: DBUG_VOID_RETURN; } + enum enum_stmt_accessed_table + { + /* + If a transactional table is about to be read. Note that + a write implies a read. + */ + STMT_READS_TRANS_TABLE= 0, + /* + If a transactional table is about to be updated. + */ + STMT_WRITES_TRANS_TABLE, + /* + If a non-transactional table is about to be read. Note that + a write implies a read. + */ + STMT_READS_NON_TRANS_TABLE, + /* + If a non-transactional table is about to be updated. + */ + STMT_WRITES_NON_TRANS_TABLE, + /* + If a temporary transactional table is about to be read. Note + that a write implies a read. + */ + STMT_READS_TEMP_TRANS_TABLE, + /* + If a temporary transactional table is about to be updated. + */ + STMT_WRITES_TEMP_TRANS_TABLE, + /* + If a temporary non-transactional table is about to be read. Note + that a write implies a read. + */ + STMT_READS_TEMP_NON_TRANS_TABLE, + /* + If a temporary non-transactional table is about to be updated. + */ + STMT_WRITES_TEMP_NON_TRANS_TABLE, + /* + The last element of the enumeration. Please, if necessary add + anything before this. + */ + STMT_ACCESS_TABLE_COUNT + }; + + /** + Sets the type of table that is about to be accessed while executing a + statement. + + @param accessed_table Enumeration type that defines the type of table, + e.g. temporary, transactional, non-transactional. + */ + inline void set_stmt_accessed_table(enum_stmt_accessed_table accessed_table) + { + DBUG_ENTER("THD::set_stmt_accessed_table"); + + DBUG_ASSERT(accessed_table >= 0 && accessed_table < STMT_ACCESS_TABLE_COUNT); + stmt_accessed_table_flag |= (1U << accessed_table); + + DBUG_VOID_RETURN; + } + + /** + Checks if a type of table is about to be accessed while executing a + statement. + + @param accessed_table Enumeration type that defines the type of table, + e.g. temporary, transactional, non-transactional. + + @return + @retval TRUE if the type of the table is about to be accessed + @retval FALSE otherwise + */ + inline bool stmt_accessed_table(enum_stmt_accessed_table accessed_table) + { + DBUG_ENTER("THD::stmt_accessed_table"); + + DBUG_ASSERT(accessed_table >= 0 && accessed_table < STMT_ACCESS_TABLE_COUNT); + + DBUG_RETURN((stmt_accessed_table_flag & (1U << accessed_table)) != 0); + } + + /** + Checks if a temporary table is about to be accessed while executing a + statement. + + @return + @retval TRUE if a temporary table is about to be accessed + @retval FALSE otherwise + */ + inline bool stmt_accessed_temp_table() + { + DBUG_ENTER("THD::stmt_accessed_temp_table"); + + DBUG_RETURN((stmt_accessed_table_flag & + ((1U << STMT_READS_TEMP_TRANS_TABLE) | + (1U << STMT_WRITES_TEMP_TRANS_TABLE) | + (1U << STMT_READS_TEMP_NON_TRANS_TABLE) | + (1U << STMT_WRITES_TEMP_NON_TRANS_TABLE))) != 0); + } + + /** + Checks if a temporary non-transactional table is about to be accessed + while executing a statement. + + @return + @retval TRUE if a temporary non-transactional table is about to be + accessed + @retval FALSE otherwise + */ + inline bool stmt_accessed_non_trans_temp_table() + { + DBUG_ENTER("THD::stmt_accessed_non_trans_temp_table"); + + DBUG_RETURN((stmt_accessed_table_flag & + ((1U << STMT_READS_TEMP_NON_TRANS_TABLE) | + (1U << STMT_WRITES_TEMP_NON_TRANS_TABLE))) != 0); + } + /** true if the parsed tree contains references to stored procedures or functions, false otherwise @@ -1317,6 +1436,12 @@ private: stored procedure has its own LEX object (but no own THD object). */ uint32 binlog_stmt_flags; + + /** + Bit field that determines the type of tables that are about to be + be accessed while executing a statement. + */ + uint32 stmt_accessed_table_flag; }; diff --git a/sql/sql_parse.cc b/sql/sql_parse.cc index 2ef8e9761b1..fbcfb3f49c2 100644 --- a/sql/sql_parse.cc +++ b/sql/sql_parse.cc @@ -5640,7 +5640,6 @@ void THD::reset_for_next_command() thd->reset_current_stmt_binlog_format_row(); thd->binlog_unsafe_warning_flags= 0; - thd->stmt_accessed_table_flag= 0; DBUG_PRINT("debug", ("is_current_stmt_binlog_format_row(): %d", From a1d90f124f30f30d3bc609d7a5783341089e54ce Mon Sep 17 00:00:00 2001 From: Marc Alff Date: Thu, 12 Aug 2010 03:51:58 -0600 Subject: [PATCH 120/129] Bug#55462 Performance schema: reduce the overhead of PFS_events_waits::m_wait_class This is a performance improvement fix. Removed the "volatile" property of PFS_events_waits::m_wait_class. Simplified the code accordingly. --- storage/perfschema/pfs.cc | 7 ------- storage/perfschema/pfs_events_waits.cc | 25 ++++-------------------- storage/perfschema/pfs_events_waits.h | 2 +- storage/perfschema/table_events_waits.cc | 12 ++---------- 4 files changed, 7 insertions(+), 39 deletions(-) diff --git a/storage/perfschema/pfs.cc b/storage/perfschema/pfs.cc index 93c9cf14e9d..60ef2a3b194 100644 --- a/storage/perfschema/pfs.cc +++ b/storage/perfschema/pfs.cc @@ -1117,7 +1117,6 @@ get_thread_mutex_locker_v1(PSI_mutex_locker_state *state, } PFS_wait_locker *pfs_locker= &pfs_thread->m_wait_locker_stack [pfs_thread->m_wait_locker_count]; - pfs_locker->m_waits_current.m_wait_class= NO_WAIT_CLASS; pfs_locker->m_target.m_mutex= pfs_mutex; pfs_locker->m_waits_current.m_thread= pfs_thread; @@ -1163,7 +1162,6 @@ get_thread_rwlock_locker_v1(PSI_rwlock_locker_state *state, } PFS_wait_locker *pfs_locker= &pfs_thread->m_wait_locker_stack [pfs_thread->m_wait_locker_count]; - pfs_locker->m_waits_current.m_wait_class= NO_WAIT_CLASS; pfs_locker->m_target.m_rwlock= pfs_rwlock; pfs_locker->m_waits_current.m_thread= pfs_thread; @@ -1222,7 +1220,6 @@ get_thread_cond_locker_v1(PSI_cond_locker_state *state, } PFS_wait_locker *pfs_locker= &pfs_thread->m_wait_locker_stack [pfs_thread->m_wait_locker_count]; - pfs_locker->m_waits_current.m_wait_class= NO_WAIT_CLASS; pfs_locker->m_target.m_cond= pfs_cond; pfs_locker->m_waits_current.m_thread= pfs_thread; @@ -1267,7 +1264,6 @@ get_thread_table_locker_v1(PSI_table_locker_state *state, } PFS_wait_locker *pfs_locker= &pfs_thread->m_wait_locker_stack [pfs_thread->m_wait_locker_count]; - pfs_locker->m_waits_current.m_wait_class= NO_WAIT_CLASS; pfs_locker->m_target.m_table= pfs_table; pfs_locker->m_waits_current.m_thread= pfs_thread; @@ -1320,7 +1316,6 @@ get_thread_file_name_locker_v1(PSI_file_locker_state *state, PFS_wait_locker *pfs_locker= &pfs_thread->m_wait_locker_stack [pfs_thread->m_wait_locker_count]; - pfs_locker->m_waits_current.m_wait_class= NO_WAIT_CLASS; pfs_locker->m_target.m_file= pfs_file; pfs_locker->m_waits_current.m_thread= pfs_thread; @@ -1372,7 +1367,6 @@ get_thread_file_stream_locker_v1(PSI_file_locker_state *state, } PFS_wait_locker *pfs_locker= &pfs_thread->m_wait_locker_stack [pfs_thread->m_wait_locker_count]; - pfs_locker->m_waits_current.m_wait_class= NO_WAIT_CLASS; pfs_locker->m_target.m_file= pfs_file; pfs_locker->m_waits_current.m_thread= pfs_thread; @@ -1441,7 +1435,6 @@ get_thread_file_descriptor_locker_v1(PSI_file_locker_state *state, } PFS_wait_locker *pfs_locker= &pfs_thread->m_wait_locker_stack [pfs_thread->m_wait_locker_count]; - pfs_locker->m_waits_current.m_wait_class= NO_WAIT_CLASS; pfs_locker->m_target.m_file= pfs_file; pfs_locker->m_waits_current.m_thread= pfs_thread; diff --git a/storage/perfschema/pfs_events_waits.cc b/storage/perfschema/pfs_events_waits.cc index e32a77512cc..b6cadf9e61c 100644 --- a/storage/perfschema/pfs_events_waits.cc +++ b/storage/perfschema/pfs_events_waits.cc @@ -80,25 +80,10 @@ void cleanup_events_waits_history_long(void) events_waits_history_long_array= NULL; } -static void copy_events_waits(PFS_events_waits *dest, - const PFS_events_waits *source) +static inline void copy_events_waits(PFS_events_waits *dest, + const PFS_events_waits *source) { - /* m_wait_class must be the first member of PFS_events_waits. */ - compile_time_assert(offsetof(PFS_events_waits, m_wait_class) == 0); - - char* dest_body= (reinterpret_cast (dest)) + sizeof(events_waits_class); - const char* source_body= (reinterpret_cast (source)) - + sizeof(events_waits_class); - - /* See comments in table_events_waits_common::make_row(). */ - - /* Signal readers they are about to read garbage ... */ - dest->m_wait_class= NO_WAIT_CLASS; - /* ... that this can generate. */ - memcpy(dest_body, source_body, - sizeof(PFS_events_waits) - sizeof(events_waits_class)); - /* Signal readers the record is now clean again. */ - dest->m_wait_class= source->m_wait_class; + memcpy(dest, source, sizeof(PFS_events_waits)); } /** @@ -116,9 +101,7 @@ void insert_events_waits_history(PFS_thread *thread, PFS_events_waits *wait) causing a potential race condition. We are not testing for this and insert a possibly empty record, to make this thread (the writer) faster. - This is ok, the truncated data will have - wait->m_wait_class == NO_WAIT_CLASS, - which readers of m_waits_history will filter out. + This is ok, the readers of m_waits_history will filter this out. */ copy_events_waits(&thread->m_waits_history[index], wait); diff --git a/storage/perfschema/pfs_events_waits.h b/storage/perfschema/pfs_events_waits.h index 9a5ed8644f3..d277db39d8d 100644 --- a/storage/perfschema/pfs_events_waits.h +++ b/storage/perfschema/pfs_events_waits.h @@ -97,7 +97,7 @@ struct PFS_events_waits - TRUNCATE EVENTS_WAITS_HISTORY - TRUNCATE EVENTS_WAITS_HISTORY_LONG */ - volatile events_waits_class m_wait_class; + events_waits_class m_wait_class; /** Executing thread. */ PFS_thread *m_thread; /** Instrument metadata. */ diff --git a/storage/perfschema/table_events_waits.cc b/storage/perfschema/table_events_waits.cc index a09d7f1ba30..5e5972b68f1 100644 --- a/storage/perfschema/table_events_waits.cc +++ b/storage/perfschema/table_events_waits.cc @@ -217,16 +217,8 @@ void table_events_waits_common::make_row(bool thread_own_wait, or 8 atomics per recorded event. The problem is that we record a *lot* of events ... - Instead, a *dirty* marking is done using m_wait_class. - Using m_wait_class alone does not guarantee anything, it just filters - out most of the bad data. - This is acceptable because this code is garbage-proof, - and won't crash on bad data, only display it, - very rarely (which is accepted). - - If a bad record is displayed, it's a very transient failure: - the next select * from EVENTS_WAITS_CURRENT/_HISTORY/_HISTORY_LONG will - show clean data again. + This code is prepared to accept *dirty* records, + and sanitizes all the data before returning a row. */ m_row.m_thread_internal_id= safe_thread->m_thread_internal_id; From 53c8b221166d6d94a98e00ad4b3ba58da4d3a7eb Mon Sep 17 00:00:00 2001 From: Guilhem Bichot Date: Wed, 11 Aug 2010 19:56:56 +0200 Subject: [PATCH 121/129] fix for Bug #55672 "mysql_upgrade dies with internal error": it couldn't parse the --ssl option. client/mysql_upgrade.c: mysql_upgrade parses its options and passes some of them to the underlying tools (mysqlcheck etc). To do this passdown, it reconstructs a command-line-suitable text from the my_option object (which contains the option's name and option's value). For options which expect no parameter, it just had to use the option's name; for other options, it had to concatenate the option's name, a "=" symbol, and the option's value; it had code to handle this latter case, but only for GET_STR options (options taking a string as value). But since the work on WL 4738, the --ssl option, a GET_BOOL, which used to have no parameter (NO_ARG), can now have one (OPT_ARG), so with --ssl we came to the "default" label, error. Fixed by constructing the command-line-suitable representation for GET_BOOL too. For --ssl it will produce --ssl=1 ; for --ssl=0, it will produce --ssl=0. mysql-test/include/mysql_upgrade_preparation.inc: handles requirements of tests which use mysql_upgrade mysql-test/r/mysql_upgrade_ssl.result: result; without the code fix we would get "internal error". mysql-test/t/mysql_upgrade.test: This test has requirements before running; moved them to an include file in order to share with mysql_upgrade_ssl. mysql-test/t/mysql_upgrade_ssl.test: test for bug. Couldn't go into mysql_upgrade.test as this new test requires SSL support. --force is needed, in case mysql_upgrade.test run before (in which case mysql_upgrade_ssl would say that upgrade has already been done); --force forces the upgrade in all cases. --- client/mysql_upgrade.c | 3 ++ .../include/mysql_upgrade_preparation.inc | 30 +++++++++++++++++ mysql-test/r/mysql_upgrade_ssl.result | 32 +++++++++++++++++++ mysql-test/t/mysql_upgrade.test | 29 +---------------- mysql-test/t/mysql_upgrade_ssl.test | 10 ++++++ 5 files changed, 76 insertions(+), 28 deletions(-) create mode 100644 mysql-test/include/mysql_upgrade_preparation.inc create mode 100644 mysql-test/r/mysql_upgrade_ssl.result create mode 100644 mysql-test/t/mysql_upgrade_ssl.test diff --git a/client/mysql_upgrade.c b/client/mysql_upgrade.c index eeab3611913..882350f813b 100644 --- a/client/mysql_upgrade.c +++ b/client/mysql_upgrade.c @@ -209,6 +209,9 @@ static void add_one_option(DYNAMIC_STRING* ds, case GET_STR: arg= argument; break; + case GET_BOOL: + arg= (*(my_bool *)opt->value) ? "1" : "0"; + break; default: die("internal error at %s: %d",__FILE__, __LINE__); } diff --git a/mysql-test/include/mysql_upgrade_preparation.inc b/mysql-test/include/mysql_upgrade_preparation.inc new file mode 100644 index 00000000000..5de8a79d6e0 --- /dev/null +++ b/mysql-test/include/mysql_upgrade_preparation.inc @@ -0,0 +1,30 @@ +# Include this in any test using mysql_upgrade + +# Can't run test of external client with embedded server +-- source include/not_embedded.inc + +# Only run test if "mysql_upgrade" is found +--require r/have_mysql_upgrade.result +--disable_query_log +select LENGTH("$MYSQL_UPGRADE")>0 as have_mysql_upgrade; +--enable_query_log + +# +# Hack: +# +# If running with Valgrind ($VALGRIND_TEST <> 0) then the resource +# consumption (CPU) for upgrading a large log table will be intense. +# Therefore, truncate the log table in advance and issue a statement +# that should be logged. +# +if (`SELECT $VALGRIND_TEST`) +{ + --disable_query_log + --disable_result_log + --disable_abort_on_error + TRUNCATE TABLE mysql.general_log; + SELECT 1; + --enable_abort_on_error + --enable_result_log + --enable_query_log +} diff --git a/mysql-test/r/mysql_upgrade_ssl.result b/mysql-test/r/mysql_upgrade_ssl.result new file mode 100644 index 00000000000..f1229c4a405 --- /dev/null +++ b/mysql-test/r/mysql_upgrade_ssl.result @@ -0,0 +1,32 @@ +# +# Bug#55672 mysql_upgrade dies with internal error +# +mtr.global_suppressions OK +mtr.test_suppressions OK +mysql.columns_priv OK +mysql.db OK +mysql.event OK +mysql.func OK +mysql.general_log +Error : You can't use locks with log tables. +status : OK +mysql.help_category OK +mysql.help_keyword OK +mysql.help_relation OK +mysql.help_topic OK +mysql.host OK +mysql.ndb_binlog_index OK +mysql.plugin OK +mysql.proc OK +mysql.procs_priv OK +mysql.servers OK +mysql.slow_log +Error : You can't use locks with log tables. +status : OK +mysql.tables_priv OK +mysql.time_zone OK +mysql.time_zone_leap_second OK +mysql.time_zone_name OK +mysql.time_zone_transition OK +mysql.time_zone_transition_type OK +mysql.user OK diff --git a/mysql-test/t/mysql_upgrade.test b/mysql-test/t/mysql_upgrade.test index 3ea612d2ca7..3c6cc45da38 100644 --- a/mysql-test/t/mysql_upgrade.test +++ b/mysql-test/t/mysql_upgrade.test @@ -1,31 +1,4 @@ -# Can't run test of external client with embedded server --- source include/not_embedded.inc - -# Only run test if "mysql_upgrade" is found ---require r/have_mysql_upgrade.result ---disable_query_log -select LENGTH("$MYSQL_UPGRADE")>0 as have_mysql_upgrade; ---enable_query_log - -# -# Hack: -# -# If running with Valgrind ($VALGRIND_TEST <> 0) then the resource -# consumption (CPU) for upgrading a large log table will be intense. -# Therefore, truncate the log table in advance and issue a statement -# that should be logged. -# -if (`SELECT $VALGRIND_TEST`) -{ - --disable_query_log - --disable_result_log - --disable_abort_on_error - TRUNCATE TABLE mysql.general_log; - SELECT 1; - --enable_abort_on_error - --enable_result_log - --enable_query_log -} +-- source include/mysql_upgrade_preparation.inc # # Basic test that we can run mysql_upgrde and that it finds the diff --git a/mysql-test/t/mysql_upgrade_ssl.test b/mysql-test/t/mysql_upgrade_ssl.test new file mode 100644 index 00000000000..d1c029bf33a --- /dev/null +++ b/mysql-test/t/mysql_upgrade_ssl.test @@ -0,0 +1,10 @@ +# mysql_upgrade tests requiring SSL support + +-- source include/have_ssl_communication.inc +-- source include/mysql_upgrade_preparation.inc + +--echo # +--echo # Bug#55672 mysql_upgrade dies with internal error +--echo # +--exec $MYSQL_UPGRADE --skip-verbose --ssl --force 2>&1 +--exit From 5d458c6fdbb6e57f5f9fb0d2dc9b22a853e4bbc6 Mon Sep 17 00:00:00 2001 From: Joerg Bruehe Date: Wed, 11 Aug 2010 22:52:23 +0200 Subject: [PATCH 122/129] Fix Bug#55015 "MySQL server is not restarted properly after RPM upgrade" The problem is that with the general spec file cleanup and alignment we also did a name change, dropping the "-community" part from the package file name. As a result of this, RPM (some versions of it) will report file conflicts, because it considers this name difference to imply different packages. To avoid this, the spec file explicitly "obsoletes" the old packages (with "-community" in the file name). Now, RPM will first install these packages and the remove the old ones, and part of that removal is running the "%preun" section which stops the server and uninstalls the service (removes the symlinks to "/etc/init.d/mysql" from the run level directories). This stop/uninstall will affect the new server! The fix is to define a "%triggerpostun" in this spec file which will watch for removal of the "-community" server. If this is done (as part of this install/upgrade), the trigger code will re-install the service and restart the server process. In addition, the "sleep" calls after starting the server have been cleaned up: Rather than doing 2* "sleep 2", it is now 1 "sleep 5". --- support-files/mysql.spec.sh | 110 +++++++++++++++++++++++++++++------- 1 file changed, 90 insertions(+), 20 deletions(-) diff --git a/support-files/mysql.spec.sh b/support-files/mysql.spec.sh index b4295027725..24e6660ba1c 100644 --- a/support-files/mysql.spec.sh +++ b/support-files/mysql.spec.sh @@ -30,7 +30,7 @@ %define mysqld_group mysql %define mysqldatadir /var/lib/mysql -%define release 1 +%define release 2 # # Macros we use which are not available in all supported versions of RPM @@ -266,7 +266,7 @@ Summary: MySQL: a very fast and reliable SQL database server Group: Applications/Databases Requires: %{distro_requires} Provides: msqlormysql mysql-server mysql MySQL MySQL-server -Obsoletes: MySQL mysql mysql-server MySQL-server +Obsoletes: MySQL mysql mysql-server MySQL-server MySQL-server-community %description -n MySQL-server%{product_suffix} The MySQL(TM) software delivers a very fast, multi-threaded, multi-user, @@ -296,7 +296,7 @@ package "MySQL-client%{product_suffix}" as well! %package -n MySQL-client%{product_suffix} Summary: MySQL - Client Group: Applications/Databases -Obsoletes: mysql-client MySQL-client +Obsoletes: mysql-client MySQL-client MySQL-client-community Provides: mysql-client MySQL-client %description -n MySQL-client%{product_suffix} @@ -310,7 +310,7 @@ Requires: MySQL-client%{product_suffix} perl Summary: MySQL - Test suite Group: Applications/Databases Provides: mysql-test -Obsoletes: mysql-bench mysql-test +Obsoletes: mysql-bench mysql-test MySQL-test-community AutoReqProv: no %description -n MySQL-test%{product_suffix} @@ -323,7 +323,7 @@ For a description of MySQL see the base MySQL RPM or http://www.mysql.com/ Summary: MySQL - Development header files and libraries Group: Applications/Databases Provides: mysql-devel -Obsoletes: mysql-devel +Obsoletes: mysql-devel MySQL-devel-community %description -n MySQL-devel%{product_suffix} This package contains the development header files and libraries necessary @@ -335,6 +335,7 @@ For a description of MySQL see the base MySQL RPM or http://www.mysql.com/ %package -n MySQL-shared%{product_suffix} Summary: MySQL - Shared libraries Group: Applications/Databases +Obsoletes: MySQL-shared-community %description -n MySQL-shared%{product_suffix} This package contains the shared libraries (*.so*) which certain languages @@ -345,7 +346,7 @@ and applications need to dynamically load and use MySQL. Summary: MySQL - embedded library Group: Applications/Databases Requires: MySQL-devel%{product_suffix} -Obsoletes: mysql-embedded +Obsoletes: mysql-embedded MySQL-embedded-community %description -n MySQL-embedded%{product_suffix} This package contains the MySQL server as an embedded library. @@ -521,6 +522,9 @@ rm -f $RBR%{_mandir}/man1/make_win_bin_dist.1* ############################################################################## %pre -n MySQL-server%{product_suffix} + +# ATTENTION: Parts of this are duplicated in the "triggerpostun" ! + mysql_datadir=%{mysqldatadir} # Check if we can safely upgrade. An upgrade is only safe if it's from one # of our RPMs in the same version family. @@ -669,6 +673,9 @@ if [ -x %{_sysconfdir}/init.d/mysql ] ; then fi %post -n MySQL-server%{product_suffix} + +# ATTENTION: Parts of this are duplicated in the "triggerpostun" ! + mysql_datadir=%{mysqldatadir} NEW_VERSION=%{mysql_version}-%{release} STATUS_FILE=$mysql_datadir/RPM_UPGRADE_MARKER @@ -697,12 +704,12 @@ if [ ! -d $mysql_datadir/test ] ; then mkdir $mysql_datadir/test; fi # ---------------------------------------------------------------------- # NOTE: This still needs to be debated. Should we check whether these links # for the other run levels exist(ed) before the upgrade? -# use insserv for older SuSE Linux versions -if [ -x /sbin/insserv ] ; then - /sbin/insserv %{_sysconfdir}/init.d/mysql # use chkconfig on Enterprise Linux and newer SuSE releases -elif [ -x /sbin/chkconfig ] ; then +if [ -x /sbin/chkconfig ] ; then /sbin/chkconfig --add mysql +# use insserv for older SuSE Linux versions +elif [ -x /sbin/insserv ] ; then + /sbin/insserv %{_sysconfdir}/init.d/mysql fi # ---------------------------------------------------------------------- @@ -783,12 +790,9 @@ if [ "$SERVER_TO_START" = "true" ] ; then # Restart in the same way that mysqld will be started normally. if [ -x %{_sysconfdir}/init.d/mysql ] ; then %{_sysconfdir}/init.d/mysql start - echo "Giving mysqld 2 seconds to start" - sleep 2 + echo "Giving mysqld 5 seconds to start" + sleep 5 fi - - # Allow mysqld_safe to start mysqld and print a message before we exit - sleep 2 fi # Collect an upgrade history ... @@ -797,7 +801,7 @@ echo >> $STATUS_FILE echo "=====" >> $STATUS_FILE STATUS_HISTORY=$mysql_datadir/RPM_UPGRADE_HISTORY cat $STATUS_FILE >> $STATUS_HISTORY -rm $STATUS_FILE +mv -f $STATUS_FILE ${STATUS_FILE}-LAST # for "triggerpostun" #echo "Thank you for installing the MySQL Community Server! For Production @@ -808,17 +812,26 @@ rm $STATUS_FILE %preun -n MySQL-server%{product_suffix} +# Which '$1' does this refer to? Fedora docs have info: +# " ... a count of the number of versions of the package that are installed. +# Action Count +# Install the first time 1 +# Upgrade 2 or higher (depending on the number of versions installed) +# Remove last version of package 0 " +# +# http://docs.fedoraproject.org/en-US/Fedora_Draft_Documentation/0.1/html/RPM_Guide/ch09s04s05.html + if [ $1 = 0 ] ; then # Stop MySQL before uninstalling it if [ -x %{_sysconfdir}/init.d/mysql ] ; then %{_sysconfdir}/init.d/mysql stop > /dev/null # Remove autostart of MySQL - # For older SuSE Linux versions - if [ -x /sbin/insserv ] ; then - /sbin/insserv -r %{_sysconfdir}/init.d/mysql # use chkconfig on Enterprise Linux and newer SuSE releases - elif [ -x /sbin/chkconfig ] ; then + if [ -x /sbin/chkconfig ] ; then /sbin/chkconfig --del mysql + # For older SuSE Linux versions + elif [ -x /sbin/insserv ] ; then + /sbin/insserv -r %{_sysconfdir}/init.d/mysql fi fi fi @@ -826,6 +839,56 @@ fi # We do not remove the mysql user since it may still own a lot of # database files. +%triggerpostun -n MySQL-server%{product_suffix} --MySQL-server-community + +# Setup: We renamed this package, so any existing "server-community" +# package will be removed when this "server" is installed. +# Problem: RPM will first run the "pre" and "post" sections of this script, +# and only then the "preun" of that old community server. +# But this "preun" includes stopping the server and uninstalling the service, +# "chkconfig --del mysql" which removes the symlinks to the start script. +# Solution: *After* the community server got removed, restart this server +# and re-install the service. +# +# For information about triggers in spec files, see the Fedora docs: +# http://docs.fedoraproject.org/en-US/Fedora_Draft_Documentation/0.1/html/RPM_Guide/ch10s02.html +# For all details of this code, see the "pre" and "post" sections. + +mysql_datadir=%{mysqldatadir} +NEW_VERSION=%{mysql_version}-%{release} +STATUS_FILE=$mysql_datadir/RPM_UPGRADE_MARKER-LAST # Note the difference! +STATUS_HISTORY=$mysql_datadir/RPM_UPGRADE_HISTORY + +if [ -f $STATUS_FILE ] ; then + SERVER_TO_START=`grep '^SERVER_TO_START=' $STATUS_FILE | cut -c17-` +else + # This should never happen, but let's be prepared + SERVER_TO_START='' +fi +echo "Analyzed: SERVER_TO_START=$SERVER_TO_START" + +if [ -x /sbin/chkconfig ] ; then + /sbin/chkconfig --add mysql +# use insserv for older SuSE Linux versions +elif [ -x /sbin/insserv ] ; then + /sbin/insserv %{_sysconfdir}/init.d/mysql +fi + +# Was the server running before the upgrade? If so, restart the new one. +if [ "$SERVER_TO_START" = "true" ] ; then + # Restart in the same way that mysqld will be started normally. + if [ -x %{_sysconfdir}/init.d/mysql ] ; then + %{_sysconfdir}/init.d/mysql start + echo "Giving mysqld 5 seconds to start" + sleep 5 + fi +fi + +echo "Trigger 'postun --community' finished at `date`" >> $STATUS_HISTORY +echo >> $STATUS_HISTORY +echo "=====" >> $STATUS_HISTORY + + # ---------------------------------------------------------------------- # Clean up the BuildRoot after build is done # ---------------------------------------------------------------------- @@ -1012,6 +1075,13 @@ fi # merging BK trees) ############################################################################## %changelog +* Wed Aug 11 2010 Joerg Bruehe + +- With a recent spec file cleanup, names have changed: A "-community" part was dropped. + Reflect that in the "Obsoletes" specifications. +- Add a "triggerpostun" to handle the uninstall of the "-community" server RPM. +- This fixes bug#55015 "MySQL server is not restarted properly after RPM upgrade". + * Tue Jun 15 2010 Joerg Bruehe - Change the behaviour on installation and upgrade: From ad264fa28700a0ed838ab762f861dc3b8b60eadd Mon Sep 17 00:00:00 2001 From: Alexander Nozdrin Date: Thu, 12 Aug 2010 16:51:46 +0400 Subject: [PATCH 123/129] Fix use of uninitialized variable. --- sql/sp_head.cc | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/sql/sp_head.cc b/sql/sp_head.cc index e94b005b9ba..a95bbe094c0 100644 --- a/sql/sp_head.cc +++ b/sql/sp_head.cc @@ -1743,7 +1743,7 @@ sp_head::execute_function(THD *thd, Item **argp, uint argcount, Field *return_value_fld) { ulonglong binlog_save_options; - bool need_binlog_call; + bool need_binlog_call= FALSE; uint arg_no; sp_rcontext *octx = thd->spcont; sp_rcontext *nctx = NULL; From 26f1efd981de6b298cda3c293e976ab55221c29a Mon Sep 17 00:00:00 2001 From: Marc Alff Date: Thu, 12 Aug 2010 08:08:52 -0600 Subject: [PATCH 124/129] Bug#55416 Renaming of performance_schema tables for 5.5 Removed table SETUP_OBJECTS. Renamed table PROCESSLIST to THREADS. Renamed table EVENTS_WAITS_SUMMARY_BY_EVENT_NAME to EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME. Adjusted Makefiles, code and tests accordingly. --- .../suite/perfschema/include/setup_helper.inc | 8 +- .../include/start_server_common.inc | 5 +- .../suite/perfschema/r/aggregate.result | 14 +- .../perfschema/r/ddl_ews_by_event_name.result | 7 - .../r/ddl_ews_global_by_event_name.result | 10 + .../perfschema/r/ddl_setup_objects.result | 7 - ..._processlist.result => ddl_threads.result} | 8 +- .../perfschema/r/dml_ews_by_event_name.result | 28 -- .../r/dml_ews_global_by_event_name.result | 28 ++ .../perfschema/r/dml_setup_objects.result | 35 --- ..._processlist.result => dml_threads.result} | 32 +- .../suite/perfschema/r/func_file_io.result | 8 +- .../perfschema/r/information_schema.result | 45 ++- mysql-test/suite/perfschema/r/misc.result | 2 +- .../suite/perfschema/r/no_threads.result | 4 +- .../suite/perfschema/r/pfs_upgrade.result | 95 +++--- mysql-test/suite/perfschema/r/schema.result | 49 ++- mysql-test/suite/perfschema/r/selects.result | 6 +- .../r/start_server_no_cond_class.result | 5 +- .../r/start_server_no_cond_inst.result | 5 +- .../r/start_server_no_file_class.result | 5 +- .../r/start_server_no_file_inst.result | 5 +- .../r/start_server_no_mutex_class.result | 5 +- .../r/start_server_no_mutex_inst.result | 5 +- .../r/start_server_no_rwlock_class.result | 5 +- .../r/start_server_no_rwlock_inst.result | 5 +- .../r/start_server_no_thread_class.result | 7 +- .../r/start_server_no_thread_inst.result | 7 +- .../perfschema/r/start_server_off.result | 5 +- .../suite/perfschema/r/start_server_on.result | 5 +- mysql-test/suite/perfschema/t/aggregate.test | 22 +- ...test => ddl_ews_global_by_event_name.test} | 11 +- .../suite/perfschema/t/ddl_setup_objects.test | 32 -- ...{ddl_processlist.test => ddl_threads.test} | 8 +- ...test => dml_ews_global_by_event_name.test} | 32 +- .../suite/perfschema/t/dml_setup_objects.test | 75 ----- ...{dml_processlist.test => dml_threads.test} | 32 +- .../suite/perfschema/t/func_file_io.test | 8 +- mysql-test/suite/perfschema/t/misc.test | 2 +- mysql-test/suite/perfschema/t/no_threads.test | 4 +- mysql-test/suite/perfschema/t/schema.test | 5 +- mysql-test/suite/perfschema/t/selects.test | 6 +- .../t/start_server_no_thread_class.test | 2 +- .../t/start_server_no_thread_inst.test | 2 +- .../suite/perfschema/t/thread_cache.test | 12 +- scripts/mysql_system_tables.sql | 94 +++--- storage/perfschema/CMakeLists.txt | 8 +- storage/perfschema/Makefile.am | 12 +- storage/perfschema/pfs_engine_table.cc | 9 +- .../perfschema/table_events_waits_summary.cc | 138 --------- .../perfschema/table_events_waits_summary.h | 52 ---- .../table_ews_global_by_event_name.cc | 166 +++++++++++ .../table_ews_global_by_event_name.h | 88 ++++++ storage/perfschema/table_setup_objects.cc | 281 ------------------ storage/perfschema/table_setup_objects.h | 125 -------- ...{table_processlist.cc => table_threads.cc} | 38 +-- .../{table_processlist.h => table_threads.h} | 22 +- 57 files changed, 598 insertions(+), 1143 deletions(-) delete mode 100644 mysql-test/suite/perfschema/r/ddl_ews_by_event_name.result create mode 100644 mysql-test/suite/perfschema/r/ddl_ews_global_by_event_name.result delete mode 100644 mysql-test/suite/perfschema/r/ddl_setup_objects.result rename mysql-test/suite/perfschema/r/{ddl_processlist.result => ddl_threads.result} (55%) delete mode 100644 mysql-test/suite/perfschema/r/dml_ews_by_event_name.result create mode 100644 mysql-test/suite/perfschema/r/dml_ews_global_by_event_name.result delete mode 100644 mysql-test/suite/perfschema/r/dml_setup_objects.result rename mysql-test/suite/perfschema/r/{dml_processlist.result => dml_threads.result} (54%) rename mysql-test/suite/perfschema/t/{ddl_ews_by_event_name.test => ddl_ews_global_by_event_name.test} (69%) delete mode 100644 mysql-test/suite/perfschema/t/ddl_setup_objects.test rename mysql-test/suite/perfschema/t/{ddl_processlist.test => ddl_threads.test} (78%) rename mysql-test/suite/perfschema/t/{dml_ews_by_event_name.test => dml_ews_global_by_event_name.test} (50%) delete mode 100644 mysql-test/suite/perfschema/t/dml_setup_objects.test rename mysql-test/suite/perfschema/t/{dml_processlist.test => dml_threads.test} (63%) create mode 100644 storage/perfschema/table_ews_global_by_event_name.cc create mode 100644 storage/perfschema/table_ews_global_by_event_name.h delete mode 100644 storage/perfschema/table_setup_objects.cc delete mode 100644 storage/perfschema/table_setup_objects.h rename storage/perfschema/{table_processlist.cc => table_threads.cc} (80%) rename storage/perfschema/{table_processlist.h => table_threads.h} (83%) diff --git a/mysql-test/suite/perfschema/include/setup_helper.inc b/mysql-test/suite/perfschema/include/setup_helper.inc index 8a2dfa86496..1c8d4e412d5 100644 --- a/mysql-test/suite/perfschema/include/setup_helper.inc +++ b/mysql-test/suite/perfschema/include/setup_helper.inc @@ -25,17 +25,17 @@ update performance_schema.SETUP_CONSUMERS set enabled='YES'; connect (con1, localhost, root, , ); -let $con1_THREAD_ID=`select thread_id from performance_schema.PROCESSLIST +let $con1_THREAD_ID=`select thread_id from performance_schema.THREADS where ID in (select connection_id())`; connect (con2, localhost, root, , ); -let $con2_THREAD_ID=`select thread_id from performance_schema.PROCESSLIST +let $con2_THREAD_ID=`select thread_id from performance_schema.THREADS where ID in (select connection_id())`; connect (con3, localhost, root, , ); -let $con3_THREAD_ID=`select thread_id from performance_schema.PROCESSLIST +let $con3_THREAD_ID=`select thread_id from performance_schema.THREADS where ID in (select connection_id())`; connection default; @@ -49,6 +49,6 @@ prepare stmt_dump_events from where thread_id=? order by event_id;"; prepare stmt_dump_thread from - "select name from performance_schema.PROCESSLIST where thread_id=? ;"; + "select name from performance_schema.THREADS where thread_id=? ;"; --enable_query_log diff --git a/mysql-test/suite/perfschema/include/start_server_common.inc b/mysql-test/suite/perfschema/include/start_server_common.inc index fa1cb953f59..083b302c5f7 100644 --- a/mysql-test/suite/perfschema/include/start_server_common.inc +++ b/mysql-test/suite/perfschema/include/start_server_common.inc @@ -29,20 +29,19 @@ select * from performance_schema.COND_INSTANCES; select * from performance_schema.EVENTS_WAITS_CURRENT; select * from performance_schema.EVENTS_WAITS_HISTORY; select * from performance_schema.EVENTS_WAITS_HISTORY_LONG; -select * from performance_schema.EVENTS_WAITS_SUMMARY_BY_EVENT_NAME; select * from performance_schema.EVENTS_WAITS_SUMMARY_BY_INSTANCE; select * from performance_schema.EVENTS_WAITS_SUMMARY_BY_THREAD_BY_EVENT_NAME; +select * from performance_schema.EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME; select * from performance_schema.FILE_INSTANCES; select * from performance_schema.FILE_SUMMARY_BY_EVENT_NAME; select * from performance_schema.FILE_SUMMARY_BY_INSTANCE; select * from performance_schema.MUTEX_INSTANCES; select * from performance_schema.PERFORMANCE_TIMERS; -select * from performance_schema.PROCESSLIST; select * from performance_schema.RWLOCK_INSTANCES; select * from performance_schema.SETUP_CONSUMERS; select * from performance_schema.SETUP_INSTRUMENTS; -select * from performance_schema.SETUP_OBJECTS; select * from performance_schema.SETUP_TIMERS; +select * from performance_schema.THREADS; --enable_result_log # This has a stable output, printing the result: diff --git a/mysql-test/suite/perfschema/r/aggregate.result b/mysql-test/suite/perfschema/r/aggregate.result index 197378ca38f..c7ac05ba69d 100644 --- a/mysql-test/suite/perfschema/r/aggregate.result +++ b/mysql-test/suite/perfschema/r/aggregate.result @@ -4,7 +4,7 @@ update performance_schema.SETUP_INSTRUMENTS set enabled = 'NO'; update performance_schema.SETUP_CONSUMERS set enabled = 'NO'; truncate table performance_schema.FILE_SUMMARY_BY_EVENT_NAME; truncate table performance_schema.FILE_SUMMARY_BY_INSTANCE; -truncate table performance_schema.EVENTS_WAITS_SUMMARY_BY_EVENT_NAME; +truncate table performance_schema.EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME; truncate table performance_schema.EVENTS_WAITS_SUMMARY_BY_INSTANCE; truncate table performance_schema.EVENTS_WAITS_SUMMARY_BY_THREAD_BY_EVENT_NAME; update performance_schema.SETUP_CONSUMERS set enabled = 'YES'; @@ -49,14 +49,14 @@ OR @dump_all; EVENT_NAME SUM_NUMBER_OF_BYTES_WRITE SUM(i.SUM_NUMBER_OF_BYTES_WRITE) "Verifying waits aggregate consistency (instance)" SELECT EVENT_NAME, e.SUM_TIMER_WAIT, SUM(i.SUM_TIMER_WAIT) -FROM performance_schema.EVENTS_WAITS_SUMMARY_BY_EVENT_NAME AS e +FROM performance_schema.EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME AS e JOIN performance_schema.EVENTS_WAITS_SUMMARY_BY_INSTANCE AS i USING (EVENT_NAME) GROUP BY EVENT_NAME HAVING (e.SUM_TIMER_WAIT < SUM(i.SUM_TIMER_WAIT)) OR @dump_all; EVENT_NAME SUM_TIMER_WAIT SUM(i.SUM_TIMER_WAIT) SELECT EVENT_NAME, e.MIN_TIMER_WAIT, MIN(i.MIN_TIMER_WAIT) -FROM performance_schema.EVENTS_WAITS_SUMMARY_BY_EVENT_NAME AS e +FROM performance_schema.EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME AS e JOIN performance_schema.EVENTS_WAITS_SUMMARY_BY_INSTANCE AS i USING (EVENT_NAME) GROUP BY EVENT_NAME HAVING (e.MIN_TIMER_WAIT > MIN(i.MIN_TIMER_WAIT)) @@ -64,7 +64,7 @@ AND (MIN(i.MIN_TIMER_WAIT) != 0) OR @dump_all; EVENT_NAME MIN_TIMER_WAIT MIN(i.MIN_TIMER_WAIT) SELECT EVENT_NAME, e.MAX_TIMER_WAIT, MAX(i.MAX_TIMER_WAIT) -FROM performance_schema.EVENTS_WAITS_SUMMARY_BY_EVENT_NAME AS e +FROM performance_schema.EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME AS e JOIN performance_schema.EVENTS_WAITS_SUMMARY_BY_INSTANCE AS i USING (EVENT_NAME) GROUP BY EVENT_NAME HAVING (e.MAX_TIMER_WAIT < MAX(i.MAX_TIMER_WAIT)) @@ -72,7 +72,7 @@ OR @dump_all; EVENT_NAME MAX_TIMER_WAIT MAX(i.MAX_TIMER_WAIT) "Verifying waits aggregate consistency (thread)" SELECT EVENT_NAME, e.SUM_TIMER_WAIT, SUM(t.SUM_TIMER_WAIT) -FROM performance_schema.EVENTS_WAITS_SUMMARY_BY_EVENT_NAME AS e +FROM performance_schema.EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME AS e JOIN performance_schema.EVENTS_WAITS_SUMMARY_BY_THREAD_BY_EVENT_NAME AS t USING (EVENT_NAME) GROUP BY EVENT_NAME @@ -80,7 +80,7 @@ HAVING (e.SUM_TIMER_WAIT < SUM(t.SUM_TIMER_WAIT)) OR @dump_all; EVENT_NAME SUM_TIMER_WAIT SUM(t.SUM_TIMER_WAIT) SELECT EVENT_NAME, e.MIN_TIMER_WAIT, MIN(t.MIN_TIMER_WAIT) -FROM performance_schema.EVENTS_WAITS_SUMMARY_BY_EVENT_NAME AS e +FROM performance_schema.EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME AS e JOIN performance_schema.EVENTS_WAITS_SUMMARY_BY_THREAD_BY_EVENT_NAME AS t USING (EVENT_NAME) GROUP BY EVENT_NAME @@ -89,7 +89,7 @@ AND (MIN(t.MIN_TIMER_WAIT) != 0) OR @dump_all; EVENT_NAME MIN_TIMER_WAIT MIN(t.MIN_TIMER_WAIT) SELECT EVENT_NAME, e.MAX_TIMER_WAIT, MAX(t.MAX_TIMER_WAIT) -FROM performance_schema.EVENTS_WAITS_SUMMARY_BY_EVENT_NAME AS e +FROM performance_schema.EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME AS e JOIN performance_schema.EVENTS_WAITS_SUMMARY_BY_THREAD_BY_EVENT_NAME AS t USING (EVENT_NAME) GROUP BY EVENT_NAME diff --git a/mysql-test/suite/perfschema/r/ddl_ews_by_event_name.result b/mysql-test/suite/perfschema/r/ddl_ews_by_event_name.result deleted file mode 100644 index 74fc4e1a640..00000000000 --- a/mysql-test/suite/perfschema/r/ddl_ews_by_event_name.result +++ /dev/null @@ -1,7 +0,0 @@ -alter table performance_schema.EVENTS_WAITS_SUMMARY_BY_EVENT_NAME add column foo integer; -ERROR 42000: Access denied for user 'root'@'localhost' to database 'performance_schema' -truncate table performance_schema.EVENTS_WAITS_SUMMARY_BY_EVENT_NAME; -ALTER TABLE performance_schema.EVENTS_WAITS_SUMMARY_BY_EVENT_NAME ADD INDEX test_index(EVENT_NAME); -ERROR 42000: Access denied for user 'root'@'localhost' to database 'performance_schema' -CREATE UNIQUE INDEX test_index ON performance_schema.EVENTS_WAITS_SUMMARY_BY_EVENT_NAME(EVENT_NAME); -ERROR 42000: Access denied for user 'root'@'localhost' to database 'performance_schema' diff --git a/mysql-test/suite/perfschema/r/ddl_ews_global_by_event_name.result b/mysql-test/suite/perfschema/r/ddl_ews_global_by_event_name.result new file mode 100644 index 00000000000..4f3ebcaea43 --- /dev/null +++ b/mysql-test/suite/perfschema/r/ddl_ews_global_by_event_name.result @@ -0,0 +1,10 @@ +alter table performance_schema.EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME +add column foo integer; +ERROR 42000: Access denied for user 'root'@'localhost' to database 'performance_schema' +truncate table performance_schema.EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME; +ALTER TABLE performance_schema.EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME +ADD INDEX test_index(EVENT_NAME); +ERROR 42000: Access denied for user 'root'@'localhost' to database 'performance_schema' +CREATE UNIQUE INDEX test_index +ON performance_schema.EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME(EVENT_NAME); +ERROR 42000: Access denied for user 'root'@'localhost' to database 'performance_schema' diff --git a/mysql-test/suite/perfschema/r/ddl_setup_objects.result b/mysql-test/suite/perfschema/r/ddl_setup_objects.result deleted file mode 100644 index c0f00745963..00000000000 --- a/mysql-test/suite/perfschema/r/ddl_setup_objects.result +++ /dev/null @@ -1,7 +0,0 @@ -alter table performance_schema.SETUP_OBJECTS add column foo integer; -ERROR 42000: Access denied for user 'root'@'localhost' to database 'performance_schema' -truncate table performance_schema.SETUP_OBJECTS; -ALTER TABLE performance_schema.SETUP_OBJECTS ADD INDEX test_index(OBJECT_NAME); -ERROR 42000: Access denied for user 'root'@'localhost' to database 'performance_schema' -CREATE UNIQUE INDEX test_index ON performance_schema.SETUP_OBJECTS(OBJECT_NAME); -ERROR 42000: Access denied for user 'root'@'localhost' to database 'performance_schema' diff --git a/mysql-test/suite/perfschema/r/ddl_processlist.result b/mysql-test/suite/perfschema/r/ddl_threads.result similarity index 55% rename from mysql-test/suite/perfschema/r/ddl_processlist.result rename to mysql-test/suite/perfschema/r/ddl_threads.result index 5a9eb766349..5d4b54d8bbe 100644 --- a/mysql-test/suite/perfschema/r/ddl_processlist.result +++ b/mysql-test/suite/perfschema/r/ddl_threads.result @@ -1,8 +1,8 @@ -alter table performance_schema.PROCESSLIST add column foo integer; +alter table performance_schema.THREADS add column foo integer; ERROR 42000: Access denied for user 'root'@'localhost' to database 'performance_schema' -truncate table performance_schema.PROCESSLIST; +truncate table performance_schema.THREADS; ERROR HY000: Invalid performance_schema usage. -ALTER TABLE performance_schema.PROCESSLIST ADD INDEX test_index(ID); +ALTER TABLE performance_schema.THREADS ADD INDEX test_index(ID); ERROR 42000: Access denied for user 'root'@'localhost' to database 'performance_schema' -CREATE UNIQUE INDEX test_index ON performance_schema.PROCESSLIST(ID); +CREATE UNIQUE INDEX test_index ON performance_schema.THREADS(ID); ERROR 42000: Access denied for user 'root'@'localhost' to database 'performance_schema' diff --git a/mysql-test/suite/perfschema/r/dml_ews_by_event_name.result b/mysql-test/suite/perfschema/r/dml_ews_by_event_name.result deleted file mode 100644 index 675fba021fe..00000000000 --- a/mysql-test/suite/perfschema/r/dml_ews_by_event_name.result +++ /dev/null @@ -1,28 +0,0 @@ -select * from performance_schema.EVENTS_WAITS_SUMMARY_BY_EVENT_NAME -where event_name like 'Wait/Synch/%' limit 1; -EVENT_NAME COUNT_STAR SUM_TIMER_WAIT MIN_TIMER_WAIT AVG_TIMER_WAIT MAX_TIMER_WAIT -# # # # # # -select * from performance_schema.EVENTS_WAITS_SUMMARY_BY_EVENT_NAME -where event_name='FOO'; -EVENT_NAME COUNT_STAR SUM_TIMER_WAIT MIN_TIMER_WAIT AVG_TIMER_WAIT MAX_TIMER_WAIT -insert into performance_schema.EVENTS_WAITS_SUMMARY_BY_EVENT_NAME -set event_name='FOO', count_star=1, sum_timer_wait=2, min_timer_wait=3, -avg_timer_wait=4, max_timer_wait=5; -ERROR 42000: INSERT command denied to user 'root'@'localhost' for table 'EVENTS_WAITS_SUMMARY_BY_EVENT_NAME' -update performance_schema.EVENTS_WAITS_SUMMARY_BY_EVENT_NAME -set count_star=12; -ERROR 42000: UPDATE command denied to user 'root'@'localhost' for table 'EVENTS_WAITS_SUMMARY_BY_EVENT_NAME' -update performance_schema.EVENTS_WAITS_SUMMARY_BY_EVENT_NAME -set count_star=12 where event_name like "FOO"; -ERROR 42000: UPDATE command denied to user 'root'@'localhost' for table 'EVENTS_WAITS_SUMMARY_BY_EVENT_NAME' -delete from performance_schema.EVENTS_WAITS_SUMMARY_BY_EVENT_NAME -where count_star=1; -ERROR 42000: DELETE command denied to user 'root'@'localhost' for table 'EVENTS_WAITS_SUMMARY_BY_EVENT_NAME' -delete from performance_schema.EVENTS_WAITS_SUMMARY_BY_EVENT_NAME; -ERROR 42000: DELETE command denied to user 'root'@'localhost' for table 'EVENTS_WAITS_SUMMARY_BY_EVENT_NAME' -LOCK TABLES performance_schema.EVENTS_WAITS_SUMMARY_BY_EVENT_NAME READ; -ERROR 42000: SELECT,LOCK TABL command denied to user 'root'@'localhost' for table 'EVENTS_WAITS_SUMMARY_BY_EVENT_NAME' -UNLOCK TABLES; -LOCK TABLES performance_schema.EVENTS_WAITS_SUMMARY_BY_EVENT_NAME WRITE; -ERROR 42000: SELECT,LOCK TABL command denied to user 'root'@'localhost' for table 'EVENTS_WAITS_SUMMARY_BY_EVENT_NAME' -UNLOCK TABLES; diff --git a/mysql-test/suite/perfschema/r/dml_ews_global_by_event_name.result b/mysql-test/suite/perfschema/r/dml_ews_global_by_event_name.result new file mode 100644 index 00000000000..64ede2fddac --- /dev/null +++ b/mysql-test/suite/perfschema/r/dml_ews_global_by_event_name.result @@ -0,0 +1,28 @@ +select * from performance_schema.EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME +where event_name like 'Wait/Synch/%' limit 1; +EVENT_NAME COUNT_STAR SUM_TIMER_WAIT MIN_TIMER_WAIT AVG_TIMER_WAIT MAX_TIMER_WAIT +# # # # # # +select * from performance_schema.EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME +where event_name='FOO'; +EVENT_NAME COUNT_STAR SUM_TIMER_WAIT MIN_TIMER_WAIT AVG_TIMER_WAIT MAX_TIMER_WAIT +insert into performance_schema.EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME +set event_name='FOO', count_star=1, sum_timer_wait=2, min_timer_wait=3, +avg_timer_wait=4, max_timer_wait=5; +ERROR 42000: INSERT command denied to user 'root'@'localhost' for table 'EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME' +update performance_schema.EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME +set count_star=12; +ERROR 42000: UPDATE command denied to user 'root'@'localhost' for table 'EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME' +update performance_schema.EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME +set count_star=12 where event_name like "FOO"; +ERROR 42000: UPDATE command denied to user 'root'@'localhost' for table 'EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME' +delete from performance_schema.EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME +where count_star=1; +ERROR 42000: DELETE command denied to user 'root'@'localhost' for table 'EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME' +delete from performance_schema.EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME; +ERROR 42000: DELETE command denied to user 'root'@'localhost' for table 'EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME' +LOCK TABLES performance_schema.EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME READ; +ERROR 42000: SELECT,LOCK TABL command denied to user 'root'@'localhost' for table 'EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME' +UNLOCK TABLES; +LOCK TABLES performance_schema.EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME WRITE; +ERROR 42000: SELECT,LOCK TABL command denied to user 'root'@'localhost' for table 'EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME' +UNLOCK TABLES; diff --git a/mysql-test/suite/perfschema/r/dml_setup_objects.result b/mysql-test/suite/perfschema/r/dml_setup_objects.result deleted file mode 100644 index a9d97357227..00000000000 --- a/mysql-test/suite/perfschema/r/dml_setup_objects.result +++ /dev/null @@ -1,35 +0,0 @@ -select * from performance_schema.SETUP_OBJECTS; -OBJECT_TYPE OBJECT_SCHEMA OBJECT_NAME ENABLED TIMED AGGREGATED -select * from performance_schema.SETUP_OBJECTS -where object_type = 'TABLE'; -OBJECT_TYPE OBJECT_SCHEMA OBJECT_NAME ENABLED TIMED AGGREGATED -select * from performance_schema.SETUP_OBJECTS -where enabled='YES'; -OBJECT_TYPE OBJECT_SCHEMA OBJECT_NAME ENABLED TIMED AGGREGATED -insert into performance_schema.SETUP_OBJECTS -set object_type='TABLE', object_schema='FOO', object_name='BAR', -enabled='YES', timed='YES', aggregated='YES'; -ERROR HY000: Table storage engine for 'SETUP_OBJECTS' doesn't have this option -update performance_schema.SETUP_OBJECTS -set object_type='TABLE'; -update performance_schema.SETUP_OBJECTS -set object_schema='ILLEGAL'; -update performance_schema.SETUP_OBJECTS -set object_name='ILLEGAL'; -update performance_schema.SETUP_OBJECTS -set enabled='NO'; -update performance_schema.SETUP_OBJECTS -set timed='NO'; -update performance_schema.SETUP_OBJECTS -set aggregated='NO'; -select * from performance_schema.SETUP_OBJECTS; -OBJECT_TYPE OBJECT_SCHEMA OBJECT_NAME ENABLED TIMED AGGREGATED -update performance_schema.SETUP_OBJECTS -set enabled='YES', timed='YES', aggregated='YES'; -delete from performance_schema.SETUP_OBJECTS -where object_type = 'TABLE'; -delete from performance_schema.SETUP_OBJECTS; -LOCK TABLES performance_schema.SETUP_OBJECTS READ; -UNLOCK TABLES; -LOCK TABLES performance_schema.SETUP_OBJECTS WRITE; -UNLOCK TABLES; diff --git a/mysql-test/suite/perfschema/r/dml_processlist.result b/mysql-test/suite/perfschema/r/dml_threads.result similarity index 54% rename from mysql-test/suite/perfschema/r/dml_processlist.result rename to mysql-test/suite/perfschema/r/dml_threads.result index ee0da5a7f1d..b4fa8705c95 100644 --- a/mysql-test/suite/perfschema/r/dml_processlist.result +++ b/mysql-test/suite/perfschema/r/dml_threads.result @@ -1,27 +1,27 @@ -select * from performance_schema.PROCESSLIST +select * from performance_schema.THREADS where name like 'Thread/%' limit 1; THREAD_ID ID NAME # # # -select * from performance_schema.PROCESSLIST +select * from performance_schema.THREADS where name='FOO'; THREAD_ID ID NAME -insert into performance_schema.PROCESSLIST +insert into performance_schema.THREADS set name='FOO', thread_id=1, id=2; -ERROR 42000: INSERT command denied to user 'root'@'localhost' for table 'PROCESSLIST' -update performance_schema.PROCESSLIST +ERROR 42000: INSERT command denied to user 'root'@'localhost' for table 'THREADS' +update performance_schema.THREADS set thread_id=12; -ERROR 42000: UPDATE command denied to user 'root'@'localhost' for table 'PROCESSLIST' -update performance_schema.PROCESSLIST +ERROR 42000: UPDATE command denied to user 'root'@'localhost' for table 'THREADS' +update performance_schema.THREADS set thread_id=12 where name like "FOO"; -ERROR 42000: UPDATE command denied to user 'root'@'localhost' for table 'PROCESSLIST' -delete from performance_schema.PROCESSLIST +ERROR 42000: UPDATE command denied to user 'root'@'localhost' for table 'THREADS' +delete from performance_schema.THREADS where id=1; -ERROR 42000: DELETE command denied to user 'root'@'localhost' for table 'PROCESSLIST' -delete from performance_schema.PROCESSLIST; -ERROR 42000: DELETE command denied to user 'root'@'localhost' for table 'PROCESSLIST' -LOCK TABLES performance_schema.PROCESSLIST READ; -ERROR 42000: SELECT,LOCK TABL command denied to user 'root'@'localhost' for table 'PROCESSLIST' +ERROR 42000: DELETE command denied to user 'root'@'localhost' for table 'THREADS' +delete from performance_schema.THREADS; +ERROR 42000: DELETE command denied to user 'root'@'localhost' for table 'THREADS' +LOCK TABLES performance_schema.THREADS READ; +ERROR 42000: SELECT,LOCK TABL command denied to user 'root'@'localhost' for table 'THREADS' UNLOCK TABLES; -LOCK TABLES performance_schema.PROCESSLIST WRITE; -ERROR 42000: SELECT,LOCK TABL command denied to user 'root'@'localhost' for table 'PROCESSLIST' +LOCK TABLES performance_schema.THREADS WRITE; +ERROR 42000: SELECT,LOCK TABL command denied to user 'root'@'localhost' for table 'THREADS' UNLOCK TABLES; diff --git a/mysql-test/suite/perfschema/r/func_file_io.result b/mysql-test/suite/perfschema/r/func_file_io.result index 69e6072fc22..201254aca21 100644 --- a/mysql-test/suite/perfschema/r/func_file_io.result +++ b/mysql-test/suite/perfschema/r/func_file_io.result @@ -90,27 +90,27 @@ SUM(SUM_NUMBER_OF_BYTES_WRITE) AS sum_num_bytes_write FROM performance_schema.FILE_SUMMARY_BY_INSTANCE WHERE FILE_NAME LIKE CONCAT('%', @@tmpdir, '%') ORDER BY NULL; SELECT EVENT_NAME, COUNT_STAR, AVG_TIMER_WAIT, SUM_TIMER_WAIT -FROM performance_schema.EVENTS_WAITS_SUMMARY_BY_EVENT_NAME +FROM performance_schema.EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME WHERE COUNT_STAR > 0 ORDER BY SUM_TIMER_WAIT DESC LIMIT 10; SELECT i.user, SUM(TIMER_WAIT) SUM_WAIT # ((TIME_TO_SEC(TIMEDIFF(NOW(), i.startup_time)) * 1000) / SUM(TIMER_WAIT)) * 100 WAIT_PERCENTAGE FROM performance_schema.EVENTS_WAITS_HISTORY_LONG h -INNER JOIN performance_schema.PROCESSLIST p USING (THREAD_ID) +INNER JOIN performance_schema.THREADS p USING (THREAD_ID) LEFT JOIN information_schema.PROCESSLIST i USING (ID) GROUP BY i.user ORDER BY SUM_WAIT DESC LIMIT 20; SELECT h.EVENT_NAME, SUM(h.TIMER_WAIT) TOTAL_WAIT FROM performance_schema.EVENTS_WAITS_HISTORY_LONG h -INNER JOIN performance_schema.PROCESSLIST p USING (THREAD_ID) +INNER JOIN performance_schema.THREADS p USING (THREAD_ID) WHERE p.ID = 1 GROUP BY h.EVENT_NAME HAVING TOTAL_WAIT > 0; SELECT i.user, h.operation, SUM(NUMBER_OF_BYTES) bytes FROM performance_schema.EVENTS_WAITS_HISTORY_LONG h -INNER JOIN performance_schema.PROCESSLIST p USING (THREAD_ID) +INNER JOIN performance_schema.THREADS p USING (THREAD_ID) LEFT JOIN information_schema.PROCESSLIST i USING (ID) GROUP BY i.user, h.operation HAVING BYTES > 0 diff --git a/mysql-test/suite/perfschema/r/information_schema.result b/mysql-test/suite/perfschema/r/information_schema.result index 86ebe80768c..8e7478564fb 100644 --- a/mysql-test/suite/perfschema/r/information_schema.result +++ b/mysql-test/suite/perfschema/r/information_schema.result @@ -6,20 +6,19 @@ performance_schema COND_INSTANCES def performance_schema EVENTS_WAITS_CURRENT def performance_schema EVENTS_WAITS_HISTORY def performance_schema EVENTS_WAITS_HISTORY_LONG def -performance_schema EVENTS_WAITS_SUMMARY_BY_EVENT_NAME def performance_schema EVENTS_WAITS_SUMMARY_BY_INSTANCE def performance_schema EVENTS_WAITS_SUMMARY_BY_THREAD_BY_EVENT_NAME def +performance_schema EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME def performance_schema FILE_INSTANCES def performance_schema FILE_SUMMARY_BY_EVENT_NAME def performance_schema FILE_SUMMARY_BY_INSTANCE def performance_schema MUTEX_INSTANCES def performance_schema PERFORMANCE_TIMERS def -performance_schema PROCESSLIST def performance_schema RWLOCK_INSTANCES def performance_schema SETUP_CONSUMERS def performance_schema SETUP_INSTRUMENTS def -performance_schema SETUP_OBJECTS def performance_schema SETUP_TIMERS def +performance_schema THREADS def select upper(TABLE_NAME), TABLE_TYPE, ENGINE from information_schema.tables where TABLE_SCHEMA='performance_schema'; @@ -28,20 +27,19 @@ COND_INSTANCES BASE TABLE PERFORMANCE_SCHEMA EVENTS_WAITS_CURRENT BASE TABLE PERFORMANCE_SCHEMA EVENTS_WAITS_HISTORY BASE TABLE PERFORMANCE_SCHEMA EVENTS_WAITS_HISTORY_LONG BASE TABLE PERFORMANCE_SCHEMA -EVENTS_WAITS_SUMMARY_BY_EVENT_NAME BASE TABLE PERFORMANCE_SCHEMA EVENTS_WAITS_SUMMARY_BY_INSTANCE BASE TABLE PERFORMANCE_SCHEMA EVENTS_WAITS_SUMMARY_BY_THREAD_BY_EVENT_NAME BASE TABLE PERFORMANCE_SCHEMA +EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME BASE TABLE PERFORMANCE_SCHEMA FILE_INSTANCES BASE TABLE PERFORMANCE_SCHEMA FILE_SUMMARY_BY_EVENT_NAME BASE TABLE PERFORMANCE_SCHEMA FILE_SUMMARY_BY_INSTANCE BASE TABLE PERFORMANCE_SCHEMA MUTEX_INSTANCES BASE TABLE PERFORMANCE_SCHEMA PERFORMANCE_TIMERS BASE TABLE PERFORMANCE_SCHEMA -PROCESSLIST BASE TABLE PERFORMANCE_SCHEMA RWLOCK_INSTANCES BASE TABLE PERFORMANCE_SCHEMA SETUP_CONSUMERS BASE TABLE PERFORMANCE_SCHEMA SETUP_INSTRUMENTS BASE TABLE PERFORMANCE_SCHEMA -SETUP_OBJECTS BASE TABLE PERFORMANCE_SCHEMA SETUP_TIMERS BASE TABLE PERFORMANCE_SCHEMA +THREADS BASE TABLE PERFORMANCE_SCHEMA select upper(TABLE_NAME), VERSION, ROW_FORMAT from information_schema.tables where TABLE_SCHEMA='performance_schema'; @@ -50,20 +48,19 @@ COND_INSTANCES 10 Dynamic EVENTS_WAITS_CURRENT 10 Dynamic EVENTS_WAITS_HISTORY 10 Dynamic EVENTS_WAITS_HISTORY_LONG 10 Dynamic -EVENTS_WAITS_SUMMARY_BY_EVENT_NAME 10 Dynamic EVENTS_WAITS_SUMMARY_BY_INSTANCE 10 Dynamic EVENTS_WAITS_SUMMARY_BY_THREAD_BY_EVENT_NAME 10 Dynamic +EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME 10 Dynamic FILE_INSTANCES 10 Dynamic FILE_SUMMARY_BY_EVENT_NAME 10 Dynamic FILE_SUMMARY_BY_INSTANCE 10 Dynamic MUTEX_INSTANCES 10 Dynamic PERFORMANCE_TIMERS 10 Fixed -PROCESSLIST 10 Dynamic RWLOCK_INSTANCES 10 Dynamic SETUP_CONSUMERS 10 Dynamic SETUP_INSTRUMENTS 10 Dynamic -SETUP_OBJECTS 10 Dynamic SETUP_TIMERS 10 Dynamic +THREADS 10 Dynamic select upper(TABLE_NAME), TABLE_ROWS, AVG_ROW_LENGTH from information_schema.tables where TABLE_SCHEMA='performance_schema'; @@ -72,20 +69,19 @@ COND_INSTANCES 1000 0 EVENTS_WAITS_CURRENT 1000 0 EVENTS_WAITS_HISTORY 1000 0 EVENTS_WAITS_HISTORY_LONG 10000 0 -EVENTS_WAITS_SUMMARY_BY_EVENT_NAME 1000 0 EVENTS_WAITS_SUMMARY_BY_INSTANCE 1000 0 EVENTS_WAITS_SUMMARY_BY_THREAD_BY_EVENT_NAME 1000 0 +EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME 1000 0 FILE_INSTANCES 1000 0 FILE_SUMMARY_BY_EVENT_NAME 1000 0 FILE_SUMMARY_BY_INSTANCE 1000 0 MUTEX_INSTANCES 1000 0 PERFORMANCE_TIMERS 5 0 -PROCESSLIST 1000 0 RWLOCK_INSTANCES 1000 0 SETUP_CONSUMERS 8 0 SETUP_INSTRUMENTS 1000 0 -SETUP_OBJECTS 1000 0 SETUP_TIMERS 1 0 +THREADS 1000 0 select upper(TABLE_NAME), DATA_LENGTH, MAX_DATA_LENGTH from information_schema.tables where TABLE_SCHEMA='performance_schema'; @@ -94,20 +90,19 @@ COND_INSTANCES 0 0 EVENTS_WAITS_CURRENT 0 0 EVENTS_WAITS_HISTORY 0 0 EVENTS_WAITS_HISTORY_LONG 0 0 -EVENTS_WAITS_SUMMARY_BY_EVENT_NAME 0 0 EVENTS_WAITS_SUMMARY_BY_INSTANCE 0 0 EVENTS_WAITS_SUMMARY_BY_THREAD_BY_EVENT_NAME 0 0 +EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME 0 0 FILE_INSTANCES 0 0 FILE_SUMMARY_BY_EVENT_NAME 0 0 FILE_SUMMARY_BY_INSTANCE 0 0 MUTEX_INSTANCES 0 0 PERFORMANCE_TIMERS 0 0 -PROCESSLIST 0 0 RWLOCK_INSTANCES 0 0 SETUP_CONSUMERS 0 0 SETUP_INSTRUMENTS 0 0 -SETUP_OBJECTS 0 0 SETUP_TIMERS 0 0 +THREADS 0 0 select upper(TABLE_NAME), INDEX_LENGTH, DATA_FREE, AUTO_INCREMENT from information_schema.tables where TABLE_SCHEMA='performance_schema'; @@ -116,20 +111,19 @@ COND_INSTANCES 0 0 NULL EVENTS_WAITS_CURRENT 0 0 NULL EVENTS_WAITS_HISTORY 0 0 NULL EVENTS_WAITS_HISTORY_LONG 0 0 NULL -EVENTS_WAITS_SUMMARY_BY_EVENT_NAME 0 0 NULL EVENTS_WAITS_SUMMARY_BY_INSTANCE 0 0 NULL EVENTS_WAITS_SUMMARY_BY_THREAD_BY_EVENT_NAME 0 0 NULL +EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME 0 0 NULL FILE_INSTANCES 0 0 NULL FILE_SUMMARY_BY_EVENT_NAME 0 0 NULL FILE_SUMMARY_BY_INSTANCE 0 0 NULL MUTEX_INSTANCES 0 0 NULL PERFORMANCE_TIMERS 0 0 NULL -PROCESSLIST 0 0 NULL RWLOCK_INSTANCES 0 0 NULL SETUP_CONSUMERS 0 0 NULL SETUP_INSTRUMENTS 0 0 NULL -SETUP_OBJECTS 0 0 NULL SETUP_TIMERS 0 0 NULL +THREADS 0 0 NULL select upper(TABLE_NAME), CREATE_TIME, UPDATE_TIME, CHECK_TIME from information_schema.tables where TABLE_SCHEMA='performance_schema'; @@ -138,20 +132,19 @@ COND_INSTANCES NULL NULL NULL EVENTS_WAITS_CURRENT NULL NULL NULL EVENTS_WAITS_HISTORY NULL NULL NULL EVENTS_WAITS_HISTORY_LONG NULL NULL NULL -EVENTS_WAITS_SUMMARY_BY_EVENT_NAME NULL NULL NULL EVENTS_WAITS_SUMMARY_BY_INSTANCE NULL NULL NULL EVENTS_WAITS_SUMMARY_BY_THREAD_BY_EVENT_NAME NULL NULL NULL +EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME NULL NULL NULL FILE_INSTANCES NULL NULL NULL FILE_SUMMARY_BY_EVENT_NAME NULL NULL NULL FILE_SUMMARY_BY_INSTANCE NULL NULL NULL MUTEX_INSTANCES NULL NULL NULL PERFORMANCE_TIMERS NULL NULL NULL -PROCESSLIST NULL NULL NULL RWLOCK_INSTANCES NULL NULL NULL SETUP_CONSUMERS NULL NULL NULL SETUP_INSTRUMENTS NULL NULL NULL -SETUP_OBJECTS NULL NULL NULL SETUP_TIMERS NULL NULL NULL +THREADS NULL NULL NULL select upper(TABLE_NAME), TABLE_COLLATION, CHECKSUM from information_schema.tables where TABLE_SCHEMA='performance_schema'; @@ -160,20 +153,19 @@ COND_INSTANCES utf8_general_ci NULL EVENTS_WAITS_CURRENT utf8_general_ci NULL EVENTS_WAITS_HISTORY utf8_general_ci NULL EVENTS_WAITS_HISTORY_LONG utf8_general_ci NULL -EVENTS_WAITS_SUMMARY_BY_EVENT_NAME utf8_general_ci NULL EVENTS_WAITS_SUMMARY_BY_INSTANCE utf8_general_ci NULL EVENTS_WAITS_SUMMARY_BY_THREAD_BY_EVENT_NAME utf8_general_ci NULL +EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME utf8_general_ci NULL FILE_INSTANCES utf8_general_ci NULL FILE_SUMMARY_BY_EVENT_NAME utf8_general_ci NULL FILE_SUMMARY_BY_INSTANCE utf8_general_ci NULL MUTEX_INSTANCES utf8_general_ci NULL PERFORMANCE_TIMERS utf8_general_ci NULL -PROCESSLIST utf8_general_ci NULL RWLOCK_INSTANCES utf8_general_ci NULL SETUP_CONSUMERS utf8_general_ci NULL SETUP_INSTRUMENTS utf8_general_ci NULL -SETUP_OBJECTS utf8_general_ci NULL SETUP_TIMERS utf8_general_ci NULL +THREADS utf8_general_ci NULL select upper(TABLE_NAME), TABLE_COMMENT from information_schema.tables where TABLE_SCHEMA='performance_schema'; @@ -182,17 +174,16 @@ COND_INSTANCES EVENTS_WAITS_CURRENT EVENTS_WAITS_HISTORY EVENTS_WAITS_HISTORY_LONG -EVENTS_WAITS_SUMMARY_BY_EVENT_NAME EVENTS_WAITS_SUMMARY_BY_INSTANCE EVENTS_WAITS_SUMMARY_BY_THREAD_BY_EVENT_NAME +EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME FILE_INSTANCES FILE_SUMMARY_BY_EVENT_NAME FILE_SUMMARY_BY_INSTANCE MUTEX_INSTANCES PERFORMANCE_TIMERS -PROCESSLIST RWLOCK_INSTANCES SETUP_CONSUMERS SETUP_INSTRUMENTS -SETUP_OBJECTS SETUP_TIMERS +THREADS diff --git a/mysql-test/suite/perfschema/r/misc.result b/mysql-test/suite/perfschema/r/misc.result index 00619595749..e389a4ce65c 100644 --- a/mysql-test/suite/perfschema/r/misc.result +++ b/mysql-test/suite/perfschema/r/misc.result @@ -1,6 +1,6 @@ SELECT EVENT_ID FROM performance_schema.EVENTS_WAITS_CURRENT WHERE THREAD_ID IN -(SELECT THREAD_ID FROM performance_schema.PROCESSLIST) +(SELECT THREAD_ID FROM performance_schema.THREADS) AND EVENT_NAME IN (SELECT NAME FROM performance_schema.SETUP_INSTRUMENTS WHERE NAME LIKE "wait/synch/%") diff --git a/mysql-test/suite/perfschema/r/no_threads.result b/mysql-test/suite/perfschema/r/no_threads.result index b38dc9fd733..79d16809eee 100644 --- a/mysql-test/suite/perfschema/r/no_threads.result +++ b/mysql-test/suite/perfschema/r/no_threads.result @@ -17,11 +17,11 @@ show variables like "performance_schema_max_thread%"; Variable_name Value performance_schema_max_thread_classes 50 performance_schema_max_thread_instances 10 -select count(*) from performance_schema.PROCESSLIST +select count(*) from performance_schema.THREADS where name like "thread/sql/main"; count(*) 1 -select count(*) from performance_schema.PROCESSLIST +select count(*) from performance_schema.THREADS where name like "thread/sql/OneConnection"; count(*) 0 diff --git a/mysql-test/suite/perfschema/r/pfs_upgrade.result b/mysql-test/suite/perfschema/r/pfs_upgrade.result index 2d0d82ef19c..31d12598357 100644 --- a/mysql-test/suite/perfschema/r/pfs_upgrade.result +++ b/mysql-test/suite/perfschema/r/pfs_upgrade.result @@ -12,21 +12,20 @@ ERROR 1050 (42S01) at line 183: Table 'COND_INSTANCES' already exists ERROR 1050 (42S01) at line 213: Table 'EVENTS_WAITS_CURRENT' already exists ERROR 1050 (42S01) at line 227: Table 'EVENTS_WAITS_HISTORY' already exists ERROR 1050 (42S01) at line 241: Table 'EVENTS_WAITS_HISTORY_LONG' already exists -ERROR 1050 (42S01) at line 261: Table 'EVENTS_WAITS_SUMMARY_BY_EVENT_NAME' already exists -ERROR 1050 (42S01) at line 282: Table 'EVENTS_WAITS_SUMMARY_BY_INSTANCE' already exists -ERROR 1050 (42S01) at line 303: Table 'EVENTS_WAITS_SUMMARY_BY_THREAD_BY_EVENT_NAME' already exists +ERROR 1050 (42S01) at line 262: Table 'EVENTS_WAITS_SUMMARY_BY_INSTANCE' already exists +ERROR 1050 (42S01) at line 283: Table 'EVENTS_WAITS_SUMMARY_BY_THREAD_BY_EVENT_NAME' already exists +ERROR 1050 (42S01) at line 303: Table 'EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME' already exists ERROR 1050 (42S01) at line 320: Table 'FILE_INSTANCES' already exists ERROR 1050 (42S01) at line 339: Table 'FILE_SUMMARY_BY_EVENT_NAME' already exists ERROR 1050 (42S01) at line 359: Table 'FILE_SUMMARY_BY_INSTANCE' already exists ERROR 1050 (42S01) at line 376: Table 'MUTEX_INSTANCES' already exists ERROR 1050 (42S01) at line 394: Table 'PERFORMANCE_TIMERS' already exists -ERROR 1050 (42S01) at line 411: Table 'PROCESSLIST' already exists -ERROR 1050 (42S01) at line 429: Table 'RWLOCK_INSTANCES' already exists -ERROR 1050 (42S01) at line 445: Table 'SETUP_CONSUMERS' already exists -ERROR 1050 (42S01) at line 462: Table 'SETUP_INSTRUMENTS' already exists -ERROR 1050 (42S01) at line 482: Table 'SETUP_OBJECTS' already exists -ERROR 1050 (42S01) at line 498: Table 'SETUP_TIMERS' already exists -ERROR 1644 (HY000) at line 1138: Unexpected content found in the performance_schema database. +ERROR 1050 (42S01) at line 412: Table 'RWLOCK_INSTANCES' already exists +ERROR 1050 (42S01) at line 428: Table 'SETUP_CONSUMERS' already exists +ERROR 1050 (42S01) at line 445: Table 'SETUP_INSTRUMENTS' already exists +ERROR 1050 (42S01) at line 461: Table 'SETUP_TIMERS' already exists +ERROR 1050 (42S01) at line 478: Table 'THREADS' already exists +ERROR 1644 (HY000) at line 1118: Unexpected content found in the performance_schema database. FATAL ERROR: Upgrade failed show tables like "user_table"; Tables_in_performance_schema (user_table) @@ -43,21 +42,20 @@ ERROR 1050 (42S01) at line 183: Table 'COND_INSTANCES' already exists ERROR 1050 (42S01) at line 213: Table 'EVENTS_WAITS_CURRENT' already exists ERROR 1050 (42S01) at line 227: Table 'EVENTS_WAITS_HISTORY' already exists ERROR 1050 (42S01) at line 241: Table 'EVENTS_WAITS_HISTORY_LONG' already exists -ERROR 1050 (42S01) at line 261: Table 'EVENTS_WAITS_SUMMARY_BY_EVENT_NAME' already exists -ERROR 1050 (42S01) at line 282: Table 'EVENTS_WAITS_SUMMARY_BY_INSTANCE' already exists -ERROR 1050 (42S01) at line 303: Table 'EVENTS_WAITS_SUMMARY_BY_THREAD_BY_EVENT_NAME' already exists +ERROR 1050 (42S01) at line 262: Table 'EVENTS_WAITS_SUMMARY_BY_INSTANCE' already exists +ERROR 1050 (42S01) at line 283: Table 'EVENTS_WAITS_SUMMARY_BY_THREAD_BY_EVENT_NAME' already exists +ERROR 1050 (42S01) at line 303: Table 'EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME' already exists ERROR 1050 (42S01) at line 320: Table 'FILE_INSTANCES' already exists ERROR 1050 (42S01) at line 339: Table 'FILE_SUMMARY_BY_EVENT_NAME' already exists ERROR 1050 (42S01) at line 359: Table 'FILE_SUMMARY_BY_INSTANCE' already exists ERROR 1050 (42S01) at line 376: Table 'MUTEX_INSTANCES' already exists ERROR 1050 (42S01) at line 394: Table 'PERFORMANCE_TIMERS' already exists -ERROR 1050 (42S01) at line 411: Table 'PROCESSLIST' already exists -ERROR 1050 (42S01) at line 429: Table 'RWLOCK_INSTANCES' already exists -ERROR 1050 (42S01) at line 445: Table 'SETUP_CONSUMERS' already exists -ERROR 1050 (42S01) at line 462: Table 'SETUP_INSTRUMENTS' already exists -ERROR 1050 (42S01) at line 482: Table 'SETUP_OBJECTS' already exists -ERROR 1050 (42S01) at line 498: Table 'SETUP_TIMERS' already exists -ERROR 1644 (HY000) at line 1138: Unexpected content found in the performance_schema database. +ERROR 1050 (42S01) at line 412: Table 'RWLOCK_INSTANCES' already exists +ERROR 1050 (42S01) at line 428: Table 'SETUP_CONSUMERS' already exists +ERROR 1050 (42S01) at line 445: Table 'SETUP_INSTRUMENTS' already exists +ERROR 1050 (42S01) at line 461: Table 'SETUP_TIMERS' already exists +ERROR 1050 (42S01) at line 478: Table 'THREADS' already exists +ERROR 1644 (HY000) at line 1118: Unexpected content found in the performance_schema database. FATAL ERROR: Upgrade failed show tables like "user_view"; Tables_in_performance_schema (user_view) @@ -72,21 +70,20 @@ ERROR 1050 (42S01) at line 183: Table 'COND_INSTANCES' already exists ERROR 1050 (42S01) at line 213: Table 'EVENTS_WAITS_CURRENT' already exists ERROR 1050 (42S01) at line 227: Table 'EVENTS_WAITS_HISTORY' already exists ERROR 1050 (42S01) at line 241: Table 'EVENTS_WAITS_HISTORY_LONG' already exists -ERROR 1050 (42S01) at line 261: Table 'EVENTS_WAITS_SUMMARY_BY_EVENT_NAME' already exists -ERROR 1050 (42S01) at line 282: Table 'EVENTS_WAITS_SUMMARY_BY_INSTANCE' already exists -ERROR 1050 (42S01) at line 303: Table 'EVENTS_WAITS_SUMMARY_BY_THREAD_BY_EVENT_NAME' already exists +ERROR 1050 (42S01) at line 262: Table 'EVENTS_WAITS_SUMMARY_BY_INSTANCE' already exists +ERROR 1050 (42S01) at line 283: Table 'EVENTS_WAITS_SUMMARY_BY_THREAD_BY_EVENT_NAME' already exists +ERROR 1050 (42S01) at line 303: Table 'EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME' already exists ERROR 1050 (42S01) at line 320: Table 'FILE_INSTANCES' already exists ERROR 1050 (42S01) at line 339: Table 'FILE_SUMMARY_BY_EVENT_NAME' already exists ERROR 1050 (42S01) at line 359: Table 'FILE_SUMMARY_BY_INSTANCE' already exists ERROR 1050 (42S01) at line 376: Table 'MUTEX_INSTANCES' already exists ERROR 1050 (42S01) at line 394: Table 'PERFORMANCE_TIMERS' already exists -ERROR 1050 (42S01) at line 411: Table 'PROCESSLIST' already exists -ERROR 1050 (42S01) at line 429: Table 'RWLOCK_INSTANCES' already exists -ERROR 1050 (42S01) at line 445: Table 'SETUP_CONSUMERS' already exists -ERROR 1050 (42S01) at line 462: Table 'SETUP_INSTRUMENTS' already exists -ERROR 1050 (42S01) at line 482: Table 'SETUP_OBJECTS' already exists -ERROR 1050 (42S01) at line 498: Table 'SETUP_TIMERS' already exists -ERROR 1644 (HY000) at line 1138: Unexpected content found in the performance_schema database. +ERROR 1050 (42S01) at line 412: Table 'RWLOCK_INSTANCES' already exists +ERROR 1050 (42S01) at line 428: Table 'SETUP_CONSUMERS' already exists +ERROR 1050 (42S01) at line 445: Table 'SETUP_INSTRUMENTS' already exists +ERROR 1050 (42S01) at line 461: Table 'SETUP_TIMERS' already exists +ERROR 1050 (42S01) at line 478: Table 'THREADS' already exists +ERROR 1644 (HY000) at line 1118: Unexpected content found in the performance_schema database. FATAL ERROR: Upgrade failed select name from mysql.proc where db='performance_schema'; name @@ -101,21 +98,20 @@ ERROR 1050 (42S01) at line 183: Table 'COND_INSTANCES' already exists ERROR 1050 (42S01) at line 213: Table 'EVENTS_WAITS_CURRENT' already exists ERROR 1050 (42S01) at line 227: Table 'EVENTS_WAITS_HISTORY' already exists ERROR 1050 (42S01) at line 241: Table 'EVENTS_WAITS_HISTORY_LONG' already exists -ERROR 1050 (42S01) at line 261: Table 'EVENTS_WAITS_SUMMARY_BY_EVENT_NAME' already exists -ERROR 1050 (42S01) at line 282: Table 'EVENTS_WAITS_SUMMARY_BY_INSTANCE' already exists -ERROR 1050 (42S01) at line 303: Table 'EVENTS_WAITS_SUMMARY_BY_THREAD_BY_EVENT_NAME' already exists +ERROR 1050 (42S01) at line 262: Table 'EVENTS_WAITS_SUMMARY_BY_INSTANCE' already exists +ERROR 1050 (42S01) at line 283: Table 'EVENTS_WAITS_SUMMARY_BY_THREAD_BY_EVENT_NAME' already exists +ERROR 1050 (42S01) at line 303: Table 'EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME' already exists ERROR 1050 (42S01) at line 320: Table 'FILE_INSTANCES' already exists ERROR 1050 (42S01) at line 339: Table 'FILE_SUMMARY_BY_EVENT_NAME' already exists ERROR 1050 (42S01) at line 359: Table 'FILE_SUMMARY_BY_INSTANCE' already exists ERROR 1050 (42S01) at line 376: Table 'MUTEX_INSTANCES' already exists ERROR 1050 (42S01) at line 394: Table 'PERFORMANCE_TIMERS' already exists -ERROR 1050 (42S01) at line 411: Table 'PROCESSLIST' already exists -ERROR 1050 (42S01) at line 429: Table 'RWLOCK_INSTANCES' already exists -ERROR 1050 (42S01) at line 445: Table 'SETUP_CONSUMERS' already exists -ERROR 1050 (42S01) at line 462: Table 'SETUP_INSTRUMENTS' already exists -ERROR 1050 (42S01) at line 482: Table 'SETUP_OBJECTS' already exists -ERROR 1050 (42S01) at line 498: Table 'SETUP_TIMERS' already exists -ERROR 1644 (HY000) at line 1138: Unexpected content found in the performance_schema database. +ERROR 1050 (42S01) at line 412: Table 'RWLOCK_INSTANCES' already exists +ERROR 1050 (42S01) at line 428: Table 'SETUP_CONSUMERS' already exists +ERROR 1050 (42S01) at line 445: Table 'SETUP_INSTRUMENTS' already exists +ERROR 1050 (42S01) at line 461: Table 'SETUP_TIMERS' already exists +ERROR 1050 (42S01) at line 478: Table 'THREADS' already exists +ERROR 1644 (HY000) at line 1118: Unexpected content found in the performance_schema database. FATAL ERROR: Upgrade failed select name from mysql.proc where db='performance_schema'; name @@ -130,21 +126,20 @@ ERROR 1050 (42S01) at line 183: Table 'COND_INSTANCES' already exists ERROR 1050 (42S01) at line 213: Table 'EVENTS_WAITS_CURRENT' already exists ERROR 1050 (42S01) at line 227: Table 'EVENTS_WAITS_HISTORY' already exists ERROR 1050 (42S01) at line 241: Table 'EVENTS_WAITS_HISTORY_LONG' already exists -ERROR 1050 (42S01) at line 261: Table 'EVENTS_WAITS_SUMMARY_BY_EVENT_NAME' already exists -ERROR 1050 (42S01) at line 282: Table 'EVENTS_WAITS_SUMMARY_BY_INSTANCE' already exists -ERROR 1050 (42S01) at line 303: Table 'EVENTS_WAITS_SUMMARY_BY_THREAD_BY_EVENT_NAME' already exists +ERROR 1050 (42S01) at line 262: Table 'EVENTS_WAITS_SUMMARY_BY_INSTANCE' already exists +ERROR 1050 (42S01) at line 283: Table 'EVENTS_WAITS_SUMMARY_BY_THREAD_BY_EVENT_NAME' already exists +ERROR 1050 (42S01) at line 303: Table 'EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME' already exists ERROR 1050 (42S01) at line 320: Table 'FILE_INSTANCES' already exists ERROR 1050 (42S01) at line 339: Table 'FILE_SUMMARY_BY_EVENT_NAME' already exists ERROR 1050 (42S01) at line 359: Table 'FILE_SUMMARY_BY_INSTANCE' already exists ERROR 1050 (42S01) at line 376: Table 'MUTEX_INSTANCES' already exists ERROR 1050 (42S01) at line 394: Table 'PERFORMANCE_TIMERS' already exists -ERROR 1050 (42S01) at line 411: Table 'PROCESSLIST' already exists -ERROR 1050 (42S01) at line 429: Table 'RWLOCK_INSTANCES' already exists -ERROR 1050 (42S01) at line 445: Table 'SETUP_CONSUMERS' already exists -ERROR 1050 (42S01) at line 462: Table 'SETUP_INSTRUMENTS' already exists -ERROR 1050 (42S01) at line 482: Table 'SETUP_OBJECTS' already exists -ERROR 1050 (42S01) at line 498: Table 'SETUP_TIMERS' already exists -ERROR 1644 (HY000) at line 1138: Unexpected content found in the performance_schema database. +ERROR 1050 (42S01) at line 412: Table 'RWLOCK_INSTANCES' already exists +ERROR 1050 (42S01) at line 428: Table 'SETUP_CONSUMERS' already exists +ERROR 1050 (42S01) at line 445: Table 'SETUP_INSTRUMENTS' already exists +ERROR 1050 (42S01) at line 461: Table 'SETUP_TIMERS' already exists +ERROR 1050 (42S01) at line 478: Table 'THREADS' already exists +ERROR 1644 (HY000) at line 1118: Unexpected content found in the performance_schema database. FATAL ERROR: Upgrade failed select name from mysql.event where db='performance_schema'; name diff --git a/mysql-test/suite/perfschema/r/schema.result b/mysql-test/suite/perfschema/r/schema.result index d402df70ed5..a802539b7e0 100644 --- a/mysql-test/suite/perfschema/r/schema.result +++ b/mysql-test/suite/perfschema/r/schema.result @@ -12,20 +12,19 @@ COND_INSTANCES EVENTS_WAITS_CURRENT EVENTS_WAITS_HISTORY EVENTS_WAITS_HISTORY_LONG -EVENTS_WAITS_SUMMARY_BY_EVENT_NAME EVENTS_WAITS_SUMMARY_BY_INSTANCE EVENTS_WAITS_SUMMARY_BY_THREAD_BY_EVENT_NAME +EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME FILE_INSTANCES FILE_SUMMARY_BY_EVENT_NAME FILE_SUMMARY_BY_INSTANCE MUTEX_INSTANCES PERFORMANCE_TIMERS -PROCESSLIST RWLOCK_INSTANCES SETUP_CONSUMERS SETUP_INSTRUMENTS -SETUP_OBJECTS SETUP_TIMERS +THREADS show create table COND_INSTANCES; Table Create Table COND_INSTANCES CREATE TABLE `COND_INSTANCES` ( @@ -92,16 +91,6 @@ EVENTS_WAITS_HISTORY_LONG CREATE TABLE `EVENTS_WAITS_HISTORY_LONG` ( `NUMBER_OF_BYTES` bigint(20) unsigned DEFAULT NULL, `FLAGS` int(10) unsigned DEFAULT NULL ) ENGINE=PERFORMANCE_SCHEMA DEFAULT CHARSET=utf8 -show create table EVENTS_WAITS_SUMMARY_BY_EVENT_NAME; -Table Create Table -EVENTS_WAITS_SUMMARY_BY_EVENT_NAME CREATE TABLE `EVENTS_WAITS_SUMMARY_BY_EVENT_NAME` ( - `EVENT_NAME` varchar(128) NOT NULL, - `COUNT_STAR` bigint(20) unsigned NOT NULL, - `SUM_TIMER_WAIT` bigint(20) unsigned NOT NULL, - `MIN_TIMER_WAIT` bigint(20) unsigned NOT NULL, - `AVG_TIMER_WAIT` bigint(20) unsigned NOT NULL, - `MAX_TIMER_WAIT` bigint(20) unsigned NOT NULL -) ENGINE=PERFORMANCE_SCHEMA DEFAULT CHARSET=utf8 show create table EVENTS_WAITS_SUMMARY_BY_INSTANCE; Table Create Table EVENTS_WAITS_SUMMARY_BY_INSTANCE CREATE TABLE `EVENTS_WAITS_SUMMARY_BY_INSTANCE` ( @@ -124,6 +113,16 @@ EVENTS_WAITS_SUMMARY_BY_THREAD_BY_EVENT_NAME CREATE TABLE `EVENTS_WAITS_SUMMARY_ `AVG_TIMER_WAIT` bigint(20) unsigned NOT NULL, `MAX_TIMER_WAIT` bigint(20) unsigned NOT NULL ) ENGINE=PERFORMANCE_SCHEMA DEFAULT CHARSET=utf8 +show create table EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME; +Table Create Table +EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME CREATE TABLE `EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME` ( + `EVENT_NAME` varchar(128) NOT NULL, + `COUNT_STAR` bigint(20) unsigned NOT NULL, + `SUM_TIMER_WAIT` bigint(20) unsigned NOT NULL, + `MIN_TIMER_WAIT` bigint(20) unsigned NOT NULL, + `AVG_TIMER_WAIT` bigint(20) unsigned NOT NULL, + `MAX_TIMER_WAIT` bigint(20) unsigned NOT NULL +) ENGINE=PERFORMANCE_SCHEMA DEFAULT CHARSET=utf8 show create table FILE_INSTANCES; Table Create Table FILE_INSTANCES CREATE TABLE `FILE_INSTANCES` ( @@ -165,13 +164,6 @@ PERFORMANCE_TIMERS CREATE TABLE `PERFORMANCE_TIMERS` ( `TIMER_RESOLUTION` bigint(20) DEFAULT NULL, `TIMER_OVERHEAD` bigint(20) DEFAULT NULL ) ENGINE=PERFORMANCE_SCHEMA DEFAULT CHARSET=utf8 -show create table PROCESSLIST; -Table Create Table -PROCESSLIST CREATE TABLE `PROCESSLIST` ( - `THREAD_ID` int(11) NOT NULL, - `ID` int(11) NOT NULL, - `NAME` varchar(64) NOT NULL -) ENGINE=PERFORMANCE_SCHEMA DEFAULT CHARSET=utf8 show create table RWLOCK_INSTANCES; Table Create Table RWLOCK_INSTANCES CREATE TABLE `RWLOCK_INSTANCES` ( @@ -193,19 +185,16 @@ SETUP_INSTRUMENTS CREATE TABLE `SETUP_INSTRUMENTS` ( `ENABLED` enum('YES','NO') NOT NULL, `TIMED` enum('YES','NO') NOT NULL ) ENGINE=PERFORMANCE_SCHEMA DEFAULT CHARSET=utf8 -show create table SETUP_OBJECTS; -Table Create Table -SETUP_OBJECTS CREATE TABLE `SETUP_OBJECTS` ( - `OBJECT_TYPE` varchar(64) DEFAULT NULL, - `OBJECT_SCHEMA` varchar(64) DEFAULT NULL, - `OBJECT_NAME` varchar(64) DEFAULT NULL, - `ENABLED` enum('YES','NO') NOT NULL, - `TIMED` enum('YES','NO') NOT NULL, - `AGGREGATED` enum('YES','NO') NOT NULL -) ENGINE=PERFORMANCE_SCHEMA DEFAULT CHARSET=utf8 show create table SETUP_TIMERS; Table Create Table SETUP_TIMERS CREATE TABLE `SETUP_TIMERS` ( `NAME` varchar(64) NOT NULL, `TIMER_NAME` enum('CYCLE','NANOSECOND','MICROSECOND','MILLISECOND','TICK') NOT NULL ) ENGINE=PERFORMANCE_SCHEMA DEFAULT CHARSET=utf8 +show create table THREADS; +Table Create Table +THREADS CREATE TABLE `THREADS` ( + `THREAD_ID` int(11) NOT NULL, + `ID` int(11) NOT NULL, + `NAME` varchar(64) NOT NULL +) ENGINE=PERFORMANCE_SCHEMA DEFAULT CHARSET=utf8 diff --git a/mysql-test/suite/perfschema/r/selects.result b/mysql-test/suite/perfschema/r/selects.result index 9b91c6f0fc8..dfc9007c740 100644 --- a/mysql-test/suite/perfschema/r/selects.result +++ b/mysql-test/suite/perfschema/r/selects.result @@ -13,7 +13,7 @@ OPERATION TOTAL chsize [NUM_BYTES] SELECT EVENT_ID FROM performance_schema.EVENTS_WAITS_CURRENT WHERE THREAD_ID IN -(SELECT THREAD_ID FROM performance_schema.PROCESSLIST) +(SELECT THREAD_ID FROM performance_schema.THREADS) AND EVENT_NAME IN (SELECT NAME FROM performance_schema.SETUP_INSTRUMENTS WHERE NAME LIKE "wait/synch/%") @@ -86,7 +86,7 @@ DROP TRIGGER t_ps_trigger; DROP PROCEDURE IF EXISTS t_ps_proc; CREATE PROCEDURE t_ps_proc(IN tid INT, OUT pid INT) BEGIN -SELECT id FROM performance_schema.PROCESSLIST +SELECT id FROM performance_schema.THREADS WHERE THREAD_ID = tid INTO pid; END; | @@ -94,7 +94,7 @@ CALL t_ps_proc(0, @p_id); DROP FUNCTION IF EXISTS t_ps_proc; CREATE FUNCTION t_ps_func(tid INT) RETURNS int BEGIN -return (SELECT id FROM performance_schema.PROCESSLIST +return (SELECT id FROM performance_schema.THREADS WHERE THREAD_ID = tid); END; | diff --git a/mysql-test/suite/perfschema/r/start_server_no_cond_class.result b/mysql-test/suite/perfschema/r/start_server_no_cond_class.result index d6089139d5a..48891adce73 100644 --- a/mysql-test/suite/perfschema/r/start_server_no_cond_class.result +++ b/mysql-test/suite/perfschema/r/start_server_no_cond_class.result @@ -21,20 +21,19 @@ select * from performance_schema.COND_INSTANCES; select * from performance_schema.EVENTS_WAITS_CURRENT; select * from performance_schema.EVENTS_WAITS_HISTORY; select * from performance_schema.EVENTS_WAITS_HISTORY_LONG; -select * from performance_schema.EVENTS_WAITS_SUMMARY_BY_EVENT_NAME; select * from performance_schema.EVENTS_WAITS_SUMMARY_BY_INSTANCE; select * from performance_schema.EVENTS_WAITS_SUMMARY_BY_THREAD_BY_EVENT_NAME; +select * from performance_schema.EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME; select * from performance_schema.FILE_INSTANCES; select * from performance_schema.FILE_SUMMARY_BY_EVENT_NAME; select * from performance_schema.FILE_SUMMARY_BY_INSTANCE; select * from performance_schema.MUTEX_INSTANCES; select * from performance_schema.PERFORMANCE_TIMERS; -select * from performance_schema.PROCESSLIST; select * from performance_schema.RWLOCK_INSTANCES; select * from performance_schema.SETUP_CONSUMERS; select * from performance_schema.SETUP_INSTRUMENTS; -select * from performance_schema.SETUP_OBJECTS; select * from performance_schema.SETUP_TIMERS; +select * from performance_schema.THREADS; show variables like "performance_schema%"; Variable_name Value performance_schema ON diff --git a/mysql-test/suite/perfschema/r/start_server_no_cond_inst.result b/mysql-test/suite/perfschema/r/start_server_no_cond_inst.result index eaa04c7629d..cb1d64bf1e7 100644 --- a/mysql-test/suite/perfschema/r/start_server_no_cond_inst.result +++ b/mysql-test/suite/perfschema/r/start_server_no_cond_inst.result @@ -21,20 +21,19 @@ select * from performance_schema.COND_INSTANCES; select * from performance_schema.EVENTS_WAITS_CURRENT; select * from performance_schema.EVENTS_WAITS_HISTORY; select * from performance_schema.EVENTS_WAITS_HISTORY_LONG; -select * from performance_schema.EVENTS_WAITS_SUMMARY_BY_EVENT_NAME; select * from performance_schema.EVENTS_WAITS_SUMMARY_BY_INSTANCE; select * from performance_schema.EVENTS_WAITS_SUMMARY_BY_THREAD_BY_EVENT_NAME; +select * from performance_schema.EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME; select * from performance_schema.FILE_INSTANCES; select * from performance_schema.FILE_SUMMARY_BY_EVENT_NAME; select * from performance_schema.FILE_SUMMARY_BY_INSTANCE; select * from performance_schema.MUTEX_INSTANCES; select * from performance_schema.PERFORMANCE_TIMERS; -select * from performance_schema.PROCESSLIST; select * from performance_schema.RWLOCK_INSTANCES; select * from performance_schema.SETUP_CONSUMERS; select * from performance_schema.SETUP_INSTRUMENTS; -select * from performance_schema.SETUP_OBJECTS; select * from performance_schema.SETUP_TIMERS; +select * from performance_schema.THREADS; show variables like "performance_schema%"; Variable_name Value performance_schema ON diff --git a/mysql-test/suite/perfschema/r/start_server_no_file_class.result b/mysql-test/suite/perfschema/r/start_server_no_file_class.result index d68ec00a456..3856d241d73 100644 --- a/mysql-test/suite/perfschema/r/start_server_no_file_class.result +++ b/mysql-test/suite/perfschema/r/start_server_no_file_class.result @@ -21,20 +21,19 @@ select * from performance_schema.COND_INSTANCES; select * from performance_schema.EVENTS_WAITS_CURRENT; select * from performance_schema.EVENTS_WAITS_HISTORY; select * from performance_schema.EVENTS_WAITS_HISTORY_LONG; -select * from performance_schema.EVENTS_WAITS_SUMMARY_BY_EVENT_NAME; select * from performance_schema.EVENTS_WAITS_SUMMARY_BY_INSTANCE; select * from performance_schema.EVENTS_WAITS_SUMMARY_BY_THREAD_BY_EVENT_NAME; +select * from performance_schema.EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME; select * from performance_schema.FILE_INSTANCES; select * from performance_schema.FILE_SUMMARY_BY_EVENT_NAME; select * from performance_schema.FILE_SUMMARY_BY_INSTANCE; select * from performance_schema.MUTEX_INSTANCES; select * from performance_schema.PERFORMANCE_TIMERS; -select * from performance_schema.PROCESSLIST; select * from performance_schema.RWLOCK_INSTANCES; select * from performance_schema.SETUP_CONSUMERS; select * from performance_schema.SETUP_INSTRUMENTS; -select * from performance_schema.SETUP_OBJECTS; select * from performance_schema.SETUP_TIMERS; +select * from performance_schema.THREADS; show variables like "performance_schema%"; Variable_name Value performance_schema ON diff --git a/mysql-test/suite/perfschema/r/start_server_no_file_inst.result b/mysql-test/suite/perfschema/r/start_server_no_file_inst.result index 258712ebf68..e52f04cbae7 100644 --- a/mysql-test/suite/perfschema/r/start_server_no_file_inst.result +++ b/mysql-test/suite/perfschema/r/start_server_no_file_inst.result @@ -21,20 +21,19 @@ select * from performance_schema.COND_INSTANCES; select * from performance_schema.EVENTS_WAITS_CURRENT; select * from performance_schema.EVENTS_WAITS_HISTORY; select * from performance_schema.EVENTS_WAITS_HISTORY_LONG; -select * from performance_schema.EVENTS_WAITS_SUMMARY_BY_EVENT_NAME; select * from performance_schema.EVENTS_WAITS_SUMMARY_BY_INSTANCE; select * from performance_schema.EVENTS_WAITS_SUMMARY_BY_THREAD_BY_EVENT_NAME; +select * from performance_schema.EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME; select * from performance_schema.FILE_INSTANCES; select * from performance_schema.FILE_SUMMARY_BY_EVENT_NAME; select * from performance_schema.FILE_SUMMARY_BY_INSTANCE; select * from performance_schema.MUTEX_INSTANCES; select * from performance_schema.PERFORMANCE_TIMERS; -select * from performance_schema.PROCESSLIST; select * from performance_schema.RWLOCK_INSTANCES; select * from performance_schema.SETUP_CONSUMERS; select * from performance_schema.SETUP_INSTRUMENTS; -select * from performance_schema.SETUP_OBJECTS; select * from performance_schema.SETUP_TIMERS; +select * from performance_schema.THREADS; show variables like "performance_schema%"; Variable_name Value performance_schema ON diff --git a/mysql-test/suite/perfschema/r/start_server_no_mutex_class.result b/mysql-test/suite/perfschema/r/start_server_no_mutex_class.result index d221cb2c22a..aab39dfb619 100644 --- a/mysql-test/suite/perfschema/r/start_server_no_mutex_class.result +++ b/mysql-test/suite/perfschema/r/start_server_no_mutex_class.result @@ -21,20 +21,19 @@ select * from performance_schema.COND_INSTANCES; select * from performance_schema.EVENTS_WAITS_CURRENT; select * from performance_schema.EVENTS_WAITS_HISTORY; select * from performance_schema.EVENTS_WAITS_HISTORY_LONG; -select * from performance_schema.EVENTS_WAITS_SUMMARY_BY_EVENT_NAME; select * from performance_schema.EVENTS_WAITS_SUMMARY_BY_INSTANCE; select * from performance_schema.EVENTS_WAITS_SUMMARY_BY_THREAD_BY_EVENT_NAME; +select * from performance_schema.EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME; select * from performance_schema.FILE_INSTANCES; select * from performance_schema.FILE_SUMMARY_BY_EVENT_NAME; select * from performance_schema.FILE_SUMMARY_BY_INSTANCE; select * from performance_schema.MUTEX_INSTANCES; select * from performance_schema.PERFORMANCE_TIMERS; -select * from performance_schema.PROCESSLIST; select * from performance_schema.RWLOCK_INSTANCES; select * from performance_schema.SETUP_CONSUMERS; select * from performance_schema.SETUP_INSTRUMENTS; -select * from performance_schema.SETUP_OBJECTS; select * from performance_schema.SETUP_TIMERS; +select * from performance_schema.THREADS; show variables like "performance_schema%"; Variable_name Value performance_schema ON diff --git a/mysql-test/suite/perfschema/r/start_server_no_mutex_inst.result b/mysql-test/suite/perfschema/r/start_server_no_mutex_inst.result index adfd4c5ec17..0665058a469 100644 --- a/mysql-test/suite/perfschema/r/start_server_no_mutex_inst.result +++ b/mysql-test/suite/perfschema/r/start_server_no_mutex_inst.result @@ -21,20 +21,19 @@ select * from performance_schema.COND_INSTANCES; select * from performance_schema.EVENTS_WAITS_CURRENT; select * from performance_schema.EVENTS_WAITS_HISTORY; select * from performance_schema.EVENTS_WAITS_HISTORY_LONG; -select * from performance_schema.EVENTS_WAITS_SUMMARY_BY_EVENT_NAME; select * from performance_schema.EVENTS_WAITS_SUMMARY_BY_INSTANCE; select * from performance_schema.EVENTS_WAITS_SUMMARY_BY_THREAD_BY_EVENT_NAME; +select * from performance_schema.EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME; select * from performance_schema.FILE_INSTANCES; select * from performance_schema.FILE_SUMMARY_BY_EVENT_NAME; select * from performance_schema.FILE_SUMMARY_BY_INSTANCE; select * from performance_schema.MUTEX_INSTANCES; select * from performance_schema.PERFORMANCE_TIMERS; -select * from performance_schema.PROCESSLIST; select * from performance_schema.RWLOCK_INSTANCES; select * from performance_schema.SETUP_CONSUMERS; select * from performance_schema.SETUP_INSTRUMENTS; -select * from performance_schema.SETUP_OBJECTS; select * from performance_schema.SETUP_TIMERS; +select * from performance_schema.THREADS; show variables like "performance_schema%"; Variable_name Value performance_schema ON diff --git a/mysql-test/suite/perfschema/r/start_server_no_rwlock_class.result b/mysql-test/suite/perfschema/r/start_server_no_rwlock_class.result index 5248becf0e5..721f9957b1e 100644 --- a/mysql-test/suite/perfschema/r/start_server_no_rwlock_class.result +++ b/mysql-test/suite/perfschema/r/start_server_no_rwlock_class.result @@ -21,20 +21,19 @@ select * from performance_schema.COND_INSTANCES; select * from performance_schema.EVENTS_WAITS_CURRENT; select * from performance_schema.EVENTS_WAITS_HISTORY; select * from performance_schema.EVENTS_WAITS_HISTORY_LONG; -select * from performance_schema.EVENTS_WAITS_SUMMARY_BY_EVENT_NAME; select * from performance_schema.EVENTS_WAITS_SUMMARY_BY_INSTANCE; select * from performance_schema.EVENTS_WAITS_SUMMARY_BY_THREAD_BY_EVENT_NAME; +select * from performance_schema.EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME; select * from performance_schema.FILE_INSTANCES; select * from performance_schema.FILE_SUMMARY_BY_EVENT_NAME; select * from performance_schema.FILE_SUMMARY_BY_INSTANCE; select * from performance_schema.MUTEX_INSTANCES; select * from performance_schema.PERFORMANCE_TIMERS; -select * from performance_schema.PROCESSLIST; select * from performance_schema.RWLOCK_INSTANCES; select * from performance_schema.SETUP_CONSUMERS; select * from performance_schema.SETUP_INSTRUMENTS; -select * from performance_schema.SETUP_OBJECTS; select * from performance_schema.SETUP_TIMERS; +select * from performance_schema.THREADS; show variables like "performance_schema%"; Variable_name Value performance_schema ON diff --git a/mysql-test/suite/perfschema/r/start_server_no_rwlock_inst.result b/mysql-test/suite/perfschema/r/start_server_no_rwlock_inst.result index e7a94c4a60d..63398bce1f5 100644 --- a/mysql-test/suite/perfschema/r/start_server_no_rwlock_inst.result +++ b/mysql-test/suite/perfschema/r/start_server_no_rwlock_inst.result @@ -21,20 +21,19 @@ select * from performance_schema.COND_INSTANCES; select * from performance_schema.EVENTS_WAITS_CURRENT; select * from performance_schema.EVENTS_WAITS_HISTORY; select * from performance_schema.EVENTS_WAITS_HISTORY_LONG; -select * from performance_schema.EVENTS_WAITS_SUMMARY_BY_EVENT_NAME; select * from performance_schema.EVENTS_WAITS_SUMMARY_BY_INSTANCE; select * from performance_schema.EVENTS_WAITS_SUMMARY_BY_THREAD_BY_EVENT_NAME; +select * from performance_schema.EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME; select * from performance_schema.FILE_INSTANCES; select * from performance_schema.FILE_SUMMARY_BY_EVENT_NAME; select * from performance_schema.FILE_SUMMARY_BY_INSTANCE; select * from performance_schema.MUTEX_INSTANCES; select * from performance_schema.PERFORMANCE_TIMERS; -select * from performance_schema.PROCESSLIST; select * from performance_schema.RWLOCK_INSTANCES; select * from performance_schema.SETUP_CONSUMERS; select * from performance_schema.SETUP_INSTRUMENTS; -select * from performance_schema.SETUP_OBJECTS; select * from performance_schema.SETUP_TIMERS; +select * from performance_schema.THREADS; show variables like "performance_schema%"; Variable_name Value performance_schema ON diff --git a/mysql-test/suite/perfschema/r/start_server_no_thread_class.result b/mysql-test/suite/perfschema/r/start_server_no_thread_class.result index 92f1ec29b38..006f0fc6002 100644 --- a/mysql-test/suite/perfschema/r/start_server_no_thread_class.result +++ b/mysql-test/suite/perfschema/r/start_server_no_thread_class.result @@ -21,20 +21,19 @@ select * from performance_schema.COND_INSTANCES; select * from performance_schema.EVENTS_WAITS_CURRENT; select * from performance_schema.EVENTS_WAITS_HISTORY; select * from performance_schema.EVENTS_WAITS_HISTORY_LONG; -select * from performance_schema.EVENTS_WAITS_SUMMARY_BY_EVENT_NAME; select * from performance_schema.EVENTS_WAITS_SUMMARY_BY_INSTANCE; select * from performance_schema.EVENTS_WAITS_SUMMARY_BY_THREAD_BY_EVENT_NAME; +select * from performance_schema.EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME; select * from performance_schema.FILE_INSTANCES; select * from performance_schema.FILE_SUMMARY_BY_EVENT_NAME; select * from performance_schema.FILE_SUMMARY_BY_INSTANCE; select * from performance_schema.MUTEX_INSTANCES; select * from performance_schema.PERFORMANCE_TIMERS; -select * from performance_schema.PROCESSLIST; select * from performance_schema.RWLOCK_INSTANCES; select * from performance_schema.SETUP_CONSUMERS; select * from performance_schema.SETUP_INSTRUMENTS; -select * from performance_schema.SETUP_OBJECTS; select * from performance_schema.SETUP_TIMERS; +select * from performance_schema.THREADS; show variables like "performance_schema%"; Variable_name Value performance_schema ON @@ -66,7 +65,7 @@ select variable_value > 0 from information_schema.global_status where variable_name like 'PERFORMANCE_SCHEMA_THREAD_CLASSES_LOST'; variable_value > 0 1 -select count(*) from performance_schema.PROCESSLIST; +select count(*) from performance_schema.THREADS; count(*) 0 show status like "performance_schema_thread_instances_lost"; diff --git a/mysql-test/suite/perfschema/r/start_server_no_thread_inst.result b/mysql-test/suite/perfschema/r/start_server_no_thread_inst.result index 3ecf7fe98db..e0377e10583 100644 --- a/mysql-test/suite/perfschema/r/start_server_no_thread_inst.result +++ b/mysql-test/suite/perfschema/r/start_server_no_thread_inst.result @@ -21,20 +21,19 @@ select * from performance_schema.COND_INSTANCES; select * from performance_schema.EVENTS_WAITS_CURRENT; select * from performance_schema.EVENTS_WAITS_HISTORY; select * from performance_schema.EVENTS_WAITS_HISTORY_LONG; -select * from performance_schema.EVENTS_WAITS_SUMMARY_BY_EVENT_NAME; select * from performance_schema.EVENTS_WAITS_SUMMARY_BY_INSTANCE; select * from performance_schema.EVENTS_WAITS_SUMMARY_BY_THREAD_BY_EVENT_NAME; +select * from performance_schema.EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME; select * from performance_schema.FILE_INSTANCES; select * from performance_schema.FILE_SUMMARY_BY_EVENT_NAME; select * from performance_schema.FILE_SUMMARY_BY_INSTANCE; select * from performance_schema.MUTEX_INSTANCES; select * from performance_schema.PERFORMANCE_TIMERS; -select * from performance_schema.PROCESSLIST; select * from performance_schema.RWLOCK_INSTANCES; select * from performance_schema.SETUP_CONSUMERS; select * from performance_schema.SETUP_INSTRUMENTS; -select * from performance_schema.SETUP_OBJECTS; select * from performance_schema.SETUP_TIMERS; +select * from performance_schema.THREADS; show variables like "performance_schema%"; Variable_name Value performance_schema ON @@ -64,7 +63,7 @@ Performance_schema_thread_classes_lost 0 show variables like "performance_schema_max_thread_instances"; Variable_name Value performance_schema_max_thread_instances 0 -select count(*) from performance_schema.PROCESSLIST; +select count(*) from performance_schema.THREADS; count(*) 0 select variable_value > 0 from information_schema.global_status diff --git a/mysql-test/suite/perfschema/r/start_server_off.result b/mysql-test/suite/perfschema/r/start_server_off.result index 4ce5aa75ce7..5f72cb4eba1 100644 --- a/mysql-test/suite/perfschema/r/start_server_off.result +++ b/mysql-test/suite/perfschema/r/start_server_off.result @@ -21,20 +21,19 @@ select * from performance_schema.COND_INSTANCES; select * from performance_schema.EVENTS_WAITS_CURRENT; select * from performance_schema.EVENTS_WAITS_HISTORY; select * from performance_schema.EVENTS_WAITS_HISTORY_LONG; -select * from performance_schema.EVENTS_WAITS_SUMMARY_BY_EVENT_NAME; select * from performance_schema.EVENTS_WAITS_SUMMARY_BY_INSTANCE; select * from performance_schema.EVENTS_WAITS_SUMMARY_BY_THREAD_BY_EVENT_NAME; +select * from performance_schema.EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME; select * from performance_schema.FILE_INSTANCES; select * from performance_schema.FILE_SUMMARY_BY_EVENT_NAME; select * from performance_schema.FILE_SUMMARY_BY_INSTANCE; select * from performance_schema.MUTEX_INSTANCES; select * from performance_schema.PERFORMANCE_TIMERS; -select * from performance_schema.PROCESSLIST; select * from performance_schema.RWLOCK_INSTANCES; select * from performance_schema.SETUP_CONSUMERS; select * from performance_schema.SETUP_INSTRUMENTS; -select * from performance_schema.SETUP_OBJECTS; select * from performance_schema.SETUP_TIMERS; +select * from performance_schema.THREADS; show variables like "performance_schema%"; Variable_name Value performance_schema OFF diff --git a/mysql-test/suite/perfschema/r/start_server_on.result b/mysql-test/suite/perfschema/r/start_server_on.result index 1d9dc731c7b..2639fb8e540 100644 --- a/mysql-test/suite/perfschema/r/start_server_on.result +++ b/mysql-test/suite/perfschema/r/start_server_on.result @@ -21,20 +21,19 @@ select * from performance_schema.COND_INSTANCES; select * from performance_schema.EVENTS_WAITS_CURRENT; select * from performance_schema.EVENTS_WAITS_HISTORY; select * from performance_schema.EVENTS_WAITS_HISTORY_LONG; -select * from performance_schema.EVENTS_WAITS_SUMMARY_BY_EVENT_NAME; select * from performance_schema.EVENTS_WAITS_SUMMARY_BY_INSTANCE; select * from performance_schema.EVENTS_WAITS_SUMMARY_BY_THREAD_BY_EVENT_NAME; +select * from performance_schema.EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME; select * from performance_schema.FILE_INSTANCES; select * from performance_schema.FILE_SUMMARY_BY_EVENT_NAME; select * from performance_schema.FILE_SUMMARY_BY_INSTANCE; select * from performance_schema.MUTEX_INSTANCES; select * from performance_schema.PERFORMANCE_TIMERS; -select * from performance_schema.PROCESSLIST; select * from performance_schema.RWLOCK_INSTANCES; select * from performance_schema.SETUP_CONSUMERS; select * from performance_schema.SETUP_INSTRUMENTS; -select * from performance_schema.SETUP_OBJECTS; select * from performance_schema.SETUP_TIMERS; +select * from performance_schema.THREADS; show variables like "performance_schema%"; Variable_name Value performance_schema ON diff --git a/mysql-test/suite/perfschema/t/aggregate.test b/mysql-test/suite/perfschema/t/aggregate.test index 0fa4651ecda..a8ca3dd91e2 100644 --- a/mysql-test/suite/perfschema/t/aggregate.test +++ b/mysql-test/suite/perfschema/t/aggregate.test @@ -31,7 +31,7 @@ update performance_schema.SETUP_CONSUMERS set enabled = 'NO'; # Cleanup statistics truncate table performance_schema.FILE_SUMMARY_BY_EVENT_NAME; truncate table performance_schema.FILE_SUMMARY_BY_INSTANCE; -truncate table performance_schema.EVENTS_WAITS_SUMMARY_BY_EVENT_NAME; +truncate table performance_schema.EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME; truncate table performance_schema.EVENTS_WAITS_SUMMARY_BY_INSTANCE; truncate table performance_schema.EVENTS_WAITS_SUMMARY_BY_THREAD_BY_EVENT_NAME; @@ -66,9 +66,9 @@ set @dump_all=FALSE; # because doing so removes a row in FILE_SUMMARY_BY_INSTANCE. # Likewise: -# - COUNT/SUM/MAX(EVENTS_WAITS_SUMMARY_BY_EVENT_NAME) >= +# - COUNT/SUM/MAX(EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME) >= # COUNT/SUM/MAX(EVENTS_WAITS_SUMMARY_BY_INSTANCE) -# - MIN(EVENTS_WAITS_SUMMARY_BY_EVENT_NAME) <= +# - MIN(EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME) <= # MIN(EVENTS_WAITS_SUMMARY_BY_INSTANCE) # There will be equality only when an instrument instance # is not removed, which is next to impossible to predictably guarantee @@ -80,9 +80,9 @@ set @dump_all=FALSE; # Both cause a row to be deleted from EVENTS_WAITS_SUMMARY_BY_INSTANCE. # Likewise: -# - COUNT/SUM/MAX(EVENTS_WAITS_SUMMARY_BY_EVENT_NAME) >= +# - COUNT/SUM/MAX(EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME) >= # COUNT/SUM/MAX(EVENTS_WAITS_SUMMARY_BY_THREAD_BY_EVENT_NAME) -# - MIN(EVENTS_WAITS_SUMMARY_BY_EVENT_NAME) <= +# - MIN(EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME) <= # MIN(EVENTS_WAITS_SUMMARY_BY_THREAD_BY_EVENT_NAME) # There will be equality only when no thread is removed, # that is if no thread disconnects, or no sub thread (for example insert @@ -131,14 +131,14 @@ OR @dump_all; --echo "Verifying waits aggregate consistency (instance)" SELECT EVENT_NAME, e.SUM_TIMER_WAIT, SUM(i.SUM_TIMER_WAIT) -FROM performance_schema.EVENTS_WAITS_SUMMARY_BY_EVENT_NAME AS e +FROM performance_schema.EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME AS e JOIN performance_schema.EVENTS_WAITS_SUMMARY_BY_INSTANCE AS i USING (EVENT_NAME) GROUP BY EVENT_NAME HAVING (e.SUM_TIMER_WAIT < SUM(i.SUM_TIMER_WAIT)) OR @dump_all; SELECT EVENT_NAME, e.MIN_TIMER_WAIT, MIN(i.MIN_TIMER_WAIT) -FROM performance_schema.EVENTS_WAITS_SUMMARY_BY_EVENT_NAME AS e +FROM performance_schema.EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME AS e JOIN performance_schema.EVENTS_WAITS_SUMMARY_BY_INSTANCE AS i USING (EVENT_NAME) GROUP BY EVENT_NAME HAVING (e.MIN_TIMER_WAIT > MIN(i.MIN_TIMER_WAIT)) @@ -146,7 +146,7 @@ AND (MIN(i.MIN_TIMER_WAIT) != 0) OR @dump_all; SELECT EVENT_NAME, e.MAX_TIMER_WAIT, MAX(i.MAX_TIMER_WAIT) -FROM performance_schema.EVENTS_WAITS_SUMMARY_BY_EVENT_NAME AS e +FROM performance_schema.EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME AS e JOIN performance_schema.EVENTS_WAITS_SUMMARY_BY_INSTANCE AS i USING (EVENT_NAME) GROUP BY EVENT_NAME HAVING (e.MAX_TIMER_WAIT < MAX(i.MAX_TIMER_WAIT)) @@ -155,7 +155,7 @@ OR @dump_all; --echo "Verifying waits aggregate consistency (thread)" SELECT EVENT_NAME, e.SUM_TIMER_WAIT, SUM(t.SUM_TIMER_WAIT) -FROM performance_schema.EVENTS_WAITS_SUMMARY_BY_EVENT_NAME AS e +FROM performance_schema.EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME AS e JOIN performance_schema.EVENTS_WAITS_SUMMARY_BY_THREAD_BY_EVENT_NAME AS t USING (EVENT_NAME) GROUP BY EVENT_NAME @@ -163,7 +163,7 @@ HAVING (e.SUM_TIMER_WAIT < SUM(t.SUM_TIMER_WAIT)) OR @dump_all; SELECT EVENT_NAME, e.MIN_TIMER_WAIT, MIN(t.MIN_TIMER_WAIT) -FROM performance_schema.EVENTS_WAITS_SUMMARY_BY_EVENT_NAME AS e +FROM performance_schema.EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME AS e JOIN performance_schema.EVENTS_WAITS_SUMMARY_BY_THREAD_BY_EVENT_NAME AS t USING (EVENT_NAME) GROUP BY EVENT_NAME @@ -172,7 +172,7 @@ AND (MIN(t.MIN_TIMER_WAIT) != 0) OR @dump_all; SELECT EVENT_NAME, e.MAX_TIMER_WAIT, MAX(t.MAX_TIMER_WAIT) -FROM performance_schema.EVENTS_WAITS_SUMMARY_BY_EVENT_NAME AS e +FROM performance_schema.EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME AS e JOIN performance_schema.EVENTS_WAITS_SUMMARY_BY_THREAD_BY_EVENT_NAME AS t USING (EVENT_NAME) GROUP BY EVENT_NAME diff --git a/mysql-test/suite/perfschema/t/ddl_ews_by_event_name.test b/mysql-test/suite/perfschema/t/ddl_ews_global_by_event_name.test similarity index 69% rename from mysql-test/suite/perfschema/t/ddl_ews_by_event_name.test rename to mysql-test/suite/perfschema/t/ddl_ews_global_by_event_name.test index fbf2d2925a7..c7a767b013b 100644 --- a/mysql-test/suite/perfschema/t/ddl_ews_by_event_name.test +++ b/mysql-test/suite/perfschema/t/ddl_ews_global_by_event_name.test @@ -19,13 +19,16 @@ --source include/have_perfschema.inc -- error ER_DBACCESS_DENIED_ERROR -alter table performance_schema.EVENTS_WAITS_SUMMARY_BY_EVENT_NAME add column foo integer; +alter table performance_schema.EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME + add column foo integer; -truncate table performance_schema.EVENTS_WAITS_SUMMARY_BY_EVENT_NAME; +truncate table performance_schema.EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME; -- error ER_DBACCESS_DENIED_ERROR -ALTER TABLE performance_schema.EVENTS_WAITS_SUMMARY_BY_EVENT_NAME ADD INDEX test_index(EVENT_NAME); +ALTER TABLE performance_schema.EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME + ADD INDEX test_index(EVENT_NAME); -- error ER_DBACCESS_DENIED_ERROR -CREATE UNIQUE INDEX test_index ON performance_schema.EVENTS_WAITS_SUMMARY_BY_EVENT_NAME(EVENT_NAME); +CREATE UNIQUE INDEX test_index + ON performance_schema.EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME(EVENT_NAME); diff --git a/mysql-test/suite/perfschema/t/ddl_setup_objects.test b/mysql-test/suite/perfschema/t/ddl_setup_objects.test deleted file mode 100644 index 6ae6156ef00..00000000000 --- a/mysql-test/suite/perfschema/t/ddl_setup_objects.test +++ /dev/null @@ -1,32 +0,0 @@ -# Copyright (C) 2009 Sun Microsystems, Inc -# -# 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 - -# Tests for PERFORMANCE_SCHEMA - ---source include/not_embedded.inc ---source include/have_perfschema.inc - ---replace_result '\'setup_objects' '\'SETUP_OBJECTS' --- error ER_DBACCESS_DENIED_ERROR -alter table performance_schema.SETUP_OBJECTS add column foo integer; - -truncate table performance_schema.SETUP_OBJECTS; - --- error ER_DBACCESS_DENIED_ERROR -ALTER TABLE performance_schema.SETUP_OBJECTS ADD INDEX test_index(OBJECT_NAME); - --- error ER_DBACCESS_DENIED_ERROR -CREATE UNIQUE INDEX test_index ON performance_schema.SETUP_OBJECTS(OBJECT_NAME); - diff --git a/mysql-test/suite/perfschema/t/ddl_processlist.test b/mysql-test/suite/perfschema/t/ddl_threads.test similarity index 78% rename from mysql-test/suite/perfschema/t/ddl_processlist.test rename to mysql-test/suite/perfschema/t/ddl_threads.test index fb133b66e26..12613e30c1f 100644 --- a/mysql-test/suite/perfschema/t/ddl_processlist.test +++ b/mysql-test/suite/perfschema/t/ddl_threads.test @@ -19,14 +19,14 @@ --source include/have_perfschema.inc -- error ER_DBACCESS_DENIED_ERROR -alter table performance_schema.PROCESSLIST add column foo integer; +alter table performance_schema.THREADS add column foo integer; -- error ER_WRONG_PERFSCHEMA_USAGE -truncate table performance_schema.PROCESSLIST; +truncate table performance_schema.THREADS; -- error ER_DBACCESS_DENIED_ERROR -ALTER TABLE performance_schema.PROCESSLIST ADD INDEX test_index(ID); +ALTER TABLE performance_schema.THREADS ADD INDEX test_index(ID); -- error ER_DBACCESS_DENIED_ERROR -CREATE UNIQUE INDEX test_index ON performance_schema.PROCESSLIST(ID); +CREATE UNIQUE INDEX test_index ON performance_schema.THREADS(ID); diff --git a/mysql-test/suite/perfschema/t/dml_ews_by_event_name.test b/mysql-test/suite/perfschema/t/dml_ews_global_by_event_name.test similarity index 50% rename from mysql-test/suite/perfschema/t/dml_ews_by_event_name.test rename to mysql-test/suite/perfschema/t/dml_ews_global_by_event_name.test index c1fddbe9f87..cd3918f38be 100644 --- a/mysql-test/suite/perfschema/t/dml_ews_by_event_name.test +++ b/mysql-test/suite/perfschema/t/dml_ews_global_by_event_name.test @@ -19,44 +19,44 @@ --source include/have_perfschema.inc --replace_column 1 # 2 # 3 # 4 # 5 # 6 # -select * from performance_schema.EVENTS_WAITS_SUMMARY_BY_EVENT_NAME +select * from performance_schema.EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME where event_name like 'Wait/Synch/%' limit 1; -select * from performance_schema.EVENTS_WAITS_SUMMARY_BY_EVENT_NAME +select * from performance_schema.EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME where event_name='FOO'; ---replace_result '\'events_waits_summary_by_event_name' '\'EVENTS_WAITS_SUMMARY_BY_EVENT_NAME' +--replace_result '\'events_waits_summary_global_by_event_name' '\'EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME' --error ER_TABLEACCESS_DENIED_ERROR -insert into performance_schema.EVENTS_WAITS_SUMMARY_BY_EVENT_NAME +insert into performance_schema.EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME set event_name='FOO', count_star=1, sum_timer_wait=2, min_timer_wait=3, avg_timer_wait=4, max_timer_wait=5; ---replace_result '\'events_waits_summary_by_event_name' '\'EVENTS_WAITS_SUMMARY_BY_EVENT_NAME' +--replace_result '\'events_waits_summary_global_by_event_name' '\'EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME' --error ER_TABLEACCESS_DENIED_ERROR -update performance_schema.EVENTS_WAITS_SUMMARY_BY_EVENT_NAME +update performance_schema.EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME set count_star=12; ---replace_result '\'events_waits_summary_by_event_name' '\'EVENTS_WAITS_SUMMARY_BY_EVENT_NAME' +--replace_result '\'events_waits_summary_global_by_event_name' '\'EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME' --error ER_TABLEACCESS_DENIED_ERROR -update performance_schema.EVENTS_WAITS_SUMMARY_BY_EVENT_NAME +update performance_schema.EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME set count_star=12 where event_name like "FOO"; ---replace_result '\'events_waits_summary_by_event_name' '\'EVENTS_WAITS_SUMMARY_BY_EVENT_NAME' +--replace_result '\'events_waits_summary_global_by_event_name' '\'EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME' --error ER_TABLEACCESS_DENIED_ERROR -delete from performance_schema.EVENTS_WAITS_SUMMARY_BY_EVENT_NAME +delete from performance_schema.EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME where count_star=1; ---replace_result '\'events_waits_summary_by_event_name' '\'EVENTS_WAITS_SUMMARY_BY_EVENT_NAME' +--replace_result '\'events_waits_summary_global_by_event_name' '\'EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME' --error ER_TABLEACCESS_DENIED_ERROR -delete from performance_schema.EVENTS_WAITS_SUMMARY_BY_EVENT_NAME; +delete from performance_schema.EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME; ---replace_result '\'events_waits_summary_by_event_name' '\'EVENTS_WAITS_SUMMARY_BY_EVENT_NAME' +--replace_result '\'events_waits_summary_global_by_event_name' '\'EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME' -- error ER_TABLEACCESS_DENIED_ERROR -LOCK TABLES performance_schema.EVENTS_WAITS_SUMMARY_BY_EVENT_NAME READ; +LOCK TABLES performance_schema.EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME READ; UNLOCK TABLES; ---replace_result '\'events_waits_summary_by_event_name' '\'EVENTS_WAITS_SUMMARY_BY_EVENT_NAME' +--replace_result '\'events_waits_summary_global_by_event_name' '\'EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME' -- error ER_TABLEACCESS_DENIED_ERROR -LOCK TABLES performance_schema.EVENTS_WAITS_SUMMARY_BY_EVENT_NAME WRITE; +LOCK TABLES performance_schema.EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME WRITE; UNLOCK TABLES; diff --git a/mysql-test/suite/perfschema/t/dml_setup_objects.test b/mysql-test/suite/perfschema/t/dml_setup_objects.test deleted file mode 100644 index 21fac64d924..00000000000 --- a/mysql-test/suite/perfschema/t/dml_setup_objects.test +++ /dev/null @@ -1,75 +0,0 @@ -# Copyright (C) 2009 Sun Microsystems, Inc -# -# 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 - -# Tests for PERFORMANCE_SCHEMA - ---source include/not_embedded.inc ---source include/have_perfschema.inc - -select * from performance_schema.SETUP_OBJECTS; - -select * from performance_schema.SETUP_OBJECTS - where object_type = 'TABLE'; - -select * from performance_schema.SETUP_OBJECTS - where enabled='YES'; - -# Not implemented yet ---replace_result '\'setup_objects' '\'SETUP_OBJECTS' ---error ER_ILLEGAL_HA -insert into performance_schema.SETUP_OBJECTS - set object_type='TABLE', object_schema='FOO', object_name='BAR', - enabled='YES', timed='YES', aggregated='YES'; - -# Not implemented yet -# --error ER_ILLEGAL_HA -update performance_schema.SETUP_OBJECTS - set object_type='TABLE'; - -# Not implemented yet -# --error ER_ILLEGAL_HA -update performance_schema.SETUP_OBJECTS - set object_schema='ILLEGAL'; - -# Not implemented yet -# --error ER_ILLEGAL_HA -update performance_schema.SETUP_OBJECTS - set object_name='ILLEGAL'; - -update performance_schema.SETUP_OBJECTS - set enabled='NO'; - -update performance_schema.SETUP_OBJECTS - set timed='NO'; - -update performance_schema.SETUP_OBJECTS - set aggregated='NO'; - -select * from performance_schema.SETUP_OBJECTS; - -update performance_schema.SETUP_OBJECTS - set enabled='YES', timed='YES', aggregated='YES'; - -delete from performance_schema.SETUP_OBJECTS - where object_type = 'TABLE'; - -delete from performance_schema.SETUP_OBJECTS; - -LOCK TABLES performance_schema.SETUP_OBJECTS READ; -UNLOCK TABLES; - -LOCK TABLES performance_schema.SETUP_OBJECTS WRITE; -UNLOCK TABLES; - diff --git a/mysql-test/suite/perfschema/t/dml_processlist.test b/mysql-test/suite/perfschema/t/dml_threads.test similarity index 63% rename from mysql-test/suite/perfschema/t/dml_processlist.test rename to mysql-test/suite/perfschema/t/dml_threads.test index 6062b8481f0..6ea456fee69 100644 --- a/mysql-test/suite/perfschema/t/dml_processlist.test +++ b/mysql-test/suite/perfschema/t/dml_threads.test @@ -19,43 +19,43 @@ --source include/have_perfschema.inc --replace_column 1 # 2 # 3 # -select * from performance_schema.PROCESSLIST +select * from performance_schema.THREADS where name like 'Thread/%' limit 1; -select * from performance_schema.PROCESSLIST +select * from performance_schema.THREADS where name='FOO'; ---replace_result '\'processlist' '\'PROCESSLIST' +--replace_result '\'threads' '\'THREADS' --error ER_TABLEACCESS_DENIED_ERROR -insert into performance_schema.PROCESSLIST +insert into performance_schema.THREADS set name='FOO', thread_id=1, id=2; ---replace_result '\'processlist' '\'PROCESSLIST' +--replace_result '\'threads' '\'THREADS' --error ER_TABLEACCESS_DENIED_ERROR -update performance_schema.PROCESSLIST +update performance_schema.THREADS set thread_id=12; ---replace_result '\'processlist' '\'PROCESSLIST' +--replace_result '\'threads' '\'THREADS' --error ER_TABLEACCESS_DENIED_ERROR -update performance_schema.PROCESSLIST +update performance_schema.THREADS set thread_id=12 where name like "FOO"; ---replace_result '\'processlist' '\'PROCESSLIST' +--replace_result '\'threads' '\'THREADS' --error ER_TABLEACCESS_DENIED_ERROR -delete from performance_schema.PROCESSLIST +delete from performance_schema.THREADS where id=1; ---replace_result '\'processlist' '\'PROCESSLIST' +--replace_result '\'threads' '\'THREADS' --error ER_TABLEACCESS_DENIED_ERROR -delete from performance_schema.PROCESSLIST; +delete from performance_schema.THREADS; ---replace_result '\'processlist' '\'PROCESSLIST' +--replace_result '\'threads' '\'THREADS' -- error ER_TABLEACCESS_DENIED_ERROR -LOCK TABLES performance_schema.PROCESSLIST READ; +LOCK TABLES performance_schema.THREADS READ; UNLOCK TABLES; ---replace_result '\'processlist' '\'PROCESSLIST' +--replace_result '\'threads' '\'THREADS' -- error ER_TABLEACCESS_DENIED_ERROR -LOCK TABLES performance_schema.PROCESSLIST WRITE; +LOCK TABLES performance_schema.THREADS WRITE; UNLOCK TABLES; diff --git a/mysql-test/suite/perfschema/t/func_file_io.test b/mysql-test/suite/perfschema/t/func_file_io.test index 4317f68d13b..6b6335ac424 100644 --- a/mysql-test/suite/perfschema/t/func_file_io.test +++ b/mysql-test/suite/perfschema/t/func_file_io.test @@ -144,7 +144,7 @@ WHERE FILE_NAME LIKE CONCAT('%', @@tmpdir, '%') ORDER BY NULL; # --disable_result_log SELECT EVENT_NAME, COUNT_STAR, AVG_TIMER_WAIT, SUM_TIMER_WAIT -FROM performance_schema.EVENTS_WAITS_SUMMARY_BY_EVENT_NAME +FROM performance_schema.EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME WHERE COUNT_STAR > 0 ORDER BY SUM_TIMER_WAIT DESC LIMIT 10; @@ -158,7 +158,7 @@ LIMIT 10; SELECT i.user, SUM(TIMER_WAIT) SUM_WAIT # ((TIME_TO_SEC(TIMEDIFF(NOW(), i.startup_time)) * 1000) / SUM(TIMER_WAIT)) * 100 WAIT_PERCENTAGE FROM performance_schema.EVENTS_WAITS_HISTORY_LONG h -INNER JOIN performance_schema.PROCESSLIST p USING (THREAD_ID) +INNER JOIN performance_schema.THREADS p USING (THREAD_ID) LEFT JOIN information_schema.PROCESSLIST i USING (ID) GROUP BY i.user ORDER BY SUM_WAIT DESC @@ -171,7 +171,7 @@ LIMIT 20; --disable_result_log SELECT h.EVENT_NAME, SUM(h.TIMER_WAIT) TOTAL_WAIT FROM performance_schema.EVENTS_WAITS_HISTORY_LONG h -INNER JOIN performance_schema.PROCESSLIST p USING (THREAD_ID) +INNER JOIN performance_schema.THREADS p USING (THREAD_ID) WHERE p.ID = 1 GROUP BY h.EVENT_NAME HAVING TOTAL_WAIT > 0; @@ -184,7 +184,7 @@ HAVING TOTAL_WAIT > 0; --disable_result_log SELECT i.user, h.operation, SUM(NUMBER_OF_BYTES) bytes FROM performance_schema.EVENTS_WAITS_HISTORY_LONG h -INNER JOIN performance_schema.PROCESSLIST p USING (THREAD_ID) +INNER JOIN performance_schema.THREADS p USING (THREAD_ID) LEFT JOIN information_schema.PROCESSLIST i USING (ID) GROUP BY i.user, h.operation HAVING BYTES > 0 diff --git a/mysql-test/suite/perfschema/t/misc.test b/mysql-test/suite/perfschema/t/misc.test index dfa865e8702..d497c205d50 100644 --- a/mysql-test/suite/perfschema/t/misc.test +++ b/mysql-test/suite/perfschema/t/misc.test @@ -27,7 +27,7 @@ --disable_result_log SELECT EVENT_ID FROM performance_schema.EVENTS_WAITS_CURRENT WHERE THREAD_ID IN - (SELECT THREAD_ID FROM performance_schema.PROCESSLIST) + (SELECT THREAD_ID FROM performance_schema.THREADS) AND EVENT_NAME IN (SELECT NAME FROM performance_schema.SETUP_INSTRUMENTS WHERE NAME LIKE "wait/synch/%") diff --git a/mysql-test/suite/perfschema/t/no_threads.test b/mysql-test/suite/perfschema/t/no_threads.test index 3d3f712e364..9254535bf1f 100644 --- a/mysql-test/suite/perfschema/t/no_threads.test +++ b/mysql-test/suite/perfschema/t/no_threads.test @@ -45,10 +45,10 @@ show variables like "performance_schema_max_thread%"; # Verification : in this main thread -select count(*) from performance_schema.PROCESSLIST +select count(*) from performance_schema.THREADS where name like "thread/sql/main"; -select count(*) from performance_schema.PROCESSLIST +select count(*) from performance_schema.THREADS where name like "thread/sql/OneConnection"; select event_name, operation, diff --git a/mysql-test/suite/perfschema/t/schema.test b/mysql-test/suite/perfschema/t/schema.test index d13c399a97b..727c4f5a755 100644 --- a/mysql-test/suite/perfschema/t/schema.test +++ b/mysql-test/suite/perfschema/t/schema.test @@ -29,18 +29,17 @@ show create table COND_INSTANCES; show create table EVENTS_WAITS_CURRENT; show create table EVENTS_WAITS_HISTORY; show create table EVENTS_WAITS_HISTORY_LONG; -show create table EVENTS_WAITS_SUMMARY_BY_EVENT_NAME; show create table EVENTS_WAITS_SUMMARY_BY_INSTANCE; show create table EVENTS_WAITS_SUMMARY_BY_THREAD_BY_EVENT_NAME; +show create table EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME; show create table FILE_INSTANCES; show create table FILE_SUMMARY_BY_EVENT_NAME; show create table FILE_SUMMARY_BY_INSTANCE; show create table MUTEX_INSTANCES; show create table PERFORMANCE_TIMERS; -show create table PROCESSLIST; show create table RWLOCK_INSTANCES; show create table SETUP_CONSUMERS; show create table SETUP_INSTRUMENTS; -show create table SETUP_OBJECTS; show create table SETUP_TIMERS; +show create table THREADS; diff --git a/mysql-test/suite/perfschema/t/selects.test b/mysql-test/suite/perfschema/t/selects.test index a0c000b80c1..b673c896024 100644 --- a/mysql-test/suite/perfschema/t/selects.test +++ b/mysql-test/suite/perfschema/t/selects.test @@ -45,7 +45,7 @@ LIMIT 1; --replace_column 1 [EVENT_ID] SELECT EVENT_ID FROM performance_schema.EVENTS_WAITS_CURRENT WHERE THREAD_ID IN - (SELECT THREAD_ID FROM performance_schema.PROCESSLIST) + (SELECT THREAD_ID FROM performance_schema.THREADS) AND EVENT_NAME IN (SELECT NAME FROM performance_schema.SETUP_INSTRUMENTS WHERE NAME LIKE "wait/synch/%") @@ -138,7 +138,7 @@ delimiter |; CREATE PROCEDURE t_ps_proc(IN tid INT, OUT pid INT) BEGIN - SELECT id FROM performance_schema.PROCESSLIST + SELECT id FROM performance_schema.THREADS WHERE THREAD_ID = tid INTO pid; END; @@ -157,7 +157,7 @@ delimiter |; CREATE FUNCTION t_ps_func(tid INT) RETURNS int BEGIN - return (SELECT id FROM performance_schema.PROCESSLIST + return (SELECT id FROM performance_schema.THREADS WHERE THREAD_ID = tid); END; diff --git a/mysql-test/suite/perfschema/t/start_server_no_thread_class.test b/mysql-test/suite/perfschema/t/start_server_no_thread_class.test index ba214ba9966..1ed0fecb538 100644 --- a/mysql-test/suite/perfschema/t/start_server_no_thread_class.test +++ b/mysql-test/suite/perfschema/t/start_server_no_thread_class.test @@ -31,7 +31,7 @@ select variable_value > 0 from information_schema.global_status where variable_name like 'PERFORMANCE_SCHEMA_THREAD_CLASSES_LOST'; # Expect no instances -select count(*) from performance_schema.PROCESSLIST; +select count(*) from performance_schema.THREADS; # Expect no instances lost show status like "performance_schema_thread_instances_lost"; diff --git a/mysql-test/suite/perfschema/t/start_server_no_thread_inst.test b/mysql-test/suite/perfschema/t/start_server_no_thread_inst.test index 7d8a44ebcd5..489f814ba10 100644 --- a/mysql-test/suite/perfschema/t/start_server_no_thread_inst.test +++ b/mysql-test/suite/perfschema/t/start_server_no_thread_inst.test @@ -33,7 +33,7 @@ show status like "performance_schema_thread_classes_lost"; # Expect no instances show variables like "performance_schema_max_thread_instances"; -select count(*) from performance_schema.PROCESSLIST; +select count(*) from performance_schema.THREADS; # Expect instances lost select variable_value > 0 from information_schema.global_status diff --git a/mysql-test/suite/perfschema/t/thread_cache.test b/mysql-test/suite/perfschema/t/thread_cache.test index 8c3271ba406..5560f66babb 100644 --- a/mysql-test/suite/perfschema/t/thread_cache.test +++ b/mysql-test/suite/perfschema/t/thread_cache.test @@ -30,14 +30,14 @@ connect (con1, localhost, root, , ); let $con1_ID=`select connection_id()`; -let $con1_THREAD_ID=`select thread_id from performance_schema.PROCESSLIST +let $con1_THREAD_ID=`select thread_id from performance_schema.THREADS where ID = connection_id()`; connect (con2, localhost, root, , ); let $con2_ID=`select connection_id()`; -let $con2_THREAD_ID=`select thread_id from performance_schema.PROCESSLIST +let $con2_THREAD_ID=`select thread_id from performance_schema.THREADS where ID = connection_id()`; connection default; @@ -58,7 +58,7 @@ connect (con3, localhost, root, , ); let $con3_ID=`select connection_id()`; -let $con3_THREAD_ID=`select thread_id from performance_schema.PROCESSLIST +let $con3_THREAD_ID=`select thread_id from performance_schema.THREADS where ID = connection_id()`; disconnect con3; @@ -82,14 +82,14 @@ connect (con1, localhost, root, , ); let $con1_ID=`select connection_id()`; -let $con1_THREAD_ID=`select thread_id from performance_schema.PROCESSLIST +let $con1_THREAD_ID=`select thread_id from performance_schema.THREADS where ID = connection_id()`; connect (con2, localhost, root, , ); let $con2_ID=`select connection_id()`; -let $con2_THREAD_ID=`select thread_id from performance_schema.PROCESSLIST +let $con2_THREAD_ID=`select thread_id from performance_schema.THREADS where ID = connection_id()`; connection default; @@ -108,7 +108,7 @@ connect (con3, localhost, root, , ); let $con3_ID=`select connection_id()`; -let $con3_THREAD_ID=`select thread_id from performance_schema.PROCESSLIST +let $con3_THREAD_ID=`select thread_id from performance_schema.THREADS where ID = connection_id()`; disconnect con3; diff --git a/scripts/mysql_system_tables.sql b/scripts/mysql_system_tables.sql index b5ee4d6dd41..dd620b80475 100644 --- a/scripts/mysql_system_tables.sql +++ b/scripts/mysql_system_tables.sql @@ -241,26 +241,6 @@ PREPARE stmt FROM @str; EXECUTE stmt; DROP PREPARE stmt; --- --- TABLE EVENTS_WAITS_SUMMARY_BY_EVENT_NAME --- - -SET @l1="CREATE TABLE performance_schema.EVENTS_WAITS_SUMMARY_BY_EVENT_NAME("; -SET @l2="EVENT_NAME VARCHAR(128) not null,"; -SET @l3="COUNT_STAR BIGINT unsigned not null,"; -SET @l4="SUM_TIMER_WAIT BIGINT unsigned not null,"; -SET @l5="MIN_TIMER_WAIT BIGINT unsigned not null,"; -SET @l6="AVG_TIMER_WAIT BIGINT unsigned not null,"; -SET @l7="MAX_TIMER_WAIT BIGINT unsigned not null"; -SET @l8=")ENGINE=PERFORMANCE_SCHEMA;"; - -SET @cmd=concat(@l1,@l2,@l3,@l4,@l5,@l6,@l7,@l8); - -SET @str = IF(@have_pfs = 1, @cmd, 'SET @dummy = 0'); -PREPARE stmt FROM @str; -EXECUTE stmt; -DROP PREPARE stmt; - -- -- TABLE EVENTS_WAITS_SUMMARY_BY_INSTANCE -- @@ -303,6 +283,26 @@ PREPARE stmt FROM @str; EXECUTE stmt; DROP PREPARE stmt; +-- +-- TABLE EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME +-- + +SET @l1="CREATE TABLE performance_schema.EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME("; +SET @l2="EVENT_NAME VARCHAR(128) not null,"; +SET @l3="COUNT_STAR BIGINT unsigned not null,"; +SET @l4="SUM_TIMER_WAIT BIGINT unsigned not null,"; +SET @l5="MIN_TIMER_WAIT BIGINT unsigned not null,"; +SET @l6="AVG_TIMER_WAIT BIGINT unsigned not null,"; +SET @l7="MAX_TIMER_WAIT BIGINT unsigned not null"; +SET @l8=")ENGINE=PERFORMANCE_SCHEMA;"; + +SET @cmd=concat(@l1,@l2,@l3,@l4,@l5,@l6,@l7,@l8); + +SET @str = IF(@have_pfs = 1, @cmd, 'SET @dummy = 0'); +PREPARE stmt FROM @str; +EXECUTE stmt; +DROP PREPARE stmt; + -- -- TABLE FILE_INSTANCES -- @@ -394,23 +394,6 @@ PREPARE stmt FROM @str; EXECUTE stmt; DROP PREPARE stmt; --- --- TABLE PROCESSLIST --- - -SET @l1="CREATE TABLE performance_schema.PROCESSLIST("; -SET @l2="THREAD_ID INTEGER not null,"; -SET @l3="ID INTEGER not null,"; -SET @l4="NAME VARCHAR(64) not null"; -SET @l5=")ENGINE=PERFORMANCE_SCHEMA;"; - -SET @cmd=concat(@l1,@l2,@l3,@l4,@l5); - -SET @str = IF(@have_pfs = 1, @cmd, 'SET @dummy = 0'); -PREPARE stmt FROM @str; -EXECUTE stmt; -DROP PREPARE stmt; - -- -- TABLE RWLOCK_INSTANCES -- @@ -462,26 +445,6 @@ PREPARE stmt FROM @str; EXECUTE stmt; DROP PREPARE stmt; --- --- TABLE SETUP_OBJECTS --- - -SET @l1="CREATE TABLE performance_schema.SETUP_OBJECTS("; -SET @l2="OBJECT_TYPE VARCHAR(64),"; -SET @l3="OBJECT_SCHEMA VARCHAR(64),"; -SET @l4="OBJECT_NAME VARCHAR(64),"; -SET @l5="ENABLED ENUM ('YES', 'NO') not null,"; -SET @l6="TIMED ENUM ('YES', 'NO') not null,"; -SET @l7="AGGREGATED ENUM ('YES', 'NO') not null"; -SET @l8=")ENGINE=PERFORMANCE_SCHEMA;"; - -SET @cmd=concat(@l1,@l2,@l3,@l4,@l5,@l6,@l7,@l8); - -SET @str = IF(@have_pfs = 1, @cmd, 'SET @dummy = 0'); -PREPARE stmt FROM @str; -EXECUTE stmt; -DROP PREPARE stmt; - -- -- TABLE SETUP_TIMERS -- @@ -498,3 +461,20 @@ PREPARE stmt FROM @str; EXECUTE stmt; DROP PREPARE stmt; +-- +-- TABLE THREADS +-- + +SET @l1="CREATE TABLE performance_schema.THREADS("; +SET @l2="THREAD_ID INTEGER not null,"; +SET @l3="ID INTEGER not null,"; +SET @l4="NAME VARCHAR(64) not null"; +SET @l5=")ENGINE=PERFORMANCE_SCHEMA;"; + +SET @cmd=concat(@l1,@l2,@l3,@l4,@l5); + +SET @str = IF(@have_pfs = 1, @cmd, 'SET @dummy = 0'); +PREPARE stmt FROM @str; +EXECUTE stmt; +DROP PREPARE stmt; + diff --git a/storage/perfschema/CMakeLists.txt b/storage/perfschema/CMakeLists.txt index 5cd651a35bd..a3999da4ba1 100644 --- a/storage/perfschema/CMakeLists.txt +++ b/storage/perfschema/CMakeLists.txt @@ -38,15 +38,15 @@ SET(PERFSCHEMA_SOURCES ha_perfschema.h table_all_instr.h table_events_waits.h table_events_waits_summary.h + table_ews_global_by_event_name.h table_file_instances.h table_file_summary.h table_performance_timers.h - table_processlist.h table_setup_consumers.h table_setup_instruments.h - table_setup_objects.h table_setup_timers.h table_sync_instances.h + table_threads.h ha_perfschema.cc pfs.cc pfs_column_values.cc @@ -60,15 +60,15 @@ SET(PERFSCHEMA_SOURCES ha_perfschema.h table_all_instr.cc table_events_waits.cc table_events_waits_summary.cc + table_ews_global_by_event_name.cc table_file_instances.cc table_file_summary.cc table_performance_timers.cc - table_processlist.cc table_setup_consumers.cc table_setup_instruments.cc - table_setup_objects.cc table_setup_timers.cc table_sync_instances.cc + table_threads.cc pfs_atomic.cc pfs_check.cc ) diff --git a/storage/perfschema/Makefile.am b/storage/perfschema/Makefile.am index 374415cfdfd..762f5b85790 100644 --- a/storage/perfschema/Makefile.am +++ b/storage/perfschema/Makefile.am @@ -39,12 +39,12 @@ noinst_HEADERS = ha_perfschema.h pfs_engine_table.h pfs.h pfs_server.h \ table_setup_instruments.h table_performance_timers.h \ table_setup_timers.h \ table_setup_consumers.h table_events_waits.h \ - pfs_events_waits.h pfs_timer.h table_processlist.h \ + pfs_events_waits.h pfs_timer.h table_threads.h \ table_sync_instances.h \ table_events_waits_summary.h pfs_stat.h \ - table_all_instr.h \ + table_ews_global_by_event_name.h table_all_instr.h \ table_file_instances.h table_file_summary.h \ - table_setup_objects.h pfs_lock.h pfs_atomic.h + pfs_lock.h pfs_atomic.h PSE_SOURCES = ha_perfschema.cc pfs_engine_table.cc pfs.cc pfs_server.cc \ pfs_global.cc pfs_instr_class.cc pfs_instr.cc \ @@ -52,12 +52,12 @@ PSE_SOURCES = ha_perfschema.cc pfs_engine_table.cc pfs.cc pfs_server.cc \ table_setup_instruments.cc table_performance_timers.cc \ table_setup_timers.cc \ table_setup_consumers.cc table_events_waits.cc \ - pfs_events_waits.cc pfs_timer.cc table_processlist.cc \ + pfs_events_waits.cc pfs_timer.cc table_threads.cc \ table_sync_instances.cc \ table_events_waits_summary.cc \ - table_all_instr.cc \ + table_ews_global_by_event_name.cc table_all_instr.cc \ table_file_instances.cc table_file_summary.cc \ - table_setup_objects.cc pfs_atomic.cc pfs_check.cc + pfs_atomic.cc pfs_check.cc EXTRA_LIBRARIES = libperfschema.a noinst_LIBRARIES = @plugin_perfschema_static_target@ diff --git a/storage/perfschema/pfs_engine_table.cc b/storage/perfschema/pfs_engine_table.cc index 7b6fd055729..df00811959c 100644 --- a/storage/perfschema/pfs_engine_table.cc +++ b/storage/perfschema/pfs_engine_table.cc @@ -23,11 +23,11 @@ #include "table_events_waits.h" #include "table_setup_consumers.h" #include "table_setup_instruments.h" -#include "table_setup_objects.h" #include "table_setup_timers.h" #include "table_performance_timers.h" -#include "table_processlist.h" +#include "table_threads.h" #include "table_events_waits_summary.h" +#include "table_ews_global_by_event_name.h" #include "table_sync_instances.h" #include "table_file_instances.h" #include "table_file_summary.h" @@ -52,13 +52,12 @@ static PFS_engine_table_share *all_shares[]= &table_events_waits_history_long::m_share, &table_setup_consumers::m_share, &table_setup_instruments::m_share, - &table_setup_objects::m_share, &table_setup_timers::m_share, &table_performance_timers::m_share, - &table_processlist::m_share, + &table_threads::m_share, &table_events_waits_summary_by_thread_by_event_name::m_share, - &table_events_waits_summary_by_event_name::m_share, &table_events_waits_summary_by_instance::m_share, + &table_ews_global_by_event_name::m_share, &table_file_summary_by_event_name::m_share, &table_file_summary_by_instance::m_share, &table_mutex_instances::m_share, diff --git a/storage/perfschema/table_events_waits_summary.cc b/storage/perfschema/table_events_waits_summary.cc index 9d0d6fe0f67..435a3500f06 100644 --- a/storage/perfschema/table_events_waits_summary.cc +++ b/storage/perfschema/table_events_waits_summary.cc @@ -338,144 +338,6 @@ int table_events_waits_summary_by_thread_by_event_name return 0; } -THR_LOCK table_events_waits_summary_by_event_name::m_table_lock; - -static const TABLE_FIELD_TYPE ews_by_event_name_field_types[]= -{ - { - { C_STRING_WITH_LEN("EVENT_NAME") }, - { C_STRING_WITH_LEN("varchar(128)") }, - { NULL, 0} - }, - { - { C_STRING_WITH_LEN("COUNT_STAR") }, - { C_STRING_WITH_LEN("bigint(20)") }, - { NULL, 0} - }, - { - { C_STRING_WITH_LEN("SUM_TIMER_WAIT") }, - { C_STRING_WITH_LEN("bigint(20)") }, - { NULL, 0} - }, - { - { C_STRING_WITH_LEN("MIN_TIMER_WAIT") }, - { C_STRING_WITH_LEN("bigint(20)") }, - { NULL, 0} - }, - { - { C_STRING_WITH_LEN("AVG_TIMER_WAIT") }, - { C_STRING_WITH_LEN("bigint(20)") }, - { NULL, 0} - }, - { - { C_STRING_WITH_LEN("MAX_TIMER_WAIT") }, - { C_STRING_WITH_LEN("bigint(20)") }, - { NULL, 0} - } -}; - -TABLE_FIELD_DEF -table_events_waits_summary_by_event_name::m_field_def= -{ 6, ews_by_event_name_field_types }; - -PFS_engine_table_share -table_events_waits_summary_by_event_name::m_share= -{ - { C_STRING_WITH_LEN("EVENTS_WAITS_SUMMARY_BY_EVENT_NAME") }, - &pfs_truncatable_acl, - &table_events_waits_summary_by_event_name::create, - NULL, /* write_row */ - &table_events_waits_summary_by_event_name::delete_all_rows, - 1000, /* records */ - sizeof(pos_all_instr_class), - &m_table_lock, - &m_field_def, - false /* checked */ -}; - -PFS_engine_table* table_events_waits_summary_by_event_name::create(void) -{ - return new table_events_waits_summary_by_event_name(); -} - -int table_events_waits_summary_by_event_name::delete_all_rows(void) -{ - reset_instrument_class_waits(); - return 0; -} - -table_events_waits_summary_by_event_name -::table_events_waits_summary_by_event_name() - : table_all_instr_class(&m_share) -{} - -void table_events_waits_summary_by_event_name -::make_instr_row(PFS_instr_class *klass) -{ - m_row.m_name= klass->m_name; - m_row.m_name_length= klass->m_name_length; - - m_row.m_count= klass->m_wait_stat.m_count; - m_row.m_sum= klass->m_wait_stat.m_sum; - m_row.m_min= klass->m_wait_stat.m_min; - m_row.m_max= klass->m_wait_stat.m_max; - - if (m_row.m_count) - m_row.m_avg= m_row.m_sum / m_row.m_count; - else - { - m_row.m_min= 0; - m_row.m_avg= 0; - } -} - -int table_events_waits_summary_by_event_name -::read_row_values(TABLE *table, unsigned char *, Field **fields, - bool read_all) -{ - Field *f; - - /* Set the null bits */ - DBUG_ASSERT(table->s->null_bytes == 0); - - /* - The row always exist, - the instrument classes are static and never disappear. - */ - - for (; (f= *fields) ; fields++) - { - if (read_all || bitmap_is_set(table->read_set, f->field_index)) - { - switch(f->field_index) - { - case 0: /* NAME */ - set_field_varchar_utf8(f, m_row.m_name, m_row.m_name_length); - break; - case 1: /* COUNT */ - set_field_ulonglong(f, m_row.m_count); - break; - case 2: /* SUM */ - set_field_ulonglong(f, m_row.m_sum); - break; - case 3: /* MIN */ - set_field_ulonglong(f, m_row.m_min); - break; - case 4: /* AVG */ - set_field_ulonglong(f, m_row.m_avg); - break; - case 5: /* MAX */ - set_field_ulonglong(f, m_row.m_max); - break; - default: - DBUG_ASSERT(false); - } - } - } - - return 0; -} - THR_LOCK table_events_waits_summary_by_instance::m_table_lock; static const TABLE_FIELD_TYPE ews_by_instance_field_types[]= diff --git a/storage/perfschema/table_events_waits_summary.h b/storage/perfschema/table_events_waits_summary.h index 47ec9523d68..628bb75553f 100644 --- a/storage/perfschema/table_events_waits_summary.h +++ b/storage/perfschema/table_events_waits_summary.h @@ -144,58 +144,6 @@ private: pos_events_waits_summary_by_thread_by_event_name m_next_pos; }; -/** A row of PERFORMANCE_SCHEMA.EVENTS_WAITS_SUMMARY_BY_EVENT_NAME. */ -struct row_events_waits_summary_by_event_name -{ - /** Column EVENT_NAME. */ - const char *m_name; - /** Length in bytes of @c m_name. */ - uint m_name_length; - /** Column COUNT_STAR. */ - ulonglong m_count; - /** Column SUM_TIMER_WAIT. */ - ulonglong m_sum; - /** Column MIN_TIMER_WAIT. */ - ulonglong m_min; - /** Column AVG_TIMER_WAIT. */ - ulonglong m_avg; - /** Column MAX_TIMER_WAIT. */ - ulonglong m_max; -}; - -/** Table PERFORMANCE_SCHEMA.EVENTS_WAITS_SUMMARY_BY_EVENT_NAME. */ -class table_events_waits_summary_by_event_name : public table_all_instr_class -{ -public: - /** Table share */ - static PFS_engine_table_share m_share; - static PFS_engine_table* create(); - static int delete_all_rows(); - -protected: - virtual void make_instr_row(PFS_instr_class *klass); - - virtual int read_row_values(TABLE *table, - unsigned char *buf, - Field **fields, - bool read_all); - - table_events_waits_summary_by_event_name(); - -public: - ~table_events_waits_summary_by_event_name() - {} - -private: - /** Table share lock. */ - static THR_LOCK m_table_lock; - /** Fields definition. */ - static TABLE_FIELD_DEF m_field_def; - - /** Current row. */ - row_events_waits_summary_by_event_name m_row; -}; - /** A row of PERFORMANCE_SCHEMA.EVENTS_WAITS_SUMMARY_BY_INSTANCE. */ struct row_events_waits_summary_by_instance { diff --git a/storage/perfschema/table_ews_global_by_event_name.cc b/storage/perfschema/table_ews_global_by_event_name.cc new file mode 100644 index 00000000000..35e744ed96b --- /dev/null +++ b/storage/perfschema/table_ews_global_by_event_name.cc @@ -0,0 +1,166 @@ +/* Copyright (c) 2008, 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, + 51 Franklin Street, Suite 500, Boston, MA 02110-1335 USA */ + +/** + @file storage/perfschema/table_ews_global_by_event_name.cc + Table EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME (implementation). +*/ + +#include "my_global.h" +#include "my_pthread.h" +#include "pfs_instr_class.h" +#include "pfs_column_types.h" +#include "pfs_column_values.h" +#include "table_ews_global_by_event_name.h" +#include "pfs_global.h" + +THR_LOCK table_ews_global_by_event_name::m_table_lock; + +static const TABLE_FIELD_TYPE field_types[]= +{ + { + { C_STRING_WITH_LEN("EVENT_NAME") }, + { C_STRING_WITH_LEN("varchar(128)") }, + { NULL, 0} + }, + { + { C_STRING_WITH_LEN("COUNT_STAR") }, + { C_STRING_WITH_LEN("bigint(20)") }, + { NULL, 0} + }, + { + { C_STRING_WITH_LEN("SUM_TIMER_WAIT") }, + { C_STRING_WITH_LEN("bigint(20)") }, + { NULL, 0} + }, + { + { C_STRING_WITH_LEN("MIN_TIMER_WAIT") }, + { C_STRING_WITH_LEN("bigint(20)") }, + { NULL, 0} + }, + { + { C_STRING_WITH_LEN("AVG_TIMER_WAIT") }, + { C_STRING_WITH_LEN("bigint(20)") }, + { NULL, 0} + }, + { + { C_STRING_WITH_LEN("MAX_TIMER_WAIT") }, + { C_STRING_WITH_LEN("bigint(20)") }, + { NULL, 0} + } +}; + +TABLE_FIELD_DEF +table_ews_global_by_event_name::m_field_def= +{ 6, field_types }; + +PFS_engine_table_share +table_ews_global_by_event_name::m_share= +{ + { C_STRING_WITH_LEN("EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME") }, + &pfs_truncatable_acl, + &table_ews_global_by_event_name::create, + NULL, /* write_row */ + &table_ews_global_by_event_name::delete_all_rows, + 1000, /* records */ + sizeof(pos_all_instr_class), + &m_table_lock, + &m_field_def, + false /* checked */ +}; + +PFS_engine_table* table_ews_global_by_event_name::create(void) +{ + return new table_ews_global_by_event_name(); +} + +int table_ews_global_by_event_name::delete_all_rows(void) +{ + reset_instrument_class_waits(); + return 0; +} + +table_ews_global_by_event_name +::table_ews_global_by_event_name() + : table_all_instr_class(&m_share) +{} + +void table_ews_global_by_event_name +::make_instr_row(PFS_instr_class *klass) +{ + m_row.m_name= klass->m_name; + m_row.m_name_length= klass->m_name_length; + + m_row.m_count= klass->m_wait_stat.m_count; + m_row.m_sum= klass->m_wait_stat.m_sum; + m_row.m_min= klass->m_wait_stat.m_min; + m_row.m_max= klass->m_wait_stat.m_max; + + if (m_row.m_count) + m_row.m_avg= m_row.m_sum / m_row.m_count; + else + { + m_row.m_min= 0; + m_row.m_avg= 0; + } +} + +int table_ews_global_by_event_name +::read_row_values(TABLE *table, unsigned char *, Field **fields, + bool read_all) +{ + Field *f; + + /* Set the null bits */ + DBUG_ASSERT(table->s->null_bytes == 0); + + /* + The row always exist, + the instrument classes are static and never disappear. + */ + + for (; (f= *fields) ; fields++) + { + if (read_all || bitmap_is_set(table->read_set, f->field_index)) + { + switch(f->field_index) + { + case 0: /* NAME */ + set_field_varchar_utf8(f, m_row.m_name, m_row.m_name_length); + break; + case 1: /* COUNT */ + set_field_ulonglong(f, m_row.m_count); + break; + case 2: /* SUM */ + set_field_ulonglong(f, m_row.m_sum); + break; + case 3: /* MIN */ + set_field_ulonglong(f, m_row.m_min); + break; + case 4: /* AVG */ + set_field_ulonglong(f, m_row.m_avg); + break; + case 5: /* MAX */ + set_field_ulonglong(f, m_row.m_max); + break; + default: + DBUG_ASSERT(false); + } + } + } + + return 0; +} + diff --git a/storage/perfschema/table_ews_global_by_event_name.h b/storage/perfschema/table_ews_global_by_event_name.h new file mode 100644 index 00000000000..402ed9d80de --- /dev/null +++ b/storage/perfschema/table_ews_global_by_event_name.h @@ -0,0 +1,88 @@ +/* Copyright (c) 2008, 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, + 51 Franklin Street, Suite 500, Boston, MA 02110-1335 USA */ + +#ifndef TABLE_EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME_H +#define TABLE_EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME_H + +/** + @file storage/perfschema/table_ews_global_by_event_name.h + Table EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME (declarations). +*/ + +#include "pfs_column_types.h" +#include "pfs_engine_table.h" +#include "pfs_instr_class.h" +#include "pfs_instr.h" +#include "table_all_instr.h" + +/** + @addtogroup Performance_schema_tables + @{ +*/ + +/** A row of PERFORMANCE_SCHEMA.EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME. */ +struct row_ews_global_by_event_name +{ + /** Column EVENT_NAME. */ + const char *m_name; + /** Length in bytes of @c m_name. */ + uint m_name_length; + /** Column COUNT_STAR. */ + ulonglong m_count; + /** Column SUM_TIMER_WAIT. */ + ulonglong m_sum; + /** Column MIN_TIMER_WAIT. */ + ulonglong m_min; + /** Column AVG_TIMER_WAIT. */ + ulonglong m_avg; + /** Column MAX_TIMER_WAIT. */ + ulonglong m_max; +}; + +/** Table PERFORMANCE_SCHEMA.EVENTS_WAITS_SUMMARY_GLOBAL_BY_EVENT_NAME. */ +class table_ews_global_by_event_name : public table_all_instr_class +{ +public: + /** Table share */ + static PFS_engine_table_share m_share; + static PFS_engine_table* create(); + static int delete_all_rows(); + +protected: + virtual void make_instr_row(PFS_instr_class *klass); + + virtual int read_row_values(TABLE *table, + unsigned char *buf, + Field **fields, + bool read_all); + + table_ews_global_by_event_name(); + +public: + ~table_ews_global_by_event_name() + {} + +private: + /** Table share lock. */ + static THR_LOCK m_table_lock; + /** Fields definition. */ + static TABLE_FIELD_DEF m_field_def; + + /** Current row. */ + row_ews_global_by_event_name m_row; +}; + +/** @} */ +#endif diff --git a/storage/perfschema/table_setup_objects.cc b/storage/perfschema/table_setup_objects.cc deleted file mode 100644 index b75bece83bd..00000000000 --- a/storage/perfschema/table_setup_objects.cc +++ /dev/null @@ -1,281 +0,0 @@ -/* Copyright (C) 2008-2009 Sun Microsystems, Inc - - 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 */ - -/** - @file storage/perfschema/table_setup_objects.cc - Table SETUP_OBJECTS (implementation). -*/ - -#include "sql_priv.h" -#include "unireg.h" -#include "pfs_instr_class.h" -#include "pfs_column_types.h" -#include "pfs_column_values.h" -#include "table_setup_objects.h" -#include "pfs_global.h" - -THR_LOCK table_setup_objects::m_table_lock; - -static const TABLE_FIELD_TYPE field_types[]= -{ - { - { C_STRING_WITH_LEN("OBJECT_TYPE") }, - { C_STRING_WITH_LEN("varchar(64)") }, - { NULL, 0} - }, - { - { C_STRING_WITH_LEN("OBJECT_SCHEMA") }, - { C_STRING_WITH_LEN("varchar(64)") }, - { NULL, 0} - }, - { - { C_STRING_WITH_LEN("OBJECT_NAME") }, - { C_STRING_WITH_LEN("varchar(64)") }, - { NULL, 0} - }, - { - { C_STRING_WITH_LEN("ENABLED") }, - { C_STRING_WITH_LEN("enum(\'YES\',\'NO\')") }, - { NULL, 0} - }, - { - { C_STRING_WITH_LEN("TIMED") }, - { C_STRING_WITH_LEN("enum(\'YES\',\'NO\')") }, - { NULL, 0} - }, - { - { C_STRING_WITH_LEN("AGGREGATED") }, - { C_STRING_WITH_LEN("enum(\'YES\',\'NO\')") }, - { NULL, 0} - } -}; - -TABLE_FIELD_DEF -table_setup_objects::m_field_def= -{ 6, field_types }; - -PFS_engine_table_share -table_setup_objects::m_share= -{ - { C_STRING_WITH_LEN("SETUP_OBJECTS") }, - &pfs_editable_acl, - &table_setup_objects::create, - table_setup_objects::write_row, - table_setup_objects::delete_all_rows, - 1000, /* records */ - sizeof(pos_setup_objects), - &m_table_lock, - &m_field_def, - false /* checked */ -}; - -PFS_engine_table* table_setup_objects::create(void) -{ - return new table_setup_objects(); -} - -int table_setup_objects::write_row(TABLE *table, unsigned char *buf, - Field **fields) -{ - /* Not implemented */ - return HA_ERR_WRONG_COMMAND; -} - -int table_setup_objects::delete_all_rows(void) -{ - /* Not implemented */ - return HA_ERR_WRONG_COMMAND; -} - -table_setup_objects::table_setup_objects() - : PFS_engine_table(&m_share, &m_pos), - m_row_exists(false), m_pos(), m_next_pos() -{} - -void table_setup_objects::reset_position(void) -{ - m_pos.reset(); - m_next_pos.reset(); -} - -int table_setup_objects::rnd_next(void) -{ - PFS_table_share *table_share; - - for (m_pos.set_at(&m_next_pos); - m_pos.has_more_view(); - m_pos.next_view()) - { - switch (m_pos.m_index_1) { - case pos_setup_objects::VIEW_TABLE: - for ( ; m_pos.m_index_2 < table_share_max; m_pos.m_index_2++) - { - table_share= &table_share_array[m_pos.m_index_2]; - if (table_share->m_lock.is_populated()) - { - make_row(table_share); - m_next_pos.set_after(&m_pos); - return 0; - } - } - break; - case pos_setup_objects::VIEW_EVENT: - case pos_setup_objects::VIEW_PROCEDURE: - case pos_setup_objects::VIEW_FUNCTION: - default: - break; - } - } - - return HA_ERR_END_OF_FILE; -} - -int table_setup_objects::rnd_pos(const void *pos) -{ - PFS_table_share *share; - - set_position(pos); - - switch (m_pos.m_index_1) { - case pos_setup_objects::VIEW_TABLE: - DBUG_ASSERT(m_pos.m_index_2 < table_share_max); - share= &table_share_array[m_pos.m_index_2]; - if (share->m_lock.is_populated()) - { - make_row(share); - return 0; - } - break; - case pos_setup_objects::VIEW_EVENT: - case pos_setup_objects::VIEW_PROCEDURE: - case pos_setup_objects::VIEW_FUNCTION: - default: - break; - } - - return HA_ERR_RECORD_DELETED; -} - -void table_setup_objects::make_row(PFS_table_share *share) -{ - pfs_lock lock; - - m_row_exists= false; - if (share == NULL) - return; - - share->m_lock.begin_optimistic_lock(&lock); - - m_row.m_schema_name= &share->m_schema_name[0]; - m_row.m_schema_name_length= share->m_schema_name_length; - m_row.m_object_name= &share->m_table_name[0]; - m_row.m_object_name_length= share->m_table_name_length; - m_row.m_enabled_ptr= &share->m_enabled; - m_row.m_timed_ptr= &share->m_timed; - m_row.m_aggregated_ptr= &share->m_aggregated; - - if (share->m_lock.end_optimistic_lock(&lock)) - m_row_exists= true; -} - -int table_setup_objects::read_row_values(TABLE *table, - unsigned char *buf, - Field **fields, - bool read_all) -{ - Field *f; - - if (unlikely(! m_row_exists)) - return HA_ERR_RECORD_DELETED; - - /* Set the null bits */ - DBUG_ASSERT(table->s->null_bytes == 1); - buf[0]= 0; - - for (; (f= *fields) ; fields++) - { - if (read_all || bitmap_is_set(table->read_set, f->field_index)) - { - switch(f->field_index) - { - case 0: /* OBJECT_TYPE */ - set_field_varchar_utf8(f, "TABLE", 5); - break; - case 1: /* OBJECT_SCHEMA */ - set_field_varchar_utf8(f, m_row.m_schema_name, - m_row.m_schema_name_length); - break; - case 2: /* OBJECT_NAME */ - set_field_varchar_utf8(f, m_row.m_object_name, - m_row.m_object_name_length); - break; - case 3: /* ENABLED */ - set_field_enum(f, (*m_row.m_enabled_ptr) ? ENUM_YES : ENUM_NO); - break; - case 4: /* TIMED */ - set_field_enum(f, (*m_row.m_timed_ptr) ? ENUM_YES : ENUM_NO); - break; - case 5: /* AGGREGATED */ - set_field_enum(f, (*m_row.m_aggregated_ptr) ? ENUM_YES : ENUM_NO); - break; - default: - DBUG_ASSERT(false); - } - } - } - - return 0; -} - -int table_setup_objects::update_row_values(TABLE *table, - const unsigned char *, - unsigned char *, - Field **fields) -{ - Field *f; - enum_yes_no value; - - for (; (f= *fields) ; fields++) - { - if (bitmap_is_set(table->write_set, f->field_index)) - { - switch(f->field_index) - { - case 0: /* OBJECT_TYPE */ - case 1: /* OBJECT_SCHEMA */ - case 2: /* OBJECT_NAME */ - my_error(ER_WRONG_PERFSCHEMA_USAGE, MYF(0)); - return HA_ERR_WRONG_COMMAND; - case 3: /* ENABLED */ - value= (enum_yes_no) get_field_enum(f); - *m_row.m_enabled_ptr= (value == ENUM_YES) ? true : false; - break; - case 4: /* TIMED */ - value= (enum_yes_no) get_field_enum(f); - *m_row.m_timed_ptr= (value == ENUM_YES) ? true : false; - break; - case 5: /* AGGREGATED */ - value= (enum_yes_no) get_field_enum(f); - *m_row.m_aggregated_ptr= (value == ENUM_YES) ? true : false; - break; - default: - DBUG_ASSERT(false); - } - } - } - - return 0; -} - diff --git a/storage/perfschema/table_setup_objects.h b/storage/perfschema/table_setup_objects.h deleted file mode 100644 index 994e12016a6..00000000000 --- a/storage/perfschema/table_setup_objects.h +++ /dev/null @@ -1,125 +0,0 @@ -/* Copyright (C) 2008-2009 Sun Microsystems, Inc - - 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 */ - -#ifndef TABLE_SETUP_OBJECTS_H -#define TABLE_SETUP_OBJECTS_H - -/** - @file storage/perfschema/table_setup_objects.h - Table SETUP_OBJECTS (declarations). -*/ - -#include "pfs_instr_class.h" -#include "pfs_engine_table.h" - -/** - @addtogroup Performance_schema_tables - @{ -*/ - -/** A row of PERFORMANCE_SCHEMA.SETUP_OBJECTS. */ -struct row_setup_objects -{ - /** Column SCHEMA_NAME. */ - const char *m_schema_name; - /** Length in bytes of @c m_schema_name. */ - uint m_schema_name_length; - /** Column OBJECT_NAME. */ - const char *m_object_name; - /** Length in bytes of @c m_object_name. */ - uint m_object_name_length; - /** Column ENABLED. */ - bool *m_enabled_ptr; - /** Column TIMED. */ - bool *m_timed_ptr; - /** Column AGGREGATED. */ - bool *m_aggregated_ptr; -}; - -/** Position of a cursor on PERFORMANCE_SCHEMA.SETUP_OBJECTS. */ -struct pos_setup_objects : public PFS_double_index, - public PFS_object_view_constants -{ - pos_setup_objects() - : PFS_double_index(VIEW_TABLE, 0) - {} - - inline void reset(void) - { - m_index_1= VIEW_TABLE; - m_index_2= 0; - } - - inline bool has_more_view(void) - { return (m_index_1 <= VIEW_FUNCTION); } - - inline void next_view(void) - { - m_index_1++; - m_index_2= 0; - } -}; - -/** Table PERFORMANCE_SCHEMA.SETUP_OBJECTS. */ -class table_setup_objects : public PFS_engine_table -{ -public: - /** Table share. */ - static PFS_engine_table_share m_share; - static PFS_engine_table* create(); - static int write_row(TABLE *table, unsigned char *buf, Field **fields); - static int delete_all_rows(); - - virtual int rnd_next(); - virtual int rnd_pos(const void *pos); - virtual void reset_position(void); - -protected: - virtual int read_row_values(TABLE *table, - unsigned char *buf, - Field **fields, - bool read_all); - - virtual int update_row_values(TABLE *table, - const unsigned char *old_buf, - unsigned char *new_buf, - Field **fields); - - table_setup_objects(); - -public: - ~table_setup_objects() - {} - -private: - void make_row(PFS_table_share *share); - - /** Table share lock. */ - static THR_LOCK m_table_lock; - /** Fields definition. */ - static TABLE_FIELD_DEF m_field_def; - - /** Current row. */ - row_setup_objects m_row; - /** True is the current row exists. */ - bool m_row_exists; - /** Current position. */ - pos_setup_objects m_pos; - /** Next position. */ - pos_setup_objects m_next_pos; -}; - -/** @} */ -#endif diff --git a/storage/perfschema/table_processlist.cc b/storage/perfschema/table_threads.cc similarity index 80% rename from storage/perfschema/table_processlist.cc rename to storage/perfschema/table_threads.cc index 06c628c5f80..bba7806cab9 100644 --- a/storage/perfschema/table_processlist.cc +++ b/storage/perfschema/table_threads.cc @@ -14,17 +14,17 @@ 51 Franklin Street, Suite 500, Boston, MA 02110-1335 USA */ /** - @file storage/perfschema/table_processlist.cc - Table PROCESSLIST (implementation). + @file storage/perfschema/table_threads.cc + Table THREADS (implementation). */ #include "my_global.h" #include "my_pthread.h" -#include "table_processlist.h" +#include "table_threads.h" #include "pfs_instr_class.h" #include "pfs_instr.h" -THR_LOCK table_processlist::m_table_lock; +THR_LOCK table_threads::m_table_lock; static const TABLE_FIELD_TYPE field_types[]= { @@ -46,15 +46,15 @@ static const TABLE_FIELD_TYPE field_types[]= }; TABLE_FIELD_DEF -table_processlist::m_field_def= +table_threads::m_field_def= { 3, field_types }; PFS_engine_table_share -table_processlist::m_share= +table_threads::m_share= { - { C_STRING_WITH_LEN("PROCESSLIST") }, + { C_STRING_WITH_LEN("THREADS") }, &pfs_readonly_acl, - &table_processlist::create, + &table_threads::create, NULL, /* write_row */ NULL, /* delete_all_rows */ 1000, /* records */ @@ -64,23 +64,23 @@ table_processlist::m_share= false /* checked */ }; -PFS_engine_table* table_processlist::create(void) +PFS_engine_table* table_threads::create(void) { - return new table_processlist(); + return new table_threads(); } -table_processlist::table_processlist() +table_threads::table_threads() : PFS_engine_table(&m_share, &m_pos), m_row_exists(false), m_pos(0), m_next_pos(0) {} -void table_processlist::reset_position(void) +void table_threads::reset_position(void) { m_pos.m_index= 0; m_next_pos.m_index= 0; } -int table_processlist::rnd_next(void) +int table_threads::rnd_next(void) { PFS_thread *pfs; @@ -100,7 +100,7 @@ int table_processlist::rnd_next(void) return HA_ERR_END_OF_FILE; } -int table_processlist::rnd_pos(const void *pos) +int table_threads::rnd_pos(const void *pos) { PFS_thread *pfs; @@ -116,7 +116,7 @@ int table_processlist::rnd_pos(const void *pos) return HA_ERR_RECORD_DELETED; } -void table_processlist::make_row(PFS_thread *pfs) +void table_threads::make_row(PFS_thread *pfs) { pfs_lock lock; PFS_thread_class *safe_class; @@ -139,10 +139,10 @@ void table_processlist::make_row(PFS_thread *pfs) m_row_exists= true; } -int table_processlist::read_row_values(TABLE *table, - unsigned char *, - Field **fields, - bool read_all) +int table_threads::read_row_values(TABLE *table, + unsigned char *, + Field **fields, + bool read_all) { Field *f; diff --git a/storage/perfschema/table_processlist.h b/storage/perfschema/table_threads.h similarity index 83% rename from storage/perfschema/table_processlist.h rename to storage/perfschema/table_threads.h index d4fe5e4af1a..9df323f6d82 100644 --- a/storage/perfschema/table_processlist.h +++ b/storage/perfschema/table_threads.h @@ -13,12 +13,12 @@ along with this program; if not, write to the Free Software Foundation, 51 Franklin Street, Suite 500, Boston, MA 02110-1335 USA */ -#ifndef TABLE_PROCESSIST_H -#define TABLE_PROCESSIST_H +#ifndef TABLE_THREADS_H +#define TABLE_THREADS_H /** - @file storage/perfschema/table_processlist.h - Table PROCESSLIST (declarations). + @file storage/perfschema/table_threads.h + Table THREADS (declarations). */ #include "pfs_column_types.h" @@ -31,8 +31,8 @@ struct PFS_thread; @{ */ -/** A row of PERFORMANCE_SCHEMA.PROCESSLIST. */ -struct row_processlist +/** A row of PERFORMANCE_SCHEMA.THREADS. */ +struct row_threads { /** Column THREAD_ID. */ ulong m_thread_internal_id; @@ -44,8 +44,8 @@ struct row_processlist uint m_name_length; }; -/** Table PERFORMANCE_SCHEMA.PROCESSLIST. */ -class table_processlist : public PFS_engine_table +/** Table PERFORMANCE_SCHEMA.THREADS. */ +class table_threads : public PFS_engine_table { public: /** Table share. */ @@ -63,10 +63,10 @@ protected: bool read_all); protected: - table_processlist(); + table_threads(); public: - ~table_processlist() + ~table_threads() {} private: @@ -78,7 +78,7 @@ private: static TABLE_FIELD_DEF m_field_def; /** Current row. */ - row_processlist m_row; + row_threads m_row; /** True is the current row exists. */ bool m_row_exists; /** Current position. */ From 8b645bed977cbdbec7ab6ece552a6adfaeacf030 Mon Sep 17 00:00:00 2001 From: Alexander Nozdrin Date: Thu, 12 Aug 2010 19:19:57 +0400 Subject: [PATCH 125/129] Patch for Bug#55854 (MySQL AB should not be AUTHOR, copyright incorrect). Fixing copyright text. --- CMakeLists.txt | 4 ++-- client/CMakeLists.txt | 4 ++-- cmd-line-utils/libedit/CMakeLists.txt | 8 ++++---- cmd-line-utils/readline/CMakeLists.txt | 4 ++-- dbug/CMakeLists.txt | 4 ++-- extra/CMakeLists.txt | 5 ++--- extra/yassl/CMakeLists.txt | 4 ++-- extra/yassl/taocrypt/CMakeLists.txt | 4 ++-- include/CMakeLists.txt | 8 ++++---- libmysql/CMakeLists.txt | 4 ++-- libmysqld/CMakeLists.txt | 4 ++-- libmysqld/examples/CMakeLists.txt | 4 ++-- libservices/CMakeLists.txt | 4 ++-- man/CMakeLists.txt | 8 ++++---- mysql-test/CMakeLists.txt | 8 ++++---- mysql-test/lib/My/SafeProcess/CMakeLists.txt | 4 ++-- mysys/CMakeLists.txt | 6 ++---- plugin/audit_null/CMakeLists.txt | 8 ++++---- plugin/audit_null/audit_null.c | 2 +- plugin/daemon_example/CMakeLists.txt | 8 ++++---- plugin/fulltext/CMakeLists.txt | 8 ++++---- plugin/semisync/CMakeLists.txt | 6 ++---- regex/CMakeLists.txt | 5 ++--- scripts/CMakeLists.txt | 4 ++-- sql-bench/CMakeLists.txt | 8 ++++---- sql/CMakeLists.txt | 5 ++--- sql/examples/CMakeLists.txt | 4 ++-- sql/share/CMakeLists.txt | 8 ++++---- storage/archive/CMakeLists.txt | 5 ++--- storage/blackhole/CMakeLists.txt | 5 ++--- storage/csv/CMakeLists.txt | 4 ++-- storage/example/CMakeLists.txt | 4 ++-- storage/federated/CMakeLists.txt | 4 ++-- storage/heap/CMakeLists.txt | 4 ++-- storage/ibmdb2i/CMakeLists.txt | 4 ++-- storage/innobase/CMakeLists.txt | 6 +++--- storage/myisam/CMakeLists.txt | 4 ++-- storage/myisammrg/CMakeLists.txt | 4 ++-- strings/CMakeLists.txt | 4 ++-- support-files/CMakeLists.txt | 8 ++++---- tests/CMakeLists.txt | 4 ++-- unittest/examples/CMakeLists.txt | 5 ++--- unittest/mysys/CMakeLists.txt | 4 ++-- unittest/mytap/CMakeLists.txt | 5 ++--- vio/CMakeLists.txt | 5 ++--- zlib/CMakeLists.txt | 5 ++--- 46 files changed, 112 insertions(+), 125 deletions(-) diff --git a/CMakeLists.txt b/CMakeLists.txt index 3ba9e1cf7f9..eecfa422bf6 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -1,4 +1,4 @@ -# Copyright (C) 2006-2008 MySQL AB, 2009 Sun Microsystems, Inc +# Copyright (c) 2006, 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 @@ -11,7 +11,7 @@ # # 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 +# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA CMAKE_MINIMUM_REQUIRED(VERSION 2.6) # Avoid warnings in higher versions diff --git a/client/CMakeLists.txt b/client/CMakeLists.txt index d0bb8d43edd..771ebf290f1 100644 --- a/client/CMakeLists.txt +++ b/client/CMakeLists.txt @@ -1,4 +1,4 @@ -# Copyright (C) 2006 MySQL AB +# Copyright (c) 2006, 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 @@ -11,7 +11,7 @@ # # 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 +# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA INCLUDE_DIRECTORIES( ${CMAKE_SOURCE_DIR}/include diff --git a/cmd-line-utils/libedit/CMakeLists.txt b/cmd-line-utils/libedit/CMakeLists.txt index 517cbb4211f..b0e375dfcbd 100644 --- a/cmd-line-utils/libedit/CMakeLists.txt +++ b/cmd-line-utils/libedit/CMakeLists.txt @@ -1,17 +1,17 @@ -# Copyright (C) 2009 Sun Microsystems, Inc +# Copyright (c) 2006, 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 +# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA INCLUDE_DIRECTORIES(BEFORE ${CMAKE_CURRENT_SOURCE_DIR} ) INCLUDE(CheckIncludeFile) diff --git a/cmd-line-utils/readline/CMakeLists.txt b/cmd-line-utils/readline/CMakeLists.txt index 506dc1a0ef6..ed6a6b902ea 100644 --- a/cmd-line-utils/readline/CMakeLists.txt +++ b/cmd-line-utils/readline/CMakeLists.txt @@ -1,4 +1,4 @@ -# Copyright (C) 2007 MySQL AB +# Copyright (c) 2006, 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 @@ -11,7 +11,7 @@ # # 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 +# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA INCLUDE_DIRECTORIES(${CMAKE_SOURCE_DIR}/include ${CMAKE_SOURCE_DIR}/cmd-line-utils) diff --git a/dbug/CMakeLists.txt b/dbug/CMakeLists.txt index 4cf6dd88cb7..b0a6eba5d08 100644 --- a/dbug/CMakeLists.txt +++ b/dbug/CMakeLists.txt @@ -1,4 +1,4 @@ -# Copyright (C) 2006 MySQL AB +# Copyright (c) 2006, 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 @@ -11,7 +11,7 @@ # # 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 +# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA INCLUDE_DIRECTORIES( ${CMAKE_SOURCE_DIR}/dbug diff --git a/extra/CMakeLists.txt b/extra/CMakeLists.txt index 27fc31cbdde..a569641a198 100644 --- a/extra/CMakeLists.txt +++ b/extra/CMakeLists.txt @@ -1,4 +1,4 @@ -# Copyright (C) 2006 MySQL AB +# Copyright (c) 2006, 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 @@ -11,8 +11,7 @@ # # 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 - +# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA INCLUDE_DIRECTORIES( ${CMAKE_SOURCE_DIR}/include diff --git a/extra/yassl/CMakeLists.txt b/extra/yassl/CMakeLists.txt index ea991fee8dc..46e1abbc08e 100644 --- a/extra/yassl/CMakeLists.txt +++ b/extra/yassl/CMakeLists.txt @@ -1,4 +1,4 @@ -# Copyright (C) 2006 MySQL AB +# Copyright (c) 2006, 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 @@ -11,7 +11,7 @@ # # 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 +# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA INCLUDE_DIRECTORIES( ${CMAKE_SOURCE_DIR}/include diff --git a/extra/yassl/taocrypt/CMakeLists.txt b/extra/yassl/taocrypt/CMakeLists.txt index 1781ea6f2fa..750731a0449 100644 --- a/extra/yassl/taocrypt/CMakeLists.txt +++ b/extra/yassl/taocrypt/CMakeLists.txt @@ -1,4 +1,4 @@ -# Copyright (C) 2006 MySQL AB +# Copyright (c) 2006, 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 @@ -11,7 +11,7 @@ # # 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 +# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA INCLUDE_DIRECTORIES(${CMAKE_SOURCE_DIR}/extra/yassl/taocrypt/mySTL ${CMAKE_SOURCE_DIR}/extra/yassl/taocrypt/include) diff --git a/include/CMakeLists.txt b/include/CMakeLists.txt index c3922231047..aee7561d242 100644 --- a/include/CMakeLists.txt +++ b/include/CMakeLists.txt @@ -1,17 +1,17 @@ -# Copyright (C) 2009 Sun Microsystems, Inc +# Copyright (c) 2006, 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 +# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA SET(HEADERS_GEN_CONFIGURE ${CMAKE_CURRENT_BINARY_DIR}/mysql_version.h diff --git a/libmysql/CMakeLists.txt b/libmysql/CMakeLists.txt index 2ae09c1707a..0de582a0212 100644 --- a/libmysql/CMakeLists.txt +++ b/libmysql/CMakeLists.txt @@ -1,4 +1,4 @@ -# Copyright (C) 2006 MySQL AB +# Copyright (c) 2006, 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 @@ -11,7 +11,7 @@ # # 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 +# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA INCLUDE_DIRECTORIES( ${CMAKE_SOURCE_DIR}/include diff --git a/libmysqld/CMakeLists.txt b/libmysqld/CMakeLists.txt index a7efcb024ec..61724d73c9a 100644 --- a/libmysqld/CMakeLists.txt +++ b/libmysqld/CMakeLists.txt @@ -1,4 +1,4 @@ -# Copyright (C) 2006 MySQL AB +# Copyright (c) 2006, 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 @@ -11,7 +11,7 @@ # # 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 +# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA ADD_DEFINITIONS(-DMYSQL_SERVER -DEMBEDDED_LIBRARY ${SSL_DEFINES}) diff --git a/libmysqld/examples/CMakeLists.txt b/libmysqld/examples/CMakeLists.txt index f98470a2047..f4a888c10ef 100644 --- a/libmysqld/examples/CMakeLists.txt +++ b/libmysqld/examples/CMakeLists.txt @@ -1,4 +1,4 @@ -# Copyright (C) 2006 MySQL AB +# Copyright (c) 2006, 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 @@ -11,7 +11,7 @@ # # 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 +# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA INCLUDE_DIRECTORIES(${CMAKE_SOURCE_DIR}/include ${CMAKE_SOURCE_DIR}/libmysqld/include diff --git a/libservices/CMakeLists.txt b/libservices/CMakeLists.txt index da84368b46c..79431ff65fe 100644 --- a/libservices/CMakeLists.txt +++ b/libservices/CMakeLists.txt @@ -1,4 +1,4 @@ -# Copyright (C) 2006 MySQL AB +# Copyright (c) 2006, 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 @@ -11,7 +11,7 @@ # # 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 +# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA INCLUDE_DIRECTORIES(${CMAKE_SOURCE_DIR}/include) diff --git a/man/CMakeLists.txt b/man/CMakeLists.txt index 1113b73fd8d..7c96deada08 100644 --- a/man/CMakeLists.txt +++ b/man/CMakeLists.txt @@ -1,17 +1,17 @@ -# Copyright (C) 2009 Sun Microsystems, Inc +# Copyright (c) 2006, 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 +# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA # Copy man pages FILE(GLOB MAN1_FILES *.1) diff --git a/mysql-test/CMakeLists.txt b/mysql-test/CMakeLists.txt index 9745699b61d..6ba53bd9c2c 100644 --- a/mysql-test/CMakeLists.txt +++ b/mysql-test/CMakeLists.txt @@ -1,17 +1,17 @@ -# Copyright (C) 2009 Sun Microsystems, Inc +# Copyright (c) 2006, 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 +# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA INSTALL( DIRECTORY . diff --git a/mysql-test/lib/My/SafeProcess/CMakeLists.txt b/mysql-test/lib/My/SafeProcess/CMakeLists.txt index f79c2d450b9..810096805c8 100644 --- a/mysql-test/lib/My/SafeProcess/CMakeLists.txt +++ b/mysql-test/lib/My/SafeProcess/CMakeLists.txt @@ -1,4 +1,4 @@ -# Copyright (C) 2006 MySQL AB +# Copyright (c) 2006, 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 @@ -11,7 +11,7 @@ # # 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 +# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA SET(INSTALL_ARGS DESTINATION "${INSTALL_MYSQLTESTDIR}/lib/My/SafeProcess" diff --git a/mysys/CMakeLists.txt b/mysys/CMakeLists.txt index ae41151a981..49a2e4f6728 100644 --- a/mysys/CMakeLists.txt +++ b/mysys/CMakeLists.txt @@ -1,4 +1,4 @@ -# Copyright (C) 2006 MySQL AB, 2009 Sun Microsystems, Inc +# Copyright (c) 2006, 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 @@ -11,9 +11,7 @@ # # 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 - - +# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA INCLUDE_DIRECTORIES(${ZLIB_INCLUDE_DIR} ${CMAKE_SOURCE_DIR}/include ${CMAKE_SOURCE_DIR}/mysys) diff --git a/plugin/audit_null/CMakeLists.txt b/plugin/audit_null/CMakeLists.txt index 4baa1da35fe..b88c4922f60 100644 --- a/plugin/audit_null/CMakeLists.txt +++ b/plugin/audit_null/CMakeLists.txt @@ -1,17 +1,17 @@ -# Copyright (C) 2010 Sun Microsystems, Inc +# Copyright (c) 2006, 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 +# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA MYSQL_ADD_PLUGIN(audit_null audit_null.c MODULE_ONLY MODULE_OUTPUT_NAME "adt_null") diff --git a/plugin/audit_null/audit_null.c b/plugin/audit_null/audit_null.c index e0c53ed0f19..4d231d3e39b 100644 --- a/plugin/audit_null/audit_null.c +++ b/plugin/audit_null/audit_null.c @@ -144,7 +144,7 @@ mysql_declare_plugin(audit_null) MYSQL_AUDIT_PLUGIN, /* type */ &audit_null_descriptor, /* descriptor */ "NULL_AUDIT", /* name */ - "MySQL AB", /* author */ + "Oracle Corp", /* author */ "Simple NULL Audit", /* description */ PLUGIN_LICENSE_GPL, audit_null_plugin_init, /* init function (when loaded) */ diff --git a/plugin/daemon_example/CMakeLists.txt b/plugin/daemon_example/CMakeLists.txt index de4310b0244..60aa00687ba 100644 --- a/plugin/daemon_example/CMakeLists.txt +++ b/plugin/daemon_example/CMakeLists.txt @@ -1,17 +1,17 @@ -# Copyright (C) 2009 Sun Microsystems, Inc +# Copyright (c) 2006, 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 +# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA MYSQL_ADD_PLUGIN(daemon_example daemon_example.cc MODULE_ONLY MODULE_OUTPUT_NAME "libdaemon_example") diff --git a/plugin/fulltext/CMakeLists.txt b/plugin/fulltext/CMakeLists.txt index 394cb8dc51d..305ae7fe143 100644 --- a/plugin/fulltext/CMakeLists.txt +++ b/plugin/fulltext/CMakeLists.txt @@ -1,17 +1,17 @@ -# Copyright (C) 2009 Sun Microsystems, Inc +# Copyright (c) 2006, 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 +# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA MYSQL_ADD_PLUGIN(ftexample plugin_example.c MODULE_ONLY MODULE_OUTPUT_NAME "mypluglib") diff --git a/plugin/semisync/CMakeLists.txt b/plugin/semisync/CMakeLists.txt index 2ebd67292f3..f1ada507f4f 100644 --- a/plugin/semisync/CMakeLists.txt +++ b/plugin/semisync/CMakeLists.txt @@ -1,4 +1,4 @@ -# Copyright (C) 2009 Sun Microsystems,Inc +# Copyright (c) 2006, 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 @@ -11,9 +11,7 @@ # # 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 - - +# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA SET(SEMISYNC_MASTER_SOURCES semisync.cc semisync_master.cc semisync_master_plugin.cc diff --git a/regex/CMakeLists.txt b/regex/CMakeLists.txt index 02132eefaad..83c13015671 100644 --- a/regex/CMakeLists.txt +++ b/regex/CMakeLists.txt @@ -1,4 +1,4 @@ -# Copyright (C) 2006 MySQL AB +# Copyright (c) 2006, 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 @@ -11,8 +11,7 @@ # # 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 - +# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA INCLUDE_DIRECTORIES(${CMAKE_SOURCE_DIR}/include) diff --git a/scripts/CMakeLists.txt b/scripts/CMakeLists.txt index 5180206c529..c7eafac2781 100644 --- a/scripts/CMakeLists.txt +++ b/scripts/CMakeLists.txt @@ -1,3 +1,4 @@ +# Copyright (c) 2006, 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 @@ -10,8 +11,7 @@ # # 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 - +# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA # Build comp_sql - used for embedding SQL in C or C++ programs IF(NOT CMAKE_CROSSCOMPILING) diff --git a/sql-bench/CMakeLists.txt b/sql-bench/CMakeLists.txt index 95f69fd2a8e..f8be18c6653 100644 --- a/sql-bench/CMakeLists.txt +++ b/sql-bench/CMakeLists.txt @@ -1,17 +1,17 @@ -# Copyright (C) 2009 Sun Microsystems, Inc +# Copyright (c) 2006, 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 +# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA # Install sql-bench files diff --git a/sql/CMakeLists.txt b/sql/CMakeLists.txt index 943d6b2eece..06e1a77e33e 100644 --- a/sql/CMakeLists.txt +++ b/sql/CMakeLists.txt @@ -1,4 +1,4 @@ -# Copyright (C) 2006 MySQL AB +# Copyright (c) 2006, 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 @@ -11,8 +11,7 @@ # # 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 - +# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA INCLUDE_DIRECTORIES( ${CMAKE_SOURCE_DIR}/include diff --git a/sql/examples/CMakeLists.txt b/sql/examples/CMakeLists.txt index 3c5cc23ec3b..abe4de402bf 100644 --- a/sql/examples/CMakeLists.txt +++ b/sql/examples/CMakeLists.txt @@ -1,4 +1,4 @@ -# Copyright (C) 2006 MySQL AB +# Copyright (c) 2006, 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 @@ -11,7 +11,7 @@ # # 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 +# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA SET(CMAKE_CXX_FLAGS_DEBUG "${CMAKE_CXX_FLAGS_DEBUG} -DSAFE_MUTEX") SET(CMAKE_C_FLAGS_DEBUG "${CMAKE_C_FLAGS_DEBUG} -DSAFE_MUTEX") diff --git a/sql/share/CMakeLists.txt b/sql/share/CMakeLists.txt index 14de851aaa2..f8fd51fda23 100644 --- a/sql/share/CMakeLists.txt +++ b/sql/share/CMakeLists.txt @@ -1,17 +1,17 @@ -# Copyright (C) 2009 Sun Microsystems, Inc +# Copyright (c) 2006, 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 +# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA SET (dirs danish diff --git a/storage/archive/CMakeLists.txt b/storage/archive/CMakeLists.txt index d47fd254b0e..78fb95c0d26 100644 --- a/storage/archive/CMakeLists.txt +++ b/storage/archive/CMakeLists.txt @@ -1,4 +1,4 @@ -# Copyright (C) 2006 MySQL AB +# Copyright (c) 2006, 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 @@ -11,8 +11,7 @@ # # 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 - +# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA SET(ARCHIVE_SOURCES azio.c ha_archive.cc ha_archive.h) MYSQL_ADD_PLUGIN(archive ${ARCHIVE_SOURCES} STORAGE_ENGINE LINK_LIBRARIES ${ZLIB_LIBRARY}) diff --git a/storage/blackhole/CMakeLists.txt b/storage/blackhole/CMakeLists.txt index 5a4bb3fe607..bc14fdde0c1 100644 --- a/storage/blackhole/CMakeLists.txt +++ b/storage/blackhole/CMakeLists.txt @@ -1,4 +1,4 @@ -# Copyright (C) 2006 MySQL AB +# Copyright (c) 2006, 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 @@ -11,8 +11,7 @@ # # 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 - +# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA SET(BLACKHOLE_SOURCES ha_blackhole.cc ha_blackhole.h) MYSQL_ADD_PLUGIN(blackhole ${BLACKHOLE_SOURCES} STORAGE_ENGINE) diff --git a/storage/csv/CMakeLists.txt b/storage/csv/CMakeLists.txt index 73d1794a369..910942325b9 100644 --- a/storage/csv/CMakeLists.txt +++ b/storage/csv/CMakeLists.txt @@ -1,4 +1,4 @@ -# Copyright (C) 2006 MySQL AB +# Copyright (c) 2006, 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 @@ -11,7 +11,7 @@ # # 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 +# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA SET(CSV_PLUGIN_STATIC "csv") SET(CSV_PLUGIN_MANDATORY TRUE) diff --git a/storage/example/CMakeLists.txt b/storage/example/CMakeLists.txt index 5a6f5d78c6b..3d94d09f075 100644 --- a/storage/example/CMakeLists.txt +++ b/storage/example/CMakeLists.txt @@ -1,4 +1,4 @@ -# Copyright (C) 2006 MySQL AB +# Copyright (c) 2006, 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 @@ -11,7 +11,7 @@ # # 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 +# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA SET(EXAMPLE_PLUGIN_DYNAMIC "ha_example") SET(EXAMPLE_SOURCES ha_example.cc) diff --git a/storage/federated/CMakeLists.txt b/storage/federated/CMakeLists.txt index ac55543f276..74f29b1f8bd 100644 --- a/storage/federated/CMakeLists.txt +++ b/storage/federated/CMakeLists.txt @@ -1,4 +1,4 @@ -# Copyright (C) 2006 MySQL AB +# Copyright (c) 2006, 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 @@ -11,7 +11,7 @@ # # 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 +# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA SET(FEDERATED_PLUGIN_STATIC "federated") SET(FEDERATED_PLUGIN_DYNAMIC "ha_federated") diff --git a/storage/heap/CMakeLists.txt b/storage/heap/CMakeLists.txt index 2c0b65b0cc4..8f3c1be809f 100644 --- a/storage/heap/CMakeLists.txt +++ b/storage/heap/CMakeLists.txt @@ -1,4 +1,4 @@ -# Copyright (C) 2006 MySQL AB +# Copyright (c) 2006, 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 @@ -11,7 +11,7 @@ # # 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 +# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA SET(HEAP_PLUGIN_STATIC "heap") SET(HEAP_PLUGIN_MANDATORY TRUE) diff --git a/storage/ibmdb2i/CMakeLists.txt b/storage/ibmdb2i/CMakeLists.txt index e8db6989583..54da2b00ef2 100644 --- a/storage/ibmdb2i/CMakeLists.txt +++ b/storage/ibmdb2i/CMakeLists.txt @@ -1,4 +1,4 @@ -# Copyright (C) 2006 MySQL AB +# Copyright (c) 2006, 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 @@ -11,7 +11,7 @@ # # 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 +# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA CHECK_INCLUDE_FILES(qlgusr.h HAVE_PASE_ENVIRONMENT) IF(HAVE_PASE_ENVIRONMENT) diff --git a/storage/innobase/CMakeLists.txt b/storage/innobase/CMakeLists.txt index 2575580d646..e993aa0d96a 100644 --- a/storage/innobase/CMakeLists.txt +++ b/storage/innobase/CMakeLists.txt @@ -1,5 +1,5 @@ -# Copyright (C) 2009 Oracle/Innobase Oy -# +# Copyright (c) 2006, 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. @@ -11,7 +11,7 @@ # # 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 +# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA # This is the CMakeLists for InnoDB Plugin diff --git a/storage/myisam/CMakeLists.txt b/storage/myisam/CMakeLists.txt index b057a62a6dd..487fbded2df 100644 --- a/storage/myisam/CMakeLists.txt +++ b/storage/myisam/CMakeLists.txt @@ -1,4 +1,4 @@ -# Copyright (C) 2006 MySQL AB +# Copyright (c) 2006, 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 @@ -11,7 +11,7 @@ # # 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 +# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA SET(MYISAM_SOURCES ft_boolean_search.c ft_nlq_search.c ft_parser.c ft_static.c ha_myisam.cc diff --git a/storage/myisammrg/CMakeLists.txt b/storage/myisammrg/CMakeLists.txt index 739bcd565bc..eec3ca783dc 100644 --- a/storage/myisammrg/CMakeLists.txt +++ b/storage/myisammrg/CMakeLists.txt @@ -1,4 +1,4 @@ -# Copyright (C) 2006 MySQL AB +# Copyright (c) 2006, 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 @@ -11,7 +11,7 @@ # # 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 +# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA SET(MYISAMMRG_SOURCES myrg_close.c myrg_create.c myrg_delete.c myrg_extra.c myrg_info.c ha_myisammrg.cc diff --git a/strings/CMakeLists.txt b/strings/CMakeLists.txt index e1e14f20218..552bf942700 100644 --- a/strings/CMakeLists.txt +++ b/strings/CMakeLists.txt @@ -1,4 +1,4 @@ -# Copyright (C) 2006 MySQL AB +# Copyright (c) 2006, 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 @@ -11,7 +11,7 @@ # # 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 +# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA INCLUDE_DIRECTORIES(${CMAKE_SOURCE_DIR}/include) diff --git a/support-files/CMakeLists.txt b/support-files/CMakeLists.txt index 72c4d1ab2d0..ef676c8ee2a 100644 --- a/support-files/CMakeLists.txt +++ b/support-files/CMakeLists.txt @@ -1,17 +1,17 @@ -# Copyright (C) 2009 Sun Microsystems, Inc +# Copyright (c) 2006, 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 +# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA IF(WIN32) SET(localstatedir "C:\\mysql\\data") diff --git a/tests/CMakeLists.txt b/tests/CMakeLists.txt index b0e3342b1bc..8bd6320ba62 100644 --- a/tests/CMakeLists.txt +++ b/tests/CMakeLists.txt @@ -1,4 +1,4 @@ -# Copyright (C) 2006 MySQL AB +# Copyright (c) 2006, 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 @@ -11,7 +11,7 @@ # # 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 +# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA ADD_DEFINITIONS("-DMYSQL_CLIENT") diff --git a/unittest/examples/CMakeLists.txt b/unittest/examples/CMakeLists.txt index a5aa5a93985..52272bc412e 100644 --- a/unittest/examples/CMakeLists.txt +++ b/unittest/examples/CMakeLists.txt @@ -1,4 +1,4 @@ -# Copyright (C) 2007 MySQL AB +# Copyright (c) 2006, 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 @@ -11,8 +11,7 @@ # # 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 - +# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA INCLUDE_DIRECTORIES(${CMAKE_SOURCE_DIR}/include ${CMAKE_SOURCE_DIR}/zlib ${CMAKE_SOURCE_DIR}/sql diff --git a/unittest/mysys/CMakeLists.txt b/unittest/mysys/CMakeLists.txt index 56a3d67f25f..f23a5addba0 100644 --- a/unittest/mysys/CMakeLists.txt +++ b/unittest/mysys/CMakeLists.txt @@ -1,4 +1,4 @@ -# Copyright (C) 2007 MySQL AB, 2009 Sun Microsystems,Inc +# Copyright (c) 2006, 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 @@ -11,7 +11,7 @@ # # 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 +# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA INCLUDE_DIRECTORIES(${CMAKE_SOURCE_DIR}/include ${CMAKE_SOURCE_DIR}/sql diff --git a/unittest/mytap/CMakeLists.txt b/unittest/mytap/CMakeLists.txt index 8a2f6c9639a..c4f213e338a 100644 --- a/unittest/mytap/CMakeLists.txt +++ b/unittest/mytap/CMakeLists.txt @@ -1,4 +1,4 @@ -# Copyright (C) 2007 MySQL AB, 2009 Sun Microsystems, Inc +# Copyright (c) 2006, 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 @@ -11,8 +11,7 @@ # # 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 - +# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA INCLUDE_DIRECTORIES(${CMAKE_SOURCE_DIR}/include) ADD_LIBRARY(mytap tap.c) diff --git a/vio/CMakeLists.txt b/vio/CMakeLists.txt index dae2ed2bb2f..e61281a43d8 100644 --- a/vio/CMakeLists.txt +++ b/vio/CMakeLists.txt @@ -1,4 +1,4 @@ -# Copyright (C) 2006 MySQL AB +# Copyright (c) 2006, 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 @@ -11,8 +11,7 @@ # # 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 - +# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA INCLUDE_DIRECTORIES(${CMAKE_SOURCE_DIR}/include ${SSL_INCLUDE_DIRS}) diff --git a/zlib/CMakeLists.txt b/zlib/CMakeLists.txt index 4be153bfdfa..68799947e44 100644 --- a/zlib/CMakeLists.txt +++ b/zlib/CMakeLists.txt @@ -1,4 +1,4 @@ -# Copyright (C) 2006 MySQL AB +# Copyright (c) 2006, 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 @@ -11,8 +11,7 @@ # # 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 - +# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA INCLUDE_DIRECTORIES( ${CMAKE_SOURCE_DIR}/include From daf0e6b725ec0866ee79d02db26ab4b04954151f Mon Sep 17 00:00:00 2001 From: Mattias Jonsson Date: Fri, 13 Aug 2010 09:50:25 +0200 Subject: [PATCH 126/129] Bug#53676: Unexpected errors and possible table corruption on ADD PARTITION and LOCK TABLE Bug#53770: Server crash at handler.cc:2076 on LOAD DATA after timed out COALESCE PARTITION 5.5 fix for: Bug#51042: REORGANIZE PARTITION can leave table in an inconsistent state in case of crash Needs to be back-ported to 5.1 5.5 fix for: Bug#50418: DROP PARTITION does not interact with transactions Main problem was non-persistent operations done before meta-data lock was taken (53770+53676). And 53676 needed to keep the table/partitions opened and locked while copying the data to the new partitions. Also added thorough tests to spot some additional bugs in the ddl_log code, which could result in bad state between the .frm and partitions. Collapsed patch, includes all fixes required from the reviewers. mysql-test/r/partition_innodb.result: updated result with new test mysql-test/suite/parts/inc/partition_crash.inc: crash test include file mysql-test/suite/parts/inc/partition_crash_add.inc: test all states in fast_alter_partition_table ADD PARTITION branch mysql-test/suite/parts/inc/partition_crash_change.inc: test all states in fast_alter_partition_table CHANGE PARTITION branch mysql-test/suite/parts/inc/partition_crash_drop.inc: test all states in fast_alter_partition_table DROP PARTITION branch mysql-test/suite/parts/inc/partition_fail.inc: recovery test including injecting errors mysql-test/suite/parts/inc/partition_fail_add.inc: test all states in fast_alter_partition_table ADD PARTITION branch mysql-test/suite/parts/inc/partition_fail_change.inc: test all states in fast_alter_partition_table CHANGE PARTITION branch mysql-test/suite/parts/inc/partition_fail_drop.inc: test all states in fast_alter_partition_table DROP PARTITION branch mysql-test/suite/parts/inc/partition_mgm_crash.inc: include file that runs all crash and failure injection tests. mysql-test/suite/parts/r/partition_debug_innodb.result: new test result file mysql-test/suite/parts/r/partition_debug_myisam.result: new test result file mysql-test/suite/parts/r/partition_special_innodb.result: updated result mysql-test/suite/parts/r/partition_special_myisam.result: updated result mysql-test/suite/parts/t/partition_debug_innodb-master.opt: opt file for using with crashing tests of partitioned innodb mysql-test/suite/parts/t/partition_debug_innodb.test: partitioned innodb test that require debug builds mysql-test/suite/parts/t/partition_debug_myisam-master.opt: opt file for using with crashing tests of partitioned myisam mysql-test/suite/parts/t/partition_debug_myisam.test: partitioned myisam test that require debug builds mysql-test/suite/parts/t/partition_special_innodb-master.opt: added innodb-file-per-table to easier verify partition status on disk mysql-test/suite/parts/t/partition_special_innodb.test: added test case mysql-test/suite/parts/t/partition_special_myisam.test: added test case mysql-test/t/partition_innodb.test: added test case sql/sql_base.cc: Moved alter_close_tables to sql_partition.cc sql/sql_base.h: removed some non existing and duplicated functions. sql/sql_partition.cc: fast_alter_partition_table: Spletted abort_and_upgrad_lock_and_close_table to its parts (wait_while_table_is_used and alter_close_tables) and always have wait_while_table_is_used before any persistent operations (including logs, which will be executed on failure) and alter_close_tables after create/read/write operations and before drop operations. moved alter_close_tables here from sql_base.cc Added error injections for better test coverage. write_log_final_change_partition: fixed a log_entry linking bug (delete_frm was not linked to change/drop partition) and drop partition must be executed before change partition (change partition can rename a partition to an old name, like REORG p1 INTO (p1,p2). write_log_add_change_partition: need to use drop_frm first, and relinking that entry and reusing its execute entry. sql/sql_table.cc: added initialization of next_active_log_entry. sql/table.h: removed a duplicate declaration. --- mysql-test/r/partition_innodb.result | 62 + .../suite/parts/inc/partition_crash.inc | 28 + .../suite/parts/inc/partition_crash_add.inc | 33 + .../parts/inc/partition_crash_change.inc | 40 + .../suite/parts/inc/partition_crash_drop.inc | 30 + mysql-test/suite/parts/inc/partition_fail.inc | 18 + .../suite/parts/inc/partition_fail_add.inc | 33 + .../suite/parts/inc/partition_fail_change.inc | 40 + .../suite/parts/inc/partition_fail_drop.inc | 30 + .../suite/parts/inc/partition_mgm_crash.inc | 34 + .../parts/r/partition_debug_innodb.result | 3923 +++++++++++++++ .../parts/r/partition_debug_myisam.result | 4256 +++++++++++++++++ .../parts/r/partition_special_innodb.result | 68 + .../parts/r/partition_special_myisam.result | 19 + .../parts/t/partition_debug_innodb-master.opt | 1 + .../suite/parts/t/partition_debug_innodb.test | 26 + .../parts/t/partition_debug_myisam-master.opt | 1 + .../suite/parts/t/partition_debug_myisam.test | 17 + .../t/partition_special_innodb-master.opt | 2 +- .../parts/t/partition_special_innodb.test | 129 + .../parts/t/partition_special_myisam.test | 40 + mysql-test/t/partition_innodb.test | 44 + sql/sql_base.cc | 81 - sql/sql_base.h | 8 - sql/sql_partition.cc | 307 +- sql/sql_table.cc | 1 + sql/table.h | 1 - 27 files changed, 9100 insertions(+), 172 deletions(-) create mode 100644 mysql-test/suite/parts/inc/partition_crash.inc create mode 100644 mysql-test/suite/parts/inc/partition_crash_add.inc create mode 100644 mysql-test/suite/parts/inc/partition_crash_change.inc create mode 100644 mysql-test/suite/parts/inc/partition_crash_drop.inc create mode 100644 mysql-test/suite/parts/inc/partition_fail.inc create mode 100644 mysql-test/suite/parts/inc/partition_fail_add.inc create mode 100644 mysql-test/suite/parts/inc/partition_fail_change.inc create mode 100644 mysql-test/suite/parts/inc/partition_fail_drop.inc create mode 100644 mysql-test/suite/parts/inc/partition_mgm_crash.inc create mode 100644 mysql-test/suite/parts/r/partition_debug_innodb.result create mode 100644 mysql-test/suite/parts/r/partition_debug_myisam.result create mode 100644 mysql-test/suite/parts/t/partition_debug_innodb-master.opt create mode 100644 mysql-test/suite/parts/t/partition_debug_innodb.test create mode 100644 mysql-test/suite/parts/t/partition_debug_myisam-master.opt create mode 100644 mysql-test/suite/parts/t/partition_debug_myisam.test diff --git a/mysql-test/r/partition_innodb.result b/mysql-test/r/partition_innodb.result index 58d014938bf..107ad719e2b 100644 --- a/mysql-test/r/partition_innodb.result +++ b/mysql-test/r/partition_innodb.result @@ -1,5 +1,67 @@ drop table if exists t1, t2; # +# Bug#50418: DROP PARTITION does not interact with transactions +# +CREATE TABLE t1 ( +id INT AUTO_INCREMENT NOT NULL, +name CHAR(50) NOT NULL, +myDate DATE NOT NULL, +PRIMARY KEY (id, myDate), +INDEX idx_date (myDate) +) ENGINE=InnoDB +PARTITION BY RANGE ( TO_DAYS(myDate) ) ( +PARTITION p0 VALUES LESS THAN (734028), +PARTITION p1 VALUES LESS THAN (734029), +PARTITION p2 VALUES LESS THAN (734030), +PARTITION p3 VALUES LESS THAN MAXVALUE +) ; +INSERT INTO t1 VALUES +(NULL, 'Lachlan', '2009-09-13'), +(NULL, 'Clint', '2009-09-13'), +(NULL, 'John', '2009-09-14'), +(NULL, 'Dave', '2009-09-14'), +(NULL, 'Jeremy', '2009-09-15'), +(NULL, 'Scott', '2009-09-15'), +(NULL, 'Jeff', '2009-09-16'), +(NULL, 'Joe', '2009-09-16'); +SET AUTOCOMMIT=0; +SELECT * FROM t1 FOR UPDATE; +id name myDate +1 Lachlan 2009-09-13 +2 Clint 2009-09-13 +3 John 2009-09-14 +4 Dave 2009-09-14 +5 Jeremy 2009-09-15 +6 Scott 2009-09-15 +7 Jeff 2009-09-16 +8 Joe 2009-09-16 +UPDATE t1 SET name = 'Mattias' WHERE id = 7; +SELECT * FROM t1 WHERE id = 7; +id name myDate +7 Mattias 2009-09-16 +# Connection con1 +SET lock_wait_timeout = 1; +# After the patch it will wait and fail on timeout. +ALTER TABLE t1 DROP PARTITION p3; +ERROR HY000: Lock wait timeout exceeded; try restarting transaction +SHOW WARNINGS; +Level Code Message +Error 1205 Lock wait timeout exceeded; try restarting transaction +# Connection default +SELECT * FROM t1; +id name myDate +1 Lachlan 2009-09-13 +2 Clint 2009-09-13 +3 John 2009-09-14 +4 Dave 2009-09-14 +5 Jeremy 2009-09-15 +6 Scott 2009-09-15 +7 Mattias 2009-09-16 +8 Joe 2009-09-16 +# No changes. +COMMIT; +DROP TABLE t1; +# # Bug#51830: Incorrect partition pruning on range partition (regression) # CREATE TABLE t1 (a INT NOT NULL) diff --git a/mysql-test/suite/parts/inc/partition_crash.inc b/mysql-test/suite/parts/inc/partition_crash.inc new file mode 100644 index 00000000000..f18b8728784 --- /dev/null +++ b/mysql-test/suite/parts/inc/partition_crash.inc @@ -0,0 +1,28 @@ +# Include file to decrease test code duplication + +--eval $create_statement +--eval $insert_statement +--echo # State before crash +--replace_result #p# #P# +--list_files $DATADIR/test +SHOW CREATE TABLE t1; +--sorted_result +SELECT * FROM t1; +--exec echo "wait" > $MYSQLTEST_VARDIR/tmp/mysqld.1.expect +--disable_reconnect +# CR_SERVER_LOST +--error 2013 +--eval $crash_statement +--echo # State after crash (before recovery) +--replace_regex /sqlx.*\./sqlx-nnnn_nnnn./ /#p#/#P#/ +--list_files $DATADIR/test +--exec echo "restart" > $MYSQLTEST_VARDIR/tmp/mysqld.1.expect +--enable_reconnect +--source include/wait_until_connected_again.inc +--echo # State after crash recovery +--replace_result #p# #P# +--list_files $DATADIR/test +SHOW CREATE TABLE t1; +--sorted_result +SELECT * FROM t1; +DROP TABLE t1; diff --git a/mysql-test/suite/parts/inc/partition_crash_add.inc b/mysql-test/suite/parts/inc/partition_crash_add.inc new file mode 100644 index 00000000000..c7cec9c8791 --- /dev/null +++ b/mysql-test/suite/parts/inc/partition_crash_add.inc @@ -0,0 +1,33 @@ +# To be used with partition mgm commands like +# ALTER TABLE t1 ADD PARTITION (LIST/RANGE PARTITIONING). +--echo # Crash testing ADD PARTITION +SET SESSION debug="+d,crash_add_partition_1"; +--source suite/parts/inc/partition_crash.inc +SET SESSION debug="-d,crash_add_partition_1"; +SET SESSION debug="+d,crash_add_partition_2"; +--source suite/parts/inc/partition_crash.inc +SET SESSION debug="-d,crash_add_partition_2"; +SET SESSION debug="+d,crash_add_partition_3"; +--source suite/parts/inc/partition_crash.inc +SET SESSION debug="-d,crash_add_partition_3"; +SET SESSION debug="+d,crash_add_partition_4"; +--source suite/parts/inc/partition_crash.inc +SET SESSION debug="-d,crash_add_partition_4"; +SET SESSION debug="+d,crash_add_partition_5"; +--source suite/parts/inc/partition_crash.inc +SET SESSION debug="-d,crash_add_partition_5"; +SET SESSION debug="+d,crash_add_partition_6"; +--source suite/parts/inc/partition_crash.inc +SET SESSION debug="-d,crash_add_partition_6"; +SET SESSION debug="+d,crash_add_partition_7"; +--source suite/parts/inc/partition_crash.inc +SET SESSION debug="-d,crash_add_partition_7"; +SET SESSION debug="+d,crash_add_partition_8"; +--source suite/parts/inc/partition_crash.inc +SET SESSION debug="-d,crash_add_partition_8"; +SET SESSION debug="+d,crash_add_partition_9"; +--source suite/parts/inc/partition_crash.inc +SET SESSION debug="-d,crash_add_partition_9"; +SET SESSION debug="+d,crash_add_partition_10"; +--source suite/parts/inc/partition_crash.inc +SET SESSION debug="-d,crash_add_partition_10"; diff --git a/mysql-test/suite/parts/inc/partition_crash_change.inc b/mysql-test/suite/parts/inc/partition_crash_change.inc new file mode 100644 index 00000000000..2a6630b6537 --- /dev/null +++ b/mysql-test/suite/parts/inc/partition_crash_change.inc @@ -0,0 +1,40 @@ +# To be used with partition mgm commands like +# ALTER TABLE t1 COALESCE/REBUILD/REORGANIZE PARTITION. +--echo # Test change partition (REORGANIZE/REBUILD/COALESCE +--echo # or ADD HASH PARTITION). +SET SESSION debug="+d,crash_change_partition_1"; +--source suite/parts/inc/partition_crash.inc +SET SESSION debug="-d,crash_change_partition_1"; +SET SESSION debug="+d,crash_change_partition_2"; +--source suite/parts/inc/partition_crash.inc +SET SESSION debug="-d,crash_change_partition_2"; +SET SESSION debug="+d,crash_change_partition_3"; +--source suite/parts/inc/partition_crash.inc +SET SESSION debug="-d,crash_change_partition_3"; +SET SESSION debug="+d,crash_change_partition_4"; +--source suite/parts/inc/partition_crash.inc +SET SESSION debug="-d,crash_change_partition_4"; +SET SESSION debug="+d,crash_change_partition_5"; +--source suite/parts/inc/partition_crash.inc +SET SESSION debug="-d,crash_change_partition_5"; +SET SESSION debug="+d,crash_change_partition_6"; +--source suite/parts/inc/partition_crash.inc +SET SESSION debug="-d,crash_change_partition_6"; +SET SESSION debug="+d,crash_change_partition_7"; +--source suite/parts/inc/partition_crash.inc +SET SESSION debug="-d,crash_change_partition_7"; +SET SESSION debug="+d,crash_change_partition_8"; +--source suite/parts/inc/partition_crash.inc +SET SESSION debug="-d,crash_change_partition_8"; +SET SESSION debug="+d,crash_change_partition_9"; +--source suite/parts/inc/partition_crash.inc +SET SESSION debug="-d,crash_change_partition_9"; +SET SESSION debug="+d,crash_change_partition_10"; +--source suite/parts/inc/partition_crash.inc +SET SESSION debug="-d,crash_change_partition_10"; +SET SESSION debug="+d,crash_change_partition_11"; +--source suite/parts/inc/partition_crash.inc +SET SESSION debug="-d,crash_change_partition_11"; +SET SESSION debug="+d,crash_change_partition_12"; +--source suite/parts/inc/partition_crash.inc +SET SESSION debug="-d,crash_change_partition_12"; diff --git a/mysql-test/suite/parts/inc/partition_crash_drop.inc b/mysql-test/suite/parts/inc/partition_crash_drop.inc new file mode 100644 index 00000000000..0e35e126f4e --- /dev/null +++ b/mysql-test/suite/parts/inc/partition_crash_drop.inc @@ -0,0 +1,30 @@ +# To be used with partition mgm commands like +# ALTER TABLE t1 DROP PARTITION. +--echo # Test DROP PARTITION +SET SESSION debug="+d,crash_drop_partition_1"; +--source suite/parts/inc/partition_crash.inc +SET SESSION debug="-d,crash_drop_partition_1"; +SET SESSION debug="+d,crash_drop_partition_2"; +--source suite/parts/inc/partition_crash.inc +SET SESSION debug="-d,crash_drop_partition_2"; +SET SESSION debug="+d,crash_drop_partition_3"; +--source suite/parts/inc/partition_crash.inc +SET SESSION debug="-d,crash_drop_partition_3"; +SET SESSION debug="+d,crash_drop_partition_4"; +--source suite/parts/inc/partition_crash.inc +SET SESSION debug="-d,crash_drop_partition_4"; +SET SESSION debug="+d,crash_drop_partition_5"; +--source suite/parts/inc/partition_crash.inc +SET SESSION debug="-d,crash_drop_partition_5"; +SET SESSION debug="+d,crash_drop_partition_6"; +--source suite/parts/inc/partition_crash.inc +SET SESSION debug="-d,crash_drop_partition_6"; +SET SESSION debug="+d,crash_drop_partition_7"; +--source suite/parts/inc/partition_crash.inc +SET SESSION debug="-d,crash_drop_partition_7"; +SET SESSION debug="+d,crash_drop_partition_8"; +--source suite/parts/inc/partition_crash.inc +SET SESSION debug="-d,crash_drop_partition_8"; +SET SESSION debug="+d,crash_drop_partition_9"; +--source suite/parts/inc/partition_crash.inc +SET SESSION debug="-d,crash_drop_partition_9"; diff --git a/mysql-test/suite/parts/inc/partition_fail.inc b/mysql-test/suite/parts/inc/partition_fail.inc new file mode 100644 index 00000000000..6942b40042a --- /dev/null +++ b/mysql-test/suite/parts/inc/partition_fail.inc @@ -0,0 +1,18 @@ +# Include file to decrease test code duplication + +--eval $create_statement +--eval $insert_statement +--echo # State before failure +--list_files $DATADIR/test +SHOW CREATE TABLE t1; +--sorted_result +SELECT * FROM t1; +--disable_abort_on_error +--eval $fail_statement +--enable_abort_on_error +--echo # State after failure +--list_files $DATADIR/test +SHOW CREATE TABLE t1; +--sorted_result +SELECT * FROM t1; +DROP TABLE t1; diff --git a/mysql-test/suite/parts/inc/partition_fail_add.inc b/mysql-test/suite/parts/inc/partition_fail_add.inc new file mode 100644 index 00000000000..71d09792fd1 --- /dev/null +++ b/mysql-test/suite/parts/inc/partition_fail_add.inc @@ -0,0 +1,33 @@ +# To be used with partition mgm commands like +# ALTER TABLE t1 ADD PARTITION (LIST/RANGE PARTITIONING). +--echo # Error recovery testing ADD PARTITION +SET SESSION debug="+d,fail_add_partition_1"; +--source suite/parts/inc/partition_fail.inc +SET SESSION debug="-d,fail_add_partition_1"; +SET SESSION debug="+d,fail_add_partition_2"; +--source suite/parts/inc/partition_fail.inc +SET SESSION debug="-d,fail_add_partition_2"; +SET SESSION debug="+d,fail_add_partition_3"; +--source suite/parts/inc/partition_fail.inc +SET SESSION debug="-d,fail_add_partition_3"; +SET SESSION debug="+d,fail_add_partition_4"; +--source suite/parts/inc/partition_fail.inc +SET SESSION debug="-d,fail_add_partition_4"; +SET SESSION debug="+d,fail_add_partition_5"; +--source suite/parts/inc/partition_fail.inc +SET SESSION debug="-d,fail_add_partition_5"; +SET SESSION debug="+d,fail_add_partition_6"; +--source suite/parts/inc/partition_fail.inc +SET SESSION debug="-d,fail_add_partition_6"; +SET SESSION debug="+d,fail_add_partition_7"; +--source suite/parts/inc/partition_fail.inc +SET SESSION debug="-d,fail_add_partition_7"; +SET SESSION debug="+d,fail_add_partition_8"; +--source suite/parts/inc/partition_fail.inc +SET SESSION debug="-d,fail_add_partition_8"; +SET SESSION debug="+d,fail_add_partition_9"; +--source suite/parts/inc/partition_fail.inc +SET SESSION debug="-d,fail_add_partition_9"; +SET SESSION debug="+d,fail_add_partition_10"; +--source suite/parts/inc/partition_fail.inc +SET SESSION debug="-d,fail_add_partition_10"; diff --git a/mysql-test/suite/parts/inc/partition_fail_change.inc b/mysql-test/suite/parts/inc/partition_fail_change.inc new file mode 100644 index 00000000000..390dea34fab --- /dev/null +++ b/mysql-test/suite/parts/inc/partition_fail_change.inc @@ -0,0 +1,40 @@ +# To be used with partition mgm commands like +# ALTER TABLE t1 COALESCE/REBUILD/REORGANIZE PARTITION. +--echo # Error recovery change partition (REORGANIZE/REBUILD/COALESCE +--echo # or ADD HASH PARTITION). +SET SESSION debug="+d,fail_change_partition_1"; +--source suite/parts/inc/partition_fail.inc +SET SESSION debug="-d,fail_change_partition_1"; +SET SESSION debug="+d,fail_change_partition_2"; +--source suite/parts/inc/partition_fail.inc +SET SESSION debug="-d,fail_change_partition_2"; +SET SESSION debug="+d,fail_change_partition_3"; +--source suite/parts/inc/partition_fail.inc +SET SESSION debug="-d,fail_change_partition_3"; +SET SESSION debug="+d,fail_change_partition_4"; +--source suite/parts/inc/partition_fail.inc +SET SESSION debug="-d,fail_change_partition_4"; +SET SESSION debug="+d,fail_change_partition_5"; +--source suite/parts/inc/partition_fail.inc +SET SESSION debug="-d,fail_change_partition_5"; +SET SESSION debug="+d,fail_change_partition_6"; +--source suite/parts/inc/partition_fail.inc +SET SESSION debug="-d,fail_change_partition_6"; +SET SESSION debug="+d,fail_change_partition_7"; +--source suite/parts/inc/partition_fail.inc +SET SESSION debug="-d,fail_change_partition_7"; +SET SESSION debug="+d,fail_change_partition_8"; +--source suite/parts/inc/partition_fail.inc +SET SESSION debug="-d,fail_change_partition_8"; +SET SESSION debug="+d,fail_change_partition_9"; +--source suite/parts/inc/partition_fail.inc +SET SESSION debug="-d,fail_change_partition_9"; +SET SESSION debug="+d,fail_change_partition_10"; +--source suite/parts/inc/partition_fail.inc +SET SESSION debug="-d,fail_change_partition_10"; +SET SESSION debug="+d,fail_change_partition_11"; +--source suite/parts/inc/partition_fail.inc +SET SESSION debug="-d,fail_change_partition_11"; +SET SESSION debug="+d,fail_change_partition_12"; +--source suite/parts/inc/partition_fail.inc +SET SESSION debug="-d,fail_change_partition_12"; diff --git a/mysql-test/suite/parts/inc/partition_fail_drop.inc b/mysql-test/suite/parts/inc/partition_fail_drop.inc new file mode 100644 index 00000000000..54a57ba845f --- /dev/null +++ b/mysql-test/suite/parts/inc/partition_fail_drop.inc @@ -0,0 +1,30 @@ +# To be used with partition mgm commands like +# ALTER TABLE t1 DROP PARTITION. +--echo # Error recovery DROP PARTITION +SET SESSION debug="+d,fail_drop_partition_1"; +--source suite/parts/inc/partition_fail.inc +SET SESSION debug="-d,fail_drop_partition_1"; +SET SESSION debug="+d,fail_drop_partition_2"; +--source suite/parts/inc/partition_fail.inc +SET SESSION debug="-d,fail_drop_partition_2"; +SET SESSION debug="+d,fail_drop_partition_3"; +--source suite/parts/inc/partition_fail.inc +SET SESSION debug="-d,fail_drop_partition_3"; +SET SESSION debug="+d,fail_drop_partition_4"; +--source suite/parts/inc/partition_fail.inc +SET SESSION debug="-d,fail_drop_partition_4"; +SET SESSION debug="+d,fail_drop_partition_5"; +--source suite/parts/inc/partition_fail.inc +SET SESSION debug="-d,fail_drop_partition_5"; +SET SESSION debug="+d,fail_drop_partition_6"; +--source suite/parts/inc/partition_fail.inc +SET SESSION debug="-d,fail_drop_partition_6"; +SET SESSION debug="+d,fail_drop_partition_7"; +--source suite/parts/inc/partition_fail.inc +SET SESSION debug="-d,fail_drop_partition_7"; +SET SESSION debug="+d,fail_drop_partition_8"; +--source suite/parts/inc/partition_fail.inc +SET SESSION debug="-d,fail_drop_partition_8"; +SET SESSION debug="+d,fail_drop_partition_9"; +--source suite/parts/inc/partition_fail.inc +SET SESSION debug="-d,fail_drop_partition_9"; diff --git a/mysql-test/suite/parts/inc/partition_mgm_crash.inc b/mysql-test/suite/parts/inc/partition_mgm_crash.inc new file mode 100644 index 00000000000..2148d7ed1b6 --- /dev/null +++ b/mysql-test/suite/parts/inc/partition_mgm_crash.inc @@ -0,0 +1,34 @@ +# collection of tests which crashes the server and checks recovery. +# also using error injection to test recovery of failures. +# uses $DATADIR and $engine + +--echo # +--echo # Bug#53676: Unexpected errors and possible table corruption on +--echo # ADD PARTITION and LOCK TABLE +--echo # Bug#53770: Server crash at handler.cc:2076 on LOAD DATA +--echo # after timed out COALESCE PARTITION +--echo # Extended crash recovery testing of fast_alter_partition_table. +call mtr.add_suppression("Attempting backtrace. You can use the following information to find out"); + +let $create_statement= CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = $engine +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +let $insert_statement= INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); + +let $crash_statement= ALTER TABLE t1 ADD PARTITION +(PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +--source suite/parts/inc/partition_crash_add.inc +let $fail_statement= $crash_statement; +--source suite/parts/inc/partition_fail_add.inc +let $crash_statement= ALTER TABLE t1 DROP PARTITION p10; +--source suite/parts/inc/partition_crash_drop.inc +let $fail_statement= $crash_statement; +--source suite/parts/inc/partition_fail_drop.inc +let $crash_statement= ALTER TABLE t1 REORGANIZE PARTITION p10 INTO +(PARTITION p10 VALUES IN (10,11,12,13,14,15,16,17,18,19), + PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +--source suite/parts/inc/partition_crash_change.inc +let $fail_statement= $crash_statement; +--source suite/parts/inc/partition_fail_change.inc diff --git a/mysql-test/suite/parts/r/partition_debug_innodb.result b/mysql-test/suite/parts/r/partition_debug_innodb.result new file mode 100644 index 00000000000..eb2218e204e --- /dev/null +++ b/mysql-test/suite/parts/r/partition_debug_innodb.result @@ -0,0 +1,3923 @@ +DROP TABLE IF EXISTS t1; +call mtr.add_suppression("InnoDB: Warning: allocated tablespace .*, old maximum was"); +call mtr.add_suppression("InnoDB: Error: table .* does not exist in the InnoDB internal"); +call mtr.add_suppression("InnoDB: Warning: MySQL is trying to drop table "); +# Test crash and failure recovery in fast_alter_partition_table. +# +# Bug#53676: Unexpected errors and possible table corruption on +# ADD PARTITION and LOCK TABLE +# Bug#53770: Server crash at handler.cc:2076 on LOAD DATA +# after timed out COALESCE PARTITION +# Extended crash recovery testing of fast_alter_partition_table. +call mtr.add_suppression("Attempting backtrace. You can use the following information to find out"); +# Crash testing ADD PARTITION +SET SESSION debug="+d,crash_add_partition_1"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'InnoDB' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before crash +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 ADD PARTITION +(PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Lost connection to MySQL server during query +# State after crash (before recovery) +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +# State after crash recovery +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,crash_add_partition_1"; +SET SESSION debug="+d,crash_add_partition_2"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'InnoDB' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before crash +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 ADD PARTITION +(PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Lost connection to MySQL server during query +# State after crash (before recovery) +#sql-t1.frm +#sql-t1.par +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +# State after crash recovery +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,crash_add_partition_2"; +SET SESSION debug="+d,crash_add_partition_3"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'InnoDB' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before crash +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 ADD PARTITION +(PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Lost connection to MySQL server during query +# State after crash (before recovery) +#sql-t1.frm +#sql-t1.par +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +# State after crash recovery +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,crash_add_partition_3"; +SET SESSION debug="+d,crash_add_partition_4"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'InnoDB' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before crash +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 ADD PARTITION +(PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Lost connection to MySQL server during query +# State after crash (before recovery) +#sql-t1.frm +#sql-t1.par +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +# State after crash recovery +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,crash_add_partition_4"; +SET SESSION debug="+d,crash_add_partition_5"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'InnoDB' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before crash +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 ADD PARTITION +(PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Lost connection to MySQL server during query +# State after crash (before recovery) +#sql-t1.frm +#sql-t1.par +t1#P#p0.ibd +t1#P#p10.ibd +t1#P#p20.ibd +t1.frm +t1.par +# State after crash recovery +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,crash_add_partition_5"; +SET SESSION debug="+d,crash_add_partition_6"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'InnoDB' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before crash +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 ADD PARTITION +(PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Lost connection to MySQL server during query +# State after crash (before recovery) +#sql-t1.frm +#sql-t1.par +t1#P#p0.ibd +t1#P#p10.ibd +t1#P#p20.ibd +t1.frm +t1.par +# State after crash recovery +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,crash_add_partition_6"; +SET SESSION debug="+d,crash_add_partition_7"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'InnoDB' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before crash +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 ADD PARTITION +(PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Lost connection to MySQL server during query +# State after crash (before recovery) +#sql-t1.frm +#sql-t1.par +t1#P#p0.ibd +t1#P#p10.ibd +t1#P#p20.ibd +t1.frm +t1.par +# State after crash recovery +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,crash_add_partition_7"; +SET SESSION debug="+d,crash_add_partition_8"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'InnoDB' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before crash +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 ADD PARTITION +(PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Lost connection to MySQL server during query +# State after crash (before recovery) +#sql-t1.frm +#sql-t1.par +t1#P#p0.ibd +t1#P#p10.ibd +t1#P#p20.ibd +t1.frm +t1.par +# State after crash recovery +t1#P#p0.ibd +t1#P#p10.ibd +t1#P#p20.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB, + PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,crash_add_partition_8"; +SET SESSION debug="+d,crash_add_partition_9"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'InnoDB' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before crash +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 ADD PARTITION +(PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Lost connection to MySQL server during query +# State after crash (before recovery) +t1#P#p0.ibd +t1#P#p10.ibd +t1#P#p20.ibd +t1.frm +t1.par +# State after crash recovery +t1#P#p0.ibd +t1#P#p10.ibd +t1#P#p20.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB, + PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,crash_add_partition_9"; +SET SESSION debug="+d,crash_add_partition_10"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'InnoDB' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before crash +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 ADD PARTITION +(PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Lost connection to MySQL server during query +# State after crash (before recovery) +t1#P#p0.ibd +t1#P#p10.ibd +t1#P#p20.ibd +t1.frm +t1.par +# State after crash recovery +t1#P#p0.ibd +t1#P#p10.ibd +t1#P#p20.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB, + PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,crash_add_partition_10"; +# Error recovery testing ADD PARTITION +SET SESSION debug="+d,fail_add_partition_1"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'InnoDB' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before failure +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 ADD PARTITION +(PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Unknown error +# State after failure +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,fail_add_partition_1"; +SET SESSION debug="+d,fail_add_partition_2"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'InnoDB' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before failure +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 ADD PARTITION +(PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Unknown error +# State after failure +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,fail_add_partition_2"; +SET SESSION debug="+d,fail_add_partition_3"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'InnoDB' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before failure +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 ADD PARTITION +(PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Unknown error +# State after failure +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,fail_add_partition_3"; +SET SESSION debug="+d,fail_add_partition_4"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'InnoDB' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before failure +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 ADD PARTITION +(PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Unknown error +# State after failure +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,fail_add_partition_4"; +SET SESSION debug="+d,fail_add_partition_5"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'InnoDB' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before failure +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 ADD PARTITION +(PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Unknown error +# State after failure +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,fail_add_partition_5"; +SET SESSION debug="+d,fail_add_partition_6"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'InnoDB' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before failure +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 ADD PARTITION +(PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Unknown error +# State after failure +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,fail_add_partition_6"; +SET SESSION debug="+d,fail_add_partition_7"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'InnoDB' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before failure +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 ADD PARTITION +(PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Unknown error +# State after failure +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,fail_add_partition_7"; +SET SESSION debug="+d,fail_add_partition_8"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'InnoDB' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before failure +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 ADD PARTITION +(PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Unknown error +# State after failure +t1#P#p0.ibd +t1#P#p10.ibd +t1#P#p20.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB, + PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,fail_add_partition_8"; +SET SESSION debug="+d,fail_add_partition_9"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'InnoDB' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before failure +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 ADD PARTITION +(PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Unknown error +# State after failure +t1#P#p0.ibd +t1#P#p10.ibd +t1#P#p20.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB, + PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,fail_add_partition_9"; +SET SESSION debug="+d,fail_add_partition_10"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'InnoDB' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before failure +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 ADD PARTITION +(PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Unknown error +# State after failure +t1#P#p0.ibd +t1#P#p10.ibd +t1#P#p20.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB, + PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,fail_add_partition_10"; +# Test DROP PARTITION +SET SESSION debug="+d,crash_drop_partition_1"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'InnoDB' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before crash +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 DROP PARTITION p10; +ERROR HY000: Lost connection to MySQL server during query +# State after crash (before recovery) +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +# State after crash recovery +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,crash_drop_partition_1"; +SET SESSION debug="+d,crash_drop_partition_2"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'InnoDB' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before crash +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 DROP PARTITION p10; +ERROR HY000: Lost connection to MySQL server during query +# State after crash (before recovery) +#sql-t1.frm +#sql-t1.par +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +# State after crash recovery +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,crash_drop_partition_2"; +SET SESSION debug="+d,crash_drop_partition_3"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'InnoDB' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before crash +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 DROP PARTITION p10; +ERROR HY000: Lost connection to MySQL server during query +# State after crash (before recovery) +#sql-t1.frm +#sql-t1.par +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +# State after crash recovery +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,crash_drop_partition_3"; +SET SESSION debug="+d,crash_drop_partition_4"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'InnoDB' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before crash +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 DROP PARTITION p10; +ERROR HY000: Lost connection to MySQL server during query +# State after crash (before recovery) +#sql-t1.frm +#sql-t1.par +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +# State after crash recovery +t1#P#p0.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,crash_drop_partition_4"; +SET SESSION debug="+d,crash_drop_partition_5"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'InnoDB' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before crash +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 DROP PARTITION p10; +ERROR HY000: Lost connection to MySQL server during query +# State after crash (before recovery) +#sql-t1.frm +#sql-t1.par +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +# State after crash recovery +t1#P#p0.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,crash_drop_partition_5"; +SET SESSION debug="+d,crash_drop_partition_6"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'InnoDB' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before crash +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 DROP PARTITION p10; +ERROR HY000: Lost connection to MySQL server during query +# State after crash (before recovery) +#sql-t1.frm +#sql-t1.par +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +# State after crash recovery +t1#P#p0.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,crash_drop_partition_6"; +SET SESSION debug="+d,crash_drop_partition_7"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'InnoDB' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before crash +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 DROP PARTITION p10; +ERROR HY000: Lost connection to MySQL server during query +# State after crash (before recovery) +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +# State after crash recovery +t1#P#p0.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,crash_drop_partition_7"; +SET SESSION debug="+d,crash_drop_partition_8"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'InnoDB' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before crash +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 DROP PARTITION p10; +ERROR HY000: Lost connection to MySQL server during query +# State after crash (before recovery) +t1#P#p0.ibd +t1.frm +t1.par +# State after crash recovery +t1#P#p0.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,crash_drop_partition_8"; +SET SESSION debug="+d,crash_drop_partition_9"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'InnoDB' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before crash +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 DROP PARTITION p10; +ERROR HY000: Lost connection to MySQL server during query +# State after crash (before recovery) +t1#P#p0.ibd +t1.frm +t1.par +# State after crash recovery +t1#P#p0.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,crash_drop_partition_9"; +# Error recovery DROP PARTITION +SET SESSION debug="+d,fail_drop_partition_1"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'InnoDB' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before failure +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 DROP PARTITION p10; +ERROR HY000: Unknown error +# State after failure +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,fail_drop_partition_1"; +SET SESSION debug="+d,fail_drop_partition_2"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'InnoDB' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before failure +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 DROP PARTITION p10; +ERROR HY000: Unknown error +# State after failure +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,fail_drop_partition_2"; +SET SESSION debug="+d,fail_drop_partition_3"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'InnoDB' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before failure +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 DROP PARTITION p10; +ERROR HY000: Unknown error +# State after failure +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,fail_drop_partition_3"; +SET SESSION debug="+d,fail_drop_partition_4"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'InnoDB' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before failure +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 DROP PARTITION p10; +ERROR HY000: Unknown error +# State after failure +t1#P#p0.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,fail_drop_partition_4"; +SET SESSION debug="+d,fail_drop_partition_5"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'InnoDB' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before failure +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 DROP PARTITION p10; +ERROR HY000: Unknown error +# State after failure +t1#P#p0.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,fail_drop_partition_5"; +SET SESSION debug="+d,fail_drop_partition_6"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'InnoDB' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before failure +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 DROP PARTITION p10; +ERROR HY000: Unknown error +# State after failure +t1#P#p0.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,fail_drop_partition_6"; +SET SESSION debug="+d,fail_drop_partition_7"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'InnoDB' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before failure +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 DROP PARTITION p10; +ERROR HY000: Unknown error +# State after failure +t1#P#p0.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,fail_drop_partition_7"; +SET SESSION debug="+d,fail_drop_partition_8"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'InnoDB' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before failure +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 DROP PARTITION p10; +ERROR HY000: Unknown error +# State after failure +t1#P#p0.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,fail_drop_partition_8"; +SET SESSION debug="+d,fail_drop_partition_9"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'InnoDB' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before failure +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 DROP PARTITION p10; +ERROR HY000: Unknown error +# State after failure +t1#P#p0.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,fail_drop_partition_9"; +# Test change partition (REORGANIZE/REBUILD/COALESCE +# or ADD HASH PARTITION). +SET SESSION debug="+d,crash_change_partition_1"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'InnoDB' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before crash +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 REORGANIZE PARTITION p10 INTO +(PARTITION p10 VALUES IN (10,11,12,13,14,15,16,17,18,19), +PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Lost connection to MySQL server during query +# State after crash (before recovery) +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +# State after crash recovery +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,crash_change_partition_1"; +SET SESSION debug="+d,crash_change_partition_2"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'InnoDB' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before crash +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 REORGANIZE PARTITION p10 INTO +(PARTITION p10 VALUES IN (10,11,12,13,14,15,16,17,18,19), +PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Lost connection to MySQL server during query +# State after crash (before recovery) +#sql-t1.frm +#sql-t1.par +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +# State after crash recovery +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,crash_change_partition_2"; +SET SESSION debug="+d,crash_change_partition_3"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'InnoDB' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before crash +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 REORGANIZE PARTITION p10 INTO +(PARTITION p10 VALUES IN (10,11,12,13,14,15,16,17,18,19), +PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Lost connection to MySQL server during query +# State after crash (before recovery) +#sql-t1.frm +#sql-t1.par +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +# State after crash recovery +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,crash_change_partition_3"; +SET SESSION debug="+d,crash_change_partition_4"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'InnoDB' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before crash +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 REORGANIZE PARTITION p10 INTO +(PARTITION p10 VALUES IN (10,11,12,13,14,15,16,17,18,19), +PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Lost connection to MySQL server during query +# State after crash (before recovery) +#sql-t1.frm +#sql-t1.par +t1#P#p0.ibd +t1#P#p10#TMP#.ibd +t1#P#p10.ibd +t1#P#p20#TMP#.ibd +t1.frm +t1.par +# State after crash recovery +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,crash_change_partition_4"; +SET SESSION debug="+d,crash_change_partition_5"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'InnoDB' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before crash +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 REORGANIZE PARTITION p10 INTO +(PARTITION p10 VALUES IN (10,11,12,13,14,15,16,17,18,19), +PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Lost connection to MySQL server during query +# State after crash (before recovery) +#sql-t1.frm +#sql-t1.par +t1#P#p0.ibd +t1#P#p10#TMP#.ibd +t1#P#p10.ibd +t1#P#p20#TMP#.ibd +t1.frm +t1.par +# State after crash recovery +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,crash_change_partition_5"; +SET SESSION debug="+d,crash_change_partition_6"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'InnoDB' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before crash +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 REORGANIZE PARTITION p10 INTO +(PARTITION p10 VALUES IN (10,11,12,13,14,15,16,17,18,19), +PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Lost connection to MySQL server during query +# State after crash (before recovery) +#sql-t1.frm +#sql-t1.par +t1#P#p0.ibd +t1#P#p10#TMP#.ibd +t1#P#p10.ibd +t1#P#p20#TMP#.ibd +t1.frm +t1.par +# State after crash recovery +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,crash_change_partition_6"; +SET SESSION debug="+d,crash_change_partition_7"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'InnoDB' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before crash +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 REORGANIZE PARTITION p10 INTO +(PARTITION p10 VALUES IN (10,11,12,13,14,15,16,17,18,19), +PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Lost connection to MySQL server during query +# State after crash (before recovery) +#sql-t1.frm +#sql-t1.par +t1#P#p0.ibd +t1#P#p10#TMP#.ibd +t1#P#p10.ibd +t1#P#p20#TMP#.ibd +t1.frm +t1.par +# State after crash recovery +t1#P#p0.ibd +t1#P#p10.ibd +t1#P#p20.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (10,11,12,13,14,15,16,17,18,19) ENGINE = InnoDB, + PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,crash_change_partition_7"; +SET SESSION debug="+d,crash_change_partition_8"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'InnoDB' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before crash +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 REORGANIZE PARTITION p10 INTO +(PARTITION p10 VALUES IN (10,11,12,13,14,15,16,17,18,19), +PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Lost connection to MySQL server during query +# State after crash (before recovery) +#sql-t1.frm +#sql-t1.par +t1#P#p0.ibd +t1#P#p10#TMP#.ibd +t1#P#p10.ibd +t1#P#p20#TMP#.ibd +t1.frm +t1.par +# State after crash recovery +t1#P#p0.ibd +t1#P#p10.ibd +t1#P#p20.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (10,11,12,13,14,15,16,17,18,19) ENGINE = InnoDB, + PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,crash_change_partition_8"; +SET SESSION debug="+d,crash_change_partition_9"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'InnoDB' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before crash +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 REORGANIZE PARTITION p10 INTO +(PARTITION p10 VALUES IN (10,11,12,13,14,15,16,17,18,19), +PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Lost connection to MySQL server during query +# State after crash (before recovery) +t1#P#p0.ibd +t1#P#p10#TMP#.ibd +t1#P#p10.ibd +t1#P#p20#TMP#.ibd +t1.frm +t1.par +# State after crash recovery +t1#P#p0.ibd +t1#P#p10.ibd +t1#P#p20.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (10,11,12,13,14,15,16,17,18,19) ENGINE = InnoDB, + PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,crash_change_partition_9"; +SET SESSION debug="+d,crash_change_partition_10"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'InnoDB' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before crash +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 REORGANIZE PARTITION p10 INTO +(PARTITION p10 VALUES IN (10,11,12,13,14,15,16,17,18,19), +PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Lost connection to MySQL server during query +# State after crash (before recovery) +t1#P#p0.ibd +t1#P#p10#TMP#.ibd +t1#P#p10.ibd +t1#P#p20#TMP#.ibd +t1.frm +t1.par +# State after crash recovery +t1#P#p0.ibd +t1#P#p10.ibd +t1#P#p20.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (10,11,12,13,14,15,16,17,18,19) ENGINE = InnoDB, + PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,crash_change_partition_10"; +SET SESSION debug="+d,crash_change_partition_11"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'InnoDB' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before crash +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 REORGANIZE PARTITION p10 INTO +(PARTITION p10 VALUES IN (10,11,12,13,14,15,16,17,18,19), +PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Lost connection to MySQL server during query +# State after crash (before recovery) +t1#P#p0.ibd +t1#P#p10.ibd +t1#P#p20.ibd +t1.frm +t1.par +# State after crash recovery +t1#P#p0.ibd +t1#P#p10.ibd +t1#P#p20.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (10,11,12,13,14,15,16,17,18,19) ENGINE = InnoDB, + PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,crash_change_partition_11"; +SET SESSION debug="+d,crash_change_partition_12"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'InnoDB' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before crash +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 REORGANIZE PARTITION p10 INTO +(PARTITION p10 VALUES IN (10,11,12,13,14,15,16,17,18,19), +PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Lost connection to MySQL server during query +# State after crash (before recovery) +t1#P#p0.ibd +t1#P#p10.ibd +t1#P#p20.ibd +t1.frm +t1.par +# State after crash recovery +t1#P#p0.ibd +t1#P#p10.ibd +t1#P#p20.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (10,11,12,13,14,15,16,17,18,19) ENGINE = InnoDB, + PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,crash_change_partition_12"; +# Error recovery change partition (REORGANIZE/REBUILD/COALESCE +# or ADD HASH PARTITION). +SET SESSION debug="+d,fail_change_partition_1"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'InnoDB' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before failure +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 REORGANIZE PARTITION p10 INTO +(PARTITION p10 VALUES IN (10,11,12,13,14,15,16,17,18,19), +PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Unknown error +# State after failure +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,fail_change_partition_1"; +SET SESSION debug="+d,fail_change_partition_2"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'InnoDB' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before failure +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 REORGANIZE PARTITION p10 INTO +(PARTITION p10 VALUES IN (10,11,12,13,14,15,16,17,18,19), +PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Unknown error +# State after failure +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,fail_change_partition_2"; +SET SESSION debug="+d,fail_change_partition_3"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'InnoDB' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before failure +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 REORGANIZE PARTITION p10 INTO +(PARTITION p10 VALUES IN (10,11,12,13,14,15,16,17,18,19), +PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Unknown error +# State after failure +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,fail_change_partition_3"; +SET SESSION debug="+d,fail_change_partition_4"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'InnoDB' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before failure +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 REORGANIZE PARTITION p10 INTO +(PARTITION p10 VALUES IN (10,11,12,13,14,15,16,17,18,19), +PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Unknown error +# State after failure +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,fail_change_partition_4"; +SET SESSION debug="+d,fail_change_partition_5"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'InnoDB' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before failure +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 REORGANIZE PARTITION p10 INTO +(PARTITION p10 VALUES IN (10,11,12,13,14,15,16,17,18,19), +PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Unknown error +# State after failure +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,fail_change_partition_5"; +SET SESSION debug="+d,fail_change_partition_6"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'InnoDB' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before failure +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 REORGANIZE PARTITION p10 INTO +(PARTITION p10 VALUES IN (10,11,12,13,14,15,16,17,18,19), +PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Unknown error +# State after failure +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,fail_change_partition_6"; +SET SESSION debug="+d,fail_change_partition_7"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'InnoDB' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before failure +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 REORGANIZE PARTITION p10 INTO +(PARTITION p10 VALUES IN (10,11,12,13,14,15,16,17,18,19), +PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Unknown error +# State after failure +t1#P#p0.ibd +t1#P#p10.ibd +t1#P#p20.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (10,11,12,13,14,15,16,17,18,19) ENGINE = InnoDB, + PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,fail_change_partition_7"; +SET SESSION debug="+d,fail_change_partition_8"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'InnoDB' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before failure +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 REORGANIZE PARTITION p10 INTO +(PARTITION p10 VALUES IN (10,11,12,13,14,15,16,17,18,19), +PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Unknown error +# State after failure +t1#P#p0.ibd +t1#P#p10.ibd +t1#P#p20.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (10,11,12,13,14,15,16,17,18,19) ENGINE = InnoDB, + PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,fail_change_partition_8"; +SET SESSION debug="+d,fail_change_partition_9"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'InnoDB' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before failure +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 REORGANIZE PARTITION p10 INTO +(PARTITION p10 VALUES IN (10,11,12,13,14,15,16,17,18,19), +PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Unknown error +# State after failure +t1#P#p0.ibd +t1#P#p10.ibd +t1#P#p20.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (10,11,12,13,14,15,16,17,18,19) ENGINE = InnoDB, + PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,fail_change_partition_9"; +SET SESSION debug="+d,fail_change_partition_10"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'InnoDB' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before failure +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 REORGANIZE PARTITION p10 INTO +(PARTITION p10 VALUES IN (10,11,12,13,14,15,16,17,18,19), +PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Unknown error +# State after failure +t1#P#p0.ibd +t1#P#p10.ibd +t1#P#p20.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (10,11,12,13,14,15,16,17,18,19) ENGINE = InnoDB, + PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,fail_change_partition_10"; +SET SESSION debug="+d,fail_change_partition_11"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'InnoDB' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before failure +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 REORGANIZE PARTITION p10 INTO +(PARTITION p10 VALUES IN (10,11,12,13,14,15,16,17,18,19), +PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Unknown error +# State after failure +t1#P#p0.ibd +t1#P#p10.ibd +t1#P#p20.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (10,11,12,13,14,15,16,17,18,19) ENGINE = InnoDB, + PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,fail_change_partition_11"; +SET SESSION debug="+d,fail_change_partition_12"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'InnoDB' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before failure +t1#P#p0.ibd +t1#P#p10.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 REORGANIZE PARTITION p10 INTO +(PARTITION p10 VALUES IN (10,11,12,13,14,15,16,17,18,19), +PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Unknown error +# State after failure +t1#P#p0.ibd +t1#P#p10.ibd +t1#P#p20.ibd +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = InnoDB, + PARTITION p10 VALUES IN (10,11,12,13,14,15,16,17,18,19) ENGINE = InnoDB, + PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29) ENGINE = InnoDB) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,fail_change_partition_12"; diff --git a/mysql-test/suite/parts/r/partition_debug_myisam.result b/mysql-test/suite/parts/r/partition_debug_myisam.result new file mode 100644 index 00000000000..d3f40aedee5 --- /dev/null +++ b/mysql-test/suite/parts/r/partition_debug_myisam.result @@ -0,0 +1,4256 @@ +DROP TABLE IF EXISTS t1; +# Test crash and failure recovery in fast_alter_partition_table. +# +# Bug#53676: Unexpected errors and possible table corruption on +# ADD PARTITION and LOCK TABLE +# Bug#53770: Server crash at handler.cc:2076 on LOAD DATA +# after timed out COALESCE PARTITION +# Extended crash recovery testing of fast_alter_partition_table. +call mtr.add_suppression("Attempting backtrace. You can use the following information to find out"); +# Crash testing ADD PARTITION +SET SESSION debug="+d,crash_add_partition_1"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'MyISAM' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before crash +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 ADD PARTITION +(PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Lost connection to MySQL server during query +# State after crash (before recovery) +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +# State after crash recovery +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,crash_add_partition_1"; +SET SESSION debug="+d,crash_add_partition_2"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'MyISAM' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before crash +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 ADD PARTITION +(PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Lost connection to MySQL server during query +# State after crash (before recovery) +#sql-t1.frm +#sql-t1.par +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +# State after crash recovery +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,crash_add_partition_2"; +SET SESSION debug="+d,crash_add_partition_3"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'MyISAM' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before crash +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 ADD PARTITION +(PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Lost connection to MySQL server during query +# State after crash (before recovery) +#sql-t1.frm +#sql-t1.par +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +# State after crash recovery +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,crash_add_partition_3"; +SET SESSION debug="+d,crash_add_partition_4"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'MyISAM' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before crash +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 ADD PARTITION +(PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Lost connection to MySQL server during query +# State after crash (before recovery) +#sql-t1.frm +#sql-t1.par +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +# State after crash recovery +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,crash_add_partition_4"; +SET SESSION debug="+d,crash_add_partition_5"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'MyISAM' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before crash +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 ADD PARTITION +(PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Lost connection to MySQL server during query +# State after crash (before recovery) +#sql-t1.frm +#sql-t1.par +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1#P#p20.MYD +t1#P#p20.MYI +t1.frm +t1.par +# State after crash recovery +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,crash_add_partition_5"; +SET SESSION debug="+d,crash_add_partition_6"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'MyISAM' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before crash +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 ADD PARTITION +(PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Lost connection to MySQL server during query +# State after crash (before recovery) +#sql-t1.frm +#sql-t1.par +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1#P#p20.MYD +t1#P#p20.MYI +t1.frm +t1.par +# State after crash recovery +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,crash_add_partition_6"; +SET SESSION debug="+d,crash_add_partition_7"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'MyISAM' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before crash +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 ADD PARTITION +(PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Lost connection to MySQL server during query +# State after crash (before recovery) +#sql-t1.frm +#sql-t1.par +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1#P#p20.MYD +t1#P#p20.MYI +t1.frm +t1.par +# State after crash recovery +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,crash_add_partition_7"; +SET SESSION debug="+d,crash_add_partition_8"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'MyISAM' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before crash +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 ADD PARTITION +(PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Lost connection to MySQL server during query +# State after crash (before recovery) +#sql-t1.frm +#sql-t1.par +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1#P#p20.MYD +t1#P#p20.MYI +t1.frm +t1.par +# State after crash recovery +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1#P#p20.MYD +t1#P#p20.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM, + PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,crash_add_partition_8"; +SET SESSION debug="+d,crash_add_partition_9"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'MyISAM' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before crash +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 ADD PARTITION +(PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Lost connection to MySQL server during query +# State after crash (before recovery) +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1#P#p20.MYD +t1#P#p20.MYI +t1.frm +t1.par +# State after crash recovery +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1#P#p20.MYD +t1#P#p20.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM, + PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,crash_add_partition_9"; +SET SESSION debug="+d,crash_add_partition_10"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'MyISAM' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before crash +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 ADD PARTITION +(PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Lost connection to MySQL server during query +# State after crash (before recovery) +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1#P#p20.MYD +t1#P#p20.MYI +t1.frm +t1.par +# State after crash recovery +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1#P#p20.MYD +t1#P#p20.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM, + PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,crash_add_partition_10"; +# Error recovery testing ADD PARTITION +SET SESSION debug="+d,fail_add_partition_1"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'MyISAM' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before failure +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 ADD PARTITION +(PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Unknown error +# State after failure +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,fail_add_partition_1"; +SET SESSION debug="+d,fail_add_partition_2"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'MyISAM' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before failure +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 ADD PARTITION +(PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Unknown error +# State after failure +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,fail_add_partition_2"; +SET SESSION debug="+d,fail_add_partition_3"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'MyISAM' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before failure +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 ADD PARTITION +(PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Unknown error +# State after failure +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,fail_add_partition_3"; +SET SESSION debug="+d,fail_add_partition_4"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'MyISAM' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before failure +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 ADD PARTITION +(PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Unknown error +# State after failure +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,fail_add_partition_4"; +SET SESSION debug="+d,fail_add_partition_5"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'MyISAM' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before failure +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 ADD PARTITION +(PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Unknown error +# State after failure +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,fail_add_partition_5"; +SET SESSION debug="+d,fail_add_partition_6"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'MyISAM' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before failure +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 ADD PARTITION +(PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Unknown error +# State after failure +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,fail_add_partition_6"; +SET SESSION debug="+d,fail_add_partition_7"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'MyISAM' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before failure +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 ADD PARTITION +(PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Unknown error +# State after failure +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,fail_add_partition_7"; +SET SESSION debug="+d,fail_add_partition_8"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'MyISAM' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before failure +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 ADD PARTITION +(PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Unknown error +# State after failure +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1#P#p20.MYD +t1#P#p20.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM, + PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,fail_add_partition_8"; +SET SESSION debug="+d,fail_add_partition_9"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'MyISAM' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before failure +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 ADD PARTITION +(PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Unknown error +# State after failure +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1#P#p20.MYD +t1#P#p20.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM, + PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,fail_add_partition_9"; +SET SESSION debug="+d,fail_add_partition_10"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'MyISAM' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before failure +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 ADD PARTITION +(PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Unknown error +# State after failure +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1#P#p20.MYD +t1#P#p20.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM, + PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,fail_add_partition_10"; +# Test DROP PARTITION +SET SESSION debug="+d,crash_drop_partition_1"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'MyISAM' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before crash +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 DROP PARTITION p10; +ERROR HY000: Lost connection to MySQL server during query +# State after crash (before recovery) +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +# State after crash recovery +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,crash_drop_partition_1"; +SET SESSION debug="+d,crash_drop_partition_2"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'MyISAM' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before crash +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 DROP PARTITION p10; +ERROR HY000: Lost connection to MySQL server during query +# State after crash (before recovery) +#sql-t1.frm +#sql-t1.par +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +# State after crash recovery +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,crash_drop_partition_2"; +SET SESSION debug="+d,crash_drop_partition_3"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'MyISAM' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before crash +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 DROP PARTITION p10; +ERROR HY000: Lost connection to MySQL server during query +# State after crash (before recovery) +#sql-t1.frm +#sql-t1.par +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +# State after crash recovery +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,crash_drop_partition_3"; +SET SESSION debug="+d,crash_drop_partition_4"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'MyISAM' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before crash +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 DROP PARTITION p10; +ERROR HY000: Lost connection to MySQL server during query +# State after crash (before recovery) +#sql-t1.frm +#sql-t1.par +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +# State after crash recovery +t1#P#p0.MYD +t1#P#p0.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,crash_drop_partition_4"; +SET SESSION debug="+d,crash_drop_partition_5"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'MyISAM' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before crash +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 DROP PARTITION p10; +ERROR HY000: Lost connection to MySQL server during query +# State after crash (before recovery) +#sql-t1.frm +#sql-t1.par +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +# State after crash recovery +t1#P#p0.MYD +t1#P#p0.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,crash_drop_partition_5"; +SET SESSION debug="+d,crash_drop_partition_6"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'MyISAM' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before crash +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 DROP PARTITION p10; +ERROR HY000: Lost connection to MySQL server during query +# State after crash (before recovery) +#sql-t1.frm +#sql-t1.par +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +# State after crash recovery +t1#P#p0.MYD +t1#P#p0.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,crash_drop_partition_6"; +SET SESSION debug="+d,crash_drop_partition_7"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'MyISAM' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before crash +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 DROP PARTITION p10; +ERROR HY000: Lost connection to MySQL server during query +# State after crash (before recovery) +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +# State after crash recovery +t1#P#p0.MYD +t1#P#p0.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,crash_drop_partition_7"; +SET SESSION debug="+d,crash_drop_partition_8"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'MyISAM' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before crash +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 DROP PARTITION p10; +ERROR HY000: Lost connection to MySQL server during query +# State after crash (before recovery) +t1#P#p0.MYD +t1#P#p0.MYI +t1.frm +t1.par +# State after crash recovery +t1#P#p0.MYD +t1#P#p0.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,crash_drop_partition_8"; +SET SESSION debug="+d,crash_drop_partition_9"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'MyISAM' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before crash +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 DROP PARTITION p10; +ERROR HY000: Lost connection to MySQL server during query +# State after crash (before recovery) +t1#P#p0.MYD +t1#P#p0.MYI +t1.frm +t1.par +# State after crash recovery +t1#P#p0.MYD +t1#P#p0.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,crash_drop_partition_9"; +# Error recovery DROP PARTITION +SET SESSION debug="+d,fail_drop_partition_1"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'MyISAM' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before failure +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 DROP PARTITION p10; +ERROR HY000: Unknown error +# State after failure +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,fail_drop_partition_1"; +SET SESSION debug="+d,fail_drop_partition_2"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'MyISAM' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before failure +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 DROP PARTITION p10; +ERROR HY000: Unknown error +# State after failure +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,fail_drop_partition_2"; +SET SESSION debug="+d,fail_drop_partition_3"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'MyISAM' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before failure +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 DROP PARTITION p10; +ERROR HY000: Unknown error +# State after failure +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,fail_drop_partition_3"; +SET SESSION debug="+d,fail_drop_partition_4"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'MyISAM' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before failure +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 DROP PARTITION p10; +ERROR HY000: Unknown error +# State after failure +t1#P#p0.MYD +t1#P#p0.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,fail_drop_partition_4"; +SET SESSION debug="+d,fail_drop_partition_5"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'MyISAM' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before failure +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 DROP PARTITION p10; +ERROR HY000: Unknown error +# State after failure +t1#P#p0.MYD +t1#P#p0.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,fail_drop_partition_5"; +SET SESSION debug="+d,fail_drop_partition_6"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'MyISAM' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before failure +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 DROP PARTITION p10; +ERROR HY000: Unknown error +# State after failure +t1#P#p0.MYD +t1#P#p0.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,fail_drop_partition_6"; +SET SESSION debug="+d,fail_drop_partition_7"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'MyISAM' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before failure +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 DROP PARTITION p10; +ERROR HY000: Unknown error +# State after failure +t1#P#p0.MYD +t1#P#p0.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,fail_drop_partition_7"; +SET SESSION debug="+d,fail_drop_partition_8"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'MyISAM' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before failure +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 DROP PARTITION p10; +ERROR HY000: Unknown error +# State after failure +t1#P#p0.MYD +t1#P#p0.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,fail_drop_partition_8"; +SET SESSION debug="+d,fail_drop_partition_9"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'MyISAM' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before failure +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 DROP PARTITION p10; +ERROR HY000: Unknown error +# State after failure +t1#P#p0.MYD +t1#P#p0.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,fail_drop_partition_9"; +# Test change partition (REORGANIZE/REBUILD/COALESCE +# or ADD HASH PARTITION). +SET SESSION debug="+d,crash_change_partition_1"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'MyISAM' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before crash +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 REORGANIZE PARTITION p10 INTO +(PARTITION p10 VALUES IN (10,11,12,13,14,15,16,17,18,19), +PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Lost connection to MySQL server during query +# State after crash (before recovery) +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +# State after crash recovery +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,crash_change_partition_1"; +SET SESSION debug="+d,crash_change_partition_2"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'MyISAM' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before crash +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 REORGANIZE PARTITION p10 INTO +(PARTITION p10 VALUES IN (10,11,12,13,14,15,16,17,18,19), +PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Lost connection to MySQL server during query +# State after crash (before recovery) +#sql-t1.frm +#sql-t1.par +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +# State after crash recovery +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,crash_change_partition_2"; +SET SESSION debug="+d,crash_change_partition_3"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'MyISAM' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before crash +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 REORGANIZE PARTITION p10 INTO +(PARTITION p10 VALUES IN (10,11,12,13,14,15,16,17,18,19), +PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Lost connection to MySQL server during query +# State after crash (before recovery) +#sql-t1.frm +#sql-t1.par +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +# State after crash recovery +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,crash_change_partition_3"; +SET SESSION debug="+d,crash_change_partition_4"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'MyISAM' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before crash +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 REORGANIZE PARTITION p10 INTO +(PARTITION p10 VALUES IN (10,11,12,13,14,15,16,17,18,19), +PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Lost connection to MySQL server during query +# State after crash (before recovery) +#sql-t1.frm +#sql-t1.par +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10#TMP#.MYD +t1#P#p10#TMP#.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1#P#p20#TMP#.MYD +t1#P#p20#TMP#.MYI +t1.frm +t1.par +# State after crash recovery +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,crash_change_partition_4"; +SET SESSION debug="+d,crash_change_partition_5"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'MyISAM' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before crash +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 REORGANIZE PARTITION p10 INTO +(PARTITION p10 VALUES IN (10,11,12,13,14,15,16,17,18,19), +PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Lost connection to MySQL server during query +# State after crash (before recovery) +#sql-t1.frm +#sql-t1.par +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10#TMP#.MYD +t1#P#p10#TMP#.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1#P#p20#TMP#.MYD +t1#P#p20#TMP#.MYI +t1.frm +t1.par +# State after crash recovery +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,crash_change_partition_5"; +SET SESSION debug="+d,crash_change_partition_6"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'MyISAM' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before crash +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 REORGANIZE PARTITION p10 INTO +(PARTITION p10 VALUES IN (10,11,12,13,14,15,16,17,18,19), +PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Lost connection to MySQL server during query +# State after crash (before recovery) +#sql-t1.frm +#sql-t1.par +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10#TMP#.MYD +t1#P#p10#TMP#.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1#P#p20#TMP#.MYD +t1#P#p20#TMP#.MYI +t1.frm +t1.par +# State after crash recovery +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,crash_change_partition_6"; +SET SESSION debug="+d,crash_change_partition_7"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'MyISAM' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before crash +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 REORGANIZE PARTITION p10 INTO +(PARTITION p10 VALUES IN (10,11,12,13,14,15,16,17,18,19), +PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Lost connection to MySQL server during query +# State after crash (before recovery) +#sql-t1.frm +#sql-t1.par +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10#TMP#.MYD +t1#P#p10#TMP#.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1#P#p20#TMP#.MYD +t1#P#p20#TMP#.MYI +t1.frm +t1.par +# State after crash recovery +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1#P#p20.MYD +t1#P#p20.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (10,11,12,13,14,15,16,17,18,19) ENGINE = MyISAM, + PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,crash_change_partition_7"; +SET SESSION debug="+d,crash_change_partition_8"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'MyISAM' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before crash +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 REORGANIZE PARTITION p10 INTO +(PARTITION p10 VALUES IN (10,11,12,13,14,15,16,17,18,19), +PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Lost connection to MySQL server during query +# State after crash (before recovery) +#sql-t1.frm +#sql-t1.par +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10#TMP#.MYD +t1#P#p10#TMP#.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1#P#p20#TMP#.MYD +t1#P#p20#TMP#.MYI +t1.frm +t1.par +# State after crash recovery +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1#P#p20.MYD +t1#P#p20.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (10,11,12,13,14,15,16,17,18,19) ENGINE = MyISAM, + PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,crash_change_partition_8"; +SET SESSION debug="+d,crash_change_partition_9"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'MyISAM' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before crash +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 REORGANIZE PARTITION p10 INTO +(PARTITION p10 VALUES IN (10,11,12,13,14,15,16,17,18,19), +PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Lost connection to MySQL server during query +# State after crash (before recovery) +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10#TMP#.MYD +t1#P#p10#TMP#.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1#P#p20#TMP#.MYD +t1#P#p20#TMP#.MYI +t1.frm +t1.par +# State after crash recovery +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1#P#p20.MYD +t1#P#p20.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (10,11,12,13,14,15,16,17,18,19) ENGINE = MyISAM, + PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,crash_change_partition_9"; +SET SESSION debug="+d,crash_change_partition_10"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'MyISAM' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before crash +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 REORGANIZE PARTITION p10 INTO +(PARTITION p10 VALUES IN (10,11,12,13,14,15,16,17,18,19), +PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Lost connection to MySQL server during query +# State after crash (before recovery) +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10#TMP#.MYD +t1#P#p10#TMP#.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1#P#p20#TMP#.MYD +t1#P#p20#TMP#.MYI +t1.frm +t1.par +# State after crash recovery +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1#P#p20.MYD +t1#P#p20.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (10,11,12,13,14,15,16,17,18,19) ENGINE = MyISAM, + PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,crash_change_partition_10"; +SET SESSION debug="+d,crash_change_partition_11"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'MyISAM' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before crash +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 REORGANIZE PARTITION p10 INTO +(PARTITION p10 VALUES IN (10,11,12,13,14,15,16,17,18,19), +PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Lost connection to MySQL server during query +# State after crash (before recovery) +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1#P#p20.MYD +t1#P#p20.MYI +t1.frm +t1.par +# State after crash recovery +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1#P#p20.MYD +t1#P#p20.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (10,11,12,13,14,15,16,17,18,19) ENGINE = MyISAM, + PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,crash_change_partition_11"; +SET SESSION debug="+d,crash_change_partition_12"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'MyISAM' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before crash +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 REORGANIZE PARTITION p10 INTO +(PARTITION p10 VALUES IN (10,11,12,13,14,15,16,17,18,19), +PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Lost connection to MySQL server during query +# State after crash (before recovery) +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1#P#p20.MYD +t1#P#p20.MYI +t1.frm +t1.par +# State after crash recovery +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1#P#p20.MYD +t1#P#p20.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (10,11,12,13,14,15,16,17,18,19) ENGINE = MyISAM, + PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,crash_change_partition_12"; +# Error recovery change partition (REORGANIZE/REBUILD/COALESCE +# or ADD HASH PARTITION). +SET SESSION debug="+d,fail_change_partition_1"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'MyISAM' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before failure +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 REORGANIZE PARTITION p10 INTO +(PARTITION p10 VALUES IN (10,11,12,13,14,15,16,17,18,19), +PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Unknown error +# State after failure +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,fail_change_partition_1"; +SET SESSION debug="+d,fail_change_partition_2"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'MyISAM' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before failure +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 REORGANIZE PARTITION p10 INTO +(PARTITION p10 VALUES IN (10,11,12,13,14,15,16,17,18,19), +PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Unknown error +# State after failure +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,fail_change_partition_2"; +SET SESSION debug="+d,fail_change_partition_3"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'MyISAM' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before failure +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 REORGANIZE PARTITION p10 INTO +(PARTITION p10 VALUES IN (10,11,12,13,14,15,16,17,18,19), +PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Unknown error +# State after failure +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,fail_change_partition_3"; +SET SESSION debug="+d,fail_change_partition_4"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'MyISAM' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before failure +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 REORGANIZE PARTITION p10 INTO +(PARTITION p10 VALUES IN (10,11,12,13,14,15,16,17,18,19), +PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Unknown error +# State after failure +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,fail_change_partition_4"; +SET SESSION debug="+d,fail_change_partition_5"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'MyISAM' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before failure +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 REORGANIZE PARTITION p10 INTO +(PARTITION p10 VALUES IN (10,11,12,13,14,15,16,17,18,19), +PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Unknown error +# State after failure +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,fail_change_partition_5"; +SET SESSION debug="+d,fail_change_partition_6"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'MyISAM' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before failure +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 REORGANIZE PARTITION p10 INTO +(PARTITION p10 VALUES IN (10,11,12,13,14,15,16,17,18,19), +PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Unknown error +# State after failure +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,fail_change_partition_6"; +SET SESSION debug="+d,fail_change_partition_7"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'MyISAM' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before failure +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 REORGANIZE PARTITION p10 INTO +(PARTITION p10 VALUES IN (10,11,12,13,14,15,16,17,18,19), +PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Unknown error +# State after failure +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1#P#p20.MYD +t1#P#p20.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (10,11,12,13,14,15,16,17,18,19) ENGINE = MyISAM, + PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,fail_change_partition_7"; +SET SESSION debug="+d,fail_change_partition_8"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'MyISAM' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before failure +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 REORGANIZE PARTITION p10 INTO +(PARTITION p10 VALUES IN (10,11,12,13,14,15,16,17,18,19), +PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Unknown error +# State after failure +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1#P#p20.MYD +t1#P#p20.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (10,11,12,13,14,15,16,17,18,19) ENGINE = MyISAM, + PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,fail_change_partition_8"; +SET SESSION debug="+d,fail_change_partition_9"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'MyISAM' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before failure +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 REORGANIZE PARTITION p10 INTO +(PARTITION p10 VALUES IN (10,11,12,13,14,15,16,17,18,19), +PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Unknown error +# State after failure +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1#P#p20.MYD +t1#P#p20.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (10,11,12,13,14,15,16,17,18,19) ENGINE = MyISAM, + PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,fail_change_partition_9"; +SET SESSION debug="+d,fail_change_partition_10"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'MyISAM' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before failure +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 REORGANIZE PARTITION p10 INTO +(PARTITION p10 VALUES IN (10,11,12,13,14,15,16,17,18,19), +PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Unknown error +# State after failure +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1#P#p20.MYD +t1#P#p20.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (10,11,12,13,14,15,16,17,18,19) ENGINE = MyISAM, + PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,fail_change_partition_10"; +SET SESSION debug="+d,fail_change_partition_11"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'MyISAM' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before failure +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 REORGANIZE PARTITION p10 INTO +(PARTITION p10 VALUES IN (10,11,12,13,14,15,16,17,18,19), +PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Unknown error +# State after failure +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1#P#p20.MYD +t1#P#p20.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (10,11,12,13,14,15,16,17,18,19) ENGINE = MyISAM, + PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,fail_change_partition_11"; +SET SESSION debug="+d,fail_change_partition_12"; +CREATE TABLE t1 (a INT, b VARCHAR(64)) +ENGINE = 'MyISAM' +PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9), +PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19)); +INSERT INTO t1 VALUES (1, "Original from partition p0"), (2, "Original from partition p0"), (3, "Original from partition p0"), (4, "Original from partition p0"), (11, "Original from partition p1"), (12, "Original from partition p1"), (13, "Original from partition p1"), (14, "Original from partition p1"); +# State before failure +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (11,12,13,14,15,16,17,18,19) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +ALTER TABLE t1 REORGANIZE PARTITION p10 INTO +(PARTITION p10 VALUES IN (10,11,12,13,14,15,16,17,18,19), +PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29)); +ERROR HY000: Unknown error +# State after failure +t1#P#p0.MYD +t1#P#p0.MYI +t1#P#p10.MYD +t1#P#p10.MYI +t1#P#p20.MYD +t1#P#p20.MYI +t1.frm +t1.par +SHOW CREATE TABLE t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `a` int(11) DEFAULT NULL, + `b` varchar(64) DEFAULT NULL +) ENGINE=MyISAM DEFAULT CHARSET=latin1 +/*!50100 PARTITION BY LIST (a) +(PARTITION p0 VALUES IN (0,1,2,3,4,5,6,7,8,9) ENGINE = MyISAM, + PARTITION p10 VALUES IN (10,11,12,13,14,15,16,17,18,19) ENGINE = MyISAM, + PARTITION p20 VALUES IN (20,21,22,23,24,25,26,27,28,29) ENGINE = MyISAM) */ +SELECT * FROM t1; +a b +1 Original from partition p0 +11 Original from partition p1 +12 Original from partition p1 +13 Original from partition p1 +14 Original from partition p1 +2 Original from partition p0 +3 Original from partition p0 +4 Original from partition p0 +DROP TABLE t1; +SET SESSION debug="-d,fail_change_partition_12"; diff --git a/mysql-test/suite/parts/r/partition_special_innodb.result b/mysql-test/suite/parts/r/partition_special_innodb.result index a9c5b2e766e..b8dffd61fbe 100644 --- a/mysql-test/suite/parts/r/partition_special_innodb.result +++ b/mysql-test/suite/parts/r/partition_special_innodb.result @@ -216,3 +216,71 @@ SET SESSION lock_wait_timeout= 1; ALTER TABLE t1 AUTO_INCREMENT = 10; ERROR HY000: Lock wait timeout exceeded; try restarting transaction DROP TABLE t1; +# +# Bug#53676: Unexpected errors and possible table corruption on +# ADD PARTITION and LOCK TABLE +CREATE TABLE t1 ( i INT NOT NULL AUTO_INCREMENT PRIMARY KEY, f INT ) +ENGINE = InnoDB PARTITION BY HASH(i) PARTITIONS 2; +SET lock_wait_timeout = 2; +#Connection 1 locks the table +LOCK TABLE t1 READ; +# Connection 2 tries to add partitions: +# First attempt: lock wait timeout (as expected) +ALTER TABLE t1 ADD PARTITION PARTITIONS 2; +ERROR HY000: Lock wait timeout exceeded; try restarting transaction +# Second attempt: says that partition already exists +ALTER TABLE t1 ADD PARTITION PARTITIONS 2; +ERROR HY000: Lock wait timeout exceeded; try restarting transaction +# Connection 1 unlocks the table and locks it again: +UNLOCK TABLES; +LOCK TABLE t1 READ; +# Connection 2 tries again to add partitions: +# Third attempt: says that the table does not exist +ALTER TABLE t1 ADD PARTITION PARTITIONS 2; +ERROR HY000: Lock wait timeout exceeded; try restarting transaction +# Check table returns the same +CHECK TABLE t1; +Table Op Msg_type Msg_text +test.t1 check Error Lock wait timeout exceeded; try restarting transaction +test.t1 check error Corrupt +UNLOCK TABLES; +DROP TABLE t1; +CREATE TABLE t2 ( i INT NOT NULL AUTO_INCREMENT PRIMARY KEY, f INT ) +ENGINE = InnoDB PARTITION BY HASH(i) PARTITIONS 2; +SET lock_wait_timeout = 2; +LOCK TABLE t2 READ; +ALTER TABLE t2 ADD PARTITION PARTITIONS 2; +ERROR HY000: Lock wait timeout exceeded; try restarting transaction +ALTER TABLE t2 ADD PARTITION PARTITIONS 2; +UNLOCK TABLES; +CHECK TABLE t2; +Table Op Msg_type Msg_text +test.t2 check status OK +SELECT * FROM t2; +i f +DROP TABLE t2; +CREATE TABLE t3 ( i INT NOT NULL AUTO_INCREMENT PRIMARY KEY, f INT ) +ENGINE = InnoDB PARTITION BY HASH(i) PARTITIONS 2; +SET lock_wait_timeout = 2; +# Connection 1 locks the table +LOCK TABLE t3 READ; +# Connection 2 tries to add partitions (timeout): +ALTER TABLE t3 ADD PARTITION PARTITIONS 2; +ERROR HY000: Lock wait timeout exceeded; try restarting transaction +SET lock_wait_timeout = 2; +# Connection 3 tries to add partitions (partition already exists): +ALTER TABLE t3 ADD PARTITION PARTITIONS 2; +ERROR HY000: Lock wait timeout exceeded; try restarting transaction +# Connection 4 tries to rename the table: +RENAME TABLE t3 TO t4; +# Connection 1 unlocks the table: +UNLOCK TABLES; +# Connection 4 gets error on rename: +# SHOW TABLES returns the table (not renamed): +SHOW TABLES; +Tables_in_test +t4 +# Connection 5 attempts to read from the table (table does not exist): +SELECT * FROM t3; +ERROR 42S02: Table 'test.t3' doesn't exist +DROP TABLE t4; diff --git a/mysql-test/suite/parts/r/partition_special_myisam.result b/mysql-test/suite/parts/r/partition_special_myisam.result index 60c9f9666cd..f8618fcbb6d 100644 --- a/mysql-test/suite/parts/r/partition_special_myisam.result +++ b/mysql-test/suite/parts/r/partition_special_myisam.result @@ -200,3 +200,22 @@ a b c d e f g h a1 b1 c1 d1 e1 f1 g1 h1 a2 b2 c2 d2 e2 f2 g2 h2 a3 b3 c3 d3 e3 f 1983-12-31 cdef srtbvsr w 45634 13452.56 3452346456 127 1983-12-31 cdef srtbvsr w 45634 13452.56 3452346456 127 1983-12-31 cdef srtbvsr w 45634 13452.56 3452346456 127 1983-12-31 cdef srtbvsr w 45634 13452.56 3452346456 127 liuugbzvdmrlti b itiortudirtfgtibm dfi 1975-01-01 abcde abcde m 1234 123.45 32412341234 113 1975-01-01 abcde abcde m 1234 123.45 32412341234 113 1975-01-01 abcde abcde m 1234 123.45 32412341234 113 1975-01-01 abcde abcde m 1234 123.45 32412341234 113 tbhth nrzh ztfghgfh fzh ftzhj fztjh drop table t1; +# +# Bug#53770: Server crash at handler.cc:2076 on LOAD DATA +# after timed out COALESCE PARTITION +CREATE TABLE t1 ( i INT NOT NULL AUTO_INCREMENT PRIMARY KEY, f INT ) +ENGINE = MyISAM PARTITION BY HASH(i) PARTITIONS 3; +# Connection 1 starts transaction and gets lock +START TRANSACTION; +SELECT * FROM t1; +i f +SET lock_wait_timeout = 2; +# Connection 2 tries to coalesce partitions (timeout): +ALTER TABLE t1 COALESCE PARTITION 2; +ERROR HY000: Lock wait timeout exceeded; try restarting transaction +# Connection 3 tries to load into the table: +LOAD DATA LOCAL INFILE '/tmp/load.in' INTO TABLE t1 (f); +# Connection 1 commits the transaction +COMMIT; +# Connection 3... +DROP TABLE t1; diff --git a/mysql-test/suite/parts/t/partition_debug_innodb-master.opt b/mysql-test/suite/parts/t/partition_debug_innodb-master.opt new file mode 100644 index 00000000000..d6c06191422 --- /dev/null +++ b/mysql-test/suite/parts/t/partition_debug_innodb-master.opt @@ -0,0 +1 @@ +--innodb-file-format-check --innodb-file-per-table=1 --skip-stack-trace --skip-core-file diff --git a/mysql-test/suite/parts/t/partition_debug_innodb.test b/mysql-test/suite/parts/t/partition_debug_innodb.test new file mode 100644 index 00000000000..c5d8df33213 --- /dev/null +++ b/mysql-test/suite/parts/t/partition_debug_innodb.test @@ -0,0 +1,26 @@ +# Partitioning test that require debug features +# including crashing tests. + +--source include/have_debug.inc +--source include/have_innodb.inc +--source include/have_partition.inc +--source include/not_valgrind.inc + +--disable_warnings +DROP TABLE IF EXISTS t1; +--enable_warnings + +--let $DATADIR= `SELECT @@datadir;` + +# Checking with #innodb what this is... +call mtr.add_suppression("InnoDB: Warning: allocated tablespace .*, old maximum was"); +# If there is a crash or failure between the ddl_log is written and the +# operation is completed, mysql will try to drop a not yet created partition +call mtr.add_suppression("InnoDB: Error: table .* does not exist in the InnoDB internal"); +call mtr.add_suppression("InnoDB: Warning: MySQL is trying to drop table "); + + +let $engine= 'InnoDB'; + +--echo # Test crash and failure recovery in fast_alter_partition_table. +--source suite/parts/inc/partition_mgm_crash.inc diff --git a/mysql-test/suite/parts/t/partition_debug_myisam-master.opt b/mysql-test/suite/parts/t/partition_debug_myisam-master.opt new file mode 100644 index 00000000000..425fda95086 --- /dev/null +++ b/mysql-test/suite/parts/t/partition_debug_myisam-master.opt @@ -0,0 +1 @@ +--skip-stack-trace --skip-core-file diff --git a/mysql-test/suite/parts/t/partition_debug_myisam.test b/mysql-test/suite/parts/t/partition_debug_myisam.test new file mode 100644 index 00000000000..a4d5ee4bf04 --- /dev/null +++ b/mysql-test/suite/parts/t/partition_debug_myisam.test @@ -0,0 +1,17 @@ +# Partitioning test that require debug features +# including crashing tests. + +--source include/have_debug.inc +--source include/have_partition.inc +--source include/not_valgrind.inc + +--disable_warnings +DROP TABLE IF EXISTS t1; +--enable_warnings + +--let $DATADIR= `SELECT @@datadir;` + +let $engine= 'MyISAM'; + +--echo # Test crash and failure recovery in fast_alter_partition_table. +--source suite/parts/inc/partition_mgm_crash.inc diff --git a/mysql-test/suite/parts/t/partition_special_innodb-master.opt b/mysql-test/suite/parts/t/partition_special_innodb-master.opt index e76299453d3..624645d75c7 100644 --- a/mysql-test/suite/parts/t/partition_special_innodb-master.opt +++ b/mysql-test/suite/parts/t/partition_special_innodb-master.opt @@ -1 +1 @@ ---innodb_lock_wait_timeout=2 +--innodb_lock_wait_timeout=2 --innodb-file-per-table=1 diff --git a/mysql-test/suite/parts/t/partition_special_innodb.test b/mysql-test/suite/parts/t/partition_special_innodb.test index 833e489558e..9c26ab6fdb4 100644 --- a/mysql-test/suite/parts/t/partition_special_innodb.test +++ b/mysql-test/suite/parts/t/partition_special_innodb.test @@ -76,3 +76,132 @@ ALTER TABLE t1 AUTO_INCREMENT = 10; --disconnect con1 --connection default DROP TABLE t1; + +--echo # +--echo # Bug#53676: Unexpected errors and possible table corruption on +--echo # ADD PARTITION and LOCK TABLE +--connect (con1,localhost,root,,) +CREATE TABLE t1 ( i INT NOT NULL AUTO_INCREMENT PRIMARY KEY, f INT ) + ENGINE = InnoDB PARTITION BY HASH(i) PARTITIONS 2; + +--connect (con2,localhost,root,,) +SET lock_wait_timeout = 2; + +--connection con1 +--echo #Connection 1 locks the table +LOCK TABLE t1 READ; + +--connection con2 +--echo # Connection 2 tries to add partitions: +--echo # First attempt: lock wait timeout (as expected) +--error ER_LOCK_WAIT_TIMEOUT +ALTER TABLE t1 ADD PARTITION PARTITIONS 2; +--echo # Second attempt: says that partition already exists +--error ER_LOCK_WAIT_TIMEOUT +ALTER TABLE t1 ADD PARTITION PARTITIONS 2; + +--connection con1 +--echo # Connection 1 unlocks the table and locks it again: +UNLOCK TABLES; +--real_sleep 1 +LOCK TABLE t1 READ; + +--connection con2 +--echo # Connection 2 tries again to add partitions: +--echo # Third attempt: says that the table does not exist +--error ER_LOCK_WAIT_TIMEOUT +ALTER TABLE t1 ADD PARTITION PARTITIONS 2; +--echo # Check table returns the same +CHECK TABLE t1; + +--connection con1 +UNLOCK TABLES; + +--connection con2 +DROP TABLE t1; + +# End of Test1 + +# Test2 + +--connection con1 + +CREATE TABLE t2 ( i INT NOT NULL AUTO_INCREMENT PRIMARY KEY, f INT ) + ENGINE = InnoDB PARTITION BY HASH(i) PARTITIONS 2; + +--connection con2 +SET lock_wait_timeout = 2; + +--connection con1 +LOCK TABLE t2 READ; + +--connection con2 +--error ER_LOCK_WAIT_TIMEOUT +ALTER TABLE t2 ADD PARTITION PARTITIONS 2; +send ALTER TABLE t2 ADD PARTITION PARTITIONS 2; + +--connection con1 +UNLOCK TABLES; + +--connection con2 +--reap + +--connect (con3,localhost,root,,) +CHECK TABLE t2; +SELECT * FROM t2; +DROP TABLE t2; + +# End of Test2 +# Test #3 + +--connection con1 + +CREATE TABLE t3 ( i INT NOT NULL AUTO_INCREMENT PRIMARY KEY, f INT ) + ENGINE = InnoDB PARTITION BY HASH(i) PARTITIONS 2; + +--connection con2 +SET lock_wait_timeout = 2; + +--connection con1 +--echo # Connection 1 locks the table +LOCK TABLE t3 READ; + +--connection con2 +--echo # Connection 2 tries to add partitions (timeout): +--error ER_LOCK_WAIT_TIMEOUT +ALTER TABLE t3 ADD PARTITION PARTITIONS 2; + +--connection con3 +SET lock_wait_timeout = 2; +--echo # Connection 3 tries to add partitions (partition already exists): +--error ER_LOCK_WAIT_TIMEOUT +ALTER TABLE t3 ADD PARTITION PARTITIONS 2; + +--connect (con4,localhost,root,,) +--echo # Connection 4 tries to rename the table: +send RENAME TABLE t3 TO t4; + +--connection con1 +--real_sleep 1 +--echo # Connection 1 unlocks the table: +UNLOCK TABLES; + +--connection con4 +--echo # Connection 4 gets error on rename: +--reap + +--connect (con5,localhost,root,,) +--echo # SHOW TABLES returns the table (not renamed): +SHOW TABLES; +--echo # Connection 5 attempts to read from the table (table does not exist): +--error ER_NO_SUCH_TABLE +SELECT * FROM t3; +DROP TABLE t4; + +--disconnect con5 +--disconnect con4 +--disconnect con3 +--disconnect con2 +--disconnect con1 +--connection default +# End of Test #3 diff --git a/mysql-test/suite/parts/t/partition_special_myisam.test b/mysql-test/suite/parts/t/partition_special_myisam.test index e1737ebc3c2..032722cbb7d 100644 --- a/mysql-test/suite/parts/t/partition_special_myisam.test +++ b/mysql-test/suite/parts/t/partition_special_myisam.test @@ -43,3 +43,43 @@ let $engine= 'MyISAM'; --source suite/parts/inc/partition_key_8col.inc --source suite/parts/inc/partition_key_16col.inc --source suite/parts/inc/partition_key_32col.inc + +--echo # +--echo # Bug#53770: Server crash at handler.cc:2076 on LOAD DATA +--echo # after timed out COALESCE PARTITION +CREATE TABLE t1 ( i INT NOT NULL AUTO_INCREMENT PRIMARY KEY, f INT ) + ENGINE = MyISAM PARTITION BY HASH(i) PARTITIONS 3; + +--echo # Connection 1 starts transaction and gets lock +START TRANSACTION; +SELECT * FROM t1; + +--connect (con2,localhost,root,,) +SET lock_wait_timeout = 2; +--echo # Connection 2 tries to coalesce partitions (timeout): +--error ER_LOCK_WAIT_TIMEOUT +ALTER TABLE t1 COALESCE PARTITION 2; + +--connect (con3,localhost,root,,) + +perl; +open( LD, ">" . "/tmp/load.in" ) || die "Could not open file for writing " . $ENV{'MYSQLTEST_DATADIR'} . "/test/load.in"; +print LD "1\n2\n3\n"; +close( LD ); +EOF +--echo # Connection 3 tries to load into the table: +send LOAD DATA LOCAL INFILE '/tmp/load.in' INTO TABLE t1 (f); + +--connection default +--real_sleep 1 +--echo # Connection 1 commits the transaction +COMMIT; + +--connection con3 +--echo # Connection 3... +--reap +DROP TABLE t1; + +--disconnect con3 +--disconnect con2 +--connection default diff --git a/mysql-test/t/partition_innodb.test b/mysql-test/t/partition_innodb.test index 30f5894716c..f6adf014468 100644 --- a/mysql-test/t/partition_innodb.test +++ b/mysql-test/t/partition_innodb.test @@ -8,6 +8,50 @@ drop table if exists t1, t2; let $MYSQLD_DATADIR= `SELECT @@datadir`; +--echo # +--echo # Bug#50418: DROP PARTITION does not interact with transactions +--echo # +CREATE TABLE t1 ( + id INT AUTO_INCREMENT NOT NULL, + name CHAR(50) NOT NULL, + myDate DATE NOT NULL, + PRIMARY KEY (id, myDate), + INDEX idx_date (myDate) + ) ENGINE=InnoDB +PARTITION BY RANGE ( TO_DAYS(myDate) ) ( + PARTITION p0 VALUES LESS THAN (734028), + PARTITION p1 VALUES LESS THAN (734029), + PARTITION p2 VALUES LESS THAN (734030), + PARTITION p3 VALUES LESS THAN MAXVALUE + ) ; +INSERT INTO t1 VALUES +(NULL, 'Lachlan', '2009-09-13'), + (NULL, 'Clint', '2009-09-13'), + (NULL, 'John', '2009-09-14'), + (NULL, 'Dave', '2009-09-14'), + (NULL, 'Jeremy', '2009-09-15'), + (NULL, 'Scott', '2009-09-15'), + (NULL, 'Jeff', '2009-09-16'), + (NULL, 'Joe', '2009-09-16'); +SET AUTOCOMMIT=0; +SELECT * FROM t1 FOR UPDATE; +UPDATE t1 SET name = 'Mattias' WHERE id = 7; +SELECT * FROM t1 WHERE id = 7; +--connect (con1, localhost, root,,) +--echo # Connection con1 +SET lock_wait_timeout = 1; +--echo # After the patch it will wait and fail on timeout. +--error ER_LOCK_WAIT_TIMEOUT +ALTER TABLE t1 DROP PARTITION p3; +SHOW WARNINGS; +--disconnect con1 +--connection default +--echo # Connection default +SELECT * FROM t1; +--echo # No changes. +COMMIT; +DROP TABLE t1; + --echo # --echo # Bug#51830: Incorrect partition pruning on range partition (regression) --echo # diff --git a/sql/sql_base.cc b/sql/sql_base.cc index e810d5fc091..e091c26592e 100644 --- a/sql/sql_base.cc +++ b/sql/sql_base.cc @@ -8889,87 +8889,6 @@ bool is_equal(const LEX_STRING *a, const LEX_STRING *b) } -/* - Unlock and close table before renaming and dropping partitions - SYNOPSIS - alter_close_tables() - lpt Struct carrying parameters - RETURN VALUES - 0 -*/ - -static int alter_close_tables(ALTER_PARTITION_PARAM_TYPE *lpt) -{ - TABLE_SHARE *share= lpt->table->s; - THD *thd= lpt->thd; - TABLE *table; - DBUG_ENTER("alter_close_tables"); - /* - We must keep LOCK_open while manipulating with thd->open_tables. - Another thread may be working on it. - */ - mysql_mutex_lock(&LOCK_open); - /* - We can safely remove locks for all tables with the same name: - later they will all be closed anyway in - alter_partition_lock_handling(). - */ - for (table= thd->open_tables; table ; table= table->next) - { - if (!strcmp(table->s->table_name.str, share->table_name.str) && - !strcmp(table->s->db.str, share->db.str)) - { - mysql_lock_remove(thd, thd->lock, table); - table->file->close(); - table->db_stat= 0; // Mark file closed - /* - Ensure that we won't end up with a crippled table instance - in the table cache if an error occurs before we reach - alter_partition_lock_handling() and the table is closed - by close_thread_tables() instead. - */ - tdc_remove_table(thd, TDC_RT_REMOVE_UNUSED, - table->s->db.str, - table->s->table_name.str); - } - } - mysql_mutex_unlock(&LOCK_open); - DBUG_RETURN(0); -} - - -/* - SYNOPSIS - abort_and_upgrade_lock_and_close_table() - lpt Parameter passing struct - All parameters passed through the ALTER_PARTITION_PARAM_TYPE object - RETURN VALUE - 0 - DESCRIPTION - Remember old lock level (for possible downgrade later on), abort all - waiting threads and ensure that all keeping locks currently are - completed such that we own the lock exclusively and no other interaction - is ongoing. Close the table and hold the name lock. - - thd Thread object - table Table object - db Database name - table_name Table name - old_lock_level Old lock level -*/ - -int abort_and_upgrade_lock_and_close_table(ALTER_PARTITION_PARAM_TYPE *lpt) -{ - DBUG_ENTER("abort_and_upgrade_lock_and_close_table"); - - if (wait_while_table_is_used(lpt->thd, lpt->table, HA_EXTRA_FORCE_REOPEN)) - DBUG_RETURN(1); - if (alter_close_tables(lpt)) - DBUG_RETURN(1); - DBUG_RETURN(0); -} - - /* Tells if two (or more) tables have auto_increment columns and we want to lock those tables with a write lock. diff --git a/sql/sql_base.h b/sql/sql_base.h index 45f1408e2f5..2b08d8fa40e 100644 --- a/sql/sql_base.h +++ b/sql/sql_base.h @@ -103,15 +103,10 @@ bool reopen_table(TABLE *table); bool reopen_tables(THD *thd,bool get_locks,bool in_refresh); void close_data_files_and_morph_locks(THD *thd, const char *db, const char *table_name); -void close_handle_and_leave_table_as_lock(TABLE *table); bool open_new_frm(THD *thd, TABLE_SHARE *share, const char *alias, uint db_stat, uint prgflag, uint ha_open_flags, TABLE *outparam, TABLE_LIST *table_desc, MEM_ROOT *mem_root); -bool wait_for_tables(THD *thd); -bool table_is_used(TABLE *table, bool wait_for_name_lock); -TABLE *drop_locked_tables(THD *thd,const char *db, const char *table_name); -void abort_locked_tables(THD *thd,const char *db, const char *table_name); bool get_key_map_from_key_list(key_map *map, TABLE *table, List *index_list); @@ -218,7 +213,6 @@ TABLE *open_n_lock_single_table(THD *thd, TABLE_LIST *table_l, thr_lock_type lock_type, uint flags); bool open_normal_and_derived_tables(THD *thd, TABLE_LIST *tables, uint flags); bool lock_tables(THD *thd, TABLE_LIST *tables, uint counter, uint flags); -int abort_and_upgrade_lock_and_close_table(ALTER_PARTITION_PARAM_TYPE *lpt); int decide_logging_format(THD *thd, TABLE_LIST *tables); void free_io_cache(TABLE *entry); void intern_close_table(TABLE *entry); @@ -254,8 +248,6 @@ bool close_cached_tables(THD *thd, TABLE_LIST *tables, bool have_lock, bool close_cached_connection_tables(THD *thd, bool wait_for_refresh, LEX_STRING *connect_string, bool have_lock = FALSE); -void close_all_tables_for_name(THD *thd, TABLE_SHARE *share, - bool remove_from_locked_tables); OPEN_TABLE_LIST *list_open_tables(THD *thd, const char *db, const char *wild); bool remove_table_from_cache(THD *thd, const char *db, const char *table, uint flags); diff --git a/sql/sql_partition.cc b/sql/sql_partition.cc index fb880cce8d3..0107a4d8144 100644 --- a/sql/sql_partition.cc +++ b/sql/sql_partition.cc @@ -71,6 +71,8 @@ #define ERROR_INJECT_CRASH(code) \ DBUG_EVALUATE_IF(code, (abort(), 0), 0) +#define ERROR_INJECT_ERROR(code) \ + DBUG_EVALUATE_IF(code, (my_error(ER_UNKNOWN_ERROR, MYF(0)), TRUE), 0) /* Partition related functions declarations and some static constants; @@ -6109,25 +6111,32 @@ static bool write_log_add_change_partition(ALTER_PARTITION_PARAM_TYPE *lpt) { partition_info *part_info= lpt->part_info; DDL_LOG_MEMORY_ENTRY *log_entry; - DDL_LOG_MEMORY_ENTRY *exec_log_entry= NULL; + DDL_LOG_MEMORY_ENTRY *exec_log_entry= part_info->exec_log_entry; char tmp_path[FN_REFLEN + 1]; char path[FN_REFLEN + 1]; uint next_entry= 0; + DDL_LOG_MEMORY_ENTRY *old_first_log_entry= part_info->first_log_entry; + /* write_log_drop_shadow_frm(lpt) must have been run first */ + DBUG_ASSERT(old_first_log_entry); DBUG_ENTER("write_log_add_change_partition"); build_table_filename(path, sizeof(path) - 1, lpt->db, lpt->table_name, "", 0); build_table_shadow_filename(tmp_path, sizeof(tmp_path) - 1, lpt); mysql_mutex_lock(&LOCK_gdl); + + /* Relink the previous drop shadow frm entry */ + if (old_first_log_entry) + next_entry= old_first_log_entry->entry_pos; if (write_log_dropped_partitions(lpt, &next_entry, (const char*)path, FALSE)) goto error; - if (write_log_replace_delete_frm(lpt, next_entry, NULL, tmp_path, - FALSE)) - goto error; log_entry= part_info->first_log_entry; + if (write_execute_ddl_log_entry(log_entry->entry_pos, - FALSE, &exec_log_entry)) + FALSE, + /* Reuse the old execute ddl_log_entry */ + &exec_log_entry)) goto error; mysql_mutex_unlock(&LOCK_gdl); set_part_info_exec_log_entry(part_info, exec_log_entry); @@ -6136,7 +6145,7 @@ static bool write_log_add_change_partition(ALTER_PARTITION_PARAM_TYPE *lpt) error: release_part_info_log_entries(part_info->first_log_entry); mysql_mutex_unlock(&LOCK_gdl); - part_info->first_log_entry= NULL; + part_info->first_log_entry= old_first_log_entry; my_error(ER_DDL_LOG_ERROR, MYF(0)); DBUG_RETURN(TRUE); } @@ -6153,9 +6162,15 @@ error: TRUE Error FALSE Success DESCRIPTION - We will write log entries that specify to remove all partitions reorganised, - to rename others to reflect the new naming scheme and to install the shadow - frm file. + We will write log entries that specify to + 1) Install the shadow frm file. + 2) Remove all partitions reorganized. (To be able to reorganize a partition + to the same name. Like in REORGANIZE p0 INTO (p0, p1), + so that the later rename from the new p0-temporary name to p0 don't + fail because the partition already exists. + 3) Rename others to reflect the new naming scheme. + + Note that it is written in the ddl log in reverse. */ static bool write_log_final_change_partition(ALTER_PARTITION_PARAM_TYPE *lpt) @@ -6169,20 +6184,25 @@ static bool write_log_final_change_partition(ALTER_PARTITION_PARAM_TYPE *lpt) uint next_entry= 0; DBUG_ENTER("write_log_final_change_partition"); + /* + Do not link any previous log entry. + Replace the revert operations with forced retry operations. + */ part_info->first_log_entry= NULL; build_table_filename(path, sizeof(path) - 1, lpt->db, lpt->table_name, "", 0); build_table_shadow_filename(shadow_path, sizeof(shadow_path) - 1, lpt); mysql_mutex_lock(&LOCK_gdl); + if (write_log_changed_partitions(lpt, &next_entry, (const char*)path)) + goto error; if (write_log_dropped_partitions(lpt, &next_entry, (const char*)path, lpt->alter_info->flags & ALTER_REORGANIZE_PARTITION)) goto error; - if (write_log_changed_partitions(lpt, &next_entry, (const char*)path)) - goto error; - if (write_log_replace_delete_frm(lpt, 0UL, shadow_path, path, TRUE)) + if (write_log_replace_delete_frm(lpt, next_entry, shadow_path, path, TRUE)) goto error; log_entry= part_info->first_log_entry; part_info->frm_log_entry= log_entry; + /* Overwrite the revert execute log entry with this retry execute entry */ if (write_execute_ddl_log_entry(log_entry->entry_pos, FALSE, &exec_log_entry)) goto error; @@ -6281,6 +6301,55 @@ static void alter_partition_lock_handling(ALTER_PARTITION_PARAM_TYPE *lpt) } +/* + Unlock and close table before renaming and dropping partitions + SYNOPSIS + alter_close_tables() + lpt Struct carrying parameters + RETURN VALUES + 0 +*/ + +static int alter_close_tables(ALTER_PARTITION_PARAM_TYPE *lpt) +{ + TABLE_SHARE *share= lpt->table->s; + THD *thd= lpt->thd; + TABLE *table; + DBUG_ENTER("alter_close_tables"); + /* + We must keep LOCK_open while manipulating with thd->open_tables. + Another thread may be working on it. + */ + mysql_mutex_lock(&LOCK_open); + /* + We can safely remove locks for all tables with the same name: + later they will all be closed anyway in + alter_partition_lock_handling(). + */ + for (table= thd->open_tables; table ; table= table->next) + { + if (!strcmp(table->s->table_name.str, share->table_name.str) && + !strcmp(table->s->db.str, share->db.str)) + { + mysql_lock_remove(thd, thd->lock, table); + table->file->close(); + table->db_stat= 0; // Mark file closed + /* + Ensure that we won't end up with a crippled table instance + in the table cache if an error occurs before we reach + alter_partition_lock_handling() and the table is closed + by close_thread_tables() instead. + */ + tdc_remove_table(thd, TDC_RT_REMOVE_UNUSED, + table->s->db.str, + table->s->table_name.str); + } + } + mysql_mutex_unlock(&LOCK_open); + DBUG_RETURN(0); +} + + /* Handle errors for ALTER TABLE for partitioning SYNOPSIS @@ -6294,13 +6363,26 @@ static void alter_partition_lock_handling(ALTER_PARTITION_PARAM_TYPE *lpt) void handle_alter_part_error(ALTER_PARTITION_PARAM_TYPE *lpt, bool not_completed, bool drop_partition, - bool frm_install) + bool frm_install, + bool close_table) { partition_info *part_info= lpt->part_info; DBUG_ENTER("handle_alter_part_error"); + if (close_table) + { + /* + Since the error handling (ddl_log) needs to drop newly created + partitions they must be closed first to not issue errors. + But we still need some information from the part_info object, + so we clone it first to have a copy. + */ + part_info= lpt->part_info->get_clone(); + alter_close_tables(lpt); + } + if (part_info->first_log_entry && - execute_ddl_log_entry(current_thd, + execute_ddl_log_entry(lpt->thd, part_info->first_log_entry->entry_pos)) { /* @@ -6401,6 +6483,22 @@ void handle_alter_part_error(ALTER_PARTITION_PARAM_TYPE *lpt, } +/** + Downgrade an exclusive MDL lock if under LOCK TABLE. + + If we don't downgrade the lock, it will not be downgraded or released + until the table is unlocked, resulting in blocking other threads using + the table. +*/ + +static void downgrade_mdl_if_lock_tables_mode(THD *thd, MDL_ticket *ticket, + enum_mdl_type type) +{ + if (thd->locked_tables_mode) + ticket->downgrade_exclusive_lock(type); +} + + /* Actually perform the change requested by ALTER TABLE of partitions previously prepared. @@ -6438,7 +6536,9 @@ uint fast_alter_partition_table(THD *thd, TABLE *table, ALTER_PARTITION_PARAM_TYPE *lpt= &lpt_obj; bool written_bin_log= TRUE; bool not_completed= TRUE; + bool close_table_on_failure= FALSE; bool frm_install= FALSE; + MDL_ticket *mdl_ticket= table->mdl_ticket; DBUG_ENTER("fast_alter_partition_table"); lpt->thd= thd; @@ -6537,20 +6637,18 @@ uint fast_alter_partition_table(THD *thd, TABLE *table, 0) Write an entry that removes the shadow frm file if crash occurs 1) Write the new frm file as a shadow frm - 2) Write the ddl log to ensure that the operation is completed - even in the presence of a MySQL Server crash - 3) Lock the table in TL_WRITE_ONLY to ensure all other accesses to - the table have completed. This ensures that other threads can not - execute on the table in parallel. - 4) Get an exclusive metadata lock on the table. This ensures that we + 2) Get an exclusive metadata lock on the table (waits for all active + transactions using this table). This ensures that we can release all other locks on the table and since no one can open the table, there can be no new threads accessing the table. They will be hanging on this exclusive lock. - 5) Close all tables that have already been opened but didn't stumble on + 3) Write the ddl log to ensure that the operation is completed + even in the presence of a MySQL Server crash (the log is executed + before any other threads are started, so there are no locking issues). + 4) Close all tables that have already been opened but didn't stumble on the abort locked previously. This is done as part of the - close_data_files_and_morph_locks call. - 6) We are now ready to release all locks we got in this thread. - 7) Write the bin log + alter_close_tables call. + 5) Write the bin log Unfortunately the writing of the binlog is not synchronised with other logging activities. So no matter in which order the binlog is written compared to other activities there will always be cases @@ -6561,40 +6659,54 @@ uint fast_alter_partition_table(THD *thd, TABLE *table, require writing the statement first in the ddl log and then when recovering from the crash read the binlog and insert it into the binlog if not written already. - 8) Install the previously written shadow frm file - 9) Prepare handlers for drop of partitions - 10) Drop the partitions - 11) Remove entries from ddl log - 12) Reopen table if under lock tables - 13) Complete query + 6) Install the previously written shadow frm file + 7) Prepare handlers for drop of partitions + 8) Drop the partitions + 9) Remove entries from ddl log + 10) Reopen table if under lock tables + 11) Complete query We insert Error injections at all places where it could be interesting to test if recovery is properly done. */ if (write_log_drop_shadow_frm(lpt) || ERROR_INJECT_CRASH("crash_drop_partition_1") || + ERROR_INJECT_ERROR("fail_drop_partition_1") || mysql_write_frm(lpt, WFRM_WRITE_SHADOW) || ERROR_INJECT_CRASH("crash_drop_partition_2") || - write_log_drop_partition(lpt) || + ERROR_INJECT_ERROR("fail_drop_partition_2") || + wait_while_table_is_used(thd, table, HA_EXTRA_FORCE_REOPEN) || ERROR_INJECT_CRASH("crash_drop_partition_3") || - (not_completed= FALSE) || - abort_and_upgrade_lock_and_close_table(lpt) || + ERROR_INJECT_ERROR("fail_drop_partition_3") || + (close_table_on_failure= TRUE, FALSE) || + write_log_drop_partition(lpt) || + ERROR_INJECT_CRASH("crash_drop_partition_4") || + ERROR_INJECT_ERROR("fail_drop_partition_4") || + (close_table_on_failure= FALSE, FALSE) || + (not_completed= FALSE, FALSE) || + alter_close_tables(lpt) || ERROR_INJECT_CRASH("crash_drop_partition_5") || + ERROR_INJECT_ERROR("fail_drop_partition_5") || ((!thd->lex->no_write_to_binlog) && (write_bin_log(thd, FALSE, thd->query(), thd->query_length()), FALSE)) || ERROR_INJECT_CRASH("crash_drop_partition_6") || - ((frm_install= TRUE), FALSE) || + ERROR_INJECT_ERROR("fail_drop_partition_6") || + (frm_install= TRUE, FALSE) || mysql_write_frm(lpt, WFRM_INSTALL_SHADOW) || - ((frm_install= FALSE), FALSE) || + (frm_install= FALSE, FALSE) || ERROR_INJECT_CRASH("crash_drop_partition_7") || + ERROR_INJECT_ERROR("fail_drop_partition_7") || mysql_drop_partitions(lpt) || ERROR_INJECT_CRASH("crash_drop_partition_8") || + ERROR_INJECT_ERROR("fail_drop_partition_8") || (write_log_completed(lpt, FALSE), FALSE) || ERROR_INJECT_CRASH("crash_drop_partition_9") || + ERROR_INJECT_ERROR("fail_drop_partition_9") || (alter_partition_lock_handling(lpt), FALSE)) { - handle_alter_part_error(lpt, not_completed, TRUE, frm_install); + handle_alter_part_error(lpt, not_completed, TRUE, frm_install, + close_table_on_failure); goto err; } } @@ -6613,54 +6725,64 @@ uint fast_alter_partition_table(THD *thd, TABLE *table, 0) Write an entry that removes the shadow frm file if crash occurs 1) Write the new frm file as a shadow frm file - 2) Log the changes to happen in ddl log - 2) Add the new partitions - 3) Lock all partitions in TL_WRITE_ONLY to ensure that no users - are still using the old partitioning scheme. Wait until all - ongoing users have completed before progressing. - 4) Get an exclusive metadata lock on the table. This ensures that we + 2) Get an exclusive metadata lock on the table (waits for all active + transactions using this table). This ensures that we can release all other locks on the table and since no one can open the table, there can be no new threads accessing the table. They will be hanging on this exclusive lock. - 5) Close all tables that have already been opened but didn't stumble on - the abort locked previously. This is done as part of the - close_data_files_and_morph_locks call. - 6) Close all table handlers and unlock all handlers but retain - metadata lock. - 7) Write binlog - 8) Now the change is completed except for the installation of the + 3) Write an entry to remove the new parttions if crash occurs + 4) Add the new partitions. + 5) Close all instances of the table and remove them from the table cache. + 6) Write binlog + 7) Now the change is completed except for the installation of the new frm file. We thus write an action in the log to change to the shadow frm file - 9) Install the new frm file of the table where the partitions are + 8) Install the new frm file of the table where the partitions are added to the table. - 10)Wait until all accesses using the old frm file has completed - 11)Remove entries from ddl log - 12)Reopen tables if under lock tables - 13)Complete query + 9) Remove entries from ddl log + 10)Reopen tables if under lock tables + 11)Complete query */ - if (write_log_add_change_partition(lpt) || + if (write_log_drop_shadow_frm(lpt) || ERROR_INJECT_CRASH("crash_add_partition_1") || + ERROR_INJECT_ERROR("fail_add_partition_1") || mysql_write_frm(lpt, WFRM_WRITE_SHADOW) || ERROR_INJECT_CRASH("crash_add_partition_2") || - mysql_change_partitions(lpt) || + ERROR_INJECT_ERROR("fail_add_partition_2") || + wait_while_table_is_used(thd, table, HA_EXTRA_FORCE_REOPEN) || ERROR_INJECT_CRASH("crash_add_partition_3") || - abort_and_upgrade_lock_and_close_table(lpt) || + ERROR_INJECT_ERROR("fail_add_partition_3") || + (close_table_on_failure= TRUE, FALSE) || + write_log_add_change_partition(lpt) || + ERROR_INJECT_CRASH("crash_add_partition_4") || + ERROR_INJECT_ERROR("fail_add_partition_4") || + mysql_change_partitions(lpt) || ERROR_INJECT_CRASH("crash_add_partition_5") || + ERROR_INJECT_ERROR("fail_add_partition_5") || + (close_table_on_failure= FALSE, FALSE) || + alter_close_tables(lpt) || + ERROR_INJECT_CRASH("crash_add_partition_6") || + ERROR_INJECT_ERROR("fail_add_partition_6") || ((!thd->lex->no_write_to_binlog) && (write_bin_log(thd, FALSE, thd->query(), thd->query_length()), FALSE)) || - ERROR_INJECT_CRASH("crash_add_partition_6") || - write_log_rename_frm(lpt) || - (not_completed= FALSE) || ERROR_INJECT_CRASH("crash_add_partition_7") || - ((frm_install= TRUE), FALSE) || - mysql_write_frm(lpt, WFRM_INSTALL_SHADOW) || + ERROR_INJECT_ERROR("fail_add_partition_7") || + write_log_rename_frm(lpt) || + (frm_install= TRUE, FALSE) || + (not_completed= FALSE, FALSE) || ERROR_INJECT_CRASH("crash_add_partition_8") || - (write_log_completed(lpt, FALSE), FALSE) || + ERROR_INJECT_ERROR("fail_add_partition_8") || + mysql_write_frm(lpt, WFRM_INSTALL_SHADOW) || ERROR_INJECT_CRASH("crash_add_partition_9") || + ERROR_INJECT_ERROR("fail_add_partition_9") || + (write_log_completed(lpt, FALSE), FALSE) || + ERROR_INJECT_CRASH("crash_add_partition_10") || + ERROR_INJECT_ERROR("fail_add_partition_10") || (alter_partition_lock_handling(lpt), FALSE)) { - handle_alter_part_error(lpt, not_completed, FALSE, frm_install); + handle_alter_part_error(lpt, not_completed, FALSE, frm_install, + close_table_on_failure); goto err; } } @@ -6703,13 +6825,14 @@ uint fast_alter_partition_table(THD *thd, TABLE *table, removed in a crash situation 3) Add the new partitions Copy from the reorganised partitions to the new partitions - 4) Log that operation is completed and log all complete actions + 4) Get an exclusive metadata lock on the table (waits for all active + transactions using this table). This ensures that we + can release all other locks on the table and since no one can open + the table, there can be no new threads accessing the table. They + will be hanging on this exclusive lock. + 5) Close all instances of the table and remove them from the table cache. + 6) Log that operation is completed and log all complete actions needed to complete operation from here - 5) Upgrade shared metadata lock on the table to an exclusive one. - After this we can be sure that there is no other connection - using this table (they will be waiting for metadata lock). - 6) Close all table instances opened by this thread, but retain - exclusive metadata lock. 7) Write bin log 8) Prepare handlers for rename and delete of partitions 9) Rename and drop the reorged partitions such that they are no @@ -6718,36 +6841,56 @@ uint fast_alter_partition_table(THD *thd, TABLE *table, 11) Reopen the table if under lock tables 12) Complete query */ - if (write_log_add_change_partition(lpt) || + if (write_log_drop_shadow_frm(lpt) || ERROR_INJECT_CRASH("crash_change_partition_1") || + ERROR_INJECT_ERROR("fail_change_partition_1") || mysql_write_frm(lpt, WFRM_WRITE_SHADOW) || ERROR_INJECT_CRASH("crash_change_partition_2") || - mysql_change_partitions(lpt) || + ERROR_INJECT_ERROR("fail_change_partition_2") || + (close_table_on_failure= TRUE, FALSE) || + write_log_add_change_partition(lpt) || ERROR_INJECT_CRASH("crash_change_partition_3") || - write_log_final_change_partition(lpt) || + ERROR_INJECT_ERROR("fail_change_partition_3") || + mysql_change_partitions(lpt) || ERROR_INJECT_CRASH("crash_change_partition_4") || - (not_completed= FALSE) || - abort_and_upgrade_lock_and_close_table(lpt) || + ERROR_INJECT_ERROR("fail_change_partition_4") || + wait_while_table_is_used(thd, table, HA_EXTRA_FORCE_REOPEN) || + ERROR_INJECT_CRASH("crash_change_partition_5") || + ERROR_INJECT_ERROR("fail_change_partition_5") || + alter_close_tables(lpt) || + (close_table_on_failure= FALSE) || ERROR_INJECT_CRASH("crash_change_partition_6") || + ERROR_INJECT_ERROR("fail_change_partition_6") || + write_log_final_change_partition(lpt) || + (not_completed= FALSE) || + ERROR_INJECT_CRASH("crash_change_partition_7") || + ERROR_INJECT_ERROR("fail_change_partition_7") || ((!thd->lex->no_write_to_binlog) && (write_bin_log(thd, FALSE, thd->query(), thd->query_length()), FALSE)) || - ERROR_INJECT_CRASH("crash_change_partition_7") || - mysql_write_frm(lpt, WFRM_INSTALL_SHADOW) || ERROR_INJECT_CRASH("crash_change_partition_8") || - mysql_drop_partitions(lpt) || + ERROR_INJECT_ERROR("fail_change_partition_8") || + mysql_write_frm(lpt, WFRM_INSTALL_SHADOW) || ERROR_INJECT_CRASH("crash_change_partition_9") || + ERROR_INJECT_ERROR("fail_change_partition_9") || + mysql_drop_partitions(lpt) || + ERROR_INJECT_CRASH("crash_change_partition_10") || + ERROR_INJECT_ERROR("fail_change_partition_10") || mysql_rename_partitions(lpt) || ((frm_install= TRUE), FALSE) || - ERROR_INJECT_CRASH("crash_change_partition_10") || - (write_log_completed(lpt, FALSE), FALSE) || ERROR_INJECT_CRASH("crash_change_partition_11") || + ERROR_INJECT_ERROR("fail_change_partition_11") || + (write_log_completed(lpt, FALSE), FALSE) || + ERROR_INJECT_CRASH("crash_change_partition_12") || + ERROR_INJECT_ERROR("fail_change_partition_12") || (alter_partition_lock_handling(lpt), FALSE)) { - handle_alter_part_error(lpt, not_completed, FALSE, frm_install); + handle_alter_part_error(lpt, not_completed, FALSE, frm_install, + close_table_on_failure); goto err; } } + downgrade_mdl_if_lock_tables_mode(thd, mdl_ticket, MDL_SHARED_NO_READ_WRITE); /* A final step is to write the query to the binlog and send ok to the user @@ -6756,6 +6899,8 @@ uint fast_alter_partition_table(THD *thd, TABLE *table, table_list, FALSE, NULL, written_bin_log)); err: + downgrade_mdl_if_lock_tables_mode(thd, mdl_ticket, MDL_SHARED_NO_READ_WRITE); + table->m_needs_reopen= TRUE; DBUG_RETURN(TRUE); } #endif diff --git a/sql/sql_table.cc b/sql/sql_table.cc index 02a874ce62f..7f8e4f68ec5 100644 --- a/sql/sql_table.cc +++ b/sql/sql_table.cc @@ -1086,6 +1086,7 @@ static bool get_free_ddl_log_entry(DDL_LOG_MEMORY_ENTRY **active_entry, */ used_entry->next_log_entry= first_used; used_entry->prev_log_entry= NULL; + used_entry->next_active_log_entry= NULL; global_ddl_log.first_used= used_entry; if (first_used) first_used->prev_log_entry= used_entry; diff --git a/sql/table.h b/sql/table.h index 7579a8a6df3..52ac92299a6 100644 --- a/sql/table.h +++ b/sql/table.h @@ -43,7 +43,6 @@ class Security_context; struct TABLE_LIST; class ACL_internal_schema_access; class ACL_internal_table_access; -struct TABLE_LIST; class Field; /* From 827a89996a06255b471ae9f24d3f3d3cbf9f99fd Mon Sep 17 00:00:00 2001 From: Evgeny Potemkin Date: Sat, 14 Aug 2010 13:11:33 +0400 Subject: [PATCH 127/129] Bug#49746: Const expression caching led to NDB not using engine condition pushdown. NDB supports only a limited set of item nodes for use in engine condition pushdown. Because of this adding cache for const expression effectively disabled this optimization. The ndb_serialize_cond function is extended to support Item_cache and treat it as a constant values. A helper function called ndb_serialize_const is added. It is used to create Ndb_cond value node from given const item. mysql-test/suite/ndb/t/disabled.def: Bug#49746: Const expression caching led to NDB not using engine condition pushdown. Enabled ndb_condition_pushdown test after fixing appropriate bug. sql/ha_ndbcluster_cond.cc: Bug#49746: Const expression caching led to NDB not using engine condition pushdown. The ndb_serialize_cond function is extended to support Item_cache and treat it as a constant values. A helper function called ndb_serialize_const is added. It is used to create Ndb_cond value node from given const item. sql/item.cc: Bug#49746: Const expression caching led to NDB not using engine condition pushdown. The Item::cache_const_expr_analyzer function is adjusted to not create cache for Item_int_with_ref objects. sql/item.h: Bug#49746: Const expression caching led to NDB not using engine condition pushdown. The result_type() method is added to Item_cache class. The Item_cache_str now initializes its collation. --- mysql-test/suite/ndb/t/disabled.def | 1 - sql/ha_ndbcluster_cond.cc | 227 +++++++++++++++------------- sql/item.cc | 3 +- sql/item.h | 10 +- 4 files changed, 135 insertions(+), 106 deletions(-) diff --git a/mysql-test/suite/ndb/t/disabled.def b/mysql-test/suite/ndb/t/disabled.def index d38f60d6a54..c3c046e7ece 100644 --- a/mysql-test/suite/ndb/t/disabled.def +++ b/mysql-test/suite/ndb/t/disabled.def @@ -11,7 +11,6 @@ ############################################################################## ndb_binlog_discover : Bug#54851 2010-07-02 alik ndb.ndb_binlog_discover crashes the server -ndb_condition_pushdown : Bug#49746 2010-02-08 alik ndb_condition_pushdown fails in mysql-next-mr ndb_partition_error2 : Bug#40989 ndb_partition_error2 needs maintenance diff --git a/sql/ha_ndbcluster_cond.cc b/sql/ha_ndbcluster_cond.cc index 6df1f4881c3..8a96ae41453 100644 --- a/sql/ha_ndbcluster_cond.cc +++ b/sql/ha_ndbcluster_cond.cc @@ -35,6 +35,110 @@ typedef NdbDictionary::Column NDBCOL; typedef NdbDictionary::Table NDBTAB; + +/** + Serialize a constant item into a Ndb_cond node. + + @param const_type item's result type + @param item item to be serialized + @param curr_cond Ndb_cond node the item to be serialized into + @param context Traverse context +*/ + +static void ndb_serialize_const(Item_result const_type, const Item *item, + Ndb_cond *curr_cond, + Ndb_cond_traverse_context *context) +{ + DBUG_ASSERT(item->const_item()); + switch (const_type) { + case STRING_RESULT: + { + NDB_ITEM_QUALIFICATION q; + q.value_type= Item::STRING_ITEM; + curr_cond->ndb_item= new Ndb_item(NDB_VALUE, q, item); + if (! context->expecting_no_field_result()) + { + // We have not seen the field argument yet + context->expect_only(Item::FIELD_ITEM); + context->expect_only_field_result(STRING_RESULT); + context->expect_collation(item->collation.collation); + } + else + { + // Expect another logical expression + context->expect_only(Item::FUNC_ITEM); + context->expect(Item::COND_ITEM); + // Check that string result have correct collation + if (!context->expecting_collation(item->collation.collation)) + { + DBUG_PRINT("info", ("Found non-matching collation %s", + item->collation.collation->name)); + context->supported= FALSE; + } + } + break; + } + case REAL_RESULT: + { + NDB_ITEM_QUALIFICATION q; + q.value_type= Item::REAL_ITEM; + curr_cond->ndb_item= new Ndb_item(NDB_VALUE, q, item); + if (! context->expecting_no_field_result()) + { + // We have not seen the field argument yet + context->expect_only(Item::FIELD_ITEM); + context->expect_only_field_result(REAL_RESULT); + } + else + { + // Expect another logical expression + context->expect_only(Item::FUNC_ITEM); + context->expect(Item::COND_ITEM); + } + break; + } + case INT_RESULT: + { + NDB_ITEM_QUALIFICATION q; + q.value_type= Item::INT_ITEM; + curr_cond->ndb_item= new Ndb_item(NDB_VALUE, q, item); + if (! context->expecting_no_field_result()) + { + // We have not seen the field argument yet + context->expect_only(Item::FIELD_ITEM); + context->expect_only_field_result(INT_RESULT); + } + else + { + // Expect another logical expression + context->expect_only(Item::FUNC_ITEM); + context->expect(Item::COND_ITEM); + } + break; + } + case DECIMAL_RESULT: + { + NDB_ITEM_QUALIFICATION q; + q.value_type= Item::DECIMAL_ITEM; + curr_cond->ndb_item= new Ndb_item(NDB_VALUE, q, item); + if (! context->expecting_no_field_result()) + { + // We have not seen the field argument yet + context->expect_only(Item::FIELD_ITEM); + context->expect_only_field_result(DECIMAL_RESULT); + } + else + { + // Expect another logical expression + context->expect_only(Item::FUNC_ITEM); + context->expect(Item::COND_ITEM); + } + break; + } + default: + break; + } +} /* Serialize the item tree into a linked list represented by Ndb_cond for fast generation of NbdScanFilter. Adds information such as @@ -113,7 +217,7 @@ void ndb_serialize_cond(const Item *item, void *arg) to ndb_serialize_cond and end of rewrite statement is wrapped in end of ndb_serialize_cond */ - if (context->expecting(item->type())) + if (context->expecting(item->type()) || item->const_item()) { // This is the | item, save it in the rewrite context rewrite_context2->left_hand_item= item; @@ -597,108 +701,12 @@ void ndb_serialize_cond(const Item *item, void *arg) DBUG_PRINT("info", ("result type %d", func_item->result_type())); if (func_item->const_item()) { - switch (func_item->result_type()) { - case STRING_RESULT: - { - NDB_ITEM_QUALIFICATION q; - q.value_type= Item::STRING_ITEM; - curr_cond->ndb_item= new Ndb_item(NDB_VALUE, q, item); - if (! context->expecting_no_field_result()) - { - // We have not seen the field argument yet - context->expect_only(Item::FIELD_ITEM); - context->expect_only_field_result(STRING_RESULT); - context->expect_collation(func_item->collation.collation); - } - else - { - // Expect another logical expression - context->expect_only(Item::FUNC_ITEM); - context->expect(Item::COND_ITEM); - // Check that string result have correct collation - if (!context->expecting_collation(item->collation.collation)) - { - DBUG_PRINT("info", ("Found non-matching collation %s", - item->collation.collation->name)); - context->supported= FALSE; - } - } - // Skip any arguments since we will evaluate function instead - DBUG_PRINT("info", ("Skip until end of arguments marker")); - context->skip= func_item->argument_count(); - break; - } - case REAL_RESULT: - { - NDB_ITEM_QUALIFICATION q; - q.value_type= Item::REAL_ITEM; - curr_cond->ndb_item= new Ndb_item(NDB_VALUE, q, item); - if (! context->expecting_no_field_result()) - { - // We have not seen the field argument yet - context->expect_only(Item::FIELD_ITEM); - context->expect_only_field_result(REAL_RESULT); - } - else - { - // Expect another logical expression - context->expect_only(Item::FUNC_ITEM); - context->expect(Item::COND_ITEM); - } - - // Skip any arguments since we will evaluate function instead - DBUG_PRINT("info", ("Skip until end of arguments marker")); - context->skip= func_item->argument_count(); - break; - } - case INT_RESULT: - { - NDB_ITEM_QUALIFICATION q; - q.value_type= Item::INT_ITEM; - curr_cond->ndb_item= new Ndb_item(NDB_VALUE, q, item); - if (! context->expecting_no_field_result()) - { - // We have not seen the field argument yet - context->expect_only(Item::FIELD_ITEM); - context->expect_only_field_result(INT_RESULT); - } - else - { - // Expect another logical expression - context->expect_only(Item::FUNC_ITEM); - context->expect(Item::COND_ITEM); - } - - // Skip any arguments since we will evaluate function instead - DBUG_PRINT("info", ("Skip until end of arguments marker")); - context->skip= func_item->argument_count(); - break; - } - case DECIMAL_RESULT: - { - NDB_ITEM_QUALIFICATION q; - q.value_type= Item::DECIMAL_ITEM; - curr_cond->ndb_item= new Ndb_item(NDB_VALUE, q, item); - if (! context->expecting_no_field_result()) - { - // We have not seen the field argument yet - context->expect_only(Item::FIELD_ITEM); - context->expect_only_field_result(DECIMAL_RESULT); - } - else - { - // Expect another logical expression - context->expect_only(Item::FUNC_ITEM); - context->expect(Item::COND_ITEM); - } - // Skip any arguments since we will evaluate function instead - DBUG_PRINT("info", ("Skip until end of arguments marker")); - context->skip= func_item->argument_count(); - break; - } - default: - break; - } + ndb_serialize_const(func_item->result_type(), item, curr_cond, + context); + + // Skip any arguments since we will evaluate function instead + DBUG_PRINT("info", ("Skip until end of arguments marker")); + context->skip= func_item->argument_count(); } else // Function does not return constant expression @@ -883,6 +891,19 @@ void ndb_serialize_cond(const Item *item, void *arg) } break; } + case Item::CACHE_ITEM: + { + DBUG_PRINT("info", ("CACHE_ITEM")); + if (item->const_item()) + { + ndb_serialize_const(((Item_cache*)item)->result_type(), item, + curr_cond, context); + } + else + context->supported= FALSE; + + break; + } default: { DBUG_PRINT("info", ("Found item of type %d", item->type())); diff --git a/sql/item.cc b/sql/item.cc index 1decb5ec426..24f57342668 100644 --- a/sql/item.cc +++ b/sql/item.cc @@ -5931,7 +5931,8 @@ bool Item::cache_const_expr_analyzer(uchar **arg) a subselect (they use their own cache). */ if (const_item() && - !(item->basic_const_item() || item->type() == Item::FIELD_ITEM || + !(basic_const_item() || item->basic_const_item() || + item->type() == Item::FIELD_ITEM || item->type() == SUBSELECT_ITEM || /* Do not cache GET_USER_VAR() function as its const_item() may diff --git a/sql/item.h b/sql/item.h index c7a97ca716a..d1957c46d25 100644 --- a/sql/item.h +++ b/sql/item.h @@ -3266,6 +3266,12 @@ public: bool basic_const_item() const { return test(example && example->basic_const_item());} virtual void clear() { null_value= TRUE; value_cached= FALSE; } + Item_result result_type() const + { + if (!example) + return INT_RESULT; + return Field::result_merge_type(example->field_type()); + } }; @@ -3335,7 +3341,9 @@ public: is_varbinary(item->type() == FIELD_ITEM && cached_field_type == MYSQL_TYPE_VARCHAR && !((const Item_field *) item)->field->has_charset()) - {} + { + collation.set(const_cast(item->collation)); + } double val_real(); longlong val_int(); String* val_str(String *); From 4b20ccafaa3bacfd11c5fcc61e1647dbbefe7bad Mon Sep 17 00:00:00 2001 From: Mattias Jonsson Date: Mon, 16 Aug 2010 14:53:30 +0200 Subject: [PATCH 128/129] Bug#49907: ALTER TABLE ... TRUNCATE PARTITION does not wait for locks on the table Fixing the partitioning specifics after TRUNCATE TABLE in bug-42643 was fixed. Reorganize of code to decrease the size of the giant switch in mysql_execute_command, and to prepare for future parser reengineering. Moved code into Sql_statement objects. Updated patch according to davi's review comments. libmysqld/CMakeLists.txt: Added new files. libmysqld/Makefile.am: Added new files. mysql-test/r/not_partition.result: now returning error on partitioning commands if partitioning is not enabled. mysql-test/r/partition_disabled.result: There is no partition handlerton, so it cannot find the specified engine in the .frm file. mysql-test/r/partition_truncate.result: Updated test results. mysql-test/suite/parts/inc/partition_mgm.inc: Added check that TRUNCATE PARTITION does not delete on failure. mysql-test/suite/parts/r/partition_debug_sync_innodb.result: updated results. mysql-test/suite/parts/r/partition_mgm_lc0_archive.result: updated results. mysql-test/suite/parts/r/partition_mgm_lc1_archive.result: updated results. mysql-test/suite/parts/r/partition_mgm_lc2_archive.result: updated results. mysql-test/suite/parts/t/partition_debug_sync_innodb.test: Test case for this bug. mysql-test/t/not_partition.test: Added check for TRUNCATE PARTITION without partitioning. mysql-test/t/partition_truncate.test: Added test of TRUNCATE PARTITION on non partitioned table. sql/CMakeLists.txt: Added new files. sql/Makefile.am: Added new files. sql/datadict.cc: Moved out the storage engine check into an own function, including assert for lock. sql/datadict.h: added dd_frm_storage_engine. sql/sql_alter_table.cc: moved the code for SQLCOM_ALTER_TABLE in mysql_execute_command into its own file, and using the Sql_statement object to prepare for future parser reengineering. sql/sql_alter_table.h: Created Sql_statement object for ALTER TABLE. sql/sql_lex.cc: resetting m_stmt. sql/sql_lex.h: Temporary hack for forward declaration of enum_alter_table_change_level. sql/sql_parse.cc: Moved out ALTER/ANALYZE/CHECK/OPTIMIZE/REPAIR TABLE from the giant switch into their own Sql_statement objects. sql/sql_parse.h: Exporting check_merge_table_access. sql/sql_partition_admin.cc: created Sql_statement for ALTER TABLE t ANALYZE/CHECK/OPTIMIZE/REPAIR/TRUNCATE PARTITION. To be able to reuse the TABLE equivalents. sql/sql_partition_admin.h: Added Sql_statement of partition admin statements. sql/sql_table.cc: Moved table maintenance code into sql_table_maintenance.cc sql/sql_table.h: Moved table maintenance code into sql_table_maintenance.h exporting functions used by sql_table_maintenance. sql/sql_table_maintenance.cc: Moved table maintenance code from sql_table.cc sql/sql_table_maintenance.h: Sql_statement objects for ANALYZE/CHECK/OPTIMIZE/REPAIR TABLE. Also declaring the keycache functions. sql/sql_truncate.cc: Moved code from SQLCOM_TRUNCATE in mysql_execute_command into Truncate_statement::execute. Added check for partitioned table on TRUNCATE PARTITION. Moved locking fix for partitioned table into Alter_table_truncate_partition::execute. sql/sql_truncate.h: Truncate_statement declaration (sub class of Sql_statement). sql/sql_yacc.yy: Using the new Sql_statment objects. --- libmysqld/CMakeLists.txt | 3 +- libmysqld/Makefile.am | 7 +- mysql-test/r/not_partition.result | 18 +- mysql-test/r/partition_disabled.result | 2 +- mysql-test/r/partition_truncate.result | 8 + mysql-test/suite/parts/inc/partition_mgm.inc | 2 + .../r/partition_debug_sync_innodb.result | 34 + .../parts/r/partition_mgm_lc0_archive.result | 10 + .../parts/r/partition_mgm_lc1_archive.result | 10 + .../parts/r/partition_mgm_lc2_archive.result | 10 + .../parts/t/partition_debug_sync_innodb.test | 41 + mysql-test/t/not_partition.test | 1 + mysql-test/t/partition_truncate.test | 7 + sql/CMakeLists.txt | 6 +- sql/Makefile.am | 9 +- sql/datadict.cc | 87 +- sql/datadict.h | 2 + sql/sql_alter_table.cc | 106 ++ sql/sql_alter_table.h | 66 ++ sql/sql_lex.cc | 1 + sql/sql_lex.h | 18 + sql/sql_parse.cc | 176 +-- sql/sql_parse.h | 1 + sql/sql_partition_admin.cc | 139 +++ sql/sql_partition_admin.h | 236 ++++ sql/sql_table.cc | 953 +--------------- sql/sql_table.h | 30 +- sql/sql_table_maintenance.cc | 1004 +++++++++++++++++ sql/sql_table_maintenance.h | 132 +++ sql/sql_truncate.cc | 50 +- sql/sql_truncate.h | 26 + sql/sql_yacc.yy | 114 +- 32 files changed, 2116 insertions(+), 1193 deletions(-) create mode 100644 sql/sql_alter_table.cc create mode 100644 sql/sql_alter_table.h create mode 100644 sql/sql_partition_admin.cc create mode 100644 sql/sql_partition_admin.h create mode 100644 sql/sql_table_maintenance.cc create mode 100644 sql/sql_table_maintenance.h diff --git a/libmysqld/CMakeLists.txt b/libmysqld/CMakeLists.txt index a7efcb024ec..f3a0f0c5d0f 100644 --- a/libmysqld/CMakeLists.txt +++ b/libmysqld/CMakeLists.txt @@ -64,7 +64,7 @@ SET(SQL_EMBEDDED_SOURCES emb_qcache.cc libmysqld.c lib_sql.cc ../sql/sql_db.cc ../sql/sql_delete.cc ../sql/sql_derived.cc ../sql/sql_do.cc ../sql/sql_error.cc ../sql/sql_handler.cc ../sql/sql_help.cc ../sql/sql_insert.cc ../sql/datadict.cc - ../sql/sql_truncate.cc + ../sql/sql_table_maintenance.cc ../sql/sql_truncate.cc ../sql/sql_lex.cc ../sql/keycaches.cc ../sql/sql_list.cc ../sql/sql_load.cc ../sql/sql_locale.cc ../sql/sql_binlog.cc ../sql/sql_manager.cc @@ -80,6 +80,7 @@ SET(SQL_EMBEDDED_SOURCES emb_qcache.cc libmysqld.c lib_sql.cc ../sql/sql_time.cc ../sql/tztime.cc ../sql/uniques.cc ../sql/unireg.cc ../sql/partition_info.cc ../sql/sql_connect.cc ../sql/scheduler.cc ../sql/sql_audit.cc + ../sql/sql_alter_table.cc ../sql/sql_partition_admin.cc ../sql/event_parse_data.cc ../sql/sql_signal.cc ../sql/rpl_handler.cc ../sql/rpl_utility.cc diff --git a/libmysqld/Makefile.am b/libmysqld/Makefile.am index 1ffa349bcfe..7fe51698491 100644 --- a/libmysqld/Makefile.am +++ b/libmysqld/Makefile.am @@ -63,7 +63,7 @@ sqlsources = derror.cc field.cc field_conv.cc strfunc.cc filesort.cc \ protocol.cc net_serv.cc opt_range.cc \ opt_sum.cc procedure.cc records.cc sql_acl.cc \ sql_load.cc discover.cc sql_locale.cc \ - sql_profile.cc sql_truncate.cc datadict.cc \ + sql_profile.cc sql_table_maintenance.cc sql_truncate.cc datadict.cc \ sql_analyse.cc sql_base.cc sql_cache.cc sql_class.cc \ sql_crypt.cc sql_db.cc sql_delete.cc sql_error.cc sql_insert.cc \ sql_lex.cc sql_list.cc sql_manager.cc \ @@ -78,9 +78,10 @@ sqlsources = derror.cc field.cc field_conv.cc strfunc.cc filesort.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 \ debug_sync.cc sql_tablespace.cc transaction.cc \ - rpl_injector.cc my_user.c partition_info.cc \ + rpl_injector.cc my_user.c partition_info.cc sql_alter_table.cc \ sql_servers.cc event_parse_data.cc sql_signal.cc \ - rpl_handler.cc mdl.cc keycaches.cc sql_audit.cc + rpl_handler.cc mdl.cc keycaches.cc sql_audit.cc \ + sql_partition_admin.cc libmysqld_int_a_SOURCES= $(libmysqld_sources) nodist_libmysqld_int_a_SOURCES= $(libmysqlsources) $(sqlsources) diff --git a/mysql-test/r/not_partition.result b/mysql-test/r/not_partition.result index fc3e0d64b5e..2c48f56d578 100644 --- a/mysql-test/r/not_partition.result +++ b/mysql-test/r/not_partition.result @@ -21,23 +21,17 @@ Table Op Msg_type Msg_text test.t1 repair Error Unknown storage engine 'partition' test.t1 repair error Corrupt ALTER TABLE t1 REPAIR PARTITION ALL; -Table Op Msg_type Msg_text -test.t1 repair Error Unknown storage engine 'partition' -test.t1 repair error Corrupt +ERROR HY000: The 'partitioning' feature is disabled; you need MySQL built with '--with-plugin-partition' to have it working ALTER TABLE t1 CHECK PARTITION ALL; -Table Op Msg_type Msg_text -test.t1 check Error Unknown storage engine 'partition' -test.t1 check error Corrupt +ERROR HY000: The 'partitioning' feature is disabled; you need MySQL built with '--with-plugin-partition' to have it working ALTER TABLE t1 OPTIMIZE PARTITION ALL; -Table Op Msg_type Msg_text -test.t1 optimize Error Unknown storage engine 'partition' -test.t1 optimize error Corrupt +ERROR HY000: The 'partitioning' feature is disabled; you need MySQL built with '--with-plugin-partition' to have it working ALTER TABLE t1 ANALYZE PARTITION ALL; -Table Op Msg_type Msg_text -test.t1 analyze Error Unknown storage engine 'partition' -test.t1 analyze error Corrupt +ERROR HY000: The 'partitioning' feature is disabled; you need MySQL built with '--with-plugin-partition' to have it working ALTER TABLE t1 REBUILD PARTITION ALL; ERROR 42000: Unknown storage engine 'partition' +ALTER TABLE t1 TRUNCATE PARTITION ALL; +ERROR HY000: The 'partitioning' feature is disabled; you need MySQL built with '--with-plugin-partition' to have it working ALTER TABLE t1 ENGINE Memory; ERROR 42000: Unknown storage engine 'partition' ALTER TABLE t1 ADD (new INT); diff --git a/mysql-test/r/partition_disabled.result b/mysql-test/r/partition_disabled.result index df36f56a328..507c6ebe9e9 100644 --- a/mysql-test/r/partition_disabled.result +++ b/mysql-test/r/partition_disabled.result @@ -3,7 +3,7 @@ FLUSH TABLES; SELECT * FROM t1; ERROR HY000: The MySQL server is running with the --skip-partition option so it cannot execute this statement TRUNCATE TABLE t1; -ERROR HY000: The MySQL server is running with the --skip-partition option so it cannot execute this statement +ERROR 42S02: Table 'test.t1' doesn't exist ANALYZE TABLE t1; Table Op Msg_type Msg_text test.t1 analyze Error The MySQL server is running with the --skip-partition option so it cannot execute this statement diff --git a/mysql-test/r/partition_truncate.result b/mysql-test/r/partition_truncate.result index 8f594a319df..66c0cd3d9da 100644 --- a/mysql-test/r/partition_truncate.result +++ b/mysql-test/r/partition_truncate.result @@ -16,3 +16,11 @@ subpartitions 1 alter table t1 truncate partition sp1; ERROR HY000: Incorrect partition name drop table t1; +create table t1 (a int); +insert into t1 values (1), (3), (8); +alter table t1 truncate partition p0; +ERROR HY000: Partition management on a not partitioned table is not possible +select count(*) from t1; +count(*) +3 +drop table t1; diff --git a/mysql-test/suite/parts/inc/partition_mgm.inc b/mysql-test/suite/parts/inc/partition_mgm.inc index 9dfa2b2ffb3..67d1feb8046 100644 --- a/mysql-test/suite/parts/inc/partition_mgm.inc +++ b/mysql-test/suite/parts/inc/partition_mgm.inc @@ -533,6 +533,8 @@ PARTITION BY KEY (a) INSERT INTO t1 VALUES (NULL, "First"), (NULL, "Second"), (999, "Last in LT1000"), (NULL, "First in LT2000"), (NULL, "Second in LT2000"), (1999, "Last in LT2000"), (NULL, "First in MAX"), (NULL, "Second in MAX"); --error ER_PARTITION_MGMT_ON_NONPARTITIONED, ER_ILLEGAL_HA ALTER TABLE t1 TRUNCATE PARTITION MAX; +--sorted_result +SELECT * FROM t1; } if (!$no_truncate) { diff --git a/mysql-test/suite/parts/r/partition_debug_sync_innodb.result b/mysql-test/suite/parts/r/partition_debug_sync_innodb.result index 9e72259a150..268db30bda0 100644 --- a/mysql-test/suite/parts/r/partition_debug_sync_innodb.result +++ b/mysql-test/suite/parts/r/partition_debug_sync_innodb.result @@ -1,4 +1,38 @@ # +# Bug#49907: ALTER TABLE ... TRUNCATE PARTITION +# does not wait for locks on the table +# +CREATE TABLE t1 (a INT) +ENGINE = InnoDB +PARTITION BY RANGE (a) +(PARTITION p0 VALUES LESS THAN (15), +PARTITION pMax VALUES LESS THAN MAXVALUE); +INSERT INTO t1 VALUES (1), (11), (21), (33); +BEGIN; +DELETE FROM t1 WHERE a = 11; +SELECT * FROM t1; +a +1 +21 +33 +# con1 (send) +ALTER TABLE t1 TRUNCATE PARTITION pMax; +# con default +SELECT * FROM t1; +a +1 +21 +33 +# Commit will allow the TRUNCATE to finish +COMMIT; +# con1 (reap) +# con1 (disconnect) +# default connection +SELECT * FROM t1; +a +1 +DROP TABLE t1; +# # Bug#50561: ALTER PARTITIONS does not have adequate lock, breaks with # concurrent I_S query create table t1 (a int) diff --git a/mysql-test/suite/parts/r/partition_mgm_lc0_archive.result b/mysql-test/suite/parts/r/partition_mgm_lc0_archive.result index 4f623813386..f4d76874b4c 100644 --- a/mysql-test/suite/parts/r/partition_mgm_lc0_archive.result +++ b/mysql-test/suite/parts/r/partition_mgm_lc0_archive.result @@ -927,6 +927,16 @@ PARTITION MAX); INSERT INTO t1 VALUES (NULL, "First"), (NULL, "Second"), (999, "Last in LT1000"), (NULL, "First in LT2000"), (NULL, "Second in LT2000"), (1999, "Last in LT2000"), (NULL, "First in MAX"), (NULL, "Second in MAX"); ALTER TABLE t1 TRUNCATE PARTITION MAX; Got one of the listed errors +SELECT * FROM t1; +a b +1 First +1000 First in LT2000 +1001 Second in LT2000 +1999 Last in LT2000 +2 Second +2000 First in MAX +2001 Second in MAX +999 Last in LT1000 # Cleaning up before exit USE test; DROP DATABASE MySQL_Test_DB; diff --git a/mysql-test/suite/parts/r/partition_mgm_lc1_archive.result b/mysql-test/suite/parts/r/partition_mgm_lc1_archive.result index 4cd8cafa3ee..1113e7dcb0c 100644 --- a/mysql-test/suite/parts/r/partition_mgm_lc1_archive.result +++ b/mysql-test/suite/parts/r/partition_mgm_lc1_archive.result @@ -894,6 +894,16 @@ PARTITION MAX); INSERT INTO t1 VALUES (NULL, "First"), (NULL, "Second"), (999, "Last in LT1000"), (NULL, "First in LT2000"), (NULL, "Second in LT2000"), (1999, "Last in LT2000"), (NULL, "First in MAX"), (NULL, "Second in MAX"); ALTER TABLE t1 TRUNCATE PARTITION MAX; Got one of the listed errors +SELECT * FROM t1; +a b +1 First +1000 First in LT2000 +1001 Second in LT2000 +1999 Last in LT2000 +2 Second +2000 First in MAX +2001 Second in MAX +999 Last in LT1000 # Cleaning up before exit USE test; DROP DATABASE MySQL_Test_DB; diff --git a/mysql-test/suite/parts/r/partition_mgm_lc2_archive.result b/mysql-test/suite/parts/r/partition_mgm_lc2_archive.result index 6e8abfef06d..e71803fcac9 100644 --- a/mysql-test/suite/parts/r/partition_mgm_lc2_archive.result +++ b/mysql-test/suite/parts/r/partition_mgm_lc2_archive.result @@ -894,6 +894,16 @@ PARTITION MAX); INSERT INTO t1 VALUES (NULL, "First"), (NULL, "Second"), (999, "Last in LT1000"), (NULL, "First in LT2000"), (NULL, "Second in LT2000"), (1999, "Last in LT2000"), (NULL, "First in MAX"), (NULL, "Second in MAX"); ALTER TABLE t1 TRUNCATE PARTITION MAX; Got one of the listed errors +SELECT * FROM t1; +a b +1 First +1000 First in LT2000 +1001 Second in LT2000 +1999 Last in LT2000 +2 Second +2000 First in MAX +2001 Second in MAX +999 Last in LT1000 # Cleaning up before exit USE test; DROP DATABASE MySQL_Test_DB; diff --git a/mysql-test/suite/parts/t/partition_debug_sync_innodb.test b/mysql-test/suite/parts/t/partition_debug_sync_innodb.test index 79ef3d537bf..a6db0d39925 100644 --- a/mysql-test/suite/parts/t/partition_debug_sync_innodb.test +++ b/mysql-test/suite/parts/t/partition_debug_sync_innodb.test @@ -4,6 +4,47 @@ let $MYSQLD_DATADIR=`SELECT @@datadir`; +--echo # +--echo # Bug#49907: ALTER TABLE ... TRUNCATE PARTITION +--echo # does not wait for locks on the table +--echo # +CREATE TABLE t1 (a INT) +ENGINE = InnoDB +PARTITION BY RANGE (a) +(PARTITION p0 VALUES LESS THAN (15), + PARTITION pMax VALUES LESS THAN MAXVALUE); +INSERT INTO t1 VALUES (1), (11), (21), (33); +BEGIN; +DELETE FROM t1 WHERE a = 11; +--sorted_result +SELECT * FROM t1; + +--connect (con1, localhost, root,,) +--echo # con1 (send) +--send +ALTER TABLE t1 TRUNCATE PARTITION pMax; + +--connection default +--echo # con default +let $wait_condition= + SELECT COUNT(*) = 1 FROM INFORMATION_SCHEMA.PROCESSLIST + WHERE STATE = "Waiting for table" AND INFO = "ALTER TABLE t1 TRUNCATE PARTITION pMax"; +--source include/wait_condition.inc +--sorted_result +SELECT * FROM t1; +--echo # Commit will allow the TRUNCATE to finish +COMMIT; + +--echo # con1 (reap) +--connection con1 +--reap +--echo # con1 (disconnect) +--disconnect con1 +--connection default +--echo # default connection +SELECT * FROM t1; +DROP TABLE t1; + --echo # --echo # Bug#50561: ALTER PARTITIONS does not have adequate lock, breaks with --echo # concurrent I_S query diff --git a/mysql-test/t/not_partition.test b/mysql-test/t/not_partition.test index 78ca44acf18..38b88c00ba3 100644 --- a/mysql-test/t/not_partition.test +++ b/mysql-test/t/not_partition.test @@ -27,6 +27,7 @@ ALTER TABLE t1 CHECK PARTITION ALL; ALTER TABLE t1 OPTIMIZE PARTITION ALL; ALTER TABLE t1 ANALYZE PARTITION ALL; ALTER TABLE t1 REBUILD PARTITION ALL; +ALTER TABLE t1 TRUNCATE PARTITION ALL; ALTER TABLE t1 ENGINE Memory; ALTER TABLE t1 ADD (new INT); DROP TABLE t1; diff --git a/mysql-test/t/partition_truncate.test b/mysql-test/t/partition_truncate.test index 93b9cf62d14..165213d204c 100644 --- a/mysql-test/t/partition_truncate.test +++ b/mysql-test/t/partition_truncate.test @@ -24,3 +24,10 @@ subpartitions 1 --error ER_WRONG_PARTITION_NAME alter table t1 truncate partition sp1; drop table t1; + +create table t1 (a int); +insert into t1 values (1), (3), (8); +--error ER_PARTITION_MGMT_ON_NONPARTITIONED +alter table t1 truncate partition p0; +select count(*) from t1; +drop table t1; diff --git a/sql/CMakeLists.txt b/sql/CMakeLists.txt index 943d6b2eece..1a162d39e0b 100644 --- a/sql/CMakeLists.txt +++ b/sql/CMakeLists.txt @@ -71,9 +71,9 @@ SET (SQL_SOURCE 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_profile.cc event_parse_data.cc - sql_signal.cc rpl_handler.cc mdl.cc + sql_connect.cc scheduler.cc sql_partition_admin.cc + sql_profile.cc event_parse_data.cc sql_alter_table.cc + sql_signal.cc rpl_handler.cc mdl.cc sql_table_maintenance.cc transaction.cc sys_vars.cc sql_truncate.cc datadict.cc ${GEN_SOURCES} ${MYSYS_LIBWRAP_SOURCE}) diff --git a/sql/Makefile.am b/sql/Makefile.am index 7fed55f3cd6..b99afcbdbeb 100644 --- a/sql/Makefile.am +++ b/sql/Makefile.am @@ -122,11 +122,11 @@ noinst_HEADERS = item.h item_func.h item_sum.h item_cmpfunc.h \ 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 \ - sql_audit.h \ + sql_audit.h sql_alter_table.h sql_partition_admin.h \ contributors.h sql_servers.h sql_signal.h records.h \ sql_prepare.h rpl_handler.h replication.h mdl.h \ sql_plist.h transaction.h sys_vars.h sql_truncate.h \ - datadict.h + sql_table_maintenance.h datadict.h mysqld_SOURCES = sql_lex.cc sql_handler.cc sql_partition.cc \ item.cc item_sum.cc item_buff.cc item_func.cc \ @@ -143,7 +143,8 @@ mysqld_SOURCES = sql_lex.cc sql_handler.cc sql_partition.cc \ datadict.cc sql_profile.cc \ sql_prepare.cc sql_error.cc sql_locale.cc \ sql_update.cc sql_delete.cc uniques.cc sql_do.cc \ - procedure.cc sql_test.cc sql_truncate.cc \ + procedure.cc sql_test.cc sql_table_maintenance.cc \ + sql_truncate.cc \ log.cc init.cc derror.cc sql_acl.cc \ unireg.cc des_key_file.cc \ log_event.cc rpl_record.cc \ @@ -171,7 +172,7 @@ mysqld_SOURCES = sql_lex.cc sql_handler.cc sql_partition.cc \ sql_builtin.cc sql_tablespace.cc partition_info.cc \ sql_servers.cc event_parse_data.cc sql_signal.cc \ rpl_handler.cc mdl.cc transaction.cc sql_audit.cc \ - sha2.cc + sql_alter_table.cc sql_partition_admin.cc sha2.cc nodist_mysqld_SOURCES = mini_client_errors.c pack.c client.c my_time.c my_user.c diff --git a/sql/datadict.cc b/sql/datadict.cc index 33c3b6bc700..362435a94db 100644 --- a/sql/datadict.cc +++ b/sql/datadict.cc @@ -22,7 +22,9 @@ /** Check type of .frm if we are not going to parse it. - @param path path to FRM file + @param[in] thd The current session. + @param[in] path path to FRM file. + @param[out] dbt db_type of the table if FRMTYPE_TABLE, otherwise undefined. @retval FRMTYPE_ERROR error @retval FRMTYPE_TABLE table @@ -65,6 +67,58 @@ frm_type_enum dd_frm_type(THD *thd, char *path, enum legacy_db_type *dbt) } +/** + Given a table name, check type of .frm and legacy table type. + + @param[in] thd The current session. + @param[in] db Table schema. + @param[in] table_name Table database. + @param[out] table_type handlerton of the table if FRMTYPE_TABLE, + otherwise undefined. + + @return FALSE if FRMTYPE_TABLE and storage engine found. TRUE otherwise. +*/ + +bool dd_frm_storage_engine(THD *thd, const char *db, const char *table_name, + handlerton **table_type) +{ + char path[FN_REFLEN + 1]; + enum legacy_db_type db_type; + LEX_STRING db_name = {(char *) db, strlen(db)}; + + /* There should be at least some lock on the table. */ + DBUG_ASSERT(thd->mdl_context.is_lock_owner(MDL_key::TABLE, db, + table_name, MDL_SHARED)); + + if (check_db_name(&db_name)) + { + my_error(ER_WRONG_DB_NAME, MYF(0), db_name.str); + return TRUE; + } + + if (check_table_name(table_name, strlen(table_name), FALSE)) + { + my_error(ER_WRONG_TABLE_NAME, MYF(0), table_name); + return TRUE; + } + + (void) build_table_filename(path, sizeof(path) - 1, db, + table_name, reg_ext, 0); + + dd_frm_type(thd, path, &db_type); + + /* Type is unknown if the object is not found or is not a table. */ + if (db_type == DB_TYPE_UNKNOWN || + !(*table_type= ha_resolve_by_legacy_type(thd, db_type))) + { + my_error(ER_NO_SUCH_TABLE, MYF(0), db, table_name); + return TRUE; + } + + return FALSE; +} + + /** Given a table name, check if the storage engine for the table referred by this name supports an option 'flag'. @@ -84,40 +138,11 @@ bool dd_check_storage_engine_flag(THD *thd, const char *db, const char *table_name, uint32 flag, bool *yes_no) { - char path[FN_REFLEN + 1]; - enum legacy_db_type db_type; handlerton *table_type; - LEX_STRING db_name = {(char *) db, strlen(db)}; - if (check_db_name(&db_name)) - { - my_error(ER_WRONG_DB_NAME, MYF(0), db_name.str); + if (dd_frm_storage_engine(thd, db, table_name, &table_type)) return TRUE; - } - if (check_table_name(table_name, strlen(table_name), FALSE)) - { - my_error(ER_WRONG_TABLE_NAME, MYF(0), table_name); - return TRUE; - } - - /* There should be at least some lock on the table. */ - DBUG_ASSERT(thd->mdl_context.is_lock_owner(MDL_key::TABLE, db, - table_name, MDL_SHARED)); - - (void) build_table_filename(path, sizeof(path) - 1, db, - table_name, reg_ext, 0); - - dd_frm_type(thd, path, &db_type); - - /* Type is unknown if the object is not found or is not a table. */ - if (db_type == DB_TYPE_UNKNOWN) - { - my_error(ER_NO_SUCH_TABLE, MYF(0), db, table_name); - return TRUE; - } - - table_type= ha_resolve_by_legacy_type(thd, db_type); *yes_no= ha_check_storage_engine_flag(table_type, flag); return FALSE; diff --git a/sql/datadict.h b/sql/datadict.h index 05b5a9bba4b..65e40998929 100644 --- a/sql/datadict.h +++ b/sql/datadict.h @@ -31,6 +31,8 @@ enum frm_type_enum frm_type_enum dd_frm_type(THD *thd, char *path, enum legacy_db_type *dbt); +bool dd_frm_storage_engine(THD *thd, const char *db, const char *table_name, + handlerton **table_type); bool dd_check_storage_engine_flag(THD *thd, const char *db, const char *table_name, uint32 flag, diff --git a/sql/sql_alter_table.cc b/sql/sql_alter_table.cc new file mode 100644 index 00000000000..607a8d5f5df --- /dev/null +++ b/sql/sql_alter_table.cc @@ -0,0 +1,106 @@ +/* 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 */ + +#include "sql_parse.h" // check_access, + // check_merge_table_access +#include "sql_table.h" // mysql_alter_table, + // mysql_exchange_partition +#include "sql_alter_table.h" + +bool Alter_table_statement::execute(THD *thd) +{ + LEX *lex= thd->lex; + /* first SELECT_LEX (have special meaning for many of non-SELECTcommands) */ + SELECT_LEX *select_lex= &lex->select_lex; + /* first table of first SELECT_LEX */ + TABLE_LIST *first_table= (TABLE_LIST*) select_lex->table_list.first; + /* + Code in mysql_alter_table() may modify its HA_CREATE_INFO argument, + so we have to use a copy of this structure to make execution + prepared statement- safe. A shallow copy is enough as no memory + referenced from this structure will be modified. + @todo move these into constructor... + */ + HA_CREATE_INFO create_info(lex->create_info); + Alter_info alter_info(lex->alter_info, thd->mem_root); + ulong priv=0; + ulong priv_needed= ALTER_ACL; + bool result; + + DBUG_ENTER("Alter_table_statement::execute"); + + if (thd->is_fatal_error) /* out of memory creating a copy of alter_info */ + DBUG_RETURN(TRUE); + /* + We also require DROP priv for ALTER TABLE ... DROP PARTITION, as well + as for RENAME TO, as being done by SQLCOM_RENAME_TABLE + */ + if (alter_info.flags & (ALTER_DROP_PARTITION | ALTER_RENAME)) + priv_needed|= DROP_ACL; + + /* Must be set in the parser */ + DBUG_ASSERT(select_lex->db); + DBUG_ASSERT(!(alter_info.flags & ALTER_ADMIN_PARTITION)); + if (check_access(thd, priv_needed, first_table->db, + &first_table->grant.privilege, + &first_table->grant.m_internal, + 0, 0) || + check_access(thd, INSERT_ACL | CREATE_ACL, select_lex->db, + &priv, + NULL, /* Don't use first_tab->grant with sel_lex->db */ + 0, 0) || + check_merge_table_access(thd, first_table->db, + create_info.merge_list.first)) + DBUG_RETURN(TRUE); /* purecov: inspected */ + + if (check_grant(thd, priv_needed, first_table, FALSE, UINT_MAX, FALSE)) + DBUG_RETURN(TRUE); /* purecov: inspected */ + + if (lex->name.str && !test_all_bits(priv, INSERT_ACL | CREATE_ACL)) + { + // Rename of table + TABLE_LIST tmp_table; + bzero((char*) &tmp_table,sizeof(tmp_table)); + tmp_table.table_name= lex->name.str; + tmp_table.db= select_lex->db; + tmp_table.grant.privilege= priv; + if (check_grant(thd, INSERT_ACL | CREATE_ACL, &tmp_table, FALSE, + UINT_MAX, FALSE)) + DBUG_RETURN(TRUE); /* purecov: inspected */ + } + + /* Don't yet allow changing of symlinks with ALTER TABLE */ + if (create_info.data_file_name) + push_warning_printf(thd, MYSQL_ERROR::WARN_LEVEL_WARN, + WARN_OPTION_IGNORED, ER(WARN_OPTION_IGNORED), + "DATA DIRECTORY"); + if (create_info.index_file_name) + push_warning_printf(thd, MYSQL_ERROR::WARN_LEVEL_WARN, + WARN_OPTION_IGNORED, ER(WARN_OPTION_IGNORED), + "INDEX DIRECTORY"); + create_info.data_file_name= create_info.index_file_name= NULL; + + thd->enable_slow_log= opt_log_slow_admin_statements; + + result= mysql_alter_table(thd, select_lex->db, lex->name.str, + &create_info, + first_table, + &alter_info, + select_lex->order_list.elements, + select_lex->order_list.first, + lex->ignore); + + DBUG_RETURN(result); +} diff --git a/sql/sql_alter_table.h b/sql/sql_alter_table.h new file mode 100644 index 00000000000..6a17f87f5a4 --- /dev/null +++ b/sql/sql_alter_table.h @@ -0,0 +1,66 @@ +/* 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 */ + +#ifndef SQL_ALTER_TABLE_H +#define SQL_ALTER_TABLE_H + +/** + Alter_table_common represents the common properties of the ALTER TABLE + statements. + @todo move Alter_info and other ALTER generic structures from Lex here. +*/ +class Alter_table_common : public Sql_statement +{ +protected: + /** + Constructor. + @param lex the LEX structure for this statement. + */ + Alter_table_common(LEX *lex) + : Sql_statement(lex) + {} + + virtual ~Alter_table_common() + {} + +}; + +/** + Alter_table_statement represents the generic ALTER TABLE statement. + @todo move Alter_info and other ALTER specific structures from Lex here. +*/ +class Alter_table_statement : public Alter_table_common +{ +public: + /** + Constructor, used to represent a ALTER TABLE statement. + @param lex the LEX structure for this statement. + */ + Alter_table_statement(LEX *lex) + : Alter_table_common(lex) + {} + + ~Alter_table_statement() + {} + + /** + Execute a ALTER TABLE statement at runtime. + @param thd the current thread. + @return false on success. + */ + bool execute(THD *thd); +}; + +#endif diff --git a/sql/sql_lex.cc b/sql/sql_lex.cc index b70f33a6c3f..140cdb21eef 100644 --- a/sql/sql_lex.cc +++ b/sql/sql_lex.cc @@ -401,6 +401,7 @@ void lex_start(THD *thd) lex->spname= NULL; lex->sphead= NULL; lex->spcont= NULL; + lex->m_stmt= NULL; lex->proc_list.first= 0; lex->escape_used= FALSE; lex->query_tables= 0; diff --git a/sql/sql_lex.h b/sql/sql_lex.h index e6c4e69d1a6..d0f20d4e997 100644 --- a/sql/sql_lex.h +++ b/sql/sql_lex.h @@ -919,6 +919,24 @@ enum enum_alter_table_change_level ALTER_TABLE_INDEX_CHANGED= 2 }; + +/** + Temporary hack to enable a class bound forward declaration + of the enum_alter_table_change_level enumeration. To be + removed once Alter_info is moved to the sql_alter_table.h + header. +*/ +class Alter_table_change_level +{ +private: + typedef enum enum_alter_table_change_level enum_type; + enum_type value; +public: + void operator = (enum_type v) { value = v; } + operator enum_type () { return value; } +}; + + /** @brief Parsing data for CREATE or ALTER TABLE. diff --git a/sql/sql_parse.cc b/sql/sql_parse.cc index fbcfb3f49c2..2f02188d122 100644 --- a/sql/sql_parse.cc +++ b/sql/sql_parse.cc @@ -50,6 +50,7 @@ // mysql_backup_table, // mysql_restore_table #include "sql_truncate.h" // mysql_truncate_table +#include "sql_table_maintenance.h" // mysql_assign_to_keycache #include "sql_connect.h" // check_user, // decrease_user_connections, // thd_init_client_charset, check_mqh, @@ -659,8 +660,7 @@ end: every child. Set 'db' for every child if not present. */ #ifndef NO_EMBEDDED_ACCESS_CHECKS -static bool check_merge_table_access(THD *thd, char *db, - TABLE_LIST *table_list) +bool check_merge_table_access(THD *thd, char *db, TABLE_LIST *table_list) { int error= 0; @@ -2831,77 +2831,6 @@ end_with_restore_list: } #endif /* HAVE_REPLICATION */ - case SQLCOM_ALTER_TABLE: - DBUG_ASSERT(first_table == all_tables && first_table != 0); - { - ulong priv=0; - ulong priv_needed= ALTER_ACL; - /* - Code in mysql_alter_table() may modify its HA_CREATE_INFO argument, - so we have to use a copy of this structure to make execution - prepared statement- safe. A shallow copy is enough as no memory - referenced from this structure will be modified. - */ - HA_CREATE_INFO create_info(lex->create_info); - Alter_info alter_info(lex->alter_info, thd->mem_root); - - if (thd->is_fatal_error) /* out of memory creating a copy of alter_info */ - goto error; - /* - We also require DROP priv for ALTER TABLE ... DROP PARTITION, as well - as for RENAME TO, as being done by SQLCOM_RENAME_TABLE - */ - if (alter_info.flags & (ALTER_DROP_PARTITION | ALTER_RENAME)) - priv_needed|= DROP_ACL; - - /* Must be set in the parser */ - DBUG_ASSERT(select_lex->db); - if (check_access(thd, priv_needed, first_table->db, - &first_table->grant.privilege, - &first_table->grant.m_internal, - 0, 0) || - check_access(thd, INSERT_ACL | CREATE_ACL, select_lex->db, - &priv, - NULL, /* Do not use first_table->grant with select_lex->db */ - 0, 0) || - check_merge_table_access(thd, first_table->db, - create_info.merge_list.first)) - goto error; /* purecov: inspected */ - if (check_grant(thd, priv_needed, all_tables, FALSE, UINT_MAX, FALSE)) - goto error; - if (lex->name.str && !test_all_bits(priv,INSERT_ACL | CREATE_ACL)) - { // Rename of table - TABLE_LIST tmp_table; - bzero((char*) &tmp_table,sizeof(tmp_table)); - tmp_table.table_name= lex->name.str; - tmp_table.db=select_lex->db; - tmp_table.grant.privilege=priv; - if (check_grant(thd, INSERT_ACL | CREATE_ACL, &tmp_table, FALSE, - UINT_MAX, FALSE)) - goto error; - } - - /* Don't yet allow changing of symlinks with ALTER TABLE */ - if (create_info.data_file_name) - push_warning_printf(thd, MYSQL_ERROR::WARN_LEVEL_WARN, - WARN_OPTION_IGNORED, ER(WARN_OPTION_IGNORED), - "DATA DIRECTORY"); - if (create_info.index_file_name) - push_warning_printf(thd, MYSQL_ERROR::WARN_LEVEL_WARN, - WARN_OPTION_IGNORED, ER(WARN_OPTION_IGNORED), - "INDEX DIRECTORY"); - create_info.data_file_name= create_info.index_file_name= NULL; - - thd->enable_slow_log= opt_log_slow_admin_statements; - res= mysql_alter_table(thd, select_lex->db, lex->name.str, - &create_info, - first_table, - &alter_info, - select_lex->order_list.elements, - select_lex->order_list.first, - lex->ignore); - break; - } case SQLCOM_RENAME_TABLE: { DBUG_ASSERT(first_table == all_tables && first_table != 0); @@ -3021,81 +2950,6 @@ end_with_restore_list: res = mysql_checksum_table(thd, first_table, &lex->check_opt); break; } - case SQLCOM_REPAIR: - { - DBUG_ASSERT(first_table == all_tables && first_table != 0); - if (check_table_access(thd, SELECT_ACL | INSERT_ACL, all_tables, - FALSE, UINT_MAX, FALSE)) - goto error; /* purecov: inspected */ - thd->enable_slow_log= opt_log_slow_admin_statements; - res= mysql_repair_table(thd, first_table, &lex->check_opt); - /* ! we write after unlocking the table */ - if (!res && !lex->no_write_to_binlog) - { - /* - Presumably, REPAIR and binlog writing doesn't require synchronization - */ - res= write_bin_log(thd, TRUE, thd->query(), thd->query_length()); - } - select_lex->table_list.first= first_table; - lex->query_tables=all_tables; - break; - } - case SQLCOM_CHECK: - { - DBUG_ASSERT(first_table == all_tables && first_table != 0); - if (check_table_access(thd, SELECT_ACL, all_tables, - TRUE, UINT_MAX, FALSE)) - goto error; /* purecov: inspected */ - thd->enable_slow_log= opt_log_slow_admin_statements; - res = mysql_check_table(thd, first_table, &lex->check_opt); - select_lex->table_list.first= first_table; - lex->query_tables=all_tables; - break; - } - case SQLCOM_ANALYZE: - { - DBUG_ASSERT(first_table == all_tables && first_table != 0); - if (check_table_access(thd, SELECT_ACL | INSERT_ACL, all_tables, - FALSE, UINT_MAX, FALSE)) - goto error; /* purecov: inspected */ - thd->enable_slow_log= opt_log_slow_admin_statements; - res= mysql_analyze_table(thd, first_table, &lex->check_opt); - /* ! we write after unlocking the table */ - if (!res && !lex->no_write_to_binlog) - { - /* - Presumably, ANALYZE and binlog writing doesn't require synchronization - */ - res= write_bin_log(thd, TRUE, thd->query(), thd->query_length()); - } - select_lex->table_list.first= first_table; - lex->query_tables=all_tables; - break; - } - - case SQLCOM_OPTIMIZE: - { - DBUG_ASSERT(first_table == all_tables && first_table != 0); - if (check_table_access(thd, SELECT_ACL | INSERT_ACL, all_tables, - FALSE, UINT_MAX, FALSE)) - goto error; /* purecov: inspected */ - thd->enable_slow_log= opt_log_slow_admin_statements; - res= (specialflag & (SPECIAL_SAFE_MODE | SPECIAL_NO_NEW_FUNC)) ? - mysql_recreate_table(thd, first_table) : - mysql_optimize_table(thd, first_table, &lex->check_opt); - /* ! we write after unlocking the table */ - if (!res && !lex->no_write_to_binlog) - { - /* - Presumably, OPTIMIZE and binlog writing doesn't require synchronization - */ - res= write_bin_log(thd, TRUE, thd->query(), thd->query_length()); - } - select_lex->table_list.first= first_table; - lex->query_tables=all_tables; - break; - } case SQLCOM_UPDATE: { ha_rows found= 0, updated= 0; @@ -3316,23 +3170,6 @@ end_with_restore_list: break; } - case SQLCOM_TRUNCATE: - DBUG_ASSERT(first_table == all_tables && first_table != 0); - if (check_one_table_access(thd, DROP_ACL, all_tables)) - goto error; - /* - Don't allow this within a transaction because we want to use - re-generate table - */ - if (thd->in_active_multi_stmt_transaction()) - { - my_message(ER_LOCK_OR_ACTIVE_TRANSACTION, - ER(ER_LOCK_OR_ACTIVE_TRANSACTION), MYF(0)); - goto error; - } - if (! (res= mysql_truncate_table(thd, first_table))) - my_ok(thd); - break; case SQLCOM_DELETE: { DBUG_ASSERT(first_table == all_tables && first_table != 0); @@ -4718,6 +4555,14 @@ create_sp_error: my_ok(thd, 1); break; } + case SQLCOM_ANALYZE: + case SQLCOM_CHECK: + case SQLCOM_OPTIMIZE: + case SQLCOM_REPAIR: + case SQLCOM_TRUNCATE: + case SQLCOM_ALTER_TABLE: + DBUG_ASSERT(first_table == all_tables && first_table != 0); + /* fall through */ case SQLCOM_SIGNAL: case SQLCOM_RESIGNAL: DBUG_ASSERT(lex->m_stmt != NULL); @@ -7853,6 +7698,7 @@ bool parse_sql(THD *thd, { bool ret_value; DBUG_ASSERT(thd->m_parser_state == NULL); + DBUG_ASSERT(thd->lex->m_stmt == NULL); MYSQL_QUERY_PARSE_START(thd->query()); /* Backup creation context. */ diff --git a/sql/sql_parse.h b/sql/sql_parse.h index 8b7fe8f7b83..dd5b8aacc0a 100644 --- a/sql/sql_parse.h +++ b/sql/sql_parse.h @@ -155,6 +155,7 @@ bool check_single_table_access(THD *thd, ulong privilege, bool check_routine_access(THD *thd,ulong want_access,char *db,char *name, bool is_proc, bool no_errors); bool check_some_access(THD *thd, ulong want_access, TABLE_LIST *table); +bool check_merge_table_access(THD *thd, char *db, TABLE_LIST *table_list); bool check_some_routine_access(THD *thd, const char *db, const char *name, bool is_proc); bool check_access(THD *thd, ulong want_access, const char *db, ulong *save_priv, GRANT_INTERNAL_INFO *grant_internal_info, diff --git a/sql/sql_partition_admin.cc b/sql/sql_partition_admin.cc new file mode 100644 index 00000000000..fc0183e9b3d --- /dev/null +++ b/sql/sql_partition_admin.cc @@ -0,0 +1,139 @@ +/* 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 */ + +#include "sql_parse.h" // check_one_table_access +#include "sql_table.h" // mysql_alter_table, etc. +#include "sql_lex.h" // Sql_statement +#include "sql_truncate.h" // mysql_truncate_table, + // Truncate_statement +#include "sql_table_maintenance.h" // Analyze/Check/.._table_statement +#include "sql_partition_admin.h" // Alter_table_*_partition + +#ifndef WITH_PARTITION_STORAGE_ENGINE + +bool Partition_statement_unsupported::execute(THD *) +{ + DBUG_ENTER("Partition_statement_unsupported::execute"); + /* error, partitioning support not compiled in... */ + my_error(ER_FEATURE_DISABLED, MYF(0), "partitioning", + "--with-plugin-partition"); + DBUG_RETURN(TRUE); +} + +#else + +bool Alter_table_analyze_partition_statement::execute(THD *thd) +{ + bool res; + DBUG_ENTER("Alter_table_analyze_partition_statement::execute"); + + /* + Flag that it is an ALTER command which administrates partitions, used + by ha_partition + */ + m_lex->alter_info.flags|= ALTER_ADMIN_PARTITION; + + res= Analyze_table_statement::execute(thd); + + DBUG_RETURN(res); +} + + +bool Alter_table_check_partition_statement::execute(THD *thd) +{ + bool res; + DBUG_ENTER("Alter_table_check_partition_statement::execute"); + + /* + Flag that it is an ALTER command which administrates partitions, used + by ha_partition + */ + m_lex->alter_info.flags|= ALTER_ADMIN_PARTITION; + + res= Check_table_statement::execute(thd); + + DBUG_RETURN(res); +} + + +bool Alter_table_optimize_partition_statement::execute(THD *thd) +{ + bool res; + DBUG_ENTER("Alter_table_optimize_partition_statement::execute"); + + /* + Flag that it is an ALTER command which administrates partitions, used + by ha_partition + */ + m_lex->alter_info.flags|= ALTER_ADMIN_PARTITION; + + res= Optimize_table_statement::execute(thd); + + DBUG_RETURN(res); +} + + +bool Alter_table_repair_partition_statement::execute(THD *thd) +{ + bool res; + DBUG_ENTER("Alter_table_repair_partition_statement::execute"); + + /* + Flag that it is an ALTER command which administrates partitions, used + by ha_partition + */ + m_lex->alter_info.flags|= ALTER_ADMIN_PARTITION; + + res= Repair_table_statement::execute(thd); + + DBUG_RETURN(res); +} + + +bool Alter_table_truncate_partition_statement::execute(THD *thd) +{ + TABLE_LIST *first_table= thd->lex->select_lex.table_list.first; + bool res; + enum_sql_command original_sql_command; + DBUG_ENTER("Alter_table_truncate_partition_statement::execute"); + + /* + Execute TRUNCATE PARTITION just like TRUNCATE TABLE. + Some storage engines (InnoDB, partition) checks thd_sql_command, + so we set it to SQLCOM_TRUNCATE during the execution. + */ + original_sql_command= m_lex->sql_command; + m_lex->sql_command= SQLCOM_TRUNCATE; + + /* + Flag that it is an ALTER command which administrates partitions, used + by ha_partition. + */ + m_lex->alter_info.flags|= ALTER_ADMIN_PARTITION; + + /* + Fix the lock types (not the same as ordinary ALTER TABLE). + */ + first_table->lock_type= TL_WRITE; + first_table->mdl_request.set_type(MDL_SHARED_NO_READ_WRITE); + + /* execute as a TRUNCATE TABLE */ + res= Truncate_statement::execute(thd); + + m_lex->sql_command= original_sql_command; + DBUG_RETURN(res); +} + +#endif /* WITH_PARTITION_STORAGE_ENGINE */ diff --git a/sql/sql_partition_admin.h b/sql/sql_partition_admin.h new file mode 100644 index 00000000000..36bafec4202 --- /dev/null +++ b/sql/sql_partition_admin.h @@ -0,0 +1,236 @@ +/* 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 */ + +#ifndef SQL_PARTITION_ADMIN_H +#define SQL_PARTITION_ADMIN_H + +#ifndef WITH_PARTITION_STORAGE_ENGINE + +/** + Stub class that returns a error if the partition storage engine is + not supported. +*/ +class Partition_statement_unsupported : public Sql_statement +{ +public: + Partition_statement_unsupported(LEX *lex) + : Sql_statement(lex) + {} + + ~Partition_statement_unsupported() + {} + + bool execute(THD *thd); +}; + + +class Alter_table_analyze_partition_statement : + public Partition_statement_unsupported +{ +public: + Alter_table_analyze_partition_statement(LEX *lex) + : Partition_statement_unsupported(lex) + {} + + ~Alter_table_analyze_partition_statement() + {} +}; + + +class Alter_table_check_partition_statement : + public Partition_statement_unsupported +{ +public: + Alter_table_check_partition_statement(LEX *lex) + : Partition_statement_unsupported(lex) + {} + + ~Alter_table_check_partition_statement() + {} +}; + + +class Alter_table_optimize_partition_statement : + public Partition_statement_unsupported +{ +public: + Alter_table_optimize_partition_statement(LEX *lex) + : Partition_statement_unsupported(lex) + {} + + ~Alter_table_optimize_partition_statement() + {} +}; + + +class Alter_table_repair_partition_statement : + public Partition_statement_unsupported +{ +public: + Alter_table_repair_partition_statement(LEX *lex) + : Partition_statement_unsupported(lex) + {} + + ~Alter_table_repair_partition_statement() + {} +}; + + +class Alter_table_truncate_partition_statement : + public Partition_statement_unsupported +{ +public: + Alter_table_truncate_partition_statement(LEX *lex) + : Partition_statement_unsupported(lex) + {} + + ~Alter_table_truncate_partition_statement() + {} +}; + + +#else + +/** + Class that represents the ALTER TABLE t1 ANALYZE PARTITION p statement. +*/ +class Alter_table_analyze_partition_statement : public Analyze_table_statement +{ +public: + /** + Constructor, used to represent a ALTER TABLE ANALYZE PARTITION statement. + @param lex the LEX structure for this statement. + */ + Alter_table_analyze_partition_statement(LEX *lex) + : Analyze_table_statement(lex) + {} + + ~Alter_table_analyze_partition_statement() + {} + + /** + Execute a ALTER TABLE ANALYZE PARTITION statement at runtime. + @param thd the current thread. + @return false on success. + */ + bool execute(THD *thd); +}; + + +/** + Class that represents the ALTER TABLE t1 CHECK PARTITION p statement. +*/ +class Alter_table_check_partition_statement : public Check_table_statement +{ +public: + /** + Constructor, used to represent a ALTER TABLE CHECK PARTITION statement. + @param lex the LEX structure for this statement. + */ + Alter_table_check_partition_statement(LEX *lex) + : Check_table_statement(lex) + {} + + ~Alter_table_check_partition_statement() + {} + + /** + Execute a ALTER TABLE CHECK PARTITION statement at runtime. + @param thd the current thread. + @return false on success. + */ + bool execute(THD *thd); +}; + + +/** + Class that represents the ALTER TABLE t1 OPTIMIZE PARTITION p statement. +*/ +class Alter_table_optimize_partition_statement : public Optimize_table_statement +{ +public: + /** + Constructor, used to represent a ALTER TABLE OPTIMIZE PARTITION statement. + @param lex the LEX structure for this statement. + */ + Alter_table_optimize_partition_statement(LEX *lex) + : Optimize_table_statement(lex) + {} + + ~Alter_table_optimize_partition_statement() + {} + + /** + Execute a ALTER TABLE OPTIMIZE PARTITION statement at runtime. + @param thd the current thread. + @return false on success. + */ + bool execute(THD *thd); +}; + + +/** + Class that represents the ALTER TABLE t1 REPAIR PARTITION p statement. +*/ +class Alter_table_repair_partition_statement : public Repair_table_statement +{ +public: + /** + Constructor, used to represent a ALTER TABLE REPAIR PARTITION statement. + @param lex the LEX structure for this statement. + */ + Alter_table_repair_partition_statement(LEX *lex) + : Repair_table_statement(lex) + {} + + ~Alter_table_repair_partition_statement() + {} + + /** + Execute a ALTER TABLE REPAIR PARTITION statement at runtime. + @param thd the current thread. + @return false on success. + */ + bool execute(THD *thd); +}; + + +/** + Class that represents the ALTER TABLE t1 TRUNCATE PARTITION p statement. +*/ +class Alter_table_truncate_partition_statement : public Truncate_statement +{ +public: + /** + Constructor, used to represent a ALTER TABLE TRUNCATE PARTITION statement. + @param lex the LEX structure for this statement. + */ + Alter_table_truncate_partition_statement(LEX *lex) + : Truncate_statement(lex) + {} + + ~Alter_table_truncate_partition_statement() + {} + + /** + Execute a ALTER TABLE TRUNCATE PARTITION statement at runtime. + @param thd the current thread. + @return false on success. + */ + bool execute(THD *thd); +}; + +#endif /* WITH_PARTITION_STORAGE_ENGINE */ +#endif /* SQL_PARTITION_ADMIN_H */ diff --git a/sql/sql_table.cc b/sql/sql_table.cc index 7f8e4f68ec5..1db7aa55792 100644 --- a/sql/sql_table.cc +++ b/sql/sql_table.cc @@ -51,7 +51,6 @@ #include "sql_parse.h" #include "sql_show.h" #include "transaction.h" -#include "keycaches.h" #include "datadict.h" // dd_frm_type() #ifdef __WIN__ @@ -78,10 +77,6 @@ mysql_prepare_create_table(THD *thd, HA_CREATE_INFO *create_info, uint *db_options, handler *file, KEY **key_info_buffer, uint *key_count, int select_field_count); -static bool -mysql_prepare_alter_table(THD *thd, TABLE *table, - HA_CREATE_INFO *create_info, - Alter_info *alter_info); /** @@ -4394,885 +4389,6 @@ mysql_rename_table(handlerton *base, const char *old_db, } -static int send_check_errmsg(THD *thd, TABLE_LIST* table, - const char* operator_name, const char* errmsg) - -{ - Protocol *protocol= thd->protocol; - protocol->prepare_for_resend(); - protocol->store(table->alias, system_charset_info); - protocol->store((char*) operator_name, system_charset_info); - protocol->store(STRING_WITH_LEN("error"), system_charset_info); - protocol->store(errmsg, system_charset_info); - thd->clear_error(); - if (protocol->write()) - return -1; - return 1; -} - - -static int prepare_for_repair(THD *thd, TABLE_LIST *table_list, - HA_CHECK_OPT *check_opt) -{ - int error= 0; - TABLE tmp_table, *table; - TABLE_SHARE *share; - bool has_mdl_lock= FALSE; - char from[FN_REFLEN],tmp[FN_REFLEN+32]; - const char **ext; - MY_STAT stat_info; - Open_table_context ot_ctx(thd, (MYSQL_OPEN_IGNORE_FLUSH | - MYSQL_OPEN_HAS_MDL_LOCK | - MYSQL_LOCK_IGNORE_TIMEOUT)); - DBUG_ENTER("prepare_for_repair"); - - if (!(check_opt->sql_flags & TT_USEFRM)) - DBUG_RETURN(0); - - if (!(table= table_list->table)) - { - char key[MAX_DBKEY_LENGTH]; - uint key_length; - /* - If the table didn't exist, we have a shared metadata lock - on it that is left from mysql_admin_table()'s attempt to - open it. Release the shared metadata lock before trying to - acquire the exclusive lock to satisfy MDL asserts and avoid - deadlocks. - */ - thd->mdl_context.release_transactional_locks(); - /* - Attempt to do full-blown table open in mysql_admin_table() has failed. - Let us try to open at least a .FRM for this table. - */ - my_hash_value_type hash_value; - - key_length= create_table_def_key(thd, key, table_list, 0); - table_list->mdl_request.init(MDL_key::TABLE, - table_list->db, table_list->table_name, - MDL_EXCLUSIVE); - - if (lock_table_names(thd, table_list, table_list->next_global, - thd->variables.lock_wait_timeout, - MYSQL_OPEN_SKIP_TEMPORARY)) - DBUG_RETURN(0); - has_mdl_lock= TRUE; - - hash_value= my_calc_hash(&table_def_cache, (uchar*) key, key_length); - mysql_mutex_lock(&LOCK_open); - if (!(share= (get_table_share(thd, table_list, key, key_length, 0, - &error, hash_value)))) - { - mysql_mutex_unlock(&LOCK_open); - DBUG_RETURN(0); // Can't open frm file - } - - if (open_table_from_share(thd, share, "", 0, 0, 0, &tmp_table, FALSE)) - { - release_table_share(share); - mysql_mutex_unlock(&LOCK_open); - DBUG_RETURN(0); // Out of memory - } - mysql_mutex_unlock(&LOCK_open); - table= &tmp_table; - } - - /* A MERGE table must not come here. */ - DBUG_ASSERT(table->file->ht->db_type != DB_TYPE_MRG_MYISAM); - - /* - REPAIR TABLE ... USE_FRM for temporary tables makes little sense. - */ - if (table->s->tmp_table) - { - error= send_check_errmsg(thd, table_list, "repair", - "Cannot repair temporary table from .frm file"); - goto end; - } - - /* - User gave us USE_FRM which means that the header in the index file is - trashed. - In this case we will try to fix the table the following way: - - Rename the data file to a temporary name - - Truncate the table - - Replace the new data file with the old one - - Run a normal repair using the new index file and the old data file - */ - - if (table->s->frm_version != FRM_VER_TRUE_VARCHAR) - { - error= send_check_errmsg(thd, table_list, "repair", - "Failed repairing incompatible .frm file"); - goto end; - } - - /* - Check if this is a table type that stores index and data separately, - like ISAM or MyISAM. We assume fixed order of engine file name - extentions array. First element of engine file name extentions array - is meta/index file extention. Second element - data file extention. - */ - ext= table->file->bas_ext(); - if (!ext[0] || !ext[1]) - goto end; // No data file - - // Name of data file - strxmov(from, table->s->normalized_path.str, ext[1], NullS); - if (!mysql_file_stat(key_file_misc, from, &stat_info, MYF(0))) - goto end; // Can't use USE_FRM flag - - my_snprintf(tmp, sizeof(tmp), "%s-%lx_%lx", - from, current_pid, thd->thread_id); - - if (table_list->table) - { - /* - Table was successfully open in mysql_admin_table(). Now we need - to close it, but leave it protected by exclusive metadata lock. - */ - if (wait_while_table_is_used(thd, table, HA_EXTRA_FORCE_REOPEN)) - goto end; - close_all_tables_for_name(thd, table_list->table->s, FALSE); - table_list->table= 0; - } - /* - After this point we have an exclusive metadata lock on our table - in both cases when table was successfully open in mysql_admin_table() - and when it was open in prepare_for_repair(). - */ - - if (my_rename(from, tmp, MYF(MY_WME))) - { - error= send_check_errmsg(thd, table_list, "repair", - "Failed renaming data file"); - goto end; - } - if (dd_recreate_table(thd, table_list->db, table_list->table_name)) - { - error= send_check_errmsg(thd, table_list, "repair", - "Failed generating table from .frm file"); - goto end; - } - /* - 'FALSE' for 'using_transactions' means don't postpone - invalidation till the end of a transaction, but do it - immediately. - */ - query_cache_invalidate3(thd, table_list, FALSE); - if (mysql_file_rename(key_file_misc, tmp, from, MYF(MY_WME))) - { - error= send_check_errmsg(thd, table_list, "repair", - "Failed restoring .MYD file"); - goto end; - } - - if (thd->locked_tables_list.reopen_tables(thd)) - goto end; - - /* - Now we should be able to open the partially repaired table - to finish the repair in the handler later on. - */ - if (open_table(thd, table_list, thd->mem_root, &ot_ctx)) - { - error= send_check_errmsg(thd, table_list, "repair", - "Failed to open partially repaired table"); - goto end; - } - -end: - thd->locked_tables_list.unlink_all_closed_tables(thd, NULL, 0); - if (table == &tmp_table) - { - mysql_mutex_lock(&LOCK_open); - closefrm(table, 1); // Free allocated memory - mysql_mutex_unlock(&LOCK_open); - } - /* In case of a temporary table there will be no metadata lock. */ - if (error && has_mdl_lock) - thd->mdl_context.release_transactional_locks(); - - DBUG_RETURN(error); -} - - - -/* - RETURN VALUES - FALSE Message sent to net (admin operation went ok) - TRUE Message should be sent by caller - (admin operation or network communication failed) -*/ -static bool mysql_admin_table(THD* thd, TABLE_LIST* tables, - HA_CHECK_OPT* check_opt, - const char *operator_name, - thr_lock_type lock_type, - bool open_for_modify, - bool no_warnings_for_error, - uint extra_open_options, - int (*prepare_func)(THD *, TABLE_LIST *, - HA_CHECK_OPT *), - int (handler::*operator_func)(THD *, - HA_CHECK_OPT *), - int (view_operator_func)(THD *, TABLE_LIST*)) -{ - TABLE_LIST *table; - SELECT_LEX *select= &thd->lex->select_lex; - List field_list; - Item *item; - Protocol *protocol= thd->protocol; - LEX *lex= thd->lex; - int result_code; - DBUG_ENTER("mysql_admin_table"); - - field_list.push_back(item = new Item_empty_string("Table", NAME_CHAR_LEN*2)); - item->maybe_null = 1; - field_list.push_back(item = new Item_empty_string("Op", 10)); - item->maybe_null = 1; - field_list.push_back(item = new Item_empty_string("Msg_type", 10)); - item->maybe_null = 1; - field_list.push_back(item = new Item_empty_string("Msg_text", 255)); - item->maybe_null = 1; - if (protocol->send_result_set_metadata(&field_list, - Protocol::SEND_NUM_ROWS | Protocol::SEND_EOF)) - DBUG_RETURN(TRUE); - - mysql_ha_rm_tables(thd, tables); - - for (table= tables; table; table= table->next_local) - { - char table_name[NAME_LEN*2+2]; - char* db = table->db; - bool fatal_error=0; - bool open_error; - - DBUG_PRINT("admin", ("table: '%s'.'%s'", table->db, table->table_name)); - DBUG_PRINT("admin", ("extra_open_options: %u", extra_open_options)); - strxmov(table_name, db, ".", table->table_name, NullS); - thd->open_options|= extra_open_options; - table->lock_type= lock_type; - /* - To make code safe for re-execution we need to reset type of MDL - request as code below may change it. - To allow concurrent execution of read-only operations we acquire - weak metadata lock for them. - */ - table->mdl_request.set_type((lock_type >= TL_WRITE_ALLOW_WRITE) ? - MDL_SHARED_NO_READ_WRITE : MDL_SHARED_READ); - /* open only one table from local list of command */ - { - TABLE_LIST *save_next_global, *save_next_local; - save_next_global= table->next_global; - table->next_global= 0; - save_next_local= table->next_local; - table->next_local= 0; - select->table_list.first= table; - /* - Time zone tables and SP tables can be add to lex->query_tables list, - so it have to be prepared. - TODO: Investigate if we can put extra tables into argument instead of - using lex->query_tables - */ - lex->query_tables= table; - lex->query_tables_last= &table->next_global; - lex->query_tables_own_last= 0; - thd->no_warnings_for_error= no_warnings_for_error; - if (view_operator_func == NULL) - table->required_type=FRMTYPE_TABLE; - - open_error= open_and_lock_tables(thd, table, TRUE, 0); - thd->no_warnings_for_error= 0; - table->next_global= save_next_global; - table->next_local= save_next_local; - thd->open_options&= ~extra_open_options; - /* - Under locked tables, we know that the table can be opened, - so any errors opening the table are logical errors. - In these cases it does not make sense to try to repair. - */ - if (open_error && thd->locked_tables_mode) - { - result_code= HA_ADMIN_FAILED; - goto send_result; - } -#ifdef WITH_PARTITION_STORAGE_ENGINE - if (table->table) - { - /* - Set up which partitions that should be processed - if ALTER TABLE t ANALYZE/CHECK/OPTIMIZE/REPAIR PARTITION .. - CACHE INDEX/LOAD INDEX for specified partitions - */ - Alter_info *alter_info= &lex->alter_info; - - if (alter_info->flags & ALTER_ADMIN_PARTITION) - { - if (!table->table->part_info) - { - my_error(ER_PARTITION_MGMT_ON_NONPARTITIONED, MYF(0)); - DBUG_RETURN(TRUE); - } - uint num_parts_found; - uint num_parts_opt= alter_info->partition_names.elements; - num_parts_found= set_part_state(alter_info, table->table->part_info, - PART_ADMIN); - if (num_parts_found != num_parts_opt && - (!(alter_info->flags & ALTER_ALL_PARTITION))) - { - char buff[FN_REFLEN + MYSQL_ERRMSG_SIZE]; - size_t length; - DBUG_PRINT("admin", ("sending non existent partition error")); - protocol->prepare_for_resend(); - protocol->store(table_name, system_charset_info); - protocol->store(operator_name, system_charset_info); - protocol->store(STRING_WITH_LEN("error"), system_charset_info); - length= my_snprintf(buff, sizeof(buff), - ER(ER_DROP_PARTITION_NON_EXISTENT), - table_name); - protocol->store(buff, length, system_charset_info); - if(protocol->write()) - goto err; - my_eof(thd); - goto err; - } - } - } -#endif - } - DBUG_PRINT("admin", ("table: 0x%lx", (long) table->table)); - - if (prepare_func) - { - DBUG_PRINT("admin", ("calling prepare_func")); - switch ((*prepare_func)(thd, table, check_opt)) { - case 1: // error, message written to net - trans_rollback_stmt(thd); - trans_rollback(thd); - close_thread_tables(thd); - thd->mdl_context.release_transactional_locks(); - DBUG_PRINT("admin", ("simple error, admin next table")); - continue; - case -1: // error, message could be written to net - /* purecov: begin inspected */ - DBUG_PRINT("admin", ("severe error, stop")); - goto err; - /* purecov: end */ - default: // should be 0 otherwise - DBUG_PRINT("admin", ("prepare_func succeeded")); - ; - } - } - - /* - CHECK TABLE command is only command where VIEW allowed here and this - command use only temporary teble method for VIEWs resolving => there - can't be VIEW tree substitition of join view => if opening table - succeed then table->table will have real TABLE pointer as value (in - case of join view substitution table->table can be 0, but here it is - impossible) - */ - if (!table->table) - { - DBUG_PRINT("admin", ("open table failed")); - if (thd->warning_info->is_empty()) - push_warning(thd, MYSQL_ERROR::WARN_LEVEL_WARN, - ER_CHECK_NO_SUCH_TABLE, ER(ER_CHECK_NO_SUCH_TABLE)); - /* if it was a view will check md5 sum */ - if (table->view && - view_checksum(thd, table) == HA_ADMIN_WRONG_CHECKSUM) - push_warning(thd, MYSQL_ERROR::WARN_LEVEL_WARN, - ER_VIEW_CHECKSUM, ER(ER_VIEW_CHECKSUM)); - if (thd->stmt_da->is_error() && - (thd->stmt_da->sql_errno() == ER_NO_SUCH_TABLE || - thd->stmt_da->sql_errno() == ER_FILE_NOT_FOUND)) - /* A missing table is just issued as a failed command */ - result_code= HA_ADMIN_FAILED; - else - /* Default failure code is corrupt table */ - result_code= HA_ADMIN_CORRUPT; - goto send_result; - } - - if (table->view) - { - DBUG_PRINT("admin", ("calling view_operator_func")); - result_code= (*view_operator_func)(thd, table); - goto send_result; - } - - if (table->schema_table) - { - result_code= HA_ADMIN_NOT_IMPLEMENTED; - goto send_result; - } - - if ((table->table->db_stat & HA_READ_ONLY) && open_for_modify) - { - /* purecov: begin inspected */ - char buff[FN_REFLEN + MYSQL_ERRMSG_SIZE]; - size_t length; - enum_sql_command save_sql_command= lex->sql_command; - DBUG_PRINT("admin", ("sending error message")); - protocol->prepare_for_resend(); - protocol->store(table_name, system_charset_info); - protocol->store(operator_name, system_charset_info); - protocol->store(STRING_WITH_LEN("error"), system_charset_info); - length= my_snprintf(buff, sizeof(buff), ER(ER_OPEN_AS_READONLY), - table_name); - protocol->store(buff, length, system_charset_info); - trans_commit_stmt(thd); - trans_commit(thd); - close_thread_tables(thd); - thd->mdl_context.release_transactional_locks(); - lex->reset_query_tables_list(FALSE); - /* - Restore Query_tables_list::sql_command value to make statement - safe for re-execution. - */ - lex->sql_command= save_sql_command; - table->table=0; // For query cache - if (protocol->write()) - goto err; - thd->stmt_da->reset_diagnostics_area(); - continue; - /* purecov: end */ - } - - /* - Close all instances of the table to allow MyISAM "repair" - to rename files. - @todo: This code does not close all instances of the table. - It only closes instances in other connections, but if this - connection has LOCK TABLE t1 a READ, t1 b WRITE, - both t1 instances will be kept open. - There is no need to execute this branch for InnoDB, which does - repair by recreate. There is no need to do it for OPTIMIZE, - which doesn't move files around. - Hence, this code should be moved to prepare_for_repair(), - and executed only for MyISAM engine. - */ - if (lock_type == TL_WRITE && !table->table->s->tmp_table) - { - if (wait_while_table_is_used(thd, table->table, - HA_EXTRA_PREPARE_FOR_RENAME)) - goto err; - DEBUG_SYNC(thd, "after_admin_flush"); - /* Flush entries in the query cache involving this table. */ - query_cache_invalidate3(thd, table->table, 0); - /* - XXX: hack: switch off open_for_modify to skip the - flush that is made later in the execution flow. - */ - open_for_modify= 0; - } - - if (table->table->s->crashed && operator_func == &handler::ha_check) - { - /* purecov: begin inspected */ - DBUG_PRINT("admin", ("sending crashed warning")); - protocol->prepare_for_resend(); - protocol->store(table_name, system_charset_info); - protocol->store(operator_name, system_charset_info); - protocol->store(STRING_WITH_LEN("warning"), system_charset_info); - protocol->store(STRING_WITH_LEN("Table is marked as crashed"), - system_charset_info); - if (protocol->write()) - goto err; - /* purecov: end */ - } - - if (operator_func == &handler::ha_repair && - !(check_opt->sql_flags & TT_USEFRM)) - { - if ((table->table->file->check_old_types() == HA_ADMIN_NEEDS_ALTER) || - (table->table->file->ha_check_for_upgrade(check_opt) == - HA_ADMIN_NEEDS_ALTER)) - { - DBUG_PRINT("admin", ("recreating table")); - trans_rollback_stmt(thd); - trans_rollback(thd); - close_thread_tables(thd); - thd->mdl_context.release_transactional_locks(); - tmp_disable_binlog(thd); // binlogging is done by caller if wanted - result_code= mysql_recreate_table(thd, table); - reenable_binlog(thd); - /* - mysql_recreate_table() can push OK or ERROR. - Clear 'OK' status. If there is an error, keep it: - we will store the error message in a result set row - and then clear. - */ - if (thd->stmt_da->is_ok()) - thd->stmt_da->reset_diagnostics_area(); - table->table= NULL; - result_code= result_code ? HA_ADMIN_FAILED : HA_ADMIN_OK; - goto send_result; - } - } - - DBUG_PRINT("admin", ("calling operator_func '%s'", operator_name)); - result_code = (table->table->file->*operator_func)(thd, check_opt); - DBUG_PRINT("admin", ("operator_func returned: %d", result_code)); - -send_result: - - lex->cleanup_after_one_table_open(); - thd->clear_error(); // these errors shouldn't get client - { - List_iterator_fast it(thd->warning_info->warn_list()); - MYSQL_ERROR *err; - while ((err= it++)) - { - protocol->prepare_for_resend(); - protocol->store(table_name, system_charset_info); - protocol->store((char*) operator_name, system_charset_info); - protocol->store(warning_level_names[err->get_level()].str, - warning_level_names[err->get_level()].length, - system_charset_info); - protocol->store(err->get_message_text(), system_charset_info); - if (protocol->write()) - goto err; - } - thd->warning_info->clear_warning_info(thd->query_id); - } - protocol->prepare_for_resend(); - protocol->store(table_name, system_charset_info); - protocol->store(operator_name, system_charset_info); - -send_result_message: - - DBUG_PRINT("info", ("result_code: %d", result_code)); - switch (result_code) { - case HA_ADMIN_NOT_IMPLEMENTED: - { - char buf[MYSQL_ERRMSG_SIZE]; - size_t length=my_snprintf(buf, sizeof(buf), - ER(ER_CHECK_NOT_IMPLEMENTED), operator_name); - protocol->store(STRING_WITH_LEN("note"), system_charset_info); - protocol->store(buf, length, system_charset_info); - } - break; - - case HA_ADMIN_NOT_BASE_TABLE: - { - char buf[MYSQL_ERRMSG_SIZE]; - size_t length= my_snprintf(buf, sizeof(buf), - ER(ER_BAD_TABLE_ERROR), table_name); - protocol->store(STRING_WITH_LEN("note"), system_charset_info); - protocol->store(buf, length, system_charset_info); - } - break; - - case HA_ADMIN_OK: - protocol->store(STRING_WITH_LEN("status"), system_charset_info); - protocol->store(STRING_WITH_LEN("OK"), system_charset_info); - break; - - case HA_ADMIN_FAILED: - protocol->store(STRING_WITH_LEN("status"), system_charset_info); - protocol->store(STRING_WITH_LEN("Operation failed"), - system_charset_info); - break; - - case HA_ADMIN_REJECT: - protocol->store(STRING_WITH_LEN("status"), system_charset_info); - protocol->store(STRING_WITH_LEN("Operation need committed state"), - system_charset_info); - open_for_modify= FALSE; - break; - - case HA_ADMIN_ALREADY_DONE: - protocol->store(STRING_WITH_LEN("status"), system_charset_info); - protocol->store(STRING_WITH_LEN("Table is already up to date"), - system_charset_info); - break; - - case HA_ADMIN_CORRUPT: - protocol->store(STRING_WITH_LEN("error"), system_charset_info); - protocol->store(STRING_WITH_LEN("Corrupt"), system_charset_info); - fatal_error=1; - break; - - case HA_ADMIN_INVALID: - protocol->store(STRING_WITH_LEN("error"), system_charset_info); - protocol->store(STRING_WITH_LEN("Invalid argument"), - system_charset_info); - break; - - case HA_ADMIN_TRY_ALTER: - { - /* - This is currently used only by InnoDB. ha_innobase::optimize() answers - "try with alter", so here we close the table, do an ALTER TABLE, - reopen the table and do ha_innobase::analyze() on it. - We have to end the row, so analyze could return more rows. - */ - trans_commit_stmt(thd); - trans_commit(thd); - close_thread_tables(thd); - thd->mdl_context.release_transactional_locks(); - DEBUG_SYNC(thd, "ha_admin_try_alter"); - protocol->store(STRING_WITH_LEN("note"), system_charset_info); - protocol->store(STRING_WITH_LEN( - "Table does not support optimize, doing recreate + analyze instead"), - system_charset_info); - if (protocol->write()) - goto err; - DBUG_PRINT("info", ("HA_ADMIN_TRY_ALTER, trying analyze...")); - TABLE_LIST *save_next_local= table->next_local, - *save_next_global= table->next_global; - table->next_local= table->next_global= 0; - tmp_disable_binlog(thd); // binlogging is done by caller if wanted - result_code= mysql_recreate_table(thd, table); - reenable_binlog(thd); - /* - mysql_recreate_table() can push OK or ERROR. - Clear 'OK' status. If there is an error, keep it: - we will store the error message in a result set row - and then clear. - */ - if (thd->stmt_da->is_ok()) - thd->stmt_da->reset_diagnostics_area(); - trans_commit_stmt(thd); - trans_commit(thd); - close_thread_tables(thd); - thd->mdl_context.release_transactional_locks(); - table->table= NULL; - if (!result_code) // recreation went ok - { - /* Clear the ticket released above. */ - table->mdl_request.ticket= NULL; - DEBUG_SYNC(thd, "ha_admin_open_ltable"); - table->mdl_request.set_type(MDL_SHARED_WRITE); - if ((table->table= open_ltable(thd, table, lock_type, 0))) - { - result_code= table->table->file->ha_analyze(thd, check_opt); - if (result_code == HA_ADMIN_ALREADY_DONE) - result_code= HA_ADMIN_OK; - else if (result_code) // analyze failed - table->table->file->print_error(result_code, MYF(0)); - } - else - result_code= -1; // open failed - } - /* Start a new row for the final status row */ - protocol->prepare_for_resend(); - protocol->store(table_name, system_charset_info); - protocol->store(operator_name, system_charset_info); - if (result_code) // either mysql_recreate_table or analyze failed - { - DBUG_ASSERT(thd->is_error()); - if (thd->is_error()) - { - const char *err_msg= thd->stmt_da->message(); - if (!thd->vio_ok()) - { - sql_print_error("%s", err_msg); - } - else - { - /* Hijack the row already in-progress. */ - protocol->store(STRING_WITH_LEN("error"), system_charset_info); - protocol->store(err_msg, system_charset_info); - if (protocol->write()) - goto err; - /* Start off another row for HA_ADMIN_FAILED */ - protocol->prepare_for_resend(); - protocol->store(table_name, system_charset_info); - protocol->store(operator_name, system_charset_info); - } - thd->clear_error(); - } - } - result_code= result_code ? HA_ADMIN_FAILED : HA_ADMIN_OK; - table->next_local= save_next_local; - table->next_global= save_next_global; - goto send_result_message; - } - case HA_ADMIN_WRONG_CHECKSUM: - { - protocol->store(STRING_WITH_LEN("note"), system_charset_info); - protocol->store(ER(ER_VIEW_CHECKSUM), strlen(ER(ER_VIEW_CHECKSUM)), - system_charset_info); - break; - } - - case HA_ADMIN_NEEDS_UPGRADE: - case HA_ADMIN_NEEDS_ALTER: - { - char buf[MYSQL_ERRMSG_SIZE]; - size_t length; - - protocol->store(STRING_WITH_LEN("error"), system_charset_info); - length=my_snprintf(buf, sizeof(buf), ER(ER_TABLE_NEEDS_UPGRADE), - table->table_name); - protocol->store(buf, length, system_charset_info); - fatal_error=1; - break; - } - - default: // Probably HA_ADMIN_INTERNAL_ERROR - { - char buf[MYSQL_ERRMSG_SIZE]; - size_t length=my_snprintf(buf, sizeof(buf), - "Unknown - internal error %d during operation", - result_code); - protocol->store(STRING_WITH_LEN("error"), system_charset_info); - protocol->store(buf, length, system_charset_info); - fatal_error=1; - break; - } - } - if (table->table) - { - if (table->table->s->tmp_table) - { - /* - If the table was not opened successfully, do not try to get - status information. (Bug#47633) - */ - if (open_for_modify && !open_error) - table->table->file->info(HA_STATUS_CONST); - } - else if (open_for_modify || fatal_error) - { - mysql_mutex_lock(&LOCK_open); - tdc_remove_table(thd, TDC_RT_REMOVE_UNUSED, - table->db, table->table_name); - mysql_mutex_unlock(&LOCK_open); - /* - May be something modified. Consequently, we have to - invalidate the query cache. - */ - table->table= 0; // For query cache - query_cache_invalidate3(thd, table, 0); - } - } - /* Error path, a admin command failed. */ - trans_commit_stmt(thd); - trans_commit_implicit(thd); - close_thread_tables(thd); - thd->mdl_context.release_transactional_locks(); - - /* - If it is CHECK TABLE v1, v2, v3, and v1, v2, v3 are views, we will run - separate open_tables() for each CHECK TABLE argument. - Right now we do not have a separate method to reset the prelocking - state in the lex to the state after parsing, so each open will pollute - this state: add elements to lex->srotuines_list, TABLE_LISTs to - lex->query_tables. Below is a lame attempt to recover from this - pollution. - @todo: have a method to reset a prelocking context, or use separate - contexts for each open. - */ - for (Sroutine_hash_entry *rt= - (Sroutine_hash_entry*)thd->lex->sroutines_list.first; - rt; rt= rt->next) - rt->mdl_request.ticket= NULL; - - if (protocol->write()) - goto err; - } - - my_eof(thd); - DBUG_RETURN(FALSE); - -err: - trans_rollback_stmt(thd); - trans_rollback(thd); - close_thread_tables(thd); // Shouldn't be needed - thd->mdl_context.release_transactional_locks(); - if (table) - table->table=0; - DBUG_RETURN(TRUE); -} - - -bool mysql_repair_table(THD* thd, TABLE_LIST* tables, HA_CHECK_OPT* check_opt) -{ - DBUG_ENTER("mysql_repair_table"); - DBUG_RETURN(mysql_admin_table(thd, tables, check_opt, - "repair", TL_WRITE, 1, - test(check_opt->sql_flags & TT_USEFRM), - HA_OPEN_FOR_REPAIR, - &prepare_for_repair, - &handler::ha_repair, 0)); -} - - -bool mysql_optimize_table(THD* thd, TABLE_LIST* tables, HA_CHECK_OPT* check_opt) -{ - DBUG_ENTER("mysql_optimize_table"); - DBUG_RETURN(mysql_admin_table(thd, tables, check_opt, - "optimize", TL_WRITE, 1,0,0,0, - &handler::ha_optimize, 0)); -} - - -/* - Assigned specified indexes for a table into key cache - - SYNOPSIS - mysql_assign_to_keycache() - thd Thread object - tables Table list (one table only) - - RETURN VALUES - FALSE ok - TRUE error -*/ - -bool mysql_assign_to_keycache(THD* thd, TABLE_LIST* tables, - LEX_STRING *key_cache_name) -{ - HA_CHECK_OPT check_opt; - KEY_CACHE *key_cache; - DBUG_ENTER("mysql_assign_to_keycache"); - - check_opt.init(); - mysql_mutex_lock(&LOCK_global_system_variables); - if (!(key_cache= get_key_cache(key_cache_name))) - { - mysql_mutex_unlock(&LOCK_global_system_variables); - my_error(ER_UNKNOWN_KEY_CACHE, MYF(0), key_cache_name->str); - DBUG_RETURN(TRUE); - } - mysql_mutex_unlock(&LOCK_global_system_variables); - check_opt.key_cache= key_cache; - DBUG_RETURN(mysql_admin_table(thd, tables, &check_opt, - "assign_to_keycache", TL_READ_NO_INSERT, 0, 0, - 0, 0, &handler::assign_to_keycache, 0)); -} - - -/* - Preload specified indexes for a table into key cache - - SYNOPSIS - mysql_preload_keys() - thd Thread object - tables Table list (one table only) - - RETURN VALUES - FALSE ok - TRUE error -*/ - -bool mysql_preload_keys(THD* thd, TABLE_LIST* tables) -{ - DBUG_ENTER("mysql_preload_keys"); - /* - We cannot allow concurrent inserts. The storage engine reads - directly from the index file, bypassing the cache. It could read - outdated information if parallel inserts into cache blocks happen. - */ - DBUG_RETURN(mysql_admin_table(thd, tables, 0, - "preload_keys", TL_READ_NO_INSERT, 0, 0, 0, 0, - &handler::preload_keys, 0)); -} - - /* Create a table identical to the specified table @@ -5436,29 +4552,6 @@ err: } -bool mysql_analyze_table(THD* thd, TABLE_LIST* tables, HA_CHECK_OPT* check_opt) -{ - thr_lock_type lock_type = TL_READ_NO_INSERT; - - DBUG_ENTER("mysql_analyze_table"); - DBUG_RETURN(mysql_admin_table(thd, tables, check_opt, - "analyze", lock_type, 1, 0, 0, 0, - &handler::ha_analyze, 0)); -} - - -bool mysql_check_table(THD* thd, TABLE_LIST* tables,HA_CHECK_OPT* check_opt) -{ - thr_lock_type lock_type = TL_READ_NO_INSERT; - - DBUG_ENTER("mysql_check_table"); - DBUG_RETURN(mysql_admin_table(thd, tables, check_opt, - "check", lock_type, - 0, 0, HA_OPEN_FOR_REPAIR, 0, - &handler::ha_check, &view_checksum)); -} - - /* table_list should contain just one table */ static int mysql_discard_or_import_tablespace(THD *thd, @@ -5569,7 +4662,7 @@ is_index_maintenance_unique (TABLE *table, Alter_info *alter_info) /* SYNOPSIS - compare_tables() + mysql_compare_tables() table The original table. alter_info Alter options, fields and keys for the new table. @@ -5609,17 +4702,16 @@ is_index_maintenance_unique (TABLE *table, Alter_info *alter_info) FALSE success */ -static bool -compare_tables(TABLE *table, - Alter_info *alter_info, - HA_CREATE_INFO *create_info, - uint order_num, - enum_alter_table_change_level *need_copy_table, - KEY **key_info_buffer, - uint **index_drop_buffer, uint *index_drop_count, - uint **index_add_buffer, uint *index_add_count, - uint *candidate_key_count) +mysql_compare_tables(TABLE *table, + Alter_info *alter_info, + HA_CREATE_INFO *create_info, + uint order_num, + enum_alter_table_change_level *need_copy_table, + KEY **key_info_buffer, + uint **index_drop_buffer, uint *index_drop_count, + uint **index_add_buffer, uint *index_add_count, + uint *candidate_key_count) { Field **f_ptr, *field; uint changes= 0, tmp; @@ -5635,7 +4727,7 @@ compare_tables(TABLE *table, */ bool varchar= create_info->varchar; bool not_nullable= true; - DBUG_ENTER("compare_tables"); + DBUG_ENTER("mysql_compare_tables"); /* Create a copy of alter_info. @@ -5646,7 +4738,7 @@ compare_tables(TABLE *table, mysql_prepare_create_table. Unfortunately, mysql_prepare_create_table performs its transformations "in-place", that is, modifies the argument. Since we would - like to keep compare_tables() idempotent (not altering any + like to keep mysql_compare_tables() idempotent (not altering any of the arguments) we create a copy of alter_info here and pass it to mysql_prepare_create_table, then use the result to evaluate possibility of fast ALTER TABLE, and then @@ -6026,7 +5118,7 @@ blob_length_by_type(enum_field_types type) @retval FALSE success */ -static bool +bool mysql_prepare_alter_table(THD *thd, TABLE *table, HA_CREATE_INFO *create_info, Alter_info *alter_info) @@ -6435,7 +5527,7 @@ err: Important is the fact, that this function tries to do as little work as possible, by finding out whether a intermediate table is needed to copy data into and when finishing the altering to use it as the original table. - For this reason the function compare_tables() is called, which decides + For this reason the function mysql_compare_tables() is called, which decides based on all kind of data how similar are the new and the original tables. @@ -6873,13 +5965,13 @@ bool mysql_alter_table(THD *thd,char *new_db, char *new_name, { enum_alter_table_change_level need_copy_table_res; /* Check how much the tables differ. */ - if (compare_tables(table, alter_info, - create_info, order_num, - &need_copy_table_res, - &key_info_buffer, - &index_drop_buffer, &index_drop_count, - &index_add_buffer, &index_add_count, - &candidate_key_count)) + if (mysql_compare_tables(table, alter_info, + create_info, order_num, + &need_copy_table_res, + &key_info_buffer, + &index_drop_buffer, &index_drop_count, + &index_add_buffer, &index_add_count, + &candidate_key_count)) goto err; DBUG_EXECUTE_IF("alter_table_only_metadata_change", { @@ -7393,7 +6485,7 @@ bool mysql_alter_table(THD *thd,char *new_db, char *new_name, it should become the actual table. Later, we will recycle the old table. However, in case of ALTER TABLE RENAME there might be no intermediate table. This is when the old and new tables are compatible, according to - compare_table(). Then, we need one additional call to + mysql_compare_table(). Then, we need one additional call to mysql_rename_table() with flag NO_FRM_RENAME, which does nothing else but actual rename in the SE and the FRM is not touched. Note that, if the table is renamed and the SE is also changed, then an intermediate table @@ -8048,3 +7140,4 @@ static bool check_engine(THD *thd, const char *table_name, } return FALSE; } + diff --git a/sql/sql_table.h b/sql/sql_table.h index dca4b706605..2e1cc89d585 100644 --- a/sql/sql_table.h +++ b/sql/sql_table.h @@ -19,7 +19,6 @@ #include "my_global.h" /* my_bool */ #include "my_sys.h" // pthread_mutex_t -class Alter_info; class Alter_info; class Create_field; struct TABLE_LIST; @@ -28,11 +27,12 @@ struct TABLE; struct handlerton; typedef struct st_ha_check_opt HA_CHECK_OPT; typedef struct st_ha_create_information HA_CREATE_INFO; +typedef struct st_key KEY; typedef struct st_key_cache KEY_CACHE; typedef struct st_lock_param_type ALTER_PARTITION_PARAM_TYPE; -typedef struct st_lock_param_type ALTER_PARTITION_PARAM_TYPE; typedef struct st_mysql_lex_string LEX_STRING; typedef struct st_order ORDER; +class Alter_table_change_level; enum ddl_log_entry_code { @@ -139,12 +139,23 @@ bool mysql_create_table_no_lock(THD *thd, const char *db, HA_CREATE_INFO *create_info, Alter_info *alter_info, bool tmp_table, uint select_field_count); - +bool mysql_prepare_alter_table(THD *thd, TABLE *table, + HA_CREATE_INFO *create_info, + Alter_info *alter_info); bool mysql_alter_table(THD *thd, char *new_db, char *new_name, HA_CREATE_INFO *create_info, TABLE_LIST *table_list, Alter_info *alter_info, uint order_num, ORDER *order, bool ignore); +bool mysql_compare_tables(TABLE *table, + Alter_info *alter_info, + HA_CREATE_INFO *create_info, + uint order_num, + Alter_table_change_level *need_copy_table, + KEY **key_info_buffer, + uint **index_drop_buffer, uint *index_drop_count, + uint **index_add_buffer, uint *index_add_count, + uint *candidate_key_count); bool mysql_recreate_table(THD *thd, TABLE_LIST *table_list); bool mysql_create_like_table(THD *thd, TABLE_LIST *table, TABLE_LIST *src_table, @@ -158,19 +169,6 @@ bool mysql_restore_table(THD* thd, TABLE_LIST* table_list); bool mysql_checksum_table(THD* thd, TABLE_LIST* table_list, HA_CHECK_OPT* check_opt); -bool mysql_check_table(THD* thd, TABLE_LIST* table_list, - HA_CHECK_OPT* check_opt); -bool mysql_repair_table(THD* thd, TABLE_LIST* table_list, - HA_CHECK_OPT* check_opt); -bool mysql_analyze_table(THD* thd, TABLE_LIST* table_list, - HA_CHECK_OPT* check_opt); -bool mysql_optimize_table(THD* thd, TABLE_LIST* table_list, - HA_CHECK_OPT* check_opt); -bool mysql_assign_to_keycache(THD* thd, TABLE_LIST* table_list, - LEX_STRING *key_cache_name); -bool mysql_preload_keys(THD* thd, TABLE_LIST* table_list); -int reassign_keycache_tables(THD* thd, KEY_CACHE *src_cache, - KEY_CACHE *dst_cache); bool mysql_rm_table(THD *thd,TABLE_LIST *tables, my_bool if_exists, my_bool drop_temporary); int mysql_rm_table_part2(THD *thd, TABLE_LIST *tables, bool if_exists, diff --git a/sql/sql_table_maintenance.cc b/sql/sql_table_maintenance.cc new file mode 100644 index 00000000000..b7033208788 --- /dev/null +++ b/sql/sql_table_maintenance.cc @@ -0,0 +1,1004 @@ +/* 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 */ + +#include "sql_class.h" // THD +#include "keycaches.h" // get_key_cache +#include "sql_base.h" // Open_table_context +#include "lock.h" // MYSQL_OPEN_* +#include "sql_handler.h" // mysql_ha_rm_tables +#include "partition_element.h" // PART_ADMIN +#include "sql_partition.h" // set_part_state +#include "transaction.h" // trans_rollback_stmt +#include "sql_view.h" // view_checksum +#include "sql_table.h" // mysql_recreate_table +#include "debug_sync.h" // DEBUG_SYNC +#include "sql_acl.h" // *_ACL +#include "sp.h" // Sroutine_hash_entry +#include "sql_parse.h" // check_table_access +#include "sql_table_maintenance.h" + +static int send_check_errmsg(THD *thd, TABLE_LIST* table, + const char* operator_name, const char* errmsg) + +{ + Protocol *protocol= thd->protocol; + protocol->prepare_for_resend(); + protocol->store(table->alias, system_charset_info); + protocol->store((char*) operator_name, system_charset_info); + protocol->store(STRING_WITH_LEN("error"), system_charset_info); + protocol->store(errmsg, system_charset_info); + thd->clear_error(); + if (protocol->write()) + return -1; + return 1; +} + + +static int prepare_for_repair(THD *thd, TABLE_LIST *table_list, + HA_CHECK_OPT *check_opt) +{ + int error= 0; + TABLE tmp_table, *table; + TABLE_SHARE *share; + bool has_mdl_lock= FALSE; + char from[FN_REFLEN],tmp[FN_REFLEN+32]; + const char **ext; + MY_STAT stat_info; + Open_table_context ot_ctx(thd, (MYSQL_OPEN_IGNORE_FLUSH | + MYSQL_OPEN_HAS_MDL_LOCK | + MYSQL_LOCK_IGNORE_TIMEOUT)); + DBUG_ENTER("prepare_for_repair"); + + if (!(check_opt->sql_flags & TT_USEFRM)) + DBUG_RETURN(0); + + if (!(table= table_list->table)) + { + char key[MAX_DBKEY_LENGTH]; + uint key_length; + /* + If the table didn't exist, we have a shared metadata lock + on it that is left from mysql_admin_table()'s attempt to + open it. Release the shared metadata lock before trying to + acquire the exclusive lock to satisfy MDL asserts and avoid + deadlocks. + */ + thd->mdl_context.release_transactional_locks(); + /* + Attempt to do full-blown table open in mysql_admin_table() has failed. + Let us try to open at least a .FRM for this table. + */ + my_hash_value_type hash_value; + + key_length= create_table_def_key(thd, key, table_list, 0); + table_list->mdl_request.init(MDL_key::TABLE, + table_list->db, table_list->table_name, + MDL_EXCLUSIVE); + + if (lock_table_names(thd, table_list, table_list->next_global, + thd->variables.lock_wait_timeout, + MYSQL_OPEN_SKIP_TEMPORARY)) + DBUG_RETURN(0); + has_mdl_lock= TRUE; + + hash_value= my_calc_hash(&table_def_cache, (uchar*) key, key_length); + mysql_mutex_lock(&LOCK_open); + if (!(share= (get_table_share(thd, table_list, key, key_length, 0, + &error, hash_value)))) + { + mysql_mutex_unlock(&LOCK_open); + DBUG_RETURN(0); // Can't open frm file + } + + if (open_table_from_share(thd, share, "", 0, 0, 0, &tmp_table, FALSE)) + { + release_table_share(share); + mysql_mutex_unlock(&LOCK_open); + DBUG_RETURN(0); // Out of memory + } + mysql_mutex_unlock(&LOCK_open); + table= &tmp_table; + } + + /* A MERGE table must not come here. */ + DBUG_ASSERT(table->file->ht->db_type != DB_TYPE_MRG_MYISAM); + + /* + REPAIR TABLE ... USE_FRM for temporary tables makes little sense. + */ + if (table->s->tmp_table) + { + error= send_check_errmsg(thd, table_list, "repair", + "Cannot repair temporary table from .frm file"); + goto end; + } + + /* + User gave us USE_FRM which means that the header in the index file is + trashed. + In this case we will try to fix the table the following way: + - Rename the data file to a temporary name + - Truncate the table + - Replace the new data file with the old one + - Run a normal repair using the new index file and the old data file + */ + + if (table->s->frm_version != FRM_VER_TRUE_VARCHAR) + { + error= send_check_errmsg(thd, table_list, "repair", + "Failed repairing incompatible .frm file"); + goto end; + } + + /* + Check if this is a table type that stores index and data separately, + like ISAM or MyISAM. We assume fixed order of engine file name + extentions array. First element of engine file name extentions array + is meta/index file extention. Second element - data file extention. + */ + ext= table->file->bas_ext(); + if (!ext[0] || !ext[1]) + goto end; // No data file + + // Name of data file + strxmov(from, table->s->normalized_path.str, ext[1], NullS); + if (!mysql_file_stat(key_file_misc, from, &stat_info, MYF(0))) + goto end; // Can't use USE_FRM flag + + my_snprintf(tmp, sizeof(tmp), "%s-%lx_%lx", + from, current_pid, thd->thread_id); + + if (table_list->table) + { + /* + Table was successfully open in mysql_admin_table(). Now we need + to close it, but leave it protected by exclusive metadata lock. + */ + if (wait_while_table_is_used(thd, table, HA_EXTRA_FORCE_REOPEN)) + goto end; + close_all_tables_for_name(thd, table_list->table->s, FALSE); + table_list->table= 0; + } + /* + After this point we have an exclusive metadata lock on our table + in both cases when table was successfully open in mysql_admin_table() + and when it was open in prepare_for_repair(). + */ + + if (my_rename(from, tmp, MYF(MY_WME))) + { + error= send_check_errmsg(thd, table_list, "repair", + "Failed renaming data file"); + goto end; + } + if (dd_recreate_table(thd, table_list->db, table_list->table_name)) + { + error= send_check_errmsg(thd, table_list, "repair", + "Failed generating table from .frm file"); + goto end; + } + /* + 'FALSE' for 'using_transactions' means don't postpone + invalidation till the end of a transaction, but do it + immediately. + */ + query_cache_invalidate3(thd, table_list, FALSE); + if (mysql_file_rename(key_file_misc, tmp, from, MYF(MY_WME))) + { + error= send_check_errmsg(thd, table_list, "repair", + "Failed restoring .MYD file"); + goto end; + } + + if (thd->locked_tables_list.reopen_tables(thd)) + goto end; + + /* + Now we should be able to open the partially repaired table + to finish the repair in the handler later on. + */ + if (open_table(thd, table_list, thd->mem_root, &ot_ctx)) + { + error= send_check_errmsg(thd, table_list, "repair", + "Failed to open partially repaired table"); + goto end; + } + +end: + thd->locked_tables_list.unlink_all_closed_tables(thd, NULL, 0); + if (table == &tmp_table) + { + mysql_mutex_lock(&LOCK_open); + closefrm(table, 1); // Free allocated memory + mysql_mutex_unlock(&LOCK_open); + } + /* In case of a temporary table there will be no metadata lock. */ + if (error && has_mdl_lock) + thd->mdl_context.release_transactional_locks(); + + DBUG_RETURN(error); +} + + + +/* + RETURN VALUES + FALSE Message sent to net (admin operation went ok) + TRUE Message should be sent by caller + (admin operation or network communication failed) +*/ +static bool mysql_admin_table(THD* thd, TABLE_LIST* tables, + HA_CHECK_OPT* check_opt, + const char *operator_name, + thr_lock_type lock_type, + bool open_for_modify, + bool no_warnings_for_error, + uint extra_open_options, + int (*prepare_func)(THD *, TABLE_LIST *, + HA_CHECK_OPT *), + int (handler::*operator_func)(THD *, + HA_CHECK_OPT *), + int (view_operator_func)(THD *, TABLE_LIST*)) +{ + TABLE_LIST *table; + SELECT_LEX *select= &thd->lex->select_lex; + List field_list; + Item *item; + Protocol *protocol= thd->protocol; + LEX *lex= thd->lex; + int result_code; + DBUG_ENTER("mysql_admin_table"); + + field_list.push_back(item = new Item_empty_string("Table", NAME_CHAR_LEN*2)); + item->maybe_null = 1; + field_list.push_back(item = new Item_empty_string("Op", 10)); + item->maybe_null = 1; + field_list.push_back(item = new Item_empty_string("Msg_type", 10)); + item->maybe_null = 1; + field_list.push_back(item = new Item_empty_string("Msg_text", 255)); + item->maybe_null = 1; + if (protocol->send_result_set_metadata(&field_list, + Protocol::SEND_NUM_ROWS | Protocol::SEND_EOF)) + DBUG_RETURN(TRUE); + + mysql_ha_rm_tables(thd, tables); + + for (table= tables; table; table= table->next_local) + { + char table_name[NAME_LEN*2+2]; + char* db = table->db; + bool fatal_error=0; + bool open_error; + + DBUG_PRINT("admin", ("table: '%s'.'%s'", table->db, table->table_name)); + DBUG_PRINT("admin", ("extra_open_options: %u", extra_open_options)); + strxmov(table_name, db, ".", table->table_name, NullS); + thd->open_options|= extra_open_options; + table->lock_type= lock_type; + /* + To make code safe for re-execution we need to reset type of MDL + request as code below may change it. + To allow concurrent execution of read-only operations we acquire + weak metadata lock for them. + */ + table->mdl_request.set_type((lock_type >= TL_WRITE_ALLOW_WRITE) ? + MDL_SHARED_NO_READ_WRITE : MDL_SHARED_READ); + /* open only one table from local list of command */ + { + TABLE_LIST *save_next_global, *save_next_local; + save_next_global= table->next_global; + table->next_global= 0; + save_next_local= table->next_local; + table->next_local= 0; + select->table_list.first= table; + /* + Time zone tables and SP tables can be add to lex->query_tables list, + so it have to be prepared. + TODO: Investigate if we can put extra tables into argument instead of + using lex->query_tables + */ + lex->query_tables= table; + lex->query_tables_last= &table->next_global; + lex->query_tables_own_last= 0; + thd->no_warnings_for_error= no_warnings_for_error; + if (view_operator_func == NULL) + table->required_type=FRMTYPE_TABLE; + + open_error= open_and_lock_tables(thd, table, TRUE, 0); + thd->no_warnings_for_error= 0; + table->next_global= save_next_global; + table->next_local= save_next_local; + thd->open_options&= ~extra_open_options; + /* + Under locked tables, we know that the table can be opened, + so any errors opening the table are logical errors. + In these cases it does not make sense to try to repair. + */ + if (open_error && thd->locked_tables_mode) + { + result_code= HA_ADMIN_FAILED; + goto send_result; + } +#ifdef WITH_PARTITION_STORAGE_ENGINE + if (table->table) + { + /* + Set up which partitions that should be processed + if ALTER TABLE t ANALYZE/CHECK/OPTIMIZE/REPAIR PARTITION .. + CACHE INDEX/LOAD INDEX for specified partitions + */ + Alter_info *alter_info= &lex->alter_info; + + if (alter_info->flags & ALTER_ADMIN_PARTITION) + { + if (!table->table->part_info) + { + my_error(ER_PARTITION_MGMT_ON_NONPARTITIONED, MYF(0)); + DBUG_RETURN(TRUE); + } + uint num_parts_found; + uint num_parts_opt= alter_info->partition_names.elements; + num_parts_found= set_part_state(alter_info, table->table->part_info, + PART_ADMIN); + if (num_parts_found != num_parts_opt && + (!(alter_info->flags & ALTER_ALL_PARTITION))) + { + char buff[FN_REFLEN + MYSQL_ERRMSG_SIZE]; + size_t length; + DBUG_PRINT("admin", ("sending non existent partition error")); + protocol->prepare_for_resend(); + protocol->store(table_name, system_charset_info); + protocol->store(operator_name, system_charset_info); + protocol->store(STRING_WITH_LEN("error"), system_charset_info); + length= my_snprintf(buff, sizeof(buff), + ER(ER_DROP_PARTITION_NON_EXISTENT), + table_name); + protocol->store(buff, length, system_charset_info); + if(protocol->write()) + goto err; + my_eof(thd); + goto err; + } + } + } +#endif + } + DBUG_PRINT("admin", ("table: 0x%lx", (long) table->table)); + + if (prepare_func) + { + DBUG_PRINT("admin", ("calling prepare_func")); + switch ((*prepare_func)(thd, table, check_opt)) { + case 1: // error, message written to net + trans_rollback_stmt(thd); + trans_rollback(thd); + close_thread_tables(thd); + thd->mdl_context.release_transactional_locks(); + DBUG_PRINT("admin", ("simple error, admin next table")); + continue; + case -1: // error, message could be written to net + /* purecov: begin inspected */ + DBUG_PRINT("admin", ("severe error, stop")); + goto err; + /* purecov: end */ + default: // should be 0 otherwise + DBUG_PRINT("admin", ("prepare_func succeeded")); + ; + } + } + + /* + CHECK TABLE command is only command where VIEW allowed here and this + command use only temporary teble method for VIEWs resolving => there + can't be VIEW tree substitition of join view => if opening table + succeed then table->table will have real TABLE pointer as value (in + case of join view substitution table->table can be 0, but here it is + impossible) + */ + if (!table->table) + { + DBUG_PRINT("admin", ("open table failed")); + if (thd->warning_info->is_empty()) + push_warning(thd, MYSQL_ERROR::WARN_LEVEL_WARN, + ER_CHECK_NO_SUCH_TABLE, ER(ER_CHECK_NO_SUCH_TABLE)); + /* if it was a view will check md5 sum */ + if (table->view && + view_checksum(thd, table) == HA_ADMIN_WRONG_CHECKSUM) + push_warning(thd, MYSQL_ERROR::WARN_LEVEL_WARN, + ER_VIEW_CHECKSUM, ER(ER_VIEW_CHECKSUM)); + if (thd->stmt_da->is_error() && + (thd->stmt_da->sql_errno() == ER_NO_SUCH_TABLE || + thd->stmt_da->sql_errno() == ER_FILE_NOT_FOUND)) + /* A missing table is just issued as a failed command */ + result_code= HA_ADMIN_FAILED; + else + /* Default failure code is corrupt table */ + result_code= HA_ADMIN_CORRUPT; + goto send_result; + } + + if (table->view) + { + DBUG_PRINT("admin", ("calling view_operator_func")); + result_code= (*view_operator_func)(thd, table); + goto send_result; + } + + if (table->schema_table) + { + result_code= HA_ADMIN_NOT_IMPLEMENTED; + goto send_result; + } + + if ((table->table->db_stat & HA_READ_ONLY) && open_for_modify) + { + /* purecov: begin inspected */ + char buff[FN_REFLEN + MYSQL_ERRMSG_SIZE]; + size_t length; + enum_sql_command save_sql_command= lex->sql_command; + DBUG_PRINT("admin", ("sending error message")); + protocol->prepare_for_resend(); + protocol->store(table_name, system_charset_info); + protocol->store(operator_name, system_charset_info); + protocol->store(STRING_WITH_LEN("error"), system_charset_info); + length= my_snprintf(buff, sizeof(buff), ER(ER_OPEN_AS_READONLY), + table_name); + protocol->store(buff, length, system_charset_info); + trans_commit_stmt(thd); + trans_commit(thd); + close_thread_tables(thd); + thd->mdl_context.release_transactional_locks(); + lex->reset_query_tables_list(FALSE); + /* + Restore Query_tables_list::sql_command value to make statement + safe for re-execution. + */ + lex->sql_command= save_sql_command; + table->table=0; // For query cache + if (protocol->write()) + goto err; + thd->stmt_da->reset_diagnostics_area(); + continue; + /* purecov: end */ + } + + /* + Close all instances of the table to allow MyISAM "repair" + to rename files. + @todo: This code does not close all instances of the table. + It only closes instances in other connections, but if this + connection has LOCK TABLE t1 a READ, t1 b WRITE, + both t1 instances will be kept open. + There is no need to execute this branch for InnoDB, which does + repair by recreate. There is no need to do it for OPTIMIZE, + which doesn't move files around. + Hence, this code should be moved to prepare_for_repair(), + and executed only for MyISAM engine. + */ + if (lock_type == TL_WRITE && !table->table->s->tmp_table) + { + if (wait_while_table_is_used(thd, table->table, + HA_EXTRA_PREPARE_FOR_RENAME)) + goto err; + DEBUG_SYNC(thd, "after_admin_flush"); + /* Flush entries in the query cache involving this table. */ + query_cache_invalidate3(thd, table->table, 0); + /* + XXX: hack: switch off open_for_modify to skip the + flush that is made later in the execution flow. + */ + open_for_modify= 0; + } + + if (table->table->s->crashed && operator_func == &handler::ha_check) + { + /* purecov: begin inspected */ + DBUG_PRINT("admin", ("sending crashed warning")); + protocol->prepare_for_resend(); + protocol->store(table_name, system_charset_info); + protocol->store(operator_name, system_charset_info); + protocol->store(STRING_WITH_LEN("warning"), system_charset_info); + protocol->store(STRING_WITH_LEN("Table is marked as crashed"), + system_charset_info); + if (protocol->write()) + goto err; + /* purecov: end */ + } + + if (operator_func == &handler::ha_repair && + !(check_opt->sql_flags & TT_USEFRM)) + { + if ((table->table->file->check_old_types() == HA_ADMIN_NEEDS_ALTER) || + (table->table->file->ha_check_for_upgrade(check_opt) == + HA_ADMIN_NEEDS_ALTER)) + { + DBUG_PRINT("admin", ("recreating table")); + trans_rollback_stmt(thd); + trans_rollback(thd); + close_thread_tables(thd); + thd->mdl_context.release_transactional_locks(); + tmp_disable_binlog(thd); // binlogging is done by caller if wanted + result_code= mysql_recreate_table(thd, table); + reenable_binlog(thd); + /* + mysql_recreate_table() can push OK or ERROR. + Clear 'OK' status. If there is an error, keep it: + we will store the error message in a result set row + and then clear. + */ + if (thd->stmt_da->is_ok()) + thd->stmt_da->reset_diagnostics_area(); + table->table= NULL; + result_code= result_code ? HA_ADMIN_FAILED : HA_ADMIN_OK; + goto send_result; + } + } + + DBUG_PRINT("admin", ("calling operator_func '%s'", operator_name)); + result_code = (table->table->file->*operator_func)(thd, check_opt); + DBUG_PRINT("admin", ("operator_func returned: %d", result_code)); + +send_result: + + lex->cleanup_after_one_table_open(); + thd->clear_error(); // these errors shouldn't get client + { + List_iterator_fast it(thd->warning_info->warn_list()); + MYSQL_ERROR *err; + while ((err= it++)) + { + protocol->prepare_for_resend(); + protocol->store(table_name, system_charset_info); + protocol->store((char*) operator_name, system_charset_info); + protocol->store(warning_level_names[err->get_level()].str, + warning_level_names[err->get_level()].length, + system_charset_info); + protocol->store(err->get_message_text(), system_charset_info); + if (protocol->write()) + goto err; + } + thd->warning_info->clear_warning_info(thd->query_id); + } + protocol->prepare_for_resend(); + protocol->store(table_name, system_charset_info); + protocol->store(operator_name, system_charset_info); + +send_result_message: + + DBUG_PRINT("info", ("result_code: %d", result_code)); + switch (result_code) { + case HA_ADMIN_NOT_IMPLEMENTED: + { + char buf[MYSQL_ERRMSG_SIZE]; + size_t length=my_snprintf(buf, sizeof(buf), + ER(ER_CHECK_NOT_IMPLEMENTED), operator_name); + protocol->store(STRING_WITH_LEN("note"), system_charset_info); + protocol->store(buf, length, system_charset_info); + } + break; + + case HA_ADMIN_NOT_BASE_TABLE: + { + char buf[MYSQL_ERRMSG_SIZE]; + size_t length= my_snprintf(buf, sizeof(buf), + ER(ER_BAD_TABLE_ERROR), table_name); + protocol->store(STRING_WITH_LEN("note"), system_charset_info); + protocol->store(buf, length, system_charset_info); + } + break; + + case HA_ADMIN_OK: + protocol->store(STRING_WITH_LEN("status"), system_charset_info); + protocol->store(STRING_WITH_LEN("OK"), system_charset_info); + break; + + case HA_ADMIN_FAILED: + protocol->store(STRING_WITH_LEN("status"), system_charset_info); + protocol->store(STRING_WITH_LEN("Operation failed"), + system_charset_info); + break; + + case HA_ADMIN_REJECT: + protocol->store(STRING_WITH_LEN("status"), system_charset_info); + protocol->store(STRING_WITH_LEN("Operation need committed state"), + system_charset_info); + open_for_modify= FALSE; + break; + + case HA_ADMIN_ALREADY_DONE: + protocol->store(STRING_WITH_LEN("status"), system_charset_info); + protocol->store(STRING_WITH_LEN("Table is already up to date"), + system_charset_info); + break; + + case HA_ADMIN_CORRUPT: + protocol->store(STRING_WITH_LEN("error"), system_charset_info); + protocol->store(STRING_WITH_LEN("Corrupt"), system_charset_info); + fatal_error=1; + break; + + case HA_ADMIN_INVALID: + protocol->store(STRING_WITH_LEN("error"), system_charset_info); + protocol->store(STRING_WITH_LEN("Invalid argument"), + system_charset_info); + break; + + case HA_ADMIN_TRY_ALTER: + { + /* + This is currently used only by InnoDB. ha_innobase::optimize() answers + "try with alter", so here we close the table, do an ALTER TABLE, + reopen the table and do ha_innobase::analyze() on it. + We have to end the row, so analyze could return more rows. + */ + trans_commit_stmt(thd); + trans_commit(thd); + close_thread_tables(thd); + thd->mdl_context.release_transactional_locks(); + DEBUG_SYNC(thd, "ha_admin_try_alter"); + protocol->store(STRING_WITH_LEN("note"), system_charset_info); + protocol->store(STRING_WITH_LEN( + "Table does not support optimize, doing recreate + analyze instead"), + system_charset_info); + if (protocol->write()) + goto err; + DBUG_PRINT("info", ("HA_ADMIN_TRY_ALTER, trying analyze...")); + TABLE_LIST *save_next_local= table->next_local, + *save_next_global= table->next_global; + table->next_local= table->next_global= 0; + tmp_disable_binlog(thd); // binlogging is done by caller if wanted + result_code= mysql_recreate_table(thd, table); + reenable_binlog(thd); + /* + mysql_recreate_table() can push OK or ERROR. + Clear 'OK' status. If there is an error, keep it: + we will store the error message in a result set row + and then clear. + */ + if (thd->stmt_da->is_ok()) + thd->stmt_da->reset_diagnostics_area(); + trans_commit_stmt(thd); + trans_commit(thd); + close_thread_tables(thd); + thd->mdl_context.release_transactional_locks(); + table->table= NULL; + if (!result_code) // recreation went ok + { + /* Clear the ticket released above. */ + table->mdl_request.ticket= NULL; + DEBUG_SYNC(thd, "ha_admin_open_ltable"); + table->mdl_request.set_type(MDL_SHARED_WRITE); + if ((table->table= open_ltable(thd, table, lock_type, 0))) + { + result_code= table->table->file->ha_analyze(thd, check_opt); + if (result_code == HA_ADMIN_ALREADY_DONE) + result_code= HA_ADMIN_OK; + else if (result_code) // analyze failed + table->table->file->print_error(result_code, MYF(0)); + } + else + result_code= -1; // open failed + } + /* Start a new row for the final status row */ + protocol->prepare_for_resend(); + protocol->store(table_name, system_charset_info); + protocol->store(operator_name, system_charset_info); + if (result_code) // either mysql_recreate_table or analyze failed + { + DBUG_ASSERT(thd->is_error()); + if (thd->is_error()) + { + const char *err_msg= thd->stmt_da->message(); + if (!thd->vio_ok()) + { + sql_print_error("%s", err_msg); + } + else + { + /* Hijack the row already in-progress. */ + protocol->store(STRING_WITH_LEN("error"), system_charset_info); + protocol->store(err_msg, system_charset_info); + if (protocol->write()) + goto err; + /* Start off another row for HA_ADMIN_FAILED */ + protocol->prepare_for_resend(); + protocol->store(table_name, system_charset_info); + protocol->store(operator_name, system_charset_info); + } + thd->clear_error(); + } + } + result_code= result_code ? HA_ADMIN_FAILED : HA_ADMIN_OK; + table->next_local= save_next_local; + table->next_global= save_next_global; + goto send_result_message; + } + case HA_ADMIN_WRONG_CHECKSUM: + { + protocol->store(STRING_WITH_LEN("note"), system_charset_info); + protocol->store(ER(ER_VIEW_CHECKSUM), strlen(ER(ER_VIEW_CHECKSUM)), + system_charset_info); + break; + } + + case HA_ADMIN_NEEDS_UPGRADE: + case HA_ADMIN_NEEDS_ALTER: + { + char buf[MYSQL_ERRMSG_SIZE]; + size_t length; + + protocol->store(STRING_WITH_LEN("error"), system_charset_info); + length=my_snprintf(buf, sizeof(buf), ER(ER_TABLE_NEEDS_UPGRADE), + table->table_name); + protocol->store(buf, length, system_charset_info); + fatal_error=1; + break; + } + + default: // Probably HA_ADMIN_INTERNAL_ERROR + { + char buf[MYSQL_ERRMSG_SIZE]; + size_t length=my_snprintf(buf, sizeof(buf), + "Unknown - internal error %d during operation", + result_code); + protocol->store(STRING_WITH_LEN("error"), system_charset_info); + protocol->store(buf, length, system_charset_info); + fatal_error=1; + break; + } + } + if (table->table) + { + if (table->table->s->tmp_table) + { + /* + If the table was not opened successfully, do not try to get + status information. (Bug#47633) + */ + if (open_for_modify && !open_error) + table->table->file->info(HA_STATUS_CONST); + } + else if (open_for_modify || fatal_error) + { + mysql_mutex_lock(&LOCK_open); + tdc_remove_table(thd, TDC_RT_REMOVE_UNUSED, + table->db, table->table_name); + mysql_mutex_unlock(&LOCK_open); + /* + May be something modified. Consequently, we have to + invalidate the query cache. + */ + table->table= 0; // For query cache + query_cache_invalidate3(thd, table, 0); + } + } + /* Error path, a admin command failed. */ + trans_commit_stmt(thd); + trans_commit_implicit(thd); + close_thread_tables(thd); + thd->mdl_context.release_transactional_locks(); + + /* + If it is CHECK TABLE v1, v2, v3, and v1, v2, v3 are views, we will run + separate open_tables() for each CHECK TABLE argument. + Right now we do not have a separate method to reset the prelocking + state in the lex to the state after parsing, so each open will pollute + this state: add elements to lex->srotuines_list, TABLE_LISTs to + lex->query_tables. Below is a lame attempt to recover from this + pollution. + @todo: have a method to reset a prelocking context, or use separate + contexts for each open. + */ + for (Sroutine_hash_entry *rt= + (Sroutine_hash_entry*)thd->lex->sroutines_list.first; + rt; rt= rt->next) + rt->mdl_request.ticket= NULL; + + if (protocol->write()) + goto err; + } + + my_eof(thd); + DBUG_RETURN(FALSE); + +err: + trans_rollback_stmt(thd); + trans_rollback(thd); + close_thread_tables(thd); // Shouldn't be needed + thd->mdl_context.release_transactional_locks(); + if (table) + table->table=0; + DBUG_RETURN(TRUE); +} + + +/* + Assigned specified indexes for a table into key cache + + SYNOPSIS + mysql_assign_to_keycache() + thd Thread object + tables Table list (one table only) + + RETURN VALUES + FALSE ok + TRUE error +*/ + +bool mysql_assign_to_keycache(THD* thd, TABLE_LIST* tables, + LEX_STRING *key_cache_name) +{ + HA_CHECK_OPT check_opt; + KEY_CACHE *key_cache; + DBUG_ENTER("mysql_assign_to_keycache"); + + check_opt.init(); + mysql_mutex_lock(&LOCK_global_system_variables); + if (!(key_cache= get_key_cache(key_cache_name))) + { + mysql_mutex_unlock(&LOCK_global_system_variables); + my_error(ER_UNKNOWN_KEY_CACHE, MYF(0), key_cache_name->str); + DBUG_RETURN(TRUE); + } + mysql_mutex_unlock(&LOCK_global_system_variables); + check_opt.key_cache= key_cache; + DBUG_RETURN(mysql_admin_table(thd, tables, &check_opt, + "assign_to_keycache", TL_READ_NO_INSERT, 0, 0, + 0, 0, &handler::assign_to_keycache, 0)); +} + + +/* + Preload specified indexes for a table into key cache + + SYNOPSIS + mysql_preload_keys() + thd Thread object + tables Table list (one table only) + + RETURN VALUES + FALSE ok + TRUE error +*/ + +bool mysql_preload_keys(THD* thd, TABLE_LIST* tables) +{ + DBUG_ENTER("mysql_preload_keys"); + /* + We cannot allow concurrent inserts. The storage engine reads + directly from the index file, bypassing the cache. It could read + outdated information if parallel inserts into cache blocks happen. + */ + DBUG_RETURN(mysql_admin_table(thd, tables, 0, + "preload_keys", TL_READ_NO_INSERT, 0, 0, 0, 0, + &handler::preload_keys, 0)); +} + + +bool Analyze_table_statement::execute(THD *thd) +{ + TABLE_LIST *first_table= m_lex->select_lex.table_list.first; + bool res= TRUE; + thr_lock_type lock_type = TL_READ_NO_INSERT; + DBUG_ENTER("Analyze_table_statement::execute"); + + if (check_table_access(thd, SELECT_ACL | INSERT_ACL, first_table, + FALSE, UINT_MAX, FALSE)) + goto error; + thd->enable_slow_log= opt_log_slow_admin_statements; + res= mysql_admin_table(thd, first_table, &m_lex->check_opt, + "analyze", lock_type, 1, 0, 0, 0, + &handler::ha_analyze, 0); + /* ! we write after unlocking the table */ + if (!res && !m_lex->no_write_to_binlog) + { + /* + Presumably, ANALYZE and binlog writing doesn't require synchronization + */ + res= write_bin_log(thd, TRUE, thd->query(), thd->query_length()); + } + m_lex->select_lex.table_list.first= first_table; + m_lex->query_tables= first_table; + +error: + DBUG_RETURN(res); +} + + +bool Check_table_statement::execute(THD *thd) +{ + TABLE_LIST *first_table= m_lex->select_lex.table_list.first; + thr_lock_type lock_type = TL_READ_NO_INSERT; + bool res= TRUE; + DBUG_ENTER("Check_table_statement::execute"); + + if (check_table_access(thd, SELECT_ACL, first_table, + TRUE, UINT_MAX, FALSE)) + goto error; /* purecov: inspected */ + thd->enable_slow_log= opt_log_slow_admin_statements; + + res= mysql_admin_table(thd, first_table, &m_lex->check_opt, "check", + lock_type, 0, 0, HA_OPEN_FOR_REPAIR, 0, + &handler::ha_check, &view_checksum); + + m_lex->select_lex.table_list.first= first_table; + m_lex->query_tables= first_table; + +error: + DBUG_RETURN(res); +} + + +bool Optimize_table_statement::execute(THD *thd) +{ + TABLE_LIST *first_table= m_lex->select_lex.table_list.first; + bool res= TRUE; + DBUG_ENTER("Optimize_table_statement::execute"); + + if (check_table_access(thd, SELECT_ACL | INSERT_ACL, first_table, + FALSE, UINT_MAX, FALSE)) + goto error; /* purecov: inspected */ + thd->enable_slow_log= opt_log_slow_admin_statements; + res= (specialflag & (SPECIAL_SAFE_MODE | SPECIAL_NO_NEW_FUNC)) ? + mysql_recreate_table(thd, first_table) : + mysql_admin_table(thd, first_table, &m_lex->check_opt, + "optimize", TL_WRITE, 1, 0, 0, 0, + &handler::ha_optimize, 0); + /* ! we write after unlocking the table */ + if (!res && !m_lex->no_write_to_binlog) + { + /* + Presumably, OPTIMIZE and binlog writing doesn't require synchronization + */ + res= write_bin_log(thd, TRUE, thd->query(), thd->query_length()); + } + m_lex->select_lex.table_list.first= first_table; + m_lex->query_tables= first_table; + +error: + DBUG_RETURN(res); +} + + +bool Repair_table_statement::execute(THD *thd) +{ + TABLE_LIST *first_table= m_lex->select_lex.table_list.first; + bool res= TRUE; + DBUG_ENTER("Repair_table_statement::execute"); + + if (check_table_access(thd, SELECT_ACL | INSERT_ACL, first_table, + FALSE, UINT_MAX, FALSE)) + goto error; /* purecov: inspected */ + thd->enable_slow_log= opt_log_slow_admin_statements; + res= mysql_admin_table(thd, first_table, &m_lex->check_opt, "repair", + TL_WRITE, 1, + test(m_lex->check_opt.sql_flags & TT_USEFRM), + HA_OPEN_FOR_REPAIR, &prepare_for_repair, + &handler::ha_repair, 0); + + /* ! we write after unlocking the table */ + if (!res && !m_lex->no_write_to_binlog) + { + /* + Presumably, REPAIR and binlog writing doesn't require synchronization + */ + res= write_bin_log(thd, TRUE, thd->query(), thd->query_length()); + } + m_lex->select_lex.table_list.first= first_table; + m_lex->query_tables= first_table; + +error: + DBUG_RETURN(res); +} diff --git a/sql/sql_table_maintenance.h b/sql/sql_table_maintenance.h new file mode 100644 index 00000000000..fdfffec8361 --- /dev/null +++ b/sql/sql_table_maintenance.h @@ -0,0 +1,132 @@ +/* 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 */ + +#ifndef SQL_TABLE_MAINTENANCE_H +#define SQL_TABLE_MAINTENANCE_H + + +bool mysql_assign_to_keycache(THD* thd, TABLE_LIST* table_list, + LEX_STRING *key_cache_name); +bool mysql_preload_keys(THD* thd, TABLE_LIST* table_list); +int reassign_keycache_tables(THD* thd, KEY_CACHE *src_cache, + KEY_CACHE *dst_cache); + +/** + Analyze_statement represents the ANALYZE TABLE statement. +*/ +class Analyze_table_statement : public Sql_statement +{ +public: + /** + Constructor, used to represent a ANALYZE TABLE statement. + @param lex the LEX structure for this statement. + */ + Analyze_table_statement(LEX *lex) + : Sql_statement(lex) + {} + + ~Analyze_table_statement() + {} + + /** + Execute a ANALYZE TABLE statement at runtime. + @param thd the current thread. + @return false on success. + */ + bool execute(THD *thd); +}; + + + +/** + Check_table_statement represents the CHECK TABLE statement. +*/ +class Check_table_statement : public Sql_statement +{ +public: + /** + Constructor, used to represent a CHECK TABLE statement. + @param lex the LEX structure for this statement. + */ + Check_table_statement(LEX *lex) + : Sql_statement(lex) + {} + + ~Check_table_statement() + {} + + /** + Execute a CHECK TABLE statement at runtime. + @param thd the current thread. + @return false on success. + */ + bool execute(THD *thd); +}; + + + +/** + Optimize_table_statement represents the OPTIMIZE TABLE statement. +*/ +class Optimize_table_statement : public Sql_statement +{ +public: + /** + Constructor, used to represent a OPTIMIZE TABLE statement. + @param lex the LEX structure for this statement. + */ + Optimize_table_statement(LEX *lex) + : Sql_statement(lex) + {} + + ~Optimize_table_statement() + {} + + /** + Execute a OPTIMIZE TABLE statement at runtime. + @param thd the current thread. + @return false on success. + */ + bool execute(THD *thd); +}; + + + +/** + Repair_table_statement represents the REPAIR TABLE statement. +*/ +class Repair_table_statement : public Sql_statement +{ +public: + /** + Constructor, used to represent a REPAIR TABLE statement. + @param lex the LEX structure for this statement. + */ + Repair_table_statement(LEX *lex) + : Sql_statement(lex) + {} + + ~Repair_table_statement() + {} + + /** + Execute a REPAIR TABLE statement at runtime. + @param thd the current thread. + @return false on success. + */ + bool execute(THD *thd); +}; + +#endif diff --git a/sql/sql_truncate.cc b/sql/sql_truncate.cc index ee5c707cd69..62e51d9dfe6 100644 --- a/sql/sql_truncate.cc +++ b/sql/sql_truncate.cc @@ -13,7 +13,6 @@ along with this program; if not, write to the Free Software Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA */ -#include "sql_truncate.h" #include "sql_priv.h" #include "transaction.h" #include "debug_sync.h" @@ -25,6 +24,9 @@ #include "sql_handler.h" // mysql_ha_rm_tables #include "datadict.h" // dd_recreate_table() #include "lock.h" // MYSQL_OPEN_TEMPORARY_ONLY +#include "sql_acl.h" // DROP_ACL +#include "sql_parse.h" // check_one_table_access() +#include "sql_truncate.h" /* @@ -242,6 +244,7 @@ static bool open_and_lock_table_for_truncate(THD *thd, TABLE_LIST *table_ref, MDL_ticket **ticket_downgrade) { TABLE *table= NULL; + handlerton *table_type; DBUG_ENTER("open_and_lock_table_for_truncate"); DBUG_ASSERT(table_ref->lock_type == TL_WRITE); @@ -265,7 +268,8 @@ static bool open_and_lock_table_for_truncate(THD *thd, TABLE_LIST *table_ref, table_ref->table_name, FALSE))) DBUG_RETURN(TRUE); - *hton_can_recreate= ha_check_storage_engine_flag(table->s->db_type(), + table_type= table->s->db_type(); + *hton_can_recreate= ha_check_storage_engine_flag(table_type, HTON_CAN_RECREATE); table_ref->mdl_request.ticket= table->mdl_ticket; } @@ -281,11 +285,25 @@ static bool open_and_lock_table_for_truncate(THD *thd, TABLE_LIST *table_ref, MYSQL_OPEN_SKIP_TEMPORARY)) DBUG_RETURN(TRUE); - if (dd_check_storage_engine_flag(thd, table_ref->db, table_ref->table_name, - HTON_CAN_RECREATE, hton_can_recreate)) + if (dd_frm_storage_engine(thd, table_ref->db, table_ref->table_name, + &table_type)) DBUG_RETURN(TRUE); + *hton_can_recreate= ha_check_storage_engine_flag(table_type, + HTON_CAN_RECREATE); } +#ifdef WITH_PARTITION_STORAGE_ENGINE + /* + TODO: Add support for TRUNCATE PARTITION for NDB and other engines + supporting native partitioning. + */ + if (thd->lex->alter_info.flags & ALTER_ADMIN_PARTITION && + table_type != partition_hton) + { + my_error(ER_PARTITION_MGMT_ON_NONPARTITIONED, MYF(0)); + DBUG_RETURN(TRUE); + } +#endif DEBUG_SYNC(thd, "lock_table_for_truncate"); if (*hton_can_recreate) @@ -477,3 +495,27 @@ bool mysql_truncate_table(THD *thd, TABLE_LIST *table_ref) DBUG_RETURN(test(error)); } + +bool Truncate_statement::execute(THD *thd) +{ + TABLE_LIST *first_table= thd->lex->select_lex.table_list.first; + bool res= TRUE; + DBUG_ENTER("Truncate_statement::execute"); + + if (check_one_table_access(thd, DROP_ACL, first_table)) + goto error; + /* + Don't allow this within a transaction because we want to use + re-generate table + */ + if (thd->in_active_multi_stmt_transaction()) + { + my_message(ER_LOCK_OR_ACTIVE_TRANSACTION, + ER(ER_LOCK_OR_ACTIVE_TRANSACTION), MYF(0)); + goto error; + } + if (! (res= mysql_truncate_table(thd, first_table))) + my_ok(thd); +error: + DBUG_RETURN(res); +} diff --git a/sql/sql_truncate.h b/sql/sql_truncate.h index 11c07c7187c..b8b1d3da53d 100644 --- a/sql/sql_truncate.h +++ b/sql/sql_truncate.h @@ -20,4 +20,30 @@ struct TABLE_LIST; bool mysql_truncate_table(THD *thd, TABLE_LIST *table_ref); +/** + Truncate_statement represents the TRUNCATE statement. +*/ +class Truncate_statement : public Sql_statement +{ +public: + /** + Constructor, used to represent a ALTER TABLE statement. + @param lex the LEX structure for this statement. + */ + Truncate_statement(LEX *lex) + : Sql_statement(lex) + {} + + ~Truncate_statement() + {} + + /** + Execute a TRUNCATE statement at runtime. + @param thd the current thread. + @return false on success. + */ + bool execute(THD *thd); +}; + + #endif diff --git a/sql/sql_yacc.yy b/sql/sql_yacc.yy index ca951897055..64ce1a5f64b 100644 --- a/sql/sql_yacc.yy +++ b/sql/sql_yacc.yy @@ -51,6 +51,10 @@ #include "sp_pcontext.h" #include "sp_rcontext.h" #include "sp.h" +#include "sql_alter_table.h" // Alter_table*_statement +#include "sql_truncate.h" // Truncate_statement +#include "sql_table_maintenance.h" // Analyze/Check..._table_stmt +#include "sql_partition_admin.h" // Alter_table_*_partition_stmt #include "sql_signal.h" #include "event_parse_data.h" #include @@ -6172,9 +6176,20 @@ alter: lex->no_write_to_binlog= 0; lex->create_info.storage_media= HA_SM_DEFAULT; lex->create_last_non_select_table= lex->last_table(); + DBUG_ASSERT(!lex->m_stmt); } alter_commands - {} + { + THD *thd= YYTHD; + LEX *lex= thd->lex; + if (!lex->m_stmt) + { + /* Create a generic ALTER TABLE statment. */ + lex->m_stmt= new (thd->mem_root) Alter_table_statement(lex); + if (lex->m_stmt == NULL) + MYSQL_YYABORT; + } + } | ALTER DATABASE ident_or_empty { Lex->create_info.default_table_charset= NULL; @@ -6393,38 +6408,54 @@ alter_commands: | OPTIMIZE PARTITION_SYM opt_no_write_to_binlog all_or_alt_part_name_list { - LEX *lex= Lex; - lex->sql_command= SQLCOM_OPTIMIZE; - lex->alter_info.flags|= ALTER_ADMIN_PARTITION; + THD *thd= YYTHD; + LEX *lex= thd->lex; lex->no_write_to_binlog= $3; lex->check_opt.init(); + DBUG_ASSERT(!lex->m_stmt); + lex->m_stmt= new (thd->mem_root) + Alter_table_optimize_partition_statement(lex); + if (lex->m_stmt == NULL) + MYSQL_YYABORT; } opt_no_write_to_binlog | ANALYZE_SYM PARTITION_SYM opt_no_write_to_binlog all_or_alt_part_name_list { - LEX *lex= Lex; - lex->sql_command= SQLCOM_ANALYZE; - lex->alter_info.flags|= ALTER_ADMIN_PARTITION; + THD *thd= YYTHD; + LEX *lex= thd->lex; lex->no_write_to_binlog= $3; lex->check_opt.init(); + DBUG_ASSERT(!lex->m_stmt); + lex->m_stmt= new (thd->mem_root) + Alter_table_analyze_partition_statement(lex); + if (lex->m_stmt == NULL) + MYSQL_YYABORT; } | CHECK_SYM PARTITION_SYM all_or_alt_part_name_list { - LEX *lex= Lex; - lex->sql_command= SQLCOM_CHECK; - lex->alter_info.flags|= ALTER_ADMIN_PARTITION; + THD *thd= YYTHD; + LEX *lex= thd->lex; lex->check_opt.init(); + DBUG_ASSERT(!lex->m_stmt); + lex->m_stmt= new (thd->mem_root) + Alter_table_check_partition_statement(lex); + if (lex->m_stmt == NULL) + MYSQL_YYABORT; } opt_mi_check_type | REPAIR PARTITION_SYM opt_no_write_to_binlog all_or_alt_part_name_list { - LEX *lex= Lex; - lex->sql_command= SQLCOM_REPAIR; - lex->alter_info.flags|= ALTER_ADMIN_PARTITION; + THD *thd= YYTHD; + LEX *lex= thd->lex; lex->no_write_to_binlog= $3; lex->check_opt.init(); + DBUG_ASSERT(!lex->m_stmt); + lex->m_stmt= new (thd->mem_root) + Alter_table_repair_partition_statement(lex); + if (lex->m_stmt == NULL) + MYSQL_YYABORT; } opt_mi_repair_type | COALESCE PARTITION_SYM opt_no_write_to_binlog real_ulong_num @@ -6436,12 +6467,14 @@ alter_commands: } | TRUNCATE_SYM PARTITION_SYM all_or_alt_part_name_list { - LEX *lex= Lex; - lex->sql_command= SQLCOM_TRUNCATE; - lex->alter_info.flags|= ALTER_ADMIN_PARTITION; + THD *thd= YYTHD; + LEX *lex= thd->lex; lex->check_opt.init(); - lex->query_tables->mdl_request.set_type(MDL_SHARED_NO_READ_WRITE); - lex->query_tables->lock_type= TL_WRITE; + DBUG_ASSERT(!lex->m_stmt); + lex->m_stmt= new (thd->mem_root) + Alter_table_truncate_partition_statement(lex); + if (lex->m_stmt == NULL) + MYSQL_YYABORT; } | reorg_partition_rule ; @@ -6878,7 +6911,14 @@ repair: YYPS->m_lock_type= TL_UNLOCK; } table_list opt_mi_repair_type - {} + { + THD *thd= YYTHD; + LEX* lex= thd->lex; + DBUG_ASSERT(!lex->m_stmt); + lex->m_stmt= new (thd->mem_root) Repair_table_statement(lex); + if (lex->m_stmt == NULL) + MYSQL_YYABORT; + } ; opt_mi_repair_type: @@ -6909,7 +6949,14 @@ analyze: YYPS->m_lock_type= TL_UNLOCK; } table_list - {} + { + THD *thd= YYTHD; + LEX* lex= thd->lex; + DBUG_ASSERT(!lex->m_stmt); + lex->m_stmt= new (thd->mem_root) Analyze_table_statement(lex); + if (lex->m_stmt == NULL) + MYSQL_YYABORT; + } ; binlog_base64_event: @@ -6937,7 +6984,14 @@ check: YYPS->m_lock_type= TL_UNLOCK; } table_list opt_mi_check_type - {} + { + THD *thd= YYTHD; + LEX* lex= thd->lex; + DBUG_ASSERT(!lex->m_stmt); + lex->m_stmt= new (thd->mem_root) Check_table_statement(lex); + if (lex->m_stmt == NULL) + MYSQL_YYABORT; + } ; opt_mi_check_type: @@ -6971,7 +7025,14 @@ optimize: YYPS->m_lock_type= TL_UNLOCK; } table_list - {} + { + THD *thd= YYTHD; + LEX* lex= thd->lex; + DBUG_ASSERT(!lex->m_stmt); + lex->m_stmt= new (thd->mem_root) Optimize_table_statement(lex); + if (lex->m_stmt == NULL) + MYSQL_YYABORT; + } ; opt_no_write_to_binlog: @@ -10698,7 +10759,14 @@ truncate: YYPS->m_mdl_type= MDL_SHARED_NO_READ_WRITE; } table_name - {} + { + THD *thd= YYTHD; + LEX* lex= thd->lex; + DBUG_ASSERT(!lex->m_stmt); + lex->m_stmt= new (thd->mem_root) Truncate_statement(lex); + if (lex->m_stmt == NULL) + MYSQL_YYABORT; + } ; opt_table_sym: From b67924eb4e6c29dd9f9e4ceddfc30b6f0a93ef0e Mon Sep 17 00:00:00 2001 From: Mattias Jonsson Date: Mon, 16 Aug 2010 16:25:23 +0200 Subject: [PATCH 129/129] Rename of sql_alter_table -> sql_alter and sql_table_maintenance -> sql_admin --- libmysqld/CMakeLists.txt | 4 ++-- libmysqld/Makefile.am | 4 ++-- sql/CMakeLists.txt | 4 ++-- sql/Makefile.am | 8 ++++---- sql/{sql_table_maintenance.cc => sql_admin.cc} | 2 +- sql/{sql_table_maintenance.h => sql_admin.h} | 0 sql/{sql_alter_table.cc => sql_alter.cc} | 2 +- sql/{sql_alter_table.h => sql_alter.h} | 0 sql/sql_lex.h | 2 +- sql/sql_parse.cc | 2 +- sql/sql_partition_admin.cc | 2 +- sql/sql_yacc.yy | 4 ++-- 12 files changed, 17 insertions(+), 17 deletions(-) rename sql/{sql_table_maintenance.cc => sql_admin.cc} (99%) rename sql/{sql_table_maintenance.h => sql_admin.h} (100%) rename sql/{sql_alter_table.cc => sql_alter.cc} (99%) rename sql/{sql_alter_table.h => sql_alter.h} (100%) diff --git a/libmysqld/CMakeLists.txt b/libmysqld/CMakeLists.txt index f3a0f0c5d0f..06bbd6a05ec 100644 --- a/libmysqld/CMakeLists.txt +++ b/libmysqld/CMakeLists.txt @@ -64,7 +64,7 @@ SET(SQL_EMBEDDED_SOURCES emb_qcache.cc libmysqld.c lib_sql.cc ../sql/sql_db.cc ../sql/sql_delete.cc ../sql/sql_derived.cc ../sql/sql_do.cc ../sql/sql_error.cc ../sql/sql_handler.cc ../sql/sql_help.cc ../sql/sql_insert.cc ../sql/datadict.cc - ../sql/sql_table_maintenance.cc ../sql/sql_truncate.cc + ../sql/sql_admin.cc ../sql/sql_truncate.cc ../sql/sql_lex.cc ../sql/keycaches.cc ../sql/sql_list.cc ../sql/sql_load.cc ../sql/sql_locale.cc ../sql/sql_binlog.cc ../sql/sql_manager.cc @@ -80,7 +80,7 @@ SET(SQL_EMBEDDED_SOURCES emb_qcache.cc libmysqld.c lib_sql.cc ../sql/sql_time.cc ../sql/tztime.cc ../sql/uniques.cc ../sql/unireg.cc ../sql/partition_info.cc ../sql/sql_connect.cc ../sql/scheduler.cc ../sql/sql_audit.cc - ../sql/sql_alter_table.cc ../sql/sql_partition_admin.cc + ../sql/sql_alter.cc ../sql/sql_partition_admin.cc ../sql/event_parse_data.cc ../sql/sql_signal.cc ../sql/rpl_handler.cc ../sql/rpl_utility.cc diff --git a/libmysqld/Makefile.am b/libmysqld/Makefile.am index 7fe51698491..6af4588126c 100644 --- a/libmysqld/Makefile.am +++ b/libmysqld/Makefile.am @@ -63,7 +63,7 @@ sqlsources = derror.cc field.cc field_conv.cc strfunc.cc filesort.cc \ protocol.cc net_serv.cc opt_range.cc \ opt_sum.cc procedure.cc records.cc sql_acl.cc \ sql_load.cc discover.cc sql_locale.cc \ - sql_profile.cc sql_table_maintenance.cc sql_truncate.cc datadict.cc \ + sql_profile.cc sql_admin.cc sql_truncate.cc datadict.cc \ sql_analyse.cc sql_base.cc sql_cache.cc sql_class.cc \ sql_crypt.cc sql_db.cc sql_delete.cc sql_error.cc sql_insert.cc \ sql_lex.cc sql_list.cc sql_manager.cc \ @@ -78,7 +78,7 @@ sqlsources = derror.cc field.cc field_conv.cc strfunc.cc filesort.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 \ debug_sync.cc sql_tablespace.cc transaction.cc \ - rpl_injector.cc my_user.c partition_info.cc sql_alter_table.cc \ + rpl_injector.cc my_user.c partition_info.cc sql_alter.cc \ sql_servers.cc event_parse_data.cc sql_signal.cc \ rpl_handler.cc mdl.cc keycaches.cc sql_audit.cc \ sql_partition_admin.cc diff --git a/sql/CMakeLists.txt b/sql/CMakeLists.txt index 1a162d39e0b..a32c4a4b7e2 100644 --- a/sql/CMakeLists.txt +++ b/sql/CMakeLists.txt @@ -72,8 +72,8 @@ SET (SQL_SOURCE 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_partition_admin.cc - sql_profile.cc event_parse_data.cc sql_alter_table.cc - sql_signal.cc rpl_handler.cc mdl.cc sql_table_maintenance.cc + sql_profile.cc event_parse_data.cc sql_alter.cc + sql_signal.cc rpl_handler.cc mdl.cc sql_admin.cc transaction.cc sys_vars.cc sql_truncate.cc datadict.cc ${GEN_SOURCES} ${MYSYS_LIBWRAP_SOURCE}) diff --git a/sql/Makefile.am b/sql/Makefile.am index b99afcbdbeb..4fb7bfe919c 100644 --- a/sql/Makefile.am +++ b/sql/Makefile.am @@ -122,11 +122,11 @@ noinst_HEADERS = item.h item_func.h item_sum.h item_cmpfunc.h \ 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 \ - sql_audit.h sql_alter_table.h sql_partition_admin.h \ + sql_audit.h sql_alter.h sql_partition_admin.h \ contributors.h sql_servers.h sql_signal.h records.h \ sql_prepare.h rpl_handler.h replication.h mdl.h \ sql_plist.h transaction.h sys_vars.h sql_truncate.h \ - sql_table_maintenance.h datadict.h + sql_admin.h datadict.h mysqld_SOURCES = sql_lex.cc sql_handler.cc sql_partition.cc \ item.cc item_sum.cc item_buff.cc item_func.cc \ @@ -143,7 +143,7 @@ mysqld_SOURCES = sql_lex.cc sql_handler.cc sql_partition.cc \ datadict.cc sql_profile.cc \ sql_prepare.cc sql_error.cc sql_locale.cc \ sql_update.cc sql_delete.cc uniques.cc sql_do.cc \ - procedure.cc sql_test.cc sql_table_maintenance.cc \ + procedure.cc sql_test.cc sql_admin.cc \ sql_truncate.cc \ log.cc init.cc derror.cc sql_acl.cc \ unireg.cc des_key_file.cc \ @@ -172,7 +172,7 @@ mysqld_SOURCES = sql_lex.cc sql_handler.cc sql_partition.cc \ sql_builtin.cc sql_tablespace.cc partition_info.cc \ sql_servers.cc event_parse_data.cc sql_signal.cc \ rpl_handler.cc mdl.cc transaction.cc sql_audit.cc \ - sql_alter_table.cc sql_partition_admin.cc sha2.cc + sql_alter.cc sql_partition_admin.cc sha2.cc nodist_mysqld_SOURCES = mini_client_errors.c pack.c client.c my_time.c my_user.c diff --git a/sql/sql_table_maintenance.cc b/sql/sql_admin.cc similarity index 99% rename from sql/sql_table_maintenance.cc rename to sql/sql_admin.cc index b7033208788..6f0405bd4a8 100644 --- a/sql/sql_table_maintenance.cc +++ b/sql/sql_admin.cc @@ -27,7 +27,7 @@ #include "sql_acl.h" // *_ACL #include "sp.h" // Sroutine_hash_entry #include "sql_parse.h" // check_table_access -#include "sql_table_maintenance.h" +#include "sql_admin.h" static int send_check_errmsg(THD *thd, TABLE_LIST* table, const char* operator_name, const char* errmsg) diff --git a/sql/sql_table_maintenance.h b/sql/sql_admin.h similarity index 100% rename from sql/sql_table_maintenance.h rename to sql/sql_admin.h diff --git a/sql/sql_alter_table.cc b/sql/sql_alter.cc similarity index 99% rename from sql/sql_alter_table.cc rename to sql/sql_alter.cc index 607a8d5f5df..046e09b20a3 100644 --- a/sql/sql_alter_table.cc +++ b/sql/sql_alter.cc @@ -17,7 +17,7 @@ // check_merge_table_access #include "sql_table.h" // mysql_alter_table, // mysql_exchange_partition -#include "sql_alter_table.h" +#include "sql_alter.h" bool Alter_table_statement::execute(THD *thd) { diff --git a/sql/sql_alter_table.h b/sql/sql_alter.h similarity index 100% rename from sql/sql_alter_table.h rename to sql/sql_alter.h diff --git a/sql/sql_lex.h b/sql/sql_lex.h index d0f20d4e997..0eb8e5de6d2 100644 --- a/sql/sql_lex.h +++ b/sql/sql_lex.h @@ -923,7 +923,7 @@ enum enum_alter_table_change_level /** Temporary hack to enable a class bound forward declaration of the enum_alter_table_change_level enumeration. To be - removed once Alter_info is moved to the sql_alter_table.h + removed once Alter_info is moved to the sql_alter.h header. */ class Alter_table_change_level diff --git a/sql/sql_parse.cc b/sql/sql_parse.cc index 2f02188d122..806a2984905 100644 --- a/sql/sql_parse.cc +++ b/sql/sql_parse.cc @@ -50,7 +50,7 @@ // mysql_backup_table, // mysql_restore_table #include "sql_truncate.h" // mysql_truncate_table -#include "sql_table_maintenance.h" // mysql_assign_to_keycache +#include "sql_admin.h" // mysql_assign_to_keycache #include "sql_connect.h" // check_user, // decrease_user_connections, // thd_init_client_charset, check_mqh, diff --git a/sql/sql_partition_admin.cc b/sql/sql_partition_admin.cc index fc0183e9b3d..fee33303a04 100644 --- a/sql/sql_partition_admin.cc +++ b/sql/sql_partition_admin.cc @@ -18,7 +18,7 @@ #include "sql_lex.h" // Sql_statement #include "sql_truncate.h" // mysql_truncate_table, // Truncate_statement -#include "sql_table_maintenance.h" // Analyze/Check/.._table_statement +#include "sql_admin.h" // Analyze/Check/.._table_statement #include "sql_partition_admin.h" // Alter_table_*_partition #ifndef WITH_PARTITION_STORAGE_ENGINE diff --git a/sql/sql_yacc.yy b/sql/sql_yacc.yy index 64ce1a5f64b..443b80799aa 100644 --- a/sql/sql_yacc.yy +++ b/sql/sql_yacc.yy @@ -51,9 +51,9 @@ #include "sp_pcontext.h" #include "sp_rcontext.h" #include "sp.h" -#include "sql_alter_table.h" // Alter_table*_statement +#include "sql_alter.h" // Alter_table*_statement #include "sql_truncate.h" // Truncate_statement -#include "sql_table_maintenance.h" // Analyze/Check..._table_stmt +#include "sql_admin.h" // Analyze/Check..._table_stmt #include "sql_partition_admin.h" // Alter_table_*_partition_stmt #include "sql_signal.h" #include "event_parse_data.h"