From e53199e76b0e89e3601651e48c5667793d0fa954 Mon Sep 17 00:00:00 2001 From: Andrei Date: Wed, 2 Feb 2022 20:02:20 +0200 Subject: [PATCH 01/45] MDEV-27721 rpl.rpl_relay_max_extension test is not FreeBSD-compatible Fixed the test to execute only on linux as it depends on unportable sed. --- mysql-test/suite/rpl/t/rpl_relay_max_extension.test | 2 ++ 1 file changed, 2 insertions(+) diff --git a/mysql-test/suite/rpl/t/rpl_relay_max_extension.test b/mysql-test/suite/rpl/t/rpl_relay_max_extension.test index e1e087f2e0e..acca2f6954c 100644 --- a/mysql-test/suite/rpl/t/rpl_relay_max_extension.test +++ b/mysql-test/suite/rpl/t/rpl_relay_max_extension.test @@ -28,6 +28,8 @@ # showed # +# MDEV-27721 rpl.rpl_relay_max_extension test is not FreeBSD-compatible +--source include/linux.inc --source include/have_innodb.inc --source include/have_binlog_format_row.inc --let $rpl_topology=1->2 From a319220e6214390730030e1063fca7675e5e98a4 Mon Sep 17 00:00:00 2001 From: Sergei Golubchik Date: Sun, 6 Feb 2022 23:00:34 +0100 Subject: [PATCH 02/45] update test result --- mysql-test/suite/galera_sr/r/MDEV-27615.result | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/mysql-test/suite/galera_sr/r/MDEV-27615.result b/mysql-test/suite/galera_sr/r/MDEV-27615.result index a3475811285..e3bfd0ed539 100644 --- a/mysql-test/suite/galera_sr/r/MDEV-27615.result +++ b/mysql-test/suite/galera_sr/r/MDEV-27615.result @@ -15,7 +15,7 @@ SET DEBUG_SYNC='now WAIT_FOR before_fragment'; SET GLOBAL wsrep_cluster_address = ''; SET DEBUG_SYNC = 'now SIGNAL continue'; connection node_2; -ERROR HY000: Lost connection to MySQL server during query +ERROR HY000: Lost connection to server during query connection node_2a; SELECT * FROM mysql.wsrep_streaming_log; node_uuid trx_id seqno flags frag From 881918bf775d86d589cec6b213ce2efb8bf76563 Mon Sep 17 00:00:00 2001 From: Vladislav Vaintroub Date: Mon, 7 Feb 2022 00:23:14 +0100 Subject: [PATCH 03/45] MDEV-27754 : Assertion with innodb_flush_method=O_DSYNC If innodb_flush_method=O_DSYNC, log_sys.flushed_to_disk_lsn is changed without 'flush_lock' protection inside log_write(). This leads to a race condition, if there are 2 threads running in parallel, doing log_write_up_to() with different values for 'flush_to_disk' In this case, log_write() and log_write_flush_to_disk_low() can execute at the same time, and both would change flushed_lsn. The fix is to remove special treatment of durable writes from log_write(). There is no apparent reason for this special treatment, log_write_flush_to_disk_low() is already optimized for durable writes. Nor there is an apparent reason to call log_flush_notify() more often in for O_DSYNC. --- storage/innobase/log/log0log.cc | 7 +------ 1 file changed, 1 insertion(+), 6 deletions(-) diff --git a/storage/innobase/log/log0log.cc b/storage/innobase/log/log0log.cc index 914337d2a54..cee2fa978ab 100644 --- a/storage/innobase/log/log0log.cc +++ b/storage/innobase/log/log0log.cc @@ -639,8 +639,7 @@ loop: } } -/** Flush the recently written changes to the log file. -and invoke mysql_mutex_lock(&log_sys.mutex). */ +/** Flush the recently written changes to the log file.*/ static void log_write_flush_to_disk_low(lsn_t lsn) { if (!log_sys.log.writes_are_durable()) @@ -780,10 +779,6 @@ static void log_write(bool rotate_key) start_offset - area_start); srv_stats.log_padded.add(pad_size); log_sys.write_lsn = write_lsn; - if (log_sys.log.writes_are_durable()) { - log_sys.set_flushed_lsn(write_lsn); - log_flush_notify(write_lsn); - } return; } From 5c89386fdbd5eb9062e10247380ad65cb85c9f29 Mon Sep 17 00:00:00 2001 From: Sergei Petrunia Date: Mon, 7 Feb 2022 12:10:18 +0300 Subject: [PATCH 04/45] MDEV-17785: Window functions not working in ONLY_FULL_GROUP_BY mode (Backport Varun Gupta's patch + edit the commit comment) Name resolution code produced errors for valid queries with window functions (but not for queries which used aggregate functions as window functions). Name resolution code worked incorrectly, because window function objects had is_window_func_sum_expr()=false. This was so, because mark_as_window_func_sum_expr() was only called for aggregate functions used as window functions. The fix is to call it for any window function. --- mysql-test/r/win.result | 32 +++++++++++++++++++ .../encryption/r/tempfiles_encrypted.result | 32 +++++++++++++++++++ mysql-test/t/win.test | 27 ++++++++++++++++ sql/item_windowfunc.cc | 3 ++ sql/sql_yacc.yy | 3 -- 5 files changed, 94 insertions(+), 3 deletions(-) diff --git a/mysql-test/r/win.result b/mysql-test/r/win.result index bc017ea70a3..30650f29555 100644 --- a/mysql-test/r/win.result +++ b/mysql-test/r/win.result @@ -4198,5 +4198,37 @@ drop procedure sp7; drop view v1,v2; drop table t1; # +# MDEV-17785: Window functions not working in ONLY_FULL_GROUP_BY mode +# +CREATE TABLE t1(a VARCHAR(10), b int); +INSERT INTO t1 VALUES +('Maths', 60),('Maths', 60), +('Maths', 70),('Maths', 55), +('Biology', 60), ('Biology', 70); +SET @save_sql_mode= @@sql_mode; +SET sql_mode = 'ONLY_FULL_GROUP_BY'; +SELECT +RANK() OVER (PARTITION BY a ORDER BY b) AS rank, +a, b FROM t1 ORDER BY a, b DESC; +rank a b +2 Biology 70 +1 Biology 60 +4 Maths 70 +2 Maths 60 +2 Maths 60 +1 Maths 55 +SET sql_mode= @save_sql_mode; +DROP TABLE t1; +CREATE TABLE t1(i int,j int); +INSERT INTO t1 VALUES (1,1), (1,5),(1,4), (2,2),(2,5), (3,3),(4,4); +INSERT INTO t1 VALUES (1,1), (1,5),(1,4), (2,2),(2,5), (3,3),(4,4); +SELECT i, LAST_VALUE(COUNT(i)) OVER (PARTITION BY i ORDER BY j) FROM t1 GROUP BY i; +i LAST_VALUE(COUNT(i)) OVER (PARTITION BY i ORDER BY j) +1 6 +2 4 +3 2 +4 2 +DROP TABLE t1; +# # End of 10.2 tests # diff --git a/mysql-test/suite/encryption/r/tempfiles_encrypted.result b/mysql-test/suite/encryption/r/tempfiles_encrypted.result index f66a5fd0b25..aaba6bb044a 100644 --- a/mysql-test/suite/encryption/r/tempfiles_encrypted.result +++ b/mysql-test/suite/encryption/r/tempfiles_encrypted.result @@ -4204,6 +4204,38 @@ drop procedure sp7; drop view v1,v2; drop table t1; # +# MDEV-17785: Window functions not working in ONLY_FULL_GROUP_BY mode +# +CREATE TABLE t1(a VARCHAR(10), b int); +INSERT INTO t1 VALUES +('Maths', 60),('Maths', 60), +('Maths', 70),('Maths', 55), +('Biology', 60), ('Biology', 70); +SET @save_sql_mode= @@sql_mode; +SET sql_mode = 'ONLY_FULL_GROUP_BY'; +SELECT +RANK() OVER (PARTITION BY a ORDER BY b) AS rank, +a, b FROM t1 ORDER BY a, b DESC; +rank a b +2 Biology 70 +1 Biology 60 +4 Maths 70 +2 Maths 60 +2 Maths 60 +1 Maths 55 +SET sql_mode= @save_sql_mode; +DROP TABLE t1; +CREATE TABLE t1(i int,j int); +INSERT INTO t1 VALUES (1,1), (1,5),(1,4), (2,2),(2,5), (3,3),(4,4); +INSERT INTO t1 VALUES (1,1), (1,5),(1,4), (2,2),(2,5), (3,3),(4,4); +SELECT i, LAST_VALUE(COUNT(i)) OVER (PARTITION BY i ORDER BY j) FROM t1 GROUP BY i; +i LAST_VALUE(COUNT(i)) OVER (PARTITION BY i ORDER BY j) +1 6 +2 4 +3 2 +4 2 +DROP TABLE t1; +# # End of 10.2 tests # # diff --git a/mysql-test/t/win.test b/mysql-test/t/win.test index 72e789dff3f..126ed735c88 100644 --- a/mysql-test/t/win.test +++ b/mysql-test/t/win.test @@ -2703,6 +2703,33 @@ drop procedure sp7; drop view v1,v2; drop table t1; +--echo # +--echo # MDEV-17785: Window functions not working in ONLY_FULL_GROUP_BY mode +--echo # + +CREATE TABLE t1(a VARCHAR(10), b int); + +INSERT INTO t1 VALUES +('Maths', 60),('Maths', 60), +('Maths', 70),('Maths', 55), +('Biology', 60), ('Biology', 70); + +SET @save_sql_mode= @@sql_mode; +SET sql_mode = 'ONLY_FULL_GROUP_BY'; + +SELECT + RANK() OVER (PARTITION BY a ORDER BY b) AS rank, + a, b FROM t1 ORDER BY a, b DESC; + +SET sql_mode= @save_sql_mode; +DROP TABLE t1; + +CREATE TABLE t1(i int,j int); +INSERT INTO t1 VALUES (1,1), (1,5),(1,4), (2,2),(2,5), (3,3),(4,4); +INSERT INTO t1 VALUES (1,1), (1,5),(1,4), (2,2),(2,5), (3,3),(4,4); +SELECT i, LAST_VALUE(COUNT(i)) OVER (PARTITION BY i ORDER BY j) FROM t1 GROUP BY i; +DROP TABLE t1; + --echo # --echo # End of 10.2 tests --echo # diff --git a/sql/item_windowfunc.cc b/sql/item_windowfunc.cc index bb4a8a9f3af..03f99540771 100644 --- a/sql/item_windowfunc.cc +++ b/sql/item_windowfunc.cc @@ -93,6 +93,9 @@ Item_window_func::fix_fields(THD *thd, Item **ref) my_error(ER_NO_ORDER_LIST_IN_WINDOW_SPEC, MYF(0), window_func()->func_name()); return true; } + + window_func()->mark_as_window_func_sum_expr(); + /* TODO: why the last parameter is 'ref' in this call? What if window_func decides to substitute itself for something else and does *ref=.... ? diff --git a/sql/sql_yacc.yy b/sql/sql_yacc.yy index a4b105862f3..6f3274aced5 100644 --- a/sql/sql_yacc.yy +++ b/sql/sql_yacc.yy @@ -10557,9 +10557,6 @@ window_func: simple_window_func | sum_expr - { - ((Item_sum *) $1)->mark_as_window_func_sum_expr(); - } ; simple_window_func: From 21413aee0a32c80708a02a96074c108f3db419f1 Mon Sep 17 00:00:00 2001 From: Teemu Ollakka Date: Thu, 3 Feb 2022 12:06:25 +0000 Subject: [PATCH 05/45] MDEV-27737 Wsrep SST scripts not working on FreeBSD MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit - Changed SST scripts to use /usr/bin/env bash instead of /bin/bash for better portability. - Fixed use of mktemp on non-Linux platforms to produce temporary file instead of directory. Reviewed-by: Jan Lindström --- scripts/wsrep_sst_mariabackup.sh | 5 ++++- scripts/wsrep_sst_mysqldump.sh | 5 ++++- scripts/wsrep_sst_rsync.sh | 6 ++++-- 3 files changed, 12 insertions(+), 4 deletions(-) diff --git a/scripts/wsrep_sst_mariabackup.sh b/scripts/wsrep_sst_mariabackup.sh index aa9442b0601..471b0e5f5b0 100644 --- a/scripts/wsrep_sst_mariabackup.sh +++ b/scripts/wsrep_sst_mariabackup.sh @@ -1,4 +1,7 @@ -#!/bin/bash -ue +#!/usr/bin/env bash + +set -ue + # Copyright (C) 2017-2021 MariaDB # Copyright (C) 2013 Percona Inc # diff --git a/scripts/wsrep_sst_mysqldump.sh b/scripts/wsrep_sst_mysqldump.sh index bed2cac0a9a..1c8fc181328 100644 --- a/scripts/wsrep_sst_mysqldump.sh +++ b/scripts/wsrep_sst_mysqldump.sh @@ -1,4 +1,7 @@ -#!/bin/bash -ue +#!/usr/bin/env bash + +set -ue + # Copyright (C) 2009-2015 Codership Oy # Copyright (C) 2017-2021 MariaDB # diff --git a/scripts/wsrep_sst_rsync.sh b/scripts/wsrep_sst_rsync.sh index 28dfed18218..cc73db5da87 100644 --- a/scripts/wsrep_sst_rsync.sh +++ b/scripts/wsrep_sst_rsync.sh @@ -1,4 +1,6 @@ -#!/bin/bash -ue +#!/usr/bin/env bash + +set -ue # Copyright (C) 2017-2021 MariaDB # Copyright (C) 2010-2014 Codership Oy @@ -740,7 +742,7 @@ EOF elif [ "$OS" = 'Linux' ]; then tmpfile=$(mktemp "--tmpdir=$tmpdir") else - tmpfile=$(TMPDIR="$tmpdir"; mktemp '-d') + tmpfile=$(TMPDIR="$tmpdir"; mktemp) fi wsrep_log_info "Extracting binlog files:" From ae33a006f7c50d8f98c3b931574b2d2e2a7381b9 Mon Sep 17 00:00:00 2001 From: Vladislav Vaintroub Date: Fri, 4 Feb 2022 00:33:10 +0100 Subject: [PATCH 06/45] MDEV-27738 Windows : mysql-test-run --extern does not work Use portable quoting in mtr_add_arg. --- 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 aa6a02a4541..bbe5df4c57a 100755 --- a/mysql-test/mysql-test-run.pl +++ b/mysql-test/mysql-test-run.pl @@ -1908,7 +1908,7 @@ sub collect_mysqld_features_from_running_server () } mtr_add_arg($args, "--silent"); # Tab separated output - mtr_add_arg($args, "-e '%s'", "use mysql; SHOW VARIABLES"); + mtr_add_arg($args, "-e \"use mysql; SHOW VARIABLES\""); my $cmd= "$mysql " . join(' ', @$args); mtr_verbose("cmd: $cmd"); From df02de68f3b42741289d85296255a1a169358a12 Mon Sep 17 00:00:00 2001 From: Monty Date: Mon, 17 Aug 2020 19:01:43 +0300 Subject: [PATCH 07/45] Fixed my_addr_resolve (cherry picked from 10.6) When a server is compiled with -fPIE, my_addr_resolve needs to subtract the info.dli_fbase from symbol addresses in memory for addr2line to recognize them. When a server is compiled without -fPIE, my_addr_resolve should not do it. Unfortunately not all compilers define __PIE__ when -fPIE was used (e.g. older gcc doesn't), so we have to resort to run-time detection. --- mysys/my_addr_resolve.c | 22 +++++++++++++++++----- 1 file changed, 17 insertions(+), 5 deletions(-) diff --git a/mysys/my_addr_resolve.c b/mysys/my_addr_resolve.c index 0603a50fac7..86670cf1db2 100644 --- a/mysys/my_addr_resolve.c +++ b/mysys/my_addr_resolve.c @@ -170,6 +170,7 @@ static pid_t pid; static char addr2line_binary[1024]; static char output[1024]; static struct pollfd poll_fds; +static void *addr_offset; int start_addr2line_fork(const char *binary_path) { @@ -297,7 +298,6 @@ static int addr_resolve(void *ptr, my_addr_loc *loc) int my_addr_resolve(void *ptr, my_addr_loc *loc) { Dl_info info; - int error; if (!dladdr(ptr, &info)) return 1; @@ -307,7 +307,7 @@ int my_addr_resolve(void *ptr, my_addr_loc *loc) /* We use dli_fname in case the path is longer than the length of our static string. We don't want to allocate anything - dynamicaly here as we are in a "crashed" state. + dynamically here as we are in a "crashed" state. */ if (start_addr2line_fork(info.dli_fname)) { @@ -318,10 +318,22 @@ int my_addr_resolve(void *ptr, my_addr_loc *loc) } /* Save result for future comparisons. */ strnmov(addr2line_binary, info.dli_fname, sizeof(addr2line_binary)); + + /* + Check if we should use info.dli_fbase as an offset or not + for the base program. This is depending on if the compilation is + done with PIE or not. + */ + addr_offset= info.dli_fbase; +#ifndef __PIE__ + if (strcmp(info.dli_fname, my_progname) == 0 && + addr_resolve((void*) my_addr_resolve, loc) == 0 && + strcmp(loc->func, "my_addr_resolve") == 0) + addr_offset= 0; +#endif } - if (!(error= addr_resolve((void*) (ptr - info.dli_fbase), loc))) - return 0; - return error; + + return addr_resolve((void*) (ptr - addr_offset), loc); } From 88fb89acb7ad6a7300b01d02d71d2cee00449ec4 Mon Sep 17 00:00:00 2001 From: Monty Date: Wed, 2 Feb 2022 16:41:13 +0200 Subject: [PATCH 08/45] Fixes some compiler issues on AIX ( --- include/my_alarm.h | 2 +- mysys/my_addr_resolve.c | 2 +- mysys/my_gethwaddr.c | 3 ++- 3 files changed, 4 insertions(+), 3 deletions(-) diff --git a/include/my_alarm.h b/include/my_alarm.h index 14a81c1ef17..df5cb7f51de 100644 --- a/include/my_alarm.h +++ b/include/my_alarm.h @@ -31,7 +31,7 @@ extern ulong my_time_to_wait_for_lock; #include #ifdef HAVE_SIGHANDLER_T #define sig_return sighandler_t -#elif defined(SOLARIS) || defined(__sun) || defined(__APPLE__) || defined(__FreeBSD__) +#elif defined(SOLARIS) || defined(__sun) || defined(__APPLE__) || defined(__FreeBSD__) || defined(_AIX) typedef void (*sig_return)(int); /* Returns type from signal */ #else typedef void (*sig_return)(void); /* Returns type from signal */ diff --git a/mysys/my_addr_resolve.c b/mysys/my_addr_resolve.c index 86670cf1db2..444a47bb7c5 100644 --- a/mysys/my_addr_resolve.c +++ b/mysys/my_addr_resolve.c @@ -324,7 +324,7 @@ int my_addr_resolve(void *ptr, my_addr_loc *loc) for the base program. This is depending on if the compilation is done with PIE or not. */ - addr_offset= info.dli_fbase; + addr_offset= (void*) info.dli_fbase; #ifndef __PIE__ if (strcmp(info.dli_fname, my_progname) == 0 && addr_resolve((void*) my_addr_resolve, loc) == 0 && diff --git a/mysys/my_gethwaddr.c b/mysys/my_gethwaddr.c index 70e1d549e15..46b62a0166d 100644 --- a/mysys/my_gethwaddr.c +++ b/mysys/my_gethwaddr.c @@ -23,6 +23,7 @@ #ifndef MAIN +#if defined(__APPLE__) || defined(__FreeBSD__) || defined(__linux__) || defined(__sun) || defined(_WIN32) static my_bool memcpy_and_test(uchar *to, uchar *from, uint len) { uint i, res= 1; @@ -32,6 +33,7 @@ static my_bool memcpy_and_test(uchar *to, uchar *from, uint len) res= 0; return res; } +#endif #if defined(__APPLE__) || defined(__FreeBSD__) #include @@ -195,4 +197,3 @@ int main(int argc __attribute__((unused)),char **argv) return 0; } #endif - From 0ec27d7b1f7b5f1f49a3099faa554994bc58603a Mon Sep 17 00:00:00 2001 From: Monty Date: Wed, 2 Feb 2022 14:26:38 +0200 Subject: [PATCH 09/45] Don't run innodb_defgragment under valgrind (too slow) --- mysql-test/suite/innodb/t/innodb_defragment.test | 2 ++ 1 file changed, 2 insertions(+) diff --git a/mysql-test/suite/innodb/t/innodb_defragment.test b/mysql-test/suite/innodb/t/innodb_defragment.test index d9f5f56316e..51ef78377cb 100644 --- a/mysql-test/suite/innodb/t/innodb_defragment.test +++ b/mysql-test/suite/innodb/t/innodb_defragment.test @@ -1,6 +1,8 @@ --source include/have_innodb.inc --source include/big_test.inc --source include/not_embedded.inc +# Valgrind is to slow for this test +--source include/not_valgrind.inc set global innodb_defragment_stats_accuracy = 80; From a1c23807530c6ffd5d400f71d9226bca5b91fb62 Mon Sep 17 00:00:00 2001 From: Monty Date: Sun, 6 Feb 2022 16:05:48 +0200 Subject: [PATCH 10/45] MENT-328 Retry BACKUP STAGE BLOCK DDL in case of deadlocks MENT-328 wrongly assumed that the backup failed because of warnings from mariabackup about not found files. This is normal (and the error message should be deleted). randgen failed because mariabackup didn't retry BACKUP STAGE BLOCK DDL if it failed with a deadlock. To simplify things, I implemented the retry loop in the server as this particular deadlock should be quickly resolved. --- mysql-test/main/backup_locks.result | 23 +++++++++++++++++- mysql-test/main/backup_locks.test | 31 ++++++++++++++++++++++-- sql/backup.cc | 37 ++++++++++++++++++++++------- 3 files changed, 79 insertions(+), 12 deletions(-) diff --git a/mysql-test/main/backup_locks.result b/mysql-test/main/backup_locks.result index 1505c39f166..1e567c1a58d 100644 --- a/mysql-test/main/backup_locks.result +++ b/mysql-test/main/backup_locks.result @@ -39,6 +39,28 @@ MDL_INTENTION_EXCLUSIVE Schema metadata lock test select * from t1; ERROR 40001: Deadlock found when trying to get lock; try restarting transaction backup unlock; +connection con1; +connection default; +# +# Check that BACKUP LOCK blocks some operations +# +create sequence seq1; +create sequence seq2; +backup lock seq1; +connection con1; +CREATE OR REPLACE SEQUENCE seq1 START -28; +ERROR HY000: Sequence 'test.seq1' values are conflicting +SET STATEMENT max_statement_time=10 FOR CREATE OR REPLACE SEQUENCE seq1 START 50; +ERROR 70100: Query execution was interrupted (max_statement_time exceeded) +SET STATEMENT max_statement_time=10 FOR ALTER SEQUENCE IF EXISTS seq1 NOMAXVALUE; +ERROR 70100: Query execution was interrupted (max_statement_time exceeded) +SET STATEMENT max_statement_time=10 FOR ALTER SEQUENCE IF EXISTS seq1 MAXVALUE 1000; +ERROR 70100: Query execution was interrupted (max_statement_time exceeded) +SET STATEMENT max_statement_time=10 for rename table seq2 to seq3, seq3 to seq1; +ERROR 70100: Query execution was interrupted (max_statement_time exceeded) +connection default; +backup unlock; +drop table seq1,seq2; # # BACKUP LOCK and BACKUP UNLOCK are not allowed in procedures. # @@ -141,7 +163,6 @@ ERROR HY000: Can't execute the given command because you have active locked tabl SET STATEMENT max_statement_time=180 FOR BACKUP LOCK test.u; # restart # -connection con1; connection default; disconnect con1; show tables; diff --git a/mysql-test/main/backup_locks.test b/mysql-test/main/backup_locks.test index d2f3d95d703..1271abfd993 100644 --- a/mysql-test/main/backup_locks.test +++ b/mysql-test/main/backup_locks.test @@ -43,10 +43,39 @@ SELECT LOCK_MODE, LOCK_TYPE, TABLE_SCHEMA, TABLE_NAME FROM information_schema.me --error ER_LOCK_DEADLOCK select * from t1; backup unlock; +connection con1; +--reap +connection default; + +--echo # +--echo # Check that BACKUP LOCK blocks some operations +--echo # + +# These test has to be done with timeouts as we want to ensure that the tables +# doesn't change + +create sequence seq1; +create sequence seq2; +backup lock seq1; +connection con1; +--error ER_SEQUENCE_INVALID_DATA +CREATE OR REPLACE SEQUENCE seq1 START -28; +--error ER_STATEMENT_TIMEOUT +SET STATEMENT max_statement_time=10 FOR CREATE OR REPLACE SEQUENCE seq1 START 50; +--error ER_STATEMENT_TIMEOUT +SET STATEMENT max_statement_time=10 FOR ALTER SEQUENCE IF EXISTS seq1 NOMAXVALUE; +--error ER_STATEMENT_TIMEOUT +SET STATEMENT max_statement_time=10 FOR ALTER SEQUENCE IF EXISTS seq1 MAXVALUE 1000; +--error ER_STATEMENT_TIMEOUT +SET STATEMENT max_statement_time=10 for rename table seq2 to seq3, seq3 to seq1; +connection default; +backup unlock; +drop table seq1,seq2; --echo # --echo # BACKUP LOCK and BACKUP UNLOCK are not allowed in procedures. --echo # + delimiter |; --error ER_SP_BADSTATEMENT CREATE PROCEDURE p_BACKUP_LOCK() @@ -162,8 +191,6 @@ SET STATEMENT max_statement_time=180 FOR BACKUP LOCK test.u; --echo # -connection con1; ---reap connection default; disconnect con1; show tables; diff --git a/sql/backup.cc b/sql/backup.cc index 539dc9c31f4..c856048b49a 100644 --- a/sql/backup.cc +++ b/sql/backup.cc @@ -233,8 +233,12 @@ static bool backup_flush(THD *thd) This will probably require a callback from the InnoDB code. */ +/* Retry to get inital lock for 0.1 + 0.5 + 2.25 + 11.25 + 56.25 = 70.35 sec */ +#define MAX_RETRY_COUNT 5 + static bool backup_block_ddl(THD *thd) { + uint sleep_time; DBUG_ENTER("backup_block_ddl"); kill_delayed_threads(); @@ -275,17 +279,32 @@ static bool backup_block_ddl(THD *thd) block new DDL's, in addition to all previous blocks We didn't do this lock above, as we wanted DDL's to be executed while we wait for non transactional tables (which may take a while). + + We do this lock in a loop as we can get a deadlock if there are multi-object + ddl statements like + RENAME TABLE t1 TO t2, t3 TO t3 + and the MDL happens in the middle of it. */ - if (thd->mdl_context.upgrade_shared_lock(backup_flush_ticket, - MDL_BACKUP_WAIT_DDL, - thd->variables.lock_wait_timeout)) + sleep_time= 100; // Start with 0.1 seconds + for (uint i= 0 ; i <= MAX_RETRY_COUNT ; i++) { - /* - Could be a timeout. Downgrade lock to what is was before this function - was called so that this function can be called again - */ - backup_flush_ticket->downgrade_lock(MDL_BACKUP_FLUSH); - DBUG_RETURN(1); + if (!thd->mdl_context.upgrade_shared_lock(backup_flush_ticket, + MDL_BACKUP_WAIT_DDL, + thd->variables.lock_wait_timeout)) + break; + if (thd->get_stmt_da()->sql_errno() != ER_LOCK_DEADLOCK || thd->killed || + i == MAX_RETRY_COUNT) + { + /* + Could be a timeout. Downgrade lock to what is was before this function + was called so that this function can be called again + */ + backup_flush_ticket->downgrade_lock(MDL_BACKUP_FLUSH); + DBUG_RETURN(1); + } + thd->clear_error(); // Forget the DEADLOCK error + my_sleep(sleep_time); + sleep_time*= 5; // Wait a bit longer next time } DBUG_RETURN(0); } From d314bd266491baf0954d13fa51dc22b730a6f4d1 Mon Sep 17 00:00:00 2001 From: Monty Date: Wed, 2 Feb 2022 14:09:21 +0200 Subject: [PATCH 11/45] MDEV-27442 Wrong result upon query with DISTINCT and EXISTS subquery The problem was that get_best_group_min_max() did not check if fields used by the "group_min_max optimization" where used in sub queries. Because of this, it did not detect that a key (b,a) was used in the WHERE clause for the statement: SELECT DISTINCT b FROM t1 WHERE EXISTS ( SELECT 1 FROM DUAL WHERE a > 1 ). Fixed by also traversing the sub queries when checking if a field is used. This disables group_min_max_optimization for the above query. Reviewer: Sergei Petrunia --- mysql-test/main/group_min_max.result | 16 ++++++++++++++++ mysql-test/main/group_min_max.test | 11 +++++++++++ sql/opt_range.cc | 2 +- 3 files changed, 28 insertions(+), 1 deletion(-) diff --git a/mysql-test/main/group_min_max.result b/mysql-test/main/group_min_max.result index a17f3f09c3b..f264f221ab5 100644 --- a/mysql-test/main/group_min_max.result +++ b/mysql-test/main/group_min_max.result @@ -4027,3 +4027,19 @@ drop table t1; # # End of 10.1 tests # +# +# MDEV-27442 Wrong result upon query with DISTINCT and EXISTS subquery +# +CREATE TABLE t1 (a int, b int, KEY b (b,a)) ENGINE=MyISAM; +INSERT INTO t1 VALUES (0,100),(2,100),(2,101),(3,102); +# Must not use Using index for group-by +explain SELECT DISTINCT b FROM t1 WHERE EXISTS ( SELECT 1 FROM DUAL WHERE a > 1 ); +id select_type table type possible_keys key key_len ref rows Extra +1 PRIMARY t1 index NULL b 10 NULL 4 Using where; Using index +2 DEPENDENT SUBQUERY NULL NULL NULL NULL NULL NULL NULL No tables used +SELECT DISTINCT b FROM t1 WHERE EXISTS ( SELECT 1 FROM DUAL WHERE a > 1 ); +b +100 +101 +102 +DROP TABLE t1; diff --git a/mysql-test/main/group_min_max.test b/mysql-test/main/group_min_max.test index 526552dda92..4622fe473a0 100644 --- a/mysql-test/main/group_min_max.test +++ b/mysql-test/main/group_min_max.test @@ -1689,3 +1689,14 @@ drop table t1; --echo # --echo # End of 10.1 tests --echo # + +--echo # +--echo # MDEV-27442 Wrong result upon query with DISTINCT and EXISTS subquery +--echo # + +CREATE TABLE t1 (a int, b int, KEY b (b,a)) ENGINE=MyISAM; +INSERT INTO t1 VALUES (0,100),(2,100),(2,101),(3,102); +--echo # Must not use Using index for group-by +explain SELECT DISTINCT b FROM t1 WHERE EXISTS ( SELECT 1 FROM DUAL WHERE a > 1 ); +SELECT DISTINCT b FROM t1 WHERE EXISTS ( SELECT 1 FROM DUAL WHERE a > 1 ); +DROP TABLE t1; diff --git a/sql/opt_range.cc b/sql/opt_range.cc index ae24a257aaa..e3d26896900 100644 --- a/sql/opt_range.cc +++ b/sql/opt_range.cc @@ -14000,7 +14000,7 @@ get_best_group_min_max(PARAM *param, SEL_TREE *tree, double read_time) key_part_range[1]= last_part; /* Check if cur_part is referenced in the WHERE clause. */ - if (join->conds->walk(&Item::find_item_in_field_list_processor, 0, + if (join->conds->walk(&Item::find_item_in_field_list_processor, true, key_part_range)) { cause= "keypart reference from where clause"; From 38058c04a4fc021f381f8000e40ed23bd4fb8d75 Mon Sep 17 00:00:00 2001 From: Monty Date: Wed, 2 Feb 2022 14:25:25 +0200 Subject: [PATCH 12/45] MDEV-26585 Wrong query results when `using index for group-by` The problem was that "group_min_max optimization" does not work if some aggregate functions, like COUNT(*), is used. The function get_best_group_min_max() is using the join->sum_funcs array to check which aggregate functions are used. The bug was that aggregates in HAVING where not yet added to join->sum_funcs at the time get_best_group_min_max() was called. Fixed by populate join->sum_funcs already in prepare, which means that all sum functions will be in join->sum_funcs in get_best_group_min_max(). A benefit of this approach is that we can remove several calls to make_sum_func_list() from the code and simplify the function. I removed some wrong setting of 'sort_and_group'. This variable is set when alloc_group_fields() is called, as part of allocating the cache needed by end_send_group() and does not need to be set by other functions. One problematic thing was that Spider is using *join->sum_funcs to detect at which stage the optimizer is and do internal calculations of aggregate functions. Updating join->sum_funcs early caused Spider to fail when trying to find min/max values in opt_sum_query(). Fixed by temporarily resetting sum_funcs during opt_sum_query(). Reviewer: Sergei Petrunia --- mysql-test/main/group_min_max.result | 21 ++++++++ mysql-test/main/group_min_max.test | 22 ++++++++- sql/sql_select.cc | 72 +++++++++++++++++----------- sql/sql_select.h | 14 +++++- 4 files changed, 97 insertions(+), 32 deletions(-) diff --git a/mysql-test/main/group_min_max.result b/mysql-test/main/group_min_max.result index f264f221ab5..4f7c49092d3 100644 --- a/mysql-test/main/group_min_max.result +++ b/mysql-test/main/group_min_max.result @@ -4043,3 +4043,24 @@ b 101 102 DROP TABLE t1; +# +# MDEV-26585 Wrong query results when `using index for group-by` +# +CREATE TABLE `t1` ( +`id` int(11) NOT NULL AUTO_INCREMENT, +`owner_id` int(11) DEFAULT NULL, +`foo` tinyint(1) DEFAULT 0, +`whatever` varchar(255) DEFAULT NULL, +PRIMARY KEY (`id`), +KEY `index_t1_on_owner_id_and_foo` (`owner_id`,`foo`) +) engine=InnoDB DEFAULT CHARSET=utf8; +INSERT INTO t1 (owner_id, foo, whatever) +VALUES (1, TRUE, "yello"), (1, FALSE, "yello"), (2, TRUE, "yello"), +(2, TRUE, "yello"), (2, FALSE, "yello"); +EXPLAIN SELECT DISTINCT owner_id FROM t1 WHERE foo = true GROUP BY owner_id HAVING (COUNT(*) = 1); +id select_type table type possible_keys key key_len ref rows Extra +1 SIMPLE t1 index NULL index_t1_on_owner_id_and_foo 7 NULL 5 Using where; Using index +SELECT DISTINCT owner_id FROM t1 WHERE foo = true GROUP BY owner_id HAVING (COUNT(*) = 1); +owner_id +1 +DROP TABLE t1; diff --git a/mysql-test/main/group_min_max.test b/mysql-test/main/group_min_max.test index 4622fe473a0..b1d912684c6 100644 --- a/mysql-test/main/group_min_max.test +++ b/mysql-test/main/group_min_max.test @@ -4,7 +4,7 @@ # --source include/default_optimizer_switch.inc - +--source include/have_innodb.inc # # TODO: # Add queries with: @@ -1700,3 +1700,23 @@ INSERT INTO t1 VALUES (0,100),(2,100),(2,101),(3,102); explain SELECT DISTINCT b FROM t1 WHERE EXISTS ( SELECT 1 FROM DUAL WHERE a > 1 ); SELECT DISTINCT b FROM t1 WHERE EXISTS ( SELECT 1 FROM DUAL WHERE a > 1 ); DROP TABLE t1; + +--echo # +--echo # MDEV-26585 Wrong query results when `using index for group-by` +--echo # + +CREATE TABLE `t1` ( + `id` int(11) NOT NULL AUTO_INCREMENT, + `owner_id` int(11) DEFAULT NULL, + `foo` tinyint(1) DEFAULT 0, + `whatever` varchar(255) DEFAULT NULL, + PRIMARY KEY (`id`), + KEY `index_t1_on_owner_id_and_foo` (`owner_id`,`foo`) +) engine=InnoDB DEFAULT CHARSET=utf8; + +INSERT INTO t1 (owner_id, foo, whatever) +VALUES (1, TRUE, "yello"), (1, FALSE, "yello"), (2, TRUE, "yello"), + (2, TRUE, "yello"), (2, FALSE, "yello"); +EXPLAIN SELECT DISTINCT owner_id FROM t1 WHERE foo = true GROUP BY owner_id HAVING (COUNT(*) = 1); +SELECT DISTINCT owner_id FROM t1 WHERE foo = true GROUP BY owner_id HAVING (COUNT(*) = 1); +DROP TABLE t1; diff --git a/sql/sql_select.cc b/sql/sql_select.cc index 6fdde5f82dd..fdf58349fc2 100644 --- a/sql/sql_select.cc +++ b/sql/sql_select.cc @@ -1589,7 +1589,8 @@ bool JOIN::prepare_stage2() #endif if (select_lex->olap == ROLLUP_TYPE && rollup_init()) goto err; - if (alloc_func_list()) + if (alloc_func_list() || + make_sum_func_list(all_fields, fields_list, false)) goto err; res= FALSE; @@ -2204,7 +2205,21 @@ JOIN::optimize_inner() If all items were resolved by opt_sum_query, there is no need to open any tables. */ - if ((res=opt_sum_query(thd, select_lex->leaf_tables, all_fields, conds))) + + /* + The following resetting and restoring of sum_funcs is needed to + go around a bug in spider where it assumes that + make_sum_func_list() has not been called yet and do logical + choices based on this if special handling of min/max functions should + be done. We disable this special handling while we are trying to find + out if we can replace MIN/MAX values with constants. + */ + Item_sum **save_func_sums= sum_funcs, *tmp_sum_funcs= 0; + sum_funcs= &tmp_sum_funcs; + res= opt_sum_query(thd, select_lex->leaf_tables, all_fields, conds); + sum_funcs= save_func_sums; + + if (res) { DBUG_ASSERT(res >= 0); if (res == HA_ERR_KEY_NOT_FOUND) @@ -2776,13 +2791,15 @@ int JOIN::optimize_stage2() calc_group_buffer(this, group_list); } - if (test_if_subpart(group_list, order) || - (!group_list && tmp_table_param.sum_func_count)) - { + /* + We can ignore ORDER BY if it's a prefix of the GROUP BY list + (as MariaDB is by default sorting on GROUP BY) or + if there is no GROUP BY and aggregate functions are used + (as the result will only contain one row). + */ + if (order && (test_if_subpart(group_list, order) || + (!group_list && tmp_table_param.sum_func_count))) order=0; - if (is_indexed_agg_distinct(this, NULL)) - sort_and_group= 0; - } // Can't use sort on head table if using join buffering if (full_join || hash_join) @@ -2814,7 +2831,6 @@ int JOIN::optimize_stage2() if (select_lex->have_window_funcs()) simple_order= FALSE; - /* If the hint FORCE INDEX FOR ORDER BY/GROUP BY is used for the table whose columns are required to be returned in a sorted order, then @@ -3540,7 +3556,7 @@ bool JOIN::make_aggr_tables_info() // for the first table if (group_list || tmp_table_param.sum_func_count) { - if (make_sum_func_list(*curr_all_fields, *curr_fields_list, true, true)) + if (make_sum_func_list(*curr_all_fields, *curr_fields_list, true)) DBUG_RETURN(true); if (prepare_sum_aggregators(sum_funcs, !join_tab->is_using_agg_loose_index_scan())) @@ -3650,7 +3666,7 @@ bool JOIN::make_aggr_tables_info() last_tab->all_fields= &tmp_all_fields3; last_tab->fields= &tmp_fields_list3; } - if (make_sum_func_list(*curr_all_fields, *curr_fields_list, true, true)) + if (make_sum_func_list(*curr_all_fields, *curr_fields_list, true)) DBUG_RETURN(true); if (prepare_sum_aggregators(sum_funcs, !join_tab || @@ -3846,8 +3862,6 @@ JOIN::create_postjoin_aggr_table(JOIN_TAB *tab, List *table_fields, } else { - if (make_sum_func_list(all_fields, fields_list, false)) - goto err; if (prepare_sum_aggregators(sum_funcs, !join_tab->is_using_agg_loose_index_scan())) goto err; @@ -7089,8 +7103,7 @@ void optimize_keyuse(JOIN *join, DYNAMIC_ARRAY *keyuse_array) Check for the presence of AGGFN(DISTINCT a) queries that may be subject to loose index scan. - - Check if the query is a subject to AGGFN(DISTINCT) using loose index scan + Check if the query is a subject to AGGFN(DISTINCT) using loose index scan (QUICK_GROUP_MIN_MAX_SELECT). Optionally (if out_args is supplied) will push the arguments of AGGFN(DISTINCT) to the list @@ -7123,14 +7136,11 @@ is_indexed_agg_distinct(JOIN *join, List *out_args) Item_sum **sum_item_ptr; bool result= false; - if (join->table_count != 1 || /* reference more than 1 table */ + if (join->table_count != 1 || /* reference more than 1 table */ join->select_distinct || /* or a DISTINCT */ join->select_lex->olap == ROLLUP_TYPE) /* Check (B3) for ROLLUP */ return false; - if (join->make_sum_func_list(join->all_fields, join->fields_list, true)) - return false; - Bitmap first_aggdistinct_fields; bool first_aggdistinct_fields_initialized= false; for (sum_item_ptr= join->sum_funcs; *sum_item_ptr; sum_item_ptr++) @@ -7232,16 +7242,23 @@ add_group_and_distinct_keys(JOIN *join, JOIN_TAB *join_tab) while ((item= select_items_it++)) item->walk(&Item::collect_item_field_processor, 0, &indexed_fields); } - else if (join->tmp_table_param.sum_func_count && - is_indexed_agg_distinct(join, &indexed_fields)) + else if (!join->tmp_table_param.sum_func_count || + !is_indexed_agg_distinct(join, &indexed_fields)) { - join->sort_and_group= 1; - } - else + /* + There where no GROUP BY fields and also either no aggregate + functions or not all aggregate functions where used with the + same DISTINCT (or MIN() / MAX() that works similarly). + Nothing to do there. + */ return; + } if (indexed_fields.elements == 0) + { + /* There where no index we could use to satisfy the GROUP BY */ return; + } /* Intersect the keys of all group fields. */ cur_item= indexed_fields_it++; @@ -25692,16 +25709,13 @@ bool JOIN::alloc_func_list() bool JOIN::make_sum_func_list(List &field_list, List &send_result_set_metadata, - bool before_group_by, bool recompute) + bool before_group_by) { List_iterator_fast it(field_list); Item_sum **func; Item *item; DBUG_ENTER("make_sum_func_list"); - if (*sum_funcs && !recompute) - DBUG_RETURN(FALSE); /* We have already initialized sum_funcs. */ - func= sum_funcs; while ((item=it++)) { @@ -25848,7 +25862,7 @@ change_to_use_tmp_fields(THD *thd, Ref_ptr_array ref_pointer_array, Change all funcs to be fields in tmp table. @param thd THD pointer - @param ref_pointer_array array of pointers to top elements of filed list + @param ref_pointer_array array of pointers to top elements of field list @param res_selected_fields new list of items of select item list @param res_all_fields new list of all items @param elements number of elements in select item list diff --git a/sql/sql_select.h b/sql/sql_select.h index 29e42ff8ef8..eea1ca9becd 100644 --- a/sql/sql_select.h +++ b/sql/sql_select.h @@ -1196,7 +1196,17 @@ public: Indicates that grouping will be performed on the result set during query execution. This field belongs to query execution. - @see make_group_fields, alloc_group_fields, JOIN::exec + If 'sort_and_group' is set, then the optimizer is going to use on of + the following algorithms to resolve GROUP BY. + + - If one table, sort the table and then calculate groups on the fly. + - If more than one table, create a temporary table to hold the join, + sort it and then resolve group by on the fly. + + The 'on the fly' calculation is done in end_send_group() + + @see make_group_fields, alloc_group_fields, JOIN::exec, + setup_end_select_func */ bool sort_and_group; bool first_record,full_join, no_field_update; @@ -1654,7 +1664,7 @@ public: bool make_range_rowid_filters(); bool init_range_rowid_filters(); bool make_sum_func_list(List &all_fields, List &send_fields, - bool before_group_by, bool recompute= FALSE); + bool before_group_by); /// Initialzes a slice, see comments for ref_ptrs above. Ref_ptr_array ref_ptr_array_slice(size_t slice_num) From c0a44ff7f19cc697ab5b940b5af539b5f630bc55 Mon Sep 17 00:00:00 2001 From: Daniel Bartholomew Date: Tue, 8 Feb 2022 16:28:44 -0500 Subject: [PATCH 13/45] bump the VERSION --- VERSION | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/VERSION b/VERSION index 3c9ab398726..d9c4622d96b 100644 --- a/VERSION +++ b/VERSION @@ -1,3 +1,3 @@ MYSQL_VERSION_MAJOR=10 MYSQL_VERSION_MINOR=2 -MYSQL_VERSION_PATCH=42 +MYSQL_VERSION_PATCH=43 From 30cc63fa1a2aaae1a63bed8e83adb71a9abf0b95 Mon Sep 17 00:00:00 2001 From: Daniel Bartholomew Date: Tue, 8 Feb 2022 16:47:37 -0500 Subject: [PATCH 14/45] bump the VERSION --- VERSION | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/VERSION b/VERSION index 2504c916680..6deead00756 100644 --- a/VERSION +++ b/VERSION @@ -1,4 +1,4 @@ MYSQL_VERSION_MAJOR=10 MYSQL_VERSION_MINOR=3 -MYSQL_VERSION_PATCH=33 +MYSQL_VERSION_PATCH=34 SERVER_MATURITY=stable From 2f07b21cf3aafe4b467c1758e5f9283ebe6eab35 Mon Sep 17 00:00:00 2001 From: Daniel Bartholomew Date: Tue, 8 Feb 2022 17:10:48 -0500 Subject: [PATCH 15/45] bump the VERSION --- VERSION | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/VERSION b/VERSION index 16ab780f3f3..cd6f03a2b81 100644 --- a/VERSION +++ b/VERSION @@ -1,4 +1,4 @@ MYSQL_VERSION_MAJOR=10 MYSQL_VERSION_MINOR=4 -MYSQL_VERSION_PATCH=23 +MYSQL_VERSION_PATCH=24 SERVER_MATURITY=stable From f7704d74cb99f3b5cdd106ef76bd9cd8cef6eb8a Mon Sep 17 00:00:00 2001 From: Daniel Bartholomew Date: Tue, 8 Feb 2022 17:31:40 -0500 Subject: [PATCH 16/45] bump the VERSION --- VERSION | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/VERSION b/VERSION index c986c33613e..9d94c079411 100644 --- a/VERSION +++ b/VERSION @@ -1,4 +1,4 @@ MYSQL_VERSION_MAJOR=10 MYSQL_VERSION_MINOR=5 -MYSQL_VERSION_PATCH=14 +MYSQL_VERSION_PATCH=15 SERVER_MATURITY=stable From fa73117bf8d3a271ca724fbec08efede9387d7d7 Mon Sep 17 00:00:00 2001 From: Daniel Bartholomew Date: Tue, 8 Feb 2022 17:51:29 -0500 Subject: [PATCH 17/45] bump the VERSION --- VERSION | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/VERSION b/VERSION index cbe56835de8..38d0bcd7a05 100644 --- a/VERSION +++ b/VERSION @@ -1,4 +1,4 @@ MYSQL_VERSION_MAJOR=10 MYSQL_VERSION_MINOR=6 -MYSQL_VERSION_PATCH=6 +MYSQL_VERSION_PATCH=7 SERVER_MATURITY=stable From 9055db2f28b9e6b2c16810fb78d4cc23f86d005e Mon Sep 17 00:00:00 2001 From: Daniel Bartholomew Date: Tue, 8 Feb 2022 18:15:35 -0500 Subject: [PATCH 18/45] bump the VERSION --- VERSION | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/VERSION b/VERSION index c60a3f96635..d6ba95be162 100644 --- a/VERSION +++ b/VERSION @@ -1,4 +1,4 @@ MYSQL_VERSION_MAJOR=10 MYSQL_VERSION_MINOR=7 -MYSQL_VERSION_PATCH=2 +MYSQL_VERSION_PATCH=3 SERVER_MATURITY=stable From 5c46751f238ee8dcef1e718ac5f63952bff5d09d Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Marko=20M=C3=A4kel=C3=A4?= Date: Wed, 9 Feb 2022 08:36:41 +0200 Subject: [PATCH 19/45] MDEV-27734 Set innodb_change_buffering=none by default The aim of the InnoDB change buffer is to avoid delays when a leaf page of a secondary index is not present in the buffer pool, and a record needs to be inserted, delete-marked, or purged. Instead of reading the page into the buffer pool for making such a modification, we may insert a record to the change buffer (a special index tree in the InnoDB system tablespace). The buffered changes are guaranteed to be merged if the index page actually needs to be read later. The change buffer could be useful when the database is stored on a rotational medium (hard disk) where random seeks are slower than sequential reads or writes. Obviously, the change buffer will cause write amplification, due to potentially large amount of metadata that is being written to the change buffer. We will have to write redo log records for modifying the change buffer tree as well as the user tablespace. Furthermore, in the user tablespace, we must maintain a change buffer bitmap page that uses 2 bits for estimating the amount of free space in pages, and 1 bit to specify whether buffered changes exist. This bitmap needs to be updated on every operation, which could reduce performance. Even if the change buffer were free of bugs such as MDEV-24449 (potentially causing the corruption of any page in the system tablespace) or MDEV-26977 (corruption of secondary indexes due to a currently unknown reason), it will make diagnosis of other data corruption harder. Because of all this, it is best to disable the change buffer by default. --- mysql-test/suite/innodb/r/ibuf_not_empty.result | 1 + .../innodb/r/innodb-change-buffer-recovery.result | 1 + mysql-test/suite/innodb/t/ibuf_not_empty.test | 1 + .../innodb/t/innodb-change-buffer-recovery.test | 1 + .../r/innodb_change_buffering_basic.result | 14 +++++++------- mysql-test/suite/sys_vars/r/sysvars_innodb.result | 2 +- storage/innobase/handler/ha_innodb.cc | 2 +- 7 files changed, 13 insertions(+), 9 deletions(-) diff --git a/mysql-test/suite/innodb/r/ibuf_not_empty.result b/mysql-test/suite/innodb/r/ibuf_not_empty.result index d1b8203b063..f2da89990b0 100644 --- a/mysql-test/suite/innodb/r/ibuf_not_empty.result +++ b/mysql-test/suite/innodb/r/ibuf_not_empty.result @@ -5,6 +5,7 @@ c INT, INDEX(b)) ENGINE=InnoDB STATS_PERSISTENT=0; SET GLOBAL innodb_change_buffering_debug = 1; +SET GLOBAL innodb_change_buffering=all; INSERT INTO t1 SELECT 0,'x',1 FROM seq_1_to_1024; # restart: --innodb-force-recovery=6 --innodb-change-buffer-dump check table t1; diff --git a/mysql-test/suite/innodb/r/innodb-change-buffer-recovery.result b/mysql-test/suite/innodb/r/innodb-change-buffer-recovery.result index 678c8c67be5..f676d15b134 100644 --- a/mysql-test/suite/innodb/r/innodb-change-buffer-recovery.result +++ b/mysql-test/suite/innodb/r/innodb-change-buffer-recovery.result @@ -13,6 +13,7 @@ c INT, INDEX(b)) ENGINE=InnoDB STATS_PERSISTENT=0; SET GLOBAL innodb_change_buffering_debug = 1; +SET GLOBAL innodb_change_buffering = all; INSERT INTO t1 SELECT 0,'x',1 FROM seq_1_to_8192; BEGIN; SELECT b FROM t1 LIMIT 3; diff --git a/mysql-test/suite/innodb/t/ibuf_not_empty.test b/mysql-test/suite/innodb/t/ibuf_not_empty.test index 545a78c887e..96ceb81ac00 100644 --- a/mysql-test/suite/innodb/t/ibuf_not_empty.test +++ b/mysql-test/suite/innodb/t/ibuf_not_empty.test @@ -24,6 +24,7 @@ ENGINE=InnoDB STATS_PERSISTENT=0; # change buffering is possible, so that the change buffer will be used # whenever possible. SET GLOBAL innodb_change_buffering_debug = 1; +SET GLOBAL innodb_change_buffering=all; # Create enough rows for the table, so that the change buffer will be # used for modifying the secondary index page. There must be multiple diff --git a/mysql-test/suite/innodb/t/innodb-change-buffer-recovery.test b/mysql-test/suite/innodb/t/innodb-change-buffer-recovery.test index a12ca43cec1..129037e783b 100644 --- a/mysql-test/suite/innodb/t/innodb-change-buffer-recovery.test +++ b/mysql-test/suite/innodb/t/innodb-change-buffer-recovery.test @@ -33,6 +33,7 @@ ENGINE=InnoDB STATS_PERSISTENT=0; # change buffering is possible, so that the change buffer will be used # whenever possible. SET GLOBAL innodb_change_buffering_debug = 1; +SET GLOBAL innodb_change_buffering = all; let SEARCH_FILE = $MYSQLTEST_VARDIR/log/mysqld.1.err; # Create enough rows for the table, so that the change buffer will be diff --git a/mysql-test/suite/sys_vars/r/innodb_change_buffering_basic.result b/mysql-test/suite/sys_vars/r/innodb_change_buffering_basic.result index 92e22c6aa34..c11f4ee617c 100644 --- a/mysql-test/suite/sys_vars/r/innodb_change_buffering_basic.result +++ b/mysql-test/suite/sys_vars/r/innodb_change_buffering_basic.result @@ -1,28 +1,28 @@ SET @start_global_value = @@global.innodb_change_buffering; SELECT @start_global_value; @start_global_value -all +none Valid values are 'all', 'deletes', 'changes', 'inserts', 'none', 'purges' select @@global.innodb_change_buffering in ('all', 'deletes', 'changes', 'inserts', 'none', 'purges'); @@global.innodb_change_buffering in ('all', 'deletes', 'changes', 'inserts', 'none', 'purges') 1 select @@global.innodb_change_buffering; @@global.innodb_change_buffering -all +none select @@session.innodb_change_buffering; ERROR HY000: Variable 'innodb_change_buffering' is a GLOBAL variable show global variables like 'innodb_change_buffering'; Variable_name Value -innodb_change_buffering all +innodb_change_buffering none show session variables like 'innodb_change_buffering'; Variable_name Value -innodb_change_buffering all +innodb_change_buffering none select * from information_schema.global_variables where variable_name='innodb_change_buffering'; VARIABLE_NAME VARIABLE_VALUE -INNODB_CHANGE_BUFFERING all +INNODB_CHANGE_BUFFERING none select * from information_schema.session_variables where variable_name='innodb_change_buffering'; VARIABLE_NAME VARIABLE_VALUE -INNODB_CHANGE_BUFFERING all +INNODB_CHANGE_BUFFERING none set global innodb_change_buffering='none'; select @@global.innodb_change_buffering; @@global.innodb_change_buffering @@ -62,4 +62,4 @@ ERROR 42000: Variable 'innodb_change_buffering' can't be set to the value of 'so SET @@global.innodb_change_buffering = @start_global_value; SELECT @@global.innodb_change_buffering; @@global.innodb_change_buffering -all +none diff --git a/mysql-test/suite/sys_vars/r/sysvars_innodb.result b/mysql-test/suite/sys_vars/r/sysvars_innodb.result index ecd107f67c8..c333b56fd2e 100644 --- a/mysql-test/suite/sys_vars/r/sysvars_innodb.result +++ b/mysql-test/suite/sys_vars/r/sysvars_innodb.result @@ -311,7 +311,7 @@ READ_ONLY NO COMMAND_LINE_ARGUMENT OPTIONAL VARIABLE_NAME INNODB_CHANGE_BUFFERING SESSION_VALUE NULL -DEFAULT_VALUE all +DEFAULT_VALUE none VARIABLE_SCOPE GLOBAL VARIABLE_TYPE ENUM VARIABLE_COMMENT Buffer changes to secondary indexes. diff --git a/storage/innobase/handler/ha_innodb.cc b/storage/innobase/handler/ha_innodb.cc index 646e2619348..2962e6a4a22 100644 --- a/storage/innobase/handler/ha_innodb.cc +++ b/storage/innobase/handler/ha_innodb.cc @@ -19623,7 +19623,7 @@ static MYSQL_SYSVAR_BOOL(numa_interleave, srv_numa_interleave, static MYSQL_SYSVAR_ENUM(change_buffering, innodb_change_buffering, PLUGIN_VAR_RQCMDARG, "Buffer changes to secondary indexes.", - NULL, NULL, IBUF_USE_ALL, &innodb_change_buffering_typelib); + NULL, NULL, IBUF_USE_NONE, &innodb_change_buffering_typelib); static MYSQL_SYSVAR_UINT(change_buffer_max_size, srv_change_buffer_max_size, From fd101daa84ec5f70f09c48e3fb7a4ce8f6d26edb Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Marko=20M=C3=A4kel=C3=A4?= Date: Wed, 9 Feb 2022 15:10:10 +0200 Subject: [PATCH 20/45] MDEV-27716 mtr_t::commit() acquires log_sys.mutex when writing no log mtr_t::is_block_dirtied(), mtr_t::memo_push(): Never set m_made_dirty for pages of the temporary tablespace. Ever since commit 5eb539555b36a60944eefeb84d5d6d436ba61e63 we never add those pages to buf_pool.flush_list. mtr_t::commit(): Implement part of mtr_t::prepare_write() here, and avoid acquiring log_sys.mutex if no log is written. During IMPORT TABLESPACE fixup, we do not write log, but we must add pages to buf_pool.flush_list and for that, be prepared to acquire log_sys.flush_order_mutex. mtr_t::do_write(): Replaces mtr_t::prepare_write(). --- storage/innobase/include/mtr0mtr.h | 6 ++-- storage/innobase/include/mtr0mtr.inl | 9 +++--- storage/innobase/mtr/mtr0mtr.cc | 46 ++++++++++++++-------------- 3 files changed, 31 insertions(+), 30 deletions(-) diff --git a/storage/innobase/include/mtr0mtr.h b/storage/innobase/include/mtr0mtr.h index 3e72bf9acd7..3f9777ad225 100644 --- a/storage/innobase/include/mtr0mtr.h +++ b/storage/innobase/include/mtr0mtr.h @@ -623,9 +623,9 @@ private: @param type extended record subtype; @see mrec_ext_t */ inline void log_write_extended(const buf_block_t &block, byte type); - /** Prepare to write the mini-transaction log to the redo log buffer. - @return number of bytes to write in finish_write() */ - inline ulint prepare_write(); + /** Append the redo log records to the redo log buffer. + @return {start_lsn,flush_ahead} */ + std::pair do_write(); /** Append the redo log records to the redo log buffer. @param len number of bytes to write diff --git a/storage/innobase/include/mtr0mtr.inl b/storage/innobase/include/mtr0mtr.inl index 48bdb9bb6d1..bc2986503f9 100644 --- a/storage/innobase/include/mtr0mtr.inl +++ b/storage/innobase/include/mtr0mtr.inl @@ -1,7 +1,7 @@ /***************************************************************************** Copyright (c) 1995, 2014, Oracle and/or its affiliates. All Rights Reserved. -Copyright (c) 2017, 2021, MariaDB Corporation. +Copyright (c) 2017, 2022, MariaDB Corporation. 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 @@ -32,7 +32,8 @@ inline bool mtr_t::is_block_dirtied(const buf_block_t *block) { ut_ad(block->page.state() == BUF_BLOCK_FILE_PAGE); ut_ad(block->page.buf_fix_count()); - return block->page.oldest_modification() <= 1; + return block->page.oldest_modification() <= 1 && + block->page.id().space() < SRV_TMP_SPACE_ID; } /** @@ -51,8 +52,8 @@ mtr_t::memo_push(void* object, mtr_memo_type_t type) grab log_sys.flush_order_mutex at mtr_t::commit() so that we can insert the dirtied page into the flush list. */ - if ((type == MTR_MEMO_PAGE_X_FIX || type == MTR_MEMO_PAGE_SX_FIX) - && !m_made_dirty) { + if (!m_made_dirty + && (type == MTR_MEMO_PAGE_X_FIX || type == MTR_MEMO_PAGE_SX_FIX)) { m_made_dirty = is_block_dirtied( reinterpret_cast(object)); diff --git a/storage/innobase/mtr/mtr0mtr.cc b/storage/innobase/mtr/mtr0mtr.cc index a8dffa48c35..ca97a9e77e4 100644 --- a/storage/innobase/mtr/mtr0mtr.cc +++ b/storage/innobase/mtr/mtr0mtr.cc @@ -404,18 +404,27 @@ void mtr_t::commit() std::pair lsns; - if (const ulint len= prepare_write()) - lsns= finish_write(len); + if (UNIV_LIKELY(m_log_mode == MTR_LOG_ALL)) + { + lsns= do_write(); + + if (m_made_dirty) + mysql_mutex_lock(&log_sys.flush_order_mutex); + + /* It is now safe to release log_sys.mutex because the + buf_pool.flush_order_mutex will ensure that we are the first one + to insert into buf_pool.flush_list. */ + mysql_mutex_unlock(&log_sys.mutex); + } else + { + ut_ad(m_log_mode == MTR_LOG_NO_REDO); + ut_ad(m_log.size() == 0); + m_commit_lsn= log_sys.get_lsn(); lsns= { m_commit_lsn, PAGE_FLUSH_NO }; - - if (m_made_dirty) - mysql_mutex_lock(&log_sys.flush_order_mutex); - - /* It is now safe to release the log mutex because the - flush_order mutex will ensure that we are the first one - to insert into the flush list. */ - mysql_mutex_unlock(&log_sys.mutex); + if (UNIV_UNLIKELY(m_made_dirty)) /* This should be IMPORT TABLESPACE */ + mysql_mutex_lock(&log_sys.flush_order_mutex); + } if (m_freed_pages) { @@ -517,7 +526,7 @@ void mtr_t::commit_shrink(fil_space_t &space) log_write_and_flush_prepare(); - const lsn_t start_lsn= finish_write(prepare_write()).first; + const lsn_t start_lsn= do_write().first; mysql_mutex_lock(&log_sys.flush_order_mutex); /* Durably write the reduced FSP_SIZE before truncating the data file. */ @@ -924,19 +933,10 @@ struct mtr_write_log } }; -/** Prepare to write the mini-transaction log to the redo log buffer. -@return number of bytes to write in finish_write() */ -inline ulint mtr_t::prepare_write() +std::pair mtr_t::do_write() { ut_ad(!recv_no_log_write); - - if (UNIV_UNLIKELY(m_log_mode != MTR_LOG_ALL)) { - ut_ad(m_log_mode == MTR_LOG_NO_REDO); - ut_ad(m_log.size() == 0); - mysql_mutex_lock(&log_sys.mutex); - m_commit_lsn = log_sys.get_lsn(); - return 0; - } + ut_ad(m_log_mode == MTR_LOG_ALL); ulint len = m_log.size(); ut_ad(len > 0); @@ -968,7 +968,7 @@ inline ulint mtr_t::prepare_write() /* check and attempt a checkpoint if exceeding capacity */ log_margin_checkpoint_age(len); - return(len); + return finish_write(len); } /** Append the redo log records to the redo log buffer. From 9bd7e526e7b82a2dc554e942d41072f47dd471fa Mon Sep 17 00:00:00 2001 From: Sergei Golubchik Date: Wed, 9 Feb 2022 16:36:11 +0100 Subject: [PATCH 21/45] support lzma < 5.1.3alpha where `lzma_allocator *allocator` isn't declared const --- include/providers/lzma.h | 10 ++++++++-- 1 file changed, 8 insertions(+), 2 deletions(-) diff --git a/include/providers/lzma.h b/include/providers/lzma.h index 0ba04ede472..8125bb8cb04 100644 --- a/include/providers/lzma.h +++ b/include/providers/lzma.h @@ -52,12 +52,18 @@ typedef enum #define lzma_stream_buffer_decode(...) provider_service_lzma->lzma_stream_buffer_decode_ptr (__VA_ARGS__) #define lzma_easy_buffer_encode(...) provider_service_lzma->lzma_easy_buffer_encode_ptr (__VA_ARGS__) +#elif LZMA_VERSION < 50010030 +#define lzma_maybe_const +#endif + +#ifndef lzma_maybe_const +#define lzma_maybe_const const #endif #define DEFINE_lzma_stream_buffer_decode(NAME) NAME( \ uint64_t *memlimit, \ uint32_t flags, \ - const lzma_allocator *allocator, \ + lzma_maybe_const lzma_allocator *allocator, \ const uint8_t *in, \ size_t *in_pos, \ size_t in_size, \ @@ -69,7 +75,7 @@ typedef enum #define DEFINE_lzma_easy_buffer_encode(NAME) NAME( \ uint32_t preset, \ lzma_check check, \ - const lzma_allocator *allocator, \ + lzma_maybe_const lzma_allocator *allocator, \ const uint8_t *in, \ size_t in_size, \ uint8_t *out, \ From e375f5192487687acaf98c4320f51e2d8ef3c4ae Mon Sep 17 00:00:00 2001 From: Vincent Milum Jr Date: Wed, 9 Feb 2022 13:31:09 -0800 Subject: [PATCH 22/45] MDEV-27790: Fix mis-matched braces for non-Linux targets Ran into this while compiling on FreeBSD 13.0-RELEASE After this one change, it compiles and runs just fine on my FreeBSD Aarch64 server. --- storage/innobase/os/os0file.cc | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/storage/innobase/os/os0file.cc b/storage/innobase/os/os0file.cc index 66c8e76929d..b3a7e233709 100644 --- a/storage/innobase/os/os0file.cc +++ b/storage/innobase/os/os0file.cc @@ -1303,8 +1303,9 @@ use_o_direct: default: break; } + } # ifdef __linux__ - } else if (type == OS_LOG_FILE && !log_sys.is_opened()) { + else if (type == OS_LOG_FILE && !log_sys.is_opened()) { struct stat st; char b[20 + sizeof "/sys/dev/block/" ":" "/../queue/physical_block_size"]; From ad1fb06982d70c7ef61ac792f9dab7eae0e4abf8 Mon Sep 17 00:00:00 2001 From: Monty Date: Thu, 10 Feb 2022 12:28:46 +0200 Subject: [PATCH 23/45] MDEV-27789 mysql_upgrade / mariadb-upgrade in 10.6.6 is putting password in host argument Removed all dependencies of command line arguments based on positions in an array (this kind of code should never have been written). Instead use option names, which are stable. Reviewer: Sergei Golubchik --- client/mysql_upgrade.c | 26 +++++++++++--------------- 1 file changed, 11 insertions(+), 15 deletions(-) diff --git a/client/mysql_upgrade.c b/client/mysql_upgrade.c index 8c186b521c1..b9f4a437bab 100644 --- a/client/mysql_upgrade.c +++ b/client/mysql_upgrade.c @@ -121,7 +121,6 @@ static struct my_option my_long_options[]= &opt_not_used, &opt_not_used, 0 , GET_BOOL, NO_ARG, 0, 0, 0, 0, 0, 0}, {"host", 'h', "Connect to host.", 0, 0, 0, GET_STR, REQUIRED_ARG, 0, 0, 0, 0, 0, 0}, -#define PASSWORD_OPT 12 {"password", 'p', "Password to use when connecting to server. If password is not given," " it's solicited on the tty.", &opt_password,&opt_password, @@ -158,7 +157,6 @@ static struct my_option my_long_options[]= {"upgrade-system-tables", 's', "Only upgrade the system tables in the mysql database. Tables in other databases are not checked or touched.", &opt_systables_only, &opt_systables_only, 0, GET_BOOL, NO_ARG, 0, 0, 0, 0, 0, 0}, -#define USER_OPT (array_elements(my_long_options) - 6) {"user", 'u', "User for login.", &opt_user, &opt_user, 0, GET_STR, REQUIRED_ARG, 0, 0, 0, 0, 0, 0}, {"verbose", 'v', "Display more output about the process; Using it twice will print connection argument; Using it 3 times will print out all CHECK, RENAME and ALTER TABLE during the check phase.", @@ -264,11 +262,11 @@ static void print_error(const char *error_msg, DYNAMIC_STRING *output) */ static void add_one_option_cmd_line(DYNAMIC_STRING *ds, - const struct my_option *opt, - const char* arg) + const char *name, + const char *arg) { dynstr_append(ds, "--"); - dynstr_append(ds, opt->name); + dynstr_append(ds, name); if (arg) { dynstr_append(ds, "="); @@ -278,10 +276,10 @@ static void add_one_option_cmd_line(DYNAMIC_STRING *ds, } static void add_one_option_cnf_file(DYNAMIC_STRING *ds, - const struct my_option *opt, - const char* arg) + const char *name, + const char *arg) { - dynstr_append(ds, opt->name); + dynstr_append(ds, name); if (arg) { dynstr_append(ds, "="); @@ -324,7 +322,7 @@ get_one_option(int optid, const struct my_option *opt, if (argument) { /* Add password to ds_args before overwriting the arg with x's */ - add_one_option_cnf_file(&ds_args, opt, argument); + add_one_option_cnf_file(&ds_args, opt->name, argument); while (*argument) *argument++= 'x'; /* Destroy argument */ tty_password= 0; @@ -383,7 +381,7 @@ get_one_option(int optid, const struct my_option *opt, case OPT_SHARED_MEMORY_BASE_NAME: /* --shared-memory-base-name */ case OPT_PLUGIN_DIR: /* --plugin-dir */ case OPT_DEFAULT_AUTH: /* --default-auth */ - add_one_option_cmd_line(&conn_args, opt, argument); + add_one_option_cmd_line(&conn_args, opt->name, argument); break; } @@ -394,7 +392,7 @@ get_one_option(int optid, const struct my_option *opt, it can be passed on to "mysql" and "mysqlcheck" Save it in the ds_args string */ - add_one_option_cnf_file(&ds_args, opt, argument); + add_one_option_cnf_file(&ds_args, opt->name, argument); } return 0; } @@ -1349,12 +1347,10 @@ int main(int argc, char **argv) { opt_password= get_tty_password(NullS); /* add password to defaults file */ - add_one_option_cnf_file(&ds_args, &my_long_options[PASSWORD_OPT], opt_password); - DBUG_ASSERT(strcmp(my_long_options[PASSWORD_OPT].name, "password") == 0); + add_one_option_cnf_file(&ds_args, "password", opt_password); } /* add user to defaults file */ - add_one_option_cnf_file(&ds_args, &my_long_options[USER_OPT], opt_user); - DBUG_ASSERT(strcmp(my_long_options[USER_OPT].name, "user") == 0); + add_one_option_cnf_file(&ds_args, "user", opt_user); cnf_file_path= strmov(defaults_file, "--defaults-file="); { From 9e39d0ae44595dbd1570805d97c9c874778a6be8 Mon Sep 17 00:00:00 2001 From: Sergei Golubchik Date: Thu, 10 Feb 2022 11:27:14 +0100 Subject: [PATCH 24/45] MDEV-25787 Bug report: crash on SELECT DISTINCT thousands_blob_fields fix a debug assert to account for not opened temp tables --- storage/maria/ha_maria.cc | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/storage/maria/ha_maria.cc b/storage/maria/ha_maria.cc index fd28164cb59..ce23e670c17 100644 --- a/storage/maria/ha_maria.cc +++ b/storage/maria/ha_maria.cc @@ -2789,7 +2789,7 @@ int ha_maria::delete_table(const char *name) void ha_maria::drop_table(const char *name) { - DBUG_ASSERT(file->s->temporary); + DBUG_ASSERT(!file || file->s->temporary); (void) ha_close(); (void) maria_delete_table_files(name, 1, MY_WME); } From 0168d1eda30dad4b517659422e347175eb89e923 Mon Sep 17 00:00:00 2001 From: Oleksandr Byelkin Date: Wed, 15 Sep 2021 16:06:02 +0200 Subject: [PATCH 25/45] MDEV-25766 Unused CTE lead to a crash in find_field_in_tables/find_order_in_list Do not assume that subquery Item always present. --- mysql-test/r/cte_nonrecursive.result | 33 +++++++++++++++++++++++++ mysql-test/t/cte_nonrecursive.test | 36 ++++++++++++++++++++++++++++ sql/sql_base.cc | 7 +++--- 3 files changed, 73 insertions(+), 3 deletions(-) diff --git a/mysql-test/r/cte_nonrecursive.result b/mysql-test/r/cte_nonrecursive.result index b2fee0d3c6f..4aaf11de8bf 100644 --- a/mysql-test/r/cte_nonrecursive.result +++ b/mysql-test/r/cte_nonrecursive.result @@ -2184,4 +2184,37 @@ select * from t1; a 7 drop table t1,t2; +# +# MDEV-25766: Unused CTE lead to a crash in +# find_field_in_tables/find_order_in_list +# +create table t1 (f1 INTEGER); +create view v1 as +select +subq_0.c4 as c2, +subq_0.c4 as c4 +from +(select +ref_0.f1 as c4 +from +t1 as ref_0 +where (select 1) +) as subq_0 +order by c2, c4 desc; +WITH +unused_with AS (select +subq_0.c4 as c6 +from +(select +11 as c4 +from +v1 as ref_0 +) as subq_0, +v1 as ref_2 +) +select 1 ; +1 +1 +drop view v1; +drop table t1; # End of 10.2 tests diff --git a/mysql-test/t/cte_nonrecursive.test b/mysql-test/t/cte_nonrecursive.test index 175be8b9881..723332b43b6 100644 --- a/mysql-test/t/cte_nonrecursive.test +++ b/mysql-test/t/cte_nonrecursive.test @@ -1624,4 +1624,40 @@ select * from t1; drop table t1,t2; +--echo # +--echo # MDEV-25766: Unused CTE lead to a crash in +--echo # find_field_in_tables/find_order_in_list +--echo # + +create table t1 (f1 INTEGER); + +create view v1 as +select + subq_0.c4 as c2, + subq_0.c4 as c4 + from + (select + ref_0.f1 as c4 + from + t1 as ref_0 + where (select 1) + ) as subq_0 + order by c2, c4 desc; + +WITH +unused_with AS (select + subq_0.c4 as c6 + from + (select + 11 as c4 + from + v1 as ref_0 + ) as subq_0, + v1 as ref_2 +) +select 1 ; + +drop view v1; +drop table t1; + --echo # End of 10.2 tests diff --git a/sql/sql_base.cc b/sql/sql_base.cc index 248dedf36e4..a6c07600591 100644 --- a/sql/sql_base.cc +++ b/sql/sql_base.cc @@ -6011,9 +6011,10 @@ find_field_in_tables(THD *thd, Item_ident *item, sl=sl->outer_select()) { Item *subs= sl->master_unit()->item; - if (subs->type() == Item::SUBSELECT_ITEM && - ((Item_subselect*)subs)->substype() == Item_subselect::IN_SUBS && - ((Item_in_subselect*)subs)->test_strategy(SUBS_SEMI_JOIN)) + if (!subs || + (subs->type() == Item::SUBSELECT_ITEM && + ((Item_subselect*)subs)->substype() == Item_subselect::IN_SUBS && + ((Item_in_subselect*)subs)->test_strategy(SUBS_SEMI_JOIN))) { continue; } From 8c7c92adf384b2d0294502d5b38684e68d5eaf27 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Marko=20M=C3=A4kel=C3=A4?= Date: Thu, 10 Feb 2022 15:39:27 +0200 Subject: [PATCH 26/45] MDEV-27787 mariadb-backup --backup is allocating extra memory for log records In commit 685d958e38b825ad9829be311f26729cccf37c46 (MDEV-14425), the log parsing in mariadb-backup --backup was rewritten. The parameter STORE_IF_EXISTS that is being passed to recv_sys.parse_mtr() or recv_sys.parse_pmem() instead of STORE_NO caused unnecessary additional memory allocation for redo log records. --- extra/mariabackup/xtrabackup.cc | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/extra/mariabackup/xtrabackup.cc b/extra/mariabackup/xtrabackup.cc index fe2c89b741c..c32ba4cc1be 100644 --- a/extra/mariabackup/xtrabackup.cc +++ b/extra/mariabackup/xtrabackup.cc @@ -3003,7 +3003,7 @@ static bool xtrabackup_copy_logfile() #ifdef HAVE_PMEM if (log_sys.is_pmem()) { - if ((ut_d(r=) recv_sys.parse_pmem(STORE_IF_EXISTS)) != recv_sys_t::OK) + if ((ut_d(r=) recv_sys.parse_pmem(STORE_NO)) != recv_sys_t::OK) { ut_ad(r == recv_sys_t::GOT_EOF); goto retry; @@ -3073,7 +3073,7 @@ static bool xtrabackup_copy_logfile() start_offset= recv_sys.offset; } - while ((ut_d(r=)recv_sys.parse_pmem(STORE_IF_EXISTS)) == recv_sys_t::OK); + while ((ut_d(r=)recv_sys.parse_pmem(STORE_NO)) == recv_sys_t::OK); ut_ad(r == recv_sys_t::GOT_EOF); pthread_cond_broadcast(&scanned_lsn_cond); @@ -3109,7 +3109,7 @@ static bool xtrabackup_copy_logfile() if (log_sys.buf[recv_sys.offset] <= 1) break; - if (recv_sys.parse_mtr(STORE_IF_EXISTS) == recv_sys_t::OK) + if (recv_sys.parse_mtr(STORE_NO) == recv_sys_t::OK) { do { @@ -3119,7 +3119,7 @@ static bool xtrabackup_copy_logfile() sequence_offset)); *seq= 1; } - while ((r= recv_sys.parse_mtr(STORE_IF_EXISTS)) == recv_sys_t::OK); + while ((r= recv_sys.parse_mtr(STORE_NO)) == recv_sys_t::OK); if (ds_write(dst_log_file, log_sys.buf + start_offset, recv_sys.offset - start_offset)) From a635c40648519fd6c3729c9657872a16a0a20821 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Marko=20M=C3=A4kel=C3=A4?= Date: Thu, 10 Feb 2022 16:37:12 +0200 Subject: [PATCH 27/45] MDEV-27774 Reduce scalability bottlenecks in mtr_t::commit() A prominent bottleneck in mtr_t::commit() is log_sys.mutex between log_sys.append_prepare() and log_close(). User-visible change: The minimum innodb_log_file_size will be increased from 1MiB to 4MiB so that some conditions can be trivially satisfied. log_sys.latch (log_latch): Replaces log_sys.mutex and log_sys.flush_order_mutex. Copying mtr_t::m_log to log_sys.buf is protected by a shared log_sys.latch. Writes from log_sys.buf to the file system will be protected by an exclusive log_sys.latch. log_sys.lsn_lock: Protects the allocation of log buffer in log_sys.append_prepare(). sspin_lock: A simple spin lock, for log_sys.lsn_lock. Thanks to Vladislav Vaintroub for suggesting this idea, and for reviewing these changes. mariadb-backup: Replace some use of log_sys.mutex with recv_sys.mutex. buf_pool_t::insert_into_flush_list(): Implement sorting of flush_list because ordering is otherwise no longer guaranteed. Ordering by LSN is needed for the proper operation of redo log checkpoints. log_sys.append_prepare(): Advance log_sys.lsn and log_sys.buf_free by the length, and return the old values. Also increment write_to_buf, which was previously done in log_close(). mtr_t::finish_write(): Obtain the buffer pointer from log_sys.append_prepare(). log_sys.buf_free: Make the field Atomic_relaxed, to simplify log_flush_margin(). Use only loads and stores to avoid costly read-modify-write atomic operations. buf_pool.flush_list_requests: Replaces export_vars.innodb_buffer_pool_write_requests and srv_stats.buf_pool_write_requests. Protected by buf_pool.flush_list_mutex. buf_pool_t::insert_into_flush_list(): Do not invoke page_cleaner_wakeup(). Let the caller do that after a batch of calls. recv_recover_page(): Invoke a minimal part of buf_pool.insert_into_flush_list(). ReleaseBlocks::modified: A number of pages added to buf_pool.flush_list. ReleaseBlocks::operator(): Merge buf_flush_note_modification() here. log_t::set_capacity(): Renamed from log_set_capacity(). --- extra/mariabackup/xtrabackup.cc | 61 ++-- .../r/innodb_encrypt_log_corruption.result | 20 +- .../suite/innodb/r/log_corruption.result | 20 +- .../suite/innodb/r/log_file_size.result | 2 +- mysql-test/suite/innodb/t/log_corruption.test | 22 +- mysql-test/suite/innodb/t/log_file_size.test | 2 +- .../mariabackup/innodb_redo_log_overwrite.opt | 2 +- .../mariabackup/innodb_redo_overwrite.opt | 2 +- .../mariabackup/innodb_redo_overwrite.result | 3 +- .../mariabackup/innodb_redo_overwrite.test | 3 +- .../suite/perfschema/r/sxlock_func.result | 2 + .../suite/sys_vars/r/sysvars_innodb.result | 2 +- storage/innobase/buf/buf0flu.cc | 68 ++-- storage/innobase/fil/fil0fil.cc | 44 +-- storage/innobase/handler/ha_innodb.cc | 15 +- storage/innobase/include/buf0buf.h | 17 +- storage/innobase/include/buf0flu.h | 29 +- storage/innobase/include/fil0fil.h | 23 +- storage/innobase/include/log0log.h | 91 +++--- storage/innobase/include/log0recv.h | 6 +- storage/innobase/include/mtr0mtr.h | 8 +- storage/innobase/include/mtr0mtr.inl | 5 +- storage/innobase/include/srv0srv.h | 4 - storage/innobase/include/srw_lock.h | 11 +- storage/innobase/include/univ.i | 3 +- storage/innobase/log/log0log.cc | 126 +++----- storage/innobase/log/log0recv.cc | 66 ++-- storage/innobase/mtr/mtr0mtr.cc | 297 ++++++++++-------- storage/innobase/srv/srv0mon.cc | 7 +- storage/innobase/srv/srv0srv.cc | 11 +- storage/innobase/srv/srv0start.cc | 18 +- storage/innobase/sync/srw_lock.cc | 9 +- 32 files changed, 487 insertions(+), 512 deletions(-) diff --git a/extra/mariabackup/xtrabackup.cc b/extra/mariabackup/xtrabackup.cc index c32ba4cc1be..673ff3999cd 100644 --- a/extra/mariabackup/xtrabackup.cc +++ b/extra/mariabackup/xtrabackup.cc @@ -1582,9 +1582,8 @@ struct my_option xb_server_options[] = {"innodb_log_file_size", OPT_INNODB_LOG_FILE_SIZE, "Ignored for mysqld option compatibility", (G_PTR*) &srv_log_file_size, (G_PTR*) &srv_log_file_size, 0, - GET_ULL, REQUIRED_ARG, 48 << 20, 1 << 20, - std::numeric_limits::max(), 0, - UNIV_PAGE_SIZE_MAX, 0}, + GET_ULL, REQUIRED_ARG, 96 << 20, 4 << 20, + std::numeric_limits::max(), 0, 4096, 0}, {"innodb_log_group_home_dir", OPT_INNODB_LOG_GROUP_HOME_DIR, "Path to InnoDB log files.", &srv_log_group_home_dir, &srv_log_group_home_dir, 0, GET_STR, REQUIRED_ARG, 0, 0, 0, 0, 0, 0}, @@ -2540,10 +2539,10 @@ void xtrabackup_io_throttling() if (!xtrabackup_backup) return; - mysql_mutex_lock(&log_sys.mutex); + mysql_mutex_lock(&recv_sys.mutex); if (xtrabackup_throttle && (io_ticket--) < 0) - mysql_cond_wait(&wait_throttle, &log_sys.mutex); - mysql_mutex_unlock(&log_sys.mutex); + mysql_cond_wait(&wait_throttle, &recv_sys.mutex); + mysql_mutex_unlock(&recv_sys.mutex); } static @@ -2972,7 +2971,7 @@ skip: @return whether the operation failed */ static bool xtrabackup_copy_logfile() { - mysql_mutex_assert_owner(&log_sys.mutex); + mysql_mutex_assert_owner(&recv_sys.mutex); DBUG_EXECUTE_IF("log_checksum_mismatch", return false;); ut_a(dst_log_file); @@ -2980,7 +2979,6 @@ static bool xtrabackup_copy_logfile() const size_t sequence_offset{log_sys.is_encrypted() ? 8U + 5U : 5U}; const size_t block_size_1{log_sys.get_block_size() - 1}; - mysql_mutex_lock(&recv_sys.mutex); #ifdef HAVE_PMEM if (log_sys.is_pmem()) { @@ -3127,7 +3125,6 @@ static bool xtrabackup_copy_logfile() #ifdef HAVE_PMEM write_error: #endif - mysql_mutex_unlock(&recv_sys.mutex); msg("Error: write to ib_logfile0 failed"); return true; } @@ -3148,12 +3145,11 @@ static bool xtrabackup_copy_logfile() if (recv_sys.offset < log_sys.get_block_size()) break; - mysql_mutex_unlock(&recv_sys.mutex); - if (xtrabackup_throttle && io_ticket-- < 0) - mysql_cond_wait(&wait_throttle, &log_sys.mutex); + mysql_cond_wait(&wait_throttle, &recv_sys.mutex); retry_count= 0; + continue; } else { @@ -3173,7 +3169,6 @@ static bool xtrabackup_copy_logfile() mysql_mutex_lock(&recv_sys.mutex); } - mysql_mutex_unlock(&recv_sys.mutex); msg(">> log scanned up to (" LSN_PF ")", recv_sys.lsn); return false; } @@ -3204,16 +3199,16 @@ extern lsn_t server_lsn_after_lock; static void log_copying_thread() { my_thread_init(); - mysql_mutex_lock(&log_sys.mutex); + mysql_mutex_lock(&recv_sys.mutex); while (!xtrabackup_copy_logfile() && (!metadata_to_lsn || metadata_to_lsn > recv_sys.lsn)) { timespec abstime; set_timespec_nsec(abstime, 1000ULL * xtrabackup_log_copy_interval); - mysql_cond_timedwait(&log_copying_stop, &log_sys.mutex, &abstime); + mysql_cond_timedwait(&log_copying_stop, &recv_sys.mutex, &abstime); } log_copying_running= false; - mysql_mutex_unlock(&log_sys.mutex); + mysql_mutex_unlock(&recv_sys.mutex); my_thread_end(); } @@ -3226,13 +3221,13 @@ static void *io_watching_thread(void*) /* currently, for --backup only */ ut_a(xtrabackup_backup); - mysql_mutex_lock(&log_sys.mutex); + mysql_mutex_lock(&recv_sys.mutex); while (log_copying_running && !metadata_to_lsn) { timespec abstime; set_timespec(abstime, 1); - mysql_cond_timedwait(&log_copying_stop, &log_sys.mutex, &abstime); + mysql_cond_timedwait(&log_copying_stop, &recv_sys.mutex, &abstime); io_ticket= xtrabackup_throttle; mysql_cond_broadcast(&wait_throttle); } @@ -3240,7 +3235,7 @@ static void *io_watching_thread(void*) /* stop io throttle */ xtrabackup_throttle= 0; mysql_cond_broadcast(&wait_throttle); - mysql_mutex_unlock(&log_sys.mutex); + mysql_mutex_unlock(&recv_sys.mutex); return nullptr; } @@ -4512,7 +4507,7 @@ static void stop_backup_threads(bool running) @return whether the operation succeeded */ static bool xtrabackup_backup_low() { - mysql_mutex_lock(&log_sys.mutex); + mysql_mutex_lock(&recv_sys.mutex); ut_ad(!metadata_to_lsn); /* read the latest checkpoint lsn */ @@ -4531,19 +4526,19 @@ static bool xtrabackup_backup_low() recv_sys.lsn = lsn; mysql_cond_broadcast(&log_copying_stop); const bool running= log_copying_running; - mysql_mutex_unlock(&log_sys.mutex); + mysql_mutex_unlock(&recv_sys.mutex); stop_backup_threads(running); - mysql_mutex_lock(&log_sys.mutex); + mysql_mutex_lock(&recv_sys.mutex); } if (metadata_to_lsn && xtrabackup_copy_logfile()) { - mysql_mutex_unlock(&log_sys.mutex); + mysql_mutex_unlock(&recv_sys.mutex); ds_close(dst_log_file); dst_log_file = NULL; return false; } - mysql_mutex_unlock(&log_sys.mutex); + mysql_mutex_unlock(&recv_sys.mutex); if (ds_close(dst_log_file) || !metadata_to_lsn) { dst_log_file = NULL; @@ -4632,10 +4627,10 @@ static bool xtrabackup_backup_func() if(innodb_init_param()) { fail: if (log_copying_running) { - mysql_mutex_lock(&log_sys.mutex); + mysql_mutex_lock(&recv_sys.mutex); metadata_to_lsn = 1; mysql_cond_broadcast(&log_copying_stop); - mysql_mutex_unlock(&log_sys.mutex); + mysql_mutex_unlock(&recv_sys.mutex); stop_backup_threads(true); } @@ -4692,12 +4687,12 @@ fail: log_sys.create(); /* get current checkpoint_lsn */ - mysql_mutex_lock(&log_sys.mutex); + mysql_mutex_lock(&recv_sys.mutex); if (recv_sys.find_checkpoint() != DB_SUCCESS) { msg("Error: cannot read redo log header"); unlock_and_fail: - mysql_mutex_unlock(&log_sys.mutex); + mysql_mutex_unlock(&recv_sys.mutex); free_and_fail: aligned_free(const_cast(field_ref_zero)); field_ref_zero = nullptr; @@ -4710,7 +4705,7 @@ free_and_fail: } recv_needed_recovery = true; - mysql_mutex_unlock(&log_sys.mutex); + mysql_mutex_unlock(&recv_sys.mutex); /* create extra LSN dir if it does not exist. */ if (xtrabackup_extra_lsndir @@ -4772,12 +4767,12 @@ free_and_fail: /* copy log file by current position */ - mysql_mutex_lock(&log_sys.mutex); + mysql_mutex_lock(&recv_sys.mutex); recv_sys.lsn = log_sys.next_checkpoint_lsn; const bool log_copy_failed = xtrabackup_copy_logfile(); - mysql_mutex_unlock(&log_sys.mutex); + mysql_mutex_unlock(&recv_sys.mutex); if (log_copy_failed) { log_copying_running = false; @@ -5212,7 +5207,7 @@ xb_delta_open_matching_space( return OS_FILE_CLOSED; } - mysql_mutex_lock(&log_sys.mutex); + mysql_mutex_lock(&recv_sys.mutex); if (!fil_is_user_tablespace_id(info.space_id)) { found: /* open the file and return its handle */ @@ -5225,7 +5220,7 @@ found: msg("mariabackup: Cannot open file %s\n", real_name); } exit: - mysql_mutex_unlock(&log_sys.mutex); + mysql_mutex_unlock(&recv_sys.mutex); return file; } diff --git a/mysql-test/suite/encryption/r/innodb_encrypt_log_corruption.result b/mysql-test/suite/encryption/r/innodb_encrypt_log_corruption.result index c1771fe534b..3c3e4831d8a 100644 --- a/mysql-test/suite/encryption/r/innodb_encrypt_log_corruption.result +++ b/mysql-test/suite/encryption/r/innodb_encrypt_log_corruption.result @@ -20,7 +20,7 @@ AND support IN ('YES', 'DEFAULT', 'ENABLED'); ENGINE SUPPORT COMMENT TRANSACTIONS XA SAVEPOINTS FOUND 1 /InnoDB: Upgrade after a crash is not supported. This redo log was created before MariaDB 10\.2\.2, and we did not find a valid checkpoint/ in mysqld.1.err # empty redo log from before MariaDB 10.2.2 -# restart: --innodb-data-home-dir=MYSQLTEST_VARDIR/tmp/log_corruption --innodb-log-group-home-dir=MYSQLTEST_VARDIR/tmp/log_corruption --innodb-force-recovery=5 --innodb-log-file-size=2m +# restart: --innodb-data-home-dir=MYSQLTEST_VARDIR/tmp/log_corruption --innodb-log-group-home-dir=MYSQLTEST_VARDIR/tmp/log_corruption --innodb-force-recovery=5 --innodb-log-file-size=4m SELECT COUNT(*) FROM INFORMATION_SCHEMA.ENGINES WHERE engine = 'innodb' AND support IN ('YES', 'DEFAULT', 'ENABLED'); @@ -28,7 +28,7 @@ COUNT(*) 1 FOUND 1 /InnoDB: Upgrading redo log:/ in mysqld.1.err # Corrupted multi-file redo log from before MariaDB 10.2.2 -# restart: --innodb-data-home-dir=MYSQLTEST_VARDIR/tmp/log_corruption --innodb-log-group-home-dir=MYSQLTEST_VARDIR/tmp/log_corruption --innodb-force-recovery=5 --innodb-log-file-size=2m +# restart: --innodb-data-home-dir=MYSQLTEST_VARDIR/tmp/log_corruption --innodb-log-group-home-dir=MYSQLTEST_VARDIR/tmp/log_corruption --innodb-force-recovery=5 --innodb-log-file-size=4m SELECT COUNT(*) FROM INFORMATION_SCHEMA.ENGINES WHERE engine = 'innodb' AND support IN ('YES', 'DEFAULT', 'ENABLED'); @@ -36,7 +36,7 @@ COUNT(*) 0 FOUND 1 /InnoDB: Upgrade after a crash is not supported. This redo log was created before MariaDB 10\.2\.2, and it appears corrupted/ in mysqld.1.err # Empty multi-file redo log (wrong offset) from before MariaDB 10.2.2 -# restart: --innodb-data-home-dir=MYSQLTEST_VARDIR/tmp/log_corruption --innodb-log-group-home-dir=MYSQLTEST_VARDIR/tmp/log_corruption --innodb-force-recovery=5 --innodb-log-file-size=2m +# restart: --innodb-data-home-dir=MYSQLTEST_VARDIR/tmp/log_corruption --innodb-log-group-home-dir=MYSQLTEST_VARDIR/tmp/log_corruption --innodb-force-recovery=5 --innodb-log-file-size=4m SELECT COUNT(*) FROM INFORMATION_SCHEMA.ENGINES WHERE engine = 'innodb' AND support IN ('YES', 'DEFAULT', 'ENABLED'); @@ -45,7 +45,7 @@ COUNT(*) FOUND 3 /Upgrade after a crash is not supported. This redo log was created before MariaDB 10\.2\.2, and we did not find a valid checkpoint\./ in mysqld.1.err # Multi-file redo log with size mismatch from after MariaDB 10.2.2 # Corrupted multi-file redo log from after MariaDB 10.2.2 -# restart: --innodb-data-home-dir=MYSQLTEST_VARDIR/tmp/log_corruption --innodb-log-group-home-dir=MYSQLTEST_VARDIR/tmp/log_corruption --innodb-force-recovery=5 --innodb-log-file-size=2m +# restart: --innodb-data-home-dir=MYSQLTEST_VARDIR/tmp/log_corruption --innodb-log-group-home-dir=MYSQLTEST_VARDIR/tmp/log_corruption --innodb-force-recovery=5 --innodb-log-file-size=4m SELECT COUNT(*) FROM INFORMATION_SCHEMA.ENGINES WHERE engine = 'innodb' AND support IN ('YES', 'DEFAULT', 'ENABLED'); @@ -53,15 +53,16 @@ COUNT(*) 0 FOUND 3 /Upgrade after a crash is not supported. This redo log was created before MariaDB 10\.2\.2, and we did not find a valid checkpoint\./ in mysqld.1.err FOUND 1 /InnoDB: No valid checkpoint was found; the log was created with BogoDB 1\.2\.3\.4\./ in mysqld.1.err -# restart: --innodb-data-home-dir=MYSQLTEST_VARDIR/tmp/log_corruption --innodb-log-group-home-dir=MYSQLTEST_VARDIR/tmp/log_corruption --innodb-force-recovery=5 --innodb-log-file-size=2m +# restart: --innodb-data-home-dir=MYSQLTEST_VARDIR/tmp/log_corruption --innodb-log-group-home-dir=MYSQLTEST_VARDIR/tmp/log_corruption --innodb-force-recovery=5 --innodb-log-file-size=4m SELECT COUNT(*) FROM INFORMATION_SCHEMA.ENGINES WHERE engine = 'innodb' AND support IN ('YES', 'DEFAULT', 'ENABLED'); COUNT(*) 0 +FOUND 1 /InnoDB: Log file .*ib_logfile1 is of different size 2097152 bytes than other log files 1048576 bytes!/ in mysqld.1.err FOUND 2 /InnoDB: No valid checkpoint was found; the log was created with BogoDB 1\.2\.3\.4\./ in mysqld.1.err # Empty multi-file redo log from after MariaDB 10.2.2 -# restart: --innodb-data-home-dir=MYSQLTEST_VARDIR/tmp/log_corruption --innodb-log-group-home-dir=MYSQLTEST_VARDIR/tmp/log_corruption --innodb-force-recovery=5 --innodb-log-file-size=2m +# restart: --innodb-data-home-dir=MYSQLTEST_VARDIR/tmp/log_corruption --innodb-log-group-home-dir=MYSQLTEST_VARDIR/tmp/log_corruption --innodb-force-recovery=5 --innodb-log-file-size=4m SELECT COUNT(*) FROM INFORMATION_SCHEMA.ENGINES WHERE engine = 'innodb' AND support IN ('YES', 'DEFAULT', 'ENABLED'); @@ -74,6 +75,7 @@ SELECT * FROM INFORMATION_SCHEMA.ENGINES WHERE engine = 'innodb' AND support IN ('YES', 'DEFAULT', 'ENABLED'); ENGINE SUPPORT COMMENT TRANSACTIONS XA SAVEPOINTS +FOUND 1 /InnoDB: Log file .*ib_logfile1 is of different size 2097152 bytes than other log files 4194304 bytes!/ in mysqld.1.err FOUND 1 /InnoDB: Invalid log header checksum/ in mysqld.1.err # distant future redo log format, with valid header checksum # restart: --innodb-data-home-dir=MYSQLTEST_VARDIR/tmp/log_corruption --innodb-log-group-home-dir=MYSQLTEST_VARDIR/tmp/log_corruption @@ -165,7 +167,7 @@ AND support IN ('YES', 'DEFAULT', 'ENABLED'); ENGINE SUPPORT COMMENT TRANSACTIONS XA SAVEPOINTS FOUND 3 /\[ERROR\] InnoDB: Upgrade after a crash is not supported\. The redo log was created with MariaDB 10\.3\.1\./ in mysqld.1.err # Empty 10.3 redo log -# restart: --innodb-data-home-dir=MYSQLTEST_VARDIR/tmp/log_corruption --innodb-log-group-home-dir=MYSQLTEST_VARDIR/tmp/log_corruption --innodb-force-recovery=5 --innodb-log-file-size=2m +# restart: --innodb-data-home-dir=MYSQLTEST_VARDIR/tmp/log_corruption --innodb-log-group-home-dir=MYSQLTEST_VARDIR/tmp/log_corruption --innodb-force-recovery=5 --innodb-log-file-size=4m SELECT COUNT(*) FROM INFORMATION_SCHEMA.ENGINES WHERE engine = 'innodb' AND support IN ('YES', 'DEFAULT', 'ENABLED'); @@ -173,7 +175,7 @@ COUNT(*) 1 FOUND 1 /InnoDB: log sequence number 1213964\b.*; transaction id 0/ in mysqld.1.err # Empty 10.2 redo log -# restart: --innodb-data-home-dir=MYSQLTEST_VARDIR/tmp/log_corruption --innodb-log-group-home-dir=MYSQLTEST_VARDIR/tmp/log_corruption --innodb-force-recovery=5 --innodb-log-file-size=2m +# restart: --innodb-data-home-dir=MYSQLTEST_VARDIR/tmp/log_corruption --innodb-log-group-home-dir=MYSQLTEST_VARDIR/tmp/log_corruption --innodb-force-recovery=5 --innodb-log-file-size=4m SELECT COUNT(*) FROM INFORMATION_SCHEMA.ENGINES WHERE engine = 'innodb' AND support IN ('YES', 'DEFAULT', 'ENABLED'); @@ -181,7 +183,7 @@ COUNT(*) 1 FOUND 3 /InnoDB: Upgrading redo log:/ in mysqld.1.err # Empty 10.5 redo log -# restart: --innodb-data-home-dir=MYSQLTEST_VARDIR/tmp/log_corruption --innodb-log-group-home-dir=MYSQLTEST_VARDIR/tmp/log_corruption --innodb-force-recovery=5 --innodb-log-file-size=2m +# restart: --innodb-data-home-dir=MYSQLTEST_VARDIR/tmp/log_corruption --innodb-log-group-home-dir=MYSQLTEST_VARDIR/tmp/log_corruption --innodb-force-recovery=5 --innodb-log-file-size=4m SELECT COUNT(*) FROM INFORMATION_SCHEMA.ENGINES WHERE engine = 'innodb' AND support IN ('YES', 'DEFAULT', 'ENABLED'); diff --git a/mysql-test/suite/innodb/r/log_corruption.result b/mysql-test/suite/innodb/r/log_corruption.result index 12e9d340bbd..df58a90dcec 100644 --- a/mysql-test/suite/innodb/r/log_corruption.result +++ b/mysql-test/suite/innodb/r/log_corruption.result @@ -20,7 +20,7 @@ AND support IN ('YES', 'DEFAULT', 'ENABLED'); ENGINE SUPPORT COMMENT TRANSACTIONS XA SAVEPOINTS FOUND 1 /InnoDB: Upgrade after a crash is not supported. This redo log was created before MariaDB 10\.2\.2, and we did not find a valid checkpoint/ in mysqld.1.err # empty redo log from before MariaDB 10.2.2 -# restart: --innodb-data-home-dir=MYSQLTEST_VARDIR/tmp/log_corruption --innodb-log-group-home-dir=MYSQLTEST_VARDIR/tmp/log_corruption --innodb-force-recovery=5 --innodb-log-file-size=2m +# restart: --innodb-data-home-dir=MYSQLTEST_VARDIR/tmp/log_corruption --innodb-log-group-home-dir=MYSQLTEST_VARDIR/tmp/log_corruption --innodb-force-recovery=5 --innodb-log-file-size=4m SELECT COUNT(*) FROM INFORMATION_SCHEMA.ENGINES WHERE engine = 'innodb' AND support IN ('YES', 'DEFAULT', 'ENABLED'); @@ -28,7 +28,7 @@ COUNT(*) 1 FOUND 1 /InnoDB: Upgrading redo log:/ in mysqld.1.err # Corrupted multi-file redo log from before MariaDB 10.2.2 -# restart: --innodb-data-home-dir=MYSQLTEST_VARDIR/tmp/log_corruption --innodb-log-group-home-dir=MYSQLTEST_VARDIR/tmp/log_corruption --innodb-force-recovery=5 --innodb-log-file-size=2m +# restart: --innodb-data-home-dir=MYSQLTEST_VARDIR/tmp/log_corruption --innodb-log-group-home-dir=MYSQLTEST_VARDIR/tmp/log_corruption --innodb-force-recovery=5 --innodb-log-file-size=4m SELECT COUNT(*) FROM INFORMATION_SCHEMA.ENGINES WHERE engine = 'innodb' AND support IN ('YES', 'DEFAULT', 'ENABLED'); @@ -36,7 +36,7 @@ COUNT(*) 0 FOUND 1 /InnoDB: Upgrade after a crash is not supported. This redo log was created before MariaDB 10\.2\.2, and it appears corrupted/ in mysqld.1.err # Empty multi-file redo log (wrong offset) from before MariaDB 10.2.2 -# restart: --innodb-data-home-dir=MYSQLTEST_VARDIR/tmp/log_corruption --innodb-log-group-home-dir=MYSQLTEST_VARDIR/tmp/log_corruption --innodb-force-recovery=5 --innodb-log-file-size=2m +# restart: --innodb-data-home-dir=MYSQLTEST_VARDIR/tmp/log_corruption --innodb-log-group-home-dir=MYSQLTEST_VARDIR/tmp/log_corruption --innodb-force-recovery=5 --innodb-log-file-size=4m SELECT COUNT(*) FROM INFORMATION_SCHEMA.ENGINES WHERE engine = 'innodb' AND support IN ('YES', 'DEFAULT', 'ENABLED'); @@ -45,7 +45,7 @@ COUNT(*) FOUND 3 /Upgrade after a crash is not supported. This redo log was created before MariaDB 10\.2\.2, and we did not find a valid checkpoint\./ in mysqld.1.err # Multi-file redo log with size mismatch from after MariaDB 10.2.2 # Corrupted multi-file redo log from after MariaDB 10.2.2 -# restart: --innodb-data-home-dir=MYSQLTEST_VARDIR/tmp/log_corruption --innodb-log-group-home-dir=MYSQLTEST_VARDIR/tmp/log_corruption --innodb-force-recovery=5 --innodb-log-file-size=2m +# restart: --innodb-data-home-dir=MYSQLTEST_VARDIR/tmp/log_corruption --innodb-log-group-home-dir=MYSQLTEST_VARDIR/tmp/log_corruption --innodb-force-recovery=5 --innodb-log-file-size=4m SELECT COUNT(*) FROM INFORMATION_SCHEMA.ENGINES WHERE engine = 'innodb' AND support IN ('YES', 'DEFAULT', 'ENABLED'); @@ -53,15 +53,16 @@ COUNT(*) 0 FOUND 3 /Upgrade after a crash is not supported. This redo log was created before MariaDB 10\.2\.2, and we did not find a valid checkpoint\./ in mysqld.1.err FOUND 1 /InnoDB: No valid checkpoint was found; the log was created with BogoDB 1\.2\.3\.4\./ in mysqld.1.err -# restart: --innodb-data-home-dir=MYSQLTEST_VARDIR/tmp/log_corruption --innodb-log-group-home-dir=MYSQLTEST_VARDIR/tmp/log_corruption --innodb-force-recovery=5 --innodb-log-file-size=2m +# restart: --innodb-data-home-dir=MYSQLTEST_VARDIR/tmp/log_corruption --innodb-log-group-home-dir=MYSQLTEST_VARDIR/tmp/log_corruption --innodb-force-recovery=5 --innodb-log-file-size=4m SELECT COUNT(*) FROM INFORMATION_SCHEMA.ENGINES WHERE engine = 'innodb' AND support IN ('YES', 'DEFAULT', 'ENABLED'); COUNT(*) 0 +FOUND 1 /InnoDB: Log file .*ib_logfile1 is of different size 2097152 bytes than other log files 1048576 bytes!/ in mysqld.1.err FOUND 2 /InnoDB: No valid checkpoint was found; the log was created with BogoDB 1\.2\.3\.4\./ in mysqld.1.err # Empty multi-file redo log from after MariaDB 10.2.2 -# restart: --innodb-data-home-dir=MYSQLTEST_VARDIR/tmp/log_corruption --innodb-log-group-home-dir=MYSQLTEST_VARDIR/tmp/log_corruption --innodb-force-recovery=5 --innodb-log-file-size=2m +# restart: --innodb-data-home-dir=MYSQLTEST_VARDIR/tmp/log_corruption --innodb-log-group-home-dir=MYSQLTEST_VARDIR/tmp/log_corruption --innodb-force-recovery=5 --innodb-log-file-size=4m SELECT COUNT(*) FROM INFORMATION_SCHEMA.ENGINES WHERE engine = 'innodb' AND support IN ('YES', 'DEFAULT', 'ENABLED'); @@ -74,6 +75,7 @@ SELECT * FROM INFORMATION_SCHEMA.ENGINES WHERE engine = 'innodb' AND support IN ('YES', 'DEFAULT', 'ENABLED'); ENGINE SUPPORT COMMENT TRANSACTIONS XA SAVEPOINTS +FOUND 1 /InnoDB: Log file .*ib_logfile1 is of different size 2097152 bytes than other log files 4194304 bytes!/ in mysqld.1.err FOUND 1 /InnoDB: Invalid log header checksum/ in mysqld.1.err # distant future redo log format, with valid header checksum # restart: --innodb-data-home-dir=MYSQLTEST_VARDIR/tmp/log_corruption --innodb-log-group-home-dir=MYSQLTEST_VARDIR/tmp/log_corruption @@ -165,7 +167,7 @@ AND support IN ('YES', 'DEFAULT', 'ENABLED'); ENGINE SUPPORT COMMENT TRANSACTIONS XA SAVEPOINTS FOUND 3 /\[ERROR\] InnoDB: Upgrade after a crash is not supported\. The redo log was created with MariaDB 10\.3\.1\./ in mysqld.1.err # Empty 10.3 redo log -# restart: --innodb-data-home-dir=MYSQLTEST_VARDIR/tmp/log_corruption --innodb-log-group-home-dir=MYSQLTEST_VARDIR/tmp/log_corruption --innodb-force-recovery=5 --innodb-log-file-size=2m +# restart: --innodb-data-home-dir=MYSQLTEST_VARDIR/tmp/log_corruption --innodb-log-group-home-dir=MYSQLTEST_VARDIR/tmp/log_corruption --innodb-force-recovery=5 --innodb-log-file-size=4m SELECT COUNT(*) FROM INFORMATION_SCHEMA.ENGINES WHERE engine = 'innodb' AND support IN ('YES', 'DEFAULT', 'ENABLED'); @@ -173,7 +175,7 @@ COUNT(*) 1 FOUND 1 /InnoDB: log sequence number 1213964\b.*; transaction id 0/ in mysqld.1.err # Empty 10.2 redo log -# restart: --innodb-data-home-dir=MYSQLTEST_VARDIR/tmp/log_corruption --innodb-log-group-home-dir=MYSQLTEST_VARDIR/tmp/log_corruption --innodb-force-recovery=5 --innodb-log-file-size=2m +# restart: --innodb-data-home-dir=MYSQLTEST_VARDIR/tmp/log_corruption --innodb-log-group-home-dir=MYSQLTEST_VARDIR/tmp/log_corruption --innodb-force-recovery=5 --innodb-log-file-size=4m SELECT COUNT(*) FROM INFORMATION_SCHEMA.ENGINES WHERE engine = 'innodb' AND support IN ('YES', 'DEFAULT', 'ENABLED'); @@ -181,7 +183,7 @@ COUNT(*) 1 FOUND 3 /InnoDB: Upgrading redo log:/ in mysqld.1.err # Empty 10.5 redo log -# restart: --innodb-data-home-dir=MYSQLTEST_VARDIR/tmp/log_corruption --innodb-log-group-home-dir=MYSQLTEST_VARDIR/tmp/log_corruption --innodb-force-recovery=5 --innodb-log-file-size=2m +# restart: --innodb-data-home-dir=MYSQLTEST_VARDIR/tmp/log_corruption --innodb-log-group-home-dir=MYSQLTEST_VARDIR/tmp/log_corruption --innodb-force-recovery=5 --innodb-log-file-size=4m SELECT COUNT(*) FROM INFORMATION_SCHEMA.ENGINES WHERE engine = 'innodb' AND support IN ('YES', 'DEFAULT', 'ENABLED'); diff --git a/mysql-test/suite/innodb/r/log_file_size.result b/mysql-test/suite/innodb/r/log_file_size.result index 47ca20af2f4..7b4935e1ab1 100644 --- a/mysql-test/suite/innodb/r/log_file_size.result +++ b/mysql-test/suite/innodb/r/log_file_size.result @@ -1,5 +1,5 @@ CREATE TABLE t1(a INT PRIMARY KEY) ENGINE=InnoDB; -# restart: --innodb-log-file-size=2m +# restart: --innodb-log-file-size=4m CHECK TABLE t1; Table Op Msg_type Msg_text test.t1 check status OK diff --git a/mysql-test/suite/innodb/t/log_corruption.test b/mysql-test/suite/innodb/t/log_corruption.test index dad5f67afca..7d351bf565c 100644 --- a/mysql-test/suite/innodb/t/log_corruption.test +++ b/mysql-test/suite/innodb/t/log_corruption.test @@ -16,7 +16,7 @@ call mtr.add_suppression("InnoDB: Log scan aborted at LSN"); call mtr.add_suppression("InnoDB: Missing MLOG_FILE_NAME or MLOG_FILE_DELETE before MLOG_CHECKPOINT for tablespace 42\\r?$"); call mtr.add_suppression("InnoDB: Obtaining redo log encryption key version 1 failed"); call mtr.add_suppression("InnoDB: Decrypting checkpoint failed"); -call mtr.add_suppression("InnoDB: Log file .*ib_logfile1 is of different size 2097152 bytes than other log files 1048576 bytes!"); +call mtr.add_suppression("InnoDB: Log file .*ib_logfile1 is of different size 2097152 bytes than other log files (1048576|4194304) bytes!"); --enable_query_log let bugdir= $MYSQLTEST_VARDIR/tmp/log_corruption; @@ -161,7 +161,7 @@ die unless seek(OUT, 0x800, 0); print OUT pack("NnnNx[496]N", 0x80000944, 12, 12, 0, 0xb2a); close OUT or die; EOF ---let $restart_parameters= $dirs --innodb-force-recovery=5 --innodb-log-file-size=2m +--let $restart_parameters= $dirs --innodb-force-recovery=5 --innodb-log-file-size=4m --source include/start_mysqld.inc SELECT COUNT(*) FROM INFORMATION_SCHEMA.ENGINES WHERE engine = 'innodb' @@ -191,7 +191,7 @@ print OUT chr(0) x 2048; close OUT or die; EOF ---let $restart_parameters= $dirs --innodb-force-recovery=5 --innodb-log-file-size=2m +--let $restart_parameters= $dirs --innodb-force-recovery=5 --innodb-log-file-size=4m --source include/start_mysqld.inc SELECT COUNT(*) FROM INFORMATION_SCHEMA.ENGINES WHERE engine = 'innodb' @@ -210,7 +210,7 @@ print OUT chr(0) x 1536; close OUT or die; EOF ---let $restart_parameters= $dirs --innodb-force-recovery=5 --innodb-log-file-size=2m +--let $restart_parameters= $dirs --innodb-force-recovery=5 --innodb-log-file-size=4m --source include/start_mysqld.inc SELECT COUNT(*) FROM INFORMATION_SCHEMA.ENGINES WHERE engine = 'innodb' @@ -241,7 +241,7 @@ close OUT or die; EOF --echo # Corrupted multi-file redo log from after MariaDB 10.2.2 ---let $restart_parameters= $dirs --innodb-force-recovery=5 --innodb-log-file-size=2m +--let $restart_parameters= $dirs --innodb-force-recovery=5 --innodb-log-file-size=4m --source include/start_mysqld.inc SELECT COUNT(*) FROM INFORMATION_SCHEMA.ENGINES WHERE engine = 'innodb' @@ -259,13 +259,14 @@ print OUT chr(0); close OUT or die; EOF ---let $restart_parameters= $dirs --innodb-force-recovery=5 --innodb-log-file-size=2m +--let $restart_parameters= $dirs --innodb-force-recovery=5 --innodb-log-file-size=4m --source include/start_mysqld.inc SELECT COUNT(*) FROM INFORMATION_SCHEMA.ENGINES WHERE engine = 'innodb' AND support IN ('YES', 'DEFAULT', 'ENABLED'); --source include/shutdown_mysqld.inc --let SEARCH_PATTERN=InnoDB: Log file .*ib_logfile1 is of different size 2097152 bytes than other log files 1048576 bytes! +--source include/search_pattern_in_file.inc --let SEARCH_PATTERN=InnoDB: No valid checkpoint was found; the log was created with BogoDB 1\\.2\\.3\\.4\\. --source include/search_pattern_in_file.inc @@ -282,7 +283,7 @@ print OUT $_, pack("N", mycrc32($_, 0, $polynomial)); close OUT or die; EOF ---let $restart_parameters= $dirs --innodb-force-recovery=5 --innodb-log-file-size=2m +--let $restart_parameters= $dirs --innodb-force-recovery=5 --innodb-log-file-size=4m --source include/start_mysqld.inc SELECT COUNT(*) FROM INFORMATION_SCHEMA.ENGINES WHERE engine = 'innodb' @@ -304,6 +305,8 @@ EOF --source include/start_mysqld.inc eval $check_no_innodb; --source include/shutdown_mysqld.inc +--let SEARCH_PATTERN=InnoDB: Log file .*ib_logfile1 is of different size 2097152 bytes than other log files 4194304 bytes! +--source include/search_pattern_in_file.inc let SEARCH_PATTERN=InnoDB: Invalid log header checksum; --source include/search_pattern_in_file.inc @@ -351,6 +354,9 @@ die unless seek(OUT, 0x210, 0); print OUT pack("NNx[264]", 0, 0x80c); print OUT pack("NNx[212]N", 0x590dbaac, 0xfe922582, 0xc72d49c4); close OUT or die; +die unless open OUT, ">", "$ENV{bugdir}/ib_logfile1"; +print OUT pack("x[4194304]"); +close OUT or die; EOF # Anything below innodb_force_recovery=6 must find a valid redo log. # Missing tablespace files are tolerated already with innodb_force_recovery=1. @@ -533,7 +539,7 @@ print OUT pack("NnnNx[496]N", 0x80000944, 12, 12, 1, 0x46c8a2a2); close OUT or die; EOF ---let $restart_parameters= $dirs --innodb-force-recovery=5 --innodb-log-file-size=2m +--let $restart_parameters= $dirs --innodb-force-recovery=5 --innodb-log-file-size=4m --source include/start_mysqld.inc SELECT COUNT(*) FROM INFORMATION_SCHEMA.ENGINES WHERE engine = 'innodb' diff --git a/mysql-test/suite/innodb/t/log_file_size.test b/mysql-test/suite/innodb/t/log_file_size.test index 22838475c60..261b024fa41 100644 --- a/mysql-test/suite/innodb/t/log_file_size.test +++ b/mysql-test/suite/innodb/t/log_file_size.test @@ -55,7 +55,7 @@ let $check_no_innodb=SELECT * FROM INFORMATION_SCHEMA.ENGINES WHERE engine = 'innodb' AND support IN ('YES', 'DEFAULT', 'ENABLED'); ---let $restart_parameters= --innodb-log-file-size=2m +--let $restart_parameters= --innodb-log-file-size=4m --source include/start_mysqld.inc let SEARCH_FILE= $MYSQLTEST_VARDIR/log/mysqld.1.err; diff --git a/mysql-test/suite/mariabackup/innodb_redo_log_overwrite.opt b/mysql-test/suite/mariabackup/innodb_redo_log_overwrite.opt index 95b88d038ee..a0b4b588279 100644 --- a/mysql-test/suite/mariabackup/innodb_redo_log_overwrite.opt +++ b/mysql-test/suite/mariabackup/innodb_redo_log_overwrite.opt @@ -1 +1 @@ ---loose-innodb-log-file-size=2097152 +--loose-innodb-log-file-size=4194304 diff --git a/mysql-test/suite/mariabackup/innodb_redo_overwrite.opt b/mysql-test/suite/mariabackup/innodb_redo_overwrite.opt index 19c08c8c945..a0b4b588279 100644 --- a/mysql-test/suite/mariabackup/innodb_redo_overwrite.opt +++ b/mysql-test/suite/mariabackup/innodb_redo_overwrite.opt @@ -1 +1 @@ ---loose-innodb-log-file-size=2m +--loose-innodb-log-file-size=4194304 diff --git a/mysql-test/suite/mariabackup/innodb_redo_overwrite.result b/mysql-test/suite/mariabackup/innodb_redo_overwrite.result index abc0c57bcce..bab5d4331e0 100644 --- a/mysql-test/suite/mariabackup/innodb_redo_overwrite.result +++ b/mysql-test/suite/mariabackup/innodb_redo_overwrite.result @@ -1,5 +1,4 @@ -CREATE TABLE t(i INT) ENGINE=INNODB; -INSERT INTO t SELECT seq%10 FROM seq_0_to_51199; +CREATE TABLE t ENGINE=INNODB SELECT seq%10 i FROM seq_0_to_204796; # xtrabackup backup FOUND 1 /Was only able to copy log from \d+ to \d+, not \d+; try increasing innodb_log_file_size\b/ in backup.log NOT FOUND /failed: redo log block checksum does not match/ in backup.log diff --git a/mysql-test/suite/mariabackup/innodb_redo_overwrite.test b/mysql-test/suite/mariabackup/innodb_redo_overwrite.test index 7e0c1cef54f..34198222cea 100644 --- a/mysql-test/suite/mariabackup/innodb_redo_overwrite.test +++ b/mysql-test/suite/mariabackup/innodb_redo_overwrite.test @@ -3,8 +3,7 @@ --source include/have_debug.inc --source include/have_sequence.inc -CREATE TABLE t(i INT) ENGINE=INNODB; -INSERT INTO t SELECT seq%10 FROM seq_0_to_51199; +CREATE TABLE t ENGINE=INNODB SELECT seq%10 i FROM seq_0_to_204796; --echo # xtrabackup backup --let $targetdir=$MYSQLTEST_VARDIR/tmp/backup diff --git a/mysql-test/suite/perfschema/r/sxlock_func.result b/mysql-test/suite/perfschema/r/sxlock_func.result index 8f4c2fdcece..56a3a3f37b3 100644 --- a/mysql-test/suite/perfschema/r/sxlock_func.result +++ b/mysql-test/suite/perfschema/r/sxlock_func.result @@ -10,6 +10,7 @@ name wait/synch/rwlock/innodb/dict_operation_lock wait/synch/rwlock/innodb/fil_space_latch wait/synch/rwlock/innodb/lock_latch +wait/synch/rwlock/innodb/log_latch wait/synch/rwlock/innodb/trx_i_s_cache_lock wait/synch/rwlock/innodb/trx_purge_latch TRUNCATE TABLE performance_schema.events_waits_history_long; @@ -41,6 +42,7 @@ ORDER BY event_name; event_name wait/synch/rwlock/innodb/fil_space_latch wait/synch/rwlock/innodb/lock_latch +wait/synch/rwlock/innodb/log_latch SELECT event_name FROM performance_schema.events_waits_history_long WHERE event_name = 'wait/synch/sxlock/innodb/index_tree_rw_lock' AND operation IN ('try_shared_lock','shared_lock') LIMIT 1; diff --git a/mysql-test/suite/sys_vars/r/sysvars_innodb.result b/mysql-test/suite/sys_vars/r/sysvars_innodb.result index 40702bca323..69986f31882 100644 --- a/mysql-test/suite/sys_vars/r/sysvars_innodb.result +++ b/mysql-test/suite/sys_vars/r/sysvars_innodb.result @@ -1011,7 +1011,7 @@ DEFAULT_VALUE 100663296 VARIABLE_SCOPE GLOBAL VARIABLE_TYPE BIGINT UNSIGNED VARIABLE_COMMENT Redo log size in bytes. -NUMERIC_MIN_VALUE 1048576 +NUMERIC_MIN_VALUE 4194304 NUMERIC_MAX_VALUE 18446744073709551615 NUMERIC_BLOCK_SIZE 4096 ENUM_VALUE_LIST NULL diff --git a/storage/innobase/buf/buf0flu.cc b/storage/innobase/buf/buf0flu.cc index 0ca0ab56052..220997758e9 100644 --- a/storage/innobase/buf/buf0flu.cc +++ b/storage/innobase/buf/buf0flu.cc @@ -115,6 +115,7 @@ static void buf_flush_validate_skip() /** Wake up the page cleaner if needed */ void buf_pool_t::page_cleaner_wakeup() { + ut_d(buf_flush_validate_skip()); if (!page_cleaner_idle()) return; double dirty_pct= double(UT_LIST_GET_LEN(buf_pool.flush_list)) * 100.0 / @@ -155,7 +156,7 @@ void buf_pool_t::page_cleaner_wakeup() } } -inline void buf_pool_t::delete_from_flush_list_low(buf_page_t *bpage) +inline void buf_pool_t::delete_from_flush_list_low(buf_page_t *bpage) noexcept { ut_ad(!fsp_is_system_temporary(bpage->id().space())); mysql_mutex_assert_owner(&flush_list_mutex); @@ -166,13 +167,9 @@ inline void buf_pool_t::delete_from_flush_list_low(buf_page_t *bpage) /** Insert a modified block into the flush list. @param block modified block @param lsn start LSN of the mini-transaction that modified the block */ -void buf_pool_t::insert_into_flush_list(buf_block_t *block, lsn_t lsn) +void buf_pool_t::insert_into_flush_list(buf_block_t *block, lsn_t lsn) noexcept { - mysql_mutex_assert_not_owner(&mutex); -#ifdef SAFE_MUTEX - if (!recv_recovery_is_on()) - mysql_mutex_assert_owner(&log_sys.flush_order_mutex); -#endif /* SAFE_MUTEX */ + ut_ad(recv_recovery_is_on() || log_sys.latch.is_locked()); ut_ad(lsn > 2); static_assert(log_t::FIRST_LSN >= 2, "compatibility"); ut_ad(!fsp_is_system_temporary(block->page.id().space())); @@ -191,16 +188,27 @@ void buf_pool_t::insert_into_flush_list(buf_block_t *block, lsn_t lsn) MEM_CHECK_DEFINED(block->page.zip.data ? block->page.zip.data : block->page.frame, block->physical_size()); - UT_LIST_ADD_FIRST(flush_list, &block->page); - ut_d(buf_flush_validate_skip()); - page_cleaner_wakeup(); + if (buf_page_t *prev= UT_LIST_GET_FIRST(flush_list)) + { + if (prev->oldest_modification() <= lsn) + goto insert_first; + while (buf_page_t *next= UT_LIST_GET_NEXT(list, prev)) + if (next->oldest_modification() <= lsn) + break; + else + prev= next; + UT_LIST_INSERT_AFTER(flush_list, prev, &block->page); + } + else + insert_first: + UT_LIST_ADD_FIRST(flush_list, &block->page); mysql_mutex_unlock(&flush_list_mutex); } /** Remove a block from flush_list. @param bpage buffer pool page @param clear whether to invoke buf_page_t::clear_oldest_modification() */ -void buf_pool_t::delete_from_flush_list(buf_page_t *bpage, bool clear) +void buf_pool_t::delete_from_flush_list(buf_page_t *bpage, bool clear) noexcept { delete_from_flush_list_low(bpage); stat.flush_list_bytes-= bpage->physical_size(); @@ -743,7 +751,7 @@ not_compressed: } /** Free a page whose underlying file page has been freed. */ -inline void buf_pool_t::release_freed_page(buf_page_t *bpage) +inline void buf_pool_t::release_freed_page(buf_page_t *bpage) noexcept { mysql_mutex_assert_owner(&mutex); mysql_mutex_lock(&flush_list_mutex); @@ -1696,12 +1704,12 @@ inline void log_t::write_checkpoint(lsn_t end_lsn) noexcept #endif { n_pending_checkpoint_writes++; - mysql_mutex_unlock(&mutex); + latch.wr_unlock(); /* FIXME: issue an asynchronous write */ log.write(offset, {c, get_block_size()}); if (srv_file_flush_method != SRV_O_DSYNC) ut_a(log.flush()); - mysql_mutex_lock(&mutex); + latch.wr_lock(SRW_LOCK_CALL); n_pending_checkpoint_writes--; } @@ -1712,7 +1720,7 @@ inline void log_t::write_checkpoint(lsn_t end_lsn) noexcept DBUG_PRINT("ib_log", ("checkpoint ended at " LSN_PF ", flushed to " LSN_PF, next_checkpoint_lsn, get_flushed_lsn())); - mysql_mutex_unlock(&mutex); + latch.wr_unlock(); } /** Initiate a log checkpoint, discarding the start of the log. @@ -1722,7 +1730,7 @@ inline void log_t::write_checkpoint(lsn_t end_lsn) noexcept static bool log_checkpoint_low(lsn_t oldest_lsn, lsn_t end_lsn) { ut_ad(!srv_read_only_mode); - mysql_mutex_assert_owner(&log_sys.mutex); + ut_ad(log_sys.latch.is_write_locked()); ut_ad(oldest_lsn <= end_lsn); ut_ad(end_lsn == log_sys.get_lsn()); ut_ad(!recv_no_log_write); @@ -1735,7 +1743,7 @@ static bool log_checkpoint_low(lsn_t oldest_lsn, lsn_t end_lsn) /* Do nothing, because nothing was logged (other than a FILE_CHECKPOINT record) since the previous checkpoint. */ do_nothing: - mysql_mutex_unlock(&log_sys.mutex); + log_sys.latch.wr_unlock(); return true; } @@ -1748,13 +1756,14 @@ static bool log_checkpoint_low(lsn_t oldest_lsn, lsn_t end_lsn) It is important that we write out the redo log before any further dirty pages are flushed to the tablespace files. At this point, - because we hold log_sys.mutex, mtr_t::commit() in other threads will - be blocked, and no pages can be added to the flush lists. */ + because we hold exclusive log_sys.latch, + mtr_t::commit() in other threads will be blocked, + and no pages can be added to buf_pool.flush_list. */ const lsn_t flush_lsn{fil_names_clear(oldest_lsn)}; ut_ad(flush_lsn >= end_lsn + SIZE_OF_FILE_CHECKPOINT); - mysql_mutex_unlock(&log_sys.mutex); + log_sys.latch.wr_unlock(); log_write_up_to(flush_lsn, true); - mysql_mutex_lock(&log_sys.mutex); + log_sys.latch.wr_lock(SRW_LOCK_CALL); if (log_sys.last_checkpoint_lsn >= oldest_lsn) goto do_nothing; @@ -1763,13 +1772,12 @@ static bool log_checkpoint_low(lsn_t oldest_lsn, lsn_t end_lsn) if (log_sys.n_pending_checkpoint_writes) { /* A checkpoint write is running */ - mysql_mutex_unlock(&log_sys.mutex); + log_sys.latch.wr_unlock(); return false; } log_sys.next_checkpoint_lsn= oldest_lsn; log_sys.write_checkpoint(end_lsn); - mysql_mutex_assert_not_owner(&log_sys.mutex); return true; } @@ -1793,12 +1801,10 @@ static bool log_checkpoint() fil_flush_file_spaces(); } - mysql_mutex_lock(&log_sys.mutex); + log_sys.latch.wr_lock(SRW_LOCK_CALL); const lsn_t end_lsn= log_sys.get_lsn(); - mysql_mutex_lock(&log_sys.flush_order_mutex); mysql_mutex_lock(&buf_pool.flush_list_mutex); const lsn_t oldest_lsn= buf_pool.get_oldest_modification(end_lsn); - mysql_mutex_unlock(&log_sys.flush_order_mutex); mysql_mutex_unlock(&buf_pool.flush_list_mutex); return log_checkpoint_low(oldest_lsn, end_lsn); } @@ -1835,7 +1841,6 @@ ATTRIBUTE_COLD void buf_flush_wait_flushed(lsn_t sync_lsn) { ut_ad(sync_lsn); ut_ad(sync_lsn < LSN_MAX); - mysql_mutex_assert_not_owner(&log_sys.mutex); ut_ad(!srv_read_only_mode); if (recv_recovery_is_on()) @@ -1893,7 +1898,6 @@ ATTRIBUTE_COLD void buf_flush_wait_flushed(lsn_t sync_lsn) @param furious true=furious flushing, false=limit to innodb_io_capacity */ ATTRIBUTE_COLD void buf_flush_ahead(lsn_t lsn, bool furious) { - mysql_mutex_assert_not_owner(&log_sys.mutex); ut_ad(!srv_read_only_mode); if (recv_recovery_is_on()) @@ -1952,11 +1956,9 @@ ATTRIBUTE_COLD static void buf_flush_sync_for_checkpoint(lsn_t lsn) fil_flush_file_spaces(); } - mysql_mutex_lock(&log_sys.mutex); + log_sys.latch.wr_lock(SRW_LOCK_CALL); const lsn_t newest_lsn= log_sys.get_lsn(); - mysql_mutex_lock(&log_sys.flush_order_mutex); mysql_mutex_lock(&buf_pool.flush_list_mutex); - mysql_mutex_unlock(&log_sys.flush_order_mutex); lsn_t measure= buf_pool.get_oldest_modification(0); const lsn_t checkpoint_lsn= measure ? measure : newest_lsn; @@ -1970,13 +1972,11 @@ ATTRIBUTE_COLD static void buf_flush_sync_for_checkpoint(lsn_t lsn) } else { - mysql_mutex_unlock(&log_sys.mutex); + log_sys.latch.wr_unlock(); if (!measure) measure= LSN_MAX; } - mysql_mutex_assert_not_owner(&log_sys.mutex); - /* After attempting log checkpoint, check if we have reached our target. */ const lsn_t target= buf_flush_sync_lsn; diff --git a/storage/innobase/fil/fil0fil.cc b/storage/innobase/fil/fil0fil.cc index ce6acde05f6..94bac460333 100644 --- a/storage/innobase/fil/fil0fil.cc +++ b/storage/innobase/fil/fil0fil.cc @@ -881,18 +881,21 @@ bool fil_space_free(uint32_t id, bool x_latched) } if (!recv_recovery_is_on()) { - mysql_mutex_lock(&log_sys.mutex); - } + log_sys.latch.wr_lock(SRW_LOCK_CALL); - mysql_mutex_assert_owner(&log_sys.mutex); + if (space->max_lsn) { + ut_d(space->max_lsn = 0); + fil_system.named_spaces.remove(*space); + } - if (space->max_lsn != 0) { - ut_d(space->max_lsn = 0); - fil_system.named_spaces.remove(*space); - } + log_sys.latch.wr_unlock(); + } else { + ut_ad(log_sys.latch.is_write_locked()); - if (!recv_recovery_is_on()) { - mysql_mutex_unlock(&log_sys.mutex); + if (space->max_lsn) { + ut_d(space->max_lsn = 0); + fil_system.named_spaces.remove(*space); + } } fil_space_free_low(space); @@ -1474,9 +1477,9 @@ static void fil_name_write_rename_low(uint32_t space_id, const char *old_name, static void fil_name_commit_durable(mtr_t *mtr) { - mysql_mutex_lock(&log_sys.mutex); + log_sys.latch.wr_lock(SRW_LOCK_CALL); auto lsn= mtr->commit_files(); - mysql_mutex_unlock(&log_sys.mutex); + log_sys.latch.wr_unlock(); log_write_up_to(lsn, true); } @@ -1647,13 +1650,13 @@ pfs_os_file_t fil_delete_tablespace(uint32_t id) handle= fil_system.detach(space, true); mysql_mutex_unlock(&fil_system.mutex); - mysql_mutex_lock(&log_sys.mutex); + log_sys.latch.wr_lock(SRW_LOCK_CALL); if (space->max_lsn) { ut_d(space->max_lsn = 0); fil_system.named_spaces.remove(*space); } - mysql_mutex_unlock(&log_sys.mutex); + log_sys.latch.wr_unlock(); fil_space_free_low(space); } @@ -1853,11 +1856,12 @@ static bool fil_rename_tablespace(uint32_t id, const char *old_path, ut_ad(strchr(new_file_name, '/')); if (!recv_recovery_is_on()) { - mysql_mutex_lock(&log_sys.mutex); + log_sys.latch.wr_lock(SRW_LOCK_CALL); } - /* log_sys.mutex is above fil_system.mutex in the latching order */ - mysql_mutex_assert_owner(&log_sys.mutex); + /* log_sys.latch is above fil_system.mutex in the latching order */ + ut_ad(log_sys.latch.is_write_locked() || + srv_operation == SRV_OPERATION_RESTORE_DELTA); mysql_mutex_lock(&fil_system.mutex); space->release(); ut_ad(node->name == old_file_name); @@ -1880,7 +1884,7 @@ skip_second_rename: } if (!recv_recovery_is_on()) { - mysql_mutex_unlock(&log_sys.mutex); + log_sys.latch.wr_unlock(); } mysql_mutex_unlock(&fil_system.mutex); @@ -3031,7 +3035,7 @@ void fil_names_dirty( fil_space_t* space) { - mysql_mutex_assert_owner(&log_sys.mutex); + ut_ad(log_sys.latch.is_write_locked()); ut_ad(recv_recovery_is_on()); ut_ad(log_sys.get_lsn() != 0); ut_ad(space->max_lsn == 0); @@ -3045,7 +3049,7 @@ fil_names_dirty( tablespace was modified for the first time since fil_names_clear(). */ ATTRIBUTE_NOINLINE ATTRIBUTE_COLD void mtr_t::name_write() { - mysql_mutex_assert_owner(&log_sys.mutex); + ut_ad(log_sys.latch.is_write_locked()); ut_d(fil_space_validate_for_mtr_commit(m_user_space)); ut_ad(!m_user_space->max_lsn); m_user_space->max_lsn= log_sys.get_lsn(); @@ -3073,7 +3077,7 @@ lsn_t fil_names_clear(lsn_t lsn) { mtr_t mtr; - mysql_mutex_assert_owner(&log_sys.mutex); + ut_ad(log_sys.latch.is_write_locked()); ut_ad(lsn); ut_ad(log_sys.is_latest()); diff --git a/storage/innobase/handler/ha_innodb.cc b/storage/innobase/handler/ha_innodb.cc index 4f3c3041455..a8ed2dd6bfb 100644 --- a/storage/innobase/handler/ha_innodb.cc +++ b/storage/innobase/handler/ha_innodb.cc @@ -242,10 +242,10 @@ static void innodb_max_purge_lag_wait_update(THD *thd, st_mysql_sys_var *, if (thd_kill_level(thd)) break; /* Adjust for purge_coordinator_state::refresh() */ - mysql_mutex_lock(&log_sys.mutex); + log_sys.latch.rd_lock(SRW_LOCK_CALL); const lsn_t last= log_sys.last_checkpoint_lsn, max_age= log_sys.max_checkpoint_age; - mysql_mutex_unlock(&log_sys.mutex); + log_sys.latch.rd_unlock(); const lsn_t lsn= log_sys.get_lsn(); if ((lsn - last) / 4 >= max_age / 5) buf_flush_ahead(last + max_age / 5, false); @@ -534,8 +534,6 @@ mysql_pfs_key_t fts_pll_tokenize_mutex_key; mysql_pfs_key_t ibuf_bitmap_mutex_key; mysql_pfs_key_t ibuf_mutex_key; mysql_pfs_key_t ibuf_pessimistic_insert_mutex_key; -mysql_pfs_key_t log_sys_mutex_key; -mysql_pfs_key_t log_flush_order_mutex_key; mysql_pfs_key_t recalc_pool_mutex_key; mysql_pfs_key_t purge_sys_pq_mutex_key; mysql_pfs_key_t recv_sys_mutex_key; @@ -571,12 +569,10 @@ static PSI_mutex_info all_innodb_mutexes[] = { PSI_KEY(fts_cache_init_mutex), PSI_KEY(fts_delete_mutex), PSI_KEY(fts_doc_id_mutex), - PSI_KEY(log_flush_order_mutex), PSI_KEY(ibuf_bitmap_mutex), PSI_KEY(ibuf_mutex), PSI_KEY(ibuf_pessimistic_insert_mutex), PSI_KEY(index_online_log), - PSI_KEY(log_sys_mutex), PSI_KEY(page_zip_stat_per_index_mutex), PSI_KEY(purge_sys_pq_mutex), PSI_KEY(recv_sys_mutex), @@ -603,6 +599,7 @@ mysql_pfs_key_t fil_space_latch_key; mysql_pfs_key_t trx_i_s_cache_lock_key; mysql_pfs_key_t trx_purge_latch_key; mysql_pfs_key_t lock_latch_key; +mysql_pfs_key_t log_latch_key; /* all_innodb_rwlocks array contains rwlocks that are performance schema instrumented if "UNIV_PFS_RWLOCK" @@ -617,6 +614,7 @@ static PSI_rwlock_info all_innodb_rwlocks[] = { &trx_i_s_cache_lock_key, "trx_i_s_cache_lock", 0 }, { &trx_purge_latch_key, "trx_purge_latch", 0 }, { &lock_latch_key, "lock_latch", 0 }, + { &log_latch_key, "log_latch", 0 }, { &index_tree_rw_lock_key, "index_tree_rw_lock", PSI_RWLOCK_FLAG_SX } }; # endif /* UNIV_PFS_RWLOCK */ @@ -949,8 +947,7 @@ static SHOW_VAR innodb_status_variables[]= { {"buffer_pool_reads", &export_vars.innodb_buffer_pool_reads, SHOW_SIZE_T}, {"buffer_pool_wait_free", &buf_pool.stat.LRU_waits, SHOW_SIZE_T}, - {"buffer_pool_write_requests", - &export_vars.innodb_buffer_pool_write_requests, SHOW_SIZE_T}, + {"buffer_pool_write_requests", &buf_pool.flush_list_requests, SHOW_SIZE_T}, {"checkpoint_age", &export_vars.innodb_checkpoint_age, SHOW_SIZE_T}, {"checkpoint_max_age", &export_vars.innodb_checkpoint_max_age, SHOW_SIZE_T}, {"data_fsyncs", (size_t*) &os_n_fsyncs, SHOW_SIZE_T}, @@ -19235,7 +19232,7 @@ static MYSQL_SYSVAR_SIZE_T(log_buffer_size, log_sys.buf_size, static MYSQL_SYSVAR_ULONGLONG(log_file_size, srv_log_file_size, PLUGIN_VAR_RQCMDARG | PLUGIN_VAR_READONLY, "Redo log size in bytes.", - NULL, NULL, 96 << 20, 1U << 20, std::numeric_limits::max(), 4096); + NULL, NULL, 96 << 20, 4 << 20, std::numeric_limits::max(), 4096); static MYSQL_SYSVAR_UINT(old_blocks_pct, innobase_old_blocks_pct, PLUGIN_VAR_RQCMDARG, diff --git a/storage/innobase/include/buf0buf.h b/storage/innobase/include/buf0buf.h index 703087d1b7f..88d1989bc73 100644 --- a/storage/innobase/include/buf0buf.h +++ b/storage/innobase/include/buf0buf.h @@ -1,7 +1,7 @@ /***************************************************************************** Copyright (c) 1995, 2016, Oracle and/or its affiliates. All Rights Reserved. -Copyright (c) 2013, 2021, MariaDB Corporation. +Copyright (c) 2013, 2022, MariaDB Corporation. 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 @@ -1755,6 +1755,9 @@ public: FlushHp flush_hp; /** modified blocks (a subset of LRU) */ UT_LIST_BASE_NODE_T(buf_page_t) flush_list; + /** number of blocks ever added to flush_list; + protected by flush_list_mutex */ + size_t flush_list_requests; private: /** whether the page cleaner needs wakeup from indefinite sleep */ bool page_cleaner_is_idle; @@ -1765,7 +1768,7 @@ public: pthread_cond_t do_flush_list; /** @return whether the page cleaner must sleep due to being idle */ - bool page_cleaner_idle() const + bool page_cleaner_idle() const noexcept { mysql_mutex_assert_owner(&flush_list_mutex); return page_cleaner_is_idle; @@ -1885,24 +1888,24 @@ public: private: /** Remove a block from the flush list. */ - inline void delete_from_flush_list_low(buf_page_t *bpage); + inline void delete_from_flush_list_low(buf_page_t *bpage) noexcept; /** Remove a block from flush_list. @param bpage buffer pool page @param clear whether to invoke buf_page_t::clear_oldest_modification() */ - void delete_from_flush_list(buf_page_t *bpage, bool clear); + void delete_from_flush_list(buf_page_t *bpage, bool clear) noexcept; public: /** Remove a block from flush_list. @param bpage buffer pool page */ - void delete_from_flush_list(buf_page_t *bpage) + void delete_from_flush_list(buf_page_t *bpage) noexcept { delete_from_flush_list(bpage, true); } /** Insert a modified block into the flush list. @param block modified block @param lsn start LSN of the mini-transaction that modified the block */ - void insert_into_flush_list(buf_block_t *block, lsn_t lsn); + void insert_into_flush_list(buf_block_t *block, lsn_t lsn) noexcept; /** Free a page whose underlying file page has been freed. */ - inline void release_freed_page(buf_page_t *bpage); + inline void release_freed_page(buf_page_t *bpage) noexcept; private: /** Temporary memory for page_compressed and encrypted I/O */ diff --git a/storage/innobase/include/buf0flu.h b/storage/innobase/include/buf0flu.h index 665fd1115e7..af38f61b13b 100644 --- a/storage/innobase/include/buf0flu.h +++ b/storage/innobase/include/buf0flu.h @@ -1,7 +1,7 @@ /***************************************************************************** Copyright (c) 1995, 2016, Oracle and/or its affiliates. All Rights Reserved. -Copyright (c) 2014, 2021, MariaDB Corporation. +Copyright (c) 2014, 2022, MariaDB Corporation. 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 @@ -103,33 +103,6 @@ ATTRIBUTE_COLD void buf_flush_wait_flushed(lsn_t sync_lsn); @param furious true=furious flushing, false=limit to innodb_io_capacity */ ATTRIBUTE_COLD void buf_flush_ahead(lsn_t lsn, bool furious); -/********************************************************************//** -This function should be called at a mini-transaction commit, if a page was -modified in it. Puts the block to the list of modified blocks, if it not -already in it. */ -inline void buf_flush_note_modification(buf_block_t *b, lsn_t start, lsn_t end) -{ - ut_ad(!srv_read_only_mode); - ut_d(const auto s= b->page.state()); - ut_ad(s > buf_page_t::FREED); - ut_ad(s < buf_page_t::READ_FIX); - ut_ad(mach_read_from_8(b->page.frame + FIL_PAGE_LSN) <= end); - mach_write_to_8(b->page.frame + FIL_PAGE_LSN, end); - if (UNIV_LIKELY_NULL(b->page.zip.data)) - memcpy_aligned<8>(FIL_PAGE_LSN + b->page.zip.data, - FIL_PAGE_LSN + b->page.frame, 8); - - const lsn_t oldest_modification= b->page.oldest_modification(); - - if (oldest_modification > 1) - ut_ad(oldest_modification <= start); - else if (fsp_is_system_temporary(b->page.id().space())) - b->page.set_temp_modified(); - else - buf_pool.insert_into_flush_list(b, start); - srv_stats.buf_pool_write_requests.inc(); -} - /** Initialize page_cleaner. */ ATTRIBUTE_COLD void buf_flush_page_cleaner_init(); diff --git a/storage/innobase/include/fil0fil.h b/storage/innobase/include/fil0fil.h index 81005d43c8b..a05485696f6 100644 --- a/storage/innobase/include/fil0fil.h +++ b/storage/innobase/include/fil0fil.h @@ -354,13 +354,10 @@ struct fil_space_t final /** fil_system.spaces chain node */ fil_space_t *hash; - lsn_t max_lsn; - /*!< LSN of the most recent - fil_names_write_if_was_clean(). - Reset to 0 by fil_names_clear(). - Protected by log_sys.mutex. - If and only if this is nonzero, the - tablespace will be in named_spaces. */ + /** LSN of the most recent fil_names_write_if_was_clean(). + Reset to 0 by fil_names_clear(). Protected by exclusive log_sys.latch. + If and only if max_lsn is nonzero, this is in fil_system.named_spaces. */ + lsn_t max_lsn; /** tablespace identifier */ uint32_t id; /** whether undo tablespace truncation is in progress */ @@ -1043,7 +1040,7 @@ struct fil_node_t final { /** tablespace containing this file */ fil_space_t *space; - /** file name; protected by fil_system.mutex and log_sys.mutex */ + /** file name; protected by fil_system.mutex and exclusive log_sys.latch */ char *name; /** file handle */ pfs_os_file_t handle; @@ -1434,14 +1431,12 @@ public: /** nonzero if fil_node_open_file_low() should avoid moving the tablespace to the end of space_list, for FIFO policy of try_to_close() */ ulint freeze_space_list; + /** list of all tablespaces */ ilist space_list; - /*!< list of all file spaces */ + /** list of all tablespaces for which a FILE_MODIFY record has been written + since the latest redo log checkpoint. + Protected only by exclusive log_sys.latch. */ ilist named_spaces; - /*!< list of all file spaces - for which a FILE_MODIFY - record has been written since - the latest redo log checkpoint. - Protected only by log_sys.mutex. */ /** list of all ENCRYPTED=DEFAULT tablespaces that need to be converted to the current value of innodb_encrypt_tables */ diff --git a/storage/innobase/include/log0log.h b/storage/innobase/include/log0log.h index 618bda3b87a..220d1680513 100644 --- a/storage/innobase/include/log0log.h +++ b/storage/innobase/include/log0log.h @@ -37,6 +37,7 @@ Created 12/9/1995 Heikki Tuuri #include "os0file.h" #include "span.h" #include "my_atomic_wrapper.h" +#include "srw_lock.h" #include using st_::span; @@ -57,16 +58,6 @@ static inline void delete_log_file(const char* suffix) os_file_delete_if_exists(innodb_log_file_key, path.c_str(), nullptr); } -/** Calculate the recommended highest values for lsn - last_checkpoint_lsn -and lsn - buf_pool.get_oldest_modification(). -@param[in] file_size requested innodb_log_file_size -@retval true on success -@retval false if the smallest log is too small to -accommodate the number of OS threads in the database server */ -bool -log_set_capacity(ulonglong file_size) - MY_ATTRIBUTE((warn_unused_result)); - struct completion_callback; /** Ensure that the log has been written to the log file up to a given @@ -83,10 +74,10 @@ void log_write_up_to(lsn_t lsn, bool durable, void log_buffer_flush_to_disk(bool durable= true); -/** Prepare to invoke log_write_and_flush(), before acquiring log_sys.mutex. */ +/** Prepare to invoke log_write_and_flush(), before acquiring log_sys.latch. */ ATTRIBUTE_COLD void log_write_and_flush_prepare(); -/** Durably write the log up to log_sys.lsn() and release log_sys.mutex. */ +/** Durably write the log up to log_sys.get_lsn(). */ ATTRIBUTE_COLD void log_write_and_flush(); /** Make a checkpoint */ @@ -202,35 +193,38 @@ private: preflush buffer pool pages, or initiate a log checkpoint. This must hold if lsn - last_checkpoint_lsn > max_checkpoint_age. */ std::atomic check_flush_or_checkpoint_; + public: - /** mutex protecting the log */ - MY_ALIGNED(CPU_LEVEL1_DCACHE_LINESIZE) mysql_mutex_t mutex; + /** rw-lock protecting buf */ + MY_ALIGNED(CPU_LEVEL1_DCACHE_LINESIZE) srw_lock latch; private: /** Last written LSN */ lsn_t write_lsn; public: - /** first free offset within the log buffer in use */ - size_t buf_free; - /** recommended maximum size of buf, after which the buffer is flushed */ - size_t max_buf_free; - /** mutex that ensures that inserts into buf_pool.flush_list are in - LSN order; allows mtr_t::commit() to release log_sys.mutex earlier */ - MY_ALIGNED(CPU_LEVEL1_DCACHE_LINESIZE) mysql_mutex_t flush_order_mutex; /** log record buffer, written to by mtr_t::commit() */ byte *buf; /** buffer for writing data to ib_logfile0, or nullptr if is_pmem() In write_buf(), buf and flush_buf are swapped */ byte *flush_buf; - /** number of write requests (to buf); protected by mutex */ - ulint write_to_buf; /** number of std::swap(buf, flush_buf) and writes from buf to log; - protected by mutex */ + protected by latch.wr_lock() */ ulint write_to_log; - /** number of waits in append_prepare() */ - ulint waits; /** innodb_log_buffer_size (size of buf and flush_buf, in bytes) */ size_t buf_size; +private: + /** spin lock protecting lsn, buf_free in append_prepare() */ + MY_ALIGNED(CPU_LEVEL1_DCACHE_LINESIZE) sspin_lock lsn_lock; +public: + /** first free offset within buf use; protected by lsn_lock */ + Atomic_relaxed buf_free; + /** number of write requests (to buf); protected by exclusive lsn_lock */ + ulint write_to_buf; + /** number of waits in append_prepare(); protected by lsn_lock */ + ulint waits; + /** recommended maximum size of buf, after which the buffer is flushed */ + size_t max_buf_free; + /** log file size in bytes, including the header */ lsn_t file_size; private: @@ -272,11 +266,11 @@ public: /*!< this is the maximum allowed value for lsn - last_checkpoint_lsn when a new query step is started */ - /** latest completed checkpoint (protected by log_sys.mutex) */ + /** latest completed checkpoint (protected by latch.wr_lock()) */ Atomic_relaxed last_checkpoint_lsn; lsn_t next_checkpoint_lsn; /*!< next checkpoint lsn */ - /** next checkpoint number (protected by mutex) */ + /** next checkpoint number (protected by latch.wr_lock()) */ ulint next_checkpoint_no; /** number of pending checkpoint writes */ ulint n_pending_checkpoint_writes; @@ -299,6 +293,9 @@ public: void close_file(); + /** Calculate the checkpoint safety margins. */ + static void set_capacity(); + lsn_t get_lsn(std::memory_order order= std::memory_order_relaxed) const { return lsn.load(order); } void set_lsn(lsn_t lsn) { this->lsn.store(lsn, std::memory_order_release); } @@ -310,17 +307,17 @@ public: /** Initialize the LSN on initial log file creation. */ lsn_t init_lsn() noexcept { - mysql_mutex_lock(&mutex); + latch.wr_lock(SRW_LOCK_CALL); const lsn_t lsn{get_lsn()}; flushed_to_disk_lsn.store(lsn, std::memory_order_relaxed); write_lsn= lsn; - mysql_mutex_unlock(&mutex); + latch.wr_unlock(); return lsn; } void set_recovered_lsn(lsn_t lsn) noexcept { - mysql_mutex_assert_owner(&mutex); + ut_ad(latch.is_write_locked()); write_lsn= lsn; this->lsn.store(lsn, std::memory_order_relaxed); flushed_to_disk_lsn.store(lsn, std::memory_order_relaxed); @@ -360,20 +357,29 @@ public: static size_t get_block_size() { return 512; } #endif +private: + /** Wait in append_prepare() for buffer to become available + @param ex whether log_sys.latch is exclusively locked */ + ATTRIBUTE_COLD static void append_prepare_wait(bool ex) noexcept; +public: /** Reserve space in the log buffer for appending data. - @param size upper limit of the length of the data to append(), in bytes - @return the current LSN */ - inline lsn_t append_prepare(size_t size) noexcept; + @tparam pmem log_sys.is_pmem() + @param size total length of the data to append(), in bytes + @param ex whether log_sys.latch is exclusively locked + @return the start LSN and the buffer position for append() */ + template + inline std::pair append_prepare(size_t size, bool ex) noexcept; /** Append a string of bytes to the redo log. + @param d destination @param s string of bytes @param size length of str, in bytes */ - void append(const void *s, size_t size) noexcept + void append(byte *&d, const void *s, size_t size) noexcept { - mysql_mutex_assert_owner(&mutex); - ut_ad(buf_free + size <= (is_pmem() ? file_size : buf_size)); - memcpy(buf + buf_free, s, size); - buf_free+= size; + ut_ad(latch.is_locked()); + ut_ad(d + size <= buf + (is_pmem() ? file_size : buf_size)); + memcpy(d, s, size); + d+= size; } /** Set the log file format. */ @@ -409,14 +415,15 @@ public: return START_OFFSET + (lsn - first_lsn) % capacity(); } - /** Write checkpoint information to the log header and release mutex. + /** Write checkpoint information and invoke latch.wr_unlock(). @param end_lsn start LSN of the FILE_CHECKPOINT mini-transaction */ inline void write_checkpoint(lsn_t end_lsn) noexcept; - /** Write buf to ib_logfile0 and release mutex. + /** Write buf to ib_logfile0. + @tparam release_latch whether to invoke latch.wr_unlock() @return new write target @retval 0 if everything was written */ - inline lsn_t write_buf() noexcept; + template inline lsn_t write_buf() noexcept; /** Create the log. */ void create(lsn_t lsn) noexcept; diff --git a/storage/innobase/include/log0recv.h b/storage/innobase/include/log0recv.h index b352b0d5b1a..e2d2024b028 100644 --- a/storage/innobase/include/log0recv.h +++ b/storage/innobase/include/log0recv.h @@ -420,9 +420,9 @@ extern bool recv_no_ibuf_operations; /** TRUE when recv_init_crash_recovery() has been called. */ extern bool recv_needed_recovery; #ifdef UNIV_DEBUG -/** TRUE if writing to the redo log (mtr_commit) is forbidden. -Protected by log_sys.mutex. */ -extern bool recv_no_log_write; +/** whether writing to the redo log is forbidden; +protected by exclusive log_sys.latch. */ +extern bool recv_no_log_write; #endif /* UNIV_DEBUG */ /** TRUE if buf_page_is_corrupted() should check if the log sequence diff --git a/storage/innobase/include/mtr0mtr.h b/storage/innobase/include/mtr0mtr.h index ed2cc64ba7a..dce1b4e9378 100644 --- a/storage/innobase/include/mtr0mtr.h +++ b/storage/innobase/include/mtr0mtr.h @@ -107,7 +107,7 @@ struct mtr_t { /** Commit a mini-transaction that did not modify any pages, but generated some redo log on a higher level, such as FILE_MODIFY records and an optional FILE_CHECKPOINT marker. - The caller must hold log_sys.mutex. + The caller must hold exclusive log_sys.latch. This is to be used at log_checkpoint(). @param checkpoint_lsn the log sequence number of a checkpoint, or 0 @return current LSN */ @@ -632,13 +632,15 @@ private: ATTRIBUTE_NOINLINE void encrypt(); /** Append the redo log records to the redo log buffer. + @param ex whether log_sys.latch is already exclusively locked @return {start_lsn,flush_ahead} */ - std::pair do_write(); + std::pair do_write(bool ex); /** Append the redo log records to the redo log buffer. @param len number of bytes to write + @param ex whether log_sys.latch is exclusively locked @return {start_lsn,flush_ahead} */ - std::pair finish_write(size_t len); + std::pair finish_write(size_t len, bool ex); /** Release the resources */ inline void release_resources(); diff --git a/storage/innobase/include/mtr0mtr.inl b/storage/innobase/include/mtr0mtr.inl index 21ff912e9c7..b275f3ebcbe 100644 --- a/storage/innobase/include/mtr0mtr.inl +++ b/storage/innobase/include/mtr0mtr.inl @@ -49,9 +49,8 @@ mtr_t::memo_push(void* object, mtr_memo_type_t type) ut_ad(ut_is_2pow(type)); /* If this mtr has x-fixed a clean page then we set - the made_dirty flag. This tells us if we need to - grab log_sys.flush_order_mutex at mtr_t::commit() so that we - can insert the dirtied page into the flush list. */ + the made_dirty flag. This tells mtr_t::commit() + to hold log_sys.latch longer. */ if (!m_made_dirty && (type == MTR_MEMO_PAGE_X_FIX || type == MTR_MEMO_PAGE_SX_FIX)) { diff --git a/storage/innobase/include/srv0srv.h b/storage/innobase/include/srv0srv.h index 5fe293a3649..36f7a7095b3 100644 --- a/storage/innobase/include/srv0srv.h +++ b/storage/innobase/include/srv0srv.h @@ -86,9 +86,6 @@ struct srv_stats_t /** Count the amount of data written in total (in bytes) */ ulint_ctr_1_t data_written; - /** Store the number of write requests issued */ - ulint_ctr_1_t buf_pool_write_requests; - /** Number of buffer pool reads that led to the reading of a disk page */ ulint_ctr_1_t buf_pool_reads; @@ -684,7 +681,6 @@ struct export_var_t{ ulint innodb_buffer_pool_pages_old; ulint innodb_buffer_pool_read_requests; /*!< buf_pool.stat.n_page_gets */ ulint innodb_buffer_pool_reads; /*!< srv_buf_pool_reads */ - ulint innodb_buffer_pool_write_requests;/*!< srv_stats.buf_pool_write_requests */ ulint innodb_buffer_pool_read_ahead_rnd;/*!< srv_read_ahead_rnd */ ulint innodb_buffer_pool_read_ahead; /*!< srv_read_ahead */ ulint innodb_buffer_pool_read_ahead_evicted;/*!< srv_read_ahead evicted*/ diff --git a/storage/innobase/include/srw_lock.h b/storage/innobase/include/srw_lock.h index 1705c63b8ad..9fba021df25 100644 --- a/storage/innobase/include/srw_lock.h +++ b/storage/innobase/include/srw_lock.h @@ -1,6 +1,6 @@ /***************************************************************************** -Copyright (c) 2020, 2021, MariaDB Corporation. +Copyright (c) 2020, 2022, MariaDB Corporation. 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 @@ -520,3 +520,12 @@ typedef srw_lock_impl srw_lock; typedef srw_lock_impl srw_spin_lock; #endif + +/** Simple spin lock */ +struct sspin_lock +{ + std::atomic word{0}; + void lock() noexcept; + void unlock() noexcept + { ut_ad(word); word.store(0, std::memory_order_release); } +}; diff --git a/storage/innobase/include/univ.i b/storage/innobase/include/univ.i index cb34f6c31f6..8dcd3c984de 100644 --- a/storage/innobase/include/univ.i +++ b/storage/innobase/include/univ.i @@ -517,8 +517,6 @@ extern mysql_pfs_key_t fts_pll_tokenize_mutex_key; extern mysql_pfs_key_t ibuf_bitmap_mutex_key; extern mysql_pfs_key_t ibuf_mutex_key; extern mysql_pfs_key_t ibuf_pessimistic_insert_mutex_key; -extern mysql_pfs_key_t log_sys_mutex_key; -extern mysql_pfs_key_t log_flush_order_mutex_key; extern mysql_pfs_key_t recalc_pool_mutex_key; extern mysql_pfs_key_t purge_sys_pq_mutex_key; extern mysql_pfs_key_t recv_sys_mutex_key; @@ -547,5 +545,6 @@ extern mysql_pfs_key_t index_tree_rw_lock_key; extern mysql_pfs_key_t index_online_log_key; extern mysql_pfs_key_t trx_sys_rw_lock_key; extern mysql_pfs_key_t lock_latch_key; +extern mysql_pfs_key_t log_latch_key; # endif /* UNIV_PFS_RWLOCK */ #endif /* HAVE_PSI_INTERFACE */ diff --git a/storage/innobase/log/log0log.cc b/storage/innobase/log/log0log.cc index bd146237000..739adcf1b97 100644 --- a/storage/innobase/log/log0log.cc +++ b/storage/innobase/log/log0log.cc @@ -74,52 +74,24 @@ log_t log_sys; #define LOG_BUF_FLUSH_MARGIN ((4 * 4096) /* cf. log_t::append_prepare() */ \ + (4U << srv_page_size_shift)) -/** Calculate the recommended highest values for lsn - last_checkpoint_lsn -and lsn - buf_pool.get_oldest_modification(). -@param[in] file_size requested innodb_log_file_size -@retval true on success -@retval false if the smallest log group is too small to -accommodate the number of OS threads in the database server */ -bool -log_set_capacity(ulonglong file_size) +void log_t::set_capacity() { - mysql_mutex_assert_owner(&log_sys.mutex); + ut_ad(log_sys.latch.is_write_locked()); /* Margin for the free space in the smallest log, before a new query step which modifies the database, is started */ - const size_t LOG_CHECKPOINT_FREE_PER_THREAD = 4U - << srv_page_size_shift; - const size_t LOG_CHECKPOINT_EXTRA_FREE = 8U << srv_page_size_shift; - lsn_t margin; - ulint free; - - lsn_t smallest_capacity = file_size - log_t::START_OFFSET; + lsn_t smallest_capacity = srv_log_file_size - log_t::START_OFFSET; /* Add extra safety */ smallest_capacity -= smallest_capacity / 10; - /* For each OS thread we must reserve so much free space in the - smallest log group that it can accommodate the log entries produced - by single query steps: running out of free log space is a serious - system error which requires rebooting the database. */ - - free = LOG_CHECKPOINT_FREE_PER_THREAD * 10 - + LOG_CHECKPOINT_EXTRA_FREE; - if (free >= smallest_capacity / 2) { - sql_print_error("InnoDB: innodb_log_file_size is too small." - " %s", INNODB_PARAMETERS_MSG); - return false; - } - - margin = smallest_capacity - free; - margin = margin - margin / 10; /* Add still some extra safety */ + lsn_t margin = smallest_capacity - (48 << srv_page_size_shift); + margin -= margin / 10; /* Add still some extra safety */ log_sys.log_capacity = smallest_capacity; log_sys.max_modified_age_async = margin - margin / 8; log_sys.max_checkpoint_age = margin; - - return(true); } /** Initialize the redo log subsystem. */ @@ -128,14 +100,7 @@ void log_t::create() ut_ad(this == &log_sys); ut_ad(!is_initialised()); -#if defined(__aarch64__) - mysql_mutex_init(log_sys_mutex_key, &mutex, MY_MUTEX_INIT_FAST); - mysql_mutex_init( - log_flush_order_mutex_key, &flush_order_mutex, MY_MUTEX_INIT_FAST); -#else - mysql_mutex_init(log_sys_mutex_key, &mutex, nullptr); - mysql_mutex_init(log_flush_order_mutex_key, &flush_order_mutex, nullptr); -#endif + latch.SRW_LOCK_INIT(log_latch_key); /* LSN 0 and 1 are reserved; @see buf_page_t::oldest_modification_ */ lsn.store(FIRST_LSN, std::memory_order_relaxed); @@ -272,7 +237,7 @@ void log_t::attach(log_file_t file, os_offset_t size) void log_t::create(lsn_t lsn) noexcept { - mysql_mutex_assert_owner(&mutex); + ut_ad(latch.is_write_locked()); ut_ad(!recv_no_log_write); ut_ad(is_latest()); ut_ad(this == &log_sys); @@ -516,7 +481,6 @@ static size_t log_pad(lsn_t lsn, size_t pad, byte *begin, byte *extra) inline void log_t::persist(lsn_t lsn) noexcept { ut_ad(is_pmem()); - mysql_mutex_assert_not_owner(&mutex); ut_ad(!write_lock.is_owner()); ut_ad(!flush_lock.is_owner()); @@ -551,13 +515,13 @@ inline void log_t::persist(lsn_t lsn) noexcept } #endif -/** Write buf to ib_logfile0 and release mutex. +/** Write buf to ib_logfile0. +@tparam release_latch whether to invoke latch.wr_unlock() @return new write target @retval 0 if everything was written */ -inline lsn_t log_t::write_buf() noexcept +template inline lsn_t log_t::write_buf() noexcept { - mysql_mutex_assert_owner(&mutex); - + ut_ad(latch.is_write_locked()); ut_ad(!srv_read_only_mode); ut_ad(!is_pmem()); @@ -565,7 +529,8 @@ inline lsn_t log_t::write_buf() noexcept if (write_lsn >= lsn) { - mysql_mutex_unlock(&mutex); + if (release_latch) + latch.wr_unlock(); ut_ad(write_lsn == lsn); } else @@ -581,31 +546,33 @@ inline lsn_t log_t::write_buf() noexcept const byte *write_buf{buf}; size_t length{buf_free}; ut_ad(length >= (calc_lsn_offset(write_lsn) & block_size_1)); - buf_free&= block_size_1; - ut_ad(buf_free == ((lsn - first_lsn) & block_size_1)); + const size_t new_buf_free{length & block_size_1}; + buf_free= new_buf_free; + ut_ad(new_buf_free == ((lsn - first_lsn) & block_size_1)); - if (buf_free) + if (new_buf_free) { #if 0 /* TODO: Pad the last log block with dummy records. */ - buf_free= log_pad(lsn, get_block_size() - buf_free, - buf + buf_free, flush_buf); + buf_free= log_pad(lsn, get_block_size() - new_buf_free, + buf + new_buf_free, flush_buf); ... /* TODO: Update the LSN and adjust other code. */ #else /* The rest of the block will be written as garbage. (We want to avoid memset() while holding mutex.) This block will be overwritten later, once records beyond the current LSN are generated. */ - MEM_MAKE_DEFINED(buf + length, get_block_size() - buf_free); + MEM_MAKE_DEFINED(buf + length, get_block_size() - new_buf_free); buf[length]= 0; /* allow recovery to catch EOF faster */ length&= ~block_size_1; - memcpy_aligned<16>(flush_buf, buf + length, (buf_free + 15) & ~15); + memcpy_aligned<16>(flush_buf, buf + length, (new_buf_free + 15) & ~15); length+= get_block_size(); #endif } std::swap(buf, flush_buf); write_to_log++; - mysql_mutex_unlock(&mutex); + if (release_latch) + latch.wr_unlock(); if (UNIV_UNLIKELY(srv_shutdown_state > SRV_SHUTDOWN_INITIATED)) { @@ -690,8 +657,8 @@ repeat: if (write_lock.acquire(lsn, durable ? nullptr : callback) == group_commit_lock::ACQUIRED) { - mysql_mutex_lock(&log_sys.mutex); - write_lsn= log_sys.write_buf(); + log_sys.latch.wr_lock(SRW_LOCK_CALL); + write_lsn= log_sys.write_buf(); } else write_lsn= 0; @@ -718,11 +685,9 @@ void log_buffer_flush_to_disk(bool durable) log_write_up_to(log_sys.get_lsn(std::memory_order_acquire), durable); } -/** Prepare to invoke log_write_and_flush(), before acquiring log_sys.mutex. */ +/** Prepare to invoke log_write_and_flush(), before acquiring log_sys.latch. */ ATTRIBUTE_COLD void log_write_and_flush_prepare() { - mysql_mutex_assert_not_owner(&log_sys.mutex); - if (log_sys.is_pmem()) return; @@ -732,23 +697,18 @@ ATTRIBUTE_COLD void log_write_and_flush_prepare() group_commit_lock::ACQUIRED); } -/** Durably write the log and release log_sys.mutex */ +/** Durably write the log up to log_sys.get_lsn(). */ ATTRIBUTE_COLD void log_write_and_flush() { ut_ad(!srv_read_only_mode); if (!log_sys.is_pmem()) { - const lsn_t write_lsn{log_sys.write_buf()}; - const lsn_t flush_lsn{log_flush(write_lock.value())}; - if (write_lsn || flush_lsn) - log_write_up_to(std::max(write_lsn, flush_lsn), true, &dummy_callback); + log_sys.write_buf(); + log_flush(write_lock.value()); } #ifdef HAVE_PMEM else - { - mysql_mutex_unlock(&log_sys.mutex); log_sys.persist(log_sys.get_lsn()); - } #endif } @@ -758,11 +718,7 @@ Tries to establish a big enough margin of free space in the log buffer, such that a new log entry can be catenated without an immediate need for a flush. */ ATTRIBUTE_COLD static void log_flush_margin() { - mysql_mutex_lock(&log_sys.mutex); - const bool flush{log_sys.buf_free > log_sys.max_buf_free}; - mysql_mutex_unlock(&log_sys.mutex); - - if (flush) + if (log_sys.buf_free > log_sys.max_buf_free) log_buffer_flush_to_disk(false); } @@ -775,26 +731,27 @@ ATTRIBUTE_COLD static void log_checkpoint_margin() { while (log_sys.check_flush_or_checkpoint()) { - mysql_mutex_lock(&log_sys.mutex); + log_sys.latch.rd_lock(SRW_LOCK_CALL); ut_ad(!recv_no_log_write); if (!log_sys.check_flush_or_checkpoint()) { func_exit: - mysql_mutex_unlock(&log_sys.mutex); + log_sys.latch.rd_unlock(); return; } const lsn_t lsn= log_sys.get_lsn(); const lsn_t checkpoint= log_sys.last_checkpoint_lsn; const lsn_t sync_lsn= checkpoint + log_sys.max_checkpoint_age; + if (lsn <= sync_lsn) { log_sys.set_check_flush_or_checkpoint(false); goto func_exit; } - mysql_mutex_unlock(&log_sys.mutex); + log_sys.latch.rd_unlock(); /* We must wait to prevent the tail of the log overwriting the head. */ buf_flush_wait_flushed(std::min(sync_lsn, checkpoint + (1U << 20))); @@ -944,9 +901,9 @@ wait_suspend_loop: } if (log_sys.is_initialised()) { - mysql_mutex_lock(&log_sys.mutex); + log_sys.latch.rd_lock(SRW_LOCK_CALL); const ulint n_write = log_sys.n_pending_checkpoint_writes; - mysql_mutex_unlock(&log_sys.mutex); + log_sys.latch.rd_unlock(); if (n_write) { if (srv_print_verbose_log && count > 600) { @@ -987,7 +944,7 @@ wait_suspend_loop: ? SIZE_OF_FILE_CHECKPOINT + 8 : SIZE_OF_FILE_CHECKPOINT; - mysql_mutex_lock(&log_sys.mutex); + log_sys.latch.rd_lock(SRW_LOCK_CALL); lsn = log_sys.get_lsn(); @@ -995,7 +952,7 @@ wait_suspend_loop: && lsn != log_sys.last_checkpoint_lsn + sizeof_cp; ut_ad(lsn >= log_sys.last_checkpoint_lsn); - mysql_mutex_unlock(&log_sys.mutex); + log_sys.latch.rd_unlock(); if (lsn_changed) { goto loop; @@ -1041,7 +998,7 @@ log_print( double time_elapsed; time_t current_time; - mysql_mutex_lock(&log_sys.mutex); + log_sys.latch.rd_lock(SRW_LOCK_CALL); const lsn_t lsn= log_sys.get_lsn(); mysql_mutex_lock(&buf_pool.flush_list_mutex); @@ -1079,7 +1036,7 @@ log_print( log_sys.n_log_ios_old = log_sys.n_log_ios; log_sys.last_printout_time = current_time; - mysql_mutex_unlock(&log_sys.mutex); + log_sys.latch.rd_unlock(); } /**********************************************************************//** @@ -1112,8 +1069,7 @@ void log_t::close() ut_ad(!flush_buf); #endif - mysql_mutex_destroy(&mutex); - mysql_mutex_destroy(&flush_order_mutex); + latch.destroy(); recv_sys.close(); diff --git a/storage/innobase/log/log0recv.cc b/storage/innobase/log/log0recv.cc index fb667a3670c..5b2a006859d 100644 --- a/storage/innobase/log/log0recv.cc +++ b/storage/innobase/log/log0recv.cc @@ -62,7 +62,7 @@ recv_sys_t recv_sys; bool recv_needed_recovery; #ifdef UNIV_DEBUG /** TRUE if writing to the redo log (mtr_commit) is forbidden. -Protected by log_sys.mutex. */ +Protected by log_sys.latch. */ bool recv_no_log_write = false; #endif /* UNIV_DEBUG */ @@ -2235,7 +2235,9 @@ template inline recv_sys_t::parse_mtr_result recv_sys_t::parse(store_t store, source &l) noexcept { - mysql_mutex_assert_owner(&log_sys.mutex); + ut_ad(log_sys.latch.is_write_locked() || + srv_operation == SRV_OPERATION_BACKUP || + srv_operation == SRV_OPERATION_BACKUP_NO_DEFER); mysql_mutex_assert_owner(&mutex); ut_ad(log_sys.next_checkpoint_lsn); ut_ad(log_sys.is_latest()); @@ -2970,17 +2972,23 @@ set_start_lsn: if (start_lsn) { ut_ad(end_lsn >= start_lsn); + ut_ad(!block->page.oldest_modification()); mach_write_to_8(FIL_PAGE_LSN + frame, end_lsn); - if (UNIV_LIKELY(frame == block->page.frame)) { + if (UNIV_LIKELY(!block->page.zip.data)) { mach_write_to_8(srv_page_size - FIL_PAGE_END_LSN_OLD_CHKSUM + frame, end_lsn); } else { buf_zip_decompress(block, false); } - - buf_block_modify_clock_inc(block); - buf_flush_note_modification(block, start_lsn, end_lsn); + /* The following is adapted from + buf_pool_t::insert_into_flush_list() */ + mysql_mutex_lock(&buf_pool.flush_list_mutex); + buf_pool.stat.flush_list_bytes+= block->physical_size(); + block->page.set_oldest_modification(start_lsn); + UT_LIST_ADD_FIRST(buf_pool.flush_list, &block->page); + buf_pool.page_cleaner_wakeup(); + mysql_mutex_unlock(&buf_pool.flush_list_mutex); } else if (free_page && init) { /* There have been no operations that modify the page. Any buffered changes must not be merged. A subsequent @@ -3271,9 +3279,6 @@ void recv_sys_t::apply(bool last_batch) srv_operation == SRV_OPERATION_RESTORE || srv_operation == SRV_OPERATION_RESTORE_EXPORT); -#ifdef SAFE_MUTEX - DBUG_ASSERT(!last_batch == mysql_mutex_is_owner(&log_sys.mutex)); -#endif /* SAFE_MUTEX */ mysql_mutex_assert_owner(&mutex); timespec abstime; @@ -3283,15 +3288,15 @@ void recv_sys_t::apply(bool last_batch) if (is_corrupt_log()) return; if (last_batch) - { - mysql_mutex_assert_not_owner(&log_sys.mutex); my_cond_wait(&cond, &mutex.m_mutex); - } else { - mysql_mutex_unlock(&mutex); + ut_ad(log_sys.latch.is_write_locked()); + log_sys.latch.wr_unlock(); set_timespec_nsec(abstime, 500000000ULL); /* 0.5s */ - my_cond_timedwait(&cond, &log_sys.mutex.m_mutex, &abstime); + my_cond_timedwait(&cond, &mutex.m_mutex, &abstime); + mysql_mutex_unlock(&mutex); + log_sys.latch.wr_lock(SRW_LOCK_CALL); mysql_mutex_lock(&mutex); } } @@ -3398,7 +3403,6 @@ next_free_block: { if (last_batch) { - mysql_mutex_assert_not_owner(&log_sys.mutex); if (!empty) my_cond_wait(&cond, &mutex.m_mutex); else @@ -3412,9 +3416,12 @@ next_free_block: } else { - mysql_mutex_unlock(&mutex); + ut_ad(log_sys.latch.is_write_locked()); + log_sys.latch.wr_unlock(); set_timespec_nsec(abstime, 500000000ULL); /* 0.5s */ - my_cond_timedwait(&cond, &log_sys.mutex.m_mutex, &abstime); + my_cond_timedwait(&cond, &mutex.m_mutex, &abstime); + mysql_mutex_unlock(&mutex); + log_sys.latch.wr_lock(SRW_LOCK_CALL); mysql_mutex_lock(&mutex); } continue; @@ -3432,10 +3439,9 @@ next_free_block: else { mlog_init.reset(); - mysql_mutex_unlock(&log_sys.mutex); + log_sys.latch.wr_unlock(); } - mysql_mutex_assert_not_owner(&log_sys.mutex); mysql_mutex_unlock(&mutex); if (last_batch && srv_operation != SRV_OPERATION_RESTORE && @@ -3451,7 +3457,7 @@ next_free_block: if (!last_batch) { buf_pool_invalidate(); - mysql_mutex_lock(&log_sys.mutex); + log_sys.latch.wr_lock(SRW_LOCK_CALL); } #ifdef HAVE_PMEM else if (log_sys.is_pmem()) @@ -3511,7 +3517,7 @@ static bool recv_scan_log(bool last_phase) for (ut_d(lsn_t source_offset= 0);;) { - mysql_mutex_assert_owner(&log_sys.mutex); + ut_ad(log_sys.latch.is_write_locked()); #ifdef UNIV_DEBUG const bool wrap{source_offset + recv_sys.len == log_sys.file_size}; #endif @@ -3868,7 +3874,7 @@ recv_init_crash_recovery_spaces(bool rescan, bool& missing_tablespace) static dberr_t recv_rename_files() { mysql_mutex_assert_owner(&recv_sys.mutex); - mysql_mutex_assert_owner(&log_sys.mutex); + ut_ad(log_sys.latch.is_write_locked()); dberr_t err= DB_SUCCESS; @@ -3963,20 +3969,16 @@ dberr_t recv_recovery_from_checkpoint_start() recv_sys.recovery_on = true; - mysql_mutex_lock(&log_sys.mutex); + log_sys.latch.wr_lock(SRW_LOCK_CALL); dberr_t err = recv_sys.find_checkpoint(); if (err != DB_SUCCESS) { early_exit: - mysql_mutex_unlock(&log_sys.mutex); + log_sys.latch.wr_unlock(); return err; } - if (!log_set_capacity(srv_log_file_size)) { -err_exit: - err = DB_ERROR; - goto early_exit; - } + log_sys.set_capacity(); /* Start reading the log from the checkpoint lsn. The variable contiguous_lsn contains an lsn up to which the log is known to @@ -4103,7 +4105,9 @@ read_only_recovery: } if (recv_sys.lsn < log_sys.next_checkpoint_lsn) { - goto err_exit; +err_exit: + err = DB_ERROR; + goto early_exit; } if (!srv_read_only_mode && log_sys.is_latest()) { @@ -4142,7 +4146,7 @@ read_only_recovery: err = recv_rename_files(); } mysql_mutex_unlock(&recv_sys.mutex); - mysql_mutex_unlock(&log_sys.mutex); + log_sys.latch.wr_unlock(); recv_lsn_checks_on = true; diff --git a/storage/innobase/mtr/mtr0mtr.cc b/storage/innobase/mtr/mtr0mtr.cc index 2b5d8946db4..bf17d79cf7a 100644 --- a/storage/innobase/mtr/mtr0mtr.cc +++ b/storage/innobase/mtr/mtr0mtr.cc @@ -312,16 +312,10 @@ struct DebugCheck { struct ReleaseBlocks { const lsn_t start, end; -#ifdef UNIV_DEBUG - const mtr_buf_t &memo; - - ReleaseBlocks(lsn_t start, lsn_t end, const mtr_buf_t &memo) : - start(start), end(end), memo(memo) -#else /* UNIV_DEBUG */ - ReleaseBlocks(lsn_t start, lsn_t end, const mtr_buf_t&) : - start(start), end(end) -#endif /* UNIV_DEBUG */ + mutable size_t modified; + ReleaseBlocks(lsn_t start, lsn_t end) : start(start), end(end), modified(0) { + ut_ad(!srv_read_only_mode); ut_ad(start); ut_ad(end); } @@ -340,8 +334,25 @@ struct ReleaseBlocks return true; } - buf_flush_note_modification(static_cast(slot->object), - start, end); + modified++; + buf_block_t *b= static_cast(slot->object); + ut_d(const auto s= b->page.state()); + ut_ad(s > buf_page_t::FREED); + ut_ad(s < buf_page_t::READ_FIX); + ut_ad(mach_read_from_8(b->page.frame + FIL_PAGE_LSN) <= end); + mach_write_to_8(b->page.frame + FIL_PAGE_LSN, end); + if (UNIV_LIKELY_NULL(b->page.zip.data)) + memcpy_aligned<8>(FIL_PAGE_LSN + b->page.zip.data, + FIL_PAGE_LSN + b->page.frame, 8); + + const lsn_t oldest_modification= b->page.oldest_modification(); + + if (oldest_modification > 1) + ut_ad(oldest_modification <= start); + else if (fsp_is_system_temporary(b->page.id().space())) + b->page.set_temp_modified(); + else + buf_pool.insert_into_flush_list(b, start); return true; } }; @@ -403,15 +414,9 @@ void mtr_t::commit() if (UNIV_LIKELY(m_log_mode == MTR_LOG_ALL)) { - lsns= do_write(); - - if (m_made_dirty) - mysql_mutex_lock(&log_sys.flush_order_mutex); - - /* It is now safe to release log_sys.mutex because the - buf_pool.flush_order_mutex will ensure that we are the first one - to insert into buf_pool.flush_list. */ - mysql_mutex_unlock(&log_sys.mutex); + lsns= do_write(false); + if (!m_made_dirty) + log_sys.latch.rd_unlock(); } else { @@ -420,7 +425,7 @@ void mtr_t::commit() m_commit_lsn= log_sys.get_lsn(); lsns= { m_commit_lsn, PAGE_FLUSH_NO }; if (UNIV_UNLIKELY(m_made_dirty)) /* This should be IMPORT TABLESPACE */ - mysql_mutex_lock(&log_sys.flush_order_mutex); + log_sys.latch.rd_lock(SRW_LOCK_CALL); } if (m_freed_pages) @@ -445,16 +450,23 @@ void mtr_t::commit() else ut_ad(!m_freed_space); - m_memo.for_each_block_in_reverse(CIterate - (ReleaseBlocks(lsns.first, m_commit_lsn, - m_memo))); + ReleaseBlocks rb{lsns.first, m_commit_lsn}; + m_memo.for_each_block_in_reverse(CIterate(rb)); if (m_made_dirty) - mysql_mutex_unlock(&log_sys.flush_order_mutex); + log_sys.latch.rd_unlock(); m_memo.for_each_block_in_reverse(CIterate()); if (UNIV_UNLIKELY(lsns.second != PAGE_FLUSH_NO)) buf_flush_ahead(m_commit_lsn, lsns.second == PAGE_FLUSH_SYNC); + + if (rb.modified) + { + mysql_mutex_lock(&buf_pool.flush_list_mutex); + buf_pool.flush_list_requests+= rb.modified; + buf_pool.page_cleaner_wakeup(); + mysql_mutex_unlock(&buf_pool.flush_list_mutex); + } } else m_memo.for_each_block_in_reverse(CIterate()); @@ -523,12 +535,13 @@ void mtr_t::commit_shrink(fil_space_t &space) ut_ad(UT_LIST_GET_LEN(space.chain) == 1); log_write_and_flush_prepare(); + log_sys.latch.wr_lock(SRW_LOCK_CALL); - const lsn_t start_lsn= do_write().first; + const lsn_t start_lsn= do_write(true).first; - mysql_mutex_lock(&log_sys.flush_order_mutex); /* Durably write the reduced FSP_SIZE before truncating the data file. */ log_write_and_flush(); + ut_ad(log_sys.latch.is_write_locked()); os_file_truncate(space.chain.start->name, space.chain.start->handle, os_offset_t{space.size} << srv_page_size_shift, true); @@ -557,9 +570,8 @@ void mtr_t::commit_shrink(fil_space_t &space) m_memo.for_each_block_in_reverse(CIterate{space}); m_memo.for_each_block_in_reverse(CIterate - (ReleaseBlocks(start_lsn, m_commit_lsn, - m_memo))); - mysql_mutex_unlock(&log_sys.flush_order_mutex); + (ReleaseBlocks{start_lsn, m_commit_lsn})); + log_sys.latch.wr_unlock(); mysql_mutex_lock(&fil_system.mutex); ut_ad(space.is_being_truncated); @@ -582,7 +594,7 @@ This is to be used at log_checkpoint(). @return current LSN */ lsn_t mtr_t::commit_files(lsn_t checkpoint_lsn) { - mysql_mutex_assert_owner(&log_sys.mutex); + ut_ad(log_sys.latch.is_write_locked()); ut_ad(is_active()); ut_ad(!is_inside_ibuf()); ut_ad(m_log_mode == MTR_LOG_ALL); @@ -616,7 +628,7 @@ lsn_t mtr_t::commit_files(lsn_t checkpoint_lsn) m_crc= 0; m_log.for_each_block([this](const mtr_buf_t::block_t *b) { m_crc= my_crc32c(m_crc, b->begin(), b->used()); return true; }); - finish_write(size); + finish_write(size, true); release_resources(); if (checkpoint_lsn) @@ -753,8 +765,6 @@ mtr_t::release_page(const void* ptr, mtr_memo_type_t type) ut_ad(0); } -static bool log_margin_warned; -static time_t log_margin_warn_time; static bool log_close_warned; static time_t log_close_warn_time; @@ -774,65 +784,73 @@ ATTRIBUTE_COLD static void log_overwrite_warning(lsn_t age, lsn_t capacity) } } -/** Reserve space in the log buffer for appending data. -@param size upper limit of the length of the data to append(), in bytes -@return the current LSN */ -inline lsn_t log_t::append_prepare(size_t size) noexcept +/** Wait in append_prepare() for buffer to become available +@param ex whether log_sys.latch is exclusively locked */ +ATTRIBUTE_COLD void log_t::append_prepare_wait(bool ex) noexcept { - mysql_mutex_assert_owner(&mutex); + log_sys.waits++; + log_sys.lsn_lock.unlock(); - lsn_t lsn= get_lsn(); + if (ex) + log_sys.latch.wr_unlock(); + else + log_sys.latch.rd_unlock(); - if (UNIV_UNLIKELY(size > log_capacity)) + DEBUG_SYNC_C("log_buf_size_exceeded"); + log_buffer_flush_to_disk(log_sys.is_pmem()); + + if (ex) + log_sys.latch.wr_lock(SRW_LOCK_CALL); + else + log_sys.latch.rd_lock(SRW_LOCK_CALL); + + log_sys.lsn_lock.lock(); +} + +/** Reserve space in the log buffer for appending data. +@tparam pmem log_sys.is_pmem() +@param size total length of the data to append(), in bytes +@param ex whether log_sys.latch is exclusively locked +@return the start LSN and the buffer position for append() */ +template +inline +std::pair log_t::append_prepare(size_t size, bool ex) noexcept +{ + ut_ad(latch.is_locked()); + ut_ad(pmem == is_pmem()); +#ifndef _WIN32 // there is no accurate is_write_locked() on SRWLOCK + ut_ad(ex == latch.is_write_locked()); +#endif + const lsn_t checkpoint_margin{last_checkpoint_lsn + log_capacity - size}; + const size_t avail{(pmem ? size_t(capacity()) : buf_size) - size}; + lsn_lock.lock(); + write_to_buf++; + + for (ut_d(int count= 50); + UNIV_UNLIKELY((pmem + ? size_t(get_lsn() - + get_flushed_lsn(std::memory_order_relaxed)) + : size_t{buf_free}) > avail); ) { - time_t t= time(nullptr); - - /* return with warning output to avoid deadlock */ - if (!log_margin_warned || difftime(t, log_margin_warn_time) > 15) - { - log_margin_warned= true; - log_margin_warn_time= t; - - sql_print_error("InnoDB: innodb_log_file_size is too small " - "for mini-transaction size %zu", size); - } - goto throttle; + append_prepare_wait(ex); + ut_ad(count--); } - else if (UNIV_UNLIKELY(lsn + size > last_checkpoint_lsn + log_capacity)) - throttle: + + const lsn_t l{lsn.load(std::memory_order_relaxed)}; + lsn.store(l + size, std::memory_order_relaxed); + const size_t b{buf_free}; + size_t new_buf_free{b}; + new_buf_free+= size; + if (pmem && new_buf_free >= file_size) + new_buf_free-= size_t(capacity()); + buf_free= new_buf_free; + lsn_lock.unlock(); + + if (UNIV_UNLIKELY(l > checkpoint_margin) || + (!pmem && b >= max_buf_free)) set_check_flush_or_checkpoint(); - if (is_pmem()) - { - for (ut_d(int count= 50); capacity() - size < - size_t(lsn - flushed_to_disk_lsn.load(std::memory_order_relaxed)); ) - { - waits++; - mysql_mutex_unlock(&mutex); - DEBUG_SYNC_C("log_buf_size_exceeded"); - log_write_up_to(lsn, true); - ut_ad(count--); - mysql_mutex_lock(&mutex); - lsn= get_lsn(); - } - return lsn; - } - - /* Calculate the amount of free space needed. */ - size= (4 * 4096) - size + log_sys.buf_size; - - for (ut_d(int count= 50); UNIV_UNLIKELY(buf_free > size); ) - { - waits++; - mysql_mutex_unlock(&mutex); - DEBUG_SYNC_C("log_buf_size_exceeded"); - log_write_up_to(lsn, false); - ut_ad(count--); - mysql_mutex_lock(&mutex); - lsn= get_lsn(); - } - - return lsn; + return {l, &buf[b]}; } /** Finish appending data to the log. @@ -840,9 +858,7 @@ inline lsn_t log_t::append_prepare(size_t size) noexcept @return whether buf_flush_ahead() will have to be invoked */ static mtr_t::page_flush_ahead log_close(lsn_t lsn) noexcept { - mysql_mutex_assert_owner(&log_sys.mutex); - log_sys.write_to_buf++; - log_sys.set_lsn(lsn); + ut_ad(log_sys.latch.is_locked()); const lsn_t checkpoint_age= lsn - log_sys.last_checkpoint_lsn; @@ -859,10 +875,11 @@ static mtr_t::page_flush_ahead log_close(lsn_t lsn) noexcept return mtr_t::PAGE_FLUSH_SYNC; } -std::pair mtr_t::do_write() +std::pair mtr_t::do_write(bool ex) { ut_ad(!recv_no_log_write); ut_ad(m_log_mode == MTR_LOG_ALL); + ut_ad(!ex || log_sys.latch.is_write_locked()); size_t len= m_log.size() + 5; ut_ad(len > 5); @@ -879,86 +896,93 @@ std::pair mtr_t::do_write() { m_crc= my_crc32c(m_crc, b->begin(), b->used()); return true; }); } - mysql_mutex_lock(&log_sys.mutex); + if (!ex) + log_sys.latch.rd_lock(SRW_LOCK_CALL); - if (m_user_space && !is_predefined_tablespace(m_user_space->id) && - !m_user_space->max_lsn) - name_write(); + if (UNIV_UNLIKELY(m_user_space && !m_user_space->max_lsn && + !is_predefined_tablespace(m_user_space->id))) + { + if (!ex) + { + log_sys.latch.rd_unlock(); + log_sys.latch.wr_lock(SRW_LOCK_CALL); + if (UNIV_LIKELY(!m_user_space->max_lsn)) + name_write(); + std::pair p{finish_write(len, true)}; + log_sys.latch.wr_unlock(); + log_sys.latch.rd_lock(SRW_LOCK_CALL); + return p; + } + else + name_write(); + } - return finish_write(len); + return finish_write(len, ex); } /** Write the mini-transaction log to the redo log buffer. +@param len number of bytes to write +@param ex whether log_sys.latch is exclusively locked @return {start_lsn,flush_ahead} */ -std::pair mtr_t::finish_write(size_t len) +std::pair +mtr_t::finish_write(size_t len, bool ex) { ut_ad(!recv_no_log_write); ut_ad(m_log_mode == MTR_LOG_ALL); - const lsn_t start_lsn= log_sys.append_prepare(len); const size_t size{m_commit_lsn ? 5U + 8U : 5U}; + std::pair start; if (!log_sys.is_pmem()) { - m_log.for_each_block([](const mtr_buf_t::block_t *b) - { log_sys.append(b->begin(), b->used()); return true; }); - - if (log_sys.buf_free >= log_sys.max_buf_free) - log_sys.set_check_flush_or_checkpoint(); + start= log_sys.append_prepare(len, ex); + m_log.for_each_block([&start](const mtr_buf_t::block_t *b) + { log_sys.append(start.second, b->begin(), b->used()); return true; }); #ifdef HAVE_PMEM write_trailer: #endif - log_sys.buf[log_sys.buf_free]= - log_sys.get_sequence_bit(start_lsn + len - size); + *start.second++= log_sys.get_sequence_bit(start.first + len - size); if (m_commit_lsn) { - byte *nonce= log_sys.buf + log_sys.buf_free + 1; - mach_write_to_8(nonce, m_commit_lsn); - m_crc= my_crc32c(m_crc, nonce, 8); - mach_write_to_4(&log_sys.buf[log_sys.buf_free + 9], m_crc); - log_sys.buf_free+= 8 + 5; - } - else - { - mach_write_to_4(&log_sys.buf[log_sys.buf_free + 1], m_crc); - log_sys.buf_free+= 5; + mach_write_to_8(start.second, m_commit_lsn); + m_crc= my_crc32c(m_crc, start.second, 8); + start.second+= 8; } + mach_write_to_4(start.second, m_crc); } #ifdef HAVE_PMEM - else if (UNIV_LIKELY(log_sys.buf_free + len < log_sys.file_size)) - { - m_log.for_each_block([](const mtr_buf_t::block_t *b) - { log_sys.append(b->begin(), b->used()); return true; }); - goto write_trailer; - } else { - m_log.for_each_block([](const mtr_buf_t::block_t *b) + start= log_sys.append_prepare(len, ex); + if (UNIV_LIKELY(start.second + len <= &log_sys.buf[log_sys.file_size])) + { + m_log.for_each_block([&start](const mtr_buf_t::block_t *b) + { log_sys.append(start.second, b->begin(), b->used()); return true; }); + goto write_trailer; + } + m_log.for_each_block([&start](const mtr_buf_t::block_t *b) { size_t size{b->used()}; - const size_t size_left{log_sys.file_size - log_sys.buf_free}; + const size_t size_left(&log_sys.buf[log_sys.file_size] - start.second); const byte *src= b->begin(); - if (size <= size_left) - { - ::memcpy(log_sys.buf + log_sys.buf_free, src, size); - log_sys.buf_free+= size; - } - else + if (size > size_left) { + ::memcpy(start.second, src, size_left); + start.second= &log_sys.buf[log_sys.START_OFFSET]; + src+= size_left; size-= size_left; - ::memcpy(log_sys.buf + log_sys.buf_free, src, size_left); - ::memcpy(log_sys.buf + log_sys.START_OFFSET, src + size_left, size); - log_sys.buf_free= log_sys.START_OFFSET + size; } + ::memcpy(start.second, src, size); + start.second+= size; return true; }); - const size_t size_left{log_sys.file_size - log_sys.buf_free}; + const size_t size_left(&log_sys.buf[log_sys.file_size] - start.second); if (size_left > size) goto write_trailer; byte tail[5 + 8]; - tail[0]= log_sys.get_sequence_bit(start_lsn + len - size); + tail[0]= log_sys.get_sequence_bit(start.first + len - size); if (m_commit_lsn) { @@ -969,15 +993,14 @@ std::pair mtr_t::finish_write(size_t len) else mach_write_to_4(tail + 1, m_crc); - ::memcpy(log_sys.buf + log_sys.buf_free, tail, size_left); + ::memcpy(start.second, tail, size_left); ::memcpy(log_sys.buf + log_sys.START_OFFSET, tail + size_left, size - size_left); - log_sys.buf_free= log_sys.START_OFFSET + (size - size_left); } #endif - m_commit_lsn= start_lsn + len; - return {start_lsn, log_close(m_commit_lsn)}; + m_commit_lsn= start.first + len; + return {start.first, log_close(m_commit_lsn)}; } /** Find out whether a block was not X-latched by the mini-transaction */ diff --git a/storage/innobase/srv/srv0mon.cc b/storage/innobase/srv/srv0mon.cc index 90d71556a5b..520ff7adff5 100644 --- a/storage/innobase/srv/srv0mon.cc +++ b/storage/innobase/srv/srv0mon.cc @@ -1371,6 +1371,7 @@ corresponding monitors are turned on/off/reset, and do appropriate mathematics to deduct the actual value. Please also refer to srv_export_innodb_status() for related global counters used by the existing status variables.*/ +TPOOL_SUPPRESS_TSAN void srv_mon_process_existing_counter( /*=============================*/ @@ -1405,7 +1406,7 @@ srv_mon_process_existing_counter( /* innodb_buffer_pool_write_requests, the number of write request */ case MONITOR_OVLD_BUF_POOL_WRITE_REQUEST: - value = srv_stats.buf_pool_write_requests; + value = buf_pool.flush_list_requests; break; /* innodb_buffer_pool_wait_free */ @@ -1714,10 +1715,10 @@ srv_mon_process_existing_counter( break; case MONITOR_LSN_CHECKPOINT_AGE: - mysql_mutex_lock(&log_sys.mutex); + log_sys.latch.rd_lock(SRW_LOCK_CALL); value = static_cast(log_sys.get_lsn() - log_sys.last_checkpoint_lsn); - mysql_mutex_unlock(&log_sys.mutex); + log_sys.latch.rd_unlock(); break; case MONITOR_OVLD_BUF_OLDEST_LSN: diff --git a/storage/innobase/srv/srv0srv.cc b/storage/innobase/srv/srv0srv.cc index c3c4c05c6bf..29a6316fae9 100644 --- a/storage/innobase/srv/srv0srv.cc +++ b/storage/innobase/srv/srv0srv.cc @@ -1024,9 +1024,6 @@ srv_export_innodb_status(void) export_vars.innodb_buffer_pool_read_requests = buf_pool.stat.n_page_gets; - export_vars.innodb_buffer_pool_write_requests = - srv_stats.buf_pool_write_requests; - export_vars.innodb_buffer_pool_reads = srv_stats.buf_pool_reads; export_vars.innodb_buffer_pool_read_ahead_rnd = @@ -1167,13 +1164,13 @@ srv_export_innodb_status(void) mysql_mutex_unlock(&srv_innodb_monitor_mutex); - mysql_mutex_lock(&log_sys.mutex); + log_sys.latch.rd_lock(SRW_LOCK_CALL); export_vars.innodb_lsn_current = log_sys.get_lsn(); export_vars.innodb_lsn_flushed = log_sys.get_flushed_lsn(); export_vars.innodb_lsn_last_checkpoint = log_sys.last_checkpoint_lsn; export_vars.innodb_checkpoint_max_age = static_cast( log_sys.max_checkpoint_age); - mysql_mutex_unlock(&log_sys.mutex); + log_sys.latch.rd_unlock(); export_vars.innodb_os_log_written = export_vars.innodb_lsn_current - recv_sys.lsn; @@ -1818,10 +1815,10 @@ void purge_coordinator_state::refresh(bool full) lsn_hwm= adaptive_purge_threshold + series[n_threads]; } - mysql_mutex_lock(&log_sys.mutex); + log_sys.latch.rd_lock(SRW_LOCK_CALL); const lsn_t last= log_sys.last_checkpoint_lsn, max_age= log_sys.max_checkpoint_age; - mysql_mutex_unlock(&log_sys.mutex); + log_sys.latch.rd_unlock(); lsn_age_factor= ulint(((log_sys.get_lsn() - last) * 100) / max_age); } diff --git a/storage/innobase/srv/srv0start.cc b/storage/innobase/srv/srv0start.cc index ba2628ae04c..2166bb51ab8 100644 --- a/storage/innobase/srv/srv0start.cc +++ b/storage/innobase/srv/srv0start.cc @@ -195,12 +195,8 @@ static dberr_t create_log_file(bool create_new_db, lsn_t lsn, DBUG_ASSERT(!buf_pool.any_io_pending()); - mysql_mutex_lock(&log_sys.mutex); - if (!log_set_capacity(srv_log_file_size)) { -err_exit: - mysql_mutex_unlock(&log_sys.mutex); - return DB_ERROR; - } + log_sys.latch.wr_lock(SRW_LOCK_CALL); + log_sys.set_capacity(); logfile0 = get_log_file_path(LOG_FILE_NAME_PREFIX) .append(INIT_LOG_FILE0); @@ -213,7 +209,9 @@ err_exit: if (!ret) { sql_print_error("InnoDB: Cannot create %s", logfile0.c_str()); - goto err_exit; +err_exit: + log_sys.latch.wr_unlock(); + return DB_ERROR; } ret = os_file_set_size(logfile0.c_str(), file, srv_log_file_size); @@ -244,7 +242,7 @@ err_exit: /* Enable checkpoints in buf_flush_page_cleaner(). */ recv_sys.recovery_on = false; - mysql_mutex_unlock(&log_sys.mutex); + log_sys.latch.wr_unlock(); log_make_checkpoint(); log_buffer_flush_to_disk(); @@ -801,7 +799,7 @@ static lsn_t srv_prepare_to_delete_redo_log_file() DBUG_EXECUTE_IF("innodb_log_abort_1", DBUG_RETURN(0);); DBUG_PRINT("ib_log", ("After innodb_log_abort_1")); - mysql_mutex_lock(&log_sys.mutex); + log_sys.latch.wr_lock(SRW_LOCK_CALL); const bool latest_format{log_sys.is_latest()}; lsn_t flushed_lsn{log_sys.get_lsn()}; @@ -846,7 +844,7 @@ same_size: } } - mysql_mutex_unlock(&log_sys.mutex); + log_sys.latch.wr_unlock(); log_write_up_to(flushed_lsn, false); diff --git a/storage/innobase/sync/srw_lock.cc b/storage/innobase/sync/srw_lock.cc index 71414e8ddb2..bc3ef0a7b4e 100644 --- a/storage/innobase/sync/srw_lock.cc +++ b/storage/innobase/sync/srw_lock.cc @@ -1,6 +1,6 @@ /***************************************************************************** -Copyright (c) 2020, 2021, MariaDB Corporation. +Copyright (c) 2020, 2022, MariaDB Corporation. 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 @@ -102,6 +102,13 @@ static inline void srw_pause(unsigned delay) HMT_medium(); } +void sspin_lock::lock() noexcept +{ + while (word.exchange(true, std::memory_order_acquire)) + while (word.load(std::memory_order_relaxed)) + srw_pause(1); +} + #ifdef SUX_LOCK_GENERIC template<> void srw_mutex_impl::wr_wait() { From 1b8bb44106f528f742faa19d23bd6e822be04f39 Mon Sep 17 00:00:00 2001 From: Sergei Golubchik Date: Thu, 10 Feb 2022 13:03:02 +0100 Subject: [PATCH 28/45] MDEV-26351 segfault - (MARIA_HA *) 0x0 in ha_maria::extra use the correct check. before invoking handler methods we need to know that the table was opened, not only created. --- mysql-test/r/tmp_table_error.result | 2634 ++++++++++++++++++++++++++ mysql-test/t/tmp_table_error.test | 2637 +++++++++++++++++++++++++++ sql/records.cc | 2 +- 3 files changed, 5272 insertions(+), 1 deletion(-) create mode 100644 mysql-test/r/tmp_table_error.result create mode 100644 mysql-test/t/tmp_table_error.test diff --git a/mysql-test/r/tmp_table_error.result b/mysql-test/r/tmp_table_error.result new file mode 100644 index 00000000000..c0c8b203dfb --- /dev/null +++ b/mysql-test/r/tmp_table_error.result @@ -0,0 +1,2634 @@ +call mtr.add_suppression('Index for table'); +create table t1 ( +a int primary key, +b text +) engine=innodb; +create table t2 as +select +1 +from +(select distinct +b as c0, +b as c1, +b as c2, +b as c3, +b as c4, +b as c5, +b as c6, +b as c7, +b as c8, +b as c9, +b as c10, +b as c11, +b as c12, +b as c13, +b as c14, +b as c15, +b as c16, +b as c17, +b as c18, +b as c19, +b as c20, +b as c21, +b as c22, +b as c23, +b as c24, +b as c25, +b as c26, +b as c27, +b as c28, +b as c29, +b as c30, +b as c31, +b as c32, +b as c33, +b as c34, +b as c35, +b as c36, +b as c37, +b as c38, +b as c39, +b as c40, +b as c41, +b as c42, +b as c43, +b as c45, +b as c46, +b as c47, +b as c48, +b as c49, +b as c50, +b as c51, +b as c52, +b as c53, +b as c54, +b as c55, +b as c56, +b as c57, +b as c58, +b as c59, +b as c60, +b as c61, +b as c62, +b as c63, +b as c64, +b as c65, +b as c66, +b as c67, +b as c68, +b as c69, +b as c70, +b as c71, +b as c72, +b as c73, +b as c74, +b as c75, +b as c76, +b as c77, +b as c78, +b as c79, +b as c80, +b as c81, +b as c82, +b as c83, +b as c84, +b as c85, +b as c86, +b as c87, +b as c88, +b as c89, +b as c90, +b as c91, +b as c92, +b as c93, +b as c94, +b as c95, +b as c96, +b as c97, +b as c98, +b as c99, +b as c100, +b as c101, +b as c102, +b as c103, +b as c104, +b as c105, +b as c106, +b as c107, +b as c108, +b as c109, +b as c110, +b as c111, +b as c112, +b as c113, +b as c114, +b as c115, +b as c116, +b as c117, +b as c118, +b as c119, +b as c120, +b as c121, +b as c122, +b as c123, +b as c124, +b as c125, +b as c126, +b as c127, +b as c128, +b as c129, +b as c130, +b as c131, +b as c132, +b as c133, +b as c134, +b as c135, +b as c136, +b as c137, +b as c138, +b as c139, +b as c140, +b as c141, +b as c142, +b as c143, +b as c144, +b as c145, +b as c146, +b as c147, +b as c148, +b as c149, +b as c150, +b as c151, +b as c152, +b as c153, +b as c154, +b as c155, +b as c156, +b as c157, +b as c158, +b as c159, +b as c160, +b as c161, +b as c162, +b as c163, +b as c164, +b as c165, +b as c166, +b as c167, +b as c168, +b as c169, +b as c170, +b as c171, +b as c172, +b as c173, +b as c174, +b as c175, +b as c176, +b as c177, +b as c178, +b as c179, +b as c180, +b as c181, +b as c182, +b as c183, +b as c184, +b as c185, +b as c186, +b as c187, +b as c188, +b as c189, +b as c190, +b as c191, +b as c192, +b as c193, +b as c194, +b as c195, +b as c196, +b as c197, +b as c198, +b as c199, +b as c200, +b as c201, +b as c202, +b as c203, +b as c204, +b as c205, +b as c206, +b as c207, +b as c208, +b as c209, +b as c210, +b as c211, +b as c212, +b as c213, +b as c214, +b as c215, +b as c216, +b as c217, +b as c218, +b as c219, +b as c220, +b as c221, +b as c222, +b as c223, +b as c224, +b as c225, +b as c226, +b as c227, +b as c228, +b as c229, +b as c230, +b as c231, +b as c232, +b as c233, +b as c234, +b as c235, +b as c236, +b as c237, +b as c238, +b as c239, +b as c240, +b as c241, +b as c242, +b as c243, +b as c244, +b as c245, +b as c246, +b as c247, +b as c248, +b as c249, +b as c250, +b as c251, +b as c252, +b as c253, +b as c254, +b as c255, +b as c256, +b as c257, +b as c258, +b as c259, +b as c260, +b as c261, +b as c262, +b as c263, +b as c264, +b as c265, +b as c266, +b as c267, +b as c268, +b as c269, +b as c270, +b as c271, +b as c272, +b as c273, +b as c274, +b as c275, +b as c276, +b as c277, +b as c278, +b as c279, +b as c280, +b as c281, +b as c282, +b as c283, +b as c284, +b as c285, +b as c286, +b as c287, +b as c288, +b as c289, +b as c290, +b as c291, +b as c292, +b as c293, +b as c294, +b as c295, +b as c296, +b as c297, +b as c298, +b as c299, +b as c300, +b as c301, +b as c302, +b as c303, +b as c304, +b as c305, +b as c306, +b as c307, +b as c308, +b as c309, +b as c310, +b as c311, +b as c312, +b as c313, +b as c314, +b as c315, +b as c316, +b as c317, +b as c318, +b as c319, +b as c320, +b as c321, +b as c322, +b as c323, +b as c324, +b as c325, +b as c326, +b as c327, +b as c328, +b as c329, +b as c330, +b as c331, +b as c332, +b as c333, +b as c334, +b as c335, +b as c336, +b as c337, +b as c338, +b as c339, +b as c340, +b as c341, +b as c342, +b as c343, +b as c344, +b as c345, +b as c346, +b as c347, +b as c348, +b as c349, +b as c350, +b as c351, +b as c352, +b as c353, +b as c354, +b as c355, +b as c356, +b as c357, +b as c358, +b as c359, +b as c360, +b as c361, +b as c362, +b as c363, +b as c364, +b as c365, +b as c366, +b as c367, +b as c368, +b as c369, +b as c370, +b as c371, +b as c372, +b as c373, +b as c374, +b as c375, +b as c376, +b as c377, +b as c378, +b as c379, +b as c380, +b as c381, +b as c382, +b as c383, +b as c384, +b as c385, +b as c386, +b as c387, +b as c388, +b as c389, +b as c390, +b as c391, +b as c392, +b as c393, +b as c394, +b as c395, +b as c396, +b as c397, +b as c398, +b as c399, +b as c400, +b as c401, +b as c402, +b as c403, +b as c404, +b as c405, +b as c406, +b as c407, +b as c409, +b as c410, +b as c411, +b as c412, +b as c413, +b as c414, +b as c415, +b as c416, +b as c417, +b as c418, +b as c419, +b as c420, +b as c421, +b as c422, +b as c423, +b as c424, +b as c425, +b as c426, +b as c427, +b as c428, +b as c429, +b as c430, +b as c431, +b as c432, +b as c433, +b as c434, +b as c435, +b as c436, +b as c437, +b as c438, +b as c439, +b as c440, +b as c441, +b as c442, +b as c443, +b as c444, +b as c445, +b as c446, +b as c447, +b as c448, +b as c449, +b as c450, +b as c451, +b as c452, +b as c453, +b as c454, +b as c455, +b as c456, +b as c457, +b as c458, +b as c459, +b as c460, +b as c461, +b as c462, +b as c463, +b as c464, +b as c465, +b as c466, +b as c467, +b as c468, +b as c469, +b as c470, +b as c471, +b as c472, +b as c473, +b as c474, +b as c475, +b as c476, +b as c477, +b as c478, +b as c479, +b as c480, +b as c481, +b as c482, +b as c483, +b as c484, +b as c485, +b as c486, +b as c487, +b as c488, +b as c489, +b as c490, +b as c491, +b as c492, +b as c493, +b as c494, +b as c495, +b as c496, +b as c497, +b as c498, +b as c499, +b as c500, +b as c501, +b as c502, +b as c503, +b as c504, +b as c505, +b as c506, +b as c507, +b as c508, +b as c509, +b as c510, +b as c511, +b as c512, +b as c513, +b as c514, +b as c515, +b as c516, +b as c517, +b as c518, +b as c519, +b as c520, +b as c521, +b as c522, +b as c523, +b as c524, +b as c525, +b as c526, +b as c527, +b as c528, +b as c529, +b as c530, +b as c531, +b as c532, +b as c533, +b as c534, +b as c535, +b as c536, +b as c537, +b as c538, +b as c539, +b as c540, +b as c541, +b as c542, +b as c543, +b as c544, +b as c545, +b as c546, +b as c547, +b as c548, +b as c549, +b as c550, +b as c551, +b as c552, +b as c553, +b as c554, +b as c555, +b as c556, +b as c557, +b as c558, +b as c559, +b as c560, +b as c561, +b as c562, +b as c563, +b as c564, +b as c565, +b as c566, +b as c567, +b as c568, +b as c569, +b as c570, +b as c571, +b as c572, +b as c573, +b as c574, +b as c575, +b as c576, +b as c577, +b as c578, +b as c579, +b as c580, +b as c581, +b as c582, +b as c583, +b as c584, +b as c585, +b as c586, +b as c587, +b as c588, +b as c589, +b as c590, +b as c591, +b as c592, +b as c593, +b as c594, +b as c595, +b as c596, +b as c597, +b as c598, +b as c599, +b as c600, +b as c601, +b as c602, +b as c603, +b as c604, +b as c605, +b as c606, +b as c607, +b as c608, +b as c609, +b as c610, +b as c611, +b as c612, +b as c613, +b as c614, +b as c615, +b as c616, +b as c617, +b as c618, +b as c619, +b as c620, +b as c621, +b as c622, +b as c623, +b as c624, +b as c625, +b as c626, +b as c627, +b as c628, +b as c629, +b as c630, +b as c631, +b as c632, +b as c633, +b as c634, +b as c635, +b as c636, +b as c637, +b as c638, +b as c639, +b as c640, +b as c641, +b as c642, +b as c643, +b as c644, +b as c645, +b as c646, +b as c647, +b as c648, +b as c649, +b as c650, +b as c651, +b as c652, +b as c653, +b as c654, +b as c655, +b as c656, +b as c657, +b as c658, +b as c659, +b as c660, +b as c661, +b as c662, +b as c663, +b as c664, +b as c665, +b as c666, +b as c667, +b as c668, +b as c669, +b as c670, +b as c671, +b as c672, +b as c673, +b as c674, +b as c675, +b as c676, +b as c677, +b as c678, +b as c679, +b as c680, +b as c681, +b as c682, +b as c683, +b as c684, +b as c685, +b as c686, +b as c687, +b as c688, +b as c689, +b as c690, +b as c691, +b as c692, +b as c693, +b as c694, +b as c695, +b as c696, +b as c697, +b as c698, +b as c699, +b as c700, +b as c701, +b as c702, +b as c703, +b as c704, +b as c705, +b as c706, +b as c707, +b as c708, +b as c709, +b as c710, +b as c711, +b as c712, +b as c713, +b as c714, +b as c715, +b as c716, +b as c717, +b as c718, +b as c719, +b as c720, +b as c721, +b as c722, +b as c723, +b as c724, +b as c725, +b as c726, +b as c727, +b as c728, +b as c729, +b as c730, +b as c731, +b as c732, +b as c733, +b as c734, +b as c735, +b as c736, +b as c737, +b as c738, +b as c739, +b as c740, +b as c741, +b as c742, +b as c743, +b as c744, +b as c745, +b as c746, +b as c747, +b as c748, +b as c749, +b as c750, +b as c751, +b as c752, +b as c753, +b as c754, +b as c755, +b as c756, +b as c757, +b as c758, +b as c759, +b as c760, +b as c761, +b as c762, +b as c763, +b as c764, +b as c765, +b as c766, +b as c767, +b as c768, +b as c769, +b as c770, +b as c771, +b as c772, +b as c773, +b as c774, +b as c775, +b as c776, +b as c777, +b as c778, +b as c779, +b as c780, +b as c781, +b as c782, +b as c783, +b as c784, +b as c785, +b as c786, +b as c787, +b as c788, +b as c789, +b as c790, +b as c791, +b as c792, +b as c793, +b as c794, +b as c795, +b as c796, +b as c797, +b as c798, +b as c799, +b as c800, +b as c801, +b as c802, +b as c803, +b as c804, +b as c805, +b as c806, +b as c807, +b as c808, +b as c809, +b as c810, +b as c811, +b as c812, +b as c813, +b as c814, +b as c815, +b as c816, +b as c817, +b as c818, +b as c819, +b as c820, +b as c821, +b as c822, +b as c823, +b as c824, +b as c825, +b as c826, +b as c827, +b as c828, +b as c829, +b as c830, +b as c831, +b as c832, +b as c833, +b as c834, +b as c835, +b as c836, +b as c837, +b as c838, +b as c839, +b as c840, +b as c841, +b as c842, +b as c843, +b as c844, +b as c845, +b as c846, +b as c847, +b as c848, +b as c849, +b as c850, +b as c851, +b as c852, +b as c853, +b as c854, +b as c855, +b as c856, +b as c857, +b as c858, +b as c859, +b as c860, +b as c861, +b as c862, +b as c863, +b as c864, +b as c865, +b as c866, +b as c867, +b as c868, +b as c869, +b as c870, +b as c871, +b as c872, +b as c873, +b as c874, +b as c875, +b as c876, +b as c877, +b as c878, +b as c879, +b as c880, +b as c881, +b as c882, +b as c883, +b as c884, +b as c885, +b as c886, +b as c887, +b as c888, +b as c889, +b as c890, +b as c891, +b as c892, +b as c893, +b as c894, +b as c895, +b as c897, +b as c898, +b as c899, +b as c900, +b as c901, +b as c902, +b as c903, +b as c904, +b as c905, +b as c906, +b as c907, +b as c908, +b as c909, +b as c910, +b as c911, +b as c912, +b as c913, +b as c914, +b as c915, +b as c916, +b as c917, +b as c918, +b as c919, +b as c920, +b as c921, +b as c922, +b as c923, +b as c924, +b as c925, +b as c926, +b as c927, +b as c928, +b as c929, +b as c930, +b as c931, +b as c932, +b as c933, +b as c934, +b as c935, +b as c936, +b as c937, +b as c938, +b as c939, +b as c940, +b as c941, +b as c942, +b as c943, +b as c944, +b as c945, +b as c946, +b as c947, +b as c948, +b as c949, +b as c950, +b as c951, +b as c952, +b as c953, +b as c954, +b as c955, +b as c956, +b as c957, +b as c958, +b as c959, +b as c960, +b as c961, +b as c962, +b as c963, +b as c964, +b as c965, +b as c966, +b as c967, +b as c968, +b as c969, +b as c970, +b as c971, +b as c972, +b as c973, +b as c974, +b as c975, +b as c976, +b as c977, +b as c978, +b as c979, +b as c980, +b as c981, +b as c982, +b as c983, +b as c984, +b as c985, +b as c986, +b as c987, +b as c988, +b as c989, +b as c990, +b as c991, +b as c992, +b as c993, +b as c995, +b as c996, +b as c997, +b as c998, +b as c999, +b as c1000, +b as c1001, +b as c1002, +b as c1003, +b as c1004, +b as c1005, +b as c1006, +b as c1007, +b as c1008, +b as c1009, +b as c1010, +b as c1011, +b as c1012, +b as c1013, +b as c1014, +b as c1015, +b as c1016, +b as c1017, +b as c1018, +b as c1019, +b as c1020, +b as c1021, +b as c1022, +b as c1023, +b as c1024, +b as c1025, +b as c1026, +b as c1027, +b as c1028, +b as c1029, +b as c1030, +b as c1031, +b as c1032, +b as c1033, +b as c1034, +b as c1035, +b as c1036, +b as c1037, +b as c1038, +b as c1039, +b as c1040, +b as c1041, +b as c1042, +b as c1043, +b as c1044, +b as c1045, +b as c1046, +b as c1047, +b as c1048, +b as c1049, +b as c1050, +b as c1051, +b as c1052, +b as c1053, +b as c1054, +b as c1055, +b as c1056, +b as c1057, +b as c1058, +b as c1059, +b as c1060, +b as c1061, +b as c1062, +b as c1063, +b as c1064, +b as c1065, +b as c1066, +b as c1067, +b as c1068, +b as c1069, +b as c1070, +b as c1071, +b as c1072, +b as c1073, +b as c1074, +b as c1075, +b as c1076, +b as c1077, +b as c1078, +b as c1079, +b as c1080, +b as c1081, +b as c1082, +b as c1083, +b as c1084, +b as c1085, +b as c1086, +b as c1087, +b as c1088, +b as c1089, +b as c1090, +b as c1091, +b as c1092, +b as c1093, +b as c1094, +b as c1095, +b as c1096, +b as c1097, +b as c1098, +b as c1099, +b as c1100, +b as c1101, +b as c1102, +b as c1103, +b as c1104, +b as c1105, +b as c1106, +b as c1107, +b as c1108, +b as c1109, +b as c1110, +b as c1111, +b as c1112, +b as c1113, +b as c1114, +b as c1115, +b as c1116, +b as c1117, +b as c1118, +b as c1119, +b as c1120, +b as c1121, +b as c1122, +b as c1123, +b as c1124, +b as c1125, +b as c1126, +b as c1127, +b as c1128, +b as c1129, +b as c1130, +b as c1131, +b as c1132, +b as c1133, +b as c1134, +b as c1135, +b as c1136, +b as c1137, +b as c1138, +b as c1139, +b as c1140, +b as c1141, +b as c1142, +b as c1143, +b as c1144, +b as c1145, +b as c1146, +b as c1147, +b as c1148, +b as c1149, +b as c1150, +b as c1151, +b as c1152, +b as c1153, +b as c1154, +b as c1155, +b as c1156, +b as c1157, +b as c1158, +b as c1159, +b as c1160, +b as c1161, +b as c1162, +b as c1163, +b as c1164, +b as c1165, +b as c1166, +b as c1167, +b as c1168, +b as c1169, +b as c1170, +b as c1171, +b as c1172, +b as c1173, +b as c1174, +b as c1175, +b as c1176, +b as c1177, +b as c1178, +b as c1179, +b as c1180, +b as c1181, +b as c1182, +b as c1183, +b as c1184, +b as c1185, +b as c1186, +b as c1187, +b as c1188, +b as c1189, +b as c1190, +b as c1191, +b as c1192, +b as c1193, +b as c1194, +b as c1195, +b as c1196, +b as c1197, +b as c1198, +b as c1199, +b as c1200, +b as c1201, +b as c1202, +b as c1203, +b as c1204, +b as c1205, +b as c1206, +b as c1207, +b as c1208, +b as c1209, +b as c1210, +b as c1211, +b as c1212, +b as c1213, +b as c1214, +b as c1215, +b as c1216, +b as c1217, +b as c1218, +b as c1219, +b as c1220, +b as c1221, +b as c1222, +b as c1223, +b as c1224, +b as c1225, +b as c1226, +b as c1227, +b as c1228, +b as c1229, +b as c1230, +b as c1231, +b as c1232, +b as c1233, +b as c1234, +b as c1235, +b as c1236, +b as c1237, +b as c1238, +b as c1239, +b as c1240, +b as c1241, +b as c1242, +b as c1243, +b as c1244, +b as c1245, +b as c1246, +b as c1247, +b as c1248, +b as c1249, +b as c1250, +b as c1251, +b as c1252, +b as c1253, +b as c1254, +b as c1255, +b as c1256, +b as c1257, +b as c1258, +b as c1259, +b as c1260, +b as c1261, +b as c1262, +b as c1263, +b as c1264, +b as c1265, +b as c1266, +b as c1267, +b as c1268, +b as c1269, +b as c1270, +b as c1271, +b as c1272, +b as c1273, +b as c1274, +b as c1275, +b as c1276, +b as c1277, +b as c1278, +b as c1279, +b as c1280, +b as c1281, +b as c1282, +b as c1283, +b as c1284, +b as c1285, +b as c1286, +b as c1287, +b as c1288, +b as c1289, +b as c1290, +b as c1291, +b as c1292, +b as c1293, +b as c1294, +b as c1295, +b as c1296, +b as c1297, +b as c1298, +b as c1299, +b as c1300, +b as c1301, +b as c1302, +b as c1303, +b as c1304, +b as c1305, +b as c1306, +b as c1307, +b as c1308, +b as c1309, +b as c1310, +b as c1311, +b as c1312, +b as c1313, +b as c1314, +b as c1315, +b as c1316, +b as c1317, +b as c1318, +b as c1319, +b as c1320, +b as c1321, +b as c1322, +b as c1323, +b as c1324, +b as c1325, +b as c1326, +b as c1327, +b as c1328, +b as c1329, +b as c1330, +b as c1331, +b as c1332, +b as c1333, +b as c1334, +b as c1335, +b as c1336, +b as c1337, +b as c1338, +b as c1339, +b as c1340, +b as c1341, +b as c1342, +b as c1343, +b as c1344, +b as c1345, +b as c1346, +b as c1347, +b as c1348, +b as c1349, +b as c1350, +b as c1351, +b as c1352, +b as c1353, +b as c1354, +b as c1355, +b as c1356, +b as c1357, +b as c1358, +b as c1359, +b as c1360, +b as c1361, +b as c1362, +b as c1363, +b as c1364, +b as c1365, +b as c1366, +b as c1367, +b as c1368, +b as c1369, +b as c1370, +b as c1371, +b as c1372, +b as c1373, +b as c1374, +b as c1375, +b as c1376, +b as c1377, +b as c1378, +b as c1379, +b as c1380, +b as c1381, +b as c1382, +b as c1383, +b as c1384, +b as c1385, +b as c1386, +b as c1387, +b as c1388, +b as c1389, +b as c1390, +b as c1391, +b as c1392, +b as c1393, +b as c1394, +b as c1395, +b as c1396, +b as c1397, +b as c1398, +b as c1399, +b as c1400, +b as c1401, +b as c1402, +b as c1403, +b as c1404, +b as c1405, +b as c1406, +b as c1407, +b as c1408, +b as c1409, +b as c1410, +b as c1411, +b as c1412, +b as c1413, +b as c1414, +b as c1415, +b as c1416, +b as c1417, +b as c1418, +b as c1419, +b as c1420, +b as c1421, +b as c1422, +b as c1423, +b as c1424, +b as c1425, +b as c1426, +b as c1427, +b as c1428, +b as c1429, +b as c1430, +b as c1431, +b as c1432, +b as c1433, +b as c1434, +b as c1435, +b as c1436, +b as c1437, +b as c1438, +b as c1439, +b as c1440, +b as c1441, +b as c1442, +b as c1443, +b as c1444, +b as c1445, +b as c1446, +b as c1447, +b as c1448, +b as c1449, +b as c1451, +b as c1452, +b as c1453, +b as c1454, +b as c1455, +b as c1456, +b as c1457, +b as c1458, +b as c1459, +b as c1460, +b as c1461, +b as c1462, +b as c1463, +b as c1464, +b as c1465, +b as c1466, +b as c1467, +b as c1468, +b as c1469, +b as c1470, +b as c1471, +b as c1472, +b as c1473, +b as c1474, +b as c1475, +b as c1476, +b as c1477, +b as c1478, +b as c1479, +b as c1480, +b as c1481, +b as c1482, +b as c1483, +b as c1484, +b as c1485, +b as c1486, +b as c1487, +b as c1488, +b as c1489, +b as c1490, +b as c1491, +b as c1492, +b as c1493, +b as c1494, +b as c1495, +b as c1496, +b as c1497, +b as c1498, +b as c1499, +b as c1500, +b as c1501, +b as c1502, +b as c1503, +b as c1504, +b as c1505, +b as c1506, +b as c1507, +b as c1508, +b as c1509, +b as c1510, +b as c1511, +b as c1512, +b as c1513, +b as c1514, +b as c1515, +b as c1516, +b as c1517, +b as c1518, +b as c1519, +b as c1520, +b as c1521, +b as c1522, +b as c1523, +b as c1524, +b as c1525, +b as c1526, +b as c1527, +b as c1528, +b as c1529, +b as c1530, +b as c1531, +b as c1532, +b as c1533, +b as c1534, +b as c1535, +b as c1536, +b as c1537, +b as c1538, +b as c1539, +b as c1540, +b as c1541, +b as c1542, +b as c1543, +b as c1544, +b as c1545, +b as c1546, +b as c1547, +b as c1548, +b as c1549, +b as c1550, +b as c1551, +b as c1552, +b as c1553, +b as c1554, +b as c1555, +b as c1556, +b as c1557, +b as c1558, +b as c1559, +b as c1560, +b as c1561, +b as c1562, +b as c1563, +b as c1564, +b as c1565, +b as c1566, +b as c1567, +b as c1568, +b as c1569, +b as c1570, +b as c1571, +b as c1572, +b as c1573, +b as c1574, +b as c1575, +b as c1576, +b as c1577, +b as c1578, +b as c1579, +b as c1580, +b as c1581, +b as c1582, +b as c1583, +b as c1584, +b as c1585, +b as c1586, +b as c1587, +b as c1588, +b as c1589, +b as c1590, +b as c1591, +b as c1592, +b as c1593, +b as c1594, +b as c1595, +b as c1596, +b as c1597, +b as c1598, +b as c1599, +b as c1600, +b as c1601, +b as c1602, +b as c1603, +b as c1604, +b as c1605, +b as c1606, +b as c1607, +b as c1608, +b as c1609, +b as c1610, +b as c1611, +b as c1612, +b as c1613, +b as c1614, +b as c1615, +b as c1616, +b as c1617, +b as c1618, +b as c1619, +b as c1620, +b as c1621, +b as c1622, +b as c1623, +b as c1624, +b as c1625, +b as c1626, +b as c1627, +b as c1628, +b as c1629, +b as c1630, +b as c1631, +b as c1632, +b as c1633, +b as c1634, +b as c1635, +b as c1636, +b as c1637, +b as c1638, +b as c1639, +b as c1640, +b as c1641, +b as c1642, +b as c1643, +b as c1644, +b as c1645, +b as c1646, +b as c1647, +b as c1648, +b as c1649, +b as c1650, +b as c1651, +b as c1652, +b as c1653, +b as c1654, +b as c1655, +b as c1656, +b as c1657, +b as c1658, +b as c1659, +b as c1660, +b as c1661, +b as c1662, +b as c1663, +b as c1664, +b as c1665, +b as c1666, +b as c1667, +b as c1668, +b as c1669, +b as c1670, +b as c1671, +b as c1672, +b as c1673, +b as c1674, +b as c1675, +b as c1676, +b as c1677, +b as c1678, +b as c1679, +b as c1680, +b as c1681, +b as c1682, +b as c1683, +b as c1684, +b as c1685, +b as c1686, +b as c1687, +b as c1688, +b as c1689, +b as c1690, +b as c1691, +b as c1692, +b as c1693, +b as c1694, +b as c1695, +b as c1696, +b as c1697, +b as c1698, +b as c1699, +b as c1700, +b as c1701, +b as c1702, +b as c1703, +b as c1704, +b as c1705, +b as c1706, +b as c1707, +b as c1708, +b as c1709, +b as c1710, +b as c1711, +b as c1712, +b as c1713, +b as c1714, +b as c1715, +b as c1716, +b as c1717, +b as c1718, +b as c1719, +b as c1720, +b as c1721, +b as c1722, +b as c1723, +b as c1724, +b as c1725, +b as c1726, +b as c1727, +b as c1728, +b as c1729, +b as c1730, +b as c1731, +b as c1732, +b as c1733, +b as c1734, +b as c1735, +b as c1736, +b as c1737, +b as c1738, +b as c1739, +b as c1740, +b as c1741, +b as c1742, +b as c1743, +b as c1744, +b as c1745, +b as c1746, +b as c1747, +b as c1748, +b as c1749, +b as c1750, +b as c1751, +b as c1752, +b as c1753, +b as c1754, +b as c1755, +b as c1756, +b as c1757, +b as c1758, +b as c1759, +b as c1760, +b as c1761, +b as c1762, +b as c1763, +b as c1764, +b as c1765, +b as c1766, +b as c1767, +b as c1768, +b as c1769, +b as c1770, +b as c1771, +b as c1772, +b as c1773, +b as c1774, +b as c1775, +b as c1776, +b as c1777, +b as c1778, +b as c1779, +b as c1780, +b as c1781, +b as c1782, +b as c1783, +b as c1784, +b as c1785, +b as c1786, +b as c1787, +b as c1788, +b as c1789, +b as c1790, +b as c1791, +b as c1792, +b as c1793, +b as c1794, +b as c1795, +b as c1796, +b as c1797, +b as c1798, +b as c1799, +b as c1800, +b as c1801, +b as c1802, +b as c1803, +b as c1804, +b as c1805, +b as c1806, +b as c1807, +b as c1808, +b as c1809, +b as c1810, +b as c1811, +b as c1812, +b as c1813, +b as c1814, +b as c1815, +b as c1816, +b as c1817, +b as c1818, +b as c1819, +b as c1820, +b as c1821, +b as c1822, +b as c1823, +b as c1824, +b as c1825, +b as c1826, +b as c1827, +b as c1828, +b as c1829, +b as c1830, +b as c1831, +b as c1832, +b as c1833, +b as c1834, +b as c1835, +b as c1836, +b as c1837, +b as c1838, +b as c1839, +b as c1840, +b as c1841, +b as c1842, +b as c1843, +b as c1844, +b as c1845, +b as c1846, +b as c1847, +b as c1848, +b as c1849, +b as c1850, +b as c1851, +b as c1852, +b as c1853, +b as c1854, +b as c1855, +b as c1856, +b as c1857, +b as c1858, +b as c1859, +b as c1860, +b as c1861, +b as c1862, +b as c1863, +b as c1864, +b as c1865, +b as c1866, +b as c1867, +b as c1868, +b as c1869, +b as c1870, +b as c1871, +b as c1872, +b as c1873, +b as c1874, +b as c1875, +b as c1876, +b as c1877, +b as c1878, +b as c1879, +b as c1880, +b as c1881, +b as c1882, +b as c1883, +b as c1884, +b as c1885, +b as c1886, +b as c1887, +b as c1888, +b as c1889, +b as c1890, +b as c1891, +b as c1892, +b as c1893, +b as c1894, +b as c1895, +b as c1896, +b as c1897, +b as c1898, +b as c1899, +b as c1900, +b as c1901, +b as c1902, +b as c1903, +b as c1904, +b as c1905, +b as c1906, +b as c1907, +b as c1908, +b as c1909, +b as c1910, +b as c1911, +b as c1912, +b as c1913, +b as c1914, +b as c1915, +b as c1916, +b as c1917, +b as c1918, +b as c1919, +b as c1920, +b as c1921, +b as c1922, +b as c1923, +b as c1924, +b as c1925, +b as c1926, +b as c1927, +b as c1928, +b as c1929, +b as c1930, +b as c1931, +b as c1932, +b as c1933, +b as c1934, +b as c1935, +b as c1936, +b as c1937, +b as c1938, +b as c1939, +b as c1940, +b as c1941, +b as c1942, +b as c1943, +b as c1944, +b as c1945, +b as c1946, +b as c1947, +b as c1948, +b as c1949, +b as c1950, +b as c1951, +b as c1952, +b as c1953, +b as c1954, +b as c1955, +b as c1956, +b as c1957, +b as c1958, +b as c1959, +b as c1960, +b as c1961, +b as c1962, +b as c1963, +b as c1964, +b as c1965, +b as c1966, +b as c1967, +b as c1968, +b as c1969, +b as c1970, +b as c1971, +b as c1972, +b as c1973, +b as c1974, +b as c1975, +b as c1976, +b as c1977, +b as c1978, +b as c1979, +b as c1980, +b as c1981, +b as c1982, +b as c1983, +b as c1984, +b as c1985, +b as c1986, +b as c1987, +b as c1988, +b as c1989, +b as c1990, +b as c1991, +b as c1992, +b as c1993, +b as c1994, +b as c1995, +b as c1996, +b as c1997, +b as c1998, +b as c1999, +b as c2000, +b as c2001, +b as c2002, +b as c2003, +b as c2004, +b as c2005, +b as c2006, +b as c2007, +b as c2008, +b as c2009, +b as c2010, +b as c2011, +b as c2012, +b as c2013, +b as c2014, +b as c2015, +b as c2016, +b as c2017, +b as c2018, +b as c2019, +b as c2020, +b as c2021, +b as c2022, +b as c2023, +b as c2024, +b as c2025, +b as c2026, +b as c2027, +b as c2028, +b as c2029, +b as c2030, +b as c2031, +b as c2032, +b as c2033, +b as c2034, +b as c2035, +b as c2036, +b as c2037, +b as c2038, +b as c2039, +b as c2040, +b as c2041, +b as c2042, +b as c2043, +b as c2044, +b as c2045, +b as c2046, +b as c2047, +b as c2048, +b as c2049, +b as c2050, +b as c2051, +b as c2052, +b as c2053, +b as c2054, +b as c2055, +b as c2056, +b as c2057, +b as c2058, +b as c2059, +b as c2060, +b as c2061, +b as c2062, +b as c2063, +b as c2064, +b as c2065, +b as c2066, +b as c2067, +b as c2068, +b as c2069, +b as c2070, +b as c2071, +b as c2072, +b as c2073, +b as c2074, +b as c2075, +b as c2076, +b as c2077, +b as c2078, +b as c2079, +b as c2080, +b as c2081, +b as c2082, +b as c2083, +b as c2084, +b as c2085, +b as c2086, +b as c2087, +b as c2088, +b as c2089, +b as c2090, +b as c2091, +b as c2092, +b as c2093, +b as c2094, +b as c2095, +b as c2096, +b as c2097, +b as c2098, +b as c2099, +b as c2100, +b as c2101, +b as c2102, +b as c2103, +b as c2104, +b as c2105, +b as c2106, +b as c2107, +b as c2108, +b as c2109, +b as c2110, +b as c2111, +b as c2112, +b as c2113, +b as c2114, +b as c2115, +b as c2116, +b as c2117, +b as c2118, +b as c2119, +b as c2120, +b as c2121, +b as c2122, +b as c2123, +b as c2124, +b as c2125, +b as c2126, +b as c2127, +b as c2128, +b as c2129, +b as c2130, +b as c2131, +b as c2132, +b as c2133, +b as c2134, +b as c2135, +b as c2136, +b as c2137, +b as c2138, +b as c2139, +b as c2140, +b as c2141, +b as c2142, +b as c2143, +b as c2144, +b as c2145, +b as c2146, +b as c2147, +b as c2148, +b as c2149, +b as c2150, +b as c2151, +b as c2152, +b as c2153, +b as c2154, +b as c2155, +b as c2156, +b as c2157, +b as c2158, +b as c2159, +b as c2160, +b as c2161, +b as c2162, +b as c2163, +b as c2164, +b as c2165, +b as c2166, +b as c2167, +b as c2168, +b as c2169, +b as c2170, +b as c2171, +b as c2172, +b as c2173, +b as c2174, +b as c2175, +b as c2176, +b as c2177, +b as c2178, +b as c2179, +b as c2180, +b as c2181, +b as c2182, +b as c2183, +b as c2184, +b as c2185, +b as c2186, +b as c2187, +b as c2188, +b as c2189, +b as c2190, +b as c2191, +b as c2192, +b as c2193, +b as c2194, +b as c2195, +b as c2196, +b as c2197, +b as c2198, +b as c2199, +b as c2200, +b as c2201, +b as c2202, +b as c2203, +b as c2204, +b as c2205, +b as c2206, +b as c2207, +b as c2208, +b as c2209, +b as c2210, +b as c2211, +b as c2212, +b as c2213, +b as c2214, +b as c2215, +b as c2216, +b as c2217, +b as c2218, +b as c2219, +b as c2220, +b as c2221, +b as c2222, +b as c2223, +b as c2224, +b as c2225, +b as c2226, +b as c2227, +b as c2228, +b as c2229, +b as c2230, +b as c2231, +b as c2232, +b as c2233, +b as c2234, +b as c2235, +b as c2236, +b as c2237, +b as c2238, +b as c2239, +b as c2240, +b as c2241, +b as c2242, +b as c2243, +b as c2244, +b as c2245, +b as c2246, +b as c2247, +b as c2248, +b as c2249, +b as c2250, +b as c2251, +b as c2252, +b as c2253, +b as c2254, +b as c2255, +b as c2256, +b as c2257, +b as c2258, +b as c2259, +b as c2260, +b as c2261, +b as c2262, +b as c2263, +b as c2264, +b as c2265, +b as c2266, +b as c2267, +b as c2268, +b as c2269, +b as c2270, +b as c2271, +b as c2272, +b as c2273, +b as c2274, +b as c2275, +b as c2276, +b as c2277, +b as c2278, +b as c2279, +b as c2280, +b as c2281, +b as c2282, +b as c2283, +b as c2284, +b as c2285, +b as c2286, +b as c2287, +b as c2288, +b as c2289, +b as c2290, +b as c2291, +b as c2292, +b as c2293, +b as c2294, +b as c2295, +b as c2296, +b as c2297, +b as c2298, +b as c2299, +b as c2300, +b as c2301, +b as c2302, +b as c2303, +b as c2304, +b as c2305, +b as c2306, +b as c2307, +b as c2308, +b as c2309, +b as c2310, +b as c2311, +b as c2312, +b as c2313, +b as c2314, +b as c2315, +b as c2316, +b as c2317, +b as c2318, +b as c2319, +b as c2320, +b as c2321, +b as c2322, +b as c2323, +b as c2324, +b as c2325, +b as c2326, +b as c2327, +b as c2328, +b as c2329, +b as c2330, +b as c2331, +b as c2332, +b as c2333, +b as c2334, +b as c2335, +b as c2336, +b as c2337, +b as c2338, +b as c2339, +b as c2340, +b as c2341, +b as c2342, +b as c2343, +b as c2344, +b as c2345, +b as c2346, +b as c2347, +b as c2348, +b as c2349, +b as c2350, +b as c2351, +b as c2352, +b as c2353, +b as c2354, +b as c2355, +b as c2356, +b as c2357, +b as c2358, +b as c2359, +b as c2360, +b as c2361, +b as c2362, +b as c2363, +b as c2364, +b as c2365, +b as c2366, +b as c2367, +b as c2368, +b as c2369, +b as c2370, +b as c2371, +b as c2372, +b as c2373, +b as c2374, +b as c2375, +b as c2376, +b as c2377, +b as c2378, +b as c2379, +b as c2380, +b as c2381, +b as c2382, +b as c2383, +b as c2384, +b as c2385, +b as c2386, +b as c2387, +b as c2388, +b as c2389, +b as c2390, +b as c2391, +b as c2392, +b as c2393, +b as c2394, +b as c2395, +b as c2396, +b as c2397, +b as c2398, +b as c2399, +b as c2400, +b as c2401, +b as c2402, +b as c2403, +b as c2404, +b as c2405, +b as c2406, +b as c2407, +b as c2408, +b as c2409, +b as c2410, +b as c2411, +b as c2412, +b as c2413, +b as c2414, +b as c2415, +b as c2416, +b as c2417, +b as c2418, +b as c2419, +b as c2420, +b as c2421, +b as c2422, +b as c2423, +b as c2424, +b as c2425, +b as c2426, +b as c2427, +b as c2428, +b as c2429, +b as c2430, +b as c2431, +b as c2432, +b as c2433, +b as c2434, +b as c2435, +b as c2436, +b as c2437, +b as c2438, +b as c2439, +b as c2440, +b as c2441, +b as c2442, +b as c2443, +b as c2444, +b as c2445, +b as c2446, +b as c2447, +b as c2448, +b as c2449, +b as c2450, +b as c2451, +b as c2452, +b as c2453, +b as c2454, +b as c2455, +b as c2456, +b as c2457, +b as c2458, +b as c2459, +b as c2460, +b as c2461, +b as c2462, +b as c2463, +b as c2464, +b as c2465, +b as c2466, +b as c2467, +b as c2468, +b as c2469, +b as c2470, +b as c2471, +b as c2472, +b as c2473, +b as c2474, +b as c2475, +b as c2476, +b as c2477, +b as c2478, +b as c2479, +b as c2480, +b as c2481, +b as c2482, +b as c2483, +b as c2484, +b as c2485, +b as c2486, +b as c2487, +b as c2488, +b as c2489, +b as c2490, +b as c2491, +b as c2492, +b as c2493, +b as c2494, +b as c2495, +b as c2496, +b as c2497, +b as c2498, +b as c2499, +b as c2500, +b as c2501, +b as c2503, +b as c2504, +b as c2505, +b as c2506, +b as c2507, +b as c2508, +b as c2509, +b as c2510, +b as c2511, +b as c2512, +b as c2513, +b as c2514, +b as c2515, +b as c2516, +b as c2517, +b as c2518, +b as c2519, +b as c2520, +b as c2521, +b as c2522, +b as c2523, +b as c2524, +b as c2525, +b as c2526, +b as c2527, +b as c2528, +b as c2529, +b as c2530, +b as c2531, +b as c2532, +b as c2533, +b as c2534, +b as c2535, +b as c2536, +b as c2537, +b as c2538, +b as c2539, +b as c2540, +b as c2541, +b as c2542, +b as c2543, +b as c2544, +b as c2545, +b as c2546, +b as c2547, +b as c2548, +b as c2549, +b as c2550, +b as c2551, +b as c2552, +b as c2553, +b as c2554, +b as c2555, +b as c2556, +b as c2557, +b as c2558, +b as c2559, +b as c2560, +b as c2561, +b as c2562, +b as c2563, +b as c2564, +b as c2565, +b as c2566, +b as c2567, +b as c2568, +b as c2569, +b as c2570, +b as c2571, +b as c2572, +b as c2573, +b as c2574, +b as c2575, +b as c2576, +b as c2577, +b as c2578, +b as c2579, +b as c2580, +b as c2581, +b as c2582, +b as c2583, +b as c2584, +b as c2585, +b as c2586, +b as c2587, +b as c2588, +b as c2589, +b as c2590, +b as c2591, +b as c2592, +b as c2593, +b as c2594, +b as c2595, +b as c2596, +b as c2597, +b as c2598, +b as c2599, +b as c2600, +b as c2601, +b as c2602, +b as c2603, +b as c2604, +b as c2605, +b as c2606, +b as c2607, +b as c2608, +b as c2609, +b as c2610, +b as c2611, +b as c2612, +b as c2613, +b as c2614, +b as c2615, +b as c2616, +b as c2617, +b as c2618, +b as c2619, +b as c2620, +b as c2621, +b as c2622, +b as c2623, +b as c2624, +b as c2626 +from t1 +) as tt1; +ERROR HY000: Index for table 'tmp' is corrupt; try to repair it +drop table t1; diff --git a/mysql-test/t/tmp_table_error.test b/mysql-test/t/tmp_table_error.test new file mode 100644 index 00000000000..e09e45085fa --- /dev/null +++ b/mysql-test/t/tmp_table_error.test @@ -0,0 +1,2637 @@ +source include/have_innodb.inc; +call mtr.add_suppression('Index for table'); +create table t1 ( + a int primary key, + b text +) engine=innodb; + +--replace_regex /'.*'/'tmp'/ +--error 126 +create table t2 as +select + 1 + from + (select distinct + b as c0, + b as c1, + b as c2, + b as c3, + b as c4, + b as c5, + b as c6, + b as c7, + b as c8, + b as c9, + b as c10, + b as c11, + b as c12, + b as c13, + b as c14, + b as c15, + b as c16, + b as c17, + b as c18, + b as c19, + b as c20, + b as c21, + b as c22, + b as c23, + b as c24, + b as c25, + b as c26, + b as c27, + b as c28, + b as c29, + b as c30, + b as c31, + b as c32, + b as c33, + b as c34, + b as c35, + b as c36, + b as c37, + b as c38, + b as c39, + b as c40, + b as c41, + b as c42, + b as c43, + b as c45, + b as c46, + b as c47, + b as c48, + b as c49, + b as c50, + b as c51, + b as c52, + b as c53, + b as c54, + b as c55, + b as c56, + b as c57, + b as c58, + b as c59, + b as c60, + b as c61, + b as c62, + b as c63, + b as c64, + b as c65, + b as c66, + b as c67, + b as c68, + b as c69, + b as c70, + b as c71, + b as c72, + b as c73, + b as c74, + b as c75, + b as c76, + b as c77, + b as c78, + b as c79, + b as c80, + b as c81, + b as c82, + b as c83, + b as c84, + b as c85, + b as c86, + b as c87, + b as c88, + b as c89, + b as c90, + b as c91, + b as c92, + b as c93, + b as c94, + b as c95, + b as c96, + b as c97, + b as c98, + b as c99, + b as c100, + b as c101, + b as c102, + b as c103, + b as c104, + b as c105, + b as c106, + b as c107, + b as c108, + b as c109, + b as c110, + b as c111, + b as c112, + b as c113, + b as c114, + b as c115, + b as c116, + b as c117, + b as c118, + b as c119, + b as c120, + b as c121, + b as c122, + b as c123, + b as c124, + b as c125, + b as c126, + b as c127, + b as c128, + b as c129, + b as c130, + b as c131, + b as c132, + b as c133, + b as c134, + b as c135, + b as c136, + b as c137, + b as c138, + b as c139, + b as c140, + b as c141, + b as c142, + b as c143, + b as c144, + b as c145, + b as c146, + b as c147, + b as c148, + b as c149, + b as c150, + b as c151, + b as c152, + b as c153, + b as c154, + b as c155, + b as c156, + b as c157, + b as c158, + b as c159, + b as c160, + b as c161, + b as c162, + b as c163, + b as c164, + b as c165, + b as c166, + b as c167, + b as c168, + b as c169, + b as c170, + b as c171, + b as c172, + b as c173, + b as c174, + b as c175, + b as c176, + b as c177, + b as c178, + b as c179, + b as c180, + b as c181, + b as c182, + b as c183, + b as c184, + b as c185, + b as c186, + b as c187, + b as c188, + b as c189, + b as c190, + b as c191, + b as c192, + b as c193, + b as c194, + b as c195, + b as c196, + b as c197, + b as c198, + b as c199, + b as c200, + b as c201, + b as c202, + b as c203, + b as c204, + b as c205, + b as c206, + b as c207, + b as c208, + b as c209, + b as c210, + b as c211, + b as c212, + b as c213, + b as c214, + b as c215, + b as c216, + b as c217, + b as c218, + b as c219, + b as c220, + b as c221, + b as c222, + b as c223, + b as c224, + b as c225, + b as c226, + b as c227, + b as c228, + b as c229, + b as c230, + b as c231, + b as c232, + b as c233, + b as c234, + b as c235, + b as c236, + b as c237, + b as c238, + b as c239, + b as c240, + b as c241, + b as c242, + b as c243, + b as c244, + b as c245, + b as c246, + b as c247, + b as c248, + b as c249, + b as c250, + b as c251, + b as c252, + b as c253, + b as c254, + b as c255, + b as c256, + b as c257, + b as c258, + b as c259, + b as c260, + b as c261, + b as c262, + b as c263, + b as c264, + b as c265, + b as c266, + b as c267, + b as c268, + b as c269, + b as c270, + b as c271, + b as c272, + b as c273, + b as c274, + b as c275, + b as c276, + b as c277, + b as c278, + b as c279, + b as c280, + b as c281, + b as c282, + b as c283, + b as c284, + b as c285, + b as c286, + b as c287, + b as c288, + b as c289, + b as c290, + b as c291, + b as c292, + b as c293, + b as c294, + b as c295, + b as c296, + b as c297, + b as c298, + b as c299, + b as c300, + b as c301, + b as c302, + b as c303, + b as c304, + b as c305, + b as c306, + b as c307, + b as c308, + b as c309, + b as c310, + b as c311, + b as c312, + b as c313, + b as c314, + b as c315, + b as c316, + b as c317, + b as c318, + b as c319, + b as c320, + b as c321, + b as c322, + b as c323, + b as c324, + b as c325, + b as c326, + b as c327, + b as c328, + b as c329, + b as c330, + b as c331, + b as c332, + b as c333, + b as c334, + b as c335, + b as c336, + b as c337, + b as c338, + b as c339, + b as c340, + b as c341, + b as c342, + b as c343, + b as c344, + b as c345, + b as c346, + b as c347, + b as c348, + b as c349, + b as c350, + b as c351, + b as c352, + b as c353, + b as c354, + b as c355, + b as c356, + b as c357, + b as c358, + b as c359, + b as c360, + b as c361, + b as c362, + b as c363, + b as c364, + b as c365, + b as c366, + b as c367, + b as c368, + b as c369, + b as c370, + b as c371, + b as c372, + b as c373, + b as c374, + b as c375, + b as c376, + b as c377, + b as c378, + b as c379, + b as c380, + b as c381, + b as c382, + b as c383, + b as c384, + b as c385, + b as c386, + b as c387, + b as c388, + b as c389, + b as c390, + b as c391, + b as c392, + b as c393, + b as c394, + b as c395, + b as c396, + b as c397, + b as c398, + b as c399, + b as c400, + b as c401, + b as c402, + b as c403, + b as c404, + b as c405, + b as c406, + b as c407, + b as c409, + b as c410, + b as c411, + b as c412, + b as c413, + b as c414, + b as c415, + b as c416, + b as c417, + b as c418, + b as c419, + b as c420, + b as c421, + b as c422, + b as c423, + b as c424, + b as c425, + b as c426, + b as c427, + b as c428, + b as c429, + b as c430, + b as c431, + b as c432, + b as c433, + b as c434, + b as c435, + b as c436, + b as c437, + b as c438, + b as c439, + b as c440, + b as c441, + b as c442, + b as c443, + b as c444, + b as c445, + b as c446, + b as c447, + b as c448, + b as c449, + b as c450, + b as c451, + b as c452, + b as c453, + b as c454, + b as c455, + b as c456, + b as c457, + b as c458, + b as c459, + b as c460, + b as c461, + b as c462, + b as c463, + b as c464, + b as c465, + b as c466, + b as c467, + b as c468, + b as c469, + b as c470, + b as c471, + b as c472, + b as c473, + b as c474, + b as c475, + b as c476, + b as c477, + b as c478, + b as c479, + b as c480, + b as c481, + b as c482, + b as c483, + b as c484, + b as c485, + b as c486, + b as c487, + b as c488, + b as c489, + b as c490, + b as c491, + b as c492, + b as c493, + b as c494, + b as c495, + b as c496, + b as c497, + b as c498, + b as c499, + b as c500, + b as c501, + b as c502, + b as c503, + b as c504, + b as c505, + b as c506, + b as c507, + b as c508, + b as c509, + b as c510, + b as c511, + b as c512, + b as c513, + b as c514, + b as c515, + b as c516, + b as c517, + b as c518, + b as c519, + b as c520, + b as c521, + b as c522, + b as c523, + b as c524, + b as c525, + b as c526, + b as c527, + b as c528, + b as c529, + b as c530, + b as c531, + b as c532, + b as c533, + b as c534, + b as c535, + b as c536, + b as c537, + b as c538, + b as c539, + b as c540, + b as c541, + b as c542, + b as c543, + b as c544, + b as c545, + b as c546, + b as c547, + b as c548, + b as c549, + b as c550, + b as c551, + b as c552, + b as c553, + b as c554, + b as c555, + b as c556, + b as c557, + b as c558, + b as c559, + b as c560, + b as c561, + b as c562, + b as c563, + b as c564, + b as c565, + b as c566, + b as c567, + b as c568, + b as c569, + b as c570, + b as c571, + b as c572, + b as c573, + b as c574, + b as c575, + b as c576, + b as c577, + b as c578, + b as c579, + b as c580, + b as c581, + b as c582, + b as c583, + b as c584, + b as c585, + b as c586, + b as c587, + b as c588, + b as c589, + b as c590, + b as c591, + b as c592, + b as c593, + b as c594, + b as c595, + b as c596, + b as c597, + b as c598, + b as c599, + b as c600, + b as c601, + b as c602, + b as c603, + b as c604, + b as c605, + b as c606, + b as c607, + b as c608, + b as c609, + b as c610, + b as c611, + b as c612, + b as c613, + b as c614, + b as c615, + b as c616, + b as c617, + b as c618, + b as c619, + b as c620, + b as c621, + b as c622, + b as c623, + b as c624, + b as c625, + b as c626, + b as c627, + b as c628, + b as c629, + b as c630, + b as c631, + b as c632, + b as c633, + b as c634, + b as c635, + b as c636, + b as c637, + b as c638, + b as c639, + b as c640, + b as c641, + b as c642, + b as c643, + b as c644, + b as c645, + b as c646, + b as c647, + b as c648, + b as c649, + b as c650, + b as c651, + b as c652, + b as c653, + b as c654, + b as c655, + b as c656, + b as c657, + b as c658, + b as c659, + b as c660, + b as c661, + b as c662, + b as c663, + b as c664, + b as c665, + b as c666, + b as c667, + b as c668, + b as c669, + b as c670, + b as c671, + b as c672, + b as c673, + b as c674, + b as c675, + b as c676, + b as c677, + b as c678, + b as c679, + b as c680, + b as c681, + b as c682, + b as c683, + b as c684, + b as c685, + b as c686, + b as c687, + b as c688, + b as c689, + b as c690, + b as c691, + b as c692, + b as c693, + b as c694, + b as c695, + b as c696, + b as c697, + b as c698, + b as c699, + b as c700, + b as c701, + b as c702, + b as c703, + b as c704, + b as c705, + b as c706, + b as c707, + b as c708, + b as c709, + b as c710, + b as c711, + b as c712, + b as c713, + b as c714, + b as c715, + b as c716, + b as c717, + b as c718, + b as c719, + b as c720, + b as c721, + b as c722, + b as c723, + b as c724, + b as c725, + b as c726, + b as c727, + b as c728, + b as c729, + b as c730, + b as c731, + b as c732, + b as c733, + b as c734, + b as c735, + b as c736, + b as c737, + b as c738, + b as c739, + b as c740, + b as c741, + b as c742, + b as c743, + b as c744, + b as c745, + b as c746, + b as c747, + b as c748, + b as c749, + b as c750, + b as c751, + b as c752, + b as c753, + b as c754, + b as c755, + b as c756, + b as c757, + b as c758, + b as c759, + b as c760, + b as c761, + b as c762, + b as c763, + b as c764, + b as c765, + b as c766, + b as c767, + b as c768, + b as c769, + b as c770, + b as c771, + b as c772, + b as c773, + b as c774, + b as c775, + b as c776, + b as c777, + b as c778, + b as c779, + b as c780, + b as c781, + b as c782, + b as c783, + b as c784, + b as c785, + b as c786, + b as c787, + b as c788, + b as c789, + b as c790, + b as c791, + b as c792, + b as c793, + b as c794, + b as c795, + b as c796, + b as c797, + b as c798, + b as c799, + b as c800, + b as c801, + b as c802, + b as c803, + b as c804, + b as c805, + b as c806, + b as c807, + b as c808, + b as c809, + b as c810, + b as c811, + b as c812, + b as c813, + b as c814, + b as c815, + b as c816, + b as c817, + b as c818, + b as c819, + b as c820, + b as c821, + b as c822, + b as c823, + b as c824, + b as c825, + b as c826, + b as c827, + b as c828, + b as c829, + b as c830, + b as c831, + b as c832, + b as c833, + b as c834, + b as c835, + b as c836, + b as c837, + b as c838, + b as c839, + b as c840, + b as c841, + b as c842, + b as c843, + b as c844, + b as c845, + b as c846, + b as c847, + b as c848, + b as c849, + b as c850, + b as c851, + b as c852, + b as c853, + b as c854, + b as c855, + b as c856, + b as c857, + b as c858, + b as c859, + b as c860, + b as c861, + b as c862, + b as c863, + b as c864, + b as c865, + b as c866, + b as c867, + b as c868, + b as c869, + b as c870, + b as c871, + b as c872, + b as c873, + b as c874, + b as c875, + b as c876, + b as c877, + b as c878, + b as c879, + b as c880, + b as c881, + b as c882, + b as c883, + b as c884, + b as c885, + b as c886, + b as c887, + b as c888, + b as c889, + b as c890, + b as c891, + b as c892, + b as c893, + b as c894, + b as c895, + b as c897, + b as c898, + b as c899, + b as c900, + b as c901, + b as c902, + b as c903, + b as c904, + b as c905, + b as c906, + b as c907, + b as c908, + b as c909, + b as c910, + b as c911, + b as c912, + b as c913, + b as c914, + b as c915, + b as c916, + b as c917, + b as c918, + b as c919, + b as c920, + b as c921, + b as c922, + b as c923, + b as c924, + b as c925, + b as c926, + b as c927, + b as c928, + b as c929, + b as c930, + b as c931, + b as c932, + b as c933, + b as c934, + b as c935, + b as c936, + b as c937, + b as c938, + b as c939, + b as c940, + b as c941, + b as c942, + b as c943, + b as c944, + b as c945, + b as c946, + b as c947, + b as c948, + b as c949, + b as c950, + b as c951, + b as c952, + b as c953, + b as c954, + b as c955, + b as c956, + b as c957, + b as c958, + b as c959, + b as c960, + b as c961, + b as c962, + b as c963, + b as c964, + b as c965, + b as c966, + b as c967, + b as c968, + b as c969, + b as c970, + b as c971, + b as c972, + b as c973, + b as c974, + b as c975, + b as c976, + b as c977, + b as c978, + b as c979, + b as c980, + b as c981, + b as c982, + b as c983, + b as c984, + b as c985, + b as c986, + b as c987, + b as c988, + b as c989, + b as c990, + b as c991, + b as c992, + b as c993, + b as c995, + b as c996, + b as c997, + b as c998, + b as c999, + b as c1000, + b as c1001, + b as c1002, + b as c1003, + b as c1004, + b as c1005, + b as c1006, + b as c1007, + b as c1008, + b as c1009, + b as c1010, + b as c1011, + b as c1012, + b as c1013, + b as c1014, + b as c1015, + b as c1016, + b as c1017, + b as c1018, + b as c1019, + b as c1020, + b as c1021, + b as c1022, + b as c1023, + b as c1024, + b as c1025, + b as c1026, + b as c1027, + b as c1028, + b as c1029, + b as c1030, + b as c1031, + b as c1032, + b as c1033, + b as c1034, + b as c1035, + b as c1036, + b as c1037, + b as c1038, + b as c1039, + b as c1040, + b as c1041, + b as c1042, + b as c1043, + b as c1044, + b as c1045, + b as c1046, + b as c1047, + b as c1048, + b as c1049, + b as c1050, + b as c1051, + b as c1052, + b as c1053, + b as c1054, + b as c1055, + b as c1056, + b as c1057, + b as c1058, + b as c1059, + b as c1060, + b as c1061, + b as c1062, + b as c1063, + b as c1064, + b as c1065, + b as c1066, + b as c1067, + b as c1068, + b as c1069, + b as c1070, + b as c1071, + b as c1072, + b as c1073, + b as c1074, + b as c1075, + b as c1076, + b as c1077, + b as c1078, + b as c1079, + b as c1080, + b as c1081, + b as c1082, + b as c1083, + b as c1084, + b as c1085, + b as c1086, + b as c1087, + b as c1088, + b as c1089, + b as c1090, + b as c1091, + b as c1092, + b as c1093, + b as c1094, + b as c1095, + b as c1096, + b as c1097, + b as c1098, + b as c1099, + b as c1100, + b as c1101, + b as c1102, + b as c1103, + b as c1104, + b as c1105, + b as c1106, + b as c1107, + b as c1108, + b as c1109, + b as c1110, + b as c1111, + b as c1112, + b as c1113, + b as c1114, + b as c1115, + b as c1116, + b as c1117, + b as c1118, + b as c1119, + b as c1120, + b as c1121, + b as c1122, + b as c1123, + b as c1124, + b as c1125, + b as c1126, + b as c1127, + b as c1128, + b as c1129, + b as c1130, + b as c1131, + b as c1132, + b as c1133, + b as c1134, + b as c1135, + b as c1136, + b as c1137, + b as c1138, + b as c1139, + b as c1140, + b as c1141, + b as c1142, + b as c1143, + b as c1144, + b as c1145, + b as c1146, + b as c1147, + b as c1148, + b as c1149, + b as c1150, + b as c1151, + b as c1152, + b as c1153, + b as c1154, + b as c1155, + b as c1156, + b as c1157, + b as c1158, + b as c1159, + b as c1160, + b as c1161, + b as c1162, + b as c1163, + b as c1164, + b as c1165, + b as c1166, + b as c1167, + b as c1168, + b as c1169, + b as c1170, + b as c1171, + b as c1172, + b as c1173, + b as c1174, + b as c1175, + b as c1176, + b as c1177, + b as c1178, + b as c1179, + b as c1180, + b as c1181, + b as c1182, + b as c1183, + b as c1184, + b as c1185, + b as c1186, + b as c1187, + b as c1188, + b as c1189, + b as c1190, + b as c1191, + b as c1192, + b as c1193, + b as c1194, + b as c1195, + b as c1196, + b as c1197, + b as c1198, + b as c1199, + b as c1200, + b as c1201, + b as c1202, + b as c1203, + b as c1204, + b as c1205, + b as c1206, + b as c1207, + b as c1208, + b as c1209, + b as c1210, + b as c1211, + b as c1212, + b as c1213, + b as c1214, + b as c1215, + b as c1216, + b as c1217, + b as c1218, + b as c1219, + b as c1220, + b as c1221, + b as c1222, + b as c1223, + b as c1224, + b as c1225, + b as c1226, + b as c1227, + b as c1228, + b as c1229, + b as c1230, + b as c1231, + b as c1232, + b as c1233, + b as c1234, + b as c1235, + b as c1236, + b as c1237, + b as c1238, + b as c1239, + b as c1240, + b as c1241, + b as c1242, + b as c1243, + b as c1244, + b as c1245, + b as c1246, + b as c1247, + b as c1248, + b as c1249, + b as c1250, + b as c1251, + b as c1252, + b as c1253, + b as c1254, + b as c1255, + b as c1256, + b as c1257, + b as c1258, + b as c1259, + b as c1260, + b as c1261, + b as c1262, + b as c1263, + b as c1264, + b as c1265, + b as c1266, + b as c1267, + b as c1268, + b as c1269, + b as c1270, + b as c1271, + b as c1272, + b as c1273, + b as c1274, + b as c1275, + b as c1276, + b as c1277, + b as c1278, + b as c1279, + b as c1280, + b as c1281, + b as c1282, + b as c1283, + b as c1284, + b as c1285, + b as c1286, + b as c1287, + b as c1288, + b as c1289, + b as c1290, + b as c1291, + b as c1292, + b as c1293, + b as c1294, + b as c1295, + b as c1296, + b as c1297, + b as c1298, + b as c1299, + b as c1300, + b as c1301, + b as c1302, + b as c1303, + b as c1304, + b as c1305, + b as c1306, + b as c1307, + b as c1308, + b as c1309, + b as c1310, + b as c1311, + b as c1312, + b as c1313, + b as c1314, + b as c1315, + b as c1316, + b as c1317, + b as c1318, + b as c1319, + b as c1320, + b as c1321, + b as c1322, + b as c1323, + b as c1324, + b as c1325, + b as c1326, + b as c1327, + b as c1328, + b as c1329, + b as c1330, + b as c1331, + b as c1332, + b as c1333, + b as c1334, + b as c1335, + b as c1336, + b as c1337, + b as c1338, + b as c1339, + b as c1340, + b as c1341, + b as c1342, + b as c1343, + b as c1344, + b as c1345, + b as c1346, + b as c1347, + b as c1348, + b as c1349, + b as c1350, + b as c1351, + b as c1352, + b as c1353, + b as c1354, + b as c1355, + b as c1356, + b as c1357, + b as c1358, + b as c1359, + b as c1360, + b as c1361, + b as c1362, + b as c1363, + b as c1364, + b as c1365, + b as c1366, + b as c1367, + b as c1368, + b as c1369, + b as c1370, + b as c1371, + b as c1372, + b as c1373, + b as c1374, + b as c1375, + b as c1376, + b as c1377, + b as c1378, + b as c1379, + b as c1380, + b as c1381, + b as c1382, + b as c1383, + b as c1384, + b as c1385, + b as c1386, + b as c1387, + b as c1388, + b as c1389, + b as c1390, + b as c1391, + b as c1392, + b as c1393, + b as c1394, + b as c1395, + b as c1396, + b as c1397, + b as c1398, + b as c1399, + b as c1400, + b as c1401, + b as c1402, + b as c1403, + b as c1404, + b as c1405, + b as c1406, + b as c1407, + b as c1408, + b as c1409, + b as c1410, + b as c1411, + b as c1412, + b as c1413, + b as c1414, + b as c1415, + b as c1416, + b as c1417, + b as c1418, + b as c1419, + b as c1420, + b as c1421, + b as c1422, + b as c1423, + b as c1424, + b as c1425, + b as c1426, + b as c1427, + b as c1428, + b as c1429, + b as c1430, + b as c1431, + b as c1432, + b as c1433, + b as c1434, + b as c1435, + b as c1436, + b as c1437, + b as c1438, + b as c1439, + b as c1440, + b as c1441, + b as c1442, + b as c1443, + b as c1444, + b as c1445, + b as c1446, + b as c1447, + b as c1448, + b as c1449, + b as c1451, + b as c1452, + b as c1453, + b as c1454, + b as c1455, + b as c1456, + b as c1457, + b as c1458, + b as c1459, + b as c1460, + b as c1461, + b as c1462, + b as c1463, + b as c1464, + b as c1465, + b as c1466, + b as c1467, + b as c1468, + b as c1469, + b as c1470, + b as c1471, + b as c1472, + b as c1473, + b as c1474, + b as c1475, + b as c1476, + b as c1477, + b as c1478, + b as c1479, + b as c1480, + b as c1481, + b as c1482, + b as c1483, + b as c1484, + b as c1485, + b as c1486, + b as c1487, + b as c1488, + b as c1489, + b as c1490, + b as c1491, + b as c1492, + b as c1493, + b as c1494, + b as c1495, + b as c1496, + b as c1497, + b as c1498, + b as c1499, + b as c1500, + b as c1501, + b as c1502, + b as c1503, + b as c1504, + b as c1505, + b as c1506, + b as c1507, + b as c1508, + b as c1509, + b as c1510, + b as c1511, + b as c1512, + b as c1513, + b as c1514, + b as c1515, + b as c1516, + b as c1517, + b as c1518, + b as c1519, + b as c1520, + b as c1521, + b as c1522, + b as c1523, + b as c1524, + b as c1525, + b as c1526, + b as c1527, + b as c1528, + b as c1529, + b as c1530, + b as c1531, + b as c1532, + b as c1533, + b as c1534, + b as c1535, + b as c1536, + b as c1537, + b as c1538, + b as c1539, + b as c1540, + b as c1541, + b as c1542, + b as c1543, + b as c1544, + b as c1545, + b as c1546, + b as c1547, + b as c1548, + b as c1549, + b as c1550, + b as c1551, + b as c1552, + b as c1553, + b as c1554, + b as c1555, + b as c1556, + b as c1557, + b as c1558, + b as c1559, + b as c1560, + b as c1561, + b as c1562, + b as c1563, + b as c1564, + b as c1565, + b as c1566, + b as c1567, + b as c1568, + b as c1569, + b as c1570, + b as c1571, + b as c1572, + b as c1573, + b as c1574, + b as c1575, + b as c1576, + b as c1577, + b as c1578, + b as c1579, + b as c1580, + b as c1581, + b as c1582, + b as c1583, + b as c1584, + b as c1585, + b as c1586, + b as c1587, + b as c1588, + b as c1589, + b as c1590, + b as c1591, + b as c1592, + b as c1593, + b as c1594, + b as c1595, + b as c1596, + b as c1597, + b as c1598, + b as c1599, + b as c1600, + b as c1601, + b as c1602, + b as c1603, + b as c1604, + b as c1605, + b as c1606, + b as c1607, + b as c1608, + b as c1609, + b as c1610, + b as c1611, + b as c1612, + b as c1613, + b as c1614, + b as c1615, + b as c1616, + b as c1617, + b as c1618, + b as c1619, + b as c1620, + b as c1621, + b as c1622, + b as c1623, + b as c1624, + b as c1625, + b as c1626, + b as c1627, + b as c1628, + b as c1629, + b as c1630, + b as c1631, + b as c1632, + b as c1633, + b as c1634, + b as c1635, + b as c1636, + b as c1637, + b as c1638, + b as c1639, + b as c1640, + b as c1641, + b as c1642, + b as c1643, + b as c1644, + b as c1645, + b as c1646, + b as c1647, + b as c1648, + b as c1649, + b as c1650, + b as c1651, + b as c1652, + b as c1653, + b as c1654, + b as c1655, + b as c1656, + b as c1657, + b as c1658, + b as c1659, + b as c1660, + b as c1661, + b as c1662, + b as c1663, + b as c1664, + b as c1665, + b as c1666, + b as c1667, + b as c1668, + b as c1669, + b as c1670, + b as c1671, + b as c1672, + b as c1673, + b as c1674, + b as c1675, + b as c1676, + b as c1677, + b as c1678, + b as c1679, + b as c1680, + b as c1681, + b as c1682, + b as c1683, + b as c1684, + b as c1685, + b as c1686, + b as c1687, + b as c1688, + b as c1689, + b as c1690, + b as c1691, + b as c1692, + b as c1693, + b as c1694, + b as c1695, + b as c1696, + b as c1697, + b as c1698, + b as c1699, + b as c1700, + b as c1701, + b as c1702, + b as c1703, + b as c1704, + b as c1705, + b as c1706, + b as c1707, + b as c1708, + b as c1709, + b as c1710, + b as c1711, + b as c1712, + b as c1713, + b as c1714, + b as c1715, + b as c1716, + b as c1717, + b as c1718, + b as c1719, + b as c1720, + b as c1721, + b as c1722, + b as c1723, + b as c1724, + b as c1725, + b as c1726, + b as c1727, + b as c1728, + b as c1729, + b as c1730, + b as c1731, + b as c1732, + b as c1733, + b as c1734, + b as c1735, + b as c1736, + b as c1737, + b as c1738, + b as c1739, + b as c1740, + b as c1741, + b as c1742, + b as c1743, + b as c1744, + b as c1745, + b as c1746, + b as c1747, + b as c1748, + b as c1749, + b as c1750, + b as c1751, + b as c1752, + b as c1753, + b as c1754, + b as c1755, + b as c1756, + b as c1757, + b as c1758, + b as c1759, + b as c1760, + b as c1761, + b as c1762, + b as c1763, + b as c1764, + b as c1765, + b as c1766, + b as c1767, + b as c1768, + b as c1769, + b as c1770, + b as c1771, + b as c1772, + b as c1773, + b as c1774, + b as c1775, + b as c1776, + b as c1777, + b as c1778, + b as c1779, + b as c1780, + b as c1781, + b as c1782, + b as c1783, + b as c1784, + b as c1785, + b as c1786, + b as c1787, + b as c1788, + b as c1789, + b as c1790, + b as c1791, + b as c1792, + b as c1793, + b as c1794, + b as c1795, + b as c1796, + b as c1797, + b as c1798, + b as c1799, + b as c1800, + b as c1801, + b as c1802, + b as c1803, + b as c1804, + b as c1805, + b as c1806, + b as c1807, + b as c1808, + b as c1809, + b as c1810, + b as c1811, + b as c1812, + b as c1813, + b as c1814, + b as c1815, + b as c1816, + b as c1817, + b as c1818, + b as c1819, + b as c1820, + b as c1821, + b as c1822, + b as c1823, + b as c1824, + b as c1825, + b as c1826, + b as c1827, + b as c1828, + b as c1829, + b as c1830, + b as c1831, + b as c1832, + b as c1833, + b as c1834, + b as c1835, + b as c1836, + b as c1837, + b as c1838, + b as c1839, + b as c1840, + b as c1841, + b as c1842, + b as c1843, + b as c1844, + b as c1845, + b as c1846, + b as c1847, + b as c1848, + b as c1849, + b as c1850, + b as c1851, + b as c1852, + b as c1853, + b as c1854, + b as c1855, + b as c1856, + b as c1857, + b as c1858, + b as c1859, + b as c1860, + b as c1861, + b as c1862, + b as c1863, + b as c1864, + b as c1865, + b as c1866, + b as c1867, + b as c1868, + b as c1869, + b as c1870, + b as c1871, + b as c1872, + b as c1873, + b as c1874, + b as c1875, + b as c1876, + b as c1877, + b as c1878, + b as c1879, + b as c1880, + b as c1881, + b as c1882, + b as c1883, + b as c1884, + b as c1885, + b as c1886, + b as c1887, + b as c1888, + b as c1889, + b as c1890, + b as c1891, + b as c1892, + b as c1893, + b as c1894, + b as c1895, + b as c1896, + b as c1897, + b as c1898, + b as c1899, + b as c1900, + b as c1901, + b as c1902, + b as c1903, + b as c1904, + b as c1905, + b as c1906, + b as c1907, + b as c1908, + b as c1909, + b as c1910, + b as c1911, + b as c1912, + b as c1913, + b as c1914, + b as c1915, + b as c1916, + b as c1917, + b as c1918, + b as c1919, + b as c1920, + b as c1921, + b as c1922, + b as c1923, + b as c1924, + b as c1925, + b as c1926, + b as c1927, + b as c1928, + b as c1929, + b as c1930, + b as c1931, + b as c1932, + b as c1933, + b as c1934, + b as c1935, + b as c1936, + b as c1937, + b as c1938, + b as c1939, + b as c1940, + b as c1941, + b as c1942, + b as c1943, + b as c1944, + b as c1945, + b as c1946, + b as c1947, + b as c1948, + b as c1949, + b as c1950, + b as c1951, + b as c1952, + b as c1953, + b as c1954, + b as c1955, + b as c1956, + b as c1957, + b as c1958, + b as c1959, + b as c1960, + b as c1961, + b as c1962, + b as c1963, + b as c1964, + b as c1965, + b as c1966, + b as c1967, + b as c1968, + b as c1969, + b as c1970, + b as c1971, + b as c1972, + b as c1973, + b as c1974, + b as c1975, + b as c1976, + b as c1977, + b as c1978, + b as c1979, + b as c1980, + b as c1981, + b as c1982, + b as c1983, + b as c1984, + b as c1985, + b as c1986, + b as c1987, + b as c1988, + b as c1989, + b as c1990, + b as c1991, + b as c1992, + b as c1993, + b as c1994, + b as c1995, + b as c1996, + b as c1997, + b as c1998, + b as c1999, + b as c2000, + b as c2001, + b as c2002, + b as c2003, + b as c2004, + b as c2005, + b as c2006, + b as c2007, + b as c2008, + b as c2009, + b as c2010, + b as c2011, + b as c2012, + b as c2013, + b as c2014, + b as c2015, + b as c2016, + b as c2017, + b as c2018, + b as c2019, + b as c2020, + b as c2021, + b as c2022, + b as c2023, + b as c2024, + b as c2025, + b as c2026, + b as c2027, + b as c2028, + b as c2029, + b as c2030, + b as c2031, + b as c2032, + b as c2033, + b as c2034, + b as c2035, + b as c2036, + b as c2037, + b as c2038, + b as c2039, + b as c2040, + b as c2041, + b as c2042, + b as c2043, + b as c2044, + b as c2045, + b as c2046, + b as c2047, + b as c2048, + b as c2049, + b as c2050, + b as c2051, + b as c2052, + b as c2053, + b as c2054, + b as c2055, + b as c2056, + b as c2057, + b as c2058, + b as c2059, + b as c2060, + b as c2061, + b as c2062, + b as c2063, + b as c2064, + b as c2065, + b as c2066, + b as c2067, + b as c2068, + b as c2069, + b as c2070, + b as c2071, + b as c2072, + b as c2073, + b as c2074, + b as c2075, + b as c2076, + b as c2077, + b as c2078, + b as c2079, + b as c2080, + b as c2081, + b as c2082, + b as c2083, + b as c2084, + b as c2085, + b as c2086, + b as c2087, + b as c2088, + b as c2089, + b as c2090, + b as c2091, + b as c2092, + b as c2093, + b as c2094, + b as c2095, + b as c2096, + b as c2097, + b as c2098, + b as c2099, + b as c2100, + b as c2101, + b as c2102, + b as c2103, + b as c2104, + b as c2105, + b as c2106, + b as c2107, + b as c2108, + b as c2109, + b as c2110, + b as c2111, + b as c2112, + b as c2113, + b as c2114, + b as c2115, + b as c2116, + b as c2117, + b as c2118, + b as c2119, + b as c2120, + b as c2121, + b as c2122, + b as c2123, + b as c2124, + b as c2125, + b as c2126, + b as c2127, + b as c2128, + b as c2129, + b as c2130, + b as c2131, + b as c2132, + b as c2133, + b as c2134, + b as c2135, + b as c2136, + b as c2137, + b as c2138, + b as c2139, + b as c2140, + b as c2141, + b as c2142, + b as c2143, + b as c2144, + b as c2145, + b as c2146, + b as c2147, + b as c2148, + b as c2149, + b as c2150, + b as c2151, + b as c2152, + b as c2153, + b as c2154, + b as c2155, + b as c2156, + b as c2157, + b as c2158, + b as c2159, + b as c2160, + b as c2161, + b as c2162, + b as c2163, + b as c2164, + b as c2165, + b as c2166, + b as c2167, + b as c2168, + b as c2169, + b as c2170, + b as c2171, + b as c2172, + b as c2173, + b as c2174, + b as c2175, + b as c2176, + b as c2177, + b as c2178, + b as c2179, + b as c2180, + b as c2181, + b as c2182, + b as c2183, + b as c2184, + b as c2185, + b as c2186, + b as c2187, + b as c2188, + b as c2189, + b as c2190, + b as c2191, + b as c2192, + b as c2193, + b as c2194, + b as c2195, + b as c2196, + b as c2197, + b as c2198, + b as c2199, + b as c2200, + b as c2201, + b as c2202, + b as c2203, + b as c2204, + b as c2205, + b as c2206, + b as c2207, + b as c2208, + b as c2209, + b as c2210, + b as c2211, + b as c2212, + b as c2213, + b as c2214, + b as c2215, + b as c2216, + b as c2217, + b as c2218, + b as c2219, + b as c2220, + b as c2221, + b as c2222, + b as c2223, + b as c2224, + b as c2225, + b as c2226, + b as c2227, + b as c2228, + b as c2229, + b as c2230, + b as c2231, + b as c2232, + b as c2233, + b as c2234, + b as c2235, + b as c2236, + b as c2237, + b as c2238, + b as c2239, + b as c2240, + b as c2241, + b as c2242, + b as c2243, + b as c2244, + b as c2245, + b as c2246, + b as c2247, + b as c2248, + b as c2249, + b as c2250, + b as c2251, + b as c2252, + b as c2253, + b as c2254, + b as c2255, + b as c2256, + b as c2257, + b as c2258, + b as c2259, + b as c2260, + b as c2261, + b as c2262, + b as c2263, + b as c2264, + b as c2265, + b as c2266, + b as c2267, + b as c2268, + b as c2269, + b as c2270, + b as c2271, + b as c2272, + b as c2273, + b as c2274, + b as c2275, + b as c2276, + b as c2277, + b as c2278, + b as c2279, + b as c2280, + b as c2281, + b as c2282, + b as c2283, + b as c2284, + b as c2285, + b as c2286, + b as c2287, + b as c2288, + b as c2289, + b as c2290, + b as c2291, + b as c2292, + b as c2293, + b as c2294, + b as c2295, + b as c2296, + b as c2297, + b as c2298, + b as c2299, + b as c2300, + b as c2301, + b as c2302, + b as c2303, + b as c2304, + b as c2305, + b as c2306, + b as c2307, + b as c2308, + b as c2309, + b as c2310, + b as c2311, + b as c2312, + b as c2313, + b as c2314, + b as c2315, + b as c2316, + b as c2317, + b as c2318, + b as c2319, + b as c2320, + b as c2321, + b as c2322, + b as c2323, + b as c2324, + b as c2325, + b as c2326, + b as c2327, + b as c2328, + b as c2329, + b as c2330, + b as c2331, + b as c2332, + b as c2333, + b as c2334, + b as c2335, + b as c2336, + b as c2337, + b as c2338, + b as c2339, + b as c2340, + b as c2341, + b as c2342, + b as c2343, + b as c2344, + b as c2345, + b as c2346, + b as c2347, + b as c2348, + b as c2349, + b as c2350, + b as c2351, + b as c2352, + b as c2353, + b as c2354, + b as c2355, + b as c2356, + b as c2357, + b as c2358, + b as c2359, + b as c2360, + b as c2361, + b as c2362, + b as c2363, + b as c2364, + b as c2365, + b as c2366, + b as c2367, + b as c2368, + b as c2369, + b as c2370, + b as c2371, + b as c2372, + b as c2373, + b as c2374, + b as c2375, + b as c2376, + b as c2377, + b as c2378, + b as c2379, + b as c2380, + b as c2381, + b as c2382, + b as c2383, + b as c2384, + b as c2385, + b as c2386, + b as c2387, + b as c2388, + b as c2389, + b as c2390, + b as c2391, + b as c2392, + b as c2393, + b as c2394, + b as c2395, + b as c2396, + b as c2397, + b as c2398, + b as c2399, + b as c2400, + b as c2401, + b as c2402, + b as c2403, + b as c2404, + b as c2405, + b as c2406, + b as c2407, + b as c2408, + b as c2409, + b as c2410, + b as c2411, + b as c2412, + b as c2413, + b as c2414, + b as c2415, + b as c2416, + b as c2417, + b as c2418, + b as c2419, + b as c2420, + b as c2421, + b as c2422, + b as c2423, + b as c2424, + b as c2425, + b as c2426, + b as c2427, + b as c2428, + b as c2429, + b as c2430, + b as c2431, + b as c2432, + b as c2433, + b as c2434, + b as c2435, + b as c2436, + b as c2437, + b as c2438, + b as c2439, + b as c2440, + b as c2441, + b as c2442, + b as c2443, + b as c2444, + b as c2445, + b as c2446, + b as c2447, + b as c2448, + b as c2449, + b as c2450, + b as c2451, + b as c2452, + b as c2453, + b as c2454, + b as c2455, + b as c2456, + b as c2457, + b as c2458, + b as c2459, + b as c2460, + b as c2461, + b as c2462, + b as c2463, + b as c2464, + b as c2465, + b as c2466, + b as c2467, + b as c2468, + b as c2469, + b as c2470, + b as c2471, + b as c2472, + b as c2473, + b as c2474, + b as c2475, + b as c2476, + b as c2477, + b as c2478, + b as c2479, + b as c2480, + b as c2481, + b as c2482, + b as c2483, + b as c2484, + b as c2485, + b as c2486, + b as c2487, + b as c2488, + b as c2489, + b as c2490, + b as c2491, + b as c2492, + b as c2493, + b as c2494, + b as c2495, + b as c2496, + b as c2497, + b as c2498, + b as c2499, + b as c2500, + b as c2501, + b as c2503, + b as c2504, + b as c2505, + b as c2506, + b as c2507, + b as c2508, + b as c2509, + b as c2510, + b as c2511, + b as c2512, + b as c2513, + b as c2514, + b as c2515, + b as c2516, + b as c2517, + b as c2518, + b as c2519, + b as c2520, + b as c2521, + b as c2522, + b as c2523, + b as c2524, + b as c2525, + b as c2526, + b as c2527, + b as c2528, + b as c2529, + b as c2530, + b as c2531, + b as c2532, + b as c2533, + b as c2534, + b as c2535, + b as c2536, + b as c2537, + b as c2538, + b as c2539, + b as c2540, + b as c2541, + b as c2542, + b as c2543, + b as c2544, + b as c2545, + b as c2546, + b as c2547, + b as c2548, + b as c2549, + b as c2550, + b as c2551, + b as c2552, + b as c2553, + b as c2554, + b as c2555, + b as c2556, + b as c2557, + b as c2558, + b as c2559, + b as c2560, + b as c2561, + b as c2562, + b as c2563, + b as c2564, + b as c2565, + b as c2566, + b as c2567, + b as c2568, + b as c2569, + b as c2570, + b as c2571, + b as c2572, + b as c2573, + b as c2574, + b as c2575, + b as c2576, + b as c2577, + b as c2578, + b as c2579, + b as c2580, + b as c2581, + b as c2582, + b as c2583, + b as c2584, + b as c2585, + b as c2586, + b as c2587, + b as c2588, + b as c2589, + b as c2590, + b as c2591, + b as c2592, + b as c2593, + b as c2594, + b as c2595, + b as c2596, + b as c2597, + b as c2598, + b as c2599, + b as c2600, + b as c2601, + b as c2602, + b as c2603, + b as c2604, + b as c2605, + b as c2606, + b as c2607, + b as c2608, + b as c2609, + b as c2610, + b as c2611, + b as c2612, + b as c2613, + b as c2614, + b as c2615, + b as c2616, + b as c2617, + b as c2618, + b as c2619, + b as c2620, + b as c2621, + b as c2622, + b as c2623, + b as c2624, + b as c2626 + from t1 + ) as tt1; +drop table t1; diff --git a/sql/records.cc b/sql/records.cc index 8a152cda4c2..406512b6d7e 100644 --- a/sql/records.cc +++ b/sql/records.cc @@ -325,7 +325,7 @@ void end_read_record(READ_RECORD *info) free_cache(info); if (info->table) { - if (info->table->is_created()) + if (info->table->db_stat) // if opened (void) info->table->file->extra(HA_EXTRA_NO_CACHE); if (info->read_record != rr_quick) // otherwise quick_range does it (void) info->table->file->ha_index_or_rnd_end(); From 9e2c26b0f6d91b3b6b0deaf9bc82f6e6ebf9a90b Mon Sep 17 00:00:00 2001 From: Sergei Golubchik Date: Thu, 10 Feb 2022 13:40:03 +0100 Subject: [PATCH 29/45] MDEV-26351 segfault - (MARIA_HA *) 0x0 in ha_maria::extra don't let Aria create a table that it cannot open --- mysql-test/r/tmp_table_error.result | 2 +- mysql-test/t/tmp_table_error.test | 2 +- storage/maria/ma_create.c | 6 +++--- 3 files changed, 5 insertions(+), 5 deletions(-) diff --git a/mysql-test/r/tmp_table_error.result b/mysql-test/r/tmp_table_error.result index c0c8b203dfb..3a1a9725001 100644 --- a/mysql-test/r/tmp_table_error.result +++ b/mysql-test/r/tmp_table_error.result @@ -2630,5 +2630,5 @@ b as c2624, b as c2626 from t1 ) as tt1; -ERROR HY000: Index for table 'tmp' is corrupt; try to repair it +ERROR 0A000: Aria table 'tmp' has too many columns and/or indexes and/or unique constraints. drop table t1; diff --git a/mysql-test/t/tmp_table_error.test b/mysql-test/t/tmp_table_error.test index e09e45085fa..dbddaaaa4c7 100644 --- a/mysql-test/t/tmp_table_error.test +++ b/mysql-test/t/tmp_table_error.test @@ -6,7 +6,7 @@ create table t1 ( ) engine=innodb; --replace_regex /'.*'/'tmp'/ ---error 126 +--error 140 create table t2 as select 1 diff --git a/storage/maria/ma_create.c b/storage/maria/ma_create.c index dc041b79f06..6dd1d1b1a3a 100644 --- a/storage/maria/ma_create.c +++ b/storage/maria/ma_create.c @@ -716,9 +716,10 @@ int maria_create(const char *name, enum data_file_type datafile_type, share.base.extra_options|= MA_EXTRA_OPTIONS_INSERT_ORDER; } + share.state.state.key_file_length= MY_ALIGN(info_length, maria_block_size); DBUG_PRINT("info", ("info_length: %u", info_length)); /* There are only 16 bits for the total header length. */ - if (info_length > 65535) + if (share.state.state.key_file_length > 65535) { my_printf_error(HA_WRONG_CREATE_OPTION, "Aria table '%s' has too many columns and/or " @@ -775,8 +776,7 @@ int maria_create(const char *name, enum data_file_type datafile_type, maria_set_all_keys_active(share.state.key_map, keys); - share.base.keystart = share.state.state.key_file_length= - MY_ALIGN(info_length, maria_block_size); + share.base.keystart = share.state.state.key_file_length; share.base.max_key_block_length= maria_block_size; share.base.max_key_length=ALIGN_SIZE(max_key_length+4); share.base.records=ci->max_rows; From 012e724debdb9e95ed8dc79056c113d5efcc25e4 Mon Sep 17 00:00:00 2001 From: Vladislav Vaintroub Date: Thu, 10 Feb 2022 17:25:12 +0100 Subject: [PATCH 30/45] MDEV-27796 Windows - starting server with huge innodb-log-buffer-size may fail Fixed tpool::pread() and tpool::pwrite() to return SSIZE_T on Windows, so that huge numbers are not converted to negatives. Also, make sure to never attempt reading/writing more bytes than DWORD can accomodate (4G) --- tpool/aio_simulated.cc | 9 ++++++--- tpool/tpool.h | 4 ++-- 2 files changed, 8 insertions(+), 5 deletions(-) diff --git a/tpool/aio_simulated.cc b/tpool/aio_simulated.cc index 93b2ae134b2..6b6fe71c8ab 100644 --- a/tpool/aio_simulated.cc +++ b/tpool/aio_simulated.cc @@ -72,7 +72,7 @@ struct WinIoInit static WinIoInit win_io_init; -int pread(const native_file_handle &h, void *buf, size_t count, +SSIZE_T pread(const native_file_handle &h, void *buf, size_t count, unsigned long long offset) { OVERLAPPED ov{}; @@ -81,6 +81,8 @@ int pread(const native_file_handle &h, void *buf, size_t count, ov.Offset= uli.LowPart; ov.OffsetHigh= uli.HighPart; ov.hEvent= win_get_syncio_event(); + if (count > 0xFFFFFFFF) + count= 0xFFFFFFFF; if (ReadFile(h, buf, (DWORD) count, 0, &ov) || (GetLastError() == ERROR_IO_PENDING)) @@ -93,7 +95,7 @@ int pread(const native_file_handle &h, void *buf, size_t count, return -1; } -int pwrite(const native_file_handle &h, void *buf, size_t count, +SSIZE_T pwrite(const native_file_handle &h, void *buf, size_t count, unsigned long long offset) { OVERLAPPED ov{}; @@ -102,7 +104,8 @@ int pwrite(const native_file_handle &h, void *buf, size_t count, ov.Offset= uli.LowPart; ov.OffsetHigh= uli.HighPart; ov.hEvent= win_get_syncio_event(); - + if (count > 0xFFFFFFFF) + count= 0xFFFFFFFF; if (WriteFile(h, buf, (DWORD) count, 0, &ov) || (GetLastError() == ERROR_IO_PENDING)) { diff --git a/tpool/tpool.h b/tpool/tpool.h index 3a5658c0f36..ed9411e5de5 100644 --- a/tpool/tpool.h +++ b/tpool/tpool.h @@ -252,9 +252,9 @@ create_thread_pool_win(int min_threads= DEFAULT_MIN_POOL_THREADS, opened with FILE_FLAG_OVERLAPPED, and bound to completion port. */ -int pwrite(const native_file_handle &h, void *buf, size_t count, +SSIZE_T pwrite(const native_file_handle &h, void *buf, size_t count, unsigned long long offset); -int pread(const native_file_handle &h, void *buf, size_t count, +SSIZE_T pread(const native_file_handle &h, void *buf, size_t count, unsigned long long offset); HANDLE win_get_syncio_event(); #endif From 3a52569499e2f0c4d1f25db1e81617a9d9755400 Mon Sep 17 00:00:00 2001 From: Sergei Petrunia Date: Thu, 10 Feb 2022 14:23:20 +0300 Subject: [PATCH 31/45] MDEV-25636: Bug report: abortion in sql/sql_parse.cc:6294 The asserion failure was caused by this query select /*id=1*/ from t1 where col= ( select /*id=2*/ from ... where corr_cond1 union select /*id=4*/ from ... where corr_cond2) Here, - select with id=2 was correlated due to corr_cond1. - select with id=4 was initially correlated due to corr_cond2, but then the optimizer optimized away the correlation, making the select with id=4 uncorrelated. However, since select with id=2 remained correlated, the execution had to re-compute the whole UNION. When it tried to execute select with id=4, it hit an assertion (join buffer already free'd). This is because select with id=4 has freed its execution structures after it has been executed once. The select is uncorrelated, so it did not expect it would need to be executed for the second time. Fixed this by adding this logic in st_select_lex::optimize_unflattened_subqueries(): If a member of a UNION is correlated, mark all its members as correlated, so that they are prepared to be executed multiple times. --- mysql-test/r/subselect4.result | 4 ++- mysql-test/r/union_innodb.result | 34 ++++++++++++++++++++++++ mysql-test/t/subselect4.test | 2 ++ mysql-test/t/union_innodb.test | 45 ++++++++++++++++++++++++++++++++ sql/sql_lex.cc | 16 +++++++++++- 5 files changed, 99 insertions(+), 2 deletions(-) create mode 100644 mysql-test/r/union_innodb.result create mode 100644 mysql-test/t/union_innodb.test diff --git a/mysql-test/r/subselect4.result b/mysql-test/r/subselect4.result index b1db309ec18..2657977dae7 100644 --- a/mysql-test/r/subselect4.result +++ b/mysql-test/r/subselect4.result @@ -1358,6 +1358,8 @@ INSERT IGNORE INTO t2 VALUES (8,0,0),(5,0,0); CREATE TABLE t3 (f4 int,KEY (f4)) ; INSERT IGNORE INTO t3 VALUES (0),(0); set @@optimizer_switch='semijoin=off'; +# NOTE: the following should have 'SUBQUERY', not 'DEPENDENT SUBQUERY' +# for line with id=2, see MDEV-27794. EXPLAIN SELECT * FROM t1 WHERE (SELECT f2 FROM t2 @@ -1367,7 +1369,7 @@ FROM t3 AS SQ1_t1 JOIN t3 AS SQ1_t3 ON SQ1_t3.f4 GROUP BY SQ1_t1.f4)); id select_type table type possible_keys key key_len ref rows Extra 1 PRIMARY t1 system NULL NULL NULL NULL 1 -2 SUBQUERY t2 ALL NULL NULL NULL NULL 2 Using where +2 DEPENDENT SUBQUERY t2 ALL NULL NULL NULL NULL 2 Using where 3 SUBQUERY SQ1_t1 index NULL f4 5 NULL 2 Using index; Using temporary 3 SUBQUERY SQ1_t3 index f4 f4 5 NULL 2 Using where; Using index; Using join buffer (flat, BNL join) SELECT * FROM t1 WHERE diff --git a/mysql-test/r/union_innodb.result b/mysql-test/r/union_innodb.result new file mode 100644 index 00000000000..876897fa865 --- /dev/null +++ b/mysql-test/r/union_innodb.result @@ -0,0 +1,34 @@ +# +# MDEV-25636: Bug report: abortion in sql/sql_parse.cc:6294 +# +CREATE TABLE t1 (i1 int)engine=innodb; +INSERT INTO `t1` VALUES (62),(66); +CREATE TABLE t2 (i1 int) engine=innodb; +SELECT 1 FROM t1 +WHERE t1.i1 =( SELECT t1.i1 FROM t2 +UNION SELECT i1 FROM (t1 AS dt1 natural JOIN t2) +window w1 as (partition by t1.i1)); +1 +drop table t1,t2; +# Another testcase +CREATE TABLE t1 (i3 int NOT NULL, i1 int , i2 int , i4 int , PRIMARY key(i2)); +INSERT INTO t1 VALUES (6,72,98,98),(46,1,6952,0); +SELECT i1 FROM t1 +WHERE t1.i3 = +(SELECT ref_4.i2 FROM t1 AS ref_4 +WHERE t1.i2 > (SELECT i3 FROM t1 ORDER BY i3 LIMIT 1 OFFSET 4) +UNION +SELECT ref_6.i2 +FROM (t1 AS ref_5 JOIN t1 AS ref_6 ON ((ref_6.i1 > ref_6.i2) OR (ref_5.i4 < ref_5.i4))) +WHERE (t1.i2 >= t1.i2)); +i1 +drop table t1; +# +# MDEV-25761: Assertion `aggr != __null' failed in sub_select_postjoin_aggr +# +CREATE TABLE t1 ( a int NOT NULL PRIMARY KEY) engine=innodb; +INSERT INTO t1 VALUES (0),(4),(31); +CREATE TABLE t2 (i int) engine=innodb; +DELETE FROM t1 WHERE t1.a = +(SELECT t1.a FROM t2 UNION SELECT DISTINCT 52 FROM t2 r WHERE t1.a = t1.a); +DROP TABLE t1,t2; diff --git a/mysql-test/t/subselect4.test b/mysql-test/t/subselect4.test index bd1e20cb5d6..93389571c5c 100644 --- a/mysql-test/t/subselect4.test +++ b/mysql-test/t/subselect4.test @@ -1039,6 +1039,8 @@ INSERT IGNORE INTO t3 VALUES (0),(0); set @@optimizer_switch='semijoin=off'; +--echo # NOTE: the following should have 'SUBQUERY', not 'DEPENDENT SUBQUERY' +--echo # for line with id=2, see MDEV-27794. EXPLAIN SELECT * FROM t1 WHERE (SELECT f2 FROM t2 diff --git a/mysql-test/t/union_innodb.test b/mysql-test/t/union_innodb.test new file mode 100644 index 00000000000..cb805a30bb4 --- /dev/null +++ b/mysql-test/t/union_innodb.test @@ -0,0 +1,45 @@ +--source include/have_innodb.inc + +--echo # +--echo # MDEV-25636: Bug report: abortion in sql/sql_parse.cc:6294 +--echo # + +CREATE TABLE t1 (i1 int)engine=innodb; +INSERT INTO `t1` VALUES (62),(66); +CREATE TABLE t2 (i1 int) engine=innodb; + +SELECT 1 FROM t1 +WHERE t1.i1 =( SELECT t1.i1 FROM t2 + UNION SELECT i1 FROM (t1 AS dt1 natural JOIN t2) + window w1 as (partition by t1.i1)); + +drop table t1,t2; + +--echo # Another testcase +CREATE TABLE t1 (i3 int NOT NULL, i1 int , i2 int , i4 int , PRIMARY key(i2)); +INSERT INTO t1 VALUES (6,72,98,98),(46,1,6952,0); + +SELECT i1 FROM t1 +WHERE t1.i3 = + (SELECT ref_4.i2 FROM t1 AS ref_4 + WHERE t1.i2 > (SELECT i3 FROM t1 ORDER BY i3 LIMIT 1 OFFSET 4) + UNION + SELECT ref_6.i2 + FROM (t1 AS ref_5 JOIN t1 AS ref_6 ON ((ref_6.i1 > ref_6.i2) OR (ref_5.i4 < ref_5.i4))) + WHERE (t1.i2 >= t1.i2)); + +drop table t1; + +--echo # +--echo # MDEV-25761: Assertion `aggr != __null' failed in sub_select_postjoin_aggr +--echo # + +CREATE TABLE t1 ( a int NOT NULL PRIMARY KEY) engine=innodb; +INSERT INTO t1 VALUES (0),(4),(31); + +CREATE TABLE t2 (i int) engine=innodb; + +DELETE FROM t1 WHERE t1.a = + (SELECT t1.a FROM t2 UNION SELECT DISTINCT 52 FROM t2 r WHERE t1.a = t1.a); + +DROP TABLE t1,t2; diff --git a/sql/sql_lex.cc b/sql/sql_lex.cc index 125bbfe1bfd..47ff2836aba 100644 --- a/sql/sql_lex.cc +++ b/sql/sql_lex.cc @@ -3898,7 +3898,21 @@ bool st_select_lex::optimize_unflattened_subqueries(bool const_only) } if (empty_union_result) subquery_predicate->no_rows_in_result(); - if (!is_correlated_unit) + + if (is_correlated_unit) + { + /* + Some parts of UNION are not correlated. This means we will need to + re-execute the whole UNION every time. Mark all parts of the UNION + as correlated so that they are prepared to be executed multiple + times (if we don't do that, some part of the UNION may free its + execution data at the end of first execution and crash on the second + execution) + */ + for (SELECT_LEX *sl= un->first_select(); sl; sl= sl->next_select()) + sl->uncacheable |= UNCACHEABLE_DEPENDENT; + } + else un->uncacheable&= ~UNCACHEABLE_DEPENDENT; subquery_predicate->is_correlated= is_correlated_unit; } From 7c6ec0a53be807ee13c93bb7e6826fa2ce3b29a9 Mon Sep 17 00:00:00 2001 From: Samuel Thibault Date: Tue, 8 Feb 2022 00:18:27 +0000 Subject: [PATCH 32/45] MDEV-27804 Fails to build - perf schema - thread id of type uintptr_t requires header While building on GNU/Hurd and kfreebsd. On the C++ standard uintptr_t can be defined in ref: https://www.cplusplus.com/reference/cstdint/ Fixes: 0d44792a835128a83ff07f14dbbcdd621df9f7da --- storage/perfschema/my_thread.h | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/storage/perfschema/my_thread.h b/storage/perfschema/my_thread.h index 5ddea9b1303..c1a079ce34d 100644 --- a/storage/perfschema/my_thread.h +++ b/storage/perfschema/my_thread.h @@ -14,6 +14,10 @@ #include #endif +#if defined(HAVE_INTEGER_PTHREAD_SELF) +#include +#endif + typedef pthread_key_t thread_local_key_t; typedef pthread_t my_thread_handle; typedef pthread_attr_t my_thread_attr_t; From 3b10e8f80c434277207db9a613d9110c8283ea6a Mon Sep 17 00:00:00 2001 From: Vlad Lesin Date: Wed, 9 Feb 2022 16:50:28 +0300 Subject: [PATCH 33/45] MDEV-27746 Wrong comparision of BLOB's empty preffix with non-preffixed BLOB causes rows count mismatch for clustered and secondary indexes during non-locking read row_sel_sec_rec_is_for_clust_rec() treats empty BLOB prefix field in secondary index as a field equal to any external BLOB field in clustered index. Row_sel_get_clust_rec_for_mysql::operator() doesn't zerro out clustered record pointer in row_search_mvcc(), and row_search_mvcc() thinks that delete-marked secondary index record has visible for "CHECK TABLE"'s read view old-versioned clustered index record, and row_scan_index_for_mysql() counts it as a row. The fix is to execute row_sel_sec_rec_is_for_blob() in row_sel_sec_rec_is_for_clust_rec() if clustered field contains BLOB's reference. --- .../suite/innodb/r/blob_cmp_empty.result | 19 ++++++++++++++ mysql-test/suite/innodb/t/blob_cmp_empty.test | 26 +++++++++++++++++++ storage/innobase/row/row0sel.cc | 8 +++++- 3 files changed, 52 insertions(+), 1 deletion(-) create mode 100644 mysql-test/suite/innodb/r/blob_cmp_empty.result create mode 100644 mysql-test/suite/innodb/t/blob_cmp_empty.test diff --git a/mysql-test/suite/innodb/r/blob_cmp_empty.result b/mysql-test/suite/innodb/r/blob_cmp_empty.result new file mode 100644 index 00000000000..24ae8e1c01e --- /dev/null +++ b/mysql-test/suite/innodb/r/blob_cmp_empty.result @@ -0,0 +1,19 @@ +connect prevent_purge,localhost,root,,; +start transaction with consistent snapshot; +connection default; +SET @fill_amount = (@@innodb_page_size / 2 ) + 1; +CREATE TABLE t1 (col_text TEXT NOT NULL, KEY (col_text(9))) ENGINE=InnoDB; +INSERT INTO t1 (col_text) VALUES (REPEAT('x', @fill_amount)); +UPDATE t1 SET col_text=''; +UPDATE t1 SET col_text=REPEAT('y', @fill_amount); +connect con1,localhost,root,,; +SET @fill_amount = (@@innodb_page_size / 2 ) + 1; +BEGIN; +INSERT INTO t1 (col_text) VALUES (REPEAT('z', @fill_amount)); +connection default; +CHECK TABLE t1; +Table Op Msg_type Msg_text +test.t1 check status OK +disconnect con1; +disconnect prevent_purge; +DROP TABLE t1; diff --git a/mysql-test/suite/innodb/t/blob_cmp_empty.test b/mysql-test/suite/innodb/t/blob_cmp_empty.test new file mode 100644 index 00000000000..f41ac79b16f --- /dev/null +++ b/mysql-test/suite/innodb/t/blob_cmp_empty.test @@ -0,0 +1,26 @@ +--source include/innodb_row_format.inc +--source include/count_sessions.inc +--connect(prevent_purge,localhost,root,,) +start transaction with consistent snapshot; + +--connection default +SET @fill_amount = (@@innodb_page_size / 2 ) + 1; +CREATE TABLE t1 (col_text TEXT NOT NULL, KEY (col_text(9))) ENGINE=InnoDB; + +INSERT INTO t1 (col_text) VALUES (REPEAT('x', @fill_amount)); +UPDATE t1 SET col_text=''; +UPDATE t1 SET col_text=REPEAT('y', @fill_amount); + +--connect(con1,localhost,root,,) +SET @fill_amount = (@@innodb_page_size / 2 ) + 1; +BEGIN; +INSERT INTO t1 (col_text) VALUES (REPEAT('z', @fill_amount)); + +--connection default +# If the bug is not fixed, CHECK TABLE will complain about wrong secondary index +# rows count +CHECK TABLE t1; +--disconnect con1 +--disconnect prevent_purge +DROP TABLE t1; +--source include/wait_until_count_sessions.inc diff --git a/storage/innobase/row/row0sel.cc b/storage/innobase/row/row0sel.cc index 87c67edff4b..d513ab09dcf 100644 --- a/storage/innobase/row/row0sel.cc +++ b/storage/innobase/row/row0sel.cc @@ -352,11 +352,16 @@ row_sel_sec_rec_is_for_clust_rec( } len = clust_len; + ulint prefix_len = ifield->prefix_len; if (rec_offs_nth_extern(clust_offs, clust_pos)) { + /* BLOB can contain prefix. */ len -= BTR_EXTERN_FIELD_REF_SIZE; + if (!len) { + goto compare_blobs; + } } - if (ulint prefix_len = ifield->prefix_len) { + if (prefix_len) { len = dtype_get_at_most_n_mbchars( col->prtype, col->mbminlen, col->mbmaxlen, prefix_len, len, @@ -369,6 +374,7 @@ row_sel_sec_rec_is_for_clust_rec( check_for_blob: if (rec_offs_nth_extern(clust_offs, clust_pos)) { +compare_blobs: if (!row_sel_sec_rec_is_for_blob( col->mtype, col->prtype, col->mbminlen, From bd70ae05654544a50f5aebf59ab50835a235874e Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Marko=20M=C3=A4kel=C3=A4?= Date: Fri, 11 Feb 2022 11:44:40 +0200 Subject: [PATCH 34/45] MDEV-27774 fixup: Replace sspin_lock with srw_lock srw_lock in log_sys.append_prepare() turned out to yield best throughput. We might try a NUMA aware spin lock implementation later. --- storage/innobase/include/log0log.h | 2 +- storage/innobase/include/srw_lock.h | 9 --------- storage/innobase/log/log0log.cc | 2 ++ storage/innobase/mtr/mtr0mtr.cc | 8 ++++---- storage/innobase/sync/srw_lock.cc | 7 ------- 5 files changed, 7 insertions(+), 21 deletions(-) diff --git a/storage/innobase/include/log0log.h b/storage/innobase/include/log0log.h index 220d1680513..f66d7f368ae 100644 --- a/storage/innobase/include/log0log.h +++ b/storage/innobase/include/log0log.h @@ -214,7 +214,7 @@ public: private: /** spin lock protecting lsn, buf_free in append_prepare() */ - MY_ALIGNED(CPU_LEVEL1_DCACHE_LINESIZE) sspin_lock lsn_lock; + MY_ALIGNED(CPU_LEVEL1_DCACHE_LINESIZE) srw_mutex lsn_lock; public: /** first free offset within buf use; protected by lsn_lock */ Atomic_relaxed buf_free; diff --git a/storage/innobase/include/srw_lock.h b/storage/innobase/include/srw_lock.h index 9fba021df25..f3c7456b701 100644 --- a/storage/innobase/include/srw_lock.h +++ b/storage/innobase/include/srw_lock.h @@ -520,12 +520,3 @@ typedef srw_lock_impl srw_lock; typedef srw_lock_impl srw_spin_lock; #endif - -/** Simple spin lock */ -struct sspin_lock -{ - std::atomic word{0}; - void lock() noexcept; - void unlock() noexcept - { ut_ad(word); word.store(0, std::memory_order_release); } -}; diff --git a/storage/innobase/log/log0log.cc b/storage/innobase/log/log0log.cc index 739adcf1b97..e0b84285f34 100644 --- a/storage/innobase/log/log0log.cc +++ b/storage/innobase/log/log0log.cc @@ -101,6 +101,7 @@ void log_t::create() ut_ad(!is_initialised()); latch.SRW_LOCK_INIT(log_latch_key); + lsn_lock.init(); /* LSN 0 and 1 are reserved; @see buf_page_t::oldest_modification_ */ lsn.store(FIRST_LSN, std::memory_order_relaxed); @@ -1070,6 +1071,7 @@ void log_t::close() #endif latch.destroy(); + lsn_lock.destroy(); recv_sys.close(); diff --git a/storage/innobase/mtr/mtr0mtr.cc b/storage/innobase/mtr/mtr0mtr.cc index bf17d79cf7a..977e5b762bc 100644 --- a/storage/innobase/mtr/mtr0mtr.cc +++ b/storage/innobase/mtr/mtr0mtr.cc @@ -789,7 +789,7 @@ ATTRIBUTE_COLD static void log_overwrite_warning(lsn_t age, lsn_t capacity) ATTRIBUTE_COLD void log_t::append_prepare_wait(bool ex) noexcept { log_sys.waits++; - log_sys.lsn_lock.unlock(); + log_sys.lsn_lock.wr_unlock(); if (ex) log_sys.latch.wr_unlock(); @@ -804,7 +804,7 @@ ATTRIBUTE_COLD void log_t::append_prepare_wait(bool ex) noexcept else log_sys.latch.rd_lock(SRW_LOCK_CALL); - log_sys.lsn_lock.lock(); + log_sys.lsn_lock.wr_lock(); } /** Reserve space in the log buffer for appending data. @@ -823,7 +823,7 @@ std::pair log_t::append_prepare(size_t size, bool ex) noexcept #endif const lsn_t checkpoint_margin{last_checkpoint_lsn + log_capacity - size}; const size_t avail{(pmem ? size_t(capacity()) : buf_size) - size}; - lsn_lock.lock(); + lsn_lock.wr_lock(); /* Just use SRWLOCK or pthread_mutex_t */ write_to_buf++; for (ut_d(int count= 50); @@ -844,7 +844,7 @@ std::pair log_t::append_prepare(size_t size, bool ex) noexcept if (pmem && new_buf_free >= file_size) new_buf_free-= size_t(capacity()); buf_free= new_buf_free; - lsn_lock.unlock(); + lsn_lock.wr_unlock(); if (UNIV_UNLIKELY(l > checkpoint_margin) || (!pmem && b >= max_buf_free)) diff --git a/storage/innobase/sync/srw_lock.cc b/storage/innobase/sync/srw_lock.cc index bc3ef0a7b4e..b0e2bf17e08 100644 --- a/storage/innobase/sync/srw_lock.cc +++ b/storage/innobase/sync/srw_lock.cc @@ -102,13 +102,6 @@ static inline void srw_pause(unsigned delay) HMT_medium(); } -void sspin_lock::lock() noexcept -{ - while (word.exchange(true, std::memory_order_acquire)) - while (word.load(std::memory_order_relaxed)) - srw_pause(1); -} - #ifdef SUX_LOCK_GENERIC template<> void srw_mutex_impl::wr_wait() { From fb875055c617832c19c1f7f5c44960eaf424a0c9 Mon Sep 17 00:00:00 2001 From: Krunal Bauskar Date: Fri, 11 Feb 2022 18:10:50 +0800 Subject: [PATCH 35/45] MDEV-27805: tpcc workload shows regression with MDB-10.6 - regression got revealed while running tpcc workload. - as part of MDEV-25919 changes logic for statistics computation was revamped. - if the table has changed to certain threshold then table is added to statistics recomputation queue (dict_stats_recalc_pool_add) - after the table is added to queue the background statistics thread is notified - during revamp the condition to notify background statistics threads was wrongly updated to check if the queue/vector is empty when it should check if there is queue/vector has entries to process. - vec.begin() == vec.end() : only when vector is empty - also accessing these iterator outside the parallely changing vector is not safe - fix now tend to notify background statistics thread if the logic adds an entry to the queue/vector. --- storage/innobase/dict/dict0stats_bg.cc | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/storage/innobase/dict/dict0stats_bg.cc b/storage/innobase/dict/dict0stats_bg.cc index 645f5818f57..2dd83d97687 100644 --- a/storage/innobase/dict/dict0stats_bg.cc +++ b/storage/innobase/dict/dict0stats_bg.cc @@ -108,17 +108,18 @@ static void dict_stats_recalc_pool_add(table_id_t id) { ut_ad(!srv_read_only_mode); ut_ad(id); + bool schedule = false; mysql_mutex_lock(&recalc_pool_mutex); const auto begin= recalc_pool.begin(), end= recalc_pool.end(); if (end == std::find_if(begin, end, [&](const recalc &r){return r.id == id;})) { recalc_pool.emplace_back(recalc{id, recalc::IDLE}); + schedule = true; } mysql_mutex_unlock(&recalc_pool_mutex); - - if (begin == end) + if (schedule) dict_stats_schedule_now(); } From 1a7573d5a5f79fd46b6905433b18c812d74c46cd Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Marko=20M=C3=A4kel=C3=A4?= Date: Fri, 11 Feb 2022 12:58:42 +0200 Subject: [PATCH 36/45] Disable innodb_gis.rtree_compress2 --- mysql-test/suite/innodb_gis/disabled.def | 1 + 1 file changed, 1 insertion(+) diff --git a/mysql-test/suite/innodb_gis/disabled.def b/mysql-test/suite/innodb_gis/disabled.def index bf500c1cb93..2d4d3686dd1 100644 --- a/mysql-test/suite/innodb_gis/disabled.def +++ b/mysql-test/suite/innodb_gis/disabled.def @@ -12,3 +12,4 @@ rtree_concurrent_srch : MDEV-15284 COUNT(*) mismatch rtree_recovery : MDEV-15284 COUNT(*) mismatch +rtree_compress2 : MDEV-16269 CHECK TABLE reports wrong count From 91d9e9bd809aea0876708b590f74e297d4ff074d Mon Sep 17 00:00:00 2001 From: Vladislav Vaintroub Date: Fri, 11 Feb 2022 14:27:57 +0100 Subject: [PATCH 37/45] MDEV-27813 Windows, compiling : RelWithDebInfo should use /Ob2 Fixed inlining flags. Remove /Ob1 added by CMake for RelWithDebInfo. (the actual compiler default is /Ob2 if optimizations are enabled) Allow to define custom /Ob flag with new variable MSVC_INLINE, if desired --- cmake/os/Windows.cmake | 12 ++++++++++++ 1 file changed, 12 insertions(+) diff --git a/cmake/os/Windows.cmake b/cmake/os/Windows.cmake index 71ad4ab0912..f47d4ebc98d 100644 --- a/cmake/os/Windows.cmake +++ b/cmake/os/Windows.cmake @@ -169,8 +169,20 @@ IF(MSVC) IF((NOT "${${flag}}" MATCHES "/Zi") AND (NOT "${${flag}}" MATCHES "/Z7")) STRING(APPEND ${flag} " /Zi") ENDIF() + # Remove inlining flags, added by CMake, if any. + # Compiler default is fine. + STRING(REGEX REPLACE "/Ob[0-3]" "" "${flag}" "${${flag}}" ) ENDFOREACH() + # Allow to overwrite the inlining flag + SET(MSVC_INLINE "" CACHE STRING + "MSVC Inlining option, either empty, or one of /Ob0,/Ob1,/Ob2,/Ob3") + IF(MSVC_INLINE MATCHES "/Ob[0-3]") + ADD_COMPILE_OPTIONS(${MSVC_INLINE}) + ELSEIF(NOT(MSVC_INLINE STREQUAL "")) + MESSAGE(FATAL_ERROR "Invalid option for MSVC_INLINE") + ENDIF() + IF(WITH_ASAN OR WITH_UBSAN) # Workaround something Linux specific SET(SECURITY_HARDENED 0 CACHE INTERNAL "" FORCE) From 8274c207dfd1bdac10e71f17ce3acccf330c8db6 Mon Sep 17 00:00:00 2001 From: Daniel Bartholomew Date: Sat, 12 Feb 2022 13:09:01 -0500 Subject: [PATCH 38/45] bump the VERSION --- VERSION | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/VERSION b/VERSION index b40fcec987b..bffd045a6d6 100644 --- a/VERSION +++ b/VERSION @@ -1,4 +1,4 @@ MYSQL_VERSION_MAJOR=10 MYSQL_VERSION_MINOR=8 -MYSQL_VERSION_PATCH=2 +MYSQL_VERSION_PATCH=3 SERVER_MATURITY=gamma From c62720d07f8b0f5fc76d3db5b866dd4360ef01ae Mon Sep 17 00:00:00 2001 From: Daniel Bartholomew Date: Sat, 12 Feb 2022 13:39:28 -0500 Subject: [PATCH 39/45] bump the VERSION --- VERSION | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/VERSION b/VERSION index d6ba95be162..f14fd53dad9 100644 --- a/VERSION +++ b/VERSION @@ -1,4 +1,4 @@ MYSQL_VERSION_MAJOR=10 MYSQL_VERSION_MINOR=7 -MYSQL_VERSION_PATCH=3 +MYSQL_VERSION_PATCH=4 SERVER_MATURITY=stable From d0e853b38ec549dae981d2b7971ec9cba233a96d Mon Sep 17 00:00:00 2001 From: Daniel Bartholomew Date: Sat, 12 Feb 2022 13:59:39 -0500 Subject: [PATCH 40/45] bump the VERSION --- VERSION | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/VERSION b/VERSION index 38d0bcd7a05..61106115ce1 100644 --- a/VERSION +++ b/VERSION @@ -1,4 +1,4 @@ MYSQL_VERSION_MAJOR=10 MYSQL_VERSION_MINOR=6 -MYSQL_VERSION_PATCH=7 +MYSQL_VERSION_PATCH=8 SERVER_MATURITY=stable From 1557204b05f907b1d0b1011ceb6c2ddcc758eaa5 Mon Sep 17 00:00:00 2001 From: Daniel Bartholomew Date: Sat, 12 Feb 2022 14:25:37 -0500 Subject: [PATCH 41/45] bump the VERSION --- VERSION | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/VERSION b/VERSION index 9d94c079411..98ae7ab3e4e 100644 --- a/VERSION +++ b/VERSION @@ -1,4 +1,4 @@ MYSQL_VERSION_MAJOR=10 MYSQL_VERSION_MINOR=5 -MYSQL_VERSION_PATCH=15 +MYSQL_VERSION_PATCH=16 SERVER_MATURITY=stable From b55b808b8320b36ac942a3ffb6afdb56016dc56e Mon Sep 17 00:00:00 2001 From: Daniel Bartholomew Date: Sat, 12 Feb 2022 15:00:45 -0500 Subject: [PATCH 42/45] bump the VERSION --- VERSION | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/VERSION b/VERSION index cd6f03a2b81..a1c118b88a8 100644 --- a/VERSION +++ b/VERSION @@ -1,4 +1,4 @@ MYSQL_VERSION_MAJOR=10 MYSQL_VERSION_MINOR=4 -MYSQL_VERSION_PATCH=24 +MYSQL_VERSION_PATCH=25 SERVER_MATURITY=stable From e50421be21e86541fa3815c09525623f33b3818d Mon Sep 17 00:00:00 2001 From: Daniel Bartholomew Date: Sat, 12 Feb 2022 15:18:56 -0500 Subject: [PATCH 43/45] bump the VERSION --- VERSION | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/VERSION b/VERSION index 6deead00756..bffeddf780b 100644 --- a/VERSION +++ b/VERSION @@ -1,4 +1,4 @@ MYSQL_VERSION_MAJOR=10 MYSQL_VERSION_MINOR=3 -MYSQL_VERSION_PATCH=34 +MYSQL_VERSION_PATCH=35 SERVER_MATURITY=stable From e777645d483420fb65e26bb20fde4f0f9ebcd05c Mon Sep 17 00:00:00 2001 From: Daniel Bartholomew Date: Sat, 12 Feb 2022 15:43:53 -0500 Subject: [PATCH 44/45] bump the VERSION --- VERSION | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/VERSION b/VERSION index d9c4622d96b..1686f2ed10d 100644 --- a/VERSION +++ b/VERSION @@ -1,3 +1,3 @@ MYSQL_VERSION_MAJOR=10 MYSQL_VERSION_MINOR=2 -MYSQL_VERSION_PATCH=43 +MYSQL_VERSION_PATCH=44 From 7b891008ceb2f571ce4f5916217acad8abb46464 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Marko=20M=C3=A4kel=C3=A4?= Date: Sun, 13 Feb 2022 17:33:40 +0200 Subject: [PATCH 45/45] MDEV-27817 InnoDB recovery of recently created files is not crash-safe Before commit 86dc7b4d4cfe15a2d37f8b5f60c4fce5dba9491d (MDEV-24626) all tablespace ID that needed recovery were known already in recv_init_crash_recovery_spaces(). recv_sys_t::recover_deferred(): Invoke fil_names_dirty(space) on the newly initialized tablespace. In this way, if the next log checkpoint occurs at some LSN that is after the initialization of the tablespace and before the last recovered LSN, a FILE_MODIFY record will be written, so that a subsequent recovery will succeed. The recovery was broken when commit 0261eac57f137c5daae90f5bb1eaa4bf48ee431b merged the 10.5 commit f443cd11007ab89512d4141472cbd9d3b524bad6 (MDEV-27022). --- storage/innobase/log/log0recv.cc | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/storage/innobase/log/log0recv.cc b/storage/innobase/log/log0recv.cc index 2cfd2230608..eea28a69392 100644 --- a/storage/innobase/log/log0recv.cc +++ b/storage/innobase/log/log0recv.cc @@ -905,6 +905,7 @@ bool recv_sys_t::recover_deferred(recv_sys_t::map::iterator &p, node->deferred= true; if (!space->acquire()) goto fail; + fil_names_dirty(space); const bool is_compressed= fil_space_t::is_compressed(flags); #ifdef _WIN32 const bool is_sparse= is_compressed; @@ -4224,7 +4225,6 @@ completed: err = recv_rename_files(); } mysql_mutex_unlock(&recv_sys.mutex); - mysql_mutex_unlock(&log_sys.mutex); recv_lsn_checks_on = true; @@ -4236,6 +4236,7 @@ completed: err = DB_CORRUPTION; } + mysql_mutex_unlock(&log_sys.mutex); return err; }