1
0
mirror of https://github.com/MariaDB/server.git synced 2025-08-08 11:22:35 +03:00

Merge 10.6 into 10.7

This commit is contained in:
Marko Mäkelä
2021-10-13 16:37:12 +03:00
85 changed files with 1238 additions and 391 deletions

3
.gitignore vendored
View File

@@ -359,6 +359,7 @@ x86/
build/
bld/
[Bb]in/
/cmake-build-debug/
[Oo]bj/
# Roslyn cache directories
@@ -542,7 +543,7 @@ compile_commands.json
.vscode/
# Clion && other JetBrains ides
.idea
/.idea/
.cache/clangd

View File

@@ -1685,11 +1685,14 @@ static struct my_option my_long_options[] =
&opt_default_auth, &opt_default_auth, 0,
GET_STR, REQUIRED_ARG, 0, 0, 0, 0, 0, 0},
{"binary-mode", 0,
"By default, ASCII '\\0' is disallowed and '\\r\\n' is translated to '\\n'. "
"This switch turns off both features, and also turns off parsing of all client"
"commands except \\C and DELIMITER, in non-interactive mode (for input "
"piped to mysql or loaded using the 'source' command). This is necessary "
"when processing output from mysqlbinlog that may contain blobs.",
"Binary mode allows certain character sequences to be processed as data "
"that would otherwise be treated with a special meaning by the parser. "
"Specifically, this switch turns off parsing of all client commands except "
"\\C and DELIMITER in non-interactive mode (i.e., when binary mode is "
"combined with either 1) piped input, 2) the --batch mysql option, or 3) "
"the 'source' command). Also, in binary mode, occurrences of '\\r\\n' and "
"ASCII '\\0' are preserved within strings, whereas by default, '\\r\\n' is "
"translated to '\\n' and '\\0' is disallowed in user input.",
&opt_binary_mode, &opt_binary_mode, 0, GET_BOOL, NO_ARG, 0, 0, 0, 0, 0, 0},
{"connect-expired-password", 0,
"Notify the server that this client is prepared to handle expired "
@@ -2385,8 +2388,15 @@ static bool add_line(String &buffer, char *line, size_t line_length,
{
// Found possbile one character command like \c
if (!(inchar = (uchar) *++pos))
break; // readline adds one '\'
/*
The null-terminating character (ASCII '\0') marks the end of user
input. Then, by default, upon encountering a '\0' while parsing, it
should stop. However, some data naturally contains binary zeros
(e.g., zipped files). Real_binary_mode signals the parser to expect
'\0' within the data and not to end parsing if found.
*/
if (!(inchar = (uchar) *++pos) && (!real_binary_mode || !*in_string))
break; // readline adds one '\'
if (*in_string || inchar == 'N') // \N is short for NULL
{ // Don't allow commands in string
*out++='\\';

2
debian/control vendored
View File

@@ -629,7 +629,7 @@ Recommends: libhtml-template-perl
Pre-Depends: adduser (>= 3.40),
debconf,
mariadb-common (>= ${source:Version})
Depends: galera-4 (>=26.4),
Depends: galera-4 (>= 26.4),
gawk,
iproute2 [linux-any],
libdbi-perl,

View File

@@ -161,7 +161,7 @@ EOF
# Clean up old flags before setting new one
rm -f $mysql_datadir/debian-*.flag
# Flag data dir to avoid downgrades
touch $mysql_datadir/debian-10.7.flag
touch "$mysql_datadir/debian-$MAJOR_VER.flag"
# initiate databases. Output is not allowed by debconf :-(
# This will fail if we are upgrading an existing database; in this case

View File

@@ -5,6 +5,7 @@ usr/bin/mariadb-test-embedded
usr/lib/*/libmariadb3/plugin/auth_test_plugin.so
usr/lib/*/libmariadb3/plugin/qa_auth_client.so
usr/lib/*/libmariadb3/plugin/qa_auth_interface.so
usr/lib/*/libmariadb3/plugin/test_sql_service.so
usr/lib/mysql/plugin/adt_null.so
usr/lib/mysql/plugin/auth_0x0100.so
usr/lib/mysql/plugin/auth_test_plugin.so

2
debian/po/de.po vendored
View File

@@ -10,7 +10,7 @@ msgstr ""
"POT-Creation-Date: 2019-07-23 19:16-0300\n"
"PO-Revision-Date: 2016-05-12 22:39+0100\n"
"Last-Translator: Chris Leick <c.leick@vollbio.de>\n"
"Language-Team: german <debian-l10n-german@lists.debian.org>\n"
"Language-Team: German <debian-l10n-german@lists.debian.org>\n"
"Language: \n"
"MIME-Version: 1.0\n"
"Content-Type: text/plain; charset=UTF-8\n"

2
debian/po/es.po vendored
View File

@@ -1,4 +1,4 @@
# mariadb translation to spanish
# MariaDB translation to Spanish
# Copyright (C) 2005-2016 Software in the Public Interest, SPI Inc.
# This file is distributed under the same license as the mariadb package.
#

2
debian/po/it.po vendored
View File

@@ -4,7 +4,7 @@
#
msgid ""
msgstr ""
"Project-Id-Version: mariadb-10.7 10.0.13 italian debconf templates\n"
"Project-Id-Version: mariadb-10.7 10.0.13 Italian debconf templates\n"
"Report-Msgid-Bugs-To: mariadb-10.7@packages.debian.org\n"
"POT-Creation-Date: 2019-07-23 19:16-0300\n"
"PO-Revision-Date: 2017-083-20 20:29+0100\n"

4
debian/rules vendored
View File

@@ -34,8 +34,8 @@ ifneq (,$(filter parallel=%,$(DEB_BUILD_OPTIONS)))
NUMJOBS = $(patsubst parallel=%,%,$(filter parallel=%,$(DEB_BUILD_OPTIONS)))
MAKEFLAGS += -j$(NUMJOBS)
else
# NUMJOBS cannot be empty as it is used as a parameter to mtr, default to 1.
NUMJOBS = 1
# NUMJOBS cannot be empty as it is used as a parameter to mtr, default to 'auto'.
NUMJOBS = auto
endif
# RocksDB cannot build on 32-bit platforms

109
debian/salsa-ci.yml vendored
View File

@@ -21,7 +21,7 @@ stages:
- build
- test
- upgrade in Sid
- upgrade from Buster/Stretch
- upgrade from Bullseye/Buster/Stretch
- upgrade extras
- test extras
- publish # Stage referenced by Salsa-CI template aptly stanza, so must exist even though not used
@@ -46,6 +46,11 @@ build:
- ccache -s # Show ccache stats to validate it worked
- mv ${CCACHE_TMP_DIR} ${CCACHE_WORK_DIR} || true
build bullseye-backports:
extends: .build-package
variables:
RELEASE: bullseye-backports
build buster-backports:
extends: .build-package
script:
@@ -114,7 +119,6 @@ blhc:
stage: test extras
needs:
- job: build native deb
artifacts: true
# In addition to Salsa-CI, also run these fully MariaDB specific build jobs
@@ -135,9 +139,10 @@ blhc:
dpkg -l | grep -iE 'maria|mysql|galera' || true # List installed
service mysql status || service mariadb status # Early MariaDB 10.5 only had 'mariadb'
mysql --skip-column-names -e "select @@version, @@version_comment" # Show version
echo 'SHOW DATABASES;' | mysql # List databases before upgrade
mysql -e "SELECT Host, User, plugin,authentication_string FROM user;" mysql
mysql -e "SELECT * FROM plugin;" mysql
mysql --table -e 'SHOW DATABASES;' # List databases before upgrade
mysql --table -e "SELECT host,user,plugin,authentication_string FROM user;" mysql
mysql --table -e "SELECT * FROM plugin;" mysql
mysql --table -e "SHOW PLUGINS;" mysql
.test-enable-sid-repos: &test-enable-sid-repos |
# Replace any old repos with just Sid
@@ -159,10 +164,12 @@ blhc:
cp -ra /etc/mysql debug/etc-mysql
cp -ra /var/log/mysql debug/var-log-mysql
mariadb --skip-column-names -e "select @@version, @@version_comment" # Show version
echo 'SHOW DATABASES;' | mariadb # List databases
mariadb -e "create database test; use test; create table t(a int primary key) engine=innodb; insert into t values (1); select * from t; drop table t; drop database test;" # Test that InnoDB works
mariadb -e "SELECT Host, User, plugin,authentication_string FROM user;" mysql
mariadb -e "SELECT * FROM plugin;" mysql
mariadb --table -e 'SHOW DATABASES;' # List databases
mariadb --table -e "SELECT host,user,plugin,authentication_string FROM user;" mysql
mariadb --table -e "SELECT * FROM plugin;" mysql
mariadb --table -e "SHOW PLUGINS;" mysql
# Test that InnoDB works and that command 'mysql' is also still usable
mysql -e "CREATE DATABASE test; USE test; CREATE TABLE t(a INT PRIMARY KEY) ENGINE=INNODB; INSERT INTO t VALUEs (1); SELECT * FROM t; DROP TABLE t; DROP DATABASE test;"
.test-verify-libs: &test-verify-libs
# Don't use a collapsed command as Gitlab-CI would hide each command from the output
@@ -214,7 +221,6 @@ fresh install:
stage: test
needs:
- job: build
artifacts: true
image: debian:${RELEASE}
artifacts:
when: always
@@ -236,7 +242,6 @@ mariadb-10.7 Sid upgrade:
stage: upgrade in Sid
needs:
- job: build
artifacts: true
image: debian:${RELEASE}
artifacts:
when: always
@@ -254,11 +259,36 @@ mariadb-10.7 Sid upgrade:
variables:
- $CI_COMMIT_TAG != null && $SALSA_CI_ENABLE_PIPELINE_ON_TAGS !~ /^(1|yes|true)$/
mariadb-10.3 Buster to mariadb-10.7 upgrade:
stage: upgrade from Buster/Stretch
mariadb-10.5 Bullseye to mariadb-10.7 upgrade:
stage: upgrade from Bullseye/Buster/Stretch
needs:
- job: build
image: debian:bullseye
artifacts:
when: always
name: "$CI_BUILD_NAME"
paths:
- ${WORKING_DIR}/debug
script:
- *test-prepare-container
# Install everything MariaDB currently in Debian Bullseye
- apt-get install -y 'default-mysql*' 'mariadb-*' 'libmariadb*'
# Verify installation of MariaDB from Bullseye
- *test-verify-initial
- *test-enable-sid-repos
- *test-install
- service mariadb status
- *test-verify-final
variables:
GIT_STRATEGY: none
except:
variables:
- $CI_COMMIT_TAG != null && $SALSA_CI_ENABLE_PIPELINE_ON_TAGS !~ /^(1|yes|true)$/
mariadb-10.3 Buster to mariadb-10.7 upgrade:
stage: upgrade from Bullseye/Buster/Stretch
needs:
- job: build
artifacts: true
image: debian:buster
artifacts:
when: always
@@ -282,10 +312,9 @@ mariadb-10.3 Buster to mariadb-10.7 upgrade:
- $CI_COMMIT_TAG != null && $SALSA_CI_ENABLE_PIPELINE_ON_TAGS !~ /^(1|yes|true)$/
mariadb-10.1 Stretch to mariadb-10.7 upgrade:
stage: upgrade from Buster/Stretch
stage: upgrade from Bullseye/Buster/Stretch
needs:
- job: build
artifacts: true
image: debian:stretch
artifacts:
when: always
@@ -299,8 +328,7 @@ mariadb-10.1 Stretch to mariadb-10.7 upgrade:
- apt-get install -y 'default-mysql*' 'mariadb-*' 'libmariadbd*' 'libmariadbclient*'
# Verify installation of MariaDB from Stretch
- *test-verify-initial
# Remove manpages 4.10 that conflicts with manpages-dev 5.10 on console_ioctl.4.gz
- apt-get remove -y manpages
- apt-get remove -y manpages # Workaround for Bug#99375
- *test-enable-sid-repos
- *test-install
- service mysql status
@@ -315,7 +343,6 @@ test basic features:
stage: test
needs:
- job: build
artifacts: true
image: debian:${RELEASE}
artifacts:
when: always
@@ -399,7 +426,6 @@ build mariadbclient consumer Python-MySQLdb:
stage: test
needs:
- job: build
artifacts: true
image: debian:${RELEASE}
script:
- *test-prepare-container
@@ -421,7 +447,6 @@ libmysql* to libmariadb* upgrade:
stage: upgrade in Sid
needs:
- job: build
artifacts: true
image: debian:${RELEASE}
artifacts:
when: always
@@ -455,7 +480,6 @@ default-libmysqlclient-dev Sid upgrade:
stage: upgrade in Sid
needs:
- job: build
artifacts: true
image: debian:${RELEASE}
artifacts:
when: always
@@ -473,10 +497,9 @@ default-libmysqlclient-dev Sid upgrade:
- $CI_COMMIT_TAG != null && $SALSA_CI_ENABLE_PIPELINE_ON_TAGS !~ /^(1|yes|true)$/
default-libmysqlclient-dev Buster upgrade:
stage: upgrade from Buster/Stretch
stage: upgrade from Bullseye/Buster/Stretch
needs:
- job: build
artifacts: true
image: debian:buster
artifacts:
when: always
@@ -495,10 +518,9 @@ default-libmysqlclient-dev Buster upgrade:
- $CI_COMMIT_TAG != null && $SALSA_CI_ENABLE_PIPELINE_ON_TAGS !~ /^(1|yes|true)$/
default-libmysqlclient-dev Stretch upgrade:
stage: upgrade from Buster/Stretch
stage: upgrade from Bullseye/Buster/Stretch
needs:
- job: build
artifacts: true
image: debian:stretch
artifacts:
when: always
@@ -509,8 +531,7 @@ default-libmysqlclient-dev Stretch upgrade:
- *test-prepare-container
- apt-get install -y pkg-config default-libmysqlclient-dev
- pkg-config --list-all
# Remove manpages 4.10 that conflicts with manpages-dev 5.10 on console_ioctl.4.gz
- apt-get remove -y manpages
- apt-get remove -y manpages # Workaround for Bug#99375
- *test-enable-sid-repos
- *test-install-all-libs
- *test-verify-libs
@@ -518,13 +539,36 @@ default-libmysqlclient-dev Stretch upgrade:
variables:
- $CI_COMMIT_TAG != null && $SALSA_CI_ENABLE_PIPELINE_ON_TAGS !~ /^(1|yes|true)$/
mariadb-connector-c Stretch upgrade:
stage: upgrade from Bullseye/Buster/Stretch
needs:
- job: build
image: debian:stretch
artifacts:
when: always
name: "$CI_BUILD_NAME"
paths:
- ${WORKING_DIR}/debug
script:
- *test-prepare-container
- apt-get install -y pkg-config libmariadb2 libmariadb-dev libmariadb-dev-compat
- pkg-config --list-all
- apt-get remove -y manpages # Workaround for Bug#99375
- *test-enable-sid-repos
- *test-install-all-libs
- *test-verify-libs
except:
variables:
- $CI_COMMIT_TAG != null && $SALSA_CI_ENABLE_PIPELINE_ON_TAGS !~ /^(1|yes|true)$/
allow_failure: true
# Upgrading libc from Stretch to Bookworm is not possible due to Bug#993755
# Upgrading from MySQL 8.0 with datadir in place is not possible. Users need to do a data dump.
# The Debian maintainer scripts detect this situation and simply moves old datadir aside and start fresh.
mysql-8.0 Sid to mariadb-10.7 upgrade:
stage: upgrade in Sid
needs:
- job: build
artifacts: true
image: debian:sid
artifacts:
when: always
@@ -552,7 +596,6 @@ mysql-8.0 Focal to mariadb-10.7 upgrade:
stage: upgrade extras
needs:
- job: build buster-backports
artifacts: true
image: debian:buster
artifacts:
when: always
@@ -587,7 +630,6 @@ mariadb.org-10.5 to mariadb-10.7 upgrade:
stage: upgrade extras
needs:
- job: build
artifacts: true
image: debian:sid
artifacts:
when: always
@@ -626,7 +668,6 @@ mariadb.org-10.4 to mariadb-10.7 upgrade:
stage: upgrade extras
needs:
- job: build
artifacts: true
image: debian:sid
artifacts:
when: always
@@ -659,7 +700,6 @@ mariadb.org-10.3 to mariadb-10.7 upgrade:
stage: upgrade extras
needs:
- job: build
artifacts: true
image: debian:sid
artifacts:
when: always
@@ -695,7 +735,6 @@ mariadb.org-10.2 to mariadb-10.7 upgrade:
stage: upgrade extras
needs:
- job: build
artifacts: true
image: debian:sid
artifacts:
when: always
@@ -731,7 +770,6 @@ mysql.com-5.7 to mariadb-10.7 upgrade:
stage: upgrade extras
needs:
- job: build buster-backports
artifacts: true
image: debian:buster
artifacts:
when: always
@@ -763,7 +801,6 @@ percona-xtradb-5.7 to mariadb-10.7 upgrade (MDEV-22679):
stage: upgrade extras
needs:
- job: build buster-backports
artifacts: true
image: debian:buster
artifacts:
when: always

View File

@@ -7,5 +7,5 @@ Depends: mariadb-plugin-rocksdb | mariadb-server-10.7
Restrictions: allow-stderr needs-root isolation-container
Tests: upstream
Depends: mariadb-test
Depends: mariadb-test, eatmydata
Restrictions: allow-stderr breaks-testbed

View File

@@ -59,7 +59,9 @@ fi
cd /usr/share/mysql/mysql-test
echo "starting mysql-test-tun.pl..."
perl -I. ./mysql-test-run.pl --suite=main --vardir="$WORKDIR/var" --tmpdir="$WORKDIR/tmp" \
eatmydata perl -I. ./mysql-test-run.pl --suite=main \
--vardir="$WORKDIR/var" --tmpdir="$WORKDIR/tmp" \
--parallel=auto --skip-rpl \
--force --skip-test-list=$SKIP_TEST_LST $@ 2>&1
--force --skip-test-list=$SKIP_TEST_LST \
--xml-report=$AUTOPKGTEST_ARTIFACTS/mysql-test-run-junit.xml $@ 2>&1
echo "run: OK"

View File

@@ -90,7 +90,8 @@ void ft_free_stopwords(void);
FT_INFO *ft_init_search(uint,void *, uint, uchar *, size_t,
CHARSET_INFO *, uchar *);
my_bool ft_boolean_check_syntax_string(const uchar *);
my_bool ft_boolean_check_syntax_string(const uchar *, size_t length,
CHARSET_INFO *cs);
/* Internal symbols for fulltext between maria and MyISAM */

View File

@@ -1,6 +1,6 @@
/*
Copyright (c) 2001, 2013, Oracle and/or its affiliates.
Copyright (c) 2009, 2019, MariaDB Corporation.
Copyright (c) 2009, 2021, 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

View File

@@ -197,13 +197,13 @@ enum enum_indicator_type
#define FIELD_FLAGS_COLUMN_FORMAT_MASK (3U << FIELD_FLAGS_COLUMN_FORMAT)
#define FIELD_IS_DROPPED (1U << 26) /* Intern: Field is being dropped */
#define VERS_SYS_START_FLAG (1 << 27) /* autogenerated column declared with
#define VERS_ROW_START (1 << 27) /* autogenerated column declared with
`generated always as row start`
(see II.a SQL Standard) */
#define VERS_SYS_END_FLAG (1 << 28) /* autogenerated column declared with
#define VERS_ROW_END (1 << 28) /* autogenerated column declared with
`generated always as row end`
(see II.a SQL Standard).*/
#define VERS_SYSTEM_FIELD (VERS_SYS_START_FLAG | VERS_SYS_END_FLAG)
#define VERS_SYSTEM_FIELD (VERS_ROW_START | VERS_ROW_END)
#define VERS_UPDATE_UNVERSIONED_FLAG (1 << 29) /* column that doesn't support
system versioning when table
itself supports it*/

View File

@@ -206,7 +206,14 @@ option\&.
.\" binary-mode option: mysql
\fB\-\-binary\-mode\fR
.sp
By default, ASCII '\e0' is disallowed and '\er\en' is translated to '\en'\&. This switch turns off both features, and also turns off parsing of all client commands except \eC and DELIMITER, in non-interactive mode (for input piped to mysql or loaded using the 'source' command)\&. This is necessary when processing output from mysqlbinlog that may contain blobs\&.
Binary mode allows certain character sequences to be processed as data that
would otherwise be treated with a special meaning by the parser\&.
Specifically, this switch turns off parsing of all client commands except \eC
and DELIMITER in non-interactive mode (i\&.e\&., when binary mode is combined
with either 1) piped input, 2) the --batch mysql option, or 3) the 'source'
command)\&. Also, in binary mode, occurrences of '\er\en' and ASCII '\e0' are
preserved within strings, whereas by default, '\er\en' is translated to '\en'
and '\e0' is disallowed in user input\&.
.RE
.sp
.RS 4

View File

@@ -8,3 +8,8 @@ character_set_server utf16
SHOW VARIABLES LIKE 'ft_stopword_file';
Variable_name Value
ft_stopword_file (built-in)
#
# MDEV-23269 SIGSEGV in ft_boolean_check_syntax_string on setting ft_boolean_syntax
#
SET GLOBAL ft_boolean_syntax='+ -><()~*:""&|';
SET GLOBAL ft_boolean_syntax=DEFAULT;

View File

@@ -7,3 +7,10 @@ call mtr.add_suppression("'utf16' can not be used as client character set");
SHOW VARIABLES LIKE 'collation_server';
SHOW VARIABLES LIKE 'character_set_server';
SHOW VARIABLES LIKE 'ft_stopword_file';
--echo #
--echo # MDEV-23269 SIGSEGV in ft_boolean_check_syntax_string on setting ft_boolean_syntax
--echo #
SET GLOBAL ft_boolean_syntax='+ -><()~*:""&|';
SET GLOBAL ft_boolean_syntax=DEFAULT;

View File

@@ -0,0 +1 @@
--character-set-server=utf32,latin1 --collation-server=utf32_general_ci

View File

@@ -0,0 +1,6 @@
call mtr.add_suppression("'utf32' can not be used as client character set");
#
# MDEV-23269 SIGSEGV in ft_boolean_check_syntax_string on setting ft_boolean_syntax
#
SET GLOBAL ft_boolean_syntax='+ -><()~*:""&|';
SET GLOBAL ft_boolean_syntax=DEFAULT;

View File

@@ -0,0 +1,9 @@
--source include/have_utf32.inc
call mtr.add_suppression("'utf32' can not be used as client character set");
--echo #
--echo # MDEV-23269 SIGSEGV in ft_boolean_check_syntax_string on setting ft_boolean_syntax
--echo #
SET GLOBAL ft_boolean_syntax='+ -><()~*:""&|';
SET GLOBAL ft_boolean_syntax=DEFAULT;

View File

@@ -3387,6 +3387,14 @@ CREATE OR REPLACE TABLE t1(i int);
ALTER TABLE t1 ADD b CHAR(255) DEFAULT `aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa`;
ERROR 42S22: Unknown column 'aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa' in 'DEFAULT'
DROP TABLE t1;
#
# MDEV-18278 Misleading error message in error log upon failed table creation
#
create table t1 (a int as (a));
ERROR 01000: Expression for field `a` is referring to uninitialized field `a`
show warnings;
Level Code Message
Error 4029 Expression for field `a` is referring to uninitialized field `a`
# end of 10.2 test
#
# MDEV-22703 DEFAULT() on a BLOB column can overwrite the default
@@ -3403,3 +3411,4 @@ length(DEFAULT(h))
25
INSERT INTO t1 () VALUES ();
drop table t1;
# end of 10.3 test

View File

@@ -2109,6 +2109,13 @@ CREATE OR REPLACE TABLE t1(i int);
ALTER TABLE t1 ADD b CHAR(255) DEFAULT `aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa`;
DROP TABLE t1;
--echo #
--echo # MDEV-18278 Misleading error message in error log upon failed table creation
--echo #
--error ER_EXPRESSION_REFERS_TO_UNINIT_FIELD
create table t1 (a int as (a));
show warnings;
--echo # end of 10.2 test
--echo #
@@ -2126,3 +2133,5 @@ SELECT DEFAULT(h) FROM t1;
SELECT length(DEFAULT(h)) FROM t1;
INSERT INTO t1 () VALUES ();
drop table t1;
--echo # end of 10.3 test

View File

@@ -0,0 +1 @@
--init_connect="set @a='something unique to have MTR start a dedicated mariadbd for this test and shutdown it after the test'"

View File

@@ -0,0 +1,17 @@
#
# MDEV-25925 Warning: Memory not freed: 32 on INSERT DELAYED
#
SET sql_mode='TRADITIONAL';
CREATE TABLE t1 (c BLOB) ENGINE=MyISAM;
INSERT DELAYED INTO t1 VALUES (''||'');
ERROR 22007: Truncated incorrect DOUBLE value: ''
DROP TABLE t1;
SET sql_mode=DEFAULT;
#
# MDEV-24467 Memory not freed after failed INSERT DELAYED
#
CREATE TABLE t1 (a VARCHAR(1)) ENGINE=MyISAM;
ALTER TABLE t1 ADD b BLOB DEFAULT 'x';
INSERT DELAYED INTO t1 (a) VALUES ('foo');
ERROR 22001: Data too long for column 'a' at row 1
DROP TABLE t1;

View File

@@ -0,0 +1,21 @@
--echo #
--echo # MDEV-25925 Warning: Memory not freed: 32 on INSERT DELAYED
--echo #
SET sql_mode='TRADITIONAL';
CREATE TABLE t1 (c BLOB) ENGINE=MyISAM;
--error ER_TRUNCATED_WRONG_VALUE
INSERT DELAYED INTO t1 VALUES (''||'');
DROP TABLE t1;
SET sql_mode=DEFAULT;
--echo #
--echo # MDEV-24467 Memory not freed after failed INSERT DELAYED
--echo #
CREATE TABLE t1 (a VARCHAR(1)) ENGINE=MyISAM;
ALTER TABLE t1 ADD b BLOB DEFAULT 'x';
--error ER_DATA_TOO_LONG
INSERT DELAYED INTO t1 (a) VALUES ('foo');
DROP TABLE t1;

View File

@@ -5019,6 +5019,18 @@ DROP TABLE t1;
# End of 10.1 tests
#
#
# Start of 10.2 tests
#
#
# MDEV-24742 Server crashes in Charset::numchars / String::numchars
#
SELECT NULL IN (RIGHT(AES_ENCRYPT('foo','bar'), LAST_INSERT_ID()), 'qux');
NULL IN (RIGHT(AES_ENCRYPT('foo','bar'), LAST_INSERT_ID()), 'qux')
NULL
#
# End of 10.2 tests
#
#
# Start of 10.3 tests
#
#

View File

@@ -1990,6 +1990,22 @@ DROP TABLE t1;
--echo #
--echo #
--echo # Start of 10.2 tests
--echo #
--echo #
--echo # MDEV-24742 Server crashes in Charset::numchars / String::numchars
--echo #
SELECT NULL IN (RIGHT(AES_ENCRYPT('foo','bar'), LAST_INSERT_ID()), 'qux');
--echo #
--echo # End of 10.2 tests
--echo #
--echo #
--echo # Start of 10.3 tests
--echo #

View File

@@ -538,7 +538,7 @@ a b
insert into t2 values(1);
select a,b from t2;
a b
NULL 1
12 1
drop table t1,t2;
create table t1 (a int invisible, b int, c int);
create table t2 (a int, b int, d int);
@@ -627,3 +627,18 @@ drop table t1;
create table t1 (a int, b int invisible);
insert delayed into t1 values (1);
drop table t1;
#
# MDEV-25891 Computed default for INVISIBLE column is ignored in INSERT
#
create table t1(
a int,
x int default (a),
y int default (a) invisible,
z int default (33) invisible);
insert into t1 values (1, default);
insert into t1 (a) values (2);
select a, x, y, z from t1;
a x y z
1 1 1 33
2 2 2 33
drop table t1;

View File

@@ -281,3 +281,16 @@ insert delayed into t1 values (1);
--disable_prepare_warnings
# cleanup
drop table t1;
--echo #
--echo # MDEV-25891 Computed default for INVISIBLE column is ignored in INSERT
--echo #
create table t1(
a int,
x int default (a),
y int default (a) invisible,
z int default (33) invisible);
insert into t1 values (1, default);
insert into t1 (a) values (2);
select a, x, y, z from t1;
drop table t1;

View File

@@ -1151,3 +1151,13 @@ b
1
3
drop tables t1, t2;
#
# MDEV-22464 Server crash on UPDATE with nested subquery
#
create table t1 (a int) ;
insert into t1 (a) values (1),(2),(3) ;
select a from t1 where a= (select 2 from t1 having (a = 3));
ERROR 21000: Subquery returns more than 1 row
update t1 set a= (select 2 from t1 having (a = 3));
ERROR 21000: Subquery returns more than 1 row
drop tables t1;

View File

@@ -1087,3 +1087,14 @@ update t1 left join t2 on a = b set b= 3 order by b;
select * from t2;
drop tables t1, t2;
--echo #
--echo # MDEV-22464 Server crash on UPDATE with nested subquery
--echo #
create table t1 (a int) ;
insert into t1 (a) values (1),(2),(3) ;
--error ER_SUBQUERY_NO_1_ROW
select a from t1 where a= (select 2 from t1 having (a = 3));
--error ER_SUBQUERY_NO_1_ROW
update t1 set a= (select 2 from t1 having (a = 3));
drop tables t1;

View File

@@ -0,0 +1,54 @@
# Note: This test assumes NO_BACKSLASH_ESCAPES is not set in SQL_MODE.
##############################
# Setup
##############################
#
# Saving old state
#
set @old_sql_mode= @@global.SQL_MODE;
set @@global.SQL_MODE= "";
#
# Create table for data entry
#
CREATE TABLE tb (`id` int(11) NOT NULL AUTO_INCREMENT,`cb` longblob DEFAULT NULL, PRIMARY KEY (`id`)) AUTO_INCREMENT=1 DEFAULT CHARSET=latin1;
RESET MASTER;
##############################
# Test Case
##############################
#
# \0 (0x5c00 in binary) should be allowed in data strings if
# --binary-mode is enabled.
#
FOUND 10 /\x5c\x00/ in binary_zero_inserts.sql
# MYSQL --binary-mode test < MYSQL_TMP_DIR/binary_zero_inserts.sql
#
# Ensure a row exists from each insert statement with a \0
#
SELECT COUNT(*)=8 from tb;
COUNT(*)=8
1
#
# Ensure that the binary zero was parsed and exists in the row data
# Note: We only look for 00 because the 5c only served as an escape
# in parsing.
#
# MYSQL_DUMP test tb --hex-blob | grep INSERT > MYSQL_TMP_DIR/dump.sql
FOUND 10 /00/ in dump.sql
#
# Ensure data consistency on mysqlbinlog replay
#
FLUSH LOGS;
# MYSQL_BINLOG MYSQLD_DATADIR/binlog_file > MYSQL_TMP_DIR/binlog_zeros.sql
FOUND 10 /\x5c\x00/ in binlog_zeros.sql
# MYSQL --binary-mode test < MYSQL_TMP_DIR/binlog_zeros.sql
# Table checksum is equivalent before and after binlog replay
#
# A \0 should still be treated as end-of-query in binary mode.
#
# MYSQL --binary-mode -B test < MYSQL_TMP_DIR/binary_zero_eoq.sql
##############################
# Cleanup
##############################
SET @@global.sql_mode= @old_sql_mode;
drop table tb;
RESET MASTER;

View File

@@ -0,0 +1,170 @@
#
# Purpose:
# This test ensures that the mysql client is able to properly handle the
# binary data sequence 0x5c00, i.e. the null-terminating character \0, in a
# string when --binary-mode is enabled. Specifically, this sequence is valid to
# appear anywhere within a binary data string, and it should not end the string
# or SQL command. Additionally, \0 outside of a string should still end the
# query.
#
# Methodology:
# This test initially inserts data with binary strings containing \0. To
# ensure the mysql client is able to process this data correctly, perl is used
# to create a SQL file that contains \0 in strings, and this file is used as
# input into the client. The row data is then validated by searching for binary
# zeros in mysqldump output.
#
#
# References:
# MDEV-25444: mysql --binary-mode is not able to replay some mysqlbinlog
# outputs
--echo # Note: This test assumes NO_BACKSLASH_ESCAPES is not set in SQL_MODE.
--source include/have_log_bin.inc
--echo ##############################
--echo # Setup
--echo ##############################
--echo #
--echo # Saving old state
--echo #
set @old_sql_mode= @@global.SQL_MODE;
set @@global.SQL_MODE= "";
--echo #
--echo # Create table for data entry
--echo #
CREATE TABLE tb (`id` int(11) NOT NULL AUTO_INCREMENT,`cb` longblob DEFAULT NULL, PRIMARY KEY (`id`)) AUTO_INCREMENT=1 DEFAULT CHARSET=latin1;
# Will replay binlog later and we don't want to recreate the table
RESET MASTER;
--echo ##############################
--echo # Test Case
--echo ##############################
--echo #
--echo # \0 (0x5c00 in binary) should be allowed in data strings if
--echo # --binary-mode is enabled.
--echo #
--perl
my $dir= $ENV{'MYSQL_TMP_DIR'};
open (my $FILE, '>', "$dir/binary_zero_inserts.sql") or die "open(): $!";
print $FILE "TRUNCATE TABLE tb;\n";
# INSERT INTO tb(cb) VALUES(_binary '\0');
print $FILE "INSERT INTO tb(cb) VALUES (_binary '";
print $FILE pack "H*","5c00";
print $FILE "');\n";
# INSERT INTO tb(cb) VALUES(_binary '\0A');
print $FILE "INSERT INTO tb(cb) VALUES (_binary '";
print $FILE pack "H*","5c0041";
print $FILE "');\n";
# INSERT INTO tb(cb) VALUES(_binary 'A\0');
print $FILE "INSERT INTO tb(cb) VALUES (_binary '";
print $FILE pack "H*","415c00";
print $FILE "');\n";
# INSERT INTO tb(cb) VALUES(_binary 'A\0B');
print $FILE "INSERT INTO tb(cb) VALUES (_binary '";
print $FILE pack "H*","415c0042";
print $FILE "');\n";
# INSERT INTO tb(cb) VALUES(_binary '\0A\0');
print $FILE "INSERT INTO tb(cb) VALUES (_binary '";
print $FILE pack "H*","5c00415c00";
print $FILE "');\n";
# INSERT INTO tb(cb) VALUES(_binary '\\\0');
print $FILE "INSERT INTO tb(cb) VALUES (_binary '";
print $FILE pack "H*","5c5c5c00";
print $FILE "');\n";
# INSERT INTO tb(cb) VALUES(_binary '\0\0');
print $FILE "INSERT INTO tb(cb) VALUES (_binary '";
print $FILE pack "H*","5c005c00";
print $FILE "');\n";
# INSERT INTO tb(cb) VALUES(_binary '\\0');
print $FILE "INSERT INTO tb(cb) VALUES (_binary '";
print $FILE pack "H*","5c5c00";
print $FILE "');\n";
close ($FILE);
EOF
--let SEARCH_PATTERN= \x5c\x00
--let SEARCH_FILE= $MYSQL_TMP_DIR/binary_zero_inserts.sql
--source include/search_pattern_in_file.inc
--echo # MYSQL --binary-mode test < MYSQL_TMP_DIR/binary_zero_inserts.sql
--exec $MYSQL --binary-mode test < $MYSQL_TMP_DIR/binary_zero_inserts.sql
--echo #
--echo # Ensure a row exists from each insert statement with a \0
--echo #
SELECT COUNT(*)=8 from tb;
--echo #
--echo # Ensure that the binary zero was parsed and exists in the row data
--echo # Note: We only look for 00 because the 5c only served as an escape
--echo # in parsing.
--echo #
--echo # MYSQL_DUMP test tb --hex-blob | grep INSERT > MYSQL_TMP_DIR/dump.sql
--exec $MYSQL_DUMP test tb --hex-blob | grep -A8 INSERT > $MYSQL_TMP_DIR/dump.sql
--let SEARCH_PATTERN= 00
--let SEARCH_FILE= $MYSQL_TMP_DIR/dump.sql
--source include/search_pattern_in_file.inc
--echo #
--echo # Ensure data consistency on mysqlbinlog replay
--echo #
--let $good_checksum= `CHECKSUM TABLE tb`
let $MYSQLD_DATADIR= `SELECT @@datadir`;
let $binlog_file= query_get_value(SHOW MASTER STATUS, File, 1);
FLUSH LOGS;
--echo # MYSQL_BINLOG MYSQLD_DATADIR/binlog_file > MYSQL_TMP_DIR/binlog_zeros.sql
--exec $MYSQL_BINLOG $MYSQLD_DATADIR/$binlog_file > $MYSQL_TMP_DIR/binlog_zeros.sql
--let SEARCH_PATTERN= \x5c\x00
--let SEARCH_FILE= $MYSQL_TMP_DIR/binlog_zeros.sql
--source include/search_pattern_in_file.inc
--echo # MYSQL --binary-mode test < MYSQL_TMP_DIR/binlog_zeros.sql
--exec $MYSQL --binary-mode test < $MYSQL_TMP_DIR/binlog_zeros.sql
if ($good_checksum != `CHECKSUM TABLE tb`)
{
die "Blob with binary zero data changed after binary log replay";
}
--echo # Table checksum is equivalent before and after binlog replay
--echo #
--echo # A \0 should still be treated as end-of-query in binary mode.
--echo #
--perl
my $dir= $ENV{'MYSQL_TMP_DIR'};
open (my $FILE, '>', "$dir/binary_zero_eoq.sql") or die "open(): $!";
# INSERT INTO tb(cb) VALUES(_binary 'text')\0
print $FILE "INSERT INTO tb(cb) VALUES (_binary 'text')";
print $FILE pack "H*","5c00";
close ($FILE);
EOF
--echo # MYSQL --binary-mode -B test < MYSQL_TMP_DIR/binary_zero_eoq.sql
--exec $MYSQL --binary-mode -B test < $MYSQL_TMP_DIR/binary_zero_eoq.sql
--echo ##############################
--echo # Cleanup
--echo ##############################
--remove_file $MYSQL_TMP_DIR/binary_zero_inserts.sql
--remove_file $MYSQL_TMP_DIR/binary_zero_eoq.sql
--remove_file $MYSQL_TMP_DIR/binlog_zeros.sql
--remove_file $MYSQL_TMP_DIR/dump.sql
SET @@global.sql_mode= @old_sql_mode;
drop table tb;
RESET MASTER;

View File

@@ -16,10 +16,8 @@ MDEV-20225 : MDEV-20886 galera.MDEV-20225
MW-328A : MDEV-22666 galera.MW-328A MTR failed: "Semaphore wait has lasted > 600 seconds" and do not release port 16002
MW-328B : MDEV-22666 galera.MW-328A MTR failed: "Semaphore wait has lasted > 600 seconds" and do not release port 16002
MW-329 : MDEV-19962 Galera test failure on MW-329
galera_FK_duplicate_client_insert : MDEV-24473: galera.galera_FK_duplicate_client_insert MTR failed: SIGABRT. InnoDB: Conflicting lock on table. Assertion failure in lock0lock.cc
galera_applier_ftwrl_table_alter : MDEV-26502 : galera.galera_applier_ftwrl_table_alter MTR failed : Result content mismatch
galera_as_slave_replication_bundle : MDEV-15785 OPTION_GTID_BEGIN is set in Gtid_log_event::do_apply_event()
galera_bf_abort_at_after_statement : MDEV-21557: galera_bf_abort_at_after_statement MTR failed: query 'reap' succeeded - should have failed with errno 1213
galera_bf_abort_group_commit : MDEV-18282 Galera test failure on galera.galera_bf_abort_group_commit
galera_bf_kill_debug : MDEV-24485 wsrep::client_state::do_acquire_ownership(): Assertion `state_ == s_idle || mode_ != m_local' failed
galera_bf_lock_wait : MDEV-21597 wsrep::transaction::start_transaction(): Assertion `active() == false' failed
@@ -34,15 +32,12 @@ galera_pc_ignore_sb : MDEV-20888 galera.galera_pc_ignore_sb
galera_pc_recovery : MDEV-25199 cluster fails to start up
galera_shutdown_nonprim : MDEV-21493 galera.galera_shutdown_nonprim
galera_sst_mysqldump : MDEV-26501 : galera.galera_sst_mysqldump MTR failed: galera SST with mysqldump failed
galera_toi_ddl_nonconflicting : MDEV-21518 galera.galera_toi_ddl_nonconflicting
galera_toi_truncate : MDEV-22996 Hang on galera_toi_truncate test case
galera_trigger : MDEV-24048 galera.galera_trigger MTR fails: Result content mismatch
galera_unicode_identifiers : MDEV-26500 : galera.galera_unicode_identifiers MTR failed: InnoDB: innodb_fatal_semaphore_wait_threshold was exceeded for dict_sys.mutex
galera_var_dirty_reads : MDEV-25615 Galera test failure on galera_var_dirty_reads
galera_var_ignore_apply_errors : MDEV-26770 galera_var_ignore_apply_errors fails Server did not transition to READY state
galera_var_node_address : MDEV-20485 Galera test failure
galera_var_notify_cmd : MDEV-21905 Galera test galera_var_notify_cmd causes hang
galera_var_reject_queries : assertion in inline_mysql_socket_send
galera_var_replicate_myisam_on : MDEV-24062 Galera test failure on galera_var_replicate_myisam_on
galera_var_retry_autocommit: MDEV-18181 Galera test failure on galera.galera_var_retry_autocommit
galera_wsrep_provider_unset_set: wsrep_provider is read-only for security reasons
mysql-wsrep#198 : MDEV-24446: galera.mysql-wsrep#198 MTR failed: query 'reap' failed: 2000: Unknown MySQL error

View File

@@ -3,16 +3,24 @@ connection node_1;
connection node_1;
CREATE TABLE ten (f1 INTEGER NOT NULL PRIMARY KEY) ENGINE=InnoDB;
INSERT INTO ten VALUES (1),(2),(3),(4),(5),(6),(7),(8),(9),(10);
CREATE TABLE t1 (f1 INTEGER) ENGINE=InnoDB;
CREATE TABLE t1 (id int not null primary key auto_increment, f1 INTEGER) ENGINE=InnoDB;
connection node_2;
SET SESSION wsrep_retry_autocommit = 0;
INSERT INTO t1 (f1) SELECT 1 FROM ten AS a1, ten AS a2, ten AS a3, ten AS a4, ten AS a5, ten AS a6, ten AS a7, ten AS a8;
connect node_2a, 127.0.0.1, root, , test, $NODE_MYPORT_2;
connection node_2a;
set session wsrep_sync_wait=0;
connect node_1b, 127.0.0.1, root, , test, $NODE_MYPORT_1;
connection node_1b;
SET GLOBAL debug_dbug = "d,sync.wsrep_apply_cb";
connection node_2;
INSERT INTO t1 (f1) SELECT 1 FROM ten AS a1;
connection node_1b;
SET SESSION DEBUG_SYNC = "now WAIT_FOR sync.wsrep_apply_cb_reached";
connection node_1;
TRUNCATE TABLE t1;;
connection node_1b;
SET DEBUG_SYNC = "now SIGNAL signal.wsrep_apply_cb";
SET GLOBAL debug_dbug = "";
SET DEBUG_SYNC = "RESET";
connection node_1;
TRUNCATE TABLE t1;
connection node_2;
ERROR 40001: Deadlock found when trying to get lock; try restarting transaction
SELECT COUNT(*) AS EXPECT_0 FROM t1;
EXPECT_0
0
@@ -20,5 +28,6 @@ connection node_1;
SELECT COUNT(*) AS EXPECT_0 FROM t1;
EXPECT_0
0
disconnect node_1b;
DROP TABLE t1;
DROP TABLE ten;

View File

@@ -1,11 +1,6 @@
<<<<<<< HEAD
connection node_2;
connection node_1;
||||||| merged common ancestors
=======
call mtr.add_suppression("WSREP has not yet prepared node for application use");
>>>>>>> 10.3
CREATE TABLE t1 (f1 INTEGER);
CREATE TABLE t1 (f1 INTEGER NOT NULL PRIMARY KEY) engine=innodb;
connect node_1a, 127.0.0.1, root, , test, $NODE_MYPORT_1;
connection node_1;
SET SESSION wsrep_reject_queries = ALL;
@@ -27,7 +22,7 @@ VARIABLE_VALUE = 2
INSERT INTO t1 VALUES (1);
connect node_1c, 127.0.0.1, root, , test, $NODE_MYPORT_1;
SET GLOBAL wsrep_reject_queries = NONE;
SELECT COUNT(*) = 1 FROM t1;
COUNT(*) = 1
SELECT COUNT(*) AS EXPECT_1 FROM t1;
EXPECT_1
1
DROP TABLE t1;

View File

@@ -1,23 +0,0 @@
connection node_2;
connection node_1;
connection node_1;
connection node_2;
connection node_1;
CREATE TABLE t1 (f1 INTEGER) ENGINE=InnoDB;
INSERT INTO t1 VALUES (1);
connection node_2;
SET GLOBAL wsrep_provider='none';
INSERT INTO t1 VALUES (2);
connection node_1;
INSERT INTO t1 VALUES (3);
connection node_2;
SET SESSION wsrep_sync_wait = 0;
INSERT INTO t1 VALUES (4);
SELECT COUNT(*) = 4 FROM t1;
COUNT(*) = 4
1
connection node_1;
SELECT COUNT(*) = 3 FROM t1;
COUNT(*) = 3
1
DROP TABLE t1;

View File

@@ -1,46 +0,0 @@
connection node_2;
connection node_1;
connection node_1;
connection node_2;
connection node_1;
set GLOBAL wsrep_slave_threads=26;
CREATE TABLE t1 (f1 INTEGER) ENGINE=InnoDB;
INSERT INTO t1 VALUES (1);
INSERT INTO t1 (f1) SELECT * from t1 as x1;
connection node_2;
set GLOBAL wsrep_slave_threads=16;
SET GLOBAL wsrep_provider='none';
INSERT INTO t1 VALUES (2);
connection node_1;
INSERT INTO t1 VALUES (3);
connection node_2;
INSERT INTO t1 VALUES (4);
set GLOBAL wsrep_slave_threads=5;
SELECT COUNT(*) = 5 FROM t1;
COUNT(*) = 5
1
connection node_1;
set GLOBAL wsrep_slave_threads=12;
SELECT COUNT(*) = 4 FROM t1;
COUNT(*) = 4
1
INSERT INTO t1 VALUES (100), (101), (102);
connection node_2;
set GLOBAL wsrep_slave_threads=5;
INSERT INTO t1 (f1) SELECT * from t1 as x1;
show global variables like 'wsrep_slave_threads';
Variable_name Value
wsrep_slave_threads 5
SET GLOBAL wsrep_slave_threads = 1;
SELECT COUNT(*) FROM t1;
COUNT(*)
16
connection node_1;
SELECT COUNT(*) FROM t1;
COUNT(*)
15
show global variables like 'wsrep_slave_threads';
Variable_name Value
wsrep_slave_threads 12
SET GLOBAL wsrep_slave_threads = 1;
DROP TABLE t1;

View File

@@ -8,6 +8,8 @@
CREATE TABLE t1 (f1 INTEGER PRIMARY KEY AUTO_INCREMENT, f2 INTEGER);
--connection node_2
--let $wait_condition = SELECT COUNT(*) = 1 FROM INFORMATION_SCHEMA.INNODB_SYS_TABLES WHERE NAME LIKE 'test/t1';
--source include/wait_condition.inc
--send ALTER TABLE t1 ADD COLUMN f3 INTEGER; INSERT INTO t1 (f1, f2) VALUES (DEFAULT, 123);
--connection node_1

View File

@@ -6,6 +6,7 @@
--source include/galera_cluster.inc
--source include/have_debug_sync.inc
--source include/have_debug.inc
--source include/galera_have_debug_sync.inc
#
# INSERT and TRUNCATE on different nodes
@@ -15,32 +16,51 @@
CREATE TABLE ten (f1 INTEGER NOT NULL PRIMARY KEY) ENGINE=InnoDB;
INSERT INTO ten VALUES (1),(2),(3),(4),(5),(6),(7),(8),(9),(10);
CREATE TABLE t1 (f1 INTEGER) ENGINE=InnoDB;
CREATE TABLE t1 (id int not null primary key auto_increment, f1 INTEGER) ENGINE=InnoDB;
--connection node_2
set session wsrep_sync_wait=0;
--let $wait_condition = SELECT COUNT(*) = 10 FROM ten;
--source include/wait_condition.inc
# Prevent autocommit retring from masking the deadlock error we expect to get
SET SESSION wsrep_retry_autocommit = 0;
--send INSERT INTO t1 (f1) SELECT 1 FROM ten AS a1, ten AS a2, ten AS a3, ten AS a4, ten AS a5, ten AS a6, ten AS a7, ten AS a8
--connect node_1b, 127.0.0.1, root, , test, $NODE_MYPORT_1
--connection node_1b
--connect node_2a, 127.0.0.1, root, , test, $NODE_MYPORT_2
--connection node_2a
--let $wait_condition = SELECT COUNT(*) = 1 FROM INFORMATION_SCHEMA.PROCESSLIST WHERE STATE LIKE 'Sending data%' AND INFO LIKE 'INSERT INTO t1 (f1)%';
--source include/wait_condition.inc
--connection node_1
TRUNCATE TABLE t1;
# block applier before applying
SET GLOBAL debug_dbug = "d,sync.wsrep_apply_cb";
--connection node_2
--error ER_LOCK_DEADLOCK
--send INSERT INTO t1 (f1) SELECT 1 FROM ten AS a1
--connection node_1b
# wait until applier has reached the sync point
SET SESSION DEBUG_SYNC = "now WAIT_FOR sync.wsrep_apply_cb_reached";
--connection node_1
--send TRUNCATE TABLE t1;
--connection node_1b
# release the applier
SET DEBUG_SYNC = "now SIGNAL signal.wsrep_apply_cb";
SET GLOBAL debug_dbug = "";
SET DEBUG_SYNC = "RESET";
--connection node_1
--reap
--connection node_2
--reap
--let $wait_condition = SELECT COUNT(*) = 0 FROM t1;
--source include/wait_condition.inc
SELECT COUNT(*) AS EXPECT_0 FROM t1;
--connection node_1
--let $wait_condition = SELECT COUNT(*) = 0 FROM t1;
--source include/wait_condition.inc
SELECT COUNT(*) AS EXPECT_0 FROM t1;
--disconnect node_1b
DROP TABLE t1;
DROP TABLE ten;

View File

@@ -5,9 +5,7 @@
--source include/galera_cluster.inc
--source include/have_innodb.inc
call mtr.add_suppression("WSREP has not yet prepared node for application use");
CREATE TABLE t1 (f1 INTEGER);
CREATE TABLE t1 (f1 INTEGER NOT NULL PRIMARY KEY) engine=innodb;
--connect node_1a, 127.0.0.1, root, , test, $NODE_MYPORT_1
@@ -44,6 +42,6 @@ INSERT INTO t1 VALUES (1);
--connect node_1c, 127.0.0.1, root, , test, $NODE_MYPORT_1
SET GLOBAL wsrep_reject_queries = NONE;
SELECT COUNT(*) = 1 FROM t1;
SELECT COUNT(*) AS EXPECT_1 FROM t1;
DROP TABLE t1;

View File

@@ -1,50 +0,0 @@
#
# Test that wsrep_provider can be unset and then set back to its original value
# and replication will continue except for any updates made while the value was 'none'
#
--source include/galera_cluster.inc
--source include/have_innodb.inc
# Save original auto_increment_offset values.
--let $node_1=node_1
--let $node_2=node_2
--source include/auto_increment_offset_save.inc
--connection node_1
CREATE TABLE t1 (f1 INTEGER) ENGINE=InnoDB;
INSERT INTO t1 VALUES (1);
--connection node_2
--let $wsrep_provider_orig = `SELECT @@wsrep_provider`
--let $wsrep_cluster_address_orig = `SELECT @@wsrep_cluster_address`
SET GLOBAL wsrep_provider='none';
INSERT INTO t1 VALUES (2);
--connection node_1
INSERT INTO t1 VALUES (3);
--connection node_2
--disable_query_log
--eval SET GLOBAL wsrep_provider = '$wsrep_provider_orig';
--eval SET GLOBAL wsrep_cluster_address = '$wsrep_cluster_address_orig';
--enable_query_log
SET SESSION wsrep_sync_wait = 0;
--source include/wait_until_connected_again.inc
--source include/galera_wait_ready.inc
INSERT INTO t1 VALUES (4);
# Node #2 has all the inserts
SELECT COUNT(*) = 4 FROM t1;
--connection node_1
# Node #1 is missing the insert made while Node #2 was not replicated
SELECT COUNT(*) = 3 FROM t1;
DROP TABLE t1;
--source include/auto_increment_offset_restore.inc

View File

@@ -1,67 +0,0 @@
#
# PXC-421: Test deadlock involving updates of
# wsrep_provider, wsrep_cluster_address and wsrep_slave_threads.
#
--source include/galera_cluster.inc
--source include/have_innodb.inc
# Save original auto_increment_offset values.
--let $node_1=node_1
--let $node_2=node_2
--source include/auto_increment_offset_save.inc
--connection node_1
--let $wsrep_slave_1 = `SELECT @@wsrep_slave_threads`
set GLOBAL wsrep_slave_threads=26;
CREATE TABLE t1 (f1 INTEGER) ENGINE=InnoDB;
INSERT INTO t1 VALUES (1);
INSERT INTO t1 (f1) SELECT * from t1 as x1;
--connection node_2
--let $wsrep_slave_2 = `SELECT @@wsrep_slave_threads`
set GLOBAL wsrep_slave_threads=16;
--let $wsrep_provider_orig = `SELECT @@wsrep_provider`
--let $wsrep_cluster_address_orig = `SELECT @@wsrep_cluster_address`
SET GLOBAL wsrep_provider='none';
INSERT INTO t1 VALUES (2);
--connection node_1
INSERT INTO t1 VALUES (3);
--connection node_2
--disable_query_log
--eval SET GLOBAL wsrep_provider = '$wsrep_provider_orig';
--eval SET GLOBAL wsrep_cluster_address = '$wsrep_cluster_address_orig';
--enable_query_log
--source include/wait_until_connected_again.inc
INSERT INTO t1 VALUES (4);
set GLOBAL wsrep_slave_threads=5;
# Node #2 has all the inserts
SELECT COUNT(*) = 5 FROM t1;
--connection node_1
set GLOBAL wsrep_slave_threads=12;
# Node #1 is missing the insert made while Node #2 was not replicated
SELECT COUNT(*) = 4 FROM t1;
INSERT INTO t1 VALUES (100), (101), (102);
--connection node_2
set GLOBAL wsrep_slave_threads=5;
INSERT INTO t1 (f1) SELECT * from t1 as x1;
show global variables like 'wsrep_slave_threads';
--eval SET GLOBAL wsrep_slave_threads = $wsrep_slave_2
SELECT COUNT(*) FROM t1;
--connection node_1
SELECT COUNT(*) FROM t1;
show global variables like 'wsrep_slave_threads';
--eval SET GLOBAL wsrep_slave_threads = $wsrep_slave_1
DROP TABLE t1;
--source include/auto_increment_offset_restore.inc

View File

@@ -0,0 +1,105 @@
connection node_2;
connection node_1;
connect node_1a, 127.0.0.1, root, , test, $NODE_MYPORT_1;
connect node_2a, 127.0.0.1, root, , test, $NODE_MYPORT_2;
connect node_3, 127.0.0.1, root, , test, $NODE_MYPORT_3;
connect node_3a, 127.0.0.1, root, , test, $NODE_MYPORT_3;
connection node_1;
CREATE TABLE t1 (f1 INTEGER PRIMARY KEY);
connection node_2;
SET SESSION wsrep_trx_fragment_size=1;
BEGIN;
INSERT INTO t1 VALUES (21);
connection node_1;
SELECT COUNT(*) AS EXPECT_1 FROM mysql.wsrep_streaming_log;
EXPECT_1
1
connection node_2;
SELECT COUNT(*) AS EXPECT_1 FROM mysql.wsrep_streaming_log;
EXPECT_1
1
connection node_3;
SELECT COUNT(*) AS EXPECT_1 FROM mysql.wsrep_streaming_log;
EXPECT_1
1
connection node_3a;
SET GLOBAL wsrep_provider_options = 'gmcast.isolate = 1';
SET SESSION wsrep_sync_wait = 0;
SET SESSION wsrep_sync_wait = DEFAULT;
connection node_1a;
SET SESSION wsrep_sync_wait = 0;
SET SESSION wsrep_sync_wait = DEFAULT;
connection node_2a;
SET SESSION wsrep_sync_wait = 0;
SET SESSION wsrep_sync_wait = DEFAULT;
connection node_2;
SET DEBUG_SYNC = 'wsrep_before_certification SIGNAL before_cert WAIT_FOR continue';
COMMIT;
connection node_2a;
SET DEBUG_SYNC = 'now WAIT_FOR before_cert';
SET GLOBAL wsrep_provider_options = 'gmcast.isolate = 1';
SET SESSION wsrep_sync_wait = 0;
SET SESSION wsrep_sync_wait = DEFAULT;
SET DEBUG_SYNC = 'now SIGNAL continue';
connection node_2;
ERROR HY000: Got error 6 "No such device or address" during COMMIT
connection node_2a;
SET DEBUG_SYNC = 'RESET';
connection node_1a;
SET SESSION wsrep_sync_wait = 0;
SET SESSION wsrep_sync_wait = DEFAULT;
connection node_3a;
SET GLOBAL wsrep_provider_options = 'gmcast.isolate = 0';
SET SESSION wsrep_sync_wait = 0;
SELECT COUNT(*) AS EXPECT_1 FROM mysql.wsrep_streaming_log;
EXPECT_1
1
SET SESSION wsrep_sync_wait = DEFAULT;
connection node_1a;
SET SESSION wsrep_sync_wait = 0;
SELECT COUNT(*) AS EXPECT_1 FROM mysql.wsrep_streaming_log;
EXPECT_1
1
SET SESSION wsrep_sync_wait = DEFAULT;
connection node_2a;
SET GLOBAL wsrep_provider_options = 'gmcast.isolate = 0';
SET SESSION wsrep_sync_wait = DEFAULT;
connection node_1a;
SET SESSION wsrep_sync_wait = 0;
SET SESSION wsrep_sync_wait = DEFAULT;
connection node_3a;
SET SESSION wsrep_sync_wait = 0;
SET SESSION wsrep_sync_wait = DEFAULT;
connection node_1a;
Timeout in wait_condition.inc for SELECT COUNT(*) = 0 FROM mysql.wsrep_streaming_log
Id User Host db Command Time State Info Progress
1 system user NULL Sleep 66 wsrep aborter idle NULL 0.000
2 system user NULL Sleep 66 closing tables NULL 0.000
10 root localhost test Sleep 58 NULL 0.000
11 root localhost:52722 test Sleep 56 NULL 0.000
12 root localhost:52724 test Query 0 starting show full processlist 0.000
SELECT COUNT(*) AS EXPECT_0 FROM mysql.wsrep_streaming_log;
EXPECT_0
1
connection node_2a;
Timeout in wait_condition.inc for SELECT COUNT(*) = 0 FROM mysql.wsrep_streaming_log
Id User Host db Command Time State Info Progress
1 system user NULL Sleep 96 wsrep aborter idle NULL 0.000
2 system user NULL Sleep 87 closing tables NULL 0.000
10 root localhost:37222 test Sleep 64 NULL 0.000
11 root localhost:37228 test Query 0 starting show full processlist 0.000
SELECT COUNT(*) AS EXPECT_0 FROM mysql.wsrep_streaming_log;
EXPECT_0
1
connection node_3a;
Timeout in wait_condition.inc for SELECT COUNT(*) = 0 FROM mysql.wsrep_streaming_log
Id User Host db Command Time State Info Progress
1 system user NULL Sleep 122 wsrep aborter idle NULL 0.000
2 system user NULL Sleep 117 closing tables NULL 0.000
10 root localhost:60992 test Sleep 117 NULL 0.000
11 root localhost:60994 test Query 0 starting show full processlist 0.000
SELECT COUNT(*) AS EXPECT_0 FROM mysql.wsrep_streaming_log;
EXPECT_0
1
connection node_1;
DROP TABLE t1;

View File

@@ -32,14 +32,18 @@ Killing server ...
# restart
connection node_1;
COMMIT;
SELECT COUNT(*) = 5 FROM t1;
COUNT(*) = 5
count_match
1
count_match
1
connection node_1;
SELECT COUNT(*) FROM mysql.wsrep_streaming_log;
COUNT(*)
0
connection node_2;
SET SESSION TRANSACTION ISOLATION LEVEL READ COMMITTED;
SELECT COUNT(*) = 0 FROM mysql.wsrep_streaming_log;
COUNT(*) = 0
1
SELECT COUNT(*) FROM mysql.wsrep_streaming_log;
COUNT(*)
0
connection node_1;
DROP TABLE t1;
DROP TABLE t2;

View File

@@ -37,6 +37,8 @@ push @::global_suppressions,
qr|WSREP: Protocol violation. JOIN message sender .* is not in state transfer \(SYNCED\). Message ignored.|,
qr|WSREP: Protocol violation. JOIN message sender .* is not in state transfer \(JOINED\). Message ignored.|,
qr(WSREP: Action message in non-primary configuration from member [0-9]*),
qr(WSREP: Last Applied Action message in non-primary configuration from member [0-9]*),
qr|WSREP: .*core_handle_uuid_msg.*|,
qr(WSREP: --wsrep-causal-reads=ON takes precedence over --wsrep-sync-wait=0. WSREP_SYNC_WAIT_BEFORE_READ is on),
qr(WSREP: JOIN message from member .* in non-primary configuration. Ignored.),
);

View File

@@ -0,0 +1,168 @@
#
# MDEV-26707: SR transaction rolls back locally, but not in cluster
#
# This test excercises the following scenario:
# Initially we have a three node cluster where node 2 has an active
# SR transaction that has replicated one fragment.
# Node 3 disconnects from the cluster, followed by disconnect of node 2.
# Node 2 attempts to COMMIT its transaction, but fails because node 2 is
# non-primary. This failure causes the transaction to rolled back locally
# (node 2 can't communicate with the cluster at this point, so rollback
# fragment cannot be sent successfully)
# Node 3 joins back creating non-primary view (node 1, node 3).
# Then node 2 joins back creating primary view (node 1, node 1, node 3).
# If bug is present, we have that node 2 has rolled back locally, while
# the same transaction is still active nodes 1 and 3, leaving entries
# in their wsrep_streaming_log tables.
#
--source include/galera_cluster.inc
--source include/have_debug_sync.inc
--connect node_1a, 127.0.0.1, root, , test, $NODE_MYPORT_1
--connect node_2a, 127.0.0.1, root, , test, $NODE_MYPORT_2
--connect node_3, 127.0.0.1, root, , test, $NODE_MYPORT_3
--connect node_3a, 127.0.0.1, root, , test, $NODE_MYPORT_3
--connection node_1
CREATE TABLE t1 (f1 INTEGER PRIMARY KEY);
--connection node_2
SET SESSION wsrep_trx_fragment_size=1;
BEGIN;
INSERT INTO t1 VALUES (21);
--connection node_1
SELECT COUNT(*) AS EXPECT_1 FROM mysql.wsrep_streaming_log;
--connection node_2
SELECT COUNT(*) AS EXPECT_1 FROM mysql.wsrep_streaming_log;
--connection node_3
SELECT COUNT(*) AS EXPECT_1 FROM mysql.wsrep_streaming_log;
#
# Disconnect node 3 from cluster
#
--connection node_3a
SET GLOBAL wsrep_provider_options = 'gmcast.isolate = 1';
SET SESSION wsrep_sync_wait = 0;
--let $wait_condition = SELECT VARIABLE_VALUE = 1 FROM INFORMATION_SCHEMA.GLOBAL_STATUS WHERE VARIABLE_NAME = 'wsrep_cluster_size'
--source include/wait_condition.inc
SET SESSION wsrep_sync_wait = DEFAULT;
--connection node_1a
SET SESSION wsrep_sync_wait = 0;
--let $wait_condition = SELECT VARIABLE_VALUE = 2 FROM INFORMATION_SCHEMA.GLOBAL_STATUS WHERE VARIABLE_NAME = 'wsrep_cluster_size'
--source include/wait_condition.inc
SET SESSION wsrep_sync_wait = DEFAULT;
--connection node_2a
SET SESSION wsrep_sync_wait = 0;
--let $wait_condition = SELECT VARIABLE_VALUE = 2 FROM INFORMATION_SCHEMA.GLOBAL_STATUS WHERE VARIABLE_NAME = 'wsrep_cluster_size'
--source include/wait_condition.inc
SET SESSION wsrep_sync_wait = DEFAULT;
#
# Issue commit block COMMIT before certification on node 2
#
--connection node_2
SET DEBUG_SYNC = 'wsrep_before_certification SIGNAL before_cert WAIT_FOR continue';
--send COMMIT
--connection node_2a
SET DEBUG_SYNC = 'now WAIT_FOR before_cert';
#
# Disconnect node 2
#
SET GLOBAL wsrep_provider_options = 'gmcast.isolate = 1';
SET SESSION wsrep_sync_wait = 0;
--let $wait_condition = SELECT VARIABLE_VALUE = 1 FROM INFORMATION_SCHEMA.GLOBAL_STATUS WHERE VARIABLE_NAME = 'wsrep_cluster_size'
--source include/wait_condition.inc
SET SESSION wsrep_sync_wait = DEFAULT;
#
# Unblock COMMIT and expect it to fail
#
SET DEBUG_SYNC = 'now SIGNAL continue';
--connection node_2
--error ER_ERROR_DURING_COMMIT
--reap
--connection node_2a
SET DEBUG_SYNC = 'RESET';
--connection node_1a
SET SESSION wsrep_sync_wait = 0;
--let $wait_condition = SELECT VARIABLE_VALUE = 1 FROM INFORMATION_SCHEMA.GLOBAL_STATUS WHERE VARIABLE_NAME = 'wsrep_cluster_size'
--source include/wait_condition.inc
SET SESSION wsrep_sync_wait = DEFAULT;
#
# Reconnect node 3
#
--connection node_3a
SET GLOBAL wsrep_provider_options = 'gmcast.isolate = 0';
SET SESSION wsrep_sync_wait = 0;
--let $wait_condition = SELECT VARIABLE_VALUE = 2 FROM INFORMATION_SCHEMA.GLOBAL_STATUS WHERE VARIABLE_NAME = 'wsrep_cluster_size'
--source include/wait_condition.inc
SELECT COUNT(*) AS EXPECT_1 FROM mysql.wsrep_streaming_log;
SET SESSION wsrep_sync_wait = DEFAULT;
--connection node_1a
SET SESSION wsrep_sync_wait = 0;
--let $wait_condition = SELECT VARIABLE_VALUE = 2 FROM INFORMATION_SCHEMA.GLOBAL_STATUS WHERE VARIABLE_NAME = 'wsrep_cluster_size'
--source include/wait_condition.inc
SELECT COUNT(*) AS EXPECT_1 FROM mysql.wsrep_streaming_log;
SET SESSION wsrep_sync_wait = DEFAULT;
#
# Reconnect node 2
#
--connection node_2a
SET GLOBAL wsrep_provider_options = 'gmcast.isolate = 0';
--let $wait_condition = SELECT VARIABLE_VALUE = 3 FROM INFORMATION_SCHEMA.GLOBAL_STATUS WHERE VARIABLE_NAME = 'wsrep_cluster_size'
--source include/wait_condition.inc
--source include/galera_wait_ready.inc
SET SESSION wsrep_sync_wait = DEFAULT;
--connection node_1a
SET SESSION wsrep_sync_wait = 0;
--let $wait_condition = SELECT VARIABLE_VALUE = 3 FROM INFORMATION_SCHEMA.GLOBAL_STATUS WHERE VARIABLE_NAME = 'wsrep_cluster_size'
--source include/wait_condition.inc
--source include/galera_wait_ready.inc
SET SESSION wsrep_sync_wait = DEFAULT;
--connection node_3a
SET SESSION wsrep_sync_wait = 0;
--let $wait_condition = SELECT VARIABLE_VALUE = 3 FROM INFORMATION_SCHEMA.GLOBAL_STATUS WHERE VARIABLE_NAME = 'wsrep_cluster_size'
--source include/wait_condition.inc
--source include/galera_wait_ready.inc
SET SESSION wsrep_sync_wait = DEFAULT;
#
# Expect no entries in wsrep_streaming_log
#
--connection node_1a
--let $wait_condition = SELECT COUNT(*) = 0 FROM mysql.wsrep_streaming_log
--source include/wait_condition.inc
SELECT COUNT(*) AS EXPECT_0 FROM mysql.wsrep_streaming_log;
--connection node_2a
--let $wait_condition = SELECT COUNT(*) = 0 FROM mysql.wsrep_streaming_log
--source include/wait_condition.inc
SELECT COUNT(*) AS EXPECT_0 FROM mysql.wsrep_streaming_log;
--connection node_3a
--let $wait_condition = SELECT COUNT(*) = 0 FROM mysql.wsrep_streaming_log
--source include/wait_condition.inc
SELECT COUNT(*) AS EXPECT_0 FROM mysql.wsrep_streaming_log;
--connection node_1
DROP TABLE t1;

View File

@@ -51,20 +51,37 @@ INSERT INTO t1 VALUES (5);
--source include/kill_galera.inc
--source include/start_mysqld.inc
# Expect that the SR table will get some entries after the restart
--let $wait_condition = SELECT COUNT(*) > 0 FROM mysql.wsrep_streaming_log;
--source include/wait_condition.inc
--connection node_1
# The following COMMIT usually succeeds. Due to timing,
# it is however possible that this node delivers the same
# view twice during configuration change. In which case
# this transaction will mistakenly be considered orphaned,
# and aborted.
--error 0, ER_LOCK_DEADLOCK
COMMIT;
--disable_query_log
if ($mysql_errno == 0) {
--connection node_1
SELECT COUNT(*) = 5 AS count_match FROM t1;
--connection node_2
SELECT COUNT(*) = 5 AS count_match FROM t1;
}
if ($mysql_errno == 1213) {
--connection node_1
SELECT COUNT(*) = 0 AS count_match FROM t1;
--connection node_2
SELECT COUNT(*) = 0 AS count_match FROM t1;
}
--enable_query_log
--connection node_1
COMMIT;
SELECT COUNT(*) = 5 FROM t1;
SELECT COUNT(*) FROM mysql.wsrep_streaming_log;
--connection node_2
SET SESSION TRANSACTION ISOLATION LEVEL READ COMMITTED;
--let $wait_condition = SELECT COUNT(*) = 5 FROM t1;
--source include/wait_condition.inc
SELECT COUNT(*) = 0 FROM mysql.wsrep_streaming_log;
SELECT COUNT(*) FROM mysql.wsrep_streaming_log;
--connection node_1
DROP TABLE t1;

View File

@@ -0,0 +1,52 @@
CREATE TABLE t1 (
pk INT,
f1 VARCHAR(10) NOT NULL,
f2 VARCHAR(10) NULL,
f3 INT UNSIGNED NULL,
KEY (f1),
PRIMARY KEY (pk)
) ENGINE=InnoDB;
CREATE OR REPLACE ALGORITHM=MERGE VIEW v4 AS SELECT * FROM t1;
INSERT INTO t1 VALUES (1,'k','g',6),(2,'y','r',0),(3,'t','q',1),(4,'a','r',NULL),(5,'z','t',NULL);
CREATE TABLE t2 (f VARCHAR(10) NULL) ENGINE=InnoDB;
INSERT INTO t2 VALUES (NULL),('g'),('e'),('g');
CREATE TABLE t3 (
f1 VARCHAR(10) NOT NULL,
f2 VARCHAR(10) NULL,
f3 INT UNSIGNED NULL
) ENGINE=InnoDB;
INSERT INTO t3 VALUES ('k','n',9),('y','b',8),('m','w',6);
CREATE TABLE t4 (f INT NULL) ENGINE=InnoDB;
INSERT INTO t4 VALUES (8),(9);
UPDATE t1 SET t1.pk = -109 WHERE t1.f1 IN ( SELECT 'a' FROM t4 WHERE f >= 1 );
SET DEBUG_SYNC='now SIGNAL con1_dml';
connect con1,localhost,root,,test;
SET DEBUG_SYNC='now WAIT_FOR con1_dml';
begin;
SELECT * FROM t1 for update;
pk f1 f2 f3
-109 a r NULL
1 k g 6
2 y r 0
3 t q 1
5 z t NULL
SET DEBUG_SYNC='now SIGNAL default_dml';
connection default;
SET DEBUG_SYNC='now WAIT_FOR default_dml';
UPDATE t3 AS alias1 LEFT JOIN t3 AS alias2 ON ( alias1.f1 <> alias1.f2 ) SET alias1.f3 = 59 WHERE ( EXISTS ( SELECT t1.f3 FROM t1 WHERE t1.f1 = alias1.f1 ) ) OR alias2.f1 = 'h';
connect con2,localhost,root,,test;
set debug_sync='now WAIT_FOR default_dml';
SET DEBUG_SYNC='now SIGNAL con1_dml2';
disconnect con2;
connection con1;
SET DEBUG_SYNC='now WAIT_FOR con1_dml2';
UPDATE v4, t1 SET t1.pk = 76 WHERE t1.f2 IN ( SELECT t2.f FROM t2 INNER JOIN t3 );
connection default;
ERROR 40001: Deadlock found when trying to get lock; try restarting transaction
connection con1;
COMMIT;
disconnect con1;
connection default;
DROP VIEW v4;
DROP TABLE t1, t2, t3, t4;
set debug_sync= reset;

View File

@@ -0,0 +1 @@
--loose-innodb_lock_waits

View File

@@ -0,0 +1,70 @@
--source include/have_innodb.inc
--source include/count_sessions.inc
--source include/have_debug_sync.inc
CREATE TABLE t1 (
pk INT,
f1 VARCHAR(10) NOT NULL,
f2 VARCHAR(10) NULL,
f3 INT UNSIGNED NULL,
KEY (f1),
PRIMARY KEY (pk)
) ENGINE=InnoDB;
CREATE OR REPLACE ALGORITHM=MERGE VIEW v4 AS SELECT * FROM t1;
INSERT INTO t1 VALUES (1,'k','g',6),(2,'y','r',0),(3,'t','q',1),(4,'a','r',NULL),(5,'z','t',NULL);
CREATE TABLE t2 (f VARCHAR(10) NULL) ENGINE=InnoDB;
INSERT INTO t2 VALUES (NULL),('g'),('e'),('g');
CREATE TABLE t3 (
f1 VARCHAR(10) NOT NULL,
f2 VARCHAR(10) NULL,
f3 INT UNSIGNED NULL
) ENGINE=InnoDB;
INSERT INTO t3 VALUES ('k','n',9),('y','b',8),('m','w',6);
CREATE TABLE t4 (f INT NULL) ENGINE=InnoDB;
INSERT INTO t4 VALUES (8),(9);
UPDATE t1 SET t1.pk = -109 WHERE t1.f1 IN ( SELECT 'a' FROM t4 WHERE f >= 1 );
SET DEBUG_SYNC='now SIGNAL con1_dml';
--connect (con1,localhost,root,,test)
SET DEBUG_SYNC='now WAIT_FOR con1_dml';
begin;
SELECT * FROM t1 for update; # Holds x lock of all records in the table t1
SET DEBUG_SYNC='now SIGNAL default_dml';
--connection default
SET DEBUG_SYNC='now WAIT_FOR default_dml';
--send UPDATE t3 AS alias1 LEFT JOIN t3 AS alias2 ON ( alias1.f1 <> alias1.f2 ) SET alias1.f3 = 59 WHERE ( EXISTS ( SELECT t1.f3 FROM t1 WHERE t1.f1 = alias1.f1 ) ) OR alias2.f1 = 'h'
# It holds the lock of all record in t3 and tries to acquire record lock for the table t1.
--connect (con2,localhost,root,,test)
set debug_sync='now WAIT_FOR default_dml';
let $wait_condition=
select count(*) > 0 from information_schema.innodb_lock_waits;
--source include/wait_condition.inc
SET DEBUG_SYNC='now SIGNAL con1_dml2';
disconnect con2;
# Cleanup
--connection con1
SET DEBUG_SYNC='now WAIT_FOR con1_dml2';
UPDATE v4, t1 SET t1.pk = 76 WHERE t1.f2 IN ( SELECT t2.f FROM t2 INNER JOIN t3 );
# It holds the record lock on table t1 and tries to acquire record lock on t3.
# leads to deadlock (con1 trx is waiting for default trx and vice versa)
--connection default
--error ER_LOCK_DEADLOCK
--reap
connection con1;
COMMIT;
disconnect con1;
--connection default
DROP VIEW v4;
DROP TABLE t1, t2, t3, t4;
set debug_sync= reset;

View File

@@ -21,10 +21,26 @@ ORDER BY VARIABLE_NAME;
VARIABLE_VALUE>0 VARIABLE_NAME
1 Collation used binary
1 Collation used latin1_swedish_ci
1 Collation used utf8mb3_bin
1 Collation used utf8mb3_general_ci
1 Collation used utf8mb4_bin
1 Collation used utf8_bin
1 Collation used utf8_general_ci
prepare stmt from "SELECT VARIABLE_VALUE>0, VARIABLE_NAME FROM INFORMATION_SCHEMA.FEEDBACK WHERE VARIABLE_NAME LIKE 'Collation used %' ORDER BY VARIABLE_NAME";
execute stmt;
VARIABLE_VALUE>0 VARIABLE_NAME
1 Collation used binary
1 Collation used latin1_swedish_ci
1 Collation used utf8mb3_bin
1 Collation used utf8mb3_general_ci
1 Collation used utf8mb4_bin
execute stmt;
VARIABLE_VALUE>0 VARIABLE_NAME
1 Collation used binary
1 Collation used latin1_swedish_ci
1 Collation used utf8mb3_bin
1 Collation used utf8mb3_general_ci
1 Collation used utf8mb4_bin
deallocate prepare stmt;
set global sql_mode=ONLY_FULL_GROUP_BY;
# restart
6: feedback plugin: report to 'http://mariadb.org/feedback_plugin/post' was sent
6: feedback plugin: server replied 'ok'
feedback plugin: report to 'http://mariadb.org/feedback_plugin/post' was sent
feedback plugin: server replied 'ok'

View File

@@ -38,6 +38,6 @@ perl;
while ($_=<LOG>) {
$logg{$&}++ if /feedback plugin:.*/;
}
print "$logg{$_}: $_\n" for sort keys %logg;
print "$_\n" for sort keys %logg;
close LOG;
EOF

View File

@@ -763,6 +763,25 @@ set system_versioning_alter_history= keep;
alter ignore table t1 drop pk;
drop table t1;
#
# MDEV-22660 SIGSEGV on adding system versioning and modifying system column
#
create or replace table t1 (a int);
alter table t1
add row_start timestamp(6) as row start,
add row_end timestamp(6) as row end,
add period for system_time(row_start, row_end),
with system versioning,
modify row_end varchar(8);
ERROR HY000: PERIOD FOR SYSTEM_TIME must use columns `row_start` and `row_end`
alter table t1
add row_start timestamp(6) as row start,
add row_end timestamp(6) as row end,
add period for system_time(row_start, row_end),
with system versioning,
modify row_start varchar(8);
ERROR HY000: PERIOD FOR SYSTEM_TIME must use columns `row_start` and `row_end`
drop table t1;
#
# MDEV-21941 RENAME doesn't work for system time or period fields
#
create or replace table t1 (a int) with system versioning;

View File

@@ -657,6 +657,28 @@ alter ignore table t1 drop pk;
drop table t1;
--echo #
--echo # MDEV-22660 SIGSEGV on adding system versioning and modifying system column
--echo #
create or replace table t1 (a int);
--error ER_VERS_PERIOD_COLUMNS
alter table t1
add row_start timestamp(6) as row start,
add row_end timestamp(6) as row end,
add period for system_time(row_start, row_end),
with system versioning,
modify row_end varchar(8);
--error ER_VERS_PERIOD_COLUMNS
alter table t1
add row_start timestamp(6) as row start,
add row_end timestamp(6) as row end,
add period for system_time(row_start, row_end),
with system versioning,
modify row_start varchar(8);
# cleanup
drop table t1;
--echo #
--echo # MDEV-21941 RENAME doesn't work for system time or period fields
--echo #

View File

@@ -2501,7 +2501,7 @@ Field *Field::make_new_field(MEM_ROOT *root, TABLE *new_table,
tmp->unireg_check= Field::NONE;
tmp->flags&= (NOT_NULL_FLAG | BLOB_FLAG | UNSIGNED_FLAG |
ZEROFILL_FLAG | BINARY_FLAG | ENUM_FLAG | SET_FLAG |
VERS_SYS_START_FLAG | VERS_SYS_END_FLAG |
VERS_ROW_START | VERS_ROW_END |
VERS_UPDATE_UNVERSIONED_FLAG);
tmp->reset_fields();
tmp->invisible= VISIBLE;

View File

@@ -1800,7 +1800,7 @@ public:
bool vers_sys_field() const
{
return flags & (VERS_SYS_START_FLAG | VERS_SYS_END_FLAG);
return flags & (VERS_ROW_START | VERS_ROW_END);
}
bool vers_update_unversioned() const
@@ -5306,7 +5306,7 @@ public:
}
bool vers_sys_field() const
{
return flags & (VERS_SYS_START_FLAG | VERS_SYS_END_FLAG);
return flags & (VERS_ROW_START | VERS_ROW_END);
}
void create_length_to_internal_length_bit();
void create_length_to_internal_length_newdecimal();

View File

@@ -8200,11 +8200,11 @@ bool Vers_parse_info::is_end(const char *name) const
}
bool Vers_parse_info::is_start(const Create_field &f) const
{
return f.flags & VERS_SYS_START_FLAG;
return f.flags & VERS_ROW_START;
}
bool Vers_parse_info::is_end(const Create_field &f) const
{
return f.flags & VERS_SYS_END_FLAG;
return f.flags & VERS_ROW_END;
}
static Create_field *vers_init_sys_field(THD *thd, const char *field_name, int flags, bool integer)
@@ -8264,8 +8264,8 @@ bool Vers_parse_info::fix_implicit(THD *thd, Alter_info *alter_info)
period= start_end_t(default_start, default_end);
as_row= period;
if (vers_create_sys_field(thd, default_start, alter_info, VERS_SYS_START_FLAG) ||
vers_create_sys_field(thd, default_end, alter_info, VERS_SYS_END_FLAG))
if (vers_create_sys_field(thd, default_start, alter_info, VERS_ROW_START) ||
vers_create_sys_field(thd, default_end, alter_info, VERS_ROW_END))
{
return true;
}
@@ -8420,7 +8420,7 @@ bool Vers_parse_info::fix_alter_info(THD *thd, Alter_info *alter_info,
return true;
}
my_error(ER_VERS_DUPLICATE_ROW_START_END, MYF(0),
f->flags & VERS_SYS_START_FLAG ? "START" : "END", f->field_name.str);
f->flags & VERS_ROW_START ? "START" : "END", f->field_name.str);
return true;
}
}
@@ -8534,13 +8534,13 @@ Vers_parse_info::fix_create_like(Alter_info &alter_info, HA_CREATE_INFO &create_
while ((f= it++))
{
if (f->flags & VERS_SYS_START_FLAG)
if (f->flags & VERS_ROW_START)
{
f_start= f;
if (f_end)
break;
}
else if (f->flags & VERS_SYS_END_FLAG)
else if (f->flags & VERS_ROW_END)
{
f_end= f;
if (f_start)
@@ -8686,6 +8686,7 @@ bool Vers_type_trx::check_sys_fields(const LEX_CSTRING &table_name,
return false;
}
bool Vers_parse_info::check_sys_fields(const Lex_table_name &table_name,
const Lex_table_name &db,
Alter_info *alter_info) const
@@ -8694,18 +8695,21 @@ bool Vers_parse_info::check_sys_fields(const Lex_table_name &table_name,
return true;
List_iterator<Create_field> it(alter_info->create_list);
const Create_field *row_start= NULL;
const Create_field *row_end= NULL;
const Create_field *row_start= nullptr;
const Create_field *row_end= nullptr;
while (const Create_field *f= it++)
{
if (f->flags & VERS_SYS_START_FLAG && !row_start)
if (f->flags & VERS_ROW_START && !row_start)
row_start= f;
if (f->flags & VERS_SYS_END_FLAG && !row_end)
if (f->flags & VERS_ROW_END && !row_end)
row_end= f;
}
DBUG_ASSERT(row_start);
DBUG_ASSERT(row_end);
if (!row_start || !row_end)
{
my_error(ER_VERS_PERIOD_COLUMNS, MYF(0), as_row.start.str, as_row.end.str);
return true;
}
const Vers_type_handler *row_start_vers= row_start->type_handler()->vers();
@@ -8715,10 +8719,7 @@ bool Vers_parse_info::check_sys_fields(const Lex_table_name &table_name,
return true;
}
if (row_start_vers->check_sys_fields(table_name, row_start, row_end))
return true;
return false;
return row_start_vers->check_sys_fields(table_name, row_start, row_end);
}
bool Table_period_info::check_field(const Create_field* f,

View File

@@ -360,6 +360,8 @@ String *Item_aes_crypt::val_str(String *str2)
rkey, AES_KEY_LENGTH / 8, 0, 0))
{
str2->length((uint) aes_length);
DBUG_ASSERT(collation.collation == &my_charset_bin);
str2->set_charset(&my_charset_bin);
return str2;
}
}

View File

@@ -30,7 +30,7 @@ bool Item_func_history::val_bool()
{
Item_field *f= static_cast<Item_field *>(args[0]);
DBUG_ASSERT(f->fixed());
DBUG_ASSERT(f->field->flags & VERS_SYS_END_FLAG);
DBUG_ASSERT(f->field->flags & VERS_ROW_END);
return !f->field->is_max();
}

View File

@@ -8475,7 +8475,9 @@ static int get_options(int *argc_ptr, char ***argv_ptr)
if (global_system_variables.low_priority_updates)
thr_upgraded_concurrent_insert_lock= TL_WRITE_LOW_PRIORITY;
if (ft_boolean_check_syntax_string((uchar*) ft_boolean_syntax))
if (ft_boolean_check_syntax_string((uchar*) ft_boolean_syntax,
strlen(ft_boolean_syntax),
system_charset_info))
{
sql_print_error("Invalid ft-boolean-syntax string: %s",
ft_boolean_syntax);

View File

@@ -8865,6 +8865,8 @@ fill_record(THD *thd, TABLE *table, Field **ptr, List<Item> &values,
if (!thd->is_error())
{
thd->abort_on_warning= FALSE;
if (table->default_field && table->update_default_fields(ignore_errors))
goto err;
if (table->versioned())
table->vers_update_fields();
if (table->vfield &&

View File

@@ -121,11 +121,13 @@ public:
*/
enum explain_connection_type connection_type;
protected:
/*
A node may have children nodes. When a node's explain structure is
created, children nodes may not yet have QPFs. This is why we store ids.
*/
Dynamic_array<int> children;
public:
void add_child(int select_no)
{
children.append(select_no);

View File

@@ -1349,7 +1349,18 @@ values_loop_end:
abort:
#ifndef EMBEDDED_LIBRARY
if (lock_type == TL_WRITE_DELAYED)
{
end_delayed_insert(thd);
/*
In case of an error (e.g. data truncation), the data type specific data
in fields (e.g. Field_blob::value) was not taken over
by the delayed writer thread. All fields in table_list->table
will be freed by free_root() soon. We need to free the specific
data before free_root() to avoid a memory leak.
*/
for (Field **ptr= table_list->table->field ; *ptr ; ptr++)
(*ptr)->free();
}
#endif
if (table != NULL)
table->file->ha_release_auto_increment();

View File

@@ -9707,7 +9707,7 @@ bool LEX::last_field_generated_always_as_row_start()
Vers_parse_info &info= vers_get_info();
Lex_ident *p= &info.as_row.start;
return last_field_generated_always_as_row_start_or_end(p, "START",
VERS_SYS_START_FLAG);
VERS_ROW_START);
}
@@ -9716,7 +9716,7 @@ bool LEX::last_field_generated_always_as_row_end()
Vers_parse_info &info= vers_get_info();
Lex_ident *p= &info.as_row.end;
return last_field_generated_always_as_row_start_or_end(p, "END",
VERS_SYS_END_FLAG);
VERS_ROW_END);
}
void st_select_lex_unit::reset_distinct()

View File

@@ -4914,7 +4914,8 @@ mysql_select(THD *thd, TABLE_LIST *tables, List<Item> &fields, COND *conds,
bool free_join= 1;
DBUG_ENTER("mysql_select");
select_lex->context.resolve_in_select_list= TRUE;
if (!fields.is_empty())
select_lex->context.resolve_in_select_list= true;
JOIN *join;
if (select_lex->join != 0)
{
@@ -21216,26 +21217,33 @@ evaluate_join_record(JOIN *join, JOIN_TAB *join_tab,
will be re-evaluated again. It could be fixed, but, probably,
it's not worth doing now.
*/
if (tab->select_cond && !tab->select_cond->val_int())
if (tab->select_cond)
{
/* The condition attached to table tab is false */
if (tab == join_tab)
const longlong res= tab->select_cond->val_int();
if (join->thd->is_error())
DBUG_RETURN(NESTED_LOOP_ERROR);
if (!res)
{
found= 0;
if (not_exists_opt_is_applicable)
DBUG_RETURN(NESTED_LOOP_NO_MORE_ROWS);
}
else
{
/*
Set a return point if rejected predicate is attached
not to the last table of the current nest level.
*/
join->return_tab= tab;
if (not_exists_opt_is_applicable)
DBUG_RETURN(NESTED_LOOP_NO_MORE_ROWS);
/* The condition attached to table tab is false */
if (tab == join_tab)
{
found= 0;
if (not_exists_opt_is_applicable)
DBUG_RETURN(NESTED_LOOP_NO_MORE_ROWS);
}
else
DBUG_RETURN(NESTED_LOOP_OK);
{
/*
Set a return point if rejected predicate is attached
not to the last table of the current nest level.
*/
join->return_tab= tab;
if (not_exists_opt_is_applicable)
DBUG_RETURN(NESTED_LOOP_NO_MORE_ROWS);
else
DBUG_RETURN(NESTED_LOOP_OK);
}
}
}
}

View File

@@ -2234,11 +2234,11 @@ int show_create_table_ex(THD *thd, TABLE_LIST *table_list,
}
else
{
if (field->flags & VERS_SYS_START_FLAG)
if (field->flags & VERS_ROW_START)
{
packet->append(STRING_WITH_LEN(" GENERATED ALWAYS AS ROW START"));
}
else if (field->flags & VERS_SYS_END_FLAG)
else if (field->flags & VERS_ROW_END)
{
packet->append(STRING_WITH_LEN(" GENERATED ALWAYS AS ROW END"));
}
@@ -6099,7 +6099,7 @@ static int get_schema_column_record(THD *thd, TABLE_LIST *tables,
}
else if (field->flags & VERS_SYSTEM_FIELD)
{
if (field->flags & VERS_SYS_START_FLAG)
if (field->flags & VERS_ROW_START)
{
table->field[21]->store(STRING_WITH_LEN("ROW START"), cs);
buf.set(STRING_WITH_LEN("STORED GENERATED"), cs);

View File

@@ -7854,7 +7854,7 @@ mysql_prepare_alter_table(THD *thd, TABLE *table,
def= new (thd->mem_root) Create_field(thd, field, field);
def->invisible= INVISIBLE_SYSTEM;
alter_info->flags|= ALTER_CHANGE_COLUMN;
if (field->flags & VERS_SYS_START_FLAG)
if (field->flags & VERS_ROW_START)
create_info->vers_info.as_row.start= def->field_name= Vers_parse_info::default_start;
else
create_info->vers_info.as_row.end= def->field_name= Vers_parse_info::default_end;
@@ -7885,9 +7885,9 @@ mysql_prepare_alter_table(THD *thd, TABLE *table,
def->change= alter->name;
def->field_name= alter->new_name;
column_rename_param.fields.push_back(def);
if (field->flags & VERS_SYS_START_FLAG)
if (field->flags & VERS_ROW_START)
create_info->vers_info.as_row.start= alter->new_name;
else if (field->flags & VERS_SYS_END_FLAG)
else if (field->flags & VERS_ROW_END)
create_info->vers_info.as_row.end= alter->new_name;
if (table->s->period.name)
{
@@ -7949,9 +7949,9 @@ mysql_prepare_alter_table(THD *thd, TABLE *table,
!vers_system_invisible)
{
StringBuffer<NAME_LEN*3> tmp;
if (!(dropped_sys_vers_fields & VERS_SYS_START_FLAG))
if (!(dropped_sys_vers_fields & VERS_ROW_START))
append_drop_column(thd, &tmp, table->vers_start_field());
if (!(dropped_sys_vers_fields & VERS_SYS_END_FLAG))
if (!(dropped_sys_vers_fields & VERS_ROW_END))
append_drop_column(thd, &tmp, table->vers_end_field());
my_error(ER_MISSING, MYF(0), table->s->table_name.str, tmp.c_ptr());
goto err;

View File

@@ -8160,7 +8160,7 @@ Field *Type_handler_longlong::
const Column_definition_attributes *attr,
uint32 flags) const
{
if (flags & (VERS_SYS_START_FLAG|VERS_SYS_END_FLAG))
if (flags & (VERS_ROW_START|VERS_ROW_END))
return new (mem_root)
Field_vers_trx_id(rec.ptr(), (uint32) attr->length,
rec.null_ptr(), rec.null_bit(),

View File

@@ -1236,7 +1236,9 @@ static Sys_var_ulong Sys_flush_time(
static bool check_ftb_syntax(sys_var *self, THD *thd, set_var *var)
{
return ft_boolean_check_syntax_string((uchar*)
(var->save_result.string_value.str));
(var->save_result.string_value.str),
var->save_result.string_value.length,
self->charset(thd));
}
static bool query_cache_flush(sys_var *self, THD *thd, enum_var_type type)
{

View File

@@ -1347,7 +1347,10 @@ bool parse_vcol_defs(THD *thd, MEM_ROOT *mem_root, TABLE *table,
if (check_vcol_forward_refs(field, field->vcol_info, 0) ||
check_vcol_forward_refs(field, field->check_constraint, 1) ||
check_vcol_forward_refs(field, field->default_value, 0))
{
*error_reported= true;
goto end;
}
}
table->find_constraint_correlated_indexes();
@@ -2647,9 +2650,9 @@ int TABLE_SHARE::init_from_binary_frm_image(THD *thd, bool write,
if (versioned)
{
if (i == vers.start_fieldno)
flags|= VERS_SYS_START_FLAG;
flags|= VERS_ROW_START;
else if (i == vers.end_fieldno)
flags|= VERS_SYS_END_FLAG;
flags|= VERS_ROW_END;
if (flags & VERS_SYSTEM_FIELD)
{

View File

@@ -428,7 +428,14 @@ static inline
int wsrep_after_statement(THD* thd)
{
DBUG_ENTER("wsrep_after_statement");
DBUG_RETURN(thd->wsrep_cs().state() != wsrep::client_state::s_none &&
WSREP_DEBUG("wsrep_after_statement for %lu client_state %s "
" client_mode %s trans_state %s",
thd_get_thread_id(thd),
wsrep::to_c_string(thd->wsrep_cs().state()),
wsrep::to_c_string(thd->wsrep_cs().mode()),
wsrep::to_c_string(thd->wsrep_cs().transaction().state()));
DBUG_RETURN((thd->wsrep_cs().state() != wsrep::client_state::s_none &&
thd->wsrep_cs().mode() == Wsrep_client_state::m_local) &&
!thd->internal_transaction() ?
thd->wsrep_cs().after_statement() : 0);
}

View File

@@ -12,6 +12,7 @@
#include <mysql.h>
#include <sql_error.h>
#include <stdio.h>
#include <cassert>
#include "bsonudf.h"
@@ -691,7 +692,7 @@ PVAL BJNX::GetCalcValue(PGLOBAL g, PBVAL bap, int n)
break;
default:
break;
DBUG_ASSERT(!"Implement new op type support.");
} // endswitch Op
return valp = AllocateValue(g, type, lng, prec);
@@ -4979,7 +4980,7 @@ char *bbin_array_add(UDF_INIT *initid, UDF_ARGS *args, char *result,
uint n = 2;
int* x = GetIntArgPtr(g, args, n);
BJNX bnx(g, NULL, TYPE_STRING);
PBVAL top, jarp = NULL, jvp = NULL;
PBVAL jarp = NULL, top = NULL, jvp = NULL;
PBVAL jsp = bnx.MakeValue(args, 0, true, &top);
if (bnx.CheckPath(g, args, jsp, jvp, 2))

View File

@@ -191,7 +191,7 @@ static void PROFILE_Save( FILE *file, PROFILESECTION *section )
secno++;
}
for (key = section->key; key; key = key->next)
for (key = section->key; key; key = key->next) {
if (key->name[0]) {
fprintf(file, "%s", SVP(key->name));
@@ -199,9 +199,9 @@ static void PROFILE_Save( FILE *file, PROFILESECTION *section )
fprintf(file, "=%s", SVP(key->value));
fprintf(file, "\n");
} // endif key->name
} // endfor section
} // endif key->name
}
} // endfor section
} // end of PROFILE_Save

View File

@@ -126,7 +126,7 @@ static void buf_flush_validate_skip()
#endif /* UNIV_DEBUG */
/** Wake up the page cleaner if needed */
inline void buf_pool_t::page_cleaner_wakeup()
void buf_pool_t::page_cleaner_wakeup()
{
if (!page_cleaner_idle())
return;

View File

@@ -17143,7 +17143,12 @@ innodb_max_dirty_pages_pct_update(
}
srv_max_buf_pool_modified_pct = in_val;
pthread_cond_signal(&buf_pool.do_flush_list);
mysql_mutex_unlock(&LOCK_global_system_variables);
mysql_mutex_lock(&buf_pool.flush_list_mutex);
buf_pool.page_cleaner_wakeup();
mysql_mutex_unlock(&buf_pool.flush_list_mutex);
mysql_mutex_lock(&LOCK_global_system_variables);
}
/****************************************************************//**
@@ -17174,7 +17179,12 @@ innodb_max_dirty_pages_pct_lwm_update(
}
srv_max_dirty_pages_pct_lwm = in_val;
pthread_cond_signal(&buf_pool.do_flush_list);
mysql_mutex_unlock(&LOCK_global_system_variables);
mysql_mutex_lock(&buf_pool.flush_list_mutex);
buf_pool.page_cleaner_wakeup();
mysql_mutex_unlock(&buf_pool.flush_list_mutex);
mysql_mutex_lock(&LOCK_global_system_variables);
}
/*************************************************************//**

View File

@@ -1841,7 +1841,7 @@ public:
return page_cleaner_is_idle;
}
/** Wake up the page cleaner if needed */
inline void page_cleaner_wakeup();
void page_cleaner_wakeup();
/** Register whether an explicit wakeup of the page cleaner is needed */
void page_cleaner_set_idle(bool deep_sleep)

View File

@@ -1483,7 +1483,10 @@ inline void fil_space_t::reacquire()
inline bool fil_space_t::set_stopping_check()
{
mysql_mutex_assert_owner(&fil_system.mutex);
#if defined __GNUC__ && (defined __i386__ || defined __x86_64__)
#if defined __clang_major__ && __clang_major__ < 10
/* Only clang-10 introduced support for asm goto */
return n_pending.fetch_or(STOPPING, std::memory_order_relaxed) & STOPPING;
#elif defined __GNUC__ && (defined __i386__ || defined __x86_64__)
static_assert(STOPPING == 1U << 31, "compatibility");
__asm__ goto("lock btsl $31, %0\t\njnc %l1" : : "m" (n_pending)
: "cc", "memory" : not_stopped);

View File

@@ -803,6 +803,9 @@ void log_write_up_to(lsn_t lsn, bool flush_to_disk, bool rotate_key,
return;
}
repeat:
lsn_t ret_lsn1= 0, ret_lsn2= 0;
if (flush_to_disk &&
flush_lock.acquire(lsn, callback) != group_commit_lock::ACQUIRED)
return;
@@ -817,20 +820,32 @@ void log_write_up_to(lsn_t lsn, bool flush_to_disk, bool rotate_key,
log_write(rotate_key);
ut_a(log_sys.write_lsn == write_lsn);
write_lock.release(write_lsn);
ret_lsn1= write_lock.release(write_lsn);
}
if (!flush_to_disk)
return;
if (flush_to_disk)
{
/* Flush the highest written lsn.*/
auto flush_lsn = write_lock.value();
flush_lock.set_pending(flush_lsn);
log_write_flush_to_disk_low(flush_lsn);
ret_lsn2= flush_lock.release(flush_lsn);
/* Flush the highest written lsn.*/
auto flush_lsn = write_lock.value();
flush_lock.set_pending(flush_lsn);
log_write_flush_to_disk_low(flush_lsn);
flush_lock.release(flush_lsn);
log_flush_notify(flush_lsn);
DBUG_EXECUTE_IF("crash_after_log_write_upto", DBUG_SUICIDE(););
}
log_flush_notify(flush_lsn);
DBUG_EXECUTE_IF("crash_after_log_write_upto", DBUG_SUICIDE(););
if (ret_lsn1 || ret_lsn2)
{
/*
There is no new group commit lead, some async waiters could stall.
Rerun log_write_up_to(), to prevent that.
*/
lsn= std::max(ret_lsn1, ret_lsn2);
static const completion_callback dummy{[](void *) {},nullptr};
callback= &dummy;
goto repeat;
}
}
/** Write to the log file up to the last log entry.

View File

@@ -274,11 +274,11 @@ group_commit_lock::lock_return_code group_commit_lock::acquire(value_type num, c
return lock_return_code::EXPIRED;
}
void group_commit_lock::release(value_type num)
group_commit_lock::value_type group_commit_lock::release(value_type num)
{
completion_callback callbacks[1000];
size_t callback_count = 0;
value_type ret = 0;
std::unique_lock<std::mutex> lk(m_mtx);
m_lock = false;
@@ -359,6 +359,12 @@ void group_commit_lock::release(value_type num)
{
wakeup_list->m_group_commit_leader=true;
}
else
{
/* Tell the caller that some pending callbacks left, and he should
do something to prevent stalls. This should be a rare situation.*/
ret= m_pending_callbacks[0].first;
}
}
lk.unlock();
@@ -371,6 +377,7 @@ void group_commit_lock::release(value_type num)
next= cur->m_next;
cur->m_sema.wake();
}
return ret;
}
#ifndef DBUG_OFF

View File

@@ -39,16 +39,23 @@ It has a state consisting of
Operations supported on this semaphore
1.acquire(num):
1.acquire(num, callback):
- waits until current value exceeds num, or until lock is granted.
if running synchronously (callback is nullptr)
- returns EXPIRED if current_value >= num,
or ACQUIRED, if current_value < num and lock is granted.
or ACQUIRED, if current_value < num and lock is granted,
or CALLBACK_QUEUED, if callback was not nullptr, and function
would otherwise have to wait
2.release(num)
- releases lock
- sets new current value to max(num,current_value)
- releases some threads waiting in acquire()
- executes some callbacks
- might return some lsn, meaning there are some pending
callbacks left, and there is no new group commit lead
(i.e caller must do something to flush those pending callbacks)
3. value()
- read current value
@@ -82,7 +89,7 @@ public:
CALLBACK_QUEUED
};
lock_return_code acquire(value_type num, const completion_callback *cb);
void release(value_type num);
value_type release(value_type num);
value_type value() const;
value_type pending() const;
void set_pending(value_type num);

View File

@@ -308,7 +308,10 @@ Hence, we will manually translate fetch_or() using GCC-style inline
assembler code or a Microsoft intrinsic function.
*/
#if defined __GNUC__ && (defined __i386__ || defined __x86_64__)
#if defined __clang_major__ && __clang_major__ < 10
/* Only clang-10 introduced support for asm goto */
#elif defined __GNUC__ && (defined __i386__ || defined __x86_64__)
# define IF_FETCH_OR_GOTO(mem, bit, label) \
__asm__ goto("lock btsl $" #bit ", %0\n\t" \
"jc %l1" : : "m" (mem) : "cc", "memory" : label);

View File

@@ -79,18 +79,25 @@ FT_WORD * ft_linearize(TREE *wtree, MEM_ROOT *mem_root)
DBUG_RETURN(wlist);
}
my_bool ft_boolean_check_syntax_string(const uchar *str)
my_bool ft_boolean_check_syntax_string(const uchar *str, size_t length,
CHARSET_INFO *cs)
{
uint i, j;
if (cs->mbminlen != 1)
{
DBUG_ASSERT(0);
return 1;
}
if (!str ||
(strlen((char*) str)+1 != sizeof(DEFAULT_FTB_SYNTAX)) ||
(length + 1 != sizeof(DEFAULT_FTB_SYNTAX)) ||
(str[0] != ' ' && str[1] != ' '))
return 1;
for (i=0; i<sizeof(DEFAULT_FTB_SYNTAX); i++)
{
/* limiting to 7-bit ascii only */
if ((unsigned char)(str[i]) > 127 || my_isalnum(default_charset_info, str[i]))
if ((unsigned char)(str[i]) > 127 || my_isalnum(cs, str[i]))
return 1;
for (j=0; j<i; j++)
if (str[i] == str[j] && (i != 11 || j != 10))